Merge tag 'drm-intel-next-2015-01-17' of git://anongit.freedesktop.org/drm-intel...
authorDave Airlie <airlied@redhat.com>
Mon, 26 Jan 2015 23:01:09 +0000 (09:01 +1000)
committerDave Airlie <airlied@redhat.com>
Mon, 26 Jan 2015 23:01:09 +0000 (09:01 +1000)
- refactor i915/snd-hda interaction to use the component framework (Imre)
- psr cleanups and small fixes (Rodrigo)
- a few perf w/a from Ken Graunke
- switch to atomic plane helpers (Matt Roper)
- wc mmap support (Chris Wilson & Akash Goel)
- smaller things all over

* tag 'drm-intel-next-2015-01-17' of git://anongit.freedesktop.org/drm-intel: (40 commits)
  drm/i915: Update DRIVER_DATE to 20150117
  i915: reuse %ph to dump small buffers
  drm/i915: Ensure the HiZ RAW Stall Optimization is on for Cherryview.
  drm/i915: Enable the HiZ RAW Stall Optimization on Broadwell.
  drm/i915: PSR link standby at debugfs
  drm/i915: group link_standby setup and let this info visible everywhere.
  drm/i915: Add missing vbt check.
  drm/i915: PSR HSW/BDW: Fix inverted logic at sink main_link_active bit.
  drm/i915: PSR VLV/CHV: Remove condition checks that only applies to Haswell.
  drm/i915: VLV/CHV PSR needs to exit PSR on every flush.
  drm/i915: Fix kerneldoc for i915 atomic plane code
  drm/i915: Don't pretend SDVO hotplug works on 915
  drm/i915: Don't register HDMI connectors for eDP ports on VLV/CHV
  drm/i915: Remove I915_HAS_HOTPLUG() check from i915_hpd_irq_setup()
  drm/i915: Make hpd arrays big enough to avoid out of bounds access
  Revert "drm/i915/chv: Use timeout mode for RC6 on chv"
  drm/i915: Improve HiZ throughput on Cherryview.
  drm/i915: Reset CSB read pointer in ring init
  drm/i915: Drop unused position fields (v2)
  drm/i915: Move to atomic plane helpers (v9)
  ...

1720 files changed:
Documentation/ABI/testing/sysfs-class-mei
Documentation/DocBook/drm.tmpl
Documentation/devicetree/bindings/drm/atmel/hlcdc-dc.txt [new file with mode: 0644]
Documentation/devicetree/bindings/drm/bridge/dw_hdmi.txt [new file with mode: 0644]
Documentation/devicetree/bindings/gpu/st,stih4xx.txt
Documentation/devicetree/bindings/net/davinci_emac.txt
Documentation/devicetree/bindings/video/dw_hdmi-rockchip.txt [new file with mode: 0644]
Documentation/devicetree/bindings/video/renesas,du.txt
Documentation/kernel-parameters.txt
Documentation/networking/ip-sysctl.txt
Documentation/target/tcm_mod_builder.py
Documentation/thermal/cpu-cooling-api.txt
MAINTAINERS
Makefile
arch/arm/boot/dts/at91sam9263.dtsi
arch/arm/boot/dts/berlin2q-marvell-dmp.dts
arch/arm/boot/dts/berlin2q.dtsi
arch/arm/boot/dts/dra7-evm.dts
arch/arm/boot/dts/exynos5250.dtsi
arch/arm/boot/dts/exynos5420-arndale-octa.dts
arch/arm/boot/dts/exynos5420.dtsi
arch/arm/boot/dts/imx25.dtsi
arch/arm/boot/dts/imx51-babbage.dts
arch/arm/boot/dts/imx6qdl.dtsi
arch/arm/boot/dts/imx6sx-sdb.dts
arch/arm/boot/dts/ls1021a.dtsi
arch/arm/boot/dts/omap3-n900.dts
arch/arm/boot/dts/rk3288-evb.dtsi
arch/arm/boot/dts/sama5d3xmb.dtsi
arch/arm/boot/dts/sama5d4.dtsi
arch/arm/boot/dts/ste-nomadik-nhk15.dts
arch/arm/boot/dts/vf610-twr.dts
arch/arm/configs/exynos_defconfig
arch/arm/configs/omap2plus_defconfig
arch/arm/mach-at91/board-dt-sama5.c
arch/arm/mach-imx/clk-imx6q.c
arch/arm/mach-imx/clk-imx6sx.c
arch/arm/mach-omap2/board-generic.c
arch/arm/mach-omap2/common.h
arch/arm/mach-omap2/control.h
arch/arm/mach-omap2/omap-headsmp.S
arch/arm/mach-omap2/omap-smp.c
arch/arm/mach-omap2/timer.c
arch/arm/mach-rockchip/rockchip.c
arch/arm/mach-shmobile/setup-r8a7740.c
arch/arm/mach-shmobile/setup-sh73a0.c
arch/arm64/include/asm/kvm_emulate.h
arch/arm64/include/asm/unistd.h
arch/arm64/include/asm/unistd32.h
arch/arm64/kvm/hyp.S
arch/arm64/kvm/reset.c
arch/arm64/mm/init.c
arch/m68k/include/asm/unistd.h
arch/m68k/include/uapi/asm/unistd.h
arch/m68k/kernel/syscalltable.S
arch/powerpc/crypto/sha1.c
arch/powerpc/include/asm/thread_info.h
arch/powerpc/platforms/powernv/opal-wrappers.S
arch/s390/hypfs/hypfs_vm.c
arch/s390/include/asm/irqflags.h
arch/s390/include/asm/timex.h
arch/s390/include/uapi/asm/unistd.h
arch/s390/kernel/syscalls.S
arch/s390/kernel/uprobes.c
arch/s390/kernel/vtime.c
arch/s390/mm/pgtable.c
arch/s390/net/bpf_jit_comp.c
arch/x86/crypto/sha-mb/sha1_mb.c
arch/x86/kernel/cpu/perf_event_intel_ds.c
arch/x86/kernel/cpu/perf_event_intel_rapl.c
arch/x86/kernel/kprobes/core.c
arch/x86/xen/enlighten.c
arch/x86/xen/p2m.c
arch/x86/xen/setup.c
arch/x86/xen/time.c
block/blk-core.c
block/blk-mq-tag.c
block/blk-mq-tag.h
block/blk-mq.c
block/blk-mq.h
block/blk-timeout.c
crypto/aes_generic.c
crypto/ansi_cprng.c
crypto/blowfish_generic.c
crypto/camellia_generic.c
crypto/cast5_generic.c
crypto/cast6_generic.c
crypto/crc32c_generic.c
crypto/crct10dif_generic.c
crypto/des_generic.c
crypto/ghash-generic.c
crypto/krng.c
crypto/salsa20_generic.c
crypto/serpent_generic.c
crypto/sha1_generic.c
crypto/sha256_generic.c
crypto/sha512_generic.c
crypto/tea.c
crypto/tgr192.c
crypto/twofish_generic.c
crypto/wp512.c
drivers/acpi/int340x_thermal.c
drivers/ata/Kconfig
drivers/ata/ahci.c
drivers/ata/ahci_xgene.c
drivers/ata/libahci.c
drivers/ata/libata-core.c
drivers/ata/libata-eh.c
drivers/ata/libata-scsi.c
drivers/ata/libata-sff.c
drivers/ata/sata_dwc_460ex.c
drivers/ata/sata_sil24.c
drivers/block/null_blk.c
drivers/block/nvme-core.c
drivers/block/virtio_blk.c
drivers/bus/arm-cci.c
drivers/clk/at91/clk-slow.c
drivers/clk/berlin/bg2q.c
drivers/clk/clk-ppc-corenet.c
drivers/clk/clk.c
drivers/clk/rockchip/clk-cpu.c
drivers/clk/rockchip/clk-rk3188.c
drivers/clk/rockchip/clk-rk3288.c
drivers/dma/dw/core.c
drivers/dma/dw/platform.c
drivers/gpio/gpio-crystalcove.c
drivers/gpio/gpio-dln2.c
drivers/gpio/gpio-grgpio.c
drivers/gpio/gpiolib-of.c
drivers/gpio/gpiolib-sysfs.c
drivers/gpio/gpiolib.c
drivers/gpio/gpiolib.h
drivers/gpu/drm/Kconfig
drivers/gpu/drm/Makefile
drivers/gpu/drm/amd/amdkfd/Makefile
drivers/gpu/drm/amd/amdkfd/cik_regs.h
drivers/gpu/drm/amd/amdkfd/kfd_chardev.c
drivers/gpu/drm/amd/amdkfd/kfd_device.c
drivers/gpu/drm/amd/amdkfd/kfd_device_queue_manager.c
drivers/gpu/drm/amd/amdkfd/kfd_device_queue_manager.h
drivers/gpu/drm/amd/amdkfd/kfd_device_queue_manager_cik.c [new file with mode: 0644]
drivers/gpu/drm/amd/amdkfd/kfd_device_queue_manager_vi.c [new file with mode: 0644]
drivers/gpu/drm/amd/amdkfd/kfd_doorbell.c
drivers/gpu/drm/amd/amdkfd/kfd_flat_memory.c
drivers/gpu/drm/amd/amdkfd/kfd_interrupt.c [deleted file]
drivers/gpu/drm/amd/amdkfd/kfd_kernel_queue.c
drivers/gpu/drm/amd/amdkfd/kfd_kernel_queue.h
drivers/gpu/drm/amd/amdkfd/kfd_kernel_queue_cik.c [new file with mode: 0644]
drivers/gpu/drm/amd/amdkfd/kfd_kernel_queue_vi.c [new file with mode: 0644]
drivers/gpu/drm/amd/amdkfd/kfd_module.c
drivers/gpu/drm/amd/amdkfd/kfd_mqd_manager.c
drivers/gpu/drm/amd/amdkfd/kfd_mqd_manager_cik.c [new file with mode: 0644]
drivers/gpu/drm/amd/amdkfd/kfd_mqd_manager_vi.c [new file with mode: 0644]
drivers/gpu/drm/amd/amdkfd/kfd_packet_manager.c
drivers/gpu/drm/amd/amdkfd/kfd_priv.h
drivers/gpu/drm/amd/amdkfd/kfd_process.c
drivers/gpu/drm/amd/amdkfd/kfd_process_queue_manager.c
drivers/gpu/drm/amd/amdkfd/kfd_topology.c
drivers/gpu/drm/amd/include/cik_structs.h [new file with mode: 0644]
drivers/gpu/drm/amd/include/kgd_kfd_interface.h
drivers/gpu/drm/armada/armada_crtc.c
drivers/gpu/drm/ast/ast_fb.c
drivers/gpu/drm/atmel-hlcdc/Kconfig [new file with mode: 0644]
drivers/gpu/drm/atmel-hlcdc/Makefile [new file with mode: 0644]
drivers/gpu/drm/atmel-hlcdc/atmel_hlcdc_crtc.c [new file with mode: 0644]
drivers/gpu/drm/atmel-hlcdc/atmel_hlcdc_dc.c [new file with mode: 0644]
drivers/gpu/drm/atmel-hlcdc/atmel_hlcdc_dc.h [new file with mode: 0644]
drivers/gpu/drm/atmel-hlcdc/atmel_hlcdc_layer.c [new file with mode: 0644]
drivers/gpu/drm/atmel-hlcdc/atmel_hlcdc_layer.h [new file with mode: 0644]
drivers/gpu/drm/atmel-hlcdc/atmel_hlcdc_output.c [new file with mode: 0644]
drivers/gpu/drm/atmel-hlcdc/atmel_hlcdc_plane.c [new file with mode: 0644]
drivers/gpu/drm/bochs/bochs_fbdev.c
drivers/gpu/drm/bochs/bochs_kms.c
drivers/gpu/drm/bridge/Kconfig
drivers/gpu/drm/bridge/Makefile
drivers/gpu/drm/bridge/dw_hdmi.c [new file with mode: 0644]
drivers/gpu/drm/bridge/dw_hdmi.h [new file with mode: 0644]
drivers/gpu/drm/cirrus/cirrus_fbdev.c
drivers/gpu/drm/drm_atomic.c
drivers/gpu/drm/drm_atomic_helper.c
drivers/gpu/drm/drm_cache.c
drivers/gpu/drm/drm_crtc.c
drivers/gpu/drm/drm_crtc_helper.c
drivers/gpu/drm/drm_crtc_internal.h
drivers/gpu/drm/drm_drv.c
drivers/gpu/drm/drm_fb_helper.c
drivers/gpu/drm/drm_fops.c
drivers/gpu/drm/drm_info.c
drivers/gpu/drm/drm_internal.h
drivers/gpu/drm/drm_ioctl.c
drivers/gpu/drm/drm_irq.c
drivers/gpu/drm/drm_modes.c
drivers/gpu/drm/drm_plane_helper.c
drivers/gpu/drm/drm_probe_helper.c
drivers/gpu/drm/exynos/Kconfig
drivers/gpu/drm/exynos/exynos_drm_drv.c
drivers/gpu/drm/exynos/exynos_hdmi.c
drivers/gpu/drm/exynos/exynos_mixer.c
drivers/gpu/drm/gma500/framebuffer.c
drivers/gpu/drm/i2c/adv7511.c
drivers/gpu/drm/i915/i915_gem.c
drivers/gpu/drm/i915/i915_irq.c
drivers/gpu/drm/i915/intel_display.c
drivers/gpu/drm/i915/intel_drv.h
drivers/gpu/drm/i915/intel_pm.c
drivers/gpu/drm/imx/Kconfig
drivers/gpu/drm/imx/Makefile
drivers/gpu/drm/imx/dw_hdmi-imx.c [new file with mode: 0644]
drivers/gpu/drm/imx/imx-drm-core.c
drivers/gpu/drm/imx/imx-drm.h
drivers/gpu/drm/imx/imx-hdmi.c [deleted file]
drivers/gpu/drm/imx/imx-hdmi.h [deleted file]
drivers/gpu/drm/imx/imx-ldb.c
drivers/gpu/drm/imx/imx-tve.c
drivers/gpu/drm/imx/ipuv3-crtc.c
drivers/gpu/drm/imx/parallel-display.c
drivers/gpu/drm/mgag200/mgag200_fb.c
drivers/gpu/drm/msm/mdp/mdp4/mdp4_crtc.c
drivers/gpu/drm/msm/mdp/mdp5/mdp5_crtc.c
drivers/gpu/drm/msm/mdp/mdp5/mdp5_plane.c
drivers/gpu/drm/msm/msm_atomic.c
drivers/gpu/drm/msm/msm_drv.c
drivers/gpu/drm/msm/msm_drv.h
drivers/gpu/drm/msm/msm_fbdev.c
drivers/gpu/drm/nouveau/Kbuild [new file with mode: 0644]
drivers/gpu/drm/nouveau/Kconfig
drivers/gpu/drm/nouveau/Makefile [deleted file]
drivers/gpu/drm/nouveau/core/core/client.c [deleted file]
drivers/gpu/drm/nouveau/core/core/engctx.c [deleted file]
drivers/gpu/drm/nouveau/core/core/engine.c [deleted file]
drivers/gpu/drm/nouveau/core/core/enum.c [deleted file]
drivers/gpu/drm/nouveau/core/core/event.c [deleted file]
drivers/gpu/drm/nouveau/core/core/gpuobj.c [deleted file]
drivers/gpu/drm/nouveau/core/core/handle.c [deleted file]
drivers/gpu/drm/nouveau/core/core/ioctl.c [deleted file]
drivers/gpu/drm/nouveau/core/core/mm.c [deleted file]
drivers/gpu/drm/nouveau/core/core/namedb.c [deleted file]
drivers/gpu/drm/nouveau/core/core/notify.c [deleted file]
drivers/gpu/drm/nouveau/core/core/object.c [deleted file]
drivers/gpu/drm/nouveau/core/core/option.c [deleted file]
drivers/gpu/drm/nouveau/core/core/parent.c [deleted file]
drivers/gpu/drm/nouveau/core/core/printk.c [deleted file]
drivers/gpu/drm/nouveau/core/core/ramht.c [deleted file]
drivers/gpu/drm/nouveau/core/core/subdev.c [deleted file]
drivers/gpu/drm/nouveau/core/engine/bsp/nv84.c [deleted file]
drivers/gpu/drm/nouveau/core/engine/bsp/nv98.c [deleted file]
drivers/gpu/drm/nouveau/core/engine/bsp/nvc0.c [deleted file]
drivers/gpu/drm/nouveau/core/engine/bsp/nve0.c [deleted file]
drivers/gpu/drm/nouveau/core/engine/copy/fuc/nva3.fuc [deleted file]
drivers/gpu/drm/nouveau/core/engine/copy/fuc/nva3.fuc.h [deleted file]
drivers/gpu/drm/nouveau/core/engine/copy/fuc/nvc0.fuc.h [deleted file]
drivers/gpu/drm/nouveau/core/engine/copy/nva3.c [deleted file]
drivers/gpu/drm/nouveau/core/engine/copy/nvc0.c [deleted file]
drivers/gpu/drm/nouveau/core/engine/copy/nve0.c [deleted file]
drivers/gpu/drm/nouveau/core/engine/crypt/fuc/nv98.fuc [deleted file]
drivers/gpu/drm/nouveau/core/engine/crypt/fuc/nv98.fuc.h [deleted file]
drivers/gpu/drm/nouveau/core/engine/crypt/nv84.c [deleted file]
drivers/gpu/drm/nouveau/core/engine/crypt/nv98.c [deleted file]
drivers/gpu/drm/nouveau/core/engine/device/acpi.c [deleted file]
drivers/gpu/drm/nouveau/core/engine/device/acpi.h [deleted file]
drivers/gpu/drm/nouveau/core/engine/device/base.c [deleted file]
drivers/gpu/drm/nouveau/core/engine/device/ctrl.c [deleted file]
drivers/gpu/drm/nouveau/core/engine/device/gm100.c [deleted file]
drivers/gpu/drm/nouveau/core/engine/device/nv04.c [deleted file]
drivers/gpu/drm/nouveau/core/engine/device/nv10.c [deleted file]
drivers/gpu/drm/nouveau/core/engine/device/nv20.c [deleted file]
drivers/gpu/drm/nouveau/core/engine/device/nv30.c [deleted file]
drivers/gpu/drm/nouveau/core/engine/device/nv40.c [deleted file]
drivers/gpu/drm/nouveau/core/engine/device/nv50.c [deleted file]
drivers/gpu/drm/nouveau/core/engine/device/nvc0.c [deleted file]
drivers/gpu/drm/nouveau/core/engine/device/nve0.c [deleted file]
drivers/gpu/drm/nouveau/core/engine/device/priv.h [deleted file]
drivers/gpu/drm/nouveau/core/engine/disp/base.c [deleted file]
drivers/gpu/drm/nouveau/core/engine/disp/conn.c [deleted file]
drivers/gpu/drm/nouveau/core/engine/disp/conn.h [deleted file]
drivers/gpu/drm/nouveau/core/engine/disp/dacnv50.c [deleted file]
drivers/gpu/drm/nouveau/core/engine/disp/dport.c [deleted file]
drivers/gpu/drm/nouveau/core/engine/disp/dport.h [deleted file]
drivers/gpu/drm/nouveau/core/engine/disp/gm107.c [deleted file]
drivers/gpu/drm/nouveau/core/engine/disp/gm204.c [deleted file]
drivers/gpu/drm/nouveau/core/engine/disp/hdanva3.c [deleted file]
drivers/gpu/drm/nouveau/core/engine/disp/hdanvd0.c [deleted file]
drivers/gpu/drm/nouveau/core/engine/disp/hdminv84.c [deleted file]
drivers/gpu/drm/nouveau/core/engine/disp/hdminva3.c [deleted file]
drivers/gpu/drm/nouveau/core/engine/disp/hdminvd0.c [deleted file]
drivers/gpu/drm/nouveau/core/engine/disp/hdminve0.c [deleted file]
drivers/gpu/drm/nouveau/core/engine/disp/nv04.c [deleted file]
drivers/gpu/drm/nouveau/core/engine/disp/nv50.c [deleted file]
drivers/gpu/drm/nouveau/core/engine/disp/nv50.h [deleted file]
drivers/gpu/drm/nouveau/core/engine/disp/nv84.c [deleted file]
drivers/gpu/drm/nouveau/core/engine/disp/nv94.c [deleted file]
drivers/gpu/drm/nouveau/core/engine/disp/nva0.c [deleted file]
drivers/gpu/drm/nouveau/core/engine/disp/nva3.c [deleted file]
drivers/gpu/drm/nouveau/core/engine/disp/nvd0.c [deleted file]
drivers/gpu/drm/nouveau/core/engine/disp/nve0.c [deleted file]
drivers/gpu/drm/nouveau/core/engine/disp/nvf0.c [deleted file]
drivers/gpu/drm/nouveau/core/engine/disp/outp.c [deleted file]
drivers/gpu/drm/nouveau/core/engine/disp/outp.h [deleted file]
drivers/gpu/drm/nouveau/core/engine/disp/outpdp.c [deleted file]
drivers/gpu/drm/nouveau/core/engine/disp/outpdp.h [deleted file]
drivers/gpu/drm/nouveau/core/engine/disp/piornv50.c [deleted file]
drivers/gpu/drm/nouveau/core/engine/disp/priv.h [deleted file]
drivers/gpu/drm/nouveau/core/engine/disp/sorgm204.c [deleted file]
drivers/gpu/drm/nouveau/core/engine/disp/sornv50.c [deleted file]
drivers/gpu/drm/nouveau/core/engine/disp/sornv94.c [deleted file]
drivers/gpu/drm/nouveau/core/engine/disp/sornvd0.c [deleted file]
drivers/gpu/drm/nouveau/core/engine/disp/vga.c [deleted file]
drivers/gpu/drm/nouveau/core/engine/dmaobj/base.c [deleted file]
drivers/gpu/drm/nouveau/core/engine/dmaobj/nv04.c [deleted file]
drivers/gpu/drm/nouveau/core/engine/dmaobj/nv50.c [deleted file]
drivers/gpu/drm/nouveau/core/engine/dmaobj/nvc0.c [deleted file]
drivers/gpu/drm/nouveau/core/engine/dmaobj/nvd0.c [deleted file]
drivers/gpu/drm/nouveau/core/engine/dmaobj/priv.h [deleted file]
drivers/gpu/drm/nouveau/core/engine/falcon.c [deleted file]
drivers/gpu/drm/nouveau/core/engine/fifo/base.c [deleted file]
drivers/gpu/drm/nouveau/core/engine/fifo/gk20a.c [deleted file]
drivers/gpu/drm/nouveau/core/engine/fifo/nv04.c [deleted file]
drivers/gpu/drm/nouveau/core/engine/fifo/nv04.h [deleted file]
drivers/gpu/drm/nouveau/core/engine/fifo/nv10.c [deleted file]
drivers/gpu/drm/nouveau/core/engine/fifo/nv108.c [deleted file]
drivers/gpu/drm/nouveau/core/engine/fifo/nv17.c [deleted file]
drivers/gpu/drm/nouveau/core/engine/fifo/nv40.c [deleted file]
drivers/gpu/drm/nouveau/core/engine/fifo/nv50.c [deleted file]
drivers/gpu/drm/nouveau/core/engine/fifo/nv50.h [deleted file]
drivers/gpu/drm/nouveau/core/engine/fifo/nv84.c [deleted file]
drivers/gpu/drm/nouveau/core/engine/fifo/nvc0.c [deleted file]
drivers/gpu/drm/nouveau/core/engine/fifo/nve0.c [deleted file]
drivers/gpu/drm/nouveau/core/engine/fifo/nve0.h [deleted file]
drivers/gpu/drm/nouveau/core/engine/graph/ctx.h [deleted file]
drivers/gpu/drm/nouveau/core/engine/graph/ctxgk110b.c [deleted file]
drivers/gpu/drm/nouveau/core/engine/graph/ctxgk20a.c [deleted file]
drivers/gpu/drm/nouveau/core/engine/graph/ctxgm107.c [deleted file]
drivers/gpu/drm/nouveau/core/engine/graph/ctxnv108.c [deleted file]
drivers/gpu/drm/nouveau/core/engine/graph/ctxnv40.c [deleted file]
drivers/gpu/drm/nouveau/core/engine/graph/ctxnv50.c [deleted file]
drivers/gpu/drm/nouveau/core/engine/graph/ctxnvc0.c [deleted file]
drivers/gpu/drm/nouveau/core/engine/graph/ctxnvc0.h [deleted file]
drivers/gpu/drm/nouveau/core/engine/graph/ctxnvc1.c [deleted file]
drivers/gpu/drm/nouveau/core/engine/graph/ctxnvc4.c [deleted file]
drivers/gpu/drm/nouveau/core/engine/graph/ctxnvc8.c [deleted file]
drivers/gpu/drm/nouveau/core/engine/graph/ctxnvd7.c [deleted file]
drivers/gpu/drm/nouveau/core/engine/graph/ctxnvd9.c [deleted file]
drivers/gpu/drm/nouveau/core/engine/graph/ctxnve4.c [deleted file]
drivers/gpu/drm/nouveau/core/engine/graph/ctxnvf0.c [deleted file]
drivers/gpu/drm/nouveau/core/engine/graph/fuc/com.fuc [deleted file]
drivers/gpu/drm/nouveau/core/engine/graph/fuc/gpc.fuc [deleted file]
drivers/gpu/drm/nouveau/core/engine/graph/fuc/gpcgm107.fuc5 [deleted file]
drivers/gpu/drm/nouveau/core/engine/graph/fuc/gpcgm107.fuc5.h [deleted file]
drivers/gpu/drm/nouveau/core/engine/graph/fuc/gpcnv108.fuc5 [deleted file]
drivers/gpu/drm/nouveau/core/engine/graph/fuc/gpcnv108.fuc5.h [deleted file]
drivers/gpu/drm/nouveau/core/engine/graph/fuc/gpcnvc0.fuc [deleted file]
drivers/gpu/drm/nouveau/core/engine/graph/fuc/gpcnvc0.fuc.h [deleted file]
drivers/gpu/drm/nouveau/core/engine/graph/fuc/gpcnvd7.fuc [deleted file]
drivers/gpu/drm/nouveau/core/engine/graph/fuc/gpcnvd7.fuc.h [deleted file]
drivers/gpu/drm/nouveau/core/engine/graph/fuc/gpcnve0.fuc [deleted file]
drivers/gpu/drm/nouveau/core/engine/graph/fuc/gpcnve0.fuc.h [deleted file]
drivers/gpu/drm/nouveau/core/engine/graph/fuc/gpcnvf0.fuc [deleted file]
drivers/gpu/drm/nouveau/core/engine/graph/fuc/gpcnvf0.fuc.h [deleted file]
drivers/gpu/drm/nouveau/core/engine/graph/fuc/hub.fuc [deleted file]
drivers/gpu/drm/nouveau/core/engine/graph/fuc/hubgm107.fuc5 [deleted file]
drivers/gpu/drm/nouveau/core/engine/graph/fuc/hubgm107.fuc5.h [deleted file]
drivers/gpu/drm/nouveau/core/engine/graph/fuc/hubnv108.fuc5 [deleted file]
drivers/gpu/drm/nouveau/core/engine/graph/fuc/hubnv108.fuc5.h [deleted file]
drivers/gpu/drm/nouveau/core/engine/graph/fuc/hubnvc0.fuc [deleted file]
drivers/gpu/drm/nouveau/core/engine/graph/fuc/hubnvc0.fuc.h [deleted file]
drivers/gpu/drm/nouveau/core/engine/graph/fuc/hubnvd7.fuc [deleted file]
drivers/gpu/drm/nouveau/core/engine/graph/fuc/hubnvd7.fuc.h [deleted file]
drivers/gpu/drm/nouveau/core/engine/graph/fuc/hubnve0.fuc [deleted file]
drivers/gpu/drm/nouveau/core/engine/graph/fuc/hubnve0.fuc.h [deleted file]
drivers/gpu/drm/nouveau/core/engine/graph/fuc/hubnvf0.fuc [deleted file]
drivers/gpu/drm/nouveau/core/engine/graph/fuc/hubnvf0.fuc.h [deleted file]
drivers/gpu/drm/nouveau/core/engine/graph/fuc/macros.fuc [deleted file]
drivers/gpu/drm/nouveau/core/engine/graph/fuc/os.h [deleted file]
drivers/gpu/drm/nouveau/core/engine/graph/gk110b.c [deleted file]
drivers/gpu/drm/nouveau/core/engine/graph/gk20a.c [deleted file]
drivers/gpu/drm/nouveau/core/engine/graph/gm107.c [deleted file]
drivers/gpu/drm/nouveau/core/engine/graph/nv04.c [deleted file]
drivers/gpu/drm/nouveau/core/engine/graph/nv10.c [deleted file]
drivers/gpu/drm/nouveau/core/engine/graph/nv108.c [deleted file]
drivers/gpu/drm/nouveau/core/engine/graph/nv20.c [deleted file]
drivers/gpu/drm/nouveau/core/engine/graph/nv20.h [deleted file]
drivers/gpu/drm/nouveau/core/engine/graph/nv25.c [deleted file]
drivers/gpu/drm/nouveau/core/engine/graph/nv2a.c [deleted file]
drivers/gpu/drm/nouveau/core/engine/graph/nv30.c [deleted file]
drivers/gpu/drm/nouveau/core/engine/graph/nv34.c [deleted file]
drivers/gpu/drm/nouveau/core/engine/graph/nv35.c [deleted file]
drivers/gpu/drm/nouveau/core/engine/graph/nv40.c [deleted file]
drivers/gpu/drm/nouveau/core/engine/graph/nv40.h [deleted file]
drivers/gpu/drm/nouveau/core/engine/graph/nv50.c [deleted file]
drivers/gpu/drm/nouveau/core/engine/graph/nv50.h [deleted file]
drivers/gpu/drm/nouveau/core/engine/graph/nvc0.c [deleted file]
drivers/gpu/drm/nouveau/core/engine/graph/nvc0.h [deleted file]
drivers/gpu/drm/nouveau/core/engine/graph/nvc1.c [deleted file]
drivers/gpu/drm/nouveau/core/engine/graph/nvc4.c [deleted file]
drivers/gpu/drm/nouveau/core/engine/graph/nvc8.c [deleted file]
drivers/gpu/drm/nouveau/core/engine/graph/nvd7.c [deleted file]
drivers/gpu/drm/nouveau/core/engine/graph/nvd9.c [deleted file]
drivers/gpu/drm/nouveau/core/engine/graph/nve4.c [deleted file]
drivers/gpu/drm/nouveau/core/engine/graph/nvf0.c [deleted file]
drivers/gpu/drm/nouveau/core/engine/graph/regs.h [deleted file]
drivers/gpu/drm/nouveau/core/engine/mpeg/nv31.c [deleted file]
drivers/gpu/drm/nouveau/core/engine/mpeg/nv31.h [deleted file]
drivers/gpu/drm/nouveau/core/engine/mpeg/nv40.c [deleted file]
drivers/gpu/drm/nouveau/core/engine/mpeg/nv44.c [deleted file]
drivers/gpu/drm/nouveau/core/engine/mpeg/nv50.c [deleted file]
drivers/gpu/drm/nouveau/core/engine/mpeg/nv84.c [deleted file]
drivers/gpu/drm/nouveau/core/engine/perfmon/base.c [deleted file]
drivers/gpu/drm/nouveau/core/engine/perfmon/daemon.c [deleted file]
drivers/gpu/drm/nouveau/core/engine/perfmon/nv40.c [deleted file]
drivers/gpu/drm/nouveau/core/engine/perfmon/nv40.h [deleted file]
drivers/gpu/drm/nouveau/core/engine/perfmon/nv50.c [deleted file]
drivers/gpu/drm/nouveau/core/engine/perfmon/nv84.c [deleted file]
drivers/gpu/drm/nouveau/core/engine/perfmon/nva3.c [deleted file]
drivers/gpu/drm/nouveau/core/engine/perfmon/nvc0.c [deleted file]
drivers/gpu/drm/nouveau/core/engine/perfmon/nvc0.h [deleted file]
drivers/gpu/drm/nouveau/core/engine/perfmon/nve0.c [deleted file]
drivers/gpu/drm/nouveau/core/engine/perfmon/nvf0.c [deleted file]
drivers/gpu/drm/nouveau/core/engine/perfmon/priv.h [deleted file]
drivers/gpu/drm/nouveau/core/engine/ppp/nv98.c [deleted file]
drivers/gpu/drm/nouveau/core/engine/ppp/nvc0.c [deleted file]
drivers/gpu/drm/nouveau/core/engine/software/nv04.c [deleted file]
drivers/gpu/drm/nouveau/core/engine/software/nv10.c [deleted file]
drivers/gpu/drm/nouveau/core/engine/software/nv50.c [deleted file]
drivers/gpu/drm/nouveau/core/engine/software/nv50.h [deleted file]
drivers/gpu/drm/nouveau/core/engine/software/nvc0.c [deleted file]
drivers/gpu/drm/nouveau/core/engine/vp/nv84.c [deleted file]
drivers/gpu/drm/nouveau/core/engine/vp/nv98.c [deleted file]
drivers/gpu/drm/nouveau/core/engine/vp/nvc0.c [deleted file]
drivers/gpu/drm/nouveau/core/engine/vp/nve0.c [deleted file]
drivers/gpu/drm/nouveau/core/engine/xtensa.c [deleted file]
drivers/gpu/drm/nouveau/core/include/core/client.h [deleted file]
drivers/gpu/drm/nouveau/core/include/core/debug.h [deleted file]
drivers/gpu/drm/nouveau/core/include/core/device.h [deleted file]
drivers/gpu/drm/nouveau/core/include/core/engctx.h [deleted file]
drivers/gpu/drm/nouveau/core/include/core/engine.h [deleted file]
drivers/gpu/drm/nouveau/core/include/core/enum.h [deleted file]
drivers/gpu/drm/nouveau/core/include/core/event.h [deleted file]
drivers/gpu/drm/nouveau/core/include/core/gpuobj.h [deleted file]
drivers/gpu/drm/nouveau/core/include/core/handle.h [deleted file]
drivers/gpu/drm/nouveau/core/include/core/ioctl.h [deleted file]
drivers/gpu/drm/nouveau/core/include/core/mm.h [deleted file]
drivers/gpu/drm/nouveau/core/include/core/namedb.h [deleted file]
drivers/gpu/drm/nouveau/core/include/core/notify.h [deleted file]
drivers/gpu/drm/nouveau/core/include/core/object.h [deleted file]
drivers/gpu/drm/nouveau/core/include/core/option.h [deleted file]
drivers/gpu/drm/nouveau/core/include/core/parent.h [deleted file]
drivers/gpu/drm/nouveau/core/include/core/printk.h [deleted file]
drivers/gpu/drm/nouveau/core/include/core/ramht.h [deleted file]
drivers/gpu/drm/nouveau/core/include/core/subdev.h [deleted file]
drivers/gpu/drm/nouveau/core/include/engine/bsp.h [deleted file]
drivers/gpu/drm/nouveau/core/include/engine/copy.h [deleted file]
drivers/gpu/drm/nouveau/core/include/engine/crypt.h [deleted file]
drivers/gpu/drm/nouveau/core/include/engine/device.h [deleted file]
drivers/gpu/drm/nouveau/core/include/engine/disp.h [deleted file]
drivers/gpu/drm/nouveau/core/include/engine/dmaobj.h [deleted file]
drivers/gpu/drm/nouveau/core/include/engine/falcon.h [deleted file]
drivers/gpu/drm/nouveau/core/include/engine/fifo.h [deleted file]
drivers/gpu/drm/nouveau/core/include/engine/graph.h [deleted file]
drivers/gpu/drm/nouveau/core/include/engine/mpeg.h [deleted file]
drivers/gpu/drm/nouveau/core/include/engine/perfmon.h [deleted file]
drivers/gpu/drm/nouveau/core/include/engine/ppp.h [deleted file]
drivers/gpu/drm/nouveau/core/include/engine/software.h [deleted file]
drivers/gpu/drm/nouveau/core/include/engine/vp.h [deleted file]
drivers/gpu/drm/nouveau/core/include/engine/xtensa.h [deleted file]
drivers/gpu/drm/nouveau/core/include/nvif/class.h [deleted symlink]
drivers/gpu/drm/nouveau/core/include/nvif/event.h [deleted symlink]
drivers/gpu/drm/nouveau/core/include/nvif/ioctl.h [deleted symlink]
drivers/gpu/drm/nouveau/core/include/nvif/unpack.h [deleted symlink]
drivers/gpu/drm/nouveau/core/include/subdev/bar.h [deleted file]
drivers/gpu/drm/nouveau/core/include/subdev/bios.h [deleted file]
drivers/gpu/drm/nouveau/core/include/subdev/bios/M0203.h [deleted file]
drivers/gpu/drm/nouveau/core/include/subdev/bios/M0205.h [deleted file]
drivers/gpu/drm/nouveau/core/include/subdev/bios/M0209.h [deleted file]
drivers/gpu/drm/nouveau/core/include/subdev/bios/P0260.h [deleted file]
drivers/gpu/drm/nouveau/core/include/subdev/bios/bit.h [deleted file]
drivers/gpu/drm/nouveau/core/include/subdev/bios/bmp.h [deleted file]
drivers/gpu/drm/nouveau/core/include/subdev/bios/boost.h [deleted file]
drivers/gpu/drm/nouveau/core/include/subdev/bios/conn.h [deleted file]
drivers/gpu/drm/nouveau/core/include/subdev/bios/cstep.h [deleted file]
drivers/gpu/drm/nouveau/core/include/subdev/bios/dcb.h [deleted file]
drivers/gpu/drm/nouveau/core/include/subdev/bios/disp.h [deleted file]
drivers/gpu/drm/nouveau/core/include/subdev/bios/dp.h [deleted file]
drivers/gpu/drm/nouveau/core/include/subdev/bios/extdev.h [deleted file]
drivers/gpu/drm/nouveau/core/include/subdev/bios/fan.h [deleted file]
drivers/gpu/drm/nouveau/core/include/subdev/bios/gpio.h [deleted file]
drivers/gpu/drm/nouveau/core/include/subdev/bios/i2c.h [deleted file]
drivers/gpu/drm/nouveau/core/include/subdev/bios/image.h [deleted file]
drivers/gpu/drm/nouveau/core/include/subdev/bios/init.h [deleted file]
drivers/gpu/drm/nouveau/core/include/subdev/bios/mxm.h [deleted file]
drivers/gpu/drm/nouveau/core/include/subdev/bios/npde.h [deleted file]
drivers/gpu/drm/nouveau/core/include/subdev/bios/pcir.h [deleted file]
drivers/gpu/drm/nouveau/core/include/subdev/bios/perf.h [deleted file]
drivers/gpu/drm/nouveau/core/include/subdev/bios/pll.h [deleted file]
drivers/gpu/drm/nouveau/core/include/subdev/bios/pmu.h [deleted file]
drivers/gpu/drm/nouveau/core/include/subdev/bios/ramcfg.h [deleted file]
drivers/gpu/drm/nouveau/core/include/subdev/bios/rammap.h [deleted file]
drivers/gpu/drm/nouveau/core/include/subdev/bios/therm.h [deleted file]
drivers/gpu/drm/nouveau/core/include/subdev/bios/timing.h [deleted file]
drivers/gpu/drm/nouveau/core/include/subdev/bios/vmap.h [deleted file]
drivers/gpu/drm/nouveau/core/include/subdev/bios/volt.h [deleted file]
drivers/gpu/drm/nouveau/core/include/subdev/bios/xpio.h [deleted file]
drivers/gpu/drm/nouveau/core/include/subdev/bus.h [deleted file]
drivers/gpu/drm/nouveau/core/include/subdev/clock.h [deleted file]
drivers/gpu/drm/nouveau/core/include/subdev/devinit.h [deleted file]
drivers/gpu/drm/nouveau/core/include/subdev/fb.h [deleted file]
drivers/gpu/drm/nouveau/core/include/subdev/fb/regsnv04.h [deleted file]
drivers/gpu/drm/nouveau/core/include/subdev/fuse.h [deleted file]
drivers/gpu/drm/nouveau/core/include/subdev/gpio.h [deleted file]
drivers/gpu/drm/nouveau/core/include/subdev/i2c.h [deleted file]
drivers/gpu/drm/nouveau/core/include/subdev/ibus.h [deleted file]
drivers/gpu/drm/nouveau/core/include/subdev/instmem.h [deleted file]
drivers/gpu/drm/nouveau/core/include/subdev/ltc.h [deleted file]
drivers/gpu/drm/nouveau/core/include/subdev/mc.h [deleted file]
drivers/gpu/drm/nouveau/core/include/subdev/mxm.h [deleted file]
drivers/gpu/drm/nouveau/core/include/subdev/pwr.h [deleted file]
drivers/gpu/drm/nouveau/core/include/subdev/therm.h [deleted file]
drivers/gpu/drm/nouveau/core/include/subdev/timer.h [deleted file]
drivers/gpu/drm/nouveau/core/include/subdev/vga.h [deleted file]
drivers/gpu/drm/nouveau/core/include/subdev/vm.h [deleted file]
drivers/gpu/drm/nouveau/core/include/subdev/volt.h [deleted file]
drivers/gpu/drm/nouveau/core/os.h [deleted file]
drivers/gpu/drm/nouveau/core/subdev/bar/base.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/bar/gk20a.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/bar/nv50.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/bar/nvc0.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/bar/priv.h [deleted file]
drivers/gpu/drm/nouveau/core/subdev/bios/M0203.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/bios/M0205.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/bios/M0209.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/bios/P0260.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/bios/base.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/bios/bit.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/bios/boost.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/bios/conn.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/bios/cstep.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/bios/dcb.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/bios/disp.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/bios/dp.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/bios/extdev.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/bios/fan.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/bios/gpio.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/bios/i2c.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/bios/image.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/bios/init.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/bios/mxm.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/bios/npde.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/bios/pcir.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/bios/perf.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/bios/pll.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/bios/pmu.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/bios/priv.h [deleted file]
drivers/gpu/drm/nouveau/core/subdev/bios/ramcfg.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/bios/rammap.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/bios/shadow.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/bios/shadowacpi.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/bios/shadowof.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/bios/shadowpci.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/bios/shadowramin.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/bios/shadowrom.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/bios/therm.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/bios/timing.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/bios/vmap.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/bios/volt.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/bios/xpio.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/bus/hwsq.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/bus/hwsq.h [deleted file]
drivers/gpu/drm/nouveau/core/subdev/bus/nv04.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/bus/nv04.h [deleted file]
drivers/gpu/drm/nouveau/core/subdev/bus/nv31.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/bus/nv50.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/bus/nv94.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/bus/nvc0.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/clock/base.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/clock/gk20a.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/clock/nv04.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/clock/nv40.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/clock/nv50.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/clock/nv50.h [deleted file]
drivers/gpu/drm/nouveau/core/subdev/clock/nv84.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/clock/nva3.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/clock/nva3.h [deleted file]
drivers/gpu/drm/nouveau/core/subdev/clock/nvaa.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/clock/nvc0.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/clock/nve0.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/clock/pll.h [deleted file]
drivers/gpu/drm/nouveau/core/subdev/clock/pllnv04.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/clock/pllnva3.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/clock/seq.h [deleted file]
drivers/gpu/drm/nouveau/core/subdev/devinit/base.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/devinit/fbmem.h [deleted file]
drivers/gpu/drm/nouveau/core/subdev/devinit/gm107.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/devinit/gm204.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/devinit/nv04.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/devinit/nv04.h [deleted file]
drivers/gpu/drm/nouveau/core/subdev/devinit/nv05.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/devinit/nv10.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/devinit/nv1a.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/devinit/nv20.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/devinit/nv50.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/devinit/nv50.h [deleted file]
drivers/gpu/drm/nouveau/core/subdev/devinit/nv84.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/devinit/nv98.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/devinit/nva3.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/devinit/nvaf.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/devinit/nvc0.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/devinit/priv.h [deleted file]
drivers/gpu/drm/nouveau/core/subdev/fb/base.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/fb/gddr3.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/fb/gddr5.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/fb/gk20a.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/fb/gm107.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/fb/nv04.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/fb/nv04.h [deleted file]
drivers/gpu/drm/nouveau/core/subdev/fb/nv10.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/fb/nv1a.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/fb/nv20.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/fb/nv25.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/fb/nv30.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/fb/nv35.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/fb/nv36.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/fb/nv40.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/fb/nv40.h [deleted file]
drivers/gpu/drm/nouveau/core/subdev/fb/nv41.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/fb/nv44.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/fb/nv46.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/fb/nv47.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/fb/nv49.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/fb/nv4e.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/fb/nv50.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/fb/nv50.h [deleted file]
drivers/gpu/drm/nouveau/core/subdev/fb/nv84.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/fb/nva3.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/fb/nvaa.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/fb/nvaf.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/fb/nvc0.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/fb/nvc0.h [deleted file]
drivers/gpu/drm/nouveau/core/subdev/fb/nve0.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/fb/priv.h [deleted file]
drivers/gpu/drm/nouveau/core/subdev/fb/ramfuc.h [deleted file]
drivers/gpu/drm/nouveau/core/subdev/fb/ramgk20a.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/fb/ramgm107.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/fb/ramnv04.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/fb/ramnv10.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/fb/ramnv1a.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/fb/ramnv20.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/fb/ramnv40.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/fb/ramnv41.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/fb/ramnv44.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/fb/ramnv49.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/fb/ramnv4e.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/fb/ramnv50.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/fb/ramnva3.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/fb/ramnvaa.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/fb/ramnvc0.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/fb/ramnve0.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/fb/ramseq.h [deleted file]
drivers/gpu/drm/nouveau/core/subdev/fb/sddr2.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/fb/sddr3.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/fuse/base.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/fuse/g80.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/fuse/gf100.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/fuse/gm107.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/fuse/priv.h [deleted file]
drivers/gpu/drm/nouveau/core/subdev/gpio/base.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/gpio/nv10.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/gpio/nv50.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/gpio/nv94.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/gpio/nvd0.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/gpio/nve0.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/gpio/priv.h [deleted file]
drivers/gpu/drm/nouveau/core/subdev/i2c/anx9805.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/i2c/aux.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/i2c/base.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/i2c/bit.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/i2c/gf117.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/i2c/gm204.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/i2c/nv04.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/i2c/nv4e.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/i2c/nv50.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/i2c/nv50.h [deleted file]
drivers/gpu/drm/nouveau/core/subdev/i2c/nv94.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/i2c/nvd0.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/i2c/nve0.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/i2c/pad.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/i2c/pad.h [deleted file]
drivers/gpu/drm/nouveau/core/subdev/i2c/padgm204.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/i2c/padnv04.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/i2c/padnv94.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/i2c/port.h [deleted file]
drivers/gpu/drm/nouveau/core/subdev/i2c/priv.h [deleted file]
drivers/gpu/drm/nouveau/core/subdev/ibus/gk20a.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/ibus/nvc0.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/ibus/nve0.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/instmem/base.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/instmem/nv04.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/instmem/nv04.h [deleted file]
drivers/gpu/drm/nouveau/core/subdev/instmem/nv40.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/instmem/nv50.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/instmem/priv.h [deleted file]
drivers/gpu/drm/nouveau/core/subdev/ltc/base.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/ltc/gf100.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/ltc/gk104.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/ltc/gm107.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/ltc/priv.h [deleted file]
drivers/gpu/drm/nouveau/core/subdev/mc/base.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/mc/gk20a.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/mc/nv04.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/mc/nv04.h [deleted file]
drivers/gpu/drm/nouveau/core/subdev/mc/nv40.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/mc/nv44.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/mc/nv4c.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/mc/nv50.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/mc/nv94.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/mc/nv98.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/mc/nvc0.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/mc/nvc3.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/mc/priv.h [deleted file]
drivers/gpu/drm/nouveau/core/subdev/mxm/base.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/mxm/mxms.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/mxm/mxms.h [deleted file]
drivers/gpu/drm/nouveau/core/subdev/mxm/nv50.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/pwr/base.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/pwr/fuc/arith.fuc [deleted file]
drivers/gpu/drm/nouveau/core/subdev/pwr/fuc/host.fuc [deleted file]
drivers/gpu/drm/nouveau/core/subdev/pwr/fuc/i2c_.fuc [deleted file]
drivers/gpu/drm/nouveau/core/subdev/pwr/fuc/idle.fuc [deleted file]
drivers/gpu/drm/nouveau/core/subdev/pwr/fuc/kernel.fuc [deleted file]
drivers/gpu/drm/nouveau/core/subdev/pwr/fuc/macros.fuc [deleted file]
drivers/gpu/drm/nouveau/core/subdev/pwr/fuc/memx.fuc [deleted file]
drivers/gpu/drm/nouveau/core/subdev/pwr/fuc/nv108.fuc [deleted file]
drivers/gpu/drm/nouveau/core/subdev/pwr/fuc/nv108.fuc.h [deleted file]
drivers/gpu/drm/nouveau/core/subdev/pwr/fuc/nva3.fuc [deleted file]
drivers/gpu/drm/nouveau/core/subdev/pwr/fuc/nva3.fuc.h [deleted file]
drivers/gpu/drm/nouveau/core/subdev/pwr/fuc/nvc0.fuc [deleted file]
drivers/gpu/drm/nouveau/core/subdev/pwr/fuc/nvc0.fuc.h [deleted file]
drivers/gpu/drm/nouveau/core/subdev/pwr/fuc/nvd0.fuc [deleted file]
drivers/gpu/drm/nouveau/core/subdev/pwr/fuc/nvd0.fuc.h [deleted file]
drivers/gpu/drm/nouveau/core/subdev/pwr/fuc/os.h [deleted file]
drivers/gpu/drm/nouveau/core/subdev/pwr/fuc/perf.fuc [deleted file]
drivers/gpu/drm/nouveau/core/subdev/pwr/fuc/test.fuc [deleted file]
drivers/gpu/drm/nouveau/core/subdev/pwr/gk104.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/pwr/memx.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/pwr/nv108.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/pwr/nva3.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/pwr/nvc0.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/pwr/nvd0.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/pwr/priv.h [deleted file]
drivers/gpu/drm/nouveau/core/subdev/therm/base.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/therm/fan.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/therm/fannil.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/therm/fanpwm.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/therm/fantog.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/therm/gm107.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/therm/ic.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/therm/nv40.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/therm/nv50.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/therm/nv84.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/therm/nva3.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/therm/nvd0.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/therm/priv.h [deleted file]
drivers/gpu/drm/nouveau/core/subdev/therm/temp.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/timer/base.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/timer/gk20a.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/timer/nv04.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/timer/nv04.h [deleted file]
drivers/gpu/drm/nouveau/core/subdev/timer/priv.h [deleted file]
drivers/gpu/drm/nouveau/core/subdev/vm/base.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/vm/nv04.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/vm/nv04.h [deleted file]
drivers/gpu/drm/nouveau/core/subdev/vm/nv41.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/vm/nv44.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/vm/nv50.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/vm/nvc0.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/volt/base.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/volt/gk20a.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/volt/gpio.c [deleted file]
drivers/gpu/drm/nouveau/core/subdev/volt/nv40.c [deleted file]
drivers/gpu/drm/nouveau/dispnv04/Kbuild [new file with mode: 0644]
drivers/gpu/drm/nouveau/dispnv04/Makefile [deleted file]
drivers/gpu/drm/nouveau/dispnv04/crtc.c
drivers/gpu/drm/nouveau/dispnv04/dac.c
drivers/gpu/drm/nouveau/dispnv04/dfp.c
drivers/gpu/drm/nouveau/dispnv04/disp.c
drivers/gpu/drm/nouveau/dispnv04/disp.h
drivers/gpu/drm/nouveau/dispnv04/hw.c
drivers/gpu/drm/nouveau/dispnv04/hw.h
drivers/gpu/drm/nouveau/dispnv04/tvnv04.c
drivers/gpu/drm/nouveau/dispnv04/tvnv17.c
drivers/gpu/drm/nouveau/include/nvif/class.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/include/nvif/client.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/include/nvif/device.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/include/nvif/driver.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/include/nvif/event.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/include/nvif/ioctl.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/include/nvif/list.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/include/nvif/notify.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/include/nvif/object.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/include/nvif/os.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/include/nvif/unpack.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/include/nvkm/core/client.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/include/nvkm/core/debug.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/include/nvkm/core/device.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/include/nvkm/core/devidx.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/include/nvkm/core/engctx.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/include/nvkm/core/engine.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/include/nvkm/core/enum.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/include/nvkm/core/event.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/include/nvkm/core/gpuobj.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/include/nvkm/core/handle.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/include/nvkm/core/ioctl.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/include/nvkm/core/mm.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/include/nvkm/core/namedb.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/include/nvkm/core/notify.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/include/nvkm/core/object.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/include/nvkm/core/option.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/include/nvkm/core/os.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/include/nvkm/core/parent.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/include/nvkm/core/printk.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/include/nvkm/core/ramht.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/include/nvkm/core/subdev.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/include/nvkm/engine/bsp.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/include/nvkm/engine/ce.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/include/nvkm/engine/cipher.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/include/nvkm/engine/device.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/include/nvkm/engine/disp.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/include/nvkm/engine/dmaobj.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/include/nvkm/engine/falcon.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/include/nvkm/engine/fifo.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/include/nvkm/engine/gr.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/include/nvkm/engine/mpeg.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/include/nvkm/engine/mspdec.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/include/nvkm/engine/msppp.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/include/nvkm/engine/msvld.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/include/nvkm/engine/pm.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/include/nvkm/engine/sec.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/include/nvkm/engine/sw.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/include/nvkm/engine/vp.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/include/nvkm/engine/xtensa.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/include/nvkm/subdev/bar.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/include/nvkm/subdev/bios.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/include/nvkm/subdev/bios/M0203.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/include/nvkm/subdev/bios/M0205.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/include/nvkm/subdev/bios/M0209.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/include/nvkm/subdev/bios/P0260.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/include/nvkm/subdev/bios/bit.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/include/nvkm/subdev/bios/bmp.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/include/nvkm/subdev/bios/boost.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/include/nvkm/subdev/bios/conn.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/include/nvkm/subdev/bios/cstep.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/include/nvkm/subdev/bios/dcb.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/include/nvkm/subdev/bios/disp.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/include/nvkm/subdev/bios/dp.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/include/nvkm/subdev/bios/extdev.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/include/nvkm/subdev/bios/fan.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/include/nvkm/subdev/bios/gpio.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/include/nvkm/subdev/bios/i2c.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/include/nvkm/subdev/bios/image.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/include/nvkm/subdev/bios/init.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/include/nvkm/subdev/bios/mxm.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/include/nvkm/subdev/bios/npde.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/include/nvkm/subdev/bios/pcir.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/include/nvkm/subdev/bios/perf.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/include/nvkm/subdev/bios/pll.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/include/nvkm/subdev/bios/pmu.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/include/nvkm/subdev/bios/ramcfg.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/include/nvkm/subdev/bios/rammap.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/include/nvkm/subdev/bios/therm.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/include/nvkm/subdev/bios/timing.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/include/nvkm/subdev/bios/vmap.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/include/nvkm/subdev/bios/volt.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/include/nvkm/subdev/bios/xpio.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/include/nvkm/subdev/bus.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/include/nvkm/subdev/clk.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/include/nvkm/subdev/devinit.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/include/nvkm/subdev/fb.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/include/nvkm/subdev/fuse.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/include/nvkm/subdev/gpio.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/include/nvkm/subdev/i2c.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/include/nvkm/subdev/ibus.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/include/nvkm/subdev/instmem.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/include/nvkm/subdev/ltc.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/include/nvkm/subdev/mc.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/include/nvkm/subdev/mmu.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/include/nvkm/subdev/mxm.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/include/nvkm/subdev/pmu.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/include/nvkm/subdev/therm.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/include/nvkm/subdev/timer.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/include/nvkm/subdev/vga.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/include/nvkm/subdev/volt.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/nouveau_abi16.c
drivers/gpu/drm/nouveau/nouveau_abi16.h
drivers/gpu/drm/nouveau/nouveau_agp.c
drivers/gpu/drm/nouveau/nouveau_bios.c
drivers/gpu/drm/nouveau/nouveau_bo.c
drivers/gpu/drm/nouveau/nouveau_bo.h
drivers/gpu/drm/nouveau/nouveau_chan.c
drivers/gpu/drm/nouveau/nouveau_chan.h
drivers/gpu/drm/nouveau/nouveau_connector.c
drivers/gpu/drm/nouveau/nouveau_connector.h
drivers/gpu/drm/nouveau/nouveau_display.c
drivers/gpu/drm/nouveau/nouveau_display.h
drivers/gpu/drm/nouveau/nouveau_dma.c
drivers/gpu/drm/nouveau/nouveau_dp.c
drivers/gpu/drm/nouveau/nouveau_drm.c
drivers/gpu/drm/nouveau/nouveau_drm.h
drivers/gpu/drm/nouveau/nouveau_encoder.h
drivers/gpu/drm/nouveau/nouveau_fbcon.c
drivers/gpu/drm/nouveau/nouveau_fbcon.h
drivers/gpu/drm/nouveau/nouveau_fence.c
drivers/gpu/drm/nouveau/nouveau_fence.h
drivers/gpu/drm/nouveau/nouveau_gem.c
drivers/gpu/drm/nouveau/nouveau_hwmon.c
drivers/gpu/drm/nouveau/nouveau_nvif.c
drivers/gpu/drm/nouveau/nouveau_platform.c
drivers/gpu/drm/nouveau/nouveau_platform.h
drivers/gpu/drm/nouveau/nouveau_reg.h
drivers/gpu/drm/nouveau/nouveau_sgdma.c
drivers/gpu/drm/nouveau/nouveau_sysfs.c
drivers/gpu/drm/nouveau/nouveau_ttm.c
drivers/gpu/drm/nouveau/nv04_fence.c
drivers/gpu/drm/nouveau/nv50_display.c
drivers/gpu/drm/nouveau/nv84_fence.c
drivers/gpu/drm/nouveau/nvif/Kbuild [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvif/class.h [deleted file]
drivers/gpu/drm/nouveau/nvif/client.c
drivers/gpu/drm/nouveau/nvif/client.h [deleted file]
drivers/gpu/drm/nouveau/nvif/device.c
drivers/gpu/drm/nouveau/nvif/device.h [deleted file]
drivers/gpu/drm/nouveau/nvif/driver.h [deleted file]
drivers/gpu/drm/nouveau/nvif/event.h [deleted file]
drivers/gpu/drm/nouveau/nvif/ioctl.h [deleted file]
drivers/gpu/drm/nouveau/nvif/list.h [deleted file]
drivers/gpu/drm/nouveau/nvif/notify.c
drivers/gpu/drm/nouveau/nvif/notify.h [deleted file]
drivers/gpu/drm/nouveau/nvif/object.c
drivers/gpu/drm/nouveau/nvif/object.h [deleted file]
drivers/gpu/drm/nouveau/nvif/os.h [deleted symlink]
drivers/gpu/drm/nouveau/nvif/unpack.h [deleted file]
drivers/gpu/drm/nouveau/nvkm/Kbuild [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/core/Kbuild [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/core/client.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/core/engctx.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/core/engine.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/core/enum.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/core/event.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/core/gpuobj.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/core/handle.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/core/ioctl.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/core/mm.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/core/namedb.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/core/notify.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/core/object.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/core/option.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/core/parent.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/core/printk.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/core/ramht.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/core/subdev.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/Kbuild [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/bsp/Kbuild [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/bsp/g84.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/ce/Kbuild [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/ce/fuc/com.fuc [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/ce/fuc/gf100.fuc3 [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/ce/fuc/gf100.fuc3.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/ce/fuc/gt215.fuc3 [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/ce/fuc/gt215.fuc3.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/ce/gf100.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/ce/gk104.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/ce/gt215.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/cipher/Kbuild [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/cipher/g84.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/device/Kbuild [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/device/acpi.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/device/acpi.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/device/base.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/device/ctrl.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/device/gf100.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/device/gk104.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/device/gm100.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/device/nv04.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/device/nv10.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/device/nv20.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/device/nv30.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/device/nv40.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/device/nv50.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/device/priv.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/disp/Kbuild [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/disp/base.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/disp/conn.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/disp/conn.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/disp/dacnv50.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/disp/dport.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/disp/dport.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/disp/g84.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/disp/g94.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/disp/gf110.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/disp/gk104.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/disp/gk110.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/disp/gm107.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/disp/gm204.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/disp/gt200.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/disp/gt215.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/disp/hdagf110.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/disp/hdagt215.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/disp/hdmig84.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/disp/hdmigf110.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/disp/hdmigk104.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/disp/hdmigt215.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/disp/nv04.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/disp/nv50.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/disp/nv50.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/disp/outp.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/disp/outp.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/disp/outpdp.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/disp/outpdp.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/disp/piornv50.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/disp/priv.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/disp/sorg94.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/disp/sorgf110.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/disp/sorgm204.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/disp/sornv50.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/disp/vga.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/dmaobj/Kbuild [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/dmaobj/base.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/dmaobj/gf100.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/dmaobj/gf110.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/dmaobj/nv04.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/dmaobj/nv50.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/dmaobj/priv.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/falcon.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/fifo/Kbuild [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/fifo/base.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/fifo/g84.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/fifo/gf100.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/fifo/gk104.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/fifo/gk104.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/fifo/gk208.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/fifo/gk20a.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/fifo/nv04.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/fifo/nv04.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/fifo/nv10.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/fifo/nv17.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/fifo/nv40.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/fifo/nv50.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/fifo/nv50.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/gr/Kbuild [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/gr/ctxgf100.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/gr/ctxgf100.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/gr/ctxgf104.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/gr/ctxgf108.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/gr/ctxgf110.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/gr/ctxgf117.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/gr/ctxgf119.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/gr/ctxgk104.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/gr/ctxgk110.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/gr/ctxgk110b.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/gr/ctxgk208.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/gr/ctxgk20a.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/gr/ctxgm107.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/gr/ctxnv40.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/gr/ctxnv40.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/gr/ctxnv50.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/gr/fuc/com.fuc [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/gr/fuc/gpc.fuc [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/gr/fuc/gpcgf100.fuc3 [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/gr/fuc/gpcgf100.fuc3.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/gr/fuc/gpcgf117.fuc3 [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/gr/fuc/gpcgf117.fuc3.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/gr/fuc/gpcgk104.fuc3 [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/gr/fuc/gpcgk104.fuc3.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/gr/fuc/gpcgk110.fuc3 [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/gr/fuc/gpcgk110.fuc3.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/gr/fuc/gpcgk208.fuc5 [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/gr/fuc/gpcgk208.fuc5.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/gr/fuc/gpcgm107.fuc5 [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/gr/fuc/gpcgm107.fuc5.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/gr/fuc/hub.fuc [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/gr/fuc/hubgf100.fuc3 [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/gr/fuc/hubgf100.fuc3.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/gr/fuc/hubgf117.fuc3 [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/gr/fuc/hubgf117.fuc3.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/gr/fuc/hubgk104.fuc3 [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/gr/fuc/hubgk104.fuc3.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/gr/fuc/hubgk110.fuc3 [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/gr/fuc/hubgk110.fuc3.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/gr/fuc/hubgk208.fuc5 [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/gr/fuc/hubgk208.fuc5.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/gr/fuc/hubgm107.fuc5 [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/gr/fuc/hubgm107.fuc5.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/gr/fuc/macros.fuc [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/gr/fuc/os.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/gr/gf100.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/gr/gf100.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/gr/gf104.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/gr/gf108.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/gr/gf110.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/gr/gf117.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/gr/gf119.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/gr/gk104.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/gr/gk110.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/gr/gk110b.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/gr/gk208.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/gr/gk20a.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/gr/gm107.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/gr/nv04.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/gr/nv10.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/gr/nv20.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/gr/nv20.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/gr/nv25.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/gr/nv2a.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/gr/nv30.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/gr/nv34.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/gr/nv35.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/gr/nv40.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/gr/nv40.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/gr/nv50.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/gr/nv50.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/gr/regs.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/mpeg/Kbuild [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/mpeg/g84.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/mpeg/nv31.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/mpeg/nv31.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/mpeg/nv40.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/mpeg/nv44.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/mpeg/nv50.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/mspdec/Kbuild [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/mspdec/g98.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/mspdec/gf100.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/mspdec/gk104.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/msppp/Kbuild [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/msppp/g98.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/msppp/gf100.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/msvld/Kbuild [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/msvld/g98.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/msvld/gf100.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/msvld/gk104.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/pm/Kbuild [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/pm/base.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/pm/daemon.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/pm/g84.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/pm/gf100.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/pm/gf100.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/pm/gk104.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/pm/gk110.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/pm/gt215.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/pm/nv40.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/pm/nv40.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/pm/nv50.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/pm/priv.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/sec/Kbuild [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/sec/fuc/g98.fuc0s [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/sec/fuc/g98.fuc0s.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/sec/g98.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/sw/Kbuild [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/sw/gf100.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/sw/nv04.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/sw/nv10.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/sw/nv50.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/sw/nv50.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/vp/Kbuild [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/vp/g84.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/engine/xtensa.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/Kbuild [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/bar/Kbuild [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/bar/base.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/bar/gf100.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/bar/gk20a.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/bar/nv50.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/bar/priv.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/bios/Kbuild [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/bios/M0203.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/bios/M0205.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/bios/M0209.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/bios/P0260.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/bios/base.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/bios/bit.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/bios/boost.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/bios/conn.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/bios/cstep.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/bios/dcb.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/bios/disp.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/bios/dp.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/bios/extdev.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/bios/fan.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/bios/gpio.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/bios/i2c.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/bios/image.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/bios/init.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/bios/mxm.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/bios/npde.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/bios/pcir.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/bios/perf.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/bios/pll.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/bios/pmu.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/bios/priv.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/bios/ramcfg.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/bios/rammap.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/bios/shadow.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/bios/shadowacpi.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/bios/shadowof.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/bios/shadowpci.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/bios/shadowramin.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/bios/shadowrom.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/bios/therm.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/bios/timing.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/bios/vmap.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/bios/volt.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/bios/xpio.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/bus/Kbuild [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/bus/g94.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/bus/gf100.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/bus/hwsq.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/bus/hwsq.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/bus/nv04.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/bus/nv04.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/bus/nv31.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/bus/nv50.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/clk/Kbuild [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/clk/base.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/clk/g84.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/clk/gf100.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/clk/gk104.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/clk/gk20a.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/clk/gt215.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/clk/gt215.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/clk/mcp77.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/clk/nv04.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/clk/nv40.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/clk/nv50.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/clk/nv50.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/clk/pll.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/clk/pllgt215.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/clk/pllnv04.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/clk/seq.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/devinit/Kbuild [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/devinit/base.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/devinit/fbmem.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/devinit/g84.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/devinit/g98.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/devinit/gf100.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/devinit/gm107.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/devinit/gm204.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/devinit/gt215.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/devinit/mcp89.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/devinit/nv04.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/devinit/nv04.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/devinit/nv05.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/devinit/nv10.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/devinit/nv1a.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/devinit/nv20.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/devinit/nv50.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/devinit/nv50.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/devinit/priv.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/fb/Kbuild [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/fb/base.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/fb/g84.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/fb/gddr3.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/fb/gddr5.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/fb/gf100.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/fb/gf100.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/fb/gk104.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/fb/gk20a.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/fb/gm107.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/fb/gt215.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/fb/mcp77.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/fb/mcp89.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/fb/nv04.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/fb/nv04.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/fb/nv10.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/fb/nv1a.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/fb/nv20.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/fb/nv25.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/fb/nv30.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/fb/nv35.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/fb/nv36.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/fb/nv40.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/fb/nv40.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/fb/nv41.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/fb/nv44.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/fb/nv46.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/fb/nv47.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/fb/nv49.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/fb/nv4e.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/fb/nv50.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/fb/nv50.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/fb/priv.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/fb/ramfuc.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/fb/ramgf100.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/fb/ramgk104.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/fb/ramgk20a.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/fb/ramgm107.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/fb/ramgt215.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/fb/rammcp77.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/fb/ramnv04.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/fb/ramnv10.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/fb/ramnv1a.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/fb/ramnv20.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/fb/ramnv40.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/fb/ramnv41.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/fb/ramnv44.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/fb/ramnv49.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/fb/ramnv4e.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/fb/ramnv50.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/fb/ramseq.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/fb/regsnv04.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/fb/sddr2.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/fb/sddr3.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/fuse/Kbuild [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/fuse/base.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/fuse/gf100.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/fuse/gm107.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/fuse/nv50.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/fuse/priv.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/gpio/Kbuild [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/gpio/base.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/gpio/g94.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/gpio/gf110.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/gpio/gk104.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/gpio/nv10.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/gpio/nv50.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/gpio/priv.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/i2c/Kbuild [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/i2c/anx9805.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/i2c/aux.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/i2c/base.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/i2c/bit.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/i2c/g94.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/i2c/gf110.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/i2c/gf117.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/i2c/gk104.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/i2c/gm204.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/i2c/nv04.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/i2c/nv4e.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/i2c/nv50.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/i2c/nv50.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/i2c/pad.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/i2c/pad.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/i2c/padg94.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/i2c/padgm204.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/i2c/padnv04.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/i2c/port.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/i2c/priv.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/ibus/Kbuild [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/ibus/gf100.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/ibus/gk104.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/ibus/gk20a.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/instmem/Kbuild [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/instmem/base.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/instmem/nv04.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/instmem/nv04.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/instmem/nv40.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/instmem/nv50.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/instmem/priv.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/ltc/Kbuild [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/ltc/base.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/ltc/gf100.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/ltc/gk104.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/ltc/gm107.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/ltc/priv.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/mc/Kbuild [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/mc/base.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/mc/g94.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/mc/g98.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/mc/gf100.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/mc/gf106.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/mc/gk20a.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/mc/nv04.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/mc/nv04.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/mc/nv40.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/mc/nv44.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/mc/nv4c.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/mc/nv50.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/mc/priv.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/mmu/Kbuild [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/mmu/base.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/mmu/gf100.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/mmu/nv04.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/mmu/nv04.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/mmu/nv41.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/mmu/nv44.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/mmu/nv50.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/mxm/Kbuild [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/mxm/base.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/mxm/mxms.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/mxm/mxms.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/mxm/nv50.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/pmu/Kbuild [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/pmu/base.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/pmu/fuc/arith.fuc [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/pmu/fuc/gf100.fuc3 [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/pmu/fuc/gf100.fuc3.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/pmu/fuc/gf110.fuc4 [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/pmu/fuc/gf110.fuc4.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/pmu/fuc/gk208.fuc5 [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/pmu/fuc/gk208.fuc5.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/pmu/fuc/gt215.fuc3 [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/pmu/fuc/gt215.fuc3.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/pmu/fuc/host.fuc [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/pmu/fuc/i2c_.fuc [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/pmu/fuc/idle.fuc [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/pmu/fuc/kernel.fuc [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/pmu/fuc/macros.fuc [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/pmu/fuc/memx.fuc [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/pmu/fuc/os.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/pmu/fuc/perf.fuc [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/pmu/fuc/test.fuc [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/pmu/gf100.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/pmu/gf110.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/pmu/gk104.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/pmu/gk208.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/pmu/gk20a.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/pmu/gt215.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/pmu/memx.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/pmu/priv.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/therm/Kbuild [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/therm/base.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/therm/fan.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/therm/fannil.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/therm/fanpwm.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/therm/fantog.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/therm/g84.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/therm/gf110.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/therm/gm107.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/therm/gt215.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/therm/ic.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/therm/nv40.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/therm/nv50.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/therm/priv.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/therm/temp.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/timer/Kbuild [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/timer/base.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/timer/gk20a.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/timer/nv04.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/timer/nv04.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/timer/priv.h [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/volt/Kbuild [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/volt/base.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/volt/gk20a.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/volt/gpio.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/nvkm/subdev/volt/nv40.c [new file with mode: 0644]
drivers/gpu/drm/omapdrm/omap_fbdev.c
drivers/gpu/drm/panel/panel-simple.c
drivers/gpu/drm/qxl/qxl_fb.c
drivers/gpu/drm/radeon/Makefile
drivers/gpu/drm/radeon/cik.c
drivers/gpu/drm/radeon/cik_reg.h
drivers/gpu/drm/radeon/cik_sdma.c
drivers/gpu/drm/radeon/ni.c
drivers/gpu/drm/radeon/ni_dma.c
drivers/gpu/drm/radeon/nid.h
drivers/gpu/drm/radeon/radeon_asic.c
drivers/gpu/drm/radeon/radeon_fb.c
drivers/gpu/drm/radeon/radeon_gem.c
drivers/gpu/drm/radeon/radeon_kfd.c
drivers/gpu/drm/radeon/radeon_kfd.h
drivers/gpu/drm/radeon/radeon_pm.c
drivers/gpu/drm/radeon/si.c
drivers/gpu/drm/radeon/si_dma.c
drivers/gpu/drm/radeon/si_dpm.c
drivers/gpu/drm/radeon/sid.h
drivers/gpu/drm/rcar-du/rcar_du_crtc.c
drivers/gpu/drm/rcar-du/rcar_du_crtc.h
drivers/gpu/drm/rcar-du/rcar_du_drv.c
drivers/gpu/drm/rcar-du/rcar_du_drv.h
drivers/gpu/drm/rcar-du/rcar_du_encoder.c
drivers/gpu/drm/rcar-du/rcar_du_group.c
drivers/gpu/drm/rcar-du/rcar_du_hdmicon.c
drivers/gpu/drm/rcar-du/rcar_du_hdmienc.c
drivers/gpu/drm/rcar-du/rcar_du_kms.c
drivers/gpu/drm/rcar-du/rcar_du_plane.c
drivers/gpu/drm/rcar-du/rcar_du_regs.h
drivers/gpu/drm/rcar-du/rcar_du_vgacon.c
drivers/gpu/drm/rockchip/Kconfig
drivers/gpu/drm/rockchip/Makefile
drivers/gpu/drm/rockchip/dw_hdmi-rockchip.c [new file with mode: 0644]
drivers/gpu/drm/rockchip/rockchip_drm_drv.c
drivers/gpu/drm/rockchip/rockchip_drm_vop.c
drivers/gpu/drm/sti/Makefile
drivers/gpu/drm/sti/sti_awg_utils.c [new file with mode: 0644]
drivers/gpu/drm/sti/sti_awg_utils.h [new file with mode: 0644]
drivers/gpu/drm/sti/sti_drm_crtc.c
drivers/gpu/drm/sti/sti_dvo.c [new file with mode: 0644]
drivers/gpu/drm/sti/sti_tvout.c
drivers/gpu/drm/tegra/dc.c
drivers/gpu/drm/udl/udl_fb.c
drivers/gpu/ipu-v3/ipu-dc.c
drivers/gpu/ipu-v3/ipu-di.c
drivers/iio/adc/ad799x.c
drivers/iio/inkern.c
drivers/infiniband/hw/mlx4/main.c
drivers/input/mouse/elantech.c
drivers/input/serio/i8042-x86ia64io.h
drivers/input/serio/i8042.c
drivers/isdn/hardware/eicon/message.c
drivers/leds/leds-netxbig.c
drivers/mcb/mcb-internal.h
drivers/mcb/mcb-pci.c
drivers/mfd/da9052-core.c
drivers/mfd/rtsx_usb.c
drivers/mfd/tps65218.c
drivers/misc/cxl/context.c
drivers/misc/cxl/file.c
drivers/misc/mei/hw-me.c
drivers/mmc/host/sdhci-acpi.c
drivers/mmc/host/sdhci-pci.c
drivers/mmc/host/sdhci-pci.h
drivers/mmc/host/sdhci-pxav3.c
drivers/mmc/host/sdhci.c
drivers/net/can/c_can/c_can_platform.c
drivers/net/can/dev.c
drivers/net/can/m_can/m_can.c
drivers/net/can/usb/kvaser_usb.c
drivers/net/ethernet/atheros/alx/main.c
drivers/net/ethernet/broadcom/bgmac.c
drivers/net/ethernet/broadcom/tg3.c
drivers/net/ethernet/cadence/at91_ether.c
drivers/net/ethernet/chelsio/cxgb4vf/cxgb4vf_main.c
drivers/net/ethernet/chelsio/cxgb4vf/t4vf_hw.c
drivers/net/ethernet/dnet.c
drivers/net/ethernet/emulex/benet/be_main.c
drivers/net/ethernet/freescale/fec.h
drivers/net/ethernet/freescale/fec_main.c
drivers/net/ethernet/intel/Kconfig
drivers/net/ethernet/intel/i40e/Makefile
drivers/net/ethernet/intel/i40e/i40e_osdep.h
drivers/net/ethernet/intel/i40e/i40e_txrx.c
drivers/net/ethernet/intel/i40e/i40e_txrx.h
drivers/net/ethernet/mellanox/mlx4/en_netdev.c
drivers/net/ethernet/mellanox/mlx4/main.c
drivers/net/ethernet/neterion/s2io.c
drivers/net/ethernet/renesas/sh_eth.c
drivers/net/ethernet/renesas/sh_eth.h
drivers/net/ethernet/samsung/sxgbe/sxgbe_main.c
drivers/net/ethernet/samsung/sxgbe/sxgbe_platform.c
drivers/net/ethernet/ti/cpsw.c
drivers/net/ethernet/ti/cpsw_ale.c
drivers/net/ethernet/ti/cpsw_ale.h
drivers/net/ethernet/ti/davinci_emac.c
drivers/net/team/team.c
drivers/net/usb/kaweth.c
drivers/net/usb/r8152.c
drivers/net/wireless/iwlwifi/iwl-7000.c
drivers/net/wireless/iwlwifi/iwl-8000.c
drivers/net/wireless/iwlwifi/iwl-fw-file.h
drivers/net/wireless/iwlwifi/mvm/fw-api-scan.h
drivers/net/wireless/iwlwifi/mvm/scan.c
drivers/net/wireless/iwlwifi/mvm/tx.c
drivers/net/wireless/iwlwifi/mvm/utils.c
drivers/net/wireless/iwlwifi/pcie/drv.c
drivers/net/wireless/rtlwifi/pci.c
drivers/net/xen-netfront.c
drivers/phy/phy-miphy28lp.c
drivers/phy/phy-omap-control.c
drivers/phy/phy-sun4i-usb.c
drivers/phy/phy-ti-pipe3.c
drivers/pinctrl/core.c
drivers/pinctrl/pinctrl-rockchip.c
drivers/pinctrl/pinctrl-xway.c
drivers/pinctrl/qcom/pinctrl-msm.c
drivers/reset/reset-sunxi.c
drivers/s390/crypto/ap_bus.c
drivers/scsi/scsi_lib.c
drivers/staging/vt6655/baseband.c
drivers/staging/vt6655/channel.c
drivers/staging/vt6655/device_main.c
drivers/staging/vt6655/rxtx.c
drivers/target/iscsi/iscsi_target.c
drivers/target/iscsi/iscsi_target_core.h
drivers/target/target_core_device.c
drivers/target/target_core_file.c
drivers/target/target_core_iblock.c
drivers/target/target_core_pr.c
drivers/target/target_core_rd.c
drivers/target/target_core_sbc.c
drivers/target/target_core_spc.c
drivers/target/target_core_user.c
drivers/thermal/imx_thermal.c
drivers/thermal/int340x_thermal/acpi_thermal_rel.c
drivers/thermal/int340x_thermal/processor_thermal_device.c
drivers/thermal/of-thermal.c
drivers/thermal/rcar_thermal.c
drivers/thermal/thermal_core.h
drivers/tty/n_tty.c
drivers/tty/serial/8250/8250_pci.c
drivers/tty/serial/samsung.c
drivers/tty/serial/serial_core.c
drivers/tty/tty_io.c
drivers/usb/chipidea/core.c
drivers/usb/chipidea/host.c
drivers/usb/dwc2/gadget.c
drivers/usb/dwc3/dwc3-pci.c
drivers/usb/dwc3/gadget.c
drivers/usb/gadget/function/f_hid.c
drivers/usb/gadget/function/f_midi.c
drivers/usb/gadget/function/f_uac1.c
drivers/usb/gadget/legacy/inode.c
drivers/usb/gadget/udc/atmel_usba_udc.c
drivers/usb/gadget/udc/bdc/bdc_ep.c
drivers/usb/host/ehci-sched.c
drivers/usb/host/ehci-tegra.c
drivers/usb/host/pci-quirks.c
drivers/usb/host/xhci-pci.c
drivers/usb/host/xhci.c
drivers/usb/musb/Kconfig
drivers/usb/musb/blackfin.c
drivers/usb/musb/musb_cppi41.c
drivers/usb/musb/musb_debugfs.c
drivers/usb/musb/musb_host.c
drivers/usb/phy/phy-mv-usb.c
drivers/usb/phy/phy.c
drivers/usb/serial/console.c
drivers/usb/serial/cp210x.c
drivers/usb/serial/generic.c
drivers/usb/serial/keyspan.c
drivers/usb/serial/option.c
drivers/usb/serial/qcserial.c
drivers/usb/storage/uas-detect.h
drivers/usb/storage/unusual_uas.h
drivers/vhost/scsi.c
drivers/video/fbdev/broadsheetfb.c
drivers/video/fbdev/simplefb.c
fs/fuse/dev.c
fs/fuse/dir.c
fs/fuse/fuse_i.h
fs/fuse/inode.c
fs/kernfs/dir.c
fs/lockd/svc.c
fs/locks.c
fs/nfs/nfs4client.c
fs/nfs/nfs4proc.c
include/asm-generic/tlb.h
include/drm/bridge/dw_hdmi.h [new file with mode: 0644]
include/drm/drmP.h
include/drm/drm_atomic.h
include/drm/drm_atomic_helper.h
include/drm/drm_crtc.h
include/drm/drm_crtc_helper.h
include/drm/drm_fb_helper.h
include/drm/drm_modes.h
include/linux/blk-mq.h
include/linux/blk_types.h
include/linux/compiler.h
include/linux/genetlink.h
include/linux/libata.h
include/linux/mmc/sdhci.h
include/linux/netdevice.h
include/linux/nfs_fs_sb.h
include/linux/phy/omap_control_phy.h
include/net/genetlink.h
include/target/target_core_backend.h
include/target/target_core_backend_configfs.h
include/target/target_core_base.h
include/uapi/drm/drm.h
include/uapi/drm/drm_mode.h
include/uapi/linux/can/netlink.h
include/uapi/linux/openvswitch.h
include/uapi/linux/uinput.h
include/video/imx-ipu-v3.h
include/xen/interface/nmi.h [new file with mode: 0644]
kernel/range.c
kernel/trace/ftrace.c
kernel/trace/trace.c
kernel/trace/trace_events.c
kernel/workqueue.c
mm/memory.c
net/bridge/br_input.c
net/core/dev.c
net/core/neighbour.c
net/ipv4/ip_sockglue.c
net/ipv4/netfilter/nft_redir_ipv4.c
net/ipv6/datagram.c
net/ipv6/netfilter/nft_redir_ipv6.c
net/ipv6/route.c
net/mac80211/mlme.c
net/netfilter/ipvs/ip_vs_ftp.c
net/netfilter/nf_conntrack_core.c
net/netfilter/nf_tables_api.c
net/netfilter/nfnetlink.c
net/netfilter/nft_nat.c
net/netlink/af_netlink.c
net/netlink/af_netlink.h
net/netlink/genetlink.c
net/openvswitch/datapath.c
net/packet/af_packet.c
net/sctp/socket.c
net/tipc/bcast.c
net/wireless/reg.c
scripts/recordmcount.pl
sound/firewire/amdtp.c
sound/firewire/amdtp.h
sound/firewire/bebob/bebob_stream.c
sound/firewire/fireworks/fireworks_stream.c
sound/usb/mixer.c
tools/include/asm-generic/bitops.h
tools/include/asm-generic/bitops/arch_hweight.h [new file with mode: 0644]
tools/include/asm-generic/bitops/const_hweight.h [new file with mode: 0644]
tools/include/asm-generic/bitops/hweight.h [new file with mode: 0644]
tools/include/linux/bitops.h
tools/lib/api/fs/debugfs.c
tools/lib/api/fs/fs.c
tools/perf/MANIFEST
tools/perf/Makefile.perf
tools/perf/arch/powerpc/util/skip-callchain-idx.c
tools/perf/bench/sched-pipe.c
tools/perf/builtin-top.c
tools/perf/config/Makefile
tools/perf/config/Makefile.arch
tools/perf/perf-sys.h
tools/perf/tests/dwarf-unwind.c
tools/perf/util/annotate.h
tools/perf/util/cache.h
tools/perf/util/hweight.c [deleted file]
tools/perf/util/include/asm/hweight.h [deleted file]
tools/perf/util/machine.c
tools/perf/util/probe-event.c
tools/perf/util/python-ext-sources
tools/perf/util/unwind-libunwind.c
tools/testing/selftests/exec/execveat.c
tools/testing/selftests/mqueue/mq_perf_tests.c
tools/testing/selftests/vm/Makefile

index 0ec8b8178c41305a4435b208646715c22b94154a..80d9888a8ece2673686ead1cda4504ce568a1051 100644 (file)
@@ -14,3 +14,18 @@ Description:
                The /sys/class/mei/meiN directory is created for
                each probed mei device
 
+What:          /sys/class/mei/meiN/fw_status
+Date:          Nov 2014
+KernelVersion: 3.19
+Contact:       Tomas Winkler <tomas.winkler@intel.com>
+Description:   Display fw status registers content
+
+               The ME FW writes its status information into fw status
+               registers for BIOS and OS to monitor fw health.
+
+               The register contains running state, power management
+               state, error codes, and others. The way the registers
+               are decoded depends on PCH or SoC generation.
+               Also number of registers varies between 1 and 6
+               depending on generation.
+
index 10cffd95fd7e7348d9ccbbca80f4689a495b4bbc..77d045557daf48d6fa332f80e021bd00a74f9eb5 100644 (file)
               Driver supports dedicated render nodes.
             </para></listitem>
           </varlistentry>
+          <varlistentry>
+            <term>DRIVER_ATOMIC</term>
+            <listitem><para>
+              Driver supports atomic properties.  In this case the driver
+              must implement appropriate obj->atomic_get_property() vfuncs
+              for any modeset objects with driver specific properties.
+            </para></listitem>
+          </varlistentry>
         </variablelist>
       </sect3>
       <sect3>
@@ -1377,7 +1385,7 @@ int max_width, max_height;</synopsis>
       <itemizedlist>
         <listitem>
         DRM_PLANE_TYPE_PRIMARY represents a "main" plane for a CRTC.  Primary
-        planes are the planes operated upon by by CRTC modesetting and flipping
+        planes are the planes operated upon by CRTC modesetting and flipping
         operations described in <xref linkend="drm-kms-crtcops"/>.
         </listitem>
         <listitem>
@@ -2362,6 +2370,7 @@ void intel_crt_init(struct drm_device *dev)
     </sect2>
     <sect2>
       <title>Modeset Helper Functions Reference</title>
+!Iinclude/drm/drm_crtc_helper.h
 !Edrivers/gpu/drm/drm_crtc_helper.c
 !Pdrivers/gpu/drm/drm_crtc_helper.c overview
     </sect2>
@@ -2564,8 +2573,8 @@ void intel_crt_init(struct drm_device *dev)
        <td valign="top" >Description/Restrictions</td>
        </tr>
        <tr>
-       <td rowspan="25" valign="top" >DRM</td>
-       <td rowspan="4" valign="top" >Generic</td>
+       <td rowspan="36" valign="top" >DRM</td>
+       <td rowspan="5" valign="top" >Connector</td>
        <td valign="top" >“EDID”</td>
        <td valign="top" >BLOB | IMMUTABLE</td>
        <td valign="top" >0</td>
@@ -2594,7 +2603,14 @@ void intel_crt_init(struct drm_device *dev)
        <td valign="top" >Contains tiling information for a connector.</td>
        </tr>
        <tr>
-       <td rowspan="1" valign="top" >Plane</td>
+       <td valign="top" >“CRTC_ID”</td>
+       <td valign="top" >OBJECT</td>
+       <td valign="top" >DRM_MODE_OBJECT_CRTC</td>
+       <td valign="top" >Connector</td>
+       <td valign="top" >CRTC that connector is attached to (atomic)</td>
+       </tr>
+       <tr>
+       <td rowspan="11" valign="top" >Plane</td>
        <td valign="top" >“type”</td>
        <td valign="top" >ENUM | IMMUTABLE</td>
        <td valign="top" >{ "Overlay", "Primary", "Cursor" }</td>
@@ -2602,6 +2618,76 @@ void intel_crt_init(struct drm_device *dev)
        <td valign="top" >Plane type</td>
        </tr>
        <tr>
+       <td valign="top" >“SRC_X”</td>
+       <td valign="top" >RANGE</td>
+       <td valign="top" >Min=0, Max=UINT_MAX</td>
+       <td valign="top" >Plane</td>
+       <td valign="top" >Scanout source x coordinate in 16.16 fixed point (atomic)</td>
+       </tr>
+       <tr>
+       <td valign="top" >“SRC_Y”</td>
+       <td valign="top" >RANGE</td>
+       <td valign="top" >Min=0, Max=UINT_MAX</td>
+       <td valign="top" >Plane</td>
+       <td valign="top" >Scanout source y coordinate in 16.16 fixed point (atomic)</td>
+       </tr>
+       <tr>
+       <td valign="top" >“SRC_W”</td>
+       <td valign="top" >RANGE</td>
+       <td valign="top" >Min=0, Max=UINT_MAX</td>
+       <td valign="top" >Plane</td>
+       <td valign="top" >Scanout source width in 16.16 fixed point (atomic)</td>
+       </tr>
+       <tr>
+       <td valign="top" >“SRC_H”</td>
+       <td valign="top" >RANGE</td>
+       <td valign="top" >Min=0, Max=UINT_MAX</td>
+       <td valign="top" >Plane</td>
+       <td valign="top" >Scanout source height in 16.16 fixed point (atomic)</td>
+       </tr>
+       <tr>
+       <td valign="top" >“CRTC_X”</td>
+       <td valign="top" >SIGNED_RANGE</td>
+       <td valign="top" >Min=INT_MIN, Max=INT_MAX</td>
+       <td valign="top" >Plane</td>
+       <td valign="top" >Scanout CRTC (destination) x coordinate (atomic)</td>
+       </tr>
+       <tr>
+       <td valign="top" >“CRTC_Y”</td>
+       <td valign="top" >SIGNED_RANGE</td>
+       <td valign="top" >Min=INT_MIN, Max=INT_MAX</td>
+       <td valign="top" >Plane</td>
+       <td valign="top" >Scanout CRTC (destination) y coordinate (atomic)</td>
+       </tr>
+       <tr>
+       <td valign="top" >“CRTC_W”</td>
+       <td valign="top" >RANGE</td>
+       <td valign="top" >Min=0, Max=UINT_MAX</td>
+       <td valign="top" >Plane</td>
+       <td valign="top" >Scanout CRTC (destination) width (atomic)</td>
+       </tr>
+       <tr>
+       <td valign="top" >“CRTC_H”</td>
+       <td valign="top" >RANGE</td>
+       <td valign="top" >Min=0, Max=UINT_MAX</td>
+       <td valign="top" >Plane</td>
+       <td valign="top" >Scanout CRTC (destination) height (atomic)</td>
+       </tr>
+       <tr>
+       <td valign="top" >“FB_ID”</td>
+       <td valign="top" >OBJECT</td>
+       <td valign="top" >DRM_MODE_OBJECT_FB</td>
+       <td valign="top" >Plane</td>
+       <td valign="top" >Scanout framebuffer (atomic)</td>
+       </tr>
+       <tr>
+       <td valign="top" >“CRTC_ID”</td>
+       <td valign="top" >OBJECT</td>
+       <td valign="top" >DRM_MODE_OBJECT_CRTC</td>
+       <td valign="top" >Plane</td>
+       <td valign="top" >CRTC that plane is attached to (atomic)</td>
+       </tr>
+       <tr>
        <td rowspan="2" valign="top" >DVI-I</td>
        <td valign="top" >“subconnector”</td>
        <td valign="top" >ENUM</td>
diff --git a/Documentation/devicetree/bindings/drm/atmel/hlcdc-dc.txt b/Documentation/devicetree/bindings/drm/atmel/hlcdc-dc.txt
new file mode 100644 (file)
index 0000000..ebc1a91
--- /dev/null
@@ -0,0 +1,53 @@
+Device-Tree bindings for Atmel's HLCDC (High LCD Controller) DRM driver
+
+The Atmel HLCDC Display Controller is subdevice of the HLCDC MFD device.
+See ../mfd/atmel-hlcdc.txt for more details.
+
+Required properties:
+ - compatible: value should be "atmel,hlcdc-display-controller"
+ - pinctrl-names: the pin control state names. Should contain "default".
+ - pinctrl-0: should contain the default pinctrl states.
+ - #address-cells: should be set to 1.
+ - #size-cells: should be set to 0.
+
+Required children nodes:
+ Children nodes are encoding available output ports and their connections
+ to external devices using the OF graph reprensentation (see ../graph.txt).
+ At least one port node is required.
+
+Example:
+
+       hlcdc: hlcdc@f0030000 {
+               compatible = "atmel,sama5d3-hlcdc";
+               reg = <0xf0030000 0x2000>;
+               interrupts = <36 IRQ_TYPE_LEVEL_HIGH 0>;
+               clocks = <&lcdc_clk>, <&lcdck>, <&clk32k>;
+               clock-names = "periph_clk","sys_clk", "slow_clk";
+               status = "disabled";
+
+               hlcdc-display-controller {
+                       compatible = "atmel,hlcdc-display-controller";
+                       pinctrl-names = "default";
+                       pinctrl-0 = <&pinctrl_lcd_base &pinctrl_lcd_rgb888>;
+                       #address-cells = <1>;
+                       #size-cells = <0>;
+
+                       port@0 {
+                               #address-cells = <1>;
+                               #size-cells = <0>;
+                               reg = <0>;
+
+                               hlcdc_panel_output: endpoint@0 {
+                                       reg = <0>;
+                                       remote-endpoint = <&panel_input>;
+                               };
+                       };
+               };
+
+               hlcdc_pwm: hlcdc-pwm {
+                       compatible = "atmel,hlcdc-pwm";
+                       pinctrl-names = "default";
+                       pinctrl-0 = <&pinctrl_lcd_pwm>;
+                       #pwm-cells = <3>;
+               };
+       };
diff --git a/Documentation/devicetree/bindings/drm/bridge/dw_hdmi.txt b/Documentation/devicetree/bindings/drm/bridge/dw_hdmi.txt
new file mode 100644 (file)
index 0000000..a905c14
--- /dev/null
@@ -0,0 +1,50 @@
+DesignWare HDMI bridge bindings
+
+Required properties:
+- compatible: platform specific such as:
+   * "snps,dw-hdmi-tx"
+   * "fsl,imx6q-hdmi"
+   * "fsl,imx6dl-hdmi"
+   * "rockchip,rk3288-dw-hdmi"
+- reg: Physical base address and length of the controller's registers.
+- interrupts: The HDMI interrupt number
+- clocks, clock-names : must have the phandles to the HDMI iahb and isfr clocks,
+  as described in Documentation/devicetree/bindings/clock/clock-bindings.txt,
+  the clocks are soc specific, the clock-names should be "iahb", "isfr"
+-port@[X]: SoC specific port nodes with endpoint definitions as defined
+   in Documentation/devicetree/bindings/media/video-interfaces.txt,
+   please refer to the SoC specific binding document:
+    * Documentation/devicetree/bindings/drm/imx/hdmi.txt
+    * Documentation/devicetree/bindings/video/dw_hdmi-rockchip.txt
+
+Optional properties
+- reg-io-width: the width of the reg:1,4, default set to 1 if not present
+- ddc-i2c-bus: phandle of an I2C controller used for DDC EDID probing
+- clocks, clock-names: phandle to the HDMI CEC clock, name should be "cec"
+
+Example:
+       hdmi: hdmi@0120000 {
+               compatible = "fsl,imx6q-hdmi";
+               reg = <0x00120000 0x9000>;
+               interrupts = <0 115 0x04>;
+               gpr = <&gpr>;
+               clocks = <&clks 123>, <&clks 124>;
+               clock-names = "iahb", "isfr";
+               ddc-i2c-bus = <&i2c2>;
+
+               port@0 {
+                       reg = <0>;
+
+                       hdmi_mux_0: endpoint {
+                               remote-endpoint = <&ipu1_di0_hdmi>;
+                       };
+               };
+
+               port@1 {
+                       reg = <1>;
+
+                       hdmi_mux_1: endpoint {
+                               remote-endpoint = <&ipu1_di1_hdmi>;
+                       };
+               };
+       };
index c99eb34e640b6782c066758f20922b21be6f75f0..6b1d75f1a5297f7eb76c9618103f5f4400b8f7f8 100644 (file)
@@ -83,6 +83,22 @@ sti-hda:
   - clock-names: names of the clocks listed in clocks property in the same
     order.
 
+sti-dvo:
+  Required properties:
+  must be a child of sti-tvout
+  - compatible: "st,stih<chip>-dvo"
+  - reg: Physical base address of the IP registers and length of memory mapped region.
+  - reg-names: names of the mapped memory regions listed in regs property in
+    the same order.
+  - clocks: from common clock binding: handle hardware IP needed clocks, the
+    number of clocks may depend of the SoC type.
+    See ../clocks/clock-bindings.txt for details.
+  - clock-names: names of the clocks listed in clocks property in the same
+    order.
+  - pinctrl-0: pin control handle
+  - pinctrl-name: names of the pin control to use
+  - sti,panel: phandle of the panel connected to the DVO output
+
 sti-hqvdp:
   must be a child of sti-display-subsystem
   Required properties:
@@ -198,6 +214,19 @@ Example:
                                clock-names     = "pix", "hddac";
                                clocks          = <&clockgen_c_vcc CLK_S_PIX_HD>, <&clockgen_c_vcc CLK_S_HDDAC>;
                        };
+
+                       sti-dvo@8d00400 {
+                               compatible      = "st,stih407-dvo";
+                               reg             = <0x8d00400 0x200>;
+                               reg-names       = "dvo-reg";
+                               clock-names     = "dvo_pix", "dvo",
+                                                 "main_parent", "aux_parent";
+                               clocks          = <&clk_s_d2_flexgen CLK_PIX_DVO>, <&clk_s_d2_flexgen CLK_DVO>,
+                                                 <&clk_s_d2_quadfs 0>, <&clk_s_d2_quadfs 1>;
+                               pinctrl-names   = "default";
+                               pinctrl-0       = <&pinctrl_dvo>;
+                               sti,panel       = <&panel_dvo>;
+                       };
                };
 
                sti-hqvdp@9c000000 {
index 032808843f90a3b1db0389b0a60dd075c9ea3ac6..24c5cdaba8d279a4b132fbd2f964ae1460b3fd0f 100644 (file)
@@ -4,7 +4,8 @@ This file provides information, what the device node
 for the davinci_emac interface contains.
 
 Required properties:
-- compatible: "ti,davinci-dm6467-emac" or "ti,am3517-emac"
+- compatible: "ti,davinci-dm6467-emac", "ti,am3517-emac" or
+  "ti,dm816-emac"
 - reg: Offset and length of the register set for the device
 - ti,davinci-ctrl-reg-offset: offset to control register
 - ti,davinci-ctrl-mod-reg-offset: offset to control module register
diff --git a/Documentation/devicetree/bindings/video/dw_hdmi-rockchip.txt b/Documentation/devicetree/bindings/video/dw_hdmi-rockchip.txt
new file mode 100644 (file)
index 0000000..668091f
--- /dev/null
@@ -0,0 +1,46 @@
+Rockchip specific extensions to the Synopsys Designware HDMI
+================================
+
+Required properties:
+- compatible: "rockchip,rk3288-dw-hdmi";
+- reg: Physical base address and length of the controller's registers.
+- clocks: phandle to hdmi iahb and isfr clocks.
+- clock-names: should be "iahb" "isfr"
+- rockchip,grf: this soc should set GRF regs to mux vopl/vopb.
+- interrupts: HDMI interrupt number
+- ports: contain a port node with endpoint definitions as defined in
+  Documentation/devicetree/bindings/media/video-interfaces.txt. For
+  vopb,set the reg = <0> and set the reg = <1> for vopl.
+- reg-io-width: the width of the reg:1,4, the value should be 4 on
+  rk3288 platform
+
+Optional properties
+- ddc-i2c-bus: phandle of an I2C controller used for DDC EDID probing
+- clocks, clock-names: phandle to the HDMI CEC clock, name should be "cec"
+
+Example:
+hdmi: hdmi@ff980000 {
+       compatible = "rockchip,rk3288-dw-hdmi";
+       reg = <0xff980000 0x20000>;
+       reg-io-width = <4>;
+       ddc-i2c-bus = <&i2c5>;
+       rockchip,grf = <&grf>;
+       interrupts = <GIC_SPI 103 IRQ_TYPE_LEVEL_HIGH>;
+       clocks = <&cru  PCLK_HDMI_CTRL>, <&cru SCLK_HDMI_HDCP>;
+       clock-names = "iahb", "isfr";
+       status = "disabled";
+       ports {
+               hdmi_in: port {
+                       #address-cells = <1>;
+                       #size-cells = <0>;
+                       hdmi_in_vopb: endpoint@0 {
+                               reg = <0>;
+                               remote-endpoint = <&vopb_out_hdmi>;
+                       };
+                       hdmi_in_vopl: endpoint@1 {
+                               reg = <1>;
+                               remote-endpoint = <&vopl_out_hdmi>;
+                       };
+               };
+       };
+};
index 5102830f276017135a05289e5c92bd87ae6e9d21..c902323928f700a356d7e8fd118cde2e680e2c94 100644 (file)
@@ -26,6 +26,10 @@ Required Properties:
       per LVDS encoder. The functional clocks must be named "du.x" with "x"
       being the channel numerical index. The LVDS clocks must be named
       "lvds.x" with "x" being the LVDS encoder numerical index.
+    - In addition to the functional and encoder clocks, all DU versions also
+      support externally supplied pixel clocks. Those clocks are optional.
+      When supplied they must be named "dclkin.x" with "x" being the input
+      clock numerical index.
 
 Required nodes:
 
index 4df73da11adc586344ad6474ccb66f09ee22d66e..176d4fe4f076be0c785de56ade5cbca399e591e2 100644 (file)
@@ -1277,6 +1277,7 @@ bytes respectively. Such letter suffixes can also be entirely omitted.
        i8042.notimeout [HW] Ignore timeout condition signalled by controller
        i8042.reset     [HW] Reset the controller during init and cleanup
        i8042.unlock    [HW] Unlock (ignore) the keylock
+       i8042.kbdreset  [HW] Reset device connected to KBD port
 
        i810=           [HW,DRM]
 
index 9bffdfc648dc66149401296d73eb6fc04564ebd1..85b0221791048aabb65bcee8090562384ab1c628 100644 (file)
@@ -66,6 +66,8 @@ fwmark_reflect - BOOLEAN
 route/max_size - INTEGER
        Maximum number of routes allowed in the kernel.  Increase
        this when using large numbers of interfaces and/or routes.
+       From linux kernel 3.6 onwards, this is deprecated for ipv4
+       as route cache is no longer used.
 
 neigh/default/gc_thresh1 - INTEGER
        Minimum number of entries to keep.  Garbage collector will not
index 230ce71f4d75529ff4e071ed25e7bf0b4f72cd3c..2b47704f75cb3bfedf836cf02c75afd82c91e405 100755 (executable)
@@ -389,9 +389,6 @@ def tcm_mod_build_configfs(proto_ident, fabric_mod_dir_var, fabric_mod_name):
        buf += "        .release_cmd                    = " + fabric_mod_name + "_release_cmd,\n"
        buf += "        .shutdown_session               = " + fabric_mod_name + "_shutdown_session,\n"
        buf += "        .close_session                  = " + fabric_mod_name + "_close_session,\n"
-       buf += "        .stop_session                   = " + fabric_mod_name + "_stop_session,\n"
-       buf += "        .fall_back_to_erl0              = " + fabric_mod_name + "_reset_nexus,\n"
-       buf += "        .sess_logged_in                 = " + fabric_mod_name + "_sess_logged_in,\n"
        buf += "        .sess_get_index                 = " + fabric_mod_name + "_sess_get_index,\n"
        buf += "        .sess_get_initiator_sid         = NULL,\n"
        buf += "        .write_pending                  = " + fabric_mod_name + "_write_pending,\n"
@@ -402,7 +399,7 @@ def tcm_mod_build_configfs(proto_ident, fabric_mod_dir_var, fabric_mod_name):
        buf += "        .queue_data_in                  = " + fabric_mod_name + "_queue_data_in,\n"
        buf += "        .queue_status                   = " + fabric_mod_name + "_queue_status,\n"
        buf += "        .queue_tm_rsp                   = " + fabric_mod_name + "_queue_tm_rsp,\n"
-       buf += "        .is_state_remove                = " + fabric_mod_name + "_is_state_remove,\n"
+       buf += "        .aborted_task                   = " + fabric_mod_name + "_aborted_task,\n"
        buf += "        /*\n"
        buf += "         * Setup function pointers for generic logic in target_core_fabric_configfs.c\n"
        buf += "         */\n"
@@ -428,7 +425,7 @@ def tcm_mod_build_configfs(proto_ident, fabric_mod_dir_var, fabric_mod_name):
        buf += "        /*\n"
        buf += "         * Register the top level struct config_item_type with TCM core\n"
        buf += "         */\n"
-       buf += "        fabric = target_fabric_configfs_init(THIS_MODULE, \"" + fabric_mod_name[4:] + "\");\n"
+       buf += "        fabric = target_fabric_configfs_init(THIS_MODULE, \"" + fabric_mod_name + "\");\n"
        buf += "        if (IS_ERR(fabric)) {\n"
        buf += "                printk(KERN_ERR \"target_fabric_configfs_init() failed\\n\");\n"
        buf += "                return PTR_ERR(fabric);\n"
@@ -595,7 +592,7 @@ def tcm_mod_dump_fabric_ops(proto_ident, fabric_mod_dir_var, fabric_mod_name):
                if re.search('get_fabric_name', fo):
                        buf += "char *" + fabric_mod_name + "_get_fabric_name(void)\n"
                        buf += "{\n"
-                       buf += "        return \"" + fabric_mod_name[4:] + "\";\n"
+                       buf += "        return \"" + fabric_mod_name + "\";\n"
                        buf += "}\n\n"
                        bufi += "char *" + fabric_mod_name + "_get_fabric_name(void);\n"
                        continue
@@ -820,27 +817,6 @@ def tcm_mod_dump_fabric_ops(proto_ident, fabric_mod_dir_var, fabric_mod_name):
                        buf += "}\n\n"
                        bufi += "void " + fabric_mod_name + "_close_session(struct se_session *);\n"
 
-               if re.search('stop_session\)\(', fo):
-                       buf += "void " + fabric_mod_name + "_stop_session(struct se_session *se_sess, int sess_sleep , int conn_sleep)\n"
-                       buf += "{\n"
-                       buf += "        return;\n"
-                       buf += "}\n\n"
-                       bufi += "void " + fabric_mod_name + "_stop_session(struct se_session *, int, int);\n"
-
-               if re.search('fall_back_to_erl0\)\(', fo):
-                       buf += "void " + fabric_mod_name + "_reset_nexus(struct se_session *se_sess)\n"
-                       buf += "{\n"
-                       buf += "        return;\n"
-                       buf += "}\n\n"
-                       bufi += "void " + fabric_mod_name + "_reset_nexus(struct se_session *);\n"
-
-               if re.search('sess_logged_in\)\(', fo):
-                       buf += "int " + fabric_mod_name + "_sess_logged_in(struct se_session *se_sess)\n"
-                       buf += "{\n"
-                       buf += "        return 0;\n"
-                       buf += "}\n\n"
-                       bufi += "int " + fabric_mod_name + "_sess_logged_in(struct se_session *);\n"
-
                if re.search('sess_get_index\)\(', fo):
                        buf += "u32 " + fabric_mod_name + "_sess_get_index(struct se_session *se_sess)\n"
                        buf += "{\n"
@@ -898,19 +874,18 @@ def tcm_mod_dump_fabric_ops(proto_ident, fabric_mod_dir_var, fabric_mod_name):
                        bufi += "int " + fabric_mod_name + "_queue_status(struct se_cmd *);\n"
 
                if re.search('queue_tm_rsp\)\(', fo):
-                       buf += "int " + fabric_mod_name + "_queue_tm_rsp(struct se_cmd *se_cmd)\n"
+                       buf += "void " + fabric_mod_name + "_queue_tm_rsp(struct se_cmd *se_cmd)\n"
                        buf += "{\n"
-                       buf += "        return 0;\n"
+                       buf += "        return;\n"
                        buf += "}\n\n"
-                       bufi += "int " + fabric_mod_name + "_queue_tm_rsp(struct se_cmd *);\n"
+                       bufi += "void " + fabric_mod_name + "_queue_tm_rsp(struct se_cmd *);\n"
 
-               if re.search('is_state_remove\)\(', fo):
-                       buf += "int " + fabric_mod_name + "_is_state_remove(struct se_cmd *se_cmd)\n"
+               if re.search('aborted_task\)\(', fo):
+                       buf += "void " + fabric_mod_name + "_aborted_task(struct se_cmd *se_cmd)\n"
                        buf += "{\n"
-                       buf += "        return 0;\n"
+                       buf += "        return;\n"
                        buf += "}\n\n"
-                       bufi += "int " + fabric_mod_name + "_is_state_remove(struct se_cmd *);\n"
-
+                       bufi += "void " + fabric_mod_name + "_aborted_task(struct se_cmd *);\n"
 
        ret = p.write(buf)
        if ret:
@@ -1018,11 +993,11 @@ def main(modname, proto_ident):
        tcm_mod_build_kbuild(fabric_mod_dir, fabric_mod_name)
        tcm_mod_build_kconfig(fabric_mod_dir, fabric_mod_name)
 
-       input = raw_input("Would you like to add " + fabric_mod_name + "to drivers/target/Makefile..? [yes,no]: ")
+       input = raw_input("Would you like to add " + fabric_mod_name + " to drivers/target/Makefile..? [yes,no]: ")
        if input == "yes" or input == "y":
                tcm_mod_add_kbuild(tcm_dir, fabric_mod_name)
 
-       input = raw_input("Would you like to add " + fabric_mod_name + "to drivers/target/Kconfig..? [yes,no]: ")
+       input = raw_input("Would you like to add " + fabric_mod_name + " to drivers/target/Kconfig..? [yes,no]: ")
        if input == "yes" or input == "y":
                tcm_mod_add_kconfig(tcm_dir, fabric_mod_name)
 
index fca24c931ec8dcb737012b6b67f6b88a8fef2223..753e47cc2e2036cd53e176241f579addd3b43ec1 100644 (file)
@@ -3,7 +3,7 @@ CPU cooling APIs How To
 
 Written by Amit Daniel Kachhap <amit.kachhap@linaro.org>
 
-Updated: 12 May 2012
+Updated: 6 Jan 2015
 
 Copyright (c)  2012 Samsung Electronics Co., Ltd(http://www.samsung.com)
 
@@ -25,7 +25,18 @@ the user. The registration APIs returns the cooling device pointer.
 
    clip_cpus: cpumask of cpus where the frequency constraints will happen.
 
-1.1.2 void cpufreq_cooling_unregister(struct thermal_cooling_device *cdev)
+1.1.2 struct thermal_cooling_device *of_cpufreq_cooling_register(
+       struct device_node *np, const struct cpumask *clip_cpus)
+
+    This interface function registers the cpufreq cooling device with
+    the name "thermal-cpufreq-%x" linking it with a device tree node, in
+    order to bind it via the thermal DT code. This api can support multiple
+    instances of cpufreq cooling devices.
+
+    np: pointer to the cooling device device tree node
+    clip_cpus: cpumask of cpus where the frequency constraints will happen.
+
+1.1.3 void cpufreq_cooling_unregister(struct thermal_cooling_device *cdev)
 
     This interface function unregisters the "thermal-cpufreq-%x" cooling device.
 
index 3589d67437f867e121bc36b0ff2b92e758499c04..aa97dffe59e1b1e6159d3c042bf1fd1ed0135240 100644 (file)
@@ -624,6 +624,8 @@ L:      dri-devel@lists.freedesktop.org
 T:      git git://people.freedesktop.org/~gabbayo/linux.git
 S:      Supported
 F:      drivers/gpu/drm/amd/amdkfd/
+F:     drivers/gpu/drm/amd/include/cik_structs.h
+F:     drivers/gpu/drm/amd/include/kgd_kfd_interface.h
 F:      drivers/gpu/drm/radeon/radeon_kfd.c
 F:      drivers/gpu/drm/radeon/radeon_kfd.h
 F:      include/uapi/linux/kfd_ioctl.h
@@ -754,13 +756,6 @@ L: linux-media@vger.kernel.org
 S:     Maintained
 F:     drivers/media/i2c/aptina-pll.*
 
-ARASAN COMPACT FLASH PATA CONTROLLER
-M:     Viresh Kumar <viresh.linux@gmail.com>
-L:     linux-ide@vger.kernel.org
-S:     Maintained
-F:     include/linux/pata_arasan_cf_data.h
-F:     drivers/ata/pata_arasan_cf.c
-
 ARC FRAMEBUFFER DRIVER
 M:     Jaya Kumar <jayalk@intworks.biz>
 S:     Maintained
@@ -2346,7 +2341,8 @@ CAN NETWORK LAYER
 M:     Oliver Hartkopp <socketcan@hartkopp.net>
 L:     linux-can@vger.kernel.org
 W:     http://gitorious.org/linux-can
-T:     git git://gitorious.org/linux-can/linux-can-next.git
+T:     git git://git.kernel.org/pub/scm/linux/kernel/git/mkl/linux-can.git
+T:     git git://git.kernel.org/pub/scm/linux/kernel/git/mkl/linux-can-next.git
 S:     Maintained
 F:     Documentation/networking/can.txt
 F:     net/can/
@@ -2361,7 +2357,8 @@ M:        Wolfgang Grandegger <wg@grandegger.com>
 M:     Marc Kleine-Budde <mkl@pengutronix.de>
 L:     linux-can@vger.kernel.org
 W:     http://gitorious.org/linux-can
-T:     git git://gitorious.org/linux-can/linux-can-next.git
+T:     git git://git.kernel.org/pub/scm/linux/kernel/git/mkl/linux-can.git
+T:     git git://git.kernel.org/pub/scm/linux/kernel/git/mkl/linux-can-next.git
 S:     Maintained
 F:     drivers/net/can/
 F:     include/linux/can/dev.h
@@ -3183,7 +3180,7 @@ L:        dmaengine@vger.kernel.org
 Q:     https://patchwork.kernel.org/project/linux-dmaengine/list/
 S:     Maintained
 F:     drivers/dma/
-F:     include/linux/dma*
+F:     include/linux/dmaengine.h
 F:     Documentation/dmaengine/
 T:     git git://git.infradead.org/users/vkoul/slave-dma.git
 
@@ -4749,7 +4746,7 @@ S:        Supported
 F:     drivers/scsi/ipr.*
 
 IBM Power Virtual Ethernet Device Driver
-M:     Santiago Leon <santil@linux.vnet.ibm.com>
+M:     Thomas Falcon <tlfalcon@linux.vnet.ibm.com>
 L:     netdev@vger.kernel.org
 S:     Supported
 F:     drivers/net/ethernet/ibm/ibmveth.*
@@ -4930,7 +4927,6 @@ F:        include/uapi/linux/inotify.h
 
 INPUT (KEYBOARD, MOUSE, JOYSTICK, TOUCHSCREEN) DRIVERS
 M:     Dmitry Torokhov <dmitry.torokhov@gmail.com>
-M:     Dmitry Torokhov <dtor@mail.ru>
 L:     linux-input@vger.kernel.org
 Q:     http://patchwork.kernel.org/project/linux-input/list/
 T:     git git://git.kernel.org/pub/scm/linux/kernel/git/dtor/input.git
@@ -5280,6 +5276,15 @@ W:       www.open-iscsi.org
 Q:     http://patchwork.kernel.org/project/linux-rdma/list/
 F:     drivers/infiniband/ulp/iser/
 
+ISCSI EXTENSIONS FOR RDMA (ISER) TARGET
+M:     Sagi Grimberg <sagig@mellanox.com>
+T:     git git://git.kernel.org/pub/scm/linux/kernel/git/nab/target-pending.git master
+L:     linux-rdma@vger.kernel.org
+L:     target-devel@vger.kernel.org
+S:     Supported
+W:     http://www.linux-iscsi.org
+F:     drivers/infiniband/ulp/isert
+
 ISDN SUBSYSTEM
 M:     Karsten Keil <isdn@linux-pingi.de>
 L:     isdn4linux@listserv.isdn4linux.de (subscribers-only)
@@ -5694,6 +5699,49 @@ F:       drivers/lguest/
 F:     include/linux/lguest*.h
 F:     tools/lguest/
 
+LIBATA SUBSYSTEM (Serial and Parallel ATA drivers)
+M:     Tejun Heo <tj@kernel.org>
+L:     linux-ide@vger.kernel.org
+T:     git git://git.kernel.org/pub/scm/linux/kernel/git/tj/libata.git
+S:     Maintained
+F:     drivers/ata/
+F:     include/linux/ata.h
+F:     include/linux/libata.h
+
+LIBATA PATA ARASAN COMPACT FLASH CONTROLLER
+M:     Viresh Kumar <viresh.linux@gmail.com>
+L:     linux-ide@vger.kernel.org
+T:     git git://git.kernel.org/pub/scm/linux/kernel/git/tj/libata.git
+S:     Maintained
+F:     include/linux/pata_arasan_cf_data.h
+F:     drivers/ata/pata_arasan_cf.c
+
+LIBATA PATA DRIVERS
+M:     Bartlomiej Zolnierkiewicz <b.zolnierkie@samsung.com>
+M:     Tejun Heo <tj@kernel.org>
+L:     linux-ide@vger.kernel.org
+T:     git git://git.kernel.org/pub/scm/linux/kernel/git/tj/libata.git
+S:     Maintained
+F:     drivers/ata/pata_*.c
+F:     drivers/ata/ata_generic.c
+
+LIBATA SATA AHCI PLATFORM devices support
+M:     Hans de Goede <hdegoede@redhat.com>
+M:     Tejun Heo <tj@kernel.org>
+L:     linux-ide@vger.kernel.org
+T:     git git://git.kernel.org/pub/scm/linux/kernel/git/tj/libata.git
+S:     Maintained
+F:     drivers/ata/ahci_platform.c
+F:     drivers/ata/libahci_platform.c
+F:     include/linux/ahci_platform.h
+
+LIBATA SATA PROMISE TX2/TX4 CONTROLLER DRIVER
+M:     Mikael Pettersson <mikpelinux@gmail.com>
+L:     linux-ide@vger.kernel.org
+T:     git git://git.kernel.org/pub/scm/linux/kernel/git/tj/libata.git
+S:     Maintained
+F:     drivers/ata/sata_promise.*
+
 LIBLOCKDEP
 M:     Sasha Levin <sasha.levin@oracle.com>
 S:     Maintained
@@ -7400,6 +7448,7 @@ F:        drivers/crypto/picoxcell*
 PIN CONTROL SUBSYSTEM
 M:     Linus Walleij <linus.walleij@linaro.org>
 L:     linux-gpio@vger.kernel.org
+T:     git git://git.kernel.org/pub/scm/linux/kernel/git/linusw/linux-pinctrl.git
 S:     Maintained
 F:     drivers/pinctrl/
 F:     include/linux/pinctrl/
@@ -7567,12 +7616,6 @@ W:       http://wireless.kernel.org/en/users/Drivers/p54
 S:     Obsolete
 F:     drivers/net/wireless/prism54/
 
-PROMISE SATA TX2/TX4 CONTROLLER LIBATA DRIVER
-M:     Mikael Pettersson <mikpelinux@gmail.com>
-L:     linux-ide@vger.kernel.org
-S:     Maintained
-F:     drivers/ata/sata_promise.*
-
 PS3 NETWORK SUPPORT
 M:     Geoff Levand <geoff@infradead.org>
 L:     netdev@vger.kernel.org
@@ -7738,8 +7781,7 @@ F:        Documentation/scsi/LICENSE.qla2xxx
 F:     drivers/scsi/qla2xxx/
 
 QLOGIC QLA4XXX iSCSI DRIVER
-M:     Vikas Chaudhary <vikas.chaudhary@qlogic.com>
-M:     iscsi-driver@qlogic.com
+M:     QLogic-Storage-Upstream@qlogic.com
 L:     linux-scsi@vger.kernel.org
 S:     Supported
 F:     Documentation/scsi/LICENSE.qla4xxx
@@ -8547,25 +8589,6 @@ S:       Maintained
 F:     drivers/misc/phantom.c
 F:     include/uapi/linux/phantom.h
 
-SERIAL ATA (SATA) SUBSYSTEM
-M:     Tejun Heo <tj@kernel.org>
-L:     linux-ide@vger.kernel.org
-T:     git git://git.kernel.org/pub/scm/linux/kernel/git/tj/libata.git
-S:     Supported
-F:     drivers/ata/
-F:     include/linux/ata.h
-F:     include/linux/libata.h
-
-SERIAL ATA AHCI PLATFORM devices support
-M:     Hans de Goede <hdegoede@redhat.com>
-M:     Tejun Heo <tj@kernel.org>
-L:     linux-ide@vger.kernel.org
-T:     git git://git.kernel.org/pub/scm/linux/kernel/git/tj/libata.git
-S:     Supported
-F:     drivers/ata/ahci_platform.c
-F:     drivers/ata/libahci_platform.c
-F:     include/linux/ahci_platform.h
-
 SERVER ENGINES 10Gbps iSCSI - BladeEngine 2 DRIVER
 M:     Jayamohan Kallickal <jayamohan.kallickal@emulex.com>
 L:     linux-scsi@vger.kernel.org
@@ -9534,7 +9557,8 @@ F:        drivers/platform/x86/thinkpad_acpi.c
 TI BANDGAP AND THERMAL DRIVER
 M:     Eduardo Valentin <edubezval@gmail.com>
 L:     linux-pm@vger.kernel.org
-S:     Supported
+L:     linux-omap@vger.kernel.org
+S:     Maintained
 F:     drivers/thermal/ti-soc-thermal/
 
 TI CLOCK DRIVER
index e41a3356abee83f08288362950bfceebd25ec3c2..fb93350cf6456c89649aff15a99efae74eca5cb8 100644 (file)
--- a/Makefile
+++ b/Makefile
@@ -1,7 +1,7 @@
 VERSION = 3
 PATCHLEVEL = 19
 SUBLEVEL = 0
-EXTRAVERSION = -rc4
+EXTRAVERSION = -rc5
 NAME = Diseased Newt
 
 # *DOCUMENTATION*
index 1467750e3377d161bddff0cfcce1f35d91c9261b..e8c6c600a5b69335bbea0fdabf70e7ccee7ff163 100644 (file)
                        interrupts = <26 IRQ_TYPE_LEVEL_HIGH 3>;
                        pinctrl-names = "default";
                        pinctrl-0 = <&pinctrl_fb>;
+                       clocks = <&lcd_clk>, <&lcd_clk>;
+                       clock-names = "lcdc_clk", "hclk";
                        status = "disabled";
                };
 
index 28e7e2060c3399c204f547b37fc325fa1069e8d8..a98ac1bd8f65124fe69d43aa8e8b467a2a7c911c 100644 (file)
@@ -65,6 +65,8 @@
 };
 
 &sdhci2 {
+       broken-cd;
+       bus-width = <8>;
        non-removable;
        status = "okay";
 };
index 35253c947a7cd0002211dac773d7f1f9723d6fce..e2f61f27944e24fd45cc65518126f932409ea610 100644 (file)
@@ -83,7 +83,8 @@
                        compatible = "mrvl,pxav3-mmc";
                        reg = <0xab1000 0x200>;
                        interrupts = <GIC_SPI 28 IRQ_TYPE_LEVEL_HIGH>;
-                       clocks = <&chip CLKID_SDIO1XIN>;
+                       clocks = <&chip CLKID_NFC_ECC>, <&chip CLKID_NFC>;
+                       clock-names = "io", "core";
                        status = "disabled";
                };
 
                                interrupt-parent = <&gic>;
                                interrupts = <GIC_SPI 3 IRQ_TYPE_LEVEL_HIGH>;
                        };
-
-                       gpio4: gpio@5000 {
-                               compatible = "snps,dw-apb-gpio";
-                               reg = <0x5000 0x400>;
-                               #address-cells = <1>;
-                               #size-cells = <0>;
-
-                               porte: gpio-port@4 {
-                                       compatible = "snps,dw-apb-gpio-port";
-                                       gpio-controller;
-                                       #gpio-cells = <2>;
-                                       snps,nr-gpios = <32>;
-                                       reg = <0>;
-                               };
-                       };
-
-                       gpio5: gpio@c000 {
-                               compatible = "snps,dw-apb-gpio";
-                               reg = <0xc000 0x400>;
-                               #address-cells = <1>;
-                               #size-cells = <0>;
-
-                               portf: gpio-port@5 {
-                                       compatible = "snps,dw-apb-gpio-port";
-                                       gpio-controller;
-                                       #gpio-cells = <2>;
-                                       snps,nr-gpios = <32>;
-                                       reg = <0>;
-                               };
-                       };
                };
 
                chip: chip-control@ea0000 {
                        ranges = <0 0xfc0000 0x10000>;
                        interrupt-parent = <&sic>;
 
+                       sm_gpio1: gpio@5000 {
+                               compatible = "snps,dw-apb-gpio";
+                               reg = <0x5000 0x400>;
+                               #address-cells = <1>;
+                               #size-cells = <0>;
+
+                               portf: gpio-port@5 {
+                                       compatible = "snps,dw-apb-gpio-port";
+                                       gpio-controller;
+                                       #gpio-cells = <2>;
+                                       snps,nr-gpios = <32>;
+                                       reg = <0>;
+                               };
+                       };
+
                        i2c2: i2c@7000 {
                                compatible = "snps,designware-i2c";
                                #address-cells = <1>;
                                status = "disabled";
                        };
 
+                       sm_gpio0: gpio@c000 {
+                               compatible = "snps,dw-apb-gpio";
+                               reg = <0xc000 0x400>;
+                               #address-cells = <1>;
+                               #size-cells = <0>;
+
+                               porte: gpio-port@4 {
+                                       compatible = "snps,dw-apb-gpio-port";
+                                       gpio-controller;
+                                       #gpio-cells = <2>;
+                                       snps,nr-gpios = <32>;
+                                       reg = <0>;
+                               };
+                       };
+
                        sysctrl: pin-controller@d000 {
                                compatible = "marvell,berlin2q-system-ctrl";
                                reg = <0xd000 0x100>;
index 10b725c7bfc02fc79e8c694150ec1e23c5493175..ad4118f7e1a6106139af2a6bfe56d3534c306af9 100644 (file)
                };
                partition@5 {
                        label = "QSPI.u-boot-spl-os";
-                       reg = <0x00140000 0x00010000>;
+                       reg = <0x00140000 0x00080000>;
                };
                partition@6 {
                        label = "QSPI.u-boot-env";
-                       reg = <0x00150000 0x00010000>;
+                       reg = <0x001c0000 0x00010000>;
                };
                partition@7 {
                        label = "QSPI.u-boot-env.backup1";
-                       reg = <0x00160000 0x0010000>;
+                       reg = <0x001d0000 0x0010000>;
                };
                partition@8 {
                        label = "QSPI.kernel";
-                       reg = <0x00170000 0x0800000>;
+                       reg = <0x001e0000 0x0800000>;
                };
                partition@9 {
                        label = "QSPI.file-system";
-                       reg = <0x00970000 0x01690000>;
+                       reg = <0x009e0000 0x01620000>;
                };
        };
 };
index 0a229fcd7acfdfff4e07b4359cf0c7776e510efc..d75c89d7666a0a0bea5fff5139439f8090eee793 100644 (file)
 
        dp_phy: video-phy@10040720 {
                compatible = "samsung,exynos5250-dp-video-phy";
-               reg = <0x10040720 4>;
+               samsung,pmu-syscon = <&pmu_system_controller>;
                #phy-cells = <0>;
        };
 
index aa7a7d727a7e80033df0cddb0b9cce8596d48ddc..db2c1c4cd90076b5c7bb47d12737e46bf4938264 100644 (file)
 &usbdrd_dwc3_1 {
        dr_mode = "host";
 };
+
+&cci {
+       status = "disabled";
+};
index 517e50f6760b0cf4d77bc55bf899f0aa5e3667a1..6d38f8bfd0e68e71358608a9af0ec32dbc5a53c2 100644 (file)
                };
        };
 
-       cci@10d20000 {
+       cci: cci@10d20000 {
                compatible = "arm,cci-400";
                #address-cells = <1>;
                #size-cells = <1>;
        };
 
        dp_phy: video-phy@10040728 {
-               compatible = "samsung,exynos5250-dp-video-phy";
-               reg = <0x10040728 4>;
+               compatible = "samsung,exynos5420-dp-video-phy";
+               samsung,pmu-syscon = <&pmu_system_controller>;
                #phy-cells = <0>;
        };
 
index 58d3c3cf2923f5ffae5e1657140fc7b94f4090c1..d238676a910753a4d7b2ff9e80d4599fe36da057 100644 (file)
                                #size-cells = <0>;
                                compatible = "fsl,imx25-cspi", "fsl,imx35-cspi";
                                reg = <0x43fa4000 0x4000>;
-                               clocks = <&clks 62>, <&clks 62>;
+                               clocks = <&clks 78>, <&clks 78>;
                                clock-names = "ipg", "per";
                                interrupts = <14>;
                                status = "disabled";
index 56569cecaa7852795ab94f6046321f13bddd837e..649befeb2cf96ef4b968f809a98d5d718227b002 100644 (file)
                #address-cells = <1>;
                #size-cells = <0>;
 
-               reg_usbh1_vbus: regulator@0 {
-                       compatible = "regulator-fixed";
-                       pinctrl-names = "default";
-                       pinctrl-0 = <&pinctrl_usbh1reg>;
-                       reg = <0>;
-                       regulator-name = "usbh1_vbus";
-                       regulator-min-microvolt = <5000000>;
-                       regulator-max-microvolt = <5000000>;
-                       gpio = <&gpio2 5 GPIO_ACTIVE_HIGH>;
-                       enable-active-high;
-               };
-
-               reg_usbotg_vbus: regulator@1 {
+               reg_hub_reset: regulator@0 {
                        compatible = "regulator-fixed";
                        pinctrl-names = "default";
                        pinctrl-0 = <&pinctrl_usbotgreg>;
-                       reg = <1>;
-                       regulator-name = "usbotg_vbus";
+                       reg = <0>;
+                       regulator-name = "hub_reset";
                        regulator-min-microvolt = <5000000>;
                        regulator-max-microvolt = <5000000>;
                        gpio = <&gpio1 7 GPIO_ACTIVE_HIGH>;
                        reg = <0>;
                        clocks = <&clks IMX5_CLK_DUMMY>;
                        clock-names = "main_clk";
+                       reset-gpios = <&gpio2 5 GPIO_ACTIVE_LOW>;
                };
        };
 };
 &usbh1 {
        pinctrl-names = "default";
        pinctrl-0 = <&pinctrl_usbh1>;
-       vbus-supply = <&reg_usbh1_vbus>;
+       vbus-supply = <&reg_hub_reset>;
        fsl,usbphy = <&usbh1phy>;
        phy_type = "ulpi";
        status = "okay";
        dr_mode = "otg";
        disable-over-current;
        phy_type = "utmi_wide";
-       vbus-supply = <&reg_usbotg_vbus>;
        status = "okay";
 };
 
index 4fc03b7f1ceec52fe5d327974cd2929127de21f9..2109d0763c1b6dca448449ba74709c6ced666cbb 100644 (file)
                        vpu: vpu@02040000 {
                                compatible = "cnm,coda960";
                                reg = <0x02040000 0x3c000>;
-                               interrupts = <0 3 IRQ_TYPE_LEVEL_HIGH>,
-                                            <0 12 IRQ_TYPE_LEVEL_HIGH>;
+                               interrupts = <0 12 IRQ_TYPE_LEVEL_HIGH>,
+                                            <0 3 IRQ_TYPE_LEVEL_HIGH>;
                                interrupt-names = "bit", "jpeg";
                                clocks = <&clks IMX6QDL_CLK_VPU_AXI>,
                                         <&clks IMX6QDL_CLK_MMDC_CH0_AXI>,
index 1e6e5cc1c14cf283fb8b3bd9321f44218fbe4fb3..8c1febd7e3f2757176d1ba0ab14450133010d177 100644 (file)
        pinctrl-0 = <&pinctrl_enet1>;
        phy-supply = <&reg_enet_3v3>;
        phy-mode = "rgmii";
+       phy-handle = <&ethphy1>;
        status = "okay";
+
+       mdio {
+               #address-cells = <1>;
+               #size-cells = <0>;
+
+               ethphy1: ethernet-phy@0 {
+                       reg = <0>;
+               };
+
+               ethphy2: ethernet-phy@1 {
+                       reg = <1>;
+               };
+       };
 };
 
 &fec2 {
        pinctrl-names = "default";
        pinctrl-0 = <&pinctrl_enet2>;
        phy-mode = "rgmii";
+       phy-handle = <&ethphy2>;
        status = "okay";
 };
 
index 657da14cb4b5b2cc96bc1b4139c871f5fac65307..c70bb27ac65a63e1f197408e4a9ccb822d3407c4 100644 (file)
                scfg: scfg@1570000 {
                        compatible = "fsl,ls1021a-scfg", "syscon";
                        reg = <0x0 0x1570000 0x0 0x10000>;
+                       big-endian;
                };
 
                clockgen: clocking@1ee1000 {
index 53f3ca064140470866dbfe12773af1ddb76d1632..b550c41b46f1ecc83fcc9abf551fbeff4f44e2a0 100644 (file)
                };
        };
 
+       /* Ethernet is on some early development boards and qemu */
        ethernet@gpmc {
                compatible = "smsc,lan91c94";
-
-               status = "disabled";
-
                interrupt-parent = <&gpio2>;
                interrupts = <22 IRQ_TYPE_LEVEL_HIGH>;  /* gpio54 */
                reg = <1 0x300 0xf>;            /* 16 byte IO range at offset 0x300 */
index 3e067dd65d0c87d7845809bd121859f86de1a879..6194d673e80be828c7067bccf498569c121b2a74 100644 (file)
 };
 
 &pinctrl {
+       pcfg_pull_none_drv_8ma: pcfg-pull-none-drv-8ma {
+               drive-strength = <8>;
+       };
+
+       pcfg_pull_up_drv_8ma: pcfg-pull-up-drv-8ma {
+               bias-pull-up;
+               drive-strength = <8>;
+       };
+
        backlight {
                bl_en: bl-en {
                        rockchip,pins = <7 2 RK_FUNC_GPIO &pcfg_pull_none>;
                };
        };
 
+       sdmmc {
+               /*
+                * Default drive strength isn't enough to achieve even
+                * high-speed mode on EVB board so bump up to 8ma.
+                */
+               sdmmc_bus4: sdmmc-bus4 {
+                       rockchip,pins = <6 16 RK_FUNC_1 &pcfg_pull_up_drv_8ma>,
+                                       <6 17 RK_FUNC_1 &pcfg_pull_up_drv_8ma>,
+                                       <6 18 RK_FUNC_1 &pcfg_pull_up_drv_8ma>,
+                                       <6 19 RK_FUNC_1 &pcfg_pull_up_drv_8ma>;
+               };
+
+               sdmmc_clk: sdmmc-clk {
+                       rockchip,pins = <6 20 RK_FUNC_1 &pcfg_pull_none_drv_8ma>;
+               };
+
+               sdmmc_cmd: sdmmc-cmd {
+                       rockchip,pins = <6 21 RK_FUNC_1 &pcfg_pull_up_drv_8ma>;
+               };
+       };
+
        usb {
                host_vbus_drv: host-vbus-drv {
                        rockchip,pins = <0 14 RK_FUNC_GPIO &pcfg_pull_none>;
index 49c10d33df302b7d967f0861c1424f636026a943..77e03655aca3626ad369b81b572b755987fd1609 100644 (file)
                        "Headphone Jack", "HPOUTR",
                        "IN2L", "Line In Jack",
                        "IN2R", "Line In Jack",
-                       "MICBIAS", "IN1L",
+                       "Mic", "MICBIAS",
                        "IN1L", "Mic";
 
                atmel,ssc-controller = <&ssc0>;
index 1b0f30c2c4a58d907aafd9d54e80d11e80d5722c..b94995d1889fc3ca780d69ac79a9c3be53620189 100644 (file)
 
                        pit: timer@fc068630 {
                                compatible = "atmel,at91sam9260-pit";
-                               reg = <0xfc068630 0xf>;
+                               reg = <0xfc068630 0x10>;
                                interrupts = <3 IRQ_TYPE_LEVEL_HIGH 5>;
                                clocks = <&h32ck>;
                        };
index a8c00ee7522a1872ee5af06debe66c6acdba49f8..3d0b8755caeee62f77ac214d343ab40cebba2ce0 100644 (file)
                stmpe2401_1 {
                        stmpe2401_1_nhk_mode: stmpe2401_1_nhk {
                                nhk_cfg1 {
-                                       ste,pins = "GPIO76_B20"; // IRQ line
+                                       pins = "GPIO76_B20"; // IRQ line
                                        ste,input = <0>;
                                };
                                nhk_cfg2 {
-                                       ste,pins = "GPIO77_B8"; // reset line
+                                       pins = "GPIO77_B8"; // reset line
                                        ste,output = <1>;
                                };
                        };
                stmpe2401_2 {
                        stmpe2401_2_nhk_mode: stmpe2401_2_nhk {
                                nhk_cfg1 {
-                                       ste,pins = "GPIO78_A8"; // IRQ line
+                                       pins = "GPIO78_A8"; // IRQ line
                                        ste,input = <0>;
                                };
                                nhk_cfg2 {
-                                       ste,pins = "GPIO79_C9"; // reset line
+                                       pins = "GPIO79_C9"; // reset line
                                        ste,output = <1>;
                                };
                        };
index a0f762159cb26501b517a1af0d529da8abc42283..f2b64b1b00fa5231fc2493164fcc89f434687cd1 100644 (file)
 
 &fec0 {
        phy-mode = "rmii";
+       phy-handle = <&ethphy0>;
        pinctrl-names = "default";
        pinctrl-0 = <&pinctrl_fec0>;
        status = "okay";
+
+       mdio {
+               #address-cells = <1>;
+               #size-cells = <0>;
+
+               ethphy0: ethernet-phy@0 {
+                       reg = <0>;
+               };
+
+               ethphy1: ethernet-phy@1 {
+                       reg = <1>;
+               };
+       };
 };
 
 &fec1 {
        phy-mode = "rmii";
+       phy-handle = <&ethphy1>;
        pinctrl-names = "default";
        pinctrl-0 = <&pinctrl_fec1>;
        status = "okay";
index 5ef14de00a29ba2f433fc93a47d95912569817c8..3d0c5d65c741933fad5947aa028dfdf11f7eda4d 100644 (file)
@@ -84,7 +84,8 @@ CONFIG_DEBUG_GPIO=y
 CONFIG_POWER_SUPPLY=y
 CONFIG_BATTERY_SBS=y
 CONFIG_CHARGER_TPS65090=y
-# CONFIG_HWMON is not set
+CONFIG_HWMON=y
+CONFIG_SENSORS_LM90=y
 CONFIG_THERMAL=y
 CONFIG_EXYNOS_THERMAL=y
 CONFIG_EXYNOS_THERMAL_CORE=y
@@ -109,11 +110,26 @@ CONFIG_REGULATOR_S2MPA01=y
 CONFIG_REGULATOR_S2MPS11=y
 CONFIG_REGULATOR_S5M8767=y
 CONFIG_REGULATOR_TPS65090=y
+CONFIG_DRM=y
+CONFIG_DRM_BRIDGE=y
+CONFIG_DRM_PTN3460=y
+CONFIG_DRM_PS8622=y
+CONFIG_DRM_EXYNOS=y
+CONFIG_DRM_EXYNOS_FIMD=y
+CONFIG_DRM_EXYNOS_DP=y
+CONFIG_DRM_PANEL=y
+CONFIG_DRM_PANEL_SIMPLE=y
 CONFIG_FB=y
 CONFIG_FB_MODE_HELPERS=y
 CONFIG_FB_SIMPLE=y
 CONFIG_EXYNOS_VIDEO=y
 CONFIG_EXYNOS_MIPI_DSI=y
+CONFIG_BACKLIGHT_LCD_SUPPORT=y
+CONFIG_LCD_CLASS_DEVICE=y
+CONFIG_LCD_PLATFORM=y
+CONFIG_BACKLIGHT_CLASS_DEVICE=y
+CONFIG_BACKLIGHT_GENERIC=y
+CONFIG_BACKLIGHT_PWM=y
 CONFIG_FRAMEBUFFER_CONSOLE=y
 CONFIG_FONTS=y
 CONFIG_FONT_7x14=y
index c2c3a852af9fcb28a4fc03bf69322fad6cf52f79..667d9d52aa01aaa230bd2e12a9b4575778285f38 100644 (file)
@@ -68,7 +68,7 @@ CONFIG_CPU_FREQ_DEFAULT_GOV_ONDEMAND=y
 CONFIG_CPU_FREQ_GOV_POWERSAVE=y
 CONFIG_CPU_FREQ_GOV_USERSPACE=y
 CONFIG_CPU_FREQ_GOV_CONSERVATIVE=y
-CONFIG_GENERIC_CPUFREQ_CPU0=y
+CONFIG_CPUFREQ_DT=y
 # CONFIG_ARM_OMAP2PLUS_CPUFREQ is not set
 CONFIG_CPU_IDLE=y
 CONFIG_BINFMT_MISC=y
index 8fb9ef5333f17648d8a28aaa0385badc9c0ed65a..97f7367d32b8a2b9af60abb3f6b4df68dd860489 100644 (file)
@@ -17,6 +17,7 @@
 #include <linux/of_platform.h>
 #include <linux/phy.h>
 #include <linux/clk-provider.h>
+#include <linux/phy.h>
 
 #include <asm/setup.h>
 #include <asm/irq.h>
 
 #include "generic.h"
 
+static int ksz8081_phy_fixup(struct phy_device *phy)
+{
+       int value;
+
+       value = phy_read(phy, 0x16);
+       value &= ~0x20;
+       phy_write(phy, 0x16, value);
+
+       return 0;
+}
+
 static void __init sama5_dt_device_init(void)
 {
+       if (of_machine_is_compatible("atmel,sama5d4ek") &&
+          IS_ENABLED(CONFIG_PHYLIB)) {
+               phy_register_fixup_for_id("fc028000.etherne:00",
+                                               ksz8081_phy_fixup);
+       }
+
        of_platform_populate(NULL, of_default_bus_match_table, NULL, NULL);
 }
 
index 5951660d1bd2363db0326cd83b07fcec7cc908f1..2daef619d0534d626daef9ac2bfd8fcacbb91a19 100644 (file)
@@ -144,7 +144,7 @@ static void __init imx6q_clocks_init(struct device_node *ccm_node)
                post_div_table[1].div = 1;
                post_div_table[2].div = 1;
                video_div_table[1].div = 1;
-               video_div_table[2].div = 1;
+               video_div_table[3].div = 1;
        }
 
        clk[IMX6QDL_PLL1_BYPASS_SRC] = imx_clk_mux("pll1_bypass_src", base + 0x00, 14, 2, pll_bypass_src_sels, ARRAY_SIZE(pll_bypass_src_sels));
index 17354a11356fbd0291ca5629db26446370c951d2..5a3e5a159e708b35a13427b6c766d48bc8cf15b0 100644 (file)
@@ -558,6 +558,9 @@ static void __init imx6sx_clocks_init(struct device_node *ccm_node)
        clk_set_parent(clks[IMX6SX_CLK_GPU_CORE_SEL], clks[IMX6SX_CLK_PLL3_PFD0]);
        clk_set_parent(clks[IMX6SX_CLK_GPU_AXI_SEL], clks[IMX6SX_CLK_PLL3_PFD0]);
 
+       clk_set_parent(clks[IMX6SX_CLK_QSPI1_SEL], clks[IMX6SX_CLK_PLL2_BUS]);
+       clk_set_parent(clks[IMX6SX_CLK_QSPI2_SEL], clks[IMX6SX_CLK_PLL2_BUS]);
+
        /* Set initial power mode */
        imx6q_set_lpm(WAIT_CLOCKED);
 }
index 608079a1aba6774e5ff6682354ecc08ba2d7a882..b61c049f92d6a361de57b16fe11c4773c12b88c6 100644 (file)
@@ -77,6 +77,24 @@ MACHINE_END
 #endif
 
 #ifdef CONFIG_ARCH_OMAP3
+/* Some boards need board name for legacy userspace in /proc/cpuinfo */
+static const char *const n900_boards_compat[] __initconst = {
+       "nokia,omap3-n900",
+       NULL,
+};
+
+DT_MACHINE_START(OMAP3_N900_DT, "Nokia RX-51 board")
+       .reserve        = omap_reserve,
+       .map_io         = omap3_map_io,
+       .init_early     = omap3430_init_early,
+       .init_machine   = omap_generic_init,
+       .init_late      = omap3_init_late,
+       .init_time      = omap3_sync32k_timer_init,
+       .dt_compat      = n900_boards_compat,
+       .restart        = omap3xxx_restart,
+MACHINE_END
+
+/* Generic omap3 boards, most boards can use these */
 static const char *const omap3_boards_compat[] __initconst = {
        "ti,omap3430",
        "ti,omap3",
index 377eea849e7bcdaf1142f6b1087ed6857a92b046..db57741c9c8ae69175f007ddca876c2bd8afe9cc 100644 (file)
@@ -249,6 +249,7 @@ extern void omap4_cpu_die(unsigned int cpu);
 extern struct smp_operations omap4_smp_ops;
 
 extern void omap5_secondary_startup(void);
+extern void omap5_secondary_hyp_startup(void);
 #endif
 
 #if defined(CONFIG_SMP) && defined(CONFIG_PM)
index a3c013345c45fa3b495924edaaa8628e636e147d..a80ac2d70bb1bca42084187851c09b914cd51871 100644 (file)
 #define OMAP5XXX_CONTROL_STATUS                0x134
 #define OMAP5_DEVICETYPE_MASK          (0x7 << 6)
 
+/* DRA7XX CONTROL CORE BOOTSTRAP */
+#define DRA7_CTRL_CORE_BOOTSTRAP       0x6c4
+#define DRA7_SPEEDSELECT_MASK          (0x3 << 8)
+
 /*
  * REVISIT: This list of registers is not comprehensive - there are more
  * that should be added.
index 4993d4bfe9b2a579d7adcc37726cb6828a78f130..6d1dffca6c7b6d68f3bd6e29a16bf5334c54a5fb 100644 (file)
@@ -22,6 +22,7 @@
 
 /* Physical address needed since MMU not enabled yet on secondary core */
 #define AUX_CORE_BOOT0_PA                      0x48281800
+#define API_HYP_ENTRY                          0x102
 
 /*
  * OMAP5 specific entry point for secondary CPU to jump from ROM
@@ -40,6 +41,26 @@ wait:        ldr     r2, =AUX_CORE_BOOT0_PA  @ read from AuxCoreBoot0
        bne     wait
        b       secondary_startup
 ENDPROC(omap5_secondary_startup)
+/*
+ * Same as omap5_secondary_startup except we call into the ROM to
+ * enable HYP mode first.  This is called instead of
+ * omap5_secondary_startup if the primary CPU was put into HYP mode by
+ * the boot loader.
+ */
+ENTRY(omap5_secondary_hyp_startup)
+wait_2:        ldr     r2, =AUX_CORE_BOOT0_PA  @ read from AuxCoreBoot0
+       ldr     r0, [r2]
+       mov     r0, r0, lsr #5
+       mrc     p15, 0, r4, c0, c0, 5
+       and     r4, r4, #0x0f
+       cmp     r0, r4
+       bne     wait_2
+       ldr     r12, =API_HYP_ENTRY
+       adr     r0, hyp_boot
+       smc     #0
+hyp_boot:
+       b       secondary_startup
+ENDPROC(omap5_secondary_hyp_startup)
 /*
  * OMAP4 specific entry point for secondary CPU to jump from ROM
  * code.  This routine also provides a holding flag into which
index 256e84ef0f679072324892a04d90817b81ceee36..5305ec7341eca5579398a10b72f263a2fbbe8e0e 100644 (file)
@@ -22,6 +22,7 @@
 #include <linux/irqchip/arm-gic.h>
 
 #include <asm/smp_scu.h>
+#include <asm/virt.h>
 
 #include "omap-secure.h"
 #include "omap-wakeupgen.h"
@@ -227,8 +228,16 @@ static void __init omap4_smp_prepare_cpus(unsigned int max_cpus)
        if (omap_secure_apis_support())
                omap_auxcoreboot_addr(virt_to_phys(startup_addr));
        else
-               writel_relaxed(virt_to_phys(omap5_secondary_startup),
-                              base + OMAP_AUX_CORE_BOOT_1);
+               /*
+                * If the boot CPU is in HYP mode then start secondary
+                * CPU in HYP mode as well.
+                */
+               if ((__boot_cpu_mode & MODE_MASK) == HYP_MODE)
+                       writel_relaxed(virt_to_phys(omap5_secondary_hyp_startup),
+                                      base + OMAP_AUX_CORE_BOOT_1);
+               else
+                       writel_relaxed(virt_to_phys(omap5_secondary_startup),
+                                      base + OMAP_AUX_CORE_BOOT_1);
 
 }
 
index 4f61148ec1689b667f30a5259aa98037c5fa06ec..7d45c84c69ba38a3da362456c941bb39ef90d7a2 100644 (file)
@@ -54,6 +54,7 @@
 
 #include "soc.h"
 #include "common.h"
+#include "control.h"
 #include "powerdomain.h"
 #include "omap-secure.h"
 
@@ -496,7 +497,8 @@ static void __init realtime_counter_init(void)
        void __iomem *base;
        static struct clk *sys_clk;
        unsigned long rate;
-       unsigned int reg, num, den;
+       unsigned int reg;
+       unsigned long long num, den;
 
        base = ioremap(REALTIME_COUNTER_BASE, SZ_32);
        if (!base) {
@@ -511,13 +513,42 @@ static void __init realtime_counter_init(void)
        }
 
        rate = clk_get_rate(sys_clk);
+
+       if (soc_is_dra7xx()) {
+               /*
+                * Errata i856 says the 32.768KHz crystal does not start at
+                * power on, so the CPU falls back to an emulated 32KHz clock
+                * based on sysclk / 610 instead. This causes the master counter
+                * frequency to not be 6.144MHz but at sysclk / 610 * 375 / 2
+                * (OR sysclk * 75 / 244)
+                *
+                * This affects at least the DRA7/AM572x 1.0, 1.1 revisions.
+                * Of course any board built without a populated 32.768KHz
+                * crystal would also need this fix even if the CPU is fixed
+                * later.
+                *
+                * Either case can be detected by using the two speedselect bits
+                * If they are not 0, then the 32.768KHz clock driving the
+                * coarse counter that corrects the fine counter every time it
+                * ticks is actually rate/610 rather than 32.768KHz and we
+                * should compensate to avoid the 570ppm (at 20MHz, much worse
+                * at other rates) too fast system time.
+                */
+               reg = omap_ctrl_readl(DRA7_CTRL_CORE_BOOTSTRAP);
+               if (reg & DRA7_SPEEDSELECT_MASK) {
+                       num = 75;
+                       den = 244;
+                       goto sysclk1_based;
+               }
+       }
+
        /* Numerator/denumerator values refer TRM Realtime Counter section */
        switch (rate) {
-       case 1200000:
+       case 12000000:
                num = 64;
                den = 125;
                break;
-       case 1300000:
+       case 13000000:
                num = 768;
                den = 1625;
                break;
@@ -529,11 +560,11 @@ static void __init realtime_counter_init(void)
                num = 192;
                den = 625;
                break;
-       case 2600000:
+       case 26000000:
                num = 384;
                den = 1625;
                break;
-       case 2700000:
+       case 27000000:
                num = 256;
                den = 1125;
                break;
@@ -545,6 +576,7 @@ static void __init realtime_counter_init(void)
                break;
        }
 
+sysclk1_based:
        /* Program numerator and denumerator registers */
        reg = readl_relaxed(base + INCREMENTER_NUMERATOR_OFFSET) &
                        NUMERATOR_DENUMERATOR_MASK;
@@ -556,7 +588,7 @@ static void __init realtime_counter_init(void)
        reg |= den;
        writel_relaxed(reg, base + INCREMENTER_DENUMERATOR_RELOAD_OFFSET);
 
-       arch_timer_freq = (rate / den) * num;
+       arch_timer_freq = DIV_ROUND_UP_ULL(rate * num, den);
        set_cntfreq();
 
        iounmap(base);
index d226b71d21d5c6c0bdb702af93323f59934b22d4..a611f48525828fcef5cb1dbacc9d2430f5de8867 100644 (file)
 #include <linux/init.h>
 #include <linux/of_platform.h>
 #include <linux/irqchip.h>
+#include <linux/clk-provider.h>
+#include <linux/clocksource.h>
+#include <linux/mfd/syscon.h>
+#include <linux/regmap.h>
 #include <asm/mach/arch.h>
 #include <asm/mach/map.h>
 #include <asm/hardware/cache-l2x0.h>
 #include "core.h"
 
+#define RK3288_GRF_SOC_CON0 0x244
+
+static void __init rockchip_timer_init(void)
+{
+       if (of_machine_is_compatible("rockchip,rk3288")) {
+               struct regmap *grf;
+
+               /*
+                * Disable auto jtag/sdmmc switching that causes issues
+                * with the mmc controllers making them unreliable
+                */
+               grf = syscon_regmap_lookup_by_compatible("rockchip,rk3288-grf");
+               if (!IS_ERR(grf))
+                       regmap_write(grf, RK3288_GRF_SOC_CON0, 0x10000000);
+               else
+                       pr_err("rockchip: could not get grf syscon\n");
+       }
+
+       of_clk_init(NULL);
+       clocksource_of_init();
+}
+
 static void __init rockchip_dt_init(void)
 {
        of_platform_populate(NULL, of_default_bus_match_table, NULL, NULL);
@@ -42,6 +68,7 @@ static const char * const rockchip_board_dt_compat[] = {
 DT_MACHINE_START(ROCKCHIP_DT, "Rockchip Cortex-A9 (Device Tree)")
        .l2c_aux_val    = 0,
        .l2c_aux_mask   = ~0,
+       .init_time      = rockchip_timer_init,
        .dt_compat      = rockchip_board_dt_compat,
        .init_machine   = rockchip_dt_init,
 MACHINE_END
index 79ad93dfdae4ee7083f2c2f1351ee863355d20c4..d191cf4197313482b961f1a6ed91f11954eff9a4 100644 (file)
@@ -800,7 +800,14 @@ void __init r8a7740_init_irq_of(void)
        void __iomem *intc_msk_base = ioremap_nocache(0xe6900040, 0x10);
        void __iomem *pfc_inta_ctrl = ioremap_nocache(0xe605807c, 0x4);
 
+#ifdef CONFIG_ARCH_SHMOBILE_LEGACY
+       void __iomem *gic_dist_base = ioremap_nocache(0xc2800000, 0x1000);
+       void __iomem *gic_cpu_base = ioremap_nocache(0xc2000000, 0x1000);
+
+       gic_init(0, 29, gic_dist_base, gic_cpu_base);
+#else
        irqchip_init();
+#endif
 
        /* route signals to GIC */
        iowrite32(0x0, pfc_inta_ctrl);
index 93ebe3430bfe707ac234b35f37deb54a1998a531..fb5e1bb34be80b1d5c529a728e55b7a7d41fa8c8 100644 (file)
@@ -595,6 +595,7 @@ static struct platform_device ipmmu_device = {
 
 static struct renesas_intc_irqpin_config irqpin0_platform_data = {
        .irq_base = irq_pin(0), /* IRQ0 -> IRQ7 */
+       .control_parent = true,
 };
 
 static struct resource irqpin0_resources[] = {
@@ -656,6 +657,7 @@ static struct platform_device irqpin1_device = {
 
 static struct renesas_intc_irqpin_config irqpin2_platform_data = {
        .irq_base = irq_pin(16), /* IRQ16 -> IRQ23 */
+       .control_parent = true,
 };
 
 static struct resource irqpin2_resources[] = {
@@ -686,6 +688,7 @@ static struct platform_device irqpin2_device = {
 
 static struct renesas_intc_irqpin_config irqpin3_platform_data = {
        .irq_base = irq_pin(24), /* IRQ24 -> IRQ31 */
+       .control_parent = true,
 };
 
 static struct resource irqpin3_resources[] = {
index 8127e45e263752821c833d1c354a8033372b2a47..865a7e28ea2d166efc0f27911970fd480bce4c3d 100644 (file)
@@ -41,6 +41,8 @@ void kvm_inject_pabt(struct kvm_vcpu *vcpu, unsigned long addr);
 static inline void vcpu_reset_hcr(struct kvm_vcpu *vcpu)
 {
        vcpu->arch.hcr_el2 = HCR_GUEST_FLAGS;
+       if (test_bit(KVM_ARM_VCPU_EL1_32BIT, vcpu->arch.features))
+               vcpu->arch.hcr_el2 &= ~HCR_RW;
 }
 
 static inline unsigned long *vcpu_pc(const struct kvm_vcpu *vcpu)
index b780c6c76eec6ad9bef97543bca351a2f7225479..23e9432ac11240a15b5dc4fecfe7d275cdfb10db 100644 (file)
@@ -44,7 +44,7 @@
 #define __ARM_NR_compat_cacheflush     (__ARM_NR_COMPAT_BASE+2)
 #define __ARM_NR_compat_set_tls                (__ARM_NR_COMPAT_BASE+5)
 
-#define __NR_compat_syscalls           387
+#define __NR_compat_syscalls           388
 #endif
 
 #define __ARCH_WANT_SYS_CLONE
index 8893cebcea5b8d903fed25db1a6dcb6effa14cef..27224426e0bf920de713c22cd4b6ca125c84d9bf 100644 (file)
@@ -795,3 +795,5 @@ __SYSCALL(__NR_getrandom, sys_getrandom)
 __SYSCALL(__NR_memfd_create, sys_memfd_create)
 #define __NR_bpf 386
 __SYSCALL(__NR_bpf, sys_bpf)
+#define __NR_execveat 387
+__SYSCALL(__NR_execveat, compat_sys_execveat)
index fbe909fb0a1a8b95ab4f6e3ade19daaa21c70436..c3ca89c27c6b351839ec62f763ca99d34ac5b3c2 100644 (file)
@@ -1014,6 +1014,7 @@ ENTRY(__kvm_tlb_flush_vmid_ipa)
         * Instead, we invalidate Stage-2 for this IPA, and the
         * whole of Stage-1. Weep...
         */
+       lsr     x1, x1, #12
        tlbi    ipas2e1is, x1
        /*
         * We have to ensure completion of the invalidation at Stage-2,
index 70a7816535cd4a9bf575b9767a9a9fd62dbe21e6..0b43265789858cbe71f761eebbc48927834b7fe8 100644 (file)
@@ -90,7 +90,6 @@ int kvm_reset_vcpu(struct kvm_vcpu *vcpu)
                        if (!cpu_has_32bit_el1())
                                return -EINVAL;
                        cpu_reset = &default_regs_reset32;
-                       vcpu->arch.hcr_el2 &= ~HCR_RW;
                } else {
                        cpu_reset = &default_regs_reset;
                }
index bac492c12fcc4bd054e09f8db8022b64dcaa8f74..c95464a33f36175d1f7905ad61bd5176654efd0f 100644 (file)
@@ -335,14 +335,8 @@ static int keep_initrd;
 
 void free_initrd_mem(unsigned long start, unsigned long end)
 {
-       if (!keep_initrd) {
-               if (start == initrd_start)
-                       start = round_down(start, PAGE_SIZE);
-               if (end == initrd_end)
-                       end = round_up(end, PAGE_SIZE);
-
+       if (!keep_initrd)
                free_reserved_area((void *)start, (void *)end, 0, "initrd");
-       }
 }
 
 static int __init keepinitrd_setup(char *__unused)
index 75e75d7b1702fb6434c59e9155dbba1d71623b17..244e0dbe45dbeda359e233cde23b4652f0ce13dc 100644 (file)
@@ -4,7 +4,7 @@
 #include <uapi/asm/unistd.h>
 
 
-#define NR_syscalls            355
+#define NR_syscalls            356
 
 #define __ARCH_WANT_OLD_READDIR
 #define __ARCH_WANT_OLD_STAT
index 2c1bec9a14b67da42a8ed09b644373d0cf35b5ef..61fb6cb9d2ae3c66a1c0c6dec1ac95adb83dd810 100644 (file)
 #define __NR_getrandom         352
 #define __NR_memfd_create      353
 #define __NR_bpf               354
+#define __NR_execveat          355
 
 #endif /* _UAPI_ASM_M68K_UNISTD_H_ */
index 2ca219e184cd16e6ebad1bd9123061695691c843..a0ec4303f2c8e57a04fb353178d43b0be6a461fe 100644 (file)
@@ -375,4 +375,5 @@ ENTRY(sys_call_table)
        .long sys_getrandom
        .long sys_memfd_create
        .long sys_bpf
+       .long sys_execveat              /* 355 */
 
index d3feba5a275f6465fa46b850ed57cb688bd834ea..c154cebc1041c4ac24d72c5e51b93bfec2f0d9ee 100644 (file)
@@ -154,4 +154,5 @@ module_exit(sha1_powerpc_mod_fini);
 MODULE_LICENSE("GPL");
 MODULE_DESCRIPTION("SHA1 Secure Hash Algorithm");
 
+MODULE_ALIAS_CRYPTO("sha1");
 MODULE_ALIAS_CRYPTO("sha1-powerpc");
index ebc4f165690a9fc0113864b6857708b5df8c317a..0be6c681cab1341061c02031464d5355ff8a4d7d 100644 (file)
@@ -23,9 +23,9 @@
 #define THREAD_SIZE            (1 << THREAD_SHIFT)
 
 #ifdef CONFIG_PPC64
-#define CURRENT_THREAD_INFO(dest, sp)  clrrdi dest, sp, THREAD_SHIFT
+#define CURRENT_THREAD_INFO(dest, sp)  stringify_in_c(clrrdi dest, sp, THREAD_SHIFT)
 #else
-#define CURRENT_THREAD_INFO(dest, sp)  rlwinm dest, sp, 0, 0, 31-THREAD_SHIFT
+#define CURRENT_THREAD_INFO(dest, sp)  stringify_in_c(rlwinm dest, sp, 0, 0, 31-THREAD_SHIFT)
 #endif
 
 #ifndef __ASSEMBLY__
@@ -71,12 +71,13 @@ struct thread_info {
 #define THREAD_SIZE_ORDER      (THREAD_SHIFT - PAGE_SHIFT)
 
 /* how to get the thread information struct from C */
-register unsigned long __current_r1 asm("r1");
 static inline struct thread_info *current_thread_info(void)
 {
-       /* gcc4, at least, is smart enough to turn this into a single
-        * rlwinm for ppc32 and clrrdi for ppc64 */
-       return (struct thread_info *)(__current_r1 & ~(THREAD_SIZE-1));
+       unsigned long val;
+
+       asm (CURRENT_THREAD_INFO(%0,1) : "=r" (val));
+
+       return (struct thread_info *)val;
 }
 
 #endif /* __ASSEMBLY__ */
index 54eca8b3b288f8fcca45ef5f44c5211832b3416f..0509bca5e830b656c8a553c047740b68b172f4b1 100644 (file)
@@ -40,7 +40,6 @@ BEGIN_FTR_SECTION;                                            \
        b       1f;                                             \
 END_FTR_SECTION(0, 1);                                         \
        ld      r12,opal_tracepoint_refcount@toc(r2);           \
-       std     r12,32(r1);                                     \
        cmpdi   r12,0;                                          \
        bne-    LABEL;                                          \
 1:
index 32040ace00ea2431a18428dca5c34c0c4ebde10c..afbe07907c10b6304e52b5eb234d33694fd9693a 100644 (file)
@@ -231,7 +231,7 @@ failed:
 struct dbfs_d2fc_hdr {
        u64     len;            /* Length of d2fc buffer without header */
        u16     version;        /* Version of header */
-       char    tod_ext[16];    /* TOD clock for d2fc */
+       char    tod_ext[STORE_CLOCK_EXT_SIZE]; /* TOD clock for d2fc */
        u64     count;          /* Number of VM guests in d2fc buffer */
        char    reserved[30];
 } __attribute__ ((packed));
index 37b9091ab8c010c88a22bb2851f0133b10c6f032..16aa0c779e0762e210fe6652a0a5efda24771381 100644 (file)
@@ -36,7 +36,7 @@ static inline notrace void __arch_local_irq_ssm(unsigned long flags)
 
 static inline notrace unsigned long arch_local_save_flags(void)
 {
-       return __arch_local_irq_stosm(0x00);
+       return __arch_local_irq_stnsm(0xff);
 }
 
 static inline notrace unsigned long arch_local_irq_save(void)
index 8beee1cceba4ed17831736a11c6f5167155335d6..98eb2a5792234d9d12c303bdb1301f869f706b60 100644 (file)
@@ -67,20 +67,22 @@ static inline void local_tick_enable(unsigned long long comp)
        set_clock_comparator(S390_lowcore.clock_comparator);
 }
 
-#define CLOCK_TICK_RATE        1193180 /* Underlying HZ */
+#define CLOCK_TICK_RATE                1193180 /* Underlying HZ */
+#define STORE_CLOCK_EXT_SIZE   16      /* stcke writes 16 bytes */
 
 typedef unsigned long long cycles_t;
 
-static inline void get_tod_clock_ext(char clk[16])
+static inline void get_tod_clock_ext(char *clk)
 {
-       typedef struct { char _[sizeof(clk)]; } addrtype;
+       typedef struct { char _[STORE_CLOCK_EXT_SIZE]; } addrtype;
 
        asm volatile("stcke %0" : "=Q" (*(addrtype *) clk) : : "cc");
 }
 
 static inline unsigned long long get_tod_clock(void)
 {
-       unsigned char clk[16];
+       unsigned char clk[STORE_CLOCK_EXT_SIZE];
+
        get_tod_clock_ext(clk);
        return *((unsigned long long *)&clk[1]);
 }
index 2b446cf0cc65543d38defaf1985d4246f767449b..67878af257a083c531140f74b951019e2a1537e0 100644 (file)
 #define __NR_bpf               351
 #define __NR_s390_pci_mmio_write       352
 #define __NR_s390_pci_mmio_read                353
-#define NR_syscalls 354
+#define __NR_execveat          354
+#define NR_syscalls 355
 
 /* 
  * There are some system calls that are not present on 64 bit, some
index a2987243bc76c89bd07a6d4a298825bea9664ab8..939ec474b1dd705e7814f94c94df4faeb8009aa2 100644 (file)
@@ -362,3 +362,4 @@ SYSCALL(sys_memfd_create,sys_memfd_create,compat_sys_memfd_create) /* 350 */
 SYSCALL(sys_bpf,sys_bpf,compat_sys_bpf)
 SYSCALL(sys_ni_syscall,sys_s390_pci_mmio_write,compat_sys_s390_pci_mmio_write)
 SYSCALL(sys_ni_syscall,sys_s390_pci_mmio_read,compat_sys_s390_pci_mmio_read)
+SYSCALL(sys_execveat,sys_execveat,compat_sys_execveat)
index f6b3cd056ec22c1c28b908c4cefc46bc4a4e2099..cc7328080b609a653b72c1ca2c6989f054e3be74 100644 (file)
@@ -48,6 +48,30 @@ bool arch_uprobe_xol_was_trapped(struct task_struct *tsk)
        return false;
 }
 
+static int check_per_event(unsigned short cause, unsigned long control,
+                          struct pt_regs *regs)
+{
+       if (!(regs->psw.mask & PSW_MASK_PER))
+               return 0;
+       /* user space single step */
+       if (control == 0)
+               return 1;
+       /* over indication for storage alteration */
+       if ((control & 0x20200000) && (cause & 0x2000))
+               return 1;
+       if (cause & 0x8000) {
+               /* all branches */
+               if ((control & 0x80800000) == 0x80000000)
+                       return 1;
+               /* branch into selected range */
+               if (((control & 0x80800000) == 0x80800000) &&
+                   regs->psw.addr >= current->thread.per_user.start &&
+                   regs->psw.addr <= current->thread.per_user.end)
+                       return 1;
+       }
+       return 0;
+}
+
 int arch_uprobe_post_xol(struct arch_uprobe *auprobe, struct pt_regs *regs)
 {
        int fixup = probe_get_fixup_type(auprobe->insn);
@@ -71,9 +95,13 @@ int arch_uprobe_post_xol(struct arch_uprobe *auprobe, struct pt_regs *regs)
                if (regs->psw.addr - utask->xol_vaddr == ilen)
                        regs->psw.addr = utask->vaddr + ilen;
        }
-       /* If per tracing was active generate trap */
-       if (regs->psw.mask & PSW_MASK_PER)
-               do_per_trap(regs);
+       if (check_per_event(current->thread.per_event.cause,
+                           current->thread.per_user.control, regs)) {
+               /* fix per address */
+               current->thread.per_event.address = utask->vaddr;
+               /* trigger per event */
+               set_pt_regs_flag(regs, PIF_PER_TRAP);
+       }
        return 0;
 }
 
@@ -106,6 +134,7 @@ void arch_uprobe_abort_xol(struct arch_uprobe *auprobe, struct pt_regs *regs)
        clear_thread_flag(TIF_UPROBE_SINGLESTEP);
        regs->int_code = auprobe->saved_int_code;
        regs->psw.addr = current->utask->vaddr;
+       current->thread.per_event.address = current->utask->vaddr;
 }
 
 unsigned long arch_uretprobe_hijack_return_addr(unsigned long trampoline,
@@ -146,17 +175,20 @@ static void adjust_psw_addr(psw_t *psw, unsigned long len)
        __rc;                                           \
 })
 
-#define emu_store_ril(ptr, input)                      \
+#define emu_store_ril(regs, ptr, input)                        \
 ({                                                     \
        unsigned int mask = sizeof(*(ptr)) - 1;         \
+       __typeof__(ptr) __ptr = (ptr);                  \
        int __rc = 0;                                   \
                                                        \
        if (!test_facility(34))                         \
                __rc = EMU_ILLEGAL_OP;                  \
-       else if ((u64 __force)ptr & mask)               \
+       else if ((u64 __force)__ptr & mask)             \
                __rc = EMU_SPECIFICATION;               \
-       else if (put_user(*(input), ptr))               \
+       else if (put_user(*(input), __ptr))             \
                __rc = EMU_ADDRESSING;                  \
+       if (__rc == 0)                                  \
+               sim_stor_event(regs, __ptr, mask + 1);  \
        __rc;                                           \
 })
 
@@ -197,6 +229,25 @@ union split_register {
        s16 s16[4];
 };
 
+/*
+ * If user per registers are setup to trace storage alterations and an
+ * emulated store took place on a fitting address a user trap is generated.
+ */
+static void sim_stor_event(struct pt_regs *regs, void *addr, int len)
+{
+       if (!(regs->psw.mask & PSW_MASK_PER))
+               return;
+       if (!(current->thread.per_user.control & PER_EVENT_STORE))
+               return;
+       if ((void *)current->thread.per_user.start > (addr + len))
+               return;
+       if ((void *)current->thread.per_user.end < addr)
+               return;
+       current->thread.per_event.address = regs->psw.addr;
+       current->thread.per_event.cause = PER_EVENT_STORE >> 16;
+       set_pt_regs_flag(regs, PIF_PER_TRAP);
+}
+
 /*
  * pc relative instructions are emulated, since parameters may not be
  * accessible from the xol area due to range limitations.
@@ -249,13 +300,13 @@ static void handle_insn_ril(struct arch_uprobe *auprobe, struct pt_regs *regs)
                        rc = emu_load_ril((u32 __user *)uptr, &rx->u64);
                        break;
                case 0x07: /* sthrl */
-                       rc = emu_store_ril((u16 __user *)uptr, &rx->u16[3]);
+                       rc = emu_store_ril(regs, (u16 __user *)uptr, &rx->u16[3]);
                        break;
                case 0x0b: /* stgrl */
-                       rc = emu_store_ril((u64 __user *)uptr, &rx->u64);
+                       rc = emu_store_ril(regs, (u64 __user *)uptr, &rx->u64);
                        break;
                case 0x0f: /* strl */
-                       rc = emu_store_ril((u32 __user *)uptr, &rx->u32[1]);
+                       rc = emu_store_ril(regs, (u32 __user *)uptr, &rx->u32[1]);
                        break;
                }
                break;
index 7f0089d9a4aa47ef86e7691502281c140ee637c3..e34122e539a16bad4e5727f881f982e4829cd8f0 100644 (file)
@@ -128,8 +128,6 @@ void vtime_account_irq_enter(struct task_struct *tsk)
        struct thread_info *ti = task_thread_info(tsk);
        u64 timer, system;
 
-       WARN_ON_ONCE(!irqs_disabled());
-
        timer = S390_lowcore.last_update_timer;
        S390_lowcore.last_update_timer = get_vtimer();
        S390_lowcore.system_timer += timer - S390_lowcore.last_update_timer;
index be99357d238c68e34dee133c52053e23c88a34d4..3cf8cc03fff60d7a59e7b23f4e92d477061a5f42 100644 (file)
@@ -322,11 +322,12 @@ static int gmap_alloc_table(struct gmap *gmap, unsigned long *table,
 static unsigned long __gmap_segment_gaddr(unsigned long *entry)
 {
        struct page *page;
-       unsigned long offset;
+       unsigned long offset, mask;
 
        offset = (unsigned long) entry / sizeof(unsigned long);
        offset = (offset & (PTRS_PER_PMD - 1)) * PMD_SIZE;
-       page = pmd_to_page((pmd_t *) entry);
+       mask = ~(PTRS_PER_PMD * sizeof(pmd_t) - 1);
+       page = virt_to_page((void *)((unsigned long) entry & mask));
        return page->index + offset;
 }
 
index c52ac77408ca5cac7ad50b6a2a8a3113d8af30ca..524496d47ef506d0ca888356df21fd4bb7e25053 100644 (file)
@@ -431,8 +431,8 @@ static int bpf_jit_insn(struct bpf_jit *jit, struct sock_filter *filter,
                EMIT4_DISP(0x88500000, K);
                break;
        case BPF_ALU | BPF_NEG: /* A = -A */
-               /* lnr %r5,%r5 */
-               EMIT2(0x1155);
+               /* lcr %r5,%r5 */
+               EMIT2(0x1355);
                break;
        case BPF_JMP | BPF_JA: /* ip += K */
                offset = addrs[i + K] + jit->start - jit->prg;
@@ -502,8 +502,8 @@ branch:             if (filter->jt == filter->jf) {
 xbranch:       /* Emit compare if the branch targets are different */
                if (filter->jt != filter->jf) {
                        jit->seen |= SEEN_XREG;
-                       /* cr %r5,%r12 */
-                       EMIT2(0x195c);
+                       /* clr %r5,%r12 */
+                       EMIT2(0x155c);
                }
                goto branch;
        case BPF_JMP | BPF_JSET | BPF_X: /* ip += (A & X) ? jt : jf */
index a225a5ca1037ede0a9fa8ebb109a43c22523ffaa..fd9f6b035b163001620d40811b728cc5e213c712 100644 (file)
@@ -931,4 +931,4 @@ module_exit(sha1_mb_mod_fini);
 MODULE_LICENSE("GPL");
 MODULE_DESCRIPTION("SHA1 Secure Hash Algorithm, multi buffer accelerated");
 
-MODULE_ALIAS("sha1");
+MODULE_ALIAS_CRYPTO("sha1");
index 3c895d480cd75b056ab24e686e765b70db1729f5..07398339836426eae32b55fb08fa108593cd7389 100644 (file)
@@ -568,8 +568,8 @@ struct event_constraint intel_atom_pebs_event_constraints[] = {
 };
 
 struct event_constraint intel_slm_pebs_event_constraints[] = {
-       /* UOPS_RETIRED.ALL, inv=1, cmask=16 (cycles:p). */
-       INTEL_FLAGS_EVENT_CONSTRAINT(0x108001c2, 0xf),
+       /* INST_RETIRED.ANY_P, inv=1, cmask=16 (cycles:p). */
+       INTEL_FLAGS_EVENT_CONSTRAINT(0x108000c0, 0x1),
        /* Allow all events as PEBS with no flags */
        INTEL_ALL_EVENT_CONSTRAINT(0, 0x1),
        EVENT_CONSTRAINT_END
index 673f930c700f3ae745d8a408111f072dcce00dd1..6e434f8e5fc8a34ea8f098280c9c0da3227b834e 100644 (file)
@@ -103,6 +103,13 @@ static struct kobj_attribute format_attr_##_var =          \
 
 #define RAPL_CNTR_WIDTH 32 /* 32-bit rapl counters */
 
+#define RAPL_EVENT_ATTR_STR(_name, v, str)                             \
+static struct perf_pmu_events_attr event_attr_##v = {                  \
+       .attr           = __ATTR(_name, 0444, rapl_sysfs_show, NULL),   \
+       .id             = 0,                                            \
+       .event_str      = str,                                          \
+};
+
 struct rapl_pmu {
        spinlock_t       lock;
        int              hw_unit;  /* 1/2^hw_unit Joule */
@@ -379,23 +386,36 @@ static struct attribute_group rapl_pmu_attr_group = {
        .attrs = rapl_pmu_attrs,
 };
 
-EVENT_ATTR_STR(energy-cores, rapl_cores, "event=0x01");
-EVENT_ATTR_STR(energy-pkg  ,   rapl_pkg, "event=0x02");
-EVENT_ATTR_STR(energy-ram  ,   rapl_ram, "event=0x03");
-EVENT_ATTR_STR(energy-gpu  ,   rapl_gpu, "event=0x04");
+static ssize_t rapl_sysfs_show(struct device *dev,
+                              struct device_attribute *attr,
+                              char *page)
+{
+       struct perf_pmu_events_attr *pmu_attr = \
+               container_of(attr, struct perf_pmu_events_attr, attr);
+
+       if (pmu_attr->event_str)
+               return sprintf(page, "%s", pmu_attr->event_str);
+
+       return 0;
+}
+
+RAPL_EVENT_ATTR_STR(energy-cores, rapl_cores, "event=0x01");
+RAPL_EVENT_ATTR_STR(energy-pkg  ,   rapl_pkg, "event=0x02");
+RAPL_EVENT_ATTR_STR(energy-ram  ,   rapl_ram, "event=0x03");
+RAPL_EVENT_ATTR_STR(energy-gpu  ,   rapl_gpu, "event=0x04");
 
-EVENT_ATTR_STR(energy-cores.unit, rapl_cores_unit, "Joules");
-EVENT_ATTR_STR(energy-pkg.unit  ,   rapl_pkg_unit, "Joules");
-EVENT_ATTR_STR(energy-ram.unit  ,   rapl_ram_unit, "Joules");
-EVENT_ATTR_STR(energy-gpu.unit  ,   rapl_gpu_unit, "Joules");
+RAPL_EVENT_ATTR_STR(energy-cores.unit, rapl_cores_unit, "Joules");
+RAPL_EVENT_ATTR_STR(energy-pkg.unit  ,   rapl_pkg_unit, "Joules");
+RAPL_EVENT_ATTR_STR(energy-ram.unit  ,   rapl_ram_unit, "Joules");
+RAPL_EVENT_ATTR_STR(energy-gpu.unit  ,   rapl_gpu_unit, "Joules");
 
 /*
  * we compute in 0.23 nJ increments regardless of MSR
  */
-EVENT_ATTR_STR(energy-cores.scale, rapl_cores_scale, "2.3283064365386962890625e-10");
-EVENT_ATTR_STR(energy-pkg.scale,     rapl_pkg_scale, "2.3283064365386962890625e-10");
-EVENT_ATTR_STR(energy-ram.scale,     rapl_ram_scale, "2.3283064365386962890625e-10");
-EVENT_ATTR_STR(energy-gpu.scale,     rapl_gpu_scale, "2.3283064365386962890625e-10");
+RAPL_EVENT_ATTR_STR(energy-cores.scale, rapl_cores_scale, "2.3283064365386962890625e-10");
+RAPL_EVENT_ATTR_STR(energy-pkg.scale,     rapl_pkg_scale, "2.3283064365386962890625e-10");
+RAPL_EVENT_ATTR_STR(energy-ram.scale,     rapl_ram_scale, "2.3283064365386962890625e-10");
+RAPL_EVENT_ATTR_STR(energy-gpu.scale,     rapl_gpu_scale, "2.3283064365386962890625e-10");
 
 static struct attribute *rapl_events_srv_attr[] = {
        EVENT_PTR(rapl_cores),
index f7e3cd50ece02a7b0408683d113bbafca8d49479..98f654d466e585167153e58811902675bfeb5baa 100644 (file)
@@ -1020,6 +1020,15 @@ int setjmp_pre_handler(struct kprobe *p, struct pt_regs *regs)
        regs->flags &= ~X86_EFLAGS_IF;
        trace_hardirqs_off();
        regs->ip = (unsigned long)(jp->entry);
+
+       /*
+        * jprobes use jprobe_return() which skips the normal return
+        * path of the function, and this messes up the accounting of the
+        * function graph tracer to get messed up.
+        *
+        * Pause function graph tracing while performing the jprobe function.
+        */
+       pause_graph_tracing();
        return 1;
 }
 NOKPROBE_SYMBOL(setjmp_pre_handler);
@@ -1048,24 +1057,25 @@ int longjmp_break_handler(struct kprobe *p, struct pt_regs *regs)
        struct kprobe_ctlblk *kcb = get_kprobe_ctlblk();
        u8 *addr = (u8 *) (regs->ip - 1);
        struct jprobe *jp = container_of(p, struct jprobe, kp);
+       void *saved_sp = kcb->jprobe_saved_sp;
 
        if ((addr > (u8 *) jprobe_return) &&
            (addr < (u8 *) jprobe_return_end)) {
-               if (stack_addr(regs) != kcb->jprobe_saved_sp) {
+               if (stack_addr(regs) != saved_sp) {
                        struct pt_regs *saved_regs = &kcb->jprobe_saved_regs;
                        printk(KERN_ERR
                               "current sp %p does not match saved sp %p\n",
-                              stack_addr(regs), kcb->jprobe_saved_sp);
+                              stack_addr(regs), saved_sp);
                        printk(KERN_ERR "Saved registers for jprobe %p\n", jp);
                        show_regs(saved_regs);
                        printk(KERN_ERR "Current registers\n");
                        show_regs(regs);
                        BUG();
                }
+               /* It's OK to start function graph tracing again */
+               unpause_graph_tracing();
                *regs = kcb->jprobe_saved_regs;
-               memcpy((kprobe_opcode_t *)(kcb->jprobe_saved_sp),
-                      kcb->jprobes_stack,
-                      MIN_STACK_SIZE(kcb->jprobe_saved_sp));
+               memcpy(saved_sp, kcb->jprobes_stack, MIN_STACK_SIZE(saved_sp));
                preempt_enable_no_resched();
                return 1;
        }
index 6bf3a13e3e0f7af10c8d984f829a512661d12c2e..78a881b7fc415e16f50f16e4381e968370f4fd9f 100644 (file)
@@ -40,6 +40,7 @@
 #include <xen/interface/physdev.h>
 #include <xen/interface/vcpu.h>
 #include <xen/interface/memory.h>
+#include <xen/interface/nmi.h>
 #include <xen/interface/xen-mca.h>
 #include <xen/features.h>
 #include <xen/page.h>
@@ -66,6 +67,7 @@
 #include <asm/reboot.h>
 #include <asm/stackprotector.h>
 #include <asm/hypervisor.h>
+#include <asm/mach_traps.h>
 #include <asm/mwait.h>
 #include <asm/pci_x86.h>
 #include <asm/pat.h>
@@ -1351,6 +1353,21 @@ static const struct machine_ops xen_machine_ops __initconst = {
        .emergency_restart = xen_emergency_restart,
 };
 
+static unsigned char xen_get_nmi_reason(void)
+{
+       unsigned char reason = 0;
+
+       /* Construct a value which looks like it came from port 0x61. */
+       if (test_bit(_XEN_NMIREASON_io_error,
+                    &HYPERVISOR_shared_info->arch.nmi_reason))
+               reason |= NMI_REASON_IOCHK;
+       if (test_bit(_XEN_NMIREASON_pci_serr,
+                    &HYPERVISOR_shared_info->arch.nmi_reason))
+               reason |= NMI_REASON_SERR;
+
+       return reason;
+}
+
 static void __init xen_boot_params_init_edd(void)
 {
 #if IS_ENABLED(CONFIG_EDD)
@@ -1535,9 +1552,12 @@ asmlinkage __visible void __init xen_start_kernel(void)
        pv_info = xen_info;
        pv_init_ops = xen_init_ops;
        pv_apic_ops = xen_apic_ops;
-       if (!xen_pvh_domain())
+       if (!xen_pvh_domain()) {
                pv_cpu_ops = xen_cpu_ops;
 
+               x86_platform.get_nmi_reason = xen_get_nmi_reason;
+       }
+
        if (xen_feature(XENFEAT_auto_translated_physmap))
                x86_init.resources.memory_setup = xen_auto_xlated_memory_setup;
        else
index edbc7a63fd737f0ca13edac752e1f06341f9dd97..70fb5075c901f5b0c370478b156288764f609ad8 100644 (file)
@@ -167,10 +167,13 @@ static void * __ref alloc_p2m_page(void)
        return (void *)__get_free_page(GFP_KERNEL | __GFP_REPEAT);
 }
 
-/* Only to be called in case of a race for a page just allocated! */
-static void free_p2m_page(void *p)
+static void __ref free_p2m_page(void *p)
 {
-       BUG_ON(!slab_is_available());
+       if (unlikely(!slab_is_available())) {
+               free_bootmem((unsigned long)p, PAGE_SIZE);
+               return;
+       }
+
        free_page((unsigned long)p);
 }
 
@@ -375,7 +378,7 @@ static void __init xen_rebuild_p2m_list(unsigned long *p2m)
                        p2m_missing_pte : p2m_identity_pte;
                for (i = 0; i < PMDS_PER_MID_PAGE; i++) {
                        pmdp = populate_extra_pmd(
-                               (unsigned long)(p2m + pfn + i * PTRS_PER_PTE));
+                               (unsigned long)(p2m + pfn) + i * PMD_SIZE);
                        set_pmd(pmdp, __pmd(__pa(ptep) | _KERNPG_TABLE));
                }
        }
@@ -436,10 +439,9 @@ EXPORT_SYMBOL_GPL(get_phys_to_machine);
  * a new pmd is to replace p2m_missing_pte or p2m_identity_pte by a individual
  * pmd. In case of PAE/x86-32 there are multiple pmds to allocate!
  */
-static pte_t *alloc_p2m_pmd(unsigned long addr, pte_t *ptep, pte_t *pte_pg)
+static pte_t *alloc_p2m_pmd(unsigned long addr, pte_t *pte_pg)
 {
        pte_t *ptechk;
-       pte_t *pteret = ptep;
        pte_t *pte_newpg[PMDS_PER_MID_PAGE];
        pmd_t *pmdp;
        unsigned int level;
@@ -473,8 +475,6 @@ static pte_t *alloc_p2m_pmd(unsigned long addr, pte_t *ptep, pte_t *pte_pg)
                if (ptechk == pte_pg) {
                        set_pmd(pmdp,
                                __pmd(__pa(pte_newpg[i]) | _KERNPG_TABLE));
-                       if (vaddr == (addr & ~(PMD_SIZE - 1)))
-                               pteret = pte_offset_kernel(pmdp, addr);
                        pte_newpg[i] = NULL;
                }
 
@@ -488,7 +488,7 @@ static pte_t *alloc_p2m_pmd(unsigned long addr, pte_t *ptep, pte_t *pte_pg)
                vaddr += PMD_SIZE;
        }
 
-       return pteret;
+       return lookup_address(addr, &level);
 }
 
 /*
@@ -517,7 +517,7 @@ static bool alloc_p2m(unsigned long pfn)
 
        if (pte_pg == p2m_missing_pte || pte_pg == p2m_identity_pte) {
                /* PMD level is missing, allocate a new one */
-               ptep = alloc_p2m_pmd(addr, ptep, pte_pg);
+               ptep = alloc_p2m_pmd(addr, pte_pg);
                if (!ptep)
                        return false;
        }
index dfd77dec8e2b7c1ef72d16adb1ecf7f7b80c88de..865e56cea7a0abe4d9b6feb2e1d0da27957d47e8 100644 (file)
@@ -140,7 +140,7 @@ static void __init xen_del_extra_mem(u64 start, u64 size)
 unsigned long __ref xen_chk_extra_mem(unsigned long pfn)
 {
        int i;
-       unsigned long addr = PFN_PHYS(pfn);
+       phys_addr_t addr = PFN_PHYS(pfn);
 
        for (i = 0; i < XEN_EXTRA_MEM_MAX_REGIONS; i++) {
                if (addr >= xen_extra_mem[i].start &&
@@ -160,6 +160,8 @@ void __init xen_inv_extra_mem(void)
        int i;
 
        for (i = 0; i < XEN_EXTRA_MEM_MAX_REGIONS; i++) {
+               if (!xen_extra_mem[i].size)
+                       continue;
                pfn_s = PFN_DOWN(xen_extra_mem[i].start);
                pfn_e = PFN_UP(xen_extra_mem[i].start + xen_extra_mem[i].size);
                for (pfn = pfn_s; pfn < pfn_e; pfn++)
@@ -229,15 +231,14 @@ static int __init xen_free_mfn(unsigned long mfn)
  * as a fallback if the remapping fails.
  */
 static void __init xen_set_identity_and_release_chunk(unsigned long start_pfn,
-       unsigned long end_pfn, unsigned long nr_pages, unsigned long *identity,
-       unsigned long *released)
+       unsigned long end_pfn, unsigned long nr_pages, unsigned long *released)
 {
-       unsigned long len = 0;
        unsigned long pfn, end;
        int ret;
 
        WARN_ON(start_pfn > end_pfn);
 
+       /* Release pages first. */
        end = min(end_pfn, nr_pages);
        for (pfn = start_pfn; pfn < end; pfn++) {
                unsigned long mfn = pfn_to_mfn(pfn);
@@ -250,16 +251,14 @@ static void __init xen_set_identity_and_release_chunk(unsigned long start_pfn,
                WARN(ret != 1, "Failed to release pfn %lx err=%d\n", pfn, ret);
 
                if (ret == 1) {
+                       (*released)++;
                        if (!__set_phys_to_machine(pfn, INVALID_P2M_ENTRY))
                                break;
-                       len++;
                } else
                        break;
        }
 
-       /* Need to release pages first */
-       *released += len;
-       *identity += set_phys_range_identity(start_pfn, end_pfn);
+       set_phys_range_identity(start_pfn, end_pfn);
 }
 
 /*
@@ -287,7 +286,7 @@ static void __init xen_update_mem_tables(unsigned long pfn, unsigned long mfn)
        }
 
        /* Update kernel mapping, but not for highmem. */
-       if ((pfn << PAGE_SHIFT) >= __pa(high_memory))
+       if (pfn >= PFN_UP(__pa(high_memory - 1)))
                return;
 
        if (HYPERVISOR_update_va_mapping((unsigned long)__va(pfn << PAGE_SHIFT),
@@ -318,7 +317,6 @@ static void __init xen_do_set_identity_and_remap_chunk(
        unsigned long ident_pfn_iter, remap_pfn_iter;
        unsigned long ident_end_pfn = start_pfn + size;
        unsigned long left = size;
-       unsigned long ident_cnt = 0;
        unsigned int i, chunk;
 
        WARN_ON(size == 0);
@@ -347,8 +345,7 @@ static void __init xen_do_set_identity_and_remap_chunk(
                xen_remap_mfn = mfn;
 
                /* Set identity map */
-               ident_cnt += set_phys_range_identity(ident_pfn_iter,
-                       ident_pfn_iter + chunk);
+               set_phys_range_identity(ident_pfn_iter, ident_pfn_iter + chunk);
 
                left -= chunk;
        }
@@ -371,7 +368,7 @@ static void __init xen_do_set_identity_and_remap_chunk(
 static unsigned long __init xen_set_identity_and_remap_chunk(
         const struct e820entry *list, size_t map_size, unsigned long start_pfn,
        unsigned long end_pfn, unsigned long nr_pages, unsigned long remap_pfn,
-       unsigned long *identity, unsigned long *released)
+       unsigned long *released, unsigned long *remapped)
 {
        unsigned long pfn;
        unsigned long i = 0;
@@ -386,8 +383,7 @@ static unsigned long __init xen_set_identity_and_remap_chunk(
                /* Do not remap pages beyond the current allocation */
                if (cur_pfn >= nr_pages) {
                        /* Identity map remaining pages */
-                       *identity += set_phys_range_identity(cur_pfn,
-                               cur_pfn + size);
+                       set_phys_range_identity(cur_pfn, cur_pfn + size);
                        break;
                }
                if (cur_pfn + size > nr_pages)
@@ -398,7 +394,7 @@ static unsigned long __init xen_set_identity_and_remap_chunk(
                if (!remap_range_size) {
                        pr_warning("Unable to find available pfn range, not remapping identity pages\n");
                        xen_set_identity_and_release_chunk(cur_pfn,
-                               cur_pfn + left, nr_pages, identity, released);
+                               cur_pfn + left, nr_pages, released);
                        break;
                }
                /* Adjust size to fit in current e820 RAM region */
@@ -410,7 +406,7 @@ static unsigned long __init xen_set_identity_and_remap_chunk(
                /* Update variables to reflect new mappings. */
                i += size;
                remap_pfn += size;
-               *identity += size;
+               *remapped += size;
        }
 
        /*
@@ -427,13 +423,13 @@ static unsigned long __init xen_set_identity_and_remap_chunk(
 
 static void __init xen_set_identity_and_remap(
        const struct e820entry *list, size_t map_size, unsigned long nr_pages,
-       unsigned long *released)
+       unsigned long *released, unsigned long *remapped)
 {
        phys_addr_t start = 0;
-       unsigned long identity = 0;
        unsigned long last_pfn = nr_pages;
        const struct e820entry *entry;
        unsigned long num_released = 0;
+       unsigned long num_remapped = 0;
        int i;
 
        /*
@@ -460,14 +456,14 @@ static void __init xen_set_identity_and_remap(
                                last_pfn = xen_set_identity_and_remap_chunk(
                                                list, map_size, start_pfn,
                                                end_pfn, nr_pages, last_pfn,
-                                               &identity, &num_released);
+                                               &num_released, &num_remapped);
                        start = end;
                }
        }
 
        *released = num_released;
+       *remapped = num_remapped;
 
-       pr_info("Set %ld page(s) to 1-1 mapping\n", identity);
        pr_info("Released %ld page(s)\n", num_released);
 }
 
@@ -586,6 +582,7 @@ char * __init xen_memory_setup(void)
        struct xen_memory_map memmap;
        unsigned long max_pages;
        unsigned long extra_pages = 0;
+       unsigned long remapped_pages;
        int i;
        int op;
 
@@ -635,9 +632,10 @@ char * __init xen_memory_setup(void)
         * underlying RAM.
         */
        xen_set_identity_and_remap(map, memmap.nr_entries, max_pfn,
-                                  &xen_released_pages);
+                                  &xen_released_pages, &remapped_pages);
 
        extra_pages += xen_released_pages;
+       extra_pages += remapped_pages;
 
        /*
         * Clamp the amount of extra memory to a EXTRA_MEM_RATIO
index f473d268d387fcdc8f237153b378508ec0c03f56..69087341d9aed7860dfd95549c0a8af5ffbf1ed6 100644 (file)
@@ -391,7 +391,7 @@ static const struct clock_event_device *xen_clockevent =
 
 struct xen_clock_event_device {
        struct clock_event_device evt;
-       char *name;
+       char name[16];
 };
 static DEFINE_PER_CPU(struct xen_clock_event_device, xen_clock_events) = { .evt.irq = -1 };
 
@@ -420,46 +420,38 @@ void xen_teardown_timer(int cpu)
        if (evt->irq >= 0) {
                unbind_from_irqhandler(evt->irq, NULL);
                evt->irq = -1;
-               kfree(per_cpu(xen_clock_events, cpu).name);
-               per_cpu(xen_clock_events, cpu).name = NULL;
        }
 }
 
 void xen_setup_timer(int cpu)
 {
-       char *name;
-       struct clock_event_device *evt;
+       struct xen_clock_event_device *xevt = &per_cpu(xen_clock_events, cpu);
+       struct clock_event_device *evt = &xevt->evt;
        int irq;
 
-       evt = &per_cpu(xen_clock_events, cpu).evt;
        WARN(evt->irq >= 0, "IRQ%d for CPU%d is already allocated\n", evt->irq, cpu);
        if (evt->irq >= 0)
                xen_teardown_timer(cpu);
 
        printk(KERN_INFO "installing Xen timer for CPU %d\n", cpu);
 
-       name = kasprintf(GFP_KERNEL, "timer%d", cpu);
-       if (!name)
-               name = "<timer kasprintf failed>";
+       snprintf(xevt->name, sizeof(xevt->name), "timer%d", cpu);
 
        irq = bind_virq_to_irqhandler(VIRQ_TIMER, cpu, xen_timer_interrupt,
                                      IRQF_PERCPU|IRQF_NOBALANCING|IRQF_TIMER|
                                      IRQF_FORCE_RESUME|IRQF_EARLY_RESUME,
-                                     name, NULL);
+                                     xevt->name, NULL);
        (void)xen_set_irq_priority(irq, XEN_IRQ_PRIORITY_MAX);
 
        memcpy(evt, xen_clockevent, sizeof(*evt));
 
        evt->cpumask = cpumask_of(cpu);
        evt->irq = irq;
-       per_cpu(xen_clock_events, cpu).name = name;
 }
 
 
 void xen_setup_cpu_clockevents(void)
 {
-       BUG_ON(preemptible());
-
        clockevents_register_device(this_cpu_ptr(&xen_clock_events.evt));
 }
 
index 30f6153a40c27c7154dd453301807c7d39d1451c..3ad405571dcc5105a52da4284477a187db936f64 100644 (file)
@@ -473,6 +473,25 @@ void blk_queue_bypass_end(struct request_queue *q)
 }
 EXPORT_SYMBOL_GPL(blk_queue_bypass_end);
 
+void blk_set_queue_dying(struct request_queue *q)
+{
+       queue_flag_set_unlocked(QUEUE_FLAG_DYING, q);
+
+       if (q->mq_ops)
+               blk_mq_wake_waiters(q);
+       else {
+               struct request_list *rl;
+
+               blk_queue_for_each_rl(rl, q) {
+                       if (rl->rq_pool) {
+                               wake_up(&rl->wait[BLK_RW_SYNC]);
+                               wake_up(&rl->wait[BLK_RW_ASYNC]);
+                       }
+               }
+       }
+}
+EXPORT_SYMBOL_GPL(blk_set_queue_dying);
+
 /**
  * blk_cleanup_queue - shutdown a request queue
  * @q: request queue to shutdown
@@ -486,7 +505,7 @@ void blk_cleanup_queue(struct request_queue *q)
 
        /* mark @q DYING, no new request or merges will be allowed afterwards */
        mutex_lock(&q->sysfs_lock);
-       queue_flag_set_unlocked(QUEUE_FLAG_DYING, q);
+       blk_set_queue_dying(q);
        spin_lock_irq(lock);
 
        /*
index 32e8dbb9ad1c49f0078e57fae100f0e6a7eb8a73..60c9d4a93fe470ced7471cd8653d8a00fc8922d7 100644 (file)
@@ -68,9 +68,9 @@ bool __blk_mq_tag_busy(struct blk_mq_hw_ctx *hctx)
 }
 
 /*
- * Wakeup all potentially sleeping on normal (non-reserved) tags
+ * Wakeup all potentially sleeping on tags
  */
-static void blk_mq_tag_wakeup_all(struct blk_mq_tags *tags)
+void blk_mq_tag_wakeup_all(struct blk_mq_tags *tags, bool include_reserve)
 {
        struct blk_mq_bitmap_tags *bt;
        int i, wake_index;
@@ -85,6 +85,12 @@ static void blk_mq_tag_wakeup_all(struct blk_mq_tags *tags)
 
                wake_index = bt_index_inc(wake_index);
        }
+
+       if (include_reserve) {
+               bt = &tags->breserved_tags;
+               if (waitqueue_active(&bt->bs[0].wait))
+                       wake_up(&bt->bs[0].wait);
+       }
 }
 
 /*
@@ -100,7 +106,7 @@ void __blk_mq_tag_idle(struct blk_mq_hw_ctx *hctx)
 
        atomic_dec(&tags->active_queues);
 
-       blk_mq_tag_wakeup_all(tags);
+       blk_mq_tag_wakeup_all(tags, false);
 }
 
 /*
@@ -584,7 +590,7 @@ int blk_mq_tag_update_depth(struct blk_mq_tags *tags, unsigned int tdepth)
         * static and should never need resizing.
         */
        bt_update_count(&tags->bitmap_tags, tdepth);
-       blk_mq_tag_wakeup_all(tags);
+       blk_mq_tag_wakeup_all(tags, false);
        return 0;
 }
 
index 6206ed17ef766714b655a715ffbc05fd34b0463a..a6fa0fc9d41a2e91c8bb4ce29bb2b1a0d952c8ed 100644 (file)
@@ -54,6 +54,7 @@ extern bool blk_mq_has_free_tags(struct blk_mq_tags *tags);
 extern ssize_t blk_mq_tag_sysfs_show(struct blk_mq_tags *tags, char *page);
 extern void blk_mq_tag_init_last_tag(struct blk_mq_tags *tags, unsigned int *last_tag);
 extern int blk_mq_tag_update_depth(struct blk_mq_tags *tags, unsigned int depth);
+extern void blk_mq_tag_wakeup_all(struct blk_mq_tags *tags, bool);
 
 enum {
        BLK_MQ_TAG_CACHE_MIN    = 1,
index da1ab5641227b670faac42a84fde7e223668a4d8..2f95747c287eac350b45cc272fcd3d6e9c43ee09 100644 (file)
@@ -107,7 +107,7 @@ static void blk_mq_usage_counter_release(struct percpu_ref *ref)
        wake_up_all(&q->mq_freeze_wq);
 }
 
-static void blk_mq_freeze_queue_start(struct request_queue *q)
+void blk_mq_freeze_queue_start(struct request_queue *q)
 {
        bool freeze;
 
@@ -120,6 +120,7 @@ static void blk_mq_freeze_queue_start(struct request_queue *q)
                blk_mq_run_queues(q, false);
        }
 }
+EXPORT_SYMBOL_GPL(blk_mq_freeze_queue_start);
 
 static void blk_mq_freeze_queue_wait(struct request_queue *q)
 {
@@ -136,7 +137,7 @@ void blk_mq_freeze_queue(struct request_queue *q)
        blk_mq_freeze_queue_wait(q);
 }
 
-static void blk_mq_unfreeze_queue(struct request_queue *q)
+void blk_mq_unfreeze_queue(struct request_queue *q)
 {
        bool wake;
 
@@ -149,6 +150,24 @@ static void blk_mq_unfreeze_queue(struct request_queue *q)
                wake_up_all(&q->mq_freeze_wq);
        }
 }
+EXPORT_SYMBOL_GPL(blk_mq_unfreeze_queue);
+
+void blk_mq_wake_waiters(struct request_queue *q)
+{
+       struct blk_mq_hw_ctx *hctx;
+       unsigned int i;
+
+       queue_for_each_hw_ctx(q, hctx, i)
+               if (blk_mq_hw_queue_mapped(hctx))
+                       blk_mq_tag_wakeup_all(hctx->tags, true);
+
+       /*
+        * If we are called because the queue has now been marked as
+        * dying, we need to ensure that processes currently waiting on
+        * the queue are notified as well.
+        */
+       wake_up_all(&q->mq_freeze_wq);
+}
 
 bool blk_mq_can_queue(struct blk_mq_hw_ctx *hctx)
 {
@@ -258,8 +277,10 @@ struct request *blk_mq_alloc_request(struct request_queue *q, int rw, gfp_t gfp,
                ctx = alloc_data.ctx;
        }
        blk_mq_put_ctx(ctx);
-       if (!rq)
+       if (!rq) {
+               blk_mq_queue_exit(q);
                return ERR_PTR(-EWOULDBLOCK);
+       }
        return rq;
 }
 EXPORT_SYMBOL(blk_mq_alloc_request);
@@ -383,6 +404,12 @@ void blk_mq_complete_request(struct request *rq)
 }
 EXPORT_SYMBOL(blk_mq_complete_request);
 
+int blk_mq_request_started(struct request *rq)
+{
+       return test_bit(REQ_ATOM_STARTED, &rq->atomic_flags);
+}
+EXPORT_SYMBOL_GPL(blk_mq_request_started);
+
 void blk_mq_start_request(struct request *rq)
 {
        struct request_queue *q = rq->q;
@@ -500,12 +527,38 @@ void blk_mq_add_to_requeue_list(struct request *rq, bool at_head)
 }
 EXPORT_SYMBOL(blk_mq_add_to_requeue_list);
 
+void blk_mq_cancel_requeue_work(struct request_queue *q)
+{
+       cancel_work_sync(&q->requeue_work);
+}
+EXPORT_SYMBOL_GPL(blk_mq_cancel_requeue_work);
+
 void blk_mq_kick_requeue_list(struct request_queue *q)
 {
        kblockd_schedule_work(&q->requeue_work);
 }
 EXPORT_SYMBOL(blk_mq_kick_requeue_list);
 
+void blk_mq_abort_requeue_list(struct request_queue *q)
+{
+       unsigned long flags;
+       LIST_HEAD(rq_list);
+
+       spin_lock_irqsave(&q->requeue_lock, flags);
+       list_splice_init(&q->requeue_list, &rq_list);
+       spin_unlock_irqrestore(&q->requeue_lock, flags);
+
+       while (!list_empty(&rq_list)) {
+               struct request *rq;
+
+               rq = list_first_entry(&rq_list, struct request, queuelist);
+               list_del_init(&rq->queuelist);
+               rq->errors = -EIO;
+               blk_mq_end_request(rq, rq->errors);
+       }
+}
+EXPORT_SYMBOL(blk_mq_abort_requeue_list);
+
 static inline bool is_flush_request(struct request *rq,
                struct blk_flush_queue *fq, unsigned int tag)
 {
@@ -566,13 +619,24 @@ void blk_mq_rq_timed_out(struct request *req, bool reserved)
                break;
        }
 }
-               
+
 static void blk_mq_check_expired(struct blk_mq_hw_ctx *hctx,
                struct request *rq, void *priv, bool reserved)
 {
        struct blk_mq_timeout_data *data = priv;
 
-       if (!test_bit(REQ_ATOM_STARTED, &rq->atomic_flags))
+       if (!test_bit(REQ_ATOM_STARTED, &rq->atomic_flags)) {
+               /*
+                * If a request wasn't started before the queue was
+                * marked dying, kill it here or it'll go unnoticed.
+                */
+               if (unlikely(blk_queue_dying(rq->q))) {
+                       rq->errors = -EIO;
+                       blk_mq_complete_request(rq);
+               }
+               return;
+       }
+       if (rq->cmd_flags & REQ_NO_TIMEOUT)
                return;
 
        if (time_after_eq(jiffies, rq->deadline)) {
@@ -1601,7 +1665,6 @@ static int blk_mq_init_hctx(struct request_queue *q,
        hctx->queue = q;
        hctx->queue_num = hctx_idx;
        hctx->flags = set->flags;
-       hctx->cmd_size = set->cmd_size;
 
        blk_mq_init_cpu_notifier(&hctx->cpu_notifier,
                                        blk_mq_hctx_notify, hctx);
index 206230e64f7915e642ce7306aec8b949deca43b1..4f4f943c22c3d1e907ef2c18224b8635f0057e82 100644 (file)
@@ -32,6 +32,7 @@ void blk_mq_free_queue(struct request_queue *q);
 void blk_mq_clone_flush_request(struct request *flush_rq,
                struct request *orig_rq);
 int blk_mq_update_nr_requests(struct request_queue *q, unsigned int nr);
+void blk_mq_wake_waiters(struct request_queue *q);
 
 /*
  * CPU hotplug helpers
index 56c025894cdf2d73f78c5346c9c5987d5deb0e37..246dfb16c3d988c4f84749065a66977b825c98b5 100644 (file)
@@ -190,6 +190,9 @@ void blk_add_timer(struct request *req)
        struct request_queue *q = req->q;
        unsigned long expiry;
 
+       if (req->cmd_flags & REQ_NO_TIMEOUT)
+               return;
+
        /* blk-mq has its own handler, so we don't need ->rq_timed_out_fn */
        if (!q->mq_ops && !q->rq_timed_out_fn)
                return;
index 9b3c54c1cbe826a8cb031a9affb9079f0961d1c4..3dd101144a58def9c38adae3cdf21f810cdbe0aa 100644 (file)
@@ -1475,3 +1475,4 @@ module_exit(aes_fini);
 MODULE_DESCRIPTION("Rijndael (AES) Cipher Algorithm");
 MODULE_LICENSE("Dual BSD/GPL");
 MODULE_ALIAS_CRYPTO("aes");
+MODULE_ALIAS_CRYPTO("aes-generic");
index b4485a108389a2f13b0ca28949e4f6b932818277..6f5bebc9bf01ebea38bca6dd616c6bd2c3ce2111 100644 (file)
@@ -477,3 +477,4 @@ MODULE_PARM_DESC(dbg, "Boolean to enable debugging (0/1 == off/on)");
 module_init(prng_mod_init);
 module_exit(prng_mod_fini);
 MODULE_ALIAS_CRYPTO("stdrng");
+MODULE_ALIAS_CRYPTO("ansi_cprng");
index 7bd71f02d0dde233939716f3b0059cc758ab788c..87b392a77a9395a9e4164b7e9356e739c9f96455 100644 (file)
@@ -139,3 +139,4 @@ module_exit(blowfish_mod_fini);
 MODULE_LICENSE("GPL");
 MODULE_DESCRIPTION("Blowfish Cipher Algorithm");
 MODULE_ALIAS_CRYPTO("blowfish");
+MODULE_ALIAS_CRYPTO("blowfish-generic");
index 1b74c5a3e8910741cac8c92e292b041eff40e714..a02286bf319ea3cc0b52fd21079506f0667715b3 100644 (file)
@@ -1099,3 +1099,4 @@ module_exit(camellia_fini);
 MODULE_DESCRIPTION("Camellia Cipher Algorithm");
 MODULE_LICENSE("GPL");
 MODULE_ALIAS_CRYPTO("camellia");
+MODULE_ALIAS_CRYPTO("camellia-generic");
index 84c86db67ec7a88a85fd92a93ad07af6eb935564..df5c72629383d99b9fa1c030112b8e0bfc3fbd96 100644 (file)
@@ -550,3 +550,4 @@ module_exit(cast5_mod_fini);
 MODULE_LICENSE("GPL");
 MODULE_DESCRIPTION("Cast5 Cipher Algorithm");
 MODULE_ALIAS_CRYPTO("cast5");
+MODULE_ALIAS_CRYPTO("cast5-generic");
index f408f0bd8de2525ac369ae68c4bd5a5187b22e1d..058c8d755d0366532a7e824b7e22681a40624429 100644 (file)
@@ -292,3 +292,4 @@ module_exit(cast6_mod_fini);
 MODULE_LICENSE("GPL");
 MODULE_DESCRIPTION("Cast6 Cipher Algorithm");
 MODULE_ALIAS_CRYPTO("cast6");
+MODULE_ALIAS_CRYPTO("cast6-generic");
index 2a062025749d925f858939933ebe67283f158562..06f1b60f02b223eeea70c000ec4055c470d4eeae 100644 (file)
@@ -171,4 +171,5 @@ MODULE_AUTHOR("Clay Haapala <chaapala@cisco.com>");
 MODULE_DESCRIPTION("CRC32c (Castagnoli) calculations wrapper for lib/crc32c");
 MODULE_LICENSE("GPL");
 MODULE_ALIAS_CRYPTO("crc32c");
+MODULE_ALIAS_CRYPTO("crc32c-generic");
 MODULE_SOFTDEP("pre: crc32c");
index 08bb4f50452085b65c0ed263a84f5c8298142149..c1229614c7e324e5ee9341d6f2be530afd437487 100644 (file)
@@ -125,3 +125,4 @@ MODULE_AUTHOR("Tim Chen <tim.c.chen@linux.intel.com>");
 MODULE_DESCRIPTION("T10 DIF CRC calculation.");
 MODULE_LICENSE("GPL");
 MODULE_ALIAS_CRYPTO("crct10dif");
+MODULE_ALIAS_CRYPTO("crct10dif-generic");
index 42912948776b1426ec71f2e6fe3d5debd3d67e72..a71720544d118f0134b5301924fe9ab0c572eda7 100644 (file)
@@ -983,8 +983,6 @@ static struct crypto_alg des_algs[2] = { {
        .cia_decrypt            =       des3_ede_decrypt } }
 } };
 
-MODULE_ALIAS_CRYPTO("des3_ede");
-
 static int __init des_generic_mod_init(void)
 {
        return crypto_register_algs(des_algs, ARRAY_SIZE(des_algs));
@@ -1001,4 +999,7 @@ module_exit(des_generic_mod_fini);
 MODULE_LICENSE("GPL");
 MODULE_DESCRIPTION("DES & Triple DES EDE Cipher Algorithms");
 MODULE_AUTHOR("Dag Arne Osvik <da@osvik.no>");
-MODULE_ALIAS("des");
+MODULE_ALIAS_CRYPTO("des");
+MODULE_ALIAS_CRYPTO("des-generic");
+MODULE_ALIAS_CRYPTO("des3_ede");
+MODULE_ALIAS_CRYPTO("des3_ede-generic");
index 4e97fae9666f6fd549235ea60c93f999ad00699c..bac70995e0640a49fbc56797c4f7b605791ff98b 100644 (file)
@@ -173,3 +173,4 @@ module_exit(ghash_mod_exit);
 MODULE_LICENSE("GPL");
 MODULE_DESCRIPTION("GHASH Message Digest Algorithm");
 MODULE_ALIAS_CRYPTO("ghash");
+MODULE_ALIAS_CRYPTO("ghash-generic");
index 67c88b3312107c7c16e9732fa9ffba38172629f4..0224841b6579aa8a915406f7c3a944385c6fcbd6 100644 (file)
@@ -63,3 +63,4 @@ module_exit(krng_mod_fini);
 MODULE_LICENSE("GPL");
 MODULE_DESCRIPTION("Kernel Random Number Generator");
 MODULE_ALIAS_CRYPTO("stdrng");
+MODULE_ALIAS_CRYPTO("krng");
index 3d0f9df30ac9fe368baa63598db9426c2cd8657a..f550b5d9463074b16670129341de59e069f8509c 100644 (file)
@@ -249,3 +249,4 @@ module_exit(salsa20_generic_mod_fini);
 MODULE_LICENSE("GPL");
 MODULE_DESCRIPTION ("Salsa20 stream cipher algorithm");
 MODULE_ALIAS_CRYPTO("salsa20");
+MODULE_ALIAS_CRYPTO("salsa20-generic");
index a53b5e2af335c95d046b85c0162dd0a5bb25e5e4..94970a794975ac2148fbc0d84bf2e830719070da 100644 (file)
@@ -667,3 +667,4 @@ MODULE_DESCRIPTION("Serpent and tnepres (kerneli compatible serpent reversed) Ci
 MODULE_AUTHOR("Dag Arne Osvik <osvik@ii.uib.no>");
 MODULE_ALIAS_CRYPTO("tnepres");
 MODULE_ALIAS_CRYPTO("serpent");
+MODULE_ALIAS_CRYPTO("serpent-generic");
index 039e58cfa155655f42aec3ddcb8d2761aa22b264..a3e50c37eb6f8f670e4e7da64b62d05ebc2b56d8 100644 (file)
@@ -154,3 +154,4 @@ MODULE_LICENSE("GPL");
 MODULE_DESCRIPTION("SHA1 Secure Hash Algorithm");
 
 MODULE_ALIAS_CRYPTO("sha1");
+MODULE_ALIAS_CRYPTO("sha1-generic");
index 5eb21b1200333e95c73f11d3343183c37331544c..b001ff5c2efcec0d657fd33c2273be4980db690d 100644 (file)
@@ -385,4 +385,6 @@ MODULE_LICENSE("GPL");
 MODULE_DESCRIPTION("SHA-224 and SHA-256 Secure Hash Algorithm");
 
 MODULE_ALIAS_CRYPTO("sha224");
+MODULE_ALIAS_CRYPTO("sha224-generic");
 MODULE_ALIAS_CRYPTO("sha256");
+MODULE_ALIAS_CRYPTO("sha256-generic");
index 8d0b19ed4f4b3fb90df2266132f5877a488b1e1c..1c3c3767e079af825e3f53b779cca7f8c416b257 100644 (file)
@@ -289,4 +289,6 @@ MODULE_LICENSE("GPL");
 MODULE_DESCRIPTION("SHA-512 and SHA-384 Secure Hash Algorithms");
 
 MODULE_ALIAS_CRYPTO("sha384");
+MODULE_ALIAS_CRYPTO("sha384-generic");
 MODULE_ALIAS_CRYPTO("sha512");
+MODULE_ALIAS_CRYPTO("sha512-generic");
index 495be2d0077d4a2828323d2d9ec187964cd74948..b70b441c7d1e7e6135f000fa8fa58a3057671b20 100644 (file)
@@ -270,6 +270,7 @@ static void __exit tea_mod_fini(void)
        crypto_unregister_algs(tea_algs, ARRAY_SIZE(tea_algs));
 }
 
+MODULE_ALIAS_CRYPTO("tea");
 MODULE_ALIAS_CRYPTO("xtea");
 MODULE_ALIAS_CRYPTO("xeta");
 
index 6e5651c66cf8a783b235e1f8551154e8e01641de..321bc6ff2a9d1ff714b3f27e49b68f0d48ce17e0 100644 (file)
@@ -676,6 +676,7 @@ static void __exit tgr192_mod_fini(void)
        crypto_unregister_shashes(tgr_algs, ARRAY_SIZE(tgr_algs));
 }
 
+MODULE_ALIAS_CRYPTO("tgr192");
 MODULE_ALIAS_CRYPTO("tgr160");
 MODULE_ALIAS_CRYPTO("tgr128");
 
index 523ad8c4e35918329cc08ef979d58a678f52dc5d..ebf7a3efb572715750c9529b8f54e9e724b6c5e7 100644 (file)
@@ -212,3 +212,4 @@ module_exit(twofish_mod_fini);
 MODULE_LICENSE("GPL");
 MODULE_DESCRIPTION ("Twofish Cipher Algorithm");
 MODULE_ALIAS_CRYPTO("twofish");
+MODULE_ALIAS_CRYPTO("twofish-generic");
index 0de42eb3d0400b895de0cf8e70e1015dd137ff87..7ee5a043a988350770c3fe712f45b4f3995063c9 100644 (file)
@@ -1167,6 +1167,7 @@ static void __exit wp512_mod_fini(void)
        crypto_unregister_shashes(wp_algs, ARRAY_SIZE(wp_algs));
 }
 
+MODULE_ALIAS_CRYPTO("wp512");
 MODULE_ALIAS_CRYPTO("wp384");
 MODULE_ALIAS_CRYPTO("wp256");
 
index a27d31d1ba24afcd176d1151aff62da8350e54b4..9dcf83682e367e889db67cd5ae44670878893459 100644 (file)
 
 #include "internal.h"
 
-#define DO_ENUMERATION 0x01
+#define INT3401_DEVICE 0X01
 static const struct acpi_device_id int340x_thermal_device_ids[] = {
-       {"INT3400", DO_ENUMERATION },
-       {"INT3401"},
+       {"INT3400"},
+       {"INT3401", INT3401_DEVICE},
        {"INT3402"},
        {"INT3403"},
        {"INT3404"},
@@ -34,7 +34,10 @@ static int int340x_thermal_handler_attach(struct acpi_device *adev,
                                        const struct acpi_device_id *id)
 {
 #if defined(CONFIG_INT340X_THERMAL) || defined(CONFIG_INT340X_THERMAL_MODULE)
-       if (id->driver_data == DO_ENUMERATION)
+       acpi_create_platform_device(adev);
+#elif defined(INTEL_SOC_DTS_THERMAL) || defined(INTEL_SOC_DTS_THERMAL_MODULE)
+       /* Intel SoC DTS thermal driver needs INT3401 to set IRQ descriptor */
+       if (id->driver_data == INT3401_DEVICE)
                acpi_create_platform_device(adev);
 #endif
        return 1;
index a3a13605a9c42d13baed5746f9f1bfb9bc30536c..5f601553b9b043fff9ac80552ab55dbc4173c714 100644 (file)
@@ -835,6 +835,7 @@ config PATA_AT32
 config PATA_AT91
        tristate "PATA support for AT91SAM9260"
        depends on ARM && SOC_AT91SAM9
+       depends on !ARCH_MULTIPLATFORM
        help
          This option enables support for IDE devices on the Atmel AT91SAM9260 SoC.
 
index 49f1e6890587e0b7f8970fe2dbdb7d879da92871..33bb06e006c9d6cbd9689b92a08df1481b12c568 100644 (file)
@@ -325,7 +325,6 @@ static const struct pci_device_id ahci_pci_tbl[] = {
        { PCI_VDEVICE(INTEL, 0x9d05), board_ahci }, /* Sunrise Point-LP RAID */
        { PCI_VDEVICE(INTEL, 0x9d07), board_ahci }, /* Sunrise Point-LP RAID */
        { PCI_VDEVICE(INTEL, 0xa103), board_ahci }, /* Sunrise Point-H AHCI */
-       { PCI_VDEVICE(INTEL, 0xa103), board_ahci }, /* Sunrise Point-H RAID */
        { PCI_VDEVICE(INTEL, 0xa105), board_ahci }, /* Sunrise Point-H RAID */
        { PCI_VDEVICE(INTEL, 0xa107), board_ahci }, /* Sunrise Point-H RAID */
        { PCI_VDEVICE(INTEL, 0xa10f), board_ahci }, /* Sunrise Point-H RAID */
index feeb8f1e2fe845e8f63ede5363c34b6dee64803d..cbcd2081035573e9897db0afd475224c176231d3 100644 (file)
@@ -125,10 +125,11 @@ static int xgene_ahci_restart_engine(struct ata_port *ap)
  * xgene_ahci_qc_issue - Issue commands to the device
  * @qc: Command to issue
  *
- * Due to Hardware errata for IDENTIFY DEVICE command, the controller cannot
- * clear the BSY bit after receiving the PIO setup FIS. This results in the dma
- * state machine goes into the CMFatalErrorUpdate state and locks up. By
- * restarting the dma engine, it removes the controller out of lock up state.
+ * Due to Hardware errata for IDENTIFY DEVICE command and PACKET
+ * command of ATAPI protocol set, the controller cannot clear the BSY bit
+ * after receiving the PIO setup FIS. This results in the DMA state machine
+ * going into the CMFatalErrorUpdate state and locks up. By restarting the
+ * DMA engine, it removes the controller out of lock up state.
  */
 static unsigned int xgene_ahci_qc_issue(struct ata_queued_cmd *qc)
 {
@@ -137,7 +138,8 @@ static unsigned int xgene_ahci_qc_issue(struct ata_queued_cmd *qc)
        struct xgene_ahci_context *ctx = hpriv->plat_data;
        int rc = 0;
 
-       if (unlikely(ctx->last_cmd[ap->port_no] == ATA_CMD_ID_ATA))
+       if (unlikely((ctx->last_cmd[ap->port_no] == ATA_CMD_ID_ATA) ||
+           (ctx->last_cmd[ap->port_no] == ATA_CMD_PACKET)))
                xgene_ahci_restart_engine(ap);
 
        rc = ahci_qc_issue(qc);
@@ -188,7 +190,7 @@ static unsigned int xgene_ahci_read_id(struct ata_device *dev,
         *
         * Clear reserved bit 8 (DEVSLP bit) as we don't support DEVSLP
         */
-       id[ATA_ID_FEATURE_SUPP] &= ~(1 << 8);
+       id[ATA_ID_FEATURE_SUPP] &= cpu_to_le16(~(1 << 8));
 
        return 0;
 }
index 97683e45ab043be5045ae22945a5520e845cfe4f..61a9c07e0dff5b277dba35cfa135bac449f9ce84 100644 (file)
@@ -2003,7 +2003,7 @@ static void ahci_set_aggressive_devslp(struct ata_port *ap, bool sleep)
 
        devslp = readl(port_mmio + PORT_DEVSLP);
        if (!(devslp & PORT_DEVSLP_DSP)) {
-               dev_err(ap->host->dev, "port does not support device sleep\n");
+               dev_info(ap->host->dev, "port does not support device sleep\n");
                return;
        }
 
index 5c84fb5c33720d5b83ba52d407656445a1dbe0ae..d1a05f9bb91f239b6b24f115b6bade4694152698 100644 (file)
@@ -4233,10 +4233,33 @@ static const struct ata_blacklist_entry ata_device_blacklist [] = {
        { "PIONEER DVD-RW  DVR-216D",   NULL,   ATA_HORKAGE_NOSETXFER },
 
        /* devices that don't properly handle queued TRIM commands */
-       { "Micron_M500*",               NULL,   ATA_HORKAGE_NO_NCQ_TRIM, },
-       { "Crucial_CT???M500SSD*",      NULL,   ATA_HORKAGE_NO_NCQ_TRIM, },
-       { "Micron_M550*",               NULL,   ATA_HORKAGE_NO_NCQ_TRIM, },
-       { "Crucial_CT*M550SSD*",        NULL,   ATA_HORKAGE_NO_NCQ_TRIM, },
+       { "Micron_M[56]*",              NULL,   ATA_HORKAGE_NO_NCQ_TRIM |
+                                               ATA_HORKAGE_ZERO_AFTER_TRIM, },
+       { "Crucial_CT*SSD*",            NULL,   ATA_HORKAGE_NO_NCQ_TRIM, },
+
+       /*
+        * As defined, the DRAT (Deterministic Read After Trim) and RZAT
+        * (Return Zero After Trim) flags in the ATA Command Set are
+        * unreliable in the sense that they only define what happens if
+        * the device successfully executed the DSM TRIM command. TRIM
+        * is only advisory, however, and the device is free to silently
+        * ignore all or parts of the request.
+        *
+        * Whitelist drives that are known to reliably return zeroes
+        * after TRIM.
+        */
+
+       /*
+        * The intel 510 drive has buggy DRAT/RZAT. Explicitly exclude
+        * that model before whitelisting all other intel SSDs.
+        */
+       { "INTEL*SSDSC2MH*",            NULL,   0, },
+
+       { "INTEL*SSD*",                 NULL,   ATA_HORKAGE_ZERO_AFTER_TRIM, },
+       { "SSD*INTEL*",                 NULL,   ATA_HORKAGE_ZERO_AFTER_TRIM, },
+       { "Samsung*SSD*",               NULL,   ATA_HORKAGE_ZERO_AFTER_TRIM, },
+       { "SAMSUNG*SSD*",               NULL,   ATA_HORKAGE_ZERO_AFTER_TRIM, },
+       { "ST[1248][0248]0[FH]*",       NULL,   ATA_HORKAGE_ZERO_AFTER_TRIM, },
 
        /*
         * Some WD SATA-I drives spin up and down erratically when the link
@@ -4748,7 +4771,10 @@ static struct ata_queued_cmd *ata_qc_new(struct ata_port *ap)
                return NULL;
 
        for (i = 0, tag = ap->last_tag + 1; i < max_queue; i++, tag++) {
-               tag = tag < max_queue ? tag : 0;
+               if (ap->flags & ATA_FLAG_LOWTAG)
+                       tag = i;
+               else
+                       tag = tag < max_queue ? tag : 0;
 
                /* the last tag is reserved for internal command. */
                if (tag == ATA_TAG_INTERNAL)
index 3dbec8954c867e435689c313d1b1f2f383aaea1e..8d00c2638bed8ea499fb55bcd1b8b660c80be814 100644 (file)
@@ -2389,6 +2389,7 @@ const char *ata_get_cmd_descript(u8 command)
 
        return NULL;
 }
+EXPORT_SYMBOL_GPL(ata_get_cmd_descript);
 
 /**
  *     ata_eh_link_report - report error handling to user
index e364e86e84d75b7d4ec8f18bba0eb4fc2b21a43c..6abd17a85b1369d4515302090c6eb57a2d1d088b 100644 (file)
@@ -2532,13 +2532,15 @@ static unsigned int ata_scsiop_read_cap(struct ata_scsi_args *args, u8 *rbuf)
                rbuf[15] = lowest_aligned;
 
                if (ata_id_has_trim(args->id)) {
-                       rbuf[14] |= 0x80; /* TPE */
+                       rbuf[14] |= 0x80; /* LBPME */
 
-                       if (ata_id_has_zero_after_trim(args->id))
-                               rbuf[14] |= 0x40; /* TPRZ */
+                       if (ata_id_has_zero_after_trim(args->id) &&
+                           dev->horkage & ATA_HORKAGE_ZERO_AFTER_TRIM) {
+                               ata_dev_info(dev, "Enabling discard_zeroes_data\n");
+                               rbuf[14] |= 0x40; /* LBPRZ */
+                       }
                }
        }
-
        return 0;
 }
 
index db90aa35cb71e9456d176dcdd1214b760165cc4c..2e86e3b852666e3b57e55aafde26ba1c13f8c695 100644 (file)
@@ -1333,7 +1333,19 @@ void ata_sff_flush_pio_task(struct ata_port *ap)
        DPRINTK("ENTER\n");
 
        cancel_delayed_work_sync(&ap->sff_pio_task);
+
+       /*
+        * We wanna reset the HSM state to IDLE.  If we do so without
+        * grabbing the port lock, critical sections protected by it which
+        * expect the HSM state to stay stable may get surprised.  For
+        * example, we may set IDLE in between the time
+        * __ata_sff_port_intr() checks for HSM_ST_IDLE and before it calls
+        * ata_sff_hsm_move() causing ata_sff_hsm_move() to BUG().
+        */
+       spin_lock_irq(ap->lock);
        ap->hsm_task_state = HSM_ST_IDLE;
+       spin_unlock_irq(ap->lock);
+
        ap->sff_pio_task_link = NULL;
 
        if (ata_msg_ctl(ap))
index c7ddef89e7b02695509a5fa3076d6953435d4b86..8e8248179d20577cf83d0270e324d1a867554554 100644 (file)
@@ -797,7 +797,7 @@ static int dma_dwc_init(struct sata_dwc_device *hsdev, int irq)
        if (err) {
                dev_err(host_pvt.dwc_dev, "%s: dma_request_interrupts returns"
                        " %d\n", __func__, err);
-               goto error_out;
+               return err;
        }
 
        /* Enabe DMA */
@@ -808,11 +808,6 @@ static int dma_dwc_init(struct sata_dwc_device *hsdev, int irq)
                sata_dma_regs);
 
        return 0;
-
-error_out:
-       dma_dwc_exit(hsdev);
-
-       return err;
 }
 
 static int sata_dwc_scr_read(struct ata_link *link, unsigned int scr, u32 *val)
@@ -1662,7 +1657,7 @@ static int sata_dwc_probe(struct platform_device *ofdev)
        char *ver = (char *)&versionr;
        u8 *base = NULL;
        int err = 0;
-       int irq, rc;
+       int irq;
        struct ata_host *host;
        struct ata_port_info pi = sata_dwc_port_info[0];
        const struct ata_port_info *ppi[] = { &pi, NULL };
@@ -1725,7 +1720,7 @@ static int sata_dwc_probe(struct platform_device *ofdev)
        if (irq == NO_IRQ) {
                dev_err(&ofdev->dev, "no SATA DMA irq\n");
                err = -ENODEV;
-               goto error_out;
+               goto error_iomap;
        }
 
        /* Get physical SATA DMA register base address */
@@ -1734,14 +1729,16 @@ static int sata_dwc_probe(struct platform_device *ofdev)
                dev_err(&ofdev->dev, "ioremap failed for AHBDMA register"
                        " address\n");
                err = -ENODEV;
-               goto error_out;
+               goto error_iomap;
        }
 
        /* Save dev for later use in dev_xxx() routines */
        host_pvt.dwc_dev = &ofdev->dev;
 
        /* Initialize AHB DMAC */
-       dma_dwc_init(hsdev, irq);
+       err = dma_dwc_init(hsdev, irq);
+       if (err)
+               goto error_dma_iomap;
 
        /* Enable SATA Interrupts */
        sata_dwc_enable_interrupts(hsdev);
@@ -1759,9 +1756,8 @@ static int sata_dwc_probe(struct platform_device *ofdev)
         * device discovery process, invoking our port_start() handler &
         * error_handler() to execute a dummy Softreset EH session
         */
-       rc = ata_host_activate(host, irq, sata_dwc_isr, 0, &sata_dwc_sht);
-
-       if (rc != 0)
+       err = ata_host_activate(host, irq, sata_dwc_isr, 0, &sata_dwc_sht);
+       if (err)
                dev_err(&ofdev->dev, "failed to activate host");
 
        dev_set_drvdata(&ofdev->dev, host);
@@ -1770,7 +1766,8 @@ static int sata_dwc_probe(struct platform_device *ofdev)
 error_out:
        /* Free SATA DMA resources */
        dma_dwc_exit(hsdev);
-
+error_dma_iomap:
+       iounmap((void __iomem *)host_pvt.sata_dma_regs);
 error_iomap:
        iounmap(base);
 error_kmalloc:
@@ -1791,6 +1788,7 @@ static int sata_dwc_remove(struct platform_device *ofdev)
        /* Free SATA DMA resources */
        dma_dwc_exit(hsdev);
 
+       iounmap((void __iomem *)host_pvt.sata_dma_regs);
        iounmap(hsdev->reg_base);
        kfree(hsdev);
        kfree(host);
index d81b20ddb52736de9f9b7e15126382ebdeec2e37..ea655949023f4a6304096a33724ed2d2d8ed56c3 100644 (file)
@@ -246,7 +246,7 @@ enum {
        /* host flags */
        SIL24_COMMON_FLAGS      = ATA_FLAG_SATA | ATA_FLAG_PIO_DMA |
                                  ATA_FLAG_NCQ | ATA_FLAG_ACPI_SATA |
-                                 ATA_FLAG_AN | ATA_FLAG_PMP,
+                                 ATA_FLAG_AN | ATA_FLAG_PMP | ATA_FLAG_LOWTAG,
        SIL24_FLAG_PCIX_IRQ_WOC = (1 << 24), /* IRQ loss errata on PCI-X */
 
        IRQ_STAT_4PORTS         = 0xf,
index ae9f615382f6173c9ad6377c4bc4275403575fdf..aa2224aa7caa34d5854aebfb7ceaf4cebd29eccc 100644 (file)
@@ -530,7 +530,7 @@ static int null_add_dev(void)
                        goto out_cleanup_queues;
 
                nullb->q = blk_mq_init_queue(&nullb->tag_set);
-               if (!nullb->q) {
+               if (IS_ERR(nullb->q)) {
                        rv = -ENOMEM;
                        goto out_cleanup_tags;
                }
index b1d5d87973157b4c6e4a70b757519c37b3460201..cb529e9a82dd685b5b372bea2ed272c59fae5bc5 100644 (file)
@@ -215,6 +215,7 @@ static void nvme_set_info(struct nvme_cmd_info *cmd, void *ctx,
        cmd->fn = handler;
        cmd->ctx = ctx;
        cmd->aborted = 0;
+       blk_mq_start_request(blk_mq_rq_from_pdu(cmd));
 }
 
 /* Special values must be less than 0x1000 */
@@ -431,8 +432,13 @@ static void req_completion(struct nvme_queue *nvmeq, void *ctx,
        if (unlikely(status)) {
                if (!(status & NVME_SC_DNR || blk_noretry_request(req))
                    && (jiffies - req->start_time) < req->timeout) {
+                       unsigned long flags;
+
                        blk_mq_requeue_request(req);
-                       blk_mq_kick_requeue_list(req->q);
+                       spin_lock_irqsave(req->q->queue_lock, flags);
+                       if (!blk_queue_stopped(req->q))
+                               blk_mq_kick_requeue_list(req->q);
+                       spin_unlock_irqrestore(req->q->queue_lock, flags);
                        return;
                }
                req->errors = nvme_error_status(status);
@@ -664,8 +670,6 @@ static int nvme_queue_rq(struct blk_mq_hw_ctx *hctx,
                }
        }
 
-       blk_mq_start_request(req);
-
        nvme_set_info(cmd, iod, req_completion);
        spin_lock_irq(&nvmeq->q_lock);
        if (req->cmd_flags & REQ_DISCARD)
@@ -835,6 +839,7 @@ static int nvme_submit_async_admin_req(struct nvme_dev *dev)
        if (IS_ERR(req))
                return PTR_ERR(req);
 
+       req->cmd_flags |= REQ_NO_TIMEOUT;
        cmd_info = blk_mq_rq_to_pdu(req);
        nvme_set_info(cmd_info, req, async_req_completion);
 
@@ -1016,14 +1021,19 @@ static void nvme_abort_req(struct request *req)
        struct nvme_command cmd;
 
        if (!nvmeq->qid || cmd_rq->aborted) {
+               unsigned long flags;
+
+               spin_lock_irqsave(&dev_list_lock, flags);
                if (work_busy(&dev->reset_work))
-                       return;
+                       goto out;
                list_del_init(&dev->node);
                dev_warn(&dev->pci_dev->dev,
                        "I/O %d QID %d timeout, reset controller\n",
                                                        req->tag, nvmeq->qid);
                dev->reset_workfn = nvme_reset_failed_dev;
                queue_work(nvme_workq, &dev->reset_work);
+ out:
+               spin_unlock_irqrestore(&dev_list_lock, flags);
                return;
        }
 
@@ -1064,15 +1074,22 @@ static void nvme_cancel_queue_ios(struct blk_mq_hw_ctx *hctx,
        void *ctx;
        nvme_completion_fn fn;
        struct nvme_cmd_info *cmd;
-       static struct nvme_completion cqe = {
-               .status = cpu_to_le16(NVME_SC_ABORT_REQ << 1),
-       };
+       struct nvme_completion cqe;
+
+       if (!blk_mq_request_started(req))
+               return;
 
        cmd = blk_mq_rq_to_pdu(req);
 
        if (cmd->ctx == CMD_CTX_CANCELLED)
                return;
 
+       if (blk_queue_dying(req->q))
+               cqe.status = cpu_to_le16((NVME_SC_ABORT_REQ | NVME_SC_DNR) << 1);
+       else
+               cqe.status = cpu_to_le16(NVME_SC_ABORT_REQ << 1);
+
+
        dev_warn(nvmeq->q_dmadev, "Cancelling I/O %d QID %d\n",
                                                req->tag, nvmeq->qid);
        ctx = cancel_cmd_info(cmd, &fn);
@@ -1084,17 +1101,29 @@ static enum blk_eh_timer_return nvme_timeout(struct request *req, bool reserved)
        struct nvme_cmd_info *cmd = blk_mq_rq_to_pdu(req);
        struct nvme_queue *nvmeq = cmd->nvmeq;
 
-       dev_warn(nvmeq->q_dmadev, "Timeout I/O %d QID %d\n", req->tag,
-                                                       nvmeq->qid);
-       if (nvmeq->dev->initialized)
-               nvme_abort_req(req);
-
        /*
         * The aborted req will be completed on receiving the abort req.
         * We enable the timer again. If hit twice, it'll cause a device reset,
         * as the device then is in a faulty state.
         */
-       return BLK_EH_RESET_TIMER;
+       int ret = BLK_EH_RESET_TIMER;
+
+       dev_warn(nvmeq->q_dmadev, "Timeout I/O %d QID %d\n", req->tag,
+                                                       nvmeq->qid);
+
+       spin_lock_irq(&nvmeq->q_lock);
+       if (!nvmeq->dev->initialized) {
+               /*
+                * Force cancelled command frees the request, which requires we
+                * return BLK_EH_NOT_HANDLED.
+                */
+               nvme_cancel_queue_ios(nvmeq->hctx, req, nvmeq, reserved);
+               ret = BLK_EH_NOT_HANDLED;
+       } else
+               nvme_abort_req(req);
+       spin_unlock_irq(&nvmeq->q_lock);
+
+       return ret;
 }
 
 static void nvme_free_queue(struct nvme_queue *nvmeq)
@@ -1131,10 +1160,16 @@ static void nvme_free_queues(struct nvme_dev *dev, int lowest)
  */
 static int nvme_suspend_queue(struct nvme_queue *nvmeq)
 {
-       int vector = nvmeq->dev->entry[nvmeq->cq_vector].vector;
+       int vector;
 
        spin_lock_irq(&nvmeq->q_lock);
+       if (nvmeq->cq_vector == -1) {
+               spin_unlock_irq(&nvmeq->q_lock);
+               return 1;
+       }
+       vector = nvmeq->dev->entry[nvmeq->cq_vector].vector;
        nvmeq->dev->online_queues--;
+       nvmeq->cq_vector = -1;
        spin_unlock_irq(&nvmeq->q_lock);
 
        irq_set_affinity_hint(vector, NULL);
@@ -1169,11 +1204,13 @@ static void nvme_disable_queue(struct nvme_dev *dev, int qid)
                adapter_delete_sq(dev, qid);
                adapter_delete_cq(dev, qid);
        }
+       if (!qid && dev->admin_q)
+               blk_mq_freeze_queue_start(dev->admin_q);
        nvme_clear_queue(nvmeq);
 }
 
 static struct nvme_queue *nvme_alloc_queue(struct nvme_dev *dev, int qid,
-                                                       int depth, int vector)
+                                                       int depth)
 {
        struct device *dmadev = &dev->pci_dev->dev;
        struct nvme_queue *nvmeq = kzalloc(sizeof(*nvmeq), GFP_KERNEL);
@@ -1199,7 +1236,6 @@ static struct nvme_queue *nvme_alloc_queue(struct nvme_dev *dev, int qid,
        nvmeq->cq_phase = 1;
        nvmeq->q_db = &dev->dbs[qid * 2 * dev->db_stride];
        nvmeq->q_depth = depth;
-       nvmeq->cq_vector = vector;
        nvmeq->qid = qid;
        dev->queue_count++;
        dev->queues[qid] = nvmeq;
@@ -1244,6 +1280,7 @@ static int nvme_create_queue(struct nvme_queue *nvmeq, int qid)
        struct nvme_dev *dev = nvmeq->dev;
        int result;
 
+       nvmeq->cq_vector = qid - 1;
        result = adapter_alloc_cq(dev, qid, nvmeq);
        if (result < 0)
                return result;
@@ -1355,6 +1392,14 @@ static struct blk_mq_ops nvme_mq_ops = {
        .timeout        = nvme_timeout,
 };
 
+static void nvme_dev_remove_admin(struct nvme_dev *dev)
+{
+       if (dev->admin_q && !blk_queue_dying(dev->admin_q)) {
+               blk_cleanup_queue(dev->admin_q);
+               blk_mq_free_tag_set(&dev->admin_tagset);
+       }
+}
+
 static int nvme_alloc_admin_tags(struct nvme_dev *dev)
 {
        if (!dev->admin_q) {
@@ -1370,21 +1415,20 @@ static int nvme_alloc_admin_tags(struct nvme_dev *dev)
                        return -ENOMEM;
 
                dev->admin_q = blk_mq_init_queue(&dev->admin_tagset);
-               if (!dev->admin_q) {
+               if (IS_ERR(dev->admin_q)) {
                        blk_mq_free_tag_set(&dev->admin_tagset);
                        return -ENOMEM;
                }
-       }
+               if (!blk_get_queue(dev->admin_q)) {
+                       nvme_dev_remove_admin(dev);
+                       return -ENODEV;
+               }
+       } else
+               blk_mq_unfreeze_queue(dev->admin_q);
 
        return 0;
 }
 
-static void nvme_free_admin_tags(struct nvme_dev *dev)
-{
-       if (dev->admin_q)
-               blk_mq_free_tag_set(&dev->admin_tagset);
-}
-
 static int nvme_configure_admin_queue(struct nvme_dev *dev)
 {
        int result;
@@ -1416,7 +1460,7 @@ static int nvme_configure_admin_queue(struct nvme_dev *dev)
 
        nvmeq = dev->queues[0];
        if (!nvmeq) {
-               nvmeq = nvme_alloc_queue(dev, 0, NVME_AQ_DEPTH, 0);
+               nvmeq = nvme_alloc_queue(dev, 0, NVME_AQ_DEPTH);
                if (!nvmeq)
                        return -ENOMEM;
        }
@@ -1439,18 +1483,13 @@ static int nvme_configure_admin_queue(struct nvme_dev *dev)
        if (result)
                goto free_nvmeq;
 
-       result = nvme_alloc_admin_tags(dev);
-       if (result)
-               goto free_nvmeq;
-
+       nvmeq->cq_vector = 0;
        result = queue_request_irq(dev, nvmeq, nvmeq->irqname);
        if (result)
-               goto free_tags;
+               goto free_nvmeq;
 
        return result;
 
- free_tags:
-       nvme_free_admin_tags(dev);
  free_nvmeq:
        nvme_free_queues(dev, 0);
        return result;
@@ -1944,7 +1983,7 @@ static void nvme_create_io_queues(struct nvme_dev *dev)
        unsigned i;
 
        for (i = dev->queue_count; i <= dev->max_qid; i++)
-               if (!nvme_alloc_queue(dev, i, dev->q_depth, i - 1))
+               if (!nvme_alloc_queue(dev, i, dev->q_depth))
                        break;
 
        for (i = dev->online_queues; i <= dev->queue_count - 1; i++)
@@ -2235,13 +2274,18 @@ static void nvme_wait_dq(struct nvme_delq_ctx *dq, struct nvme_dev *dev)
                        break;
                if (!schedule_timeout(ADMIN_TIMEOUT) ||
                                        fatal_signal_pending(current)) {
+                       /*
+                        * Disable the controller first since we can't trust it
+                        * at this point, but leave the admin queue enabled
+                        * until all queue deletion requests are flushed.
+                        * FIXME: This may take a while if there are more h/w
+                        * queues than admin tags.
+                        */
                        set_current_state(TASK_RUNNING);
-
                        nvme_disable_ctrl(dev, readq(&dev->bar->cap));
-                       nvme_disable_queue(dev, 0);
-
-                       send_sig(SIGKILL, dq->worker->task, 1);
+                       nvme_clear_queue(dev->queues[0]);
                        flush_kthread_worker(dq->worker);
+                       nvme_disable_queue(dev, 0);
                        return;
                }
        }
@@ -2318,7 +2362,6 @@ static void nvme_del_queue_start(struct kthread_work *work)
 {
        struct nvme_queue *nvmeq = container_of(work, struct nvme_queue,
                                                        cmdinfo.work);
-       allow_signal(SIGKILL);
        if (nvme_delete_sq(nvmeq))
                nvme_del_queue_end(nvmeq);
 }
@@ -2376,6 +2419,34 @@ static void nvme_dev_list_remove(struct nvme_dev *dev)
                kthread_stop(tmp);
 }
 
+static void nvme_freeze_queues(struct nvme_dev *dev)
+{
+       struct nvme_ns *ns;
+
+       list_for_each_entry(ns, &dev->namespaces, list) {
+               blk_mq_freeze_queue_start(ns->queue);
+
+               spin_lock(ns->queue->queue_lock);
+               queue_flag_set(QUEUE_FLAG_STOPPED, ns->queue);
+               spin_unlock(ns->queue->queue_lock);
+
+               blk_mq_cancel_requeue_work(ns->queue);
+               blk_mq_stop_hw_queues(ns->queue);
+       }
+}
+
+static void nvme_unfreeze_queues(struct nvme_dev *dev)
+{
+       struct nvme_ns *ns;
+
+       list_for_each_entry(ns, &dev->namespaces, list) {
+               queue_flag_clear_unlocked(QUEUE_FLAG_STOPPED, ns->queue);
+               blk_mq_unfreeze_queue(ns->queue);
+               blk_mq_start_stopped_hw_queues(ns->queue, true);
+               blk_mq_kick_requeue_list(ns->queue);
+       }
+}
+
 static void nvme_dev_shutdown(struct nvme_dev *dev)
 {
        int i;
@@ -2384,8 +2455,10 @@ static void nvme_dev_shutdown(struct nvme_dev *dev)
        dev->initialized = 0;
        nvme_dev_list_remove(dev);
 
-       if (dev->bar)
+       if (dev->bar) {
+               nvme_freeze_queues(dev);
                csts = readl(&dev->bar->csts);
+       }
        if (csts & NVME_CSTS_CFS || !(csts & NVME_CSTS_RDY)) {
                for (i = dev->queue_count - 1; i >= 0; i--) {
                        struct nvme_queue *nvmeq = dev->queues[i];
@@ -2400,12 +2473,6 @@ static void nvme_dev_shutdown(struct nvme_dev *dev)
        nvme_dev_unmap(dev);
 }
 
-static void nvme_dev_remove_admin(struct nvme_dev *dev)
-{
-       if (dev->admin_q && !blk_queue_dying(dev->admin_q))
-               blk_cleanup_queue(dev->admin_q);
-}
-
 static void nvme_dev_remove(struct nvme_dev *dev)
 {
        struct nvme_ns *ns;
@@ -2413,8 +2480,10 @@ static void nvme_dev_remove(struct nvme_dev *dev)
        list_for_each_entry(ns, &dev->namespaces, list) {
                if (ns->disk->flags & GENHD_FL_UP)
                        del_gendisk(ns->disk);
-               if (!blk_queue_dying(ns->queue))
+               if (!blk_queue_dying(ns->queue)) {
+                       blk_mq_abort_requeue_list(ns->queue);
                        blk_cleanup_queue(ns->queue);
+               }
        }
 }
 
@@ -2495,6 +2564,7 @@ static void nvme_free_dev(struct kref *kref)
        nvme_free_namespaces(dev);
        nvme_release_instance(dev);
        blk_mq_free_tag_set(&dev->tagset);
+       blk_put_queue(dev->admin_q);
        kfree(dev->queues);
        kfree(dev->entry);
        kfree(dev);
@@ -2591,15 +2661,20 @@ static int nvme_dev_start(struct nvme_dev *dev)
        }
 
        nvme_init_queue(dev->queues[0], 0);
+       result = nvme_alloc_admin_tags(dev);
+       if (result)
+               goto disable;
 
        result = nvme_setup_io_queues(dev);
        if (result)
-               goto disable;
+               goto free_tags;
 
        nvme_set_irq_hints(dev);
 
        return result;
 
+ free_tags:
+       nvme_dev_remove_admin(dev);
  disable:
        nvme_disable_queue(dev, 0);
        nvme_dev_list_remove(dev);
@@ -2639,6 +2714,9 @@ static int nvme_dev_resume(struct nvme_dev *dev)
                dev->reset_workfn = nvme_remove_disks;
                queue_work(nvme_workq, &dev->reset_work);
                spin_unlock(&dev_list_lock);
+       } else {
+               nvme_unfreeze_queues(dev);
+               nvme_set_irq_hints(dev);
        }
        dev->initialized = 1;
        return 0;
@@ -2776,11 +2854,10 @@ static void nvme_remove(struct pci_dev *pdev)
        pci_set_drvdata(pdev, NULL);
        flush_work(&dev->reset_work);
        misc_deregister(&dev->miscdev);
-       nvme_dev_remove(dev);
        nvme_dev_shutdown(dev);
+       nvme_dev_remove(dev);
        nvme_dev_remove_admin(dev);
        nvme_free_queues(dev, 0);
-       nvme_free_admin_tags(dev);
        nvme_release_prp_pools(dev);
        kref_put(&dev->kref, nvme_free_dev);
 }
index 7ef7c098708fc4e482181724d574555bbb9db6d7..cdfbd21e35975178fa0c4cece78a354ef1d53007 100644 (file)
@@ -638,7 +638,7 @@ static int virtblk_probe(struct virtio_device *vdev)
                goto out_put_disk;
 
        q = vblk->disk->queue = blk_mq_init_queue(&vblk->tag_set);
-       if (!q) {
+       if (IS_ERR(q)) {
                err = -ENOMEM;
                goto out_free_tags;
        }
index 860da40b78effb96b16a779f84f9ea21d05aba95..0ce5e2d65a06b5d4e6ecbdf3390554f08751d9e2 100644 (file)
@@ -1312,6 +1312,9 @@ static int cci_probe(void)
        if (!np)
                return -ENODEV;
 
+       if (!of_device_is_available(np))
+               return -ENODEV;
+
        cci_config = of_match_node(arm_cci_matches, np)->data;
        if (!cci_config)
                return -ENODEV;
index 32f7c1b36204018d0ce151601c6ca5ef6f2cf75f..2f13bd5246b5563ec399058029fcd0740c58c3d2 100644 (file)
@@ -70,6 +70,7 @@ struct clk_sam9x5_slow {
 
 #define to_clk_sam9x5_slow(hw) container_of(hw, struct clk_sam9x5_slow, hw)
 
+static struct clk *slow_clk;
 
 static int clk_slow_osc_prepare(struct clk_hw *hw)
 {
@@ -357,6 +358,8 @@ at91_clk_register_sam9x5_slow(void __iomem *sckcr,
        clk = clk_register(NULL, &slowck->hw);
        if (IS_ERR(clk))
                kfree(slowck);
+       else
+               slow_clk = clk;
 
        return clk;
 }
@@ -433,6 +436,8 @@ at91_clk_register_sam9260_slow(struct at91_pmc *pmc,
        clk = clk_register(NULL, &slowck->hw);
        if (IS_ERR(clk))
                kfree(slowck);
+       else
+               slow_clk = clk;
 
        return clk;
 }
@@ -465,3 +470,25 @@ void __init of_at91sam9260_clk_slow_setup(struct device_node *np,
 
        of_clk_add_provider(np, of_clk_src_simple_get, clk);
 }
+
+/*
+ * FIXME: All slow clk users are not properly claiming it (get + prepare +
+ * enable) before using it.
+ * If all users properly claiming this clock decide that they don't need it
+ * anymore (or are removed), it is disabled while faulty users are still
+ * requiring it, and the system hangs.
+ * Prevent this clock from being disabled until all users are properly
+ * requesting it.
+ * Once this is done we should remove this function and the slow_clk variable.
+ */
+static int __init of_at91_clk_slow_retain(void)
+{
+       if (!slow_clk)
+               return 0;
+
+       __clk_get(slow_clk);
+       clk_prepare_enable(slow_clk);
+
+       return 0;
+}
+arch_initcall(of_at91_clk_slow_retain);
index 21784e4eb3f004af06c1b980938ab4ced9bc2894..440ef81ab15c4ba8d9f70947db7e5a0d144a97a4 100644 (file)
@@ -285,7 +285,6 @@ static const struct berlin2_gate_data bg2q_gates[] __initconst = {
        { "pbridge",    "perif",        15, CLK_IGNORE_UNUSED },
        { "sdio",       "perif",        16, CLK_IGNORE_UNUSED },
        { "nfc",        "perif",        18 },
-       { "smemc",      "perif",        19 },
        { "pcie",       "perif",        22 },
 };
 
index b6e6c85507a5a7706c8c69f2c6611d908ade8611..0a47d6f49cd6f347eca03eadf283722c737c7fb2 100644 (file)
@@ -291,7 +291,7 @@ static const struct of_device_id ppc_clk_ids[] __initconst = {
        {}
 };
 
-static struct platform_driver ppc_corenet_clk_driver __initdata = {
+static struct platform_driver ppc_corenet_clk_driver = {
        .driver = {
                .name = "ppc_corenet_clock",
                .of_match_table = ppc_clk_ids,
index f4963b7d4e17d41b6a6553854c5250a7e90bfdef..d48ac71c6c8b173793a31e95ebaa93749e883a76 100644 (file)
@@ -1366,7 +1366,7 @@ static struct clk *clk_calc_new_rates(struct clk *clk, unsigned long rate)
                new_rate = clk->ops->determine_rate(clk->hw, rate,
                                                    &best_parent_rate,
                                                    &parent_hw);
-               parent = parent_hw->clk;
+               parent = parent_hw ? parent_hw->clk : NULL;
        } else if (clk->ops->round_rate) {
                new_rate = clk->ops->round_rate(clk->hw, rate,
                                                &best_parent_rate);
index 75c8c45ef72849358e4b7bf2c3bbff7927761ae0..8539c4fd34cc37bd28810b93d6ffb815b0bd48d6 100644 (file)
@@ -124,10 +124,11 @@ static int rockchip_cpuclk_pre_rate_change(struct rockchip_cpuclk *cpuclk,
 {
        const struct rockchip_cpuclk_reg_data *reg_data = cpuclk->reg_data;
        unsigned long alt_prate, alt_div;
+       unsigned long flags;
 
        alt_prate = clk_get_rate(cpuclk->alt_parent);
 
-       spin_lock(cpuclk->lock);
+       spin_lock_irqsave(cpuclk->lock, flags);
 
        /*
         * If the old parent clock speed is less than the clock speed
@@ -164,7 +165,7 @@ static int rockchip_cpuclk_pre_rate_change(struct rockchip_cpuclk *cpuclk,
                        cpuclk->reg_base + reg_data->core_reg);
        }
 
-       spin_unlock(cpuclk->lock);
+       spin_unlock_irqrestore(cpuclk->lock, flags);
        return 0;
 }
 
@@ -173,6 +174,7 @@ static int rockchip_cpuclk_post_rate_change(struct rockchip_cpuclk *cpuclk,
 {
        const struct rockchip_cpuclk_reg_data *reg_data = cpuclk->reg_data;
        const struct rockchip_cpuclk_rate_table *rate;
+       unsigned long flags;
 
        rate = rockchip_get_cpuclk_settings(cpuclk, ndata->new_rate);
        if (!rate) {
@@ -181,7 +183,7 @@ static int rockchip_cpuclk_post_rate_change(struct rockchip_cpuclk *cpuclk,
                return -EINVAL;
        }
 
-       spin_lock(cpuclk->lock);
+       spin_lock_irqsave(cpuclk->lock, flags);
 
        if (ndata->old_rate < ndata->new_rate)
                rockchip_cpuclk_set_dividers(cpuclk, rate);
@@ -201,7 +203,7 @@ static int rockchip_cpuclk_post_rate_change(struct rockchip_cpuclk *cpuclk,
        if (ndata->old_rate > ndata->new_rate)
                rockchip_cpuclk_set_dividers(cpuclk, rate);
 
-       spin_unlock(cpuclk->lock);
+       spin_unlock_irqrestore(cpuclk->lock, flags);
        return 0;
 }
 
index c54078960847c91f6f499ecb8f26924338bb2ab4..7eb684c50d42ce9f0d06ffa4de1ecef4270808b7 100644 (file)
@@ -210,6 +210,17 @@ PNAME(mux_sclk_hsadc_p)            = { "hsadc_src", "hsadc_frac", "ext_hsadc" };
 PNAME(mux_mac_p)               = { "gpll", "dpll" };
 PNAME(mux_sclk_macref_p)       = { "mac_src", "ext_rmii" };
 
+static struct rockchip_pll_clock rk3066_pll_clks[] __initdata = {
+       [apll] = PLL(pll_rk3066, PLL_APLL, "apll", mux_pll_p, 0, RK2928_PLL_CON(0),
+                    RK2928_MODE_CON, 0, 5, 0, rk3188_pll_rates),
+       [dpll] = PLL(pll_rk3066, PLL_DPLL, "dpll", mux_pll_p, 0, RK2928_PLL_CON(4),
+                    RK2928_MODE_CON, 4, 4, 0, NULL),
+       [cpll] = PLL(pll_rk3066, PLL_CPLL, "cpll", mux_pll_p, 0, RK2928_PLL_CON(8),
+                    RK2928_MODE_CON, 8, 6, ROCKCHIP_PLL_SYNC_RATE, rk3188_pll_rates),
+       [gpll] = PLL(pll_rk3066, PLL_GPLL, "gpll", mux_pll_p, 0, RK2928_PLL_CON(12),
+                    RK2928_MODE_CON, 12, 7, ROCKCHIP_PLL_SYNC_RATE, rk3188_pll_rates),
+};
+
 static struct rockchip_pll_clock rk3188_pll_clks[] __initdata = {
        [apll] = PLL(pll_rk3066, PLL_APLL, "apll", mux_pll_p, 0, RK2928_PLL_CON(0),
                     RK2928_MODE_CON, 0, 6, 0, rk3188_pll_rates),
@@ -427,11 +438,11 @@ static struct rockchip_clk_branch common_clk_branches[] __initdata = {
        /* hclk_peri gates */
        GATE(0, "hclk_peri_axi_matrix", "hclk_peri", CLK_IGNORE_UNUSED, RK2928_CLKGATE_CON(4), 0, GFLAGS),
        GATE(0, "hclk_peri_ahb_arbi", "hclk_peri", CLK_IGNORE_UNUSED, RK2928_CLKGATE_CON(4), 6, GFLAGS),
-       GATE(0, "hclk_emem_peri", "hclk_peri", 0, RK2928_CLKGATE_CON(4), 7, GFLAGS),
+       GATE(0, "hclk_emem_peri", "hclk_peri", CLK_IGNORE_UNUSED, RK2928_CLKGATE_CON(4), 7, GFLAGS),
        GATE(HCLK_EMAC, "hclk_emac", "hclk_peri", 0, RK2928_CLKGATE_CON(7), 0, GFLAGS),
        GATE(HCLK_NANDC0, "hclk_nandc0", "hclk_peri", 0, RK2928_CLKGATE_CON(5), 9, GFLAGS),
-       GATE(0, "hclk_usb_peri", "hclk_peri", 0, RK2928_CLKGATE_CON(4), 5, GFLAGS),
-       GATE(HCLK_OTG0, "hclk_usbotg0", "hclk_peri", 0, RK2928_CLKGATE_CON(5), 13, GFLAGS),
+       GATE(0, "hclk_usb_peri", "hclk_peri", CLK_IGNORE_UNUSED, RK2928_CLKGATE_CON(4), 5, GFLAGS),
+       GATE(HCLK_OTG0, "hclk_usbotg0", "hclk_peri", CLK_IGNORE_UNUSED, RK2928_CLKGATE_CON(5), 13, GFLAGS),
        GATE(HCLK_HSADC, "hclk_hsadc", "hclk_peri", 0, RK2928_CLKGATE_CON(7), 5, GFLAGS),
        GATE(HCLK_PIDF, "hclk_pidfilter", "hclk_peri", 0, RK2928_CLKGATE_CON(7), 6, GFLAGS),
        GATE(HCLK_SDMMC, "hclk_sdmmc", "hclk_peri", 0, RK2928_CLKGATE_CON(5), 10, GFLAGS),
@@ -592,7 +603,8 @@ static struct rockchip_clk_branch rk3066a_clk_branches[] __initdata = {
        GATE(0, "hclk_cif1", "hclk_cpu", 0, RK2928_CLKGATE_CON(6), 6, GFLAGS),
        GATE(0, "hclk_hdmi", "hclk_cpu", 0, RK2928_CLKGATE_CON(4), 14, GFLAGS),
 
-       GATE(HCLK_OTG1, "hclk_usbotg1", "hclk_peri", 0, RK2928_CLKGATE_CON(5), 14, GFLAGS),
+       GATE(HCLK_OTG1, "hclk_usbotg1", "hclk_peri", CLK_IGNORE_UNUSED,
+                       RK2928_CLKGATE_CON(5), 14, GFLAGS),
 
        GATE(0, "aclk_cif1", "aclk_vio1", 0, RK2928_CLKGATE_CON(6), 7, GFLAGS),
 
@@ -680,7 +692,8 @@ static struct rockchip_clk_branch rk3188_clk_branches[] __initdata = {
        GATE(0, "hclk_imem0", "hclk_cpu", 0, RK2928_CLKGATE_CON(4), 14, GFLAGS),
        GATE(0, "hclk_imem1", "hclk_cpu", 0, RK2928_CLKGATE_CON(4), 15, GFLAGS),
 
-       GATE(HCLK_OTG1, "hclk_usbotg1", "hclk_peri", 0, RK2928_CLKGATE_CON(7), 3, GFLAGS),
+       GATE(HCLK_OTG1, "hclk_usbotg1", "hclk_peri", CLK_IGNORE_UNUSED,
+                       RK2928_CLKGATE_CON(7), 3, GFLAGS),
        GATE(HCLK_HSIC, "hclk_hsic", "hclk_peri", 0, RK2928_CLKGATE_CON(7), 4, GFLAGS),
 
        GATE(PCLK_TIMER3, "pclk_timer3", "pclk_cpu", 0, RK2928_CLKGATE_CON(7), 9, GFLAGS),
@@ -735,8 +748,8 @@ static void __init rk3188_common_clk_init(struct device_node *np)
 static void __init rk3066a_clk_init(struct device_node *np)
 {
        rk3188_common_clk_init(np);
-       rockchip_clk_register_plls(rk3188_pll_clks,
-                                  ARRAY_SIZE(rk3188_pll_clks),
+       rockchip_clk_register_plls(rk3066_pll_clks,
+                                  ARRAY_SIZE(rk3066_pll_clks),
                                   RK3066_GRF_SOC_STATUS);
        rockchip_clk_register_branches(rk3066a_clk_branches,
                                  ARRAY_SIZE(rk3066a_clk_branches));
index ac6be7c0132d1e27cfad2f95169212b70f3d31d2..11194b8329fe5a639a6241ed0718888f985df854 100644 (file)
@@ -145,20 +145,20 @@ struct rockchip_pll_rate_table rk3288_pll_rates[] = {
        }
 
 static struct rockchip_cpuclk_rate_table rk3288_cpuclk_rates[] __initdata = {
-       RK3288_CPUCLK_RATE(1800000000, 2, 4, 2, 4, 4),
-       RK3288_CPUCLK_RATE(1704000000, 2, 4, 2, 4, 4),
-       RK3288_CPUCLK_RATE(1608000000, 2, 4, 2, 4, 4),
-       RK3288_CPUCLK_RATE(1512000000, 2, 4, 2, 4, 4),
-       RK3288_CPUCLK_RATE(1416000000, 2, 4, 2, 4, 4),
-       RK3288_CPUCLK_RATE(1200000000, 2, 4, 2, 4, 4),
-       RK3288_CPUCLK_RATE(1008000000, 2, 4, 2, 4, 4),
-       RK3288_CPUCLK_RATE( 816000000, 2, 4, 2, 4, 4),
-       RK3288_CPUCLK_RATE( 696000000, 2, 4, 2, 4, 4),
-       RK3288_CPUCLK_RATE( 600000000, 2, 4, 2, 4, 4),
-       RK3288_CPUCLK_RATE( 408000000, 2, 4, 2, 4, 4),
-       RK3288_CPUCLK_RATE( 312000000, 2, 4, 2, 4, 4),
-       RK3288_CPUCLK_RATE( 216000000, 2, 4, 2, 4, 4),
-       RK3288_CPUCLK_RATE( 126000000, 2, 4, 2, 4, 4),
+       RK3288_CPUCLK_RATE(1800000000, 1, 3, 1, 3, 3),
+       RK3288_CPUCLK_RATE(1704000000, 1, 3, 1, 3, 3),
+       RK3288_CPUCLK_RATE(1608000000, 1, 3, 1, 3, 3),
+       RK3288_CPUCLK_RATE(1512000000, 1, 3, 1, 3, 3),
+       RK3288_CPUCLK_RATE(1416000000, 1, 3, 1, 3, 3),
+       RK3288_CPUCLK_RATE(1200000000, 1, 3, 1, 3, 3),
+       RK3288_CPUCLK_RATE(1008000000, 1, 3, 1, 3, 3),
+       RK3288_CPUCLK_RATE( 816000000, 1, 3, 1, 3, 3),
+       RK3288_CPUCLK_RATE( 696000000, 1, 3, 1, 3, 3),
+       RK3288_CPUCLK_RATE( 600000000, 1, 3, 1, 3, 3),
+       RK3288_CPUCLK_RATE( 408000000, 1, 3, 1, 3, 3),
+       RK3288_CPUCLK_RATE( 312000000, 1, 3, 1, 3, 3),
+       RK3288_CPUCLK_RATE( 216000000, 1, 3, 1, 3, 3),
+       RK3288_CPUCLK_RATE( 126000000, 1, 3, 1, 3, 3),
 };
 
 static const struct rockchip_cpuclk_reg_data rk3288_cpuclk_data = {
index 380478562b7d3187d42a64c221caf5714e6e59ec..5c062548957c3183fba608e13354d204c0a4b40c 100644 (file)
@@ -1505,7 +1505,6 @@ int dw_dma_probe(struct dw_dma_chip *chip, struct dw_dma_platform_data *pdata)
        dw->regs = chip->regs;
        chip->dw = dw;
 
-       pm_runtime_enable(chip->dev);
        pm_runtime_get_sync(chip->dev);
 
        dw_params = dma_read_byaddr(chip->regs, DW_PARAMS);
@@ -1703,7 +1702,6 @@ int dw_dma_remove(struct dw_dma_chip *chip)
        }
 
        pm_runtime_put_sync_suspend(chip->dev);
-       pm_runtime_disable(chip->dev);
        return 0;
 }
 EXPORT_SYMBOL_GPL(dw_dma_remove);
index a630161473a4fa69c2586a257949d7f0956d4db7..32ea1aca7a0ea27dc28ddd58c20281f482f53c45 100644 (file)
@@ -15,6 +15,7 @@
 #include <linux/module.h>
 #include <linux/device.h>
 #include <linux/clk.h>
+#include <linux/pm_runtime.h>
 #include <linux/platform_device.h>
 #include <linux/dmaengine.h>
 #include <linux/dma-mapping.h>
@@ -185,6 +186,8 @@ static int dw_probe(struct platform_device *pdev)
        if (err)
                return err;
 
+       pm_runtime_enable(&pdev->dev);
+
        err = dw_dma_probe(chip, pdata);
        if (err)
                goto err_dw_dma_probe;
@@ -205,6 +208,7 @@ static int dw_probe(struct platform_device *pdev)
        return 0;
 
 err_dw_dma_probe:
+       pm_runtime_disable(&pdev->dev);
        clk_disable_unprepare(chip->clk);
        return err;
 }
@@ -217,6 +221,7 @@ static int dw_remove(struct platform_device *pdev)
                of_dma_controller_free(pdev->dev.of_node);
 
        dw_dma_remove(chip);
+       pm_runtime_disable(&pdev->dev);
        clk_disable_unprepare(chip->clk);
 
        return 0;
index 55d4803d71b0db4c3a27b909bfeb20d4d3b668ed..3d9e08f7e823edf13aa719460ecc13f8327c8b31 100644 (file)
@@ -272,7 +272,7 @@ static irqreturn_t crystalcove_gpio_irq_handler(int irq, void *data)
        for (gpio = 0; gpio < CRYSTALCOVE_GPIO_NUM; gpio++) {
                if (pending & BIT(gpio)) {
                        virq = irq_find_mapping(cg->chip.irqdomain, gpio);
-                       generic_handle_irq(virq);
+                       handle_nested_irq(virq);
                }
        }
 
index 978b51eae2ec61bbba18db37cf05b8e93db2037e..ce3c1558cb0a6f6cfa5a818736da54ff8fc5ed07 100644 (file)
 
 #define DLN2_GPIO_MAX_PINS 32
 
-struct dln2_irq_work {
-       struct work_struct work;
-       struct dln2_gpio *dln2;
-       int pin;
-       int type;
-};
-
 struct dln2_gpio {
        struct platform_device *pdev;
        struct gpio_chip gpio;
@@ -64,10 +57,12 @@ struct dln2_gpio {
         */
        DECLARE_BITMAP(output_enabled, DLN2_GPIO_MAX_PINS);
 
-       DECLARE_BITMAP(irqs_masked, DLN2_GPIO_MAX_PINS);
-       DECLARE_BITMAP(irqs_enabled, DLN2_GPIO_MAX_PINS);
-       DECLARE_BITMAP(irqs_pending, DLN2_GPIO_MAX_PINS);
-       struct dln2_irq_work *irq_work;
+       /* active IRQs - not synced to hardware */
+       DECLARE_BITMAP(unmasked_irqs, DLN2_GPIO_MAX_PINS);
+       /* active IRQS - synced to hardware */
+       DECLARE_BITMAP(enabled_irqs, DLN2_GPIO_MAX_PINS);
+       int irq_type[DLN2_GPIO_MAX_PINS];
+       struct mutex irq_lock;
 };
 
 struct dln2_gpio_pin {
@@ -141,16 +136,16 @@ static int dln2_gpio_pin_get_out_val(struct dln2_gpio *dln2, unsigned int pin)
        return !!ret;
 }
 
-static void dln2_gpio_pin_set_out_val(struct dln2_gpio *dln2,
-                                     unsigned int pin, int value)
+static int dln2_gpio_pin_set_out_val(struct dln2_gpio *dln2,
+                                    unsigned int pin, int value)
 {
        struct dln2_gpio_pin_val req = {
                .pin = cpu_to_le16(pin),
                .value = value,
        };
 
-       dln2_transfer_tx(dln2->pdev, DLN2_GPIO_PIN_SET_OUT_VAL, &req,
-                        sizeof(req));
+       return dln2_transfer_tx(dln2->pdev, DLN2_GPIO_PIN_SET_OUT_VAL, &req,
+                               sizeof(req));
 }
 
 #define DLN2_GPIO_DIRECTION_IN         0
@@ -267,6 +262,13 @@ static int dln2_gpio_direction_input(struct gpio_chip *chip, unsigned offset)
 static int dln2_gpio_direction_output(struct gpio_chip *chip, unsigned offset,
                                      int value)
 {
+       struct dln2_gpio *dln2 = container_of(chip, struct dln2_gpio, gpio);
+       int ret;
+
+       ret = dln2_gpio_pin_set_out_val(dln2, offset, value);
+       if (ret < 0)
+               return ret;
+
        return dln2_gpio_set_direction(chip, offset, DLN2_GPIO_DIRECTION_OUT);
 }
 
@@ -297,36 +299,13 @@ static int dln2_gpio_set_event_cfg(struct dln2_gpio *dln2, unsigned pin,
                                &req, sizeof(req));
 }
 
-static void dln2_irq_work(struct work_struct *w)
-{
-       struct dln2_irq_work *iw = container_of(w, struct dln2_irq_work, work);
-       struct dln2_gpio *dln2 = iw->dln2;
-       u8 type = iw->type & DLN2_GPIO_EVENT_MASK;
-
-       if (test_bit(iw->pin, dln2->irqs_enabled))
-               dln2_gpio_set_event_cfg(dln2, iw->pin, type, 0);
-       else
-               dln2_gpio_set_event_cfg(dln2, iw->pin, DLN2_GPIO_EVENT_NONE, 0);
-}
-
-static void dln2_irq_enable(struct irq_data *irqd)
-{
-       struct gpio_chip *gc = irq_data_get_irq_chip_data(irqd);
-       struct dln2_gpio *dln2 = container_of(gc, struct dln2_gpio, gpio);
-       int pin = irqd_to_hwirq(irqd);
-
-       set_bit(pin, dln2->irqs_enabled);
-       schedule_work(&dln2->irq_work[pin].work);
-}
-
-static void dln2_irq_disable(struct irq_data *irqd)
+static void dln2_irq_unmask(struct irq_data *irqd)
 {
        struct gpio_chip *gc = irq_data_get_irq_chip_data(irqd);
        struct dln2_gpio *dln2 = container_of(gc, struct dln2_gpio, gpio);
        int pin = irqd_to_hwirq(irqd);
 
-       clear_bit(pin, dln2->irqs_enabled);
-       schedule_work(&dln2->irq_work[pin].work);
+       set_bit(pin, dln2->unmasked_irqs);
 }
 
 static void dln2_irq_mask(struct irq_data *irqd)
@@ -335,27 +314,7 @@ static void dln2_irq_mask(struct irq_data *irqd)
        struct dln2_gpio *dln2 = container_of(gc, struct dln2_gpio, gpio);
        int pin = irqd_to_hwirq(irqd);
 
-       set_bit(pin, dln2->irqs_masked);
-}
-
-static void dln2_irq_unmask(struct irq_data *irqd)
-{
-       struct gpio_chip *gc = irq_data_get_irq_chip_data(irqd);
-       struct dln2_gpio *dln2 = container_of(gc, struct dln2_gpio, gpio);
-       struct device *dev = dln2->gpio.dev;
-       int pin = irqd_to_hwirq(irqd);
-
-       if (test_and_clear_bit(pin, dln2->irqs_pending)) {
-               int irq;
-
-               irq = irq_find_mapping(dln2->gpio.irqdomain, pin);
-               if (!irq) {
-                       dev_err(dev, "pin %d not mapped to IRQ\n", pin);
-                       return;
-               }
-
-               generic_handle_irq(irq);
-       }
+       clear_bit(pin, dln2->unmasked_irqs);
 }
 
 static int dln2_irq_set_type(struct irq_data *irqd, unsigned type)
@@ -366,19 +325,19 @@ static int dln2_irq_set_type(struct irq_data *irqd, unsigned type)
 
        switch (type) {
        case IRQ_TYPE_LEVEL_HIGH:
-               dln2->irq_work[pin].type = DLN2_GPIO_EVENT_LVL_HIGH;
+               dln2->irq_type[pin] = DLN2_GPIO_EVENT_LVL_HIGH;
                break;
        case IRQ_TYPE_LEVEL_LOW:
-               dln2->irq_work[pin].type = DLN2_GPIO_EVENT_LVL_LOW;
+               dln2->irq_type[pin] = DLN2_GPIO_EVENT_LVL_LOW;
                break;
        case IRQ_TYPE_EDGE_BOTH:
-               dln2->irq_work[pin].type = DLN2_GPIO_EVENT_CHANGE;
+               dln2->irq_type[pin] = DLN2_GPIO_EVENT_CHANGE;
                break;
        case IRQ_TYPE_EDGE_RISING:
-               dln2->irq_work[pin].type = DLN2_GPIO_EVENT_CHANGE_RISING;
+               dln2->irq_type[pin] = DLN2_GPIO_EVENT_CHANGE_RISING;
                break;
        case IRQ_TYPE_EDGE_FALLING:
-               dln2->irq_work[pin].type = DLN2_GPIO_EVENT_CHANGE_FALLING;
+               dln2->irq_type[pin] = DLN2_GPIO_EVENT_CHANGE_FALLING;
                break;
        default:
                return -EINVAL;
@@ -387,13 +346,50 @@ static int dln2_irq_set_type(struct irq_data *irqd, unsigned type)
        return 0;
 }
 
+static void dln2_irq_bus_lock(struct irq_data *irqd)
+{
+       struct gpio_chip *gc = irq_data_get_irq_chip_data(irqd);
+       struct dln2_gpio *dln2 = container_of(gc, struct dln2_gpio, gpio);
+
+       mutex_lock(&dln2->irq_lock);
+}
+
+static void dln2_irq_bus_unlock(struct irq_data *irqd)
+{
+       struct gpio_chip *gc = irq_data_get_irq_chip_data(irqd);
+       struct dln2_gpio *dln2 = container_of(gc, struct dln2_gpio, gpio);
+       int pin = irqd_to_hwirq(irqd);
+       int enabled, unmasked;
+       unsigned type;
+       int ret;
+
+       enabled = test_bit(pin, dln2->enabled_irqs);
+       unmasked = test_bit(pin, dln2->unmasked_irqs);
+
+       if (enabled != unmasked) {
+               if (unmasked) {
+                       type = dln2->irq_type[pin] & DLN2_GPIO_EVENT_MASK;
+                       set_bit(pin, dln2->enabled_irqs);
+               } else {
+                       type = DLN2_GPIO_EVENT_NONE;
+                       clear_bit(pin, dln2->enabled_irqs);
+               }
+
+               ret = dln2_gpio_set_event_cfg(dln2, pin, type, 0);
+               if (ret)
+                       dev_err(dln2->gpio.dev, "failed to set event\n");
+       }
+
+       mutex_unlock(&dln2->irq_lock);
+}
+
 static struct irq_chip dln2_gpio_irqchip = {
        .name = "dln2-irq",
-       .irq_enable = dln2_irq_enable,
-       .irq_disable = dln2_irq_disable,
        .irq_mask = dln2_irq_mask,
        .irq_unmask = dln2_irq_unmask,
        .irq_set_type = dln2_irq_set_type,
+       .irq_bus_lock = dln2_irq_bus_lock,
+       .irq_bus_sync_unlock = dln2_irq_bus_unlock,
 };
 
 static void dln2_gpio_event(struct platform_device *pdev, u16 echo,
@@ -425,14 +421,7 @@ static void dln2_gpio_event(struct platform_device *pdev, u16 echo,
                return;
        }
 
-       if (!test_bit(pin, dln2->irqs_enabled))
-               return;
-       if (test_bit(pin, dln2->irqs_masked)) {
-               set_bit(pin, dln2->irqs_pending);
-               return;
-       }
-
-       switch (dln2->irq_work[pin].type) {
+       switch (dln2->irq_type[pin]) {
        case DLN2_GPIO_EVENT_CHANGE_RISING:
                if (event->value)
                        generic_handle_irq(irq);
@@ -451,7 +440,7 @@ static int dln2_gpio_probe(struct platform_device *pdev)
        struct dln2_gpio *dln2;
        struct device *dev = &pdev->dev;
        int pins;
-       int i, ret;
+       int ret;
 
        pins = dln2_gpio_get_pin_count(pdev);
        if (pins < 0) {
@@ -467,15 +456,7 @@ static int dln2_gpio_probe(struct platform_device *pdev)
        if (!dln2)
                return -ENOMEM;
 
-       dln2->irq_work = devm_kcalloc(&pdev->dev, pins,
-                                     sizeof(struct dln2_irq_work), GFP_KERNEL);
-       if (!dln2->irq_work)
-               return -ENOMEM;
-       for (i = 0; i < pins; i++) {
-               INIT_WORK(&dln2->irq_work[i].work, dln2_irq_work);
-               dln2->irq_work[i].pin = i;
-               dln2->irq_work[i].dln2 = dln2;
-       }
+       mutex_init(&dln2->irq_lock);
 
        dln2->pdev = pdev;
 
@@ -529,11 +510,8 @@ out:
 static int dln2_gpio_remove(struct platform_device *pdev)
 {
        struct dln2_gpio *dln2 = platform_get_drvdata(pdev);
-       int i;
 
        dln2_unregister_event_cb(pdev, DLN2_GPIO_CONDITION_MET_EV);
-       for (i = 0; i < dln2->gpio.ngpio; i++)
-               flush_work(&dln2->irq_work[i].work);
        gpiochip_remove(&dln2->gpio);
 
        return 0;
index 09daaf2aeb563d982c71807b8155df4b2c50a6c5..3a5a71050559c7c52964a5b55764ef9b16e82361 100644 (file)
@@ -441,7 +441,8 @@ static int grgpio_probe(struct platform_device *ofdev)
        err = gpiochip_add(gc);
        if (err) {
                dev_err(&ofdev->dev, "Could not add gpiochip\n");
-               irq_domain_remove(priv->domain);
+               if (priv->domain)
+                       irq_domain_remove(priv->domain);
                return err;
        }
 
index 604dbe60bdee1abdddb8d706947391987628ab9e..08261f2b3a82afed1ed6c2bdcfcf51804ddbb59d 100644 (file)
@@ -45,8 +45,14 @@ static int of_gpiochip_find_and_xlate(struct gpio_chip *gc, void *data)
                return false;
 
        ret = gc->of_xlate(gc, &gg_data->gpiospec, gg_data->flags);
-       if (ret < 0)
-               return false;
+       if (ret < 0) {
+               /* We've found the gpio chip, but the translation failed.
+                * Return true to stop looking and return the translation
+                * error via out_gpio
+                */
+               gg_data->out_gpio = ERR_PTR(ret);
+               return true;
+        }
 
        gg_data->out_gpio = gpiochip_get_desc(gc, ret);
        return true;
index 2ac1800b58bb7052032ecd23d3acf270a1deb132..f62aa115d79ab4f9fe7e249dbb146dfdde44153e 100644 (file)
@@ -128,7 +128,7 @@ static ssize_t gpio_value_store(struct device *dev,
        return status;
 }
 
-static const DEVICE_ATTR(value, 0644,
+static DEVICE_ATTR(value, 0644,
                gpio_value_show, gpio_value_store);
 
 static irqreturn_t gpio_sysfs_irq(int irq, void *priv)
@@ -353,17 +353,46 @@ static ssize_t gpio_active_low_store(struct device *dev,
        return status ? : size;
 }
 
-static const DEVICE_ATTR(active_low, 0644,
+static DEVICE_ATTR(active_low, 0644,
                gpio_active_low_show, gpio_active_low_store);
 
-static const struct attribute *gpio_attrs[] = {
+static umode_t gpio_is_visible(struct kobject *kobj, struct attribute *attr,
+                              int n)
+{
+       struct device *dev = container_of(kobj, struct device, kobj);
+       struct gpio_desc *desc = dev_get_drvdata(dev);
+       umode_t mode = attr->mode;
+       bool show_direction = test_bit(FLAG_SYSFS_DIR, &desc->flags);
+
+       if (attr == &dev_attr_direction.attr) {
+               if (!show_direction)
+                       mode = 0;
+       } else if (attr == &dev_attr_edge.attr) {
+               if (gpiod_to_irq(desc) < 0)
+                       mode = 0;
+               if (!show_direction && test_bit(FLAG_IS_OUT, &desc->flags))
+                       mode = 0;
+       }
+
+       return mode;
+}
+
+static struct attribute *gpio_attrs[] = {
+       &dev_attr_direction.attr,
+       &dev_attr_edge.attr,
        &dev_attr_value.attr,
        &dev_attr_active_low.attr,
        NULL,
 };
 
-static const struct attribute_group gpio_attr_group = {
-       .attrs = (struct attribute **) gpio_attrs,
+static const struct attribute_group gpio_group = {
+       .attrs = gpio_attrs,
+       .is_visible = gpio_is_visible,
+};
+
+static const struct attribute_group *gpio_groups[] = {
+       &gpio_group,
+       NULL
 };
 
 /*
@@ -400,16 +429,13 @@ static ssize_t chip_ngpio_show(struct device *dev,
 }
 static DEVICE_ATTR(ngpio, 0444, chip_ngpio_show, NULL);
 
-static const struct attribute *gpiochip_attrs[] = {
+static struct attribute *gpiochip_attrs[] = {
        &dev_attr_base.attr,
        &dev_attr_label.attr,
        &dev_attr_ngpio.attr,
        NULL,
 };
-
-static const struct attribute_group gpiochip_attr_group = {
-       .attrs = (struct attribute **) gpiochip_attrs,
-};
+ATTRIBUTE_GROUPS(gpiochip);
 
 /*
  * /sys/class/gpio/export ... write-only
@@ -556,45 +582,30 @@ int gpiod_export(struct gpio_desc *desc, bool direction_may_change)
                goto fail_unlock;
        }
 
-       if (!desc->chip->direction_input || !desc->chip->direction_output)
-               direction_may_change = false;
+       if (desc->chip->direction_input && desc->chip->direction_output &&
+                       direction_may_change) {
+               set_bit(FLAG_SYSFS_DIR, &desc->flags);
+       }
+
        spin_unlock_irqrestore(&gpio_lock, flags);
 
        offset = gpio_chip_hwgpio(desc);
        if (desc->chip->names && desc->chip->names[offset])
                ioname = desc->chip->names[offset];
 
-       dev = device_create(&gpio_class, desc->chip->dev, MKDEV(0, 0),
-                           desc, ioname ? ioname : "gpio%u",
-                           desc_to_gpio(desc));
+       dev = device_create_with_groups(&gpio_class, desc->chip->dev,
+                                       MKDEV(0, 0), desc, gpio_groups,
+                                       ioname ? ioname : "gpio%u",
+                                       desc_to_gpio(desc));
        if (IS_ERR(dev)) {
                status = PTR_ERR(dev);
                goto fail_unlock;
        }
 
-       status = sysfs_create_group(&dev->kobj, &gpio_attr_group);
-       if (status)
-               goto fail_unregister_device;
-
-       if (direction_may_change) {
-               status = device_create_file(dev, &dev_attr_direction);
-               if (status)
-                       goto fail_unregister_device;
-       }
-
-       if (gpiod_to_irq(desc) >= 0 && (direction_may_change ||
-                                      !test_bit(FLAG_IS_OUT, &desc->flags))) {
-               status = device_create_file(dev, &dev_attr_edge);
-               if (status)
-                       goto fail_unregister_device;
-       }
-
        set_bit(FLAG_EXPORT, &desc->flags);
        mutex_unlock(&sysfs_lock);
        return 0;
 
-fail_unregister_device:
-       device_unregister(dev);
 fail_unlock:
        mutex_unlock(&sysfs_lock);
        gpiod_dbg(desc, "%s: status %d\n", __func__, status);
@@ -718,6 +729,7 @@ void gpiod_unexport(struct gpio_desc *desc)
                dev = class_find_device(&gpio_class, NULL, desc, match_export);
                if (dev) {
                        gpio_setup_irq(desc, dev, 0);
+                       clear_bit(FLAG_SYSFS_DIR, &desc->flags);
                        clear_bit(FLAG_EXPORT, &desc->flags);
                } else
                        status = -ENODEV;
@@ -750,13 +762,13 @@ int gpiochip_export(struct gpio_chip *chip)
 
        /* use chip->base for the ID; it's already known to be unique */
        mutex_lock(&sysfs_lock);
-       dev = device_create(&gpio_class, chip->dev, MKDEV(0, 0), chip,
-                               "gpiochip%d", chip->base);
-       if (!IS_ERR(dev)) {
-               status = sysfs_create_group(&dev->kobj,
-                               &gpiochip_attr_group);
-       } else
+       dev = device_create_with_groups(&gpio_class, chip->dev, MKDEV(0, 0),
+                                       chip, gpiochip_groups,
+                                       "gpiochip%d", chip->base);
+       if (IS_ERR(dev))
                status = PTR_ERR(dev);
+       else
+               status = 0;
        chip->exported = (status == 0);
        mutex_unlock(&sysfs_lock);
 
index 487afe6f22fcd6872b16995cffcb8179c374a276..568aa2b6bdb019e9285372d731d8a9e9bcbed1f7 100644 (file)
@@ -248,29 +248,30 @@ int gpiochip_add(struct gpio_chip *chip)
                base = gpiochip_find_base(chip->ngpio);
                if (base < 0) {
                        status = base;
-                       goto unlock;
+                       spin_unlock_irqrestore(&gpio_lock, flags);
+                       goto err_free_descs;
                }
                chip->base = base;
        }
 
        status = gpiochip_add_to_list(chip);
+       if (status) {
+               spin_unlock_irqrestore(&gpio_lock, flags);
+               goto err_free_descs;
+       }
 
-       if (status == 0) {
-               for (id = 0; id < chip->ngpio; id++) {
-                       struct gpio_desc *desc = &descs[id];
-                       desc->chip = chip;
-
-                       /* REVISIT:  most hardware initializes GPIOs as
-                        * inputs (often with pullups enabled) so power
-                        * usage is minimized.  Linux code should set the
-                        * gpio direction first thing; but until it does,
-                        * and in case chip->get_direction is not set,
-                        * we may expose the wrong direction in sysfs.
-                        */
-                       desc->flags = !chip->direction_input
-                               ? (1 << FLAG_IS_OUT)
-                               : 0;
-               }
+       for (id = 0; id < chip->ngpio; id++) {
+               struct gpio_desc *desc = &descs[id];
+
+               desc->chip = chip;
+
+               /* REVISIT: most hardware initializes GPIOs as inputs (often
+                * with pullups enabled) so power usage is minimized. Linux
+                * code should set the gpio direction first thing; but until
+                * it does, and in case chip->get_direction is not set, we may
+                * expose the wrong direction in sysfs.
+                */
+               desc->flags = !chip->direction_input ? (1 << FLAG_IS_OUT) : 0;
        }
 
        chip->desc = descs;
@@ -284,12 +285,9 @@ int gpiochip_add(struct gpio_chip *chip)
        of_gpiochip_add(chip);
        acpi_gpiochip_add(chip);
 
-       if (status)
-               goto fail;
-
        status = gpiochip_export(chip);
        if (status)
-               goto fail;
+               goto err_remove_chip;
 
        pr_debug("%s: registered GPIOs %d to %d on device: %s\n", __func__,
                chip->base, chip->base + chip->ngpio - 1,
@@ -297,11 +295,15 @@ int gpiochip_add(struct gpio_chip *chip)
 
        return 0;
 
-unlock:
+err_remove_chip:
+       acpi_gpiochip_remove(chip);
+       of_gpiochip_remove(chip);
+       spin_lock_irqsave(&gpio_lock, flags);
+       list_del(&chip->list);
        spin_unlock_irqrestore(&gpio_lock, flags);
-fail:
-       kfree(descs);
        chip->desc = NULL;
+err_free_descs:
+       kfree(descs);
 
        /* failures here can mean systems won't boot... */
        pr_err("%s: GPIOs %d..%d (%s) failed to register\n", __func__,
@@ -325,14 +327,15 @@ void gpiochip_remove(struct gpio_chip *chip)
        unsigned long   flags;
        unsigned        id;
 
-       acpi_gpiochip_remove(chip);
-
-       spin_lock_irqsave(&gpio_lock, flags);
+       gpiochip_unexport(chip);
 
        gpiochip_irqchip_remove(chip);
+
+       acpi_gpiochip_remove(chip);
        gpiochip_remove_pin_ranges(chip);
        of_gpiochip_remove(chip);
 
+       spin_lock_irqsave(&gpio_lock, flags);
        for (id = 0; id < chip->ngpio; id++) {
                if (test_bit(FLAG_REQUESTED, &chip->desc[id].flags))
                        dev_crit(chip->dev, "REMOVING GPIOCHIP WITH GPIOS STILL REQUESTED\n");
@@ -342,7 +345,6 @@ void gpiochip_remove(struct gpio_chip *chip)
 
        list_del(&chip->list);
        spin_unlock_irqrestore(&gpio_lock, flags);
-       gpiochip_unexport(chip);
 
        kfree(chip->desc);
        chip->desc = NULL;
index e3a52113a5410531472522ca2e1781e73bd91306..550a5eafbd38ce6f1ed5a1d9a899649df75b2fa0 100644 (file)
@@ -77,6 +77,7 @@ struct gpio_desc {
 #define FLAG_OPEN_DRAIN        7       /* Gpio is open drain type */
 #define FLAG_OPEN_SOURCE 8     /* Gpio is open source type */
 #define FLAG_USED_AS_IRQ 9     /* GPIO is connected to an IRQ */
+#define FLAG_SYSFS_DIR 10      /* show sysfs direction attribute */
 
 #define ID_SHIFT       16      /* add new flags before this one */
 
index c3413b6adb17caec6ac0f273bfa80ef8bacca960..ea283894a12a1f43383de404bb67c113f403c15c 100644 (file)
@@ -183,6 +183,8 @@ source "drivers/gpu/drm/cirrus/Kconfig"
 
 source "drivers/gpu/drm/armada/Kconfig"
 
+source "drivers/gpu/drm/atmel-hlcdc/Kconfig"
+
 source "drivers/gpu/drm/rcar-du/Kconfig"
 
 source "drivers/gpu/drm/shmobile/Kconfig"
index e620807418ea7559eddc9d5a994a0c5e1f829a9c..cf0eed8208b53ef352a360994a623f557a4bc8c9 100644 (file)
@@ -55,6 +55,7 @@ obj-$(CONFIG_DRM_GMA500) += gma500/
 obj-$(CONFIG_DRM_UDL) += udl/
 obj-$(CONFIG_DRM_AST) += ast/
 obj-$(CONFIG_DRM_ARMADA) += armada/
+obj-$(CONFIG_DRM_ATMEL_HLCDC)  += atmel-hlcdc/
 obj-$(CONFIG_DRM_RCAR_DU) += rcar-du/
 obj-$(CONFIG_DRM_SHMOBILE) +=shmobile/
 obj-$(CONFIG_DRM_OMAP) += omapdrm/
index be6246de5091d0a589c25de25d147d8ed786af39..0f4960148126d96adb7cbdf9432da533428c4080 100644 (file)
@@ -7,8 +7,10 @@ ccflags-y := -Iinclude/drm -Idrivers/gpu/drm/amd/include/
 amdkfd-y       := kfd_module.o kfd_device.o kfd_chardev.o kfd_topology.o \
                kfd_pasid.o kfd_doorbell.o kfd_flat_memory.o \
                kfd_process.o kfd_queue.o kfd_mqd_manager.o \
-               kfd_kernel_queue.o kfd_packet_manager.o \
+               kfd_mqd_manager_cik.o kfd_mqd_manager_vi.o \
+               kfd_kernel_queue.o kfd_kernel_queue_cik.o \
+               kfd_kernel_queue_vi.o kfd_packet_manager.o \
                kfd_process_queue_manager.o kfd_device_queue_manager.o \
-               kfd_interrupt.o
+               kfd_device_queue_manager_cik.o kfd_device_queue_manager_vi.o \
 
 obj-$(CONFIG_HSA_AMD)  += amdkfd.o
index 607fc5ceadbeffcb0e5682c4bdb4a2b7d6a2d078..01ff332fabd4b81fdd84b2cb0f547870978d362b 100644 (file)
 #define        IB_ATC_EN                                       (1U << 23)
 #define        DEFAULT_MIN_IB_AVAIL_SIZE                       (3U << 20)
 
+#define        AQL_ENABLE                                      1
+
 #define CP_HQD_DEQUEUE_REQUEST                         0xC974
 #define        DEQUEUE_REQUEST_DRAIN                           1
 #define DEQUEUE_REQUEST_RESET                          2
 #define        MQD_VMID_MASK                                   (0xf << 0)
 #define        MQD_CONTROL_PRIV_STATE_EN                       (1U << 8)
 
+#define        SDMA_RB_VMID(x)                                 (x << 24)
+#define        SDMA_RB_ENABLE                                  (1 << 0)
+#define        SDMA_RB_SIZE(x)                                 ((x) << 1) /* log2 */
+#define        SDMA_RPTR_WRITEBACK_ENABLE                      (1 << 12)
+#define        SDMA_RPTR_WRITEBACK_TIMER(x)                    ((x) << 16) /* log2 */
+#define        SDMA_OFFSET(x)                                  (x << 0)
+#define        SDMA_DB_ENABLE                                  (1 << 28)
+#define        SDMA_ATC                                        (1 << 0)
+#define        SDMA_VA_PTR32                                   (1 << 4)
+#define        SDMA_VA_SHARED_BASE(x)                          (x << 8)
+
 #define GRBM_GFX_INDEX                                 0x30800
 #define        INSTANCE_INDEX(x)                               ((x) << 0)
 #define        SH_INDEX(x)                                     ((x) << 8)
index fcfdf23e1913ed01663b46bebfda5eec8bc4079d..732087dcac914bf88bf5b6e9e244ac92922ba568 100644 (file)
@@ -141,6 +141,8 @@ static int kfd_ioctl_get_version(struct file *filep, struct kfd_process *p,
 static int set_queue_properties_from_user(struct queue_properties *q_properties,
                                struct kfd_ioctl_create_queue_args *args)
 {
+       void *tmp;
+
        if (args->queue_percentage > KFD_MAX_QUEUE_PERCENTAGE) {
                pr_err("kfd: queue percentage must be between 0 to KFD_MAX_QUEUE_PERCENTAGE\n");
                return -EINVAL;
@@ -178,6 +180,20 @@ static int set_queue_properties_from_user(struct queue_properties *q_properties,
                return -EFAULT;
        }
 
+       tmp = (void *)(uintptr_t)args->eop_buffer_address;
+       if (tmp != NULL &&
+               !access_ok(VERIFY_WRITE, tmp, sizeof(uint32_t))) {
+               pr_debug("kfd: can't access eop buffer");
+               return -EFAULT;
+       }
+
+       tmp = (void *)(uintptr_t)args->ctx_save_restore_address;
+       if (tmp != NULL &&
+               !access_ok(VERIFY_WRITE, tmp, sizeof(uint32_t))) {
+               pr_debug("kfd: can't access ctx save restore buffer");
+               return -EFAULT;
+       }
+
        q_properties->is_interop = false;
        q_properties->queue_percent = args->queue_percentage;
        q_properties->priority = args->queue_priority;
@@ -185,9 +201,16 @@ static int set_queue_properties_from_user(struct queue_properties *q_properties,
        q_properties->queue_size = args->ring_size;
        q_properties->read_ptr = (uint32_t *) args->read_pointer_address;
        q_properties->write_ptr = (uint32_t *) args->write_pointer_address;
+       q_properties->eop_ring_buffer_address = args->eop_buffer_address;
+       q_properties->eop_ring_buffer_size = args->eop_buffer_size;
+       q_properties->ctx_save_restore_area_address =
+                       args->ctx_save_restore_address;
+       q_properties->ctx_save_restore_area_size = args->ctx_save_restore_size;
        if (args->queue_type == KFD_IOC_QUEUE_TYPE_COMPUTE ||
                args->queue_type == KFD_IOC_QUEUE_TYPE_COMPUTE_AQL)
                q_properties->type = KFD_QUEUE_TYPE_COMPUTE;
+       else if (args->queue_type == KFD_IOC_QUEUE_TYPE_SDMA)
+               q_properties->type = KFD_QUEUE_TYPE_SDMA;
        else
                return -ENOTSUPP;
 
@@ -214,6 +237,11 @@ static int set_queue_properties_from_user(struct queue_properties *q_properties,
 
        pr_debug("Queue Format (%d)\n", q_properties->format);
 
+       pr_debug("Queue EOP (0x%llX)\n", q_properties->eop_ring_buffer_address);
+
+       pr_debug("Queue CTX save arex (0x%llX)\n",
+                       q_properties->ctx_save_restore_area_address);
+
        return 0;
 }
 
@@ -235,9 +263,12 @@ static int kfd_ioctl_create_queue(struct file *filep, struct kfd_process *p,
        if (err)
                return err;
 
+       pr_debug("kfd: looking for gpu id 0x%x\n", args->gpu_id);
        dev = kfd_device_by_id(args->gpu_id);
-       if (dev == NULL)
+       if (dev == NULL) {
+               pr_debug("kfd: gpu id 0x%x was not found\n", args->gpu_id);
                return -EINVAL;
+       }
 
        mutex_lock(&p->mutex);
 
@@ -251,8 +282,8 @@ static int kfd_ioctl_create_queue(struct file *filep, struct kfd_process *p,
                        p->pasid,
                        dev->id);
 
-       err = pqm_create_queue(&p->pqm, dev, filep, &q_properties, 0,
-                               KFD_QUEUE_TYPE_COMPUTE, &queue_id);
+       err = pqm_create_queue(&p->pqm, dev, filep, &q_properties,
+                               0, q_properties.type, &queue_id);
        if (err != 0)
                goto err_create_queue;
 
@@ -385,7 +416,7 @@ static int kfd_ioctl_set_memory_policy(struct file *filep,
                (args->alternate_policy == KFD_IOC_CACHE_POLICY_COHERENT)
                   ? cache_policy_coherent : cache_policy_noncoherent;
 
-       if (!dev->dqm->set_cache_memory_policy(dev->dqm,
+       if (!dev->dqm->ops.set_cache_memory_policy(dev->dqm,
                                &pdd->qpd,
                                default_policy,
                                alternate_policy,
index 43884ebd4303fedd47b56431737a0f726852c552..1ba8332419faee78ce45f7179b379bd5a285ffb1 100644 (file)
 #include <linux/slab.h>
 #include "kfd_priv.h"
 #include "kfd_device_queue_manager.h"
+#include "kfd_pm4_headers.h"
 
 #define MQD_SIZE_ALIGNED 768
 
 static const struct kfd_device_info kaveri_device_info = {
+       .asic_family = CHIP_KAVERI,
        .max_pasid_bits = 16,
        .ih_ring_entry_size = 4 * sizeof(uint32_t),
        .mqd_size_aligned = MQD_SIZE_ALIGNED
 };
 
+static const struct kfd_device_info carrizo_device_info = {
+       .asic_family = CHIP_CARRIZO,
+       .max_pasid_bits = 16,
+       .ih_ring_entry_size = 4 * sizeof(uint32_t),
+       .num_of_watch_points = 4,
+       .mqd_size_aligned = MQD_SIZE_ALIGNED
+};
+
 struct kfd_deviceid {
        unsigned short did;
        const struct kfd_device_info *device_info;
@@ -63,9 +73,13 @@ static const struct kfd_deviceid supported_devices[] = {
        { 0x1318, &kaveri_device_info },        /* Kaveri */
        { 0x131B, &kaveri_device_info },        /* Kaveri */
        { 0x131C, &kaveri_device_info },        /* Kaveri */
-       { 0x131D, &kaveri_device_info },        /* Kaveri */
+       { 0x131D, &kaveri_device_info }         /* Kaveri */
 };
 
+static int kfd_gtt_sa_init(struct kfd_dev *kfd, unsigned int buf_size,
+                               unsigned int chunk_size);
+static void kfd_gtt_sa_fini(struct kfd_dev *kfd);
+
 static const struct kfd_device_info *lookup_device_info(unsigned short did)
 {
        size_t i;
@@ -173,16 +187,39 @@ bool kgd2kfd_device_init(struct kfd_dev *kfd,
                max_num_of_queues_per_process *
                kfd->device_info->mqd_size_aligned;
 
-       /* add another 512KB for all other allocations on gart */
+       /*
+        * calculate max size of runlist packet.
+        * There can be only 2 packets at once
+        */
+       size += (max_num_of_processes * sizeof(struct pm4_map_process) +
+               max_num_of_processes * max_num_of_queues_per_process *
+               sizeof(struct pm4_map_queues) + sizeof(struct pm4_runlist)) * 2;
+
+       /* Add size of HIQ & DIQ */
+       size += KFD_KERNEL_QUEUE_SIZE * 2;
+
+       /* add another 512KB for all other allocations on gart (HPD, fences) */
        size += 512 * 1024;
 
-       if (kfd2kgd->init_sa_manager(kfd->kgd, size)) {
+       if (kfd2kgd->init_gtt_mem_allocation(kfd->kgd, size, &kfd->gtt_mem,
+                       &kfd->gtt_start_gpu_addr, &kfd->gtt_start_cpu_ptr)) {
                dev_err(kfd_device,
-                       "Error initializing sa manager for device (%x:%x)\n",
-                       kfd->pdev->vendor, kfd->pdev->device);
+                       "Could not allocate %d bytes for device (%x:%x)\n",
+                       size, kfd->pdev->vendor, kfd->pdev->device);
                goto out;
        }
 
+       dev_info(kfd_device,
+               "Allocated %d bytes on gart for device(%x:%x)\n",
+               size, kfd->pdev->vendor, kfd->pdev->device);
+
+       /* Initialize GTT sa with 512 byte chunk size */
+       if (kfd_gtt_sa_init(kfd, size, 512) != 0) {
+               dev_err(kfd_device,
+                       "Error initializing gtt sub-allocator\n");
+               goto kfd_gtt_sa_init_error;
+       }
+
        kfd_doorbell_init(kfd);
 
        if (kfd_topology_add_device(kfd) != 0) {
@@ -192,13 +229,6 @@ bool kgd2kfd_device_init(struct kfd_dev *kfd,
                goto kfd_topology_add_device_error;
        }
 
-       if (kfd_interrupt_init(kfd)) {
-               dev_err(kfd_device,
-                       "Error initializing interrupts for device (%x:%x)\n",
-                       kfd->pdev->vendor, kfd->pdev->device);
-               goto kfd_interrupt_error;
-       }
-
        if (!device_iommu_pasid_init(kfd)) {
                dev_err(kfd_device,
                        "Error initializing iommuv2 for device (%x:%x)\n",
@@ -216,7 +246,7 @@ bool kgd2kfd_device_init(struct kfd_dev *kfd,
                goto device_queue_manager_error;
        }
 
-       if (kfd->dqm->start(kfd->dqm) != 0) {
+       if (kfd->dqm->ops.start(kfd->dqm) != 0) {
                dev_err(kfd_device,
                        "Error starting queuen manager for device (%x:%x)\n",
                        kfd->pdev->vendor, kfd->pdev->device);
@@ -237,11 +267,11 @@ dqm_start_error:
 device_queue_manager_error:
        amd_iommu_free_device(kfd->pdev);
 device_iommu_pasid_error:
-       kfd_interrupt_exit(kfd);
-kfd_interrupt_error:
        kfd_topology_remove_device(kfd);
 kfd_topology_add_device_error:
-       kfd2kgd->fini_sa_manager(kfd->kgd);
+       kfd_gtt_sa_fini(kfd);
+kfd_gtt_sa_init_error:
+       kfd2kgd->free_gtt_mem(kfd->kgd, kfd->gtt_mem);
        dev_err(kfd_device,
                "device (%x:%x) NOT added due to errors\n",
                kfd->pdev->vendor, kfd->pdev->device);
@@ -254,8 +284,9 @@ void kgd2kfd_device_exit(struct kfd_dev *kfd)
        if (kfd->init_complete) {
                device_queue_manager_uninit(kfd->dqm);
                amd_iommu_free_device(kfd->pdev);
-               kfd_interrupt_exit(kfd);
                kfd_topology_remove_device(kfd);
+               kfd_gtt_sa_fini(kfd);
+               kfd2kgd->free_gtt_mem(kfd->kgd, kfd->gtt_mem);
        }
 
        kfree(kfd);
@@ -266,7 +297,7 @@ void kgd2kfd_suspend(struct kfd_dev *kfd)
        BUG_ON(kfd == NULL);
 
        if (kfd->init_complete) {
-               kfd->dqm->stop(kfd->dqm);
+               kfd->dqm->ops.stop(kfd->dqm);
                amd_iommu_set_invalidate_ctx_cb(kfd->pdev, NULL);
                amd_iommu_free_device(kfd->pdev);
        }
@@ -287,7 +318,7 @@ int kgd2kfd_resume(struct kfd_dev *kfd)
                        return -ENXIO;
                amd_iommu_set_invalidate_ctx_cb(kfd->pdev,
                                                iommu_pasid_shutdown_callback);
-               kfd->dqm->start(kfd->dqm);
+               kfd->dqm->ops.start(kfd->dqm);
        }
 
        return 0;
@@ -296,13 +327,190 @@ int kgd2kfd_resume(struct kfd_dev *kfd)
 /* This is called directly from KGD at ISR. */
 void kgd2kfd_interrupt(struct kfd_dev *kfd, const void *ih_ring_entry)
 {
-       if (kfd->init_complete) {
-               spin_lock(&kfd->interrupt_lock);
+       /* Process interrupts / schedule work as necessary */
+}
+
+static int kfd_gtt_sa_init(struct kfd_dev *kfd, unsigned int buf_size,
+                               unsigned int chunk_size)
+{
+       unsigned int num_of_bits;
+
+       BUG_ON(!kfd);
+       BUG_ON(!kfd->gtt_mem);
+       BUG_ON(buf_size < chunk_size);
+       BUG_ON(buf_size == 0);
+       BUG_ON(chunk_size == 0);
+
+       kfd->gtt_sa_chunk_size = chunk_size;
+       kfd->gtt_sa_num_of_chunks = buf_size / chunk_size;
+
+       num_of_bits = kfd->gtt_sa_num_of_chunks / BITS_PER_BYTE;
+       BUG_ON(num_of_bits == 0);
+
+       kfd->gtt_sa_bitmap = kzalloc(num_of_bits, GFP_KERNEL);
+
+       if (!kfd->gtt_sa_bitmap)
+               return -ENOMEM;
+
+       pr_debug("kfd: gtt_sa_num_of_chunks = %d, gtt_sa_bitmap = %p\n",
+                       kfd->gtt_sa_num_of_chunks, kfd->gtt_sa_bitmap);
+
+       mutex_init(&kfd->gtt_sa_lock);
 
-               if (kfd->interrupts_active
-                   && enqueue_ih_ring_entry(kfd, ih_ring_entry))
-                       schedule_work(&kfd->interrupt_work);
+       return 0;
+
+}
+
+static void kfd_gtt_sa_fini(struct kfd_dev *kfd)
+{
+       mutex_destroy(&kfd->gtt_sa_lock);
+       kfree(kfd->gtt_sa_bitmap);
+}
+
+static inline uint64_t kfd_gtt_sa_calc_gpu_addr(uint64_t start_addr,
+                                               unsigned int bit_num,
+                                               unsigned int chunk_size)
+{
+       return start_addr + bit_num * chunk_size;
+}
 
-               spin_unlock(&kfd->interrupt_lock);
+static inline uint32_t *kfd_gtt_sa_calc_cpu_addr(void *start_addr,
+                                               unsigned int bit_num,
+                                               unsigned int chunk_size)
+{
+       return (uint32_t *) ((uint64_t) start_addr + bit_num * chunk_size);
+}
+
+int kfd_gtt_sa_allocate(struct kfd_dev *kfd, unsigned int size,
+                       struct kfd_mem_obj **mem_obj)
+{
+       unsigned int found, start_search, cur_size;
+
+       BUG_ON(!kfd);
+
+       if (size == 0)
+               return -EINVAL;
+
+       if (size > kfd->gtt_sa_num_of_chunks * kfd->gtt_sa_chunk_size)
+               return -ENOMEM;
+
+       *mem_obj = kmalloc(sizeof(struct kfd_mem_obj), GFP_KERNEL);
+       if ((*mem_obj) == NULL)
+               return -ENOMEM;
+
+       pr_debug("kfd: allocated mem_obj = %p for size = %d\n", *mem_obj, size);
+
+       start_search = 0;
+
+       mutex_lock(&kfd->gtt_sa_lock);
+
+kfd_gtt_restart_search:
+       /* Find the first chunk that is free */
+       found = find_next_zero_bit(kfd->gtt_sa_bitmap,
+                                       kfd->gtt_sa_num_of_chunks,
+                                       start_search);
+
+       pr_debug("kfd: found = %d\n", found);
+
+       /* If there wasn't any free chunk, bail out */
+       if (found == kfd->gtt_sa_num_of_chunks)
+               goto kfd_gtt_no_free_chunk;
+
+       /* Update fields of mem_obj */
+       (*mem_obj)->range_start = found;
+       (*mem_obj)->range_end = found;
+       (*mem_obj)->gpu_addr = kfd_gtt_sa_calc_gpu_addr(
+                                       kfd->gtt_start_gpu_addr,
+                                       found,
+                                       kfd->gtt_sa_chunk_size);
+       (*mem_obj)->cpu_ptr = kfd_gtt_sa_calc_cpu_addr(
+                                       kfd->gtt_start_cpu_ptr,
+                                       found,
+                                       kfd->gtt_sa_chunk_size);
+
+       pr_debug("kfd: gpu_addr = %p, cpu_addr = %p\n",
+                       (uint64_t *) (*mem_obj)->gpu_addr, (*mem_obj)->cpu_ptr);
+
+       /* If we need only one chunk, mark it as allocated and get out */
+       if (size <= kfd->gtt_sa_chunk_size) {
+               pr_debug("kfd: single bit\n");
+               set_bit(found, kfd->gtt_sa_bitmap);
+               goto kfd_gtt_out;
        }
+
+       /* Otherwise, try to see if we have enough contiguous chunks */
+       cur_size = size - kfd->gtt_sa_chunk_size;
+       do {
+               (*mem_obj)->range_end =
+                       find_next_zero_bit(kfd->gtt_sa_bitmap,
+                                       kfd->gtt_sa_num_of_chunks, ++found);
+               /*
+                * If next free chunk is not contiguous than we need to
+                * restart our search from the last free chunk we found (which
+                * wasn't contiguous to the previous ones
+                */
+               if ((*mem_obj)->range_end != found) {
+                       start_search = found;
+                       goto kfd_gtt_restart_search;
+               }
+
+               /*
+                * If we reached end of buffer, bail out with error
+                */
+               if (found == kfd->gtt_sa_num_of_chunks)
+                       goto kfd_gtt_no_free_chunk;
+
+               /* Check if we don't need another chunk */
+               if (cur_size <= kfd->gtt_sa_chunk_size)
+                       cur_size = 0;
+               else
+                       cur_size -= kfd->gtt_sa_chunk_size;
+
+       } while (cur_size > 0);
+
+       pr_debug("kfd: range_start = %d, range_end = %d\n",
+               (*mem_obj)->range_start, (*mem_obj)->range_end);
+
+       /* Mark the chunks as allocated */
+       for (found = (*mem_obj)->range_start;
+               found <= (*mem_obj)->range_end;
+               found++)
+               set_bit(found, kfd->gtt_sa_bitmap);
+
+kfd_gtt_out:
+       mutex_unlock(&kfd->gtt_sa_lock);
+       return 0;
+
+kfd_gtt_no_free_chunk:
+       pr_debug("kfd: allocation failed with mem_obj = %p\n", mem_obj);
+       mutex_unlock(&kfd->gtt_sa_lock);
+       kfree(mem_obj);
+       return -ENOMEM;
+}
+
+int kfd_gtt_sa_free(struct kfd_dev *kfd, struct kfd_mem_obj *mem_obj)
+{
+       unsigned int bit;
+
+       BUG_ON(!kfd);
+
+       /* Act like kfree when trying to free a NULL object */
+       if (!mem_obj)
+               return 0;
+
+       pr_debug("kfd: free mem_obj = %p, range_start = %d, range_end = %d\n",
+                       mem_obj, mem_obj->range_start, mem_obj->range_end);
+
+       mutex_lock(&kfd->gtt_sa_lock);
+
+       /* Mark the chunks as free */
+       for (bit = mem_obj->range_start;
+               bit <= mem_obj->range_end;
+               bit++)
+               clear_bit(bit, kfd->gtt_sa_bitmap);
+
+       mutex_unlock(&kfd->gtt_sa_lock);
+
+       kfree(mem_obj);
+       return 0;
 }
index 9c8961d22360722a5382de9dde19b35d9b3d27ad..a5c69e96ba6f09c1b48824b317563a33d39ec53d 100644 (file)
 #include <linux/types.h>
 #include <linux/printk.h>
 #include <linux/bitops.h>
+#include <linux/sched.h>
 #include "kfd_priv.h"
 #include "kfd_device_queue_manager.h"
 #include "kfd_mqd_manager.h"
 #include "cik_regs.h"
 #include "kfd_kernel_queue.h"
-#include "../../radeon/cik_reg.h"
 
 /* Size of the per-pipe EOP queue */
 #define CIK_HPD_EOP_BYTES_LOG2 11
 #define CIK_HPD_EOP_BYTES (1U << CIK_HPD_EOP_BYTES_LOG2)
 
-static bool is_mem_initialized;
-
-static int init_memory(struct device_queue_manager *dqm);
 static int set_pasid_vmid_mapping(struct device_queue_manager *dqm,
                                        unsigned int pasid, unsigned int vmid);
 
 static int create_compute_queue_nocpsch(struct device_queue_manager *dqm,
                                        struct queue *q,
                                        struct qcm_process_device *qpd);
+
 static int execute_queues_cpsch(struct device_queue_manager *dqm, bool lock);
 static int destroy_queues_cpsch(struct device_queue_manager *dqm, bool lock);
 
+static int create_sdma_queue_nocpsch(struct device_queue_manager *dqm,
+                                       struct queue *q,
+                                       struct qcm_process_device *qpd);
+
+static void deallocate_sdma_queue(struct device_queue_manager *dqm,
+                               unsigned int sdma_queue_id);
+
+static inline
+enum KFD_MQD_TYPE get_mqd_type_from_queue_type(enum kfd_queue_type type)
+{
+       if (type == KFD_QUEUE_TYPE_SDMA)
+               return KFD_MQD_TYPE_SDMA;
+       return KFD_MQD_TYPE_CP;
+}
 
-static inline unsigned int get_pipes_num(struct device_queue_manager *dqm)
+inline unsigned int get_pipes_num(struct device_queue_manager *dqm)
 {
        BUG_ON(!dqm || !dqm->dev);
        return dqm->dev->shared_resources.compute_pipe_count;
@@ -67,7 +79,7 @@ static inline unsigned int get_pipes_num_cpsch(void)
        return PIPE_PER_ME_CP_SCHEDULING;
 }
 
-static inline unsigned int
+inline unsigned int
 get_sh_mem_bases_nybble_64(struct kfd_process_device *pdd)
 {
        uint32_t nybble;
@@ -75,10 +87,9 @@ get_sh_mem_bases_nybble_64(struct kfd_process_device *pdd)
        nybble = (pdd->lds_base >> 60) & 0x0E;
 
        return nybble;
-
 }
 
-static inline unsigned int get_sh_mem_bases_32(struct kfd_process_device *pdd)
+inline unsigned int get_sh_mem_bases_32(struct kfd_process_device *pdd)
 {
        unsigned int shared_base;
 
@@ -87,41 +98,7 @@ static inline unsigned int get_sh_mem_bases_32(struct kfd_process_device *pdd)
        return shared_base;
 }
 
-static uint32_t compute_sh_mem_bases_64bit(unsigned int top_address_nybble);
-static void init_process_memory(struct device_queue_manager *dqm,
-                               struct qcm_process_device *qpd)
-{
-       struct kfd_process_device *pdd;
-       unsigned int temp;
-
-       BUG_ON(!dqm || !qpd);
-
-       pdd = qpd_to_pdd(qpd);
-
-       /* check if sh_mem_config register already configured */
-       if (qpd->sh_mem_config == 0) {
-               qpd->sh_mem_config =
-                       ALIGNMENT_MODE(SH_MEM_ALIGNMENT_MODE_UNALIGNED) |
-                       DEFAULT_MTYPE(MTYPE_NONCACHED) |
-                       APE1_MTYPE(MTYPE_NONCACHED);
-               qpd->sh_mem_ape1_limit = 0;
-               qpd->sh_mem_ape1_base = 0;
-       }
-
-       if (qpd->pqm->process->is_32bit_user_mode) {
-               temp = get_sh_mem_bases_32(pdd);
-               qpd->sh_mem_bases = SHARED_BASE(temp);
-               qpd->sh_mem_config |= PTR32;
-       } else {
-               temp = get_sh_mem_bases_nybble_64(pdd);
-               qpd->sh_mem_bases = compute_sh_mem_bases_64bit(temp);
-       }
-
-       pr_debug("kfd: is32bit process: %d sh_mem_bases nybble: 0x%X and register 0x%X\n",
-               qpd->pqm->process->is_32bit_user_mode, temp, qpd->sh_mem_bases);
-}
-
-static void program_sh_mem_settings(struct device_queue_manager *dqm,
+void program_sh_mem_settings(struct device_queue_manager *dqm,
                                        struct qcm_process_device *qpd)
 {
        return kfd2kgd->program_sh_mem_settings(dqm->dev->kgd, qpd->vmid,
@@ -193,7 +170,10 @@ static int create_queue_nocpsch(struct device_queue_manager *dqm,
        *allocated_vmid = qpd->vmid;
        q->properties.vmid = qpd->vmid;
 
-       retval = create_compute_queue_nocpsch(dqm, q, qpd);
+       if (q->properties.type == KFD_QUEUE_TYPE_COMPUTE)
+               retval = create_compute_queue_nocpsch(dqm, q, qpd);
+       if (q->properties.type == KFD_QUEUE_TYPE_SDMA)
+               retval = create_sdma_queue_nocpsch(dqm, q, qpd);
 
        if (retval != 0) {
                if (list_empty(&qpd->queues_list)) {
@@ -206,7 +186,8 @@ static int create_queue_nocpsch(struct device_queue_manager *dqm,
 
        list_add(&q->list, &qpd->queues_list);
        dqm->queue_count++;
-
+       if (q->properties.type == KFD_QUEUE_TYPE_SDMA)
+               dqm->sdma_queue_count++;
        mutex_unlock(&dqm->lock);
        return 0;
 }
@@ -214,12 +195,12 @@ static int create_queue_nocpsch(struct device_queue_manager *dqm,
 static int allocate_hqd(struct device_queue_manager *dqm, struct queue *q)
 {
        bool set;
-       int pipe, bit;
+       int pipe, bit, i;
 
        set = false;
 
-       for (pipe = dqm->next_pipe_to_allocate; pipe < get_pipes_num(dqm);
-                       pipe = (pipe + 1) % get_pipes_num(dqm)) {
+       for (pipe = dqm->next_pipe_to_allocate, i = 0; i < get_pipes_num(dqm);
+                       pipe = ((pipe + 1) % get_pipes_num(dqm)), ++i) {
                if (dqm->allocated_queues[pipe] != 0) {
                        bit = find_first_bit(
                                (unsigned long *)&dqm->allocated_queues[pipe],
@@ -260,7 +241,7 @@ static int create_compute_queue_nocpsch(struct device_queue_manager *dqm,
 
        BUG_ON(!dqm || !q || !qpd);
 
-       mqd = dqm->get_mqd_manager(dqm, KFD_MQD_TYPE_CIK_COMPUTE);
+       mqd = dqm->ops.get_mqd_manager(dqm, KFD_MQD_TYPE_COMPUTE);
        if (mqd == NULL)
                return -ENOMEM;
 
@@ -280,7 +261,7 @@ static int create_compute_queue_nocpsch(struct device_queue_manager *dqm,
                        q->queue);
 
        retval = mqd->load_mqd(mqd, q->mqd, q->pipe,
-                       q->queue, q->properties.write_ptr);
+                       q->queue, (uint32_t __user *) q->properties.write_ptr);
        if (retval != 0) {
                deallocate_hqd(dqm, q);
                mqd->uninit_mqd(mqd, q->mqd, q->mqd_mem_obj);
@@ -304,22 +285,32 @@ static int destroy_queue_nocpsch(struct device_queue_manager *dqm,
        pr_debug("kfd: In Func %s\n", __func__);
 
        mutex_lock(&dqm->lock);
-       mqd = dqm->get_mqd_manager(dqm, KFD_MQD_TYPE_CIK_COMPUTE);
-       if (mqd == NULL) {
-               retval = -ENOMEM;
-               goto out;
+
+       if (q->properties.type == KFD_QUEUE_TYPE_COMPUTE) {
+               mqd = dqm->ops.get_mqd_manager(dqm, KFD_MQD_TYPE_COMPUTE);
+               if (mqd == NULL) {
+                       retval = -ENOMEM;
+                       goto out;
+               }
+               deallocate_hqd(dqm, q);
+       } else if (q->properties.type == KFD_QUEUE_TYPE_SDMA) {
+               mqd = dqm->ops.get_mqd_manager(dqm, KFD_MQD_TYPE_SDMA);
+               if (mqd == NULL) {
+                       retval = -ENOMEM;
+                       goto out;
+               }
+               dqm->sdma_queue_count--;
+               deallocate_sdma_queue(dqm, q->sdma_id);
        }
 
        retval = mqd->destroy_mqd(mqd, q->mqd,
-                               KFD_PREEMPT_TYPE_WAVEFRONT,
+                               KFD_PREEMPT_TYPE_WAVEFRONT_RESET,
                                QUEUE_PREEMPT_DEFAULT_TIMEOUT_MS,
                                q->pipe, q->queue);
 
        if (retval != 0)
                goto out;
 
-       deallocate_hqd(dqm, q);
-
        mqd->uninit_mqd(mqd, q->mqd, q->mqd_mem_obj);
 
        list_del(&q->list);
@@ -340,7 +331,7 @@ static int update_queue(struct device_queue_manager *dqm, struct queue *q)
        BUG_ON(!dqm || !q || !q->mqd);
 
        mutex_lock(&dqm->lock);
-       mqd = dqm->get_mqd_manager(dqm, KFD_MQD_TYPE_CIK_COMPUTE);
+       mqd = dqm->ops.get_mqd_manager(dqm, q->properties.type);
        if (mqd == NULL) {
                mutex_unlock(&dqm->lock);
                return -ENOMEM;
@@ -391,6 +382,7 @@ static int register_process_nocpsch(struct device_queue_manager *dqm,
                                        struct qcm_process_device *qpd)
 {
        struct device_process_node *n;
+       int retval;
 
        BUG_ON(!dqm || !qpd);
 
@@ -405,12 +397,13 @@ static int register_process_nocpsch(struct device_queue_manager *dqm,
        mutex_lock(&dqm->lock);
        list_add(&n->list, &dqm->queues);
 
-       init_process_memory(dqm, qpd);
+       retval = dqm->ops_asic_specific.register_process(dqm, qpd);
+
        dqm->processes_count++;
 
        mutex_unlock(&dqm->lock);
 
-       return 0;
+       return retval;
 }
 
 static int unregister_process_nocpsch(struct device_queue_manager *dqm,
@@ -455,48 +448,7 @@ set_pasid_vmid_mapping(struct device_queue_manager *dqm, unsigned int pasid,
                                                vmid);
 }
 
-static uint32_t compute_sh_mem_bases_64bit(unsigned int top_address_nybble)
-{
-       /* In 64-bit mode, we can only control the top 3 bits of the LDS,
-        * scratch and GPUVM apertures.
-        * The hardware fills in the remaining 59 bits according to the
-        * following pattern:
-        * LDS:         X0000000'00000000 - X0000001'00000000 (4GB)
-        * Scratch:     X0000001'00000000 - X0000002'00000000 (4GB)
-        * GPUVM:       Y0010000'00000000 - Y0020000'00000000 (1TB)
-        *
-        * (where X/Y is the configurable nybble with the low-bit 0)
-        *
-        * LDS and scratch will have the same top nybble programmed in the
-        * top 3 bits of SH_MEM_BASES.PRIVATE_BASE.
-        * GPUVM can have a different top nybble programmed in the
-        * top 3 bits of SH_MEM_BASES.SHARED_BASE.
-        * We don't bother to support different top nybbles
-        * for LDS/Scratch and GPUVM.
-        */
-
-       BUG_ON((top_address_nybble & 1) || top_address_nybble > 0xE ||
-               top_address_nybble == 0);
-
-       return PRIVATE_BASE(top_address_nybble << 12) |
-                       SHARED_BASE(top_address_nybble << 12);
-}
-
-static int init_memory(struct device_queue_manager *dqm)
-{
-       int i, retval;
-
-       for (i = 8; i < 16; i++)
-               set_pasid_vmid_mapping(dqm, 0, i);
-
-       retval = kfd2kgd->init_memory(dqm->dev->kgd);
-       if (retval == 0)
-               is_mem_initialized = true;
-       return retval;
-}
-
-
-static int init_pipelines(struct device_queue_manager *dqm,
+int init_pipelines(struct device_queue_manager *dqm,
                        unsigned int pipes_num, unsigned int first_pipe)
 {
        void *hpdptr;
@@ -515,11 +467,8 @@ static int init_pipelines(struct device_queue_manager *dqm,
         * because it contains no data when there are no active queues.
         */
 
-       err = kfd2kgd->allocate_mem(dqm->dev->kgd,
-                               CIK_HPD_EOP_BYTES * pipes_num,
-                               PAGE_SIZE,
-                               KFD_MEMPOOL_SYSTEM_WRITECOMBINE,
-                               (struct kgd_mem **) &dqm->pipeline_mem);
+       err = kfd_gtt_sa_allocate(dqm->dev, CIK_HPD_EOP_BYTES * pipes_num,
+                                       &dqm->pipeline_mem);
 
        if (err) {
                pr_err("kfd: error allocate vidmem num pipes: %d\n",
@@ -532,10 +481,9 @@ static int init_pipelines(struct device_queue_manager *dqm,
 
        memset(hpdptr, 0, CIK_HPD_EOP_BYTES * pipes_num);
 
-       mqd = dqm->get_mqd_manager(dqm, KFD_MQD_TYPE_CIK_COMPUTE);
+       mqd = dqm->ops.get_mqd_manager(dqm, KFD_MQD_TYPE_COMPUTE);
        if (mqd == NULL) {
-               kfd2kgd->free_mem(dqm->dev->kgd,
-                               (struct kgd_mem *) dqm->pipeline_mem);
+               kfd_gtt_sa_free(dqm->dev, dqm->pipeline_mem);
                return -ENOMEM;
        }
 
@@ -551,7 +499,6 @@ static int init_pipelines(struct device_queue_manager *dqm,
        return 0;
 }
 
-
 static int init_scheduler(struct device_queue_manager *dqm)
 {
        int retval;
@@ -561,10 +508,6 @@ static int init_scheduler(struct device_queue_manager *dqm)
        pr_debug("kfd: In %s\n", __func__);
 
        retval = init_pipelines(dqm, get_pipes_num(dqm), KFD_DQM_FIRST_PIPE);
-       if (retval != 0)
-               return retval;
-
-       retval = init_memory(dqm);
 
        return retval;
 }
@@ -581,6 +524,7 @@ static int initialize_nocpsch(struct device_queue_manager *dqm)
        mutex_init(&dqm->lock);
        INIT_LIST_HEAD(&dqm->queues);
        dqm->queue_count = dqm->next_pipe_to_allocate = 0;
+       dqm->sdma_queue_count = 0;
        dqm->allocated_queues = kcalloc(get_pipes_num(dqm),
                                        sizeof(unsigned int), GFP_KERNEL);
        if (!dqm->allocated_queues) {
@@ -592,6 +536,7 @@ static int initialize_nocpsch(struct device_queue_manager *dqm)
                dqm->allocated_queues[i] = (1 << QUEUES_PER_PIPE) - 1;
 
        dqm->vmid_bitmap = (1 << VMID_PER_DEVICE) - 1;
+       dqm->sdma_bitmap = (1 << CIK_SDMA_QUEUES) - 1;
 
        init_scheduler(dqm);
        return 0;
@@ -609,8 +554,7 @@ static void uninitialize_nocpsch(struct device_queue_manager *dqm)
        for (i = 0 ; i < KFD_MQD_TYPE_MAX ; i++)
                kfree(dqm->mqds[i]);
        mutex_destroy(&dqm->lock);
-       kfd2kgd->free_mem(dqm->dev->kgd,
-                       (struct kgd_mem *) dqm->pipeline_mem);
+       kfd_gtt_sa_free(dqm->dev, dqm->pipeline_mem);
 }
 
 static int start_nocpsch(struct device_queue_manager *dqm)
@@ -623,6 +567,77 @@ static int stop_nocpsch(struct device_queue_manager *dqm)
        return 0;
 }
 
+static int allocate_sdma_queue(struct device_queue_manager *dqm,
+                               unsigned int *sdma_queue_id)
+{
+       int bit;
+
+       if (dqm->sdma_bitmap == 0)
+               return -ENOMEM;
+
+       bit = find_first_bit((unsigned long *)&dqm->sdma_bitmap,
+                               CIK_SDMA_QUEUES);
+
+       clear_bit(bit, (unsigned long *)&dqm->sdma_bitmap);
+       *sdma_queue_id = bit;
+
+       return 0;
+}
+
+static void deallocate_sdma_queue(struct device_queue_manager *dqm,
+                               unsigned int sdma_queue_id)
+{
+       if (sdma_queue_id < 0 || sdma_queue_id >= CIK_SDMA_QUEUES)
+               return;
+       set_bit(sdma_queue_id, (unsigned long *)&dqm->sdma_bitmap);
+}
+
+static void init_sdma_vm(struct device_queue_manager *dqm, struct queue *q,
+                               struct qcm_process_device *qpd)
+{
+       uint32_t value = SDMA_ATC;
+
+       if (q->process->is_32bit_user_mode)
+               value |= SDMA_VA_PTR32 | get_sh_mem_bases_32(qpd_to_pdd(qpd));
+       else
+               value |= SDMA_VA_SHARED_BASE(get_sh_mem_bases_nybble_64(
+                                                       qpd_to_pdd(qpd)));
+       q->properties.sdma_vm_addr = value;
+}
+
+static int create_sdma_queue_nocpsch(struct device_queue_manager *dqm,
+                                       struct queue *q,
+                                       struct qcm_process_device *qpd)
+{
+       struct mqd_manager *mqd;
+       int retval;
+
+       mqd = dqm->ops.get_mqd_manager(dqm, KFD_MQD_TYPE_SDMA);
+       if (!mqd)
+               return -ENOMEM;
+
+       retval = allocate_sdma_queue(dqm, &q->sdma_id);
+       if (retval != 0)
+               return retval;
+
+       q->properties.sdma_queue_id = q->sdma_id % CIK_SDMA_QUEUES_PER_ENGINE;
+       q->properties.sdma_engine_id = q->sdma_id / CIK_SDMA_ENGINE_NUM;
+
+       pr_debug("kfd: sdma id is:    %d\n", q->sdma_id);
+       pr_debug("     sdma queue id: %d\n", q->properties.sdma_queue_id);
+       pr_debug("     sdma engine id: %d\n", q->properties.sdma_engine_id);
+
+       retval = mqd->init_mqd(mqd, &q->mqd, &q->mqd_mem_obj,
+                               &q->gart_mqd_addr, &q->properties);
+       if (retval != 0) {
+               deallocate_sdma_queue(dqm, q->sdma_id);
+               return retval;
+       }
+
+       init_sdma_vm(dqm, q, qpd);
+       return 0;
+}
+
 /*
  * Device Queue Manager implementation for cp scheduler
  */
@@ -664,8 +679,9 @@ static int initialize_cpsch(struct device_queue_manager *dqm)
        mutex_init(&dqm->lock);
        INIT_LIST_HEAD(&dqm->queues);
        dqm->queue_count = dqm->processes_count = 0;
+       dqm->sdma_queue_count = 0;
        dqm->active_runlist = false;
-       retval = init_pipelines(dqm, get_pipes_num(dqm), 0);
+       retval = dqm->ops_asic_specific.initialize(dqm);
        if (retval != 0)
                goto fail_init_pipelines;
 
@@ -696,18 +712,14 @@ static int start_cpsch(struct device_queue_manager *dqm)
        pr_debug("kfd: allocating fence memory\n");
 
        /* allocate fence memory on the gart */
-       retval = kfd2kgd->allocate_mem(dqm->dev->kgd,
-                                       sizeof(*dqm->fence_addr),
-                                       32,
-                                       KFD_MEMPOOL_SYSTEM_WRITECOMBINE,
-                                       (struct kgd_mem **) &dqm->fence_mem);
+       retval = kfd_gtt_sa_allocate(dqm->dev, sizeof(*dqm->fence_addr),
+                                       &dqm->fence_mem);
 
        if (retval != 0)
                goto fail_allocate_vidmem;
 
        dqm->fence_addr = dqm->fence_mem->cpu_ptr;
        dqm->fence_gpu_addr = dqm->fence_mem->gpu_addr;
-
        list_for_each_entry(node, &dqm->queues, list)
                if (node->qpd->pqm->process && dqm->dev)
                        kfd_bind_process_to_device(dqm->dev,
@@ -736,8 +748,7 @@ static int stop_cpsch(struct device_queue_manager *dqm)
                pdd = qpd_to_pdd(node->qpd);
                pdd->bound = false;
        }
-       kfd2kgd->free_mem(dqm->dev->kgd,
-                       (struct kgd_mem *) dqm->fence_mem);
+       kfd_gtt_sa_free(dqm->dev, dqm->fence_mem);
        pm_uninit(&dqm->packets);
 
        return 0;
@@ -778,6 +789,14 @@ static void destroy_kernel_queue_cpsch(struct device_queue_manager *dqm,
        mutex_unlock(&dqm->lock);
 }
 
+static void select_sdma_engine_id(struct queue *q)
+{
+       static int sdma_id;
+
+       q->sdma_id = sdma_id;
+       sdma_id = (sdma_id + 1) % 2;
+}
+
 static int create_queue_cpsch(struct device_queue_manager *dqm, struct queue *q,
                        struct qcm_process_device *qpd, int *allocate_vmid)
 {
@@ -793,7 +812,12 @@ static int create_queue_cpsch(struct device_queue_manager *dqm, struct queue *q,
 
        mutex_lock(&dqm->lock);
 
-       mqd = dqm->get_mqd_manager(dqm, KFD_MQD_TYPE_CIK_CP);
+       if (q->properties.type == KFD_QUEUE_TYPE_SDMA)
+               select_sdma_engine_id(q);
+
+       mqd = dqm->ops.get_mqd_manager(dqm,
+                       get_mqd_type_from_queue_type(q->properties.type));
+
        if (mqd == NULL) {
                mutex_unlock(&dqm->lock);
                return -ENOMEM;
@@ -810,6 +834,9 @@ static int create_queue_cpsch(struct device_queue_manager *dqm, struct queue *q,
                retval = execute_queues_cpsch(dqm, false);
        }
 
+       if (q->properties.type == KFD_QUEUE_TYPE_SDMA)
+                       dqm->sdma_queue_count++;
+
 out:
        mutex_unlock(&dqm->lock);
        return retval;
@@ -827,12 +854,20 @@ static int fence_wait_timeout(unsigned int *fence_addr,
                        pr_err("kfd: qcm fence wait loop timeout expired\n");
                        return -ETIME;
                }
-               cpu_relax();
+               schedule();
        }
 
        return 0;
 }
 
+static int destroy_sdma_queues(struct device_queue_manager *dqm,
+                               unsigned int sdma_engine)
+{
+       return pm_send_unmap_queue(&dqm->packets, KFD_QUEUE_TYPE_SDMA,
+                       KFD_PREEMPT_TYPE_FILTER_ALL_QUEUES, 0, false,
+                       sdma_engine);
+}
+
 static int destroy_queues_cpsch(struct device_queue_manager *dqm, bool lock)
 {
        int retval;
@@ -845,6 +880,15 @@ static int destroy_queues_cpsch(struct device_queue_manager *dqm, bool lock)
                mutex_lock(&dqm->lock);
        if (dqm->active_runlist == false)
                goto out;
+
+       pr_debug("kfd: Before destroying queues, sdma queue count is : %u\n",
+               dqm->sdma_queue_count);
+
+       if (dqm->sdma_queue_count > 0) {
+               destroy_sdma_queues(dqm, 0);
+               destroy_sdma_queues(dqm, 1);
+       }
+
        retval = pm_send_unmap_queue(&dqm->packets, KFD_QUEUE_TYPE_COMPUTE,
                        KFD_PREEMPT_TYPE_FILTER_ALL_QUEUES, 0, false, 0);
        if (retval != 0)
@@ -916,13 +960,16 @@ static int destroy_queue_cpsch(struct device_queue_manager *dqm,
 
        /* remove queue from list to prevent rescheduling after preemption */
        mutex_lock(&dqm->lock);
-
-       mqd = dqm->get_mqd_manager(dqm, KFD_MQD_TYPE_CIK_CP);
+       mqd = dqm->ops.get_mqd_manager(dqm,
+                       get_mqd_type_from_queue_type(q->properties.type));
        if (!mqd) {
                retval = -ENOMEM;
                goto failed;
        }
 
+       if (q->properties.type == KFD_QUEUE_TYPE_SDMA)
+               dqm->sdma_queue_count--;
+
        list_del(&q->list);
        dqm->queue_count--;
 
@@ -954,8 +1001,7 @@ static bool set_cache_memory_policy(struct device_queue_manager *dqm,
                                   void __user *alternate_aperture_base,
                                   uint64_t alternate_aperture_size)
 {
-       uint32_t default_mtype;
-       uint32_t ape1_mtype;
+       bool retval;
 
        pr_debug("kfd: In func %s\n", __func__);
 
@@ -992,18 +1038,13 @@ static bool set_cache_memory_policy(struct device_queue_manager *dqm,
                qpd->sh_mem_ape1_limit = limit >> 16;
        }
 
-       default_mtype = (default_policy == cache_policy_coherent) ?
-                       MTYPE_NONCACHED :
-                       MTYPE_CACHED;
-
-       ape1_mtype = (alternate_policy == cache_policy_coherent) ?
-                       MTYPE_NONCACHED :
-                       MTYPE_CACHED;
-
-       qpd->sh_mem_config = (qpd->sh_mem_config & PTR32)
-                       | ALIGNMENT_MODE(SH_MEM_ALIGNMENT_MODE_UNALIGNED)
-                       | DEFAULT_MTYPE(default_mtype)
-                       | APE1_MTYPE(ape1_mtype);
+       retval = dqm->ops_asic_specific.set_cache_memory_policy(
+                       dqm,
+                       qpd,
+                       default_policy,
+                       alternate_policy,
+                       alternate_aperture_base,
+                       alternate_aperture_size);
 
        if ((sched_policy == KFD_SCHED_POLICY_NO_HWS) && (qpd->vmid != 0))
                program_sh_mem_settings(dqm, qpd);
@@ -1013,7 +1054,7 @@ static bool set_cache_memory_policy(struct device_queue_manager *dqm,
                qpd->sh_mem_ape1_limit);
 
        mutex_unlock(&dqm->lock);
-       return true;
+       return retval;
 
 out:
        mutex_unlock(&dqm->lock);
@@ -1026,6 +1067,8 @@ struct device_queue_manager *device_queue_manager_init(struct kfd_dev *dev)
 
        BUG_ON(!dev);
 
+       pr_debug("kfd: loading device queue manager\n");
+
        dqm = kzalloc(sizeof(struct device_queue_manager), GFP_KERNEL);
        if (!dqm)
                return NULL;
@@ -1035,40 +1078,47 @@ struct device_queue_manager *device_queue_manager_init(struct kfd_dev *dev)
        case KFD_SCHED_POLICY_HWS:
        case KFD_SCHED_POLICY_HWS_NO_OVERSUBSCRIPTION:
                /* initialize dqm for cp scheduling */
-               dqm->create_queue = create_queue_cpsch;
-               dqm->initialize = initialize_cpsch;
-               dqm->start = start_cpsch;
-               dqm->stop = stop_cpsch;
-               dqm->destroy_queue = destroy_queue_cpsch;
-               dqm->update_queue = update_queue;
-               dqm->get_mqd_manager = get_mqd_manager_nocpsch;
-               dqm->register_process = register_process_nocpsch;
-               dqm->unregister_process = unregister_process_nocpsch;
-               dqm->uninitialize = uninitialize_nocpsch;
-               dqm->create_kernel_queue = create_kernel_queue_cpsch;
-               dqm->destroy_kernel_queue = destroy_kernel_queue_cpsch;
-               dqm->set_cache_memory_policy = set_cache_memory_policy;
+               dqm->ops.create_queue = create_queue_cpsch;
+               dqm->ops.initialize = initialize_cpsch;
+               dqm->ops.start = start_cpsch;
+               dqm->ops.stop = stop_cpsch;
+               dqm->ops.destroy_queue = destroy_queue_cpsch;
+               dqm->ops.update_queue = update_queue;
+               dqm->ops.get_mqd_manager = get_mqd_manager_nocpsch;
+               dqm->ops.register_process = register_process_nocpsch;
+               dqm->ops.unregister_process = unregister_process_nocpsch;
+               dqm->ops.uninitialize = uninitialize_nocpsch;
+               dqm->ops.create_kernel_queue = create_kernel_queue_cpsch;
+               dqm->ops.destroy_kernel_queue = destroy_kernel_queue_cpsch;
+               dqm->ops.set_cache_memory_policy = set_cache_memory_policy;
                break;
        case KFD_SCHED_POLICY_NO_HWS:
                /* initialize dqm for no cp scheduling */
-               dqm->start = start_nocpsch;
-               dqm->stop = stop_nocpsch;
-               dqm->create_queue = create_queue_nocpsch;
-               dqm->destroy_queue = destroy_queue_nocpsch;
-               dqm->update_queue = update_queue;
-               dqm->get_mqd_manager = get_mqd_manager_nocpsch;
-               dqm->register_process = register_process_nocpsch;
-               dqm->unregister_process = unregister_process_nocpsch;
-               dqm->initialize = initialize_nocpsch;
-               dqm->uninitialize = uninitialize_nocpsch;
-               dqm->set_cache_memory_policy = set_cache_memory_policy;
+               dqm->ops.start = start_nocpsch;
+               dqm->ops.stop = stop_nocpsch;
+               dqm->ops.create_queue = create_queue_nocpsch;
+               dqm->ops.destroy_queue = destroy_queue_nocpsch;
+               dqm->ops.update_queue = update_queue;
+               dqm->ops.get_mqd_manager = get_mqd_manager_nocpsch;
+               dqm->ops.register_process = register_process_nocpsch;
+               dqm->ops.unregister_process = unregister_process_nocpsch;
+               dqm->ops.initialize = initialize_nocpsch;
+               dqm->ops.uninitialize = uninitialize_nocpsch;
+               dqm->ops.set_cache_memory_policy = set_cache_memory_policy;
                break;
        default:
                BUG();
                break;
        }
 
-       if (dqm->initialize(dqm) != 0) {
+       switch (dev->device_info->asic_family) {
+       case CHIP_CARRIZO:
+               device_queue_manager_init_vi(&dqm->ops_asic_specific);
+       case CHIP_KAVERI:
+               device_queue_manager_init_cik(&dqm->ops_asic_specific);
+       }
+
+       if (dqm->ops.initialize(dqm) != 0) {
                kfree(dqm);
                return NULL;
        }
@@ -1080,7 +1130,6 @@ void device_queue_manager_uninit(struct device_queue_manager *dqm)
 {
        BUG_ON(!dqm);
 
-       dqm->uninitialize(dqm);
+       dqm->ops.uninitialize(dqm);
        kfree(dqm);
 }
-
index c3f189e8ae35da5527efebe3ae016b47b2b3342c..19347956eeb9c9f519aa77fb3f360fe233fe1eb4 100644 (file)
@@ -36,6 +36,9 @@
 #define KFD_VMID_START_OFFSET                  (8)
 #define VMID_PER_DEVICE                                CIK_VMID_NUM
 #define KFD_DQM_FIRST_PIPE                     (0)
+#define CIK_SDMA_QUEUES                                (4)
+#define CIK_SDMA_QUEUES_PER_ENGINE             (2)
+#define CIK_SDMA_ENGINE_NUM                    (2)
 
 struct device_process_node {
        struct qcm_process_device *qpd;
@@ -43,7 +46,7 @@ struct device_process_node {
 };
 
 /**
- * struct device_queue_manager
+ * struct device_queue_manager_ops
  *
  * @create_queue: Queue creation routine.
  *
@@ -78,15 +81,9 @@ struct device_process_node {
  * @set_cache_memory_policy: Sets memory policy (cached/ non cached) for the
  * memory apertures.
  *
- * This struct is a base class for the kfd queues scheduler in the
- * device level. The device base class should expose the basic operations
- * for queue creation and queue destruction. This base class hides the
- * scheduling mode of the driver and the specific implementation of the
- * concrete device. This class is the only class in the queues scheduler
- * that configures the H/W.
  */
 
-struct device_queue_manager {
+struct device_queue_manager_ops {
        int     (*create_queue)(struct device_queue_manager *dqm,
                                struct queue *q,
                                struct qcm_process_device *qpd,
@@ -121,7 +118,23 @@ struct device_queue_manager {
                                           enum cache_policy alternate_policy,
                                           void __user *alternate_aperture_base,
                                           uint64_t alternate_aperture_size);
+};
+
+/**
+ * struct device_queue_manager
+ *
+ * This struct is a base class for the kfd queues scheduler in the
+ * device level. The device base class should expose the basic operations
+ * for queue creation and queue destruction. This base class hides the
+ * scheduling mode of the driver and the specific implementation of the
+ * concrete device. This class is the only class in the queues scheduler
+ * that configures the H/W.
+ *
+ */
 
+struct device_queue_manager {
+       struct device_queue_manager_ops ops;
+       struct device_queue_manager_ops ops_asic_specific;
 
        struct mqd_manager      *mqds[KFD_MQD_TYPE_MAX];
        struct packet_manager   packets;
@@ -130,8 +143,10 @@ struct device_queue_manager {
        struct list_head        queues;
        unsigned int            processes_count;
        unsigned int            queue_count;
+       unsigned int            sdma_queue_count;
        unsigned int            next_pipe_to_allocate;
        unsigned int            *allocated_queues;
+       unsigned int            sdma_bitmap;
        unsigned int            vmid_bitmap;
        uint64_t                pipelines_addr;
        struct kfd_mem_obj      *pipeline_mem;
@@ -141,6 +156,14 @@ struct device_queue_manager {
        bool                    active_runlist;
 };
 
-
+void device_queue_manager_init_cik(struct device_queue_manager_ops *ops);
+void device_queue_manager_init_vi(struct device_queue_manager_ops *ops);
+void program_sh_mem_settings(struct device_queue_manager *dqm,
+                                       struct qcm_process_device *qpd);
+inline unsigned int get_sh_mem_bases_32(struct kfd_process_device *qpd);
+inline unsigned int get_sh_mem_bases_nybble_64(struct kfd_process_device *pdd);
+int init_pipelines(struct device_queue_manager *dqm,
+               unsigned int pipes_num, unsigned int first_pipe);
+inline unsigned int get_pipes_num(struct device_queue_manager *dqm);
 
 #endif /* KFD_DEVICE_QUEUE_MANAGER_H_ */
diff --git a/drivers/gpu/drm/amd/amdkfd/kfd_device_queue_manager_cik.c b/drivers/gpu/drm/amd/amdkfd/kfd_device_queue_manager_cik.c
new file mode 100644 (file)
index 0000000..6b07246
--- /dev/null
@@ -0,0 +1,135 @@
+/*
+ * Copyright 2014 Advanced Micro Devices, 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.
+ *
+ */
+
+#include "kfd_device_queue_manager.h"
+#include "cik_regs.h"
+
+static bool set_cache_memory_policy_cik(struct device_queue_manager *dqm,
+                                  struct qcm_process_device *qpd,
+                                  enum cache_policy default_policy,
+                                  enum cache_policy alternate_policy,
+                                  void __user *alternate_aperture_base,
+                                  uint64_t alternate_aperture_size);
+static int register_process_cik(struct device_queue_manager *dqm,
+                                       struct qcm_process_device *qpd);
+static int initialize_cpsch_cik(struct device_queue_manager *dqm);
+
+void device_queue_manager_init_cik(struct device_queue_manager_ops *ops)
+{
+       ops->set_cache_memory_policy = set_cache_memory_policy_cik;
+       ops->register_process = register_process_cik;
+       ops->initialize = initialize_cpsch_cik;
+}
+
+static uint32_t compute_sh_mem_bases_64bit(unsigned int top_address_nybble)
+{
+       /* In 64-bit mode, we can only control the top 3 bits of the LDS,
+        * scratch and GPUVM apertures.
+        * The hardware fills in the remaining 59 bits according to the
+        * following pattern:
+        * LDS:         X0000000'00000000 - X0000001'00000000 (4GB)
+        * Scratch:     X0000001'00000000 - X0000002'00000000 (4GB)
+        * GPUVM:       Y0010000'00000000 - Y0020000'00000000 (1TB)
+        *
+        * (where X/Y is the configurable nybble with the low-bit 0)
+        *
+        * LDS and scratch will have the same top nybble programmed in the
+        * top 3 bits of SH_MEM_BASES.PRIVATE_BASE.
+        * GPUVM can have a different top nybble programmed in the
+        * top 3 bits of SH_MEM_BASES.SHARED_BASE.
+        * We don't bother to support different top nybbles
+        * for LDS/Scratch and GPUVM.
+        */
+
+       BUG_ON((top_address_nybble & 1) || top_address_nybble > 0xE ||
+               top_address_nybble == 0);
+
+       return PRIVATE_BASE(top_address_nybble << 12) |
+                       SHARED_BASE(top_address_nybble << 12);
+}
+
+static bool set_cache_memory_policy_cik(struct device_queue_manager *dqm,
+                                  struct qcm_process_device *qpd,
+                                  enum cache_policy default_policy,
+                                  enum cache_policy alternate_policy,
+                                  void __user *alternate_aperture_base,
+                                  uint64_t alternate_aperture_size)
+{
+       uint32_t default_mtype;
+       uint32_t ape1_mtype;
+
+       default_mtype = (default_policy == cache_policy_coherent) ?
+                       MTYPE_NONCACHED :
+                       MTYPE_CACHED;
+
+       ape1_mtype = (alternate_policy == cache_policy_coherent) ?
+                       MTYPE_NONCACHED :
+                       MTYPE_CACHED;
+
+       qpd->sh_mem_config = (qpd->sh_mem_config & PTR32)
+                       | ALIGNMENT_MODE(SH_MEM_ALIGNMENT_MODE_UNALIGNED)
+                       | DEFAULT_MTYPE(default_mtype)
+                       | APE1_MTYPE(ape1_mtype);
+
+       return true;
+}
+
+static int register_process_cik(struct device_queue_manager *dqm,
+               struct qcm_process_device *qpd)
+{
+       struct kfd_process_device *pdd;
+       unsigned int temp;
+
+       BUG_ON(!dqm || !qpd);
+
+       pdd = qpd_to_pdd(qpd);
+
+       /* check if sh_mem_config register already configured */
+       if (qpd->sh_mem_config == 0) {
+               qpd->sh_mem_config =
+                       ALIGNMENT_MODE(SH_MEM_ALIGNMENT_MODE_UNALIGNED) |
+                       DEFAULT_MTYPE(MTYPE_NONCACHED) |
+                       APE1_MTYPE(MTYPE_NONCACHED);
+               qpd->sh_mem_ape1_limit = 0;
+               qpd->sh_mem_ape1_base = 0;
+       }
+
+       if (qpd->pqm->process->is_32bit_user_mode) {
+               temp = get_sh_mem_bases_32(pdd);
+               qpd->sh_mem_bases = SHARED_BASE(temp);
+               qpd->sh_mem_config |= PTR32;
+       } else {
+               temp = get_sh_mem_bases_nybble_64(pdd);
+               qpd->sh_mem_bases = compute_sh_mem_bases_64bit(temp);
+       }
+
+       pr_debug("kfd: is32bit process: %d sh_mem_bases nybble: 0x%X and register 0x%X\n",
+               qpd->pqm->process->is_32bit_user_mode, temp, qpd->sh_mem_bases);
+
+       return 0;
+}
+
+static int initialize_cpsch_cik(struct device_queue_manager *dqm)
+{
+       return init_pipelines(dqm, get_pipes_num(dqm), 0);
+}
diff --git a/drivers/gpu/drm/amd/amdkfd/kfd_device_queue_manager_vi.c b/drivers/gpu/drm/amd/amdkfd/kfd_device_queue_manager_vi.c
new file mode 100644 (file)
index 0000000..20553dc
--- /dev/null
@@ -0,0 +1,64 @@
+/*
+ * Copyright 2014 Advanced Micro Devices, 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.
+ *
+ */
+
+#include "kfd_device_queue_manager.h"
+
+static bool set_cache_memory_policy_vi(struct device_queue_manager *dqm,
+                                  struct qcm_process_device *qpd,
+                                  enum cache_policy default_policy,
+                                  enum cache_policy alternate_policy,
+                                  void __user *alternate_aperture_base,
+                                  uint64_t alternate_aperture_size);
+static int register_process_vi(struct device_queue_manager *dqm,
+                                       struct qcm_process_device *qpd);
+static int initialize_cpsch_vi(struct device_queue_manager *dqm);
+
+void device_queue_manager_init_vi(struct device_queue_manager_ops *ops)
+{
+       pr_warn("amdkfd: VI DQM is not currently supported\n");
+
+       ops->set_cache_memory_policy = set_cache_memory_policy_vi;
+       ops->register_process = register_process_vi;
+       ops->initialize = initialize_cpsch_vi;
+}
+
+static bool set_cache_memory_policy_vi(struct device_queue_manager *dqm,
+                                  struct qcm_process_device *qpd,
+                                  enum cache_policy default_policy,
+                                  enum cache_policy alternate_policy,
+                                  void __user *alternate_aperture_base,
+                                  uint64_t alternate_aperture_size)
+{
+       return false;
+}
+
+static int register_process_vi(struct device_queue_manager *dqm,
+                                       struct qcm_process_device *qpd)
+{
+       return -1;
+}
+
+static int initialize_cpsch_vi(struct device_queue_manager *dqm)
+{
+       return 0;
+}
index b5791a5c7c06156f73121629383ca9618741f853..1a9b355dd114595f8bcf156907e486ebe2bbbdb4 100644 (file)
@@ -137,10 +137,6 @@ int kfd_doorbell_mmap(struct kfd_process *process, struct vm_area_struct *vma)
        if (dev == NULL)
                return -EINVAL;
 
-       /* Find if pdd exists for combination of process and gpu id */
-       if (!kfd_get_process_device_data(dev, process, 0))
-               return -EINVAL;
-
        /* Calculate physical address of doorbell */
        address = kfd_get_process_doorbells(dev, process);
 
index e64aa99e5e416349071f3c0906be347ed42e3e53..35b98757463305c9d1740542704f64cfc9db702a 100644 (file)
@@ -303,10 +303,11 @@ int kfd_init_apertures(struct kfd_process *process)
        while ((dev = kfd_topology_enum_kfd_devices(id)) != NULL &&
                id < NUM_OF_SUPPORTED_GPUS) {
 
-               pdd = kfd_get_process_device_data(dev, process, 1);
-               if (!pdd)
+               pdd = kfd_create_process_device_data(dev, process);
+               if (pdd == NULL) {
+                       pr_err("Failed to create process device data\n");
                        return -1;
-
+               }
                /*
                 * For 64 bit process aperture will be statically reserved in
                 * the x86_64 non canonical process address space
diff --git a/drivers/gpu/drm/amd/amdkfd/kfd_interrupt.c b/drivers/gpu/drm/amd/amdkfd/kfd_interrupt.c
deleted file mode 100644 (file)
index 5b99909..0000000
+++ /dev/null
@@ -1,176 +0,0 @@
-/*
- * Copyright 2014 Advanced Micro Devices, 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.
- */
-
-/*
- * KFD Interrupts.
- *
- * AMD GPUs deliver interrupts by pushing an interrupt description onto the
- * interrupt ring and then sending an interrupt. KGD receives the interrupt
- * in ISR and sends us a pointer to each new entry on the interrupt ring.
- *
- * We generally can't process interrupt-signaled events from ISR, so we call
- * out to each interrupt client module (currently only the scheduler) to ask if
- * each interrupt is interesting. If they return true, then it requires further
- * processing so we copy it to an internal interrupt ring and call each
- * interrupt client again from a work-queue.
- *
- * There's no acknowledgment for the interrupts we use. The hardware simply
- * queues a new interrupt each time without waiting.
- *
- * The fixed-size internal queue means that it's possible for us to lose
- * interrupts because we have no back-pressure to the hardware.
- */
-
-#include <linux/slab.h>
-#include <linux/device.h>
-#include "kfd_priv.h"
-
-#define KFD_INTERRUPT_RING_SIZE 256
-
-static void interrupt_wq(struct work_struct *);
-
-int kfd_interrupt_init(struct kfd_dev *kfd)
-{
-       void *interrupt_ring = kmalloc_array(KFD_INTERRUPT_RING_SIZE,
-                                       kfd->device_info->ih_ring_entry_size,
-                                       GFP_KERNEL);
-       if (!interrupt_ring)
-               return -ENOMEM;
-
-       kfd->interrupt_ring = interrupt_ring;
-       kfd->interrupt_ring_size =
-               KFD_INTERRUPT_RING_SIZE * kfd->device_info->ih_ring_entry_size;
-       atomic_set(&kfd->interrupt_ring_wptr, 0);
-       atomic_set(&kfd->interrupt_ring_rptr, 0);
-
-       spin_lock_init(&kfd->interrupt_lock);
-
-       INIT_WORK(&kfd->interrupt_work, interrupt_wq);
-
-       kfd->interrupts_active = true;
-
-       /*
-        * After this function returns, the interrupt will be enabled. This
-        * barrier ensures that the interrupt running on a different processor
-        * sees all the above writes.
-        */
-       smp_wmb();
-
-       return 0;
-}
-
-void kfd_interrupt_exit(struct kfd_dev *kfd)
-{
-       /*
-        * Stop the interrupt handler from writing to the ring and scheduling
-        * workqueue items. The spinlock ensures that any interrupt running
-        * after we have unlocked sees interrupts_active = false.
-        */
-       unsigned long flags;
-
-       spin_lock_irqsave(&kfd->interrupt_lock, flags);
-       kfd->interrupts_active = false;
-       spin_unlock_irqrestore(&kfd->interrupt_lock, flags);
-
-       /*
-        * Flush_scheduled_work ensures that there are no outstanding
-        * work-queue items that will access interrupt_ring. New work items
-        * can't be created because we stopped interrupt handling above.
-        */
-       flush_scheduled_work();
-
-       kfree(kfd->interrupt_ring);
-}
-
-/*
- * This assumes that it can't be called concurrently with itself
- * but only with dequeue_ih_ring_entry.
- */
-bool enqueue_ih_ring_entry(struct kfd_dev *kfd,        const void *ih_ring_entry)
-{
-       unsigned int rptr = atomic_read(&kfd->interrupt_ring_rptr);
-       unsigned int wptr = atomic_read(&kfd->interrupt_ring_wptr);
-
-       if ((rptr - wptr) % kfd->interrupt_ring_size ==
-                                       kfd->device_info->ih_ring_entry_size) {
-               /* This is very bad, the system is likely to hang. */
-               dev_err_ratelimited(kfd_chardev(),
-                       "Interrupt ring overflow, dropping interrupt.\n");
-               return false;
-       }
-
-       memcpy(kfd->interrupt_ring + wptr, ih_ring_entry,
-                       kfd->device_info->ih_ring_entry_size);
-
-       wptr = (wptr + kfd->device_info->ih_ring_entry_size) %
-                       kfd->interrupt_ring_size;
-       smp_wmb(); /* Ensure memcpy'd data is visible before wptr update. */
-       atomic_set(&kfd->interrupt_ring_wptr, wptr);
-
-       return true;
-}
-
-/*
- * This assumes that it can't be called concurrently with itself
- * but only with enqueue_ih_ring_entry.
- */
-static bool dequeue_ih_ring_entry(struct kfd_dev *kfd, void *ih_ring_entry)
-{
-       /*
-        * Assume that wait queues have an implicit barrier, i.e. anything that
-        * happened in the ISR before it queued work is visible.
-        */
-
-       unsigned int wptr = atomic_read(&kfd->interrupt_ring_wptr);
-       unsigned int rptr = atomic_read(&kfd->interrupt_ring_rptr);
-
-       if (rptr == wptr)
-               return false;
-
-       memcpy(ih_ring_entry, kfd->interrupt_ring + rptr,
-                       kfd->device_info->ih_ring_entry_size);
-
-       rptr = (rptr + kfd->device_info->ih_ring_entry_size) %
-                       kfd->interrupt_ring_size;
-
-       /*
-        * Ensure the rptr write update is not visible until
-        * memcpy has finished reading.
-        */
-       smp_mb();
-       atomic_set(&kfd->interrupt_ring_rptr, rptr);
-
-       return true;
-}
-
-static void interrupt_wq(struct work_struct *work)
-{
-       struct kfd_dev *dev = container_of(work, struct kfd_dev,
-                                               interrupt_work);
-
-       uint32_t ih_ring_entry[DIV_ROUND_UP(
-                               dev->device_info->ih_ring_entry_size,
-                               sizeof(uint32_t))];
-
-       while (dequeue_ih_ring_entry(dev, ih_ring_entry))
-               ;
-}
index 93507141072495b9c7815b4d5cad2cf124b9abe3..c04b1ac60bd9e7f9f8e56e30e3b34a811479511c 100644 (file)
@@ -56,8 +56,8 @@ static bool initialize(struct kernel_queue *kq, struct kfd_dev *dev,
        switch (type) {
        case KFD_QUEUE_TYPE_DIQ:
        case KFD_QUEUE_TYPE_HIQ:
-               kq->mqd = dev->dqm->get_mqd_manager(dev->dqm,
-                                               KFD_MQD_TYPE_CIK_HIQ);
+               kq->mqd = dev->dqm->ops.get_mqd_manager(dev->dqm,
+                                               KFD_MQD_TYPE_HIQ);
                break;
        default:
                BUG();
@@ -72,23 +72,19 @@ static bool initialize(struct kernel_queue *kq, struct kfd_dev *dev,
        if (prop.doorbell_ptr == NULL)
                goto err_get_kernel_doorbell;
 
-       retval = kfd2kgd->allocate_mem(dev->kgd,
-                                       queue_size,
-                                       PAGE_SIZE,
-                                       KFD_MEMPOOL_SYSTEM_WRITECOMBINE,
-                                       (struct kgd_mem **) &kq->pq);
-
+       retval = kfd_gtt_sa_allocate(dev, queue_size, &kq->pq);
        if (retval != 0)
                goto err_pq_allocate_vidmem;
 
        kq->pq_kernel_addr = kq->pq->cpu_ptr;
        kq->pq_gpu_addr = kq->pq->gpu_addr;
 
-       retval = kfd2kgd->allocate_mem(dev->kgd,
-                                       sizeof(*kq->rptr_kernel),
-                                       32,
-                                       KFD_MEMPOOL_SYSTEM_WRITECOMBINE,
-                                       (struct kgd_mem **) &kq->rptr_mem);
+       retval = kq->ops_asic_specific.initialize(kq, dev, type, queue_size);
+       if (retval == false)
+               goto err_eop_allocate_vidmem;
+
+       retval = kfd_gtt_sa_allocate(dev, sizeof(*kq->rptr_kernel),
+                                       &kq->rptr_mem);
 
        if (retval != 0)
                goto err_rptr_allocate_vidmem;
@@ -96,11 +92,8 @@ static bool initialize(struct kernel_queue *kq, struct kfd_dev *dev,
        kq->rptr_kernel = kq->rptr_mem->cpu_ptr;
        kq->rptr_gpu_addr = kq->rptr_mem->gpu_addr;
 
-       retval = kfd2kgd->allocate_mem(dev->kgd,
-                                       sizeof(*kq->wptr_kernel),
-                                       32,
-                                       KFD_MEMPOOL_SYSTEM_WRITECOMBINE,
-                                       (struct kgd_mem **) &kq->wptr_mem);
+       retval = kfd_gtt_sa_allocate(dev, sizeof(*kq->wptr_kernel),
+                                       &kq->wptr_mem);
 
        if (retval != 0)
                goto err_wptr_allocate_vidmem;
@@ -121,6 +114,8 @@ static bool initialize(struct kernel_queue *kq, struct kfd_dev *dev,
        prop.queue_address = kq->pq_gpu_addr;
        prop.read_ptr = (uint32_t *) kq->rptr_gpu_addr;
        prop.write_ptr = (uint32_t *) kq->wptr_gpu_addr;
+       prop.eop_ring_buffer_address = kq->eop_gpu_addr;
+       prop.eop_ring_buffer_size = PAGE_SIZE;
 
        if (init_queue(&kq->queue, prop) != 0)
                goto err_init_queue;
@@ -145,11 +140,8 @@ static bool initialize(struct kernel_queue *kq, struct kfd_dev *dev,
        } else {
                /* allocate fence for DIQ */
 
-               retval = kfd2kgd->allocate_mem(dev->kgd,
-                                       sizeof(uint32_t),
-                                       32,
-                                       KFD_MEMPOOL_SYSTEM_WRITECOMBINE,
-                                       (struct kgd_mem **) &kq->fence_mem_obj);
+               retval = kfd_gtt_sa_allocate(dev, sizeof(uint32_t),
+                                               &kq->fence_mem_obj);
 
                if (retval != 0)
                        goto err_alloc_fence;
@@ -165,11 +157,13 @@ err_alloc_fence:
 err_init_mqd:
        uninit_queue(kq->queue);
 err_init_queue:
-       kfd2kgd->free_mem(dev->kgd, (struct kgd_mem *) kq->wptr_mem);
+       kfd_gtt_sa_free(dev, kq->wptr_mem);
 err_wptr_allocate_vidmem:
-       kfd2kgd->free_mem(dev->kgd, (struct kgd_mem *) kq->rptr_mem);
+       kfd_gtt_sa_free(dev, kq->rptr_mem);
 err_rptr_allocate_vidmem:
-       kfd2kgd->free_mem(dev->kgd, (struct kgd_mem *) kq->pq);
+       kfd_gtt_sa_free(dev, kq->eop_mem);
+err_eop_allocate_vidmem:
+       kfd_gtt_sa_free(dev, kq->pq);
 err_pq_allocate_vidmem:
        pr_err("kfd: error init pq\n");
        kfd_release_kernel_doorbell(dev, prop.doorbell_ptr);
@@ -190,10 +184,13 @@ static void uninitialize(struct kernel_queue *kq)
                                        QUEUE_PREEMPT_DEFAULT_TIMEOUT_MS,
                                        kq->queue->pipe,
                                        kq->queue->queue);
+       else if (kq->queue->properties.type == KFD_QUEUE_TYPE_DIQ)
+               kfd_gtt_sa_free(kq->dev, kq->fence_mem_obj);
 
-       kfd2kgd->free_mem(kq->dev->kgd, (struct kgd_mem *) kq->rptr_mem);
-       kfd2kgd->free_mem(kq->dev->kgd, (struct kgd_mem *) kq->wptr_mem);
-       kfd2kgd->free_mem(kq->dev->kgd, (struct kgd_mem *) kq->pq);
+       kfd_gtt_sa_free(kq->dev, kq->rptr_mem);
+       kfd_gtt_sa_free(kq->dev, kq->wptr_mem);
+       kq->ops_asic_specific.uninitialize(kq);
+       kfd_gtt_sa_free(kq->dev, kq->pq);
        kfd_release_kernel_doorbell(kq->dev,
                                        kq->queue->properties.doorbell_ptr);
        uninit_queue(kq->queue);
@@ -265,28 +262,6 @@ static void submit_packet(struct kernel_queue *kq)
                                kq->pending_wptr);
 }
 
-static int sync_with_hw(struct kernel_queue *kq, unsigned long timeout_ms)
-{
-       unsigned long org_timeout_ms;
-
-       BUG_ON(!kq);
-
-       org_timeout_ms = timeout_ms;
-       timeout_ms += jiffies * 1000 / HZ;
-       while (*kq->wptr_kernel != *kq->rptr_kernel) {
-               if (time_after(jiffies * 1000 / HZ, timeout_ms)) {
-                       pr_err("kfd: kernel_queue %s timeout expired %lu\n",
-                               __func__, org_timeout_ms);
-                       pr_err("kfd: wptr: %d rptr: %d\n",
-                               *kq->wptr_kernel, *kq->rptr_kernel);
-                       return -ETIME;
-               }
-               schedule();
-       }
-
-       return 0;
-}
-
 static void rollback_packet(struct kernel_queue *kq)
 {
        BUG_ON(!kq);
@@ -304,14 +279,20 @@ struct kernel_queue *kernel_queue_init(struct kfd_dev *dev,
        if (!kq)
                return NULL;
 
-       kq->initialize = initialize;
-       kq->uninitialize = uninitialize;
-       kq->acquire_packet_buffer = acquire_packet_buffer;
-       kq->submit_packet = submit_packet;
-       kq->sync_with_hw = sync_with_hw;
-       kq->rollback_packet = rollback_packet;
+       kq->ops.initialize = initialize;
+       kq->ops.uninitialize = uninitialize;
+       kq->ops.acquire_packet_buffer = acquire_packet_buffer;
+       kq->ops.submit_packet = submit_packet;
+       kq->ops.rollback_packet = rollback_packet;
+
+       switch (dev->device_info->asic_family) {
+       case CHIP_CARRIZO:
+               kernel_queue_init_vi(&kq->ops_asic_specific);
+       case CHIP_KAVERI:
+               kernel_queue_init_cik(&kq->ops_asic_specific);
+       }
 
-       if (kq->initialize(kq, dev, type, KFD_KERNEL_QUEUE_SIZE) == false) {
+       if (kq->ops.initialize(kq, dev, type, KFD_KERNEL_QUEUE_SIZE) == false) {
                pr_err("kfd: failed to init kernel queue\n");
                kfree(kq);
                return NULL;
@@ -323,7 +304,7 @@ void kernel_queue_uninit(struct kernel_queue *kq)
 {
        BUG_ON(!kq);
 
-       kq->uninitialize(kq);
+       kq->ops.uninitialize(kq);
        kfree(kq);
 }
 
@@ -335,19 +316,18 @@ static __attribute__((unused)) void test_kq(struct kfd_dev *dev)
 
        BUG_ON(!dev);
 
-       pr_debug("kfd: starting kernel queue test\n");
+       pr_err("kfd: starting kernel queue test\n");
 
        kq = kernel_queue_init(dev, KFD_QUEUE_TYPE_HIQ);
        BUG_ON(!kq);
 
-       retval = kq->acquire_packet_buffer(kq, 5, &buffer);
+       retval = kq->ops.acquire_packet_buffer(kq, 5, &buffer);
        BUG_ON(retval != 0);
        for (i = 0; i < 5; i++)
                buffer[i] = kq->nop_packet;
-       kq->submit_packet(kq);
-       kq->sync_with_hw(kq, 1000);
+       kq->ops.submit_packet(kq);
 
-       pr_debug("kfd: ending kernel queue test\n");
+       pr_err("kfd: ending kernel queue test\n");
 }
 
 
index dcd2bdb68d44f2821dcd9c4bffbb4c658ed6a7e2..594053136ee4d44812784c6ac402ddef0cd66b65 100644 (file)
 #include <linux/types.h>
 #include "kfd_priv.h"
 
-struct kernel_queue {
-       /* interface */
+/**
+ * struct kernel_queue_ops
+ *
+ * @initialize: Initialize a kernel queue, including allocations of GART memory
+ * needed for the queue.
+ *
+ * @uninitialize: Uninitialize a kernel queue and free all its memory usages.
+ *
+ * @acquire_packet_buffer: Returns a pointer to the location in the kernel
+ * queue ring buffer where the calling function can write its packet. It is
+ * Guaranteed that there is enough space for that packet. It also updates the
+ * pending write pointer to that location so subsequent calls to
+ * acquire_packet_buffer will get a correct write pointer
+ *
+ * @submit_packet: Update the write pointer and doorbell of a kernel queue.
+ *
+ * @sync_with_hw: Wait until the write pointer and the read pointer of a kernel
+ * queue are equal, which means the CP has read all the submitted packets.
+ *
+ * @rollback_packet: This routine is called if we failed to build an acquired
+ * packet for some reason. It just overwrites the pending wptr with the current
+ * one
+ *
+ */
+struct kernel_queue_ops {
        bool    (*initialize)(struct kernel_queue *kq, struct kfd_dev *dev,
                        enum kfd_queue_type type, unsigned int queue_size);
        void    (*uninitialize)(struct kernel_queue *kq);
@@ -38,9 +61,12 @@ struct kernel_queue {
                                        unsigned int **buffer_ptr);
 
        void    (*submit_packet)(struct kernel_queue *kq);
-       int     (*sync_with_hw)(struct kernel_queue *kq,
-                               unsigned long timeout_ms);
        void    (*rollback_packet)(struct kernel_queue *kq);
+};
+
+struct kernel_queue {
+       struct kernel_queue_ops ops;
+       struct kernel_queue_ops ops_asic_specific;
 
        /* data */
        struct kfd_dev          *dev;
@@ -58,6 +84,9 @@ struct kernel_queue {
        struct kfd_mem_obj      *pq;
        uint64_t                pq_gpu_addr;
        uint32_t                *pq_kernel_addr;
+       struct kfd_mem_obj      *eop_mem;
+       uint64_t                eop_gpu_addr;
+       uint32_t                *eop_kernel_addr;
 
        struct kfd_mem_obj      *fence_mem_obj;
        uint64_t                fence_gpu_addr;
@@ -66,4 +95,7 @@ struct kernel_queue {
        struct list_head        list;
 };
 
+void kernel_queue_init_cik(struct kernel_queue_ops *ops);
+void kernel_queue_init_vi(struct kernel_queue_ops *ops);
+
 #endif /* KFD_KERNEL_QUEUE_H_ */
diff --git a/drivers/gpu/drm/amd/amdkfd/kfd_kernel_queue_cik.c b/drivers/gpu/drm/amd/amdkfd/kfd_kernel_queue_cik.c
new file mode 100644 (file)
index 0000000..a90eb44
--- /dev/null
@@ -0,0 +1,44 @@
+/*
+ * Copyright 2014 Advanced Micro Devices, 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.
+ *
+ */
+
+#include "kfd_kernel_queue.h"
+
+static bool initialize_cik(struct kernel_queue *kq, struct kfd_dev *dev,
+                       enum kfd_queue_type type, unsigned int queue_size);
+static void uninitialize_cik(struct kernel_queue *kq);
+
+void kernel_queue_init_cik(struct kernel_queue_ops *ops)
+{
+       ops->initialize = initialize_cik;
+       ops->uninitialize = uninitialize_cik;
+}
+
+static bool initialize_cik(struct kernel_queue *kq, struct kfd_dev *dev,
+                       enum kfd_queue_type type, unsigned int queue_size)
+{
+       return true;
+}
+
+static void uninitialize_cik(struct kernel_queue *kq)
+{
+}
diff --git a/drivers/gpu/drm/amd/amdkfd/kfd_kernel_queue_vi.c b/drivers/gpu/drm/amd/amdkfd/kfd_kernel_queue_vi.c
new file mode 100644 (file)
index 0000000..f1d4828
--- /dev/null
@@ -0,0 +1,56 @@
+/*
+ * Copyright 2014 Advanced Micro Devices, 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.
+ *
+ */
+
+#include "kfd_kernel_queue.h"
+
+static bool initialize_vi(struct kernel_queue *kq, struct kfd_dev *dev,
+                       enum kfd_queue_type type, unsigned int queue_size);
+static void uninitialize_vi(struct kernel_queue *kq);
+
+void kernel_queue_init_vi(struct kernel_queue_ops *ops)
+{
+       ops->initialize = initialize_vi;
+       ops->uninitialize = uninitialize_vi;
+}
+
+static bool initialize_vi(struct kernel_queue *kq, struct kfd_dev *dev,
+                       enum kfd_queue_type type, unsigned int queue_size)
+{
+       int retval;
+
+       retval = kfd_gtt_sa_allocate(dev, PAGE_SIZE, &kq->eop_mem);
+       if (retval != 0)
+               return false;
+
+       kq->eop_gpu_addr = kq->eop_mem->gpu_addr;
+       kq->eop_kernel_addr = kq->eop_mem->cpu_ptr;
+
+       memset(kq->eop_kernel_addr, 0, PAGE_SIZE);
+
+       return true;
+}
+
+static void uninitialize_vi(struct kernel_queue *kq)
+{
+       kfd_gtt_sa_free(kq->dev, kq->eop_mem);
+}
index 95d5af138e6e7f2bcbd8d76351f7e12827031189..14c4115c4ae1e86b85a14fda29d9a6f34df23854 100644 (file)
@@ -48,7 +48,7 @@ static const struct kgd2kfd_calls kgd2kfd = {
 int sched_policy = KFD_SCHED_POLICY_HWS;
 module_param(sched_policy, int, 0444);
 MODULE_PARM_DESC(sched_policy,
-       "Kernel cmdline parameter that defines the amdkfd scheduling policy");
+       "Scheduling policy (0 = HWS (Default), 1 = HWS without over-subscription, 2 = Non-HWS (Used for debugging only)");
 
 int max_num_of_processes = KFD_MAX_NUM_OF_PROCESSES_DEFAULT;
 module_param(max_num_of_processes, int, 0444);
index 4c3828cf45bf71fbbae7e26f21f22bcd927fadce..b1ef1368c3bbb0bb7900601f43681ee99a83e69c 100644 (file)
  *
  */
 
-#include <linux/printk.h>
-#include <linux/slab.h>
 #include "kfd_priv.h"
-#include "kfd_mqd_manager.h"
-#include "cik_regs.h"
-#include "../../radeon/cik_reg.h"
-
-inline void busy_wait(unsigned long ms)
-{
-       while (time_before(jiffies, ms))
-               cpu_relax();
-}
-
-static inline struct cik_mqd *get_mqd(void *mqd)
-{
-       return (struct cik_mqd *)mqd;
-}
-
-static int init_mqd(struct mqd_manager *mm, void **mqd,
-               struct kfd_mem_obj **mqd_mem_obj, uint64_t *gart_addr,
-               struct queue_properties *q)
-{
-       uint64_t addr;
-       struct cik_mqd *m;
-       int retval;
-
-       BUG_ON(!mm || !q || !mqd);
-
-       pr_debug("kfd: In func %s\n", __func__);
-
-       retval = kfd2kgd->allocate_mem(mm->dev->kgd,
-                                       sizeof(struct cik_mqd),
-                                       256,
-                                       KFD_MEMPOOL_SYSTEM_WRITECOMBINE,
-                                       (struct kgd_mem **) mqd_mem_obj);
-
-       if (retval != 0)
-               return -ENOMEM;
-
-       m = (struct cik_mqd *) (*mqd_mem_obj)->cpu_ptr;
-       addr = (*mqd_mem_obj)->gpu_addr;
-
-       memset(m, 0, ALIGN(sizeof(struct cik_mqd), 256));
-
-       m->header = 0xC0310800;
-       m->compute_pipelinestat_enable = 1;
-       m->compute_static_thread_mgmt_se0 = 0xFFFFFFFF;
-       m->compute_static_thread_mgmt_se1 = 0xFFFFFFFF;
-       m->compute_static_thread_mgmt_se2 = 0xFFFFFFFF;
-       m->compute_static_thread_mgmt_se3 = 0xFFFFFFFF;
-
-       /*
-        * Make sure to use the last queue state saved on mqd when the cp
-        * reassigns the queue, so when queue is switched on/off (e.g over
-        * subscription or quantum timeout) the context will be consistent
-        */
-       m->cp_hqd_persistent_state =
-                               DEFAULT_CP_HQD_PERSISTENT_STATE | PRELOAD_REQ;
-
-       m->cp_mqd_control             = MQD_CONTROL_PRIV_STATE_EN;
-       m->cp_mqd_base_addr_lo        = lower_32_bits(addr);
-       m->cp_mqd_base_addr_hi        = upper_32_bits(addr);
-
-       m->cp_hqd_ib_control = DEFAULT_MIN_IB_AVAIL_SIZE | IB_ATC_EN;
-       /* Although WinKFD writes this, I suspect it should not be necessary */
-       m->cp_hqd_ib_control = IB_ATC_EN | DEFAULT_MIN_IB_AVAIL_SIZE;
-
-       m->cp_hqd_quantum = QUANTUM_EN | QUANTUM_SCALE_1MS |
-                               QUANTUM_DURATION(10);
-
-       /*
-        * Pipe Priority
-        * Identifies the pipe relative priority when this queue is connected
-        * to the pipeline. The pipe priority is against the GFX pipe and HP3D.
-        * In KFD we are using a fixed pipe priority set to CS_MEDIUM.
-        * 0 = CS_LOW (typically below GFX)
-        * 1 = CS_MEDIUM (typically between HP3D and GFX
-        * 2 = CS_HIGH (typically above HP3D)
-        */
-       m->cp_hqd_pipe_priority = 1;
-       m->cp_hqd_queue_priority = 15;
-
-       *mqd = m;
-       if (gart_addr != NULL)
-               *gart_addr = addr;
-       retval = mm->update_mqd(mm, m, q);
-
-       return retval;
-}
-
-static void uninit_mqd(struct mqd_manager *mm, void *mqd,
-                       struct kfd_mem_obj *mqd_mem_obj)
-{
-       BUG_ON(!mm || !mqd);
-       kfd2kgd->free_mem(mm->dev->kgd, (struct kgd_mem *) mqd_mem_obj);
-}
-
-static int load_mqd(struct mqd_manager *mm, void *mqd, uint32_t pipe_id,
-                       uint32_t queue_id, uint32_t __user *wptr)
-{
-       return kfd2kgd->hqd_load(mm->dev->kgd, mqd, pipe_id, queue_id, wptr);
-
-}
-
-static int update_mqd(struct mqd_manager *mm, void *mqd,
-                       struct queue_properties *q)
-{
-       struct cik_mqd *m;
-
-       BUG_ON(!mm || !q || !mqd);
-
-       pr_debug("kfd: In func %s\n", __func__);
-
-       m = get_mqd(mqd);
-       m->cp_hqd_pq_control = DEFAULT_RPTR_BLOCK_SIZE |
-                               DEFAULT_MIN_AVAIL_SIZE | PQ_ATC_EN;
-
-       /*
-        * Calculating queue size which is log base 2 of actual queue size -1
-        * dwords and another -1 for ffs
-        */
-       m->cp_hqd_pq_control |= ffs(q->queue_size / sizeof(unsigned int))
-                                                               - 1 - 1;
-       m->cp_hqd_pq_base_lo = lower_32_bits((uint64_t)q->queue_address >> 8);
-       m->cp_hqd_pq_base_hi = upper_32_bits((uint64_t)q->queue_address >> 8);
-       m->cp_hqd_pq_rptr_report_addr_lo = lower_32_bits((uint64_t)q->read_ptr);
-       m->cp_hqd_pq_rptr_report_addr_hi = upper_32_bits((uint64_t)q->read_ptr);
-       m->cp_hqd_pq_doorbell_control = DOORBELL_EN |
-                                       DOORBELL_OFFSET(q->doorbell_off);
-
-       m->cp_hqd_vmid = q->vmid;
-
-       if (q->format == KFD_QUEUE_FORMAT_AQL) {
-               m->cp_hqd_iq_rptr = AQL_ENABLE;
-               m->cp_hqd_pq_control |= NO_UPDATE_RPTR;
-       }
-
-       m->cp_hqd_active = 0;
-       q->is_active = false;
-       if (q->queue_size > 0 &&
-                       q->queue_address != 0 &&
-                       q->queue_percent > 0) {
-               m->cp_hqd_active = 1;
-               q->is_active = true;
-       }
-
-       return 0;
-}
-
-static int destroy_mqd(struct mqd_manager *mm, void *mqd,
-                       enum kfd_preempt_type type,
-                       unsigned int timeout, uint32_t pipe_id,
-                       uint32_t queue_id)
-{
-       return kfd2kgd->hqd_destroy(mm->dev->kgd, type, timeout,
-                                       pipe_id, queue_id);
-}
-
-static bool is_occupied(struct mqd_manager *mm, void *mqd,
-                       uint64_t queue_address, uint32_t pipe_id,
-                       uint32_t queue_id)
-{
-
-       return kfd2kgd->hqd_is_occupied(mm->dev->kgd, queue_address,
-                                       pipe_id, queue_id);
-
-}
-
-/*
- * HIQ MQD Implementation, concrete implementation for HIQ MQD implementation.
- * The HIQ queue in Kaveri is using the same MQD structure as all the user mode
- * queues but with different initial values.
- */
-
-static int init_mqd_hiq(struct mqd_manager *mm, void **mqd,
-               struct kfd_mem_obj **mqd_mem_obj, uint64_t *gart_addr,
-               struct queue_properties *q)
-{
-       uint64_t addr;
-       struct cik_mqd *m;
-       int retval;
-
-       BUG_ON(!mm || !q || !mqd || !mqd_mem_obj);
-
-       pr_debug("kfd: In func %s\n", __func__);
-
-       retval = kfd2kgd->allocate_mem(mm->dev->kgd,
-                                       sizeof(struct cik_mqd),
-                                       256,
-                                       KFD_MEMPOOL_SYSTEM_WRITECOMBINE,
-                                       (struct kgd_mem **) mqd_mem_obj);
-
-       if (retval != 0)
-               return -ENOMEM;
-
-       m = (struct cik_mqd *) (*mqd_mem_obj)->cpu_ptr;
-       addr = (*mqd_mem_obj)->gpu_addr;
-
-       memset(m, 0, ALIGN(sizeof(struct cik_mqd), 256));
-
-       m->header = 0xC0310800;
-       m->compute_pipelinestat_enable = 1;
-       m->compute_static_thread_mgmt_se0 = 0xFFFFFFFF;
-       m->compute_static_thread_mgmt_se1 = 0xFFFFFFFF;
-       m->compute_static_thread_mgmt_se2 = 0xFFFFFFFF;
-       m->compute_static_thread_mgmt_se3 = 0xFFFFFFFF;
-
-       m->cp_hqd_persistent_state = DEFAULT_CP_HQD_PERSISTENT_STATE |
-                                       PRELOAD_REQ;
-       m->cp_hqd_quantum = QUANTUM_EN | QUANTUM_SCALE_1MS |
-                               QUANTUM_DURATION(10);
-
-       m->cp_mqd_control             = MQD_CONTROL_PRIV_STATE_EN;
-       m->cp_mqd_base_addr_lo        = lower_32_bits(addr);
-       m->cp_mqd_base_addr_hi        = upper_32_bits(addr);
-
-       m->cp_hqd_ib_control = DEFAULT_MIN_IB_AVAIL_SIZE;
-
-       /*
-        * Pipe Priority
-        * Identifies the pipe relative priority when this queue is connected
-        * to the pipeline. The pipe priority is against the GFX pipe and HP3D.
-        * In KFD we are using a fixed pipe priority set to CS_MEDIUM.
-        * 0 = CS_LOW (typically below GFX)
-        * 1 = CS_MEDIUM (typically between HP3D and GFX
-        * 2 = CS_HIGH (typically above HP3D)
-        */
-       m->cp_hqd_pipe_priority = 1;
-       m->cp_hqd_queue_priority = 15;
-
-       *mqd = m;
-       if (gart_addr)
-               *gart_addr = addr;
-       retval = mm->update_mqd(mm, m, q);
-
-       return retval;
-}
-
-static int update_mqd_hiq(struct mqd_manager *mm, void *mqd,
-                               struct queue_properties *q)
-{
-       struct cik_mqd *m;
-
-       BUG_ON(!mm || !q || !mqd);
-
-       pr_debug("kfd: In func %s\n", __func__);
-
-       m = get_mqd(mqd);
-       m->cp_hqd_pq_control = DEFAULT_RPTR_BLOCK_SIZE |
-                               DEFAULT_MIN_AVAIL_SIZE |
-                               PRIV_STATE |
-                               KMD_QUEUE;
-
-       /*
-        * Calculating queue size which is log base 2 of actual queue
-        * size -1 dwords
-        */
-       m->cp_hqd_pq_control |= ffs(q->queue_size / sizeof(unsigned int))
-                                                               - 1 - 1;
-       m->cp_hqd_pq_base_lo = lower_32_bits((uint64_t)q->queue_address >> 8);
-       m->cp_hqd_pq_base_hi = upper_32_bits((uint64_t)q->queue_address >> 8);
-       m->cp_hqd_pq_rptr_report_addr_lo = lower_32_bits((uint64_t)q->read_ptr);
-       m->cp_hqd_pq_rptr_report_addr_hi = upper_32_bits((uint64_t)q->read_ptr);
-       m->cp_hqd_pq_doorbell_control = DOORBELL_EN |
-                                       DOORBELL_OFFSET(q->doorbell_off);
-
-       m->cp_hqd_vmid = q->vmid;
-
-       m->cp_hqd_active = 0;
-       q->is_active = false;
-       if (q->queue_size > 0 &&
-                       q->queue_address != 0 &&
-                       q->queue_percent > 0) {
-               m->cp_hqd_active = 1;
-               q->is_active = true;
-       }
-
-       return 0;
-}
 
 struct mqd_manager *mqd_manager_init(enum KFD_MQD_TYPE type,
                                        struct kfd_dev *dev)
 {
-       struct mqd_manager *mqd;
-
-       BUG_ON(!dev);
-       BUG_ON(type >= KFD_MQD_TYPE_MAX);
-
-       pr_debug("kfd: In func %s\n", __func__);
-
-       mqd = kzalloc(sizeof(struct mqd_manager), GFP_KERNEL);
-       if (!mqd)
-               return NULL;
-
-       mqd->dev = dev;
-
-       switch (type) {
-       case KFD_MQD_TYPE_CIK_CP:
-       case KFD_MQD_TYPE_CIK_COMPUTE:
-               mqd->init_mqd = init_mqd;
-               mqd->uninit_mqd = uninit_mqd;
-               mqd->load_mqd = load_mqd;
-               mqd->update_mqd = update_mqd;
-               mqd->destroy_mqd = destroy_mqd;
-               mqd->is_occupied = is_occupied;
-               break;
-       case KFD_MQD_TYPE_CIK_HIQ:
-               mqd->init_mqd = init_mqd_hiq;
-               mqd->uninit_mqd = uninit_mqd;
-               mqd->load_mqd = load_mqd;
-               mqd->update_mqd = update_mqd_hiq;
-               mqd->destroy_mqd = destroy_mqd;
-               mqd->is_occupied = is_occupied;
-               break;
-       default:
-               kfree(mqd);
-               return NULL;
+       switch (dev->device_info->asic_family) {
+       case CHIP_KAVERI:
+               return mqd_manager_init_cik(type, dev);
+       case CHIP_CARRIZO:
+               return mqd_manager_init_vi(type, dev);
        }
 
-       return mqd;
+       return NULL;
 }
-
-/* SDMA queues should be implemented here when the cp will supports them */
diff --git a/drivers/gpu/drm/amd/amdkfd/kfd_mqd_manager_cik.c b/drivers/gpu/drm/amd/amdkfd/kfd_mqd_manager_cik.c
new file mode 100644 (file)
index 0000000..a318743
--- /dev/null
@@ -0,0 +1,448 @@
+/*
+ * Copyright 2014 Advanced Micro Devices, 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.
+ *
+ */
+
+#include <linux/printk.h>
+#include <linux/slab.h>
+#include "kfd_priv.h"
+#include "kfd_mqd_manager.h"
+#include "cik_regs.h"
+#include "cik_structs.h"
+
+static inline struct cik_mqd *get_mqd(void *mqd)
+{
+       return (struct cik_mqd *)mqd;
+}
+
+static int init_mqd(struct mqd_manager *mm, void **mqd,
+               struct kfd_mem_obj **mqd_mem_obj, uint64_t *gart_addr,
+               struct queue_properties *q)
+{
+       uint64_t addr;
+       struct cik_mqd *m;
+       int retval;
+
+       BUG_ON(!mm || !q || !mqd);
+
+       pr_debug("kfd: In func %s\n", __func__);
+
+       retval = kfd_gtt_sa_allocate(mm->dev, sizeof(struct cik_mqd),
+                                       mqd_mem_obj);
+
+       if (retval != 0)
+               return -ENOMEM;
+
+       m = (struct cik_mqd *) (*mqd_mem_obj)->cpu_ptr;
+       addr = (*mqd_mem_obj)->gpu_addr;
+
+       memset(m, 0, ALIGN(sizeof(struct cik_mqd), 256));
+
+       m->header = 0xC0310800;
+       m->compute_pipelinestat_enable = 1;
+       m->compute_static_thread_mgmt_se0 = 0xFFFFFFFF;
+       m->compute_static_thread_mgmt_se1 = 0xFFFFFFFF;
+       m->compute_static_thread_mgmt_se2 = 0xFFFFFFFF;
+       m->compute_static_thread_mgmt_se3 = 0xFFFFFFFF;
+
+       /*
+        * Make sure to use the last queue state saved on mqd when the cp
+        * reassigns the queue, so when queue is switched on/off (e.g over
+        * subscription or quantum timeout) the context will be consistent
+        */
+       m->cp_hqd_persistent_state =
+                               DEFAULT_CP_HQD_PERSISTENT_STATE | PRELOAD_REQ;
+
+       m->cp_mqd_control             = MQD_CONTROL_PRIV_STATE_EN;
+       m->cp_mqd_base_addr_lo        = lower_32_bits(addr);
+       m->cp_mqd_base_addr_hi        = upper_32_bits(addr);
+
+       m->cp_hqd_ib_control = DEFAULT_MIN_IB_AVAIL_SIZE | IB_ATC_EN;
+       /* Although WinKFD writes this, I suspect it should not be necessary */
+       m->cp_hqd_ib_control = IB_ATC_EN | DEFAULT_MIN_IB_AVAIL_SIZE;
+
+       m->cp_hqd_quantum = QUANTUM_EN | QUANTUM_SCALE_1MS |
+                               QUANTUM_DURATION(10);
+
+       /*
+        * Pipe Priority
+        * Identifies the pipe relative priority when this queue is connected
+        * to the pipeline. The pipe priority is against the GFX pipe and HP3D.
+        * In KFD we are using a fixed pipe priority set to CS_MEDIUM.
+        * 0 = CS_LOW (typically below GFX)
+        * 1 = CS_MEDIUM (typically between HP3D and GFX
+        * 2 = CS_HIGH (typically above HP3D)
+        */
+       m->cp_hqd_pipe_priority = 1;
+       m->cp_hqd_queue_priority = 15;
+
+       *mqd = m;
+       if (gart_addr != NULL)
+               *gart_addr = addr;
+       retval = mm->update_mqd(mm, m, q);
+
+       return retval;
+}
+
+static int init_mqd_sdma(struct mqd_manager *mm, void **mqd,
+                       struct kfd_mem_obj **mqd_mem_obj, uint64_t *gart_addr,
+                       struct queue_properties *q)
+{
+       int retval;
+       struct cik_sdma_rlc_registers *m;
+
+       BUG_ON(!mm || !mqd || !mqd_mem_obj);
+
+       retval = kfd_gtt_sa_allocate(mm->dev,
+                                       sizeof(struct cik_sdma_rlc_registers),
+                                       mqd_mem_obj);
+
+       if (retval != 0)
+               return -ENOMEM;
+
+       m = (struct cik_sdma_rlc_registers *) (*mqd_mem_obj)->cpu_ptr;
+
+       memset(m, 0, sizeof(struct cik_sdma_rlc_registers));
+
+       *mqd = m;
+       if (gart_addr != NULL)
+               *gart_addr = (*mqd_mem_obj)->gpu_addr;
+
+       retval = mm->update_mqd(mm, m, q);
+
+       return retval;
+}
+
+static void uninit_mqd(struct mqd_manager *mm, void *mqd,
+                       struct kfd_mem_obj *mqd_mem_obj)
+{
+       BUG_ON(!mm || !mqd);
+       kfd_gtt_sa_free(mm->dev, mqd_mem_obj);
+}
+
+static void uninit_mqd_sdma(struct mqd_manager *mm, void *mqd,
+                               struct kfd_mem_obj *mqd_mem_obj)
+{
+       BUG_ON(!mm || !mqd);
+       kfd_gtt_sa_free(mm->dev, mqd_mem_obj);
+}
+
+static int load_mqd(struct mqd_manager *mm, void *mqd, uint32_t pipe_id,
+                       uint32_t queue_id, uint32_t __user *wptr)
+{
+       return kfd2kgd->hqd_load(mm->dev->kgd, mqd, pipe_id, queue_id, wptr);
+}
+
+static int load_mqd_sdma(struct mqd_manager *mm, void *mqd,
+                       uint32_t pipe_id, uint32_t queue_id,
+                       uint32_t __user *wptr)
+{
+       return kfd2kgd->hqd_sdma_load(mm->dev->kgd, mqd);
+}
+
+static int update_mqd(struct mqd_manager *mm, void *mqd,
+                       struct queue_properties *q)
+{
+       struct cik_mqd *m;
+
+       BUG_ON(!mm || !q || !mqd);
+
+       pr_debug("kfd: In func %s\n", __func__);
+
+       m = get_mqd(mqd);
+       m->cp_hqd_pq_control = DEFAULT_RPTR_BLOCK_SIZE |
+                               DEFAULT_MIN_AVAIL_SIZE | PQ_ATC_EN;
+
+       /*
+        * Calculating queue size which is log base 2 of actual queue size -1
+        * dwords and another -1 for ffs
+        */
+       m->cp_hqd_pq_control |= ffs(q->queue_size / sizeof(unsigned int))
+                                                               - 1 - 1;
+       m->cp_hqd_pq_base_lo = lower_32_bits((uint64_t)q->queue_address >> 8);
+       m->cp_hqd_pq_base_hi = upper_32_bits((uint64_t)q->queue_address >> 8);
+       m->cp_hqd_pq_rptr_report_addr_lo = lower_32_bits((uint64_t)q->read_ptr);
+       m->cp_hqd_pq_rptr_report_addr_hi = upper_32_bits((uint64_t)q->read_ptr);
+       m->cp_hqd_pq_doorbell_control = DOORBELL_EN |
+                                       DOORBELL_OFFSET(q->doorbell_off);
+
+       m->cp_hqd_vmid = q->vmid;
+
+       if (q->format == KFD_QUEUE_FORMAT_AQL) {
+               m->cp_hqd_iq_rptr = AQL_ENABLE;
+               m->cp_hqd_pq_control |= NO_UPDATE_RPTR;
+       }
+
+       m->cp_hqd_active = 0;
+       q->is_active = false;
+       if (q->queue_size > 0 &&
+                       q->queue_address != 0 &&
+                       q->queue_percent > 0) {
+               m->cp_hqd_active = 1;
+               q->is_active = true;
+       }
+
+       return 0;
+}
+
+static int update_mqd_sdma(struct mqd_manager *mm, void *mqd,
+                               struct queue_properties *q)
+{
+       struct cik_sdma_rlc_registers *m;
+
+       BUG_ON(!mm || !mqd || !q);
+
+       m = get_sdma_mqd(mqd);
+       m->sdma_rlc_rb_cntl =
+               SDMA_RB_SIZE((ffs(q->queue_size / sizeof(unsigned int)))) |
+               SDMA_RB_VMID(q->vmid) |
+               SDMA_RPTR_WRITEBACK_ENABLE |
+               SDMA_RPTR_WRITEBACK_TIMER(6);
+
+       m->sdma_rlc_rb_base = lower_32_bits(q->queue_address >> 8);
+       m->sdma_rlc_rb_base_hi = upper_32_bits(q->queue_address >> 8);
+       m->sdma_rlc_rb_rptr_addr_lo = lower_32_bits((uint64_t)q->read_ptr);
+       m->sdma_rlc_rb_rptr_addr_hi = upper_32_bits((uint64_t)q->read_ptr);
+       m->sdma_rlc_doorbell = SDMA_OFFSET(q->doorbell_off) | SDMA_DB_ENABLE;
+       m->sdma_rlc_virtual_addr = q->sdma_vm_addr;
+
+       m->sdma_engine_id = q->sdma_engine_id;
+       m->sdma_queue_id = q->sdma_queue_id;
+
+       q->is_active = false;
+       if (q->queue_size > 0 &&
+                       q->queue_address != 0 &&
+                       q->queue_percent > 0) {
+               m->sdma_rlc_rb_cntl |= SDMA_RB_ENABLE;
+               q->is_active = true;
+       }
+
+       return 0;
+}
+
+static int destroy_mqd(struct mqd_manager *mm, void *mqd,
+                       enum kfd_preempt_type type,
+                       unsigned int timeout, uint32_t pipe_id,
+                       uint32_t queue_id)
+{
+       return kfd2kgd->hqd_destroy(mm->dev->kgd, type, timeout,
+                                       pipe_id, queue_id);
+}
+
+/*
+ * preempt type here is ignored because there is only one way
+ * to preempt sdma queue
+ */
+static int destroy_mqd_sdma(struct mqd_manager *mm, void *mqd,
+                               enum kfd_preempt_type type,
+                               unsigned int timeout, uint32_t pipe_id,
+                               uint32_t queue_id)
+{
+       return kfd2kgd->hqd_sdma_destroy(mm->dev->kgd, mqd, timeout);
+}
+
+static bool is_occupied(struct mqd_manager *mm, void *mqd,
+                       uint64_t queue_address, uint32_t pipe_id,
+                       uint32_t queue_id)
+{
+
+       return kfd2kgd->hqd_is_occupied(mm->dev->kgd, queue_address,
+                                       pipe_id, queue_id);
+
+}
+
+static bool is_occupied_sdma(struct mqd_manager *mm, void *mqd,
+                       uint64_t queue_address, uint32_t pipe_id,
+                       uint32_t queue_id)
+{
+       return kfd2kgd->hqd_sdma_is_occupied(mm->dev->kgd, mqd);
+}
+
+/*
+ * HIQ MQD Implementation, concrete implementation for HIQ MQD implementation.
+ * The HIQ queue in Kaveri is using the same MQD structure as all the user mode
+ * queues but with different initial values.
+ */
+
+static int init_mqd_hiq(struct mqd_manager *mm, void **mqd,
+               struct kfd_mem_obj **mqd_mem_obj, uint64_t *gart_addr,
+               struct queue_properties *q)
+{
+       uint64_t addr;
+       struct cik_mqd *m;
+       int retval;
+
+       BUG_ON(!mm || !q || !mqd || !mqd_mem_obj);
+
+       pr_debug("kfd: In func %s\n", __func__);
+
+       retval = kfd_gtt_sa_allocate(mm->dev, sizeof(struct cik_mqd),
+                                       mqd_mem_obj);
+
+       if (retval != 0)
+               return -ENOMEM;
+
+       m = (struct cik_mqd *) (*mqd_mem_obj)->cpu_ptr;
+       addr = (*mqd_mem_obj)->gpu_addr;
+
+       memset(m, 0, ALIGN(sizeof(struct cik_mqd), 256));
+
+       m->header = 0xC0310800;
+       m->compute_pipelinestat_enable = 1;
+       m->compute_static_thread_mgmt_se0 = 0xFFFFFFFF;
+       m->compute_static_thread_mgmt_se1 = 0xFFFFFFFF;
+       m->compute_static_thread_mgmt_se2 = 0xFFFFFFFF;
+       m->compute_static_thread_mgmt_se3 = 0xFFFFFFFF;
+
+       m->cp_hqd_persistent_state = DEFAULT_CP_HQD_PERSISTENT_STATE |
+                                       PRELOAD_REQ;
+       m->cp_hqd_quantum = QUANTUM_EN | QUANTUM_SCALE_1MS |
+                               QUANTUM_DURATION(10);
+
+       m->cp_mqd_control             = MQD_CONTROL_PRIV_STATE_EN;
+       m->cp_mqd_base_addr_lo        = lower_32_bits(addr);
+       m->cp_mqd_base_addr_hi        = upper_32_bits(addr);
+
+       m->cp_hqd_ib_control = DEFAULT_MIN_IB_AVAIL_SIZE;
+
+       /*
+        * Pipe Priority
+        * Identifies the pipe relative priority when this queue is connected
+        * to the pipeline. The pipe priority is against the GFX pipe and HP3D.
+        * In KFD we are using a fixed pipe priority set to CS_MEDIUM.
+        * 0 = CS_LOW (typically below GFX)
+        * 1 = CS_MEDIUM (typically between HP3D and GFX
+        * 2 = CS_HIGH (typically above HP3D)
+        */
+       m->cp_hqd_pipe_priority = 1;
+       m->cp_hqd_queue_priority = 15;
+
+       *mqd = m;
+       if (gart_addr)
+               *gart_addr = addr;
+       retval = mm->update_mqd(mm, m, q);
+
+       return retval;
+}
+
+static int update_mqd_hiq(struct mqd_manager *mm, void *mqd,
+                               struct queue_properties *q)
+{
+       struct cik_mqd *m;
+
+       BUG_ON(!mm || !q || !mqd);
+
+       pr_debug("kfd: In func %s\n", __func__);
+
+       m = get_mqd(mqd);
+       m->cp_hqd_pq_control = DEFAULT_RPTR_BLOCK_SIZE |
+                               DEFAULT_MIN_AVAIL_SIZE |
+                               PRIV_STATE |
+                               KMD_QUEUE;
+
+       /*
+        * Calculating queue size which is log base 2 of actual queue
+        * size -1 dwords
+        */
+       m->cp_hqd_pq_control |= ffs(q->queue_size / sizeof(unsigned int))
+                                                               - 1 - 1;
+       m->cp_hqd_pq_base_lo = lower_32_bits((uint64_t)q->queue_address >> 8);
+       m->cp_hqd_pq_base_hi = upper_32_bits((uint64_t)q->queue_address >> 8);
+       m->cp_hqd_pq_rptr_report_addr_lo = lower_32_bits((uint64_t)q->read_ptr);
+       m->cp_hqd_pq_rptr_report_addr_hi = upper_32_bits((uint64_t)q->read_ptr);
+       m->cp_hqd_pq_doorbell_control = DOORBELL_EN |
+                                       DOORBELL_OFFSET(q->doorbell_off);
+
+       m->cp_hqd_vmid = q->vmid;
+
+       m->cp_hqd_active = 0;
+       q->is_active = false;
+       if (q->queue_size > 0 &&
+                       q->queue_address != 0 &&
+                       q->queue_percent > 0) {
+               m->cp_hqd_active = 1;
+               q->is_active = true;
+       }
+
+       return 0;
+}
+
+struct cik_sdma_rlc_registers *get_sdma_mqd(void *mqd)
+{
+       struct cik_sdma_rlc_registers *m;
+
+       BUG_ON(!mqd);
+
+       m = (struct cik_sdma_rlc_registers *)mqd;
+
+       return m;
+}
+
+struct mqd_manager *mqd_manager_init_cik(enum KFD_MQD_TYPE type,
+               struct kfd_dev *dev)
+{
+       struct mqd_manager *mqd;
+
+       BUG_ON(!dev);
+       BUG_ON(type >= KFD_MQD_TYPE_MAX);
+
+       pr_debug("kfd: In func %s\n", __func__);
+
+       mqd = kzalloc(sizeof(struct mqd_manager), GFP_KERNEL);
+       if (!mqd)
+               return NULL;
+
+       mqd->dev = dev;
+
+       switch (type) {
+       case KFD_MQD_TYPE_CP:
+       case KFD_MQD_TYPE_COMPUTE:
+               mqd->init_mqd = init_mqd;
+               mqd->uninit_mqd = uninit_mqd;
+               mqd->load_mqd = load_mqd;
+               mqd->update_mqd = update_mqd;
+               mqd->destroy_mqd = destroy_mqd;
+               mqd->is_occupied = is_occupied;
+               break;
+       case KFD_MQD_TYPE_HIQ:
+               mqd->init_mqd = init_mqd_hiq;
+               mqd->uninit_mqd = uninit_mqd;
+               mqd->load_mqd = load_mqd;
+               mqd->update_mqd = update_mqd_hiq;
+               mqd->destroy_mqd = destroy_mqd;
+               mqd->is_occupied = is_occupied;
+               break;
+       case KFD_MQD_TYPE_SDMA:
+               mqd->init_mqd = init_mqd_sdma;
+               mqd->uninit_mqd = uninit_mqd_sdma;
+               mqd->load_mqd = load_mqd_sdma;
+               mqd->update_mqd = update_mqd_sdma;
+               mqd->destroy_mqd = destroy_mqd_sdma;
+               mqd->is_occupied = is_occupied_sdma;
+               break;
+       default:
+               kfree(mqd);
+               return NULL;
+       }
+
+       return mqd;
+}
+
diff --git a/drivers/gpu/drm/amd/amdkfd/kfd_mqd_manager_vi.c b/drivers/gpu/drm/amd/amdkfd/kfd_mqd_manager_vi.c
new file mode 100644 (file)
index 0000000..b3a7e3b
--- /dev/null
@@ -0,0 +1,33 @@
+/*
+ * Copyright 2014 Advanced Micro Devices, 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.
+ *
+ */
+
+#include <linux/printk.h>
+#include "kfd_priv.h"
+#include "kfd_mqd_manager.h"
+
+struct mqd_manager *mqd_manager_init_vi(enum KFD_MQD_TYPE type,
+                                       struct kfd_dev *dev)
+{
+       pr_warn("amdkfd: VI MQD is not currently supported\n");
+       return NULL;
+}
index 5ce9233d2004e064f1a734d90a2ca33f3bd7880b..e2533d875f4311e2c6fa426b4ea606c981b1675b 100644 (file)
@@ -97,11 +97,8 @@ static int pm_allocate_runlist_ib(struct packet_manager *pm,
 
        pm_calc_rlib_size(pm, rl_buffer_size, is_over_subscription);
 
-       retval = kfd2kgd->allocate_mem(pm->dqm->dev->kgd,
-                                       *rl_buffer_size,
-                                       PAGE_SIZE,
-                                       KFD_MEMPOOL_SYSTEM_WRITECOMBINE,
-                                       (struct kgd_mem **) &pm->ib_buffer_obj);
+       retval = kfd_gtt_sa_allocate(pm->dqm->dev, *rl_buffer_size,
+                                       &pm->ib_buffer_obj);
 
        if (retval != 0) {
                pr_err("kfd: failed to allocate runlist IB\n");
@@ -351,7 +348,7 @@ int pm_send_set_resources(struct packet_manager *pm,
        pr_debug("kfd: In func %s\n", __func__);
 
        mutex_lock(&pm->lock);
-       pm->priv_queue->acquire_packet_buffer(pm->priv_queue,
+       pm->priv_queue->ops.acquire_packet_buffer(pm->priv_queue,
                                        sizeof(*packet) / sizeof(uint32_t),
                        (unsigned int **)&packet);
        if (packet == NULL) {
@@ -378,8 +375,7 @@ int pm_send_set_resources(struct packet_manager *pm,
        packet->queue_mask_lo = lower_32_bits(res->queue_mask);
        packet->queue_mask_hi = upper_32_bits(res->queue_mask);
 
-       pm->priv_queue->submit_packet(pm->priv_queue);
-       pm->priv_queue->sync_with_hw(pm->priv_queue, KFD_HIQ_TIMEOUT);
+       pm->priv_queue->ops.submit_packet(pm->priv_queue);
 
        mutex_unlock(&pm->lock);
 
@@ -405,7 +401,7 @@ int pm_send_runlist(struct packet_manager *pm, struct list_head *dqm_queues)
        packet_size_dwords = sizeof(struct pm4_runlist) / sizeof(uint32_t);
        mutex_lock(&pm->lock);
 
-       retval = pm->priv_queue->acquire_packet_buffer(pm->priv_queue,
+       retval = pm->priv_queue->ops.acquire_packet_buffer(pm->priv_queue,
                                        packet_size_dwords, &rl_buffer);
        if (retval != 0)
                goto fail_acquire_packet_buffer;
@@ -415,15 +411,14 @@ int pm_send_runlist(struct packet_manager *pm, struct list_head *dqm_queues)
        if (retval != 0)
                goto fail_create_runlist;
 
-       pm->priv_queue->submit_packet(pm->priv_queue);
-       pm->priv_queue->sync_with_hw(pm->priv_queue, KFD_HIQ_TIMEOUT);
+       pm->priv_queue->ops.submit_packet(pm->priv_queue);
 
        mutex_unlock(&pm->lock);
 
        return retval;
 
 fail_create_runlist:
-       pm->priv_queue->rollback_packet(pm->priv_queue);
+       pm->priv_queue->ops.rollback_packet(pm->priv_queue);
 fail_acquire_packet_buffer:
        mutex_unlock(&pm->lock);
 fail_create_runlist_ib:
@@ -441,7 +436,7 @@ int pm_send_query_status(struct packet_manager *pm, uint64_t fence_address,
        BUG_ON(!pm || !fence_address);
 
        mutex_lock(&pm->lock);
-       retval = pm->priv_queue->acquire_packet_buffer(
+       retval = pm->priv_queue->ops.acquire_packet_buffer(
                        pm->priv_queue,
                        sizeof(struct pm4_query_status) / sizeof(uint32_t),
                        (unsigned int **)&packet);
@@ -462,8 +457,7 @@ int pm_send_query_status(struct packet_manager *pm, uint64_t fence_address,
        packet->data_hi = upper_32_bits((uint64_t)fence_value);
        packet->data_lo = lower_32_bits((uint64_t)fence_value);
 
-       pm->priv_queue->submit_packet(pm->priv_queue);
-       pm->priv_queue->sync_with_hw(pm->priv_queue, KFD_HIQ_TIMEOUT);
+       pm->priv_queue->ops.submit_packet(pm->priv_queue);
        mutex_unlock(&pm->lock);
 
        return 0;
@@ -485,7 +479,7 @@ int pm_send_unmap_queue(struct packet_manager *pm, enum kfd_queue_type type,
        BUG_ON(!pm);
 
        mutex_lock(&pm->lock);
-       retval = pm->priv_queue->acquire_packet_buffer(
+       retval = pm->priv_queue->ops.acquire_packet_buffer(
                        pm->priv_queue,
                        sizeof(struct pm4_unmap_queues) / sizeof(uint32_t),
                        &buffer);
@@ -540,8 +534,7 @@ int pm_send_unmap_queue(struct packet_manager *pm, enum kfd_queue_type type,
                break;
        };
 
-       pm->priv_queue->submit_packet(pm->priv_queue);
-       pm->priv_queue->sync_with_hw(pm->priv_queue, KFD_HIQ_TIMEOUT);
+       pm->priv_queue->ops.submit_packet(pm->priv_queue);
 
        mutex_unlock(&pm->lock);
        return 0;
@@ -557,8 +550,7 @@ void pm_release_ib(struct packet_manager *pm)
 
        mutex_lock(&pm->lock);
        if (pm->allocated) {
-               kfd2kgd->free_mem(pm->dqm->dev->kgd,
-                               (struct kgd_mem *) pm->ib_buffer_obj);
+               kfd_gtt_sa_free(pm->dqm->dev, pm->ib_buffer_obj);
                pm->allocated = false;
        }
        mutex_unlock(&pm->lock);
index a5edb29507e310af8ebe437ef2a22fb218687ad1..1b35a9c87437d89cf761c5d2e9e992ffe7813ae3 100644 (file)
@@ -104,12 +104,26 @@ enum cache_policy {
        cache_policy_noncoherent
 };
 
+enum asic_family_type {
+       CHIP_KAVERI = 0,
+       CHIP_CARRIZO
+};
+
 struct kfd_device_info {
+       unsigned int asic_family;
        unsigned int max_pasid_bits;
        size_t ih_ring_entry_size;
+       uint8_t num_of_watch_points;
        uint16_t mqd_size_aligned;
 };
 
+struct kfd_mem_obj {
+       uint32_t range_start;
+       uint32_t range_end;
+       uint64_t gpu_addr;
+       uint32_t *cpu_ptr;
+};
+
 struct kfd_dev {
        struct kgd_dev *kgd;
 
@@ -135,22 +149,18 @@ struct kfd_dev {
 
        struct kgd2kfd_shared_resources shared_resources;
 
-       void *interrupt_ring;
-       size_t interrupt_ring_size;
-       atomic_t interrupt_ring_rptr;
-       atomic_t interrupt_ring_wptr;
-       struct work_struct interrupt_work;
-       spinlock_t interrupt_lock;
+       void *gtt_mem;
+       uint64_t gtt_start_gpu_addr;
+       void *gtt_start_cpu_ptr;
+       void *gtt_sa_bitmap;
+       struct mutex gtt_sa_lock;
+       unsigned int gtt_sa_chunk_size;
+       unsigned int gtt_sa_num_of_chunks;
 
        /* QCM Device instance */
        struct device_queue_manager *dqm;
 
        bool init_complete;
-       /*
-        * Interrupts of interest to KFD are copied
-        * from the HW ring into a SW ring.
-        */
-       bool interrupts_active;
 };
 
 /* KGD2KFD callbacks */
@@ -162,12 +172,6 @@ void kgd2kfd_device_exit(struct kfd_dev *kfd);
 
 extern const struct kfd2kgd_calls *kfd2kgd;
 
-struct kfd_mem_obj {
-       void *bo;
-       uint64_t gpu_addr;
-       uint32_t *cpu_ptr;
-};
-
 enum kfd_mempool {
        KFD_MEMPOOL_SYSTEM_CACHEABLE = 1,
        KFD_MEMPOOL_SYSTEM_WRITECOMBINE = 2,
@@ -285,6 +289,15 @@ struct queue_properties {
        bool is_active;
        /* Not relevant for user mode queues in cp scheduling */
        unsigned int vmid;
+       /* Relevant only for sdma queues*/
+       uint32_t sdma_engine_id;
+       uint32_t sdma_queue_id;
+       uint32_t sdma_vm_addr;
+       /* Relevant only for VI */
+       uint64_t eop_ring_buffer_address;
+       uint32_t eop_ring_buffer_size;
+       uint64_t ctx_save_restore_area_address;
+       uint32_t ctx_save_restore_area_size;
 };
 
 /**
@@ -327,6 +340,8 @@ struct queue {
        uint32_t pipe;
        uint32_t queue;
 
+       unsigned int sdma_id;
+
        struct kfd_process      *process;
        struct kfd_dev          *device;
 };
@@ -335,10 +350,10 @@ struct queue {
  * Please read the kfd_mqd_manager.h description.
  */
 enum KFD_MQD_TYPE {
-       KFD_MQD_TYPE_CIK_COMPUTE = 0, /* for no cp scheduling */
-       KFD_MQD_TYPE_CIK_HIQ, /* for hiq */
-       KFD_MQD_TYPE_CIK_CP, /* for cp queues and diq */
-       KFD_MQD_TYPE_CIK_SDMA, /* for sdma queues */
+       KFD_MQD_TYPE_COMPUTE = 0,       /* for no cp scheduling */
+       KFD_MQD_TYPE_HIQ,               /* for hiq */
+       KFD_MQD_TYPE_CP,                /* for cp queues and diq */
+       KFD_MQD_TYPE_SDMA,              /* for sdma queues */
        KFD_MQD_TYPE_MAX
 };
 
@@ -490,8 +505,9 @@ struct kfd_process_device *kfd_bind_process_to_device(struct kfd_dev *dev,
                                                        struct kfd_process *p);
 void kfd_unbind_process_from_device(struct kfd_dev *dev, unsigned int pasid);
 struct kfd_process_device *kfd_get_process_device_data(struct kfd_dev *dev,
-                                                       struct kfd_process *p,
-                                                       int create_pdd);
+                                                       struct kfd_process *p);
+struct kfd_process_device *kfd_create_process_device_data(struct kfd_dev *dev,
+                                                       struct kfd_process *p);
 
 /* Process device data iterator */
 struct kfd_process_device *kfd_get_first_process_device_data(struct kfd_process *p);
@@ -519,6 +535,13 @@ unsigned int kfd_queue_id_to_doorbell(struct kfd_dev *kfd,
                                        struct kfd_process *process,
                                        unsigned int queue_id);
 
+/* GTT Sub-Allocator */
+
+int kfd_gtt_sa_allocate(struct kfd_dev *kfd, unsigned int size,
+                       struct kfd_mem_obj **mem_obj);
+
+int kfd_gtt_sa_free(struct kfd_dev *kfd, struct kfd_mem_obj *mem_obj);
+
 extern struct device *kfd_device;
 
 /* Topology */
@@ -531,10 +554,7 @@ struct kfd_dev *kfd_device_by_pci_dev(const struct pci_dev *pdev);
 struct kfd_dev *kfd_topology_enum_kfd_devices(uint8_t idx);
 
 /* Interrupts */
-int kfd_interrupt_init(struct kfd_dev *dev);
-void kfd_interrupt_exit(struct kfd_dev *dev);
 void kgd2kfd_interrupt(struct kfd_dev *kfd, const void *ih_ring_entry);
-bool enqueue_ih_ring_entry(struct kfd_dev *kfd,        const void *ih_ring_entry);
 
 /* Power Management */
 void kgd2kfd_suspend(struct kfd_dev *kfd);
@@ -546,6 +566,8 @@ int kfd_init_apertures(struct kfd_process *process);
 /* Queue Context Management */
 inline uint32_t lower_32(uint64_t x);
 inline uint32_t upper_32(uint64_t x);
+struct cik_sdma_rlc_registers *get_sdma_mqd(void *mqd);
+inline uint32_t get_sdma_base_addr(struct cik_sdma_rlc_registers *m);
 
 int init_queue(struct queue **q, struct queue_properties properties);
 void uninit_queue(struct queue *q);
@@ -554,6 +576,10 @@ void print_queue(struct queue *q);
 
 struct mqd_manager *mqd_manager_init(enum KFD_MQD_TYPE type,
                                        struct kfd_dev *dev);
+struct mqd_manager *mqd_manager_init_cik(enum KFD_MQD_TYPE type,
+               struct kfd_dev *dev);
+struct mqd_manager *mqd_manager_init_vi(enum KFD_MQD_TYPE type,
+               struct kfd_dev *dev);
 struct device_queue_manager *device_queue_manager_init(struct kfd_dev *dev);
 void device_queue_manager_uninit(struct device_queue_manager *dqm);
 struct kernel_queue *kernel_queue_init(struct kfd_dev *dev,
index 3c76ef05cbcf798483b482ac09b7bc62223d92c5..a369c149d1727e78cb67413578e6fe7ddd11d614 100644 (file)
@@ -311,24 +311,29 @@ err_alloc_process:
 }
 
 struct kfd_process_device *kfd_get_process_device_data(struct kfd_dev *dev,
-                                                       struct kfd_process *p,
-                                                       int create_pdd)
+                                                       struct kfd_process *p)
 {
        struct kfd_process_device *pdd = NULL;
 
        list_for_each_entry(pdd, &p->per_device_data, per_device_list)
                if (pdd->dev == dev)
-                       return pdd;
-
-       if (create_pdd) {
-               pdd = kzalloc(sizeof(*pdd), GFP_KERNEL);
-               if (pdd != NULL) {
-                       pdd->dev = dev;
-                       INIT_LIST_HEAD(&pdd->qpd.queues_list);
-                       INIT_LIST_HEAD(&pdd->qpd.priv_queue_list);
-                       pdd->qpd.dqm = dev->dqm;
-                       list_add(&pdd->per_device_list, &p->per_device_data);
-               }
+                       break;
+
+       return pdd;
+}
+
+struct kfd_process_device *kfd_create_process_device_data(struct kfd_dev *dev,
+                                                       struct kfd_process *p)
+{
+       struct kfd_process_device *pdd = NULL;
+
+       pdd = kzalloc(sizeof(*pdd), GFP_KERNEL);
+       if (pdd != NULL) {
+               pdd->dev = dev;
+               INIT_LIST_HEAD(&pdd->qpd.queues_list);
+               INIT_LIST_HEAD(&pdd->qpd.priv_queue_list);
+               pdd->qpd.dqm = dev->dqm;
+               list_add(&pdd->per_device_list, &p->per_device_data);
        }
 
        return pdd;
@@ -344,11 +349,14 @@ struct kfd_process_device *kfd_get_process_device_data(struct kfd_dev *dev,
 struct kfd_process_device *kfd_bind_process_to_device(struct kfd_dev *dev,
                                                        struct kfd_process *p)
 {
-       struct kfd_process_device *pdd = kfd_get_process_device_data(dev, p, 1);
+       struct kfd_process_device *pdd;
        int err;
 
-       if (pdd == NULL)
+       pdd = kfd_get_process_device_data(dev, p);
+       if (!pdd) {
+               pr_err("Process device data doesn't exist\n");
                return ERR_PTR(-ENOMEM);
+       }
 
        if (pdd->bound)
                return pdd;
@@ -384,7 +392,7 @@ void kfd_unbind_process_from_device(struct kfd_dev *dev, unsigned int pasid)
 
        pqm_uninit(&p->pqm);
 
-       pdd = kfd_get_process_device_data(dev, p, 0);
+       pdd = kfd_get_process_device_data(dev, p);
 
        /*
         * Just mark pdd as unbound, because we still need it to call
index 47526780d736ced5470bfb2822a3892f879b0320..513eeb6e402a8513f5d1b0ff1875b77d2c50e603 100644 (file)
@@ -128,7 +128,6 @@ static int create_cp_queue(struct process_queue_manager *pqm,
        /* let DQM handle it*/
        q_properties->vmid = 0;
        q_properties->queue_id = qid;
-       q_properties->type = KFD_QUEUE_TYPE_COMPUTE;
 
        retval = init_queue(q, *q_properties);
        if (retval != 0)
@@ -167,8 +166,11 @@ int pqm_create_queue(struct process_queue_manager *pqm,
        q = NULL;
        kq = NULL;
 
-       pdd = kfd_get_process_device_data(dev, pqm->process, 1);
-       BUG_ON(!pdd);
+       pdd = kfd_get_process_device_data(dev, pqm->process);
+       if (!pdd) {
+               pr_err("Process device data doesn't exist\n");
+               return -1;
+       }
 
        retval = find_available_queue_slot(pqm, qid);
        if (retval != 0)
@@ -176,7 +178,7 @@ int pqm_create_queue(struct process_queue_manager *pqm,
 
        if (list_empty(&pqm->queues)) {
                pdd->qpd.pqm = pqm;
-               dev->dqm->register_process(dev->dqm, &pdd->qpd);
+               dev->dqm->ops.register_process(dev->dqm, &pdd->qpd);
        }
 
        pqn = kzalloc(sizeof(struct process_queue_node), GFP_KERNEL);
@@ -186,6 +188,7 @@ int pqm_create_queue(struct process_queue_manager *pqm,
        }
 
        switch (type) {
+       case KFD_QUEUE_TYPE_SDMA:
        case KFD_QUEUE_TYPE_COMPUTE:
                /* check if there is over subscription */
                if ((sched_policy == KFD_SCHED_POLICY_HWS_NO_OVERSUBSCRIPTION) &&
@@ -201,7 +204,7 @@ int pqm_create_queue(struct process_queue_manager *pqm,
                        goto err_create_queue;
                pqn->q = q;
                pqn->kq = NULL;
-               retval = dev->dqm->create_queue(dev->dqm, q, &pdd->qpd,
+               retval = dev->dqm->ops.create_queue(dev->dqm, q, &pdd->qpd,
                                                &q->properties.vmid);
                print_queue(q);
                break;
@@ -214,7 +217,8 @@ int pqm_create_queue(struct process_queue_manager *pqm,
                kq->queue->properties.queue_id = *qid;
                pqn->kq = kq;
                pqn->q = NULL;
-               retval = dev->dqm->create_kernel_queue(dev->dqm, kq, &pdd->qpd);
+               retval = dev->dqm->ops.create_kernel_queue(dev->dqm,
+                                                       kq, &pdd->qpd);
                break;
        default:
                BUG();
@@ -273,19 +277,22 @@ int pqm_destroy_queue(struct process_queue_manager *pqm, unsigned int qid)
                dev = pqn->q->device;
        BUG_ON(!dev);
 
-       pdd = kfd_get_process_device_data(dev, pqm->process, 1);
-       BUG_ON(!pdd);
+       pdd = kfd_get_process_device_data(dev, pqm->process);
+       if (!pdd) {
+               pr_err("Process device data doesn't exist\n");
+               return -1;
+       }
 
        if (pqn->kq) {
                /* destroy kernel queue (DIQ) */
                dqm = pqn->kq->dev->dqm;
-               dqm->destroy_kernel_queue(dqm, pqn->kq, &pdd->qpd);
+               dqm->ops.destroy_kernel_queue(dqm, pqn->kq, &pdd->qpd);
                kernel_queue_uninit(pqn->kq);
        }
 
        if (pqn->q) {
                dqm = pqn->q->device->dqm;
-               retval = dqm->destroy_queue(dqm, &pdd->qpd, pqn->q);
+               retval = dqm->ops.destroy_queue(dqm, &pdd->qpd, pqn->q);
                if (retval != 0)
                        return retval;
 
@@ -297,7 +304,7 @@ int pqm_destroy_queue(struct process_queue_manager *pqm, unsigned int qid)
        clear_bit(qid, pqm->queue_slot_bitmap);
 
        if (list_empty(&pqm->queues))
-               dqm->unregister_process(dqm, &pdd->qpd);
+               dqm->ops.unregister_process(dqm, &pdd->qpd);
 
        return retval;
 }
@@ -318,7 +325,8 @@ int pqm_update_queue(struct process_queue_manager *pqm, unsigned int qid,
        pqn->q->properties.queue_percent = p->queue_percent;
        pqn->q->properties.priority = p->priority;
 
-       retval = pqn->q->device->dqm->update_queue(pqn->q->device->dqm, pqn->q);
+       retval = pqn->q->device->dqm->ops.update_queue(pqn->q->device->dqm,
+                                                       pqn->q);
        if (retval != 0)
                return retval;
 
index cca1708fd811be8253ab0d2989d74e405f3dab04..498399323a8cd503f35fb3e828abf08c2368cad8 100644 (file)
@@ -27,6 +27,7 @@
 #include <linux/acpi.h>
 #include <linux/hash.h>
 #include <linux/cpufreq.h>
+#include <linux/log2.h>
 
 #include "kfd_priv.h"
 #include "kfd_crat.h"
@@ -630,10 +631,10 @@ static struct kobj_type cache_type = {
 static ssize_t node_show(struct kobject *kobj, struct attribute *attr,
                char *buffer)
 {
-       ssize_t ret;
        struct kfd_topology_device *dev;
        char public_name[KFD_TOPOLOGY_PUBLIC_NAME_SIZE];
        uint32_t i;
+       uint32_t log_max_watch_addr;
 
        /* Making sure that the buffer is an empty string */
        buffer[0] = 0;
@@ -641,8 +642,10 @@ static ssize_t node_show(struct kobject *kobj, struct attribute *attr,
        if (strcmp(attr->name, "gpu_id") == 0) {
                dev = container_of(attr, struct kfd_topology_device,
                                attr_gpuid);
-               ret = sysfs_show_32bit_val(buffer, dev->gpu_id);
-       } else if (strcmp(attr->name, "name") == 0) {
+               return sysfs_show_32bit_val(buffer, dev->gpu_id);
+       }
+
+       if (strcmp(attr->name, "name") == 0) {
                dev = container_of(attr, struct kfd_topology_device,
                                attr_name);
                for (i = 0; i < KFD_TOPOLOGY_PUBLIC_NAME_SIZE; i++) {
@@ -652,80 +655,90 @@ static ssize_t node_show(struct kobject *kobj, struct attribute *attr,
                                break;
                }
                public_name[KFD_TOPOLOGY_PUBLIC_NAME_SIZE-1] = 0x0;
-               ret = sysfs_show_str_val(buffer, public_name);
-       } else {
-               dev = container_of(attr, struct kfd_topology_device,
-                               attr_props);
-               sysfs_show_32bit_prop(buffer, "cpu_cores_count",
-                               dev->node_props.cpu_cores_count);
-               sysfs_show_32bit_prop(buffer, "simd_count",
-                               dev->node_props.simd_count);
-
-               if (dev->mem_bank_count < dev->node_props.mem_banks_count) {
-                       pr_warn("kfd: mem_banks_count truncated from %d to %d\n",
-                                       dev->node_props.mem_banks_count,
-                                       dev->mem_bank_count);
-                       sysfs_show_32bit_prop(buffer, "mem_banks_count",
-                                       dev->mem_bank_count);
-               } else {
-                       sysfs_show_32bit_prop(buffer, "mem_banks_count",
-                                       dev->node_props.mem_banks_count);
-               }
+               return sysfs_show_str_val(buffer, public_name);
+       }
 
-               sysfs_show_32bit_prop(buffer, "caches_count",
-                               dev->node_props.caches_count);
-               sysfs_show_32bit_prop(buffer, "io_links_count",
-                               dev->node_props.io_links_count);
-               sysfs_show_32bit_prop(buffer, "cpu_core_id_base",
-                               dev->node_props.cpu_core_id_base);
-               sysfs_show_32bit_prop(buffer, "simd_id_base",
-                               dev->node_props.simd_id_base);
-               sysfs_show_32bit_prop(buffer, "capability",
-                               dev->node_props.capability);
-               sysfs_show_32bit_prop(buffer, "max_waves_per_simd",
-                               dev->node_props.max_waves_per_simd);
-               sysfs_show_32bit_prop(buffer, "lds_size_in_kb",
-                               dev->node_props.lds_size_in_kb);
-               sysfs_show_32bit_prop(buffer, "gds_size_in_kb",
-                               dev->node_props.gds_size_in_kb);
-               sysfs_show_32bit_prop(buffer, "wave_front_size",
-                               dev->node_props.wave_front_size);
-               sysfs_show_32bit_prop(buffer, "array_count",
-                               dev->node_props.array_count);
-               sysfs_show_32bit_prop(buffer, "simd_arrays_per_engine",
-                               dev->node_props.simd_arrays_per_engine);
-               sysfs_show_32bit_prop(buffer, "cu_per_simd_array",
-                               dev->node_props.cu_per_simd_array);
-               sysfs_show_32bit_prop(buffer, "simd_per_cu",
-                               dev->node_props.simd_per_cu);
-               sysfs_show_32bit_prop(buffer, "max_slots_scratch_cu",
-                               dev->node_props.max_slots_scratch_cu);
-               sysfs_show_32bit_prop(buffer, "vendor_id",
-                               dev->node_props.vendor_id);
-               sysfs_show_32bit_prop(buffer, "device_id",
-                               dev->node_props.device_id);
-               sysfs_show_32bit_prop(buffer, "location_id",
-                               dev->node_props.location_id);
-
-               if (dev->gpu) {
-                       sysfs_show_32bit_prop(buffer, "max_engine_clk_fcompute",
-                                       kfd2kgd->get_max_engine_clock_in_mhz(
-                                               dev->gpu->kgd));
-                       sysfs_show_64bit_prop(buffer, "local_mem_size",
-                                       kfd2kgd->get_vmem_size(dev->gpu->kgd));
-
-                       sysfs_show_32bit_prop(buffer, "fw_version",
-                                       kfd2kgd->get_fw_version(
-                                                       dev->gpu->kgd,
-                                                       KGD_ENGINE_MEC1));
+       dev = container_of(attr, struct kfd_topology_device,
+                       attr_props);
+       sysfs_show_32bit_prop(buffer, "cpu_cores_count",
+                       dev->node_props.cpu_cores_count);
+       sysfs_show_32bit_prop(buffer, "simd_count",
+                       dev->node_props.simd_count);
+
+       if (dev->mem_bank_count < dev->node_props.mem_banks_count) {
+               pr_warn("kfd: mem_banks_count truncated from %d to %d\n",
+                               dev->node_props.mem_banks_count,
+                               dev->mem_bank_count);
+               sysfs_show_32bit_prop(buffer, "mem_banks_count",
+                               dev->mem_bank_count);
+       } else {
+               sysfs_show_32bit_prop(buffer, "mem_banks_count",
+                               dev->node_props.mem_banks_count);
+       }
 
+       sysfs_show_32bit_prop(buffer, "caches_count",
+                       dev->node_props.caches_count);
+       sysfs_show_32bit_prop(buffer, "io_links_count",
+                       dev->node_props.io_links_count);
+       sysfs_show_32bit_prop(buffer, "cpu_core_id_base",
+                       dev->node_props.cpu_core_id_base);
+       sysfs_show_32bit_prop(buffer, "simd_id_base",
+                       dev->node_props.simd_id_base);
+       sysfs_show_32bit_prop(buffer, "capability",
+                       dev->node_props.capability);
+       sysfs_show_32bit_prop(buffer, "max_waves_per_simd",
+                       dev->node_props.max_waves_per_simd);
+       sysfs_show_32bit_prop(buffer, "lds_size_in_kb",
+                       dev->node_props.lds_size_in_kb);
+       sysfs_show_32bit_prop(buffer, "gds_size_in_kb",
+                       dev->node_props.gds_size_in_kb);
+       sysfs_show_32bit_prop(buffer, "wave_front_size",
+                       dev->node_props.wave_front_size);
+       sysfs_show_32bit_prop(buffer, "array_count",
+                       dev->node_props.array_count);
+       sysfs_show_32bit_prop(buffer, "simd_arrays_per_engine",
+                       dev->node_props.simd_arrays_per_engine);
+       sysfs_show_32bit_prop(buffer, "cu_per_simd_array",
+                       dev->node_props.cu_per_simd_array);
+       sysfs_show_32bit_prop(buffer, "simd_per_cu",
+                       dev->node_props.simd_per_cu);
+       sysfs_show_32bit_prop(buffer, "max_slots_scratch_cu",
+                       dev->node_props.max_slots_scratch_cu);
+       sysfs_show_32bit_prop(buffer, "vendor_id",
+                       dev->node_props.vendor_id);
+       sysfs_show_32bit_prop(buffer, "device_id",
+                       dev->node_props.device_id);
+       sysfs_show_32bit_prop(buffer, "location_id",
+                       dev->node_props.location_id);
+
+       if (dev->gpu) {
+               log_max_watch_addr =
+                       __ilog2_u32(dev->gpu->device_info->num_of_watch_points);
+
+               if (log_max_watch_addr) {
+                       dev->node_props.capability |=
+                                       HSA_CAP_WATCH_POINTS_SUPPORTED;
+
+                       dev->node_props.capability |=
+                               ((log_max_watch_addr <<
+                                       HSA_CAP_WATCH_POINTS_TOTALBITS_SHIFT) &
+                               HSA_CAP_WATCH_POINTS_TOTALBITS_MASK);
                }
 
-               ret = sysfs_show_32bit_prop(buffer, "max_engine_clk_ccompute",
-                               cpufreq_quick_get_max(0)/1000);
+               sysfs_show_32bit_prop(buffer, "max_engine_clk_fcompute",
+                               kfd2kgd->get_max_engine_clock_in_mhz(
+                                       dev->gpu->kgd));
+               sysfs_show_64bit_prop(buffer, "local_mem_size",
+                               kfd2kgd->get_vmem_size(dev->gpu->kgd));
+
+               sysfs_show_32bit_prop(buffer, "fw_version",
+                               kfd2kgd->get_fw_version(
+                                               dev->gpu->kgd,
+                                               KGD_ENGINE_MEC1));
        }
 
-       return ret;
+       return sysfs_show_32bit_prop(buffer, "max_engine_clk_ccompute",
+                                       cpufreq_quick_get_max(0)/1000);
 }
 
 static const struct sysfs_ops node_ops = {
diff --git a/drivers/gpu/drm/amd/include/cik_structs.h b/drivers/gpu/drm/amd/include/cik_structs.h
new file mode 100644 (file)
index 0000000..749eab9
--- /dev/null
@@ -0,0 +1,293 @@
+/*
+ * Copyright 2012 Advanced Micro Devices, 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 CIK_STRUCTS_H_
+#define CIK_STRUCTS_H_
+
+struct cik_mqd {
+       uint32_t header;
+       uint32_t compute_dispatch_initiator;
+       uint32_t compute_dim_x;
+       uint32_t compute_dim_y;
+       uint32_t compute_dim_z;
+       uint32_t compute_start_x;
+       uint32_t compute_start_y;
+       uint32_t compute_start_z;
+       uint32_t compute_num_thread_x;
+       uint32_t compute_num_thread_y;
+       uint32_t compute_num_thread_z;
+       uint32_t compute_pipelinestat_enable;
+       uint32_t compute_perfcount_enable;
+       uint32_t compute_pgm_lo;
+       uint32_t compute_pgm_hi;
+       uint32_t compute_tba_lo;
+       uint32_t compute_tba_hi;
+       uint32_t compute_tma_lo;
+       uint32_t compute_tma_hi;
+       uint32_t compute_pgm_rsrc1;
+       uint32_t compute_pgm_rsrc2;
+       uint32_t compute_vmid;
+       uint32_t compute_resource_limits;
+       uint32_t compute_static_thread_mgmt_se0;
+       uint32_t compute_static_thread_mgmt_se1;
+       uint32_t compute_tmpring_size;
+       uint32_t compute_static_thread_mgmt_se2;
+       uint32_t compute_static_thread_mgmt_se3;
+       uint32_t compute_restart_x;
+       uint32_t compute_restart_y;
+       uint32_t compute_restart_z;
+       uint32_t compute_thread_trace_enable;
+       uint32_t compute_misc_reserved;
+       uint32_t compute_user_data_0;
+       uint32_t compute_user_data_1;
+       uint32_t compute_user_data_2;
+       uint32_t compute_user_data_3;
+       uint32_t compute_user_data_4;
+       uint32_t compute_user_data_5;
+       uint32_t compute_user_data_6;
+       uint32_t compute_user_data_7;
+       uint32_t compute_user_data_8;
+       uint32_t compute_user_data_9;
+       uint32_t compute_user_data_10;
+       uint32_t compute_user_data_11;
+       uint32_t compute_user_data_12;
+       uint32_t compute_user_data_13;
+       uint32_t compute_user_data_14;
+       uint32_t compute_user_data_15;
+       uint32_t cp_compute_csinvoc_count_lo;
+       uint32_t cp_compute_csinvoc_count_hi;
+       uint32_t cp_mqd_base_addr_lo;
+       uint32_t cp_mqd_base_addr_hi;
+       uint32_t cp_hqd_active;
+       uint32_t cp_hqd_vmid;
+       uint32_t cp_hqd_persistent_state;
+       uint32_t cp_hqd_pipe_priority;
+       uint32_t cp_hqd_queue_priority;
+       uint32_t cp_hqd_quantum;
+       uint32_t cp_hqd_pq_base_lo;
+       uint32_t cp_hqd_pq_base_hi;
+       uint32_t cp_hqd_pq_rptr;
+       uint32_t cp_hqd_pq_rptr_report_addr_lo;
+       uint32_t cp_hqd_pq_rptr_report_addr_hi;
+       uint32_t cp_hqd_pq_wptr_poll_addr_lo;
+       uint32_t cp_hqd_pq_wptr_poll_addr_hi;
+       uint32_t cp_hqd_pq_doorbell_control;
+       uint32_t cp_hqd_pq_wptr;
+       uint32_t cp_hqd_pq_control;
+       uint32_t cp_hqd_ib_base_addr_lo;
+       uint32_t cp_hqd_ib_base_addr_hi;
+       uint32_t cp_hqd_ib_rptr;
+       uint32_t cp_hqd_ib_control;
+       uint32_t cp_hqd_iq_timer;
+       uint32_t cp_hqd_iq_rptr;
+       uint32_t cp_hqd_dequeue_request;
+       uint32_t cp_hqd_dma_offload;
+       uint32_t cp_hqd_sema_cmd;
+       uint32_t cp_hqd_msg_type;
+       uint32_t cp_hqd_atomic0_preop_lo;
+       uint32_t cp_hqd_atomic0_preop_hi;
+       uint32_t cp_hqd_atomic1_preop_lo;
+       uint32_t cp_hqd_atomic1_preop_hi;
+       uint32_t cp_hqd_hq_status0;
+       uint32_t cp_hqd_hq_control0;
+       uint32_t cp_mqd_control;
+       uint32_t cp_mqd_query_time_lo;
+       uint32_t cp_mqd_query_time_hi;
+       uint32_t cp_mqd_connect_start_time_lo;
+       uint32_t cp_mqd_connect_start_time_hi;
+       uint32_t cp_mqd_connect_end_time_lo;
+       uint32_t cp_mqd_connect_end_time_hi;
+       uint32_t cp_mqd_connect_end_wf_count;
+       uint32_t cp_mqd_connect_end_pq_rptr;
+       uint32_t cp_mqd_connect_end_pq_wptr;
+       uint32_t cp_mqd_connect_end_ib_rptr;
+       uint32_t reserved_96;
+       uint32_t reserved_97;
+       uint32_t reserved_98;
+       uint32_t reserved_99;
+       uint32_t iqtimer_pkt_header;
+       uint32_t iqtimer_pkt_dw0;
+       uint32_t iqtimer_pkt_dw1;
+       uint32_t iqtimer_pkt_dw2;
+       uint32_t iqtimer_pkt_dw3;
+       uint32_t iqtimer_pkt_dw4;
+       uint32_t iqtimer_pkt_dw5;
+       uint32_t iqtimer_pkt_dw6;
+       uint32_t reserved_108;
+       uint32_t reserved_109;
+       uint32_t reserved_110;
+       uint32_t reserved_111;
+       uint32_t queue_doorbell_id0;
+       uint32_t queue_doorbell_id1;
+       uint32_t queue_doorbell_id2;
+       uint32_t queue_doorbell_id3;
+       uint32_t queue_doorbell_id4;
+       uint32_t queue_doorbell_id5;
+       uint32_t queue_doorbell_id6;
+       uint32_t queue_doorbell_id7;
+       uint32_t queue_doorbell_id8;
+       uint32_t queue_doorbell_id9;
+       uint32_t queue_doorbell_id10;
+       uint32_t queue_doorbell_id11;
+       uint32_t queue_doorbell_id12;
+       uint32_t queue_doorbell_id13;
+       uint32_t queue_doorbell_id14;
+       uint32_t queue_doorbell_id15;
+};
+
+struct cik_sdma_rlc_registers {
+       uint32_t sdma_rlc_rb_cntl;
+       uint32_t sdma_rlc_rb_base;
+       uint32_t sdma_rlc_rb_base_hi;
+       uint32_t sdma_rlc_rb_rptr;
+       uint32_t sdma_rlc_rb_wptr;
+       uint32_t sdma_rlc_rb_wptr_poll_cntl;
+       uint32_t sdma_rlc_rb_wptr_poll_addr_hi;
+       uint32_t sdma_rlc_rb_wptr_poll_addr_lo;
+       uint32_t sdma_rlc_rb_rptr_addr_hi;
+       uint32_t sdma_rlc_rb_rptr_addr_lo;
+       uint32_t sdma_rlc_ib_cntl;
+       uint32_t sdma_rlc_ib_rptr;
+       uint32_t sdma_rlc_ib_offset;
+       uint32_t sdma_rlc_ib_base_lo;
+       uint32_t sdma_rlc_ib_base_hi;
+       uint32_t sdma_rlc_ib_size;
+       uint32_t sdma_rlc_skip_cntl;
+       uint32_t sdma_rlc_context_status;
+       uint32_t sdma_rlc_doorbell;
+       uint32_t sdma_rlc_virtual_addr;
+       uint32_t sdma_rlc_ape1_cntl;
+       uint32_t sdma_rlc_doorbell_log;
+       uint32_t reserved_22;
+       uint32_t reserved_23;
+       uint32_t reserved_24;
+       uint32_t reserved_25;
+       uint32_t reserved_26;
+       uint32_t reserved_27;
+       uint32_t reserved_28;
+       uint32_t reserved_29;
+       uint32_t reserved_30;
+       uint32_t reserved_31;
+       uint32_t reserved_32;
+       uint32_t reserved_33;
+       uint32_t reserved_34;
+       uint32_t reserved_35;
+       uint32_t reserved_36;
+       uint32_t reserved_37;
+       uint32_t reserved_38;
+       uint32_t reserved_39;
+       uint32_t reserved_40;
+       uint32_t reserved_41;
+       uint32_t reserved_42;
+       uint32_t reserved_43;
+       uint32_t reserved_44;
+       uint32_t reserved_45;
+       uint32_t reserved_46;
+       uint32_t reserved_47;
+       uint32_t reserved_48;
+       uint32_t reserved_49;
+       uint32_t reserved_50;
+       uint32_t reserved_51;
+       uint32_t reserved_52;
+       uint32_t reserved_53;
+       uint32_t reserved_54;
+       uint32_t reserved_55;
+       uint32_t reserved_56;
+       uint32_t reserved_57;
+       uint32_t reserved_58;
+       uint32_t reserved_59;
+       uint32_t reserved_60;
+       uint32_t reserved_61;
+       uint32_t reserved_62;
+       uint32_t reserved_63;
+       uint32_t reserved_64;
+       uint32_t reserved_65;
+       uint32_t reserved_66;
+       uint32_t reserved_67;
+       uint32_t reserved_68;
+       uint32_t reserved_69;
+       uint32_t reserved_70;
+       uint32_t reserved_71;
+       uint32_t reserved_72;
+       uint32_t reserved_73;
+       uint32_t reserved_74;
+       uint32_t reserved_75;
+       uint32_t reserved_76;
+       uint32_t reserved_77;
+       uint32_t reserved_78;
+       uint32_t reserved_79;
+       uint32_t reserved_80;
+       uint32_t reserved_81;
+       uint32_t reserved_82;
+       uint32_t reserved_83;
+       uint32_t reserved_84;
+       uint32_t reserved_85;
+       uint32_t reserved_86;
+       uint32_t reserved_87;
+       uint32_t reserved_88;
+       uint32_t reserved_89;
+       uint32_t reserved_90;
+       uint32_t reserved_91;
+       uint32_t reserved_92;
+       uint32_t reserved_93;
+       uint32_t reserved_94;
+       uint32_t reserved_95;
+       uint32_t reserved_96;
+       uint32_t reserved_97;
+       uint32_t reserved_98;
+       uint32_t reserved_99;
+       uint32_t reserved_100;
+       uint32_t reserved_101;
+       uint32_t reserved_102;
+       uint32_t reserved_103;
+       uint32_t reserved_104;
+       uint32_t reserved_105;
+       uint32_t reserved_106;
+       uint32_t reserved_107;
+       uint32_t reserved_108;
+       uint32_t reserved_109;
+       uint32_t reserved_110;
+       uint32_t reserved_111;
+       uint32_t reserved_112;
+       uint32_t reserved_113;
+       uint32_t reserved_114;
+       uint32_t reserved_115;
+       uint32_t reserved_116;
+       uint32_t reserved_117;
+       uint32_t reserved_118;
+       uint32_t reserved_119;
+       uint32_t reserved_120;
+       uint32_t reserved_121;
+       uint32_t reserved_122;
+       uint32_t reserved_123;
+       uint32_t reserved_124;
+       uint32_t reserved_125;
+       uint32_t reserved_126;
+       uint32_t reserved_127;
+       uint32_t sdma_engine_id;
+       uint32_t sdma_queue_id;
+};
+
+
+
+#endif /* CIK_STRUCTS_H_ */
index 96a512208fade6825da6aa8e2645f2a088d485d2..239bc16a1ddd61c9fd65d3d1f1284025fd69df2c 100644 (file)
@@ -110,17 +110,10 @@ struct kgd2kfd_calls {
 /**
  * struct kfd2kgd_calls
  *
- * @init_sa_manager: Initialize an instance of the sa manager, used by
- * amdkfd for all system memory allocations that are mapped to the GART
- * address space
+ * @init_gtt_mem_allocation: Allocate a buffer on the gart aperture.
+ * The buffer can be used for mqds, hpds, kernel queue, fence and runlists
  *
- * @fini_sa_manager: Releases all memory allocations for amdkfd that are
- * handled by kgd sa manager
- *
- * @allocate_mem: Allocate a buffer from amdkfd's sa manager. The buffer can
- * be used for mqds, hpds, kernel queue, fence and runlists
- *
- * @free_mem: Frees a buffer that was allocated by amdkfd's sa manager
+ * @free_gtt_mem: Frees a buffer that was allocated on the gart aperture
  *
  * @get_vmem_size: Retrieves (physical) size of VRAM
  *
@@ -136,18 +129,23 @@ struct kgd2kfd_calls {
  * @set_pasid_vmid_mapping: Exposes pasid/vmid pair to the H/W for no cp
  * scheduling mode. Only used for no cp scheduling mode.
  *
- * @init_memory: Initializes memory apertures to fixed base/limit address
- * and non cached memory types.
- *
  * @init_pipeline: Initialized the compute pipelines.
  *
  * @hqd_load: Loads the mqd structure to a H/W hqd slot. used only for no cp
  * sceduling mode.
  *
+ * @hqd_sdma_load: Loads the SDMA mqd structure to a H/W SDMA hqd slot.
+ * used only for no HWS mode.
+ *
  * @hqd_is_occupies: Checks if a hqd slot is occupied.
  *
  * @hqd_destroy: Destructs and preempts the queue assigned to that hqd slot.
  *
+ * @hqd_sdma_is_occupied: Checks if an SDMA hqd slot is occupied.
+ *
+ * @hqd_sdma_destroy: Destructs and preempts the SDMA queue assigned to that
+ * SDMA hqd slot.
+ *
  * @get_fw_version: Returns FW versions from the header
  *
  * This structure contains function pointers to services that the kgd driver
@@ -155,13 +153,11 @@ struct kgd2kfd_calls {
  *
  */
 struct kfd2kgd_calls {
-       /* Memory management. */
-       int (*init_sa_manager)(struct kgd_dev *kgd, unsigned int size);
-       void (*fini_sa_manager)(struct kgd_dev *kgd);
-       int (*allocate_mem)(struct kgd_dev *kgd, size_t size, size_t alignment,
-                       enum kgd_memory_pool pool, struct kgd_mem **mem);
+       int (*init_gtt_mem_allocation)(struct kgd_dev *kgd, size_t size,
+                                       void **mem_obj, uint64_t *gpu_addr,
+                                       void **cpu_ptr);
 
-       void (*free_mem)(struct kgd_dev *kgd, struct kgd_mem *mem);
+       void (*free_gtt_mem)(struct kgd_dev *kgd, void *mem_obj);
 
        uint64_t (*get_vmem_size)(struct kgd_dev *kgd);
        uint64_t (*get_gpu_clock_counter)(struct kgd_dev *kgd);
@@ -176,25 +172,32 @@ struct kfd2kgd_calls {
        int (*set_pasid_vmid_mapping)(struct kgd_dev *kgd, unsigned int pasid,
                                        unsigned int vmid);
 
-       int (*init_memory)(struct kgd_dev *kgd);
        int (*init_pipeline)(struct kgd_dev *kgd, uint32_t pipe_id,
                                uint32_t hpd_size, uint64_t hpd_gpu_addr);
 
        int (*hqd_load)(struct kgd_dev *kgd, void *mqd, uint32_t pipe_id,
                        uint32_t queue_id, uint32_t __user *wptr);
 
+       int (*hqd_sdma_load)(struct kgd_dev *kgd, void *mqd);
+
        bool (*hqd_is_occupied)(struct kgd_dev *kgd, uint64_t queue_address,
                                uint32_t pipe_id, uint32_t queue_id);
 
        int (*hqd_destroy)(struct kgd_dev *kgd, uint32_t reset_type,
                                unsigned int timeout, uint32_t pipe_id,
                                uint32_t queue_id);
+
+       bool (*hqd_sdma_is_occupied)(struct kgd_dev *kgd, void *mqd);
+
+       int (*hqd_sdma_destroy)(struct kgd_dev *kgd, void *mqd,
+                               unsigned int timeout);
+
        uint16_t (*get_fw_version)(struct kgd_dev *kgd,
                                enum kgd_engine_type type);
 };
 
 bool kgd2kfd_init(unsigned interface_version,
-                 const struct kfd2kgd_calls *f2g,
-                 const struct kgd2kfd_calls **g2f);
+               const struct kfd2kgd_calls *f2g,
+               const struct kgd2kfd_calls **g2f);
 
-#endif /* KGD_KFD_INTERFACE_H_INCLUDED */
+#endif /* KGD_KFD_INTERFACE_H_INCLUDED */
index e3a7a5078e5ce1d5469fa740cc9bde74551ad090..42d2ffa087169fd110da85e22a496aa080d34c9a 100644 (file)
@@ -653,10 +653,6 @@ static int armada_drm_crtc_mode_set_base(struct drm_crtc *crtc, int x, int y,
        return 0;
 }
 
-static void armada_drm_crtc_load_lut(struct drm_crtc *crtc)
-{
-}
-
 /* The mode_config.mutex will be held for this call */
 static void armada_drm_crtc_disable(struct drm_crtc *crtc)
 {
@@ -678,7 +674,6 @@ static const struct drm_crtc_helper_funcs armada_crtc_helper_funcs = {
        .mode_fixup     = armada_drm_crtc_mode_fixup,
        .mode_set       = armada_drm_crtc_mode_set,
        .mode_set_base  = armada_drm_crtc_mode_set_base,
-       .load_lut       = armada_drm_crtc_load_lut,
        .disable        = armada_drm_crtc_disable,
 };
 
index 5c60ae524c454952316f9d8f8864cf8e52ce8cc4..ff68eefae27316b87d2cd72020b0639becfc7516 100644 (file)
@@ -335,18 +335,27 @@ int ast_fbdev_init(struct drm_device *dev)
 
        ret = drm_fb_helper_init(dev, &afbdev->helper,
                                 1, 1);
-       if (ret) {
-               kfree(afbdev);
-               return ret;
-       }
+       if (ret)
+               goto free;
 
-       drm_fb_helper_single_add_all_connectors(&afbdev->helper);
+       ret = drm_fb_helper_single_add_all_connectors(&afbdev->helper);
+       if (ret)
+               goto fini;
 
        /* disable all the possible outputs/crtcs before entering KMS mode */
        drm_helper_disable_unused_functions(dev);
 
-       drm_fb_helper_initial_config(&afbdev->helper, 32);
+       ret = drm_fb_helper_initial_config(&afbdev->helper, 32);
+       if (ret)
+               goto fini;
+
        return 0;
+
+fini:
+       drm_fb_helper_fini(&afbdev->helper);
+free:
+       kfree(afbdev);
+       return ret;
 }
 
 void ast_fbdev_fini(struct drm_device *dev)
diff --git a/drivers/gpu/drm/atmel-hlcdc/Kconfig b/drivers/gpu/drm/atmel-hlcdc/Kconfig
new file mode 100644 (file)
index 0000000..1a08562
--- /dev/null
@@ -0,0 +1,11 @@
+config DRM_ATMEL_HLCDC
+       tristate "DRM Support for ATMEL HLCDC Display Controller"
+       depends on DRM && OF && COMMON_CLK && MFD_ATMEL_HLCDC
+       select DRM_GEM_CMA_HELPER
+       select DRM_KMS_HELPER
+       select DRM_KMS_FB_HELPER
+       select DRM_KMS_CMA_HELPER
+       select DRM_PANEL
+       help
+         Choose this option if you have an ATMEL SoC with an HLCDC display
+         controller (i.e. at91sam9n12, at91sam9x5 family or sama5d3 family).
diff --git a/drivers/gpu/drm/atmel-hlcdc/Makefile b/drivers/gpu/drm/atmel-hlcdc/Makefile
new file mode 100644 (file)
index 0000000..10ae426
--- /dev/null
@@ -0,0 +1,7 @@
+atmel-hlcdc-dc-y := atmel_hlcdc_crtc.o \
+               atmel_hlcdc_dc.o \
+               atmel_hlcdc_layer.o \
+               atmel_hlcdc_output.o \
+               atmel_hlcdc_plane.o
+
+obj-$(CONFIG_DRM_ATMEL_HLCDC)  += atmel-hlcdc-dc.o
diff --git a/drivers/gpu/drm/atmel-hlcdc/atmel_hlcdc_crtc.c b/drivers/gpu/drm/atmel-hlcdc/atmel_hlcdc_crtc.c
new file mode 100644 (file)
index 0000000..0409b90
--- /dev/null
@@ -0,0 +1,406 @@
+/*
+ * Copyright (C) 2014 Traphandler
+ * Copyright (C) 2014 Free Electrons
+ *
+ * Author: Jean-Jacques Hiblot <jjhiblot@traphandler.com>
+ * Author: Boris BREZILLON <boris.brezillon@free-electrons.com>
+ *
+ * This program is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License version 2 as published by
+ * the Free Software Foundation.
+ *
+ * This program is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License for
+ * more details.
+ *
+ * You should have received a copy of the GNU General Public License along with
+ * this program.  If not, see <http://www.gnu.org/licenses/>.
+ */
+
+#include <linux/clk.h>
+#include <linux/pm.h>
+#include <linux/pm_runtime.h>
+
+#include <drm/drm_crtc.h>
+#include <drm/drm_crtc_helper.h>
+#include <drm/drmP.h>
+
+#include <video/videomode.h>
+
+#include "atmel_hlcdc_dc.h"
+
+/**
+ * Atmel HLCDC CRTC structure
+ *
+ * @base: base DRM CRTC structure
+ * @hlcdc: pointer to the atmel_hlcdc structure provided by the MFD device
+ * @event: pointer to the current page flip event
+ * @id: CRTC id (returned by drm_crtc_index)
+ * @dpms: DPMS mode
+ */
+struct atmel_hlcdc_crtc {
+       struct drm_crtc base;
+       struct atmel_hlcdc_dc *dc;
+       struct drm_pending_vblank_event *event;
+       int id;
+       int dpms;
+};
+
+static inline struct atmel_hlcdc_crtc *
+drm_crtc_to_atmel_hlcdc_crtc(struct drm_crtc *crtc)
+{
+       return container_of(crtc, struct atmel_hlcdc_crtc, base);
+}
+
+static void atmel_hlcdc_crtc_dpms(struct drm_crtc *c, int mode)
+{
+       struct drm_device *dev = c->dev;
+       struct atmel_hlcdc_crtc *crtc = drm_crtc_to_atmel_hlcdc_crtc(c);
+       struct regmap *regmap = crtc->dc->hlcdc->regmap;
+       unsigned int status;
+
+       if (mode != DRM_MODE_DPMS_ON)
+               mode = DRM_MODE_DPMS_OFF;
+
+       if (crtc->dpms == mode)
+               return;
+
+       pm_runtime_get_sync(dev->dev);
+
+       if (mode != DRM_MODE_DPMS_ON) {
+               regmap_write(regmap, ATMEL_HLCDC_DIS, ATMEL_HLCDC_DISP);
+               while (!regmap_read(regmap, ATMEL_HLCDC_SR, &status) &&
+                      (status & ATMEL_HLCDC_DISP))
+                       cpu_relax();
+
+               regmap_write(regmap, ATMEL_HLCDC_DIS, ATMEL_HLCDC_SYNC);
+               while (!regmap_read(regmap, ATMEL_HLCDC_SR, &status) &&
+                      (status & ATMEL_HLCDC_SYNC))
+                       cpu_relax();
+
+               regmap_write(regmap, ATMEL_HLCDC_DIS, ATMEL_HLCDC_PIXEL_CLK);
+               while (!regmap_read(regmap, ATMEL_HLCDC_SR, &status) &&
+                      (status & ATMEL_HLCDC_PIXEL_CLK))
+                       cpu_relax();
+
+               clk_disable_unprepare(crtc->dc->hlcdc->sys_clk);
+
+               pm_runtime_allow(dev->dev);
+       } else {
+               pm_runtime_forbid(dev->dev);
+
+               clk_prepare_enable(crtc->dc->hlcdc->sys_clk);
+
+               regmap_write(regmap, ATMEL_HLCDC_EN, ATMEL_HLCDC_PIXEL_CLK);
+               while (!regmap_read(regmap, ATMEL_HLCDC_SR, &status) &&
+                      !(status & ATMEL_HLCDC_PIXEL_CLK))
+                       cpu_relax();
+
+
+               regmap_write(regmap, ATMEL_HLCDC_EN, ATMEL_HLCDC_SYNC);
+               while (!regmap_read(regmap, ATMEL_HLCDC_SR, &status) &&
+                      !(status & ATMEL_HLCDC_SYNC))
+                       cpu_relax();
+
+               regmap_write(regmap, ATMEL_HLCDC_EN, ATMEL_HLCDC_DISP);
+               while (!regmap_read(regmap, ATMEL_HLCDC_SR, &status) &&
+                      !(status & ATMEL_HLCDC_DISP))
+                       cpu_relax();
+       }
+
+       pm_runtime_put_sync(dev->dev);
+
+       crtc->dpms = mode;
+}
+
+static int atmel_hlcdc_crtc_mode_set(struct drm_crtc *c,
+                                    struct drm_display_mode *mode,
+                                    struct drm_display_mode *adj,
+                                    int x, int y,
+                                    struct drm_framebuffer *old_fb)
+{
+       struct atmel_hlcdc_crtc *crtc = drm_crtc_to_atmel_hlcdc_crtc(c);
+       struct regmap *regmap = crtc->dc->hlcdc->regmap;
+       struct drm_plane *plane = c->primary;
+       struct drm_framebuffer *fb;
+       unsigned long mode_rate;
+       struct videomode vm;
+       unsigned long prate;
+       unsigned int cfg;
+       int div;
+
+       if (atmel_hlcdc_dc_mode_valid(crtc->dc, adj) != MODE_OK)
+               return -EINVAL;
+
+       vm.vfront_porch = adj->crtc_vsync_start - adj->crtc_vdisplay;
+       vm.vback_porch = adj->crtc_vtotal - adj->crtc_vsync_end;
+       vm.vsync_len = adj->crtc_vsync_end - adj->crtc_vsync_start;
+       vm.hfront_porch = adj->crtc_hsync_start - adj->crtc_hdisplay;
+       vm.hback_porch = adj->crtc_htotal - adj->crtc_hsync_end;
+       vm.hsync_len = adj->crtc_hsync_end - adj->crtc_hsync_start;
+
+       regmap_write(regmap, ATMEL_HLCDC_CFG(1),
+                    (vm.hsync_len - 1) | ((vm.vsync_len - 1) << 16));
+
+       regmap_write(regmap, ATMEL_HLCDC_CFG(2),
+                    (vm.vfront_porch - 1) | (vm.vback_porch << 16));
+
+       regmap_write(regmap, ATMEL_HLCDC_CFG(3),
+                    (vm.hfront_porch - 1) | ((vm.hback_porch - 1) << 16));
+
+       regmap_write(regmap, ATMEL_HLCDC_CFG(4),
+                    (adj->crtc_hdisplay - 1) |
+                    ((adj->crtc_vdisplay - 1) << 16));
+
+       cfg = ATMEL_HLCDC_CLKPOL;
+
+       prate = clk_get_rate(crtc->dc->hlcdc->sys_clk);
+       mode_rate = mode->crtc_clock * 1000;
+       if ((prate / 2) < mode_rate) {
+               prate *= 2;
+               cfg |= ATMEL_HLCDC_CLKSEL;
+       }
+
+       div = DIV_ROUND_UP(prate, mode_rate);
+       if (div < 2)
+               div = 2;
+
+       cfg |= ATMEL_HLCDC_CLKDIV(div);
+
+       regmap_update_bits(regmap, ATMEL_HLCDC_CFG(0),
+                          ATMEL_HLCDC_CLKSEL | ATMEL_HLCDC_CLKDIV_MASK |
+                          ATMEL_HLCDC_CLKPOL, cfg);
+
+       cfg = 0;
+
+       if (mode->flags & DRM_MODE_FLAG_NVSYNC)
+               cfg |= ATMEL_HLCDC_VSPOL;
+
+       if (mode->flags & DRM_MODE_FLAG_NHSYNC)
+               cfg |= ATMEL_HLCDC_HSPOL;
+
+       regmap_update_bits(regmap, ATMEL_HLCDC_CFG(5),
+                          ATMEL_HLCDC_HSPOL | ATMEL_HLCDC_VSPOL |
+                          ATMEL_HLCDC_VSPDLYS | ATMEL_HLCDC_VSPDLYE |
+                          ATMEL_HLCDC_DISPPOL | ATMEL_HLCDC_DISPDLY |
+                          ATMEL_HLCDC_VSPSU | ATMEL_HLCDC_VSPHO |
+                          ATMEL_HLCDC_GUARDTIME_MASK,
+                          cfg);
+
+       fb = plane->fb;
+       plane->fb = old_fb;
+
+       return atmel_hlcdc_plane_update_with_mode(plane, c, fb, 0, 0,
+                                                 adj->hdisplay, adj->vdisplay,
+                                                 x << 16, y << 16,
+                                                 adj->hdisplay << 16,
+                                                 adj->vdisplay << 16,
+                                                 adj);
+}
+
+int atmel_hlcdc_crtc_mode_set_base(struct drm_crtc *c, int x, int y,
+                                  struct drm_framebuffer *old_fb)
+{
+       struct drm_plane *plane = c->primary;
+       struct drm_framebuffer *fb = plane->fb;
+       struct drm_display_mode *mode = &c->hwmode;
+
+       plane->fb = old_fb;
+
+       return plane->funcs->update_plane(plane, c, fb,
+                                         0, 0,
+                                         mode->hdisplay,
+                                         mode->vdisplay,
+                                         x << 16, y << 16,
+                                         mode->hdisplay << 16,
+                                         mode->vdisplay << 16);
+}
+
+static void atmel_hlcdc_crtc_prepare(struct drm_crtc *crtc)
+{
+       atmel_hlcdc_crtc_dpms(crtc, DRM_MODE_DPMS_OFF);
+}
+
+static void atmel_hlcdc_crtc_commit(struct drm_crtc *crtc)
+{
+       atmel_hlcdc_crtc_dpms(crtc, DRM_MODE_DPMS_ON);
+}
+
+static bool atmel_hlcdc_crtc_mode_fixup(struct drm_crtc *crtc,
+                                       const struct drm_display_mode *mode,
+                                       struct drm_display_mode *adjusted_mode)
+{
+       return true;
+}
+
+static void atmel_hlcdc_crtc_disable(struct drm_crtc *crtc)
+{
+       struct drm_plane *plane;
+
+       atmel_hlcdc_crtc_dpms(crtc, DRM_MODE_DPMS_OFF);
+       crtc->primary->funcs->disable_plane(crtc->primary);
+
+       drm_for_each_legacy_plane(plane, &crtc->dev->mode_config.plane_list) {
+               if (plane->crtc != crtc)
+                       continue;
+
+               plane->funcs->disable_plane(crtc->primary);
+               plane->crtc = NULL;
+       }
+}
+
+static const struct drm_crtc_helper_funcs lcdc_crtc_helper_funcs = {
+       .mode_fixup = atmel_hlcdc_crtc_mode_fixup,
+       .dpms = atmel_hlcdc_crtc_dpms,
+       .mode_set = atmel_hlcdc_crtc_mode_set,
+       .mode_set_base = atmel_hlcdc_crtc_mode_set_base,
+       .prepare = atmel_hlcdc_crtc_prepare,
+       .commit = atmel_hlcdc_crtc_commit,
+       .disable = atmel_hlcdc_crtc_disable,
+};
+
+static void atmel_hlcdc_crtc_destroy(struct drm_crtc *c)
+{
+       struct atmel_hlcdc_crtc *crtc = drm_crtc_to_atmel_hlcdc_crtc(c);
+
+       drm_crtc_cleanup(c);
+       kfree(crtc);
+}
+
+void atmel_hlcdc_crtc_cancel_page_flip(struct drm_crtc *c,
+                                      struct drm_file *file)
+{
+       struct atmel_hlcdc_crtc *crtc = drm_crtc_to_atmel_hlcdc_crtc(c);
+       struct drm_pending_vblank_event *event;
+       struct drm_device *dev = c->dev;
+       unsigned long flags;
+
+       spin_lock_irqsave(&dev->event_lock, flags);
+       event = crtc->event;
+       if (event && event->base.file_priv == file) {
+               event->base.destroy(&event->base);
+               drm_vblank_put(dev, crtc->id);
+               crtc->event = NULL;
+       }
+       spin_unlock_irqrestore(&dev->event_lock, flags);
+}
+
+static void atmel_hlcdc_crtc_finish_page_flip(struct atmel_hlcdc_crtc *crtc)
+{
+       struct drm_device *dev = crtc->base.dev;
+       unsigned long flags;
+
+       spin_lock_irqsave(&dev->event_lock, flags);
+       if (crtc->event) {
+               drm_send_vblank_event(dev, crtc->id, crtc->event);
+               drm_vblank_put(dev, crtc->id);
+               crtc->event = NULL;
+       }
+       spin_unlock_irqrestore(&dev->event_lock, flags);
+}
+
+void atmel_hlcdc_crtc_irq(struct drm_crtc *c)
+{
+       drm_handle_vblank(c->dev, 0);
+       atmel_hlcdc_crtc_finish_page_flip(drm_crtc_to_atmel_hlcdc_crtc(c));
+}
+
+static int atmel_hlcdc_crtc_page_flip(struct drm_crtc *c,
+                                     struct drm_framebuffer *fb,
+                                     struct drm_pending_vblank_event *event,
+                                     uint32_t page_flip_flags)
+{
+       struct atmel_hlcdc_crtc *crtc = drm_crtc_to_atmel_hlcdc_crtc(c);
+       struct atmel_hlcdc_plane_update_req req;
+       struct drm_plane *plane = c->primary;
+       struct drm_device *dev = c->dev;
+       unsigned long flags;
+       int ret = 0;
+
+       spin_lock_irqsave(&dev->event_lock, flags);
+       if (crtc->event)
+               ret = -EBUSY;
+       spin_unlock_irqrestore(&dev->event_lock, flags);
+
+       if (ret)
+               return ret;
+
+       memset(&req, 0, sizeof(req));
+       req.crtc_x = 0;
+       req.crtc_y = 0;
+       req.crtc_h = c->mode.crtc_vdisplay;
+       req.crtc_w = c->mode.crtc_hdisplay;
+       req.src_x = c->x << 16;
+       req.src_y = c->y << 16;
+       req.src_w = req.crtc_w << 16;
+       req.src_h = req.crtc_h << 16;
+       req.fb = fb;
+
+       ret = atmel_hlcdc_plane_prepare_update_req(plane, &req, &c->hwmode);
+       if (ret)
+               return ret;
+
+       if (event) {
+               drm_vblank_get(c->dev, crtc->id);
+               spin_lock_irqsave(&dev->event_lock, flags);
+               crtc->event = event;
+               spin_unlock_irqrestore(&dev->event_lock, flags);
+       }
+
+       ret = atmel_hlcdc_plane_apply_update_req(plane, &req);
+       if (ret)
+               crtc->event = NULL;
+       else
+               plane->fb = fb;
+
+       return ret;
+}
+
+static const struct drm_crtc_funcs atmel_hlcdc_crtc_funcs = {
+       .page_flip = atmel_hlcdc_crtc_page_flip,
+       .set_config = drm_crtc_helper_set_config,
+       .destroy = atmel_hlcdc_crtc_destroy,
+};
+
+int atmel_hlcdc_crtc_create(struct drm_device *dev)
+{
+       struct atmel_hlcdc_dc *dc = dev->dev_private;
+       struct atmel_hlcdc_planes *planes = dc->planes;
+       struct atmel_hlcdc_crtc *crtc;
+       int ret;
+       int i;
+
+       crtc = kzalloc(sizeof(*crtc), GFP_KERNEL);
+       if (!crtc)
+               return -ENOMEM;
+
+       crtc->dpms = DRM_MODE_DPMS_OFF;
+       crtc->dc = dc;
+
+       ret = drm_crtc_init_with_planes(dev, &crtc->base,
+                               &planes->primary->base,
+                               planes->cursor ? &planes->cursor->base : NULL,
+                               &atmel_hlcdc_crtc_funcs);
+       if (ret < 0)
+               goto fail;
+
+       crtc->id = drm_crtc_index(&crtc->base);
+
+       if (planes->cursor)
+               planes->cursor->base.possible_crtcs = 1 << crtc->id;
+
+       for (i = 0; i < planes->noverlays; i++)
+               planes->overlays[i]->base.possible_crtcs = 1 << crtc->id;
+
+       drm_crtc_helper_add(&crtc->base, &lcdc_crtc_helper_funcs);
+
+       dc->crtc = &crtc->base;
+
+       return 0;
+
+fail:
+       atmel_hlcdc_crtc_destroy(&crtc->base);
+       return ret;
+}
+
diff --git a/drivers/gpu/drm/atmel-hlcdc/atmel_hlcdc_dc.c b/drivers/gpu/drm/atmel-hlcdc/atmel_hlcdc_dc.c
new file mode 100644 (file)
index 0000000..7320a6c
--- /dev/null
@@ -0,0 +1,579 @@
+/*
+ * Copyright (C) 2014 Traphandler
+ * Copyright (C) 2014 Free Electrons
+ * Copyright (C) 2014 Atmel
+ *
+ * Author: Jean-Jacques Hiblot <jjhiblot@traphandler.com>
+ * Author: Boris BREZILLON <boris.brezillon@free-electrons.com>
+ *
+ * This program is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License version 2 as published by
+ * the Free Software Foundation.
+ *
+ * This program is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License for
+ * more details.
+ *
+ * You should have received a copy of the GNU General Public License along with
+ * this program.  If not, see <http://www.gnu.org/licenses/>.
+ */
+
+#include <linux/clk.h>
+#include <linux/irq.h>
+#include <linux/irqchip.h>
+#include <linux/module.h>
+#include <linux/pm_runtime.h>
+
+#include "atmel_hlcdc_dc.h"
+
+#define ATMEL_HLCDC_LAYER_IRQS_OFFSET          8
+
+static const struct atmel_hlcdc_layer_desc atmel_hlcdc_sama5d3_layers[] = {
+       {
+               .name = "base",
+               .formats = &atmel_hlcdc_plane_rgb_formats,
+               .regs_offset = 0x40,
+               .id = 0,
+               .type = ATMEL_HLCDC_BASE_LAYER,
+               .nconfigs = 7,
+               .layout = {
+                       .xstride = { 2 },
+                       .default_color = 3,
+                       .general_config = 4,
+                       .disc_pos = 5,
+                       .disc_size = 6,
+               },
+       },
+       {
+               .name = "overlay1",
+               .formats = &atmel_hlcdc_plane_rgb_formats,
+               .regs_offset = 0x140,
+               .id = 1,
+               .type = ATMEL_HLCDC_OVERLAY_LAYER,
+               .nconfigs = 10,
+               .layout = {
+                       .pos = 2,
+                       .size = 3,
+                       .xstride = { 4 },
+                       .pstride = { 5 },
+                       .default_color = 6,
+                       .chroma_key = 7,
+                       .chroma_key_mask = 8,
+                       .general_config = 9,
+               },
+       },
+       {
+               .name = "overlay2",
+               .formats = &atmel_hlcdc_plane_rgb_formats,
+               .regs_offset = 0x240,
+               .id = 2,
+               .type = ATMEL_HLCDC_OVERLAY_LAYER,
+               .nconfigs = 10,
+               .layout = {
+                       .pos = 2,
+                       .size = 3,
+                       .xstride = { 4 },
+                       .pstride = { 5 },
+                       .default_color = 6,
+                       .chroma_key = 7,
+                       .chroma_key_mask = 8,
+                       .general_config = 9,
+               },
+       },
+       {
+               .name = "high-end-overlay",
+               .formats = &atmel_hlcdc_plane_rgb_and_yuv_formats,
+               .regs_offset = 0x340,
+               .id = 3,
+               .type = ATMEL_HLCDC_OVERLAY_LAYER,
+               .nconfigs = 42,
+               .layout = {
+                       .pos = 2,
+                       .size = 3,
+                       .memsize = 4,
+                       .xstride = { 5, 7 },
+                       .pstride = { 6, 8 },
+                       .default_color = 9,
+                       .chroma_key = 10,
+                       .chroma_key_mask = 11,
+                       .general_config = 12,
+                       .csc = 14,
+               },
+       },
+       {
+               .name = "cursor",
+               .formats = &atmel_hlcdc_plane_rgb_formats,
+               .regs_offset = 0x440,
+               .id = 4,
+               .type = ATMEL_HLCDC_CURSOR_LAYER,
+               .nconfigs = 10,
+               .max_width = 128,
+               .max_height = 128,
+               .layout = {
+                       .pos = 2,
+                       .size = 3,
+                       .xstride = { 4 },
+                       .pstride = { 5 },
+                       .default_color = 6,
+                       .chroma_key = 7,
+                       .chroma_key_mask = 8,
+                       .general_config = 9,
+               },
+       },
+};
+
+static const struct atmel_hlcdc_dc_desc atmel_hlcdc_dc_sama5d3 = {
+       .min_width = 0,
+       .min_height = 0,
+       .max_width = 2048,
+       .max_height = 2048,
+       .nlayers = ARRAY_SIZE(atmel_hlcdc_sama5d3_layers),
+       .layers = atmel_hlcdc_sama5d3_layers,
+};
+
+static const struct of_device_id atmel_hlcdc_of_match[] = {
+       {
+               .compatible = "atmel,sama5d3-hlcdc",
+               .data = &atmel_hlcdc_dc_sama5d3,
+       },
+       { /* sentinel */ },
+};
+
+int atmel_hlcdc_dc_mode_valid(struct atmel_hlcdc_dc *dc,
+                             struct drm_display_mode *mode)
+{
+       int vfront_porch = mode->vsync_start - mode->vdisplay;
+       int vback_porch = mode->vtotal - mode->vsync_end;
+       int vsync_len = mode->vsync_end - mode->vsync_start;
+       int hfront_porch = mode->hsync_start - mode->hdisplay;
+       int hback_porch = mode->htotal - mode->hsync_end;
+       int hsync_len = mode->hsync_end - mode->hsync_start;
+
+       if (hsync_len > 0x40 || hsync_len < 1)
+               return MODE_HSYNC;
+
+       if (vsync_len > 0x40 || vsync_len < 1)
+               return MODE_VSYNC;
+
+       if (hfront_porch > 0x200 || hfront_porch < 1 ||
+           hback_porch > 0x200 || hback_porch < 1 ||
+           mode->hdisplay < 1)
+               return MODE_H_ILLEGAL;
+
+       if (vfront_porch > 0x40 || vfront_porch < 1 ||
+           vback_porch > 0x40 || vback_porch < 0 ||
+           mode->vdisplay < 1)
+               return MODE_V_ILLEGAL;
+
+       return MODE_OK;
+}
+
+static irqreturn_t atmel_hlcdc_dc_irq_handler(int irq, void *data)
+{
+       struct drm_device *dev = data;
+       struct atmel_hlcdc_dc *dc = dev->dev_private;
+       unsigned long status;
+       unsigned int imr, isr;
+       int i;
+
+       regmap_read(dc->hlcdc->regmap, ATMEL_HLCDC_IMR, &imr);
+       regmap_read(dc->hlcdc->regmap, ATMEL_HLCDC_ISR, &isr);
+       status = imr & isr;
+       if (!status)
+               return IRQ_NONE;
+
+       if (status & ATMEL_HLCDC_SOF)
+               atmel_hlcdc_crtc_irq(dc->crtc);
+
+       for (i = 0; i < ATMEL_HLCDC_MAX_LAYERS; i++) {
+               struct atmel_hlcdc_layer *layer = dc->layers[i];
+
+               if (!(ATMEL_HLCDC_LAYER_STATUS(i) & status) || !layer)
+                       continue;
+
+               atmel_hlcdc_layer_irq(layer);
+       }
+
+       return IRQ_HANDLED;
+}
+
+static struct drm_framebuffer *atmel_hlcdc_fb_create(struct drm_device *dev,
+               struct drm_file *file_priv, struct drm_mode_fb_cmd2 *mode_cmd)
+{
+       return drm_fb_cma_create(dev, file_priv, mode_cmd);
+}
+
+static void atmel_hlcdc_fb_output_poll_changed(struct drm_device *dev)
+{
+       struct atmel_hlcdc_dc *dc = dev->dev_private;
+
+       if (dc->fbdev) {
+               drm_fbdev_cma_hotplug_event(dc->fbdev);
+       } else {
+               dc->fbdev = drm_fbdev_cma_init(dev, 24,
+                               dev->mode_config.num_crtc,
+                               dev->mode_config.num_connector);
+               if (IS_ERR(dc->fbdev))
+                       dc->fbdev = NULL;
+       }
+}
+
+static const struct drm_mode_config_funcs mode_config_funcs = {
+       .fb_create = atmel_hlcdc_fb_create,
+       .output_poll_changed = atmel_hlcdc_fb_output_poll_changed,
+};
+
+static int atmel_hlcdc_dc_modeset_init(struct drm_device *dev)
+{
+       struct atmel_hlcdc_dc *dc = dev->dev_private;
+       struct atmel_hlcdc_planes *planes;
+       int ret;
+       int i;
+
+       drm_mode_config_init(dev);
+
+       ret = atmel_hlcdc_create_outputs(dev);
+       if (ret) {
+               dev_err(dev->dev, "failed to create panel: %d\n", ret);
+               return ret;
+       }
+
+       planes = atmel_hlcdc_create_planes(dev);
+       if (IS_ERR(planes)) {
+               dev_err(dev->dev, "failed to create planes\n");
+               return PTR_ERR(planes);
+       }
+
+       dc->planes = planes;
+
+       dc->layers[planes->primary->layer.desc->id] =
+                                               &planes->primary->layer;
+
+       if (planes->cursor)
+               dc->layers[planes->cursor->layer.desc->id] =
+                                                       &planes->cursor->layer;
+
+       for (i = 0; i < planes->noverlays; i++)
+               dc->layers[planes->overlays[i]->layer.desc->id] =
+                                               &planes->overlays[i]->layer;
+
+       ret = atmel_hlcdc_crtc_create(dev);
+       if (ret) {
+               dev_err(dev->dev, "failed to create crtc\n");
+               return ret;
+       }
+
+       dev->mode_config.min_width = dc->desc->min_width;
+       dev->mode_config.min_height = dc->desc->min_height;
+       dev->mode_config.max_width = dc->desc->max_width;
+       dev->mode_config.max_height = dc->desc->max_height;
+       dev->mode_config.funcs = &mode_config_funcs;
+
+       return 0;
+}
+
+static int atmel_hlcdc_dc_load(struct drm_device *dev)
+{
+       struct platform_device *pdev = to_platform_device(dev->dev);
+       const struct of_device_id *match;
+       struct atmel_hlcdc_dc *dc;
+       int ret;
+
+       match = of_match_node(atmel_hlcdc_of_match, dev->dev->parent->of_node);
+       if (!match) {
+               dev_err(&pdev->dev, "invalid compatible string\n");
+               return -ENODEV;
+       }
+
+       if (!match->data) {
+               dev_err(&pdev->dev, "invalid hlcdc description\n");
+               return -EINVAL;
+       }
+
+       dc = devm_kzalloc(dev->dev, sizeof(*dc), GFP_KERNEL);
+       if (!dc)
+               return -ENOMEM;
+
+       dc->wq = alloc_ordered_workqueue("atmel-hlcdc-dc", 0);
+       if (!dc->wq)
+               return -ENOMEM;
+
+       dc->desc = match->data;
+       dc->hlcdc = dev_get_drvdata(dev->dev->parent);
+       dev->dev_private = dc;
+
+       ret = clk_prepare_enable(dc->hlcdc->periph_clk);
+       if (ret) {
+               dev_err(dev->dev, "failed to enable periph_clk\n");
+               goto err_destroy_wq;
+       }
+
+       pm_runtime_enable(dev->dev);
+
+       pm_runtime_put_sync(dev->dev);
+
+       ret = atmel_hlcdc_dc_modeset_init(dev);
+       if (ret < 0) {
+               dev_err(dev->dev, "failed to initialize mode setting\n");
+               goto err_periph_clk_disable;
+       }
+
+       ret = drm_vblank_init(dev, 1);
+       if (ret < 0) {
+               dev_err(dev->dev, "failed to initialize vblank\n");
+               goto err_periph_clk_disable;
+       }
+
+       pm_runtime_get_sync(dev->dev);
+       ret = drm_irq_install(dev, dc->hlcdc->irq);
+       pm_runtime_put_sync(dev->dev);
+       if (ret < 0) {
+               dev_err(dev->dev, "failed to install IRQ handler\n");
+               goto err_periph_clk_disable;
+       }
+
+       platform_set_drvdata(pdev, dev);
+
+       drm_kms_helper_poll_init(dev);
+
+       /* force connectors detection */
+       drm_helper_hpd_irq_event(dev);
+
+       return 0;
+
+err_periph_clk_disable:
+       pm_runtime_disable(dev->dev);
+       clk_disable_unprepare(dc->hlcdc->periph_clk);
+
+err_destroy_wq:
+       destroy_workqueue(dc->wq);
+
+       return ret;
+}
+
+static void atmel_hlcdc_dc_unload(struct drm_device *dev)
+{
+       struct atmel_hlcdc_dc *dc = dev->dev_private;
+
+       if (dc->fbdev)
+               drm_fbdev_cma_fini(dc->fbdev);
+       flush_workqueue(dc->wq);
+       drm_kms_helper_poll_fini(dev);
+       drm_mode_config_cleanup(dev);
+       drm_vblank_cleanup(dev);
+
+       pm_runtime_get_sync(dev->dev);
+       drm_irq_uninstall(dev);
+       pm_runtime_put_sync(dev->dev);
+
+       dev->dev_private = NULL;
+
+       pm_runtime_disable(dev->dev);
+       clk_disable_unprepare(dc->hlcdc->periph_clk);
+       destroy_workqueue(dc->wq);
+}
+
+static int atmel_hlcdc_dc_connector_plug_all(struct drm_device *dev)
+{
+       struct drm_connector *connector, *failed;
+       int ret;
+
+       mutex_lock(&dev->mode_config.mutex);
+       list_for_each_entry(connector, &dev->mode_config.connector_list, head) {
+               ret = drm_connector_register(connector);
+               if (ret) {
+                       failed = connector;
+                       goto err;
+               }
+       }
+       mutex_unlock(&dev->mode_config.mutex);
+       return 0;
+
+err:
+       list_for_each_entry(connector, &dev->mode_config.connector_list, head) {
+               if (failed == connector)
+                       break;
+
+               drm_connector_unregister(connector);
+       }
+       mutex_unlock(&dev->mode_config.mutex);
+
+       return ret;
+}
+
+static void atmel_hlcdc_dc_connector_unplug_all(struct drm_device *dev)
+{
+       mutex_lock(&dev->mode_config.mutex);
+       drm_connector_unplug_all(dev);
+       mutex_unlock(&dev->mode_config.mutex);
+}
+
+static void atmel_hlcdc_dc_preclose(struct drm_device *dev,
+                                   struct drm_file *file)
+{
+       struct drm_crtc *crtc;
+
+       list_for_each_entry(crtc, &dev->mode_config.crtc_list, head)
+               atmel_hlcdc_crtc_cancel_page_flip(crtc, file);
+}
+
+static void atmel_hlcdc_dc_lastclose(struct drm_device *dev)
+{
+       struct atmel_hlcdc_dc *dc = dev->dev_private;
+
+       drm_fbdev_cma_restore_mode(dc->fbdev);
+}
+
+static int atmel_hlcdc_dc_irq_postinstall(struct drm_device *dev)
+{
+       struct atmel_hlcdc_dc *dc = dev->dev_private;
+       unsigned int cfg = 0;
+       int i;
+
+       /* Enable interrupts on activated layers */
+       for (i = 0; i < ATMEL_HLCDC_MAX_LAYERS; i++) {
+               if (dc->layers[i])
+                       cfg |= ATMEL_HLCDC_LAYER_STATUS(i);
+       }
+
+       regmap_write(dc->hlcdc->regmap, ATMEL_HLCDC_IER, cfg);
+
+       return 0;
+}
+
+static void atmel_hlcdc_dc_irq_uninstall(struct drm_device *dev)
+{
+       struct atmel_hlcdc_dc *dc = dev->dev_private;
+       unsigned int isr;
+
+       regmap_write(dc->hlcdc->regmap, ATMEL_HLCDC_IDR, 0xffffffff);
+       regmap_read(dc->hlcdc->regmap, ATMEL_HLCDC_ISR, &isr);
+}
+
+static int atmel_hlcdc_dc_enable_vblank(struct drm_device *dev, int crtc)
+{
+       struct atmel_hlcdc_dc *dc = dev->dev_private;
+
+       /* Enable SOF (Start Of Frame) interrupt for vblank counting */
+       regmap_write(dc->hlcdc->regmap, ATMEL_HLCDC_IER, ATMEL_HLCDC_SOF);
+
+       return 0;
+}
+
+static void atmel_hlcdc_dc_disable_vblank(struct drm_device *dev, int crtc)
+{
+       struct atmel_hlcdc_dc *dc = dev->dev_private;
+
+       regmap_write(dc->hlcdc->regmap, ATMEL_HLCDC_IDR, ATMEL_HLCDC_SOF);
+}
+
+static const struct file_operations fops = {
+       .owner              = THIS_MODULE,
+       .open               = drm_open,
+       .release            = drm_release,
+       .unlocked_ioctl     = drm_ioctl,
+#ifdef CONFIG_COMPAT
+       .compat_ioctl       = drm_compat_ioctl,
+#endif
+       .poll               = drm_poll,
+       .read               = drm_read,
+       .llseek             = no_llseek,
+       .mmap               = drm_gem_cma_mmap,
+};
+
+static struct drm_driver atmel_hlcdc_dc_driver = {
+       .driver_features = DRIVER_HAVE_IRQ | DRIVER_GEM | DRIVER_MODESET,
+       .preclose = atmel_hlcdc_dc_preclose,
+       .lastclose = atmel_hlcdc_dc_lastclose,
+       .irq_handler = atmel_hlcdc_dc_irq_handler,
+       .irq_preinstall = atmel_hlcdc_dc_irq_uninstall,
+       .irq_postinstall = atmel_hlcdc_dc_irq_postinstall,
+       .irq_uninstall = atmel_hlcdc_dc_irq_uninstall,
+       .get_vblank_counter = drm_vblank_count,
+       .enable_vblank = atmel_hlcdc_dc_enable_vblank,
+       .disable_vblank = atmel_hlcdc_dc_disable_vblank,
+       .gem_free_object = drm_gem_cma_free_object,
+       .gem_vm_ops = &drm_gem_cma_vm_ops,
+       .dumb_create = drm_gem_cma_dumb_create,
+       .dumb_map_offset = drm_gem_cma_dumb_map_offset,
+       .dumb_destroy = drm_gem_dumb_destroy,
+       .fops = &fops,
+       .name = "atmel-hlcdc",
+       .desc = "Atmel HLCD Controller DRM",
+       .date = "20141504",
+       .major = 1,
+       .minor = 0,
+};
+
+static int atmel_hlcdc_dc_drm_probe(struct platform_device *pdev)
+{
+       struct drm_device *ddev;
+       int ret;
+
+       ddev = drm_dev_alloc(&atmel_hlcdc_dc_driver, &pdev->dev);
+       if (!ddev)
+               return -ENOMEM;
+
+       ret = drm_dev_set_unique(ddev, dev_name(ddev->dev));
+       if (ret)
+               goto err_unref;
+
+       ret = atmel_hlcdc_dc_load(ddev);
+       if (ret)
+               goto err_unref;
+
+       ret = drm_dev_register(ddev, 0);
+       if (ret)
+               goto err_unload;
+
+       ret = atmel_hlcdc_dc_connector_plug_all(ddev);
+       if (ret)
+               goto err_unregister;
+
+       return 0;
+
+err_unregister:
+       drm_dev_unregister(ddev);
+
+err_unload:
+       atmel_hlcdc_dc_unload(ddev);
+
+err_unref:
+       drm_dev_unref(ddev);
+
+       return ret;
+}
+
+static int atmel_hlcdc_dc_drm_remove(struct platform_device *pdev)
+{
+       struct drm_device *ddev = platform_get_drvdata(pdev);
+
+       atmel_hlcdc_dc_connector_unplug_all(ddev);
+       drm_dev_unregister(ddev);
+       atmel_hlcdc_dc_unload(ddev);
+       drm_dev_unref(ddev);
+
+       return 0;
+}
+
+static const struct of_device_id atmel_hlcdc_dc_of_match[] = {
+       { .compatible = "atmel,hlcdc-display-controller" },
+       { },
+};
+
+static struct platform_driver atmel_hlcdc_dc_platform_driver = {
+       .probe  = atmel_hlcdc_dc_drm_probe,
+       .remove = atmel_hlcdc_dc_drm_remove,
+       .driver = {
+               .name   = "atmel-hlcdc-display-controller",
+               .of_match_table = atmel_hlcdc_dc_of_match,
+       },
+};
+module_platform_driver(atmel_hlcdc_dc_platform_driver);
+
+MODULE_AUTHOR("Jean-Jacques Hiblot <jjhiblot@traphandler.com>");
+MODULE_AUTHOR("Boris Brezillon <boris.brezillon@free-electrons.com>");
+MODULE_DESCRIPTION("Atmel HLCDC Display Controller DRM Driver");
+MODULE_LICENSE("GPL");
+MODULE_ALIAS("platform:atmel-hlcdc-dc");
diff --git a/drivers/gpu/drm/atmel-hlcdc/atmel_hlcdc_dc.h b/drivers/gpu/drm/atmel-hlcdc/atmel_hlcdc_dc.h
new file mode 100644 (file)
index 0000000..7bc96af
--- /dev/null
@@ -0,0 +1,213 @@
+/*
+ * Copyright (C) 2014 Traphandler
+ * Copyright (C) 2014 Free Electrons
+ * Copyright (C) 2014 Atmel
+ *
+ * Author: Jean-Jacques Hiblot <jjhiblot@traphandler.com>
+ * Author: Boris BREZILLON <boris.brezillon@free-electrons.com>
+ *
+ * This program is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License version 2 as published by
+ * the Free Software Foundation.
+ *
+ * This program is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License for
+ * more details.
+ *
+ * You should have received a copy of the GNU General Public License along with
+ * this program.  If not, see <http://www.gnu.org/licenses/>.
+ */
+
+#ifndef DRM_ATMEL_HLCDC_H
+#define DRM_ATMEL_HLCDC_H
+
+#include <linux/clk.h>
+#include <linux/irqdomain.h>
+#include <linux/pwm.h>
+
+#include <drm/drm_crtc.h>
+#include <drm/drm_crtc_helper.h>
+#include <drm/drm_fb_cma_helper.h>
+#include <drm/drm_gem_cma_helper.h>
+#include <drm/drm_panel.h>
+#include <drm/drmP.h>
+
+#include "atmel_hlcdc_layer.h"
+
+#define ATMEL_HLCDC_MAX_LAYERS         5
+
+/**
+ * Atmel HLCDC Display Controller description structure.
+ *
+ * This structure describe the HLCDC IP capabilities and depends on the
+ * HLCDC IP version (or Atmel SoC family).
+ *
+ * @min_width: minimum width supported by the Display Controller
+ * @min_height: minimum height supported by the Display Controller
+ * @max_width: maximum width supported by the Display Controller
+ * @max_height: maximum height supported by the Display Controller
+ * @layers: a layer description table describing available layers
+ * @nlayers: layer description table size
+ */
+struct atmel_hlcdc_dc_desc {
+       int min_width;
+       int min_height;
+       int max_width;
+       int max_height;
+       const struct atmel_hlcdc_layer_desc *layers;
+       int nlayers;
+};
+
+/**
+ * Atmel HLCDC Plane properties.
+ *
+ * This structure stores plane property definitions.
+ *
+ * @alpha: alpha blending (or transparency) property
+ * @rotation: rotation property
+ */
+struct atmel_hlcdc_plane_properties {
+       struct drm_property *alpha;
+       struct drm_property *rotation;
+};
+
+/**
+ * Atmel HLCDC Plane.
+ *
+ * @base: base DRM plane structure
+ * @layer: HLCDC layer structure
+ * @properties: pointer to the property definitions structure
+ * @rotation: current rotation status
+ */
+struct atmel_hlcdc_plane {
+       struct drm_plane base;
+       struct atmel_hlcdc_layer layer;
+       struct atmel_hlcdc_plane_properties *properties;
+       unsigned int rotation;
+};
+
+static inline struct atmel_hlcdc_plane *
+drm_plane_to_atmel_hlcdc_plane(struct drm_plane *p)
+{
+       return container_of(p, struct atmel_hlcdc_plane, base);
+}
+
+static inline struct atmel_hlcdc_plane *
+atmel_hlcdc_layer_to_plane(struct atmel_hlcdc_layer *l)
+{
+       return container_of(l, struct atmel_hlcdc_plane, layer);
+}
+
+/**
+ * Atmel HLCDC Plane update request structure.
+ *
+ * @crtc_x: x position of the plane relative to the CRTC
+ * @crtc_y: y position of the plane relative to the CRTC
+ * @crtc_w: visible width of the plane
+ * @crtc_h: visible height of the plane
+ * @src_x: x buffer position
+ * @src_y: y buffer position
+ * @src_w: buffer width
+ * @src_h: buffer height
+ * @fb: framebuffer object object
+ * @bpp: bytes per pixel deduced from pixel_format
+ * @offsets: offsets to apply to the GEM buffers
+ * @xstride: value to add to the pixel pointer between each line
+ * @pstride: value to add to the pixel pointer between each pixel
+ * @nplanes: number of planes (deduced from pixel_format)
+ */
+struct atmel_hlcdc_plane_update_req {
+       int crtc_x;
+       int crtc_y;
+       unsigned int crtc_w;
+       unsigned int crtc_h;
+       uint32_t src_x;
+       uint32_t src_y;
+       uint32_t src_w;
+       uint32_t src_h;
+       struct drm_framebuffer *fb;
+
+       /* These fields are private and should not be touched */
+       int bpp[ATMEL_HLCDC_MAX_PLANES];
+       unsigned int offsets[ATMEL_HLCDC_MAX_PLANES];
+       int xstride[ATMEL_HLCDC_MAX_PLANES];
+       int pstride[ATMEL_HLCDC_MAX_PLANES];
+       int nplanes;
+};
+
+/**
+ * Atmel HLCDC Planes.
+ *
+ * This structure stores the instantiated HLCDC Planes and can be accessed by
+ * the HLCDC Display Controller or the HLCDC CRTC.
+ *
+ * @primary: primary plane
+ * @cursor: hardware cursor plane
+ * @overlays: overlay plane table
+ * @noverlays: number of overlay planes
+ */
+struct atmel_hlcdc_planes {
+       struct atmel_hlcdc_plane *primary;
+       struct atmel_hlcdc_plane *cursor;
+       struct atmel_hlcdc_plane **overlays;
+       int noverlays;
+};
+
+/**
+ * Atmel HLCDC Display Controller.
+ *
+ * @desc: HLCDC Display Controller description
+ * @hlcdc: pointer to the atmel_hlcdc structure provided by the MFD device
+ * @fbdev: framebuffer device attached to the Display Controller
+ * @crtc: CRTC provided by the display controller
+ * @planes: instantiated planes
+ * @layers: active HLCDC layer
+ * @wq: display controller workqueue
+ */
+struct atmel_hlcdc_dc {
+       const struct atmel_hlcdc_dc_desc *desc;
+       struct atmel_hlcdc *hlcdc;
+       struct drm_fbdev_cma *fbdev;
+       struct drm_crtc *crtc;
+       struct atmel_hlcdc_planes *planes;
+       struct atmel_hlcdc_layer *layers[ATMEL_HLCDC_MAX_LAYERS];
+       struct workqueue_struct *wq;
+};
+
+extern struct atmel_hlcdc_formats atmel_hlcdc_plane_rgb_formats;
+extern struct atmel_hlcdc_formats atmel_hlcdc_plane_rgb_and_yuv_formats;
+
+int atmel_hlcdc_dc_mode_valid(struct atmel_hlcdc_dc *dc,
+                             struct drm_display_mode *mode);
+
+struct atmel_hlcdc_planes *
+atmel_hlcdc_create_planes(struct drm_device *dev);
+
+int atmel_hlcdc_plane_prepare_update_req(struct drm_plane *p,
+                               struct atmel_hlcdc_plane_update_req *req,
+                               const struct drm_display_mode *mode);
+
+int atmel_hlcdc_plane_apply_update_req(struct drm_plane *p,
+                               struct atmel_hlcdc_plane_update_req *req);
+
+int atmel_hlcdc_plane_update_with_mode(struct drm_plane *p,
+                                      struct drm_crtc *crtc,
+                                      struct drm_framebuffer *fb,
+                                      int crtc_x, int crtc_y,
+                                      unsigned int crtc_w,
+                                      unsigned int crtc_h,
+                                      uint32_t src_x, uint32_t src_y,
+                                      uint32_t src_w, uint32_t src_h,
+                                      const struct drm_display_mode *mode);
+
+void atmel_hlcdc_crtc_irq(struct drm_crtc *c);
+
+void atmel_hlcdc_crtc_cancel_page_flip(struct drm_crtc *crtc,
+                                      struct drm_file *file);
+
+int atmel_hlcdc_crtc_create(struct drm_device *dev);
+
+int atmel_hlcdc_create_outputs(struct drm_device *dev);
+
+#endif /* DRM_ATMEL_HLCDC_H */
diff --git a/drivers/gpu/drm/atmel-hlcdc/atmel_hlcdc_layer.c b/drivers/gpu/drm/atmel-hlcdc/atmel_hlcdc_layer.c
new file mode 100644 (file)
index 0000000..063d2a7
--- /dev/null
@@ -0,0 +1,667 @@
+/*
+ * Copyright (C) 2014 Free Electrons
+ * Copyright (C) 2014 Atmel
+ *
+ * Author: Boris BREZILLON <boris.brezillon@free-electrons.com>
+ *
+ * This program is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License version 2 as published by
+ * the Free Software Foundation.
+ *
+ * This program is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License for
+ * more details.
+ *
+ * You should have received a copy of the GNU General Public License along with
+ * this program.  If not, see <http://www.gnu.org/licenses/>.
+ */
+
+#include <linux/dma-mapping.h>
+#include <linux/interrupt.h>
+
+#include "atmel_hlcdc_dc.h"
+
+static void
+atmel_hlcdc_layer_fb_flip_release(struct drm_flip_work *work, void *val)
+{
+       struct atmel_hlcdc_layer_fb_flip *flip = val;
+
+       if (flip->fb)
+               drm_framebuffer_unreference(flip->fb);
+       kfree(flip);
+}
+
+static void
+atmel_hlcdc_layer_fb_flip_destroy(struct atmel_hlcdc_layer_fb_flip *flip)
+{
+       if (flip->fb)
+               drm_framebuffer_unreference(flip->fb);
+       kfree(flip->task);
+       kfree(flip);
+}
+
+static void
+atmel_hlcdc_layer_fb_flip_release_queue(struct atmel_hlcdc_layer *layer,
+                                       struct atmel_hlcdc_layer_fb_flip *flip)
+{
+       int i;
+
+       if (!flip)
+               return;
+
+       for (i = 0; i < layer->max_planes; i++) {
+               if (!flip->dscrs[i])
+                       break;
+
+               flip->dscrs[i]->status = 0;
+               flip->dscrs[i] = NULL;
+       }
+
+       drm_flip_work_queue_task(&layer->gc, flip->task);
+       drm_flip_work_commit(&layer->gc, layer->wq);
+}
+
+static void atmel_hlcdc_layer_update_reset(struct atmel_hlcdc_layer *layer,
+                                          int id)
+{
+       struct atmel_hlcdc_layer_update *upd = &layer->update;
+       struct atmel_hlcdc_layer_update_slot *slot;
+
+       if (id < 0 || id > 1)
+               return;
+
+       slot = &upd->slots[id];
+       bitmap_clear(slot->updated_configs, 0, layer->desc->nconfigs);
+       memset(slot->configs, 0,
+              sizeof(*slot->configs) * layer->desc->nconfigs);
+
+       if (slot->fb_flip) {
+               atmel_hlcdc_layer_fb_flip_release_queue(layer, slot->fb_flip);
+               slot->fb_flip = NULL;
+       }
+}
+
+static void atmel_hlcdc_layer_update_apply(struct atmel_hlcdc_layer *layer)
+{
+       struct atmel_hlcdc_layer_dma_channel *dma = &layer->dma;
+       const struct atmel_hlcdc_layer_desc *desc = layer->desc;
+       struct atmel_hlcdc_layer_update *upd = &layer->update;
+       struct regmap *regmap = layer->hlcdc->regmap;
+       struct atmel_hlcdc_layer_update_slot *slot;
+       struct atmel_hlcdc_layer_fb_flip *fb_flip;
+       struct atmel_hlcdc_dma_channel_dscr *dscr;
+       unsigned int cfg;
+       u32 action = 0;
+       int i = 0;
+
+       if (upd->pending < 0 || upd->pending > 1)
+               return;
+
+       slot = &upd->slots[upd->pending];
+
+       for_each_set_bit(cfg, slot->updated_configs, layer->desc->nconfigs) {
+               regmap_write(regmap,
+                            desc->regs_offset +
+                            ATMEL_HLCDC_LAYER_CFG(layer, cfg),
+                            slot->configs[cfg]);
+               action |= ATMEL_HLCDC_LAYER_UPDATE;
+       }
+
+       fb_flip = slot->fb_flip;
+
+       if (!fb_flip->fb)
+               goto apply;
+
+       if (dma->status == ATMEL_HLCDC_LAYER_DISABLED) {
+               for (i = 0; i < fb_flip->ngems; i++) {
+                       dscr = fb_flip->dscrs[i];
+                       dscr->ctrl = ATMEL_HLCDC_LAYER_DFETCH |
+                                    ATMEL_HLCDC_LAYER_DMA_IRQ |
+                                    ATMEL_HLCDC_LAYER_ADD_IRQ |
+                                    ATMEL_HLCDC_LAYER_DONE_IRQ;
+
+                       regmap_write(regmap,
+                                    desc->regs_offset +
+                                    ATMEL_HLCDC_LAYER_PLANE_ADDR(i),
+                                    dscr->addr);
+                       regmap_write(regmap,
+                                    desc->regs_offset +
+                                    ATMEL_HLCDC_LAYER_PLANE_CTRL(i),
+                                    dscr->ctrl);
+                       regmap_write(regmap,
+                                    desc->regs_offset +
+                                    ATMEL_HLCDC_LAYER_PLANE_NEXT(i),
+                                    dscr->next);
+               }
+
+               action |= ATMEL_HLCDC_LAYER_DMA_CHAN;
+               dma->status = ATMEL_HLCDC_LAYER_ENABLED;
+       } else {
+               for (i = 0; i < fb_flip->ngems; i++) {
+                       dscr =  fb_flip->dscrs[i];
+                       dscr->ctrl = ATMEL_HLCDC_LAYER_DFETCH |
+                                    ATMEL_HLCDC_LAYER_DMA_IRQ |
+                                    ATMEL_HLCDC_LAYER_DSCR_IRQ |
+                                    ATMEL_HLCDC_LAYER_DONE_IRQ;
+
+                       regmap_write(regmap,
+                                    desc->regs_offset +
+                                    ATMEL_HLCDC_LAYER_PLANE_HEAD(i),
+                                    dscr->next);
+               }
+
+               action |= ATMEL_HLCDC_LAYER_A2Q;
+       }
+
+       /* Release unneeded descriptors */
+       for (i = fb_flip->ngems; i < layer->max_planes; i++) {
+               fb_flip->dscrs[i]->status = 0;
+               fb_flip->dscrs[i] = NULL;
+       }
+
+       dma->queue = fb_flip;
+       slot->fb_flip = NULL;
+
+apply:
+       if (action)
+               regmap_write(regmap,
+                            desc->regs_offset + ATMEL_HLCDC_LAYER_CHER,
+                            action);
+
+       atmel_hlcdc_layer_update_reset(layer, upd->pending);
+
+       upd->pending = -1;
+}
+
+void atmel_hlcdc_layer_irq(struct atmel_hlcdc_layer *layer)
+{
+       struct atmel_hlcdc_layer_dma_channel *dma = &layer->dma;
+       const struct atmel_hlcdc_layer_desc *desc = layer->desc;
+       struct regmap *regmap = layer->hlcdc->regmap;
+       struct atmel_hlcdc_layer_fb_flip *flip;
+       unsigned long flags;
+       unsigned int isr, imr;
+       unsigned int status;
+       unsigned int plane_status;
+       u32 flip_status;
+
+       int i;
+
+       regmap_read(regmap, desc->regs_offset + ATMEL_HLCDC_LAYER_IMR, &imr);
+       regmap_read(regmap, desc->regs_offset + ATMEL_HLCDC_LAYER_ISR, &isr);
+       status = imr & isr;
+       if (!status)
+               return;
+
+       spin_lock_irqsave(&layer->lock, flags);
+
+       flip = dma->queue ? dma->queue : dma->cur;
+
+       if (!flip) {
+               spin_unlock_irqrestore(&layer->lock, flags);
+               return;
+       }
+
+       /*
+        * Set LOADED and DONE flags: they'll be cleared if at least one
+        * memory plane is not LOADED or DONE.
+        */
+       flip_status = ATMEL_HLCDC_DMA_CHANNEL_DSCR_LOADED |
+                     ATMEL_HLCDC_DMA_CHANNEL_DSCR_DONE;
+       for (i = 0; i < flip->ngems; i++) {
+               plane_status = (status >> (8 * i));
+
+               if (plane_status &
+                   (ATMEL_HLCDC_LAYER_ADD_IRQ |
+                    ATMEL_HLCDC_LAYER_DSCR_IRQ) &
+                   ~flip->dscrs[i]->ctrl) {
+                       flip->dscrs[i]->status |=
+                                       ATMEL_HLCDC_DMA_CHANNEL_DSCR_LOADED;
+                       flip->dscrs[i]->ctrl |=
+                                       ATMEL_HLCDC_LAYER_ADD_IRQ |
+                                       ATMEL_HLCDC_LAYER_DSCR_IRQ;
+               }
+
+               if (plane_status &
+                   ATMEL_HLCDC_LAYER_DONE_IRQ &
+                   ~flip->dscrs[i]->ctrl) {
+                       flip->dscrs[i]->status |=
+                                       ATMEL_HLCDC_DMA_CHANNEL_DSCR_DONE;
+                       flip->dscrs[i]->ctrl |=
+                                       ATMEL_HLCDC_LAYER_DONE_IRQ;
+               }
+
+               if (plane_status & ATMEL_HLCDC_LAYER_OVR_IRQ)
+                       flip->dscrs[i]->status |=
+                                       ATMEL_HLCDC_DMA_CHANNEL_DSCR_OVERRUN;
+
+               /*
+                * Clear LOADED and DONE flags if the memory plane is either
+                * not LOADED or not DONE.
+                */
+               if (!(flip->dscrs[i]->status &
+                     ATMEL_HLCDC_DMA_CHANNEL_DSCR_LOADED))
+                       flip_status &= ~ATMEL_HLCDC_DMA_CHANNEL_DSCR_LOADED;
+
+               if (!(flip->dscrs[i]->status &
+                     ATMEL_HLCDC_DMA_CHANNEL_DSCR_DONE))
+                       flip_status &= ~ATMEL_HLCDC_DMA_CHANNEL_DSCR_DONE;
+
+               /*
+                * An overrun on one memory plane impact the whole framebuffer
+                * transfer, hence we set the OVERRUN flag as soon as there's
+                * one memory plane reporting such an overrun.
+                */
+               flip_status |= flip->dscrs[i]->status &
+                              ATMEL_HLCDC_DMA_CHANNEL_DSCR_OVERRUN;
+       }
+
+       /* Get changed bits */
+       flip_status ^= flip->status;
+       flip->status |= flip_status;
+
+       if (flip_status & ATMEL_HLCDC_DMA_CHANNEL_DSCR_LOADED) {
+               atmel_hlcdc_layer_fb_flip_release_queue(layer, dma->cur);
+               dma->cur = dma->queue;
+               dma->queue = NULL;
+       }
+
+       if (flip_status & ATMEL_HLCDC_DMA_CHANNEL_DSCR_DONE) {
+               atmel_hlcdc_layer_fb_flip_release_queue(layer, dma->cur);
+               dma->cur = NULL;
+       }
+
+       if (flip_status & ATMEL_HLCDC_DMA_CHANNEL_DSCR_OVERRUN) {
+               regmap_write(regmap,
+                            desc->regs_offset + ATMEL_HLCDC_LAYER_CHDR,
+                            ATMEL_HLCDC_LAYER_RST);
+               if (dma->queue)
+                       atmel_hlcdc_layer_fb_flip_release_queue(layer,
+                                                               dma->queue);
+
+               if (dma->cur)
+                       atmel_hlcdc_layer_fb_flip_release_queue(layer,
+                                                               dma->cur);
+
+               dma->cur = NULL;
+               dma->queue = NULL;
+       }
+
+       if (!dma->queue) {
+               atmel_hlcdc_layer_update_apply(layer);
+
+               if (!dma->cur)
+                       dma->status = ATMEL_HLCDC_LAYER_DISABLED;
+       }
+
+       spin_unlock_irqrestore(&layer->lock, flags);
+}
+
+int atmel_hlcdc_layer_disable(struct atmel_hlcdc_layer *layer)
+{
+       struct atmel_hlcdc_layer_dma_channel *dma = &layer->dma;
+       struct atmel_hlcdc_layer_update *upd = &layer->update;
+       struct regmap *regmap = layer->hlcdc->regmap;
+       const struct atmel_hlcdc_layer_desc *desc = layer->desc;
+       unsigned long flags;
+       unsigned int isr;
+
+       spin_lock_irqsave(&layer->lock, flags);
+
+       /* Disable the layer */
+       regmap_write(regmap, desc->regs_offset + ATMEL_HLCDC_LAYER_CHDR,
+                    ATMEL_HLCDC_LAYER_RST);
+
+       /* Clear all pending interrupts */
+       regmap_read(regmap, desc->regs_offset + ATMEL_HLCDC_LAYER_ISR, &isr);
+
+       /* Discard current and queued framebuffer transfers. */
+       if (dma->cur) {
+               atmel_hlcdc_layer_fb_flip_release_queue(layer, dma->cur);
+               dma->cur = NULL;
+       }
+
+       if (dma->queue) {
+               atmel_hlcdc_layer_fb_flip_release_queue(layer, dma->queue);
+               dma->queue = NULL;
+       }
+
+       /*
+        * Then discard the pending update request (if any) to prevent
+        * DMA irq handler from restarting the DMA channel after it has
+        * been disabled.
+        */
+       if (upd->pending >= 0) {
+               atmel_hlcdc_layer_update_reset(layer, upd->pending);
+               upd->pending = -1;
+       }
+
+       dma->status = ATMEL_HLCDC_LAYER_DISABLED;
+
+       spin_unlock_irqrestore(&layer->lock, flags);
+
+       return 0;
+}
+
+int atmel_hlcdc_layer_update_start(struct atmel_hlcdc_layer *layer)
+{
+       struct atmel_hlcdc_layer_dma_channel *dma = &layer->dma;
+       struct atmel_hlcdc_layer_update *upd = &layer->update;
+       struct regmap *regmap = layer->hlcdc->regmap;
+       struct atmel_hlcdc_layer_fb_flip *fb_flip;
+       struct atmel_hlcdc_layer_update_slot *slot;
+       unsigned long flags;
+       int i, j = 0;
+
+       fb_flip = kzalloc(sizeof(*fb_flip), GFP_KERNEL);
+       if (!fb_flip)
+               return -ENOMEM;
+
+       fb_flip->task = drm_flip_work_allocate_task(fb_flip, GFP_KERNEL);
+       if (!fb_flip->task) {
+               kfree(fb_flip);
+               return -ENOMEM;
+       }
+
+       spin_lock_irqsave(&layer->lock, flags);
+
+       upd->next = upd->pending ? 0 : 1;
+
+       slot = &upd->slots[upd->next];
+
+       for (i = 0; i < layer->max_planes * 4; i++) {
+               if (!dma->dscrs[i].status) {
+                       fb_flip->dscrs[j++] = &dma->dscrs[i];
+                       dma->dscrs[i].status =
+                               ATMEL_HLCDC_DMA_CHANNEL_DSCR_RESERVED;
+                       if (j == layer->max_planes)
+                               break;
+               }
+       }
+
+       if (j < layer->max_planes) {
+               for (i = 0; i < j; i++)
+                       fb_flip->dscrs[i]->status = 0;
+       }
+
+       if (j < layer->max_planes) {
+               spin_unlock_irqrestore(&layer->lock, flags);
+               atmel_hlcdc_layer_fb_flip_destroy(fb_flip);
+               return -EBUSY;
+       }
+
+       slot->fb_flip = fb_flip;
+
+       if (upd->pending >= 0) {
+               memcpy(slot->configs,
+                      upd->slots[upd->pending].configs,
+                      layer->desc->nconfigs * sizeof(u32));
+               memcpy(slot->updated_configs,
+                      upd->slots[upd->pending].updated_configs,
+                      DIV_ROUND_UP(layer->desc->nconfigs,
+                                   BITS_PER_BYTE * sizeof(unsigned long)) *
+                      sizeof(unsigned long));
+               slot->fb_flip->fb = upd->slots[upd->pending].fb_flip->fb;
+               if (upd->slots[upd->pending].fb_flip->fb) {
+                       slot->fb_flip->fb =
+                               upd->slots[upd->pending].fb_flip->fb;
+                       slot->fb_flip->ngems =
+                               upd->slots[upd->pending].fb_flip->ngems;
+                       drm_framebuffer_reference(slot->fb_flip->fb);
+               }
+       } else {
+               regmap_bulk_read(regmap,
+                                layer->desc->regs_offset +
+                                ATMEL_HLCDC_LAYER_CFG(layer, 0),
+                                upd->slots[upd->next].configs,
+                                layer->desc->nconfigs);
+       }
+
+       spin_unlock_irqrestore(&layer->lock, flags);
+
+       return 0;
+}
+
+void atmel_hlcdc_layer_update_rollback(struct atmel_hlcdc_layer *layer)
+{
+       struct atmel_hlcdc_layer_update *upd = &layer->update;
+
+       atmel_hlcdc_layer_update_reset(layer, upd->next);
+       upd->next = -1;
+}
+
+void atmel_hlcdc_layer_update_set_fb(struct atmel_hlcdc_layer *layer,
+                                    struct drm_framebuffer *fb,
+                                    unsigned int *offsets)
+{
+       struct atmel_hlcdc_layer_update *upd = &layer->update;
+       struct atmel_hlcdc_layer_fb_flip *fb_flip;
+       struct atmel_hlcdc_layer_update_slot *slot;
+       struct atmel_hlcdc_dma_channel_dscr *dscr;
+       struct drm_framebuffer *old_fb;
+       int nplanes = 0;
+       int i;
+
+       if (upd->next < 0 || upd->next > 1)
+               return;
+
+       if (fb)
+               nplanes = drm_format_num_planes(fb->pixel_format);
+
+       if (nplanes > layer->max_planes)
+               return;
+
+       slot = &upd->slots[upd->next];
+
+       fb_flip = slot->fb_flip;
+       old_fb = slot->fb_flip->fb;
+
+       for (i = 0; i < nplanes; i++) {
+               struct drm_gem_cma_object *gem;
+
+               dscr = slot->fb_flip->dscrs[i];
+               gem = drm_fb_cma_get_gem_obj(fb, i);
+               dscr->addr = gem->paddr + offsets[i];
+       }
+
+       fb_flip->ngems = nplanes;
+       fb_flip->fb = fb;
+
+       if (fb)
+               drm_framebuffer_reference(fb);
+
+       if (old_fb)
+               drm_framebuffer_unreference(old_fb);
+}
+
+void atmel_hlcdc_layer_update_cfg(struct atmel_hlcdc_layer *layer, int cfg,
+                                 u32 mask, u32 val)
+{
+       struct atmel_hlcdc_layer_update *upd = &layer->update;
+       struct atmel_hlcdc_layer_update_slot *slot;
+
+       if (upd->next < 0 || upd->next > 1)
+               return;
+
+       if (cfg >= layer->desc->nconfigs)
+               return;
+
+       slot = &upd->slots[upd->next];
+       slot->configs[cfg] &= ~mask;
+       slot->configs[cfg] |= (val & mask);
+       set_bit(cfg, slot->updated_configs);
+}
+
+void atmel_hlcdc_layer_update_commit(struct atmel_hlcdc_layer *layer)
+{
+       struct atmel_hlcdc_layer_dma_channel *dma = &layer->dma;
+       struct atmel_hlcdc_layer_update *upd = &layer->update;
+       struct atmel_hlcdc_layer_update_slot *slot;
+       unsigned long flags;
+
+       if (upd->next < 0  || upd->next > 1)
+               return;
+
+       slot = &upd->slots[upd->next];
+
+       spin_lock_irqsave(&layer->lock, flags);
+
+       /*
+        * Release pending update request and replace it by the new one.
+        */
+       if (upd->pending >= 0)
+               atmel_hlcdc_layer_update_reset(layer, upd->pending);
+
+       upd->pending = upd->next;
+       upd->next = -1;
+
+       if (!dma->queue)
+               atmel_hlcdc_layer_update_apply(layer);
+
+       spin_unlock_irqrestore(&layer->lock, flags);
+
+
+       upd->next = -1;
+}
+
+static int atmel_hlcdc_layer_dma_init(struct drm_device *dev,
+                                     struct atmel_hlcdc_layer *layer)
+{
+       struct atmel_hlcdc_layer_dma_channel *dma = &layer->dma;
+       dma_addr_t dma_addr;
+       int i;
+
+       dma->dscrs = dma_alloc_coherent(dev->dev,
+                                       layer->max_planes * 4 *
+                                       sizeof(*dma->dscrs),
+                                       &dma_addr, GFP_KERNEL);
+       if (!dma->dscrs)
+               return -ENOMEM;
+
+       for (i = 0; i < layer->max_planes * 4; i++) {
+               struct atmel_hlcdc_dma_channel_dscr *dscr = &dma->dscrs[i];
+
+               dscr->next = dma_addr + (i * sizeof(*dscr));
+       }
+
+       return 0;
+}
+
+static void atmel_hlcdc_layer_dma_cleanup(struct drm_device *dev,
+                                         struct atmel_hlcdc_layer *layer)
+{
+       struct atmel_hlcdc_layer_dma_channel *dma = &layer->dma;
+       int i;
+
+       for (i = 0; i < layer->max_planes * 4; i++) {
+               struct atmel_hlcdc_dma_channel_dscr *dscr = &dma->dscrs[i];
+
+               dscr->status = 0;
+       }
+
+       dma_free_coherent(dev->dev, layer->max_planes * 4 *
+                         sizeof(*dma->dscrs), dma->dscrs,
+                         dma->dscrs[0].next);
+}
+
+static int atmel_hlcdc_layer_update_init(struct drm_device *dev,
+                               struct atmel_hlcdc_layer *layer,
+                               const struct atmel_hlcdc_layer_desc *desc)
+{
+       struct atmel_hlcdc_layer_update *upd = &layer->update;
+       int updated_size;
+       void *buffer;
+       int i;
+
+       updated_size = DIV_ROUND_UP(desc->nconfigs,
+                                   BITS_PER_BYTE *
+                                   sizeof(unsigned long));
+
+       buffer = devm_kzalloc(dev->dev,
+                             ((desc->nconfigs * sizeof(u32)) +
+                               (updated_size * sizeof(unsigned long))) * 2,
+                             GFP_KERNEL);
+       if (!buffer)
+               return -ENOMEM;
+
+       for (i = 0; i < 2; i++) {
+               upd->slots[i].updated_configs = buffer;
+               buffer += updated_size * sizeof(unsigned long);
+               upd->slots[i].configs = buffer;
+               buffer += desc->nconfigs * sizeof(u32);
+       }
+
+       upd->pending = -1;
+       upd->next = -1;
+
+       return 0;
+}
+
+int atmel_hlcdc_layer_init(struct drm_device *dev,
+                          struct atmel_hlcdc_layer *layer,
+                          const struct atmel_hlcdc_layer_desc *desc)
+{
+       struct atmel_hlcdc_dc *dc = dev->dev_private;
+       struct regmap *regmap = dc->hlcdc->regmap;
+       unsigned int tmp;
+       int ret;
+       int i;
+
+       layer->hlcdc = dc->hlcdc;
+       layer->wq = dc->wq;
+       layer->desc = desc;
+
+       regmap_write(regmap, desc->regs_offset + ATMEL_HLCDC_LAYER_CHDR,
+                    ATMEL_HLCDC_LAYER_RST);
+       for (i = 0; i < desc->formats->nformats; i++) {
+               int nplanes = drm_format_num_planes(desc->formats->formats[i]);
+
+               if (nplanes > layer->max_planes)
+                       layer->max_planes = nplanes;
+       }
+
+       spin_lock_init(&layer->lock);
+       drm_flip_work_init(&layer->gc, desc->name,
+                          atmel_hlcdc_layer_fb_flip_release);
+       ret = atmel_hlcdc_layer_dma_init(dev, layer);
+       if (ret)
+               return ret;
+
+       ret = atmel_hlcdc_layer_update_init(dev, layer, desc);
+       if (ret)
+               return ret;
+
+       /* Flush Status Register */
+       regmap_write(regmap, desc->regs_offset + ATMEL_HLCDC_LAYER_IDR,
+                    0xffffffff);
+       regmap_read(regmap, desc->regs_offset + ATMEL_HLCDC_LAYER_ISR,
+                   &tmp);
+
+       tmp = 0;
+       for (i = 0; i < layer->max_planes; i++)
+               tmp |= (ATMEL_HLCDC_LAYER_DMA_IRQ |
+                       ATMEL_HLCDC_LAYER_DSCR_IRQ |
+                       ATMEL_HLCDC_LAYER_ADD_IRQ |
+                       ATMEL_HLCDC_LAYER_DONE_IRQ |
+                       ATMEL_HLCDC_LAYER_OVR_IRQ) << (8 * i);
+
+       regmap_write(regmap, desc->regs_offset + ATMEL_HLCDC_LAYER_IER, tmp);
+
+       return 0;
+}
+
+void atmel_hlcdc_layer_cleanup(struct drm_device *dev,
+                              struct atmel_hlcdc_layer *layer)
+{
+       const struct atmel_hlcdc_layer_desc *desc = layer->desc;
+       struct regmap *regmap = layer->hlcdc->regmap;
+
+       regmap_write(regmap, desc->regs_offset + ATMEL_HLCDC_LAYER_IDR,
+                    0xffffffff);
+       regmap_write(regmap, desc->regs_offset + ATMEL_HLCDC_LAYER_CHDR,
+                    ATMEL_HLCDC_LAYER_RST);
+
+       atmel_hlcdc_layer_dma_cleanup(dev, layer);
+       drm_flip_work_cleanup(&layer->gc);
+}
diff --git a/drivers/gpu/drm/atmel-hlcdc/atmel_hlcdc_layer.h b/drivers/gpu/drm/atmel-hlcdc/atmel_hlcdc_layer.h
new file mode 100644 (file)
index 0000000..27e56c0
--- /dev/null
@@ -0,0 +1,398 @@
+/*
+ * Copyright (C) 2014 Free Electrons
+ * Copyright (C) 2014 Atmel
+ *
+ * Author: Boris BREZILLON <boris.brezillon@free-electrons.com>
+ *
+ * This program is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License version 2 as published by
+ * the Free Software Foundation.
+ *
+ * This program is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License for
+ * more details.
+ *
+ * You should have received a copy of the GNU General Public License along with
+ * this program.  If not, see <http://www.gnu.org/licenses/>.
+ */
+
+#ifndef DRM_ATMEL_HLCDC_LAYER_H
+#define DRM_ATMEL_HLCDC_LAYER_H
+
+#include <linux/mfd/atmel-hlcdc.h>
+
+#include <drm/drm_crtc.h>
+#include <drm/drm_flip_work.h>
+#include <drm/drmP.h>
+
+#define ATMEL_HLCDC_LAYER_CHER                 0x0
+#define ATMEL_HLCDC_LAYER_CHDR                 0x4
+#define ATMEL_HLCDC_LAYER_CHSR                 0x8
+#define ATMEL_HLCDC_LAYER_DMA_CHAN             BIT(0)
+#define ATMEL_HLCDC_LAYER_UPDATE               BIT(1)
+#define ATMEL_HLCDC_LAYER_A2Q                  BIT(2)
+#define ATMEL_HLCDC_LAYER_RST                  BIT(8)
+
+#define ATMEL_HLCDC_LAYER_IER                  0xc
+#define ATMEL_HLCDC_LAYER_IDR                  0x10
+#define ATMEL_HLCDC_LAYER_IMR                  0x14
+#define ATMEL_HLCDC_LAYER_ISR                  0x18
+#define ATMEL_HLCDC_LAYER_DFETCH               BIT(0)
+#define ATMEL_HLCDC_LAYER_LFETCH               BIT(1)
+#define ATMEL_HLCDC_LAYER_DMA_IRQ              BIT(2)
+#define ATMEL_HLCDC_LAYER_DSCR_IRQ             BIT(3)
+#define ATMEL_HLCDC_LAYER_ADD_IRQ              BIT(4)
+#define ATMEL_HLCDC_LAYER_DONE_IRQ             BIT(5)
+#define ATMEL_HLCDC_LAYER_OVR_IRQ              BIT(6)
+
+#define ATMEL_HLCDC_LAYER_PLANE_HEAD(n)                (((n) * 0x10) + 0x1c)
+#define ATMEL_HLCDC_LAYER_PLANE_ADDR(n)                (((n) * 0x10) + 0x20)
+#define ATMEL_HLCDC_LAYER_PLANE_CTRL(n)                (((n) * 0x10) + 0x24)
+#define ATMEL_HLCDC_LAYER_PLANE_NEXT(n)                (((n) * 0x10) + 0x28)
+#define ATMEL_HLCDC_LAYER_CFG(p, c)            (((c) * 4) + ((p)->max_planes * 0x10) + 0x1c)
+
+#define ATMEL_HLCDC_LAYER_DMA_CFG_ID           0
+#define ATMEL_HLCDC_LAYER_DMA_CFG(p)           ATMEL_HLCDC_LAYER_CFG(p, ATMEL_HLCDC_LAYER_DMA_CFG_ID)
+#define ATMEL_HLCDC_LAYER_DMA_SIF              BIT(0)
+#define ATMEL_HLCDC_LAYER_DMA_BLEN_MASK                GENMASK(5, 4)
+#define ATMEL_HLCDC_LAYER_DMA_BLEN_SINGLE      (0 << 4)
+#define ATMEL_HLCDC_LAYER_DMA_BLEN_INCR4       (1 << 4)
+#define ATMEL_HLCDC_LAYER_DMA_BLEN_INCR8       (2 << 4)
+#define ATMEL_HLCDC_LAYER_DMA_BLEN_INCR16      (3 << 4)
+#define ATMEL_HLCDC_LAYER_DMA_DLBO             BIT(8)
+#define ATMEL_HLCDC_LAYER_DMA_ROTDIS           BIT(12)
+#define ATMEL_HLCDC_LAYER_DMA_LOCKDIS          BIT(13)
+
+#define ATMEL_HLCDC_LAYER_FORMAT_CFG_ID                1
+#define ATMEL_HLCDC_LAYER_FORMAT_CFG(p)                ATMEL_HLCDC_LAYER_CFG(p, ATMEL_HLCDC_LAYER_FORMAT_CFG_ID)
+#define ATMEL_HLCDC_LAYER_RGB                  (0 << 0)
+#define ATMEL_HLCDC_LAYER_CLUT                 (1 << 0)
+#define ATMEL_HLCDC_LAYER_YUV                  (2 << 0)
+#define ATMEL_HLCDC_RGB_MODE(m)                        (((m) & 0xf) << 4)
+#define ATMEL_HLCDC_CLUT_MODE(m)               (((m) & 0x3) << 8)
+#define ATMEL_HLCDC_YUV_MODE(m)                        (((m) & 0xf) << 12)
+#define ATMEL_HLCDC_YUV422ROT                  BIT(16)
+#define ATMEL_HLCDC_YUV422SWP                  BIT(17)
+#define ATMEL_HLCDC_DSCALEOPT                  BIT(20)
+
+#define ATMEL_HLCDC_XRGB4444_MODE              (ATMEL_HLCDC_LAYER_RGB | ATMEL_HLCDC_RGB_MODE(0))
+#define ATMEL_HLCDC_ARGB4444_MODE              (ATMEL_HLCDC_LAYER_RGB | ATMEL_HLCDC_RGB_MODE(1))
+#define ATMEL_HLCDC_RGBA4444_MODE              (ATMEL_HLCDC_LAYER_RGB | ATMEL_HLCDC_RGB_MODE(2))
+#define ATMEL_HLCDC_RGB565_MODE                        (ATMEL_HLCDC_LAYER_RGB | ATMEL_HLCDC_RGB_MODE(3))
+#define ATMEL_HLCDC_ARGB1555_MODE              (ATMEL_HLCDC_LAYER_RGB | ATMEL_HLCDC_RGB_MODE(4))
+#define ATMEL_HLCDC_XRGB8888_MODE              (ATMEL_HLCDC_LAYER_RGB | ATMEL_HLCDC_RGB_MODE(9))
+#define ATMEL_HLCDC_RGB888_MODE                        (ATMEL_HLCDC_LAYER_RGB | ATMEL_HLCDC_RGB_MODE(10))
+#define ATMEL_HLCDC_ARGB8888_MODE              (ATMEL_HLCDC_LAYER_RGB | ATMEL_HLCDC_RGB_MODE(12))
+#define ATMEL_HLCDC_RGBA8888_MODE              (ATMEL_HLCDC_LAYER_RGB | ATMEL_HLCDC_RGB_MODE(13))
+
+#define ATMEL_HLCDC_AYUV_MODE                  (ATMEL_HLCDC_LAYER_YUV | ATMEL_HLCDC_YUV_MODE(0))
+#define ATMEL_HLCDC_YUYV_MODE                  (ATMEL_HLCDC_LAYER_YUV | ATMEL_HLCDC_YUV_MODE(1))
+#define ATMEL_HLCDC_UYVY_MODE                  (ATMEL_HLCDC_LAYER_YUV | ATMEL_HLCDC_YUV_MODE(2))
+#define ATMEL_HLCDC_YVYU_MODE                  (ATMEL_HLCDC_LAYER_YUV | ATMEL_HLCDC_YUV_MODE(3))
+#define ATMEL_HLCDC_VYUY_MODE                  (ATMEL_HLCDC_LAYER_YUV | ATMEL_HLCDC_YUV_MODE(4))
+#define ATMEL_HLCDC_NV61_MODE                  (ATMEL_HLCDC_LAYER_YUV | ATMEL_HLCDC_YUV_MODE(5))
+#define ATMEL_HLCDC_YUV422_MODE                        (ATMEL_HLCDC_LAYER_YUV | ATMEL_HLCDC_YUV_MODE(6))
+#define ATMEL_HLCDC_NV21_MODE                  (ATMEL_HLCDC_LAYER_YUV | ATMEL_HLCDC_YUV_MODE(7))
+#define ATMEL_HLCDC_YUV420_MODE                        (ATMEL_HLCDC_LAYER_YUV | ATMEL_HLCDC_YUV_MODE(8))
+
+#define ATMEL_HLCDC_LAYER_POS_CFG(p)           ATMEL_HLCDC_LAYER_CFG(p, (p)->desc->layout.pos)
+#define ATMEL_HLCDC_LAYER_SIZE_CFG(p)          ATMEL_HLCDC_LAYER_CFG(p, (p)->desc->layout.size)
+#define ATMEL_HLCDC_LAYER_MEMSIZE_CFG(p)       ATMEL_HLCDC_LAYER_CFG(p, (p)->desc->layout.memsize)
+#define ATMEL_HLCDC_LAYER_XSTRIDE_CFG(p)       ATMEL_HLCDC_LAYER_CFG(p, (p)->desc->layout.xstride)
+#define ATMEL_HLCDC_LAYER_PSTRIDE_CFG(p)       ATMEL_HLCDC_LAYER_CFG(p, (p)->desc->layout.pstride)
+#define ATMEL_HLCDC_LAYER_DFLTCOLOR_CFG(p)     ATMEL_HLCDC_LAYER_CFG(p, (p)->desc->layout.default_color)
+#define ATMEL_HLCDC_LAYER_CRKEY_CFG(p)         ATMEL_HLCDC_LAYER_CFG(p, (p)->desc->layout.chroma_key)
+#define ATMEL_HLCDC_LAYER_CRKEY_MASK_CFG(p)    ATMEL_HLCDC_LAYER_CFG(p, (p)->desc->layout.chroma_key_mask)
+
+#define ATMEL_HLCDC_LAYER_GENERAL_CFG(p)       ATMEL_HLCDC_LAYER_CFG(p, (p)->desc->layout.general_config)
+#define ATMEL_HLCDC_LAYER_CRKEY                        BIT(0)
+#define ATMEL_HLCDC_LAYER_INV                  BIT(1)
+#define ATMEL_HLCDC_LAYER_ITER2BL              BIT(2)
+#define ATMEL_HLCDC_LAYER_ITER                 BIT(3)
+#define ATMEL_HLCDC_LAYER_REVALPHA             BIT(4)
+#define ATMEL_HLCDC_LAYER_GAEN                 BIT(5)
+#define ATMEL_HLCDC_LAYER_LAEN                 BIT(6)
+#define ATMEL_HLCDC_LAYER_OVR                  BIT(7)
+#define ATMEL_HLCDC_LAYER_DMA                  BIT(8)
+#define ATMEL_HLCDC_LAYER_REP                  BIT(9)
+#define ATMEL_HLCDC_LAYER_DSTKEY               BIT(10)
+#define ATMEL_HLCDC_LAYER_DISCEN               BIT(11)
+#define ATMEL_HLCDC_LAYER_GA_SHIFT             16
+#define ATMEL_HLCDC_LAYER_GA_MASK              GENMASK(23, ATMEL_HLCDC_LAYER_GA_SHIFT)
+
+#define ATMEL_HLCDC_LAYER_CSC_CFG(p, o)                ATMEL_HLCDC_LAYER_CFG(p, (p)->desc->layout.csc + o)
+
+#define ATMEL_HLCDC_LAYER_DISC_POS_CFG(p)      ATMEL_HLCDC_LAYER_CFG(p, (p)->desc->layout.disc_pos)
+
+#define ATMEL_HLCDC_LAYER_DISC_SIZE_CFG(p)     ATMEL_HLCDC_LAYER_CFG(p, (p)->desc->layout.disc_size)
+
+#define ATMEL_HLCDC_MAX_PLANES                 3
+
+#define ATMEL_HLCDC_DMA_CHANNEL_DSCR_RESERVED  BIT(0)
+#define ATMEL_HLCDC_DMA_CHANNEL_DSCR_LOADED    BIT(1)
+#define ATMEL_HLCDC_DMA_CHANNEL_DSCR_DONE      BIT(2)
+#define ATMEL_HLCDC_DMA_CHANNEL_DSCR_OVERRUN   BIT(3)
+
+/**
+ * Atmel HLCDC Layer registers layout structure
+ *
+ * Each HLCDC layer has its own register organization and a given register
+ * can be placed differently on 2 different layers depending on its
+ * capabilities.
+ * This structure stores common registers layout for a given layer and is
+ * used by HLCDC layer code to choose the appropriate register to write to
+ * or to read from.
+ *
+ * For all fields, a value of zero means "unsupported".
+ *
+ * See Atmel's datasheet for a detailled description of these registers.
+ *
+ * @xstride: xstride registers
+ * @pstride: pstride registers
+ * @pos: position register
+ * @size: displayed size register
+ * @memsize: memory size register
+ * @default_color: default color register
+ * @chroma_key: chroma key register
+ * @chroma_key_mask: chroma key mask register
+ * @general_config: general layer config register
+ * @disc_pos: discard area position register
+ * @disc_size: discard area size register
+ * @csc: color space conversion register
+ */
+struct atmel_hlcdc_layer_cfg_layout {
+       int xstride[ATMEL_HLCDC_MAX_PLANES];
+       int pstride[ATMEL_HLCDC_MAX_PLANES];
+       int pos;
+       int size;
+       int memsize;
+       int default_color;
+       int chroma_key;
+       int chroma_key_mask;
+       int general_config;
+       int disc_pos;
+       int disc_size;
+       int csc;
+};
+
+/**
+ * Atmel HLCDC framebuffer flip structure
+ *
+ * This structure is allocated when someone asked for a layer update (most
+ * likely a DRM plane update, either primary, overlay or cursor plane) and
+ * released when the layer do not need to reference the framebuffer object
+ * anymore (i.e. the layer was disabled or updated).
+ *
+ * @dscrs: DMA descriptors
+ * @fb: the referenced framebuffer object
+ * @ngems: number of GEM objects referenced by the fb element
+ * @status: fb flip operation status
+ */
+struct atmel_hlcdc_layer_fb_flip {
+       struct atmel_hlcdc_dma_channel_dscr *dscrs[ATMEL_HLCDC_MAX_PLANES];
+       struct drm_flip_task *task;
+       struct drm_framebuffer *fb;
+       int ngems;
+       u32 status;
+};
+
+/**
+ * Atmel HLCDC DMA descriptor structure
+ *
+ * This structure is used by the HLCDC DMA engine to schedule a DMA transfer.
+ *
+ * The structure fields must remain in this specific order, because they're
+ * used by the HLCDC DMA engine, which expect them in this order.
+ * HLCDC DMA descriptors must be aligned on 64 bits.
+ *
+ * @addr: buffer DMA address
+ * @ctrl: DMA transfer options
+ * @next: next DMA descriptor to fetch
+ * @gem_flip: the attached gem_flip operation
+ */
+struct atmel_hlcdc_dma_channel_dscr {
+       dma_addr_t addr;
+       u32 ctrl;
+       dma_addr_t next;
+       u32 status;
+} __aligned(sizeof(u64));
+
+/**
+ * Atmel HLCDC layer types
+ */
+enum atmel_hlcdc_layer_type {
+       ATMEL_HLCDC_BASE_LAYER,
+       ATMEL_HLCDC_OVERLAY_LAYER,
+       ATMEL_HLCDC_CURSOR_LAYER,
+       ATMEL_HLCDC_PP_LAYER,
+};
+
+/**
+ * Atmel HLCDC Supported formats structure
+ *
+ * This structure list all the formats supported by a given layer.
+ *
+ * @nformats: number of supported formats
+ * @formats: supported formats
+ */
+struct atmel_hlcdc_formats {
+       int nformats;
+       uint32_t *formats;
+};
+
+/**
+ * Atmel HLCDC Layer description structure
+ *
+ * This structure describe the capabilities provided by a given layer.
+ *
+ * @name: layer name
+ * @type: layer type
+ * @id: layer id
+ * @regs_offset: offset of the layer registers from the HLCDC registers base
+ * @nconfigs: number of config registers provided by this layer
+ * @formats: supported formats
+ * @layout: config registers layout
+ * @max_width: maximum width supported by this layer (0 means unlimited)
+ * @max_height: maximum height supported by this layer (0 means unlimited)
+ */
+struct atmel_hlcdc_layer_desc {
+       const char *name;
+       enum atmel_hlcdc_layer_type type;
+       int id;
+       int regs_offset;
+       int nconfigs;
+       struct atmel_hlcdc_formats *formats;
+       struct atmel_hlcdc_layer_cfg_layout layout;
+       int max_width;
+       int max_height;
+};
+
+/**
+ * Atmel HLCDC Layer Update Slot structure
+ *
+ * This structure stores layer update requests to be applied on next frame.
+ * This is the base structure behind the atomic layer update infrastructure.
+ *
+ * Atomic layer update provides a way to update all layer's parameters
+ * simultaneously. This is needed to avoid incompatible sequential updates
+ * like this one:
+ * 1) update layer format from RGB888 (1 plane/buffer) to YUV422
+ *    (2 planes/buffers)
+ * 2) the format update is applied but the DMA channel for the second
+ *    plane/buffer is not enabled
+ * 3) enable the DMA channel for the second plane
+ *
+ * @fb_flip: fb_flip object
+ * @updated_configs: bitmask used to record modified configs
+ * @configs: new config values
+ */
+struct atmel_hlcdc_layer_update_slot {
+       struct atmel_hlcdc_layer_fb_flip *fb_flip;
+       unsigned long *updated_configs;
+       u32 *configs;
+};
+
+/**
+ * Atmel HLCDC Layer Update structure
+ *
+ * This structure provides a way to queue layer update requests.
+ *
+ * At a given time there is at most:
+ *  - one pending update request, which means the update request has been
+ *    committed (or validated) and is waiting for the DMA channel(s) to be
+ *    available
+ *  - one request being prepared, which means someone started a layer update
+ *    but has not committed it yet. There cannot be more than one started
+ *    request, because the update lock is taken when starting a layer update
+ *    and release when committing or rolling back the request.
+ *
+ * @slots: update slots. One is used for pending request and the other one
+ *        for started update request
+ * @pending: the pending slot index or -1 if no request is pending
+ * @next: the started update slot index or -1 no update has been started
+ */
+struct atmel_hlcdc_layer_update {
+       struct atmel_hlcdc_layer_update_slot slots[2];
+       int pending;
+       int next;
+};
+
+enum atmel_hlcdc_layer_dma_channel_status {
+       ATMEL_HLCDC_LAYER_DISABLED,
+       ATMEL_HLCDC_LAYER_ENABLED,
+       ATMEL_HLCDC_LAYER_DISABLING,
+};
+
+/**
+ * Atmel HLCDC Layer DMA channel structure
+ *
+ * This structure stores information on the DMA channel associated to a
+ * given layer.
+ *
+ * @status: DMA channel status
+ * @cur: current framebuffer
+ * @queue: next framebuffer
+ * @dscrs: allocated DMA descriptors
+ */
+struct atmel_hlcdc_layer_dma_channel {
+       enum atmel_hlcdc_layer_dma_channel_status status;
+       struct atmel_hlcdc_layer_fb_flip *cur;
+       struct atmel_hlcdc_layer_fb_flip *queue;
+       struct atmel_hlcdc_dma_channel_dscr *dscrs;
+};
+
+/**
+ * Atmel HLCDC Layer structure
+ *
+ * This structure stores information on the layer instance.
+ *
+ * @desc: layer description
+ * @max_planes: maximum planes/buffers that can be associated with this layer.
+ *            This depends on the supported formats.
+ * @hlcdc: pointer to the atmel_hlcdc structure provided by the MFD device
+ * @dma: dma channel
+ * @gc: fb flip garbage collector
+ * @update: update handler
+ * @lock: layer lock
+ */
+struct atmel_hlcdc_layer {
+       const struct atmel_hlcdc_layer_desc *desc;
+       int max_planes;
+       struct atmel_hlcdc *hlcdc;
+       struct workqueue_struct *wq;
+       struct drm_flip_work gc;
+       struct atmel_hlcdc_layer_dma_channel dma;
+       struct atmel_hlcdc_layer_update update;
+       spinlock_t lock;
+};
+
+void atmel_hlcdc_layer_irq(struct atmel_hlcdc_layer *layer);
+
+int atmel_hlcdc_layer_init(struct drm_device *dev,
+                          struct atmel_hlcdc_layer *layer,
+                          const struct atmel_hlcdc_layer_desc *desc);
+
+void atmel_hlcdc_layer_cleanup(struct drm_device *dev,
+                              struct atmel_hlcdc_layer *layer);
+
+int atmel_hlcdc_layer_disable(struct atmel_hlcdc_layer *layer);
+
+int atmel_hlcdc_layer_update_start(struct atmel_hlcdc_layer *layer);
+
+void atmel_hlcdc_layer_update_cfg(struct atmel_hlcdc_layer *layer, int cfg,
+                                 u32 mask, u32 val);
+
+void atmel_hlcdc_layer_update_set_fb(struct atmel_hlcdc_layer *layer,
+                                    struct drm_framebuffer *fb,
+                                    unsigned int *offsets);
+
+void atmel_hlcdc_layer_update_set_finished(struct atmel_hlcdc_layer *layer,
+                                          void (*finished)(void *data),
+                                          void *finished_data);
+
+void atmel_hlcdc_layer_update_rollback(struct atmel_hlcdc_layer *layer);
+
+void atmel_hlcdc_layer_update_commit(struct atmel_hlcdc_layer *layer);
+
+#endif /* DRM_ATMEL_HLCDC_LAYER_H */
diff --git a/drivers/gpu/drm/atmel-hlcdc/atmel_hlcdc_output.c b/drivers/gpu/drm/atmel-hlcdc/atmel_hlcdc_output.c
new file mode 100644 (file)
index 0000000..c402192
--- /dev/null
@@ -0,0 +1,319 @@
+/*
+ * Copyright (C) 2014 Traphandler
+ * Copyright (C) 2014 Free Electrons
+ * Copyright (C) 2014 Atmel
+ *
+ * Author: Jean-Jacques Hiblot <jjhiblot@traphandler.com>
+ * Author: Boris BREZILLON <boris.brezillon@free-electrons.com>
+ *
+ * This program is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License version 2 as published by
+ * the Free Software Foundation.
+ *
+ * This program is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License for
+ * more details.
+ *
+ * You should have received a copy of the GNU General Public License along with
+ * this program.  If not, see <http://www.gnu.org/licenses/>.
+ */
+
+#include <linux/of_graph.h>
+
+#include <drm/drmP.h>
+#include <drm/drm_panel.h>
+
+#include "atmel_hlcdc_dc.h"
+
+/**
+ * Atmel HLCDC RGB output mode
+ */
+enum atmel_hlcdc_connector_rgb_mode {
+       ATMEL_HLCDC_CONNECTOR_RGB444,
+       ATMEL_HLCDC_CONNECTOR_RGB565,
+       ATMEL_HLCDC_CONNECTOR_RGB666,
+       ATMEL_HLCDC_CONNECTOR_RGB888,
+};
+
+/**
+ * Atmel HLCDC RGB connector structure
+ *
+ * This structure stores RGB slave device information.
+ *
+ * @connector: DRM connector
+ * @encoder: DRM encoder
+ * @dc: pointer to the atmel_hlcdc_dc structure
+ * @dpms: current DPMS mode
+ */
+struct atmel_hlcdc_rgb_output {
+       struct drm_connector connector;
+       struct drm_encoder encoder;
+       struct atmel_hlcdc_dc *dc;
+       int dpms;
+};
+
+static inline struct atmel_hlcdc_rgb_output *
+drm_connector_to_atmel_hlcdc_rgb_output(struct drm_connector *connector)
+{
+       return container_of(connector, struct atmel_hlcdc_rgb_output,
+                           connector);
+}
+
+static inline struct atmel_hlcdc_rgb_output *
+drm_encoder_to_atmel_hlcdc_rgb_output(struct drm_encoder *encoder)
+{
+       return container_of(encoder, struct atmel_hlcdc_rgb_output, encoder);
+}
+
+/**
+ * Atmel HLCDC Panel device structure
+ *
+ * This structure is specialization of the slave device structure to
+ * interface with drm panels.
+ *
+ * @base: base slave device fields
+ * @panel: drm panel attached to this slave device
+ */
+struct atmel_hlcdc_panel {
+       struct atmel_hlcdc_rgb_output base;
+       struct drm_panel *panel;
+};
+
+static inline struct atmel_hlcdc_panel *
+atmel_hlcdc_rgb_output_to_panel(struct atmel_hlcdc_rgb_output *output)
+{
+       return container_of(output, struct atmel_hlcdc_panel, base);
+}
+
+static void atmel_hlcdc_panel_encoder_dpms(struct drm_encoder *encoder,
+                                          int mode)
+{
+       struct atmel_hlcdc_rgb_output *rgb =
+                       drm_encoder_to_atmel_hlcdc_rgb_output(encoder);
+       struct atmel_hlcdc_panel *panel = atmel_hlcdc_rgb_output_to_panel(rgb);
+
+       if (mode != DRM_MODE_DPMS_ON)
+               mode = DRM_MODE_DPMS_OFF;
+
+       if (mode == rgb->dpms)
+               return;
+
+       if (mode != DRM_MODE_DPMS_ON)
+               drm_panel_disable(panel->panel);
+       else
+               drm_panel_enable(panel->panel);
+
+       rgb->dpms = mode;
+}
+
+static bool
+atmel_hlcdc_panel_encoder_mode_fixup(struct drm_encoder *encoder,
+                                    const struct drm_display_mode *mode,
+                                    struct drm_display_mode *adjusted)
+{
+       return true;
+}
+
+static void atmel_hlcdc_panel_encoder_prepare(struct drm_encoder *encoder)
+{
+       atmel_hlcdc_panel_encoder_dpms(encoder, DRM_MODE_DPMS_OFF);
+}
+
+static void atmel_hlcdc_panel_encoder_commit(struct drm_encoder *encoder)
+{
+       atmel_hlcdc_panel_encoder_dpms(encoder, DRM_MODE_DPMS_ON);
+}
+
+static void
+atmel_hlcdc_rgb_encoder_mode_set(struct drm_encoder *encoder,
+                                struct drm_display_mode *mode,
+                                struct drm_display_mode *adjusted)
+{
+       struct atmel_hlcdc_rgb_output *rgb =
+                       drm_encoder_to_atmel_hlcdc_rgb_output(encoder);
+       struct drm_display_info *info = &rgb->connector.display_info;
+       unsigned int cfg;
+
+       cfg = 0;
+
+       if (info->num_bus_formats) {
+               switch (info->bus_formats[0]) {
+               case MEDIA_BUS_FMT_RGB666_1X18:
+                       cfg |= ATMEL_HLCDC_CONNECTOR_RGB666 << 8;
+                       break;
+               case MEDIA_BUS_FMT_RGB888_1X24:
+                       cfg |= ATMEL_HLCDC_CONNECTOR_RGB888 << 8;
+                       break;
+               default:
+                       break;
+               }
+       }
+
+       regmap_update_bits(rgb->dc->hlcdc->regmap, ATMEL_HLCDC_CFG(5),
+                          ATMEL_HLCDC_MODE_MASK,
+                          cfg);
+}
+
+static struct drm_encoder_helper_funcs atmel_hlcdc_panel_encoder_helper_funcs = {
+       .dpms = atmel_hlcdc_panel_encoder_dpms,
+       .mode_fixup = atmel_hlcdc_panel_encoder_mode_fixup,
+       .prepare = atmel_hlcdc_panel_encoder_prepare,
+       .commit = atmel_hlcdc_panel_encoder_commit,
+       .mode_set = atmel_hlcdc_rgb_encoder_mode_set,
+};
+
+static void atmel_hlcdc_rgb_encoder_destroy(struct drm_encoder *encoder)
+{
+       drm_encoder_cleanup(encoder);
+       memset(encoder, 0, sizeof(*encoder));
+}
+
+static const struct drm_encoder_funcs atmel_hlcdc_panel_encoder_funcs = {
+       .destroy = atmel_hlcdc_rgb_encoder_destroy,
+};
+
+static int atmel_hlcdc_panel_get_modes(struct drm_connector *connector)
+{
+       struct atmel_hlcdc_rgb_output *rgb =
+                       drm_connector_to_atmel_hlcdc_rgb_output(connector);
+       struct atmel_hlcdc_panel *panel = atmel_hlcdc_rgb_output_to_panel(rgb);
+
+       return panel->panel->funcs->get_modes(panel->panel);
+}
+
+static int atmel_hlcdc_rgb_mode_valid(struct drm_connector *connector,
+                                     struct drm_display_mode *mode)
+{
+       struct atmel_hlcdc_rgb_output *rgb =
+                       drm_connector_to_atmel_hlcdc_rgb_output(connector);
+
+       return atmel_hlcdc_dc_mode_valid(rgb->dc, mode);
+}
+
+
+
+static struct drm_encoder *
+atmel_hlcdc_rgb_best_encoder(struct drm_connector *connector)
+{
+       struct atmel_hlcdc_rgb_output *rgb =
+                       drm_connector_to_atmel_hlcdc_rgb_output(connector);
+
+       return &rgb->encoder;
+}
+
+static struct drm_connector_helper_funcs atmel_hlcdc_panel_connector_helper_funcs = {
+       .get_modes = atmel_hlcdc_panel_get_modes,
+       .mode_valid = atmel_hlcdc_rgb_mode_valid,
+       .best_encoder = atmel_hlcdc_rgb_best_encoder,
+};
+
+static enum drm_connector_status
+atmel_hlcdc_panel_connector_detect(struct drm_connector *connector, bool force)
+{
+       return connector_status_connected;
+}
+
+static void
+atmel_hlcdc_panel_connector_destroy(struct drm_connector *connector)
+{
+       struct atmel_hlcdc_rgb_output *rgb =
+                       drm_connector_to_atmel_hlcdc_rgb_output(connector);
+       struct atmel_hlcdc_panel *panel = atmel_hlcdc_rgb_output_to_panel(rgb);
+
+       drm_panel_detach(panel->panel);
+       drm_connector_cleanup(connector);
+}
+
+static const struct drm_connector_funcs atmel_hlcdc_panel_connector_funcs = {
+       .dpms = drm_helper_connector_dpms,
+       .detect = atmel_hlcdc_panel_connector_detect,
+       .fill_modes = drm_helper_probe_single_connector_modes,
+       .destroy = atmel_hlcdc_panel_connector_destroy,
+};
+
+static int atmel_hlcdc_create_panel_output(struct drm_device *dev,
+                                          struct of_endpoint *ep)
+{
+       struct atmel_hlcdc_dc *dc = dev->dev_private;
+       struct device_node *np;
+       struct drm_panel *p = NULL;
+       struct atmel_hlcdc_panel *panel;
+       int ret;
+
+       np = of_graph_get_remote_port_parent(ep->local_node);
+       if (!np)
+               return -EINVAL;
+
+       p = of_drm_find_panel(np);
+       of_node_put(np);
+
+       if (!p)
+               return -EPROBE_DEFER;
+
+       panel = devm_kzalloc(dev->dev, sizeof(*panel), GFP_KERNEL);
+       if (!panel)
+               return -EINVAL;
+
+       panel->base.dpms = DRM_MODE_DPMS_OFF;
+
+       panel->base.dc = dc;
+
+       drm_encoder_helper_add(&panel->base.encoder,
+                              &atmel_hlcdc_panel_encoder_helper_funcs);
+       ret = drm_encoder_init(dev, &panel->base.encoder,
+                              &atmel_hlcdc_panel_encoder_funcs,
+                              DRM_MODE_ENCODER_LVDS);
+       if (ret)
+               return ret;
+
+       panel->base.connector.dpms = DRM_MODE_DPMS_OFF;
+       panel->base.connector.polled = DRM_CONNECTOR_POLL_CONNECT;
+       drm_connector_helper_add(&panel->base.connector,
+                                &atmel_hlcdc_panel_connector_helper_funcs);
+       ret = drm_connector_init(dev, &panel->base.connector,
+                                &atmel_hlcdc_panel_connector_funcs,
+                                DRM_MODE_CONNECTOR_LVDS);
+       if (ret)
+               goto err_encoder_cleanup;
+
+       drm_mode_connector_attach_encoder(&panel->base.connector,
+                                         &panel->base.encoder);
+       panel->base.encoder.possible_crtcs = 0x1;
+
+       drm_panel_attach(p, &panel->base.connector);
+       panel->panel = p;
+
+       return 0;
+
+err_encoder_cleanup:
+       drm_encoder_cleanup(&panel->base.encoder);
+
+       return ret;
+}
+
+int atmel_hlcdc_create_outputs(struct drm_device *dev)
+{
+       struct device_node *port_np, *np;
+       struct of_endpoint ep;
+       int ret;
+
+       port_np = of_get_child_by_name(dev->dev->of_node, "port");
+       if (!port_np)
+               return -EINVAL;
+
+       np = of_get_child_by_name(port_np, "endpoint");
+       of_node_put(port_np);
+
+       if (!np)
+               return -EINVAL;
+
+       ret = of_graph_parse_endpoint(np, &ep);
+       of_node_put(port_np);
+
+       if (ret)
+               return ret;
+
+       /* We currently only support panel output */
+       return atmel_hlcdc_create_panel_output(dev, &ep);
+}
diff --git a/drivers/gpu/drm/atmel-hlcdc/atmel_hlcdc_plane.c b/drivers/gpu/drm/atmel-hlcdc/atmel_hlcdc_plane.c
new file mode 100644 (file)
index 0000000..c5892dc
--- /dev/null
@@ -0,0 +1,856 @@
+/*
+ * Copyright (C) 2014 Free Electrons
+ * Copyright (C) 2014 Atmel
+ *
+ * Author: Boris BREZILLON <boris.brezillon@free-electrons.com>
+ *
+ * This program is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License version 2 as published by
+ * the Free Software Foundation.
+ *
+ * This program is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License for
+ * more details.
+ *
+ * You should have received a copy of the GNU General Public License along with
+ * this program.  If not, see <http://www.gnu.org/licenses/>.
+ */
+
+#include "atmel_hlcdc_dc.h"
+
+#define SUBPIXEL_MASK                  0xffff
+
+static uint32_t rgb_formats[] = {
+       DRM_FORMAT_XRGB4444,
+       DRM_FORMAT_ARGB4444,
+       DRM_FORMAT_RGBA4444,
+       DRM_FORMAT_ARGB1555,
+       DRM_FORMAT_RGB565,
+       DRM_FORMAT_RGB888,
+       DRM_FORMAT_XRGB8888,
+       DRM_FORMAT_ARGB8888,
+       DRM_FORMAT_RGBA8888,
+};
+
+struct atmel_hlcdc_formats atmel_hlcdc_plane_rgb_formats = {
+       .formats = rgb_formats,
+       .nformats = ARRAY_SIZE(rgb_formats),
+};
+
+static uint32_t rgb_and_yuv_formats[] = {
+       DRM_FORMAT_XRGB4444,
+       DRM_FORMAT_ARGB4444,
+       DRM_FORMAT_RGBA4444,
+       DRM_FORMAT_ARGB1555,
+       DRM_FORMAT_RGB565,
+       DRM_FORMAT_RGB888,
+       DRM_FORMAT_XRGB8888,
+       DRM_FORMAT_ARGB8888,
+       DRM_FORMAT_RGBA8888,
+       DRM_FORMAT_AYUV,
+       DRM_FORMAT_YUYV,
+       DRM_FORMAT_UYVY,
+       DRM_FORMAT_YVYU,
+       DRM_FORMAT_VYUY,
+       DRM_FORMAT_NV21,
+       DRM_FORMAT_NV61,
+       DRM_FORMAT_YUV422,
+       DRM_FORMAT_YUV420,
+};
+
+struct atmel_hlcdc_formats atmel_hlcdc_plane_rgb_and_yuv_formats = {
+       .formats = rgb_and_yuv_formats,
+       .nformats = ARRAY_SIZE(rgb_and_yuv_formats),
+};
+
+static int atmel_hlcdc_format_to_plane_mode(u32 format, u32 *mode)
+{
+       switch (format) {
+       case DRM_FORMAT_XRGB4444:
+               *mode = ATMEL_HLCDC_XRGB4444_MODE;
+               break;
+       case DRM_FORMAT_ARGB4444:
+               *mode = ATMEL_HLCDC_ARGB4444_MODE;
+               break;
+       case DRM_FORMAT_RGBA4444:
+               *mode = ATMEL_HLCDC_RGBA4444_MODE;
+               break;
+       case DRM_FORMAT_RGB565:
+               *mode = ATMEL_HLCDC_RGB565_MODE;
+               break;
+       case DRM_FORMAT_RGB888:
+               *mode = ATMEL_HLCDC_RGB888_MODE;
+               break;
+       case DRM_FORMAT_ARGB1555:
+               *mode = ATMEL_HLCDC_ARGB1555_MODE;
+               break;
+       case DRM_FORMAT_XRGB8888:
+               *mode = ATMEL_HLCDC_XRGB8888_MODE;
+               break;
+       case DRM_FORMAT_ARGB8888:
+               *mode = ATMEL_HLCDC_ARGB8888_MODE;
+               break;
+       case DRM_FORMAT_RGBA8888:
+               *mode = ATMEL_HLCDC_RGBA8888_MODE;
+               break;
+       case DRM_FORMAT_AYUV:
+               *mode = ATMEL_HLCDC_AYUV_MODE;
+               break;
+       case DRM_FORMAT_YUYV:
+               *mode = ATMEL_HLCDC_YUYV_MODE;
+               break;
+       case DRM_FORMAT_UYVY:
+               *mode = ATMEL_HLCDC_UYVY_MODE;
+               break;
+       case DRM_FORMAT_YVYU:
+               *mode = ATMEL_HLCDC_YVYU_MODE;
+               break;
+       case DRM_FORMAT_VYUY:
+               *mode = ATMEL_HLCDC_VYUY_MODE;
+               break;
+       case DRM_FORMAT_NV21:
+               *mode = ATMEL_HLCDC_NV21_MODE;
+               break;
+       case DRM_FORMAT_NV61:
+               *mode = ATMEL_HLCDC_NV61_MODE;
+               break;
+       case DRM_FORMAT_YUV420:
+               *mode = ATMEL_HLCDC_YUV420_MODE;
+               break;
+       case DRM_FORMAT_YUV422:
+               *mode = ATMEL_HLCDC_YUV422_MODE;
+               break;
+       default:
+               return -ENOTSUPP;
+       }
+
+       return 0;
+}
+
+static bool atmel_hlcdc_format_embedds_alpha(u32 format)
+{
+       int i;
+
+       for (i = 0; i < sizeof(format); i++) {
+               char tmp = (format >> (8 * i)) & 0xff;
+
+               if (tmp == 'A')
+                       return true;
+       }
+
+       return false;
+}
+
+static u32 heo_downscaling_xcoef[] = {
+       0x11343311,
+       0x000000f7,
+       0x1635300c,
+       0x000000f9,
+       0x1b362c08,
+       0x000000fb,
+       0x1f372804,
+       0x000000fe,
+       0x24382400,
+       0x00000000,
+       0x28371ffe,
+       0x00000004,
+       0x2c361bfb,
+       0x00000008,
+       0x303516f9,
+       0x0000000c,
+};
+
+static u32 heo_downscaling_ycoef[] = {
+       0x00123737,
+       0x00173732,
+       0x001b382d,
+       0x001f3928,
+       0x00243824,
+       0x0028391f,
+       0x002d381b,
+       0x00323717,
+};
+
+static u32 heo_upscaling_xcoef[] = {
+       0xf74949f7,
+       0x00000000,
+       0xf55f33fb,
+       0x000000fe,
+       0xf5701efe,
+       0x000000ff,
+       0xf87c0dff,
+       0x00000000,
+       0x00800000,
+       0x00000000,
+       0x0d7cf800,
+       0x000000ff,
+       0x1e70f5ff,
+       0x000000fe,
+       0x335ff5fe,
+       0x000000fb,
+};
+
+static u32 heo_upscaling_ycoef[] = {
+       0x00004040,
+       0x00075920,
+       0x00056f0c,
+       0x00027b03,
+       0x00008000,
+       0x00037b02,
+       0x000c6f05,
+       0x00205907,
+};
+
+static void
+atmel_hlcdc_plane_update_pos_and_size(struct atmel_hlcdc_plane *plane,
+                               struct atmel_hlcdc_plane_update_req *req)
+{
+       const struct atmel_hlcdc_layer_cfg_layout *layout =
+                                               &plane->layer.desc->layout;
+
+       if (layout->size)
+               atmel_hlcdc_layer_update_cfg(&plane->layer,
+                                            layout->size,
+                                            0xffffffff,
+                                            (req->crtc_w - 1) |
+                                            ((req->crtc_h - 1) << 16));
+
+       if (layout->memsize)
+               atmel_hlcdc_layer_update_cfg(&plane->layer,
+                                            layout->memsize,
+                                            0xffffffff,
+                                            (req->src_w - 1) |
+                                            ((req->src_h - 1) << 16));
+
+       if (layout->pos)
+               atmel_hlcdc_layer_update_cfg(&plane->layer,
+                                            layout->pos,
+                                            0xffffffff,
+                                            req->crtc_x |
+                                            (req->crtc_y  << 16));
+
+       /* TODO: rework the rescaling part */
+       if (req->crtc_w != req->src_w || req->crtc_h != req->src_h) {
+               u32 factor_reg = 0;
+
+               if (req->crtc_w != req->src_w) {
+                       int i;
+                       u32 factor;
+                       u32 *coeff_tab = heo_upscaling_xcoef;
+                       u32 max_memsize;
+
+                       if (req->crtc_w < req->src_w)
+                               coeff_tab = heo_downscaling_xcoef;
+                       for (i = 0; i < ARRAY_SIZE(heo_upscaling_xcoef); i++)
+                               atmel_hlcdc_layer_update_cfg(&plane->layer,
+                                                            17 + i,
+                                                            0xffffffff,
+                                                            coeff_tab[i]);
+                       factor = ((8 * 256 * req->src_w) - (256 * 4)) /
+                                req->crtc_w;
+                       factor++;
+                       max_memsize = ((factor * req->crtc_w) + (256 * 4)) /
+                                     2048;
+                       if (max_memsize > req->src_w)
+                               factor--;
+                       factor_reg |= factor | 0x80000000;
+               }
+
+               if (req->crtc_h != req->src_h) {
+                       int i;
+                       u32 factor;
+                       u32 *coeff_tab = heo_upscaling_ycoef;
+                       u32 max_memsize;
+
+                       if (req->crtc_w < req->src_w)
+                               coeff_tab = heo_downscaling_ycoef;
+                       for (i = 0; i < ARRAY_SIZE(heo_upscaling_ycoef); i++)
+                               atmel_hlcdc_layer_update_cfg(&plane->layer,
+                                                            33 + i,
+                                                            0xffffffff,
+                                                            coeff_tab[i]);
+                       factor = ((8 * 256 * req->src_w) - (256 * 4)) /
+                                req->crtc_w;
+                       factor++;
+                       max_memsize = ((factor * req->crtc_w) + (256 * 4)) /
+                                     2048;
+                       if (max_memsize > req->src_w)
+                               factor--;
+                       factor_reg |= (factor << 16) | 0x80000000;
+               }
+
+               atmel_hlcdc_layer_update_cfg(&plane->layer, 13, 0xffffffff,
+                                            factor_reg);
+       }
+}
+
+static void
+atmel_hlcdc_plane_update_general_settings(struct atmel_hlcdc_plane *plane,
+                               struct atmel_hlcdc_plane_update_req *req)
+{
+       const struct atmel_hlcdc_layer_cfg_layout *layout =
+                                               &plane->layer.desc->layout;
+       unsigned int cfg = ATMEL_HLCDC_LAYER_DMA;
+
+       if (plane->base.type != DRM_PLANE_TYPE_PRIMARY) {
+               cfg |= ATMEL_HLCDC_LAYER_OVR | ATMEL_HLCDC_LAYER_ITER2BL |
+                      ATMEL_HLCDC_LAYER_ITER;
+
+               if (atmel_hlcdc_format_embedds_alpha(req->fb->pixel_format))
+                       cfg |= ATMEL_HLCDC_LAYER_LAEN;
+               else
+                       cfg |= ATMEL_HLCDC_LAYER_GAEN;
+       }
+
+       atmel_hlcdc_layer_update_cfg(&plane->layer,
+                                    ATMEL_HLCDC_LAYER_DMA_CFG_ID,
+                                    ATMEL_HLCDC_LAYER_DMA_BLEN_MASK,
+                                    ATMEL_HLCDC_LAYER_DMA_BLEN_INCR16);
+
+       atmel_hlcdc_layer_update_cfg(&plane->layer, layout->general_config,
+                                    ATMEL_HLCDC_LAYER_ITER2BL |
+                                    ATMEL_HLCDC_LAYER_ITER |
+                                    ATMEL_HLCDC_LAYER_GAEN |
+                                    ATMEL_HLCDC_LAYER_LAEN |
+                                    ATMEL_HLCDC_LAYER_OVR |
+                                    ATMEL_HLCDC_LAYER_DMA, cfg);
+}
+
+static void atmel_hlcdc_plane_update_format(struct atmel_hlcdc_plane *plane,
+                               struct atmel_hlcdc_plane_update_req *req)
+{
+       u32 cfg;
+       int ret;
+
+       ret = atmel_hlcdc_format_to_plane_mode(req->fb->pixel_format, &cfg);
+       if (ret)
+               return;
+
+       if ((req->fb->pixel_format == DRM_FORMAT_YUV422 ||
+            req->fb->pixel_format == DRM_FORMAT_NV61) &&
+           (plane->rotation & (BIT(DRM_ROTATE_90) | BIT(DRM_ROTATE_270))))
+               cfg |= ATMEL_HLCDC_YUV422ROT;
+
+       atmel_hlcdc_layer_update_cfg(&plane->layer,
+                                    ATMEL_HLCDC_LAYER_FORMAT_CFG_ID,
+                                    0xffffffff,
+                                    cfg);
+
+       /*
+        * Rotation optimization is not working on RGB888 (rotation is still
+        * working but without any optimization).
+        */
+       if (req->fb->pixel_format == DRM_FORMAT_RGB888)
+               cfg = ATMEL_HLCDC_LAYER_DMA_ROTDIS;
+       else
+               cfg = 0;
+
+       atmel_hlcdc_layer_update_cfg(&plane->layer,
+                                    ATMEL_HLCDC_LAYER_DMA_CFG_ID,
+                                    ATMEL_HLCDC_LAYER_DMA_ROTDIS, cfg);
+}
+
+static void atmel_hlcdc_plane_update_buffers(struct atmel_hlcdc_plane *plane,
+                               struct atmel_hlcdc_plane_update_req *req)
+{
+       struct atmel_hlcdc_layer *layer = &plane->layer;
+       const struct atmel_hlcdc_layer_cfg_layout *layout =
+                                                       &layer->desc->layout;
+       int i;
+
+       atmel_hlcdc_layer_update_set_fb(&plane->layer, req->fb, req->offsets);
+
+       for (i = 0; i < req->nplanes; i++) {
+               if (layout->xstride[i]) {
+                       atmel_hlcdc_layer_update_cfg(&plane->layer,
+                                               layout->xstride[i],
+                                               0xffffffff,
+                                               req->xstride[i]);
+               }
+
+               if (layout->pstride[i]) {
+                       atmel_hlcdc_layer_update_cfg(&plane->layer,
+                                               layout->pstride[i],
+                                               0xffffffff,
+                                               req->pstride[i]);
+               }
+       }
+}
+
+static int atmel_hlcdc_plane_check_update_req(struct drm_plane *p,
+                               struct atmel_hlcdc_plane_update_req *req,
+                               const struct drm_display_mode *mode)
+{
+       struct atmel_hlcdc_plane *plane = drm_plane_to_atmel_hlcdc_plane(p);
+       const struct atmel_hlcdc_layer_cfg_layout *layout =
+                                               &plane->layer.desc->layout;
+
+       if (!layout->size &&
+           (mode->hdisplay != req->crtc_w ||
+            mode->vdisplay != req->crtc_h))
+               return -EINVAL;
+
+       if (plane->layer.desc->max_height &&
+           req->crtc_h > plane->layer.desc->max_height)
+               return -EINVAL;
+
+       if (plane->layer.desc->max_width &&
+           req->crtc_w > plane->layer.desc->max_width)
+               return -EINVAL;
+
+       if ((req->crtc_h != req->src_h || req->crtc_w != req->src_w) &&
+           (!layout->memsize ||
+            atmel_hlcdc_format_embedds_alpha(req->fb->pixel_format)))
+               return -EINVAL;
+
+       if (req->crtc_x < 0 || req->crtc_y < 0)
+               return -EINVAL;
+
+       if (req->crtc_w + req->crtc_x > mode->hdisplay ||
+           req->crtc_h + req->crtc_y > mode->vdisplay)
+               return -EINVAL;
+
+       return 0;
+}
+
+int atmel_hlcdc_plane_prepare_update_req(struct drm_plane *p,
+                               struct atmel_hlcdc_plane_update_req *req,
+                               const struct drm_display_mode *mode)
+{
+       struct atmel_hlcdc_plane *plane = drm_plane_to_atmel_hlcdc_plane(p);
+       unsigned int patched_crtc_w;
+       unsigned int patched_crtc_h;
+       unsigned int patched_src_w;
+       unsigned int patched_src_h;
+       unsigned int tmp;
+       int x_offset = 0;
+       int y_offset = 0;
+       int hsub = 1;
+       int vsub = 1;
+       int i;
+
+       if ((req->src_x | req->src_y | req->src_w | req->src_h) &
+           SUBPIXEL_MASK)
+               return -EINVAL;
+
+       req->src_x >>= 16;
+       req->src_y >>= 16;
+       req->src_w >>= 16;
+       req->src_h >>= 16;
+
+       req->nplanes = drm_format_num_planes(req->fb->pixel_format);
+       if (req->nplanes > ATMEL_HLCDC_MAX_PLANES)
+               return -EINVAL;
+
+       /*
+        * Swap width and size in case of 90 or 270 degrees rotation
+        */
+       if (plane->rotation & (BIT(DRM_ROTATE_90) | BIT(DRM_ROTATE_270))) {
+               tmp = req->crtc_w;
+               req->crtc_w = req->crtc_h;
+               req->crtc_h = tmp;
+               tmp = req->src_w;
+               req->src_w = req->src_h;
+               req->src_h = tmp;
+       }
+
+       if (req->crtc_x + req->crtc_w > mode->hdisplay)
+               patched_crtc_w = mode->hdisplay - req->crtc_x;
+       else
+               patched_crtc_w = req->crtc_w;
+
+       if (req->crtc_x < 0) {
+               patched_crtc_w += req->crtc_x;
+               x_offset = -req->crtc_x;
+               req->crtc_x = 0;
+       }
+
+       if (req->crtc_y + req->crtc_h > mode->vdisplay)
+               patched_crtc_h = mode->vdisplay - req->crtc_y;
+       else
+               patched_crtc_h = req->crtc_h;
+
+       if (req->crtc_y < 0) {
+               patched_crtc_h += req->crtc_y;
+               y_offset = -req->crtc_y;
+               req->crtc_y = 0;
+       }
+
+       patched_src_w = DIV_ROUND_CLOSEST(patched_crtc_w * req->src_w,
+                                         req->crtc_w);
+       patched_src_h = DIV_ROUND_CLOSEST(patched_crtc_h * req->src_h,
+                                         req->crtc_h);
+
+       hsub = drm_format_horz_chroma_subsampling(req->fb->pixel_format);
+       vsub = drm_format_vert_chroma_subsampling(req->fb->pixel_format);
+
+       for (i = 0; i < req->nplanes; i++) {
+               unsigned int offset = 0;
+               int xdiv = i ? hsub : 1;
+               int ydiv = i ? vsub : 1;
+
+               req->bpp[i] = drm_format_plane_cpp(req->fb->pixel_format, i);
+               if (!req->bpp[i])
+                       return -EINVAL;
+
+               switch (plane->rotation & 0xf) {
+               case BIT(DRM_ROTATE_90):
+                       offset = ((y_offset + req->src_y + patched_src_w - 1) /
+                                 ydiv) * req->fb->pitches[i];
+                       offset += ((x_offset + req->src_x) / xdiv) *
+                                 req->bpp[i];
+                       req->xstride[i] = ((patched_src_w - 1) / ydiv) *
+                                         req->fb->pitches[i];
+                       req->pstride[i] = -req->fb->pitches[i] - req->bpp[i];
+                       break;
+               case BIT(DRM_ROTATE_180):
+                       offset = ((y_offset + req->src_y + patched_src_h - 1) /
+                                 ydiv) * req->fb->pitches[i];
+                       offset += ((x_offset + req->src_x + patched_src_w - 1) /
+                                  xdiv) * req->bpp[i];
+                       req->xstride[i] = ((((patched_src_w - 1) / xdiv) - 1) *
+                                          req->bpp[i]) - req->fb->pitches[i];
+                       req->pstride[i] = -2 * req->bpp[i];
+                       break;
+               case BIT(DRM_ROTATE_270):
+                       offset = ((y_offset + req->src_y) / ydiv) *
+                                req->fb->pitches[i];
+                       offset += ((x_offset + req->src_x + patched_src_h - 1) /
+                                  xdiv) * req->bpp[i];
+                       req->xstride[i] = -(((patched_src_w - 1) / ydiv) *
+                                           req->fb->pitches[i]) -
+                                         (2 * req->bpp[i]);
+                       req->pstride[i] = req->fb->pitches[i] - req->bpp[i];
+                       break;
+               case BIT(DRM_ROTATE_0):
+               default:
+                       offset = ((y_offset + req->src_y) / ydiv) *
+                                req->fb->pitches[i];
+                       offset += ((x_offset + req->src_x) / xdiv) *
+                                 req->bpp[i];
+                       req->xstride[i] = req->fb->pitches[i] -
+                                         ((patched_src_w / xdiv) *
+                                          req->bpp[i]);
+                       req->pstride[i] = 0;
+                       break;
+               }
+
+               req->offsets[i] = offset + req->fb->offsets[i];
+       }
+
+       req->src_w = patched_src_w;
+       req->src_h = patched_src_h;
+       req->crtc_w = patched_crtc_w;
+       req->crtc_h = patched_crtc_h;
+
+       return atmel_hlcdc_plane_check_update_req(p, req, mode);
+}
+
+int atmel_hlcdc_plane_apply_update_req(struct drm_plane *p,
+                               struct atmel_hlcdc_plane_update_req *req)
+{
+       struct atmel_hlcdc_plane *plane = drm_plane_to_atmel_hlcdc_plane(p);
+       int ret;
+
+       ret = atmel_hlcdc_layer_update_start(&plane->layer);
+       if (ret)
+               return ret;
+
+       atmel_hlcdc_plane_update_pos_and_size(plane, req);
+       atmel_hlcdc_plane_update_general_settings(plane, req);
+       atmel_hlcdc_plane_update_format(plane, req);
+       atmel_hlcdc_plane_update_buffers(plane, req);
+
+       atmel_hlcdc_layer_update_commit(&plane->layer);
+
+       return 0;
+}
+
+int atmel_hlcdc_plane_update_with_mode(struct drm_plane *p,
+                                      struct drm_crtc *crtc,
+                                      struct drm_framebuffer *fb,
+                                      int crtc_x, int crtc_y,
+                                      unsigned int crtc_w,
+                                      unsigned int crtc_h,
+                                      uint32_t src_x, uint32_t src_y,
+                                      uint32_t src_w, uint32_t src_h,
+                                      const struct drm_display_mode *mode)
+{
+       struct atmel_hlcdc_plane *plane = drm_plane_to_atmel_hlcdc_plane(p);
+       struct atmel_hlcdc_plane_update_req req;
+       int ret = 0;
+
+       memset(&req, 0, sizeof(req));
+       req.crtc_x = crtc_x;
+       req.crtc_y = crtc_y;
+       req.crtc_w = crtc_w;
+       req.crtc_h = crtc_h;
+       req.src_x = src_x;
+       req.src_y = src_y;
+       req.src_w = src_w;
+       req.src_h = src_h;
+       req.fb = fb;
+
+       ret = atmel_hlcdc_plane_prepare_update_req(&plane->base, &req, mode);
+       if (ret)
+               return ret;
+
+       if (!req.crtc_h || !req.crtc_w)
+               return atmel_hlcdc_layer_disable(&plane->layer);
+
+       return atmel_hlcdc_plane_apply_update_req(&plane->base, &req);
+}
+
+static int atmel_hlcdc_plane_update(struct drm_plane *p,
+                                   struct drm_crtc *crtc,
+                                   struct drm_framebuffer *fb,
+                                   int crtc_x, int crtc_y,
+                                   unsigned int crtc_w, unsigned int crtc_h,
+                                   uint32_t src_x, uint32_t src_y,
+                                   uint32_t src_w, uint32_t src_h)
+{
+       return atmel_hlcdc_plane_update_with_mode(p, crtc, fb, crtc_x, crtc_y,
+                                                 crtc_w, crtc_h, src_x, src_y,
+                                                 src_w, src_h, &crtc->hwmode);
+}
+
+static int atmel_hlcdc_plane_disable(struct drm_plane *p)
+{
+       struct atmel_hlcdc_plane *plane = drm_plane_to_atmel_hlcdc_plane(p);
+
+       return atmel_hlcdc_layer_disable(&plane->layer);
+}
+
+static void atmel_hlcdc_plane_destroy(struct drm_plane *p)
+{
+       struct atmel_hlcdc_plane *plane = drm_plane_to_atmel_hlcdc_plane(p);
+
+       if (plane->base.fb)
+               drm_framebuffer_unreference(plane->base.fb);
+
+       atmel_hlcdc_layer_cleanup(p->dev, &plane->layer);
+
+       drm_plane_cleanup(p);
+       devm_kfree(p->dev->dev, plane);
+}
+
+static int atmel_hlcdc_plane_set_alpha(struct atmel_hlcdc_plane *plane,
+                                      u8 alpha)
+{
+       atmel_hlcdc_layer_update_start(&plane->layer);
+       atmel_hlcdc_layer_update_cfg(&plane->layer,
+                                    plane->layer.desc->layout.general_config,
+                                    ATMEL_HLCDC_LAYER_GA_MASK,
+                                    alpha << ATMEL_HLCDC_LAYER_GA_SHIFT);
+       atmel_hlcdc_layer_update_commit(&plane->layer);
+
+       return 0;
+}
+
+static int atmel_hlcdc_plane_set_rotation(struct atmel_hlcdc_plane *plane,
+                                         unsigned int rotation)
+{
+       plane->rotation = rotation;
+
+       return 0;
+}
+
+static int atmel_hlcdc_plane_set_property(struct drm_plane *p,
+                                         struct drm_property *property,
+                                         uint64_t value)
+{
+       struct atmel_hlcdc_plane *plane = drm_plane_to_atmel_hlcdc_plane(p);
+       struct atmel_hlcdc_plane_properties *props = plane->properties;
+
+       if (property == props->alpha)
+               atmel_hlcdc_plane_set_alpha(plane, value);
+       else if (property == props->rotation)
+               atmel_hlcdc_plane_set_rotation(plane, value);
+       else
+               return -EINVAL;
+
+       return 0;
+}
+
+static void atmel_hlcdc_plane_init_properties(struct atmel_hlcdc_plane *plane,
+                               const struct atmel_hlcdc_layer_desc *desc,
+                               struct atmel_hlcdc_plane_properties *props)
+{
+       struct regmap *regmap = plane->layer.hlcdc->regmap;
+
+       if (desc->type == ATMEL_HLCDC_OVERLAY_LAYER ||
+           desc->type == ATMEL_HLCDC_CURSOR_LAYER) {
+               drm_object_attach_property(&plane->base.base,
+                                          props->alpha, 255);
+
+               /* Set default alpha value */
+               regmap_update_bits(regmap,
+                               desc->regs_offset +
+                               ATMEL_HLCDC_LAYER_GENERAL_CFG(&plane->layer),
+                               ATMEL_HLCDC_LAYER_GA_MASK,
+                               ATMEL_HLCDC_LAYER_GA_MASK);
+       }
+
+       if (desc->layout.xstride && desc->layout.pstride)
+               drm_object_attach_property(&plane->base.base,
+                                          props->rotation,
+                                          BIT(DRM_ROTATE_0));
+
+       if (desc->layout.csc) {
+               /*
+                * TODO: decare a "yuv-to-rgb-conv-factors" property to let
+                * userspace modify these factors (using a BLOB property ?).
+                */
+               regmap_write(regmap,
+                            desc->regs_offset +
+                            ATMEL_HLCDC_LAYER_CSC_CFG(&plane->layer, 0),
+                            0x4c900091);
+               regmap_write(regmap,
+                            desc->regs_offset +
+                            ATMEL_HLCDC_LAYER_CSC_CFG(&plane->layer, 1),
+                            0x7a5f5090);
+               regmap_write(regmap,
+                            desc->regs_offset +
+                            ATMEL_HLCDC_LAYER_CSC_CFG(&plane->layer, 2),
+                            0x40040890);
+       }
+}
+
+static struct drm_plane_funcs layer_plane_funcs = {
+       .update_plane = atmel_hlcdc_plane_update,
+       .disable_plane = atmel_hlcdc_plane_disable,
+       .set_property = atmel_hlcdc_plane_set_property,
+       .destroy = atmel_hlcdc_plane_destroy,
+};
+
+static struct atmel_hlcdc_plane *
+atmel_hlcdc_plane_create(struct drm_device *dev,
+                        const struct atmel_hlcdc_layer_desc *desc,
+                        struct atmel_hlcdc_plane_properties *props)
+{
+       struct atmel_hlcdc_plane *plane;
+       enum drm_plane_type type;
+       int ret;
+
+       plane = devm_kzalloc(dev->dev, sizeof(*plane), GFP_KERNEL);
+       if (!plane)
+               return ERR_PTR(-ENOMEM);
+
+       ret = atmel_hlcdc_layer_init(dev, &plane->layer, desc);
+       if (ret)
+               return ERR_PTR(ret);
+
+       if (desc->type == ATMEL_HLCDC_BASE_LAYER)
+               type = DRM_PLANE_TYPE_PRIMARY;
+       else if (desc->type == ATMEL_HLCDC_CURSOR_LAYER)
+               type = DRM_PLANE_TYPE_CURSOR;
+       else
+               type = DRM_PLANE_TYPE_OVERLAY;
+
+       ret = drm_universal_plane_init(dev, &plane->base, 0,
+                                      &layer_plane_funcs,
+                                      desc->formats->formats,
+                                      desc->formats->nformats, type);
+       if (ret)
+               return ERR_PTR(ret);
+
+       /* Set default property values*/
+       atmel_hlcdc_plane_init_properties(plane, desc, props);
+
+       return plane;
+}
+
+static struct atmel_hlcdc_plane_properties *
+atmel_hlcdc_plane_create_properties(struct drm_device *dev)
+{
+       struct atmel_hlcdc_plane_properties *props;
+
+       props = devm_kzalloc(dev->dev, sizeof(*props), GFP_KERNEL);
+       if (!props)
+               return ERR_PTR(-ENOMEM);
+
+       props->alpha = drm_property_create_range(dev, 0, "alpha", 0, 255);
+       if (!props->alpha)
+               return ERR_PTR(-ENOMEM);
+
+       props->rotation = drm_mode_create_rotation_property(dev,
+                                               BIT(DRM_ROTATE_0) |
+                                               BIT(DRM_ROTATE_90) |
+                                               BIT(DRM_ROTATE_180) |
+                                               BIT(DRM_ROTATE_270));
+       if (!props->rotation)
+               return ERR_PTR(-ENOMEM);
+
+       return props;
+}
+
+struct atmel_hlcdc_planes *
+atmel_hlcdc_create_planes(struct drm_device *dev)
+{
+       struct atmel_hlcdc_dc *dc = dev->dev_private;
+       struct atmel_hlcdc_plane_properties *props;
+       struct atmel_hlcdc_planes *planes;
+       const struct atmel_hlcdc_layer_desc *descs = dc->desc->layers;
+       int nlayers = dc->desc->nlayers;
+       int i;
+
+       planes = devm_kzalloc(dev->dev, sizeof(*planes), GFP_KERNEL);
+       if (!planes)
+               return ERR_PTR(-ENOMEM);
+
+       for (i = 0; i < nlayers; i++) {
+               if (descs[i].type == ATMEL_HLCDC_OVERLAY_LAYER)
+                       planes->noverlays++;
+       }
+
+       if (planes->noverlays) {
+               planes->overlays = devm_kzalloc(dev->dev,
+                                               planes->noverlays *
+                                               sizeof(*planes->overlays),
+                                               GFP_KERNEL);
+               if (!planes->overlays)
+                       return ERR_PTR(-ENOMEM);
+       }
+
+       props = atmel_hlcdc_plane_create_properties(dev);
+       if (IS_ERR(props))
+               return ERR_CAST(props);
+
+       planes->noverlays = 0;
+       for (i = 0; i < nlayers; i++) {
+               struct atmel_hlcdc_plane *plane;
+
+               if (descs[i].type == ATMEL_HLCDC_PP_LAYER)
+                       continue;
+
+               plane = atmel_hlcdc_plane_create(dev, &descs[i], props);
+               if (IS_ERR(plane))
+                       return ERR_CAST(plane);
+
+               plane->properties = props;
+
+               switch (descs[i].type) {
+               case ATMEL_HLCDC_BASE_LAYER:
+                       if (planes->primary)
+                               return ERR_PTR(-EINVAL);
+                       planes->primary = plane;
+                       break;
+
+               case ATMEL_HLCDC_OVERLAY_LAYER:
+                       planes->overlays[planes->noverlays++] = plane;
+                       break;
+
+               case ATMEL_HLCDC_CURSOR_LAYER:
+                       if (planes->cursor)
+                               return ERR_PTR(-EINVAL);
+                       planes->cursor = plane;
+                       break;
+
+               default:
+                       break;
+               }
+       }
+
+       return planes;
+}
index 61dbf09dff5dca3549460039322406eb73fb7bf7..976d9798dc99d4b1eb498b7d8f2634c35c756a34 100644 (file)
@@ -207,12 +207,22 @@ int bochs_fbdev_init(struct bochs_device *bochs)
        if (ret)
                return ret;
 
-       drm_fb_helper_single_add_all_connectors(&bochs->fb.helper);
+       ret = drm_fb_helper_single_add_all_connectors(&bochs->fb.helper);
+       if (ret)
+               goto fini;
+
        drm_helper_disable_unused_functions(bochs->dev);
-       drm_fb_helper_initial_config(&bochs->fb.helper, 32);
+
+       ret = drm_fb_helper_initial_config(&bochs->fb.helper, 32);
+       if (ret)
+               goto fini;
 
        bochs->fb.initialized = true;
        return 0;
+
+fini:
+       drm_fb_helper_fini(&bochs->fb.helper);
+       return ret;
 }
 
 void bochs_fbdev_fini(struct bochs_device *bochs)
index 85f0f8cf1fb82974f14f5491acaca9dae02cfeb0..26bcd03a8cb6579fc62fa20449eb783a8ba9c2ac 100644 (file)
@@ -18,10 +18,6 @@ MODULE_PARM_DESC(defy, "default y resolution");
 
 /* ---------------------------------------------------------------------- */
 
-static void bochs_crtc_load_lut(struct drm_crtc *crtc)
-{
-}
-
 static void bochs_crtc_dpms(struct drm_crtc *crtc, int mode)
 {
        switch (mode) {
@@ -144,7 +140,6 @@ static const struct drm_crtc_helper_funcs bochs_helper_funcs = {
        .mode_set_base = bochs_crtc_mode_set_base,
        .prepare = bochs_crtc_prepare,
        .commit = bochs_crtc_commit,
-       .load_lut = bochs_crtc_load_lut,
 };
 
 static void bochs_crtc_init(struct drm_device *dev)
index 884923f982d9256d638a0e6c114b43bb7079f3cf..b70f3c8d4e8a537de51daa302161c67527c281fa 100644 (file)
@@ -3,3 +3,8 @@ config DRM_PTN3460
        depends on DRM
        select DRM_KMS_HELPER
        ---help---
+
+config DRM_DW_HDMI
+       tristate
+       depends on DRM
+       select DRM_KMS_HELPER
index b4733e1fbd2eef903a7c233518e15d85218c2dcc..d8a8cfd12fbbb4d72c872359408ca617a17f295e 100644 (file)
@@ -1,3 +1,4 @@
 ccflags-y := -Iinclude/drm
 
 obj-$(CONFIG_DRM_PTN3460) += ptn3460.o
+obj-$(CONFIG_DRM_DW_HDMI) += dw_hdmi.o
diff --git a/drivers/gpu/drm/bridge/dw_hdmi.c b/drivers/gpu/drm/bridge/dw_hdmi.c
new file mode 100644 (file)
index 0000000..6ea0005
--- /dev/null
@@ -0,0 +1,1714 @@
+/*
+ * Copyright (C) 2011-2013 Freescale Semiconductor, Inc.
+ *
+ * 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.
+ *
+ * Designware High-Definition Multimedia Interface (HDMI) driver
+ *
+ * Copyright (C) 2010, Guennadi Liakhovetski <g.liakhovetski@gmx.de>
+ */
+#include <linux/module.h>
+#include <linux/irq.h>
+#include <linux/delay.h>
+#include <linux/err.h>
+#include <linux/clk.h>
+#include <linux/hdmi.h>
+#include <linux/of_device.h>
+
+#include <drm/drm_of.h>
+#include <drm/drmP.h>
+#include <drm/drm_crtc_helper.h>
+#include <drm/drm_edid.h>
+#include <drm/drm_encoder_slave.h>
+#include <drm/bridge/dw_hdmi.h>
+
+#include "dw_hdmi.h"
+
+#define HDMI_EDID_LEN          512
+
+#define RGB                    0
+#define YCBCR444               1
+#define YCBCR422_16BITS                2
+#define YCBCR422_8BITS         3
+#define XVYCC444               4
+
+enum hdmi_datamap {
+       RGB444_8B = 0x01,
+       RGB444_10B = 0x03,
+       RGB444_12B = 0x05,
+       RGB444_16B = 0x07,
+       YCbCr444_8B = 0x09,
+       YCbCr444_10B = 0x0B,
+       YCbCr444_12B = 0x0D,
+       YCbCr444_16B = 0x0F,
+       YCbCr422_8B = 0x16,
+       YCbCr422_10B = 0x14,
+       YCbCr422_12B = 0x12,
+};
+
+static const u16 csc_coeff_default[3][4] = {
+       { 0x2000, 0x0000, 0x0000, 0x0000 },
+       { 0x0000, 0x2000, 0x0000, 0x0000 },
+       { 0x0000, 0x0000, 0x2000, 0x0000 }
+};
+
+static const u16 csc_coeff_rgb_out_eitu601[3][4] = {
+       { 0x2000, 0x6926, 0x74fd, 0x010e },
+       { 0x2000, 0x2cdd, 0x0000, 0x7e9a },
+       { 0x2000, 0x0000, 0x38b4, 0x7e3b }
+};
+
+static const u16 csc_coeff_rgb_out_eitu709[3][4] = {
+       { 0x2000, 0x7106, 0x7a02, 0x00a7 },
+       { 0x2000, 0x3264, 0x0000, 0x7e6d },
+       { 0x2000, 0x0000, 0x3b61, 0x7e25 }
+};
+
+static const u16 csc_coeff_rgb_in_eitu601[3][4] = {
+       { 0x2591, 0x1322, 0x074b, 0x0000 },
+       { 0x6535, 0x2000, 0x7acc, 0x0200 },
+       { 0x6acd, 0x7534, 0x2000, 0x0200 }
+};
+
+static const u16 csc_coeff_rgb_in_eitu709[3][4] = {
+       { 0x2dc5, 0x0d9b, 0x049e, 0x0000 },
+       { 0x62f0, 0x2000, 0x7d11, 0x0200 },
+       { 0x6756, 0x78ab, 0x2000, 0x0200 }
+};
+
+struct hdmi_vmode {
+       bool mdvi;
+       bool mhsyncpolarity;
+       bool mvsyncpolarity;
+       bool minterlaced;
+       bool mdataenablepolarity;
+
+       unsigned int mpixelclock;
+       unsigned int mpixelrepetitioninput;
+       unsigned int mpixelrepetitionoutput;
+};
+
+struct hdmi_data_info {
+       unsigned int enc_in_format;
+       unsigned int enc_out_format;
+       unsigned int enc_color_depth;
+       unsigned int colorimetry;
+       unsigned int pix_repet_factor;
+       unsigned int hdcp_enable;
+       struct hdmi_vmode video_mode;
+};
+
+struct dw_hdmi {
+       struct drm_connector connector;
+       struct drm_encoder *encoder;
+       struct drm_bridge *bridge;
+
+       enum dw_hdmi_devtype dev_type;
+       struct device *dev;
+       struct clk *isfr_clk;
+       struct clk *iahb_clk;
+
+       struct hdmi_data_info hdmi_data;
+       const struct dw_hdmi_plat_data *plat_data;
+
+       int vic;
+
+       u8 edid[HDMI_EDID_LEN];
+       bool cable_plugin;
+
+       bool phy_enabled;
+       struct drm_display_mode previous_mode;
+
+       struct regmap *regmap;
+       struct i2c_adapter *ddc;
+       void __iomem *regs;
+
+       unsigned int sample_rate;
+       int ratio;
+
+       void (*write)(struct dw_hdmi *hdmi, u8 val, int offset);
+       u8 (*read)(struct dw_hdmi *hdmi, int offset);
+};
+
+static void dw_hdmi_writel(struct dw_hdmi *hdmi, u8 val, int offset)
+{
+       writel(val, hdmi->regs + (offset << 2));
+}
+
+static u8 dw_hdmi_readl(struct dw_hdmi *hdmi, int offset)
+{
+       return readl(hdmi->regs + (offset << 2));
+}
+
+static void dw_hdmi_writeb(struct dw_hdmi *hdmi, u8 val, int offset)
+{
+       writeb(val, hdmi->regs + offset);
+}
+
+static u8 dw_hdmi_readb(struct dw_hdmi *hdmi, int offset)
+{
+       return readb(hdmi->regs + offset);
+}
+
+static inline void hdmi_writeb(struct dw_hdmi *hdmi, u8 val, int offset)
+{
+       hdmi->write(hdmi, val, offset);
+}
+
+static inline u8 hdmi_readb(struct dw_hdmi *hdmi, int offset)
+{
+       return hdmi->read(hdmi, offset);
+}
+
+static void hdmi_modb(struct dw_hdmi *hdmi, u8 data, u8 mask, unsigned reg)
+{
+       u8 val = hdmi_readb(hdmi, reg) & ~mask;
+
+       val |= data & mask;
+       hdmi_writeb(hdmi, val, reg);
+}
+
+static void hdmi_mask_writeb(struct dw_hdmi *hdmi, u8 data, unsigned int reg,
+                            u8 shift, u8 mask)
+{
+       hdmi_modb(hdmi, data << shift, mask, reg);
+}
+
+static void hdmi_set_clock_regenerator_n(struct dw_hdmi *hdmi,
+                                        unsigned int value)
+{
+       hdmi_writeb(hdmi, value & 0xff, HDMI_AUD_N1);
+       hdmi_writeb(hdmi, (value >> 8) & 0xff, HDMI_AUD_N2);
+       hdmi_writeb(hdmi, (value >> 16) & 0x0f, HDMI_AUD_N3);
+
+       /* nshift factor = 0 */
+       hdmi_modb(hdmi, 0, HDMI_AUD_CTS3_N_SHIFT_MASK, HDMI_AUD_CTS3);
+}
+
+static void hdmi_regenerate_cts(struct dw_hdmi *hdmi, unsigned int cts)
+{
+       /* Must be set/cleared first */
+       hdmi_modb(hdmi, 0, HDMI_AUD_CTS3_CTS_MANUAL, HDMI_AUD_CTS3);
+
+       hdmi_writeb(hdmi, cts & 0xff, HDMI_AUD_CTS1);
+       hdmi_writeb(hdmi, (cts >> 8) & 0xff, HDMI_AUD_CTS2);
+       hdmi_writeb(hdmi, ((cts >> 16) & HDMI_AUD_CTS3_AUDCTS19_16_MASK) |
+                   HDMI_AUD_CTS3_CTS_MANUAL, HDMI_AUD_CTS3);
+}
+
+static unsigned int hdmi_compute_n(unsigned int freq, unsigned long pixel_clk,
+                                  unsigned int ratio)
+{
+       unsigned int n = (128 * freq) / 1000;
+
+       switch (freq) {
+       case 32000:
+               if (pixel_clk == 25170000)
+                       n = (ratio == 150) ? 9152 : 4576;
+               else if (pixel_clk == 27020000)
+                       n = (ratio == 150) ? 8192 : 4096;
+               else if (pixel_clk == 74170000 || pixel_clk == 148350000)
+                       n = 11648;
+               else
+                       n = 4096;
+               break;
+
+       case 44100:
+               if (pixel_clk == 25170000)
+                       n = 7007;
+               else if (pixel_clk == 74170000)
+                       n = 17836;
+               else if (pixel_clk == 148350000)
+                       n = (ratio == 150) ? 17836 : 8918;
+               else
+                       n = 6272;
+               break;
+
+       case 48000:
+               if (pixel_clk == 25170000)
+                       n = (ratio == 150) ? 9152 : 6864;
+               else if (pixel_clk == 27020000)
+                       n = (ratio == 150) ? 8192 : 6144;
+               else if (pixel_clk == 74170000)
+                       n = 11648;
+               else if (pixel_clk == 148350000)
+                       n = (ratio == 150) ? 11648 : 5824;
+               else
+                       n = 6144;
+               break;
+
+       case 88200:
+               n = hdmi_compute_n(44100, pixel_clk, ratio) * 2;
+               break;
+
+       case 96000:
+               n = hdmi_compute_n(48000, pixel_clk, ratio) * 2;
+               break;
+
+       case 176400:
+               n = hdmi_compute_n(44100, pixel_clk, ratio) * 4;
+               break;
+
+       case 192000:
+               n = hdmi_compute_n(48000, pixel_clk, ratio) * 4;
+               break;
+
+       default:
+               break;
+       }
+
+       return n;
+}
+
+static unsigned int hdmi_compute_cts(unsigned int freq, unsigned long pixel_clk,
+                                    unsigned int ratio)
+{
+       unsigned int cts = 0;
+
+       pr_debug("%s: freq: %d pixel_clk: %ld ratio: %d\n", __func__, freq,
+                pixel_clk, ratio);
+
+       switch (freq) {
+       case 32000:
+               if (pixel_clk == 297000000) {
+                       cts = 222750;
+                       break;
+               }
+       case 48000:
+       case 96000:
+       case 192000:
+               switch (pixel_clk) {
+               case 25200000:
+               case 27000000:
+               case 54000000:
+               case 74250000:
+               case 148500000:
+                       cts = pixel_clk / 1000;
+                       break;
+               case 297000000:
+                       cts = 247500;
+                       break;
+               /*
+                * All other TMDS clocks are not supported by
+                * DWC_hdmi_tx. The TMDS clocks divided or
+                * multiplied by 1,001 coefficients are not
+                * supported.
+                */
+               default:
+                       break;
+               }
+               break;
+       case 44100:
+       case 88200:
+       case 176400:
+               switch (pixel_clk) {
+               case 25200000:
+                       cts = 28000;
+                       break;
+               case 27000000:
+                       cts = 30000;
+                       break;
+               case 54000000:
+                       cts = 60000;
+                       break;
+               case 74250000:
+                       cts = 82500;
+                       break;
+               case 148500000:
+                       cts = 165000;
+                       break;
+               case 297000000:
+                       cts = 247500;
+                       break;
+               default:
+                       break;
+               }
+               break;
+       default:
+               break;
+       }
+       if (ratio == 100)
+               return cts;
+       return (cts * ratio) / 100;
+}
+
+static void hdmi_set_clk_regenerator(struct dw_hdmi *hdmi,
+                                    unsigned long pixel_clk)
+{
+       unsigned int clk_n, clk_cts;
+
+       clk_n = hdmi_compute_n(hdmi->sample_rate, pixel_clk,
+                              hdmi->ratio);
+       clk_cts = hdmi_compute_cts(hdmi->sample_rate, pixel_clk,
+                                  hdmi->ratio);
+
+       if (!clk_cts) {
+               dev_dbg(hdmi->dev, "%s: pixel clock not supported: %lu\n",
+                       __func__, pixel_clk);
+               return;
+       }
+
+       dev_dbg(hdmi->dev, "%s: samplerate=%d  ratio=%d  pixelclk=%lu  N=%d cts=%d\n",
+               __func__, hdmi->sample_rate, hdmi->ratio,
+               pixel_clk, clk_n, clk_cts);
+
+       hdmi_set_clock_regenerator_n(hdmi, clk_n);
+       hdmi_regenerate_cts(hdmi, clk_cts);
+}
+
+static void hdmi_init_clk_regenerator(struct dw_hdmi *hdmi)
+{
+       hdmi_set_clk_regenerator(hdmi, 74250000);
+}
+
+static void hdmi_clk_regenerator_update_pixel_clock(struct dw_hdmi *hdmi)
+{
+       hdmi_set_clk_regenerator(hdmi, hdmi->hdmi_data.video_mode.mpixelclock);
+}
+
+/*
+ * this submodule is responsible for the video data synchronization.
+ * for example, for RGB 4:4:4 input, the data map is defined as
+ *                     pin{47~40} <==> R[7:0]
+ *                     pin{31~24} <==> G[7:0]
+ *                     pin{15~8}  <==> B[7:0]
+ */
+static void hdmi_video_sample(struct dw_hdmi *hdmi)
+{
+       int color_format = 0;
+       u8 val;
+
+       if (hdmi->hdmi_data.enc_in_format == RGB) {
+               if (hdmi->hdmi_data.enc_color_depth == 8)
+                       color_format = 0x01;
+               else if (hdmi->hdmi_data.enc_color_depth == 10)
+                       color_format = 0x03;
+               else if (hdmi->hdmi_data.enc_color_depth == 12)
+                       color_format = 0x05;
+               else if (hdmi->hdmi_data.enc_color_depth == 16)
+                       color_format = 0x07;
+               else
+                       return;
+       } else if (hdmi->hdmi_data.enc_in_format == YCBCR444) {
+               if (hdmi->hdmi_data.enc_color_depth == 8)
+                       color_format = 0x09;
+               else if (hdmi->hdmi_data.enc_color_depth == 10)
+                       color_format = 0x0B;
+               else if (hdmi->hdmi_data.enc_color_depth == 12)
+                       color_format = 0x0D;
+               else if (hdmi->hdmi_data.enc_color_depth == 16)
+                       color_format = 0x0F;
+               else
+                       return;
+       } else if (hdmi->hdmi_data.enc_in_format == YCBCR422_8BITS) {
+               if (hdmi->hdmi_data.enc_color_depth == 8)
+                       color_format = 0x16;
+               else if (hdmi->hdmi_data.enc_color_depth == 10)
+                       color_format = 0x14;
+               else if (hdmi->hdmi_data.enc_color_depth == 12)
+                       color_format = 0x12;
+               else
+                       return;
+       }
+
+       val = HDMI_TX_INVID0_INTERNAL_DE_GENERATOR_DISABLE |
+               ((color_format << HDMI_TX_INVID0_VIDEO_MAPPING_OFFSET) &
+               HDMI_TX_INVID0_VIDEO_MAPPING_MASK);
+       hdmi_writeb(hdmi, val, HDMI_TX_INVID0);
+
+       /* Enable TX stuffing: When DE is inactive, fix the output data to 0 */
+       val = HDMI_TX_INSTUFFING_BDBDATA_STUFFING_ENABLE |
+               HDMI_TX_INSTUFFING_RCRDATA_STUFFING_ENABLE |
+               HDMI_TX_INSTUFFING_GYDATA_STUFFING_ENABLE;
+       hdmi_writeb(hdmi, val, HDMI_TX_INSTUFFING);
+       hdmi_writeb(hdmi, 0x0, HDMI_TX_GYDATA0);
+       hdmi_writeb(hdmi, 0x0, HDMI_TX_GYDATA1);
+       hdmi_writeb(hdmi, 0x0, HDMI_TX_RCRDATA0);
+       hdmi_writeb(hdmi, 0x0, HDMI_TX_RCRDATA1);
+       hdmi_writeb(hdmi, 0x0, HDMI_TX_BCBDATA0);
+       hdmi_writeb(hdmi, 0x0, HDMI_TX_BCBDATA1);
+}
+
+static int is_color_space_conversion(struct dw_hdmi *hdmi)
+{
+       return hdmi->hdmi_data.enc_in_format != hdmi->hdmi_data.enc_out_format;
+}
+
+static int is_color_space_decimation(struct dw_hdmi *hdmi)
+{
+       if (hdmi->hdmi_data.enc_out_format != YCBCR422_8BITS)
+               return 0;
+       if (hdmi->hdmi_data.enc_in_format == RGB ||
+           hdmi->hdmi_data.enc_in_format == YCBCR444)
+               return 1;
+       return 0;
+}
+
+static int is_color_space_interpolation(struct dw_hdmi *hdmi)
+{
+       if (hdmi->hdmi_data.enc_in_format != YCBCR422_8BITS)
+               return 0;
+       if (hdmi->hdmi_data.enc_out_format == RGB ||
+           hdmi->hdmi_data.enc_out_format == YCBCR444)
+               return 1;
+       return 0;
+}
+
+static void dw_hdmi_update_csc_coeffs(struct dw_hdmi *hdmi)
+{
+       const u16 (*csc_coeff)[3][4] = &csc_coeff_default;
+       unsigned i;
+       u32 csc_scale = 1;
+
+       if (is_color_space_conversion(hdmi)) {
+               if (hdmi->hdmi_data.enc_out_format == RGB) {
+                       if (hdmi->hdmi_data.colorimetry ==
+                                       HDMI_COLORIMETRY_ITU_601)
+                               csc_coeff = &csc_coeff_rgb_out_eitu601;
+                       else
+                               csc_coeff = &csc_coeff_rgb_out_eitu709;
+               } else if (hdmi->hdmi_data.enc_in_format == RGB) {
+                       if (hdmi->hdmi_data.colorimetry ==
+                                       HDMI_COLORIMETRY_ITU_601)
+                               csc_coeff = &csc_coeff_rgb_in_eitu601;
+                       else
+                               csc_coeff = &csc_coeff_rgb_in_eitu709;
+                       csc_scale = 0;
+               }
+       }
+
+       /* The CSC registers are sequential, alternating MSB then LSB */
+       for (i = 0; i < ARRAY_SIZE(csc_coeff_default[0]); i++) {
+               u16 coeff_a = (*csc_coeff)[0][i];
+               u16 coeff_b = (*csc_coeff)[1][i];
+               u16 coeff_c = (*csc_coeff)[2][i];
+
+               hdmi_writeb(hdmi, coeff_a & 0xff, HDMI_CSC_COEF_A1_LSB + i * 2);
+               hdmi_writeb(hdmi, coeff_a >> 8, HDMI_CSC_COEF_A1_MSB + i * 2);
+               hdmi_writeb(hdmi, coeff_b & 0xff, HDMI_CSC_COEF_B1_LSB + i * 2);
+               hdmi_writeb(hdmi, coeff_b >> 8, HDMI_CSC_COEF_B1_MSB + i * 2);
+               hdmi_writeb(hdmi, coeff_c & 0xff, HDMI_CSC_COEF_C1_LSB + i * 2);
+               hdmi_writeb(hdmi, coeff_c >> 8, HDMI_CSC_COEF_C1_MSB + i * 2);
+       }
+
+       hdmi_modb(hdmi, csc_scale, HDMI_CSC_SCALE_CSCSCALE_MASK,
+                 HDMI_CSC_SCALE);
+}
+
+static void hdmi_video_csc(struct dw_hdmi *hdmi)
+{
+       int color_depth = 0;
+       int interpolation = HDMI_CSC_CFG_INTMODE_DISABLE;
+       int decimation = 0;
+
+       /* YCC422 interpolation to 444 mode */
+       if (is_color_space_interpolation(hdmi))
+               interpolation = HDMI_CSC_CFG_INTMODE_CHROMA_INT_FORMULA1;
+       else if (is_color_space_decimation(hdmi))
+               decimation = HDMI_CSC_CFG_DECMODE_CHROMA_INT_FORMULA3;
+
+       if (hdmi->hdmi_data.enc_color_depth == 8)
+               color_depth = HDMI_CSC_SCALE_CSC_COLORDE_PTH_24BPP;
+       else if (hdmi->hdmi_data.enc_color_depth == 10)
+               color_depth = HDMI_CSC_SCALE_CSC_COLORDE_PTH_30BPP;
+       else if (hdmi->hdmi_data.enc_color_depth == 12)
+               color_depth = HDMI_CSC_SCALE_CSC_COLORDE_PTH_36BPP;
+       else if (hdmi->hdmi_data.enc_color_depth == 16)
+               color_depth = HDMI_CSC_SCALE_CSC_COLORDE_PTH_48BPP;
+       else
+               return;
+
+       /* Configure the CSC registers */
+       hdmi_writeb(hdmi, interpolation | decimation, HDMI_CSC_CFG);
+       hdmi_modb(hdmi, color_depth, HDMI_CSC_SCALE_CSC_COLORDE_PTH_MASK,
+                 HDMI_CSC_SCALE);
+
+       dw_hdmi_update_csc_coeffs(hdmi);
+}
+
+/*
+ * HDMI video packetizer is used to packetize the data.
+ * for example, if input is YCC422 mode or repeater is used,
+ * data should be repacked this module can be bypassed.
+ */
+static void hdmi_video_packetize(struct dw_hdmi *hdmi)
+{
+       unsigned int color_depth = 0;
+       unsigned int remap_size = HDMI_VP_REMAP_YCC422_16bit;
+       unsigned int output_select = HDMI_VP_CONF_OUTPUT_SELECTOR_PP;
+       struct hdmi_data_info *hdmi_data = &hdmi->hdmi_data;
+       u8 val, vp_conf;
+
+       if (hdmi_data->enc_out_format == RGB ||
+           hdmi_data->enc_out_format == YCBCR444) {
+               if (!hdmi_data->enc_color_depth) {
+                       output_select = HDMI_VP_CONF_OUTPUT_SELECTOR_BYPASS;
+               } else if (hdmi_data->enc_color_depth == 8) {
+                       color_depth = 4;
+                       output_select = HDMI_VP_CONF_OUTPUT_SELECTOR_BYPASS;
+               } else if (hdmi_data->enc_color_depth == 10) {
+                       color_depth = 5;
+               } else if (hdmi_data->enc_color_depth == 12) {
+                       color_depth = 6;
+               } else if (hdmi_data->enc_color_depth == 16) {
+                       color_depth = 7;
+               } else {
+                       return;
+               }
+       } else if (hdmi_data->enc_out_format == YCBCR422_8BITS) {
+               if (!hdmi_data->enc_color_depth ||
+                   hdmi_data->enc_color_depth == 8)
+                       remap_size = HDMI_VP_REMAP_YCC422_16bit;
+               else if (hdmi_data->enc_color_depth == 10)
+                       remap_size = HDMI_VP_REMAP_YCC422_20bit;
+               else if (hdmi_data->enc_color_depth == 12)
+                       remap_size = HDMI_VP_REMAP_YCC422_24bit;
+               else
+                       return;
+               output_select = HDMI_VP_CONF_OUTPUT_SELECTOR_YCC422;
+       } else {
+               return;
+       }
+
+       /* set the packetizer registers */
+       val = ((color_depth << HDMI_VP_PR_CD_COLOR_DEPTH_OFFSET) &
+               HDMI_VP_PR_CD_COLOR_DEPTH_MASK) |
+               ((hdmi_data->pix_repet_factor <<
+               HDMI_VP_PR_CD_DESIRED_PR_FACTOR_OFFSET) &
+               HDMI_VP_PR_CD_DESIRED_PR_FACTOR_MASK);
+       hdmi_writeb(hdmi, val, HDMI_VP_PR_CD);
+
+       hdmi_modb(hdmi, HDMI_VP_STUFF_PR_STUFFING_STUFFING_MODE,
+                 HDMI_VP_STUFF_PR_STUFFING_MASK, HDMI_VP_STUFF);
+
+       /* Data from pixel repeater block */
+       if (hdmi_data->pix_repet_factor > 1) {
+               vp_conf = HDMI_VP_CONF_PR_EN_ENABLE |
+                         HDMI_VP_CONF_BYPASS_SELECT_PIX_REPEATER;
+       } else { /* data from packetizer block */
+               vp_conf = HDMI_VP_CONF_PR_EN_DISABLE |
+                         HDMI_VP_CONF_BYPASS_SELECT_VID_PACKETIZER;
+       }
+
+       hdmi_modb(hdmi, vp_conf,
+                 HDMI_VP_CONF_PR_EN_MASK |
+                 HDMI_VP_CONF_BYPASS_SELECT_MASK, HDMI_VP_CONF);
+
+       hdmi_modb(hdmi, 1 << HDMI_VP_STUFF_IDEFAULT_PHASE_OFFSET,
+                 HDMI_VP_STUFF_IDEFAULT_PHASE_MASK, HDMI_VP_STUFF);
+
+       hdmi_writeb(hdmi, remap_size, HDMI_VP_REMAP);
+
+       if (output_select == HDMI_VP_CONF_OUTPUT_SELECTOR_PP) {
+               vp_conf = HDMI_VP_CONF_BYPASS_EN_DISABLE |
+                         HDMI_VP_CONF_PP_EN_ENABLE |
+                         HDMI_VP_CONF_YCC422_EN_DISABLE;
+       } else if (output_select == HDMI_VP_CONF_OUTPUT_SELECTOR_YCC422) {
+               vp_conf = HDMI_VP_CONF_BYPASS_EN_DISABLE |
+                         HDMI_VP_CONF_PP_EN_DISABLE |
+                         HDMI_VP_CONF_YCC422_EN_ENABLE;
+       } else if (output_select == HDMI_VP_CONF_OUTPUT_SELECTOR_BYPASS) {
+               vp_conf = HDMI_VP_CONF_BYPASS_EN_ENABLE |
+                         HDMI_VP_CONF_PP_EN_DISABLE |
+                         HDMI_VP_CONF_YCC422_EN_DISABLE;
+       } else {
+               return;
+       }
+
+       hdmi_modb(hdmi, vp_conf,
+                 HDMI_VP_CONF_BYPASS_EN_MASK | HDMI_VP_CONF_PP_EN_ENMASK |
+                 HDMI_VP_CONF_YCC422_EN_MASK, HDMI_VP_CONF);
+
+       hdmi_modb(hdmi, HDMI_VP_STUFF_PP_STUFFING_STUFFING_MODE |
+                       HDMI_VP_STUFF_YCC422_STUFFING_STUFFING_MODE,
+                 HDMI_VP_STUFF_PP_STUFFING_MASK |
+                 HDMI_VP_STUFF_YCC422_STUFFING_MASK, HDMI_VP_STUFF);
+
+       hdmi_modb(hdmi, output_select, HDMI_VP_CONF_OUTPUT_SELECTOR_MASK,
+                 HDMI_VP_CONF);
+}
+
+static inline void hdmi_phy_test_clear(struct dw_hdmi *hdmi,
+                                      unsigned char bit)
+{
+       hdmi_modb(hdmi, bit << HDMI_PHY_TST0_TSTCLR_OFFSET,
+                 HDMI_PHY_TST0_TSTCLR_MASK, HDMI_PHY_TST0);
+}
+
+static inline void hdmi_phy_test_enable(struct dw_hdmi *hdmi,
+                                       unsigned char bit)
+{
+       hdmi_modb(hdmi, bit << HDMI_PHY_TST0_TSTEN_OFFSET,
+                 HDMI_PHY_TST0_TSTEN_MASK, HDMI_PHY_TST0);
+}
+
+static inline void hdmi_phy_test_clock(struct dw_hdmi *hdmi,
+                                      unsigned char bit)
+{
+       hdmi_modb(hdmi, bit << HDMI_PHY_TST0_TSTCLK_OFFSET,
+                 HDMI_PHY_TST0_TSTCLK_MASK, HDMI_PHY_TST0);
+}
+
+static inline void hdmi_phy_test_din(struct dw_hdmi *hdmi,
+                                    unsigned char bit)
+{
+       hdmi_writeb(hdmi, bit, HDMI_PHY_TST1);
+}
+
+static inline void hdmi_phy_test_dout(struct dw_hdmi *hdmi,
+                                     unsigned char bit)
+{
+       hdmi_writeb(hdmi, bit, HDMI_PHY_TST2);
+}
+
+static bool hdmi_phy_wait_i2c_done(struct dw_hdmi *hdmi, int msec)
+{
+       u32 val;
+
+       while ((val = hdmi_readb(hdmi, HDMI_IH_I2CMPHY_STAT0) & 0x3) == 0) {
+               if (msec-- == 0)
+                       return false;
+               udelay(1000);
+       }
+       hdmi_writeb(hdmi, val, HDMI_IH_I2CMPHY_STAT0);
+
+       return true;
+}
+
+static void __hdmi_phy_i2c_write(struct dw_hdmi *hdmi, unsigned short data,
+                                unsigned char addr)
+{
+       hdmi_writeb(hdmi, 0xFF, HDMI_IH_I2CMPHY_STAT0);
+       hdmi_writeb(hdmi, addr, HDMI_PHY_I2CM_ADDRESS_ADDR);
+       hdmi_writeb(hdmi, (unsigned char)(data >> 8),
+                   HDMI_PHY_I2CM_DATAO_1_ADDR);
+       hdmi_writeb(hdmi, (unsigned char)(data >> 0),
+                   HDMI_PHY_I2CM_DATAO_0_ADDR);
+       hdmi_writeb(hdmi, HDMI_PHY_I2CM_OPERATION_ADDR_WRITE,
+                   HDMI_PHY_I2CM_OPERATION_ADDR);
+       hdmi_phy_wait_i2c_done(hdmi, 1000);
+}
+
+static int hdmi_phy_i2c_write(struct dw_hdmi *hdmi, unsigned short data,
+                             unsigned char addr)
+{
+       __hdmi_phy_i2c_write(hdmi, data, addr);
+       return 0;
+}
+
+static void dw_hdmi_phy_enable_power(struct dw_hdmi *hdmi, u8 enable)
+{
+       hdmi_mask_writeb(hdmi, enable, HDMI_PHY_CONF0,
+                        HDMI_PHY_CONF0_PDZ_OFFSET,
+                        HDMI_PHY_CONF0_PDZ_MASK);
+}
+
+static void dw_hdmi_phy_enable_tmds(struct dw_hdmi *hdmi, u8 enable)
+{
+       hdmi_mask_writeb(hdmi, enable, HDMI_PHY_CONF0,
+                        HDMI_PHY_CONF0_ENTMDS_OFFSET,
+                        HDMI_PHY_CONF0_ENTMDS_MASK);
+}
+
+static void dw_hdmi_phy_enable_spare(struct dw_hdmi *hdmi, u8 enable)
+{
+       hdmi_mask_writeb(hdmi, enable, HDMI_PHY_CONF0,
+                        HDMI_PHY_CONF0_SPARECTRL_OFFSET,
+                        HDMI_PHY_CONF0_SPARECTRL_MASK);
+}
+
+static void dw_hdmi_phy_gen2_pddq(struct dw_hdmi *hdmi, u8 enable)
+{
+       hdmi_mask_writeb(hdmi, enable, HDMI_PHY_CONF0,
+                        HDMI_PHY_CONF0_GEN2_PDDQ_OFFSET,
+                        HDMI_PHY_CONF0_GEN2_PDDQ_MASK);
+}
+
+static void dw_hdmi_phy_gen2_txpwron(struct dw_hdmi *hdmi, u8 enable)
+{
+       hdmi_mask_writeb(hdmi, enable, HDMI_PHY_CONF0,
+                        HDMI_PHY_CONF0_GEN2_TXPWRON_OFFSET,
+                        HDMI_PHY_CONF0_GEN2_TXPWRON_MASK);
+}
+
+static void dw_hdmi_phy_sel_data_en_pol(struct dw_hdmi *hdmi, u8 enable)
+{
+       hdmi_mask_writeb(hdmi, enable, HDMI_PHY_CONF0,
+                        HDMI_PHY_CONF0_SELDATAENPOL_OFFSET,
+                        HDMI_PHY_CONF0_SELDATAENPOL_MASK);
+}
+
+static void dw_hdmi_phy_sel_interface_control(struct dw_hdmi *hdmi, u8 enable)
+{
+       hdmi_mask_writeb(hdmi, enable, HDMI_PHY_CONF0,
+                        HDMI_PHY_CONF0_SELDIPIF_OFFSET,
+                        HDMI_PHY_CONF0_SELDIPIF_MASK);
+}
+
+static int hdmi_phy_configure(struct dw_hdmi *hdmi, unsigned char prep,
+                             unsigned char res, int cscon)
+{
+       unsigned res_idx, i;
+       u8 val, msec;
+       const struct dw_hdmi_mpll_config *mpll_config =
+                                               hdmi->plat_data->mpll_cfg;
+       const struct dw_hdmi_curr_ctrl *curr_ctrl = hdmi->plat_data->cur_ctr;
+       const struct dw_hdmi_sym_term *sym_term =  hdmi->plat_data->sym_term;
+
+       if (prep)
+               return -EINVAL;
+
+       switch (res) {
+       case 0: /* color resolution 0 is 8 bit colour depth */
+       case 8:
+               res_idx = DW_HDMI_RES_8;
+               break;
+       case 10:
+               res_idx = DW_HDMI_RES_10;
+               break;
+       case 12:
+               res_idx = DW_HDMI_RES_12;
+               break;
+       default:
+               return -EINVAL;
+       }
+
+       /* Enable csc path */
+       if (cscon)
+               val = HDMI_MC_FLOWCTRL_FEED_THROUGH_OFF_CSC_IN_PATH;
+       else
+               val = HDMI_MC_FLOWCTRL_FEED_THROUGH_OFF_CSC_BYPASS;
+
+       hdmi_writeb(hdmi, val, HDMI_MC_FLOWCTRL);
+
+       /* gen2 tx power off */
+       dw_hdmi_phy_gen2_txpwron(hdmi, 0);
+
+       /* gen2 pddq */
+       dw_hdmi_phy_gen2_pddq(hdmi, 1);
+
+       /* PHY reset */
+       hdmi_writeb(hdmi, HDMI_MC_PHYRSTZ_DEASSERT, HDMI_MC_PHYRSTZ);
+       hdmi_writeb(hdmi, HDMI_MC_PHYRSTZ_ASSERT, HDMI_MC_PHYRSTZ);
+
+       hdmi_writeb(hdmi, HDMI_MC_HEACPHY_RST_ASSERT, HDMI_MC_HEACPHY_RST);
+
+       hdmi_phy_test_clear(hdmi, 1);
+       hdmi_writeb(hdmi, HDMI_PHY_I2CM_SLAVE_ADDR_PHY_GEN2,
+                   HDMI_PHY_I2CM_SLAVE_ADDR);
+       hdmi_phy_test_clear(hdmi, 0);
+
+       /* PLL/MPLL Cfg - always match on final entry */
+       for (i = 0; mpll_config[i].mpixelclock != (~0UL); i++)
+               if (hdmi->hdmi_data.video_mode.mpixelclock <=
+                   mpll_config[i].mpixelclock)
+                       break;
+
+       hdmi_phy_i2c_write(hdmi, mpll_config[i].res[res_idx].cpce, 0x06);
+       hdmi_phy_i2c_write(hdmi, mpll_config[i].res[res_idx].gmp, 0x15);
+
+       for (i = 0; curr_ctrl[i].mpixelclock != (~0UL); i++)
+               if (hdmi->hdmi_data.video_mode.mpixelclock <=
+                   curr_ctrl[i].mpixelclock)
+                       break;
+
+       if (curr_ctrl[i].mpixelclock == (~0UL)) {
+               dev_err(hdmi->dev, "Pixel clock %d - unsupported by HDMI\n",
+                       hdmi->hdmi_data.video_mode.mpixelclock);
+               return -EINVAL;
+       }
+
+       /* CURRCTRL */
+       hdmi_phy_i2c_write(hdmi, curr_ctrl[i].curr[res_idx], 0x10);
+
+       hdmi_phy_i2c_write(hdmi, 0x0000, 0x13);  /* PLLPHBYCTRL */
+       hdmi_phy_i2c_write(hdmi, 0x0006, 0x17);
+
+       for (i = 0; sym_term[i].mpixelclock != (~0UL); i++)
+               if (hdmi->hdmi_data.video_mode.mpixelclock <=
+                   sym_term[i].mpixelclock)
+                       break;
+
+       /* RESISTANCE TERM 133Ohm Cfg */
+       hdmi_phy_i2c_write(hdmi, sym_term[i].term, 0x19);  /* TXTERM */
+       /* PREEMP Cgf 0.00 */
+       hdmi_phy_i2c_write(hdmi, sym_term[i].sym_ctr, 0x09);  /* CKSYMTXCTRL */
+
+       /* TX/CK LVL 10 */
+       hdmi_phy_i2c_write(hdmi, 0x01ad, 0x0E);  /* VLEVCTRL */
+       /* REMOVE CLK TERM */
+       hdmi_phy_i2c_write(hdmi, 0x8000, 0x05);  /* CKCALCTRL */
+
+       dw_hdmi_phy_enable_power(hdmi, 1);
+
+       /* toggle TMDS enable */
+       dw_hdmi_phy_enable_tmds(hdmi, 0);
+       dw_hdmi_phy_enable_tmds(hdmi, 1);
+
+       /* gen2 tx power on */
+       dw_hdmi_phy_gen2_txpwron(hdmi, 1);
+       dw_hdmi_phy_gen2_pddq(hdmi, 0);
+
+       if (hdmi->dev_type == RK3288_HDMI)
+               dw_hdmi_phy_enable_spare(hdmi, 1);
+
+       /*Wait for PHY PLL lock */
+       msec = 5;
+       do {
+               val = hdmi_readb(hdmi, HDMI_PHY_STAT0) & HDMI_PHY_TX_PHY_LOCK;
+               if (!val)
+                       break;
+
+               if (msec == 0) {
+                       dev_err(hdmi->dev, "PHY PLL not locked\n");
+                       return -ETIMEDOUT;
+               }
+
+               udelay(1000);
+               msec--;
+       } while (1);
+
+       return 0;
+}
+
+static int dw_hdmi_phy_init(struct dw_hdmi *hdmi)
+{
+       int i, ret;
+       bool cscon = false;
+
+       /*check csc whether needed activated in HDMI mode */
+       cscon = (is_color_space_conversion(hdmi) &&
+                       !hdmi->hdmi_data.video_mode.mdvi);
+
+       /* HDMI Phy spec says to do the phy initialization sequence twice */
+       for (i = 0; i < 2; i++) {
+               dw_hdmi_phy_sel_data_en_pol(hdmi, 1);
+               dw_hdmi_phy_sel_interface_control(hdmi, 0);
+               dw_hdmi_phy_enable_tmds(hdmi, 0);
+               dw_hdmi_phy_enable_power(hdmi, 0);
+
+               /* Enable CSC */
+               ret = hdmi_phy_configure(hdmi, 0, 8, cscon);
+               if (ret)
+                       return ret;
+       }
+
+       hdmi->phy_enabled = true;
+       return 0;
+}
+
+static void hdmi_tx_hdcp_config(struct dw_hdmi *hdmi)
+{
+       u8 de;
+
+       if (hdmi->hdmi_data.video_mode.mdataenablepolarity)
+               de = HDMI_A_VIDPOLCFG_DATAENPOL_ACTIVE_HIGH;
+       else
+               de = HDMI_A_VIDPOLCFG_DATAENPOL_ACTIVE_LOW;
+
+       /* disable rx detect */
+       hdmi_modb(hdmi, HDMI_A_HDCPCFG0_RXDETECT_DISABLE,
+                 HDMI_A_HDCPCFG0_RXDETECT_MASK, HDMI_A_HDCPCFG0);
+
+       hdmi_modb(hdmi, de, HDMI_A_VIDPOLCFG_DATAENPOL_MASK, HDMI_A_VIDPOLCFG);
+
+       hdmi_modb(hdmi, HDMI_A_HDCPCFG1_ENCRYPTIONDISABLE_DISABLE,
+                 HDMI_A_HDCPCFG1_ENCRYPTIONDISABLE_MASK, HDMI_A_HDCPCFG1);
+}
+
+static void hdmi_config_AVI(struct dw_hdmi *hdmi)
+{
+       u8 val, pix_fmt, under_scan;
+       u8 act_ratio, coded_ratio, colorimetry, ext_colorimetry;
+       bool aspect_16_9;
+
+       aspect_16_9 = false; /* FIXME */
+
+       /* AVI Data Byte 1 */
+       if (hdmi->hdmi_data.enc_out_format == YCBCR444)
+               pix_fmt = HDMI_FC_AVICONF0_PIX_FMT_YCBCR444;
+       else if (hdmi->hdmi_data.enc_out_format == YCBCR422_8BITS)
+               pix_fmt = HDMI_FC_AVICONF0_PIX_FMT_YCBCR422;
+       else
+               pix_fmt = HDMI_FC_AVICONF0_PIX_FMT_RGB;
+
+               under_scan =  HDMI_FC_AVICONF0_SCAN_INFO_NODATA;
+
+       /*
+        * Active format identification data is present in the AVI InfoFrame.
+        * Under scan info, no bar data
+        */
+       val = pix_fmt | under_scan |
+               HDMI_FC_AVICONF0_ACTIVE_FMT_INFO_PRESENT |
+               HDMI_FC_AVICONF0_BAR_DATA_NO_DATA;
+
+       hdmi_writeb(hdmi, val, HDMI_FC_AVICONF0);
+
+       /* AVI Data Byte 2 -Set the Aspect Ratio */
+       if (aspect_16_9) {
+               act_ratio = HDMI_FC_AVICONF1_ACTIVE_ASPECT_RATIO_16_9;
+               coded_ratio = HDMI_FC_AVICONF1_CODED_ASPECT_RATIO_16_9;
+       } else {
+               act_ratio = HDMI_FC_AVICONF1_ACTIVE_ASPECT_RATIO_4_3;
+               coded_ratio = HDMI_FC_AVICONF1_CODED_ASPECT_RATIO_4_3;
+       }
+
+       /* Set up colorimetry */
+       if (hdmi->hdmi_data.enc_out_format == XVYCC444) {
+               colorimetry = HDMI_FC_AVICONF1_COLORIMETRY_EXTENDED_INFO;
+               if (hdmi->hdmi_data.colorimetry == HDMI_COLORIMETRY_ITU_601)
+                       ext_colorimetry =
+                               HDMI_FC_AVICONF2_EXT_COLORIMETRY_XVYCC601;
+               else /*hdmi->hdmi_data.colorimetry == HDMI_COLORIMETRY_ITU_709*/
+                       ext_colorimetry =
+                               HDMI_FC_AVICONF2_EXT_COLORIMETRY_XVYCC709;
+       } else if (hdmi->hdmi_data.enc_out_format != RGB) {
+               if (hdmi->hdmi_data.colorimetry == HDMI_COLORIMETRY_ITU_601)
+                       colorimetry = HDMI_FC_AVICONF1_COLORIMETRY_SMPTE;
+               else /*hdmi->hdmi_data.colorimetry == HDMI_COLORIMETRY_ITU_709*/
+                       colorimetry = HDMI_FC_AVICONF1_COLORIMETRY_ITUR;
+               ext_colorimetry = HDMI_FC_AVICONF2_EXT_COLORIMETRY_XVYCC601;
+       } else { /* Carries no data */
+               colorimetry = HDMI_FC_AVICONF1_COLORIMETRY_NO_DATA;
+               ext_colorimetry = HDMI_FC_AVICONF2_EXT_COLORIMETRY_XVYCC601;
+       }
+
+       val = colorimetry | coded_ratio | act_ratio;
+       hdmi_writeb(hdmi, val, HDMI_FC_AVICONF1);
+
+       /* AVI Data Byte 3 */
+       val = HDMI_FC_AVICONF2_IT_CONTENT_NO_DATA | ext_colorimetry |
+               HDMI_FC_AVICONF2_RGB_QUANT_DEFAULT |
+               HDMI_FC_AVICONF2_SCALING_NONE;
+       hdmi_writeb(hdmi, val, HDMI_FC_AVICONF2);
+
+       /* AVI Data Byte 4 */
+       hdmi_writeb(hdmi, hdmi->vic, HDMI_FC_AVIVID);
+
+       /* AVI Data Byte 5- set up input and output pixel repetition */
+       val = (((hdmi->hdmi_data.video_mode.mpixelrepetitioninput + 1) <<
+               HDMI_FC_PRCONF_INCOMING_PR_FACTOR_OFFSET) &
+               HDMI_FC_PRCONF_INCOMING_PR_FACTOR_MASK) |
+               ((hdmi->hdmi_data.video_mode.mpixelrepetitionoutput <<
+               HDMI_FC_PRCONF_OUTPUT_PR_FACTOR_OFFSET) &
+               HDMI_FC_PRCONF_OUTPUT_PR_FACTOR_MASK);
+       hdmi_writeb(hdmi, val, HDMI_FC_PRCONF);
+
+       /* IT Content and quantization range = don't care */
+       val = HDMI_FC_AVICONF3_IT_CONTENT_TYPE_GRAPHICS |
+               HDMI_FC_AVICONF3_QUANT_RANGE_LIMITED;
+       hdmi_writeb(hdmi, val, HDMI_FC_AVICONF3);
+
+       /* AVI Data Bytes 6-13 */
+       hdmi_writeb(hdmi, 0, HDMI_FC_AVIETB0);
+       hdmi_writeb(hdmi, 0, HDMI_FC_AVIETB1);
+       hdmi_writeb(hdmi, 0, HDMI_FC_AVISBB0);
+       hdmi_writeb(hdmi, 0, HDMI_FC_AVISBB1);
+       hdmi_writeb(hdmi, 0, HDMI_FC_AVIELB0);
+       hdmi_writeb(hdmi, 0, HDMI_FC_AVIELB1);
+       hdmi_writeb(hdmi, 0, HDMI_FC_AVISRB0);
+       hdmi_writeb(hdmi, 0, HDMI_FC_AVISRB1);
+}
+
+static void hdmi_av_composer(struct dw_hdmi *hdmi,
+                            const struct drm_display_mode *mode)
+{
+       u8 inv_val;
+       struct hdmi_vmode *vmode = &hdmi->hdmi_data.video_mode;
+       int hblank, vblank, h_de_hs, v_de_vs, hsync_len, vsync_len;
+
+       vmode->mhsyncpolarity = !!(mode->flags & DRM_MODE_FLAG_PHSYNC);
+       vmode->mvsyncpolarity = !!(mode->flags & DRM_MODE_FLAG_PVSYNC);
+       vmode->minterlaced = !!(mode->flags & DRM_MODE_FLAG_INTERLACE);
+       vmode->mpixelclock = mode->clock * 1000;
+
+       dev_dbg(hdmi->dev, "final pixclk = %d\n", vmode->mpixelclock);
+
+       /* Set up HDMI_FC_INVIDCONF */
+       inv_val = (hdmi->hdmi_data.hdcp_enable ?
+               HDMI_FC_INVIDCONF_HDCP_KEEPOUT_ACTIVE :
+               HDMI_FC_INVIDCONF_HDCP_KEEPOUT_INACTIVE);
+
+       inv_val |= (vmode->mvsyncpolarity ?
+               HDMI_FC_INVIDCONF_VSYNC_IN_POLARITY_ACTIVE_HIGH :
+               HDMI_FC_INVIDCONF_VSYNC_IN_POLARITY_ACTIVE_LOW);
+
+       inv_val |= (vmode->mhsyncpolarity ?
+               HDMI_FC_INVIDCONF_HSYNC_IN_POLARITY_ACTIVE_HIGH :
+               HDMI_FC_INVIDCONF_HSYNC_IN_POLARITY_ACTIVE_LOW);
+
+       inv_val |= (vmode->mdataenablepolarity ?
+               HDMI_FC_INVIDCONF_DE_IN_POLARITY_ACTIVE_HIGH :
+               HDMI_FC_INVIDCONF_DE_IN_POLARITY_ACTIVE_LOW);
+
+       if (hdmi->vic == 39)
+               inv_val |= HDMI_FC_INVIDCONF_R_V_BLANK_IN_OSC_ACTIVE_HIGH;
+       else
+               inv_val |= (vmode->minterlaced ?
+                       HDMI_FC_INVIDCONF_R_V_BLANK_IN_OSC_ACTIVE_HIGH :
+                       HDMI_FC_INVIDCONF_R_V_BLANK_IN_OSC_ACTIVE_LOW);
+
+       inv_val |= (vmode->minterlaced ?
+               HDMI_FC_INVIDCONF_IN_I_P_INTERLACED :
+               HDMI_FC_INVIDCONF_IN_I_P_PROGRESSIVE);
+
+       inv_val |= (vmode->mdvi ?
+               HDMI_FC_INVIDCONF_DVI_MODEZ_DVI_MODE :
+               HDMI_FC_INVIDCONF_DVI_MODEZ_HDMI_MODE);
+
+       hdmi_writeb(hdmi, inv_val, HDMI_FC_INVIDCONF);
+
+       /* Set up horizontal active pixel width */
+       hdmi_writeb(hdmi, mode->hdisplay >> 8, HDMI_FC_INHACTV1);
+       hdmi_writeb(hdmi, mode->hdisplay, HDMI_FC_INHACTV0);
+
+       /* Set up vertical active lines */
+       hdmi_writeb(hdmi, mode->vdisplay >> 8, HDMI_FC_INVACTV1);
+       hdmi_writeb(hdmi, mode->vdisplay, HDMI_FC_INVACTV0);
+
+       /* Set up horizontal blanking pixel region width */
+       hblank = mode->htotal - mode->hdisplay;
+       hdmi_writeb(hdmi, hblank >> 8, HDMI_FC_INHBLANK1);
+       hdmi_writeb(hdmi, hblank, HDMI_FC_INHBLANK0);
+
+       /* Set up vertical blanking pixel region width */
+       vblank = mode->vtotal - mode->vdisplay;
+       hdmi_writeb(hdmi, vblank, HDMI_FC_INVBLANK);
+
+       /* Set up HSYNC active edge delay width (in pixel clks) */
+       h_de_hs = mode->hsync_start - mode->hdisplay;
+       hdmi_writeb(hdmi, h_de_hs >> 8, HDMI_FC_HSYNCINDELAY1);
+       hdmi_writeb(hdmi, h_de_hs, HDMI_FC_HSYNCINDELAY0);
+
+       /* Set up VSYNC active edge delay (in lines) */
+       v_de_vs = mode->vsync_start - mode->vdisplay;
+       hdmi_writeb(hdmi, v_de_vs, HDMI_FC_VSYNCINDELAY);
+
+       /* Set up HSYNC active pulse width (in pixel clks) */
+       hsync_len = mode->hsync_end - mode->hsync_start;
+       hdmi_writeb(hdmi, hsync_len >> 8, HDMI_FC_HSYNCINWIDTH1);
+       hdmi_writeb(hdmi, hsync_len, HDMI_FC_HSYNCINWIDTH0);
+
+       /* Set up VSYNC active edge delay (in lines) */
+       vsync_len = mode->vsync_end - mode->vsync_start;
+       hdmi_writeb(hdmi, vsync_len, HDMI_FC_VSYNCINWIDTH);
+}
+
+static void dw_hdmi_phy_disable(struct dw_hdmi *hdmi)
+{
+       if (!hdmi->phy_enabled)
+               return;
+
+       dw_hdmi_phy_enable_tmds(hdmi, 0);
+       dw_hdmi_phy_enable_power(hdmi, 0);
+
+       hdmi->phy_enabled = false;
+}
+
+/* HDMI Initialization Step B.4 */
+static void dw_hdmi_enable_video_path(struct dw_hdmi *hdmi)
+{
+       u8 clkdis;
+
+       /* control period minimum duration */
+       hdmi_writeb(hdmi, 12, HDMI_FC_CTRLDUR);
+       hdmi_writeb(hdmi, 32, HDMI_FC_EXCTRLDUR);
+       hdmi_writeb(hdmi, 1, HDMI_FC_EXCTRLSPAC);
+
+       /* Set to fill TMDS data channels */
+       hdmi_writeb(hdmi, 0x0B, HDMI_FC_CH0PREAM);
+       hdmi_writeb(hdmi, 0x16, HDMI_FC_CH1PREAM);
+       hdmi_writeb(hdmi, 0x21, HDMI_FC_CH2PREAM);
+
+       /* Enable pixel clock and tmds data path */
+       clkdis = 0x7F;
+       clkdis &= ~HDMI_MC_CLKDIS_PIXELCLK_DISABLE;
+       hdmi_writeb(hdmi, clkdis, HDMI_MC_CLKDIS);
+
+       clkdis &= ~HDMI_MC_CLKDIS_TMDSCLK_DISABLE;
+       hdmi_writeb(hdmi, clkdis, HDMI_MC_CLKDIS);
+
+       /* Enable csc path */
+       if (is_color_space_conversion(hdmi)) {
+               clkdis &= ~HDMI_MC_CLKDIS_CSCCLK_DISABLE;
+               hdmi_writeb(hdmi, clkdis, HDMI_MC_CLKDIS);
+       }
+}
+
+static void hdmi_enable_audio_clk(struct dw_hdmi *hdmi)
+{
+       hdmi_modb(hdmi, 0, HDMI_MC_CLKDIS_AUDCLK_DISABLE, HDMI_MC_CLKDIS);
+}
+
+/* Workaround to clear the overflow condition */
+static void dw_hdmi_clear_overflow(struct dw_hdmi *hdmi)
+{
+       int count;
+       u8 val;
+
+       /* TMDS software reset */
+       hdmi_writeb(hdmi, (u8)~HDMI_MC_SWRSTZ_TMDSSWRST_REQ, HDMI_MC_SWRSTZ);
+
+       val = hdmi_readb(hdmi, HDMI_FC_INVIDCONF);
+       if (hdmi->dev_type == IMX6DL_HDMI) {
+               hdmi_writeb(hdmi, val, HDMI_FC_INVIDCONF);
+               return;
+       }
+
+       for (count = 0; count < 4; count++)
+               hdmi_writeb(hdmi, val, HDMI_FC_INVIDCONF);
+}
+
+static void hdmi_enable_overflow_interrupts(struct dw_hdmi *hdmi)
+{
+       hdmi_writeb(hdmi, 0, HDMI_FC_MASK2);
+       hdmi_writeb(hdmi, 0, HDMI_IH_MUTE_FC_STAT2);
+}
+
+static void hdmi_disable_overflow_interrupts(struct dw_hdmi *hdmi)
+{
+       hdmi_writeb(hdmi, HDMI_IH_MUTE_FC_STAT2_OVERFLOW_MASK,
+                   HDMI_IH_MUTE_FC_STAT2);
+}
+
+static int dw_hdmi_setup(struct dw_hdmi *hdmi, struct drm_display_mode *mode)
+{
+       int ret;
+
+       hdmi_disable_overflow_interrupts(hdmi);
+
+       hdmi->vic = drm_match_cea_mode(mode);
+
+       if (!hdmi->vic) {
+               dev_dbg(hdmi->dev, "Non-CEA mode used in HDMI\n");
+               hdmi->hdmi_data.video_mode.mdvi = true;
+       } else {
+               dev_dbg(hdmi->dev, "CEA mode used vic=%d\n", hdmi->vic);
+               hdmi->hdmi_data.video_mode.mdvi = false;
+       }
+
+       if ((hdmi->vic == 6) || (hdmi->vic == 7) ||
+           (hdmi->vic == 21) || (hdmi->vic == 22) ||
+           (hdmi->vic == 2) || (hdmi->vic == 3) ||
+           (hdmi->vic == 17) || (hdmi->vic == 18))
+               hdmi->hdmi_data.colorimetry = HDMI_COLORIMETRY_ITU_601;
+       else
+               hdmi->hdmi_data.colorimetry = HDMI_COLORIMETRY_ITU_709;
+
+       if ((hdmi->vic == 10) || (hdmi->vic == 11) ||
+           (hdmi->vic == 12) || (hdmi->vic == 13) ||
+           (hdmi->vic == 14) || (hdmi->vic == 15) ||
+           (hdmi->vic == 25) || (hdmi->vic == 26) ||
+           (hdmi->vic == 27) || (hdmi->vic == 28) ||
+           (hdmi->vic == 29) || (hdmi->vic == 30) ||
+           (hdmi->vic == 35) || (hdmi->vic == 36) ||
+           (hdmi->vic == 37) || (hdmi->vic == 38))
+               hdmi->hdmi_data.video_mode.mpixelrepetitionoutput = 1;
+       else
+               hdmi->hdmi_data.video_mode.mpixelrepetitionoutput = 0;
+
+       hdmi->hdmi_data.video_mode.mpixelrepetitioninput = 0;
+
+       /* TODO: Get input format from IPU (via FB driver interface) */
+       hdmi->hdmi_data.enc_in_format = RGB;
+
+       hdmi->hdmi_data.enc_out_format = RGB;
+
+       hdmi->hdmi_data.enc_color_depth = 8;
+       hdmi->hdmi_data.pix_repet_factor = 0;
+       hdmi->hdmi_data.hdcp_enable = 0;
+       hdmi->hdmi_data.video_mode.mdataenablepolarity = true;
+
+       /* HDMI Initialization Step B.1 */
+       hdmi_av_composer(hdmi, mode);
+
+       /* HDMI Initializateion Step B.2 */
+       ret = dw_hdmi_phy_init(hdmi);
+       if (ret)
+               return ret;
+
+       /* HDMI Initialization Step B.3 */
+       dw_hdmi_enable_video_path(hdmi);
+
+       /* not for DVI mode */
+       if (hdmi->hdmi_data.video_mode.mdvi) {
+               dev_dbg(hdmi->dev, "%s DVI mode\n", __func__);
+       } else {
+               dev_dbg(hdmi->dev, "%s CEA mode\n", __func__);
+
+               /* HDMI Initialization Step E - Configure audio */
+               hdmi_clk_regenerator_update_pixel_clock(hdmi);
+               hdmi_enable_audio_clk(hdmi);
+
+               /* HDMI Initialization Step F - Configure AVI InfoFrame */
+               hdmi_config_AVI(hdmi);
+       }
+
+       hdmi_video_packetize(hdmi);
+       hdmi_video_csc(hdmi);
+       hdmi_video_sample(hdmi);
+       hdmi_tx_hdcp_config(hdmi);
+
+       dw_hdmi_clear_overflow(hdmi);
+       if (hdmi->cable_plugin && !hdmi->hdmi_data.video_mode.mdvi)
+               hdmi_enable_overflow_interrupts(hdmi);
+
+       return 0;
+}
+
+/* Wait until we are registered to enable interrupts */
+static int dw_hdmi_fb_registered(struct dw_hdmi *hdmi)
+{
+       hdmi_writeb(hdmi, HDMI_PHY_I2CM_INT_ADDR_DONE_POL,
+                   HDMI_PHY_I2CM_INT_ADDR);
+
+       hdmi_writeb(hdmi, HDMI_PHY_I2CM_CTLINT_ADDR_NAC_POL |
+                   HDMI_PHY_I2CM_CTLINT_ADDR_ARBITRATION_POL,
+                   HDMI_PHY_I2CM_CTLINT_ADDR);
+
+       /* enable cable hot plug irq */
+       hdmi_writeb(hdmi, (u8)~HDMI_PHY_HPD, HDMI_PHY_MASK0);
+
+       /* Clear Hotplug interrupts */
+       hdmi_writeb(hdmi, HDMI_IH_PHY_STAT0_HPD, HDMI_IH_PHY_STAT0);
+
+       return 0;
+}
+
+static void initialize_hdmi_ih_mutes(struct dw_hdmi *hdmi)
+{
+       u8 ih_mute;
+
+       /*
+        * Boot up defaults are:
+        * HDMI_IH_MUTE   = 0x03 (disabled)
+        * HDMI_IH_MUTE_* = 0x00 (enabled)
+        *
+        * Disable top level interrupt bits in HDMI block
+        */
+       ih_mute = hdmi_readb(hdmi, HDMI_IH_MUTE) |
+                 HDMI_IH_MUTE_MUTE_WAKEUP_INTERRUPT |
+                 HDMI_IH_MUTE_MUTE_ALL_INTERRUPT;
+
+       hdmi_writeb(hdmi, ih_mute, HDMI_IH_MUTE);
+
+       /* by default mask all interrupts */
+       hdmi_writeb(hdmi, 0xff, HDMI_VP_MASK);
+       hdmi_writeb(hdmi, 0xff, HDMI_FC_MASK0);
+       hdmi_writeb(hdmi, 0xff, HDMI_FC_MASK1);
+       hdmi_writeb(hdmi, 0xff, HDMI_FC_MASK2);
+       hdmi_writeb(hdmi, 0xff, HDMI_PHY_MASK0);
+       hdmi_writeb(hdmi, 0xff, HDMI_PHY_I2CM_INT_ADDR);
+       hdmi_writeb(hdmi, 0xff, HDMI_PHY_I2CM_CTLINT_ADDR);
+       hdmi_writeb(hdmi, 0xff, HDMI_AUD_INT);
+       hdmi_writeb(hdmi, 0xff, HDMI_AUD_SPDIFINT);
+       hdmi_writeb(hdmi, 0xff, HDMI_AUD_HBR_MASK);
+       hdmi_writeb(hdmi, 0xff, HDMI_GP_MASK);
+       hdmi_writeb(hdmi, 0xff, HDMI_A_APIINTMSK);
+       hdmi_writeb(hdmi, 0xff, HDMI_CEC_MASK);
+       hdmi_writeb(hdmi, 0xff, HDMI_I2CM_INT);
+       hdmi_writeb(hdmi, 0xff, HDMI_I2CM_CTLINT);
+
+       /* Disable interrupts in the IH_MUTE_* registers */
+       hdmi_writeb(hdmi, 0xff, HDMI_IH_MUTE_FC_STAT0);
+       hdmi_writeb(hdmi, 0xff, HDMI_IH_MUTE_FC_STAT1);
+       hdmi_writeb(hdmi, 0xff, HDMI_IH_MUTE_FC_STAT2);
+       hdmi_writeb(hdmi, 0xff, HDMI_IH_MUTE_AS_STAT0);
+       hdmi_writeb(hdmi, 0xff, HDMI_IH_MUTE_PHY_STAT0);
+       hdmi_writeb(hdmi, 0xff, HDMI_IH_MUTE_I2CM_STAT0);
+       hdmi_writeb(hdmi, 0xff, HDMI_IH_MUTE_CEC_STAT0);
+       hdmi_writeb(hdmi, 0xff, HDMI_IH_MUTE_VP_STAT0);
+       hdmi_writeb(hdmi, 0xff, HDMI_IH_MUTE_I2CMPHY_STAT0);
+       hdmi_writeb(hdmi, 0xff, HDMI_IH_MUTE_AHBDMAAUD_STAT0);
+
+       /* Enable top level interrupt bits in HDMI block */
+       ih_mute &= ~(HDMI_IH_MUTE_MUTE_WAKEUP_INTERRUPT |
+                   HDMI_IH_MUTE_MUTE_ALL_INTERRUPT);
+       hdmi_writeb(hdmi, ih_mute, HDMI_IH_MUTE);
+}
+
+static void dw_hdmi_poweron(struct dw_hdmi *hdmi)
+{
+       dw_hdmi_setup(hdmi, &hdmi->previous_mode);
+}
+
+static void dw_hdmi_poweroff(struct dw_hdmi *hdmi)
+{
+       dw_hdmi_phy_disable(hdmi);
+}
+
+static void dw_hdmi_bridge_mode_set(struct drm_bridge *bridge,
+                                   struct drm_display_mode *orig_mode,
+                                   struct drm_display_mode *mode)
+{
+       struct dw_hdmi *hdmi = bridge->driver_private;
+
+       dw_hdmi_setup(hdmi, mode);
+
+       /* Store the display mode for plugin/DKMS poweron events */
+       memcpy(&hdmi->previous_mode, mode, sizeof(hdmi->previous_mode));
+}
+
+static bool dw_hdmi_bridge_mode_fixup(struct drm_bridge *bridge,
+                                     const struct drm_display_mode *mode,
+                                     struct drm_display_mode *adjusted_mode)
+{
+       return true;
+}
+
+static void dw_hdmi_bridge_disable(struct drm_bridge *bridge)
+{
+       struct dw_hdmi *hdmi = bridge->driver_private;
+
+       dw_hdmi_poweroff(hdmi);
+}
+
+static void dw_hdmi_bridge_enable(struct drm_bridge *bridge)
+{
+       struct dw_hdmi *hdmi = bridge->driver_private;
+
+       dw_hdmi_poweron(hdmi);
+}
+
+static void dw_hdmi_bridge_destroy(struct drm_bridge *bridge)
+{
+       drm_bridge_cleanup(bridge);
+       kfree(bridge);
+}
+
+static void dw_hdmi_bridge_nop(struct drm_bridge *bridge)
+{
+       /* do nothing */
+}
+
+static enum drm_connector_status
+dw_hdmi_connector_detect(struct drm_connector *connector, bool force)
+{
+       struct dw_hdmi *hdmi = container_of(connector, struct dw_hdmi,
+                                            connector);
+
+       return hdmi_readb(hdmi, HDMI_PHY_STAT0) & HDMI_PHY_HPD ?
+               connector_status_connected : connector_status_disconnected;
+}
+
+static int dw_hdmi_connector_get_modes(struct drm_connector *connector)
+{
+       struct dw_hdmi *hdmi = container_of(connector, struct dw_hdmi,
+                                            connector);
+       struct edid *edid;
+       int ret;
+
+       if (!hdmi->ddc)
+               return 0;
+
+       edid = drm_get_edid(connector, hdmi->ddc);
+       if (edid) {
+               dev_dbg(hdmi->dev, "got edid: width[%d] x height[%d]\n",
+                       edid->width_cm, edid->height_cm);
+
+               drm_mode_connector_update_edid_property(connector, edid);
+               ret = drm_add_edid_modes(connector, edid);
+               kfree(edid);
+       } else {
+               dev_dbg(hdmi->dev, "failed to get edid\n");
+       }
+
+       return 0;
+}
+
+static enum drm_mode_status
+dw_hdmi_connector_mode_valid(struct drm_connector *connector,
+                            struct drm_display_mode *mode)
+{
+       struct dw_hdmi *hdmi = container_of(connector,
+                                          struct dw_hdmi, connector);
+       enum drm_mode_status mode_status = MODE_OK;
+
+       if (hdmi->plat_data->mode_valid)
+               mode_status = hdmi->plat_data->mode_valid(connector, mode);
+
+       return mode_status;
+}
+
+static struct drm_encoder *dw_hdmi_connector_best_encoder(struct drm_connector
+                                                          *connector)
+{
+       struct dw_hdmi *hdmi = container_of(connector, struct dw_hdmi,
+                                            connector);
+
+       return hdmi->encoder;
+}
+
+static void dw_hdmi_connector_destroy(struct drm_connector *connector)
+{
+       drm_connector_unregister(connector);
+       drm_connector_cleanup(connector);
+}
+
+static struct drm_connector_funcs dw_hdmi_connector_funcs = {
+       .dpms = drm_helper_connector_dpms,
+       .fill_modes = drm_helper_probe_single_connector_modes,
+       .detect = dw_hdmi_connector_detect,
+       .destroy = dw_hdmi_connector_destroy,
+};
+
+static struct drm_connector_helper_funcs dw_hdmi_connector_helper_funcs = {
+       .get_modes = dw_hdmi_connector_get_modes,
+       .mode_valid = dw_hdmi_connector_mode_valid,
+       .best_encoder = dw_hdmi_connector_best_encoder,
+};
+
+struct drm_bridge_funcs dw_hdmi_bridge_funcs = {
+       .enable = dw_hdmi_bridge_enable,
+       .disable = dw_hdmi_bridge_disable,
+       .pre_enable = dw_hdmi_bridge_nop,
+       .post_disable = dw_hdmi_bridge_nop,
+       .mode_set = dw_hdmi_bridge_mode_set,
+       .mode_fixup = dw_hdmi_bridge_mode_fixup,
+       .destroy = dw_hdmi_bridge_destroy,
+};
+
+static irqreturn_t dw_hdmi_hardirq(int irq, void *dev_id)
+{
+       struct dw_hdmi *hdmi = dev_id;
+       u8 intr_stat;
+
+       intr_stat = hdmi_readb(hdmi, HDMI_IH_PHY_STAT0);
+       if (intr_stat)
+               hdmi_writeb(hdmi, ~0, HDMI_IH_MUTE_PHY_STAT0);
+
+       return intr_stat ? IRQ_WAKE_THREAD : IRQ_NONE;
+}
+
+static irqreturn_t dw_hdmi_irq(int irq, void *dev_id)
+{
+       struct dw_hdmi *hdmi = dev_id;
+       u8 intr_stat;
+       u8 phy_int_pol;
+
+       intr_stat = hdmi_readb(hdmi, HDMI_IH_PHY_STAT0);
+
+       phy_int_pol = hdmi_readb(hdmi, HDMI_PHY_POL0);
+
+       if (intr_stat & HDMI_IH_PHY_STAT0_HPD) {
+               if (phy_int_pol & HDMI_PHY_HPD) {
+                       dev_dbg(hdmi->dev, "EVENT=plugin\n");
+
+                       hdmi_modb(hdmi, 0, HDMI_PHY_HPD, HDMI_PHY_POL0);
+
+                       dw_hdmi_poweron(hdmi);
+               } else {
+                       dev_dbg(hdmi->dev, "EVENT=plugout\n");
+
+                       hdmi_modb(hdmi, HDMI_PHY_HPD, HDMI_PHY_HPD,
+                                 HDMI_PHY_POL0);
+
+                       dw_hdmi_poweroff(hdmi);
+               }
+               drm_helper_hpd_irq_event(hdmi->connector.dev);
+       }
+
+       hdmi_writeb(hdmi, intr_stat, HDMI_IH_PHY_STAT0);
+       hdmi_writeb(hdmi, ~HDMI_IH_PHY_STAT0_HPD, HDMI_IH_MUTE_PHY_STAT0);
+
+       return IRQ_HANDLED;
+}
+
+static int dw_hdmi_register(struct drm_device *drm, struct dw_hdmi *hdmi)
+{
+       struct drm_encoder *encoder = hdmi->encoder;
+       struct drm_bridge *bridge;
+       int ret;
+
+       bridge = devm_kzalloc(drm->dev, sizeof(*bridge), GFP_KERNEL);
+       if (!bridge) {
+               DRM_ERROR("Failed to allocate drm bridge\n");
+               return -ENOMEM;
+       }
+
+       hdmi->bridge = bridge;
+       bridge->driver_private = hdmi;
+
+       ret = drm_bridge_init(drm, bridge, &dw_hdmi_bridge_funcs);
+       if (ret) {
+               DRM_ERROR("Failed to initialize bridge with drm\n");
+               return -EINVAL;
+       }
+
+       encoder->bridge = bridge;
+       hdmi->connector.polled = DRM_CONNECTOR_POLL_HPD;
+
+       drm_connector_helper_add(&hdmi->connector,
+                                &dw_hdmi_connector_helper_funcs);
+       drm_connector_init(drm, &hdmi->connector, &dw_hdmi_connector_funcs,
+                          DRM_MODE_CONNECTOR_HDMIA);
+
+       hdmi->connector.encoder = encoder;
+
+       drm_mode_connector_attach_encoder(&hdmi->connector, encoder);
+
+       return 0;
+}
+
+int dw_hdmi_bind(struct device *dev, struct device *master,
+                void *data, struct drm_encoder *encoder,
+                struct resource *iores, int irq,
+                const struct dw_hdmi_plat_data *plat_data)
+{
+       struct drm_device *drm = data;
+       struct device_node *np = dev->of_node;
+       struct device_node *ddc_node;
+       struct dw_hdmi *hdmi;
+       int ret;
+       u32 val = 1;
+
+       hdmi = devm_kzalloc(dev, sizeof(*hdmi), GFP_KERNEL);
+       if (!hdmi)
+               return -ENOMEM;
+
+       hdmi->plat_data = plat_data;
+       hdmi->dev = dev;
+       hdmi->dev_type = plat_data->dev_type;
+       hdmi->sample_rate = 48000;
+       hdmi->ratio = 100;
+       hdmi->encoder = encoder;
+
+       of_property_read_u32(np, "reg-io-width", &val);
+
+       switch (val) {
+       case 4:
+               hdmi->write = dw_hdmi_writel;
+               hdmi->read = dw_hdmi_readl;
+               break;
+       case 1:
+               hdmi->write = dw_hdmi_writeb;
+               hdmi->read = dw_hdmi_readb;
+               break;
+       default:
+               dev_err(dev, "reg-io-width must be 1 or 4\n");
+               return -EINVAL;
+       }
+
+       ddc_node = of_parse_phandle(np, "ddc-i2c-bus", 0);
+       if (ddc_node) {
+               hdmi->ddc = of_find_i2c_adapter_by_node(ddc_node);
+               of_node_put(ddc_node);
+               if (!hdmi->ddc) {
+                       dev_dbg(hdmi->dev, "failed to read ddc node\n");
+                       return -EPROBE_DEFER;
+               }
+
+       } else {
+               dev_dbg(hdmi->dev, "no ddc property found\n");
+       }
+
+       hdmi->regs = devm_ioremap_resource(dev, iores);
+       if (IS_ERR(hdmi->regs))
+               return PTR_ERR(hdmi->regs);
+
+       hdmi->isfr_clk = devm_clk_get(hdmi->dev, "isfr");
+       if (IS_ERR(hdmi->isfr_clk)) {
+               ret = PTR_ERR(hdmi->isfr_clk);
+               dev_err(hdmi->dev, "Unable to get HDMI isfr clk: %d\n", ret);
+               return ret;
+       }
+
+       ret = clk_prepare_enable(hdmi->isfr_clk);
+       if (ret) {
+               dev_err(hdmi->dev, "Cannot enable HDMI isfr clock: %d\n", ret);
+               return ret;
+       }
+
+       hdmi->iahb_clk = devm_clk_get(hdmi->dev, "iahb");
+       if (IS_ERR(hdmi->iahb_clk)) {
+               ret = PTR_ERR(hdmi->iahb_clk);
+               dev_err(hdmi->dev, "Unable to get HDMI iahb clk: %d\n", ret);
+               goto err_isfr;
+       }
+
+       ret = clk_prepare_enable(hdmi->iahb_clk);
+       if (ret) {
+               dev_err(hdmi->dev, "Cannot enable HDMI iahb clock: %d\n", ret);
+               goto err_isfr;
+       }
+
+       /* Product and revision IDs */
+       dev_info(dev,
+                "Detected HDMI controller 0x%x:0x%x:0x%x:0x%x\n",
+                hdmi_readb(hdmi, HDMI_DESIGN_ID),
+                hdmi_readb(hdmi, HDMI_REVISION_ID),
+                hdmi_readb(hdmi, HDMI_PRODUCT_ID0),
+                hdmi_readb(hdmi, HDMI_PRODUCT_ID1));
+
+       initialize_hdmi_ih_mutes(hdmi);
+
+       ret = devm_request_threaded_irq(dev, irq, dw_hdmi_hardirq,
+                                       dw_hdmi_irq, IRQF_SHARED,
+                                       dev_name(dev), hdmi);
+       if (ret)
+               return ret;
+
+       /*
+        * To prevent overflows in HDMI_IH_FC_STAT2, set the clk regenerator
+        * N and cts values before enabling phy
+        */
+       hdmi_init_clk_regenerator(hdmi);
+
+       /*
+        * Configure registers related to HDMI interrupt
+        * generation before registering IRQ.
+        */
+       hdmi_writeb(hdmi, HDMI_PHY_HPD, HDMI_PHY_POL0);
+
+       /* Clear Hotplug interrupts */
+       hdmi_writeb(hdmi, HDMI_IH_PHY_STAT0_HPD, HDMI_IH_PHY_STAT0);
+
+       ret = dw_hdmi_fb_registered(hdmi);
+       if (ret)
+               goto err_iahb;
+
+       ret = dw_hdmi_register(drm, hdmi);
+       if (ret)
+               goto err_iahb;
+
+       /* Unmute interrupts */
+       hdmi_writeb(hdmi, ~HDMI_IH_PHY_STAT0_HPD, HDMI_IH_MUTE_PHY_STAT0);
+
+       dev_set_drvdata(dev, hdmi);
+
+       return 0;
+
+err_iahb:
+       clk_disable_unprepare(hdmi->iahb_clk);
+err_isfr:
+       clk_disable_unprepare(hdmi->isfr_clk);
+
+       return ret;
+}
+EXPORT_SYMBOL_GPL(dw_hdmi_bind);
+
+void dw_hdmi_unbind(struct device *dev, struct device *master, void *data)
+{
+       struct dw_hdmi *hdmi = dev_get_drvdata(dev);
+
+       /* Disable all interrupts */
+       hdmi_writeb(hdmi, ~0, HDMI_IH_MUTE_PHY_STAT0);
+
+       hdmi->connector.funcs->destroy(&hdmi->connector);
+       hdmi->encoder->funcs->destroy(hdmi->encoder);
+
+       clk_disable_unprepare(hdmi->iahb_clk);
+       clk_disable_unprepare(hdmi->isfr_clk);
+       i2c_put_adapter(hdmi->ddc);
+}
+EXPORT_SYMBOL_GPL(dw_hdmi_unbind);
+
+MODULE_AUTHOR("Sascha Hauer <s.hauer@pengutronix.de>");
+MODULE_AUTHOR("Andy Yan <andy.yan@rock-chips.com>");
+MODULE_AUTHOR("Yakir Yang <ykk@rock-chips.com>");
+MODULE_DESCRIPTION("DW HDMI transmitter driver");
+MODULE_LICENSE("GPL");
+MODULE_ALIAS("platform:dw-hdmi");
diff --git a/drivers/gpu/drm/bridge/dw_hdmi.h b/drivers/gpu/drm/bridge/dw_hdmi.h
new file mode 100644 (file)
index 0000000..175dbc8
--- /dev/null
@@ -0,0 +1,1034 @@
+/*
+ * Copyright (C) 2011 Freescale Semiconductor, Inc.
+ *
+ * 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.
+ */
+
+#ifndef __IMX_HDMI_H__
+#define __IMX_HDMI_H__
+
+/* Identification Registers */
+#define HDMI_DESIGN_ID                          0x0000
+#define HDMI_REVISION_ID                        0x0001
+#define HDMI_PRODUCT_ID0                        0x0002
+#define HDMI_PRODUCT_ID1                        0x0003
+#define HDMI_CONFIG0_ID                         0x0004
+#define HDMI_CONFIG1_ID                         0x0005
+#define HDMI_CONFIG2_ID                         0x0006
+#define HDMI_CONFIG3_ID                         0x0007
+
+/* Interrupt Registers */
+#define HDMI_IH_FC_STAT0                        0x0100
+#define HDMI_IH_FC_STAT1                        0x0101
+#define HDMI_IH_FC_STAT2                        0x0102
+#define HDMI_IH_AS_STAT0                        0x0103
+#define HDMI_IH_PHY_STAT0                       0x0104
+#define HDMI_IH_I2CM_STAT0                      0x0105
+#define HDMI_IH_CEC_STAT0                       0x0106
+#define HDMI_IH_VP_STAT0                        0x0107
+#define HDMI_IH_I2CMPHY_STAT0                   0x0108
+#define HDMI_IH_AHBDMAAUD_STAT0                 0x0109
+
+#define HDMI_IH_MUTE_FC_STAT0                   0x0180
+#define HDMI_IH_MUTE_FC_STAT1                   0x0181
+#define HDMI_IH_MUTE_FC_STAT2                   0x0182
+#define HDMI_IH_MUTE_AS_STAT0                   0x0183
+#define HDMI_IH_MUTE_PHY_STAT0                  0x0184
+#define HDMI_IH_MUTE_I2CM_STAT0                 0x0185
+#define HDMI_IH_MUTE_CEC_STAT0                  0x0186
+#define HDMI_IH_MUTE_VP_STAT0                   0x0187
+#define HDMI_IH_MUTE_I2CMPHY_STAT0              0x0188
+#define HDMI_IH_MUTE_AHBDMAAUD_STAT0            0x0189
+#define HDMI_IH_MUTE                            0x01FF
+
+/* Video Sample Registers */
+#define HDMI_TX_INVID0                          0x0200
+#define HDMI_TX_INSTUFFING                      0x0201
+#define HDMI_TX_GYDATA0                         0x0202
+#define HDMI_TX_GYDATA1                         0x0203
+#define HDMI_TX_RCRDATA0                        0x0204
+#define HDMI_TX_RCRDATA1                        0x0205
+#define HDMI_TX_BCBDATA0                        0x0206
+#define HDMI_TX_BCBDATA1                        0x0207
+
+/* Video Packetizer Registers */
+#define HDMI_VP_STATUS                          0x0800
+#define HDMI_VP_PR_CD                           0x0801
+#define HDMI_VP_STUFF                           0x0802
+#define HDMI_VP_REMAP                           0x0803
+#define HDMI_VP_CONF                            0x0804
+#define HDMI_VP_STAT                            0x0805
+#define HDMI_VP_INT                             0x0806
+#define HDMI_VP_MASK                            0x0807
+#define HDMI_VP_POL                             0x0808
+
+/* Frame Composer Registers */
+#define HDMI_FC_INVIDCONF                       0x1000
+#define HDMI_FC_INHACTV0                        0x1001
+#define HDMI_FC_INHACTV1                        0x1002
+#define HDMI_FC_INHBLANK0                       0x1003
+#define HDMI_FC_INHBLANK1                       0x1004
+#define HDMI_FC_INVACTV0                        0x1005
+#define HDMI_FC_INVACTV1                        0x1006
+#define HDMI_FC_INVBLANK                        0x1007
+#define HDMI_FC_HSYNCINDELAY0                   0x1008
+#define HDMI_FC_HSYNCINDELAY1                   0x1009
+#define HDMI_FC_HSYNCINWIDTH0                   0x100A
+#define HDMI_FC_HSYNCINWIDTH1                   0x100B
+#define HDMI_FC_VSYNCINDELAY                    0x100C
+#define HDMI_FC_VSYNCINWIDTH                    0x100D
+#define HDMI_FC_INFREQ0                         0x100E
+#define HDMI_FC_INFREQ1                         0x100F
+#define HDMI_FC_INFREQ2                         0x1010
+#define HDMI_FC_CTRLDUR                         0x1011
+#define HDMI_FC_EXCTRLDUR                       0x1012
+#define HDMI_FC_EXCTRLSPAC                      0x1013
+#define HDMI_FC_CH0PREAM                        0x1014
+#define HDMI_FC_CH1PREAM                        0x1015
+#define HDMI_FC_CH2PREAM                        0x1016
+#define HDMI_FC_AVICONF3                        0x1017
+#define HDMI_FC_GCP                             0x1018
+#define HDMI_FC_AVICONF0                        0x1019
+#define HDMI_FC_AVICONF1                        0x101A
+#define HDMI_FC_AVICONF2                        0x101B
+#define HDMI_FC_AVIVID                          0x101C
+#define HDMI_FC_AVIETB0                         0x101D
+#define HDMI_FC_AVIETB1                         0x101E
+#define HDMI_FC_AVISBB0                         0x101F
+#define HDMI_FC_AVISBB1                         0x1020
+#define HDMI_FC_AVIELB0                         0x1021
+#define HDMI_FC_AVIELB1                         0x1022
+#define HDMI_FC_AVISRB0                         0x1023
+#define HDMI_FC_AVISRB1                         0x1024
+#define HDMI_FC_AUDICONF0                       0x1025
+#define HDMI_FC_AUDICONF1                       0x1026
+#define HDMI_FC_AUDICONF2                       0x1027
+#define HDMI_FC_AUDICONF3                       0x1028
+#define HDMI_FC_VSDIEEEID0                      0x1029
+#define HDMI_FC_VSDSIZE                         0x102A
+#define HDMI_FC_VSDIEEEID1                      0x1030
+#define HDMI_FC_VSDIEEEID2                      0x1031
+#define HDMI_FC_VSDPAYLOAD0                     0x1032
+#define HDMI_FC_VSDPAYLOAD1                     0x1033
+#define HDMI_FC_VSDPAYLOAD2                     0x1034
+#define HDMI_FC_VSDPAYLOAD3                     0x1035
+#define HDMI_FC_VSDPAYLOAD4                     0x1036
+#define HDMI_FC_VSDPAYLOAD5                     0x1037
+#define HDMI_FC_VSDPAYLOAD6                     0x1038
+#define HDMI_FC_VSDPAYLOAD7                     0x1039
+#define HDMI_FC_VSDPAYLOAD8                     0x103A
+#define HDMI_FC_VSDPAYLOAD9                     0x103B
+#define HDMI_FC_VSDPAYLOAD10                    0x103C
+#define HDMI_FC_VSDPAYLOAD11                    0x103D
+#define HDMI_FC_VSDPAYLOAD12                    0x103E
+#define HDMI_FC_VSDPAYLOAD13                    0x103F
+#define HDMI_FC_VSDPAYLOAD14                    0x1040
+#define HDMI_FC_VSDPAYLOAD15                    0x1041
+#define HDMI_FC_VSDPAYLOAD16                    0x1042
+#define HDMI_FC_VSDPAYLOAD17                    0x1043
+#define HDMI_FC_VSDPAYLOAD18                    0x1044
+#define HDMI_FC_VSDPAYLOAD19                    0x1045
+#define HDMI_FC_VSDPAYLOAD20                    0x1046
+#define HDMI_FC_VSDPAYLOAD21                    0x1047
+#define HDMI_FC_VSDPAYLOAD22                    0x1048
+#define HDMI_FC_VSDPAYLOAD23                    0x1049
+#define HDMI_FC_SPDVENDORNAME0                  0x104A
+#define HDMI_FC_SPDVENDORNAME1                  0x104B
+#define HDMI_FC_SPDVENDORNAME2                  0x104C
+#define HDMI_FC_SPDVENDORNAME3                  0x104D
+#define HDMI_FC_SPDVENDORNAME4                  0x104E
+#define HDMI_FC_SPDVENDORNAME5                  0x104F
+#define HDMI_FC_SPDVENDORNAME6                  0x1050
+#define HDMI_FC_SPDVENDORNAME7                  0x1051
+#define HDMI_FC_SDPPRODUCTNAME0                 0x1052
+#define HDMI_FC_SDPPRODUCTNAME1                 0x1053
+#define HDMI_FC_SDPPRODUCTNAME2                 0x1054
+#define HDMI_FC_SDPPRODUCTNAME3                 0x1055
+#define HDMI_FC_SDPPRODUCTNAME4                 0x1056
+#define HDMI_FC_SDPPRODUCTNAME5                 0x1057
+#define HDMI_FC_SDPPRODUCTNAME6                 0x1058
+#define HDMI_FC_SDPPRODUCTNAME7                 0x1059
+#define HDMI_FC_SDPPRODUCTNAME8                 0x105A
+#define HDMI_FC_SDPPRODUCTNAME9                 0x105B
+#define HDMI_FC_SDPPRODUCTNAME10                0x105C
+#define HDMI_FC_SDPPRODUCTNAME11                0x105D
+#define HDMI_FC_SDPPRODUCTNAME12                0x105E
+#define HDMI_FC_SDPPRODUCTNAME13                0x105F
+#define HDMI_FC_SDPPRODUCTNAME14                0x1060
+#define HDMI_FC_SPDPRODUCTNAME15                0x1061
+#define HDMI_FC_SPDDEVICEINF                    0x1062
+#define HDMI_FC_AUDSCONF                        0x1063
+#define HDMI_FC_AUDSSTAT                        0x1064
+#define HDMI_FC_DATACH0FILL                     0x1070
+#define HDMI_FC_DATACH1FILL                     0x1071
+#define HDMI_FC_DATACH2FILL                     0x1072
+#define HDMI_FC_CTRLQHIGH                       0x1073
+#define HDMI_FC_CTRLQLOW                        0x1074
+#define HDMI_FC_ACP0                            0x1075
+#define HDMI_FC_ACP28                           0x1076
+#define HDMI_FC_ACP27                           0x1077
+#define HDMI_FC_ACP26                           0x1078
+#define HDMI_FC_ACP25                           0x1079
+#define HDMI_FC_ACP24                           0x107A
+#define HDMI_FC_ACP23                           0x107B
+#define HDMI_FC_ACP22                           0x107C
+#define HDMI_FC_ACP21                           0x107D
+#define HDMI_FC_ACP20                           0x107E
+#define HDMI_FC_ACP19                           0x107F
+#define HDMI_FC_ACP18                           0x1080
+#define HDMI_FC_ACP17                           0x1081
+#define HDMI_FC_ACP16                           0x1082
+#define HDMI_FC_ACP15                           0x1083
+#define HDMI_FC_ACP14                           0x1084
+#define HDMI_FC_ACP13                           0x1085
+#define HDMI_FC_ACP12                           0x1086
+#define HDMI_FC_ACP11                           0x1087
+#define HDMI_FC_ACP10                           0x1088
+#define HDMI_FC_ACP9                            0x1089
+#define HDMI_FC_ACP8                            0x108A
+#define HDMI_FC_ACP7                            0x108B
+#define HDMI_FC_ACP6                            0x108C
+#define HDMI_FC_ACP5                            0x108D
+#define HDMI_FC_ACP4                            0x108E
+#define HDMI_FC_ACP3                            0x108F
+#define HDMI_FC_ACP2                            0x1090
+#define HDMI_FC_ACP1                            0x1091
+#define HDMI_FC_ISCR1_0                         0x1092
+#define HDMI_FC_ISCR1_16                        0x1093
+#define HDMI_FC_ISCR1_15                        0x1094
+#define HDMI_FC_ISCR1_14                        0x1095
+#define HDMI_FC_ISCR1_13                        0x1096
+#define HDMI_FC_ISCR1_12                        0x1097
+#define HDMI_FC_ISCR1_11                        0x1098
+#define HDMI_FC_ISCR1_10                        0x1099
+#define HDMI_FC_ISCR1_9                         0x109A
+#define HDMI_FC_ISCR1_8                         0x109B
+#define HDMI_FC_ISCR1_7                         0x109C
+#define HDMI_FC_ISCR1_6                         0x109D
+#define HDMI_FC_ISCR1_5                         0x109E
+#define HDMI_FC_ISCR1_4                         0x109F
+#define HDMI_FC_ISCR1_3                         0x10A0
+#define HDMI_FC_ISCR1_2                         0x10A1
+#define HDMI_FC_ISCR1_1                         0x10A2
+#define HDMI_FC_ISCR2_15                        0x10A3
+#define HDMI_FC_ISCR2_14                        0x10A4
+#define HDMI_FC_ISCR2_13                        0x10A5
+#define HDMI_FC_ISCR2_12                        0x10A6
+#define HDMI_FC_ISCR2_11                        0x10A7
+#define HDMI_FC_ISCR2_10                        0x10A8
+#define HDMI_FC_ISCR2_9                         0x10A9
+#define HDMI_FC_ISCR2_8                         0x10AA
+#define HDMI_FC_ISCR2_7                         0x10AB
+#define HDMI_FC_ISCR2_6                         0x10AC
+#define HDMI_FC_ISCR2_5                         0x10AD
+#define HDMI_FC_ISCR2_4                         0x10AE
+#define HDMI_FC_ISCR2_3                         0x10AF
+#define HDMI_FC_ISCR2_2                         0x10B0
+#define HDMI_FC_ISCR2_1                         0x10B1
+#define HDMI_FC_ISCR2_0                         0x10B2
+#define HDMI_FC_DATAUTO0                        0x10B3
+#define HDMI_FC_DATAUTO1                        0x10B4
+#define HDMI_FC_DATAUTO2                        0x10B5
+#define HDMI_FC_DATMAN                          0x10B6
+#define HDMI_FC_DATAUTO3                        0x10B7
+#define HDMI_FC_RDRB0                           0x10B8
+#define HDMI_FC_RDRB1                           0x10B9
+#define HDMI_FC_RDRB2                           0x10BA
+#define HDMI_FC_RDRB3                           0x10BB
+#define HDMI_FC_RDRB4                           0x10BC
+#define HDMI_FC_RDRB5                           0x10BD
+#define HDMI_FC_RDRB6                           0x10BE
+#define HDMI_FC_RDRB7                           0x10BF
+#define HDMI_FC_STAT0                           0x10D0
+#define HDMI_FC_INT0                            0x10D1
+#define HDMI_FC_MASK0                           0x10D2
+#define HDMI_FC_POL0                            0x10D3
+#define HDMI_FC_STAT1                           0x10D4
+#define HDMI_FC_INT1                            0x10D5
+#define HDMI_FC_MASK1                           0x10D6
+#define HDMI_FC_POL1                            0x10D7
+#define HDMI_FC_STAT2                           0x10D8
+#define HDMI_FC_INT2                            0x10D9
+#define HDMI_FC_MASK2                           0x10DA
+#define HDMI_FC_POL2                            0x10DB
+#define HDMI_FC_PRCONF                          0x10E0
+
+#define HDMI_FC_GMD_STAT                        0x1100
+#define HDMI_FC_GMD_EN                          0x1101
+#define HDMI_FC_GMD_UP                          0x1102
+#define HDMI_FC_GMD_CONF                        0x1103
+#define HDMI_FC_GMD_HB                          0x1104
+#define HDMI_FC_GMD_PB0                         0x1105
+#define HDMI_FC_GMD_PB1                         0x1106
+#define HDMI_FC_GMD_PB2                         0x1107
+#define HDMI_FC_GMD_PB3                         0x1108
+#define HDMI_FC_GMD_PB4                         0x1109
+#define HDMI_FC_GMD_PB5                         0x110A
+#define HDMI_FC_GMD_PB6                         0x110B
+#define HDMI_FC_GMD_PB7                         0x110C
+#define HDMI_FC_GMD_PB8                         0x110D
+#define HDMI_FC_GMD_PB9                         0x110E
+#define HDMI_FC_GMD_PB10                        0x110F
+#define HDMI_FC_GMD_PB11                        0x1110
+#define HDMI_FC_GMD_PB12                        0x1111
+#define HDMI_FC_GMD_PB13                        0x1112
+#define HDMI_FC_GMD_PB14                        0x1113
+#define HDMI_FC_GMD_PB15                        0x1114
+#define HDMI_FC_GMD_PB16                        0x1115
+#define HDMI_FC_GMD_PB17                        0x1116
+#define HDMI_FC_GMD_PB18                        0x1117
+#define HDMI_FC_GMD_PB19                        0x1118
+#define HDMI_FC_GMD_PB20                        0x1119
+#define HDMI_FC_GMD_PB21                        0x111A
+#define HDMI_FC_GMD_PB22                        0x111B
+#define HDMI_FC_GMD_PB23                        0x111C
+#define HDMI_FC_GMD_PB24                        0x111D
+#define HDMI_FC_GMD_PB25                        0x111E
+#define HDMI_FC_GMD_PB26                        0x111F
+#define HDMI_FC_GMD_PB27                        0x1120
+
+#define HDMI_FC_DBGFORCE                        0x1200
+#define HDMI_FC_DBGAUD0CH0                      0x1201
+#define HDMI_FC_DBGAUD1CH0                      0x1202
+#define HDMI_FC_DBGAUD2CH0                      0x1203
+#define HDMI_FC_DBGAUD0CH1                      0x1204
+#define HDMI_FC_DBGAUD1CH1                      0x1205
+#define HDMI_FC_DBGAUD2CH1                      0x1206
+#define HDMI_FC_DBGAUD0CH2                      0x1207
+#define HDMI_FC_DBGAUD1CH2                      0x1208
+#define HDMI_FC_DBGAUD2CH2                      0x1209
+#define HDMI_FC_DBGAUD0CH3                      0x120A
+#define HDMI_FC_DBGAUD1CH3                      0x120B
+#define HDMI_FC_DBGAUD2CH3                      0x120C
+#define HDMI_FC_DBGAUD0CH4                      0x120D
+#define HDMI_FC_DBGAUD1CH4                      0x120E
+#define HDMI_FC_DBGAUD2CH4                      0x120F
+#define HDMI_FC_DBGAUD0CH5                      0x1210
+#define HDMI_FC_DBGAUD1CH5                      0x1211
+#define HDMI_FC_DBGAUD2CH5                      0x1212
+#define HDMI_FC_DBGAUD0CH6                      0x1213
+#define HDMI_FC_DBGAUD1CH6                      0x1214
+#define HDMI_FC_DBGAUD2CH6                      0x1215
+#define HDMI_FC_DBGAUD0CH7                      0x1216
+#define HDMI_FC_DBGAUD1CH7                      0x1217
+#define HDMI_FC_DBGAUD2CH7                      0x1218
+#define HDMI_FC_DBGTMDS0                        0x1219
+#define HDMI_FC_DBGTMDS1                        0x121A
+#define HDMI_FC_DBGTMDS2                        0x121B
+
+/* HDMI Source PHY Registers */
+#define HDMI_PHY_CONF0                          0x3000
+#define HDMI_PHY_TST0                           0x3001
+#define HDMI_PHY_TST1                           0x3002
+#define HDMI_PHY_TST2                           0x3003
+#define HDMI_PHY_STAT0                          0x3004
+#define HDMI_PHY_INT0                           0x3005
+#define HDMI_PHY_MASK0                          0x3006
+#define HDMI_PHY_POL0                           0x3007
+
+/* HDMI Master PHY Registers */
+#define HDMI_PHY_I2CM_SLAVE_ADDR                0x3020
+#define HDMI_PHY_I2CM_ADDRESS_ADDR              0x3021
+#define HDMI_PHY_I2CM_DATAO_1_ADDR              0x3022
+#define HDMI_PHY_I2CM_DATAO_0_ADDR              0x3023
+#define HDMI_PHY_I2CM_DATAI_1_ADDR              0x3024
+#define HDMI_PHY_I2CM_DATAI_0_ADDR              0x3025
+#define HDMI_PHY_I2CM_OPERATION_ADDR            0x3026
+#define HDMI_PHY_I2CM_INT_ADDR                  0x3027
+#define HDMI_PHY_I2CM_CTLINT_ADDR               0x3028
+#define HDMI_PHY_I2CM_DIV_ADDR                  0x3029
+#define HDMI_PHY_I2CM_SOFTRSTZ_ADDR             0x302a
+#define HDMI_PHY_I2CM_SS_SCL_HCNT_1_ADDR        0x302b
+#define HDMI_PHY_I2CM_SS_SCL_HCNT_0_ADDR        0x302c
+#define HDMI_PHY_I2CM_SS_SCL_LCNT_1_ADDR        0x302d
+#define HDMI_PHY_I2CM_SS_SCL_LCNT_0_ADDR        0x302e
+#define HDMI_PHY_I2CM_FS_SCL_HCNT_1_ADDR        0x302f
+#define HDMI_PHY_I2CM_FS_SCL_HCNT_0_ADDR        0x3030
+#define HDMI_PHY_I2CM_FS_SCL_LCNT_1_ADDR        0x3031
+#define HDMI_PHY_I2CM_FS_SCL_LCNT_0_ADDR        0x3032
+
+/* Audio Sampler Registers */
+#define HDMI_AUD_CONF0                          0x3100
+#define HDMI_AUD_CONF1                          0x3101
+#define HDMI_AUD_INT                            0x3102
+#define HDMI_AUD_CONF2                          0x3103
+#define HDMI_AUD_N1                             0x3200
+#define HDMI_AUD_N2                             0x3201
+#define HDMI_AUD_N3                             0x3202
+#define HDMI_AUD_CTS1                           0x3203
+#define HDMI_AUD_CTS2                           0x3204
+#define HDMI_AUD_CTS3                           0x3205
+#define HDMI_AUD_INPUTCLKFS                     0x3206
+#define HDMI_AUD_SPDIFINT                      0x3302
+#define HDMI_AUD_CONF0_HBR                      0x3400
+#define HDMI_AUD_HBR_STATUS                     0x3401
+#define HDMI_AUD_HBR_INT                        0x3402
+#define HDMI_AUD_HBR_POL                        0x3403
+#define HDMI_AUD_HBR_MASK                       0x3404
+
+/*
+ * Generic Parallel Audio Interface Registers
+ * Not used as GPAUD interface is not enabled in hw
+ */
+#define HDMI_GP_CONF0                           0x3500
+#define HDMI_GP_CONF1                           0x3501
+#define HDMI_GP_CONF2                           0x3502
+#define HDMI_GP_STAT                            0x3503
+#define HDMI_GP_INT                             0x3504
+#define HDMI_GP_MASK                            0x3505
+#define HDMI_GP_POL                             0x3506
+
+/* Audio DMA Registers */
+#define HDMI_AHB_DMA_CONF0                      0x3600
+#define HDMI_AHB_DMA_START                      0x3601
+#define HDMI_AHB_DMA_STOP                       0x3602
+#define HDMI_AHB_DMA_THRSLD                     0x3603
+#define HDMI_AHB_DMA_STRADDR0                   0x3604
+#define HDMI_AHB_DMA_STRADDR1                   0x3605
+#define HDMI_AHB_DMA_STRADDR2                   0x3606
+#define HDMI_AHB_DMA_STRADDR3                   0x3607
+#define HDMI_AHB_DMA_STPADDR0                   0x3608
+#define HDMI_AHB_DMA_STPADDR1                   0x3609
+#define HDMI_AHB_DMA_STPADDR2                   0x360a
+#define HDMI_AHB_DMA_STPADDR3                   0x360b
+#define HDMI_AHB_DMA_BSTADDR0                   0x360c
+#define HDMI_AHB_DMA_BSTADDR1                   0x360d
+#define HDMI_AHB_DMA_BSTADDR2                   0x360e
+#define HDMI_AHB_DMA_BSTADDR3                   0x360f
+#define HDMI_AHB_DMA_MBLENGTH0                  0x3610
+#define HDMI_AHB_DMA_MBLENGTH1                  0x3611
+#define HDMI_AHB_DMA_STAT                       0x3612
+#define HDMI_AHB_DMA_INT                        0x3613
+#define HDMI_AHB_DMA_MASK                       0x3614
+#define HDMI_AHB_DMA_POL                        0x3615
+#define HDMI_AHB_DMA_CONF1                      0x3616
+#define HDMI_AHB_DMA_BUFFSTAT                   0x3617
+#define HDMI_AHB_DMA_BUFFINT                    0x3618
+#define HDMI_AHB_DMA_BUFFMASK                   0x3619
+#define HDMI_AHB_DMA_BUFFPOL                    0x361a
+
+/* Main Controller Registers */
+#define HDMI_MC_SFRDIV                          0x4000
+#define HDMI_MC_CLKDIS                          0x4001
+#define HDMI_MC_SWRSTZ                          0x4002
+#define HDMI_MC_OPCTRL                          0x4003
+#define HDMI_MC_FLOWCTRL                        0x4004
+#define HDMI_MC_PHYRSTZ                         0x4005
+#define HDMI_MC_LOCKONCLOCK                     0x4006
+#define HDMI_MC_HEACPHY_RST                     0x4007
+
+/* Color Space  Converter Registers */
+#define HDMI_CSC_CFG                            0x4100
+#define HDMI_CSC_SCALE                          0x4101
+#define HDMI_CSC_COEF_A1_MSB                    0x4102
+#define HDMI_CSC_COEF_A1_LSB                    0x4103
+#define HDMI_CSC_COEF_A2_MSB                    0x4104
+#define HDMI_CSC_COEF_A2_LSB                    0x4105
+#define HDMI_CSC_COEF_A3_MSB                    0x4106
+#define HDMI_CSC_COEF_A3_LSB                    0x4107
+#define HDMI_CSC_COEF_A4_MSB                    0x4108
+#define HDMI_CSC_COEF_A4_LSB                    0x4109
+#define HDMI_CSC_COEF_B1_MSB                    0x410A
+#define HDMI_CSC_COEF_B1_LSB                    0x410B
+#define HDMI_CSC_COEF_B2_MSB                    0x410C
+#define HDMI_CSC_COEF_B2_LSB                    0x410D
+#define HDMI_CSC_COEF_B3_MSB                    0x410E
+#define HDMI_CSC_COEF_B3_LSB                    0x410F
+#define HDMI_CSC_COEF_B4_MSB                    0x4110
+#define HDMI_CSC_COEF_B4_LSB                    0x4111
+#define HDMI_CSC_COEF_C1_MSB                    0x4112
+#define HDMI_CSC_COEF_C1_LSB                    0x4113
+#define HDMI_CSC_COEF_C2_MSB                    0x4114
+#define HDMI_CSC_COEF_C2_LSB                    0x4115
+#define HDMI_CSC_COEF_C3_MSB                    0x4116
+#define HDMI_CSC_COEF_C3_LSB                    0x4117
+#define HDMI_CSC_COEF_C4_MSB                    0x4118
+#define HDMI_CSC_COEF_C4_LSB                    0x4119
+
+/* HDCP Encryption Engine Registers */
+#define HDMI_A_HDCPCFG0                         0x5000
+#define HDMI_A_HDCPCFG1                         0x5001
+#define HDMI_A_HDCPOBS0                         0x5002
+#define HDMI_A_HDCPOBS1                         0x5003
+#define HDMI_A_HDCPOBS2                         0x5004
+#define HDMI_A_HDCPOBS3                         0x5005
+#define HDMI_A_APIINTCLR                        0x5006
+#define HDMI_A_APIINTSTAT                       0x5007
+#define HDMI_A_APIINTMSK                        0x5008
+#define HDMI_A_VIDPOLCFG                        0x5009
+#define HDMI_A_OESSWCFG                         0x500A
+#define HDMI_A_TIMER1SETUP0                     0x500B
+#define HDMI_A_TIMER1SETUP1                     0x500C
+#define HDMI_A_TIMER2SETUP0                     0x500D
+#define HDMI_A_TIMER2SETUP1                     0x500E
+#define HDMI_A_100MSCFG                         0x500F
+#define HDMI_A_2SCFG0                           0x5010
+#define HDMI_A_2SCFG1                           0x5011
+#define HDMI_A_5SCFG0                           0x5012
+#define HDMI_A_5SCFG1                           0x5013
+#define HDMI_A_SRMVERLSB                        0x5014
+#define HDMI_A_SRMVERMSB                        0x5015
+#define HDMI_A_SRMCTRL                          0x5016
+#define HDMI_A_SFRSETUP                         0x5017
+#define HDMI_A_I2CHSETUP                        0x5018
+#define HDMI_A_INTSETUP                         0x5019
+#define HDMI_A_PRESETUP                         0x501A
+#define HDMI_A_SRM_BASE                         0x5020
+
+/* CEC Engine Registers */
+#define HDMI_CEC_CTRL                           0x7D00
+#define HDMI_CEC_STAT                           0x7D01
+#define HDMI_CEC_MASK                           0x7D02
+#define HDMI_CEC_POLARITY                       0x7D03
+#define HDMI_CEC_INT                            0x7D04
+#define HDMI_CEC_ADDR_L                         0x7D05
+#define HDMI_CEC_ADDR_H                         0x7D06
+#define HDMI_CEC_TX_CNT                         0x7D07
+#define HDMI_CEC_RX_CNT                         0x7D08
+#define HDMI_CEC_TX_DATA0                       0x7D10
+#define HDMI_CEC_TX_DATA1                       0x7D11
+#define HDMI_CEC_TX_DATA2                       0x7D12
+#define HDMI_CEC_TX_DATA3                       0x7D13
+#define HDMI_CEC_TX_DATA4                       0x7D14
+#define HDMI_CEC_TX_DATA5                       0x7D15
+#define HDMI_CEC_TX_DATA6                       0x7D16
+#define HDMI_CEC_TX_DATA7                       0x7D17
+#define HDMI_CEC_TX_DATA8                       0x7D18
+#define HDMI_CEC_TX_DATA9                       0x7D19
+#define HDMI_CEC_TX_DATA10                      0x7D1a
+#define HDMI_CEC_TX_DATA11                      0x7D1b
+#define HDMI_CEC_TX_DATA12                      0x7D1c
+#define HDMI_CEC_TX_DATA13                      0x7D1d
+#define HDMI_CEC_TX_DATA14                      0x7D1e
+#define HDMI_CEC_TX_DATA15                      0x7D1f
+#define HDMI_CEC_RX_DATA0                       0x7D20
+#define HDMI_CEC_RX_DATA1                       0x7D21
+#define HDMI_CEC_RX_DATA2                       0x7D22
+#define HDMI_CEC_RX_DATA3                       0x7D23
+#define HDMI_CEC_RX_DATA4                       0x7D24
+#define HDMI_CEC_RX_DATA5                       0x7D25
+#define HDMI_CEC_RX_DATA6                       0x7D26
+#define HDMI_CEC_RX_DATA7                       0x7D27
+#define HDMI_CEC_RX_DATA8                       0x7D28
+#define HDMI_CEC_RX_DATA9                       0x7D29
+#define HDMI_CEC_RX_DATA10                      0x7D2a
+#define HDMI_CEC_RX_DATA11                      0x7D2b
+#define HDMI_CEC_RX_DATA12                      0x7D2c
+#define HDMI_CEC_RX_DATA13                      0x7D2d
+#define HDMI_CEC_RX_DATA14                      0x7D2e
+#define HDMI_CEC_RX_DATA15                      0x7D2f
+#define HDMI_CEC_LOCK                           0x7D30
+#define HDMI_CEC_WKUPCTRL                       0x7D31
+
+/* I2C Master Registers (E-DDC) */
+#define HDMI_I2CM_SLAVE                         0x7E00
+#define HDMI_I2CMESS                            0x7E01
+#define HDMI_I2CM_DATAO                         0x7E02
+#define HDMI_I2CM_DATAI                         0x7E03
+#define HDMI_I2CM_OPERATION                     0x7E04
+#define HDMI_I2CM_INT                           0x7E05
+#define HDMI_I2CM_CTLINT                        0x7E06
+#define HDMI_I2CM_DIV                           0x7E07
+#define HDMI_I2CM_SEGADDR                       0x7E08
+#define HDMI_I2CM_SOFTRSTZ                      0x7E09
+#define HDMI_I2CM_SEGPTR                        0x7E0A
+#define HDMI_I2CM_SS_SCL_HCNT_1_ADDR            0x7E0B
+#define HDMI_I2CM_SS_SCL_HCNT_0_ADDR            0x7E0C
+#define HDMI_I2CM_SS_SCL_LCNT_1_ADDR            0x7E0D
+#define HDMI_I2CM_SS_SCL_LCNT_0_ADDR            0x7E0E
+#define HDMI_I2CM_FS_SCL_HCNT_1_ADDR            0x7E0F
+#define HDMI_I2CM_FS_SCL_HCNT_0_ADDR            0x7E10
+#define HDMI_I2CM_FS_SCL_LCNT_1_ADDR            0x7E11
+#define HDMI_I2CM_FS_SCL_LCNT_0_ADDR            0x7E12
+
+enum {
+/* IH_FC_INT2 field values */
+       HDMI_IH_FC_INT2_OVERFLOW_MASK = 0x03,
+       HDMI_IH_FC_INT2_LOW_PRIORITY_OVERFLOW = 0x02,
+       HDMI_IH_FC_INT2_HIGH_PRIORITY_OVERFLOW = 0x01,
+
+/* IH_FC_STAT2 field values */
+       HDMI_IH_FC_STAT2_OVERFLOW_MASK = 0x03,
+       HDMI_IH_FC_STAT2_LOW_PRIORITY_OVERFLOW = 0x02,
+       HDMI_IH_FC_STAT2_HIGH_PRIORITY_OVERFLOW = 0x01,
+
+/* IH_PHY_STAT0 field values */
+       HDMI_IH_PHY_STAT0_RX_SENSE3 = 0x20,
+       HDMI_IH_PHY_STAT0_RX_SENSE2 = 0x10,
+       HDMI_IH_PHY_STAT0_RX_SENSE1 = 0x8,
+       HDMI_IH_PHY_STAT0_RX_SENSE0 = 0x4,
+       HDMI_IH_PHY_STAT0_TX_PHY_LOCK = 0x2,
+       HDMI_IH_PHY_STAT0_HPD = 0x1,
+
+/* IH_MUTE_I2CMPHY_STAT0 field values */
+       HDMI_IH_MUTE_I2CMPHY_STAT0_I2CMPHYDONE = 0x2,
+       HDMI_IH_MUTE_I2CMPHY_STAT0_I2CMPHYERROR = 0x1,
+
+/* IH_AHBDMAAUD_STAT0 field values */
+       HDMI_IH_AHBDMAAUD_STAT0_ERROR = 0x20,
+       HDMI_IH_AHBDMAAUD_STAT0_LOST = 0x10,
+       HDMI_IH_AHBDMAAUD_STAT0_RETRY = 0x08,
+       HDMI_IH_AHBDMAAUD_STAT0_DONE = 0x04,
+       HDMI_IH_AHBDMAAUD_STAT0_BUFFFULL = 0x02,
+       HDMI_IH_AHBDMAAUD_STAT0_BUFFEMPTY = 0x01,
+
+/* IH_MUTE_FC_STAT2 field values */
+       HDMI_IH_MUTE_FC_STAT2_OVERFLOW_MASK = 0x03,
+       HDMI_IH_MUTE_FC_STAT2_LOW_PRIORITY_OVERFLOW = 0x02,
+       HDMI_IH_MUTE_FC_STAT2_HIGH_PRIORITY_OVERFLOW = 0x01,
+
+/* IH_MUTE_AHBDMAAUD_STAT0 field values */
+       HDMI_IH_MUTE_AHBDMAAUD_STAT0_ERROR = 0x20,
+       HDMI_IH_MUTE_AHBDMAAUD_STAT0_LOST = 0x10,
+       HDMI_IH_MUTE_AHBDMAAUD_STAT0_RETRY = 0x08,
+       HDMI_IH_MUTE_AHBDMAAUD_STAT0_DONE = 0x04,
+       HDMI_IH_MUTE_AHBDMAAUD_STAT0_BUFFFULL = 0x02,
+       HDMI_IH_MUTE_AHBDMAAUD_STAT0_BUFFEMPTY = 0x01,
+
+/* IH_MUTE field values */
+       HDMI_IH_MUTE_MUTE_WAKEUP_INTERRUPT = 0x2,
+       HDMI_IH_MUTE_MUTE_ALL_INTERRUPT = 0x1,
+
+/* TX_INVID0 field values */
+       HDMI_TX_INVID0_INTERNAL_DE_GENERATOR_MASK = 0x80,
+       HDMI_TX_INVID0_INTERNAL_DE_GENERATOR_ENABLE = 0x80,
+       HDMI_TX_INVID0_INTERNAL_DE_GENERATOR_DISABLE = 0x00,
+       HDMI_TX_INVID0_VIDEO_MAPPING_MASK = 0x1F,
+       HDMI_TX_INVID0_VIDEO_MAPPING_OFFSET = 0,
+
+/* TX_INSTUFFING field values */
+       HDMI_TX_INSTUFFING_BDBDATA_STUFFING_MASK = 0x4,
+       HDMI_TX_INSTUFFING_BDBDATA_STUFFING_ENABLE = 0x4,
+       HDMI_TX_INSTUFFING_BDBDATA_STUFFING_DISABLE = 0x0,
+       HDMI_TX_INSTUFFING_RCRDATA_STUFFING_MASK = 0x2,
+       HDMI_TX_INSTUFFING_RCRDATA_STUFFING_ENABLE = 0x2,
+       HDMI_TX_INSTUFFING_RCRDATA_STUFFING_DISABLE = 0x0,
+       HDMI_TX_INSTUFFING_GYDATA_STUFFING_MASK = 0x1,
+       HDMI_TX_INSTUFFING_GYDATA_STUFFING_ENABLE = 0x1,
+       HDMI_TX_INSTUFFING_GYDATA_STUFFING_DISABLE = 0x0,
+
+/* VP_PR_CD field values */
+       HDMI_VP_PR_CD_COLOR_DEPTH_MASK = 0xF0,
+       HDMI_VP_PR_CD_COLOR_DEPTH_OFFSET = 4,
+       HDMI_VP_PR_CD_DESIRED_PR_FACTOR_MASK = 0x0F,
+       HDMI_VP_PR_CD_DESIRED_PR_FACTOR_OFFSET = 0,
+
+/* VP_STUFF field values */
+       HDMI_VP_STUFF_IDEFAULT_PHASE_MASK = 0x20,
+       HDMI_VP_STUFF_IDEFAULT_PHASE_OFFSET = 5,
+       HDMI_VP_STUFF_IFIX_PP_TO_LAST_MASK = 0x10,
+       HDMI_VP_STUFF_IFIX_PP_TO_LAST_OFFSET = 4,
+       HDMI_VP_STUFF_ICX_GOTO_P0_ST_MASK = 0x8,
+       HDMI_VP_STUFF_ICX_GOTO_P0_ST_OFFSET = 3,
+       HDMI_VP_STUFF_YCC422_STUFFING_MASK = 0x4,
+       HDMI_VP_STUFF_YCC422_STUFFING_STUFFING_MODE = 0x4,
+       HDMI_VP_STUFF_YCC422_STUFFING_DIRECT_MODE = 0x0,
+       HDMI_VP_STUFF_PP_STUFFING_MASK = 0x2,
+       HDMI_VP_STUFF_PP_STUFFING_STUFFING_MODE = 0x2,
+       HDMI_VP_STUFF_PP_STUFFING_DIRECT_MODE = 0x0,
+       HDMI_VP_STUFF_PR_STUFFING_MASK = 0x1,
+       HDMI_VP_STUFF_PR_STUFFING_STUFFING_MODE = 0x1,
+       HDMI_VP_STUFF_PR_STUFFING_DIRECT_MODE = 0x0,
+
+/* VP_CONF field values */
+       HDMI_VP_CONF_BYPASS_EN_MASK = 0x40,
+       HDMI_VP_CONF_BYPASS_EN_ENABLE = 0x40,
+       HDMI_VP_CONF_BYPASS_EN_DISABLE = 0x00,
+       HDMI_VP_CONF_PP_EN_ENMASK = 0x20,
+       HDMI_VP_CONF_PP_EN_ENABLE = 0x20,
+       HDMI_VP_CONF_PP_EN_DISABLE = 0x00,
+       HDMI_VP_CONF_PR_EN_MASK = 0x10,
+       HDMI_VP_CONF_PR_EN_ENABLE = 0x10,
+       HDMI_VP_CONF_PR_EN_DISABLE = 0x00,
+       HDMI_VP_CONF_YCC422_EN_MASK = 0x8,
+       HDMI_VP_CONF_YCC422_EN_ENABLE = 0x8,
+       HDMI_VP_CONF_YCC422_EN_DISABLE = 0x0,
+       HDMI_VP_CONF_BYPASS_SELECT_MASK = 0x4,
+       HDMI_VP_CONF_BYPASS_SELECT_VID_PACKETIZER = 0x4,
+       HDMI_VP_CONF_BYPASS_SELECT_PIX_REPEATER = 0x0,
+       HDMI_VP_CONF_OUTPUT_SELECTOR_MASK = 0x3,
+       HDMI_VP_CONF_OUTPUT_SELECTOR_BYPASS = 0x3,
+       HDMI_VP_CONF_OUTPUT_SELECTOR_YCC422 = 0x1,
+       HDMI_VP_CONF_OUTPUT_SELECTOR_PP = 0x0,
+
+/* VP_REMAP field values */
+       HDMI_VP_REMAP_MASK = 0x3,
+       HDMI_VP_REMAP_YCC422_24bit = 0x2,
+       HDMI_VP_REMAP_YCC422_20bit = 0x1,
+       HDMI_VP_REMAP_YCC422_16bit = 0x0,
+
+/* FC_INVIDCONF field values */
+       HDMI_FC_INVIDCONF_HDCP_KEEPOUT_MASK = 0x80,
+       HDMI_FC_INVIDCONF_HDCP_KEEPOUT_ACTIVE = 0x80,
+       HDMI_FC_INVIDCONF_HDCP_KEEPOUT_INACTIVE = 0x00,
+       HDMI_FC_INVIDCONF_VSYNC_IN_POLARITY_MASK = 0x40,
+       HDMI_FC_INVIDCONF_VSYNC_IN_POLARITY_ACTIVE_HIGH = 0x40,
+       HDMI_FC_INVIDCONF_VSYNC_IN_POLARITY_ACTIVE_LOW = 0x00,
+       HDMI_FC_INVIDCONF_HSYNC_IN_POLARITY_MASK = 0x20,
+       HDMI_FC_INVIDCONF_HSYNC_IN_POLARITY_ACTIVE_HIGH = 0x20,
+       HDMI_FC_INVIDCONF_HSYNC_IN_POLARITY_ACTIVE_LOW = 0x00,
+       HDMI_FC_INVIDCONF_DE_IN_POLARITY_MASK = 0x10,
+       HDMI_FC_INVIDCONF_DE_IN_POLARITY_ACTIVE_HIGH = 0x10,
+       HDMI_FC_INVIDCONF_DE_IN_POLARITY_ACTIVE_LOW = 0x00,
+       HDMI_FC_INVIDCONF_DVI_MODEZ_MASK = 0x8,
+       HDMI_FC_INVIDCONF_DVI_MODEZ_HDMI_MODE = 0x8,
+       HDMI_FC_INVIDCONF_DVI_MODEZ_DVI_MODE = 0x0,
+       HDMI_FC_INVIDCONF_R_V_BLANK_IN_OSC_MASK = 0x2,
+       HDMI_FC_INVIDCONF_R_V_BLANK_IN_OSC_ACTIVE_HIGH = 0x2,
+       HDMI_FC_INVIDCONF_R_V_BLANK_IN_OSC_ACTIVE_LOW = 0x0,
+       HDMI_FC_INVIDCONF_IN_I_P_MASK = 0x1,
+       HDMI_FC_INVIDCONF_IN_I_P_INTERLACED = 0x1,
+       HDMI_FC_INVIDCONF_IN_I_P_PROGRESSIVE = 0x0,
+
+/* FC_AUDICONF0 field values */
+       HDMI_FC_AUDICONF0_CC_OFFSET = 4,
+       HDMI_FC_AUDICONF0_CC_MASK = 0x70,
+       HDMI_FC_AUDICONF0_CT_OFFSET = 0,
+       HDMI_FC_AUDICONF0_CT_MASK = 0xF,
+
+/* FC_AUDICONF1 field values */
+       HDMI_FC_AUDICONF1_SS_OFFSET = 3,
+       HDMI_FC_AUDICONF1_SS_MASK = 0x18,
+       HDMI_FC_AUDICONF1_SF_OFFSET = 0,
+       HDMI_FC_AUDICONF1_SF_MASK = 0x7,
+
+/* FC_AUDICONF3 field values */
+       HDMI_FC_AUDICONF3_LFEPBL_OFFSET = 5,
+       HDMI_FC_AUDICONF3_LFEPBL_MASK = 0x60,
+       HDMI_FC_AUDICONF3_DM_INH_OFFSET = 4,
+       HDMI_FC_AUDICONF3_DM_INH_MASK = 0x10,
+       HDMI_FC_AUDICONF3_LSV_OFFSET = 0,
+       HDMI_FC_AUDICONF3_LSV_MASK = 0xF,
+
+/* FC_AUDSCHNLS0 field values */
+       HDMI_FC_AUDSCHNLS0_CGMSA_OFFSET = 4,
+       HDMI_FC_AUDSCHNLS0_CGMSA_MASK = 0x30,
+       HDMI_FC_AUDSCHNLS0_COPYRIGHT_OFFSET = 0,
+       HDMI_FC_AUDSCHNLS0_COPYRIGHT_MASK = 0x01,
+
+/* FC_AUDSCHNLS3-6 field values */
+       HDMI_FC_AUDSCHNLS3_OIEC_CH0_OFFSET = 0,
+       HDMI_FC_AUDSCHNLS3_OIEC_CH0_MASK = 0x0f,
+       HDMI_FC_AUDSCHNLS3_OIEC_CH1_OFFSET = 4,
+       HDMI_FC_AUDSCHNLS3_OIEC_CH1_MASK = 0xf0,
+       HDMI_FC_AUDSCHNLS4_OIEC_CH2_OFFSET = 0,
+       HDMI_FC_AUDSCHNLS4_OIEC_CH2_MASK = 0x0f,
+       HDMI_FC_AUDSCHNLS4_OIEC_CH3_OFFSET = 4,
+       HDMI_FC_AUDSCHNLS4_OIEC_CH3_MASK = 0xf0,
+
+       HDMI_FC_AUDSCHNLS5_OIEC_CH0_OFFSET = 0,
+       HDMI_FC_AUDSCHNLS5_OIEC_CH0_MASK = 0x0f,
+       HDMI_FC_AUDSCHNLS5_OIEC_CH1_OFFSET = 4,
+       HDMI_FC_AUDSCHNLS5_OIEC_CH1_MASK = 0xf0,
+       HDMI_FC_AUDSCHNLS6_OIEC_CH2_OFFSET = 0,
+       HDMI_FC_AUDSCHNLS6_OIEC_CH2_MASK = 0x0f,
+       HDMI_FC_AUDSCHNLS6_OIEC_CH3_OFFSET = 4,
+       HDMI_FC_AUDSCHNLS6_OIEC_CH3_MASK = 0xf0,
+
+/* HDMI_FC_AUDSCHNLS7 field values */
+       HDMI_FC_AUDSCHNLS7_ACCURACY_OFFSET = 4,
+       HDMI_FC_AUDSCHNLS7_ACCURACY_MASK = 0x30,
+
+/* HDMI_FC_AUDSCHNLS8 field values */
+       HDMI_FC_AUDSCHNLS8_ORIGSAMPFREQ_MASK = 0xf0,
+       HDMI_FC_AUDSCHNLS8_ORIGSAMPFREQ_OFFSET = 4,
+       HDMI_FC_AUDSCHNLS8_WORDLEGNTH_MASK = 0x0f,
+       HDMI_FC_AUDSCHNLS8_WORDLEGNTH_OFFSET = 0,
+
+/* FC_AUDSCONF field values */
+       HDMI_FC_AUDSCONF_AUD_PACKET_SAMPFIT_MASK = 0xF0,
+       HDMI_FC_AUDSCONF_AUD_PACKET_SAMPFIT_OFFSET = 4,
+       HDMI_FC_AUDSCONF_AUD_PACKET_LAYOUT_MASK = 0x1,
+       HDMI_FC_AUDSCONF_AUD_PACKET_LAYOUT_OFFSET = 0,
+       HDMI_FC_AUDSCONF_AUD_PACKET_LAYOUT_LAYOUT1 = 0x1,
+       HDMI_FC_AUDSCONF_AUD_PACKET_LAYOUT_LAYOUT0 = 0x0,
+
+/* FC_STAT2 field values */
+       HDMI_FC_STAT2_OVERFLOW_MASK = 0x03,
+       HDMI_FC_STAT2_LOW_PRIORITY_OVERFLOW = 0x02,
+       HDMI_FC_STAT2_HIGH_PRIORITY_OVERFLOW = 0x01,
+
+/* FC_INT2 field values */
+       HDMI_FC_INT2_OVERFLOW_MASK = 0x03,
+       HDMI_FC_INT2_LOW_PRIORITY_OVERFLOW = 0x02,
+       HDMI_FC_INT2_HIGH_PRIORITY_OVERFLOW = 0x01,
+
+/* FC_MASK2 field values */
+       HDMI_FC_MASK2_OVERFLOW_MASK = 0x03,
+       HDMI_FC_MASK2_LOW_PRIORITY_OVERFLOW = 0x02,
+       HDMI_FC_MASK2_HIGH_PRIORITY_OVERFLOW = 0x01,
+
+/* FC_PRCONF field values */
+       HDMI_FC_PRCONF_INCOMING_PR_FACTOR_MASK = 0xF0,
+       HDMI_FC_PRCONF_INCOMING_PR_FACTOR_OFFSET = 4,
+       HDMI_FC_PRCONF_OUTPUT_PR_FACTOR_MASK = 0x0F,
+       HDMI_FC_PRCONF_OUTPUT_PR_FACTOR_OFFSET = 0,
+
+/* FC_AVICONF0-FC_AVICONF3 field values */
+       HDMI_FC_AVICONF0_PIX_FMT_MASK = 0x03,
+       HDMI_FC_AVICONF0_PIX_FMT_RGB = 0x00,
+       HDMI_FC_AVICONF0_PIX_FMT_YCBCR422 = 0x01,
+       HDMI_FC_AVICONF0_PIX_FMT_YCBCR444 = 0x02,
+       HDMI_FC_AVICONF0_ACTIVE_FMT_MASK = 0x40,
+       HDMI_FC_AVICONF0_ACTIVE_FMT_INFO_PRESENT = 0x40,
+       HDMI_FC_AVICONF0_ACTIVE_FMT_NO_INFO = 0x00,
+       HDMI_FC_AVICONF0_BAR_DATA_MASK = 0x0C,
+       HDMI_FC_AVICONF0_BAR_DATA_NO_DATA = 0x00,
+       HDMI_FC_AVICONF0_BAR_DATA_VERT_BAR = 0x04,
+       HDMI_FC_AVICONF0_BAR_DATA_HORIZ_BAR = 0x08,
+       HDMI_FC_AVICONF0_BAR_DATA_VERT_HORIZ_BAR = 0x0C,
+       HDMI_FC_AVICONF0_SCAN_INFO_MASK = 0x30,
+       HDMI_FC_AVICONF0_SCAN_INFO_OVERSCAN = 0x10,
+       HDMI_FC_AVICONF0_SCAN_INFO_UNDERSCAN = 0x20,
+       HDMI_FC_AVICONF0_SCAN_INFO_NODATA = 0x00,
+
+       HDMI_FC_AVICONF1_ACTIVE_ASPECT_RATIO_MASK = 0x0F,
+       HDMI_FC_AVICONF1_ACTIVE_ASPECT_RATIO_USE_CODED = 0x08,
+       HDMI_FC_AVICONF1_ACTIVE_ASPECT_RATIO_4_3 = 0x09,
+       HDMI_FC_AVICONF1_ACTIVE_ASPECT_RATIO_16_9 = 0x0A,
+       HDMI_FC_AVICONF1_ACTIVE_ASPECT_RATIO_14_9 = 0x0B,
+       HDMI_FC_AVICONF1_CODED_ASPECT_RATIO_MASK = 0x30,
+       HDMI_FC_AVICONF1_CODED_ASPECT_RATIO_NO_DATA = 0x00,
+       HDMI_FC_AVICONF1_CODED_ASPECT_RATIO_4_3 = 0x10,
+       HDMI_FC_AVICONF1_CODED_ASPECT_RATIO_16_9 = 0x20,
+       HDMI_FC_AVICONF1_COLORIMETRY_MASK = 0xC0,
+       HDMI_FC_AVICONF1_COLORIMETRY_NO_DATA = 0x00,
+       HDMI_FC_AVICONF1_COLORIMETRY_SMPTE = 0x40,
+       HDMI_FC_AVICONF1_COLORIMETRY_ITUR = 0x80,
+       HDMI_FC_AVICONF1_COLORIMETRY_EXTENDED_INFO = 0xC0,
+
+       HDMI_FC_AVICONF2_SCALING_MASK = 0x03,
+       HDMI_FC_AVICONF2_SCALING_NONE = 0x00,
+       HDMI_FC_AVICONF2_SCALING_HORIZ = 0x01,
+       HDMI_FC_AVICONF2_SCALING_VERT = 0x02,
+       HDMI_FC_AVICONF2_SCALING_HORIZ_VERT = 0x03,
+       HDMI_FC_AVICONF2_RGB_QUANT_MASK = 0x0C,
+       HDMI_FC_AVICONF2_RGB_QUANT_DEFAULT = 0x00,
+       HDMI_FC_AVICONF2_RGB_QUANT_LIMITED_RANGE = 0x04,
+       HDMI_FC_AVICONF2_RGB_QUANT_FULL_RANGE = 0x08,
+       HDMI_FC_AVICONF2_EXT_COLORIMETRY_MASK = 0x70,
+       HDMI_FC_AVICONF2_EXT_COLORIMETRY_XVYCC601 = 0x00,
+       HDMI_FC_AVICONF2_EXT_COLORIMETRY_XVYCC709 = 0x10,
+       HDMI_FC_AVICONF2_EXT_COLORIMETRY_SYCC601 = 0x20,
+       HDMI_FC_AVICONF2_EXT_COLORIMETRY_ADOBE_YCC601 = 0x30,
+       HDMI_FC_AVICONF2_EXT_COLORIMETRY_ADOBE_RGB = 0x40,
+       HDMI_FC_AVICONF2_IT_CONTENT_MASK = 0x80,
+       HDMI_FC_AVICONF2_IT_CONTENT_NO_DATA = 0x00,
+       HDMI_FC_AVICONF2_IT_CONTENT_VALID = 0x80,
+
+       HDMI_FC_AVICONF3_IT_CONTENT_TYPE_MASK = 0x03,
+       HDMI_FC_AVICONF3_IT_CONTENT_TYPE_GRAPHICS = 0x00,
+       HDMI_FC_AVICONF3_IT_CONTENT_TYPE_PHOTO = 0x01,
+       HDMI_FC_AVICONF3_IT_CONTENT_TYPE_CINEMA = 0x02,
+       HDMI_FC_AVICONF3_IT_CONTENT_TYPE_GAME = 0x03,
+       HDMI_FC_AVICONF3_QUANT_RANGE_MASK = 0x0C,
+       HDMI_FC_AVICONF3_QUANT_RANGE_LIMITED = 0x00,
+       HDMI_FC_AVICONF3_QUANT_RANGE_FULL = 0x04,
+
+/* FC_DBGFORCE field values */
+       HDMI_FC_DBGFORCE_FORCEAUDIO = 0x10,
+       HDMI_FC_DBGFORCE_FORCEVIDEO = 0x1,
+
+/* PHY_CONF0 field values */
+       HDMI_PHY_CONF0_PDZ_MASK = 0x80,
+       HDMI_PHY_CONF0_PDZ_OFFSET = 7,
+       HDMI_PHY_CONF0_ENTMDS_MASK = 0x40,
+       HDMI_PHY_CONF0_ENTMDS_OFFSET = 6,
+       HDMI_PHY_CONF0_SPARECTRL_MASK = 0x20,
+       HDMI_PHY_CONF0_SPARECTRL_OFFSET = 5,
+       HDMI_PHY_CONF0_GEN2_PDDQ_MASK = 0x10,
+       HDMI_PHY_CONF0_GEN2_PDDQ_OFFSET = 4,
+       HDMI_PHY_CONF0_GEN2_TXPWRON_MASK = 0x8,
+       HDMI_PHY_CONF0_GEN2_TXPWRON_OFFSET = 3,
+       HDMI_PHY_CONF0_GEN2_ENHPDRXSENSE_MASK = 0x4,
+       HDMI_PHY_CONF0_GEN2_ENHPDRXSENSE_OFFSET = 2,
+       HDMI_PHY_CONF0_SELDATAENPOL_MASK = 0x2,
+       HDMI_PHY_CONF0_SELDATAENPOL_OFFSET = 1,
+       HDMI_PHY_CONF0_SELDIPIF_MASK = 0x1,
+       HDMI_PHY_CONF0_SELDIPIF_OFFSET = 0,
+
+/* PHY_TST0 field values */
+       HDMI_PHY_TST0_TSTCLR_MASK = 0x20,
+       HDMI_PHY_TST0_TSTCLR_OFFSET = 5,
+       HDMI_PHY_TST0_TSTEN_MASK = 0x10,
+       HDMI_PHY_TST0_TSTEN_OFFSET = 4,
+       HDMI_PHY_TST0_TSTCLK_MASK = 0x1,
+       HDMI_PHY_TST0_TSTCLK_OFFSET = 0,
+
+/* PHY_STAT0 field values */
+       HDMI_PHY_RX_SENSE3 = 0x80,
+       HDMI_PHY_RX_SENSE2 = 0x40,
+       HDMI_PHY_RX_SENSE1 = 0x20,
+       HDMI_PHY_RX_SENSE0 = 0x10,
+       HDMI_PHY_HPD = 0x02,
+       HDMI_PHY_TX_PHY_LOCK = 0x01,
+
+/* PHY_I2CM_SLAVE_ADDR field values */
+       HDMI_PHY_I2CM_SLAVE_ADDR_PHY_GEN2 = 0x69,
+       HDMI_PHY_I2CM_SLAVE_ADDR_HEAC_PHY = 0x49,
+
+/* PHY_I2CM_OPERATION_ADDR field values */
+       HDMI_PHY_I2CM_OPERATION_ADDR_WRITE = 0x10,
+       HDMI_PHY_I2CM_OPERATION_ADDR_READ = 0x1,
+
+/* HDMI_PHY_I2CM_INT_ADDR */
+       HDMI_PHY_I2CM_INT_ADDR_DONE_POL = 0x08,
+       HDMI_PHY_I2CM_INT_ADDR_DONE_MASK = 0x04,
+
+/* HDMI_PHY_I2CM_CTLINT_ADDR */
+       HDMI_PHY_I2CM_CTLINT_ADDR_NAC_POL = 0x80,
+       HDMI_PHY_I2CM_CTLINT_ADDR_NAC_MASK = 0x40,
+       HDMI_PHY_I2CM_CTLINT_ADDR_ARBITRATION_POL = 0x08,
+       HDMI_PHY_I2CM_CTLINT_ADDR_ARBITRATION_MASK = 0x04,
+
+/* AUD_CTS3 field values */
+       HDMI_AUD_CTS3_N_SHIFT_OFFSET = 5,
+       HDMI_AUD_CTS3_N_SHIFT_MASK = 0xe0,
+       HDMI_AUD_CTS3_N_SHIFT_1 = 0,
+       HDMI_AUD_CTS3_N_SHIFT_16 = 0x20,
+       HDMI_AUD_CTS3_N_SHIFT_32 = 0x40,
+       HDMI_AUD_CTS3_N_SHIFT_64 = 0x60,
+       HDMI_AUD_CTS3_N_SHIFT_128 = 0x80,
+       HDMI_AUD_CTS3_N_SHIFT_256 = 0xa0,
+       /* note that the CTS3 MANUAL bit has been removed
+          from our part. Can't set it, will read as 0. */
+       HDMI_AUD_CTS3_CTS_MANUAL = 0x10,
+       HDMI_AUD_CTS3_AUDCTS19_16_MASK = 0x0f,
+
+/* AHB_DMA_CONF0 field values */
+       HDMI_AHB_DMA_CONF0_SW_FIFO_RST_OFFSET = 7,
+       HDMI_AHB_DMA_CONF0_SW_FIFO_RST_MASK = 0x80,
+       HDMI_AHB_DMA_CONF0_HBR = 0x10,
+       HDMI_AHB_DMA_CONF0_EN_HLOCK_OFFSET = 3,
+       HDMI_AHB_DMA_CONF0_EN_HLOCK_MASK = 0x08,
+       HDMI_AHB_DMA_CONF0_INCR_TYPE_OFFSET = 1,
+       HDMI_AHB_DMA_CONF0_INCR_TYPE_MASK = 0x06,
+       HDMI_AHB_DMA_CONF0_INCR4 = 0x0,
+       HDMI_AHB_DMA_CONF0_INCR8 = 0x2,
+       HDMI_AHB_DMA_CONF0_INCR16 = 0x4,
+       HDMI_AHB_DMA_CONF0_BURST_MODE = 0x1,
+
+/* HDMI_AHB_DMA_START field values */
+       HDMI_AHB_DMA_START_START_OFFSET = 0,
+       HDMI_AHB_DMA_START_START_MASK = 0x01,
+
+/* HDMI_AHB_DMA_STOP field values */
+       HDMI_AHB_DMA_STOP_STOP_OFFSET = 0,
+       HDMI_AHB_DMA_STOP_STOP_MASK = 0x01,
+
+/* AHB_DMA_STAT, AHB_DMA_INT, AHB_DMA_MASK, AHB_DMA_POL field values */
+       HDMI_AHB_DMA_DONE = 0x80,
+       HDMI_AHB_DMA_RETRY_SPLIT = 0x40,
+       HDMI_AHB_DMA_LOSTOWNERSHIP = 0x20,
+       HDMI_AHB_DMA_ERROR = 0x10,
+       HDMI_AHB_DMA_FIFO_THREMPTY = 0x04,
+       HDMI_AHB_DMA_FIFO_FULL = 0x02,
+       HDMI_AHB_DMA_FIFO_EMPTY = 0x01,
+
+/* AHB_DMA_BUFFSTAT, AHB_DMA_BUFFINT,AHB_DMA_BUFFMASK,AHB_DMA_BUFFPOL values */
+       HDMI_AHB_DMA_BUFFSTAT_FULL = 0x02,
+       HDMI_AHB_DMA_BUFFSTAT_EMPTY = 0x01,
+
+/* MC_CLKDIS field values */
+       HDMI_MC_CLKDIS_HDCPCLK_DISABLE = 0x40,
+       HDMI_MC_CLKDIS_CECCLK_DISABLE = 0x20,
+       HDMI_MC_CLKDIS_CSCCLK_DISABLE = 0x10,
+       HDMI_MC_CLKDIS_AUDCLK_DISABLE = 0x8,
+       HDMI_MC_CLKDIS_PREPCLK_DISABLE = 0x4,
+       HDMI_MC_CLKDIS_TMDSCLK_DISABLE = 0x2,
+       HDMI_MC_CLKDIS_PIXELCLK_DISABLE = 0x1,
+
+/* MC_SWRSTZ field values */
+       HDMI_MC_SWRSTZ_TMDSSWRST_REQ = 0x02,
+
+/* MC_FLOWCTRL field values */
+       HDMI_MC_FLOWCTRL_FEED_THROUGH_OFF_MASK = 0x1,
+       HDMI_MC_FLOWCTRL_FEED_THROUGH_OFF_CSC_IN_PATH = 0x1,
+       HDMI_MC_FLOWCTRL_FEED_THROUGH_OFF_CSC_BYPASS = 0x0,
+
+/* MC_PHYRSTZ field values */
+       HDMI_MC_PHYRSTZ_ASSERT = 0x0,
+       HDMI_MC_PHYRSTZ_DEASSERT = 0x1,
+
+/* MC_HEACPHY_RST field values */
+       HDMI_MC_HEACPHY_RST_ASSERT = 0x1,
+       HDMI_MC_HEACPHY_RST_DEASSERT = 0x0,
+
+/* CSC_CFG field values */
+       HDMI_CSC_CFG_INTMODE_MASK = 0x30,
+       HDMI_CSC_CFG_INTMODE_OFFSET = 4,
+       HDMI_CSC_CFG_INTMODE_DISABLE = 0x00,
+       HDMI_CSC_CFG_INTMODE_CHROMA_INT_FORMULA1 = 0x10,
+       HDMI_CSC_CFG_INTMODE_CHROMA_INT_FORMULA2 = 0x20,
+       HDMI_CSC_CFG_DECMODE_MASK = 0x3,
+       HDMI_CSC_CFG_DECMODE_OFFSET = 0,
+       HDMI_CSC_CFG_DECMODE_DISABLE = 0x0,
+       HDMI_CSC_CFG_DECMODE_CHROMA_INT_FORMULA1 = 0x1,
+       HDMI_CSC_CFG_DECMODE_CHROMA_INT_FORMULA2 = 0x2,
+       HDMI_CSC_CFG_DECMODE_CHROMA_INT_FORMULA3 = 0x3,
+
+/* CSC_SCALE field values */
+       HDMI_CSC_SCALE_CSC_COLORDE_PTH_MASK = 0xF0,
+       HDMI_CSC_SCALE_CSC_COLORDE_PTH_24BPP = 0x00,
+       HDMI_CSC_SCALE_CSC_COLORDE_PTH_30BPP = 0x50,
+       HDMI_CSC_SCALE_CSC_COLORDE_PTH_36BPP = 0x60,
+       HDMI_CSC_SCALE_CSC_COLORDE_PTH_48BPP = 0x70,
+       HDMI_CSC_SCALE_CSCSCALE_MASK = 0x03,
+
+/* A_HDCPCFG0 field values */
+       HDMI_A_HDCPCFG0_ELVENA_MASK = 0x80,
+       HDMI_A_HDCPCFG0_ELVENA_ENABLE = 0x80,
+       HDMI_A_HDCPCFG0_ELVENA_DISABLE = 0x00,
+       HDMI_A_HDCPCFG0_I2CFASTMODE_MASK = 0x40,
+       HDMI_A_HDCPCFG0_I2CFASTMODE_ENABLE = 0x40,
+       HDMI_A_HDCPCFG0_I2CFASTMODE_DISABLE = 0x00,
+       HDMI_A_HDCPCFG0_BYPENCRYPTION_MASK = 0x20,
+       HDMI_A_HDCPCFG0_BYPENCRYPTION_ENABLE = 0x20,
+       HDMI_A_HDCPCFG0_BYPENCRYPTION_DISABLE = 0x00,
+       HDMI_A_HDCPCFG0_SYNCRICHECK_MASK = 0x10,
+       HDMI_A_HDCPCFG0_SYNCRICHECK_ENABLE = 0x10,
+       HDMI_A_HDCPCFG0_SYNCRICHECK_DISABLE = 0x00,
+       HDMI_A_HDCPCFG0_AVMUTE_MASK = 0x8,
+       HDMI_A_HDCPCFG0_AVMUTE_ENABLE = 0x8,
+       HDMI_A_HDCPCFG0_AVMUTE_DISABLE = 0x0,
+       HDMI_A_HDCPCFG0_RXDETECT_MASK = 0x4,
+       HDMI_A_HDCPCFG0_RXDETECT_ENABLE = 0x4,
+       HDMI_A_HDCPCFG0_RXDETECT_DISABLE = 0x0,
+       HDMI_A_HDCPCFG0_EN11FEATURE_MASK = 0x2,
+       HDMI_A_HDCPCFG0_EN11FEATURE_ENABLE = 0x2,
+       HDMI_A_HDCPCFG0_EN11FEATURE_DISABLE = 0x0,
+       HDMI_A_HDCPCFG0_HDMIDVI_MASK = 0x1,
+       HDMI_A_HDCPCFG0_HDMIDVI_HDMI = 0x1,
+       HDMI_A_HDCPCFG0_HDMIDVI_DVI = 0x0,
+
+/* A_HDCPCFG1 field values */
+       HDMI_A_HDCPCFG1_DISSHA1CHECK_MASK = 0x8,
+       HDMI_A_HDCPCFG1_DISSHA1CHECK_DISABLE = 0x8,
+       HDMI_A_HDCPCFG1_DISSHA1CHECK_ENABLE = 0x0,
+       HDMI_A_HDCPCFG1_PH2UPSHFTENC_MASK = 0x4,
+       HDMI_A_HDCPCFG1_PH2UPSHFTENC_ENABLE = 0x4,
+       HDMI_A_HDCPCFG1_PH2UPSHFTENC_DISABLE = 0x0,
+       HDMI_A_HDCPCFG1_ENCRYPTIONDISABLE_MASK = 0x2,
+       HDMI_A_HDCPCFG1_ENCRYPTIONDISABLE_DISABLE = 0x2,
+       HDMI_A_HDCPCFG1_ENCRYPTIONDISABLE_ENABLE = 0x0,
+       HDMI_A_HDCPCFG1_SWRESET_MASK = 0x1,
+       HDMI_A_HDCPCFG1_SWRESET_ASSERT = 0x0,
+
+/* A_VIDPOLCFG field values */
+       HDMI_A_VIDPOLCFG_UNENCRYPTCONF_MASK = 0x60,
+       HDMI_A_VIDPOLCFG_UNENCRYPTCONF_OFFSET = 5,
+       HDMI_A_VIDPOLCFG_DATAENPOL_MASK = 0x10,
+       HDMI_A_VIDPOLCFG_DATAENPOL_ACTIVE_HIGH = 0x10,
+       HDMI_A_VIDPOLCFG_DATAENPOL_ACTIVE_LOW = 0x0,
+       HDMI_A_VIDPOLCFG_VSYNCPOL_MASK = 0x8,
+       HDMI_A_VIDPOLCFG_VSYNCPOL_ACTIVE_HIGH = 0x8,
+       HDMI_A_VIDPOLCFG_VSYNCPOL_ACTIVE_LOW = 0x0,
+       HDMI_A_VIDPOLCFG_HSYNCPOL_MASK = 0x2,
+       HDMI_A_VIDPOLCFG_HSYNCPOL_ACTIVE_HIGH = 0x2,
+       HDMI_A_VIDPOLCFG_HSYNCPOL_ACTIVE_LOW = 0x0,
+};
+
+#endif /* __IMX_HDMI_H__ */
index 502a89eb54b51a7f146e9e61e54f03a0051c9b2d..13ddf1c4bb8e45ef5be0ddcdf82d7bad9daf79e9 100644 (file)
@@ -317,17 +317,17 @@ int cirrus_fbdev_init(struct cirrus_device *cdev)
 
        ret = drm_fb_helper_init(cdev->dev, &gfbdev->helper,
                                 cdev->num_crtc, CIRRUSFB_CONN_LIMIT);
-       if (ret) {
-               kfree(gfbdev);
+       if (ret)
+               return ret;
+
+       ret = drm_fb_helper_single_add_all_connectors(&gfbdev->helper);
+       if (ret)
                return ret;
-       }
-       drm_fb_helper_single_add_all_connectors(&gfbdev->helper);
 
        /* disable all the possible outputs/crtcs before entering KMS mode */
        drm_helper_disable_unused_functions(cdev->dev);
-       drm_fb_helper_initial_config(&gfbdev->helper, bpp_sel);
 
-       return 0;
+       return drm_fb_helper_initial_config(&gfbdev->helper, bpp_sel);
 }
 
 void cirrus_fbdev_fini(struct cirrus_device *cdev)
index ff5f034cc40526ba4504d725d06228c662232417..af3f3dfdb49f2b0fe0811fa88d4f5daf6bf0d3d9 100644 (file)
@@ -56,6 +56,11 @@ drm_atomic_state_alloc(struct drm_device *dev)
        if (!state)
                return NULL;
 
+       /* TODO legacy paths should maybe do a better job about
+        * setting this appropriately?
+        */
+       state->allow_modeset = true;
+
        state->num_connector = ACCESS_ONCE(dev->mode_config.num_connector);
 
        state->crtcs = kcalloc(dev->mode_config.num_crtc,
@@ -216,6 +221,70 @@ drm_atomic_get_crtc_state(struct drm_atomic_state *state,
 }
 EXPORT_SYMBOL(drm_atomic_get_crtc_state);
 
+/**
+ * drm_atomic_crtc_set_property - set property on CRTC
+ * @crtc: the drm CRTC to set a property on
+ * @state: the state object to update with the new property value
+ * @property: the property to set
+ * @val: the new property value
+ *
+ * Use this instead of calling crtc->atomic_set_property directly.
+ * This function handles generic/core properties and calls out to
+ * driver's ->atomic_set_property() for driver properties.  To ensure
+ * consistent behavior you must call this function rather than the
+ * driver hook directly.
+ *
+ * RETURNS:
+ * Zero on success, error code on failure
+ */
+int drm_atomic_crtc_set_property(struct drm_crtc *crtc,
+               struct drm_crtc_state *state, struct drm_property *property,
+               uint64_t val)
+{
+       if (crtc->funcs->atomic_set_property)
+               return crtc->funcs->atomic_set_property(crtc, state, property, val);
+       return -EINVAL;
+}
+EXPORT_SYMBOL(drm_atomic_crtc_set_property);
+
+/*
+ * This function handles generic/core properties and calls out to
+ * driver's ->atomic_get_property() for driver properties.  To ensure
+ * consistent behavior you must call this function rather than the
+ * driver hook directly.
+ */
+int drm_atomic_crtc_get_property(struct drm_crtc *crtc,
+               const struct drm_crtc_state *state,
+               struct drm_property *property, uint64_t *val)
+{
+       if (crtc->funcs->atomic_get_property)
+               return crtc->funcs->atomic_get_property(crtc, state, property, val);
+       return -EINVAL;
+}
+
+/**
+ * drm_atomic_crtc_check - check crtc state
+ * @crtc: crtc to check
+ * @state: crtc state to check
+ *
+ * Provides core sanity checks for crtc state.
+ *
+ * RETURNS:
+ * Zero on success, error code on failure
+ */
+static int drm_atomic_crtc_check(struct drm_crtc *crtc,
+               struct drm_crtc_state *state)
+{
+       /* NOTE: we explicitly don't enforce constraints such as primary
+        * layer covering entire screen, since that is something we want
+        * to allow (on hw that supports it).  For hw that does not, it
+        * should be checked in driver's crtc->atomic_check() vfunc.
+        *
+        * TODO: Add generic modeset state checks once we support those.
+        */
+       return 0;
+}
+
 /**
  * drm_atomic_get_plane_state - get plane state
  * @state: global atomic state object
@@ -271,6 +340,183 @@ drm_atomic_get_plane_state(struct drm_atomic_state *state,
 }
 EXPORT_SYMBOL(drm_atomic_get_plane_state);
 
+/**
+ * drm_atomic_plane_set_property - set property on plane
+ * @plane: the drm plane to set a property on
+ * @state: the state object to update with the new property value
+ * @property: the property to set
+ * @val: the new property value
+ *
+ * Use this instead of calling plane->atomic_set_property directly.
+ * This function handles generic/core properties and calls out to
+ * driver's ->atomic_set_property() for driver properties.  To ensure
+ * consistent behavior you must call this function rather than the
+ * driver hook directly.
+ *
+ * RETURNS:
+ * Zero on success, error code on failure
+ */
+int drm_atomic_plane_set_property(struct drm_plane *plane,
+               struct drm_plane_state *state, struct drm_property *property,
+               uint64_t val)
+{
+       struct drm_device *dev = plane->dev;
+       struct drm_mode_config *config = &dev->mode_config;
+
+       if (property == config->prop_fb_id) {
+               struct drm_framebuffer *fb = drm_framebuffer_lookup(dev, val);
+               drm_atomic_set_fb_for_plane(state, fb);
+               if (fb)
+                       drm_framebuffer_unreference(fb);
+       } else if (property == config->prop_crtc_id) {
+               struct drm_crtc *crtc = drm_crtc_find(dev, val);
+               return drm_atomic_set_crtc_for_plane(state, crtc);
+       } else if (property == config->prop_crtc_x) {
+               state->crtc_x = U642I64(val);
+       } else if (property == config->prop_crtc_y) {
+               state->crtc_y = U642I64(val);
+       } else if (property == config->prop_crtc_w) {
+               state->crtc_w = val;
+       } else if (property == config->prop_crtc_h) {
+               state->crtc_h = val;
+       } else if (property == config->prop_src_x) {
+               state->src_x = val;
+       } else if (property == config->prop_src_y) {
+               state->src_y = val;
+       } else if (property == config->prop_src_w) {
+               state->src_w = val;
+       } else if (property == config->prop_src_h) {
+               state->src_h = val;
+       } else if (plane->funcs->atomic_set_property) {
+               return plane->funcs->atomic_set_property(plane, state,
+                               property, val);
+       } else {
+               return -EINVAL;
+       }
+
+       return 0;
+}
+EXPORT_SYMBOL(drm_atomic_plane_set_property);
+
+/*
+ * This function handles generic/core properties and calls out to
+ * driver's ->atomic_get_property() for driver properties.  To ensure
+ * consistent behavior you must call this function rather than the
+ * driver hook directly.
+ */
+static int
+drm_atomic_plane_get_property(struct drm_plane *plane,
+               const struct drm_plane_state *state,
+               struct drm_property *property, uint64_t *val)
+{
+       struct drm_device *dev = plane->dev;
+       struct drm_mode_config *config = &dev->mode_config;
+
+       if (property == config->prop_fb_id) {
+               *val = (state->fb) ? state->fb->base.id : 0;
+       } else if (property == config->prop_crtc_id) {
+               *val = (state->crtc) ? state->crtc->base.id : 0;
+       } else if (property == config->prop_crtc_x) {
+               *val = I642U64(state->crtc_x);
+       } else if (property == config->prop_crtc_y) {
+               *val = I642U64(state->crtc_y);
+       } else if (property == config->prop_crtc_w) {
+               *val = state->crtc_w;
+       } else if (property == config->prop_crtc_h) {
+               *val = state->crtc_h;
+       } else if (property == config->prop_src_x) {
+               *val = state->src_x;
+       } else if (property == config->prop_src_y) {
+               *val = state->src_y;
+       } else if (property == config->prop_src_w) {
+               *val = state->src_w;
+       } else if (property == config->prop_src_h) {
+               *val = state->src_h;
+       } else if (plane->funcs->atomic_get_property) {
+               return plane->funcs->atomic_get_property(plane, state, property, val);
+       } else {
+               return -EINVAL;
+       }
+
+       return 0;
+}
+
+/**
+ * drm_atomic_plane_check - check plane state
+ * @plane: plane to check
+ * @state: plane state to check
+ *
+ * Provides core sanity checks for plane state.
+ *
+ * RETURNS:
+ * Zero on success, error code on failure
+ */
+static int drm_atomic_plane_check(struct drm_plane *plane,
+               struct drm_plane_state *state)
+{
+       unsigned int fb_width, fb_height;
+       unsigned int i;
+
+       /* either *both* CRTC and FB must be set, or neither */
+       if (WARN_ON(state->crtc && !state->fb)) {
+               DRM_DEBUG_KMS("CRTC set but no FB\n");
+               return -EINVAL;
+       } else if (WARN_ON(state->fb && !state->crtc)) {
+               DRM_DEBUG_KMS("FB set but no CRTC\n");
+               return -EINVAL;
+       }
+
+       /* if disabled, we don't care about the rest of the state: */
+       if (!state->crtc)
+               return 0;
+
+       /* Check whether this plane is usable on this CRTC */
+       if (!(plane->possible_crtcs & drm_crtc_mask(state->crtc))) {
+               DRM_DEBUG_KMS("Invalid crtc for plane\n");
+               return -EINVAL;
+       }
+
+       /* Check whether this plane supports the fb pixel format. */
+       for (i = 0; i < plane->format_count; i++)
+               if (state->fb->pixel_format == plane->format_types[i])
+                       break;
+       if (i == plane->format_count) {
+               DRM_DEBUG_KMS("Invalid pixel format %s\n",
+                             drm_get_format_name(state->fb->pixel_format));
+               return -EINVAL;
+       }
+
+       /* Give drivers some help against integer overflows */
+       if (state->crtc_w > INT_MAX ||
+           state->crtc_x > INT_MAX - (int32_t) state->crtc_w ||
+           state->crtc_h > INT_MAX ||
+           state->crtc_y > INT_MAX - (int32_t) state->crtc_h) {
+               DRM_DEBUG_KMS("Invalid CRTC coordinates %ux%u+%d+%d\n",
+                             state->crtc_w, state->crtc_h,
+                             state->crtc_x, state->crtc_y);
+               return -ERANGE;
+       }
+
+       fb_width = state->fb->width << 16;
+       fb_height = state->fb->height << 16;
+
+       /* Make sure source coordinates are inside the fb. */
+       if (state->src_w > fb_width ||
+           state->src_x > fb_width - state->src_w ||
+           state->src_h > fb_height ||
+           state->src_y > fb_height - state->src_h) {
+               DRM_DEBUG_KMS("Invalid source coordinates "
+                             "%u.%06ux%u.%06u+%u.%06u+%u.%06u\n",
+                             state->src_w >> 16, ((state->src_w & 0xffff) * 15625) >> 10,
+                             state->src_h >> 16, ((state->src_h & 0xffff) * 15625) >> 10,
+                             state->src_x >> 16, ((state->src_x & 0xffff) * 15625) >> 10,
+                             state->src_y >> 16, ((state->src_y & 0xffff) * 15625) >> 10);
+               return -ENOSPC;
+       }
+
+       return 0;
+}
+
 /**
  * drm_atomic_get_connector_state - get connector state
  * @state: global atomic state object
@@ -342,10 +588,114 @@ drm_atomic_get_connector_state(struct drm_atomic_state *state,
 }
 EXPORT_SYMBOL(drm_atomic_get_connector_state);
 
+/**
+ * drm_atomic_connector_set_property - set property on connector.
+ * @connector: the drm connector to set a property on
+ * @state: the state object to update with the new property value
+ * @property: the property to set
+ * @val: the new property value
+ *
+ * Use this instead of calling connector->atomic_set_property directly.
+ * This function handles generic/core properties and calls out to
+ * driver's ->atomic_set_property() for driver properties.  To ensure
+ * consistent behavior you must call this function rather than the
+ * driver hook directly.
+ *
+ * RETURNS:
+ * Zero on success, error code on failure
+ */
+int drm_atomic_connector_set_property(struct drm_connector *connector,
+               struct drm_connector_state *state, struct drm_property *property,
+               uint64_t val)
+{
+       struct drm_device *dev = connector->dev;
+       struct drm_mode_config *config = &dev->mode_config;
+
+       if (property == config->prop_crtc_id) {
+               struct drm_crtc *crtc = drm_crtc_find(dev, val);
+               return drm_atomic_set_crtc_for_connector(state, crtc);
+       } else if (property == config->dpms_property) {
+               /* setting DPMS property requires special handling, which
+                * is done in legacy setprop path for us.  Disallow (for
+                * now?) atomic writes to DPMS property:
+                */
+               return -EINVAL;
+       } else if (connector->funcs->atomic_set_property) {
+               return connector->funcs->atomic_set_property(connector,
+                               state, property, val);
+       } else {
+               return -EINVAL;
+       }
+}
+EXPORT_SYMBOL(drm_atomic_connector_set_property);
+
+/*
+ * This function handles generic/core properties and calls out to
+ * driver's ->atomic_get_property() for driver properties.  To ensure
+ * consistent behavior you must call this function rather than the
+ * driver hook directly.
+ */
+static int
+drm_atomic_connector_get_property(struct drm_connector *connector,
+               const struct drm_connector_state *state,
+               struct drm_property *property, uint64_t *val)
+{
+       struct drm_device *dev = connector->dev;
+       struct drm_mode_config *config = &dev->mode_config;
+
+       if (property == config->prop_crtc_id) {
+               *val = (state->crtc) ? state->crtc->base.id : 0;
+       } else if (property == config->dpms_property) {
+               *val = connector->dpms;
+       } else if (connector->funcs->atomic_get_property) {
+               return connector->funcs->atomic_get_property(connector,
+                               state, property, val);
+       } else {
+               return -EINVAL;
+       }
+
+       return 0;
+}
+
+int drm_atomic_get_property(struct drm_mode_object *obj,
+               struct drm_property *property, uint64_t *val)
+{
+       struct drm_device *dev = property->dev;
+       int ret;
+
+       switch (obj->type) {
+       case DRM_MODE_OBJECT_CONNECTOR: {
+               struct drm_connector *connector = obj_to_connector(obj);
+               WARN_ON(!drm_modeset_is_locked(&dev->mode_config.connection_mutex));
+               ret = drm_atomic_connector_get_property(connector,
+                               connector->state, property, val);
+               break;
+       }
+       case DRM_MODE_OBJECT_CRTC: {
+               struct drm_crtc *crtc = obj_to_crtc(obj);
+               WARN_ON(!drm_modeset_is_locked(&crtc->mutex));
+               ret = drm_atomic_crtc_get_property(crtc,
+                               crtc->state, property, val);
+               break;
+       }
+       case DRM_MODE_OBJECT_PLANE: {
+               struct drm_plane *plane = obj_to_plane(obj);
+               WARN_ON(!drm_modeset_is_locked(&plane->mutex));
+               ret = drm_atomic_plane_get_property(plane,
+                               plane->state, property, val);
+               break;
+       }
+       default:
+               ret = -EINVAL;
+               break;
+       }
+
+       return ret;
+}
+
 /**
  * drm_atomic_set_crtc_for_plane - set crtc for plane
- * @state: the incoming atomic state
- * @plane: the plane whose incoming state to update
+ * @plane_state: the plane whose incoming state to update
  * @crtc: crtc to use for the plane
  *
  * Changing the assigned crtc for a plane requires us to grab the lock and state
@@ -358,16 +708,12 @@ EXPORT_SYMBOL(drm_atomic_get_connector_state);
  * sequence must be restarted. All other errors are fatal.
  */
 int
-drm_atomic_set_crtc_for_plane(struct drm_atomic_state *state,
-                             struct drm_plane *plane, struct drm_crtc *crtc)
+drm_atomic_set_crtc_for_plane(struct drm_plane_state *plane_state,
+                             struct drm_crtc *crtc)
 {
-       struct drm_plane_state *plane_state =
-                       drm_atomic_get_plane_state(state, plane);
+       struct drm_plane *plane = plane_state->plane;
        struct drm_crtc_state *crtc_state;
 
-       if (WARN_ON(IS_ERR(plane_state)))
-               return PTR_ERR(plane_state);
-
        if (plane_state->crtc) {
                crtc_state = drm_atomic_get_crtc_state(plane_state->state,
                                                       plane_state->crtc);
@@ -583,14 +929,62 @@ EXPORT_SYMBOL(drm_atomic_legacy_backoff);
  */
 int drm_atomic_check_only(struct drm_atomic_state *state)
 {
-       struct drm_mode_config *config = &state->dev->mode_config;
+       struct drm_device *dev = state->dev;
+       struct drm_mode_config *config = &dev->mode_config;
+       int nplanes = config->num_total_plane;
+       int ncrtcs = config->num_crtc;
+       int i, ret = 0;
 
        DRM_DEBUG_KMS("checking %p\n", state);
 
+       for (i = 0; i < nplanes; i++) {
+               struct drm_plane *plane = state->planes[i];
+
+               if (!plane)
+                       continue;
+
+               ret = drm_atomic_plane_check(plane, state->plane_states[i]);
+               if (ret) {
+                       DRM_DEBUG_KMS("[PLANE:%d] atomic core check failed\n",
+                                     plane->base.id);
+                       return ret;
+               }
+       }
+
+       for (i = 0; i < ncrtcs; i++) {
+               struct drm_crtc *crtc = state->crtcs[i];
+
+               if (!crtc)
+                       continue;
+
+               ret = drm_atomic_crtc_check(crtc, state->crtc_states[i]);
+               if (ret) {
+                       DRM_DEBUG_KMS("[CRTC:%d] atomic core check failed\n",
+                                     crtc->base.id);
+                       return ret;
+               }
+       }
+
        if (config->funcs->atomic_check)
-               return config->funcs->atomic_check(state->dev, state);
-       else
-               return 0;
+               ret = config->funcs->atomic_check(state->dev, state);
+
+       if (!state->allow_modeset) {
+               for (i = 0; i < ncrtcs; i++) {
+                       struct drm_crtc *crtc = state->crtcs[i];
+                       struct drm_crtc_state *crtc_state = state->crtc_states[i];
+
+                       if (!crtc)
+                               continue;
+
+                       if (crtc_state->mode_changed) {
+                               DRM_DEBUG_KMS("[CRTC:%d] requires full modeset\n",
+                                             crtc->base.id);
+                               return -EINVAL;
+                       }
+               }
+       }
+
+       return ret;
 }
 EXPORT_SYMBOL(drm_atomic_check_only);
 
@@ -655,3 +1049,315 @@ int drm_atomic_async_commit(struct drm_atomic_state *state)
        return config->funcs->atomic_commit(state->dev, state, true);
 }
 EXPORT_SYMBOL(drm_atomic_async_commit);
+
+/*
+ * The big monstor ioctl
+ */
+
+static struct drm_pending_vblank_event *create_vblank_event(
+               struct drm_device *dev, struct drm_file *file_priv, uint64_t user_data)
+{
+       struct drm_pending_vblank_event *e = NULL;
+       unsigned long flags;
+
+       spin_lock_irqsave(&dev->event_lock, flags);
+       if (file_priv->event_space < sizeof e->event) {
+               spin_unlock_irqrestore(&dev->event_lock, flags);
+               goto out;
+       }
+       file_priv->event_space -= sizeof e->event;
+       spin_unlock_irqrestore(&dev->event_lock, flags);
+
+       e = kzalloc(sizeof *e, GFP_KERNEL);
+       if (e == NULL) {
+               spin_lock_irqsave(&dev->event_lock, flags);
+               file_priv->event_space += sizeof e->event;
+               spin_unlock_irqrestore(&dev->event_lock, flags);
+               goto out;
+       }
+
+       e->event.base.type = DRM_EVENT_FLIP_COMPLETE;
+       e->event.base.length = sizeof e->event;
+       e->event.user_data = user_data;
+       e->base.event = &e->event.base;
+       e->base.file_priv = file_priv;
+       e->base.destroy = (void (*) (struct drm_pending_event *)) kfree;
+
+out:
+       return e;
+}
+
+static void destroy_vblank_event(struct drm_device *dev,
+               struct drm_file *file_priv, struct drm_pending_vblank_event *e)
+{
+       unsigned long flags;
+
+       spin_lock_irqsave(&dev->event_lock, flags);
+       file_priv->event_space += sizeof e->event;
+       spin_unlock_irqrestore(&dev->event_lock, flags);
+       kfree(e);
+}
+
+static int atomic_set_prop(struct drm_atomic_state *state,
+               struct drm_mode_object *obj, struct drm_property *prop,
+               uint64_t prop_value)
+{
+       struct drm_mode_object *ref;
+       int ret;
+
+       if (!drm_property_change_valid_get(prop, prop_value, &ref))
+               return -EINVAL;
+
+       switch (obj->type) {
+       case DRM_MODE_OBJECT_CONNECTOR: {
+               struct drm_connector *connector = obj_to_connector(obj);
+               struct drm_connector_state *connector_state;
+
+               connector_state = drm_atomic_get_connector_state(state, connector);
+               if (IS_ERR(connector_state)) {
+                       ret = PTR_ERR(connector_state);
+                       break;
+               }
+
+               ret = drm_atomic_connector_set_property(connector,
+                               connector_state, prop, prop_value);
+               break;
+       }
+       case DRM_MODE_OBJECT_CRTC: {
+               struct drm_crtc *crtc = obj_to_crtc(obj);
+               struct drm_crtc_state *crtc_state;
+
+               crtc_state = drm_atomic_get_crtc_state(state, crtc);
+               if (IS_ERR(crtc_state)) {
+                       ret = PTR_ERR(crtc_state);
+                       break;
+               }
+
+               ret = drm_atomic_crtc_set_property(crtc,
+                               crtc_state, prop, prop_value);
+               break;
+       }
+       case DRM_MODE_OBJECT_PLANE: {
+               struct drm_plane *plane = obj_to_plane(obj);
+               struct drm_plane_state *plane_state;
+
+               plane_state = drm_atomic_get_plane_state(state, plane);
+               if (IS_ERR(plane_state)) {
+                       ret = PTR_ERR(plane_state);
+                       break;
+               }
+
+               ret = drm_atomic_plane_set_property(plane,
+                               plane_state, prop, prop_value);
+               break;
+       }
+       default:
+               ret = -EINVAL;
+               break;
+       }
+
+       drm_property_change_valid_put(prop, ref);
+       return ret;
+}
+
+int drm_mode_atomic_ioctl(struct drm_device *dev,
+                         void *data, struct drm_file *file_priv)
+{
+       struct drm_mode_atomic *arg = data;
+       uint32_t __user *objs_ptr = (uint32_t __user *)(unsigned long)(arg->objs_ptr);
+       uint32_t __user *count_props_ptr = (uint32_t __user *)(unsigned long)(arg->count_props_ptr);
+       uint32_t __user *props_ptr = (uint32_t __user *)(unsigned long)(arg->props_ptr);
+       uint64_t __user *prop_values_ptr = (uint64_t __user *)(unsigned long)(arg->prop_values_ptr);
+       unsigned int copied_objs, copied_props;
+       struct drm_atomic_state *state;
+       struct drm_modeset_acquire_ctx ctx;
+       struct drm_plane *plane;
+       unsigned plane_mask = 0;
+       int ret = 0;
+       unsigned int i, j;
+
+       /* disallow for drivers not supporting atomic: */
+       if (!drm_core_check_feature(dev, DRIVER_ATOMIC))
+               return -EINVAL;
+
+       /* disallow for userspace that has not enabled atomic cap (even
+        * though this may be a bit overkill, since legacy userspace
+        * wouldn't know how to call this ioctl)
+        */
+       if (!file_priv->atomic)
+               return -EINVAL;
+
+       if (arg->flags & ~DRM_MODE_ATOMIC_FLAGS)
+               return -EINVAL;
+
+       if (arg->reserved)
+               return -EINVAL;
+
+       if ((arg->flags & DRM_MODE_PAGE_FLIP_ASYNC) &&
+                       !dev->mode_config.async_page_flip)
+               return -EINVAL;
+
+       /* can't test and expect an event at the same time. */
+       if ((arg->flags & DRM_MODE_ATOMIC_TEST_ONLY) &&
+                       (arg->flags & DRM_MODE_PAGE_FLIP_EVENT))
+               return -EINVAL;
+
+       drm_modeset_acquire_init(&ctx, 0);
+
+       state = drm_atomic_state_alloc(dev);
+       if (!state)
+               return -ENOMEM;
+
+       state->acquire_ctx = &ctx;
+       state->allow_modeset = !!(arg->flags & DRM_MODE_ATOMIC_ALLOW_MODESET);
+
+retry:
+       copied_objs = 0;
+       copied_props = 0;
+
+       for (i = 0; i < arg->count_objs; i++) {
+               uint32_t obj_id, count_props;
+               struct drm_mode_object *obj;
+
+               if (get_user(obj_id, objs_ptr + copied_objs)) {
+                       ret = -EFAULT;
+                       goto fail;
+               }
+
+               obj = drm_mode_object_find(dev, obj_id, DRM_MODE_OBJECT_ANY);
+               if (!obj || !obj->properties) {
+                       ret = -ENOENT;
+                       goto fail;
+               }
+
+               if (obj->type == DRM_MODE_OBJECT_PLANE) {
+                       plane = obj_to_plane(obj);
+                       plane_mask |= (1 << drm_plane_index(plane));
+                       plane->old_fb = plane->fb;
+               }
+
+               if (get_user(count_props, count_props_ptr + copied_objs)) {
+                       ret = -EFAULT;
+                       goto fail;
+               }
+
+               copied_objs++;
+
+               for (j = 0; j < count_props; j++) {
+                       uint32_t prop_id;
+                       uint64_t prop_value;
+                       struct drm_property *prop;
+
+                       if (get_user(prop_id, props_ptr + copied_props)) {
+                               ret = -EFAULT;
+                               goto fail;
+                       }
+
+                       prop = drm_property_find(dev, prop_id);
+                       if (!prop) {
+                               ret = -ENOENT;
+                               goto fail;
+                       }
+
+                       if (copy_from_user(&prop_value,
+                                          prop_values_ptr + copied_props,
+                                          sizeof(prop_value))) {
+                               ret = -EFAULT;
+                               goto fail;
+                       }
+
+                       ret = atomic_set_prop(state, obj, prop, prop_value);
+                       if (ret)
+                               goto fail;
+
+                       copied_props++;
+               }
+       }
+
+       if (arg->flags & DRM_MODE_PAGE_FLIP_EVENT) {
+               int ncrtcs = dev->mode_config.num_crtc;
+
+               for (i = 0; i < ncrtcs; i++) {
+                       struct drm_crtc_state *crtc_state = state->crtc_states[i];
+                       struct drm_pending_vblank_event *e;
+
+                       if (!crtc_state)
+                               continue;
+
+                       e = create_vblank_event(dev, file_priv, arg->user_data);
+                       if (!e) {
+                               ret = -ENOMEM;
+                               goto fail;
+                       }
+
+                       crtc_state->event = e;
+               }
+       }
+
+       if (arg->flags & DRM_MODE_ATOMIC_TEST_ONLY) {
+               ret = drm_atomic_check_only(state);
+               /* _check_only() does not free state, unlike _commit() */
+               drm_atomic_state_free(state);
+       } else if (arg->flags & DRM_MODE_ATOMIC_NONBLOCK) {
+               ret = drm_atomic_async_commit(state);
+       } else {
+               ret = drm_atomic_commit(state);
+       }
+
+       /* if succeeded, fixup legacy plane crtc/fb ptrs before dropping
+        * locks (ie. while it is still safe to deref plane->state).  We
+        * need to do this here because the driver entry points cannot
+        * distinguish between legacy and atomic ioctls.
+        */
+       drm_for_each_plane_mask(plane, dev, plane_mask) {
+               if (ret == 0) {
+                       struct drm_framebuffer *new_fb = plane->state->fb;
+                       if (new_fb)
+                               drm_framebuffer_reference(new_fb);
+                       plane->fb = new_fb;
+                       plane->crtc = plane->state->crtc;
+               } else {
+                       plane->old_fb = NULL;
+               }
+               if (plane->old_fb) {
+                       drm_framebuffer_unreference(plane->old_fb);
+                       plane->old_fb = NULL;
+               }
+       }
+
+       drm_modeset_drop_locks(&ctx);
+       drm_modeset_acquire_fini(&ctx);
+
+       return ret;
+
+fail:
+       if (ret == -EDEADLK)
+               goto backoff;
+
+       if (arg->flags & DRM_MODE_PAGE_FLIP_EVENT) {
+               int ncrtcs = dev->mode_config.num_crtc;
+
+               for (i = 0; i < ncrtcs; i++) {
+                       struct drm_crtc_state *crtc_state = state->crtc_states[i];
+
+                       if (!crtc_state)
+                               continue;
+
+                       destroy_vblank_event(dev, file_priv, crtc_state->event);
+                       crtc_state->event = NULL;
+               }
+       }
+
+       drm_atomic_state_free(state);
+
+       drm_modeset_drop_locks(&ctx);
+       drm_modeset_acquire_fini(&ctx);
+
+       return ret;
+
+backoff:
+       drm_atomic_state_clear(state);
+       drm_modeset_backoff(&ctx);
+
+       goto retry;
+}
index bbdbe4721573a92667fe3989bbc1e0be8123bc2b..541ba833ed36edc3e99b6f64dfc3e505d279719f 100644 (file)
@@ -330,7 +330,29 @@ mode_fixup(struct drm_atomic_state *state)
        return 0;
 }
 
-static int
+/**
+ * drm_atomic_helper_check - validate state object for modeset changes
+ * @dev: DRM device
+ * @state: the driver state object
+ *
+ * Check the state object to see if the requested state is physically possible.
+ * This does all the crtc and connector related computations for an atomic
+ * update. It computes and updates crtc_state->mode_changed, adds any additional
+ * connectors needed for full modesets and calls down into ->mode_fixup
+ * functions of the driver backend.
+ *
+ * IMPORTANT:
+ *
+ * Drivers which update ->mode_changed (e.g. in their ->atomic_check hooks if a
+ * plane update can't be done without a full modeset) _must_ call this function
+ * afterwards after that change. It is permitted to call this function multiple
+ * times for the same update, e.g. when the ->atomic_check functions depend upon
+ * the adjusted dotclock for fifo space allocation and watermark computation.
+ *
+ * RETURNS
+ * Zero for success or -errno
+ */
+int
 drm_atomic_helper_check_modeset(struct drm_device *dev,
                                struct drm_atomic_state *state)
 {
@@ -406,23 +428,23 @@ drm_atomic_helper_check_modeset(struct drm_device *dev,
 
        return mode_fixup(state);
 }
+EXPORT_SYMBOL(drm_atomic_helper_check_modeset);
 
 /**
- * drm_atomic_helper_check - validate state object
+ * drm_atomic_helper_check - validate state object for modeset changes
  * @dev: DRM device
  * @state: the driver state object
  *
  * Check the state object to see if the requested state is physically possible.
- * Only crtcs and planes have check callbacks, so for any additional (global)
- * checking that a driver needs it can simply wrap that around this function.
- * Drivers without such needs can directly use this as their ->atomic_check()
- * callback.
+ * This does all the plane update related checks using by calling into the
+ * ->atomic_check hooks provided by the driver.
  *
  * RETURNS
  * Zero for success or -errno
  */
-int drm_atomic_helper_check(struct drm_device *dev,
-                           struct drm_atomic_state *state)
+int
+drm_atomic_helper_check_planes(struct drm_device *dev,
+                              struct drm_atomic_state *state)
 {
        int nplanes = dev->mode_config.num_total_plane;
        int ncrtcs = dev->mode_config.num_crtc;
@@ -445,7 +467,7 @@ int drm_atomic_helper_check(struct drm_device *dev,
 
                ret = funcs->atomic_check(plane, plane_state);
                if (ret) {
-                       DRM_DEBUG_KMS("[PLANE:%d] atomic check failed\n",
+                       DRM_DEBUG_KMS("[PLANE:%d] atomic driver check failed\n",
                                      plane->base.id);
                        return ret;
                }
@@ -465,16 +487,49 @@ int drm_atomic_helper_check(struct drm_device *dev,
 
                ret = funcs->atomic_check(crtc, state->crtc_states[i]);
                if (ret) {
-                       DRM_DEBUG_KMS("[CRTC:%d] atomic check failed\n",
+                       DRM_DEBUG_KMS("[CRTC:%d] atomic driver check failed\n",
                                      crtc->base.id);
                        return ret;
                }
        }
 
+       return ret;
+}
+EXPORT_SYMBOL(drm_atomic_helper_check_planes);
+
+/**
+ * drm_atomic_helper_check - validate state object
+ * @dev: DRM device
+ * @state: the driver state object
+ *
+ * Check the state object to see if the requested state is physically possible.
+ * Only crtcs and planes have check callbacks, so for any additional (global)
+ * checking that a driver needs it can simply wrap that around this function.
+ * Drivers without such needs can directly use this as their ->atomic_check()
+ * callback.
+ *
+ * This just wraps the two parts of the state checking for planes and modeset
+ * state in the default order: First it calls drm_atomic_helper_check_modeset()
+ * and then drm_atomic_helper_check_planes(). The assumption is that the
+ * ->atomic_check functions depend upon an updated adjusted_mode.clock to
+ * e.g. properly compute watermarks.
+ *
+ * RETURNS
+ * Zero for success or -errno
+ */
+int drm_atomic_helper_check(struct drm_device *dev,
+                           struct drm_atomic_state *state)
+{
+       int ret;
+
        ret = drm_atomic_helper_check_modeset(dev, state);
        if (ret)
                return ret;
 
+       ret = drm_atomic_helper_check_planes(dev, state);
+       if (ret)
+               return ret;
+
        return ret;
 }
 EXPORT_SYMBOL(drm_atomic_helper_check);
@@ -1222,7 +1277,7 @@ retry:
                goto fail;
        }
 
-       ret = drm_atomic_set_crtc_for_plane(state, plane, crtc);
+       ret = drm_atomic_set_crtc_for_plane(plane_state, crtc);
        if (ret != 0)
                goto fail;
        drm_atomic_set_fb_for_plane(plane_state, fb);
@@ -1301,7 +1356,7 @@ retry:
                goto fail;
        }
 
-       ret = drm_atomic_set_crtc_for_plane(state, plane, NULL);
+       ret = drm_atomic_set_crtc_for_plane(plane_state, NULL);
        if (ret != 0)
                goto fail;
        drm_atomic_set_fb_for_plane(plane_state, NULL);
@@ -1464,7 +1519,7 @@ retry:
 
                crtc_state->enable = false;
 
-               ret = drm_atomic_set_crtc_for_plane(state, crtc->primary, NULL);
+               ret = drm_atomic_set_crtc_for_plane(primary_state, NULL);
                if (ret != 0)
                        goto fail;
 
@@ -1479,7 +1534,7 @@ retry:
        crtc_state->enable = true;
        drm_mode_copy(&crtc_state->mode, set->mode);
 
-       ret = drm_atomic_set_crtc_for_plane(state, crtc->primary, crtc);
+       ret = drm_atomic_set_crtc_for_plane(primary_state, crtc);
        if (ret != 0)
                goto fail;
        drm_atomic_set_fb_for_plane(primary_state, set->fb);
@@ -1558,8 +1613,8 @@ retry:
                goto fail;
        }
 
-       ret = crtc->funcs->atomic_set_property(crtc, crtc_state,
-                                              property, val);
+       ret = drm_atomic_crtc_set_property(crtc, crtc_state,
+                       property, val);
        if (ret)
                goto fail;
 
@@ -1617,8 +1672,8 @@ retry:
                goto fail;
        }
 
-       ret = plane->funcs->atomic_set_property(plane, plane_state,
-                                              property, val);
+       ret = drm_atomic_plane_set_property(plane, plane_state,
+                       property, val);
        if (ret)
                goto fail;
 
@@ -1676,8 +1731,8 @@ retry:
                goto fail;
        }
 
-       ret = connector->funcs->atomic_set_property(connector, connector_state,
-                                              property, val);
+       ret = drm_atomic_connector_set_property(connector, connector_state,
+                       property, val);
        if (ret)
                goto fail;
 
@@ -1751,7 +1806,7 @@ retry:
                goto fail;
        }
 
-       ret = drm_atomic_set_crtc_for_plane(state, plane, crtc);
+       ret = drm_atomic_set_crtc_for_plane(plane_state, crtc);
        if (ret != 0)
                goto fail;
        drm_atomic_set_fb_for_plane(plane_state, fb);
@@ -1814,6 +1869,9 @@ void drm_atomic_helper_crtc_reset(struct drm_crtc *crtc)
 {
        kfree(crtc->state);
        crtc->state = kzalloc(sizeof(*crtc->state), GFP_KERNEL);
+
+       if (crtc->state)
+               crtc->state->crtc = crtc;
 }
 EXPORT_SYMBOL(drm_atomic_helper_crtc_reset);
 
@@ -1873,6 +1931,9 @@ void drm_atomic_helper_plane_reset(struct drm_plane *plane)
 
        kfree(plane->state);
        plane->state = kzalloc(sizeof(*plane->state), GFP_KERNEL);
+
+       if (plane->state)
+               plane->state->plane = plane;
 }
 EXPORT_SYMBOL(drm_atomic_helper_plane_reset);
 
@@ -1930,6 +1991,9 @@ void drm_atomic_helper_connector_reset(struct drm_connector *connector)
 {
        kfree(connector->state);
        connector->state = kzalloc(sizeof(*connector->state), GFP_KERNEL);
+
+       if (connector->state)
+               connector->state->connector = connector;
 }
 EXPORT_SYMBOL(drm_atomic_helper_connector_reset);
 
index a6b690626a6b0563e026e9217859cc2505aadb76..9a62d7a53553d3a54f45d0ef0cbc1291de84fc08 100644 (file)
@@ -32,6 +32,7 @@
 #include <drm/drmP.h>
 
 #if defined(CONFIG_X86)
+#include <asm/smp.h>
 
 /*
  * clflushopt is an unordered instruction which needs fencing with mfence or
@@ -64,12 +65,6 @@ static void drm_cache_flush_clflush(struct page *pages[],
                drm_clflush_page(*pages++);
        mb();
 }
-
-static void
-drm_clflush_ipi_handler(void *null)
-{
-       wbinvd();
-}
 #endif
 
 void
@@ -82,7 +77,7 @@ drm_clflush_pages(struct page *pages[], unsigned long num_pages)
                return;
        }
 
-       if (on_each_cpu(drm_clflush_ipi_handler, NULL, 1) != 0)
+       if (wbinvd_on_all_cpus())
                printk(KERN_ERR "Timed out waiting for cache flush.\n");
 
 #elif defined(__powerpc__)
@@ -121,7 +116,7 @@ drm_clflush_sg(struct sg_table *st)
                return;
        }
 
-       if (on_each_cpu(drm_clflush_ipi_handler, NULL, 1) != 0)
+       if (wbinvd_on_all_cpus())
                printk(KERN_ERR "Timed out waiting for cache flush.\n");
 #else
        printk(KERN_ERR "Architecture has no drm_cache.c support\n");
@@ -144,7 +139,7 @@ drm_clflush_virt_range(void *addr, unsigned long length)
                return;
        }
 
-       if (on_each_cpu(drm_clflush_ipi_handler, NULL, 1) != 0)
+       if (wbinvd_on_all_cpus())
                printk(KERN_ERR "Timed out waiting for cache flush.\n");
 #else
        printk(KERN_ERR "Architecture has no drm_cache.c support\n");
index 4d0baa43de585685a34537c64c0591b0d30f168f..df90048de92e033fba88fe482662e64135deada7 100644 (file)
@@ -38,6 +38,7 @@
 #include <drm/drm_edid.h>
 #include <drm/drm_fourcc.h>
 #include <drm/drm_modeset_lock.h>
+#include <drm/drm_atomic.h>
 
 #include "drm_crtc_internal.h"
 #include "drm_internal.h"
@@ -61,8 +62,8 @@ static struct drm_framebuffer *add_framebuffer_internal(struct drm_device *dev,
 /*
  * Global properties
  */
-static const struct drm_prop_enum_list drm_dpms_enum_list[] =
-{      { DRM_MODE_DPMS_ON, "On" },
+static const struct drm_prop_enum_list drm_dpms_enum_list[] = {
+       { DRM_MODE_DPMS_ON, "On" },
        { DRM_MODE_DPMS_STANDBY, "Standby" },
        { DRM_MODE_DPMS_SUSPEND, "Suspend" },
        { DRM_MODE_DPMS_OFF, "Off" }
@@ -70,8 +71,7 @@ static const struct drm_prop_enum_list drm_dpms_enum_list[] =
 
 DRM_ENUM_NAME_FN(drm_get_dpms_name, drm_dpms_enum_list)
 
-static const struct drm_prop_enum_list drm_plane_type_enum_list[] =
-{
+static const struct drm_prop_enum_list drm_plane_type_enum_list[] = {
        { DRM_PLANE_TYPE_OVERLAY, "Overlay" },
        { DRM_PLANE_TYPE_PRIMARY, "Primary" },
        { DRM_PLANE_TYPE_CURSOR, "Cursor" },
@@ -80,8 +80,7 @@ static const struct drm_prop_enum_list drm_plane_type_enum_list[] =
 /*
  * Optional properties
  */
-static const struct drm_prop_enum_list drm_scaling_mode_enum_list[] =
-{
+static const struct drm_prop_enum_list drm_scaling_mode_enum_list[] = {
        { DRM_MODE_SCALE_NONE, "None" },
        { DRM_MODE_SCALE_FULLSCREEN, "Full" },
        { DRM_MODE_SCALE_CENTER, "Center" },
@@ -97,8 +96,7 @@ static const struct drm_prop_enum_list drm_aspect_ratio_enum_list[] = {
 /*
  * Non-global properties, but "required" for certain connectors.
  */
-static const struct drm_prop_enum_list drm_dvi_i_select_enum_list[] =
-{
+static const struct drm_prop_enum_list drm_dvi_i_select_enum_list[] = {
        { DRM_MODE_SUBCONNECTOR_Automatic, "Automatic" }, /* DVI-I and TV-out */
        { DRM_MODE_SUBCONNECTOR_DVID,      "DVI-D"     }, /* DVI-I  */
        { DRM_MODE_SUBCONNECTOR_DVIA,      "DVI-A"     }, /* DVI-I  */
@@ -106,8 +104,7 @@ static const struct drm_prop_enum_list drm_dvi_i_select_enum_list[] =
 
 DRM_ENUM_NAME_FN(drm_get_dvi_i_select_name, drm_dvi_i_select_enum_list)
 
-static const struct drm_prop_enum_list drm_dvi_i_subconnector_enum_list[] =
-{
+static const struct drm_prop_enum_list drm_dvi_i_subconnector_enum_list[] = {
        { DRM_MODE_SUBCONNECTOR_Unknown,   "Unknown"   }, /* DVI-I and TV-out */
        { DRM_MODE_SUBCONNECTOR_DVID,      "DVI-D"     }, /* DVI-I  */
        { DRM_MODE_SUBCONNECTOR_DVIA,      "DVI-A"     }, /* DVI-I  */
@@ -116,8 +113,7 @@ static const struct drm_prop_enum_list drm_dvi_i_subconnector_enum_list[] =
 DRM_ENUM_NAME_FN(drm_get_dvi_i_subconnector_name,
                 drm_dvi_i_subconnector_enum_list)
 
-static const struct drm_prop_enum_list drm_tv_select_enum_list[] =
-{
+static const struct drm_prop_enum_list drm_tv_select_enum_list[] = {
        { DRM_MODE_SUBCONNECTOR_Automatic, "Automatic" }, /* DVI-I and TV-out */
        { DRM_MODE_SUBCONNECTOR_Composite, "Composite" }, /* TV-out */
        { DRM_MODE_SUBCONNECTOR_SVIDEO,    "SVIDEO"    }, /* TV-out */
@@ -127,8 +123,7 @@ static const struct drm_prop_enum_list drm_tv_select_enum_list[] =
 
 DRM_ENUM_NAME_FN(drm_get_tv_select_name, drm_tv_select_enum_list)
 
-static const struct drm_prop_enum_list drm_tv_subconnector_enum_list[] =
-{
+static const struct drm_prop_enum_list drm_tv_subconnector_enum_list[] = {
        { DRM_MODE_SUBCONNECTOR_Unknown,   "Unknown"   }, /* DVI-I and TV-out */
        { DRM_MODE_SUBCONNECTOR_Composite, "Composite" }, /* TV-out */
        { DRM_MODE_SUBCONNECTOR_SVIDEO,    "SVIDEO"    }, /* TV-out */
@@ -154,8 +149,8 @@ struct drm_conn_prop_enum_list {
 /*
  * Connector and encoder types.
  */
-static struct drm_conn_prop_enum_list drm_connector_enum_list[] =
-{      { DRM_MODE_CONNECTOR_Unknown, "Unknown" },
+static struct drm_conn_prop_enum_list drm_connector_enum_list[] = {
+       { DRM_MODE_CONNECTOR_Unknown, "Unknown" },
        { DRM_MODE_CONNECTOR_VGA, "VGA" },
        { DRM_MODE_CONNECTOR_DVII, "DVI-I" },
        { DRM_MODE_CONNECTOR_DVID, "DVI-D" },
@@ -174,8 +169,8 @@ static struct drm_conn_prop_enum_list drm_connector_enum_list[] =
        { DRM_MODE_CONNECTOR_DSI, "DSI" },
 };
 
-static const struct drm_prop_enum_list drm_encoder_enum_list[] =
-{      { DRM_MODE_ENCODER_NONE, "None" },
+static const struct drm_prop_enum_list drm_encoder_enum_list[] = {
+       { DRM_MODE_ENCODER_NONE, "None" },
        { DRM_MODE_ENCODER_DAC, "DAC" },
        { DRM_MODE_ENCODER_TMDS, "TMDS" },
        { DRM_MODE_ENCODER_LVDS, "LVDS" },
@@ -185,8 +180,7 @@ static const struct drm_prop_enum_list drm_encoder_enum_list[] =
        { DRM_MODE_ENCODER_DPMST, "DP MST" },
 };
 
-static const struct drm_prop_enum_list drm_subpixel_enum_list[] =
-{
+static const struct drm_prop_enum_list drm_subpixel_enum_list[] = {
        { SubPixelUnknown, "Unknown" },
        { SubPixelHorizontalRGB, "Horizontal RGB" },
        { SubPixelHorizontalBGR, "Horizontal BGR" },
@@ -767,6 +761,40 @@ static void drm_mode_remove(struct drm_connector *connector,
        drm_mode_destroy(connector->dev, mode);
 }
 
+/**
+ * drm_display_info_set_bus_formats - set the supported bus formats
+ * @info: display info to store bus formats in
+ * @fmts: array containing the supported bus formats
+ * @nfmts: the number of entries in the fmts array
+ *
+ * Store the supported bus formats in display info structure.
+ * See MEDIA_BUS_FMT_* definitions in include/uapi/linux/media-bus-format.h for
+ * a full list of available formats.
+ */
+int drm_display_info_set_bus_formats(struct drm_display_info *info,
+                                    const u32 *formats,
+                                    unsigned int num_formats)
+{
+       u32 *fmts = NULL;
+
+       if (!formats && num_formats)
+               return -EINVAL;
+
+       if (formats && num_formats) {
+               fmts = kmemdup(formats, sizeof(*formats) * num_formats,
+                              GFP_KERNEL);
+               if (!formats)
+                       return -ENOMEM;
+       }
+
+       kfree(info->bus_formats);
+       info->bus_formats = fmts;
+       info->num_bus_formats = num_formats;
+
+       return 0;
+}
+EXPORT_SYMBOL(drm_display_info_set_bus_formats);
+
 /**
  * drm_connector_get_cmdline_mode - reads the user's cmdline mode
  * @connector: connector to quwery
@@ -837,6 +865,7 @@ int drm_connector_init(struct drm_device *dev,
                       const struct drm_connector_funcs *funcs,
                       int connector_type)
 {
+       struct drm_mode_config *config = &dev->mode_config;
        int ret;
        struct ida *connector_ida =
                &drm_connector_enum_list[connector_type].ida;
@@ -875,16 +904,20 @@ int drm_connector_init(struct drm_device *dev,
 
        /* We should add connectors at the end to avoid upsetting the connector
         * index too much. */
-       list_add_tail(&connector->head, &dev->mode_config.connector_list);
-       dev->mode_config.num_connector++;
+       list_add_tail(&connector->head, &config->connector_list);
+       config->num_connector++;
 
        if (connector_type != DRM_MODE_CONNECTOR_VIRTUAL)
                drm_object_attach_property(&connector->base,
-                                             dev->mode_config.edid_property,
+                                             config->edid_property,
                                              0);
 
        drm_object_attach_property(&connector->base,
-                                     dev->mode_config.dpms_property, 0);
+                                     config->dpms_property, 0);
+
+       if (drm_core_check_feature(dev, DRIVER_ATOMIC)) {
+               drm_object_attach_property(&connector->base, config->prop_crtc_id, 0);
+       }
 
        connector->debugfs_entry = NULL;
 
@@ -924,6 +957,7 @@ void drm_connector_cleanup(struct drm_connector *connector)
        ida_remove(&drm_connector_enum_list[connector->connector_type].ida,
                   connector->connector_type_id);
 
+       kfree(connector->display_info.bus_formats);
        drm_mode_object_put(dev, &connector->base);
        kfree(connector->name);
        connector->name = NULL;
@@ -1142,6 +1176,7 @@ EXPORT_SYMBOL(drm_encoder_init);
 void drm_encoder_cleanup(struct drm_encoder *encoder)
 {
        struct drm_device *dev = encoder->dev;
+
        drm_modeset_lock_all(dev);
        drm_mode_object_put(dev, &encoder->base);
        kfree(encoder->name);
@@ -1174,6 +1209,7 @@ int drm_universal_plane_init(struct drm_device *dev, struct drm_plane *plane,
                             const uint32_t *formats, uint32_t format_count,
                             enum drm_plane_type type)
 {
+       struct drm_mode_config *config = &dev->mode_config;
        int ret;
 
        ret = drm_mode_object_get(dev, &plane->base, DRM_MODE_OBJECT_PLANE);
@@ -1185,8 +1221,8 @@ int drm_universal_plane_init(struct drm_device *dev, struct drm_plane *plane,
        plane->base.properties = &plane->properties;
        plane->dev = dev;
        plane->funcs = funcs;
-       plane->format_types = kmalloc(sizeof(uint32_t) * format_count,
-                                     GFP_KERNEL);
+       plane->format_types = kmalloc_array(format_count, sizeof(uint32_t),
+                                           GFP_KERNEL);
        if (!plane->format_types) {
                DRM_DEBUG_KMS("out of memory when allocating plane\n");
                drm_mode_object_put(dev, &plane->base);
@@ -1198,15 +1234,28 @@ int drm_universal_plane_init(struct drm_device *dev, struct drm_plane *plane,
        plane->possible_crtcs = possible_crtcs;
        plane->type = type;
 
-       list_add_tail(&plane->head, &dev->mode_config.plane_list);
-       dev->mode_config.num_total_plane++;
+       list_add_tail(&plane->head, &config->plane_list);
+       config->num_total_plane++;
        if (plane->type == DRM_PLANE_TYPE_OVERLAY)
-               dev->mode_config.num_overlay_plane++;
+               config->num_overlay_plane++;
 
        drm_object_attach_property(&plane->base,
-                                  dev->mode_config.plane_type_property,
+                                  config->plane_type_property,
                                   plane->type);
 
+       if (drm_core_check_feature(dev, DRIVER_ATOMIC)) {
+               drm_object_attach_property(&plane->base, config->prop_fb_id, 0);
+               drm_object_attach_property(&plane->base, config->prop_crtc_id, 0);
+               drm_object_attach_property(&plane->base, config->prop_crtc_x, 0);
+               drm_object_attach_property(&plane->base, config->prop_crtc_y, 0);
+               drm_object_attach_property(&plane->base, config->prop_crtc_w, 0);
+               drm_object_attach_property(&plane->base, config->prop_crtc_h, 0);
+               drm_object_attach_property(&plane->base, config->prop_src_x, 0);
+               drm_object_attach_property(&plane->base, config->prop_src_y, 0);
+               drm_object_attach_property(&plane->base, config->prop_src_w, 0);
+               drm_object_attach_property(&plane->base, config->prop_src_h, 0);
+       }
+
        return 0;
 }
 EXPORT_SYMBOL(drm_universal_plane_init);
@@ -1328,50 +1377,109 @@ void drm_plane_force_disable(struct drm_plane *plane)
 }
 EXPORT_SYMBOL(drm_plane_force_disable);
 
-static int drm_mode_create_standard_connector_properties(struct drm_device *dev)
+static int drm_mode_create_standard_properties(struct drm_device *dev)
 {
-       struct drm_property *edid;
-       struct drm_property *dpms;
-       struct drm_property *dev_path;
+       struct drm_property *prop;
 
        /*
         * Standard properties (apply to all connectors)
         */
-       edid = drm_property_create(dev, DRM_MODE_PROP_BLOB |
+       prop = drm_property_create(dev, DRM_MODE_PROP_BLOB |
                                   DRM_MODE_PROP_IMMUTABLE,
                                   "EDID", 0);
-       dev->mode_config.edid_property = edid;
+       if (!prop)
+               return -ENOMEM;
+       dev->mode_config.edid_property = prop;
 
-       dpms = drm_property_create_enum(dev, 0,
+       prop = drm_property_create_enum(dev, 0,
                                   "DPMS", drm_dpms_enum_list,
                                   ARRAY_SIZE(drm_dpms_enum_list));
-       dev->mode_config.dpms_property = dpms;
-
-       dev_path = drm_property_create(dev,
-                                      DRM_MODE_PROP_BLOB |
-                                      DRM_MODE_PROP_IMMUTABLE,
-                                      "PATH", 0);
-       dev->mode_config.path_property = dev_path;
-
-       dev->mode_config.tile_property = drm_property_create(dev,
-                                                            DRM_MODE_PROP_BLOB |
-                                                            DRM_MODE_PROP_IMMUTABLE,
-                                                            "TILE", 0);
+       if (!prop)
+               return -ENOMEM;
+       dev->mode_config.dpms_property = prop;
 
-       return 0;
-}
+       prop = drm_property_create(dev,
+                                  DRM_MODE_PROP_BLOB |
+                                  DRM_MODE_PROP_IMMUTABLE,
+                                  "PATH", 0);
+       if (!prop)
+               return -ENOMEM;
+       dev->mode_config.path_property = prop;
 
-static int drm_mode_create_standard_plane_properties(struct drm_device *dev)
-{
-       struct drm_property *type;
+       prop = drm_property_create(dev,
+                                  DRM_MODE_PROP_BLOB |
+                                  DRM_MODE_PROP_IMMUTABLE,
+                                  "TILE", 0);
+       if (!prop)
+               return -ENOMEM;
+       dev->mode_config.tile_property = prop;
 
-       /*
-        * Standard properties (apply to all planes)
-        */
-       type = drm_property_create_enum(dev, DRM_MODE_PROP_IMMUTABLE,
+       prop = drm_property_create_enum(dev, DRM_MODE_PROP_IMMUTABLE,
                                        "type", drm_plane_type_enum_list,
                                        ARRAY_SIZE(drm_plane_type_enum_list));
-       dev->mode_config.plane_type_property = type;
+       if (!prop)
+               return -ENOMEM;
+       dev->mode_config.plane_type_property = prop;
+
+       prop = drm_property_create_range(dev, DRM_MODE_PROP_ATOMIC,
+                       "SRC_X", 0, UINT_MAX);
+       if (!prop)
+               return -ENOMEM;
+       dev->mode_config.prop_src_x = prop;
+
+       prop = drm_property_create_range(dev, DRM_MODE_PROP_ATOMIC,
+                       "SRC_Y", 0, UINT_MAX);
+       if (!prop)
+               return -ENOMEM;
+       dev->mode_config.prop_src_y = prop;
+
+       prop = drm_property_create_range(dev, DRM_MODE_PROP_ATOMIC,
+                       "SRC_W", 0, UINT_MAX);
+       if (!prop)
+               return -ENOMEM;
+       dev->mode_config.prop_src_w = prop;
+
+       prop = drm_property_create_range(dev, DRM_MODE_PROP_ATOMIC,
+                       "SRC_H", 0, UINT_MAX);
+       if (!prop)
+               return -ENOMEM;
+       dev->mode_config.prop_src_h = prop;
+
+       prop = drm_property_create_signed_range(dev, DRM_MODE_PROP_ATOMIC,
+                       "CRTC_X", INT_MIN, INT_MAX);
+       if (!prop)
+               return -ENOMEM;
+       dev->mode_config.prop_crtc_x = prop;
+
+       prop = drm_property_create_signed_range(dev, DRM_MODE_PROP_ATOMIC,
+                       "CRTC_Y", INT_MIN, INT_MAX);
+       if (!prop)
+               return -ENOMEM;
+       dev->mode_config.prop_crtc_y = prop;
+
+       prop = drm_property_create_range(dev, DRM_MODE_PROP_ATOMIC,
+                       "CRTC_W", 0, INT_MAX);
+       if (!prop)
+               return -ENOMEM;
+       dev->mode_config.prop_crtc_w = prop;
+
+       prop = drm_property_create_range(dev, DRM_MODE_PROP_ATOMIC,
+                       "CRTC_H", 0, INT_MAX);
+       if (!prop)
+               return -ENOMEM;
+       dev->mode_config.prop_crtc_h = prop;
+
+       prop = drm_property_create_object(dev, DRM_MODE_PROP_ATOMIC,
+                       "FB_ID", DRM_MODE_OBJECT_FB);
+       if (!prop)
+               return -ENOMEM;
+       dev->mode_config.prop_fb_id = prop;
+
+       prop = drm_property_create_object(dev, DRM_MODE_PROP_ATOMIC,
+                       "CRTC_ID", DRM_MODE_OBJECT_CRTC);
+       if (!prop)
+               return -ENOMEM;
+       dev->mode_config.prop_crtc_id = prop;
 
        return 0;
 }
@@ -1599,7 +1707,7 @@ static int drm_mode_group_init(struct drm_device *dev, struct drm_mode_group *gr
        total_objects += dev->mode_config.num_encoder;
        total_objects += dev->mode_config.num_bridge;
 
-       group->id_list = kzalloc(total_objects * sizeof(uint32_t), GFP_KERNEL);
+       group->id_list = kcalloc(total_objects, sizeof(uint32_t), GFP_KERNEL);
        if (!group->id_list)
                return -ENOMEM;
 
@@ -1629,7 +1737,8 @@ int drm_mode_group_init_legacy_group(struct drm_device *dev,
        struct drm_bridge *bridge;
        int ret;
 
-       if ((ret = drm_mode_group_init(dev, group)))
+       ret = drm_mode_group_init(dev, group);
+       if (ret)
                return ret;
 
        list_for_each_entry(crtc, &dev->mode_config.crtc_list, head)
@@ -1996,6 +2105,44 @@ static struct drm_encoder *drm_connector_get_encoder(struct drm_connector *conne
        return connector->encoder;
 }
 
+/* helper for getconnector and getproperties ioctls */
+static int get_properties(struct drm_mode_object *obj, bool atomic,
+               uint32_t __user *prop_ptr, uint64_t __user *prop_values,
+               uint32_t *arg_count_props)
+{
+       int props_count;
+       int i, ret, copied;
+
+       props_count = obj->properties->count;
+       if (!atomic)
+               props_count -= obj->properties->atomic_count;
+
+       if ((*arg_count_props >= props_count) && props_count) {
+               for (i = 0, copied = 0; copied < props_count; i++) {
+                       struct drm_property *prop = obj->properties->properties[i];
+                       uint64_t val;
+
+                       if ((prop->flags & DRM_MODE_PROP_ATOMIC) && !atomic)
+                               continue;
+
+                       ret = drm_object_property_get_value(obj, prop, &val);
+                       if (ret)
+                               return ret;
+
+                       if (put_user(prop->base.id, prop_ptr + copied))
+                               return -EFAULT;
+
+                       if (put_user(val, prop_values + copied))
+                               return -EFAULT;
+
+                       copied++;
+               }
+       }
+       *arg_count_props = props_count;
+
+       return 0;
+}
+
 /**
  * drm_mode_getconnector - get connector configuration
  * @dev: drm device for the ioctl
@@ -2017,15 +2164,12 @@ int drm_mode_getconnector(struct drm_device *dev, void *data,
        struct drm_encoder *encoder;
        struct drm_display_mode *mode;
        int mode_count = 0;
-       int props_count = 0;
        int encoders_count = 0;
        int ret = 0;
        int copied = 0;
        int i;
        struct drm_mode_modeinfo u_mode;
        struct drm_mode_modeinfo __user *mode_ptr;
-       uint32_t __user *prop_ptr;
-       uint64_t __user *prop_values;
        uint32_t __user *encoder_ptr;
 
        if (!drm_core_check_feature(dev, DRIVER_MODESET))
@@ -2036,6 +2180,7 @@ int drm_mode_getconnector(struct drm_device *dev, void *data,
        DRM_DEBUG_KMS("[CONNECTOR:%d:?]\n", out_resp->connector_id);
 
        mutex_lock(&dev->mode_config.mutex);
+       drm_modeset_lock(&dev->mode_config.connection_mutex, NULL);
 
        connector = drm_connector_find(dev, out_resp->connector_id);
        if (!connector) {
@@ -2043,13 +2188,9 @@ int drm_mode_getconnector(struct drm_device *dev, void *data,
                goto out;
        }
 
-       props_count = connector->properties.count;
-
-       for (i = 0; i < DRM_CONNECTOR_MAX_ENCODER; i++) {
-               if (connector->encoder_ids[i] != 0) {
+       for (i = 0; i < DRM_CONNECTOR_MAX_ENCODER; i++)
+               if (connector->encoder_ids[i] != 0)
                        encoders_count++;
-               }
-       }
 
        if (out_resp->count_modes == 0) {
                connector->funcs->fill_modes(connector,
@@ -2069,14 +2210,11 @@ int drm_mode_getconnector(struct drm_device *dev, void *data,
        out_resp->mm_height = connector->display_info.height_mm;
        out_resp->subpixel = connector->display_info.subpixel_order;
        out_resp->connection = connector->status;
-       drm_modeset_lock(&dev->mode_config.connection_mutex, NULL);
-
        encoder = drm_connector_get_encoder(connector);
        if (encoder)
                out_resp->encoder_id = encoder->base.id;
        else
                out_resp->encoder_id = 0;
-       drm_modeset_unlock(&dev->mode_config.connection_mutex);
 
        /*
         * This ioctl is called twice, once to determine how much space is
@@ -2100,26 +2238,12 @@ int drm_mode_getconnector(struct drm_device *dev, void *data,
        }
        out_resp->count_modes = mode_count;
 
-       if ((out_resp->count_props >= props_count) && props_count) {
-               copied = 0;
-               prop_ptr = (uint32_t __user *)(unsigned long)(out_resp->props_ptr);
-               prop_values = (uint64_t __user *)(unsigned long)(out_resp->prop_values_ptr);
-               for (i = 0; i < connector->properties.count; i++) {
-                       if (put_user(connector->properties.ids[i],
-                                    prop_ptr + copied)) {
-                               ret = -EFAULT;
-                               goto out;
-                       }
-
-                       if (put_user(connector->properties.values[i],
-                                    prop_values + copied)) {
-                               ret = -EFAULT;
-                               goto out;
-                       }
-                       copied++;
-               }
-       }
-       out_resp->count_props = props_count;
+       ret = get_properties(&connector->base, file_priv->atomic,
+                       (uint32_t __user *)(unsigned long)(out_resp->props_ptr),
+                       (uint64_t __user *)(unsigned long)(out_resp->prop_values_ptr),
+                       &out_resp->count_props);
+       if (ret)
+               goto out;
 
        if ((out_resp->count_encoders >= encoders_count) && encoders_count) {
                copied = 0;
@@ -2138,6 +2262,7 @@ int drm_mode_getconnector(struct drm_device *dev, void *data,
        out_resp->count_encoders = encoders_count;
 
 out:
+       drm_modeset_unlock(&dev->mode_config.connection_mutex);
        mutex_unlock(&dev->mode_config.mutex);
 
        return ret;
@@ -2529,7 +2654,7 @@ int drm_mode_setplane(struct drm_device *dev, void *data,
  *
  * This is a little helper to wrap internal calls to the ->set_config driver
  * interface. The only thing it adds is correct refcounting dance.
- * 
+ *
  * Returns:
  * Zero on success, negative errno on failure.
  */
@@ -2702,6 +2827,12 @@ int drm_mode_setcrtc(struct drm_device *dev, void *data,
                        goto out;
                }
 
+               mode->status = drm_mode_validate_basic(mode);
+               if (mode->status != MODE_OK) {
+                       ret = -EINVAL;
+                       goto out;
+               }
+
                drm_mode_set_crtcinfo(mode, CRTC_INTERLACE_HALVE_V);
 
                ret = drm_crtc_check_viewport(crtc, crtc_req->x, crtc_req->y,
@@ -2733,9 +2864,9 @@ int drm_mode_setcrtc(struct drm_device *dev, void *data,
                        goto out;
                }
 
-               connector_set = kmalloc(crtc_req->count_connectors *
-                                       sizeof(struct drm_connector *),
-                                       GFP_KERNEL);
+               connector_set = kmalloc_array(crtc_req->count_connectors,
+                                             sizeof(struct drm_connector *),
+                                             GFP_KERNEL);
                if (!connector_set) {
                        ret = -ENOMEM;
                        goto out;
@@ -2980,6 +3111,7 @@ int drm_mode_cursor2_ioctl(struct drm_device *dev,
                           void *data, struct drm_file *file_priv)
 {
        struct drm_mode_cursor2 *req = data;
+
        return drm_mode_cursor_common(dev, req, file_priv);
 }
 
@@ -3427,7 +3559,7 @@ int drm_mode_dirtyfb_ioctl(struct drm_device *dev,
                        ret = -EINVAL;
                        goto out_err1;
                }
-               clips = kzalloc(num_clips * sizeof(*clips), GFP_KERNEL);
+               clips = kcalloc(num_clips, sizeof(*clips), GFP_KERNEL);
                if (!clips) {
                        ret = -ENOMEM;
                        goto out_err1;
@@ -3528,7 +3660,8 @@ struct drm_property *drm_property_create(struct drm_device *dev, int flags,
        property->dev = dev;
 
        if (num_values) {
-               property->values = kzalloc(sizeof(uint64_t)*num_values, GFP_KERNEL);
+               property->values = kcalloc(num_values, sizeof(uint64_t),
+                                          GFP_KERNEL);
                if (!property->values)
                        goto fail;
        }
@@ -3834,9 +3967,11 @@ void drm_object_attach_property(struct drm_mode_object *obj,
                return;
        }
 
-       obj->properties->ids[count] = property->base.id;
+       obj->properties->properties[count] = property;
        obj->properties->values[count] = init_val;
        obj->properties->count++;
+       if (property->flags & DRM_MODE_PROP_ATOMIC)
+               obj->properties->atomic_count++;
 }
 EXPORT_SYMBOL(drm_object_attach_property);
 
@@ -3859,7 +3994,7 @@ int drm_object_property_set_value(struct drm_mode_object *obj,
        int i;
 
        for (i = 0; i < obj->properties->count; i++) {
-               if (obj->properties->ids[i] == property->base.id) {
+               if (obj->properties->properties[i] == property) {
                        obj->properties->values[i] = val;
                        return 0;
                }
@@ -3888,8 +4023,16 @@ int drm_object_property_get_value(struct drm_mode_object *obj,
 {
        int i;
 
+       /* read-only properties bypass atomic mechanism and still store
+        * their value in obj->properties->values[].. mostly to avoid
+        * having to deal w/ EDID and similar props in atomic paths:
+        */
+       if (drm_core_check_feature(property->dev, DRIVER_ATOMIC) &&
+                       !(property->flags & DRM_MODE_PROP_IMMUTABLE))
+               return drm_atomic_get_property(obj, property, val);
+
        for (i = 0; i < obj->properties->count; i++) {
-               if (obj->properties->ids[i] == property->base.id) {
+               if (obj->properties->properties[i] == property) {
                        *val = obj->properties->values[i];
                        return 0;
                }
@@ -4069,7 +4212,7 @@ int drm_mode_getblob_ioctl(struct drm_device *dev,
 
        if (out_resp->length == blob->length) {
                blob_ptr = (void __user *)(unsigned long)out_resp->data;
-               if (copy_to_user(blob_ptr, blob->data, blob->length)){
+               if (copy_to_user(blob_ptr, blob->data, blob->length)) {
                        ret = -EFAULT;
                        goto done;
                }
@@ -4205,25 +4348,38 @@ int drm_mode_connector_update_edid_property(struct drm_connector *connector,
 }
 EXPORT_SYMBOL(drm_mode_connector_update_edid_property);
 
-static bool drm_property_change_is_valid(struct drm_property *property,
-                                        uint64_t value)
+/* Some properties could refer to dynamic refcnt'd objects, or things that
+ * need special locking to handle lifetime issues (ie. to ensure the prop
+ * value doesn't become invalid part way through the property update due to
+ * race).  The value returned by reference via 'obj' should be passed back
+ * to drm_property_change_valid_put() after the property is set (and the
+ * object to which the property is attached has a chance to take it's own
+ * reference).
+ */
+bool drm_property_change_valid_get(struct drm_property *property,
+                                        uint64_t value, struct drm_mode_object **ref)
 {
+       int i;
+
        if (property->flags & DRM_MODE_PROP_IMMUTABLE)
                return false;
 
+       *ref = NULL;
+
        if (drm_property_type_is(property, DRM_MODE_PROP_RANGE)) {
                if (value < property->values[0] || value > property->values[1])
                        return false;
                return true;
        } else if (drm_property_type_is(property, DRM_MODE_PROP_SIGNED_RANGE)) {
                int64_t svalue = U642I64(value);
+
                if (svalue < U642I64(property->values[0]) ||
                                svalue > U642I64(property->values[1]))
                        return false;
                return true;
        } else if (drm_property_type_is(property, DRM_MODE_PROP_BITMASK)) {
-               int i;
                uint64_t valid_mask = 0;
+
                for (i = 0; i < property->num_values; i++)
                        valid_mask |= (1ULL << property->values[i]);
                return !(value & ~valid_mask);
@@ -4231,25 +4387,40 @@ static bool drm_property_change_is_valid(struct drm_property *property,
                /* Only the driver knows */
                return true;
        } else if (drm_property_type_is(property, DRM_MODE_PROP_OBJECT)) {
-               struct drm_mode_object *obj;
                /* a zero value for an object property translates to null: */
                if (value == 0)
                        return true;
-               /*
-                * NOTE: use _object_find() directly to bypass restriction on
-                * looking up refcnt'd objects (ie. fb's).  For a refcnt'd
-                * object this could race against object finalization, so it
-                * simply tells us that the object *was* valid.  Which is good
-                * enough.
-                */
-               obj = _object_find(property->dev, value, property->values[0]);
-               return obj != NULL;
-       } else {
-               int i;
-               for (i = 0; i < property->num_values; i++)
-                       if (property->values[i] == value)
+
+               /* handle refcnt'd objects specially: */
+               if (property->values[0] == DRM_MODE_OBJECT_FB) {
+                       struct drm_framebuffer *fb;
+                       fb = drm_framebuffer_lookup(property->dev, value);
+                       if (fb) {
+                               *ref = &fb->base;
                                return true;
-               return false;
+                       } else {
+                               return false;
+                       }
+               } else {
+                       return _object_find(property->dev, value, property->values[0]) != NULL;
+               }
+       }
+
+       for (i = 0; i < property->num_values; i++)
+               if (property->values[i] == value)
+                       return true;
+       return false;
+}
+
+void drm_property_change_valid_put(struct drm_property *property,
+               struct drm_mode_object *ref)
+{
+       if (!ref)
+               return;
+
+       if (drm_property_type_is(property, DRM_MODE_PROP_OBJECT)) {
+               if (property->values[0] == DRM_MODE_OBJECT_FB)
+                       drm_framebuffer_unreference(obj_to_fb(ref));
        }
 }
 
@@ -4368,11 +4539,6 @@ int drm_mode_obj_get_properties_ioctl(struct drm_device *dev, void *data,
        struct drm_mode_obj_get_properties *arg = data;
        struct drm_mode_object *obj;
        int ret = 0;
-       int i;
-       int copied = 0;
-       int props_count = 0;
-       uint32_t __user *props_ptr;
-       uint64_t __user *prop_values_ptr;
 
        if (!drm_core_check_feature(dev, DRIVER_MODESET))
                return -EINVAL;
@@ -4389,30 +4555,11 @@ int drm_mode_obj_get_properties_ioctl(struct drm_device *dev, void *data,
                goto out;
        }
 
-       props_count = obj->properties->count;
+       ret = get_properties(obj, file_priv->atomic,
+                       (uint32_t __user *)(unsigned long)(arg->props_ptr),
+                       (uint64_t __user *)(unsigned long)(arg->prop_values_ptr),
+                       &arg->count_props);
 
-       /* This ioctl is called twice, once to determine how much space is
-        * needed, and the 2nd time to fill it. */
-       if ((arg->count_props >= props_count) && props_count) {
-               copied = 0;
-               props_ptr = (uint32_t __user *)(unsigned long)(arg->props_ptr);
-               prop_values_ptr = (uint64_t __user *)(unsigned long)
-                                 (arg->prop_values_ptr);
-               for (i = 0; i < props_count; i++) {
-                       if (put_user(obj->properties->ids[i],
-                                    props_ptr + copied)) {
-                               ret = -EFAULT;
-                               goto out;
-                       }
-                       if (put_user(obj->properties->values[i],
-                                    prop_values_ptr + copied)) {
-                               ret = -EFAULT;
-                               goto out;
-                       }
-                       copied++;
-               }
-       }
-       arg->count_props = props_count;
 out:
        drm_modeset_unlock_all(dev);
        return ret;
@@ -4441,8 +4588,8 @@ int drm_mode_obj_set_property_ioctl(struct drm_device *dev, void *data,
        struct drm_mode_object *arg_obj;
        struct drm_mode_object *prop_obj;
        struct drm_property *property;
-       int ret = -EINVAL;
-       int i;
+       int i, ret = -EINVAL;
+       struct drm_mode_object *ref;
 
        if (!drm_core_check_feature(dev, DRIVER_MODESET))
                return -EINVAL;
@@ -4458,7 +4605,7 @@ int drm_mode_obj_set_property_ioctl(struct drm_device *dev, void *data,
                goto out;
 
        for (i = 0; i < arg_obj->properties->count; i++)
-               if (arg_obj->properties->ids[i] == arg->prop_id)
+               if (arg_obj->properties->properties[i]->base.id == arg->prop_id)
                        break;
 
        if (i == arg_obj->properties->count)
@@ -4472,7 +4619,7 @@ int drm_mode_obj_set_property_ioctl(struct drm_device *dev, void *data,
        }
        property = obj_to_property(prop_obj);
 
-       if (!drm_property_change_is_valid(property, arg->value))
+       if (!drm_property_change_valid_get(property, arg->value, &ref))
                goto out;
 
        switch (arg_obj->type) {
@@ -4489,6 +4636,8 @@ int drm_mode_obj_set_property_ioctl(struct drm_device *dev, void *data,
                break;
        }
 
+       drm_property_change_valid_put(property, ref);
+
 out:
        drm_modeset_unlock_all(dev);
        return ret;
@@ -4538,7 +4687,8 @@ int drm_mode_crtc_set_gamma_size(struct drm_crtc *crtc,
 {
        crtc->gamma_size = gamma_size;
 
-       crtc->gamma_store = kzalloc(gamma_size * sizeof(uint16_t) * 3, GFP_KERNEL);
+       crtc->gamma_store = kcalloc(gamma_size, sizeof(uint16_t) * 3,
+                                   GFP_KERNEL);
        if (!crtc->gamma_store) {
                crtc->gamma_size = 0;
                return -ENOMEM;
@@ -4753,23 +4903,23 @@ int drm_mode_page_flip_ioctl(struct drm_device *dev,
        if (page_flip->flags & DRM_MODE_PAGE_FLIP_EVENT) {
                ret = -ENOMEM;
                spin_lock_irqsave(&dev->event_lock, flags);
-               if (file_priv->event_space < sizeof e->event) {
+               if (file_priv->event_space < sizeof(e->event)) {
                        spin_unlock_irqrestore(&dev->event_lock, flags);
                        goto out;
                }
-               file_priv->event_space -= sizeof e->event;
+               file_priv->event_space -= sizeof(e->event);
                spin_unlock_irqrestore(&dev->event_lock, flags);
 
-               e = kzalloc(sizeof *e, GFP_KERNEL);
+               e = kzalloc(sizeof(*e), GFP_KERNEL);
                if (e == NULL) {
                        spin_lock_irqsave(&dev->event_lock, flags);
-                       file_priv->event_space += sizeof e->event;
+                       file_priv->event_space += sizeof(e->event);
                        spin_unlock_irqrestore(&dev->event_lock, flags);
                        goto out;
                }
 
                e->event.base.type = DRM_EVENT_FLIP_COMPLETE;
-               e->event.base.length = sizeof e->event;
+               e->event.base.length = sizeof(e->event);
                e->event.user_data = page_flip->user_data;
                e->base.event = &e->event.base;
                e->base.file_priv = file_priv;
@@ -4782,7 +4932,7 @@ int drm_mode_page_flip_ioctl(struct drm_device *dev,
        if (ret) {
                if (page_flip->flags & DRM_MODE_PAGE_FLIP_EVENT) {
                        spin_lock_irqsave(&dev->event_lock, flags);
-                       file_priv->event_space += sizeof e->event;
+                       file_priv->event_space += sizeof(e->event);
                        spin_unlock_irqrestore(&dev->event_lock, flags);
                        kfree(e);
                }
@@ -5232,8 +5382,7 @@ void drm_mode_config_init(struct drm_device *dev)
        idr_init(&dev->mode_config.tile_idr);
 
        drm_modeset_lock_all(dev);
-       drm_mode_create_standard_connector_properties(dev);
-       drm_mode_create_standard_plane_properties(dev);
+       drm_mode_create_standard_properties(dev);
        drm_modeset_unlock_all(dev);
 
        /* Just to be sure */
index d552708409ded9cb3d8a81891d4824da4711f162..b1979e7bdc8862548d3f483eac109bf7959df27e 100644 (file)
@@ -946,6 +946,7 @@ int drm_helper_crtc_mode_set(struct drm_crtc *crtc, struct drm_display_mode *mod
                crtc_state = kzalloc(sizeof(*crtc_state), GFP_KERNEL);
        if (!crtc_state)
                return -ENOMEM;
+       crtc_state->crtc = crtc;
 
        crtc_state->enable = true;
        crtc_state->planes_changed = true;
@@ -1005,6 +1006,7 @@ int drm_helper_crtc_mode_set_base(struct drm_crtc *crtc, int x, int y,
                plane_state = kzalloc(sizeof(*plane_state), GFP_KERNEL);
        if (!plane_state)
                return -ENOMEM;
+       plane_state->plane = plane;
 
        plane_state->crtc = crtc;
        drm_atomic_set_fb_for_plane(plane_state, crtc->primary->fb);
index a2945ee6d6755bc101bdd3ef184ea891b7bbeea8..247dc8b625645b308631201486df4bfd1556eef8 100644 (file)
@@ -36,3 +36,9 @@ int drm_mode_object_get(struct drm_device *dev,
 void drm_mode_object_put(struct drm_device *dev,
                         struct drm_mode_object *object);
 
+/* drm_atomic.c */
+int drm_atomic_get_property(struct drm_mode_object *obj,
+                          struct drm_property *property, uint64_t *val);
+int drm_mode_atomic_ioctl(struct drm_device *dev,
+                         void *data, struct drm_file *file_priv);
+
index 4f41377b0b80963f9ce84b3492412d025924652b..d51213464672a9c1b7d3362f355b6ddde29c2403 100644 (file)
 unsigned int drm_debug = 0;    /* 1 to enable debug output */
 EXPORT_SYMBOL(drm_debug);
 
+bool drm_atomic = 0;
+
 MODULE_AUTHOR(CORE_AUTHOR);
 MODULE_DESCRIPTION(CORE_DESC);
 MODULE_LICENSE("GPL and additional rights");
 MODULE_PARM_DESC(debug, "Enable debug output");
+MODULE_PARM_DESC(atomic, "Enable experimental atomic KMS API");
 MODULE_PARM_DESC(vblankoffdelay, "Delay until vblank irq auto-disable [msecs] (0: never disable, <0: disable immediately)");
 MODULE_PARM_DESC(timestamp_precision_usec, "Max. error on timestamps [usecs]");
 MODULE_PARM_DESC(timestamp_monotonic, "Use monotonic timestamps");
 
 module_param_named(debug, drm_debug, int, 0600);
+module_param_named_unsafe(atomic, drm_atomic, bool, 0600);
 
 static DEFINE_SPINLOCK(drm_minor_lock);
 static struct idr drm_minors_idr;
index 52ce26d6b4fb8aeda59bb6358f62a659bc0464b7..d5c1db55abf7235a1ed39b766c89bb9fc66e6183 100644 (file)
@@ -741,7 +741,9 @@ int drm_fb_helper_setcmap(struct fb_cmap *cmap, struct fb_info *info)
        int i, j, rc = 0;
        int start;
 
-       drm_modeset_lock_all(dev);
+       if (__drm_modeset_lock_all(dev, !!oops_in_progress)) {
+               return -EBUSY;
+       }
        if (!drm_fb_helper_is_bound(fb_helper)) {
                drm_modeset_unlock_all(dev);
                return -EBUSY;
@@ -915,7 +917,9 @@ int drm_fb_helper_pan_display(struct fb_var_screeninfo *var,
        int ret = 0;
        int i;
 
-       drm_modeset_lock_all(dev);
+       if (__drm_modeset_lock_all(dev, !!oops_in_progress)) {
+               return -EBUSY;
+       }
        if (!drm_fb_helper_is_bound(fb_helper)) {
                drm_modeset_unlock_all(dev);
                return -EBUSY;
@@ -1688,7 +1692,7 @@ out:
  * RETURNS:
  * Zero if everything went ok, nonzero otherwise.
  */
-bool drm_fb_helper_initial_config(struct drm_fb_helper *fb_helper, int bpp_sel)
+int drm_fb_helper_initial_config(struct drm_fb_helper *fb_helper, int bpp_sel)
 {
        struct drm_device *dev = fb_helper->dev;
        int count = 0;
index 0b9514b6cd640793b7f73e8737bf310cb28b23ee..076dd606b58080681e1cfe5a646448ee3ac46854 100644 (file)
@@ -478,64 +478,59 @@ int drm_release(struct inode *inode, struct file *filp)
 }
 EXPORT_SYMBOL(drm_release);
 
-static bool
-drm_dequeue_event(struct drm_file *file_priv,
-                 size_t total, size_t max, struct drm_pending_event **out)
+ssize_t drm_read(struct file *filp, char __user *buffer,
+                size_t count, loff_t *offset)
 {
+       struct drm_file *file_priv = filp->private_data;
        struct drm_device *dev = file_priv->minor->dev;
-       struct drm_pending_event *e;
-       unsigned long flags;
-       bool ret = false;
-
-       spin_lock_irqsave(&dev->event_lock, flags);
+       ssize_t ret = 0;
 
-       *out = NULL;
-       if (list_empty(&file_priv->event_list))
-               goto out;
-       e = list_first_entry(&file_priv->event_list,
-                            struct drm_pending_event, link);
-       if (e->event->length + total > max)
-               goto out;
+       if (!access_ok(VERIFY_WRITE, buffer, count))
+               return -EFAULT;
 
-       file_priv->event_space += e->event->length;
-       list_del(&e->link);
-       *out = e;
-       ret = true;
+       spin_lock_irq(&dev->event_lock);
+       for (;;) {
+               if (list_empty(&file_priv->event_list)) {
+                       if (ret)
+                               break;
 
-out:
-       spin_unlock_irqrestore(&dev->event_lock, flags);
-       return ret;
-}
-
-ssize_t drm_read(struct file *filp, char __user *buffer,
-                size_t count, loff_t *offset)
-{
-       struct drm_file *file_priv = filp->private_data;
-       struct drm_pending_event *e;
-       size_t total;
-       ssize_t ret;
+                       if (filp->f_flags & O_NONBLOCK) {
+                               ret = -EAGAIN;
+                               break;
+                       }
 
-       if ((filp->f_flags & O_NONBLOCK) == 0) {
-               ret = wait_event_interruptible(file_priv->event_wait,
-                                              !list_empty(&file_priv->event_list));
-               if (ret < 0)
-                       return ret;
-       }
+                       spin_unlock_irq(&dev->event_lock);
+                       ret = wait_event_interruptible(file_priv->event_wait,
+                                                      !list_empty(&file_priv->event_list));
+                       spin_lock_irq(&dev->event_lock);
+                       if (ret < 0)
+                               break;
+
+                       ret = 0;
+               } else {
+                       struct drm_pending_event *e;
+
+                       e = list_first_entry(&file_priv->event_list,
+                                            struct drm_pending_event, link);
+                       if (e->event->length + ret > count)
+                               break;
+
+                       if (__copy_to_user_inatomic(buffer + ret,
+                                                   e->event, e->event->length)) {
+                               if (ret == 0)
+                                       ret = -EFAULT;
+                               break;
+                       }
 
-       total = 0;
-       while (drm_dequeue_event(file_priv, total, count, &e)) {
-               if (copy_to_user(buffer + total,
-                                e->event, e->event->length)) {
-                       total = -EFAULT;
+                       file_priv->event_space += e->event->length;
+                       ret += e->event->length;
+                       list_del(&e->link);
                        e->destroy(e);
-                       break;
                }
-
-               total += e->event->length;
-               e->destroy(e);
        }
+       spin_unlock_irq(&dev->event_lock);
 
-       return total ?: -EAGAIN;
+       return ret;
 }
 EXPORT_SYMBOL(drm_read);
 
index 51efebd434f302d61134c2eb384935ef4c1b2521..f1b32f91d94163bcdca46a6ee5f29bd789e23336 100644 (file)
@@ -152,30 +152,6 @@ int drm_bufs_info(struct seq_file *m, void *data)
        return 0;
 }
 
-/**
- * Called when "/proc/dri/.../vblank" is read.
- */
-int drm_vblank_info(struct seq_file *m, void *data)
-{
-       struct drm_info_node *node = (struct drm_info_node *) m->private;
-       struct drm_device *dev = node->minor->dev;
-       int crtc;
-
-       mutex_lock(&dev->struct_mutex);
-       for (crtc = 0; crtc < dev->num_crtcs; crtc++) {
-               seq_printf(m, "CRTC %d enable:     %d\n",
-                          crtc, atomic_read(&dev->vblank[crtc].refcount));
-               seq_printf(m, "CRTC %d counter:    %d\n",
-                          crtc, drm_vblank_count(dev, crtc));
-               seq_printf(m, "CRTC %d last wait:  %d\n",
-                          crtc, dev->vblank[crtc].last_wait);
-               seq_printf(m, "CRTC %d in modeset: %d\n",
-                          crtc, dev->vblank[crtc].inmodeset);
-       }
-       mutex_unlock(&dev->struct_mutex);
-       return 0;
-}
-
 /**
  * Called when "/proc/dri/.../clients" is read.
  *
index 7cc0a3516871f493e74a74a2d38b600e0802c3c4..12a61d70682785a1078e5f398064d3a4dd659b10 100644 (file)
@@ -55,7 +55,6 @@ void drm_prime_remove_buf_handle_locked(struct drm_prime_file_private *prime_fpr
 int drm_name_info(struct seq_file *m, void *data);
 int drm_vm_info(struct seq_file *m, void *data);
 int drm_bufs_info(struct seq_file *m, void *data);
-int drm_vblank_info(struct seq_file *m, void *data);
 int drm_clients_info(struct seq_file *m, void* data);
 int drm_gem_name_info(struct seq_file *m, void *data);
 
index 00587a1e3c83c0dc23c05a55a7d37ea10f891847..3785d66721f2f6fdba2d134ba8eaa0c9ab8fb416 100644 (file)
@@ -32,6 +32,7 @@
 #include <drm/drm_core.h>
 #include "drm_legacy.h"
 #include "drm_internal.h"
+#include "drm_crtc_internal.h"
 
 #include <linux/pci.h>
 #include <linux/export.h>
@@ -345,6 +346,17 @@ drm_setclientcap(struct drm_device *dev, void *data, struct drm_file *file_priv)
                        return -EINVAL;
                file_priv->universal_planes = req->value;
                break;
+       case DRM_CLIENT_CAP_ATOMIC:
+               /* for now, hide behind experimental drm.atomic moduleparam */
+               if (!drm_atomic)
+                       return -EINVAL;
+               if (!drm_core_check_feature(dev, DRIVER_ATOMIC))
+                       return -EINVAL;
+               if (req->value > 1)
+                       return -EINVAL;
+               file_priv->atomic = req->value;
+               file_priv->universal_planes = req->value;
+               break;
        default:
                return -EINVAL;
        }
@@ -620,6 +632,7 @@ static const struct drm_ioctl_desc drm_ioctls[] = {
        DRM_IOCTL_DEF(DRM_IOCTL_MODE_OBJ_GETPROPERTIES, drm_mode_obj_get_properties_ioctl, DRM_CONTROL_ALLOW|DRM_UNLOCKED),
        DRM_IOCTL_DEF(DRM_IOCTL_MODE_OBJ_SETPROPERTY, drm_mode_obj_set_property_ioctl, DRM_MASTER|DRM_CONTROL_ALLOW|DRM_UNLOCKED),
        DRM_IOCTL_DEF(DRM_IOCTL_MODE_CURSOR2, drm_mode_cursor2_ioctl, DRM_MASTER|DRM_CONTROL_ALLOW|DRM_UNLOCKED),
+       DRM_IOCTL_DEF(DRM_IOCTL_MODE_ATOMIC, drm_mode_atomic_ioctl, DRM_MASTER|DRM_CONTROL_ALLOW|DRM_UNLOCKED),
 };
 
 #define DRM_CORE_IOCTL_COUNT   ARRAY_SIZE( drm_ioctls )
index 4d79dad9d44fad0ac48b2b81177ffda8430b390b..75647e7f012b303fee89d7e79cdc1e01d0645d05 100644 (file)
@@ -778,7 +778,7 @@ static struct timeval get_drm_timestamp(void)
 
 /**
  * drm_get_last_vbltimestamp - retrieve raw timestamp for the most recent
- *                            vblank interval
+ *                             vblank interval
  * @dev: DRM device
  * @crtc: which CRTC's vblank timestamp to retrieve
  * @tvblank: Pointer to target struct timeval which should receive the timestamp
@@ -933,6 +933,7 @@ void drm_send_vblank_event(struct drm_device *dev, int crtc,
 {
        struct timeval now;
        unsigned int seq;
+
        if (crtc >= 0) {
                seq = drm_vblank_count_and_time(dev, crtc, &now);
        } else {
@@ -1422,7 +1423,7 @@ static int drm_queue_vblank_event(struct drm_device *dev, int pipe,
        unsigned int seq;
        int ret;
 
-       e = kzalloc(sizeof *e, GFP_KERNEL);
+       e = kzalloc(sizeof(*e), GFP_KERNEL);
        if (e == NULL) {
                ret = -ENOMEM;
                goto err_put;
@@ -1431,7 +1432,7 @@ static int drm_queue_vblank_event(struct drm_device *dev, int pipe,
        e->pipe = pipe;
        e->base.pid = current->pid;
        e->event.base.type = DRM_EVENT_VBLANK;
-       e->event.base.length = sizeof e->event;
+       e->event.base.length = sizeof(e->event);
        e->event.user_data = vblwait->request.signal;
        e->base.event = &e->event.base;
        e->base.file_priv = file_priv;
@@ -1451,12 +1452,12 @@ static int drm_queue_vblank_event(struct drm_device *dev, int pipe,
                goto err_unlock;
        }
 
-       if (file_priv->event_space < sizeof e->event) {
+       if (file_priv->event_space < sizeof(e->event)) {
                ret = -EBUSY;
                goto err_unlock;
        }
 
-       file_priv->event_space -= sizeof e->event;
+       file_priv->event_space -= sizeof(e->event);
        seq = drm_vblank_count_and_time(dev, pipe, &now);
 
        if ((vblwait->request.type & _DRM_VBLANK_NEXTONMISS) &&
index 7689c14f2f09b2f9064f4067f1752c69d7c1e16a..20d977a52c58d93da2368803473f07e6d2d5db12 100644 (file)
@@ -615,6 +615,46 @@ void drm_display_mode_from_videomode(const struct videomode *vm,
 }
 EXPORT_SYMBOL_GPL(drm_display_mode_from_videomode);
 
+/**
+ * drm_display_mode_to_videomode - fill in @vm using @dmode,
+ * @dmode: drm_display_mode structure to use as source
+ * @vm: videomode structure to use as destination
+ *
+ * Fills out @vm using the display mode specified in @dmode.
+ */
+void drm_display_mode_to_videomode(const struct drm_display_mode *dmode,
+                                  struct videomode *vm)
+{
+       vm->hactive = dmode->hdisplay;
+       vm->hfront_porch = dmode->hsync_start - dmode->hdisplay;
+       vm->hsync_len = dmode->hsync_end - dmode->hsync_start;
+       vm->hback_porch = dmode->htotal - dmode->hsync_end;
+
+       vm->vactive = dmode->vdisplay;
+       vm->vfront_porch = dmode->vsync_start - dmode->vdisplay;
+       vm->vsync_len = dmode->vsync_end - dmode->vsync_start;
+       vm->vback_porch = dmode->vtotal - dmode->vsync_end;
+
+       vm->pixelclock = dmode->clock * 1000;
+
+       vm->flags = 0;
+       if (dmode->flags & DRM_MODE_FLAG_PHSYNC)
+               vm->flags |= DISPLAY_FLAGS_HSYNC_HIGH;
+       else if (dmode->flags & DRM_MODE_FLAG_NHSYNC)
+               vm->flags |= DISPLAY_FLAGS_HSYNC_LOW;
+       if (dmode->flags & DRM_MODE_FLAG_PVSYNC)
+               vm->flags |= DISPLAY_FLAGS_VSYNC_HIGH;
+       else if (dmode->flags & DRM_MODE_FLAG_NVSYNC)
+               vm->flags |= DISPLAY_FLAGS_VSYNC_LOW;
+       if (dmode->flags & DRM_MODE_FLAG_INTERLACE)
+               vm->flags |= DISPLAY_FLAGS_INTERLACED;
+       if (dmode->flags & DRM_MODE_FLAG_DBLSCAN)
+               vm->flags |= DISPLAY_FLAGS_DOUBLESCAN;
+       if (dmode->flags & DRM_MODE_FLAG_DBLCLK)
+               vm->flags |= DISPLAY_FLAGS_DOUBLECLK;
+}
+EXPORT_SYMBOL_GPL(drm_display_mode_to_videomode);
+
 #ifdef CONFIG_OF
 /**
  * of_get_drm_display_mode - get a drm_display_mode from devicetree
@@ -911,10 +951,41 @@ bool drm_mode_equal_no_clocks_no_stereo(const struct drm_display_mode *mode1,
 }
 EXPORT_SYMBOL(drm_mode_equal_no_clocks_no_stereo);
 
+/**
+ * drm_mode_validate_basic - make sure the mode is somewhat sane
+ * @mode: mode to check
+ *
+ * Check that the mode timings are at least somewhat reasonable.
+ * Any hardware specific limits are left up for each driver to check.
+ *
+ * Returns:
+ * The mode status
+ */
+enum drm_mode_status
+drm_mode_validate_basic(const struct drm_display_mode *mode)
+{
+       if (mode->clock == 0)
+               return MODE_CLOCK_LOW;
+
+       if (mode->hdisplay == 0 ||
+           mode->hsync_start < mode->hdisplay ||
+           mode->hsync_end < mode->hsync_start ||
+           mode->htotal < mode->hsync_end)
+               return MODE_H_ILLEGAL;
+
+       if (mode->vdisplay == 0 ||
+           mode->vsync_start < mode->vdisplay ||
+           mode->vsync_end < mode->vsync_start ||
+           mode->vtotal < mode->vsync_end)
+               return MODE_V_ILLEGAL;
+
+       return MODE_OK;
+}
+EXPORT_SYMBOL(drm_mode_validate_basic);
+
 /**
  * drm_mode_validate_size - make sure modes adhere to size constraints
- * @dev: DRM device
- * @mode_list: list of modes to check
+ * @mode: mode to check
  * @maxX: maximum width
  * @maxY: maximum height
  *
@@ -922,20 +993,21 @@ EXPORT_SYMBOL(drm_mode_equal_no_clocks_no_stereo);
  * limitations of the DRM device/connector. If a mode is too big its status
  * member is updated with the appropriate validation failure code. The list
  * itself is not changed.
+ *
+ * Returns:
+ * The mode status
  */
-void drm_mode_validate_size(struct drm_device *dev,
-                           struct list_head *mode_list,
-                           int maxX, int maxY)
+enum drm_mode_status
+drm_mode_validate_size(const struct drm_display_mode *mode,
+                      int maxX, int maxY)
 {
-       struct drm_display_mode *mode;
+       if (maxX > 0 && mode->hdisplay > maxX)
+               return MODE_VIRTUAL_X;
 
-       list_for_each_entry(mode, mode_list, head) {
-               if (maxX > 0 && mode->hdisplay > maxX)
-                       mode->status = MODE_VIRTUAL_X;
+       if (maxY > 0 && mode->vdisplay > maxY)
+               return MODE_VIRTUAL_Y;
 
-               if (maxY > 0 && mode->vdisplay > maxY)
-                       mode->status = MODE_VIRTUAL_Y;
-       }
+       return MODE_OK;
 }
 EXPORT_SYMBOL(drm_mode_validate_size);
 
index 18a1ac6ac22f396aa55b34187b7fb89a9392613b..f24c4cfe674b9e0d75a36f0ab017afef7bcddb5f 100644 (file)
@@ -142,6 +142,17 @@ int drm_plane_helper_check_update(struct drm_plane *plane,
 {
        int hscale, vscale;
 
+       if (!fb) {
+               *visible = false;
+               return 0;
+       }
+
+       /* crtc should only be NULL when disabling (i.e., !fb) */
+       if (WARN_ON(!crtc)) {
+               *visible = false;
+               return 0;
+       }
+
        if (!crtc->enabled && !can_update_disabled) {
                DRM_DEBUG_KMS("Cannot update plane of a disabled CRTC.\n");
                return -EINVAL;
@@ -155,11 +166,6 @@ int drm_plane_helper_check_update(struct drm_plane *plane,
                return -ERANGE;
        }
 
-       if (!fb) {
-               *visible = false;
-               return 0;
-       }
-
        *visible = drm_rect_clip_scaled(src, dest, clip, hscale, vscale);
        if (!*visible)
                /*
@@ -517,6 +523,7 @@ int drm_plane_helper_update(struct drm_plane *plane, struct drm_crtc *crtc,
                plane_state = kzalloc(sizeof(*plane_state), GFP_KERNEL);
        if (!plane_state)
                return -ENOMEM;
+       plane_state->plane = plane;
 
        plane_state->crtc = crtc;
        drm_atomic_set_fb_for_plane(plane_state, fb);
@@ -563,6 +570,7 @@ int drm_plane_helper_disable(struct drm_plane *plane)
                plane_state = kzalloc(sizeof(*plane_state), GFP_KERNEL);
        if (!plane_state)
                return -ENOMEM;
+       plane_state->plane = plane;
 
        plane_state->crtc = NULL;
        drm_atomic_set_fb_for_plane(plane_state, NULL);
index 7483a47de8e41630a37e7db22c5e9585dff11013..6591d48c1b9d0f3bcc4a74a8da730833cbc4e839 100644 (file)
 static bool drm_kms_helper_poll = true;
 module_param_named(poll, drm_kms_helper_poll, bool, 0600);
 
-static void drm_mode_validate_flag(struct drm_connector *connector,
-                                  int flags)
+static enum drm_mode_status
+drm_mode_validate_flag(const struct drm_display_mode *mode,
+                      int flags)
 {
-       struct drm_display_mode *mode;
+       if ((mode->flags & DRM_MODE_FLAG_INTERLACE) &&
+           !(flags & DRM_MODE_FLAG_INTERLACE))
+               return MODE_NO_INTERLACE;
 
-       if (flags == (DRM_MODE_FLAG_DBLSCAN | DRM_MODE_FLAG_INTERLACE |
-                     DRM_MODE_FLAG_3D_MASK))
-               return;
+       if ((mode->flags & DRM_MODE_FLAG_DBLSCAN) &&
+           !(flags & DRM_MODE_FLAG_DBLSCAN))
+               return MODE_NO_DBLESCAN;
 
-       list_for_each_entry(mode, &connector->modes, head) {
-               if ((mode->flags & DRM_MODE_FLAG_INTERLACE) &&
-                               !(flags & DRM_MODE_FLAG_INTERLACE))
-                       mode->status = MODE_NO_INTERLACE;
-               if ((mode->flags & DRM_MODE_FLAG_DBLSCAN) &&
-                               !(flags & DRM_MODE_FLAG_DBLSCAN))
-                       mode->status = MODE_NO_DBLESCAN;
-               if ((mode->flags & DRM_MODE_FLAG_3D_MASK) &&
-                               !(flags & DRM_MODE_FLAG_3D_MASK))
-                       mode->status = MODE_NO_STEREO;
-       }
+       if ((mode->flags & DRM_MODE_FLAG_3D_MASK) &&
+           !(flags & DRM_MODE_FLAG_3D_MASK))
+               return MODE_NO_STEREO;
 
-       return;
+       return MODE_OK;
 }
 
 static int drm_helper_probe_add_cmdline_mode(struct drm_connector *connector)
@@ -108,6 +103,7 @@ static int drm_helper_probe_single_connector_modes_merge_bits(struct drm_connect
        int count = 0;
        int mode_flags = 0;
        bool verbose_prune = true;
+       enum drm_connector_status old_status;
 
        WARN_ON(!mutex_is_locked(&dev->mode_config.mutex));
 
@@ -126,7 +122,33 @@ static int drm_helper_probe_single_connector_modes_merge_bits(struct drm_connect
                if (connector->funcs->force)
                        connector->funcs->force(connector);
        } else {
+               old_status = connector->status;
+
                connector->status = connector->funcs->detect(connector, true);
+
+               /*
+                * Normally either the driver's hpd code or the poll loop should
+                * pick up any changes and fire the hotplug event. But if
+                * userspace sneaks in a probe, we might miss a change. Hence
+                * check here, and if anything changed start the hotplug code.
+                */
+               if (old_status != connector->status) {
+                       DRM_DEBUG_KMS("[CONNECTOR:%d:%s] status updated from %d to %d\n",
+                                     connector->base.id,
+                                     connector->name,
+                                     old_status, connector->status);
+
+                       /*
+                        * The hotplug event code might call into the fb
+                        * helpers, and so expects that we do not hold any
+                        * locks. Fire up the poll struct instead, it will
+                        * disable itself again.
+                        */
+                       dev->mode_config.delayed_event = true;
+                       if (dev->mode_config.poll_enabled)
+                               schedule_delayed_work(&dev->mode_config.output_poll_work,
+                                                     0);
+               }
        }
 
        /* Re-enable polling in case the global poll config changed. */
@@ -164,18 +186,22 @@ static int drm_helper_probe_single_connector_modes_merge_bits(struct drm_connect
 
        drm_mode_connector_list_update(connector, merge_type_bits);
 
-       if (maxX && maxY)
-               drm_mode_validate_size(dev, &connector->modes, maxX, maxY);
-
        if (connector->interlace_allowed)
                mode_flags |= DRM_MODE_FLAG_INTERLACE;
        if (connector->doublescan_allowed)
                mode_flags |= DRM_MODE_FLAG_DBLSCAN;
        if (connector->stereo_allowed)
                mode_flags |= DRM_MODE_FLAG_3D_MASK;
-       drm_mode_validate_flag(connector, mode_flags);
 
        list_for_each_entry(mode, &connector->modes, head) {
+               mode->status = drm_mode_validate_basic(mode);
+
+               if (mode->status == MODE_OK)
+                       mode->status = drm_mode_validate_size(mode, maxX, maxY);
+
+               if (mode->status == MODE_OK)
+                       mode->status = drm_mode_validate_flag(mode, mode_flags);
+
                if (mode->status == MODE_OK && connector_funcs->mode_valid)
                        mode->status = connector_funcs->mode_valid(connector,
                                                                   mode);
@@ -275,10 +301,14 @@ static void output_poll_execute(struct work_struct *work)
        struct drm_device *dev = container_of(delayed_work, struct drm_device, mode_config.output_poll_work);
        struct drm_connector *connector;
        enum drm_connector_status old_status;
-       bool repoll = false, changed = false;
+       bool repoll = false, changed;
+
+       /* Pick up any changes detected by the probe functions. */
+       changed = dev->mode_config.delayed_event;
+       dev->mode_config.delayed_event = false;
 
        if (!drm_kms_helper_poll)
-               return;
+               goto out;
 
        mutex_lock(&dev->mode_config.mutex);
        list_for_each_entry(connector, &dev->mode_config.connector_list, head) {
@@ -305,6 +335,24 @@ static void output_poll_execute(struct work_struct *work)
                if (old_status != connector->status) {
                        const char *old, *new;
 
+                       /*
+                        * The poll work sets force=false when calling detect so
+                        * that drivers can avoid to do disruptive tests (e.g.
+                        * when load detect cycles could cause flickering on
+                        * other, running displays). This bears the risk that we
+                        * flip-flop between unknown here in the poll work and
+                        * the real state when userspace forces a full detect
+                        * call after receiving a hotplug event due to this
+                        * change.
+                        *
+                        * Hence clamp an unknown detect status to the old
+                        * value.
+                        */
+                       if (connector->status == connector_status_unknown) {
+                               connector->status = old_status;
+                               continue;
+                       }
+
                        old = drm_get_connector_status_name(old_status);
                        new = drm_get_connector_status_name(connector->status);
 
@@ -320,6 +368,7 @@ static void output_poll_execute(struct work_struct *work)
 
        mutex_unlock(&dev->mode_config.mutex);
 
+out:
        if (changed)
                drm_kms_helper_hotplug_event(dev);
 
index 7f9f6f9e9b7e79926ab1ed791c6fbef8defb3a02..c072999b7e0345c613acc9d07e6cb95f31293b93 100644 (file)
@@ -6,7 +6,6 @@ config DRM_EXYNOS
        select FB_CFB_FILLRECT
        select FB_CFB_COPYAREA
        select FB_CFB_IMAGEBLIT
-       select VT_HW_CONSOLE_BINDING if FRAMEBUFFER_CONSOLE
        select VIDEOMODE_HELPERS
        help
          Choose this option if you have a Samsung SoC EXYNOS chipset.
index 121470a83d1a497a61a19fe5cd09f769140efac9..1bcbe07cecfc9541a2eba9415c227ae17a9c0449 100644 (file)
@@ -645,18 +645,6 @@ static int exynos_drm_init(void)
        if (!is_exynos)
                return -ENODEV;
 
-       /*
-        * Register device object only in case of Exynos SoC.
-        *
-        * Below codes resolves temporarily infinite loop issue incurred
-        * by Exynos drm driver when using multi-platform kernel.
-        * So these codes will be replaced with more generic way later.
-        */
-       if (!of_machine_is_compatible("samsung,exynos3") &&
-                       !of_machine_is_compatible("samsung,exynos4") &&
-                       !of_machine_is_compatible("samsung,exynos5"))
-               return -ENODEV;
-
        exynos_drm_pdev = platform_device_register_simple("exynos-drm", -1,
                                                                NULL, 0);
        if (IS_ERR(exynos_drm_pdev))
index 5765a161abdd4b35c958086ad9fdf996b146dbc1..98051e8e855a1f07e8d5ef1e21995eb9783c1a1b 100644 (file)
@@ -1669,7 +1669,6 @@ static void hdmi_mode_apply(struct hdmi_context *hdata)
 
 static void hdmiphy_conf_reset(struct hdmi_context *hdata)
 {
-       u8 buffer[2];
        u32 reg;
 
        clk_disable_unprepare(hdata->res.sclk_hdmi);
@@ -1677,11 +1676,8 @@ static void hdmiphy_conf_reset(struct hdmi_context *hdata)
        clk_prepare_enable(hdata->res.sclk_hdmi);
 
        /* operation mode */
-       buffer[0] = 0x1f;
-       buffer[1] = 0x00;
-
-       if (hdata->hdmiphy_port)
-               i2c_master_send(hdata->hdmiphy_port, buffer, 2);
+       hdmiphy_reg_writeb(hdata, HDMIPHY_MODE_SET_DONE,
+                               HDMI_PHY_ENABLE_MODE_SET);
 
        if (hdata->type == HDMI_TYPE13)
                reg = HDMI_V13_PHY_RSTOUT;
index 820b76234ef4c5c6da02ebe50327066c5fe38d1a..064ed6597defefad5a2efa3bba63ba55f5551c13 100644 (file)
@@ -1026,6 +1026,7 @@ static void mixer_win_disable(struct exynos_drm_manager *mgr, int zpos)
 static void mixer_wait_for_vblank(struct exynos_drm_manager *mgr)
 {
        struct mixer_context *mixer_ctx = mgr_to_mixer(mgr);
+       int err;
 
        mutex_lock(&mixer_ctx->mixer_mutex);
        if (!mixer_ctx->powered) {
@@ -1034,7 +1035,11 @@ static void mixer_wait_for_vblank(struct exynos_drm_manager *mgr)
        }
        mutex_unlock(&mixer_ctx->mixer_mutex);
 
-       drm_vblank_get(mgr->crtc->dev, mixer_ctx->pipe);
+       err = drm_vblank_get(mgr->crtc->dev, mixer_ctx->pipe);
+       if (err < 0) {
+               DRM_DEBUG_KMS("failed to acquire vblank counter\n");
+               return;
+       }
 
        atomic_set(&mixer_ctx->wait_vsync_event, 1);
 
@@ -1262,8 +1267,6 @@ static int mixer_bind(struct device *dev, struct device *manager, void *data)
                return ret;
        }
 
-       pm_runtime_enable(dev);
-
        return 0;
 }
 
@@ -1272,8 +1275,6 @@ static void mixer_unbind(struct device *dev, struct device *master, void *data)
        struct mixer_context *ctx = dev_get_drvdata(dev);
 
        mixer_mgr_remove(&ctx->manager);
-
-       pm_runtime_disable(dev);
 }
 
 static const struct component_ops mixer_component_ops = {
index ddd90ddbc20097d7325379d7cf77d516854d60f6..2d42ce6d37577a45fc446117855244296b45760b 100644 (file)
@@ -593,6 +593,7 @@ int psb_fbdev_init(struct drm_device *dev)
 {
        struct psb_fbdev *fbdev;
        struct drm_psb_private *dev_priv = dev->dev_private;
+       int ret;
 
        fbdev = kzalloc(sizeof(struct psb_fbdev), GFP_KERNEL);
        if (!fbdev) {
@@ -604,16 +605,29 @@ int psb_fbdev_init(struct drm_device *dev)
 
        drm_fb_helper_prepare(dev, &fbdev->psb_fb_helper, &psb_fb_helper_funcs);
 
-       drm_fb_helper_init(dev, &fbdev->psb_fb_helper, dev_priv->ops->crtcs,
-                                                       INTELFB_CONN_LIMIT);
+       ret = drm_fb_helper_init(dev, &fbdev->psb_fb_helper,
+                                dev_priv->ops->crtcs, INTELFB_CONN_LIMIT);
+       if (ret)
+               goto free;
 
-       drm_fb_helper_single_add_all_connectors(&fbdev->psb_fb_helper);
+       ret = drm_fb_helper_single_add_all_connectors(&fbdev->psb_fb_helper);
+       if (ret)
+               goto fini;
 
        /* disable all the possible outputs/crtcs before entering KMS mode */
        drm_helper_disable_unused_functions(dev);
 
-       drm_fb_helper_initial_config(&fbdev->psb_fb_helper, 32);
+       ret = drm_fb_helper_initial_config(&fbdev->psb_fb_helper, 32);
+       if (ret)
+               goto fini;
+
        return 0;
+
+fini:
+       drm_fb_helper_fini(&fbdev->psb_fb_helper);
+free:
+       kfree(fbdev);
+       return ret;
 }
 
 static void psb_fbdev_fini(struct drm_device *dev)
index faf1c0c5ab2eb9300b9acef0a337bfd7bc8a0d64..fa140e04d5fa72f18237054c2b10f23f77355d83 100644 (file)
@@ -644,9 +644,6 @@ static int adv7511_encoder_mode_valid(struct drm_encoder *encoder,
        if (mode->clock > 165000)
                return MODE_CLOCK_HIGH;
 
-       if (mode->flags & DRM_MODE_FLAG_INTERLACE)
-               return MODE_NO_INTERLACE;
-
        return MODE_OK;
 }
 
index 9f430f77a52026345defa1d372bbb607a7e8f0a8..6c403654e33a121c0d6c3028e1e3e467fef84b04 100644 (file)
@@ -5111,7 +5111,7 @@ static bool mutex_is_locked_by(struct mutex *mutex, struct task_struct *task)
        if (!mutex_is_locked(mutex))
                return false;
 
-#if defined(CONFIG_SMP) || defined(CONFIG_DEBUG_MUTEXES)
+#if defined(CONFIG_SMP) && !defined(CONFIG_DEBUG_MUTEXES)
        return mutex->owner == task;
 #else
        /* Since UP may be pre-empted, we cannot assume that we own the lock */
index 49b2eab67c0d8defd748115a935a82d1e74ca8ff..8fe5a87705f7c607fd4e75df39124a42d4f3cb55 100644 (file)
@@ -296,6 +296,23 @@ void gen6_enable_rps_interrupts(struct drm_device *dev)
        spin_unlock_irq(&dev_priv->irq_lock);
 }
 
+u32 gen6_sanitize_rps_pm_mask(struct drm_i915_private *dev_priv, u32 mask)
+{
+       /*
+        * SNB,IVB can while VLV,CHV may hard hang on looping batchbuffer
+        * if GEN6_PM_UP_EI_EXPIRED is masked.
+        *
+        * TODO: verify if this can be reproduced on VLV,CHV.
+        */
+       if (INTEL_INFO(dev_priv)->gen <= 7 && !IS_HASWELL(dev_priv))
+               mask &= ~GEN6_PM_RP_UP_EI_EXPIRED;
+
+       if (INTEL_INFO(dev_priv)->gen >= 8)
+               mask &= ~GEN8_PMINTR_REDIRECT_TO_NON_DISP;
+
+       return mask;
+}
+
 void gen6_disable_rps_interrupts(struct drm_device *dev)
 {
        struct drm_i915_private *dev_priv = dev->dev_private;
@@ -308,8 +325,7 @@ void gen6_disable_rps_interrupts(struct drm_device *dev)
 
        spin_lock_irq(&dev_priv->irq_lock);
 
-       I915_WRITE(GEN6_PMINTRMSK, INTEL_INFO(dev_priv)->gen >= 8 ?
-                  ~GEN8_PMINTR_REDIRECT_TO_NON_DISP : ~0);
+       I915_WRITE(GEN6_PMINTRMSK, gen6_sanitize_rps_pm_mask(dev_priv, ~0));
 
        __gen6_disable_pm_irq(dev_priv, dev_priv->pm_rps_events);
        I915_WRITE(gen6_pm_ier(dev_priv), I915_READ(gen6_pm_ier(dev_priv)) &
index ece397b691a17463c82eb30d37119ec664c6e327..91d8ada8fe6d2965f5d0875ddb94e6666b19e6a3 100644 (file)
@@ -9705,7 +9705,7 @@ static int intel_crtc_page_flip(struct drm_crtc *crtc,
                if (obj->tiling_mode != work->old_fb_obj->tiling_mode)
                        /* vlv: DISPLAY_FLIP fails to change tiling */
                        ring = NULL;
-       } else if (IS_IVYBRIDGE(dev)) {
+       } else if (IS_IVYBRIDGE(dev) || IS_HASWELL(dev)) {
                ring = &dev_priv->ring[BCS];
        } else if (INTEL_INFO(dev)->gen >= 7) {
                ring = i915_gem_request_get_ring(obj->last_read_req);
index eca2395e13c855130d36c4d757e6a36d36f2b3ca..30e968f8c55ee51d6d083dc31383ce9ba01238b4 100644 (file)
@@ -824,6 +824,7 @@ void gen6_disable_pm_irq(struct drm_i915_private *dev_priv, uint32_t mask);
 void gen6_reset_rps_interrupts(struct drm_device *dev);
 void gen6_enable_rps_interrupts(struct drm_device *dev);
 void gen6_disable_rps_interrupts(struct drm_device *dev);
+u32 gen6_sanitize_rps_pm_mask(struct drm_i915_private *dev_priv, u32 mask);
 void intel_runtime_pm_disable_interrupts(struct drm_i915_private *dev_priv);
 void intel_runtime_pm_enable_interrupts(struct drm_i915_private *dev_priv);
 static inline bool intel_irqs_enabled(struct drm_i915_private *dev_priv)
index 66a1c7f669730ea5ec11909cc983bcc1e6a52d74..03fc7f2ee9d130d21a4fba47d79e5ce8bb62d65a 100644 (file)
@@ -3745,16 +3745,7 @@ static u32 gen6_rps_pm_mask(struct drm_i915_private *dev_priv, u8 val)
        mask |= dev_priv->pm_rps_events & (GEN6_PM_RP_DOWN_EI_EXPIRED | GEN6_PM_RP_UP_EI_EXPIRED);
        mask &= dev_priv->pm_rps_events;
 
-       /* IVB and SNB hard hangs on looping batchbuffer
-        * if GEN6_PM_UP_EI_EXPIRED is masked.
-        */
-       if (INTEL_INFO(dev_priv->dev)->gen <= 7 && !IS_HASWELL(dev_priv->dev))
-               mask |= GEN6_PM_RP_UP_EI_EXPIRED;
-
-       if (IS_GEN8(dev_priv->dev))
-               mask |= GEN8_PMINTR_REDIRECT_TO_NON_DISP;
-
-       return ~mask;
+       return gen6_sanitize_rps_pm_mask(dev_priv, ~mask);
 }
 
 /* gen6_set_rps is called to update the frequency request, but should also be
@@ -3823,7 +3814,8 @@ static void vlv_set_rps_idle(struct drm_i915_private *dev_priv)
                return;
 
        /* Mask turbo interrupt so that they will not come in between */
-       I915_WRITE(GEN6_PMINTRMSK, 0xffffffff);
+       I915_WRITE(GEN6_PMINTRMSK,
+                  gen6_sanitize_rps_pm_mask(dev_priv, ~0));
 
        vlv_force_gfx_clock(dev_priv, true);
 
index ab31848e92cf0780ce0d9416ec3c10b8d86d28b6..5d5e4092d40af42cac11ccf57cf416db5f4f0630 100644 (file)
@@ -49,6 +49,7 @@ config DRM_IMX_IPUV3
 
 config DRM_IMX_HDMI
        tristate "Freescale i.MX DRM HDMI"
+       select DRM_DW_HDMI
        depends on DRM_IMX
        help
          Choose this if you want to use HDMI on i.MX6.
index 582c438d8cbdb941e4fb76ffcb55978cda079828..f3ecd8903d973218a323680de646cff92e5aa785 100644 (file)
@@ -9,4 +9,4 @@ obj-$(CONFIG_DRM_IMX_LDB) += imx-ldb.o
 
 imx-ipuv3-crtc-objs  := ipuv3-crtc.o ipuv3-plane.o
 obj-$(CONFIG_DRM_IMX_IPUV3)    += imx-ipuv3-crtc.o
-obj-$(CONFIG_DRM_IMX_HDMI) += imx-hdmi.o
+obj-$(CONFIG_DRM_IMX_HDMI) += dw_hdmi-imx.o
diff --git a/drivers/gpu/drm/imx/dw_hdmi-imx.c b/drivers/gpu/drm/imx/dw_hdmi-imx.c
new file mode 100644 (file)
index 0000000..121d30c
--- /dev/null
@@ -0,0 +1,258 @@
+/* Copyright (C) 2011-2013 Freescale Semiconductor, Inc.
+ *
+ * derived from imx-hdmi.c(renamed to bridge/dw_hdmi.c now)
+ *
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License version 2 as
+ * published by the Free Software Foundation.
+ */
+#include <linux/module.h>
+#include <linux/platform_device.h>
+#include <linux/component.h>
+#include <linux/mfd/syscon.h>
+#include <linux/mfd/syscon/imx6q-iomuxc-gpr.h>
+#include <drm/bridge/dw_hdmi.h>
+#include <video/imx-ipu-v3.h>
+#include <linux/regmap.h>
+#include <drm/drm_of.h>
+#include <drm/drmP.h>
+#include <drm/drm_crtc_helper.h>
+#include <drm/drm_edid.h>
+#include <drm/drm_encoder_slave.h>
+
+#include "imx-drm.h"
+
+struct imx_hdmi {
+       struct device *dev;
+       struct drm_encoder encoder;
+       struct regmap *regmap;
+};
+
+static const struct dw_hdmi_mpll_config imx_mpll_cfg[] = {
+       {
+               45250000, {
+                       { 0x01e0, 0x0000 },
+                       { 0x21e1, 0x0000 },
+                       { 0x41e2, 0x0000 }
+               },
+       }, {
+               92500000, {
+                       { 0x0140, 0x0005 },
+                       { 0x2141, 0x0005 },
+                       { 0x4142, 0x0005 },
+       },
+       }, {
+               148500000, {
+                       { 0x00a0, 0x000a },
+                       { 0x20a1, 0x000a },
+                       { 0x40a2, 0x000a },
+               },
+       }, {
+               ~0UL, {
+                       { 0x00a0, 0x000a },
+                       { 0x2001, 0x000f },
+                       { 0x4002, 0x000f },
+               },
+       }
+};
+
+static const struct dw_hdmi_curr_ctrl imx_cur_ctr[] = {
+       /*      pixelclk     bpp8    bpp10   bpp12 */
+       {
+               54000000, { 0x091c, 0x091c, 0x06dc },
+       }, {
+               58400000, { 0x091c, 0x06dc, 0x06dc },
+       }, {
+               72000000, { 0x06dc, 0x06dc, 0x091c },
+       }, {
+               74250000, { 0x06dc, 0x0b5c, 0x091c },
+       }, {
+               118800000, { 0x091c, 0x091c, 0x06dc },
+       }, {
+               216000000, { 0x06dc, 0x0b5c, 0x091c },
+       }
+};
+
+static const struct dw_hdmi_sym_term imx_sym_term[] = {
+       /*pixelclk   symbol   term*/
+       { 148500000, 0x800d, 0x0005 },
+       { ~0UL,      0x0000, 0x0000 }
+};
+
+static int dw_hdmi_imx_parse_dt(struct imx_hdmi *hdmi)
+{
+       struct device_node *np = hdmi->dev->of_node;
+
+       hdmi->regmap = syscon_regmap_lookup_by_phandle(np, "gpr");
+       if (IS_ERR(hdmi->regmap)) {
+               dev_err(hdmi->dev, "Unable to get gpr\n");
+               return PTR_ERR(hdmi->regmap);
+       }
+
+       return 0;
+}
+
+static void dw_hdmi_imx_encoder_disable(struct drm_encoder *encoder)
+{
+}
+
+static bool dw_hdmi_imx_encoder_mode_fixup(struct drm_encoder *encoder,
+                                          const struct drm_display_mode *mode,
+                                          struct drm_display_mode *adj_mode)
+{
+       return true;
+}
+
+static void dw_hdmi_imx_encoder_mode_set(struct drm_encoder *encoder,
+                                        struct drm_display_mode *mode,
+                                        struct drm_display_mode *adj_mode)
+{
+}
+
+static void dw_hdmi_imx_encoder_commit(struct drm_encoder *encoder)
+{
+       struct imx_hdmi *hdmi = container_of(encoder, struct imx_hdmi, encoder);
+       int mux = imx_drm_encoder_get_mux_id(hdmi->dev->of_node, encoder);
+
+       regmap_update_bits(hdmi->regmap, IOMUXC_GPR3,
+                          IMX6Q_GPR3_HDMI_MUX_CTL_MASK,
+                          mux << IMX6Q_GPR3_HDMI_MUX_CTL_SHIFT);
+}
+
+static void dw_hdmi_imx_encoder_prepare(struct drm_encoder *encoder)
+{
+       imx_drm_panel_format(encoder, V4L2_PIX_FMT_RGB24);
+}
+
+static struct drm_encoder_helper_funcs dw_hdmi_imx_encoder_helper_funcs = {
+       .mode_fixup = dw_hdmi_imx_encoder_mode_fixup,
+       .mode_set   = dw_hdmi_imx_encoder_mode_set,
+       .prepare    = dw_hdmi_imx_encoder_prepare,
+       .commit     = dw_hdmi_imx_encoder_commit,
+       .disable    = dw_hdmi_imx_encoder_disable,
+};
+
+static struct drm_encoder_funcs dw_hdmi_imx_encoder_funcs = {
+       .destroy = drm_encoder_cleanup,
+};
+
+static struct dw_hdmi_plat_data imx6q_hdmi_drv_data = {
+       .mpll_cfg = imx_mpll_cfg,
+       .cur_ctr  = imx_cur_ctr,
+       .sym_term = imx_sym_term,
+       .dev_type = IMX6Q_HDMI,
+};
+
+static struct dw_hdmi_plat_data imx6dl_hdmi_drv_data = {
+       .mpll_cfg = imx_mpll_cfg,
+       .cur_ctr  = imx_cur_ctr,
+       .sym_term = imx_sym_term,
+       .dev_type = IMX6DL_HDMI,
+};
+
+static const struct of_device_id dw_hdmi_imx_dt_ids[] = {
+       { .compatible = "fsl,imx6q-hdmi",
+         .data = &imx6q_hdmi_drv_data
+       }, {
+         .compatible = "fsl,imx6dl-hdmi",
+         .data = &imx6dl_hdmi_drv_data
+       },
+       {},
+};
+MODULE_DEVICE_TABLE(of, dw_hdmi_imx_dt_ids);
+
+static int dw_hdmi_imx_bind(struct device *dev, struct device *master,
+                           void *data)
+{
+       struct platform_device *pdev = to_platform_device(dev);
+       const struct dw_hdmi_plat_data *plat_data;
+       const struct of_device_id *match;
+       struct drm_device *drm = data;
+       struct drm_encoder *encoder;
+       struct imx_hdmi *hdmi;
+       struct resource *iores;
+       int irq;
+       int ret;
+
+       if (!pdev->dev.of_node)
+               return -ENODEV;
+
+       hdmi = devm_kzalloc(&pdev->dev, sizeof(*hdmi), GFP_KERNEL);
+       if (!hdmi)
+               return -ENOMEM;
+
+       match = of_match_node(dw_hdmi_imx_dt_ids, pdev->dev.of_node);
+       plat_data = match->data;
+       hdmi->dev = &pdev->dev;
+       encoder = &hdmi->encoder;
+
+       irq = platform_get_irq(pdev, 0);
+       if (irq < 0)
+               return irq;
+
+       iores = platform_get_resource(pdev, IORESOURCE_MEM, 0);
+       if (!iores)
+               return -ENXIO;
+
+       platform_set_drvdata(pdev, hdmi);
+
+       encoder->possible_crtcs = drm_of_find_possible_crtcs(drm, dev->of_node);
+       /*
+        * If we failed to find the CRTC(s) which this encoder is
+        * supposed to be connected to, it's because the CRTC has
+        * not been registered yet.  Defer probing, and hope that
+        * the required CRTC is added later.
+        */
+       if (encoder->possible_crtcs == 0)
+               return -EPROBE_DEFER;
+
+       ret = dw_hdmi_imx_parse_dt(hdmi);
+       if (ret < 0)
+               return ret;
+
+       drm_encoder_helper_add(encoder, &dw_hdmi_imx_encoder_helper_funcs);
+       drm_encoder_init(drm, encoder, &dw_hdmi_imx_encoder_funcs,
+                        DRM_MODE_ENCODER_TMDS);
+
+       return dw_hdmi_bind(dev, master, data, encoder, iores, irq, plat_data);
+}
+
+static void dw_hdmi_imx_unbind(struct device *dev, struct device *master,
+                              void *data)
+{
+       return dw_hdmi_unbind(dev, master, data);
+}
+
+static const struct component_ops dw_hdmi_imx_ops = {
+       .bind   = dw_hdmi_imx_bind,
+       .unbind = dw_hdmi_imx_unbind,
+};
+
+static int dw_hdmi_imx_probe(struct platform_device *pdev)
+{
+       return component_add(&pdev->dev, &dw_hdmi_imx_ops);
+}
+
+static int dw_hdmi_imx_remove(struct platform_device *pdev)
+{
+       component_del(&pdev->dev, &dw_hdmi_imx_ops);
+
+       return 0;
+}
+
+static struct platform_driver dw_hdmi_imx_platform_driver = {
+       .probe  = dw_hdmi_imx_probe,
+       .remove = dw_hdmi_imx_remove,
+       .driver = {
+               .name = "dwhdmi-imx",
+               .of_match_table = dw_hdmi_imx_dt_ids,
+       },
+};
+
+module_platform_driver(dw_hdmi_imx_platform_driver);
+
+MODULE_AUTHOR("Andy Yan <andy.yan@rock-chips.com>");
+MODULE_AUTHOR("Yakir Yang <ykk@rock-chips.com>");
+MODULE_DESCRIPTION("IMX6 Specific DW-HDMI Driver Extension");
+MODULE_LICENSE("GPL");
+MODULE_ALIAS("platform:dwhdmi-imx");
index b250130debc87ebd138e8bac964cbadfba776b5d..a002f53aab0e3a3654a722f218be7854ffb70cd4 100644 (file)
@@ -25,6 +25,7 @@
 #include <drm/drm_gem_cma_helper.h>
 #include <drm/drm_fb_cma_helper.h>
 #include <drm/drm_plane_helper.h>
+#include <drm/drm_of.h>
 
 #include "imx-drm.h"
 
@@ -46,7 +47,6 @@ struct imx_drm_crtc {
        struct drm_crtc                         *crtc;
        int                                     pipe;
        struct imx_drm_crtc_helper_funcs        imx_drm_helper_funcs;
-       struct device_node                      *port;
 };
 
 static int legacyfb_depth = 16;
@@ -116,8 +116,7 @@ int imx_drm_panel_format_pins(struct drm_encoder *encoder,
        helper = &imx_crtc->imx_drm_helper_funcs;
        if (helper->set_interface_pix_fmt)
                return helper->set_interface_pix_fmt(encoder->crtc,
-                               encoder->encoder_type, interface_pix_fmt,
-                               hsync_pin, vsync_pin);
+                               interface_pix_fmt, hsync_pin, vsync_pin);
        return 0;
 }
 EXPORT_SYMBOL_GPL(imx_drm_panel_format_pins);
@@ -365,9 +364,10 @@ int imx_drm_add_crtc(struct drm_device *drm, struct drm_crtc *crtc,
 
        imx_drm_crtc->imx_drm_helper_funcs = *imx_drm_helper_funcs;
        imx_drm_crtc->pipe = imxdrm->pipes++;
-       imx_drm_crtc->port = port;
        imx_drm_crtc->crtc = crtc;
 
+       crtc->port = port;
+
        imxdrm->crtc[imx_drm_crtc->pipe] = imx_drm_crtc;
 
        *new_crtc = imx_drm_crtc;
@@ -408,33 +408,28 @@ int imx_drm_remove_crtc(struct imx_drm_crtc *imx_drm_crtc)
 }
 EXPORT_SYMBOL_GPL(imx_drm_remove_crtc);
 
-/*
- * Find the DRM CRTC possible mask for the connected endpoint.
- *
- * The encoder possible masks are defined by their position in the
- * mode_config crtc_list.  This means that CRTCs must not be added
- * or removed once the DRM device has been fully initialised.
- */
-static uint32_t imx_drm_find_crtc_mask(struct imx_drm_device *imxdrm,
-       struct device_node *endpoint)
+int imx_drm_encoder_parse_of(struct drm_device *drm,
+       struct drm_encoder *encoder, struct device_node *np)
 {
-       struct device_node *port;
-       unsigned i;
+       uint32_t crtc_mask = drm_of_find_possible_crtcs(drm, np);
 
-       port = of_graph_get_remote_port(endpoint);
-       if (!port)
-               return 0;
-       of_node_put(port);
+       /*
+        * If we failed to find the CRTC(s) which this encoder is
+        * supposed to be connected to, it's because the CRTC has
+        * not been registered yet.  Defer probing, and hope that
+        * the required CRTC is added later.
+        */
+       if (crtc_mask == 0)
+               return -EPROBE_DEFER;
 
-       for (i = 0; i < MAX_CRTC; i++) {
-               struct imx_drm_crtc *imx_drm_crtc = imxdrm->crtc[i];
+       encoder->possible_crtcs = crtc_mask;
 
-               if (imx_drm_crtc && imx_drm_crtc->port == port)
-                       return drm_crtc_mask(imx_drm_crtc->crtc);
-       }
+       /* FIXME: this is the mask of outputs which can clone this output. */
+       encoder->possible_clones = ~0;
 
        return 0;
 }
+EXPORT_SYMBOL_GPL(imx_drm_encoder_parse_of);
 
 static struct device_node *imx_drm_of_get_next_endpoint(
                const struct device_node *parent, struct device_node *prev)
@@ -445,48 +440,6 @@ static struct device_node *imx_drm_of_get_next_endpoint(
        return node;
 }
 
-int imx_drm_encoder_parse_of(struct drm_device *drm,
-       struct drm_encoder *encoder, struct device_node *np)
-{
-       struct imx_drm_device *imxdrm = drm->dev_private;
-       struct device_node *ep = NULL;
-       uint32_t crtc_mask = 0;
-       int i;
-
-       for (i = 0; ; i++) {
-               u32 mask;
-
-               ep = imx_drm_of_get_next_endpoint(np, ep);
-               if (!ep)
-                       break;
-
-               mask = imx_drm_find_crtc_mask(imxdrm, ep);
-
-               /*
-                * If we failed to find the CRTC(s) which this encoder is
-                * supposed to be connected to, it's because the CRTC has
-                * not been registered yet.  Defer probing, and hope that
-                * the required CRTC is added later.
-                */
-               if (mask == 0)
-                       return -EPROBE_DEFER;
-
-               crtc_mask |= mask;
-       }
-
-       of_node_put(ep);
-       if (i == 0)
-               return -ENOENT;
-
-       encoder->possible_crtcs = crtc_mask;
-
-       /* FIXME: this is the mask of outputs which can clone this output. */
-       encoder->possible_clones = ~0;
-
-       return 0;
-}
-EXPORT_SYMBOL_GPL(imx_drm_encoder_parse_of);
-
 /*
  * @node: device tree node containing encoder input ports
  * @encoder: drm_encoder
@@ -510,7 +463,7 @@ int imx_drm_encoder_get_mux_id(struct device_node *node,
 
                port = of_graph_get_remote_port(ep);
                of_node_put(port);
-               if (port == imx_crtc->port) {
+               if (port == imx_crtc->crtc->port) {
                        ret = of_graph_parse_endpoint(ep, &endpoint);
                        return ret ? ret : endpoint.port;
                }
index 7453ae00c412fbc25a90f6ca783603784edbbae4..3c559ccd6af0042a73564041477cb0950674fe7f 100644 (file)
@@ -17,7 +17,7 @@ int imx_drm_crtc_id(struct imx_drm_crtc *crtc);
 struct imx_drm_crtc_helper_funcs {
        int (*enable_vblank)(struct drm_crtc *crtc);
        void (*disable_vblank)(struct drm_crtc *crtc);
-       int (*set_interface_pix_fmt)(struct drm_crtc *crtc, u32 encoder_type,
+       int (*set_interface_pix_fmt)(struct drm_crtc *crtc,
                        u32 pix_fmt, int hsync_pin, int vsync_pin);
        const struct drm_crtc_helper_funcs *crtc_helper_funcs;
        const struct drm_crtc_funcs *crtc_funcs;
diff --git a/drivers/gpu/drm/imx/imx-hdmi.c b/drivers/gpu/drm/imx/imx-hdmi.c
deleted file mode 100644 (file)
index ddc53e0..0000000
+++ /dev/null
@@ -1,1766 +0,0 @@
-/*
- * Copyright (C) 2011-2013 Freescale Semiconductor, Inc.
- *
- * 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.
- *
- * SH-Mobile High-Definition Multimedia Interface (HDMI) driver
- * for SLISHDMI13T and SLIPHDMIT IP cores
- *
- * Copyright (C) 2010, Guennadi Liakhovetski <g.liakhovetski@gmx.de>
- */
-
-#include <linux/component.h>
-#include <linux/irq.h>
-#include <linux/delay.h>
-#include <linux/err.h>
-#include <linux/clk.h>
-#include <linux/hdmi.h>
-#include <linux/regmap.h>
-#include <linux/mfd/syscon.h>
-#include <linux/mfd/syscon/imx6q-iomuxc-gpr.h>
-#include <linux/of_device.h>
-
-#include <drm/drmP.h>
-#include <drm/drm_crtc_helper.h>
-#include <drm/drm_edid.h>
-#include <drm/drm_encoder_slave.h>
-#include <video/imx-ipu-v3.h>
-
-#include "imx-hdmi.h"
-#include "imx-drm.h"
-
-#define HDMI_EDID_LEN          512
-
-#define RGB                    0
-#define YCBCR444               1
-#define YCBCR422_16BITS                2
-#define YCBCR422_8BITS         3
-#define XVYCC444               4
-
-enum hdmi_datamap {
-       RGB444_8B = 0x01,
-       RGB444_10B = 0x03,
-       RGB444_12B = 0x05,
-       RGB444_16B = 0x07,
-       YCbCr444_8B = 0x09,
-       YCbCr444_10B = 0x0B,
-       YCbCr444_12B = 0x0D,
-       YCbCr444_16B = 0x0F,
-       YCbCr422_8B = 0x16,
-       YCbCr422_10B = 0x14,
-       YCbCr422_12B = 0x12,
-};
-
-enum imx_hdmi_devtype {
-       IMX6Q_HDMI,
-       IMX6DL_HDMI,
-};
-
-static const u16 csc_coeff_default[3][4] = {
-       { 0x2000, 0x0000, 0x0000, 0x0000 },
-       { 0x0000, 0x2000, 0x0000, 0x0000 },
-       { 0x0000, 0x0000, 0x2000, 0x0000 }
-};
-
-static const u16 csc_coeff_rgb_out_eitu601[3][4] = {
-       { 0x2000, 0x6926, 0x74fd, 0x010e },
-       { 0x2000, 0x2cdd, 0x0000, 0x7e9a },
-       { 0x2000, 0x0000, 0x38b4, 0x7e3b }
-};
-
-static const u16 csc_coeff_rgb_out_eitu709[3][4] = {
-       { 0x2000, 0x7106, 0x7a02, 0x00a7 },
-       { 0x2000, 0x3264, 0x0000, 0x7e6d },
-       { 0x2000, 0x0000, 0x3b61, 0x7e25 }
-};
-
-static const u16 csc_coeff_rgb_in_eitu601[3][4] = {
-       { 0x2591, 0x1322, 0x074b, 0x0000 },
-       { 0x6535, 0x2000, 0x7acc, 0x0200 },
-       { 0x6acd, 0x7534, 0x2000, 0x0200 }
-};
-
-static const u16 csc_coeff_rgb_in_eitu709[3][4] = {
-       { 0x2dc5, 0x0d9b, 0x049e, 0x0000 },
-       { 0x62f0, 0x2000, 0x7d11, 0x0200 },
-       { 0x6756, 0x78ab, 0x2000, 0x0200 }
-};
-
-struct hdmi_vmode {
-       bool mdvi;
-       bool mhsyncpolarity;
-       bool mvsyncpolarity;
-       bool minterlaced;
-       bool mdataenablepolarity;
-
-       unsigned int mpixelclock;
-       unsigned int mpixelrepetitioninput;
-       unsigned int mpixelrepetitionoutput;
-};
-
-struct hdmi_data_info {
-       unsigned int enc_in_format;
-       unsigned int enc_out_format;
-       unsigned int enc_color_depth;
-       unsigned int colorimetry;
-       unsigned int pix_repet_factor;
-       unsigned int hdcp_enable;
-       struct hdmi_vmode video_mode;
-};
-
-struct imx_hdmi {
-       struct drm_connector connector;
-       struct drm_encoder encoder;
-
-       enum imx_hdmi_devtype dev_type;
-       struct device *dev;
-       struct clk *isfr_clk;
-       struct clk *iahb_clk;
-
-       struct hdmi_data_info hdmi_data;
-       int vic;
-
-       u8 edid[HDMI_EDID_LEN];
-       bool cable_plugin;
-
-       bool phy_enabled;
-       struct drm_display_mode previous_mode;
-
-       struct regmap *regmap;
-       struct i2c_adapter *ddc;
-       void __iomem *regs;
-
-       unsigned int sample_rate;
-       int ratio;
-};
-
-static void imx_hdmi_set_ipu_di_mux(struct imx_hdmi *hdmi, int ipu_di)
-{
-       regmap_update_bits(hdmi->regmap, IOMUXC_GPR3,
-                          IMX6Q_GPR3_HDMI_MUX_CTL_MASK,
-                          ipu_di << IMX6Q_GPR3_HDMI_MUX_CTL_SHIFT);
-}
-
-static inline void hdmi_writeb(struct imx_hdmi *hdmi, u8 val, int offset)
-{
-       writeb(val, hdmi->regs + offset);
-}
-
-static inline u8 hdmi_readb(struct imx_hdmi *hdmi, int offset)
-{
-       return readb(hdmi->regs + offset);
-}
-
-static void hdmi_modb(struct imx_hdmi *hdmi, u8 data, u8 mask, unsigned reg)
-{
-       u8 val = hdmi_readb(hdmi, reg) & ~mask;
-
-       val |= data & mask;
-       hdmi_writeb(hdmi, val, reg);
-}
-
-static void hdmi_mask_writeb(struct imx_hdmi *hdmi, u8 data, unsigned int reg,
-                     u8 shift, u8 mask)
-{
-       hdmi_modb(hdmi, data << shift, mask, reg);
-}
-
-static void hdmi_set_clock_regenerator_n(struct imx_hdmi *hdmi,
-                                        unsigned int value)
-{
-       hdmi_writeb(hdmi, value & 0xff, HDMI_AUD_N1);
-       hdmi_writeb(hdmi, (value >> 8) & 0xff, HDMI_AUD_N2);
-       hdmi_writeb(hdmi, (value >> 16) & 0x0f, HDMI_AUD_N3);
-
-       /* nshift factor = 0 */
-       hdmi_modb(hdmi, 0, HDMI_AUD_CTS3_N_SHIFT_MASK, HDMI_AUD_CTS3);
-}
-
-static void hdmi_regenerate_cts(struct imx_hdmi *hdmi, unsigned int cts)
-{
-       /* Must be set/cleared first */
-       hdmi_modb(hdmi, 0, HDMI_AUD_CTS3_CTS_MANUAL, HDMI_AUD_CTS3);
-
-       hdmi_writeb(hdmi, cts & 0xff, HDMI_AUD_CTS1);
-       hdmi_writeb(hdmi, (cts >> 8) & 0xff, HDMI_AUD_CTS2);
-       hdmi_writeb(hdmi, ((cts >> 16) & HDMI_AUD_CTS3_AUDCTS19_16_MASK) |
-                   HDMI_AUD_CTS3_CTS_MANUAL, HDMI_AUD_CTS3);
-}
-
-static unsigned int hdmi_compute_n(unsigned int freq, unsigned long pixel_clk,
-                                  unsigned int ratio)
-{
-       unsigned int n = (128 * freq) / 1000;
-
-       switch (freq) {
-       case 32000:
-               if (pixel_clk == 25170000)
-                       n = (ratio == 150) ? 9152 : 4576;
-               else if (pixel_clk == 27020000)
-                       n = (ratio == 150) ? 8192 : 4096;
-               else if (pixel_clk == 74170000 || pixel_clk == 148350000)
-                       n = 11648;
-               else
-                       n = 4096;
-               break;
-
-       case 44100:
-               if (pixel_clk == 25170000)
-                       n = 7007;
-               else if (pixel_clk == 74170000)
-                       n = 17836;
-               else if (pixel_clk == 148350000)
-                       n = (ratio == 150) ? 17836 : 8918;
-               else
-                       n = 6272;
-               break;
-
-       case 48000:
-               if (pixel_clk == 25170000)
-                       n = (ratio == 150) ? 9152 : 6864;
-               else if (pixel_clk == 27020000)
-                       n = (ratio == 150) ? 8192 : 6144;
-               else if (pixel_clk == 74170000)
-                       n = 11648;
-               else if (pixel_clk == 148350000)
-                       n = (ratio == 150) ? 11648 : 5824;
-               else
-                       n = 6144;
-               break;
-
-       case 88200:
-               n = hdmi_compute_n(44100, pixel_clk, ratio) * 2;
-               break;
-
-       case 96000:
-               n = hdmi_compute_n(48000, pixel_clk, ratio) * 2;
-               break;
-
-       case 176400:
-               n = hdmi_compute_n(44100, pixel_clk, ratio) * 4;
-               break;
-
-       case 192000:
-               n = hdmi_compute_n(48000, pixel_clk, ratio) * 4;
-               break;
-
-       default:
-               break;
-       }
-
-       return n;
-}
-
-static unsigned int hdmi_compute_cts(unsigned int freq, unsigned long pixel_clk,
-                                    unsigned int ratio)
-{
-       unsigned int cts = 0;
-
-       pr_debug("%s: freq: %d pixel_clk: %ld ratio: %d\n", __func__, freq,
-                pixel_clk, ratio);
-
-       switch (freq) {
-       case 32000:
-               if (pixel_clk == 297000000) {
-                       cts = 222750;
-                       break;
-               }
-       case 48000:
-       case 96000:
-       case 192000:
-               switch (pixel_clk) {
-               case 25200000:
-               case 27000000:
-               case 54000000:
-               case 74250000:
-               case 148500000:
-                       cts = pixel_clk / 1000;
-                       break;
-               case 297000000:
-                       cts = 247500;
-                       break;
-               /*
-                * All other TMDS clocks are not supported by
-                * DWC_hdmi_tx. The TMDS clocks divided or
-                * multiplied by 1,001 coefficients are not
-                * supported.
-                */
-               default:
-                       break;
-               }
-               break;
-       case 44100:
-       case 88200:
-       case 176400:
-               switch (pixel_clk) {
-               case 25200000:
-                       cts = 28000;
-                       break;
-               case 27000000:
-                       cts = 30000;
-                       break;
-               case 54000000:
-                       cts = 60000;
-                       break;
-               case 74250000:
-                       cts = 82500;
-                       break;
-               case 148500000:
-                       cts = 165000;
-                       break;
-               case 297000000:
-                       cts = 247500;
-                       break;
-               default:
-                       break;
-               }
-               break;
-       default:
-               break;
-       }
-       if (ratio == 100)
-               return cts;
-       return (cts * ratio) / 100;
-}
-
-static void hdmi_set_clk_regenerator(struct imx_hdmi *hdmi,
-       unsigned long pixel_clk)
-{
-       unsigned int clk_n, clk_cts;
-
-       clk_n = hdmi_compute_n(hdmi->sample_rate, pixel_clk,
-                              hdmi->ratio);
-       clk_cts = hdmi_compute_cts(hdmi->sample_rate, pixel_clk,
-                                  hdmi->ratio);
-
-       if (!clk_cts) {
-               dev_dbg(hdmi->dev, "%s: pixel clock not supported: %lu\n",
-                        __func__, pixel_clk);
-               return;
-       }
-
-       dev_dbg(hdmi->dev, "%s: samplerate=%d  ratio=%d  pixelclk=%lu  N=%d cts=%d\n",
-               __func__, hdmi->sample_rate, hdmi->ratio,
-               pixel_clk, clk_n, clk_cts);
-
-       hdmi_set_clock_regenerator_n(hdmi, clk_n);
-       hdmi_regenerate_cts(hdmi, clk_cts);
-}
-
-static void hdmi_init_clk_regenerator(struct imx_hdmi *hdmi)
-{
-       hdmi_set_clk_regenerator(hdmi, 74250000);
-}
-
-static void hdmi_clk_regenerator_update_pixel_clock(struct imx_hdmi *hdmi)
-{
-       hdmi_set_clk_regenerator(hdmi, hdmi->hdmi_data.video_mode.mpixelclock);
-}
-
-/*
- * this submodule is responsible for the video data synchronization.
- * for example, for RGB 4:4:4 input, the data map is defined as
- *                     pin{47~40} <==> R[7:0]
- *                     pin{31~24} <==> G[7:0]
- *                     pin{15~8}  <==> B[7:0]
- */
-static void hdmi_video_sample(struct imx_hdmi *hdmi)
-{
-       int color_format = 0;
-       u8 val;
-
-       if (hdmi->hdmi_data.enc_in_format == RGB) {
-               if (hdmi->hdmi_data.enc_color_depth == 8)
-                       color_format = 0x01;
-               else if (hdmi->hdmi_data.enc_color_depth == 10)
-                       color_format = 0x03;
-               else if (hdmi->hdmi_data.enc_color_depth == 12)
-                       color_format = 0x05;
-               else if (hdmi->hdmi_data.enc_color_depth == 16)
-                       color_format = 0x07;
-               else
-                       return;
-       } else if (hdmi->hdmi_data.enc_in_format == YCBCR444) {
-               if (hdmi->hdmi_data.enc_color_depth == 8)
-                       color_format = 0x09;
-               else if (hdmi->hdmi_data.enc_color_depth == 10)
-                       color_format = 0x0B;
-               else if (hdmi->hdmi_data.enc_color_depth == 12)
-                       color_format = 0x0D;
-               else if (hdmi->hdmi_data.enc_color_depth == 16)
-                       color_format = 0x0F;
-               else
-                       return;
-       } else if (hdmi->hdmi_data.enc_in_format == YCBCR422_8BITS) {
-               if (hdmi->hdmi_data.enc_color_depth == 8)
-                       color_format = 0x16;
-               else if (hdmi->hdmi_data.enc_color_depth == 10)
-                       color_format = 0x14;
-               else if (hdmi->hdmi_data.enc_color_depth == 12)
-                       color_format = 0x12;
-               else
-                       return;
-       }
-
-       val = HDMI_TX_INVID0_INTERNAL_DE_GENERATOR_DISABLE |
-               ((color_format << HDMI_TX_INVID0_VIDEO_MAPPING_OFFSET) &
-               HDMI_TX_INVID0_VIDEO_MAPPING_MASK);
-       hdmi_writeb(hdmi, val, HDMI_TX_INVID0);
-
-       /* Enable TX stuffing: When DE is inactive, fix the output data to 0 */
-       val = HDMI_TX_INSTUFFING_BDBDATA_STUFFING_ENABLE |
-               HDMI_TX_INSTUFFING_RCRDATA_STUFFING_ENABLE |
-               HDMI_TX_INSTUFFING_GYDATA_STUFFING_ENABLE;
-       hdmi_writeb(hdmi, val, HDMI_TX_INSTUFFING);
-       hdmi_writeb(hdmi, 0x0, HDMI_TX_GYDATA0);
-       hdmi_writeb(hdmi, 0x0, HDMI_TX_GYDATA1);
-       hdmi_writeb(hdmi, 0x0, HDMI_TX_RCRDATA0);
-       hdmi_writeb(hdmi, 0x0, HDMI_TX_RCRDATA1);
-       hdmi_writeb(hdmi, 0x0, HDMI_TX_BCBDATA0);
-       hdmi_writeb(hdmi, 0x0, HDMI_TX_BCBDATA1);
-}
-
-static int is_color_space_conversion(struct imx_hdmi *hdmi)
-{
-       return hdmi->hdmi_data.enc_in_format != hdmi->hdmi_data.enc_out_format;
-}
-
-static int is_color_space_decimation(struct imx_hdmi *hdmi)
-{
-       if (hdmi->hdmi_data.enc_out_format != YCBCR422_8BITS)
-               return 0;
-       if (hdmi->hdmi_data.enc_in_format == RGB ||
-           hdmi->hdmi_data.enc_in_format == YCBCR444)
-               return 1;
-       return 0;
-}
-
-static int is_color_space_interpolation(struct imx_hdmi *hdmi)
-{
-       if (hdmi->hdmi_data.enc_in_format != YCBCR422_8BITS)
-               return 0;
-       if (hdmi->hdmi_data.enc_out_format == RGB ||
-           hdmi->hdmi_data.enc_out_format == YCBCR444)
-               return 1;
-       return 0;
-}
-
-static void imx_hdmi_update_csc_coeffs(struct imx_hdmi *hdmi)
-{
-       const u16 (*csc_coeff)[3][4] = &csc_coeff_default;
-       unsigned i;
-       u32 csc_scale = 1;
-
-       if (is_color_space_conversion(hdmi)) {
-               if (hdmi->hdmi_data.enc_out_format == RGB) {
-                       if (hdmi->hdmi_data.colorimetry ==
-                                       HDMI_COLORIMETRY_ITU_601)
-                               csc_coeff = &csc_coeff_rgb_out_eitu601;
-                       else
-                               csc_coeff = &csc_coeff_rgb_out_eitu709;
-               } else if (hdmi->hdmi_data.enc_in_format == RGB) {
-                       if (hdmi->hdmi_data.colorimetry ==
-                                       HDMI_COLORIMETRY_ITU_601)
-                               csc_coeff = &csc_coeff_rgb_in_eitu601;
-                       else
-                               csc_coeff = &csc_coeff_rgb_in_eitu709;
-                       csc_scale = 0;
-               }
-       }
-
-       /* The CSC registers are sequential, alternating MSB then LSB */
-       for (i = 0; i < ARRAY_SIZE(csc_coeff_default[0]); i++) {
-               u16 coeff_a = (*csc_coeff)[0][i];
-               u16 coeff_b = (*csc_coeff)[1][i];
-               u16 coeff_c = (*csc_coeff)[2][i];
-
-               hdmi_writeb(hdmi, coeff_a & 0xff,
-                       HDMI_CSC_COEF_A1_LSB + i * 2);
-               hdmi_writeb(hdmi, coeff_a >> 8, HDMI_CSC_COEF_A1_MSB + i * 2);
-               hdmi_writeb(hdmi, coeff_b & 0xff, HDMI_CSC_COEF_B1_LSB + i * 2);
-               hdmi_writeb(hdmi, coeff_b >> 8, HDMI_CSC_COEF_B1_MSB + i * 2);
-               hdmi_writeb(hdmi, coeff_c & 0xff,
-                       HDMI_CSC_COEF_C1_LSB + i * 2);
-               hdmi_writeb(hdmi, coeff_c >> 8, HDMI_CSC_COEF_C1_MSB + i * 2);
-       }
-
-       hdmi_modb(hdmi, csc_scale, HDMI_CSC_SCALE_CSCSCALE_MASK,
-                 HDMI_CSC_SCALE);
-}
-
-static void hdmi_video_csc(struct imx_hdmi *hdmi)
-{
-       int color_depth = 0;
-       int interpolation = HDMI_CSC_CFG_INTMODE_DISABLE;
-       int decimation = 0;
-
-       /* YCC422 interpolation to 444 mode */
-       if (is_color_space_interpolation(hdmi))
-               interpolation = HDMI_CSC_CFG_INTMODE_CHROMA_INT_FORMULA1;
-       else if (is_color_space_decimation(hdmi))
-               decimation = HDMI_CSC_CFG_DECMODE_CHROMA_INT_FORMULA3;
-
-       if (hdmi->hdmi_data.enc_color_depth == 8)
-               color_depth = HDMI_CSC_SCALE_CSC_COLORDE_PTH_24BPP;
-       else if (hdmi->hdmi_data.enc_color_depth == 10)
-               color_depth = HDMI_CSC_SCALE_CSC_COLORDE_PTH_30BPP;
-       else if (hdmi->hdmi_data.enc_color_depth == 12)
-               color_depth = HDMI_CSC_SCALE_CSC_COLORDE_PTH_36BPP;
-       else if (hdmi->hdmi_data.enc_color_depth == 16)
-               color_depth = HDMI_CSC_SCALE_CSC_COLORDE_PTH_48BPP;
-       else
-               return;
-
-       /* Configure the CSC registers */
-       hdmi_writeb(hdmi, interpolation | decimation, HDMI_CSC_CFG);
-       hdmi_modb(hdmi, color_depth, HDMI_CSC_SCALE_CSC_COLORDE_PTH_MASK,
-                 HDMI_CSC_SCALE);
-
-       imx_hdmi_update_csc_coeffs(hdmi);
-}
-
-/*
- * HDMI video packetizer is used to packetize the data.
- * for example, if input is YCC422 mode or repeater is used,
- * data should be repacked this module can be bypassed.
- */
-static void hdmi_video_packetize(struct imx_hdmi *hdmi)
-{
-       unsigned int color_depth = 0;
-       unsigned int remap_size = HDMI_VP_REMAP_YCC422_16bit;
-       unsigned int output_select = HDMI_VP_CONF_OUTPUT_SELECTOR_PP;
-       struct hdmi_data_info *hdmi_data = &hdmi->hdmi_data;
-       u8 val, vp_conf;
-
-       if (hdmi_data->enc_out_format == RGB
-               || hdmi_data->enc_out_format == YCBCR444) {
-               if (!hdmi_data->enc_color_depth)
-                       output_select = HDMI_VP_CONF_OUTPUT_SELECTOR_BYPASS;
-               else if (hdmi_data->enc_color_depth == 8) {
-                       color_depth = 4;
-                       output_select = HDMI_VP_CONF_OUTPUT_SELECTOR_BYPASS;
-               } else if (hdmi_data->enc_color_depth == 10)
-                       color_depth = 5;
-               else if (hdmi_data->enc_color_depth == 12)
-                       color_depth = 6;
-               else if (hdmi_data->enc_color_depth == 16)
-                       color_depth = 7;
-               else
-                       return;
-       } else if (hdmi_data->enc_out_format == YCBCR422_8BITS) {
-               if (!hdmi_data->enc_color_depth ||
-                   hdmi_data->enc_color_depth == 8)
-                       remap_size = HDMI_VP_REMAP_YCC422_16bit;
-               else if (hdmi_data->enc_color_depth == 10)
-                       remap_size = HDMI_VP_REMAP_YCC422_20bit;
-               else if (hdmi_data->enc_color_depth == 12)
-                       remap_size = HDMI_VP_REMAP_YCC422_24bit;
-               else
-                       return;
-               output_select = HDMI_VP_CONF_OUTPUT_SELECTOR_YCC422;
-       } else
-               return;
-
-       /* set the packetizer registers */
-       val = ((color_depth << HDMI_VP_PR_CD_COLOR_DEPTH_OFFSET) &
-               HDMI_VP_PR_CD_COLOR_DEPTH_MASK) |
-               ((hdmi_data->pix_repet_factor <<
-               HDMI_VP_PR_CD_DESIRED_PR_FACTOR_OFFSET) &
-               HDMI_VP_PR_CD_DESIRED_PR_FACTOR_MASK);
-       hdmi_writeb(hdmi, val, HDMI_VP_PR_CD);
-
-       hdmi_modb(hdmi, HDMI_VP_STUFF_PR_STUFFING_STUFFING_MODE,
-                 HDMI_VP_STUFF_PR_STUFFING_MASK, HDMI_VP_STUFF);
-
-       /* Data from pixel repeater block */
-       if (hdmi_data->pix_repet_factor > 1) {
-               vp_conf = HDMI_VP_CONF_PR_EN_ENABLE |
-                         HDMI_VP_CONF_BYPASS_SELECT_PIX_REPEATER;
-       } else { /* data from packetizer block */
-               vp_conf = HDMI_VP_CONF_PR_EN_DISABLE |
-                         HDMI_VP_CONF_BYPASS_SELECT_VID_PACKETIZER;
-       }
-
-       hdmi_modb(hdmi, vp_conf,
-                 HDMI_VP_CONF_PR_EN_MASK |
-                 HDMI_VP_CONF_BYPASS_SELECT_MASK, HDMI_VP_CONF);
-
-       hdmi_modb(hdmi, 1 << HDMI_VP_STUFF_IDEFAULT_PHASE_OFFSET,
-                 HDMI_VP_STUFF_IDEFAULT_PHASE_MASK, HDMI_VP_STUFF);
-
-       hdmi_writeb(hdmi, remap_size, HDMI_VP_REMAP);
-
-       if (output_select == HDMI_VP_CONF_OUTPUT_SELECTOR_PP) {
-               vp_conf = HDMI_VP_CONF_BYPASS_EN_DISABLE |
-                         HDMI_VP_CONF_PP_EN_ENABLE |
-                         HDMI_VP_CONF_YCC422_EN_DISABLE;
-       } else if (output_select == HDMI_VP_CONF_OUTPUT_SELECTOR_YCC422) {
-               vp_conf = HDMI_VP_CONF_BYPASS_EN_DISABLE |
-                         HDMI_VP_CONF_PP_EN_DISABLE |
-                         HDMI_VP_CONF_YCC422_EN_ENABLE;
-       } else if (output_select == HDMI_VP_CONF_OUTPUT_SELECTOR_BYPASS) {
-               vp_conf = HDMI_VP_CONF_BYPASS_EN_ENABLE |
-                         HDMI_VP_CONF_PP_EN_DISABLE |
-                         HDMI_VP_CONF_YCC422_EN_DISABLE;
-       } else {
-               return;
-       }
-
-       hdmi_modb(hdmi, vp_conf,
-                 HDMI_VP_CONF_BYPASS_EN_MASK | HDMI_VP_CONF_PP_EN_ENMASK |
-                 HDMI_VP_CONF_YCC422_EN_MASK, HDMI_VP_CONF);
-
-       hdmi_modb(hdmi, HDMI_VP_STUFF_PP_STUFFING_STUFFING_MODE |
-                       HDMI_VP_STUFF_YCC422_STUFFING_STUFFING_MODE,
-                 HDMI_VP_STUFF_PP_STUFFING_MASK |
-                 HDMI_VP_STUFF_YCC422_STUFFING_MASK, HDMI_VP_STUFF);
-
-       hdmi_modb(hdmi, output_select, HDMI_VP_CONF_OUTPUT_SELECTOR_MASK,
-                 HDMI_VP_CONF);
-}
-
-static inline void hdmi_phy_test_clear(struct imx_hdmi *hdmi,
-                                               unsigned char bit)
-{
-       hdmi_modb(hdmi, bit << HDMI_PHY_TST0_TSTCLR_OFFSET,
-                 HDMI_PHY_TST0_TSTCLR_MASK, HDMI_PHY_TST0);
-}
-
-static inline void hdmi_phy_test_enable(struct imx_hdmi *hdmi,
-                                               unsigned char bit)
-{
-       hdmi_modb(hdmi, bit << HDMI_PHY_TST0_TSTEN_OFFSET,
-                 HDMI_PHY_TST0_TSTEN_MASK, HDMI_PHY_TST0);
-}
-
-static inline void hdmi_phy_test_clock(struct imx_hdmi *hdmi,
-                                               unsigned char bit)
-{
-       hdmi_modb(hdmi, bit << HDMI_PHY_TST0_TSTCLK_OFFSET,
-                 HDMI_PHY_TST0_TSTCLK_MASK, HDMI_PHY_TST0);
-}
-
-static inline void hdmi_phy_test_din(struct imx_hdmi *hdmi,
-                                               unsigned char bit)
-{
-       hdmi_writeb(hdmi, bit, HDMI_PHY_TST1);
-}
-
-static inline void hdmi_phy_test_dout(struct imx_hdmi *hdmi,
-                                               unsigned char bit)
-{
-       hdmi_writeb(hdmi, bit, HDMI_PHY_TST2);
-}
-
-static bool hdmi_phy_wait_i2c_done(struct imx_hdmi *hdmi, int msec)
-{
-       while ((hdmi_readb(hdmi, HDMI_IH_I2CMPHY_STAT0) & 0x3) == 0) {
-               if (msec-- == 0)
-                       return false;
-               udelay(1000);
-       }
-       return true;
-}
-
-static void __hdmi_phy_i2c_write(struct imx_hdmi *hdmi, unsigned short data,
-                             unsigned char addr)
-{
-       hdmi_writeb(hdmi, 0xFF, HDMI_IH_I2CMPHY_STAT0);
-       hdmi_writeb(hdmi, addr, HDMI_PHY_I2CM_ADDRESS_ADDR);
-       hdmi_writeb(hdmi, (unsigned char)(data >> 8),
-               HDMI_PHY_I2CM_DATAO_1_ADDR);
-       hdmi_writeb(hdmi, (unsigned char)(data >> 0),
-               HDMI_PHY_I2CM_DATAO_0_ADDR);
-       hdmi_writeb(hdmi, HDMI_PHY_I2CM_OPERATION_ADDR_WRITE,
-               HDMI_PHY_I2CM_OPERATION_ADDR);
-       hdmi_phy_wait_i2c_done(hdmi, 1000);
-}
-
-static int hdmi_phy_i2c_write(struct imx_hdmi *hdmi, unsigned short data,
-                                    unsigned char addr)
-{
-       __hdmi_phy_i2c_write(hdmi, data, addr);
-       return 0;
-}
-
-static void imx_hdmi_phy_enable_power(struct imx_hdmi *hdmi, u8 enable)
-{
-       hdmi_mask_writeb(hdmi, enable, HDMI_PHY_CONF0,
-                        HDMI_PHY_CONF0_PDZ_OFFSET,
-                        HDMI_PHY_CONF0_PDZ_MASK);
-}
-
-static void imx_hdmi_phy_enable_tmds(struct imx_hdmi *hdmi, u8 enable)
-{
-       hdmi_mask_writeb(hdmi, enable, HDMI_PHY_CONF0,
-                        HDMI_PHY_CONF0_ENTMDS_OFFSET,
-                        HDMI_PHY_CONF0_ENTMDS_MASK);
-}
-
-static void imx_hdmi_phy_gen2_pddq(struct imx_hdmi *hdmi, u8 enable)
-{
-       hdmi_mask_writeb(hdmi, enable, HDMI_PHY_CONF0,
-                        HDMI_PHY_CONF0_GEN2_PDDQ_OFFSET,
-                        HDMI_PHY_CONF0_GEN2_PDDQ_MASK);
-}
-
-static void imx_hdmi_phy_gen2_txpwron(struct imx_hdmi *hdmi, u8 enable)
-{
-       hdmi_mask_writeb(hdmi, enable, HDMI_PHY_CONF0,
-                        HDMI_PHY_CONF0_GEN2_TXPWRON_OFFSET,
-                        HDMI_PHY_CONF0_GEN2_TXPWRON_MASK);
-}
-
-static void imx_hdmi_phy_sel_data_en_pol(struct imx_hdmi *hdmi, u8 enable)
-{
-       hdmi_mask_writeb(hdmi, enable, HDMI_PHY_CONF0,
-                        HDMI_PHY_CONF0_SELDATAENPOL_OFFSET,
-                        HDMI_PHY_CONF0_SELDATAENPOL_MASK);
-}
-
-static void imx_hdmi_phy_sel_interface_control(struct imx_hdmi *hdmi, u8 enable)
-{
-       hdmi_mask_writeb(hdmi, enable, HDMI_PHY_CONF0,
-                        HDMI_PHY_CONF0_SELDIPIF_OFFSET,
-                        HDMI_PHY_CONF0_SELDIPIF_MASK);
-}
-
-enum {
-       RES_8,
-       RES_10,
-       RES_12,
-       RES_MAX,
-};
-
-struct mpll_config {
-       unsigned long mpixelclock;
-       struct {
-               u16 cpce;
-               u16 gmp;
-       } res[RES_MAX];
-};
-
-static const struct mpll_config mpll_config[] = {
-       {
-               45250000, {
-                       { 0x01e0, 0x0000 },
-                       { 0x21e1, 0x0000 },
-                       { 0x41e2, 0x0000 }
-               },
-       }, {
-               92500000, {
-                       { 0x0140, 0x0005 },
-                       { 0x2141, 0x0005 },
-                       { 0x4142, 0x0005 },
-               },
-       }, {
-               148500000, {
-                       { 0x00a0, 0x000a },
-                       { 0x20a1, 0x000a },
-                       { 0x40a2, 0x000a },
-               },
-       }, {
-               ~0UL, {
-                       { 0x00a0, 0x000a },
-                       { 0x2001, 0x000f },
-                       { 0x4002, 0x000f },
-               },
-       }
-};
-
-struct curr_ctrl {
-       unsigned long mpixelclock;
-       u16 curr[RES_MAX];
-};
-
-static const struct curr_ctrl curr_ctrl[] = {
-       /*      pixelclk     bpp8    bpp10   bpp12 */
-       {
-                54000000, { 0x091c, 0x091c, 0x06dc },
-       }, {
-                58400000, { 0x091c, 0x06dc, 0x06dc },
-       }, {
-                72000000, { 0x06dc, 0x06dc, 0x091c },
-       }, {
-                74250000, { 0x06dc, 0x0b5c, 0x091c },
-       }, {
-               118800000, { 0x091c, 0x091c, 0x06dc },
-       }, {
-               216000000, { 0x06dc, 0x0b5c, 0x091c },
-       }
-};
-
-static int hdmi_phy_configure(struct imx_hdmi *hdmi, unsigned char prep,
-                             unsigned char res, int cscon)
-{
-       unsigned res_idx, i;
-       u8 val, msec;
-
-       if (prep)
-               return -EINVAL;
-
-       switch (res) {
-       case 0: /* color resolution 0 is 8 bit colour depth */
-       case 8:
-               res_idx = RES_8;
-               break;
-       case 10:
-               res_idx = RES_10;
-               break;
-       case 12:
-               res_idx = RES_12;
-               break;
-       default:
-               return -EINVAL;
-       }
-
-       /* Enable csc path */
-       if (cscon)
-               val = HDMI_MC_FLOWCTRL_FEED_THROUGH_OFF_CSC_IN_PATH;
-       else
-               val = HDMI_MC_FLOWCTRL_FEED_THROUGH_OFF_CSC_BYPASS;
-
-       hdmi_writeb(hdmi, val, HDMI_MC_FLOWCTRL);
-
-       /* gen2 tx power off */
-       imx_hdmi_phy_gen2_txpwron(hdmi, 0);
-
-       /* gen2 pddq */
-       imx_hdmi_phy_gen2_pddq(hdmi, 1);
-
-       /* PHY reset */
-       hdmi_writeb(hdmi, HDMI_MC_PHYRSTZ_DEASSERT, HDMI_MC_PHYRSTZ);
-       hdmi_writeb(hdmi, HDMI_MC_PHYRSTZ_ASSERT, HDMI_MC_PHYRSTZ);
-
-       hdmi_writeb(hdmi, HDMI_MC_HEACPHY_RST_ASSERT, HDMI_MC_HEACPHY_RST);
-
-       hdmi_phy_test_clear(hdmi, 1);
-       hdmi_writeb(hdmi, HDMI_PHY_I2CM_SLAVE_ADDR_PHY_GEN2,
-                       HDMI_PHY_I2CM_SLAVE_ADDR);
-       hdmi_phy_test_clear(hdmi, 0);
-
-       /* PLL/MPLL Cfg - always match on final entry */
-       for (i = 0; i < ARRAY_SIZE(mpll_config) - 1; i++)
-               if (hdmi->hdmi_data.video_mode.mpixelclock <=
-                   mpll_config[i].mpixelclock)
-                       break;
-
-       hdmi_phy_i2c_write(hdmi, mpll_config[i].res[res_idx].cpce, 0x06);
-       hdmi_phy_i2c_write(hdmi, mpll_config[i].res[res_idx].gmp, 0x15);
-
-       for (i = 0; i < ARRAY_SIZE(curr_ctrl); i++)
-               if (hdmi->hdmi_data.video_mode.mpixelclock <=
-                   curr_ctrl[i].mpixelclock)
-                       break;
-
-       if (i >= ARRAY_SIZE(curr_ctrl)) {
-               dev_err(hdmi->dev,
-                               "Pixel clock %d - unsupported by HDMI\n",
-                               hdmi->hdmi_data.video_mode.mpixelclock);
-               return -EINVAL;
-       }
-
-       /* CURRCTRL */
-       hdmi_phy_i2c_write(hdmi, curr_ctrl[i].curr[res_idx], 0x10);
-
-       hdmi_phy_i2c_write(hdmi, 0x0000, 0x13);  /* PLLPHBYCTRL */
-       hdmi_phy_i2c_write(hdmi, 0x0006, 0x17);
-       /* RESISTANCE TERM 133Ohm Cfg */
-       hdmi_phy_i2c_write(hdmi, 0x0005, 0x19);  /* TXTERM */
-       /* PREEMP Cgf 0.00 */
-       hdmi_phy_i2c_write(hdmi, 0x800d, 0x09);  /* CKSYMTXCTRL */
-       /* TX/CK LVL 10 */
-       hdmi_phy_i2c_write(hdmi, 0x01ad, 0x0E);  /* VLEVCTRL */
-       /* REMOVE CLK TERM */
-       hdmi_phy_i2c_write(hdmi, 0x8000, 0x05);  /* CKCALCTRL */
-
-       imx_hdmi_phy_enable_power(hdmi, 1);
-
-       /* toggle TMDS enable */
-       imx_hdmi_phy_enable_tmds(hdmi, 0);
-       imx_hdmi_phy_enable_tmds(hdmi, 1);
-
-       /* gen2 tx power on */
-       imx_hdmi_phy_gen2_txpwron(hdmi, 1);
-       imx_hdmi_phy_gen2_pddq(hdmi, 0);
-
-       /*Wait for PHY PLL lock */
-       msec = 5;
-       do {
-               val = hdmi_readb(hdmi, HDMI_PHY_STAT0) & HDMI_PHY_TX_PHY_LOCK;
-               if (!val)
-                       break;
-
-               if (msec == 0) {
-                       dev_err(hdmi->dev, "PHY PLL not locked\n");
-                       return -ETIMEDOUT;
-               }
-
-               udelay(1000);
-               msec--;
-       } while (1);
-
-       return 0;
-}
-
-static int imx_hdmi_phy_init(struct imx_hdmi *hdmi)
-{
-       int i, ret;
-       bool cscon = false;
-
-       /*check csc whether needed activated in HDMI mode */
-       cscon = (is_color_space_conversion(hdmi) &&
-                       !hdmi->hdmi_data.video_mode.mdvi);
-
-       /* HDMI Phy spec says to do the phy initialization sequence twice */
-       for (i = 0; i < 2; i++) {
-               imx_hdmi_phy_sel_data_en_pol(hdmi, 1);
-               imx_hdmi_phy_sel_interface_control(hdmi, 0);
-               imx_hdmi_phy_enable_tmds(hdmi, 0);
-               imx_hdmi_phy_enable_power(hdmi, 0);
-
-               /* Enable CSC */
-               ret = hdmi_phy_configure(hdmi, 0, 8, cscon);
-               if (ret)
-                       return ret;
-       }
-
-       hdmi->phy_enabled = true;
-       return 0;
-}
-
-static void hdmi_tx_hdcp_config(struct imx_hdmi *hdmi)
-{
-       u8 de;
-
-       if (hdmi->hdmi_data.video_mode.mdataenablepolarity)
-               de = HDMI_A_VIDPOLCFG_DATAENPOL_ACTIVE_HIGH;
-       else
-               de = HDMI_A_VIDPOLCFG_DATAENPOL_ACTIVE_LOW;
-
-       /* disable rx detect */
-       hdmi_modb(hdmi, HDMI_A_HDCPCFG0_RXDETECT_DISABLE,
-                 HDMI_A_HDCPCFG0_RXDETECT_MASK, HDMI_A_HDCPCFG0);
-
-       hdmi_modb(hdmi, de, HDMI_A_VIDPOLCFG_DATAENPOL_MASK, HDMI_A_VIDPOLCFG);
-
-       hdmi_modb(hdmi, HDMI_A_HDCPCFG1_ENCRYPTIONDISABLE_DISABLE,
-                 HDMI_A_HDCPCFG1_ENCRYPTIONDISABLE_MASK, HDMI_A_HDCPCFG1);
-}
-
-static void hdmi_config_AVI(struct imx_hdmi *hdmi)
-{
-       u8 val, pix_fmt, under_scan;
-       u8 act_ratio, coded_ratio, colorimetry, ext_colorimetry;
-       bool aspect_16_9;
-
-       aspect_16_9 = false; /* FIXME */
-
-       /* AVI Data Byte 1 */
-       if (hdmi->hdmi_data.enc_out_format == YCBCR444)
-               pix_fmt = HDMI_FC_AVICONF0_PIX_FMT_YCBCR444;
-       else if (hdmi->hdmi_data.enc_out_format == YCBCR422_8BITS)
-               pix_fmt = HDMI_FC_AVICONF0_PIX_FMT_YCBCR422;
-       else
-               pix_fmt = HDMI_FC_AVICONF0_PIX_FMT_RGB;
-
-               under_scan =  HDMI_FC_AVICONF0_SCAN_INFO_NODATA;
-
-       /*
-        * Active format identification data is present in the AVI InfoFrame.
-        * Under scan info, no bar data
-        */
-       val = pix_fmt | under_scan |
-               HDMI_FC_AVICONF0_ACTIVE_FMT_INFO_PRESENT |
-               HDMI_FC_AVICONF0_BAR_DATA_NO_DATA;
-
-       hdmi_writeb(hdmi, val, HDMI_FC_AVICONF0);
-
-       /* AVI Data Byte 2 -Set the Aspect Ratio */
-       if (aspect_16_9) {
-               act_ratio = HDMI_FC_AVICONF1_ACTIVE_ASPECT_RATIO_16_9;
-               coded_ratio = HDMI_FC_AVICONF1_CODED_ASPECT_RATIO_16_9;
-       } else {
-               act_ratio = HDMI_FC_AVICONF1_ACTIVE_ASPECT_RATIO_4_3;
-               coded_ratio = HDMI_FC_AVICONF1_CODED_ASPECT_RATIO_4_3;
-       }
-
-       /* Set up colorimetry */
-       if (hdmi->hdmi_data.enc_out_format == XVYCC444) {
-               colorimetry = HDMI_FC_AVICONF1_COLORIMETRY_EXTENDED_INFO;
-               if (hdmi->hdmi_data.colorimetry == HDMI_COLORIMETRY_ITU_601)
-                       ext_colorimetry =
-                               HDMI_FC_AVICONF2_EXT_COLORIMETRY_XVYCC601;
-               else /*hdmi->hdmi_data.colorimetry == HDMI_COLORIMETRY_ITU_709*/
-                       ext_colorimetry =
-                               HDMI_FC_AVICONF2_EXT_COLORIMETRY_XVYCC709;
-       } else if (hdmi->hdmi_data.enc_out_format != RGB) {
-               if (hdmi->hdmi_data.colorimetry == HDMI_COLORIMETRY_ITU_601)
-                       colorimetry = HDMI_FC_AVICONF1_COLORIMETRY_SMPTE;
-               else /*hdmi->hdmi_data.colorimetry == HDMI_COLORIMETRY_ITU_709*/
-                       colorimetry = HDMI_FC_AVICONF1_COLORIMETRY_ITUR;
-               ext_colorimetry = HDMI_FC_AVICONF2_EXT_COLORIMETRY_XVYCC601;
-       } else { /* Carries no data */
-               colorimetry = HDMI_FC_AVICONF1_COLORIMETRY_NO_DATA;
-               ext_colorimetry = HDMI_FC_AVICONF2_EXT_COLORIMETRY_XVYCC601;
-       }
-
-       val = colorimetry | coded_ratio | act_ratio;
-       hdmi_writeb(hdmi, val, HDMI_FC_AVICONF1);
-
-       /* AVI Data Byte 3 */
-       val = HDMI_FC_AVICONF2_IT_CONTENT_NO_DATA | ext_colorimetry |
-               HDMI_FC_AVICONF2_RGB_QUANT_DEFAULT |
-               HDMI_FC_AVICONF2_SCALING_NONE;
-       hdmi_writeb(hdmi, val, HDMI_FC_AVICONF2);
-
-       /* AVI Data Byte 4 */
-       hdmi_writeb(hdmi, hdmi->vic, HDMI_FC_AVIVID);
-
-       /* AVI Data Byte 5- set up input and output pixel repetition */
-       val = (((hdmi->hdmi_data.video_mode.mpixelrepetitioninput + 1) <<
-               HDMI_FC_PRCONF_INCOMING_PR_FACTOR_OFFSET) &
-               HDMI_FC_PRCONF_INCOMING_PR_FACTOR_MASK) |
-               ((hdmi->hdmi_data.video_mode.mpixelrepetitionoutput <<
-               HDMI_FC_PRCONF_OUTPUT_PR_FACTOR_OFFSET) &
-               HDMI_FC_PRCONF_OUTPUT_PR_FACTOR_MASK);
-       hdmi_writeb(hdmi, val, HDMI_FC_PRCONF);
-
-       /* IT Content and quantization range = don't care */
-       val = HDMI_FC_AVICONF3_IT_CONTENT_TYPE_GRAPHICS |
-               HDMI_FC_AVICONF3_QUANT_RANGE_LIMITED;
-       hdmi_writeb(hdmi, val, HDMI_FC_AVICONF3);
-
-       /* AVI Data Bytes 6-13 */
-       hdmi_writeb(hdmi, 0, HDMI_FC_AVIETB0);
-       hdmi_writeb(hdmi, 0, HDMI_FC_AVIETB1);
-       hdmi_writeb(hdmi, 0, HDMI_FC_AVISBB0);
-       hdmi_writeb(hdmi, 0, HDMI_FC_AVISBB1);
-       hdmi_writeb(hdmi, 0, HDMI_FC_AVIELB0);
-       hdmi_writeb(hdmi, 0, HDMI_FC_AVIELB1);
-       hdmi_writeb(hdmi, 0, HDMI_FC_AVISRB0);
-       hdmi_writeb(hdmi, 0, HDMI_FC_AVISRB1);
-}
-
-static void hdmi_av_composer(struct imx_hdmi *hdmi,
-                            const struct drm_display_mode *mode)
-{
-       u8 inv_val;
-       struct hdmi_vmode *vmode = &hdmi->hdmi_data.video_mode;
-       int hblank, vblank, h_de_hs, v_de_vs, hsync_len, vsync_len;
-
-       vmode->mhsyncpolarity = !!(mode->flags & DRM_MODE_FLAG_PHSYNC);
-       vmode->mvsyncpolarity = !!(mode->flags & DRM_MODE_FLAG_PVSYNC);
-       vmode->minterlaced = !!(mode->flags & DRM_MODE_FLAG_INTERLACE);
-       vmode->mpixelclock = mode->clock * 1000;
-
-       dev_dbg(hdmi->dev, "final pixclk = %d\n", vmode->mpixelclock);
-
-       /* Set up HDMI_FC_INVIDCONF */
-       inv_val = (hdmi->hdmi_data.hdcp_enable ?
-               HDMI_FC_INVIDCONF_HDCP_KEEPOUT_ACTIVE :
-               HDMI_FC_INVIDCONF_HDCP_KEEPOUT_INACTIVE);
-
-       inv_val |= (vmode->mvsyncpolarity ?
-               HDMI_FC_INVIDCONF_VSYNC_IN_POLARITY_ACTIVE_HIGH :
-               HDMI_FC_INVIDCONF_VSYNC_IN_POLARITY_ACTIVE_LOW);
-
-       inv_val |= (vmode->mhsyncpolarity ?
-               HDMI_FC_INVIDCONF_HSYNC_IN_POLARITY_ACTIVE_HIGH :
-               HDMI_FC_INVIDCONF_HSYNC_IN_POLARITY_ACTIVE_LOW);
-
-       inv_val |= (vmode->mdataenablepolarity ?
-               HDMI_FC_INVIDCONF_DE_IN_POLARITY_ACTIVE_HIGH :
-               HDMI_FC_INVIDCONF_DE_IN_POLARITY_ACTIVE_LOW);
-
-       if (hdmi->vic == 39)
-               inv_val |= HDMI_FC_INVIDCONF_R_V_BLANK_IN_OSC_ACTIVE_HIGH;
-       else
-               inv_val |= (vmode->minterlaced ?
-                       HDMI_FC_INVIDCONF_R_V_BLANK_IN_OSC_ACTIVE_HIGH :
-                       HDMI_FC_INVIDCONF_R_V_BLANK_IN_OSC_ACTIVE_LOW);
-
-       inv_val |= (vmode->minterlaced ?
-               HDMI_FC_INVIDCONF_IN_I_P_INTERLACED :
-               HDMI_FC_INVIDCONF_IN_I_P_PROGRESSIVE);
-
-       inv_val |= (vmode->mdvi ?
-               HDMI_FC_INVIDCONF_DVI_MODEZ_DVI_MODE :
-               HDMI_FC_INVIDCONF_DVI_MODEZ_HDMI_MODE);
-
-       hdmi_writeb(hdmi, inv_val, HDMI_FC_INVIDCONF);
-
-       /* Set up horizontal active pixel width */
-       hdmi_writeb(hdmi, mode->hdisplay >> 8, HDMI_FC_INHACTV1);
-       hdmi_writeb(hdmi, mode->hdisplay, HDMI_FC_INHACTV0);
-
-       /* Set up vertical active lines */
-       hdmi_writeb(hdmi, mode->vdisplay >> 8, HDMI_FC_INVACTV1);
-       hdmi_writeb(hdmi, mode->vdisplay, HDMI_FC_INVACTV0);
-
-       /* Set up horizontal blanking pixel region width */
-       hblank = mode->htotal - mode->hdisplay;
-       hdmi_writeb(hdmi, hblank >> 8, HDMI_FC_INHBLANK1);
-       hdmi_writeb(hdmi, hblank, HDMI_FC_INHBLANK0);
-
-       /* Set up vertical blanking pixel region width */
-       vblank = mode->vtotal - mode->vdisplay;
-       hdmi_writeb(hdmi, vblank, HDMI_FC_INVBLANK);
-
-       /* Set up HSYNC active edge delay width (in pixel clks) */
-       h_de_hs = mode->hsync_start - mode->hdisplay;
-       hdmi_writeb(hdmi, h_de_hs >> 8, HDMI_FC_HSYNCINDELAY1);
-       hdmi_writeb(hdmi, h_de_hs, HDMI_FC_HSYNCINDELAY0);
-
-       /* Set up VSYNC active edge delay (in lines) */
-       v_de_vs = mode->vsync_start - mode->vdisplay;
-       hdmi_writeb(hdmi, v_de_vs, HDMI_FC_VSYNCINDELAY);
-
-       /* Set up HSYNC active pulse width (in pixel clks) */
-       hsync_len = mode->hsync_end - mode->hsync_start;
-       hdmi_writeb(hdmi, hsync_len >> 8, HDMI_FC_HSYNCINWIDTH1);
-       hdmi_writeb(hdmi, hsync_len, HDMI_FC_HSYNCINWIDTH0);
-
-       /* Set up VSYNC active edge delay (in lines) */
-       vsync_len = mode->vsync_end - mode->vsync_start;
-       hdmi_writeb(hdmi, vsync_len, HDMI_FC_VSYNCINWIDTH);
-}
-
-static void imx_hdmi_phy_disable(struct imx_hdmi *hdmi)
-{
-       if (!hdmi->phy_enabled)
-               return;
-
-       imx_hdmi_phy_enable_tmds(hdmi, 0);
-       imx_hdmi_phy_enable_power(hdmi, 0);
-
-       hdmi->phy_enabled = false;
-}
-
-/* HDMI Initialization Step B.4 */
-static void imx_hdmi_enable_video_path(struct imx_hdmi *hdmi)
-{
-       u8 clkdis;
-
-       /* control period minimum duration */
-       hdmi_writeb(hdmi, 12, HDMI_FC_CTRLDUR);
-       hdmi_writeb(hdmi, 32, HDMI_FC_EXCTRLDUR);
-       hdmi_writeb(hdmi, 1, HDMI_FC_EXCTRLSPAC);
-
-       /* Set to fill TMDS data channels */
-       hdmi_writeb(hdmi, 0x0B, HDMI_FC_CH0PREAM);
-       hdmi_writeb(hdmi, 0x16, HDMI_FC_CH1PREAM);
-       hdmi_writeb(hdmi, 0x21, HDMI_FC_CH2PREAM);
-
-       /* Enable pixel clock and tmds data path */
-       clkdis = 0x7F;
-       clkdis &= ~HDMI_MC_CLKDIS_PIXELCLK_DISABLE;
-       hdmi_writeb(hdmi, clkdis, HDMI_MC_CLKDIS);
-
-       clkdis &= ~HDMI_MC_CLKDIS_TMDSCLK_DISABLE;
-       hdmi_writeb(hdmi, clkdis, HDMI_MC_CLKDIS);
-
-       /* Enable csc path */
-       if (is_color_space_conversion(hdmi)) {
-               clkdis &= ~HDMI_MC_CLKDIS_CSCCLK_DISABLE;
-               hdmi_writeb(hdmi, clkdis, HDMI_MC_CLKDIS);
-       }
-}
-
-static void hdmi_enable_audio_clk(struct imx_hdmi *hdmi)
-{
-       hdmi_modb(hdmi, 0, HDMI_MC_CLKDIS_AUDCLK_DISABLE, HDMI_MC_CLKDIS);
-}
-
-/* Workaround to clear the overflow condition */
-static void imx_hdmi_clear_overflow(struct imx_hdmi *hdmi)
-{
-       int count;
-       u8 val;
-
-       /* TMDS software reset */
-       hdmi_writeb(hdmi, (u8)~HDMI_MC_SWRSTZ_TMDSSWRST_REQ, HDMI_MC_SWRSTZ);
-
-       val = hdmi_readb(hdmi, HDMI_FC_INVIDCONF);
-       if (hdmi->dev_type == IMX6DL_HDMI) {
-               hdmi_writeb(hdmi, val, HDMI_FC_INVIDCONF);
-               return;
-       }
-
-       for (count = 0; count < 4; count++)
-               hdmi_writeb(hdmi, val, HDMI_FC_INVIDCONF);
-}
-
-static void hdmi_enable_overflow_interrupts(struct imx_hdmi *hdmi)
-{
-       hdmi_writeb(hdmi, 0, HDMI_FC_MASK2);
-       hdmi_writeb(hdmi, 0, HDMI_IH_MUTE_FC_STAT2);
-}
-
-static void hdmi_disable_overflow_interrupts(struct imx_hdmi *hdmi)
-{
-       hdmi_writeb(hdmi, HDMI_IH_MUTE_FC_STAT2_OVERFLOW_MASK,
-                   HDMI_IH_MUTE_FC_STAT2);
-}
-
-static int imx_hdmi_setup(struct imx_hdmi *hdmi, struct drm_display_mode *mode)
-{
-       int ret;
-
-       hdmi_disable_overflow_interrupts(hdmi);
-
-       hdmi->vic = drm_match_cea_mode(mode);
-
-       if (!hdmi->vic) {
-               dev_dbg(hdmi->dev, "Non-CEA mode used in HDMI\n");
-               hdmi->hdmi_data.video_mode.mdvi = true;
-       } else {
-               dev_dbg(hdmi->dev, "CEA mode used vic=%d\n", hdmi->vic);
-               hdmi->hdmi_data.video_mode.mdvi = false;
-       }
-
-       if ((hdmi->vic == 6) || (hdmi->vic == 7) ||
-               (hdmi->vic == 21) || (hdmi->vic == 22) ||
-               (hdmi->vic == 2) || (hdmi->vic == 3) ||
-               (hdmi->vic == 17) || (hdmi->vic == 18))
-               hdmi->hdmi_data.colorimetry = HDMI_COLORIMETRY_ITU_601;
-       else
-               hdmi->hdmi_data.colorimetry = HDMI_COLORIMETRY_ITU_709;
-
-       if ((hdmi->vic == 10) || (hdmi->vic == 11) ||
-               (hdmi->vic == 12) || (hdmi->vic == 13) ||
-               (hdmi->vic == 14) || (hdmi->vic == 15) ||
-               (hdmi->vic == 25) || (hdmi->vic == 26) ||
-               (hdmi->vic == 27) || (hdmi->vic == 28) ||
-               (hdmi->vic == 29) || (hdmi->vic == 30) ||
-               (hdmi->vic == 35) || (hdmi->vic == 36) ||
-               (hdmi->vic == 37) || (hdmi->vic == 38))
-               hdmi->hdmi_data.video_mode.mpixelrepetitionoutput = 1;
-       else
-               hdmi->hdmi_data.video_mode.mpixelrepetitionoutput = 0;
-
-       hdmi->hdmi_data.video_mode.mpixelrepetitioninput = 0;
-
-       /* TODO: Get input format from IPU (via FB driver interface) */
-       hdmi->hdmi_data.enc_in_format = RGB;
-
-       hdmi->hdmi_data.enc_out_format = RGB;
-
-       hdmi->hdmi_data.enc_color_depth = 8;
-       hdmi->hdmi_data.pix_repet_factor = 0;
-       hdmi->hdmi_data.hdcp_enable = 0;
-       hdmi->hdmi_data.video_mode.mdataenablepolarity = true;
-
-       /* HDMI Initialization Step B.1 */
-       hdmi_av_composer(hdmi, mode);
-
-       /* HDMI Initializateion Step B.2 */
-       ret = imx_hdmi_phy_init(hdmi);
-       if (ret)
-               return ret;
-
-       /* HDMI Initialization Step B.3 */
-       imx_hdmi_enable_video_path(hdmi);
-
-       /* not for DVI mode */
-       if (hdmi->hdmi_data.video_mode.mdvi)
-               dev_dbg(hdmi->dev, "%s DVI mode\n", __func__);
-       else {
-               dev_dbg(hdmi->dev, "%s CEA mode\n", __func__);
-
-               /* HDMI Initialization Step E - Configure audio */
-               hdmi_clk_regenerator_update_pixel_clock(hdmi);
-               hdmi_enable_audio_clk(hdmi);
-
-               /* HDMI Initialization Step F - Configure AVI InfoFrame */
-               hdmi_config_AVI(hdmi);
-       }
-
-       hdmi_video_packetize(hdmi);
-       hdmi_video_csc(hdmi);
-       hdmi_video_sample(hdmi);
-       hdmi_tx_hdcp_config(hdmi);
-
-       imx_hdmi_clear_overflow(hdmi);
-       if (hdmi->cable_plugin && !hdmi->hdmi_data.video_mode.mdvi)
-               hdmi_enable_overflow_interrupts(hdmi);
-
-       return 0;
-}
-
-/* Wait until we are registered to enable interrupts */
-static int imx_hdmi_fb_registered(struct imx_hdmi *hdmi)
-{
-       hdmi_writeb(hdmi, HDMI_PHY_I2CM_INT_ADDR_DONE_POL,
-                   HDMI_PHY_I2CM_INT_ADDR);
-
-       hdmi_writeb(hdmi, HDMI_PHY_I2CM_CTLINT_ADDR_NAC_POL |
-                   HDMI_PHY_I2CM_CTLINT_ADDR_ARBITRATION_POL,
-                   HDMI_PHY_I2CM_CTLINT_ADDR);
-
-       /* enable cable hot plug irq */
-       hdmi_writeb(hdmi, (u8)~HDMI_PHY_HPD, HDMI_PHY_MASK0);
-
-       /* Clear Hotplug interrupts */
-       hdmi_writeb(hdmi, HDMI_IH_PHY_STAT0_HPD, HDMI_IH_PHY_STAT0);
-
-       return 0;
-}
-
-static void initialize_hdmi_ih_mutes(struct imx_hdmi *hdmi)
-{
-       u8 ih_mute;
-
-       /*
-        * Boot up defaults are:
-        * HDMI_IH_MUTE   = 0x03 (disabled)
-        * HDMI_IH_MUTE_* = 0x00 (enabled)
-        *
-        * Disable top level interrupt bits in HDMI block
-        */
-       ih_mute = hdmi_readb(hdmi, HDMI_IH_MUTE) |
-                 HDMI_IH_MUTE_MUTE_WAKEUP_INTERRUPT |
-                 HDMI_IH_MUTE_MUTE_ALL_INTERRUPT;
-
-       hdmi_writeb(hdmi, ih_mute, HDMI_IH_MUTE);
-
-       /* by default mask all interrupts */
-       hdmi_writeb(hdmi, 0xff, HDMI_VP_MASK);
-       hdmi_writeb(hdmi, 0xff, HDMI_FC_MASK0);
-       hdmi_writeb(hdmi, 0xff, HDMI_FC_MASK1);
-       hdmi_writeb(hdmi, 0xff, HDMI_FC_MASK2);
-       hdmi_writeb(hdmi, 0xff, HDMI_PHY_MASK0);
-       hdmi_writeb(hdmi, 0xff, HDMI_PHY_I2CM_INT_ADDR);
-       hdmi_writeb(hdmi, 0xff, HDMI_PHY_I2CM_CTLINT_ADDR);
-       hdmi_writeb(hdmi, 0xff, HDMI_AUD_INT);
-       hdmi_writeb(hdmi, 0xff, HDMI_AUD_SPDIFINT);
-       hdmi_writeb(hdmi, 0xff, HDMI_AUD_HBR_MASK);
-       hdmi_writeb(hdmi, 0xff, HDMI_GP_MASK);
-       hdmi_writeb(hdmi, 0xff, HDMI_A_APIINTMSK);
-       hdmi_writeb(hdmi, 0xff, HDMI_CEC_MASK);
-       hdmi_writeb(hdmi, 0xff, HDMI_I2CM_INT);
-       hdmi_writeb(hdmi, 0xff, HDMI_I2CM_CTLINT);
-
-       /* Disable interrupts in the IH_MUTE_* registers */
-       hdmi_writeb(hdmi, 0xff, HDMI_IH_MUTE_FC_STAT0);
-       hdmi_writeb(hdmi, 0xff, HDMI_IH_MUTE_FC_STAT1);
-       hdmi_writeb(hdmi, 0xff, HDMI_IH_MUTE_FC_STAT2);
-       hdmi_writeb(hdmi, 0xff, HDMI_IH_MUTE_AS_STAT0);
-       hdmi_writeb(hdmi, 0xff, HDMI_IH_MUTE_PHY_STAT0);
-       hdmi_writeb(hdmi, 0xff, HDMI_IH_MUTE_I2CM_STAT0);
-       hdmi_writeb(hdmi, 0xff, HDMI_IH_MUTE_CEC_STAT0);
-       hdmi_writeb(hdmi, 0xff, HDMI_IH_MUTE_VP_STAT0);
-       hdmi_writeb(hdmi, 0xff, HDMI_IH_MUTE_I2CMPHY_STAT0);
-       hdmi_writeb(hdmi, 0xff, HDMI_IH_MUTE_AHBDMAAUD_STAT0);
-
-       /* Enable top level interrupt bits in HDMI block */
-       ih_mute &= ~(HDMI_IH_MUTE_MUTE_WAKEUP_INTERRUPT |
-                   HDMI_IH_MUTE_MUTE_ALL_INTERRUPT);
-       hdmi_writeb(hdmi, ih_mute, HDMI_IH_MUTE);
-}
-
-static void imx_hdmi_poweron(struct imx_hdmi *hdmi)
-{
-       imx_hdmi_setup(hdmi, &hdmi->previous_mode);
-}
-
-static void imx_hdmi_poweroff(struct imx_hdmi *hdmi)
-{
-       imx_hdmi_phy_disable(hdmi);
-}
-
-static enum drm_connector_status imx_hdmi_connector_detect(struct drm_connector
-                                                       *connector, bool force)
-{
-       struct imx_hdmi *hdmi = container_of(connector, struct imx_hdmi,
-                                            connector);
-
-       return hdmi_readb(hdmi, HDMI_PHY_STAT0) & HDMI_PHY_HPD ?
-               connector_status_connected : connector_status_disconnected;
-}
-
-static int imx_hdmi_connector_get_modes(struct drm_connector *connector)
-{
-       struct imx_hdmi *hdmi = container_of(connector, struct imx_hdmi,
-                                            connector);
-       struct edid *edid;
-       int ret;
-
-       if (!hdmi->ddc)
-               return 0;
-
-       edid = drm_get_edid(connector, hdmi->ddc);
-       if (edid) {
-               dev_dbg(hdmi->dev, "got edid: width[%d] x height[%d]\n",
-                       edid->width_cm, edid->height_cm);
-
-               drm_mode_connector_update_edid_property(connector, edid);
-               ret = drm_add_edid_modes(connector, edid);
-               kfree(edid);
-       } else {
-               dev_dbg(hdmi->dev, "failed to get edid\n");
-       }
-
-       return 0;
-}
-
-static struct drm_encoder *imx_hdmi_connector_best_encoder(struct drm_connector
-                                                          *connector)
-{
-       struct imx_hdmi *hdmi = container_of(connector, struct imx_hdmi,
-                                            connector);
-
-       return &hdmi->encoder;
-}
-
-static void imx_hdmi_encoder_mode_set(struct drm_encoder *encoder,
-                       struct drm_display_mode *mode,
-                       struct drm_display_mode *adjusted_mode)
-{
-       struct imx_hdmi *hdmi = container_of(encoder, struct imx_hdmi, encoder);
-
-       imx_hdmi_setup(hdmi, mode);
-
-       /* Store the display mode for plugin/DKMS poweron events */
-       memcpy(&hdmi->previous_mode, mode, sizeof(hdmi->previous_mode));
-}
-
-static bool imx_hdmi_encoder_mode_fixup(struct drm_encoder *encoder,
-                       const struct drm_display_mode *mode,
-                       struct drm_display_mode *adjusted_mode)
-{
-       return true;
-}
-
-static void imx_hdmi_encoder_disable(struct drm_encoder *encoder)
-{
-}
-
-static void imx_hdmi_encoder_dpms(struct drm_encoder *encoder, int mode)
-{
-       struct imx_hdmi *hdmi = container_of(encoder, struct imx_hdmi, encoder);
-
-       if (mode)
-               imx_hdmi_poweroff(hdmi);
-       else
-               imx_hdmi_poweron(hdmi);
-}
-
-static void imx_hdmi_encoder_prepare(struct drm_encoder *encoder)
-{
-       struct imx_hdmi *hdmi = container_of(encoder, struct imx_hdmi, encoder);
-
-       imx_hdmi_poweroff(hdmi);
-       imx_drm_panel_format(encoder, V4L2_PIX_FMT_RGB24);
-}
-
-static void imx_hdmi_encoder_commit(struct drm_encoder *encoder)
-{
-       struct imx_hdmi *hdmi = container_of(encoder, struct imx_hdmi, encoder);
-       int mux = imx_drm_encoder_get_mux_id(hdmi->dev->of_node, encoder);
-
-       imx_hdmi_set_ipu_di_mux(hdmi, mux);
-
-       imx_hdmi_poweron(hdmi);
-}
-
-static struct drm_encoder_funcs imx_hdmi_encoder_funcs = {
-       .destroy = imx_drm_encoder_destroy,
-};
-
-static struct drm_encoder_helper_funcs imx_hdmi_encoder_helper_funcs = {
-       .dpms = imx_hdmi_encoder_dpms,
-       .prepare = imx_hdmi_encoder_prepare,
-       .commit = imx_hdmi_encoder_commit,
-       .mode_set = imx_hdmi_encoder_mode_set,
-       .mode_fixup = imx_hdmi_encoder_mode_fixup,
-       .disable = imx_hdmi_encoder_disable,
-};
-
-static struct drm_connector_funcs imx_hdmi_connector_funcs = {
-       .dpms = drm_helper_connector_dpms,
-       .fill_modes = drm_helper_probe_single_connector_modes,
-       .detect = imx_hdmi_connector_detect,
-       .destroy = imx_drm_connector_destroy,
-};
-
-static struct drm_connector_helper_funcs imx_hdmi_connector_helper_funcs = {
-       .get_modes = imx_hdmi_connector_get_modes,
-       .best_encoder = imx_hdmi_connector_best_encoder,
-};
-
-static irqreturn_t imx_hdmi_hardirq(int irq, void *dev_id)
-{
-       struct imx_hdmi *hdmi = dev_id;
-       u8 intr_stat;
-
-       intr_stat = hdmi_readb(hdmi, HDMI_IH_PHY_STAT0);
-       if (intr_stat)
-               hdmi_writeb(hdmi, ~0, HDMI_IH_MUTE_PHY_STAT0);
-
-       return intr_stat ? IRQ_WAKE_THREAD : IRQ_NONE;
-}
-
-static irqreturn_t imx_hdmi_irq(int irq, void *dev_id)
-{
-       struct imx_hdmi *hdmi = dev_id;
-       u8 intr_stat;
-       u8 phy_int_pol;
-
-       intr_stat = hdmi_readb(hdmi, HDMI_IH_PHY_STAT0);
-
-       phy_int_pol = hdmi_readb(hdmi, HDMI_PHY_POL0);
-
-       if (intr_stat & HDMI_IH_PHY_STAT0_HPD) {
-               if (phy_int_pol & HDMI_PHY_HPD) {
-                       dev_dbg(hdmi->dev, "EVENT=plugin\n");
-
-                       hdmi_modb(hdmi, 0, HDMI_PHY_HPD, HDMI_PHY_POL0);
-
-                       imx_hdmi_poweron(hdmi);
-               } else {
-                       dev_dbg(hdmi->dev, "EVENT=plugout\n");
-
-                       hdmi_modb(hdmi, HDMI_PHY_HPD, HDMI_PHY_HPD,
-                               HDMI_PHY_POL0);
-
-                       imx_hdmi_poweroff(hdmi);
-               }
-               drm_helper_hpd_irq_event(hdmi->connector.dev);
-       }
-
-       hdmi_writeb(hdmi, intr_stat, HDMI_IH_PHY_STAT0);
-       hdmi_writeb(hdmi, ~HDMI_IH_PHY_STAT0_HPD, HDMI_IH_MUTE_PHY_STAT0);
-
-       return IRQ_HANDLED;
-}
-
-static int imx_hdmi_register(struct drm_device *drm, struct imx_hdmi *hdmi)
-{
-       int ret;
-
-       ret = imx_drm_encoder_parse_of(drm, &hdmi->encoder,
-                                      hdmi->dev->of_node);
-       if (ret)
-               return ret;
-
-       hdmi->connector.polled = DRM_CONNECTOR_POLL_HPD;
-
-       drm_encoder_helper_add(&hdmi->encoder, &imx_hdmi_encoder_helper_funcs);
-       drm_encoder_init(drm, &hdmi->encoder, &imx_hdmi_encoder_funcs,
-                        DRM_MODE_ENCODER_TMDS);
-
-       drm_connector_helper_add(&hdmi->connector,
-                       &imx_hdmi_connector_helper_funcs);
-       drm_connector_init(drm, &hdmi->connector, &imx_hdmi_connector_funcs,
-                          DRM_MODE_CONNECTOR_HDMIA);
-
-       hdmi->connector.encoder = &hdmi->encoder;
-
-       drm_mode_connector_attach_encoder(&hdmi->connector, &hdmi->encoder);
-
-       return 0;
-}
-
-static struct platform_device_id imx_hdmi_devtype[] = {
-       {
-               .name = "imx6q-hdmi",
-               .driver_data = IMX6Q_HDMI,
-       }, {
-               .name = "imx6dl-hdmi",
-               .driver_data = IMX6DL_HDMI,
-       }, { /* sentinel */ }
-};
-MODULE_DEVICE_TABLE(platform, imx_hdmi_devtype);
-
-static const struct of_device_id imx_hdmi_dt_ids[] = {
-{ .compatible = "fsl,imx6q-hdmi", .data = &imx_hdmi_devtype[IMX6Q_HDMI], },
-{ .compatible = "fsl,imx6dl-hdmi", .data = &imx_hdmi_devtype[IMX6DL_HDMI], },
-{ /* sentinel */ }
-};
-MODULE_DEVICE_TABLE(of, imx_hdmi_dt_ids);
-
-static int imx_hdmi_bind(struct device *dev, struct device *master, void *data)
-{
-       struct platform_device *pdev = to_platform_device(dev);
-       const struct of_device_id *of_id =
-                               of_match_device(imx_hdmi_dt_ids, dev);
-       struct drm_device *drm = data;
-       struct device_node *np = dev->of_node;
-       struct device_node *ddc_node;
-       struct imx_hdmi *hdmi;
-       struct resource *iores;
-       int ret, irq;
-
-       hdmi = devm_kzalloc(dev, sizeof(*hdmi), GFP_KERNEL);
-       if (!hdmi)
-               return -ENOMEM;
-
-       hdmi->dev = dev;
-       hdmi->sample_rate = 48000;
-       hdmi->ratio = 100;
-
-       if (of_id) {
-               const struct platform_device_id *device_id = of_id->data;
-
-               hdmi->dev_type = device_id->driver_data;
-       }
-
-       ddc_node = of_parse_phandle(np, "ddc-i2c-bus", 0);
-       if (ddc_node) {
-               hdmi->ddc = of_find_i2c_adapter_by_node(ddc_node);
-               if (!hdmi->ddc)
-                       dev_dbg(hdmi->dev, "failed to read ddc node\n");
-
-               of_node_put(ddc_node);
-       } else {
-               dev_dbg(hdmi->dev, "no ddc property found\n");
-       }
-
-       irq = platform_get_irq(pdev, 0);
-       if (irq < 0)
-               return irq;
-
-       ret = devm_request_threaded_irq(dev, irq, imx_hdmi_hardirq,
-                                       imx_hdmi_irq, IRQF_SHARED,
-                                       dev_name(dev), hdmi);
-       if (ret)
-               return ret;
-
-       iores = platform_get_resource(pdev, IORESOURCE_MEM, 0);
-       hdmi->regs = devm_ioremap_resource(dev, iores);
-       if (IS_ERR(hdmi->regs))
-               return PTR_ERR(hdmi->regs);
-
-       hdmi->regmap = syscon_regmap_lookup_by_phandle(np, "gpr");
-       if (IS_ERR(hdmi->regmap))
-               return PTR_ERR(hdmi->regmap);
-
-       hdmi->isfr_clk = devm_clk_get(hdmi->dev, "isfr");
-       if (IS_ERR(hdmi->isfr_clk)) {
-               ret = PTR_ERR(hdmi->isfr_clk);
-               dev_err(hdmi->dev,
-                       "Unable to get HDMI isfr clk: %d\n", ret);
-               return ret;
-       }
-
-       ret = clk_prepare_enable(hdmi->isfr_clk);
-       if (ret) {
-               dev_err(hdmi->dev,
-                       "Cannot enable HDMI isfr clock: %d\n", ret);
-               return ret;
-       }
-
-       hdmi->iahb_clk = devm_clk_get(hdmi->dev, "iahb");
-       if (IS_ERR(hdmi->iahb_clk)) {
-               ret = PTR_ERR(hdmi->iahb_clk);
-               dev_err(hdmi->dev,
-                       "Unable to get HDMI iahb clk: %d\n", ret);
-               goto err_isfr;
-       }
-
-       ret = clk_prepare_enable(hdmi->iahb_clk);
-       if (ret) {
-               dev_err(hdmi->dev,
-                       "Cannot enable HDMI iahb clock: %d\n", ret);
-               goto err_isfr;
-       }
-
-       /* Product and revision IDs */
-       dev_info(dev,
-               "Detected HDMI controller 0x%x:0x%x:0x%x:0x%x\n",
-               hdmi_readb(hdmi, HDMI_DESIGN_ID),
-               hdmi_readb(hdmi, HDMI_REVISION_ID),
-               hdmi_readb(hdmi, HDMI_PRODUCT_ID0),
-               hdmi_readb(hdmi, HDMI_PRODUCT_ID1));
-
-       initialize_hdmi_ih_mutes(hdmi);
-
-       /*
-        * To prevent overflows in HDMI_IH_FC_STAT2, set the clk regenerator
-        * N and cts values before enabling phy
-        */
-       hdmi_init_clk_regenerator(hdmi);
-
-       /*
-        * Configure registers related to HDMI interrupt
-        * generation before registering IRQ.
-        */
-       hdmi_writeb(hdmi, HDMI_PHY_HPD, HDMI_PHY_POL0);
-
-       /* Clear Hotplug interrupts */
-       hdmi_writeb(hdmi, HDMI_IH_PHY_STAT0_HPD, HDMI_IH_PHY_STAT0);
-
-       ret = imx_hdmi_fb_registered(hdmi);
-       if (ret)
-               goto err_iahb;
-
-       ret = imx_hdmi_register(drm, hdmi);
-       if (ret)
-               goto err_iahb;
-
-       /* Unmute interrupts */
-       hdmi_writeb(hdmi, ~HDMI_IH_PHY_STAT0_HPD, HDMI_IH_MUTE_PHY_STAT0);
-
-       dev_set_drvdata(dev, hdmi);
-
-       return 0;
-
-err_iahb:
-       clk_disable_unprepare(hdmi->iahb_clk);
-err_isfr:
-       clk_disable_unprepare(hdmi->isfr_clk);
-
-       return ret;
-}
-
-static void imx_hdmi_unbind(struct device *dev, struct device *master,
-       void *data)
-{
-       struct imx_hdmi *hdmi = dev_get_drvdata(dev);
-
-       /* Disable all interrupts */
-       hdmi_writeb(hdmi, ~0, HDMI_IH_MUTE_PHY_STAT0);
-
-       hdmi->connector.funcs->destroy(&hdmi->connector);
-       hdmi->encoder.funcs->destroy(&hdmi->encoder);
-
-       clk_disable_unprepare(hdmi->iahb_clk);
-       clk_disable_unprepare(hdmi->isfr_clk);
-       i2c_put_adapter(hdmi->ddc);
-}
-
-static const struct component_ops hdmi_ops = {
-       .bind   = imx_hdmi_bind,
-       .unbind = imx_hdmi_unbind,
-};
-
-static int imx_hdmi_platform_probe(struct platform_device *pdev)
-{
-       return component_add(&pdev->dev, &hdmi_ops);
-}
-
-static int imx_hdmi_platform_remove(struct platform_device *pdev)
-{
-       component_del(&pdev->dev, &hdmi_ops);
-       return 0;
-}
-
-static struct platform_driver imx_hdmi_driver = {
-       .probe  = imx_hdmi_platform_probe,
-       .remove = imx_hdmi_platform_remove,
-       .driver = {
-               .name = "imx-hdmi",
-               .of_match_table = imx_hdmi_dt_ids,
-       },
-};
-
-module_platform_driver(imx_hdmi_driver);
-
-MODULE_AUTHOR("Sascha Hauer <s.hauer@pengutronix.de>");
-MODULE_DESCRIPTION("i.MX6 HDMI transmitter driver");
-MODULE_LICENSE("GPL");
-MODULE_ALIAS("platform:imx-hdmi");
diff --git a/drivers/gpu/drm/imx/imx-hdmi.h b/drivers/gpu/drm/imx/imx-hdmi.h
deleted file mode 100644 (file)
index 39b6776..0000000
+++ /dev/null
@@ -1,1032 +0,0 @@
-/*
- * Copyright (C) 2011 Freescale Semiconductor, Inc.
- *
- * 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.
- */
-
-#ifndef __IMX_HDMI_H__
-#define __IMX_HDMI_H__
-
-/* Identification Registers */
-#define HDMI_DESIGN_ID                          0x0000
-#define HDMI_REVISION_ID                        0x0001
-#define HDMI_PRODUCT_ID0                        0x0002
-#define HDMI_PRODUCT_ID1                        0x0003
-#define HDMI_CONFIG0_ID                         0x0004
-#define HDMI_CONFIG1_ID                         0x0005
-#define HDMI_CONFIG2_ID                         0x0006
-#define HDMI_CONFIG3_ID                         0x0007
-
-/* Interrupt Registers */
-#define HDMI_IH_FC_STAT0                        0x0100
-#define HDMI_IH_FC_STAT1                        0x0101
-#define HDMI_IH_FC_STAT2                        0x0102
-#define HDMI_IH_AS_STAT0                        0x0103
-#define HDMI_IH_PHY_STAT0                       0x0104
-#define HDMI_IH_I2CM_STAT0                      0x0105
-#define HDMI_IH_CEC_STAT0                       0x0106
-#define HDMI_IH_VP_STAT0                        0x0107
-#define HDMI_IH_I2CMPHY_STAT0                   0x0108
-#define HDMI_IH_AHBDMAAUD_STAT0                 0x0109
-
-#define HDMI_IH_MUTE_FC_STAT0                   0x0180
-#define HDMI_IH_MUTE_FC_STAT1                   0x0181
-#define HDMI_IH_MUTE_FC_STAT2                   0x0182
-#define HDMI_IH_MUTE_AS_STAT0                   0x0183
-#define HDMI_IH_MUTE_PHY_STAT0                  0x0184
-#define HDMI_IH_MUTE_I2CM_STAT0                 0x0185
-#define HDMI_IH_MUTE_CEC_STAT0                  0x0186
-#define HDMI_IH_MUTE_VP_STAT0                   0x0187
-#define HDMI_IH_MUTE_I2CMPHY_STAT0              0x0188
-#define HDMI_IH_MUTE_AHBDMAAUD_STAT0            0x0189
-#define HDMI_IH_MUTE                            0x01FF
-
-/* Video Sample Registers */
-#define HDMI_TX_INVID0                          0x0200
-#define HDMI_TX_INSTUFFING                      0x0201
-#define HDMI_TX_GYDATA0                         0x0202
-#define HDMI_TX_GYDATA1                         0x0203
-#define HDMI_TX_RCRDATA0                        0x0204
-#define HDMI_TX_RCRDATA1                        0x0205
-#define HDMI_TX_BCBDATA0                        0x0206
-#define HDMI_TX_BCBDATA1                        0x0207
-
-/* Video Packetizer Registers */
-#define HDMI_VP_STATUS                          0x0800
-#define HDMI_VP_PR_CD                           0x0801
-#define HDMI_VP_STUFF                           0x0802
-#define HDMI_VP_REMAP                           0x0803
-#define HDMI_VP_CONF                            0x0804
-#define HDMI_VP_STAT                            0x0805
-#define HDMI_VP_INT                             0x0806
-#define HDMI_VP_MASK                            0x0807
-#define HDMI_VP_POL                             0x0808
-
-/* Frame Composer Registers */
-#define HDMI_FC_INVIDCONF                       0x1000
-#define HDMI_FC_INHACTV0                        0x1001
-#define HDMI_FC_INHACTV1                        0x1002
-#define HDMI_FC_INHBLANK0                       0x1003
-#define HDMI_FC_INHBLANK1                       0x1004
-#define HDMI_FC_INVACTV0                        0x1005
-#define HDMI_FC_INVACTV1                        0x1006
-#define HDMI_FC_INVBLANK                        0x1007
-#define HDMI_FC_HSYNCINDELAY0                   0x1008
-#define HDMI_FC_HSYNCINDELAY1                   0x1009
-#define HDMI_FC_HSYNCINWIDTH0                   0x100A
-#define HDMI_FC_HSYNCINWIDTH1                   0x100B
-#define HDMI_FC_VSYNCINDELAY                    0x100C
-#define HDMI_FC_VSYNCINWIDTH                    0x100D
-#define HDMI_FC_INFREQ0                         0x100E
-#define HDMI_FC_INFREQ1                         0x100F
-#define HDMI_FC_INFREQ2                         0x1010
-#define HDMI_FC_CTRLDUR                         0x1011
-#define HDMI_FC_EXCTRLDUR                       0x1012
-#define HDMI_FC_EXCTRLSPAC                      0x1013
-#define HDMI_FC_CH0PREAM                        0x1014
-#define HDMI_FC_CH1PREAM                        0x1015
-#define HDMI_FC_CH2PREAM                        0x1016
-#define HDMI_FC_AVICONF3                        0x1017
-#define HDMI_FC_GCP                             0x1018
-#define HDMI_FC_AVICONF0                        0x1019
-#define HDMI_FC_AVICONF1                        0x101A
-#define HDMI_FC_AVICONF2                        0x101B
-#define HDMI_FC_AVIVID                          0x101C
-#define HDMI_FC_AVIETB0                         0x101D
-#define HDMI_FC_AVIETB1                         0x101E
-#define HDMI_FC_AVISBB0                         0x101F
-#define HDMI_FC_AVISBB1                         0x1020
-#define HDMI_FC_AVIELB0                         0x1021
-#define HDMI_FC_AVIELB1                         0x1022
-#define HDMI_FC_AVISRB0                         0x1023
-#define HDMI_FC_AVISRB1                         0x1024
-#define HDMI_FC_AUDICONF0                       0x1025
-#define HDMI_FC_AUDICONF1                       0x1026
-#define HDMI_FC_AUDICONF2                       0x1027
-#define HDMI_FC_AUDICONF3                       0x1028
-#define HDMI_FC_VSDIEEEID0                      0x1029
-#define HDMI_FC_VSDSIZE                         0x102A
-#define HDMI_FC_VSDIEEEID1                      0x1030
-#define HDMI_FC_VSDIEEEID2                      0x1031
-#define HDMI_FC_VSDPAYLOAD0                     0x1032
-#define HDMI_FC_VSDPAYLOAD1                     0x1033
-#define HDMI_FC_VSDPAYLOAD2                     0x1034
-#define HDMI_FC_VSDPAYLOAD3                     0x1035
-#define HDMI_FC_VSDPAYLOAD4                     0x1036
-#define HDMI_FC_VSDPAYLOAD5                     0x1037
-#define HDMI_FC_VSDPAYLOAD6                     0x1038
-#define HDMI_FC_VSDPAYLOAD7                     0x1039
-#define HDMI_FC_VSDPAYLOAD8                     0x103A
-#define HDMI_FC_VSDPAYLOAD9                     0x103B
-#define HDMI_FC_VSDPAYLOAD10                    0x103C
-#define HDMI_FC_VSDPAYLOAD11                    0x103D
-#define HDMI_FC_VSDPAYLOAD12                    0x103E
-#define HDMI_FC_VSDPAYLOAD13                    0x103F
-#define HDMI_FC_VSDPAYLOAD14                    0x1040
-#define HDMI_FC_VSDPAYLOAD15                    0x1041
-#define HDMI_FC_VSDPAYLOAD16                    0x1042
-#define HDMI_FC_VSDPAYLOAD17                    0x1043
-#define HDMI_FC_VSDPAYLOAD18                    0x1044
-#define HDMI_FC_VSDPAYLOAD19                    0x1045
-#define HDMI_FC_VSDPAYLOAD20                    0x1046
-#define HDMI_FC_VSDPAYLOAD21                    0x1047
-#define HDMI_FC_VSDPAYLOAD22                    0x1048
-#define HDMI_FC_VSDPAYLOAD23                    0x1049
-#define HDMI_FC_SPDVENDORNAME0                  0x104A
-#define HDMI_FC_SPDVENDORNAME1                  0x104B
-#define HDMI_FC_SPDVENDORNAME2                  0x104C
-#define HDMI_FC_SPDVENDORNAME3                  0x104D
-#define HDMI_FC_SPDVENDORNAME4                  0x104E
-#define HDMI_FC_SPDVENDORNAME5                  0x104F
-#define HDMI_FC_SPDVENDORNAME6                  0x1050
-#define HDMI_FC_SPDVENDORNAME7                  0x1051
-#define HDMI_FC_SDPPRODUCTNAME0                 0x1052
-#define HDMI_FC_SDPPRODUCTNAME1                 0x1053
-#define HDMI_FC_SDPPRODUCTNAME2                 0x1054
-#define HDMI_FC_SDPPRODUCTNAME3                 0x1055
-#define HDMI_FC_SDPPRODUCTNAME4                 0x1056
-#define HDMI_FC_SDPPRODUCTNAME5                 0x1057
-#define HDMI_FC_SDPPRODUCTNAME6                 0x1058
-#define HDMI_FC_SDPPRODUCTNAME7                 0x1059
-#define HDMI_FC_SDPPRODUCTNAME8                 0x105A
-#define HDMI_FC_SDPPRODUCTNAME9                 0x105B
-#define HDMI_FC_SDPPRODUCTNAME10                0x105C
-#define HDMI_FC_SDPPRODUCTNAME11                0x105D
-#define HDMI_FC_SDPPRODUCTNAME12                0x105E
-#define HDMI_FC_SDPPRODUCTNAME13                0x105F
-#define HDMI_FC_SDPPRODUCTNAME14                0x1060
-#define HDMI_FC_SPDPRODUCTNAME15                0x1061
-#define HDMI_FC_SPDDEVICEINF                    0x1062
-#define HDMI_FC_AUDSCONF                        0x1063
-#define HDMI_FC_AUDSSTAT                        0x1064
-#define HDMI_FC_DATACH0FILL                     0x1070
-#define HDMI_FC_DATACH1FILL                     0x1071
-#define HDMI_FC_DATACH2FILL                     0x1072
-#define HDMI_FC_CTRLQHIGH                       0x1073
-#define HDMI_FC_CTRLQLOW                        0x1074
-#define HDMI_FC_ACP0                            0x1075
-#define HDMI_FC_ACP28                           0x1076
-#define HDMI_FC_ACP27                           0x1077
-#define HDMI_FC_ACP26                           0x1078
-#define HDMI_FC_ACP25                           0x1079
-#define HDMI_FC_ACP24                           0x107A
-#define HDMI_FC_ACP23                           0x107B
-#define HDMI_FC_ACP22                           0x107C
-#define HDMI_FC_ACP21                           0x107D
-#define HDMI_FC_ACP20                           0x107E
-#define HDMI_FC_ACP19                           0x107F
-#define HDMI_FC_ACP18                           0x1080
-#define HDMI_FC_ACP17                           0x1081
-#define HDMI_FC_ACP16                           0x1082
-#define HDMI_FC_ACP15                           0x1083
-#define HDMI_FC_ACP14                           0x1084
-#define HDMI_FC_ACP13                           0x1085
-#define HDMI_FC_ACP12                           0x1086
-#define HDMI_FC_ACP11                           0x1087
-#define HDMI_FC_ACP10                           0x1088
-#define HDMI_FC_ACP9                            0x1089
-#define HDMI_FC_ACP8                            0x108A
-#define HDMI_FC_ACP7                            0x108B
-#define HDMI_FC_ACP6                            0x108C
-#define HDMI_FC_ACP5                            0x108D
-#define HDMI_FC_ACP4                            0x108E
-#define HDMI_FC_ACP3                            0x108F
-#define HDMI_FC_ACP2                            0x1090
-#define HDMI_FC_ACP1                            0x1091
-#define HDMI_FC_ISCR1_0                         0x1092
-#define HDMI_FC_ISCR1_16                        0x1093
-#define HDMI_FC_ISCR1_15                        0x1094
-#define HDMI_FC_ISCR1_14                        0x1095
-#define HDMI_FC_ISCR1_13                        0x1096
-#define HDMI_FC_ISCR1_12                        0x1097
-#define HDMI_FC_ISCR1_11                        0x1098
-#define HDMI_FC_ISCR1_10                        0x1099
-#define HDMI_FC_ISCR1_9                         0x109A
-#define HDMI_FC_ISCR1_8                         0x109B
-#define HDMI_FC_ISCR1_7                         0x109C
-#define HDMI_FC_ISCR1_6                         0x109D
-#define HDMI_FC_ISCR1_5                         0x109E
-#define HDMI_FC_ISCR1_4                         0x109F
-#define HDMI_FC_ISCR1_3                         0x10A0
-#define HDMI_FC_ISCR1_2                         0x10A1
-#define HDMI_FC_ISCR1_1                         0x10A2
-#define HDMI_FC_ISCR2_15                        0x10A3
-#define HDMI_FC_ISCR2_14                        0x10A4
-#define HDMI_FC_ISCR2_13                        0x10A5
-#define HDMI_FC_ISCR2_12                        0x10A6
-#define HDMI_FC_ISCR2_11                        0x10A7
-#define HDMI_FC_ISCR2_10                        0x10A8
-#define HDMI_FC_ISCR2_9                         0x10A9
-#define HDMI_FC_ISCR2_8                         0x10AA
-#define HDMI_FC_ISCR2_7                         0x10AB
-#define HDMI_FC_ISCR2_6                         0x10AC
-#define HDMI_FC_ISCR2_5                         0x10AD
-#define HDMI_FC_ISCR2_4                         0x10AE
-#define HDMI_FC_ISCR2_3                         0x10AF
-#define HDMI_FC_ISCR2_2                         0x10B0
-#define HDMI_FC_ISCR2_1                         0x10B1
-#define HDMI_FC_ISCR2_0                         0x10B2
-#define HDMI_FC_DATAUTO0                        0x10B3
-#define HDMI_FC_DATAUTO1                        0x10B4
-#define HDMI_FC_DATAUTO2                        0x10B5
-#define HDMI_FC_DATMAN                          0x10B6
-#define HDMI_FC_DATAUTO3                        0x10B7
-#define HDMI_FC_RDRB0                           0x10B8
-#define HDMI_FC_RDRB1                           0x10B9
-#define HDMI_FC_RDRB2                           0x10BA
-#define HDMI_FC_RDRB3                           0x10BB
-#define HDMI_FC_RDRB4                           0x10BC
-#define HDMI_FC_RDRB5                           0x10BD
-#define HDMI_FC_RDRB6                           0x10BE
-#define HDMI_FC_RDRB7                           0x10BF
-#define HDMI_FC_STAT0                           0x10D0
-#define HDMI_FC_INT0                            0x10D1
-#define HDMI_FC_MASK0                           0x10D2
-#define HDMI_FC_POL0                            0x10D3
-#define HDMI_FC_STAT1                           0x10D4
-#define HDMI_FC_INT1                            0x10D5
-#define HDMI_FC_MASK1                           0x10D6
-#define HDMI_FC_POL1                            0x10D7
-#define HDMI_FC_STAT2                           0x10D8
-#define HDMI_FC_INT2                            0x10D9
-#define HDMI_FC_MASK2                           0x10DA
-#define HDMI_FC_POL2                            0x10DB
-#define HDMI_FC_PRCONF                          0x10E0
-
-#define HDMI_FC_GMD_STAT                        0x1100
-#define HDMI_FC_GMD_EN                          0x1101
-#define HDMI_FC_GMD_UP                          0x1102
-#define HDMI_FC_GMD_CONF                        0x1103
-#define HDMI_FC_GMD_HB                          0x1104
-#define HDMI_FC_GMD_PB0                         0x1105
-#define HDMI_FC_GMD_PB1                         0x1106
-#define HDMI_FC_GMD_PB2                         0x1107
-#define HDMI_FC_GMD_PB3                         0x1108
-#define HDMI_FC_GMD_PB4                         0x1109
-#define HDMI_FC_GMD_PB5                         0x110A
-#define HDMI_FC_GMD_PB6                         0x110B
-#define HDMI_FC_GMD_PB7                         0x110C
-#define HDMI_FC_GMD_PB8                         0x110D
-#define HDMI_FC_GMD_PB9                         0x110E
-#define HDMI_FC_GMD_PB10                        0x110F
-#define HDMI_FC_GMD_PB11                        0x1110
-#define HDMI_FC_GMD_PB12                        0x1111
-#define HDMI_FC_GMD_PB13                        0x1112
-#define HDMI_FC_GMD_PB14                        0x1113
-#define HDMI_FC_GMD_PB15                        0x1114
-#define HDMI_FC_GMD_PB16                        0x1115
-#define HDMI_FC_GMD_PB17                        0x1116
-#define HDMI_FC_GMD_PB18                        0x1117
-#define HDMI_FC_GMD_PB19                        0x1118
-#define HDMI_FC_GMD_PB20                        0x1119
-#define HDMI_FC_GMD_PB21                        0x111A
-#define HDMI_FC_GMD_PB22                        0x111B
-#define HDMI_FC_GMD_PB23                        0x111C
-#define HDMI_FC_GMD_PB24                        0x111D
-#define HDMI_FC_GMD_PB25                        0x111E
-#define HDMI_FC_GMD_PB26                        0x111F
-#define HDMI_FC_GMD_PB27                        0x1120
-
-#define HDMI_FC_DBGFORCE                        0x1200
-#define HDMI_FC_DBGAUD0CH0                      0x1201
-#define HDMI_FC_DBGAUD1CH0                      0x1202
-#define HDMI_FC_DBGAUD2CH0                      0x1203
-#define HDMI_FC_DBGAUD0CH1                      0x1204
-#define HDMI_FC_DBGAUD1CH1                      0x1205
-#define HDMI_FC_DBGAUD2CH1                      0x1206
-#define HDMI_FC_DBGAUD0CH2                      0x1207
-#define HDMI_FC_DBGAUD1CH2                      0x1208
-#define HDMI_FC_DBGAUD2CH2                      0x1209
-#define HDMI_FC_DBGAUD0CH3                      0x120A
-#define HDMI_FC_DBGAUD1CH3                      0x120B
-#define HDMI_FC_DBGAUD2CH3                      0x120C
-#define HDMI_FC_DBGAUD0CH4                      0x120D
-#define HDMI_FC_DBGAUD1CH4                      0x120E
-#define HDMI_FC_DBGAUD2CH4                      0x120F
-#define HDMI_FC_DBGAUD0CH5                      0x1210
-#define HDMI_FC_DBGAUD1CH5                      0x1211
-#define HDMI_FC_DBGAUD2CH5                      0x1212
-#define HDMI_FC_DBGAUD0CH6                      0x1213
-#define HDMI_FC_DBGAUD1CH6                      0x1214
-#define HDMI_FC_DBGAUD2CH6                      0x1215
-#define HDMI_FC_DBGAUD0CH7                      0x1216
-#define HDMI_FC_DBGAUD1CH7                      0x1217
-#define HDMI_FC_DBGAUD2CH7                      0x1218
-#define HDMI_FC_DBGTMDS0                        0x1219
-#define HDMI_FC_DBGTMDS1                        0x121A
-#define HDMI_FC_DBGTMDS2                        0x121B
-
-/* HDMI Source PHY Registers */
-#define HDMI_PHY_CONF0                          0x3000
-#define HDMI_PHY_TST0                           0x3001
-#define HDMI_PHY_TST1                           0x3002
-#define HDMI_PHY_TST2                           0x3003
-#define HDMI_PHY_STAT0                          0x3004
-#define HDMI_PHY_INT0                           0x3005
-#define HDMI_PHY_MASK0                          0x3006
-#define HDMI_PHY_POL0                           0x3007
-
-/* HDMI Master PHY Registers */
-#define HDMI_PHY_I2CM_SLAVE_ADDR                0x3020
-#define HDMI_PHY_I2CM_ADDRESS_ADDR              0x3021
-#define HDMI_PHY_I2CM_DATAO_1_ADDR              0x3022
-#define HDMI_PHY_I2CM_DATAO_0_ADDR              0x3023
-#define HDMI_PHY_I2CM_DATAI_1_ADDR              0x3024
-#define HDMI_PHY_I2CM_DATAI_0_ADDR              0x3025
-#define HDMI_PHY_I2CM_OPERATION_ADDR            0x3026
-#define HDMI_PHY_I2CM_INT_ADDR                  0x3027
-#define HDMI_PHY_I2CM_CTLINT_ADDR               0x3028
-#define HDMI_PHY_I2CM_DIV_ADDR                  0x3029
-#define HDMI_PHY_I2CM_SOFTRSTZ_ADDR             0x302a
-#define HDMI_PHY_I2CM_SS_SCL_HCNT_1_ADDR        0x302b
-#define HDMI_PHY_I2CM_SS_SCL_HCNT_0_ADDR        0x302c
-#define HDMI_PHY_I2CM_SS_SCL_LCNT_1_ADDR        0x302d
-#define HDMI_PHY_I2CM_SS_SCL_LCNT_0_ADDR        0x302e
-#define HDMI_PHY_I2CM_FS_SCL_HCNT_1_ADDR        0x302f
-#define HDMI_PHY_I2CM_FS_SCL_HCNT_0_ADDR        0x3030
-#define HDMI_PHY_I2CM_FS_SCL_LCNT_1_ADDR        0x3031
-#define HDMI_PHY_I2CM_FS_SCL_LCNT_0_ADDR        0x3032
-
-/* Audio Sampler Registers */
-#define HDMI_AUD_CONF0                          0x3100
-#define HDMI_AUD_CONF1                          0x3101
-#define HDMI_AUD_INT                            0x3102
-#define HDMI_AUD_CONF2                          0x3103
-#define HDMI_AUD_N1                             0x3200
-#define HDMI_AUD_N2                             0x3201
-#define HDMI_AUD_N3                             0x3202
-#define HDMI_AUD_CTS1                           0x3203
-#define HDMI_AUD_CTS2                           0x3204
-#define HDMI_AUD_CTS3                           0x3205
-#define HDMI_AUD_INPUTCLKFS                     0x3206
-#define HDMI_AUD_SPDIFINT                      0x3302
-#define HDMI_AUD_CONF0_HBR                      0x3400
-#define HDMI_AUD_HBR_STATUS                     0x3401
-#define HDMI_AUD_HBR_INT                        0x3402
-#define HDMI_AUD_HBR_POL                        0x3403
-#define HDMI_AUD_HBR_MASK                       0x3404
-
-/*
- * Generic Parallel Audio Interface Registers
- * Not used as GPAUD interface is not enabled in hw
- */
-#define HDMI_GP_CONF0                           0x3500
-#define HDMI_GP_CONF1                           0x3501
-#define HDMI_GP_CONF2                           0x3502
-#define HDMI_GP_STAT                            0x3503
-#define HDMI_GP_INT                             0x3504
-#define HDMI_GP_MASK                            0x3505
-#define HDMI_GP_POL                             0x3506
-
-/* Audio DMA Registers */
-#define HDMI_AHB_DMA_CONF0                      0x3600
-#define HDMI_AHB_DMA_START                      0x3601
-#define HDMI_AHB_DMA_STOP                       0x3602
-#define HDMI_AHB_DMA_THRSLD                     0x3603
-#define HDMI_AHB_DMA_STRADDR0                   0x3604
-#define HDMI_AHB_DMA_STRADDR1                   0x3605
-#define HDMI_AHB_DMA_STRADDR2                   0x3606
-#define HDMI_AHB_DMA_STRADDR3                   0x3607
-#define HDMI_AHB_DMA_STPADDR0                   0x3608
-#define HDMI_AHB_DMA_STPADDR1                   0x3609
-#define HDMI_AHB_DMA_STPADDR2                   0x360a
-#define HDMI_AHB_DMA_STPADDR3                   0x360b
-#define HDMI_AHB_DMA_BSTADDR0                   0x360c
-#define HDMI_AHB_DMA_BSTADDR1                   0x360d
-#define HDMI_AHB_DMA_BSTADDR2                   0x360e
-#define HDMI_AHB_DMA_BSTADDR3                   0x360f
-#define HDMI_AHB_DMA_MBLENGTH0                  0x3610
-#define HDMI_AHB_DMA_MBLENGTH1                  0x3611
-#define HDMI_AHB_DMA_STAT                       0x3612
-#define HDMI_AHB_DMA_INT                        0x3613
-#define HDMI_AHB_DMA_MASK                       0x3614
-#define HDMI_AHB_DMA_POL                        0x3615
-#define HDMI_AHB_DMA_CONF1                      0x3616
-#define HDMI_AHB_DMA_BUFFSTAT                   0x3617
-#define HDMI_AHB_DMA_BUFFINT                    0x3618
-#define HDMI_AHB_DMA_BUFFMASK                   0x3619
-#define HDMI_AHB_DMA_BUFFPOL                    0x361a
-
-/* Main Controller Registers */
-#define HDMI_MC_SFRDIV                          0x4000
-#define HDMI_MC_CLKDIS                          0x4001
-#define HDMI_MC_SWRSTZ                          0x4002
-#define HDMI_MC_OPCTRL                          0x4003
-#define HDMI_MC_FLOWCTRL                        0x4004
-#define HDMI_MC_PHYRSTZ                         0x4005
-#define HDMI_MC_LOCKONCLOCK                     0x4006
-#define HDMI_MC_HEACPHY_RST                     0x4007
-
-/* Color Space  Converter Registers */
-#define HDMI_CSC_CFG                            0x4100
-#define HDMI_CSC_SCALE                          0x4101
-#define HDMI_CSC_COEF_A1_MSB                    0x4102
-#define HDMI_CSC_COEF_A1_LSB                    0x4103
-#define HDMI_CSC_COEF_A2_MSB                    0x4104
-#define HDMI_CSC_COEF_A2_LSB                    0x4105
-#define HDMI_CSC_COEF_A3_MSB                    0x4106
-#define HDMI_CSC_COEF_A3_LSB                    0x4107
-#define HDMI_CSC_COEF_A4_MSB                    0x4108
-#define HDMI_CSC_COEF_A4_LSB                    0x4109
-#define HDMI_CSC_COEF_B1_MSB                    0x410A
-#define HDMI_CSC_COEF_B1_LSB                    0x410B
-#define HDMI_CSC_COEF_B2_MSB                    0x410C
-#define HDMI_CSC_COEF_B2_LSB                    0x410D
-#define HDMI_CSC_COEF_B3_MSB                    0x410E
-#define HDMI_CSC_COEF_B3_LSB                    0x410F
-#define HDMI_CSC_COEF_B4_MSB                    0x4110
-#define HDMI_CSC_COEF_B4_LSB                    0x4111
-#define HDMI_CSC_COEF_C1_MSB                    0x4112
-#define HDMI_CSC_COEF_C1_LSB                    0x4113
-#define HDMI_CSC_COEF_C2_MSB                    0x4114
-#define HDMI_CSC_COEF_C2_LSB                    0x4115
-#define HDMI_CSC_COEF_C3_MSB                    0x4116
-#define HDMI_CSC_COEF_C3_LSB                    0x4117
-#define HDMI_CSC_COEF_C4_MSB                    0x4118
-#define HDMI_CSC_COEF_C4_LSB                    0x4119
-
-/* HDCP Encryption Engine Registers */
-#define HDMI_A_HDCPCFG0                         0x5000
-#define HDMI_A_HDCPCFG1                         0x5001
-#define HDMI_A_HDCPOBS0                         0x5002
-#define HDMI_A_HDCPOBS1                         0x5003
-#define HDMI_A_HDCPOBS2                         0x5004
-#define HDMI_A_HDCPOBS3                         0x5005
-#define HDMI_A_APIINTCLR                        0x5006
-#define HDMI_A_APIINTSTAT                       0x5007
-#define HDMI_A_APIINTMSK                        0x5008
-#define HDMI_A_VIDPOLCFG                        0x5009
-#define HDMI_A_OESSWCFG                         0x500A
-#define HDMI_A_TIMER1SETUP0                     0x500B
-#define HDMI_A_TIMER1SETUP1                     0x500C
-#define HDMI_A_TIMER2SETUP0                     0x500D
-#define HDMI_A_TIMER2SETUP1                     0x500E
-#define HDMI_A_100MSCFG                         0x500F
-#define HDMI_A_2SCFG0                           0x5010
-#define HDMI_A_2SCFG1                           0x5011
-#define HDMI_A_5SCFG0                           0x5012
-#define HDMI_A_5SCFG1                           0x5013
-#define HDMI_A_SRMVERLSB                        0x5014
-#define HDMI_A_SRMVERMSB                        0x5015
-#define HDMI_A_SRMCTRL                          0x5016
-#define HDMI_A_SFRSETUP                         0x5017
-#define HDMI_A_I2CHSETUP                        0x5018
-#define HDMI_A_INTSETUP                         0x5019
-#define HDMI_A_PRESETUP                         0x501A
-#define HDMI_A_SRM_BASE                         0x5020
-
-/* CEC Engine Registers */
-#define HDMI_CEC_CTRL                           0x7D00
-#define HDMI_CEC_STAT                           0x7D01
-#define HDMI_CEC_MASK                           0x7D02
-#define HDMI_CEC_POLARITY                       0x7D03
-#define HDMI_CEC_INT                            0x7D04
-#define HDMI_CEC_ADDR_L                         0x7D05
-#define HDMI_CEC_ADDR_H                         0x7D06
-#define HDMI_CEC_TX_CNT                         0x7D07
-#define HDMI_CEC_RX_CNT                         0x7D08
-#define HDMI_CEC_TX_DATA0                       0x7D10
-#define HDMI_CEC_TX_DATA1                       0x7D11
-#define HDMI_CEC_TX_DATA2                       0x7D12
-#define HDMI_CEC_TX_DATA3                       0x7D13
-#define HDMI_CEC_TX_DATA4                       0x7D14
-#define HDMI_CEC_TX_DATA5                       0x7D15
-#define HDMI_CEC_TX_DATA6                       0x7D16
-#define HDMI_CEC_TX_DATA7                       0x7D17
-#define HDMI_CEC_TX_DATA8                       0x7D18
-#define HDMI_CEC_TX_DATA9                       0x7D19
-#define HDMI_CEC_TX_DATA10                      0x7D1a
-#define HDMI_CEC_TX_DATA11                      0x7D1b
-#define HDMI_CEC_TX_DATA12                      0x7D1c
-#define HDMI_CEC_TX_DATA13                      0x7D1d
-#define HDMI_CEC_TX_DATA14                      0x7D1e
-#define HDMI_CEC_TX_DATA15                      0x7D1f
-#define HDMI_CEC_RX_DATA0                       0x7D20
-#define HDMI_CEC_RX_DATA1                       0x7D21
-#define HDMI_CEC_RX_DATA2                       0x7D22
-#define HDMI_CEC_RX_DATA3                       0x7D23
-#define HDMI_CEC_RX_DATA4                       0x7D24
-#define HDMI_CEC_RX_DATA5                       0x7D25
-#define HDMI_CEC_RX_DATA6                       0x7D26
-#define HDMI_CEC_RX_DATA7                       0x7D27
-#define HDMI_CEC_RX_DATA8                       0x7D28
-#define HDMI_CEC_RX_DATA9                       0x7D29
-#define HDMI_CEC_RX_DATA10                      0x7D2a
-#define HDMI_CEC_RX_DATA11                      0x7D2b
-#define HDMI_CEC_RX_DATA12                      0x7D2c
-#define HDMI_CEC_RX_DATA13                      0x7D2d
-#define HDMI_CEC_RX_DATA14                      0x7D2e
-#define HDMI_CEC_RX_DATA15                      0x7D2f
-#define HDMI_CEC_LOCK                           0x7D30
-#define HDMI_CEC_WKUPCTRL                       0x7D31
-
-/* I2C Master Registers (E-DDC) */
-#define HDMI_I2CM_SLAVE                         0x7E00
-#define HDMI_I2CMESS                            0x7E01
-#define HDMI_I2CM_DATAO                         0x7E02
-#define HDMI_I2CM_DATAI                         0x7E03
-#define HDMI_I2CM_OPERATION                     0x7E04
-#define HDMI_I2CM_INT                           0x7E05
-#define HDMI_I2CM_CTLINT                        0x7E06
-#define HDMI_I2CM_DIV                           0x7E07
-#define HDMI_I2CM_SEGADDR                       0x7E08
-#define HDMI_I2CM_SOFTRSTZ                      0x7E09
-#define HDMI_I2CM_SEGPTR                        0x7E0A
-#define HDMI_I2CM_SS_SCL_HCNT_1_ADDR            0x7E0B
-#define HDMI_I2CM_SS_SCL_HCNT_0_ADDR            0x7E0C
-#define HDMI_I2CM_SS_SCL_LCNT_1_ADDR            0x7E0D
-#define HDMI_I2CM_SS_SCL_LCNT_0_ADDR            0x7E0E
-#define HDMI_I2CM_FS_SCL_HCNT_1_ADDR            0x7E0F
-#define HDMI_I2CM_FS_SCL_HCNT_0_ADDR            0x7E10
-#define HDMI_I2CM_FS_SCL_LCNT_1_ADDR            0x7E11
-#define HDMI_I2CM_FS_SCL_LCNT_0_ADDR            0x7E12
-
-enum {
-/* IH_FC_INT2 field values */
-       HDMI_IH_FC_INT2_OVERFLOW_MASK = 0x03,
-       HDMI_IH_FC_INT2_LOW_PRIORITY_OVERFLOW = 0x02,
-       HDMI_IH_FC_INT2_HIGH_PRIORITY_OVERFLOW = 0x01,
-
-/* IH_FC_STAT2 field values */
-       HDMI_IH_FC_STAT2_OVERFLOW_MASK = 0x03,
-       HDMI_IH_FC_STAT2_LOW_PRIORITY_OVERFLOW = 0x02,
-       HDMI_IH_FC_STAT2_HIGH_PRIORITY_OVERFLOW = 0x01,
-
-/* IH_PHY_STAT0 field values */
-       HDMI_IH_PHY_STAT0_RX_SENSE3 = 0x20,
-       HDMI_IH_PHY_STAT0_RX_SENSE2 = 0x10,
-       HDMI_IH_PHY_STAT0_RX_SENSE1 = 0x8,
-       HDMI_IH_PHY_STAT0_RX_SENSE0 = 0x4,
-       HDMI_IH_PHY_STAT0_TX_PHY_LOCK = 0x2,
-       HDMI_IH_PHY_STAT0_HPD = 0x1,
-
-/* IH_MUTE_I2CMPHY_STAT0 field values */
-       HDMI_IH_MUTE_I2CMPHY_STAT0_I2CMPHYDONE = 0x2,
-       HDMI_IH_MUTE_I2CMPHY_STAT0_I2CMPHYERROR = 0x1,
-
-/* IH_AHBDMAAUD_STAT0 field values */
-       HDMI_IH_AHBDMAAUD_STAT0_ERROR = 0x20,
-       HDMI_IH_AHBDMAAUD_STAT0_LOST = 0x10,
-       HDMI_IH_AHBDMAAUD_STAT0_RETRY = 0x08,
-       HDMI_IH_AHBDMAAUD_STAT0_DONE = 0x04,
-       HDMI_IH_AHBDMAAUD_STAT0_BUFFFULL = 0x02,
-       HDMI_IH_AHBDMAAUD_STAT0_BUFFEMPTY = 0x01,
-
-/* IH_MUTE_FC_STAT2 field values */
-       HDMI_IH_MUTE_FC_STAT2_OVERFLOW_MASK = 0x03,
-       HDMI_IH_MUTE_FC_STAT2_LOW_PRIORITY_OVERFLOW = 0x02,
-       HDMI_IH_MUTE_FC_STAT2_HIGH_PRIORITY_OVERFLOW = 0x01,
-
-/* IH_MUTE_AHBDMAAUD_STAT0 field values */
-       HDMI_IH_MUTE_AHBDMAAUD_STAT0_ERROR = 0x20,
-       HDMI_IH_MUTE_AHBDMAAUD_STAT0_LOST = 0x10,
-       HDMI_IH_MUTE_AHBDMAAUD_STAT0_RETRY = 0x08,
-       HDMI_IH_MUTE_AHBDMAAUD_STAT0_DONE = 0x04,
-       HDMI_IH_MUTE_AHBDMAAUD_STAT0_BUFFFULL = 0x02,
-       HDMI_IH_MUTE_AHBDMAAUD_STAT0_BUFFEMPTY = 0x01,
-
-/* IH_MUTE field values */
-       HDMI_IH_MUTE_MUTE_WAKEUP_INTERRUPT = 0x2,
-       HDMI_IH_MUTE_MUTE_ALL_INTERRUPT = 0x1,
-
-/* TX_INVID0 field values */
-       HDMI_TX_INVID0_INTERNAL_DE_GENERATOR_MASK = 0x80,
-       HDMI_TX_INVID0_INTERNAL_DE_GENERATOR_ENABLE = 0x80,
-       HDMI_TX_INVID0_INTERNAL_DE_GENERATOR_DISABLE = 0x00,
-       HDMI_TX_INVID0_VIDEO_MAPPING_MASK = 0x1F,
-       HDMI_TX_INVID0_VIDEO_MAPPING_OFFSET = 0,
-
-/* TX_INSTUFFING field values */
-       HDMI_TX_INSTUFFING_BDBDATA_STUFFING_MASK = 0x4,
-       HDMI_TX_INSTUFFING_BDBDATA_STUFFING_ENABLE = 0x4,
-       HDMI_TX_INSTUFFING_BDBDATA_STUFFING_DISABLE = 0x0,
-       HDMI_TX_INSTUFFING_RCRDATA_STUFFING_MASK = 0x2,
-       HDMI_TX_INSTUFFING_RCRDATA_STUFFING_ENABLE = 0x2,
-       HDMI_TX_INSTUFFING_RCRDATA_STUFFING_DISABLE = 0x0,
-       HDMI_TX_INSTUFFING_GYDATA_STUFFING_MASK = 0x1,
-       HDMI_TX_INSTUFFING_GYDATA_STUFFING_ENABLE = 0x1,
-       HDMI_TX_INSTUFFING_GYDATA_STUFFING_DISABLE = 0x0,
-
-/* VP_PR_CD field values */
-       HDMI_VP_PR_CD_COLOR_DEPTH_MASK = 0xF0,
-       HDMI_VP_PR_CD_COLOR_DEPTH_OFFSET = 4,
-       HDMI_VP_PR_CD_DESIRED_PR_FACTOR_MASK = 0x0F,
-       HDMI_VP_PR_CD_DESIRED_PR_FACTOR_OFFSET = 0,
-
-/* VP_STUFF field values */
-       HDMI_VP_STUFF_IDEFAULT_PHASE_MASK = 0x20,
-       HDMI_VP_STUFF_IDEFAULT_PHASE_OFFSET = 5,
-       HDMI_VP_STUFF_IFIX_PP_TO_LAST_MASK = 0x10,
-       HDMI_VP_STUFF_IFIX_PP_TO_LAST_OFFSET = 4,
-       HDMI_VP_STUFF_ICX_GOTO_P0_ST_MASK = 0x8,
-       HDMI_VP_STUFF_ICX_GOTO_P0_ST_OFFSET = 3,
-       HDMI_VP_STUFF_YCC422_STUFFING_MASK = 0x4,
-       HDMI_VP_STUFF_YCC422_STUFFING_STUFFING_MODE = 0x4,
-       HDMI_VP_STUFF_YCC422_STUFFING_DIRECT_MODE = 0x0,
-       HDMI_VP_STUFF_PP_STUFFING_MASK = 0x2,
-       HDMI_VP_STUFF_PP_STUFFING_STUFFING_MODE = 0x2,
-       HDMI_VP_STUFF_PP_STUFFING_DIRECT_MODE = 0x0,
-       HDMI_VP_STUFF_PR_STUFFING_MASK = 0x1,
-       HDMI_VP_STUFF_PR_STUFFING_STUFFING_MODE = 0x1,
-       HDMI_VP_STUFF_PR_STUFFING_DIRECT_MODE = 0x0,
-
-/* VP_CONF field values */
-       HDMI_VP_CONF_BYPASS_EN_MASK = 0x40,
-       HDMI_VP_CONF_BYPASS_EN_ENABLE = 0x40,
-       HDMI_VP_CONF_BYPASS_EN_DISABLE = 0x00,
-       HDMI_VP_CONF_PP_EN_ENMASK = 0x20,
-       HDMI_VP_CONF_PP_EN_ENABLE = 0x20,
-       HDMI_VP_CONF_PP_EN_DISABLE = 0x00,
-       HDMI_VP_CONF_PR_EN_MASK = 0x10,
-       HDMI_VP_CONF_PR_EN_ENABLE = 0x10,
-       HDMI_VP_CONF_PR_EN_DISABLE = 0x00,
-       HDMI_VP_CONF_YCC422_EN_MASK = 0x8,
-       HDMI_VP_CONF_YCC422_EN_ENABLE = 0x8,
-       HDMI_VP_CONF_YCC422_EN_DISABLE = 0x0,
-       HDMI_VP_CONF_BYPASS_SELECT_MASK = 0x4,
-       HDMI_VP_CONF_BYPASS_SELECT_VID_PACKETIZER = 0x4,
-       HDMI_VP_CONF_BYPASS_SELECT_PIX_REPEATER = 0x0,
-       HDMI_VP_CONF_OUTPUT_SELECTOR_MASK = 0x3,
-       HDMI_VP_CONF_OUTPUT_SELECTOR_BYPASS = 0x3,
-       HDMI_VP_CONF_OUTPUT_SELECTOR_YCC422 = 0x1,
-       HDMI_VP_CONF_OUTPUT_SELECTOR_PP = 0x0,
-
-/* VP_REMAP field values */
-       HDMI_VP_REMAP_MASK = 0x3,
-       HDMI_VP_REMAP_YCC422_24bit = 0x2,
-       HDMI_VP_REMAP_YCC422_20bit = 0x1,
-       HDMI_VP_REMAP_YCC422_16bit = 0x0,
-
-/* FC_INVIDCONF field values */
-       HDMI_FC_INVIDCONF_HDCP_KEEPOUT_MASK = 0x80,
-       HDMI_FC_INVIDCONF_HDCP_KEEPOUT_ACTIVE = 0x80,
-       HDMI_FC_INVIDCONF_HDCP_KEEPOUT_INACTIVE = 0x00,
-       HDMI_FC_INVIDCONF_VSYNC_IN_POLARITY_MASK = 0x40,
-       HDMI_FC_INVIDCONF_VSYNC_IN_POLARITY_ACTIVE_HIGH = 0x40,
-       HDMI_FC_INVIDCONF_VSYNC_IN_POLARITY_ACTIVE_LOW = 0x00,
-       HDMI_FC_INVIDCONF_HSYNC_IN_POLARITY_MASK = 0x20,
-       HDMI_FC_INVIDCONF_HSYNC_IN_POLARITY_ACTIVE_HIGH = 0x20,
-       HDMI_FC_INVIDCONF_HSYNC_IN_POLARITY_ACTIVE_LOW = 0x00,
-       HDMI_FC_INVIDCONF_DE_IN_POLARITY_MASK = 0x10,
-       HDMI_FC_INVIDCONF_DE_IN_POLARITY_ACTIVE_HIGH = 0x10,
-       HDMI_FC_INVIDCONF_DE_IN_POLARITY_ACTIVE_LOW = 0x00,
-       HDMI_FC_INVIDCONF_DVI_MODEZ_MASK = 0x8,
-       HDMI_FC_INVIDCONF_DVI_MODEZ_HDMI_MODE = 0x8,
-       HDMI_FC_INVIDCONF_DVI_MODEZ_DVI_MODE = 0x0,
-       HDMI_FC_INVIDCONF_R_V_BLANK_IN_OSC_MASK = 0x2,
-       HDMI_FC_INVIDCONF_R_V_BLANK_IN_OSC_ACTIVE_HIGH = 0x2,
-       HDMI_FC_INVIDCONF_R_V_BLANK_IN_OSC_ACTIVE_LOW = 0x0,
-       HDMI_FC_INVIDCONF_IN_I_P_MASK = 0x1,
-       HDMI_FC_INVIDCONF_IN_I_P_INTERLACED = 0x1,
-       HDMI_FC_INVIDCONF_IN_I_P_PROGRESSIVE = 0x0,
-
-/* FC_AUDICONF0 field values */
-       HDMI_FC_AUDICONF0_CC_OFFSET = 4,
-       HDMI_FC_AUDICONF0_CC_MASK = 0x70,
-       HDMI_FC_AUDICONF0_CT_OFFSET = 0,
-       HDMI_FC_AUDICONF0_CT_MASK = 0xF,
-
-/* FC_AUDICONF1 field values */
-       HDMI_FC_AUDICONF1_SS_OFFSET = 3,
-       HDMI_FC_AUDICONF1_SS_MASK = 0x18,
-       HDMI_FC_AUDICONF1_SF_OFFSET = 0,
-       HDMI_FC_AUDICONF1_SF_MASK = 0x7,
-
-/* FC_AUDICONF3 field values */
-       HDMI_FC_AUDICONF3_LFEPBL_OFFSET = 5,
-       HDMI_FC_AUDICONF3_LFEPBL_MASK = 0x60,
-       HDMI_FC_AUDICONF3_DM_INH_OFFSET = 4,
-       HDMI_FC_AUDICONF3_DM_INH_MASK = 0x10,
-       HDMI_FC_AUDICONF3_LSV_OFFSET = 0,
-       HDMI_FC_AUDICONF3_LSV_MASK = 0xF,
-
-/* FC_AUDSCHNLS0 field values */
-       HDMI_FC_AUDSCHNLS0_CGMSA_OFFSET = 4,
-       HDMI_FC_AUDSCHNLS0_CGMSA_MASK = 0x30,
-       HDMI_FC_AUDSCHNLS0_COPYRIGHT_OFFSET = 0,
-       HDMI_FC_AUDSCHNLS0_COPYRIGHT_MASK = 0x01,
-
-/* FC_AUDSCHNLS3-6 field values */
-       HDMI_FC_AUDSCHNLS3_OIEC_CH0_OFFSET = 0,
-       HDMI_FC_AUDSCHNLS3_OIEC_CH0_MASK = 0x0f,
-       HDMI_FC_AUDSCHNLS3_OIEC_CH1_OFFSET = 4,
-       HDMI_FC_AUDSCHNLS3_OIEC_CH1_MASK = 0xf0,
-       HDMI_FC_AUDSCHNLS4_OIEC_CH2_OFFSET = 0,
-       HDMI_FC_AUDSCHNLS4_OIEC_CH2_MASK = 0x0f,
-       HDMI_FC_AUDSCHNLS4_OIEC_CH3_OFFSET = 4,
-       HDMI_FC_AUDSCHNLS4_OIEC_CH3_MASK = 0xf0,
-
-       HDMI_FC_AUDSCHNLS5_OIEC_CH0_OFFSET = 0,
-       HDMI_FC_AUDSCHNLS5_OIEC_CH0_MASK = 0x0f,
-       HDMI_FC_AUDSCHNLS5_OIEC_CH1_OFFSET = 4,
-       HDMI_FC_AUDSCHNLS5_OIEC_CH1_MASK = 0xf0,
-       HDMI_FC_AUDSCHNLS6_OIEC_CH2_OFFSET = 0,
-       HDMI_FC_AUDSCHNLS6_OIEC_CH2_MASK = 0x0f,
-       HDMI_FC_AUDSCHNLS6_OIEC_CH3_OFFSET = 4,
-       HDMI_FC_AUDSCHNLS6_OIEC_CH3_MASK = 0xf0,
-
-/* HDMI_FC_AUDSCHNLS7 field values */
-       HDMI_FC_AUDSCHNLS7_ACCURACY_OFFSET = 4,
-       HDMI_FC_AUDSCHNLS7_ACCURACY_MASK = 0x30,
-
-/* HDMI_FC_AUDSCHNLS8 field values */
-       HDMI_FC_AUDSCHNLS8_ORIGSAMPFREQ_MASK = 0xf0,
-       HDMI_FC_AUDSCHNLS8_ORIGSAMPFREQ_OFFSET = 4,
-       HDMI_FC_AUDSCHNLS8_WORDLEGNTH_MASK = 0x0f,
-       HDMI_FC_AUDSCHNLS8_WORDLEGNTH_OFFSET = 0,
-
-/* FC_AUDSCONF field values */
-       HDMI_FC_AUDSCONF_AUD_PACKET_SAMPFIT_MASK = 0xF0,
-       HDMI_FC_AUDSCONF_AUD_PACKET_SAMPFIT_OFFSET = 4,
-       HDMI_FC_AUDSCONF_AUD_PACKET_LAYOUT_MASK = 0x1,
-       HDMI_FC_AUDSCONF_AUD_PACKET_LAYOUT_OFFSET = 0,
-       HDMI_FC_AUDSCONF_AUD_PACKET_LAYOUT_LAYOUT1 = 0x1,
-       HDMI_FC_AUDSCONF_AUD_PACKET_LAYOUT_LAYOUT0 = 0x0,
-
-/* FC_STAT2 field values */
-       HDMI_FC_STAT2_OVERFLOW_MASK = 0x03,
-       HDMI_FC_STAT2_LOW_PRIORITY_OVERFLOW = 0x02,
-       HDMI_FC_STAT2_HIGH_PRIORITY_OVERFLOW = 0x01,
-
-/* FC_INT2 field values */
-       HDMI_FC_INT2_OVERFLOW_MASK = 0x03,
-       HDMI_FC_INT2_LOW_PRIORITY_OVERFLOW = 0x02,
-       HDMI_FC_INT2_HIGH_PRIORITY_OVERFLOW = 0x01,
-
-/* FC_MASK2 field values */
-       HDMI_FC_MASK2_OVERFLOW_MASK = 0x03,
-       HDMI_FC_MASK2_LOW_PRIORITY_OVERFLOW = 0x02,
-       HDMI_FC_MASK2_HIGH_PRIORITY_OVERFLOW = 0x01,
-
-/* FC_PRCONF field values */
-       HDMI_FC_PRCONF_INCOMING_PR_FACTOR_MASK = 0xF0,
-       HDMI_FC_PRCONF_INCOMING_PR_FACTOR_OFFSET = 4,
-       HDMI_FC_PRCONF_OUTPUT_PR_FACTOR_MASK = 0x0F,
-       HDMI_FC_PRCONF_OUTPUT_PR_FACTOR_OFFSET = 0,
-
-/* FC_AVICONF0-FC_AVICONF3 field values */
-       HDMI_FC_AVICONF0_PIX_FMT_MASK = 0x03,
-       HDMI_FC_AVICONF0_PIX_FMT_RGB = 0x00,
-       HDMI_FC_AVICONF0_PIX_FMT_YCBCR422 = 0x01,
-       HDMI_FC_AVICONF0_PIX_FMT_YCBCR444 = 0x02,
-       HDMI_FC_AVICONF0_ACTIVE_FMT_MASK = 0x40,
-       HDMI_FC_AVICONF0_ACTIVE_FMT_INFO_PRESENT = 0x40,
-       HDMI_FC_AVICONF0_ACTIVE_FMT_NO_INFO = 0x00,
-       HDMI_FC_AVICONF0_BAR_DATA_MASK = 0x0C,
-       HDMI_FC_AVICONF0_BAR_DATA_NO_DATA = 0x00,
-       HDMI_FC_AVICONF0_BAR_DATA_VERT_BAR = 0x04,
-       HDMI_FC_AVICONF0_BAR_DATA_HORIZ_BAR = 0x08,
-       HDMI_FC_AVICONF0_BAR_DATA_VERT_HORIZ_BAR = 0x0C,
-       HDMI_FC_AVICONF0_SCAN_INFO_MASK = 0x30,
-       HDMI_FC_AVICONF0_SCAN_INFO_OVERSCAN = 0x10,
-       HDMI_FC_AVICONF0_SCAN_INFO_UNDERSCAN = 0x20,
-       HDMI_FC_AVICONF0_SCAN_INFO_NODATA = 0x00,
-
-       HDMI_FC_AVICONF1_ACTIVE_ASPECT_RATIO_MASK = 0x0F,
-       HDMI_FC_AVICONF1_ACTIVE_ASPECT_RATIO_USE_CODED = 0x08,
-       HDMI_FC_AVICONF1_ACTIVE_ASPECT_RATIO_4_3 = 0x09,
-       HDMI_FC_AVICONF1_ACTIVE_ASPECT_RATIO_16_9 = 0x0A,
-       HDMI_FC_AVICONF1_ACTIVE_ASPECT_RATIO_14_9 = 0x0B,
-       HDMI_FC_AVICONF1_CODED_ASPECT_RATIO_MASK = 0x30,
-       HDMI_FC_AVICONF1_CODED_ASPECT_RATIO_NO_DATA = 0x00,
-       HDMI_FC_AVICONF1_CODED_ASPECT_RATIO_4_3 = 0x10,
-       HDMI_FC_AVICONF1_CODED_ASPECT_RATIO_16_9 = 0x20,
-       HDMI_FC_AVICONF1_COLORIMETRY_MASK = 0xC0,
-       HDMI_FC_AVICONF1_COLORIMETRY_NO_DATA = 0x00,
-       HDMI_FC_AVICONF1_COLORIMETRY_SMPTE = 0x40,
-       HDMI_FC_AVICONF1_COLORIMETRY_ITUR = 0x80,
-       HDMI_FC_AVICONF1_COLORIMETRY_EXTENDED_INFO = 0xC0,
-
-       HDMI_FC_AVICONF2_SCALING_MASK = 0x03,
-       HDMI_FC_AVICONF2_SCALING_NONE = 0x00,
-       HDMI_FC_AVICONF2_SCALING_HORIZ = 0x01,
-       HDMI_FC_AVICONF2_SCALING_VERT = 0x02,
-       HDMI_FC_AVICONF2_SCALING_HORIZ_VERT = 0x03,
-       HDMI_FC_AVICONF2_RGB_QUANT_MASK = 0x0C,
-       HDMI_FC_AVICONF2_RGB_QUANT_DEFAULT = 0x00,
-       HDMI_FC_AVICONF2_RGB_QUANT_LIMITED_RANGE = 0x04,
-       HDMI_FC_AVICONF2_RGB_QUANT_FULL_RANGE = 0x08,
-       HDMI_FC_AVICONF2_EXT_COLORIMETRY_MASK = 0x70,
-       HDMI_FC_AVICONF2_EXT_COLORIMETRY_XVYCC601 = 0x00,
-       HDMI_FC_AVICONF2_EXT_COLORIMETRY_XVYCC709 = 0x10,
-       HDMI_FC_AVICONF2_EXT_COLORIMETRY_SYCC601 = 0x20,
-       HDMI_FC_AVICONF2_EXT_COLORIMETRY_ADOBE_YCC601 = 0x30,
-       HDMI_FC_AVICONF2_EXT_COLORIMETRY_ADOBE_RGB = 0x40,
-       HDMI_FC_AVICONF2_IT_CONTENT_MASK = 0x80,
-       HDMI_FC_AVICONF2_IT_CONTENT_NO_DATA = 0x00,
-       HDMI_FC_AVICONF2_IT_CONTENT_VALID = 0x80,
-
-       HDMI_FC_AVICONF3_IT_CONTENT_TYPE_MASK = 0x03,
-       HDMI_FC_AVICONF3_IT_CONTENT_TYPE_GRAPHICS = 0x00,
-       HDMI_FC_AVICONF3_IT_CONTENT_TYPE_PHOTO = 0x01,
-       HDMI_FC_AVICONF3_IT_CONTENT_TYPE_CINEMA = 0x02,
-       HDMI_FC_AVICONF3_IT_CONTENT_TYPE_GAME = 0x03,
-       HDMI_FC_AVICONF3_QUANT_RANGE_MASK = 0x0C,
-       HDMI_FC_AVICONF3_QUANT_RANGE_LIMITED = 0x00,
-       HDMI_FC_AVICONF3_QUANT_RANGE_FULL = 0x04,
-
-/* FC_DBGFORCE field values */
-       HDMI_FC_DBGFORCE_FORCEAUDIO = 0x10,
-       HDMI_FC_DBGFORCE_FORCEVIDEO = 0x1,
-
-/* PHY_CONF0 field values */
-       HDMI_PHY_CONF0_PDZ_MASK = 0x80,
-       HDMI_PHY_CONF0_PDZ_OFFSET = 7,
-       HDMI_PHY_CONF0_ENTMDS_MASK = 0x40,
-       HDMI_PHY_CONF0_ENTMDS_OFFSET = 6,
-       HDMI_PHY_CONF0_SPARECTRL = 0x20,
-       HDMI_PHY_CONF0_GEN2_PDDQ_MASK = 0x10,
-       HDMI_PHY_CONF0_GEN2_PDDQ_OFFSET = 4,
-       HDMI_PHY_CONF0_GEN2_TXPWRON_MASK = 0x8,
-       HDMI_PHY_CONF0_GEN2_TXPWRON_OFFSET = 3,
-       HDMI_PHY_CONF0_GEN2_ENHPDRXSENSE_MASK = 0x4,
-       HDMI_PHY_CONF0_GEN2_ENHPDRXSENSE_OFFSET = 2,
-       HDMI_PHY_CONF0_SELDATAENPOL_MASK = 0x2,
-       HDMI_PHY_CONF0_SELDATAENPOL_OFFSET = 1,
-       HDMI_PHY_CONF0_SELDIPIF_MASK = 0x1,
-       HDMI_PHY_CONF0_SELDIPIF_OFFSET = 0,
-
-/* PHY_TST0 field values */
-       HDMI_PHY_TST0_TSTCLR_MASK = 0x20,
-       HDMI_PHY_TST0_TSTCLR_OFFSET = 5,
-       HDMI_PHY_TST0_TSTEN_MASK = 0x10,
-       HDMI_PHY_TST0_TSTEN_OFFSET = 4,
-       HDMI_PHY_TST0_TSTCLK_MASK = 0x1,
-       HDMI_PHY_TST0_TSTCLK_OFFSET = 0,
-
-/* PHY_STAT0 field values */
-       HDMI_PHY_RX_SENSE3 = 0x80,
-       HDMI_PHY_RX_SENSE2 = 0x40,
-       HDMI_PHY_RX_SENSE1 = 0x20,
-       HDMI_PHY_RX_SENSE0 = 0x10,
-       HDMI_PHY_HPD = 0x02,
-       HDMI_PHY_TX_PHY_LOCK = 0x01,
-
-/* PHY_I2CM_SLAVE_ADDR field values */
-       HDMI_PHY_I2CM_SLAVE_ADDR_PHY_GEN2 = 0x69,
-       HDMI_PHY_I2CM_SLAVE_ADDR_HEAC_PHY = 0x49,
-
-/* PHY_I2CM_OPERATION_ADDR field values */
-       HDMI_PHY_I2CM_OPERATION_ADDR_WRITE = 0x10,
-       HDMI_PHY_I2CM_OPERATION_ADDR_READ = 0x1,
-
-/* HDMI_PHY_I2CM_INT_ADDR */
-       HDMI_PHY_I2CM_INT_ADDR_DONE_POL = 0x08,
-       HDMI_PHY_I2CM_INT_ADDR_DONE_MASK = 0x04,
-
-/* HDMI_PHY_I2CM_CTLINT_ADDR */
-       HDMI_PHY_I2CM_CTLINT_ADDR_NAC_POL = 0x80,
-       HDMI_PHY_I2CM_CTLINT_ADDR_NAC_MASK = 0x40,
-       HDMI_PHY_I2CM_CTLINT_ADDR_ARBITRATION_POL = 0x08,
-       HDMI_PHY_I2CM_CTLINT_ADDR_ARBITRATION_MASK = 0x04,
-
-/* AUD_CTS3 field values */
-       HDMI_AUD_CTS3_N_SHIFT_OFFSET = 5,
-       HDMI_AUD_CTS3_N_SHIFT_MASK = 0xe0,
-       HDMI_AUD_CTS3_N_SHIFT_1 = 0,
-       HDMI_AUD_CTS3_N_SHIFT_16 = 0x20,
-       HDMI_AUD_CTS3_N_SHIFT_32 = 0x40,
-       HDMI_AUD_CTS3_N_SHIFT_64 = 0x60,
-       HDMI_AUD_CTS3_N_SHIFT_128 = 0x80,
-       HDMI_AUD_CTS3_N_SHIFT_256 = 0xa0,
-       /* note that the CTS3 MANUAL bit has been removed
-          from our part. Can't set it, will read as 0. */
-       HDMI_AUD_CTS3_CTS_MANUAL = 0x10,
-       HDMI_AUD_CTS3_AUDCTS19_16_MASK = 0x0f,
-
-/* AHB_DMA_CONF0 field values */
-       HDMI_AHB_DMA_CONF0_SW_FIFO_RST_OFFSET = 7,
-       HDMI_AHB_DMA_CONF0_SW_FIFO_RST_MASK = 0x80,
-       HDMI_AHB_DMA_CONF0_HBR = 0x10,
-       HDMI_AHB_DMA_CONF0_EN_HLOCK_OFFSET = 3,
-       HDMI_AHB_DMA_CONF0_EN_HLOCK_MASK = 0x08,
-       HDMI_AHB_DMA_CONF0_INCR_TYPE_OFFSET = 1,
-       HDMI_AHB_DMA_CONF0_INCR_TYPE_MASK = 0x06,
-       HDMI_AHB_DMA_CONF0_INCR4 = 0x0,
-       HDMI_AHB_DMA_CONF0_INCR8 = 0x2,
-       HDMI_AHB_DMA_CONF0_INCR16 = 0x4,
-       HDMI_AHB_DMA_CONF0_BURST_MODE = 0x1,
-
-/* HDMI_AHB_DMA_START field values */
-       HDMI_AHB_DMA_START_START_OFFSET = 0,
-       HDMI_AHB_DMA_START_START_MASK = 0x01,
-
-/* HDMI_AHB_DMA_STOP field values */
-       HDMI_AHB_DMA_STOP_STOP_OFFSET = 0,
-       HDMI_AHB_DMA_STOP_STOP_MASK = 0x01,
-
-/* AHB_DMA_STAT, AHB_DMA_INT, AHB_DMA_MASK, AHB_DMA_POL field values */
-       HDMI_AHB_DMA_DONE = 0x80,
-       HDMI_AHB_DMA_RETRY_SPLIT = 0x40,
-       HDMI_AHB_DMA_LOSTOWNERSHIP = 0x20,
-       HDMI_AHB_DMA_ERROR = 0x10,
-       HDMI_AHB_DMA_FIFO_THREMPTY = 0x04,
-       HDMI_AHB_DMA_FIFO_FULL = 0x02,
-       HDMI_AHB_DMA_FIFO_EMPTY = 0x01,
-
-/* AHB_DMA_BUFFSTAT, AHB_DMA_BUFFINT,AHB_DMA_BUFFMASK,AHB_DMA_BUFFPOL values */
-       HDMI_AHB_DMA_BUFFSTAT_FULL = 0x02,
-       HDMI_AHB_DMA_BUFFSTAT_EMPTY = 0x01,
-
-/* MC_CLKDIS field values */
-       HDMI_MC_CLKDIS_HDCPCLK_DISABLE = 0x40,
-       HDMI_MC_CLKDIS_CECCLK_DISABLE = 0x20,
-       HDMI_MC_CLKDIS_CSCCLK_DISABLE = 0x10,
-       HDMI_MC_CLKDIS_AUDCLK_DISABLE = 0x8,
-       HDMI_MC_CLKDIS_PREPCLK_DISABLE = 0x4,
-       HDMI_MC_CLKDIS_TMDSCLK_DISABLE = 0x2,
-       HDMI_MC_CLKDIS_PIXELCLK_DISABLE = 0x1,
-
-/* MC_SWRSTZ field values */
-       HDMI_MC_SWRSTZ_TMDSSWRST_REQ = 0x02,
-
-/* MC_FLOWCTRL field values */
-       HDMI_MC_FLOWCTRL_FEED_THROUGH_OFF_MASK = 0x1,
-       HDMI_MC_FLOWCTRL_FEED_THROUGH_OFF_CSC_IN_PATH = 0x1,
-       HDMI_MC_FLOWCTRL_FEED_THROUGH_OFF_CSC_BYPASS = 0x0,
-
-/* MC_PHYRSTZ field values */
-       HDMI_MC_PHYRSTZ_ASSERT = 0x0,
-       HDMI_MC_PHYRSTZ_DEASSERT = 0x1,
-
-/* MC_HEACPHY_RST field values */
-       HDMI_MC_HEACPHY_RST_ASSERT = 0x1,
-       HDMI_MC_HEACPHY_RST_DEASSERT = 0x0,
-
-/* CSC_CFG field values */
-       HDMI_CSC_CFG_INTMODE_MASK = 0x30,
-       HDMI_CSC_CFG_INTMODE_OFFSET = 4,
-       HDMI_CSC_CFG_INTMODE_DISABLE = 0x00,
-       HDMI_CSC_CFG_INTMODE_CHROMA_INT_FORMULA1 = 0x10,
-       HDMI_CSC_CFG_INTMODE_CHROMA_INT_FORMULA2 = 0x20,
-       HDMI_CSC_CFG_DECMODE_MASK = 0x3,
-       HDMI_CSC_CFG_DECMODE_OFFSET = 0,
-       HDMI_CSC_CFG_DECMODE_DISABLE = 0x0,
-       HDMI_CSC_CFG_DECMODE_CHROMA_INT_FORMULA1 = 0x1,
-       HDMI_CSC_CFG_DECMODE_CHROMA_INT_FORMULA2 = 0x2,
-       HDMI_CSC_CFG_DECMODE_CHROMA_INT_FORMULA3 = 0x3,
-
-/* CSC_SCALE field values */
-       HDMI_CSC_SCALE_CSC_COLORDE_PTH_MASK = 0xF0,
-       HDMI_CSC_SCALE_CSC_COLORDE_PTH_24BPP = 0x00,
-       HDMI_CSC_SCALE_CSC_COLORDE_PTH_30BPP = 0x50,
-       HDMI_CSC_SCALE_CSC_COLORDE_PTH_36BPP = 0x60,
-       HDMI_CSC_SCALE_CSC_COLORDE_PTH_48BPP = 0x70,
-       HDMI_CSC_SCALE_CSCSCALE_MASK = 0x03,
-
-/* A_HDCPCFG0 field values */
-       HDMI_A_HDCPCFG0_ELVENA_MASK = 0x80,
-       HDMI_A_HDCPCFG0_ELVENA_ENABLE = 0x80,
-       HDMI_A_HDCPCFG0_ELVENA_DISABLE = 0x00,
-       HDMI_A_HDCPCFG0_I2CFASTMODE_MASK = 0x40,
-       HDMI_A_HDCPCFG0_I2CFASTMODE_ENABLE = 0x40,
-       HDMI_A_HDCPCFG0_I2CFASTMODE_DISABLE = 0x00,
-       HDMI_A_HDCPCFG0_BYPENCRYPTION_MASK = 0x20,
-       HDMI_A_HDCPCFG0_BYPENCRYPTION_ENABLE = 0x20,
-       HDMI_A_HDCPCFG0_BYPENCRYPTION_DISABLE = 0x00,
-       HDMI_A_HDCPCFG0_SYNCRICHECK_MASK = 0x10,
-       HDMI_A_HDCPCFG0_SYNCRICHECK_ENABLE = 0x10,
-       HDMI_A_HDCPCFG0_SYNCRICHECK_DISABLE = 0x00,
-       HDMI_A_HDCPCFG0_AVMUTE_MASK = 0x8,
-       HDMI_A_HDCPCFG0_AVMUTE_ENABLE = 0x8,
-       HDMI_A_HDCPCFG0_AVMUTE_DISABLE = 0x0,
-       HDMI_A_HDCPCFG0_RXDETECT_MASK = 0x4,
-       HDMI_A_HDCPCFG0_RXDETECT_ENABLE = 0x4,
-       HDMI_A_HDCPCFG0_RXDETECT_DISABLE = 0x0,
-       HDMI_A_HDCPCFG0_EN11FEATURE_MASK = 0x2,
-       HDMI_A_HDCPCFG0_EN11FEATURE_ENABLE = 0x2,
-       HDMI_A_HDCPCFG0_EN11FEATURE_DISABLE = 0x0,
-       HDMI_A_HDCPCFG0_HDMIDVI_MASK = 0x1,
-       HDMI_A_HDCPCFG0_HDMIDVI_HDMI = 0x1,
-       HDMI_A_HDCPCFG0_HDMIDVI_DVI = 0x0,
-
-/* A_HDCPCFG1 field values */
-       HDMI_A_HDCPCFG1_DISSHA1CHECK_MASK = 0x8,
-       HDMI_A_HDCPCFG1_DISSHA1CHECK_DISABLE = 0x8,
-       HDMI_A_HDCPCFG1_DISSHA1CHECK_ENABLE = 0x0,
-       HDMI_A_HDCPCFG1_PH2UPSHFTENC_MASK = 0x4,
-       HDMI_A_HDCPCFG1_PH2UPSHFTENC_ENABLE = 0x4,
-       HDMI_A_HDCPCFG1_PH2UPSHFTENC_DISABLE = 0x0,
-       HDMI_A_HDCPCFG1_ENCRYPTIONDISABLE_MASK = 0x2,
-       HDMI_A_HDCPCFG1_ENCRYPTIONDISABLE_DISABLE = 0x2,
-       HDMI_A_HDCPCFG1_ENCRYPTIONDISABLE_ENABLE = 0x0,
-       HDMI_A_HDCPCFG1_SWRESET_MASK = 0x1,
-       HDMI_A_HDCPCFG1_SWRESET_ASSERT = 0x0,
-
-/* A_VIDPOLCFG field values */
-       HDMI_A_VIDPOLCFG_UNENCRYPTCONF_MASK = 0x60,
-       HDMI_A_VIDPOLCFG_UNENCRYPTCONF_OFFSET = 5,
-       HDMI_A_VIDPOLCFG_DATAENPOL_MASK = 0x10,
-       HDMI_A_VIDPOLCFG_DATAENPOL_ACTIVE_HIGH = 0x10,
-       HDMI_A_VIDPOLCFG_DATAENPOL_ACTIVE_LOW = 0x0,
-       HDMI_A_VIDPOLCFG_VSYNCPOL_MASK = 0x8,
-       HDMI_A_VIDPOLCFG_VSYNCPOL_ACTIVE_HIGH = 0x8,
-       HDMI_A_VIDPOLCFG_VSYNCPOL_ACTIVE_LOW = 0x0,
-       HDMI_A_VIDPOLCFG_HSYNCPOL_MASK = 0x2,
-       HDMI_A_VIDPOLCFG_HSYNCPOL_ACTIVE_HIGH = 0x2,
-       HDMI_A_VIDPOLCFG_HSYNCPOL_ACTIVE_LOW = 0x0,
-};
-#endif /* __IMX_HDMI_H__ */
index c60460043e24dc5f0e19107dd1fe64c25a0da515..1b86aac0b341c7083b15e03163338989a1543592 100644 (file)
@@ -163,7 +163,7 @@ static void imx_ldb_encoder_prepare(struct drm_encoder *encoder)
 {
        struct imx_ldb_channel *imx_ldb_ch = enc_to_imx_ldb_ch(encoder);
        struct imx_ldb *ldb = imx_ldb_ch->ldb;
-       struct drm_display_mode *mode = &encoder->crtc->mode;
+       struct drm_display_mode *mode = &encoder->crtc->hwmode;
        u32 pixel_fmt;
        unsigned long serial_clk;
        unsigned long di_clk = mode->clock * 1000;
@@ -241,8 +241,8 @@ static void imx_ldb_encoder_commit(struct drm_encoder *encoder)
 }
 
 static void imx_ldb_encoder_mode_set(struct drm_encoder *encoder,
-                        struct drm_display_mode *mode,
-                        struct drm_display_mode *adjusted_mode)
+                        struct drm_display_mode *orig_mode,
+                        struct drm_display_mode *mode)
 {
        struct imx_ldb_channel *imx_ldb_ch = enc_to_imx_ldb_ch(encoder);
        struct imx_ldb *ldb = imx_ldb_ch->ldb;
@@ -574,6 +574,8 @@ static void imx_ldb_unbind(struct device *dev, struct device *master,
 
                channel->connector.funcs->destroy(&channel->connector);
                channel->encoder.funcs->destroy(&channel->encoder);
+
+               kfree(channel->edid);
        }
 }
 
index a729f4f7074c1125a04ec3e35bd87f99be95a49b..b63601d0460138f479d50c7d30dd9bdeddbc70ba 100644 (file)
@@ -307,8 +307,8 @@ static void imx_tve_encoder_prepare(struct drm_encoder *encoder)
 }
 
 static void imx_tve_encoder_mode_set(struct drm_encoder *encoder,
-                                    struct drm_display_mode *mode,
-                                    struct drm_display_mode *adjusted_mode)
+                                    struct drm_display_mode *orig_mode,
+                                    struct drm_display_mode *mode)
 {
        struct imx_tve *tve = enc_to_tve(encoder);
        unsigned long rounded_rate;
index ebee59cb96d8a3f1fa8ab831341b3babc63f452a..98551e356e12a4d2c2fdbff21b00a4e22e8b4f3f 100644 (file)
@@ -46,7 +46,6 @@ struct ipu_crtc {
        struct drm_framebuffer  *newfb;
        int                     irq;
        u32                     interface_pix_fmt;
-       unsigned long           di_clkflags;
        int                     di_hsync_pin;
        int                     di_vsync_pin;
 };
@@ -141,47 +140,51 @@ static int ipu_crtc_mode_set(struct drm_crtc *crtc,
                               int x, int y,
                               struct drm_framebuffer *old_fb)
 {
+       struct drm_device *dev = crtc->dev;
+       struct drm_encoder *encoder;
        struct ipu_crtc *ipu_crtc = to_ipu_crtc(crtc);
-       int ret;
        struct ipu_di_signal_cfg sig_cfg = {};
+       unsigned long encoder_types = 0;
        u32 out_pixel_fmt;
+       int ret;
 
        dev_dbg(ipu_crtc->dev, "%s: mode->hdisplay: %d\n", __func__,
                        mode->hdisplay);
        dev_dbg(ipu_crtc->dev, "%s: mode->vdisplay: %d\n", __func__,
                        mode->vdisplay);
 
-       out_pixel_fmt = ipu_crtc->interface_pix_fmt;
+       list_for_each_entry(encoder, &dev->mode_config.encoder_list, head)
+               if (encoder->crtc == crtc)
+                       encoder_types |= BIT(encoder->encoder_type);
 
-       if (mode->flags & DRM_MODE_FLAG_INTERLACE)
-               sig_cfg.interlaced = 1;
-       if (mode->flags & DRM_MODE_FLAG_PHSYNC)
-               sig_cfg.Hsync_pol = 1;
-       if (mode->flags & DRM_MODE_FLAG_PVSYNC)
-               sig_cfg.Vsync_pol = 1;
+       dev_dbg(ipu_crtc->dev, "%s: attached to encoder types 0x%lx\n",
+               __func__, encoder_types);
+
+       /*
+        * If we have DAC, TVDAC or LDB, then we need the IPU DI clock
+        * to be the same as the LDB DI clock.
+        */
+       if (encoder_types & (BIT(DRM_MODE_ENCODER_DAC) |
+                            BIT(DRM_MODE_ENCODER_TVDAC) |
+                            BIT(DRM_MODE_ENCODER_LVDS)))
+               sig_cfg.clkflags = IPU_DI_CLKMODE_SYNC | IPU_DI_CLKMODE_EXT;
+       else
+               sig_cfg.clkflags = 0;
+
+       out_pixel_fmt = ipu_crtc->interface_pix_fmt;
 
        sig_cfg.enable_pol = 1;
        sig_cfg.clk_pol = 0;
-       sig_cfg.width = mode->hdisplay;
-       sig_cfg.height = mode->vdisplay;
        sig_cfg.pixel_fmt = out_pixel_fmt;
-       sig_cfg.h_start_width = mode->htotal - mode->hsync_end;
-       sig_cfg.h_sync_width = mode->hsync_end - mode->hsync_start;
-       sig_cfg.h_end_width = mode->hsync_start - mode->hdisplay;
-
-       sig_cfg.v_start_width = mode->vtotal - mode->vsync_end;
-       sig_cfg.v_sync_width = mode->vsync_end - mode->vsync_start;
-       sig_cfg.v_end_width = mode->vsync_start - mode->vdisplay;
-       sig_cfg.pixelclock = mode->clock * 1000;
-       sig_cfg.clkflags = ipu_crtc->di_clkflags;
-
        sig_cfg.v_to_h_sync = 0;
-
        sig_cfg.hsync_pin = ipu_crtc->di_hsync_pin;
        sig_cfg.vsync_pin = ipu_crtc->di_vsync_pin;
 
-       ret = ipu_dc_init_sync(ipu_crtc->dc, ipu_crtc->di, sig_cfg.interlaced,
-                       out_pixel_fmt, mode->hdisplay);
+       drm_display_mode_to_videomode(mode, &sig_cfg.mode);
+
+       ret = ipu_dc_init_sync(ipu_crtc->dc, ipu_crtc->di,
+                              mode->flags & DRM_MODE_FLAG_INTERLACE,
+                              out_pixel_fmt, mode->hdisplay);
        if (ret) {
                dev_err(ipu_crtc->dev,
                                "initializing display controller failed with %d\n",
@@ -237,6 +240,18 @@ static bool ipu_crtc_mode_fixup(struct drm_crtc *crtc,
                                  const struct drm_display_mode *mode,
                                  struct drm_display_mode *adjusted_mode)
 {
+       struct ipu_crtc *ipu_crtc = to_ipu_crtc(crtc);
+       struct videomode vm;
+       int ret;
+
+       drm_display_mode_to_videomode(adjusted_mode, &vm);
+
+       ret = ipu_di_adjust_videomode(ipu_crtc->di, &vm);
+       if (ret)
+               return false;
+
+       drm_display_mode_from_videomode(&vm, adjusted_mode);
+
        return true;
 }
 
@@ -275,7 +290,7 @@ static void ipu_disable_vblank(struct drm_crtc *crtc)
        ipu_crtc->newfb = NULL;
 }
 
-static int ipu_set_interface_pix_fmt(struct drm_crtc *crtc, u32 encoder_type,
+static int ipu_set_interface_pix_fmt(struct drm_crtc *crtc,
                u32 pixfmt, int hsync_pin, int vsync_pin)
 {
        struct ipu_crtc *ipu_crtc = to_ipu_crtc(crtc);
@@ -284,19 +299,6 @@ static int ipu_set_interface_pix_fmt(struct drm_crtc *crtc, u32 encoder_type,
        ipu_crtc->di_hsync_pin = hsync_pin;
        ipu_crtc->di_vsync_pin = vsync_pin;
 
-       switch (encoder_type) {
-       case DRM_MODE_ENCODER_DAC:
-       case DRM_MODE_ENCODER_TVDAC:
-       case DRM_MODE_ENCODER_LVDS:
-               ipu_crtc->di_clkflags = IPU_DI_CLKMODE_SYNC |
-                       IPU_DI_CLKMODE_EXT;
-               break;
-       case DRM_MODE_ENCODER_TMDS:
-       case DRM_MODE_ENCODER_NONE:
-               ipu_crtc->di_clkflags = 0;
-               break;
-       }
-
        return 0;
 }
 
index 796c3c1c170a1136a22908825e49570e71d2cad5..5e83e007080f7ae757b3f6c567cd791a595bd9d1 100644 (file)
@@ -130,8 +130,8 @@ static void imx_pd_encoder_commit(struct drm_encoder *encoder)
 }
 
 static void imx_pd_encoder_mode_set(struct drm_encoder *encoder,
-                        struct drm_display_mode *mode,
-                        struct drm_display_mode *adjusted_mode)
+                        struct drm_display_mode *orig_mode,
+                        struct drm_display_mode *mode)
 {
 }
 
@@ -257,6 +257,8 @@ static void imx_pd_unbind(struct device *dev, struct device *master,
 
        imxpd->encoder.funcs->destroy(&imxpd->encoder);
        imxpd->connector.funcs->destroy(&imxpd->connector);
+
+       kfree(imxpd->edid);
 }
 
 static const struct component_ops imx_pd_ops = {
@@ -272,6 +274,7 @@ static int imx_pd_probe(struct platform_device *pdev)
 static int imx_pd_remove(struct platform_device *pdev)
 {
        component_del(&pdev->dev, &imx_pd_ops);
+
        return 0;
 }
 
index 4415af3666ab1116e0a07de45ffe1e272f5f4a9a..c36b8304042b70ddf109758b72e59bebe852ab4c 100644 (file)
@@ -303,14 +303,22 @@ int mgag200_fbdev_init(struct mga_device *mdev)
        if (ret)
                return ret;
 
-       drm_fb_helper_single_add_all_connectors(&mfbdev->helper);
+       ret = drm_fb_helper_single_add_all_connectors(&mfbdev->helper);
+       if (ret)
+               goto fini;
 
        /* disable all the possible outputs/crtcs before entering KMS mode */
        drm_helper_disable_unused_functions(mdev->dev);
 
-       drm_fb_helper_initial_config(&mfbdev->helper, bpp_sel);
+       ret = drm_fb_helper_initial_config(&mfbdev->helper, bpp_sel);
+       if (ret)
+               goto fini;
 
        return 0;
+
+fini:
+       drm_fb_helper_fini(&mfbdev->helper);
+       return ret;
 }
 
 void mgag200_fbdev_fini(struct mga_device *mdev)
index 3449213f1e76424f7794754f3009de631b9bd00b..20ae50385e5b316e4f34bb424b8adb9fe2c95bbc 100644 (file)
@@ -323,10 +323,6 @@ static void mdp4_crtc_commit(struct drm_crtc *crtc)
        drm_crtc_vblank_put(crtc);
 }
 
-static void mdp4_crtc_load_lut(struct drm_crtc *crtc)
-{
-}
-
 static int mdp4_crtc_atomic_check(struct drm_crtc *crtc,
                struct drm_crtc_state *state)
 {
@@ -515,7 +511,6 @@ static const struct drm_crtc_helper_funcs mdp4_crtc_helper_funcs = {
        .mode_set_base = drm_helper_crtc_mode_set_base,
        .prepare = mdp4_crtc_prepare,
        .commit = mdp4_crtc_commit,
-       .load_lut = mdp4_crtc_load_lut,
        .atomic_check = mdp4_crtc_atomic_check,
        .atomic_begin = mdp4_crtc_atomic_begin,
        .atomic_flush = mdp4_crtc_atomic_flush,
index f021f960a8a27f7d002fd7be8a01edb722e7323a..6b25f9f731ed58aa339be462f7a8cd7325643e54 100644 (file)
@@ -275,10 +275,6 @@ static void mdp5_crtc_commit(struct drm_crtc *crtc)
        mdp5_disable(get_kms(crtc));
 }
 
-static void mdp5_crtc_load_lut(struct drm_crtc *crtc)
-{
-}
-
 struct plane_state {
        struct drm_plane *plane;
        struct mdp5_plane_state *state;
@@ -402,7 +398,6 @@ static const struct drm_crtc_helper_funcs mdp5_crtc_helper_funcs = {
        .mode_set_base = drm_helper_crtc_mode_set_base,
        .prepare = mdp5_crtc_prepare,
        .commit = mdp5_crtc_commit,
-       .load_lut = mdp5_crtc_load_lut,
        .atomic_check = mdp5_crtc_atomic_check,
        .atomic_begin = mdp5_crtc_atomic_begin,
        .atomic_flush = mdp5_crtc_atomic_flush,
index 26e5fdea6594c7d23854bc566ffe618453c455dd..fc76f630e5b18fe653013c5b7aa95ef114210ffe 100644 (file)
@@ -113,6 +113,7 @@ static void mdp5_plane_reset(struct drm_plane *plane)
        } else {
                mdp5_state->zpos = 1 + drm_plane_index(plane);
        }
+       mdp5_state->base.plane = plane;
 
        plane->state = &mdp5_state->base;
 }
index 191968256c5822ae0a7964db31377e5ba7b0e0ce..2c396540e279efdbfdc0cd9c0038728d04c7e65b 100644 (file)
@@ -127,6 +127,26 @@ static void add_fb(struct msm_commit *c, struct drm_framebuffer *fb)
 }
 
 
+int msm_atomic_check(struct drm_device *dev,
+                    struct drm_atomic_state *state)
+{
+       int ret;
+
+       /*
+        * msm ->atomic_check can update ->mode_changed for pixel format
+        * changes, hence must be run before we check the modeset changes.
+        */
+       ret = drm_atomic_helper_check_planes(dev, state);
+       if (ret)
+               return ret;
+
+       ret = drm_atomic_helper_check_modeset(dev, state);
+       if (ret)
+               return ret;
+
+       return ret;
+}
+
 /**
  * drm_atomic_helper_commit - commit validated state object
  * @dev: DRM device
index 9a61546a0b05276cd313b0877306b02930fa2fa5..f1ebedde6346d6c966bceaf0b351a549d8d87d7f 100644 (file)
@@ -29,7 +29,7 @@ static void msm_fb_output_poll_changed(struct drm_device *dev)
 static const struct drm_mode_config_funcs mode_config_funcs = {
        .fb_create = msm_framebuffer_create,
        .output_poll_changed = msm_fb_output_poll_changed,
-       .atomic_check = drm_atomic_helper_check,
+       .atomic_check = msm_atomic_check,
        .atomic_commit = msm_atomic_commit,
 };
 
index b69ef2d5a26c0a0afa9896ed02a88a087f9cebfe..22e5391a7ce8f321d06d3bd0ec7dd1902d8b2228 100644 (file)
@@ -148,6 +148,8 @@ void __msm_fence_worker(struct work_struct *work);
                (_cb)->func = _func;                         \
        } while (0)
 
+int msm_atomic_check(struct drm_device *dev,
+                    struct drm_atomic_state *state);
 int msm_atomic_commit(struct drm_device *dev,
                struct drm_atomic_state *state, bool async);
 
index 1f3af13ccede96b0aa9ad17a49aca3dbaa358872..115b509a4a005b2fb399f7af76a31ea710ea6f78 100644 (file)
@@ -241,17 +241,23 @@ struct drm_fb_helper *msm_fbdev_init(struct drm_device *dev)
                goto fail;
        }
 
-       drm_fb_helper_single_add_all_connectors(helper);
+       ret = drm_fb_helper_single_add_all_connectors(helper);
+       if (ret)
+               goto fini;
 
        /* disable all the possible outputs/crtcs before entering KMS mode */
        drm_helper_disable_unused_functions(dev);
 
-       drm_fb_helper_initial_config(helper, 32);
+       ret = drm_fb_helper_initial_config(helper, 32);
+       if (ret)
+               goto fini;
 
        priv->fbdev = helper;
 
        return helper;
 
+fini:
+       drm_fb_helper_fini(helper);
 fail:
        kfree(fbdev);
        return NULL;
diff --git a/drivers/gpu/drm/nouveau/Kbuild b/drivers/gpu/drm/nouveau/Kbuild
new file mode 100644 (file)
index 0000000..2b76566
--- /dev/null
@@ -0,0 +1,66 @@
+ccflags-y := -Iinclude/drm
+ccflags-y += -I$(src)/include
+ccflags-y += -I$(src)/include/nvkm
+ccflags-y += -I$(src)/nvkm
+ccflags-y += -I$(src)
+
+# NVKM - HW resource manager
+#- code also used by various userspace tools/tests
+include $(src)/nvif/Kbuild
+nouveau-y := $(nvif-y)
+
+# NVIF - NVKM interface library (NVKM user interface also defined here)
+#- code also used by various userspace tools/tests
+include $(src)/nvkm/Kbuild
+nouveau-y += $(nvkm-y)
+
+# DRM - general
+ifdef CONFIG_X86
+nouveau-$(CONFIG_ACPI) += nouveau_acpi.o
+endif
+nouveau-y += nouveau_agp.o
+nouveau-$(CONFIG_DEBUG_FS) += nouveau_debugfs.o
+nouveau-y += nouveau_drm.o
+nouveau-y += nouveau_hwmon.o
+nouveau-$(CONFIG_COMPAT) += nouveau_ioc32.o
+nouveau-y += nouveau_nvif.o
+nouveau-$(CONFIG_NOUVEAU_PLATFORM_DRIVER) += nouveau_platform.o
+nouveau-y += nouveau_sysfs.o
+nouveau-y += nouveau_usif.o # userspace <-> nvif
+nouveau-y += nouveau_vga.o
+
+# DRM - memory management
+nouveau-y += nouveau_bo.o
+nouveau-y += nouveau_gem.o
+nouveau-y += nouveau_prime.o
+nouveau-y += nouveau_sgdma.o
+nouveau-y += nouveau_ttm.o
+
+# DRM - modesetting
+nouveau-$(CONFIG_DRM_NOUVEAU_BACKLIGHT) += nouveau_backlight.o
+nouveau-y += nouveau_connector.o
+nouveau-y += nouveau_display.o
+nouveau-y += nv50_display.o
+nouveau-y += nouveau_dp.o
+nouveau-y += nouveau_fbcon.o
+nouveau-y += nv04_fbcon.o
+nouveau-y += nv50_fbcon.o
+nouveau-y += nvc0_fbcon.o
+
+# DRM - command submission
+nouveau-y += nouveau_abi16.o
+nouveau-y += nouveau_chan.o
+nouveau-y += nouveau_dma.o
+nouveau-y += nouveau_fence.o
+nouveau-y += nv04_fence.o
+nouveau-y += nv10_fence.o
+nouveau-y += nv17_fence.o
+nouveau-y += nv50_fence.o
+nouveau-y += nv84_fence.o
+nouveau-y += nvc0_fence.o
+
+# DRM - prehistoric modesetting (NV04-G7x)
+nouveau-y += nouveau_bios.o
+include $(src)/dispnv04/Kbuild
+
+obj-$(CONFIG_DRM_NOUVEAU) += nouveau.o
index 40afc69a3778ab7012eded8d2e9a856c8f1ee3f6..5ab13e7939db7d0085aecd41ac18be7a8ee5782f 100644 (file)
@@ -26,7 +26,7 @@ config DRM_NOUVEAU
          Choose this option for open-source NVIDIA support.
 
 config NOUVEAU_PLATFORM_DRIVER
-       tristate "Nouveau (NVIDIA) SoC GPUs"
+       bool "Nouveau (NVIDIA) SoC GPUs"
        depends on DRM_NOUVEAU && ARCH_TEGRA
        default y
        help
diff --git a/drivers/gpu/drm/nouveau/Makefile b/drivers/gpu/drm/nouveau/Makefile
deleted file mode 100644 (file)
index 6461e35..0000000
+++ /dev/null
@@ -1,400 +0,0 @@
-#
-# Makefile for the drm device driver.  This driver provides support for the
-# Direct Rendering Infrastructure (DRI) in XFree86 4.1.0 and higher.
-
-ccflags-y := -Iinclude/drm
-ccflags-y += -I$(src)/core/include
-ccflags-y += -I$(src)/core
-ccflags-y += -I$(src)
-
-nouveau-y := core/core/client.o
-nouveau-y += core/core/engctx.o
-nouveau-y += core/core/engine.o
-nouveau-y += core/core/enum.o
-nouveau-y += core/core/event.o
-nouveau-y += core/core/gpuobj.o
-nouveau-y += core/core/handle.o
-nouveau-y += core/core/ioctl.o
-nouveau-y += core/core/mm.o
-nouveau-y += core/core/namedb.o
-nouveau-y += core/core/notify.o
-nouveau-y += core/core/object.o
-nouveau-y += core/core/option.o
-nouveau-y += core/core/parent.o
-nouveau-y += core/core/printk.o
-nouveau-y += core/core/ramht.o
-nouveau-y += core/core/subdev.o
-
-nouveau-y += core/subdev/bar/base.o
-nouveau-y += core/subdev/bar/nv50.o
-nouveau-y += core/subdev/bar/nvc0.o
-nouveau-y += core/subdev/bar/gk20a.o
-nouveau-y += core/subdev/bios/base.o
-nouveau-y += core/subdev/bios/bit.o
-nouveau-y += core/subdev/bios/boost.o
-nouveau-y += core/subdev/bios/conn.o
-nouveau-y += core/subdev/bios/cstep.o
-nouveau-y += core/subdev/bios/dcb.o
-nouveau-y += core/subdev/bios/disp.o
-nouveau-y += core/subdev/bios/dp.o
-nouveau-y += core/subdev/bios/extdev.o
-nouveau-y += core/subdev/bios/fan.o
-nouveau-y += core/subdev/bios/gpio.o
-nouveau-y += core/subdev/bios/i2c.o
-nouveau-y += core/subdev/bios/image.o
-nouveau-y += core/subdev/bios/init.o
-nouveau-y += core/subdev/bios/mxm.o
-nouveau-y += core/subdev/bios/npde.o
-nouveau-y += core/subdev/bios/pcir.o
-nouveau-y += core/subdev/bios/perf.o
-nouveau-y += core/subdev/bios/pll.o
-nouveau-y += core/subdev/bios/pmu.o
-nouveau-y += core/subdev/bios/ramcfg.o
-nouveau-y += core/subdev/bios/rammap.o
-nouveau-y += core/subdev/bios/shadow.o
-nouveau-y += core/subdev/bios/shadowacpi.o
-nouveau-y += core/subdev/bios/shadowof.o
-nouveau-y += core/subdev/bios/shadowpci.o
-nouveau-y += core/subdev/bios/shadowramin.o
-nouveau-y += core/subdev/bios/shadowrom.o
-nouveau-y += core/subdev/bios/timing.o
-nouveau-y += core/subdev/bios/therm.o
-nouveau-y += core/subdev/bios/vmap.o
-nouveau-y += core/subdev/bios/volt.o
-nouveau-y += core/subdev/bios/xpio.o
-nouveau-y += core/subdev/bios/M0203.o
-nouveau-y += core/subdev/bios/M0205.o
-nouveau-y += core/subdev/bios/M0209.o
-nouveau-y += core/subdev/bios/P0260.o
-nouveau-y += core/subdev/bus/hwsq.o
-nouveau-y += core/subdev/bus/nv04.o
-nouveau-y += core/subdev/bus/nv31.o
-nouveau-y += core/subdev/bus/nv50.o
-nouveau-y += core/subdev/bus/nv94.o
-nouveau-y += core/subdev/bus/nvc0.o
-nouveau-y += core/subdev/clock/base.o
-nouveau-y += core/subdev/clock/nv04.o
-nouveau-y += core/subdev/clock/nv40.o
-nouveau-y += core/subdev/clock/nv50.o
-nouveau-y += core/subdev/clock/nv84.o
-nouveau-y += core/subdev/clock/nva3.o
-nouveau-y += core/subdev/clock/nvaa.o
-nouveau-y += core/subdev/clock/nvc0.o
-nouveau-y += core/subdev/clock/nve0.o
-nouveau-y += core/subdev/clock/gk20a.o
-nouveau-y += core/subdev/clock/pllnv04.o
-nouveau-y += core/subdev/clock/pllnva3.o
-nouveau-y += core/subdev/devinit/base.o
-nouveau-y += core/subdev/devinit/nv04.o
-nouveau-y += core/subdev/devinit/nv05.o
-nouveau-y += core/subdev/devinit/nv10.o
-nouveau-y += core/subdev/devinit/nv1a.o
-nouveau-y += core/subdev/devinit/nv20.o
-nouveau-y += core/subdev/devinit/nv50.o
-nouveau-y += core/subdev/devinit/nv84.o
-nouveau-y += core/subdev/devinit/nv98.o
-nouveau-y += core/subdev/devinit/nva3.o
-nouveau-y += core/subdev/devinit/nvaf.o
-nouveau-y += core/subdev/devinit/nvc0.o
-nouveau-y += core/subdev/devinit/gm107.o
-nouveau-y += core/subdev/devinit/gm204.o
-nouveau-y += core/subdev/fb/base.o
-nouveau-y += core/subdev/fb/nv04.o
-nouveau-y += core/subdev/fb/nv10.o
-nouveau-y += core/subdev/fb/nv1a.o
-nouveau-y += core/subdev/fb/nv20.o
-nouveau-y += core/subdev/fb/nv25.o
-nouveau-y += core/subdev/fb/nv30.o
-nouveau-y += core/subdev/fb/nv35.o
-nouveau-y += core/subdev/fb/nv36.o
-nouveau-y += core/subdev/fb/nv40.o
-nouveau-y += core/subdev/fb/nv41.o
-nouveau-y += core/subdev/fb/nv44.o
-nouveau-y += core/subdev/fb/nv46.o
-nouveau-y += core/subdev/fb/nv47.o
-nouveau-y += core/subdev/fb/nv49.o
-nouveau-y += core/subdev/fb/nv4e.o
-nouveau-y += core/subdev/fb/nv50.o
-nouveau-y += core/subdev/fb/nv84.o
-nouveau-y += core/subdev/fb/nva3.o
-nouveau-y += core/subdev/fb/nvaa.o
-nouveau-y += core/subdev/fb/nvaf.o
-nouveau-y += core/subdev/fb/nvc0.o
-nouveau-y += core/subdev/fb/nve0.o
-nouveau-y += core/subdev/fb/gk20a.o
-nouveau-y += core/subdev/fb/gm107.o
-nouveau-y += core/subdev/fb/ramnv04.o
-nouveau-y += core/subdev/fb/ramnv10.o
-nouveau-y += core/subdev/fb/ramnv1a.o
-nouveau-y += core/subdev/fb/ramnv20.o
-nouveau-y += core/subdev/fb/ramnv40.o
-nouveau-y += core/subdev/fb/ramnv41.o
-nouveau-y += core/subdev/fb/ramnv44.o
-nouveau-y += core/subdev/fb/ramnv49.o
-nouveau-y += core/subdev/fb/ramnv4e.o
-nouveau-y += core/subdev/fb/ramnv50.o
-nouveau-y += core/subdev/fb/ramnva3.o
-nouveau-y += core/subdev/fb/ramnvaa.o
-nouveau-y += core/subdev/fb/ramnvc0.o
-nouveau-y += core/subdev/fb/ramnve0.o
-nouveau-y += core/subdev/fb/ramgk20a.o
-nouveau-y += core/subdev/fb/ramgm107.o
-nouveau-y += core/subdev/fb/sddr2.o
-nouveau-y += core/subdev/fb/sddr3.o
-nouveau-y += core/subdev/fb/gddr3.o
-nouveau-y += core/subdev/fb/gddr5.o
-nouveau-y += core/subdev/fuse/base.o
-nouveau-y += core/subdev/fuse/g80.o
-nouveau-y += core/subdev/fuse/gf100.o
-nouveau-y += core/subdev/fuse/gm107.o
-nouveau-y += core/subdev/gpio/base.o
-nouveau-y += core/subdev/gpio/nv10.o
-nouveau-y += core/subdev/gpio/nv50.o
-nouveau-y += core/subdev/gpio/nv94.o
-nouveau-y += core/subdev/gpio/nvd0.o
-nouveau-y += core/subdev/gpio/nve0.o
-nouveau-y += core/subdev/i2c/base.o
-nouveau-y += core/subdev/i2c/anx9805.o
-nouveau-y += core/subdev/i2c/aux.o
-nouveau-y += core/subdev/i2c/bit.o
-nouveau-y += core/subdev/i2c/pad.o
-nouveau-y += core/subdev/i2c/padnv04.o
-nouveau-y += core/subdev/i2c/padnv94.o
-nouveau-y += core/subdev/i2c/padgm204.o
-nouveau-y += core/subdev/i2c/nv04.o
-nouveau-y += core/subdev/i2c/nv4e.o
-nouveau-y += core/subdev/i2c/nv50.o
-nouveau-y += core/subdev/i2c/nv94.o
-nouveau-y += core/subdev/i2c/nvd0.o
-nouveau-y += core/subdev/i2c/gf117.o
-nouveau-y += core/subdev/i2c/nve0.o
-nouveau-y += core/subdev/i2c/gm204.o
-nouveau-y += core/subdev/ibus/nvc0.o
-nouveau-y += core/subdev/ibus/nve0.o
-nouveau-y += core/subdev/ibus/gk20a.o
-nouveau-y += core/subdev/instmem/base.o
-nouveau-y += core/subdev/instmem/nv04.o
-nouveau-y += core/subdev/instmem/nv40.o
-nouveau-y += core/subdev/instmem/nv50.o
-nouveau-y += core/subdev/ltc/base.o
-nouveau-y += core/subdev/ltc/gf100.o
-nouveau-y += core/subdev/ltc/gk104.o
-nouveau-y += core/subdev/ltc/gm107.o
-nouveau-y += core/subdev/mc/base.o
-nouveau-y += core/subdev/mc/nv04.o
-nouveau-y += core/subdev/mc/nv40.o
-nouveau-y += core/subdev/mc/nv44.o
-nouveau-y += core/subdev/mc/nv4c.o
-nouveau-y += core/subdev/mc/nv50.o
-nouveau-y += core/subdev/mc/nv94.o
-nouveau-y += core/subdev/mc/nv98.o
-nouveau-y += core/subdev/mc/nvc0.o
-nouveau-y += core/subdev/mc/nvc3.o
-nouveau-y += core/subdev/mc/gk20a.o
-nouveau-y += core/subdev/mxm/base.o
-nouveau-y += core/subdev/mxm/mxms.o
-nouveau-y += core/subdev/mxm/nv50.o
-nouveau-y += core/subdev/pwr/base.o
-nouveau-y += core/subdev/pwr/memx.o
-nouveau-y += core/subdev/pwr/nva3.o
-nouveau-y += core/subdev/pwr/nvc0.o
-nouveau-y += core/subdev/pwr/nvd0.o
-nouveau-y += core/subdev/pwr/gk104.o
-nouveau-y += core/subdev/pwr/nv108.o
-nouveau-y += core/subdev/therm/base.o
-nouveau-y += core/subdev/therm/fan.o
-nouveau-y += core/subdev/therm/fannil.o
-nouveau-y += core/subdev/therm/fanpwm.o
-nouveau-y += core/subdev/therm/fantog.o
-nouveau-y += core/subdev/therm/ic.o
-nouveau-y += core/subdev/therm/temp.o
-nouveau-y += core/subdev/therm/nv40.o
-nouveau-y += core/subdev/therm/nv50.o
-nouveau-y += core/subdev/therm/nv84.o
-nouveau-y += core/subdev/therm/nva3.o
-nouveau-y += core/subdev/therm/nvd0.o
-nouveau-y += core/subdev/therm/gm107.o
-nouveau-y += core/subdev/timer/base.o
-nouveau-y += core/subdev/timer/nv04.o
-nouveau-y += core/subdev/timer/gk20a.o
-nouveau-y += core/subdev/vm/base.o
-nouveau-y += core/subdev/vm/nv04.o
-nouveau-y += core/subdev/vm/nv41.o
-nouveau-y += core/subdev/vm/nv44.o
-nouveau-y += core/subdev/vm/nv50.o
-nouveau-y += core/subdev/vm/nvc0.o
-nouveau-y += core/subdev/volt/base.o
-nouveau-y += core/subdev/volt/gpio.o
-nouveau-y += core/subdev/volt/nv40.o
-nouveau-y += core/subdev/volt/gk20a.o
-
-nouveau-y += core/engine/falcon.o
-nouveau-y += core/engine/xtensa.o
-nouveau-y += core/engine/dmaobj/base.o
-nouveau-y += core/engine/dmaobj/nv04.o
-nouveau-y += core/engine/dmaobj/nv50.o
-nouveau-y += core/engine/dmaobj/nvc0.o
-nouveau-y += core/engine/dmaobj/nvd0.o
-nouveau-y += core/engine/bsp/nv84.o
-nouveau-y += core/engine/bsp/nv98.o
-nouveau-y += core/engine/bsp/nvc0.o
-nouveau-y += core/engine/bsp/nve0.o
-nouveau-y += core/engine/copy/nva3.o
-nouveau-y += core/engine/copy/nvc0.o
-nouveau-y += core/engine/copy/nve0.o
-nouveau-y += core/engine/crypt/nv84.o
-nouveau-y += core/engine/crypt/nv98.o
-nouveau-y += core/engine/device/acpi.o
-nouveau-y += core/engine/device/base.o
-nouveau-y += core/engine/device/ctrl.o
-nouveau-y += core/engine/device/nv04.o
-nouveau-y += core/engine/device/nv10.o
-nouveau-y += core/engine/device/nv20.o
-nouveau-y += core/engine/device/nv30.o
-nouveau-y += core/engine/device/nv40.o
-nouveau-y += core/engine/device/nv50.o
-nouveau-y += core/engine/device/nvc0.o
-nouveau-y += core/engine/device/nve0.o
-nouveau-y += core/engine/device/gm100.o
-nouveau-y += core/engine/disp/base.o
-nouveau-y += core/engine/disp/conn.o
-nouveau-y += core/engine/disp/outp.o
-nouveau-y += core/engine/disp/outpdp.o
-nouveau-y += core/engine/disp/nv04.o
-nouveau-y += core/engine/disp/nv50.o
-nouveau-y += core/engine/disp/nv84.o
-nouveau-y += core/engine/disp/nv94.o
-nouveau-y += core/engine/disp/nva0.o
-nouveau-y += core/engine/disp/nva3.o
-nouveau-y += core/engine/disp/nvd0.o
-nouveau-y += core/engine/disp/nve0.o
-nouveau-y += core/engine/disp/nvf0.o
-nouveau-y += core/engine/disp/gm107.o
-nouveau-y += core/engine/disp/gm204.o
-nouveau-y += core/engine/disp/dacnv50.o
-nouveau-y += core/engine/disp/dport.o
-nouveau-y += core/engine/disp/hdanva3.o
-nouveau-y += core/engine/disp/hdanvd0.o
-nouveau-y += core/engine/disp/hdminv84.o
-nouveau-y += core/engine/disp/hdminva3.o
-nouveau-y += core/engine/disp/hdminvd0.o
-nouveau-y += core/engine/disp/hdminve0.o
-nouveau-y += core/engine/disp/piornv50.o
-nouveau-y += core/engine/disp/sornv50.o
-nouveau-y += core/engine/disp/sornv94.o
-nouveau-y += core/engine/disp/sornvd0.o
-nouveau-y += core/engine/disp/sorgm204.o
-nouveau-y += core/engine/disp/vga.o
-nouveau-y += core/engine/fifo/base.o
-nouveau-y += core/engine/fifo/nv04.o
-nouveau-y += core/engine/fifo/nv10.o
-nouveau-y += core/engine/fifo/nv17.o
-nouveau-y += core/engine/fifo/nv40.o
-nouveau-y += core/engine/fifo/nv50.o
-nouveau-y += core/engine/fifo/nv84.o
-nouveau-y += core/engine/fifo/nvc0.o
-nouveau-y += core/engine/fifo/nve0.o
-nouveau-y += core/engine/fifo/gk20a.o
-nouveau-y += core/engine/fifo/nv108.o
-nouveau-y += core/engine/graph/ctxnv40.o
-nouveau-y += core/engine/graph/ctxnv50.o
-nouveau-y += core/engine/graph/ctxnvc0.o
-nouveau-y += core/engine/graph/ctxnvc1.o
-nouveau-y += core/engine/graph/ctxnvc4.o
-nouveau-y += core/engine/graph/ctxnvc8.o
-nouveau-y += core/engine/graph/ctxnvd7.o
-nouveau-y += core/engine/graph/ctxnvd9.o
-nouveau-y += core/engine/graph/ctxnve4.o
-nouveau-y += core/engine/graph/ctxgk20a.o
-nouveau-y += core/engine/graph/ctxnvf0.o
-nouveau-y += core/engine/graph/ctxgk110b.o
-nouveau-y += core/engine/graph/ctxnv108.o
-nouveau-y += core/engine/graph/ctxgm107.o
-nouveau-y += core/engine/graph/nv04.o
-nouveau-y += core/engine/graph/nv10.o
-nouveau-y += core/engine/graph/nv20.o
-nouveau-y += core/engine/graph/nv25.o
-nouveau-y += core/engine/graph/nv2a.o
-nouveau-y += core/engine/graph/nv30.o
-nouveau-y += core/engine/graph/nv34.o
-nouveau-y += core/engine/graph/nv35.o
-nouveau-y += core/engine/graph/nv40.o
-nouveau-y += core/engine/graph/nv50.o
-nouveau-y += core/engine/graph/nvc0.o
-nouveau-y += core/engine/graph/nvc1.o
-nouveau-y += core/engine/graph/nvc4.o
-nouveau-y += core/engine/graph/nvc8.o
-nouveau-y += core/engine/graph/nvd7.o
-nouveau-y += core/engine/graph/nvd9.o
-nouveau-y += core/engine/graph/nve4.o
-nouveau-y += core/engine/graph/gk20a.o
-nouveau-y += core/engine/graph/nvf0.o
-nouveau-y += core/engine/graph/gk110b.o
-nouveau-y += core/engine/graph/nv108.o
-nouveau-y += core/engine/graph/gm107.o
-nouveau-y += core/engine/mpeg/nv31.o
-nouveau-y += core/engine/mpeg/nv40.o
-nouveau-y += core/engine/mpeg/nv44.o
-nouveau-y += core/engine/mpeg/nv50.o
-nouveau-y += core/engine/mpeg/nv84.o
-nouveau-y += core/engine/perfmon/base.o
-nouveau-y += core/engine/perfmon/daemon.o
-nouveau-y += core/engine/perfmon/nv40.o
-nouveau-y += core/engine/perfmon/nv50.o
-nouveau-y += core/engine/perfmon/nv84.o
-nouveau-y += core/engine/perfmon/nva3.o
-nouveau-y += core/engine/perfmon/nvc0.o
-nouveau-y += core/engine/perfmon/nve0.o
-nouveau-y += core/engine/perfmon/nvf0.o
-nouveau-y += core/engine/ppp/nv98.o
-nouveau-y += core/engine/ppp/nvc0.o
-nouveau-y += core/engine/software/nv04.o
-nouveau-y += core/engine/software/nv10.o
-nouveau-y += core/engine/software/nv50.o
-nouveau-y += core/engine/software/nvc0.o
-nouveau-y += core/engine/vp/nv84.o
-nouveau-y += core/engine/vp/nv98.o
-nouveau-y += core/engine/vp/nvc0.o
-nouveau-y += core/engine/vp/nve0.o
-
-# nvif
-nouveau-y += nvif/object.o
-nouveau-y += nvif/client.o
-nouveau-y += nvif/device.o
-nouveau-y += nvif/notify.o
-
-# drm/core
-nouveau-y += nouveau_drm.o nouveau_chan.o nouveau_dma.o nouveau_fence.o
-nouveau-y += nouveau_vga.o nouveau_agp.o
-nouveau-y += nouveau_ttm.o nouveau_sgdma.o nouveau_bo.o nouveau_gem.o
-nouveau-y += nouveau_prime.o nouveau_abi16.o
-nouveau-y += nouveau_nvif.o nouveau_usif.o
-nouveau-y += nv04_fence.o nv10_fence.o nv17_fence.o
-nouveau-y += nv50_fence.o nv84_fence.o nvc0_fence.o
-
-# drm/kms
-nouveau-y += nouveau_bios.o nouveau_fbcon.o nouveau_display.o
-nouveau-y += nouveau_connector.o nouveau_dp.o
-nouveau-y += nv04_fbcon.o nv50_fbcon.o nvc0_fbcon.o
-
-# drm/kms/nv04:nv50
-include $(src)/dispnv04/Makefile
-
-# drm/kms/nv50-
-nouveau-y += nv50_display.o
-
-# drm/pm
-nouveau-y += nouveau_hwmon.o nouveau_sysfs.o
-
-# other random bits
-nouveau-$(CONFIG_COMPAT) += nouveau_ioc32.o
-ifdef CONFIG_X86
-nouveau-$(CONFIG_ACPI) += nouveau_acpi.o
-endif
-nouveau-$(CONFIG_DRM_NOUVEAU_BACKLIGHT) += nouveau_backlight.o
-nouveau-$(CONFIG_DEBUG_FS) += nouveau_debugfs.o
-
-obj-$(CONFIG_DRM_NOUVEAU)+= nouveau.o
-
-# platform driver
-obj-$(CONFIG_NOUVEAU_PLATFORM_DRIVER) += nouveau_platform.o
diff --git a/drivers/gpu/drm/nouveau/core/core/client.c b/drivers/gpu/drm/nouveau/core/core/client.c
deleted file mode 100644 (file)
index e962433..0000000
+++ /dev/null
@@ -1,271 +0,0 @@
-/*
- * Copyright 2012 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 <core/object.h>
-#include <core/client.h>
-#include <core/handle.h>
-#include <core/option.h>
-#include <nvif/unpack.h>
-#include <nvif/class.h>
-
-#include <nvif/unpack.h>
-#include <nvif/event.h>
-
-#include <engine/device.h>
-
-struct nvkm_client_notify {
-       struct nouveau_client *client;
-       struct nvkm_notify n;
-       u8 version;
-       u8 size;
-       union {
-               struct nvif_notify_rep_v0 v0;
-       } rep;
-};
-
-static int
-nvkm_client_notify(struct nvkm_notify *n)
-{
-       struct nvkm_client_notify *notify = container_of(n, typeof(*notify), n);
-       struct nouveau_client *client = notify->client;
-       return client->ntfy(&notify->rep, notify->size, n->data, n->size);
-}
-
-int
-nvkm_client_notify_put(struct nouveau_client *client, int index)
-{
-       if (index < ARRAY_SIZE(client->notify)) {
-               if (client->notify[index]) {
-                       nvkm_notify_put(&client->notify[index]->n);
-                       return 0;
-               }
-       }
-       return -ENOENT;
-}
-
-int
-nvkm_client_notify_get(struct nouveau_client *client, int index)
-{
-       if (index < ARRAY_SIZE(client->notify)) {
-               if (client->notify[index]) {
-                       nvkm_notify_get(&client->notify[index]->n);
-                       return 0;
-               }
-       }
-       return -ENOENT;
-}
-
-int
-nvkm_client_notify_del(struct nouveau_client *client, int index)
-{
-       if (index < ARRAY_SIZE(client->notify)) {
-               if (client->notify[index]) {
-                       nvkm_notify_fini(&client->notify[index]->n);
-                       kfree(client->notify[index]);
-                       client->notify[index] = NULL;
-                       return 0;
-               }
-       }
-       return -ENOENT;
-}
-
-int
-nvkm_client_notify_new(struct nouveau_object *object,
-                      struct nvkm_event *event, void *data, u32 size)
-{
-       struct nouveau_client *client = nouveau_client(object);
-       struct nvkm_client_notify *notify;
-       union {
-               struct nvif_notify_req_v0 v0;
-       } *req = data;
-       u8  index, reply;
-       int ret;
-
-       for (index = 0; index < ARRAY_SIZE(client->notify); index++) {
-               if (!client->notify[index])
-                       break;
-       }
-
-       if (index == ARRAY_SIZE(client->notify))
-               return -ENOSPC;
-
-       notify = kzalloc(sizeof(*notify), GFP_KERNEL);
-       if (!notify)
-               return -ENOMEM;
-
-       nv_ioctl(client, "notify new size %d\n", size);
-       if (nvif_unpack(req->v0, 0, 0, true)) {
-               nv_ioctl(client, "notify new vers %d reply %d route %02x "
-                                "token %llx\n", req->v0.version,
-                        req->v0.reply, req->v0.route, req->v0.token);
-               notify->version = req->v0.version;
-               notify->size = sizeof(notify->rep.v0);
-               notify->rep.v0.version = req->v0.version;
-               notify->rep.v0.route = req->v0.route;
-               notify->rep.v0.token = req->v0.token;
-               reply = req->v0.reply;
-       }
-
-       if (ret == 0) {
-               ret = nvkm_notify_init(object, event, nvkm_client_notify,
-                                      false, data, size, reply, &notify->n);
-               if (ret == 0) {
-                       client->notify[index] = notify;
-                       notify->client = client;
-                       return index;
-               }
-       }
-
-       kfree(notify);
-       return ret;
-}
-
-static int
-nouveau_client_devlist(struct nouveau_object *object, void *data, u32 size)
-{
-       union {
-               struct nv_client_devlist_v0 v0;
-       } *args = data;
-       int ret;
-
-       nv_ioctl(object, "client devlist size %d\n", size);
-       if (nvif_unpack(args->v0, 0, 0, true)) {
-               nv_ioctl(object, "client devlist vers %d count %d\n",
-                        args->v0.version, args->v0.count);
-               if (size == sizeof(args->v0.device[0]) * args->v0.count) {
-                       ret = nouveau_device_list(args->v0.device,
-                                                 args->v0.count);
-                       if (ret >= 0) {
-                               args->v0.count = ret;
-                               ret = 0;
-                       }
-               } else {
-                       ret = -EINVAL;
-               }
-       }
-
-       return ret;
-}
-
-static int
-nouveau_client_mthd(struct nouveau_object *object, u32 mthd,
-                   void *data, u32 size)
-{
-       switch (mthd) {
-       case NV_CLIENT_DEVLIST:
-               return nouveau_client_devlist(object, data, size);
-       default:
-               break;
-       }
-       return -EINVAL;
-}
-
-static void
-nouveau_client_dtor(struct nouveau_object *object)
-{
-       struct nouveau_client *client = (void *)object;
-       int i;
-       for (i = 0; i < ARRAY_SIZE(client->notify); i++)
-               nvkm_client_notify_del(client, i);
-       nouveau_object_ref(NULL, &client->device);
-       nouveau_handle_destroy(client->root);
-       nouveau_namedb_destroy(&client->base);
-}
-
-static struct nouveau_oclass
-nouveau_client_oclass = {
-       .ofuncs = &(struct nouveau_ofuncs) {
-               .dtor = nouveau_client_dtor,
-               .mthd = nouveau_client_mthd,
-       },
-};
-
-int
-nouveau_client_create_(const char *name, u64 devname, const char *cfg,
-                      const char *dbg, int length, void **pobject)
-{
-       struct nouveau_object *device;
-       struct nouveau_client *client;
-       int ret;
-
-       device = (void *)nouveau_device_find(devname);
-       if (!device)
-               return -ENODEV;
-
-       ret = nouveau_namedb_create_(NULL, NULL, &nouveau_client_oclass,
-                                    NV_CLIENT_CLASS, NULL,
-                                    (1ULL << NVDEV_ENGINE_DEVICE),
-                                    length, pobject);
-       client = *pobject;
-       if (ret)
-               return ret;
-
-       ret = nouveau_handle_create(nv_object(client), ~0, ~0,
-                                   nv_object(client), &client->root);
-       if (ret)
-               return ret;
-
-       /* prevent init/fini being called, os in in charge of this */
-       atomic_set(&nv_object(client)->usecount, 2);
-
-       nouveau_object_ref(device, &client->device);
-       snprintf(client->name, sizeof(client->name), "%s", name);
-       client->debug = nouveau_dbgopt(dbg, "CLIENT");
-       return 0;
-}
-
-int
-nouveau_client_init(struct nouveau_client *client)
-{
-       int ret;
-       nv_debug(client, "init running\n");
-       ret = nouveau_handle_init(client->root);
-       nv_debug(client, "init completed with %d\n", ret);
-       return ret;
-}
-
-int
-nouveau_client_fini(struct nouveau_client *client, bool suspend)
-{
-       const char *name[2] = { "fini", "suspend" };
-       int ret, i;
-       nv_debug(client, "%s running\n", name[suspend]);
-       nv_debug(client, "%s notify\n", name[suspend]);
-       for (i = 0; i < ARRAY_SIZE(client->notify); i++)
-               nvkm_client_notify_put(client, i);
-       nv_debug(client, "%s object\n", name[suspend]);
-       ret = nouveau_handle_fini(client->root, suspend);
-       nv_debug(client, "%s completed with %d\n", name[suspend], ret);
-       return ret;
-}
-
-const char *
-nouveau_client_name(void *obj)
-{
-       const char *client_name = "unknown";
-       struct nouveau_client *client = nouveau_client(obj);
-       if (client)
-               client_name = client->name;
-       return client_name;
-}
diff --git a/drivers/gpu/drm/nouveau/core/core/engctx.c b/drivers/gpu/drm/nouveau/core/core/engctx.c
deleted file mode 100644 (file)
index 84c71fa..0000000
+++ /dev/null
@@ -1,251 +0,0 @@
-/*
- * Copyright 2012 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 <core/object.h>
-#include <core/namedb.h>
-#include <core/handle.h>
-#include <core/client.h>
-#include <core/engctx.h>
-
-#include <subdev/vm.h>
-
-static inline int
-nouveau_engctx_exists(struct nouveau_object *parent,
-                     struct nouveau_engine *engine, void **pobject)
-{
-       struct nouveau_engctx *engctx;
-       struct nouveau_object *parctx;
-
-       list_for_each_entry(engctx, &engine->contexts, head) {
-               parctx = nv_pclass(nv_object(engctx), NV_PARENT_CLASS);
-               if (parctx == parent) {
-                       atomic_inc(&nv_object(engctx)->refcount);
-                       *pobject = engctx;
-                       return 1;
-               }
-       }
-
-       return 0;
-}
-
-int
-nouveau_engctx_create_(struct nouveau_object *parent,
-                      struct nouveau_object *engobj,
-                      struct nouveau_oclass *oclass,
-                      struct nouveau_object *pargpu,
-                      u32 size, u32 align, u32 flags,
-                      int length, void **pobject)
-{
-       struct nouveau_client *client = nouveau_client(parent);
-       struct nouveau_engine *engine = nv_engine(engobj);
-       struct nouveau_object *engctx;
-       unsigned long save;
-       int ret;
-
-       /* check if this engine already has a context for the parent object,
-        * and reference it instead of creating a new one
-        */
-       spin_lock_irqsave(&engine->lock, save);
-       ret = nouveau_engctx_exists(parent, engine, pobject);
-       spin_unlock_irqrestore(&engine->lock, save);
-       if (ret)
-               return ret;
-
-       /* create the new context, supports creating both raw objects and
-        * objects backed by instance memory
-        */
-       if (size) {
-               ret = nouveau_gpuobj_create_(parent, engobj, oclass,
-                                            NV_ENGCTX_CLASS,
-                                            pargpu, size, align, flags,
-                                            length, pobject);
-       } else {
-               ret = nouveau_object_create_(parent, engobj, oclass,
-                                            NV_ENGCTX_CLASS, length, pobject);
-       }
-
-       engctx = *pobject;
-       if (ret)
-               return ret;
-
-       /* must take the lock again and re-check a context doesn't already
-        * exist (in case of a race) - the lock had to be dropped before as
-        * it's not possible to allocate the object with it held.
-        */
-       spin_lock_irqsave(&engine->lock, save);
-       ret = nouveau_engctx_exists(parent, engine, pobject);
-       if (ret) {
-               spin_unlock_irqrestore(&engine->lock, save);
-               nouveau_object_ref(NULL, &engctx);
-               return ret;
-       }
-
-       if (client->vm)
-               atomic_inc(&client->vm->engref[nv_engidx(engobj)]);
-       list_add(&nv_engctx(engctx)->head, &engine->contexts);
-       nv_engctx(engctx)->addr = ~0ULL;
-       spin_unlock_irqrestore(&engine->lock, save);
-       return 0;
-}
-
-void
-nouveau_engctx_destroy(struct nouveau_engctx *engctx)
-{
-       struct nouveau_object *engobj = nv_object(engctx)->engine;
-       struct nouveau_engine *engine = nv_engine(engobj);
-       struct nouveau_client *client = nouveau_client(engctx);
-       unsigned long save;
-
-       nouveau_gpuobj_unmap(&engctx->vma);
-       spin_lock_irqsave(&engine->lock, save);
-       list_del(&engctx->head);
-       spin_unlock_irqrestore(&engine->lock, save);
-
-       if (client->vm)
-               atomic_dec(&client->vm->engref[nv_engidx(engobj)]);
-
-       if (engctx->base.size)
-               nouveau_gpuobj_destroy(&engctx->base);
-       else
-               nouveau_object_destroy(&engctx->base.base);
-}
-
-int
-nouveau_engctx_init(struct nouveau_engctx *engctx)
-{
-       struct nouveau_object *object = nv_object(engctx);
-       struct nouveau_subdev *subdev = nv_subdev(object->engine);
-       struct nouveau_object *parent;
-       struct nouveau_subdev *pardev;
-       int ret;
-
-       ret = nouveau_gpuobj_init(&engctx->base);
-       if (ret)
-               return ret;
-
-       parent = nv_pclass(object->parent, NV_PARENT_CLASS);
-       pardev = nv_subdev(parent->engine);
-       if (nv_parent(parent)->context_attach) {
-               mutex_lock(&pardev->mutex);
-               ret = nv_parent(parent)->context_attach(parent, object);
-               mutex_unlock(&pardev->mutex);
-       }
-
-       if (ret) {
-               nv_error(parent, "failed to attach %s context, %d\n",
-                        subdev->name, ret);
-               return ret;
-       }
-
-       nv_debug(parent, "attached %s context\n", subdev->name);
-       return 0;
-}
-
-int
-nouveau_engctx_fini(struct nouveau_engctx *engctx, bool suspend)
-{
-       struct nouveau_object *object = nv_object(engctx);
-       struct nouveau_subdev *subdev = nv_subdev(object->engine);
-       struct nouveau_object *parent;
-       struct nouveau_subdev *pardev;
-       int ret = 0;
-
-       parent = nv_pclass(object->parent, NV_PARENT_CLASS);
-       pardev = nv_subdev(parent->engine);
-       if (nv_parent(parent)->context_detach) {
-               mutex_lock(&pardev->mutex);
-               ret = nv_parent(parent)->context_detach(parent, suspend, object);
-               mutex_unlock(&pardev->mutex);
-       }
-
-       if (ret) {
-               nv_error(parent, "failed to detach %s context, %d\n",
-                        subdev->name, ret);
-               return ret;
-       }
-
-       nv_debug(parent, "detached %s context\n", subdev->name);
-       return nouveau_gpuobj_fini(&engctx->base, suspend);
-}
-
-int
-_nouveau_engctx_ctor(struct nouveau_object *parent,
-                    struct nouveau_object *engine,
-                    struct nouveau_oclass *oclass, void *data, u32 size,
-                    struct nouveau_object **pobject)
-{
-       struct nouveau_engctx *engctx;
-       int ret;
-
-       ret = nouveau_engctx_create(parent, engine, oclass, NULL, 256, 256,
-                                   NVOBJ_FLAG_ZERO_ALLOC, &engctx);
-       *pobject = nv_object(engctx);
-       return ret;
-}
-
-void
-_nouveau_engctx_dtor(struct nouveau_object *object)
-{
-       nouveau_engctx_destroy(nv_engctx(object));
-}
-
-int
-_nouveau_engctx_init(struct nouveau_object *object)
-{
-       return nouveau_engctx_init(nv_engctx(object));
-}
-
-
-int
-_nouveau_engctx_fini(struct nouveau_object *object, bool suspend)
-{
-       return nouveau_engctx_fini(nv_engctx(object), suspend);
-}
-
-struct nouveau_object *
-nouveau_engctx_get(struct nouveau_engine *engine, u64 addr)
-{
-       struct nouveau_engctx *engctx;
-       unsigned long flags;
-
-       spin_lock_irqsave(&engine->lock, flags);
-       list_for_each_entry(engctx, &engine->contexts, head) {
-               if (engctx->addr == addr) {
-                       engctx->save = flags;
-                       return nv_object(engctx);
-               }
-       }
-       spin_unlock_irqrestore(&engine->lock, flags);
-       return NULL;
-}
-
-void
-nouveau_engctx_put(struct nouveau_object *object)
-{
-       if (object) {
-               struct nouveau_engine *engine = nv_engine(object->engine);
-               struct nouveau_engctx *engctx = nv_engctx(object);
-               spin_unlock_irqrestore(&engine->lock, engctx->save);
-       }
-}
diff --git a/drivers/gpu/drm/nouveau/core/core/engine.c b/drivers/gpu/drm/nouveau/core/core/engine.c
deleted file mode 100644 (file)
index 1f6954a..0000000
+++ /dev/null
@@ -1,68 +0,0 @@
-/*
- * Copyright 2012 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 <core/device.h>
-#include <core/engine.h>
-#include <core/option.h>
-
-int
-nouveau_engine_create_(struct nouveau_object *parent,
-                      struct nouveau_object *engobj,
-                      struct nouveau_oclass *oclass, bool enable,
-                      const char *iname, const char *fname,
-                      int length, void **pobject)
-{
-       struct nouveau_engine *engine;
-       int ret;
-
-       ret = nouveau_subdev_create_(parent, engobj, oclass, NV_ENGINE_CLASS,
-                                    iname, fname, length, pobject);
-       engine = *pobject;
-       if (ret)
-               return ret;
-
-       if (parent) {
-               struct nouveau_device *device = nv_device(parent);
-               int engidx = nv_engidx(nv_object(engine));
-
-               if (device->disable_mask & (1ULL << engidx)) {
-                       if (!nouveau_boolopt(device->cfgopt, iname, false)) {
-                               nv_debug(engine, "engine disabled by hw/fw\n");
-                               return -ENODEV;
-                       }
-
-                       nv_warn(engine, "ignoring hw/fw engine disable\n");
-               }
-
-               if (!nouveau_boolopt(device->cfgopt, iname, enable)) {
-                       if (!enable)
-                               nv_warn(engine, "disabled, %s=1 to enable\n", iname);
-                       return -ENODEV;
-               }
-       }
-
-       INIT_LIST_HEAD(&engine->contexts);
-       spin_lock_init(&engine->lock);
-       return 0;
-}
diff --git a/drivers/gpu/drm/nouveau/core/core/enum.c b/drivers/gpu/drm/nouveau/core/core/enum.c
deleted file mode 100644 (file)
index dd43479..0000000
+++ /dev/null
@@ -1,68 +0,0 @@
-/*
- * Copyright (C) 2010 Nouveau Project
- *
- * 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 <core/os.h>
-#include <core/enum.h>
-
-const struct nouveau_enum *
-nouveau_enum_find(const struct nouveau_enum *en, u32 value)
-{
-       while (en->name) {
-               if (en->value == value)
-                       return en;
-               en++;
-       }
-
-       return NULL;
-}
-
-const struct nouveau_enum *
-nouveau_enum_print(const struct nouveau_enum *en, u32 value)
-{
-       en = nouveau_enum_find(en, value);
-       if (en)
-               pr_cont("%s", en->name);
-       else
-               pr_cont("(unknown enum 0x%08x)", value);
-       return en;
-}
-
-void
-nouveau_bitfield_print(const struct nouveau_bitfield *bf, u32 value)
-{
-       while (bf->name) {
-               if (value & bf->mask) {
-                       pr_cont(" %s", bf->name);
-                       value &= ~bf->mask;
-               }
-
-               bf++;
-       }
-
-       if (value)
-               pr_cont(" (unknown bits 0x%08x)", value);
-}
diff --git a/drivers/gpu/drm/nouveau/core/core/event.c b/drivers/gpu/drm/nouveau/core/core/event.c
deleted file mode 100644 (file)
index 760947e..0000000
+++ /dev/null
@@ -1,100 +0,0 @@
-/*
- * Copyright 2013-2014 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.
- */
-
-#include <core/object.h>
-#include <core/event.h>
-
-void
-nvkm_event_put(struct nvkm_event *event, u32 types, int index)
-{
-       assert_spin_locked(&event->refs_lock);
-       while (types) {
-               int type = __ffs(types); types &= ~(1 << type);
-               if (--event->refs[index * event->types_nr + type] == 0) {
-                       if (event->func->fini)
-                               event->func->fini(event, 1 << type, index);
-               }
-       }
-}
-
-void
-nvkm_event_get(struct nvkm_event *event, u32 types, int index)
-{
-       assert_spin_locked(&event->refs_lock);
-       while (types) {
-               int type = __ffs(types); types &= ~(1 << type);
-               if (++event->refs[index * event->types_nr + type] == 1) {
-                       if (event->func->init)
-                               event->func->init(event, 1 << type, index);
-               }
-       }
-}
-
-void
-nvkm_event_send(struct nvkm_event *event, u32 types, int index,
-               void *data, u32 size)
-{
-       struct nvkm_notify *notify;
-       unsigned long flags;
-
-       if (!event->refs || WARN_ON(index >= event->index_nr))
-               return;
-
-       spin_lock_irqsave(&event->list_lock, flags);
-       list_for_each_entry(notify, &event->list, head) {
-               if (notify->index == index && (notify->types & types)) {
-                       if (event->func->send) {
-                               event->func->send(data, size, notify);
-                               continue;
-                       }
-                       nvkm_notify_send(notify, data, size);
-               }
-       }
-       spin_unlock_irqrestore(&event->list_lock, flags);
-}
-
-void
-nvkm_event_fini(struct nvkm_event *event)
-{
-       if (event->refs) {
-               kfree(event->refs);
-               event->refs = NULL;
-       }
-}
-
-int
-nvkm_event_init(const struct nvkm_event_func *func, int types_nr, int index_nr,
-               struct nvkm_event *event)
-{
-       event->refs = kzalloc(sizeof(*event->refs) * index_nr * types_nr,
-                             GFP_KERNEL);
-       if (!event->refs)
-               return -ENOMEM;
-
-       event->func = func;
-       event->types_nr = types_nr;
-       event->index_nr = index_nr;
-       spin_lock_init(&event->refs_lock);
-       spin_lock_init(&event->list_lock);
-       INIT_LIST_HEAD(&event->list);
-       return 0;
-}
diff --git a/drivers/gpu/drm/nouveau/core/core/gpuobj.c b/drivers/gpu/drm/nouveau/core/core/gpuobj.c
deleted file mode 100644 (file)
index daee877..0000000
+++ /dev/null
@@ -1,323 +0,0 @@
-/*
- * Copyright 2012 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 <core/object.h>
-#include <core/gpuobj.h>
-
-#include <subdev/instmem.h>
-#include <subdev/bar.h>
-#include <subdev/vm.h>
-
-void
-nouveau_gpuobj_destroy(struct nouveau_gpuobj *gpuobj)
-{
-       int i;
-
-       if (gpuobj->flags & NVOBJ_FLAG_ZERO_FREE) {
-               for (i = 0; i < gpuobj->size; i += 4)
-                       nv_wo32(gpuobj, i, 0x00000000);
-       }
-
-       if (gpuobj->node) {
-               nouveau_mm_free(&nv_gpuobj(gpuobj->parent)->heap,
-                               &gpuobj->node);
-       }
-
-       if (gpuobj->heap.block_size)
-               nouveau_mm_fini(&gpuobj->heap);
-
-       nouveau_object_destroy(&gpuobj->base);
-}
-
-int
-nouveau_gpuobj_create_(struct nouveau_object *parent,
-                      struct nouveau_object *engine,
-                      struct nouveau_oclass *oclass, u32 pclass,
-                      struct nouveau_object *pargpu,
-                      u32 size, u32 align, u32 flags,
-                      int length, void **pobject)
-{
-       struct nouveau_instmem *imem = nouveau_instmem(parent);
-       struct nouveau_bar *bar = nouveau_bar(parent);
-       struct nouveau_gpuobj *gpuobj;
-       struct nouveau_mm *heap = NULL;
-       int ret, i;
-       u64 addr;
-
-       *pobject = NULL;
-
-       if (pargpu) {
-               while ((pargpu = nv_pclass(pargpu, NV_GPUOBJ_CLASS))) {
-                       if (nv_gpuobj(pargpu)->heap.block_size)
-                               break;
-                       pargpu = pargpu->parent;
-               }
-
-               if (unlikely(pargpu == NULL)) {
-                       nv_error(parent, "no gpuobj heap\n");
-                       return -EINVAL;
-               }
-
-               addr =  nv_gpuobj(pargpu)->addr;
-               heap = &nv_gpuobj(pargpu)->heap;
-               atomic_inc(&parent->refcount);
-       } else {
-               ret = imem->alloc(imem, parent, size, align, &parent);
-               pargpu = parent;
-               if (ret)
-                       return ret;
-
-               addr = nv_memobj(pargpu)->addr;
-               size = nv_memobj(pargpu)->size;
-
-               if (bar && bar->alloc) {
-                       struct nouveau_instobj *iobj = (void *)parent;
-                       struct nouveau_mem **mem = (void *)(iobj + 1);
-                       struct nouveau_mem *node = *mem;
-                       if (!bar->alloc(bar, parent, node, &pargpu)) {
-                               nouveau_object_ref(NULL, &parent);
-                               parent = pargpu;
-                       }
-               }
-       }
-
-       ret = nouveau_object_create_(parent, engine, oclass, pclass |
-                                    NV_GPUOBJ_CLASS, length, pobject);
-       nouveau_object_ref(NULL, &parent);
-       gpuobj = *pobject;
-       if (ret)
-               return ret;
-
-       gpuobj->parent = pargpu;
-       gpuobj->flags = flags;
-       gpuobj->addr = addr;
-       gpuobj->size = size;
-
-       if (heap) {
-               ret = nouveau_mm_head(heap, 0, 1, size, size,
-                                     max(align, (u32)1), &gpuobj->node);
-               if (ret)
-                       return ret;
-
-               gpuobj->addr += gpuobj->node->offset;
-       }
-
-       if (gpuobj->flags & NVOBJ_FLAG_HEAP) {
-               ret = nouveau_mm_init(&gpuobj->heap, 0, gpuobj->size, 1);
-               if (ret)
-                       return ret;
-       }
-
-       if (flags & NVOBJ_FLAG_ZERO_ALLOC) {
-               for (i = 0; i < gpuobj->size; i += 4)
-                       nv_wo32(gpuobj, i, 0x00000000);
-       }
-
-       return ret;
-}
-
-struct nouveau_gpuobj_class {
-       struct nouveau_object *pargpu;
-       u64 size;
-       u32 align;
-       u32 flags;
-};
-
-static int
-_nouveau_gpuobj_ctor(struct nouveau_object *parent,
-                    struct nouveau_object *engine,
-                    struct nouveau_oclass *oclass, void *data, u32 size,
-                    struct nouveau_object **pobject)
-{
-       struct nouveau_gpuobj_class *args = data;
-       struct nouveau_gpuobj *object;
-       int ret;
-
-       ret = nouveau_gpuobj_create(parent, engine, oclass, 0, args->pargpu,
-                                   args->size, args->align, args->flags,
-                                   &object);
-       *pobject = nv_object(object);
-       if (ret)
-               return ret;
-
-       return 0;
-}
-
-void
-_nouveau_gpuobj_dtor(struct nouveau_object *object)
-{
-       nouveau_gpuobj_destroy(nv_gpuobj(object));
-}
-
-int
-_nouveau_gpuobj_init(struct nouveau_object *object)
-{
-       return nouveau_gpuobj_init(nv_gpuobj(object));
-}
-
-int
-_nouveau_gpuobj_fini(struct nouveau_object *object, bool suspend)
-{
-       return nouveau_gpuobj_fini(nv_gpuobj(object), suspend);
-}
-
-u32
-_nouveau_gpuobj_rd32(struct nouveau_object *object, u64 addr)
-{
-       struct nouveau_gpuobj *gpuobj = nv_gpuobj(object);
-       struct nouveau_ofuncs *pfuncs = nv_ofuncs(gpuobj->parent);
-       if (gpuobj->node)
-               addr += gpuobj->node->offset;
-       return pfuncs->rd32(gpuobj->parent, addr);
-}
-
-void
-_nouveau_gpuobj_wr32(struct nouveau_object *object, u64 addr, u32 data)
-{
-       struct nouveau_gpuobj *gpuobj = nv_gpuobj(object);
-       struct nouveau_ofuncs *pfuncs = nv_ofuncs(gpuobj->parent);
-       if (gpuobj->node)
-               addr += gpuobj->node->offset;
-       pfuncs->wr32(gpuobj->parent, addr, data);
-}
-
-static struct nouveau_oclass
-_nouveau_gpuobj_oclass = {
-       .handle = 0x00000000,
-       .ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = _nouveau_gpuobj_ctor,
-               .dtor = _nouveau_gpuobj_dtor,
-               .init = _nouveau_gpuobj_init,
-               .fini = _nouveau_gpuobj_fini,
-               .rd32 = _nouveau_gpuobj_rd32,
-               .wr32 = _nouveau_gpuobj_wr32,
-       },
-};
-
-int
-nouveau_gpuobj_new(struct nouveau_object *parent, struct nouveau_object *pargpu,
-                  u32 size, u32 align, u32 flags,
-                  struct nouveau_gpuobj **pgpuobj)
-{
-       struct nouveau_object *engine = parent;
-       struct nouveau_gpuobj_class args = {
-               .pargpu = pargpu,
-               .size = size,
-               .align = align,
-               .flags = flags,
-       };
-
-       if (!nv_iclass(engine, NV_SUBDEV_CLASS))
-               engine = engine->engine;
-       BUG_ON(engine == NULL);
-
-       return nouveau_object_ctor(parent, engine, &_nouveau_gpuobj_oclass,
-                                  &args, sizeof(args),
-                                  (struct nouveau_object **)pgpuobj);
-}
-
-int
-nouveau_gpuobj_map(struct nouveau_gpuobj *gpuobj, u32 access,
-                  struct nouveau_vma *vma)
-{
-       struct nouveau_bar *bar = nouveau_bar(gpuobj);
-       int ret = -EINVAL;
-
-       if (bar && bar->umap) {
-               struct nouveau_instobj *iobj = (void *)
-                       nv_pclass(nv_object(gpuobj), NV_MEMOBJ_CLASS);
-               struct nouveau_mem **mem = (void *)(iobj + 1);
-               ret = bar->umap(bar, *mem, access, vma);
-       }
-
-       return ret;
-}
-
-int
-nouveau_gpuobj_map_vm(struct nouveau_gpuobj *gpuobj, struct nouveau_vm *vm,
-                     u32 access, struct nouveau_vma *vma)
-{
-       struct nouveau_instobj *iobj = (void *)
-               nv_pclass(nv_object(gpuobj), NV_MEMOBJ_CLASS);
-       struct nouveau_mem **mem = (void *)(iobj + 1);
-       int ret;
-
-       ret = nouveau_vm_get(vm, gpuobj->size, 12, access, vma);
-       if (ret)
-               return ret;
-
-       nouveau_vm_map(vma, *mem);
-       return 0;
-}
-
-void
-nouveau_gpuobj_unmap(struct nouveau_vma *vma)
-{
-       if (vma->node) {
-               nouveau_vm_unmap(vma);
-               nouveau_vm_put(vma);
-       }
-}
-
-/* the below is basically only here to support sharing the paged dma object
- * for PCI(E)GART on <=nv4x chipsets, and should *not* be expected to work
- * anywhere else.
- */
-
-static void
-nouveau_gpudup_dtor(struct nouveau_object *object)
-{
-       struct nouveau_gpuobj *gpuobj = (void *)object;
-       nouveau_object_ref(NULL, &gpuobj->parent);
-       nouveau_object_destroy(&gpuobj->base);
-}
-
-static struct nouveau_oclass
-nouveau_gpudup_oclass = {
-       .handle = NV_GPUOBJ_CLASS,
-       .ofuncs = &(struct nouveau_ofuncs) {
-               .dtor = nouveau_gpudup_dtor,
-               .init = nouveau_object_init,
-               .fini = nouveau_object_fini,
-       },
-};
-
-int
-nouveau_gpuobj_dup(struct nouveau_object *parent, struct nouveau_gpuobj *base,
-                  struct nouveau_gpuobj **pgpuobj)
-{
-       struct nouveau_gpuobj *gpuobj;
-       int ret;
-
-       ret = nouveau_object_create(parent, parent->engine,
-                                  &nouveau_gpudup_oclass, 0, &gpuobj);
-       *pgpuobj = gpuobj;
-       if (ret)
-               return ret;
-
-       nouveau_object_ref(nv_object(base), &gpuobj->parent);
-       gpuobj->addr = base->addr;
-       gpuobj->size = base->size;
-       return 0;
-}
diff --git a/drivers/gpu/drm/nouveau/core/core/handle.c b/drivers/gpu/drm/nouveau/core/core/handle.c
deleted file mode 100644 (file)
index 13f816c..0000000
+++ /dev/null
@@ -1,224 +0,0 @@
-/*
- * Copyright 2012 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 <core/object.h>
-#include <core/handle.h>
-#include <core/client.h>
-
-#define hprintk(h,l,f,a...) do {                                               \
-       struct nouveau_client *c = nouveau_client((h)->object);                \
-       struct nouveau_handle *p = (h)->parent; u32 n = p ? p->name : ~0;      \
-       nv_printk((c), l, "0x%08x:0x%08x "f, n, (h)->name, ##a);               \
-} while(0)
-
-int
-nouveau_handle_init(struct nouveau_handle *handle)
-{
-       struct nouveau_handle *item;
-       int ret;
-
-       hprintk(handle, TRACE, "init running\n");
-       ret = nouveau_object_inc(handle->object);
-       if (ret)
-               return ret;
-
-       hprintk(handle, TRACE, "init children\n");
-       list_for_each_entry(item, &handle->tree, head) {
-               ret = nouveau_handle_init(item);
-               if (ret)
-                       goto fail;
-       }
-
-       hprintk(handle, TRACE, "init completed\n");
-       return 0;
-fail:
-       hprintk(handle, ERROR, "init failed with %d\n", ret);
-       list_for_each_entry_continue_reverse(item, &handle->tree, head) {
-               nouveau_handle_fini(item, false);
-       }
-
-       nouveau_object_dec(handle->object, false);
-       return ret;
-}
-
-int
-nouveau_handle_fini(struct nouveau_handle *handle, bool suspend)
-{
-       static char *name[2] = { "fini", "suspend" };
-       struct nouveau_handle *item;
-       int ret;
-
-       hprintk(handle, TRACE, "%s children\n", name[suspend]);
-       list_for_each_entry(item, &handle->tree, head) {
-               ret = nouveau_handle_fini(item, suspend);
-               if (ret && suspend)
-                       goto fail;
-       }
-
-       hprintk(handle, TRACE, "%s running\n", name[suspend]);
-       if (handle->object) {
-               ret = nouveau_object_dec(handle->object, suspend);
-               if (ret && suspend)
-                       goto fail;
-       }
-
-       hprintk(handle, TRACE, "%s completed\n", name[suspend]);
-       return 0;
-fail:
-       hprintk(handle, ERROR, "%s failed with %d\n", name[suspend], ret);
-       list_for_each_entry_continue_reverse(item, &handle->tree, head) {
-               int rret = nouveau_handle_init(item);
-               if (rret)
-                       hprintk(handle, FATAL, "failed to restart, %d\n", rret);
-       }
-
-       return ret;
-}
-
-int
-nouveau_handle_create(struct nouveau_object *parent, u32 _parent, u32 _handle,
-                     struct nouveau_object *object,
-                     struct nouveau_handle **phandle)
-{
-       struct nouveau_object *namedb;
-       struct nouveau_handle *handle;
-       int ret;
-
-       namedb = parent;
-       while (!nv_iclass(namedb, NV_NAMEDB_CLASS))
-               namedb = namedb->parent;
-
-       handle = kzalloc(sizeof(*handle), GFP_KERNEL);
-       if (!handle)
-               return -ENOMEM;
-
-       INIT_LIST_HEAD(&handle->head);
-       INIT_LIST_HEAD(&handle->tree);
-       handle->name = _handle;
-       handle->priv = ~0;
-
-       ret = nouveau_namedb_insert(nv_namedb(namedb), _handle, object, handle);
-       if (ret) {
-               kfree(handle);
-               return ret;
-       }
-
-       if (nv_parent(parent)->object_attach) {
-               ret = nv_parent(parent)->object_attach(parent, object, _handle);
-               if (ret < 0) {
-                       nouveau_handle_destroy(handle);
-                       return ret;
-               }
-
-               handle->priv = ret;
-       }
-
-       if (object != namedb) {
-               while (!nv_iclass(namedb, NV_CLIENT_CLASS))
-                       namedb = namedb->parent;
-
-               handle->parent = nouveau_namedb_get(nv_namedb(namedb), _parent);
-               if (handle->parent) {
-                       list_add(&handle->head, &handle->parent->tree);
-                       nouveau_namedb_put(handle->parent);
-               }
-       }
-
-       hprintk(handle, TRACE, "created\n");
-       *phandle = handle;
-       return 0;
-}
-
-void
-nouveau_handle_destroy(struct nouveau_handle *handle)
-{
-       struct nouveau_handle *item, *temp;
-
-       hprintk(handle, TRACE, "destroy running\n");
-       list_for_each_entry_safe(item, temp, &handle->tree, head) {
-               nouveau_handle_destroy(item);
-       }
-       list_del(&handle->head);
-
-       if (handle->priv != ~0) {
-               struct nouveau_object *parent = handle->parent->object;
-               nv_parent(parent)->object_detach(parent, handle->priv);
-       }
-
-       hprintk(handle, TRACE, "destroy completed\n");
-       nouveau_namedb_remove(handle);
-       kfree(handle);
-}
-
-struct nouveau_object *
-nouveau_handle_ref(struct nouveau_object *parent, u32 name)
-{
-       struct nouveau_object *object = NULL;
-       struct nouveau_handle *handle;
-
-       while (!nv_iclass(parent, NV_NAMEDB_CLASS))
-               parent = parent->parent;
-
-       handle = nouveau_namedb_get(nv_namedb(parent), name);
-       if (handle) {
-               nouveau_object_ref(handle->object, &object);
-               nouveau_namedb_put(handle);
-       }
-
-       return object;
-}
-
-struct nouveau_handle *
-nouveau_handle_get_class(struct nouveau_object *engctx, u16 oclass)
-{
-       struct nouveau_namedb *namedb;
-       if (engctx && (namedb = (void *)nv_pclass(engctx, NV_NAMEDB_CLASS)))
-               return nouveau_namedb_get_class(namedb, oclass);
-       return NULL;
-}
-
-struct nouveau_handle *
-nouveau_handle_get_vinst(struct nouveau_object *engctx, u64 vinst)
-{
-       struct nouveau_namedb *namedb;
-       if (engctx && (namedb = (void *)nv_pclass(engctx, NV_NAMEDB_CLASS)))
-               return nouveau_namedb_get_vinst(namedb, vinst);
-       return NULL;
-}
-
-struct nouveau_handle *
-nouveau_handle_get_cinst(struct nouveau_object *engctx, u32 cinst)
-{
-       struct nouveau_namedb *namedb;
-       if (engctx && (namedb = (void *)nv_pclass(engctx, NV_NAMEDB_CLASS)))
-               return nouveau_namedb_get_cinst(namedb, cinst);
-       return NULL;
-}
-
-void
-nouveau_handle_put(struct nouveau_handle *handle)
-{
-       if (handle)
-               nouveau_namedb_put(handle);
-}
diff --git a/drivers/gpu/drm/nouveau/core/core/ioctl.c b/drivers/gpu/drm/nouveau/core/core/ioctl.c
deleted file mode 100644 (file)
index 692aa92..0000000
+++ /dev/null
@@ -1,530 +0,0 @@
-/*
- * Copyright 2014 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 <bskeggs@redhat.com>
- */
-
-#include <core/object.h>
-#include <core/parent.h>
-#include <core/handle.h>
-#include <core/namedb.h>
-#include <core/client.h>
-#include <core/device.h>
-#include <core/ioctl.h>
-#include <core/event.h>
-
-#include <nvif/unpack.h>
-#include <nvif/ioctl.h>
-
-static int
-nvkm_ioctl_nop(struct nouveau_handle *handle, void *data, u32 size)
-{
-       struct nouveau_object *object = handle->object;
-       union {
-               struct nvif_ioctl_nop none;
-       } *args = data;
-       int ret;
-
-       nv_ioctl(object, "nop size %d\n", size);
-       if (nvif_unvers(args->none)) {
-               nv_ioctl(object, "nop\n");
-       }
-
-       return ret;
-}
-
-static int
-nvkm_ioctl_sclass(struct nouveau_handle *handle, void *data, u32 size)
-{
-       struct nouveau_object *object = handle->object;
-       union {
-               struct nvif_ioctl_sclass_v0 v0;
-       } *args = data;
-       int ret;
-
-       if (!nv_iclass(object, NV_PARENT_CLASS)) {
-               nv_debug(object, "cannot have children (sclass)\n");
-               return -ENODEV;
-       }
-
-       nv_ioctl(object, "sclass size %d\n", size);
-       if (nvif_unpack(args->v0, 0, 0, true)) {
-               nv_ioctl(object, "sclass vers %d count %d\n",
-                        args->v0.version, args->v0.count);
-               if (size == args->v0.count * sizeof(args->v0.oclass[0])) {
-                       ret = nouveau_parent_lclass(object, args->v0.oclass,
-                                                           args->v0.count);
-                       if (ret >= 0) {
-                               args->v0.count = ret;
-                               ret = 0;
-                       }
-               } else {
-                       ret = -EINVAL;
-               }
-       }
-
-       return ret;
-}
-
-static int
-nvkm_ioctl_new(struct nouveau_handle *parent, void *data, u32 size)
-{
-       union {
-               struct nvif_ioctl_new_v0 v0;
-       } *args = data;
-       struct nouveau_client *client = nouveau_client(parent->object);
-       struct nouveau_object *engctx = NULL;
-       struct nouveau_object *object = NULL;
-       struct nouveau_object *engine;
-       struct nouveau_oclass *oclass;
-       struct nouveau_handle *handle;
-       u32 _handle, _oclass;
-       int ret;
-
-       nv_ioctl(client, "new size %d\n", size);
-       if (nvif_unpack(args->v0, 0, 0, true)) {
-               _handle = args->v0.handle;
-               _oclass = args->v0.oclass;
-       } else
-               return ret;
-
-       nv_ioctl(client, "new vers %d handle %08x class %08x "
-                        "route %02x token %llx\n",
-               args->v0.version, _handle, _oclass,
-               args->v0.route, args->v0.token);
-
-       if (!nv_iclass(parent->object, NV_PARENT_CLASS)) {
-               nv_debug(parent->object, "cannot have children (ctor)\n");
-               ret = -ENODEV;
-               goto fail_class;
-       }
-
-       /* check that parent supports the requested subclass */
-       ret = nouveau_parent_sclass(parent->object, _oclass, &engine, &oclass);
-       if (ret) {
-               nv_debug(parent->object, "illegal class 0x%04x\n", _oclass);
-               goto fail_class;
-       }
-
-       /* make sure engine init has been completed *before* any objects
-        * it controls are created - the constructors may depend on
-        * state calculated at init (ie. default context construction)
-        */
-       if (engine) {
-               ret = nouveau_object_inc(engine);
-               if (ret)
-                       goto fail_class;
-       }
-
-       /* if engine requires it, create a context object to insert
-        * between the parent and its children (eg. PGRAPH context)
-        */
-       if (engine && nv_engine(engine)->cclass) {
-               ret = nouveau_object_ctor(parent->object, engine,
-                                         nv_engine(engine)->cclass,
-                                         data, size, &engctx);
-               if (ret)
-                       goto fail_engctx;
-       } else {
-               nouveau_object_ref(parent->object, &engctx);
-       }
-
-       /* finally, create new object and bind it to its handle */
-       ret = nouveau_object_ctor(engctx, engine, oclass, data, size, &object);
-       client->data = object;
-       if (ret)
-               goto fail_ctor;
-
-       ret = nouveau_object_inc(object);
-       if (ret)
-               goto fail_init;
-
-       ret = nouveau_handle_create(parent->object, parent->name,
-                                   _handle, object, &handle);
-       if (ret)
-               goto fail_handle;
-
-       ret = nouveau_handle_init(handle);
-       handle->route = args->v0.route;
-       handle->token = args->v0.token;
-       if (ret)
-               nouveau_handle_destroy(handle);
-
-fail_handle:
-       nouveau_object_dec(object, false);
-fail_init:
-       nouveau_object_ref(NULL, &object);
-fail_ctor:
-       nouveau_object_ref(NULL, &engctx);
-fail_engctx:
-       if (engine)
-               nouveau_object_dec(engine, false);
-fail_class:
-       return ret;
-}
-
-static int
-nvkm_ioctl_del(struct nouveau_handle *handle, void *data, u32 size)
-{
-       struct nouveau_object *object = handle->object;
-       union {
-               struct nvif_ioctl_del none;
-       } *args = data;
-       int ret;
-
-       nv_ioctl(object, "delete size %d\n", size);
-       if (nvif_unvers(args->none)) {
-               nv_ioctl(object, "delete\n");
-               nouveau_handle_fini(handle, false);
-               nouveau_handle_destroy(handle);
-       }
-
-       return ret;
-}
-
-static int
-nvkm_ioctl_mthd(struct nouveau_handle *handle, void *data, u32 size)
-{
-       struct nouveau_object *object = handle->object;
-       struct nouveau_ofuncs *ofuncs = object->oclass->ofuncs;
-       union {
-               struct nvif_ioctl_mthd_v0 v0;
-       } *args = data;
-       int ret;
-
-       nv_ioctl(object, "mthd size %d\n", size);
-       if (nvif_unpack(args->v0, 0, 0, true)) {
-               nv_ioctl(object, "mthd vers %d mthd %02x\n",
-                        args->v0.version, args->v0.method);
-               if (ret = -ENODEV, ofuncs->mthd)
-                       ret = ofuncs->mthd(object, args->v0.method, data, size);
-       }
-
-       return ret;
-}
-
-
-static int
-nvkm_ioctl_rd(struct nouveau_handle *handle, void *data, u32 size)
-{
-       struct nouveau_object *object = handle->object;
-       struct nouveau_ofuncs *ofuncs = object->oclass->ofuncs;
-       union {
-               struct nvif_ioctl_rd_v0 v0;
-       } *args = data;
-       int ret;
-
-       nv_ioctl(object, "rd size %d\n", size);
-       if (nvif_unpack(args->v0, 0, 0, false)) {
-               nv_ioctl(object, "rd vers %d size %d addr %016llx\n",
-                       args->v0.version, args->v0.size, args->v0.addr);
-               switch (args->v0.size) {
-               case 1:
-                       if (ret = -ENODEV, ofuncs->rd08) {
-                               args->v0.data = nv_ro08(object, args->v0.addr);
-                               ret = 0;
-                       }
-                       break;
-               case 2:
-                       if (ret = -ENODEV, ofuncs->rd16) {
-                               args->v0.data = nv_ro16(object, args->v0.addr);
-                               ret = 0;
-                       }
-                       break;
-               case 4:
-                       if (ret = -ENODEV, ofuncs->rd32) {
-                               args->v0.data = nv_ro32(object, args->v0.addr);
-                               ret = 0;
-                       }
-                       break;
-               default:
-                       ret = -EINVAL;
-                       break;
-               }
-       }
-
-       return ret;
-}
-
-static int
-nvkm_ioctl_wr(struct nouveau_handle *handle, void *data, u32 size)
-{
-       struct nouveau_object *object = handle->object;
-       struct nouveau_ofuncs *ofuncs = object->oclass->ofuncs;
-       union {
-               struct nvif_ioctl_wr_v0 v0;
-       } *args = data;
-       int ret;
-
-       nv_ioctl(object, "wr size %d\n", size);
-       if (nvif_unpack(args->v0, 0, 0, false)) {
-               nv_ioctl(object, "wr vers %d size %d addr %016llx data %08x\n",
-                        args->v0.version, args->v0.size, args->v0.addr,
-                        args->v0.data);
-               switch (args->v0.size) {
-               case 1:
-                       if (ret = -ENODEV, ofuncs->wr08) {
-                               nv_wo08(object, args->v0.addr, args->v0.data);
-                               ret = 0;
-                       }
-                       break;
-               case 2:
-                       if (ret = -ENODEV, ofuncs->wr16) {
-                               nv_wo16(object, args->v0.addr, args->v0.data);
-                               ret = 0;
-                       }
-                       break;
-               case 4:
-                       if (ret = -ENODEV, ofuncs->wr32) {
-                               nv_wo32(object, args->v0.addr, args->v0.data);
-                               ret = 0;
-                       }
-                       break;
-               default:
-                       ret = -EINVAL;
-                       break;
-               }
-       }
-
-       return ret;
-}
-
-static int
-nvkm_ioctl_map(struct nouveau_handle *handle, void *data, u32 size)
-{
-       struct nouveau_object *object = handle->object;
-       struct nouveau_ofuncs *ofuncs = object->oclass->ofuncs;
-       union {
-               struct nvif_ioctl_map_v0 v0;
-       } *args = data;
-       int ret;
-
-       nv_ioctl(object, "map size %d\n", size);
-       if (nvif_unpack(args->v0, 0, 0, false)) {
-               nv_ioctl(object, "map vers %d\n", args->v0.version);
-               if (ret = -ENODEV, ofuncs->map) {
-                       ret = ofuncs->map(object, &args->v0.handle,
-                                                 &args->v0.length);
-               }
-       }
-
-       return ret;
-}
-
-static int
-nvkm_ioctl_unmap(struct nouveau_handle *handle, void *data, u32 size)
-{
-       struct nouveau_object *object = handle->object;
-       union {
-               struct nvif_ioctl_unmap none;
-       } *args = data;
-       int ret;
-
-       nv_ioctl(object, "unmap size %d\n", size);
-       if (nvif_unvers(args->none)) {
-               nv_ioctl(object, "unmap\n");
-       }
-
-       return ret;
-}
-
-static int
-nvkm_ioctl_ntfy_new(struct nouveau_handle *handle, void *data, u32 size)
-{
-       struct nouveau_object *object = handle->object;
-       struct nouveau_ofuncs *ofuncs = object->oclass->ofuncs;
-       union {
-               struct nvif_ioctl_ntfy_new_v0 v0;
-       } *args = data;
-       struct nvkm_event *event;
-       int ret;
-
-       nv_ioctl(object, "ntfy new size %d\n", size);
-       if (nvif_unpack(args->v0, 0, 0, true)) {
-               nv_ioctl(object, "ntfy new vers %d event %02x\n",
-                        args->v0.version, args->v0.event);
-               if (ret = -ENODEV, ofuncs->ntfy)
-                       ret = ofuncs->ntfy(object, args->v0.event, &event);
-               if (ret == 0) {
-                       ret = nvkm_client_notify_new(object, event, data, size);
-                       if (ret >= 0) {
-                               args->v0.index = ret;
-                               ret = 0;
-                       }
-               }
-       }
-
-       return ret;
-}
-
-static int
-nvkm_ioctl_ntfy_del(struct nouveau_handle *handle, void *data, u32 size)
-{
-       struct nouveau_client *client = nouveau_client(handle->object);
-       struct nouveau_object *object = handle->object;
-       union {
-               struct nvif_ioctl_ntfy_del_v0 v0;
-       } *args = data;
-       int ret;
-
-       nv_ioctl(object, "ntfy del size %d\n", size);
-       if (nvif_unpack(args->v0, 0, 0, false)) {
-               nv_ioctl(object, "ntfy del vers %d index %d\n",
-                        args->v0.version, args->v0.index);
-               ret = nvkm_client_notify_del(client, args->v0.index);
-       }
-
-       return ret;
-}
-
-static int
-nvkm_ioctl_ntfy_get(struct nouveau_handle *handle, void *data, u32 size)
-{
-       struct nouveau_client *client = nouveau_client(handle->object);
-       struct nouveau_object *object = handle->object;
-       union {
-               struct nvif_ioctl_ntfy_get_v0 v0;
-       } *args = data;
-       int ret;
-
-       nv_ioctl(object, "ntfy get size %d\n", size);
-       if (nvif_unpack(args->v0, 0, 0, false)) {
-               nv_ioctl(object, "ntfy get vers %d index %d\n",
-                        args->v0.version, args->v0.index);
-               ret = nvkm_client_notify_get(client, args->v0.index);
-       }
-
-       return ret;
-}
-
-static int
-nvkm_ioctl_ntfy_put(struct nouveau_handle *handle, void *data, u32 size)
-{
-       struct nouveau_client *client = nouveau_client(handle->object);
-       struct nouveau_object *object = handle->object;
-       union {
-               struct nvif_ioctl_ntfy_put_v0 v0;
-       } *args = data;
-       int ret;
-
-       nv_ioctl(object, "ntfy put size %d\n", size);
-       if (nvif_unpack(args->v0, 0, 0, false)) {
-               nv_ioctl(object, "ntfy put vers %d index %d\n",
-                        args->v0.version, args->v0.index);
-               ret = nvkm_client_notify_put(client, args->v0.index);
-       }
-
-       return ret;
-}
-
-static struct {
-       int version;
-       int (*func)(struct nouveau_handle *, void *, u32);
-}
-nvkm_ioctl_v0[] = {
-       { 0x00, nvkm_ioctl_nop },
-       { 0x00, nvkm_ioctl_sclass },
-       { 0x00, nvkm_ioctl_new },
-       { 0x00, nvkm_ioctl_del },
-       { 0x00, nvkm_ioctl_mthd },
-       { 0x00, nvkm_ioctl_rd },
-       { 0x00, nvkm_ioctl_wr },
-       { 0x00, nvkm_ioctl_map },
-       { 0x00, nvkm_ioctl_unmap },
-       { 0x00, nvkm_ioctl_ntfy_new },
-       { 0x00, nvkm_ioctl_ntfy_del },
-       { 0x00, nvkm_ioctl_ntfy_get },
-       { 0x00, nvkm_ioctl_ntfy_put },
-};
-
-static int
-nvkm_ioctl_path(struct nouveau_handle *parent, u32 type, u32 nr,
-                 u32 *path, void *data, u32 size,
-                 u8 owner, u8 *route, u64 *token)
-{
-       struct nouveau_handle *handle = parent;
-       struct nouveau_namedb *namedb;
-       struct nouveau_object *object;
-       int ret;
-
-       while ((object = parent->object), nr--) {
-               nv_ioctl(object, "path 0x%08x\n", path[nr]);
-               if (!nv_iclass(object, NV_PARENT_CLASS)) {
-                       nv_debug(object, "cannot have children (path)\n");
-                       return -EINVAL;
-               }
-
-               if (!(namedb = (void *)nv_pclass(object, NV_NAMEDB_CLASS)) ||
-                   !(handle = nouveau_namedb_get(namedb, path[nr]))) {
-                       nv_debug(object, "handle 0x%08x not found\n", path[nr]);
-                       return -ENOENT;
-               }
-               nouveau_namedb_put(handle);
-               parent = handle;
-       }
-
-       if (owner != NVIF_IOCTL_V0_OWNER_ANY &&
-           owner != handle->route) {
-               nv_ioctl(object, "object route != owner\n");
-               return -EACCES;
-       }
-       *route = handle->route;
-       *token = handle->token;
-
-       if (ret = -EINVAL, type < ARRAY_SIZE(nvkm_ioctl_v0)) {
-               if (nvkm_ioctl_v0[type].version == 0) {
-                       ret = nvkm_ioctl_v0[type].func(handle, data, size);
-               }
-       }
-
-       return ret;
-}
-
-int
-nvkm_ioctl(struct nouveau_client *client, bool supervisor,
-          void *data, u32 size, void **hack)
-{
-       union {
-               struct nvif_ioctl_v0 v0;
-       } *args = data;
-       int ret;
-
-       client->super = supervisor;
-       nv_ioctl(client, "size %d\n", size);
-
-       if (nvif_unpack(args->v0, 0, 0, true)) {
-               nv_ioctl(client, "vers %d type %02x path %d owner %02x\n",
-                        args->v0.version, args->v0.type, args->v0.path_nr,
-                        args->v0.owner);
-               ret = nvkm_ioctl_path(client->root, args->v0.type,
-                                     args->v0.path_nr, args->v0.path,
-                                     data, size, args->v0.owner,
-                                    &args->v0.route, &args->v0.token);
-       }
-
-       nv_ioctl(client, "return %d\n", ret);
-       if (hack) {
-               *hack = client->data;
-               client->data = NULL;
-       }
-       client->super = false;
-       return ret;
-}
diff --git a/drivers/gpu/drm/nouveau/core/core/mm.c b/drivers/gpu/drm/nouveau/core/core/mm.c
deleted file mode 100644 (file)
index b4f5db6..0000000
+++ /dev/null
@@ -1,303 +0,0 @@
-/*
- * Copyright 2012 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 "core/os.h"
-#include "core/mm.h"
-
-#define node(root, dir) ((root)->nl_entry.dir == &mm->nodes) ? NULL : \
-       list_entry((root)->nl_entry.dir, struct nouveau_mm_node, nl_entry)
-
-static void
-nouveau_mm_dump(struct nouveau_mm *mm, const char *header)
-{
-       struct nouveau_mm_node *node;
-
-       printk(KERN_ERR "nouveau: %s\n", header);
-       printk(KERN_ERR "nouveau: node list:\n");
-       list_for_each_entry(node, &mm->nodes, nl_entry) {
-               printk(KERN_ERR "nouveau: \t%08x %08x %d\n",
-                      node->offset, node->length, node->type);
-       }
-       printk(KERN_ERR "nouveau: free list:\n");
-       list_for_each_entry(node, &mm->free, fl_entry) {
-               printk(KERN_ERR "nouveau: \t%08x %08x %d\n",
-                      node->offset, node->length, node->type);
-       }
-}
-
-void
-nouveau_mm_free(struct nouveau_mm *mm, struct nouveau_mm_node **pthis)
-{
-       struct nouveau_mm_node *this = *pthis;
-
-       if (this) {
-               struct nouveau_mm_node *prev = node(this, prev);
-               struct nouveau_mm_node *next = node(this, next);
-
-               if (prev && prev->type == NVKM_MM_TYPE_NONE) {
-                       prev->length += this->length;
-                       list_del(&this->nl_entry);
-                       kfree(this); this = prev;
-               }
-
-               if (next && next->type == NVKM_MM_TYPE_NONE) {
-                       next->offset  = this->offset;
-                       next->length += this->length;
-                       if (this->type == NVKM_MM_TYPE_NONE)
-                               list_del(&this->fl_entry);
-                       list_del(&this->nl_entry);
-                       kfree(this); this = NULL;
-               }
-
-               if (this && this->type != NVKM_MM_TYPE_NONE) {
-                       list_for_each_entry(prev, &mm->free, fl_entry) {
-                               if (this->offset < prev->offset)
-                                       break;
-                       }
-
-                       list_add_tail(&this->fl_entry, &prev->fl_entry);
-                       this->type = NVKM_MM_TYPE_NONE;
-               }
-       }
-
-       *pthis = NULL;
-}
-
-static struct nouveau_mm_node *
-region_head(struct nouveau_mm *mm, struct nouveau_mm_node *a, u32 size)
-{
-       struct nouveau_mm_node *b;
-
-       if (a->length == size)
-               return a;
-
-       b = kmalloc(sizeof(*b), GFP_KERNEL);
-       if (unlikely(b == NULL))
-               return NULL;
-
-       b->offset = a->offset;
-       b->length = size;
-       b->heap   = a->heap;
-       b->type   = a->type;
-       a->offset += size;
-       a->length -= size;
-       list_add_tail(&b->nl_entry, &a->nl_entry);
-       if (b->type == NVKM_MM_TYPE_NONE)
-               list_add_tail(&b->fl_entry, &a->fl_entry);
-       return b;
-}
-
-int
-nouveau_mm_head(struct nouveau_mm *mm, u8 heap, u8 type, u32 size_max,
-               u32 size_min, u32 align, struct nouveau_mm_node **pnode)
-{
-       struct nouveau_mm_node *prev, *this, *next;
-       u32 mask = align - 1;
-       u32 splitoff;
-       u32 s, e;
-
-       BUG_ON(type == NVKM_MM_TYPE_NONE || type == NVKM_MM_TYPE_HOLE);
-
-       list_for_each_entry(this, &mm->free, fl_entry) {
-               if (unlikely(heap != NVKM_MM_HEAP_ANY)) {
-                       if (this->heap != heap)
-                               continue;
-               }
-               e = this->offset + this->length;
-               s = this->offset;
-
-               prev = node(this, prev);
-               if (prev && prev->type != type)
-                       s = roundup(s, mm->block_size);
-
-               next = node(this, next);
-               if (next && next->type != type)
-                       e = rounddown(e, mm->block_size);
-
-               s  = (s + mask) & ~mask;
-               e &= ~mask;
-               if (s > e || e - s < size_min)
-                       continue;
-
-               splitoff = s - this->offset;
-               if (splitoff && !region_head(mm, this, splitoff))
-                       return -ENOMEM;
-
-               this = region_head(mm, this, min(size_max, e - s));
-               if (!this)
-                       return -ENOMEM;
-
-               this->type = type;
-               list_del(&this->fl_entry);
-               *pnode = this;
-               return 0;
-       }
-
-       return -ENOSPC;
-}
-
-static struct nouveau_mm_node *
-region_tail(struct nouveau_mm *mm, struct nouveau_mm_node *a, u32 size)
-{
-       struct nouveau_mm_node *b;
-
-       if (a->length == size)
-               return a;
-
-       b = kmalloc(sizeof(*b), GFP_KERNEL);
-       if (unlikely(b == NULL))
-               return NULL;
-
-       a->length -= size;
-       b->offset  = a->offset + a->length;
-       b->length  = size;
-       b->heap    = a->heap;
-       b->type    = a->type;
-
-       list_add(&b->nl_entry, &a->nl_entry);
-       if (b->type == NVKM_MM_TYPE_NONE)
-               list_add(&b->fl_entry, &a->fl_entry);
-       return b;
-}
-
-int
-nouveau_mm_tail(struct nouveau_mm *mm, u8 heap, u8 type, u32 size_max,
-               u32 size_min, u32 align, struct nouveau_mm_node **pnode)
-{
-       struct nouveau_mm_node *prev, *this, *next;
-       u32 mask = align - 1;
-
-       BUG_ON(type == NVKM_MM_TYPE_NONE || type == NVKM_MM_TYPE_HOLE);
-
-       list_for_each_entry_reverse(this, &mm->free, fl_entry) {
-               u32 e = this->offset + this->length;
-               u32 s = this->offset;
-               u32 c = 0, a;
-               if (unlikely(heap != NVKM_MM_HEAP_ANY)) {
-                       if (this->heap != heap)
-                               continue;
-               }
-
-               prev = node(this, prev);
-               if (prev && prev->type != type)
-                       s = roundup(s, mm->block_size);
-
-               next = node(this, next);
-               if (next && next->type != type) {
-                       e = rounddown(e, mm->block_size);
-                       c = next->offset - e;
-               }
-
-               s = (s + mask) & ~mask;
-               a = e - s;
-               if (s > e || a < size_min)
-                       continue;
-
-               a  = min(a, size_max);
-               s  = (e - a) & ~mask;
-               c += (e - s) - a;
-
-               if (c && !region_tail(mm, this, c))
-                       return -ENOMEM;
-
-               this = region_tail(mm, this, a);
-               if (!this)
-                       return -ENOMEM;
-
-               this->type = type;
-               list_del(&this->fl_entry);
-               *pnode = this;
-               return 0;
-       }
-
-       return -ENOSPC;
-}
-
-int
-nouveau_mm_init(struct nouveau_mm *mm, u32 offset, u32 length, u32 block)
-{
-       struct nouveau_mm_node *node, *prev;
-       u32 next;
-
-       if (nouveau_mm_initialised(mm)) {
-               prev = list_last_entry(&mm->nodes, typeof(*node), nl_entry);
-               next = prev->offset + prev->length;
-               if (next != offset) {
-                       BUG_ON(next > offset);
-                       if (!(node = kzalloc(sizeof(*node), GFP_KERNEL)))
-                               return -ENOMEM;
-                       node->type   = NVKM_MM_TYPE_HOLE;
-                       node->offset = next;
-                       node->length = offset - next;
-                       list_add_tail(&node->nl_entry, &mm->nodes);
-               }
-               BUG_ON(block != mm->block_size);
-       } else {
-               INIT_LIST_HEAD(&mm->nodes);
-               INIT_LIST_HEAD(&mm->free);
-               mm->block_size = block;
-               mm->heap_nodes = 0;
-       }
-
-       node = kzalloc(sizeof(*node), GFP_KERNEL);
-       if (!node)
-               return -ENOMEM;
-
-       if (length) {
-               node->offset  = roundup(offset, mm->block_size);
-               node->length  = rounddown(offset + length, mm->block_size);
-               node->length -= node->offset;
-       }
-
-       list_add_tail(&node->nl_entry, &mm->nodes);
-       list_add_tail(&node->fl_entry, &mm->free);
-       node->heap = ++mm->heap_nodes;
-       return 0;
-}
-
-int
-nouveau_mm_fini(struct nouveau_mm *mm)
-{
-       struct nouveau_mm_node *node, *temp;
-       int nodes = 0;
-
-       if (!nouveau_mm_initialised(mm))
-               return 0;
-
-       list_for_each_entry(node, &mm->nodes, nl_entry) {
-               if (node->type != NVKM_MM_TYPE_HOLE) {
-                       if (++nodes > mm->heap_nodes) {
-                               nouveau_mm_dump(mm, "mm not clean!");
-                               return -EBUSY;
-                       }
-               }
-       }
-
-       list_for_each_entry_safe(node, temp, &mm->nodes, nl_entry) {
-               list_del(&node->nl_entry);
-               kfree(node);
-       }
-       mm->heap_nodes = 0;
-       return 0;
-}
diff --git a/drivers/gpu/drm/nouveau/core/core/namedb.c b/drivers/gpu/drm/nouveau/core/core/namedb.c
deleted file mode 100644 (file)
index 0594a59..0000000
+++ /dev/null
@@ -1,203 +0,0 @@
-/*
- * Copyright 2012 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 <core/object.h>
-#include <core/namedb.h>
-#include <core/handle.h>
-#include <core/gpuobj.h>
-
-static struct nouveau_handle *
-nouveau_namedb_lookup(struct nouveau_namedb *namedb, u32 name)
-{
-       struct nouveau_handle *handle;
-
-       list_for_each_entry(handle, &namedb->list, node) {
-               if (handle->name == name)
-                       return handle;
-       }
-
-       return NULL;
-}
-
-static struct nouveau_handle *
-nouveau_namedb_lookup_class(struct nouveau_namedb *namedb, u16 oclass)
-{
-       struct nouveau_handle *handle;
-
-       list_for_each_entry(handle, &namedb->list, node) {
-               if (nv_mclass(handle->object) == oclass)
-                       return handle;
-       }
-
-       return NULL;
-}
-
-static struct nouveau_handle *
-nouveau_namedb_lookup_vinst(struct nouveau_namedb *namedb, u64 vinst)
-{
-       struct nouveau_handle *handle;
-
-       list_for_each_entry(handle, &namedb->list, node) {
-               if (nv_iclass(handle->object, NV_GPUOBJ_CLASS)) {
-                       if (nv_gpuobj(handle->object)->addr == vinst)
-                               return handle;
-               }
-       }
-
-       return NULL;
-}
-
-static struct nouveau_handle *
-nouveau_namedb_lookup_cinst(struct nouveau_namedb *namedb, u32 cinst)
-{
-       struct nouveau_handle *handle;
-
-       list_for_each_entry(handle, &namedb->list, node) {
-               if (nv_iclass(handle->object, NV_GPUOBJ_CLASS)) {
-                       if (nv_gpuobj(handle->object)->node &&
-                           nv_gpuobj(handle->object)->node->offset == cinst)
-                               return handle;
-               }
-       }
-
-       return NULL;
-}
-
-int
-nouveau_namedb_insert(struct nouveau_namedb *namedb, u32 name,
-                     struct nouveau_object *object,
-                     struct nouveau_handle *handle)
-{
-       int ret = -EEXIST;
-       write_lock_irq(&namedb->lock);
-       if (!nouveau_namedb_lookup(namedb, name)) {
-               nouveau_object_ref(object, &handle->object);
-               handle->namedb = namedb;
-               list_add(&handle->node, &namedb->list);
-               ret = 0;
-       }
-       write_unlock_irq(&namedb->lock);
-       return ret;
-}
-
-void
-nouveau_namedb_remove(struct nouveau_handle *handle)
-{
-       struct nouveau_namedb *namedb = handle->namedb;
-       struct nouveau_object *object = handle->object;
-       write_lock_irq(&namedb->lock);
-       list_del(&handle->node);
-       write_unlock_irq(&namedb->lock);
-       nouveau_object_ref(NULL, &object);
-}
-
-struct nouveau_handle *
-nouveau_namedb_get(struct nouveau_namedb *namedb, u32 name)
-{
-       struct nouveau_handle *handle;
-       read_lock(&namedb->lock);
-       handle = nouveau_namedb_lookup(namedb, name);
-       if (handle == NULL)
-               read_unlock(&namedb->lock);
-       return handle;
-}
-
-struct nouveau_handle *
-nouveau_namedb_get_class(struct nouveau_namedb *namedb, u16 oclass)
-{
-       struct nouveau_handle *handle;
-       read_lock(&namedb->lock);
-       handle = nouveau_namedb_lookup_class(namedb, oclass);
-       if (handle == NULL)
-               read_unlock(&namedb->lock);
-       return handle;
-}
-
-struct nouveau_handle *
-nouveau_namedb_get_vinst(struct nouveau_namedb *namedb, u64 vinst)
-{
-       struct nouveau_handle *handle;
-       read_lock(&namedb->lock);
-       handle = nouveau_namedb_lookup_vinst(namedb, vinst);
-       if (handle == NULL)
-               read_unlock(&namedb->lock);
-       return handle;
-}
-
-struct nouveau_handle *
-nouveau_namedb_get_cinst(struct nouveau_namedb *namedb, u32 cinst)
-{
-       struct nouveau_handle *handle;
-       read_lock(&namedb->lock);
-       handle = nouveau_namedb_lookup_cinst(namedb, cinst);
-       if (handle == NULL)
-               read_unlock(&namedb->lock);
-       return handle;
-}
-
-void
-nouveau_namedb_put(struct nouveau_handle *handle)
-{
-       if (handle)
-               read_unlock(&handle->namedb->lock);
-}
-
-int
-nouveau_namedb_create_(struct nouveau_object *parent,
-                      struct nouveau_object *engine,
-                      struct nouveau_oclass *oclass, u32 pclass,
-                      struct nouveau_oclass *sclass, u64 engcls,
-                      int length, void **pobject)
-{
-       struct nouveau_namedb *namedb;
-       int ret;
-
-       ret = nouveau_parent_create_(parent, engine, oclass, pclass |
-                                    NV_NAMEDB_CLASS, sclass, engcls,
-                                    length, pobject);
-       namedb = *pobject;
-       if (ret)
-               return ret;
-
-       rwlock_init(&namedb->lock);
-       INIT_LIST_HEAD(&namedb->list);
-       return 0;
-}
-
-int
-_nouveau_namedb_ctor(struct nouveau_object *parent,
-                    struct nouveau_object *engine,
-                    struct nouveau_oclass *oclass, void *data, u32 size,
-                    struct nouveau_object **pobject)
-{
-       struct nouveau_namedb *object;
-       int ret;
-
-       ret = nouveau_namedb_create(parent, engine, oclass, 0, NULL, 0, &object);
-       *pobject = nv_object(object);
-       if (ret)
-               return ret;
-
-       return 0;
-}
diff --git a/drivers/gpu/drm/nouveau/core/core/notify.c b/drivers/gpu/drm/nouveau/core/core/notify.c
deleted file mode 100644 (file)
index 839a325..0000000
+++ /dev/null
@@ -1,168 +0,0 @@
-/*
- * Copyright 2014 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 <bskeggs@redhat.com>
- */
-
-#include <core/client.h>
-#include <core/event.h>
-#include <core/notify.h>
-
-#include <nvif/unpack.h>
-#include <nvif/event.h>
-
-static inline void
-nvkm_notify_put_locked(struct nvkm_notify *notify)
-{
-       if (notify->block++ == 0)
-               nvkm_event_put(notify->event, notify->types, notify->index);
-}
-
-void
-nvkm_notify_put(struct nvkm_notify *notify)
-{
-       struct nvkm_event *event = notify->event;
-       unsigned long flags;
-       if (likely(event) &&
-           test_and_clear_bit(NVKM_NOTIFY_USER, &notify->flags)) {
-               spin_lock_irqsave(&event->refs_lock, flags);
-               nvkm_notify_put_locked(notify);
-               spin_unlock_irqrestore(&event->refs_lock, flags);
-               if (test_bit(NVKM_NOTIFY_WORK, &notify->flags))
-                       flush_work(&notify->work);
-       }
-}
-
-static inline void
-nvkm_notify_get_locked(struct nvkm_notify *notify)
-{
-       if (--notify->block == 0)
-               nvkm_event_get(notify->event, notify->types, notify->index);
-}
-
-void
-nvkm_notify_get(struct nvkm_notify *notify)
-{
-       struct nvkm_event *event = notify->event;
-       unsigned long flags;
-       if (likely(event) &&
-           !test_and_set_bit(NVKM_NOTIFY_USER, &notify->flags)) {
-               spin_lock_irqsave(&event->refs_lock, flags);
-               nvkm_notify_get_locked(notify);
-               spin_unlock_irqrestore(&event->refs_lock, flags);
-       }
-}
-
-static inline void
-nvkm_notify_func(struct nvkm_notify *notify)
-{
-       struct nvkm_event *event = notify->event;
-       int ret = notify->func(notify);
-       unsigned long flags;
-       if ((ret == NVKM_NOTIFY_KEEP) ||
-           !test_and_clear_bit(NVKM_NOTIFY_USER, &notify->flags)) {
-               spin_lock_irqsave(&event->refs_lock, flags);
-               nvkm_notify_get_locked(notify);
-               spin_unlock_irqrestore(&event->refs_lock, flags);
-       }
-}
-
-static void
-nvkm_notify_work(struct work_struct *work)
-{
-       struct nvkm_notify *notify = container_of(work, typeof(*notify), work);
-       nvkm_notify_func(notify);
-}
-
-void
-nvkm_notify_send(struct nvkm_notify *notify, void *data, u32 size)
-{
-       struct nvkm_event *event = notify->event;
-       unsigned long flags;
-
-       assert_spin_locked(&event->list_lock);
-       BUG_ON(size != notify->size);
-
-       spin_lock_irqsave(&event->refs_lock, flags);
-       if (notify->block) {
-               spin_unlock_irqrestore(&event->refs_lock, flags);
-               return;
-       }
-       nvkm_notify_put_locked(notify);
-       spin_unlock_irqrestore(&event->refs_lock, flags);
-
-       if (test_bit(NVKM_NOTIFY_WORK, &notify->flags)) {
-               memcpy((void *)notify->data, data, size);
-               schedule_work(&notify->work);
-       } else {
-               notify->data = data;
-               nvkm_notify_func(notify);
-               notify->data = NULL;
-       }
-}
-
-void
-nvkm_notify_fini(struct nvkm_notify *notify)
-{
-       unsigned long flags;
-       if (notify->event) {
-               nvkm_notify_put(notify);
-               spin_lock_irqsave(&notify->event->list_lock, flags);
-               list_del(&notify->head);
-               spin_unlock_irqrestore(&notify->event->list_lock, flags);
-               kfree((void *)notify->data);
-               notify->event = NULL;
-       }
-}
-
-int
-nvkm_notify_init(struct nouveau_object *object, struct nvkm_event *event,
-                int (*func)(struct nvkm_notify *), bool work,
-                void *data, u32 size, u32 reply,
-                struct nvkm_notify *notify)
-{
-       unsigned long flags;
-       int ret = -ENODEV;
-       if ((notify->event = event), event->refs) {
-               ret = event->func->ctor(object, data, size, notify);
-               if (ret == 0 && (ret = -EINVAL, notify->size == reply)) {
-                       notify->flags = 0;
-                       notify->block = 1;
-                       notify->func = func;
-                       notify->data = NULL;
-                       if (ret = 0, work) {
-                               INIT_WORK(&notify->work, nvkm_notify_work);
-                               set_bit(NVKM_NOTIFY_WORK, &notify->flags);
-                               notify->data = kmalloc(reply, GFP_KERNEL);
-                               if (!notify->data)
-                                       ret = -ENOMEM;
-                       }
-               }
-               if (ret == 0) {
-                       spin_lock_irqsave(&event->list_lock, flags);
-                       list_add_tail(&notify->head, &event->list);
-                       spin_unlock_irqrestore(&event->list_lock, flags);
-               }
-       }
-       if (ret)
-               notify->event = NULL;
-       return ret;
-}
diff --git a/drivers/gpu/drm/nouveau/core/core/object.c b/drivers/gpu/drm/nouveau/core/core/object.c
deleted file mode 100644 (file)
index b086305..0000000
+++ /dev/null
@@ -1,334 +0,0 @@
-/*
- * Copyright 2012 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 <core/object.h>
-#include <core/engine.h>
-
-#ifdef NOUVEAU_OBJECT_MAGIC
-static struct list_head _objlist = LIST_HEAD_INIT(_objlist);
-static DEFINE_SPINLOCK(_objlist_lock);
-#endif
-
-int
-nouveau_object_create_(struct nouveau_object *parent,
-                      struct nouveau_object *engine,
-                      struct nouveau_oclass *oclass, u32 pclass,
-                      int size, void **pobject)
-{
-       struct nouveau_object *object;
-
-       object = *pobject = kzalloc(size, GFP_KERNEL);
-       if (!object)
-               return -ENOMEM;
-
-       nouveau_object_ref(parent, &object->parent);
-       nouveau_object_ref(engine, &object->engine);
-       object->oclass = oclass;
-       object->oclass->handle |= pclass;
-       atomic_set(&object->refcount, 1);
-       atomic_set(&object->usecount, 0);
-
-#ifdef NOUVEAU_OBJECT_MAGIC
-       object->_magic = NOUVEAU_OBJECT_MAGIC;
-       spin_lock(&_objlist_lock);
-       list_add(&object->list, &_objlist);
-       spin_unlock(&_objlist_lock);
-#endif
-       return 0;
-}
-
-int
-_nouveau_object_ctor(struct nouveau_object *parent,
-                    struct nouveau_object *engine,
-                    struct nouveau_oclass *oclass, void *data, u32 size,
-                    struct nouveau_object **pobject)
-{
-       if (size != 0)
-               return -ENOSYS;
-       return nouveau_object_create(parent, engine, oclass, 0, pobject);
-}
-
-void
-nouveau_object_destroy(struct nouveau_object *object)
-{
-#ifdef NOUVEAU_OBJECT_MAGIC
-       spin_lock(&_objlist_lock);
-       list_del(&object->list);
-       spin_unlock(&_objlist_lock);
-#endif
-       nouveau_object_ref(NULL, &object->engine);
-       nouveau_object_ref(NULL, &object->parent);
-       kfree(object);
-}
-
-int
-nouveau_object_init(struct nouveau_object *object)
-{
-       return 0;
-}
-
-int
-nouveau_object_fini(struct nouveau_object *object, bool suspend)
-{
-       return 0;
-}
-
-struct nouveau_ofuncs
-nouveau_object_ofuncs = {
-       .ctor = _nouveau_object_ctor,
-       .dtor = nouveau_object_destroy,
-       .init = nouveau_object_init,
-       .fini = nouveau_object_fini,
-};
-
-int
-nouveau_object_ctor(struct nouveau_object *parent,
-                   struct nouveau_object *engine,
-                   struct nouveau_oclass *oclass, void *data, u32 size,
-                   struct nouveau_object **pobject)
-{
-       struct nouveau_ofuncs *ofuncs = oclass->ofuncs;
-       struct nouveau_object *object = NULL;
-       int ret;
-
-       ret = ofuncs->ctor(parent, engine, oclass, data, size, &object);
-       *pobject = object;
-       if (ret < 0) {
-               if (ret != -ENODEV) {
-                       nv_error(parent, "failed to create 0x%08x, %d\n",
-                                oclass->handle, ret);
-               }
-
-               if (object) {
-                       ofuncs->dtor(object);
-                       *pobject = NULL;
-               }
-
-               return ret;
-       }
-
-       if (ret == 0) {
-               nv_trace(object, "created\n");
-               atomic_set(&object->refcount, 1);
-       }
-
-       return 0;
-}
-
-static void
-nouveau_object_dtor(struct nouveau_object *object)
-{
-       nv_trace(object, "destroying\n");
-       nv_ofuncs(object)->dtor(object);
-}
-
-void
-nouveau_object_ref(struct nouveau_object *obj, struct nouveau_object **ref)
-{
-       if (obj) {
-               atomic_inc(&obj->refcount);
-               nv_trace(obj, "inc() == %d\n", atomic_read(&obj->refcount));
-       }
-
-       if (*ref) {
-               int dead = atomic_dec_and_test(&(*ref)->refcount);
-               nv_trace(*ref, "dec() == %d\n", atomic_read(&(*ref)->refcount));
-               if (dead)
-                       nouveau_object_dtor(*ref);
-       }
-
-       *ref = obj;
-}
-
-int
-nouveau_object_inc(struct nouveau_object *object)
-{
-       int ref = atomic_add_return(1, &object->usecount);
-       int ret;
-
-       nv_trace(object, "use(+1) == %d\n", atomic_read(&object->usecount));
-       if (ref != 1)
-               return 0;
-
-       nv_trace(object, "initialising...\n");
-       if (object->parent) {
-               ret = nouveau_object_inc(object->parent);
-               if (ret) {
-                       nv_error(object, "parent failed, %d\n", ret);
-                       goto fail_parent;
-               }
-       }
-
-       if (object->engine) {
-               mutex_lock(&nv_subdev(object->engine)->mutex);
-               ret = nouveau_object_inc(object->engine);
-               mutex_unlock(&nv_subdev(object->engine)->mutex);
-               if (ret) {
-                       nv_error(object, "engine failed, %d\n", ret);
-                       goto fail_engine;
-               }
-       }
-
-       ret = nv_ofuncs(object)->init(object);
-       atomic_set(&object->usecount, 1);
-       if (ret) {
-               nv_error(object, "init failed, %d\n", ret);
-               goto fail_self;
-       }
-
-       nv_trace(object, "initialised\n");
-       return 0;
-
-fail_self:
-       if (object->engine) {
-               mutex_lock(&nv_subdev(object->engine)->mutex);
-               nouveau_object_dec(object->engine, false);
-               mutex_unlock(&nv_subdev(object->engine)->mutex);
-       }
-fail_engine:
-       if (object->parent)
-                nouveau_object_dec(object->parent, false);
-fail_parent:
-       atomic_dec(&object->usecount);
-       return ret;
-}
-
-static int
-nouveau_object_decf(struct nouveau_object *object)
-{
-       int ret;
-
-       nv_trace(object, "stopping...\n");
-
-       ret = nv_ofuncs(object)->fini(object, false);
-       atomic_set(&object->usecount, 0);
-       if (ret)
-               nv_warn(object, "failed fini, %d\n", ret);
-
-       if (object->engine) {
-               mutex_lock(&nv_subdev(object->engine)->mutex);
-               nouveau_object_dec(object->engine, false);
-               mutex_unlock(&nv_subdev(object->engine)->mutex);
-       }
-
-       if (object->parent)
-               nouveau_object_dec(object->parent, false);
-
-       nv_trace(object, "stopped\n");
-       return 0;
-}
-
-static int
-nouveau_object_decs(struct nouveau_object *object)
-{
-       int ret, rret;
-
-       nv_trace(object, "suspending...\n");
-
-       ret = nv_ofuncs(object)->fini(object, true);
-       atomic_set(&object->usecount, 0);
-       if (ret) {
-               nv_error(object, "failed suspend, %d\n", ret);
-               return ret;
-       }
-
-       if (object->engine) {
-               mutex_lock(&nv_subdev(object->engine)->mutex);
-               ret = nouveau_object_dec(object->engine, true);
-               mutex_unlock(&nv_subdev(object->engine)->mutex);
-               if (ret) {
-                       nv_warn(object, "engine failed suspend, %d\n", ret);
-                       goto fail_engine;
-               }
-       }
-
-       if (object->parent) {
-               ret = nouveau_object_dec(object->parent, true);
-               if (ret) {
-                       nv_warn(object, "parent failed suspend, %d\n", ret);
-                       goto fail_parent;
-               }
-       }
-
-       nv_trace(object, "suspended\n");
-       return 0;
-
-fail_parent:
-       if (object->engine) {
-               mutex_lock(&nv_subdev(object->engine)->mutex);
-               rret = nouveau_object_inc(object->engine);
-               mutex_unlock(&nv_subdev(object->engine)->mutex);
-               if (rret)
-                       nv_fatal(object, "engine failed to reinit, %d\n", rret);
-       }
-
-fail_engine:
-       rret = nv_ofuncs(object)->init(object);
-       if (rret)
-               nv_fatal(object, "failed to reinit, %d\n", rret);
-
-       return ret;
-}
-
-int
-nouveau_object_dec(struct nouveau_object *object, bool suspend)
-{
-       int ref = atomic_add_return(-1, &object->usecount);
-       int ret;
-
-       nv_trace(object, "use(-1) == %d\n", atomic_read(&object->usecount));
-
-       if (ref == 0) {
-               if (suspend)
-                       ret = nouveau_object_decs(object);
-               else
-                       ret = nouveau_object_decf(object);
-
-               if (ret) {
-                       atomic_inc(&object->usecount);
-                       return ret;
-               }
-       }
-
-       return 0;
-}
-
-void
-nouveau_object_debug(void)
-{
-#ifdef NOUVEAU_OBJECT_MAGIC
-       struct nouveau_object *object;
-       if (!list_empty(&_objlist)) {
-               nv_fatal(NULL, "*******************************************\n");
-               nv_fatal(NULL, "* AIIIII! object(s) still exist!!!\n");
-               nv_fatal(NULL, "*******************************************\n");
-               list_for_each_entry(object, &_objlist, list) {
-                       nv_fatal(object, "%p/%p/%d/%d\n",
-                                object->parent, object->engine,
-                                atomic_read(&object->refcount),
-                                atomic_read(&object->usecount));
-               }
-       }
-#endif
-}
diff --git a/drivers/gpu/drm/nouveau/core/core/option.c b/drivers/gpu/drm/nouveau/core/core/option.c
deleted file mode 100644 (file)
index 9f6fcc5..0000000
+++ /dev/null
@@ -1,122 +0,0 @@
-/*
- * Copyright 2012 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 <core/option.h>
-#include <core/debug.h>
-
-const char *
-nouveau_stropt(const char *optstr, const char *opt, int *arglen)
-{
-       while (optstr && *optstr != '\0') {
-               int len = strcspn(optstr, ",=");
-               switch (optstr[len]) {
-               case '=':
-                       if (!strncasecmpz(optstr, opt, len)) {
-                               optstr += len + 1;
-                               *arglen = strcspn(optstr, ",=");
-                               return *arglen ? optstr : NULL;
-                       }
-                       optstr++;
-                       break;
-               case ',':
-                       optstr++;
-                       break;
-               default:
-                       break;
-               }
-               optstr += len;
-       }
-
-       return NULL;
-}
-
-bool
-nouveau_boolopt(const char *optstr, const char *opt, bool value)
-{
-       int arglen;
-
-       optstr = nouveau_stropt(optstr, opt, &arglen);
-       if (optstr) {
-               if (!strncasecmpz(optstr, "0", arglen) ||
-                   !strncasecmpz(optstr, "no", arglen) ||
-                   !strncasecmpz(optstr, "off", arglen) ||
-                   !strncasecmpz(optstr, "false", arglen))
-                       value = false;
-               else
-               if (!strncasecmpz(optstr, "1", arglen) ||
-                   !strncasecmpz(optstr, "yes", arglen) ||
-                   !strncasecmpz(optstr, "on", arglen) ||
-                   !strncasecmpz(optstr, "true", arglen))
-                       value = true;
-       }
-
-       return value;
-}
-
-int
-nouveau_dbgopt(const char *optstr, const char *sub)
-{
-       int mode = 1, level = CONFIG_NOUVEAU_DEBUG_DEFAULT;
-
-       while (optstr) {
-               int len = strcspn(optstr, ",=");
-               switch (optstr[len]) {
-               case '=':
-                       if (strncasecmpz(optstr, sub, len))
-                               mode = 0;
-                       optstr++;
-                       break;
-               default:
-                       if (mode) {
-                               if (!strncasecmpz(optstr, "fatal", len))
-                                       level = NV_DBG_FATAL;
-                               else if (!strncasecmpz(optstr, "error", len))
-                                       level = NV_DBG_ERROR;
-                               else if (!strncasecmpz(optstr, "warn", len))
-                                       level = NV_DBG_WARN;
-                               else if (!strncasecmpz(optstr, "info", len))
-                                       level = NV_DBG_INFO_NORMAL;
-                               else if (!strncasecmpz(optstr, "debug", len))
-                                       level = NV_DBG_DEBUG;
-                               else if (!strncasecmpz(optstr, "trace", len))
-                                       level = NV_DBG_TRACE;
-                               else if (!strncasecmpz(optstr, "paranoia", len))
-                                       level = NV_DBG_PARANOIA;
-                               else if (!strncasecmpz(optstr, "spam", len))
-                                       level = NV_DBG_SPAM;
-                       }
-
-                       if (optstr[len] != '\0') {
-                               optstr++;
-                               mode = 1;
-                               break;
-                       }
-
-                       return level;
-               }
-               optstr += len;
-       }
-
-       return level;
-}
diff --git a/drivers/gpu/drm/nouveau/core/core/parent.c b/drivers/gpu/drm/nouveau/core/core/parent.c
deleted file mode 100644 (file)
index 30a2911..0000000
+++ /dev/null
@@ -1,161 +0,0 @@
-/*
- * Copyright 2012 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 <core/object.h>
-#include <core/parent.h>
-#include <core/client.h>
-
-int
-nouveau_parent_sclass(struct nouveau_object *parent, u16 handle,
-                     struct nouveau_object **pengine,
-                     struct nouveau_oclass **poclass)
-{
-       struct nouveau_sclass *sclass;
-       struct nouveau_engine *engine;
-       struct nouveau_oclass *oclass;
-       u64 mask;
-
-       sclass = nv_parent(parent)->sclass;
-       while (sclass) {
-               if ((sclass->oclass->handle & 0xffff) == handle) {
-                       *pengine = parent->engine;
-                       *poclass = sclass->oclass;
-                       return 0;
-               }
-
-               sclass = sclass->sclass;
-       }
-
-       mask = nv_parent(parent)->engine;
-       while (mask) {
-               int i = __ffs64(mask);
-
-               if (nv_iclass(parent, NV_CLIENT_CLASS))
-                       engine = nv_engine(nv_client(parent)->device);
-               else
-                       engine = nouveau_engine(parent, i);
-
-               if (engine) {
-                       oclass = engine->sclass;
-                       while (oclass->ofuncs) {
-                               if ((oclass->handle & 0xffff) == handle) {
-                                       *pengine = nv_object(engine);
-                                       *poclass = oclass;
-                                       return 0;
-                               }
-                               oclass++;
-                       }
-               }
-
-               mask &= ~(1ULL << i);
-       }
-
-       return -EINVAL;
-}
-
-int
-nouveau_parent_lclass(struct nouveau_object *parent, u32 *lclass, int size)
-{
-       struct nouveau_sclass *sclass;
-       struct nouveau_engine *engine;
-       struct nouveau_oclass *oclass;
-       int nr = -1, i;
-       u64 mask;
-
-       sclass = nv_parent(parent)->sclass;
-       while (sclass) {
-               if (++nr < size)
-                       lclass[nr] = sclass->oclass->handle & 0xffff;
-               sclass = sclass->sclass;
-       }
-
-       mask = nv_parent(parent)->engine;
-       while (i = __ffs64(mask), mask) {
-               engine = nouveau_engine(parent, i);
-               if (engine && (oclass = engine->sclass)) {
-                       while (oclass->ofuncs) {
-                               if (++nr < size)
-                                       lclass[nr] = oclass->handle & 0xffff;
-                               oclass++;
-                       }
-               }
-
-               mask &= ~(1ULL << i);
-       }
-
-       return nr + 1;
-}
-
-int
-nouveau_parent_create_(struct nouveau_object *parent,
-                      struct nouveau_object *engine,
-                      struct nouveau_oclass *oclass, u32 pclass,
-                      struct nouveau_oclass *sclass, u64 engcls,
-                      int size, void **pobject)
-{
-       struct nouveau_parent *object;
-       struct nouveau_sclass *nclass;
-       int ret;
-
-       ret = nouveau_object_create_(parent, engine, oclass, pclass |
-                                    NV_PARENT_CLASS, size, pobject);
-       object = *pobject;
-       if (ret)
-               return ret;
-
-       while (sclass && sclass->ofuncs) {
-               nclass = kzalloc(sizeof(*nclass), GFP_KERNEL);
-               if (!nclass)
-                       return -ENOMEM;
-
-               nclass->sclass = object->sclass;
-               object->sclass = nclass;
-               nclass->engine = engine ? nv_engine(engine) : NULL;
-               nclass->oclass = sclass;
-               sclass++;
-       }
-
-       object->engine = engcls;
-       return 0;
-}
-
-void
-nouveau_parent_destroy(struct nouveau_parent *parent)
-{
-       struct nouveau_sclass *sclass;
-
-       while ((sclass = parent->sclass)) {
-               parent->sclass = sclass->sclass;
-               kfree(sclass);
-       }
-
-       nouveau_object_destroy(&parent->base);
-}
-
-
-void
-_nouveau_parent_dtor(struct nouveau_object *object)
-{
-       nouveau_parent_destroy(nv_parent(object));
-}
diff --git a/drivers/gpu/drm/nouveau/core/core/printk.c b/drivers/gpu/drm/nouveau/core/core/printk.c
deleted file mode 100644 (file)
index 03e0060..0000000
+++ /dev/null
@@ -1,98 +0,0 @@
-/*
- * Copyright 2012 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 <core/object.h>
-#include <core/client.h>
-#include <core/subdev.h>
-#include <core/printk.h>
-
-int nv_info_debug_level = NV_DBG_INFO_NORMAL;
-
-void
-nv_printk_(struct nouveau_object *object, int level, const char *fmt, ...)
-{
-       static const char name[] = { '!', 'E', 'W', ' ', 'D', 'T', 'P', 'S' };
-       const char *pfx;
-       char mfmt[256];
-       va_list args;
-
-       switch (level) {
-       case NV_DBG_FATAL:
-               pfx = KERN_CRIT;
-               break;
-       case NV_DBG_ERROR:
-               pfx = KERN_ERR;
-               break;
-       case NV_DBG_WARN:
-               pfx = KERN_WARNING;
-               break;
-       case NV_DBG_INFO_NORMAL:
-               pfx = KERN_INFO;
-               break;
-       case NV_DBG_DEBUG:
-       case NV_DBG_PARANOIA:
-       case NV_DBG_TRACE:
-       case NV_DBG_SPAM:
-       default:
-               pfx = KERN_DEBUG;
-               break;
-       }
-
-       if (object && !nv_iclass(object, NV_CLIENT_CLASS)) {
-               struct nouveau_object *device = object;
-               struct nouveau_object *subdev = object;
-               char obuf[64], *ofmt = "";
-
-               if (object->engine) {
-                       snprintf(obuf, sizeof(obuf), "[0x%08x][%p]",
-                                nv_hclass(object), object);
-                       ofmt = obuf;
-                       subdev = object->engine;
-                       device = object->engine;
-               }
-
-               if (subdev->parent)
-                       device = subdev->parent;
-
-               if (level > nv_subdev(subdev)->debug)
-                       return;
-
-               snprintf(mfmt, sizeof(mfmt), "%snouveau %c[%8s][%s]%s %s", pfx,
-                        name[level], nv_subdev(subdev)->name,
-                        nv_device(device)->name, ofmt, fmt);
-       } else
-       if (object && nv_iclass(object, NV_CLIENT_CLASS)) {
-               if (level > nv_client(object)->debug)
-                       return;
-
-               snprintf(mfmt, sizeof(mfmt), "%snouveau %c[%8s] %s", pfx,
-                        name[level], nv_client(object)->name, fmt);
-       } else {
-               snprintf(mfmt, sizeof(mfmt), "%snouveau: %s", pfx, fmt);
-       }
-
-       va_start(args, fmt);
-       vprintk(mfmt, args);
-       va_end(args);
-}
diff --git a/drivers/gpu/drm/nouveau/core/core/ramht.c b/drivers/gpu/drm/nouveau/core/core/ramht.c
deleted file mode 100644 (file)
index f3b9bdd..0000000
+++ /dev/null
@@ -1,108 +0,0 @@
-/*
- * Copyright 2012 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.
- */
-
-#include <core/object.h>
-#include <core/ramht.h>
-
-#include <subdev/bar.h>
-
-static u32
-nouveau_ramht_hash(struct nouveau_ramht *ramht, int chid, u32 handle)
-{
-       u32 hash = 0;
-
-       while (handle) {
-               hash ^= (handle & ((1 << ramht->bits) - 1));
-               handle >>= ramht->bits;
-       }
-
-       hash ^= chid << (ramht->bits - 4);
-       hash  = hash << 3;
-       return hash;
-}
-
-int
-nouveau_ramht_insert(struct nouveau_ramht *ramht, int chid,
-                    u32 handle, u32 context)
-{
-       struct nouveau_bar *bar = nouveau_bar(ramht);
-       u32 co, ho;
-
-       co = ho = nouveau_ramht_hash(ramht, chid, handle);
-       do {
-               if (!nv_ro32(ramht, co + 4)) {
-                       nv_wo32(ramht, co + 0, handle);
-                       nv_wo32(ramht, co + 4, context);
-                       if (bar)
-                               bar->flush(bar);
-                       return co;
-               }
-
-               co += 8;
-               if (co >= nv_gpuobj(ramht)->size)
-                       co = 0;
-       } while (co != ho);
-
-       return -ENOMEM;
-}
-
-void
-nouveau_ramht_remove(struct nouveau_ramht *ramht, int cookie)
-{
-       struct nouveau_bar *bar = nouveau_bar(ramht);
-       nv_wo32(ramht, cookie + 0, 0x00000000);
-       nv_wo32(ramht, cookie + 4, 0x00000000);
-       if (bar)
-               bar->flush(bar);
-}
-
-static struct nouveau_oclass
-nouveau_ramht_oclass = {
-       .handle = 0x0000abcd,
-       .ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = NULL,
-               .dtor = _nouveau_gpuobj_dtor,
-               .init = _nouveau_gpuobj_init,
-               .fini = _nouveau_gpuobj_fini,
-               .rd32 = _nouveau_gpuobj_rd32,
-               .wr32 = _nouveau_gpuobj_wr32,
-       },
-};
-
-int
-nouveau_ramht_new(struct nouveau_object *parent, struct nouveau_object *pargpu,
-                 u32 size, u32 align, struct nouveau_ramht **pramht)
-{
-       struct nouveau_ramht *ramht;
-       int ret;
-
-       ret = nouveau_gpuobj_create(parent, parent->engine ?
-                                   parent->engine : parent, /* <nv50 ramht */
-                                   &nouveau_ramht_oclass, 0, pargpu, size,
-                                   align, NVOBJ_FLAG_ZERO_ALLOC, &ramht);
-       *pramht = ramht;
-       if (ret)
-               return ret;
-
-       ramht->bits = order_base_2(nv_gpuobj(ramht)->size >> 3);
-       return 0;
-}
diff --git a/drivers/gpu/drm/nouveau/core/core/subdev.c b/drivers/gpu/drm/nouveau/core/core/subdev.c
deleted file mode 100644 (file)
index 2ea5568..0000000
+++ /dev/null
@@ -1,112 +0,0 @@
-/*
- * Copyright 2012 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 <core/object.h>
-#include <core/subdev.h>
-#include <core/device.h>
-#include <core/option.h>
-
-void
-nouveau_subdev_reset(struct nouveau_object *subdev)
-{
-       nv_trace(subdev, "resetting...\n");
-       nv_ofuncs(subdev)->fini(subdev, false);
-       nv_debug(subdev, "reset\n");
-}
-
-int
-nouveau_subdev_init(struct nouveau_subdev *subdev)
-{
-       int ret = nouveau_object_init(&subdev->base);
-       if (ret)
-               return ret;
-
-       nouveau_subdev_reset(&subdev->base);
-       return 0;
-}
-
-int
-_nouveau_subdev_init(struct nouveau_object *object)
-{
-       return nouveau_subdev_init(nv_subdev(object));
-}
-
-int
-nouveau_subdev_fini(struct nouveau_subdev *subdev, bool suspend)
-{
-       if (subdev->unit) {
-               nv_mask(subdev, 0x000200, subdev->unit, 0x00000000);
-               nv_mask(subdev, 0x000200, subdev->unit, subdev->unit);
-       }
-
-       return nouveau_object_fini(&subdev->base, suspend);
-}
-
-int
-_nouveau_subdev_fini(struct nouveau_object *object, bool suspend)
-{
-       return nouveau_subdev_fini(nv_subdev(object), suspend);
-}
-
-void
-nouveau_subdev_destroy(struct nouveau_subdev *subdev)
-{
-       int subidx = nv_hclass(subdev) & 0xff;
-       nv_device(subdev)->subdev[subidx] = NULL;
-       nouveau_object_destroy(&subdev->base);
-}
-
-void
-_nouveau_subdev_dtor(struct nouveau_object *object)
-{
-       nouveau_subdev_destroy(nv_subdev(object));
-}
-
-int
-nouveau_subdev_create_(struct nouveau_object *parent,
-                      struct nouveau_object *engine,
-                      struct nouveau_oclass *oclass, u32 pclass,
-                      const char *subname, const char *sysname,
-                      int size, void **pobject)
-{
-       struct nouveau_subdev *subdev;
-       int ret;
-
-       ret = nouveau_object_create_(parent, engine, oclass, pclass |
-                                    NV_SUBDEV_CLASS, size, pobject);
-       subdev = *pobject;
-       if (ret)
-               return ret;
-
-       __mutex_init(&subdev->mutex, subname, &oclass->lock_class_key);
-       subdev->name = subname;
-
-       if (parent) {
-               struct nouveau_device *device = nv_device(parent);
-               subdev->debug = nouveau_dbgopt(device->dbgopt, subname);
-               subdev->mmio  = nv_subdev(device)->mmio;
-       }
-
-       return 0;
-}
diff --git a/drivers/gpu/drm/nouveau/core/engine/bsp/nv84.c b/drivers/gpu/drm/nouveau/core/engine/bsp/nv84.c
deleted file mode 100644 (file)
index 1e8e75c..0000000
+++ /dev/null
@@ -1,92 +0,0 @@
-/*
- * Copyright 2012 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, Ilia Mirkin
- */
-
-#include <engine/xtensa.h>
-#include <engine/bsp.h>
-
-/*******************************************************************************
- * BSP object classes
- ******************************************************************************/
-
-static struct nouveau_oclass
-nv84_bsp_sclass[] = {
-       { 0x74b0, &nouveau_object_ofuncs },
-       {},
-};
-
-/*******************************************************************************
- * BSP context
- ******************************************************************************/
-
-static struct nouveau_oclass
-nv84_bsp_cclass = {
-       .handle = NV_ENGCTX(BSP, 0x84),
-       .ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = _nouveau_xtensa_engctx_ctor,
-               .dtor = _nouveau_engctx_dtor,
-               .init = _nouveau_engctx_init,
-               .fini = _nouveau_engctx_fini,
-               .rd32 = _nouveau_engctx_rd32,
-               .wr32 = _nouveau_engctx_wr32,
-       },
-};
-
-/*******************************************************************************
- * BSP engine/subdev functions
- ******************************************************************************/
-
-static int
-nv84_bsp_ctor(struct nouveau_object *parent, struct nouveau_object *engine,
-             struct nouveau_oclass *oclass, void *data, u32 size,
-             struct nouveau_object **pobject)
-{
-       struct nouveau_xtensa *priv;
-       int ret;
-
-       ret = nouveau_xtensa_create(parent, engine, oclass, 0x103000, true,
-                                   "PBSP", "bsp", &priv);
-       *pobject = nv_object(priv);
-       if (ret)
-               return ret;
-
-       nv_subdev(priv)->unit = 0x04008000;
-       nv_engine(priv)->cclass = &nv84_bsp_cclass;
-       nv_engine(priv)->sclass = nv84_bsp_sclass;
-       priv->fifo_val = 0x1111;
-       priv->unkd28 = 0x90044;
-       return 0;
-}
-
-struct nouveau_oclass
-nv84_bsp_oclass = {
-       .handle = NV_ENGINE(BSP, 0x84),
-       .ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nv84_bsp_ctor,
-               .dtor = _nouveau_xtensa_dtor,
-               .init = _nouveau_xtensa_init,
-               .fini = _nouveau_xtensa_fini,
-               .rd32 = _nouveau_xtensa_rd32,
-               .wr32 = _nouveau_xtensa_wr32,
-       },
-};
diff --git a/drivers/gpu/drm/nouveau/core/engine/bsp/nv98.c b/drivers/gpu/drm/nouveau/core/engine/bsp/nv98.c
deleted file mode 100644 (file)
index 6b089e0..0000000
+++ /dev/null
@@ -1,111 +0,0 @@
-/*
- * Copyright 2012 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, Maarten Lankhorst, Ilia Mirkin
- */
-
-#include <engine/falcon.h>
-#include <engine/bsp.h>
-
-struct nv98_bsp_priv {
-       struct nouveau_falcon base;
-};
-
-/*******************************************************************************
- * BSP object classes
- ******************************************************************************/
-
-static struct nouveau_oclass
-nv98_bsp_sclass[] = {
-       { 0x88b1, &nouveau_object_ofuncs },
-       { 0x85b1, &nouveau_object_ofuncs },
-       { 0x86b1, &nouveau_object_ofuncs },
-       {},
-};
-
-/*******************************************************************************
- * PBSP context
- ******************************************************************************/
-
-static struct nouveau_oclass
-nv98_bsp_cclass = {
-       .handle = NV_ENGCTX(BSP, 0x98),
-       .ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = _nouveau_falcon_context_ctor,
-               .dtor = _nouveau_falcon_context_dtor,
-               .init = _nouveau_falcon_context_init,
-               .fini = _nouveau_falcon_context_fini,
-               .rd32 = _nouveau_falcon_context_rd32,
-               .wr32 = _nouveau_falcon_context_wr32,
-       },
-};
-
-/*******************************************************************************
- * PBSP engine/subdev functions
- ******************************************************************************/
-
-static int
-nv98_bsp_init(struct nouveau_object *object)
-{
-       struct nv98_bsp_priv *priv = (void *)object;
-       int ret;
-
-       ret = nouveau_falcon_init(&priv->base);
-       if (ret)
-               return ret;
-
-       nv_wr32(priv, 0x084010, 0x0000ffd2);
-       nv_wr32(priv, 0x08401c, 0x0000fff2);
-       return 0;
-}
-
-static int
-nv98_bsp_ctor(struct nouveau_object *parent, struct nouveau_object *engine,
-             struct nouveau_oclass *oclass, void *data, u32 size,
-             struct nouveau_object **pobject)
-{
-       struct nv98_bsp_priv *priv;
-       int ret;
-
-       ret = nouveau_falcon_create(parent, engine, oclass, 0x084000, true,
-                                   "PBSP", "bsp", &priv);
-       *pobject = nv_object(priv);
-       if (ret)
-               return ret;
-
-       nv_subdev(priv)->unit = 0x04008000;
-       nv_engine(priv)->cclass = &nv98_bsp_cclass;
-       nv_engine(priv)->sclass = nv98_bsp_sclass;
-       return 0;
-}
-
-struct nouveau_oclass
-nv98_bsp_oclass = {
-       .handle = NV_ENGINE(BSP, 0x98),
-       .ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nv98_bsp_ctor,
-               .dtor = _nouveau_falcon_dtor,
-               .init = nv98_bsp_init,
-               .fini = _nouveau_falcon_fini,
-               .rd32 = _nouveau_falcon_rd32,
-               .wr32 = _nouveau_falcon_wr32,
-       },
-};
diff --git a/drivers/gpu/drm/nouveau/core/engine/bsp/nvc0.c b/drivers/gpu/drm/nouveau/core/engine/bsp/nvc0.c
deleted file mode 100644 (file)
index ce860de..0000000
+++ /dev/null
@@ -1,110 +0,0 @@
-/*
- * Copyright 2012 Maarten Lankhorst
- *
- * 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: Maarten Lankhorst
- */
-
-#include <engine/falcon.h>
-#include <engine/bsp.h>
-
-struct nvc0_bsp_priv {
-       struct nouveau_falcon base;
-};
-
-/*******************************************************************************
- * BSP object classes
- ******************************************************************************/
-
-static struct nouveau_oclass
-nvc0_bsp_sclass[] = {
-       { 0x90b1, &nouveau_object_ofuncs },
-       {},
-};
-
-/*******************************************************************************
- * PBSP context
- ******************************************************************************/
-
-static struct nouveau_oclass
-nvc0_bsp_cclass = {
-       .handle = NV_ENGCTX(BSP, 0xc0),
-       .ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = _nouveau_falcon_context_ctor,
-               .dtor = _nouveau_falcon_context_dtor,
-               .init = _nouveau_falcon_context_init,
-               .fini = _nouveau_falcon_context_fini,
-               .rd32 = _nouveau_falcon_context_rd32,
-               .wr32 = _nouveau_falcon_context_wr32,
-       },
-};
-
-/*******************************************************************************
- * PBSP engine/subdev functions
- ******************************************************************************/
-
-static int
-nvc0_bsp_init(struct nouveau_object *object)
-{
-       struct nvc0_bsp_priv *priv = (void *)object;
-       int ret;
-
-       ret = nouveau_falcon_init(&priv->base);
-       if (ret)
-               return ret;
-
-       nv_wr32(priv, 0x084010, 0x0000fff2);
-       nv_wr32(priv, 0x08401c, 0x0000fff2);
-       return 0;
-}
-
-static int
-nvc0_bsp_ctor(struct nouveau_object *parent, struct nouveau_object *engine,
-             struct nouveau_oclass *oclass, void *data, u32 size,
-             struct nouveau_object **pobject)
-{
-       struct nvc0_bsp_priv *priv;
-       int ret;
-
-       ret = nouveau_falcon_create(parent, engine, oclass, 0x084000, true,
-                                   "PBSP", "bsp", &priv);
-       *pobject = nv_object(priv);
-       if (ret)
-               return ret;
-
-       nv_subdev(priv)->unit = 0x00008000;
-       nv_subdev(priv)->intr = nouveau_falcon_intr;
-       nv_engine(priv)->cclass = &nvc0_bsp_cclass;
-       nv_engine(priv)->sclass = nvc0_bsp_sclass;
-       return 0;
-}
-
-struct nouveau_oclass
-nvc0_bsp_oclass = {
-       .handle = NV_ENGINE(BSP, 0xc0),
-       .ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nvc0_bsp_ctor,
-               .dtor = _nouveau_falcon_dtor,
-               .init = nvc0_bsp_init,
-               .fini = _nouveau_falcon_fini,
-               .rd32 = _nouveau_falcon_rd32,
-               .wr32 = _nouveau_falcon_wr32,
-       },
-};
diff --git a/drivers/gpu/drm/nouveau/core/engine/bsp/nve0.c b/drivers/gpu/drm/nouveau/core/engine/bsp/nve0.c
deleted file mode 100644 (file)
index ba6aeca..0000000
+++ /dev/null
@@ -1,110 +0,0 @@
-/*
- * Copyright 2012 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 <engine/falcon.h>
-#include <engine/bsp.h>
-
-struct nve0_bsp_priv {
-       struct nouveau_falcon base;
-};
-
-/*******************************************************************************
- * BSP object classes
- ******************************************************************************/
-
-static struct nouveau_oclass
-nve0_bsp_sclass[] = {
-       { 0x95b1, &nouveau_object_ofuncs },
-       {},
-};
-
-/*******************************************************************************
- * PBSP context
- ******************************************************************************/
-
-static struct nouveau_oclass
-nve0_bsp_cclass = {
-       .handle = NV_ENGCTX(BSP, 0xe0),
-       .ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = _nouveau_falcon_context_ctor,
-               .dtor = _nouveau_falcon_context_dtor,
-               .init = _nouveau_falcon_context_init,
-               .fini = _nouveau_falcon_context_fini,
-               .rd32 = _nouveau_falcon_context_rd32,
-               .wr32 = _nouveau_falcon_context_wr32,
-       },
-};
-
-/*******************************************************************************
- * PBSP engine/subdev functions
- ******************************************************************************/
-
-static int
-nve0_bsp_init(struct nouveau_object *object)
-{
-       struct nve0_bsp_priv *priv = (void *)object;
-       int ret;
-
-       ret = nouveau_falcon_init(&priv->base);
-       if (ret)
-               return ret;
-
-       nv_wr32(priv, 0x084010, 0x0000fff2);
-       nv_wr32(priv, 0x08401c, 0x0000fff2);
-       return 0;
-}
-
-static int
-nve0_bsp_ctor(struct nouveau_object *parent, struct nouveau_object *engine,
-             struct nouveau_oclass *oclass, void *data, u32 size,
-             struct nouveau_object **pobject)
-{
-       struct nve0_bsp_priv *priv;
-       int ret;
-
-       ret = nouveau_falcon_create(parent, engine, oclass, 0x084000, true,
-                                   "PBSP", "bsp", &priv);
-       *pobject = nv_object(priv);
-       if (ret)
-               return ret;
-
-       nv_subdev(priv)->unit = 0x00008000;
-       nv_subdev(priv)->intr = nouveau_falcon_intr;
-       nv_engine(priv)->cclass = &nve0_bsp_cclass;
-       nv_engine(priv)->sclass = nve0_bsp_sclass;
-       return 0;
-}
-
-struct nouveau_oclass
-nve0_bsp_oclass = {
-       .handle = NV_ENGINE(BSP, 0xe0),
-       .ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nve0_bsp_ctor,
-               .dtor = _nouveau_falcon_dtor,
-               .init = nve0_bsp_init,
-               .fini = _nouveau_falcon_fini,
-               .rd32 = _nouveau_falcon_rd32,
-               .wr32 = _nouveau_falcon_wr32,
-       },
-};
diff --git a/drivers/gpu/drm/nouveau/core/engine/copy/fuc/nva3.fuc b/drivers/gpu/drm/nouveau/core/engine/copy/fuc/nva3.fuc
deleted file mode 100644 (file)
index 219850d..0000000
+++ /dev/null
@@ -1,872 +0,0 @@
-/* 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            ~0xffffffff
-.b32 #ctx_dst_address_high           ~0x000000ff
-.b32 #ctx_dst_address_low            ~0xffffffff
-.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/drivers/gpu/drm/nouveau/core/engine/copy/fuc/nva3.fuc.h b/drivers/gpu/drm/nouveau/core/engine/copy/fuc/nva3.fuc.h
deleted file mode 100644 (file)
index 241b272..0000000
+++ /dev/null
@@ -1,620 +0,0 @@
-uint32_t nva3_pcopy_data[] = {
-/* 0x0000: ctx_object */
-       0x00000000,
-/* 0x0004: ctx_dma */
-/* 0x0004: ctx_dma_query */
-       0x00000000,
-/* 0x0008: ctx_dma_src */
-       0x00000000,
-/* 0x000c: ctx_dma_dst */
-       0x00000000,
-/* 0x0010: ctx_query_address_high */
-       0x00000000,
-/* 0x0014: ctx_query_address_low */
-       0x00000000,
-/* 0x0018: ctx_query_counter */
-       0x00000000,
-/* 0x001c: ctx_src_address_high */
-       0x00000000,
-/* 0x0020: ctx_src_address_low */
-       0x00000000,
-/* 0x0024: ctx_src_pitch */
-       0x00000000,
-/* 0x0028: ctx_src_tile_mode */
-       0x00000000,
-/* 0x002c: ctx_src_xsize */
-       0x00000000,
-/* 0x0030: ctx_src_ysize */
-       0x00000000,
-/* 0x0034: ctx_src_zsize */
-       0x00000000,
-/* 0x0038: ctx_src_zoff */
-       0x00000000,
-/* 0x003c: ctx_src_xoff */
-       0x00000000,
-/* 0x0040: ctx_src_yoff */
-       0x00000000,
-/* 0x0044: ctx_src_cpp */
-       0x00000000,
-/* 0x0048: ctx_dst_address_high */
-       0x00000000,
-/* 0x004c: ctx_dst_address_low */
-       0x00000000,
-/* 0x0050: ctx_dst_pitch */
-       0x00000000,
-/* 0x0054: ctx_dst_tile_mode */
-       0x00000000,
-/* 0x0058: ctx_dst_xsize */
-       0x00000000,
-/* 0x005c: ctx_dst_ysize */
-       0x00000000,
-/* 0x0060: ctx_dst_zsize */
-       0x00000000,
-/* 0x0064: ctx_dst_zoff */
-       0x00000000,
-/* 0x0068: ctx_dst_xoff */
-       0x00000000,
-/* 0x006c: ctx_dst_yoff */
-       0x00000000,
-/* 0x0070: ctx_dst_cpp */
-       0x00000000,
-/* 0x0074: ctx_format */
-       0x00000000,
-/* 0x0078: ctx_swz_const0 */
-       0x00000000,
-/* 0x007c: ctx_swz_const1 */
-       0x00000000,
-/* 0x0080: ctx_xcnt */
-       0x00000000,
-/* 0x0084: ctx_ycnt */
-       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,
-/* 0x0100: dispatch_table */
-       0x00010000,
-       0x00000000,
-       0x00000000,
-       0x00010040,
-       0x00010160,
-       0x00000000,
-       0x00010050,
-       0x00010162,
-       0x00000000,
-       0x00030060,
-/* 0x0128: dispatch_dma */
-       0x00010170,
-       0x00000000,
-       0x00010170,
-       0x00000000,
-       0x00010170,
-       0x00000000,
-       0x00070080,
-       0x00000028,
-       0xfffff000,
-       0x0000002c,
-       0xfff80000,
-       0x00000030,
-       0xffffe000,
-       0x00000034,
-       0xfffff800,
-       0x00000038,
-       0xfffff000,
-       0x0000003c,
-       0xfff80000,
-       0x00000040,
-       0xffffe000,
-       0x00070088,
-       0x00000054,
-       0xfffff000,
-       0x00000058,
-       0xfff80000,
-       0x0000005c,
-       0xffffe000,
-       0x00000060,
-       0xfffff800,
-       0x00000064,
-       0xfffff000,
-       0x00000068,
-       0xfff80000,
-       0x0000006c,
-       0xffffe000,
-       0x000200c0,
-       0x00010492,
-       0x00000000,
-       0x0001051b,
-       0x00000000,
-       0x000e00c3,
-       0x0000001c,
-       0xffffff00,
-       0x00000020,
-       0x00000000,
-       0x00000048,
-       0xffffff00,
-       0x0000004c,
-       0x00000000,
-       0x00000024,
-       0xfff80000,
-       0x00000050,
-       0xfff80000,
-       0x00000080,
-       0xffff0000,
-       0x00000084,
-       0xffffe000,
-       0x00000074,
-       0xfccc0000,
-       0x00000078,
-       0x00000000,
-       0x0000007c,
-       0x00000000,
-       0x00000010,
-       0xffffff00,
-       0x00000014,
-       0x00000000,
-       0x00000018,
-       0x00000000,
-       0x00000800,
-};
-
-uint32_t nva3_pcopy_code[] = {
-/* 0x0000: main */
-       0x04fe04bd,
-       0x3517f000,
-       0xf10010fe,
-       0xf1040017,
-       0xf0fff327,
-       0x12d00023,
-       0x0c25f0c0,
-       0xf40012d0,
-       0x17f11031,
-       0x27f01200,
-       0x0012d003,
-/* 0x002f: spin */
-       0xf40031f4,
-       0x0ef40028,
-/* 0x0035: ih */
-       0x8001cffd,
-       0xf40812c4,
-       0x21f4060b,
-/* 0x0041: ih_no_chsw */
-       0x0412c472,
-       0xf4060bf4,
-/* 0x004a: ih_no_cmd */
-       0x11c4c321,
-       0x4001d00c,
-/* 0x0052: swctx */
-       0x47f101f8,
-       0x4bfe7700,
-       0x0007fe00,
-       0xf00204b9,
-       0x01f40643,
-       0x0604fa09,
-/* 0x006b: swctx_load */
-       0xfa060ef4,
-/* 0x006e: swctx_done */
-       0x03f80504,
-/* 0x0072: chsw */
-       0x27f100f8,
-       0x23cf1400,
-       0x1e3fc800,
-       0xf4170bf4,
-       0x21f40132,
-       0x1e3af052,
-       0xf00023d0,
-       0x24d00147,
-/* 0x0093: chsw_no_unload */
-       0xcf00f880,
-       0x3dc84023,
-       0x220bf41e,
-       0xf40131f4,
-       0x57f05221,
-       0x0367f004,
-/* 0x00a8: chsw_load_ctx_dma */
-       0xa07856bc,
-       0xb6018068,
-       0x87d00884,
-       0x0162b600,
-/* 0x00bb: chsw_finish_load */
-       0xf0f018f4,
-       0x23d00237,
-/* 0x00c3: dispatch */
-       0xf100f880,
-       0xcf190037,
-       0x33cf4032,
-       0xff24e400,
-       0x1024b607,
-       0x010057f1,
-       0x74bd64bd,
-/* 0x00dc: dispatch_loop */
-       0x58005658,
-       0x50b60157,
-       0x0446b804,
-       0xbb4d08f4,
-       0x47b80076,
-       0x0f08f404,
-       0xb60276bb,
-       0x57bb0374,
-       0xdf0ef400,
-/* 0x0100: dispatch_valid_mthd */
-       0xb60246bb,
-       0x45bb0344,
-       0x01459800,
-       0xb00453fd,
-       0x1bf40054,
-       0x00455820,
-       0xb0014658,
-       0x1bf40064,
-       0x00538009,
-/* 0x0127: dispatch_cmd */
-       0xf4300ef4,
-       0x55f90132,
-       0xf40c01f4,
-/* 0x0132: dispatch_invalid_bitfield */
-       0x25f0250e,
-/* 0x0135: dispatch_illegal_mthd */
-       0x0125f002,
-/* 0x0138: dispatch_error */
-       0x100047f1,
-       0xd00042d0,
-       0x27f04043,
-       0x0002d040,
-/* 0x0148: hostirq_wait */
-       0xf08002cf,
-       0x24b04024,
-       0xf71bf400,
-/* 0x0154: dispatch_done */
-       0x1d0027f1,
-       0xd00137f0,
-       0x00f80023,
-/* 0x0160: cmd_nop */
-/* 0x0162: cmd_pm_trigger */
-       0x27f100f8,
-       0x34bd2200,
-       0xd00233f0,
-       0x00f80023,
-/* 0x0170: cmd_dma */
-       0x012842b7,
-       0xf00145b6,
-       0x43801e39,
-       0x0040b701,
-       0x0644b606,
-       0xf80043d0,
-/* 0x0189: cmd_exec_set_format */
-       0xf030f400,
-       0xb00001b0,
-       0x01b00101,
-       0x0301b002,
-       0xc71d0498,
-       0x50b63045,
-       0x3446c701,
-       0xc70160b6,
-       0x70b63847,
-       0x0232f401,
-       0x94bd84bd,
-/* 0x01b4: ncomp_loop */
-       0xb60f4ac4,
-       0xb4bd0445,
-/* 0x01bc: bpc_loop */
-       0xf404a430,
-       0xa5ff0f18,
-       0x00cbbbc0,
-       0xf40231f4,
-/* 0x01ce: cmp_c0 */
-       0x1bf4220e,
-       0x10c7f00c,
-       0xf400cbbb,
-/* 0x01da: cmp_c1 */
-       0xa430160e,
-       0x0c18f406,
-       0xbb14c7f0,
-       0x0ef400cb,
-/* 0x01e9: cmp_zero */
-       0x80c7f107,
-/* 0x01ed: bpc_next */
-       0x01c83800,
-       0xb60180b6,
-       0xb5b801b0,
-       0xc308f404,
-       0xb80190b6,
-       0x08f40497,
-       0x0065fdb2,
-       0x98110680,
-       0x68fd2008,
-       0x0502f400,
-/* 0x0216: dst_xcnt */
-       0x75fd64bd,
-       0x1c078000,
-       0xf10078fd,
-       0xb6081057,
-       0x56d00654,
-       0x4057d000,
-       0x080050b7,
-       0xb61c0698,
-       0x64b60162,
-       0x11079808,
-       0xfd0172b6,
-       0x56d00567,
-       0x0050b700,
-       0x0060b401,
-       0xb40056d0,
-       0x56d00160,
-       0x0260b440,
-       0xb48056d0,
-       0x56d00360,
-       0x0050b7c0,
-       0x1e069804,
-       0x980056d0,
-       0x56d01f06,
-       0x1030f440,
-/* 0x0276: cmd_exec_set_surface_tiled */
-       0x579800f8,
-       0x6879c70a,
-       0xb66478c7,
-       0x77c70280,
-       0x0e76b060,
-       0xf0091bf4,
-       0x0ef40477,
-/* 0x0291: xtile64 */
-       0x027cf00f,
-       0xfd1170b6,
-       0x77f00947,
-/* 0x029d: xtileok */
-       0x0f5a9806,
-       0xfd115b98,
-       0xb7f000ab,
-       0x04b7bb01,
-       0xff01b2b6,
-       0xa7bbc4ab,
-       0x105d9805,
-       0xbb01e7f0,
-       0xe2b604e8,
-       0xb4deff01,
-       0xb605d8bb,
-       0xef9401e0,
-       0x02ebbb0c,
-       0xf005fefd,
-       0x60b7026c,
-       0x64b60208,
-       0x006fd008,
-       0xbb04b7bb,
-       0x5f9800cb,
-       0x115b980b,
-       0xf000fbfd,
-       0xb7bb01b7,
-       0x01b2b604,
-       0xbb00fbbb,
-       0xf0f905f7,
-       0xf00c5f98,
-       0xb8bb01b7,
-       0x01b2b604,
-       0xbb00fbbb,
-       0xf0f905f8,
-       0xb60078bb,
-       0xb7f00282,
-       0x04b8bb01,
-       0x9804b9bb,
-       0xe7f00e58,
-       0x04e9bb01,
-       0xff01e2b6,
-       0xf7bbf48e,
-       0x00cfbb04,
-       0xbb0079bb,
-       0xf0fc0589,
-       0xd9fd90fc,
-       0x00adbb00,
-       0xfd0089fd,
-       0xa8bb008f,
-       0x04a7bb00,
-       0xbb0192b6,
-       0x69d00497,
-       0x08579880,
-       0xbb075898,
-       0x7abb00ac,
-       0x0081b600,
-       0xfd1084b6,
-       0x62b7058b,
-       0x67d00600,
-       0x0060b700,
-       0x0068d004,
-/* 0x0382: cmd_exec_set_surface_linear */
-       0x6cf000f8,
-       0x0260b702,
-       0x0864b602,
-       0xd0085798,
-       0x60b70067,
-       0x57980400,
-       0x1074b607,
-       0xb70067d0,
-       0x98040060,
-       0x67d00957,
-/* 0x03ab: cmd_exec_wait */
-       0xf900f800,
-       0xf110f900,
-       0xb6080007,
-/* 0x03b6: loop */
-       0x01cf0604,
-       0x0114f000,
-       0xfcfa1bf4,
-       0xf800fc10,
-/* 0x03c5: cmd_exec_query */
-       0x0d34c800,
-       0xf5701bf4,
-       0xf103ab21,
-       0xb6080c47,
-       0x05980644,
-       0x0450b605,
-       0xd00045d0,
-       0x57f04040,
-       0x8045d00c,
-       0x040040b7,
-       0xb6040598,
-       0x45d01054,
-       0x0040b700,
-       0x0057f105,
-       0x0153f00b,
-       0xf10045d0,
-       0xb6404057,
-       0x53f10154,
-       0x45d08080,
-       0x1057f140,
-       0x1253f111,
-       0x8045d013,
-       0x151457f1,
-       0x171653f1,
-       0xf1c045d0,
-       0xf0260157,
-       0x47f10153,
-       0x44b60800,
-       0x0045d006,
-/* 0x0438: query_counter */
-       0x03ab21f5,
-       0x080c47f1,
-       0x980644b6,
-       0x45d00505,
-       0x4040d000,
-       0xd00457f0,
-       0x40b78045,
-       0x05980400,
-       0x1054b604,
-       0xb70045d0,
-       0xf1050040,
-       0xd0030057,
-       0x57f10045,
-       0x53f11110,
-       0x45d01312,
-       0x06059840,
-       0x050040b7,
-       0xf10045d0,
-       0xf0260157,
-       0x47f10153,
-       0x44b60800,
-       0x0045d006,
-/* 0x0492: cmd_exec */
-       0x21f500f8,
-       0x3fc803ab,
-       0x0e0bf400,
-       0x018921f5,
-       0x020047f1,
-/* 0x04a7: cmd_exec_no_format */
-       0xf11e0ef4,
-       0xb6081067,
-       0x77f00664,
-       0x11078001,
-       0x981c0780,
-       0x67d02007,
-       0x4067d000,
-/* 0x04c2: cmd_exec_init_src_surface */
-       0x32f444bd,
-       0xc854bd02,
-       0x0bf4043f,
-       0x8221f50a,
-       0x0a0ef403,
-/* 0x04d4: src_tiled */
-       0x027621f5,
-/* 0x04db: cmd_exec_init_dst_surface */
-       0xf40749f0,
-       0x57f00231,
-       0x083fc82c,
-       0xf50a0bf4,
-       0xf4038221,
-/* 0x04ee: dst_tiled */
-       0x21f50a0e,
-       0x49f00276,
-/* 0x04f5: cmd_exec_kick */
-       0x0057f108,
-       0x0654b608,
-       0xd0210698,
-       0x67f04056,
-       0x0063f141,
-       0x0546fd44,
-       0xc80054d0,
-       0x0bf40c3f,
-       0xc521f507,
-/* 0x0519: cmd_exec_done */
-/* 0x051b: cmd_wrcache_flush */
-       0xf100f803,
-       0xbd220027,
-       0x0133f034,
-       0xf80023d0,
-       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,
-};
diff --git a/drivers/gpu/drm/nouveau/core/engine/copy/fuc/nvc0.fuc.h b/drivers/gpu/drm/nouveau/core/engine/copy/fuc/nvc0.fuc.h
deleted file mode 100644 (file)
index 98cc421..0000000
+++ /dev/null
@@ -1,606 +0,0 @@
-uint32_t nvc0_pcopy_data[] = {
-/* 0x0000: ctx_object */
-       0x00000000,
-/* 0x0004: ctx_query_address_high */
-       0x00000000,
-/* 0x0008: ctx_query_address_low */
-       0x00000000,
-/* 0x000c: ctx_query_counter */
-       0x00000000,
-/* 0x0010: ctx_src_address_high */
-       0x00000000,
-/* 0x0014: ctx_src_address_low */
-       0x00000000,
-/* 0x0018: ctx_src_pitch */
-       0x00000000,
-/* 0x001c: ctx_src_tile_mode */
-       0x00000000,
-/* 0x0020: ctx_src_xsize */
-       0x00000000,
-/* 0x0024: ctx_src_ysize */
-       0x00000000,
-/* 0x0028: ctx_src_zsize */
-       0x00000000,
-/* 0x002c: ctx_src_zoff */
-       0x00000000,
-/* 0x0030: ctx_src_xoff */
-       0x00000000,
-/* 0x0034: ctx_src_yoff */
-       0x00000000,
-/* 0x0038: ctx_src_cpp */
-       0x00000000,
-/* 0x003c: ctx_dst_address_high */
-       0x00000000,
-/* 0x0040: ctx_dst_address_low */
-       0x00000000,
-/* 0x0044: ctx_dst_pitch */
-       0x00000000,
-/* 0x0048: ctx_dst_tile_mode */
-       0x00000000,
-/* 0x004c: ctx_dst_xsize */
-       0x00000000,
-/* 0x0050: ctx_dst_ysize */
-       0x00000000,
-/* 0x0054: ctx_dst_zsize */
-       0x00000000,
-/* 0x0058: ctx_dst_zoff */
-       0x00000000,
-/* 0x005c: ctx_dst_xoff */
-       0x00000000,
-/* 0x0060: ctx_dst_yoff */
-       0x00000000,
-/* 0x0064: ctx_dst_cpp */
-       0x00000000,
-/* 0x0068: ctx_format */
-       0x00000000,
-/* 0x006c: ctx_swz_const0 */
-       0x00000000,
-/* 0x0070: ctx_swz_const1 */
-       0x00000000,
-/* 0x0074: ctx_xcnt */
-       0x00000000,
-/* 0x0078: ctx_ycnt */
-       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,
-/* 0x0100: dispatch_table */
-       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,
-       0x00000000,
-       0x0000003c,
-       0xffffff00,
-       0x00000040,
-       0x00000000,
-       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[] = {
-/* 0x0000: main */
-       0x04fe04bd,
-       0x3517f000,
-       0xf10010fe,
-       0xf1040017,
-       0xf0fff327,
-       0x12d00023,
-       0x0c25f0c0,
-       0xf40012d0,
-       0x17f11031,
-       0x27f01200,
-       0x0012d003,
-/* 0x002f: spin */
-       0xf40031f4,
-       0x0ef40028,
-/* 0x0035: ih */
-       0x8001cffd,
-       0xf40812c4,
-       0x21f4060b,
-/* 0x0041: ih_no_chsw */
-       0x0412c4ca,
-       0xf5070bf4,
-/* 0x004b: ih_no_cmd */
-       0xc4010221,
-       0x01d00c11,
-/* 0x0053: swctx */
-       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,
-/* 0x00c3: swctx_load */
-       0xfa060ef4,
-/* 0x00c6: swctx_done */
-       0x03f80504,
-/* 0x00ca: chsw */
-       0x27f100f8,
-       0x23cf1400,
-       0x1e3fc800,
-       0xf4170bf4,
-       0x21f40132,
-       0x1e3af053,
-       0xf00023d0,
-       0x24d00147,
-/* 0x00eb: chsw_no_unload */
-       0xcf00f880,
-       0x3dc84023,
-       0x090bf41e,
-       0xf40131f4,
-/* 0x00fa: chsw_finish_load */
-       0x37f05321,
-       0x8023d002,
-/* 0x0102: dispatch */
-       0x37f100f8,
-       0x32cf1900,
-       0x0033cf40,
-       0x07ff24e4,
-       0xf11024b6,
-       0xbd010057,
-/* 0x011b: dispatch_loop */
-       0x5874bd64,
-       0x57580056,
-       0x0450b601,
-       0xf40446b8,
-       0x76bb4d08,
-       0x0447b800,
-       0xbb0f08f4,
-       0x74b60276,
-       0x0057bb03,
-/* 0x013f: dispatch_valid_mthd */
-       0xbbdf0ef4,
-       0x44b60246,
-       0x0045bb03,
-       0xfd014598,
-       0x54b00453,
-       0x201bf400,
-       0x58004558,
-       0x64b00146,
-       0x091bf400,
-       0xf4005380,
-/* 0x0166: dispatch_cmd */
-       0x32f4300e,
-       0xf455f901,
-       0x0ef40c01,
-/* 0x0171: dispatch_invalid_bitfield */
-       0x0225f025,
-/* 0x0174: dispatch_illegal_mthd */
-/* 0x0177: dispatch_error */
-       0xf10125f0,
-       0xd0100047,
-       0x43d00042,
-       0x4027f040,
-/* 0x0187: hostirq_wait */
-       0xcf0002d0,
-       0x24f08002,
-       0x0024b040,
-/* 0x0193: dispatch_done */
-       0xf1f71bf4,
-       0xf01d0027,
-       0x23d00137,
-/* 0x019f: cmd_nop */
-       0xf800f800,
-/* 0x01a1: cmd_pm_trigger */
-       0x0027f100,
-       0xf034bd22,
-       0x23d00233,
-/* 0x01af: cmd_exec_set_format */
-       0xf400f800,
-       0x01b0f030,
-       0x0101b000,
-       0xb00201b0,
-       0x04980301,
-       0x3045c71a,
-       0xc70150b6,
-       0x60b63446,
-       0x3847c701,
-       0xf40170b6,
-       0x84bd0232,
-/* 0x01da: ncomp_loop */
-       0x4ac494bd,
-       0x0445b60f,
-/* 0x01e2: bpc_loop */
-       0xa430b4bd,
-       0x0f18f404,
-       0xbbc0a5ff,
-       0x31f400cb,
-       0x220ef402,
-/* 0x01f4: cmp_c0 */
-       0xf00c1bf4,
-       0xcbbb10c7,
-       0x160ef400,
-/* 0x0200: cmp_c1 */
-       0xf406a430,
-       0xc7f00c18,
-       0x00cbbb14,
-/* 0x020f: cmp_zero */
-       0xf1070ef4,
-/* 0x0213: bpc_next */
-       0x380080c7,
-       0x80b601c8,
-       0x01b0b601,
-       0xf404b5b8,
-       0x90b6c308,
-       0x0497b801,
-       0xfdb208f4,
-       0x06800065,
-       0x1d08980e,
-       0xf40068fd,
-       0x64bd0502,
-/* 0x023c: dst_xcnt */
-       0x800075fd,
-       0x78fd1907,
-       0x1057f100,
-       0x0654b608,
-       0xd00056d0,
-       0x50b74057,
-       0x06980800,
-       0x0162b619,
-       0x980864b6,
-       0x72b60e07,
-       0x0567fd01,
-       0xb70056d0,
-       0xb4010050,
-       0x56d00060,
-       0x0160b400,
-       0xb44056d0,
-       0x56d00260,
-       0x0360b480,
-       0xb7c056d0,
-       0x98040050,
-       0x56d01b06,
-       0x1c069800,
-       0xf44056d0,
-       0x00f81030,
-/* 0x029c: cmd_exec_set_surface_tiled */
-       0xc7075798,
-       0x78c76879,
-       0x0380b664,
-       0xb06077c7,
-       0x1bf40e76,
-       0x0477f009,
-/* 0x02b7: xtile64 */
-       0xf00f0ef4,
-       0x70b6027c,
-       0x0947fd11,
-/* 0x02c3: xtileok */
-       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,
-/* 0x03a8: cmd_exec_set_surface_linear */
-       0xb7026cf0,
-       0xb6020260,
-       0x57980864,
-       0x0067d005,
-       0x040060b7,
-       0xb6045798,
-       0x67d01074,
-       0x0060b700,
-       0x06579804,
-       0xf80067d0,
-/* 0x03d1: cmd_exec_wait */
-       0xf900f900,
-       0x0007f110,
-       0x0604b608,
-/* 0x03dc: loop */
-       0xf00001cf,
-       0x1bf40114,
-       0xfc10fcfa,
-/* 0x03eb: cmd_exec_query */
-       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,
-/* 0x045e: query_counter */
-       0x21f50045,
-       0x47f103d1,
-       0x44b6080c,
-       0x02059806,
-       0xd00045d0,
-       0x57f04040,
-       0x8045d004,
-       0x040040b7,
-       0xb6010598,
-       0x45d01054,
-       0x0040b700,
-       0x0057f105,
-       0x0045d003,
-       0x111057f1,
-       0x131253f1,
-       0x984045d0,
-       0x40b70305,
-       0x45d00500,
-       0x0157f100,
-       0x0153f026,
-       0x080047f1,
-       0xd00644b6,
-       0x00f80045,
-/* 0x04b8: cmd_exec */
-       0x03d121f5,
-       0xf4003fc8,
-       0x21f50e0b,
-       0x47f101af,
-       0x0ef40200,
-/* 0x04cd: cmd_exec_no_format */
-       0x1067f11e,
-       0x0664b608,
-       0x800177f0,
-       0x07800e07,
-       0x1d079819,
-       0xd00067d0,
-       0x44bd4067,
-/* 0x04e8: cmd_exec_init_src_surface */
-       0xbd0232f4,
-       0x043fc854,
-       0xf50a0bf4,
-       0xf403a821,
-/* 0x04fa: src_tiled */
-       0x21f50a0e,
-       0x49f0029c,
-/* 0x0501: cmd_exec_init_dst_surface */
-       0x0231f407,
-       0xc82c57f0,
-       0x0bf4083f,
-       0xa821f50a,
-       0x0a0ef403,
-/* 0x0514: dst_tiled */
-       0x029c21f5,
-/* 0x051b: cmd_exec_kick */
-       0xf10849f0,
-       0xb6080057,
-       0x06980654,
-       0x4056d01e,
-       0xf14167f0,
-       0xfd440063,
-       0x54d00546,
-       0x0c3fc800,
-       0xf5070bf4,
-/* 0x053f: cmd_exec_done */
-       0xf803eb21,
-/* 0x0541: cmd_wrcache_flush */
-       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/drivers/gpu/drm/nouveau/core/engine/copy/nva3.c b/drivers/gpu/drm/nouveau/core/engine/copy/nva3.c
deleted file mode 100644 (file)
index abb410e..0000000
+++ /dev/null
@@ -1,156 +0,0 @@
-/*
- * Copyright 2012 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 <engine/falcon.h>
-#include <engine/fifo.h>
-#include <engine/copy.h>
-
-#include <subdev/fb.h>
-#include <subdev/vm.h>
-
-#include <core/client.h>
-#include <core/enum.h>
-
-
-#include "fuc/nva3.fuc.h"
-
-struct nva3_copy_priv {
-       struct nouveau_falcon base;
-};
-
-/*******************************************************************************
- * Copy object classes
- ******************************************************************************/
-
-static struct nouveau_oclass
-nva3_copy_sclass[] = {
-       { 0x85b5, &nouveau_object_ofuncs },
-       {}
-};
-
-/*******************************************************************************
- * PCOPY context
- ******************************************************************************/
-
-static struct nouveau_oclass
-nva3_copy_cclass = {
-       .handle = NV_ENGCTX(COPY0, 0xa3),
-       .ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = _nouveau_falcon_context_ctor,
-               .dtor = _nouveau_falcon_context_dtor,
-               .init = _nouveau_falcon_context_init,
-               .fini = _nouveau_falcon_context_fini,
-               .rd32 = _nouveau_falcon_context_rd32,
-               .wr32 = _nouveau_falcon_context_wr32,
-
-       },
-};
-
-/*******************************************************************************
- * PCOPY engine/subdev functions
- ******************************************************************************/
-
-static const struct nouveau_enum nva3_copy_isr_error_name[] = {
-       { 0x0001, "ILLEGAL_MTHD" },
-       { 0x0002, "INVALID_ENUM" },
-       { 0x0003, "INVALID_BITFIELD" },
-       {}
-};
-
-void
-nva3_copy_intr(struct nouveau_subdev *subdev)
-{
-       struct nouveau_fifo *pfifo = nouveau_fifo(subdev);
-       struct nouveau_engine *engine = nv_engine(subdev);
-       struct nouveau_falcon *falcon = (void *)subdev;
-       struct nouveau_object *engctx;
-       u32 dispatch = nv_ro32(falcon, 0x01c);
-       u32 stat = nv_ro32(falcon, 0x008) & dispatch & ~(dispatch >> 16);
-       u64 inst = nv_ro32(falcon, 0x050) & 0x3fffffff;
-       u32 ssta = nv_ro32(falcon, 0x040) & 0x0000ffff;
-       u32 addr = nv_ro32(falcon, 0x040) >> 16;
-       u32 mthd = (addr & 0x07ff) << 2;
-       u32 subc = (addr & 0x3800) >> 11;
-       u32 data = nv_ro32(falcon, 0x044);
-       int chid;
-
-       engctx = nouveau_engctx_get(engine, inst);
-       chid   = pfifo->chid(pfifo, engctx);
-
-       if (stat & 0x00000040) {
-               nv_error(falcon, "DISPATCH_ERROR [");
-               nouveau_enum_print(nva3_copy_isr_error_name, ssta);
-               pr_cont("] ch %d [0x%010llx %s] subc %d mthd 0x%04x data 0x%08x\n",
-                      chid, inst << 12, nouveau_client_name(engctx), subc,
-                      mthd, data);
-               nv_wo32(falcon, 0x004, 0x00000040);
-               stat &= ~0x00000040;
-       }
-
-       if (stat) {
-               nv_error(falcon, "unhandled intr 0x%08x\n", stat);
-               nv_wo32(falcon, 0x004, stat);
-       }
-
-       nouveau_engctx_put(engctx);
-}
-
-static int
-nva3_copy_ctor(struct nouveau_object *parent, struct nouveau_object *engine,
-              struct nouveau_oclass *oclass, void *data, u32 size,
-              struct nouveau_object **pobject)
-{
-       bool enable = (nv_device(parent)->chipset != 0xaf);
-       struct nva3_copy_priv *priv;
-       int ret;
-
-       ret = nouveau_falcon_create(parent, engine, oclass, 0x104000, enable,
-                                   "PCE0", "copy0", &priv);
-       *pobject = nv_object(priv);
-       if (ret)
-               return ret;
-
-       nv_subdev(priv)->unit = 0x00802000;
-       nv_subdev(priv)->intr = nva3_copy_intr;
-       nv_engine(priv)->cclass = &nva3_copy_cclass;
-       nv_engine(priv)->sclass = nva3_copy_sclass;
-       nv_falcon(priv)->code.data = nva3_pcopy_code;
-       nv_falcon(priv)->code.size = sizeof(nva3_pcopy_code);
-       nv_falcon(priv)->data.data = nva3_pcopy_data;
-       nv_falcon(priv)->data.size = sizeof(nva3_pcopy_data);
-       return 0;
-}
-
-struct nouveau_oclass
-nva3_copy_oclass = {
-       .handle = NV_ENGINE(COPY0, 0xa3),
-       .ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nva3_copy_ctor,
-               .dtor = _nouveau_falcon_dtor,
-               .init = _nouveau_falcon_init,
-               .fini = _nouveau_falcon_fini,
-               .rd32 = _nouveau_falcon_rd32,
-               .wr32 = _nouveau_falcon_wr32,
-       },
-};
diff --git a/drivers/gpu/drm/nouveau/core/engine/copy/nvc0.c b/drivers/gpu/drm/nouveau/core/engine/copy/nvc0.c
deleted file mode 100644 (file)
index 9261694..0000000
+++ /dev/null
@@ -1,172 +0,0 @@
-/*
- * Copyright 2012 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 <engine/falcon.h>
-#include <engine/fifo.h>
-#include <engine/copy.h>
-
-#include <core/enum.h>
-#include <core/enum.h>
-
-#include "fuc/nvc0.fuc.h"
-
-struct nvc0_copy_priv {
-       struct nouveau_falcon base;
-};
-
-/*******************************************************************************
- * Copy object classes
- ******************************************************************************/
-
-static struct nouveau_oclass
-nvc0_copy0_sclass[] = {
-       { 0x90b5, &nouveau_object_ofuncs },
-       {},
-};
-
-static struct nouveau_oclass
-nvc0_copy1_sclass[] = {
-       { 0x90b8, &nouveau_object_ofuncs },
-       {},
-};
-
-/*******************************************************************************
- * PCOPY context
- ******************************************************************************/
-
-static struct nouveau_ofuncs
-nvc0_copy_context_ofuncs = {
-       .ctor = _nouveau_falcon_context_ctor,
-       .dtor = _nouveau_falcon_context_dtor,
-       .init = _nouveau_falcon_context_init,
-       .fini = _nouveau_falcon_context_fini,
-       .rd32 = _nouveau_falcon_context_rd32,
-       .wr32 = _nouveau_falcon_context_wr32,
-};
-
-static struct nouveau_oclass
-nvc0_copy0_cclass = {
-       .handle = NV_ENGCTX(COPY0, 0xc0),
-       .ofuncs = &nvc0_copy_context_ofuncs,
-};
-
-static struct nouveau_oclass
-nvc0_copy1_cclass = {
-       .handle = NV_ENGCTX(COPY1, 0xc0),
-       .ofuncs = &nvc0_copy_context_ofuncs,
-};
-
-/*******************************************************************************
- * PCOPY engine/subdev functions
- ******************************************************************************/
-
-static int
-nvc0_copy_init(struct nouveau_object *object)
-{
-       struct nvc0_copy_priv *priv = (void *)object;
-       int ret;
-
-       ret = nouveau_falcon_init(&priv->base);
-       if (ret)
-               return ret;
-
-       nv_wo32(priv, 0x084, nv_engidx(object) - NVDEV_ENGINE_COPY0);
-       return 0;
-}
-
-static int
-nvc0_copy0_ctor(struct nouveau_object *parent, struct nouveau_object *engine,
-               struct nouveau_oclass *oclass, void *data, u32 size,
-               struct nouveau_object **pobject)
-{
-       struct nvc0_copy_priv *priv;
-       int ret;
-
-       ret = nouveau_falcon_create(parent, engine, oclass, 0x104000, true,
-                                   "PCE0", "copy0", &priv);
-       *pobject = nv_object(priv);
-       if (ret)
-               return ret;
-
-       nv_subdev(priv)->unit = 0x00000040;
-       nv_subdev(priv)->intr = nva3_copy_intr;
-       nv_engine(priv)->cclass = &nvc0_copy0_cclass;
-       nv_engine(priv)->sclass = nvc0_copy0_sclass;
-       nv_falcon(priv)->code.data = nvc0_pcopy_code;
-       nv_falcon(priv)->code.size = sizeof(nvc0_pcopy_code);
-       nv_falcon(priv)->data.data = nvc0_pcopy_data;
-       nv_falcon(priv)->data.size = sizeof(nvc0_pcopy_data);
-       return 0;
-}
-
-static int
-nvc0_copy1_ctor(struct nouveau_object *parent, struct nouveau_object *engine,
-               struct nouveau_oclass *oclass, void *data, u32 size,
-               struct nouveau_object **pobject)
-{
-       struct nvc0_copy_priv *priv;
-       int ret;
-
-       ret = nouveau_falcon_create(parent, engine, oclass, 0x105000, true,
-                                   "PCE1", "copy1", &priv);
-       *pobject = nv_object(priv);
-       if (ret)
-               return ret;
-
-       nv_subdev(priv)->unit = 0x00000080;
-       nv_subdev(priv)->intr = nva3_copy_intr;
-       nv_engine(priv)->cclass = &nvc0_copy1_cclass;
-       nv_engine(priv)->sclass = nvc0_copy1_sclass;
-       nv_falcon(priv)->code.data = nvc0_pcopy_code;
-       nv_falcon(priv)->code.size = sizeof(nvc0_pcopy_code);
-       nv_falcon(priv)->data.data = nvc0_pcopy_data;
-       nv_falcon(priv)->data.size = sizeof(nvc0_pcopy_data);
-       return 0;
-}
-
-struct nouveau_oclass
-nvc0_copy0_oclass = {
-       .handle = NV_ENGINE(COPY0, 0xc0),
-       .ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nvc0_copy0_ctor,
-               .dtor = _nouveau_falcon_dtor,
-               .init = nvc0_copy_init,
-               .fini = _nouveau_falcon_fini,
-               .rd32 = _nouveau_falcon_rd32,
-               .wr32 = _nouveau_falcon_wr32,
-       },
-};
-
-struct nouveau_oclass
-nvc0_copy1_oclass = {
-       .handle = NV_ENGINE(COPY1, 0xc0),
-       .ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nvc0_copy1_ctor,
-               .dtor = _nouveau_falcon_dtor,
-               .init = nvc0_copy_init,
-               .fini = _nouveau_falcon_fini,
-               .rd32 = _nouveau_falcon_rd32,
-               .wr32 = _nouveau_falcon_wr32,
-       },
-};
diff --git a/drivers/gpu/drm/nouveau/core/engine/copy/nve0.c b/drivers/gpu/drm/nouveau/core/engine/copy/nve0.c
deleted file mode 100644 (file)
index c7194b3..0000000
+++ /dev/null
@@ -1,176 +0,0 @@
-/*
- * Copyright 2012 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 <core/os.h>
-#include <core/enum.h>
-#include <core/engctx.h>
-
-#include <engine/copy.h>
-
-struct nve0_copy_priv {
-       struct nouveau_engine base;
-};
-
-/*******************************************************************************
- * Copy object classes
- ******************************************************************************/
-
-static struct nouveau_oclass
-nve0_copy_sclass[] = {
-       { 0xa0b5, &nouveau_object_ofuncs },
-       {},
-};
-
-/*******************************************************************************
- * PCOPY context
- ******************************************************************************/
-
-static struct nouveau_ofuncs
-nve0_copy_context_ofuncs = {
-       .ctor = _nouveau_engctx_ctor,
-       .dtor = _nouveau_engctx_dtor,
-       .init = _nouveau_engctx_init,
-       .fini = _nouveau_engctx_fini,
-       .rd32 = _nouveau_engctx_rd32,
-       .wr32 = _nouveau_engctx_wr32,
-};
-
-static struct nouveau_oclass
-nve0_copy_cclass = {
-       .handle = NV_ENGCTX(COPY0, 0xc0),
-       .ofuncs = &nve0_copy_context_ofuncs,
-};
-
-/*******************************************************************************
- * PCOPY engine/subdev functions
- ******************************************************************************/
-
-static void
-nve0_copy_intr(struct nouveau_subdev *subdev)
-{
-       const int ce = nv_subidx(nv_object(subdev)) - NVDEV_ENGINE_COPY0;
-       struct nve0_copy_priv *priv = (void *)subdev;
-       u32 stat = nv_rd32(priv, 0x104908 + (ce * 0x1000));
-
-       if (stat) {
-               nv_warn(priv, "unhandled intr 0x%08x\n", stat);
-               nv_wr32(priv, 0x104908 + (ce * 0x1000), stat);
-       }
-}
-
-static int
-nve0_copy0_ctor(struct nouveau_object *parent, struct nouveau_object *engine,
-               struct nouveau_oclass *oclass, void *data, u32 size,
-               struct nouveau_object **pobject)
-{
-       struct nve0_copy_priv *priv;
-       int ret;
-
-       ret = nouveau_engine_create(parent, engine, oclass, true,
-                                   "PCE0", "copy0", &priv);
-       *pobject = nv_object(priv);
-       if (ret)
-               return ret;
-
-       nv_subdev(priv)->unit = 0x00000040;
-       nv_subdev(priv)->intr = nve0_copy_intr;
-       nv_engine(priv)->cclass = &nve0_copy_cclass;
-       nv_engine(priv)->sclass = nve0_copy_sclass;
-       return 0;
-}
-
-static int
-nve0_copy1_ctor(struct nouveau_object *parent, struct nouveau_object *engine,
-               struct nouveau_oclass *oclass, void *data, u32 size,
-               struct nouveau_object **pobject)
-{
-       struct nve0_copy_priv *priv;
-       int ret;
-
-       ret = nouveau_engine_create(parent, engine, oclass, true,
-                                   "PCE1", "copy1", &priv);
-       *pobject = nv_object(priv);
-       if (ret)
-               return ret;
-
-       nv_subdev(priv)->unit = 0x00000080;
-       nv_subdev(priv)->intr = nve0_copy_intr;
-       nv_engine(priv)->cclass = &nve0_copy_cclass;
-       nv_engine(priv)->sclass = nve0_copy_sclass;
-       return 0;
-}
-
-static int
-nve0_copy2_ctor(struct nouveau_object *parent, struct nouveau_object *engine,
-               struct nouveau_oclass *oclass, void *data, u32 size,
-               struct nouveau_object **pobject)
-{
-       struct nve0_copy_priv *priv;
-       int ret;
-
-       ret = nouveau_engine_create(parent, engine, oclass, true,
-                                   "PCE2", "copy2", &priv);
-       *pobject = nv_object(priv);
-       if (ret)
-               return ret;
-
-       nv_subdev(priv)->unit = 0x00200000;
-       nv_subdev(priv)->intr = nve0_copy_intr;
-       nv_engine(priv)->cclass = &nve0_copy_cclass;
-       nv_engine(priv)->sclass = nve0_copy_sclass;
-       return 0;
-}
-
-struct nouveau_oclass
-nve0_copy0_oclass = {
-       .handle = NV_ENGINE(COPY0, 0xe0),
-       .ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nve0_copy0_ctor,
-               .dtor = _nouveau_engine_dtor,
-               .init = _nouveau_engine_init,
-               .fini = _nouveau_engine_fini,
-       },
-};
-
-struct nouveau_oclass
-nve0_copy1_oclass = {
-       .handle = NV_ENGINE(COPY1, 0xe0),
-       .ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nve0_copy1_ctor,
-               .dtor = _nouveau_engine_dtor,
-               .init = _nouveau_engine_init,
-               .fini = _nouveau_engine_fini,
-       },
-};
-
-struct nouveau_oclass
-nve0_copy2_oclass = {
-       .handle = NV_ENGINE(COPY2, 0xe0),
-       .ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nve0_copy2_ctor,
-               .dtor = _nouveau_engine_dtor,
-               .init = _nouveau_engine_init,
-               .fini = _nouveau_engine_fini,
-       },
-};
diff --git a/drivers/gpu/drm/nouveau/core/engine/crypt/fuc/nv98.fuc b/drivers/gpu/drm/nouveau/core/engine/crypt/fuc/nv98.fuc
deleted file mode 100644 (file)
index 629da02..0000000
+++ /dev/null
@@ -1,698 +0,0 @@
-/*
- *  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)
-                       bset $r3 0x1e
-                       st b32 D[$r5] $r3
-                       add b32 $r4 0x180 - 0x60
-                       shl b32 $r4 8
-                       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/drivers/gpu/drm/nouveau/core/engine/crypt/fuc/nv98.fuc.h b/drivers/gpu/drm/nouveau/core/engine/crypt/fuc/nv98.fuc.h
deleted file mode 100644 (file)
index 38676c7..0000000
+++ /dev/null
@@ -1,584 +0,0 @@
-uint32_t nv98_pcrypt_data[] = {
-/* 0x0000: ctx_dma */
-/* 0x0000: ctx_dma_query */
-       0x00000000,
-/* 0x0004: ctx_dma_src */
-       0x00000000,
-/* 0x0008: ctx_dma_dst */
-       0x00000000,
-/* 0x000c: ctx_query_address_high */
-       0x00000000,
-/* 0x0010: ctx_query_address_low */
-       0x00000000,
-/* 0x0014: ctx_query_counter */
-       0x00000000,
-/* 0x0018: ctx_cond_address_high */
-       0x00000000,
-/* 0x001c: ctx_cond_address_low */
-       0x00000000,
-/* 0x0020: ctx_cond_off */
-       0x00000000,
-/* 0x0024: ctx_src_address_high */
-       0x00000000,
-/* 0x0028: ctx_src_address_low */
-       0x00000000,
-/* 0x002c: ctx_dst_address_high */
-       0x00000000,
-/* 0x0030: ctx_dst_address_low */
-       0x00000000,
-/* 0x0034: ctx_mode */
-       0x00000000,
-       0x00000000,
-       0x00000000,
-/* 0x0040: ctx_key */
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-/* 0x0050: ctx_iv */
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-/* 0x0080: swap */
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-/* 0x00a0: common_cmd_dtable */
-       0x0002000c,
-       0xffffff00,
-       0x00020010,
-       0x0000000f,
-       0x00020014,
-       0x00000000,
-       0x00000192,
-       0xfffffffe,
-       0x00020018,
-       0xffffff00,
-       0x0002001c,
-       0x0000000f,
-       0x000001d7,
-       0xfffffff8,
-       0x00000260,
-       0xffffffff,
-/* 0x00e0: engine_cmd_dtable */
-       0x00020040,
-       0x00000000,
-       0x00020044,
-       0x00000000,
-       0x00020048,
-       0x00000000,
-       0x0002004c,
-       0x00000000,
-       0x00020050,
-       0x00000000,
-       0x00020054,
-       0x00000000,
-       0x00020058,
-       0x00000000,
-       0x0002005c,
-       0x00000000,
-       0x00020024,
-       0xffffff00,
-       0x00020028,
-       0x0000000f,
-       0x0002002c,
-       0xffffff00,
-       0x00020030,
-       0x0000000f,
-       0x00000271,
-       0xfffffff0,
-       0x00010285,
-       0xf000000f,
-/* 0x0150: crypt_dtable */
-       0x04db0321,
-       0x04b1032f,
-       0x04db0339,
-       0x04db034b,
-       0x04db0361,
-       0x04db0377,
-       0x04db0395,
-       0x04db03af,
-       0x04db03cd,
-       0x04db03e3,
-       0x04db03f9,
-       0x04db040f,
-       0x04830429,
-       0x0483043b,
-       0x0483045d,
-       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,
-};
-
-uint32_t nv98_pcrypt_code[] = {
-       0x17f004bd,
-       0x0010fe35,
-       0xf10004fe,
-       0xf0fff017,
-       0x27f10013,
-       0x21d00400,
-       0x0c15f0c0,
-       0xf00021d0,
-       0x27f10317,
-       0x21d01200,
-       0x1031f400,
-/* 0x002f: spin */
-       0xf40031f4,
-       0x0ef40028,
-/* 0x0035: ih */
-       0x8001cffd,
-       0xb00812c4,
-       0x0bf40024,
-       0x0027f167,
-       0x002bfe77,
-       0xf00007fe,
-       0x23f00027,
-       0x0037f105,
-       0x0034cf14,
-       0xb0014594,
-       0x18f40055,
-       0x0602fa17,
-       0x4af003f8,
-       0x0034d01e,
-       0xd00147f0,
-       0x0ef48034,
-/* 0x0075: ctxload */
-       0x4034cf33,
-       0xb0014f94,
-       0x18f400f5,
-       0x0502fa21,
-       0x57f003f8,
-       0x0267f000,
-/* 0x008c: ctxload_dma_loop */
-       0xa07856bc,
-       0xb6018068,
-       0x87d00884,
-       0x0162b600,
-/* 0x009f: dummyload */
-       0xf0f018f4,
-       0x35d00257,
-/* 0x00a5: noctx */
-       0x0412c480,
-       0xf50024b0,
-       0xf100df0b,
-       0xcf190037,
-       0x33cf4032,
-       0xff24e400,
-       0x1024b607,
-       0x07bf45e4,
-       0xf50054b0,
-       0xf100b90b,
-       0xf1fae057,
-       0xb000ce67,
-       0x18f4c044,
-       0xa057f14d,
-       0x8867f1fc,
-       0x8044b000,
-       0xb03f18f4,
-       0x18f46044,
-       0x5044b019,
-       0xf1741bf4,
-       0xbd220027,
-       0x0233f034,
-       0xf50023d0,
-/* 0x0103: dma_cmd */
-       0xb000810e,
-       0x18f46344,
-       0x0245945e,
-       0xfe8050b7,
-       0x801e39f0,
-       0x40b70053,
-       0x44b60120,
-       0x0043d008,
-/* 0x0123: dtable_cmd */
-       0xb8600ef4,
-       0x18f40446,
-       0x0344b63e,
-       0x980045bb,
-       0x53fd0145,
-       0x0054b004,
-       0x58291bf4,
-       0x46580045,
-       0x0264b001,
-       0x98170bf4,
-       0x67fd0807,
-       0x0164b004,
-       0xf9300bf4,
-       0x0f01f455,
-/* 0x015b: cmd_setctx */
-       0x80280ef4,
-       0x0ef40053,
-/* 0x0161: invalid_bitfield */
-       0x0125f022,
-/* 0x0164: dispatch_error */
-/* 0x0164: illegal_mthd */
-       0x100047f1,
-       0xd00042d0,
-       0x47f04043,
-       0x0004d040,
-/* 0x0174: im_loop */
-       0xf08004cf,
-       0x44b04044,
-       0xf71bf400,
-/* 0x0180: cmddone */
-       0x1d0037f1,
-       0xd00147f0,
-/* 0x018a: nocmd */
-       0x11c40034,
-       0x4001d00c,
-/* 0x0192: cmd_query_get */
-       0x38f201f8,
-       0x0325f001,
-       0x0b0047f1,
-/* 0x019c: ptimer_retry */
-       0xcf4046cf,
-       0x47cf0045,
-       0x0467b840,
-       0x98f41bf4,
-       0x04800504,
-       0x21008020,
-       0x80220580,
-       0x0bfe2306,
-       0x03049800,
-       0xfe1844b6,
-       0x04980047,
-       0x8057f104,
-       0x0253f000,
-       0xf80645fa,
-/* 0x01d7: cmd_cond_mode */
-       0xf400f803,
-       0x25f00131,
-       0x0534b002,
-       0xf41218f4,
-       0x34b00132,
-       0x0b18f402,
-       0x800136f0,
-/* 0x01f2: return */
-       0x00f80803,
-/* 0x01f4: cmd_cond_mode_queryful */
-       0x98060498,
-       0x56c40705,
-       0x0855b6ff,
-       0xfd1844b6,
-       0x47fe0545,
-       0x000bfe00,
-       0x008057f1,
-       0xfa0253f0,
-       0x34b00565,
-       0x131bf402,
-       0x049803f8,
-       0x0044b021,
-       0x800b4cf0,
-       0x00f80804,
-/* 0x022c: cmd_cond_mode_double */
-       0xb61060b6,
-       0x65fa1050,
-       0x9803f805,
-       0x06982005,
-       0x0456b824,
-       0x980b4cf0,
-       0x06982105,
-       0x0456b825,
-       0xfd0b5cf0,
-       0x34b00445,
-       0x0b5cf003,
-       0x800645fd,
-       0x00f80804,
-/* 0x0260: cmd_wrcache_flush */
-       0xf10132f4,
-       0xbd220027,
-       0x0133f034,
-       0xf80023d0,
-/* 0x0271: crypt_cmd_mode */
-       0x0131f400,
-       0xb00225f0,
-       0x18f40f34,
-       0x0132f409,
-/* 0x0283: crypt_cmd_mode_return */
-       0xf80d0380,
-/* 0x0285: crypt_cmd_length */
-       0x0034b000,
-       0xf4fb0bf4,
-       0x47f0033c,
-       0x0743f040,
-       0xf00604fa,
-       0x43f05047,
-       0x0604fa06,
-       0x3cf503f8,
-       0x47f1c407,
-       0x4bfe2100,
-       0x09049800,
-       0x950a0598,
-       0x44b60858,
-       0x0548fd18,
-       0x98ff55c4,
-       0x07980b06,
-       0x0878950c,
-       0xfd1864b6,
-       0x77c40568,
-       0x0d0898ff,
-       0x580284b6,
-       0x95f9a889,
-       0xf9a98958,
-       0x013cf495,
-       0x3cf403f8,
-       0xf803f861,
-       0x18489503,
-       0xbb084994,
-       0x81b60095,
-       0x09088000,
-       0x950a0980,
-       0x69941868,
-       0x0097bb08,
-       0x800081b6,
-       0x09800b08,
-       0x023cf40c,
-       0xf05047f0,
-       0x04fa0643,
-       0xf803f805,
-/* 0x0321: crypt_copy_prep */
-       0x203cf500,
-       0x003cf594,
-       0x003cf588,
-/* 0x032f: crypt_store_prep */
-       0xf500f88c,
-       0xf594103c,
-       0xf88c063c,
-/* 0x0339: crypt_ecb_e_prep */
-       0x303cf500,
-       0x003cf594,
-       0x003cf588,
-       0x003cf5d0,
-/* 0x034b: crypt_ecb_d_prep */
-       0xf500f88c,
-       0xf5c8773c,
-       0xf594303c,
-       0xf588003c,
-       0xf5d4003c,
-       0xf88c003c,
-/* 0x0361: crypt_cbc_e_prep */
-       0x403cf500,
-       0x003cf594,
-       0x063cf588,
-       0x663cf5ac,
-       0x063cf5d0,
-/* 0x0377: crypt_cbc_d_prep */
-       0xf500f88c,
-       0xf5c8773c,
-       0xf594503c,
-       0xf584623c,
-       0xf588063c,
-       0xf5d4603c,
-       0xf5ac203c,
-       0xf88c003c,
-/* 0x0395: crypt_pcbc_e_prep */
-       0x503cf500,
-       0x003cf594,
-       0x063cf588,
-       0x663cf5ac,
-       0x063cf5d0,
-       0x063cf58c,
-/* 0x03af: crypt_pcbc_d_prep */
-       0xf500f8ac,
-       0xf5c8773c,
-       0xf594503c,
-       0xf588003c,
-       0xf5d4013c,
-       0xf5ac163c,
-       0xf58c063c,
-       0xf8ac063c,
-/* 0x03cd: crypt_cfb_e_prep */
-       0x403cf500,
-       0x663cf594,
-       0x003cf5d0,
-       0x063cf588,
-       0x063cf5ac,
-/* 0x03e3: crypt_cfb_d_prep */
-       0xf500f88c,
-       0xf594403c,
-       0xf5d0603c,
-       0xf588063c,
-       0xf5ac603c,
-       0xf88c003c,
-/* 0x03f9: crypt_ofb_prep */
-       0x403cf500,
-       0x663cf594,
-       0x003cf5d0,
-       0x603cf588,
-       0x003cf5ac,
-/* 0x040f: crypt_ctr_prep */
-       0xf500f88c,
-       0xf594503c,
-       0xf5d0613c,
-       0xf5b0163c,
-       0xf588003c,
-       0xf5ac103c,
-       0xf88c003c,
-/* 0x0429: crypt_cbc_mac_prep */
-       0x303cf500,
-       0x003cf594,
-       0x063cf588,
-       0x663cf5ac,
-/* 0x043b: crypt_cmac_finish_complete_prep */
-       0xf500f8d0,
-       0xf594703c,
-       0xf588003c,
-       0xf5ac063c,
-       0xf5ac003c,
-       0xf5d0003c,
-       0xf5bc003c,
-       0xf5ac063c,
-       0xf8d0663c,
-/* 0x045d: crypt_cmac_finish_partial_prep */
-       0x803cf500,
-       0x003cf594,
-       0x063cf588,
-       0x003cf5ac,
-       0x003cf5ac,
-       0x003cf5d0,
-       0x003cf5bc,
-       0x063cf5bc,
-       0x663cf5ac,
-/* 0x0483: crypt_do_in */
-       0xbb00f8d0,
-       0x47fe0035,
-       0x8097f100,
-       0x0293f000,
-/* 0x0490: crypt_do_in_loop */
-       0xf80559fa,
-       0x223cf403,
-       0xf50609fa,
-       0xf898103c,
-       0x1050b603,
-       0xf40453b8,
-       0x3cf4e91b,
-       0xf803f801,
-/* 0x04b1: crypt_do_out */
-       0x0037bb00,
-       0xf10067fe,
-       0xf0008097,
-/* 0x04be: crypt_do_out_loop */
-       0x3cf50293,
-       0x3cf49810,
-       0x0579fa61,
-       0xf40679fa,
-       0x03f8013c,
-       0xb81070b6,
-       0x1bf40473,
-/* 0x04db: crypt_do_inout */
-       0xbb00f8e8,
-       0x97f10035,
-       0x93f00080,
-/* 0x04e5: crypt_do_inout_loop */
-       0x0047fe02,
-       0xf80559fa,
-       0x213cf403,
-       0xf50609fa,
-       0xf498103c,
-       0x67fe613c,
-       0x0579fa00,
-       0xf40679fa,
-       0x03f8013c,
-       0xb61050b6,
-       0x53b81070,
-       0xd41bf404,
-       0x000000f8,
-       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,
-};
diff --git a/drivers/gpu/drm/nouveau/core/engine/crypt/nv84.c b/drivers/gpu/drm/nouveau/core/engine/crypt/nv84.c
deleted file mode 100644 (file)
index ea5c42f..0000000
+++ /dev/null
@@ -1,188 +0,0 @@
-/*
- * Copyright 2012 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 <core/client.h>
-#include <core/os.h>
-#include <core/enum.h>
-#include <core/engctx.h>
-#include <core/gpuobj.h>
-
-#include <subdev/fb.h>
-
-#include <engine/fifo.h>
-#include <engine/crypt.h>
-
-struct nv84_crypt_priv {
-       struct nouveau_engine base;
-};
-
-/*******************************************************************************
- * Crypt object classes
- ******************************************************************************/
-
-static int
-nv84_crypt_object_ctor(struct nouveau_object *parent,
-                      struct nouveau_object *engine,
-                      struct nouveau_oclass *oclass, void *data, u32 size,
-                      struct nouveau_object **pobject)
-{
-       struct nouveau_gpuobj *obj;
-       int ret;
-
-       ret = nouveau_gpuobj_create(parent, engine, oclass, 0, parent,
-                                   16, 16, 0, &obj);
-       *pobject = nv_object(obj);
-       if (ret)
-               return ret;
-
-       nv_wo32(obj, 0x00, nv_mclass(obj));
-       nv_wo32(obj, 0x04, 0x00000000);
-       nv_wo32(obj, 0x08, 0x00000000);
-       nv_wo32(obj, 0x0c, 0x00000000);
-       return 0;
-}
-
-static struct nouveau_ofuncs
-nv84_crypt_ofuncs = {
-       .ctor = nv84_crypt_object_ctor,
-       .dtor = _nouveau_gpuobj_dtor,
-       .init = _nouveau_gpuobj_init,
-       .fini = _nouveau_gpuobj_fini,
-       .rd32 = _nouveau_gpuobj_rd32,
-       .wr32 = _nouveau_gpuobj_wr32,
-};
-
-static struct nouveau_oclass
-nv84_crypt_sclass[] = {
-       { 0x74c1, &nv84_crypt_ofuncs },
-       {}
-};
-
-/*******************************************************************************
- * PCRYPT context
- ******************************************************************************/
-
-static struct nouveau_oclass
-nv84_crypt_cclass = {
-       .handle = NV_ENGCTX(CRYPT, 0x84),
-       .ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = _nouveau_engctx_ctor,
-               .dtor = _nouveau_engctx_dtor,
-               .init = _nouveau_engctx_init,
-               .fini = _nouveau_engctx_fini,
-               .rd32 = _nouveau_engctx_rd32,
-               .wr32 = _nouveau_engctx_wr32,
-       },
-};
-
-/*******************************************************************************
- * PCRYPT engine/subdev functions
- ******************************************************************************/
-
-static const struct nouveau_bitfield nv84_crypt_intr_mask[] = {
-       { 0x00000001, "INVALID_STATE" },
-       { 0x00000002, "ILLEGAL_MTHD" },
-       { 0x00000004, "ILLEGAL_CLASS" },
-       { 0x00000080, "QUERY" },
-       { 0x00000100, "FAULT" },
-       {}
-};
-
-static void
-nv84_crypt_intr(struct nouveau_subdev *subdev)
-{
-       struct nouveau_fifo *pfifo = nouveau_fifo(subdev);
-       struct nouveau_engine *engine = nv_engine(subdev);
-       struct nouveau_object *engctx;
-       struct nv84_crypt_priv *priv = (void *)subdev;
-       u32 stat = nv_rd32(priv, 0x102130);
-       u32 mthd = nv_rd32(priv, 0x102190);
-       u32 data = nv_rd32(priv, 0x102194);
-       u32 inst = nv_rd32(priv, 0x102188) & 0x7fffffff;
-       int chid;
-
-       engctx = nouveau_engctx_get(engine, inst);
-       chid   = pfifo->chid(pfifo, engctx);
-
-       if (stat) {
-               nv_error(priv, "%s", "");
-               nouveau_bitfield_print(nv84_crypt_intr_mask, stat);
-               pr_cont(" ch %d [0x%010llx %s] mthd 0x%04x data 0x%08x\n",
-                      chid, (u64)inst << 12, nouveau_client_name(engctx),
-                      mthd, data);
-       }
-
-       nv_wr32(priv, 0x102130, stat);
-       nv_wr32(priv, 0x10200c, 0x10);
-
-       nouveau_engctx_put(engctx);
-}
-
-static int
-nv84_crypt_ctor(struct nouveau_object *parent, struct nouveau_object *engine,
-              struct nouveau_oclass *oclass, void *data, u32 size,
-              struct nouveau_object **pobject)
-{
-       struct nv84_crypt_priv *priv;
-       int ret;
-
-       ret = nouveau_engine_create(parent, engine, oclass, true,
-                                   "PCRYPT", "crypt", &priv);
-       *pobject = nv_object(priv);
-       if (ret)
-               return ret;
-
-       nv_subdev(priv)->unit = 0x00004000;
-       nv_subdev(priv)->intr = nv84_crypt_intr;
-       nv_engine(priv)->cclass = &nv84_crypt_cclass;
-       nv_engine(priv)->sclass = nv84_crypt_sclass;
-       return 0;
-}
-
-static int
-nv84_crypt_init(struct nouveau_object *object)
-{
-       struct nv84_crypt_priv *priv = (void *)object;
-       int ret;
-
-       ret = nouveau_engine_init(&priv->base);
-       if (ret)
-               return ret;
-
-       nv_wr32(priv, 0x102130, 0xffffffff);
-       nv_wr32(priv, 0x102140, 0xffffffbf);
-       nv_wr32(priv, 0x10200c, 0x00000010);
-       return 0;
-}
-
-struct nouveau_oclass
-nv84_crypt_oclass = {
-       .handle = NV_ENGINE(CRYPT, 0x84),
-       .ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nv84_crypt_ctor,
-               .dtor = _nouveau_engine_dtor,
-               .init = nv84_crypt_init,
-               .fini = _nouveau_engine_fini,
-       },
-};
diff --git a/drivers/gpu/drm/nouveau/core/engine/crypt/nv98.c b/drivers/gpu/drm/nouveau/core/engine/crypt/nv98.c
deleted file mode 100644 (file)
index 5571c09..0000000
+++ /dev/null
@@ -1,156 +0,0 @@
-/*
- * Copyright 2012 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 <core/client.h>
-#include <core/os.h>
-#include <core/enum.h>
-#include <core/engctx.h>
-
-#include <subdev/timer.h>
-#include <subdev/fb.h>
-
-#include <engine/falcon.h>
-#include <engine/fifo.h>
-#include <engine/crypt.h>
-
-#include "fuc/nv98.fuc.h"
-
-struct nv98_crypt_priv {
-       struct nouveau_falcon base;
-};
-
-/*******************************************************************************
- * Crypt object classes
- ******************************************************************************/
-
-static struct nouveau_oclass
-nv98_crypt_sclass[] = {
-       { 0x88b4, &nouveau_object_ofuncs },
-       {},
-};
-
-/*******************************************************************************
- * PCRYPT context
- ******************************************************************************/
-
-static struct nouveau_oclass
-nv98_crypt_cclass = {
-       .handle = NV_ENGCTX(CRYPT, 0x98),
-       .ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = _nouveau_falcon_context_ctor,
-               .dtor = _nouveau_falcon_context_dtor,
-               .init = _nouveau_falcon_context_init,
-               .fini = _nouveau_falcon_context_fini,
-               .rd32 = _nouveau_falcon_context_rd32,
-               .wr32 = _nouveau_falcon_context_wr32,
-       },
-};
-
-/*******************************************************************************
- * PCRYPT engine/subdev functions
- ******************************************************************************/
-
-static const struct nouveau_enum nv98_crypt_isr_error_name[] = {
-       { 0x0000, "ILLEGAL_MTHD" },
-       { 0x0001, "INVALID_BITFIELD" },
-       { 0x0002, "INVALID_ENUM" },
-       { 0x0003, "QUERY" },
-       {}
-};
-
-static void
-nv98_crypt_intr(struct nouveau_subdev *subdev)
-{
-       struct nouveau_fifo *pfifo = nouveau_fifo(subdev);
-       struct nouveau_engine *engine = nv_engine(subdev);
-       struct nouveau_object *engctx;
-       struct nv98_crypt_priv *priv = (void *)subdev;
-       u32 disp = nv_rd32(priv, 0x08701c);
-       u32 stat = nv_rd32(priv, 0x087008) & disp & ~(disp >> 16);
-       u32 inst = nv_rd32(priv, 0x087050) & 0x3fffffff;
-       u32 ssta = nv_rd32(priv, 0x087040) & 0x0000ffff;
-       u32 addr = nv_rd32(priv, 0x087040) >> 16;
-       u32 mthd = (addr & 0x07ff) << 2;
-       u32 subc = (addr & 0x3800) >> 11;
-       u32 data = nv_rd32(priv, 0x087044);
-       int chid;
-
-       engctx = nouveau_engctx_get(engine, inst);
-       chid   = pfifo->chid(pfifo, engctx);
-
-       if (stat & 0x00000040) {
-               nv_error(priv, "DISPATCH_ERROR [");
-               nouveau_enum_print(nv98_crypt_isr_error_name, ssta);
-               pr_cont("] ch %d [0x%010llx %s] subc %d mthd 0x%04x data 0x%08x\n",
-                      chid, (u64)inst << 12, nouveau_client_name(engctx),
-                      subc, mthd, data);
-               nv_wr32(priv, 0x087004, 0x00000040);
-               stat &= ~0x00000040;
-       }
-
-       if (stat) {
-               nv_error(priv, "unhandled intr 0x%08x\n", stat);
-               nv_wr32(priv, 0x087004, stat);
-       }
-
-       nouveau_engctx_put(engctx);
-}
-
-static int
-nv98_crypt_ctor(struct nouveau_object *parent, struct nouveau_object *engine,
-              struct nouveau_oclass *oclass, void *data, u32 size,
-              struct nouveau_object **pobject)
-{
-       struct nv98_crypt_priv *priv;
-       int ret;
-
-       ret = nouveau_falcon_create(parent, engine, oclass, 0x087000, true,
-                                   "PCRYPT", "crypt", &priv);
-       *pobject = nv_object(priv);
-       if (ret)
-               return ret;
-
-       nv_subdev(priv)->unit = 0x00004000;
-       nv_subdev(priv)->intr = nv98_crypt_intr;
-       nv_engine(priv)->cclass = &nv98_crypt_cclass;
-       nv_engine(priv)->sclass = nv98_crypt_sclass;
-       nv_falcon(priv)->code.data = nv98_pcrypt_code;
-       nv_falcon(priv)->code.size = sizeof(nv98_pcrypt_code);
-       nv_falcon(priv)->data.data = nv98_pcrypt_data;
-       nv_falcon(priv)->data.size = sizeof(nv98_pcrypt_data);
-       return 0;
-}
-
-struct nouveau_oclass
-nv98_crypt_oclass = {
-       .handle = NV_ENGINE(CRYPT, 0x98),
-       .ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nv98_crypt_ctor,
-               .dtor = _nouveau_falcon_dtor,
-               .init = _nouveau_falcon_init,
-               .fini = _nouveau_falcon_fini,
-               .rd32 = _nouveau_falcon_rd32,
-               .wr32 = _nouveau_falcon_wr32,
-       },
-};
diff --git a/drivers/gpu/drm/nouveau/core/engine/device/acpi.c b/drivers/gpu/drm/nouveau/core/engine/device/acpi.c
deleted file mode 100644 (file)
index 4dbf0ba..0000000
+++ /dev/null
@@ -1,59 +0,0 @@
-/*
- * Copyright 2014 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 "acpi.h"
-
-#ifdef CONFIG_ACPI
-static int
-nvkm_acpi_ntfy(struct notifier_block *nb, unsigned long val, void *data)
-{
-       struct nouveau_device *device =
-               container_of(nb, typeof(*device), acpi.nb);
-       struct acpi_bus_event *info = data;
-
-       if (!strcmp(info->device_class, "ac_adapter"))
-               nvkm_event_send(&device->event, 1, 0, NULL, 0);
-
-       return NOTIFY_DONE;
-}
-#endif
-
-int
-nvkm_acpi_fini(struct nouveau_device *device, bool suspend)
-{
-#ifdef CONFIG_ACPI
-       unregister_acpi_notifier(&device->acpi.nb);
-#endif
-       return 0;
-}
-
-int
-nvkm_acpi_init(struct nouveau_device *device)
-{
-#ifdef CONFIG_ACPI
-       device->acpi.nb.notifier_call = nvkm_acpi_ntfy;
-       register_acpi_notifier(&device->acpi.nb);
-#endif
-       return 0;
-}
diff --git a/drivers/gpu/drm/nouveau/core/engine/device/acpi.h b/drivers/gpu/drm/nouveau/core/engine/device/acpi.h
deleted file mode 100644 (file)
index cc49f4f..0000000
+++ /dev/null
@@ -1,9 +0,0 @@
-#ifndef __NVKM_DEVICE_ACPI_H__
-#define __NVKM_DEVICE_ACPI_H__
-
-#include <engine/device.h>
-
-int nvkm_acpi_init(struct nouveau_device *);
-int nvkm_acpi_fini(struct nouveau_device *, bool);
-
-#endif
diff --git a/drivers/gpu/drm/nouveau/core/engine/device/base.c b/drivers/gpu/drm/nouveau/core/engine/device/base.c
deleted file mode 100644 (file)
index 137e0b0..0000000
+++ /dev/null
@@ -1,715 +0,0 @@
-/*
- * Copyright 2012 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 <core/object.h>
-#include <core/device.h>
-#include <core/client.h>
-#include <core/option.h>
-#include <nvif/unpack.h>
-#include <nvif/class.h>
-
-#include <subdev/bios.h>
-#include <subdev/fb.h>
-#include <subdev/instmem.h>
-
-#include "priv.h"
-#include "acpi.h"
-
-static DEFINE_MUTEX(nv_devices_mutex);
-static LIST_HEAD(nv_devices);
-
-struct nouveau_device *
-nouveau_device_find(u64 name)
-{
-       struct nouveau_device *device, *match = NULL;
-       mutex_lock(&nv_devices_mutex);
-       list_for_each_entry(device, &nv_devices, head) {
-               if (device->handle == name) {
-                       match = device;
-                       break;
-               }
-       }
-       mutex_unlock(&nv_devices_mutex);
-       return match;
-}
-
-int
-nouveau_device_list(u64 *name, int size)
-{
-       struct nouveau_device *device;
-       int nr = 0;
-       mutex_lock(&nv_devices_mutex);
-       list_for_each_entry(device, &nv_devices, head) {
-               if (nr++ < size)
-                       name[nr - 1] = device->handle;
-       }
-       mutex_unlock(&nv_devices_mutex);
-       return nr;
-}
-
-/******************************************************************************
- * nouveau_devobj (0x0080): class implementation
- *****************************************************************************/
-
-struct nouveau_devobj {
-       struct nouveau_parent base;
-       struct nouveau_object *subdev[NVDEV_SUBDEV_NR];
-};
-
-static int
-nouveau_devobj_info(struct nouveau_object *object, void *data, u32 size)
-{
-       struct nouveau_device *device = nv_device(object);
-       struct nouveau_fb *pfb = nouveau_fb(device);
-       struct nouveau_instmem *imem = nouveau_instmem(device);
-       union {
-               struct nv_device_info_v0 v0;
-       } *args = data;
-       int ret;
-
-       nv_ioctl(object, "device info size %d\n", size);
-       if (nvif_unpack(args->v0, 0, 0, false)) {
-               nv_ioctl(object, "device info vers %d\n", args->v0.version);
-       } else
-               return ret;
-
-       switch (device->chipset) {
-       case 0x01a:
-       case 0x01f:
-       case 0x04c:
-       case 0x04e:
-       case 0x063:
-       case 0x067:
-       case 0x068:
-       case 0x0aa:
-       case 0x0ac:
-       case 0x0af:
-               args->v0.platform = NV_DEVICE_INFO_V0_IGP;
-               break;
-       default:
-               if (device->pdev) {
-                       if (pci_find_capability(device->pdev, PCI_CAP_ID_AGP))
-                               args->v0.platform = NV_DEVICE_INFO_V0_AGP;
-                       else
-                       if (pci_is_pcie(device->pdev))
-                               args->v0.platform = NV_DEVICE_INFO_V0_PCIE;
-                       else
-                               args->v0.platform = NV_DEVICE_INFO_V0_PCI;
-               } else {
-                       args->v0.platform = NV_DEVICE_INFO_V0_SOC;
-               }
-               break;
-       }
-
-       switch (device->card_type) {
-       case NV_04: args->v0.family = NV_DEVICE_INFO_V0_TNT; break;
-       case NV_10:
-       case NV_11: args->v0.family = NV_DEVICE_INFO_V0_CELSIUS; break;
-       case NV_20: args->v0.family = NV_DEVICE_INFO_V0_KELVIN; break;
-       case NV_30: args->v0.family = NV_DEVICE_INFO_V0_RANKINE; break;
-       case NV_40: args->v0.family = NV_DEVICE_INFO_V0_CURIE; break;
-       case NV_50: args->v0.family = NV_DEVICE_INFO_V0_TESLA; break;
-       case NV_C0: args->v0.family = NV_DEVICE_INFO_V0_FERMI; break;
-       case NV_E0: args->v0.family = NV_DEVICE_INFO_V0_KEPLER; break;
-       case GM100: args->v0.family = NV_DEVICE_INFO_V0_MAXWELL; break;
-       default:
-               args->v0.family = 0;
-               break;
-       }
-
-       args->v0.chipset  = device->chipset;
-       args->v0.revision = device->chiprev;
-       if (pfb)  args->v0.ram_size = args->v0.ram_user = pfb->ram->size;
-       else      args->v0.ram_size = args->v0.ram_user = 0;
-       if (imem) args->v0.ram_user = args->v0.ram_user - imem->reserved;
-       return 0;
-}
-
-static int
-nouveau_devobj_mthd(struct nouveau_object *object, u32 mthd,
-                   void *data, u32 size)
-{
-       switch (mthd) {
-       case NV_DEVICE_V0_INFO:
-               return nouveau_devobj_info(object, data, size);
-       default:
-               break;
-       }
-       return -EINVAL;
-}
-
-static u8
-nouveau_devobj_rd08(struct nouveau_object *object, u64 addr)
-{
-       return nv_rd08(object->engine, addr);
-}
-
-static u16
-nouveau_devobj_rd16(struct nouveau_object *object, u64 addr)
-{
-       return nv_rd16(object->engine, addr);
-}
-
-static u32
-nouveau_devobj_rd32(struct nouveau_object *object, u64 addr)
-{
-       return nv_rd32(object->engine, addr);
-}
-
-static void
-nouveau_devobj_wr08(struct nouveau_object *object, u64 addr, u8 data)
-{
-       nv_wr08(object->engine, addr, data);
-}
-
-static void
-nouveau_devobj_wr16(struct nouveau_object *object, u64 addr, u16 data)
-{
-       nv_wr16(object->engine, addr, data);
-}
-
-static void
-nouveau_devobj_wr32(struct nouveau_object *object, u64 addr, u32 data)
-{
-       nv_wr32(object->engine, addr, data);
-}
-
-static int
-nouveau_devobj_map(struct nouveau_object *object, u64 *addr, u32 *size)
-{
-       struct nouveau_device *device = nv_device(object);
-       *addr = nv_device_resource_start(device, 0);
-       *size = nv_device_resource_len(device, 0);
-       return 0;
-}
-
-static const u64 disable_map[] = {
-       [NVDEV_SUBDEV_VBIOS]    = NV_DEVICE_V0_DISABLE_VBIOS,
-       [NVDEV_SUBDEV_DEVINIT]  = NV_DEVICE_V0_DISABLE_CORE,
-       [NVDEV_SUBDEV_GPIO]     = NV_DEVICE_V0_DISABLE_CORE,
-       [NVDEV_SUBDEV_I2C]      = NV_DEVICE_V0_DISABLE_CORE,
-       [NVDEV_SUBDEV_CLOCK]    = NV_DEVICE_V0_DISABLE_CORE,
-       [NVDEV_SUBDEV_MXM]      = NV_DEVICE_V0_DISABLE_CORE,
-       [NVDEV_SUBDEV_MC]       = NV_DEVICE_V0_DISABLE_CORE,
-       [NVDEV_SUBDEV_BUS]      = NV_DEVICE_V0_DISABLE_CORE,
-       [NVDEV_SUBDEV_TIMER]    = NV_DEVICE_V0_DISABLE_CORE,
-       [NVDEV_SUBDEV_FB]       = NV_DEVICE_V0_DISABLE_CORE,
-       [NVDEV_SUBDEV_LTC]      = NV_DEVICE_V0_DISABLE_CORE,
-       [NVDEV_SUBDEV_IBUS]     = NV_DEVICE_V0_DISABLE_CORE,
-       [NVDEV_SUBDEV_INSTMEM]  = NV_DEVICE_V0_DISABLE_CORE,
-       [NVDEV_SUBDEV_VM]       = NV_DEVICE_V0_DISABLE_CORE,
-       [NVDEV_SUBDEV_BAR]      = NV_DEVICE_V0_DISABLE_CORE,
-       [NVDEV_SUBDEV_VOLT]     = NV_DEVICE_V0_DISABLE_CORE,
-       [NVDEV_SUBDEV_THERM]    = NV_DEVICE_V0_DISABLE_CORE,
-       [NVDEV_SUBDEV_PWR]      = NV_DEVICE_V0_DISABLE_CORE,
-       [NVDEV_SUBDEV_FUSE]     = NV_DEVICE_V0_DISABLE_CORE,
-       [NVDEV_ENGINE_DMAOBJ]   = NV_DEVICE_V0_DISABLE_CORE,
-       [NVDEV_ENGINE_PERFMON]  = NV_DEVICE_V0_DISABLE_CORE,
-       [NVDEV_ENGINE_FIFO]     = NV_DEVICE_V0_DISABLE_FIFO,
-       [NVDEV_ENGINE_SW]       = NV_DEVICE_V0_DISABLE_FIFO,
-       [NVDEV_ENGINE_GR]       = NV_DEVICE_V0_DISABLE_GRAPH,
-       [NVDEV_ENGINE_MPEG]     = NV_DEVICE_V0_DISABLE_MPEG,
-       [NVDEV_ENGINE_ME]       = NV_DEVICE_V0_DISABLE_ME,
-       [NVDEV_ENGINE_VP]       = NV_DEVICE_V0_DISABLE_VP,
-       [NVDEV_ENGINE_CRYPT]    = NV_DEVICE_V0_DISABLE_CRYPT,
-       [NVDEV_ENGINE_BSP]      = NV_DEVICE_V0_DISABLE_BSP,
-       [NVDEV_ENGINE_PPP]      = NV_DEVICE_V0_DISABLE_PPP,
-       [NVDEV_ENGINE_COPY0]    = NV_DEVICE_V0_DISABLE_COPY0,
-       [NVDEV_ENGINE_COPY1]    = NV_DEVICE_V0_DISABLE_COPY1,
-       [NVDEV_ENGINE_COPY2]    = NV_DEVICE_V0_DISABLE_COPY1,
-       [NVDEV_ENGINE_VIC]      = NV_DEVICE_V0_DISABLE_VIC,
-       [NVDEV_ENGINE_VENC]     = NV_DEVICE_V0_DISABLE_VENC,
-       [NVDEV_ENGINE_DISP]     = NV_DEVICE_V0_DISABLE_DISP,
-       [NVDEV_SUBDEV_NR]       = 0,
-};
-
-static void
-nouveau_devobj_dtor(struct nouveau_object *object)
-{
-       struct nouveau_devobj *devobj = (void *)object;
-       int i;
-
-       for (i = NVDEV_SUBDEV_NR - 1; i >= 0; i--)
-               nouveau_object_ref(NULL, &devobj->subdev[i]);
-
-       nouveau_parent_destroy(&devobj->base);
-}
-
-static struct nouveau_oclass
-nouveau_devobj_oclass_super = {
-       .handle = NV_DEVICE,
-       .ofuncs = &(struct nouveau_ofuncs) {
-               .dtor = nouveau_devobj_dtor,
-               .init = _nouveau_parent_init,
-               .fini = _nouveau_parent_fini,
-               .mthd = nouveau_devobj_mthd,
-               .map  = nouveau_devobj_map,
-               .rd08 = nouveau_devobj_rd08,
-               .rd16 = nouveau_devobj_rd16,
-               .rd32 = nouveau_devobj_rd32,
-               .wr08 = nouveau_devobj_wr08,
-               .wr16 = nouveau_devobj_wr16,
-               .wr32 = nouveau_devobj_wr32,
-       }
-};
-
-static int
-nouveau_devobj_ctor(struct nouveau_object *parent,
-                   struct nouveau_object *engine,
-                   struct nouveau_oclass *oclass, void *data, u32 size,
-                   struct nouveau_object **pobject)
-{
-       union {
-               struct nv_device_v0 v0;
-       } *args = data;
-       struct nouveau_client *client = nv_client(parent);
-       struct nouveau_device *device;
-       struct nouveau_devobj *devobj;
-       u32 boot0, strap;
-       u64 disable, mmio_base, mmio_size;
-       void __iomem *map;
-       int ret, i, c;
-
-       nv_ioctl(parent, "create device size %d\n", size);
-       if (nvif_unpack(args->v0, 0, 0, false)) {
-               nv_ioctl(parent, "create device v%d device %016llx "
-                                "disable %016llx debug0 %016llx\n",
-                        args->v0.version, args->v0.device,
-                        args->v0.disable, args->v0.debug0);
-       } else
-               return ret;
-
-       /* give priviledged clients register access */
-       if (client->super)
-               oclass = &nouveau_devobj_oclass_super;
-
-       /* find the device subdev that matches what the client requested */
-       device = nv_device(client->device);
-       if (args->v0.device != ~0) {
-               device = nouveau_device_find(args->v0.device);
-               if (!device)
-                       return -ENODEV;
-       }
-
-       ret = nouveau_parent_create(parent, nv_object(device), oclass, 0,
-                                   nouveau_control_oclass,
-                                   (1ULL << NVDEV_ENGINE_DMAOBJ) |
-                                   (1ULL << NVDEV_ENGINE_FIFO) |
-                                   (1ULL << NVDEV_ENGINE_DISP) |
-                                   (1ULL << NVDEV_ENGINE_PERFMON), &devobj);
-       *pobject = nv_object(devobj);
-       if (ret)
-               return ret;
-
-       mmio_base = nv_device_resource_start(device, 0);
-       mmio_size = nv_device_resource_len(device, 0);
-
-       /* translate api disable mask into internal mapping */
-       disable = args->v0.debug0;
-       for (i = 0; i < NVDEV_SUBDEV_NR; i++) {
-               if (args->v0.disable & disable_map[i])
-                       disable |= (1ULL << i);
-       }
-
-       /* identify the chipset, and determine classes of subdev/engines */
-       if (!(args->v0.disable & NV_DEVICE_V0_DISABLE_IDENTIFY) &&
-           !device->card_type) {
-               map = ioremap(mmio_base, 0x102000);
-               if (map == NULL)
-                       return -ENOMEM;
-
-               /* switch mmio to cpu's native endianness */
-#ifndef __BIG_ENDIAN
-               if (ioread32_native(map + 0x000004) != 0x00000000)
-#else
-               if (ioread32_native(map + 0x000004) == 0x00000000)
-#endif
-                       iowrite32_native(0x01000001, map + 0x000004);
-
-               /* read boot0 and strapping information */
-               boot0 = ioread32_native(map + 0x000000);
-               strap = ioread32_native(map + 0x101000);
-               iounmap(map);
-
-               /* determine chipset and derive architecture from it */
-               if ((boot0 & 0x1f000000) > 0) {
-                       device->chipset = (boot0 & 0x1ff00000) >> 20;
-                       device->chiprev = (boot0 & 0x000000ff);
-                       switch (device->chipset & 0x1f0) {
-                       case 0x010: {
-                               if (0x461 & (1 << (device->chipset & 0xf)))
-                                       device->card_type = NV_10;
-                               else
-                                       device->card_type = NV_11;
-                               device->chiprev = 0x00;
-                               break;
-                       }
-                       case 0x020: device->card_type = NV_20; break;
-                       case 0x030: device->card_type = NV_30; break;
-                       case 0x040:
-                       case 0x060: device->card_type = NV_40; break;
-                       case 0x050:
-                       case 0x080:
-                       case 0x090:
-                       case 0x0a0: device->card_type = NV_50; break;
-                       case 0x0c0:
-                       case 0x0d0: device->card_type = NV_C0; break;
-                       case 0x0e0:
-                       case 0x0f0:
-                       case 0x100: device->card_type = NV_E0; break;
-                       case 0x110:
-                       case 0x120: device->card_type = GM100; break;
-                       default:
-                               break;
-                       }
-               } else
-               if ((boot0 & 0xff00fff0) == 0x20004000) {
-                       if (boot0 & 0x00f00000)
-                               device->chipset = 0x05;
-                       else
-                               device->chipset = 0x04;
-                       device->card_type = NV_04;
-               }
-
-               switch (device->card_type) {
-               case NV_04: ret = nv04_identify(device); break;
-               case NV_10:
-               case NV_11: ret = nv10_identify(device); break;
-               case NV_20: ret = nv20_identify(device); break;
-               case NV_30: ret = nv30_identify(device); break;
-               case NV_40: ret = nv40_identify(device); break;
-               case NV_50: ret = nv50_identify(device); break;
-               case NV_C0: ret = nvc0_identify(device); break;
-               case NV_E0: ret = nve0_identify(device); break;
-               case GM100: ret = gm100_identify(device); break;
-               default:
-                       ret = -EINVAL;
-                       break;
-               }
-
-               if (ret) {
-                       nv_error(device, "unknown chipset, 0x%08x\n", boot0);
-                       return ret;
-               }
-
-               nv_info(device, "BOOT0  : 0x%08x\n", boot0);
-               nv_info(device, "Chipset: %s (NV%02X)\n",
-                       device->cname, device->chipset);
-               nv_info(device, "Family : NV%02X\n", device->card_type);
-
-               /* determine frequency of timing crystal */
-               if ( device->card_type <= NV_10 || device->chipset < 0x17 ||
-                   (device->chipset >= 0x20 && device->chipset < 0x25))
-                       strap &= 0x00000040;
-               else
-                       strap &= 0x00400040;
-
-               switch (strap) {
-               case 0x00000000: device->crystal = 13500; break;
-               case 0x00000040: device->crystal = 14318; break;
-               case 0x00400000: device->crystal = 27000; break;
-               case 0x00400040: device->crystal = 25000; break;
-               }
-
-               nv_debug(device, "crystal freq: %dKHz\n", device->crystal);
-       } else
-       if ( (args->v0.disable & NV_DEVICE_V0_DISABLE_IDENTIFY)) {
-               device->cname = "NULL";
-               device->oclass[NVDEV_SUBDEV_VBIOS] = &nouveau_bios_oclass;
-       }
-
-       if (!(args->v0.disable & NV_DEVICE_V0_DISABLE_MMIO) &&
-           !nv_subdev(device)->mmio) {
-               nv_subdev(device)->mmio  = ioremap(mmio_base, mmio_size);
-               if (!nv_subdev(device)->mmio) {
-                       nv_error(device, "unable to map device registers\n");
-                       return -ENOMEM;
-               }
-       }
-
-       /* ensure requested subsystems are available for use */
-       for (i = 1, c = 1; i < NVDEV_SUBDEV_NR; i++) {
-               if (!(oclass = device->oclass[i]) || (disable & (1ULL << i)))
-                       continue;
-
-               if (device->subdev[i]) {
-                       nouveau_object_ref(device->subdev[i],
-                                         &devobj->subdev[i]);
-                       continue;
-               }
-
-               ret = nouveau_object_ctor(nv_object(device), NULL,
-                                         oclass, NULL, i,
-                                         &devobj->subdev[i]);
-               if (ret == -ENODEV)
-                       continue;
-               if (ret)
-                       return ret;
-
-               device->subdev[i] = devobj->subdev[i];
-
-               /* note: can't init *any* subdevs until devinit has been run
-                * due to not knowing exactly what the vbios init tables will
-                * mess with.  devinit also can't be run until all of its
-                * dependencies have been created.
-                *
-                * this code delays init of any subdev until all of devinit's
-                * dependencies have been created, and then initialises each
-                * subdev in turn as they're created.
-                */
-               while (i >= NVDEV_SUBDEV_DEVINIT_LAST && c <= i) {
-                       struct nouveau_object *subdev = devobj->subdev[c++];
-                       if (subdev && !nv_iclass(subdev, NV_ENGINE_CLASS)) {
-                               ret = nouveau_object_inc(subdev);
-                               if (ret)
-                                       return ret;
-                               atomic_dec(&nv_object(device)->usecount);
-                       } else
-                       if (subdev) {
-                               nouveau_subdev_reset(subdev);
-                       }
-               }
-       }
-
-       return 0;
-}
-
-static struct nouveau_ofuncs
-nouveau_devobj_ofuncs = {
-       .ctor = nouveau_devobj_ctor,
-       .dtor = nouveau_devobj_dtor,
-       .init = _nouveau_parent_init,
-       .fini = _nouveau_parent_fini,
-       .mthd = nouveau_devobj_mthd,
-};
-
-/******************************************************************************
- * nouveau_device: engine functions
- *****************************************************************************/
-
-static struct nouveau_oclass
-nouveau_device_sclass[] = {
-       { 0x0080, &nouveau_devobj_ofuncs },
-       {}
-};
-
-static int
-nouveau_device_event_ctor(struct nouveau_object *object, void *data, u32 size,
-                         struct nvkm_notify *notify)
-{
-       if (!WARN_ON(size != 0)) {
-               notify->size  = 0;
-               notify->types = 1;
-               notify->index = 0;
-               return 0;
-       }
-       return -EINVAL;
-}
-
-static const struct nvkm_event_func
-nouveau_device_event_func = {
-       .ctor = nouveau_device_event_ctor,
-};
-
-static int
-nouveau_device_fini(struct nouveau_object *object, bool suspend)
-{
-       struct nouveau_device *device = (void *)object;
-       struct nouveau_object *subdev;
-       int ret, i;
-
-       for (i = NVDEV_SUBDEV_NR - 1; i >= 0; i--) {
-               if ((subdev = device->subdev[i])) {
-                       if (!nv_iclass(subdev, NV_ENGINE_CLASS)) {
-                               ret = nouveau_object_dec(subdev, suspend);
-                               if (ret && suspend)
-                                       goto fail;
-                       }
-               }
-       }
-
-       ret = nvkm_acpi_fini(device, suspend);
-fail:
-       for (; ret && i < NVDEV_SUBDEV_NR; i++) {
-               if ((subdev = device->subdev[i])) {
-                       if (!nv_iclass(subdev, NV_ENGINE_CLASS)) {
-                               ret = nouveau_object_inc(subdev);
-                               if (ret) {
-                                       /* XXX */
-                               }
-                       }
-               }
-       }
-
-       return ret;
-}
-
-static int
-nouveau_device_init(struct nouveau_object *object)
-{
-       struct nouveau_device *device = (void *)object;
-       struct nouveau_object *subdev;
-       int ret, i = 0;
-
-       ret = nvkm_acpi_init(device);
-       if (ret)
-               goto fail;
-
-       for (i = 0; i < NVDEV_SUBDEV_NR; i++) {
-               if ((subdev = device->subdev[i])) {
-                       if (!nv_iclass(subdev, NV_ENGINE_CLASS)) {
-                               ret = nouveau_object_inc(subdev);
-                               if (ret)
-                                       goto fail;
-                       } else {
-                               nouveau_subdev_reset(subdev);
-                       }
-               }
-       }
-
-       ret = 0;
-fail:
-       for (--i; ret && i >= 0; i--) {
-               if ((subdev = device->subdev[i])) {
-                       if (!nv_iclass(subdev, NV_ENGINE_CLASS))
-                               nouveau_object_dec(subdev, false);
-               }
-       }
-
-       if (ret)
-               nvkm_acpi_fini(device, false);
-       return ret;
-}
-
-static void
-nouveau_device_dtor(struct nouveau_object *object)
-{
-       struct nouveau_device *device = (void *)object;
-
-       nvkm_event_fini(&device->event);
-
-       mutex_lock(&nv_devices_mutex);
-       list_del(&device->head);
-       mutex_unlock(&nv_devices_mutex);
-
-       if (nv_subdev(device)->mmio)
-               iounmap(nv_subdev(device)->mmio);
-
-       nouveau_engine_destroy(&device->base);
-}
-
-resource_size_t
-nv_device_resource_start(struct nouveau_device *device, unsigned int bar)
-{
-       if (nv_device_is_pci(device)) {
-               return pci_resource_start(device->pdev, bar);
-       } else {
-               struct resource *res;
-               res = platform_get_resource(device->platformdev,
-                                           IORESOURCE_MEM, bar);
-               if (!res)
-                       return 0;
-               return res->start;
-       }
-}
-
-resource_size_t
-nv_device_resource_len(struct nouveau_device *device, unsigned int bar)
-{
-       if (nv_device_is_pci(device)) {
-               return pci_resource_len(device->pdev, bar);
-       } else {
-               struct resource *res;
-               res = platform_get_resource(device->platformdev,
-                                           IORESOURCE_MEM, bar);
-               if (!res)
-                       return 0;
-               return resource_size(res);
-       }
-}
-
-int
-nv_device_get_irq(struct nouveau_device *device, bool stall)
-{
-       if (nv_device_is_pci(device)) {
-               return device->pdev->irq;
-       } else {
-               return platform_get_irq_byname(device->platformdev,
-                                              stall ? "stall" : "nonstall");
-       }
-}
-
-static struct nouveau_oclass
-nouveau_device_oclass = {
-       .handle = NV_ENGINE(DEVICE, 0x00),
-       .ofuncs = &(struct nouveau_ofuncs) {
-               .dtor = nouveau_device_dtor,
-               .init = nouveau_device_init,
-               .fini = nouveau_device_fini,
-       },
-};
-
-int
-nouveau_device_create_(void *dev, enum nv_bus_type type, u64 name,
-                      const char *sname, const char *cfg, const char *dbg,
-                      int length, void **pobject)
-{
-       struct nouveau_device *device;
-       int ret = -EEXIST;
-
-       mutex_lock(&nv_devices_mutex);
-       list_for_each_entry(device, &nv_devices, head) {
-               if (device->handle == name)
-                       goto done;
-       }
-
-       ret = nouveau_engine_create_(NULL, NULL, &nouveau_device_oclass, true,
-                                    "DEVICE", "device", length, pobject);
-       device = *pobject;
-       if (ret)
-               goto done;
-
-       switch (type) {
-       case NOUVEAU_BUS_PCI:
-               device->pdev = dev;
-               break;
-       case NOUVEAU_BUS_PLATFORM:
-               device->platformdev = dev;
-               break;
-       }
-       device->handle = name;
-       device->cfgopt = cfg;
-       device->dbgopt = dbg;
-       device->name = sname;
-
-       nv_subdev(device)->debug = nouveau_dbgopt(device->dbgopt, "DEVICE");
-       nv_engine(device)->sclass = nouveau_device_sclass;
-       list_add(&device->head, &nv_devices);
-
-       ret = nvkm_event_init(&nouveau_device_event_func, 1, 1,
-                             &device->event);
-done:
-       mutex_unlock(&nv_devices_mutex);
-       return ret;
-}
diff --git a/drivers/gpu/drm/nouveau/core/engine/device/ctrl.c b/drivers/gpu/drm/nouveau/core/engine/device/ctrl.c
deleted file mode 100644 (file)
index e34101a..0000000
+++ /dev/null
@@ -1,205 +0,0 @@
-/*
- * Copyright 2013 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 <bskeggs@redhat.com>
- */
-
-#include <core/client.h>
-#include <core/object.h>
-#include <nvif/unpack.h>
-#include <nvif/class.h>
-#include <nvif/ioctl.h>
-
-#include <subdev/clock.h>
-
-#include "priv.h"
-
-static int
-nouveau_control_mthd_pstate_info(struct nouveau_object *object,
-                                void *data, u32 size)
-{
-       union {
-               struct nvif_control_pstate_info_v0 v0;
-       } *args = data;
-       struct nouveau_clock *clk = nouveau_clock(object);
-       int ret;
-
-       nv_ioctl(object, "control pstate info size %d\n", size);
-       if (nvif_unpack(args->v0, 0, 0, false)) {
-               nv_ioctl(object, "control pstate info vers %d\n",
-                        args->v0.version);
-       } else
-               return ret;
-
-       if (clk) {
-               args->v0.count = clk->state_nr;
-               args->v0.ustate_ac = clk->ustate_ac;
-               args->v0.ustate_dc = clk->ustate_dc;
-               args->v0.pwrsrc = clk->pwrsrc;
-               args->v0.pstate = clk->pstate;
-       } else {
-               args->v0.count = 0;
-               args->v0.ustate_ac = NVIF_CONTROL_PSTATE_INFO_V0_USTATE_DISABLE;
-               args->v0.ustate_dc = NVIF_CONTROL_PSTATE_INFO_V0_USTATE_DISABLE;
-               args->v0.pwrsrc = -ENOSYS;
-               args->v0.pstate = NVIF_CONTROL_PSTATE_INFO_V0_PSTATE_UNKNOWN;
-       }
-
-       return 0;
-}
-
-static int
-nouveau_control_mthd_pstate_attr(struct nouveau_object *object,
-                                void *data, u32 size)
-{
-       union {
-               struct nvif_control_pstate_attr_v0 v0;
-       } *args = data;
-       struct nouveau_clock *clk = nouveau_clock(object);
-       struct nouveau_clocks *domain;
-       struct nouveau_pstate *pstate;
-       struct nouveau_cstate *cstate;
-       int i = 0, j = -1;
-       u32 lo, hi;
-       int ret;
-
-       nv_ioctl(object, "control pstate attr size %d\n", size);
-       if (nvif_unpack(args->v0, 0, 0, false)) {
-               nv_ioctl(object, "control pstate attr vers %d state %d "
-                                "index %d\n",
-                        args->v0.version, args->v0.state, args->v0.index);
-               if (!clk)
-                       return -ENODEV;
-               if (args->v0.state < NVIF_CONTROL_PSTATE_ATTR_V0_STATE_CURRENT)
-                       return -EINVAL;
-               if (args->v0.state >= clk->state_nr)
-                       return -EINVAL;
-       } else
-               return ret;
-       domain = clk->domains;
-
-       while (domain->name != nv_clk_src_max) {
-               if (domain->mname && ++j == args->v0.index)
-                       break;
-               domain++;
-       }
-
-       if (domain->name == nv_clk_src_max)
-               return -EINVAL;
-
-       if (args->v0.state != NVIF_CONTROL_PSTATE_ATTR_V0_STATE_CURRENT) {
-               list_for_each_entry(pstate, &clk->states, head) {
-                       if (i++ == args->v0.state)
-                               break;
-               }
-
-               lo = pstate->base.domain[domain->name];
-               hi = lo;
-               list_for_each_entry(cstate, &pstate->list, head) {
-                       lo = min(lo, cstate->domain[domain->name]);
-                       hi = max(hi, cstate->domain[domain->name]);
-               }
-
-               args->v0.state = pstate->pstate;
-       } else {
-               lo = max(clk->read(clk, domain->name), 0);
-               hi = lo;
-       }
-
-       snprintf(args->v0.name, sizeof(args->v0.name), "%s", domain->mname);
-       snprintf(args->v0.unit, sizeof(args->v0.unit), "MHz");
-       args->v0.min = lo / domain->mdiv;
-       args->v0.max = hi / domain->mdiv;
-
-       args->v0.index = 0;
-       while ((++domain)->name != nv_clk_src_max) {
-               if (domain->mname) {
-                       args->v0.index = ++j;
-                       break;
-               }
-       }
-
-       return 0;
-}
-
-static int
-nouveau_control_mthd_pstate_user(struct nouveau_object *object,
-                                void *data, u32 size)
-{
-       union {
-               struct nvif_control_pstate_user_v0 v0;
-       } *args = data;
-       struct nouveau_clock *clk = nouveau_clock(object);
-       int ret;
-
-       nv_ioctl(object, "control pstate user size %d\n", size);
-       if (nvif_unpack(args->v0, 0, 0, false)) {
-               nv_ioctl(object, "control pstate user vers %d ustate %d "
-                                "pwrsrc %d\n", args->v0.version,
-                        args->v0.ustate, args->v0.pwrsrc);
-               if (!clk)
-                       return -ENODEV;
-       } else
-               return ret;
-
-       if (args->v0.pwrsrc >= 0) {
-               ret |= nouveau_clock_ustate(clk, args->v0.ustate, args->v0.pwrsrc);
-       } else {
-               ret |= nouveau_clock_ustate(clk, args->v0.ustate, 0);
-               ret |= nouveau_clock_ustate(clk, args->v0.ustate, 1);
-       }
-
-       return ret;
-}
-
-static int
-nouveau_control_mthd(struct nouveau_object *object, u32 mthd,
-                    void *data, u32 size)
-{
-       switch (mthd) {
-       case NVIF_CONTROL_PSTATE_INFO:
-               return nouveau_control_mthd_pstate_info(object, data, size);
-       case NVIF_CONTROL_PSTATE_ATTR:
-               return nouveau_control_mthd_pstate_attr(object, data, size);
-       case NVIF_CONTROL_PSTATE_USER:
-               return nouveau_control_mthd_pstate_user(object, data, size);
-       default:
-               break;
-       }
-       return -EINVAL;
-}
-
-static struct nouveau_ofuncs
-nouveau_control_ofuncs = {
-       .ctor = _nouveau_object_ctor,
-       .dtor = nouveau_object_destroy,
-       .init = nouveau_object_init,
-       .fini = nouveau_object_fini,
-       .mthd = nouveau_control_mthd,
-};
-
-struct nouveau_oclass
-nouveau_control_oclass[] = {
-       { .handle = NVIF_IOCTL_NEW_V0_CONTROL,
-         .ofuncs = &nouveau_control_ofuncs
-       },
-       {}
-};
diff --git a/drivers/gpu/drm/nouveau/core/engine/device/gm100.c b/drivers/gpu/drm/nouveau/core/engine/device/gm100.c
deleted file mode 100644 (file)
index 4e74a33..0000000
+++ /dev/null
@@ -1,150 +0,0 @@
-/*
- * Copyright 2012 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 <subdev/bios.h>
-#include <subdev/bus.h>
-#include <subdev/gpio.h>
-#include <subdev/i2c.h>
-#include <subdev/fuse.h>
-#include <subdev/clock.h>
-#include <subdev/therm.h>
-#include <subdev/mxm.h>
-#include <subdev/devinit.h>
-#include <subdev/mc.h>
-#include <subdev/timer.h>
-#include <subdev/fb.h>
-#include <subdev/ltc.h>
-#include <subdev/ibus.h>
-#include <subdev/instmem.h>
-#include <subdev/vm.h>
-#include <subdev/bar.h>
-#include <subdev/pwr.h>
-#include <subdev/volt.h>
-
-#include <engine/device.h>
-#include <engine/dmaobj.h>
-#include <engine/fifo.h>
-#include <engine/software.h>
-#include <engine/graph.h>
-#include <engine/disp.h>
-#include <engine/copy.h>
-#include <engine/bsp.h>
-#include <engine/vp.h>
-#include <engine/ppp.h>
-#include <engine/perfmon.h>
-
-int
-gm100_identify(struct nouveau_device *device)
-{
-       switch (device->chipset) {
-       case 0x117:
-               device->cname = "GM107";
-               device->oclass[NVDEV_SUBDEV_VBIOS  ] = &nouveau_bios_oclass;
-               device->oclass[NVDEV_SUBDEV_GPIO   ] =  nve0_gpio_oclass;
-               device->oclass[NVDEV_SUBDEV_I2C    ] =  nvd0_i2c_oclass;
-               device->oclass[NVDEV_SUBDEV_FUSE   ] = &gm107_fuse_oclass;
-               device->oclass[NVDEV_SUBDEV_CLOCK  ] = &nve0_clock_oclass;
-               device->oclass[NVDEV_SUBDEV_THERM  ] = &gm107_therm_oclass;
-               device->oclass[NVDEV_SUBDEV_MXM    ] = &nv50_mxm_oclass;
-               device->oclass[NVDEV_SUBDEV_DEVINIT] =  gm107_devinit_oclass;
-               device->oclass[NVDEV_SUBDEV_MC     ] =  gk20a_mc_oclass;
-               device->oclass[NVDEV_SUBDEV_BUS    ] =  nvc0_bus_oclass;
-               device->oclass[NVDEV_SUBDEV_TIMER  ] = &gk20a_timer_oclass;
-               device->oclass[NVDEV_SUBDEV_FB     ] =  gm107_fb_oclass;
-               device->oclass[NVDEV_SUBDEV_LTC    ] =  gm107_ltc_oclass;
-               device->oclass[NVDEV_SUBDEV_IBUS   ] = &nve0_ibus_oclass;
-               device->oclass[NVDEV_SUBDEV_INSTMEM] =  nv50_instmem_oclass;
-               device->oclass[NVDEV_SUBDEV_VM     ] = &nvc0_vmmgr_oclass;
-               device->oclass[NVDEV_SUBDEV_BAR    ] = &nvc0_bar_oclass;
-               device->oclass[NVDEV_SUBDEV_PWR    ] =  nv108_pwr_oclass;
-
-#if 0
-               device->oclass[NVDEV_SUBDEV_VOLT   ] = &nv40_volt_oclass;
-#endif
-               device->oclass[NVDEV_ENGINE_DMAOBJ ] =  nvd0_dmaeng_oclass;
-               device->oclass[NVDEV_ENGINE_FIFO   ] =  nv108_fifo_oclass;
-               device->oclass[NVDEV_ENGINE_SW     ] =  nvc0_software_oclass;
-               device->oclass[NVDEV_ENGINE_GR     ] =  gm107_graph_oclass;
-               device->oclass[NVDEV_ENGINE_DISP   ] =  gm107_disp_oclass;
-               device->oclass[NVDEV_ENGINE_COPY0  ] = &nve0_copy0_oclass;
-#if 0
-               device->oclass[NVDEV_ENGINE_COPY1  ] = &nve0_copy1_oclass;
-#endif
-               device->oclass[NVDEV_ENGINE_COPY2  ] = &nve0_copy2_oclass;
-#if 0
-               device->oclass[NVDEV_ENGINE_BSP    ] = &nve0_bsp_oclass;
-               device->oclass[NVDEV_ENGINE_VP     ] = &nve0_vp_oclass;
-               device->oclass[NVDEV_ENGINE_PPP    ] = &nvc0_ppp_oclass;
-#endif
-               break;
-       case 0x124:
-               device->cname = "GM204";
-               device->oclass[NVDEV_SUBDEV_VBIOS  ] = &nouveau_bios_oclass;
-               device->oclass[NVDEV_SUBDEV_GPIO   ] =  nve0_gpio_oclass;
-               device->oclass[NVDEV_SUBDEV_I2C    ] =  gm204_i2c_oclass;
-               device->oclass[NVDEV_SUBDEV_FUSE   ] = &gm107_fuse_oclass;
-#if 0
-               /* looks to be some non-trivial changes */
-               device->oclass[NVDEV_SUBDEV_CLOCK  ] = &nve0_clock_oclass;
-               /* priv ring says no to 0x10eb14 writes */
-               device->oclass[NVDEV_SUBDEV_THERM  ] = &gm107_therm_oclass;
-#endif
-               device->oclass[NVDEV_SUBDEV_MXM    ] = &nv50_mxm_oclass;
-               device->oclass[NVDEV_SUBDEV_DEVINIT] =  gm204_devinit_oclass;
-               device->oclass[NVDEV_SUBDEV_MC     ] =  gk20a_mc_oclass;
-               device->oclass[NVDEV_SUBDEV_BUS    ] =  nvc0_bus_oclass;
-               device->oclass[NVDEV_SUBDEV_TIMER  ] = &gk20a_timer_oclass;
-               device->oclass[NVDEV_SUBDEV_FB     ] =  gm107_fb_oclass;
-               device->oclass[NVDEV_SUBDEV_LTC    ] =  gm107_ltc_oclass;
-               device->oclass[NVDEV_SUBDEV_IBUS   ] = &nve0_ibus_oclass;
-               device->oclass[NVDEV_SUBDEV_INSTMEM] =  nv50_instmem_oclass;
-               device->oclass[NVDEV_SUBDEV_VM     ] = &nvc0_vmmgr_oclass;
-               device->oclass[NVDEV_SUBDEV_BAR    ] = &nvc0_bar_oclass;
-               device->oclass[NVDEV_SUBDEV_PWR    ] =  nv108_pwr_oclass;
-#if 0
-               device->oclass[NVDEV_SUBDEV_VOLT   ] = &nv40_volt_oclass;
-#endif
-               device->oclass[NVDEV_ENGINE_DMAOBJ ] =  nvd0_dmaeng_oclass;
-#if 0
-               device->oclass[NVDEV_ENGINE_FIFO   ] =  nv108_fifo_oclass;
-               device->oclass[NVDEV_ENGINE_SW     ] =  nvc0_software_oclass;
-               device->oclass[NVDEV_ENGINE_GR     ] =  gm107_graph_oclass;
-#endif
-               device->oclass[NVDEV_ENGINE_DISP   ] =  gm204_disp_oclass;
-#if 0
-               device->oclass[NVDEV_ENGINE_COPY0  ] = &gm204_copy0_oclass;
-               device->oclass[NVDEV_ENGINE_COPY1  ] = &gm204_copy1_oclass;
-               device->oclass[NVDEV_ENGINE_COPY2  ] = &gm204_copy2_oclass;
-               device->oclass[NVDEV_ENGINE_BSP    ] = &nve0_bsp_oclass;
-               device->oclass[NVDEV_ENGINE_VP     ] = &nve0_vp_oclass;
-               device->oclass[NVDEV_ENGINE_PPP    ] = &nvc0_ppp_oclass;
-#endif
-               break;
-       default:
-               nv_fatal(device, "unknown Maxwell chipset\n");
-               return -EINVAL;
-       }
-
-       return 0;
-}
diff --git a/drivers/gpu/drm/nouveau/core/engine/device/nv04.c b/drivers/gpu/drm/nouveau/core/engine/device/nv04.c
deleted file mode 100644 (file)
index 573b55f..0000000
+++ /dev/null
@@ -1,89 +0,0 @@
-/*
- * Copyright 2012 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 <subdev/bios.h>
-#include <subdev/bus.h>
-#include <subdev/i2c.h>
-#include <subdev/clock.h>
-#include <subdev/devinit.h>
-#include <subdev/mc.h>
-#include <subdev/timer.h>
-#include <subdev/fb.h>
-#include <subdev/instmem.h>
-#include <subdev/vm.h>
-
-#include <engine/device.h>
-#include <engine/dmaobj.h>
-#include <engine/fifo.h>
-#include <engine/software.h>
-#include <engine/graph.h>
-#include <engine/disp.h>
-
-int
-nv04_identify(struct nouveau_device *device)
-{
-       switch (device->chipset) {
-       case 0x04:
-               device->cname = "NV04";
-               device->oclass[NVDEV_SUBDEV_VBIOS  ] = &nouveau_bios_oclass;
-               device->oclass[NVDEV_SUBDEV_I2C    ] =  nv04_i2c_oclass;
-               device->oclass[NVDEV_SUBDEV_CLOCK  ] = &nv04_clock_oclass;
-               device->oclass[NVDEV_SUBDEV_DEVINIT] =  nv04_devinit_oclass;
-               device->oclass[NVDEV_SUBDEV_MC     ] =  nv04_mc_oclass;
-               device->oclass[NVDEV_SUBDEV_BUS    ] =  nv04_bus_oclass;
-               device->oclass[NVDEV_SUBDEV_TIMER  ] = &nv04_timer_oclass;
-               device->oclass[NVDEV_SUBDEV_FB     ] =  nv04_fb_oclass;
-               device->oclass[NVDEV_SUBDEV_INSTMEM] =  nv04_instmem_oclass;
-               device->oclass[NVDEV_SUBDEV_VM     ] = &nv04_vmmgr_oclass;
-               device->oclass[NVDEV_ENGINE_DMAOBJ ] =  nv04_dmaeng_oclass;
-               device->oclass[NVDEV_ENGINE_FIFO   ] =  nv04_fifo_oclass;
-               device->oclass[NVDEV_ENGINE_SW     ] =  nv04_software_oclass;
-               device->oclass[NVDEV_ENGINE_GR     ] = &nv04_graph_oclass;
-               device->oclass[NVDEV_ENGINE_DISP   ] =  nv04_disp_oclass;
-               break;
-       case 0x05:
-               device->cname = "NV05";
-               device->oclass[NVDEV_SUBDEV_VBIOS  ] = &nouveau_bios_oclass;
-               device->oclass[NVDEV_SUBDEV_I2C    ] =  nv04_i2c_oclass;
-               device->oclass[NVDEV_SUBDEV_CLOCK  ] = &nv04_clock_oclass;
-               device->oclass[NVDEV_SUBDEV_DEVINIT] =  nv05_devinit_oclass;
-               device->oclass[NVDEV_SUBDEV_MC     ] =  nv04_mc_oclass;
-               device->oclass[NVDEV_SUBDEV_BUS    ] =  nv04_bus_oclass;
-               device->oclass[NVDEV_SUBDEV_TIMER  ] = &nv04_timer_oclass;
-               device->oclass[NVDEV_SUBDEV_FB     ] =  nv04_fb_oclass;
-               device->oclass[NVDEV_SUBDEV_INSTMEM] =  nv04_instmem_oclass;
-               device->oclass[NVDEV_SUBDEV_VM     ] = &nv04_vmmgr_oclass;
-               device->oclass[NVDEV_ENGINE_DMAOBJ ] =  nv04_dmaeng_oclass;
-               device->oclass[NVDEV_ENGINE_FIFO   ] =  nv04_fifo_oclass;
-               device->oclass[NVDEV_ENGINE_SW     ] =  nv04_software_oclass;
-               device->oclass[NVDEV_ENGINE_GR     ] = &nv04_graph_oclass;
-               device->oclass[NVDEV_ENGINE_DISP   ] =  nv04_disp_oclass;
-               break;
-       default:
-               nv_fatal(device, "unknown RIVA chipset\n");
-               return -EINVAL;
-       }
-
-       return 0;
-}
diff --git a/drivers/gpu/drm/nouveau/core/engine/device/nv10.c b/drivers/gpu/drm/nouveau/core/engine/device/nv10.c
deleted file mode 100644 (file)
index 183a85a..0000000
+++ /dev/null
@@ -1,204 +0,0 @@
-/*
- * Copyright 2012 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 <subdev/bios.h>
-#include <subdev/bus.h>
-#include <subdev/gpio.h>
-#include <subdev/i2c.h>
-#include <subdev/clock.h>
-#include <subdev/devinit.h>
-#include <subdev/mc.h>
-#include <subdev/timer.h>
-#include <subdev/fb.h>
-#include <subdev/instmem.h>
-#include <subdev/vm.h>
-
-#include <engine/device.h>
-#include <engine/dmaobj.h>
-#include <engine/fifo.h>
-#include <engine/software.h>
-#include <engine/graph.h>
-#include <engine/disp.h>
-
-int
-nv10_identify(struct nouveau_device *device)
-{
-       switch (device->chipset) {
-       case 0x10:
-               device->cname = "NV10";
-               device->oclass[NVDEV_SUBDEV_VBIOS  ] = &nouveau_bios_oclass;
-               device->oclass[NVDEV_SUBDEV_GPIO   ] =  nv10_gpio_oclass;
-               device->oclass[NVDEV_SUBDEV_I2C    ] =  nv04_i2c_oclass;
-               device->oclass[NVDEV_SUBDEV_CLOCK  ] = &nv04_clock_oclass;
-               device->oclass[NVDEV_SUBDEV_DEVINIT] =  nv10_devinit_oclass;
-               device->oclass[NVDEV_SUBDEV_MC     ] =  nv04_mc_oclass;
-               device->oclass[NVDEV_SUBDEV_BUS    ] =  nv04_bus_oclass;
-               device->oclass[NVDEV_SUBDEV_TIMER  ] = &nv04_timer_oclass;
-               device->oclass[NVDEV_SUBDEV_FB     ] =  nv10_fb_oclass;
-               device->oclass[NVDEV_SUBDEV_INSTMEM] =  nv04_instmem_oclass;
-               device->oclass[NVDEV_SUBDEV_VM     ] = &nv04_vmmgr_oclass;
-               device->oclass[NVDEV_ENGINE_DMAOBJ ] =  nv04_dmaeng_oclass;
-               device->oclass[NVDEV_ENGINE_GR     ] = &nv10_graph_oclass;
-               device->oclass[NVDEV_ENGINE_DISP   ] =  nv04_disp_oclass;
-               break;
-       case 0x15:
-               device->cname = "NV15";
-               device->oclass[NVDEV_SUBDEV_VBIOS  ] = &nouveau_bios_oclass;
-               device->oclass[NVDEV_SUBDEV_GPIO   ] =  nv10_gpio_oclass;
-               device->oclass[NVDEV_SUBDEV_I2C    ] =  nv04_i2c_oclass;
-               device->oclass[NVDEV_SUBDEV_CLOCK  ] = &nv04_clock_oclass;
-               device->oclass[NVDEV_SUBDEV_DEVINIT] =  nv10_devinit_oclass;
-               device->oclass[NVDEV_SUBDEV_MC     ] =  nv04_mc_oclass;
-               device->oclass[NVDEV_SUBDEV_BUS    ] =  nv04_bus_oclass;
-               device->oclass[NVDEV_SUBDEV_TIMER  ] = &nv04_timer_oclass;
-               device->oclass[NVDEV_SUBDEV_FB     ] =  nv10_fb_oclass;
-               device->oclass[NVDEV_SUBDEV_INSTMEM] =  nv04_instmem_oclass;
-               device->oclass[NVDEV_SUBDEV_VM     ] = &nv04_vmmgr_oclass;
-               device->oclass[NVDEV_ENGINE_DMAOBJ ] =  nv04_dmaeng_oclass;
-               device->oclass[NVDEV_ENGINE_FIFO   ] =  nv10_fifo_oclass;
-               device->oclass[NVDEV_ENGINE_SW     ] =  nv10_software_oclass;
-               device->oclass[NVDEV_ENGINE_GR     ] = &nv10_graph_oclass;
-               device->oclass[NVDEV_ENGINE_DISP   ] =  nv04_disp_oclass;
-               break;
-       case 0x16:
-               device->cname = "NV16";
-               device->oclass[NVDEV_SUBDEV_VBIOS  ] = &nouveau_bios_oclass;
-               device->oclass[NVDEV_SUBDEV_GPIO   ] =  nv10_gpio_oclass;
-               device->oclass[NVDEV_SUBDEV_I2C    ] =  nv04_i2c_oclass;
-               device->oclass[NVDEV_SUBDEV_CLOCK  ] = &nv04_clock_oclass;
-               device->oclass[NVDEV_SUBDEV_DEVINIT] =  nv10_devinit_oclass;
-               device->oclass[NVDEV_SUBDEV_MC     ] =  nv04_mc_oclass;
-               device->oclass[NVDEV_SUBDEV_BUS    ] =  nv04_bus_oclass;
-               device->oclass[NVDEV_SUBDEV_TIMER  ] = &nv04_timer_oclass;
-               device->oclass[NVDEV_SUBDEV_FB     ] =  nv10_fb_oclass;
-               device->oclass[NVDEV_SUBDEV_INSTMEM] =  nv04_instmem_oclass;
-               device->oclass[NVDEV_SUBDEV_VM     ] = &nv04_vmmgr_oclass;
-               device->oclass[NVDEV_ENGINE_DMAOBJ ] =  nv04_dmaeng_oclass;
-               device->oclass[NVDEV_ENGINE_FIFO   ] =  nv10_fifo_oclass;
-               device->oclass[NVDEV_ENGINE_SW     ] =  nv10_software_oclass;
-               device->oclass[NVDEV_ENGINE_GR     ] = &nv10_graph_oclass;
-               device->oclass[NVDEV_ENGINE_DISP   ] =  nv04_disp_oclass;
-               break;
-       case 0x1a:
-               device->cname = "nForce";
-               device->oclass[NVDEV_SUBDEV_VBIOS  ] = &nouveau_bios_oclass;
-               device->oclass[NVDEV_SUBDEV_GPIO   ] =  nv10_gpio_oclass;
-               device->oclass[NVDEV_SUBDEV_I2C    ] =  nv04_i2c_oclass;
-               device->oclass[NVDEV_SUBDEV_CLOCK  ] = &nv04_clock_oclass;
-               device->oclass[NVDEV_SUBDEV_DEVINIT] =  nv1a_devinit_oclass;
-               device->oclass[NVDEV_SUBDEV_MC     ] =  nv04_mc_oclass;
-               device->oclass[NVDEV_SUBDEV_BUS    ] =  nv04_bus_oclass;
-               device->oclass[NVDEV_SUBDEV_TIMER  ] = &nv04_timer_oclass;
-               device->oclass[NVDEV_SUBDEV_FB     ] =  nv1a_fb_oclass;
-               device->oclass[NVDEV_SUBDEV_INSTMEM] =  nv04_instmem_oclass;
-               device->oclass[NVDEV_SUBDEV_VM     ] = &nv04_vmmgr_oclass;
-               device->oclass[NVDEV_ENGINE_DMAOBJ ] =  nv04_dmaeng_oclass;
-               device->oclass[NVDEV_ENGINE_FIFO   ] =  nv10_fifo_oclass;
-               device->oclass[NVDEV_ENGINE_SW     ] =  nv10_software_oclass;
-               device->oclass[NVDEV_ENGINE_GR     ] = &nv10_graph_oclass;
-               device->oclass[NVDEV_ENGINE_DISP   ] =  nv04_disp_oclass;
-               break;
-       case 0x11:
-               device->cname = "NV11";
-               device->oclass[NVDEV_SUBDEV_VBIOS  ] = &nouveau_bios_oclass;
-               device->oclass[NVDEV_SUBDEV_GPIO   ] =  nv10_gpio_oclass;
-               device->oclass[NVDEV_SUBDEV_I2C    ] =  nv04_i2c_oclass;
-               device->oclass[NVDEV_SUBDEV_CLOCK  ] = &nv04_clock_oclass;
-               device->oclass[NVDEV_SUBDEV_DEVINIT] =  nv10_devinit_oclass;
-               device->oclass[NVDEV_SUBDEV_MC     ] =  nv04_mc_oclass;
-               device->oclass[NVDEV_SUBDEV_BUS    ] =  nv04_bus_oclass;
-               device->oclass[NVDEV_SUBDEV_TIMER  ] = &nv04_timer_oclass;
-               device->oclass[NVDEV_SUBDEV_FB     ] =  nv10_fb_oclass;
-               device->oclass[NVDEV_SUBDEV_INSTMEM] =  nv04_instmem_oclass;
-               device->oclass[NVDEV_SUBDEV_VM     ] = &nv04_vmmgr_oclass;
-               device->oclass[NVDEV_ENGINE_DMAOBJ ] =  nv04_dmaeng_oclass;
-               device->oclass[NVDEV_ENGINE_FIFO   ] =  nv10_fifo_oclass;
-               device->oclass[NVDEV_ENGINE_SW     ] =  nv10_software_oclass;
-               device->oclass[NVDEV_ENGINE_GR     ] = &nv10_graph_oclass;
-               device->oclass[NVDEV_ENGINE_DISP   ] =  nv04_disp_oclass;
-               break;
-       case 0x17:
-               device->cname = "NV17";
-               device->oclass[NVDEV_SUBDEV_VBIOS  ] = &nouveau_bios_oclass;
-               device->oclass[NVDEV_SUBDEV_GPIO   ] =  nv10_gpio_oclass;
-               device->oclass[NVDEV_SUBDEV_I2C    ] =  nv04_i2c_oclass;
-               device->oclass[NVDEV_SUBDEV_CLOCK  ] = &nv04_clock_oclass;
-               device->oclass[NVDEV_SUBDEV_DEVINIT] =  nv10_devinit_oclass;
-               device->oclass[NVDEV_SUBDEV_MC     ] =  nv04_mc_oclass;
-               device->oclass[NVDEV_SUBDEV_BUS    ] =  nv04_bus_oclass;
-               device->oclass[NVDEV_SUBDEV_TIMER  ] = &nv04_timer_oclass;
-               device->oclass[NVDEV_SUBDEV_FB     ] =  nv10_fb_oclass;
-               device->oclass[NVDEV_SUBDEV_INSTMEM] =  nv04_instmem_oclass;
-               device->oclass[NVDEV_SUBDEV_VM     ] = &nv04_vmmgr_oclass;
-               device->oclass[NVDEV_ENGINE_DMAOBJ ] =  nv04_dmaeng_oclass;
-               device->oclass[NVDEV_ENGINE_FIFO   ] =  nv17_fifo_oclass;
-               device->oclass[NVDEV_ENGINE_SW     ] =  nv10_software_oclass;
-               device->oclass[NVDEV_ENGINE_GR     ] = &nv10_graph_oclass;
-               device->oclass[NVDEV_ENGINE_DISP   ] =  nv04_disp_oclass;
-               break;
-       case 0x1f:
-               device->cname = "nForce2";
-               device->oclass[NVDEV_SUBDEV_VBIOS  ] = &nouveau_bios_oclass;
-               device->oclass[NVDEV_SUBDEV_GPIO   ] =  nv10_gpio_oclass;
-               device->oclass[NVDEV_SUBDEV_I2C    ] =  nv04_i2c_oclass;
-               device->oclass[NVDEV_SUBDEV_CLOCK  ] = &nv04_clock_oclass;
-               device->oclass[NVDEV_SUBDEV_DEVINIT] =  nv1a_devinit_oclass;
-               device->oclass[NVDEV_SUBDEV_MC     ] =  nv04_mc_oclass;
-               device->oclass[NVDEV_SUBDEV_BUS    ] =  nv04_bus_oclass;
-               device->oclass[NVDEV_SUBDEV_TIMER  ] = &nv04_timer_oclass;
-               device->oclass[NVDEV_SUBDEV_FB     ] =  nv1a_fb_oclass;
-               device->oclass[NVDEV_SUBDEV_INSTMEM] =  nv04_instmem_oclass;
-               device->oclass[NVDEV_SUBDEV_VM     ] = &nv04_vmmgr_oclass;
-               device->oclass[NVDEV_ENGINE_DMAOBJ ] =  nv04_dmaeng_oclass;
-               device->oclass[NVDEV_ENGINE_FIFO   ] =  nv17_fifo_oclass;
-               device->oclass[NVDEV_ENGINE_SW     ] =  nv10_software_oclass;
-               device->oclass[NVDEV_ENGINE_GR     ] = &nv10_graph_oclass;
-               device->oclass[NVDEV_ENGINE_DISP   ] =  nv04_disp_oclass;
-               break;
-       case 0x18:
-               device->cname = "NV18";
-               device->oclass[NVDEV_SUBDEV_VBIOS  ] = &nouveau_bios_oclass;
-               device->oclass[NVDEV_SUBDEV_GPIO   ] =  nv10_gpio_oclass;
-               device->oclass[NVDEV_SUBDEV_I2C    ] =  nv04_i2c_oclass;
-               device->oclass[NVDEV_SUBDEV_CLOCK  ] = &nv04_clock_oclass;
-               device->oclass[NVDEV_SUBDEV_DEVINIT] =  nv10_devinit_oclass;
-               device->oclass[NVDEV_SUBDEV_MC     ] =  nv04_mc_oclass;
-               device->oclass[NVDEV_SUBDEV_BUS    ] =  nv04_bus_oclass;
-               device->oclass[NVDEV_SUBDEV_TIMER  ] = &nv04_timer_oclass;
-               device->oclass[NVDEV_SUBDEV_FB     ] =  nv10_fb_oclass;
-               device->oclass[NVDEV_SUBDEV_INSTMEM] =  nv04_instmem_oclass;
-               device->oclass[NVDEV_SUBDEV_VM     ] = &nv04_vmmgr_oclass;
-               device->oclass[NVDEV_ENGINE_DMAOBJ ] =  nv04_dmaeng_oclass;
-               device->oclass[NVDEV_ENGINE_FIFO   ] =  nv17_fifo_oclass;
-               device->oclass[NVDEV_ENGINE_SW     ] =  nv10_software_oclass;
-               device->oclass[NVDEV_ENGINE_GR     ] = &nv10_graph_oclass;
-               device->oclass[NVDEV_ENGINE_DISP   ] =  nv04_disp_oclass;
-               break;
-       default:
-               nv_fatal(device, "unknown Celsius chipset\n");
-               return -EINVAL;
-       }
-
-       return 0;
-}
diff --git a/drivers/gpu/drm/nouveau/core/engine/device/nv20.c b/drivers/gpu/drm/nouveau/core/engine/device/nv20.c
deleted file mode 100644 (file)
index aa564c6..0000000
+++ /dev/null
@@ -1,131 +0,0 @@
-/*
- * Copyright 2012 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 <subdev/bios.h>
-#include <subdev/bus.h>
-#include <subdev/gpio.h>
-#include <subdev/i2c.h>
-#include <subdev/clock.h>
-#include <subdev/therm.h>
-#include <subdev/devinit.h>
-#include <subdev/mc.h>
-#include <subdev/timer.h>
-#include <subdev/fb.h>
-#include <subdev/instmem.h>
-#include <subdev/vm.h>
-
-#include <engine/device.h>
-#include <engine/dmaobj.h>
-#include <engine/fifo.h>
-#include <engine/software.h>
-#include <engine/graph.h>
-#include <engine/disp.h>
-
-int
-nv20_identify(struct nouveau_device *device)
-{
-       switch (device->chipset) {
-       case 0x20:
-               device->cname = "NV20";
-               device->oclass[NVDEV_SUBDEV_VBIOS  ] = &nouveau_bios_oclass;
-               device->oclass[NVDEV_SUBDEV_GPIO   ] =  nv10_gpio_oclass;
-               device->oclass[NVDEV_SUBDEV_I2C    ] =  nv04_i2c_oclass;
-               device->oclass[NVDEV_SUBDEV_CLOCK  ] = &nv04_clock_oclass;
-               device->oclass[NVDEV_SUBDEV_DEVINIT] =  nv20_devinit_oclass;
-               device->oclass[NVDEV_SUBDEV_MC     ] =  nv04_mc_oclass;
-               device->oclass[NVDEV_SUBDEV_BUS    ] =  nv04_bus_oclass;
-               device->oclass[NVDEV_SUBDEV_TIMER  ] = &nv04_timer_oclass;
-               device->oclass[NVDEV_SUBDEV_FB     ] =  nv20_fb_oclass;
-               device->oclass[NVDEV_SUBDEV_INSTMEM] =  nv04_instmem_oclass;
-               device->oclass[NVDEV_SUBDEV_VM     ] = &nv04_vmmgr_oclass;
-               device->oclass[NVDEV_ENGINE_DMAOBJ ] =  nv04_dmaeng_oclass;
-               device->oclass[NVDEV_ENGINE_FIFO   ] =  nv17_fifo_oclass;
-               device->oclass[NVDEV_ENGINE_SW     ] =  nv10_software_oclass;
-               device->oclass[NVDEV_ENGINE_GR     ] = &nv20_graph_oclass;
-               device->oclass[NVDEV_ENGINE_DISP   ] =  nv04_disp_oclass;
-               break;
-       case 0x25:
-               device->cname = "NV25";
-               device->oclass[NVDEV_SUBDEV_VBIOS  ] = &nouveau_bios_oclass;
-               device->oclass[NVDEV_SUBDEV_GPIO   ] =  nv10_gpio_oclass;
-               device->oclass[NVDEV_SUBDEV_I2C    ] =  nv04_i2c_oclass;
-               device->oclass[NVDEV_SUBDEV_CLOCK  ] = &nv04_clock_oclass;
-               device->oclass[NVDEV_SUBDEV_DEVINIT] =  nv20_devinit_oclass;
-               device->oclass[NVDEV_SUBDEV_MC     ] =  nv04_mc_oclass;
-               device->oclass[NVDEV_SUBDEV_BUS    ] =  nv04_bus_oclass;
-               device->oclass[NVDEV_SUBDEV_TIMER  ] = &nv04_timer_oclass;
-               device->oclass[NVDEV_SUBDEV_FB     ] =  nv25_fb_oclass;
-               device->oclass[NVDEV_SUBDEV_INSTMEM] =  nv04_instmem_oclass;
-               device->oclass[NVDEV_SUBDEV_VM     ] = &nv04_vmmgr_oclass;
-               device->oclass[NVDEV_ENGINE_DMAOBJ ] =  nv04_dmaeng_oclass;
-               device->oclass[NVDEV_ENGINE_FIFO   ] =  nv17_fifo_oclass;
-               device->oclass[NVDEV_ENGINE_SW     ] =  nv10_software_oclass;
-               device->oclass[NVDEV_ENGINE_GR     ] = &nv25_graph_oclass;
-               device->oclass[NVDEV_ENGINE_DISP   ] =  nv04_disp_oclass;
-               break;
-       case 0x28:
-               device->cname = "NV28";
-               device->oclass[NVDEV_SUBDEV_VBIOS  ] = &nouveau_bios_oclass;
-               device->oclass[NVDEV_SUBDEV_GPIO   ] =  nv10_gpio_oclass;
-               device->oclass[NVDEV_SUBDEV_I2C    ] =  nv04_i2c_oclass;
-               device->oclass[NVDEV_SUBDEV_CLOCK  ] = &nv04_clock_oclass;
-               device->oclass[NVDEV_SUBDEV_DEVINIT] =  nv20_devinit_oclass;
-               device->oclass[NVDEV_SUBDEV_MC     ] =  nv04_mc_oclass;
-               device->oclass[NVDEV_SUBDEV_BUS    ] =  nv04_bus_oclass;
-               device->oclass[NVDEV_SUBDEV_TIMER  ] = &nv04_timer_oclass;
-               device->oclass[NVDEV_SUBDEV_FB     ] =  nv25_fb_oclass;
-               device->oclass[NVDEV_SUBDEV_INSTMEM] =  nv04_instmem_oclass;
-               device->oclass[NVDEV_SUBDEV_VM     ] = &nv04_vmmgr_oclass;
-               device->oclass[NVDEV_ENGINE_DMAOBJ ] =  nv04_dmaeng_oclass;
-               device->oclass[NVDEV_ENGINE_FIFO   ] =  nv17_fifo_oclass;
-               device->oclass[NVDEV_ENGINE_SW     ] =  nv10_software_oclass;
-               device->oclass[NVDEV_ENGINE_GR     ] = &nv25_graph_oclass;
-               device->oclass[NVDEV_ENGINE_DISP   ] =  nv04_disp_oclass;
-               break;
-       case 0x2a:
-               device->cname = "NV2A";
-               device->oclass[NVDEV_SUBDEV_VBIOS  ] = &nouveau_bios_oclass;
-               device->oclass[NVDEV_SUBDEV_GPIO   ] =  nv10_gpio_oclass;
-               device->oclass[NVDEV_SUBDEV_I2C    ] =  nv04_i2c_oclass;
-               device->oclass[NVDEV_SUBDEV_CLOCK  ] = &nv04_clock_oclass;
-               device->oclass[NVDEV_SUBDEV_DEVINIT] =  nv20_devinit_oclass;
-               device->oclass[NVDEV_SUBDEV_MC     ] =  nv04_mc_oclass;
-               device->oclass[NVDEV_SUBDEV_BUS    ] =  nv04_bus_oclass;
-               device->oclass[NVDEV_SUBDEV_TIMER  ] = &nv04_timer_oclass;
-               device->oclass[NVDEV_SUBDEV_FB     ] =  nv25_fb_oclass;
-               device->oclass[NVDEV_SUBDEV_INSTMEM] =  nv04_instmem_oclass;
-               device->oclass[NVDEV_SUBDEV_VM     ] = &nv04_vmmgr_oclass;
-               device->oclass[NVDEV_ENGINE_DMAOBJ ] =  nv04_dmaeng_oclass;
-               device->oclass[NVDEV_ENGINE_FIFO   ] =  nv17_fifo_oclass;
-               device->oclass[NVDEV_ENGINE_SW     ] =  nv10_software_oclass;
-               device->oclass[NVDEV_ENGINE_GR     ] = &nv2a_graph_oclass;
-               device->oclass[NVDEV_ENGINE_DISP   ] =  nv04_disp_oclass;
-               break;
-       default:
-               nv_fatal(device, "unknown Kelvin chipset\n");
-               return -EINVAL;
-       }
-
-       return 0;
-}
diff --git a/drivers/gpu/drm/nouveau/core/engine/device/nv30.c b/drivers/gpu/drm/nouveau/core/engine/device/nv30.c
deleted file mode 100644 (file)
index 11bd31d..0000000
+++ /dev/null
@@ -1,153 +0,0 @@
-/*
- * Copyright 2012 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 <subdev/bios.h>
-#include <subdev/bus.h>
-#include <subdev/gpio.h>
-#include <subdev/i2c.h>
-#include <subdev/clock.h>
-#include <subdev/devinit.h>
-#include <subdev/mc.h>
-#include <subdev/timer.h>
-#include <subdev/fb.h>
-#include <subdev/instmem.h>
-#include <subdev/vm.h>
-
-#include <engine/device.h>
-#include <engine/dmaobj.h>
-#include <engine/fifo.h>
-#include <engine/software.h>
-#include <engine/graph.h>
-#include <engine/mpeg.h>
-#include <engine/disp.h>
-
-int
-nv30_identify(struct nouveau_device *device)
-{
-       switch (device->chipset) {
-       case 0x30:
-               device->cname = "NV30";
-               device->oclass[NVDEV_SUBDEV_VBIOS  ] = &nouveau_bios_oclass;
-               device->oclass[NVDEV_SUBDEV_GPIO   ] =  nv10_gpio_oclass;
-               device->oclass[NVDEV_SUBDEV_I2C    ] =  nv04_i2c_oclass;
-               device->oclass[NVDEV_SUBDEV_CLOCK  ] = &nv04_clock_oclass;
-               device->oclass[NVDEV_SUBDEV_DEVINIT] =  nv20_devinit_oclass;
-               device->oclass[NVDEV_SUBDEV_MC     ] =  nv04_mc_oclass;
-               device->oclass[NVDEV_SUBDEV_BUS    ] =  nv04_bus_oclass;
-               device->oclass[NVDEV_SUBDEV_TIMER  ] = &nv04_timer_oclass;
-               device->oclass[NVDEV_SUBDEV_FB     ] =  nv30_fb_oclass;
-               device->oclass[NVDEV_SUBDEV_INSTMEM] =  nv04_instmem_oclass;
-               device->oclass[NVDEV_SUBDEV_VM     ] = &nv04_vmmgr_oclass;
-               device->oclass[NVDEV_ENGINE_DMAOBJ ] =  nv04_dmaeng_oclass;
-               device->oclass[NVDEV_ENGINE_FIFO   ] =  nv17_fifo_oclass;
-               device->oclass[NVDEV_ENGINE_SW     ] =  nv10_software_oclass;
-               device->oclass[NVDEV_ENGINE_GR     ] = &nv30_graph_oclass;
-               device->oclass[NVDEV_ENGINE_DISP   ] =  nv04_disp_oclass;
-               break;
-       case 0x35:
-               device->cname = "NV35";
-               device->oclass[NVDEV_SUBDEV_VBIOS  ] = &nouveau_bios_oclass;
-               device->oclass[NVDEV_SUBDEV_GPIO   ] =  nv10_gpio_oclass;
-               device->oclass[NVDEV_SUBDEV_I2C    ] =  nv04_i2c_oclass;
-               device->oclass[NVDEV_SUBDEV_CLOCK  ] = &nv04_clock_oclass;
-               device->oclass[NVDEV_SUBDEV_DEVINIT] =  nv20_devinit_oclass;
-               device->oclass[NVDEV_SUBDEV_MC     ] =  nv04_mc_oclass;
-               device->oclass[NVDEV_SUBDEV_BUS    ] =  nv04_bus_oclass;
-               device->oclass[NVDEV_SUBDEV_TIMER  ] = &nv04_timer_oclass;
-               device->oclass[NVDEV_SUBDEV_FB     ] =  nv35_fb_oclass;
-               device->oclass[NVDEV_SUBDEV_INSTMEM] =  nv04_instmem_oclass;
-               device->oclass[NVDEV_SUBDEV_VM     ] = &nv04_vmmgr_oclass;
-               device->oclass[NVDEV_ENGINE_DMAOBJ ] =  nv04_dmaeng_oclass;
-               device->oclass[NVDEV_ENGINE_FIFO   ] =  nv17_fifo_oclass;
-               device->oclass[NVDEV_ENGINE_SW     ] =  nv10_software_oclass;
-               device->oclass[NVDEV_ENGINE_GR     ] = &nv35_graph_oclass;
-               device->oclass[NVDEV_ENGINE_DISP   ] =  nv04_disp_oclass;
-               break;
-       case 0x31:
-               device->cname = "NV31";
-               device->oclass[NVDEV_SUBDEV_VBIOS  ] = &nouveau_bios_oclass;
-               device->oclass[NVDEV_SUBDEV_GPIO   ] =  nv10_gpio_oclass;
-               device->oclass[NVDEV_SUBDEV_I2C    ] =  nv04_i2c_oclass;
-               device->oclass[NVDEV_SUBDEV_CLOCK  ] = &nv04_clock_oclass;
-               device->oclass[NVDEV_SUBDEV_DEVINIT] =  nv20_devinit_oclass;
-               device->oclass[NVDEV_SUBDEV_MC     ] =  nv04_mc_oclass;
-               device->oclass[NVDEV_SUBDEV_BUS    ] =  nv31_bus_oclass;
-               device->oclass[NVDEV_SUBDEV_TIMER  ] = &nv04_timer_oclass;
-               device->oclass[NVDEV_SUBDEV_FB     ] =  nv30_fb_oclass;
-               device->oclass[NVDEV_SUBDEV_INSTMEM] =  nv04_instmem_oclass;
-               device->oclass[NVDEV_SUBDEV_VM     ] = &nv04_vmmgr_oclass;
-               device->oclass[NVDEV_ENGINE_DMAOBJ ] =  nv04_dmaeng_oclass;
-               device->oclass[NVDEV_ENGINE_FIFO   ] =  nv17_fifo_oclass;
-               device->oclass[NVDEV_ENGINE_SW     ] =  nv10_software_oclass;
-               device->oclass[NVDEV_ENGINE_GR     ] = &nv30_graph_oclass;
-               device->oclass[NVDEV_ENGINE_MPEG   ] = &nv31_mpeg_oclass;
-               device->oclass[NVDEV_ENGINE_DISP   ] =  nv04_disp_oclass;
-               break;
-       case 0x36:
-               device->cname = "NV36";
-               device->oclass[NVDEV_SUBDEV_VBIOS  ] = &nouveau_bios_oclass;
-               device->oclass[NVDEV_SUBDEV_GPIO   ] =  nv10_gpio_oclass;
-               device->oclass[NVDEV_SUBDEV_I2C    ] =  nv04_i2c_oclass;
-               device->oclass[NVDEV_SUBDEV_CLOCK  ] = &nv04_clock_oclass;
-               device->oclass[NVDEV_SUBDEV_DEVINIT] =  nv20_devinit_oclass;
-               device->oclass[NVDEV_SUBDEV_MC     ] =  nv04_mc_oclass;
-               device->oclass[NVDEV_SUBDEV_BUS    ] =  nv31_bus_oclass;
-               device->oclass[NVDEV_SUBDEV_TIMER  ] = &nv04_timer_oclass;
-               device->oclass[NVDEV_SUBDEV_FB     ] =  nv36_fb_oclass;
-               device->oclass[NVDEV_SUBDEV_INSTMEM] =  nv04_instmem_oclass;
-               device->oclass[NVDEV_SUBDEV_VM     ] = &nv04_vmmgr_oclass;
-               device->oclass[NVDEV_ENGINE_DMAOBJ ] =  nv04_dmaeng_oclass;
-               device->oclass[NVDEV_ENGINE_FIFO   ] =  nv17_fifo_oclass;
-               device->oclass[NVDEV_ENGINE_SW     ] =  nv10_software_oclass;
-               device->oclass[NVDEV_ENGINE_GR     ] = &nv35_graph_oclass;
-               device->oclass[NVDEV_ENGINE_MPEG   ] = &nv31_mpeg_oclass;
-               device->oclass[NVDEV_ENGINE_DISP   ] =  nv04_disp_oclass;
-               break;
-       case 0x34:
-               device->cname = "NV34";
-               device->oclass[NVDEV_SUBDEV_VBIOS  ] = &nouveau_bios_oclass;
-               device->oclass[NVDEV_SUBDEV_GPIO   ] =  nv10_gpio_oclass;
-               device->oclass[NVDEV_SUBDEV_I2C    ] =  nv04_i2c_oclass;
-               device->oclass[NVDEV_SUBDEV_CLOCK  ] = &nv04_clock_oclass;
-               device->oclass[NVDEV_SUBDEV_DEVINIT] =  nv10_devinit_oclass;
-               device->oclass[NVDEV_SUBDEV_MC     ] =  nv04_mc_oclass;
-               device->oclass[NVDEV_SUBDEV_BUS    ] =  nv31_bus_oclass;
-               device->oclass[NVDEV_SUBDEV_TIMER  ] = &nv04_timer_oclass;
-               device->oclass[NVDEV_SUBDEV_FB     ] =  nv10_fb_oclass;
-               device->oclass[NVDEV_SUBDEV_INSTMEM] =  nv04_instmem_oclass;
-               device->oclass[NVDEV_SUBDEV_VM     ] = &nv04_vmmgr_oclass;
-               device->oclass[NVDEV_ENGINE_DMAOBJ ] =  nv04_dmaeng_oclass;
-               device->oclass[NVDEV_ENGINE_FIFO   ] =  nv17_fifo_oclass;
-               device->oclass[NVDEV_ENGINE_SW     ] =  nv10_software_oclass;
-               device->oclass[NVDEV_ENGINE_GR     ] = &nv34_graph_oclass;
-               device->oclass[NVDEV_ENGINE_MPEG   ] = &nv31_mpeg_oclass;
-               device->oclass[NVDEV_ENGINE_DISP   ] =  nv04_disp_oclass;
-               break;
-       default:
-               nv_fatal(device, "unknown Rankine chipset\n");
-               return -EINVAL;
-       }
-
-       return 0;
-}
diff --git a/drivers/gpu/drm/nouveau/core/engine/device/nv40.c b/drivers/gpu/drm/nouveau/core/engine/device/nv40.c
deleted file mode 100644 (file)
index e96c223..0000000
+++ /dev/null
@@ -1,427 +0,0 @@
-/*
- * Copyright 2012 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 <subdev/bios.h>
-#include <subdev/bus.h>
-#include <subdev/vm.h>
-#include <subdev/gpio.h>
-#include <subdev/i2c.h>
-#include <subdev/clock.h>
-#include <subdev/therm.h>
-#include <subdev/devinit.h>
-#include <subdev/mc.h>
-#include <subdev/timer.h>
-#include <subdev/fb.h>
-#include <subdev/instmem.h>
-#include <subdev/vm.h>
-#include <subdev/volt.h>
-
-#include <engine/device.h>
-#include <engine/dmaobj.h>
-#include <engine/fifo.h>
-#include <engine/software.h>
-#include <engine/graph.h>
-#include <engine/mpeg.h>
-#include <engine/disp.h>
-#include <engine/perfmon.h>
-
-int
-nv40_identify(struct nouveau_device *device)
-{
-       switch (device->chipset) {
-       case 0x40:
-               device->cname = "NV40";
-               device->oclass[NVDEV_SUBDEV_VBIOS  ] = &nouveau_bios_oclass;
-               device->oclass[NVDEV_SUBDEV_GPIO   ] =  nv10_gpio_oclass;
-               device->oclass[NVDEV_SUBDEV_I2C    ] =  nv04_i2c_oclass;
-               device->oclass[NVDEV_SUBDEV_CLOCK  ] = &nv40_clock_oclass;
-               device->oclass[NVDEV_SUBDEV_THERM  ] = &nv40_therm_oclass;
-               device->oclass[NVDEV_SUBDEV_DEVINIT] =  nv1a_devinit_oclass;
-               device->oclass[NVDEV_SUBDEV_MC     ] =  nv40_mc_oclass;
-               device->oclass[NVDEV_SUBDEV_BUS    ] =  nv31_bus_oclass;
-               device->oclass[NVDEV_SUBDEV_TIMER  ] = &nv04_timer_oclass;
-               device->oclass[NVDEV_SUBDEV_FB     ] =  nv40_fb_oclass;
-               device->oclass[NVDEV_SUBDEV_INSTMEM] =  nv40_instmem_oclass;
-               device->oclass[NVDEV_SUBDEV_VM     ] = &nv04_vmmgr_oclass;
-               device->oclass[NVDEV_SUBDEV_VOLT   ] = &nv40_volt_oclass;
-               device->oclass[NVDEV_ENGINE_DMAOBJ ] =  nv04_dmaeng_oclass;
-               device->oclass[NVDEV_ENGINE_FIFO   ] =  nv40_fifo_oclass;
-               device->oclass[NVDEV_ENGINE_SW     ] =  nv10_software_oclass;
-               device->oclass[NVDEV_ENGINE_GR     ] = &nv40_graph_oclass;
-               device->oclass[NVDEV_ENGINE_MPEG   ] = &nv40_mpeg_oclass;
-               device->oclass[NVDEV_ENGINE_DISP   ] =  nv04_disp_oclass;
-               device->oclass[NVDEV_ENGINE_PERFMON] =  nv40_perfmon_oclass;
-               break;
-       case 0x41:
-               device->cname = "NV41";
-               device->oclass[NVDEV_SUBDEV_VBIOS  ] = &nouveau_bios_oclass;
-               device->oclass[NVDEV_SUBDEV_GPIO   ] =  nv10_gpio_oclass;
-               device->oclass[NVDEV_SUBDEV_I2C    ] =  nv04_i2c_oclass;
-               device->oclass[NVDEV_SUBDEV_CLOCK  ] = &nv40_clock_oclass;
-               device->oclass[NVDEV_SUBDEV_THERM  ] = &nv40_therm_oclass;
-               device->oclass[NVDEV_SUBDEV_DEVINIT] =  nv1a_devinit_oclass;
-               device->oclass[NVDEV_SUBDEV_MC     ] =  nv40_mc_oclass;
-               device->oclass[NVDEV_SUBDEV_BUS    ] =  nv31_bus_oclass;
-               device->oclass[NVDEV_SUBDEV_TIMER  ] = &nv04_timer_oclass;
-               device->oclass[NVDEV_SUBDEV_FB     ] =  nv41_fb_oclass;
-               device->oclass[NVDEV_SUBDEV_INSTMEM] =  nv40_instmem_oclass;
-               device->oclass[NVDEV_SUBDEV_VM     ] = &nv41_vmmgr_oclass;
-               device->oclass[NVDEV_SUBDEV_VOLT   ] = &nv40_volt_oclass;
-               device->oclass[NVDEV_ENGINE_DMAOBJ ] =  nv04_dmaeng_oclass;
-               device->oclass[NVDEV_ENGINE_FIFO   ] =  nv40_fifo_oclass;
-               device->oclass[NVDEV_ENGINE_SW     ] =  nv10_software_oclass;
-               device->oclass[NVDEV_ENGINE_GR     ] = &nv40_graph_oclass;
-               device->oclass[NVDEV_ENGINE_MPEG   ] = &nv40_mpeg_oclass;
-               device->oclass[NVDEV_ENGINE_DISP   ] =  nv04_disp_oclass;
-               device->oclass[NVDEV_ENGINE_PERFMON] =  nv40_perfmon_oclass;
-               break;
-       case 0x42:
-               device->cname = "NV42";
-               device->oclass[NVDEV_SUBDEV_VBIOS  ] = &nouveau_bios_oclass;
-               device->oclass[NVDEV_SUBDEV_GPIO   ] =  nv10_gpio_oclass;
-               device->oclass[NVDEV_SUBDEV_I2C    ] =  nv04_i2c_oclass;
-               device->oclass[NVDEV_SUBDEV_CLOCK  ] = &nv40_clock_oclass;
-               device->oclass[NVDEV_SUBDEV_THERM  ] = &nv40_therm_oclass;
-               device->oclass[NVDEV_SUBDEV_DEVINIT] =  nv1a_devinit_oclass;
-               device->oclass[NVDEV_SUBDEV_MC     ] =  nv40_mc_oclass;
-               device->oclass[NVDEV_SUBDEV_BUS    ] =  nv31_bus_oclass;
-               device->oclass[NVDEV_SUBDEV_TIMER  ] = &nv04_timer_oclass;
-               device->oclass[NVDEV_SUBDEV_FB     ] =  nv41_fb_oclass;
-               device->oclass[NVDEV_SUBDEV_INSTMEM] =  nv40_instmem_oclass;
-               device->oclass[NVDEV_SUBDEV_VM     ] = &nv41_vmmgr_oclass;
-               device->oclass[NVDEV_SUBDEV_VOLT   ] = &nv40_volt_oclass;
-               device->oclass[NVDEV_ENGINE_DMAOBJ ] =  nv04_dmaeng_oclass;
-               device->oclass[NVDEV_ENGINE_FIFO   ] =  nv40_fifo_oclass;
-               device->oclass[NVDEV_ENGINE_SW     ] =  nv10_software_oclass;
-               device->oclass[NVDEV_ENGINE_GR     ] = &nv40_graph_oclass;
-               device->oclass[NVDEV_ENGINE_MPEG   ] = &nv40_mpeg_oclass;
-               device->oclass[NVDEV_ENGINE_DISP   ] =  nv04_disp_oclass;
-               device->oclass[NVDEV_ENGINE_PERFMON] =  nv40_perfmon_oclass;
-               break;
-       case 0x43:
-               device->cname = "NV43";
-               device->oclass[NVDEV_SUBDEV_VBIOS  ] = &nouveau_bios_oclass;
-               device->oclass[NVDEV_SUBDEV_GPIO   ] =  nv10_gpio_oclass;
-               device->oclass[NVDEV_SUBDEV_I2C    ] =  nv04_i2c_oclass;
-               device->oclass[NVDEV_SUBDEV_CLOCK  ] = &nv40_clock_oclass;
-               device->oclass[NVDEV_SUBDEV_THERM  ] = &nv40_therm_oclass;
-               device->oclass[NVDEV_SUBDEV_DEVINIT] =  nv1a_devinit_oclass;
-               device->oclass[NVDEV_SUBDEV_MC     ] =  nv40_mc_oclass;
-               device->oclass[NVDEV_SUBDEV_BUS    ] =  nv31_bus_oclass;
-               device->oclass[NVDEV_SUBDEV_TIMER  ] = &nv04_timer_oclass;
-               device->oclass[NVDEV_SUBDEV_FB     ] =  nv41_fb_oclass;
-               device->oclass[NVDEV_SUBDEV_INSTMEM] =  nv40_instmem_oclass;
-               device->oclass[NVDEV_SUBDEV_VM     ] = &nv41_vmmgr_oclass;
-               device->oclass[NVDEV_SUBDEV_VOLT   ] = &nv40_volt_oclass;
-               device->oclass[NVDEV_ENGINE_DMAOBJ ] =  nv04_dmaeng_oclass;
-               device->oclass[NVDEV_ENGINE_FIFO   ] =  nv40_fifo_oclass;
-               device->oclass[NVDEV_ENGINE_SW     ] =  nv10_software_oclass;
-               device->oclass[NVDEV_ENGINE_GR     ] = &nv40_graph_oclass;
-               device->oclass[NVDEV_ENGINE_MPEG   ] = &nv40_mpeg_oclass;
-               device->oclass[NVDEV_ENGINE_DISP   ] =  nv04_disp_oclass;
-               device->oclass[NVDEV_ENGINE_PERFMON] =  nv40_perfmon_oclass;
-               break;
-       case 0x45:
-               device->cname = "NV45";
-               device->oclass[NVDEV_SUBDEV_VBIOS  ] = &nouveau_bios_oclass;
-               device->oclass[NVDEV_SUBDEV_GPIO   ] =  nv10_gpio_oclass;
-               device->oclass[NVDEV_SUBDEV_I2C    ] =  nv04_i2c_oclass;
-               device->oclass[NVDEV_SUBDEV_CLOCK  ] = &nv40_clock_oclass;
-               device->oclass[NVDEV_SUBDEV_THERM  ] = &nv40_therm_oclass;
-               device->oclass[NVDEV_SUBDEV_DEVINIT] =  nv1a_devinit_oclass;
-               device->oclass[NVDEV_SUBDEV_MC     ] =  nv40_mc_oclass;
-               device->oclass[NVDEV_SUBDEV_BUS    ] =  nv31_bus_oclass;
-               device->oclass[NVDEV_SUBDEV_TIMER  ] = &nv04_timer_oclass;
-               device->oclass[NVDEV_SUBDEV_FB     ] =  nv40_fb_oclass;
-               device->oclass[NVDEV_SUBDEV_INSTMEM] =  nv40_instmem_oclass;
-               device->oclass[NVDEV_SUBDEV_VM     ] = &nv04_vmmgr_oclass;
-               device->oclass[NVDEV_SUBDEV_VOLT   ] = &nv40_volt_oclass;
-               device->oclass[NVDEV_ENGINE_DMAOBJ ] =  nv04_dmaeng_oclass;
-               device->oclass[NVDEV_ENGINE_FIFO   ] =  nv40_fifo_oclass;
-               device->oclass[NVDEV_ENGINE_SW     ] =  nv10_software_oclass;
-               device->oclass[NVDEV_ENGINE_GR     ] = &nv40_graph_oclass;
-               device->oclass[NVDEV_ENGINE_MPEG   ] = &nv44_mpeg_oclass;
-               device->oclass[NVDEV_ENGINE_DISP   ] =  nv04_disp_oclass;
-               device->oclass[NVDEV_ENGINE_PERFMON] =  nv40_perfmon_oclass;
-               break;
-       case 0x47:
-               device->cname = "G70";
-               device->oclass[NVDEV_SUBDEV_VBIOS  ] = &nouveau_bios_oclass;
-               device->oclass[NVDEV_SUBDEV_GPIO   ] =  nv10_gpio_oclass;
-               device->oclass[NVDEV_SUBDEV_I2C    ] =  nv04_i2c_oclass;
-               device->oclass[NVDEV_SUBDEV_CLOCK  ] = &nv40_clock_oclass;
-               device->oclass[NVDEV_SUBDEV_THERM  ] = &nv40_therm_oclass;
-               device->oclass[NVDEV_SUBDEV_DEVINIT] =  nv1a_devinit_oclass;
-               device->oclass[NVDEV_SUBDEV_MC     ] =  nv40_mc_oclass;
-               device->oclass[NVDEV_SUBDEV_BUS    ] =  nv31_bus_oclass;
-               device->oclass[NVDEV_SUBDEV_TIMER  ] = &nv04_timer_oclass;
-               device->oclass[NVDEV_SUBDEV_FB     ] =  nv47_fb_oclass;
-               device->oclass[NVDEV_SUBDEV_INSTMEM] =  nv40_instmem_oclass;
-               device->oclass[NVDEV_SUBDEV_VM     ] = &nv41_vmmgr_oclass;
-               device->oclass[NVDEV_SUBDEV_VOLT   ] = &nv40_volt_oclass;
-               device->oclass[NVDEV_ENGINE_DMAOBJ ] =  nv04_dmaeng_oclass;
-               device->oclass[NVDEV_ENGINE_FIFO   ] =  nv40_fifo_oclass;
-               device->oclass[NVDEV_ENGINE_SW     ] =  nv10_software_oclass;
-               device->oclass[NVDEV_ENGINE_GR     ] = &nv40_graph_oclass;
-               device->oclass[NVDEV_ENGINE_MPEG   ] = &nv44_mpeg_oclass;
-               device->oclass[NVDEV_ENGINE_DISP   ] =  nv04_disp_oclass;
-               device->oclass[NVDEV_ENGINE_PERFMON] =  nv40_perfmon_oclass;
-               break;
-       case 0x49:
-               device->cname = "G71";
-               device->oclass[NVDEV_SUBDEV_VBIOS  ] = &nouveau_bios_oclass;
-               device->oclass[NVDEV_SUBDEV_GPIO   ] =  nv10_gpio_oclass;
-               device->oclass[NVDEV_SUBDEV_I2C    ] =  nv04_i2c_oclass;
-               device->oclass[NVDEV_SUBDEV_CLOCK  ] = &nv40_clock_oclass;
-               device->oclass[NVDEV_SUBDEV_THERM  ] = &nv40_therm_oclass;
-               device->oclass[NVDEV_SUBDEV_DEVINIT] =  nv1a_devinit_oclass;
-               device->oclass[NVDEV_SUBDEV_MC     ] =  nv40_mc_oclass;
-               device->oclass[NVDEV_SUBDEV_BUS    ] =  nv31_bus_oclass;
-               device->oclass[NVDEV_SUBDEV_TIMER  ] = &nv04_timer_oclass;
-               device->oclass[NVDEV_SUBDEV_FB     ] =  nv49_fb_oclass;
-               device->oclass[NVDEV_SUBDEV_INSTMEM] =  nv40_instmem_oclass;
-               device->oclass[NVDEV_SUBDEV_VM     ] = &nv41_vmmgr_oclass;
-               device->oclass[NVDEV_SUBDEV_VOLT   ] = &nv40_volt_oclass;
-               device->oclass[NVDEV_ENGINE_DMAOBJ ] =  nv04_dmaeng_oclass;
-               device->oclass[NVDEV_ENGINE_FIFO   ] =  nv40_fifo_oclass;
-               device->oclass[NVDEV_ENGINE_SW     ] =  nv10_software_oclass;
-               device->oclass[NVDEV_ENGINE_GR     ] = &nv40_graph_oclass;
-               device->oclass[NVDEV_ENGINE_MPEG   ] = &nv44_mpeg_oclass;
-               device->oclass[NVDEV_ENGINE_DISP   ] =  nv04_disp_oclass;
-               device->oclass[NVDEV_ENGINE_PERFMON] =  nv40_perfmon_oclass;
-               break;
-       case 0x4b:
-               device->cname = "G73";
-               device->oclass[NVDEV_SUBDEV_VBIOS  ] = &nouveau_bios_oclass;
-               device->oclass[NVDEV_SUBDEV_GPIO   ] =  nv10_gpio_oclass;
-               device->oclass[NVDEV_SUBDEV_I2C    ] =  nv04_i2c_oclass;
-               device->oclass[NVDEV_SUBDEV_CLOCK  ] = &nv40_clock_oclass;
-               device->oclass[NVDEV_SUBDEV_THERM  ] = &nv40_therm_oclass;
-               device->oclass[NVDEV_SUBDEV_DEVINIT] =  nv1a_devinit_oclass;
-               device->oclass[NVDEV_SUBDEV_MC     ] =  nv40_mc_oclass;
-               device->oclass[NVDEV_SUBDEV_BUS    ] =  nv31_bus_oclass;
-               device->oclass[NVDEV_SUBDEV_TIMER  ] = &nv04_timer_oclass;
-               device->oclass[NVDEV_SUBDEV_FB     ] =  nv49_fb_oclass;
-               device->oclass[NVDEV_SUBDEV_INSTMEM] =  nv40_instmem_oclass;
-               device->oclass[NVDEV_SUBDEV_VM     ] = &nv41_vmmgr_oclass;
-               device->oclass[NVDEV_SUBDEV_VOLT   ] = &nv40_volt_oclass;
-               device->oclass[NVDEV_ENGINE_DMAOBJ ] =  nv04_dmaeng_oclass;
-               device->oclass[NVDEV_ENGINE_FIFO   ] =  nv40_fifo_oclass;
-               device->oclass[NVDEV_ENGINE_SW     ] =  nv10_software_oclass;
-               device->oclass[NVDEV_ENGINE_GR     ] = &nv40_graph_oclass;
-               device->oclass[NVDEV_ENGINE_MPEG   ] = &nv44_mpeg_oclass;
-               device->oclass[NVDEV_ENGINE_DISP   ] =  nv04_disp_oclass;
-               device->oclass[NVDEV_ENGINE_PERFMON] =  nv40_perfmon_oclass;
-               break;
-       case 0x44:
-               device->cname = "NV44";
-               device->oclass[NVDEV_SUBDEV_VBIOS  ] = &nouveau_bios_oclass;
-               device->oclass[NVDEV_SUBDEV_GPIO   ] =  nv10_gpio_oclass;
-               device->oclass[NVDEV_SUBDEV_I2C    ] =  nv04_i2c_oclass;
-               device->oclass[NVDEV_SUBDEV_CLOCK  ] = &nv40_clock_oclass;
-               device->oclass[NVDEV_SUBDEV_THERM  ] = &nv40_therm_oclass;
-               device->oclass[NVDEV_SUBDEV_DEVINIT] =  nv1a_devinit_oclass;
-               device->oclass[NVDEV_SUBDEV_MC     ] =  nv44_mc_oclass;
-               device->oclass[NVDEV_SUBDEV_BUS    ] =  nv31_bus_oclass;
-               device->oclass[NVDEV_SUBDEV_TIMER  ] = &nv04_timer_oclass;
-               device->oclass[NVDEV_SUBDEV_FB     ] =  nv44_fb_oclass;
-               device->oclass[NVDEV_SUBDEV_INSTMEM] =  nv40_instmem_oclass;
-               device->oclass[NVDEV_SUBDEV_VM     ] = &nv44_vmmgr_oclass;
-               device->oclass[NVDEV_SUBDEV_VOLT   ] = &nv40_volt_oclass;
-               device->oclass[NVDEV_ENGINE_DMAOBJ ] =  nv04_dmaeng_oclass;
-               device->oclass[NVDEV_ENGINE_FIFO   ] =  nv40_fifo_oclass;
-               device->oclass[NVDEV_ENGINE_SW     ] =  nv10_software_oclass;
-               device->oclass[NVDEV_ENGINE_GR     ] = &nv40_graph_oclass;
-               device->oclass[NVDEV_ENGINE_MPEG   ] = &nv44_mpeg_oclass;
-               device->oclass[NVDEV_ENGINE_DISP   ] =  nv04_disp_oclass;
-               device->oclass[NVDEV_ENGINE_PERFMON] =  nv40_perfmon_oclass;
-               break;
-       case 0x46:
-               device->cname = "G72";
-               device->oclass[NVDEV_SUBDEV_VBIOS  ] = &nouveau_bios_oclass;
-               device->oclass[NVDEV_SUBDEV_GPIO   ] =  nv10_gpio_oclass;
-               device->oclass[NVDEV_SUBDEV_I2C    ] =  nv04_i2c_oclass;
-               device->oclass[NVDEV_SUBDEV_CLOCK  ] = &nv40_clock_oclass;
-               device->oclass[NVDEV_SUBDEV_THERM  ] = &nv40_therm_oclass;
-               device->oclass[NVDEV_SUBDEV_DEVINIT] =  nv1a_devinit_oclass;
-               device->oclass[NVDEV_SUBDEV_MC     ] =  nv44_mc_oclass;
-               device->oclass[NVDEV_SUBDEV_BUS    ] =  nv31_bus_oclass;
-               device->oclass[NVDEV_SUBDEV_TIMER  ] = &nv04_timer_oclass;
-               device->oclass[NVDEV_SUBDEV_FB     ] =  nv46_fb_oclass;
-               device->oclass[NVDEV_SUBDEV_INSTMEM] =  nv40_instmem_oclass;
-               device->oclass[NVDEV_SUBDEV_VM     ] = &nv44_vmmgr_oclass;
-               device->oclass[NVDEV_SUBDEV_VOLT   ] = &nv40_volt_oclass;
-               device->oclass[NVDEV_ENGINE_DMAOBJ ] =  nv04_dmaeng_oclass;
-               device->oclass[NVDEV_ENGINE_FIFO   ] =  nv40_fifo_oclass;
-               device->oclass[NVDEV_ENGINE_SW     ] =  nv10_software_oclass;
-               device->oclass[NVDEV_ENGINE_GR     ] = &nv40_graph_oclass;
-               device->oclass[NVDEV_ENGINE_MPEG   ] = &nv44_mpeg_oclass;
-               device->oclass[NVDEV_ENGINE_DISP   ] =  nv04_disp_oclass;
-               device->oclass[NVDEV_ENGINE_PERFMON] =  nv40_perfmon_oclass;
-               break;
-       case 0x4a:
-               device->cname = "NV44A";
-               device->oclass[NVDEV_SUBDEV_VBIOS  ] = &nouveau_bios_oclass;
-               device->oclass[NVDEV_SUBDEV_GPIO   ] =  nv10_gpio_oclass;
-               device->oclass[NVDEV_SUBDEV_I2C    ] =  nv04_i2c_oclass;
-               device->oclass[NVDEV_SUBDEV_CLOCK  ] = &nv40_clock_oclass;
-               device->oclass[NVDEV_SUBDEV_THERM  ] = &nv40_therm_oclass;
-               device->oclass[NVDEV_SUBDEV_DEVINIT] =  nv1a_devinit_oclass;
-               device->oclass[NVDEV_SUBDEV_MC     ] =  nv44_mc_oclass;
-               device->oclass[NVDEV_SUBDEV_BUS    ] =  nv31_bus_oclass;
-               device->oclass[NVDEV_SUBDEV_TIMER  ] = &nv04_timer_oclass;
-               device->oclass[NVDEV_SUBDEV_FB     ] =  nv44_fb_oclass;
-               device->oclass[NVDEV_SUBDEV_INSTMEM] =  nv40_instmem_oclass;
-               device->oclass[NVDEV_SUBDEV_VM     ] = &nv44_vmmgr_oclass;
-               device->oclass[NVDEV_SUBDEV_VOLT   ] = &nv40_volt_oclass;
-               device->oclass[NVDEV_ENGINE_DMAOBJ ] =  nv04_dmaeng_oclass;
-               device->oclass[NVDEV_ENGINE_FIFO   ] =  nv40_fifo_oclass;
-               device->oclass[NVDEV_ENGINE_SW     ] =  nv10_software_oclass;
-               device->oclass[NVDEV_ENGINE_GR     ] = &nv40_graph_oclass;
-               device->oclass[NVDEV_ENGINE_MPEG   ] = &nv44_mpeg_oclass;
-               device->oclass[NVDEV_ENGINE_DISP   ] =  nv04_disp_oclass;
-               device->oclass[NVDEV_ENGINE_PERFMON] =  nv40_perfmon_oclass;
-               break;
-       case 0x4c:
-               device->cname = "C61";
-               device->oclass[NVDEV_SUBDEV_VBIOS  ] = &nouveau_bios_oclass;
-               device->oclass[NVDEV_SUBDEV_GPIO   ] =  nv10_gpio_oclass;
-               device->oclass[NVDEV_SUBDEV_I2C    ] =  nv04_i2c_oclass;
-               device->oclass[NVDEV_SUBDEV_CLOCK  ] = &nv40_clock_oclass;
-               device->oclass[NVDEV_SUBDEV_THERM  ] = &nv40_therm_oclass;
-               device->oclass[NVDEV_SUBDEV_DEVINIT] =  nv1a_devinit_oclass;
-               device->oclass[NVDEV_SUBDEV_MC     ] =  nv4c_mc_oclass;
-               device->oclass[NVDEV_SUBDEV_BUS    ] =  nv31_bus_oclass;
-               device->oclass[NVDEV_SUBDEV_TIMER  ] = &nv04_timer_oclass;
-               device->oclass[NVDEV_SUBDEV_FB     ] =  nv46_fb_oclass;
-               device->oclass[NVDEV_SUBDEV_INSTMEM] =  nv40_instmem_oclass;
-               device->oclass[NVDEV_SUBDEV_VM     ] = &nv44_vmmgr_oclass;
-               device->oclass[NVDEV_SUBDEV_VOLT   ] = &nv40_volt_oclass;
-               device->oclass[NVDEV_ENGINE_DMAOBJ ] =  nv04_dmaeng_oclass;
-               device->oclass[NVDEV_ENGINE_FIFO   ] =  nv40_fifo_oclass;
-               device->oclass[NVDEV_ENGINE_SW     ] =  nv10_software_oclass;
-               device->oclass[NVDEV_ENGINE_GR     ] = &nv40_graph_oclass;
-               device->oclass[NVDEV_ENGINE_MPEG   ] = &nv44_mpeg_oclass;
-               device->oclass[NVDEV_ENGINE_DISP   ] =  nv04_disp_oclass;
-               device->oclass[NVDEV_ENGINE_PERFMON] =  nv40_perfmon_oclass;
-               break;
-       case 0x4e:
-               device->cname = "C51";
-               device->oclass[NVDEV_SUBDEV_VBIOS  ] = &nouveau_bios_oclass;
-               device->oclass[NVDEV_SUBDEV_GPIO   ] =  nv10_gpio_oclass;
-               device->oclass[NVDEV_SUBDEV_I2C    ] =  nv4e_i2c_oclass;
-               device->oclass[NVDEV_SUBDEV_CLOCK  ] = &nv40_clock_oclass;
-               device->oclass[NVDEV_SUBDEV_THERM  ] = &nv40_therm_oclass;
-               device->oclass[NVDEV_SUBDEV_DEVINIT] =  nv1a_devinit_oclass;
-               device->oclass[NVDEV_SUBDEV_MC     ] =  nv4c_mc_oclass;
-               device->oclass[NVDEV_SUBDEV_BUS    ] =  nv31_bus_oclass;
-               device->oclass[NVDEV_SUBDEV_TIMER  ] = &nv04_timer_oclass;
-               device->oclass[NVDEV_SUBDEV_FB     ] =  nv4e_fb_oclass;
-               device->oclass[NVDEV_SUBDEV_INSTMEM] =  nv40_instmem_oclass;
-               device->oclass[NVDEV_SUBDEV_VM     ] = &nv44_vmmgr_oclass;
-               device->oclass[NVDEV_SUBDEV_VOLT   ] = &nv40_volt_oclass;
-               device->oclass[NVDEV_ENGINE_DMAOBJ ] =  nv04_dmaeng_oclass;
-               device->oclass[NVDEV_ENGINE_FIFO   ] =  nv40_fifo_oclass;
-               device->oclass[NVDEV_ENGINE_SW     ] =  nv10_software_oclass;
-               device->oclass[NVDEV_ENGINE_GR     ] = &nv40_graph_oclass;
-               device->oclass[NVDEV_ENGINE_MPEG   ] = &nv44_mpeg_oclass;
-               device->oclass[NVDEV_ENGINE_DISP   ] =  nv04_disp_oclass;
-               device->oclass[NVDEV_ENGINE_PERFMON] =  nv40_perfmon_oclass;
-               break;
-       case 0x63:
-               device->cname = "C73";
-               device->oclass[NVDEV_SUBDEV_VBIOS  ] = &nouveau_bios_oclass;
-               device->oclass[NVDEV_SUBDEV_GPIO   ] =  nv10_gpio_oclass;
-               device->oclass[NVDEV_SUBDEV_I2C    ] =  nv04_i2c_oclass;
-               device->oclass[NVDEV_SUBDEV_CLOCK  ] = &nv40_clock_oclass;
-               device->oclass[NVDEV_SUBDEV_THERM  ] = &nv40_therm_oclass;
-               device->oclass[NVDEV_SUBDEV_DEVINIT] =  nv1a_devinit_oclass;
-               device->oclass[NVDEV_SUBDEV_MC     ] =  nv4c_mc_oclass;
-               device->oclass[NVDEV_SUBDEV_BUS    ] =  nv31_bus_oclass;
-               device->oclass[NVDEV_SUBDEV_TIMER  ] = &nv04_timer_oclass;
-               device->oclass[NVDEV_SUBDEV_FB     ] =  nv46_fb_oclass;
-               device->oclass[NVDEV_SUBDEV_INSTMEM] =  nv40_instmem_oclass;
-               device->oclass[NVDEV_SUBDEV_VM     ] = &nv44_vmmgr_oclass;
-               device->oclass[NVDEV_SUBDEV_VOLT   ] = &nv40_volt_oclass;
-               device->oclass[NVDEV_ENGINE_DMAOBJ ] =  nv04_dmaeng_oclass;
-               device->oclass[NVDEV_ENGINE_FIFO   ] =  nv40_fifo_oclass;
-               device->oclass[NVDEV_ENGINE_SW     ] =  nv10_software_oclass;
-               device->oclass[NVDEV_ENGINE_GR     ] = &nv40_graph_oclass;
-               device->oclass[NVDEV_ENGINE_MPEG   ] = &nv44_mpeg_oclass;
-               device->oclass[NVDEV_ENGINE_DISP   ] =  nv04_disp_oclass;
-               device->oclass[NVDEV_ENGINE_PERFMON] =  nv40_perfmon_oclass;
-               break;
-       case 0x67:
-               device->cname = "C67";
-               device->oclass[NVDEV_SUBDEV_VBIOS  ] = &nouveau_bios_oclass;
-               device->oclass[NVDEV_SUBDEV_GPIO   ] =  nv10_gpio_oclass;
-               device->oclass[NVDEV_SUBDEV_I2C    ] =  nv04_i2c_oclass;
-               device->oclass[NVDEV_SUBDEV_CLOCK  ] = &nv40_clock_oclass;
-               device->oclass[NVDEV_SUBDEV_THERM  ] = &nv40_therm_oclass;
-               device->oclass[NVDEV_SUBDEV_DEVINIT] =  nv1a_devinit_oclass;
-               device->oclass[NVDEV_SUBDEV_MC     ] =  nv4c_mc_oclass;
-               device->oclass[NVDEV_SUBDEV_BUS    ] =  nv31_bus_oclass;
-               device->oclass[NVDEV_SUBDEV_TIMER  ] = &nv04_timer_oclass;
-               device->oclass[NVDEV_SUBDEV_FB     ] =  nv46_fb_oclass;
-               device->oclass[NVDEV_SUBDEV_INSTMEM] =  nv40_instmem_oclass;
-               device->oclass[NVDEV_SUBDEV_VM     ] = &nv44_vmmgr_oclass;
-               device->oclass[NVDEV_SUBDEV_VOLT   ] = &nv40_volt_oclass;
-               device->oclass[NVDEV_ENGINE_DMAOBJ ] =  nv04_dmaeng_oclass;
-               device->oclass[NVDEV_ENGINE_FIFO   ] =  nv40_fifo_oclass;
-               device->oclass[NVDEV_ENGINE_SW     ] =  nv10_software_oclass;
-               device->oclass[NVDEV_ENGINE_GR     ] = &nv40_graph_oclass;
-               device->oclass[NVDEV_ENGINE_MPEG   ] = &nv44_mpeg_oclass;
-               device->oclass[NVDEV_ENGINE_DISP   ] =  nv04_disp_oclass;
-               device->oclass[NVDEV_ENGINE_PERFMON] =  nv40_perfmon_oclass;
-               break;
-       case 0x68:
-               device->cname = "C68";
-               device->oclass[NVDEV_SUBDEV_VBIOS  ] = &nouveau_bios_oclass;
-               device->oclass[NVDEV_SUBDEV_GPIO   ] =  nv10_gpio_oclass;
-               device->oclass[NVDEV_SUBDEV_I2C    ] =  nv04_i2c_oclass;
-               device->oclass[NVDEV_SUBDEV_CLOCK  ] = &nv40_clock_oclass;
-               device->oclass[NVDEV_SUBDEV_THERM  ] = &nv40_therm_oclass;
-               device->oclass[NVDEV_SUBDEV_DEVINIT] =  nv1a_devinit_oclass;
-               device->oclass[NVDEV_SUBDEV_MC     ] =  nv4c_mc_oclass;
-               device->oclass[NVDEV_SUBDEV_BUS    ] =  nv31_bus_oclass;
-               device->oclass[NVDEV_SUBDEV_TIMER  ] = &nv04_timer_oclass;
-               device->oclass[NVDEV_SUBDEV_FB     ] =  nv46_fb_oclass;
-               device->oclass[NVDEV_SUBDEV_INSTMEM] =  nv40_instmem_oclass;
-               device->oclass[NVDEV_SUBDEV_VM     ] = &nv44_vmmgr_oclass;
-               device->oclass[NVDEV_SUBDEV_VOLT   ] = &nv40_volt_oclass;
-               device->oclass[NVDEV_ENGINE_DMAOBJ ] =  nv04_dmaeng_oclass;
-               device->oclass[NVDEV_ENGINE_FIFO   ] =  nv40_fifo_oclass;
-               device->oclass[NVDEV_ENGINE_SW     ] =  nv10_software_oclass;
-               device->oclass[NVDEV_ENGINE_GR     ] = &nv40_graph_oclass;
-               device->oclass[NVDEV_ENGINE_MPEG   ] = &nv44_mpeg_oclass;
-               device->oclass[NVDEV_ENGINE_DISP   ] =  nv04_disp_oclass;
-               device->oclass[NVDEV_ENGINE_PERFMON] =  nv40_perfmon_oclass;
-               break;
-       default:
-               nv_fatal(device, "unknown Curie chipset\n");
-               return -EINVAL;
-       }
-
-       return 0;
-}
diff --git a/drivers/gpu/drm/nouveau/core/engine/device/nv50.c b/drivers/gpu/drm/nouveau/core/engine/device/nv50.c
deleted file mode 100644 (file)
index 96f568d..0000000
+++ /dev/null
@@ -1,475 +0,0 @@
-/*
- * Copyright 2012 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 <subdev/bios.h>
-#include <subdev/bus.h>
-#include <subdev/gpio.h>
-#include <subdev/i2c.h>
-#include <subdev/fuse.h>
-#include <subdev/clock.h>
-#include <subdev/therm.h>
-#include <subdev/mxm.h>
-#include <subdev/devinit.h>
-#include <subdev/mc.h>
-#include <subdev/timer.h>
-#include <subdev/fb.h>
-#include <subdev/instmem.h>
-#include <subdev/vm.h>
-#include <subdev/bar.h>
-#include <subdev/pwr.h>
-#include <subdev/volt.h>
-
-#include <engine/device.h>
-#include <engine/dmaobj.h>
-#include <engine/fifo.h>
-#include <engine/software.h>
-#include <engine/graph.h>
-#include <engine/mpeg.h>
-#include <engine/vp.h>
-#include <engine/crypt.h>
-#include <engine/bsp.h>
-#include <engine/ppp.h>
-#include <engine/copy.h>
-#include <engine/disp.h>
-#include <engine/perfmon.h>
-
-int
-nv50_identify(struct nouveau_device *device)
-{
-       switch (device->chipset) {
-       case 0x50:
-               device->cname = "G80";
-               device->oclass[NVDEV_SUBDEV_VBIOS  ] = &nouveau_bios_oclass;
-               device->oclass[NVDEV_SUBDEV_GPIO   ] =  nv50_gpio_oclass;
-               device->oclass[NVDEV_SUBDEV_I2C    ] =  nv50_i2c_oclass;
-               device->oclass[NVDEV_SUBDEV_FUSE   ] =  &g80_fuse_oclass;
-               device->oclass[NVDEV_SUBDEV_CLOCK  ] =  nv50_clock_oclass;
-               device->oclass[NVDEV_SUBDEV_THERM  ] = &nv50_therm_oclass;
-               device->oclass[NVDEV_SUBDEV_MXM    ] = &nv50_mxm_oclass;
-               device->oclass[NVDEV_SUBDEV_DEVINIT] =  nv50_devinit_oclass;
-               device->oclass[NVDEV_SUBDEV_MC     ] =  nv50_mc_oclass;
-               device->oclass[NVDEV_SUBDEV_BUS    ] =  nv50_bus_oclass;
-               device->oclass[NVDEV_SUBDEV_TIMER  ] = &nv04_timer_oclass;
-               device->oclass[NVDEV_SUBDEV_FB     ] =  nv50_fb_oclass;
-               device->oclass[NVDEV_SUBDEV_INSTMEM] =  nv50_instmem_oclass;
-               device->oclass[NVDEV_SUBDEV_VM     ] = &nv50_vmmgr_oclass;
-               device->oclass[NVDEV_SUBDEV_BAR    ] = &nv50_bar_oclass;
-               device->oclass[NVDEV_SUBDEV_VOLT   ] = &nv40_volt_oclass;
-               device->oclass[NVDEV_ENGINE_DMAOBJ ] =  nv50_dmaeng_oclass;
-               device->oclass[NVDEV_ENGINE_FIFO   ] =  nv50_fifo_oclass;
-               device->oclass[NVDEV_ENGINE_SW     ] =  nv50_software_oclass;
-               device->oclass[NVDEV_ENGINE_GR     ] = &nv50_graph_oclass;
-               device->oclass[NVDEV_ENGINE_MPEG   ] = &nv50_mpeg_oclass;
-               device->oclass[NVDEV_ENGINE_DISP   ] =  nv50_disp_oclass;
-               device->oclass[NVDEV_ENGINE_PERFMON] =  nv50_perfmon_oclass;
-               break;
-       case 0x84:
-               device->cname = "G84";
-               device->oclass[NVDEV_SUBDEV_VBIOS  ] = &nouveau_bios_oclass;
-               device->oclass[NVDEV_SUBDEV_GPIO   ] =  nv50_gpio_oclass;
-               device->oclass[NVDEV_SUBDEV_I2C    ] =  nv50_i2c_oclass;
-               device->oclass[NVDEV_SUBDEV_FUSE   ] =  &g80_fuse_oclass;
-               device->oclass[NVDEV_SUBDEV_CLOCK  ] =  nv84_clock_oclass;
-               device->oclass[NVDEV_SUBDEV_THERM  ] = &nv84_therm_oclass;
-               device->oclass[NVDEV_SUBDEV_MXM    ] = &nv50_mxm_oclass;
-               device->oclass[NVDEV_SUBDEV_DEVINIT] =  nv84_devinit_oclass;
-               device->oclass[NVDEV_SUBDEV_MC     ] =  nv50_mc_oclass;
-               device->oclass[NVDEV_SUBDEV_BUS    ] =  nv50_bus_oclass;
-               device->oclass[NVDEV_SUBDEV_TIMER  ] = &nv04_timer_oclass;
-               device->oclass[NVDEV_SUBDEV_FB     ] =  nv84_fb_oclass;
-               device->oclass[NVDEV_SUBDEV_INSTMEM] =  nv50_instmem_oclass;
-               device->oclass[NVDEV_SUBDEV_VM     ] = &nv50_vmmgr_oclass;
-               device->oclass[NVDEV_SUBDEV_BAR    ] = &nv50_bar_oclass;
-               device->oclass[NVDEV_SUBDEV_VOLT   ] = &nv40_volt_oclass;
-               device->oclass[NVDEV_ENGINE_DMAOBJ ] =  nv50_dmaeng_oclass;
-               device->oclass[NVDEV_ENGINE_FIFO   ] =  nv84_fifo_oclass;
-               device->oclass[NVDEV_ENGINE_SW     ] =  nv50_software_oclass;
-               device->oclass[NVDEV_ENGINE_GR     ] = &nv50_graph_oclass;
-               device->oclass[NVDEV_ENGINE_MPEG   ] = &nv84_mpeg_oclass;
-               device->oclass[NVDEV_ENGINE_VP     ] = &nv84_vp_oclass;
-               device->oclass[NVDEV_ENGINE_CRYPT  ] = &nv84_crypt_oclass;
-               device->oclass[NVDEV_ENGINE_BSP    ] = &nv84_bsp_oclass;
-               device->oclass[NVDEV_ENGINE_DISP   ] =  nv84_disp_oclass;
-               device->oclass[NVDEV_ENGINE_PERFMON] =  nv84_perfmon_oclass;
-               break;
-       case 0x86:
-               device->cname = "G86";
-               device->oclass[NVDEV_SUBDEV_VBIOS  ] = &nouveau_bios_oclass;
-               device->oclass[NVDEV_SUBDEV_GPIO   ] =  nv50_gpio_oclass;
-               device->oclass[NVDEV_SUBDEV_I2C    ] =  nv50_i2c_oclass;
-               device->oclass[NVDEV_SUBDEV_FUSE   ] =  &g80_fuse_oclass;
-               device->oclass[NVDEV_SUBDEV_CLOCK  ] =  nv84_clock_oclass;
-               device->oclass[NVDEV_SUBDEV_THERM  ] = &nv84_therm_oclass;
-               device->oclass[NVDEV_SUBDEV_MXM    ] = &nv50_mxm_oclass;
-               device->oclass[NVDEV_SUBDEV_DEVINIT] =  nv84_devinit_oclass;
-               device->oclass[NVDEV_SUBDEV_MC     ] =  nv50_mc_oclass;
-               device->oclass[NVDEV_SUBDEV_BUS    ] =  nv50_bus_oclass;
-               device->oclass[NVDEV_SUBDEV_TIMER  ] = &nv04_timer_oclass;
-               device->oclass[NVDEV_SUBDEV_FB     ] =  nv84_fb_oclass;
-               device->oclass[NVDEV_SUBDEV_INSTMEM] =  nv50_instmem_oclass;
-               device->oclass[NVDEV_SUBDEV_VM     ] = &nv50_vmmgr_oclass;
-               device->oclass[NVDEV_SUBDEV_BAR    ] = &nv50_bar_oclass;
-               device->oclass[NVDEV_SUBDEV_VOLT   ] = &nv40_volt_oclass;
-               device->oclass[NVDEV_ENGINE_DMAOBJ ] =  nv50_dmaeng_oclass;
-               device->oclass[NVDEV_ENGINE_FIFO   ] =  nv84_fifo_oclass;
-               device->oclass[NVDEV_ENGINE_SW     ] =  nv50_software_oclass;
-               device->oclass[NVDEV_ENGINE_GR     ] = &nv50_graph_oclass;
-               device->oclass[NVDEV_ENGINE_MPEG   ] = &nv84_mpeg_oclass;
-               device->oclass[NVDEV_ENGINE_VP     ] = &nv84_vp_oclass;
-               device->oclass[NVDEV_ENGINE_CRYPT  ] = &nv84_crypt_oclass;
-               device->oclass[NVDEV_ENGINE_BSP    ] = &nv84_bsp_oclass;
-               device->oclass[NVDEV_ENGINE_DISP   ] =  nv84_disp_oclass;
-               device->oclass[NVDEV_ENGINE_PERFMON] =  nv84_perfmon_oclass;
-               break;
-       case 0x92:
-               device->cname = "G92";
-               device->oclass[NVDEV_SUBDEV_VBIOS  ] = &nouveau_bios_oclass;
-               device->oclass[NVDEV_SUBDEV_GPIO   ] =  nv50_gpio_oclass;
-               device->oclass[NVDEV_SUBDEV_I2C    ] =  nv50_i2c_oclass;
-               device->oclass[NVDEV_SUBDEV_FUSE   ] =  &g80_fuse_oclass;
-               device->oclass[NVDEV_SUBDEV_CLOCK  ] =  nv84_clock_oclass;
-               device->oclass[NVDEV_SUBDEV_THERM  ] = &nv84_therm_oclass;
-               device->oclass[NVDEV_SUBDEV_MXM    ] = &nv50_mxm_oclass;
-               device->oclass[NVDEV_SUBDEV_DEVINIT] =  nv84_devinit_oclass;
-               device->oclass[NVDEV_SUBDEV_MC     ] =  nv50_mc_oclass;
-               device->oclass[NVDEV_SUBDEV_BUS    ] =  nv50_bus_oclass;
-               device->oclass[NVDEV_SUBDEV_TIMER  ] = &nv04_timer_oclass;
-               device->oclass[NVDEV_SUBDEV_FB     ] =  nv84_fb_oclass;
-               device->oclass[NVDEV_SUBDEV_INSTMEM] =  nv50_instmem_oclass;
-               device->oclass[NVDEV_SUBDEV_VM     ] = &nv50_vmmgr_oclass;
-               device->oclass[NVDEV_SUBDEV_BAR    ] = &nv50_bar_oclass;
-               device->oclass[NVDEV_SUBDEV_VOLT   ] = &nv40_volt_oclass;
-               device->oclass[NVDEV_ENGINE_DMAOBJ ] =  nv50_dmaeng_oclass;
-               device->oclass[NVDEV_ENGINE_FIFO   ] =  nv84_fifo_oclass;
-               device->oclass[NVDEV_ENGINE_SW     ] =  nv50_software_oclass;
-               device->oclass[NVDEV_ENGINE_GR     ] = &nv50_graph_oclass;
-               device->oclass[NVDEV_ENGINE_MPEG   ] = &nv84_mpeg_oclass;
-               device->oclass[NVDEV_ENGINE_VP     ] = &nv84_vp_oclass;
-               device->oclass[NVDEV_ENGINE_CRYPT  ] = &nv84_crypt_oclass;
-               device->oclass[NVDEV_ENGINE_BSP    ] = &nv84_bsp_oclass;
-               device->oclass[NVDEV_ENGINE_DISP   ] =  nv84_disp_oclass;
-               device->oclass[NVDEV_ENGINE_PERFMON] =  nv84_perfmon_oclass;
-               break;
-       case 0x94:
-               device->cname = "G94";
-               device->oclass[NVDEV_SUBDEV_VBIOS  ] = &nouveau_bios_oclass;
-               device->oclass[NVDEV_SUBDEV_GPIO   ] =  nv94_gpio_oclass;
-               device->oclass[NVDEV_SUBDEV_I2C    ] =  nv94_i2c_oclass;
-               device->oclass[NVDEV_SUBDEV_FUSE   ] =  &g80_fuse_oclass;
-               device->oclass[NVDEV_SUBDEV_CLOCK  ] =  nv84_clock_oclass;
-               device->oclass[NVDEV_SUBDEV_THERM  ] = &nv84_therm_oclass;
-               device->oclass[NVDEV_SUBDEV_MXM    ] = &nv50_mxm_oclass;
-               device->oclass[NVDEV_SUBDEV_DEVINIT] =  nv84_devinit_oclass;
-               device->oclass[NVDEV_SUBDEV_MC     ] =  nv94_mc_oclass;
-               device->oclass[NVDEV_SUBDEV_BUS    ] =  nv94_bus_oclass;
-               device->oclass[NVDEV_SUBDEV_TIMER  ] = &nv04_timer_oclass;
-               device->oclass[NVDEV_SUBDEV_FB     ] =  nv84_fb_oclass;
-               device->oclass[NVDEV_SUBDEV_INSTMEM] =  nv50_instmem_oclass;
-               device->oclass[NVDEV_SUBDEV_VM     ] = &nv50_vmmgr_oclass;
-               device->oclass[NVDEV_SUBDEV_BAR    ] = &nv50_bar_oclass;
-               device->oclass[NVDEV_SUBDEV_VOLT   ] = &nv40_volt_oclass;
-               device->oclass[NVDEV_ENGINE_DMAOBJ ] =  nv50_dmaeng_oclass;
-               device->oclass[NVDEV_ENGINE_FIFO   ] =  nv84_fifo_oclass;
-               device->oclass[NVDEV_ENGINE_SW     ] =  nv50_software_oclass;
-               device->oclass[NVDEV_ENGINE_GR     ] = &nv50_graph_oclass;
-               device->oclass[NVDEV_ENGINE_MPEG   ] = &nv84_mpeg_oclass;
-               device->oclass[NVDEV_ENGINE_VP     ] = &nv84_vp_oclass;
-               device->oclass[NVDEV_ENGINE_CRYPT  ] = &nv84_crypt_oclass;
-               device->oclass[NVDEV_ENGINE_BSP    ] = &nv84_bsp_oclass;
-               device->oclass[NVDEV_ENGINE_DISP   ] =  nv94_disp_oclass;
-               device->oclass[NVDEV_ENGINE_PERFMON] =  nv84_perfmon_oclass;
-               break;
-       case 0x96:
-               device->cname = "G96";
-               device->oclass[NVDEV_SUBDEV_VBIOS  ] = &nouveau_bios_oclass;
-               device->oclass[NVDEV_SUBDEV_GPIO   ] =  nv94_gpio_oclass;
-               device->oclass[NVDEV_SUBDEV_I2C    ] =  nv94_i2c_oclass;
-               device->oclass[NVDEV_SUBDEV_FUSE   ] =  &g80_fuse_oclass;
-               device->oclass[NVDEV_SUBDEV_CLOCK  ] =  nv84_clock_oclass;
-               device->oclass[NVDEV_SUBDEV_THERM  ] = &nv84_therm_oclass;
-               device->oclass[NVDEV_SUBDEV_MXM    ] = &nv50_mxm_oclass;
-               device->oclass[NVDEV_SUBDEV_DEVINIT] =  nv84_devinit_oclass;
-               device->oclass[NVDEV_SUBDEV_MC     ] =  nv94_mc_oclass;
-               device->oclass[NVDEV_SUBDEV_BUS    ] =  nv94_bus_oclass;
-               device->oclass[NVDEV_SUBDEV_TIMER  ] = &nv04_timer_oclass;
-               device->oclass[NVDEV_SUBDEV_FB     ] =  nv84_fb_oclass;
-               device->oclass[NVDEV_SUBDEV_INSTMEM] =  nv50_instmem_oclass;
-               device->oclass[NVDEV_SUBDEV_VM     ] = &nv50_vmmgr_oclass;
-               device->oclass[NVDEV_SUBDEV_BAR    ] = &nv50_bar_oclass;
-               device->oclass[NVDEV_SUBDEV_VOLT   ] = &nv40_volt_oclass;
-               device->oclass[NVDEV_ENGINE_DMAOBJ ] =  nv50_dmaeng_oclass;
-               device->oclass[NVDEV_ENGINE_FIFO   ] =  nv84_fifo_oclass;
-               device->oclass[NVDEV_ENGINE_SW     ] =  nv50_software_oclass;
-               device->oclass[NVDEV_ENGINE_GR     ] = &nv50_graph_oclass;
-               device->oclass[NVDEV_ENGINE_MPEG   ] = &nv84_mpeg_oclass;
-               device->oclass[NVDEV_ENGINE_VP     ] = &nv84_vp_oclass;
-               device->oclass[NVDEV_ENGINE_CRYPT  ] = &nv84_crypt_oclass;
-               device->oclass[NVDEV_ENGINE_BSP    ] = &nv84_bsp_oclass;
-               device->oclass[NVDEV_ENGINE_DISP   ] =  nv94_disp_oclass;
-               device->oclass[NVDEV_ENGINE_PERFMON] =  nv84_perfmon_oclass;
-               break;
-       case 0x98:
-               device->cname = "G98";
-               device->oclass[NVDEV_SUBDEV_VBIOS  ] = &nouveau_bios_oclass;
-               device->oclass[NVDEV_SUBDEV_GPIO   ] =  nv94_gpio_oclass;
-               device->oclass[NVDEV_SUBDEV_I2C    ] =  nv94_i2c_oclass;
-               device->oclass[NVDEV_SUBDEV_FUSE   ] =  &g80_fuse_oclass;
-               device->oclass[NVDEV_SUBDEV_CLOCK  ] =  nv84_clock_oclass;
-               device->oclass[NVDEV_SUBDEV_THERM  ] = &nv84_therm_oclass;
-               device->oclass[NVDEV_SUBDEV_MXM    ] = &nv50_mxm_oclass;
-               device->oclass[NVDEV_SUBDEV_DEVINIT] =  nv98_devinit_oclass;
-               device->oclass[NVDEV_SUBDEV_MC     ] =  nv98_mc_oclass;
-               device->oclass[NVDEV_SUBDEV_BUS    ] =  nv94_bus_oclass;
-               device->oclass[NVDEV_SUBDEV_TIMER  ] = &nv04_timer_oclass;
-               device->oclass[NVDEV_SUBDEV_FB     ] =  nv84_fb_oclass;
-               device->oclass[NVDEV_SUBDEV_INSTMEM] =  nv50_instmem_oclass;
-               device->oclass[NVDEV_SUBDEV_VM     ] = &nv50_vmmgr_oclass;
-               device->oclass[NVDEV_SUBDEV_BAR    ] = &nv50_bar_oclass;
-               device->oclass[NVDEV_SUBDEV_VOLT   ] = &nv40_volt_oclass;
-               device->oclass[NVDEV_ENGINE_DMAOBJ ] =  nv50_dmaeng_oclass;
-               device->oclass[NVDEV_ENGINE_FIFO   ] =  nv84_fifo_oclass;
-               device->oclass[NVDEV_ENGINE_SW     ] =  nv50_software_oclass;
-               device->oclass[NVDEV_ENGINE_GR     ] = &nv50_graph_oclass;
-               device->oclass[NVDEV_ENGINE_VP     ] = &nv98_vp_oclass;
-               device->oclass[NVDEV_ENGINE_CRYPT  ] = &nv98_crypt_oclass;
-               device->oclass[NVDEV_ENGINE_BSP    ] = &nv98_bsp_oclass;
-               device->oclass[NVDEV_ENGINE_PPP    ] = &nv98_ppp_oclass;
-               device->oclass[NVDEV_ENGINE_DISP   ] =  nv94_disp_oclass;
-               device->oclass[NVDEV_ENGINE_PERFMON] =  nv84_perfmon_oclass;
-               break;
-       case 0xa0:
-               device->cname = "G200";
-               device->oclass[NVDEV_SUBDEV_VBIOS  ] = &nouveau_bios_oclass;
-               device->oclass[NVDEV_SUBDEV_GPIO   ] =  nv94_gpio_oclass;
-               device->oclass[NVDEV_SUBDEV_I2C    ] =  nv50_i2c_oclass;
-               device->oclass[NVDEV_SUBDEV_FUSE   ] =  &g80_fuse_oclass;
-               device->oclass[NVDEV_SUBDEV_CLOCK  ] =  nv84_clock_oclass;
-               device->oclass[NVDEV_SUBDEV_THERM  ] = &nv84_therm_oclass;
-               device->oclass[NVDEV_SUBDEV_MXM    ] = &nv50_mxm_oclass;
-               device->oclass[NVDEV_SUBDEV_DEVINIT] =  nv84_devinit_oclass;
-               device->oclass[NVDEV_SUBDEV_MC     ] =  nv98_mc_oclass;
-               device->oclass[NVDEV_SUBDEV_BUS    ] =  nv94_bus_oclass;
-               device->oclass[NVDEV_SUBDEV_TIMER  ] = &nv04_timer_oclass;
-               device->oclass[NVDEV_SUBDEV_FB     ] =  nv84_fb_oclass;
-               device->oclass[NVDEV_SUBDEV_INSTMEM] =  nv50_instmem_oclass;
-               device->oclass[NVDEV_SUBDEV_VM     ] = &nv50_vmmgr_oclass;
-               device->oclass[NVDEV_SUBDEV_BAR    ] = &nv50_bar_oclass;
-               device->oclass[NVDEV_SUBDEV_VOLT   ] = &nv40_volt_oclass;
-               device->oclass[NVDEV_ENGINE_DMAOBJ ] =  nv50_dmaeng_oclass;
-               device->oclass[NVDEV_ENGINE_FIFO   ] =  nv84_fifo_oclass;
-               device->oclass[NVDEV_ENGINE_SW     ] =  nv50_software_oclass;
-               device->oclass[NVDEV_ENGINE_GR     ] = &nv50_graph_oclass;
-               device->oclass[NVDEV_ENGINE_MPEG   ] = &nv84_mpeg_oclass;
-               device->oclass[NVDEV_ENGINE_VP     ] = &nv84_vp_oclass;
-               device->oclass[NVDEV_ENGINE_CRYPT  ] = &nv84_crypt_oclass;
-               device->oclass[NVDEV_ENGINE_BSP    ] = &nv84_bsp_oclass;
-               device->oclass[NVDEV_ENGINE_DISP   ] =  nva0_disp_oclass;
-               device->oclass[NVDEV_ENGINE_PERFMON] =  nv84_perfmon_oclass;
-               break;
-       case 0xaa:
-               device->cname = "MCP77/MCP78";
-               device->oclass[NVDEV_SUBDEV_VBIOS  ] = &nouveau_bios_oclass;
-               device->oclass[NVDEV_SUBDEV_GPIO   ] =  nv94_gpio_oclass;
-               device->oclass[NVDEV_SUBDEV_I2C    ] =  nv94_i2c_oclass;
-               device->oclass[NVDEV_SUBDEV_FUSE   ] =  &g80_fuse_oclass;
-               device->oclass[NVDEV_SUBDEV_CLOCK  ] =  nvaa_clock_oclass;
-               device->oclass[NVDEV_SUBDEV_THERM  ] = &nv84_therm_oclass;
-               device->oclass[NVDEV_SUBDEV_MXM    ] = &nv50_mxm_oclass;
-               device->oclass[NVDEV_SUBDEV_DEVINIT] =  nv98_devinit_oclass;
-               device->oclass[NVDEV_SUBDEV_MC     ] =  nv98_mc_oclass;
-               device->oclass[NVDEV_SUBDEV_BUS    ] =  nv94_bus_oclass;
-               device->oclass[NVDEV_SUBDEV_TIMER  ] = &nv04_timer_oclass;
-               device->oclass[NVDEV_SUBDEV_FB     ] =  nvaa_fb_oclass;
-               device->oclass[NVDEV_SUBDEV_INSTMEM] =  nv50_instmem_oclass;
-               device->oclass[NVDEV_SUBDEV_VM     ] = &nv50_vmmgr_oclass;
-               device->oclass[NVDEV_SUBDEV_BAR    ] = &nv50_bar_oclass;
-               device->oclass[NVDEV_SUBDEV_VOLT   ] = &nv40_volt_oclass;
-               device->oclass[NVDEV_ENGINE_DMAOBJ ] =  nv50_dmaeng_oclass;
-               device->oclass[NVDEV_ENGINE_FIFO   ] =  nv84_fifo_oclass;
-               device->oclass[NVDEV_ENGINE_SW     ] =  nv50_software_oclass;
-               device->oclass[NVDEV_ENGINE_GR     ] = &nv50_graph_oclass;
-               device->oclass[NVDEV_ENGINE_VP     ] = &nv98_vp_oclass;
-               device->oclass[NVDEV_ENGINE_CRYPT  ] = &nv98_crypt_oclass;
-               device->oclass[NVDEV_ENGINE_BSP    ] = &nv98_bsp_oclass;
-               device->oclass[NVDEV_ENGINE_PPP    ] = &nv98_ppp_oclass;
-               device->oclass[NVDEV_ENGINE_DISP   ] =  nv94_disp_oclass;
-               device->oclass[NVDEV_ENGINE_PERFMON] =  nv84_perfmon_oclass;
-               break;
-       case 0xac:
-               device->cname = "MCP79/MCP7A";
-               device->oclass[NVDEV_SUBDEV_VBIOS  ] = &nouveau_bios_oclass;
-               device->oclass[NVDEV_SUBDEV_GPIO   ] =  nv94_gpio_oclass;
-               device->oclass[NVDEV_SUBDEV_I2C    ] =  nv94_i2c_oclass;
-               device->oclass[NVDEV_SUBDEV_FUSE   ] =  &g80_fuse_oclass;
-               device->oclass[NVDEV_SUBDEV_CLOCK  ] =  nvaa_clock_oclass;
-               device->oclass[NVDEV_SUBDEV_THERM  ] = &nv84_therm_oclass;
-               device->oclass[NVDEV_SUBDEV_MXM    ] = &nv50_mxm_oclass;
-               device->oclass[NVDEV_SUBDEV_DEVINIT] =  nv98_devinit_oclass;
-               device->oclass[NVDEV_SUBDEV_MC     ] =  nv98_mc_oclass;
-               device->oclass[NVDEV_SUBDEV_BUS    ] =  nv94_bus_oclass;
-               device->oclass[NVDEV_SUBDEV_TIMER  ] = &nv04_timer_oclass;
-               device->oclass[NVDEV_SUBDEV_FB     ] =  nvaa_fb_oclass;
-               device->oclass[NVDEV_SUBDEV_INSTMEM] =  nv50_instmem_oclass;
-               device->oclass[NVDEV_SUBDEV_VM     ] = &nv50_vmmgr_oclass;
-               device->oclass[NVDEV_SUBDEV_BAR    ] = &nv50_bar_oclass;
-               device->oclass[NVDEV_SUBDEV_VOLT   ] = &nv40_volt_oclass;
-               device->oclass[NVDEV_ENGINE_DMAOBJ ] =  nv50_dmaeng_oclass;
-               device->oclass[NVDEV_ENGINE_FIFO   ] =  nv84_fifo_oclass;
-               device->oclass[NVDEV_ENGINE_SW     ] =  nv50_software_oclass;
-               device->oclass[NVDEV_ENGINE_GR     ] = &nv50_graph_oclass;
-               device->oclass[NVDEV_ENGINE_VP     ] = &nv98_vp_oclass;
-               device->oclass[NVDEV_ENGINE_CRYPT  ] = &nv98_crypt_oclass;
-               device->oclass[NVDEV_ENGINE_BSP    ] = &nv98_bsp_oclass;
-               device->oclass[NVDEV_ENGINE_PPP    ] = &nv98_ppp_oclass;
-               device->oclass[NVDEV_ENGINE_DISP   ] =  nv94_disp_oclass;
-               device->oclass[NVDEV_ENGINE_PERFMON] =  nv84_perfmon_oclass;
-               break;
-       case 0xa3:
-               device->cname = "GT215";
-               device->oclass[NVDEV_SUBDEV_VBIOS  ] = &nouveau_bios_oclass;
-               device->oclass[NVDEV_SUBDEV_GPIO   ] =  nv94_gpio_oclass;
-               device->oclass[NVDEV_SUBDEV_I2C    ] =  nv94_i2c_oclass;
-               device->oclass[NVDEV_SUBDEV_FUSE   ] =  &g80_fuse_oclass;
-               device->oclass[NVDEV_SUBDEV_CLOCK  ] = &nva3_clock_oclass;
-               device->oclass[NVDEV_SUBDEV_THERM  ] = &nva3_therm_oclass;
-               device->oclass[NVDEV_SUBDEV_MXM    ] = &nv50_mxm_oclass;
-               device->oclass[NVDEV_SUBDEV_DEVINIT] =  nva3_devinit_oclass;
-               device->oclass[NVDEV_SUBDEV_MC     ] =  nv98_mc_oclass;
-               device->oclass[NVDEV_SUBDEV_BUS    ] =  nv94_bus_oclass;
-               device->oclass[NVDEV_SUBDEV_TIMER  ] = &nv04_timer_oclass;
-               device->oclass[NVDEV_SUBDEV_FB     ] =  nva3_fb_oclass;
-               device->oclass[NVDEV_SUBDEV_INSTMEM] =  nv50_instmem_oclass;
-               device->oclass[NVDEV_SUBDEV_VM     ] = &nv50_vmmgr_oclass;
-               device->oclass[NVDEV_SUBDEV_BAR    ] = &nv50_bar_oclass;
-               device->oclass[NVDEV_SUBDEV_PWR    ] =  nva3_pwr_oclass;
-               device->oclass[NVDEV_SUBDEV_VOLT   ] = &nv40_volt_oclass;
-               device->oclass[NVDEV_ENGINE_DMAOBJ ] =  nv50_dmaeng_oclass;
-               device->oclass[NVDEV_ENGINE_FIFO   ] =  nv84_fifo_oclass;
-               device->oclass[NVDEV_ENGINE_SW     ] =  nv50_software_oclass;
-               device->oclass[NVDEV_ENGINE_GR     ] = &nv50_graph_oclass;
-               device->oclass[NVDEV_ENGINE_MPEG   ] = &nv84_mpeg_oclass;
-               device->oclass[NVDEV_ENGINE_VP     ] = &nv98_vp_oclass;
-               device->oclass[NVDEV_ENGINE_BSP    ] = &nv98_bsp_oclass;
-               device->oclass[NVDEV_ENGINE_PPP    ] = &nv98_ppp_oclass;
-               device->oclass[NVDEV_ENGINE_COPY0  ] = &nva3_copy_oclass;
-               device->oclass[NVDEV_ENGINE_DISP   ] =  nva3_disp_oclass;
-               device->oclass[NVDEV_ENGINE_PERFMON] =  nva3_perfmon_oclass;
-               break;
-       case 0xa5:
-               device->cname = "GT216";
-               device->oclass[NVDEV_SUBDEV_VBIOS  ] = &nouveau_bios_oclass;
-               device->oclass[NVDEV_SUBDEV_GPIO   ] =  nv94_gpio_oclass;
-               device->oclass[NVDEV_SUBDEV_I2C    ] =  nv94_i2c_oclass;
-               device->oclass[NVDEV_SUBDEV_FUSE   ] =  &g80_fuse_oclass;
-               device->oclass[NVDEV_SUBDEV_CLOCK  ] = &nva3_clock_oclass;
-               device->oclass[NVDEV_SUBDEV_THERM  ] = &nva3_therm_oclass;
-               device->oclass[NVDEV_SUBDEV_MXM    ] = &nv50_mxm_oclass;
-               device->oclass[NVDEV_SUBDEV_DEVINIT] =  nva3_devinit_oclass;
-               device->oclass[NVDEV_SUBDEV_MC     ] =  nv98_mc_oclass;
-               device->oclass[NVDEV_SUBDEV_BUS    ] =  nv94_bus_oclass;
-               device->oclass[NVDEV_SUBDEV_TIMER  ] = &nv04_timer_oclass;
-               device->oclass[NVDEV_SUBDEV_FB     ] =  nva3_fb_oclass;
-               device->oclass[NVDEV_SUBDEV_INSTMEM] =  nv50_instmem_oclass;
-               device->oclass[NVDEV_SUBDEV_VM     ] = &nv50_vmmgr_oclass;
-               device->oclass[NVDEV_SUBDEV_BAR    ] = &nv50_bar_oclass;
-               device->oclass[NVDEV_SUBDEV_PWR    ] =  nva3_pwr_oclass;
-               device->oclass[NVDEV_SUBDEV_VOLT   ] = &nv40_volt_oclass;
-               device->oclass[NVDEV_ENGINE_DMAOBJ ] =  nv50_dmaeng_oclass;
-               device->oclass[NVDEV_ENGINE_FIFO   ] =  nv84_fifo_oclass;
-               device->oclass[NVDEV_ENGINE_SW     ] =  nv50_software_oclass;
-               device->oclass[NVDEV_ENGINE_GR     ] = &nv50_graph_oclass;
-               device->oclass[NVDEV_ENGINE_VP     ] = &nv98_vp_oclass;
-               device->oclass[NVDEV_ENGINE_BSP    ] = &nv98_bsp_oclass;
-               device->oclass[NVDEV_ENGINE_PPP    ] = &nv98_ppp_oclass;
-               device->oclass[NVDEV_ENGINE_COPY0  ] = &nva3_copy_oclass;
-               device->oclass[NVDEV_ENGINE_DISP   ] =  nva3_disp_oclass;
-               device->oclass[NVDEV_ENGINE_PERFMON] =  nva3_perfmon_oclass;
-               break;
-       case 0xa8:
-               device->cname = "GT218";
-               device->oclass[NVDEV_SUBDEV_VBIOS  ] = &nouveau_bios_oclass;
-               device->oclass[NVDEV_SUBDEV_GPIO   ] =  nv94_gpio_oclass;
-               device->oclass[NVDEV_SUBDEV_I2C    ] =  nv94_i2c_oclass;
-               device->oclass[NVDEV_SUBDEV_FUSE   ] =  &g80_fuse_oclass;
-               device->oclass[NVDEV_SUBDEV_CLOCK  ] = &nva3_clock_oclass;
-               device->oclass[NVDEV_SUBDEV_THERM  ] = &nva3_therm_oclass;
-               device->oclass[NVDEV_SUBDEV_MXM    ] = &nv50_mxm_oclass;
-               device->oclass[NVDEV_SUBDEV_DEVINIT] =  nva3_devinit_oclass;
-               device->oclass[NVDEV_SUBDEV_MC     ] =  nv98_mc_oclass;
-               device->oclass[NVDEV_SUBDEV_BUS    ] =  nv94_bus_oclass;
-               device->oclass[NVDEV_SUBDEV_TIMER  ] = &nv04_timer_oclass;
-               device->oclass[NVDEV_SUBDEV_FB     ] =  nva3_fb_oclass;
-               device->oclass[NVDEV_SUBDEV_INSTMEM] =  nv50_instmem_oclass;
-               device->oclass[NVDEV_SUBDEV_VM     ] = &nv50_vmmgr_oclass;
-               device->oclass[NVDEV_SUBDEV_BAR    ] = &nv50_bar_oclass;
-               device->oclass[NVDEV_SUBDEV_PWR    ] =  nva3_pwr_oclass;
-               device->oclass[NVDEV_SUBDEV_VOLT   ] = &nv40_volt_oclass;
-               device->oclass[NVDEV_ENGINE_DMAOBJ ] =  nv50_dmaeng_oclass;
-               device->oclass[NVDEV_ENGINE_FIFO   ] =  nv84_fifo_oclass;
-               device->oclass[NVDEV_ENGINE_SW     ] =  nv50_software_oclass;
-               device->oclass[NVDEV_ENGINE_GR     ] = &nv50_graph_oclass;
-               device->oclass[NVDEV_ENGINE_VP     ] = &nv98_vp_oclass;
-               device->oclass[NVDEV_ENGINE_BSP    ] = &nv98_bsp_oclass;
-               device->oclass[NVDEV_ENGINE_PPP    ] = &nv98_ppp_oclass;
-               device->oclass[NVDEV_ENGINE_COPY0  ] = &nva3_copy_oclass;
-               device->oclass[NVDEV_ENGINE_DISP   ] =  nva3_disp_oclass;
-               device->oclass[NVDEV_ENGINE_PERFMON] =  nva3_perfmon_oclass;
-               break;
-       case 0xaf:
-               device->cname = "MCP89";
-               device->oclass[NVDEV_SUBDEV_VBIOS  ] = &nouveau_bios_oclass;
-               device->oclass[NVDEV_SUBDEV_GPIO   ] =  nv94_gpio_oclass;
-               device->oclass[NVDEV_SUBDEV_I2C    ] =  nv94_i2c_oclass;
-               device->oclass[NVDEV_SUBDEV_FUSE   ] =  &g80_fuse_oclass;
-               device->oclass[NVDEV_SUBDEV_CLOCK  ] = &nva3_clock_oclass;
-               device->oclass[NVDEV_SUBDEV_THERM  ] = &nva3_therm_oclass;
-               device->oclass[NVDEV_SUBDEV_MXM    ] = &nv50_mxm_oclass;
-               device->oclass[NVDEV_SUBDEV_DEVINIT] =  nvaf_devinit_oclass;
-               device->oclass[NVDEV_SUBDEV_MC     ] =  nv98_mc_oclass;
-               device->oclass[NVDEV_SUBDEV_BUS    ] =  nv94_bus_oclass;
-               device->oclass[NVDEV_SUBDEV_TIMER  ] = &nv04_timer_oclass;
-               device->oclass[NVDEV_SUBDEV_FB     ] =  nvaf_fb_oclass;
-               device->oclass[NVDEV_SUBDEV_INSTMEM] =  nv50_instmem_oclass;
-               device->oclass[NVDEV_SUBDEV_VM     ] = &nv50_vmmgr_oclass;
-               device->oclass[NVDEV_SUBDEV_BAR    ] = &nv50_bar_oclass;
-               device->oclass[NVDEV_SUBDEV_PWR    ] =  nva3_pwr_oclass;
-               device->oclass[NVDEV_SUBDEV_VOLT   ] = &nv40_volt_oclass;
-               device->oclass[NVDEV_ENGINE_DMAOBJ ] =  nv50_dmaeng_oclass;
-               device->oclass[NVDEV_ENGINE_FIFO   ] =  nv84_fifo_oclass;
-               device->oclass[NVDEV_ENGINE_SW     ] =  nv50_software_oclass;
-               device->oclass[NVDEV_ENGINE_GR     ] = &nv50_graph_oclass;
-               device->oclass[NVDEV_ENGINE_VP     ] = &nv98_vp_oclass;
-               device->oclass[NVDEV_ENGINE_BSP    ] = &nv98_bsp_oclass;
-               device->oclass[NVDEV_ENGINE_PPP    ] = &nv98_ppp_oclass;
-               device->oclass[NVDEV_ENGINE_COPY0  ] = &nva3_copy_oclass;
-               device->oclass[NVDEV_ENGINE_DISP   ] =  nva3_disp_oclass;
-               device->oclass[NVDEV_ENGINE_PERFMON] =  nva3_perfmon_oclass;
-               break;
-       default:
-               nv_fatal(device, "unknown Tesla chipset\n");
-               return -EINVAL;
-       }
-
-       return 0;
-}
diff --git a/drivers/gpu/drm/nouveau/core/engine/device/nvc0.c b/drivers/gpu/drm/nouveau/core/engine/device/nvc0.c
deleted file mode 100644 (file)
index 72a40f9..0000000
+++ /dev/null
@@ -1,357 +0,0 @@
-/*
- * Copyright 2012 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 <subdev/bios.h>
-#include <subdev/bus.h>
-#include <subdev/gpio.h>
-#include <subdev/i2c.h>
-#include <subdev/fuse.h>
-#include <subdev/clock.h>
-#include <subdev/therm.h>
-#include <subdev/mxm.h>
-#include <subdev/devinit.h>
-#include <subdev/mc.h>
-#include <subdev/timer.h>
-#include <subdev/fb.h>
-#include <subdev/ltc.h>
-#include <subdev/ibus.h>
-#include <subdev/instmem.h>
-#include <subdev/vm.h>
-#include <subdev/bar.h>
-#include <subdev/pwr.h>
-#include <subdev/volt.h>
-
-#include <engine/device.h>
-#include <engine/dmaobj.h>
-#include <engine/fifo.h>
-#include <engine/software.h>
-#include <engine/graph.h>
-#include <engine/vp.h>
-#include <engine/bsp.h>
-#include <engine/ppp.h>
-#include <engine/copy.h>
-#include <engine/disp.h>
-#include <engine/perfmon.h>
-
-int
-nvc0_identify(struct nouveau_device *device)
-{
-       switch (device->chipset) {
-       case 0xc0:
-               device->cname = "GF100";
-               device->oclass[NVDEV_SUBDEV_VBIOS  ] = &nouveau_bios_oclass;
-               device->oclass[NVDEV_SUBDEV_GPIO   ] =  nv94_gpio_oclass;
-               device->oclass[NVDEV_SUBDEV_I2C    ] =  nv94_i2c_oclass;
-               device->oclass[NVDEV_SUBDEV_FUSE   ] = &gf100_fuse_oclass;
-               device->oclass[NVDEV_SUBDEV_CLOCK  ] = &nvc0_clock_oclass;
-               device->oclass[NVDEV_SUBDEV_THERM  ] = &nva3_therm_oclass;
-               device->oclass[NVDEV_SUBDEV_MXM    ] = &nv50_mxm_oclass;
-               device->oclass[NVDEV_SUBDEV_DEVINIT] =  nvc0_devinit_oclass;
-               device->oclass[NVDEV_SUBDEV_MC     ] =  nvc0_mc_oclass;
-               device->oclass[NVDEV_SUBDEV_BUS    ] =  nvc0_bus_oclass;
-               device->oclass[NVDEV_SUBDEV_TIMER  ] = &nv04_timer_oclass;
-               device->oclass[NVDEV_SUBDEV_FB     ] =  nvc0_fb_oclass;
-               device->oclass[NVDEV_SUBDEV_LTC    ] =  gf100_ltc_oclass;
-               device->oclass[NVDEV_SUBDEV_IBUS   ] = &nvc0_ibus_oclass;
-               device->oclass[NVDEV_SUBDEV_INSTMEM] =  nv50_instmem_oclass;
-               device->oclass[NVDEV_SUBDEV_VM     ] = &nvc0_vmmgr_oclass;
-               device->oclass[NVDEV_SUBDEV_BAR    ] = &nvc0_bar_oclass;
-               device->oclass[NVDEV_SUBDEV_PWR    ] =  nvc0_pwr_oclass;
-               device->oclass[NVDEV_SUBDEV_VOLT   ] = &nv40_volt_oclass;
-               device->oclass[NVDEV_ENGINE_DMAOBJ ] =  nvc0_dmaeng_oclass;
-               device->oclass[NVDEV_ENGINE_FIFO   ] =  nvc0_fifo_oclass;
-               device->oclass[NVDEV_ENGINE_SW     ] =  nvc0_software_oclass;
-               device->oclass[NVDEV_ENGINE_GR     ] =  nvc0_graph_oclass;
-               device->oclass[NVDEV_ENGINE_VP     ] = &nvc0_vp_oclass;
-               device->oclass[NVDEV_ENGINE_BSP    ] = &nvc0_bsp_oclass;
-               device->oclass[NVDEV_ENGINE_PPP    ] = &nvc0_ppp_oclass;
-               device->oclass[NVDEV_ENGINE_COPY0  ] = &nvc0_copy0_oclass;
-               device->oclass[NVDEV_ENGINE_COPY1  ] = &nvc0_copy1_oclass;
-               device->oclass[NVDEV_ENGINE_DISP   ] =  nva3_disp_oclass;
-               device->oclass[NVDEV_ENGINE_PERFMON] = &nvc0_perfmon_oclass;
-               break;
-       case 0xc4:
-               device->cname = "GF104";
-               device->oclass[NVDEV_SUBDEV_VBIOS  ] = &nouveau_bios_oclass;
-               device->oclass[NVDEV_SUBDEV_GPIO   ] =  nv94_gpio_oclass;
-               device->oclass[NVDEV_SUBDEV_I2C    ] =  nv94_i2c_oclass;
-               device->oclass[NVDEV_SUBDEV_FUSE   ] = &gf100_fuse_oclass;
-               device->oclass[NVDEV_SUBDEV_CLOCK  ] = &nvc0_clock_oclass;
-               device->oclass[NVDEV_SUBDEV_THERM  ] = &nva3_therm_oclass;
-               device->oclass[NVDEV_SUBDEV_MXM    ] = &nv50_mxm_oclass;
-               device->oclass[NVDEV_SUBDEV_DEVINIT] =  nvc0_devinit_oclass;
-               device->oclass[NVDEV_SUBDEV_MC     ] =  nvc0_mc_oclass;
-               device->oclass[NVDEV_SUBDEV_BUS    ] =  nvc0_bus_oclass;
-               device->oclass[NVDEV_SUBDEV_TIMER  ] = &nv04_timer_oclass;
-               device->oclass[NVDEV_SUBDEV_FB     ] =  nvc0_fb_oclass;
-               device->oclass[NVDEV_SUBDEV_LTC    ] =  gf100_ltc_oclass;
-               device->oclass[NVDEV_SUBDEV_IBUS   ] = &nvc0_ibus_oclass;
-               device->oclass[NVDEV_SUBDEV_INSTMEM] =  nv50_instmem_oclass;
-               device->oclass[NVDEV_SUBDEV_VM     ] = &nvc0_vmmgr_oclass;
-               device->oclass[NVDEV_SUBDEV_BAR    ] = &nvc0_bar_oclass;
-               device->oclass[NVDEV_SUBDEV_PWR    ] =  nvc0_pwr_oclass;
-               device->oclass[NVDEV_SUBDEV_VOLT   ] = &nv40_volt_oclass;
-               device->oclass[NVDEV_ENGINE_DMAOBJ ] =  nvc0_dmaeng_oclass;
-               device->oclass[NVDEV_ENGINE_FIFO   ] =  nvc0_fifo_oclass;
-               device->oclass[NVDEV_ENGINE_SW     ] =  nvc0_software_oclass;
-               device->oclass[NVDEV_ENGINE_GR     ] =  nvc4_graph_oclass;
-               device->oclass[NVDEV_ENGINE_VP     ] = &nvc0_vp_oclass;
-               device->oclass[NVDEV_ENGINE_BSP    ] = &nvc0_bsp_oclass;
-               device->oclass[NVDEV_ENGINE_PPP    ] = &nvc0_ppp_oclass;
-               device->oclass[NVDEV_ENGINE_COPY0  ] = &nvc0_copy0_oclass;
-               device->oclass[NVDEV_ENGINE_COPY1  ] = &nvc0_copy1_oclass;
-               device->oclass[NVDEV_ENGINE_DISP   ] =  nva3_disp_oclass;
-               device->oclass[NVDEV_ENGINE_PERFMON] = &nvc0_perfmon_oclass;
-               break;
-       case 0xc3:
-               device->cname = "GF106";
-               device->oclass[NVDEV_SUBDEV_VBIOS  ] = &nouveau_bios_oclass;
-               device->oclass[NVDEV_SUBDEV_GPIO   ] =  nv94_gpio_oclass;
-               device->oclass[NVDEV_SUBDEV_I2C    ] =  nv94_i2c_oclass;
-               device->oclass[NVDEV_SUBDEV_FUSE   ] = &gf100_fuse_oclass;
-               device->oclass[NVDEV_SUBDEV_CLOCK  ] = &nvc0_clock_oclass;
-               device->oclass[NVDEV_SUBDEV_THERM  ] = &nva3_therm_oclass;
-               device->oclass[NVDEV_SUBDEV_MXM    ] = &nv50_mxm_oclass;
-               device->oclass[NVDEV_SUBDEV_DEVINIT] =  nvc0_devinit_oclass;
-               device->oclass[NVDEV_SUBDEV_MC     ] =  nvc3_mc_oclass;
-               device->oclass[NVDEV_SUBDEV_BUS    ] =  nvc0_bus_oclass;
-               device->oclass[NVDEV_SUBDEV_TIMER  ] = &nv04_timer_oclass;
-               device->oclass[NVDEV_SUBDEV_FB     ] =  nvc0_fb_oclass;
-               device->oclass[NVDEV_SUBDEV_LTC    ] =  gf100_ltc_oclass;
-               device->oclass[NVDEV_SUBDEV_IBUS   ] = &nvc0_ibus_oclass;
-               device->oclass[NVDEV_SUBDEV_INSTMEM] =  nv50_instmem_oclass;
-               device->oclass[NVDEV_SUBDEV_VM     ] = &nvc0_vmmgr_oclass;
-               device->oclass[NVDEV_SUBDEV_BAR    ] = &nvc0_bar_oclass;
-               device->oclass[NVDEV_SUBDEV_PWR    ] =  nvc0_pwr_oclass;
-               device->oclass[NVDEV_SUBDEV_VOLT   ] = &nv40_volt_oclass;
-               device->oclass[NVDEV_ENGINE_DMAOBJ ] =  nvc0_dmaeng_oclass;
-               device->oclass[NVDEV_ENGINE_FIFO   ] =  nvc0_fifo_oclass;
-               device->oclass[NVDEV_ENGINE_SW     ] =  nvc0_software_oclass;
-               device->oclass[NVDEV_ENGINE_GR     ] =  nvc4_graph_oclass;
-               device->oclass[NVDEV_ENGINE_VP     ] = &nvc0_vp_oclass;
-               device->oclass[NVDEV_ENGINE_BSP    ] = &nvc0_bsp_oclass;
-               device->oclass[NVDEV_ENGINE_PPP    ] = &nvc0_ppp_oclass;
-               device->oclass[NVDEV_ENGINE_COPY0  ] = &nvc0_copy0_oclass;
-               device->oclass[NVDEV_ENGINE_DISP   ] =  nva3_disp_oclass;
-               device->oclass[NVDEV_ENGINE_PERFMON] = &nvc0_perfmon_oclass;
-               break;
-       case 0xce:
-               device->cname = "GF114";
-               device->oclass[NVDEV_SUBDEV_VBIOS  ] = &nouveau_bios_oclass;
-               device->oclass[NVDEV_SUBDEV_GPIO   ] =  nv94_gpio_oclass;
-               device->oclass[NVDEV_SUBDEV_I2C    ] =  nv94_i2c_oclass;
-               device->oclass[NVDEV_SUBDEV_FUSE   ] = &gf100_fuse_oclass;
-               device->oclass[NVDEV_SUBDEV_CLOCK  ] = &nvc0_clock_oclass;
-               device->oclass[NVDEV_SUBDEV_THERM  ] = &nva3_therm_oclass;
-               device->oclass[NVDEV_SUBDEV_MXM    ] = &nv50_mxm_oclass;
-               device->oclass[NVDEV_SUBDEV_DEVINIT] =  nvc0_devinit_oclass;
-               device->oclass[NVDEV_SUBDEV_MC     ] =  nvc0_mc_oclass;
-               device->oclass[NVDEV_SUBDEV_BUS    ] =  nvc0_bus_oclass;
-               device->oclass[NVDEV_SUBDEV_TIMER  ] = &nv04_timer_oclass;
-               device->oclass[NVDEV_SUBDEV_FB     ] =  nvc0_fb_oclass;
-               device->oclass[NVDEV_SUBDEV_LTC    ] =  gf100_ltc_oclass;
-               device->oclass[NVDEV_SUBDEV_IBUS   ] = &nvc0_ibus_oclass;
-               device->oclass[NVDEV_SUBDEV_INSTMEM] =  nv50_instmem_oclass;
-               device->oclass[NVDEV_SUBDEV_VM     ] = &nvc0_vmmgr_oclass;
-               device->oclass[NVDEV_SUBDEV_BAR    ] = &nvc0_bar_oclass;
-               device->oclass[NVDEV_SUBDEV_PWR    ] =  nvc0_pwr_oclass;
-               device->oclass[NVDEV_SUBDEV_VOLT   ] = &nv40_volt_oclass;
-               device->oclass[NVDEV_ENGINE_DMAOBJ ] =  nvc0_dmaeng_oclass;
-               device->oclass[NVDEV_ENGINE_FIFO   ] =  nvc0_fifo_oclass;
-               device->oclass[NVDEV_ENGINE_SW     ] =  nvc0_software_oclass;
-               device->oclass[NVDEV_ENGINE_GR     ] =  nvc4_graph_oclass;
-               device->oclass[NVDEV_ENGINE_VP     ] = &nvc0_vp_oclass;
-               device->oclass[NVDEV_ENGINE_BSP    ] = &nvc0_bsp_oclass;
-               device->oclass[NVDEV_ENGINE_PPP    ] = &nvc0_ppp_oclass;
-               device->oclass[NVDEV_ENGINE_COPY0  ] = &nvc0_copy0_oclass;
-               device->oclass[NVDEV_ENGINE_COPY1  ] = &nvc0_copy1_oclass;
-               device->oclass[NVDEV_ENGINE_DISP   ] =  nva3_disp_oclass;
-               device->oclass[NVDEV_ENGINE_PERFMON] = &nvc0_perfmon_oclass;
-               break;
-       case 0xcf:
-               device->cname = "GF116";
-               device->oclass[NVDEV_SUBDEV_VBIOS  ] = &nouveau_bios_oclass;
-               device->oclass[NVDEV_SUBDEV_GPIO   ] =  nv94_gpio_oclass;
-               device->oclass[NVDEV_SUBDEV_I2C    ] =  nv94_i2c_oclass;
-               device->oclass[NVDEV_SUBDEV_FUSE   ] = &gf100_fuse_oclass;
-               device->oclass[NVDEV_SUBDEV_CLOCK  ] = &nvc0_clock_oclass;
-               device->oclass[NVDEV_SUBDEV_THERM  ] = &nva3_therm_oclass;
-               device->oclass[NVDEV_SUBDEV_MXM    ] = &nv50_mxm_oclass;
-               device->oclass[NVDEV_SUBDEV_DEVINIT] =  nvc0_devinit_oclass;
-               device->oclass[NVDEV_SUBDEV_MC     ] =  nvc3_mc_oclass;
-               device->oclass[NVDEV_SUBDEV_BUS    ] =  nvc0_bus_oclass;
-               device->oclass[NVDEV_SUBDEV_TIMER  ] = &nv04_timer_oclass;
-               device->oclass[NVDEV_SUBDEV_FB     ] =  nvc0_fb_oclass;
-               device->oclass[NVDEV_SUBDEV_LTC    ] =  gf100_ltc_oclass;
-               device->oclass[NVDEV_SUBDEV_IBUS   ] = &nvc0_ibus_oclass;
-               device->oclass[NVDEV_SUBDEV_INSTMEM] =  nv50_instmem_oclass;
-               device->oclass[NVDEV_SUBDEV_VM     ] = &nvc0_vmmgr_oclass;
-               device->oclass[NVDEV_SUBDEV_BAR    ] = &nvc0_bar_oclass;
-               device->oclass[NVDEV_SUBDEV_PWR    ] =  nvc0_pwr_oclass;
-               device->oclass[NVDEV_SUBDEV_VOLT   ] = &nv40_volt_oclass;
-               device->oclass[NVDEV_ENGINE_DMAOBJ ] =  nvc0_dmaeng_oclass;
-               device->oclass[NVDEV_ENGINE_FIFO   ] =  nvc0_fifo_oclass;
-               device->oclass[NVDEV_ENGINE_SW     ] =  nvc0_software_oclass;
-               device->oclass[NVDEV_ENGINE_GR     ] =  nvc4_graph_oclass;
-               device->oclass[NVDEV_ENGINE_VP     ] = &nvc0_vp_oclass;
-               device->oclass[NVDEV_ENGINE_BSP    ] = &nvc0_bsp_oclass;
-               device->oclass[NVDEV_ENGINE_PPP    ] = &nvc0_ppp_oclass;
-               device->oclass[NVDEV_ENGINE_COPY0  ] = &nvc0_copy0_oclass;
-               device->oclass[NVDEV_ENGINE_DISP   ] =  nva3_disp_oclass;
-               device->oclass[NVDEV_ENGINE_PERFMON] = &nvc0_perfmon_oclass;
-               break;
-       case 0xc1:
-               device->cname = "GF108";
-               device->oclass[NVDEV_SUBDEV_VBIOS  ] = &nouveau_bios_oclass;
-               device->oclass[NVDEV_SUBDEV_GPIO   ] =  nv94_gpio_oclass;
-               device->oclass[NVDEV_SUBDEV_I2C    ] =  nv94_i2c_oclass;
-               device->oclass[NVDEV_SUBDEV_FUSE   ] = &gf100_fuse_oclass;
-               device->oclass[NVDEV_SUBDEV_CLOCK  ] = &nvc0_clock_oclass;
-               device->oclass[NVDEV_SUBDEV_THERM  ] = &nva3_therm_oclass;
-               device->oclass[NVDEV_SUBDEV_MXM    ] = &nv50_mxm_oclass;
-               device->oclass[NVDEV_SUBDEV_DEVINIT] =  nvc0_devinit_oclass;
-               device->oclass[NVDEV_SUBDEV_MC     ] =  nvc3_mc_oclass;
-               device->oclass[NVDEV_SUBDEV_BUS    ] =  nvc0_bus_oclass;
-               device->oclass[NVDEV_SUBDEV_TIMER  ] = &nv04_timer_oclass;
-               device->oclass[NVDEV_SUBDEV_FB     ] =  nvc0_fb_oclass;
-               device->oclass[NVDEV_SUBDEV_LTC    ] =  gf100_ltc_oclass;
-               device->oclass[NVDEV_SUBDEV_IBUS   ] = &nvc0_ibus_oclass;
-               device->oclass[NVDEV_SUBDEV_INSTMEM] =  nv50_instmem_oclass;
-               device->oclass[NVDEV_SUBDEV_VM     ] = &nvc0_vmmgr_oclass;
-               device->oclass[NVDEV_SUBDEV_BAR    ] = &nvc0_bar_oclass;
-               device->oclass[NVDEV_SUBDEV_PWR    ] =  nvc0_pwr_oclass;
-               device->oclass[NVDEV_SUBDEV_VOLT   ] = &nv40_volt_oclass;
-               device->oclass[NVDEV_ENGINE_DMAOBJ ] =  nvc0_dmaeng_oclass;
-               device->oclass[NVDEV_ENGINE_FIFO   ] =  nvc0_fifo_oclass;
-               device->oclass[NVDEV_ENGINE_SW     ] =  nvc0_software_oclass;
-               device->oclass[NVDEV_ENGINE_GR     ] =  nvc1_graph_oclass;
-               device->oclass[NVDEV_ENGINE_VP     ] = &nvc0_vp_oclass;
-               device->oclass[NVDEV_ENGINE_BSP    ] = &nvc0_bsp_oclass;
-               device->oclass[NVDEV_ENGINE_PPP    ] = &nvc0_ppp_oclass;
-               device->oclass[NVDEV_ENGINE_COPY0  ] = &nvc0_copy0_oclass;
-               device->oclass[NVDEV_ENGINE_DISP   ] =  nva3_disp_oclass;
-               device->oclass[NVDEV_ENGINE_PERFMON] = &nvc0_perfmon_oclass;
-               break;
-       case 0xc8:
-               device->cname = "GF110";
-               device->oclass[NVDEV_SUBDEV_VBIOS  ] = &nouveau_bios_oclass;
-               device->oclass[NVDEV_SUBDEV_GPIO   ] =  nv94_gpio_oclass;
-               device->oclass[NVDEV_SUBDEV_I2C    ] =  nv94_i2c_oclass;
-               device->oclass[NVDEV_SUBDEV_FUSE   ] = &gf100_fuse_oclass;
-               device->oclass[NVDEV_SUBDEV_CLOCK  ] = &nvc0_clock_oclass;
-               device->oclass[NVDEV_SUBDEV_THERM  ] = &nva3_therm_oclass;
-               device->oclass[NVDEV_SUBDEV_MXM    ] = &nv50_mxm_oclass;
-               device->oclass[NVDEV_SUBDEV_DEVINIT] =  nvc0_devinit_oclass;
-               device->oclass[NVDEV_SUBDEV_MC     ] =  nvc0_mc_oclass;
-               device->oclass[NVDEV_SUBDEV_BUS    ] =  nvc0_bus_oclass;
-               device->oclass[NVDEV_SUBDEV_TIMER  ] = &nv04_timer_oclass;
-               device->oclass[NVDEV_SUBDEV_FB     ] =  nvc0_fb_oclass;
-               device->oclass[NVDEV_SUBDEV_LTC    ] =  gf100_ltc_oclass;
-               device->oclass[NVDEV_SUBDEV_IBUS   ] = &nvc0_ibus_oclass;
-               device->oclass[NVDEV_SUBDEV_INSTMEM] =  nv50_instmem_oclass;
-               device->oclass[NVDEV_SUBDEV_VM     ] = &nvc0_vmmgr_oclass;
-               device->oclass[NVDEV_SUBDEV_BAR    ] = &nvc0_bar_oclass;
-               device->oclass[NVDEV_SUBDEV_PWR    ] =  nvc0_pwr_oclass;
-               device->oclass[NVDEV_SUBDEV_VOLT   ] = &nv40_volt_oclass;
-               device->oclass[NVDEV_ENGINE_DMAOBJ ] =  nvc0_dmaeng_oclass;
-               device->oclass[NVDEV_ENGINE_FIFO   ] =  nvc0_fifo_oclass;
-               device->oclass[NVDEV_ENGINE_SW     ] =  nvc0_software_oclass;
-               device->oclass[NVDEV_ENGINE_GR     ] =  nvc8_graph_oclass;
-               device->oclass[NVDEV_ENGINE_VP     ] = &nvc0_vp_oclass;
-               device->oclass[NVDEV_ENGINE_BSP    ] = &nvc0_bsp_oclass;
-               device->oclass[NVDEV_ENGINE_PPP    ] = &nvc0_ppp_oclass;
-               device->oclass[NVDEV_ENGINE_COPY0  ] = &nvc0_copy0_oclass;
-               device->oclass[NVDEV_ENGINE_COPY1  ] = &nvc0_copy1_oclass;
-               device->oclass[NVDEV_ENGINE_DISP   ] =  nva3_disp_oclass;
-               device->oclass[NVDEV_ENGINE_PERFMON] = &nvc0_perfmon_oclass;
-               break;
-       case 0xd9:
-               device->cname = "GF119";
-               device->oclass[NVDEV_SUBDEV_VBIOS  ] = &nouveau_bios_oclass;
-               device->oclass[NVDEV_SUBDEV_GPIO   ] =  nvd0_gpio_oclass;
-               device->oclass[NVDEV_SUBDEV_I2C    ] =  nvd0_i2c_oclass;
-               device->oclass[NVDEV_SUBDEV_FUSE   ] = &gf100_fuse_oclass;
-               device->oclass[NVDEV_SUBDEV_CLOCK  ] = &nvc0_clock_oclass;
-               device->oclass[NVDEV_SUBDEV_THERM  ] = &nvd0_therm_oclass;
-               device->oclass[NVDEV_SUBDEV_MXM    ] = &nv50_mxm_oclass;
-               device->oclass[NVDEV_SUBDEV_DEVINIT] =  nvc0_devinit_oclass;
-               device->oclass[NVDEV_SUBDEV_MC     ] =  nvc3_mc_oclass;
-               device->oclass[NVDEV_SUBDEV_BUS    ] =  nvc0_bus_oclass;
-               device->oclass[NVDEV_SUBDEV_TIMER  ] = &nv04_timer_oclass;
-               device->oclass[NVDEV_SUBDEV_FB     ] =  nvc0_fb_oclass;
-               device->oclass[NVDEV_SUBDEV_LTC    ] =  gf100_ltc_oclass;
-               device->oclass[NVDEV_SUBDEV_IBUS   ] = &nvc0_ibus_oclass;
-               device->oclass[NVDEV_SUBDEV_INSTMEM] =  nv50_instmem_oclass;
-               device->oclass[NVDEV_SUBDEV_VM     ] = &nvc0_vmmgr_oclass;
-               device->oclass[NVDEV_SUBDEV_BAR    ] = &nvc0_bar_oclass;
-               device->oclass[NVDEV_SUBDEV_PWR    ] =  nvd0_pwr_oclass;
-               device->oclass[NVDEV_SUBDEV_VOLT   ] = &nv40_volt_oclass;
-               device->oclass[NVDEV_ENGINE_DMAOBJ ] =  nvd0_dmaeng_oclass;
-               device->oclass[NVDEV_ENGINE_FIFO   ] =  nvc0_fifo_oclass;
-               device->oclass[NVDEV_ENGINE_SW     ] =  nvc0_software_oclass;
-               device->oclass[NVDEV_ENGINE_GR     ] =  nvd9_graph_oclass;
-               device->oclass[NVDEV_ENGINE_VP     ] = &nvc0_vp_oclass;
-               device->oclass[NVDEV_ENGINE_BSP    ] = &nvc0_bsp_oclass;
-               device->oclass[NVDEV_ENGINE_PPP    ] = &nvc0_ppp_oclass;
-               device->oclass[NVDEV_ENGINE_COPY0  ] = &nvc0_copy0_oclass;
-               device->oclass[NVDEV_ENGINE_DISP   ] =  nvd0_disp_oclass;
-               device->oclass[NVDEV_ENGINE_PERFMON] = &nvc0_perfmon_oclass;
-               break;
-       case 0xd7:
-               device->cname = "GF117";
-               device->oclass[NVDEV_SUBDEV_VBIOS  ] = &nouveau_bios_oclass;
-               device->oclass[NVDEV_SUBDEV_GPIO   ] =  nvd0_gpio_oclass;
-               device->oclass[NVDEV_SUBDEV_I2C    ] =  gf117_i2c_oclass;
-               device->oclass[NVDEV_SUBDEV_FUSE   ] = &gf100_fuse_oclass;
-               device->oclass[NVDEV_SUBDEV_CLOCK  ] = &nvc0_clock_oclass;
-               device->oclass[NVDEV_SUBDEV_THERM  ] = &nvd0_therm_oclass;
-               device->oclass[NVDEV_SUBDEV_MXM    ] = &nv50_mxm_oclass;
-               device->oclass[NVDEV_SUBDEV_DEVINIT] =  nvc0_devinit_oclass;
-               device->oclass[NVDEV_SUBDEV_MC     ] =  nvc3_mc_oclass;
-               device->oclass[NVDEV_SUBDEV_BUS    ] =  nvc0_bus_oclass;
-               device->oclass[NVDEV_SUBDEV_TIMER  ] = &nv04_timer_oclass;
-               device->oclass[NVDEV_SUBDEV_FB     ] =  nvc0_fb_oclass;
-               device->oclass[NVDEV_SUBDEV_LTC    ] =  gf100_ltc_oclass;
-               device->oclass[NVDEV_SUBDEV_IBUS   ] = &nvc0_ibus_oclass;
-               device->oclass[NVDEV_SUBDEV_INSTMEM] =  nv50_instmem_oclass;
-               device->oclass[NVDEV_SUBDEV_VM     ] = &nvc0_vmmgr_oclass;
-               device->oclass[NVDEV_SUBDEV_BAR    ] = &nvc0_bar_oclass;
-               device->oclass[NVDEV_ENGINE_DMAOBJ ] =  nvd0_dmaeng_oclass;
-               device->oclass[NVDEV_ENGINE_FIFO   ] =  nvc0_fifo_oclass;
-               device->oclass[NVDEV_ENGINE_SW     ] =  nvc0_software_oclass;
-               device->oclass[NVDEV_ENGINE_GR     ] =  nvd7_graph_oclass;
-               device->oclass[NVDEV_ENGINE_VP     ] = &nvc0_vp_oclass;
-               device->oclass[NVDEV_ENGINE_BSP    ] = &nvc0_bsp_oclass;
-               device->oclass[NVDEV_ENGINE_PPP    ] = &nvc0_ppp_oclass;
-               device->oclass[NVDEV_ENGINE_COPY0  ] = &nvc0_copy0_oclass;
-               device->oclass[NVDEV_ENGINE_DISP   ] =  nvd0_disp_oclass;
-               device->oclass[NVDEV_ENGINE_PERFMON] = &nvc0_perfmon_oclass;
-               break;
-       default:
-               nv_fatal(device, "unknown Fermi chipset\n");
-               return -EINVAL;
-       }
-
-       return 0;
-       }
diff --git a/drivers/gpu/drm/nouveau/core/engine/device/nve0.c b/drivers/gpu/drm/nouveau/core/engine/device/nve0.c
deleted file mode 100644 (file)
index 7329226..0000000
+++ /dev/null
@@ -1,324 +0,0 @@
-/*
- * Copyright 2012 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 <subdev/bios.h>
-#include <subdev/bus.h>
-#include <subdev/gpio.h>
-#include <subdev/i2c.h>
-#include <subdev/fuse.h>
-#include <subdev/clock.h>
-#include <subdev/therm.h>
-#include <subdev/mxm.h>
-#include <subdev/devinit.h>
-#include <subdev/mc.h>
-#include <subdev/timer.h>
-#include <subdev/fb.h>
-#include <subdev/ltc.h>
-#include <subdev/ibus.h>
-#include <subdev/instmem.h>
-#include <subdev/vm.h>
-#include <subdev/bar.h>
-#include <subdev/pwr.h>
-#include <subdev/volt.h>
-
-#include <engine/device.h>
-#include <engine/dmaobj.h>
-#include <engine/fifo.h>
-#include <engine/software.h>
-#include <engine/graph.h>
-#include <engine/disp.h>
-#include <engine/copy.h>
-#include <engine/bsp.h>
-#include <engine/vp.h>
-#include <engine/ppp.h>
-#include <engine/perfmon.h>
-
-int
-nve0_identify(struct nouveau_device *device)
-{
-       switch (device->chipset) {
-       case 0xe4:
-               device->cname = "GK104";
-               device->oclass[NVDEV_SUBDEV_VBIOS  ] = &nouveau_bios_oclass;
-               device->oclass[NVDEV_SUBDEV_GPIO   ] =  nve0_gpio_oclass;
-               device->oclass[NVDEV_SUBDEV_I2C    ] =  nve0_i2c_oclass;
-               device->oclass[NVDEV_SUBDEV_FUSE   ] = &gf100_fuse_oclass;
-               device->oclass[NVDEV_SUBDEV_CLOCK  ] = &nve0_clock_oclass;
-               device->oclass[NVDEV_SUBDEV_THERM  ] = &nvd0_therm_oclass;
-               device->oclass[NVDEV_SUBDEV_MXM    ] = &nv50_mxm_oclass;
-               device->oclass[NVDEV_SUBDEV_DEVINIT] =  nvc0_devinit_oclass;
-               device->oclass[NVDEV_SUBDEV_MC     ] =  nvc3_mc_oclass;
-               device->oclass[NVDEV_SUBDEV_BUS    ] =  nvc0_bus_oclass;
-               device->oclass[NVDEV_SUBDEV_TIMER  ] = &nv04_timer_oclass;
-               device->oclass[NVDEV_SUBDEV_FB     ] =  nve0_fb_oclass;
-               device->oclass[NVDEV_SUBDEV_LTC    ] =  gk104_ltc_oclass;
-               device->oclass[NVDEV_SUBDEV_IBUS   ] = &nve0_ibus_oclass;
-               device->oclass[NVDEV_SUBDEV_INSTMEM] =  nv50_instmem_oclass;
-               device->oclass[NVDEV_SUBDEV_VM     ] = &nvc0_vmmgr_oclass;
-               device->oclass[NVDEV_SUBDEV_BAR    ] = &nvc0_bar_oclass;
-               device->oclass[NVDEV_SUBDEV_PWR    ] =  gk104_pwr_oclass;
-               device->oclass[NVDEV_SUBDEV_VOLT   ] = &nv40_volt_oclass;
-               device->oclass[NVDEV_ENGINE_DMAOBJ ] =  nvd0_dmaeng_oclass;
-               device->oclass[NVDEV_ENGINE_FIFO   ] =  nve0_fifo_oclass;
-               device->oclass[NVDEV_ENGINE_SW     ] =  nvc0_software_oclass;
-               device->oclass[NVDEV_ENGINE_GR     ] =  nve4_graph_oclass;
-               device->oclass[NVDEV_ENGINE_DISP   ] =  nve0_disp_oclass;
-               device->oclass[NVDEV_ENGINE_COPY0  ] = &nve0_copy0_oclass;
-               device->oclass[NVDEV_ENGINE_COPY1  ] = &nve0_copy1_oclass;
-               device->oclass[NVDEV_ENGINE_COPY2  ] = &nve0_copy2_oclass;
-               device->oclass[NVDEV_ENGINE_BSP    ] = &nve0_bsp_oclass;
-               device->oclass[NVDEV_ENGINE_VP     ] = &nve0_vp_oclass;
-               device->oclass[NVDEV_ENGINE_PPP    ] = &nvc0_ppp_oclass;
-               device->oclass[NVDEV_ENGINE_PERFMON] = &nve0_perfmon_oclass;
-               break;
-       case 0xe7:
-               device->cname = "GK107";
-               device->oclass[NVDEV_SUBDEV_VBIOS  ] = &nouveau_bios_oclass;
-               device->oclass[NVDEV_SUBDEV_GPIO   ] =  nve0_gpio_oclass;
-               device->oclass[NVDEV_SUBDEV_I2C    ] =  nve0_i2c_oclass;
-               device->oclass[NVDEV_SUBDEV_FUSE   ] = &gf100_fuse_oclass;
-               device->oclass[NVDEV_SUBDEV_CLOCK  ] = &nve0_clock_oclass;
-               device->oclass[NVDEV_SUBDEV_THERM  ] = &nvd0_therm_oclass;
-               device->oclass[NVDEV_SUBDEV_MXM    ] = &nv50_mxm_oclass;
-               device->oclass[NVDEV_SUBDEV_DEVINIT] =  nvc0_devinit_oclass;
-               device->oclass[NVDEV_SUBDEV_MC     ] =  nvc3_mc_oclass;
-               device->oclass[NVDEV_SUBDEV_BUS    ] =  nvc0_bus_oclass;
-               device->oclass[NVDEV_SUBDEV_TIMER  ] = &nv04_timer_oclass;
-               device->oclass[NVDEV_SUBDEV_FB     ] =  nve0_fb_oclass;
-               device->oclass[NVDEV_SUBDEV_LTC    ] =  gk104_ltc_oclass;
-               device->oclass[NVDEV_SUBDEV_IBUS   ] = &nve0_ibus_oclass;
-               device->oclass[NVDEV_SUBDEV_INSTMEM] =  nv50_instmem_oclass;
-               device->oclass[NVDEV_SUBDEV_VM     ] = &nvc0_vmmgr_oclass;
-               device->oclass[NVDEV_SUBDEV_BAR    ] = &nvc0_bar_oclass;
-               device->oclass[NVDEV_SUBDEV_PWR    ] =  nvd0_pwr_oclass;
-               device->oclass[NVDEV_SUBDEV_VOLT   ] = &nv40_volt_oclass;
-               device->oclass[NVDEV_ENGINE_DMAOBJ ] =  nvd0_dmaeng_oclass;
-               device->oclass[NVDEV_ENGINE_FIFO   ] =  nve0_fifo_oclass;
-               device->oclass[NVDEV_ENGINE_SW     ] =  nvc0_software_oclass;
-               device->oclass[NVDEV_ENGINE_GR     ] =  nve4_graph_oclass;
-               device->oclass[NVDEV_ENGINE_DISP   ] =  nve0_disp_oclass;
-               device->oclass[NVDEV_ENGINE_COPY0  ] = &nve0_copy0_oclass;
-               device->oclass[NVDEV_ENGINE_COPY1  ] = &nve0_copy1_oclass;
-               device->oclass[NVDEV_ENGINE_COPY2  ] = &nve0_copy2_oclass;
-               device->oclass[NVDEV_ENGINE_BSP    ] = &nve0_bsp_oclass;
-               device->oclass[NVDEV_ENGINE_VP     ] = &nve0_vp_oclass;
-               device->oclass[NVDEV_ENGINE_PPP    ] = &nvc0_ppp_oclass;
-               device->oclass[NVDEV_ENGINE_PERFMON] = &nve0_perfmon_oclass;
-               break;
-       case 0xe6:
-               device->cname = "GK106";
-               device->oclass[NVDEV_SUBDEV_VBIOS  ] = &nouveau_bios_oclass;
-               device->oclass[NVDEV_SUBDEV_GPIO   ] =  nve0_gpio_oclass;
-               device->oclass[NVDEV_SUBDEV_I2C    ] =  nve0_i2c_oclass;
-               device->oclass[NVDEV_SUBDEV_FUSE   ] = &gf100_fuse_oclass;
-               device->oclass[NVDEV_SUBDEV_CLOCK  ] = &nve0_clock_oclass;
-               device->oclass[NVDEV_SUBDEV_THERM  ] = &nvd0_therm_oclass;
-               device->oclass[NVDEV_SUBDEV_MXM    ] = &nv50_mxm_oclass;
-               device->oclass[NVDEV_SUBDEV_DEVINIT] =  nvc0_devinit_oclass;
-               device->oclass[NVDEV_SUBDEV_MC     ] =  nvc3_mc_oclass;
-               device->oclass[NVDEV_SUBDEV_BUS    ] =  nvc0_bus_oclass;
-               device->oclass[NVDEV_SUBDEV_TIMER  ] = &nv04_timer_oclass;
-               device->oclass[NVDEV_SUBDEV_FB     ] =  nve0_fb_oclass;
-               device->oclass[NVDEV_SUBDEV_LTC    ] =  gk104_ltc_oclass;
-               device->oclass[NVDEV_SUBDEV_IBUS   ] = &nve0_ibus_oclass;
-               device->oclass[NVDEV_SUBDEV_INSTMEM] =  nv50_instmem_oclass;
-               device->oclass[NVDEV_SUBDEV_VM     ] = &nvc0_vmmgr_oclass;
-               device->oclass[NVDEV_SUBDEV_BAR    ] = &nvc0_bar_oclass;
-               device->oclass[NVDEV_SUBDEV_PWR    ] =  gk104_pwr_oclass;
-               device->oclass[NVDEV_SUBDEV_VOLT   ] = &nv40_volt_oclass;
-               device->oclass[NVDEV_ENGINE_DMAOBJ ] =  nvd0_dmaeng_oclass;
-               device->oclass[NVDEV_ENGINE_FIFO   ] =  nve0_fifo_oclass;
-               device->oclass[NVDEV_ENGINE_SW     ] =  nvc0_software_oclass;
-               device->oclass[NVDEV_ENGINE_GR     ] =  nve4_graph_oclass;
-               device->oclass[NVDEV_ENGINE_DISP   ] =  nve0_disp_oclass;
-               device->oclass[NVDEV_ENGINE_COPY0  ] = &nve0_copy0_oclass;
-               device->oclass[NVDEV_ENGINE_COPY1  ] = &nve0_copy1_oclass;
-               device->oclass[NVDEV_ENGINE_COPY2  ] = &nve0_copy2_oclass;
-               device->oclass[NVDEV_ENGINE_BSP    ] = &nve0_bsp_oclass;
-               device->oclass[NVDEV_ENGINE_VP     ] = &nve0_vp_oclass;
-               device->oclass[NVDEV_ENGINE_PPP    ] = &nvc0_ppp_oclass;
-               device->oclass[NVDEV_ENGINE_PERFMON] = &nve0_perfmon_oclass;
-               break;
-       case 0xea:
-               device->cname = "GK20A";
-               device->oclass[NVDEV_SUBDEV_CLOCK  ] = &gk20a_clock_oclass;
-               device->oclass[NVDEV_SUBDEV_MC     ] =  gk20a_mc_oclass;
-               device->oclass[NVDEV_SUBDEV_BUS    ] =  nvc0_bus_oclass;
-               device->oclass[NVDEV_SUBDEV_FUSE   ] = &gf100_fuse_oclass;
-               device->oclass[NVDEV_SUBDEV_TIMER  ] = &gk20a_timer_oclass;
-               device->oclass[NVDEV_SUBDEV_FB     ] =  gk20a_fb_oclass;
-               device->oclass[NVDEV_SUBDEV_LTC    ] =  gk104_ltc_oclass;
-               device->oclass[NVDEV_SUBDEV_IBUS   ] = &gk20a_ibus_oclass;
-               device->oclass[NVDEV_SUBDEV_INSTMEM] = nv50_instmem_oclass;
-               device->oclass[NVDEV_SUBDEV_VM     ] = &nvc0_vmmgr_oclass;
-               device->oclass[NVDEV_SUBDEV_BAR    ] = &gk20a_bar_oclass;
-               device->oclass[NVDEV_ENGINE_DMAOBJ ] =  nvd0_dmaeng_oclass;
-               device->oclass[NVDEV_ENGINE_FIFO   ] =  gk20a_fifo_oclass;
-               device->oclass[NVDEV_ENGINE_SW     ] =  nvc0_software_oclass;
-               device->oclass[NVDEV_ENGINE_GR     ] =  gk20a_graph_oclass;
-               device->oclass[NVDEV_ENGINE_COPY2  ] = &nve0_copy2_oclass;
-               device->oclass[NVDEV_ENGINE_PERFMON] = &nve0_perfmon_oclass;
-               device->oclass[NVDEV_SUBDEV_VOLT   ] = &gk20a_volt_oclass;
-               break;
-       case 0xf0:
-               device->cname = "GK110";
-               device->oclass[NVDEV_SUBDEV_VBIOS  ] = &nouveau_bios_oclass;
-               device->oclass[NVDEV_SUBDEV_GPIO   ] =  nve0_gpio_oclass;
-               device->oclass[NVDEV_SUBDEV_I2C    ] =  nve0_i2c_oclass;
-               device->oclass[NVDEV_SUBDEV_FUSE   ] = &gf100_fuse_oclass;
-               device->oclass[NVDEV_SUBDEV_CLOCK  ] = &nve0_clock_oclass;
-               device->oclass[NVDEV_SUBDEV_THERM  ] = &nvd0_therm_oclass;
-               device->oclass[NVDEV_SUBDEV_MXM    ] = &nv50_mxm_oclass;
-               device->oclass[NVDEV_SUBDEV_DEVINIT] =  nvc0_devinit_oclass;
-               device->oclass[NVDEV_SUBDEV_MC     ] =  nvc3_mc_oclass;
-               device->oclass[NVDEV_SUBDEV_BUS    ] =  nvc0_bus_oclass;
-               device->oclass[NVDEV_SUBDEV_TIMER  ] = &nv04_timer_oclass;
-               device->oclass[NVDEV_SUBDEV_FB     ] =  nve0_fb_oclass;
-               device->oclass[NVDEV_SUBDEV_LTC    ] =  gk104_ltc_oclass;
-               device->oclass[NVDEV_SUBDEV_IBUS   ] = &nve0_ibus_oclass;
-               device->oclass[NVDEV_SUBDEV_INSTMEM] =  nv50_instmem_oclass;
-               device->oclass[NVDEV_SUBDEV_VM     ] = &nvc0_vmmgr_oclass;
-               device->oclass[NVDEV_SUBDEV_BAR    ] = &nvc0_bar_oclass;
-               device->oclass[NVDEV_SUBDEV_PWR    ] =  nvd0_pwr_oclass;
-               device->oclass[NVDEV_SUBDEV_VOLT   ] = &nv40_volt_oclass;
-               device->oclass[NVDEV_ENGINE_DMAOBJ ] =  nvd0_dmaeng_oclass;
-               device->oclass[NVDEV_ENGINE_FIFO   ] =  nve0_fifo_oclass;
-               device->oclass[NVDEV_ENGINE_SW     ] =  nvc0_software_oclass;
-               device->oclass[NVDEV_ENGINE_GR     ] =  nvf0_graph_oclass;
-               device->oclass[NVDEV_ENGINE_DISP   ] =  nvf0_disp_oclass;
-               device->oclass[NVDEV_ENGINE_COPY0  ] = &nve0_copy0_oclass;
-               device->oclass[NVDEV_ENGINE_COPY1  ] = &nve0_copy1_oclass;
-               device->oclass[NVDEV_ENGINE_COPY2  ] = &nve0_copy2_oclass;
-               device->oclass[NVDEV_ENGINE_BSP    ] = &nve0_bsp_oclass;
-               device->oclass[NVDEV_ENGINE_VP     ] = &nve0_vp_oclass;
-               device->oclass[NVDEV_ENGINE_PPP    ] = &nvc0_ppp_oclass;
-               device->oclass[NVDEV_ENGINE_PERFMON] = &nvf0_perfmon_oclass;
-               break;
-       case 0xf1:
-               device->cname = "GK110B";
-               device->oclass[NVDEV_SUBDEV_VBIOS  ] = &nouveau_bios_oclass;
-               device->oclass[NVDEV_SUBDEV_GPIO   ] =  nve0_gpio_oclass;
-               device->oclass[NVDEV_SUBDEV_I2C    ] =  nvd0_i2c_oclass;
-               device->oclass[NVDEV_SUBDEV_FUSE   ] = &gf100_fuse_oclass;
-               device->oclass[NVDEV_SUBDEV_CLOCK  ] = &nve0_clock_oclass;
-               device->oclass[NVDEV_SUBDEV_THERM  ] = &nvd0_therm_oclass;
-               device->oclass[NVDEV_SUBDEV_MXM    ] = &nv50_mxm_oclass;
-               device->oclass[NVDEV_SUBDEV_DEVINIT] =  nvc0_devinit_oclass;
-               device->oclass[NVDEV_SUBDEV_MC     ] =  nvc3_mc_oclass;
-               device->oclass[NVDEV_SUBDEV_BUS    ] =  nvc0_bus_oclass;
-               device->oclass[NVDEV_SUBDEV_TIMER  ] = &nv04_timer_oclass;
-               device->oclass[NVDEV_SUBDEV_FB     ] =  nve0_fb_oclass;
-               device->oclass[NVDEV_SUBDEV_LTC    ] =  gk104_ltc_oclass;
-               device->oclass[NVDEV_SUBDEV_IBUS   ] = &nve0_ibus_oclass;
-               device->oclass[NVDEV_SUBDEV_INSTMEM] =  nv50_instmem_oclass;
-               device->oclass[NVDEV_SUBDEV_VM     ] = &nvc0_vmmgr_oclass;
-               device->oclass[NVDEV_SUBDEV_BAR    ] = &nvc0_bar_oclass;
-               device->oclass[NVDEV_SUBDEV_PWR    ] =  nvd0_pwr_oclass;
-               device->oclass[NVDEV_SUBDEV_VOLT   ] = &nv40_volt_oclass;
-               device->oclass[NVDEV_ENGINE_DMAOBJ ] =  nvd0_dmaeng_oclass;
-               device->oclass[NVDEV_ENGINE_FIFO   ] =  nve0_fifo_oclass;
-               device->oclass[NVDEV_ENGINE_SW     ] =  nvc0_software_oclass;
-               device->oclass[NVDEV_ENGINE_GR     ] =  gk110b_graph_oclass;
-               device->oclass[NVDEV_ENGINE_DISP   ] =  nvf0_disp_oclass;
-               device->oclass[NVDEV_ENGINE_COPY0  ] = &nve0_copy0_oclass;
-               device->oclass[NVDEV_ENGINE_COPY1  ] = &nve0_copy1_oclass;
-               device->oclass[NVDEV_ENGINE_COPY2  ] = &nve0_copy2_oclass;
-               device->oclass[NVDEV_ENGINE_BSP    ] = &nve0_bsp_oclass;
-               device->oclass[NVDEV_ENGINE_VP     ] = &nve0_vp_oclass;
-               device->oclass[NVDEV_ENGINE_PPP    ] = &nvc0_ppp_oclass;
-               device->oclass[NVDEV_ENGINE_PERFMON] = &nvf0_perfmon_oclass;
-               break;
-       case 0x106:
-               device->cname = "GK208B";
-               device->oclass[NVDEV_SUBDEV_VBIOS  ] = &nouveau_bios_oclass;
-               device->oclass[NVDEV_SUBDEV_GPIO   ] =  nve0_gpio_oclass;
-               device->oclass[NVDEV_SUBDEV_I2C    ] =  nve0_i2c_oclass;
-               device->oclass[NVDEV_SUBDEV_FUSE   ] = &gf100_fuse_oclass;
-               device->oclass[NVDEV_SUBDEV_CLOCK  ] = &nve0_clock_oclass;
-               device->oclass[NVDEV_SUBDEV_THERM  ] = &nvd0_therm_oclass;
-               device->oclass[NVDEV_SUBDEV_MXM    ] = &nv50_mxm_oclass;
-               device->oclass[NVDEV_SUBDEV_DEVINIT] =  nvc0_devinit_oclass;
-               device->oclass[NVDEV_SUBDEV_MC     ] =  gk20a_mc_oclass;
-               device->oclass[NVDEV_SUBDEV_BUS    ] =  nvc0_bus_oclass;
-               device->oclass[NVDEV_SUBDEV_TIMER  ] = &nv04_timer_oclass;
-               device->oclass[NVDEV_SUBDEV_FB     ] =  nve0_fb_oclass;
-               device->oclass[NVDEV_SUBDEV_LTC    ] =  gk104_ltc_oclass;
-               device->oclass[NVDEV_SUBDEV_IBUS   ] = &nve0_ibus_oclass;
-               device->oclass[NVDEV_SUBDEV_INSTMEM] =  nv50_instmem_oclass;
-               device->oclass[NVDEV_SUBDEV_VM     ] = &nvc0_vmmgr_oclass;
-               device->oclass[NVDEV_SUBDEV_BAR    ] = &nvc0_bar_oclass;
-               device->oclass[NVDEV_SUBDEV_PWR    ] =  nv108_pwr_oclass;
-               device->oclass[NVDEV_SUBDEV_VOLT   ] = &nv40_volt_oclass;
-               device->oclass[NVDEV_ENGINE_DMAOBJ ] =  nvd0_dmaeng_oclass;
-               device->oclass[NVDEV_ENGINE_FIFO   ] =  nv108_fifo_oclass;
-               device->oclass[NVDEV_ENGINE_SW     ] =  nvc0_software_oclass;
-               device->oclass[NVDEV_ENGINE_GR     ] =  nv108_graph_oclass;
-               device->oclass[NVDEV_ENGINE_DISP   ] =  nvf0_disp_oclass;
-               device->oclass[NVDEV_ENGINE_COPY0  ] = &nve0_copy0_oclass;
-               device->oclass[NVDEV_ENGINE_COPY1  ] = &nve0_copy1_oclass;
-               device->oclass[NVDEV_ENGINE_COPY2  ] = &nve0_copy2_oclass;
-               device->oclass[NVDEV_ENGINE_BSP    ] = &nve0_bsp_oclass;
-               device->oclass[NVDEV_ENGINE_VP     ] = &nve0_vp_oclass;
-               device->oclass[NVDEV_ENGINE_PPP    ] = &nvc0_ppp_oclass;
-               break;
-       case 0x108:
-               device->cname = "GK208";
-               device->oclass[NVDEV_SUBDEV_VBIOS  ] = &nouveau_bios_oclass;
-               device->oclass[NVDEV_SUBDEV_GPIO   ] =  nve0_gpio_oclass;
-               device->oclass[NVDEV_SUBDEV_I2C    ] =  nve0_i2c_oclass;
-               device->oclass[NVDEV_SUBDEV_FUSE   ] = &gf100_fuse_oclass;
-               device->oclass[NVDEV_SUBDEV_CLOCK  ] = &nve0_clock_oclass;
-               device->oclass[NVDEV_SUBDEV_THERM  ] = &nvd0_therm_oclass;
-               device->oclass[NVDEV_SUBDEV_MXM    ] = &nv50_mxm_oclass;
-               device->oclass[NVDEV_SUBDEV_DEVINIT] =  nvc0_devinit_oclass;
-               device->oclass[NVDEV_SUBDEV_MC     ] =  gk20a_mc_oclass;
-               device->oclass[NVDEV_SUBDEV_BUS    ] =  nvc0_bus_oclass;
-               device->oclass[NVDEV_SUBDEV_TIMER  ] = &nv04_timer_oclass;
-               device->oclass[NVDEV_SUBDEV_FB     ] =  nve0_fb_oclass;
-               device->oclass[NVDEV_SUBDEV_LTC    ] =  gk104_ltc_oclass;
-               device->oclass[NVDEV_SUBDEV_IBUS   ] = &nve0_ibus_oclass;
-               device->oclass[NVDEV_SUBDEV_INSTMEM] =  nv50_instmem_oclass;
-               device->oclass[NVDEV_SUBDEV_VM     ] = &nvc0_vmmgr_oclass;
-               device->oclass[NVDEV_SUBDEV_BAR    ] = &nvc0_bar_oclass;
-               device->oclass[NVDEV_SUBDEV_PWR    ] =  nv108_pwr_oclass;
-               device->oclass[NVDEV_SUBDEV_VOLT   ] = &nv40_volt_oclass;
-               device->oclass[NVDEV_ENGINE_DMAOBJ ] =  nvd0_dmaeng_oclass;
-               device->oclass[NVDEV_ENGINE_FIFO   ] =  nv108_fifo_oclass;
-               device->oclass[NVDEV_ENGINE_SW     ] =  nvc0_software_oclass;
-               device->oclass[NVDEV_ENGINE_GR     ] =  nv108_graph_oclass;
-               device->oclass[NVDEV_ENGINE_DISP   ] =  nvf0_disp_oclass;
-               device->oclass[NVDEV_ENGINE_COPY0  ] = &nve0_copy0_oclass;
-               device->oclass[NVDEV_ENGINE_COPY1  ] = &nve0_copy1_oclass;
-               device->oclass[NVDEV_ENGINE_COPY2  ] = &nve0_copy2_oclass;
-               device->oclass[NVDEV_ENGINE_BSP    ] = &nve0_bsp_oclass;
-               device->oclass[NVDEV_ENGINE_VP     ] = &nve0_vp_oclass;
-               device->oclass[NVDEV_ENGINE_PPP    ] = &nvc0_ppp_oclass;
-               break;
-       default:
-               nv_fatal(device, "unknown Kepler chipset\n");
-               return -EINVAL;
-       }
-
-       return 0;
-}
diff --git a/drivers/gpu/drm/nouveau/core/engine/device/priv.h b/drivers/gpu/drm/nouveau/core/engine/device/priv.h
deleted file mode 100644 (file)
index 035fd5b..0000000
+++ /dev/null
@@ -1,8 +0,0 @@
-#ifndef __NVKM_DEVICE_PRIV_H__
-#define __NVKM_DEVICE_PRIV_H__
-
-#include <engine/device.h>
-
-extern struct nouveau_oclass nouveau_control_oclass[];
-
-#endif
diff --git a/drivers/gpu/drm/nouveau/core/engine/disp/base.c b/drivers/gpu/drm/nouveau/core/engine/disp/base.c
deleted file mode 100644 (file)
index 64b8466..0000000
+++ /dev/null
@@ -1,242 +0,0 @@
-/*
- * Copyright 2013 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 <core/os.h>
-#include <nvif/unpack.h>
-#include <nvif/class.h>
-#include <nvif/event.h>
-
-#include "priv.h"
-#include "outp.h"
-#include "conn.h"
-
-int
-nouveau_disp_vblank_ctor(struct nouveau_object *object, void *data, u32 size,
-                        struct nvkm_notify *notify)
-{
-       struct nouveau_disp *disp =
-               container_of(notify->event, typeof(*disp), vblank);
-       union {
-               struct nvif_notify_head_req_v0 v0;
-       } *req = data;
-       int ret;
-
-       if (nvif_unpack(req->v0, 0, 0, false)) {
-               notify->size = sizeof(struct nvif_notify_head_rep_v0);
-               if (ret = -ENXIO, req->v0.head <= disp->vblank.index_nr) {
-                       notify->types = 1;
-                       notify->index = req->v0.head;
-                       return 0;
-               }
-       }
-
-       return ret;
-}
-
-void
-nouveau_disp_vblank(struct nouveau_disp *disp, int head)
-{
-       struct nvif_notify_head_rep_v0 rep = {};
-       nvkm_event_send(&disp->vblank, 1, head, &rep, sizeof(rep));
-}
-
-static int
-nouveau_disp_hpd_ctor(struct nouveau_object *object, void *data, u32 size,
-                     struct nvkm_notify *notify)
-{
-       struct nouveau_disp *disp =
-               container_of(notify->event, typeof(*disp), hpd);
-       union {
-               struct nvif_notify_conn_req_v0 v0;
-       } *req = data;
-       struct nvkm_output *outp;
-       int ret;
-
-       if (nvif_unpack(req->v0, 0, 0, false)) {
-               notify->size = sizeof(struct nvif_notify_conn_rep_v0);
-               list_for_each_entry(outp, &disp->outp, head) {
-                       if (ret = -ENXIO, outp->conn->index == req->v0.conn) {
-                               if (ret = -ENODEV, outp->conn->hpd.event) {
-                                       notify->types = req->v0.mask;
-                                       notify->index = req->v0.conn;
-                                       ret = 0;
-                               }
-                               break;
-                       }
-               }
-       }
-
-       return ret;
-}
-
-static const struct nvkm_event_func
-nouveau_disp_hpd_func = {
-       .ctor = nouveau_disp_hpd_ctor
-};
-
-int
-nouveau_disp_ntfy(struct nouveau_object *object, u32 type,
-                 struct nvkm_event **event)
-{
-       struct nouveau_disp *disp = (void *)object->engine;
-       switch (type) {
-       case NV04_DISP_NTFY_VBLANK:
-               *event = &disp->vblank;
-               return 0;
-       case NV04_DISP_NTFY_CONN:
-               *event = &disp->hpd;
-               return 0;
-       default:
-               break;
-       }
-       return -EINVAL;
-}
-
-int
-_nouveau_disp_fini(struct nouveau_object *object, bool suspend)
-{
-       struct nouveau_disp *disp = (void *)object;
-       struct nvkm_output *outp;
-       int ret;
-
-       list_for_each_entry(outp, &disp->outp, head) {
-               ret = nv_ofuncs(outp)->fini(nv_object(outp), suspend);
-               if (ret && suspend)
-                       goto fail_outp;
-       }
-
-       return nouveau_engine_fini(&disp->base, suspend);
-
-fail_outp:
-       list_for_each_entry_continue_reverse(outp, &disp->outp, head) {
-               nv_ofuncs(outp)->init(nv_object(outp));
-       }
-
-       return ret;
-}
-
-int
-_nouveau_disp_init(struct nouveau_object *object)
-{
-       struct nouveau_disp *disp = (void *)object;
-       struct nvkm_output *outp;
-       int ret;
-
-       ret = nouveau_engine_init(&disp->base);
-       if (ret)
-               return ret;
-
-       list_for_each_entry(outp, &disp->outp, head) {
-               ret = nv_ofuncs(outp)->init(nv_object(outp));
-               if (ret)
-                       goto fail_outp;
-       }
-
-       return ret;
-
-fail_outp:
-       list_for_each_entry_continue_reverse(outp, &disp->outp, head) {
-               nv_ofuncs(outp)->fini(nv_object(outp), false);
-       }
-
-       return ret;
-}
-
-void
-_nouveau_disp_dtor(struct nouveau_object *object)
-{
-       struct nouveau_disp *disp = (void *)object;
-       struct nvkm_output *outp, *outt;
-
-       nvkm_event_fini(&disp->vblank);
-       nvkm_event_fini(&disp->hpd);
-
-       if (disp->outp.next) {
-               list_for_each_entry_safe(outp, outt, &disp->outp, head) {
-                       nouveau_object_ref(NULL, (struct nouveau_object **)&outp);
-               }
-       }
-
-       nouveau_engine_destroy(&disp->base);
-}
-
-int
-nouveau_disp_create_(struct nouveau_object *parent,
-                    struct nouveau_object *engine,
-                    struct nouveau_oclass *oclass, int heads,
-                    const char *intname, const char *extname,
-                    int length, void **pobject)
-{
-       struct nouveau_disp_impl *impl = (void *)oclass;
-       struct nouveau_bios *bios = nouveau_bios(parent);
-       struct nouveau_disp *disp;
-       struct nouveau_oclass **sclass;
-       struct nouveau_object *object;
-       struct dcb_output dcbE;
-       u8  hpd = 0, ver, hdr;
-       u32 data;
-       int ret, i;
-
-       ret = nouveau_engine_create_(parent, engine, oclass, true,
-                                    intname, extname, length, pobject);
-       disp = *pobject;
-       if (ret)
-               return ret;
-
-       INIT_LIST_HEAD(&disp->outp);
-
-       /* create output objects for each display path in the vbios */
-       i = -1;
-       while ((data = dcb_outp_parse(bios, ++i, &ver, &hdr, &dcbE))) {
-               if (dcbE.type == DCB_OUTPUT_UNUSED)
-                       continue;
-               if (dcbE.type == DCB_OUTPUT_EOL)
-                       break;
-               data = dcbE.location << 4 | dcbE.type;
-
-               oclass = nvkm_output_oclass;
-               sclass = impl->outp;
-               while (sclass && sclass[0]) {
-                       if (sclass[0]->handle == data) {
-                               oclass = sclass[0];
-                               break;
-                       }
-                       sclass++;
-               }
-
-               nouveau_object_ctor(*pobject, *pobject, oclass,
-                                   &dcbE, i, &object);
-               hpd = max(hpd, (u8)(dcbE.connector + 1));
-       }
-
-       ret = nvkm_event_init(&nouveau_disp_hpd_func, 3, hpd, &disp->hpd);
-       if (ret)
-               return ret;
-
-       ret = nvkm_event_init(impl->vblank, 1, heads, &disp->vblank);
-       if (ret)
-               return ret;
-
-       return 0;
-}
diff --git a/drivers/gpu/drm/nouveau/core/engine/disp/conn.c b/drivers/gpu/drm/nouveau/core/engine/disp/conn.c
deleted file mode 100644 (file)
index 1496b56..0000000
+++ /dev/null
@@ -1,175 +0,0 @@
-/*
- * Copyright 2014 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 <core/os.h>
-#include <nvif/event.h>
-
-#include <subdev/gpio.h>
-
-#include "conn.h"
-#include "outp.h"
-
-static int
-nvkm_connector_hpd(struct nvkm_notify *notify)
-{
-       struct nvkm_connector *conn = container_of(notify, typeof(*conn), hpd);
-       struct nouveau_disp *disp = nouveau_disp(conn);
-       struct nouveau_gpio *gpio = nouveau_gpio(conn);
-       const struct nvkm_gpio_ntfy_rep *line = notify->data;
-       struct nvif_notify_conn_rep_v0 rep;
-       int index = conn->index;
-
-       DBG("HPD: %d\n", line->mask);
-
-       if (!gpio->get(gpio, 0, DCB_GPIO_UNUSED, conn->hpd.index))
-               rep.mask = NVIF_NOTIFY_CONN_V0_UNPLUG;
-       else
-               rep.mask = NVIF_NOTIFY_CONN_V0_PLUG;
-       rep.version = 0;
-
-       nvkm_event_send(&disp->hpd, rep.mask, index, &rep, sizeof(rep));
-       return NVKM_NOTIFY_KEEP;
-}
-
-int
-_nvkm_connector_fini(struct nouveau_object *object, bool suspend)
-{
-       struct nvkm_connector *conn = (void *)object;
-       nvkm_notify_put(&conn->hpd);
-       return nouveau_object_fini(&conn->base, suspend);
-}
-
-int
-_nvkm_connector_init(struct nouveau_object *object)
-{
-       struct nvkm_connector *conn = (void *)object;
-       int ret = nouveau_object_init(&conn->base);
-       if (ret == 0)
-               nvkm_notify_get(&conn->hpd);
-       return ret;
-}
-
-void
-_nvkm_connector_dtor(struct nouveau_object *object)
-{
-       struct nvkm_connector *conn = (void *)object;
-       nvkm_notify_fini(&conn->hpd);
-       nouveau_object_destroy(&conn->base);
-}
-
-int
-nvkm_connector_create_(struct nouveau_object *parent,
-                      struct nouveau_object *engine,
-                      struct nouveau_oclass *oclass,
-                      struct nvbios_connE *info, int index,
-                      int length, void **pobject)
-{
-       static const u8 hpd[] = { 0x07, 0x08, 0x51, 0x52, 0x5e, 0x5f, 0x60 };
-       struct nouveau_gpio *gpio = nouveau_gpio(parent);
-       struct nouveau_disp *disp = (void *)engine;
-       struct nvkm_connector *conn;
-       struct nvkm_output *outp;
-       struct dcb_gpio_func func;
-       int ret;
-
-       list_for_each_entry(outp, &disp->outp, head) {
-               if (outp->conn && outp->conn->index == index) {
-                       atomic_inc(&nv_object(outp->conn)->refcount);
-                       *pobject = outp->conn;
-                       return 1;
-               }
-       }
-
-       ret = nouveau_object_create_(parent, engine, oclass, 0, length, pobject);
-       conn = *pobject;
-       if (ret)
-               return ret;
-
-       conn->info = *info;
-       conn->index = index;
-
-       DBG("type %02x loc %d hpd %02x dp %x di %x sr %x lcdid %x\n",
-           info->type, info->location, info->hpd, info->dp,
-           info->di, info->sr, info->lcdid);
-
-       if ((info->hpd = ffs(info->hpd))) {
-               if (--info->hpd >= ARRAY_SIZE(hpd)) {
-                       ERR("hpd %02x unknown\n", info->hpd);
-                       return 0;
-               }
-               info->hpd = hpd[info->hpd];
-
-               ret = gpio->find(gpio, 0, info->hpd, DCB_GPIO_UNUSED, &func);
-               if (ret) {
-                       ERR("func %02x lookup failed, %d\n", info->hpd, ret);
-                       return 0;
-               }
-
-               ret = nvkm_notify_init(NULL, &gpio->event, nvkm_connector_hpd,
-                                      true, &(struct nvkm_gpio_ntfy_req) {
-                                       .mask = NVKM_GPIO_TOGGLED,
-                                       .line = func.line,
-                                      },
-                                      sizeof(struct nvkm_gpio_ntfy_req),
-                                      sizeof(struct nvkm_gpio_ntfy_rep),
-                                      &conn->hpd);
-               if (ret) {
-                       ERR("func %02x failed, %d\n", info->hpd, ret);
-               } else {
-                       DBG("func %02x (HPD)\n", info->hpd);
-               }
-       }
-
-       return 0;
-}
-
-int
-_nvkm_connector_ctor(struct nouveau_object *parent,
-                    struct nouveau_object *engine,
-                    struct nouveau_oclass *oclass, void *info, u32 index,
-                    struct nouveau_object **pobject)
-{
-       struct nvkm_connector *conn;
-       int ret;
-
-       ret = nvkm_connector_create(parent, engine, oclass, info, index, &conn);
-       *pobject = nv_object(conn);
-       if (ret)
-               return ret;
-
-       return 0;
-}
-
-struct nouveau_oclass *
-nvkm_connector_oclass = &(struct nvkm_connector_impl) {
-       .base = {
-               .handle = 0,
-               .ofuncs = &(struct nouveau_ofuncs) {
-                       .ctor = _nvkm_connector_ctor,
-                       .dtor = _nvkm_connector_dtor,
-                       .init = _nvkm_connector_init,
-                       .fini = _nvkm_connector_fini,
-               },
-       },
-}.base;
diff --git a/drivers/gpu/drm/nouveau/core/engine/disp/conn.h b/drivers/gpu/drm/nouveau/core/engine/disp/conn.h
deleted file mode 100644 (file)
index 55e5f5c..0000000
+++ /dev/null
@@ -1,56 +0,0 @@
-#ifndef __NVKM_DISP_CONN_H__
-#define __NVKM_DISP_CONN_H__
-
-#include "priv.h"
-
-struct nvkm_connector {
-       struct nouveau_object base;
-       struct list_head head;
-
-       struct nvbios_connE info;
-       int index;
-
-       struct nvkm_notify hpd;
-};
-
-#define nvkm_connector_create(p,e,c,b,i,d)                                     \
-       nvkm_connector_create_((p), (e), (c), (b), (i), sizeof(**d), (void **)d)
-#define nvkm_connector_destroy(d) ({                                           \
-       struct nvkm_connector *disp = (d);                                     \
-       _nvkm_connector_dtor(nv_object(disp));                                 \
-})
-#define nvkm_connector_init(d) ({                                              \
-       struct nvkm_connector *disp = (d);                                     \
-       _nvkm_connector_init(nv_object(disp));                                 \
-})
-#define nvkm_connector_fini(d,s) ({                                            \
-       struct nvkm_connector *disp = (d);                                     \
-       _nvkm_connector_fini(nv_object(disp), (s));                            \
-})
-
-int nvkm_connector_create_(struct nouveau_object *, struct nouveau_object *,
-                          struct nouveau_oclass *, struct nvbios_connE *,
-                          int, int, void **);
-
-int  _nvkm_connector_ctor(struct nouveau_object *, struct nouveau_object *,
-                         struct nouveau_oclass *, void *, u32,
-                         struct nouveau_object **);
-void _nvkm_connector_dtor(struct nouveau_object *);
-int  _nvkm_connector_init(struct nouveau_object *);
-int  _nvkm_connector_fini(struct nouveau_object *, bool);
-
-struct nvkm_connector_impl {
-       struct nouveau_oclass base;
-};
-
-#ifndef MSG
-#define MSG(l,f,a...) do {                                                     \
-       struct nvkm_connector *_conn = (void *)conn;                           \
-       nv_##l(nv_object(conn)->engine, "%02x:%02x%02x: "f, _conn->index,      \
-              _conn->info.location, _conn->info.type, ##a);                   \
-} while(0)
-#define DBG(f,a...) MSG(debug, f, ##a)
-#define ERR(f,a...) MSG(error, f, ##a)
-#endif
-
-#endif
diff --git a/drivers/gpu/drm/nouveau/core/engine/disp/dacnv50.c b/drivers/gpu/drm/nouveau/core/engine/disp/dacnv50.c
deleted file mode 100644 (file)
index b36addf..0000000
+++ /dev/null
@@ -1,101 +0,0 @@
-/*
- * Copyright 2012 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 <core/client.h>
-#include <nvif/unpack.h>
-#include <nvif/class.h>
-
-#include <subdev/bios.h>
-#include <subdev/bios/dcb.h>
-#include <subdev/timer.h>
-
-#include "nv50.h"
-
-int
-nv50_dac_power(NV50_DISP_MTHD_V1)
-{
-       const u32 doff = outp->or * 0x800;
-       union {
-               struct nv50_disp_dac_pwr_v0 v0;
-       } *args = data;
-       u32 stat;
-       int ret;
-
-       nv_ioctl(object, "disp dac pwr size %d\n", size);
-       if (nvif_unpack(args->v0, 0, 0, false)) {
-               nv_ioctl(object, "disp dac pwr vers %d state %d data %d "
-                                "vsync %d hsync %d\n",
-                        args->v0.version, args->v0.state, args->v0.data,
-                        args->v0.vsync, args->v0.hsync);
-               stat  = 0x00000040 * !args->v0.state;
-               stat |= 0x00000010 * !args->v0.data;
-               stat |= 0x00000004 * !args->v0.vsync;
-               stat |= 0x00000001 * !args->v0.hsync;
-       } else
-               return ret;
-
-       nv_wait(priv, 0x61a004 + doff, 0x80000000, 0x00000000);
-       nv_mask(priv, 0x61a004 + doff, 0xc000007f, 0x80000000 | stat);
-       nv_wait(priv, 0x61a004 + doff, 0x80000000, 0x00000000);
-       return 0;
-}
-
-int
-nv50_dac_sense(NV50_DISP_MTHD_V1)
-{
-       union {
-               struct nv50_disp_dac_load_v0 v0;
-       } *args = data;
-       const u32 doff = outp->or * 0x800;
-       u32 loadval;
-       int ret;
-
-       nv_ioctl(object, "disp dac load size %d\n", size);
-       if (nvif_unpack(args->v0, 0, 0, false)) {
-               nv_ioctl(object, "disp dac load vers %d data %08x\n",
-                        args->v0.version, args->v0.data);
-               if (args->v0.data & 0xfff00000)
-                       return -EINVAL;
-               loadval = args->v0.data;
-       } else
-               return ret;
-
-       nv_mask(priv, 0x61a004 + doff, 0x807f0000, 0x80150000);
-       nv_wait(priv, 0x61a004 + doff, 0x80000000, 0x00000000);
-
-       nv_wr32(priv, 0x61a00c + doff, 0x00100000 | loadval);
-       mdelay(9);
-       udelay(500);
-       loadval = nv_mask(priv, 0x61a00c + doff, 0xffffffff, 0x00000000);
-
-       nv_mask(priv, 0x61a004 + doff, 0x807f0000, 0x80550000);
-       nv_wait(priv, 0x61a004 + doff, 0x80000000, 0x00000000);
-
-       nv_debug(priv, "DAC%d sense: 0x%08x\n", outp->or, loadval);
-       if (!(loadval & 0x80000000))
-               return -ETIMEDOUT;
-
-       args->v0.load = (loadval & 0x38000000) >> 27;
-       return 0;
-}
diff --git a/drivers/gpu/drm/nouveau/core/engine/disp/dport.c b/drivers/gpu/drm/nouveau/core/engine/disp/dport.c
deleted file mode 100644 (file)
index 16db08d..0000000
+++ /dev/null
@@ -1,402 +0,0 @@
-/*
- * Copyright 2013 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 <subdev/bios.h>
-#include <subdev/bios/dcb.h>
-#include <subdev/bios/dp.h>
-#include <subdev/bios/init.h>
-#include <subdev/i2c.h>
-
-#include "nv50.h"
-
-#include <nvif/class.h>
-
-#include "dport.h"
-#include "outpdp.h"
-
-/******************************************************************************
- * link training
- *****************************************************************************/
-struct dp_state {
-       struct nvkm_output_dp *outp;
-       int link_nr;
-       u32 link_bw;
-       u8  stat[6];
-       u8  conf[4];
-       bool pc2;
-       u8  pc2stat;
-       u8  pc2conf[2];
-};
-
-static int
-dp_set_link_config(struct dp_state *dp)
-{
-       struct nvkm_output_dp_impl *impl = (void *)nv_oclass(dp->outp);
-       struct nvkm_output_dp *outp = dp->outp;
-       struct nouveau_disp *disp = nouveau_disp(outp);
-       struct nouveau_bios *bios = nouveau_bios(disp);
-       struct nvbios_init init = {
-               .subdev = nv_subdev(disp),
-               .bios = bios,
-               .offset = 0x0000,
-               .outp = &outp->base.info,
-               .crtc = -1,
-               .execute = 1,
-       };
-       u32 lnkcmp;
-       u8 sink[2];
-       int ret;
-
-       DBG("%d lanes at %d KB/s\n", dp->link_nr, dp->link_bw);
-
-       /* set desired link configuration on the source */
-       if ((lnkcmp = dp->outp->info.lnkcmp)) {
-               if (outp->version < 0x30) {
-                       while ((dp->link_bw / 10) < nv_ro16(bios, lnkcmp))
-                               lnkcmp += 4;
-                       init.offset = nv_ro16(bios, lnkcmp + 2);
-               } else {
-                       while ((dp->link_bw / 27000) < nv_ro08(bios, lnkcmp))
-                               lnkcmp += 3;
-                       init.offset = nv_ro16(bios, lnkcmp + 1);
-               }
-
-               nvbios_exec(&init);
-       }
-
-       ret = impl->lnk_ctl(outp, dp->link_nr, dp->link_bw / 27000,
-                           outp->dpcd[DPCD_RC02] &
-                                      DPCD_RC02_ENHANCED_FRAME_CAP);
-       if (ret) {
-               if (ret < 0)
-                       ERR("lnk_ctl failed with %d\n", ret);
-               return ret;
-       }
-
-       impl->lnk_pwr(outp, dp->link_nr);
-
-       /* set desired link configuration on the sink */
-       sink[0] = dp->link_bw / 27000;
-       sink[1] = dp->link_nr;
-       if (outp->dpcd[DPCD_RC02] & DPCD_RC02_ENHANCED_FRAME_CAP)
-               sink[1] |= DPCD_LC01_ENHANCED_FRAME_EN;
-
-       return nv_wraux(outp->base.edid, DPCD_LC00_LINK_BW_SET, sink, 2);
-}
-
-static void
-dp_set_training_pattern(struct dp_state *dp, u8 pattern)
-{
-       struct nvkm_output_dp_impl *impl = (void *)nv_oclass(dp->outp);
-       struct nvkm_output_dp *outp = dp->outp;
-       u8 sink_tp;
-
-       DBG("training pattern %d\n", pattern);
-       impl->pattern(outp, pattern);
-
-       nv_rdaux(outp->base.edid, DPCD_LC02, &sink_tp, 1);
-       sink_tp &= ~DPCD_LC02_TRAINING_PATTERN_SET;
-       sink_tp |= pattern;
-       nv_wraux(outp->base.edid, DPCD_LC02, &sink_tp, 1);
-}
-
-static int
-dp_link_train_commit(struct dp_state *dp, bool pc)
-{
-       struct nvkm_output_dp_impl *impl = (void *)nv_oclass(dp->outp);
-       struct nvkm_output_dp *outp = dp->outp;
-       int ret, i;
-
-       for (i = 0; i < dp->link_nr; i++) {
-               u8 lane = (dp->stat[4 + (i >> 1)] >> ((i & 1) * 4)) & 0xf;
-               u8 lpc2 = (dp->pc2stat >> (i * 2)) & 0x3;
-               u8 lpre = (lane & 0x0c) >> 2;
-               u8 lvsw = (lane & 0x03) >> 0;
-               u8 hivs = 3 - lpre;
-               u8 hipe = 3;
-               u8 hipc = 3;
-
-               if (lpc2 >= hipc)
-                       lpc2 = hipc | DPCD_LC0F_LANE0_MAX_POST_CURSOR2_REACHED;
-               if (lpre >= hipe) {
-                       lpre = hipe | DPCD_LC03_MAX_SWING_REACHED; /* yes. */
-                       lvsw = hivs = 3 - (lpre & 3);
-               } else
-               if (lvsw >= hivs) {
-                       lvsw = hivs | DPCD_LC03_MAX_SWING_REACHED;
-               }
-
-               dp->conf[i] = (lpre << 3) | lvsw;
-               dp->pc2conf[i >> 1] |= lpc2 << ((i & 1) * 4);
-
-               DBG("config lane %d %02x %02x\n", i, dp->conf[i], lpc2);
-               impl->drv_ctl(outp, i, lvsw & 3, lpre & 3, lpc2 & 3);
-       }
-
-       ret = nv_wraux(outp->base.edid, DPCD_LC03(0), dp->conf, 4);
-       if (ret)
-               return ret;
-
-       if (pc) {
-               ret = nv_wraux(outp->base.edid, DPCD_LC0F, dp->pc2conf, 2);
-               if (ret)
-                       return ret;
-       }
-
-       return 0;
-}
-
-static int
-dp_link_train_update(struct dp_state *dp, bool pc, u32 delay)
-{
-       struct nvkm_output_dp *outp = dp->outp;
-       int ret;
-
-       if (outp->dpcd[DPCD_RC0E_AUX_RD_INTERVAL])
-               mdelay(outp->dpcd[DPCD_RC0E_AUX_RD_INTERVAL] * 4);
-       else
-               udelay(delay);
-
-       ret = nv_rdaux(outp->base.edid, DPCD_LS02, dp->stat, 6);
-       if (ret)
-               return ret;
-
-       if (pc) {
-               ret = nv_rdaux(outp->base.edid, DPCD_LS0C, &dp->pc2stat, 1);
-               if (ret)
-                       dp->pc2stat = 0x00;
-               DBG("status %6ph pc2 %02x\n", dp->stat, dp->pc2stat);
-       } else {
-               DBG("status %6ph\n", dp->stat);
-       }
-
-       return 0;
-}
-
-static int
-dp_link_train_cr(struct dp_state *dp)
-{
-       bool cr_done = false, abort = false;
-       int voltage = dp->conf[0] & DPCD_LC03_VOLTAGE_SWING_SET;
-       int tries = 0, i;
-
-       dp_set_training_pattern(dp, 1);
-
-       do {
-               if (dp_link_train_commit(dp, false) ||
-                   dp_link_train_update(dp, false, 100))
-                       break;
-
-               cr_done = true;
-               for (i = 0; i < dp->link_nr; i++) {
-                       u8 lane = (dp->stat[i >> 1] >> ((i & 1) * 4)) & 0xf;
-                       if (!(lane & DPCD_LS02_LANE0_CR_DONE)) {
-                               cr_done = false;
-                               if (dp->conf[i] & DPCD_LC03_MAX_SWING_REACHED)
-                                       abort = true;
-                               break;
-                       }
-               }
-
-               if ((dp->conf[0] & DPCD_LC03_VOLTAGE_SWING_SET) != voltage) {
-                       voltage = dp->conf[0] & DPCD_LC03_VOLTAGE_SWING_SET;
-                       tries = 0;
-               }
-       } while (!cr_done && !abort && ++tries < 5);
-
-       return cr_done ? 0 : -1;
-}
-
-static int
-dp_link_train_eq(struct dp_state *dp)
-{
-       struct nvkm_output_dp *outp = dp->outp;
-       bool eq_done = false, cr_done = true;
-       int tries = 0, i;
-
-       if (outp->dpcd[2] & DPCD_RC02_TPS3_SUPPORTED)
-               dp_set_training_pattern(dp, 3);
-       else
-               dp_set_training_pattern(dp, 2);
-
-       do {
-               if ((tries &&
-                   dp_link_train_commit(dp, dp->pc2)) ||
-                   dp_link_train_update(dp, dp->pc2, 400))
-                       break;
-
-               eq_done = !!(dp->stat[2] & DPCD_LS04_INTERLANE_ALIGN_DONE);
-               for (i = 0; i < dp->link_nr && eq_done; i++) {
-                       u8 lane = (dp->stat[i >> 1] >> ((i & 1) * 4)) & 0xf;
-                       if (!(lane & DPCD_LS02_LANE0_CR_DONE))
-                               cr_done = false;
-                       if (!(lane & DPCD_LS02_LANE0_CHANNEL_EQ_DONE) ||
-                           !(lane & DPCD_LS02_LANE0_SYMBOL_LOCKED))
-                               eq_done = false;
-               }
-       } while (!eq_done && cr_done && ++tries <= 5);
-
-       return eq_done ? 0 : -1;
-}
-
-static void
-dp_link_train_init(struct dp_state *dp, bool spread)
-{
-       struct nvkm_output_dp *outp = dp->outp;
-       struct nouveau_disp *disp = nouveau_disp(outp);
-       struct nouveau_bios *bios = nouveau_bios(disp);
-       struct nvbios_init init = {
-               .subdev = nv_subdev(disp),
-               .bios = bios,
-               .outp = &outp->base.info,
-               .crtc = -1,
-               .execute = 1,
-       };
-
-       /* set desired spread */
-       if (spread)
-               init.offset = outp->info.script[2];
-       else
-               init.offset = outp->info.script[3];
-       nvbios_exec(&init);
-
-       /* pre-train script */
-       init.offset = outp->info.script[0];
-       nvbios_exec(&init);
-}
-
-static void
-dp_link_train_fini(struct dp_state *dp)
-{
-       struct nvkm_output_dp *outp = dp->outp;
-       struct nouveau_disp *disp = nouveau_disp(outp);
-       struct nouveau_bios *bios = nouveau_bios(disp);
-       struct nvbios_init init = {
-               .subdev = nv_subdev(disp),
-               .bios = bios,
-               .outp = &outp->base.info,
-               .crtc = -1,
-               .execute = 1,
-       };
-
-       /* post-train script */
-       init.offset = outp->info.script[1],
-       nvbios_exec(&init);
-}
-
-static const struct dp_rates {
-       u32 rate;
-       u8  bw;
-       u8  nr;
-} nouveau_dp_rates[] = {
-       { 2160000, 0x14, 4 },
-       { 1080000, 0x0a, 4 },
-       { 1080000, 0x14, 2 },
-       {  648000, 0x06, 4 },
-       {  540000, 0x0a, 2 },
-       {  540000, 0x14, 1 },
-       {  324000, 0x06, 2 },
-       {  270000, 0x0a, 1 },
-       {  162000, 0x06, 1 },
-       {}
-};
-
-void
-nouveau_dp_train(struct work_struct *w)
-{
-       struct nvkm_output_dp *outp = container_of(w, typeof(*outp), lt.work);
-       struct nv50_disp_priv *priv = (void *)nouveau_disp(outp);
-       const struct dp_rates *cfg = nouveau_dp_rates;
-       struct dp_state _dp = {
-               .outp = outp,
-       }, *dp = &_dp;
-       u32 datarate = 0;
-       int ret;
-
-       if (!outp->base.info.location && priv->sor.magic)
-               priv->sor.magic(&outp->base);
-
-       /* bring capabilities within encoder limits */
-       if (nv_mclass(priv) < GF110_DISP)
-               outp->dpcd[2] &= ~DPCD_RC02_TPS3_SUPPORTED;
-       if ((outp->dpcd[2] & 0x1f) > outp->base.info.dpconf.link_nr) {
-               outp->dpcd[2] &= ~DPCD_RC02_MAX_LANE_COUNT;
-               outp->dpcd[2] |= outp->base.info.dpconf.link_nr;
-       }
-       if (outp->dpcd[1] > outp->base.info.dpconf.link_bw)
-               outp->dpcd[1] = outp->base.info.dpconf.link_bw;
-       dp->pc2 = outp->dpcd[2] & DPCD_RC02_TPS3_SUPPORTED;
-
-       /* restrict link config to the lowest required rate, if requested */
-       if (datarate) {
-               datarate = (datarate / 8) * 10; /* 8B/10B coding overhead */
-               while (cfg[1].rate >= datarate)
-                       cfg++;
-       }
-       cfg--;
-
-       /* disable link interrupt handling during link training */
-       nvkm_notify_put(&outp->irq);
-
-       /* enable down-spreading and execute pre-train script from vbios */
-       dp_link_train_init(dp, outp->dpcd[3] & 0x01);
-
-       while (ret = -EIO, (++cfg)->rate) {
-               /* select next configuration supported by encoder and sink */
-               while (cfg->nr > (outp->dpcd[2] & DPCD_RC02_MAX_LANE_COUNT) ||
-                      cfg->bw > (outp->dpcd[DPCD_RC01_MAX_LINK_RATE]))
-                       cfg++;
-               dp->link_bw = cfg->bw * 27000;
-               dp->link_nr = cfg->nr;
-
-               /* program selected link configuration */
-               ret = dp_set_link_config(dp);
-               if (ret == 0) {
-                       /* attempt to train the link at this configuration */
-                       memset(dp->stat, 0x00, sizeof(dp->stat));
-                       if (!dp_link_train_cr(dp) &&
-                           !dp_link_train_eq(dp))
-                               break;
-               } else
-               if (ret) {
-                       /* dp_set_link_config() handled training, or
-                        * we failed to communicate with the sink.
-                        */
-                       break;
-               }
-       }
-
-       /* finish link training and execute post-train script from vbios */
-       dp_set_training_pattern(dp, 0);
-       if (ret < 0)
-               ERR("link training failed\n");
-
-       dp_link_train_fini(dp);
-
-       /* signal completion and enable link interrupt handling */
-       DBG("training complete\n");
-       atomic_set(&outp->lt.done, 1);
-       wake_up(&outp->lt.wait);
-       nvkm_notify_get(&outp->irq);
-}
diff --git a/drivers/gpu/drm/nouveau/core/engine/disp/dport.h b/drivers/gpu/drm/nouveau/core/engine/disp/dport.h
deleted file mode 100644 (file)
index 5628d2d..0000000
+++ /dev/null
@@ -1,75 +0,0 @@
-#ifndef __NVKM_DISP_DPORT_H__
-#define __NVKM_DISP_DPORT_H__
-
-/* DPCD Receiver Capabilities */
-#define DPCD_RC00_DPCD_REV                                              0x00000
-#define DPCD_RC01_MAX_LINK_RATE                                         0x00001
-#define DPCD_RC02                                                       0x00002
-#define DPCD_RC02_ENHANCED_FRAME_CAP                                       0x80
-#define DPCD_RC02_TPS3_SUPPORTED                                           0x40
-#define DPCD_RC02_MAX_LANE_COUNT                                           0x1f
-#define DPCD_RC03                                                       0x00003
-#define DPCD_RC03_MAX_DOWNSPREAD                                           0x01
-#define DPCD_RC0E_AUX_RD_INTERVAL                                       0x0000e
-
-/* DPCD Link Configuration */
-#define DPCD_LC00_LINK_BW_SET                                           0x00100
-#define DPCD_LC01                                                       0x00101
-#define DPCD_LC01_ENHANCED_FRAME_EN                                        0x80
-#define DPCD_LC01_LANE_COUNT_SET                                           0x1f
-#define DPCD_LC02                                                       0x00102
-#define DPCD_LC02_TRAINING_PATTERN_SET                                     0x03
-#define DPCD_LC03(l)                                            ((l) +  0x00103)
-#define DPCD_LC03_MAX_PRE_EMPHASIS_REACHED                                 0x20
-#define DPCD_LC03_PRE_EMPHASIS_SET                                         0x18
-#define DPCD_LC03_MAX_SWING_REACHED                                        0x04
-#define DPCD_LC03_VOLTAGE_SWING_SET                                        0x03
-#define DPCD_LC0F                                                       0x0010f
-#define DPCD_LC0F_LANE1_MAX_POST_CURSOR2_REACHED                           0x40
-#define DPCD_LC0F_LANE1_POST_CURSOR2_SET                                   0x30
-#define DPCD_LC0F_LANE0_MAX_POST_CURSOR2_REACHED                           0x04
-#define DPCD_LC0F_LANE0_POST_CURSOR2_SET                                   0x03
-#define DPCD_LC10                                                       0x00110
-#define DPCD_LC10_LANE3_MAX_POST_CURSOR2_REACHED                           0x40
-#define DPCD_LC10_LANE3_POST_CURSOR2_SET                                   0x30
-#define DPCD_LC10_LANE2_MAX_POST_CURSOR2_REACHED                           0x04
-#define DPCD_LC10_LANE2_POST_CURSOR2_SET                                   0x03
-
-/* DPCD Link/Sink Status */
-#define DPCD_LS02                                                       0x00202
-#define DPCD_LS02_LANE1_SYMBOL_LOCKED                                      0x40
-#define DPCD_LS02_LANE1_CHANNEL_EQ_DONE                                    0x20
-#define DPCD_LS02_LANE1_CR_DONE                                            0x10
-#define DPCD_LS02_LANE0_SYMBOL_LOCKED                                      0x04
-#define DPCD_LS02_LANE0_CHANNEL_EQ_DONE                                    0x02
-#define DPCD_LS02_LANE0_CR_DONE                                            0x01
-#define DPCD_LS03                                                       0x00203
-#define DPCD_LS03_LANE3_SYMBOL_LOCKED                                      0x40
-#define DPCD_LS03_LANE3_CHANNEL_EQ_DONE                                    0x20
-#define DPCD_LS03_LANE3_CR_DONE                                            0x10
-#define DPCD_LS03_LANE2_SYMBOL_LOCKED                                      0x04
-#define DPCD_LS03_LANE2_CHANNEL_EQ_DONE                                    0x02
-#define DPCD_LS03_LANE2_CR_DONE                                            0x01
-#define DPCD_LS04                                                       0x00204
-#define DPCD_LS04_LINK_STATUS_UPDATED                                      0x80
-#define DPCD_LS04_DOWNSTREAM_PORT_STATUS_CHANGED                           0x40
-#define DPCD_LS04_INTERLANE_ALIGN_DONE                                     0x01
-#define DPCD_LS06                                                       0x00206
-#define DPCD_LS06_LANE1_PRE_EMPHASIS                                       0xc0
-#define DPCD_LS06_LANE1_VOLTAGE_SWING                                      0x30
-#define DPCD_LS06_LANE0_PRE_EMPHASIS                                       0x0c
-#define DPCD_LS06_LANE0_VOLTAGE_SWING                                      0x03
-#define DPCD_LS07                                                       0x00207
-#define DPCD_LS07_LANE3_PRE_EMPHASIS                                       0xc0
-#define DPCD_LS07_LANE3_VOLTAGE_SWING                                      0x30
-#define DPCD_LS07_LANE2_PRE_EMPHASIS                                       0x0c
-#define DPCD_LS07_LANE2_VOLTAGE_SWING                                      0x03
-#define DPCD_LS0C                                                       0x0020c
-#define DPCD_LS0C_LANE3_POST_CURSOR2                                       0xc0
-#define DPCD_LS0C_LANE2_POST_CURSOR2                                       0x30
-#define DPCD_LS0C_LANE1_POST_CURSOR2                                       0x0c
-#define DPCD_LS0C_LANE0_POST_CURSOR2                                       0x03
-
-void nouveau_dp_train(struct work_struct *);
-
-#endif
diff --git a/drivers/gpu/drm/nouveau/core/engine/disp/gm107.c b/drivers/gpu/drm/nouveau/core/engine/disp/gm107.c
deleted file mode 100644 (file)
index e2ad054..0000000
+++ /dev/null
@@ -1,107 +0,0 @@
-/*
- * Copyright 2012 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 <engine/software.h>
-#include <engine/disp.h>
-
-#include <nvif/class.h>
-
-#include "nv50.h"
-
-/*******************************************************************************
- * Base display object
- ******************************************************************************/
-
-static struct nouveau_oclass
-gm107_disp_sclass[] = {
-       { GM107_DISP_CORE_CHANNEL_DMA, &nvd0_disp_core_ofuncs.base },
-       { GK110_DISP_BASE_CHANNEL_DMA, &nvd0_disp_base_ofuncs.base },
-       { GK104_DISP_OVERLAY_CONTROL_DMA, &nvd0_disp_ovly_ofuncs.base },
-       { GK104_DISP_OVERLAY, &nvd0_disp_oimm_ofuncs.base },
-       { GK104_DISP_CURSOR, &nvd0_disp_curs_ofuncs.base },
-       {}
-};
-
-static struct nouveau_oclass
-gm107_disp_main_oclass[] = {
-       { GM107_DISP, &nvd0_disp_main_ofuncs },
-       {}
-};
-
-/*******************************************************************************
- * Display engine implementation
- ******************************************************************************/
-
-static int
-gm107_disp_ctor(struct nouveau_object *parent, struct nouveau_object *engine,
-              struct nouveau_oclass *oclass, void *data, u32 size,
-              struct nouveau_object **pobject)
-{
-       struct nv50_disp_priv *priv;
-       int heads = nv_rd32(parent, 0x022448);
-       int ret;
-
-       ret = nouveau_disp_create(parent, engine, oclass, heads,
-                                 "PDISP", "display", &priv);
-       *pobject = nv_object(priv);
-       if (ret)
-               return ret;
-
-       ret = nvkm_event_init(&nvd0_disp_chan_uevent, 1, 17, &priv->uevent);
-       if (ret)
-               return ret;
-
-       nv_engine(priv)->sclass = gm107_disp_main_oclass;
-       nv_engine(priv)->cclass = &nv50_disp_cclass;
-       nv_subdev(priv)->intr = nvd0_disp_intr;
-       INIT_WORK(&priv->supervisor, nvd0_disp_intr_supervisor);
-       priv->sclass = gm107_disp_sclass;
-       priv->head.nr = heads;
-       priv->dac.nr = 3;
-       priv->sor.nr = 4;
-       priv->dac.power = nv50_dac_power;
-       priv->dac.sense = nv50_dac_sense;
-       priv->sor.power = nv50_sor_power;
-       priv->sor.hda_eld = nvd0_hda_eld;
-       priv->sor.hdmi = nve0_hdmi_ctrl;
-       return 0;
-}
-
-struct nouveau_oclass *
-gm107_disp_oclass = &(struct nv50_disp_impl) {
-       .base.base.handle = NV_ENGINE(DISP, 0x07),
-       .base.base.ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = gm107_disp_ctor,
-               .dtor = _nouveau_disp_dtor,
-               .init = _nouveau_disp_init,
-               .fini = _nouveau_disp_fini,
-       },
-       .base.vblank = &nvd0_disp_vblank_func,
-       .base.outp =  nvd0_disp_outp_sclass,
-       .mthd.core = &nve0_disp_core_mthd_chan,
-       .mthd.base = &nvd0_disp_base_mthd_chan,
-       .mthd.ovly = &nve0_disp_ovly_mthd_chan,
-       .mthd.prev = -0x020000,
-       .head.scanoutpos = nvd0_disp_main_scanoutpos,
-}.base.base;
diff --git a/drivers/gpu/drm/nouveau/core/engine/disp/gm204.c b/drivers/gpu/drm/nouveau/core/engine/disp/gm204.c
deleted file mode 100644 (file)
index 672ded7..0000000
+++ /dev/null
@@ -1,114 +0,0 @@
-/*
- * Copyright 2012 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 <engine/software.h>
-#include <engine/disp.h>
-
-#include <nvif/class.h>
-
-#include "nv50.h"
-
-/*******************************************************************************
- * Base display object
- ******************************************************************************/
-
-static struct nouveau_oclass
-gm204_disp_sclass[] = {
-       { GM204_DISP_CORE_CHANNEL_DMA, &nvd0_disp_core_ofuncs.base },
-       { GK110_DISP_BASE_CHANNEL_DMA, &nvd0_disp_base_ofuncs.base },
-       { GK104_DISP_OVERLAY_CONTROL_DMA, &nvd0_disp_ovly_ofuncs.base },
-       { GK104_DISP_OVERLAY, &nvd0_disp_oimm_ofuncs.base },
-       { GK104_DISP_CURSOR, &nvd0_disp_curs_ofuncs.base },
-       {}
-};
-
-static struct nouveau_oclass
-gm204_disp_main_oclass[] = {
-       { GM204_DISP, &nvd0_disp_main_ofuncs },
-       {}
-};
-
-/*******************************************************************************
- * Display engine implementation
- ******************************************************************************/
-
-static int
-gm204_disp_ctor(struct nouveau_object *parent, struct nouveau_object *engine,
-              struct nouveau_oclass *oclass, void *data, u32 size,
-              struct nouveau_object **pobject)
-{
-       struct nv50_disp_priv *priv;
-       int heads = nv_rd32(parent, 0x022448);
-       int ret;
-
-       ret = nouveau_disp_create(parent, engine, oclass, heads,
-                                 "PDISP", "display", &priv);
-       *pobject = nv_object(priv);
-       if (ret)
-               return ret;
-
-       ret = nvkm_event_init(&nvd0_disp_chan_uevent, 1, 17, &priv->uevent);
-       if (ret)
-               return ret;
-
-       nv_engine(priv)->sclass = gm204_disp_main_oclass;
-       nv_engine(priv)->cclass = &nv50_disp_cclass;
-       nv_subdev(priv)->intr = nvd0_disp_intr;
-       INIT_WORK(&priv->supervisor, nvd0_disp_intr_supervisor);
-       priv->sclass = gm204_disp_sclass;
-       priv->head.nr = heads;
-       priv->dac.nr = 3;
-       priv->sor.nr = 4;
-       priv->dac.power = nv50_dac_power;
-       priv->dac.sense = nv50_dac_sense;
-       priv->sor.power = nv50_sor_power;
-       priv->sor.hda_eld = nvd0_hda_eld;
-       priv->sor.hdmi = nvd0_hdmi_ctrl;
-       priv->sor.magic = gm204_sor_magic;
-       return 0;
-}
-
-struct nouveau_oclass *
-gm204_disp_outp_sclass[] = {
-       &gm204_sor_dp_impl.base.base,
-       NULL
-};
-
-struct nouveau_oclass *
-gm204_disp_oclass = &(struct nv50_disp_impl) {
-       .base.base.handle = NV_ENGINE(DISP, 0x07),
-       .base.base.ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = gm204_disp_ctor,
-               .dtor = _nouveau_disp_dtor,
-               .init = _nouveau_disp_init,
-               .fini = _nouveau_disp_fini,
-       },
-       .base.vblank = &nvd0_disp_vblank_func,
-       .base.outp =  gm204_disp_outp_sclass,
-       .mthd.core = &nve0_disp_core_mthd_chan,
-       .mthd.base = &nvd0_disp_base_mthd_chan,
-       .mthd.ovly = &nve0_disp_ovly_mthd_chan,
-       .mthd.prev = -0x020000,
-       .head.scanoutpos = nvd0_disp_main_scanoutpos,
-}.base.base;
diff --git a/drivers/gpu/drm/nouveau/core/engine/disp/hdanva3.c b/drivers/gpu/drm/nouveau/core/engine/disp/hdanva3.c
deleted file mode 100644 (file)
index fe9ef58..0000000
+++ /dev/null
@@ -1,69 +0,0 @@
-/*
- * Copyright 2012 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 <core/client.h>
-#include <nvif/unpack.h>
-#include <nvif/class.h>
-
-#include <subdev/timer.h>
-
-#include "nv50.h"
-
-int
-nva3_hda_eld(NV50_DISP_MTHD_V1)
-{
-       union {
-               struct nv50_disp_sor_hda_eld_v0 v0;
-       } *args = data;
-       const u32 soff = outp->or * 0x800;
-       int ret, i;
-
-       nv_ioctl(object, "disp sor hda eld size %d\n", size);
-       if (nvif_unpack(args->v0, 0, 0, true)) {
-               nv_ioctl(object, "disp sor hda eld vers %d\n", args->v0.version);
-               if (size > 0x60)
-                       return -E2BIG;
-       } else
-               return ret;
-
-       if (size && args->v0.data[0]) {
-               if (outp->info.type == DCB_OUTPUT_DP) {
-                       nv_mask(priv, 0x61c1e0 + soff, 0x8000000d, 0x80000001);
-                       nv_wait(priv, 0x61c1e0 + soff, 0x80000000, 0x00000000);
-               }
-               for (i = 0; i < size; i++)
-                       nv_wr32(priv, 0x61c440 + soff, (i << 8) | args->v0.data[0]);
-               for (; i < 0x60; i++)
-                       nv_wr32(priv, 0x61c440 + soff, (i << 8));
-               nv_mask(priv, 0x61c448 + soff, 0x80000003, 0x80000003);
-       } else {
-               if (outp->info.type == DCB_OUTPUT_DP) {
-                       nv_mask(priv, 0x61c1e0 + soff, 0x80000001, 0x80000000);
-                       nv_wait(priv, 0x61c1e0 + soff, 0x80000000, 0x00000000);
-               }
-               nv_mask(priv, 0x61c448 + soff, 0x80000003, 0x80000000 | !!size);
-       }
-
-       return 0;
-}
diff --git a/drivers/gpu/drm/nouveau/core/engine/disp/hdanvd0.c b/drivers/gpu/drm/nouveau/core/engine/disp/hdanvd0.c
deleted file mode 100644 (file)
index 1d4e843..0000000
+++ /dev/null
@@ -1,71 +0,0 @@
-/*
- * Copyright 2012 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 <core/client.h>
-#include <nvif/unpack.h>
-#include <nvif/class.h>
-
-#include <subdev/timer.h>
-
-#include "nv50.h"
-
-int
-nvd0_hda_eld(NV50_DISP_MTHD_V1)
-{
-       union {
-               struct nv50_disp_sor_hda_eld_v0 v0;
-       } *args = data;
-       const u32 soff = outp->or * 0x030;
-       const u32 hoff = head * 0x800;
-       int ret, i;
-
-       nv_ioctl(object, "disp sor hda eld size %d\n", size);
-       if (nvif_unpack(args->v0, 0, 0, true)) {
-               nv_ioctl(object, "disp sor hda eld vers %d\n", args->v0.version);
-               if (size > 0x60)
-                       return -E2BIG;
-       } else
-               return ret;
-
-       if (size && args->v0.data[0]) {
-               if (outp->info.type == DCB_OUTPUT_DP) {
-                       nv_mask(priv, 0x616618 + hoff, 0x8000000c, 0x80000001);
-                       nv_wait(priv, 0x616618 + hoff, 0x80000000, 0x00000000);
-               }
-               nv_mask(priv, 0x616548 + hoff, 0x00000070, 0x00000000);
-               for (i = 0; i < size; i++)
-                       nv_wr32(priv, 0x10ec00 + soff, (i << 8) | args->v0.data[i]);
-               for (; i < 0x60; i++)
-                       nv_wr32(priv, 0x10ec00 + soff, (i << 8));
-               nv_mask(priv, 0x10ec10 + soff, 0x80000003, 0x80000003);
-       } else {
-               if (outp->info.type == DCB_OUTPUT_DP) {
-                       nv_mask(priv, 0x616618 + hoff, 0x80000001, 0x80000000);
-                       nv_wait(priv, 0x616618 + hoff, 0x80000000, 0x00000000);
-               }
-               nv_mask(priv, 0x10ec10 + soff, 0x80000003, 0x80000000 | !!size);
-       }
-
-       return 0;
-}
diff --git a/drivers/gpu/drm/nouveau/core/engine/disp/hdminv84.c b/drivers/gpu/drm/nouveau/core/engine/disp/hdminv84.c
deleted file mode 100644 (file)
index fa276de..0000000
+++ /dev/null
@@ -1,91 +0,0 @@
-/*
- * Copyright 2012 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 <core/client.h>
-#include <nvif/unpack.h>
-#include <nvif/class.h>
-
-#include "nv50.h"
-
-int
-nv84_hdmi_ctrl(NV50_DISP_MTHD_V1)
-{
-       const u32 hoff = (head * 0x800);
-       union {
-               struct nv50_disp_sor_hdmi_pwr_v0 v0;
-       } *args = data;
-       u32 ctrl;
-       int ret;
-
-       nv_ioctl(object, "disp sor hdmi ctrl size %d\n", size);
-       if (nvif_unpack(args->v0, 0, 0, false)) {
-               nv_ioctl(object, "disp sor hdmi ctrl vers %d state %d "
-                                "max_ac_packet %d rekey %d\n",
-                        args->v0.version, args->v0.state,
-                        args->v0.max_ac_packet, args->v0.rekey);
-               if (args->v0.max_ac_packet > 0x1f || args->v0.rekey > 0x7f)
-                       return -EINVAL;
-               ctrl  = 0x40000000 * !!args->v0.state;
-               ctrl |= args->v0.max_ac_packet << 16;
-               ctrl |= args->v0.rekey;
-               ctrl |= 0x1f000000; /* ??? */
-       } else
-               return ret;
-
-       if (!(ctrl & 0x40000000)) {
-               nv_mask(priv, 0x6165a4 + hoff, 0x40000000, 0x00000000);
-               nv_mask(priv, 0x616520 + hoff, 0x00000001, 0x00000000);
-               nv_mask(priv, 0x616500 + hoff, 0x00000001, 0x00000000);
-               return 0;
-       }
-
-       /* AVI InfoFrame */
-       nv_mask(priv, 0x616520 + hoff, 0x00000001, 0x00000000);
-       nv_wr32(priv, 0x616528 + hoff, 0x000d0282);
-       nv_wr32(priv, 0x61652c + hoff, 0x0000006f);
-       nv_wr32(priv, 0x616530 + hoff, 0x00000000);
-       nv_wr32(priv, 0x616534 + hoff, 0x00000000);
-       nv_wr32(priv, 0x616538 + hoff, 0x00000000);
-       nv_mask(priv, 0x616520 + hoff, 0x00000001, 0x00000001);
-
-       /* Audio InfoFrame */
-       nv_mask(priv, 0x616500 + hoff, 0x00000001, 0x00000000);
-       nv_wr32(priv, 0x616508 + hoff, 0x000a0184);
-       nv_wr32(priv, 0x61650c + hoff, 0x00000071);
-       nv_wr32(priv, 0x616510 + hoff, 0x00000000);
-       nv_mask(priv, 0x616500 + hoff, 0x00000001, 0x00000001);
-
-       nv_mask(priv, 0x6165d0 + hoff, 0x00070001, 0x00010001); /* SPARE, HW_CTS */
-       nv_mask(priv, 0x616568 + hoff, 0x00010101, 0x00000000); /* ACR_CTRL, ?? */
-       nv_mask(priv, 0x616578 + hoff, 0x80000000, 0x80000000); /* ACR_0441_ENABLE */
-
-       /* ??? */
-       nv_mask(priv, 0x61733c, 0x00100000, 0x00100000); /* RESETF */
-       nv_mask(priv, 0x61733c, 0x10000000, 0x10000000); /* LOOKUP_EN */
-       nv_mask(priv, 0x61733c, 0x00100000, 0x00000000); /* !RESETF */
-
-       /* HDMI_CTRL */
-       nv_mask(priv, 0x6165a4 + hoff, 0x5f1f007f, ctrl);
-       return 0;
-}
diff --git a/drivers/gpu/drm/nouveau/core/engine/disp/hdminva3.c b/drivers/gpu/drm/nouveau/core/engine/disp/hdminva3.c
deleted file mode 100644 (file)
index 57eeed1..0000000
+++ /dev/null
@@ -1,91 +0,0 @@
-/*
- * Copyright 2012 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 <core/client.h>
-#include <nvif/unpack.h>
-#include <nvif/class.h>
-
-#include "nv50.h"
-
-int
-nva3_hdmi_ctrl(NV50_DISP_MTHD_V1)
-{
-       const u32 soff = outp->or * 0x800;
-       union {
-               struct nv50_disp_sor_hdmi_pwr_v0 v0;
-       } *args = data;
-       u32 ctrl;
-       int ret;
-
-       nv_ioctl(object, "disp sor hdmi ctrl size %d\n", size);
-       if (nvif_unpack(args->v0, 0, 0, false)) {
-               nv_ioctl(object, "disp sor hdmi ctrl vers %d state %d "
-                                "max_ac_packet %d rekey %d\n",
-                        args->v0.version, args->v0.state,
-                        args->v0.max_ac_packet, args->v0.rekey);
-               if (args->v0.max_ac_packet > 0x1f || args->v0.rekey > 0x7f)
-                       return -EINVAL;
-               ctrl  = 0x40000000 * !!args->v0.state;
-               ctrl |= args->v0.max_ac_packet << 16;
-               ctrl |= args->v0.rekey;
-               ctrl |= 0x1f000000; /* ??? */
-       } else
-               return ret;
-
-       if (!(ctrl & 0x40000000)) {
-               nv_mask(priv, 0x61c5a4 + soff, 0x40000000, 0x00000000);
-               nv_mask(priv, 0x61c520 + soff, 0x00000001, 0x00000000);
-               nv_mask(priv, 0x61c500 + soff, 0x00000001, 0x00000000);
-               return 0;
-       }
-
-       /* AVI InfoFrame */
-       nv_mask(priv, 0x61c520 + soff, 0x00000001, 0x00000000);
-       nv_wr32(priv, 0x61c528 + soff, 0x000d0282);
-       nv_wr32(priv, 0x61c52c + soff, 0x0000006f);
-       nv_wr32(priv, 0x61c530 + soff, 0x00000000);
-       nv_wr32(priv, 0x61c534 + soff, 0x00000000);
-       nv_wr32(priv, 0x61c538 + soff, 0x00000000);
-       nv_mask(priv, 0x61c520 + soff, 0x00000001, 0x00000001);
-
-       /* Audio InfoFrame */
-       nv_mask(priv, 0x61c500 + soff, 0x00000001, 0x00000000);
-       nv_wr32(priv, 0x61c508 + soff, 0x000a0184);
-       nv_wr32(priv, 0x61c50c + soff, 0x00000071);
-       nv_wr32(priv, 0x61c510 + soff, 0x00000000);
-       nv_mask(priv, 0x61c500 + soff, 0x00000001, 0x00000001);
-
-       nv_mask(priv, 0x61c5d0 + soff, 0x00070001, 0x00010001); /* SPARE, HW_CTS */
-       nv_mask(priv, 0x61c568 + soff, 0x00010101, 0x00000000); /* ACR_CTRL, ?? */
-       nv_mask(priv, 0x61c578 + soff, 0x80000000, 0x80000000); /* ACR_0441_ENABLE */
-
-       /* ??? */
-       nv_mask(priv, 0x61733c, 0x00100000, 0x00100000); /* RESETF */
-       nv_mask(priv, 0x61733c, 0x10000000, 0x10000000); /* LOOKUP_EN */
-       nv_mask(priv, 0x61733c, 0x00100000, 0x00000000); /* !RESETF */
-
-       /* HDMI_CTRL */
-       nv_mask(priv, 0x61c5a4 + soff, 0x5f1f007f, ctrl);
-       return 0;
-}
diff --git a/drivers/gpu/drm/nouveau/core/engine/disp/hdminvd0.c b/drivers/gpu/drm/nouveau/core/engine/disp/hdminvd0.c
deleted file mode 100644 (file)
index bac4fc4..0000000
+++ /dev/null
@@ -1,79 +0,0 @@
-/*
- * Copyright 2012 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 <core/client.h>
-#include <nvif/unpack.h>
-#include <nvif/class.h>
-
-#include "nv50.h"
-
-int
-nvd0_hdmi_ctrl(NV50_DISP_MTHD_V1)
-{
-       const u32 hoff = (head * 0x800);
-       union {
-               struct nv50_disp_sor_hdmi_pwr_v0 v0;
-       } *args = data;
-       u32 ctrl;
-       int ret;
-
-       nv_ioctl(object, "disp sor hdmi ctrl size %d\n", size);
-       if (nvif_unpack(args->v0, 0, 0, false)) {
-               nv_ioctl(object, "disp sor hdmi ctrl vers %d state %d "
-                                "max_ac_packet %d rekey %d\n",
-                        args->v0.version, args->v0.state,
-                        args->v0.max_ac_packet, args->v0.rekey);
-               if (args->v0.max_ac_packet > 0x1f || args->v0.rekey > 0x7f)
-                       return -EINVAL;
-               ctrl  = 0x40000000 * !!args->v0.state;
-               ctrl |= args->v0.max_ac_packet << 16;
-               ctrl |= args->v0.rekey;
-       } else
-               return ret;
-
-       if (!(ctrl & 0x40000000)) {
-               nv_mask(priv, 0x616798 + hoff, 0x40000000, 0x00000000);
-               nv_mask(priv, 0x6167a4 + hoff, 0x00000001, 0x00000000);
-               nv_mask(priv, 0x616714 + hoff, 0x00000001, 0x00000000);
-               return 0;
-       }
-
-       /* AVI InfoFrame */
-       nv_mask(priv, 0x616714 + hoff, 0x00000001, 0x00000000);
-       nv_wr32(priv, 0x61671c + hoff, 0x000d0282);
-       nv_wr32(priv, 0x616720 + hoff, 0x0000006f);
-       nv_wr32(priv, 0x616724 + hoff, 0x00000000);
-       nv_wr32(priv, 0x616728 + hoff, 0x00000000);
-       nv_wr32(priv, 0x61672c + hoff, 0x00000000);
-       nv_mask(priv, 0x616714 + hoff, 0x00000001, 0x00000001);
-
-       /* ??? InfoFrame? */
-       nv_mask(priv, 0x6167a4 + hoff, 0x00000001, 0x00000000);
-       nv_wr32(priv, 0x6167ac + hoff, 0x00000010);
-       nv_mask(priv, 0x6167a4 + hoff, 0x00000001, 0x00000001);
-
-       /* HDMI_CTRL */
-       nv_mask(priv, 0x616798 + hoff, 0x401f007f, ctrl);
-       return 0;
-}
diff --git a/drivers/gpu/drm/nouveau/core/engine/disp/hdminve0.c b/drivers/gpu/drm/nouveau/core/engine/disp/hdminve0.c
deleted file mode 100644 (file)
index 528d14e..0000000
+++ /dev/null
@@ -1,83 +0,0 @@
-/*
- * Copyright 2014 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 <core/client.h>
-#include <nvif/unpack.h>
-#include <nvif/class.h>
-
-#include "nv50.h"
-
-int
-nve0_hdmi_ctrl(NV50_DISP_MTHD_V1)
-{
-       const u32 hoff = (head * 0x800);
-       const u32 hdmi = (head * 0x400);
-       union {
-               struct nv50_disp_sor_hdmi_pwr_v0 v0;
-       } *args = data;
-       u32 ctrl;
-       int ret;
-
-       nv_ioctl(object, "disp sor hdmi ctrl size %d\n", size);
-       if (nvif_unpack(args->v0, 0, 0, false)) {
-               nv_ioctl(object, "disp sor hdmi ctrl vers %d state %d "
-                                "max_ac_packet %d rekey %d\n",
-                        args->v0.version, args->v0.state,
-                        args->v0.max_ac_packet, args->v0.rekey);
-               if (args->v0.max_ac_packet > 0x1f || args->v0.rekey > 0x7f)
-                       return -EINVAL;
-               ctrl  = 0x40000000 * !!args->v0.state;
-               ctrl |= args->v0.max_ac_packet << 16;
-               ctrl |= args->v0.rekey;
-       } else
-               return ret;
-
-       if (!(ctrl & 0x40000000)) {
-               nv_mask(priv, 0x616798 + hoff, 0x40000000, 0x00000000);
-               nv_mask(priv, 0x6900c0 + hdmi, 0x00000001, 0x00000000);
-               nv_mask(priv, 0x690000 + hdmi, 0x00000001, 0x00000000);
-               return 0;
-       }
-
-       /* AVI InfoFrame */
-       nv_mask(priv, 0x690000 + hdmi, 0x00000001, 0x00000000);
-       nv_wr32(priv, 0x690008 + hdmi, 0x000d0282);
-       nv_wr32(priv, 0x69000c + hdmi, 0x0000006f);
-       nv_wr32(priv, 0x690010 + hdmi, 0x00000000);
-       nv_wr32(priv, 0x690014 + hdmi, 0x00000000);
-       nv_wr32(priv, 0x690018 + hdmi, 0x00000000);
-       nv_mask(priv, 0x690000 + hdmi, 0x00000001, 0x00000001);
-
-       /* ??? InfoFrame? */
-       nv_mask(priv, 0x6900c0 + hdmi, 0x00000001, 0x00000000);
-       nv_wr32(priv, 0x6900cc + hdmi, 0x00000010);
-       nv_mask(priv, 0x6900c0 + hdmi, 0x00000001, 0x00000001);
-
-       /* ??? */
-       nv_wr32(priv, 0x690080 + hdmi, 0x82000000);
-
-       /* HDMI_CTRL */
-       nv_mask(priv, 0x616798 + hoff, 0x401f007f, ctrl);
-       return 0;
-}
diff --git a/drivers/gpu/drm/nouveau/core/engine/disp/nv04.c b/drivers/gpu/drm/nouveau/core/engine/disp/nv04.c
deleted file mode 100644 (file)
index 366f315..0000000
+++ /dev/null
@@ -1,205 +0,0 @@
-/*
- * Copyright 2012 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 "priv.h"
-
-#include <core/client.h>
-#include <core/event.h>
-#include <nvif/unpack.h>
-#include <nvif/class.h>
-
-struct nv04_disp_priv {
-       struct nouveau_disp base;
-};
-
-static int
-nv04_disp_scanoutpos(struct nouveau_object *object, struct nv04_disp_priv *priv,
-                    void *data, u32 size, int head)
-{
-       const u32 hoff = head * 0x2000;
-       union {
-               struct nv04_disp_scanoutpos_v0 v0;
-       } *args = data;
-       u32 line;
-       int ret;
-
-       nv_ioctl(object, "disp scanoutpos size %d\n", size);
-       if (nvif_unpack(args->v0, 0, 0, false)) {
-               nv_ioctl(object, "disp scanoutpos vers %d\n", args->v0.version);
-               args->v0.vblanks = nv_rd32(priv, 0x680800 + hoff) & 0xffff;
-               args->v0.vtotal  = nv_rd32(priv, 0x680804 + hoff) & 0xffff;
-               args->v0.vblanke = args->v0.vtotal - 1;
-
-               args->v0.hblanks = nv_rd32(priv, 0x680820 + hoff) & 0xffff;
-               args->v0.htotal  = nv_rd32(priv, 0x680824 + hoff) & 0xffff;
-               args->v0.hblanke = args->v0.htotal - 1;
-
-               /*
-                * If output is vga instead of digital then vtotal/htotal is
-                * invalid so we have to give up and trigger the timestamping
-                * fallback in the drm core.
-                */
-               if (!args->v0.vtotal || !args->v0.htotal)
-                       return -ENOTSUPP;
-
-               args->v0.time[0] = ktime_to_ns(ktime_get());
-               line = nv_rd32(priv, 0x600868 + hoff);
-               args->v0.time[1] = ktime_to_ns(ktime_get());
-               args->v0.hline = (line & 0xffff0000) >> 16;
-               args->v0.vline = (line & 0x0000ffff);
-       } else
-               return ret;
-
-       return 0;
-}
-
-static int
-nv04_disp_mthd(struct nouveau_object *object, u32 mthd, void *data, u32 size)
-{
-       union {
-               struct nv04_disp_mthd_v0 v0;
-       } *args = data;
-       struct nv04_disp_priv *priv = (void *)object->engine;
-       int head, ret;
-
-       nv_ioctl(object, "disp mthd size %d\n", size);
-       if (nvif_unpack(args->v0, 0, 0, true)) {
-               nv_ioctl(object, "disp mthd vers %d mthd %02x head %d\n",
-                        args->v0.version, args->v0.method, args->v0.head);
-               mthd = args->v0.method;
-               head = args->v0.head;
-       } else
-               return ret;
-
-       if (head < 0 || head >= 2)
-               return -ENXIO;
-
-       switch (mthd) {
-       case NV04_DISP_SCANOUTPOS:
-               return nv04_disp_scanoutpos(object, priv, data, size, head);
-       default:
-               break;
-       }
-
-       return -EINVAL;
-}
-
-static struct nouveau_ofuncs
-nv04_disp_ofuncs = {
-       .ctor = _nouveau_object_ctor,
-       .dtor = nouveau_object_destroy,
-       .init = nouveau_object_init,
-       .fini = nouveau_object_fini,
-       .mthd = nv04_disp_mthd,
-       .ntfy = nouveau_disp_ntfy,
-};
-
-static struct nouveau_oclass
-nv04_disp_sclass[] = {
-       { NV04_DISP, &nv04_disp_ofuncs },
-       {},
-};
-
-/*******************************************************************************
- * Display engine implementation
- ******************************************************************************/
-
-static void
-nv04_disp_vblank_init(struct nvkm_event *event, int type, int head)
-{
-       struct nouveau_disp *disp = container_of(event, typeof(*disp), vblank);
-       nv_wr32(disp, 0x600140 + (head * 0x2000) , 0x00000001);
-}
-
-static void
-nv04_disp_vblank_fini(struct nvkm_event *event, int type, int head)
-{
-       struct nouveau_disp *disp = container_of(event, typeof(*disp), vblank);
-       nv_wr32(disp, 0x600140 + (head * 0x2000) , 0x00000000);
-}
-
-static const struct nvkm_event_func
-nv04_disp_vblank_func = {
-       .ctor = nouveau_disp_vblank_ctor,
-       .init = nv04_disp_vblank_init,
-       .fini = nv04_disp_vblank_fini,
-};
-
-static void
-nv04_disp_intr(struct nouveau_subdev *subdev)
-{
-       struct nv04_disp_priv *priv = (void *)subdev;
-       u32 crtc0 = nv_rd32(priv, 0x600100);
-       u32 crtc1 = nv_rd32(priv, 0x602100);
-       u32 pvideo;
-
-       if (crtc0 & 0x00000001) {
-               nouveau_disp_vblank(&priv->base, 0);
-               nv_wr32(priv, 0x600100, 0x00000001);
-       }
-
-       if (crtc1 & 0x00000001) {
-               nouveau_disp_vblank(&priv->base, 1);
-               nv_wr32(priv, 0x602100, 0x00000001);
-       }
-
-       if (nv_device(priv)->chipset >= 0x10 &&
-           nv_device(priv)->chipset <= 0x40) {
-               pvideo = nv_rd32(priv, 0x8100);
-               if (pvideo & ~0x11)
-                       nv_info(priv, "PVIDEO intr: %08x\n", pvideo);
-               nv_wr32(priv, 0x8100, pvideo);
-       }
-}
-
-static int
-nv04_disp_ctor(struct nouveau_object *parent, struct nouveau_object *engine,
-              struct nouveau_oclass *oclass, void *data, u32 size,
-              struct nouveau_object **pobject)
-{
-       struct nv04_disp_priv *priv;
-       int ret;
-
-       ret = nouveau_disp_create(parent, engine, oclass, 2, "DISPLAY",
-                                 "display", &priv);
-       *pobject = nv_object(priv);
-       if (ret)
-               return ret;
-
-       nv_engine(priv)->sclass = nv04_disp_sclass;
-       nv_subdev(priv)->intr = nv04_disp_intr;
-       return 0;
-}
-
-struct nouveau_oclass *
-nv04_disp_oclass = &(struct nouveau_disp_impl) {
-       .base.handle = NV_ENGINE(DISP, 0x04),
-       .base.ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nv04_disp_ctor,
-               .dtor = _nouveau_disp_dtor,
-               .init = _nouveau_disp_init,
-               .fini = _nouveau_disp_fini,
-       },
-       .vblank = &nv04_disp_vblank_func,
-}.base;
diff --git a/drivers/gpu/drm/nouveau/core/engine/disp/nv50.c b/drivers/gpu/drm/nouveau/core/engine/disp/nv50.c
deleted file mode 100644 (file)
index 44a8290..0000000
+++ /dev/null
@@ -1,2017 +0,0 @@
-/*
- * Copyright 2012 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 <core/object.h>
-#include <core/client.h>
-#include <core/parent.h>
-#include <core/handle.h>
-#include <core/enum.h>
-#include <nvif/unpack.h>
-#include <nvif/class.h>
-#include <nvif/event.h>
-
-#include <subdev/bios.h>
-#include <subdev/bios/dcb.h>
-#include <subdev/bios/disp.h>
-#include <subdev/bios/init.h>
-#include <subdev/bios/pll.h>
-#include <subdev/devinit.h>
-#include <subdev/timer.h>
-#include <subdev/fb.h>
-
-#include "nv50.h"
-
-/*******************************************************************************
- * EVO channel base class
- ******************************************************************************/
-
-static int
-nv50_disp_chan_create_(struct nouveau_object *parent,
-                      struct nouveau_object *engine,
-                      struct nouveau_oclass *oclass, int head,
-                      int length, void **pobject)
-{
-       const struct nv50_disp_chan_impl *impl = (void *)oclass->ofuncs;
-       struct nv50_disp_base *base = (void *)parent;
-       struct nv50_disp_chan *chan;
-       int chid = impl->chid + head;
-       int ret;
-
-       if (base->chan & (1 << chid))
-               return -EBUSY;
-       base->chan |= (1 << chid);
-
-       ret = nouveau_namedb_create_(parent, engine, oclass, 0, NULL,
-                                    (1ULL << NVDEV_ENGINE_DMAOBJ),
-                                    length, pobject);
-       chan = *pobject;
-       if (ret)
-               return ret;
-       chan->chid = chid;
-
-       nv_parent(chan)->object_attach = impl->attach;
-       nv_parent(chan)->object_detach = impl->detach;
-       return 0;
-}
-
-static void
-nv50_disp_chan_destroy(struct nv50_disp_chan *chan)
-{
-       struct nv50_disp_base *base = (void *)nv_object(chan)->parent;
-       base->chan &= ~(1 << chan->chid);
-       nouveau_namedb_destroy(&chan->base);
-}
-
-static void
-nv50_disp_chan_uevent_fini(struct nvkm_event *event, int type, int index)
-{
-       struct nv50_disp_priv *priv = container_of(event, typeof(*priv), uevent);
-       nv_mask(priv, 0x610028, 0x00000001 << index, 0x00000000 << index);
-       nv_wr32(priv, 0x610020, 0x00000001 << index);
-}
-
-static void
-nv50_disp_chan_uevent_init(struct nvkm_event *event, int types, int index)
-{
-       struct nv50_disp_priv *priv = container_of(event, typeof(*priv), uevent);
-       nv_wr32(priv, 0x610020, 0x00000001 << index);
-       nv_mask(priv, 0x610028, 0x00000001 << index, 0x00000001 << index);
-}
-
-void
-nv50_disp_chan_uevent_send(struct nv50_disp_priv *priv, int chid)
-{
-       struct nvif_notify_uevent_rep {
-       } rep;
-
-       nvkm_event_send(&priv->uevent, 1, chid, &rep, sizeof(rep));
-}
-
-int
-nv50_disp_chan_uevent_ctor(struct nouveau_object *object, void *data, u32 size,
-                          struct nvkm_notify *notify)
-{
-       struct nv50_disp_dmac *dmac = (void *)object;
-       union {
-               struct nvif_notify_uevent_req none;
-       } *args = data;
-       int ret;
-
-       if (nvif_unvers(args->none)) {
-               notify->size  = sizeof(struct nvif_notify_uevent_rep);
-               notify->types = 1;
-               notify->index = dmac->base.chid;
-               return 0;
-       }
-
-       return ret;
-}
-
-const struct nvkm_event_func
-nv50_disp_chan_uevent = {
-       .ctor = nv50_disp_chan_uevent_ctor,
-       .init = nv50_disp_chan_uevent_init,
-       .fini = nv50_disp_chan_uevent_fini,
-};
-
-int
-nv50_disp_chan_ntfy(struct nouveau_object *object, u32 type,
-                   struct nvkm_event **pevent)
-{
-       struct nv50_disp_priv *priv = (void *)object->engine;
-       switch (type) {
-       case NV50_DISP_CORE_CHANNEL_DMA_V0_NTFY_UEVENT:
-               *pevent = &priv->uevent;
-               return 0;
-       default:
-               break;
-       }
-       return -EINVAL;
-}
-
-int
-nv50_disp_chan_map(struct nouveau_object *object, u64 *addr, u32 *size)
-{
-       struct nv50_disp_chan *chan = (void *)object;
-       *addr = nv_device_resource_start(nv_device(object), 0) +
-               0x640000 + (chan->chid * 0x1000);
-       *size = 0x001000;
-       return 0;
-}
-
-u32
-nv50_disp_chan_rd32(struct nouveau_object *object, u64 addr)
-{
-       struct nv50_disp_priv *priv = (void *)object->engine;
-       struct nv50_disp_chan *chan = (void *)object;
-       return nv_rd32(priv, 0x640000 + (chan->chid * 0x1000) + addr);
-}
-
-void
-nv50_disp_chan_wr32(struct nouveau_object *object, u64 addr, u32 data)
-{
-       struct nv50_disp_priv *priv = (void *)object->engine;
-       struct nv50_disp_chan *chan = (void *)object;
-       nv_wr32(priv, 0x640000 + (chan->chid * 0x1000) + addr, data);
-}
-
-/*******************************************************************************
- * EVO DMA channel base class
- ******************************************************************************/
-
-static int
-nv50_disp_dmac_object_attach(struct nouveau_object *parent,
-                            struct nouveau_object *object, u32 name)
-{
-       struct nv50_disp_base *base = (void *)parent->parent;
-       struct nv50_disp_chan *chan = (void *)parent;
-       u32 addr = nv_gpuobj(object)->node->offset;
-       u32 chid = chan->chid;
-       u32 data = (chid << 28) | (addr << 10) | chid;
-       return nouveau_ramht_insert(base->ramht, chid, name, data);
-}
-
-static void
-nv50_disp_dmac_object_detach(struct nouveau_object *parent, int cookie)
-{
-       struct nv50_disp_base *base = (void *)parent->parent;
-       nouveau_ramht_remove(base->ramht, cookie);
-}
-
-static int
-nv50_disp_dmac_create_(struct nouveau_object *parent,
-                      struct nouveau_object *engine,
-                      struct nouveau_oclass *oclass, u32 pushbuf, int head,
-                      int length, void **pobject)
-{
-       struct nv50_disp_dmac *dmac;
-       int ret;
-
-       ret = nv50_disp_chan_create_(parent, engine, oclass, head,
-                                    length, pobject);
-       dmac = *pobject;
-       if (ret)
-               return ret;
-
-       dmac->pushdma = (void *)nouveau_handle_ref(parent, pushbuf);
-       if (!dmac->pushdma)
-               return -ENOENT;
-
-       switch (nv_mclass(dmac->pushdma)) {
-       case 0x0002:
-       case 0x003d:
-               if (dmac->pushdma->limit - dmac->pushdma->start != 0xfff)
-                       return -EINVAL;
-
-               switch (dmac->pushdma->target) {
-               case NV_MEM_TARGET_VRAM:
-                       dmac->push = 0x00000000 | dmac->pushdma->start >> 8;
-                       break;
-               case NV_MEM_TARGET_PCI_NOSNOOP:
-                       dmac->push = 0x00000003 | dmac->pushdma->start >> 8;
-                       break;
-               default:
-                       return -EINVAL;
-               }
-               break;
-       default:
-               return -EINVAL;
-       }
-
-       return 0;
-}
-
-void
-nv50_disp_dmac_dtor(struct nouveau_object *object)
-{
-       struct nv50_disp_dmac *dmac = (void *)object;
-       nouveau_object_ref(NULL, (struct nouveau_object **)&dmac->pushdma);
-       nv50_disp_chan_destroy(&dmac->base);
-}
-
-static int
-nv50_disp_dmac_init(struct nouveau_object *object)
-{
-       struct nv50_disp_priv *priv = (void *)object->engine;
-       struct nv50_disp_dmac *dmac = (void *)object;
-       int chid = dmac->base.chid;
-       int ret;
-
-       ret = nv50_disp_chan_init(&dmac->base);
-       if (ret)
-               return ret;
-
-       /* enable error reporting */
-       nv_mask(priv, 0x610028, 0x00010000 << chid, 0x00010000 << chid);
-
-       /* initialise channel for dma command submission */
-       nv_wr32(priv, 0x610204 + (chid * 0x0010), dmac->push);
-       nv_wr32(priv, 0x610208 + (chid * 0x0010), 0x00010000);
-       nv_wr32(priv, 0x61020c + (chid * 0x0010), chid);
-       nv_mask(priv, 0x610200 + (chid * 0x0010), 0x00000010, 0x00000010);
-       nv_wr32(priv, 0x640000 + (chid * 0x1000), 0x00000000);
-       nv_wr32(priv, 0x610200 + (chid * 0x0010), 0x00000013);
-
-       /* wait for it to go inactive */
-       if (!nv_wait(priv, 0x610200 + (chid * 0x10), 0x80000000, 0x00000000)) {
-               nv_error(dmac, "init timeout, 0x%08x\n",
-                        nv_rd32(priv, 0x610200 + (chid * 0x10)));
-               return -EBUSY;
-       }
-
-       return 0;
-}
-
-static int
-nv50_disp_dmac_fini(struct nouveau_object *object, bool suspend)
-{
-       struct nv50_disp_priv *priv = (void *)object->engine;
-       struct nv50_disp_dmac *dmac = (void *)object;
-       int chid = dmac->base.chid;
-
-       /* deactivate channel */
-       nv_mask(priv, 0x610200 + (chid * 0x0010), 0x00001010, 0x00001000);
-       nv_mask(priv, 0x610200 + (chid * 0x0010), 0x00000003, 0x00000000);
-       if (!nv_wait(priv, 0x610200 + (chid * 0x10), 0x001e0000, 0x00000000)) {
-               nv_error(dmac, "fini timeout, 0x%08x\n",
-                        nv_rd32(priv, 0x610200 + (chid * 0x10)));
-               if (suspend)
-                       return -EBUSY;
-       }
-
-       /* disable error reporting and completion notifications */
-       nv_mask(priv, 0x610028, 0x00010001 << chid, 0x00000000 << chid);
-
-       return nv50_disp_chan_fini(&dmac->base, suspend);
-}
-
-/*******************************************************************************
- * EVO master channel object
- ******************************************************************************/
-
-static void
-nv50_disp_mthd_list(struct nv50_disp_priv *priv, int debug, u32 base, int c,
-                   const struct nv50_disp_mthd_list *list, int inst)
-{
-       struct nouveau_object *disp = nv_object(priv);
-       int i;
-
-       for (i = 0; list->data[i].mthd; i++) {
-               if (list->data[i].addr) {
-                       u32 next = nv_rd32(priv, list->data[i].addr + base + 0);
-                       u32 prev = nv_rd32(priv, list->data[i].addr + base + c);
-                       u32 mthd = list->data[i].mthd + (list->mthd * inst);
-                       const char *name = list->data[i].name;
-                       char mods[16];
-
-                       if (prev != next)
-                               snprintf(mods, sizeof(mods), "-> 0x%08x", next);
-                       else
-                               snprintf(mods, sizeof(mods), "%13c", ' ');
-
-                       nv_printk_(disp, debug, "\t0x%04x: 0x%08x %s%s%s\n",
-                                  mthd, prev, mods, name ? " // " : "",
-                                  name ? name : "");
-               }
-       }
-}
-
-void
-nv50_disp_mthd_chan(struct nv50_disp_priv *priv, int debug, int head,
-                   const struct nv50_disp_mthd_chan *chan)
-{
-       struct nouveau_object *disp = nv_object(priv);
-       const struct nv50_disp_impl *impl = (void *)disp->oclass;
-       const struct nv50_disp_mthd_list *list;
-       int i, j;
-
-       if (debug > nv_subdev(priv)->debug)
-               return;
-
-       for (i = 0; (list = chan->data[i].mthd) != NULL; i++) {
-               u32 base = head * chan->addr;
-               for (j = 0; j < chan->data[i].nr; j++, base += list->addr) {
-                       const char *cname = chan->name;
-                       const char *sname = "";
-                       char cname_[16], sname_[16];
-
-                       if (chan->addr) {
-                               snprintf(cname_, sizeof(cname_), "%s %d",
-                                        chan->name, head);
-                               cname = cname_;
-                       }
-
-                       if (chan->data[i].nr > 1) {
-                               snprintf(sname_, sizeof(sname_), " - %s %d",
-                                        chan->data[i].name, j);
-                               sname = sname_;
-                       }
-
-                       nv_printk_(disp, debug, "%s%s:\n", cname, sname);
-                       nv50_disp_mthd_list(priv, debug, base, impl->mthd.prev,
-                                           list, j);
-               }
-       }
-}
-
-const struct nv50_disp_mthd_list
-nv50_disp_core_mthd_base = {
-       .mthd = 0x0000,
-       .addr = 0x000000,
-       .data = {
-               { 0x0080, 0x000000 },
-               { 0x0084, 0x610bb8 },
-               { 0x0088, 0x610b9c },
-               { 0x008c, 0x000000 },
-               {}
-       }
-};
-
-static const struct nv50_disp_mthd_list
-nv50_disp_core_mthd_dac = {
-       .mthd = 0x0080,
-       .addr = 0x000008,
-       .data = {
-               { 0x0400, 0x610b58 },
-               { 0x0404, 0x610bdc },
-               { 0x0420, 0x610828 },
-               {}
-       }
-};
-
-const struct nv50_disp_mthd_list
-nv50_disp_core_mthd_sor = {
-       .mthd = 0x0040,
-       .addr = 0x000008,
-       .data = {
-               { 0x0600, 0x610b70 },
-               {}
-       }
-};
-
-const struct nv50_disp_mthd_list
-nv50_disp_core_mthd_pior = {
-       .mthd = 0x0040,
-       .addr = 0x000008,
-       .data = {
-               { 0x0700, 0x610b80 },
-               {}
-       }
-};
-
-static const struct nv50_disp_mthd_list
-nv50_disp_core_mthd_head = {
-       .mthd = 0x0400,
-       .addr = 0x000540,
-       .data = {
-               { 0x0800, 0x610ad8 },
-               { 0x0804, 0x610ad0 },
-               { 0x0808, 0x610a48 },
-               { 0x080c, 0x610a78 },
-               { 0x0810, 0x610ac0 },
-               { 0x0814, 0x610af8 },
-               { 0x0818, 0x610b00 },
-               { 0x081c, 0x610ae8 },
-               { 0x0820, 0x610af0 },
-               { 0x0824, 0x610b08 },
-               { 0x0828, 0x610b10 },
-               { 0x082c, 0x610a68 },
-               { 0x0830, 0x610a60 },
-               { 0x0834, 0x000000 },
-               { 0x0838, 0x610a40 },
-               { 0x0840, 0x610a24 },
-               { 0x0844, 0x610a2c },
-               { 0x0848, 0x610aa8 },
-               { 0x084c, 0x610ab0 },
-               { 0x0860, 0x610a84 },
-               { 0x0864, 0x610a90 },
-               { 0x0868, 0x610b18 },
-               { 0x086c, 0x610b20 },
-               { 0x0870, 0x610ac8 },
-               { 0x0874, 0x610a38 },
-               { 0x0880, 0x610a58 },
-               { 0x0884, 0x610a9c },
-               { 0x08a0, 0x610a70 },
-               { 0x08a4, 0x610a50 },
-               { 0x08a8, 0x610ae0 },
-               { 0x08c0, 0x610b28 },
-               { 0x08c4, 0x610b30 },
-               { 0x08c8, 0x610b40 },
-               { 0x08d4, 0x610b38 },
-               { 0x08d8, 0x610b48 },
-               { 0x08dc, 0x610b50 },
-               { 0x0900, 0x610a18 },
-               { 0x0904, 0x610ab8 },
-               {}
-       }
-};
-
-static const struct nv50_disp_mthd_chan
-nv50_disp_core_mthd_chan = {
-       .name = "Core",
-       .addr = 0x000000,
-       .data = {
-               { "Global", 1, &nv50_disp_core_mthd_base },
-               {    "DAC", 3, &nv50_disp_core_mthd_dac  },
-               {    "SOR", 2, &nv50_disp_core_mthd_sor  },
-               {   "PIOR", 3, &nv50_disp_core_mthd_pior },
-               {   "HEAD", 2, &nv50_disp_core_mthd_head },
-               {}
-       }
-};
-
-int
-nv50_disp_core_ctor(struct nouveau_object *parent,
-                   struct nouveau_object *engine,
-                   struct nouveau_oclass *oclass, void *data, u32 size,
-                   struct nouveau_object **pobject)
-{
-       union {
-               struct nv50_disp_core_channel_dma_v0 v0;
-       } *args = data;
-       struct nv50_disp_dmac *mast;
-       int ret;
-
-       nv_ioctl(parent, "create disp core channel dma size %d\n", size);
-       if (nvif_unpack(args->v0, 0, 0, false)) {
-               nv_ioctl(parent, "create disp core channel dma vers %d "
-                                "pushbuf %08x\n",
-                        args->v0.version, args->v0.pushbuf);
-       } else
-               return ret;
-
-       ret = nv50_disp_dmac_create_(parent, engine, oclass, args->v0.pushbuf,
-                                    0, sizeof(*mast), (void **)&mast);
-       *pobject = nv_object(mast);
-       if (ret)
-               return ret;
-
-       return 0;
-}
-
-static int
-nv50_disp_core_init(struct nouveau_object *object)
-{
-       struct nv50_disp_priv *priv = (void *)object->engine;
-       struct nv50_disp_dmac *mast = (void *)object;
-       int ret;
-
-       ret = nv50_disp_chan_init(&mast->base);
-       if (ret)
-               return ret;
-
-       /* enable error reporting */
-       nv_mask(priv, 0x610028, 0x00010000, 0x00010000);
-
-       /* attempt to unstick channel from some unknown state */
-       if ((nv_rd32(priv, 0x610200) & 0x009f0000) == 0x00020000)
-               nv_mask(priv, 0x610200, 0x00800000, 0x00800000);
-       if ((nv_rd32(priv, 0x610200) & 0x003f0000) == 0x00030000)
-               nv_mask(priv, 0x610200, 0x00600000, 0x00600000);
-
-       /* initialise channel for dma command submission */
-       nv_wr32(priv, 0x610204, mast->push);
-       nv_wr32(priv, 0x610208, 0x00010000);
-       nv_wr32(priv, 0x61020c, 0x00000000);
-       nv_mask(priv, 0x610200, 0x00000010, 0x00000010);
-       nv_wr32(priv, 0x640000, 0x00000000);
-       nv_wr32(priv, 0x610200, 0x01000013);
-
-       /* wait for it to go inactive */
-       if (!nv_wait(priv, 0x610200, 0x80000000, 0x00000000)) {
-               nv_error(mast, "init: 0x%08x\n", nv_rd32(priv, 0x610200));
-               return -EBUSY;
-       }
-
-       return 0;
-}
-
-static int
-nv50_disp_core_fini(struct nouveau_object *object, bool suspend)
-{
-       struct nv50_disp_priv *priv = (void *)object->engine;
-       struct nv50_disp_dmac *mast = (void *)object;
-
-       /* deactivate channel */
-       nv_mask(priv, 0x610200, 0x00000010, 0x00000000);
-       nv_mask(priv, 0x610200, 0x00000003, 0x00000000);
-       if (!nv_wait(priv, 0x610200, 0x001e0000, 0x00000000)) {
-               nv_error(mast, "fini: 0x%08x\n", nv_rd32(priv, 0x610200));
-               if (suspend)
-                       return -EBUSY;
-       }
-
-       /* disable error reporting and completion notifications */
-       nv_mask(priv, 0x610028, 0x00010001, 0x00000000);
-
-       return nv50_disp_chan_fini(&mast->base, suspend);
-}
-
-struct nv50_disp_chan_impl
-nv50_disp_core_ofuncs = {
-       .base.ctor = nv50_disp_core_ctor,
-       .base.dtor = nv50_disp_dmac_dtor,
-       .base.init = nv50_disp_core_init,
-       .base.fini = nv50_disp_core_fini,
-       .base.map  = nv50_disp_chan_map,
-       .base.ntfy = nv50_disp_chan_ntfy,
-       .base.rd32 = nv50_disp_chan_rd32,
-       .base.wr32 = nv50_disp_chan_wr32,
-       .chid = 0,
-       .attach = nv50_disp_dmac_object_attach,
-       .detach = nv50_disp_dmac_object_detach,
-};
-
-/*******************************************************************************
- * EVO sync channel objects
- ******************************************************************************/
-
-static const struct nv50_disp_mthd_list
-nv50_disp_base_mthd_base = {
-       .mthd = 0x0000,
-       .addr = 0x000000,
-       .data = {
-               { 0x0080, 0x000000 },
-               { 0x0084, 0x0008c4 },
-               { 0x0088, 0x0008d0 },
-               { 0x008c, 0x0008dc },
-               { 0x0090, 0x0008e4 },
-               { 0x0094, 0x610884 },
-               { 0x00a0, 0x6108a0 },
-               { 0x00a4, 0x610878 },
-               { 0x00c0, 0x61086c },
-               { 0x00e0, 0x610858 },
-               { 0x00e4, 0x610860 },
-               { 0x00e8, 0x6108ac },
-               { 0x00ec, 0x6108b4 },
-               { 0x0100, 0x610894 },
-               { 0x0110, 0x6108bc },
-               { 0x0114, 0x61088c },
-               {}
-       }
-};
-
-const struct nv50_disp_mthd_list
-nv50_disp_base_mthd_image = {
-       .mthd = 0x0400,
-       .addr = 0x000000,
-       .data = {
-               { 0x0800, 0x6108f0 },
-               { 0x0804, 0x6108fc },
-               { 0x0808, 0x61090c },
-               { 0x080c, 0x610914 },
-               { 0x0810, 0x610904 },
-               {}
-       }
-};
-
-static const struct nv50_disp_mthd_chan
-nv50_disp_base_mthd_chan = {
-       .name = "Base",
-       .addr = 0x000540,
-       .data = {
-               { "Global", 1, &nv50_disp_base_mthd_base },
-               {  "Image", 2, &nv50_disp_base_mthd_image },
-               {}
-       }
-};
-
-int
-nv50_disp_base_ctor(struct nouveau_object *parent,
-                   struct nouveau_object *engine,
-                   struct nouveau_oclass *oclass, void *data, u32 size,
-                   struct nouveau_object **pobject)
-{
-       union {
-               struct nv50_disp_base_channel_dma_v0 v0;
-       } *args = data;
-       struct nv50_disp_priv *priv = (void *)engine;
-       struct nv50_disp_dmac *dmac;
-       int ret;
-
-       nv_ioctl(parent, "create disp base channel dma size %d\n", size);
-       if (nvif_unpack(args->v0, 0, 0, false)) {
-               nv_ioctl(parent, "create disp base channel dma vers %d "
-                                "pushbuf %08x head %d\n",
-                        args->v0.version, args->v0.pushbuf, args->v0.head);
-               if (args->v0.head > priv->head.nr)
-                       return -EINVAL;
-       } else
-               return ret;
-
-       ret = nv50_disp_dmac_create_(parent, engine, oclass, args->v0.pushbuf,
-                                    args->v0.head, sizeof(*dmac),
-                                    (void **)&dmac);
-       *pobject = nv_object(dmac);
-       if (ret)
-               return ret;
-
-       return 0;
-}
-
-struct nv50_disp_chan_impl
-nv50_disp_base_ofuncs = {
-       .base.ctor = nv50_disp_base_ctor,
-       .base.dtor = nv50_disp_dmac_dtor,
-       .base.init = nv50_disp_dmac_init,
-       .base.fini = nv50_disp_dmac_fini,
-       .base.ntfy = nv50_disp_chan_ntfy,
-       .base.map  = nv50_disp_chan_map,
-       .base.rd32 = nv50_disp_chan_rd32,
-       .base.wr32 = nv50_disp_chan_wr32,
-       .chid = 1,
-       .attach = nv50_disp_dmac_object_attach,
-       .detach = nv50_disp_dmac_object_detach,
-};
-
-/*******************************************************************************
- * EVO overlay channel objects
- ******************************************************************************/
-
-const struct nv50_disp_mthd_list
-nv50_disp_ovly_mthd_base = {
-       .mthd = 0x0000,
-       .addr = 0x000000,
-       .data = {
-               { 0x0080, 0x000000 },
-               { 0x0084, 0x0009a0 },
-               { 0x0088, 0x0009c0 },
-               { 0x008c, 0x0009c8 },
-               { 0x0090, 0x6109b4 },
-               { 0x0094, 0x610970 },
-               { 0x00a0, 0x610998 },
-               { 0x00a4, 0x610964 },
-               { 0x00c0, 0x610958 },
-               { 0x00e0, 0x6109a8 },
-               { 0x00e4, 0x6109d0 },
-               { 0x00e8, 0x6109d8 },
-               { 0x0100, 0x61094c },
-               { 0x0104, 0x610984 },
-               { 0x0108, 0x61098c },
-               { 0x0800, 0x6109f8 },
-               { 0x0808, 0x610a08 },
-               { 0x080c, 0x610a10 },
-               { 0x0810, 0x610a00 },
-               {}
-       }
-};
-
-static const struct nv50_disp_mthd_chan
-nv50_disp_ovly_mthd_chan = {
-       .name = "Overlay",
-       .addr = 0x000540,
-       .data = {
-               { "Global", 1, &nv50_disp_ovly_mthd_base },
-               {}
-       }
-};
-
-int
-nv50_disp_ovly_ctor(struct nouveau_object *parent,
-                   struct nouveau_object *engine,
-                   struct nouveau_oclass *oclass, void *data, u32 size,
-                   struct nouveau_object **pobject)
-{
-       union {
-               struct nv50_disp_overlay_channel_dma_v0 v0;
-       } *args = data;
-       struct nv50_disp_priv *priv = (void *)engine;
-       struct nv50_disp_dmac *dmac;
-       int ret;
-
-       nv_ioctl(parent, "create disp overlay channel dma size %d\n", size);
-       if (nvif_unpack(args->v0, 0, 0, false)) {
-               nv_ioctl(parent, "create disp overlay channel dma vers %d "
-                                "pushbuf %08x head %d\n",
-                        args->v0.version, args->v0.pushbuf, args->v0.head);
-               if (args->v0.head > priv->head.nr)
-                       return -EINVAL;
-       } else
-               return ret;
-
-       ret = nv50_disp_dmac_create_(parent, engine, oclass, args->v0.pushbuf,
-                                    args->v0.head, sizeof(*dmac),
-                                    (void **)&dmac);
-       *pobject = nv_object(dmac);
-       if (ret)
-               return ret;
-
-       return 0;
-}
-
-struct nv50_disp_chan_impl
-nv50_disp_ovly_ofuncs = {
-       .base.ctor = nv50_disp_ovly_ctor,
-       .base.dtor = nv50_disp_dmac_dtor,
-       .base.init = nv50_disp_dmac_init,
-       .base.fini = nv50_disp_dmac_fini,
-       .base.ntfy = nv50_disp_chan_ntfy,
-       .base.map  = nv50_disp_chan_map,
-       .base.rd32 = nv50_disp_chan_rd32,
-       .base.wr32 = nv50_disp_chan_wr32,
-       .chid = 3,
-       .attach = nv50_disp_dmac_object_attach,
-       .detach = nv50_disp_dmac_object_detach,
-};
-
-/*******************************************************************************
- * EVO PIO channel base class
- ******************************************************************************/
-
-static int
-nv50_disp_pioc_create_(struct nouveau_object *parent,
-                      struct nouveau_object *engine,
-                      struct nouveau_oclass *oclass, int head,
-                      int length, void **pobject)
-{
-       return nv50_disp_chan_create_(parent, engine, oclass, head,
-                                     length, pobject);
-}
-
-void
-nv50_disp_pioc_dtor(struct nouveau_object *object)
-{
-       struct nv50_disp_pioc *pioc = (void *)object;
-       nv50_disp_chan_destroy(&pioc->base);
-}
-
-static int
-nv50_disp_pioc_init(struct nouveau_object *object)
-{
-       struct nv50_disp_priv *priv = (void *)object->engine;
-       struct nv50_disp_pioc *pioc = (void *)object;
-       int chid = pioc->base.chid;
-       int ret;
-
-       ret = nv50_disp_chan_init(&pioc->base);
-       if (ret)
-               return ret;
-
-       nv_wr32(priv, 0x610200 + (chid * 0x10), 0x00002000);
-       if (!nv_wait(priv, 0x610200 + (chid * 0x10), 0x00000000, 0x00000000)) {
-               nv_error(pioc, "timeout0: 0x%08x\n",
-                        nv_rd32(priv, 0x610200 + (chid * 0x10)));
-               return -EBUSY;
-       }
-
-       nv_wr32(priv, 0x610200 + (chid * 0x10), 0x00000001);
-       if (!nv_wait(priv, 0x610200 + (chid * 0x10), 0x00030000, 0x00010000)) {
-               nv_error(pioc, "timeout1: 0x%08x\n",
-                        nv_rd32(priv, 0x610200 + (chid * 0x10)));
-               return -EBUSY;
-       }
-
-       return 0;
-}
-
-static int
-nv50_disp_pioc_fini(struct nouveau_object *object, bool suspend)
-{
-       struct nv50_disp_priv *priv = (void *)object->engine;
-       struct nv50_disp_pioc *pioc = (void *)object;
-       int chid = pioc->base.chid;
-
-       nv_mask(priv, 0x610200 + (chid * 0x10), 0x00000001, 0x00000000);
-       if (!nv_wait(priv, 0x610200 + (chid * 0x10), 0x00030000, 0x00000000)) {
-               nv_error(pioc, "timeout: 0x%08x\n",
-                        nv_rd32(priv, 0x610200 + (chid * 0x10)));
-               if (suspend)
-                       return -EBUSY;
-       }
-
-       return nv50_disp_chan_fini(&pioc->base, suspend);
-}
-
-/*******************************************************************************
- * EVO immediate overlay channel objects
- ******************************************************************************/
-
-int
-nv50_disp_oimm_ctor(struct nouveau_object *parent,
-                   struct nouveau_object *engine,
-                   struct nouveau_oclass *oclass, void *data, u32 size,
-                   struct nouveau_object **pobject)
-{
-       union {
-               struct nv50_disp_overlay_v0 v0;
-       } *args = data;
-       struct nv50_disp_priv *priv = (void *)engine;
-       struct nv50_disp_pioc *pioc;
-       int ret;
-
-       nv_ioctl(parent, "create disp overlay size %d\n", size);
-       if (nvif_unpack(args->v0, 0, 0, false)) {
-               nv_ioctl(parent, "create disp overlay vers %d head %d\n",
-                        args->v0.version, args->v0.head);
-               if (args->v0.head > priv->head.nr)
-                       return -EINVAL;
-       } else
-               return ret;
-
-       ret = nv50_disp_pioc_create_(parent, engine, oclass, args->v0.head,
-                                    sizeof(*pioc), (void **)&pioc);
-       *pobject = nv_object(pioc);
-       if (ret)
-               return ret;
-
-       return 0;
-}
-
-struct nv50_disp_chan_impl
-nv50_disp_oimm_ofuncs = {
-       .base.ctor = nv50_disp_oimm_ctor,
-       .base.dtor = nv50_disp_pioc_dtor,
-       .base.init = nv50_disp_pioc_init,
-       .base.fini = nv50_disp_pioc_fini,
-       .base.ntfy = nv50_disp_chan_ntfy,
-       .base.map  = nv50_disp_chan_map,
-       .base.rd32 = nv50_disp_chan_rd32,
-       .base.wr32 = nv50_disp_chan_wr32,
-       .chid = 5,
-};
-
-/*******************************************************************************
- * EVO cursor channel objects
- ******************************************************************************/
-
-int
-nv50_disp_curs_ctor(struct nouveau_object *parent,
-                   struct nouveau_object *engine,
-                   struct nouveau_oclass *oclass, void *data, u32 size,
-                   struct nouveau_object **pobject)
-{
-       union {
-               struct nv50_disp_cursor_v0 v0;
-       } *args = data;
-       struct nv50_disp_priv *priv = (void *)engine;
-       struct nv50_disp_pioc *pioc;
-       int ret;
-
-       nv_ioctl(parent, "create disp cursor size %d\n", size);
-       if (nvif_unpack(args->v0, 0, 0, false)) {
-               nv_ioctl(parent, "create disp cursor vers %d head %d\n",
-                        args->v0.version, args->v0.head);
-               if (args->v0.head > priv->head.nr)
-                       return -EINVAL;
-       } else
-               return ret;
-
-       ret = nv50_disp_pioc_create_(parent, engine, oclass, args->v0.head,
-                                    sizeof(*pioc), (void **)&pioc);
-       *pobject = nv_object(pioc);
-       if (ret)
-               return ret;
-
-       return 0;
-}
-
-struct nv50_disp_chan_impl
-nv50_disp_curs_ofuncs = {
-       .base.ctor = nv50_disp_curs_ctor,
-       .base.dtor = nv50_disp_pioc_dtor,
-       .base.init = nv50_disp_pioc_init,
-       .base.fini = nv50_disp_pioc_fini,
-       .base.ntfy = nv50_disp_chan_ntfy,
-       .base.map  = nv50_disp_chan_map,
-       .base.rd32 = nv50_disp_chan_rd32,
-       .base.wr32 = nv50_disp_chan_wr32,
-       .chid = 7,
-};
-
-/*******************************************************************************
- * Base display object
- ******************************************************************************/
-
-int
-nv50_disp_main_scanoutpos(NV50_DISP_MTHD_V0)
-{
-       const u32 blanke = nv_rd32(priv, 0x610aec + (head * 0x540));
-       const u32 blanks = nv_rd32(priv, 0x610af4 + (head * 0x540));
-       const u32 total  = nv_rd32(priv, 0x610afc + (head * 0x540));
-       union {
-               struct nv04_disp_scanoutpos_v0 v0;
-       } *args = data;
-       int ret;
-
-       nv_ioctl(object, "disp scanoutpos size %d\n", size);
-       if (nvif_unpack(args->v0, 0, 0, false)) {
-               nv_ioctl(object, "disp scanoutpos vers %d\n", args->v0.version);
-               args->v0.vblanke = (blanke & 0xffff0000) >> 16;
-               args->v0.hblanke = (blanke & 0x0000ffff);
-               args->v0.vblanks = (blanks & 0xffff0000) >> 16;
-               args->v0.hblanks = (blanks & 0x0000ffff);
-               args->v0.vtotal  = ( total & 0xffff0000) >> 16;
-               args->v0.htotal  = ( total & 0x0000ffff);
-               args->v0.time[0] = ktime_to_ns(ktime_get());
-               args->v0.vline = /* vline read locks hline */
-                       nv_rd32(priv, 0x616340 + (head * 0x800)) & 0xffff;
-               args->v0.time[1] = ktime_to_ns(ktime_get());
-               args->v0.hline =
-                       nv_rd32(priv, 0x616344 + (head * 0x800)) & 0xffff;
-       } else
-               return ret;
-
-       return 0;
-}
-
-int
-nv50_disp_main_mthd(struct nouveau_object *object, u32 mthd,
-                   void *data, u32 size)
-{
-       const struct nv50_disp_impl *impl = (void *)nv_oclass(object->engine);
-       union {
-               struct nv50_disp_mthd_v0 v0;
-               struct nv50_disp_mthd_v1 v1;
-       } *args = data;
-       struct nv50_disp_priv *priv = (void *)object->engine;
-       struct nvkm_output *outp = NULL;
-       struct nvkm_output *temp;
-       u16 type, mask = 0;
-       int head, ret;
-
-       if (mthd != NV50_DISP_MTHD)
-               return -EINVAL;
-
-       nv_ioctl(object, "disp mthd size %d\n", size);
-       if (nvif_unpack(args->v0, 0, 0, true)) {
-               nv_ioctl(object, "disp mthd vers %d mthd %02x head %d\n",
-                        args->v0.version, args->v0.method, args->v0.head);
-               mthd = args->v0.method;
-               head = args->v0.head;
-       } else
-       if (nvif_unpack(args->v1, 1, 1, true)) {
-               nv_ioctl(object, "disp mthd vers %d mthd %02x "
-                                "type %04x mask %04x\n",
-                        args->v1.version, args->v1.method,
-                        args->v1.hasht, args->v1.hashm);
-               mthd = args->v1.method;
-               type = args->v1.hasht;
-               mask = args->v1.hashm;
-               head = ffs((mask >> 8) & 0x0f) - 1;
-       } else
-               return ret;
-
-       if (head < 0 || head >= priv->head.nr)
-               return -ENXIO;
-
-       if (mask) {
-               list_for_each_entry(temp, &priv->base.outp, head) {
-                       if ((temp->info.hasht         == type) &&
-                           (temp->info.hashm & mask) == mask) {
-                               outp = temp;
-                               break;
-                       }
-               }
-               if (outp == NULL)
-                       return -ENXIO;
-       }
-
-       switch (mthd) {
-       case NV50_DISP_SCANOUTPOS:
-               return impl->head.scanoutpos(object, priv, data, size, head);
-       default:
-               break;
-       }
-
-       switch (mthd * !!outp) {
-       case NV50_DISP_MTHD_V1_DAC_PWR:
-               return priv->dac.power(object, priv, data, size, head, outp);
-       case NV50_DISP_MTHD_V1_DAC_LOAD:
-               return priv->dac.sense(object, priv, data, size, head, outp);
-       case NV50_DISP_MTHD_V1_SOR_PWR:
-               return priv->sor.power(object, priv, data, size, head, outp);
-       case NV50_DISP_MTHD_V1_SOR_HDA_ELD:
-               if (!priv->sor.hda_eld)
-                       return -ENODEV;
-               return priv->sor.hda_eld(object, priv, data, size, head, outp);
-       case NV50_DISP_MTHD_V1_SOR_HDMI_PWR:
-               if (!priv->sor.hdmi)
-                       return -ENODEV;
-               return priv->sor.hdmi(object, priv, data, size, head, outp);
-       case NV50_DISP_MTHD_V1_SOR_LVDS_SCRIPT: {
-               union {
-                       struct nv50_disp_sor_lvds_script_v0 v0;
-               } *args = data;
-               nv_ioctl(object, "disp sor lvds script size %d\n", size);
-               if (nvif_unpack(args->v0, 0, 0, false)) {
-                       nv_ioctl(object, "disp sor lvds script "
-                                        "vers %d name %04x\n",
-                                args->v0.version, args->v0.script);
-                       priv->sor.lvdsconf = args->v0.script;
-                       return 0;
-               } else
-                       return ret;
-       }
-               break;
-       case NV50_DISP_MTHD_V1_SOR_DP_PWR: {
-               struct nvkm_output_dp *outpdp = (void *)outp;
-               union {
-                       struct nv50_disp_sor_dp_pwr_v0 v0;
-               } *args = data;
-               nv_ioctl(object, "disp sor dp pwr size %d\n", size);
-               if (nvif_unpack(args->v0, 0, 0, false)) {
-                       nv_ioctl(object, "disp sor dp pwr vers %d state %d\n",
-                                args->v0.version, args->v0.state);
-                       if (args->v0.state == 0) {
-                               nvkm_notify_put(&outpdp->irq);
-                               ((struct nvkm_output_dp_impl *)nv_oclass(outp))
-                                       ->lnk_pwr(outpdp, 0);
-                               atomic_set(&outpdp->lt.done, 0);
-                               return 0;
-                       } else
-                       if (args->v0.state != 0) {
-                               nvkm_output_dp_train(&outpdp->base, 0, true);
-                               return 0;
-                       }
-               } else
-                       return ret;
-       }
-               break;
-       case NV50_DISP_MTHD_V1_PIOR_PWR:
-               if (!priv->pior.power)
-                       return -ENODEV;
-               return priv->pior.power(object, priv, data, size, head, outp);
-       default:
-               break;
-       }
-
-       return -EINVAL;
-}
-
-int
-nv50_disp_main_ctor(struct nouveau_object *parent,
-                   struct nouveau_object *engine,
-                   struct nouveau_oclass *oclass, void *data, u32 size,
-                   struct nouveau_object **pobject)
-{
-       struct nv50_disp_priv *priv = (void *)engine;
-       struct nv50_disp_base *base;
-       int ret;
-
-       ret = nouveau_parent_create(parent, engine, oclass, 0,
-                                   priv->sclass, 0, &base);
-       *pobject = nv_object(base);
-       if (ret)
-               return ret;
-
-       return nouveau_ramht_new(nv_object(base), nv_object(base), 0x1000, 0,
-                               &base->ramht);
-}
-
-void
-nv50_disp_main_dtor(struct nouveau_object *object)
-{
-       struct nv50_disp_base *base = (void *)object;
-       nouveau_ramht_ref(NULL, &base->ramht);
-       nouveau_parent_destroy(&base->base);
-}
-
-static int
-nv50_disp_main_init(struct nouveau_object *object)
-{
-       struct nv50_disp_priv *priv = (void *)object->engine;
-       struct nv50_disp_base *base = (void *)object;
-       int ret, i;
-       u32 tmp;
-
-       ret = nouveau_parent_init(&base->base);
-       if (ret)
-               return ret;
-
-       /* The below segments of code copying values from one register to
-        * another appear to inform EVO of the display capabilities or
-        * something similar.  NFI what the 0x614004 caps are for..
-        */
-       tmp = nv_rd32(priv, 0x614004);
-       nv_wr32(priv, 0x610184, tmp);
-
-       /* ... CRTC caps */
-       for (i = 0; i < priv->head.nr; i++) {
-               tmp = nv_rd32(priv, 0x616100 + (i * 0x800));
-               nv_wr32(priv, 0x610190 + (i * 0x10), tmp);
-               tmp = nv_rd32(priv, 0x616104 + (i * 0x800));
-               nv_wr32(priv, 0x610194 + (i * 0x10), tmp);
-               tmp = nv_rd32(priv, 0x616108 + (i * 0x800));
-               nv_wr32(priv, 0x610198 + (i * 0x10), tmp);
-               tmp = nv_rd32(priv, 0x61610c + (i * 0x800));
-               nv_wr32(priv, 0x61019c + (i * 0x10), tmp);
-       }
-
-       /* ... DAC caps */
-       for (i = 0; i < priv->dac.nr; i++) {
-               tmp = nv_rd32(priv, 0x61a000 + (i * 0x800));
-               nv_wr32(priv, 0x6101d0 + (i * 0x04), tmp);
-       }
-
-       /* ... SOR caps */
-       for (i = 0; i < priv->sor.nr; i++) {
-               tmp = nv_rd32(priv, 0x61c000 + (i * 0x800));
-               nv_wr32(priv, 0x6101e0 + (i * 0x04), tmp);
-       }
-
-       /* ... PIOR caps */
-       for (i = 0; i < priv->pior.nr; i++) {
-               tmp = nv_rd32(priv, 0x61e000 + (i * 0x800));
-               nv_wr32(priv, 0x6101f0 + (i * 0x04), tmp);
-       }
-
-       /* steal display away from vbios, or something like that */
-       if (nv_rd32(priv, 0x610024) & 0x00000100) {
-               nv_wr32(priv, 0x610024, 0x00000100);
-               nv_mask(priv, 0x6194e8, 0x00000001, 0x00000000);
-               if (!nv_wait(priv, 0x6194e8, 0x00000002, 0x00000000)) {
-                       nv_error(priv, "timeout acquiring display\n");
-                       return -EBUSY;
-               }
-       }
-
-       /* point at display engine memory area (hash table, objects) */
-       nv_wr32(priv, 0x610010, (nv_gpuobj(base->ramht)->addr >> 8) | 9);
-
-       /* enable supervisor interrupts, disable everything else */
-       nv_wr32(priv, 0x61002c, 0x00000370);
-       nv_wr32(priv, 0x610028, 0x00000000);
-       return 0;
-}
-
-static int
-nv50_disp_main_fini(struct nouveau_object *object, bool suspend)
-{
-       struct nv50_disp_priv *priv = (void *)object->engine;
-       struct nv50_disp_base *base = (void *)object;
-
-       /* disable all interrupts */
-       nv_wr32(priv, 0x610024, 0x00000000);
-       nv_wr32(priv, 0x610020, 0x00000000);
-
-       return nouveau_parent_fini(&base->base, suspend);
-}
-
-struct nouveau_ofuncs
-nv50_disp_main_ofuncs = {
-       .ctor = nv50_disp_main_ctor,
-       .dtor = nv50_disp_main_dtor,
-       .init = nv50_disp_main_init,
-       .fini = nv50_disp_main_fini,
-       .mthd = nv50_disp_main_mthd,
-       .ntfy = nouveau_disp_ntfy,
-};
-
-static struct nouveau_oclass
-nv50_disp_main_oclass[] = {
-       { NV50_DISP, &nv50_disp_main_ofuncs },
-       {}
-};
-
-static struct nouveau_oclass
-nv50_disp_sclass[] = {
-       { NV50_DISP_CORE_CHANNEL_DMA, &nv50_disp_core_ofuncs.base },
-       { NV50_DISP_BASE_CHANNEL_DMA, &nv50_disp_base_ofuncs.base },
-       { NV50_DISP_OVERLAY_CHANNEL_DMA, &nv50_disp_ovly_ofuncs.base },
-       { NV50_DISP_OVERLAY, &nv50_disp_oimm_ofuncs.base },
-       { NV50_DISP_CURSOR, &nv50_disp_curs_ofuncs.base },
-       {}
-};
-
-/*******************************************************************************
- * Display context, tracks instmem allocation and prevents more than one
- * client using the display hardware at any time.
- ******************************************************************************/
-
-static int
-nv50_disp_data_ctor(struct nouveau_object *parent,
-                   struct nouveau_object *engine,
-                   struct nouveau_oclass *oclass, void *data, u32 size,
-                   struct nouveau_object **pobject)
-{
-       struct nv50_disp_priv *priv = (void *)engine;
-       struct nouveau_engctx *ectx;
-       int ret = -EBUSY;
-
-       /* no context needed for channel objects... */
-       if (nv_mclass(parent) != NV_DEVICE) {
-               atomic_inc(&parent->refcount);
-               *pobject = parent;
-               return 1;
-       }
-
-       /* allocate display hardware to client */
-       mutex_lock(&nv_subdev(priv)->mutex);
-       if (list_empty(&nv_engine(priv)->contexts)) {
-               ret = nouveau_engctx_create(parent, engine, oclass, NULL,
-                                           0x10000, 0x10000,
-                                           NVOBJ_FLAG_HEAP, &ectx);
-               *pobject = nv_object(ectx);
-       }
-       mutex_unlock(&nv_subdev(priv)->mutex);
-       return ret;
-}
-
-struct nouveau_oclass
-nv50_disp_cclass = {
-       .handle = NV_ENGCTX(DISP, 0x50),
-       .ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nv50_disp_data_ctor,
-               .dtor = _nouveau_engctx_dtor,
-               .init = _nouveau_engctx_init,
-               .fini = _nouveau_engctx_fini,
-               .rd32 = _nouveau_engctx_rd32,
-               .wr32 = _nouveau_engctx_wr32,
-       },
-};
-
-/*******************************************************************************
- * Display engine implementation
- ******************************************************************************/
-
-static void
-nv50_disp_vblank_fini(struct nvkm_event *event, int type, int head)
-{
-       struct nouveau_disp *disp = container_of(event, typeof(*disp), vblank);
-       nv_mask(disp, 0x61002c, (4 << head), 0);
-}
-
-static void
-nv50_disp_vblank_init(struct nvkm_event *event, int type, int head)
-{
-       struct nouveau_disp *disp = container_of(event, typeof(*disp), vblank);
-       nv_mask(disp, 0x61002c, (4 << head), (4 << head));
-}
-
-const struct nvkm_event_func
-nv50_disp_vblank_func = {
-       .ctor = nouveau_disp_vblank_ctor,
-       .init = nv50_disp_vblank_init,
-       .fini = nv50_disp_vblank_fini,
-};
-
-static const struct nouveau_enum
-nv50_disp_intr_error_type[] = {
-       { 3, "ILLEGAL_MTHD" },
-       { 4, "INVALID_VALUE" },
-       { 5, "INVALID_STATE" },
-       { 7, "INVALID_HANDLE" },
-       {}
-};
-
-static const struct nouveau_enum
-nv50_disp_intr_error_code[] = {
-       { 0x00, "" },
-       {}
-};
-
-static void
-nv50_disp_intr_error(struct nv50_disp_priv *priv, int chid)
-{
-       struct nv50_disp_impl *impl = (void *)nv_object(priv)->oclass;
-       u32 data = nv_rd32(priv, 0x610084 + (chid * 0x08));
-       u32 addr = nv_rd32(priv, 0x610080 + (chid * 0x08));
-       u32 code = (addr & 0x00ff0000) >> 16;
-       u32 type = (addr & 0x00007000) >> 12;
-       u32 mthd = (addr & 0x00000ffc);
-       const struct nouveau_enum *ec, *et;
-       char ecunk[6], etunk[6];
-
-       et = nouveau_enum_find(nv50_disp_intr_error_type, type);
-       if (!et)
-               snprintf(etunk, sizeof(etunk), "UNK%02X", type);
-
-       ec = nouveau_enum_find(nv50_disp_intr_error_code, code);
-       if (!ec)
-               snprintf(ecunk, sizeof(ecunk), "UNK%02X", code);
-
-       nv_error(priv, "%s [%s] chid %d mthd 0x%04x data 0x%08x\n",
-                et ? et->name : etunk, ec ? ec->name : ecunk,
-                chid, mthd, data);
-
-       if (chid == 0) {
-               switch (mthd) {
-               case 0x0080:
-                       nv50_disp_mthd_chan(priv, NV_DBG_ERROR, chid - 0,
-                                           impl->mthd.core);
-                       break;
-               default:
-                       break;
-               }
-       } else
-       if (chid <= 2) {
-               switch (mthd) {
-               case 0x0080:
-                       nv50_disp_mthd_chan(priv, NV_DBG_ERROR, chid - 1,
-                                           impl->mthd.base);
-                       break;
-               default:
-                       break;
-               }
-       } else
-       if (chid <= 4) {
-               switch (mthd) {
-               case 0x0080:
-                       nv50_disp_mthd_chan(priv, NV_DBG_ERROR, chid - 3,
-                                           impl->mthd.ovly);
-                       break;
-               default:
-                       break;
-               }
-       }
-
-       nv_wr32(priv, 0x610020, 0x00010000 << chid);
-       nv_wr32(priv, 0x610080 + (chid * 0x08), 0x90000000);
-}
-
-static struct nvkm_output *
-exec_lookup(struct nv50_disp_priv *priv, int head, int or, u32 ctrl,
-           u32 *data, u8 *ver, u8 *hdr, u8 *cnt, u8 *len,
-           struct nvbios_outp *info)
-{
-       struct nouveau_bios *bios = nouveau_bios(priv);
-       struct nvkm_output *outp;
-       u16 mask, type;
-
-       if (or < 4) {
-               type = DCB_OUTPUT_ANALOG;
-               mask = 0;
-       } else
-       if (or < 8) {
-               switch (ctrl & 0x00000f00) {
-               case 0x00000000: type = DCB_OUTPUT_LVDS; mask = 1; break;
-               case 0x00000100: type = DCB_OUTPUT_TMDS; mask = 1; break;
-               case 0x00000200: type = DCB_OUTPUT_TMDS; mask = 2; break;
-               case 0x00000500: type = DCB_OUTPUT_TMDS; mask = 3; break;
-               case 0x00000800: type = DCB_OUTPUT_DP; mask = 1; break;
-               case 0x00000900: type = DCB_OUTPUT_DP; mask = 2; break;
-               default:
-                       nv_error(priv, "unknown SOR mc 0x%08x\n", ctrl);
-                       return NULL;
-               }
-               or  -= 4;
-       } else {
-               or   = or - 8;
-               type = 0x0010;
-               mask = 0;
-               switch (ctrl & 0x00000f00) {
-               case 0x00000000: type |= priv->pior.type[or]; break;
-               default:
-                       nv_error(priv, "unknown PIOR mc 0x%08x\n", ctrl);
-                       return NULL;
-               }
-       }
-
-       mask  = 0x00c0 & (mask << 6);
-       mask |= 0x0001 << or;
-       mask |= 0x0100 << head;
-
-       list_for_each_entry(outp, &priv->base.outp, head) {
-               if ((outp->info.hasht & 0xff) == type &&
-                   (outp->info.hashm & mask) == mask) {
-                       *data = nvbios_outp_match(bios, outp->info.hasht,
-                                                       outp->info.hashm,
-                                                 ver, hdr, cnt, len, info);
-                       if (!*data)
-                               return NULL;
-                       return outp;
-               }
-       }
-
-       return NULL;
-}
-
-static struct nvkm_output *
-exec_script(struct nv50_disp_priv *priv, int head, int id)
-{
-       struct nouveau_bios *bios = nouveau_bios(priv);
-       struct nvkm_output *outp;
-       struct nvbios_outp info;
-       u8  ver, hdr, cnt, len;
-       u32 data, ctrl = 0;
-       u32 reg;
-       int i;
-
-       /* DAC */
-       for (i = 0; !(ctrl & (1 << head)) && i < priv->dac.nr; i++)
-               ctrl = nv_rd32(priv, 0x610b5c + (i * 8));
-
-       /* SOR */
-       if (!(ctrl & (1 << head))) {
-               if (nv_device(priv)->chipset  < 0x90 ||
-                   nv_device(priv)->chipset == 0x92 ||
-                   nv_device(priv)->chipset == 0xa0) {
-                       reg = 0x610b74;
-               } else {
-                       reg = 0x610798;
-               }
-               for (i = 0; !(ctrl & (1 << head)) && i < priv->sor.nr; i++)
-                       ctrl = nv_rd32(priv, reg + (i * 8));
-               i += 4;
-       }
-
-       /* PIOR */
-       if (!(ctrl & (1 << head))) {
-               for (i = 0; !(ctrl & (1 << head)) && i < priv->pior.nr; i++)
-                       ctrl = nv_rd32(priv, 0x610b84 + (i * 8));
-               i += 8;
-       }
-
-       if (!(ctrl & (1 << head)))
-               return NULL;
-       i--;
-
-       outp = exec_lookup(priv, head, i, ctrl, &data, &ver, &hdr, &cnt, &len, &info);
-       if (outp) {
-               struct nvbios_init init = {
-                       .subdev = nv_subdev(priv),
-                       .bios = bios,
-                       .offset = info.script[id],
-                       .outp = &outp->info,
-                       .crtc = head,
-                       .execute = 1,
-               };
-
-               nvbios_exec(&init);
-       }
-
-       return outp;
-}
-
-static struct nvkm_output *
-exec_clkcmp(struct nv50_disp_priv *priv, int head, int id, u32 pclk, u32 *conf)
-{
-       struct nouveau_bios *bios = nouveau_bios(priv);
-       struct nvkm_output *outp;
-       struct nvbios_outp info1;
-       struct nvbios_ocfg info2;
-       u8  ver, hdr, cnt, len;
-       u32 data, ctrl = 0;
-       u32 reg;
-       int i;
-
-       /* DAC */
-       for (i = 0; !(ctrl & (1 << head)) && i < priv->dac.nr; i++)
-               ctrl = nv_rd32(priv, 0x610b58 + (i * 8));
-
-       /* SOR */
-       if (!(ctrl & (1 << head))) {
-               if (nv_device(priv)->chipset  < 0x90 ||
-                   nv_device(priv)->chipset == 0x92 ||
-                   nv_device(priv)->chipset == 0xa0) {
-                       reg = 0x610b70;
-               } else {
-                       reg = 0x610794;
-               }
-               for (i = 0; !(ctrl & (1 << head)) && i < priv->sor.nr; i++)
-                       ctrl = nv_rd32(priv, reg + (i * 8));
-               i += 4;
-       }
-
-       /* PIOR */
-       if (!(ctrl & (1 << head))) {
-               for (i = 0; !(ctrl & (1 << head)) && i < priv->pior.nr; i++)
-                       ctrl = nv_rd32(priv, 0x610b80 + (i * 8));
-               i += 8;
-       }
-
-       if (!(ctrl & (1 << head)))
-               return NULL;
-       i--;
-
-       outp = exec_lookup(priv, head, i, ctrl, &data, &ver, &hdr, &cnt, &len, &info1);
-       if (!outp)
-               return NULL;
-
-       if (outp->info.location == 0) {
-               switch (outp->info.type) {
-               case DCB_OUTPUT_TMDS:
-                       *conf = (ctrl & 0x00000f00) >> 8;
-                       if (pclk >= 165000)
-                               *conf |= 0x0100;
-                       break;
-               case DCB_OUTPUT_LVDS:
-                       *conf = priv->sor.lvdsconf;
-                       break;
-               case DCB_OUTPUT_DP:
-                       *conf = (ctrl & 0x00000f00) >> 8;
-                       break;
-               case DCB_OUTPUT_ANALOG:
-               default:
-                       *conf = 0x00ff;
-                       break;
-               }
-       } else {
-               *conf = (ctrl & 0x00000f00) >> 8;
-               pclk = pclk / 2;
-       }
-
-       data = nvbios_ocfg_match(bios, data, *conf, &ver, &hdr, &cnt, &len, &info2);
-       if (data && id < 0xff) {
-               data = nvbios_oclk_match(bios, info2.clkcmp[id], pclk);
-               if (data) {
-                       struct nvbios_init init = {
-                               .subdev = nv_subdev(priv),
-                               .bios = bios,
-                               .offset = data,
-                               .outp = &outp->info,
-                               .crtc = head,
-                               .execute = 1,
-                       };
-
-                       nvbios_exec(&init);
-               }
-       }
-
-       return outp;
-}
-
-static void
-nv50_disp_intr_unk10_0(struct nv50_disp_priv *priv, int head)
-{
-       exec_script(priv, head, 1);
-}
-
-static void
-nv50_disp_intr_unk20_0(struct nv50_disp_priv *priv, int head)
-{
-       struct nvkm_output *outp = exec_script(priv, head, 2);
-
-       /* the binary driver does this outside of the supervisor handling
-        * (after the third supervisor from a detach).  we (currently?)
-        * allow both detach/attach to happen in the same set of
-        * supervisor interrupts, so it would make sense to execute this
-        * (full power down?) script after all the detach phases of the
-        * supervisor handling.  like with training if needed from the
-        * second supervisor, nvidia doesn't do this, so who knows if it's
-        * entirely safe, but it does appear to work..
-        *
-        * without this script being run, on some configurations i've
-        * seen, switching from DP to TMDS on a DP connector may result
-        * in a blank screen (SOR_PWR off/on can restore it)
-        */
-       if (outp && outp->info.type == DCB_OUTPUT_DP) {
-               struct nvkm_output_dp *outpdp = (void *)outp;
-               struct nvbios_init init = {
-                       .subdev = nv_subdev(priv),
-                       .bios = nouveau_bios(priv),
-                       .outp = &outp->info,
-                       .crtc = head,
-                       .offset = outpdp->info.script[4],
-                       .execute = 1,
-               };
-
-               nvbios_exec(&init);
-               atomic_set(&outpdp->lt.done, 0);
-       }
-}
-
-static void
-nv50_disp_intr_unk20_1(struct nv50_disp_priv *priv, int head)
-{
-       struct nouveau_devinit *devinit = nouveau_devinit(priv);
-       u32 pclk = nv_rd32(priv, 0x610ad0 + (head * 0x540)) & 0x3fffff;
-       if (pclk)
-               devinit->pll_set(devinit, PLL_VPLL0 + head, pclk);
-}
-
-static void
-nv50_disp_intr_unk20_2_dp(struct nv50_disp_priv *priv, int head,
-                         struct dcb_output *outp, u32 pclk)
-{
-       const int link = !(outp->sorconf.link & 1);
-       const int   or = ffs(outp->or) - 1;
-       const u32 soff = (  or * 0x800);
-       const u32 loff = (link * 0x080) + soff;
-       const u32 ctrl = nv_rd32(priv, 0x610794 + (or * 8));
-       const u32 symbol = 100000;
-       const s32 vactive = nv_rd32(priv, 0x610af8 + (head * 0x540)) & 0xffff;
-       const s32 vblanke = nv_rd32(priv, 0x610ae8 + (head * 0x540)) & 0xffff;
-       const s32 vblanks = nv_rd32(priv, 0x610af0 + (head * 0x540)) & 0xffff;
-       u32 dpctrl = nv_rd32(priv, 0x61c10c + loff);
-       u32 clksor = nv_rd32(priv, 0x614300 + soff);
-       int bestTU = 0, bestVTUi = 0, bestVTUf = 0, bestVTUa = 0;
-       int TU, VTUi, VTUf, VTUa;
-       u64 link_data_rate, link_ratio, unk;
-       u32 best_diff = 64 * symbol;
-       u32 link_nr, link_bw, bits;
-       u64 value;
-
-       link_bw = (clksor & 0x000c0000) ? 270000 : 162000;
-       link_nr = hweight32(dpctrl & 0x000f0000);
-
-       /* symbols/hblank - algorithm taken from comments in tegra driver */
-       value = vblanke + vactive - vblanks - 7;
-       value = value * link_bw;
-       do_div(value, pclk);
-       value = value - (3 * !!(dpctrl & 0x00004000)) - (12 / link_nr);
-       nv_mask(priv, 0x61c1e8 + soff, 0x0000ffff, value);
-
-       /* symbols/vblank - algorithm taken from comments in tegra driver */
-       value = vblanks - vblanke - 25;
-       value = value * link_bw;
-       do_div(value, pclk);
-       value = value - ((36 / link_nr) + 3) - 1;
-       nv_mask(priv, 0x61c1ec + soff, 0x00ffffff, value);
-
-       /* watermark / activesym */
-       if      ((ctrl & 0xf0000) == 0x60000) bits = 30;
-       else if ((ctrl & 0xf0000) == 0x50000) bits = 24;
-       else                                  bits = 18;
-
-       link_data_rate = (pclk * bits / 8) / link_nr;
-
-       /* calculate ratio of packed data rate to link symbol rate */
-       link_ratio = link_data_rate * symbol;
-       do_div(link_ratio, link_bw);
-
-       for (TU = 64; TU >= 32; TU--) {
-               /* calculate average number of valid symbols in each TU */
-               u32 tu_valid = link_ratio * TU;
-               u32 calc, diff;
-
-               /* find a hw representation for the fraction.. */
-               VTUi = tu_valid / symbol;
-               calc = VTUi * symbol;
-               diff = tu_valid - calc;
-               if (diff) {
-                       if (diff >= (symbol / 2)) {
-                               VTUf = symbol / (symbol - diff);
-                               if (symbol - (VTUf * diff))
-                                       VTUf++;
-
-                               if (VTUf <= 15) {
-                                       VTUa  = 1;
-                                       calc += symbol - (symbol / VTUf);
-                               } else {
-                                       VTUa  = 0;
-                                       VTUf  = 1;
-                                       calc += symbol;
-                               }
-                       } else {
-                               VTUa  = 0;
-                               VTUf  = min((int)(symbol / diff), 15);
-                               calc += symbol / VTUf;
-                       }
-
-                       diff = calc - tu_valid;
-               } else {
-                       /* no remainder, but the hw doesn't like the fractional
-                        * part to be zero.  decrement the integer part and
-                        * have the fraction add a whole symbol back
-                        */
-                       VTUa = 0;
-                       VTUf = 1;
-                       VTUi--;
-               }
-
-               if (diff < best_diff) {
-                       best_diff = diff;
-                       bestTU = TU;
-                       bestVTUa = VTUa;
-                       bestVTUf = VTUf;
-                       bestVTUi = VTUi;
-                       if (diff == 0)
-                               break;
-               }
-       }
-
-       if (!bestTU) {
-               nv_error(priv, "unable to find suitable dp config\n");
-               return;
-       }
-
-       /* XXX close to vbios numbers, but not right */
-       unk  = (symbol - link_ratio) * bestTU;
-       unk *= link_ratio;
-       do_div(unk, symbol);
-       do_div(unk, symbol);
-       unk += 6;
-
-       nv_mask(priv, 0x61c10c + loff, 0x000001fc, bestTU << 2);
-       nv_mask(priv, 0x61c128 + loff, 0x010f7f3f, bestVTUa << 24 |
-                                                  bestVTUf << 16 |
-                                                  bestVTUi << 8 | unk);
-}
-
-static void
-nv50_disp_intr_unk20_2(struct nv50_disp_priv *priv, int head)
-{
-       struct nvkm_output *outp;
-       u32 pclk = nv_rd32(priv, 0x610ad0 + (head * 0x540)) & 0x3fffff;
-       u32 hval, hreg = 0x614200 + (head * 0x800);
-       u32 oval, oreg;
-       u32 mask, conf;
-
-       outp = exec_clkcmp(priv, head, 0xff, pclk, &conf);
-       if (!outp)
-               return;
-
-       /* we allow both encoder attach and detach operations to occur
-        * within a single supervisor (ie. modeset) sequence.  the
-        * encoder detach scripts quite often switch off power to the
-        * lanes, which requires the link to be re-trained.
-        *
-        * this is not generally an issue as the sink "must" (heh)
-        * signal an irq when it's lost sync so the driver can
-        * re-train.
-        *
-        * however, on some boards, if one does not configure at least
-        * the gpu side of the link *before* attaching, then various
-        * things can go horribly wrong (PDISP disappearing from mmio,
-        * third supervisor never happens, etc).
-        *
-        * the solution is simply to retrain here, if necessary.  last
-        * i checked, the binary driver userspace does not appear to
-        * trigger this situation (it forces an UPDATE between steps).
-        */
-       if (outp->info.type == DCB_OUTPUT_DP) {
-               u32 soff = (ffs(outp->info.or) - 1) * 0x08;
-               u32 ctrl, datarate;
-
-               if (outp->info.location == 0) {
-                       ctrl = nv_rd32(priv, 0x610794 + soff);
-                       soff = 1;
-               } else {
-                       ctrl = nv_rd32(priv, 0x610b80 + soff);
-                       soff = 2;
-               }
-
-               switch ((ctrl & 0x000f0000) >> 16) {
-               case 6: datarate = pclk * 30; break;
-               case 5: datarate = pclk * 24; break;
-               case 2:
-               default:
-                       datarate = pclk * 18;
-                       break;
-               }
-
-               if (nvkm_output_dp_train(outp, datarate / soff, true))
-                       ERR("link not trained before attach\n");
-       }
-
-       exec_clkcmp(priv, head, 0, pclk, &conf);
-
-       if (!outp->info.location && outp->info.type == DCB_OUTPUT_ANALOG) {
-               oreg = 0x614280 + (ffs(outp->info.or) - 1) * 0x800;
-               oval = 0x00000000;
-               hval = 0x00000000;
-               mask = 0xffffffff;
-       } else
-       if (!outp->info.location) {
-               if (outp->info.type == DCB_OUTPUT_DP)
-                       nv50_disp_intr_unk20_2_dp(priv, head, &outp->info, pclk);
-               oreg = 0x614300 + (ffs(outp->info.or) - 1) * 0x800;
-               oval = (conf & 0x0100) ? 0x00000101 : 0x00000000;
-               hval = 0x00000000;
-               mask = 0x00000707;
-       } else {
-               oreg = 0x614380 + (ffs(outp->info.or) - 1) * 0x800;
-               oval = 0x00000001;
-               hval = 0x00000001;
-               mask = 0x00000707;
-       }
-
-       nv_mask(priv, hreg, 0x0000000f, hval);
-       nv_mask(priv, oreg, mask, oval);
-}
-
-/* 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_disp_intr_unk40_0_tmds(struct nv50_disp_priv *priv, struct dcb_output *outp)
-{
-       struct nouveau_bios *bios = nouveau_bios(priv);
-       const int link = !(outp->sorconf.link & 1);
-       const int   or = ffs(outp->or) - 1;
-       const u32 loff = (or * 0x800) + (link * 0x80);
-       const u16 mask = (outp->sorconf.link << 6) | outp->or;
-       struct dcb_output match;
-       u8  ver, hdr;
-
-       if (dcb_outp_match(bios, DCB_OUTPUT_DP, mask, &ver, &hdr, &match))
-               nv_mask(priv, 0x61c10c + loff, 0x00000001, 0x00000000);
-}
-
-static void
-nv50_disp_intr_unk40_0(struct nv50_disp_priv *priv, int head)
-{
-       struct nvkm_output *outp;
-       u32 pclk = nv_rd32(priv, 0x610ad0 + (head * 0x540)) & 0x3fffff;
-       u32 conf;
-
-       outp = exec_clkcmp(priv, head, 1, pclk, &conf);
-       if (!outp)
-               return;
-
-       if (outp->info.location == 0 && outp->info.type == DCB_OUTPUT_TMDS)
-               nv50_disp_intr_unk40_0_tmds(priv, &outp->info);
-}
-
-void
-nv50_disp_intr_supervisor(struct work_struct *work)
-{
-       struct nv50_disp_priv *priv =
-               container_of(work, struct nv50_disp_priv, supervisor);
-       struct nv50_disp_impl *impl = (void *)nv_object(priv)->oclass;
-       u32 super = nv_rd32(priv, 0x610030);
-       int head;
-
-       nv_debug(priv, "supervisor 0x%08x 0x%08x\n", priv->super, super);
-
-       if (priv->super & 0x00000010) {
-               nv50_disp_mthd_chan(priv, NV_DBG_DEBUG, 0, impl->mthd.core);
-               for (head = 0; head < priv->head.nr; head++) {
-                       if (!(super & (0x00000020 << head)))
-                               continue;
-                       if (!(super & (0x00000080 << head)))
-                               continue;
-                       nv50_disp_intr_unk10_0(priv, head);
-               }
-       } else
-       if (priv->super & 0x00000020) {
-               for (head = 0; head < priv->head.nr; head++) {
-                       if (!(super & (0x00000080 << head)))
-                               continue;
-                       nv50_disp_intr_unk20_0(priv, head);
-               }
-               for (head = 0; head < priv->head.nr; head++) {
-                       if (!(super & (0x00000200 << head)))
-                               continue;
-                       nv50_disp_intr_unk20_1(priv, head);
-               }
-               for (head = 0; head < priv->head.nr; head++) {
-                       if (!(super & (0x00000080 << head)))
-                               continue;
-                       nv50_disp_intr_unk20_2(priv, head);
-               }
-       } else
-       if (priv->super & 0x00000040) {
-               for (head = 0; head < priv->head.nr; head++) {
-                       if (!(super & (0x00000080 << head)))
-                               continue;
-                       nv50_disp_intr_unk40_0(priv, head);
-               }
-       }
-
-       nv_wr32(priv, 0x610030, 0x80000000);
-}
-
-void
-nv50_disp_intr(struct nouveau_subdev *subdev)
-{
-       struct nv50_disp_priv *priv = (void *)subdev;
-       u32 intr0 = nv_rd32(priv, 0x610020);
-       u32 intr1 = nv_rd32(priv, 0x610024);
-
-       while (intr0 & 0x001f0000) {
-               u32 chid = __ffs(intr0 & 0x001f0000) - 16;
-               nv50_disp_intr_error(priv, chid);
-               intr0 &= ~(0x00010000 << chid);
-       }
-
-       while (intr0 & 0x0000001f) {
-               u32 chid = __ffs(intr0 & 0x0000001f);
-               nv50_disp_chan_uevent_send(priv, chid);
-               intr0 &= ~(0x00000001 << chid);
-       }
-
-       if (intr1 & 0x00000004) {
-               nouveau_disp_vblank(&priv->base, 0);
-               nv_wr32(priv, 0x610024, 0x00000004);
-               intr1 &= ~0x00000004;
-       }
-
-       if (intr1 & 0x00000008) {
-               nouveau_disp_vblank(&priv->base, 1);
-               nv_wr32(priv, 0x610024, 0x00000008);
-               intr1 &= ~0x00000008;
-       }
-
-       if (intr1 & 0x00000070) {
-               priv->super = (intr1 & 0x00000070);
-               schedule_work(&priv->supervisor);
-               nv_wr32(priv, 0x610024, priv->super);
-               intr1 &= ~0x00000070;
-       }
-}
-
-static int
-nv50_disp_ctor(struct nouveau_object *parent, struct nouveau_object *engine,
-              struct nouveau_oclass *oclass, void *data, u32 size,
-              struct nouveau_object **pobject)
-{
-       struct nv50_disp_priv *priv;
-       int ret;
-
-       ret = nouveau_disp_create(parent, engine, oclass, 2, "PDISP",
-                                 "display", &priv);
-       *pobject = nv_object(priv);
-       if (ret)
-               return ret;
-
-       ret = nvkm_event_init(&nv50_disp_chan_uevent, 1, 9, &priv->uevent);
-       if (ret)
-               return ret;
-
-       nv_engine(priv)->sclass = nv50_disp_main_oclass;
-       nv_engine(priv)->cclass = &nv50_disp_cclass;
-       nv_subdev(priv)->intr = nv50_disp_intr;
-       INIT_WORK(&priv->supervisor, nv50_disp_intr_supervisor);
-       priv->sclass = nv50_disp_sclass;
-       priv->head.nr = 2;
-       priv->dac.nr = 3;
-       priv->sor.nr = 2;
-       priv->pior.nr = 3;
-       priv->dac.power = nv50_dac_power;
-       priv->dac.sense = nv50_dac_sense;
-       priv->sor.power = nv50_sor_power;
-       priv->pior.power = nv50_pior_power;
-       return 0;
-}
-
-struct nouveau_oclass *
-nv50_disp_outp_sclass[] = {
-       &nv50_pior_dp_impl.base.base,
-       NULL
-};
-
-struct nouveau_oclass *
-nv50_disp_oclass = &(struct nv50_disp_impl) {
-       .base.base.handle = NV_ENGINE(DISP, 0x50),
-       .base.base.ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nv50_disp_ctor,
-               .dtor = _nouveau_disp_dtor,
-               .init = _nouveau_disp_init,
-               .fini = _nouveau_disp_fini,
-       },
-       .base.vblank = &nv50_disp_vblank_func,
-       .base.outp =  nv50_disp_outp_sclass,
-       .mthd.core = &nv50_disp_core_mthd_chan,
-       .mthd.base = &nv50_disp_base_mthd_chan,
-       .mthd.ovly = &nv50_disp_ovly_mthd_chan,
-       .mthd.prev = 0x000004,
-       .head.scanoutpos = nv50_disp_main_scanoutpos,
-}.base.base;
diff --git a/drivers/gpu/drm/nouveau/core/engine/disp/nv50.h b/drivers/gpu/drm/nouveau/core/engine/disp/nv50.h
deleted file mode 100644 (file)
index 7f08078..0000000
+++ /dev/null
@@ -1,252 +0,0 @@
-#ifndef __NV50_DISP_H__
-#define __NV50_DISP_H__
-
-#include <core/parent.h>
-#include <core/namedb.h>
-#include <core/engctx.h>
-#include <core/ramht.h>
-#include <core/event.h>
-
-#include <engine/dmaobj.h>
-
-#include "dport.h"
-#include "priv.h"
-#include "outp.h"
-#include "outpdp.h"
-
-#define NV50_DISP_MTHD_ struct nouveau_object *object,                         \
-       struct nv50_disp_priv *priv, void *data, u32 size
-#define NV50_DISP_MTHD_V0 NV50_DISP_MTHD_, int head
-#define NV50_DISP_MTHD_V1 NV50_DISP_MTHD_, int head, struct nvkm_output *outp
-
-struct nv50_disp_priv {
-       struct nouveau_disp base;
-       struct nouveau_oclass *sclass;
-
-       struct work_struct supervisor;
-       u32 super;
-
-       struct nvkm_event uevent;
-
-       struct {
-               int nr;
-       } head;
-       struct {
-               int nr;
-               int (*power)(NV50_DISP_MTHD_V1);
-               int (*sense)(NV50_DISP_MTHD_V1);
-       } dac;
-       struct {
-               int nr;
-               int (*power)(NV50_DISP_MTHD_V1);
-               int (*hda_eld)(NV50_DISP_MTHD_V1);
-               int (*hdmi)(NV50_DISP_MTHD_V1);
-               u32 lvdsconf;
-               void (*magic)(struct nvkm_output *);
-       } sor;
-       struct {
-               int nr;
-               int (*power)(NV50_DISP_MTHD_V1);
-               u8 type[3];
-       } pior;
-};
-
-struct nv50_disp_impl {
-       struct nouveau_disp_impl base;
-       struct {
-               const struct nv50_disp_mthd_chan *core;
-               const struct nv50_disp_mthd_chan *base;
-               const struct nv50_disp_mthd_chan *ovly;
-               int prev;
-       } mthd;
-       struct {
-               int (*scanoutpos)(NV50_DISP_MTHD_V0);
-       } head;
-};
-
-int nv50_disp_main_scanoutpos(NV50_DISP_MTHD_V0);
-int nv50_disp_main_mthd(struct nouveau_object *, u32, void *, u32);
-
-int nvd0_disp_main_scanoutpos(NV50_DISP_MTHD_V0);
-
-int nv50_dac_power(NV50_DISP_MTHD_V1);
-int nv50_dac_sense(NV50_DISP_MTHD_V1);
-
-int nva3_hda_eld(NV50_DISP_MTHD_V1);
-int nvd0_hda_eld(NV50_DISP_MTHD_V1);
-
-int nv84_hdmi_ctrl(NV50_DISP_MTHD_V1);
-int nva3_hdmi_ctrl(NV50_DISP_MTHD_V1);
-int nvd0_hdmi_ctrl(NV50_DISP_MTHD_V1);
-int nve0_hdmi_ctrl(NV50_DISP_MTHD_V1);
-
-int nv50_sor_power(NV50_DISP_MTHD_V1);
-
-int nv94_sor_dp_train_init(struct nv50_disp_priv *, int, int, int, u16, u16,
-                          u32, struct dcb_output *);
-int nv94_sor_dp_train_fini(struct nv50_disp_priv *, int, int, int, u16, u16,
-                          u32, struct dcb_output *);
-int nv94_sor_dp_train(struct nv50_disp_priv *, int, int, u16, u16, u32,
-                     struct dcb_output *);
-int nv94_sor_dp_lnkctl(struct nv50_disp_priv *, int, int, int, u16, u16, u32,
-                      struct dcb_output *);
-int nv94_sor_dp_drvctl(struct nv50_disp_priv *, int, int, int, u16, u16, u32,
-                      struct dcb_output *);
-
-int nvd0_sor_dp_train(struct nv50_disp_priv *, int, int, u16, u16, u32,
-                     struct dcb_output *);
-int nvd0_sor_dp_lnkctl(struct nv50_disp_priv *, int, int, int, u16, u16, u32,
-                      struct dcb_output *);
-int nvd0_sor_dp_drvctl(struct nv50_disp_priv *, int, int, int, u16, u16, u32,
-                      struct dcb_output *);
-
-int nv50_pior_power(NV50_DISP_MTHD_V1);
-
-struct nv50_disp_base {
-       struct nouveau_parent base;
-       struct nouveau_ramht *ramht;
-       u32 chan;
-};
-
-struct nv50_disp_chan_impl {
-       struct nouveau_ofuncs base;
-       int chid;
-       int  (*attach)(struct nouveau_object *, struct nouveau_object *, u32);
-       void (*detach)(struct nouveau_object *, int);
-};
-
-struct nv50_disp_chan {
-       struct nouveau_namedb base;
-       int chid;
-};
-
-int  nv50_disp_chan_ntfy(struct nouveau_object *, u32, struct nvkm_event **);
-int  nv50_disp_chan_map(struct nouveau_object *, u64 *, u32 *);
-u32  nv50_disp_chan_rd32(struct nouveau_object *, u64);
-void nv50_disp_chan_wr32(struct nouveau_object *, u64, u32);
-extern const struct nvkm_event_func nv50_disp_chan_uevent;
-int  nv50_disp_chan_uevent_ctor(struct nouveau_object *, void *, u32,
-                               struct nvkm_notify *);
-void nv50_disp_chan_uevent_send(struct nv50_disp_priv *, int);
-
-extern const struct nvkm_event_func nvd0_disp_chan_uevent;
-
-#define nv50_disp_chan_init(a)                                                 \
-       nouveau_namedb_init(&(a)->base)
-#define nv50_disp_chan_fini(a,b)                                               \
-       nouveau_namedb_fini(&(a)->base, (b))
-
-struct nv50_disp_dmac {
-       struct nv50_disp_chan base;
-       struct nouveau_dmaobj *pushdma;
-       u32 push;
-};
-
-void nv50_disp_dmac_dtor(struct nouveau_object *);
-
-struct nv50_disp_pioc {
-       struct nv50_disp_chan base;
-};
-
-void nv50_disp_pioc_dtor(struct nouveau_object *);
-
-struct nv50_disp_mthd_list {
-       u32 mthd;
-       u32 addr;
-       struct {
-               u32 mthd;
-               u32 addr;
-               const char *name;
-       } data[];
-};
-
-struct nv50_disp_mthd_chan {
-       const char *name;
-       u32 addr;
-       struct {
-               const char *name;
-               int nr;
-               const struct nv50_disp_mthd_list *mthd;
-       } data[];
-};
-
-extern struct nv50_disp_chan_impl nv50_disp_core_ofuncs;
-int nv50_disp_core_ctor(struct nouveau_object *, struct nouveau_object *,
-                       struct nouveau_oclass *, void *, u32,
-                       struct nouveau_object **);
-extern const struct nv50_disp_mthd_list nv50_disp_core_mthd_base;
-extern const struct nv50_disp_mthd_list nv50_disp_core_mthd_sor;
-extern const struct nv50_disp_mthd_list nv50_disp_core_mthd_pior;
-extern struct nv50_disp_chan_impl nv50_disp_base_ofuncs;
-int nv50_disp_base_ctor(struct nouveau_object *, struct nouveau_object *,
-                       struct nouveau_oclass *, void *, u32,
-                       struct nouveau_object **);
-extern const struct nv50_disp_mthd_list nv50_disp_base_mthd_image;
-extern struct nv50_disp_chan_impl nv50_disp_ovly_ofuncs;
-int nv50_disp_ovly_ctor(struct nouveau_object *, struct nouveau_object *,
-                       struct nouveau_oclass *, void *, u32,
-                       struct nouveau_object **);
-extern const struct nv50_disp_mthd_list nv50_disp_ovly_mthd_base;
-extern struct nv50_disp_chan_impl nv50_disp_oimm_ofuncs;
-int nv50_disp_oimm_ctor(struct nouveau_object *, struct nouveau_object *,
-                       struct nouveau_oclass *, void *, u32,
-                       struct nouveau_object **);
-extern struct nv50_disp_chan_impl nv50_disp_curs_ofuncs;
-int nv50_disp_curs_ctor(struct nouveau_object *, struct nouveau_object *,
-                       struct nouveau_oclass *, void *, u32,
-                       struct nouveau_object **);
-extern struct nouveau_ofuncs nv50_disp_main_ofuncs;
-int  nv50_disp_main_ctor(struct nouveau_object *, struct nouveau_object *,
-                        struct nouveau_oclass *, void *, u32,
-                        struct nouveau_object **);
-void nv50_disp_main_dtor(struct nouveau_object *);
-extern struct nouveau_omthds nv50_disp_main_omthds[];
-extern struct nouveau_oclass nv50_disp_cclass;
-void nv50_disp_mthd_chan(struct nv50_disp_priv *, int debug, int head,
-                        const struct nv50_disp_mthd_chan *);
-void nv50_disp_intr_supervisor(struct work_struct *);
-void nv50_disp_intr(struct nouveau_subdev *);
-extern const struct nvkm_event_func nv50_disp_vblank_func;
-
-extern const struct nv50_disp_mthd_chan nv84_disp_core_mthd_chan;
-extern const struct nv50_disp_mthd_list nv84_disp_core_mthd_dac;
-extern const struct nv50_disp_mthd_list nv84_disp_core_mthd_head;
-extern const struct nv50_disp_mthd_chan nv84_disp_base_mthd_chan;
-extern const struct nv50_disp_mthd_chan nv84_disp_ovly_mthd_chan;
-
-extern const struct nv50_disp_mthd_chan nv94_disp_core_mthd_chan;
-
-extern struct nv50_disp_chan_impl nvd0_disp_core_ofuncs;
-extern const struct nv50_disp_mthd_list nvd0_disp_core_mthd_base;
-extern const struct nv50_disp_mthd_list nvd0_disp_core_mthd_dac;
-extern const struct nv50_disp_mthd_list nvd0_disp_core_mthd_sor;
-extern const struct nv50_disp_mthd_list nvd0_disp_core_mthd_pior;
-extern struct nv50_disp_chan_impl nvd0_disp_base_ofuncs;
-extern struct nv50_disp_chan_impl nvd0_disp_ovly_ofuncs;
-extern const struct nv50_disp_mthd_chan nvd0_disp_base_mthd_chan;
-extern struct nv50_disp_chan_impl nvd0_disp_oimm_ofuncs;
-extern struct nv50_disp_chan_impl nvd0_disp_curs_ofuncs;
-extern struct nouveau_ofuncs nvd0_disp_main_ofuncs;
-extern struct nouveau_oclass nvd0_disp_cclass;
-void nvd0_disp_intr_supervisor(struct work_struct *);
-void nvd0_disp_intr(struct nouveau_subdev *);
-extern const struct nvkm_event_func nvd0_disp_vblank_func;
-
-extern const struct nv50_disp_mthd_chan nve0_disp_core_mthd_chan;
-extern const struct nv50_disp_mthd_chan nve0_disp_ovly_mthd_chan;
-
-extern struct nvkm_output_dp_impl nv50_pior_dp_impl;
-extern struct nouveau_oclass *nv50_disp_outp_sclass[];
-
-extern struct nvkm_output_dp_impl nv94_sor_dp_impl;
-int nv94_sor_dp_lnk_pwr(struct nvkm_output_dp *, int);
-extern struct nouveau_oclass *nv94_disp_outp_sclass[];
-
-extern struct nvkm_output_dp_impl nvd0_sor_dp_impl;
-int nvd0_sor_dp_lnk_ctl(struct nvkm_output_dp *, int, int, bool);
-extern struct nouveau_oclass *nvd0_disp_outp_sclass[];
-
-void gm204_sor_magic(struct nvkm_output *outp);
-extern struct nvkm_output_dp_impl gm204_sor_dp_impl;
-
-#endif
diff --git a/drivers/gpu/drm/nouveau/core/engine/disp/nv84.c b/drivers/gpu/drm/nouveau/core/engine/disp/nv84.c
deleted file mode 100644 (file)
index 13eff5e..0000000
+++ /dev/null
@@ -1,276 +0,0 @@
-/*
- * Copyright 2012 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 <engine/software.h>
-#include <engine/disp.h>
-
-#include <nvif/class.h>
-
-#include "nv50.h"
-
-/*******************************************************************************
- * EVO master channel object
- ******************************************************************************/
-
-const struct nv50_disp_mthd_list
-nv84_disp_core_mthd_dac = {
-       .mthd = 0x0080,
-       .addr = 0x000008,
-       .data = {
-               { 0x0400, 0x610b58 },
-               { 0x0404, 0x610bdc },
-               { 0x0420, 0x610bc4 },
-               {}
-       }
-};
-
-const struct nv50_disp_mthd_list
-nv84_disp_core_mthd_head = {
-       .mthd = 0x0400,
-       .addr = 0x000540,
-       .data = {
-               { 0x0800, 0x610ad8 },
-               { 0x0804, 0x610ad0 },
-               { 0x0808, 0x610a48 },
-               { 0x080c, 0x610a78 },
-               { 0x0810, 0x610ac0 },
-               { 0x0814, 0x610af8 },
-               { 0x0818, 0x610b00 },
-               { 0x081c, 0x610ae8 },
-               { 0x0820, 0x610af0 },
-               { 0x0824, 0x610b08 },
-               { 0x0828, 0x610b10 },
-               { 0x082c, 0x610a68 },
-               { 0x0830, 0x610a60 },
-               { 0x0834, 0x000000 },
-               { 0x0838, 0x610a40 },
-               { 0x0840, 0x610a24 },
-               { 0x0844, 0x610a2c },
-               { 0x0848, 0x610aa8 },
-               { 0x084c, 0x610ab0 },
-               { 0x085c, 0x610c5c },
-               { 0x0860, 0x610a84 },
-               { 0x0864, 0x610a90 },
-               { 0x0868, 0x610b18 },
-               { 0x086c, 0x610b20 },
-               { 0x0870, 0x610ac8 },
-               { 0x0874, 0x610a38 },
-               { 0x0878, 0x610c50 },
-               { 0x0880, 0x610a58 },
-               { 0x0884, 0x610a9c },
-               { 0x089c, 0x610c68 },
-               { 0x08a0, 0x610a70 },
-               { 0x08a4, 0x610a50 },
-               { 0x08a8, 0x610ae0 },
-               { 0x08c0, 0x610b28 },
-               { 0x08c4, 0x610b30 },
-               { 0x08c8, 0x610b40 },
-               { 0x08d4, 0x610b38 },
-               { 0x08d8, 0x610b48 },
-               { 0x08dc, 0x610b50 },
-               { 0x0900, 0x610a18 },
-               { 0x0904, 0x610ab8 },
-               { 0x0910, 0x610c70 },
-               { 0x0914, 0x610c78 },
-               {}
-       }
-};
-
-const struct nv50_disp_mthd_chan
-nv84_disp_core_mthd_chan = {
-       .name = "Core",
-       .addr = 0x000000,
-       .data = {
-               { "Global", 1, &nv50_disp_core_mthd_base },
-               {    "DAC", 3, &nv84_disp_core_mthd_dac  },
-               {    "SOR", 2, &nv50_disp_core_mthd_sor  },
-               {   "PIOR", 3, &nv50_disp_core_mthd_pior },
-               {   "HEAD", 2, &nv84_disp_core_mthd_head },
-               {}
-       }
-};
-
-/*******************************************************************************
- * EVO sync channel objects
- ******************************************************************************/
-
-static const struct nv50_disp_mthd_list
-nv84_disp_base_mthd_base = {
-       .mthd = 0x0000,
-       .addr = 0x000000,
-       .data = {
-               { 0x0080, 0x000000 },
-               { 0x0084, 0x0008c4 },
-               { 0x0088, 0x0008d0 },
-               { 0x008c, 0x0008dc },
-               { 0x0090, 0x0008e4 },
-               { 0x0094, 0x610884 },
-               { 0x00a0, 0x6108a0 },
-               { 0x00a4, 0x610878 },
-               { 0x00c0, 0x61086c },
-               { 0x00c4, 0x610800 },
-               { 0x00c8, 0x61080c },
-               { 0x00cc, 0x610818 },
-               { 0x00e0, 0x610858 },
-               { 0x00e4, 0x610860 },
-               { 0x00e8, 0x6108ac },
-               { 0x00ec, 0x6108b4 },
-               { 0x00fc, 0x610824 },
-               { 0x0100, 0x610894 },
-               { 0x0104, 0x61082c },
-               { 0x0110, 0x6108bc },
-               { 0x0114, 0x61088c },
-               {}
-       }
-};
-
-const struct nv50_disp_mthd_chan
-nv84_disp_base_mthd_chan = {
-       .name = "Base",
-       .addr = 0x000540,
-       .data = {
-               { "Global", 1, &nv84_disp_base_mthd_base },
-               {  "Image", 2, &nv50_disp_base_mthd_image },
-               {}
-       }
-};
-
-/*******************************************************************************
- * EVO overlay channel objects
- ******************************************************************************/
-
-static const struct nv50_disp_mthd_list
-nv84_disp_ovly_mthd_base = {
-       .mthd = 0x0000,
-       .addr = 0x000000,
-       .data = {
-               { 0x0080, 0x000000 },
-               { 0x0084, 0x6109a0 },
-               { 0x0088, 0x6109c0 },
-               { 0x008c, 0x6109c8 },
-               { 0x0090, 0x6109b4 },
-               { 0x0094, 0x610970 },
-               { 0x00a0, 0x610998 },
-               { 0x00a4, 0x610964 },
-               { 0x00c0, 0x610958 },
-               { 0x00e0, 0x6109a8 },
-               { 0x00e4, 0x6109d0 },
-               { 0x00e8, 0x6109d8 },
-               { 0x0100, 0x61094c },
-               { 0x0104, 0x610984 },
-               { 0x0108, 0x61098c },
-               { 0x0800, 0x6109f8 },
-               { 0x0808, 0x610a08 },
-               { 0x080c, 0x610a10 },
-               { 0x0810, 0x610a00 },
-               {}
-       }
-};
-
-const struct nv50_disp_mthd_chan
-nv84_disp_ovly_mthd_chan = {
-       .name = "Overlay",
-       .addr = 0x000540,
-       .data = {
-               { "Global", 1, &nv84_disp_ovly_mthd_base },
-               {}
-       }
-};
-
-/*******************************************************************************
- * Base display object
- ******************************************************************************/
-
-static struct nouveau_oclass
-nv84_disp_sclass[] = {
-       { G82_DISP_CORE_CHANNEL_DMA, &nv50_disp_core_ofuncs.base },
-       { G82_DISP_BASE_CHANNEL_DMA, &nv50_disp_base_ofuncs.base },
-       { G82_DISP_OVERLAY_CHANNEL_DMA, &nv50_disp_ovly_ofuncs.base },
-       { G82_DISP_OVERLAY, &nv50_disp_oimm_ofuncs.base },
-       { G82_DISP_CURSOR, &nv50_disp_curs_ofuncs.base },
-       {}
-};
-
-static struct nouveau_oclass
-nv84_disp_main_oclass[] = {
-       { G82_DISP, &nv50_disp_main_ofuncs },
-       {}
-};
-
-/*******************************************************************************
- * Display engine implementation
- ******************************************************************************/
-
-static int
-nv84_disp_ctor(struct nouveau_object *parent, struct nouveau_object *engine,
-              struct nouveau_oclass *oclass, void *data, u32 size,
-              struct nouveau_object **pobject)
-{
-       struct nv50_disp_priv *priv;
-       int ret;
-
-       ret = nouveau_disp_create(parent, engine, oclass, 2, "PDISP",
-                                 "display", &priv);
-       *pobject = nv_object(priv);
-       if (ret)
-               return ret;
-
-       ret = nvkm_event_init(&nv50_disp_chan_uevent, 1, 9, &priv->uevent);
-       if (ret)
-               return ret;
-
-       nv_engine(priv)->sclass = nv84_disp_main_oclass;
-       nv_engine(priv)->cclass = &nv50_disp_cclass;
-       nv_subdev(priv)->intr = nv50_disp_intr;
-       INIT_WORK(&priv->supervisor, nv50_disp_intr_supervisor);
-       priv->sclass = nv84_disp_sclass;
-       priv->head.nr = 2;
-       priv->dac.nr = 3;
-       priv->sor.nr = 2;
-       priv->pior.nr = 3;
-       priv->dac.power = nv50_dac_power;
-       priv->dac.sense = nv50_dac_sense;
-       priv->sor.power = nv50_sor_power;
-       priv->sor.hdmi = nv84_hdmi_ctrl;
-       priv->pior.power = nv50_pior_power;
-       return 0;
-}
-
-struct nouveau_oclass *
-nv84_disp_oclass = &(struct nv50_disp_impl) {
-       .base.base.handle = NV_ENGINE(DISP, 0x82),
-       .base.base.ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nv84_disp_ctor,
-               .dtor = _nouveau_disp_dtor,
-               .init = _nouveau_disp_init,
-               .fini = _nouveau_disp_fini,
-       },
-       .base.vblank = &nv50_disp_vblank_func,
-       .base.outp =  nv50_disp_outp_sclass,
-       .mthd.core = &nv84_disp_core_mthd_chan,
-       .mthd.base = &nv84_disp_base_mthd_chan,
-       .mthd.ovly = &nv84_disp_ovly_mthd_chan,
-       .mthd.prev = 0x000004,
-       .head.scanoutpos = nv50_disp_main_scanoutpos,
-}.base.base;
diff --git a/drivers/gpu/drm/nouveau/core/engine/disp/nv94.c b/drivers/gpu/drm/nouveau/core/engine/disp/nv94.c
deleted file mode 100644 (file)
index 2bb7ac5..0000000
+++ /dev/null
@@ -1,142 +0,0 @@
-/*
- * Copyright 2012 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 <engine/software.h>
-#include <engine/disp.h>
-
-#include <nvif/class.h>
-
-#include "nv50.h"
-
-/*******************************************************************************
- * EVO master channel object
- ******************************************************************************/
-
-const struct nv50_disp_mthd_list
-nv94_disp_core_mthd_sor = {
-       .mthd = 0x0040,
-       .addr = 0x000008,
-       .data = {
-               { 0x0600, 0x610794 },
-               {}
-       }
-};
-
-const struct nv50_disp_mthd_chan
-nv94_disp_core_mthd_chan = {
-       .name = "Core",
-       .addr = 0x000000,
-       .data = {
-               { "Global", 1, &nv50_disp_core_mthd_base },
-               {    "DAC", 3, &nv84_disp_core_mthd_dac  },
-               {    "SOR", 4, &nv94_disp_core_mthd_sor  },
-               {   "PIOR", 3, &nv50_disp_core_mthd_pior },
-               {   "HEAD", 2, &nv84_disp_core_mthd_head },
-               {}
-       }
-};
-
-/*******************************************************************************
- * Base display object
- ******************************************************************************/
-
-static struct nouveau_oclass
-nv94_disp_sclass[] = {
-       { GT206_DISP_CORE_CHANNEL_DMA, &nv50_disp_core_ofuncs.base },
-       { GT200_DISP_BASE_CHANNEL_DMA, &nv50_disp_base_ofuncs.base },
-       { GT200_DISP_OVERLAY_CHANNEL_DMA, &nv50_disp_ovly_ofuncs.base },
-       { G82_DISP_OVERLAY, &nv50_disp_oimm_ofuncs.base },
-       { G82_DISP_CURSOR, &nv50_disp_curs_ofuncs.base },
-       {}
-};
-
-static struct nouveau_oclass
-nv94_disp_main_oclass[] = {
-       { GT206_DISP, &nv50_disp_main_ofuncs },
-       {}
-};
-
-/*******************************************************************************
- * Display engine implementation
- ******************************************************************************/
-
-static int
-nv94_disp_ctor(struct nouveau_object *parent, struct nouveau_object *engine,
-              struct nouveau_oclass *oclass, void *data, u32 size,
-              struct nouveau_object **pobject)
-{
-       struct nv50_disp_priv *priv;
-       int ret;
-
-       ret = nouveau_disp_create(parent, engine, oclass, 2, "PDISP",
-                                 "display", &priv);
-       *pobject = nv_object(priv);
-       if (ret)
-               return ret;
-
-       ret = nvkm_event_init(&nv50_disp_chan_uevent, 1, 9, &priv->uevent);
-       if (ret)
-               return ret;
-
-       nv_engine(priv)->sclass = nv94_disp_main_oclass;
-       nv_engine(priv)->cclass = &nv50_disp_cclass;
-       nv_subdev(priv)->intr = nv50_disp_intr;
-       INIT_WORK(&priv->supervisor, nv50_disp_intr_supervisor);
-       priv->sclass = nv94_disp_sclass;
-       priv->head.nr = 2;
-       priv->dac.nr = 3;
-       priv->sor.nr = 4;
-       priv->pior.nr = 3;
-       priv->dac.power = nv50_dac_power;
-       priv->dac.sense = nv50_dac_sense;
-       priv->sor.power = nv50_sor_power;
-       priv->sor.hdmi = nv84_hdmi_ctrl;
-       priv->pior.power = nv50_pior_power;
-       return 0;
-}
-
-struct nouveau_oclass *
-nv94_disp_outp_sclass[] = {
-       &nv50_pior_dp_impl.base.base,
-       &nv94_sor_dp_impl.base.base,
-       NULL
-};
-
-struct nouveau_oclass *
-nv94_disp_oclass = &(struct nv50_disp_impl) {
-       .base.base.handle = NV_ENGINE(DISP, 0x88),
-       .base.base.ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nv94_disp_ctor,
-               .dtor = _nouveau_disp_dtor,
-               .init = _nouveau_disp_init,
-               .fini = _nouveau_disp_fini,
-       },
-       .base.vblank = &nv50_disp_vblank_func,
-       .base.outp =  nv94_disp_outp_sclass,
-       .mthd.core = &nv94_disp_core_mthd_chan,
-       .mthd.base = &nv84_disp_base_mthd_chan,
-       .mthd.ovly = &nv84_disp_ovly_mthd_chan,
-       .mthd.prev = 0x000004,
-       .head.scanoutpos = nv50_disp_main_scanoutpos,
-}.base.base;
diff --git a/drivers/gpu/drm/nouveau/core/engine/disp/nva0.c b/drivers/gpu/drm/nouveau/core/engine/disp/nva0.c
deleted file mode 100644 (file)
index b32456c..0000000
+++ /dev/null
@@ -1,152 +0,0 @@
-/*
- * Copyright 2012 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 <engine/software.h>
-#include <engine/disp.h>
-
-#include <nvif/class.h>
-
-#include "nv50.h"
-
-/*******************************************************************************
- * EVO overlay channel objects
- ******************************************************************************/
-
-static const struct nv50_disp_mthd_list
-nva0_disp_ovly_mthd_base = {
-       .mthd = 0x0000,
-       .addr = 0x000000,
-       .data = {
-               { 0x0080, 0x000000 },
-               { 0x0084, 0x6109a0 },
-               { 0x0088, 0x6109c0 },
-               { 0x008c, 0x6109c8 },
-               { 0x0090, 0x6109b4 },
-               { 0x0094, 0x610970 },
-               { 0x00a0, 0x610998 },
-               { 0x00a4, 0x610964 },
-               { 0x00b0, 0x610c98 },
-               { 0x00b4, 0x610ca4 },
-               { 0x00b8, 0x610cac },
-               { 0x00c0, 0x610958 },
-               { 0x00e0, 0x6109a8 },
-               { 0x00e4, 0x6109d0 },
-               { 0x00e8, 0x6109d8 },
-               { 0x0100, 0x61094c },
-               { 0x0104, 0x610984 },
-               { 0x0108, 0x61098c },
-               { 0x0800, 0x6109f8 },
-               { 0x0808, 0x610a08 },
-               { 0x080c, 0x610a10 },
-               { 0x0810, 0x610a00 },
-               {}
-       }
-};
-
-static const struct nv50_disp_mthd_chan
-nva0_disp_ovly_mthd_chan = {
-       .name = "Overlay",
-       .addr = 0x000540,
-       .data = {
-               { "Global", 1, &nva0_disp_ovly_mthd_base },
-               {}
-       }
-};
-
-/*******************************************************************************
- * Base display object
- ******************************************************************************/
-
-static struct nouveau_oclass
-nva0_disp_sclass[] = {
-       { GT200_DISP_CORE_CHANNEL_DMA, &nv50_disp_core_ofuncs.base },
-       { GT200_DISP_BASE_CHANNEL_DMA, &nv50_disp_base_ofuncs.base },
-       { GT200_DISP_OVERLAY_CHANNEL_DMA, &nv50_disp_ovly_ofuncs.base },
-       { G82_DISP_OVERLAY, &nv50_disp_oimm_ofuncs.base },
-       { G82_DISP_CURSOR, &nv50_disp_curs_ofuncs.base },
-       {}
-};
-
-static struct nouveau_oclass
-nva0_disp_main_oclass[] = {
-       { GT200_DISP, &nv50_disp_main_ofuncs },
-       {}
-};
-
-/*******************************************************************************
- * Display engine implementation
- ******************************************************************************/
-
-static int
-nva0_disp_ctor(struct nouveau_object *parent, struct nouveau_object *engine,
-              struct nouveau_oclass *oclass, void *data, u32 size,
-              struct nouveau_object **pobject)
-{
-       struct nv50_disp_priv *priv;
-       int ret;
-
-       ret = nouveau_disp_create(parent, engine, oclass, 2, "PDISP",
-                                 "display", &priv);
-       *pobject = nv_object(priv);
-       if (ret)
-               return ret;
-
-       ret = nvkm_event_init(&nv50_disp_chan_uevent, 1, 9, &priv->uevent);
-       if (ret)
-               return ret;
-
-       nv_engine(priv)->sclass = nva0_disp_main_oclass;
-       nv_engine(priv)->cclass = &nv50_disp_cclass;
-       nv_subdev(priv)->intr = nv50_disp_intr;
-       INIT_WORK(&priv->supervisor, nv50_disp_intr_supervisor);
-       priv->sclass = nva0_disp_sclass;
-       priv->head.nr = 2;
-       priv->dac.nr = 3;
-       priv->sor.nr = 2;
-       priv->pior.nr = 3;
-       priv->dac.power = nv50_dac_power;
-       priv->dac.sense = nv50_dac_sense;
-       priv->sor.power = nv50_sor_power;
-       priv->sor.hdmi = nv84_hdmi_ctrl;
-       priv->pior.power = nv50_pior_power;
-       return 0;
-}
-
-struct nouveau_oclass *
-nva0_disp_oclass = &(struct nv50_disp_impl) {
-       .base.base.handle = NV_ENGINE(DISP, 0x83),
-       .base.base.ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nva0_disp_ctor,
-               .dtor = _nouveau_disp_dtor,
-               .init = _nouveau_disp_init,
-               .fini = _nouveau_disp_fini,
-       },
-       .base.vblank = &nv50_disp_vblank_func,
-       .base.outp =  nv50_disp_outp_sclass,
-       .mthd.core = &nv84_disp_core_mthd_chan,
-       .mthd.base = &nv84_disp_base_mthd_chan,
-       .mthd.ovly = &nva0_disp_ovly_mthd_chan,
-       .mthd.prev = 0x000004,
-       .head.scanoutpos = nv50_disp_main_scanoutpos,
-}.base.base;
diff --git a/drivers/gpu/drm/nouveau/core/engine/disp/nva3.c b/drivers/gpu/drm/nouveau/core/engine/disp/nva3.c
deleted file mode 100644 (file)
index 951d79f..0000000
+++ /dev/null
@@ -1,108 +0,0 @@
-/*
- * Copyright 2012 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 <engine/software.h>
-#include <engine/disp.h>
-
-#include <nvif/class.h>
-
-#include "nv50.h"
-
-/*******************************************************************************
- * Base display object
- ******************************************************************************/
-
-static struct nouveau_oclass
-nva3_disp_sclass[] = {
-       { GT214_DISP_CORE_CHANNEL_DMA, &nv50_disp_core_ofuncs.base },
-       { GT214_DISP_BASE_CHANNEL_DMA, &nv50_disp_base_ofuncs.base },
-       { GT214_DISP_OVERLAY_CHANNEL_DMA, &nv50_disp_ovly_ofuncs.base },
-       { GT214_DISP_OVERLAY, &nv50_disp_oimm_ofuncs.base },
-       { GT214_DISP_CURSOR, &nv50_disp_curs_ofuncs.base },
-       {}
-};
-
-static struct nouveau_oclass
-nva3_disp_main_oclass[] = {
-       { GT214_DISP, &nv50_disp_main_ofuncs },
-       {}
-};
-
-/*******************************************************************************
- * Display engine implementation
- ******************************************************************************/
-
-static int
-nva3_disp_ctor(struct nouveau_object *parent, struct nouveau_object *engine,
-              struct nouveau_oclass *oclass, void *data, u32 size,
-              struct nouveau_object **pobject)
-{
-       struct nv50_disp_priv *priv;
-       int ret;
-
-       ret = nouveau_disp_create(parent, engine, oclass, 2, "PDISP",
-                                 "display", &priv);
-       *pobject = nv_object(priv);
-       if (ret)
-               return ret;
-
-       ret = nvkm_event_init(&nv50_disp_chan_uevent, 1, 9, &priv->uevent);
-       if (ret)
-               return ret;
-
-       nv_engine(priv)->sclass = nva3_disp_main_oclass;
-       nv_engine(priv)->cclass = &nv50_disp_cclass;
-       nv_subdev(priv)->intr = nv50_disp_intr;
-       INIT_WORK(&priv->supervisor, nv50_disp_intr_supervisor);
-       priv->sclass = nva3_disp_sclass;
-       priv->head.nr = 2;
-       priv->dac.nr = 3;
-       priv->sor.nr = 4;
-       priv->pior.nr = 3;
-       priv->dac.power = nv50_dac_power;
-       priv->dac.sense = nv50_dac_sense;
-       priv->sor.power = nv50_sor_power;
-       priv->sor.hda_eld = nva3_hda_eld;
-       priv->sor.hdmi = nva3_hdmi_ctrl;
-       priv->pior.power = nv50_pior_power;
-       return 0;
-}
-
-struct nouveau_oclass *
-nva3_disp_oclass = &(struct nv50_disp_impl) {
-       .base.base.handle = NV_ENGINE(DISP, 0x85),
-       .base.base.ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nva3_disp_ctor,
-               .dtor = _nouveau_disp_dtor,
-               .init = _nouveau_disp_init,
-               .fini = _nouveau_disp_fini,
-       },
-       .base.vblank = &nv50_disp_vblank_func,
-       .base.outp =  nv94_disp_outp_sclass,
-       .mthd.core = &nv94_disp_core_mthd_chan,
-       .mthd.base = &nv84_disp_base_mthd_chan,
-       .mthd.ovly = &nv84_disp_ovly_mthd_chan,
-       .mthd.prev = 0x000004,
-       .head.scanoutpos = nv50_disp_main_scanoutpos,
-}.base.base;
diff --git a/drivers/gpu/drm/nouveau/core/engine/disp/nvd0.c b/drivers/gpu/drm/nouveau/core/engine/disp/nvd0.c
deleted file mode 100644 (file)
index 181a2d5..0000000
+++ /dev/null
@@ -1,1313 +0,0 @@
-/*
- * Copyright 2012 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 <core/object.h>
-#include <core/client.h>
-#include <core/parent.h>
-#include <core/handle.h>
-#include <nvif/unpack.h>
-#include <nvif/class.h>
-
-#include <engine/disp.h>
-
-#include <subdev/bios.h>
-#include <subdev/bios/dcb.h>
-#include <subdev/bios/disp.h>
-#include <subdev/bios/init.h>
-#include <subdev/bios/pll.h>
-#include <subdev/devinit.h>
-#include <subdev/fb.h>
-#include <subdev/timer.h>
-
-#include "nv50.h"
-
-/*******************************************************************************
- * EVO channel base class
- ******************************************************************************/
-
-static void
-nvd0_disp_chan_uevent_fini(struct nvkm_event *event, int type, int index)
-{
-       struct nv50_disp_priv *priv = container_of(event, typeof(*priv), uevent);
-       nv_mask(priv, 0x610090, 0x00000001 << index, 0x00000000 << index);
-       nv_wr32(priv, 0x61008c, 0x00000001 << index);
-}
-
-static void
-nvd0_disp_chan_uevent_init(struct nvkm_event *event, int types, int index)
-{
-       struct nv50_disp_priv *priv = container_of(event, typeof(*priv), uevent);
-       nv_wr32(priv, 0x61008c, 0x00000001 << index);
-       nv_mask(priv, 0x610090, 0x00000001 << index, 0x00000001 << index);
-}
-
-const struct nvkm_event_func
-nvd0_disp_chan_uevent = {
-       .ctor = nv50_disp_chan_uevent_ctor,
-       .init = nvd0_disp_chan_uevent_init,
-       .fini = nvd0_disp_chan_uevent_fini,
-};
-
-/*******************************************************************************
- * EVO DMA channel base class
- ******************************************************************************/
-
-static int
-nvd0_disp_dmac_object_attach(struct nouveau_object *parent,
-                            struct nouveau_object *object, u32 name)
-{
-       struct nv50_disp_base *base = (void *)parent->parent;
-       struct nv50_disp_chan *chan = (void *)parent;
-       u32 addr = nv_gpuobj(object)->node->offset;
-       u32 data = (chan->chid << 27) | (addr << 9) | 0x00000001;
-       return nouveau_ramht_insert(base->ramht, chan->chid, name, data);
-}
-
-static void
-nvd0_disp_dmac_object_detach(struct nouveau_object *parent, int cookie)
-{
-       struct nv50_disp_base *base = (void *)parent->parent;
-       nouveau_ramht_remove(base->ramht, cookie);
-}
-
-static int
-nvd0_disp_dmac_init(struct nouveau_object *object)
-{
-       struct nv50_disp_priv *priv = (void *)object->engine;
-       struct nv50_disp_dmac *dmac = (void *)object;
-       int chid = dmac->base.chid;
-       int ret;
-
-       ret = nv50_disp_chan_init(&dmac->base);
-       if (ret)
-               return ret;
-
-       /* enable error reporting */
-       nv_mask(priv, 0x6100a0, 0x00000001 << chid, 0x00000001 << chid);
-
-       /* initialise channel for dma command submission */
-       nv_wr32(priv, 0x610494 + (chid * 0x0010), dmac->push);
-       nv_wr32(priv, 0x610498 + (chid * 0x0010), 0x00010000);
-       nv_wr32(priv, 0x61049c + (chid * 0x0010), 0x00000001);
-       nv_mask(priv, 0x610490 + (chid * 0x0010), 0x00000010, 0x00000010);
-       nv_wr32(priv, 0x640000 + (chid * 0x1000), 0x00000000);
-       nv_wr32(priv, 0x610490 + (chid * 0x0010), 0x00000013);
-
-       /* wait for it to go inactive */
-       if (!nv_wait(priv, 0x610490 + (chid * 0x10), 0x80000000, 0x00000000)) {
-               nv_error(dmac, "init: 0x%08x\n",
-                        nv_rd32(priv, 0x610490 + (chid * 0x10)));
-               return -EBUSY;
-       }
-
-       return 0;
-}
-
-static int
-nvd0_disp_dmac_fini(struct nouveau_object *object, bool suspend)
-{
-       struct nv50_disp_priv *priv = (void *)object->engine;
-       struct nv50_disp_dmac *dmac = (void *)object;
-       int chid = dmac->base.chid;
-
-       /* deactivate channel */
-       nv_mask(priv, 0x610490 + (chid * 0x0010), 0x00001010, 0x00001000);
-       nv_mask(priv, 0x610490 + (chid * 0x0010), 0x00000003, 0x00000000);
-       if (!nv_wait(priv, 0x610490 + (chid * 0x10), 0x001e0000, 0x00000000)) {
-               nv_error(dmac, "fini: 0x%08x\n",
-                        nv_rd32(priv, 0x610490 + (chid * 0x10)));
-               if (suspend)
-                       return -EBUSY;
-       }
-
-       /* disable error reporting and completion notification */
-       nv_mask(priv, 0x610090, 0x00000001 << chid, 0x00000000);
-       nv_mask(priv, 0x6100a0, 0x00000001 << chid, 0x00000000);
-
-       return nv50_disp_chan_fini(&dmac->base, suspend);
-}
-
-/*******************************************************************************
- * EVO master channel object
- ******************************************************************************/
-
-const struct nv50_disp_mthd_list
-nvd0_disp_core_mthd_base = {
-       .mthd = 0x0000,
-       .addr = 0x000000,
-       .data = {
-               { 0x0080, 0x660080 },
-               { 0x0084, 0x660084 },
-               { 0x0088, 0x660088 },
-               { 0x008c, 0x000000 },
-               {}
-       }
-};
-
-const struct nv50_disp_mthd_list
-nvd0_disp_core_mthd_dac = {
-       .mthd = 0x0020,
-       .addr = 0x000020,
-       .data = {
-               { 0x0180, 0x660180 },
-               { 0x0184, 0x660184 },
-               { 0x0188, 0x660188 },
-               { 0x0190, 0x660190 },
-               {}
-       }
-};
-
-const struct nv50_disp_mthd_list
-nvd0_disp_core_mthd_sor = {
-       .mthd = 0x0020,
-       .addr = 0x000020,
-       .data = {
-               { 0x0200, 0x660200 },
-               { 0x0204, 0x660204 },
-               { 0x0208, 0x660208 },
-               { 0x0210, 0x660210 },
-               {}
-       }
-};
-
-const struct nv50_disp_mthd_list
-nvd0_disp_core_mthd_pior = {
-       .mthd = 0x0020,
-       .addr = 0x000020,
-       .data = {
-               { 0x0300, 0x660300 },
-               { 0x0304, 0x660304 },
-               { 0x0308, 0x660308 },
-               { 0x0310, 0x660310 },
-               {}
-       }
-};
-
-static const struct nv50_disp_mthd_list
-nvd0_disp_core_mthd_head = {
-       .mthd = 0x0300,
-       .addr = 0x000300,
-       .data = {
-               { 0x0400, 0x660400 },
-               { 0x0404, 0x660404 },
-               { 0x0408, 0x660408 },
-               { 0x040c, 0x66040c },
-               { 0x0410, 0x660410 },
-               { 0x0414, 0x660414 },
-               { 0x0418, 0x660418 },
-               { 0x041c, 0x66041c },
-               { 0x0420, 0x660420 },
-               { 0x0424, 0x660424 },
-               { 0x0428, 0x660428 },
-               { 0x042c, 0x66042c },
-               { 0x0430, 0x660430 },
-               { 0x0434, 0x660434 },
-               { 0x0438, 0x660438 },
-               { 0x0440, 0x660440 },
-               { 0x0444, 0x660444 },
-               { 0x0448, 0x660448 },
-               { 0x044c, 0x66044c },
-               { 0x0450, 0x660450 },
-               { 0x0454, 0x660454 },
-               { 0x0458, 0x660458 },
-               { 0x045c, 0x66045c },
-               { 0x0460, 0x660460 },
-               { 0x0468, 0x660468 },
-               { 0x046c, 0x66046c },
-               { 0x0470, 0x660470 },
-               { 0x0474, 0x660474 },
-               { 0x0480, 0x660480 },
-               { 0x0484, 0x660484 },
-               { 0x048c, 0x66048c },
-               { 0x0490, 0x660490 },
-               { 0x0494, 0x660494 },
-               { 0x0498, 0x660498 },
-               { 0x04b0, 0x6604b0 },
-               { 0x04b8, 0x6604b8 },
-               { 0x04bc, 0x6604bc },
-               { 0x04c0, 0x6604c0 },
-               { 0x04c4, 0x6604c4 },
-               { 0x04c8, 0x6604c8 },
-               { 0x04d0, 0x6604d0 },
-               { 0x04d4, 0x6604d4 },
-               { 0x04e0, 0x6604e0 },
-               { 0x04e4, 0x6604e4 },
-               { 0x04e8, 0x6604e8 },
-               { 0x04ec, 0x6604ec },
-               { 0x04f0, 0x6604f0 },
-               { 0x04f4, 0x6604f4 },
-               { 0x04f8, 0x6604f8 },
-               { 0x04fc, 0x6604fc },
-               { 0x0500, 0x660500 },
-               { 0x0504, 0x660504 },
-               { 0x0508, 0x660508 },
-               { 0x050c, 0x66050c },
-               { 0x0510, 0x660510 },
-               { 0x0514, 0x660514 },
-               { 0x0518, 0x660518 },
-               { 0x051c, 0x66051c },
-               { 0x052c, 0x66052c },
-               { 0x0530, 0x660530 },
-               { 0x054c, 0x66054c },
-               { 0x0550, 0x660550 },
-               { 0x0554, 0x660554 },
-               { 0x0558, 0x660558 },
-               { 0x055c, 0x66055c },
-               {}
-       }
-};
-
-static const struct nv50_disp_mthd_chan
-nvd0_disp_core_mthd_chan = {
-       .name = "Core",
-       .addr = 0x000000,
-       .data = {
-               { "Global", 1, &nvd0_disp_core_mthd_base },
-               {    "DAC", 3, &nvd0_disp_core_mthd_dac  },
-               {    "SOR", 8, &nvd0_disp_core_mthd_sor  },
-               {   "PIOR", 4, &nvd0_disp_core_mthd_pior },
-               {   "HEAD", 4, &nvd0_disp_core_mthd_head },
-               {}
-       }
-};
-
-static int
-nvd0_disp_core_init(struct nouveau_object *object)
-{
-       struct nv50_disp_priv *priv = (void *)object->engine;
-       struct nv50_disp_dmac *mast = (void *)object;
-       int ret;
-
-       ret = nv50_disp_chan_init(&mast->base);
-       if (ret)
-               return ret;
-
-       /* enable error reporting */
-       nv_mask(priv, 0x6100a0, 0x00000001, 0x00000001);
-
-       /* initialise channel for dma command submission */
-       nv_wr32(priv, 0x610494, mast->push);
-       nv_wr32(priv, 0x610498, 0x00010000);
-       nv_wr32(priv, 0x61049c, 0x00000001);
-       nv_mask(priv, 0x610490, 0x00000010, 0x00000010);
-       nv_wr32(priv, 0x640000, 0x00000000);
-       nv_wr32(priv, 0x610490, 0x01000013);
-
-       /* wait for it to go inactive */
-       if (!nv_wait(priv, 0x610490, 0x80000000, 0x00000000)) {
-               nv_error(mast, "init: 0x%08x\n", nv_rd32(priv, 0x610490));
-               return -EBUSY;
-       }
-
-       return 0;
-}
-
-static int
-nvd0_disp_core_fini(struct nouveau_object *object, bool suspend)
-{
-       struct nv50_disp_priv *priv = (void *)object->engine;
-       struct nv50_disp_dmac *mast = (void *)object;
-
-       /* deactivate channel */
-       nv_mask(priv, 0x610490, 0x00000010, 0x00000000);
-       nv_mask(priv, 0x610490, 0x00000003, 0x00000000);
-       if (!nv_wait(priv, 0x610490, 0x001e0000, 0x00000000)) {
-               nv_error(mast, "fini: 0x%08x\n", nv_rd32(priv, 0x610490));
-               if (suspend)
-                       return -EBUSY;
-       }
-
-       /* disable error reporting and completion notification */
-       nv_mask(priv, 0x610090, 0x00000001, 0x00000000);
-       nv_mask(priv, 0x6100a0, 0x00000001, 0x00000000);
-
-       return nv50_disp_chan_fini(&mast->base, suspend);
-}
-
-struct nv50_disp_chan_impl
-nvd0_disp_core_ofuncs = {
-       .base.ctor = nv50_disp_core_ctor,
-       .base.dtor = nv50_disp_dmac_dtor,
-       .base.init = nvd0_disp_core_init,
-       .base.fini = nvd0_disp_core_fini,
-       .base.ntfy = nv50_disp_chan_ntfy,
-       .base.map  = nv50_disp_chan_map,
-       .base.rd32 = nv50_disp_chan_rd32,
-       .base.wr32 = nv50_disp_chan_wr32,
-       .chid = 0,
-       .attach = nvd0_disp_dmac_object_attach,
-       .detach = nvd0_disp_dmac_object_detach,
-};
-
-/*******************************************************************************
- * EVO sync channel objects
- ******************************************************************************/
-
-static const struct nv50_disp_mthd_list
-nvd0_disp_base_mthd_base = {
-       .mthd = 0x0000,
-       .addr = 0x000000,
-       .data = {
-               { 0x0080, 0x661080 },
-               { 0x0084, 0x661084 },
-               { 0x0088, 0x661088 },
-               { 0x008c, 0x66108c },
-               { 0x0090, 0x661090 },
-               { 0x0094, 0x661094 },
-               { 0x00a0, 0x6610a0 },
-               { 0x00a4, 0x6610a4 },
-               { 0x00c0, 0x6610c0 },
-               { 0x00c4, 0x6610c4 },
-               { 0x00c8, 0x6610c8 },
-               { 0x00cc, 0x6610cc },
-               { 0x00e0, 0x6610e0 },
-               { 0x00e4, 0x6610e4 },
-               { 0x00e8, 0x6610e8 },
-               { 0x00ec, 0x6610ec },
-               { 0x00fc, 0x6610fc },
-               { 0x0100, 0x661100 },
-               { 0x0104, 0x661104 },
-               { 0x0108, 0x661108 },
-               { 0x010c, 0x66110c },
-               { 0x0110, 0x661110 },
-               { 0x0114, 0x661114 },
-               { 0x0118, 0x661118 },
-               { 0x011c, 0x66111c },
-               { 0x0130, 0x661130 },
-               { 0x0134, 0x661134 },
-               { 0x0138, 0x661138 },
-               { 0x013c, 0x66113c },
-               { 0x0140, 0x661140 },
-               { 0x0144, 0x661144 },
-               { 0x0148, 0x661148 },
-               { 0x014c, 0x66114c },
-               { 0x0150, 0x661150 },
-               { 0x0154, 0x661154 },
-               { 0x0158, 0x661158 },
-               { 0x015c, 0x66115c },
-               { 0x0160, 0x661160 },
-               { 0x0164, 0x661164 },
-               { 0x0168, 0x661168 },
-               { 0x016c, 0x66116c },
-               {}
-       }
-};
-
-static const struct nv50_disp_mthd_list
-nvd0_disp_base_mthd_image = {
-       .mthd = 0x0400,
-       .addr = 0x000400,
-       .data = {
-               { 0x0400, 0x661400 },
-               { 0x0404, 0x661404 },
-               { 0x0408, 0x661408 },
-               { 0x040c, 0x66140c },
-               { 0x0410, 0x661410 },
-               {}
-       }
-};
-
-const struct nv50_disp_mthd_chan
-nvd0_disp_base_mthd_chan = {
-       .name = "Base",
-       .addr = 0x001000,
-       .data = {
-               { "Global", 1, &nvd0_disp_base_mthd_base },
-               {  "Image", 2, &nvd0_disp_base_mthd_image },
-               {}
-       }
-};
-
-struct nv50_disp_chan_impl
-nvd0_disp_base_ofuncs = {
-       .base.ctor = nv50_disp_base_ctor,
-       .base.dtor = nv50_disp_dmac_dtor,
-       .base.init = nvd0_disp_dmac_init,
-       .base.fini = nvd0_disp_dmac_fini,
-       .base.ntfy = nv50_disp_chan_ntfy,
-       .base.map  = nv50_disp_chan_map,
-       .base.rd32 = nv50_disp_chan_rd32,
-       .base.wr32 = nv50_disp_chan_wr32,
-       .chid = 1,
-       .attach = nvd0_disp_dmac_object_attach,
-       .detach = nvd0_disp_dmac_object_detach,
-};
-
-/*******************************************************************************
- * EVO overlay channel objects
- ******************************************************************************/
-
-static const struct nv50_disp_mthd_list
-nvd0_disp_ovly_mthd_base = {
-       .mthd = 0x0000,
-       .data = {
-               { 0x0080, 0x665080 },
-               { 0x0084, 0x665084 },
-               { 0x0088, 0x665088 },
-               { 0x008c, 0x66508c },
-               { 0x0090, 0x665090 },
-               { 0x0094, 0x665094 },
-               { 0x00a0, 0x6650a0 },
-               { 0x00a4, 0x6650a4 },
-               { 0x00b0, 0x6650b0 },
-               { 0x00b4, 0x6650b4 },
-               { 0x00b8, 0x6650b8 },
-               { 0x00c0, 0x6650c0 },
-               { 0x00e0, 0x6650e0 },
-               { 0x00e4, 0x6650e4 },
-               { 0x00e8, 0x6650e8 },
-               { 0x0100, 0x665100 },
-               { 0x0104, 0x665104 },
-               { 0x0108, 0x665108 },
-               { 0x010c, 0x66510c },
-               { 0x0110, 0x665110 },
-               { 0x0118, 0x665118 },
-               { 0x011c, 0x66511c },
-               { 0x0120, 0x665120 },
-               { 0x0124, 0x665124 },
-               { 0x0130, 0x665130 },
-               { 0x0134, 0x665134 },
-               { 0x0138, 0x665138 },
-               { 0x013c, 0x66513c },
-               { 0x0140, 0x665140 },
-               { 0x0144, 0x665144 },
-               { 0x0148, 0x665148 },
-               { 0x014c, 0x66514c },
-               { 0x0150, 0x665150 },
-               { 0x0154, 0x665154 },
-               { 0x0158, 0x665158 },
-               { 0x015c, 0x66515c },
-               { 0x0160, 0x665160 },
-               { 0x0164, 0x665164 },
-               { 0x0168, 0x665168 },
-               { 0x016c, 0x66516c },
-               { 0x0400, 0x665400 },
-               { 0x0408, 0x665408 },
-               { 0x040c, 0x66540c },
-               { 0x0410, 0x665410 },
-               {}
-       }
-};
-
-static const struct nv50_disp_mthd_chan
-nvd0_disp_ovly_mthd_chan = {
-       .name = "Overlay",
-       .addr = 0x001000,
-       .data = {
-               { "Global", 1, &nvd0_disp_ovly_mthd_base },
-               {}
-       }
-};
-
-struct nv50_disp_chan_impl
-nvd0_disp_ovly_ofuncs = {
-       .base.ctor = nv50_disp_ovly_ctor,
-       .base.dtor = nv50_disp_dmac_dtor,
-       .base.init = nvd0_disp_dmac_init,
-       .base.fini = nvd0_disp_dmac_fini,
-       .base.ntfy = nv50_disp_chan_ntfy,
-       .base.map  = nv50_disp_chan_map,
-       .base.rd32 = nv50_disp_chan_rd32,
-       .base.wr32 = nv50_disp_chan_wr32,
-       .chid = 5,
-       .attach = nvd0_disp_dmac_object_attach,
-       .detach = nvd0_disp_dmac_object_detach,
-};
-
-/*******************************************************************************
- * EVO PIO channel base class
- ******************************************************************************/
-
-static int
-nvd0_disp_pioc_init(struct nouveau_object *object)
-{
-       struct nv50_disp_priv *priv = (void *)object->engine;
-       struct nv50_disp_pioc *pioc = (void *)object;
-       int chid = pioc->base.chid;
-       int ret;
-
-       ret = nv50_disp_chan_init(&pioc->base);
-       if (ret)
-               return ret;
-
-       /* enable error reporting */
-       nv_mask(priv, 0x6100a0, 0x00000001 << chid, 0x00000001 << chid);
-
-       /* activate channel */
-       nv_wr32(priv, 0x610490 + (chid * 0x10), 0x00000001);
-       if (!nv_wait(priv, 0x610490 + (chid * 0x10), 0x00030000, 0x00010000)) {
-               nv_error(pioc, "init: 0x%08x\n",
-                        nv_rd32(priv, 0x610490 + (chid * 0x10)));
-               return -EBUSY;
-       }
-
-       return 0;
-}
-
-static int
-nvd0_disp_pioc_fini(struct nouveau_object *object, bool suspend)
-{
-       struct nv50_disp_priv *priv = (void *)object->engine;
-       struct nv50_disp_pioc *pioc = (void *)object;
-       int chid = pioc->base.chid;
-
-       nv_mask(priv, 0x610490 + (chid * 0x10), 0x00000001, 0x00000000);
-       if (!nv_wait(priv, 0x610490 + (chid * 0x10), 0x00030000, 0x00000000)) {
-               nv_error(pioc, "timeout: 0x%08x\n",
-                        nv_rd32(priv, 0x610490 + (chid * 0x10)));
-               if (suspend)
-                       return -EBUSY;
-       }
-
-       /* disable error reporting and completion notification */
-       nv_mask(priv, 0x610090, 0x00000001 << chid, 0x00000000);
-       nv_mask(priv, 0x6100a0, 0x00000001 << chid, 0x00000000);
-
-       return nv50_disp_chan_fini(&pioc->base, suspend);
-}
-
-/*******************************************************************************
- * EVO immediate overlay channel objects
- ******************************************************************************/
-
-struct nv50_disp_chan_impl
-nvd0_disp_oimm_ofuncs = {
-       .base.ctor = nv50_disp_oimm_ctor,
-       .base.dtor = nv50_disp_pioc_dtor,
-       .base.init = nvd0_disp_pioc_init,
-       .base.fini = nvd0_disp_pioc_fini,
-       .base.ntfy = nv50_disp_chan_ntfy,
-       .base.map  = nv50_disp_chan_map,
-       .base.rd32 = nv50_disp_chan_rd32,
-       .base.wr32 = nv50_disp_chan_wr32,
-       .chid = 9,
-};
-
-/*******************************************************************************
- * EVO cursor channel objects
- ******************************************************************************/
-
-struct nv50_disp_chan_impl
-nvd0_disp_curs_ofuncs = {
-       .base.ctor = nv50_disp_curs_ctor,
-       .base.dtor = nv50_disp_pioc_dtor,
-       .base.init = nvd0_disp_pioc_init,
-       .base.fini = nvd0_disp_pioc_fini,
-       .base.ntfy = nv50_disp_chan_ntfy,
-       .base.map  = nv50_disp_chan_map,
-       .base.rd32 = nv50_disp_chan_rd32,
-       .base.wr32 = nv50_disp_chan_wr32,
-       .chid = 13,
-};
-
-/*******************************************************************************
- * Base display object
- ******************************************************************************/
-
-int
-nvd0_disp_main_scanoutpos(NV50_DISP_MTHD_V0)
-{
-       const u32 total  = nv_rd32(priv, 0x640414 + (head * 0x300));
-       const u32 blanke = nv_rd32(priv, 0x64041c + (head * 0x300));
-       const u32 blanks = nv_rd32(priv, 0x640420 + (head * 0x300));
-       union {
-               struct nv04_disp_scanoutpos_v0 v0;
-       } *args = data;
-       int ret;
-
-       nv_ioctl(object, "disp scanoutpos size %d\n", size);
-       if (nvif_unpack(args->v0, 0, 0, false)) {
-               nv_ioctl(object, "disp scanoutpos vers %d\n", args->v0.version);
-               args->v0.vblanke = (blanke & 0xffff0000) >> 16;
-               args->v0.hblanke = (blanke & 0x0000ffff);
-               args->v0.vblanks = (blanks & 0xffff0000) >> 16;
-               args->v0.hblanks = (blanks & 0x0000ffff);
-               args->v0.vtotal  = ( total & 0xffff0000) >> 16;
-               args->v0.htotal  = ( total & 0x0000ffff);
-               args->v0.time[0] = ktime_to_ns(ktime_get());
-               args->v0.vline = /* vline read locks hline */
-                       nv_rd32(priv, 0x616340 + (head * 0x800)) & 0xffff;
-               args->v0.time[1] = ktime_to_ns(ktime_get());
-               args->v0.hline =
-                       nv_rd32(priv, 0x616344 + (head * 0x800)) & 0xffff;
-       } else
-               return ret;
-
-       return 0;
-}
-
-static int
-nvd0_disp_main_init(struct nouveau_object *object)
-{
-       struct nv50_disp_priv *priv = (void *)object->engine;
-       struct nv50_disp_base *base = (void *)object;
-       int ret, i;
-       u32 tmp;
-
-       ret = nouveau_parent_init(&base->base);
-       if (ret)
-               return ret;
-
-       /* The below segments of code copying values from one register to
-        * another appear to inform EVO of the display capabilities or
-        * something similar.
-        */
-
-       /* ... CRTC caps */
-       for (i = 0; i < priv->head.nr; i++) {
-               tmp = nv_rd32(priv, 0x616104 + (i * 0x800));
-               nv_wr32(priv, 0x6101b4 + (i * 0x800), tmp);
-               tmp = nv_rd32(priv, 0x616108 + (i * 0x800));
-               nv_wr32(priv, 0x6101b8 + (i * 0x800), tmp);
-               tmp = nv_rd32(priv, 0x61610c + (i * 0x800));
-               nv_wr32(priv, 0x6101bc + (i * 0x800), tmp);
-       }
-
-       /* ... DAC caps */
-       for (i = 0; i < priv->dac.nr; i++) {
-               tmp = nv_rd32(priv, 0x61a000 + (i * 0x800));
-               nv_wr32(priv, 0x6101c0 + (i * 0x800), tmp);
-       }
-
-       /* ... SOR caps */
-       for (i = 0; i < priv->sor.nr; i++) {
-               tmp = nv_rd32(priv, 0x61c000 + (i * 0x800));
-               nv_wr32(priv, 0x6301c4 + (i * 0x800), tmp);
-       }
-
-       /* steal display away from vbios, or something like that */
-       if (nv_rd32(priv, 0x6100ac) & 0x00000100) {
-               nv_wr32(priv, 0x6100ac, 0x00000100);
-               nv_mask(priv, 0x6194e8, 0x00000001, 0x00000000);
-               if (!nv_wait(priv, 0x6194e8, 0x00000002, 0x00000000)) {
-                       nv_error(priv, "timeout acquiring display\n");
-                       return -EBUSY;
-               }
-       }
-
-       /* point at display engine memory area (hash table, objects) */
-       nv_wr32(priv, 0x610010, (nv_gpuobj(object->parent)->addr >> 8) | 9);
-
-       /* enable supervisor interrupts, disable everything else */
-       nv_wr32(priv, 0x610090, 0x00000000);
-       nv_wr32(priv, 0x6100a0, 0x00000000);
-       nv_wr32(priv, 0x6100b0, 0x00000307);
-
-       /* disable underflow reporting, preventing an intermittent issue
-        * on some nve4 boards where the production vbios left this
-        * setting enabled by default.
-        *
-        * ftp://download.nvidia.com/open-gpu-doc/gk104-disable-underflow-reporting/1/gk104-disable-underflow-reporting.txt
-        */
-       for (i = 0; i < priv->head.nr; i++)
-               nv_mask(priv, 0x616308 + (i * 0x800), 0x00000111, 0x00000010);
-
-       return 0;
-}
-
-static int
-nvd0_disp_main_fini(struct nouveau_object *object, bool suspend)
-{
-       struct nv50_disp_priv *priv = (void *)object->engine;
-       struct nv50_disp_base *base = (void *)object;
-
-       /* disable all interrupts */
-       nv_wr32(priv, 0x6100b0, 0x00000000);
-
-       return nouveau_parent_fini(&base->base, suspend);
-}
-
-struct nouveau_ofuncs
-nvd0_disp_main_ofuncs = {
-       .ctor = nv50_disp_main_ctor,
-       .dtor = nv50_disp_main_dtor,
-       .init = nvd0_disp_main_init,
-       .fini = nvd0_disp_main_fini,
-       .mthd = nv50_disp_main_mthd,
-       .ntfy = nouveau_disp_ntfy,
-};
-
-static struct nouveau_oclass
-nvd0_disp_main_oclass[] = {
-       { GF110_DISP, &nvd0_disp_main_ofuncs },
-       {}
-};
-
-static struct nouveau_oclass
-nvd0_disp_sclass[] = {
-       { GF110_DISP_CORE_CHANNEL_DMA, &nvd0_disp_core_ofuncs.base },
-       { GF110_DISP_BASE_CHANNEL_DMA, &nvd0_disp_base_ofuncs.base },
-       { GF110_DISP_OVERLAY_CONTROL_DMA, &nvd0_disp_ovly_ofuncs.base },
-       { GF110_DISP_OVERLAY, &nvd0_disp_oimm_ofuncs.base },
-       { GF110_DISP_CURSOR, &nvd0_disp_curs_ofuncs.base },
-       {}
-};
-
-/*******************************************************************************
- * Display engine implementation
- ******************************************************************************/
-
-static void
-nvd0_disp_vblank_init(struct nvkm_event *event, int type, int head)
-{
-       struct nouveau_disp *disp = container_of(event, typeof(*disp), vblank);
-       nv_mask(disp, 0x6100c0 + (head * 0x800), 0x00000001, 0x00000001);
-}
-
-static void
-nvd0_disp_vblank_fini(struct nvkm_event *event, int type, int head)
-{
-       struct nouveau_disp *disp = container_of(event, typeof(*disp), vblank);
-       nv_mask(disp, 0x6100c0 + (head * 0x800), 0x00000001, 0x00000000);
-}
-
-const struct nvkm_event_func
-nvd0_disp_vblank_func = {
-       .ctor = nouveau_disp_vblank_ctor,
-       .init = nvd0_disp_vblank_init,
-       .fini = nvd0_disp_vblank_fini,
-};
-
-static struct nvkm_output *
-exec_lookup(struct nv50_disp_priv *priv, int head, int or, u32 ctrl,
-           u32 *data, u8 *ver, u8 *hdr, u8 *cnt, u8 *len,
-           struct nvbios_outp *info)
-{
-       struct nouveau_bios *bios = nouveau_bios(priv);
-       struct nvkm_output *outp;
-       u16 mask, type;
-
-       if (or < 4) {
-               type = DCB_OUTPUT_ANALOG;
-               mask = 0;
-       } else {
-               or -= 4;
-               switch (ctrl & 0x00000f00) {
-               case 0x00000000: type = DCB_OUTPUT_LVDS; mask = 1; break;
-               case 0x00000100: type = DCB_OUTPUT_TMDS; mask = 1; break;
-               case 0x00000200: type = DCB_OUTPUT_TMDS; mask = 2; break;
-               case 0x00000500: type = DCB_OUTPUT_TMDS; mask = 3; break;
-               case 0x00000800: type = DCB_OUTPUT_DP; mask = 1; break;
-               case 0x00000900: type = DCB_OUTPUT_DP; mask = 2; break;
-               default:
-                       nv_error(priv, "unknown SOR mc 0x%08x\n", ctrl);
-                       return 0x0000;
-               }
-       }
-
-       mask  = 0x00c0 & (mask << 6);
-       mask |= 0x0001 << or;
-       mask |= 0x0100 << head;
-
-       list_for_each_entry(outp, &priv->base.outp, head) {
-               if ((outp->info.hasht & 0xff) == type &&
-                   (outp->info.hashm & mask) == mask) {
-                       *data = nvbios_outp_match(bios, outp->info.hasht,
-                                                       outp->info.hashm,
-                                                 ver, hdr, cnt, len, info);
-                       if (!*data)
-                               return NULL;
-                       return outp;
-               }
-       }
-
-       return NULL;
-}
-
-static struct nvkm_output *
-exec_script(struct nv50_disp_priv *priv, int head, int id)
-{
-       struct nouveau_bios *bios = nouveau_bios(priv);
-       struct nvkm_output *outp;
-       struct nvbios_outp info;
-       u8  ver, hdr, cnt, len;
-       u32 data, ctrl = 0;
-       int or;
-
-       for (or = 0; !(ctrl & (1 << head)) && or < 8; or++) {
-               ctrl = nv_rd32(priv, 0x640180 + (or * 0x20));
-               if (ctrl & (1 << head))
-                       break;
-       }
-
-       if (or == 8)
-               return NULL;
-
-       outp = exec_lookup(priv, head, or, ctrl, &data, &ver, &hdr, &cnt, &len, &info);
-       if (outp) {
-               struct nvbios_init init = {
-                       .subdev = nv_subdev(priv),
-                       .bios = bios,
-                       .offset = info.script[id],
-                       .outp = &outp->info,
-                       .crtc = head,
-                       .execute = 1,
-               };
-
-               nvbios_exec(&init);
-       }
-
-       return outp;
-}
-
-static struct nvkm_output *
-exec_clkcmp(struct nv50_disp_priv *priv, int head, int id, u32 pclk, u32 *conf)
-{
-       struct nouveau_bios *bios = nouveau_bios(priv);
-       struct nvkm_output *outp;
-       struct nvbios_outp info1;
-       struct nvbios_ocfg info2;
-       u8  ver, hdr, cnt, len;
-       u32 data, ctrl = 0;
-       int or;
-
-       for (or = 0; !(ctrl & (1 << head)) && or < 8; or++) {
-               ctrl = nv_rd32(priv, 0x660180 + (or * 0x20));
-               if (ctrl & (1 << head))
-                       break;
-       }
-
-       if (or == 8)
-               return NULL;
-
-       outp = exec_lookup(priv, head, or, ctrl, &data, &ver, &hdr, &cnt, &len, &info1);
-       if (!outp)
-               return NULL;
-
-       switch (outp->info.type) {
-       case DCB_OUTPUT_TMDS:
-               *conf = (ctrl & 0x00000f00) >> 8;
-               if (pclk >= 165000)
-                       *conf |= 0x0100;
-               break;
-       case DCB_OUTPUT_LVDS:
-               *conf = priv->sor.lvdsconf;
-               break;
-       case DCB_OUTPUT_DP:
-               *conf = (ctrl & 0x00000f00) >> 8;
-               break;
-       case DCB_OUTPUT_ANALOG:
-       default:
-               *conf = 0x00ff;
-               break;
-       }
-
-       data = nvbios_ocfg_match(bios, data, *conf, &ver, &hdr, &cnt, &len, &info2);
-       if (data && id < 0xff) {
-               data = nvbios_oclk_match(bios, info2.clkcmp[id], pclk);
-               if (data) {
-                       struct nvbios_init init = {
-                               .subdev = nv_subdev(priv),
-                               .bios = bios,
-                               .offset = data,
-                               .outp = &outp->info,
-                               .crtc = head,
-                               .execute = 1,
-                       };
-
-                       nvbios_exec(&init);
-               }
-       }
-
-       return outp;
-}
-
-static void
-nvd0_disp_intr_unk1_0(struct nv50_disp_priv *priv, int head)
-{
-       exec_script(priv, head, 1);
-}
-
-static void
-nvd0_disp_intr_unk2_0(struct nv50_disp_priv *priv, int head)
-{
-       struct nvkm_output *outp = exec_script(priv, head, 2);
-
-       /* see note in nv50_disp_intr_unk20_0() */
-       if (outp && outp->info.type == DCB_OUTPUT_DP) {
-               struct nvkm_output_dp *outpdp = (void *)outp;
-               struct nvbios_init init = {
-                       .subdev = nv_subdev(priv),
-                       .bios = nouveau_bios(priv),
-                       .outp = &outp->info,
-                       .crtc = head,
-                       .offset = outpdp->info.script[4],
-                       .execute = 1,
-               };
-
-               nvbios_exec(&init);
-               atomic_set(&outpdp->lt.done, 0);
-       }
-}
-
-static void
-nvd0_disp_intr_unk2_1(struct nv50_disp_priv *priv, int head)
-{
-       struct nouveau_devinit *devinit = nouveau_devinit(priv);
-       u32 pclk = nv_rd32(priv, 0x660450 + (head * 0x300)) / 1000;
-       if (pclk)
-               devinit->pll_set(devinit, PLL_VPLL0 + head, pclk);
-       nv_wr32(priv, 0x612200 + (head * 0x800), 0x00000000);
-}
-
-static void
-nvd0_disp_intr_unk2_2_tu(struct nv50_disp_priv *priv, int head,
-                        struct dcb_output *outp)
-{
-       const int or = ffs(outp->or) - 1;
-       const u32 ctrl = nv_rd32(priv, 0x660200 + (or   * 0x020));
-       const u32 conf = nv_rd32(priv, 0x660404 + (head * 0x300));
-       const s32 vactive = nv_rd32(priv, 0x660414 + (head * 0x300)) & 0xffff;
-       const s32 vblanke = nv_rd32(priv, 0x66041c + (head * 0x300)) & 0xffff;
-       const s32 vblanks = nv_rd32(priv, 0x660420 + (head * 0x300)) & 0xffff;
-       const u32 pclk = nv_rd32(priv, 0x660450 + (head * 0x300)) / 1000;
-       const u32 link = ((ctrl & 0xf00) == 0x800) ? 0 : 1;
-       const u32 hoff = (head * 0x800);
-       const u32 soff = (  or * 0x800);
-       const u32 loff = (link * 0x080) + soff;
-       const u32 symbol = 100000;
-       const u32 TU = 64;
-       u32 dpctrl = nv_rd32(priv, 0x61c10c + loff);
-       u32 clksor = nv_rd32(priv, 0x612300 + soff);
-       u32 datarate, link_nr, link_bw, bits;
-       u64 ratio, value;
-
-       link_nr  = hweight32(dpctrl & 0x000f0000);
-       link_bw  = (clksor & 0x007c0000) >> 18;
-       link_bw *= 27000;
-
-       /* symbols/hblank - algorithm taken from comments in tegra driver */
-       value = vblanke + vactive - vblanks - 7;
-       value = value * link_bw;
-       do_div(value, pclk);
-       value = value - (3 * !!(dpctrl & 0x00004000)) - (12 / link_nr);
-       nv_mask(priv, 0x616620 + hoff, 0x0000ffff, value);
-
-       /* symbols/vblank - algorithm taken from comments in tegra driver */
-       value = vblanks - vblanke - 25;
-       value = value * link_bw;
-       do_div(value, pclk);
-       value = value - ((36 / link_nr) + 3) - 1;
-       nv_mask(priv, 0x616624 + hoff, 0x00ffffff, value);
-
-       /* watermark */
-       if      ((conf & 0x3c0) == 0x180) bits = 30;
-       else if ((conf & 0x3c0) == 0x140) bits = 24;
-       else                              bits = 18;
-       datarate = (pclk * bits) / 8;
-
-       ratio  = datarate;
-       ratio *= symbol;
-       do_div(ratio, link_nr * link_bw);
-
-       value  = (symbol - ratio) * TU;
-       value *= ratio;
-       do_div(value, symbol);
-       do_div(value, symbol);
-
-       value += 5;
-       value |= 0x08000000;
-
-       nv_wr32(priv, 0x616610 + hoff, value);
-}
-
-static void
-nvd0_disp_intr_unk2_2(struct nv50_disp_priv *priv, int head)
-{
-       struct nvkm_output *outp;
-       u32 pclk = nv_rd32(priv, 0x660450 + (head * 0x300)) / 1000;
-       u32 conf, addr, data;
-
-       outp = exec_clkcmp(priv, head, 0xff, pclk, &conf);
-       if (!outp)
-               return;
-
-       /* see note in nv50_disp_intr_unk20_2() */
-       if (outp->info.type == DCB_OUTPUT_DP) {
-               u32 sync = nv_rd32(priv, 0x660404 + (head * 0x300));
-               switch ((sync & 0x000003c0) >> 6) {
-               case 6: pclk = pclk * 30; break;
-               case 5: pclk = pclk * 24; break;
-               case 2:
-               default:
-                       pclk = pclk * 18;
-                       break;
-               }
-
-               if (nvkm_output_dp_train(outp, pclk, true))
-                       ERR("link not trained before attach\n");
-       } else {
-               if (priv->sor.magic)
-                       priv->sor.magic(outp);
-       }
-
-       exec_clkcmp(priv, head, 0, pclk, &conf);
-
-       if (outp->info.type == DCB_OUTPUT_ANALOG) {
-               addr = 0x612280 + (ffs(outp->info.or) - 1) * 0x800;
-               data = 0x00000000;
-       } else {
-               addr = 0x612300 + (ffs(outp->info.or) - 1) * 0x800;
-               data = (conf & 0x0100) ? 0x00000101 : 0x00000000;
-               switch (outp->info.type) {
-               case DCB_OUTPUT_TMDS:
-                       nv_mask(priv, addr, 0x007c0000, 0x00280000);
-                       break;
-               case DCB_OUTPUT_DP:
-                       nvd0_disp_intr_unk2_2_tu(priv, head, &outp->info);
-                       break;
-               default:
-                       break;
-               }
-       }
-
-       nv_mask(priv, addr, 0x00000707, data);
-}
-
-static void
-nvd0_disp_intr_unk4_0(struct nv50_disp_priv *priv, int head)
-{
-       u32 pclk = nv_rd32(priv, 0x660450 + (head * 0x300)) / 1000;
-       u32 conf;
-
-       exec_clkcmp(priv, head, 1, pclk, &conf);
-}
-
-void
-nvd0_disp_intr_supervisor(struct work_struct *work)
-{
-       struct nv50_disp_priv *priv =
-               container_of(work, struct nv50_disp_priv, supervisor);
-       struct nv50_disp_impl *impl = (void *)nv_object(priv)->oclass;
-       u32 mask[4];
-       int head;
-
-       nv_debug(priv, "supervisor %d\n", ffs(priv->super));
-       for (head = 0; head < priv->head.nr; head++) {
-               mask[head] = nv_rd32(priv, 0x6101d4 + (head * 0x800));
-               nv_debug(priv, "head %d: 0x%08x\n", head, mask[head]);
-       }
-
-       if (priv->super & 0x00000001) {
-               nv50_disp_mthd_chan(priv, NV_DBG_DEBUG, 0, impl->mthd.core);
-               for (head = 0; head < priv->head.nr; head++) {
-                       if (!(mask[head] & 0x00001000))
-                               continue;
-                       nv_debug(priv, "supervisor 1.0 - head %d\n", head);
-                       nvd0_disp_intr_unk1_0(priv, head);
-               }
-       } else
-       if (priv->super & 0x00000002) {
-               for (head = 0; head < priv->head.nr; head++) {
-                       if (!(mask[head] & 0x00001000))
-                               continue;
-                       nv_debug(priv, "supervisor 2.0 - head %d\n", head);
-                       nvd0_disp_intr_unk2_0(priv, head);
-               }
-               for (head = 0; head < priv->head.nr; head++) {
-                       if (!(mask[head] & 0x00010000))
-                               continue;
-                       nv_debug(priv, "supervisor 2.1 - head %d\n", head);
-                       nvd0_disp_intr_unk2_1(priv, head);
-               }
-               for (head = 0; head < priv->head.nr; head++) {
-                       if (!(mask[head] & 0x00001000))
-                               continue;
-                       nv_debug(priv, "supervisor 2.2 - head %d\n", head);
-                       nvd0_disp_intr_unk2_2(priv, head);
-               }
-       } else
-       if (priv->super & 0x00000004) {
-               for (head = 0; head < priv->head.nr; head++) {
-                       if (!(mask[head] & 0x00001000))
-                               continue;
-                       nv_debug(priv, "supervisor 3.0 - head %d\n", head);
-                       nvd0_disp_intr_unk4_0(priv, head);
-               }
-       }
-
-       for (head = 0; head < priv->head.nr; head++)
-               nv_wr32(priv, 0x6101d4 + (head * 0x800), 0x00000000);
-       nv_wr32(priv, 0x6101d0, 0x80000000);
-}
-
-static void
-nvd0_disp_intr_error(struct nv50_disp_priv *priv, int chid)
-{
-       const struct nv50_disp_impl *impl = (void *)nv_object(priv)->oclass;
-       u32 mthd = nv_rd32(priv, 0x6101f0 + (chid * 12));
-       u32 data = nv_rd32(priv, 0x6101f4 + (chid * 12));
-       u32 unkn = nv_rd32(priv, 0x6101f8 + (chid * 12));
-
-       nv_error(priv, "chid %d mthd 0x%04x data 0x%08x "
-                      "0x%08x 0x%08x\n",
-                chid, (mthd & 0x0000ffc), data, mthd, unkn);
-
-       if (chid == 0) {
-               switch (mthd & 0xffc) {
-               case 0x0080:
-                       nv50_disp_mthd_chan(priv, NV_DBG_ERROR, chid - 0,
-                                           impl->mthd.core);
-                       break;
-               default:
-                       break;
-               }
-       } else
-       if (chid <= 4) {
-               switch (mthd & 0xffc) {
-               case 0x0080:
-                       nv50_disp_mthd_chan(priv, NV_DBG_ERROR, chid - 1,
-                                           impl->mthd.base);
-                       break;
-               default:
-                       break;
-               }
-       } else
-       if (chid <= 8) {
-               switch (mthd & 0xffc) {
-               case 0x0080:
-                       nv50_disp_mthd_chan(priv, NV_DBG_ERROR, chid - 5,
-                                           impl->mthd.ovly);
-                       break;
-               default:
-                       break;
-               }
-       }
-
-       nv_wr32(priv, 0x61009c, (1 << chid));
-       nv_wr32(priv, 0x6101f0 + (chid * 12), 0x90000000);
-}
-
-void
-nvd0_disp_intr(struct nouveau_subdev *subdev)
-{
-       struct nv50_disp_priv *priv = (void *)subdev;
-       u32 intr = nv_rd32(priv, 0x610088);
-       int i;
-
-       if (intr & 0x00000001) {
-               u32 stat = nv_rd32(priv, 0x61008c);
-               while (stat) {
-                       int chid = __ffs(stat); stat &= ~(1 << chid);
-                       nv50_disp_chan_uevent_send(priv, chid);
-                       nv_wr32(priv, 0x61008c, 1 << chid);
-               }
-               intr &= ~0x00000001;
-       }
-
-       if (intr & 0x00000002) {
-               u32 stat = nv_rd32(priv, 0x61009c);
-               int chid = ffs(stat) - 1;
-               if (chid >= 0)
-                       nvd0_disp_intr_error(priv, chid);
-               intr &= ~0x00000002;
-       }
-
-       if (intr & 0x00100000) {
-               u32 stat = nv_rd32(priv, 0x6100ac);
-               if (stat & 0x00000007) {
-                       priv->super = (stat & 0x00000007);
-                       schedule_work(&priv->supervisor);
-                       nv_wr32(priv, 0x6100ac, priv->super);
-                       stat &= ~0x00000007;
-               }
-
-               if (stat) {
-                       nv_info(priv, "unknown intr24 0x%08x\n", stat);
-                       nv_wr32(priv, 0x6100ac, stat);
-               }
-
-               intr &= ~0x00100000;
-       }
-
-       for (i = 0; i < priv->head.nr; i++) {
-               u32 mask = 0x01000000 << i;
-               if (mask & intr) {
-                       u32 stat = nv_rd32(priv, 0x6100bc + (i * 0x800));
-                       if (stat & 0x00000001)
-                               nouveau_disp_vblank(&priv->base, i);
-                       nv_mask(priv, 0x6100bc + (i * 0x800), 0, 0);
-                       nv_rd32(priv, 0x6100c0 + (i * 0x800));
-               }
-       }
-}
-
-static int
-nvd0_disp_ctor(struct nouveau_object *parent, struct nouveau_object *engine,
-              struct nouveau_oclass *oclass, void *data, u32 size,
-              struct nouveau_object **pobject)
-{
-       struct nv50_disp_priv *priv;
-       int heads = nv_rd32(parent, 0x022448);
-       int ret;
-
-       ret = nouveau_disp_create(parent, engine, oclass, heads,
-                                 "PDISP", "display", &priv);
-       *pobject = nv_object(priv);
-       if (ret)
-               return ret;
-
-       ret = nvkm_event_init(&nvd0_disp_chan_uevent, 1, 17, &priv->uevent);
-       if (ret)
-               return ret;
-
-       nv_engine(priv)->sclass = nvd0_disp_main_oclass;
-       nv_engine(priv)->cclass = &nv50_disp_cclass;
-       nv_subdev(priv)->intr = nvd0_disp_intr;
-       INIT_WORK(&priv->supervisor, nvd0_disp_intr_supervisor);
-       priv->sclass = nvd0_disp_sclass;
-       priv->head.nr = heads;
-       priv->dac.nr = 3;
-       priv->sor.nr = 4;
-       priv->dac.power = nv50_dac_power;
-       priv->dac.sense = nv50_dac_sense;
-       priv->sor.power = nv50_sor_power;
-       priv->sor.hda_eld = nvd0_hda_eld;
-       priv->sor.hdmi = nvd0_hdmi_ctrl;
-       return 0;
-}
-
-struct nouveau_oclass *
-nvd0_disp_outp_sclass[] = {
-       &nvd0_sor_dp_impl.base.base,
-       NULL
-};
-
-struct nouveau_oclass *
-nvd0_disp_oclass = &(struct nv50_disp_impl) {
-       .base.base.handle = NV_ENGINE(DISP, 0x90),
-       .base.base.ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nvd0_disp_ctor,
-               .dtor = _nouveau_disp_dtor,
-               .init = _nouveau_disp_init,
-               .fini = _nouveau_disp_fini,
-       },
-       .base.vblank = &nvd0_disp_vblank_func,
-       .base.outp =  nvd0_disp_outp_sclass,
-       .mthd.core = &nvd0_disp_core_mthd_chan,
-       .mthd.base = &nvd0_disp_base_mthd_chan,
-       .mthd.ovly = &nvd0_disp_ovly_mthd_chan,
-       .mthd.prev = -0x020000,
-       .head.scanoutpos = nvd0_disp_main_scanoutpos,
-}.base.base;
diff --git a/drivers/gpu/drm/nouveau/core/engine/disp/nve0.c b/drivers/gpu/drm/nouveau/core/engine/disp/nve0.c
deleted file mode 100644 (file)
index 55debec..0000000
+++ /dev/null
@@ -1,272 +0,0 @@
-/*
- * Copyright 2012 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 <engine/software.h>
-#include <engine/disp.h>
-
-#include <nvif/class.h>
-
-#include "nv50.h"
-
-/*******************************************************************************
- * EVO master channel object
- ******************************************************************************/
-
-static const struct nv50_disp_mthd_list
-nve0_disp_core_mthd_head = {
-       .mthd = 0x0300,
-       .addr = 0x000300,
-       .data = {
-               { 0x0400, 0x660400 },
-               { 0x0404, 0x660404 },
-               { 0x0408, 0x660408 },
-               { 0x040c, 0x66040c },
-               { 0x0410, 0x660410 },
-               { 0x0414, 0x660414 },
-               { 0x0418, 0x660418 },
-               { 0x041c, 0x66041c },
-               { 0x0420, 0x660420 },
-               { 0x0424, 0x660424 },
-               { 0x0428, 0x660428 },
-               { 0x042c, 0x66042c },
-               { 0x0430, 0x660430 },
-               { 0x0434, 0x660434 },
-               { 0x0438, 0x660438 },
-               { 0x0440, 0x660440 },
-               { 0x0444, 0x660444 },
-               { 0x0448, 0x660448 },
-               { 0x044c, 0x66044c },
-               { 0x0450, 0x660450 },
-               { 0x0454, 0x660454 },
-               { 0x0458, 0x660458 },
-               { 0x045c, 0x66045c },
-               { 0x0460, 0x660460 },
-               { 0x0468, 0x660468 },
-               { 0x046c, 0x66046c },
-               { 0x0470, 0x660470 },
-               { 0x0474, 0x660474 },
-               { 0x047c, 0x66047c },
-               { 0x0480, 0x660480 },
-               { 0x0484, 0x660484 },
-               { 0x0488, 0x660488 },
-               { 0x048c, 0x66048c },
-               { 0x0490, 0x660490 },
-               { 0x0494, 0x660494 },
-               { 0x0498, 0x660498 },
-               { 0x04a0, 0x6604a0 },
-               { 0x04b0, 0x6604b0 },
-               { 0x04b8, 0x6604b8 },
-               { 0x04bc, 0x6604bc },
-               { 0x04c0, 0x6604c0 },
-               { 0x04c4, 0x6604c4 },
-               { 0x04c8, 0x6604c8 },
-               { 0x04d0, 0x6604d0 },
-               { 0x04d4, 0x6604d4 },
-               { 0x04e0, 0x6604e0 },
-               { 0x04e4, 0x6604e4 },
-               { 0x04e8, 0x6604e8 },
-               { 0x04ec, 0x6604ec },
-               { 0x04f0, 0x6604f0 },
-               { 0x04f4, 0x6604f4 },
-               { 0x04f8, 0x6604f8 },
-               { 0x04fc, 0x6604fc },
-               { 0x0500, 0x660500 },
-               { 0x0504, 0x660504 },
-               { 0x0508, 0x660508 },
-               { 0x050c, 0x66050c },
-               { 0x0510, 0x660510 },
-               { 0x0514, 0x660514 },
-               { 0x0518, 0x660518 },
-               { 0x051c, 0x66051c },
-               { 0x0520, 0x660520 },
-               { 0x0524, 0x660524 },
-               { 0x052c, 0x66052c },
-               { 0x0530, 0x660530 },
-               { 0x054c, 0x66054c },
-               { 0x0550, 0x660550 },
-               { 0x0554, 0x660554 },
-               { 0x0558, 0x660558 },
-               { 0x055c, 0x66055c },
-               {}
-       }
-};
-
-const struct nv50_disp_mthd_chan
-nve0_disp_core_mthd_chan = {
-       .name = "Core",
-       .addr = 0x000000,
-       .data = {
-               { "Global", 1, &nvd0_disp_core_mthd_base },
-               {    "DAC", 3, &nvd0_disp_core_mthd_dac  },
-               {    "SOR", 8, &nvd0_disp_core_mthd_sor  },
-               {   "PIOR", 4, &nvd0_disp_core_mthd_pior },
-               {   "HEAD", 4, &nve0_disp_core_mthd_head },
-               {}
-       }
-};
-
-/*******************************************************************************
- * EVO overlay channel objects
- ******************************************************************************/
-
-static const struct nv50_disp_mthd_list
-nve0_disp_ovly_mthd_base = {
-       .mthd = 0x0000,
-       .data = {
-               { 0x0080, 0x665080 },
-               { 0x0084, 0x665084 },
-               { 0x0088, 0x665088 },
-               { 0x008c, 0x66508c },
-               { 0x0090, 0x665090 },
-               { 0x0094, 0x665094 },
-               { 0x00a0, 0x6650a0 },
-               { 0x00a4, 0x6650a4 },
-               { 0x00b0, 0x6650b0 },
-               { 0x00b4, 0x6650b4 },
-               { 0x00b8, 0x6650b8 },
-               { 0x00c0, 0x6650c0 },
-               { 0x00c4, 0x6650c4 },
-               { 0x00e0, 0x6650e0 },
-               { 0x00e4, 0x6650e4 },
-               { 0x00e8, 0x6650e8 },
-               { 0x0100, 0x665100 },
-               { 0x0104, 0x665104 },
-               { 0x0108, 0x665108 },
-               { 0x010c, 0x66510c },
-               { 0x0110, 0x665110 },
-               { 0x0118, 0x665118 },
-               { 0x011c, 0x66511c },
-               { 0x0120, 0x665120 },
-               { 0x0124, 0x665124 },
-               { 0x0130, 0x665130 },
-               { 0x0134, 0x665134 },
-               { 0x0138, 0x665138 },
-               { 0x013c, 0x66513c },
-               { 0x0140, 0x665140 },
-               { 0x0144, 0x665144 },
-               { 0x0148, 0x665148 },
-               { 0x014c, 0x66514c },
-               { 0x0150, 0x665150 },
-               { 0x0154, 0x665154 },
-               { 0x0158, 0x665158 },
-               { 0x015c, 0x66515c },
-               { 0x0160, 0x665160 },
-               { 0x0164, 0x665164 },
-               { 0x0168, 0x665168 },
-               { 0x016c, 0x66516c },
-               { 0x0400, 0x665400 },
-               { 0x0404, 0x665404 },
-               { 0x0408, 0x665408 },
-               { 0x040c, 0x66540c },
-               { 0x0410, 0x665410 },
-               {}
-       }
-};
-
-const struct nv50_disp_mthd_chan
-nve0_disp_ovly_mthd_chan = {
-       .name = "Overlay",
-       .addr = 0x001000,
-       .data = {
-               { "Global", 1, &nve0_disp_ovly_mthd_base },
-               {}
-       }
-};
-
-/*******************************************************************************
- * Base display object
- ******************************************************************************/
-
-static struct nouveau_oclass
-nve0_disp_sclass[] = {
-       { GK104_DISP_CORE_CHANNEL_DMA, &nvd0_disp_core_ofuncs.base },
-       { GK104_DISP_BASE_CHANNEL_DMA, &nvd0_disp_base_ofuncs.base },
-       { GK104_DISP_OVERLAY_CONTROL_DMA, &nvd0_disp_ovly_ofuncs.base },
-       { GK104_DISP_OVERLAY, &nvd0_disp_oimm_ofuncs.base },
-       { GK104_DISP_CURSOR, &nvd0_disp_curs_ofuncs.base },
-       {}
-};
-
-static struct nouveau_oclass
-nve0_disp_main_oclass[] = {
-       { GK104_DISP, &nvd0_disp_main_ofuncs },
-       {}
-};
-
-/*******************************************************************************
- * Display engine implementation
- ******************************************************************************/
-
-static int
-nve0_disp_ctor(struct nouveau_object *parent, struct nouveau_object *engine,
-              struct nouveau_oclass *oclass, void *data, u32 size,
-              struct nouveau_object **pobject)
-{
-       struct nv50_disp_priv *priv;
-       int heads = nv_rd32(parent, 0x022448);
-       int ret;
-
-       ret = nouveau_disp_create(parent, engine, oclass, heads,
-                                 "PDISP", "display", &priv);
-       *pobject = nv_object(priv);
-       if (ret)
-               return ret;
-
-       ret = nvkm_event_init(&nvd0_disp_chan_uevent, 1, 17, &priv->uevent);
-       if (ret)
-               return ret;
-
-       nv_engine(priv)->sclass = nve0_disp_main_oclass;
-       nv_engine(priv)->cclass = &nv50_disp_cclass;
-       nv_subdev(priv)->intr = nvd0_disp_intr;
-       INIT_WORK(&priv->supervisor, nvd0_disp_intr_supervisor);
-       priv->sclass = nve0_disp_sclass;
-       priv->head.nr = heads;
-       priv->dac.nr = 3;
-       priv->sor.nr = 4;
-       priv->dac.power = nv50_dac_power;
-       priv->dac.sense = nv50_dac_sense;
-       priv->sor.power = nv50_sor_power;
-       priv->sor.hda_eld = nvd0_hda_eld;
-       priv->sor.hdmi = nve0_hdmi_ctrl;
-       return 0;
-}
-
-struct nouveau_oclass *
-nve0_disp_oclass = &(struct nv50_disp_impl) {
-       .base.base.handle = NV_ENGINE(DISP, 0x91),
-       .base.base.ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nve0_disp_ctor,
-               .dtor = _nouveau_disp_dtor,
-               .init = _nouveau_disp_init,
-               .fini = _nouveau_disp_fini,
-       },
-       .base.vblank = &nvd0_disp_vblank_func,
-       .base.outp =  nvd0_disp_outp_sclass,
-       .mthd.core = &nve0_disp_core_mthd_chan,
-       .mthd.base = &nvd0_disp_base_mthd_chan,
-       .mthd.ovly = &nve0_disp_ovly_mthd_chan,
-       .mthd.prev = -0x020000,
-       .head.scanoutpos = nvd0_disp_main_scanoutpos,
-}.base.base;
diff --git a/drivers/gpu/drm/nouveau/core/engine/disp/nvf0.c b/drivers/gpu/drm/nouveau/core/engine/disp/nvf0.c
deleted file mode 100644 (file)
index 3e7e2d2..0000000
+++ /dev/null
@@ -1,107 +0,0 @@
-/*
- * Copyright 2012 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 <engine/software.h>
-#include <engine/disp.h>
-
-#include <nvif/class.h>
-
-#include "nv50.h"
-
-/*******************************************************************************
- * Base display object
- ******************************************************************************/
-
-static struct nouveau_oclass
-nvf0_disp_sclass[] = {
-       { GK110_DISP_CORE_CHANNEL_DMA, &nvd0_disp_core_ofuncs.base },
-       { GK110_DISP_BASE_CHANNEL_DMA, &nvd0_disp_base_ofuncs.base },
-       { GK104_DISP_OVERLAY_CONTROL_DMA, &nvd0_disp_ovly_ofuncs.base },
-       { GK104_DISP_OVERLAY, &nvd0_disp_oimm_ofuncs.base },
-       { GK104_DISP_CURSOR, &nvd0_disp_curs_ofuncs.base },
-       {}
-};
-
-static struct nouveau_oclass
-nvf0_disp_main_oclass[] = {
-       { GK110_DISP, &nvd0_disp_main_ofuncs },
-       {}
-};
-
-/*******************************************************************************
- * Display engine implementation
- ******************************************************************************/
-
-static int
-nvf0_disp_ctor(struct nouveau_object *parent, struct nouveau_object *engine,
-              struct nouveau_oclass *oclass, void *data, u32 size,
-              struct nouveau_object **pobject)
-{
-       struct nv50_disp_priv *priv;
-       int heads = nv_rd32(parent, 0x022448);
-       int ret;
-
-       ret = nouveau_disp_create(parent, engine, oclass, heads,
-                                 "PDISP", "display", &priv);
-       *pobject = nv_object(priv);
-       if (ret)
-               return ret;
-
-       ret = nvkm_event_init(&nvd0_disp_chan_uevent, 1, 17, &priv->uevent);
-       if (ret)
-               return ret;
-
-       nv_engine(priv)->sclass = nvf0_disp_main_oclass;
-       nv_engine(priv)->cclass = &nv50_disp_cclass;
-       nv_subdev(priv)->intr = nvd0_disp_intr;
-       INIT_WORK(&priv->supervisor, nvd0_disp_intr_supervisor);
-       priv->sclass = nvf0_disp_sclass;
-       priv->head.nr = heads;
-       priv->dac.nr = 3;
-       priv->sor.nr = 4;
-       priv->dac.power = nv50_dac_power;
-       priv->dac.sense = nv50_dac_sense;
-       priv->sor.power = nv50_sor_power;
-       priv->sor.hda_eld = nvd0_hda_eld;
-       priv->sor.hdmi = nve0_hdmi_ctrl;
-       return 0;
-}
-
-struct nouveau_oclass *
-nvf0_disp_oclass = &(struct nv50_disp_impl) {
-       .base.base.handle = NV_ENGINE(DISP, 0x92),
-       .base.base.ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nvf0_disp_ctor,
-               .dtor = _nouveau_disp_dtor,
-               .init = _nouveau_disp_init,
-               .fini = _nouveau_disp_fini,
-       },
-       .base.vblank = &nvd0_disp_vblank_func,
-       .base.outp =  nvd0_disp_outp_sclass,
-       .mthd.core = &nve0_disp_core_mthd_chan,
-       .mthd.base = &nvd0_disp_base_mthd_chan,
-       .mthd.ovly = &nve0_disp_ovly_mthd_chan,
-       .mthd.prev = -0x020000,
-       .head.scanoutpos = nvd0_disp_main_scanoutpos,
-}.base.base;
diff --git a/drivers/gpu/drm/nouveau/core/engine/disp/outp.c b/drivers/gpu/drm/nouveau/core/engine/disp/outp.c
deleted file mode 100644 (file)
index bbd9b6f..0000000
+++ /dev/null
@@ -1,141 +0,0 @@
-/*
- * Copyright 2014 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 <subdev/i2c.h>
-#include <subdev/bios.h>
-#include <subdev/bios/conn.h>
-
-#include "outp.h"
-
-int
-_nvkm_output_fini(struct nouveau_object *object, bool suspend)
-{
-       struct nvkm_output *outp = (void *)object;
-       nv_ofuncs(outp->conn)->fini(nv_object(outp->conn), suspend);
-       return nouveau_object_fini(&outp->base, suspend);
-}
-
-int
-_nvkm_output_init(struct nouveau_object *object)
-{
-       struct nvkm_output *outp = (void *)object;
-       int ret = nouveau_object_init(&outp->base);
-       if (ret == 0)
-               nv_ofuncs(outp->conn)->init(nv_object(outp->conn));
-       return 0;
-}
-
-void
-_nvkm_output_dtor(struct nouveau_object *object)
-{
-       struct nvkm_output *outp = (void *)object;
-       list_del(&outp->head);
-       nouveau_object_ref(NULL, (void *)&outp->conn);
-       nouveau_object_destroy(&outp->base);
-}
-
-int
-nvkm_output_create_(struct nouveau_object *parent,
-                   struct nouveau_object *engine,
-                   struct nouveau_oclass *oclass,
-                   struct dcb_output *dcbE, int index,
-                   int length, void **pobject)
-{
-       struct nouveau_bios *bios = nouveau_bios(engine);
-       struct nouveau_i2c *i2c = nouveau_i2c(parent);
-       struct nouveau_disp *disp = (void *)engine;
-       struct nvbios_connE connE;
-       struct nvkm_output *outp;
-       u8  ver, hdr;
-       u32 data;
-       int ret;
-
-       ret = nouveau_object_create_(parent, engine, oclass, 0, length, pobject);
-       outp = *pobject;
-       if (ret)
-               return ret;
-
-       outp->info = *dcbE;
-       outp->index = index;
-       outp->or = ffs(outp->info.or) - 1;
-
-       DBG("type %02x loc %d or %d link %d con %x edid %x bus %d head %x\n",
-           dcbE->type, dcbE->location, dcbE->or, dcbE->type >= 2 ?
-           dcbE->sorconf.link : 0, dcbE->connector, dcbE->i2c_index,
-           dcbE->bus, dcbE->heads);
-
-       if (outp->info.type != DCB_OUTPUT_DP)
-               outp->port = i2c->find(i2c, NV_I2C_PORT(outp->info.i2c_index));
-       else
-               outp->port = i2c->find(i2c, NV_I2C_AUX(outp->info.i2c_index));
-       outp->edid = outp->port;
-
-       data = nvbios_connEp(bios, outp->info.connector, &ver, &hdr, &connE);
-       if (!data) {
-               DBG("vbios connector data not found\n");
-               memset(&connE, 0x00, sizeof(connE));
-               connE.type = DCB_CONNECTOR_NONE;
-       }
-
-       ret = nouveau_object_ctor(parent, engine, nvkm_connector_oclass,
-                                &connE, outp->info.connector,
-                                (struct nouveau_object **)&outp->conn);
-       if (ret < 0) {
-               ERR("error %d creating connector, disabling\n", ret);
-               return ret;
-       }
-
-       list_add_tail(&outp->head, &disp->outp);
-       return 0;
-}
-
-int
-_nvkm_output_ctor(struct nouveau_object *parent,
-                 struct nouveau_object *engine,
-                 struct nouveau_oclass *oclass, void *dcbE, u32 index,
-                 struct nouveau_object **pobject)
-{
-       struct nvkm_output *outp;
-       int ret;
-
-       ret = nvkm_output_create(parent, engine, oclass, dcbE, index, &outp);
-       *pobject = nv_object(outp);
-       if (ret)
-               return ret;
-
-       return 0;
-}
-
-struct nouveau_oclass *
-nvkm_output_oclass = &(struct nvkm_output_impl) {
-       .base = {
-               .handle = 0,
-               .ofuncs = &(struct nouveau_ofuncs) {
-                       .ctor = _nvkm_output_ctor,
-                       .dtor = _nvkm_output_dtor,
-                       .init = _nvkm_output_init,
-                       .fini = _nvkm_output_fini,
-               },
-       },
-}.base;
diff --git a/drivers/gpu/drm/nouveau/core/engine/disp/outp.h b/drivers/gpu/drm/nouveau/core/engine/disp/outp.h
deleted file mode 100644 (file)
index 187f435..0000000
+++ /dev/null
@@ -1,60 +0,0 @@
-#ifndef __NVKM_DISP_OUTP_H__
-#define __NVKM_DISP_OUTP_H__
-
-#include "priv.h"
-
-struct nvkm_output {
-       struct nouveau_object base;
-       struct list_head head;
-
-       struct dcb_output info;
-       int index;
-       int or;
-
-       struct nouveau_i2c_port *port;
-       struct nouveau_i2c_port *edid;
-
-       struct nvkm_connector *conn;
-};
-
-#define nvkm_output_create(p,e,c,b,i,d)                                        \
-       nvkm_output_create_((p), (e), (c), (b), (i), sizeof(**d), (void **)d)
-#define nvkm_output_destroy(d) ({                                              \
-       struct nvkm_output *_outp = (d);                                       \
-       _nvkm_output_dtor(nv_object(_outp));                                   \
-})
-#define nvkm_output_init(d) ({                                                 \
-       struct nvkm_output *_outp = (d);                                       \
-       _nvkm_output_init(nv_object(_outp));                                   \
-})
-#define nvkm_output_fini(d,s) ({                                               \
-       struct nvkm_output *_outp = (d);                                       \
-       _nvkm_output_fini(nv_object(_outp), (s));                              \
-})
-
-int nvkm_output_create_(struct nouveau_object *, struct nouveau_object *,
-                       struct nouveau_oclass *, struct dcb_output *,
-                       int, int, void **);
-
-int  _nvkm_output_ctor(struct nouveau_object *, struct nouveau_object *,
-                      struct nouveau_oclass *, void *, u32,
-                      struct nouveau_object **);
-void _nvkm_output_dtor(struct nouveau_object *);
-int  _nvkm_output_init(struct nouveau_object *);
-int  _nvkm_output_fini(struct nouveau_object *, bool);
-
-struct nvkm_output_impl {
-       struct nouveau_oclass base;
-};
-
-#ifndef MSG
-#define MSG(l,f,a...) do {                                                     \
-       struct nvkm_output *_outp = (void *)outp;                              \
-       nv_##l(nv_object(outp)->engine, "%02x:%04x:%04x: "f, _outp->index,     \
-              _outp->info.hasht, _outp->info.hashm, ##a);                     \
-} while(0)
-#define DBG(f,a...) MSG(debug, f, ##a)
-#define ERR(f,a...) MSG(error, f, ##a)
-#endif
-
-#endif
diff --git a/drivers/gpu/drm/nouveau/core/engine/disp/outpdp.c b/drivers/gpu/drm/nouveau/core/engine/disp/outpdp.c
deleted file mode 100644 (file)
index 667a907..0000000
+++ /dev/null
@@ -1,302 +0,0 @@
-/*
- * Copyright 2014 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 <core/os.h>
-#include <nvif/event.h>
-
-#include <subdev/i2c.h>
-
-#include "outpdp.h"
-#include "conn.h"
-#include "dport.h"
-
-int
-nvkm_output_dp_train(struct nvkm_output *base, u32 datarate, bool wait)
-{
-       struct nvkm_output_dp *outp = (void *)base;
-       bool retrain = true;
-       u8 link[2], stat[3];
-       u32 linkrate;
-       int ret, i;
-
-       /* check that the link is trained at a high enough rate */
-       ret = nv_rdaux(outp->base.edid, DPCD_LC00_LINK_BW_SET, link, 2);
-       if (ret) {
-               DBG("failed to read link config, assuming no sink\n");
-               goto done;
-       }
-
-       linkrate = link[0] * 27000 * (link[1] & DPCD_LC01_LANE_COUNT_SET);
-       linkrate = (linkrate * 8) / 10; /* 8B/10B coding overhead */
-       datarate = (datarate + 9) / 10; /* -> decakilobits */
-       if (linkrate < datarate) {
-               DBG("link not trained at sufficient rate\n");
-               goto done;
-       }
-
-       /* check that link is still trained */
-       ret = nv_rdaux(outp->base.edid, DPCD_LS02, stat, 3);
-       if (ret) {
-               DBG("failed to read link status, assuming no sink\n");
-               goto done;
-       }
-
-       if (stat[2] & DPCD_LS04_INTERLANE_ALIGN_DONE) {
-               for (i = 0; i < (link[1] & DPCD_LC01_LANE_COUNT_SET); i++) {
-                       u8 lane = (stat[i >> 1] >> ((i & 1) * 4)) & 0x0f;
-                       if (!(lane & DPCD_LS02_LANE0_CR_DONE) ||
-                           !(lane & DPCD_LS02_LANE0_CHANNEL_EQ_DONE) ||
-                           !(lane & DPCD_LS02_LANE0_SYMBOL_LOCKED)) {
-                               DBG("lane %d not equalised\n", lane);
-                               goto done;
-                       }
-               }
-               retrain = false;
-       } else {
-               DBG("no inter-lane alignment\n");
-       }
-
-done:
-       if (retrain || !atomic_read(&outp->lt.done)) {
-               /* no sink, but still need to configure source */
-               if (outp->dpcd[DPCD_RC00_DPCD_REV] == 0x00) {
-                       outp->dpcd[DPCD_RC01_MAX_LINK_RATE] =
-                               outp->base.info.dpconf.link_bw;
-                       outp->dpcd[DPCD_RC02] =
-                               outp->base.info.dpconf.link_nr;
-               }
-               atomic_set(&outp->lt.done, 0);
-               schedule_work(&outp->lt.work);
-       } else {
-               nvkm_notify_get(&outp->irq);
-       }
-
-       if (wait) {
-               if (!wait_event_timeout(outp->lt.wait,
-                                       atomic_read(&outp->lt.done),
-                                       msecs_to_jiffies(2000)))
-                       ret = -ETIMEDOUT;
-       }
-
-       return ret;
-}
-
-static void
-nvkm_output_dp_enable(struct nvkm_output_dp *outp, bool present)
-{
-       struct nouveau_i2c_port *port = outp->base.edid;
-       if (present) {
-               if (!outp->present) {
-                       nouveau_i2c(port)->acquire_pad(port, 0);
-                       DBG("aux power -> always\n");
-                       outp->present = true;
-               }
-               nvkm_output_dp_train(&outp->base, 0, true);
-       } else {
-               if (outp->present) {
-                       nouveau_i2c(port)->release_pad(port);
-                       DBG("aux power -> demand\n");
-                       outp->present = false;
-               }
-               atomic_set(&outp->lt.done, 0);
-       }
-}
-
-static void
-nvkm_output_dp_detect(struct nvkm_output_dp *outp)
-{
-       struct nouveau_i2c_port *port = outp->base.edid;
-       int ret = nouveau_i2c(port)->acquire_pad(port, 0);
-       if (ret == 0) {
-               ret = nv_rdaux(outp->base.edid, DPCD_RC00_DPCD_REV,
-                              outp->dpcd, sizeof(outp->dpcd));
-               nvkm_output_dp_enable(outp, ret == 0);
-               nouveau_i2c(port)->release_pad(port);
-       }
-}
-
-static int
-nvkm_output_dp_hpd(struct nvkm_notify *notify)
-{
-       struct nvkm_connector *conn = container_of(notify, typeof(*conn), hpd);
-       struct nvkm_output_dp *outp;
-       struct nouveau_disp *disp = nouveau_disp(conn);
-       const struct nvkm_i2c_ntfy_rep *line = notify->data;
-       struct nvif_notify_conn_rep_v0 rep = {};
-
-       list_for_each_entry(outp, &disp->outp, base.head) {
-               if (outp->base.conn == conn &&
-                   outp->info.type == DCB_OUTPUT_DP) {
-                       DBG("HPD: %d\n", line->mask);
-                       nvkm_output_dp_detect(outp);
-
-                       if (line->mask & NVKM_I2C_UNPLUG)
-                               rep.mask |= NVIF_NOTIFY_CONN_V0_UNPLUG;
-                       if (line->mask & NVKM_I2C_PLUG)
-                               rep.mask |= NVIF_NOTIFY_CONN_V0_PLUG;
-
-                       nvkm_event_send(&disp->hpd, rep.mask, conn->index,
-                                       &rep, sizeof(rep));
-                       return NVKM_NOTIFY_KEEP;
-               }
-       }
-
-       WARN_ON(1);
-       return NVKM_NOTIFY_DROP;
-}
-
-static int
-nvkm_output_dp_irq(struct nvkm_notify *notify)
-{
-       struct nvkm_output_dp *outp = container_of(notify, typeof(*outp), irq);
-       struct nouveau_disp *disp = nouveau_disp(outp);
-       const struct nvkm_i2c_ntfy_rep *line = notify->data;
-       struct nvif_notify_conn_rep_v0 rep = {
-               .mask = NVIF_NOTIFY_CONN_V0_IRQ,
-       };
-       int index = outp->base.info.connector;
-
-       DBG("IRQ: %d\n", line->mask);
-       nvkm_output_dp_train(&outp->base, 0, true);
-
-       nvkm_event_send(&disp->hpd, rep.mask, index, &rep, sizeof(rep));
-       return NVKM_NOTIFY_DROP;
-}
-
-int
-_nvkm_output_dp_fini(struct nouveau_object *object, bool suspend)
-{
-       struct nvkm_output_dp *outp = (void *)object;
-       nvkm_notify_put(&outp->irq);
-       nvkm_output_dp_enable(outp, false);
-       return nvkm_output_fini(&outp->base, suspend);
-}
-
-int
-_nvkm_output_dp_init(struct nouveau_object *object)
-{
-       struct nvkm_output_dp *outp = (void *)object;
-       nvkm_output_dp_detect(outp);
-       return nvkm_output_init(&outp->base);
-}
-
-void
-_nvkm_output_dp_dtor(struct nouveau_object *object)
-{
-       struct nvkm_output_dp *outp = (void *)object;
-       nvkm_notify_fini(&outp->irq);
-       nvkm_output_destroy(&outp->base);
-}
-
-int
-nvkm_output_dp_create_(struct nouveau_object *parent,
-                      struct nouveau_object *engine,
-                      struct nouveau_oclass *oclass,
-                      struct dcb_output *info, int index,
-                      int length, void **pobject)
-{
-       struct nouveau_bios *bios = nouveau_bios(parent);
-       struct nouveau_i2c *i2c = nouveau_i2c(parent);
-       struct nvkm_output_dp *outp;
-       u8  hdr, cnt, len;
-       u32 data;
-       int ret;
-
-       ret = nvkm_output_create_(parent, engine, oclass, info, index,
-                                 length, pobject);
-       outp = *pobject;
-       if (ret)
-               return ret;
-
-       nvkm_notify_fini(&outp->base.conn->hpd);
-
-       /* access to the aux channel is not optional... */
-       if (!outp->base.edid) {
-               ERR("aux channel not found\n");
-               return -ENODEV;
-       }
-
-       /* nor is the bios data for this output... */
-       data = nvbios_dpout_match(bios, outp->base.info.hasht,
-                                 outp->base.info.hashm, &outp->version,
-                                 &hdr, &cnt, &len, &outp->info);
-       if (!data) {
-               ERR("no bios dp data\n");
-               return -ENODEV;
-       }
-
-       DBG("bios dp %02x %02x %02x %02x\n", outp->version, hdr, cnt, len);
-
-       /* link training */
-       INIT_WORK(&outp->lt.work, nouveau_dp_train);
-       init_waitqueue_head(&outp->lt.wait);
-       atomic_set(&outp->lt.done, 0);
-
-       /* link maintenance */
-       ret = nvkm_notify_init(NULL, &i2c->event, nvkm_output_dp_irq, true,
-                              &(struct nvkm_i2c_ntfy_req) {
-                               .mask = NVKM_I2C_IRQ,
-                               .port = outp->base.edid->index,
-                              },
-                              sizeof(struct nvkm_i2c_ntfy_req),
-                              sizeof(struct nvkm_i2c_ntfy_rep),
-                              &outp->irq);
-       if (ret) {
-               ERR("error monitoring aux irq event: %d\n", ret);
-               return ret;
-       }
-
-       /* hotplug detect, replaces gpio-based mechanism with aux events */
-       ret = nvkm_notify_init(NULL, &i2c->event, nvkm_output_dp_hpd, true,
-                              &(struct nvkm_i2c_ntfy_req) {
-                               .mask = NVKM_I2C_PLUG | NVKM_I2C_UNPLUG,
-                               .port = outp->base.edid->index,
-                              },
-                              sizeof(struct nvkm_i2c_ntfy_req),
-                              sizeof(struct nvkm_i2c_ntfy_rep),
-                              &outp->base.conn->hpd);
-       if (ret) {
-               ERR("error monitoring aux hpd events: %d\n", ret);
-               return ret;
-       }
-
-       return 0;
-}
-
-int
-_nvkm_output_dp_ctor(struct nouveau_object *parent,
-                    struct nouveau_object *engine,
-                    struct nouveau_oclass *oclass, void *info, u32 index,
-                    struct nouveau_object **pobject)
-{
-       struct nvkm_output_dp *outp;
-       int ret;
-
-       ret = nvkm_output_dp_create(parent, engine, oclass, info, index, &outp);
-       *pobject = nv_object(outp);
-       if (ret)
-               return ret;
-
-       return 0;
-}
diff --git a/drivers/gpu/drm/nouveau/core/engine/disp/outpdp.h b/drivers/gpu/drm/nouveau/core/engine/disp/outpdp.h
deleted file mode 100644 (file)
index 1fac367..0000000
+++ /dev/null
@@ -1,62 +0,0 @@
-#ifndef __NVKM_DISP_OUTP_DP_H__
-#define __NVKM_DISP_OUTP_DP_H__
-
-#include <subdev/bios.h>
-#include <subdev/bios/dp.h>
-
-#include "outp.h"
-
-struct nvkm_output_dp {
-       struct nvkm_output base;
-
-       struct nvbios_dpout info;
-       u8 version;
-
-       struct nvkm_notify irq;
-       bool present;
-       u8 dpcd[16];
-
-       struct {
-               struct work_struct work;
-               wait_queue_head_t wait;
-               atomic_t done;
-       } lt;
-};
-
-#define nvkm_output_dp_create(p,e,c,b,i,d)                                     \
-       nvkm_output_dp_create_((p), (e), (c), (b), (i), sizeof(**d), (void **)d)
-#define nvkm_output_dp_destroy(d) ({                                           \
-       struct nvkm_output_dp *_outp = (d);                                    \
-       _nvkm_output_dp_dtor(nv_object(_outp));                                \
-})
-#define nvkm_output_dp_init(d) ({                                              \
-       struct nvkm_output_dp *_outp = (d);                                    \
-       _nvkm_output_dp_init(nv_object(_outp));                                \
-})
-#define nvkm_output_dp_fini(d,s) ({                                            \
-       struct nvkm_output_dp *_outp = (d);                                    \
-       _nvkm_output_dp_fini(nv_object(_outp), (s));                           \
-})
-
-int nvkm_output_dp_create_(struct nouveau_object *, struct nouveau_object *,
-                          struct nouveau_oclass *, struct dcb_output *,
-                          int, int, void **);
-
-int  _nvkm_output_dp_ctor(struct nouveau_object *, struct nouveau_object *,
-                         struct nouveau_oclass *, void *, u32,
-                         struct nouveau_object **);
-void _nvkm_output_dp_dtor(struct nouveau_object *);
-int  _nvkm_output_dp_init(struct nouveau_object *);
-int  _nvkm_output_dp_fini(struct nouveau_object *, bool);
-
-struct nvkm_output_dp_impl {
-       struct nvkm_output_impl base;
-       int (*pattern)(struct nvkm_output_dp *, int);
-       int (*lnk_pwr)(struct nvkm_output_dp *, int nr);
-       int (*lnk_ctl)(struct nvkm_output_dp *, int nr, int bw, bool ef);
-       int (*drv_ctl)(struct nvkm_output_dp *, int ln, int vs, int pe, int pc);
-};
-
-int nvkm_output_dp_train(struct nvkm_output *, u32 rate, bool wait);
-
-#endif
diff --git a/drivers/gpu/drm/nouveau/core/engine/disp/piornv50.c b/drivers/gpu/drm/nouveau/core/engine/disp/piornv50.c
deleted file mode 100644 (file)
index d00f89a..0000000
+++ /dev/null
@@ -1,172 +0,0 @@
-/*
- * Copyright 2012 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 <core/client.h>
-#include <nvif/unpack.h>
-#include <nvif/class.h>
-
-#include <subdev/bios.h>
-#include <subdev/bios/dcb.h>
-#include <subdev/timer.h>
-#include <subdev/i2c.h>
-
-#include "nv50.h"
-
-/******************************************************************************
- * TMDS
- *****************************************************************************/
-
-static int
-nv50_pior_tmds_ctor(struct nouveau_object *parent,
-                   struct nouveau_object *engine,
-                   struct nouveau_oclass *oclass, void *info, u32 index,
-                   struct nouveau_object **pobject)
-{
-       struct nouveau_i2c *i2c = nouveau_i2c(parent);
-       struct nvkm_output *outp;
-       int ret;
-
-       ret = nvkm_output_create(parent, engine, oclass, info, index, &outp);
-       *pobject = nv_object(outp);
-       if (ret)
-               return ret;
-
-       outp->edid = i2c->find_type(i2c, NV_I2C_TYPE_EXTDDC(outp->info.extdev));
-       return 0;
-}
-
-struct nvkm_output_impl
-nv50_pior_tmds_impl = {
-       .base.handle = DCB_OUTPUT_TMDS | 0x0100,
-       .base.ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nv50_pior_tmds_ctor,
-               .dtor = _nvkm_output_dtor,
-               .init = _nvkm_output_init,
-               .fini = _nvkm_output_fini,
-       },
-};
-
-/******************************************************************************
- * DisplayPort
- *****************************************************************************/
-
-static int
-nv50_pior_dp_pattern(struct nvkm_output_dp *outp, int pattern)
-{
-       struct nouveau_i2c_port *port = outp->base.edid;
-       if (port && port->func->pattern)
-               return port->func->pattern(port, pattern);
-       return port ? 0 : -ENODEV;
-}
-
-static int
-nv50_pior_dp_lnk_pwr(struct nvkm_output_dp *outp, int nr)
-{
-       return 0;
-}
-
-static int
-nv50_pior_dp_lnk_ctl(struct nvkm_output_dp *outp, int nr, int bw, bool ef)
-{
-       struct nouveau_i2c_port *port = outp->base.edid;
-       if (port && port->func->lnk_ctl)
-               return port->func->lnk_ctl(port, nr, bw, ef);
-       return port ? 0 : -ENODEV;
-}
-
-static int
-nv50_pior_dp_drv_ctl(struct nvkm_output_dp *outp, int ln, int vs, int pe, int pc)
-{
-       struct nouveau_i2c_port *port = outp->base.edid;
-       if (port && port->func->drv_ctl)
-               return port->func->drv_ctl(port, ln, vs, pe);
-       return port ? 0 : -ENODEV;
-}
-
-static int
-nv50_pior_dp_ctor(struct nouveau_object *parent,
-                 struct nouveau_object *engine,
-                 struct nouveau_oclass *oclass, void *info, u32 index,
-                 struct nouveau_object **pobject)
-{
-       struct nouveau_i2c *i2c = nouveau_i2c(parent);
-       struct nvkm_output_dp *outp;
-       int ret;
-
-       ret = nvkm_output_dp_create(parent, engine, oclass, info, index, &outp);
-       *pobject = nv_object(outp);
-       if (ret)
-               return ret;
-
-       outp->base.edid = i2c->find_type(i2c, NV_I2C_TYPE_EXTAUX(
-                                        outp->base.info.extdev));
-       return 0;
-}
-
-struct nvkm_output_dp_impl
-nv50_pior_dp_impl = {
-       .base.base.handle = DCB_OUTPUT_DP | 0x0010,
-       .base.base.ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nv50_pior_dp_ctor,
-               .dtor = _nvkm_output_dp_dtor,
-               .init = _nvkm_output_dp_init,
-               .fini = _nvkm_output_dp_fini,
-       },
-       .pattern = nv50_pior_dp_pattern,
-       .lnk_pwr = nv50_pior_dp_lnk_pwr,
-       .lnk_ctl = nv50_pior_dp_lnk_ctl,
-       .drv_ctl = nv50_pior_dp_drv_ctl,
-};
-
-/******************************************************************************
- * General PIOR handling
- *****************************************************************************/
-
-int
-nv50_pior_power(NV50_DISP_MTHD_V1)
-{
-       const u32 soff = outp->or * 0x800;
-       union {
-               struct nv50_disp_pior_pwr_v0 v0;
-       } *args = data;
-       u32 ctrl, type;
-       int ret;
-
-       nv_ioctl(object, "disp pior pwr size %d\n", size);
-       if (nvif_unpack(args->v0, 0, 0, false)) {
-               nv_ioctl(object, "disp pior pwr vers %d state %d type %x\n",
-                        args->v0.version, args->v0.state, args->v0.type);
-               if (args->v0.type > 0x0f)
-                       return -EINVAL;
-               ctrl = !!args->v0.state;
-               type = args->v0.type;
-       } else
-               return ret;
-
-       nv_wait(priv, 0x61e004 + soff, 0x80000000, 0x00000000);
-       nv_mask(priv, 0x61e004 + soff, 0x80000101, 0x80000000 | ctrl);
-       nv_wait(priv, 0x61e004 + soff, 0x80000000, 0x00000000);
-       priv->pior.type[outp->or] = type;
-       return 0;
-}
diff --git a/drivers/gpu/drm/nouveau/core/engine/disp/priv.h b/drivers/gpu/drm/nouveau/core/engine/disp/priv.h
deleted file mode 100644 (file)
index 6a0511d..0000000
+++ /dev/null
@@ -1,48 +0,0 @@
-#ifndef __NVKM_DISP_PRIV_H__
-#define __NVKM_DISP_PRIV_H__
-
-#include <subdev/bios.h>
-#include <subdev/bios/dcb.h>
-#include <subdev/bios/conn.h>
-
-#include <engine/disp.h>
-
-struct nouveau_disp_impl {
-       struct nouveau_oclass base;
-       struct nouveau_oclass **outp;
-       struct nouveau_oclass **conn;
-       const struct nvkm_event_func *vblank;
-};
-
-#define nouveau_disp_create(p,e,c,h,i,x,d)                                     \
-       nouveau_disp_create_((p), (e), (c), (h), (i), (x),                     \
-                            sizeof(**d), (void **)d)
-#define nouveau_disp_destroy(d) ({                                             \
-       struct nouveau_disp *disp = (d);                                       \
-       _nouveau_disp_dtor(nv_object(disp));                                   \
-})
-#define nouveau_disp_init(d) ({                                                \
-       struct nouveau_disp *disp = (d);                                       \
-       _nouveau_disp_init(nv_object(disp));                                   \
-})
-#define nouveau_disp_fini(d,s) ({                                              \
-       struct nouveau_disp *disp = (d);                                       \
-       _nouveau_disp_fini(nv_object(disp), (s));                              \
-})
-
-int  nouveau_disp_create_(struct nouveau_object *, struct nouveau_object *,
-                         struct nouveau_oclass *, int heads,
-                         const char *, const char *, int, void **);
-void _nouveau_disp_dtor(struct nouveau_object *);
-int  _nouveau_disp_init(struct nouveau_object *);
-int  _nouveau_disp_fini(struct nouveau_object *, bool);
-
-extern struct nouveau_oclass *nvkm_output_oclass;
-extern struct nouveau_oclass *nvkm_connector_oclass;
-
-int  nouveau_disp_vblank_ctor(struct nouveau_object *, void *data, u32 size,
-                             struct nvkm_notify *);
-void nouveau_disp_vblank(struct nouveau_disp *, int head);
-int  nouveau_disp_ntfy(struct nouveau_object *, u32, struct nvkm_event **);
-
-#endif
diff --git a/drivers/gpu/drm/nouveau/core/engine/disp/sorgm204.c b/drivers/gpu/drm/nouveau/core/engine/disp/sorgm204.c
deleted file mode 100644 (file)
index 0b4fad3..0000000
+++ /dev/null
@@ -1,144 +0,0 @@
-/*
- * Copyright 2012 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 <core/os.h>
-
-#include <subdev/bios.h>
-#include <subdev/bios/dcb.h>
-#include <subdev/bios/dp.h>
-#include <subdev/bios/init.h>
-#include <subdev/timer.h>
-
-#include "nv50.h"
-
-static inline u32
-gm204_sor_soff(struct nvkm_output_dp *outp)
-{
-       return (ffs(outp->base.info.or) - 1) * 0x800;
-}
-
-static inline u32
-gm204_sor_loff(struct nvkm_output_dp *outp)
-{
-       return gm204_sor_soff(outp) + !(outp->base.info.sorconf.link & 1) * 0x80;
-}
-
-void
-gm204_sor_magic(struct nvkm_output *outp)
-{
-       struct nv50_disp_priv *priv = (void *)nouveau_disp(outp);
-       const u32 soff = outp->or * 0x100;
-       const u32 data = outp->or + 1;
-       if (outp->info.sorconf.link & 1)
-               nv_mask(priv, 0x612308 + soff, 0x0000001f, 0x00000000 | data);
-       if (outp->info.sorconf.link & 2)
-               nv_mask(priv, 0x612388 + soff, 0x0000001f, 0x00000010 | data);
-}
-
-static inline u32
-gm204_sor_dp_lane_map(struct nv50_disp_priv *priv, u8 lane)
-{
-       return lane * 0x08;
-}
-
-static int
-gm204_sor_dp_pattern(struct nvkm_output_dp *outp, int pattern)
-{
-       struct nv50_disp_priv *priv = (void *)nouveau_disp(outp);
-       const u32 soff = gm204_sor_soff(outp);
-       const u32 data = 0x01010101 * pattern;
-       if (outp->base.info.sorconf.link & 1)
-               nv_mask(priv, 0x61c110 + soff, 0x0f0f0f0f, data);
-       else
-               nv_mask(priv, 0x61c12c + soff, 0x0f0f0f0f, data);
-       return 0;
-}
-
-static int
-gm204_sor_dp_lnk_pwr(struct nvkm_output_dp *outp, int nr)
-{
-       struct nv50_disp_priv *priv = (void *)nouveau_disp(outp);
-       const u32 soff = gm204_sor_soff(outp);
-       const u32 loff = gm204_sor_loff(outp);
-       u32 mask = 0, i;
-
-       for (i = 0; i < nr; i++)
-               mask |= 1 << (gm204_sor_dp_lane_map(priv, i) >> 3);
-
-       nv_mask(priv, 0x61c130 + loff, 0x0000000f, mask);
-       nv_mask(priv, 0x61c034 + soff, 0x80000000, 0x80000000);
-       nv_wait(priv, 0x61c034 + soff, 0x80000000, 0x00000000);
-       return 0;
-}
-
-static int
-gm204_sor_dp_drv_ctl(struct nvkm_output_dp *outp, int ln, int vs, int pe, int pc)
-{
-       struct nv50_disp_priv *priv = (void *)nouveau_disp(outp);
-       struct nouveau_bios *bios = nouveau_bios(priv);
-       const u32 shift = gm204_sor_dp_lane_map(priv, ln);
-       const u32 loff = gm204_sor_loff(outp);
-       u32 addr, data[4];
-       u8  ver, hdr, cnt, len;
-       struct nvbios_dpout info;
-       struct nvbios_dpcfg ocfg;
-
-       addr = nvbios_dpout_match(bios, outp->base.info.hasht,
-                                       outp->base.info.hashm,
-                                &ver, &hdr, &cnt, &len, &info);
-       if (!addr)
-               return -ENODEV;
-
-       addr = nvbios_dpcfg_match(bios, addr, pc, vs, pe,
-                                &ver, &hdr, &cnt, &len, &ocfg);
-       if (!addr)
-               return -EINVAL;
-
-       data[0] = nv_rd32(priv, 0x61c118 + loff) & ~(0x000000ff << shift);
-       data[1] = nv_rd32(priv, 0x61c120 + loff) & ~(0x000000ff << shift);
-       data[2] = nv_rd32(priv, 0x61c130 + loff);
-       if ((data[2] & 0x0000ff00) < (ocfg.tx_pu << 8) || ln == 0)
-               data[2] = (data[2] & ~0x0000ff00) | (ocfg.tx_pu << 8);
-       nv_wr32(priv, 0x61c118 + loff, data[0] | (ocfg.dc << shift));
-       nv_wr32(priv, 0x61c120 + loff, data[1] | (ocfg.pe << shift));
-       nv_wr32(priv, 0x61c130 + loff, data[2] | (ocfg.tx_pu << 8));
-       data[3] = nv_rd32(priv, 0x61c13c + loff) & ~(0x000000ff << shift);
-       nv_wr32(priv, 0x61c13c + loff, data[3] | (ocfg.pc << shift));
-       return 0;
-}
-
-struct nvkm_output_dp_impl
-gm204_sor_dp_impl = {
-       .base.base.handle = DCB_OUTPUT_DP,
-       .base.base.ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = _nvkm_output_dp_ctor,
-               .dtor = _nvkm_output_dp_dtor,
-               .init = _nvkm_output_dp_init,
-               .fini = _nvkm_output_dp_fini,
-       },
-       .pattern = gm204_sor_dp_pattern,
-       .lnk_pwr = gm204_sor_dp_lnk_pwr,
-       .lnk_ctl = nvd0_sor_dp_lnk_ctl,
-       .drv_ctl = gm204_sor_dp_drv_ctl,
-};
diff --git a/drivers/gpu/drm/nouveau/core/engine/disp/sornv50.c b/drivers/gpu/drm/nouveau/core/engine/disp/sornv50.c
deleted file mode 100644 (file)
index ddf1760..0000000
+++ /dev/null
@@ -1,58 +0,0 @@
-/*
- * Copyright 2012 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 <core/client.h>
-#include <nvif/unpack.h>
-#include <nvif/class.h>
-
-#include <subdev/bios.h>
-#include <subdev/bios/dcb.h>
-#include <subdev/timer.h>
-
-#include "nv50.h"
-
-int
-nv50_sor_power(NV50_DISP_MTHD_V1)
-{
-       union {
-               struct nv50_disp_sor_pwr_v0 v0;
-       } *args = data;
-       const u32 soff = outp->or * 0x800;
-       u32 stat;
-       int ret;
-
-       nv_ioctl(object, "disp sor pwr size %d\n", size);
-       if (nvif_unpack(args->v0, 0, 0, false)) {
-               nv_ioctl(object, "disp sor pwr vers %d state %d\n",
-                        args->v0.version, args->v0.state);
-               stat = !!args->v0.state;
-       } else
-               return ret;
-
-       nv_wait(priv, 0x61c004 + soff, 0x80000000, 0x00000000);
-       nv_mask(priv, 0x61c004 + soff, 0x80000001, 0x80000000 | stat);
-       nv_wait(priv, 0x61c004 + soff, 0x80000000, 0x00000000);
-       nv_wait(priv, 0x61c030 + soff, 0x10000000, 0x00000000);
-       return 0;
-}
diff --git a/drivers/gpu/drm/nouveau/core/engine/disp/sornv94.c b/drivers/gpu/drm/nouveau/core/engine/disp/sornv94.c
deleted file mode 100644 (file)
index 39f85d6..0000000
+++ /dev/null
@@ -1,151 +0,0 @@
-/*
- * Copyright 2012 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 <core/os.h>
-
-#include <subdev/bios.h>
-#include <subdev/bios/dcb.h>
-#include <subdev/bios/dp.h>
-#include <subdev/bios/init.h>
-#include <subdev/timer.h>
-
-#include "nv50.h"
-#include "outpdp.h"
-
-static inline u32
-nv94_sor_soff(struct nvkm_output_dp *outp)
-{
-       return (ffs(outp->base.info.or) - 1) * 0x800;
-}
-
-static inline u32
-nv94_sor_loff(struct nvkm_output_dp *outp)
-{
-       return nv94_sor_soff(outp) + !(outp->base.info.sorconf.link & 1) * 0x80;
-}
-
-static inline u32
-nv94_sor_dp_lane_map(struct nv50_disp_priv *priv, u8 lane)
-{
-       static const u8 nvaf[] = { 24, 16, 8, 0 }; /* thanks, apple.. */
-       static const u8 nv94[] = { 16, 8, 0, 24 };
-       if (nv_device(priv)->chipset == 0xaf)
-               return nvaf[lane];
-       return nv94[lane];
-}
-
-static int
-nv94_sor_dp_pattern(struct nvkm_output_dp *outp, int pattern)
-{
-       struct nv50_disp_priv *priv = (void *)nouveau_disp(outp);
-       const u32 loff = nv94_sor_loff(outp);
-       nv_mask(priv, 0x61c10c + loff, 0x0f000000, pattern << 24);
-       return 0;
-}
-
-int
-nv94_sor_dp_lnk_pwr(struct nvkm_output_dp *outp, int nr)
-{
-       struct nv50_disp_priv *priv = (void *)nouveau_disp(outp);
-       const u32 soff = nv94_sor_soff(outp);
-       const u32 loff = nv94_sor_loff(outp);
-       u32 mask = 0, i;
-
-       for (i = 0; i < nr; i++)
-               mask |= 1 << (nv94_sor_dp_lane_map(priv, i) >> 3);
-
-       nv_mask(priv, 0x61c130 + loff, 0x0000000f, mask);
-       nv_mask(priv, 0x61c034 + soff, 0x80000000, 0x80000000);
-       nv_wait(priv, 0x61c034 + soff, 0x80000000, 0x00000000);
-       return 0;
-}
-
-static int
-nv94_sor_dp_lnk_ctl(struct nvkm_output_dp *outp, int nr, int bw, bool ef)
-{
-       struct nv50_disp_priv *priv = (void *)nouveau_disp(outp);
-       const u32 soff = nv94_sor_soff(outp);
-       const u32 loff = nv94_sor_loff(outp);
-       u32 dpctrl = 0x00000000;
-       u32 clksor = 0x00000000;
-
-       dpctrl |= ((1 << nr) - 1) << 16;
-       if (ef)
-               dpctrl |= 0x00004000;
-       if (bw > 0x06)
-               clksor |= 0x00040000;
-
-       nv_mask(priv, 0x614300 + soff, 0x000c0000, clksor);
-       nv_mask(priv, 0x61c10c + loff, 0x001f4000, dpctrl);
-       return 0;
-}
-
-static int
-nv94_sor_dp_drv_ctl(struct nvkm_output_dp *outp, int ln, int vs, int pe, int pc)
-{
-       struct nv50_disp_priv *priv = (void *)nouveau_disp(outp);
-       struct nouveau_bios *bios = nouveau_bios(priv);
-       const u32 shift = nv94_sor_dp_lane_map(priv, ln);
-       const u32 loff = nv94_sor_loff(outp);
-       u32 addr, data[3];
-       u8  ver, hdr, cnt, len;
-       struct nvbios_dpout info;
-       struct nvbios_dpcfg ocfg;
-
-       addr = nvbios_dpout_match(bios, outp->base.info.hasht,
-                                       outp->base.info.hashm,
-                                &ver, &hdr, &cnt, &len, &info);
-       if (!addr)
-               return -ENODEV;
-
-       addr = nvbios_dpcfg_match(bios, addr, 0, vs, pe,
-                                &ver, &hdr, &cnt, &len, &ocfg);
-       if (!addr)
-               return -EINVAL;
-
-       data[0] = nv_rd32(priv, 0x61c118 + loff) & ~(0x000000ff << shift);
-       data[1] = nv_rd32(priv, 0x61c120 + loff) & ~(0x000000ff << shift);
-       data[2] = nv_rd32(priv, 0x61c130 + loff);
-       if ((data[2] & 0x0000ff00) < (ocfg.tx_pu << 8) || ln == 0)
-               data[2] = (data[2] & ~0x0000ff00) | (ocfg.tx_pu << 8);
-       nv_wr32(priv, 0x61c118 + loff, data[0] | (ocfg.dc << shift));
-       nv_wr32(priv, 0x61c120 + loff, data[1] | (ocfg.pe << shift));
-       nv_wr32(priv, 0x61c130 + loff, data[2] | (ocfg.tx_pu << 8));
-       return 0;
-}
-
-struct nvkm_output_dp_impl
-nv94_sor_dp_impl = {
-       .base.base.handle = DCB_OUTPUT_DP,
-       .base.base.ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = _nvkm_output_dp_ctor,
-               .dtor = _nvkm_output_dp_dtor,
-               .init = _nvkm_output_dp_init,
-               .fini = _nvkm_output_dp_fini,
-       },
-       .pattern = nv94_sor_dp_pattern,
-       .lnk_pwr = nv94_sor_dp_lnk_pwr,
-       .lnk_ctl = nv94_sor_dp_lnk_ctl,
-       .drv_ctl = nv94_sor_dp_drv_ctl,
-};
diff --git a/drivers/gpu/drm/nouveau/core/engine/disp/sornvd0.c b/drivers/gpu/drm/nouveau/core/engine/disp/sornvd0.c
deleted file mode 100644 (file)
index fdab293..0000000
+++ /dev/null
@@ -1,131 +0,0 @@
-/*
- * Copyright 2012 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 <core/os.h>
-
-#include <subdev/bios.h>
-#include <subdev/bios/dcb.h>
-#include <subdev/bios/dp.h>
-#include <subdev/bios/init.h>
-#include <subdev/timer.h>
-
-#include "nv50.h"
-
-static inline u32
-nvd0_sor_soff(struct nvkm_output_dp *outp)
-{
-       return (ffs(outp->base.info.or) - 1) * 0x800;
-}
-
-static inline u32
-nvd0_sor_loff(struct nvkm_output_dp *outp)
-{
-       return nvd0_sor_soff(outp) + !(outp->base.info.sorconf.link & 1) * 0x80;
-}
-
-static inline u32
-nvd0_sor_dp_lane_map(struct nv50_disp_priv *priv, u8 lane)
-{
-       static const u8 nvd0[] = { 16, 8, 0, 24 };
-       return nvd0[lane];
-}
-
-static int
-nvd0_sor_dp_pattern(struct nvkm_output_dp *outp, int pattern)
-{
-       struct nv50_disp_priv *priv = (void *)nouveau_disp(outp);
-       const u32 loff = nvd0_sor_loff(outp);
-       nv_mask(priv, 0x61c110 + loff, 0x0f0f0f0f, 0x01010101 * pattern);
-       return 0;
-}
-
-int
-nvd0_sor_dp_lnk_ctl(struct nvkm_output_dp *outp, int nr, int bw, bool ef)
-{
-       struct nv50_disp_priv *priv = (void *)nouveau_disp(outp);
-       const u32 soff = nvd0_sor_soff(outp);
-       const u32 loff = nvd0_sor_loff(outp);
-       u32 dpctrl = 0x00000000;
-       u32 clksor = 0x00000000;
-
-       clksor |= bw << 18;
-       dpctrl |= ((1 << nr) - 1) << 16;
-       if (ef)
-               dpctrl |= 0x00004000;
-
-       nv_mask(priv, 0x612300 + soff, 0x007c0000, clksor);
-       nv_mask(priv, 0x61c10c + loff, 0x001f4000, dpctrl);
-       return 0;
-}
-
-static int
-nvd0_sor_dp_drv_ctl(struct nvkm_output_dp *outp, int ln, int vs, int pe, int pc)
-{
-       struct nv50_disp_priv *priv = (void *)nouveau_disp(outp);
-       struct nouveau_bios *bios = nouveau_bios(priv);
-       const u32 shift = nvd0_sor_dp_lane_map(priv, ln);
-       const u32 loff = nvd0_sor_loff(outp);
-       u32 addr, data[4];
-       u8  ver, hdr, cnt, len;
-       struct nvbios_dpout info;
-       struct nvbios_dpcfg ocfg;
-
-       addr = nvbios_dpout_match(bios, outp->base.info.hasht,
-                                       outp->base.info.hashm,
-                                &ver, &hdr, &cnt, &len, &info);
-       if (!addr)
-               return -ENODEV;
-
-       addr = nvbios_dpcfg_match(bios, addr, pc, vs, pe,
-                                &ver, &hdr, &cnt, &len, &ocfg);
-       if (!addr)
-               return -EINVAL;
-
-       data[0] = nv_rd32(priv, 0x61c118 + loff) & ~(0x000000ff << shift);
-       data[1] = nv_rd32(priv, 0x61c120 + loff) & ~(0x000000ff << shift);
-       data[2] = nv_rd32(priv, 0x61c130 + loff);
-       if ((data[2] & 0x0000ff00) < (ocfg.tx_pu << 8) || ln == 0)
-               data[2] = (data[2] & ~0x0000ff00) | (ocfg.tx_pu << 8);
-       nv_wr32(priv, 0x61c118 + loff, data[0] | (ocfg.dc << shift));
-       nv_wr32(priv, 0x61c120 + loff, data[1] | (ocfg.pe << shift));
-       nv_wr32(priv, 0x61c130 + loff, data[2] | (ocfg.tx_pu << 8));
-       data[3] = nv_rd32(priv, 0x61c13c + loff) & ~(0x000000ff << shift);
-       nv_wr32(priv, 0x61c13c + loff, data[3] | (ocfg.pc << shift));
-       return 0;
-}
-
-struct nvkm_output_dp_impl
-nvd0_sor_dp_impl = {
-       .base.base.handle = DCB_OUTPUT_DP,
-       .base.base.ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = _nvkm_output_dp_ctor,
-               .dtor = _nvkm_output_dp_dtor,
-               .init = _nvkm_output_dp_init,
-               .fini = _nvkm_output_dp_fini,
-       },
-       .pattern = nvd0_sor_dp_pattern,
-       .lnk_pwr = nv94_sor_dp_lnk_pwr,
-       .lnk_ctl = nvd0_sor_dp_lnk_ctl,
-       .drv_ctl = nvd0_sor_dp_drv_ctl,
-};
diff --git a/drivers/gpu/drm/nouveau/core/engine/disp/vga.c b/drivers/gpu/drm/nouveau/core/engine/disp/vga.c
deleted file mode 100644 (file)
index 8836c3c..0000000
+++ /dev/null
@@ -1,220 +0,0 @@
-/*
- * Copyright 2012 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 <core/subdev.h>
-#include <core/device.h>
-#include <subdev/vga.h>
-
-u8
-nv_rdport(void *obj, int head, u16 port)
-{
-       struct nouveau_device *device = nv_device(obj);
-
-       if (device->card_type >= NV_50)
-               return nv_rd08(obj, 0x601000 + port);
-
-       if (port == 0x03c0 || port == 0x03c1 || /* AR */
-           port == 0x03c2 || port == 0x03da || /* INP0 */
-           port == 0x03d4 || port == 0x03d5)   /* CR */
-               return nv_rd08(obj, 0x601000 + (head * 0x2000) + port);
-
-       if (port == 0x03c2 || port == 0x03cc || /* MISC */
-           port == 0x03c4 || port == 0x03c5 || /* SR */
-           port == 0x03ce || port == 0x03cf) { /* GR */
-               if (device->card_type < NV_40)
-                       head = 0; /* CR44 selects head */
-               return nv_rd08(obj, 0x0c0000 + (head * 0x2000) + port);
-       }
-
-       nv_error(obj, "unknown vga port 0x%04x\n", port);
-       return 0x00;
-}
-
-void
-nv_wrport(void *obj, int head, u16 port, u8 data)
-{
-       struct nouveau_device *device = nv_device(obj);
-
-       if (device->card_type >= NV_50)
-               nv_wr08(obj, 0x601000 + port, data);
-       else
-       if (port == 0x03c0 || port == 0x03c1 || /* AR */
-           port == 0x03c2 || port == 0x03da || /* INP0 */
-           port == 0x03d4 || port == 0x03d5)   /* CR */
-               nv_wr08(obj, 0x601000 + (head * 0x2000) + port, data);
-       else
-       if (port == 0x03c2 || port == 0x03cc || /* MISC */
-           port == 0x03c4 || port == 0x03c5 || /* SR */
-           port == 0x03ce || port == 0x03cf) { /* GR */
-               if (device->card_type < NV_40)
-                       head = 0; /* CR44 selects head */
-               nv_wr08(obj, 0x0c0000 + (head * 0x2000) + port, data);
-       } else
-               nv_error(obj, "unknown vga port 0x%04x\n", port);
-}
-
-u8
-nv_rdvgas(void *obj, int head, u8 index)
-{
-       nv_wrport(obj, head, 0x03c4, index);
-       return nv_rdport(obj, head, 0x03c5);
-}
-
-void
-nv_wrvgas(void *obj, int head, u8 index, u8 value)
-{
-       nv_wrport(obj, head, 0x03c4, index);
-       nv_wrport(obj, head, 0x03c5, value);
-}
-
-u8
-nv_rdvgag(void *obj, int head, u8 index)
-{
-       nv_wrport(obj, head, 0x03ce, index);
-       return nv_rdport(obj, head, 0x03cf);
-}
-
-void
-nv_wrvgag(void *obj, int head, u8 index, u8 value)
-{
-       nv_wrport(obj, head, 0x03ce, index);
-       nv_wrport(obj, head, 0x03cf, value);
-}
-
-u8
-nv_rdvgac(void *obj, int head, u8 index)
-{
-       nv_wrport(obj, head, 0x03d4, index);
-       return nv_rdport(obj, head, 0x03d5);
-}
-
-void
-nv_wrvgac(void *obj, int head, u8 index, u8 value)
-{
-       nv_wrport(obj, head, 0x03d4, index);
-       nv_wrport(obj, head, 0x03d5, value);
-}
-
-u8
-nv_rdvgai(void *obj, int head, u16 port, u8 index)
-{
-       if (port == 0x03c4) return nv_rdvgas(obj, head, index);
-       if (port == 0x03ce) return nv_rdvgag(obj, head, index);
-       if (port == 0x03d4) return nv_rdvgac(obj, head, index);
-       nv_error(obj, "unknown indexed vga port 0x%04x\n", port);
-       return 0x00;
-}
-
-void
-nv_wrvgai(void *obj, int head, u16 port, u8 index, u8 value)
-{
-       if      (port == 0x03c4) nv_wrvgas(obj, head, index, value);
-       else if (port == 0x03ce) nv_wrvgag(obj, head, index, value);
-       else if (port == 0x03d4) nv_wrvgac(obj, head, index, value);
-       else nv_error(obj, "unknown indexed vga port 0x%04x\n", port);
-}
-
-bool
-nv_lockvgac(void *obj, bool lock)
-{
-       struct nouveau_device *dev = nv_device(obj);
-
-       bool locked = !nv_rdvgac(obj, 0, 0x1f);
-       u8 data = lock ? 0x99 : 0x57;
-       if (dev->card_type < NV_50)
-               nv_wrvgac(obj, 0, 0x1f, data);
-       else
-               nv_wrvgac(obj, 0, 0x3f, data);
-       if (dev->chipset == 0x11) {
-               if (!(nv_rd32(obj, 0x001084) & 0x10000000))
-                       nv_wrvgac(obj, 1, 0x1f, data);
-       }
-       return locked;
-}
-
-/* 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
- */
-u8
-nv_rdvgaowner(void *obj)
-{
-       if (nv_device(obj)->card_type < NV_50) {
-               if (nv_device(obj)->chipset == 0x11) {
-                       u32 tied = nv_rd32(obj, 0x001084) & 0x10000000;
-                       if (tied == 0) {
-                               u8 slA = nv_rdvgac(obj, 0, 0x28) & 0x80;
-                               u8 tvA = nv_rdvgac(obj, 0, 0x33) & 0x01;
-                               u8 slB = nv_rdvgac(obj, 1, 0x28) & 0x80;
-                               u8 tvB = nv_rdvgac(obj, 1, 0x33) & 0x01;
-                               if (slA && !tvA) return 0x00;
-                               if (slB && !tvB) return 0x03;
-                               if (slA) return 0x00;
-                               if (slB) return 0x03;
-                               return 0x00;
-                       }
-                       return 0x04;
-               }
-
-               return nv_rdvgac(obj, 0, 0x44);
-       }
-
-       nv_error(obj, "rdvgaowner after nv4x\n");
-       return 0x00;
-}
-
-void
-nv_wrvgaowner(void *obj, u8 select)
-{
-       if (nv_device(obj)->card_type < NV_50) {
-               u8 owner = (select == 1) ? 3 : select;
-               if (nv_device(obj)->chipset == 0x11) {
-                       /* workaround hw lockup bug */
-                       nv_rdvgac(obj, 0, 0x1f);
-                       nv_rdvgac(obj, 1, 0x1f);
-               }
-
-               nv_wrvgac(obj, 0, 0x44, owner);
-
-               if (nv_device(obj)->chipset == 0x11) {
-                       nv_wrvgac(obj, 0, 0x2e, owner);
-                       nv_wrvgac(obj, 0, 0x2e, owner);
-               }
-       } else
-               nv_error(obj, "wrvgaowner after nv4x\n");
-}
diff --git a/drivers/gpu/drm/nouveau/core/engine/dmaobj/base.c b/drivers/gpu/drm/nouveau/core/engine/dmaobj/base.c
deleted file mode 100644 (file)
index e1500f7..0000000
+++ /dev/null
@@ -1,165 +0,0 @@
-/*
- * Copyright 2012 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 <core/object.h>
-#include <core/client.h>
-#include <nvif/unpack.h>
-#include <nvif/class.h>
-
-#include <subdev/fb.h>
-#include <subdev/instmem.h>
-
-#include "priv.h"
-
-static int
-nvkm_dmaobj_bind(struct nouveau_dmaobj *dmaobj, struct nouveau_object *parent,
-                struct nouveau_gpuobj **pgpuobj)
-{
-       const struct nvkm_dmaeng_impl *impl = (void *)
-               nv_oclass(nv_object(dmaobj)->engine);
-       int ret = 0;
-
-       if (nv_object(dmaobj) == parent) { /* ctor bind */
-               if (nv_mclass(parent->parent) == NV_DEVICE) {
-                       /* delayed, or no, binding */
-                       return 0;
-               }
-               ret = impl->bind(dmaobj, parent, pgpuobj);
-               if (ret == 0)
-                       nouveau_object_ref(NULL, &parent);
-               return ret;
-       }
-
-       return impl->bind(dmaobj, parent, pgpuobj);
-}
-
-int
-nvkm_dmaobj_create_(struct nouveau_object *parent,
-                   struct nouveau_object *engine,
-                   struct nouveau_oclass *oclass, void **pdata, u32 *psize,
-                   int length, void **pobject)
-{
-       union {
-               struct nv_dma_v0 v0;
-       } *args = *pdata;
-       struct nouveau_instmem *instmem = nouveau_instmem(parent);
-       struct nouveau_client *client = nouveau_client(parent);
-       struct nouveau_device *device = nv_device(parent);
-       struct nouveau_fb *pfb = nouveau_fb(parent);
-       struct nouveau_dmaobj *dmaobj;
-       void *data = *pdata;
-       u32 size = *psize;
-       int ret;
-
-       ret = nouveau_object_create_(parent, engine, oclass, 0, length, pobject);
-       dmaobj = *pobject;
-       if (ret)
-               return ret;
-
-       nv_ioctl(parent, "create dma size %d\n", *psize);
-       if (nvif_unpack(args->v0, 0, 0, true)) {
-               nv_ioctl(parent, "create dma vers %d target %d access %d "
-                                "start %016llx limit %016llx\n",
-                        args->v0.version, args->v0.target, args->v0.access,
-                        args->v0.start, args->v0.limit);
-               dmaobj->target = args->v0.target;
-               dmaobj->access = args->v0.access;
-               dmaobj->start  = args->v0.start;
-               dmaobj->limit  = args->v0.limit;
-       } else
-               return ret;
-
-       *pdata = data;
-       *psize = size;
-
-       if (dmaobj->start > dmaobj->limit)
-               return -EINVAL;
-
-       switch (dmaobj->target) {
-       case NV_DMA_V0_TARGET_VM:
-               dmaobj->target = NV_MEM_TARGET_VM;
-               break;
-       case NV_DMA_V0_TARGET_VRAM:
-               if (!client->super) {
-                       if (dmaobj->limit >= pfb->ram->size - instmem->reserved)
-                               return -EACCES;
-                       if (device->card_type >= NV_50)
-                               return -EACCES;
-               }
-               dmaobj->target = NV_MEM_TARGET_VRAM;
-               break;
-       case NV_DMA_V0_TARGET_PCI:
-               if (!client->super)
-                       return -EACCES;
-               dmaobj->target = NV_MEM_TARGET_PCI;
-               break;
-       case NV_DMA_V0_TARGET_PCI_US:
-       case NV_DMA_V0_TARGET_AGP:
-               if (!client->super)
-                       return -EACCES;
-               dmaobj->target = NV_MEM_TARGET_PCI_NOSNOOP;
-               break;
-       default:
-               return -EINVAL;
-       }
-
-       switch (dmaobj->access) {
-       case NV_DMA_V0_ACCESS_VM:
-               dmaobj->access = NV_MEM_ACCESS_VM;
-               break;
-       case NV_DMA_V0_ACCESS_RD:
-               dmaobj->access = NV_MEM_ACCESS_RO;
-               break;
-       case NV_DMA_V0_ACCESS_WR:
-               dmaobj->access = NV_MEM_ACCESS_WO;
-               break;
-       case NV_DMA_V0_ACCESS_RDWR:
-               dmaobj->access = NV_MEM_ACCESS_RW;
-               break;
-       default:
-               return -EINVAL;
-       }
-
-       return ret;
-}
-
-int
-_nvkm_dmaeng_ctor(struct nouveau_object *parent, struct nouveau_object *engine,
-                 struct nouveau_oclass *oclass, void *data, u32 size,
-                 struct nouveau_object **pobject)
-{
-       const struct nvkm_dmaeng_impl *impl = (void *)oclass;
-       struct nouveau_dmaeng *dmaeng;
-       int ret;
-
-       ret = nouveau_engine_create(parent, engine, oclass, true, "DMAOBJ",
-                                   "dmaobj", &dmaeng);
-       *pobject = nv_object(dmaeng);
-       if (ret)
-               return ret;
-
-       nv_engine(dmaeng)->sclass = impl->sclass;
-       dmaeng->bind = nvkm_dmaobj_bind;
-       return 0;
-}
diff --git a/drivers/gpu/drm/nouveau/core/engine/dmaobj/nv04.c b/drivers/gpu/drm/nouveau/core/engine/dmaobj/nv04.c
deleted file mode 100644 (file)
index 20c9dbf..0000000
+++ /dev/null
@@ -1,165 +0,0 @@
-/*
- * Copyright 2012 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 <core/gpuobj.h>
-#include <nvif/class.h>
-
-#include <subdev/fb.h>
-#include <subdev/vm/nv04.h>
-
-#include "priv.h"
-
-struct nv04_dmaobj_priv {
-       struct nouveau_dmaobj base;
-       bool clone;
-       u32 flags0;
-       u32 flags2;
-};
-
-static int
-nv04_dmaobj_bind(struct nouveau_dmaobj *dmaobj,
-                struct nouveau_object *parent,
-                struct nouveau_gpuobj **pgpuobj)
-{
-       struct nv04_dmaobj_priv *priv = (void *)dmaobj;
-       struct nouveau_gpuobj *gpuobj;
-       u64 offset = priv->base.start & 0xfffff000;
-       u64 adjust = priv->base.start & 0x00000fff;
-       u32 length = priv->base.limit - priv->base.start;
-       int ret;
-
-       if (!nv_iclass(parent, NV_ENGCTX_CLASS)) {
-               switch (nv_mclass(parent->parent)) {
-               case NV03_CHANNEL_DMA:
-               case NV10_CHANNEL_DMA:
-               case NV17_CHANNEL_DMA:
-               case NV40_CHANNEL_DMA:
-                       break;
-               default:
-                       return -EINVAL;
-               }
-       }
-
-       if (priv->clone) {
-               struct nv04_vmmgr_priv *vmm = nv04_vmmgr(dmaobj);
-               struct nouveau_gpuobj *pgt = vmm->vm->pgt[0].obj[0];
-               if (!dmaobj->start)
-                       return nouveau_gpuobj_dup(parent, pgt, pgpuobj);
-               offset  = nv_ro32(pgt, 8 + (offset >> 10));
-               offset &= 0xfffff000;
-       }
-
-       ret = nouveau_gpuobj_new(parent, parent, 16, 16, 0, &gpuobj);
-       *pgpuobj = gpuobj;
-       if (ret == 0) {
-               nv_wo32(*pgpuobj, 0x00, priv->flags0 | (adjust << 20));
-               nv_wo32(*pgpuobj, 0x04, length);
-               nv_wo32(*pgpuobj, 0x08, priv->flags2 | offset);
-               nv_wo32(*pgpuobj, 0x0c, priv->flags2 | offset);
-       }
-
-       return ret;
-}
-
-static int
-nv04_dmaobj_ctor(struct nouveau_object *parent, struct nouveau_object *engine,
-                struct nouveau_oclass *oclass, void *data, u32 size,
-                struct nouveau_object **pobject)
-{
-       struct nouveau_dmaeng *dmaeng = (void *)engine;
-       struct nv04_vmmgr_priv *vmm = nv04_vmmgr(engine);
-       struct nv04_dmaobj_priv *priv;
-       int ret;
-
-       ret = nvkm_dmaobj_create(parent, engine, oclass, &data, &size, &priv);
-       *pobject = nv_object(priv);
-       if (ret || (ret = -ENOSYS, size))
-               return ret;
-
-       if (priv->base.target == NV_MEM_TARGET_VM) {
-               if (nv_object(vmm)->oclass == &nv04_vmmgr_oclass)
-                       priv->clone = true;
-               priv->base.target = NV_MEM_TARGET_PCI;
-               priv->base.access = NV_MEM_ACCESS_RW;
-       }
-
-       priv->flags0 = nv_mclass(priv);
-       switch (priv->base.target) {
-       case NV_MEM_TARGET_VRAM:
-               priv->flags0 |= 0x00003000;
-               break;
-       case NV_MEM_TARGET_PCI:
-               priv->flags0 |= 0x00023000;
-               break;
-       case NV_MEM_TARGET_PCI_NOSNOOP:
-               priv->flags0 |= 0x00033000;
-               break;
-       default:
-               return -EINVAL;
-       }
-
-       switch (priv->base.access) {
-       case NV_MEM_ACCESS_RO:
-               priv->flags0 |= 0x00004000;
-               break;
-       case NV_MEM_ACCESS_WO:
-               priv->flags0 |= 0x00008000;
-       case NV_MEM_ACCESS_RW:
-               priv->flags2 |= 0x00000002;
-               break;
-       default:
-               return -EINVAL;
-       }
-
-       return dmaeng->bind(&priv->base, nv_object(priv), (void *)pobject);
-}
-
-static struct nouveau_ofuncs
-nv04_dmaobj_ofuncs = {
-       .ctor =  nv04_dmaobj_ctor,
-       .dtor = _nvkm_dmaobj_dtor,
-       .init = _nvkm_dmaobj_init,
-       .fini = _nvkm_dmaobj_fini,
-};
-
-static struct nouveau_oclass
-nv04_dmaeng_sclass[] = {
-       { NV_DMA_FROM_MEMORY, &nv04_dmaobj_ofuncs },
-       { NV_DMA_TO_MEMORY, &nv04_dmaobj_ofuncs },
-       { NV_DMA_IN_MEMORY, &nv04_dmaobj_ofuncs },
-       {}
-};
-
-struct nouveau_oclass *
-nv04_dmaeng_oclass = &(struct nvkm_dmaeng_impl) {
-       .base.handle = NV_ENGINE(DMAOBJ, 0x04),
-       .base.ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = _nvkm_dmaeng_ctor,
-               .dtor = _nvkm_dmaeng_dtor,
-               .init = _nvkm_dmaeng_init,
-               .fini = _nvkm_dmaeng_fini,
-       },
-       .sclass = nv04_dmaeng_sclass,
-       .bind = nv04_dmaobj_bind,
-}.base;
diff --git a/drivers/gpu/drm/nouveau/core/engine/dmaobj/nv50.c b/drivers/gpu/drm/nouveau/core/engine/dmaobj/nv50.c
deleted file mode 100644 (file)
index a740ddb..0000000
+++ /dev/null
@@ -1,197 +0,0 @@
-/*
- * Copyright 2012 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 <core/client.h>
-#include <core/gpuobj.h>
-#include <nvif/unpack.h>
-#include <nvif/class.h>
-
-#include <subdev/fb.h>
-
-#include "priv.h"
-
-struct nv50_dmaobj_priv {
-       struct nouveau_dmaobj base;
-       u32 flags0;
-       u32 flags5;
-};
-
-static int
-nv50_dmaobj_bind(struct nouveau_dmaobj *dmaobj,
-                struct nouveau_object *parent,
-                struct nouveau_gpuobj **pgpuobj)
-{
-       struct nv50_dmaobj_priv *priv = (void *)dmaobj;
-       int ret;
-
-       if (!nv_iclass(parent, NV_ENGCTX_CLASS)) {
-               switch (nv_mclass(parent->parent)) {
-               case NV40_CHANNEL_DMA:
-               case NV50_CHANNEL_GPFIFO:
-               case G82_CHANNEL_GPFIFO:
-               case NV50_DISP_CORE_CHANNEL_DMA:
-               case G82_DISP_CORE_CHANNEL_DMA:
-               case GT206_DISP_CORE_CHANNEL_DMA:
-               case GT200_DISP_CORE_CHANNEL_DMA:
-               case GT214_DISP_CORE_CHANNEL_DMA:
-               case NV50_DISP_BASE_CHANNEL_DMA:
-               case G82_DISP_BASE_CHANNEL_DMA:
-               case GT200_DISP_BASE_CHANNEL_DMA:
-               case GT214_DISP_BASE_CHANNEL_DMA:
-               case NV50_DISP_OVERLAY_CHANNEL_DMA:
-               case G82_DISP_OVERLAY_CHANNEL_DMA:
-               case GT200_DISP_OVERLAY_CHANNEL_DMA:
-               case GT214_DISP_OVERLAY_CHANNEL_DMA:
-                       break;
-               default:
-                       return -EINVAL;
-               }
-       }
-
-       ret = nouveau_gpuobj_new(parent, parent, 24, 32, 0, pgpuobj);
-       if (ret == 0) {
-               nv_wo32(*pgpuobj, 0x00, priv->flags0 | nv_mclass(dmaobj));
-               nv_wo32(*pgpuobj, 0x04, lower_32_bits(priv->base.limit));
-               nv_wo32(*pgpuobj, 0x08, lower_32_bits(priv->base.start));
-               nv_wo32(*pgpuobj, 0x0c, upper_32_bits(priv->base.limit) << 24 |
-                                       upper_32_bits(priv->base.start));
-               nv_wo32(*pgpuobj, 0x10, 0x00000000);
-               nv_wo32(*pgpuobj, 0x14, priv->flags5);
-       }
-
-       return ret;
-}
-
-static int
-nv50_dmaobj_ctor(struct nouveau_object *parent, struct nouveau_object *engine,
-                struct nouveau_oclass *oclass, void *data, u32 size,
-                struct nouveau_object **pobject)
-{
-       struct nouveau_dmaeng *dmaeng = (void *)engine;
-       union {
-               struct nv50_dma_v0 v0;
-       } *args;
-       struct nv50_dmaobj_priv *priv;
-       u32 user, part, comp, kind;
-       int ret;
-
-       ret = nvkm_dmaobj_create(parent, engine, oclass, &data, &size, &priv);
-       *pobject = nv_object(priv);
-       if (ret)
-               return ret;
-       args = data;
-
-       nv_ioctl(parent, "create nv50 dma size %d\n", size);
-       if (nvif_unpack(args->v0, 0, 0, false)) {
-               nv_ioctl(parent, "create nv50 dma vers %d priv %d part %d "
-                                "comp %d kind %02x\n", args->v0.version,
-                        args->v0.priv, args->v0.part, args->v0.comp,
-                        args->v0.kind);
-               user = args->v0.priv;
-               part = args->v0.part;
-               comp = args->v0.comp;
-               kind = args->v0.kind;
-       } else
-       if (size == 0) {
-               if (priv->base.target != NV_MEM_TARGET_VM) {
-                       user = NV50_DMA_V0_PRIV_US;
-                       part = NV50_DMA_V0_PART_256;
-                       comp = NV50_DMA_V0_COMP_NONE;
-                       kind = NV50_DMA_V0_KIND_PITCH;
-               } else {
-                       user = NV50_DMA_V0_PRIV_VM;
-                       part = NV50_DMA_V0_PART_VM;
-                       comp = NV50_DMA_V0_COMP_VM;
-                       kind = NV50_DMA_V0_KIND_VM;
-               }
-       } else
-               return ret;
-
-       if (user > 2 || part > 2 || comp > 3 || kind > 0x7f)
-               return -EINVAL;
-       priv->flags0 = (comp << 29) | (kind << 22) | (user << 20);
-       priv->flags5 = (part << 16);
-
-       switch (priv->base.target) {
-       case NV_MEM_TARGET_VM:
-               priv->flags0 |= 0x00000000;
-               break;
-       case NV_MEM_TARGET_VRAM:
-               priv->flags0 |= 0x00010000;
-               break;
-       case NV_MEM_TARGET_PCI:
-               priv->flags0 |= 0x00020000;
-               break;
-       case NV_MEM_TARGET_PCI_NOSNOOP:
-               priv->flags0 |= 0x00030000;
-               break;
-       default:
-               return -EINVAL;
-       }
-
-       switch (priv->base.access) {
-       case NV_MEM_ACCESS_VM:
-               break;
-       case NV_MEM_ACCESS_RO:
-               priv->flags0 |= 0x00040000;
-               break;
-       case NV_MEM_ACCESS_WO:
-       case NV_MEM_ACCESS_RW:
-               priv->flags0 |= 0x00080000;
-               break;
-       default:
-               return -EINVAL;
-       }
-
-       return dmaeng->bind(&priv->base, nv_object(priv), (void *)pobject);
-}
-
-static struct nouveau_ofuncs
-nv50_dmaobj_ofuncs = {
-       .ctor =  nv50_dmaobj_ctor,
-       .dtor = _nvkm_dmaobj_dtor,
-       .init = _nvkm_dmaobj_init,
-       .fini = _nvkm_dmaobj_fini,
-};
-
-static struct nouveau_oclass
-nv50_dmaeng_sclass[] = {
-       { NV_DMA_FROM_MEMORY, &nv50_dmaobj_ofuncs },
-       { NV_DMA_TO_MEMORY, &nv50_dmaobj_ofuncs },
-       { NV_DMA_IN_MEMORY, &nv50_dmaobj_ofuncs },
-       {}
-};
-
-struct nouveau_oclass *
-nv50_dmaeng_oclass = &(struct nvkm_dmaeng_impl) {
-       .base.handle = NV_ENGINE(DMAOBJ, 0x50),
-       .base.ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = _nvkm_dmaeng_ctor,
-               .dtor = _nvkm_dmaeng_dtor,
-               .init = _nvkm_dmaeng_init,
-               .fini = _nvkm_dmaeng_fini,
-       },
-       .sclass = nv50_dmaeng_sclass,
-       .bind = nv50_dmaobj_bind,
-}.base;
diff --git a/drivers/gpu/drm/nouveau/core/engine/dmaobj/nvc0.c b/drivers/gpu/drm/nouveau/core/engine/dmaobj/nvc0.c
deleted file mode 100644 (file)
index 88ec33b..0000000
+++ /dev/null
@@ -1,179 +0,0 @@
-/*
- * Copyright 2012 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 <core/client.h>
-#include <core/device.h>
-#include <core/gpuobj.h>
-#include <nvif/unpack.h>
-#include <nvif/class.h>
-
-#include <subdev/fb.h>
-
-#include "priv.h"
-
-struct nvc0_dmaobj_priv {
-       struct nouveau_dmaobj base;
-       u32 flags0;
-       u32 flags5;
-};
-
-static int
-nvc0_dmaobj_bind(struct nouveau_dmaobj *dmaobj,
-                struct nouveau_object *parent,
-                struct nouveau_gpuobj **pgpuobj)
-{
-       struct nvc0_dmaobj_priv *priv = (void *)dmaobj;
-       int ret;
-
-       if (!nv_iclass(parent, NV_ENGCTX_CLASS)) {
-               switch (nv_mclass(parent->parent)) {
-               case GT214_DISP_CORE_CHANNEL_DMA:
-               case GT214_DISP_BASE_CHANNEL_DMA:
-               case GT214_DISP_OVERLAY_CHANNEL_DMA:
-                       break;
-               default:
-                       return -EINVAL;
-               }
-       } else
-               return 0;
-
-       ret = nouveau_gpuobj_new(parent, parent, 24, 32, 0, pgpuobj);
-       if (ret == 0) {
-               nv_wo32(*pgpuobj, 0x00, priv->flags0 | nv_mclass(dmaobj));
-               nv_wo32(*pgpuobj, 0x04, lower_32_bits(priv->base.limit));
-               nv_wo32(*pgpuobj, 0x08, lower_32_bits(priv->base.start));
-               nv_wo32(*pgpuobj, 0x0c, upper_32_bits(priv->base.limit) << 24 |
-                                       upper_32_bits(priv->base.start));
-               nv_wo32(*pgpuobj, 0x10, 0x00000000);
-               nv_wo32(*pgpuobj, 0x14, priv->flags5);
-       }
-
-       return ret;
-}
-
-static int
-nvc0_dmaobj_ctor(struct nouveau_object *parent, struct nouveau_object *engine,
-                struct nouveau_oclass *oclass, void *data, u32 size,
-                struct nouveau_object **pobject)
-{
-       struct nouveau_dmaeng *dmaeng = (void *)engine;
-       union {
-               struct gf100_dma_v0 v0;
-       } *args;
-       struct nvc0_dmaobj_priv *priv;
-       u32 kind, user, unkn;
-       int ret;
-
-       ret = nvkm_dmaobj_create(parent, engine, oclass, &data, &size, &priv);
-       *pobject = nv_object(priv);
-       if (ret)
-               return ret;
-       args = data;
-
-       nv_ioctl(parent, "create gf100 dma size %d\n", size);
-       if (nvif_unpack(args->v0, 0, 0, false)) {
-               nv_ioctl(parent, "create gf100 dma vers %d priv %d kind %02x\n",
-                        args->v0.version, args->v0.priv, args->v0.kind);
-               kind = args->v0.kind;
-               user = args->v0.priv;
-               unkn = 0;
-       } else
-       if (size == 0) {
-               if (priv->base.target != NV_MEM_TARGET_VM) {
-                       kind = GF100_DMA_V0_KIND_PITCH;
-                       user = GF100_DMA_V0_PRIV_US;
-                       unkn = 2;
-               } else {
-                       kind = GF100_DMA_V0_KIND_VM;
-                       user = GF100_DMA_V0_PRIV_VM;
-                       unkn = 0;
-               }
-       } else
-               return ret;
-
-       if (user > 2)
-               return -EINVAL;
-       priv->flags0 |= (kind << 22) | (user << 20);
-       priv->flags5 |= (unkn << 16);
-
-       switch (priv->base.target) {
-       case NV_MEM_TARGET_VM:
-               priv->flags0 |= 0x00000000;
-               break;
-       case NV_MEM_TARGET_VRAM:
-               priv->flags0 |= 0x00010000;
-               break;
-       case NV_MEM_TARGET_PCI:
-               priv->flags0 |= 0x00020000;
-               break;
-       case NV_MEM_TARGET_PCI_NOSNOOP:
-               priv->flags0 |= 0x00030000;
-               break;
-       default:
-               return -EINVAL;
-       }
-
-       switch (priv->base.access) {
-       case NV_MEM_ACCESS_VM:
-               break;
-       case NV_MEM_ACCESS_RO:
-               priv->flags0 |= 0x00040000;
-               break;
-       case NV_MEM_ACCESS_WO:
-       case NV_MEM_ACCESS_RW:
-               priv->flags0 |= 0x00080000;
-               break;
-       }
-
-       return dmaeng->bind(&priv->base, nv_object(priv), (void *)pobject);
-}
-
-static struct nouveau_ofuncs
-nvc0_dmaobj_ofuncs = {
-       .ctor =  nvc0_dmaobj_ctor,
-       .dtor = _nvkm_dmaobj_dtor,
-       .init = _nvkm_dmaobj_init,
-       .fini = _nvkm_dmaobj_fini,
-};
-
-static struct nouveau_oclass
-nvc0_dmaeng_sclass[] = {
-       { NV_DMA_FROM_MEMORY, &nvc0_dmaobj_ofuncs },
-       { NV_DMA_TO_MEMORY, &nvc0_dmaobj_ofuncs },
-       { NV_DMA_IN_MEMORY, &nvc0_dmaobj_ofuncs },
-       {}
-};
-
-struct nouveau_oclass *
-nvc0_dmaeng_oclass = &(struct nvkm_dmaeng_impl) {
-       .base.handle = NV_ENGINE(DMAOBJ, 0xc0),
-       .base.ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = _nvkm_dmaeng_ctor,
-               .dtor = _nvkm_dmaeng_dtor,
-               .init = _nvkm_dmaeng_init,
-               .fini = _nvkm_dmaeng_fini,
-       },
-       .sclass = nvc0_dmaeng_sclass,
-       .bind = nvc0_dmaobj_bind,
-}.base;
diff --git a/drivers/gpu/drm/nouveau/core/engine/dmaobj/nvd0.c b/drivers/gpu/drm/nouveau/core/engine/dmaobj/nvd0.c
deleted file mode 100644 (file)
index 19f5f65..0000000
+++ /dev/null
@@ -1,168 +0,0 @@
-/*
- * Copyright 2012 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 <core/client.h>
-#include <core/device.h>
-#include <core/gpuobj.h>
-#include <nvif/unpack.h>
-#include <nvif/class.h>
-
-#include <subdev/fb.h>
-
-#include "priv.h"
-
-struct nvd0_dmaobj_priv {
-       struct nouveau_dmaobj base;
-       u32 flags0;
-};
-
-static int
-nvd0_dmaobj_bind(struct nouveau_dmaobj *dmaobj,
-                struct nouveau_object *parent,
-                struct nouveau_gpuobj **pgpuobj)
-{
-       struct nvd0_dmaobj_priv *priv = (void *)dmaobj;
-       int ret;
-
-       if (!nv_iclass(parent, NV_ENGCTX_CLASS)) {
-               switch (nv_mclass(parent->parent)) {
-               case GF110_DISP_CORE_CHANNEL_DMA:
-               case GK104_DISP_CORE_CHANNEL_DMA:
-               case GK110_DISP_CORE_CHANNEL_DMA:
-               case GM107_DISP_CORE_CHANNEL_DMA:
-               case GM204_DISP_CORE_CHANNEL_DMA:
-               case GF110_DISP_BASE_CHANNEL_DMA:
-               case GK104_DISP_BASE_CHANNEL_DMA:
-               case GK110_DISP_BASE_CHANNEL_DMA:
-               case GF110_DISP_OVERLAY_CONTROL_DMA:
-               case GK104_DISP_OVERLAY_CONTROL_DMA:
-                       break;
-               default:
-                       return -EINVAL;
-               }
-       } else
-               return 0;
-
-       ret = nouveau_gpuobj_new(parent, parent, 24, 32, 0, pgpuobj);
-       if (ret == 0) {
-               nv_wo32(*pgpuobj, 0x00, priv->flags0);
-               nv_wo32(*pgpuobj, 0x04, priv->base.start >> 8);
-               nv_wo32(*pgpuobj, 0x08, priv->base.limit >> 8);
-               nv_wo32(*pgpuobj, 0x0c, 0x00000000);
-               nv_wo32(*pgpuobj, 0x10, 0x00000000);
-               nv_wo32(*pgpuobj, 0x14, 0x00000000);
-       }
-
-       return ret;
-}
-
-static int
-nvd0_dmaobj_ctor(struct nouveau_object *parent, struct nouveau_object *engine,
-                struct nouveau_oclass *oclass, void *data, u32 size,
-                struct nouveau_object **pobject)
-{
-       struct nouveau_dmaeng *dmaeng = (void *)engine;
-       union {
-               struct gf110_dma_v0 v0;
-       } *args;
-       struct nvd0_dmaobj_priv *priv;
-       u32 kind, page;
-       int ret;
-
-       ret = nvkm_dmaobj_create(parent, engine, oclass, &data, &size, &priv);
-       *pobject = nv_object(priv);
-       if (ret)
-               return ret;
-       args = data;
-
-       nv_ioctl(parent, "create gf110 dma size %d\n", size);
-       if (nvif_unpack(args->v0, 0, 0, false)) {
-               nv_ioctl(parent, "create gf100 dma vers %d page %d kind %02x\n",
-                        args->v0.version, args->v0.page, args->v0.kind);
-               kind = args->v0.kind;
-               page = args->v0.page;
-       } else
-       if (size == 0) {
-               if (priv->base.target != NV_MEM_TARGET_VM) {
-                       kind = GF110_DMA_V0_KIND_PITCH;
-                       page = GF110_DMA_V0_PAGE_SP;
-               } else {
-                       kind = GF110_DMA_V0_KIND_VM;
-                       page = GF110_DMA_V0_PAGE_LP;
-               }
-       } else
-               return ret;
-
-       if (page > 1)
-               return -EINVAL;
-       priv->flags0 = (kind << 20) | (page << 6);
-
-       switch (priv->base.target) {
-       case NV_MEM_TARGET_VRAM:
-               priv->flags0 |= 0x00000009;
-               break;
-       case NV_MEM_TARGET_VM:
-       case NV_MEM_TARGET_PCI:
-       case NV_MEM_TARGET_PCI_NOSNOOP:
-               /* XXX: don't currently know how to construct a real one
-                *      of these.  we only use them to represent pushbufs
-                *      on these chipsets, and the classes that use them
-                *      deal with the target themselves.
-                */
-               break;
-       default:
-               return -EINVAL;
-       }
-
-       return dmaeng->bind(&priv->base, nv_object(priv), (void *)pobject);
-}
-
-static struct nouveau_ofuncs
-nvd0_dmaobj_ofuncs = {
-       .ctor =  nvd0_dmaobj_ctor,
-       .dtor = _nvkm_dmaobj_dtor,
-       .init = _nvkm_dmaobj_init,
-       .fini = _nvkm_dmaobj_fini,
-};
-
-static struct nouveau_oclass
-nvd0_dmaeng_sclass[] = {
-       { NV_DMA_FROM_MEMORY, &nvd0_dmaobj_ofuncs },
-       { NV_DMA_TO_MEMORY, &nvd0_dmaobj_ofuncs },
-       { NV_DMA_IN_MEMORY, &nvd0_dmaobj_ofuncs },
-       {}
-};
-
-struct nouveau_oclass *
-nvd0_dmaeng_oclass = &(struct nvkm_dmaeng_impl) {
-       .base.handle = NV_ENGINE(DMAOBJ, 0xd0),
-       .base.ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = _nvkm_dmaeng_ctor,
-               .dtor = _nvkm_dmaeng_dtor,
-               .init = _nvkm_dmaeng_init,
-               .fini = _nvkm_dmaeng_fini,
-       },
-       .sclass = nvd0_dmaeng_sclass,
-       .bind = nvd0_dmaobj_bind,
-}.base;
diff --git a/drivers/gpu/drm/nouveau/core/engine/dmaobj/priv.h b/drivers/gpu/drm/nouveau/core/engine/dmaobj/priv.h
deleted file mode 100644 (file)
index 36f7438..0000000
+++ /dev/null
@@ -1,30 +0,0 @@
-#ifndef __NVKM_DMAOBJ_PRIV_H__
-#define __NVKM_DMAOBJ_PRIV_H__
-
-#include <engine/dmaobj.h>
-
-#define nvkm_dmaobj_create(p,e,c,pa,sa,d)                                      \
-       nvkm_dmaobj_create_((p), (e), (c), (pa), (sa), sizeof(**d), (void **)d)
-
-int nvkm_dmaobj_create_(struct nouveau_object *, struct nouveau_object *,
-                       struct nouveau_oclass *, void **, u32 *,
-                       int, void **);
-#define _nvkm_dmaobj_dtor nouveau_object_destroy
-#define _nvkm_dmaobj_init nouveau_object_init
-#define _nvkm_dmaobj_fini nouveau_object_fini
-
-int _nvkm_dmaeng_ctor(struct nouveau_object *, struct nouveau_object *,
-                     struct nouveau_oclass *, void *, u32,
-                     struct nouveau_object **);
-#define _nvkm_dmaeng_dtor _nouveau_engine_dtor
-#define _nvkm_dmaeng_init _nouveau_engine_init
-#define _nvkm_dmaeng_fini _nouveau_engine_fini
-
-struct nvkm_dmaeng_impl {
-       struct nouveau_oclass base;
-       struct nouveau_oclass *sclass;
-       int (*bind)(struct nouveau_dmaobj *, struct nouveau_object *,
-                   struct nouveau_gpuobj **);
-};
-
-#endif
diff --git a/drivers/gpu/drm/nouveau/core/engine/falcon.c b/drivers/gpu/drm/nouveau/core/engine/falcon.c
deleted file mode 100644 (file)
index 2914646..0000000
+++ /dev/null
@@ -1,278 +0,0 @@
-/*
- * Copyright 2012 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.
- */
-
-#include <engine/falcon.h>
-#include <subdev/timer.h>
-
-void
-nouveau_falcon_intr(struct nouveau_subdev *subdev)
-{
-       struct nouveau_falcon *falcon = (void *)subdev;
-       u32 dispatch = nv_ro32(falcon, 0x01c);
-       u32 intr = nv_ro32(falcon, 0x008) & dispatch & ~(dispatch >> 16);
-
-       if (intr & 0x00000010) {
-               nv_debug(falcon, "ucode halted\n");
-               nv_wo32(falcon, 0x004, 0x00000010);
-               intr &= ~0x00000010;
-       }
-
-       if (intr)  {
-               nv_error(falcon, "unhandled intr 0x%08x\n", intr);
-               nv_wo32(falcon, 0x004, intr);
-       }
-}
-
-u32
-_nouveau_falcon_rd32(struct nouveau_object *object, u64 addr)
-{
-       struct nouveau_falcon *falcon = (void *)object;
-       return nv_rd32(falcon, falcon->addr + addr);
-}
-
-void
-_nouveau_falcon_wr32(struct nouveau_object *object, u64 addr, u32 data)
-{
-       struct nouveau_falcon *falcon = (void *)object;
-       nv_wr32(falcon, falcon->addr + addr, data);
-}
-
-static void *
-vmemdup(const void *src, size_t len)
-{
-       void *p = vmalloc(len);
-
-       if (p)
-               memcpy(p, src, len);
-       return p;
-}
-
-int
-_nouveau_falcon_init(struct nouveau_object *object)
-{
-       struct nouveau_device *device = nv_device(object);
-       struct nouveau_falcon *falcon = (void *)object;
-       const struct firmware *fw;
-       char name[32] = "internal";
-       int ret, i;
-       u32 caps;
-
-       /* enable engine, and determine its capabilities */
-       ret = nouveau_engine_init(&falcon->base);
-       if (ret)
-               return ret;
-
-       if (device->chipset <  0xa3 ||
-           device->chipset == 0xaa || device->chipset == 0xac) {
-               falcon->version = 0;
-               falcon->secret  = (falcon->addr == 0x087000) ? 1 : 0;
-       } else {
-               caps = nv_ro32(falcon, 0x12c);
-               falcon->version = (caps & 0x0000000f);
-               falcon->secret  = (caps & 0x00000030) >> 4;
-       }
-
-       caps = nv_ro32(falcon, 0x108);
-       falcon->code.limit = (caps & 0x000001ff) << 8;
-       falcon->data.limit = (caps & 0x0003fe00) >> 1;
-
-       nv_debug(falcon, "falcon version: %d\n", falcon->version);
-       nv_debug(falcon, "secret level: %d\n", falcon->secret);
-       nv_debug(falcon, "code limit: %d\n", falcon->code.limit);
-       nv_debug(falcon, "data limit: %d\n", falcon->data.limit);
-
-       /* wait for 'uc halted' to be signalled before continuing */
-       if (falcon->secret && falcon->version < 4) {
-               if (!falcon->version)
-                       nv_wait(falcon, 0x008, 0x00000010, 0x00000010);
-               else
-                       nv_wait(falcon, 0x180, 0x80000000, 0);
-               nv_wo32(falcon, 0x004, 0x00000010);
-       }
-
-       /* disable all interrupts */
-       nv_wo32(falcon, 0x014, 0xffffffff);
-
-       /* no default ucode provided by the engine implementation, try and
-        * locate a "self-bootstrapping" firmware image for the engine
-        */
-       if (!falcon->code.data) {
-               snprintf(name, sizeof(name), "nouveau/nv%02x_fuc%03x",
-                        device->chipset, falcon->addr >> 12);
-
-               ret = request_firmware(&fw, name, nv_device_base(device));
-               if (ret == 0) {
-                       falcon->code.data = vmemdup(fw->data, fw->size);
-                       falcon->code.size = fw->size;
-                       falcon->data.data = NULL;
-                       falcon->data.size = 0;
-                       release_firmware(fw);
-               }
-
-               falcon->external = true;
-       }
-
-       /* next step is to try and load "static code/data segment" firmware
-        * images for the engine
-        */
-       if (!falcon->code.data) {
-               snprintf(name, sizeof(name), "nouveau/nv%02x_fuc%03xd",
-                        device->chipset, falcon->addr >> 12);
-
-               ret = request_firmware(&fw, name, nv_device_base(device));
-               if (ret) {
-                       nv_error(falcon, "unable to load firmware data\n");
-                       return ret;
-               }
-
-               falcon->data.data = vmemdup(fw->data, fw->size);
-               falcon->data.size = fw->size;
-               release_firmware(fw);
-               if (!falcon->data.data)
-                       return -ENOMEM;
-
-               snprintf(name, sizeof(name), "nouveau/nv%02x_fuc%03xc",
-                        device->chipset, falcon->addr >> 12);
-
-               ret = request_firmware(&fw, name, nv_device_base(device));
-               if (ret) {
-                       nv_error(falcon, "unable to load firmware code\n");
-                       return ret;
-               }
-
-               falcon->code.data = vmemdup(fw->data, fw->size);
-               falcon->code.size = fw->size;
-               release_firmware(fw);
-               if (!falcon->code.data)
-                       return -ENOMEM;
-       }
-
-       nv_debug(falcon, "firmware: %s (%s)\n", name, falcon->data.data ?
-                "static code/data segments" : "self-bootstrapping");
-
-       /* ensure any "self-bootstrapping" firmware image is in vram */
-       if (!falcon->data.data && !falcon->core) {
-               ret = nouveau_gpuobj_new(object->parent, NULL,
-                                        falcon->code.size, 256, 0,
-                                       &falcon->core);
-               if (ret) {
-                       nv_error(falcon, "core allocation failed, %d\n", ret);
-                       return ret;
-               }
-
-               for (i = 0; i < falcon->code.size; i += 4)
-                       nv_wo32(falcon->core, i, falcon->code.data[i / 4]);
-       }
-
-       /* upload firmware bootloader (or the full code segments) */
-       if (falcon->core) {
-               if (device->card_type < NV_C0)
-                       nv_wo32(falcon, 0x618, 0x04000000);
-               else
-                       nv_wo32(falcon, 0x618, 0x00000114);
-               nv_wo32(falcon, 0x11c, 0);
-               nv_wo32(falcon, 0x110, falcon->core->addr >> 8);
-               nv_wo32(falcon, 0x114, 0);
-               nv_wo32(falcon, 0x118, 0x00006610);
-       } else {
-               if (falcon->code.size > falcon->code.limit ||
-                   falcon->data.size > falcon->data.limit) {
-                       nv_error(falcon, "ucode exceeds falcon limit(s)\n");
-                       return -EINVAL;
-               }
-
-               if (falcon->version < 3) {
-                       nv_wo32(falcon, 0xff8, 0x00100000);
-                       for (i = 0; i < falcon->code.size / 4; i++)
-                               nv_wo32(falcon, 0xff4, falcon->code.data[i]);
-               } else {
-                       nv_wo32(falcon, 0x180, 0x01000000);
-                       for (i = 0; i < falcon->code.size / 4; i++) {
-                               if ((i & 0x3f) == 0)
-                                       nv_wo32(falcon, 0x188, i >> 6);
-                               nv_wo32(falcon, 0x184, falcon->code.data[i]);
-                       }
-               }
-       }
-
-       /* upload data segment (if necessary), zeroing the remainder */
-       if (falcon->version < 3) {
-               nv_wo32(falcon, 0xff8, 0x00000000);
-               for (i = 0; !falcon->core && i < falcon->data.size / 4; i++)
-                       nv_wo32(falcon, 0xff4, falcon->data.data[i]);
-               for (; i < falcon->data.limit; i += 4)
-                       nv_wo32(falcon, 0xff4, 0x00000000);
-       } else {
-               nv_wo32(falcon, 0x1c0, 0x01000000);
-               for (i = 0; !falcon->core && i < falcon->data.size / 4; i++)
-                       nv_wo32(falcon, 0x1c4, falcon->data.data[i]);
-               for (; i < falcon->data.limit / 4; i++)
-                       nv_wo32(falcon, 0x1c4, 0x00000000);
-       }
-
-       /* start it running */
-       nv_wo32(falcon, 0x10c, 0x00000001); /* BLOCK_ON_FIFO */
-       nv_wo32(falcon, 0x104, 0x00000000); /* ENTRY */
-       nv_wo32(falcon, 0x100, 0x00000002); /* TRIGGER */
-       nv_wo32(falcon, 0x048, 0x00000003); /* FIFO | CHSW */
-       return 0;
-}
-
-int
-_nouveau_falcon_fini(struct nouveau_object *object, bool suspend)
-{
-       struct nouveau_falcon *falcon = (void *)object;
-
-       if (!suspend) {
-               nouveau_gpuobj_ref(NULL, &falcon->core);
-               if (falcon->external) {
-                       vfree(falcon->data.data);
-                       vfree(falcon->code.data);
-                       falcon->code.data = NULL;
-               }
-       }
-
-       nv_mo32(falcon, 0x048, 0x00000003, 0x00000000);
-       nv_wo32(falcon, 0x014, 0xffffffff);
-
-       return nouveau_engine_fini(&falcon->base, suspend);
-}
-
-int
-nouveau_falcon_create_(struct nouveau_object *parent,
-                      struct nouveau_object *engine,
-                      struct nouveau_oclass *oclass, u32 addr, bool enable,
-                      const char *iname, const char *fname,
-                      int length, void **pobject)
-{
-       struct nouveau_falcon *falcon;
-       int ret;
-
-       ret = nouveau_engine_create_(parent, engine, oclass, enable, iname,
-                                    fname, length, pobject);
-       falcon = *pobject;
-       if (ret)
-               return ret;
-
-       falcon->addr = addr;
-       return 0;
-}
diff --git a/drivers/gpu/drm/nouveau/core/engine/fifo/base.c b/drivers/gpu/drm/nouveau/core/engine/fifo/base.c
deleted file mode 100644 (file)
index ac8375c..0000000
+++ /dev/null
@@ -1,283 +0,0 @@
-/*
- * Copyright 2012 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 <core/client.h>
-#include <core/object.h>
-#include <core/handle.h>
-#include <core/event.h>
-#include <nvif/unpack.h>
-#include <nvif/class.h>
-#include <nvif/event.h>
-
-#include <engine/dmaobj.h>
-#include <engine/fifo.h>
-
-static int
-nouveau_fifo_event_ctor(struct nouveau_object *object, void *data, u32 size,
-                       struct nvkm_notify *notify)
-{
-       if (size == 0) {
-               notify->size  = 0;
-               notify->types = 1;
-               notify->index = 0;
-               return 0;
-       }
-       return -ENOSYS;
-}
-
-static const struct nvkm_event_func
-nouveau_fifo_event_func = {
-       .ctor = nouveau_fifo_event_ctor,
-};
-
-int
-nouveau_fifo_channel_create_(struct nouveau_object *parent,
-                            struct nouveau_object *engine,
-                            struct nouveau_oclass *oclass,
-                            int bar, u32 addr, u32 size, u32 pushbuf,
-                            u64 engmask, int len, void **ptr)
-{
-       struct nouveau_device *device = nv_device(engine);
-       struct nouveau_fifo *priv = (void *)engine;
-       struct nouveau_fifo_chan *chan;
-       struct nouveau_dmaeng *dmaeng;
-       unsigned long flags;
-       int ret;
-
-       /* create base object class */
-       ret = nouveau_namedb_create_(parent, engine, oclass, 0, NULL,
-                                    engmask, len, ptr);
-       chan = *ptr;
-       if (ret)
-               return ret;
-
-       /* validate dma object representing push buffer */
-       chan->pushdma = (void *)nouveau_handle_ref(parent, pushbuf);
-       if (!chan->pushdma)
-               return -ENOENT;
-
-       dmaeng = (void *)chan->pushdma->base.engine;
-       switch (chan->pushdma->base.oclass->handle) {
-       case NV_DMA_FROM_MEMORY:
-       case NV_DMA_IN_MEMORY:
-               break;
-       default:
-               return -EINVAL;
-       }
-
-       ret = dmaeng->bind(chan->pushdma, parent, &chan->pushgpu);
-       if (ret)
-               return ret;
-
-       /* find a free fifo channel */
-       spin_lock_irqsave(&priv->lock, flags);
-       for (chan->chid = priv->min; chan->chid < priv->max; chan->chid++) {
-               if (!priv->channel[chan->chid]) {
-                       priv->channel[chan->chid] = nv_object(chan);
-                       break;
-               }
-       }
-       spin_unlock_irqrestore(&priv->lock, flags);
-
-       if (chan->chid == priv->max) {
-               nv_error(priv, "no free channels\n");
-               return -ENOSPC;
-       }
-
-       chan->addr = nv_device_resource_start(device, bar) +
-                    addr + size * chan->chid;
-       chan->size = size;
-       nvkm_event_send(&priv->cevent, 1, 0, NULL, 0);
-       return 0;
-}
-
-void
-nouveau_fifo_channel_destroy(struct nouveau_fifo_chan *chan)
-{
-       struct nouveau_fifo *priv = (void *)nv_object(chan)->engine;
-       unsigned long flags;
-
-       if (chan->user)
-               iounmap(chan->user);
-
-       spin_lock_irqsave(&priv->lock, flags);
-       priv->channel[chan->chid] = NULL;
-       spin_unlock_irqrestore(&priv->lock, flags);
-
-       nouveau_gpuobj_ref(NULL, &chan->pushgpu);
-       nouveau_object_ref(NULL, (struct nouveau_object **)&chan->pushdma);
-       nouveau_namedb_destroy(&chan->base);
-}
-
-void
-_nouveau_fifo_channel_dtor(struct nouveau_object *object)
-{
-       struct nouveau_fifo_chan *chan = (void *)object;
-       nouveau_fifo_channel_destroy(chan);
-}
-
-int
-_nouveau_fifo_channel_map(struct nouveau_object *object, u64 *addr, u32 *size)
-{
-       struct nouveau_fifo_chan *chan = (void *)object;
-       *addr = chan->addr;
-       *size = chan->size;
-       return 0;
-}
-
-u32
-_nouveau_fifo_channel_rd32(struct nouveau_object *object, u64 addr)
-{
-       struct nouveau_fifo_chan *chan = (void *)object;
-       if (unlikely(!chan->user)) {
-               chan->user = ioremap(chan->addr, chan->size);
-               if (WARN_ON_ONCE(chan->user == NULL))
-                       return 0;
-       }
-       return ioread32_native(chan->user + addr);
-}
-
-void
-_nouveau_fifo_channel_wr32(struct nouveau_object *object, u64 addr, u32 data)
-{
-       struct nouveau_fifo_chan *chan = (void *)object;
-       if (unlikely(!chan->user)) {
-               chan->user = ioremap(chan->addr, chan->size);
-               if (WARN_ON_ONCE(chan->user == NULL))
-                       return;
-       }
-       iowrite32_native(data, chan->user + addr);
-}
-
-int
-nouveau_fifo_uevent_ctor(struct nouveau_object *object, void *data, u32 size,
-                        struct nvkm_notify *notify)
-{
-       union {
-               struct nvif_notify_uevent_req none;
-       } *req = data;
-       int ret;
-
-       if (nvif_unvers(req->none)) {
-               notify->size  = sizeof(struct nvif_notify_uevent_rep);
-               notify->types = 1;
-               notify->index = 0;
-       }
-
-       return ret;
-}
-
-void
-nouveau_fifo_uevent(struct nouveau_fifo *fifo)
-{
-       struct nvif_notify_uevent_rep rep = {
-       };
-       nvkm_event_send(&fifo->uevent, 1, 0, &rep, sizeof(rep));
-}
-
-int
-_nouveau_fifo_channel_ntfy(struct nouveau_object *object, u32 type,
-                          struct nvkm_event **event)
-{
-       struct nouveau_fifo *fifo = (void *)object->engine;
-       switch (type) {
-       case G82_CHANNEL_DMA_V0_NTFY_UEVENT:
-               if (nv_mclass(object) >= G82_CHANNEL_DMA) {
-                       *event = &fifo->uevent;
-                       return 0;
-               }
-               break;
-       default:
-               break;
-       }
-       return -EINVAL;
-}
-
-static int
-nouveau_fifo_chid(struct nouveau_fifo *priv, struct nouveau_object *object)
-{
-       int engidx = nv_hclass(priv) & 0xff;
-
-       while (object && object->parent) {
-               if ( nv_iclass(object->parent, NV_ENGCTX_CLASS) &&
-                   (nv_hclass(object->parent) & 0xff) == engidx)
-                       return nouveau_fifo_chan(object)->chid;
-               object = object->parent;
-       }
-
-       return -1;
-}
-
-const char *
-nouveau_client_name_for_fifo_chid(struct nouveau_fifo *fifo, u32 chid)
-{
-       struct nouveau_fifo_chan *chan = NULL;
-       unsigned long flags;
-
-       spin_lock_irqsave(&fifo->lock, flags);
-       if (chid >= fifo->min && chid <= fifo->max)
-               chan = (void *)fifo->channel[chid];
-       spin_unlock_irqrestore(&fifo->lock, flags);
-
-       return nouveau_client_name(chan);
-}
-
-void
-nouveau_fifo_destroy(struct nouveau_fifo *priv)
-{
-       kfree(priv->channel);
-       nvkm_event_fini(&priv->uevent);
-       nvkm_event_fini(&priv->cevent);
-       nouveau_engine_destroy(&priv->base);
-}
-
-int
-nouveau_fifo_create_(struct nouveau_object *parent,
-                    struct nouveau_object *engine,
-                    struct nouveau_oclass *oclass,
-                    int min, int max, int length, void **pobject)
-{
-       struct nouveau_fifo *priv;
-       int ret;
-
-       ret = nouveau_engine_create_(parent, engine, oclass, true, "PFIFO",
-                                    "fifo", length, pobject);
-       priv = *pobject;
-       if (ret)
-               return ret;
-
-       priv->min = min;
-       priv->max = max;
-       priv->channel = kzalloc(sizeof(*priv->channel) * (max + 1), GFP_KERNEL);
-       if (!priv->channel)
-               return -ENOMEM;
-
-       ret = nvkm_event_init(&nouveau_fifo_event_func, 1, 1, &priv->cevent);
-       if (ret)
-               return ret;
-
-       priv->chid = nouveau_fifo_chid;
-       spin_lock_init(&priv->lock);
-       return 0;
-}
diff --git a/drivers/gpu/drm/nouveau/core/engine/fifo/gk20a.c b/drivers/gpu/drm/nouveau/core/engine/fifo/gk20a.c
deleted file mode 100644 (file)
index 327456e..0000000
+++ /dev/null
@@ -1,35 +0,0 @@
-/*
- * Copyright (c) 2014, NVIDIA CORPORATION. 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 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 "nve0.h"
-
-struct nouveau_oclass *
-gk20a_fifo_oclass = &(struct nve0_fifo_impl) {
-       .base.handle = NV_ENGINE(FIFO, 0xea),
-       .base.ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nve0_fifo_ctor,
-               .dtor = nve0_fifo_dtor,
-               .init = nve0_fifo_init,
-               .fini = nve0_fifo_fini,
-       },
-       .channels = 128,
-}.base;
diff --git a/drivers/gpu/drm/nouveau/core/engine/fifo/nv04.c b/drivers/gpu/drm/nouveau/core/engine/fifo/nv04.c
deleted file mode 100644 (file)
index 1931057..0000000
+++ /dev/null
@@ -1,656 +0,0 @@
-/*
- * Copyright 2012 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 <core/client.h>
-#include <nvif/unpack.h>
-#include <nvif/class.h>
-#include <core/engctx.h>
-#include <core/namedb.h>
-#include <core/handle.h>
-#include <core/ramht.h>
-#include <core/event.h>
-
-#include <subdev/instmem.h>
-#include <subdev/instmem/nv04.h>
-#include <subdev/timer.h>
-#include <subdev/fb.h>
-
-#include <engine/fifo.h>
-
-#include "nv04.h"
-
-static struct ramfc_desc
-nv04_ramfc[] = {
-       { 32,  0, 0x00,  0, NV04_PFIFO_CACHE1_DMA_PUT },
-       { 32,  0, 0x04,  0, NV04_PFIFO_CACHE1_DMA_GET },
-       { 16,  0, 0x08,  0, NV04_PFIFO_CACHE1_DMA_INSTANCE },
-       { 16, 16, 0x08,  0, NV04_PFIFO_CACHE1_DMA_DCOUNT },
-       { 32,  0, 0x0c,  0, NV04_PFIFO_CACHE1_DMA_STATE },
-       { 32,  0, 0x10,  0, NV04_PFIFO_CACHE1_DMA_FETCH },
-       { 32,  0, 0x14,  0, NV04_PFIFO_CACHE1_ENGINE },
-       { 32,  0, 0x18,  0, NV04_PFIFO_CACHE1_PULL1 },
-       {}
-};
-
-/*******************************************************************************
- * FIFO channel objects
- ******************************************************************************/
-
-int
-nv04_fifo_object_attach(struct nouveau_object *parent,
-                       struct nouveau_object *object, u32 handle)
-{
-       struct nv04_fifo_priv *priv = (void *)parent->engine;
-       struct nv04_fifo_chan *chan = (void *)parent;
-       u32 context, chid = chan->base.chid;
-       int ret;
-
-       if (nv_iclass(object, NV_GPUOBJ_CLASS))
-               context = nv_gpuobj(object)->addr >> 4;
-       else
-               context = 0x00000004; /* just non-zero */
-
-       switch (nv_engidx(object->engine)) {
-       case NVDEV_ENGINE_DMAOBJ:
-       case NVDEV_ENGINE_SW:
-               context |= 0x00000000;
-               break;
-       case NVDEV_ENGINE_GR:
-               context |= 0x00010000;
-               break;
-       case NVDEV_ENGINE_MPEG:
-               context |= 0x00020000;
-               break;
-       default:
-               return -EINVAL;
-       }
-
-       context |= 0x80000000; /* valid */
-       context |= chid << 24;
-
-       mutex_lock(&nv_subdev(priv)->mutex);
-       ret = nouveau_ramht_insert(priv->ramht, chid, handle, context);
-       mutex_unlock(&nv_subdev(priv)->mutex);
-       return ret;
-}
-
-void
-nv04_fifo_object_detach(struct nouveau_object *parent, int cookie)
-{
-       struct nv04_fifo_priv *priv = (void *)parent->engine;
-       mutex_lock(&nv_subdev(priv)->mutex);
-       nouveau_ramht_remove(priv->ramht, cookie);
-       mutex_unlock(&nv_subdev(priv)->mutex);
-}
-
-int
-nv04_fifo_context_attach(struct nouveau_object *parent,
-                        struct nouveau_object *object)
-{
-       nv_engctx(object)->addr = nouveau_fifo_chan(parent)->chid;
-       return 0;
-}
-
-static int
-nv04_fifo_chan_ctor(struct nouveau_object *parent,
-                   struct nouveau_object *engine,
-                   struct nouveau_oclass *oclass, void *data, u32 size,
-                   struct nouveau_object **pobject)
-{
-       union {
-               struct nv03_channel_dma_v0 v0;
-       } *args = data;
-       struct nv04_fifo_priv *priv = (void *)engine;
-       struct nv04_fifo_chan *chan;
-       int ret;
-
-       nv_ioctl(parent, "create channel dma size %d\n", size);
-       if (nvif_unpack(args->v0, 0, 0, false)) {
-               nv_ioctl(parent, "create channel dma vers %d pushbuf %08x "
-                                "offset %016llx\n", args->v0.version,
-                        args->v0.pushbuf, args->v0.offset);
-       } else
-               return ret;
-
-       ret = nouveau_fifo_channel_create(parent, engine, oclass, 0, 0x800000,
-                                         0x10000, args->v0.pushbuf,
-                                         (1ULL << NVDEV_ENGINE_DMAOBJ) |
-                                         (1ULL << NVDEV_ENGINE_SW) |
-                                         (1ULL << NVDEV_ENGINE_GR), &chan);
-       *pobject = nv_object(chan);
-       if (ret)
-               return ret;
-
-       args->v0.chid = chan->base.chid;
-
-       nv_parent(chan)->object_attach = nv04_fifo_object_attach;
-       nv_parent(chan)->object_detach = nv04_fifo_object_detach;
-       nv_parent(chan)->context_attach = nv04_fifo_context_attach;
-       chan->ramfc = chan->base.chid * 32;
-
-       nv_wo32(priv->ramfc, chan->ramfc + 0x00, args->v0.offset);
-       nv_wo32(priv->ramfc, chan->ramfc + 0x04, args->v0.offset);
-       nv_wo32(priv->ramfc, chan->ramfc + 0x08, chan->base.pushgpu->addr >> 4);
-       nv_wo32(priv->ramfc, chan->ramfc + 0x10,
-                            NV_PFIFO_CACHE1_DMA_FETCH_TRIG_128_BYTES |
-                            NV_PFIFO_CACHE1_DMA_FETCH_SIZE_128_BYTES |
-#ifdef __BIG_ENDIAN
-                            NV_PFIFO_CACHE1_BIG_ENDIAN |
-#endif
-                            NV_PFIFO_CACHE1_DMA_FETCH_MAX_REQS_8);
-       return 0;
-}
-
-void
-nv04_fifo_chan_dtor(struct nouveau_object *object)
-{
-       struct nv04_fifo_priv *priv = (void *)object->engine;
-       struct nv04_fifo_chan *chan = (void *)object;
-       struct ramfc_desc *c = priv->ramfc_desc;
-
-       do {
-               nv_wo32(priv->ramfc, chan->ramfc + c->ctxp, 0x00000000);
-       } while ((++c)->bits);
-
-       nouveau_fifo_channel_destroy(&chan->base);
-}
-
-int
-nv04_fifo_chan_init(struct nouveau_object *object)
-{
-       struct nv04_fifo_priv *priv = (void *)object->engine;
-       struct nv04_fifo_chan *chan = (void *)object;
-       u32 mask = 1 << chan->base.chid;
-       unsigned long flags;
-       int ret;
-
-       ret = nouveau_fifo_channel_init(&chan->base);
-       if (ret)
-               return ret;
-
-       spin_lock_irqsave(&priv->base.lock, flags);
-       nv_mask(priv, NV04_PFIFO_MODE, mask, mask);
-       spin_unlock_irqrestore(&priv->base.lock, flags);
-       return 0;
-}
-
-int
-nv04_fifo_chan_fini(struct nouveau_object *object, bool suspend)
-{
-       struct nv04_fifo_priv *priv = (void *)object->engine;
-       struct nv04_fifo_chan *chan = (void *)object;
-       struct nouveau_gpuobj *fctx = priv->ramfc;
-       struct ramfc_desc *c;
-       unsigned long flags;
-       u32 data = chan->ramfc;
-       u32 chid;
-
-       /* prevent fifo context switches */
-       spin_lock_irqsave(&priv->base.lock, flags);
-       nv_wr32(priv, NV03_PFIFO_CACHES, 0);
-
-       /* if this channel is active, replace it with a null context */
-       chid = nv_rd32(priv, NV03_PFIFO_CACHE1_PUSH1) & priv->base.max;
-       if (chid == chan->base.chid) {
-               nv_mask(priv, NV04_PFIFO_CACHE1_DMA_PUSH, 0x00000001, 0);
-               nv_wr32(priv, NV03_PFIFO_CACHE1_PUSH0, 0);
-               nv_mask(priv, NV04_PFIFO_CACHE1_PULL0, 0x00000001, 0);
-
-               c = priv->ramfc_desc;
-               do {
-                       u32 rm = ((1ULL << c->bits) - 1) << c->regs;
-                       u32 cm = ((1ULL << c->bits) - 1) << c->ctxs;
-                       u32 rv = (nv_rd32(priv, c->regp) &  rm) >> c->regs;
-                       u32 cv = (nv_ro32(fctx, c->ctxp + data) & ~cm);
-                       nv_wo32(fctx, c->ctxp + data, cv | (rv << c->ctxs));
-               } while ((++c)->bits);
-
-               c = priv->ramfc_desc;
-               do {
-                       nv_wr32(priv, c->regp, 0x00000000);
-               } while ((++c)->bits);
-
-               nv_wr32(priv, NV03_PFIFO_CACHE1_GET, 0);
-               nv_wr32(priv, NV03_PFIFO_CACHE1_PUT, 0);
-               nv_wr32(priv, NV03_PFIFO_CACHE1_PUSH1, priv->base.max);
-               nv_wr32(priv, NV03_PFIFO_CACHE1_PUSH0, 1);
-               nv_wr32(priv, NV04_PFIFO_CACHE1_PULL0, 1);
-       }
-
-       /* restore normal operation, after disabling dma mode */
-       nv_mask(priv, NV04_PFIFO_MODE, 1 << chan->base.chid, 0);
-       nv_wr32(priv, NV03_PFIFO_CACHES, 1);
-       spin_unlock_irqrestore(&priv->base.lock, flags);
-
-       return nouveau_fifo_channel_fini(&chan->base, suspend);
-}
-
-static struct nouveau_ofuncs
-nv04_fifo_ofuncs = {
-       .ctor = nv04_fifo_chan_ctor,
-       .dtor = nv04_fifo_chan_dtor,
-       .init = nv04_fifo_chan_init,
-       .fini = nv04_fifo_chan_fini,
-       .map  = _nouveau_fifo_channel_map,
-       .rd32 = _nouveau_fifo_channel_rd32,
-       .wr32 = _nouveau_fifo_channel_wr32,
-       .ntfy = _nouveau_fifo_channel_ntfy
-};
-
-static struct nouveau_oclass
-nv04_fifo_sclass[] = {
-       { NV03_CHANNEL_DMA, &nv04_fifo_ofuncs },
-       {}
-};
-
-/*******************************************************************************
- * FIFO context - basically just the instmem reserved for the channel
- ******************************************************************************/
-
-int
-nv04_fifo_context_ctor(struct nouveau_object *parent,
-                      struct nouveau_object *engine,
-                      struct nouveau_oclass *oclass, void *data, u32 size,
-                      struct nouveau_object **pobject)
-{
-       struct nv04_fifo_base *base;
-       int ret;
-
-       ret = nouveau_fifo_context_create(parent, engine, oclass, NULL, 0x1000,
-                                         0x1000, NVOBJ_FLAG_HEAP, &base);
-       *pobject = nv_object(base);
-       if (ret)
-               return ret;
-
-       return 0;
-}
-
-static struct nouveau_oclass
-nv04_fifo_cclass = {
-       .handle = NV_ENGCTX(FIFO, 0x04),
-       .ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nv04_fifo_context_ctor,
-               .dtor = _nouveau_fifo_context_dtor,
-               .init = _nouveau_fifo_context_init,
-               .fini = _nouveau_fifo_context_fini,
-               .rd32 = _nouveau_fifo_context_rd32,
-               .wr32 = _nouveau_fifo_context_wr32,
-       },
-};
-
-/*******************************************************************************
- * PFIFO engine
- ******************************************************************************/
-
-void
-nv04_fifo_pause(struct nouveau_fifo *pfifo, unsigned long *pflags)
-__acquires(priv->base.lock)
-{
-       struct nv04_fifo_priv *priv = (void *)pfifo;
-       unsigned long flags;
-
-       spin_lock_irqsave(&priv->base.lock, flags);
-       *pflags = flags;
-
-       nv_wr32(priv, NV03_PFIFO_CACHES, 0x00000000);
-       nv_mask(priv, NV04_PFIFO_CACHE1_PULL0, 0x00000001, 0x00000000);
-
-       /* in some cases the puller may be left in an inconsistent state
-        * if you try to stop it while it's busy translating handles.
-        * sometimes you get a CACHE_ERROR, sometimes it just fails
-        * silently; sending incorrect instance offsets to PGRAPH after
-        * it's started up again.
-        *
-        * to avoid this, we invalidate the most recently calculated
-        * instance.
-        */
-       if (!nv_wait(priv, NV04_PFIFO_CACHE1_PULL0,
-                          NV04_PFIFO_CACHE1_PULL0_HASH_BUSY, 0x00000000))
-               nv_warn(priv, "timeout idling puller\n");
-
-       if (nv_rd32(priv, NV04_PFIFO_CACHE1_PULL0) &
-                         NV04_PFIFO_CACHE1_PULL0_HASH_FAILED)
-               nv_wr32(priv, NV03_PFIFO_INTR_0, NV_PFIFO_INTR_CACHE_ERROR);
-
-       nv_wr32(priv, NV04_PFIFO_CACHE1_HASH, 0x00000000);
-}
-
-void
-nv04_fifo_start(struct nouveau_fifo *pfifo, unsigned long *pflags)
-__releases(priv->base.lock)
-{
-       struct nv04_fifo_priv *priv = (void *)pfifo;
-       unsigned long flags = *pflags;
-
-       nv_mask(priv, NV04_PFIFO_CACHE1_PULL0, 0x00000001, 0x00000001);
-       nv_wr32(priv, NV03_PFIFO_CACHES, 0x00000001);
-
-       spin_unlock_irqrestore(&priv->base.lock, flags);
-}
-
-static const char *
-nv_dma_state_err(u32 state)
-{
-       static const char * const desc[] = {
-               "NONE", "CALL_SUBR_ACTIVE", "INVALID_MTHD", "RET_SUBR_INACTIVE",
-               "INVALID_CMD", "IB_EMPTY"/* NV50+ */, "MEM_FAULT", "UNK"
-       };
-       return desc[(state >> 29) & 0x7];
-}
-
-static bool
-nv04_fifo_swmthd(struct nv04_fifo_priv *priv, u32 chid, u32 addr, u32 data)
-{
-       struct nv04_fifo_chan *chan = NULL;
-       struct nouveau_handle *bind;
-       const int subc = (addr >> 13) & 0x7;
-       const int mthd = addr & 0x1ffc;
-       bool handled = false;
-       unsigned long flags;
-       u32 engine;
-
-       spin_lock_irqsave(&priv->base.lock, flags);
-       if (likely(chid >= priv->base.min && chid <= priv->base.max))
-               chan = (void *)priv->base.channel[chid];
-       if (unlikely(!chan))
-               goto out;
-
-       switch (mthd) {
-       case 0x0000:
-               bind = nouveau_namedb_get(nv_namedb(chan), data);
-               if (unlikely(!bind))
-                       break;
-
-               if (nv_engidx(bind->object->engine) == NVDEV_ENGINE_SW) {
-                       engine = 0x0000000f << (subc * 4);
-                       chan->subc[subc] = data;
-                       handled = true;
-
-                       nv_mask(priv, NV04_PFIFO_CACHE1_ENGINE, engine, 0);
-               }
-
-               nouveau_namedb_put(bind);
-               break;
-       default:
-               engine = nv_rd32(priv, NV04_PFIFO_CACHE1_ENGINE);
-               if (unlikely(((engine >> (subc * 4)) & 0xf) != 0))
-                       break;
-
-               bind = nouveau_namedb_get(nv_namedb(chan), chan->subc[subc]);
-               if (likely(bind)) {
-                       if (!nv_call(bind->object, mthd, data))
-                               handled = true;
-                       nouveau_namedb_put(bind);
-               }
-               break;
-       }
-
-out:
-       spin_unlock_irqrestore(&priv->base.lock, flags);
-       return handled;
-}
-
-static void
-nv04_fifo_cache_error(struct nouveau_device *device,
-               struct nv04_fifo_priv *priv, u32 chid, u32 get)
-{
-       u32 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 (device->card_type < NV_40) {
-               mthd = nv_rd32(priv, NV04_PFIFO_CACHE1_METHOD(ptr));
-               data = nv_rd32(priv, NV04_PFIFO_CACHE1_DATA(ptr));
-       } else {
-               mthd = nv_rd32(priv, NV40_PFIFO_CACHE1_METHOD(ptr));
-               data = nv_rd32(priv, NV40_PFIFO_CACHE1_DATA(ptr));
-       }
-
-       if (!nv04_fifo_swmthd(priv, chid, mthd, data)) {
-               const char *client_name =
-                       nouveau_client_name_for_fifo_chid(&priv->base, chid);
-               nv_error(priv,
-                        "CACHE_ERROR - ch %d [%s] subc %d mthd 0x%04x data 0x%08x\n",
-                        chid, client_name, (mthd >> 13) & 7, mthd & 0x1ffc,
-                        data);
-       }
-
-       nv_wr32(priv, NV04_PFIFO_CACHE1_DMA_PUSH, 0);
-       nv_wr32(priv, NV03_PFIFO_INTR_0, NV_PFIFO_INTR_CACHE_ERROR);
-
-       nv_wr32(priv, NV03_PFIFO_CACHE1_PUSH0,
-               nv_rd32(priv, NV03_PFIFO_CACHE1_PUSH0) & ~1);
-       nv_wr32(priv, NV03_PFIFO_CACHE1_GET, get + 4);
-       nv_wr32(priv, NV03_PFIFO_CACHE1_PUSH0,
-               nv_rd32(priv, NV03_PFIFO_CACHE1_PUSH0) | 1);
-       nv_wr32(priv, NV04_PFIFO_CACHE1_HASH, 0);
-
-       nv_wr32(priv, NV04_PFIFO_CACHE1_DMA_PUSH,
-               nv_rd32(priv, NV04_PFIFO_CACHE1_DMA_PUSH) | 1);
-       nv_wr32(priv, NV04_PFIFO_CACHE1_PULL0, 1);
-}
-
-static void
-nv04_fifo_dma_pusher(struct nouveau_device *device, struct nv04_fifo_priv *priv,
-               u32 chid)
-{
-       const char *client_name;
-       u32 dma_get = nv_rd32(priv, 0x003244);
-       u32 dma_put = nv_rd32(priv, 0x003240);
-       u32 push = nv_rd32(priv, 0x003220);
-       u32 state = nv_rd32(priv, 0x003228);
-
-       client_name = nouveau_client_name_for_fifo_chid(&priv->base, chid);
-
-       if (device->card_type == NV_50) {
-               u32 ho_get = nv_rd32(priv, 0x003328);
-               u32 ho_put = nv_rd32(priv, 0x003320);
-               u32 ib_get = nv_rd32(priv, 0x003334);
-               u32 ib_put = nv_rd32(priv, 0x003330);
-
-               nv_error(priv,
-                        "DMA_PUSHER - ch %d [%s] get 0x%02x%08x put 0x%02x%08x ib_get 0x%08x ib_put 0x%08x state 0x%08x (err: %s) push 0x%08x\n",
-                        chid, client_name, ho_get, dma_get, ho_put, dma_put,
-                        ib_get, ib_put, state, nv_dma_state_err(state), push);
-
-               /* METHOD_COUNT, in DMA_STATE on earlier chipsets */
-               nv_wr32(priv, 0x003364, 0x00000000);
-               if (dma_get != dma_put || ho_get != ho_put) {
-                       nv_wr32(priv, 0x003244, dma_put);
-                       nv_wr32(priv, 0x003328, ho_put);
-               } else
-               if (ib_get != ib_put)
-                       nv_wr32(priv, 0x003334, ib_put);
-       } else {
-               nv_error(priv,
-                        "DMA_PUSHER - ch %d [%s] get 0x%08x put 0x%08x state 0x%08x (err: %s) push 0x%08x\n",
-                        chid, client_name, dma_get, dma_put, state,
-                        nv_dma_state_err(state), push);
-
-               if (dma_get != dma_put)
-                       nv_wr32(priv, 0x003244, dma_put);
-       }
-
-       nv_wr32(priv, 0x003228, 0x00000000);
-       nv_wr32(priv, 0x003220, 0x00000001);
-       nv_wr32(priv, 0x002100, NV_PFIFO_INTR_DMA_PUSHER);
-}
-
-void
-nv04_fifo_intr(struct nouveau_subdev *subdev)
-{
-       struct nouveau_device *device = nv_device(subdev);
-       struct nv04_fifo_priv *priv = (void *)subdev;
-       uint32_t status, reassign;
-       int cnt = 0;
-
-       reassign = nv_rd32(priv, NV03_PFIFO_CACHES) & 1;
-       while ((status = nv_rd32(priv, NV03_PFIFO_INTR_0)) && (cnt++ < 100)) {
-               uint32_t chid, get;
-
-               nv_wr32(priv, NV03_PFIFO_CACHES, 0);
-
-               chid = nv_rd32(priv, NV03_PFIFO_CACHE1_PUSH1) & priv->base.max;
-               get  = nv_rd32(priv, NV03_PFIFO_CACHE1_GET);
-
-               if (status & NV_PFIFO_INTR_CACHE_ERROR) {
-                       nv04_fifo_cache_error(device, priv, chid, get);
-                       status &= ~NV_PFIFO_INTR_CACHE_ERROR;
-               }
-
-               if (status & NV_PFIFO_INTR_DMA_PUSHER) {
-                       nv04_fifo_dma_pusher(device, priv, chid);
-                       status &= ~NV_PFIFO_INTR_DMA_PUSHER;
-               }
-
-               if (status & NV_PFIFO_INTR_SEMAPHORE) {
-                       uint32_t sem;
-
-                       status &= ~NV_PFIFO_INTR_SEMAPHORE;
-                       nv_wr32(priv, NV03_PFIFO_INTR_0,
-                               NV_PFIFO_INTR_SEMAPHORE);
-
-                       sem = nv_rd32(priv, NV10_PFIFO_CACHE1_SEMAPHORE);
-                       nv_wr32(priv, NV10_PFIFO_CACHE1_SEMAPHORE, sem | 0x1);
-
-                       nv_wr32(priv, NV03_PFIFO_CACHE1_GET, get + 4);
-                       nv_wr32(priv, NV04_PFIFO_CACHE1_PULL0, 1);
-               }
-
-               if (device->card_type == NV_50) {
-                       if (status & 0x00000010) {
-                               status &= ~0x00000010;
-                               nv_wr32(priv, 0x002100, 0x00000010);
-                       }
-
-                       if (status & 0x40000000) {
-                               nv_wr32(priv, 0x002100, 0x40000000);
-                               nouveau_fifo_uevent(&priv->base);
-                               status &= ~0x40000000;
-                       }
-               }
-
-               if (status) {
-                       nv_warn(priv, "unknown intr 0x%08x, ch %d\n",
-                               status, chid);
-                       nv_wr32(priv, NV03_PFIFO_INTR_0, status);
-                       status = 0;
-               }
-
-               nv_wr32(priv, NV03_PFIFO_CACHES, reassign);
-       }
-
-       if (status) {
-               nv_error(priv, "still angry after %d spins, halt\n", cnt);
-               nv_wr32(priv, 0x002140, 0);
-               nv_wr32(priv, 0x000140, 0);
-       }
-
-       nv_wr32(priv, 0x000100, 0x00000100);
-}
-
-static int
-nv04_fifo_ctor(struct nouveau_object *parent, struct nouveau_object *engine,
-              struct nouveau_oclass *oclass, void *data, u32 size,
-              struct nouveau_object **pobject)
-{
-       struct nv04_instmem_priv *imem = nv04_instmem(parent);
-       struct nv04_fifo_priv *priv;
-       int ret;
-
-       ret = nouveau_fifo_create(parent, engine, oclass, 0, 15, &priv);
-       *pobject = nv_object(priv);
-       if (ret)
-               return ret;
-
-       nouveau_ramht_ref(imem->ramht, &priv->ramht);
-       nouveau_gpuobj_ref(imem->ramro, &priv->ramro);
-       nouveau_gpuobj_ref(imem->ramfc, &priv->ramfc);
-
-       nv_subdev(priv)->unit = 0x00000100;
-       nv_subdev(priv)->intr = nv04_fifo_intr;
-       nv_engine(priv)->cclass = &nv04_fifo_cclass;
-       nv_engine(priv)->sclass = nv04_fifo_sclass;
-       priv->base.pause = nv04_fifo_pause;
-       priv->base.start = nv04_fifo_start;
-       priv->ramfc_desc = nv04_ramfc;
-       return 0;
-}
-
-void
-nv04_fifo_dtor(struct nouveau_object *object)
-{
-       struct nv04_fifo_priv *priv = (void *)object;
-       nouveau_gpuobj_ref(NULL, &priv->ramfc);
-       nouveau_gpuobj_ref(NULL, &priv->ramro);
-       nouveau_ramht_ref(NULL, &priv->ramht);
-       nouveau_fifo_destroy(&priv->base);
-}
-
-int
-nv04_fifo_init(struct nouveau_object *object)
-{
-       struct nv04_fifo_priv *priv = (void *)object;
-       int ret;
-
-       ret = nouveau_fifo_init(&priv->base);
-       if (ret)
-               return ret;
-
-       nv_wr32(priv, NV04_PFIFO_DELAY_0, 0x000000ff);
-       nv_wr32(priv, NV04_PFIFO_DMA_TIMESLICE, 0x0101ffff);
-
-       nv_wr32(priv, NV03_PFIFO_RAMHT, (0x03 << 24) /* search 128 */ |
-                                      ((priv->ramht->bits - 9) << 16) |
-                                       (priv->ramht->base.addr >> 8));
-       nv_wr32(priv, NV03_PFIFO_RAMRO, priv->ramro->addr >> 8);
-       nv_wr32(priv, NV03_PFIFO_RAMFC, priv->ramfc->addr >> 8);
-
-       nv_wr32(priv, NV03_PFIFO_CACHE1_PUSH1, priv->base.max);
-
-       nv_wr32(priv, NV03_PFIFO_INTR_0, 0xffffffff);
-       nv_wr32(priv, NV03_PFIFO_INTR_EN_0, 0xffffffff);
-
-       nv_wr32(priv, NV03_PFIFO_CACHE1_PUSH0, 1);
-       nv_wr32(priv, NV04_PFIFO_CACHE1_PULL0, 1);
-       nv_wr32(priv, NV03_PFIFO_CACHES, 1);
-       return 0;
-}
-
-struct nouveau_oclass *
-nv04_fifo_oclass = &(struct nouveau_oclass) {
-       .handle = NV_ENGINE(FIFO, 0x04),
-       .ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nv04_fifo_ctor,
-               .dtor = nv04_fifo_dtor,
-               .init = nv04_fifo_init,
-               .fini = _nouveau_fifo_fini,
-       },
-};
diff --git a/drivers/gpu/drm/nouveau/core/engine/fifo/nv04.h b/drivers/gpu/drm/nouveau/core/engine/fifo/nv04.h
deleted file mode 100644 (file)
index 496a4b4..0000000
+++ /dev/null
@@ -1,178 +0,0 @@
-#ifndef __NV04_FIFO_H__
-#define __NV04_FIFO_H__
-
-#include <engine/fifo.h>
-
-#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))
-
-struct ramfc_desc {
-       unsigned bits:6;
-       unsigned ctxs:5;
-       unsigned ctxp:8;
-       unsigned regs:5;
-       unsigned regp;
-};
-
-struct nv04_fifo_priv {
-       struct nouveau_fifo base;
-       struct ramfc_desc *ramfc_desc;
-       struct nouveau_ramht  *ramht;
-       struct nouveau_gpuobj *ramro;
-       struct nouveau_gpuobj *ramfc;
-};
-
-struct nv04_fifo_base {
-       struct nouveau_fifo_base base;
-};
-
-struct nv04_fifo_chan {
-       struct nouveau_fifo_chan base;
-       u32 subc[8];
-       u32 ramfc;
-};
-
-int  nv04_fifo_object_attach(struct nouveau_object *,
-                            struct nouveau_object *, u32);
-void nv04_fifo_object_detach(struct nouveau_object *, int);
-
-void nv04_fifo_chan_dtor(struct nouveau_object *);
-int  nv04_fifo_chan_init(struct nouveau_object *);
-int  nv04_fifo_chan_fini(struct nouveau_object *, bool suspend);
-
-int  nv04_fifo_context_ctor(struct nouveau_object *, struct nouveau_object *,
-                           struct nouveau_oclass *, void *, u32,
-                           struct nouveau_object **);
-
-void nv04_fifo_dtor(struct nouveau_object *);
-int  nv04_fifo_init(struct nouveau_object *);
-void nv04_fifo_pause(struct nouveau_fifo *, unsigned long *);
-void nv04_fifo_start(struct nouveau_fifo *, unsigned long *);
-
-#endif
diff --git a/drivers/gpu/drm/nouveau/core/engine/fifo/nv10.c b/drivers/gpu/drm/nouveau/core/engine/fifo/nv10.c
deleted file mode 100644 (file)
index 2a32add..0000000
+++ /dev/null
@@ -1,183 +0,0 @@
-/*
- * Copyright 2012 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 <core/client.h>
-#include <nvif/unpack.h>
-#include <nvif/class.h>
-#include <core/engctx.h>
-#include <core/ramht.h>
-
-#include <subdev/instmem.h>
-#include <subdev/instmem/nv04.h>
-#include <subdev/fb.h>
-
-#include <engine/fifo.h>
-
-#include "nv04.h"
-
-static struct ramfc_desc
-nv10_ramfc[] = {
-       { 32,  0, 0x00,  0, NV04_PFIFO_CACHE1_DMA_PUT },
-       { 32,  0, 0x04,  0, NV04_PFIFO_CACHE1_DMA_GET },
-       { 32,  0, 0x08,  0, NV10_PFIFO_CACHE1_REF_CNT },
-       { 16,  0, 0x0c,  0, NV04_PFIFO_CACHE1_DMA_INSTANCE },
-       { 16, 16, 0x0c,  0, NV04_PFIFO_CACHE1_DMA_DCOUNT },
-       { 32,  0, 0x10,  0, NV04_PFIFO_CACHE1_DMA_STATE },
-       { 32,  0, 0x14,  0, NV04_PFIFO_CACHE1_DMA_FETCH },
-       { 32,  0, 0x18,  0, NV04_PFIFO_CACHE1_ENGINE },
-       { 32,  0, 0x1c,  0, NV04_PFIFO_CACHE1_PULL1 },
-       {}
-};
-
-/*******************************************************************************
- * FIFO channel objects
- ******************************************************************************/
-
-static int
-nv10_fifo_chan_ctor(struct nouveau_object *parent,
-                   struct nouveau_object *engine,
-                   struct nouveau_oclass *oclass, void *data, u32 size,
-                   struct nouveau_object **pobject)
-{
-       union {
-               struct nv03_channel_dma_v0 v0;
-       } *args = data;
-       struct nv04_fifo_priv *priv = (void *)engine;
-       struct nv04_fifo_chan *chan;
-       int ret;
-
-       nv_ioctl(parent, "create channel dma size %d\n", size);
-       if (nvif_unpack(args->v0, 0, 0, false)) {
-               nv_ioctl(parent, "create channel dma vers %d pushbuf %08x "
-                                "offset %016llx\n", args->v0.version,
-                        args->v0.pushbuf, args->v0.offset);
-       } else
-               return ret;
-
-       ret = nouveau_fifo_channel_create(parent, engine, oclass, 0, 0x800000,
-                                         0x10000, args->v0.pushbuf,
-                                         (1ULL << NVDEV_ENGINE_DMAOBJ) |
-                                         (1ULL << NVDEV_ENGINE_SW) |
-                                         (1ULL << NVDEV_ENGINE_GR), &chan);
-       *pobject = nv_object(chan);
-       if (ret)
-               return ret;
-
-       args->v0.chid = chan->base.chid;
-
-       nv_parent(chan)->object_attach = nv04_fifo_object_attach;
-       nv_parent(chan)->object_detach = nv04_fifo_object_detach;
-       nv_parent(chan)->context_attach = nv04_fifo_context_attach;
-       chan->ramfc = chan->base.chid * 32;
-
-       nv_wo32(priv->ramfc, chan->ramfc + 0x00, args->v0.offset);
-       nv_wo32(priv->ramfc, chan->ramfc + 0x04, args->v0.offset);
-       nv_wo32(priv->ramfc, chan->ramfc + 0x0c, chan->base.pushgpu->addr >> 4);
-       nv_wo32(priv->ramfc, chan->ramfc + 0x14,
-                            NV_PFIFO_CACHE1_DMA_FETCH_TRIG_128_BYTES |
-                            NV_PFIFO_CACHE1_DMA_FETCH_SIZE_128_BYTES |
-#ifdef __BIG_ENDIAN
-                            NV_PFIFO_CACHE1_BIG_ENDIAN |
-#endif
-                            NV_PFIFO_CACHE1_DMA_FETCH_MAX_REQS_8);
-       return 0;
-}
-
-static struct nouveau_ofuncs
-nv10_fifo_ofuncs = {
-       .ctor = nv10_fifo_chan_ctor,
-       .dtor = nv04_fifo_chan_dtor,
-       .init = nv04_fifo_chan_init,
-       .fini = nv04_fifo_chan_fini,
-       .map  = _nouveau_fifo_channel_map,
-       .rd32 = _nouveau_fifo_channel_rd32,
-       .wr32 = _nouveau_fifo_channel_wr32,
-       .ntfy = _nouveau_fifo_channel_ntfy
-};
-
-static struct nouveau_oclass
-nv10_fifo_sclass[] = {
-       { NV10_CHANNEL_DMA, &nv10_fifo_ofuncs },
-       {}
-};
-
-/*******************************************************************************
- * FIFO context - basically just the instmem reserved for the channel
- ******************************************************************************/
-
-static struct nouveau_oclass
-nv10_fifo_cclass = {
-       .handle = NV_ENGCTX(FIFO, 0x10),
-       .ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nv04_fifo_context_ctor,
-               .dtor = _nouveau_fifo_context_dtor,
-               .init = _nouveau_fifo_context_init,
-               .fini = _nouveau_fifo_context_fini,
-               .rd32 = _nouveau_fifo_context_rd32,
-               .wr32 = _nouveau_fifo_context_wr32,
-       },
-};
-
-/*******************************************************************************
- * PFIFO engine
- ******************************************************************************/
-
-static int
-nv10_fifo_ctor(struct nouveau_object *parent, struct nouveau_object *engine,
-              struct nouveau_oclass *oclass, void *data, u32 size,
-              struct nouveau_object **pobject)
-{
-       struct nv04_instmem_priv *imem = nv04_instmem(parent);
-       struct nv04_fifo_priv *priv;
-       int ret;
-
-       ret = nouveau_fifo_create(parent, engine, oclass, 0, 31, &priv);
-       *pobject = nv_object(priv);
-       if (ret)
-               return ret;
-
-       nouveau_ramht_ref(imem->ramht, &priv->ramht);
-       nouveau_gpuobj_ref(imem->ramro, &priv->ramro);
-       nouveau_gpuobj_ref(imem->ramfc, &priv->ramfc);
-
-       nv_subdev(priv)->unit = 0x00000100;
-       nv_subdev(priv)->intr = nv04_fifo_intr;
-       nv_engine(priv)->cclass = &nv10_fifo_cclass;
-       nv_engine(priv)->sclass = nv10_fifo_sclass;
-       priv->base.pause = nv04_fifo_pause;
-       priv->base.start = nv04_fifo_start;
-       priv->ramfc_desc = nv10_ramfc;
-       return 0;
-}
-
-struct nouveau_oclass *
-nv10_fifo_oclass = &(struct nouveau_oclass) {
-       .handle = NV_ENGINE(FIFO, 0x10),
-       .ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nv10_fifo_ctor,
-               .dtor = nv04_fifo_dtor,
-               .init = nv04_fifo_init,
-               .fini = _nouveau_fifo_fini,
-       },
-};
diff --git a/drivers/gpu/drm/nouveau/core/engine/fifo/nv108.c b/drivers/gpu/drm/nouveau/core/engine/fifo/nv108.c
deleted file mode 100644 (file)
index 09362a5..0000000
+++ /dev/null
@@ -1,37 +0,0 @@
-/*
- * Copyright 2013 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 "nve0.h"
-
-struct nouveau_oclass *
-nv108_fifo_oclass = &(struct nve0_fifo_impl) {
-       .base.handle = NV_ENGINE(FIFO, 0x08),
-       .base.ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nve0_fifo_ctor,
-               .dtor = nve0_fifo_dtor,
-               .init = nve0_fifo_init,
-               .fini = _nouveau_fifo_fini,
-       },
-       .channels = 1024,
-}.base;
diff --git a/drivers/gpu/drm/nouveau/core/engine/fifo/nv17.c b/drivers/gpu/drm/nouveau/core/engine/fifo/nv17.c
deleted file mode 100644 (file)
index 12d76c8..0000000
+++ /dev/null
@@ -1,220 +0,0 @@
-/*
- * Copyright 2012 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 <core/client.h>
-#include <nvif/unpack.h>
-#include <nvif/class.h>
-#include <core/engctx.h>
-#include <core/ramht.h>
-
-#include <subdev/instmem.h>
-#include <subdev/instmem/nv04.h>
-#include <subdev/fb.h>
-
-#include <engine/fifo.h>
-
-#include "nv04.h"
-
-static struct ramfc_desc
-nv17_ramfc[] = {
-       { 32,  0, 0x00,  0, NV04_PFIFO_CACHE1_DMA_PUT },
-       { 32,  0, 0x04,  0, NV04_PFIFO_CACHE1_DMA_GET },
-       { 32,  0, 0x08,  0, NV10_PFIFO_CACHE1_REF_CNT },
-       { 16,  0, 0x0c,  0, NV04_PFIFO_CACHE1_DMA_INSTANCE },
-       { 16, 16, 0x0c,  0, NV04_PFIFO_CACHE1_DMA_DCOUNT },
-       { 32,  0, 0x10,  0, NV04_PFIFO_CACHE1_DMA_STATE },
-       { 32,  0, 0x14,  0, NV04_PFIFO_CACHE1_DMA_FETCH },
-       { 32,  0, 0x18,  0, NV04_PFIFO_CACHE1_ENGINE },
-       { 32,  0, 0x1c,  0, NV04_PFIFO_CACHE1_PULL1 },
-       { 32,  0, 0x20,  0, NV10_PFIFO_CACHE1_ACQUIRE_VALUE },
-       { 32,  0, 0x24,  0, NV10_PFIFO_CACHE1_ACQUIRE_TIMESTAMP },
-       { 32,  0, 0x28,  0, NV10_PFIFO_CACHE1_ACQUIRE_TIMEOUT },
-       { 32,  0, 0x2c,  0, NV10_PFIFO_CACHE1_SEMAPHORE },
-       { 32,  0, 0x30,  0, NV10_PFIFO_CACHE1_DMA_SUBROUTINE },
-       {}
-};
-
-/*******************************************************************************
- * FIFO channel objects
- ******************************************************************************/
-
-static int
-nv17_fifo_chan_ctor(struct nouveau_object *parent,
-                   struct nouveau_object *engine,
-                   struct nouveau_oclass *oclass, void *data, u32 size,
-                   struct nouveau_object **pobject)
-{
-       union {
-               struct nv03_channel_dma_v0 v0;
-       } *args = data;
-       struct nv04_fifo_priv *priv = (void *)engine;
-       struct nv04_fifo_chan *chan;
-       int ret;
-
-       nv_ioctl(parent, "create channel dma size %d\n", size);
-       if (nvif_unpack(args->v0, 0, 0, false)) {
-               nv_ioctl(parent, "create channel dma vers %d pushbuf %08x "
-                                "offset %016llx\n", args->v0.version,
-                        args->v0.pushbuf, args->v0.offset);
-       } else
-               return ret;
-
-       ret = nouveau_fifo_channel_create(parent, engine, oclass, 0, 0x800000,
-                                         0x10000, args->v0.pushbuf,
-                                         (1ULL << NVDEV_ENGINE_DMAOBJ) |
-                                         (1ULL << NVDEV_ENGINE_SW) |
-                                         (1ULL << NVDEV_ENGINE_GR) |
-                                         (1ULL << NVDEV_ENGINE_MPEG), /* NV31- */
-                                         &chan);
-       *pobject = nv_object(chan);
-       if (ret)
-               return ret;
-
-       args->v0.chid = chan->base.chid;
-
-       nv_parent(chan)->object_attach = nv04_fifo_object_attach;
-       nv_parent(chan)->object_detach = nv04_fifo_object_detach;
-       nv_parent(chan)->context_attach = nv04_fifo_context_attach;
-       chan->ramfc = chan->base.chid * 64;
-
-       nv_wo32(priv->ramfc, chan->ramfc + 0x00, args->v0.offset);
-       nv_wo32(priv->ramfc, chan->ramfc + 0x04, args->v0.offset);
-       nv_wo32(priv->ramfc, chan->ramfc + 0x0c, chan->base.pushgpu->addr >> 4);
-       nv_wo32(priv->ramfc, chan->ramfc + 0x14,
-                            NV_PFIFO_CACHE1_DMA_FETCH_TRIG_128_BYTES |
-                            NV_PFIFO_CACHE1_DMA_FETCH_SIZE_128_BYTES |
-#ifdef __BIG_ENDIAN
-                            NV_PFIFO_CACHE1_BIG_ENDIAN |
-#endif
-                            NV_PFIFO_CACHE1_DMA_FETCH_MAX_REQS_8);
-       return 0;
-}
-
-static struct nouveau_ofuncs
-nv17_fifo_ofuncs = {
-       .ctor = nv17_fifo_chan_ctor,
-       .dtor = nv04_fifo_chan_dtor,
-       .init = nv04_fifo_chan_init,
-       .fini = nv04_fifo_chan_fini,
-       .map  = _nouveau_fifo_channel_map,
-       .rd32 = _nouveau_fifo_channel_rd32,
-       .wr32 = _nouveau_fifo_channel_wr32,
-       .ntfy = _nouveau_fifo_channel_ntfy
-};
-
-static struct nouveau_oclass
-nv17_fifo_sclass[] = {
-       { NV17_CHANNEL_DMA, &nv17_fifo_ofuncs },
-       {}
-};
-
-/*******************************************************************************
- * FIFO context - basically just the instmem reserved for the channel
- ******************************************************************************/
-
-static struct nouveau_oclass
-nv17_fifo_cclass = {
-       .handle = NV_ENGCTX(FIFO, 0x17),
-       .ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nv04_fifo_context_ctor,
-               .dtor = _nouveau_fifo_context_dtor,
-               .init = _nouveau_fifo_context_init,
-               .fini = _nouveau_fifo_context_fini,
-               .rd32 = _nouveau_fifo_context_rd32,
-               .wr32 = _nouveau_fifo_context_wr32,
-       },
-};
-
-/*******************************************************************************
- * PFIFO engine
- ******************************************************************************/
-
-static int
-nv17_fifo_ctor(struct nouveau_object *parent, struct nouveau_object *engine,
-              struct nouveau_oclass *oclass, void *data, u32 size,
-              struct nouveau_object **pobject)
-{
-       struct nv04_instmem_priv *imem = nv04_instmem(parent);
-       struct nv04_fifo_priv *priv;
-       int ret;
-
-       ret = nouveau_fifo_create(parent, engine, oclass, 0, 31, &priv);
-       *pobject = nv_object(priv);
-       if (ret)
-               return ret;
-
-       nouveau_ramht_ref(imem->ramht, &priv->ramht);
-       nouveau_gpuobj_ref(imem->ramro, &priv->ramro);
-       nouveau_gpuobj_ref(imem->ramfc, &priv->ramfc);
-
-       nv_subdev(priv)->unit = 0x00000100;
-       nv_subdev(priv)->intr = nv04_fifo_intr;
-       nv_engine(priv)->cclass = &nv17_fifo_cclass;
-       nv_engine(priv)->sclass = nv17_fifo_sclass;
-       priv->base.pause = nv04_fifo_pause;
-       priv->base.start = nv04_fifo_start;
-       priv->ramfc_desc = nv17_ramfc;
-       return 0;
-}
-
-static int
-nv17_fifo_init(struct nouveau_object *object)
-{
-       struct nv04_fifo_priv *priv = (void *)object;
-       int ret;
-
-       ret = nouveau_fifo_init(&priv->base);
-       if (ret)
-               return ret;
-
-       nv_wr32(priv, NV04_PFIFO_DELAY_0, 0x000000ff);
-       nv_wr32(priv, NV04_PFIFO_DMA_TIMESLICE, 0x0101ffff);
-
-       nv_wr32(priv, NV03_PFIFO_RAMHT, (0x03 << 24) /* search 128 */ |
-                                      ((priv->ramht->bits - 9) << 16) |
-                                       (priv->ramht->base.addr >> 8));
-       nv_wr32(priv, NV03_PFIFO_RAMRO, priv->ramro->addr >> 8);
-       nv_wr32(priv, NV03_PFIFO_RAMFC, priv->ramfc->addr >> 8 | 0x00010000);
-
-       nv_wr32(priv, NV03_PFIFO_CACHE1_PUSH1, priv->base.max);
-
-       nv_wr32(priv, NV03_PFIFO_INTR_0, 0xffffffff);
-       nv_wr32(priv, NV03_PFIFO_INTR_EN_0, 0xffffffff);
-
-       nv_wr32(priv, NV03_PFIFO_CACHE1_PUSH0, 1);
-       nv_wr32(priv, NV04_PFIFO_CACHE1_PULL0, 1);
-       nv_wr32(priv, NV03_PFIFO_CACHES, 1);
-       return 0;
-}
-
-struct nouveau_oclass *
-nv17_fifo_oclass = &(struct nouveau_oclass) {
-       .handle = NV_ENGINE(FIFO, 0x17),
-       .ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nv17_fifo_ctor,
-               .dtor = nv04_fifo_dtor,
-               .init = nv17_fifo_init,
-               .fini = _nouveau_fifo_fini,
-       },
-};
diff --git a/drivers/gpu/drm/nouveau/core/engine/fifo/nv40.c b/drivers/gpu/drm/nouveau/core/engine/fifo/nv40.c
deleted file mode 100644 (file)
index 9f49c3a..0000000
+++ /dev/null
@@ -1,361 +0,0 @@
-/*
- * Copyright 2012 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 <core/client.h>
-#include <nvif/unpack.h>
-#include <nvif/class.h>
-#include <core/engctx.h>
-#include <core/ramht.h>
-
-#include <subdev/instmem.h>
-#include <subdev/instmem/nv04.h>
-#include <subdev/fb.h>
-
-#include <engine/fifo.h>
-
-#include "nv04.h"
-
-static struct ramfc_desc
-nv40_ramfc[] = {
-       { 32,  0, 0x00,  0, NV04_PFIFO_CACHE1_DMA_PUT },
-       { 32,  0, 0x04,  0, NV04_PFIFO_CACHE1_DMA_GET },
-       { 32,  0, 0x08,  0, NV10_PFIFO_CACHE1_REF_CNT },
-       { 32,  0, 0x0c,  0, NV04_PFIFO_CACHE1_DMA_INSTANCE },
-       { 32,  0, 0x10,  0, NV04_PFIFO_CACHE1_DMA_DCOUNT },
-       { 32,  0, 0x14,  0, NV04_PFIFO_CACHE1_DMA_STATE },
-       { 28,  0, 0x18,  0, NV04_PFIFO_CACHE1_DMA_FETCH },
-       {  2, 28, 0x18, 28, 0x002058 },
-       { 32,  0, 0x1c,  0, NV04_PFIFO_CACHE1_ENGINE },
-       { 32,  0, 0x20,  0, NV04_PFIFO_CACHE1_PULL1 },
-       { 32,  0, 0x24,  0, NV10_PFIFO_CACHE1_ACQUIRE_VALUE },
-       { 32,  0, 0x28,  0, NV10_PFIFO_CACHE1_ACQUIRE_TIMESTAMP },
-       { 32,  0, 0x2c,  0, NV10_PFIFO_CACHE1_ACQUIRE_TIMEOUT },
-       { 32,  0, 0x30,  0, NV10_PFIFO_CACHE1_SEMAPHORE },
-       { 32,  0, 0x34,  0, NV10_PFIFO_CACHE1_DMA_SUBROUTINE },
-       { 32,  0, 0x38,  0, NV40_PFIFO_GRCTX_INSTANCE },
-       { 17,  0, 0x3c,  0, NV04_PFIFO_DMA_TIMESLICE },
-       { 32,  0, 0x40,  0, 0x0032e4 },
-       { 32,  0, 0x44,  0, 0x0032e8 },
-       { 32,  0, 0x4c,  0, 0x002088 },
-       { 32,  0, 0x50,  0, 0x003300 },
-       { 32,  0, 0x54,  0, 0x00330c },
-       {}
-};
-
-/*******************************************************************************
- * FIFO channel objects
- ******************************************************************************/
-
-static int
-nv40_fifo_object_attach(struct nouveau_object *parent,
-                       struct nouveau_object *object, u32 handle)
-{
-       struct nv04_fifo_priv *priv = (void *)parent->engine;
-       struct nv04_fifo_chan *chan = (void *)parent;
-       u32 context, chid = chan->base.chid;
-       int ret;
-
-       if (nv_iclass(object, NV_GPUOBJ_CLASS))
-               context = nv_gpuobj(object)->addr >> 4;
-       else
-               context = 0x00000004; /* just non-zero */
-
-       switch (nv_engidx(object->engine)) {
-       case NVDEV_ENGINE_DMAOBJ:
-       case NVDEV_ENGINE_SW:
-               context |= 0x00000000;
-               break;
-       case NVDEV_ENGINE_GR:
-               context |= 0x00100000;
-               break;
-       case NVDEV_ENGINE_MPEG:
-               context |= 0x00200000;
-               break;
-       default:
-               return -EINVAL;
-       }
-
-       context |= chid << 23;
-
-       mutex_lock(&nv_subdev(priv)->mutex);
-       ret = nouveau_ramht_insert(priv->ramht, chid, handle, context);
-       mutex_unlock(&nv_subdev(priv)->mutex);
-       return ret;
-}
-
-static int
-nv40_fifo_context_attach(struct nouveau_object *parent,
-                        struct nouveau_object *engctx)
-{
-       struct nv04_fifo_priv *priv = (void *)parent->engine;
-       struct nv04_fifo_chan *chan = (void *)parent;
-       unsigned long flags;
-       u32 reg, ctx;
-
-       switch (nv_engidx(engctx->engine)) {
-       case NVDEV_ENGINE_SW:
-               return 0;
-       case NVDEV_ENGINE_GR:
-               reg = 0x32e0;
-               ctx = 0x38;
-               break;
-       case NVDEV_ENGINE_MPEG:
-               reg = 0x330c;
-               ctx = 0x54;
-               break;
-       default:
-               return -EINVAL;
-       }
-
-       spin_lock_irqsave(&priv->base.lock, flags);
-       nv_engctx(engctx)->addr = nv_gpuobj(engctx)->addr >> 4;
-       nv_mask(priv, 0x002500, 0x00000001, 0x00000000);
-
-       if ((nv_rd32(priv, 0x003204) & priv->base.max) == chan->base.chid)
-               nv_wr32(priv, reg, nv_engctx(engctx)->addr);
-       nv_wo32(priv->ramfc, chan->ramfc + ctx, nv_engctx(engctx)->addr);
-
-       nv_mask(priv, 0x002500, 0x00000001, 0x00000001);
-       spin_unlock_irqrestore(&priv->base.lock, flags);
-       return 0;
-}
-
-static int
-nv40_fifo_context_detach(struct nouveau_object *parent, bool suspend,
-                        struct nouveau_object *engctx)
-{
-       struct nv04_fifo_priv *priv = (void *)parent->engine;
-       struct nv04_fifo_chan *chan = (void *)parent;
-       unsigned long flags;
-       u32 reg, ctx;
-
-       switch (nv_engidx(engctx->engine)) {
-       case NVDEV_ENGINE_SW:
-               return 0;
-       case NVDEV_ENGINE_GR:
-               reg = 0x32e0;
-               ctx = 0x38;
-               break;
-       case NVDEV_ENGINE_MPEG:
-               reg = 0x330c;
-               ctx = 0x54;
-               break;
-       default:
-               return -EINVAL;
-       }
-
-       spin_lock_irqsave(&priv->base.lock, flags);
-       nv_mask(priv, 0x002500, 0x00000001, 0x00000000);
-
-       if ((nv_rd32(priv, 0x003204) & priv->base.max) == chan->base.chid)
-               nv_wr32(priv, reg, 0x00000000);
-       nv_wo32(priv->ramfc, chan->ramfc + ctx, 0x00000000);
-
-       nv_mask(priv, 0x002500, 0x00000001, 0x00000001);
-       spin_unlock_irqrestore(&priv->base.lock, flags);
-       return 0;
-}
-
-static int
-nv40_fifo_chan_ctor(struct nouveau_object *parent,
-                   struct nouveau_object *engine,
-                   struct nouveau_oclass *oclass, void *data, u32 size,
-                   struct nouveau_object **pobject)
-{
-       union {
-               struct nv03_channel_dma_v0 v0;
-       } *args = data;
-       struct nv04_fifo_priv *priv = (void *)engine;
-       struct nv04_fifo_chan *chan;
-       int ret;
-
-       nv_ioctl(parent, "create channel dma size %d\n", size);
-       if (nvif_unpack(args->v0, 0, 0, false)) {
-               nv_ioctl(parent, "create channel dma vers %d pushbuf %08x "
-                                "offset %016llx\n", args->v0.version,
-                        args->v0.pushbuf, args->v0.offset);
-       } else
-               return ret;
-
-       ret = nouveau_fifo_channel_create(parent, engine, oclass, 0, 0xc00000,
-                                         0x1000, args->v0.pushbuf,
-                                         (1ULL << NVDEV_ENGINE_DMAOBJ) |
-                                         (1ULL << NVDEV_ENGINE_SW) |
-                                         (1ULL << NVDEV_ENGINE_GR) |
-                                         (1ULL << NVDEV_ENGINE_MPEG), &chan);
-       *pobject = nv_object(chan);
-       if (ret)
-               return ret;
-
-       args->v0.chid = chan->base.chid;
-
-       nv_parent(chan)->context_attach = nv40_fifo_context_attach;
-       nv_parent(chan)->context_detach = nv40_fifo_context_detach;
-       nv_parent(chan)->object_attach = nv40_fifo_object_attach;
-       nv_parent(chan)->object_detach = nv04_fifo_object_detach;
-       chan->ramfc = chan->base.chid * 128;
-
-       nv_wo32(priv->ramfc, chan->ramfc + 0x00, args->v0.offset);
-       nv_wo32(priv->ramfc, chan->ramfc + 0x04, args->v0.offset);
-       nv_wo32(priv->ramfc, chan->ramfc + 0x0c, chan->base.pushgpu->addr >> 4);
-       nv_wo32(priv->ramfc, chan->ramfc + 0x18, 0x30000000 |
-                            NV_PFIFO_CACHE1_DMA_FETCH_TRIG_128_BYTES |
-                            NV_PFIFO_CACHE1_DMA_FETCH_SIZE_128_BYTES |
-#ifdef __BIG_ENDIAN
-                            NV_PFIFO_CACHE1_BIG_ENDIAN |
-#endif
-                            NV_PFIFO_CACHE1_DMA_FETCH_MAX_REQS_8);
-       nv_wo32(priv->ramfc, chan->ramfc + 0x3c, 0x0001ffff);
-       return 0;
-}
-
-static struct nouveau_ofuncs
-nv40_fifo_ofuncs = {
-       .ctor = nv40_fifo_chan_ctor,
-       .dtor = nv04_fifo_chan_dtor,
-       .init = nv04_fifo_chan_init,
-       .fini = nv04_fifo_chan_fini,
-       .map  = _nouveau_fifo_channel_map,
-       .rd32 = _nouveau_fifo_channel_rd32,
-       .wr32 = _nouveau_fifo_channel_wr32,
-       .ntfy = _nouveau_fifo_channel_ntfy
-};
-
-static struct nouveau_oclass
-nv40_fifo_sclass[] = {
-       { NV40_CHANNEL_DMA, &nv40_fifo_ofuncs },
-       {}
-};
-
-/*******************************************************************************
- * FIFO context - basically just the instmem reserved for the channel
- ******************************************************************************/
-
-static struct nouveau_oclass
-nv40_fifo_cclass = {
-       .handle = NV_ENGCTX(FIFO, 0x40),
-       .ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nv04_fifo_context_ctor,
-               .dtor = _nouveau_fifo_context_dtor,
-               .init = _nouveau_fifo_context_init,
-               .fini = _nouveau_fifo_context_fini,
-               .rd32 = _nouveau_fifo_context_rd32,
-               .wr32 = _nouveau_fifo_context_wr32,
-       },
-};
-
-/*******************************************************************************
- * PFIFO engine
- ******************************************************************************/
-
-static int
-nv40_fifo_ctor(struct nouveau_object *parent, struct nouveau_object *engine,
-              struct nouveau_oclass *oclass, void *data, u32 size,
-              struct nouveau_object **pobject)
-{
-       struct nv04_instmem_priv *imem = nv04_instmem(parent);
-       struct nv04_fifo_priv *priv;
-       int ret;
-
-       ret = nouveau_fifo_create(parent, engine, oclass, 0, 31, &priv);
-       *pobject = nv_object(priv);
-       if (ret)
-               return ret;
-
-       nouveau_ramht_ref(imem->ramht, &priv->ramht);
-       nouveau_gpuobj_ref(imem->ramro, &priv->ramro);
-       nouveau_gpuobj_ref(imem->ramfc, &priv->ramfc);
-
-       nv_subdev(priv)->unit = 0x00000100;
-       nv_subdev(priv)->intr = nv04_fifo_intr;
-       nv_engine(priv)->cclass = &nv40_fifo_cclass;
-       nv_engine(priv)->sclass = nv40_fifo_sclass;
-       priv->base.pause = nv04_fifo_pause;
-       priv->base.start = nv04_fifo_start;
-       priv->ramfc_desc = nv40_ramfc;
-       return 0;
-}
-
-static int
-nv40_fifo_init(struct nouveau_object *object)
-{
-       struct nv04_fifo_priv *priv = (void *)object;
-       struct nouveau_fb *pfb = nouveau_fb(object);
-       int ret;
-
-       ret = nouveau_fifo_init(&priv->base);
-       if (ret)
-               return ret;
-
-       nv_wr32(priv, 0x002040, 0x000000ff);
-       nv_wr32(priv, 0x002044, 0x2101ffff);
-       nv_wr32(priv, 0x002058, 0x00000001);
-
-       nv_wr32(priv, NV03_PFIFO_RAMHT, (0x03 << 24) /* search 128 */ |
-                                      ((priv->ramht->bits - 9) << 16) |
-                                       (priv->ramht->base.addr >> 8));
-       nv_wr32(priv, NV03_PFIFO_RAMRO, priv->ramro->addr >> 8);
-
-       switch (nv_device(priv)->chipset) {
-       case 0x47:
-       case 0x49:
-       case 0x4b:
-               nv_wr32(priv, 0x002230, 0x00000001);
-       case 0x40:
-       case 0x41:
-       case 0x42:
-       case 0x43:
-       case 0x45:
-       case 0x48:
-               nv_wr32(priv, 0x002220, 0x00030002);
-               break;
-       default:
-               nv_wr32(priv, 0x002230, 0x00000000);
-               nv_wr32(priv, 0x002220, ((pfb->ram->size - 512 * 1024 +
-                                        priv->ramfc->addr) >> 16) |
-                                       0x00030000);
-               break;
-       }
-
-       nv_wr32(priv, NV03_PFIFO_CACHE1_PUSH1, priv->base.max);
-
-       nv_wr32(priv, NV03_PFIFO_INTR_0, 0xffffffff);
-       nv_wr32(priv, NV03_PFIFO_INTR_EN_0, 0xffffffff);
-
-       nv_wr32(priv, NV03_PFIFO_CACHE1_PUSH0, 1);
-       nv_wr32(priv, NV04_PFIFO_CACHE1_PULL0, 1);
-       nv_wr32(priv, NV03_PFIFO_CACHES, 1);
-       return 0;
-}
-
-struct nouveau_oclass *
-nv40_fifo_oclass = &(struct nouveau_oclass) {
-       .handle = NV_ENGINE(FIFO, 0x40),
-       .ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nv40_fifo_ctor,
-               .dtor = nv04_fifo_dtor,
-               .init = nv40_fifo_init,
-               .fini = _nouveau_fifo_fini,
-       },
-};
diff --git a/drivers/gpu/drm/nouveau/core/engine/fifo/nv50.c b/drivers/gpu/drm/nouveau/core/engine/fifo/nv50.c
deleted file mode 100644 (file)
index 5d1e86b..0000000
+++ /dev/null
@@ -1,541 +0,0 @@
-/*
- * Copyright 2012 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 <core/client.h>
-#include <core/engctx.h>
-#include <core/ramht.h>
-#include <nvif/unpack.h>
-#include <nvif/class.h>
-
-#include <subdev/timer.h>
-#include <subdev/bar.h>
-
-#include <engine/dmaobj.h>
-#include <engine/fifo.h>
-
-#include "nv04.h"
-#include "nv50.h"
-
-/*******************************************************************************
- * FIFO channel objects
- ******************************************************************************/
-
-static void
-nv50_fifo_playlist_update_locked(struct nv50_fifo_priv *priv)
-{
-       struct nouveau_bar *bar = nouveau_bar(priv);
-       struct nouveau_gpuobj *cur;
-       int i, p;
-
-       cur = priv->playlist[priv->cur_playlist];
-       priv->cur_playlist = !priv->cur_playlist;
-
-       for (i = priv->base.min, p = 0; i < priv->base.max; i++) {
-               if (nv_rd32(priv, 0x002600 + (i * 4)) & 0x80000000)
-                       nv_wo32(cur, p++ * 4, i);
-       }
-
-       bar->flush(bar);
-
-       nv_wr32(priv, 0x0032f4, cur->addr >> 12);
-       nv_wr32(priv, 0x0032ec, p);
-       nv_wr32(priv, 0x002500, 0x00000101);
-}
-
-void
-nv50_fifo_playlist_update(struct nv50_fifo_priv *priv)
-{
-       mutex_lock(&nv_subdev(priv)->mutex);
-       nv50_fifo_playlist_update_locked(priv);
-       mutex_unlock(&nv_subdev(priv)->mutex);
-}
-
-static int
-nv50_fifo_context_attach(struct nouveau_object *parent,
-                        struct nouveau_object *object)
-{
-       struct nouveau_bar *bar = nouveau_bar(parent);
-       struct nv50_fifo_base *base = (void *)parent->parent;
-       struct nouveau_gpuobj *ectx = (void *)object;
-       u64 limit = ectx->addr + ectx->size - 1;
-       u64 start = ectx->addr;
-       u32 addr;
-
-       switch (nv_engidx(object->engine)) {
-       case NVDEV_ENGINE_SW   : return 0;
-       case NVDEV_ENGINE_GR   : addr = 0x0000; break;
-       case NVDEV_ENGINE_MPEG : addr = 0x0060; break;
-       default:
-               return -EINVAL;
-       }
-
-       nv_engctx(ectx)->addr = nv_gpuobj(base)->addr >> 12;
-       nv_wo32(base->eng, addr + 0x00, 0x00190000);
-       nv_wo32(base->eng, addr + 0x04, lower_32_bits(limit));
-       nv_wo32(base->eng, addr + 0x08, lower_32_bits(start));
-       nv_wo32(base->eng, addr + 0x0c, upper_32_bits(limit) << 24 |
-                                       upper_32_bits(start));
-       nv_wo32(base->eng, addr + 0x10, 0x00000000);
-       nv_wo32(base->eng, addr + 0x14, 0x00000000);
-       bar->flush(bar);
-       return 0;
-}
-
-static int
-nv50_fifo_context_detach(struct nouveau_object *parent, bool suspend,
-                        struct nouveau_object *object)
-{
-       struct nouveau_bar *bar = nouveau_bar(parent);
-       struct nv50_fifo_priv *priv = (void *)parent->engine;
-       struct nv50_fifo_base *base = (void *)parent->parent;
-       struct nv50_fifo_chan *chan = (void *)parent;
-       u32 addr, me;
-       int ret = 0;
-
-       switch (nv_engidx(object->engine)) {
-       case NVDEV_ENGINE_SW   : return 0;
-       case NVDEV_ENGINE_GR   : addr = 0x0000; break;
-       case NVDEV_ENGINE_MPEG : addr = 0x0060; break;
-       default:
-               return -EINVAL;
-       }
-
-       /* HW bug workaround:
-        *
-        * PFIFO will hang forever if the connected engines don't report
-        * that they've processed the context switch request.
-        *
-        * In order for the kickoff to work, we need to ensure all the
-        * connected engines are in a state where they can answer.
-        *
-        * Newer chipsets don't seem to suffer from this issue, and well,
-        * there's also a "ignore these engines" bitmask reg we can use
-        * if we hit the issue there..
-        */
-       me = nv_mask(priv, 0x00b860, 0x00000001, 0x00000001);
-
-       /* do the kickoff... */
-       nv_wr32(priv, 0x0032fc, nv_gpuobj(base)->addr >> 12);
-       if (!nv_wait_ne(priv, 0x0032fc, 0xffffffff, 0xffffffff)) {
-               nv_error(priv, "channel %d [%s] unload timeout\n",
-                        chan->base.chid, nouveau_client_name(chan));
-               if (suspend)
-                       ret = -EBUSY;
-       }
-       nv_wr32(priv, 0x00b860, me);
-
-       if (ret == 0) {
-               nv_wo32(base->eng, addr + 0x00, 0x00000000);
-               nv_wo32(base->eng, addr + 0x04, 0x00000000);
-               nv_wo32(base->eng, addr + 0x08, 0x00000000);
-               nv_wo32(base->eng, addr + 0x0c, 0x00000000);
-               nv_wo32(base->eng, addr + 0x10, 0x00000000);
-               nv_wo32(base->eng, addr + 0x14, 0x00000000);
-               bar->flush(bar);
-       }
-
-       return ret;
-}
-
-static int
-nv50_fifo_object_attach(struct nouveau_object *parent,
-                       struct nouveau_object *object, u32 handle)
-{
-       struct nv50_fifo_chan *chan = (void *)parent;
-       u32 context;
-
-       if (nv_iclass(object, NV_GPUOBJ_CLASS))
-               context = nv_gpuobj(object)->node->offset >> 4;
-       else
-               context = 0x00000004; /* just non-zero */
-
-       switch (nv_engidx(object->engine)) {
-       case NVDEV_ENGINE_DMAOBJ:
-       case NVDEV_ENGINE_SW    : context |= 0x00000000; break;
-       case NVDEV_ENGINE_GR    : context |= 0x00100000; break;
-       case NVDEV_ENGINE_MPEG  : context |= 0x00200000; break;
-       default:
-               return -EINVAL;
-       }
-
-       return nouveau_ramht_insert(chan->ramht, 0, handle, context);
-}
-
-void
-nv50_fifo_object_detach(struct nouveau_object *parent, int cookie)
-{
-       struct nv50_fifo_chan *chan = (void *)parent;
-       nouveau_ramht_remove(chan->ramht, cookie);
-}
-
-static int
-nv50_fifo_chan_ctor_dma(struct nouveau_object *parent,
-                       struct nouveau_object *engine,
-                       struct nouveau_oclass *oclass, void *data, u32 size,
-                       struct nouveau_object **pobject)
-{
-       union {
-               struct nv03_channel_dma_v0 v0;
-       } *args = data;
-       struct nouveau_bar *bar = nouveau_bar(parent);
-       struct nv50_fifo_base *base = (void *)parent;
-       struct nv50_fifo_chan *chan;
-       int ret;
-
-       nv_ioctl(parent, "create channel dma size %d\n", size);
-       if (nvif_unpack(args->v0, 0, 0, false)) {
-               nv_ioctl(parent, "create channel dma vers %d pushbuf %08x "
-                                "offset %016llx\n", args->v0.version,
-                        args->v0.pushbuf, args->v0.offset);
-       } else
-               return ret;
-
-       ret = nouveau_fifo_channel_create(parent, engine, oclass, 0, 0xc00000,
-                                         0x2000, args->v0.pushbuf,
-                                         (1ULL << NVDEV_ENGINE_DMAOBJ) |
-                                         (1ULL << NVDEV_ENGINE_SW) |
-                                         (1ULL << NVDEV_ENGINE_GR) |
-                                         (1ULL << NVDEV_ENGINE_MPEG), &chan);
-       *pobject = nv_object(chan);
-       if (ret)
-               return ret;
-
-       args->v0.chid = chan->base.chid;
-
-       nv_parent(chan)->context_attach = nv50_fifo_context_attach;
-       nv_parent(chan)->context_detach = nv50_fifo_context_detach;
-       nv_parent(chan)->object_attach = nv50_fifo_object_attach;
-       nv_parent(chan)->object_detach = nv50_fifo_object_detach;
-
-       ret = nouveau_ramht_new(nv_object(chan), nv_object(chan), 0x8000, 16,
-                               &chan->ramht);
-       if (ret)
-               return ret;
-
-       nv_wo32(base->ramfc, 0x08, lower_32_bits(args->v0.offset));
-       nv_wo32(base->ramfc, 0x0c, upper_32_bits(args->v0.offset));
-       nv_wo32(base->ramfc, 0x10, lower_32_bits(args->v0.offset));
-       nv_wo32(base->ramfc, 0x14, upper_32_bits(args->v0.offset));
-       nv_wo32(base->ramfc, 0x3c, 0x003f6078);
-       nv_wo32(base->ramfc, 0x44, 0x01003fff);
-       nv_wo32(base->ramfc, 0x48, chan->base.pushgpu->node->offset >> 4);
-       nv_wo32(base->ramfc, 0x4c, 0xffffffff);
-       nv_wo32(base->ramfc, 0x60, 0x7fffffff);
-       nv_wo32(base->ramfc, 0x78, 0x00000000);
-       nv_wo32(base->ramfc, 0x7c, 0x30000001);
-       nv_wo32(base->ramfc, 0x80, ((chan->ramht->bits - 9) << 27) |
-                                  (4 << 24) /* SEARCH_FULL */ |
-                                  (chan->ramht->base.node->offset >> 4));
-       bar->flush(bar);
-       return 0;
-}
-
-static int
-nv50_fifo_chan_ctor_ind(struct nouveau_object *parent,
-                       struct nouveau_object *engine,
-                       struct nouveau_oclass *oclass, void *data, u32 size,
-                       struct nouveau_object **pobject)
-{
-       union {
-               struct nv50_channel_gpfifo_v0 v0;
-       } *args = data;
-       struct nouveau_bar *bar = nouveau_bar(parent);
-       struct nv50_fifo_base *base = (void *)parent;
-       struct nv50_fifo_chan *chan;
-       u64 ioffset, ilength;
-       int ret;
-
-       nv_ioctl(parent, "create channel gpfifo size %d\n", size);
-       if (nvif_unpack(args->v0, 0, 0, false)) {
-               nv_ioctl(parent, "create channel gpfifo vers %d pushbuf %08x "
-                                "ioffset %016llx ilength %08x\n",
-                        args->v0.version, args->v0.pushbuf, args->v0.ioffset,
-                        args->v0.ilength);
-       } else
-               return ret;
-
-       ret = nouveau_fifo_channel_create(parent, engine, oclass, 0, 0xc00000,
-                                         0x2000, args->v0.pushbuf,
-                                         (1ULL << NVDEV_ENGINE_DMAOBJ) |
-                                         (1ULL << NVDEV_ENGINE_SW) |
-                                         (1ULL << NVDEV_ENGINE_GR) |
-                                         (1ULL << NVDEV_ENGINE_MPEG), &chan);
-       *pobject = nv_object(chan);
-       if (ret)
-               return ret;
-
-       args->v0.chid = chan->base.chid;
-
-       nv_parent(chan)->context_attach = nv50_fifo_context_attach;
-       nv_parent(chan)->context_detach = nv50_fifo_context_detach;
-       nv_parent(chan)->object_attach = nv50_fifo_object_attach;
-       nv_parent(chan)->object_detach = nv50_fifo_object_detach;
-
-       ret = nouveau_ramht_new(nv_object(chan), nv_object(chan), 0x8000, 16,
-                              &chan->ramht);
-       if (ret)
-               return ret;
-
-       ioffset = args->v0.ioffset;
-       ilength = order_base_2(args->v0.ilength / 8);
-
-       nv_wo32(base->ramfc, 0x3c, 0x403f6078);
-       nv_wo32(base->ramfc, 0x44, 0x01003fff);
-       nv_wo32(base->ramfc, 0x48, chan->base.pushgpu->node->offset >> 4);
-       nv_wo32(base->ramfc, 0x50, lower_32_bits(ioffset));
-       nv_wo32(base->ramfc, 0x54, upper_32_bits(ioffset) | (ilength << 16));
-       nv_wo32(base->ramfc, 0x60, 0x7fffffff);
-       nv_wo32(base->ramfc, 0x78, 0x00000000);
-       nv_wo32(base->ramfc, 0x7c, 0x30000001);
-       nv_wo32(base->ramfc, 0x80, ((chan->ramht->bits - 9) << 27) |
-                                  (4 << 24) /* SEARCH_FULL */ |
-                                  (chan->ramht->base.node->offset >> 4));
-       bar->flush(bar);
-       return 0;
-}
-
-void
-nv50_fifo_chan_dtor(struct nouveau_object *object)
-{
-       struct nv50_fifo_chan *chan = (void *)object;
-       nouveau_ramht_ref(NULL, &chan->ramht);
-       nouveau_fifo_channel_destroy(&chan->base);
-}
-
-static int
-nv50_fifo_chan_init(struct nouveau_object *object)
-{
-       struct nv50_fifo_priv *priv = (void *)object->engine;
-       struct nv50_fifo_base *base = (void *)object->parent;
-       struct nv50_fifo_chan *chan = (void *)object;
-       struct nouveau_gpuobj *ramfc = base->ramfc;
-       u32 chid = chan->base.chid;
-       int ret;
-
-       ret = nouveau_fifo_channel_init(&chan->base);
-       if (ret)
-               return ret;
-
-       nv_wr32(priv, 0x002600 + (chid * 4), 0x80000000 | ramfc->addr >> 12);
-       nv50_fifo_playlist_update(priv);
-       return 0;
-}
-
-int
-nv50_fifo_chan_fini(struct nouveau_object *object, bool suspend)
-{
-       struct nv50_fifo_priv *priv = (void *)object->engine;
-       struct nv50_fifo_chan *chan = (void *)object;
-       u32 chid = chan->base.chid;
-
-       /* remove channel from playlist, fifo will unload context */
-       nv_mask(priv, 0x002600 + (chid * 4), 0x80000000, 0x00000000);
-       nv50_fifo_playlist_update(priv);
-       nv_wr32(priv, 0x002600 + (chid * 4), 0x00000000);
-
-       return nouveau_fifo_channel_fini(&chan->base, suspend);
-}
-
-static struct nouveau_ofuncs
-nv50_fifo_ofuncs_dma = {
-       .ctor = nv50_fifo_chan_ctor_dma,
-       .dtor = nv50_fifo_chan_dtor,
-       .init = nv50_fifo_chan_init,
-       .fini = nv50_fifo_chan_fini,
-       .map  = _nouveau_fifo_channel_map,
-       .rd32 = _nouveau_fifo_channel_rd32,
-       .wr32 = _nouveau_fifo_channel_wr32,
-       .ntfy = _nouveau_fifo_channel_ntfy
-};
-
-static struct nouveau_ofuncs
-nv50_fifo_ofuncs_ind = {
-       .ctor = nv50_fifo_chan_ctor_ind,
-       .dtor = nv50_fifo_chan_dtor,
-       .init = nv50_fifo_chan_init,
-       .fini = nv50_fifo_chan_fini,
-       .map  = _nouveau_fifo_channel_map,
-       .rd32 = _nouveau_fifo_channel_rd32,
-       .wr32 = _nouveau_fifo_channel_wr32,
-       .ntfy = _nouveau_fifo_channel_ntfy
-};
-
-static struct nouveau_oclass
-nv50_fifo_sclass[] = {
-       { NV50_CHANNEL_DMA, &nv50_fifo_ofuncs_dma },
-       { NV50_CHANNEL_GPFIFO, &nv50_fifo_ofuncs_ind },
-       {}
-};
-
-/*******************************************************************************
- * FIFO context - basically just the instmem reserved for the channel
- ******************************************************************************/
-
-static int
-nv50_fifo_context_ctor(struct nouveau_object *parent,
-                      struct nouveau_object *engine,
-                      struct nouveau_oclass *oclass, void *data, u32 size,
-                      struct nouveau_object **pobject)
-{
-       struct nv50_fifo_base *base;
-       int ret;
-
-       ret = nouveau_fifo_context_create(parent, engine, oclass, NULL, 0x10000,
-                                         0x1000, NVOBJ_FLAG_HEAP, &base);
-       *pobject = nv_object(base);
-       if (ret)
-               return ret;
-
-       ret = nouveau_gpuobj_new(nv_object(base), nv_object(base), 0x0200,
-                                0x1000, NVOBJ_FLAG_ZERO_ALLOC, &base->ramfc);
-       if (ret)
-               return ret;
-
-       ret = nouveau_gpuobj_new(nv_object(base), nv_object(base), 0x1200, 0,
-                                NVOBJ_FLAG_ZERO_ALLOC, &base->eng);
-       if (ret)
-               return ret;
-
-       ret = nouveau_gpuobj_new(nv_object(base), nv_object(base), 0x4000, 0, 0,
-                               &base->pgd);
-       if (ret)
-               return ret;
-
-       ret = nouveau_vm_ref(nouveau_client(parent)->vm, &base->vm, base->pgd);
-       if (ret)
-               return ret;
-
-       return 0;
-}
-
-void
-nv50_fifo_context_dtor(struct nouveau_object *object)
-{
-       struct nv50_fifo_base *base = (void *)object;
-       nouveau_vm_ref(NULL, &base->vm, base->pgd);
-       nouveau_gpuobj_ref(NULL, &base->pgd);
-       nouveau_gpuobj_ref(NULL, &base->eng);
-       nouveau_gpuobj_ref(NULL, &base->ramfc);
-       nouveau_gpuobj_ref(NULL, &base->cache);
-       nouveau_fifo_context_destroy(&base->base);
-}
-
-static struct nouveau_oclass
-nv50_fifo_cclass = {
-       .handle = NV_ENGCTX(FIFO, 0x50),
-       .ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nv50_fifo_context_ctor,
-               .dtor = nv50_fifo_context_dtor,
-               .init = _nouveau_fifo_context_init,
-               .fini = _nouveau_fifo_context_fini,
-               .rd32 = _nouveau_fifo_context_rd32,
-               .wr32 = _nouveau_fifo_context_wr32,
-       },
-};
-
-/*******************************************************************************
- * PFIFO engine
- ******************************************************************************/
-
-static int
-nv50_fifo_ctor(struct nouveau_object *parent, struct nouveau_object *engine,
-              struct nouveau_oclass *oclass, void *data, u32 size,
-              struct nouveau_object **pobject)
-{
-       struct nv50_fifo_priv *priv;
-       int ret;
-
-       ret = nouveau_fifo_create(parent, engine, oclass, 1, 127, &priv);
-       *pobject = nv_object(priv);
-       if (ret)
-               return ret;
-
-       ret = nouveau_gpuobj_new(nv_object(priv), NULL, 128 * 4, 0x1000, 0,
-                               &priv->playlist[0]);
-       if (ret)
-               return ret;
-
-       ret = nouveau_gpuobj_new(nv_object(priv), NULL, 128 * 4, 0x1000, 0,
-                               &priv->playlist[1]);
-       if (ret)
-               return ret;
-
-       nv_subdev(priv)->unit = 0x00000100;
-       nv_subdev(priv)->intr = nv04_fifo_intr;
-       nv_engine(priv)->cclass = &nv50_fifo_cclass;
-       nv_engine(priv)->sclass = nv50_fifo_sclass;
-       priv->base.pause = nv04_fifo_pause;
-       priv->base.start = nv04_fifo_start;
-       return 0;
-}
-
-void
-nv50_fifo_dtor(struct nouveau_object *object)
-{
-       struct nv50_fifo_priv *priv = (void *)object;
-
-       nouveau_gpuobj_ref(NULL, &priv->playlist[1]);
-       nouveau_gpuobj_ref(NULL, &priv->playlist[0]);
-
-       nouveau_fifo_destroy(&priv->base);
-}
-
-int
-nv50_fifo_init(struct nouveau_object *object)
-{
-       struct nv50_fifo_priv *priv = (void *)object;
-       int ret, i;
-
-       ret = nouveau_fifo_init(&priv->base);
-       if (ret)
-               return ret;
-
-       nv_mask(priv, 0x000200, 0x00000100, 0x00000000);
-       nv_mask(priv, 0x000200, 0x00000100, 0x00000100);
-       nv_wr32(priv, 0x00250c, 0x6f3cfc34);
-       nv_wr32(priv, 0x002044, 0x01003fff);
-
-       nv_wr32(priv, 0x002100, 0xffffffff);
-       nv_wr32(priv, 0x002140, 0xbfffffff);
-
-       for (i = 0; i < 128; i++)
-               nv_wr32(priv, 0x002600 + (i * 4), 0x00000000);
-       nv50_fifo_playlist_update_locked(priv);
-
-       nv_wr32(priv, 0x003200, 0x00000001);
-       nv_wr32(priv, 0x003250, 0x00000001);
-       nv_wr32(priv, 0x002500, 0x00000001);
-       return 0;
-}
-
-struct nouveau_oclass *
-nv50_fifo_oclass = &(struct nouveau_oclass) {
-       .handle = NV_ENGINE(FIFO, 0x50),
-       .ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nv50_fifo_ctor,
-               .dtor = nv50_fifo_dtor,
-               .init = nv50_fifo_init,
-               .fini = _nouveau_fifo_fini,
-       },
-};
diff --git a/drivers/gpu/drm/nouveau/core/engine/fifo/nv50.h b/drivers/gpu/drm/nouveau/core/engine/fifo/nv50.h
deleted file mode 100644 (file)
index 3a9ceb3..0000000
+++ /dev/null
@@ -1,36 +0,0 @@
-#ifndef __NV50_FIFO_H__
-#define __NV50_FIFO_H__
-
-struct nv50_fifo_priv {
-       struct nouveau_fifo base;
-       struct nouveau_gpuobj *playlist[2];
-       int cur_playlist;
-};
-
-struct nv50_fifo_base {
-       struct nouveau_fifo_base base;
-       struct nouveau_gpuobj *ramfc;
-       struct nouveau_gpuobj *cache;
-       struct nouveau_gpuobj *eng;
-       struct nouveau_gpuobj *pgd;
-       struct nouveau_vm *vm;
-};
-
-struct nv50_fifo_chan {
-       struct nouveau_fifo_chan base;
-       u32 subc[8];
-       struct nouveau_ramht *ramht;
-};
-
-void nv50_fifo_playlist_update(struct nv50_fifo_priv *);
-
-void nv50_fifo_object_detach(struct nouveau_object *, int);
-void nv50_fifo_chan_dtor(struct nouveau_object *);
-int  nv50_fifo_chan_fini(struct nouveau_object *, bool);
-
-void nv50_fifo_context_dtor(struct nouveau_object *);
-
-void nv50_fifo_dtor(struct nouveau_object *);
-int  nv50_fifo_init(struct nouveau_object *);
-
-#endif
diff --git a/drivers/gpu/drm/nouveau/core/engine/fifo/nv84.c b/drivers/gpu/drm/nouveau/core/engine/fifo/nv84.c
deleted file mode 100644 (file)
index 1f42996..0000000
+++ /dev/null
@@ -1,481 +0,0 @@
-/*
- * Copyright 2012 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 <core/os.h>
-#include <core/client.h>
-#include <core/engctx.h>
-#include <core/ramht.h>
-#include <core/event.h>
-#include <nvif/unpack.h>
-#include <nvif/class.h>
-
-#include <subdev/timer.h>
-#include <subdev/bar.h>
-
-#include <engine/dmaobj.h>
-#include <engine/fifo.h>
-
-#include "nv04.h"
-#include "nv50.h"
-
-/*******************************************************************************
- * FIFO channel objects
- ******************************************************************************/
-
-static int
-nv84_fifo_context_attach(struct nouveau_object *parent,
-                        struct nouveau_object *object)
-{
-       struct nouveau_bar *bar = nouveau_bar(parent);
-       struct nv50_fifo_base *base = (void *)parent->parent;
-       struct nouveau_gpuobj *ectx = (void *)object;
-       u64 limit = ectx->addr + ectx->size - 1;
-       u64 start = ectx->addr;
-       u32 addr;
-
-       switch (nv_engidx(object->engine)) {
-       case NVDEV_ENGINE_SW   : return 0;
-       case NVDEV_ENGINE_GR   : addr = 0x0020; break;
-       case NVDEV_ENGINE_VP   : addr = 0x0040; break;
-       case NVDEV_ENGINE_PPP  :
-       case NVDEV_ENGINE_MPEG : addr = 0x0060; break;
-       case NVDEV_ENGINE_BSP  : addr = 0x0080; break;
-       case NVDEV_ENGINE_CRYPT: addr = 0x00a0; break;
-       case NVDEV_ENGINE_COPY0: addr = 0x00c0; break;
-       default:
-               return -EINVAL;
-       }
-
-       nv_engctx(ectx)->addr = nv_gpuobj(base)->addr >> 12;
-       nv_wo32(base->eng, addr + 0x00, 0x00190000);
-       nv_wo32(base->eng, addr + 0x04, lower_32_bits(limit));
-       nv_wo32(base->eng, addr + 0x08, lower_32_bits(start));
-       nv_wo32(base->eng, addr + 0x0c, upper_32_bits(limit) << 24 |
-                                       upper_32_bits(start));
-       nv_wo32(base->eng, addr + 0x10, 0x00000000);
-       nv_wo32(base->eng, addr + 0x14, 0x00000000);
-       bar->flush(bar);
-       return 0;
-}
-
-static int
-nv84_fifo_context_detach(struct nouveau_object *parent, bool suspend,
-                        struct nouveau_object *object)
-{
-       struct nouveau_bar *bar = nouveau_bar(parent);
-       struct nv50_fifo_priv *priv = (void *)parent->engine;
-       struct nv50_fifo_base *base = (void *)parent->parent;
-       struct nv50_fifo_chan *chan = (void *)parent;
-       u32 addr, save, engn;
-       bool done;
-
-       switch (nv_engidx(object->engine)) {
-       case NVDEV_ENGINE_SW   : return 0;
-       case NVDEV_ENGINE_GR   : engn = 0; addr = 0x0020; break;
-       case NVDEV_ENGINE_VP   : engn = 3; addr = 0x0040; break;
-       case NVDEV_ENGINE_PPP  :
-       case NVDEV_ENGINE_MPEG : engn = 1; addr = 0x0060; break;
-       case NVDEV_ENGINE_BSP  : engn = 5; addr = 0x0080; break;
-       case NVDEV_ENGINE_CRYPT: engn = 4; addr = 0x00a0; break;
-       case NVDEV_ENGINE_COPY0: engn = 2; addr = 0x00c0; break;
-       default:
-               return -EINVAL;
-       }
-
-       save = nv_mask(priv, 0x002520, 0x0000003f, 1 << engn);
-       nv_wr32(priv, 0x0032fc, nv_gpuobj(base)->addr >> 12);
-       done = nv_wait_ne(priv, 0x0032fc, 0xffffffff, 0xffffffff);
-       nv_wr32(priv, 0x002520, save);
-       if (!done) {
-               nv_error(priv, "channel %d [%s] unload timeout\n",
-                        chan->base.chid, nouveau_client_name(chan));
-               if (suspend)
-                       return -EBUSY;
-       }
-
-       nv_wo32(base->eng, addr + 0x00, 0x00000000);
-       nv_wo32(base->eng, addr + 0x04, 0x00000000);
-       nv_wo32(base->eng, addr + 0x08, 0x00000000);
-       nv_wo32(base->eng, addr + 0x0c, 0x00000000);
-       nv_wo32(base->eng, addr + 0x10, 0x00000000);
-       nv_wo32(base->eng, addr + 0x14, 0x00000000);
-       bar->flush(bar);
-       return 0;
-}
-
-static int
-nv84_fifo_object_attach(struct nouveau_object *parent,
-                       struct nouveau_object *object, u32 handle)
-{
-       struct nv50_fifo_chan *chan = (void *)parent;
-       u32 context;
-
-       if (nv_iclass(object, NV_GPUOBJ_CLASS))
-               context = nv_gpuobj(object)->node->offset >> 4;
-       else
-               context = 0x00000004; /* just non-zero */
-
-       switch (nv_engidx(object->engine)) {
-       case NVDEV_ENGINE_DMAOBJ:
-       case NVDEV_ENGINE_SW    : context |= 0x00000000; break;
-       case NVDEV_ENGINE_GR    : context |= 0x00100000; break;
-       case NVDEV_ENGINE_MPEG  :
-       case NVDEV_ENGINE_PPP   : context |= 0x00200000; break;
-       case NVDEV_ENGINE_ME    :
-       case NVDEV_ENGINE_COPY0 : context |= 0x00300000; break;
-       case NVDEV_ENGINE_VP    : context |= 0x00400000; break;
-       case NVDEV_ENGINE_CRYPT :
-       case NVDEV_ENGINE_VIC   : context |= 0x00500000; break;
-       case NVDEV_ENGINE_BSP   : context |= 0x00600000; break;
-       default:
-               return -EINVAL;
-       }
-
-       return nouveau_ramht_insert(chan->ramht, 0, handle, context);
-}
-
-static int
-nv84_fifo_chan_ctor_dma(struct nouveau_object *parent,
-                       struct nouveau_object *engine,
-                       struct nouveau_oclass *oclass, void *data, u32 size,
-                       struct nouveau_object **pobject)
-{
-       union {
-               struct nv03_channel_dma_v0 v0;
-       } *args = data;
-       struct nouveau_bar *bar = nouveau_bar(parent);
-       struct nv50_fifo_base *base = (void *)parent;
-       struct nv50_fifo_chan *chan;
-       int ret;
-
-       nv_ioctl(parent, "create channel dma size %d\n", size);
-       if (nvif_unpack(args->v0, 0, 0, false)) {
-               nv_ioctl(parent, "create channel dma vers %d pushbuf %08x "
-                                "offset %016llx\n", args->v0.version,
-                        args->v0.pushbuf, args->v0.offset);
-       } else
-               return ret;
-
-       ret = nouveau_fifo_channel_create(parent, engine, oclass, 0, 0xc00000,
-                                         0x2000, args->v0.pushbuf,
-                                         (1ULL << NVDEV_ENGINE_DMAOBJ) |
-                                         (1ULL << NVDEV_ENGINE_SW) |
-                                         (1ULL << NVDEV_ENGINE_GR) |
-                                         (1ULL << NVDEV_ENGINE_MPEG) |
-                                         (1ULL << NVDEV_ENGINE_ME) |
-                                         (1ULL << NVDEV_ENGINE_VP) |
-                                         (1ULL << NVDEV_ENGINE_CRYPT) |
-                                         (1ULL << NVDEV_ENGINE_BSP) |
-                                         (1ULL << NVDEV_ENGINE_PPP) |
-                                         (1ULL << NVDEV_ENGINE_COPY0) |
-                                         (1ULL << NVDEV_ENGINE_VIC), &chan);
-       *pobject = nv_object(chan);
-       if (ret)
-               return ret;
-
-       args->v0.chid = chan->base.chid;
-
-       ret = nouveau_ramht_new(nv_object(chan), nv_object(chan), 0x8000, 16,
-                              &chan->ramht);
-       if (ret)
-               return ret;
-
-       nv_parent(chan)->context_attach = nv84_fifo_context_attach;
-       nv_parent(chan)->context_detach = nv84_fifo_context_detach;
-       nv_parent(chan)->object_attach = nv84_fifo_object_attach;
-       nv_parent(chan)->object_detach = nv50_fifo_object_detach;
-
-       nv_wo32(base->ramfc, 0x08, lower_32_bits(args->v0.offset));
-       nv_wo32(base->ramfc, 0x0c, upper_32_bits(args->v0.offset));
-       nv_wo32(base->ramfc, 0x10, lower_32_bits(args->v0.offset));
-       nv_wo32(base->ramfc, 0x14, upper_32_bits(args->v0.offset));
-       nv_wo32(base->ramfc, 0x3c, 0x003f6078);
-       nv_wo32(base->ramfc, 0x44, 0x01003fff);
-       nv_wo32(base->ramfc, 0x48, chan->base.pushgpu->node->offset >> 4);
-       nv_wo32(base->ramfc, 0x4c, 0xffffffff);
-       nv_wo32(base->ramfc, 0x60, 0x7fffffff);
-       nv_wo32(base->ramfc, 0x78, 0x00000000);
-       nv_wo32(base->ramfc, 0x7c, 0x30000001);
-       nv_wo32(base->ramfc, 0x80, ((chan->ramht->bits - 9) << 27) |
-                                  (4 << 24) /* SEARCH_FULL */ |
-                                  (chan->ramht->base.node->offset >> 4));
-       nv_wo32(base->ramfc, 0x88, base->cache->addr >> 10);
-       nv_wo32(base->ramfc, 0x98, nv_gpuobj(base)->addr >> 12);
-       bar->flush(bar);
-       return 0;
-}
-
-static int
-nv84_fifo_chan_ctor_ind(struct nouveau_object *parent,
-                       struct nouveau_object *engine,
-                       struct nouveau_oclass *oclass, void *data, u32 size,
-                       struct nouveau_object **pobject)
-{
-       union {
-               struct nv50_channel_gpfifo_v0 v0;
-       } *args = data;
-       struct nouveau_bar *bar = nouveau_bar(parent);
-       struct nv50_fifo_base *base = (void *)parent;
-       struct nv50_fifo_chan *chan;
-       u64 ioffset, ilength;
-       int ret;
-
-       nv_ioctl(parent, "create channel gpfifo size %d\n", size);
-       if (nvif_unpack(args->v0, 0, 0, false)) {
-               nv_ioctl(parent, "create channel gpfifo vers %d pushbuf %08x "
-                                "ioffset %016llx ilength %08x\n",
-                        args->v0.version, args->v0.pushbuf, args->v0.ioffset,
-                        args->v0.ilength);
-       } else
-               return ret;
-
-       ret = nouveau_fifo_channel_create(parent, engine, oclass, 0, 0xc00000,
-                                         0x2000, args->v0.pushbuf,
-                                         (1ULL << NVDEV_ENGINE_DMAOBJ) |
-                                         (1ULL << NVDEV_ENGINE_SW) |
-                                         (1ULL << NVDEV_ENGINE_GR) |
-                                         (1ULL << NVDEV_ENGINE_MPEG) |
-                                         (1ULL << NVDEV_ENGINE_ME) |
-                                         (1ULL << NVDEV_ENGINE_VP) |
-                                         (1ULL << NVDEV_ENGINE_CRYPT) |
-                                         (1ULL << NVDEV_ENGINE_BSP) |
-                                         (1ULL << NVDEV_ENGINE_PPP) |
-                                         (1ULL << NVDEV_ENGINE_COPY0) |
-                                         (1ULL << NVDEV_ENGINE_VIC), &chan);
-       *pobject = nv_object(chan);
-       if (ret)
-               return ret;
-
-       args->v0.chid = chan->base.chid;
-
-       ret = nouveau_ramht_new(nv_object(chan), nv_object(chan), 0x8000, 16,
-                              &chan->ramht);
-       if (ret)
-               return ret;
-
-       nv_parent(chan)->context_attach = nv84_fifo_context_attach;
-       nv_parent(chan)->context_detach = nv84_fifo_context_detach;
-       nv_parent(chan)->object_attach = nv84_fifo_object_attach;
-       nv_parent(chan)->object_detach = nv50_fifo_object_detach;
-
-       ioffset = args->v0.ioffset;
-       ilength = order_base_2(args->v0.ilength / 8);
-
-       nv_wo32(base->ramfc, 0x3c, 0x403f6078);
-       nv_wo32(base->ramfc, 0x44, 0x01003fff);
-       nv_wo32(base->ramfc, 0x48, chan->base.pushgpu->node->offset >> 4);
-       nv_wo32(base->ramfc, 0x50, lower_32_bits(ioffset));
-       nv_wo32(base->ramfc, 0x54, upper_32_bits(ioffset) | (ilength << 16));
-       nv_wo32(base->ramfc, 0x60, 0x7fffffff);
-       nv_wo32(base->ramfc, 0x78, 0x00000000);
-       nv_wo32(base->ramfc, 0x7c, 0x30000001);
-       nv_wo32(base->ramfc, 0x80, ((chan->ramht->bits - 9) << 27) |
-                                  (4 << 24) /* SEARCH_FULL */ |
-                                  (chan->ramht->base.node->offset >> 4));
-       nv_wo32(base->ramfc, 0x88, base->cache->addr >> 10);
-       nv_wo32(base->ramfc, 0x98, nv_gpuobj(base)->addr >> 12);
-       bar->flush(bar);
-       return 0;
-}
-
-static int
-nv84_fifo_chan_init(struct nouveau_object *object)
-{
-       struct nv50_fifo_priv *priv = (void *)object->engine;
-       struct nv50_fifo_base *base = (void *)object->parent;
-       struct nv50_fifo_chan *chan = (void *)object;
-       struct nouveau_gpuobj *ramfc = base->ramfc;
-       u32 chid = chan->base.chid;
-       int ret;
-
-       ret = nouveau_fifo_channel_init(&chan->base);
-       if (ret)
-               return ret;
-
-       nv_wr32(priv, 0x002600 + (chid * 4), 0x80000000 | ramfc->addr >> 8);
-       nv50_fifo_playlist_update(priv);
-       return 0;
-}
-
-static struct nouveau_ofuncs
-nv84_fifo_ofuncs_dma = {
-       .ctor = nv84_fifo_chan_ctor_dma,
-       .dtor = nv50_fifo_chan_dtor,
-       .init = nv84_fifo_chan_init,
-       .fini = nv50_fifo_chan_fini,
-       .map  = _nouveau_fifo_channel_map,
-       .rd32 = _nouveau_fifo_channel_rd32,
-       .wr32 = _nouveau_fifo_channel_wr32,
-       .ntfy = _nouveau_fifo_channel_ntfy
-};
-
-static struct nouveau_ofuncs
-nv84_fifo_ofuncs_ind = {
-       .ctor = nv84_fifo_chan_ctor_ind,
-       .dtor = nv50_fifo_chan_dtor,
-       .init = nv84_fifo_chan_init,
-       .fini = nv50_fifo_chan_fini,
-       .map  = _nouveau_fifo_channel_map,
-       .rd32 = _nouveau_fifo_channel_rd32,
-       .wr32 = _nouveau_fifo_channel_wr32,
-       .ntfy = _nouveau_fifo_channel_ntfy
-};
-
-static struct nouveau_oclass
-nv84_fifo_sclass[] = {
-       { G82_CHANNEL_DMA, &nv84_fifo_ofuncs_dma },
-       { G82_CHANNEL_GPFIFO, &nv84_fifo_ofuncs_ind },
-       {}
-};
-
-/*******************************************************************************
- * FIFO context - basically just the instmem reserved for the channel
- ******************************************************************************/
-
-static int
-nv84_fifo_context_ctor(struct nouveau_object *parent,
-                      struct nouveau_object *engine,
-                      struct nouveau_oclass *oclass, void *data, u32 size,
-                      struct nouveau_object **pobject)
-{
-       struct nv50_fifo_base *base;
-       int ret;
-
-       ret = nouveau_fifo_context_create(parent, engine, oclass, NULL, 0x10000,
-                                         0x1000, NVOBJ_FLAG_HEAP, &base);
-       *pobject = nv_object(base);
-       if (ret)
-               return ret;
-
-       ret = nouveau_gpuobj_new(nv_object(base), nv_object(base), 0x0200, 0,
-                                NVOBJ_FLAG_ZERO_ALLOC, &base->eng);
-       if (ret)
-               return ret;
-
-       ret = nouveau_gpuobj_new(nv_object(base), nv_object(base), 0x4000, 0,
-                                0, &base->pgd);
-       if (ret)
-               return ret;
-
-       ret = nouveau_vm_ref(nouveau_client(parent)->vm, &base->vm, base->pgd);
-       if (ret)
-               return ret;
-
-       ret = nouveau_gpuobj_new(nv_object(base), nv_object(base), 0x1000,
-                                0x400, NVOBJ_FLAG_ZERO_ALLOC, &base->cache);
-       if (ret)
-               return ret;
-
-       ret = nouveau_gpuobj_new(nv_object(base), nv_object(base), 0x0100,
-                                0x100, NVOBJ_FLAG_ZERO_ALLOC, &base->ramfc);
-       if (ret)
-               return ret;
-
-       return 0;
-}
-
-static struct nouveau_oclass
-nv84_fifo_cclass = {
-       .handle = NV_ENGCTX(FIFO, 0x84),
-       .ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nv84_fifo_context_ctor,
-               .dtor = nv50_fifo_context_dtor,
-               .init = _nouveau_fifo_context_init,
-               .fini = _nouveau_fifo_context_fini,
-               .rd32 = _nouveau_fifo_context_rd32,
-               .wr32 = _nouveau_fifo_context_wr32,
-       },
-};
-
-/*******************************************************************************
- * PFIFO engine
- ******************************************************************************/
-
-static void
-nv84_fifo_uevent_init(struct nvkm_event *event, int type, int index)
-{
-       struct nouveau_fifo *fifo = container_of(event, typeof(*fifo), uevent);
-       nv_mask(fifo, 0x002140, 0x40000000, 0x40000000);
-}
-
-static void
-nv84_fifo_uevent_fini(struct nvkm_event *event, int type, int index)
-{
-       struct nouveau_fifo *fifo = container_of(event, typeof(*fifo), uevent);
-       nv_mask(fifo, 0x002140, 0x40000000, 0x00000000);
-}
-
-static const struct nvkm_event_func
-nv84_fifo_uevent_func = {
-       .ctor = nouveau_fifo_uevent_ctor,
-       .init = nv84_fifo_uevent_init,
-       .fini = nv84_fifo_uevent_fini,
-};
-
-static int
-nv84_fifo_ctor(struct nouveau_object *parent, struct nouveau_object *engine,
-              struct nouveau_oclass *oclass, void *data, u32 size,
-              struct nouveau_object **pobject)
-{
-       struct nv50_fifo_priv *priv;
-       int ret;
-
-       ret = nouveau_fifo_create(parent, engine, oclass, 1, 127, &priv);
-       *pobject = nv_object(priv);
-       if (ret)
-               return ret;
-
-       ret = nouveau_gpuobj_new(nv_object(priv), NULL, 128 * 4, 0x1000, 0,
-                               &priv->playlist[0]);
-       if (ret)
-               return ret;
-
-       ret = nouveau_gpuobj_new(nv_object(priv), NULL, 128 * 4, 0x1000, 0,
-                               &priv->playlist[1]);
-       if (ret)
-               return ret;
-
-       ret = nvkm_event_init(&nv84_fifo_uevent_func, 1, 1, &priv->base.uevent);
-       if (ret)
-               return ret;
-
-       nv_subdev(priv)->unit = 0x00000100;
-       nv_subdev(priv)->intr = nv04_fifo_intr;
-       nv_engine(priv)->cclass = &nv84_fifo_cclass;
-       nv_engine(priv)->sclass = nv84_fifo_sclass;
-       priv->base.pause = nv04_fifo_pause;
-       priv->base.start = nv04_fifo_start;
-       return 0;
-}
-
-struct nouveau_oclass *
-nv84_fifo_oclass = &(struct nouveau_oclass) {
-       .handle = NV_ENGINE(FIFO, 0x84),
-       .ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nv84_fifo_ctor,
-               .dtor = nv50_fifo_dtor,
-               .init = nv50_fifo_init,
-               .fini = _nouveau_fifo_fini,
-       },
-};
diff --git a/drivers/gpu/drm/nouveau/core/engine/fifo/nvc0.c b/drivers/gpu/drm/nouveau/core/engine/fifo/nvc0.c
deleted file mode 100644 (file)
index 074d434..0000000
+++ /dev/null
@@ -1,975 +0,0 @@
-/*
- * Copyright 2012 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 <core/client.h>
-#include <core/handle.h>
-#include <core/namedb.h>
-#include <core/gpuobj.h>
-#include <core/engctx.h>
-#include <core/event.h>
-#include <nvif/unpack.h>
-#include <nvif/class.h>
-#include <core/enum.h>
-
-#include <subdev/timer.h>
-#include <subdev/bar.h>
-#include <subdev/fb.h>
-#include <subdev/vm.h>
-
-#include <engine/dmaobj.h>
-#include <engine/fifo.h>
-
-struct nvc0_fifo_priv {
-       struct nouveau_fifo base;
-
-       struct work_struct fault;
-       u64 mask;
-
-       struct {
-               struct nouveau_gpuobj *mem[2];
-               int active;
-               wait_queue_head_t wait;
-       } runlist;
-
-       struct {
-               struct nouveau_gpuobj *mem;
-               struct nouveau_vma bar;
-       } user;
-       int spoon_nr;
-};
-
-struct nvc0_fifo_base {
-       struct nouveau_fifo_base base;
-       struct nouveau_gpuobj *pgd;
-       struct nouveau_vm *vm;
-};
-
-struct nvc0_fifo_chan {
-       struct nouveau_fifo_chan base;
-       enum {
-               STOPPED,
-               RUNNING,
-               KILLED
-       } state;
-};
-
-/*******************************************************************************
- * FIFO channel objects
- ******************************************************************************/
-
-static void
-nvc0_fifo_runlist_update(struct nvc0_fifo_priv *priv)
-{
-       struct nouveau_bar *bar = nouveau_bar(priv);
-       struct nouveau_gpuobj *cur;
-       int i, p;
-
-       mutex_lock(&nv_subdev(priv)->mutex);
-       cur = priv->runlist.mem[priv->runlist.active];
-       priv->runlist.active = !priv->runlist.active;
-
-       for (i = 0, p = 0; i < 128; i++) {
-               struct nvc0_fifo_chan *chan = (void *)priv->base.channel[i];
-               if (chan && chan->state == RUNNING) {
-                       nv_wo32(cur, p + 0, i);
-                       nv_wo32(cur, p + 4, 0x00000004);
-                       p += 8;
-               }
-       }
-       bar->flush(bar);
-
-       nv_wr32(priv, 0x002270, cur->addr >> 12);
-       nv_wr32(priv, 0x002274, 0x01f00000 | (p >> 3));
-
-       if (wait_event_timeout(priv->runlist.wait,
-                              !(nv_rd32(priv, 0x00227c) & 0x00100000),
-                              msecs_to_jiffies(2000)) == 0)
-               nv_error(priv, "runlist update timeout\n");
-       mutex_unlock(&nv_subdev(priv)->mutex);
-}
-
-static int
-nvc0_fifo_context_attach(struct nouveau_object *parent,
-                        struct nouveau_object *object)
-{
-       struct nouveau_bar *bar = nouveau_bar(parent);
-       struct nvc0_fifo_base *base = (void *)parent->parent;
-       struct nouveau_engctx *ectx = (void *)object;
-       u32 addr;
-       int ret;
-
-       switch (nv_engidx(object->engine)) {
-       case NVDEV_ENGINE_SW   : return 0;
-       case NVDEV_ENGINE_GR   : addr = 0x0210; break;
-       case NVDEV_ENGINE_COPY0: addr = 0x0230; break;
-       case NVDEV_ENGINE_COPY1: addr = 0x0240; break;
-       case NVDEV_ENGINE_BSP  : addr = 0x0270; break;
-       case NVDEV_ENGINE_VP   : addr = 0x0250; break;
-       case NVDEV_ENGINE_PPP  : addr = 0x0260; break;
-       default:
-               return -EINVAL;
-       }
-
-       if (!ectx->vma.node) {
-               ret = nouveau_gpuobj_map_vm(nv_gpuobj(ectx), base->vm,
-                                           NV_MEM_ACCESS_RW, &ectx->vma);
-               if (ret)
-                       return ret;
-
-               nv_engctx(ectx)->addr = nv_gpuobj(base)->addr >> 12;
-       }
-
-       nv_wo32(base, addr + 0x00, lower_32_bits(ectx->vma.offset) | 4);
-       nv_wo32(base, addr + 0x04, upper_32_bits(ectx->vma.offset));
-       bar->flush(bar);
-       return 0;
-}
-
-static int
-nvc0_fifo_context_detach(struct nouveau_object *parent, bool suspend,
-                        struct nouveau_object *object)
-{
-       struct nouveau_bar *bar = nouveau_bar(parent);
-       struct nvc0_fifo_priv *priv = (void *)parent->engine;
-       struct nvc0_fifo_base *base = (void *)parent->parent;
-       struct nvc0_fifo_chan *chan = (void *)parent;
-       u32 addr;
-
-       switch (nv_engidx(object->engine)) {
-       case NVDEV_ENGINE_SW   : return 0;
-       case NVDEV_ENGINE_GR   : addr = 0x0210; break;
-       case NVDEV_ENGINE_COPY0: addr = 0x0230; break;
-       case NVDEV_ENGINE_COPY1: addr = 0x0240; break;
-       case NVDEV_ENGINE_BSP  : addr = 0x0270; break;
-       case NVDEV_ENGINE_VP   : addr = 0x0250; break;
-       case NVDEV_ENGINE_PPP  : addr = 0x0260; break;
-       default:
-               return -EINVAL;
-       }
-
-       nv_wr32(priv, 0x002634, chan->base.chid);
-       if (!nv_wait(priv, 0x002634, 0xffffffff, chan->base.chid)) {
-               nv_error(priv, "channel %d [%s] kick timeout\n",
-                        chan->base.chid, nouveau_client_name(chan));
-               if (suspend)
-                       return -EBUSY;
-       }
-
-       nv_wo32(base, addr + 0x00, 0x00000000);
-       nv_wo32(base, addr + 0x04, 0x00000000);
-       bar->flush(bar);
-       return 0;
-}
-
-static int
-nvc0_fifo_chan_ctor(struct nouveau_object *parent,
-                   struct nouveau_object *engine,
-                   struct nouveau_oclass *oclass, void *data, u32 size,
-                   struct nouveau_object **pobject)
-{
-       union {
-               struct nv50_channel_gpfifo_v0 v0;
-       } *args = data;
-       struct nouveau_bar *bar = nouveau_bar(parent);
-       struct nvc0_fifo_priv *priv = (void *)engine;
-       struct nvc0_fifo_base *base = (void *)parent;
-       struct nvc0_fifo_chan *chan;
-       u64 usermem, ioffset, ilength;
-       int ret, i;
-
-       nv_ioctl(parent, "create channel gpfifo size %d\n", size);
-       if (nvif_unpack(args->v0, 0, 0, false)) {
-               nv_ioctl(parent, "create channel gpfifo vers %d pushbuf %08x "
-                                "ioffset %016llx ilength %08x\n",
-                        args->v0.version, args->v0.pushbuf, args->v0.ioffset,
-                        args->v0.ilength);
-       } else
-               return ret;
-
-       ret = nouveau_fifo_channel_create(parent, engine, oclass, 1,
-                                         priv->user.bar.offset, 0x1000,
-                                         args->v0.pushbuf,
-                                         (1ULL << NVDEV_ENGINE_SW) |
-                                         (1ULL << NVDEV_ENGINE_GR) |
-                                         (1ULL << NVDEV_ENGINE_COPY0) |
-                                         (1ULL << NVDEV_ENGINE_COPY1) |
-                                         (1ULL << NVDEV_ENGINE_BSP) |
-                                         (1ULL << NVDEV_ENGINE_VP) |
-                                         (1ULL << NVDEV_ENGINE_PPP), &chan);
-       *pobject = nv_object(chan);
-       if (ret)
-               return ret;
-
-       args->v0.chid = chan->base.chid;
-
-       nv_parent(chan)->context_attach = nvc0_fifo_context_attach;
-       nv_parent(chan)->context_detach = nvc0_fifo_context_detach;
-
-       usermem = chan->base.chid * 0x1000;
-       ioffset = args->v0.ioffset;
-       ilength = order_base_2(args->v0.ilength / 8);
-
-       for (i = 0; i < 0x1000; i += 4)
-               nv_wo32(priv->user.mem, usermem + i, 0x00000000);
-
-       nv_wo32(base, 0x08, lower_32_bits(priv->user.mem->addr + usermem));
-       nv_wo32(base, 0x0c, upper_32_bits(priv->user.mem->addr + usermem));
-       nv_wo32(base, 0x10, 0x0000face);
-       nv_wo32(base, 0x30, 0xfffff902);
-       nv_wo32(base, 0x48, lower_32_bits(ioffset));
-       nv_wo32(base, 0x4c, upper_32_bits(ioffset) | (ilength << 16));
-       nv_wo32(base, 0x54, 0x00000002);
-       nv_wo32(base, 0x84, 0x20400000);
-       nv_wo32(base, 0x94, 0x30000001);
-       nv_wo32(base, 0x9c, 0x00000100);
-       nv_wo32(base, 0xa4, 0x1f1f1f1f);
-       nv_wo32(base, 0xa8, 0x1f1f1f1f);
-       nv_wo32(base, 0xac, 0x0000001f);
-       nv_wo32(base, 0xb8, 0xf8000000);
-       nv_wo32(base, 0xf8, 0x10003080); /* 0x002310 */
-       nv_wo32(base, 0xfc, 0x10000010); /* 0x002350 */
-       bar->flush(bar);
-       return 0;
-}
-
-static int
-nvc0_fifo_chan_init(struct nouveau_object *object)
-{
-       struct nouveau_gpuobj *base = nv_gpuobj(object->parent);
-       struct nvc0_fifo_priv *priv = (void *)object->engine;
-       struct nvc0_fifo_chan *chan = (void *)object;
-       u32 chid = chan->base.chid;
-       int ret;
-
-       ret = nouveau_fifo_channel_init(&chan->base);
-       if (ret)
-               return ret;
-
-       nv_wr32(priv, 0x003000 + (chid * 8), 0xc0000000 | base->addr >> 12);
-
-       if (chan->state == STOPPED && (chan->state = RUNNING) == RUNNING) {
-               nv_wr32(priv, 0x003004 + (chid * 8), 0x001f0001);
-               nvc0_fifo_runlist_update(priv);
-       }
-
-       return 0;
-}
-
-static void nvc0_fifo_intr_engine(struct nvc0_fifo_priv *priv);
-
-static int
-nvc0_fifo_chan_fini(struct nouveau_object *object, bool suspend)
-{
-       struct nvc0_fifo_priv *priv = (void *)object->engine;
-       struct nvc0_fifo_chan *chan = (void *)object;
-       u32 chid = chan->base.chid;
-
-       if (chan->state == RUNNING && (chan->state = STOPPED) == STOPPED) {
-               nv_mask(priv, 0x003004 + (chid * 8), 0x00000001, 0x00000000);
-               nvc0_fifo_runlist_update(priv);
-       }
-
-       nvc0_fifo_intr_engine(priv);
-
-       nv_wr32(priv, 0x003000 + (chid * 8), 0x00000000);
-       return nouveau_fifo_channel_fini(&chan->base, suspend);
-}
-
-static struct nouveau_ofuncs
-nvc0_fifo_ofuncs = {
-       .ctor = nvc0_fifo_chan_ctor,
-       .dtor = _nouveau_fifo_channel_dtor,
-       .init = nvc0_fifo_chan_init,
-       .fini = nvc0_fifo_chan_fini,
-       .map  = _nouveau_fifo_channel_map,
-       .rd32 = _nouveau_fifo_channel_rd32,
-       .wr32 = _nouveau_fifo_channel_wr32,
-       .ntfy = _nouveau_fifo_channel_ntfy
-};
-
-static struct nouveau_oclass
-nvc0_fifo_sclass[] = {
-       { FERMI_CHANNEL_GPFIFO, &nvc0_fifo_ofuncs },
-       {}
-};
-
-/*******************************************************************************
- * FIFO context - instmem heap and vm setup
- ******************************************************************************/
-
-static int
-nvc0_fifo_context_ctor(struct nouveau_object *parent,
-                      struct nouveau_object *engine,
-                      struct nouveau_oclass *oclass, void *data, u32 size,
-                      struct nouveau_object **pobject)
-{
-       struct nvc0_fifo_base *base;
-       int ret;
-
-       ret = nouveau_fifo_context_create(parent, engine, oclass, NULL, 0x1000,
-                                         0x1000, NVOBJ_FLAG_ZERO_ALLOC |
-                                         NVOBJ_FLAG_HEAP, &base);
-       *pobject = nv_object(base);
-       if (ret)
-               return ret;
-
-       ret = nouveau_gpuobj_new(nv_object(base), NULL, 0x10000, 0x1000, 0,
-                               &base->pgd);
-       if (ret)
-               return ret;
-
-       nv_wo32(base, 0x0200, lower_32_bits(base->pgd->addr));
-       nv_wo32(base, 0x0204, upper_32_bits(base->pgd->addr));
-       nv_wo32(base, 0x0208, 0xffffffff);
-       nv_wo32(base, 0x020c, 0x000000ff);
-
-       ret = nouveau_vm_ref(nouveau_client(parent)->vm, &base->vm, base->pgd);
-       if (ret)
-               return ret;
-
-       return 0;
-}
-
-static void
-nvc0_fifo_context_dtor(struct nouveau_object *object)
-{
-       struct nvc0_fifo_base *base = (void *)object;
-       nouveau_vm_ref(NULL, &base->vm, base->pgd);
-       nouveau_gpuobj_ref(NULL, &base->pgd);
-       nouveau_fifo_context_destroy(&base->base);
-}
-
-static struct nouveau_oclass
-nvc0_fifo_cclass = {
-       .handle = NV_ENGCTX(FIFO, 0xc0),
-       .ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nvc0_fifo_context_ctor,
-               .dtor = nvc0_fifo_context_dtor,
-               .init = _nouveau_fifo_context_init,
-               .fini = _nouveau_fifo_context_fini,
-               .rd32 = _nouveau_fifo_context_rd32,
-               .wr32 = _nouveau_fifo_context_wr32,
-       },
-};
-
-/*******************************************************************************
- * PFIFO engine
- ******************************************************************************/
-
-static inline int
-nvc0_fifo_engidx(struct nvc0_fifo_priv *priv, u32 engn)
-{
-       switch (engn) {
-       case NVDEV_ENGINE_GR   : engn = 0; break;
-       case NVDEV_ENGINE_BSP  : engn = 1; break;
-       case NVDEV_ENGINE_PPP  : engn = 2; break;
-       case NVDEV_ENGINE_VP   : engn = 3; break;
-       case NVDEV_ENGINE_COPY0: engn = 4; break;
-       case NVDEV_ENGINE_COPY1: engn = 5; break;
-       default:
-               return -1;
-       }
-
-       return engn;
-}
-
-static inline struct nouveau_engine *
-nvc0_fifo_engine(struct nvc0_fifo_priv *priv, u32 engn)
-{
-       switch (engn) {
-       case 0: engn = NVDEV_ENGINE_GR; break;
-       case 1: engn = NVDEV_ENGINE_BSP; break;
-       case 2: engn = NVDEV_ENGINE_PPP; break;
-       case 3: engn = NVDEV_ENGINE_VP; break;
-       case 4: engn = NVDEV_ENGINE_COPY0; break;
-       case 5: engn = NVDEV_ENGINE_COPY1; break;
-       default:
-               return NULL;
-       }
-
-       return nouveau_engine(priv, engn);
-}
-
-static void
-nvc0_fifo_recover_work(struct work_struct *work)
-{
-       struct nvc0_fifo_priv *priv = container_of(work, typeof(*priv), fault);
-       struct nouveau_object *engine;
-       unsigned long flags;
-       u32 engn, engm = 0;
-       u64 mask, todo;
-
-       spin_lock_irqsave(&priv->base.lock, flags);
-       mask = priv->mask;
-       priv->mask = 0ULL;
-       spin_unlock_irqrestore(&priv->base.lock, flags);
-
-       for (todo = mask; engn = __ffs64(todo), todo; todo &= ~(1 << engn))
-               engm |= 1 << nvc0_fifo_engidx(priv, engn);
-       nv_mask(priv, 0x002630, engm, engm);
-
-       for (todo = mask; engn = __ffs64(todo), todo; todo &= ~(1 << engn)) {
-               if ((engine = (void *)nouveau_engine(priv, engn))) {
-                       nv_ofuncs(engine)->fini(engine, false);
-                       WARN_ON(nv_ofuncs(engine)->init(engine));
-               }
-       }
-
-       nvc0_fifo_runlist_update(priv);
-       nv_wr32(priv, 0x00262c, engm);
-       nv_mask(priv, 0x002630, engm, 0x00000000);
-}
-
-static void
-nvc0_fifo_recover(struct nvc0_fifo_priv *priv, struct nouveau_engine *engine,
-                 struct nvc0_fifo_chan *chan)
-{
-       struct nouveau_object *engobj = nv_object(engine);
-       u32 chid = chan->base.chid;
-       unsigned long flags;
-
-       nv_error(priv, "%s engine fault on channel %d, recovering...\n",
-                      nv_subdev(engine)->name, chid);
-
-       nv_mask(priv, 0x003004 + (chid * 0x08), 0x00000001, 0x00000000);
-       chan->state = KILLED;
-
-       spin_lock_irqsave(&priv->base.lock, flags);
-       priv->mask |= 1ULL << nv_engidx(engobj);
-       spin_unlock_irqrestore(&priv->base.lock, flags);
-       schedule_work(&priv->fault);
-}
-
-static int
-nvc0_fifo_swmthd(struct nvc0_fifo_priv *priv, u32 chid, u32 mthd, u32 data)
-{
-       struct nvc0_fifo_chan *chan = NULL;
-       struct nouveau_handle *bind;
-       unsigned long flags;
-       int ret = -EINVAL;
-
-       spin_lock_irqsave(&priv->base.lock, flags);
-       if (likely(chid >= priv->base.min && chid <= priv->base.max))
-               chan = (void *)priv->base.channel[chid];
-       if (unlikely(!chan))
-               goto out;
-
-       bind = nouveau_namedb_get_class(nv_namedb(chan), 0x906e);
-       if (likely(bind)) {
-               if (!mthd || !nv_call(bind->object, mthd, data))
-                       ret = 0;
-               nouveau_namedb_put(bind);
-       }
-
-out:
-       spin_unlock_irqrestore(&priv->base.lock, flags);
-       return ret;
-}
-
-static const struct nouveau_enum
-nvc0_fifo_sched_reason[] = {
-       { 0x0a, "CTXSW_TIMEOUT" },
-       {}
-};
-
-static void
-nvc0_fifo_intr_sched_ctxsw(struct nvc0_fifo_priv *priv)
-{
-       struct nouveau_engine *engine;
-       struct nvc0_fifo_chan *chan;
-       u32 engn;
-
-       for (engn = 0; engn < 6; engn++) {
-               u32 stat = nv_rd32(priv, 0x002640 + (engn * 0x04));
-               u32 busy = (stat & 0x80000000);
-               u32 save = (stat & 0x00100000); /* maybe? */
-               u32 unk0 = (stat & 0x00040000);
-               u32 unk1 = (stat & 0x00001000);
-               u32 chid = (stat & 0x0000007f);
-               (void)save;
-
-               if (busy && unk0 && unk1) {
-                       if (!(chan = (void *)priv->base.channel[chid]))
-                               continue;
-                       if (!(engine = nvc0_fifo_engine(priv, engn)))
-                               continue;
-                       nvc0_fifo_recover(priv, engine, chan);
-               }
-       }
-}
-
-static void
-nvc0_fifo_intr_sched(struct nvc0_fifo_priv *priv)
-{
-       u32 intr = nv_rd32(priv, 0x00254c);
-       u32 code = intr & 0x000000ff;
-       const struct nouveau_enum *en;
-       char enunk[6] = "";
-
-       en = nouveau_enum_find(nvc0_fifo_sched_reason, code);
-       if (!en)
-               snprintf(enunk, sizeof(enunk), "UNK%02x", code);
-
-       nv_error(priv, "SCHED_ERROR [ %s ]\n", en ? en->name : enunk);
-
-       switch (code) {
-       case 0x0a:
-               nvc0_fifo_intr_sched_ctxsw(priv);
-               break;
-       default:
-               break;
-       }
-}
-
-static const struct nouveau_enum
-nvc0_fifo_fault_engine[] = {
-       { 0x00, "PGRAPH", NULL, NVDEV_ENGINE_GR },
-       { 0x03, "PEEPHOLE", NULL, NVDEV_ENGINE_IFB },
-       { 0x04, "BAR1", NULL, NVDEV_SUBDEV_BAR },
-       { 0x05, "BAR3", NULL, NVDEV_SUBDEV_INSTMEM },
-       { 0x07, "PFIFO", NULL, NVDEV_ENGINE_FIFO },
-       { 0x10, "PBSP", NULL, NVDEV_ENGINE_BSP },
-       { 0x11, "PPPP", NULL, NVDEV_ENGINE_PPP },
-       { 0x13, "PCOUNTER" },
-       { 0x14, "PVP", NULL, NVDEV_ENGINE_VP },
-       { 0x15, "PCOPY0", NULL, NVDEV_ENGINE_COPY0 },
-       { 0x16, "PCOPY1", NULL, NVDEV_ENGINE_COPY1 },
-       { 0x17, "PDAEMON" },
-       {}
-};
-
-static const struct nouveau_enum
-nvc0_fifo_fault_reason[] = {
-       { 0x00, "PT_NOT_PRESENT" },
-       { 0x01, "PT_TOO_SHORT" },
-       { 0x02, "PAGE_NOT_PRESENT" },
-       { 0x03, "VM_LIMIT_EXCEEDED" },
-       { 0x04, "NO_CHANNEL" },
-       { 0x05, "PAGE_SYSTEM_ONLY" },
-       { 0x06, "PAGE_READ_ONLY" },
-       { 0x0a, "COMPRESSED_SYSRAM" },
-       { 0x0c, "INVALID_STORAGE_TYPE" },
-       {}
-};
-
-static const struct nouveau_enum
-nvc0_fifo_fault_hubclient[] = {
-       { 0x01, "PCOPY0" },
-       { 0x02, "PCOPY1" },
-       { 0x04, "DISPATCH" },
-       { 0x05, "CTXCTL" },
-       { 0x06, "PFIFO" },
-       { 0x07, "BAR_READ" },
-       { 0x08, "BAR_WRITE" },
-       { 0x0b, "PVP" },
-       { 0x0c, "PPPP" },
-       { 0x0d, "PBSP" },
-       { 0x11, "PCOUNTER" },
-       { 0x12, "PDAEMON" },
-       { 0x14, "CCACHE" },
-       { 0x15, "CCACHE_POST" },
-       {}
-};
-
-static const struct nouveau_enum
-nvc0_fifo_fault_gpcclient[] = {
-       { 0x01, "TEX" },
-       { 0x0c, "ESETUP" },
-       { 0x0e, "CTXCTL" },
-       { 0x0f, "PROP" },
-       {}
-};
-
-static void
-nvc0_fifo_intr_fault(struct nvc0_fifo_priv *priv, int unit)
-{
-       u32 inst = nv_rd32(priv, 0x002800 + (unit * 0x10));
-       u32 valo = nv_rd32(priv, 0x002804 + (unit * 0x10));
-       u32 vahi = nv_rd32(priv, 0x002808 + (unit * 0x10));
-       u32 stat = nv_rd32(priv, 0x00280c + (unit * 0x10));
-       u32 gpc    = (stat & 0x1f000000) >> 24;
-       u32 client = (stat & 0x00001f00) >> 8;
-       u32 write  = (stat & 0x00000080);
-       u32 hub    = (stat & 0x00000040);
-       u32 reason = (stat & 0x0000000f);
-       struct nouveau_object *engctx = NULL, *object;
-       struct nouveau_engine *engine = NULL;
-       const struct nouveau_enum *er, *eu, *ec;
-       char erunk[6] = "";
-       char euunk[6] = "";
-       char ecunk[6] = "";
-       char gpcid[3] = "";
-
-       er = nouveau_enum_find(nvc0_fifo_fault_reason, reason);
-       if (!er)
-               snprintf(erunk, sizeof(erunk), "UNK%02X", reason);
-
-       eu = nouveau_enum_find(nvc0_fifo_fault_engine, unit);
-       if (eu) {
-               switch (eu->data2) {
-               case NVDEV_SUBDEV_BAR:
-                       nv_mask(priv, 0x001704, 0x00000000, 0x00000000);
-                       break;
-               case NVDEV_SUBDEV_INSTMEM:
-                       nv_mask(priv, 0x001714, 0x00000000, 0x00000000);
-                       break;
-               case NVDEV_ENGINE_IFB:
-                       nv_mask(priv, 0x001718, 0x00000000, 0x00000000);
-                       break;
-               default:
-                       engine = nouveau_engine(priv, eu->data2);
-                       if (engine)
-                               engctx = nouveau_engctx_get(engine, inst);
-                       break;
-               }
-       } else {
-               snprintf(euunk, sizeof(euunk), "UNK%02x", unit);
-       }
-
-       if (hub) {
-               ec = nouveau_enum_find(nvc0_fifo_fault_hubclient, client);
-       } else {
-               ec = nouveau_enum_find(nvc0_fifo_fault_gpcclient, client);
-               snprintf(gpcid, sizeof(gpcid), "%d", gpc);
-       }
-
-       if (!ec)
-               snprintf(ecunk, sizeof(ecunk), "UNK%02x", client);
-
-       nv_error(priv, "%s fault at 0x%010llx [%s] from %s/%s%s%s%s on "
-                      "channel 0x%010llx [%s]\n", write ? "write" : "read",
-                (u64)vahi << 32 | valo, er ? er->name : erunk,
-                eu ? eu->name : euunk, hub ? "" : "GPC", gpcid, hub ? "" : "/",
-                ec ? ec->name : ecunk, (u64)inst << 12,
-                nouveau_client_name(engctx));
-
-       object = engctx;
-       while (object) {
-               switch (nv_mclass(object)) {
-               case FERMI_CHANNEL_GPFIFO:
-                       nvc0_fifo_recover(priv, engine, (void *)object);
-                       break;
-               }
-               object = object->parent;
-       }
-
-       nouveau_engctx_put(engctx);
-}
-
-static const struct nouveau_bitfield
-nvc0_fifo_pbdma_intr[] = {
-/*     { 0x00008000, "" }      seen with null ib push */
-       { 0x00200000, "ILLEGAL_MTHD" },
-       { 0x00800000, "EMPTY_SUBC" },
-       {}
-};
-
-static void
-nvc0_fifo_intr_pbdma(struct nvc0_fifo_priv *priv, int unit)
-{
-       u32 stat = nv_rd32(priv, 0x040108 + (unit * 0x2000));
-       u32 addr = nv_rd32(priv, 0x0400c0 + (unit * 0x2000));
-       u32 data = nv_rd32(priv, 0x0400c4 + (unit * 0x2000));
-       u32 chid = nv_rd32(priv, 0x040120 + (unit * 0x2000)) & 0x7f;
-       u32 subc = (addr & 0x00070000) >> 16;
-       u32 mthd = (addr & 0x00003ffc);
-       u32 show = stat;
-
-       if (stat & 0x00800000) {
-               if (!nvc0_fifo_swmthd(priv, chid, mthd, data))
-                       show &= ~0x00800000;
-       }
-
-       if (show) {
-               nv_error(priv, "PBDMA%d:", unit);
-               nouveau_bitfield_print(nvc0_fifo_pbdma_intr, show);
-               pr_cont("\n");
-               nv_error(priv,
-                        "PBDMA%d: ch %d [%s] subc %d mthd 0x%04x data 0x%08x\n",
-                        unit, chid,
-                        nouveau_client_name_for_fifo_chid(&priv->base, chid),
-                        subc, mthd, data);
-       }
-
-       nv_wr32(priv, 0x0400c0 + (unit * 0x2000), 0x80600008);
-       nv_wr32(priv, 0x040108 + (unit * 0x2000), stat);
-}
-
-static void
-nvc0_fifo_intr_runlist(struct nvc0_fifo_priv *priv)
-{
-       u32 intr = nv_rd32(priv, 0x002a00);
-
-       if (intr & 0x10000000) {
-               wake_up(&priv->runlist.wait);
-               nv_wr32(priv, 0x002a00, 0x10000000);
-               intr &= ~0x10000000;
-       }
-
-       if (intr) {
-               nv_error(priv, "RUNLIST 0x%08x\n", intr);
-               nv_wr32(priv, 0x002a00, intr);
-       }
-}
-
-static void
-nvc0_fifo_intr_engine_unit(struct nvc0_fifo_priv *priv, int engn)
-{
-       u32 intr = nv_rd32(priv, 0x0025a8 + (engn * 0x04));
-       u32 inte = nv_rd32(priv, 0x002628);
-       u32 unkn;
-
-       nv_wr32(priv, 0x0025a8 + (engn * 0x04), intr);
-
-       for (unkn = 0; unkn < 8; unkn++) {
-               u32 ints = (intr >> (unkn * 0x04)) & inte;
-               if (ints & 0x1) {
-                       nouveau_fifo_uevent(&priv->base);
-                       ints &= ~1;
-               }
-               if (ints) {
-                       nv_error(priv, "ENGINE %d %d %01x", engn, unkn, ints);
-                       nv_mask(priv, 0x002628, ints, 0);
-               }
-       }
-}
-
-static void
-nvc0_fifo_intr_engine(struct nvc0_fifo_priv *priv)
-{
-       u32 mask = nv_rd32(priv, 0x0025a4);
-       while (mask) {
-               u32 unit = __ffs(mask);
-               nvc0_fifo_intr_engine_unit(priv, unit);
-               mask &= ~(1 << unit);
-       }
-}
-
-static void
-nvc0_fifo_intr(struct nouveau_subdev *subdev)
-{
-       struct nvc0_fifo_priv *priv = (void *)subdev;
-       u32 mask = nv_rd32(priv, 0x002140);
-       u32 stat = nv_rd32(priv, 0x002100) & mask;
-
-       if (stat & 0x00000001) {
-               u32 intr = nv_rd32(priv, 0x00252c);
-               nv_warn(priv, "INTR 0x00000001: 0x%08x\n", intr);
-               nv_wr32(priv, 0x002100, 0x00000001);
-               stat &= ~0x00000001;
-       }
-
-       if (stat & 0x00000100) {
-               nvc0_fifo_intr_sched(priv);
-               nv_wr32(priv, 0x002100, 0x00000100);
-               stat &= ~0x00000100;
-       }
-
-       if (stat & 0x00010000) {
-               u32 intr = nv_rd32(priv, 0x00256c);
-               nv_warn(priv, "INTR 0x00010000: 0x%08x\n", intr);
-               nv_wr32(priv, 0x002100, 0x00010000);
-               stat &= ~0x00010000;
-       }
-
-       if (stat & 0x01000000) {
-               u32 intr = nv_rd32(priv, 0x00258c);
-               nv_warn(priv, "INTR 0x01000000: 0x%08x\n", intr);
-               nv_wr32(priv, 0x002100, 0x01000000);
-               stat &= ~0x01000000;
-       }
-
-       if (stat & 0x10000000) {
-               u32 mask = nv_rd32(priv, 0x00259c);
-               while (mask) {
-                       u32 unit = __ffs(mask);
-                       nvc0_fifo_intr_fault(priv, unit);
-                       nv_wr32(priv, 0x00259c, (1 << unit));
-                       mask &= ~(1 << unit);
-               }
-               stat &= ~0x10000000;
-       }
-
-       if (stat & 0x20000000) {
-               u32 mask = nv_rd32(priv, 0x0025a0);
-               while (mask) {
-                       u32 unit = __ffs(mask);
-                       nvc0_fifo_intr_pbdma(priv, unit);
-                       nv_wr32(priv, 0x0025a0, (1 << unit));
-                       mask &= ~(1 << unit);
-               }
-               stat &= ~0x20000000;
-       }
-
-       if (stat & 0x40000000) {
-               nvc0_fifo_intr_runlist(priv);
-               stat &= ~0x40000000;
-       }
-
-       if (stat & 0x80000000) {
-               nvc0_fifo_intr_engine(priv);
-               stat &= ~0x80000000;
-       }
-
-       if (stat) {
-               nv_error(priv, "INTR 0x%08x\n", stat);
-               nv_mask(priv, 0x002140, stat, 0x00000000);
-               nv_wr32(priv, 0x002100, stat);
-       }
-}
-
-static void
-nvc0_fifo_uevent_init(struct nvkm_event *event, int type, int index)
-{
-       struct nouveau_fifo *fifo = container_of(event, typeof(*fifo), uevent);
-       nv_mask(fifo, 0x002140, 0x80000000, 0x80000000);
-}
-
-static void
-nvc0_fifo_uevent_fini(struct nvkm_event *event, int type, int index)
-{
-       struct nouveau_fifo *fifo = container_of(event, typeof(*fifo), uevent);
-       nv_mask(fifo, 0x002140, 0x80000000, 0x00000000);
-}
-
-static const struct nvkm_event_func
-nvc0_fifo_uevent_func = {
-       .ctor = nouveau_fifo_uevent_ctor,
-       .init = nvc0_fifo_uevent_init,
-       .fini = nvc0_fifo_uevent_fini,
-};
-
-static int
-nvc0_fifo_ctor(struct nouveau_object *parent, struct nouveau_object *engine,
-              struct nouveau_oclass *oclass, void *data, u32 size,
-              struct nouveau_object **pobject)
-{
-       struct nvc0_fifo_priv *priv;
-       int ret;
-
-       ret = nouveau_fifo_create(parent, engine, oclass, 0, 127, &priv);
-       *pobject = nv_object(priv);
-       if (ret)
-               return ret;
-
-       INIT_WORK(&priv->fault, nvc0_fifo_recover_work);
-
-       ret = nouveau_gpuobj_new(nv_object(priv), NULL, 0x1000, 0x1000, 0,
-                               &priv->runlist.mem[0]);
-       if (ret)
-               return ret;
-
-       ret = nouveau_gpuobj_new(nv_object(priv), NULL, 0x1000, 0x1000, 0,
-                               &priv->runlist.mem[1]);
-       if (ret)
-               return ret;
-
-       init_waitqueue_head(&priv->runlist.wait);
-
-       ret = nouveau_gpuobj_new(nv_object(priv), NULL, 128 * 0x1000, 0x1000, 0,
-                               &priv->user.mem);
-       if (ret)
-               return ret;
-
-       ret = nouveau_gpuobj_map(priv->user.mem, NV_MEM_ACCESS_RW,
-                               &priv->user.bar);
-       if (ret)
-               return ret;
-
-       ret = nvkm_event_init(&nvc0_fifo_uevent_func, 1, 1, &priv->base.uevent);
-       if (ret)
-               return ret;
-
-       nv_subdev(priv)->unit = 0x00000100;
-       nv_subdev(priv)->intr = nvc0_fifo_intr;
-       nv_engine(priv)->cclass = &nvc0_fifo_cclass;
-       nv_engine(priv)->sclass = nvc0_fifo_sclass;
-       return 0;
-}
-
-static void
-nvc0_fifo_dtor(struct nouveau_object *object)
-{
-       struct nvc0_fifo_priv *priv = (void *)object;
-
-       nouveau_gpuobj_unmap(&priv->user.bar);
-       nouveau_gpuobj_ref(NULL, &priv->user.mem);
-       nouveau_gpuobj_ref(NULL, &priv->runlist.mem[0]);
-       nouveau_gpuobj_ref(NULL, &priv->runlist.mem[1]);
-
-       nouveau_fifo_destroy(&priv->base);
-}
-
-static int
-nvc0_fifo_init(struct nouveau_object *object)
-{
-       struct nvc0_fifo_priv *priv = (void *)object;
-       int ret, i;
-
-       ret = nouveau_fifo_init(&priv->base);
-       if (ret)
-               return ret;
-
-       nv_wr32(priv, 0x000204, 0xffffffff);
-       nv_wr32(priv, 0x002204, 0xffffffff);
-
-       priv->spoon_nr = hweight32(nv_rd32(priv, 0x002204));
-       nv_debug(priv, "%d PBDMA unit(s)\n", priv->spoon_nr);
-
-       /* assign engines to PBDMAs */
-       if (priv->spoon_nr >= 3) {
-               nv_wr32(priv, 0x002208, ~(1 << 0)); /* PGRAPH */
-               nv_wr32(priv, 0x00220c, ~(1 << 1)); /* PVP */
-               nv_wr32(priv, 0x002210, ~(1 << 1)); /* PPP */
-               nv_wr32(priv, 0x002214, ~(1 << 1)); /* PBSP */
-               nv_wr32(priv, 0x002218, ~(1 << 2)); /* PCE0 */
-               nv_wr32(priv, 0x00221c, ~(1 << 1)); /* PCE1 */
-       }
-
-       /* PBDMA[n] */
-       for (i = 0; i < priv->spoon_nr; i++) {
-               nv_mask(priv, 0x04013c + (i * 0x2000), 0x10000100, 0x00000000);
-               nv_wr32(priv, 0x040108 + (i * 0x2000), 0xffffffff); /* INTR */
-               nv_wr32(priv, 0x04010c + (i * 0x2000), 0xfffffeff); /* INTREN */
-       }
-
-       nv_mask(priv, 0x002200, 0x00000001, 0x00000001);
-       nv_wr32(priv, 0x002254, 0x10000000 | priv->user.bar.offset >> 12);
-
-       nv_wr32(priv, 0x002100, 0xffffffff);
-       nv_wr32(priv, 0x002140, 0x7fffffff);
-       nv_wr32(priv, 0x002628, 0x00000001); /* ENGINE_INTR_EN */
-       return 0;
-}
-
-struct nouveau_oclass *
-nvc0_fifo_oclass = &(struct nouveau_oclass) {
-       .handle = NV_ENGINE(FIFO, 0xc0),
-       .ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nvc0_fifo_ctor,
-               .dtor = nvc0_fifo_dtor,
-               .init = nvc0_fifo_init,
-               .fini = _nouveau_fifo_fini,
-       },
-};
diff --git a/drivers/gpu/drm/nouveau/core/engine/fifo/nve0.c b/drivers/gpu/drm/nouveau/core/engine/fifo/nve0.c
deleted file mode 100644 (file)
index 6a8db7c..0000000
+++ /dev/null
@@ -1,1147 +0,0 @@
-/*
- * Copyright 2012 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 <core/client.h>
-#include <core/handle.h>
-#include <core/namedb.h>
-#include <core/gpuobj.h>
-#include <core/engctx.h>
-#include <core/event.h>
-#include <nvif/unpack.h>
-#include <nvif/class.h>
-#include <core/enum.h>
-
-#include <subdev/timer.h>
-#include <subdev/bar.h>
-#include <subdev/fb.h>
-#include <subdev/vm.h>
-
-#include <engine/dmaobj.h>
-
-#include "nve0.h"
-
-#define _(a,b) { (a), ((1ULL << (a)) | (b)) }
-static const struct {
-       u64 subdev;
-       u64 mask;
-} fifo_engine[] = {
-       _(NVDEV_ENGINE_GR      , (1ULL << NVDEV_ENGINE_SW) |
-                                (1ULL << NVDEV_ENGINE_COPY2)),
-       _(NVDEV_ENGINE_VP      , 0),
-       _(NVDEV_ENGINE_PPP     , 0),
-       _(NVDEV_ENGINE_BSP     , 0),
-       _(NVDEV_ENGINE_COPY0   , 0),
-       _(NVDEV_ENGINE_COPY1   , 0),
-       _(NVDEV_ENGINE_VENC    , 0),
-};
-#undef _
-#define FIFO_ENGINE_NR ARRAY_SIZE(fifo_engine)
-
-struct nve0_fifo_engn {
-       struct nouveau_gpuobj *runlist[2];
-       int cur_runlist;
-       wait_queue_head_t wait;
-};
-
-struct nve0_fifo_priv {
-       struct nouveau_fifo base;
-
-       struct work_struct fault;
-       u64 mask;
-
-       struct nve0_fifo_engn engine[FIFO_ENGINE_NR];
-       struct {
-               struct nouveau_gpuobj *mem;
-               struct nouveau_vma bar;
-       } user;
-       int spoon_nr;
-};
-
-struct nve0_fifo_base {
-       struct nouveau_fifo_base base;
-       struct nouveau_gpuobj *pgd;
-       struct nouveau_vm *vm;
-};
-
-struct nve0_fifo_chan {
-       struct nouveau_fifo_chan base;
-       u32 engine;
-       enum {
-               STOPPED,
-               RUNNING,
-               KILLED
-       } state;
-};
-
-/*******************************************************************************
- * FIFO channel objects
- ******************************************************************************/
-
-static void
-nve0_fifo_runlist_update(struct nve0_fifo_priv *priv, u32 engine)
-{
-       struct nouveau_bar *bar = nouveau_bar(priv);
-       struct nve0_fifo_engn *engn = &priv->engine[engine];
-       struct nouveau_gpuobj *cur;
-       int i, p;
-
-       mutex_lock(&nv_subdev(priv)->mutex);
-       cur = engn->runlist[engn->cur_runlist];
-       engn->cur_runlist = !engn->cur_runlist;
-
-       for (i = 0, p = 0; i < priv->base.max; i++) {
-               struct nve0_fifo_chan *chan = (void *)priv->base.channel[i];
-               if (chan && chan->state == RUNNING && chan->engine == engine) {
-                       nv_wo32(cur, p + 0, i);
-                       nv_wo32(cur, p + 4, 0x00000000);
-                       p += 8;
-               }
-       }
-       bar->flush(bar);
-
-       nv_wr32(priv, 0x002270, cur->addr >> 12);
-       nv_wr32(priv, 0x002274, (engine << 20) | (p >> 3));
-
-       if (wait_event_timeout(engn->wait, !(nv_rd32(priv, 0x002284 +
-                              (engine * 0x08)) & 0x00100000),
-                               msecs_to_jiffies(2000)) == 0)
-               nv_error(priv, "runlist %d update timeout\n", engine);
-       mutex_unlock(&nv_subdev(priv)->mutex);
-}
-
-static int
-nve0_fifo_context_attach(struct nouveau_object *parent,
-                        struct nouveau_object *object)
-{
-       struct nouveau_bar *bar = nouveau_bar(parent);
-       struct nve0_fifo_base *base = (void *)parent->parent;
-       struct nouveau_engctx *ectx = (void *)object;
-       u32 addr;
-       int ret;
-
-       switch (nv_engidx(object->engine)) {
-       case NVDEV_ENGINE_SW   :
-               return 0;
-       case NVDEV_ENGINE_COPY0:
-       case NVDEV_ENGINE_COPY1:
-       case NVDEV_ENGINE_COPY2:
-               nv_engctx(ectx)->addr = nv_gpuobj(base)->addr >> 12;
-               return 0;
-       case NVDEV_ENGINE_GR   : addr = 0x0210; break;
-       case NVDEV_ENGINE_BSP  : addr = 0x0270; break;
-       case NVDEV_ENGINE_VP   : addr = 0x0250; break;
-       case NVDEV_ENGINE_PPP  : addr = 0x0260; break;
-       default:
-               return -EINVAL;
-       }
-
-       if (!ectx->vma.node) {
-               ret = nouveau_gpuobj_map_vm(nv_gpuobj(ectx), base->vm,
-                                           NV_MEM_ACCESS_RW, &ectx->vma);
-               if (ret)
-                       return ret;
-
-               nv_engctx(ectx)->addr = nv_gpuobj(base)->addr >> 12;
-       }
-
-       nv_wo32(base, addr + 0x00, lower_32_bits(ectx->vma.offset) | 4);
-       nv_wo32(base, addr + 0x04, upper_32_bits(ectx->vma.offset));
-       bar->flush(bar);
-       return 0;
-}
-
-static int
-nve0_fifo_context_detach(struct nouveau_object *parent, bool suspend,
-                        struct nouveau_object *object)
-{
-       struct nouveau_bar *bar = nouveau_bar(parent);
-       struct nve0_fifo_priv *priv = (void *)parent->engine;
-       struct nve0_fifo_base *base = (void *)parent->parent;
-       struct nve0_fifo_chan *chan = (void *)parent;
-       u32 addr;
-
-       switch (nv_engidx(object->engine)) {
-       case NVDEV_ENGINE_SW   : return 0;
-       case NVDEV_ENGINE_COPY0:
-       case NVDEV_ENGINE_COPY1:
-       case NVDEV_ENGINE_COPY2: addr = 0x0000; break;
-       case NVDEV_ENGINE_GR   : addr = 0x0210; break;
-       case NVDEV_ENGINE_BSP  : addr = 0x0270; break;
-       case NVDEV_ENGINE_VP   : addr = 0x0250; break;
-       case NVDEV_ENGINE_PPP  : addr = 0x0260; break;
-       default:
-               return -EINVAL;
-       }
-
-       nv_wr32(priv, 0x002634, chan->base.chid);
-       if (!nv_wait(priv, 0x002634, 0xffffffff, chan->base.chid)) {
-               nv_error(priv, "channel %d [%s] kick timeout\n",
-                        chan->base.chid, nouveau_client_name(chan));
-               if (suspend)
-                       return -EBUSY;
-       }
-
-       if (addr) {
-               nv_wo32(base, addr + 0x00, 0x00000000);
-               nv_wo32(base, addr + 0x04, 0x00000000);
-               bar->flush(bar);
-       }
-
-       return 0;
-}
-
-static int
-nve0_fifo_chan_ctor(struct nouveau_object *parent,
-                   struct nouveau_object *engine,
-                   struct nouveau_oclass *oclass, void *data, u32 size,
-                   struct nouveau_object **pobject)
-{
-       union {
-               struct kepler_channel_gpfifo_a_v0 v0;
-       } *args = data;
-       struct nouveau_bar *bar = nouveau_bar(parent);
-       struct nve0_fifo_priv *priv = (void *)engine;
-       struct nve0_fifo_base *base = (void *)parent;
-       struct nve0_fifo_chan *chan;
-       u64 usermem, ioffset, ilength;
-       int ret, i;
-
-       nv_ioctl(parent, "create channel gpfifo size %d\n", size);
-       if (nvif_unpack(args->v0, 0, 0, false)) {
-               nv_ioctl(parent, "create channel gpfifo vers %d pushbuf %08x "
-                                "ioffset %016llx ilength %08x engine %08x\n",
-                        args->v0.version, args->v0.pushbuf, args->v0.ioffset,
-                        args->v0.ilength, args->v0.engine);
-       } else
-               return ret;
-
-       for (i = 0; i < FIFO_ENGINE_NR; i++) {
-               if (args->v0.engine & (1 << i)) {
-                       if (nouveau_engine(parent, fifo_engine[i].subdev)) {
-                               args->v0.engine = (1 << i);
-                               break;
-                       }
-               }
-       }
-
-       if (i == FIFO_ENGINE_NR) {
-               nv_error(priv, "unsupported engines 0x%08x\n", args->v0.engine);
-               return -ENODEV;
-       }
-
-       ret = nouveau_fifo_channel_create(parent, engine, oclass, 1,
-                                         priv->user.bar.offset, 0x200,
-                                         args->v0.pushbuf,
-                                         fifo_engine[i].mask, &chan);
-       *pobject = nv_object(chan);
-       if (ret)
-               return ret;
-
-       args->v0.chid = chan->base.chid;
-
-       nv_parent(chan)->context_attach = nve0_fifo_context_attach;
-       nv_parent(chan)->context_detach = nve0_fifo_context_detach;
-       chan->engine = i;
-
-       usermem = chan->base.chid * 0x200;
-       ioffset = args->v0.ioffset;
-       ilength = order_base_2(args->v0.ilength / 8);
-
-       for (i = 0; i < 0x200; i += 4)
-               nv_wo32(priv->user.mem, usermem + i, 0x00000000);
-
-       nv_wo32(base, 0x08, lower_32_bits(priv->user.mem->addr + usermem));
-       nv_wo32(base, 0x0c, upper_32_bits(priv->user.mem->addr + usermem));
-       nv_wo32(base, 0x10, 0x0000face);
-       nv_wo32(base, 0x30, 0xfffff902);
-       nv_wo32(base, 0x48, lower_32_bits(ioffset));
-       nv_wo32(base, 0x4c, upper_32_bits(ioffset) | (ilength << 16));
-       nv_wo32(base, 0x84, 0x20400000);
-       nv_wo32(base, 0x94, 0x30000001);
-       nv_wo32(base, 0x9c, 0x00000100);
-       nv_wo32(base, 0xac, 0x0000001f);
-       nv_wo32(base, 0xe8, chan->base.chid);
-       nv_wo32(base, 0xb8, 0xf8000000);
-       nv_wo32(base, 0xf8, 0x10003080); /* 0x002310 */
-       nv_wo32(base, 0xfc, 0x10000010); /* 0x002350 */
-       bar->flush(bar);
-       return 0;
-}
-
-static int
-nve0_fifo_chan_init(struct nouveau_object *object)
-{
-       struct nouveau_gpuobj *base = nv_gpuobj(object->parent);
-       struct nve0_fifo_priv *priv = (void *)object->engine;
-       struct nve0_fifo_chan *chan = (void *)object;
-       u32 chid = chan->base.chid;
-       int ret;
-
-       ret = nouveau_fifo_channel_init(&chan->base);
-       if (ret)
-               return ret;
-
-       nv_mask(priv, 0x800004 + (chid * 8), 0x000f0000, chan->engine << 16);
-       nv_wr32(priv, 0x800000 + (chid * 8), 0x80000000 | base->addr >> 12);
-
-       if (chan->state == STOPPED && (chan->state = RUNNING) == RUNNING) {
-               nv_mask(priv, 0x800004 + (chid * 8), 0x00000400, 0x00000400);
-               nve0_fifo_runlist_update(priv, chan->engine);
-               nv_mask(priv, 0x800004 + (chid * 8), 0x00000400, 0x00000400);
-       }
-
-       return 0;
-}
-
-static int
-nve0_fifo_chan_fini(struct nouveau_object *object, bool suspend)
-{
-       struct nve0_fifo_priv *priv = (void *)object->engine;
-       struct nve0_fifo_chan *chan = (void *)object;
-       u32 chid = chan->base.chid;
-
-       if (chan->state == RUNNING && (chan->state = STOPPED) == STOPPED) {
-               nv_mask(priv, 0x800004 + (chid * 8), 0x00000800, 0x00000800);
-               nve0_fifo_runlist_update(priv, chan->engine);
-       }
-
-       nv_wr32(priv, 0x800000 + (chid * 8), 0x00000000);
-       return nouveau_fifo_channel_fini(&chan->base, suspend);
-}
-
-static struct nouveau_ofuncs
-nve0_fifo_ofuncs = {
-       .ctor = nve0_fifo_chan_ctor,
-       .dtor = _nouveau_fifo_channel_dtor,
-       .init = nve0_fifo_chan_init,
-       .fini = nve0_fifo_chan_fini,
-       .map  = _nouveau_fifo_channel_map,
-       .rd32 = _nouveau_fifo_channel_rd32,
-       .wr32 = _nouveau_fifo_channel_wr32,
-       .ntfy = _nouveau_fifo_channel_ntfy
-};
-
-static struct nouveau_oclass
-nve0_fifo_sclass[] = {
-       { KEPLER_CHANNEL_GPFIFO_A, &nve0_fifo_ofuncs },
-       {}
-};
-
-/*******************************************************************************
- * FIFO context - instmem heap and vm setup
- ******************************************************************************/
-
-static int
-nve0_fifo_context_ctor(struct nouveau_object *parent,
-                   struct nouveau_object *engine,
-                   struct nouveau_oclass *oclass, void *data, u32 size,
-                   struct nouveau_object **pobject)
-{
-       struct nve0_fifo_base *base;
-       int ret;
-
-       ret = nouveau_fifo_context_create(parent, engine, oclass, NULL, 0x1000,
-                                         0x1000, NVOBJ_FLAG_ZERO_ALLOC, &base);
-       *pobject = nv_object(base);
-       if (ret)
-               return ret;
-
-       ret = nouveau_gpuobj_new(nv_object(base), NULL, 0x10000, 0x1000, 0,
-                               &base->pgd);
-       if (ret)
-               return ret;
-
-       nv_wo32(base, 0x0200, lower_32_bits(base->pgd->addr));
-       nv_wo32(base, 0x0204, upper_32_bits(base->pgd->addr));
-       nv_wo32(base, 0x0208, 0xffffffff);
-       nv_wo32(base, 0x020c, 0x000000ff);
-
-       ret = nouveau_vm_ref(nouveau_client(parent)->vm, &base->vm, base->pgd);
-       if (ret)
-               return ret;
-
-       return 0;
-}
-
-static void
-nve0_fifo_context_dtor(struct nouveau_object *object)
-{
-       struct nve0_fifo_base *base = (void *)object;
-       nouveau_vm_ref(NULL, &base->vm, base->pgd);
-       nouveau_gpuobj_ref(NULL, &base->pgd);
-       nouveau_fifo_context_destroy(&base->base);
-}
-
-static struct nouveau_oclass
-nve0_fifo_cclass = {
-       .handle = NV_ENGCTX(FIFO, 0xe0),
-       .ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nve0_fifo_context_ctor,
-               .dtor = nve0_fifo_context_dtor,
-               .init = _nouveau_fifo_context_init,
-               .fini = _nouveau_fifo_context_fini,
-               .rd32 = _nouveau_fifo_context_rd32,
-               .wr32 = _nouveau_fifo_context_wr32,
-       },
-};
-
-/*******************************************************************************
- * PFIFO engine
- ******************************************************************************/
-
-static inline int
-nve0_fifo_engidx(struct nve0_fifo_priv *priv, u32 engn)
-{
-       switch (engn) {
-       case NVDEV_ENGINE_GR   :
-       case NVDEV_ENGINE_COPY2: engn = 0; break;
-       case NVDEV_ENGINE_BSP  : engn = 1; break;
-       case NVDEV_ENGINE_PPP  : engn = 2; break;
-       case NVDEV_ENGINE_VP   : engn = 3; break;
-       case NVDEV_ENGINE_COPY0: engn = 4; break;
-       case NVDEV_ENGINE_COPY1: engn = 5; break;
-       case NVDEV_ENGINE_VENC : engn = 6; break;
-       default:
-               return -1;
-       }
-
-       return engn;
-}
-
-static inline struct nouveau_engine *
-nve0_fifo_engine(struct nve0_fifo_priv *priv, u32 engn)
-{
-       if (engn >= ARRAY_SIZE(fifo_engine))
-               return NULL;
-       return nouveau_engine(priv, fifo_engine[engn].subdev);
-}
-
-static void
-nve0_fifo_recover_work(struct work_struct *work)
-{
-       struct nve0_fifo_priv *priv = container_of(work, typeof(*priv), fault);
-       struct nouveau_object *engine;
-       unsigned long flags;
-       u32 engn, engm = 0;
-       u64 mask, todo;
-
-       spin_lock_irqsave(&priv->base.lock, flags);
-       mask = priv->mask;
-       priv->mask = 0ULL;
-       spin_unlock_irqrestore(&priv->base.lock, flags);
-
-       for (todo = mask; engn = __ffs64(todo), todo; todo &= ~(1 << engn))
-               engm |= 1 << nve0_fifo_engidx(priv, engn);
-       nv_mask(priv, 0x002630, engm, engm);
-
-       for (todo = mask; engn = __ffs64(todo), todo; todo &= ~(1 << engn)) {
-               if ((engine = (void *)nouveau_engine(priv, engn))) {
-                       nv_ofuncs(engine)->fini(engine, false);
-                       WARN_ON(nv_ofuncs(engine)->init(engine));
-               }
-               nve0_fifo_runlist_update(priv, nve0_fifo_engidx(priv, engn));
-       }
-
-       nv_wr32(priv, 0x00262c, engm);
-       nv_mask(priv, 0x002630, engm, 0x00000000);
-}
-
-static void
-nve0_fifo_recover(struct nve0_fifo_priv *priv, struct nouveau_engine *engine,
-                 struct nve0_fifo_chan *chan)
-{
-       struct nouveau_object *engobj = nv_object(engine);
-       u32 chid = chan->base.chid;
-       unsigned long flags;
-
-       nv_error(priv, "%s engine fault on channel %d, recovering...\n",
-                      nv_subdev(engine)->name, chid);
-
-       nv_mask(priv, 0x800004 + (chid * 0x08), 0x00000800, 0x00000800);
-       chan->state = KILLED;
-
-       spin_lock_irqsave(&priv->base.lock, flags);
-       priv->mask |= 1ULL << nv_engidx(engobj);
-       spin_unlock_irqrestore(&priv->base.lock, flags);
-       schedule_work(&priv->fault);
-}
-
-static int
-nve0_fifo_swmthd(struct nve0_fifo_priv *priv, u32 chid, u32 mthd, u32 data)
-{
-       struct nve0_fifo_chan *chan = NULL;
-       struct nouveau_handle *bind;
-       unsigned long flags;
-       int ret = -EINVAL;
-
-       spin_lock_irqsave(&priv->base.lock, flags);
-       if (likely(chid >= priv->base.min && chid <= priv->base.max))
-               chan = (void *)priv->base.channel[chid];
-       if (unlikely(!chan))
-               goto out;
-
-       bind = nouveau_namedb_get_class(nv_namedb(chan), 0x906e);
-       if (likely(bind)) {
-               if (!mthd || !nv_call(bind->object, mthd, data))
-                       ret = 0;
-               nouveau_namedb_put(bind);
-       }
-
-out:
-       spin_unlock_irqrestore(&priv->base.lock, flags);
-       return ret;
-}
-
-static const struct nouveau_enum
-nve0_fifo_bind_reason[] = {
-       { 0x01, "BIND_NOT_UNBOUND" },
-       { 0x02, "SNOOP_WITHOUT_BAR1" },
-       { 0x03, "UNBIND_WHILE_RUNNING" },
-       { 0x05, "INVALID_RUNLIST" },
-       { 0x06, "INVALID_CTX_TGT" },
-       { 0x0b, "UNBIND_WHILE_PARKED" },
-       {}
-};
-
-static void
-nve0_fifo_intr_bind(struct nve0_fifo_priv *priv)
-{
-       u32 intr = nv_rd32(priv, 0x00252c);
-       u32 code = intr & 0x000000ff;
-       const struct nouveau_enum *en;
-       char enunk[6] = "";
-
-       en = nouveau_enum_find(nve0_fifo_bind_reason, code);
-       if (!en)
-               snprintf(enunk, sizeof(enunk), "UNK%02x", code);
-
-       nv_error(priv, "BIND_ERROR [ %s ]\n", en ? en->name : enunk);
-}
-
-static const struct nouveau_enum
-nve0_fifo_sched_reason[] = {
-       { 0x0a, "CTXSW_TIMEOUT" },
-       {}
-};
-
-static void
-nve0_fifo_intr_sched_ctxsw(struct nve0_fifo_priv *priv)
-{
-       struct nouveau_engine *engine;
-       struct nve0_fifo_chan *chan;
-       u32 engn;
-
-       for (engn = 0; engn < ARRAY_SIZE(fifo_engine); engn++) {
-               u32 stat = nv_rd32(priv, 0x002640 + (engn * 0x04));
-               u32 busy = (stat & 0x80000000);
-               u32 next = (stat & 0x07ff0000) >> 16;
-               u32 chsw = (stat & 0x00008000);
-               u32 save = (stat & 0x00004000);
-               u32 load = (stat & 0x00002000);
-               u32 prev = (stat & 0x000007ff);
-               u32 chid = load ? next : prev;
-               (void)save;
-
-               if (busy && chsw) {
-                       if (!(chan = (void *)priv->base.channel[chid]))
-                               continue;
-                       if (!(engine = nve0_fifo_engine(priv, engn)))
-                               continue;
-                       nve0_fifo_recover(priv, engine, chan);
-               }
-       }
-}
-
-static void
-nve0_fifo_intr_sched(struct nve0_fifo_priv *priv)
-{
-       u32 intr = nv_rd32(priv, 0x00254c);
-       u32 code = intr & 0x000000ff;
-       const struct nouveau_enum *en;
-       char enunk[6] = "";
-
-       en = nouveau_enum_find(nve0_fifo_sched_reason, code);
-       if (!en)
-               snprintf(enunk, sizeof(enunk), "UNK%02x", code);
-
-       nv_error(priv, "SCHED_ERROR [ %s ]\n", en ? en->name : enunk);
-
-       switch (code) {
-       case 0x0a:
-               nve0_fifo_intr_sched_ctxsw(priv);
-               break;
-       default:
-               break;
-       }
-}
-
-static void
-nve0_fifo_intr_chsw(struct nve0_fifo_priv *priv)
-{
-       u32 stat = nv_rd32(priv, 0x00256c);
-       nv_error(priv, "CHSW_ERROR 0x%08x\n", stat);
-       nv_wr32(priv, 0x00256c, stat);
-}
-
-static void
-nve0_fifo_intr_dropped_fault(struct nve0_fifo_priv *priv)
-{
-       u32 stat = nv_rd32(priv, 0x00259c);
-       nv_error(priv, "DROPPED_MMU_FAULT 0x%08x\n", stat);
-}
-
-static const struct nouveau_enum
-nve0_fifo_fault_engine[] = {
-       { 0x00, "GR", NULL, NVDEV_ENGINE_GR },
-       { 0x03, "IFB", NULL, NVDEV_ENGINE_IFB },
-       { 0x04, "BAR1", NULL, NVDEV_SUBDEV_BAR },
-       { 0x05, "BAR3", NULL, NVDEV_SUBDEV_INSTMEM },
-       { 0x07, "PBDMA0", NULL, NVDEV_ENGINE_FIFO },
-       { 0x08, "PBDMA1", NULL, NVDEV_ENGINE_FIFO },
-       { 0x09, "PBDMA2", NULL, NVDEV_ENGINE_FIFO },
-       { 0x10, "MSVLD", NULL, NVDEV_ENGINE_BSP },
-       { 0x11, "MSPPP", NULL, NVDEV_ENGINE_PPP },
-       { 0x13, "PERF" },
-       { 0x14, "MSPDEC", NULL, NVDEV_ENGINE_VP },
-       { 0x15, "CE0", NULL, NVDEV_ENGINE_COPY0 },
-       { 0x16, "CE1", NULL, NVDEV_ENGINE_COPY1 },
-       { 0x17, "PMU" },
-       { 0x19, "MSENC", NULL, NVDEV_ENGINE_VENC },
-       { 0x1b, "CE2", NULL, NVDEV_ENGINE_COPY2 },
-       {}
-};
-
-static const struct nouveau_enum
-nve0_fifo_fault_reason[] = {
-       { 0x00, "PDE" },
-       { 0x01, "PDE_SIZE" },
-       { 0x02, "PTE" },
-       { 0x03, "VA_LIMIT_VIOLATION" },
-       { 0x04, "UNBOUND_INST_BLOCK" },
-       { 0x05, "PRIV_VIOLATION" },
-       { 0x06, "RO_VIOLATION" },
-       { 0x07, "WO_VIOLATION" },
-       { 0x08, "PITCH_MASK_VIOLATION" },
-       { 0x09, "WORK_CREATION" },
-       { 0x0a, "UNSUPPORTED_APERTURE" },
-       { 0x0b, "COMPRESSION_FAILURE" },
-       { 0x0c, "UNSUPPORTED_KIND" },
-       { 0x0d, "REGION_VIOLATION" },
-       { 0x0e, "BOTH_PTES_VALID" },
-       { 0x0f, "INFO_TYPE_POISONED" },
-       {}
-};
-
-static const struct nouveau_enum
-nve0_fifo_fault_hubclient[] = {
-       { 0x00, "VIP" },
-       { 0x01, "CE0" },
-       { 0x02, "CE1" },
-       { 0x03, "DNISO" },
-       { 0x04, "FE" },
-       { 0x05, "FECS" },
-       { 0x06, "HOST" },
-       { 0x07, "HOST_CPU" },
-       { 0x08, "HOST_CPU_NB" },
-       { 0x09, "ISO" },
-       { 0x0a, "MMU" },
-       { 0x0b, "MSPDEC" },
-       { 0x0c, "MSPPP" },
-       { 0x0d, "MSVLD" },
-       { 0x0e, "NISO" },
-       { 0x0f, "P2P" },
-       { 0x10, "PD" },
-       { 0x11, "PERF" },
-       { 0x12, "PMU" },
-       { 0x13, "RASTERTWOD" },
-       { 0x14, "SCC" },
-       { 0x15, "SCC_NB" },
-       { 0x16, "SEC" },
-       { 0x17, "SSYNC" },
-       { 0x18, "GR_COPY" },
-       { 0x19, "CE2" },
-       { 0x1a, "XV" },
-       { 0x1b, "MMU_NB" },
-       { 0x1c, "MSENC" },
-       { 0x1d, "DFALCON" },
-       { 0x1e, "SKED" },
-       { 0x1f, "AFALCON" },
-       {}
-};
-
-static const struct nouveau_enum
-nve0_fifo_fault_gpcclient[] = {
-       { 0x00, "L1_0" }, { 0x01, "T1_0" }, { 0x02, "PE_0" },
-       { 0x03, "L1_1" }, { 0x04, "T1_1" }, { 0x05, "PE_1" },
-       { 0x06, "L1_2" }, { 0x07, "T1_2" }, { 0x08, "PE_2" },
-       { 0x09, "L1_3" }, { 0x0a, "T1_3" }, { 0x0b, "PE_3" },
-       { 0x0c, "RAST" },
-       { 0x0d, "GCC" },
-       { 0x0e, "GPCCS" },
-       { 0x0f, "PROP_0" },
-       { 0x10, "PROP_1" },
-       { 0x11, "PROP_2" },
-       { 0x12, "PROP_3" },
-       { 0x13, "L1_4" }, { 0x14, "T1_4" }, { 0x15, "PE_4" },
-       { 0x16, "L1_5" }, { 0x17, "T1_5" }, { 0x18, "PE_5" },
-       { 0x19, "L1_6" }, { 0x1a, "T1_6" }, { 0x1b, "PE_6" },
-       { 0x1c, "L1_7" }, { 0x1d, "T1_7" }, { 0x1e, "PE_7" },
-       { 0x1f, "GPM" },
-       { 0x20, "LTP_UTLB_0" },
-       { 0x21, "LTP_UTLB_1" },
-       { 0x22, "LTP_UTLB_2" },
-       { 0x23, "LTP_UTLB_3" },
-       { 0x24, "GPC_RGG_UTLB" },
-       {}
-};
-
-static void
-nve0_fifo_intr_fault(struct nve0_fifo_priv *priv, int unit)
-{
-       u32 inst = nv_rd32(priv, 0x002800 + (unit * 0x10));
-       u32 valo = nv_rd32(priv, 0x002804 + (unit * 0x10));
-       u32 vahi = nv_rd32(priv, 0x002808 + (unit * 0x10));
-       u32 stat = nv_rd32(priv, 0x00280c + (unit * 0x10));
-       u32 gpc    = (stat & 0x1f000000) >> 24;
-       u32 client = (stat & 0x00001f00) >> 8;
-       u32 write  = (stat & 0x00000080);
-       u32 hub    = (stat & 0x00000040);
-       u32 reason = (stat & 0x0000000f);
-       struct nouveau_object *engctx = NULL, *object;
-       struct nouveau_engine *engine = NULL;
-       const struct nouveau_enum *er, *eu, *ec;
-       char erunk[6] = "";
-       char euunk[6] = "";
-       char ecunk[6] = "";
-       char gpcid[3] = "";
-
-       er = nouveau_enum_find(nve0_fifo_fault_reason, reason);
-       if (!er)
-               snprintf(erunk, sizeof(erunk), "UNK%02X", reason);
-
-       eu = nouveau_enum_find(nve0_fifo_fault_engine, unit);
-       if (eu) {
-               switch (eu->data2) {
-               case NVDEV_SUBDEV_BAR:
-                       nv_mask(priv, 0x001704, 0x00000000, 0x00000000);
-                       break;
-               case NVDEV_SUBDEV_INSTMEM:
-                       nv_mask(priv, 0x001714, 0x00000000, 0x00000000);
-                       break;
-               case NVDEV_ENGINE_IFB:
-                       nv_mask(priv, 0x001718, 0x00000000, 0x00000000);
-                       break;
-               default:
-                       engine = nouveau_engine(priv, eu->data2);
-                       if (engine)
-                               engctx = nouveau_engctx_get(engine, inst);
-                       break;
-               }
-       } else {
-               snprintf(euunk, sizeof(euunk), "UNK%02x", unit);
-       }
-
-       if (hub) {
-               ec = nouveau_enum_find(nve0_fifo_fault_hubclient, client);
-       } else {
-               ec = nouveau_enum_find(nve0_fifo_fault_gpcclient, client);
-               snprintf(gpcid, sizeof(gpcid), "%d", gpc);
-       }
-
-       if (!ec)
-               snprintf(ecunk, sizeof(ecunk), "UNK%02x", client);
-
-       nv_error(priv, "%s fault at 0x%010llx [%s] from %s/%s%s%s%s on "
-                      "channel 0x%010llx [%s]\n", write ? "write" : "read",
-                (u64)vahi << 32 | valo, er ? er->name : erunk,
-                eu ? eu->name : euunk, hub ? "" : "GPC", gpcid, hub ? "" : "/",
-                ec ? ec->name : ecunk, (u64)inst << 12,
-                nouveau_client_name(engctx));
-
-       object = engctx;
-       while (object) {
-               switch (nv_mclass(object)) {
-               case KEPLER_CHANNEL_GPFIFO_A:
-                       nve0_fifo_recover(priv, engine, (void *)object);
-                       break;
-               }
-               object = object->parent;
-       }
-
-       nouveau_engctx_put(engctx);
-}
-
-static const struct nouveau_bitfield nve0_fifo_pbdma_intr_0[] = {
-       { 0x00000001, "MEMREQ" },
-       { 0x00000002, "MEMACK_TIMEOUT" },
-       { 0x00000004, "MEMACK_EXTRA" },
-       { 0x00000008, "MEMDAT_TIMEOUT" },
-       { 0x00000010, "MEMDAT_EXTRA" },
-       { 0x00000020, "MEMFLUSH" },
-       { 0x00000040, "MEMOP" },
-       { 0x00000080, "LBCONNECT" },
-       { 0x00000100, "LBREQ" },
-       { 0x00000200, "LBACK_TIMEOUT" },
-       { 0x00000400, "LBACK_EXTRA" },
-       { 0x00000800, "LBDAT_TIMEOUT" },
-       { 0x00001000, "LBDAT_EXTRA" },
-       { 0x00002000, "GPFIFO" },
-       { 0x00004000, "GPPTR" },
-       { 0x00008000, "GPENTRY" },
-       { 0x00010000, "GPCRC" },
-       { 0x00020000, "PBPTR" },
-       { 0x00040000, "PBENTRY" },
-       { 0x00080000, "PBCRC" },
-       { 0x00100000, "XBARCONNECT" },
-       { 0x00200000, "METHOD" },
-       { 0x00400000, "METHODCRC" },
-       { 0x00800000, "DEVICE" },
-       { 0x02000000, "SEMAPHORE" },
-       { 0x04000000, "ACQUIRE" },
-       { 0x08000000, "PRI" },
-       { 0x20000000, "NO_CTXSW_SEG" },
-       { 0x40000000, "PBSEG" },
-       { 0x80000000, "SIGNATURE" },
-       {}
-};
-
-static void
-nve0_fifo_intr_pbdma_0(struct nve0_fifo_priv *priv, int unit)
-{
-       u32 mask = nv_rd32(priv, 0x04010c + (unit * 0x2000));
-       u32 stat = nv_rd32(priv, 0x040108 + (unit * 0x2000)) & mask;
-       u32 addr = nv_rd32(priv, 0x0400c0 + (unit * 0x2000));
-       u32 data = nv_rd32(priv, 0x0400c4 + (unit * 0x2000));
-       u32 chid = nv_rd32(priv, 0x040120 + (unit * 0x2000)) & 0xfff;
-       u32 subc = (addr & 0x00070000) >> 16;
-       u32 mthd = (addr & 0x00003ffc);
-       u32 show = stat;
-
-       if (stat & 0x00800000) {
-               if (!nve0_fifo_swmthd(priv, chid, mthd, data))
-                       show &= ~0x00800000;
-               nv_wr32(priv, 0x0400c0 + (unit * 0x2000), 0x80600008);
-       }
-
-       if (show) {
-               nv_error(priv, "PBDMA%d:", unit);
-               nouveau_bitfield_print(nve0_fifo_pbdma_intr_0, show);
-               pr_cont("\n");
-               nv_error(priv,
-                        "PBDMA%d: ch %d [%s] subc %d mthd 0x%04x data 0x%08x\n",
-                        unit, chid,
-                        nouveau_client_name_for_fifo_chid(&priv->base, chid),
-                        subc, mthd, data);
-       }
-
-       nv_wr32(priv, 0x040108 + (unit * 0x2000), stat);
-}
-
-static const struct nouveau_bitfield nve0_fifo_pbdma_intr_1[] = {
-       { 0x00000001, "HCE_RE_ILLEGAL_OP" },
-       { 0x00000002, "HCE_RE_ALIGNB" },
-       { 0x00000004, "HCE_PRIV" },
-       { 0x00000008, "HCE_ILLEGAL_MTHD" },
-       { 0x00000010, "HCE_ILLEGAL_CLASS" },
-       {}
-};
-
-static void
-nve0_fifo_intr_pbdma_1(struct nve0_fifo_priv *priv, int unit)
-{
-       u32 mask = nv_rd32(priv, 0x04014c + (unit * 0x2000));
-       u32 stat = nv_rd32(priv, 0x040148 + (unit * 0x2000)) & mask;
-       u32 chid = nv_rd32(priv, 0x040120 + (unit * 0x2000)) & 0xfff;
-
-       if (stat) {
-               nv_error(priv, "PBDMA%d:", unit);
-               nouveau_bitfield_print(nve0_fifo_pbdma_intr_1, stat);
-               pr_cont("\n");
-               nv_error(priv, "PBDMA%d: ch %d %08x %08x\n", unit, chid,
-                        nv_rd32(priv, 0x040150 + (unit * 0x2000)),
-                        nv_rd32(priv, 0x040154 + (unit * 0x2000)));
-       }
-
-       nv_wr32(priv, 0x040148 + (unit * 0x2000), stat);
-}
-
-static void
-nve0_fifo_intr_runlist(struct nve0_fifo_priv *priv)
-{
-       u32 mask = nv_rd32(priv, 0x002a00);
-       while (mask) {
-               u32 engn = __ffs(mask);
-               wake_up(&priv->engine[engn].wait);
-               nv_wr32(priv, 0x002a00, 1 << engn);
-               mask &= ~(1 << engn);
-       }
-}
-
-static void
-nve0_fifo_intr_engine(struct nve0_fifo_priv *priv)
-{
-       nouveau_fifo_uevent(&priv->base);
-}
-
-static void
-nve0_fifo_intr(struct nouveau_subdev *subdev)
-{
-       struct nve0_fifo_priv *priv = (void *)subdev;
-       u32 mask = nv_rd32(priv, 0x002140);
-       u32 stat = nv_rd32(priv, 0x002100) & mask;
-
-       if (stat & 0x00000001) {
-               nve0_fifo_intr_bind(priv);
-               nv_wr32(priv, 0x002100, 0x00000001);
-               stat &= ~0x00000001;
-       }
-
-       if (stat & 0x00000010) {
-               nv_error(priv, "PIO_ERROR\n");
-               nv_wr32(priv, 0x002100, 0x00000010);
-               stat &= ~0x00000010;
-       }
-
-       if (stat & 0x00000100) {
-               nve0_fifo_intr_sched(priv);
-               nv_wr32(priv, 0x002100, 0x00000100);
-               stat &= ~0x00000100;
-       }
-
-       if (stat & 0x00010000) {
-               nve0_fifo_intr_chsw(priv);
-               nv_wr32(priv, 0x002100, 0x00010000);
-               stat &= ~0x00010000;
-       }
-
-       if (stat & 0x00800000) {
-               nv_error(priv, "FB_FLUSH_TIMEOUT\n");
-               nv_wr32(priv, 0x002100, 0x00800000);
-               stat &= ~0x00800000;
-       }
-
-       if (stat & 0x01000000) {
-               nv_error(priv, "LB_ERROR\n");
-               nv_wr32(priv, 0x002100, 0x01000000);
-               stat &= ~0x01000000;
-       }
-
-       if (stat & 0x08000000) {
-               nve0_fifo_intr_dropped_fault(priv);
-               nv_wr32(priv, 0x002100, 0x08000000);
-               stat &= ~0x08000000;
-       }
-
-       if (stat & 0x10000000) {
-               u32 mask = nv_rd32(priv, 0x00259c);
-               while (mask) {
-                       u32 unit = __ffs(mask);
-                       nve0_fifo_intr_fault(priv, unit);
-                       nv_wr32(priv, 0x00259c, (1 << unit));
-                       mask &= ~(1 << unit);
-               }
-               stat &= ~0x10000000;
-       }
-
-       if (stat & 0x20000000) {
-               u32 mask = nv_rd32(priv, 0x0025a0);
-               while (mask) {
-                       u32 unit = __ffs(mask);
-                       nve0_fifo_intr_pbdma_0(priv, unit);
-                       nve0_fifo_intr_pbdma_1(priv, unit);
-                       nv_wr32(priv, 0x0025a0, (1 << unit));
-                       mask &= ~(1 << unit);
-               }
-               stat &= ~0x20000000;
-       }
-
-       if (stat & 0x40000000) {
-               nve0_fifo_intr_runlist(priv);
-               stat &= ~0x40000000;
-       }
-
-       if (stat & 0x80000000) {
-               nv_wr32(priv, 0x002100, 0x80000000);
-               nve0_fifo_intr_engine(priv);
-               stat &= ~0x80000000;
-       }
-
-       if (stat) {
-               nv_error(priv, "INTR 0x%08x\n", stat);
-               nv_mask(priv, 0x002140, stat, 0x00000000);
-               nv_wr32(priv, 0x002100, stat);
-       }
-}
-
-static void
-nve0_fifo_uevent_init(struct nvkm_event *event, int type, int index)
-{
-       struct nouveau_fifo *fifo = container_of(event, typeof(*fifo), uevent);
-       nv_mask(fifo, 0x002140, 0x80000000, 0x80000000);
-}
-
-static void
-nve0_fifo_uevent_fini(struct nvkm_event *event, int type, int index)
-{
-       struct nouveau_fifo *fifo = container_of(event, typeof(*fifo), uevent);
-       nv_mask(fifo, 0x002140, 0x80000000, 0x00000000);
-}
-
-static const struct nvkm_event_func
-nve0_fifo_uevent_func = {
-       .ctor = nouveau_fifo_uevent_ctor,
-       .init = nve0_fifo_uevent_init,
-       .fini = nve0_fifo_uevent_fini,
-};
-
-int
-nve0_fifo_fini(struct nouveau_object *object, bool suspend)
-{
-       struct nve0_fifo_priv *priv = (void *)object;
-       int ret;
-
-       ret = nouveau_fifo_fini(&priv->base, suspend);
-       if (ret)
-               return ret;
-
-       /* allow mmu fault interrupts, even when we're not using fifo */
-       nv_mask(priv, 0x002140, 0x10000000, 0x10000000);
-       return 0;
-}
-
-int
-nve0_fifo_init(struct nouveau_object *object)
-{
-       struct nve0_fifo_priv *priv = (void *)object;
-       int ret, i;
-
-       ret = nouveau_fifo_init(&priv->base);
-       if (ret)
-               return ret;
-
-       /* enable all available PBDMA units */
-       nv_wr32(priv, 0x000204, 0xffffffff);
-       priv->spoon_nr = hweight32(nv_rd32(priv, 0x000204));
-       nv_debug(priv, "%d PBDMA unit(s)\n", priv->spoon_nr);
-
-       /* PBDMA[n] */
-       for (i = 0; i < priv->spoon_nr; i++) {
-               nv_mask(priv, 0x04013c + (i * 0x2000), 0x10000100, 0x00000000);
-               nv_wr32(priv, 0x040108 + (i * 0x2000), 0xffffffff); /* INTR */
-               nv_wr32(priv, 0x04010c + (i * 0x2000), 0xfffffeff); /* INTREN */
-       }
-
-       /* PBDMA[n].HCE */
-       for (i = 0; i < priv->spoon_nr; i++) {
-               nv_wr32(priv, 0x040148 + (i * 0x2000), 0xffffffff); /* INTR */
-               nv_wr32(priv, 0x04014c + (i * 0x2000), 0xffffffff); /* INTREN */
-       }
-
-       nv_wr32(priv, 0x002254, 0x10000000 | priv->user.bar.offset >> 12);
-
-       nv_wr32(priv, 0x002100, 0xffffffff);
-       nv_wr32(priv, 0x002140, 0x7fffffff);
-       return 0;
-}
-
-void
-nve0_fifo_dtor(struct nouveau_object *object)
-{
-       struct nve0_fifo_priv *priv = (void *)object;
-       int i;
-
-       nouveau_gpuobj_unmap(&priv->user.bar);
-       nouveau_gpuobj_ref(NULL, &priv->user.mem);
-
-       for (i = 0; i < FIFO_ENGINE_NR; i++) {
-               nouveau_gpuobj_ref(NULL, &priv->engine[i].runlist[1]);
-               nouveau_gpuobj_ref(NULL, &priv->engine[i].runlist[0]);
-       }
-
-       nouveau_fifo_destroy(&priv->base);
-}
-
-int
-nve0_fifo_ctor(struct nouveau_object *parent, struct nouveau_object *engine,
-              struct nouveau_oclass *oclass, void *data, u32 size,
-              struct nouveau_object **pobject)
-{
-       struct nve0_fifo_impl *impl = (void *)oclass;
-       struct nve0_fifo_priv *priv;
-       int ret, i;
-
-       ret = nouveau_fifo_create(parent, engine, oclass, 0,
-                                 impl->channels - 1, &priv);
-       *pobject = nv_object(priv);
-       if (ret)
-               return ret;
-
-       INIT_WORK(&priv->fault, nve0_fifo_recover_work);
-
-       for (i = 0; i < FIFO_ENGINE_NR; i++) {
-               ret = nouveau_gpuobj_new(nv_object(priv), NULL, 0x8000, 0x1000,
-                                        0, &priv->engine[i].runlist[0]);
-               if (ret)
-                       return ret;
-
-               ret = nouveau_gpuobj_new(nv_object(priv), NULL, 0x8000, 0x1000,
-                                        0, &priv->engine[i].runlist[1]);
-               if (ret)
-                       return ret;
-
-               init_waitqueue_head(&priv->engine[i].wait);
-       }
-
-       ret = nouveau_gpuobj_new(nv_object(priv), NULL, impl->channels * 0x200,
-                               0x1000, NVOBJ_FLAG_ZERO_ALLOC, &priv->user.mem);
-       if (ret)
-               return ret;
-
-       ret = nouveau_gpuobj_map(priv->user.mem, NV_MEM_ACCESS_RW,
-                               &priv->user.bar);
-       if (ret)
-               return ret;
-
-       ret = nvkm_event_init(&nve0_fifo_uevent_func, 1, 1, &priv->base.uevent);
-       if (ret)
-               return ret;
-
-       nv_subdev(priv)->unit = 0x00000100;
-       nv_subdev(priv)->intr = nve0_fifo_intr;
-       nv_engine(priv)->cclass = &nve0_fifo_cclass;
-       nv_engine(priv)->sclass = nve0_fifo_sclass;
-       return 0;
-}
-
-struct nouveau_oclass *
-nve0_fifo_oclass = &(struct nve0_fifo_impl) {
-       .base.handle = NV_ENGINE(FIFO, 0xe0),
-       .base.ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nve0_fifo_ctor,
-               .dtor = nve0_fifo_dtor,
-               .init = nve0_fifo_init,
-               .fini = nve0_fifo_fini,
-       },
-       .channels = 4096,
-}.base;
diff --git a/drivers/gpu/drm/nouveau/core/engine/fifo/nve0.h b/drivers/gpu/drm/nouveau/core/engine/fifo/nve0.h
deleted file mode 100644 (file)
index e96b32b..0000000
+++ /dev/null
@@ -1,18 +0,0 @@
-#ifndef __NVKM_FIFO_NVE0_H__
-#define __NVKM_FIFO_NVE0_H__
-
-#include <engine/fifo.h>
-
-int  nve0_fifo_ctor(struct nouveau_object *, struct nouveau_object *,
-                   struct nouveau_oclass *, void *, u32,
-                   struct nouveau_object **);
-void nve0_fifo_dtor(struct nouveau_object *);
-int  nve0_fifo_init(struct nouveau_object *);
-int  nve0_fifo_fini(struct nouveau_object *, bool);
-
-struct nve0_fifo_impl {
-       struct nouveau_oclass base;
-       u32 channels;
-};
-
-#endif
diff --git a/drivers/gpu/drm/nouveau/core/engine/graph/ctx.h b/drivers/gpu/drm/nouveau/core/engine/graph/ctx.h
deleted file mode 100644 (file)
index e194701..0000000
+++ /dev/null
@@ -1,129 +0,0 @@
-#ifndef __NOUVEAU_GRCTX_H__
-#define __NOUVEAU_GRCTX_H__
-
-struct nouveau_grctx {
-       struct nouveau_device *device;
-
-       enum {
-               NOUVEAU_GRCTX_PROG,
-               NOUVEAU_GRCTX_VALS
-       } mode;
-       void *data;
-
-       u32 ctxprog_max;
-       u32 ctxprog_len;
-       u32 ctxprog_reg;
-       int ctxprog_label[32];
-       u32 ctxvals_pos;
-       u32 ctxvals_base;
-};
-
-static inline void
-cp_out(struct nouveau_grctx *ctx, u32 inst)
-{
-       u32 *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, u32 val)
-{
-       cp_out(ctx, CP_LOAD_SR | val);
-}
-
-static inline void
-cp_ctx(struct nouveau_grctx *ctx, u32 reg, u32 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)
-{
-       u32 *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)
-#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)
-
-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, u32 reg, u32 val)
-{
-       if (ctx->mode != NOUVEAU_GRCTX_VALS)
-               return;
-
-       reg = (reg - 0x00400000) / 4;
-       reg = (reg - ctx->ctxprog_reg) + ctx->ctxvals_base;
-
-       nv_wo32(ctx->data, reg * 4, val);
-}
-
-#endif
diff --git a/drivers/gpu/drm/nouveau/core/engine/graph/ctxgk110b.c b/drivers/gpu/drm/nouveau/core/engine/graph/ctxgk110b.c
deleted file mode 100644 (file)
index 3adb7fe..0000000
+++ /dev/null
@@ -1,104 +0,0 @@
-/*
- * Copyright 2013 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 <bskeggs@redhat.com>
- */
-
-#include "ctxnvc0.h"
-
-/*******************************************************************************
- * PGRAPH context register lists
- ******************************************************************************/
-
-static const struct nvc0_graph_init
-gk110b_grctx_init_sm_0[] = {
-       { 0x419e04,   1, 0x04, 0x00000000 },
-       { 0x419e08,   1, 0x04, 0x0000001d },
-       { 0x419e0c,   1, 0x04, 0x00000000 },
-       { 0x419e10,   1, 0x04, 0x00001c02 },
-       { 0x419e44,   1, 0x04, 0x0013eff2 },
-       { 0x419e48,   1, 0x04, 0x00000000 },
-       { 0x419e4c,   1, 0x04, 0x0000007f },
-       { 0x419e50,   2, 0x04, 0x00000000 },
-       { 0x419e58,   1, 0x04, 0x00000001 },
-       { 0x419e5c,   3, 0x04, 0x00000000 },
-       { 0x419e68,   1, 0x04, 0x00000002 },
-       { 0x419e6c,  12, 0x04, 0x00000000 },
-       { 0x419eac,   1, 0x04, 0x00001f8f },
-       { 0x419eb0,   1, 0x04, 0x0db00d2f },
-       { 0x419eb8,   1, 0x04, 0x00000000 },
-       { 0x419ec8,   1, 0x04, 0x0001304f },
-       { 0x419f30,   4, 0x04, 0x00000000 },
-       { 0x419f40,   1, 0x04, 0x00000018 },
-       { 0x419f44,   3, 0x04, 0x00000000 },
-       { 0x419f58,   1, 0x04, 0x00000000 },
-       { 0x419f70,   1, 0x04, 0x00006300 },
-       { 0x419f78,   1, 0x04, 0x000000eb },
-       { 0x419f7c,   1, 0x04, 0x00000404 },
-       {}
-};
-
-static const struct nvc0_graph_pack
-gk110b_grctx_pack_tpc[] = {
-       { nvd7_grctx_init_pe_0 },
-       { nvf0_grctx_init_tex_0 },
-       { nvf0_grctx_init_mpc_0 },
-       { nvf0_grctx_init_l1c_0 },
-       { gk110b_grctx_init_sm_0 },
-       {}
-};
-
-/*******************************************************************************
- * PGRAPH context implementation
- ******************************************************************************/
-
-struct nouveau_oclass *
-gk110b_grctx_oclass = &(struct nvc0_grctx_oclass) {
-       .base.handle = NV_ENGCTX(GR, 0xf1),
-       .base.ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nvc0_graph_context_ctor,
-               .dtor = nvc0_graph_context_dtor,
-               .init = _nouveau_graph_context_init,
-               .fini = _nouveau_graph_context_fini,
-               .rd32 = _nouveau_graph_context_rd32,
-               .wr32 = _nouveau_graph_context_wr32,
-       },
-       .main  = nve4_grctx_generate_main,
-       .unkn  = nve4_grctx_generate_unkn,
-       .hub   = nvf0_grctx_pack_hub,
-       .gpc   = nvf0_grctx_pack_gpc,
-       .zcull = nvc0_grctx_pack_zcull,
-       .tpc   = gk110b_grctx_pack_tpc,
-       .ppc   = nvf0_grctx_pack_ppc,
-       .icmd  = nvf0_grctx_pack_icmd,
-       .mthd  = nvf0_grctx_pack_mthd,
-       .bundle = nve4_grctx_generate_bundle,
-       .bundle_size = 0x3000,
-       .bundle_min_gpm_fifo_depth = 0x180,
-       .bundle_token_limit = 0x600,
-       .pagepool = nve4_grctx_generate_pagepool,
-       .pagepool_size = 0x8000,
-       .attrib = nvd7_grctx_generate_attrib,
-       .attrib_nr_max = 0x324,
-       .attrib_nr = 0x218,
-       .alpha_nr_max = 0x7ff,
-       .alpha_nr = 0x648,
-}.base;
diff --git a/drivers/gpu/drm/nouveau/core/engine/graph/ctxgk20a.c b/drivers/gpu/drm/nouveau/core/engine/graph/ctxgk20a.c
deleted file mode 100644 (file)
index 36fc983..0000000
+++ /dev/null
@@ -1,63 +0,0 @@
-/*
- * Copyright (c) 2014, NVIDIA CORPORATION. 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 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 "ctxnvc0.h"
-
-static const struct nvc0_graph_pack
-gk20a_grctx_pack_mthd[] = {
-       { nve4_grctx_init_a097_0, 0xa297 },
-       { nvc0_grctx_init_902d_0, 0x902d },
-       {}
-};
-
-struct nouveau_oclass *
-gk20a_grctx_oclass = &(struct nvc0_grctx_oclass) {
-       .base.handle = NV_ENGCTX(GR, 0xea),
-       .base.ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nvc0_graph_context_ctor,
-               .dtor = nvc0_graph_context_dtor,
-               .init = _nouveau_graph_context_init,
-               .fini = _nouveau_graph_context_fini,
-               .rd32 = _nouveau_graph_context_rd32,
-               .wr32 = _nouveau_graph_context_wr32,
-       },
-       .main  = nve4_grctx_generate_main,
-       .unkn  = nve4_grctx_generate_unkn,
-       .hub   = nve4_grctx_pack_hub,
-       .gpc   = nve4_grctx_pack_gpc,
-       .zcull = nvc0_grctx_pack_zcull,
-       .tpc   = nve4_grctx_pack_tpc,
-       .ppc   = nve4_grctx_pack_ppc,
-       .icmd  = nve4_grctx_pack_icmd,
-       .mthd  = gk20a_grctx_pack_mthd,
-       .bundle = nve4_grctx_generate_bundle,
-       .bundle_size = 0x1800,
-       .bundle_min_gpm_fifo_depth = 0x62,
-       .bundle_token_limit = 0x100,
-       .pagepool = nve4_grctx_generate_pagepool,
-       .pagepool_size = 0x8000,
-       .attrib = nvd7_grctx_generate_attrib,
-       .attrib_nr_max = 0x240,
-       .attrib_nr = 0x240,
-       .alpha_nr_max = 0x648 + (0x648 / 2),
-       .alpha_nr = 0x648,
-}.base;
diff --git a/drivers/gpu/drm/nouveau/core/engine/graph/ctxgm107.c b/drivers/gpu/drm/nouveau/core/engine/graph/ctxgm107.c
deleted file mode 100644 (file)
index 62e918b..0000000
+++ /dev/null
@@ -1,1032 +0,0 @@
-/*
- * Copyright 2013 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 <bskeggs@redhat.com>
- */
-
-#include "ctxnvc0.h"
-
-/*******************************************************************************
- * PGRAPH context register lists
- ******************************************************************************/
-
-static const struct nvc0_graph_init
-gm107_grctx_init_icmd_0[] = {
-       { 0x001000,   1, 0x01, 0x00000004 },
-       { 0x000039,   3, 0x01, 0x00000000 },
-       { 0x0000a9,   1, 0x01, 0x0000ffff },
-       { 0x000038,   1, 0x01, 0x0fac6881 },
-       { 0x00003d,   1, 0x01, 0x00000001 },
-       { 0x0000e8,   8, 0x01, 0x00000400 },
-       { 0x000078,   8, 0x01, 0x00000300 },
-       { 0x000050,   1, 0x01, 0x00000011 },
-       { 0x000058,   8, 0x01, 0x00000008 },
-       { 0x000208,   8, 0x01, 0x00000001 },
-       { 0x000081,   1, 0x01, 0x00000001 },
-       { 0x000085,   1, 0x01, 0x00000004 },
-       { 0x000088,   1, 0x01, 0x00000400 },
-       { 0x000090,   1, 0x01, 0x00000300 },
-       { 0x000098,   1, 0x01, 0x00001001 },
-       { 0x0000e3,   1, 0x01, 0x00000001 },
-       { 0x0000da,   1, 0x01, 0x00000001 },
-       { 0x0000f8,   1, 0x01, 0x00000003 },
-       { 0x0000fa,   1, 0x01, 0x00000001 },
-       { 0x0000b1,   2, 0x01, 0x00000001 },
-       { 0x00009f,   4, 0x01, 0x0000ffff },
-       { 0x0000a8,   1, 0x01, 0x0000ffff },
-       { 0x0000ad,   1, 0x01, 0x0000013e },
-       { 0x0000e1,   1, 0x01, 0x00000010 },
-       { 0x000290,  16, 0x01, 0x00000000 },
-       { 0x0003b0,  16, 0x01, 0x00000000 },
-       { 0x0002a0,  16, 0x01, 0x00000000 },
-       { 0x000420,  16, 0x01, 0x00000000 },
-       { 0x0002b0,  16, 0x01, 0x00000000 },
-       { 0x000430,  16, 0x01, 0x00000000 },
-       { 0x0002c0,  16, 0x01, 0x00000000 },
-       { 0x0004d0,  16, 0x01, 0x00000000 },
-       { 0x000720,  16, 0x01, 0x00000000 },
-       { 0x0008c0,  16, 0x01, 0x00000000 },
-       { 0x000890,  16, 0x01, 0x00000000 },
-       { 0x0008e0,  16, 0x01, 0x00000000 },
-       { 0x0008a0,  16, 0x01, 0x00000000 },
-       { 0x0008f0,  16, 0x01, 0x00000000 },
-       { 0x00094c,   1, 0x01, 0x000000ff },
-       { 0x00094d,   1, 0x01, 0xffffffff },
-       { 0x00094e,   1, 0x01, 0x00000002 },
-       { 0x0002f2,   2, 0x01, 0x00000001 },
-       { 0x0002f5,   1, 0x01, 0x00000001 },
-       { 0x0002f7,   1, 0x01, 0x00000001 },
-       { 0x000303,   1, 0x01, 0x00000001 },
-       { 0x0002e6,   1, 0x01, 0x00000001 },
-       { 0x000466,   1, 0x01, 0x00000052 },
-       { 0x000301,   1, 0x01, 0x3f800000 },
-       { 0x000304,   1, 0x01, 0x30201000 },
-       { 0x000305,   1, 0x01, 0x70605040 },
-       { 0x000306,   1, 0x01, 0xb8a89888 },
-       { 0x000307,   1, 0x01, 0xf8e8d8c8 },
-       { 0x00030a,   1, 0x01, 0x00ffff00 },
-       { 0x0000de,   1, 0x01, 0x00000001 },
-       { 0x00030b,   1, 0x01, 0x0000001a },
-       { 0x00030c,   1, 0x01, 0x00000001 },
-       { 0x000318,   1, 0x01, 0x00000001 },
-       { 0x000340,   1, 0x01, 0x00000000 },
-       { 0x00037d,   1, 0x01, 0x00000006 },
-       { 0x0003a0,   1, 0x01, 0x00000002 },
-       { 0x0003aa,   1, 0x01, 0x00000001 },
-       { 0x0003a9,   1, 0x01, 0x00000001 },
-       { 0x000380,   1, 0x01, 0x00000001 },
-       { 0x000383,   1, 0x01, 0x00000011 },
-       { 0x000360,   1, 0x01, 0x00000040 },
-       { 0x000366,   2, 0x01, 0x00000000 },
-       { 0x000368,   1, 0x01, 0x00000fff },
-       { 0x000370,   2, 0x01, 0x00000000 },
-       { 0x000372,   1, 0x01, 0x000fffff },
-       { 0x00037a,   1, 0x01, 0x00000012 },
-       { 0x000619,   1, 0x01, 0x00000003 },
-       { 0x000811,   1, 0x01, 0x00000003 },
-       { 0x000812,   1, 0x01, 0x00000004 },
-       { 0x000813,   1, 0x01, 0x00000006 },
-       { 0x000814,   1, 0x01, 0x00000008 },
-       { 0x000815,   1, 0x01, 0x0000000b },
-       { 0x000800,   6, 0x01, 0x00000001 },
-       { 0x000632,   1, 0x01, 0x00000001 },
-       { 0x000633,   1, 0x01, 0x00000002 },
-       { 0x000634,   1, 0x01, 0x00000003 },
-       { 0x000635,   1, 0x01, 0x00000004 },
-       { 0x000654,   1, 0x01, 0x3f800000 },
-       { 0x000657,   1, 0x01, 0x3f800000 },
-       { 0x000655,   2, 0x01, 0x3f800000 },
-       { 0x0006cd,   1, 0x01, 0x3f800000 },
-       { 0x0007f5,   1, 0x01, 0x3f800000 },
-       { 0x0007dc,   1, 0x01, 0x39291909 },
-       { 0x0007dd,   1, 0x01, 0x79695949 },
-       { 0x0007de,   1, 0x01, 0xb9a99989 },
-       { 0x0007df,   1, 0x01, 0xf9e9d9c9 },
-       { 0x0007e8,   1, 0x01, 0x00003210 },
-       { 0x0007e9,   1, 0x01, 0x00007654 },
-       { 0x0007ea,   1, 0x01, 0x00000098 },
-       { 0x0007ec,   1, 0x01, 0x39291909 },
-       { 0x0007ed,   1, 0x01, 0x79695949 },
-       { 0x0007ee,   1, 0x01, 0xb9a99989 },
-       { 0x0007ef,   1, 0x01, 0xf9e9d9c9 },
-       { 0x0007f0,   1, 0x01, 0x00003210 },
-       { 0x0007f1,   1, 0x01, 0x00007654 },
-       { 0x0007f2,   1, 0x01, 0x00000098 },
-       { 0x0005a5,   1, 0x01, 0x00000001 },
-       { 0x0005d0,   1, 0x01, 0x20181008 },
-       { 0x0005d1,   1, 0x01, 0x40383028 },
-       { 0x0005d2,   1, 0x01, 0x60585048 },
-       { 0x0005d3,   1, 0x01, 0x80787068 },
-       { 0x000980, 128, 0x01, 0x00000000 },
-       { 0x000468,   1, 0x01, 0x00000004 },
-       { 0x00046c,   1, 0x01, 0x00000001 },
-       { 0x000470,  96, 0x01, 0x00000000 },
-       { 0x000510,  16, 0x01, 0x3f800000 },
-       { 0x000520,   1, 0x01, 0x000002b6 },
-       { 0x000529,   1, 0x01, 0x00000001 },
-       { 0x000530,  16, 0x01, 0xffff0000 },
-       { 0x000550,  32, 0x01, 0xffff0000 },
-       { 0x000585,   1, 0x01, 0x0000003f },
-       { 0x000576,   1, 0x01, 0x00000003 },
-       { 0x00057b,   1, 0x01, 0x00000059 },
-       { 0x000586,   1, 0x01, 0x00000040 },
-       { 0x000582,   2, 0x01, 0x00000080 },
-       { 0x000595,   1, 0x01, 0x00400040 },
-       { 0x000596,   1, 0x01, 0x00000492 },
-       { 0x000597,   1, 0x01, 0x08080203 },
-       { 0x0005ad,   1, 0x01, 0x00000008 },
-       { 0x000598,   1, 0x01, 0x00020001 },
-       { 0x0005c2,   1, 0x01, 0x00000001 },
-       { 0x000638,   2, 0x01, 0x00000001 },
-       { 0x00063a,   1, 0x01, 0x00000002 },
-       { 0x00063b,   2, 0x01, 0x00000001 },
-       { 0x00063d,   1, 0x01, 0x00000002 },
-       { 0x00063e,   1, 0x01, 0x00000001 },
-       { 0x0008b8,   8, 0x01, 0x00000001 },
-       { 0x000900,   8, 0x01, 0x00000001 },
-       { 0x000908,   8, 0x01, 0x00000002 },
-       { 0x000910,  16, 0x01, 0x00000001 },
-       { 0x000920,   8, 0x01, 0x00000002 },
-       { 0x000928,   8, 0x01, 0x00000001 },
-       { 0x000662,   1, 0x01, 0x00000001 },
-       { 0x000648,   9, 0x01, 0x00000001 },
-       { 0x000658,   1, 0x01, 0x0000000f },
-       { 0x0007ff,   1, 0x01, 0x0000000a },
-       { 0x00066a,   1, 0x01, 0x40000000 },
-       { 0x00066b,   1, 0x01, 0x10000000 },
-       { 0x00066c,   2, 0x01, 0xffff0000 },
-       { 0x0007af,   2, 0x01, 0x00000008 },
-       { 0x0007f6,   1, 0x01, 0x00000001 },
-       { 0x0006b2,   1, 0x01, 0x00000055 },
-       { 0x0007ad,   1, 0x01, 0x00000003 },
-       { 0x000971,   1, 0x01, 0x00000008 },
-       { 0x000972,   1, 0x01, 0x00000040 },
-       { 0x000973,   1, 0x01, 0x0000012c },
-       { 0x00097c,   1, 0x01, 0x00000040 },
-       { 0x000975,   1, 0x01, 0x00000020 },
-       { 0x000976,   1, 0x01, 0x00000001 },
-       { 0x000977,   1, 0x01, 0x00000020 },
-       { 0x000978,   1, 0x01, 0x00000001 },
-       { 0x000957,   1, 0x01, 0x00000003 },
-       { 0x00095e,   1, 0x01, 0x20164010 },
-       { 0x00095f,   1, 0x01, 0x00000020 },
-       { 0x000a0d,   1, 0x01, 0x00000006 },
-       { 0x00097d,   1, 0x01, 0x0000000c },
-       { 0x000683,   1, 0x01, 0x00000006 },
-       { 0x000687,   1, 0x01, 0x003fffff },
-       { 0x0006a0,   1, 0x01, 0x00000005 },
-       { 0x000840,   1, 0x01, 0x00400008 },
-       { 0x000841,   1, 0x01, 0x08000080 },
-       { 0x000842,   1, 0x01, 0x00400008 },
-       { 0x000843,   1, 0x01, 0x08000080 },
-       { 0x000818,   8, 0x01, 0x00000000 },
-       { 0x000848,  16, 0x01, 0x00000000 },
-       { 0x000738,   1, 0x01, 0x00000000 },
-       { 0x0006aa,   1, 0x01, 0x00000001 },
-       { 0x0006ab,   1, 0x01, 0x00000002 },
-       { 0x0006ac,   1, 0x01, 0x00000080 },
-       { 0x0006ad,   2, 0x01, 0x00000100 },
-       { 0x0006b1,   1, 0x01, 0x00000011 },
-       { 0x0006bb,   1, 0x01, 0x000000cf },
-       { 0x0006ce,   1, 0x01, 0x2a712488 },
-       { 0x000739,   1, 0x01, 0x4085c000 },
-       { 0x00073a,   1, 0x01, 0x00000080 },
-       { 0x000786,   1, 0x01, 0x80000100 },
-       { 0x00073c,   1, 0x01, 0x00010100 },
-       { 0x00073d,   1, 0x01, 0x02800000 },
-       { 0x000787,   1, 0x01, 0x000000cf },
-       { 0x00078c,   1, 0x01, 0x00000008 },
-       { 0x000792,   1, 0x01, 0x00000001 },
-       { 0x000794,   3, 0x01, 0x00000001 },
-       { 0x000797,   1, 0x01, 0x000000cf },
-       { 0x000836,   1, 0x01, 0x00000001 },
-       { 0x00079a,   1, 0x01, 0x00000002 },
-       { 0x000833,   1, 0x01, 0x04444480 },
-       { 0x0007a1,   1, 0x01, 0x00000001 },
-       { 0x0007a3,   3, 0x01, 0x00000001 },
-       { 0x000831,   1, 0x01, 0x00000004 },
-       { 0x000b07,   1, 0x01, 0x00000002 },
-       { 0x000b08,   2, 0x01, 0x00000100 },
-       { 0x000b0a,   1, 0x01, 0x00000001 },
-       { 0x000a04,   1, 0x01, 0x000000ff },
-       { 0x000a0b,   1, 0x01, 0x00000040 },
-       { 0x00097f,   1, 0x01, 0x00000100 },
-       { 0x000a02,   1, 0x01, 0x00000001 },
-       { 0x000809,   1, 0x01, 0x00000007 },
-       { 0x00c221,   1, 0x01, 0x00000040 },
-       { 0x00c1b0,   8, 0x01, 0x0000000f },
-       { 0x00c1b8,   1, 0x01, 0x0fac6881 },
-       { 0x00c1b9,   1, 0x01, 0x00fac688 },
-       { 0x00c401,   1, 0x01, 0x00000001 },
-       { 0x00c402,   1, 0x01, 0x00010001 },
-       { 0x00c403,   2, 0x01, 0x00000001 },
-       { 0x00c40e,   1, 0x01, 0x00000020 },
-       { 0x01e100,   1, 0x01, 0x00000001 },
-       { 0x001000,   1, 0x01, 0x00000002 },
-       { 0x0006aa,   1, 0x01, 0x00000001 },
-       { 0x0006ad,   2, 0x01, 0x00000100 },
-       { 0x0006b1,   1, 0x01, 0x00000011 },
-       { 0x00078c,   1, 0x01, 0x00000008 },
-       { 0x000792,   1, 0x01, 0x00000001 },
-       { 0x000794,   3, 0x01, 0x00000001 },
-       { 0x000797,   1, 0x01, 0x000000cf },
-       { 0x00079a,   1, 0x01, 0x00000002 },
-       { 0x0007a1,   1, 0x01, 0x00000001 },
-       { 0x0007a3,   3, 0x01, 0x00000001 },
-       { 0x000831,   1, 0x01, 0x00000004 },
-       { 0x01e100,   1, 0x01, 0x00000001 },
-       { 0x001000,   1, 0x01, 0x00000008 },
-       { 0x000039,   3, 0x01, 0x00000000 },
-       { 0x000380,   1, 0x01, 0x00000001 },
-       { 0x000366,   2, 0x01, 0x00000000 },
-       { 0x000368,   1, 0x01, 0x00000fff },
-       { 0x000370,   2, 0x01, 0x00000000 },
-       { 0x000372,   1, 0x01, 0x000fffff },
-       { 0x000813,   1, 0x01, 0x00000006 },
-       { 0x000814,   1, 0x01, 0x00000008 },
-       { 0x000818,   8, 0x01, 0x00000000 },
-       { 0x000848,  16, 0x01, 0x00000000 },
-       { 0x000738,   1, 0x01, 0x00000000 },
-       { 0x000b07,   1, 0x01, 0x00000002 },
-       { 0x000b08,   2, 0x01, 0x00000100 },
-       { 0x000b0a,   1, 0x01, 0x00000001 },
-       { 0x000a04,   1, 0x01, 0x000000ff },
-       { 0x000a0b,   1, 0x01, 0x00000040 },
-       { 0x00097f,   1, 0x01, 0x00000100 },
-       { 0x000a02,   1, 0x01, 0x00000001 },
-       { 0x000809,   1, 0x01, 0x00000007 },
-       { 0x00c221,   1, 0x01, 0x00000040 },
-       { 0x00c401,   1, 0x01, 0x00000001 },
-       { 0x00c402,   1, 0x01, 0x00010001 },
-       { 0x00c403,   2, 0x01, 0x00000001 },
-       { 0x00c40e,   1, 0x01, 0x00000020 },
-       { 0x01e100,   1, 0x01, 0x00000001 },
-       { 0x001000,   1, 0x01, 0x00000001 },
-       { 0x000b07,   1, 0x01, 0x00000002 },
-       { 0x000b08,   2, 0x01, 0x00000100 },
-       { 0x000b0a,   1, 0x01, 0x00000001 },
-       { 0x01e100,   1, 0x01, 0x00000001 },
-       {}
-};
-
-static const struct nvc0_graph_pack
-gm107_grctx_pack_icmd[] = {
-       { gm107_grctx_init_icmd_0 },
-       {}
-};
-
-static const struct nvc0_graph_init
-gm107_grctx_init_b097_0[] = {
-       { 0x000800,   8, 0x40, 0x00000000 },
-       { 0x000804,   8, 0x40, 0x00000000 },
-       { 0x000808,   8, 0x40, 0x00000400 },
-       { 0x00080c,   8, 0x40, 0x00000300 },
-       { 0x000810,   1, 0x04, 0x000000cf },
-       { 0x000850,   7, 0x40, 0x00000000 },
-       { 0x000814,   8, 0x40, 0x00000040 },
-       { 0x000818,   8, 0x40, 0x00000001 },
-       { 0x00081c,   8, 0x40, 0x00000000 },
-       { 0x000820,   8, 0x40, 0x00000000 },
-       { 0x001c00,  16, 0x10, 0x00000000 },
-       { 0x001c04,  16, 0x10, 0x00000000 },
-       { 0x001c08,  16, 0x10, 0x00000000 },
-       { 0x001c0c,  16, 0x10, 0x00000000 },
-       { 0x001d00,  16, 0x10, 0x00000000 },
-       { 0x001d04,  16, 0x10, 0x00000000 },
-       { 0x001d08,  16, 0x10, 0x00000000 },
-       { 0x001d0c,  16, 0x10, 0x00000000 },
-       { 0x001f00,  16, 0x08, 0x00000000 },
-       { 0x001f04,  16, 0x08, 0x00000000 },
-       { 0x001f80,  16, 0x08, 0x00000000 },
-       { 0x001f84,  16, 0x08, 0x00000000 },
-       { 0x002000,   1, 0x04, 0x00000000 },
-       { 0x002040,   1, 0x04, 0x00000011 },
-       { 0x002080,   1, 0x04, 0x00000020 },
-       { 0x0020c0,   1, 0x04, 0x00000030 },
-       { 0x002100,   1, 0x04, 0x00000040 },
-       { 0x002140,   1, 0x04, 0x00000051 },
-       { 0x00200c,   6, 0x40, 0x00000001 },
-       { 0x002010,   1, 0x04, 0x00000000 },
-       { 0x002050,   1, 0x04, 0x00000000 },
-       { 0x002090,   1, 0x04, 0x00000001 },
-       { 0x0020d0,   1, 0x04, 0x00000002 },
-       { 0x002110,   1, 0x04, 0x00000003 },
-       { 0x002150,   1, 0x04, 0x00000004 },
-       { 0x000380,   4, 0x20, 0x00000000 },
-       { 0x000384,   4, 0x20, 0x00000000 },
-       { 0x000388,   4, 0x20, 0x00000000 },
-       { 0x00038c,   4, 0x20, 0x00000000 },
-       { 0x000700,   4, 0x10, 0x00000000 },
-       { 0x000704,   4, 0x10, 0x00000000 },
-       { 0x000708,   4, 0x10, 0x00000000 },
-       { 0x002800, 128, 0x04, 0x00000000 },
-       { 0x000a00,  16, 0x20, 0x00000000 },
-       { 0x000a04,  16, 0x20, 0x00000000 },
-       { 0x000a08,  16, 0x20, 0x00000000 },
-       { 0x000a0c,  16, 0x20, 0x00000000 },
-       { 0x000a10,  16, 0x20, 0x00000000 },
-       { 0x000a14,  16, 0x20, 0x00000000 },
-       { 0x000c00,  16, 0x10, 0x00000000 },
-       { 0x000c04,  16, 0x10, 0x00000000 },
-       { 0x000c08,  16, 0x10, 0x00000000 },
-       { 0x000c0c,  16, 0x10, 0x3f800000 },
-       { 0x000d00,   8, 0x08, 0xffff0000 },
-       { 0x000d04,   8, 0x08, 0xffff0000 },
-       { 0x000e00,  16, 0x10, 0x00000000 },
-       { 0x000e04,  16, 0x10, 0xffff0000 },
-       { 0x000e08,  16, 0x10, 0xffff0000 },
-       { 0x000d40,   4, 0x08, 0x00000000 },
-       { 0x000d44,   4, 0x08, 0x00000000 },
-       { 0x001e00,   8, 0x20, 0x00000001 },
-       { 0x001e04,   8, 0x20, 0x00000001 },
-       { 0x001e08,   8, 0x20, 0x00000002 },
-       { 0x001e0c,   8, 0x20, 0x00000001 },
-       { 0x001e10,   8, 0x20, 0x00000001 },
-       { 0x001e14,   8, 0x20, 0x00000002 },
-       { 0x001e18,   8, 0x20, 0x00000001 },
-       { 0x001480,   8, 0x10, 0x00000000 },
-       { 0x001484,   8, 0x10, 0x00000000 },
-       { 0x001488,   8, 0x10, 0x00000000 },
-       { 0x003400, 128, 0x04, 0x00000000 },
-       { 0x00030c,   1, 0x04, 0x00000001 },
-       { 0x001944,   1, 0x04, 0x00000000 },
-       { 0x001514,   1, 0x04, 0x00000000 },
-       { 0x000d68,   1, 0x04, 0x0000ffff },
-       { 0x00121c,   1, 0x04, 0x0fac6881 },
-       { 0x000fac,   1, 0x04, 0x00000001 },
-       { 0x001538,   1, 0x04, 0x00000001 },
-       { 0x000fe0,   2, 0x04, 0x00000000 },
-       { 0x000fe8,   1, 0x04, 0x00000014 },
-       { 0x000fec,   1, 0x04, 0x00000040 },
-       { 0x000ff0,   1, 0x04, 0x00000000 },
-       { 0x00179c,   1, 0x04, 0x00000000 },
-       { 0x001228,   1, 0x04, 0x00000400 },
-       { 0x00122c,   1, 0x04, 0x00000300 },
-       { 0x001230,   1, 0x04, 0x00010001 },
-       { 0x0007f8,   1, 0x04, 0x00000000 },
-       { 0x0015b4,   1, 0x04, 0x00000001 },
-       { 0x0015cc,   1, 0x04, 0x00000000 },
-       { 0x001534,   1, 0x04, 0x00000000 },
-       { 0x000754,   1, 0x04, 0x00000001 },
-       { 0x000fb0,   1, 0x04, 0x00000000 },
-       { 0x0015d0,   1, 0x04, 0x00000000 },
-       { 0x00153c,   1, 0x04, 0x00000000 },
-       { 0x0016b4,   1, 0x04, 0x00000003 },
-       { 0x000fbc,   4, 0x04, 0x0000ffff },
-       { 0x000df8,   2, 0x04, 0x00000000 },
-       { 0x001948,   1, 0x04, 0x00000000 },
-       { 0x001970,   1, 0x04, 0x00000001 },
-       { 0x00161c,   1, 0x04, 0x000009f0 },
-       { 0x000dcc,   1, 0x04, 0x00000010 },
-       { 0x0015e4,   1, 0x04, 0x00000000 },
-       { 0x001160,  32, 0x04, 0x25e00040 },
-       { 0x001880,  32, 0x04, 0x00000000 },
-       { 0x000f84,   2, 0x04, 0x00000000 },
-       { 0x0017c8,   2, 0x04, 0x00000000 },
-       { 0x0017d0,   1, 0x04, 0x000000ff },
-       { 0x0017d4,   1, 0x04, 0xffffffff },
-       { 0x0017d8,   1, 0x04, 0x00000002 },
-       { 0x0017dc,   1, 0x04, 0x00000000 },
-       { 0x0015f4,   2, 0x04, 0x00000000 },
-       { 0x001434,   2, 0x04, 0x00000000 },
-       { 0x000d74,   1, 0x04, 0x00000000 },
-       { 0x0013a4,   1, 0x04, 0x00000000 },
-       { 0x001318,   1, 0x04, 0x00000001 },
-       { 0x001080,   2, 0x04, 0x00000000 },
-       { 0x001088,   2, 0x04, 0x00000001 },
-       { 0x001090,   1, 0x04, 0x00000000 },
-       { 0x001094,   1, 0x04, 0x00000001 },
-       { 0x001098,   1, 0x04, 0x00000000 },
-       { 0x00109c,   1, 0x04, 0x00000001 },
-       { 0x0010a0,   2, 0x04, 0x00000000 },
-       { 0x001644,   1, 0x04, 0x00000000 },
-       { 0x000748,   1, 0x04, 0x00000000 },
-       { 0x000de8,   1, 0x04, 0x00000000 },
-       { 0x001648,   1, 0x04, 0x00000000 },
-       { 0x0012a4,   1, 0x04, 0x00000000 },
-       { 0x001120,   4, 0x04, 0x00000000 },
-       { 0x001118,   1, 0x04, 0x00000000 },
-       { 0x00164c,   1, 0x04, 0x00000000 },
-       { 0x001658,   1, 0x04, 0x00000000 },
-       { 0x001910,   1, 0x04, 0x00000290 },
-       { 0x001518,   1, 0x04, 0x00000000 },
-       { 0x00165c,   1, 0x04, 0x00000001 },
-       { 0x001520,   1, 0x04, 0x00000000 },
-       { 0x001604,   1, 0x04, 0x00000000 },
-       { 0x001570,   1, 0x04, 0x00000000 },
-       { 0x0013b0,   2, 0x04, 0x3f800000 },
-       { 0x00020c,   1, 0x04, 0x00000000 },
-       { 0x001670,   1, 0x04, 0x30201000 },
-       { 0x001674,   1, 0x04, 0x70605040 },
-       { 0x001678,   1, 0x04, 0xb8a89888 },
-       { 0x00167c,   1, 0x04, 0xf8e8d8c8 },
-       { 0x00166c,   1, 0x04, 0x00000000 },
-       { 0x001680,   1, 0x04, 0x00ffff00 },
-       { 0x0012d0,   1, 0x04, 0x00000003 },
-       { 0x0012d4,   1, 0x04, 0x00000002 },
-       { 0x001684,   2, 0x04, 0x00000000 },
-       { 0x000dac,   2, 0x04, 0x00001b02 },
-       { 0x000db4,   1, 0x04, 0x00000000 },
-       { 0x00168c,   1, 0x04, 0x00000000 },
-       { 0x0015bc,   1, 0x04, 0x00000000 },
-       { 0x00156c,   1, 0x04, 0x00000000 },
-       { 0x00187c,   1, 0x04, 0x00000000 },
-       { 0x001110,   1, 0x04, 0x00000001 },
-       { 0x000dc0,   3, 0x04, 0x00000000 },
-       { 0x000f40,   5, 0x04, 0x00000000 },
-       { 0x001234,   1, 0x04, 0x00000000 },
-       { 0x001690,   1, 0x04, 0x00000000 },
-       { 0x000790,   5, 0x04, 0x00000000 },
-       { 0x00077c,   1, 0x04, 0x00000000 },
-       { 0x001000,   1, 0x04, 0x00000010 },
-       { 0x0010fc,   1, 0x04, 0x00000000 },
-       { 0x001290,   1, 0x04, 0x00000000 },
-       { 0x000218,   1, 0x04, 0x00000010 },
-       { 0x0012d8,   1, 0x04, 0x00000000 },
-       { 0x0012dc,   1, 0x04, 0x00000010 },
-       { 0x000d94,   1, 0x04, 0x00000001 },
-       { 0x00155c,   2, 0x04, 0x00000000 },
-       { 0x001564,   1, 0x04, 0x00000fff },
-       { 0x001574,   2, 0x04, 0x00000000 },
-       { 0x00157c,   1, 0x04, 0x000fffff },
-       { 0x001354,   1, 0x04, 0x00000000 },
-       { 0x001610,   1, 0x04, 0x00000012 },
-       { 0x001608,   2, 0x04, 0x00000000 },
-       { 0x00260c,   1, 0x04, 0x00000000 },
-       { 0x0007ac,   1, 0x04, 0x00000000 },
-       { 0x00162c,   1, 0x04, 0x00000003 },
-       { 0x000210,   1, 0x04, 0x00000000 },
-       { 0x000320,   1, 0x04, 0x00000000 },
-       { 0x000324,   6, 0x04, 0x3f800000 },
-       { 0x000750,   1, 0x04, 0x00000000 },
-       { 0x000760,   1, 0x04, 0x39291909 },
-       { 0x000764,   1, 0x04, 0x79695949 },
-       { 0x000768,   1, 0x04, 0xb9a99989 },
-       { 0x00076c,   1, 0x04, 0xf9e9d9c9 },
-       { 0x000770,   1, 0x04, 0x30201000 },
-       { 0x000774,   1, 0x04, 0x70605040 },
-       { 0x000778,   1, 0x04, 0x00009080 },
-       { 0x000780,   1, 0x04, 0x39291909 },
-       { 0x000784,   1, 0x04, 0x79695949 },
-       { 0x000788,   1, 0x04, 0xb9a99989 },
-       { 0x00078c,   1, 0x04, 0xf9e9d9c9 },
-       { 0x0007d0,   1, 0x04, 0x30201000 },
-       { 0x0007d4,   1, 0x04, 0x70605040 },
-       { 0x0007d8,   1, 0x04, 0x00009080 },
-       { 0x00037c,   1, 0x04, 0x00000001 },
-       { 0x000740,   2, 0x04, 0x00000000 },
-       { 0x002600,   1, 0x04, 0x00000000 },
-       { 0x001918,   1, 0x04, 0x00000000 },
-       { 0x00191c,   1, 0x04, 0x00000900 },
-       { 0x001920,   1, 0x04, 0x00000405 },
-       { 0x001308,   1, 0x04, 0x00000001 },
-       { 0x001924,   1, 0x04, 0x00000000 },
-       { 0x0013ac,   1, 0x04, 0x00000000 },
-       { 0x00192c,   1, 0x04, 0x00000001 },
-       { 0x00193c,   1, 0x04, 0x00002c1c },
-       { 0x000d7c,   1, 0x04, 0x00000000 },
-       { 0x000f8c,   1, 0x04, 0x00000000 },
-       { 0x0002c0,   1, 0x04, 0x00000001 },
-       { 0x001510,   1, 0x04, 0x00000000 },
-       { 0x001940,   1, 0x04, 0x00000000 },
-       { 0x000ff4,   2, 0x04, 0x00000000 },
-       { 0x00194c,   2, 0x04, 0x00000000 },
-       { 0x001968,   1, 0x04, 0x00000000 },
-       { 0x001590,   1, 0x04, 0x0000003f },
-       { 0x0007e8,   4, 0x04, 0x00000000 },
-       { 0x00196c,   1, 0x04, 0x00000011 },
-       { 0x0002e4,   1, 0x04, 0x0000b001 },
-       { 0x00036c,   2, 0x04, 0x00000000 },
-       { 0x00197c,   1, 0x04, 0x00000000 },
-       { 0x000fcc,   2, 0x04, 0x00000000 },
-       { 0x0002d8,   1, 0x04, 0x00000040 },
-       { 0x001980,   1, 0x04, 0x00000080 },
-       { 0x001504,   1, 0x04, 0x00000080 },
-       { 0x001984,   1, 0x04, 0x00000000 },
-       { 0x000f60,   1, 0x04, 0x00000000 },
-       { 0x000f64,   1, 0x04, 0x00400040 },
-       { 0x000f68,   1, 0x04, 0x00002212 },
-       { 0x000f6c,   1, 0x04, 0x08080203 },
-       { 0x001108,   1, 0x04, 0x00000008 },
-       { 0x000f70,   1, 0x04, 0x00080001 },
-       { 0x000ffc,   1, 0x04, 0x00000000 },
-       { 0x000300,   1, 0x04, 0x00000001 },
-       { 0x0013a8,   1, 0x04, 0x00000000 },
-       { 0x0012ec,   1, 0x04, 0x00000000 },
-       { 0x001310,   1, 0x04, 0x00000000 },
-       { 0x001314,   1, 0x04, 0x00000001 },
-       { 0x001380,   1, 0x04, 0x00000000 },
-       { 0x001384,   4, 0x04, 0x00000001 },
-       { 0x001394,   1, 0x04, 0x00000000 },
-       { 0x00139c,   1, 0x04, 0x00000000 },
-       { 0x001398,   1, 0x04, 0x00000000 },
-       { 0x001594,   1, 0x04, 0x00000000 },
-       { 0x001598,   4, 0x04, 0x00000001 },
-       { 0x000f54,   3, 0x04, 0x00000000 },
-       { 0x0019bc,   1, 0x04, 0x00000000 },
-       { 0x000f9c,   2, 0x04, 0x00000000 },
-       { 0x0012cc,   1, 0x04, 0x00000000 },
-       { 0x0012e8,   1, 0x04, 0x00000000 },
-       { 0x00130c,   1, 0x04, 0x00000001 },
-       { 0x001360,   8, 0x04, 0x00000000 },
-       { 0x00133c,   2, 0x04, 0x00000001 },
-       { 0x001344,   1, 0x04, 0x00000002 },
-       { 0x001348,   2, 0x04, 0x00000001 },
-       { 0x001350,   1, 0x04, 0x00000002 },
-       { 0x001358,   1, 0x04, 0x00000001 },
-       { 0x0012e4,   1, 0x04, 0x00000000 },
-       { 0x00131c,   4, 0x04, 0x00000000 },
-       { 0x0019c0,   1, 0x04, 0x00000000 },
-       { 0x001140,   1, 0x04, 0x00000000 },
-       { 0x000dd0,   1, 0x04, 0x00000000 },
-       { 0x000dd4,   1, 0x04, 0x00000001 },
-       { 0x0002f4,   1, 0x04, 0x00000000 },
-       { 0x0019c4,   1, 0x04, 0x00000000 },
-       { 0x0019c8,   1, 0x04, 0x00001500 },
-       { 0x00135c,   1, 0x04, 0x00000000 },
-       { 0x000f90,   1, 0x04, 0x00000000 },
-       { 0x0019e0,   8, 0x04, 0x00000001 },
-       { 0x0019cc,   1, 0x04, 0x00000001 },
-       { 0x0015b8,   1, 0x04, 0x00000000 },
-       { 0x001a00,   1, 0x04, 0x00001111 },
-       { 0x001a04,   7, 0x04, 0x00000000 },
-       { 0x000d6c,   2, 0x04, 0xffff0000 },
-       { 0x0010f8,   1, 0x04, 0x00001010 },
-       { 0x000d80,   5, 0x04, 0x00000000 },
-       { 0x000da0,   1, 0x04, 0x00000000 },
-       { 0x0007a4,   2, 0x04, 0x00000000 },
-       { 0x001508,   1, 0x04, 0x80000000 },
-       { 0x00150c,   1, 0x04, 0x40000000 },
-       { 0x001668,   1, 0x04, 0x00000000 },
-       { 0x000318,   2, 0x04, 0x00000008 },
-       { 0x000d9c,   1, 0x04, 0x00000001 },
-       { 0x000f14,   1, 0x04, 0x00000000 },
-       { 0x000374,   1, 0x04, 0x00000000 },
-       { 0x000378,   1, 0x04, 0x0000000c },
-       { 0x0007dc,   1, 0x04, 0x00000000 },
-       { 0x00074c,   1, 0x04, 0x00000055 },
-       { 0x001420,   1, 0x04, 0x00000003 },
-       { 0x001008,   1, 0x04, 0x00000008 },
-       { 0x00100c,   1, 0x04, 0x00000040 },
-       { 0x001010,   1, 0x04, 0x0000012c },
-       { 0x000d60,   1, 0x04, 0x00000040 },
-       { 0x001018,   1, 0x04, 0x00000020 },
-       { 0x00101c,   1, 0x04, 0x00000001 },
-       { 0x001020,   1, 0x04, 0x00000020 },
-       { 0x001024,   1, 0x04, 0x00000001 },
-       { 0x001444,   3, 0x04, 0x00000000 },
-       { 0x000360,   1, 0x04, 0x20164010 },
-       { 0x000364,   1, 0x04, 0x00000020 },
-       { 0x000368,   1, 0x04, 0x00000000 },
-       { 0x000da8,   1, 0x04, 0x00000030 },
-       { 0x000de4,   1, 0x04, 0x00000000 },
-       { 0x000204,   1, 0x04, 0x00000006 },
-       { 0x0002d0,   1, 0x04, 0x003fffff },
-       { 0x001220,   1, 0x04, 0x00000005 },
-       { 0x000fdc,   1, 0x04, 0x00000000 },
-       { 0x000f98,   1, 0x04, 0x00400008 },
-       { 0x001284,   1, 0x04, 0x08000080 },
-       { 0x001450,   1, 0x04, 0x00400008 },
-       { 0x001454,   1, 0x04, 0x08000080 },
-       { 0x000214,   1, 0x04, 0x00000000 },
-       {}
-};
-
-static const struct nvc0_graph_pack
-gm107_grctx_pack_mthd[] = {
-       { gm107_grctx_init_b097_0, 0xb097 },
-       { nvc0_grctx_init_902d_0, 0x902d },
-       {}
-};
-
-static const struct nvc0_graph_init
-gm107_grctx_init_fe_0[] = {
-       { 0x404004,   8, 0x04, 0x00000000 },
-       { 0x404024,   1, 0x04, 0x0000e000 },
-       { 0x404028,   8, 0x04, 0x00000000 },
-       { 0x4040a8,   8, 0x04, 0x00000000 },
-       { 0x4040c8,   1, 0x04, 0xf800008f },
-       { 0x4040d0,   6, 0x04, 0x00000000 },
-       { 0x4040f8,   1, 0x04, 0x00000000 },
-       { 0x404100,  10, 0x04, 0x00000000 },
-       { 0x404130,   2, 0x04, 0x00000000 },
-       { 0x404150,   1, 0x04, 0x0000002e },
-       { 0x404154,   1, 0x04, 0x00000400 },
-       { 0x404158,   1, 0x04, 0x00000200 },
-       { 0x404164,   1, 0x04, 0x00000045 },
-       { 0x40417c,   2, 0x04, 0x00000000 },
-       { 0x404194,   1, 0x04, 0x01000700 },
-       { 0x4041a0,   4, 0x04, 0x00000000 },
-       { 0x404200,   4, 0x04, 0x00000000 },
-       {}
-};
-
-static const struct nvc0_graph_init
-gm107_grctx_init_ds_0[] = {
-       { 0x405800,   1, 0x04, 0x0f8001bf },
-       { 0x405830,   1, 0x04, 0x0aa01000 },
-       { 0x405834,   1, 0x04, 0x08000000 },
-       { 0x405838,   1, 0x04, 0x00000000 },
-       { 0x405854,   1, 0x04, 0x00000000 },
-       { 0x405870,   4, 0x04, 0x00000001 },
-       { 0x405a00,   2, 0x04, 0x00000000 },
-       { 0x405a18,   1, 0x04, 0x00000000 },
-       { 0x405a1c,   1, 0x04, 0x000000ff },
-       {}
-};
-
-static const struct nvc0_graph_init
-gm107_grctx_init_pd_0[] = {
-       { 0x406020,   1, 0x04, 0x07410001 },
-       { 0x406028,   4, 0x04, 0x00000001 },
-       { 0x4064a8,   1, 0x04, 0x00000000 },
-       { 0x4064ac,   1, 0x04, 0x00003fff },
-       { 0x4064b0,   3, 0x04, 0x00000000 },
-       { 0x4064c0,   1, 0x04, 0x80400280 },
-       { 0x4064c4,   1, 0x04, 0x0400ffff },
-       { 0x4064c8,   1, 0x04, 0x018001ff },
-       { 0x4064cc,   9, 0x04, 0x00000000 },
-       { 0x4064fc,   1, 0x04, 0x0000022a },
-       { 0x406500,   1, 0x04, 0x00000000 },
-       {}
-};
-
-static const struct nvc0_graph_init
-gm107_grctx_init_be_0[] = {
-       { 0x408800,   1, 0x04, 0x32802a3c },
-       { 0x408804,   1, 0x04, 0x00000040 },
-       { 0x408808,   1, 0x04, 0x1003e005 },
-       { 0x408840,   1, 0x04, 0x0000000b },
-       { 0x408900,   1, 0x04, 0xb080b801 },
-       { 0x408904,   1, 0x04, 0x63038001 },
-       { 0x408908,   1, 0x04, 0x02c8102f },
-       { 0x408980,   1, 0x04, 0x0000011d },
-       {}
-};
-
-static const struct nvc0_graph_pack
-gm107_grctx_pack_hub[] = {
-       { nvc0_grctx_init_main_0 },
-       { gm107_grctx_init_fe_0 },
-       { nvf0_grctx_init_pri_0 },
-       { nve4_grctx_init_memfmt_0 },
-       { gm107_grctx_init_ds_0 },
-       { nvf0_grctx_init_cwd_0 },
-       { gm107_grctx_init_pd_0 },
-       { nv108_grctx_init_rstr2d_0 },
-       { nve4_grctx_init_scc_0 },
-       { gm107_grctx_init_be_0 },
-       {}
-};
-
-static const struct nvc0_graph_init
-gm107_grctx_init_gpc_unk_0[] = {
-       { 0x418380,   1, 0x04, 0x00000056 },
-       {}
-};
-
-static const struct nvc0_graph_init
-gm107_grctx_init_gpc_unk_1[] = {
-       { 0x418600,   1, 0x04, 0x0000007f },
-       { 0x418684,   1, 0x04, 0x0000001f },
-       { 0x418700,   1, 0x04, 0x00000002 },
-       { 0x418704,   1, 0x04, 0x00000080 },
-       { 0x418708,   1, 0x04, 0x40000000 },
-       { 0x41870c,   2, 0x04, 0x00000000 },
-       {}
-};
-
-static const struct nvc0_graph_init
-gm107_grctx_init_setup_0[] = {
-       { 0x418800,   1, 0x04, 0x7006863a },
-       { 0x418810,   1, 0x04, 0x00000000 },
-       { 0x418828,   1, 0x04, 0x00000044 },
-       { 0x418830,   1, 0x04, 0x10000001 },
-       { 0x4188d8,   1, 0x04, 0x00000008 },
-       { 0x4188e0,   1, 0x04, 0x01000000 },
-       { 0x4188e8,   5, 0x04, 0x00000000 },
-       { 0x4188fc,   1, 0x04, 0x20100058 },
-       {}
-};
-
-static const struct nvc0_graph_init
-gm107_grctx_init_gpc_unk_2[] = {
-       { 0x418d24,   1, 0x04, 0x00000000 },
-       { 0x418e00,   1, 0x04, 0x90000000 },
-       { 0x418e24,   1, 0x04, 0x00000000 },
-       { 0x418e28,   1, 0x04, 0x00000030 },
-       { 0x418e30,   1, 0x04, 0x00000000 },
-       { 0x418e34,   1, 0x04, 0x00010000 },
-       { 0x418e38,   1, 0x04, 0x00000000 },
-       { 0x418e40,  22, 0x04, 0x00000000 },
-       { 0x418ea0,   2, 0x04, 0x00000000 },
-       {}
-};
-
-static const struct nvc0_graph_pack
-gm107_grctx_pack_gpc[] = {
-       { gm107_grctx_init_gpc_unk_0 },
-       { nv108_grctx_init_prop_0 },
-       { gm107_grctx_init_gpc_unk_1 },
-       { gm107_grctx_init_setup_0 },
-       { nvc0_grctx_init_zcull_0 },
-       { nv108_grctx_init_crstr_0 },
-       { nve4_grctx_init_gpm_0 },
-       { gm107_grctx_init_gpc_unk_2 },
-       { nvc0_grctx_init_gcc_0 },
-       {}
-};
-
-static const struct nvc0_graph_init
-gm107_grctx_init_tex_0[] = {
-       { 0x419a00,   1, 0x04, 0x000300f0 },
-       { 0x419a04,   1, 0x04, 0x00000005 },
-       { 0x419a08,   1, 0x04, 0x00000421 },
-       { 0x419a0c,   1, 0x04, 0x00120000 },
-       { 0x419a10,   1, 0x04, 0x00000000 },
-       { 0x419a14,   1, 0x04, 0x00002200 },
-       { 0x419a1c,   1, 0x04, 0x0000c000 },
-       { 0x419a20,   1, 0x04, 0x20008a00 },
-       { 0x419a30,   1, 0x04, 0x00000001 },
-       { 0x419a3c,   1, 0x04, 0x00000002 },
-       { 0x419ac4,   1, 0x04, 0x00000000 },
-       {}
-};
-
-static const struct nvc0_graph_init
-gm107_grctx_init_mpc_0[] = {
-       { 0x419c00,   1, 0x04, 0x0000001a },
-       { 0x419c04,   1, 0x04, 0x80000006 },
-       { 0x419c08,   1, 0x04, 0x00000002 },
-       { 0x419c20,   1, 0x04, 0x00000000 },
-       { 0x419c24,   1, 0x04, 0x00084210 },
-       { 0x419c28,   1, 0x04, 0x3efbefbe },
-       { 0x419c2c,   1, 0x04, 0x00000000 },
-       { 0x419c34,   1, 0x04, 0x01ff1ff3 },
-       { 0x419c3c,   1, 0x04, 0x00001919 },
-       {}
-};
-
-static const struct nvc0_graph_init
-gm107_grctx_init_l1c_0[] = {
-       { 0x419c84,   1, 0x04, 0x00000020 },
-       {}
-};
-
-static const struct nvc0_graph_init
-gm107_grctx_init_sm_0[] = {
-       { 0x419e04,   3, 0x04, 0x00000000 },
-       { 0x419e10,   1, 0x04, 0x00001c02 },
-       { 0x419e44,   1, 0x04, 0x00d3eff2 },
-       { 0x419e48,   1, 0x04, 0x00000000 },
-       { 0x419e4c,   1, 0x04, 0x0000007f },
-       { 0x419e50,   1, 0x04, 0x00000000 },
-       { 0x419e60,   4, 0x04, 0x00000000 },
-       { 0x419e74,  10, 0x04, 0x00000000 },
-       { 0x419eac,   1, 0x04, 0x0001cf8b },
-       { 0x419eb0,   1, 0x04, 0x00030300 },
-       { 0x419eb8,   1, 0x04, 0x00000000 },
-       { 0x419ef0,  24, 0x04, 0x00000000 },
-       { 0x419f68,   2, 0x04, 0x00000000 },
-       { 0x419f70,   1, 0x04, 0x00000020 },
-       { 0x419f78,   1, 0x04, 0x000003eb },
-       { 0x419f7c,   1, 0x04, 0x00000000 },
-       {}
-};
-
-static const struct nvc0_graph_pack
-gm107_grctx_pack_tpc[] = {
-       { nvd7_grctx_init_pe_0 },
-       { gm107_grctx_init_tex_0 },
-       { gm107_grctx_init_mpc_0 },
-       { gm107_grctx_init_l1c_0 },
-       { gm107_grctx_init_sm_0 },
-       {}
-};
-
-static const struct nvc0_graph_init
-gm107_grctx_init_cbm_0[] = {
-       { 0x41bec0,   1, 0x04, 0x00000000 },
-       { 0x41bec4,   1, 0x04, 0x01050000 },
-       { 0x41bee4,   1, 0x04, 0x00000000 },
-       { 0x41bef0,   1, 0x04, 0x000003ff },
-       { 0x41bef4,   2, 0x04, 0x00000000 },
-       {}
-};
-
-static const struct nvc0_graph_init
-gm107_grctx_init_wwdx_0[] = {
-       { 0x41bf00,   1, 0x04, 0x0a418820 },
-       { 0x41bf04,   1, 0x04, 0x062080e6 },
-       { 0x41bf08,   1, 0x04, 0x020398a4 },
-       { 0x41bf0c,   1, 0x04, 0x0e629062 },
-       { 0x41bf10,   1, 0x04, 0x0a418820 },
-       { 0x41bf14,   1, 0x04, 0x000000e6 },
-       { 0x41bfd0,   1, 0x04, 0x00900103 },
-       { 0x41bfe0,   1, 0x04, 0x80000000 },
-       { 0x41bfe4,   1, 0x04, 0x00000000 },
-       {}
-};
-
-static const struct nvc0_graph_pack
-gm107_grctx_pack_ppc[] = {
-       { nve4_grctx_init_pes_0 },
-       { gm107_grctx_init_cbm_0 },
-       { gm107_grctx_init_wwdx_0 },
-       {}
-};
-
-/*******************************************************************************
- * PGRAPH context implementation
- ******************************************************************************/
-
-static void
-gm107_grctx_generate_bundle(struct nvc0_grctx *info)
-{
-       const struct nvc0_grctx_oclass *impl = nvc0_grctx_impl(info->priv);
-       const u32 state_limit = min(impl->bundle_min_gpm_fifo_depth,
-                                   impl->bundle_size / 0x20);
-       const u32 token_limit = impl->bundle_token_limit;
-       const u32 access = NV_MEM_ACCESS_RW | NV_MEM_ACCESS_SYS;
-       const int s = 8;
-       const int b = mmio_vram(info, impl->bundle_size, (1 << s), access);
-       mmio_refn(info, 0x408004, 0x00000000, s, b);
-       mmio_refn(info, 0x408008, 0x80000000 | (impl->bundle_size >> s), 0, b);
-       mmio_refn(info, 0x418e24, 0x00000000, s, b);
-       mmio_refn(info, 0x418e28, 0x80000000 | (impl->bundle_size >> s), 0, b);
-       mmio_wr32(info, 0x4064c8, (state_limit << 16) | token_limit);
-}
-
-static void
-gm107_grctx_generate_pagepool(struct nvc0_grctx *info)
-{
-       const struct nvc0_grctx_oclass *impl = nvc0_grctx_impl(info->priv);
-       const u32 access = NV_MEM_ACCESS_RW | NV_MEM_ACCESS_SYS;
-       const int s = 8;
-       const int b = mmio_vram(info, impl->pagepool_size, (1 << s), access);
-       mmio_refn(info, 0x40800c, 0x00000000, s, b);
-       mmio_wr32(info, 0x408010, 0x80000000);
-       mmio_refn(info, 0x419004, 0x00000000, s, b);
-       mmio_wr32(info, 0x419008, 0x00000000);
-       mmio_wr32(info, 0x4064cc, 0x80000000);
-       mmio_wr32(info, 0x418e30, 0x80000000); /* guess at it being related */
-}
-
-static void
-gm107_grctx_generate_attrib(struct nvc0_grctx *info)
-{
-       struct nvc0_graph_priv *priv = info->priv;
-       const struct nvc0_grctx_oclass *impl = (void *)nvc0_grctx_impl(priv);
-       const u32  alpha = impl->alpha_nr;
-       const u32 attrib = impl->attrib_nr;
-       const u32   size = 0x20 * (impl->attrib_nr_max + impl->alpha_nr_max);
-       const u32 access = NV_MEM_ACCESS_RW;
-       const int s = 12;
-       const int b = mmio_vram(info, size * priv->tpc_total, (1 << s), access);
-       const int max_batches = 0xffff;
-       u32 bo = 0;
-       u32 ao = bo + impl->attrib_nr_max * priv->tpc_total;
-       int gpc, ppc, n = 0;
-
-       mmio_refn(info, 0x418810, 0x80000000, s, b);
-       mmio_refn(info, 0x419848, 0x10000000, s, b);
-       mmio_refn(info, 0x419c2c, 0x10000000, s, b);
-       mmio_wr32(info, 0x405830, (attrib << 16) | alpha);
-       mmio_wr32(info, 0x4064c4, ((alpha / 4) << 16) | max_batches);
-
-       for (gpc = 0; gpc < priv->gpc_nr; gpc++) {
-               for (ppc = 0; ppc < priv->ppc_nr[gpc]; ppc++, n++) {
-                       const u32 as =  alpha * priv->ppc_tpc_nr[gpc][ppc];
-                       const u32 bs = attrib * priv->ppc_tpc_nr[gpc][ppc];
-                       const u32 u = 0x418ea0 + (n * 0x04);
-                       const u32 o = PPC_UNIT(gpc, ppc, 0);
-                       mmio_wr32(info, o + 0xc0, bs);
-                       mmio_wr32(info, o + 0xf4, bo);
-                       bo += impl->attrib_nr_max * priv->ppc_tpc_nr[gpc][ppc];
-                       mmio_wr32(info, o + 0xe4, as);
-                       mmio_wr32(info, o + 0xf8, ao);
-                       ao += impl->alpha_nr_max * priv->ppc_tpc_nr[gpc][ppc];
-                       mmio_wr32(info, u, (0x715 /*XXX*/ << 16) | bs);
-               }
-       }
-}
-
-static void
-gm107_grctx_generate_tpcid(struct nvc0_graph_priv *priv)
-{
-       int gpc, tpc, id;
-
-       for (tpc = 0, id = 0; tpc < 4; tpc++) {
-               for (gpc = 0; gpc < priv->gpc_nr; gpc++) {
-                       if (tpc < priv->tpc_nr[gpc]) {
-                               nv_wr32(priv, TPC_UNIT(gpc, tpc, 0x698), id);
-                               nv_wr32(priv, GPC_UNIT(gpc, 0x0c10 + tpc * 4), id);
-                               nv_wr32(priv, TPC_UNIT(gpc, tpc, 0x088), id);
-                               id++;
-                       }
-
-                       nv_wr32(priv, GPC_UNIT(gpc, 0x0c08), priv->tpc_nr[gpc]);
-                       nv_wr32(priv, GPC_UNIT(gpc, 0x0c8c), priv->tpc_nr[gpc]);
-               }
-       }
-}
-
-static void
-gm107_grctx_generate_main(struct nvc0_graph_priv *priv, struct nvc0_grctx *info)
-{
-       struct nvc0_grctx_oclass *oclass = (void *)nv_engine(priv)->cclass;
-       int i;
-
-       nvc0_graph_mmio(priv, oclass->hub);
-       nvc0_graph_mmio(priv, oclass->gpc);
-       nvc0_graph_mmio(priv, oclass->zcull);
-       nvc0_graph_mmio(priv, oclass->tpc);
-       nvc0_graph_mmio(priv, oclass->ppc);
-
-       nv_wr32(priv, 0x404154, 0x00000000);
-
-       oclass->bundle(info);
-       oclass->pagepool(info);
-       oclass->attrib(info);
-       oclass->unkn(priv);
-
-       gm107_grctx_generate_tpcid(priv);
-       nvc0_grctx_generate_r406028(priv);
-       nve4_grctx_generate_r418bb8(priv);
-       nvc0_grctx_generate_r406800(priv);
-
-       nv_wr32(priv, 0x4064d0, 0x00000001);
-       for (i = 1; i < 8; i++)
-               nv_wr32(priv, 0x4064d0 + (i * 0x04), 0x00000000);
-       nv_wr32(priv, 0x406500, 0x00000001);
-
-       nv_wr32(priv, 0x405b00, (priv->tpc_total << 8) | priv->gpc_nr);
-
-       if (priv->gpc_nr == 1) {
-               nv_mask(priv, 0x408850, 0x0000000f, priv->tpc_nr[0]);
-               nv_mask(priv, 0x408958, 0x0000000f, priv->tpc_nr[0]);
-       } else {
-               nv_mask(priv, 0x408850, 0x0000000f, priv->gpc_nr);
-               nv_mask(priv, 0x408958, 0x0000000f, priv->gpc_nr);
-       }
-
-       nvc0_graph_icmd(priv, oclass->icmd);
-       nv_wr32(priv, 0x404154, 0x00000400);
-       nvc0_graph_mthd(priv, oclass->mthd);
-
-       nv_mask(priv, 0x419e00, 0x00808080, 0x00808080);
-       nv_mask(priv, 0x419ccc, 0x80000000, 0x80000000);
-       nv_mask(priv, 0x419f80, 0x80000000, 0x80000000);
-       nv_mask(priv, 0x419f88, 0x80000000, 0x80000000);
-}
-
-struct nouveau_oclass *
-gm107_grctx_oclass = &(struct nvc0_grctx_oclass) {
-       .base.handle = NV_ENGCTX(GR, 0x08),
-       .base.ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nvc0_graph_context_ctor,
-               .dtor = nvc0_graph_context_dtor,
-               .init = _nouveau_graph_context_init,
-               .fini = _nouveau_graph_context_fini,
-               .rd32 = _nouveau_graph_context_rd32,
-               .wr32 = _nouveau_graph_context_wr32,
-       },
-       .main  = gm107_grctx_generate_main,
-       .unkn  = nve4_grctx_generate_unkn,
-       .hub   = gm107_grctx_pack_hub,
-       .gpc   = gm107_grctx_pack_gpc,
-       .zcull = nvc0_grctx_pack_zcull,
-       .tpc   = gm107_grctx_pack_tpc,
-       .ppc   = gm107_grctx_pack_ppc,
-       .icmd  = gm107_grctx_pack_icmd,
-       .mthd  = gm107_grctx_pack_mthd,
-       .bundle = gm107_grctx_generate_bundle,
-       .bundle_size = 0x3000,
-       .bundle_min_gpm_fifo_depth = 0x180,
-       .bundle_token_limit = 0x2c0,
-       .pagepool = gm107_grctx_generate_pagepool,
-       .pagepool_size = 0x8000,
-       .attrib = gm107_grctx_generate_attrib,
-       .attrib_nr_max = 0xff0,
-       .attrib_nr = 0xaa0,
-       .alpha_nr_max = 0x1800,
-       .alpha_nr = 0x1000,
-}.base;
diff --git a/drivers/gpu/drm/nouveau/core/engine/graph/ctxnv108.c b/drivers/gpu/drm/nouveau/core/engine/graph/ctxnv108.c
deleted file mode 100644 (file)
index ce252ad..0000000
+++ /dev/null
@@ -1,565 +0,0 @@
-/*
- * Copyright 2013 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 <bskeggs@redhat.com>
- */
-
-#include "ctxnvc0.h"
-
-/*******************************************************************************
- * PGRAPH context register lists
- ******************************************************************************/
-
-static const struct nvc0_graph_init
-nv108_grctx_init_icmd_0[] = {
-       { 0x001000,   1, 0x01, 0x00000004 },
-       { 0x000039,   3, 0x01, 0x00000000 },
-       { 0x0000a9,   1, 0x01, 0x0000ffff },
-       { 0x000038,   1, 0x01, 0x0fac6881 },
-       { 0x00003d,   1, 0x01, 0x00000001 },
-       { 0x0000e8,   8, 0x01, 0x00000400 },
-       { 0x000078,   8, 0x01, 0x00000300 },
-       { 0x000050,   1, 0x01, 0x00000011 },
-       { 0x000058,   8, 0x01, 0x00000008 },
-       { 0x000208,   8, 0x01, 0x00000001 },
-       { 0x000081,   1, 0x01, 0x00000001 },
-       { 0x000085,   1, 0x01, 0x00000004 },
-       { 0x000088,   1, 0x01, 0x00000400 },
-       { 0x000090,   1, 0x01, 0x00000300 },
-       { 0x000098,   1, 0x01, 0x00001001 },
-       { 0x0000e3,   1, 0x01, 0x00000001 },
-       { 0x0000da,   1, 0x01, 0x00000001 },
-       { 0x0000f8,   1, 0x01, 0x00000003 },
-       { 0x0000fa,   1, 0x01, 0x00000001 },
-       { 0x00009f,   4, 0x01, 0x0000ffff },
-       { 0x0000b1,   1, 0x01, 0x00000001 },
-       { 0x0000ad,   1, 0x01, 0x0000013e },
-       { 0x0000e1,   1, 0x01, 0x00000010 },
-       { 0x000290,  16, 0x01, 0x00000000 },
-       { 0x0003b0,  16, 0x01, 0x00000000 },
-       { 0x0002a0,  16, 0x01, 0x00000000 },
-       { 0x000420,  16, 0x01, 0x00000000 },
-       { 0x0002b0,  16, 0x01, 0x00000000 },
-       { 0x000430,  16, 0x01, 0x00000000 },
-       { 0x0002c0,  16, 0x01, 0x00000000 },
-       { 0x0004d0,  16, 0x01, 0x00000000 },
-       { 0x000720,  16, 0x01, 0x00000000 },
-       { 0x0008c0,  16, 0x01, 0x00000000 },
-       { 0x000890,  16, 0x01, 0x00000000 },
-       { 0x0008e0,  16, 0x01, 0x00000000 },
-       { 0x0008a0,  16, 0x01, 0x00000000 },
-       { 0x0008f0,  16, 0x01, 0x00000000 },
-       { 0x00094c,   1, 0x01, 0x000000ff },
-       { 0x00094d,   1, 0x01, 0xffffffff },
-       { 0x00094e,   1, 0x01, 0x00000002 },
-       { 0x0002ec,   1, 0x01, 0x00000001 },
-       { 0x0002f2,   2, 0x01, 0x00000001 },
-       { 0x0002f5,   1, 0x01, 0x00000001 },
-       { 0x0002f7,   1, 0x01, 0x00000001 },
-       { 0x000303,   1, 0x01, 0x00000001 },
-       { 0x0002e6,   1, 0x01, 0x00000001 },
-       { 0x000466,   1, 0x01, 0x00000052 },
-       { 0x000301,   1, 0x01, 0x3f800000 },
-       { 0x000304,   1, 0x01, 0x30201000 },
-       { 0x000305,   1, 0x01, 0x70605040 },
-       { 0x000306,   1, 0x01, 0xb8a89888 },
-       { 0x000307,   1, 0x01, 0xf8e8d8c8 },
-       { 0x00030a,   1, 0x01, 0x00ffff00 },
-       { 0x00030b,   1, 0x01, 0x0000001a },
-       { 0x00030c,   1, 0x01, 0x00000001 },
-       { 0x000318,   1, 0x01, 0x00000001 },
-       { 0x000340,   1, 0x01, 0x00000000 },
-       { 0x000375,   1, 0x01, 0x00000001 },
-       { 0x00037d,   1, 0x01, 0x00000006 },
-       { 0x0003a0,   1, 0x01, 0x00000002 },
-       { 0x0003aa,   1, 0x01, 0x00000001 },
-       { 0x0003a9,   1, 0x01, 0x00000001 },
-       { 0x000380,   1, 0x01, 0x00000001 },
-       { 0x000383,   1, 0x01, 0x00000011 },
-       { 0x000360,   1, 0x01, 0x00000040 },
-       { 0x000366,   2, 0x01, 0x00000000 },
-       { 0x000368,   1, 0x01, 0x00000fff },
-       { 0x000370,   2, 0x01, 0x00000000 },
-       { 0x000372,   1, 0x01, 0x000fffff },
-       { 0x00037a,   1, 0x01, 0x00000012 },
-       { 0x000619,   1, 0x01, 0x00000003 },
-       { 0x000811,   1, 0x01, 0x00000003 },
-       { 0x000812,   1, 0x01, 0x00000004 },
-       { 0x000813,   1, 0x01, 0x00000006 },
-       { 0x000814,   1, 0x01, 0x00000008 },
-       { 0x000815,   1, 0x01, 0x0000000b },
-       { 0x000800,   6, 0x01, 0x00000001 },
-       { 0x000632,   1, 0x01, 0x00000001 },
-       { 0x000633,   1, 0x01, 0x00000002 },
-       { 0x000634,   1, 0x01, 0x00000003 },
-       { 0x000635,   1, 0x01, 0x00000004 },
-       { 0x000654,   1, 0x01, 0x3f800000 },
-       { 0x000657,   1, 0x01, 0x3f800000 },
-       { 0x000655,   2, 0x01, 0x3f800000 },
-       { 0x0006cd,   1, 0x01, 0x3f800000 },
-       { 0x0007f5,   1, 0x01, 0x3f800000 },
-       { 0x0007dc,   1, 0x01, 0x39291909 },
-       { 0x0007dd,   1, 0x01, 0x79695949 },
-       { 0x0007de,   1, 0x01, 0xb9a99989 },
-       { 0x0007df,   1, 0x01, 0xf9e9d9c9 },
-       { 0x0007e8,   1, 0x01, 0x00003210 },
-       { 0x0007e9,   1, 0x01, 0x00007654 },
-       { 0x0007ea,   1, 0x01, 0x00000098 },
-       { 0x0007ec,   1, 0x01, 0x39291909 },
-       { 0x0007ed,   1, 0x01, 0x79695949 },
-       { 0x0007ee,   1, 0x01, 0xb9a99989 },
-       { 0x0007ef,   1, 0x01, 0xf9e9d9c9 },
-       { 0x0007f0,   1, 0x01, 0x00003210 },
-       { 0x0007f1,   1, 0x01, 0x00007654 },
-       { 0x0007f2,   1, 0x01, 0x00000098 },
-       { 0x0005a5,   1, 0x01, 0x00000001 },
-       { 0x000980, 128, 0x01, 0x00000000 },
-       { 0x000468,   1, 0x01, 0x00000004 },
-       { 0x00046c,   1, 0x01, 0x00000001 },
-       { 0x000470,  96, 0x01, 0x00000000 },
-       { 0x000510,  16, 0x01, 0x3f800000 },
-       { 0x000520,   1, 0x01, 0x000002b6 },
-       { 0x000529,   1, 0x01, 0x00000001 },
-       { 0x000530,  16, 0x01, 0xffff0000 },
-       { 0x000585,   1, 0x01, 0x0000003f },
-       { 0x000576,   1, 0x01, 0x00000003 },
-       { 0x00057b,   1, 0x01, 0x00000059 },
-       { 0x000586,   1, 0x01, 0x00000040 },
-       { 0x000582,   2, 0x01, 0x00000080 },
-       { 0x0005c2,   1, 0x01, 0x00000001 },
-       { 0x000638,   2, 0x01, 0x00000001 },
-       { 0x00063a,   1, 0x01, 0x00000002 },
-       { 0x00063b,   2, 0x01, 0x00000001 },
-       { 0x00063d,   1, 0x01, 0x00000002 },
-       { 0x00063e,   1, 0x01, 0x00000001 },
-       { 0x0008b8,   8, 0x01, 0x00000001 },
-       { 0x000900,   8, 0x01, 0x00000001 },
-       { 0x000908,   8, 0x01, 0x00000002 },
-       { 0x000910,  16, 0x01, 0x00000001 },
-       { 0x000920,   8, 0x01, 0x00000002 },
-       { 0x000928,   8, 0x01, 0x00000001 },
-       { 0x000662,   1, 0x01, 0x00000001 },
-       { 0x000648,   9, 0x01, 0x00000001 },
-       { 0x000658,   1, 0x01, 0x0000000f },
-       { 0x0007ff,   1, 0x01, 0x0000000a },
-       { 0x00066a,   1, 0x01, 0x40000000 },
-       { 0x00066b,   1, 0x01, 0x10000000 },
-       { 0x00066c,   2, 0x01, 0xffff0000 },
-       { 0x0007af,   2, 0x01, 0x00000008 },
-       { 0x0007f6,   1, 0x01, 0x00000001 },
-       { 0x00080b,   1, 0x01, 0x00000002 },
-       { 0x0006b2,   1, 0x01, 0x00000055 },
-       { 0x0007ad,   1, 0x01, 0x00000003 },
-       { 0x000937,   1, 0x01, 0x00000001 },
-       { 0x000971,   1, 0x01, 0x00000008 },
-       { 0x000972,   1, 0x01, 0x00000040 },
-       { 0x000973,   1, 0x01, 0x0000012c },
-       { 0x00097c,   1, 0x01, 0x00000040 },
-       { 0x000979,   1, 0x01, 0x00000003 },
-       { 0x000975,   1, 0x01, 0x00000020 },
-       { 0x000976,   1, 0x01, 0x00000001 },
-       { 0x000977,   1, 0x01, 0x00000020 },
-       { 0x000978,   1, 0x01, 0x00000001 },
-       { 0x000957,   1, 0x01, 0x00000003 },
-       { 0x00095e,   1, 0x01, 0x20164010 },
-       { 0x00095f,   1, 0x01, 0x00000020 },
-       { 0x000a0d,   1, 0x01, 0x00000006 },
-       { 0x00097d,   1, 0x01, 0x00000020 },
-       { 0x000683,   1, 0x01, 0x00000006 },
-       { 0x000685,   1, 0x01, 0x003fffff },
-       { 0x000687,   1, 0x01, 0x003fffff },
-       { 0x0006a0,   1, 0x01, 0x00000005 },
-       { 0x000840,   1, 0x01, 0x00400008 },
-       { 0x000841,   1, 0x01, 0x08000080 },
-       { 0x000842,   1, 0x01, 0x00400008 },
-       { 0x000843,   1, 0x01, 0x08000080 },
-       { 0x0006aa,   1, 0x01, 0x00000001 },
-       { 0x0006ab,   1, 0x01, 0x00000002 },
-       { 0x0006ac,   1, 0x01, 0x00000080 },
-       { 0x0006ad,   2, 0x01, 0x00000100 },
-       { 0x0006b1,   1, 0x01, 0x00000011 },
-       { 0x0006bb,   1, 0x01, 0x000000cf },
-       { 0x0006ce,   1, 0x01, 0x2a712488 },
-       { 0x000739,   1, 0x01, 0x4085c000 },
-       { 0x00073a,   1, 0x01, 0x00000080 },
-       { 0x000786,   1, 0x01, 0x80000100 },
-       { 0x00073c,   1, 0x01, 0x00010100 },
-       { 0x00073d,   1, 0x01, 0x02800000 },
-       { 0x000787,   1, 0x01, 0x000000cf },
-       { 0x00078c,   1, 0x01, 0x00000008 },
-       { 0x000792,   1, 0x01, 0x00000001 },
-       { 0x000794,   3, 0x01, 0x00000001 },
-       { 0x000797,   1, 0x01, 0x000000cf },
-       { 0x000836,   1, 0x01, 0x00000001 },
-       { 0x00079a,   1, 0x01, 0x00000002 },
-       { 0x000833,   1, 0x01, 0x04444480 },
-       { 0x0007a1,   1, 0x01, 0x00000001 },
-       { 0x0007a3,   3, 0x01, 0x00000001 },
-       { 0x000831,   1, 0x01, 0x00000004 },
-       { 0x000b07,   1, 0x01, 0x00000002 },
-       { 0x000b08,   2, 0x01, 0x00000100 },
-       { 0x000b0a,   1, 0x01, 0x00000001 },
-       { 0x000a04,   1, 0x01, 0x000000ff },
-       { 0x000a0b,   1, 0x01, 0x00000040 },
-       { 0x00097f,   1, 0x01, 0x00000100 },
-       { 0x000a02,   1, 0x01, 0x00000001 },
-       { 0x000809,   1, 0x01, 0x00000007 },
-       { 0x00c221,   1, 0x01, 0x00000040 },
-       { 0x00c1b0,   8, 0x01, 0x0000000f },
-       { 0x00c1b8,   1, 0x01, 0x0fac6881 },
-       { 0x00c1b9,   1, 0x01, 0x00fac688 },
-       { 0x00c401,   1, 0x01, 0x00000001 },
-       { 0x00c402,   1, 0x01, 0x00010001 },
-       { 0x00c403,   2, 0x01, 0x00000001 },
-       { 0x00c40e,   1, 0x01, 0x00000020 },
-       { 0x00c500,   1, 0x01, 0x00000003 },
-       { 0x01e100,   1, 0x01, 0x00000001 },
-       { 0x001000,   1, 0x01, 0x00000002 },
-       { 0x0006aa,   1, 0x01, 0x00000001 },
-       { 0x0006ad,   2, 0x01, 0x00000100 },
-       { 0x0006b1,   1, 0x01, 0x00000011 },
-       { 0x00078c,   1, 0x01, 0x00000008 },
-       { 0x000792,   1, 0x01, 0x00000001 },
-       { 0x000794,   3, 0x01, 0x00000001 },
-       { 0x000797,   1, 0x01, 0x000000cf },
-       { 0x00079a,   1, 0x01, 0x00000002 },
-       { 0x0007a1,   1, 0x01, 0x00000001 },
-       { 0x0007a3,   3, 0x01, 0x00000001 },
-       { 0x000831,   1, 0x01, 0x00000004 },
-       { 0x01e100,   1, 0x01, 0x00000001 },
-       { 0x001000,   1, 0x01, 0x00000008 },
-       { 0x000039,   3, 0x01, 0x00000000 },
-       { 0x000380,   1, 0x01, 0x00000001 },
-       { 0x000366,   2, 0x01, 0x00000000 },
-       { 0x000368,   1, 0x01, 0x00000fff },
-       { 0x000370,   2, 0x01, 0x00000000 },
-       { 0x000372,   1, 0x01, 0x000fffff },
-       { 0x000813,   1, 0x01, 0x00000006 },
-       { 0x000814,   1, 0x01, 0x00000008 },
-       { 0x000957,   1, 0x01, 0x00000003 },
-       { 0x000b07,   1, 0x01, 0x00000002 },
-       { 0x000b08,   2, 0x01, 0x00000100 },
-       { 0x000b0a,   1, 0x01, 0x00000001 },
-       { 0x000a04,   1, 0x01, 0x000000ff },
-       { 0x000a0b,   1, 0x01, 0x00000040 },
-       { 0x00097f,   1, 0x01, 0x00000100 },
-       { 0x000a02,   1, 0x01, 0x00000001 },
-       { 0x000809,   1, 0x01, 0x00000007 },
-       { 0x00c221,   1, 0x01, 0x00000040 },
-       { 0x00c401,   1, 0x01, 0x00000001 },
-       { 0x00c402,   1, 0x01, 0x00010001 },
-       { 0x00c403,   2, 0x01, 0x00000001 },
-       { 0x00c40e,   1, 0x01, 0x00000020 },
-       { 0x00c500,   1, 0x01, 0x00000003 },
-       { 0x01e100,   1, 0x01, 0x00000001 },
-       { 0x001000,   1, 0x01, 0x00000001 },
-       { 0x000b07,   1, 0x01, 0x00000002 },
-       { 0x000b08,   2, 0x01, 0x00000100 },
-       { 0x000b0a,   1, 0x01, 0x00000001 },
-       { 0x01e100,   1, 0x01, 0x00000001 },
-       {}
-};
-
-static const struct nvc0_graph_pack
-nv108_grctx_pack_icmd[] = {
-       { nv108_grctx_init_icmd_0 },
-       {}
-};
-
-static const struct nvc0_graph_init
-nv108_grctx_init_fe_0[] = {
-       { 0x404004,   8, 0x04, 0x00000000 },
-       { 0x404024,   1, 0x04, 0x0000e000 },
-       { 0x404028,   8, 0x04, 0x00000000 },
-       { 0x4040a8,   8, 0x04, 0x00000000 },
-       { 0x4040c8,   1, 0x04, 0xf800008f },
-       { 0x4040d0,   6, 0x04, 0x00000000 },
-       { 0x4040e8,   1, 0x04, 0x00001000 },
-       { 0x4040f8,   1, 0x04, 0x00000000 },
-       { 0x404100,  10, 0x04, 0x00000000 },
-       { 0x404130,   2, 0x04, 0x00000000 },
-       { 0x404138,   1, 0x04, 0x20000040 },
-       { 0x404150,   1, 0x04, 0x0000002e },
-       { 0x404154,   1, 0x04, 0x00000400 },
-       { 0x404158,   1, 0x04, 0x00000200 },
-       { 0x404164,   1, 0x04, 0x00000055 },
-       { 0x40417c,   2, 0x04, 0x00000000 },
-       { 0x404194,   1, 0x04, 0x01000700 },
-       { 0x4041a0,   4, 0x04, 0x00000000 },
-       { 0x404200,   1, 0x04, 0x0000a197 },
-       { 0x404204,   1, 0x04, 0x0000a1c0 },
-       { 0x404208,   1, 0x04, 0x0000a140 },
-       { 0x40420c,   1, 0x04, 0x0000902d },
-       {}
-};
-
-static const struct nvc0_graph_init
-nv108_grctx_init_ds_0[] = {
-       { 0x405800,   1, 0x04, 0x0f8000bf },
-       { 0x405830,   1, 0x04, 0x02180648 },
-       { 0x405834,   1, 0x04, 0x08000000 },
-       { 0x405838,   1, 0x04, 0x00000000 },
-       { 0x405854,   1, 0x04, 0x00000000 },
-       { 0x405870,   4, 0x04, 0x00000001 },
-       { 0x405a00,   2, 0x04, 0x00000000 },
-       { 0x405a18,   1, 0x04, 0x00000000 },
-       { 0x405a1c,   1, 0x04, 0x000000ff },
-       {}
-};
-
-static const struct nvc0_graph_init
-nv108_grctx_init_pd_0[] = {
-       { 0x406020,   1, 0x04, 0x034103c1 },
-       { 0x406028,   4, 0x04, 0x00000001 },
-       { 0x4064a8,   1, 0x04, 0x00000000 },
-       { 0x4064ac,   1, 0x04, 0x00003fff },
-       { 0x4064b0,   3, 0x04, 0x00000000 },
-       { 0x4064c0,   1, 0x04, 0x802000f0 },
-       { 0x4064c4,   1, 0x04, 0x0192ffff },
-       { 0x4064c8,   1, 0x04, 0x00c20200 },
-       { 0x4064cc,   9, 0x04, 0x00000000 },
-       { 0x4064fc,   1, 0x04, 0x0000022a },
-       {}
-};
-
-const struct nvc0_graph_init
-nv108_grctx_init_rstr2d_0[] = {
-       { 0x407804,   1, 0x04, 0x00000063 },
-       { 0x40780c,   1, 0x04, 0x0a418820 },
-       { 0x407810,   1, 0x04, 0x062080e6 },
-       { 0x407814,   1, 0x04, 0x020398a4 },
-       { 0x407818,   1, 0x04, 0x0e629062 },
-       { 0x40781c,   1, 0x04, 0x0a418820 },
-       { 0x407820,   1, 0x04, 0x000000e6 },
-       { 0x4078bc,   1, 0x04, 0x00000103 },
-       {}
-};
-
-static const struct nvc0_graph_init
-nv108_grctx_init_be_0[] = {
-       { 0x408800,   1, 0x04, 0x32802a3c },
-       { 0x408804,   1, 0x04, 0x00000040 },
-       { 0x408808,   1, 0x04, 0x1003e005 },
-       { 0x408840,   1, 0x04, 0x0000000b },
-       { 0x408900,   1, 0x04, 0xb080b801 },
-       { 0x408904,   1, 0x04, 0x62000001 },
-       { 0x408908,   1, 0x04, 0x02c8102f },
-       { 0x408980,   1, 0x04, 0x0000011d },
-       {}
-};
-
-static const struct nvc0_graph_pack
-nv108_grctx_pack_hub[] = {
-       { nvc0_grctx_init_main_0 },
-       { nv108_grctx_init_fe_0 },
-       { nvf0_grctx_init_pri_0 },
-       { nve4_grctx_init_memfmt_0 },
-       { nv108_grctx_init_ds_0 },
-       { nvf0_grctx_init_cwd_0 },
-       { nv108_grctx_init_pd_0 },
-       { nv108_grctx_init_rstr2d_0 },
-       { nve4_grctx_init_scc_0 },
-       { nv108_grctx_init_be_0 },
-       {}
-};
-
-const struct nvc0_graph_init
-nv108_grctx_init_prop_0[] = {
-       { 0x418400,   1, 0x04, 0x38005e00 },
-       { 0x418404,   1, 0x04, 0x71e0ffff },
-       { 0x41840c,   1, 0x04, 0x00001008 },
-       { 0x418410,   1, 0x04, 0x0fff0fff },
-       { 0x418414,   1, 0x04, 0x02200fff },
-       { 0x418450,   6, 0x04, 0x00000000 },
-       { 0x418468,   1, 0x04, 0x00000001 },
-       { 0x41846c,   2, 0x04, 0x00000000 },
-       {}
-};
-
-static const struct nvc0_graph_init
-nv108_grctx_init_gpc_unk_1[] = {
-       { 0x418600,   1, 0x04, 0x0000007f },
-       { 0x418684,   1, 0x04, 0x0000001f },
-       { 0x418700,   1, 0x04, 0x00000002 },
-       { 0x418704,   2, 0x04, 0x00000080 },
-       { 0x41870c,   2, 0x04, 0x00000000 },
-       {}
-};
-
-static const struct nvc0_graph_init
-nv108_grctx_init_setup_0[] = {
-       { 0x418800,   1, 0x04, 0x7006863a },
-       { 0x418808,   1, 0x04, 0x00000000 },
-       { 0x41880c,   1, 0x04, 0x00000030 },
-       { 0x418810,   1, 0x04, 0x00000000 },
-       { 0x418828,   1, 0x04, 0x00000044 },
-       { 0x418830,   1, 0x04, 0x10000001 },
-       { 0x4188d8,   1, 0x04, 0x00000008 },
-       { 0x4188e0,   1, 0x04, 0x01000000 },
-       { 0x4188e8,   5, 0x04, 0x00000000 },
-       { 0x4188fc,   1, 0x04, 0x20100058 },
-       {}
-};
-
-const struct nvc0_graph_init
-nv108_grctx_init_crstr_0[] = {
-       { 0x418b00,   1, 0x04, 0x0000001e },
-       { 0x418b08,   1, 0x04, 0x0a418820 },
-       { 0x418b0c,   1, 0x04, 0x062080e6 },
-       { 0x418b10,   1, 0x04, 0x020398a4 },
-       { 0x418b14,   1, 0x04, 0x0e629062 },
-       { 0x418b18,   1, 0x04, 0x0a418820 },
-       { 0x418b1c,   1, 0x04, 0x000000e6 },
-       { 0x418bb8,   1, 0x04, 0x00000103 },
-       {}
-};
-
-static const struct nvc0_graph_init
-nv108_grctx_init_gpm_0[] = {
-       { 0x418c08,   1, 0x04, 0x00000001 },
-       { 0x418c10,   8, 0x04, 0x00000000 },
-       { 0x418c40,   1, 0x04, 0xffffffff },
-       { 0x418c6c,   1, 0x04, 0x00000001 },
-       { 0x418c80,   1, 0x04, 0x2020000c },
-       { 0x418c8c,   1, 0x04, 0x00000001 },
-       {}
-};
-
-static const struct nvc0_graph_pack
-nv108_grctx_pack_gpc[] = {
-       { nvc0_grctx_init_gpc_unk_0 },
-       { nv108_grctx_init_prop_0 },
-       { nv108_grctx_init_gpc_unk_1 },
-       { nv108_grctx_init_setup_0 },
-       { nvc0_grctx_init_zcull_0 },
-       { nv108_grctx_init_crstr_0 },
-       { nv108_grctx_init_gpm_0 },
-       { nvf0_grctx_init_gpc_unk_2 },
-       { nvc0_grctx_init_gcc_0 },
-       {}
-};
-
-static const struct nvc0_graph_init
-nv108_grctx_init_tex_0[] = {
-       { 0x419a00,   1, 0x04, 0x000100f0 },
-       { 0x419a04,   1, 0x04, 0x00000001 },
-       { 0x419a08,   1, 0x04, 0x00000421 },
-       { 0x419a0c,   1, 0x04, 0x00120000 },
-       { 0x419a10,   1, 0x04, 0x00000000 },
-       { 0x419a14,   1, 0x04, 0x00000200 },
-       { 0x419a1c,   1, 0x04, 0x0000c000 },
-       { 0x419a20,   1, 0x04, 0x00000800 },
-       { 0x419a30,   1, 0x04, 0x00000001 },
-       { 0x419ac4,   1, 0x04, 0x0037f440 },
-       {}
-};
-
-static const struct nvc0_graph_init
-nv108_grctx_init_sm_0[] = {
-       { 0x419e04,   1, 0x04, 0x00000000 },
-       { 0x419e08,   1, 0x04, 0x0000001d },
-       { 0x419e0c,   1, 0x04, 0x00000000 },
-       { 0x419e10,   1, 0x04, 0x00001c02 },
-       { 0x419e44,   1, 0x04, 0x0013eff2 },
-       { 0x419e48,   1, 0x04, 0x00000000 },
-       { 0x419e4c,   1, 0x04, 0x0000007f },
-       { 0x419e50,   2, 0x04, 0x00000000 },
-       { 0x419e58,   1, 0x04, 0x00000001 },
-       { 0x419e5c,   3, 0x04, 0x00000000 },
-       { 0x419e68,   1, 0x04, 0x00000002 },
-       { 0x419e6c,  12, 0x04, 0x00000000 },
-       { 0x419eac,   1, 0x04, 0x00001f8f },
-       { 0x419eb0,   1, 0x04, 0x0db00d2f },
-       { 0x419eb8,   1, 0x04, 0x00000000 },
-       { 0x419ec8,   1, 0x04, 0x0001304f },
-       { 0x419f30,   4, 0x04, 0x00000000 },
-       { 0x419f40,   1, 0x04, 0x00000018 },
-       { 0x419f44,   3, 0x04, 0x00000000 },
-       { 0x419f58,   1, 0x04, 0x00000020 },
-       { 0x419f70,   1, 0x04, 0x00000000 },
-       { 0x419f78,   1, 0x04, 0x000001eb },
-       { 0x419f7c,   1, 0x04, 0x00000404 },
-       {}
-};
-
-static const struct nvc0_graph_pack
-nv108_grctx_pack_tpc[] = {
-       { nvd7_grctx_init_pe_0 },
-       { nv108_grctx_init_tex_0 },
-       { nvf0_grctx_init_mpc_0 },
-       { nvf0_grctx_init_l1c_0 },
-       { nv108_grctx_init_sm_0 },
-       {}
-};
-
-static const struct nvc0_graph_init
-nv108_grctx_init_cbm_0[] = {
-       { 0x41bec0,   1, 0x04, 0x10000000 },
-       { 0x41bec4,   1, 0x04, 0x00037f7f },
-       { 0x41bee4,   1, 0x04, 0x00000000 },
-       { 0x41bef0,   1, 0x04, 0x000003ff },
-       {}
-};
-
-static const struct nvc0_graph_pack
-nv108_grctx_pack_ppc[] = {
-       { nve4_grctx_init_pes_0 },
-       { nv108_grctx_init_cbm_0 },
-       { nvd7_grctx_init_wwdx_0 },
-       {}
-};
-
-/*******************************************************************************
- * PGRAPH context implementation
- ******************************************************************************/
-
-struct nouveau_oclass *
-nv108_grctx_oclass = &(struct nvc0_grctx_oclass) {
-       .base.handle = NV_ENGCTX(GR, 0x08),
-       .base.ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nvc0_graph_context_ctor,
-               .dtor = nvc0_graph_context_dtor,
-               .init = _nouveau_graph_context_init,
-               .fini = _nouveau_graph_context_fini,
-               .rd32 = _nouveau_graph_context_rd32,
-               .wr32 = _nouveau_graph_context_wr32,
-       },
-       .main  = nve4_grctx_generate_main,
-       .unkn  = nve4_grctx_generate_unkn,
-       .hub   = nv108_grctx_pack_hub,
-       .gpc   = nv108_grctx_pack_gpc,
-       .zcull = nvc0_grctx_pack_zcull,
-       .tpc   = nv108_grctx_pack_tpc,
-       .ppc   = nv108_grctx_pack_ppc,
-       .icmd  = nv108_grctx_pack_icmd,
-       .mthd  = nvf0_grctx_pack_mthd,
-       .bundle = nve4_grctx_generate_bundle,
-       .bundle_size = 0x3000,
-       .bundle_min_gpm_fifo_depth = 0xc2,
-       .bundle_token_limit = 0x200,
-       .pagepool = nve4_grctx_generate_pagepool,
-       .pagepool_size = 0x8000,
-       .attrib = nvd7_grctx_generate_attrib,
-       .attrib_nr_max = 0x324,
-       .attrib_nr = 0x218,
-       .alpha_nr_max = 0x7ff,
-       .alpha_nr = 0x648,
-}.base;
diff --git a/drivers/gpu/drm/nouveau/core/engine/graph/ctxnv40.c b/drivers/gpu/drm/nouveau/core/engine/graph/ctxnv40.c
deleted file mode 100644 (file)
index 7bbb1e1..0000000
+++ /dev/null
@@ -1,695 +0,0 @@
-/*
- * 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 <core/gpuobj.h>
-
-/* NVIDIA context programs handle a number of other conditions which are
- * not implemented in our versions.  It's not clear why NVIDIA context
- * programs have this code, nor whether it's strictly necessary for
- * correct operation.  We'll implement additional handling if/when we
- * discover it's necessary.
- *
- * - On context save, NVIDIA set 0x400314 bit 0 to 1 if the "3D state"
- *   flag is set, this gets saved into the context.
- * - On context save, the context program for all cards load nsource
- *   into a flag register and check for ILLEGAL_MTHD.  If it's set,
- *   opcode 0x60000d is called before resuming normal operation.
- * - Some context programs check more conditions than the above.  NV44
- *   checks: ((nsource & 0x0857) || (0x400718 & 0x0100) || (intr & 0x0001))
- *   and calls 0x60000d before resuming normal operation.
- * - At the very beginning of NVIDIA's context programs, flag 9 is checked
- *   and if true 0x800001 is called with count=0, pos=0, the flag is cleared
- *   and then the ctxprog is aborted.  It looks like a complicated NOP,
- *   its purpose is unknown.
- * - In the section of code that loads the per-vs state, NVIDIA check
- *   flag 10.  If it's set, they only transfer the small 0x300 byte block
- *   of state + the state for a single vs as opposed to the state for
- *   all vs units.  It doesn't seem likely that it'll occur in normal
- *   operation, especially seeing as it appears NVIDIA may have screwed
- *   up the ctxprogs for some cards and have an invalid instruction
- *   rather than a cp_lsr(ctx, dwords_for_1_vs_unit) instruction.
- * - There's a number of places where context offset 0 (where we place
- *   the PRAMIN offset of the context) is loaded into either 0x408000,
- *   0x408004 or 0x408008.  Not sure what's up there either.
- * - The ctxprogs for some cards save 0x400a00 again during the cleanup
- *   path for auto-loadctx.
- */
-
-#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_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_STATUS                ((3 * 32) + 0)
-#define CP_FLAG_STATUS_IDLE           0
-#define CP_FLAG_STATUS_BUSY           1
-#define CP_FLAG_AUTO_SAVE             ((3 * 32) + 4)
-#define CP_FLAG_AUTO_SAVE_NOT_PENDING 0
-#define CP_FLAG_AUTO_SAVE_PENDING     1
-#define CP_FLAG_AUTO_LOAD             ((3 * 32) + 5)
-#define CP_FLAG_AUTO_LOAD_NOT_PENDING 0
-#define CP_FLAG_AUTO_LOAD_PENDING     1
-#define CP_FLAG_UNK54                 ((3 * 32) + 6)
-#define CP_FLAG_UNK54_CLEAR           0
-#define CP_FLAG_UNK54_SET             1
-#define CP_FLAG_ALWAYS                ((3 * 32) + 8)
-#define CP_FLAG_ALWAYS_FALSE          0
-#define CP_FLAG_ALWAYS_TRUE           1
-#define CP_FLAG_UNK57                 ((3 * 32) + 9)
-#define CP_FLAG_UNK57_CLEAR           0
-#define CP_FLAG_UNK57_SET             1
-
-#define CP_CTX                   0x00100000
-#define CP_CTX_COUNT             0x000fc000
-#define CP_CTX_COUNT_SHIFT               14
-#define CP_CTX_REG               0x00003fff
-#define CP_LOAD_SR               0x00200000
-#define CP_LOAD_SR_VALUE         0x000fffff
-#define CP_BRA                   0x00400000
-#define CP_BRA_IP                0x0000ff00
-#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_NEXT_TO_SWAP          0x00600007
-#define CP_NEXT_TO_CURRENT       0x00600009
-#define CP_SET_CONTEXT_POINTER   0x0060000a
-#define CP_END                   0x0060000e
-#define CP_LOAD_MAGIC_UNK01      0x00800001 /* unknown */
-#define CP_LOAD_MAGIC_NV44TCL    0x00800029 /* per-vs state (0x4497) */
-#define CP_LOAD_MAGIC_NV40TCL    0x00800041 /* per-vs state (0x4097) */
-
-#include "nv40.h"
-#include "ctx.h"
-
-/* TODO:
- *  - get vs count from 0x1540
- */
-
-static int
-nv40_graph_vs_count(struct nouveau_device *device)
-{
-
-       switch (device->chipset) {
-       case 0x47:
-       case 0x49:
-       case 0x4b:
-               return 8;
-       case 0x40:
-               return 6;
-       case 0x41:
-       case 0x42:
-               return 5;
-       case 0x43:
-       case 0x44:
-       case 0x46:
-       case 0x4a:
-               return 3;
-       case 0x4c:
-       case 0x4e:
-       case 0x67:
-       default:
-               return 1;
-       }
-}
-
-
-enum cp_label {
-       cp_check_load = 1,
-       cp_setup_auto_load,
-       cp_setup_load,
-       cp_setup_save,
-       cp_swap_state,
-       cp_swap_state3d_3_is_save,
-       cp_prepare_exit,
-       cp_exit,
-};
-
-static void
-nv40_graph_construct_general(struct nouveau_grctx *ctx)
-{
-       struct nouveau_device *device = ctx->device;
-       int i;
-
-       cp_ctx(ctx, 0x4000a4, 1);
-       gr_def(ctx, 0x4000a4, 0x00000008);
-       cp_ctx(ctx, 0x400144, 58);
-       gr_def(ctx, 0x400144, 0x00000001);
-       cp_ctx(ctx, 0x400314, 1);
-       gr_def(ctx, 0x400314, 0x00000000);
-       cp_ctx(ctx, 0x400400, 10);
-       cp_ctx(ctx, 0x400480, 10);
-       cp_ctx(ctx, 0x400500, 19);
-       gr_def(ctx, 0x400514, 0x00040000);
-       gr_def(ctx, 0x400524, 0x55555555);
-       gr_def(ctx, 0x400528, 0x55555555);
-       gr_def(ctx, 0x40052c, 0x55555555);
-       gr_def(ctx, 0x400530, 0x55555555);
-       cp_ctx(ctx, 0x400560, 6);
-       gr_def(ctx, 0x400568, 0x0000ffff);
-       gr_def(ctx, 0x40056c, 0x0000ffff);
-       cp_ctx(ctx, 0x40057c, 5);
-       cp_ctx(ctx, 0x400710, 3);
-       gr_def(ctx, 0x400710, 0x20010001);
-       gr_def(ctx, 0x400714, 0x0f73ef00);
-       cp_ctx(ctx, 0x400724, 1);
-       gr_def(ctx, 0x400724, 0x02008821);
-       cp_ctx(ctx, 0x400770, 3);
-       if (device->chipset == 0x40) {
-               cp_ctx(ctx, 0x400814, 4);
-               cp_ctx(ctx, 0x400828, 5);
-               cp_ctx(ctx, 0x400840, 5);
-               gr_def(ctx, 0x400850, 0x00000040);
-               cp_ctx(ctx, 0x400858, 4);
-               gr_def(ctx, 0x400858, 0x00000040);
-               gr_def(ctx, 0x40085c, 0x00000040);
-               gr_def(ctx, 0x400864, 0x80000000);
-               cp_ctx(ctx, 0x40086c, 9);
-               gr_def(ctx, 0x40086c, 0x80000000);
-               gr_def(ctx, 0x400870, 0x80000000);
-               gr_def(ctx, 0x400874, 0x80000000);
-               gr_def(ctx, 0x400878, 0x80000000);
-               gr_def(ctx, 0x400888, 0x00000040);
-               gr_def(ctx, 0x40088c, 0x80000000);
-               cp_ctx(ctx, 0x4009c0, 8);
-               gr_def(ctx, 0x4009cc, 0x80000000);
-               gr_def(ctx, 0x4009dc, 0x80000000);
-       } else {
-               cp_ctx(ctx, 0x400840, 20);
-               if (nv44_graph_class(ctx->device)) {
-                       for (i = 0; i < 8; i++)
-                               gr_def(ctx, 0x400860 + (i * 4), 0x00000001);
-               }
-               gr_def(ctx, 0x400880, 0x00000040);
-               gr_def(ctx, 0x400884, 0x00000040);
-               gr_def(ctx, 0x400888, 0x00000040);
-               cp_ctx(ctx, 0x400894, 11);
-               gr_def(ctx, 0x400894, 0x00000040);
-               if (!nv44_graph_class(ctx->device)) {
-                       for (i = 0; i < 8; i++)
-                               gr_def(ctx, 0x4008a0 + (i * 4), 0x80000000);
-               }
-               cp_ctx(ctx, 0x4008e0, 2);
-               cp_ctx(ctx, 0x4008f8, 2);
-               if (device->chipset == 0x4c ||
-                   (device->chipset & 0xf0) == 0x60)
-                       cp_ctx(ctx, 0x4009f8, 1);
-       }
-       cp_ctx(ctx, 0x400a00, 73);
-       gr_def(ctx, 0x400b0c, 0x0b0b0b0c);
-       cp_ctx(ctx, 0x401000, 4);
-       cp_ctx(ctx, 0x405004, 1);
-       switch (device->chipset) {
-       case 0x47:
-       case 0x49:
-       case 0x4b:
-               cp_ctx(ctx, 0x403448, 1);
-               gr_def(ctx, 0x403448, 0x00001010);
-               break;
-       default:
-               cp_ctx(ctx, 0x403440, 1);
-               switch (device->chipset) {
-               case 0x40:
-                       gr_def(ctx, 0x403440, 0x00000010);
-                       break;
-               case 0x44:
-               case 0x46:
-               case 0x4a:
-                       gr_def(ctx, 0x403440, 0x00003010);
-                       break;
-               case 0x41:
-               case 0x42:
-               case 0x43:
-               case 0x4c:
-               case 0x4e:
-               case 0x67:
-               default:
-                       gr_def(ctx, 0x403440, 0x00001010);
-                       break;
-               }
-               break;
-       }
-}
-
-static void
-nv40_graph_construct_state3d(struct nouveau_grctx *ctx)
-{
-       struct nouveau_device *device = ctx->device;
-       int i;
-
-       if (device->chipset == 0x40) {
-               cp_ctx(ctx, 0x401880, 51);
-               gr_def(ctx, 0x401940, 0x00000100);
-       } else
-       if (device->chipset == 0x46 || device->chipset == 0x47 ||
-           device->chipset == 0x49 || device->chipset == 0x4b) {
-               cp_ctx(ctx, 0x401880, 32);
-               for (i = 0; i < 16; i++)
-                       gr_def(ctx, 0x401880 + (i * 4), 0x00000111);
-               if (device->chipset == 0x46)
-                       cp_ctx(ctx, 0x401900, 16);
-               cp_ctx(ctx, 0x401940, 3);
-       }
-       cp_ctx(ctx, 0x40194c, 18);
-       gr_def(ctx, 0x401954, 0x00000111);
-       gr_def(ctx, 0x401958, 0x00080060);
-       gr_def(ctx, 0x401974, 0x00000080);
-       gr_def(ctx, 0x401978, 0xffff0000);
-       gr_def(ctx, 0x40197c, 0x00000001);
-       gr_def(ctx, 0x401990, 0x46400000);
-       if (device->chipset == 0x40) {
-               cp_ctx(ctx, 0x4019a0, 2);
-               cp_ctx(ctx, 0x4019ac, 5);
-       } else {
-               cp_ctx(ctx, 0x4019a0, 1);
-               cp_ctx(ctx, 0x4019b4, 3);
-       }
-       gr_def(ctx, 0x4019bc, 0xffff0000);
-       switch (device->chipset) {
-       case 0x46:
-       case 0x47:
-       case 0x49:
-       case 0x4b:
-               cp_ctx(ctx, 0x4019c0, 18);
-               for (i = 0; i < 16; i++)
-                       gr_def(ctx, 0x4019c0 + (i * 4), 0x88888888);
-               break;
-       }
-       cp_ctx(ctx, 0x401a08, 8);
-       gr_def(ctx, 0x401a10, 0x0fff0000);
-       gr_def(ctx, 0x401a14, 0x0fff0000);
-       gr_def(ctx, 0x401a1c, 0x00011100);
-       cp_ctx(ctx, 0x401a2c, 4);
-       cp_ctx(ctx, 0x401a44, 26);
-       for (i = 0; i < 16; i++)
-               gr_def(ctx, 0x401a44 + (i * 4), 0x07ff0000);
-       gr_def(ctx, 0x401a8c, 0x4b7fffff);
-       if (device->chipset == 0x40) {
-               cp_ctx(ctx, 0x401ab8, 3);
-       } else {
-               cp_ctx(ctx, 0x401ab8, 1);
-               cp_ctx(ctx, 0x401ac0, 1);
-       }
-       cp_ctx(ctx, 0x401ad0, 8);
-       gr_def(ctx, 0x401ad0, 0x30201000);
-       gr_def(ctx, 0x401ad4, 0x70605040);
-       gr_def(ctx, 0x401ad8, 0xb8a89888);
-       gr_def(ctx, 0x401adc, 0xf8e8d8c8);
-       cp_ctx(ctx, 0x401b10, device->chipset == 0x40 ? 2 : 1);
-       gr_def(ctx, 0x401b10, 0x40100000);
-       cp_ctx(ctx, 0x401b18, device->chipset == 0x40 ? 6 : 5);
-       gr_def(ctx, 0x401b28, device->chipset == 0x40 ?
-                             0x00000004 : 0x00000000);
-       cp_ctx(ctx, 0x401b30, 25);
-       gr_def(ctx, 0x401b34, 0x0000ffff);
-       gr_def(ctx, 0x401b68, 0x435185d6);
-       gr_def(ctx, 0x401b6c, 0x2155b699);
-       gr_def(ctx, 0x401b70, 0xfedcba98);
-       gr_def(ctx, 0x401b74, 0x00000098);
-       gr_def(ctx, 0x401b84, 0xffffffff);
-       gr_def(ctx, 0x401b88, 0x00ff7000);
-       gr_def(ctx, 0x401b8c, 0x0000ffff);
-       if (device->chipset != 0x44 && device->chipset != 0x4a &&
-           device->chipset != 0x4e)
-               cp_ctx(ctx, 0x401b94, 1);
-       cp_ctx(ctx, 0x401b98, 8);
-       gr_def(ctx, 0x401b9c, 0x00ff0000);
-       cp_ctx(ctx, 0x401bc0, 9);
-       gr_def(ctx, 0x401be0, 0x00ffff00);
-       cp_ctx(ctx, 0x401c00, 192);
-       for (i = 0; i < 16; i++) { /* fragment texture units */
-               gr_def(ctx, 0x401c40 + (i * 4), 0x00018488);
-               gr_def(ctx, 0x401c80 + (i * 4), 0x00028202);
-               gr_def(ctx, 0x401d00 + (i * 4), 0x0000aae4);
-               gr_def(ctx, 0x401d40 + (i * 4), 0x01012000);
-               gr_def(ctx, 0x401d80 + (i * 4), 0x00080008);
-               gr_def(ctx, 0x401e00 + (i * 4), 0x00100008);
-       }
-       for (i = 0; i < 4; i++) { /* vertex texture units */
-               gr_def(ctx, 0x401e90 + (i * 4), 0x0001bc80);
-               gr_def(ctx, 0x401ea0 + (i * 4), 0x00000202);
-               gr_def(ctx, 0x401ec0 + (i * 4), 0x00000008);
-               gr_def(ctx, 0x401ee0 + (i * 4), 0x00080008);
-       }
-       cp_ctx(ctx, 0x400f5c, 3);
-       gr_def(ctx, 0x400f5c, 0x00000002);
-       cp_ctx(ctx, 0x400f84, 1);
-}
-
-static void
-nv40_graph_construct_state3d_2(struct nouveau_grctx *ctx)
-{
-       struct nouveau_device *device = ctx->device;
-       int i;
-
-       cp_ctx(ctx, 0x402000, 1);
-       cp_ctx(ctx, 0x402404, device->chipset == 0x40 ? 1 : 2);
-       switch (device->chipset) {
-       case 0x40:
-               gr_def(ctx, 0x402404, 0x00000001);
-               break;
-       case 0x4c:
-       case 0x4e:
-       case 0x67:
-               gr_def(ctx, 0x402404, 0x00000020);
-               break;
-       case 0x46:
-       case 0x49:
-       case 0x4b:
-               gr_def(ctx, 0x402404, 0x00000421);
-               break;
-       default:
-               gr_def(ctx, 0x402404, 0x00000021);
-       }
-       if (device->chipset != 0x40)
-               gr_def(ctx, 0x402408, 0x030c30c3);
-       switch (device->chipset) {
-       case 0x44:
-       case 0x46:
-       case 0x4a:
-       case 0x4c:
-       case 0x4e:
-       case 0x67:
-               cp_ctx(ctx, 0x402440, 1);
-               gr_def(ctx, 0x402440, 0x00011001);
-               break;
-       default:
-               break;
-       }
-       cp_ctx(ctx, 0x402480, device->chipset == 0x40 ? 8 : 9);
-       gr_def(ctx, 0x402488, 0x3e020200);
-       gr_def(ctx, 0x40248c, 0x00ffffff);
-       switch (device->chipset) {
-       case 0x40:
-               gr_def(ctx, 0x402490, 0x60103f00);
-               break;
-       case 0x47:
-               gr_def(ctx, 0x402490, 0x40103f00);
-               break;
-       case 0x41:
-       case 0x42:
-       case 0x49:
-       case 0x4b:
-               gr_def(ctx, 0x402490, 0x20103f00);
-               break;
-       default:
-               gr_def(ctx, 0x402490, 0x0c103f00);
-               break;
-       }
-       gr_def(ctx, 0x40249c, device->chipset <= 0x43 ?
-                             0x00020000 : 0x00040000);
-       cp_ctx(ctx, 0x402500, 31);
-       gr_def(ctx, 0x402530, 0x00008100);
-       if (device->chipset == 0x40)
-               cp_ctx(ctx, 0x40257c, 6);
-       cp_ctx(ctx, 0x402594, 16);
-       cp_ctx(ctx, 0x402800, 17);
-       gr_def(ctx, 0x402800, 0x00000001);
-       switch (device->chipset) {
-       case 0x47:
-       case 0x49:
-       case 0x4b:
-               cp_ctx(ctx, 0x402864, 1);
-               gr_def(ctx, 0x402864, 0x00001001);
-               cp_ctx(ctx, 0x402870, 3);
-               gr_def(ctx, 0x402878, 0x00000003);
-               if (device->chipset != 0x47) { /* belong at end!! */
-                       cp_ctx(ctx, 0x402900, 1);
-                       cp_ctx(ctx, 0x402940, 1);
-                       cp_ctx(ctx, 0x402980, 1);
-                       cp_ctx(ctx, 0x4029c0, 1);
-                       cp_ctx(ctx, 0x402a00, 1);
-                       cp_ctx(ctx, 0x402a40, 1);
-                       cp_ctx(ctx, 0x402a80, 1);
-                       cp_ctx(ctx, 0x402ac0, 1);
-               }
-               break;
-       case 0x40:
-               cp_ctx(ctx, 0x402844, 1);
-               gr_def(ctx, 0x402844, 0x00000001);
-               cp_ctx(ctx, 0x402850, 1);
-               break;
-       default:
-               cp_ctx(ctx, 0x402844, 1);
-               gr_def(ctx, 0x402844, 0x00001001);
-               cp_ctx(ctx, 0x402850, 2);
-               gr_def(ctx, 0x402854, 0x00000003);
-               break;
-       }
-
-       cp_ctx(ctx, 0x402c00, 4);
-       gr_def(ctx, 0x402c00, device->chipset == 0x40 ?
-                             0x80800001 : 0x00888001);
-       switch (device->chipset) {
-       case 0x47:
-       case 0x49:
-       case 0x4b:
-               cp_ctx(ctx, 0x402c20, 40);
-               for (i = 0; i < 32; i++)
-                       gr_def(ctx, 0x402c40 + (i * 4), 0xffffffff);
-               cp_ctx(ctx, 0x4030b8, 13);
-               gr_def(ctx, 0x4030dc, 0x00000005);
-               gr_def(ctx, 0x4030e8, 0x0000ffff);
-               break;
-       default:
-               cp_ctx(ctx, 0x402c10, 4);
-               if (device->chipset == 0x40)
-                       cp_ctx(ctx, 0x402c20, 36);
-               else
-               if (device->chipset <= 0x42)
-                       cp_ctx(ctx, 0x402c20, 24);
-               else
-               if (device->chipset <= 0x4a)
-                       cp_ctx(ctx, 0x402c20, 16);
-               else
-                       cp_ctx(ctx, 0x402c20, 8);
-               cp_ctx(ctx, 0x402cb0, device->chipset == 0x40 ? 12 : 13);
-               gr_def(ctx, 0x402cd4, 0x00000005);
-               if (device->chipset != 0x40)
-                       gr_def(ctx, 0x402ce0, 0x0000ffff);
-               break;
-       }
-
-       cp_ctx(ctx, 0x403400, device->chipset == 0x40 ? 4 : 3);
-       cp_ctx(ctx, 0x403410, device->chipset == 0x40 ? 4 : 3);
-       cp_ctx(ctx, 0x403420, nv40_graph_vs_count(ctx->device));
-       for (i = 0; i < nv40_graph_vs_count(ctx->device); i++)
-               gr_def(ctx, 0x403420 + (i * 4), 0x00005555);
-
-       if (device->chipset != 0x40) {
-               cp_ctx(ctx, 0x403600, 1);
-               gr_def(ctx, 0x403600, 0x00000001);
-       }
-       cp_ctx(ctx, 0x403800, 1);
-
-       cp_ctx(ctx, 0x403c18, 1);
-       gr_def(ctx, 0x403c18, 0x00000001);
-       switch (device->chipset) {
-       case 0x46:
-       case 0x47:
-       case 0x49:
-       case 0x4b:
-               cp_ctx(ctx, 0x405018, 1);
-               gr_def(ctx, 0x405018, 0x08e00001);
-               cp_ctx(ctx, 0x405c24, 1);
-               gr_def(ctx, 0x405c24, 0x000e3000);
-               break;
-       }
-       if (device->chipset != 0x4e)
-               cp_ctx(ctx, 0x405800, 11);
-       cp_ctx(ctx, 0x407000, 1);
-}
-
-static void
-nv40_graph_construct_state3d_3(struct nouveau_grctx *ctx)
-{
-       int len = nv44_graph_class(ctx->device) ? 0x0084 : 0x0684;
-
-       cp_out (ctx, 0x300000);
-       cp_lsr (ctx, len - 4);
-       cp_bra (ctx, SWAP_DIRECTION, SAVE, cp_swap_state3d_3_is_save);
-       cp_lsr (ctx, len);
-       cp_name(ctx, cp_swap_state3d_3_is_save);
-       cp_out (ctx, 0x800001);
-
-       ctx->ctxvals_pos += len;
-}
-
-static void
-nv40_graph_construct_shader(struct nouveau_grctx *ctx)
-{
-       struct nouveau_device *device = ctx->device;
-       struct nouveau_gpuobj *obj = ctx->data;
-       int vs, vs_nr, vs_len, vs_nr_b0, vs_nr_b1, b0_offset, b1_offset;
-       int offset, i;
-
-       vs_nr    = nv40_graph_vs_count(ctx->device);
-       vs_nr_b0 = 363;
-       vs_nr_b1 = device->chipset == 0x40 ? 128 : 64;
-       if (device->chipset == 0x40) {
-               b0_offset = 0x2200/4; /* 33a0 */
-               b1_offset = 0x55a0/4; /* 1500 */
-               vs_len = 0x6aa0/4;
-       } else
-       if (device->chipset == 0x41 || device->chipset == 0x42) {
-               b0_offset = 0x2200/4; /* 2200 */
-               b1_offset = 0x4400/4; /* 0b00 */
-               vs_len = 0x4f00/4;
-       } else {
-               b0_offset = 0x1d40/4; /* 2200 */
-               b1_offset = 0x3f40/4; /* 0b00 : 0a40 */
-               vs_len = nv44_graph_class(device) ? 0x4980/4 : 0x4a40/4;
-       }
-
-       cp_lsr(ctx, vs_len * vs_nr + 0x300/4);
-       cp_out(ctx, nv44_graph_class(device) ? 0x800029 : 0x800041);
-
-       offset = ctx->ctxvals_pos;
-       ctx->ctxvals_pos += (0x0300/4 + (vs_nr * vs_len));
-
-       if (ctx->mode != NOUVEAU_GRCTX_VALS)
-               return;
-
-       offset += 0x0280/4;
-       for (i = 0; i < 16; i++, offset += 2)
-               nv_wo32(obj, offset * 4, 0x3f800000);
-
-       for (vs = 0; vs < vs_nr; vs++, offset += vs_len) {
-               for (i = 0; i < vs_nr_b0 * 6; i += 6)
-                       nv_wo32(obj, (offset + b0_offset + i) * 4, 0x00000001);
-               for (i = 0; i < vs_nr_b1 * 4; i += 4)
-                       nv_wo32(obj, (offset + b1_offset + i) * 4, 0x3f800000);
-       }
-}
-
-static void
-nv40_grctx_generate(struct nouveau_grctx *ctx)
-{
-       /* 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_wait(ctx, STATUS, IDLE);
-       cp_out (ctx, CP_NEXT_TO_SWAP);
-       cp_name(ctx, cp_setup_load);
-       cp_wait(ctx, STATUS, IDLE);
-       cp_set (ctx, SWAP_DIRECTION, LOAD);
-       cp_out (ctx, 0x00910880); /* ?? */
-       cp_out (ctx, 0x00901ffe); /* ?? */
-       cp_out (ctx, 0x01940000); /* ?? */
-       cp_lsr (ctx, 0x20);
-       cp_out (ctx, 0x0060000b); /* ?? */
-       cp_wait(ctx, UNK57, CLEAR);
-       cp_out (ctx, 0x0060000c); /* ?? */
-       cp_bra (ctx, ALWAYS, TRUE, cp_swap_state);
-
-       /* setup for context save */
-       cp_name(ctx, cp_setup_save);
-       cp_set (ctx, SWAP_DIRECTION, SAVE);
-
-       /* general PGRAPH state */
-       cp_name(ctx, cp_swap_state);
-       cp_pos (ctx, 0x00020/4);
-       nv40_graph_construct_general(ctx);
-       cp_wait(ctx, STATUS, IDLE);
-
-       /* 3D state, block 1 */
-       cp_bra (ctx, UNK54, CLEAR, cp_prepare_exit);
-       nv40_graph_construct_state3d(ctx);
-       cp_wait(ctx, STATUS, IDLE);
-
-       /* 3D state, block 2 */
-       nv40_graph_construct_state3d_2(ctx);
-
-       /* Some other block of "random" state */
-       nv40_graph_construct_state3d_3(ctx);
-
-       /* Per-vertex shader state */
-       cp_pos (ctx, ctx->ctxvals_pos);
-       nv40_graph_construct_shader(ctx);
-
-       /* pre-exit state updates */
-       cp_name(ctx, cp_prepare_exit);
-       cp_bra (ctx, SWAP_DIRECTION, SAVE, cp_check_load);
-       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);
-}
-
-void
-nv40_grctx_fill(struct nouveau_device *device, struct nouveau_gpuobj *mem)
-{
-       nv40_grctx_generate(&(struct nouveau_grctx) {
-                            .device = device,
-                            .mode = NOUVEAU_GRCTX_VALS,
-                            .data = mem,
-                          });
-}
-
-int
-nv40_grctx_init(struct nouveau_device *device, u32 *size)
-{
-       u32 *ctxprog = kmalloc(256 * 4, GFP_KERNEL), i;
-       struct nouveau_grctx ctx = {
-               .device = device,
-               .mode = NOUVEAU_GRCTX_PROG,
-               .data = ctxprog,
-               .ctxprog_max = 256,
-       };
-
-       if (!ctxprog)
-               return -ENOMEM;
-
-       nv40_grctx_generate(&ctx);
-
-       nv_wr32(device, 0x400324, 0);
-       for (i = 0; i < ctx.ctxprog_len; i++)
-               nv_wr32(device, 0x400328, ctxprog[i]);
-       *size = ctx.ctxvals_pos * 4;
-
-       kfree(ctxprog);
-       return 0;
-}
diff --git a/drivers/gpu/drm/nouveau/core/engine/graph/ctxnv50.c b/drivers/gpu/drm/nouveau/core/engine/graph/ctxnv50.c
deleted file mode 100644 (file)
index 1d0e33f..0000000
+++ /dev/null
@@ -1,3347 +0,0 @@
-/*
- * 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.
- */
-
-#include <core/gpuobj.h>
-
-#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_XFER_SWITCH           ((0 * 32) + 0xe)
-#define CP_FLAG_XFER_SWITCH_DISABLE   0
-#define CP_FLAG_XFER_SWITCH_ENABLE    1
-#define CP_FLAG_STATE                 ((0 * 32) + 0x1c)
-#define CP_FLAG_STATE_STOPPED         0
-#define CP_FLAG_STATE_RUNNING         1
-#define CP_FLAG_UNK1D                 ((0 * 32) + 0x1d)
-#define CP_FLAG_UNK1D_CLEAR           0
-#define CP_FLAG_UNK1D_SET             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_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 "nv50.h"
-#include "ctx.h"
-
-#define IS_NVA3F(x) (((x) > 0xa0 && (x) < 0xaa) || (x) == 0xaf)
-#define IS_NVAAF(x) ((x) >= 0xaa && (x) <= 0xac)
-
-#include <subdev/fb.h>
-
-/*
- * 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,
-};
-
-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. */
-
-static int
-nv50_grctx_generate(struct nouveau_grctx *ctx)
-{
-       cp_set (ctx, STATE, RUNNING);
-       cp_set (ctx, XFER_SWITCH, ENABLE);
-       /* 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_prepare_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);
-
-       /* setup for context save */
-       cp_name(ctx, cp_setup_save);
-       cp_set (ctx, UNK1D, SET);
-       cp_wait(ctx, STATUS, BUSY);
-       cp_wait(ctx, INTR, PENDING);
-       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_set (ctx, XFER_SWITCH, DISABLE);
-       cp_set (ctx, STATE, STOPPED);
-       cp_out (ctx, CP_END);
-       ctx->ctxvals_pos += 0x400; /* padding... no idea why you need it */
-
-       return 0;
-}
-
-void
-nv50_grctx_fill(struct nouveau_device *device, struct nouveau_gpuobj *mem)
-{
-       nv50_grctx_generate(&(struct nouveau_grctx) {
-                            .device = device,
-                            .mode = NOUVEAU_GRCTX_VALS,
-                            .data = mem,
-                          });
-}
-
-int
-nv50_grctx_init(struct nouveau_device *device, u32 *size)
-{
-       u32 *ctxprog = kmalloc(512 * 4, GFP_KERNEL), i;
-       struct nouveau_grctx ctx = {
-               .device = device,
-               .mode = NOUVEAU_GRCTX_PROG,
-               .data = ctxprog,
-               .ctxprog_max = 512,
-       };
-
-       if (!ctxprog)
-               return -ENOMEM;
-       nv50_grctx_generate(&ctx);
-
-       nv_wr32(device, 0x400324, 0);
-       for (i = 0; i < ctx.ctxprog_len; i++)
-               nv_wr32(device, 0x400328, ctxprog[i]);
-       *size = ctx.ctxvals_pos * 4;
-       kfree(ctxprog);
-       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 nouveau_device *device = ctx->device;
-       int i, j;
-       int offset, base;
-       u32 units = nv_rd32 (ctx->device, 0x1540);
-
-       /* 0800: DISPATCH */
-       cp_ctx(ctx, 0x400808, 7);
-       gr_def(ctx, 0x400814, 0x00000030);
-       cp_ctx(ctx, 0x400834, 0x32);
-       if (device->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(device->chipset))
-               gr_def(ctx, 0x400894, 0x00001000);
-       gr_def(ctx, 0x4008e8, 0x00000003);
-       gr_def(ctx, 0x4008ec, 0x00001000);
-       if (device->chipset == 0x50)
-               cp_ctx(ctx, 0x400908, 0xb);
-       else if (device->chipset < 0xa0)
-               cp_ctx(ctx, 0x400908, 0xc);
-       else
-               cp_ctx(ctx, 0x400908, 0xe);
-
-       if (device->chipset >= 0xa0)
-               cp_ctx(ctx, 0x400b00, 0x1);
-       if (IS_NVA3F(device->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 (device->chipset < 0xa0) {
-               cp_ctx(ctx, 0x401008, 0x4);
-               gr_def(ctx, 0x401014, 0x00001000);
-       } else if (!IS_NVA3F(device->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 (device->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 (device->chipset == 0x50) {
-               cp_ctx(ctx, 0x40181c, 0xe);
-               gr_def(ctx, 0x401850, 0x00000004);
-       } else if (device->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 (device->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 (device->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 (device->chipset == 0x50)
-               gr_def(ctx, 0x402800, 0x00000006);
-
-       /* 2C00: ZCULL */
-       cp_ctx(ctx, 0x402c08, 0x6);
-       if (device->chipset != 0x50)
-               gr_def(ctx, 0x402c14, 0x01000000);
-       gr_def(ctx, 0x402c18, 0x000000ff);
-       if (device->chipset == 0x50)
-               cp_ctx(ctx, 0x402ca0, 0x1);
-       else
-               cp_ctx(ctx, 0x402ca0, 0x2);
-       if (device->chipset < 0xa0)
-               gr_def(ctx, 0x402ca0, 0x00000400);
-       else if (!IS_NVA3F(device->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 (device->chipset >= 0xa0) {
-               cp_ctx(ctx, 0x403404, 0x1);
-               gr_def(ctx, 0x403404, 0x00000001);
-       }
-
-       /* 5000: CCACHE */
-       cp_ctx(ctx, 0x405000, 0x1);
-       switch (device->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 (device->chipset == 0x50)
-               cp_ctx(ctx, 0x4063e0, 0x1);
-
-       /* 6800: M2MF */
-       if (device->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 (device->chipset == 0x98)
-                       gr_def(ctx, 0x406818, 0x00000f80);
-               else
-                       gr_def(ctx, 0x406818, 0x00001f80);
-               if (IS_NVA3F(device->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 (device->chipset == 0x50)
-                               gr_def(ctx, 0x407000 + (i<<8), 0x1b74f820);
-                       else if (device->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 (device->chipset == 0x50) {
-                               cp_ctx(ctx, 0x407010 + (i<<8), 1);
-                       } else if (device->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 (device->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 (device->chipset != 0xa5)
-                               gr_def(ctx, 0x407080 + (i<<8), 0x027c10fa);
-                       else
-                               gr_def(ctx, 0x407080 + (i<<8), 0x827c10fa);
-                       if (device->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 (device->chipset < 0xa0)
-                               cp_ctx(ctx, 0x407094 + (i<<8), 1);
-                       else if (!IS_NVA3F(device->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 (device->chipset < 0x90)
-               gr_def(ctx, 0x407c00, 0x00010040);
-       else if (device->chipset < 0xa0)
-               gr_def(ctx, 0x407c00, 0x00390040);
-       else
-               gr_def(ctx, 0x407c00, 0x003d0040);
-       gr_def(ctx, 0x407c08, 0x00000022);
-       if (device->chipset >= 0xa0) {
-               cp_ctx(ctx, 0x407c10, 0x3);
-               cp_ctx(ctx, 0x407c20, 0x1);
-               cp_ctx(ctx, 0x407c2c, 0x1);
-       }
-
-       if (device->chipset < 0xa0) {
-               cp_ctx(ctx, 0x407d00, 0x9);
-       } else {
-               cp_ctx(ctx, 0x407d00, 0x15);
-       }
-       if (device->chipset == 0x98)
-               gr_def(ctx, 0x407d08, 0x00380040);
-       else {
-               if (device->chipset < 0x90)
-                       gr_def(ctx, 0x407d08, 0x00010040);
-               else if (device->chipset < 0xa0)
-                       gr_def(ctx, 0x407d08, 0x00390040);
-               else {
-                       if (nouveau_fb(device)->ram->type != NV_MEM_TYPE_GDDR5)
-                               gr_def(ctx, 0x407d08, 0x003d0040);
-                       else
-                               gr_def(ctx, 0x407d08, 0x003c0040);
-               }
-               gr_def(ctx, 0x407d0c, 0x00000022);
-       }
-
-       /* 8000+: per-TP state */
-       for (i = 0; i < 10; i++) {
-               if (units & (1<<i)) {
-                       if (device->chipset < 0xa0)
-                               base = 0x408000 + (i<<12);
-                       else
-                               base = 0x408000 + (i<<11);
-                       if (device->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 < (device->chipset < 0xa0 ? 2 : 4); j++) {
-                               if (!(units & (1 << (j+24)))) continue;
-                               if (device->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 (device->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, 0x018c0000);
-                                       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 (device->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 (device->chipset == 0x50)
-                                       gr_def(ctx, offset + 0x5c, 0x00000080);
-                               else
-                                       gr_def(ctx, offset + 0x5c, 0x08000080);
-                               if (device->chipset >= 0xa0)
-                                       gr_def(ctx, offset + 0x68, 0x0000003e);
-                       }
-
-                       if (device->chipset < 0xa0)
-                               cp_ctx(ctx, base + 0x300, 0x4);
-                       else
-                               cp_ctx(ctx, base + 0x300, 0x5);
-                       if (device->chipset == 0x50)
-                               gr_def(ctx, base + 0x304, 0x00007070);
-                       else if (device->chipset < 0xa0)
-                               gr_def(ctx, base + 0x304, 0x00027070);
-                       else if (!IS_NVA3F(device->chipset))
-                               gr_def(ctx, base + 0x304, 0x01127070);
-                       else
-                               gr_def(ctx, base + 0x304, 0x05127070);
-
-                       if (device->chipset < 0xa0)
-                               cp_ctx(ctx, base + 0x318, 1);
-                       else
-                               cp_ctx(ctx, base + 0x320, 1);
-                       if (device->chipset == 0x50)
-                               gr_def(ctx, base + 0x318, 0x0003ffff);
-                       else if (device->chipset < 0xa0)
-                               gr_def(ctx, base + 0x318, 0x03ffffff);
-                       else
-                               gr_def(ctx, base + 0x320, 0x07ffffff);
-
-                       if (device->chipset < 0xa0)
-                               cp_ctx(ctx, base + 0x324, 5);
-                       else
-                               cp_ctx(ctx, base + 0x328, 4);
-
-                       if (device->chipset < 0xa0) {
-                               cp_ctx(ctx, base + 0x340, 9);
-                               offset = base + 0x340;
-                       } else if (!IS_NVA3F(device->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 (device->chipset == 0x84)
-                               gr_def(ctx, offset + 0x8, 0x05100202);
-                       else
-                               gr_def(ctx, offset + 0x8, 0x05010202);
-                       gr_def(ctx, offset + 0xc, 0x00030201);
-                       if (device->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 (device->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 (device->chipset == 0x50 || IS_NVAAF(device->chipset))
-                               gr_def(ctx, offset + 0xc, 0x00008000);
-                       gr_def(ctx, offset + 0x14, 0x00039e00);
-                       cp_ctx(ctx, offset + 0x1c, 2);
-                       if (device->chipset == 0x50)
-                               gr_def(ctx, offset + 0x1c, 0x00000040);
-                       else
-                               gr_def(ctx, offset + 0x1c, 0x00000100);
-                       gr_def(ctx, offset + 0x20, 0x00003800);
-
-                       if (device->chipset >= 0xa0) {
-                               cp_ctx(ctx, base + 0x54c, 2);
-                               if (!IS_NVA3F(device->chipset))
-                                       gr_def(ctx, base + 0x54c, 0x003fe006);
-                               else
-                                       gr_def(ctx, base + 0x54c, 0x003fe007);
-                               gr_def(ctx, base + 0x550, 0x003fe000);
-                       }
-
-                       if (device->chipset < 0xa0)
-                               offset = base + 0xa00;
-                       else
-                               offset = base + 0x680;
-                       cp_ctx(ctx, offset, 1);
-                       gr_def(ctx, offset, 0x00404040);
-
-                       if (device->chipset < 0xa0)
-                               offset = base + 0xe00;
-                       else
-                               offset = base + 0x700;
-                       cp_ctx(ctx, offset, 2);
-                       if (device->chipset < 0xa0)
-                               gr_def(ctx, offset, 0x0077f005);
-                       else if (device->chipset == 0xa5)
-                               gr_def(ctx, offset, 0x6cf7f007);
-                       else if (device->chipset == 0xa8)
-                               gr_def(ctx, offset, 0x6cfff007);
-                       else if (device->chipset == 0xac)
-                               gr_def(ctx, offset, 0x0cfff007);
-                       else
-                               gr_def(ctx, offset, 0x0cf7f007);
-                       if (device->chipset == 0x50)
-                               gr_def(ctx, offset + 0x4, 0x00007fff);
-                       else if (device->chipset < 0xa0)
-                               gr_def(ctx, offset + 0x4, 0x003f7fff);
-                       else
-                               gr_def(ctx, offset + 0x4, 0x02bf7fff);
-                       cp_ctx(ctx, offset + 0x2c, 1);
-                       if (device->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 (device->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, u32 val) {
-       int i;
-       if (val && ctx->mode == NOUVEAU_GRCTX_VALS)
-               for (i = 0; i < num; i++)
-                       nv_wo32(ctx->data, 4 * (ctx->ctxvals_pos + i), val);
-       ctx->ctxvals_pos += num;
-}
-
-static void
-nv50_graph_construct_mmio_ddata(struct nouveau_grctx *ctx)
-{
-       struct nouveau_device *device = ctx->device;
-       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 (device->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(device->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 (device->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 (device->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(device->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 (device->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 (device->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 (device->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(device->chipset)) {
-               dd_emit(ctx, 1, 3);     /* 00000003 */
-               dd_emit(ctx, 1, 0);     /* 00000001 UNK1418. Alone. */
-       }
-       if (device->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 (device->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 (device->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 (device->chipset != 0x50)
-               dd_emit(ctx, 8, 0);     /* 00000001 */
-       if (device->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(device->chipset))
-               dd_emit(ctx, 1, 0);     /* 00000001 */
-       dd_emit(ctx, 1, 2);             /* 00000003 POLYGON_MODE_BACK */
-       if (device->chipset >= 0xa0)
-               dd_emit(ctx, 1, 0);     /* 00000003 VTX_ATTR_DEFINE.SIZE - 1 */
-       dd_emit(ctx, 1, 0);             /* 0000ffff CB_ADDR_INDEX */
-       if (device->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 (device->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(device->chipset))
-               dd_emit(ctx, 1, 0x200);
-       dd_emit(ctx, 1, 0);             /* 00000001 */
-       if (device->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(device->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, u32 val) {
-       int i;
-       if (val && ctx->mode == NOUVEAU_GRCTX_VALS)
-               for (i = 0; i < num; i++)
-                       nv_wo32(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 nouveau_device *device = ctx->device;
-       int i;
-       int offset;
-       int size = 0;
-       u32 units = nv_rd32 (ctx->device, 0x1540);
-
-       offset = (ctx->ctxvals_pos+0x3f)&~0x3f;
-       ctx->ctxvals_base = offset;
-
-       if (device->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 (device->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 (device->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 nouveau_device *device = ctx->device;
-       /* SEEK */
-       if (device->chipset == 0x50)
-               xf_emit(ctx, 5, 0);
-       else if (!IS_NVA3F(device->chipset))
-               xf_emit(ctx, 6, 0);
-       else
-               xf_emit(ctx, 4, 0);
-       /* SEEK */
-       /* the PGRAPH's internal FIFO */
-       if (device->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(device->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 (device->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 (device->chipset == 0x50)
-               xf_emit(ctx, 0x1c, 0);
-       else if (device->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 nouveau_device *device = ctx->device;
-       int smallm2mf = 0;
-       if (device->chipset < 0x92 || device->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 nouveau_device *device = ctx->device;
-       xf_emit(ctx, 2, 0);             /* RO */
-       xf_emit(ctx, 0x800, 0);         /* ffffffff */
-       switch (device->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 nouveau_device *device = ctx->device;
-       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 (device->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 (device->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 nouveau_device *device = ctx->device;
-       /* 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 (device->chipset >= 0xa0)
-               xf_emit(ctx, 1, 0x0fac6881);
-       if (IS_NVA3F(device->chipset)) {
-               xf_emit(ctx, 1, 1);
-               xf_emit(ctx, 3, 0);
-       }
-}
-
-static void
-nv50_graph_construct_gene_unk14xx(struct nouveau_grctx *ctx)
-{
-       struct nouveau_device *device = ctx->device;
-       /* middle of area 2 on pre-NVA0, beginning of area 2 on NVA0, area 7 on >NVA0 */
-       if (device->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 (device->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 (device->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 (device->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(device->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 (device->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 nouveau_device *device = ctx->device;
-       /* 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 (device->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 (device->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 nouveau_device *device = ctx->device;
-       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(device->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 (device->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 (device->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 (device->chipset != 0x50)
-               xf_emit(ctx, 1, 0);     /* 000003ff */
-}
-
-static void
-nv50_graph_construct_gene_vfetch(struct nouveau_grctx *ctx)
-{
-       struct nouveau_device *device = ctx->device;
-       int acnt = 0x10, rep, i;
-       /* beginning of strand 1 on pre-NVA0, strand 3 on NVAx */
-       if (IS_NVA3F(device->chipset))
-               acnt = 0x20;
-       /* SEEK */
-       if (device->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(device->chipset))
-               xf_emit(ctx, 0xb, 0);   /* RO */
-       else if (device->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 (device->chipset == 0x50)
-               xf_emit(ctx, 1, 0x3ff); /* 3ff tesla UNK0D68 */
-       else
-               xf_emit(ctx, 1, 0x7ff); /* 7ff tesla UNK0D68 */
-       if (device->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 (device->chipset > 0x50 && device->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(device->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 (device->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(device->chipset)) {
-               xf_emit(ctx, acnt, 0);          /* f */
-               xf_emit(ctx, 3, 0);             /* f/1f */
-       }
-       /* SEEK */
-       if (IS_NVA3F(device->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 (device->chipset < 0xa0) {
-               xf_emit(ctx, 0x41, 0);  /* RO */
-               /* SEEK */
-               xf_emit(ctx, 0x11, 0);  /* RO */
-       } else if (!IS_NVA3F(device->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(device->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 (device->chipset < 0xa0)
-               xf_emit(ctx, 8, 0);     /* RO */
-       else if (IS_NVA3F(device->chipset))
-               xf_emit(ctx, 0xc, 0);   /* RO */
-       else
-               xf_emit(ctx, 7, 0);     /* RO */
-       /* SEEK */
-       xf_emit(ctx, 0xa, 0);           /* RO */
-       if (device->chipset == 0xa0)
-               rep = 0xc;
-       else
-               rep = 4;
-       for (i = 0; i < rep; i++) {
-               /* SEEK */
-               if (IS_NVA3F(device->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(device->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 nouveau_device *device = ctx->device;
-       /* 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 (device->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 nouveau_device *device = ctx->device;
-       /* 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 (device->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 nouveau_device *device = ctx->device;
-       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(device->chipset))
-               xf_emit(ctx, 1, 3);     /* 00000003 UNK16B4 */
-       else if (device->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 (device->chipset != 0x50) {
-               xf_emit(ctx, 1, 0);     /* 3ff */
-               xf_emit(ctx, 1, 1);     /* 00000001 tesla UNK1110 */
-       }
-       if (IS_NVA3F(device->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 (device->chipset != 0x50)
-               xf_emit(ctx, 1, 3);     /* 00000003 tesla UNK1100 */
-       if (device->chipset < 0xa0)
-               xf_emit(ctx, 0x1c, 0);  /* RO */
-       else if (IS_NVA3F(device->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 (device->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 (device->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 nouveau_device *device = ctx->device;
-       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 (device->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 (device->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 (device->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 nouveau_device *device = ctx->device;
-       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(device->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 nouveau_device *device = ctx->device;
-       /* 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(device->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 nouveau_device *device = ctx->device;
-       int magic2;
-       if (device->chipset == 0x50) {
-               magic2 = 0x00003e60;
-       } else if (!IS_NVA3F(device->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(device->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 (device->chipset >= 0xa0 && !IS_NVAAF(device->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 (device->chipset == 0x86 || device->chipset == 0x92 || device->chipset == 0x98 || device->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 (device->chipset != 0xa0) {
-                       if (IS_NVA3F(device->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 (device->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 (device->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(device->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 (device->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 (device->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 (device->chipset >= 0xa0)
-               xf_emit(ctx, 1, 0);     /* 00000001 UNK12E4? NVA3+ only? */
-       if (IS_NVA3F(device->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 nouveau_device *device = ctx->device;
-       int magic3;
-       switch (device->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(device->chipset))
-               xf_emit(ctx, 0x1f, 0);  /* ffffffff */
-       else if (device->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 (device->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 (device->chipset == 0x94 || device->chipset == 0x96)
-               xf_emit(ctx, 0x1020, 0);        /* 4 x (0x400 x 0xffffffff, ff, 0, 0, 0, 4 x ffffffff) */
-       else if (device->chipset < 0xa0)
-               xf_emit(ctx, 0xa20, 0); /* 4 x (0x280 x 0xffffffff, ff, 0, 0, 0, 4 x ffffffff) */
-       else if (!IS_NVA3F(device->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 nouveau_device *device = ctx->device;
-       int magic1, magic2;
-       if (device->chipset == 0x50) {
-               magic1 = 0x3ff;
-               magic2 = 0x00003e60;
-       } else if (!IS_NVA3F(device->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(device->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(device->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 (device->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(device->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(device->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(device->chipset))
-               xf_emit(ctx, 1, 1);     /* 0000001f tesla UNK169C */
-       if (device->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(device->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(device->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(device->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(device->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 (device->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(device->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 (device->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(device->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(device->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 nouveau_device *device = ctx->device;
-       xf_emit(ctx, 2, 0);             /* 1 LINKED_TSC. yes, 2. */
-       if (device->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 (device->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 (device->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(device->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 nouveau_device *device = ctx->device;
-       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(device->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 nouveau_device *device = ctx->device;
-       if (device->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 nouveau_device *device = ctx->device;
-       int i, mpcnt = 2;
-       switch (device->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 (device->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 (device->chipset == 0x86 || device->chipset == 0x98 || device->chipset == 0xa8 || IS_NVAAF(device->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 (device->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(device->chipset))
-                       xf_emit(ctx, 0xb, 0);   /* RO */
-               else if (device->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 (device->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(device->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(device->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(device->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 (device->chipset == 0x50)
-               xf_emit(ctx, 0x3a0, 0);
-       else if (device->chipset < 0x94)
-               xf_emit(ctx, 0x3a2, 0);
-       else if (device->chipset == 0x98 || device->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 nouveau_device *device = ctx->device;
-       int i;
-       u32 offset;
-       u32 units = nv_rd32 (ctx->device, 0x1540);
-       int size = 0;
-
-       offset = (ctx->ctxvals_pos+0x3f)&~0x3f;
-
-       if (device->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/drivers/gpu/drm/nouveau/core/engine/graph/ctxnvc0.c b/drivers/gpu/drm/nouveau/core/engine/graph/ctxnvc0.c
deleted file mode 100644 (file)
index b8e5fe6..0000000
+++ /dev/null
@@ -1,1386 +0,0 @@
-/*
- * 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 "ctxnvc0.h"
-
-/*******************************************************************************
- * PGRAPH context register lists
- ******************************************************************************/
-
-static const struct nvc0_graph_init
-nvc0_grctx_init_icmd_0[] = {
-       { 0x001000,   1, 0x01, 0x00000004 },
-       { 0x0000a9,   1, 0x01, 0x0000ffff },
-       { 0x000038,   1, 0x01, 0x0fac6881 },
-       { 0x00003d,   1, 0x01, 0x00000001 },
-       { 0x0000e8,   8, 0x01, 0x00000400 },
-       { 0x000078,   8, 0x01, 0x00000300 },
-       { 0x000050,   1, 0x01, 0x00000011 },
-       { 0x000058,   8, 0x01, 0x00000008 },
-       { 0x000208,   8, 0x01, 0x00000001 },
-       { 0x000081,   1, 0x01, 0x00000001 },
-       { 0x000085,   1, 0x01, 0x00000004 },
-       { 0x000088,   1, 0x01, 0x00000400 },
-       { 0x000090,   1, 0x01, 0x00000300 },
-       { 0x000098,   1, 0x01, 0x00001001 },
-       { 0x0000e3,   1, 0x01, 0x00000001 },
-       { 0x0000da,   1, 0x01, 0x00000001 },
-       { 0x0000f8,   1, 0x01, 0x00000003 },
-       { 0x0000fa,   1, 0x01, 0x00000001 },
-       { 0x00009f,   4, 0x01, 0x0000ffff },
-       { 0x0000b1,   1, 0x01, 0x00000001 },
-       { 0x0000b2,  40, 0x01, 0x00000000 },
-       { 0x000210,   8, 0x01, 0x00000040 },
-       { 0x000218,   8, 0x01, 0x0000c080 },
-       { 0x0000ad,   1, 0x01, 0x0000013e },
-       { 0x0000e1,   1, 0x01, 0x00000010 },
-       { 0x000290,  16, 0x01, 0x00000000 },
-       { 0x0003b0,  16, 0x01, 0x00000000 },
-       { 0x0002a0,  16, 0x01, 0x00000000 },
-       { 0x000420,  16, 0x01, 0x00000000 },
-       { 0x0002b0,  16, 0x01, 0x00000000 },
-       { 0x000430,  16, 0x01, 0x00000000 },
-       { 0x0002c0,  16, 0x01, 0x00000000 },
-       { 0x0004d0,  16, 0x01, 0x00000000 },
-       { 0x000720,  16, 0x01, 0x00000000 },
-       { 0x0008c0,  16, 0x01, 0x00000000 },
-       { 0x000890,  16, 0x01, 0x00000000 },
-       { 0x0008e0,  16, 0x01, 0x00000000 },
-       { 0x0008a0,  16, 0x01, 0x00000000 },
-       { 0x0008f0,  16, 0x01, 0x00000000 },
-       { 0x00094c,   1, 0x01, 0x000000ff },
-       { 0x00094d,   1, 0x01, 0xffffffff },
-       { 0x00094e,   1, 0x01, 0x00000002 },
-       { 0x0002ec,   1, 0x01, 0x00000001 },
-       { 0x000303,   1, 0x01, 0x00000001 },
-       { 0x0002e6,   1, 0x01, 0x00000001 },
-       { 0x000466,   1, 0x01, 0x00000052 },
-       { 0x000301,   1, 0x01, 0x3f800000 },
-       { 0x000304,   1, 0x01, 0x30201000 },
-       { 0x000305,   1, 0x01, 0x70605040 },
-       { 0x000306,   1, 0x01, 0xb8a89888 },
-       { 0x000307,   1, 0x01, 0xf8e8d8c8 },
-       { 0x00030a,   1, 0x01, 0x00ffff00 },
-       { 0x00030b,   1, 0x01, 0x0000001a },
-       { 0x00030c,   1, 0x01, 0x00000001 },
-       { 0x000318,   1, 0x01, 0x00000001 },
-       { 0x000340,   1, 0x01, 0x00000000 },
-       { 0x000375,   1, 0x01, 0x00000001 },
-       { 0x000351,   1, 0x01, 0x00000100 },
-       { 0x00037d,   1, 0x01, 0x00000006 },
-       { 0x0003a0,   1, 0x01, 0x00000002 },
-       { 0x0003aa,   1, 0x01, 0x00000001 },
-       { 0x0003a9,   1, 0x01, 0x00000001 },
-       { 0x000380,   1, 0x01, 0x00000001 },
-       { 0x000360,   1, 0x01, 0x00000040 },
-       { 0x000366,   2, 0x01, 0x00000000 },
-       { 0x000368,   1, 0x01, 0x00001fff },
-       { 0x000370,   2, 0x01, 0x00000000 },
-       { 0x000372,   1, 0x01, 0x003fffff },
-       { 0x00037a,   1, 0x01, 0x00000012 },
-       { 0x0005e0,   5, 0x01, 0x00000022 },
-       { 0x000619,   1, 0x01, 0x00000003 },
-       { 0x000811,   1, 0x01, 0x00000003 },
-       { 0x000812,   1, 0x01, 0x00000004 },
-       { 0x000813,   1, 0x01, 0x00000006 },
-       { 0x000814,   1, 0x01, 0x00000008 },
-       { 0x000815,   1, 0x01, 0x0000000b },
-       { 0x000800,   6, 0x01, 0x00000001 },
-       { 0x000632,   1, 0x01, 0x00000001 },
-       { 0x000633,   1, 0x01, 0x00000002 },
-       { 0x000634,   1, 0x01, 0x00000003 },
-       { 0x000635,   1, 0x01, 0x00000004 },
-       { 0x000654,   1, 0x01, 0x3f800000 },
-       { 0x000657,   1, 0x01, 0x3f800000 },
-       { 0x000655,   2, 0x01, 0x3f800000 },
-       { 0x0006cd,   1, 0x01, 0x3f800000 },
-       { 0x0007f5,   1, 0x01, 0x3f800000 },
-       { 0x0007dc,   1, 0x01, 0x39291909 },
-       { 0x0007dd,   1, 0x01, 0x79695949 },
-       { 0x0007de,   1, 0x01, 0xb9a99989 },
-       { 0x0007df,   1, 0x01, 0xf9e9d9c9 },
-       { 0x0007e8,   1, 0x01, 0x00003210 },
-       { 0x0007e9,   1, 0x01, 0x00007654 },
-       { 0x0007ea,   1, 0x01, 0x00000098 },
-       { 0x0007ec,   1, 0x01, 0x39291909 },
-       { 0x0007ed,   1, 0x01, 0x79695949 },
-       { 0x0007ee,   1, 0x01, 0xb9a99989 },
-       { 0x0007ef,   1, 0x01, 0xf9e9d9c9 },
-       { 0x0007f0,   1, 0x01, 0x00003210 },
-       { 0x0007f1,   1, 0x01, 0x00007654 },
-       { 0x0007f2,   1, 0x01, 0x00000098 },
-       { 0x0005a5,   1, 0x01, 0x00000001 },
-       { 0x000980, 128, 0x01, 0x00000000 },
-       { 0x000468,   1, 0x01, 0x00000004 },
-       { 0x00046c,   1, 0x01, 0x00000001 },
-       { 0x000470,  96, 0x01, 0x00000000 },
-       { 0x000510,  16, 0x01, 0x3f800000 },
-       { 0x000520,   1, 0x01, 0x000002b6 },
-       { 0x000529,   1, 0x01, 0x00000001 },
-       { 0x000530,  16, 0x01, 0xffff0000 },
-       { 0x000585,   1, 0x01, 0x0000003f },
-       { 0x000576,   1, 0x01, 0x00000003 },
-       { 0x000586,   1, 0x01, 0x00000040 },
-       { 0x000582,   2, 0x01, 0x00000080 },
-       { 0x0005c2,   1, 0x01, 0x00000001 },
-       { 0x000638,   2, 0x01, 0x00000001 },
-       { 0x00063a,   1, 0x01, 0x00000002 },
-       { 0x00063b,   2, 0x01, 0x00000001 },
-       { 0x00063d,   1, 0x01, 0x00000002 },
-       { 0x00063e,   1, 0x01, 0x00000001 },
-       { 0x0008b8,   8, 0x01, 0x00000001 },
-       { 0x000900,   8, 0x01, 0x00000001 },
-       { 0x000908,   8, 0x01, 0x00000002 },
-       { 0x000910,  16, 0x01, 0x00000001 },
-       { 0x000920,   8, 0x01, 0x00000002 },
-       { 0x000928,   8, 0x01, 0x00000001 },
-       { 0x000648,   9, 0x01, 0x00000001 },
-       { 0x000658,   1, 0x01, 0x0000000f },
-       { 0x0007ff,   1, 0x01, 0x0000000a },
-       { 0x00066a,   1, 0x01, 0x40000000 },
-       { 0x00066b,   1, 0x01, 0x10000000 },
-       { 0x00066c,   2, 0x01, 0xffff0000 },
-       { 0x0007af,   2, 0x01, 0x00000008 },
-       { 0x0007f6,   1, 0x01, 0x00000001 },
-       { 0x0006b2,   1, 0x01, 0x00000055 },
-       { 0x0007ad,   1, 0x01, 0x00000003 },
-       { 0x000937,   1, 0x01, 0x00000001 },
-       { 0x000971,   1, 0x01, 0x00000008 },
-       { 0x000972,   1, 0x01, 0x00000040 },
-       { 0x000973,   1, 0x01, 0x0000012c },
-       { 0x00097c,   1, 0x01, 0x00000040 },
-       { 0x000979,   1, 0x01, 0x00000003 },
-       { 0x000975,   1, 0x01, 0x00000020 },
-       { 0x000976,   1, 0x01, 0x00000001 },
-       { 0x000977,   1, 0x01, 0x00000020 },
-       { 0x000978,   1, 0x01, 0x00000001 },
-       { 0x000957,   1, 0x01, 0x00000003 },
-       { 0x00095e,   1, 0x01, 0x20164010 },
-       { 0x00095f,   1, 0x01, 0x00000020 },
-       { 0x000683,   1, 0x01, 0x00000006 },
-       { 0x000685,   1, 0x01, 0x003fffff },
-       { 0x000687,   1, 0x01, 0x00000c48 },
-       { 0x0006a0,   1, 0x01, 0x00000005 },
-       { 0x000840,   1, 0x01, 0x00300008 },
-       { 0x000841,   1, 0x01, 0x04000080 },
-       { 0x000842,   1, 0x01, 0x00300008 },
-       { 0x000843,   1, 0x01, 0x04000080 },
-       { 0x000818,   8, 0x01, 0x00000000 },
-       { 0x000848,  16, 0x01, 0x00000000 },
-       { 0x000738,   1, 0x01, 0x00000000 },
-       { 0x0006aa,   1, 0x01, 0x00000001 },
-       { 0x0006ab,   1, 0x01, 0x00000002 },
-       { 0x0006ac,   1, 0x01, 0x00000080 },
-       { 0x0006ad,   2, 0x01, 0x00000100 },
-       { 0x0006b1,   1, 0x01, 0x00000011 },
-       { 0x0006bb,   1, 0x01, 0x000000cf },
-       { 0x0006ce,   1, 0x01, 0x2a712488 },
-       { 0x000739,   1, 0x01, 0x4085c000 },
-       { 0x00073a,   1, 0x01, 0x00000080 },
-       { 0x000786,   1, 0x01, 0x80000100 },
-       { 0x00073c,   1, 0x01, 0x00010100 },
-       { 0x00073d,   1, 0x01, 0x02800000 },
-       { 0x000787,   1, 0x01, 0x000000cf },
-       { 0x00078c,   1, 0x01, 0x00000008 },
-       { 0x000792,   1, 0x01, 0x00000001 },
-       { 0x000794,   3, 0x01, 0x00000001 },
-       { 0x000797,   1, 0x01, 0x000000cf },
-       { 0x000836,   1, 0x01, 0x00000001 },
-       { 0x00079a,   1, 0x01, 0x00000002 },
-       { 0x000833,   1, 0x01, 0x04444480 },
-       { 0x0007a1,   1, 0x01, 0x00000001 },
-       { 0x0007a3,   3, 0x01, 0x00000001 },
-       { 0x000831,   1, 0x01, 0x00000004 },
-       { 0x00080c,   1, 0x01, 0x00000002 },
-       { 0x00080d,   2, 0x01, 0x00000100 },
-       { 0x00080f,   1, 0x01, 0x00000001 },
-       { 0x000823,   1, 0x01, 0x00000002 },
-       { 0x000824,   2, 0x01, 0x00000100 },
-       { 0x000826,   1, 0x01, 0x00000001 },
-       { 0x00095d,   1, 0x01, 0x00000001 },
-       { 0x00082b,   1, 0x01, 0x00000004 },
-       { 0x000942,   1, 0x01, 0x00010001 },
-       { 0x000943,   1, 0x01, 0x00000001 },
-       { 0x000944,   1, 0x01, 0x00000022 },
-       { 0x0007c5,   1, 0x01, 0x00010001 },
-       { 0x000834,   1, 0x01, 0x00000001 },
-       { 0x0007c7,   1, 0x01, 0x00000001 },
-       { 0x00c1b0,   8, 0x01, 0x0000000f },
-       { 0x00c1b8,   1, 0x01, 0x0fac6881 },
-       { 0x00c1b9,   1, 0x01, 0x00fac688 },
-       { 0x01e100,   1, 0x01, 0x00000001 },
-       { 0x001000,   1, 0x01, 0x00000002 },
-       { 0x0006aa,   1, 0x01, 0x00000001 },
-       { 0x0006ad,   2, 0x01, 0x00000100 },
-       { 0x0006b1,   1, 0x01, 0x00000011 },
-       { 0x00078c,   1, 0x01, 0x00000008 },
-       { 0x000792,   1, 0x01, 0x00000001 },
-       { 0x000794,   3, 0x01, 0x00000001 },
-       { 0x000797,   1, 0x01, 0x000000cf },
-       { 0x00079a,   1, 0x01, 0x00000002 },
-       { 0x000833,   1, 0x01, 0x04444480 },
-       { 0x0007a1,   1, 0x01, 0x00000001 },
-       { 0x0007a3,   3, 0x01, 0x00000001 },
-       { 0x000831,   1, 0x01, 0x00000004 },
-       { 0x01e100,   1, 0x01, 0x00000001 },
-       { 0x001000,   1, 0x01, 0x00000014 },
-       { 0x000351,   1, 0x01, 0x00000100 },
-       { 0x000957,   1, 0x01, 0x00000003 },
-       { 0x00095d,   1, 0x01, 0x00000001 },
-       { 0x00082b,   1, 0x01, 0x00000004 },
-       { 0x000942,   1, 0x01, 0x00010001 },
-       { 0x000943,   1, 0x01, 0x00000001 },
-       { 0x0007c5,   1, 0x01, 0x00010001 },
-       { 0x000834,   1, 0x01, 0x00000001 },
-       { 0x0007c7,   1, 0x01, 0x00000001 },
-       { 0x01e100,   1, 0x01, 0x00000001 },
-       { 0x001000,   1, 0x01, 0x00000001 },
-       { 0x00080c,   1, 0x01, 0x00000002 },
-       { 0x00080d,   2, 0x01, 0x00000100 },
-       { 0x00080f,   1, 0x01, 0x00000001 },
-       { 0x000823,   1, 0x01, 0x00000002 },
-       { 0x000824,   2, 0x01, 0x00000100 },
-       { 0x000826,   1, 0x01, 0x00000001 },
-       { 0x01e100,   1, 0x01, 0x00000001 },
-       {}
-};
-
-const struct nvc0_graph_pack
-nvc0_grctx_pack_icmd[] = {
-       { nvc0_grctx_init_icmd_0 },
-       {}
-};
-
-static const struct nvc0_graph_init
-nvc0_grctx_init_9097_0[] = {
-       { 0x000800,   8, 0x40, 0x00000000 },
-       { 0x000804,   8, 0x40, 0x00000000 },
-       { 0x000808,   8, 0x40, 0x00000400 },
-       { 0x00080c,   8, 0x40, 0x00000300 },
-       { 0x000810,   1, 0x04, 0x000000cf },
-       { 0x000850,   7, 0x40, 0x00000000 },
-       { 0x000814,   8, 0x40, 0x00000040 },
-       { 0x000818,   8, 0x40, 0x00000001 },
-       { 0x00081c,   8, 0x40, 0x00000000 },
-       { 0x000820,   8, 0x40, 0x00000000 },
-       { 0x002700,   8, 0x20, 0x00000000 },
-       { 0x002704,   8, 0x20, 0x00000000 },
-       { 0x002708,   8, 0x20, 0x00000000 },
-       { 0x00270c,   8, 0x20, 0x00000000 },
-       { 0x002710,   8, 0x20, 0x00014000 },
-       { 0x002714,   8, 0x20, 0x00000040 },
-       { 0x001c00,  16, 0x10, 0x00000000 },
-       { 0x001c04,  16, 0x10, 0x00000000 },
-       { 0x001c08,  16, 0x10, 0x00000000 },
-       { 0x001c0c,  16, 0x10, 0x00000000 },
-       { 0x001d00,  16, 0x10, 0x00000000 },
-       { 0x001d04,  16, 0x10, 0x00000000 },
-       { 0x001d08,  16, 0x10, 0x00000000 },
-       { 0x001d0c,  16, 0x10, 0x00000000 },
-       { 0x001f00,  16, 0x08, 0x00000000 },
-       { 0x001f04,  16, 0x08, 0x00000000 },
-       { 0x001f80,  16, 0x08, 0x00000000 },
-       { 0x001f84,  16, 0x08, 0x00000000 },
-       { 0x002200,   5, 0x10, 0x00000022 },
-       { 0x002000,   1, 0x04, 0x00000000 },
-       { 0x002040,   1, 0x04, 0x00000011 },
-       { 0x002080,   1, 0x04, 0x00000020 },
-       { 0x0020c0,   1, 0x04, 0x00000030 },
-       { 0x002100,   1, 0x04, 0x00000040 },
-       { 0x002140,   1, 0x04, 0x00000051 },
-       { 0x00200c,   6, 0x40, 0x00000001 },
-       { 0x002010,   1, 0x04, 0x00000000 },
-       { 0x002050,   1, 0x04, 0x00000000 },
-       { 0x002090,   1, 0x04, 0x00000001 },
-       { 0x0020d0,   1, 0x04, 0x00000002 },
-       { 0x002110,   1, 0x04, 0x00000003 },
-       { 0x002150,   1, 0x04, 0x00000004 },
-       { 0x000380,   4, 0x20, 0x00000000 },
-       { 0x000384,   4, 0x20, 0x00000000 },
-       { 0x000388,   4, 0x20, 0x00000000 },
-       { 0x00038c,   4, 0x20, 0x00000000 },
-       { 0x000700,   4, 0x10, 0x00000000 },
-       { 0x000704,   4, 0x10, 0x00000000 },
-       { 0x000708,   4, 0x10, 0x00000000 },
-       { 0x002800, 128, 0x04, 0x00000000 },
-       { 0x000a00,  16, 0x20, 0x00000000 },
-       { 0x000a04,  16, 0x20, 0x00000000 },
-       { 0x000a08,  16, 0x20, 0x00000000 },
-       { 0x000a0c,  16, 0x20, 0x00000000 },
-       { 0x000a10,  16, 0x20, 0x00000000 },
-       { 0x000a14,  16, 0x20, 0x00000000 },
-       { 0x000c00,  16, 0x10, 0x00000000 },
-       { 0x000c04,  16, 0x10, 0x00000000 },
-       { 0x000c08,  16, 0x10, 0x00000000 },
-       { 0x000c0c,  16, 0x10, 0x3f800000 },
-       { 0x000d00,   8, 0x08, 0xffff0000 },
-       { 0x000d04,   8, 0x08, 0xffff0000 },
-       { 0x000e00,  16, 0x10, 0x00000000 },
-       { 0x000e04,  16, 0x10, 0xffff0000 },
-       { 0x000e08,  16, 0x10, 0xffff0000 },
-       { 0x000d40,   4, 0x08, 0x00000000 },
-       { 0x000d44,   4, 0x08, 0x00000000 },
-       { 0x001e00,   8, 0x20, 0x00000001 },
-       { 0x001e04,   8, 0x20, 0x00000001 },
-       { 0x001e08,   8, 0x20, 0x00000002 },
-       { 0x001e0c,   8, 0x20, 0x00000001 },
-       { 0x001e10,   8, 0x20, 0x00000001 },
-       { 0x001e14,   8, 0x20, 0x00000002 },
-       { 0x001e18,   8, 0x20, 0x00000001 },
-       { 0x003400, 128, 0x04, 0x00000000 },
-       { 0x00030c,   1, 0x04, 0x00000001 },
-       { 0x001944,   1, 0x04, 0x00000000 },
-       { 0x001514,   1, 0x04, 0x00000000 },
-       { 0x000d68,   1, 0x04, 0x0000ffff },
-       { 0x00121c,   1, 0x04, 0x0fac6881 },
-       { 0x000fac,   1, 0x04, 0x00000001 },
-       { 0x001538,   1, 0x04, 0x00000001 },
-       { 0x000fe0,   2, 0x04, 0x00000000 },
-       { 0x000fe8,   1, 0x04, 0x00000014 },
-       { 0x000fec,   1, 0x04, 0x00000040 },
-       { 0x000ff0,   1, 0x04, 0x00000000 },
-       { 0x00179c,   1, 0x04, 0x00000000 },
-       { 0x001228,   1, 0x04, 0x00000400 },
-       { 0x00122c,   1, 0x04, 0x00000300 },
-       { 0x001230,   1, 0x04, 0x00010001 },
-       { 0x0007f8,   1, 0x04, 0x00000000 },
-       { 0x0015b4,   1, 0x04, 0x00000001 },
-       { 0x0015cc,   1, 0x04, 0x00000000 },
-       { 0x001534,   1, 0x04, 0x00000000 },
-       { 0x000fb0,   1, 0x04, 0x00000000 },
-       { 0x0015d0,   1, 0x04, 0x00000000 },
-       { 0x00153c,   1, 0x04, 0x00000000 },
-       { 0x0016b4,   1, 0x04, 0x00000003 },
-       { 0x000fbc,   4, 0x04, 0x0000ffff },
-       { 0x000df8,   2, 0x04, 0x00000000 },
-       { 0x001948,   1, 0x04, 0x00000000 },
-       { 0x001970,   1, 0x04, 0x00000001 },
-       { 0x00161c,   1, 0x04, 0x000009f0 },
-       { 0x000dcc,   1, 0x04, 0x00000010 },
-       { 0x00163c,   1, 0x04, 0x00000000 },
-       { 0x0015e4,   1, 0x04, 0x00000000 },
-       { 0x001160,  32, 0x04, 0x25e00040 },
-       { 0x001880,  32, 0x04, 0x00000000 },
-       { 0x000f84,   2, 0x04, 0x00000000 },
-       { 0x0017c8,   2, 0x04, 0x00000000 },
-       { 0x0017d0,   1, 0x04, 0x000000ff },
-       { 0x0017d4,   1, 0x04, 0xffffffff },
-       { 0x0017d8,   1, 0x04, 0x00000002 },
-       { 0x0017dc,   1, 0x04, 0x00000000 },
-       { 0x0015f4,   2, 0x04, 0x00000000 },
-       { 0x001434,   2, 0x04, 0x00000000 },
-       { 0x000d74,   1, 0x04, 0x00000000 },
-       { 0x000dec,   1, 0x04, 0x00000001 },
-       { 0x0013a4,   1, 0x04, 0x00000000 },
-       { 0x001318,   1, 0x04, 0x00000001 },
-       { 0x001644,   1, 0x04, 0x00000000 },
-       { 0x000748,   1, 0x04, 0x00000000 },
-       { 0x000de8,   1, 0x04, 0x00000000 },
-       { 0x001648,   1, 0x04, 0x00000000 },
-       { 0x0012a4,   1, 0x04, 0x00000000 },
-       { 0x001120,   4, 0x04, 0x00000000 },
-       { 0x001118,   1, 0x04, 0x00000000 },
-       { 0x00164c,   1, 0x04, 0x00000000 },
-       { 0x001658,   1, 0x04, 0x00000000 },
-       { 0x001910,   1, 0x04, 0x00000290 },
-       { 0x001518,   1, 0x04, 0x00000000 },
-       { 0x00165c,   1, 0x04, 0x00000001 },
-       { 0x001520,   1, 0x04, 0x00000000 },
-       { 0x001604,   1, 0x04, 0x00000000 },
-       { 0x001570,   1, 0x04, 0x00000000 },
-       { 0x0013b0,   2, 0x04, 0x3f800000 },
-       { 0x00020c,   1, 0x04, 0x00000000 },
-       { 0x001670,   1, 0x04, 0x30201000 },
-       { 0x001674,   1, 0x04, 0x70605040 },
-       { 0x001678,   1, 0x04, 0xb8a89888 },
-       { 0x00167c,   1, 0x04, 0xf8e8d8c8 },
-       { 0x00166c,   1, 0x04, 0x00000000 },
-       { 0x001680,   1, 0x04, 0x00ffff00 },
-       { 0x0012d0,   1, 0x04, 0x00000003 },
-       { 0x0012d4,   1, 0x04, 0x00000002 },
-       { 0x001684,   2, 0x04, 0x00000000 },
-       { 0x000dac,   2, 0x04, 0x00001b02 },
-       { 0x000db4,   1, 0x04, 0x00000000 },
-       { 0x00168c,   1, 0x04, 0x00000000 },
-       { 0x0015bc,   1, 0x04, 0x00000000 },
-       { 0x00156c,   1, 0x04, 0x00000000 },
-       { 0x00187c,   1, 0x04, 0x00000000 },
-       { 0x001110,   1, 0x04, 0x00000001 },
-       { 0x000dc0,   3, 0x04, 0x00000000 },
-       { 0x001234,   1, 0x04, 0x00000000 },
-       { 0x001690,   1, 0x04, 0x00000000 },
-       { 0x0012ac,   1, 0x04, 0x00000001 },
-       { 0x0002c4,   1, 0x04, 0x00000000 },
-       { 0x000790,   5, 0x04, 0x00000000 },
-       { 0x00077c,   1, 0x04, 0x00000000 },
-       { 0x001000,   1, 0x04, 0x00000010 },
-       { 0x0010fc,   1, 0x04, 0x00000000 },
-       { 0x001290,   1, 0x04, 0x00000000 },
-       { 0x000218,   1, 0x04, 0x00000010 },
-       { 0x0012d8,   1, 0x04, 0x00000000 },
-       { 0x0012dc,   1, 0x04, 0x00000010 },
-       { 0x000d94,   1, 0x04, 0x00000001 },
-       { 0x00155c,   2, 0x04, 0x00000000 },
-       { 0x001564,   1, 0x04, 0x00001fff },
-       { 0x001574,   2, 0x04, 0x00000000 },
-       { 0x00157c,   1, 0x04, 0x003fffff },
-       { 0x001354,   1, 0x04, 0x00000000 },
-       { 0x001664,   1, 0x04, 0x00000000 },
-       { 0x001610,   1, 0x04, 0x00000012 },
-       { 0x001608,   2, 0x04, 0x00000000 },
-       { 0x00162c,   1, 0x04, 0x00000003 },
-       { 0x000210,   1, 0x04, 0x00000000 },
-       { 0x000320,   1, 0x04, 0x00000000 },
-       { 0x000324,   6, 0x04, 0x3f800000 },
-       { 0x000750,   1, 0x04, 0x00000000 },
-       { 0x000760,   1, 0x04, 0x39291909 },
-       { 0x000764,   1, 0x04, 0x79695949 },
-       { 0x000768,   1, 0x04, 0xb9a99989 },
-       { 0x00076c,   1, 0x04, 0xf9e9d9c9 },
-       { 0x000770,   1, 0x04, 0x30201000 },
-       { 0x000774,   1, 0x04, 0x70605040 },
-       { 0x000778,   1, 0x04, 0x00009080 },
-       { 0x000780,   1, 0x04, 0x39291909 },
-       { 0x000784,   1, 0x04, 0x79695949 },
-       { 0x000788,   1, 0x04, 0xb9a99989 },
-       { 0x00078c,   1, 0x04, 0xf9e9d9c9 },
-       { 0x0007d0,   1, 0x04, 0x30201000 },
-       { 0x0007d4,   1, 0x04, 0x70605040 },
-       { 0x0007d8,   1, 0x04, 0x00009080 },
-       { 0x00037c,   1, 0x04, 0x00000001 },
-       { 0x000740,   2, 0x04, 0x00000000 },
-       { 0x002600,   1, 0x04, 0x00000000 },
-       { 0x001918,   1, 0x04, 0x00000000 },
-       { 0x00191c,   1, 0x04, 0x00000900 },
-       { 0x001920,   1, 0x04, 0x00000405 },
-       { 0x001308,   1, 0x04, 0x00000001 },
-       { 0x001924,   1, 0x04, 0x00000000 },
-       { 0x0013ac,   1, 0x04, 0x00000000 },
-       { 0x00192c,   1, 0x04, 0x00000001 },
-       { 0x00193c,   1, 0x04, 0x00002c1c },
-       { 0x000d7c,   1, 0x04, 0x00000000 },
-       { 0x000f8c,   1, 0x04, 0x00000000 },
-       { 0x0002c0,   1, 0x04, 0x00000001 },
-       { 0x001510,   1, 0x04, 0x00000000 },
-       { 0x001940,   1, 0x04, 0x00000000 },
-       { 0x000ff4,   2, 0x04, 0x00000000 },
-       { 0x00194c,   2, 0x04, 0x00000000 },
-       { 0x001968,   1, 0x04, 0x00000000 },
-       { 0x001590,   1, 0x04, 0x0000003f },
-       { 0x0007e8,   4, 0x04, 0x00000000 },
-       { 0x00196c,   1, 0x04, 0x00000011 },
-       { 0x00197c,   1, 0x04, 0x00000000 },
-       { 0x000fcc,   2, 0x04, 0x00000000 },
-       { 0x0002d8,   1, 0x04, 0x00000040 },
-       { 0x001980,   1, 0x04, 0x00000080 },
-       { 0x001504,   1, 0x04, 0x00000080 },
-       { 0x001984,   1, 0x04, 0x00000000 },
-       { 0x000300,   1, 0x04, 0x00000001 },
-       { 0x0013a8,   1, 0x04, 0x00000000 },
-       { 0x0012ec,   1, 0x04, 0x00000000 },
-       { 0x001310,   1, 0x04, 0x00000000 },
-       { 0x001314,   1, 0x04, 0x00000001 },
-       { 0x001380,   1, 0x04, 0x00000000 },
-       { 0x001384,   4, 0x04, 0x00000001 },
-       { 0x001394,   1, 0x04, 0x00000000 },
-       { 0x00139c,   1, 0x04, 0x00000000 },
-       { 0x001398,   1, 0x04, 0x00000000 },
-       { 0x001594,   1, 0x04, 0x00000000 },
-       { 0x001598,   4, 0x04, 0x00000001 },
-       { 0x000f54,   3, 0x04, 0x00000000 },
-       { 0x0019bc,   1, 0x04, 0x00000000 },
-       { 0x000f9c,   2, 0x04, 0x00000000 },
-       { 0x0012cc,   1, 0x04, 0x00000000 },
-       { 0x0012e8,   1, 0x04, 0x00000000 },
-       { 0x00130c,   1, 0x04, 0x00000001 },
-       { 0x001360,   8, 0x04, 0x00000000 },
-       { 0x00133c,   2, 0x04, 0x00000001 },
-       { 0x001344,   1, 0x04, 0x00000002 },
-       { 0x001348,   2, 0x04, 0x00000001 },
-       { 0x001350,   1, 0x04, 0x00000002 },
-       { 0x001358,   1, 0x04, 0x00000001 },
-       { 0x0012e4,   1, 0x04, 0x00000000 },
-       { 0x00131c,   4, 0x04, 0x00000000 },
-       { 0x0019c0,   1, 0x04, 0x00000000 },
-       { 0x001140,   1, 0x04, 0x00000000 },
-       { 0x0019c4,   1, 0x04, 0x00000000 },
-       { 0x0019c8,   1, 0x04, 0x00001500 },
-       { 0x00135c,   1, 0x04, 0x00000000 },
-       { 0x000f90,   1, 0x04, 0x00000000 },
-       { 0x0019e0,   8, 0x04, 0x00000001 },
-       { 0x0019cc,   1, 0x04, 0x00000001 },
-       { 0x0015b8,   1, 0x04, 0x00000000 },
-       { 0x001a00,   1, 0x04, 0x00001111 },
-       { 0x001a04,   7, 0x04, 0x00000000 },
-       { 0x000d6c,   2, 0x04, 0xffff0000 },
-       { 0x0010f8,   1, 0x04, 0x00001010 },
-       { 0x000d80,   5, 0x04, 0x00000000 },
-       { 0x000da0,   1, 0x04, 0x00000000 },
-       { 0x001508,   1, 0x04, 0x80000000 },
-       { 0x00150c,   1, 0x04, 0x40000000 },
-       { 0x001668,   1, 0x04, 0x00000000 },
-       { 0x000318,   2, 0x04, 0x00000008 },
-       { 0x000d9c,   1, 0x04, 0x00000001 },
-       { 0x0007dc,   1, 0x04, 0x00000000 },
-       { 0x00074c,   1, 0x04, 0x00000055 },
-       { 0x001420,   1, 0x04, 0x00000003 },
-       { 0x0017bc,   2, 0x04, 0x00000000 },
-       { 0x0017c4,   1, 0x04, 0x00000001 },
-       { 0x001008,   1, 0x04, 0x00000008 },
-       { 0x00100c,   1, 0x04, 0x00000040 },
-       { 0x001010,   1, 0x04, 0x0000012c },
-       { 0x000d60,   1, 0x04, 0x00000040 },
-       { 0x00075c,   1, 0x04, 0x00000003 },
-       { 0x001018,   1, 0x04, 0x00000020 },
-       { 0x00101c,   1, 0x04, 0x00000001 },
-       { 0x001020,   1, 0x04, 0x00000020 },
-       { 0x001024,   1, 0x04, 0x00000001 },
-       { 0x001444,   3, 0x04, 0x00000000 },
-       { 0x000360,   1, 0x04, 0x20164010 },
-       { 0x000364,   1, 0x04, 0x00000020 },
-       { 0x000368,   1, 0x04, 0x00000000 },
-       { 0x000de4,   1, 0x04, 0x00000000 },
-       { 0x000204,   1, 0x04, 0x00000006 },
-       { 0x000208,   1, 0x04, 0x00000000 },
-       { 0x0002cc,   1, 0x04, 0x003fffff },
-       { 0x0002d0,   1, 0x04, 0x00000c48 },
-       { 0x001220,   1, 0x04, 0x00000005 },
-       { 0x000fdc,   1, 0x04, 0x00000000 },
-       { 0x000f98,   1, 0x04, 0x00300008 },
-       { 0x001284,   1, 0x04, 0x04000080 },
-       { 0x001450,   1, 0x04, 0x00300008 },
-       { 0x001454,   1, 0x04, 0x04000080 },
-       { 0x000214,   1, 0x04, 0x00000000 },
-       {}
-};
-
-const struct nvc0_graph_init
-nvc0_grctx_init_902d_0[] = {
-       { 0x000200,   1, 0x04, 0x000000cf },
-       { 0x000204,   1, 0x04, 0x00000001 },
-       { 0x000208,   1, 0x04, 0x00000020 },
-       { 0x00020c,   1, 0x04, 0x00000001 },
-       { 0x000210,   1, 0x04, 0x00000000 },
-       { 0x000214,   1, 0x04, 0x00000080 },
-       { 0x000218,   2, 0x04, 0x00000100 },
-       { 0x000220,   2, 0x04, 0x00000000 },
-       { 0x000230,   1, 0x04, 0x000000cf },
-       { 0x000234,   1, 0x04, 0x00000001 },
-       { 0x000238,   1, 0x04, 0x00000020 },
-       { 0x00023c,   1, 0x04, 0x00000001 },
-       { 0x000244,   1, 0x04, 0x00000080 },
-       { 0x000248,   2, 0x04, 0x00000100 },
-       {}
-};
-
-const struct nvc0_graph_init
-nvc0_grctx_init_9039_0[] = {
-       { 0x00030c,   3, 0x04, 0x00000000 },
-       { 0x000320,   1, 0x04, 0x00000000 },
-       { 0x000238,   2, 0x04, 0x00000000 },
-       { 0x000318,   2, 0x04, 0x00000000 },
-       {}
-};
-
-const struct nvc0_graph_init
-nvc0_grctx_init_90c0_0[] = {
-       { 0x00270c,   8, 0x20, 0x00000000 },
-       { 0x00030c,   1, 0x04, 0x00000001 },
-       { 0x001944,   1, 0x04, 0x00000000 },
-       { 0x000758,   1, 0x04, 0x00000100 },
-       { 0x0002c4,   1, 0x04, 0x00000000 },
-       { 0x000790,   5, 0x04, 0x00000000 },
-       { 0x00077c,   1, 0x04, 0x00000000 },
-       { 0x000204,   3, 0x04, 0x00000000 },
-       { 0x000214,   1, 0x04, 0x00000000 },
-       { 0x00024c,   1, 0x04, 0x00000000 },
-       { 0x000d94,   1, 0x04, 0x00000001 },
-       { 0x001608,   2, 0x04, 0x00000000 },
-       { 0x001664,   1, 0x04, 0x00000000 },
-       {}
-};
-
-const struct nvc0_graph_pack
-nvc0_grctx_pack_mthd[] = {
-       { nvc0_grctx_init_9097_0, 0x9097 },
-       { nvc0_grctx_init_902d_0, 0x902d },
-       { nvc0_grctx_init_9039_0, 0x9039 },
-       { nvc0_grctx_init_90c0_0, 0x90c0 },
-       {}
-};
-
-const struct nvc0_graph_init
-nvc0_grctx_init_main_0[] = {
-       { 0x400204,   2, 0x04, 0x00000000 },
-       {}
-};
-
-const struct nvc0_graph_init
-nvc0_grctx_init_fe_0[] = {
-       { 0x404004,  11, 0x04, 0x00000000 },
-       { 0x404044,   1, 0x04, 0x00000000 },
-       { 0x404094,  13, 0x04, 0x00000000 },
-       { 0x4040c8,   1, 0x04, 0xf0000087 },
-       { 0x4040d0,   6, 0x04, 0x00000000 },
-       { 0x4040e8,   1, 0x04, 0x00001000 },
-       { 0x4040f8,   1, 0x04, 0x00000000 },
-       { 0x404130,   2, 0x04, 0x00000000 },
-       { 0x404138,   1, 0x04, 0x20000040 },
-       { 0x404150,   1, 0x04, 0x0000002e },
-       { 0x404154,   1, 0x04, 0x00000400 },
-       { 0x404158,   1, 0x04, 0x00000200 },
-       { 0x404164,   1, 0x04, 0x00000055 },
-       { 0x404168,   1, 0x04, 0x00000000 },
-       { 0x404174,   3, 0x04, 0x00000000 },
-       { 0x404200,   8, 0x04, 0x00000000 },
-       {}
-};
-
-const struct nvc0_graph_init
-nvc0_grctx_init_pri_0[] = {
-       { 0x404404,  14, 0x04, 0x00000000 },
-       { 0x404460,   2, 0x04, 0x00000000 },
-       { 0x404468,   1, 0x04, 0x00ffffff },
-       { 0x40446c,   1, 0x04, 0x00000000 },
-       { 0x404480,   1, 0x04, 0x00000001 },
-       { 0x404498,   1, 0x04, 0x00000001 },
-       {}
-};
-
-const struct nvc0_graph_init
-nvc0_grctx_init_memfmt_0[] = {
-       { 0x404604,   1, 0x04, 0x00000015 },
-       { 0x404608,   1, 0x04, 0x00000000 },
-       { 0x40460c,   1, 0x04, 0x00002e00 },
-       { 0x404610,   1, 0x04, 0x00000100 },
-       { 0x404618,   8, 0x04, 0x00000000 },
-       { 0x404638,   1, 0x04, 0x00000004 },
-       { 0x40463c,   8, 0x04, 0x00000000 },
-       { 0x40465c,   1, 0x04, 0x007f0100 },
-       { 0x404660,   7, 0x04, 0x00000000 },
-       { 0x40467c,   1, 0x04, 0x00000002 },
-       { 0x404680,   8, 0x04, 0x00000000 },
-       { 0x4046a0,   1, 0x04, 0x007f0080 },
-       { 0x4046a4,  18, 0x04, 0x00000000 },
-       { 0x4046f0,   2, 0x04, 0x00000000 },
-       { 0x404700,  13, 0x04, 0x00000000 },
-       { 0x404734,   1, 0x04, 0x00000100 },
-       { 0x404738,   8, 0x04, 0x00000000 },
-       {}
-};
-
-static const struct nvc0_graph_init
-nvc0_grctx_init_ds_0[] = {
-       { 0x405800,   1, 0x04, 0x078000bf },
-       { 0x405830,   1, 0x04, 0x02180000 },
-       { 0x405834,   2, 0x04, 0x00000000 },
-       { 0x405854,   1, 0x04, 0x00000000 },
-       { 0x405870,   4, 0x04, 0x00000001 },
-       { 0x405a00,   2, 0x04, 0x00000000 },
-       { 0x405a18,   1, 0x04, 0x00000000 },
-       {}
-};
-
-static const struct nvc0_graph_init
-nvc0_grctx_init_pd_0[] = {
-       { 0x406020,   1, 0x04, 0x000103c1 },
-       { 0x406028,   4, 0x04, 0x00000001 },
-       { 0x4064a8,   1, 0x04, 0x00000000 },
-       { 0x4064ac,   1, 0x04, 0x00003fff },
-       { 0x4064b4,   2, 0x04, 0x00000000 },
-       {}
-};
-
-const struct nvc0_graph_init
-nvc0_grctx_init_rstr2d_0[] = {
-       { 0x407804,   1, 0x04, 0x00000023 },
-       { 0x40780c,   1, 0x04, 0x0a418820 },
-       { 0x407810,   1, 0x04, 0x062080e6 },
-       { 0x407814,   1, 0x04, 0x020398a4 },
-       { 0x407818,   1, 0x04, 0x0e629062 },
-       { 0x40781c,   1, 0x04, 0x0a418820 },
-       { 0x407820,   1, 0x04, 0x000000e6 },
-       { 0x4078bc,   1, 0x04, 0x00000103 },
-       {}
-};
-
-const struct nvc0_graph_init
-nvc0_grctx_init_scc_0[] = {
-       { 0x408000,   2, 0x04, 0x00000000 },
-       { 0x408008,   1, 0x04, 0x00000018 },
-       { 0x40800c,   2, 0x04, 0x00000000 },
-       { 0x408014,   1, 0x04, 0x00000069 },
-       { 0x408018,   1, 0x04, 0xe100e100 },
-       { 0x408064,   1, 0x04, 0x00000000 },
-       {}
-};
-
-static const struct nvc0_graph_init
-nvc0_grctx_init_be_0[] = {
-       { 0x408800,   1, 0x04, 0x02802a3c },
-       { 0x408804,   1, 0x04, 0x00000040 },
-       { 0x408808,   1, 0x04, 0x0003e00d },
-       { 0x408900,   1, 0x04, 0x3080b801 },
-       { 0x408904,   1, 0x04, 0x02000001 },
-       { 0x408908,   1, 0x04, 0x00c80929 },
-       { 0x408980,   1, 0x04, 0x0000011d },
-       {}
-};
-
-const struct nvc0_graph_pack
-nvc0_grctx_pack_hub[] = {
-       { nvc0_grctx_init_main_0 },
-       { nvc0_grctx_init_fe_0 },
-       { nvc0_grctx_init_pri_0 },
-       { nvc0_grctx_init_memfmt_0 },
-       { nvc0_grctx_init_ds_0 },
-       { nvc0_grctx_init_pd_0 },
-       { nvc0_grctx_init_rstr2d_0 },
-       { nvc0_grctx_init_scc_0 },
-       { nvc0_grctx_init_be_0 },
-       {}
-};
-
-const struct nvc0_graph_init
-nvc0_grctx_init_gpc_unk_0[] = {
-       { 0x418380,   1, 0x04, 0x00000016 },
-       {}
-};
-
-const struct nvc0_graph_init
-nvc0_grctx_init_prop_0[] = {
-       { 0x418400,   1, 0x04, 0x38004e00 },
-       { 0x418404,   1, 0x04, 0x71e0ffff },
-       { 0x418408,   1, 0x04, 0x00000000 },
-       { 0x41840c,   1, 0x04, 0x00001008 },
-       { 0x418410,   1, 0x04, 0x0fff0fff },
-       { 0x418414,   1, 0x04, 0x00200fff },
-       { 0x418450,   6, 0x04, 0x00000000 },
-       { 0x418468,   1, 0x04, 0x00000001 },
-       { 0x41846c,   2, 0x04, 0x00000000 },
-       {}
-};
-
-const struct nvc0_graph_init
-nvc0_grctx_init_gpc_unk_1[] = {
-       { 0x418600,   1, 0x04, 0x0000001f },
-       { 0x418684,   1, 0x04, 0x0000000f },
-       { 0x418700,   1, 0x04, 0x00000002 },
-       { 0x418704,   1, 0x04, 0x00000080 },
-       { 0x418708,   1, 0x04, 0x00000000 },
-       { 0x41870c,   1, 0x04, 0x07c80000 },
-       { 0x418710,   1, 0x04, 0x00000000 },
-       {}
-};
-
-static const struct nvc0_graph_init
-nvc0_grctx_init_setup_0[] = {
-       { 0x418800,   1, 0x04, 0x0006860a },
-       { 0x418808,   3, 0x04, 0x00000000 },
-       { 0x418828,   1, 0x04, 0x00008442 },
-       { 0x418830,   1, 0x04, 0x00000001 },
-       { 0x4188d8,   1, 0x04, 0x00000008 },
-       { 0x4188e0,   1, 0x04, 0x01000000 },
-       { 0x4188e8,   5, 0x04, 0x00000000 },
-       { 0x4188fc,   1, 0x04, 0x00100000 },
-       {}
-};
-
-const struct nvc0_graph_init
-nvc0_grctx_init_zcull_0[] = {
-       { 0x41891c,   1, 0x04, 0x00ff00ff },
-       { 0x418924,   1, 0x04, 0x00000000 },
-       { 0x418928,   1, 0x04, 0x00ffff00 },
-       { 0x41892c,   1, 0x04, 0x0000ff00 },
-       {}
-};
-
-const struct nvc0_graph_init
-nvc0_grctx_init_crstr_0[] = {
-       { 0x418b00,   1, 0x04, 0x00000000 },
-       { 0x418b08,   1, 0x04, 0x0a418820 },
-       { 0x418b0c,   1, 0x04, 0x062080e6 },
-       { 0x418b10,   1, 0x04, 0x020398a4 },
-       { 0x418b14,   1, 0x04, 0x0e629062 },
-       { 0x418b18,   1, 0x04, 0x0a418820 },
-       { 0x418b1c,   1, 0x04, 0x000000e6 },
-       { 0x418bb8,   1, 0x04, 0x00000103 },
-       {}
-};
-
-const struct nvc0_graph_init
-nvc0_grctx_init_gpm_0[] = {
-       { 0x418c08,   1, 0x04, 0x00000001 },
-       { 0x418c10,   8, 0x04, 0x00000000 },
-       { 0x418c80,   1, 0x04, 0x20200004 },
-       { 0x418c8c,   1, 0x04, 0x00000001 },
-       {}
-};
-
-const struct nvc0_graph_init
-nvc0_grctx_init_gcc_0[] = {
-       { 0x419000,   1, 0x04, 0x00000780 },
-       { 0x419004,   2, 0x04, 0x00000000 },
-       { 0x419014,   1, 0x04, 0x00000004 },
-       {}
-};
-
-const struct nvc0_graph_pack
-nvc0_grctx_pack_gpc[] = {
-       { nvc0_grctx_init_gpc_unk_0 },
-       { nvc0_grctx_init_prop_0 },
-       { nvc0_grctx_init_gpc_unk_1 },
-       { nvc0_grctx_init_setup_0 },
-       { nvc0_grctx_init_zcull_0 },
-       { nvc0_grctx_init_crstr_0 },
-       { nvc0_grctx_init_gpm_0 },
-       { nvc0_grctx_init_gcc_0 },
-       {}
-};
-
-static const struct nvc0_graph_init
-nvc0_grctx_init_zcullr_0[] = {
-       { 0x418a00,   3, 0x04, 0x00000000 },
-       { 0x418a0c,   1, 0x04, 0x00010000 },
-       { 0x418a10,   3, 0x04, 0x00000000 },
-       { 0x418a20,   3, 0x04, 0x00000000 },
-       { 0x418a2c,   1, 0x04, 0x00010000 },
-       { 0x418a30,   3, 0x04, 0x00000000 },
-       { 0x418a40,   3, 0x04, 0x00000000 },
-       { 0x418a4c,   1, 0x04, 0x00010000 },
-       { 0x418a50,   3, 0x04, 0x00000000 },
-       { 0x418a60,   3, 0x04, 0x00000000 },
-       { 0x418a6c,   1, 0x04, 0x00010000 },
-       { 0x418a70,   3, 0x04, 0x00000000 },
-       { 0x418a80,   3, 0x04, 0x00000000 },
-       { 0x418a8c,   1, 0x04, 0x00010000 },
-       { 0x418a90,   3, 0x04, 0x00000000 },
-       { 0x418aa0,   3, 0x04, 0x00000000 },
-       { 0x418aac,   1, 0x04, 0x00010000 },
-       { 0x418ab0,   3, 0x04, 0x00000000 },
-       { 0x418ac0,   3, 0x04, 0x00000000 },
-       { 0x418acc,   1, 0x04, 0x00010000 },
-       { 0x418ad0,   3, 0x04, 0x00000000 },
-       { 0x418ae0,   3, 0x04, 0x00000000 },
-       { 0x418aec,   1, 0x04, 0x00010000 },
-       { 0x418af0,   3, 0x04, 0x00000000 },
-       {}
-};
-
-const struct nvc0_graph_pack
-nvc0_grctx_pack_zcull[] = {
-       { nvc0_grctx_init_zcullr_0 },
-       {}
-};
-
-const struct nvc0_graph_init
-nvc0_grctx_init_pe_0[] = {
-       { 0x419818,   1, 0x04, 0x00000000 },
-       { 0x41983c,   1, 0x04, 0x00038bc7 },
-       { 0x419848,   1, 0x04, 0x00000000 },
-       { 0x419864,   1, 0x04, 0x0000012a },
-       { 0x419888,   1, 0x04, 0x00000000 },
-       {}
-};
-
-static const struct nvc0_graph_init
-nvc0_grctx_init_tex_0[] = {
-       { 0x419a00,   1, 0x04, 0x000001f0 },
-       { 0x419a04,   1, 0x04, 0x00000001 },
-       { 0x419a08,   1, 0x04, 0x00000023 },
-       { 0x419a0c,   1, 0x04, 0x00020000 },
-       { 0x419a10,   1, 0x04, 0x00000000 },
-       { 0x419a14,   1, 0x04, 0x00000200 },
-       {}
-};
-
-const struct nvc0_graph_init
-nvc0_grctx_init_wwdx_0[] = {
-       { 0x419b00,   1, 0x04, 0x0a418820 },
-       { 0x419b04,   1, 0x04, 0x062080e6 },
-       { 0x419b08,   1, 0x04, 0x020398a4 },
-       { 0x419b0c,   1, 0x04, 0x0e629062 },
-       { 0x419b10,   1, 0x04, 0x0a418820 },
-       { 0x419b14,   1, 0x04, 0x000000e6 },
-       { 0x419bd0,   1, 0x04, 0x00900103 },
-       { 0x419be0,   1, 0x04, 0x00000001 },
-       { 0x419be4,   1, 0x04, 0x00000000 },
-       {}
-};
-
-const struct nvc0_graph_init
-nvc0_grctx_init_mpc_0[] = {
-       { 0x419c00,   1, 0x04, 0x00000002 },
-       { 0x419c04,   1, 0x04, 0x00000006 },
-       { 0x419c08,   1, 0x04, 0x00000002 },
-       { 0x419c20,   1, 0x04, 0x00000000 },
-       {}
-};
-
-static const struct nvc0_graph_init
-nvc0_grctx_init_l1c_0[] = {
-       { 0x419cb0,   1, 0x04, 0x00060048 },
-       { 0x419ce8,   1, 0x04, 0x00000000 },
-       { 0x419cf4,   1, 0x04, 0x00000183 },
-       {}
-};
-
-const struct nvc0_graph_init
-nvc0_grctx_init_tpccs_0[] = {
-       { 0x419d20,   1, 0x04, 0x02180000 },
-       { 0x419d24,   1, 0x04, 0x00001fff },
-       {}
-};
-
-static const struct nvc0_graph_init
-nvc0_grctx_init_sm_0[] = {
-       { 0x419e04,   3, 0x04, 0x00000000 },
-       { 0x419e10,   1, 0x04, 0x00000002 },
-       { 0x419e44,   1, 0x04, 0x001beff2 },
-       { 0x419e48,   1, 0x04, 0x00000000 },
-       { 0x419e4c,   1, 0x04, 0x0000000f },
-       { 0x419e50,  17, 0x04, 0x00000000 },
-       { 0x419e98,   1, 0x04, 0x00000000 },
-       { 0x419f50,   2, 0x04, 0x00000000 },
-       {}
-};
-
-const struct nvc0_graph_pack
-nvc0_grctx_pack_tpc[] = {
-       { nvc0_grctx_init_pe_0 },
-       { nvc0_grctx_init_tex_0 },
-       { nvc0_grctx_init_wwdx_0 },
-       { nvc0_grctx_init_mpc_0 },
-       { nvc0_grctx_init_l1c_0 },
-       { nvc0_grctx_init_tpccs_0 },
-       { nvc0_grctx_init_sm_0 },
-       {}
-};
-
-/*******************************************************************************
- * PGRAPH context implementation
- ******************************************************************************/
-
-int
-nvc0_grctx_mmio_data(struct nvc0_grctx *info, u32 size, u32 align, u32 access)
-{
-       if (info->data) {
-               info->buffer[info->buffer_nr] = round_up(info->addr, align);
-               info->addr = info->buffer[info->buffer_nr] + size;
-               info->data->size = size;
-               info->data->align = align;
-               info->data->access = access;
-               info->data++;
-               return info->buffer_nr++;
-       }
-       return -1;
-}
-
-void
-nvc0_grctx_mmio_item(struct nvc0_grctx *info, u32 addr, u32 data,
-                    int shift, int buffer)
-{
-       if (info->data) {
-               if (shift >= 0) {
-                       info->mmio->addr = addr;
-                       info->mmio->data = data;
-                       info->mmio->shift = shift;
-                       info->mmio->buffer = buffer;
-                       if (buffer >= 0)
-                               data |= info->buffer[buffer] >> shift;
-                       info->mmio++;
-               } else
-                       return;
-       } else {
-               if (buffer >= 0)
-                       return;
-       }
-
-       nv_wr32(info->priv, addr, data);
-}
-
-void
-nvc0_grctx_generate_bundle(struct nvc0_grctx *info)
-{
-       const struct nvc0_grctx_oclass *impl = nvc0_grctx_impl(info->priv);
-       const u32 access = NV_MEM_ACCESS_RW | NV_MEM_ACCESS_SYS;
-       const int s = 8;
-       const int b = mmio_vram(info, impl->bundle_size, (1 << s), access);
-       mmio_refn(info, 0x408004, 0x00000000, s, b);
-       mmio_refn(info, 0x408008, 0x80000000 | (impl->bundle_size >> s), 0, b);
-       mmio_refn(info, 0x418808, 0x00000000, s, b);
-       mmio_refn(info, 0x41880c, 0x80000000 | (impl->bundle_size >> s), 0, b);
-}
-
-void
-nvc0_grctx_generate_pagepool(struct nvc0_grctx *info)
-{
-       const struct nvc0_grctx_oclass *impl = nvc0_grctx_impl(info->priv);
-       const u32 access = NV_MEM_ACCESS_RW | NV_MEM_ACCESS_SYS;
-       const int s = 8;
-       const int b = mmio_vram(info, impl->pagepool_size, (1 << s), access);
-       mmio_refn(info, 0x40800c, 0x00000000, s, b);
-       mmio_wr32(info, 0x408010, 0x80000000);
-       mmio_refn(info, 0x419004, 0x00000000, s, b);
-       mmio_wr32(info, 0x419008, 0x00000000);
-}
-
-void
-nvc0_grctx_generate_attrib(struct nvc0_grctx *info)
-{
-       struct nvc0_graph_priv *priv = info->priv;
-       const struct nvc0_grctx_oclass *impl = nvc0_grctx_impl(priv);
-       const u32 attrib = impl->attrib_nr;
-       const u32   size = 0x20 * (impl->attrib_nr_max + impl->alpha_nr_max);
-       const u32 access = NV_MEM_ACCESS_RW;
-       const int s = 12;
-       const int b = mmio_vram(info, size * priv->tpc_total, (1 << s), access);
-       int gpc, tpc;
-       u32 bo = 0;
-
-       mmio_refn(info, 0x418810, 0x80000000, s, b);
-       mmio_refn(info, 0x419848, 0x10000000, s, b);
-       mmio_wr32(info, 0x405830, (attrib << 16));
-
-       for (gpc = 0; gpc < priv->gpc_nr; gpc++) {
-               for (tpc = 0; tpc < priv->tpc_nr[gpc]; tpc++) {
-                       const u32 o = TPC_UNIT(gpc, tpc, 0x0520);
-                       mmio_skip(info, o, (attrib << 16) | ++bo);
-                       mmio_wr32(info, o, (attrib << 16) | --bo);
-                       bo += impl->attrib_nr_max;
-               }
-       }
-}
-
-void
-nvc0_grctx_generate_unkn(struct nvc0_graph_priv *priv)
-{
-}
-
-void
-nvc0_grctx_generate_tpcid(struct nvc0_graph_priv *priv)
-{
-       int gpc, tpc, id;
-
-       for (tpc = 0, id = 0; tpc < 4; tpc++) {
-               for (gpc = 0; gpc < priv->gpc_nr; gpc++) {
-                       if (tpc < priv->tpc_nr[gpc]) {
-                               nv_wr32(priv, TPC_UNIT(gpc, tpc, 0x698), id);
-                               nv_wr32(priv, TPC_UNIT(gpc, tpc, 0x4e8), id);
-                               nv_wr32(priv, GPC_UNIT(gpc, 0x0c10 + tpc * 4), id);
-                               nv_wr32(priv, TPC_UNIT(gpc, tpc, 0x088), id);
-                               id++;
-                       }
-
-                       nv_wr32(priv, GPC_UNIT(gpc, 0x0c08), priv->tpc_nr[gpc]);
-                       nv_wr32(priv, GPC_UNIT(gpc, 0x0c8c), priv->tpc_nr[gpc]);
-               }
-       }
-}
-
-void
-nvc0_grctx_generate_r406028(struct nvc0_graph_priv *priv)
-{
-       u32 tmp[GPC_MAX / 8] = {}, i = 0;
-       for (i = 0; i < priv->gpc_nr; i++)
-               tmp[i / 8] |= priv->tpc_nr[i] << ((i % 8) * 4);
-       for (i = 0; i < 4; i++) {
-               nv_wr32(priv, 0x406028 + (i * 4), tmp[i]);
-               nv_wr32(priv, 0x405870 + (i * 4), tmp[i]);
-       }
-}
-
-void
-nvc0_grctx_generate_r4060a8(struct nvc0_graph_priv *priv)
-{
-       u8  tpcnr[GPC_MAX], data[TPC_MAX];
-       int gpc, tpc, i;
-
-       memcpy(tpcnr, priv->tpc_nr, sizeof(priv->tpc_nr));
-       memset(data, 0x1f, sizeof(data));
-
-       gpc = -1;
-       for (tpc = 0; tpc < priv->tpc_total; tpc++) {
-               do {
-                       gpc = (gpc + 1) % priv->gpc_nr;
-               } while (!tpcnr[gpc]);
-               tpcnr[gpc]--;
-               data[tpc] = gpc;
-       }
-
-       for (i = 0; i < 4; i++)
-               nv_wr32(priv, 0x4060a8 + (i * 4), ((u32 *)data)[i]);
-}
-
-void
-nvc0_grctx_generate_r418bb8(struct nvc0_graph_priv *priv)
-{
-       u32 data[6] = {}, data2[2] = {};
-       u8  tpcnr[GPC_MAX];
-       u8  shift, ntpcv;
-       int gpc, tpc, i;
-
-       /* calculate first set of magics */
-       memcpy(tpcnr, priv->tpc_nr, sizeof(priv->tpc_nr));
-
-       gpc = -1;
-       for (tpc = 0; tpc < priv->tpc_total; tpc++) {
-               do {
-                       gpc = (gpc + 1) % priv->gpc_nr;
-               } while (!tpcnr[gpc]);
-               tpcnr[gpc]--;
-
-               data[tpc / 6] |= gpc << ((tpc % 6) * 5);
-       }
-
-       for (; tpc < 32; tpc++)
-               data[tpc / 6] |= 7 << ((tpc % 6) * 5);
-
-       /* and the second... */
-       shift = 0;
-       ntpcv = priv->tpc_total;
-       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(priv, 0x418bb8, (priv->tpc_total << 8) |
-                                priv->magic_not_rop_nr);
-       for (i = 0; i < 6; i++)
-               nv_wr32(priv, 0x418b08 + (i * 4), data[i]);
-
-       /* GPC_BROADCAST.TP_BROADCAST */
-       nv_wr32(priv, 0x419bd0, (priv->tpc_total << 8) |
-                                priv->magic_not_rop_nr | data2[0]);
-       nv_wr32(priv, 0x419be4, data2[1]);
-       for (i = 0; i < 6; i++)
-               nv_wr32(priv, 0x419b00 + (i * 4), data[i]);
-
-       /* UNK78xx */
-       nv_wr32(priv, 0x4078bc, (priv->tpc_total << 8) |
-                                priv->magic_not_rop_nr);
-       for (i = 0; i < 6; i++)
-               nv_wr32(priv, 0x40780c + (i * 4), data[i]);
-}
-
-void
-nvc0_grctx_generate_r406800(struct nvc0_graph_priv *priv)
-{
-       u64 tpc_mask = 0, tpc_set = 0;
-       u8  tpcnr[GPC_MAX];
-       int gpc, tpc;
-       int i, a, b;
-
-       memcpy(tpcnr, priv->tpc_nr, sizeof(priv->tpc_nr));
-       for (gpc = 0; gpc < priv->gpc_nr; gpc++)
-               tpc_mask |= ((1ULL << priv->tpc_nr[gpc]) - 1) << (gpc * 8);
-
-       for (i = 0, gpc = -1, b = -1; i < 32; i++) {
-               a = (i * (priv->tpc_total - 1)) / 32;
-               if (a != b) {
-                       b = a;
-                       do {
-                               gpc = (gpc + 1) % priv->gpc_nr;
-                       } while (!tpcnr[gpc]);
-                       tpc = priv->tpc_nr[gpc] - tpcnr[gpc]--;
-
-                       tpc_set |= 1ULL << ((gpc * 8) + tpc);
-               }
-
-               nv_wr32(priv, 0x406800 + (i * 0x20), lower_32_bits(tpc_set));
-               nv_wr32(priv, 0x406c00 + (i * 0x20), lower_32_bits(tpc_set ^ tpc_mask));
-               if (priv->gpc_nr > 4) {
-                       nv_wr32(priv, 0x406804 + (i * 0x20), upper_32_bits(tpc_set));
-                       nv_wr32(priv, 0x406c04 + (i * 0x20), upper_32_bits(tpc_set ^ tpc_mask));
-               }
-       }
-}
-
-void
-nvc0_grctx_generate_main(struct nvc0_graph_priv *priv, struct nvc0_grctx *info)
-{
-       struct nvc0_grctx_oclass *oclass = (void *)nv_engine(priv)->cclass;
-
-       nouveau_mc(priv)->unk260(nouveau_mc(priv), 0);
-
-       nvc0_graph_mmio(priv, oclass->hub);
-       nvc0_graph_mmio(priv, oclass->gpc);
-       nvc0_graph_mmio(priv, oclass->zcull);
-       nvc0_graph_mmio(priv, oclass->tpc);
-       nvc0_graph_mmio(priv, oclass->ppc);
-
-       nv_wr32(priv, 0x404154, 0x00000000);
-
-       oclass->bundle(info);
-       oclass->pagepool(info);
-       oclass->attrib(info);
-       oclass->unkn(priv);
-
-       nvc0_grctx_generate_tpcid(priv);
-       nvc0_grctx_generate_r406028(priv);
-       nvc0_grctx_generate_r4060a8(priv);
-       nvc0_grctx_generate_r418bb8(priv);
-       nvc0_grctx_generate_r406800(priv);
-
-       nvc0_graph_icmd(priv, oclass->icmd);
-       nv_wr32(priv, 0x404154, 0x00000400);
-       nvc0_graph_mthd(priv, oclass->mthd);
-       nouveau_mc(priv)->unk260(nouveau_mc(priv), 1);
-}
-
-int
-nvc0_grctx_generate(struct nvc0_graph_priv *priv)
-{
-       struct nvc0_grctx_oclass *oclass = (void *)nv_engine(priv)->cclass;
-       struct nouveau_bar *bar = nouveau_bar(priv);
-       struct nouveau_gpuobj *chan;
-       struct nvc0_grctx info;
-       int ret, i;
-
-       /* allocate memory to for a "channel", which we'll use to generate
-        * the default context values
-        */
-       ret = nouveau_gpuobj_new(nv_object(priv), NULL, 0x80000 + priv->size,
-                                0x1000, NVOBJ_FLAG_ZERO_ALLOC, &chan);
-       if (ret) {
-               nv_error(priv, "failed to allocate channel memory, %d\n", ret);
-               return ret;
-       }
-
-       /* PGD pointer */
-       nv_wo32(chan, 0x0200, lower_32_bits(chan->addr + 0x1000));
-       nv_wo32(chan, 0x0204, upper_32_bits(chan->addr + 0x1000));
-       nv_wo32(chan, 0x0208, 0xffffffff);
-       nv_wo32(chan, 0x020c, 0x000000ff);
-
-       /* PGT[0] pointer */
-       nv_wo32(chan, 0x1000, 0x00000000);
-       nv_wo32(chan, 0x1004, 0x00000001 | (chan->addr + 0x2000) >> 8);
-
-       /* identity-map the whole "channel" into its own vm */
-       for (i = 0; i < chan->size / 4096; i++) {
-               u64 addr = ((chan->addr + (i * 4096)) >> 8) | 1;
-               nv_wo32(chan, 0x2000 + (i * 8), lower_32_bits(addr));
-               nv_wo32(chan, 0x2004 + (i * 8), upper_32_bits(addr));
-       }
-
-       /* context pointer (virt) */
-       nv_wo32(chan, 0x0210, 0x00080004);
-       nv_wo32(chan, 0x0214, 0x00000000);
-
-       bar->flush(bar);
-
-       nv_wr32(priv, 0x100cb8, (chan->addr + 0x1000) >> 8);
-       nv_wr32(priv, 0x100cbc, 0x80000001);
-       nv_wait(priv, 0x100c80, 0x00008000, 0x00008000);
-
-       /* setup default state for mmio list construction */
-       info.priv = priv;
-       info.data = priv->mmio_data;
-       info.mmio = priv->mmio_list;
-       info.addr = 0x2000 + (i * 8);
-       info.buffer_nr = 0;
-
-       /* make channel current */
-       if (priv->firmware) {
-               nv_wr32(priv, 0x409840, 0x00000030);
-               nv_wr32(priv, 0x409500, 0x80000000 | chan->addr >> 12);
-               nv_wr32(priv, 0x409504, 0x00000003);
-               if (!nv_wait(priv, 0x409800, 0x00000010, 0x00000010))
-                       nv_error(priv, "load_ctx timeout\n");
-
-               nv_wo32(chan, 0x8001c, 1);
-               nv_wo32(chan, 0x80020, 0);
-               nv_wo32(chan, 0x80028, 0);
-               nv_wo32(chan, 0x8002c, 0);
-               bar->flush(bar);
-       } else {
-               nv_wr32(priv, 0x409840, 0x80000000);
-               nv_wr32(priv, 0x409500, 0x80000000 | chan->addr >> 12);
-               nv_wr32(priv, 0x409504, 0x00000001);
-               if (!nv_wait(priv, 0x409800, 0x80000000, 0x80000000))
-                       nv_error(priv, "HUB_SET_CHAN timeout\n");
-       }
-
-       oclass->main(priv, &info);
-
-       /* trigger a context unload by unsetting the "next channel valid" bit
-        * and faking a context switch interrupt
-        */
-       nv_mask(priv, 0x409b04, 0x80000000, 0x00000000);
-       nv_wr32(priv, 0x409000, 0x00000100);
-       if (!nv_wait(priv, 0x409b00, 0x80000000, 0x00000000)) {
-               nv_error(priv, "grctx template channel unload timeout\n");
-               ret = -EBUSY;
-               goto done;
-       }
-
-       priv->data = kmalloc(priv->size, GFP_KERNEL);
-       if (priv->data) {
-               for (i = 0; i < priv->size; i += 4)
-                       priv->data[i / 4] = nv_ro32(chan, 0x80000 + i);
-               ret = 0;
-       } else {
-               ret = -ENOMEM;
-       }
-
-done:
-       nouveau_gpuobj_ref(NULL, &chan);
-       return ret;
-}
-
-struct nouveau_oclass *
-nvc0_grctx_oclass = &(struct nvc0_grctx_oclass) {
-       .base.handle = NV_ENGCTX(GR, 0xc0),
-       .base.ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nvc0_graph_context_ctor,
-               .dtor = nvc0_graph_context_dtor,
-               .init = _nouveau_graph_context_init,
-               .fini = _nouveau_graph_context_fini,
-               .rd32 = _nouveau_graph_context_rd32,
-               .wr32 = _nouveau_graph_context_wr32,
-       },
-       .main  = nvc0_grctx_generate_main,
-       .unkn  = nvc0_grctx_generate_unkn,
-       .hub   = nvc0_grctx_pack_hub,
-       .gpc   = nvc0_grctx_pack_gpc,
-       .zcull = nvc0_grctx_pack_zcull,
-       .tpc   = nvc0_grctx_pack_tpc,
-       .icmd  = nvc0_grctx_pack_icmd,
-       .mthd  = nvc0_grctx_pack_mthd,
-       .bundle = nvc0_grctx_generate_bundle,
-       .bundle_size = 0x1800,
-       .pagepool = nvc0_grctx_generate_pagepool,
-       .pagepool_size = 0x8000,
-       .attrib = nvc0_grctx_generate_attrib,
-       .attrib_nr_max = 0x324,
-       .attrib_nr = 0x218,
-}.base;
diff --git a/drivers/gpu/drm/nouveau/core/engine/graph/ctxnvc0.h b/drivers/gpu/drm/nouveau/core/engine/graph/ctxnvc0.h
deleted file mode 100644 (file)
index c776cd7..0000000
+++ /dev/null
@@ -1,202 +0,0 @@
-#ifndef __NVKM_GRCTX_NVC0_H__
-#define __NVKM_GRCTX_NVC0_H__
-
-#include "nvc0.h"
-
-struct nvc0_grctx {
-       struct nvc0_graph_priv *priv;
-       struct nvc0_graph_data *data;
-       struct nvc0_graph_mmio *mmio;
-       int buffer_nr;
-       u64 buffer[4];
-       u64 addr;
-};
-
-int  nvc0_grctx_mmio_data(struct nvc0_grctx *, u32 size, u32 align, u32 access);
-void nvc0_grctx_mmio_item(struct nvc0_grctx *, u32 addr, u32 data, int s, int);
-
-#define mmio_vram(a,b,c,d) nvc0_grctx_mmio_data((a), (b), (c), (d))
-#define mmio_refn(a,b,c,d,e) nvc0_grctx_mmio_item((a), (b), (c), (d), (e))
-#define mmio_skip(a,b,c) mmio_refn((a), (b), (c), -1, -1)
-#define mmio_wr32(a,b,c) mmio_refn((a), (b), (c),  0, -1)
-
-struct nvc0_grctx_oclass {
-       struct nouveau_oclass base;
-       /* main context generation function */
-       void  (*main)(struct nvc0_graph_priv *, struct nvc0_grctx *);
-       /* context-specific modify-on-first-load list generation function */
-       void  (*unkn)(struct nvc0_graph_priv *);
-       /* mmio context data */
-       const struct nvc0_graph_pack *hub;
-       const struct nvc0_graph_pack *gpc;
-       const struct nvc0_graph_pack *zcull;
-       const struct nvc0_graph_pack *tpc;
-       const struct nvc0_graph_pack *ppc;
-       /* indirect context data, generated with icmds/mthds */
-       const struct nvc0_graph_pack *icmd;
-       const struct nvc0_graph_pack *mthd;
-       /* bundle circular buffer */
-       void (*bundle)(struct nvc0_grctx *);
-       u32 bundle_size;
-       u32 bundle_min_gpm_fifo_depth;
-       u32 bundle_token_limit;
-       /* pagepool */
-       void (*pagepool)(struct nvc0_grctx *);
-       u32 pagepool_size;
-       /* attribute(/alpha) circular buffer */
-       void (*attrib)(struct nvc0_grctx *);
-       u32 attrib_nr_max;
-       u32 attrib_nr;
-       u32 alpha_nr_max;
-       u32 alpha_nr;
-};
-
-static inline const struct nvc0_grctx_oclass *
-nvc0_grctx_impl(struct nvc0_graph_priv *priv)
-{
-       return (void *)nv_engine(priv)->cclass;
-}
-
-extern struct nouveau_oclass *nvc0_grctx_oclass;
-int  nvc0_grctx_generate(struct nvc0_graph_priv *);
-void nvc0_grctx_generate_main(struct nvc0_graph_priv *, struct nvc0_grctx *);
-void nvc0_grctx_generate_bundle(struct nvc0_grctx *);
-void nvc0_grctx_generate_pagepool(struct nvc0_grctx *);
-void nvc0_grctx_generate_attrib(struct nvc0_grctx *);
-void nvc0_grctx_generate_unkn(struct nvc0_graph_priv *);
-void nvc0_grctx_generate_tpcid(struct nvc0_graph_priv *);
-void nvc0_grctx_generate_r406028(struct nvc0_graph_priv *);
-void nvc0_grctx_generate_r4060a8(struct nvc0_graph_priv *);
-void nvc0_grctx_generate_r418bb8(struct nvc0_graph_priv *);
-void nvc0_grctx_generate_r406800(struct nvc0_graph_priv *);
-
-extern struct nouveau_oclass *nvc1_grctx_oclass;
-void nvc1_grctx_generate_attrib(struct nvc0_grctx *);
-void nvc1_grctx_generate_unkn(struct nvc0_graph_priv *);
-
-extern struct nouveau_oclass *nvc4_grctx_oclass;
-extern struct nouveau_oclass *nvc8_grctx_oclass;
-
-extern struct nouveau_oclass *nvd7_grctx_oclass;
-void nvd7_grctx_generate_attrib(struct nvc0_grctx *);
-
-extern struct nouveau_oclass *nvd9_grctx_oclass;
-
-extern struct nouveau_oclass *nve4_grctx_oclass;
-extern struct nouveau_oclass *gk20a_grctx_oclass;
-void nve4_grctx_generate_main(struct nvc0_graph_priv *, struct nvc0_grctx *);
-void nve4_grctx_generate_bundle(struct nvc0_grctx *);
-void nve4_grctx_generate_pagepool(struct nvc0_grctx *);
-void nve4_grctx_generate_unkn(struct nvc0_graph_priv *);
-void nve4_grctx_generate_r418bb8(struct nvc0_graph_priv *);
-
-extern struct nouveau_oclass *nvf0_grctx_oclass;
-extern struct nouveau_oclass *gk110b_grctx_oclass;
-extern struct nouveau_oclass *nv108_grctx_oclass;
-extern struct nouveau_oclass *gm107_grctx_oclass;
-
-/* context init value lists */
-
-extern const struct nvc0_graph_pack nvc0_grctx_pack_icmd[];
-
-extern const struct nvc0_graph_pack nvc0_grctx_pack_mthd[];
-extern const struct nvc0_graph_init nvc0_grctx_init_902d_0[];
-extern const struct nvc0_graph_init nvc0_grctx_init_9039_0[];
-extern const struct nvc0_graph_init nvc0_grctx_init_90c0_0[];
-
-extern const struct nvc0_graph_pack nvc0_grctx_pack_hub[];
-extern const struct nvc0_graph_init nvc0_grctx_init_main_0[];
-extern const struct nvc0_graph_init nvc0_grctx_init_fe_0[];
-extern const struct nvc0_graph_init nvc0_grctx_init_pri_0[];
-extern const struct nvc0_graph_init nvc0_grctx_init_memfmt_0[];
-extern const struct nvc0_graph_init nvc0_grctx_init_rstr2d_0[];
-extern const struct nvc0_graph_init nvc0_grctx_init_scc_0[];
-
-extern const struct nvc0_graph_pack nvc0_grctx_pack_gpc[];
-extern const struct nvc0_graph_init nvc0_grctx_init_gpc_unk_0[];
-extern const struct nvc0_graph_init nvc0_grctx_init_prop_0[];
-extern const struct nvc0_graph_init nvc0_grctx_init_gpc_unk_1[];
-extern const struct nvc0_graph_init nvc0_grctx_init_zcull_0[];
-extern const struct nvc0_graph_init nvc0_grctx_init_crstr_0[];
-extern const struct nvc0_graph_init nvc0_grctx_init_gpm_0[];
-extern const struct nvc0_graph_init nvc0_grctx_init_gcc_0[];
-
-extern const struct nvc0_graph_pack nvc0_grctx_pack_zcull[];
-
-extern const struct nvc0_graph_pack nvc0_grctx_pack_tpc[];
-extern const struct nvc0_graph_init nvc0_grctx_init_pe_0[];
-extern const struct nvc0_graph_init nvc0_grctx_init_wwdx_0[];
-extern const struct nvc0_graph_init nvc0_grctx_init_mpc_0[];
-extern const struct nvc0_graph_init nvc0_grctx_init_tpccs_0[];
-
-extern const struct nvc0_graph_init nvc4_grctx_init_tex_0[];
-extern const struct nvc0_graph_init nvc4_grctx_init_l1c_0[];
-extern const struct nvc0_graph_init nvc4_grctx_init_sm_0[];
-
-extern const struct nvc0_graph_init nvc1_grctx_init_9097_0[];
-
-extern const struct nvc0_graph_init nvc1_grctx_init_gpm_0[];
-
-extern const struct nvc0_graph_init nvc1_grctx_init_pe_0[];
-extern const struct nvc0_graph_init nvc1_grctx_init_wwdx_0[];
-extern const struct nvc0_graph_init nvc1_grctx_init_tpccs_0[];
-
-extern const struct nvc0_graph_init nvc8_grctx_init_9197_0[];
-extern const struct nvc0_graph_init nvc8_grctx_init_9297_0[];
-
-extern const struct nvc0_graph_pack nvd9_grctx_pack_icmd[];
-
-extern const struct nvc0_graph_pack nvd9_grctx_pack_mthd[];
-
-extern const struct nvc0_graph_init nvd9_grctx_init_fe_0[];
-extern const struct nvc0_graph_init nvd9_grctx_init_be_0[];
-
-extern const struct nvc0_graph_init nvd9_grctx_init_prop_0[];
-extern const struct nvc0_graph_init nvd9_grctx_init_gpc_unk_1[];
-extern const struct nvc0_graph_init nvd9_grctx_init_crstr_0[];
-
-extern const struct nvc0_graph_init nvd9_grctx_init_sm_0[];
-
-extern const struct nvc0_graph_init nvd7_grctx_init_pe_0[];
-
-extern const struct nvc0_graph_init nvd7_grctx_init_wwdx_0[];
-
-extern const struct nvc0_graph_init nve4_grctx_init_memfmt_0[];
-extern const struct nvc0_graph_init nve4_grctx_init_ds_0[];
-extern const struct nvc0_graph_init nve4_grctx_init_scc_0[];
-
-extern const struct nvc0_graph_init nve4_grctx_init_gpm_0[];
-
-extern const struct nvc0_graph_init nve4_grctx_init_pes_0[];
-
-extern const struct nvc0_graph_pack nve4_grctx_pack_hub[];
-extern const struct nvc0_graph_pack nve4_grctx_pack_gpc[];
-extern const struct nvc0_graph_pack nve4_grctx_pack_tpc[];
-extern const struct nvc0_graph_pack nve4_grctx_pack_ppc[];
-extern const struct nvc0_graph_pack nve4_grctx_pack_icmd[];
-extern const struct nvc0_graph_init nve4_grctx_init_a097_0[];
-
-extern const struct nvc0_graph_pack nvf0_grctx_pack_icmd[];
-
-extern const struct nvc0_graph_pack nvf0_grctx_pack_mthd[];
-
-extern const struct nvc0_graph_pack nvf0_grctx_pack_hub[];
-extern const struct nvc0_graph_init nvf0_grctx_init_pri_0[];
-extern const struct nvc0_graph_init nvf0_grctx_init_cwd_0[];
-
-extern const struct nvc0_graph_pack nvf0_grctx_pack_gpc[];
-extern const struct nvc0_graph_init nvf0_grctx_init_gpc_unk_2[];
-
-extern const struct nvc0_graph_init nvf0_grctx_init_tex_0[];
-extern const struct nvc0_graph_init nvf0_grctx_init_mpc_0[];
-extern const struct nvc0_graph_init nvf0_grctx_init_l1c_0[];
-
-extern const struct nvc0_graph_pack nvf0_grctx_pack_ppc[];
-
-extern const struct nvc0_graph_init nv108_grctx_init_rstr2d_0[];
-
-extern const struct nvc0_graph_init nv108_grctx_init_prop_0[];
-extern const struct nvc0_graph_init nv108_grctx_init_crstr_0[];
-
-
-#endif
diff --git a/drivers/gpu/drm/nouveau/core/engine/graph/ctxnvc1.c b/drivers/gpu/drm/nouveau/core/engine/graph/ctxnvc1.c
deleted file mode 100644 (file)
index c6ba8fe..0000000
+++ /dev/null
@@ -1,805 +0,0 @@
-/*
- * Copyright 2013 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 <bskeggs@redhat.com>
- */
-
-#include "ctxnvc0.h"
-
-/*******************************************************************************
- * PGRAPH context register lists
- ******************************************************************************/
-
-static const struct nvc0_graph_init
-nvc1_grctx_init_icmd_0[] = {
-       { 0x001000,   1, 0x01, 0x00000004 },
-       { 0x0000a9,   1, 0x01, 0x0000ffff },
-       { 0x000038,   1, 0x01, 0x0fac6881 },
-       { 0x00003d,   1, 0x01, 0x00000001 },
-       { 0x0000e8,   8, 0x01, 0x00000400 },
-       { 0x000078,   8, 0x01, 0x00000300 },
-       { 0x000050,   1, 0x01, 0x00000011 },
-       { 0x000058,   8, 0x01, 0x00000008 },
-       { 0x000208,   8, 0x01, 0x00000001 },
-       { 0x000081,   1, 0x01, 0x00000001 },
-       { 0x000085,   1, 0x01, 0x00000004 },
-       { 0x000088,   1, 0x01, 0x00000400 },
-       { 0x000090,   1, 0x01, 0x00000300 },
-       { 0x000098,   1, 0x01, 0x00001001 },
-       { 0x0000e3,   1, 0x01, 0x00000001 },
-       { 0x0000da,   1, 0x01, 0x00000001 },
-       { 0x0000f8,   1, 0x01, 0x00000003 },
-       { 0x0000fa,   1, 0x01, 0x00000001 },
-       { 0x00009f,   4, 0x01, 0x0000ffff },
-       { 0x0000b1,   1, 0x01, 0x00000001 },
-       { 0x0000b2,  40, 0x01, 0x00000000 },
-       { 0x000210,   8, 0x01, 0x00000040 },
-       { 0x000218,   8, 0x01, 0x0000c080 },
-       { 0x0000ad,   1, 0x01, 0x0000013e },
-       { 0x0000e1,   1, 0x01, 0x00000010 },
-       { 0x000290,  16, 0x01, 0x00000000 },
-       { 0x0003b0,  16, 0x01, 0x00000000 },
-       { 0x0002a0,  16, 0x01, 0x00000000 },
-       { 0x000420,  16, 0x01, 0x00000000 },
-       { 0x0002b0,  16, 0x01, 0x00000000 },
-       { 0x000430,  16, 0x01, 0x00000000 },
-       { 0x0002c0,  16, 0x01, 0x00000000 },
-       { 0x0004d0,  16, 0x01, 0x00000000 },
-       { 0x000720,  16, 0x01, 0x00000000 },
-       { 0x0008c0,  16, 0x01, 0x00000000 },
-       { 0x000890,  16, 0x01, 0x00000000 },
-       { 0x0008e0,  16, 0x01, 0x00000000 },
-       { 0x0008a0,  16, 0x01, 0x00000000 },
-       { 0x0008f0,  16, 0x01, 0x00000000 },
-       { 0x00094c,   1, 0x01, 0x000000ff },
-       { 0x00094d,   1, 0x01, 0xffffffff },
-       { 0x00094e,   1, 0x01, 0x00000002 },
-       { 0x0002ec,   1, 0x01, 0x00000001 },
-       { 0x000303,   1, 0x01, 0x00000001 },
-       { 0x0002e6,   1, 0x01, 0x00000001 },
-       { 0x000466,   1, 0x01, 0x00000052 },
-       { 0x000301,   1, 0x01, 0x3f800000 },
-       { 0x000304,   1, 0x01, 0x30201000 },
-       { 0x000305,   1, 0x01, 0x70605040 },
-       { 0x000306,   1, 0x01, 0xb8a89888 },
-       { 0x000307,   1, 0x01, 0xf8e8d8c8 },
-       { 0x00030a,   1, 0x01, 0x00ffff00 },
-       { 0x00030b,   1, 0x01, 0x0000001a },
-       { 0x00030c,   1, 0x01, 0x00000001 },
-       { 0x000318,   1, 0x01, 0x00000001 },
-       { 0x000340,   1, 0x01, 0x00000000 },
-       { 0x000375,   1, 0x01, 0x00000001 },
-       { 0x000351,   1, 0x01, 0x00000100 },
-       { 0x00037d,   1, 0x01, 0x00000006 },
-       { 0x0003a0,   1, 0x01, 0x00000002 },
-       { 0x0003aa,   1, 0x01, 0x00000001 },
-       { 0x0003a9,   1, 0x01, 0x00000001 },
-       { 0x000380,   1, 0x01, 0x00000001 },
-       { 0x000360,   1, 0x01, 0x00000040 },
-       { 0x000366,   2, 0x01, 0x00000000 },
-       { 0x000368,   1, 0x01, 0x00001fff },
-       { 0x000370,   2, 0x01, 0x00000000 },
-       { 0x000372,   1, 0x01, 0x003fffff },
-       { 0x00037a,   1, 0x01, 0x00000012 },
-       { 0x0005e0,   5, 0x01, 0x00000022 },
-       { 0x000619,   1, 0x01, 0x00000003 },
-       { 0x000811,   1, 0x01, 0x00000003 },
-       { 0x000812,   1, 0x01, 0x00000004 },
-       { 0x000813,   1, 0x01, 0x00000006 },
-       { 0x000814,   1, 0x01, 0x00000008 },
-       { 0x000815,   1, 0x01, 0x0000000b },
-       { 0x000800,   6, 0x01, 0x00000001 },
-       { 0x000632,   1, 0x01, 0x00000001 },
-       { 0x000633,   1, 0x01, 0x00000002 },
-       { 0x000634,   1, 0x01, 0x00000003 },
-       { 0x000635,   1, 0x01, 0x00000004 },
-       { 0x000654,   1, 0x01, 0x3f800000 },
-       { 0x000657,   1, 0x01, 0x3f800000 },
-       { 0x000655,   2, 0x01, 0x3f800000 },
-       { 0x0006cd,   1, 0x01, 0x3f800000 },
-       { 0x0007f5,   1, 0x01, 0x3f800000 },
-       { 0x0007dc,   1, 0x01, 0x39291909 },
-       { 0x0007dd,   1, 0x01, 0x79695949 },
-       { 0x0007de,   1, 0x01, 0xb9a99989 },
-       { 0x0007df,   1, 0x01, 0xf9e9d9c9 },
-       { 0x0007e8,   1, 0x01, 0x00003210 },
-       { 0x0007e9,   1, 0x01, 0x00007654 },
-       { 0x0007ea,   1, 0x01, 0x00000098 },
-       { 0x0007ec,   1, 0x01, 0x39291909 },
-       { 0x0007ed,   1, 0x01, 0x79695949 },
-       { 0x0007ee,   1, 0x01, 0xb9a99989 },
-       { 0x0007ef,   1, 0x01, 0xf9e9d9c9 },
-       { 0x0007f0,   1, 0x01, 0x00003210 },
-       { 0x0007f1,   1, 0x01, 0x00007654 },
-       { 0x0007f2,   1, 0x01, 0x00000098 },
-       { 0x0005a5,   1, 0x01, 0x00000001 },
-       { 0x000980, 128, 0x01, 0x00000000 },
-       { 0x000468,   1, 0x01, 0x00000004 },
-       { 0x00046c,   1, 0x01, 0x00000001 },
-       { 0x000470,  96, 0x01, 0x00000000 },
-       { 0x000510,  16, 0x01, 0x3f800000 },
-       { 0x000520,   1, 0x01, 0x000002b6 },
-       { 0x000529,   1, 0x01, 0x00000001 },
-       { 0x000530,  16, 0x01, 0xffff0000 },
-       { 0x000585,   1, 0x01, 0x0000003f },
-       { 0x000576,   1, 0x01, 0x00000003 },
-       { 0x00057b,   1, 0x01, 0x00000059 },
-       { 0x000586,   1, 0x01, 0x00000040 },
-       { 0x000582,   2, 0x01, 0x00000080 },
-       { 0x0005c2,   1, 0x01, 0x00000001 },
-       { 0x000638,   2, 0x01, 0x00000001 },
-       { 0x00063a,   1, 0x01, 0x00000002 },
-       { 0x00063b,   2, 0x01, 0x00000001 },
-       { 0x00063d,   1, 0x01, 0x00000002 },
-       { 0x00063e,   1, 0x01, 0x00000001 },
-       { 0x0008b8,   8, 0x01, 0x00000001 },
-       { 0x000900,   8, 0x01, 0x00000001 },
-       { 0x000908,   8, 0x01, 0x00000002 },
-       { 0x000910,  16, 0x01, 0x00000001 },
-       { 0x000920,   8, 0x01, 0x00000002 },
-       { 0x000928,   8, 0x01, 0x00000001 },
-       { 0x000648,   9, 0x01, 0x00000001 },
-       { 0x000658,   1, 0x01, 0x0000000f },
-       { 0x0007ff,   1, 0x01, 0x0000000a },
-       { 0x00066a,   1, 0x01, 0x40000000 },
-       { 0x00066b,   1, 0x01, 0x10000000 },
-       { 0x00066c,   2, 0x01, 0xffff0000 },
-       { 0x0007af,   2, 0x01, 0x00000008 },
-       { 0x0007f6,   1, 0x01, 0x00000001 },
-       { 0x0006b2,   1, 0x01, 0x00000055 },
-       { 0x0007ad,   1, 0x01, 0x00000003 },
-       { 0x000937,   1, 0x01, 0x00000001 },
-       { 0x000971,   1, 0x01, 0x00000008 },
-       { 0x000972,   1, 0x01, 0x00000040 },
-       { 0x000973,   1, 0x01, 0x0000012c },
-       { 0x00097c,   1, 0x01, 0x00000040 },
-       { 0x000979,   1, 0x01, 0x00000003 },
-       { 0x000975,   1, 0x01, 0x00000020 },
-       { 0x000976,   1, 0x01, 0x00000001 },
-       { 0x000977,   1, 0x01, 0x00000020 },
-       { 0x000978,   1, 0x01, 0x00000001 },
-       { 0x000957,   1, 0x01, 0x00000003 },
-       { 0x00095e,   1, 0x01, 0x20164010 },
-       { 0x00095f,   1, 0x01, 0x00000020 },
-       { 0x000683,   1, 0x01, 0x00000006 },
-       { 0x000685,   1, 0x01, 0x003fffff },
-       { 0x000687,   1, 0x01, 0x00000c48 },
-       { 0x0006a0,   1, 0x01, 0x00000005 },
-       { 0x000840,   1, 0x01, 0x00300008 },
-       { 0x000841,   1, 0x01, 0x04000080 },
-       { 0x000842,   1, 0x01, 0x00300008 },
-       { 0x000843,   1, 0x01, 0x04000080 },
-       { 0x000818,   8, 0x01, 0x00000000 },
-       { 0x000848,  16, 0x01, 0x00000000 },
-       { 0x000738,   1, 0x01, 0x00000000 },
-       { 0x0006aa,   1, 0x01, 0x00000001 },
-       { 0x0006ab,   1, 0x01, 0x00000002 },
-       { 0x0006ac,   1, 0x01, 0x00000080 },
-       { 0x0006ad,   2, 0x01, 0x00000100 },
-       { 0x0006b1,   1, 0x01, 0x00000011 },
-       { 0x0006bb,   1, 0x01, 0x000000cf },
-       { 0x0006ce,   1, 0x01, 0x2a712488 },
-       { 0x000739,   1, 0x01, 0x4085c000 },
-       { 0x00073a,   1, 0x01, 0x00000080 },
-       { 0x000786,   1, 0x01, 0x80000100 },
-       { 0x00073c,   1, 0x01, 0x00010100 },
-       { 0x00073d,   1, 0x01, 0x02800000 },
-       { 0x000787,   1, 0x01, 0x000000cf },
-       { 0x00078c,   1, 0x01, 0x00000008 },
-       { 0x000792,   1, 0x01, 0x00000001 },
-       { 0x000794,   3, 0x01, 0x00000001 },
-       { 0x000797,   1, 0x01, 0x000000cf },
-       { 0x000836,   1, 0x01, 0x00000001 },
-       { 0x00079a,   1, 0x01, 0x00000002 },
-       { 0x000833,   1, 0x01, 0x04444480 },
-       { 0x0007a1,   1, 0x01, 0x00000001 },
-       { 0x0007a3,   3, 0x01, 0x00000001 },
-       { 0x000831,   1, 0x01, 0x00000004 },
-       { 0x00080c,   1, 0x01, 0x00000002 },
-       { 0x00080d,   2, 0x01, 0x00000100 },
-       { 0x00080f,   1, 0x01, 0x00000001 },
-       { 0x000823,   1, 0x01, 0x00000002 },
-       { 0x000824,   2, 0x01, 0x00000100 },
-       { 0x000826,   1, 0x01, 0x00000001 },
-       { 0x00095d,   1, 0x01, 0x00000001 },
-       { 0x00082b,   1, 0x01, 0x00000004 },
-       { 0x000942,   1, 0x01, 0x00010001 },
-       { 0x000943,   1, 0x01, 0x00000001 },
-       { 0x000944,   1, 0x01, 0x00000022 },
-       { 0x0007c5,   1, 0x01, 0x00010001 },
-       { 0x000834,   1, 0x01, 0x00000001 },
-       { 0x0007c7,   1, 0x01, 0x00000001 },
-       { 0x00c1b0,   8, 0x01, 0x0000000f },
-       { 0x00c1b8,   1, 0x01, 0x0fac6881 },
-       { 0x00c1b9,   1, 0x01, 0x00fac688 },
-       { 0x01e100,   1, 0x01, 0x00000001 },
-       { 0x001000,   1, 0x01, 0x00000002 },
-       { 0x0006aa,   1, 0x01, 0x00000001 },
-       { 0x0006ad,   2, 0x01, 0x00000100 },
-       { 0x0006b1,   1, 0x01, 0x00000011 },
-       { 0x00078c,   1, 0x01, 0x00000008 },
-       { 0x000792,   1, 0x01, 0x00000001 },
-       { 0x000794,   3, 0x01, 0x00000001 },
-       { 0x000797,   1, 0x01, 0x000000cf },
-       { 0x00079a,   1, 0x01, 0x00000002 },
-       { 0x000833,   1, 0x01, 0x04444480 },
-       { 0x0007a1,   1, 0x01, 0x00000001 },
-       { 0x0007a3,   3, 0x01, 0x00000001 },
-       { 0x000831,   1, 0x01, 0x00000004 },
-       { 0x01e100,   1, 0x01, 0x00000001 },
-       { 0x001000,   1, 0x01, 0x00000014 },
-       { 0x000351,   1, 0x01, 0x00000100 },
-       { 0x000957,   1, 0x01, 0x00000003 },
-       { 0x00095d,   1, 0x01, 0x00000001 },
-       { 0x00082b,   1, 0x01, 0x00000004 },
-       { 0x000942,   1, 0x01, 0x00010001 },
-       { 0x000943,   1, 0x01, 0x00000001 },
-       { 0x0007c5,   1, 0x01, 0x00010001 },
-       { 0x000834,   1, 0x01, 0x00000001 },
-       { 0x0007c7,   1, 0x01, 0x00000001 },
-       { 0x01e100,   1, 0x01, 0x00000001 },
-       { 0x001000,   1, 0x01, 0x00000001 },
-       { 0x00080c,   1, 0x01, 0x00000002 },
-       { 0x00080d,   2, 0x01, 0x00000100 },
-       { 0x00080f,   1, 0x01, 0x00000001 },
-       { 0x000823,   1, 0x01, 0x00000002 },
-       { 0x000824,   2, 0x01, 0x00000100 },
-       { 0x000826,   1, 0x01, 0x00000001 },
-       { 0x01e100,   1, 0x01, 0x00000001 },
-       {}
-};
-
-static const struct nvc0_graph_pack
-nvc1_grctx_pack_icmd[] = {
-       { nvc1_grctx_init_icmd_0 },
-       {}
-};
-
-const struct nvc0_graph_init
-nvc1_grctx_init_9097_0[] = {
-       { 0x000800,   8, 0x40, 0x00000000 },
-       { 0x000804,   8, 0x40, 0x00000000 },
-       { 0x000808,   8, 0x40, 0x00000400 },
-       { 0x00080c,   8, 0x40, 0x00000300 },
-       { 0x000810,   1, 0x04, 0x000000cf },
-       { 0x000850,   7, 0x40, 0x00000000 },
-       { 0x000814,   8, 0x40, 0x00000040 },
-       { 0x000818,   8, 0x40, 0x00000001 },
-       { 0x00081c,   8, 0x40, 0x00000000 },
-       { 0x000820,   8, 0x40, 0x00000000 },
-       { 0x002700,   8, 0x20, 0x00000000 },
-       { 0x002704,   8, 0x20, 0x00000000 },
-       { 0x002708,   8, 0x20, 0x00000000 },
-       { 0x00270c,   8, 0x20, 0x00000000 },
-       { 0x002710,   8, 0x20, 0x00014000 },
-       { 0x002714,   8, 0x20, 0x00000040 },
-       { 0x001c00,  16, 0x10, 0x00000000 },
-       { 0x001c04,  16, 0x10, 0x00000000 },
-       { 0x001c08,  16, 0x10, 0x00000000 },
-       { 0x001c0c,  16, 0x10, 0x00000000 },
-       { 0x001d00,  16, 0x10, 0x00000000 },
-       { 0x001d04,  16, 0x10, 0x00000000 },
-       { 0x001d08,  16, 0x10, 0x00000000 },
-       { 0x001d0c,  16, 0x10, 0x00000000 },
-       { 0x001f00,  16, 0x08, 0x00000000 },
-       { 0x001f04,  16, 0x08, 0x00000000 },
-       { 0x001f80,  16, 0x08, 0x00000000 },
-       { 0x001f84,  16, 0x08, 0x00000000 },
-       { 0x002200,   5, 0x10, 0x00000022 },
-       { 0x002000,   1, 0x04, 0x00000000 },
-       { 0x002040,   1, 0x04, 0x00000011 },
-       { 0x002080,   1, 0x04, 0x00000020 },
-       { 0x0020c0,   1, 0x04, 0x00000030 },
-       { 0x002100,   1, 0x04, 0x00000040 },
-       { 0x002140,   1, 0x04, 0x00000051 },
-       { 0x00200c,   6, 0x40, 0x00000001 },
-       { 0x002010,   1, 0x04, 0x00000000 },
-       { 0x002050,   1, 0x04, 0x00000000 },
-       { 0x002090,   1, 0x04, 0x00000001 },
-       { 0x0020d0,   1, 0x04, 0x00000002 },
-       { 0x002110,   1, 0x04, 0x00000003 },
-       { 0x002150,   1, 0x04, 0x00000004 },
-       { 0x000380,   4, 0x20, 0x00000000 },
-       { 0x000384,   4, 0x20, 0x00000000 },
-       { 0x000388,   4, 0x20, 0x00000000 },
-       { 0x00038c,   4, 0x20, 0x00000000 },
-       { 0x000700,   4, 0x10, 0x00000000 },
-       { 0x000704,   4, 0x10, 0x00000000 },
-       { 0x000708,   4, 0x10, 0x00000000 },
-       { 0x002800, 128, 0x04, 0x00000000 },
-       { 0x000a00,  16, 0x20, 0x00000000 },
-       { 0x000a04,  16, 0x20, 0x00000000 },
-       { 0x000a08,  16, 0x20, 0x00000000 },
-       { 0x000a0c,  16, 0x20, 0x00000000 },
-       { 0x000a10,  16, 0x20, 0x00000000 },
-       { 0x000a14,  16, 0x20, 0x00000000 },
-       { 0x000c00,  16, 0x10, 0x00000000 },
-       { 0x000c04,  16, 0x10, 0x00000000 },
-       { 0x000c08,  16, 0x10, 0x00000000 },
-       { 0x000c0c,  16, 0x10, 0x3f800000 },
-       { 0x000d00,   8, 0x08, 0xffff0000 },
-       { 0x000d04,   8, 0x08, 0xffff0000 },
-       { 0x000e00,  16, 0x10, 0x00000000 },
-       { 0x000e04,  16, 0x10, 0xffff0000 },
-       { 0x000e08,  16, 0x10, 0xffff0000 },
-       { 0x000d40,   4, 0x08, 0x00000000 },
-       { 0x000d44,   4, 0x08, 0x00000000 },
-       { 0x001e00,   8, 0x20, 0x00000001 },
-       { 0x001e04,   8, 0x20, 0x00000001 },
-       { 0x001e08,   8, 0x20, 0x00000002 },
-       { 0x001e0c,   8, 0x20, 0x00000001 },
-       { 0x001e10,   8, 0x20, 0x00000001 },
-       { 0x001e14,   8, 0x20, 0x00000002 },
-       { 0x001e18,   8, 0x20, 0x00000001 },
-       { 0x00030c,   1, 0x04, 0x00000001 },
-       { 0x001944,   1, 0x04, 0x00000000 },
-       { 0x001514,   1, 0x04, 0x00000000 },
-       { 0x000d68,   1, 0x04, 0x0000ffff },
-       { 0x00121c,   1, 0x04, 0x0fac6881 },
-       { 0x000fac,   1, 0x04, 0x00000001 },
-       { 0x001538,   1, 0x04, 0x00000001 },
-       { 0x000fe0,   2, 0x04, 0x00000000 },
-       { 0x000fe8,   1, 0x04, 0x00000014 },
-       { 0x000fec,   1, 0x04, 0x00000040 },
-       { 0x000ff0,   1, 0x04, 0x00000000 },
-       { 0x00179c,   1, 0x04, 0x00000000 },
-       { 0x001228,   1, 0x04, 0x00000400 },
-       { 0x00122c,   1, 0x04, 0x00000300 },
-       { 0x001230,   1, 0x04, 0x00010001 },
-       { 0x0007f8,   1, 0x04, 0x00000000 },
-       { 0x0015b4,   1, 0x04, 0x00000001 },
-       { 0x0015cc,   1, 0x04, 0x00000000 },
-       { 0x001534,   1, 0x04, 0x00000000 },
-       { 0x000fb0,   1, 0x04, 0x00000000 },
-       { 0x0015d0,   1, 0x04, 0x00000000 },
-       { 0x00153c,   1, 0x04, 0x00000000 },
-       { 0x0016b4,   1, 0x04, 0x00000003 },
-       { 0x000fbc,   4, 0x04, 0x0000ffff },
-       { 0x000df8,   2, 0x04, 0x00000000 },
-       { 0x001948,   1, 0x04, 0x00000000 },
-       { 0x001970,   1, 0x04, 0x00000001 },
-       { 0x00161c,   1, 0x04, 0x000009f0 },
-       { 0x000dcc,   1, 0x04, 0x00000010 },
-       { 0x00163c,   1, 0x04, 0x00000000 },
-       { 0x0015e4,   1, 0x04, 0x00000000 },
-       { 0x001160,  32, 0x04, 0x25e00040 },
-       { 0x001880,  32, 0x04, 0x00000000 },
-       { 0x000f84,   2, 0x04, 0x00000000 },
-       { 0x0017c8,   2, 0x04, 0x00000000 },
-       { 0x0017d0,   1, 0x04, 0x000000ff },
-       { 0x0017d4,   1, 0x04, 0xffffffff },
-       { 0x0017d8,   1, 0x04, 0x00000002 },
-       { 0x0017dc,   1, 0x04, 0x00000000 },
-       { 0x0015f4,   2, 0x04, 0x00000000 },
-       { 0x001434,   2, 0x04, 0x00000000 },
-       { 0x000d74,   1, 0x04, 0x00000000 },
-       { 0x000dec,   1, 0x04, 0x00000001 },
-       { 0x0013a4,   1, 0x04, 0x00000000 },
-       { 0x001318,   1, 0x04, 0x00000001 },
-       { 0x001644,   1, 0x04, 0x00000000 },
-       { 0x000748,   1, 0x04, 0x00000000 },
-       { 0x000de8,   1, 0x04, 0x00000000 },
-       { 0x001648,   1, 0x04, 0x00000000 },
-       { 0x0012a4,   1, 0x04, 0x00000000 },
-       { 0x001120,   4, 0x04, 0x00000000 },
-       { 0x001118,   1, 0x04, 0x00000000 },
-       { 0x00164c,   1, 0x04, 0x00000000 },
-       { 0x001658,   1, 0x04, 0x00000000 },
-       { 0x001910,   1, 0x04, 0x00000290 },
-       { 0x001518,   1, 0x04, 0x00000000 },
-       { 0x00165c,   1, 0x04, 0x00000001 },
-       { 0x001520,   1, 0x04, 0x00000000 },
-       { 0x001604,   1, 0x04, 0x00000000 },
-       { 0x001570,   1, 0x04, 0x00000000 },
-       { 0x0013b0,   2, 0x04, 0x3f800000 },
-       { 0x00020c,   1, 0x04, 0x00000000 },
-       { 0x001670,   1, 0x04, 0x30201000 },
-       { 0x001674,   1, 0x04, 0x70605040 },
-       { 0x001678,   1, 0x04, 0xb8a89888 },
-       { 0x00167c,   1, 0x04, 0xf8e8d8c8 },
-       { 0x00166c,   1, 0x04, 0x00000000 },
-       { 0x001680,   1, 0x04, 0x00ffff00 },
-       { 0x0012d0,   1, 0x04, 0x00000003 },
-       { 0x0012d4,   1, 0x04, 0x00000002 },
-       { 0x001684,   2, 0x04, 0x00000000 },
-       { 0x000dac,   2, 0x04, 0x00001b02 },
-       { 0x000db4,   1, 0x04, 0x00000000 },
-       { 0x00168c,   1, 0x04, 0x00000000 },
-       { 0x0015bc,   1, 0x04, 0x00000000 },
-       { 0x00156c,   1, 0x04, 0x00000000 },
-       { 0x00187c,   1, 0x04, 0x00000000 },
-       { 0x001110,   1, 0x04, 0x00000001 },
-       { 0x000dc0,   3, 0x04, 0x00000000 },
-       { 0x001234,   1, 0x04, 0x00000000 },
-       { 0x001690,   1, 0x04, 0x00000000 },
-       { 0x0012ac,   1, 0x04, 0x00000001 },
-       { 0x0002c4,   1, 0x04, 0x00000000 },
-       { 0x000790,   5, 0x04, 0x00000000 },
-       { 0x00077c,   1, 0x04, 0x00000000 },
-       { 0x001000,   1, 0x04, 0x00000010 },
-       { 0x0010fc,   1, 0x04, 0x00000000 },
-       { 0x001290,   1, 0x04, 0x00000000 },
-       { 0x000218,   1, 0x04, 0x00000010 },
-       { 0x0012d8,   1, 0x04, 0x00000000 },
-       { 0x0012dc,   1, 0x04, 0x00000010 },
-       { 0x000d94,   1, 0x04, 0x00000001 },
-       { 0x00155c,   2, 0x04, 0x00000000 },
-       { 0x001564,   1, 0x04, 0x00001fff },
-       { 0x001574,   2, 0x04, 0x00000000 },
-       { 0x00157c,   1, 0x04, 0x003fffff },
-       { 0x001354,   1, 0x04, 0x00000000 },
-       { 0x001664,   1, 0x04, 0x00000000 },
-       { 0x001610,   1, 0x04, 0x00000012 },
-       { 0x001608,   2, 0x04, 0x00000000 },
-       { 0x00162c,   1, 0x04, 0x00000003 },
-       { 0x000210,   1, 0x04, 0x00000000 },
-       { 0x000320,   1, 0x04, 0x00000000 },
-       { 0x000324,   6, 0x04, 0x3f800000 },
-       { 0x000750,   1, 0x04, 0x00000000 },
-       { 0x000760,   1, 0x04, 0x39291909 },
-       { 0x000764,   1, 0x04, 0x79695949 },
-       { 0x000768,   1, 0x04, 0xb9a99989 },
-       { 0x00076c,   1, 0x04, 0xf9e9d9c9 },
-       { 0x000770,   1, 0x04, 0x30201000 },
-       { 0x000774,   1, 0x04, 0x70605040 },
-       { 0x000778,   1, 0x04, 0x00009080 },
-       { 0x000780,   1, 0x04, 0x39291909 },
-       { 0x000784,   1, 0x04, 0x79695949 },
-       { 0x000788,   1, 0x04, 0xb9a99989 },
-       { 0x00078c,   1, 0x04, 0xf9e9d9c9 },
-       { 0x0007d0,   1, 0x04, 0x30201000 },
-       { 0x0007d4,   1, 0x04, 0x70605040 },
-       { 0x0007d8,   1, 0x04, 0x00009080 },
-       { 0x00037c,   1, 0x04, 0x00000001 },
-       { 0x000740,   2, 0x04, 0x00000000 },
-       { 0x002600,   1, 0x04, 0x00000000 },
-       { 0x001918,   1, 0x04, 0x00000000 },
-       { 0x00191c,   1, 0x04, 0x00000900 },
-       { 0x001920,   1, 0x04, 0x00000405 },
-       { 0x001308,   1, 0x04, 0x00000001 },
-       { 0x001924,   1, 0x04, 0x00000000 },
-       { 0x0013ac,   1, 0x04, 0x00000000 },
-       { 0x00192c,   1, 0x04, 0x00000001 },
-       { 0x00193c,   1, 0x04, 0x00002c1c },
-       { 0x000d7c,   1, 0x04, 0x00000000 },
-       { 0x000f8c,   1, 0x04, 0x00000000 },
-       { 0x0002c0,   1, 0x04, 0x00000001 },
-       { 0x001510,   1, 0x04, 0x00000000 },
-       { 0x001940,   1, 0x04, 0x00000000 },
-       { 0x000ff4,   2, 0x04, 0x00000000 },
-       { 0x00194c,   2, 0x04, 0x00000000 },
-       { 0x001968,   1, 0x04, 0x00000000 },
-       { 0x001590,   1, 0x04, 0x0000003f },
-       { 0x0007e8,   4, 0x04, 0x00000000 },
-       { 0x00196c,   1, 0x04, 0x00000011 },
-       { 0x00197c,   1, 0x04, 0x00000000 },
-       { 0x000fcc,   2, 0x04, 0x00000000 },
-       { 0x0002d8,   1, 0x04, 0x00000040 },
-       { 0x001980,   1, 0x04, 0x00000080 },
-       { 0x001504,   1, 0x04, 0x00000080 },
-       { 0x001984,   1, 0x04, 0x00000000 },
-       { 0x000300,   1, 0x04, 0x00000001 },
-       { 0x0013a8,   1, 0x04, 0x00000000 },
-       { 0x0012ec,   1, 0x04, 0x00000000 },
-       { 0x001310,   1, 0x04, 0x00000000 },
-       { 0x001314,   1, 0x04, 0x00000001 },
-       { 0x001380,   1, 0x04, 0x00000000 },
-       { 0x001384,   4, 0x04, 0x00000001 },
-       { 0x001394,   1, 0x04, 0x00000000 },
-       { 0x00139c,   1, 0x04, 0x00000000 },
-       { 0x001398,   1, 0x04, 0x00000000 },
-       { 0x001594,   1, 0x04, 0x00000000 },
-       { 0x001598,   4, 0x04, 0x00000001 },
-       { 0x000f54,   3, 0x04, 0x00000000 },
-       { 0x0019bc,   1, 0x04, 0x00000000 },
-       { 0x000f9c,   2, 0x04, 0x00000000 },
-       { 0x0012cc,   1, 0x04, 0x00000000 },
-       { 0x0012e8,   1, 0x04, 0x00000000 },
-       { 0x00130c,   1, 0x04, 0x00000001 },
-       { 0x001360,   8, 0x04, 0x00000000 },
-       { 0x00133c,   2, 0x04, 0x00000001 },
-       { 0x001344,   1, 0x04, 0x00000002 },
-       { 0x001348,   2, 0x04, 0x00000001 },
-       { 0x001350,   1, 0x04, 0x00000002 },
-       { 0x001358,   1, 0x04, 0x00000001 },
-       { 0x0012e4,   1, 0x04, 0x00000000 },
-       { 0x00131c,   4, 0x04, 0x00000000 },
-       { 0x0019c0,   1, 0x04, 0x00000000 },
-       { 0x001140,   1, 0x04, 0x00000000 },
-       { 0x0019c4,   1, 0x04, 0x00000000 },
-       { 0x0019c8,   1, 0x04, 0x00001500 },
-       { 0x00135c,   1, 0x04, 0x00000000 },
-       { 0x000f90,   1, 0x04, 0x00000000 },
-       { 0x0019e0,   8, 0x04, 0x00000001 },
-       { 0x0019cc,   1, 0x04, 0x00000001 },
-       { 0x0015b8,   1, 0x04, 0x00000000 },
-       { 0x001a00,   1, 0x04, 0x00001111 },
-       { 0x001a04,   7, 0x04, 0x00000000 },
-       { 0x000d6c,   2, 0x04, 0xffff0000 },
-       { 0x0010f8,   1, 0x04, 0x00001010 },
-       { 0x000d80,   5, 0x04, 0x00000000 },
-       { 0x000da0,   1, 0x04, 0x00000000 },
-       { 0x001508,   1, 0x04, 0x80000000 },
-       { 0x00150c,   1, 0x04, 0x40000000 },
-       { 0x001668,   1, 0x04, 0x00000000 },
-       { 0x000318,   2, 0x04, 0x00000008 },
-       { 0x000d9c,   1, 0x04, 0x00000001 },
-       { 0x0007dc,   1, 0x04, 0x00000000 },
-       { 0x00074c,   1, 0x04, 0x00000055 },
-       { 0x001420,   1, 0x04, 0x00000003 },
-       { 0x0017bc,   2, 0x04, 0x00000000 },
-       { 0x0017c4,   1, 0x04, 0x00000001 },
-       { 0x001008,   1, 0x04, 0x00000008 },
-       { 0x00100c,   1, 0x04, 0x00000040 },
-       { 0x001010,   1, 0x04, 0x0000012c },
-       { 0x000d60,   1, 0x04, 0x00000040 },
-       { 0x00075c,   1, 0x04, 0x00000003 },
-       { 0x001018,   1, 0x04, 0x00000020 },
-       { 0x00101c,   1, 0x04, 0x00000001 },
-       { 0x001020,   1, 0x04, 0x00000020 },
-       { 0x001024,   1, 0x04, 0x00000001 },
-       { 0x001444,   3, 0x04, 0x00000000 },
-       { 0x000360,   1, 0x04, 0x20164010 },
-       { 0x000364,   1, 0x04, 0x00000020 },
-       { 0x000368,   1, 0x04, 0x00000000 },
-       { 0x000de4,   1, 0x04, 0x00000000 },
-       { 0x000204,   1, 0x04, 0x00000006 },
-       { 0x000208,   1, 0x04, 0x00000000 },
-       { 0x0002cc,   1, 0x04, 0x003fffff },
-       { 0x0002d0,   1, 0x04, 0x00000c48 },
-       { 0x001220,   1, 0x04, 0x00000005 },
-       { 0x000fdc,   1, 0x04, 0x00000000 },
-       { 0x000f98,   1, 0x04, 0x00300008 },
-       { 0x001284,   1, 0x04, 0x04000080 },
-       { 0x001450,   1, 0x04, 0x00300008 },
-       { 0x001454,   1, 0x04, 0x04000080 },
-       { 0x000214,   1, 0x04, 0x00000000 },
-       {}
-};
-
-static const struct nvc0_graph_init
-nvc1_grctx_init_9197_0[] = {
-       { 0x003400, 128, 0x04, 0x00000000 },
-       { 0x0002e4,   1, 0x04, 0x0000b001 },
-       {}
-};
-
-static const struct nvc0_graph_pack
-nvc1_grctx_pack_mthd[] = {
-       { nvc1_grctx_init_9097_0, 0x9097 },
-       { nvc1_grctx_init_9197_0, 0x9197 },
-       { nvc0_grctx_init_902d_0, 0x902d },
-       { nvc0_grctx_init_9039_0, 0x9039 },
-       { nvc0_grctx_init_90c0_0, 0x90c0 },
-       {}
-};
-
-static const struct nvc0_graph_init
-nvc1_grctx_init_ds_0[] = {
-       { 0x405800,   1, 0x04, 0x0f8000bf },
-       { 0x405830,   1, 0x04, 0x02180218 },
-       { 0x405834,   2, 0x04, 0x00000000 },
-       { 0x405854,   1, 0x04, 0x00000000 },
-       { 0x405870,   4, 0x04, 0x00000001 },
-       { 0x405a00,   2, 0x04, 0x00000000 },
-       { 0x405a18,   1, 0x04, 0x00000000 },
-       {}
-};
-
-static const struct nvc0_graph_init
-nvc1_grctx_init_pd_0[] = {
-       { 0x406020,   1, 0x04, 0x000103c1 },
-       { 0x406028,   4, 0x04, 0x00000001 },
-       { 0x4064a8,   1, 0x04, 0x00000000 },
-       { 0x4064ac,   1, 0x04, 0x00003fff },
-       { 0x4064b4,   2, 0x04, 0x00000000 },
-       { 0x4064c0,   1, 0x04, 0x80140078 },
-       { 0x4064c4,   1, 0x04, 0x0086ffff },
-       {}
-};
-
-static const struct nvc0_graph_init
-nvc1_grctx_init_be_0[] = {
-       { 0x408800,   1, 0x04, 0x02802a3c },
-       { 0x408804,   1, 0x04, 0x00000040 },
-       { 0x408808,   1, 0x04, 0x1003e005 },
-       { 0x408900,   1, 0x04, 0x3080b801 },
-       { 0x408904,   1, 0x04, 0x62000001 },
-       { 0x408908,   1, 0x04, 0x00c80929 },
-       { 0x408980,   1, 0x04, 0x0000011d },
-       {}
-};
-
-static const struct nvc0_graph_pack
-nvc1_grctx_pack_hub[] = {
-       { nvc0_grctx_init_main_0 },
-       { nvc0_grctx_init_fe_0 },
-       { nvc0_grctx_init_pri_0 },
-       { nvc0_grctx_init_memfmt_0 },
-       { nvc1_grctx_init_ds_0 },
-       { nvc1_grctx_init_pd_0 },
-       { nvc0_grctx_init_rstr2d_0 },
-       { nvc0_grctx_init_scc_0 },
-       { nvc1_grctx_init_be_0 },
-       {}
-};
-
-static const struct nvc0_graph_init
-nvc1_grctx_init_setup_0[] = {
-       { 0x418800,   1, 0x04, 0x0006860a },
-       { 0x418808,   3, 0x04, 0x00000000 },
-       { 0x418828,   1, 0x04, 0x00008442 },
-       { 0x418830,   1, 0x04, 0x10000001 },
-       { 0x4188d8,   1, 0x04, 0x00000008 },
-       { 0x4188e0,   1, 0x04, 0x01000000 },
-       { 0x4188e8,   5, 0x04, 0x00000000 },
-       { 0x4188fc,   1, 0x04, 0x00100018 },
-       {}
-};
-
-const struct nvc0_graph_init
-nvc1_grctx_init_gpm_0[] = {
-       { 0x418c08,   1, 0x04, 0x00000001 },
-       { 0x418c10,   8, 0x04, 0x00000000 },
-       { 0x418c6c,   1, 0x04, 0x00000001 },
-       { 0x418c80,   1, 0x04, 0x20200004 },
-       { 0x418c8c,   1, 0x04, 0x00000001 },
-       {}
-};
-
-static const struct nvc0_graph_pack
-nvc1_grctx_pack_gpc[] = {
-       { nvc0_grctx_init_gpc_unk_0 },
-       { nvc0_grctx_init_prop_0 },
-       { nvc0_grctx_init_gpc_unk_1 },
-       { nvc1_grctx_init_setup_0 },
-       { nvc0_grctx_init_zcull_0 },
-       { nvc0_grctx_init_crstr_0 },
-       { nvc1_grctx_init_gpm_0 },
-       { nvc0_grctx_init_gcc_0 },
-       {}
-};
-
-const struct nvc0_graph_init
-nvc1_grctx_init_pe_0[] = {
-       { 0x419818,   1, 0x04, 0x00000000 },
-       { 0x41983c,   1, 0x04, 0x00038bc7 },
-       { 0x419848,   1, 0x04, 0x00000000 },
-       { 0x419864,   1, 0x04, 0x00000129 },
-       { 0x419888,   1, 0x04, 0x00000000 },
-       {}
-};
-
-const struct nvc0_graph_init
-nvc1_grctx_init_wwdx_0[] = {
-       { 0x419b00,   1, 0x04, 0x0a418820 },
-       { 0x419b04,   1, 0x04, 0x062080e6 },
-       { 0x419b08,   1, 0x04, 0x020398a4 },
-       { 0x419b0c,   1, 0x04, 0x0e629062 },
-       { 0x419b10,   1, 0x04, 0x0a418820 },
-       { 0x419b14,   1, 0x04, 0x000000e6 },
-       { 0x419bd0,   1, 0x04, 0x00900103 },
-       { 0x419be0,   1, 0x04, 0x00400001 },
-       { 0x419be4,   1, 0x04, 0x00000000 },
-       {}
-};
-
-const struct nvc0_graph_init
-nvc1_grctx_init_tpccs_0[] = {
-       { 0x419d20,   1, 0x04, 0x12180000 },
-       { 0x419d24,   1, 0x04, 0x00001fff },
-       { 0x419d44,   1, 0x04, 0x02180218 },
-       {}
-};
-
-static const struct nvc0_graph_pack
-nvc1_grctx_pack_tpc[] = {
-       { nvc1_grctx_init_pe_0 },
-       { nvc4_grctx_init_tex_0 },
-       { nvc1_grctx_init_wwdx_0 },
-       { nvc0_grctx_init_mpc_0 },
-       { nvc4_grctx_init_l1c_0 },
-       { nvc1_grctx_init_tpccs_0 },
-       { nvc4_grctx_init_sm_0 },
-       {}
-};
-
-/*******************************************************************************
- * PGRAPH context implementation
- ******************************************************************************/
-
-void
-nvc1_grctx_generate_attrib(struct nvc0_grctx *info)
-{
-       struct nvc0_graph_priv *priv = info->priv;
-       const struct nvc0_grctx_oclass *impl = nvc0_grctx_impl(priv);
-       const u32  alpha = impl->alpha_nr;
-       const u32   beta = impl->attrib_nr;
-       const u32   size = 0x20 * (impl->attrib_nr_max + impl->alpha_nr_max);
-       const u32 access = NV_MEM_ACCESS_RW;
-       const int s = 12;
-       const int b = mmio_vram(info, size * priv->tpc_total, (1 << s), access);
-       const int timeslice_mode = 1;
-       const int max_batches = 0xffff;
-       u32 bo = 0;
-       u32 ao = bo + impl->attrib_nr_max * priv->tpc_total;
-       int gpc, tpc;
-
-       mmio_refn(info, 0x418810, 0x80000000, s, b);
-       mmio_refn(info, 0x419848, 0x10000000, s, b);
-       mmio_wr32(info, 0x405830, (beta << 16) | alpha);
-       mmio_wr32(info, 0x4064c4, ((alpha / 4) << 16) | max_batches);
-
-       for (gpc = 0; gpc < priv->gpc_nr; gpc++) {
-               for (tpc = 0; tpc < priv->tpc_nr[gpc]; tpc++) {
-                       const u32 a = alpha;
-                       const u32 b =  beta;
-                       const u32 t = timeslice_mode;
-                       const u32 o = TPC_UNIT(gpc, tpc, 0x500);
-                       mmio_skip(info, o + 0x20, (t << 28) | (b << 16) | ++bo);
-                       mmio_wr32(info, o + 0x20, (t << 28) | (b << 16) | --bo);
-                       bo += impl->attrib_nr_max;
-                       mmio_wr32(info, o + 0x44, (a << 16) | ao);
-                       ao += impl->alpha_nr_max;
-               }
-       }
-}
-
-void
-nvc1_grctx_generate_unkn(struct nvc0_graph_priv *priv)
-{
-       nv_mask(priv, 0x418c6c, 0x00000001, 0x00000001);
-       nv_mask(priv, 0x41980c, 0x00000010, 0x00000010);
-       nv_mask(priv, 0x419814, 0x00000004, 0x00000004);
-       nv_mask(priv, 0x4064c0, 0x80000000, 0x80000000);
-       nv_mask(priv, 0x405800, 0x08000000, 0x08000000);
-       nv_mask(priv, 0x419c00, 0x00000008, 0x00000008);
-}
-
-struct nouveau_oclass *
-nvc1_grctx_oclass = &(struct nvc0_grctx_oclass) {
-       .base.handle = NV_ENGCTX(GR, 0xc1),
-       .base.ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nvc0_graph_context_ctor,
-               .dtor = nvc0_graph_context_dtor,
-               .init = _nouveau_graph_context_init,
-               .fini = _nouveau_graph_context_fini,
-               .rd32 = _nouveau_graph_context_rd32,
-               .wr32 = _nouveau_graph_context_wr32,
-       },
-       .main  = nvc0_grctx_generate_main,
-       .unkn  = nvc1_grctx_generate_unkn,
-       .hub   = nvc1_grctx_pack_hub,
-       .gpc   = nvc1_grctx_pack_gpc,
-       .zcull = nvc0_grctx_pack_zcull,
-       .tpc   = nvc1_grctx_pack_tpc,
-       .icmd  = nvc1_grctx_pack_icmd,
-       .mthd  = nvc1_grctx_pack_mthd,
-       .bundle = nvc0_grctx_generate_bundle,
-       .bundle_size = 0x1800,
-       .pagepool = nvc0_grctx_generate_pagepool,
-       .pagepool_size = 0x8000,
-       .attrib = nvc1_grctx_generate_attrib,
-       .attrib_nr_max = 0x324,
-       .attrib_nr = 0x218,
-       .alpha_nr_max = 0x324,
-       .alpha_nr = 0x218,
-}.base;
diff --git a/drivers/gpu/drm/nouveau/core/engine/graph/ctxnvc4.c b/drivers/gpu/drm/nouveau/core/engine/graph/ctxnvc4.c
deleted file mode 100644 (file)
index 41705c6..0000000
+++ /dev/null
@@ -1,109 +0,0 @@
-/*
- * Copyright 2013 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 <bskeggs@redhat.com>
- */
-
-#include "ctxnvc0.h"
-
-/*******************************************************************************
- * PGRAPH context register lists
- ******************************************************************************/
-
-const struct nvc0_graph_init
-nvc4_grctx_init_tex_0[] = {
-       { 0x419a00,   1, 0x04, 0x000001f0 },
-       { 0x419a04,   1, 0x04, 0x00000001 },
-       { 0x419a08,   1, 0x04, 0x00000023 },
-       { 0x419a0c,   1, 0x04, 0x00020000 },
-       { 0x419a10,   1, 0x04, 0x00000000 },
-       { 0x419a14,   1, 0x04, 0x00000200 },
-       { 0x419a1c,   1, 0x04, 0x00000000 },
-       { 0x419a20,   1, 0x04, 0x00000800 },
-       { 0x419ac4,   1, 0x04, 0x0007f440 },
-       {}
-};
-
-const struct nvc0_graph_init
-nvc4_grctx_init_l1c_0[] = {
-       { 0x419cb0,   1, 0x04, 0x00020048 },
-       { 0x419ce8,   1, 0x04, 0x00000000 },
-       { 0x419cf4,   1, 0x04, 0x00000183 },
-       {}
-};
-
-const struct nvc0_graph_init
-nvc4_grctx_init_sm_0[] = {
-       { 0x419e04,   3, 0x04, 0x00000000 },
-       { 0x419e10,   1, 0x04, 0x00000002 },
-       { 0x419e44,   1, 0x04, 0x001beff2 },
-       { 0x419e48,   1, 0x04, 0x00000000 },
-       { 0x419e4c,   1, 0x04, 0x0000000f },
-       { 0x419e50,  17, 0x04, 0x00000000 },
-       { 0x419e98,   1, 0x04, 0x00000000 },
-       { 0x419ee0,   1, 0x04, 0x00011110 },
-       { 0x419f30,  11, 0x04, 0x00000000 },
-       {}
-};
-
-static const struct nvc0_graph_pack
-nvc4_grctx_pack_tpc[] = {
-       { nvc0_grctx_init_pe_0 },
-       { nvc4_grctx_init_tex_0 },
-       { nvc0_grctx_init_wwdx_0 },
-       { nvc0_grctx_init_mpc_0 },
-       { nvc4_grctx_init_l1c_0 },
-       { nvc0_grctx_init_tpccs_0 },
-       { nvc4_grctx_init_sm_0 },
-       {}
-};
-
-/*******************************************************************************
- * PGRAPH context implementation
- ******************************************************************************/
-
-struct nouveau_oclass *
-nvc4_grctx_oclass = &(struct nvc0_grctx_oclass) {
-       .base.handle = NV_ENGCTX(GR, 0xc3),
-       .base.ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nvc0_graph_context_ctor,
-               .dtor = nvc0_graph_context_dtor,
-               .init = _nouveau_graph_context_init,
-               .fini = _nouveau_graph_context_fini,
-               .rd32 = _nouveau_graph_context_rd32,
-               .wr32 = _nouveau_graph_context_wr32,
-       },
-       .main  = nvc0_grctx_generate_main,
-       .unkn  = nvc0_grctx_generate_unkn,
-       .hub   = nvc0_grctx_pack_hub,
-       .gpc   = nvc0_grctx_pack_gpc,
-       .zcull = nvc0_grctx_pack_zcull,
-       .tpc   = nvc4_grctx_pack_tpc,
-       .icmd  = nvc0_grctx_pack_icmd,
-       .mthd  = nvc0_grctx_pack_mthd,
-       .bundle = nvc0_grctx_generate_bundle,
-       .bundle_size = 0x1800,
-       .pagepool = nvc0_grctx_generate_pagepool,
-       .pagepool_size = 0x8000,
-       .attrib = nvc0_grctx_generate_attrib,
-       .attrib_nr_max = 0x324,
-       .attrib_nr = 0x218,
-}.base;
diff --git a/drivers/gpu/drm/nouveau/core/engine/graph/ctxnvc8.c b/drivers/gpu/drm/nouveau/core/engine/graph/ctxnvc8.c
deleted file mode 100644 (file)
index 8f804cd..0000000
+++ /dev/null
@@ -1,360 +0,0 @@
-/*
- * Copyright 2013 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 <bskeggs@redhat.com>
- */
-
-#include "ctxnvc0.h"
-
-/*******************************************************************************
- * PGRAPH context register lists
- ******************************************************************************/
-
-static const struct nvc0_graph_init
-nvc8_grctx_init_icmd_0[] = {
-       { 0x001000,   1, 0x01, 0x00000004 },
-       { 0x0000a9,   1, 0x01, 0x0000ffff },
-       { 0x000038,   1, 0x01, 0x0fac6881 },
-       { 0x00003d,   1, 0x01, 0x00000001 },
-       { 0x0000e8,   8, 0x01, 0x00000400 },
-       { 0x000078,   8, 0x01, 0x00000300 },
-       { 0x000050,   1, 0x01, 0x00000011 },
-       { 0x000058,   8, 0x01, 0x00000008 },
-       { 0x000208,   8, 0x01, 0x00000001 },
-       { 0x000081,   1, 0x01, 0x00000001 },
-       { 0x000085,   1, 0x01, 0x00000004 },
-       { 0x000088,   1, 0x01, 0x00000400 },
-       { 0x000090,   1, 0x01, 0x00000300 },
-       { 0x000098,   1, 0x01, 0x00001001 },
-       { 0x0000e3,   1, 0x01, 0x00000001 },
-       { 0x0000da,   1, 0x01, 0x00000001 },
-       { 0x0000f8,   1, 0x01, 0x00000003 },
-       { 0x0000fa,   1, 0x01, 0x00000001 },
-       { 0x00009f,   4, 0x01, 0x0000ffff },
-       { 0x0000b1,   1, 0x01, 0x00000001 },
-       { 0x0000b2,  40, 0x01, 0x00000000 },
-       { 0x000210,   8, 0x01, 0x00000040 },
-       { 0x000218,   8, 0x01, 0x0000c080 },
-       { 0x0000ad,   1, 0x01, 0x0000013e },
-       { 0x0000e1,   1, 0x01, 0x00000010 },
-       { 0x000290,  16, 0x01, 0x00000000 },
-       { 0x0003b0,  16, 0x01, 0x00000000 },
-       { 0x0002a0,  16, 0x01, 0x00000000 },
-       { 0x000420,  16, 0x01, 0x00000000 },
-       { 0x0002b0,  16, 0x01, 0x00000000 },
-       { 0x000430,  16, 0x01, 0x00000000 },
-       { 0x0002c0,  16, 0x01, 0x00000000 },
-       { 0x0004d0,  16, 0x01, 0x00000000 },
-       { 0x000720,  16, 0x01, 0x00000000 },
-       { 0x0008c0,  16, 0x01, 0x00000000 },
-       { 0x000890,  16, 0x01, 0x00000000 },
-       { 0x0008e0,  16, 0x01, 0x00000000 },
-       { 0x0008a0,  16, 0x01, 0x00000000 },
-       { 0x0008f0,  16, 0x01, 0x00000000 },
-       { 0x00094c,   1, 0x01, 0x000000ff },
-       { 0x00094d,   1, 0x01, 0xffffffff },
-       { 0x00094e,   1, 0x01, 0x00000002 },
-       { 0x0002ec,   1, 0x01, 0x00000001 },
-       { 0x000303,   1, 0x01, 0x00000001 },
-       { 0x0002e6,   1, 0x01, 0x00000001 },
-       { 0x000466,   1, 0x01, 0x00000052 },
-       { 0x000301,   1, 0x01, 0x3f800000 },
-       { 0x000304,   1, 0x01, 0x30201000 },
-       { 0x000305,   1, 0x01, 0x70605040 },
-       { 0x000306,   1, 0x01, 0xb8a89888 },
-       { 0x000307,   1, 0x01, 0xf8e8d8c8 },
-       { 0x00030a,   1, 0x01, 0x00ffff00 },
-       { 0x00030b,   1, 0x01, 0x0000001a },
-       { 0x00030c,   1, 0x01, 0x00000001 },
-       { 0x000318,   1, 0x01, 0x00000001 },
-       { 0x000340,   1, 0x01, 0x00000000 },
-       { 0x000375,   1, 0x01, 0x00000001 },
-       { 0x000351,   1, 0x01, 0x00000100 },
-       { 0x00037d,   1, 0x01, 0x00000006 },
-       { 0x0003a0,   1, 0x01, 0x00000002 },
-       { 0x0003aa,   1, 0x01, 0x00000001 },
-       { 0x0003a9,   1, 0x01, 0x00000001 },
-       { 0x000380,   1, 0x01, 0x00000001 },
-       { 0x000360,   1, 0x01, 0x00000040 },
-       { 0x000366,   2, 0x01, 0x00000000 },
-       { 0x000368,   1, 0x01, 0x00001fff },
-       { 0x000370,   2, 0x01, 0x00000000 },
-       { 0x000372,   1, 0x01, 0x003fffff },
-       { 0x00037a,   1, 0x01, 0x00000012 },
-       { 0x0005e0,   5, 0x01, 0x00000022 },
-       { 0x000619,   1, 0x01, 0x00000003 },
-       { 0x000811,   1, 0x01, 0x00000003 },
-       { 0x000812,   1, 0x01, 0x00000004 },
-       { 0x000813,   1, 0x01, 0x00000006 },
-       { 0x000814,   1, 0x01, 0x00000008 },
-       { 0x000815,   1, 0x01, 0x0000000b },
-       { 0x000800,   6, 0x01, 0x00000001 },
-       { 0x000632,   1, 0x01, 0x00000001 },
-       { 0x000633,   1, 0x01, 0x00000002 },
-       { 0x000634,   1, 0x01, 0x00000003 },
-       { 0x000635,   1, 0x01, 0x00000004 },
-       { 0x000654,   1, 0x01, 0x3f800000 },
-       { 0x000657,   1, 0x01, 0x3f800000 },
-       { 0x000655,   2, 0x01, 0x3f800000 },
-       { 0x0006cd,   1, 0x01, 0x3f800000 },
-       { 0x0007f5,   1, 0x01, 0x3f800000 },
-       { 0x0007dc,   1, 0x01, 0x39291909 },
-       { 0x0007dd,   1, 0x01, 0x79695949 },
-       { 0x0007de,   1, 0x01, 0xb9a99989 },
-       { 0x0007df,   1, 0x01, 0xf9e9d9c9 },
-       { 0x0007e8,   1, 0x01, 0x00003210 },
-       { 0x0007e9,   1, 0x01, 0x00007654 },
-       { 0x0007ea,   1, 0x01, 0x00000098 },
-       { 0x0007ec,   1, 0x01, 0x39291909 },
-       { 0x0007ed,   1, 0x01, 0x79695949 },
-       { 0x0007ee,   1, 0x01, 0xb9a99989 },
-       { 0x0007ef,   1, 0x01, 0xf9e9d9c9 },
-       { 0x0007f0,   1, 0x01, 0x00003210 },
-       { 0x0007f1,   1, 0x01, 0x00007654 },
-       { 0x0007f2,   1, 0x01, 0x00000098 },
-       { 0x0005a5,   1, 0x01, 0x00000001 },
-       { 0x000980, 128, 0x01, 0x00000000 },
-       { 0x000468,   1, 0x01, 0x00000004 },
-       { 0x00046c,   1, 0x01, 0x00000001 },
-       { 0x000470,  96, 0x01, 0x00000000 },
-       { 0x000510,  16, 0x01, 0x3f800000 },
-       { 0x000520,   1, 0x01, 0x000002b6 },
-       { 0x000529,   1, 0x01, 0x00000001 },
-       { 0x000530,  16, 0x01, 0xffff0000 },
-       { 0x000585,   1, 0x01, 0x0000003f },
-       { 0x000576,   1, 0x01, 0x00000003 },
-       { 0x00057b,   1, 0x01, 0x00000059 },
-       { 0x000586,   1, 0x01, 0x00000040 },
-       { 0x000582,   2, 0x01, 0x00000080 },
-       { 0x0005c2,   1, 0x01, 0x00000001 },
-       { 0x000638,   2, 0x01, 0x00000001 },
-       { 0x00063a,   1, 0x01, 0x00000002 },
-       { 0x00063b,   2, 0x01, 0x00000001 },
-       { 0x00063d,   1, 0x01, 0x00000002 },
-       { 0x00063e,   1, 0x01, 0x00000001 },
-       { 0x0008b8,   8, 0x01, 0x00000001 },
-       { 0x000900,   8, 0x01, 0x00000001 },
-       { 0x000908,   8, 0x01, 0x00000002 },
-       { 0x000910,  16, 0x01, 0x00000001 },
-       { 0x000920,   8, 0x01, 0x00000002 },
-       { 0x000928,   8, 0x01, 0x00000001 },
-       { 0x000648,   9, 0x01, 0x00000001 },
-       { 0x000658,   1, 0x01, 0x0000000f },
-       { 0x0007ff,   1, 0x01, 0x0000000a },
-       { 0x00066a,   1, 0x01, 0x40000000 },
-       { 0x00066b,   1, 0x01, 0x10000000 },
-       { 0x00066c,   2, 0x01, 0xffff0000 },
-       { 0x0007af,   2, 0x01, 0x00000008 },
-       { 0x0007f6,   1, 0x01, 0x00000001 },
-       { 0x0006b2,   1, 0x01, 0x00000055 },
-       { 0x0007ad,   1, 0x01, 0x00000003 },
-       { 0x000937,   1, 0x01, 0x00000001 },
-       { 0x000971,   1, 0x01, 0x00000008 },
-       { 0x000972,   1, 0x01, 0x00000040 },
-       { 0x000973,   1, 0x01, 0x0000012c },
-       { 0x00097c,   1, 0x01, 0x00000040 },
-       { 0x000979,   1, 0x01, 0x00000003 },
-       { 0x000975,   1, 0x01, 0x00000020 },
-       { 0x000976,   1, 0x01, 0x00000001 },
-       { 0x000977,   1, 0x01, 0x00000020 },
-       { 0x000978,   1, 0x01, 0x00000001 },
-       { 0x000957,   1, 0x01, 0x00000003 },
-       { 0x00095e,   1, 0x01, 0x20164010 },
-       { 0x00095f,   1, 0x01, 0x00000020 },
-       { 0x00097d,   1, 0x01, 0x00000020 },
-       { 0x000683,   1, 0x01, 0x00000006 },
-       { 0x000685,   1, 0x01, 0x003fffff },
-       { 0x000687,   1, 0x01, 0x00000c48 },
-       { 0x0006a0,   1, 0x01, 0x00000005 },
-       { 0x000840,   1, 0x01, 0x00300008 },
-       { 0x000841,   1, 0x01, 0x04000080 },
-       { 0x000842,   1, 0x01, 0x00300008 },
-       { 0x000843,   1, 0x01, 0x04000080 },
-       { 0x000818,   8, 0x01, 0x00000000 },
-       { 0x000848,  16, 0x01, 0x00000000 },
-       { 0x000738,   1, 0x01, 0x00000000 },
-       { 0x0006aa,   1, 0x01, 0x00000001 },
-       { 0x0006ab,   1, 0x01, 0x00000002 },
-       { 0x0006ac,   1, 0x01, 0x00000080 },
-       { 0x0006ad,   2, 0x01, 0x00000100 },
-       { 0x0006b1,   1, 0x01, 0x00000011 },
-       { 0x0006bb,   1, 0x01, 0x000000cf },
-       { 0x0006ce,   1, 0x01, 0x2a712488 },
-       { 0x000739,   1, 0x01, 0x4085c000 },
-       { 0x00073a,   1, 0x01, 0x00000080 },
-       { 0x000786,   1, 0x01, 0x80000100 },
-       { 0x00073c,   1, 0x01, 0x00010100 },
-       { 0x00073d,   1, 0x01, 0x02800000 },
-       { 0x000787,   1, 0x01, 0x000000cf },
-       { 0x00078c,   1, 0x01, 0x00000008 },
-       { 0x000792,   1, 0x01, 0x00000001 },
-       { 0x000794,   3, 0x01, 0x00000001 },
-       { 0x000797,   1, 0x01, 0x000000cf },
-       { 0x000836,   1, 0x01, 0x00000001 },
-       { 0x00079a,   1, 0x01, 0x00000002 },
-       { 0x000833,   1, 0x01, 0x04444480 },
-       { 0x0007a1,   1, 0x01, 0x00000001 },
-       { 0x0007a3,   3, 0x01, 0x00000001 },
-       { 0x000831,   1, 0x01, 0x00000004 },
-       { 0x00080c,   1, 0x01, 0x00000002 },
-       { 0x00080d,   2, 0x01, 0x00000100 },
-       { 0x00080f,   1, 0x01, 0x00000001 },
-       { 0x000823,   1, 0x01, 0x00000002 },
-       { 0x000824,   2, 0x01, 0x00000100 },
-       { 0x000826,   1, 0x01, 0x00000001 },
-       { 0x00095d,   1, 0x01, 0x00000001 },
-       { 0x00082b,   1, 0x01, 0x00000004 },
-       { 0x000942,   1, 0x01, 0x00010001 },
-       { 0x000943,   1, 0x01, 0x00000001 },
-       { 0x000944,   1, 0x01, 0x00000022 },
-       { 0x0007c5,   1, 0x01, 0x00010001 },
-       { 0x000834,   1, 0x01, 0x00000001 },
-       { 0x0007c7,   1, 0x01, 0x00000001 },
-       { 0x00c1b0,   8, 0x01, 0x0000000f },
-       { 0x00c1b8,   1, 0x01, 0x0fac6881 },
-       { 0x00c1b9,   1, 0x01, 0x00fac688 },
-       { 0x01e100,   1, 0x01, 0x00000001 },
-       { 0x001000,   1, 0x01, 0x00000002 },
-       { 0x0006aa,   1, 0x01, 0x00000001 },
-       { 0x0006ad,   2, 0x01, 0x00000100 },
-       { 0x0006b1,   1, 0x01, 0x00000011 },
-       { 0x00078c,   1, 0x01, 0x00000008 },
-       { 0x000792,   1, 0x01, 0x00000001 },
-       { 0x000794,   3, 0x01, 0x00000001 },
-       { 0x000797,   1, 0x01, 0x000000cf },
-       { 0x00079a,   1, 0x01, 0x00000002 },
-       { 0x000833,   1, 0x01, 0x04444480 },
-       { 0x0007a1,   1, 0x01, 0x00000001 },
-       { 0x0007a3,   3, 0x01, 0x00000001 },
-       { 0x000831,   1, 0x01, 0x00000004 },
-       { 0x01e100,   1, 0x01, 0x00000001 },
-       { 0x001000,   1, 0x01, 0x00000014 },
-       { 0x000351,   1, 0x01, 0x00000100 },
-       { 0x000957,   1, 0x01, 0x00000003 },
-       { 0x00095d,   1, 0x01, 0x00000001 },
-       { 0x00082b,   1, 0x01, 0x00000004 },
-       { 0x000942,   1, 0x01, 0x00010001 },
-       { 0x000943,   1, 0x01, 0x00000001 },
-       { 0x0007c5,   1, 0x01, 0x00010001 },
-       { 0x000834,   1, 0x01, 0x00000001 },
-       { 0x0007c7,   1, 0x01, 0x00000001 },
-       { 0x01e100,   1, 0x01, 0x00000001 },
-       { 0x001000,   1, 0x01, 0x00000001 },
-       { 0x00080c,   1, 0x01, 0x00000002 },
-       { 0x00080d,   2, 0x01, 0x00000100 },
-       { 0x00080f,   1, 0x01, 0x00000001 },
-       { 0x000823,   1, 0x01, 0x00000002 },
-       { 0x000824,   2, 0x01, 0x00000100 },
-       { 0x000826,   1, 0x01, 0x00000001 },
-       { 0x01e100,   1, 0x01, 0x00000001 },
-       {}
-};
-
-static const struct nvc0_graph_pack
-nvc8_grctx_pack_icmd[] = {
-       { nvc8_grctx_init_icmd_0 },
-       {}
-};
-
-const struct nvc0_graph_init
-nvc8_grctx_init_9197_0[] = {
-       { 0x0002e4,   1, 0x04, 0x0000b001 },
-       {}
-};
-
-const struct nvc0_graph_init
-nvc8_grctx_init_9297_0[] = {
-       { 0x003400, 128, 0x04, 0x00000000 },
-       { 0x00036c,   2, 0x04, 0x00000000 },
-       { 0x0007a4,   2, 0x04, 0x00000000 },
-       { 0x000374,   1, 0x04, 0x00000000 },
-       { 0x000378,   1, 0x04, 0x00000020 },
-       {}
-};
-
-static const struct nvc0_graph_pack
-nvc8_grctx_pack_mthd[] = {
-       { nvc1_grctx_init_9097_0, 0x9097 },
-       { nvc8_grctx_init_9197_0, 0x9197 },
-       { nvc8_grctx_init_9297_0, 0x9297 },
-       { nvc0_grctx_init_902d_0, 0x902d },
-       { nvc0_grctx_init_9039_0, 0x9039 },
-       { nvc0_grctx_init_90c0_0, 0x90c0 },
-       {}
-};
-
-static const struct nvc0_graph_init
-nvc8_grctx_init_setup_0[] = {
-       { 0x418800,   1, 0x04, 0x0006860a },
-       { 0x418808,   3, 0x04, 0x00000000 },
-       { 0x418828,   1, 0x04, 0x00008442 },
-       { 0x418830,   1, 0x04, 0x00000001 },
-       { 0x4188d8,   1, 0x04, 0x00000008 },
-       { 0x4188e0,   1, 0x04, 0x01000000 },
-       { 0x4188e8,   5, 0x04, 0x00000000 },
-       { 0x4188fc,   1, 0x04, 0x20100000 },
-       {}
-};
-
-static const struct nvc0_graph_pack
-nvc8_grctx_pack_gpc[] = {
-       { nvc0_grctx_init_gpc_unk_0 },
-       { nvc0_grctx_init_prop_0 },
-       { nvc0_grctx_init_gpc_unk_1 },
-       { nvc8_grctx_init_setup_0 },
-       { nvc0_grctx_init_zcull_0 },
-       { nvc0_grctx_init_crstr_0 },
-       { nvc0_grctx_init_gpm_0 },
-       { nvc0_grctx_init_gcc_0 },
-       {}
-};
-
-/*******************************************************************************
- * PGRAPH context implementation
- ******************************************************************************/
-
-struct nouveau_oclass *
-nvc8_grctx_oclass = &(struct nvc0_grctx_oclass) {
-       .base.handle = NV_ENGCTX(GR, 0xc8),
-       .base.ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nvc0_graph_context_ctor,
-               .dtor = nvc0_graph_context_dtor,
-               .init = _nouveau_graph_context_init,
-               .fini = _nouveau_graph_context_fini,
-               .rd32 = _nouveau_graph_context_rd32,
-               .wr32 = _nouveau_graph_context_wr32,
-       },
-       .main  = nvc0_grctx_generate_main,
-       .unkn  = nvc0_grctx_generate_unkn,
-       .hub   = nvc0_grctx_pack_hub,
-       .gpc   = nvc8_grctx_pack_gpc,
-       .zcull = nvc0_grctx_pack_zcull,
-       .tpc   = nvc0_grctx_pack_tpc,
-       .icmd  = nvc8_grctx_pack_icmd,
-       .mthd  = nvc8_grctx_pack_mthd,
-       .bundle = nvc0_grctx_generate_bundle,
-       .bundle_size = 0x1800,
-       .pagepool = nvc0_grctx_generate_pagepool,
-       .pagepool_size = 0x8000,
-       .attrib = nvc0_grctx_generate_attrib,
-       .attrib_nr_max = 0x324,
-       .attrib_nr = 0x218,
-}.base;
diff --git a/drivers/gpu/drm/nouveau/core/engine/graph/ctxnvd7.c b/drivers/gpu/drm/nouveau/core/engine/graph/ctxnvd7.c
deleted file mode 100644 (file)
index fcf534f..0000000
+++ /dev/null
@@ -1,282 +0,0 @@
-/*
- * Copyright 2013 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 <bskeggs@redhat.com>
- */
-
-#include "ctxnvc0.h"
-
-/*******************************************************************************
- * PGRAPH context register lists
- ******************************************************************************/
-
-static const struct nvc0_graph_init
-nvd7_grctx_init_ds_0[] = {
-       { 0x405800,   1, 0x04, 0x0f8000bf },
-       { 0x405830,   1, 0x04, 0x02180324 },
-       { 0x405834,   1, 0x04, 0x08000000 },
-       { 0x405838,   1, 0x04, 0x00000000 },
-       { 0x405854,   1, 0x04, 0x00000000 },
-       { 0x405870,   4, 0x04, 0x00000001 },
-       { 0x405a00,   2, 0x04, 0x00000000 },
-       { 0x405a18,   1, 0x04, 0x00000000 },
-       {}
-};
-
-static const struct nvc0_graph_init
-nvd7_grctx_init_pd_0[] = {
-       { 0x406020,   1, 0x04, 0x000103c1 },
-       { 0x406028,   4, 0x04, 0x00000001 },
-       { 0x4064a8,   1, 0x04, 0x00000000 },
-       { 0x4064ac,   1, 0x04, 0x00003fff },
-       { 0x4064b4,   3, 0x04, 0x00000000 },
-       { 0x4064c0,   1, 0x04, 0x801a0078 },
-       { 0x4064c4,   1, 0x04, 0x00c9ffff },
-       { 0x4064d0,   8, 0x04, 0x00000000 },
-       {}
-};
-
-static const struct nvc0_graph_pack
-nvd7_grctx_pack_hub[] = {
-       { nvc0_grctx_init_main_0 },
-       { nvd9_grctx_init_fe_0 },
-       { nvc0_grctx_init_pri_0 },
-       { nvc0_grctx_init_memfmt_0 },
-       { nvd7_grctx_init_ds_0 },
-       { nvd7_grctx_init_pd_0 },
-       { nvc0_grctx_init_rstr2d_0 },
-       { nvc0_grctx_init_scc_0 },
-       { nvd9_grctx_init_be_0 },
-       {}
-};
-
-static const struct nvc0_graph_init
-nvd7_grctx_init_setup_0[] = {
-       { 0x418800,   1, 0x04, 0x7006860a },
-       { 0x418808,   3, 0x04, 0x00000000 },
-       { 0x418828,   1, 0x04, 0x00008442 },
-       { 0x418830,   1, 0x04, 0x10000001 },
-       { 0x4188d8,   1, 0x04, 0x00000008 },
-       { 0x4188e0,   1, 0x04, 0x01000000 },
-       { 0x4188e8,   5, 0x04, 0x00000000 },
-       { 0x4188fc,   1, 0x04, 0x20100018 },
-       {}
-};
-
-static const struct nvc0_graph_pack
-nvd7_grctx_pack_gpc[] = {
-       { nvc0_grctx_init_gpc_unk_0 },
-       { nvd9_grctx_init_prop_0 },
-       { nvd9_grctx_init_gpc_unk_1 },
-       { nvd7_grctx_init_setup_0 },
-       { nvc0_grctx_init_zcull_0 },
-       { nvd9_grctx_init_crstr_0 },
-       { nvc1_grctx_init_gpm_0 },
-       { nvc0_grctx_init_gcc_0 },
-       {}
-};
-
-const struct nvc0_graph_init
-nvd7_grctx_init_pe_0[] = {
-       { 0x419848,   1, 0x04, 0x00000000 },
-       { 0x419864,   1, 0x04, 0x00000129 },
-       { 0x419888,   1, 0x04, 0x00000000 },
-       {}
-};
-
-static const struct nvc0_graph_init
-nvd7_grctx_init_tex_0[] = {
-       { 0x419a00,   1, 0x04, 0x000001f0 },
-       { 0x419a04,   1, 0x04, 0x00000001 },
-       { 0x419a08,   1, 0x04, 0x00000023 },
-       { 0x419a0c,   1, 0x04, 0x00020000 },
-       { 0x419a10,   1, 0x04, 0x00000000 },
-       { 0x419a14,   1, 0x04, 0x00000200 },
-       { 0x419a1c,   1, 0x04, 0x00008000 },
-       { 0x419a20,   1, 0x04, 0x00000800 },
-       { 0x419ac4,   1, 0x04, 0x0017f440 },
-       {}
-};
-
-static const struct nvc0_graph_init
-nvd7_grctx_init_mpc_0[] = {
-       { 0x419c00,   1, 0x04, 0x0000000a },
-       { 0x419c04,   1, 0x04, 0x00000006 },
-       { 0x419c08,   1, 0x04, 0x00000002 },
-       { 0x419c20,   1, 0x04, 0x00000000 },
-       { 0x419c24,   1, 0x04, 0x00084210 },
-       { 0x419c28,   1, 0x04, 0x3efbefbe },
-       {}
-};
-
-static const struct nvc0_graph_pack
-nvd7_grctx_pack_tpc[] = {
-       { nvd7_grctx_init_pe_0 },
-       { nvd7_grctx_init_tex_0 },
-       { nvd7_grctx_init_mpc_0 },
-       { nvc4_grctx_init_l1c_0 },
-       { nvd9_grctx_init_sm_0 },
-       {}
-};
-
-static const struct nvc0_graph_init
-nvd7_grctx_init_pes_0[] = {
-       { 0x41be24,   1, 0x04, 0x00000002 },
-       {}
-};
-
-static const struct nvc0_graph_init
-nvd7_grctx_init_cbm_0[] = {
-       { 0x41bec0,   1, 0x04, 0x12180000 },
-       { 0x41bec4,   1, 0x04, 0x00003fff },
-       { 0x41bee4,   1, 0x04, 0x03240218 },
-       {}
-};
-
-const struct nvc0_graph_init
-nvd7_grctx_init_wwdx_0[] = {
-       { 0x41bf00,   1, 0x04, 0x0a418820 },
-       { 0x41bf04,   1, 0x04, 0x062080e6 },
-       { 0x41bf08,   1, 0x04, 0x020398a4 },
-       { 0x41bf0c,   1, 0x04, 0x0e629062 },
-       { 0x41bf10,   1, 0x04, 0x0a418820 },
-       { 0x41bf14,   1, 0x04, 0x000000e6 },
-       { 0x41bfd0,   1, 0x04, 0x00900103 },
-       { 0x41bfe0,   1, 0x04, 0x00400001 },
-       { 0x41bfe4,   1, 0x04, 0x00000000 },
-       {}
-};
-
-static const struct nvc0_graph_pack
-nvd7_grctx_pack_ppc[] = {
-       { nvd7_grctx_init_pes_0 },
-       { nvd7_grctx_init_cbm_0 },
-       { nvd7_grctx_init_wwdx_0 },
-       {}
-};
-
-/*******************************************************************************
- * PGRAPH context implementation
- ******************************************************************************/
-
-void
-nvd7_grctx_generate_attrib(struct nvc0_grctx *info)
-{
-       struct nvc0_graph_priv *priv = info->priv;
-       const struct nvc0_grctx_oclass *impl = nvc0_grctx_impl(priv);
-       const u32  alpha = impl->alpha_nr;
-       const u32   beta = impl->attrib_nr;
-       const u32   size = 0x20 * (impl->attrib_nr_max + impl->alpha_nr_max);
-       const u32 access = NV_MEM_ACCESS_RW;
-       const int s = 12;
-       const int b = mmio_vram(info, size * priv->tpc_total, (1 << s), access);
-       const int timeslice_mode = 1;
-       const int max_batches = 0xffff;
-       u32 bo = 0;
-       u32 ao = bo + impl->attrib_nr_max * priv->tpc_total;
-       int gpc, ppc;
-
-       mmio_refn(info, 0x418810, 0x80000000, s, b);
-       mmio_refn(info, 0x419848, 0x10000000, s, b);
-       mmio_wr32(info, 0x405830, (beta << 16) | alpha);
-       mmio_wr32(info, 0x4064c4, ((alpha / 4) << 16) | max_batches);
-
-       for (gpc = 0; gpc < priv->gpc_nr; gpc++) {
-               for (ppc = 0; ppc < priv->ppc_nr[gpc]; ppc++) {
-                       const u32 a = alpha * priv->ppc_tpc_nr[gpc][ppc];
-                       const u32 b =  beta * priv->ppc_tpc_nr[gpc][ppc];
-                       const u32 t = timeslice_mode;
-                       const u32 o = PPC_UNIT(gpc, ppc, 0);
-                       mmio_skip(info, o + 0xc0, (t << 28) | (b << 16) | ++bo);
-                       mmio_wr32(info, o + 0xc0, (t << 28) | (b << 16) | --bo);
-                       bo += impl->attrib_nr_max * priv->ppc_tpc_nr[gpc][ppc];
-                       mmio_wr32(info, o + 0xe4, (a << 16) | ao);
-                       ao += impl->alpha_nr_max * priv->ppc_tpc_nr[gpc][ppc];
-               }
-       }
-}
-
-void
-nvd7_grctx_generate_main(struct nvc0_graph_priv *priv, struct nvc0_grctx *info)
-{
-       struct nvc0_grctx_oclass *oclass = (void *)nv_engine(priv)->cclass;
-       int i;
-
-       nouveau_mc(priv)->unk260(nouveau_mc(priv), 0);
-
-       nvc0_graph_mmio(priv, oclass->hub);
-       nvc0_graph_mmio(priv, oclass->gpc);
-       nvc0_graph_mmio(priv, oclass->zcull);
-       nvc0_graph_mmio(priv, oclass->tpc);
-       nvc0_graph_mmio(priv, oclass->ppc);
-
-       nv_wr32(priv, 0x404154, 0x00000000);
-
-       oclass->bundle(info);
-       oclass->pagepool(info);
-       oclass->attrib(info);
-       oclass->unkn(priv);
-
-       nvc0_grctx_generate_tpcid(priv);
-       nvc0_grctx_generate_r406028(priv);
-       nvc0_grctx_generate_r4060a8(priv);
-       nve4_grctx_generate_r418bb8(priv);
-       nvc0_grctx_generate_r406800(priv);
-
-       for (i = 0; i < 8; i++)
-               nv_wr32(priv, 0x4064d0 + (i * 0x04), 0x00000000);
-
-       nvc0_graph_icmd(priv, oclass->icmd);
-       nv_wr32(priv, 0x404154, 0x00000400);
-       nvc0_graph_mthd(priv, oclass->mthd);
-       nouveau_mc(priv)->unk260(nouveau_mc(priv), 1);
-}
-
-struct nouveau_oclass *
-nvd7_grctx_oclass = &(struct nvc0_grctx_oclass) {
-       .base.handle = NV_ENGCTX(GR, 0xd7),
-       .base.ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nvc0_graph_context_ctor,
-               .dtor = nvc0_graph_context_dtor,
-               .init = _nouveau_graph_context_init,
-               .fini = _nouveau_graph_context_fini,
-               .rd32 = _nouveau_graph_context_rd32,
-               .wr32 = _nouveau_graph_context_wr32,
-       },
-       .main  = nvd7_grctx_generate_main,
-       .unkn  = nve4_grctx_generate_unkn,
-       .hub   = nvd7_grctx_pack_hub,
-       .gpc   = nvd7_grctx_pack_gpc,
-       .zcull = nvc0_grctx_pack_zcull,
-       .tpc   = nvd7_grctx_pack_tpc,
-       .ppc   = nvd7_grctx_pack_ppc,
-       .icmd  = nvd9_grctx_pack_icmd,
-       .mthd  = nvd9_grctx_pack_mthd,
-       .bundle = nvc0_grctx_generate_bundle,
-       .bundle_size = 0x1800,
-       .pagepool = nvc0_grctx_generate_pagepool,
-       .pagepool_size = 0x8000,
-       .attrib = nvd7_grctx_generate_attrib,
-       .attrib_nr_max = 0x324,
-       .attrib_nr = 0x218,
-       .alpha_nr_max = 0x7ff,
-       .alpha_nr = 0x324,
-}.base;
diff --git a/drivers/gpu/drm/nouveau/core/engine/graph/ctxnvd9.c b/drivers/gpu/drm/nouveau/core/engine/graph/ctxnvd9.c
deleted file mode 100644 (file)
index b9a301b..0000000
+++ /dev/null
@@ -1,530 +0,0 @@
-/*
- * Copyright 2013 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 <bskeggs@redhat.com>
- */
-
-#include "ctxnvc0.h"
-
-/*******************************************************************************
- * PGRAPH context register lists
- ******************************************************************************/
-
-static const struct nvc0_graph_init
-nvd9_grctx_init_icmd_0[] = {
-       { 0x001000,   1, 0x01, 0x00000004 },
-       { 0x0000a9,   1, 0x01, 0x0000ffff },
-       { 0x000038,   1, 0x01, 0x0fac6881 },
-       { 0x00003d,   1, 0x01, 0x00000001 },
-       { 0x0000e8,   8, 0x01, 0x00000400 },
-       { 0x000078,   8, 0x01, 0x00000300 },
-       { 0x000050,   1, 0x01, 0x00000011 },
-       { 0x000058,   8, 0x01, 0x00000008 },
-       { 0x000208,   8, 0x01, 0x00000001 },
-       { 0x000081,   1, 0x01, 0x00000001 },
-       { 0x000085,   1, 0x01, 0x00000004 },
-       { 0x000088,   1, 0x01, 0x00000400 },
-       { 0x000090,   1, 0x01, 0x00000300 },
-       { 0x000098,   1, 0x01, 0x00001001 },
-       { 0x0000e3,   1, 0x01, 0x00000001 },
-       { 0x0000da,   1, 0x01, 0x00000001 },
-       { 0x0000f8,   1, 0x01, 0x00000003 },
-       { 0x0000fa,   1, 0x01, 0x00000001 },
-       { 0x00009f,   4, 0x01, 0x0000ffff },
-       { 0x0000b1,   1, 0x01, 0x00000001 },
-       { 0x0000b2,  40, 0x01, 0x00000000 },
-       { 0x000210,   8, 0x01, 0x00000040 },
-       { 0x000400,  24, 0x01, 0x00000040 },
-       { 0x000218,   8, 0x01, 0x0000c080 },
-       { 0x000440,  24, 0x01, 0x0000c080 },
-       { 0x0000ad,   1, 0x01, 0x0000013e },
-       { 0x0000e1,   1, 0x01, 0x00000010 },
-       { 0x000290,  16, 0x01, 0x00000000 },
-       { 0x0003b0,  16, 0x01, 0x00000000 },
-       { 0x0002a0,  16, 0x01, 0x00000000 },
-       { 0x000420,  16, 0x01, 0x00000000 },
-       { 0x0002b0,  16, 0x01, 0x00000000 },
-       { 0x000430,  16, 0x01, 0x00000000 },
-       { 0x0002c0,  16, 0x01, 0x00000000 },
-       { 0x0004d0,  16, 0x01, 0x00000000 },
-       { 0x000720,  16, 0x01, 0x00000000 },
-       { 0x0008c0,  16, 0x01, 0x00000000 },
-       { 0x000890,  16, 0x01, 0x00000000 },
-       { 0x0008e0,  16, 0x01, 0x00000000 },
-       { 0x0008a0,  16, 0x01, 0x00000000 },
-       { 0x0008f0,  16, 0x01, 0x00000000 },
-       { 0x00094c,   1, 0x01, 0x000000ff },
-       { 0x00094d,   1, 0x01, 0xffffffff },
-       { 0x00094e,   1, 0x01, 0x00000002 },
-       { 0x0002ec,   1, 0x01, 0x00000001 },
-       { 0x000303,   1, 0x01, 0x00000001 },
-       { 0x0002e6,   1, 0x01, 0x00000001 },
-       { 0x000466,   1, 0x01, 0x00000052 },
-       { 0x000301,   1, 0x01, 0x3f800000 },
-       { 0x000304,   1, 0x01, 0x30201000 },
-       { 0x000305,   1, 0x01, 0x70605040 },
-       { 0x000306,   1, 0x01, 0xb8a89888 },
-       { 0x000307,   1, 0x01, 0xf8e8d8c8 },
-       { 0x00030a,   1, 0x01, 0x00ffff00 },
-       { 0x00030b,   1, 0x01, 0x0000001a },
-       { 0x00030c,   1, 0x01, 0x00000001 },
-       { 0x000318,   1, 0x01, 0x00000001 },
-       { 0x000340,   1, 0x01, 0x00000000 },
-       { 0x000375,   1, 0x01, 0x00000001 },
-       { 0x000351,   1, 0x01, 0x00000100 },
-       { 0x00037d,   1, 0x01, 0x00000006 },
-       { 0x0003a0,   1, 0x01, 0x00000002 },
-       { 0x0003aa,   1, 0x01, 0x00000001 },
-       { 0x0003a9,   1, 0x01, 0x00000001 },
-       { 0x000380,   1, 0x01, 0x00000001 },
-       { 0x000360,   1, 0x01, 0x00000040 },
-       { 0x000366,   2, 0x01, 0x00000000 },
-       { 0x000368,   1, 0x01, 0x00001fff },
-       { 0x000370,   2, 0x01, 0x00000000 },
-       { 0x000372,   1, 0x01, 0x003fffff },
-       { 0x00037a,   1, 0x01, 0x00000012 },
-       { 0x0005e0,   5, 0x01, 0x00000022 },
-       { 0x000619,   1, 0x01, 0x00000003 },
-       { 0x000811,   1, 0x01, 0x00000003 },
-       { 0x000812,   1, 0x01, 0x00000004 },
-       { 0x000813,   1, 0x01, 0x00000006 },
-       { 0x000814,   1, 0x01, 0x00000008 },
-       { 0x000815,   1, 0x01, 0x0000000b },
-       { 0x000800,   6, 0x01, 0x00000001 },
-       { 0x000632,   1, 0x01, 0x00000001 },
-       { 0x000633,   1, 0x01, 0x00000002 },
-       { 0x000634,   1, 0x01, 0x00000003 },
-       { 0x000635,   1, 0x01, 0x00000004 },
-       { 0x000654,   1, 0x01, 0x3f800000 },
-       { 0x000657,   1, 0x01, 0x3f800000 },
-       { 0x000655,   2, 0x01, 0x3f800000 },
-       { 0x0006cd,   1, 0x01, 0x3f800000 },
-       { 0x0007f5,   1, 0x01, 0x3f800000 },
-       { 0x0007dc,   1, 0x01, 0x39291909 },
-       { 0x0007dd,   1, 0x01, 0x79695949 },
-       { 0x0007de,   1, 0x01, 0xb9a99989 },
-       { 0x0007df,   1, 0x01, 0xf9e9d9c9 },
-       { 0x0007e8,   1, 0x01, 0x00003210 },
-       { 0x0007e9,   1, 0x01, 0x00007654 },
-       { 0x0007ea,   1, 0x01, 0x00000098 },
-       { 0x0007ec,   1, 0x01, 0x39291909 },
-       { 0x0007ed,   1, 0x01, 0x79695949 },
-       { 0x0007ee,   1, 0x01, 0xb9a99989 },
-       { 0x0007ef,   1, 0x01, 0xf9e9d9c9 },
-       { 0x0007f0,   1, 0x01, 0x00003210 },
-       { 0x0007f1,   1, 0x01, 0x00007654 },
-       { 0x0007f2,   1, 0x01, 0x00000098 },
-       { 0x0005a5,   1, 0x01, 0x00000001 },
-       { 0x000980, 128, 0x01, 0x00000000 },
-       { 0x000468,   1, 0x01, 0x00000004 },
-       { 0x00046c,   1, 0x01, 0x00000001 },
-       { 0x000470,  96, 0x01, 0x00000000 },
-       { 0x000510,  16, 0x01, 0x3f800000 },
-       { 0x000520,   1, 0x01, 0x000002b6 },
-       { 0x000529,   1, 0x01, 0x00000001 },
-       { 0x000530,  16, 0x01, 0xffff0000 },
-       { 0x000585,   1, 0x01, 0x0000003f },
-       { 0x000576,   1, 0x01, 0x00000003 },
-       { 0x00057b,   1, 0x01, 0x00000059 },
-       { 0x000586,   1, 0x01, 0x00000040 },
-       { 0x000582,   2, 0x01, 0x00000080 },
-       { 0x0005c2,   1, 0x01, 0x00000001 },
-       { 0x000638,   2, 0x01, 0x00000001 },
-       { 0x00063a,   1, 0x01, 0x00000002 },
-       { 0x00063b,   2, 0x01, 0x00000001 },
-       { 0x00063d,   1, 0x01, 0x00000002 },
-       { 0x00063e,   1, 0x01, 0x00000001 },
-       { 0x0008b8,   8, 0x01, 0x00000001 },
-       { 0x000900,   8, 0x01, 0x00000001 },
-       { 0x000908,   8, 0x01, 0x00000002 },
-       { 0x000910,  16, 0x01, 0x00000001 },
-       { 0x000920,   8, 0x01, 0x00000002 },
-       { 0x000928,   8, 0x01, 0x00000001 },
-       { 0x000648,   9, 0x01, 0x00000001 },
-       { 0x000658,   1, 0x01, 0x0000000f },
-       { 0x0007ff,   1, 0x01, 0x0000000a },
-       { 0x00066a,   1, 0x01, 0x40000000 },
-       { 0x00066b,   1, 0x01, 0x10000000 },
-       { 0x00066c,   2, 0x01, 0xffff0000 },
-       { 0x0007af,   2, 0x01, 0x00000008 },
-       { 0x0007f6,   1, 0x01, 0x00000001 },
-       { 0x0006b2,   1, 0x01, 0x00000055 },
-       { 0x0007ad,   1, 0x01, 0x00000003 },
-       { 0x000937,   1, 0x01, 0x00000001 },
-       { 0x000971,   1, 0x01, 0x00000008 },
-       { 0x000972,   1, 0x01, 0x00000040 },
-       { 0x000973,   1, 0x01, 0x0000012c },
-       { 0x00097c,   1, 0x01, 0x00000040 },
-       { 0x000979,   1, 0x01, 0x00000003 },
-       { 0x000975,   1, 0x01, 0x00000020 },
-       { 0x000976,   1, 0x01, 0x00000001 },
-       { 0x000977,   1, 0x01, 0x00000020 },
-       { 0x000978,   1, 0x01, 0x00000001 },
-       { 0x000957,   1, 0x01, 0x00000003 },
-       { 0x00095e,   1, 0x01, 0x20164010 },
-       { 0x00095f,   1, 0x01, 0x00000020 },
-       { 0x00097d,   1, 0x01, 0x00000020 },
-       { 0x000683,   1, 0x01, 0x00000006 },
-       { 0x000685,   1, 0x01, 0x003fffff },
-       { 0x000687,   1, 0x01, 0x00000c48 },
-       { 0x0006a0,   1, 0x01, 0x00000005 },
-       { 0x000840,   1, 0x01, 0x00300008 },
-       { 0x000841,   1, 0x01, 0x04000080 },
-       { 0x000842,   1, 0x01, 0x00300008 },
-       { 0x000843,   1, 0x01, 0x04000080 },
-       { 0x000818,   8, 0x01, 0x00000000 },
-       { 0x000848,  16, 0x01, 0x00000000 },
-       { 0x000738,   1, 0x01, 0x00000000 },
-       { 0x0006aa,   1, 0x01, 0x00000001 },
-       { 0x0006ab,   1, 0x01, 0x00000002 },
-       { 0x0006ac,   1, 0x01, 0x00000080 },
-       { 0x0006ad,   2, 0x01, 0x00000100 },
-       { 0x0006b1,   1, 0x01, 0x00000011 },
-       { 0x0006bb,   1, 0x01, 0x000000cf },
-       { 0x0006ce,   1, 0x01, 0x2a712488 },
-       { 0x000739,   1, 0x01, 0x4085c000 },
-       { 0x00073a,   1, 0x01, 0x00000080 },
-       { 0x000786,   1, 0x01, 0x80000100 },
-       { 0x00073c,   1, 0x01, 0x00010100 },
-       { 0x00073d,   1, 0x01, 0x02800000 },
-       { 0x000787,   1, 0x01, 0x000000cf },
-       { 0x00078c,   1, 0x01, 0x00000008 },
-       { 0x000792,   1, 0x01, 0x00000001 },
-       { 0x000794,   3, 0x01, 0x00000001 },
-       { 0x000797,   1, 0x01, 0x000000cf },
-       { 0x000836,   1, 0x01, 0x00000001 },
-       { 0x00079a,   1, 0x01, 0x00000002 },
-       { 0x000833,   1, 0x01, 0x04444480 },
-       { 0x0007a1,   1, 0x01, 0x00000001 },
-       { 0x0007a3,   3, 0x01, 0x00000001 },
-       { 0x000831,   1, 0x01, 0x00000004 },
-       { 0x00080c,   1, 0x01, 0x00000002 },
-       { 0x00080d,   2, 0x01, 0x00000100 },
-       { 0x00080f,   1, 0x01, 0x00000001 },
-       { 0x000823,   1, 0x01, 0x00000002 },
-       { 0x000824,   2, 0x01, 0x00000100 },
-       { 0x000826,   1, 0x01, 0x00000001 },
-       { 0x00095d,   1, 0x01, 0x00000001 },
-       { 0x00082b,   1, 0x01, 0x00000004 },
-       { 0x000942,   1, 0x01, 0x00010001 },
-       { 0x000943,   1, 0x01, 0x00000001 },
-       { 0x000944,   1, 0x01, 0x00000022 },
-       { 0x0007c5,   1, 0x01, 0x00010001 },
-       { 0x000834,   1, 0x01, 0x00000001 },
-       { 0x0007c7,   1, 0x01, 0x00000001 },
-       { 0x00c1b0,   8, 0x01, 0x0000000f },
-       { 0x00c1b8,   1, 0x01, 0x0fac6881 },
-       { 0x00c1b9,   1, 0x01, 0x00fac688 },
-       { 0x01e100,   1, 0x01, 0x00000001 },
-       { 0x001000,   1, 0x01, 0x00000002 },
-       { 0x0006aa,   1, 0x01, 0x00000001 },
-       { 0x0006ad,   2, 0x01, 0x00000100 },
-       { 0x0006b1,   1, 0x01, 0x00000011 },
-       { 0x00078c,   1, 0x01, 0x00000008 },
-       { 0x000792,   1, 0x01, 0x00000001 },
-       { 0x000794,   3, 0x01, 0x00000001 },
-       { 0x000797,   1, 0x01, 0x000000cf },
-       { 0x00079a,   1, 0x01, 0x00000002 },
-       { 0x000833,   1, 0x01, 0x04444480 },
-       { 0x0007a1,   1, 0x01, 0x00000001 },
-       { 0x0007a3,   3, 0x01, 0x00000001 },
-       { 0x000831,   1, 0x01, 0x00000004 },
-       { 0x01e100,   1, 0x01, 0x00000001 },
-       { 0x001000,   1, 0x01, 0x00000014 },
-       { 0x000351,   1, 0x01, 0x00000100 },
-       { 0x000957,   1, 0x01, 0x00000003 },
-       { 0x00095d,   1, 0x01, 0x00000001 },
-       { 0x00082b,   1, 0x01, 0x00000004 },
-       { 0x000942,   1, 0x01, 0x00010001 },
-       { 0x000943,   1, 0x01, 0x00000001 },
-       { 0x0007c5,   1, 0x01, 0x00010001 },
-       { 0x000834,   1, 0x01, 0x00000001 },
-       { 0x0007c7,   1, 0x01, 0x00000001 },
-       { 0x01e100,   1, 0x01, 0x00000001 },
-       { 0x001000,   1, 0x01, 0x00000001 },
-       { 0x00080c,   1, 0x01, 0x00000002 },
-       { 0x00080d,   2, 0x01, 0x00000100 },
-       { 0x00080f,   1, 0x01, 0x00000001 },
-       { 0x000823,   1, 0x01, 0x00000002 },
-       { 0x000824,   2, 0x01, 0x00000100 },
-       { 0x000826,   1, 0x01, 0x00000001 },
-       { 0x01e100,   1, 0x01, 0x00000001 },
-       {}
-};
-
-const struct nvc0_graph_pack
-nvd9_grctx_pack_icmd[] = {
-       { nvd9_grctx_init_icmd_0 },
-       {}
-};
-
-static const struct nvc0_graph_init
-nvd9_grctx_init_90c0_0[] = {
-       { 0x002700,   8, 0x20, 0x00000000 },
-       { 0x002704,   8, 0x20, 0x00000000 },
-       { 0x002708,   8, 0x20, 0x00000000 },
-       { 0x00270c,   8, 0x20, 0x00000000 },
-       { 0x002710,   8, 0x20, 0x00014000 },
-       { 0x002714,   8, 0x20, 0x00000040 },
-       { 0x00030c,   1, 0x04, 0x00000001 },
-       { 0x001944,   1, 0x04, 0x00000000 },
-       { 0x000758,   1, 0x04, 0x00000100 },
-       { 0x0002c4,   1, 0x04, 0x00000000 },
-       { 0x000790,   5, 0x04, 0x00000000 },
-       { 0x00077c,   1, 0x04, 0x00000000 },
-       { 0x000204,   3, 0x04, 0x00000000 },
-       { 0x000214,   1, 0x04, 0x00000000 },
-       { 0x00024c,   1, 0x04, 0x00000000 },
-       { 0x000d94,   1, 0x04, 0x00000001 },
-       { 0x001608,   2, 0x04, 0x00000000 },
-       { 0x001664,   1, 0x04, 0x00000000 },
-       {}
-};
-
-const struct nvc0_graph_pack
-nvd9_grctx_pack_mthd[] = {
-       { nvc1_grctx_init_9097_0, 0x9097 },
-       { nvc8_grctx_init_9197_0, 0x9197 },
-       { nvc8_grctx_init_9297_0, 0x9297 },
-       { nvc0_grctx_init_902d_0, 0x902d },
-       { nvc0_grctx_init_9039_0, 0x9039 },
-       { nvd9_grctx_init_90c0_0, 0x90c0 },
-       {}
-};
-
-const struct nvc0_graph_init
-nvd9_grctx_init_fe_0[] = {
-       { 0x404004,  10, 0x04, 0x00000000 },
-       { 0x404044,   1, 0x04, 0x00000000 },
-       { 0x404094,  13, 0x04, 0x00000000 },
-       { 0x4040c8,   1, 0x04, 0xf0000087 },
-       { 0x4040d0,   6, 0x04, 0x00000000 },
-       { 0x4040e8,   1, 0x04, 0x00001000 },
-       { 0x4040f8,   1, 0x04, 0x00000000 },
-       { 0x404130,   2, 0x04, 0x00000000 },
-       { 0x404138,   1, 0x04, 0x20000040 },
-       { 0x404150,   1, 0x04, 0x0000002e },
-       { 0x404154,   1, 0x04, 0x00000400 },
-       { 0x404158,   1, 0x04, 0x00000200 },
-       { 0x404164,   1, 0x04, 0x00000055 },
-       { 0x404168,   1, 0x04, 0x00000000 },
-       { 0x404178,   2, 0x04, 0x00000000 },
-       { 0x404200,   8, 0x04, 0x00000000 },
-       {}
-};
-
-static const struct nvc0_graph_init
-nvd9_grctx_init_ds_0[] = {
-       { 0x405800,   1, 0x04, 0x0f8000bf },
-       { 0x405830,   1, 0x04, 0x02180218 },
-       { 0x405834,   1, 0x04, 0x08000000 },
-       { 0x405838,   1, 0x04, 0x00000000 },
-       { 0x405854,   1, 0x04, 0x00000000 },
-       { 0x405870,   4, 0x04, 0x00000001 },
-       { 0x405a00,   2, 0x04, 0x00000000 },
-       { 0x405a18,   1, 0x04, 0x00000000 },
-       {}
-};
-
-static const struct nvc0_graph_init
-nvd9_grctx_init_pd_0[] = {
-       { 0x406020,   1, 0x04, 0x000103c1 },
-       { 0x406028,   4, 0x04, 0x00000001 },
-       { 0x4064a8,   1, 0x04, 0x00000000 },
-       { 0x4064ac,   1, 0x04, 0x00003fff },
-       { 0x4064b4,   3, 0x04, 0x00000000 },
-       { 0x4064c0,   1, 0x04, 0x80140078 },
-       { 0x4064c4,   1, 0x04, 0x0086ffff },
-       {}
-};
-
-const struct nvc0_graph_init
-nvd9_grctx_init_be_0[] = {
-       { 0x408800,   1, 0x04, 0x02802a3c },
-       { 0x408804,   1, 0x04, 0x00000040 },
-       { 0x408808,   1, 0x04, 0x1043e005 },
-       { 0x408900,   1, 0x04, 0x3080b801 },
-       { 0x408904,   1, 0x04, 0x62000001 },
-       { 0x408908,   1, 0x04, 0x00c8102f },
-       { 0x408980,   1, 0x04, 0x0000011d },
-       {}
-};
-
-static const struct nvc0_graph_pack
-nvd9_grctx_pack_hub[] = {
-       { nvc0_grctx_init_main_0 },
-       { nvd9_grctx_init_fe_0 },
-       { nvc0_grctx_init_pri_0 },
-       { nvc0_grctx_init_memfmt_0 },
-       { nvd9_grctx_init_ds_0 },
-       { nvd9_grctx_init_pd_0 },
-       { nvc0_grctx_init_rstr2d_0 },
-       { nvc0_grctx_init_scc_0 },
-       { nvd9_grctx_init_be_0 },
-       {}
-};
-
-const struct nvc0_graph_init
-nvd9_grctx_init_prop_0[] = {
-       { 0x418400,   1, 0x04, 0x38004e00 },
-       { 0x418404,   1, 0x04, 0x71e0ffff },
-       { 0x41840c,   1, 0x04, 0x00001008 },
-       { 0x418410,   1, 0x04, 0x0fff0fff },
-       { 0x418414,   1, 0x04, 0x02200fff },
-       { 0x418450,   6, 0x04, 0x00000000 },
-       { 0x418468,   1, 0x04, 0x00000001 },
-       { 0x41846c,   2, 0x04, 0x00000000 },
-       {}
-};
-
-const struct nvc0_graph_init
-nvd9_grctx_init_gpc_unk_1[] = {
-       { 0x418600,   1, 0x04, 0x0000001f },
-       { 0x418684,   1, 0x04, 0x0000000f },
-       { 0x418700,   1, 0x04, 0x00000002 },
-       { 0x418704,   1, 0x04, 0x00000080 },
-       { 0x418708,   3, 0x04, 0x00000000 },
-       {}
-};
-
-static const struct nvc0_graph_init
-nvd9_grctx_init_setup_0[] = {
-       { 0x418800,   1, 0x04, 0x7006860a },
-       { 0x418808,   3, 0x04, 0x00000000 },
-       { 0x418828,   1, 0x04, 0x00008442 },
-       { 0x418830,   1, 0x04, 0x10000001 },
-       { 0x4188d8,   1, 0x04, 0x00000008 },
-       { 0x4188e0,   1, 0x04, 0x01000000 },
-       { 0x4188e8,   5, 0x04, 0x00000000 },
-       { 0x4188fc,   1, 0x04, 0x20100008 },
-       {}
-};
-
-const struct nvc0_graph_init
-nvd9_grctx_init_crstr_0[] = {
-       { 0x418b00,   1, 0x04, 0x00000006 },
-       { 0x418b08,   1, 0x04, 0x0a418820 },
-       { 0x418b0c,   1, 0x04, 0x062080e6 },
-       { 0x418b10,   1, 0x04, 0x020398a4 },
-       { 0x418b14,   1, 0x04, 0x0e629062 },
-       { 0x418b18,   1, 0x04, 0x0a418820 },
-       { 0x418b1c,   1, 0x04, 0x000000e6 },
-       { 0x418bb8,   1, 0x04, 0x00000103 },
-       {}
-};
-
-static const struct nvc0_graph_pack
-nvd9_grctx_pack_gpc[] = {
-       { nvc0_grctx_init_gpc_unk_0 },
-       { nvd9_grctx_init_prop_0 },
-       { nvd9_grctx_init_gpc_unk_1 },
-       { nvd9_grctx_init_setup_0 },
-       { nvc0_grctx_init_zcull_0 },
-       { nvd9_grctx_init_crstr_0 },
-       { nvc1_grctx_init_gpm_0 },
-       { nvc0_grctx_init_gcc_0 },
-       {}
-};
-
-static const struct nvc0_graph_init
-nvd9_grctx_init_tex_0[] = {
-       { 0x419a00,   1, 0x04, 0x000001f0 },
-       { 0x419a04,   1, 0x04, 0x00000001 },
-       { 0x419a08,   1, 0x04, 0x00000023 },
-       { 0x419a0c,   1, 0x04, 0x00020000 },
-       { 0x419a10,   1, 0x04, 0x00000000 },
-       { 0x419a14,   1, 0x04, 0x00000200 },
-       { 0x419a1c,   1, 0x04, 0x00000000 },
-       { 0x419a20,   1, 0x04, 0x00000800 },
-       { 0x419ac4,   1, 0x04, 0x0017f440 },
-       {}
-};
-
-static const struct nvc0_graph_init
-nvd9_grctx_init_mpc_0[] = {
-       { 0x419c00,   1, 0x04, 0x0000000a },
-       { 0x419c04,   1, 0x04, 0x00000006 },
-       { 0x419c08,   1, 0x04, 0x00000002 },
-       { 0x419c20,   1, 0x04, 0x00000000 },
-       { 0x419c24,   1, 0x04, 0x00084210 },
-       { 0x419c28,   1, 0x04, 0x3cf3cf3c },
-       {}
-};
-
-const struct nvc0_graph_init
-nvd9_grctx_init_sm_0[] = {
-       { 0x419e04,   3, 0x04, 0x00000000 },
-       { 0x419e10,   1, 0x04, 0x00000002 },
-       { 0x419e44,   1, 0x04, 0x001beff2 },
-       { 0x419e48,   1, 0x04, 0x00000000 },
-       { 0x419e4c,   1, 0x04, 0x0000000f },
-       { 0x419e50,  17, 0x04, 0x00000000 },
-       { 0x419e98,   1, 0x04, 0x00000000 },
-       { 0x419ee0,   1, 0x04, 0x00010110 },
-       { 0x419f30,  11, 0x04, 0x00000000 },
-       {}
-};
-
-static const struct nvc0_graph_pack
-nvd9_grctx_pack_tpc[] = {
-       { nvc1_grctx_init_pe_0 },
-       { nvd9_grctx_init_tex_0 },
-       { nvc1_grctx_init_wwdx_0 },
-       { nvd9_grctx_init_mpc_0 },
-       { nvc4_grctx_init_l1c_0 },
-       { nvc1_grctx_init_tpccs_0 },
-       { nvd9_grctx_init_sm_0 },
-       {}
-};
-
-/*******************************************************************************
- * PGRAPH context implementation
- ******************************************************************************/
-
-struct nouveau_oclass *
-nvd9_grctx_oclass = &(struct nvc0_grctx_oclass) {
-       .base.handle = NV_ENGCTX(GR, 0xd9),
-       .base.ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nvc0_graph_context_ctor,
-               .dtor = nvc0_graph_context_dtor,
-               .init = _nouveau_graph_context_init,
-               .fini = _nouveau_graph_context_fini,
-               .rd32 = _nouveau_graph_context_rd32,
-               .wr32 = _nouveau_graph_context_wr32,
-       },
-       .main  = nvc0_grctx_generate_main,
-       .unkn  = nvc1_grctx_generate_unkn,
-       .hub   = nvd9_grctx_pack_hub,
-       .gpc   = nvd9_grctx_pack_gpc,
-       .zcull = nvc0_grctx_pack_zcull,
-       .tpc   = nvd9_grctx_pack_tpc,
-       .icmd  = nvd9_grctx_pack_icmd,
-       .mthd  = nvd9_grctx_pack_mthd,
-       .bundle = nvc0_grctx_generate_bundle,
-       .bundle_size = 0x1800,
-       .pagepool = nvc0_grctx_generate_pagepool,
-       .pagepool_size = 0x8000,
-       .attrib = nvc1_grctx_generate_attrib,
-       .attrib_nr_max = 0x324,
-       .attrib_nr = 0x218,
-       .alpha_nr_max = 0x324,
-       .alpha_nr = 0x218,
-}.base;
diff --git a/drivers/gpu/drm/nouveau/core/engine/graph/ctxnve4.c b/drivers/gpu/drm/nouveau/core/engine/graph/ctxnve4.c
deleted file mode 100644 (file)
index ccac2ee..0000000
+++ /dev/null
@@ -1,1020 +0,0 @@
-/*
- * Copyright 2013 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 <bskeggs@redhat.com>
- */
-
-#include "ctxnvc0.h"
-
-/*******************************************************************************
- * PGRAPH context register lists
- ******************************************************************************/
-
-static const struct nvc0_graph_init
-nve4_grctx_init_icmd_0[] = {
-       { 0x001000,   1, 0x01, 0x00000004 },
-       { 0x000039,   3, 0x01, 0x00000000 },
-       { 0x0000a9,   1, 0x01, 0x0000ffff },
-       { 0x000038,   1, 0x01, 0x0fac6881 },
-       { 0x00003d,   1, 0x01, 0x00000001 },
-       { 0x0000e8,   8, 0x01, 0x00000400 },
-       { 0x000078,   8, 0x01, 0x00000300 },
-       { 0x000050,   1, 0x01, 0x00000011 },
-       { 0x000058,   8, 0x01, 0x00000008 },
-       { 0x000208,   8, 0x01, 0x00000001 },
-       { 0x000081,   1, 0x01, 0x00000001 },
-       { 0x000085,   1, 0x01, 0x00000004 },
-       { 0x000088,   1, 0x01, 0x00000400 },
-       { 0x000090,   1, 0x01, 0x00000300 },
-       { 0x000098,   1, 0x01, 0x00001001 },
-       { 0x0000e3,   1, 0x01, 0x00000001 },
-       { 0x0000da,   1, 0x01, 0x00000001 },
-       { 0x0000f8,   1, 0x01, 0x00000003 },
-       { 0x0000fa,   1, 0x01, 0x00000001 },
-       { 0x00009f,   4, 0x01, 0x0000ffff },
-       { 0x0000b1,   1, 0x01, 0x00000001 },
-       { 0x0000ad,   1, 0x01, 0x0000013e },
-       { 0x0000e1,   1, 0x01, 0x00000010 },
-       { 0x000290,  16, 0x01, 0x00000000 },
-       { 0x0003b0,  16, 0x01, 0x00000000 },
-       { 0x0002a0,  16, 0x01, 0x00000000 },
-       { 0x000420,  16, 0x01, 0x00000000 },
-       { 0x0002b0,  16, 0x01, 0x00000000 },
-       { 0x000430,  16, 0x01, 0x00000000 },
-       { 0x0002c0,  16, 0x01, 0x00000000 },
-       { 0x0004d0,  16, 0x01, 0x00000000 },
-       { 0x000720,  16, 0x01, 0x00000000 },
-       { 0x0008c0,  16, 0x01, 0x00000000 },
-       { 0x000890,  16, 0x01, 0x00000000 },
-       { 0x0008e0,  16, 0x01, 0x00000000 },
-       { 0x0008a0,  16, 0x01, 0x00000000 },
-       { 0x0008f0,  16, 0x01, 0x00000000 },
-       { 0x00094c,   1, 0x01, 0x000000ff },
-       { 0x00094d,   1, 0x01, 0xffffffff },
-       { 0x00094e,   1, 0x01, 0x00000002 },
-       { 0x0002ec,   1, 0x01, 0x00000001 },
-       { 0x000303,   1, 0x01, 0x00000001 },
-       { 0x0002e6,   1, 0x01, 0x00000001 },
-       { 0x000466,   1, 0x01, 0x00000052 },
-       { 0x000301,   1, 0x01, 0x3f800000 },
-       { 0x000304,   1, 0x01, 0x30201000 },
-       { 0x000305,   1, 0x01, 0x70605040 },
-       { 0x000306,   1, 0x01, 0xb8a89888 },
-       { 0x000307,   1, 0x01, 0xf8e8d8c8 },
-       { 0x00030a,   1, 0x01, 0x00ffff00 },
-       { 0x00030b,   1, 0x01, 0x0000001a },
-       { 0x00030c,   1, 0x01, 0x00000001 },
-       { 0x000318,   1, 0x01, 0x00000001 },
-       { 0x000340,   1, 0x01, 0x00000000 },
-       { 0x000375,   1, 0x01, 0x00000001 },
-       { 0x00037d,   1, 0x01, 0x00000006 },
-       { 0x0003a0,   1, 0x01, 0x00000002 },
-       { 0x0003aa,   1, 0x01, 0x00000001 },
-       { 0x0003a9,   1, 0x01, 0x00000001 },
-       { 0x000380,   1, 0x01, 0x00000001 },
-       { 0x000383,   1, 0x01, 0x00000011 },
-       { 0x000360,   1, 0x01, 0x00000040 },
-       { 0x000366,   2, 0x01, 0x00000000 },
-       { 0x000368,   1, 0x01, 0x00000fff },
-       { 0x000370,   2, 0x01, 0x00000000 },
-       { 0x000372,   1, 0x01, 0x000fffff },
-       { 0x00037a,   1, 0x01, 0x00000012 },
-       { 0x000619,   1, 0x01, 0x00000003 },
-       { 0x000811,   1, 0x01, 0x00000003 },
-       { 0x000812,   1, 0x01, 0x00000004 },
-       { 0x000813,   1, 0x01, 0x00000006 },
-       { 0x000814,   1, 0x01, 0x00000008 },
-       { 0x000815,   1, 0x01, 0x0000000b },
-       { 0x000800,   6, 0x01, 0x00000001 },
-       { 0x000632,   1, 0x01, 0x00000001 },
-       { 0x000633,   1, 0x01, 0x00000002 },
-       { 0x000634,   1, 0x01, 0x00000003 },
-       { 0x000635,   1, 0x01, 0x00000004 },
-       { 0x000654,   1, 0x01, 0x3f800000 },
-       { 0x000657,   1, 0x01, 0x3f800000 },
-       { 0x000655,   2, 0x01, 0x3f800000 },
-       { 0x0006cd,   1, 0x01, 0x3f800000 },
-       { 0x0007f5,   1, 0x01, 0x3f800000 },
-       { 0x0007dc,   1, 0x01, 0x39291909 },
-       { 0x0007dd,   1, 0x01, 0x79695949 },
-       { 0x0007de,   1, 0x01, 0xb9a99989 },
-       { 0x0007df,   1, 0x01, 0xf9e9d9c9 },
-       { 0x0007e8,   1, 0x01, 0x00003210 },
-       { 0x0007e9,   1, 0x01, 0x00007654 },
-       { 0x0007ea,   1, 0x01, 0x00000098 },
-       { 0x0007ec,   1, 0x01, 0x39291909 },
-       { 0x0007ed,   1, 0x01, 0x79695949 },
-       { 0x0007ee,   1, 0x01, 0xb9a99989 },
-       { 0x0007ef,   1, 0x01, 0xf9e9d9c9 },
-       { 0x0007f0,   1, 0x01, 0x00003210 },
-       { 0x0007f1,   1, 0x01, 0x00007654 },
-       { 0x0007f2,   1, 0x01, 0x00000098 },
-       { 0x0005a5,   1, 0x01, 0x00000001 },
-       { 0x000980, 128, 0x01, 0x00000000 },
-       { 0x000468,   1, 0x01, 0x00000004 },
-       { 0x00046c,   1, 0x01, 0x00000001 },
-       { 0x000470,  96, 0x01, 0x00000000 },
-       { 0x000510,  16, 0x01, 0x3f800000 },
-       { 0x000520,   1, 0x01, 0x000002b6 },
-       { 0x000529,   1, 0x01, 0x00000001 },
-       { 0x000530,  16, 0x01, 0xffff0000 },
-       { 0x000585,   1, 0x01, 0x0000003f },
-       { 0x000576,   1, 0x01, 0x00000003 },
-       { 0x00057b,   1, 0x01, 0x00000059 },
-       { 0x000586,   1, 0x01, 0x00000040 },
-       { 0x000582,   2, 0x01, 0x00000080 },
-       { 0x0005c2,   1, 0x01, 0x00000001 },
-       { 0x000638,   2, 0x01, 0x00000001 },
-       { 0x00063a,   1, 0x01, 0x00000002 },
-       { 0x00063b,   2, 0x01, 0x00000001 },
-       { 0x00063d,   1, 0x01, 0x00000002 },
-       { 0x00063e,   1, 0x01, 0x00000001 },
-       { 0x0008b8,   8, 0x01, 0x00000001 },
-       { 0x000900,   8, 0x01, 0x00000001 },
-       { 0x000908,   8, 0x01, 0x00000002 },
-       { 0x000910,  16, 0x01, 0x00000001 },
-       { 0x000920,   8, 0x01, 0x00000002 },
-       { 0x000928,   8, 0x01, 0x00000001 },
-       { 0x000648,   9, 0x01, 0x00000001 },
-       { 0x000658,   1, 0x01, 0x0000000f },
-       { 0x0007ff,   1, 0x01, 0x0000000a },
-       { 0x00066a,   1, 0x01, 0x40000000 },
-       { 0x00066b,   1, 0x01, 0x10000000 },
-       { 0x00066c,   2, 0x01, 0xffff0000 },
-       { 0x0007af,   2, 0x01, 0x00000008 },
-       { 0x0007f6,   1, 0x01, 0x00000001 },
-       { 0x0006b2,   1, 0x01, 0x00000055 },
-       { 0x0007ad,   1, 0x01, 0x00000003 },
-       { 0x000937,   1, 0x01, 0x00000001 },
-       { 0x000971,   1, 0x01, 0x00000008 },
-       { 0x000972,   1, 0x01, 0x00000040 },
-       { 0x000973,   1, 0x01, 0x0000012c },
-       { 0x00097c,   1, 0x01, 0x00000040 },
-       { 0x000979,   1, 0x01, 0x00000003 },
-       { 0x000975,   1, 0x01, 0x00000020 },
-       { 0x000976,   1, 0x01, 0x00000001 },
-       { 0x000977,   1, 0x01, 0x00000020 },
-       { 0x000978,   1, 0x01, 0x00000001 },
-       { 0x000957,   1, 0x01, 0x00000003 },
-       { 0x00095e,   1, 0x01, 0x20164010 },
-       { 0x00095f,   1, 0x01, 0x00000020 },
-       { 0x00097d,   1, 0x01, 0x00000020 },
-       { 0x000683,   1, 0x01, 0x00000006 },
-       { 0x000685,   1, 0x01, 0x003fffff },
-       { 0x000687,   1, 0x01, 0x003fffff },
-       { 0x0006a0,   1, 0x01, 0x00000005 },
-       { 0x000840,   1, 0x01, 0x00400008 },
-       { 0x000841,   1, 0x01, 0x08000080 },
-       { 0x000842,   1, 0x01, 0x00400008 },
-       { 0x000843,   1, 0x01, 0x08000080 },
-       { 0x0006aa,   1, 0x01, 0x00000001 },
-       { 0x0006ab,   1, 0x01, 0x00000002 },
-       { 0x0006ac,   1, 0x01, 0x00000080 },
-       { 0x0006ad,   2, 0x01, 0x00000100 },
-       { 0x0006b1,   1, 0x01, 0x00000011 },
-       { 0x0006bb,   1, 0x01, 0x000000cf },
-       { 0x0006ce,   1, 0x01, 0x2a712488 },
-       { 0x000739,   1, 0x01, 0x4085c000 },
-       { 0x00073a,   1, 0x01, 0x00000080 },
-       { 0x000786,   1, 0x01, 0x80000100 },
-       { 0x00073c,   1, 0x01, 0x00010100 },
-       { 0x00073d,   1, 0x01, 0x02800000 },
-       { 0x000787,   1, 0x01, 0x000000cf },
-       { 0x00078c,   1, 0x01, 0x00000008 },
-       { 0x000792,   1, 0x01, 0x00000001 },
-       { 0x000794,   3, 0x01, 0x00000001 },
-       { 0x000797,   1, 0x01, 0x000000cf },
-       { 0x000836,   1, 0x01, 0x00000001 },
-       { 0x00079a,   1, 0x01, 0x00000002 },
-       { 0x000833,   1, 0x01, 0x04444480 },
-       { 0x0007a1,   1, 0x01, 0x00000001 },
-       { 0x0007a3,   3, 0x01, 0x00000001 },
-       { 0x000831,   1, 0x01, 0x00000004 },
-       { 0x000b07,   1, 0x01, 0x00000002 },
-       { 0x000b08,   2, 0x01, 0x00000100 },
-       { 0x000b0a,   1, 0x01, 0x00000001 },
-       { 0x000a04,   1, 0x01, 0x000000ff },
-       { 0x000a0b,   1, 0x01, 0x00000040 },
-       { 0x00097f,   1, 0x01, 0x00000100 },
-       { 0x000a02,   1, 0x01, 0x00000001 },
-       { 0x000809,   1, 0x01, 0x00000007 },
-       { 0x00c221,   1, 0x01, 0x00000040 },
-       { 0x00c1b0,   8, 0x01, 0x0000000f },
-       { 0x00c1b8,   1, 0x01, 0x0fac6881 },
-       { 0x00c1b9,   1, 0x01, 0x00fac688 },
-       { 0x00c401,   1, 0x01, 0x00000001 },
-       { 0x00c402,   1, 0x01, 0x00010001 },
-       { 0x00c403,   2, 0x01, 0x00000001 },
-       { 0x00c40e,   1, 0x01, 0x00000020 },
-       { 0x00c500,   1, 0x01, 0x00000003 },
-       { 0x01e100,   1, 0x01, 0x00000001 },
-       { 0x001000,   1, 0x01, 0x00000002 },
-       { 0x0006aa,   1, 0x01, 0x00000001 },
-       { 0x0006ad,   2, 0x01, 0x00000100 },
-       { 0x0006b1,   1, 0x01, 0x00000011 },
-       { 0x00078c,   1, 0x01, 0x00000008 },
-       { 0x000792,   1, 0x01, 0x00000001 },
-       { 0x000794,   3, 0x01, 0x00000001 },
-       { 0x000797,   1, 0x01, 0x000000cf },
-       { 0x00079a,   1, 0x01, 0x00000002 },
-       { 0x000833,   1, 0x01, 0x04444480 },
-       { 0x0007a1,   1, 0x01, 0x00000001 },
-       { 0x0007a3,   3, 0x01, 0x00000001 },
-       { 0x000831,   1, 0x01, 0x00000004 },
-       { 0x01e100,   1, 0x01, 0x00000001 },
-       { 0x001000,   1, 0x01, 0x00000008 },
-       { 0x000039,   3, 0x01, 0x00000000 },
-       { 0x000380,   1, 0x01, 0x00000001 },
-       { 0x000366,   2, 0x01, 0x00000000 },
-       { 0x000368,   1, 0x01, 0x00000fff },
-       { 0x000370,   2, 0x01, 0x00000000 },
-       { 0x000372,   1, 0x01, 0x000fffff },
-       { 0x000813,   1, 0x01, 0x00000006 },
-       { 0x000814,   1, 0x01, 0x00000008 },
-       { 0x000957,   1, 0x01, 0x00000003 },
-       { 0x000b07,   1, 0x01, 0x00000002 },
-       { 0x000b08,   2, 0x01, 0x00000100 },
-       { 0x000b0a,   1, 0x01, 0x00000001 },
-       { 0x000a04,   1, 0x01, 0x000000ff },
-       { 0x00097f,   1, 0x01, 0x00000100 },
-       { 0x000a02,   1, 0x01, 0x00000001 },
-       { 0x000809,   1, 0x01, 0x00000007 },
-       { 0x00c221,   1, 0x01, 0x00000040 },
-       { 0x00c401,   1, 0x01, 0x00000001 },
-       { 0x00c402,   1, 0x01, 0x00010001 },
-       { 0x00c403,   2, 0x01, 0x00000001 },
-       { 0x00c40e,   1, 0x01, 0x00000020 },
-       { 0x00c500,   1, 0x01, 0x00000003 },
-       { 0x01e100,   1, 0x01, 0x00000001 },
-       { 0x001000,   1, 0x01, 0x00000001 },
-       { 0x000b07,   1, 0x01, 0x00000002 },
-       { 0x000b08,   2, 0x01, 0x00000100 },
-       { 0x000b0a,   1, 0x01, 0x00000001 },
-       { 0x01e100,   1, 0x01, 0x00000001 },
-       {}
-};
-
-const struct nvc0_graph_pack
-nve4_grctx_pack_icmd[] = {
-       { nve4_grctx_init_icmd_0 },
-       {}
-};
-
-const struct nvc0_graph_init
-nve4_grctx_init_a097_0[] = {
-       { 0x000800,   8, 0x40, 0x00000000 },
-       { 0x000804,   8, 0x40, 0x00000000 },
-       { 0x000808,   8, 0x40, 0x00000400 },
-       { 0x00080c,   8, 0x40, 0x00000300 },
-       { 0x000810,   1, 0x04, 0x000000cf },
-       { 0x000850,   7, 0x40, 0x00000000 },
-       { 0x000814,   8, 0x40, 0x00000040 },
-       { 0x000818,   8, 0x40, 0x00000001 },
-       { 0x00081c,   8, 0x40, 0x00000000 },
-       { 0x000820,   8, 0x40, 0x00000000 },
-       { 0x001c00,  16, 0x10, 0x00000000 },
-       { 0x001c04,  16, 0x10, 0x00000000 },
-       { 0x001c08,  16, 0x10, 0x00000000 },
-       { 0x001c0c,  16, 0x10, 0x00000000 },
-       { 0x001d00,  16, 0x10, 0x00000000 },
-       { 0x001d04,  16, 0x10, 0x00000000 },
-       { 0x001d08,  16, 0x10, 0x00000000 },
-       { 0x001d0c,  16, 0x10, 0x00000000 },
-       { 0x001f00,  16, 0x08, 0x00000000 },
-       { 0x001f04,  16, 0x08, 0x00000000 },
-       { 0x001f80,  16, 0x08, 0x00000000 },
-       { 0x001f84,  16, 0x08, 0x00000000 },
-       { 0x002000,   1, 0x04, 0x00000000 },
-       { 0x002040,   1, 0x04, 0x00000011 },
-       { 0x002080,   1, 0x04, 0x00000020 },
-       { 0x0020c0,   1, 0x04, 0x00000030 },
-       { 0x002100,   1, 0x04, 0x00000040 },
-       { 0x002140,   1, 0x04, 0x00000051 },
-       { 0x00200c,   6, 0x40, 0x00000001 },
-       { 0x002010,   1, 0x04, 0x00000000 },
-       { 0x002050,   1, 0x04, 0x00000000 },
-       { 0x002090,   1, 0x04, 0x00000001 },
-       { 0x0020d0,   1, 0x04, 0x00000002 },
-       { 0x002110,   1, 0x04, 0x00000003 },
-       { 0x002150,   1, 0x04, 0x00000004 },
-       { 0x000380,   4, 0x20, 0x00000000 },
-       { 0x000384,   4, 0x20, 0x00000000 },
-       { 0x000388,   4, 0x20, 0x00000000 },
-       { 0x00038c,   4, 0x20, 0x00000000 },
-       { 0x000700,   4, 0x10, 0x00000000 },
-       { 0x000704,   4, 0x10, 0x00000000 },
-       { 0x000708,   4, 0x10, 0x00000000 },
-       { 0x002800, 128, 0x04, 0x00000000 },
-       { 0x000a00,  16, 0x20, 0x00000000 },
-       { 0x000a04,  16, 0x20, 0x00000000 },
-       { 0x000a08,  16, 0x20, 0x00000000 },
-       { 0x000a0c,  16, 0x20, 0x00000000 },
-       { 0x000a10,  16, 0x20, 0x00000000 },
-       { 0x000a14,  16, 0x20, 0x00000000 },
-       { 0x000c00,  16, 0x10, 0x00000000 },
-       { 0x000c04,  16, 0x10, 0x00000000 },
-       { 0x000c08,  16, 0x10, 0x00000000 },
-       { 0x000c0c,  16, 0x10, 0x3f800000 },
-       { 0x000d00,   8, 0x08, 0xffff0000 },
-       { 0x000d04,   8, 0x08, 0xffff0000 },
-       { 0x000e00,  16, 0x10, 0x00000000 },
-       { 0x000e04,  16, 0x10, 0xffff0000 },
-       { 0x000e08,  16, 0x10, 0xffff0000 },
-       { 0x000d40,   4, 0x08, 0x00000000 },
-       { 0x000d44,   4, 0x08, 0x00000000 },
-       { 0x001e00,   8, 0x20, 0x00000001 },
-       { 0x001e04,   8, 0x20, 0x00000001 },
-       { 0x001e08,   8, 0x20, 0x00000002 },
-       { 0x001e0c,   8, 0x20, 0x00000001 },
-       { 0x001e10,   8, 0x20, 0x00000001 },
-       { 0x001e14,   8, 0x20, 0x00000002 },
-       { 0x001e18,   8, 0x20, 0x00000001 },
-       { 0x003400, 128, 0x04, 0x00000000 },
-       { 0x00030c,   1, 0x04, 0x00000001 },
-       { 0x001944,   1, 0x04, 0x00000000 },
-       { 0x001514,   1, 0x04, 0x00000000 },
-       { 0x000d68,   1, 0x04, 0x0000ffff },
-       { 0x00121c,   1, 0x04, 0x0fac6881 },
-       { 0x000fac,   1, 0x04, 0x00000001 },
-       { 0x001538,   1, 0x04, 0x00000001 },
-       { 0x000fe0,   2, 0x04, 0x00000000 },
-       { 0x000fe8,   1, 0x04, 0x00000014 },
-       { 0x000fec,   1, 0x04, 0x00000040 },
-       { 0x000ff0,   1, 0x04, 0x00000000 },
-       { 0x00179c,   1, 0x04, 0x00000000 },
-       { 0x001228,   1, 0x04, 0x00000400 },
-       { 0x00122c,   1, 0x04, 0x00000300 },
-       { 0x001230,   1, 0x04, 0x00010001 },
-       { 0x0007f8,   1, 0x04, 0x00000000 },
-       { 0x0015b4,   1, 0x04, 0x00000001 },
-       { 0x0015cc,   1, 0x04, 0x00000000 },
-       { 0x001534,   1, 0x04, 0x00000000 },
-       { 0x000fb0,   1, 0x04, 0x00000000 },
-       { 0x0015d0,   1, 0x04, 0x00000000 },
-       { 0x00153c,   1, 0x04, 0x00000000 },
-       { 0x0016b4,   1, 0x04, 0x00000003 },
-       { 0x000fbc,   4, 0x04, 0x0000ffff },
-       { 0x000df8,   2, 0x04, 0x00000000 },
-       { 0x001948,   1, 0x04, 0x00000000 },
-       { 0x001970,   1, 0x04, 0x00000001 },
-       { 0x00161c,   1, 0x04, 0x000009f0 },
-       { 0x000dcc,   1, 0x04, 0x00000010 },
-       { 0x00163c,   1, 0x04, 0x00000000 },
-       { 0x0015e4,   1, 0x04, 0x00000000 },
-       { 0x001160,  32, 0x04, 0x25e00040 },
-       { 0x001880,  32, 0x04, 0x00000000 },
-       { 0x000f84,   2, 0x04, 0x00000000 },
-       { 0x0017c8,   2, 0x04, 0x00000000 },
-       { 0x0017d0,   1, 0x04, 0x000000ff },
-       { 0x0017d4,   1, 0x04, 0xffffffff },
-       { 0x0017d8,   1, 0x04, 0x00000002 },
-       { 0x0017dc,   1, 0x04, 0x00000000 },
-       { 0x0015f4,   2, 0x04, 0x00000000 },
-       { 0x001434,   2, 0x04, 0x00000000 },
-       { 0x000d74,   1, 0x04, 0x00000000 },
-       { 0x000dec,   1, 0x04, 0x00000001 },
-       { 0x0013a4,   1, 0x04, 0x00000000 },
-       { 0x001318,   1, 0x04, 0x00000001 },
-       { 0x001644,   1, 0x04, 0x00000000 },
-       { 0x000748,   1, 0x04, 0x00000000 },
-       { 0x000de8,   1, 0x04, 0x00000000 },
-       { 0x001648,   1, 0x04, 0x00000000 },
-       { 0x0012a4,   1, 0x04, 0x00000000 },
-       { 0x001120,   4, 0x04, 0x00000000 },
-       { 0x001118,   1, 0x04, 0x00000000 },
-       { 0x00164c,   1, 0x04, 0x00000000 },
-       { 0x001658,   1, 0x04, 0x00000000 },
-       { 0x001910,   1, 0x04, 0x00000290 },
-       { 0x001518,   1, 0x04, 0x00000000 },
-       { 0x00165c,   1, 0x04, 0x00000001 },
-       { 0x001520,   1, 0x04, 0x00000000 },
-       { 0x001604,   1, 0x04, 0x00000000 },
-       { 0x001570,   1, 0x04, 0x00000000 },
-       { 0x0013b0,   2, 0x04, 0x3f800000 },
-       { 0x00020c,   1, 0x04, 0x00000000 },
-       { 0x001670,   1, 0x04, 0x30201000 },
-       { 0x001674,   1, 0x04, 0x70605040 },
-       { 0x001678,   1, 0x04, 0xb8a89888 },
-       { 0x00167c,   1, 0x04, 0xf8e8d8c8 },
-       { 0x00166c,   1, 0x04, 0x00000000 },
-       { 0x001680,   1, 0x04, 0x00ffff00 },
-       { 0x0012d0,   1, 0x04, 0x00000003 },
-       { 0x0012d4,   1, 0x04, 0x00000002 },
-       { 0x001684,   2, 0x04, 0x00000000 },
-       { 0x000dac,   2, 0x04, 0x00001b02 },
-       { 0x000db4,   1, 0x04, 0x00000000 },
-       { 0x00168c,   1, 0x04, 0x00000000 },
-       { 0x0015bc,   1, 0x04, 0x00000000 },
-       { 0x00156c,   1, 0x04, 0x00000000 },
-       { 0x00187c,   1, 0x04, 0x00000000 },
-       { 0x001110,   1, 0x04, 0x00000001 },
-       { 0x000dc0,   3, 0x04, 0x00000000 },
-       { 0x001234,   1, 0x04, 0x00000000 },
-       { 0x001690,   1, 0x04, 0x00000000 },
-       { 0x0012ac,   1, 0x04, 0x00000001 },
-       { 0x000790,   5, 0x04, 0x00000000 },
-       { 0x00077c,   1, 0x04, 0x00000000 },
-       { 0x001000,   1, 0x04, 0x00000010 },
-       { 0x0010fc,   1, 0x04, 0x00000000 },
-       { 0x001290,   1, 0x04, 0x00000000 },
-       { 0x000218,   1, 0x04, 0x00000010 },
-       { 0x0012d8,   1, 0x04, 0x00000000 },
-       { 0x0012dc,   1, 0x04, 0x00000010 },
-       { 0x000d94,   1, 0x04, 0x00000001 },
-       { 0x00155c,   2, 0x04, 0x00000000 },
-       { 0x001564,   1, 0x04, 0x00000fff },
-       { 0x001574,   2, 0x04, 0x00000000 },
-       { 0x00157c,   1, 0x04, 0x000fffff },
-       { 0x001354,   1, 0x04, 0x00000000 },
-       { 0x001610,   1, 0x04, 0x00000012 },
-       { 0x001608,   2, 0x04, 0x00000000 },
-       { 0x00260c,   1, 0x04, 0x00000000 },
-       { 0x0007ac,   1, 0x04, 0x00000000 },
-       { 0x00162c,   1, 0x04, 0x00000003 },
-       { 0x000210,   1, 0x04, 0x00000000 },
-       { 0x000320,   1, 0x04, 0x00000000 },
-       { 0x000324,   6, 0x04, 0x3f800000 },
-       { 0x000750,   1, 0x04, 0x00000000 },
-       { 0x000760,   1, 0x04, 0x39291909 },
-       { 0x000764,   1, 0x04, 0x79695949 },
-       { 0x000768,   1, 0x04, 0xb9a99989 },
-       { 0x00076c,   1, 0x04, 0xf9e9d9c9 },
-       { 0x000770,   1, 0x04, 0x30201000 },
-       { 0x000774,   1, 0x04, 0x70605040 },
-       { 0x000778,   1, 0x04, 0x00009080 },
-       { 0x000780,   1, 0x04, 0x39291909 },
-       { 0x000784,   1, 0x04, 0x79695949 },
-       { 0x000788,   1, 0x04, 0xb9a99989 },
-       { 0x00078c,   1, 0x04, 0xf9e9d9c9 },
-       { 0x0007d0,   1, 0x04, 0x30201000 },
-       { 0x0007d4,   1, 0x04, 0x70605040 },
-       { 0x0007d8,   1, 0x04, 0x00009080 },
-       { 0x00037c,   1, 0x04, 0x00000001 },
-       { 0x000740,   2, 0x04, 0x00000000 },
-       { 0x002600,   1, 0x04, 0x00000000 },
-       { 0x001918,   1, 0x04, 0x00000000 },
-       { 0x00191c,   1, 0x04, 0x00000900 },
-       { 0x001920,   1, 0x04, 0x00000405 },
-       { 0x001308,   1, 0x04, 0x00000001 },
-       { 0x001924,   1, 0x04, 0x00000000 },
-       { 0x0013ac,   1, 0x04, 0x00000000 },
-       { 0x00192c,   1, 0x04, 0x00000001 },
-       { 0x00193c,   1, 0x04, 0x00002c1c },
-       { 0x000d7c,   1, 0x04, 0x00000000 },
-       { 0x000f8c,   1, 0x04, 0x00000000 },
-       { 0x0002c0,   1, 0x04, 0x00000001 },
-       { 0x001510,   1, 0x04, 0x00000000 },
-       { 0x001940,   1, 0x04, 0x00000000 },
-       { 0x000ff4,   2, 0x04, 0x00000000 },
-       { 0x00194c,   2, 0x04, 0x00000000 },
-       { 0x001968,   1, 0x04, 0x00000000 },
-       { 0x001590,   1, 0x04, 0x0000003f },
-       { 0x0007e8,   4, 0x04, 0x00000000 },
-       { 0x00196c,   1, 0x04, 0x00000011 },
-       { 0x0002e4,   1, 0x04, 0x0000b001 },
-       { 0x00036c,   2, 0x04, 0x00000000 },
-       { 0x00197c,   1, 0x04, 0x00000000 },
-       { 0x000fcc,   2, 0x04, 0x00000000 },
-       { 0x0002d8,   1, 0x04, 0x00000040 },
-       { 0x001980,   1, 0x04, 0x00000080 },
-       { 0x001504,   1, 0x04, 0x00000080 },
-       { 0x001984,   1, 0x04, 0x00000000 },
-       { 0x000300,   1, 0x04, 0x00000001 },
-       { 0x0013a8,   1, 0x04, 0x00000000 },
-       { 0x0012ec,   1, 0x04, 0x00000000 },
-       { 0x001310,   1, 0x04, 0x00000000 },
-       { 0x001314,   1, 0x04, 0x00000001 },
-       { 0x001380,   1, 0x04, 0x00000000 },
-       { 0x001384,   4, 0x04, 0x00000001 },
-       { 0x001394,   1, 0x04, 0x00000000 },
-       { 0x00139c,   1, 0x04, 0x00000000 },
-       { 0x001398,   1, 0x04, 0x00000000 },
-       { 0x001594,   1, 0x04, 0x00000000 },
-       { 0x001598,   4, 0x04, 0x00000001 },
-       { 0x000f54,   3, 0x04, 0x00000000 },
-       { 0x0019bc,   1, 0x04, 0x00000000 },
-       { 0x000f9c,   2, 0x04, 0x00000000 },
-       { 0x0012cc,   1, 0x04, 0x00000000 },
-       { 0x0012e8,   1, 0x04, 0x00000000 },
-       { 0x00130c,   1, 0x04, 0x00000001 },
-       { 0x001360,   8, 0x04, 0x00000000 },
-       { 0x00133c,   2, 0x04, 0x00000001 },
-       { 0x001344,   1, 0x04, 0x00000002 },
-       { 0x001348,   2, 0x04, 0x00000001 },
-       { 0x001350,   1, 0x04, 0x00000002 },
-       { 0x001358,   1, 0x04, 0x00000001 },
-       { 0x0012e4,   1, 0x04, 0x00000000 },
-       { 0x00131c,   4, 0x04, 0x00000000 },
-       { 0x0019c0,   1, 0x04, 0x00000000 },
-       { 0x001140,   1, 0x04, 0x00000000 },
-       { 0x0019c4,   1, 0x04, 0x00000000 },
-       { 0x0019c8,   1, 0x04, 0x00001500 },
-       { 0x00135c,   1, 0x04, 0x00000000 },
-       { 0x000f90,   1, 0x04, 0x00000000 },
-       { 0x0019e0,   8, 0x04, 0x00000001 },
-       { 0x0019cc,   1, 0x04, 0x00000001 },
-       { 0x0015b8,   1, 0x04, 0x00000000 },
-       { 0x001a00,   1, 0x04, 0x00001111 },
-       { 0x001a04,   7, 0x04, 0x00000000 },
-       { 0x000d6c,   2, 0x04, 0xffff0000 },
-       { 0x0010f8,   1, 0x04, 0x00001010 },
-       { 0x000d80,   5, 0x04, 0x00000000 },
-       { 0x000da0,   1, 0x04, 0x00000000 },
-       { 0x0007a4,   2, 0x04, 0x00000000 },
-       { 0x001508,   1, 0x04, 0x80000000 },
-       { 0x00150c,   1, 0x04, 0x40000000 },
-       { 0x001668,   1, 0x04, 0x00000000 },
-       { 0x000318,   2, 0x04, 0x00000008 },
-       { 0x000d9c,   1, 0x04, 0x00000001 },
-       { 0x000374,   1, 0x04, 0x00000000 },
-       { 0x000378,   1, 0x04, 0x00000020 },
-       { 0x0007dc,   1, 0x04, 0x00000000 },
-       { 0x00074c,   1, 0x04, 0x00000055 },
-       { 0x001420,   1, 0x04, 0x00000003 },
-       { 0x0017bc,   2, 0x04, 0x00000000 },
-       { 0x0017c4,   1, 0x04, 0x00000001 },
-       { 0x001008,   1, 0x04, 0x00000008 },
-       { 0x00100c,   1, 0x04, 0x00000040 },
-       { 0x001010,   1, 0x04, 0x0000012c },
-       { 0x000d60,   1, 0x04, 0x00000040 },
-       { 0x00075c,   1, 0x04, 0x00000003 },
-       { 0x001018,   1, 0x04, 0x00000020 },
-       { 0x00101c,   1, 0x04, 0x00000001 },
-       { 0x001020,   1, 0x04, 0x00000020 },
-       { 0x001024,   1, 0x04, 0x00000001 },
-       { 0x001444,   3, 0x04, 0x00000000 },
-       { 0x000360,   1, 0x04, 0x20164010 },
-       { 0x000364,   1, 0x04, 0x00000020 },
-       { 0x000368,   1, 0x04, 0x00000000 },
-       { 0x000de4,   1, 0x04, 0x00000000 },
-       { 0x000204,   1, 0x04, 0x00000006 },
-       { 0x000208,   1, 0x04, 0x00000000 },
-       { 0x0002cc,   2, 0x04, 0x003fffff },
-       { 0x001220,   1, 0x04, 0x00000005 },
-       { 0x000fdc,   1, 0x04, 0x00000000 },
-       { 0x000f98,   1, 0x04, 0x00400008 },
-       { 0x001284,   1, 0x04, 0x08000080 },
-       { 0x001450,   1, 0x04, 0x00400008 },
-       { 0x001454,   1, 0x04, 0x08000080 },
-       { 0x000214,   1, 0x04, 0x00000000 },
-       {}
-};
-
-static const struct nvc0_graph_pack
-nve4_grctx_pack_mthd[] = {
-       { nve4_grctx_init_a097_0, 0xa097 },
-       { nvc0_grctx_init_902d_0, 0x902d },
-       {}
-};
-
-static const struct nvc0_graph_init
-nve4_grctx_init_fe_0[] = {
-       { 0x404010,   5, 0x04, 0x00000000 },
-       { 0x404024,   1, 0x04, 0x0000e000 },
-       { 0x404028,   1, 0x04, 0x00000000 },
-       { 0x4040a8,   8, 0x04, 0x00000000 },
-       { 0x4040c8,   1, 0x04, 0xf800008f },
-       { 0x4040d0,   6, 0x04, 0x00000000 },
-       { 0x4040e8,   1, 0x04, 0x00001000 },
-       { 0x4040f8,   1, 0x04, 0x00000000 },
-       { 0x404130,   2, 0x04, 0x00000000 },
-       { 0x404138,   1, 0x04, 0x20000040 },
-       { 0x404150,   1, 0x04, 0x0000002e },
-       { 0x404154,   1, 0x04, 0x00000400 },
-       { 0x404158,   1, 0x04, 0x00000200 },
-       { 0x404164,   1, 0x04, 0x00000055 },
-       { 0x4041a0,   4, 0x04, 0x00000000 },
-       { 0x404200,   4, 0x04, 0x00000000 },
-       {}
-};
-
-const struct nvc0_graph_init
-nve4_grctx_init_memfmt_0[] = {
-       { 0x404604,   1, 0x04, 0x00000014 },
-       { 0x404608,   1, 0x04, 0x00000000 },
-       { 0x40460c,   1, 0x04, 0x00003fff },
-       { 0x404610,   1, 0x04, 0x00000100 },
-       { 0x404618,   4, 0x04, 0x00000000 },
-       { 0x40462c,   2, 0x04, 0x00000000 },
-       { 0x404640,   1, 0x04, 0x00000000 },
-       { 0x404654,   1, 0x04, 0x00000000 },
-       { 0x404660,   1, 0x04, 0x00000000 },
-       { 0x404678,   1, 0x04, 0x00000000 },
-       { 0x40467c,   1, 0x04, 0x00000002 },
-       { 0x404680,   8, 0x04, 0x00000000 },
-       { 0x4046a0,   1, 0x04, 0x007f0080 },
-       { 0x4046a4,   8, 0x04, 0x00000000 },
-       { 0x4046c8,   3, 0x04, 0x00000000 },
-       { 0x404700,   3, 0x04, 0x00000000 },
-       { 0x404718,   7, 0x04, 0x00000000 },
-       { 0x404734,   1, 0x04, 0x00000100 },
-       { 0x404738,   2, 0x04, 0x00000000 },
-       { 0x404744,   2, 0x04, 0x00000000 },
-       { 0x404754,   1, 0x04, 0x00000000 },
-       {}
-};
-
-const struct nvc0_graph_init
-nve4_grctx_init_ds_0[] = {
-       { 0x405800,   1, 0x04, 0x0f8000bf },
-       { 0x405830,   1, 0x04, 0x02180648 },
-       { 0x405834,   1, 0x04, 0x08000000 },
-       { 0x405838,   1, 0x04, 0x00000000 },
-       { 0x405854,   1, 0x04, 0x00000000 },
-       { 0x405870,   4, 0x04, 0x00000001 },
-       { 0x405a00,   2, 0x04, 0x00000000 },
-       { 0x405a18,   1, 0x04, 0x00000000 },
-       {}
-};
-
-static const struct nvc0_graph_init
-nve4_grctx_init_cwd_0[] = {
-       { 0x405b00,   1, 0x04, 0x00000000 },
-       { 0x405b10,   1, 0x04, 0x00001000 },
-       {}
-};
-
-static const struct nvc0_graph_init
-nve4_grctx_init_pd_0[] = {
-       { 0x406020,   1, 0x04, 0x004103c1 },
-       { 0x406028,   4, 0x04, 0x00000001 },
-       { 0x4064a8,   1, 0x04, 0x00000000 },
-       { 0x4064ac,   1, 0x04, 0x00003fff },
-       { 0x4064b4,   2, 0x04, 0x00000000 },
-       { 0x4064c0,   1, 0x04, 0x801a00f0 },
-       { 0x4064c4,   1, 0x04, 0x0192ffff },
-       { 0x4064c8,   1, 0x04, 0x01800600 },
-       { 0x4064cc,   9, 0x04, 0x00000000 },
-       { 0x4064fc,   1, 0x04, 0x0000022a },
-       {}
-};
-
-static const struct nvc0_graph_init
-nve4_grctx_init_sked_0[] = {
-       { 0x407040,   1, 0x04, 0x00000000 },
-       {}
-};
-
-const struct nvc0_graph_init
-nve4_grctx_init_scc_0[] = {
-       { 0x408000,   2, 0x04, 0x00000000 },
-       { 0x408008,   1, 0x04, 0x00000030 },
-       { 0x40800c,   2, 0x04, 0x00000000 },
-       { 0x408014,   1, 0x04, 0x00000069 },
-       { 0x408018,   1, 0x04, 0xe100e100 },
-       { 0x408064,   1, 0x04, 0x00000000 },
-       {}
-};
-
-static const struct nvc0_graph_init
-nve4_grctx_init_be_0[] = {
-       { 0x408800,   1, 0x04, 0x02802a3c },
-       { 0x408804,   1, 0x04, 0x00000040 },
-       { 0x408808,   1, 0x04, 0x1043e005 },
-       { 0x408840,   1, 0x04, 0x0000000b },
-       { 0x408900,   1, 0x04, 0x3080b801 },
-       { 0x408904,   1, 0x04, 0x62000001 },
-       { 0x408908,   1, 0x04, 0x00c8102f },
-       { 0x408980,   1, 0x04, 0x0000011d },
-       {}
-};
-
-const struct nvc0_graph_pack
-nve4_grctx_pack_hub[] = {
-       { nvc0_grctx_init_main_0 },
-       { nve4_grctx_init_fe_0 },
-       { nvc0_grctx_init_pri_0 },
-       { nve4_grctx_init_memfmt_0 },
-       { nve4_grctx_init_ds_0 },
-       { nve4_grctx_init_cwd_0 },
-       { nve4_grctx_init_pd_0 },
-       { nve4_grctx_init_sked_0 },
-       { nvc0_grctx_init_rstr2d_0 },
-       { nve4_grctx_init_scc_0 },
-       { nve4_grctx_init_be_0 },
-       {}
-};
-
-static const struct nvc0_graph_init
-nve4_grctx_init_setup_0[] = {
-       { 0x418800,   1, 0x04, 0x7006860a },
-       { 0x418808,   3, 0x04, 0x00000000 },
-       { 0x418828,   1, 0x04, 0x00000044 },
-       { 0x418830,   1, 0x04, 0x10000001 },
-       { 0x4188d8,   1, 0x04, 0x00000008 },
-       { 0x4188e0,   1, 0x04, 0x01000000 },
-       { 0x4188e8,   5, 0x04, 0x00000000 },
-       { 0x4188fc,   1, 0x04, 0x20100018 },
-       {}
-};
-
-const struct nvc0_graph_init
-nve4_grctx_init_gpm_0[] = {
-       { 0x418c08,   1, 0x04, 0x00000001 },
-       { 0x418c10,   8, 0x04, 0x00000000 },
-       { 0x418c40,   1, 0x04, 0xffffffff },
-       { 0x418c6c,   1, 0x04, 0x00000001 },
-       { 0x418c80,   1, 0x04, 0x20200004 },
-       { 0x418c8c,   1, 0x04, 0x00000001 },
-       {}
-};
-
-const struct nvc0_graph_pack
-nve4_grctx_pack_gpc[] = {
-       { nvc0_grctx_init_gpc_unk_0 },
-       { nvd9_grctx_init_prop_0 },
-       { nvd9_grctx_init_gpc_unk_1 },
-       { nve4_grctx_init_setup_0 },
-       { nvc0_grctx_init_zcull_0 },
-       { nvd9_grctx_init_crstr_0 },
-       { nve4_grctx_init_gpm_0 },
-       { nvc0_grctx_init_gcc_0 },
-       {}
-};
-
-static const struct nvc0_graph_init
-nve4_grctx_init_tex_0[] = {
-       { 0x419a00,   1, 0x04, 0x000000f0 },
-       { 0x419a04,   1, 0x04, 0x00000001 },
-       { 0x419a08,   1, 0x04, 0x00000021 },
-       { 0x419a0c,   1, 0x04, 0x00020000 },
-       { 0x419a10,   1, 0x04, 0x00000000 },
-       { 0x419a14,   1, 0x04, 0x00000200 },
-       { 0x419a1c,   1, 0x04, 0x0000c000 },
-       { 0x419a20,   1, 0x04, 0x00000800 },
-       { 0x419a30,   1, 0x04, 0x00000001 },
-       { 0x419ac4,   1, 0x04, 0x0037f440 },
-       {}
-};
-
-static const struct nvc0_graph_init
-nve4_grctx_init_mpc_0[] = {
-       { 0x419c00,   1, 0x04, 0x0000000a },
-       { 0x419c04,   1, 0x04, 0x80000006 },
-       { 0x419c08,   1, 0x04, 0x00000002 },
-       { 0x419c20,   1, 0x04, 0x00000000 },
-       { 0x419c24,   1, 0x04, 0x00084210 },
-       { 0x419c28,   1, 0x04, 0x3efbefbe },
-       {}
-};
-
-static const struct nvc0_graph_init
-nve4_grctx_init_l1c_0[] = {
-       { 0x419ce8,   1, 0x04, 0x00000000 },
-       { 0x419cf4,   1, 0x04, 0x00003203 },
-       {}
-};
-
-static const struct nvc0_graph_init
-nve4_grctx_init_sm_0[] = {
-       { 0x419e04,   3, 0x04, 0x00000000 },
-       { 0x419e10,   1, 0x04, 0x00000402 },
-       { 0x419e44,   1, 0x04, 0x0013eff2 },
-       { 0x419e48,   1, 0x04, 0x00000000 },
-       { 0x419e4c,   1, 0x04, 0x0000007f },
-       { 0x419e50,  19, 0x04, 0x00000000 },
-       { 0x419eac,   1, 0x04, 0x00001f8f },
-       { 0x419eb0,   1, 0x04, 0x00000d3f },
-       { 0x419ec8,   1, 0x04, 0x0001304f },
-       { 0x419f30,   8, 0x04, 0x00000000 },
-       { 0x419f58,   1, 0x04, 0x00000000 },
-       { 0x419f70,   1, 0x04, 0x00000000 },
-       { 0x419f78,   1, 0x04, 0x0000000b },
-       { 0x419f7c,   1, 0x04, 0x0000027c },
-       {}
-};
-
-const struct nvc0_graph_pack
-nve4_grctx_pack_tpc[] = {
-       { nvd7_grctx_init_pe_0 },
-       { nve4_grctx_init_tex_0 },
-       { nve4_grctx_init_mpc_0 },
-       { nve4_grctx_init_l1c_0 },
-       { nve4_grctx_init_sm_0 },
-       {}
-};
-
-const struct nvc0_graph_init
-nve4_grctx_init_pes_0[] = {
-       { 0x41be24,   1, 0x04, 0x00000006 },
-       {}
-};
-
-static const struct nvc0_graph_init
-nve4_grctx_init_cbm_0[] = {
-       { 0x41bec0,   1, 0x04, 0x12180000 },
-       { 0x41bec4,   1, 0x04, 0x00037f7f },
-       { 0x41bee4,   1, 0x04, 0x06480430 },
-       {}
-};
-
-const struct nvc0_graph_pack
-nve4_grctx_pack_ppc[] = {
-       { nve4_grctx_init_pes_0 },
-       { nve4_grctx_init_cbm_0 },
-       { nvd7_grctx_init_wwdx_0 },
-       {}
-};
-
-/*******************************************************************************
- * PGRAPH context implementation
- ******************************************************************************/
-
-void
-nve4_grctx_generate_bundle(struct nvc0_grctx *info)
-{
-       const struct nvc0_grctx_oclass *impl = nvc0_grctx_impl(info->priv);
-       const u32 state_limit = min(impl->bundle_min_gpm_fifo_depth,
-                                   impl->bundle_size / 0x20);
-       const u32 token_limit = impl->bundle_token_limit;
-       const u32 access = NV_MEM_ACCESS_RW | NV_MEM_ACCESS_SYS;
-       const int s = 8;
-       const int b = mmio_vram(info, impl->bundle_size, (1 << s), access);
-       mmio_refn(info, 0x408004, 0x00000000, s, b);
-       mmio_refn(info, 0x408008, 0x80000000 | (impl->bundle_size >> s), 0, b);
-       mmio_refn(info, 0x418808, 0x00000000, s, b);
-       mmio_refn(info, 0x41880c, 0x80000000 | (impl->bundle_size >> s), 0, b);
-       mmio_wr32(info, 0x4064c8, (state_limit << 16) | token_limit);
-}
-
-void
-nve4_grctx_generate_pagepool(struct nvc0_grctx *info)
-{
-       const struct nvc0_grctx_oclass *impl = nvc0_grctx_impl(info->priv);
-       const u32 access = NV_MEM_ACCESS_RW | NV_MEM_ACCESS_SYS;
-       const int s = 8;
-       const int b = mmio_vram(info, impl->pagepool_size, (1 << s), access);
-       mmio_refn(info, 0x40800c, 0x00000000, s, b);
-       mmio_wr32(info, 0x408010, 0x80000000);
-       mmio_refn(info, 0x419004, 0x00000000, s, b);
-       mmio_wr32(info, 0x419008, 0x00000000);
-       mmio_wr32(info, 0x4064cc, 0x80000000);
-}
-
-void
-nve4_grctx_generate_unkn(struct nvc0_graph_priv *priv)
-{
-       nv_mask(priv, 0x418c6c, 0x00000001, 0x00000001);
-       nv_mask(priv, 0x41980c, 0x00000010, 0x00000010);
-       nv_mask(priv, 0x41be08, 0x00000004, 0x00000004);
-       nv_mask(priv, 0x4064c0, 0x80000000, 0x80000000);
-       nv_mask(priv, 0x405800, 0x08000000, 0x08000000);
-       nv_mask(priv, 0x419c00, 0x00000008, 0x00000008);
-}
-
-void
-nve4_grctx_generate_r418bb8(struct nvc0_graph_priv *priv)
-{
-       u32 data[6] = {}, data2[2] = {};
-       u8  tpcnr[GPC_MAX];
-       u8  shift, ntpcv;
-       int gpc, tpc, i;
-
-       /* calculate first set of magics */
-       memcpy(tpcnr, priv->tpc_nr, sizeof(priv->tpc_nr));
-
-       gpc = -1;
-       for (tpc = 0; tpc < priv->tpc_total; tpc++) {
-               do {
-                       gpc = (gpc + 1) % priv->gpc_nr;
-               } while (!tpcnr[gpc]);
-               tpcnr[gpc]--;
-
-               data[tpc / 6] |= gpc << ((tpc % 6) * 5);
-       }
-
-       for (; tpc < 32; tpc++)
-               data[tpc / 6] |= 7 << ((tpc % 6) * 5);
-
-       /* and the second... */
-       shift = 0;
-       ntpcv = priv->tpc_total;
-       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(priv, 0x418bb8, (priv->tpc_total << 8) |
-                                priv->magic_not_rop_nr);
-       for (i = 0; i < 6; i++)
-               nv_wr32(priv, 0x418b08 + (i * 4), data[i]);
-
-       /* GPC_BROADCAST.TP_BROADCAST */
-       nv_wr32(priv, 0x41bfd0, (priv->tpc_total << 8) |
-                                priv->magic_not_rop_nr | data2[0]);
-       nv_wr32(priv, 0x41bfe4, data2[1]);
-       for (i = 0; i < 6; i++)
-               nv_wr32(priv, 0x41bf00 + (i * 4), data[i]);
-
-       /* UNK78xx */
-       nv_wr32(priv, 0x4078bc, (priv->tpc_total << 8) |
-                                priv->magic_not_rop_nr);
-       for (i = 0; i < 6; i++)
-               nv_wr32(priv, 0x40780c + (i * 4), data[i]);
-}
-
-void
-nve4_grctx_generate_main(struct nvc0_graph_priv *priv, struct nvc0_grctx *info)
-{
-       struct nvc0_grctx_oclass *oclass = (void *)nv_engine(priv)->cclass;
-       int i;
-
-       nouveau_mc(priv)->unk260(nouveau_mc(priv), 0);
-
-       nvc0_graph_mmio(priv, oclass->hub);
-       nvc0_graph_mmio(priv, oclass->gpc);
-       nvc0_graph_mmio(priv, oclass->zcull);
-       nvc0_graph_mmio(priv, oclass->tpc);
-       nvc0_graph_mmio(priv, oclass->ppc);
-
-       nv_wr32(priv, 0x404154, 0x00000000);
-
-       oclass->bundle(info);
-       oclass->pagepool(info);
-       oclass->attrib(info);
-       oclass->unkn(priv);
-
-       nvc0_grctx_generate_tpcid(priv);
-       nvc0_grctx_generate_r406028(priv);
-       nve4_grctx_generate_r418bb8(priv);
-       nvc0_grctx_generate_r406800(priv);
-
-       for (i = 0; i < 8; i++)
-               nv_wr32(priv, 0x4064d0 + (i * 0x04), 0x00000000);
-
-       nv_wr32(priv, 0x405b00, (priv->tpc_total << 8) | priv->gpc_nr);
-       if (priv->gpc_nr == 1) {
-               nv_mask(priv, 0x408850, 0x0000000f, priv->tpc_nr[0]);
-               nv_mask(priv, 0x408958, 0x0000000f, priv->tpc_nr[0]);
-       } else {
-               nv_mask(priv, 0x408850, 0x0000000f, priv->gpc_nr);
-               nv_mask(priv, 0x408958, 0x0000000f, priv->gpc_nr);
-       }
-       nv_mask(priv, 0x419f78, 0x00000001, 0x00000000);
-
-       nvc0_graph_icmd(priv, oclass->icmd);
-       nv_wr32(priv, 0x404154, 0x00000400);
-       nvc0_graph_mthd(priv, oclass->mthd);
-       nouveau_mc(priv)->unk260(nouveau_mc(priv), 1);
-
-       nv_mask(priv, 0x418800, 0x00200000, 0x00200000);
-       nv_mask(priv, 0x41be10, 0x00800000, 0x00800000);
-}
-
-struct nouveau_oclass *
-nve4_grctx_oclass = &(struct nvc0_grctx_oclass) {
-       .base.handle = NV_ENGCTX(GR, 0xe4),
-       .base.ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nvc0_graph_context_ctor,
-               .dtor = nvc0_graph_context_dtor,
-               .init = _nouveau_graph_context_init,
-               .fini = _nouveau_graph_context_fini,
-               .rd32 = _nouveau_graph_context_rd32,
-               .wr32 = _nouveau_graph_context_wr32,
-       },
-       .main  = nve4_grctx_generate_main,
-       .unkn  = nve4_grctx_generate_unkn,
-       .hub   = nve4_grctx_pack_hub,
-       .gpc   = nve4_grctx_pack_gpc,
-       .zcull = nvc0_grctx_pack_zcull,
-       .tpc   = nve4_grctx_pack_tpc,
-       .ppc   = nve4_grctx_pack_ppc,
-       .icmd  = nve4_grctx_pack_icmd,
-       .mthd  = nve4_grctx_pack_mthd,
-       .bundle = nve4_grctx_generate_bundle,
-       .bundle_size = 0x3000,
-       .bundle_min_gpm_fifo_depth = 0x180,
-       .bundle_token_limit = 0x600,
-       .pagepool = nve4_grctx_generate_pagepool,
-       .pagepool_size = 0x8000,
-       .attrib = nvd7_grctx_generate_attrib,
-       .attrib_nr_max = 0x324,
-       .attrib_nr = 0x218,
-       .alpha_nr_max = 0x7ff,
-       .alpha_nr = 0x648,
-}.base;
diff --git a/drivers/gpu/drm/nouveau/core/engine/graph/ctxnvf0.c b/drivers/gpu/drm/nouveau/core/engine/graph/ctxnvf0.c
deleted file mode 100644 (file)
index e9b0dcf..0000000
+++ /dev/null
@@ -1,843 +0,0 @@
-/*
- * Copyright 2013 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 <bskeggs@redhat.com>
- */
-
-#include "ctxnvc0.h"
-
-/*******************************************************************************
- * PGRAPH context register lists
- ******************************************************************************/
-
-static const struct nvc0_graph_init
-nvf0_grctx_init_icmd_0[] = {
-       { 0x001000,   1, 0x01, 0x00000004 },
-       { 0x000039,   3, 0x01, 0x00000000 },
-       { 0x0000a9,   1, 0x01, 0x0000ffff },
-       { 0x000038,   1, 0x01, 0x0fac6881 },
-       { 0x00003d,   1, 0x01, 0x00000001 },
-       { 0x0000e8,   8, 0x01, 0x00000400 },
-       { 0x000078,   8, 0x01, 0x00000300 },
-       { 0x000050,   1, 0x01, 0x00000011 },
-       { 0x000058,   8, 0x01, 0x00000008 },
-       { 0x000208,   8, 0x01, 0x00000001 },
-       { 0x000081,   1, 0x01, 0x00000001 },
-       { 0x000085,   1, 0x01, 0x00000004 },
-       { 0x000088,   1, 0x01, 0x00000400 },
-       { 0x000090,   1, 0x01, 0x00000300 },
-       { 0x000098,   1, 0x01, 0x00001001 },
-       { 0x0000e3,   1, 0x01, 0x00000001 },
-       { 0x0000da,   1, 0x01, 0x00000001 },
-       { 0x0000f8,   1, 0x01, 0x00000003 },
-       { 0x0000fa,   1, 0x01, 0x00000001 },
-       { 0x00009f,   4, 0x01, 0x0000ffff },
-       { 0x0000b1,   1, 0x01, 0x00000001 },
-       { 0x0000ad,   1, 0x01, 0x0000013e },
-       { 0x0000e1,   1, 0x01, 0x00000010 },
-       { 0x000290,  16, 0x01, 0x00000000 },
-       { 0x0003b0,  16, 0x01, 0x00000000 },
-       { 0x0002a0,  16, 0x01, 0x00000000 },
-       { 0x000420,  16, 0x01, 0x00000000 },
-       { 0x0002b0,  16, 0x01, 0x00000000 },
-       { 0x000430,  16, 0x01, 0x00000000 },
-       { 0x0002c0,  16, 0x01, 0x00000000 },
-       { 0x0004d0,  16, 0x01, 0x00000000 },
-       { 0x000720,  16, 0x01, 0x00000000 },
-       { 0x0008c0,  16, 0x01, 0x00000000 },
-       { 0x000890,  16, 0x01, 0x00000000 },
-       { 0x0008e0,  16, 0x01, 0x00000000 },
-       { 0x0008a0,  16, 0x01, 0x00000000 },
-       { 0x0008f0,  16, 0x01, 0x00000000 },
-       { 0x00094c,   1, 0x01, 0x000000ff },
-       { 0x00094d,   1, 0x01, 0xffffffff },
-       { 0x00094e,   1, 0x01, 0x00000002 },
-       { 0x0002ec,   1, 0x01, 0x00000001 },
-       { 0x0002f2,   2, 0x01, 0x00000001 },
-       { 0x0002f5,   1, 0x01, 0x00000001 },
-       { 0x0002f7,   1, 0x01, 0x00000001 },
-       { 0x000303,   1, 0x01, 0x00000001 },
-       { 0x0002e6,   1, 0x01, 0x00000001 },
-       { 0x000466,   1, 0x01, 0x00000052 },
-       { 0x000301,   1, 0x01, 0x3f800000 },
-       { 0x000304,   1, 0x01, 0x30201000 },
-       { 0x000305,   1, 0x01, 0x70605040 },
-       { 0x000306,   1, 0x01, 0xb8a89888 },
-       { 0x000307,   1, 0x01, 0xf8e8d8c8 },
-       { 0x00030a,   1, 0x01, 0x00ffff00 },
-       { 0x00030b,   1, 0x01, 0x0000001a },
-       { 0x00030c,   1, 0x01, 0x00000001 },
-       { 0x000318,   1, 0x01, 0x00000001 },
-       { 0x000340,   1, 0x01, 0x00000000 },
-       { 0x000375,   1, 0x01, 0x00000001 },
-       { 0x00037d,   1, 0x01, 0x00000006 },
-       { 0x0003a0,   1, 0x01, 0x00000002 },
-       { 0x0003aa,   1, 0x01, 0x00000001 },
-       { 0x0003a9,   1, 0x01, 0x00000001 },
-       { 0x000380,   1, 0x01, 0x00000001 },
-       { 0x000383,   1, 0x01, 0x00000011 },
-       { 0x000360,   1, 0x01, 0x00000040 },
-       { 0x000366,   2, 0x01, 0x00000000 },
-       { 0x000368,   1, 0x01, 0x00000fff },
-       { 0x000370,   2, 0x01, 0x00000000 },
-       { 0x000372,   1, 0x01, 0x000fffff },
-       { 0x00037a,   1, 0x01, 0x00000012 },
-       { 0x000619,   1, 0x01, 0x00000003 },
-       { 0x000811,   1, 0x01, 0x00000003 },
-       { 0x000812,   1, 0x01, 0x00000004 },
-       { 0x000813,   1, 0x01, 0x00000006 },
-       { 0x000814,   1, 0x01, 0x00000008 },
-       { 0x000815,   1, 0x01, 0x0000000b },
-       { 0x000800,   6, 0x01, 0x00000001 },
-       { 0x000632,   1, 0x01, 0x00000001 },
-       { 0x000633,   1, 0x01, 0x00000002 },
-       { 0x000634,   1, 0x01, 0x00000003 },
-       { 0x000635,   1, 0x01, 0x00000004 },
-       { 0x000654,   1, 0x01, 0x3f800000 },
-       { 0x000657,   1, 0x01, 0x3f800000 },
-       { 0x000655,   2, 0x01, 0x3f800000 },
-       { 0x0006cd,   1, 0x01, 0x3f800000 },
-       { 0x0007f5,   1, 0x01, 0x3f800000 },
-       { 0x0007dc,   1, 0x01, 0x39291909 },
-       { 0x0007dd,   1, 0x01, 0x79695949 },
-       { 0x0007de,   1, 0x01, 0xb9a99989 },
-       { 0x0007df,   1, 0x01, 0xf9e9d9c9 },
-       { 0x0007e8,   1, 0x01, 0x00003210 },
-       { 0x0007e9,   1, 0x01, 0x00007654 },
-       { 0x0007ea,   1, 0x01, 0x00000098 },
-       { 0x0007ec,   1, 0x01, 0x39291909 },
-       { 0x0007ed,   1, 0x01, 0x79695949 },
-       { 0x0007ee,   1, 0x01, 0xb9a99989 },
-       { 0x0007ef,   1, 0x01, 0xf9e9d9c9 },
-       { 0x0007f0,   1, 0x01, 0x00003210 },
-       { 0x0007f1,   1, 0x01, 0x00007654 },
-       { 0x0007f2,   1, 0x01, 0x00000098 },
-       { 0x0005a5,   1, 0x01, 0x00000001 },
-       { 0x000980, 128, 0x01, 0x00000000 },
-       { 0x000468,   1, 0x01, 0x00000004 },
-       { 0x00046c,   1, 0x01, 0x00000001 },
-       { 0x000470,  96, 0x01, 0x00000000 },
-       { 0x000510,  16, 0x01, 0x3f800000 },
-       { 0x000520,   1, 0x01, 0x000002b6 },
-       { 0x000529,   1, 0x01, 0x00000001 },
-       { 0x000530,  16, 0x01, 0xffff0000 },
-       { 0x000585,   1, 0x01, 0x0000003f },
-       { 0x000576,   1, 0x01, 0x00000003 },
-       { 0x00057b,   1, 0x01, 0x00000059 },
-       { 0x000586,   1, 0x01, 0x00000040 },
-       { 0x000582,   2, 0x01, 0x00000080 },
-       { 0x0005c2,   1, 0x01, 0x00000001 },
-       { 0x000638,   2, 0x01, 0x00000001 },
-       { 0x00063a,   1, 0x01, 0x00000002 },
-       { 0x00063b,   2, 0x01, 0x00000001 },
-       { 0x00063d,   1, 0x01, 0x00000002 },
-       { 0x00063e,   1, 0x01, 0x00000001 },
-       { 0x0008b8,   8, 0x01, 0x00000001 },
-       { 0x000900,   8, 0x01, 0x00000001 },
-       { 0x000908,   8, 0x01, 0x00000002 },
-       { 0x000910,  16, 0x01, 0x00000001 },
-       { 0x000920,   8, 0x01, 0x00000002 },
-       { 0x000928,   8, 0x01, 0x00000001 },
-       { 0x000662,   1, 0x01, 0x00000001 },
-       { 0x000648,   9, 0x01, 0x00000001 },
-       { 0x000658,   1, 0x01, 0x0000000f },
-       { 0x0007ff,   1, 0x01, 0x0000000a },
-       { 0x00066a,   1, 0x01, 0x40000000 },
-       { 0x00066b,   1, 0x01, 0x10000000 },
-       { 0x00066c,   2, 0x01, 0xffff0000 },
-       { 0x0007af,   2, 0x01, 0x00000008 },
-       { 0x0007f6,   1, 0x01, 0x00000001 },
-       { 0x00080b,   1, 0x01, 0x00000002 },
-       { 0x0006b2,   1, 0x01, 0x00000055 },
-       { 0x0007ad,   1, 0x01, 0x00000003 },
-       { 0x000937,   1, 0x01, 0x00000001 },
-       { 0x000971,   1, 0x01, 0x00000008 },
-       { 0x000972,   1, 0x01, 0x00000040 },
-       { 0x000973,   1, 0x01, 0x0000012c },
-       { 0x00097c,   1, 0x01, 0x00000040 },
-       { 0x000979,   1, 0x01, 0x00000003 },
-       { 0x000975,   1, 0x01, 0x00000020 },
-       { 0x000976,   1, 0x01, 0x00000001 },
-       { 0x000977,   1, 0x01, 0x00000020 },
-       { 0x000978,   1, 0x01, 0x00000001 },
-       { 0x000957,   1, 0x01, 0x00000003 },
-       { 0x00095e,   1, 0x01, 0x20164010 },
-       { 0x00095f,   1, 0x01, 0x00000020 },
-       { 0x000a0d,   1, 0x01, 0x00000006 },
-       { 0x00097d,   1, 0x01, 0x00000020 },
-       { 0x000683,   1, 0x01, 0x00000006 },
-       { 0x000685,   1, 0x01, 0x003fffff },
-       { 0x000687,   1, 0x01, 0x003fffff },
-       { 0x0006a0,   1, 0x01, 0x00000005 },
-       { 0x000840,   1, 0x01, 0x00400008 },
-       { 0x000841,   1, 0x01, 0x08000080 },
-       { 0x000842,   1, 0x01, 0x00400008 },
-       { 0x000843,   1, 0x01, 0x08000080 },
-       { 0x0006aa,   1, 0x01, 0x00000001 },
-       { 0x0006ab,   1, 0x01, 0x00000002 },
-       { 0x0006ac,   1, 0x01, 0x00000080 },
-       { 0x0006ad,   2, 0x01, 0x00000100 },
-       { 0x0006b1,   1, 0x01, 0x00000011 },
-       { 0x0006bb,   1, 0x01, 0x000000cf },
-       { 0x0006ce,   1, 0x01, 0x2a712488 },
-       { 0x000739,   1, 0x01, 0x4085c000 },
-       { 0x00073a,   1, 0x01, 0x00000080 },
-       { 0x000786,   1, 0x01, 0x80000100 },
-       { 0x00073c,   1, 0x01, 0x00010100 },
-       { 0x00073d,   1, 0x01, 0x02800000 },
-       { 0x000787,   1, 0x01, 0x000000cf },
-       { 0x00078c,   1, 0x01, 0x00000008 },
-       { 0x000792,   1, 0x01, 0x00000001 },
-       { 0x000794,   3, 0x01, 0x00000001 },
-       { 0x000797,   1, 0x01, 0x000000cf },
-       { 0x000836,   1, 0x01, 0x00000001 },
-       { 0x00079a,   1, 0x01, 0x00000002 },
-       { 0x000833,   1, 0x01, 0x04444480 },
-       { 0x0007a1,   1, 0x01, 0x00000001 },
-       { 0x0007a3,   3, 0x01, 0x00000001 },
-       { 0x000831,   1, 0x01, 0x00000004 },
-       { 0x000b07,   1, 0x01, 0x00000002 },
-       { 0x000b08,   2, 0x01, 0x00000100 },
-       { 0x000b0a,   1, 0x01, 0x00000001 },
-       { 0x000a04,   1, 0x01, 0x000000ff },
-       { 0x000a0b,   1, 0x01, 0x00000040 },
-       { 0x00097f,   1, 0x01, 0x00000100 },
-       { 0x000a02,   1, 0x01, 0x00000001 },
-       { 0x000809,   1, 0x01, 0x00000007 },
-       { 0x00c221,   1, 0x01, 0x00000040 },
-       { 0x00c1b0,   8, 0x01, 0x0000000f },
-       { 0x00c1b8,   1, 0x01, 0x0fac6881 },
-       { 0x00c1b9,   1, 0x01, 0x00fac688 },
-       { 0x00c401,   1, 0x01, 0x00000001 },
-       { 0x00c402,   1, 0x01, 0x00010001 },
-       { 0x00c403,   2, 0x01, 0x00000001 },
-       { 0x00c40e,   1, 0x01, 0x00000020 },
-       { 0x00c500,   1, 0x01, 0x00000003 },
-       { 0x01e100,   1, 0x01, 0x00000001 },
-       { 0x001000,   1, 0x01, 0x00000002 },
-       { 0x0006aa,   1, 0x01, 0x00000001 },
-       { 0x0006ad,   2, 0x01, 0x00000100 },
-       { 0x0006b1,   1, 0x01, 0x00000011 },
-       { 0x00078c,   1, 0x01, 0x00000008 },
-       { 0x000792,   1, 0x01, 0x00000001 },
-       { 0x000794,   3, 0x01, 0x00000001 },
-       { 0x000797,   1, 0x01, 0x000000cf },
-       { 0x00079a,   1, 0x01, 0x00000002 },
-       { 0x000833,   1, 0x01, 0x04444480 },
-       { 0x0007a1,   1, 0x01, 0x00000001 },
-       { 0x0007a3,   3, 0x01, 0x00000001 },
-       { 0x000831,   1, 0x01, 0x00000004 },
-       { 0x01e100,   1, 0x01, 0x00000001 },
-       { 0x001000,   1, 0x01, 0x00000008 },
-       { 0x000039,   3, 0x01, 0x00000000 },
-       { 0x000380,   1, 0x01, 0x00000001 },
-       { 0x000366,   2, 0x01, 0x00000000 },
-       { 0x000368,   1, 0x01, 0x00000fff },
-       { 0x000370,   2, 0x01, 0x00000000 },
-       { 0x000372,   1, 0x01, 0x000fffff },
-       { 0x000813,   1, 0x01, 0x00000006 },
-       { 0x000814,   1, 0x01, 0x00000008 },
-       { 0x000957,   1, 0x01, 0x00000003 },
-       { 0x000b07,   1, 0x01, 0x00000002 },
-       { 0x000b08,   2, 0x01, 0x00000100 },
-       { 0x000b0a,   1, 0x01, 0x00000001 },
-       { 0x000a04,   1, 0x01, 0x000000ff },
-       { 0x000a0b,   1, 0x01, 0x00000040 },
-       { 0x00097f,   1, 0x01, 0x00000100 },
-       { 0x000a02,   1, 0x01, 0x00000001 },
-       { 0x000809,   1, 0x01, 0x00000007 },
-       { 0x00c221,   1, 0x01, 0x00000040 },
-       { 0x00c401,   1, 0x01, 0x00000001 },
-       { 0x00c402,   1, 0x01, 0x00010001 },
-       { 0x00c403,   2, 0x01, 0x00000001 },
-       { 0x00c40e,   1, 0x01, 0x00000020 },
-       { 0x00c500,   1, 0x01, 0x00000003 },
-       { 0x01e100,   1, 0x01, 0x00000001 },
-       { 0x001000,   1, 0x01, 0x00000001 },
-       { 0x000b07,   1, 0x01, 0x00000002 },
-       { 0x000b08,   2, 0x01, 0x00000100 },
-       { 0x000b0a,   1, 0x01, 0x00000001 },
-       { 0x01e100,   1, 0x01, 0x00000001 },
-       {}
-};
-
-const struct nvc0_graph_pack
-nvf0_grctx_pack_icmd[] = {
-       { nvf0_grctx_init_icmd_0 },
-       {}
-};
-
-static const struct nvc0_graph_init
-nvf0_grctx_init_a197_0[] = {
-       { 0x000800,   8, 0x40, 0x00000000 },
-       { 0x000804,   8, 0x40, 0x00000000 },
-       { 0x000808,   8, 0x40, 0x00000400 },
-       { 0x00080c,   8, 0x40, 0x00000300 },
-       { 0x000810,   1, 0x04, 0x000000cf },
-       { 0x000850,   7, 0x40, 0x00000000 },
-       { 0x000814,   8, 0x40, 0x00000040 },
-       { 0x000818,   8, 0x40, 0x00000001 },
-       { 0x00081c,   8, 0x40, 0x00000000 },
-       { 0x000820,   8, 0x40, 0x00000000 },
-       { 0x001c00,  16, 0x10, 0x00000000 },
-       { 0x001c04,  16, 0x10, 0x00000000 },
-       { 0x001c08,  16, 0x10, 0x00000000 },
-       { 0x001c0c,  16, 0x10, 0x00000000 },
-       { 0x001d00,  16, 0x10, 0x00000000 },
-       { 0x001d04,  16, 0x10, 0x00000000 },
-       { 0x001d08,  16, 0x10, 0x00000000 },
-       { 0x001d0c,  16, 0x10, 0x00000000 },
-       { 0x001f00,  16, 0x08, 0x00000000 },
-       { 0x001f04,  16, 0x08, 0x00000000 },
-       { 0x001f80,  16, 0x08, 0x00000000 },
-       { 0x001f84,  16, 0x08, 0x00000000 },
-       { 0x002000,   1, 0x04, 0x00000000 },
-       { 0x002040,   1, 0x04, 0x00000011 },
-       { 0x002080,   1, 0x04, 0x00000020 },
-       { 0x0020c0,   1, 0x04, 0x00000030 },
-       { 0x002100,   1, 0x04, 0x00000040 },
-       { 0x002140,   1, 0x04, 0x00000051 },
-       { 0x00200c,   6, 0x40, 0x00000001 },
-       { 0x002010,   1, 0x04, 0x00000000 },
-       { 0x002050,   1, 0x04, 0x00000000 },
-       { 0x002090,   1, 0x04, 0x00000001 },
-       { 0x0020d0,   1, 0x04, 0x00000002 },
-       { 0x002110,   1, 0x04, 0x00000003 },
-       { 0x002150,   1, 0x04, 0x00000004 },
-       { 0x000380,   4, 0x20, 0x00000000 },
-       { 0x000384,   4, 0x20, 0x00000000 },
-       { 0x000388,   4, 0x20, 0x00000000 },
-       { 0x00038c,   4, 0x20, 0x00000000 },
-       { 0x000700,   4, 0x10, 0x00000000 },
-       { 0x000704,   4, 0x10, 0x00000000 },
-       { 0x000708,   4, 0x10, 0x00000000 },
-       { 0x002800, 128, 0x04, 0x00000000 },
-       { 0x000a00,  16, 0x20, 0x00000000 },
-       { 0x000a04,  16, 0x20, 0x00000000 },
-       { 0x000a08,  16, 0x20, 0x00000000 },
-       { 0x000a0c,  16, 0x20, 0x00000000 },
-       { 0x000a10,  16, 0x20, 0x00000000 },
-       { 0x000a14,  16, 0x20, 0x00000000 },
-       { 0x000c00,  16, 0x10, 0x00000000 },
-       { 0x000c04,  16, 0x10, 0x00000000 },
-       { 0x000c08,  16, 0x10, 0x00000000 },
-       { 0x000c0c,  16, 0x10, 0x3f800000 },
-       { 0x000d00,   8, 0x08, 0xffff0000 },
-       { 0x000d04,   8, 0x08, 0xffff0000 },
-       { 0x000e00,  16, 0x10, 0x00000000 },
-       { 0x000e04,  16, 0x10, 0xffff0000 },
-       { 0x000e08,  16, 0x10, 0xffff0000 },
-       { 0x000d40,   4, 0x08, 0x00000000 },
-       { 0x000d44,   4, 0x08, 0x00000000 },
-       { 0x001e00,   8, 0x20, 0x00000001 },
-       { 0x001e04,   8, 0x20, 0x00000001 },
-       { 0x001e08,   8, 0x20, 0x00000002 },
-       { 0x001e0c,   8, 0x20, 0x00000001 },
-       { 0x001e10,   8, 0x20, 0x00000001 },
-       { 0x001e14,   8, 0x20, 0x00000002 },
-       { 0x001e18,   8, 0x20, 0x00000001 },
-       { 0x003400, 128, 0x04, 0x00000000 },
-       { 0x00030c,   1, 0x04, 0x00000001 },
-       { 0x001944,   1, 0x04, 0x00000000 },
-       { 0x001514,   1, 0x04, 0x00000000 },
-       { 0x000d68,   1, 0x04, 0x0000ffff },
-       { 0x00121c,   1, 0x04, 0x0fac6881 },
-       { 0x000fac,   1, 0x04, 0x00000001 },
-       { 0x001538,   1, 0x04, 0x00000001 },
-       { 0x000fe0,   2, 0x04, 0x00000000 },
-       { 0x000fe8,   1, 0x04, 0x00000014 },
-       { 0x000fec,   1, 0x04, 0x00000040 },
-       { 0x000ff0,   1, 0x04, 0x00000000 },
-       { 0x00179c,   1, 0x04, 0x00000000 },
-       { 0x001228,   1, 0x04, 0x00000400 },
-       { 0x00122c,   1, 0x04, 0x00000300 },
-       { 0x001230,   1, 0x04, 0x00010001 },
-       { 0x0007f8,   1, 0x04, 0x00000000 },
-       { 0x0015b4,   1, 0x04, 0x00000001 },
-       { 0x0015cc,   1, 0x04, 0x00000000 },
-       { 0x001534,   1, 0x04, 0x00000000 },
-       { 0x000fb0,   1, 0x04, 0x00000000 },
-       { 0x0015d0,   1, 0x04, 0x00000000 },
-       { 0x00153c,   1, 0x04, 0x00000000 },
-       { 0x0016b4,   1, 0x04, 0x00000003 },
-       { 0x000fbc,   4, 0x04, 0x0000ffff },
-       { 0x000df8,   2, 0x04, 0x00000000 },
-       { 0x001948,   1, 0x04, 0x00000000 },
-       { 0x001970,   1, 0x04, 0x00000001 },
-       { 0x00161c,   1, 0x04, 0x000009f0 },
-       { 0x000dcc,   1, 0x04, 0x00000010 },
-       { 0x00163c,   1, 0x04, 0x00000000 },
-       { 0x0015e4,   1, 0x04, 0x00000000 },
-       { 0x001160,  32, 0x04, 0x25e00040 },
-       { 0x001880,  32, 0x04, 0x00000000 },
-       { 0x000f84,   2, 0x04, 0x00000000 },
-       { 0x0017c8,   2, 0x04, 0x00000000 },
-       { 0x0017d0,   1, 0x04, 0x000000ff },
-       { 0x0017d4,   1, 0x04, 0xffffffff },
-       { 0x0017d8,   1, 0x04, 0x00000002 },
-       { 0x0017dc,   1, 0x04, 0x00000000 },
-       { 0x0015f4,   2, 0x04, 0x00000000 },
-       { 0x001434,   2, 0x04, 0x00000000 },
-       { 0x000d74,   1, 0x04, 0x00000000 },
-       { 0x000dec,   1, 0x04, 0x00000001 },
-       { 0x0013a4,   1, 0x04, 0x00000000 },
-       { 0x001318,   1, 0x04, 0x00000001 },
-       { 0x001644,   1, 0x04, 0x00000000 },
-       { 0x000748,   1, 0x04, 0x00000000 },
-       { 0x000de8,   1, 0x04, 0x00000000 },
-       { 0x001648,   1, 0x04, 0x00000000 },
-       { 0x0012a4,   1, 0x04, 0x00000000 },
-       { 0x001120,   4, 0x04, 0x00000000 },
-       { 0x001118,   1, 0x04, 0x00000000 },
-       { 0x00164c,   1, 0x04, 0x00000000 },
-       { 0x001658,   1, 0x04, 0x00000000 },
-       { 0x001910,   1, 0x04, 0x00000290 },
-       { 0x001518,   1, 0x04, 0x00000000 },
-       { 0x00165c,   1, 0x04, 0x00000001 },
-       { 0x001520,   1, 0x04, 0x00000000 },
-       { 0x001604,   1, 0x04, 0x00000000 },
-       { 0x001570,   1, 0x04, 0x00000000 },
-       { 0x0013b0,   2, 0x04, 0x3f800000 },
-       { 0x00020c,   1, 0x04, 0x00000000 },
-       { 0x001670,   1, 0x04, 0x30201000 },
-       { 0x001674,   1, 0x04, 0x70605040 },
-       { 0x001678,   1, 0x04, 0xb8a89888 },
-       { 0x00167c,   1, 0x04, 0xf8e8d8c8 },
-       { 0x00166c,   1, 0x04, 0x00000000 },
-       { 0x001680,   1, 0x04, 0x00ffff00 },
-       { 0x0012d0,   1, 0x04, 0x00000003 },
-       { 0x0012d4,   1, 0x04, 0x00000002 },
-       { 0x001684,   2, 0x04, 0x00000000 },
-       { 0x000dac,   2, 0x04, 0x00001b02 },
-       { 0x000db4,   1, 0x04, 0x00000000 },
-       { 0x00168c,   1, 0x04, 0x00000000 },
-       { 0x0015bc,   1, 0x04, 0x00000000 },
-       { 0x00156c,   1, 0x04, 0x00000000 },
-       { 0x00187c,   1, 0x04, 0x00000000 },
-       { 0x001110,   1, 0x04, 0x00000001 },
-       { 0x000dc0,   3, 0x04, 0x00000000 },
-       { 0x001234,   1, 0x04, 0x00000000 },
-       { 0x001690,   1, 0x04, 0x00000000 },
-       { 0x0012ac,   1, 0x04, 0x00000001 },
-       { 0x0002c4,   1, 0x04, 0x00000000 },
-       { 0x000790,   5, 0x04, 0x00000000 },
-       { 0x00077c,   1, 0x04, 0x00000000 },
-       { 0x001000,   1, 0x04, 0x00000010 },
-       { 0x0010fc,   1, 0x04, 0x00000000 },
-       { 0x001290,   1, 0x04, 0x00000000 },
-       { 0x000218,   1, 0x04, 0x00000010 },
-       { 0x0012d8,   1, 0x04, 0x00000000 },
-       { 0x0012dc,   1, 0x04, 0x00000010 },
-       { 0x000d94,   1, 0x04, 0x00000001 },
-       { 0x00155c,   2, 0x04, 0x00000000 },
-       { 0x001564,   1, 0x04, 0x00000fff },
-       { 0x001574,   2, 0x04, 0x00000000 },
-       { 0x00157c,   1, 0x04, 0x000fffff },
-       { 0x001354,   1, 0x04, 0x00000000 },
-       { 0x001610,   1, 0x04, 0x00000012 },
-       { 0x001608,   2, 0x04, 0x00000000 },
-       { 0x00260c,   1, 0x04, 0x00000000 },
-       { 0x0007ac,   1, 0x04, 0x00000000 },
-       { 0x00162c,   1, 0x04, 0x00000003 },
-       { 0x000210,   1, 0x04, 0x00000000 },
-       { 0x000320,   1, 0x04, 0x00000000 },
-       { 0x000324,   6, 0x04, 0x3f800000 },
-       { 0x000750,   1, 0x04, 0x00000000 },
-       { 0x000760,   1, 0x04, 0x39291909 },
-       { 0x000764,   1, 0x04, 0x79695949 },
-       { 0x000768,   1, 0x04, 0xb9a99989 },
-       { 0x00076c,   1, 0x04, 0xf9e9d9c9 },
-       { 0x000770,   1, 0x04, 0x30201000 },
-       { 0x000774,   1, 0x04, 0x70605040 },
-       { 0x000778,   1, 0x04, 0x00009080 },
-       { 0x000780,   1, 0x04, 0x39291909 },
-       { 0x000784,   1, 0x04, 0x79695949 },
-       { 0x000788,   1, 0x04, 0xb9a99989 },
-       { 0x00078c,   1, 0x04, 0xf9e9d9c9 },
-       { 0x0007d0,   1, 0x04, 0x30201000 },
-       { 0x0007d4,   1, 0x04, 0x70605040 },
-       { 0x0007d8,   1, 0x04, 0x00009080 },
-       { 0x00037c,   1, 0x04, 0x00000001 },
-       { 0x000740,   2, 0x04, 0x00000000 },
-       { 0x002600,   1, 0x04, 0x00000000 },
-       { 0x001918,   1, 0x04, 0x00000000 },
-       { 0x00191c,   1, 0x04, 0x00000900 },
-       { 0x001920,   1, 0x04, 0x00000405 },
-       { 0x001308,   1, 0x04, 0x00000001 },
-       { 0x001924,   1, 0x04, 0x00000000 },
-       { 0x0013ac,   1, 0x04, 0x00000000 },
-       { 0x00192c,   1, 0x04, 0x00000001 },
-       { 0x00193c,   1, 0x04, 0x00002c1c },
-       { 0x000d7c,   1, 0x04, 0x00000000 },
-       { 0x000f8c,   1, 0x04, 0x00000000 },
-       { 0x0002c0,   1, 0x04, 0x00000001 },
-       { 0x001510,   1, 0x04, 0x00000000 },
-       { 0x001940,   1, 0x04, 0x00000000 },
-       { 0x000ff4,   2, 0x04, 0x00000000 },
-       { 0x00194c,   2, 0x04, 0x00000000 },
-       { 0x001968,   1, 0x04, 0x00000000 },
-       { 0x001590,   1, 0x04, 0x0000003f },
-       { 0x0007e8,   4, 0x04, 0x00000000 },
-       { 0x00196c,   1, 0x04, 0x00000011 },
-       { 0x0002e4,   1, 0x04, 0x0000b001 },
-       { 0x00036c,   2, 0x04, 0x00000000 },
-       { 0x00197c,   1, 0x04, 0x00000000 },
-       { 0x000fcc,   2, 0x04, 0x00000000 },
-       { 0x0002d8,   1, 0x04, 0x00000040 },
-       { 0x001980,   1, 0x04, 0x00000080 },
-       { 0x001504,   1, 0x04, 0x00000080 },
-       { 0x001984,   1, 0x04, 0x00000000 },
-       { 0x000300,   1, 0x04, 0x00000001 },
-       { 0x0013a8,   1, 0x04, 0x00000000 },
-       { 0x0012ec,   1, 0x04, 0x00000000 },
-       { 0x001310,   1, 0x04, 0x00000000 },
-       { 0x001314,   1, 0x04, 0x00000001 },
-       { 0x001380,   1, 0x04, 0x00000000 },
-       { 0x001384,   4, 0x04, 0x00000001 },
-       { 0x001394,   1, 0x04, 0x00000000 },
-       { 0x00139c,   1, 0x04, 0x00000000 },
-       { 0x001398,   1, 0x04, 0x00000000 },
-       { 0x001594,   1, 0x04, 0x00000000 },
-       { 0x001598,   4, 0x04, 0x00000001 },
-       { 0x000f54,   3, 0x04, 0x00000000 },
-       { 0x0019bc,   1, 0x04, 0x00000000 },
-       { 0x000f9c,   2, 0x04, 0x00000000 },
-       { 0x0012cc,   1, 0x04, 0x00000000 },
-       { 0x0012e8,   1, 0x04, 0x00000000 },
-       { 0x00130c,   1, 0x04, 0x00000001 },
-       { 0x001360,   8, 0x04, 0x00000000 },
-       { 0x00133c,   2, 0x04, 0x00000001 },
-       { 0x001344,   1, 0x04, 0x00000002 },
-       { 0x001348,   2, 0x04, 0x00000001 },
-       { 0x001350,   1, 0x04, 0x00000002 },
-       { 0x001358,   1, 0x04, 0x00000001 },
-       { 0x0012e4,   1, 0x04, 0x00000000 },
-       { 0x00131c,   4, 0x04, 0x00000000 },
-       { 0x0019c0,   1, 0x04, 0x00000000 },
-       { 0x001140,   1, 0x04, 0x00000000 },
-       { 0x0019c4,   1, 0x04, 0x00000000 },
-       { 0x0019c8,   1, 0x04, 0x00001500 },
-       { 0x00135c,   1, 0x04, 0x00000000 },
-       { 0x000f90,   1, 0x04, 0x00000000 },
-       { 0x0019e0,   8, 0x04, 0x00000001 },
-       { 0x0019cc,   1, 0x04, 0x00000001 },
-       { 0x0015b8,   1, 0x04, 0x00000000 },
-       { 0x001a00,   1, 0x04, 0x00001111 },
-       { 0x001a04,   7, 0x04, 0x00000000 },
-       { 0x000d6c,   2, 0x04, 0xffff0000 },
-       { 0x0010f8,   1, 0x04, 0x00001010 },
-       { 0x000d80,   5, 0x04, 0x00000000 },
-       { 0x000da0,   1, 0x04, 0x00000000 },
-       { 0x0007a4,   2, 0x04, 0x00000000 },
-       { 0x001508,   1, 0x04, 0x80000000 },
-       { 0x00150c,   1, 0x04, 0x40000000 },
-       { 0x001668,   1, 0x04, 0x00000000 },
-       { 0x000318,   2, 0x04, 0x00000008 },
-       { 0x000d9c,   1, 0x04, 0x00000001 },
-       { 0x000ddc,   1, 0x04, 0x00000002 },
-       { 0x000374,   1, 0x04, 0x00000000 },
-       { 0x000378,   1, 0x04, 0x00000020 },
-       { 0x0007dc,   1, 0x04, 0x00000000 },
-       { 0x00074c,   1, 0x04, 0x00000055 },
-       { 0x001420,   1, 0x04, 0x00000003 },
-       { 0x0017bc,   2, 0x04, 0x00000000 },
-       { 0x0017c4,   1, 0x04, 0x00000001 },
-       { 0x001008,   1, 0x04, 0x00000008 },
-       { 0x00100c,   1, 0x04, 0x00000040 },
-       { 0x001010,   1, 0x04, 0x0000012c },
-       { 0x000d60,   1, 0x04, 0x00000040 },
-       { 0x00075c,   1, 0x04, 0x00000003 },
-       { 0x001018,   1, 0x04, 0x00000020 },
-       { 0x00101c,   1, 0x04, 0x00000001 },
-       { 0x001020,   1, 0x04, 0x00000020 },
-       { 0x001024,   1, 0x04, 0x00000001 },
-       { 0x001444,   3, 0x04, 0x00000000 },
-       { 0x000360,   1, 0x04, 0x20164010 },
-       { 0x000364,   1, 0x04, 0x00000020 },
-       { 0x000368,   1, 0x04, 0x00000000 },
-       { 0x000de4,   1, 0x04, 0x00000000 },
-       { 0x000204,   1, 0x04, 0x00000006 },
-       { 0x000208,   1, 0x04, 0x00000000 },
-       { 0x0002cc,   2, 0x04, 0x003fffff },
-       { 0x001220,   1, 0x04, 0x00000005 },
-       { 0x000fdc,   1, 0x04, 0x00000000 },
-       { 0x000f98,   1, 0x04, 0x00400008 },
-       { 0x001284,   1, 0x04, 0x08000080 },
-       { 0x001450,   1, 0x04, 0x00400008 },
-       { 0x001454,   1, 0x04, 0x08000080 },
-       { 0x000214,   1, 0x04, 0x00000000 },
-       {}
-};
-
-const struct nvc0_graph_pack
-nvf0_grctx_pack_mthd[] = {
-       { nvf0_grctx_init_a197_0, 0xa197 },
-       { nvc0_grctx_init_902d_0, 0x902d },
-       {}
-};
-
-static const struct nvc0_graph_init
-nvf0_grctx_init_fe_0[] = {
-       { 0x404004,   8, 0x04, 0x00000000 },
-       { 0x404024,   1, 0x04, 0x0000e000 },
-       { 0x404028,   8, 0x04, 0x00000000 },
-       { 0x4040a8,   8, 0x04, 0x00000000 },
-       { 0x4040c8,   1, 0x04, 0xf800008f },
-       { 0x4040d0,   6, 0x04, 0x00000000 },
-       { 0x4040e8,   1, 0x04, 0x00001000 },
-       { 0x4040f8,   1, 0x04, 0x00000000 },
-       { 0x404100,  10, 0x04, 0x00000000 },
-       { 0x404130,   2, 0x04, 0x00000000 },
-       { 0x404138,   1, 0x04, 0x20000040 },
-       { 0x404150,   1, 0x04, 0x0000002e },
-       { 0x404154,   1, 0x04, 0x00000400 },
-       { 0x404158,   1, 0x04, 0x00000200 },
-       { 0x404164,   1, 0x04, 0x00000055 },
-       { 0x40417c,   2, 0x04, 0x00000000 },
-       { 0x4041a0,   4, 0x04, 0x00000000 },
-       { 0x404200,   1, 0x04, 0x0000a197 },
-       { 0x404204,   1, 0x04, 0x0000a1c0 },
-       { 0x404208,   1, 0x04, 0x0000a140 },
-       { 0x40420c,   1, 0x04, 0x0000902d },
-       {}
-};
-
-const struct nvc0_graph_init
-nvf0_grctx_init_pri_0[] = {
-       { 0x404404,  12, 0x04, 0x00000000 },
-       { 0x404438,   1, 0x04, 0x00000000 },
-       { 0x404460,   2, 0x04, 0x00000000 },
-       { 0x404468,   1, 0x04, 0x00ffffff },
-       { 0x40446c,   1, 0x04, 0x00000000 },
-       { 0x404480,   1, 0x04, 0x00000001 },
-       { 0x404498,   1, 0x04, 0x00000001 },
-       {}
-};
-
-const struct nvc0_graph_init
-nvf0_grctx_init_cwd_0[] = {
-       { 0x405b00,   1, 0x04, 0x00000000 },
-       { 0x405b10,   1, 0x04, 0x00001000 },
-       { 0x405b20,   1, 0x04, 0x04000000 },
-       {}
-};
-
-static const struct nvc0_graph_init
-nvf0_grctx_init_pd_0[] = {
-       { 0x406020,   1, 0x04, 0x034103c1 },
-       { 0x406028,   4, 0x04, 0x00000001 },
-       { 0x4064a8,   1, 0x04, 0x00000000 },
-       { 0x4064ac,   1, 0x04, 0x00003fff },
-       { 0x4064b0,   3, 0x04, 0x00000000 },
-       { 0x4064c0,   1, 0x04, 0x802000f0 },
-       { 0x4064c4,   1, 0x04, 0x0192ffff },
-       { 0x4064c8,   1, 0x04, 0x018007c0 },
-       { 0x4064cc,   9, 0x04, 0x00000000 },
-       { 0x4064fc,   1, 0x04, 0x0000022a },
-       {}
-};
-
-static const struct nvc0_graph_init
-nvf0_grctx_init_be_0[] = {
-       { 0x408800,   1, 0x04, 0x12802a3c },
-       { 0x408804,   1, 0x04, 0x00000040 },
-       { 0x408808,   1, 0x04, 0x1003e005 },
-       { 0x408840,   1, 0x04, 0x0000000b },
-       { 0x408900,   1, 0x04, 0x3080b801 },
-       { 0x408904,   1, 0x04, 0x62000001 },
-       { 0x408908,   1, 0x04, 0x00c8102f },
-       { 0x408980,   1, 0x04, 0x0000011d },
-       {}
-};
-
-const struct nvc0_graph_pack
-nvf0_grctx_pack_hub[] = {
-       { nvc0_grctx_init_main_0 },
-       { nvf0_grctx_init_fe_0 },
-       { nvf0_grctx_init_pri_0 },
-       { nve4_grctx_init_memfmt_0 },
-       { nve4_grctx_init_ds_0 },
-       { nvf0_grctx_init_cwd_0 },
-       { nvf0_grctx_init_pd_0 },
-       { nvc0_grctx_init_rstr2d_0 },
-       { nve4_grctx_init_scc_0 },
-       { nvf0_grctx_init_be_0 },
-       {}
-};
-
-static const struct nvc0_graph_init
-nvf0_grctx_init_setup_0[] = {
-       { 0x418800,   1, 0x04, 0x7006860a },
-       { 0x418808,   1, 0x04, 0x00000000 },
-       { 0x41880c,   1, 0x04, 0x00000030 },
-       { 0x418810,   1, 0x04, 0x00000000 },
-       { 0x418828,   1, 0x04, 0x00000044 },
-       { 0x418830,   1, 0x04, 0x10000001 },
-       { 0x4188d8,   1, 0x04, 0x00000008 },
-       { 0x4188e0,   1, 0x04, 0x01000000 },
-       { 0x4188e8,   5, 0x04, 0x00000000 },
-       { 0x4188fc,   1, 0x04, 0x20100018 },
-       {}
-};
-
-const struct nvc0_graph_init
-nvf0_grctx_init_gpc_unk_2[] = {
-       { 0x418d24,   1, 0x04, 0x00000000 },
-       {}
-};
-
-const struct nvc0_graph_pack
-nvf0_grctx_pack_gpc[] = {
-       { nvc0_grctx_init_gpc_unk_0 },
-       { nvd9_grctx_init_prop_0 },
-       { nvd9_grctx_init_gpc_unk_1 },
-       { nvf0_grctx_init_setup_0 },
-       { nvc0_grctx_init_zcull_0 },
-       { nvd9_grctx_init_crstr_0 },
-       { nve4_grctx_init_gpm_0 },
-       { nvf0_grctx_init_gpc_unk_2 },
-       { nvc0_grctx_init_gcc_0 },
-       {}
-};
-
-const struct nvc0_graph_init
-nvf0_grctx_init_tex_0[] = {
-       { 0x419a00,   1, 0x04, 0x000000f0 },
-       { 0x419a04,   1, 0x04, 0x00000001 },
-       { 0x419a08,   1, 0x04, 0x00000021 },
-       { 0x419a0c,   1, 0x04, 0x00020000 },
-       { 0x419a10,   1, 0x04, 0x00000000 },
-       { 0x419a14,   1, 0x04, 0x00000200 },
-       { 0x419a1c,   1, 0x04, 0x0000c000 },
-       { 0x419a20,   1, 0x04, 0x00020800 },
-       { 0x419a30,   1, 0x04, 0x00000001 },
-       { 0x419ac4,   1, 0x04, 0x0037f440 },
-       {}
-};
-
-const struct nvc0_graph_init
-nvf0_grctx_init_mpc_0[] = {
-       { 0x419c00,   1, 0x04, 0x0000001a },
-       { 0x419c04,   1, 0x04, 0x80000006 },
-       { 0x419c08,   1, 0x04, 0x00000002 },
-       { 0x419c20,   1, 0x04, 0x00000000 },
-       { 0x419c24,   1, 0x04, 0x00084210 },
-       { 0x419c28,   1, 0x04, 0x3efbefbe },
-       {}
-};
-
-const struct nvc0_graph_init
-nvf0_grctx_init_l1c_0[] = {
-       { 0x419ce8,   1, 0x04, 0x00000000 },
-       { 0x419cf4,   1, 0x04, 0x00000203 },
-       {}
-};
-
-static const struct nvc0_graph_init
-nvf0_grctx_init_sm_0[] = {
-       { 0x419e04,   1, 0x04, 0x00000000 },
-       { 0x419e08,   1, 0x04, 0x0000001d },
-       { 0x419e0c,   1, 0x04, 0x00000000 },
-       { 0x419e10,   1, 0x04, 0x00001c02 },
-       { 0x419e44,   1, 0x04, 0x0013eff2 },
-       { 0x419e48,   1, 0x04, 0x00000000 },
-       { 0x419e4c,   1, 0x04, 0x0000007f },
-       { 0x419e50,   2, 0x04, 0x00000000 },
-       { 0x419e58,   1, 0x04, 0x00000001 },
-       { 0x419e5c,   3, 0x04, 0x00000000 },
-       { 0x419e68,   1, 0x04, 0x00000002 },
-       { 0x419e6c,  12, 0x04, 0x00000000 },
-       { 0x419eac,   1, 0x04, 0x00001f8f },
-       { 0x419eb0,   1, 0x04, 0x0db00d2f },
-       { 0x419eb8,   1, 0x04, 0x00000000 },
-       { 0x419ec8,   1, 0x04, 0x0001304f },
-       { 0x419f30,   4, 0x04, 0x00000000 },
-       { 0x419f40,   1, 0x04, 0x00000018 },
-       { 0x419f44,   3, 0x04, 0x00000000 },
-       { 0x419f58,   1, 0x04, 0x00000000 },
-       { 0x419f70,   1, 0x04, 0x00007300 },
-       { 0x419f78,   1, 0x04, 0x000000eb },
-       { 0x419f7c,   1, 0x04, 0x00000404 },
-       {}
-};
-
-static const struct nvc0_graph_pack
-nvf0_grctx_pack_tpc[] = {
-       { nvd7_grctx_init_pe_0 },
-       { nvf0_grctx_init_tex_0 },
-       { nvf0_grctx_init_mpc_0 },
-       { nvf0_grctx_init_l1c_0 },
-       { nvf0_grctx_init_sm_0 },
-       {}
-};
-
-static const struct nvc0_graph_init
-nvf0_grctx_init_cbm_0[] = {
-       { 0x41bec0,   1, 0x04, 0x10000000 },
-       { 0x41bec4,   1, 0x04, 0x00037f7f },
-       { 0x41bee4,   1, 0x04, 0x00000000 },
-       {}
-};
-
-const struct nvc0_graph_pack
-nvf0_grctx_pack_ppc[] = {
-       { nve4_grctx_init_pes_0 },
-       { nvf0_grctx_init_cbm_0 },
-       { nvd7_grctx_init_wwdx_0 },
-       {}
-};
-
-/*******************************************************************************
- * PGRAPH context implementation
- ******************************************************************************/
-
-struct nouveau_oclass *
-nvf0_grctx_oclass = &(struct nvc0_grctx_oclass) {
-       .base.handle = NV_ENGCTX(GR, 0xf0),
-       .base.ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nvc0_graph_context_ctor,
-               .dtor = nvc0_graph_context_dtor,
-               .init = _nouveau_graph_context_init,
-               .fini = _nouveau_graph_context_fini,
-               .rd32 = _nouveau_graph_context_rd32,
-               .wr32 = _nouveau_graph_context_wr32,
-       },
-       .main  = nve4_grctx_generate_main,
-       .unkn  = nve4_grctx_generate_unkn,
-       .hub   = nvf0_grctx_pack_hub,
-       .gpc   = nvf0_grctx_pack_gpc,
-       .zcull = nvc0_grctx_pack_zcull,
-       .tpc   = nvf0_grctx_pack_tpc,
-       .ppc   = nvf0_grctx_pack_ppc,
-       .icmd  = nvf0_grctx_pack_icmd,
-       .mthd  = nvf0_grctx_pack_mthd,
-       .bundle = nve4_grctx_generate_bundle,
-       .bundle_size = 0x3000,
-       .bundle_min_gpm_fifo_depth = 0x180,
-       .bundle_token_limit = 0x7c0,
-       .pagepool = nve4_grctx_generate_pagepool,
-       .pagepool_size = 0x8000,
-       .attrib = nvd7_grctx_generate_attrib,
-       .attrib_nr_max = 0x324,
-       .attrib_nr = 0x218,
-       .alpha_nr_max = 0x7ff,
-       .alpha_nr = 0x648,
-}.base;
diff --git a/drivers/gpu/drm/nouveau/core/engine/graph/fuc/com.fuc b/drivers/gpu/drm/nouveau/core/engine/graph/fuc/com.fuc
deleted file mode 100644 (file)
index e37d810..0000000
+++ /dev/null
@@ -1,335 +0,0 @@
-/* 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
- */
-
-#ifdef INCLUDE_CODE
-// 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 b32 $r12 $r14
-       bset $r12 31                    // MMIO_CTRL_PENDING
-       nv_iowr(NV_PGRAPH_FECS_MMIO_CTRL, 0, $r12)
-       nv_rd32_wait:
-               nv_iord($r12, NV_PGRAPH_FECS_MMIO_CTRL, 0)
-               xbit $r12 $r12 31
-               bra ne #nv_rd32_wait
-       mov $r10 6                      // DONE_MMIO_RD
-       call(wait_doneo)
-       nv_iord($r15, NV_PGRAPH_FECS_MMIO_RDVAL, 0)
-       ret
-
-// nv_wr32 - write 32-bit value to nv register
-//
-// In : $r14 register
-//      $r15 value
-//
-nv_wr32:
-       nv_iowr(NV_PGRAPH_FECS_MMIO_WRVAL, 0, $r15)
-       mov b32 $r12 $r14
-       bset $r12 31                    // MMIO_CTRL_PENDING
-       bset $r12 30                    // MMIO_CTRL_WRITE
-       nv_iowr(NV_PGRAPH_FECS_MMIO_CTRL, 0, $r12)
-       nv_wr32_wait:
-               nv_iord($r12, NV_PGRAPH_FECS_MMIO_CTRL, 0)
-               xbit $r12 $r12 31
-               bra ne #nv_wr32_wait
-       ret
-
-// wait_donez - wait on FUC_DONE bit to become clear
-//
-// In : $r10 bit to wait on
-//
-wait_donez:
-       trace_set(T_WAIT);
-       nv_iowr(NV_PGRAPH_FECS_CC_SCRATCH_VAL(6), 0, $r10)
-       wait_donez_ne:
-               nv_iord($r8, NV_PGRAPH_FECS_SIGNAL, 0)
-               xbit $r8 $r8 $r10
-               bra ne #wait_donez_ne
-       trace_clr(T_WAIT)
-       ret
-
-// wait_doneo - wait on FUC_DONE bit to become set
-//
-// In : $r10 bit to wait on
-//
-wait_doneo:
-       trace_set(T_WAIT);
-       nv_iowr(NV_PGRAPH_FECS_CC_SCRATCH_VAL(6), 0, $r10)
-       wait_doneo_e:
-               nv_iord($r8, NV_PGRAPH_FECS_SIGNAL, 0)
-               xbit $r8 $r8 $r10
-               bra e #wait_doneo_e
-       trace_clr(T_WAIT)
-       ret
-
-// 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)
-       clear b32 $r9
-       or $r11 $r11
-       bra e #mmctx_base_disabled
-               nv_iowr(NV_PGRAPH_FECS_MMCTX_BASE, 0, $r11)
-               bset $r9 0                      // BASE_EN
-       mmctx_base_disabled:
-       or $r14 $r14
-       bra e #mmctx_multi_disabled
-               nv_iowr(NV_PGRAPH_FECS_MMCTX_MULTI_STRIDE, 0, $r14)
-               nv_iowr(NV_PGRAPH_FECS_MMCTX_MULTI_MASK, 0, $r15)
-               bset $r9 1                      // MULTI_EN
-       mmctx_multi_disabled:
-
-       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
-       nv_iowr(NV_PGRAPH_FECS_MMCTX_CTRL, 0, $r11)
-
-       // loop over the mmio list, and send requests to the hw
-       mmctx_exec_loop:
-               // wait for space in mmctx queue
-               mmctx_wait_free:
-                       nv_iord($r14, NV_PGRAPH_FECS_MMCTX_CTRL, 0)
-                       and $r14 0x1f
-                       bra e #mmctx_wait_free
-
-               // queue up an entry
-               ld b32 $r14 D[$r12]
-               or $r14 $r9
-               nv_iowr(NV_PGRAPH_FECS_MMCTX_QUEUE, 0, $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:
-                       nv_iord($r11, NV_PGRAPH_FECS_MMCTX_CTRL, 0)
-                       and $r11 0x1f
-                       cmpu b32 $r11 0x10
-                       bra ne #mmctx_fini_wait
-               mov $r10 5                      // 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
-               nv_iowr(NV_PGRAPH_FECS_MMCTX_CTRL, 0, $r11)
-               mmctx_stop_wait:
-                       // wait for STOP_TRIGGER to clear
-                       nv_iord($r11, NV_PGRAPH_FECS_MMCTX_CTRL, 0)
-                       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 $r9 NV_PGRAPH_FECS_STRAND_CMD_ENABLE
-       nv_iowr(NV_PGRAPH_FECS_STRAND_CMD, 0x3f, $r9)
-       call(strand_wait)
-       ret
-
-// unknown - call after issuing strand commands
-//
-strand_post:
-       mov $r9 NV_PGRAPH_FECS_STRAND_CMD_DISABLE
-       nv_iowr(NV_PGRAPH_FECS_STRAND_CMD, 0x3f, $r9)
-       call(strand_wait)
-       ret
-
-// Selects strand set?!
-//
-// In: $r14 id
-//
-strand_set:
-       mov $r12 0xf
-       nv_iowr(NV_PGRAPH_FECS_STRAND_FILTER, 0x3f, $r12)
-       mov $r12 NV_PGRAPH_FECS_STRAND_CMD_DEACTIVATE_FILTER
-       nv_iowr(NV_PGRAPH_FECS_STRAND_CMD, 0x3f, $r12)
-       nv_iowr(NV_PGRAPH_FECS_STRAND_FILTER, 0x3f, $r14)
-       mov $r12 NV_PGRAPH_FECS_STRAND_CMD_ACTIVATE_FILTER
-       nv_iowr(NV_PGRAPH_FECS_STRAND_CMD, 0x3f, $r12)
-       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)
-
-       clear b32 $r12
-       nv_iowr(NV_PGRAPH_FECS_STRAND_SELECT, 0x3f, $r12)
-       mov $r12 NV_PGRAPH_FECS_STRAND_CMD_SEEK
-       nv_iowr(NV_PGRAPH_FECS_STRAND_CMD, 0x3f, $r12)
-       call(strand_wait)
-       sub b32 $r12 $r0 1
-       nv_iowr(NV_PGRAPH_FECS_STRAND_DATA, 0x3f, $r12)
-       mov $r12 NV_PGRAPH_FECS_STRAND_CMD_GET_INFO
-       nv_iowr(NV_PGRAPH_FECS_STRAND_CMD, 0x3f, $r12)
-       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.
-       nv_mkio($r8, NV_PGRAPH_FECS_STRAND_SAVE_SWBASE, 0x00)
-       nv_iord($r9, NV_PGRAPH_FECS_STRANDS_CNT, 0x00)
-       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
-#endif
diff --git a/drivers/gpu/drm/nouveau/core/engine/graph/fuc/gpc.fuc b/drivers/gpu/drm/nouveau/core/engine/graph/fuc/gpc.fuc
deleted file mode 100644 (file)
index 7445f12..0000000
+++ /dev/null
@@ -1,378 +0,0 @@
-/* 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
- */
-
-/* TODO
- * - bracket certain functions with scratch writes, useful for debugging
- * - watchdog timer around ctx operations
- */
-
-#ifdef INCLUDE_DATA
-gpc_mmio_list_head:    .b32 #mmio_list_base
-gpc_mmio_list_tail:
-tpc_mmio_list_head:    .b32 #mmio_list_base
-tpc_mmio_list_tail:
-unk_mmio_list_head:    .b32 #mmio_list_base
-unk_mmio_list_tail:    .b32 #mmio_list_base
-
-gpc_id:                        .b32 0
-
-tpc_count:             .b32 0
-tpc_mask:              .b32 0
-
-#if NV_PGRAPH_GPCX_UNK__SIZE > 0
-unk_count:             .b32 0
-unk_mask:              .b32 0
-#endif
-
-cmd_queue:             queue_init
-
-mmio_list_base:
-#endif
-
-#ifdef INCLUDE_CODE
-// reports an exception to the host
-//
-// In: $r15 error code (see os.h)
-//
-error:
-       push $r14
-       nv_wr32(NV_PGRAPH_FECS_CC_SCRATCH_VAL(5), $r15)
-       mov $r15 1
-       nv_wr32(NV_PGRAPH_FECS_INTR_UP_SET, $r15)
-       pop $r14
-       ret
-
-// GPC fuc initialisation, executed by triggering ucode start, will
-// fall through to main loop after completion.
-//
-// Input:
-//   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
-
-       // setup stack
-       nv_iord($r1, NV_PGRAPH_GPCX_GPCCS_CAPS, 0)
-       extr $r1 $r1 9:17
-       shl b32 $r1 8
-       mov $sp $r1
-
-       // enable fifo access
-       mov $r2 NV_PGRAPH_GPCX_GPCCS_ACCESS_FIFO
-       nv_iowr(NV_PGRAPH_GPCX_GPCCS_ACCESS, 0, $r2)
-
-       // setup i0 handler, and route all interrupts to it
-       mov $r1 #ih
-       mov $iv0 $r1
-       nv_iowr(NV_PGRAPH_GPCX_GPCCS_INTR_ROUTE, 0, $r0)
-
-       // enable fifo interrupt
-       mov $r2 NV_PGRAPH_GPCX_GPCCS_INTR_EN_SET_FIFO
-       nv_iowr(NV_PGRAPH_GPCX_GPCCS_INTR_EN_SET, 0, $r2)
-
-       // enable interrupts
-       bset $flags ie0
-
-       // figure out which GPC we are, and how many TPCs we have
-       nv_iord($r2, NV_PGRAPH_GPCX_GPCCS_UNITS, 0)
-       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
-       nv_iord($r2, NV_PGRAPH_GPCX_GPCCS_MYINDEX, 0)
-       st b32 D[$r0 + #gpc_id] $r2
-
-#if NV_PGRAPH_GPCX_UNK__SIZE > 0
-       // figure out which, and how many, UNKs are actually present
-       imm32($r14, 0x500c30)
-       clear b32 $r2
-       clear b32 $r3
-       clear b32 $r4
-       init_unk_loop:
-               call(nv_rd32)
-               cmp b32 $r15 0
-               bra z #init_unk_next
-                       mov $r15 1
-                       shl b32 $r15 $r2
-                       or $r4 $r15
-                       add b32 $r3 1
-               init_unk_next:
-               add b32 $r2 1
-               add b32 $r14 4
-               cmp b32 $r2 NV_PGRAPH_GPCX_UNK__SIZE
-               bra ne #init_unk_loop
-       init_unk_done:
-       st b32 D[$r0 + #unk_count] $r3
-       st b32 D[$r0 + #unk_mask] $r4
-#endif
-
-       // initialise context base, and size tracking
-       nv_iord($r2, NV_PGRAPH_GPCX_GPCCS_CC_SCRATCH_VAL(1), 0)
-       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
-       shr b32 $r5 $r2 8
-       nv_iowr(NV_PGRAPH_GPCX_GPCCS_MMCTX_SAVE_SWBASE, 0, $r5)
-       nv_iowr(NV_PGRAPH_GPCX_GPCCS_MMCTX_LOAD_SWBASE, 0, $r5)
-
-       // calculate GPC mmio context size
-       ld b32 $r14 D[$r0 + #gpc_mmio_list_head]
-       ld b32 $r15 D[$r0 + #gpc_mmio_list_tail]
-       call(mmctx_size)
-       add b32 $r2 $r15
-       add b32 $r3 $r15
-
-       // calculate per-TPC mmio context size
-       ld b32 $r14 D[$r0 + #tpc_mmio_list_head]
-       ld b32 $r15 D[$r0 + #tpc_mmio_list_tail]
-       call(mmctx_size)
-       ld b32 $r14 D[$r0 + #tpc_count]
-       mulu $r14 $r15
-       add b32 $r2 $r14
-       add b32 $r3 $r14
-
-#if NV_PGRAPH_GPCX_UNK__SIZE > 0
-       // calculate per-UNK mmio context size
-       ld b32 $r14 D[$r0 + #unk_mmio_list_head]
-       ld b32 $r15 D[$r0 + #unk_mmio_list_tail]
-       call(mmctx_size)
-       ld b32 $r14 D[$r0 + #unk_count]
-       mulu $r14 $r15
-       add b32 $r2 $r14
-       add b32 $r3 $r14
-#endif
-
-       // round up base/size to 256 byte boundary (for strand SWBASE)
-       shr b32 $r3 2
-       nv_iowr(NV_PGRAPH_GPCX_GPCCS_MMCTX_LOAD_COUNT, 0, $r3) // 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
-       nv_iowr(NV_PGRAPH_GPCX_GPCCS_CC_SCRATCH_VAL(1), 0, $r3)
-       clear b32 $r2
-       bset $r2 31
-       nv_iowr(NV_PGRAPH_GPCX_GPCCS_CC_SCRATCH_SET(0), 0, $r2)
-
-// 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
-       clear b32 $r0
-
-       // incoming fifo command?
-       nv_iord($r10, NV_PGRAPH_GPCX_GPCCS_INTR, 0)
-       and $r11 $r10 NV_PGRAPH_GPCX_GPCCS_INTR_FIFO
-       bra e #ih_no_fifo
-               // queue incoming fifo command for later processing
-               mov $r13 #cmd_queue
-               nv_iord($r14, NV_PGRAPH_GPCX_GPCCS_FIFO_CMD, 0)
-               nv_iord($r15, NV_PGRAPH_GPCX_GPCCS_FIFO_DATA, 0)
-               call(queue_put)
-               mov $r14 1
-               nv_iowr(NV_PGRAPH_GPCX_GPCCS_FIFO_ACK, 0, $r14)
-
-       // ack, and wake up main()
-       ih_no_fifo:
-       nv_iowr(NV_PGRAPH_GPCX_GPCCS_INTR_ACK, 0, $r10)
-
-       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
-       nv_wr32(0x409418, $r15) // 0x409418 - HUB_BAR_SET
-       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 $r15 NV_PGRAPH_GPCX_GPCCS_RED_SWITCH_POWER
-       nv_iowr(NV_PGRAPH_GPCX_GPCCS_RED_SWITCH, 0, $r15)
-       mov $r14 8
-       ctx_redswitch_delay:
-               sub b32 $r14 1
-               bra ne #ctx_redswitch_delay
-       or $r15 NV_PGRAPH_GPCX_GPCCS_RED_SWITCH_UNK11
-       or $r15 NV_PGRAPH_GPCX_GPCCS_RED_SWITCH_ENABLE
-       nv_iowr(NV_PGRAPH_GPCX_GPCCS_RED_SWITCH, 0, $r15)
-       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
-       nv_iowr(NV_PGRAPH_GPCX_GPCCS_MEM_BASE, 0, $r15)
-       bra not $p1 #ctx_xfer_not_load
-               call(ctx_redswitch)
-       ctx_xfer_not_load:
-
-       // strands
-       call(strand_pre)
-       clear b32 $r2
-       nv_iowr(NV_PGRAPH_GPCX_GPCCS_STRAND_SELECT, 0x3f, $r2)
-       xbit $r2 $flags $p1     // SAVE/LOAD
-       add b32 $r2 NV_PGRAPH_GPCX_GPCCS_STRAND_CMD_SAVE
-       nv_iowr(NV_PGRAPH_GPCX_GPCCS_STRAND_CMD, 0x3f, $r2)
-
-       // mmio context
-       xbit $r10 $flags $p1    // direction
-       or $r10 2               // first
-       imm32($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
-#if !NV_PGRAPH_GPCX_UNK__SIZE
-       or $r10 4               // last
-#endif
-       imm32($r11, 0x504000)
-       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)
-
-#if NV_PGRAPH_GPCX_UNK__SIZE > 0
-       // per-UNK mmio context
-       xbit $r10 $flags $p1    // direction
-       or $r10 4               // last
-       imm32($r11, 0x503000)
-       ld b32 $r12 D[$r0 + #gpc_id]
-       shl b32 $r12 15
-       add b32 $r11 $r12       // base = NV_PGRAPH_GPCn_UNK0
-       ld b32 $r12 D[$r0 + #unk_mmio_list_head]
-       ld b32 $r13 D[$r0 + #unk_mmio_list_tail]
-       ld b32 $r15 D[$r0 + #unk_mask]
-       mov $r14 0x200          // stride = 0x200
-       call(mmctx_xfer)
-#endif
-
-       // 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:
-               call(strand_post)
-
-       // mark completion in HUB's barrier
-       ctx_xfer_done:
-       call(hub_barrier_done)
-       ret
-#endif
diff --git a/drivers/gpu/drm/nouveau/core/engine/graph/fuc/gpcgm107.fuc5 b/drivers/gpu/drm/nouveau/core/engine/graph/fuc/gpcgm107.fuc5
deleted file mode 100644 (file)
index e730603..0000000
+++ /dev/null
@@ -1,42 +0,0 @@
-/*
- * Copyright 2013 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 <bskeggs@redhat.com>
- */
-
-#define NV_PGRAPH_GPCX_UNK__SIZE                                     0x00000002
-
-#define CHIPSET GK208
-#include "macros.fuc"
-
-.section #gm107_grgpc_data
-#define INCLUDE_DATA
-#include "com.fuc"
-#include "gpc.fuc"
-#undef INCLUDE_DATA
-
-.section #gm107_grgpc_code
-#define INCLUDE_CODE
-bra #init
-#include "com.fuc"
-#include "gpc.fuc"
-.align 256
-#undef INCLUDE_CODE
diff --git a/drivers/gpu/drm/nouveau/core/engine/graph/fuc/gpcgm107.fuc5.h b/drivers/gpu/drm/nouveau/core/engine/graph/fuc/gpcgm107.fuc5.h
deleted file mode 100644 (file)
index 6d53b67..0000000
+++ /dev/null
@@ -1,473 +0,0 @@
-uint32_t gm107_grgpc_data[] = {
-/* 0x0000: gpc_mmio_list_head */
-       0x0000006c,
-/* 0x0004: gpc_mmio_list_tail */
-/* 0x0004: tpc_mmio_list_head */
-       0x0000006c,
-/* 0x0008: tpc_mmio_list_tail */
-/* 0x0008: unk_mmio_list_head */
-       0x0000006c,
-/* 0x000c: unk_mmio_list_tail */
-       0x0000006c,
-/* 0x0010: gpc_id */
-       0x00000000,
-/* 0x0014: tpc_count */
-       0x00000000,
-/* 0x0018: tpc_mask */
-       0x00000000,
-/* 0x001c: unk_count */
-       0x00000000,
-/* 0x0020: unk_mask */
-       0x00000000,
-/* 0x0024: cmd_queue */
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-};
-
-uint32_t gm107_grgpc_code[] = {
-       0x03140ef5,
-/* 0x0004: queue_put */
-       0x9800d898,
-       0x86f001d9,
-       0xf489a408,
-       0x020f0b1b,
-       0x0002f87e,
-/* 0x001a: queue_put_next */
-       0x98c400f8,
-       0x0384b607,
-       0xb6008dbb,
-       0x8eb50880,
-       0x018fb500,
-       0xf00190b6,
-       0xd9b50f94,
-/* 0x0037: queue_get */
-       0xf400f801,
-       0xd8980131,
-       0x01d99800,
-       0x0bf489a4,
-       0x0789c421,
-       0xbb0394b6,
-       0x90b6009d,
-       0x009e9808,
-       0xb6019f98,
-       0x84f00180,
-       0x00d8b50f,
-/* 0x0063: queue_get_done */
-       0xf80132f4,
-/* 0x0065: nv_rd32 */
-       0xf0ecb200,
-       0x00801fc9,
-       0x0cf601ca,
-/* 0x0073: nv_rd32_wait */
-       0x8c04bd00,
-       0xcf01ca00,
-       0xccc800cc,
-       0xf61bf41f,
-       0xec7e060a,
-       0x008f0000,
-       0xffcf01cb,
-/* 0x008f: nv_wr32 */
-       0x8000f800,
-       0xf601cc00,
-       0x04bd000f,
-       0xc9f0ecb2,
-       0x1ec9f01f,
-       0x01ca0080,
-       0xbd000cf6,
-/* 0x00a9: nv_wr32_wait */
-       0xca008c04,
-       0x00cccf01,
-       0xf41fccc8,
-       0x00f8f61b,
-/* 0x00b8: wait_donez */
-       0x99f094bd,
-       0x37008000,
-       0x0009f602,
-       0x008004bd,
-       0x0af60206,
-/* 0x00cf: wait_donez_ne */
-       0x8804bd00,
-       0xcf010000,
-       0x8aff0088,
-       0xf61bf488,
-       0x99f094bd,
-       0x17008000,
-       0x0009f602,
-       0x00f804bd,
-/* 0x00ec: wait_doneo */
-       0x99f094bd,
-       0x37008000,
-       0x0009f602,
-       0x008004bd,
-       0x0af60206,
-/* 0x0103: wait_doneo_e */
-       0x8804bd00,
-       0xcf010000,
-       0x8aff0088,
-       0xf60bf488,
-       0x99f094bd,
-       0x17008000,
-       0x0009f602,
-       0x00f804bd,
-/* 0x0120: mmctx_size */
-/* 0x0122: nv_mmctx_size_loop */
-       0xe89894bd,
-       0x1a85b600,
-       0xb60180b6,
-       0x98bb0284,
-       0x04e0b600,
-       0x1bf4efa4,
-       0xf89fb2ec,
-/* 0x013d: mmctx_xfer */
-       0xf094bd00,
-       0x00800199,
-       0x09f60237,
-       0xbd04bd00,
-       0x05bbfd94,
-       0x800f0bf4,
-       0xf601c400,
-       0x04bd000b,
-/* 0x015f: mmctx_base_disabled */
-       0xfd0099f0,
-       0x0bf405ee,
-       0xc6008018,
-       0x000ef601,
-       0x008004bd,
-       0x0ff601c7,
-       0xf004bd00,
-/* 0x017a: mmctx_multi_disabled */
-       0xabc80199,
-       0x10b4b600,
-       0xc80cb9f0,
-       0xe4b601ae,
-       0x05befd11,
-       0x01c50080,
-       0xbd000bf6,
-/* 0x0195: mmctx_exec_loop */
-/* 0x0195: mmctx_wait_free */
-       0xc5008e04,
-       0x00eecf01,
-       0xf41fe4f0,
-       0xce98f60b,
-       0x05e9fd00,
-       0x01c80080,
-       0xbd000ef6,
-       0x04c0b604,
-       0x1bf4cda4,
-       0x02abc8df,
-/* 0x01bf: mmctx_fini_wait */
-       0x8b1c1bf4,
-       0xcf01c500,
-       0xb4f000bb,
-       0x10b4b01f,
-       0x0af31bf4,
-       0x00b87e05,
-       0x250ef400,
-/* 0x01d8: mmctx_stop */
-       0xb600abc8,
-       0xb9f010b4,
-       0x12b9f00c,
-       0x01c50080,
-       0xbd000bf6,
-/* 0x01ed: mmctx_stop_wait */
-       0xc5008b04,
-       0x00bbcf01,
-       0xf412bbc8,
-/* 0x01fa: mmctx_done */
-       0x94bdf61b,
-       0x800199f0,
-       0xf6021700,
-       0x04bd0009,
-/* 0x020a: strand_wait */
-       0xa0f900f8,
-       0xb87e020a,
-       0xa0fc0000,
-/* 0x0216: strand_pre */
-       0x0c0900f8,
-       0x024afc80,
-       0xbd0009f6,
-       0x020a7e04,
-/* 0x0227: strand_post */
-       0x0900f800,
-       0x4afc800d,
-       0x0009f602,
-       0x0a7e04bd,
-       0x00f80002,
-/* 0x0238: strand_set */
-       0xfc800f0c,
-       0x0cf6024f,
-       0x0c04bd00,
-       0x4afc800b,
-       0x000cf602,
-       0xfc8004bd,
-       0x0ef6024f,
-       0x0c04bd00,
-       0x4afc800a,
-       0x000cf602,
-       0x0a7e04bd,
-       0x00f80002,
-/* 0x0268: strand_ctx_init */
-       0x99f094bd,
-       0x37008003,
-       0x0009f602,
-       0x167e04bd,
-       0x030e0002,
-       0x0002387e,
-       0xfc80c4bd,
-       0x0cf60247,
-       0x0c04bd00,
-       0x4afc8001,
-       0x000cf602,
-       0x0a7e04bd,
-       0x0c920002,
-       0x46fc8001,
-       0x000cf602,
-       0x020c04bd,
-       0x024afc80,
-       0xbd000cf6,
-       0x020a7e04,
-       0x02277e00,
-       0x42008800,
-       0x20008902,
-       0x0099cf02,
-/* 0x02c7: ctx_init_strand_loop */
-       0xf608fe95,
-       0x8ef6008e,
-       0x808acf40,
-       0xb606a5b6,
-       0xeabb01a0,
-       0x0480b600,
-       0xf40192b6,
-       0xe4b6e81b,
-       0xf2efbc08,
-       0x99f094bd,
-       0x17008003,
-       0x0009f602,
-       0x00f804bd,
-/* 0x02f8: error */
-       0xffb2e0f9,
-       0x4098148e,
-       0x00008f7e,
-       0xffb2010f,
-       0x409c1c8e,
-       0x00008f7e,
-       0x00f8e0fc,
-/* 0x0314: init */
-       0x004104bd,
-       0x0011cf42,
-       0x010911e7,
-       0xfe0814b6,
-       0x02020014,
-       0xf6120040,
-       0x04bd0002,
-       0xfe047241,
-       0x00400010,
-       0x0000f607,
-       0x040204bd,
-       0xf6040040,
-       0x04bd0002,
-       0x821031f4,
-       0xcf018200,
-       0x01030022,
-       0xbb1f24f0,
-       0x32b60432,
-       0x0502b501,
-       0x820603b5,
-       0xcf018600,
-       0x02b50022,
-       0x0c308e04,
-       0xbd24bd50,
-/* 0x0377: init_unk_loop */
-       0x7e44bd34,
-       0xb0000065,
-       0x0bf400f6,
-       0xbb010f0e,
-       0x4ffd04f2,
-       0x0130b605,
-/* 0x038c: init_unk_next */
-       0xb60120b6,
-       0x26b004e0,
-       0xe21bf402,
-/* 0x0398: init_unk_done */
-       0xb50703b5,
-       0x00820804,
-       0x22cf0201,
-       0x9534bd00,
-       0x00800825,
-       0x05f601c0,
-       0x8004bd00,
-       0xf601c100,
-       0x04bd0005,
-       0x98000e98,
-       0x207e010f,
-       0x2fbb0001,
-       0x003fbb00,
-       0x98010e98,
-       0x207e020f,
-       0x0e980001,
-       0x00effd05,
-       0xbb002ebb,
-       0x0e98003e,
-       0x030f9802,
-       0x0001207e,
-       0xfd070e98,
-       0x2ebb00ef,
-       0x003ebb00,
-       0x800235b6,
-       0xf601d300,
-       0x04bd0003,
-       0xb60825b6,
-       0x20b60635,
-       0x0130b601,
-       0xb60824b6,
-       0x2fb20834,
-       0x0002687e,
-       0x80003fbb,
-       0xf6020100,
-       0x04bd0003,
-       0x29f024bd,
-       0x3000801f,
-       0x0002f602,
-/* 0x0436: main */
-       0x31f404bd,
-       0x0028f400,
-       0x377e240d,
-       0x01f40000,
-       0x04e4b0f4,
-       0xfe1d18f4,
-       0x06020181,
-       0x12fd20bd,
-       0x01e4b604,
-       0xfe051efd,
-       0x097e0018,
-       0x0ef40005,
-/* 0x0465: main_not_ctx_xfer */
-       0x10ef94d4,
-       0x7e01f5f0,
-       0xf40002f8,
-/* 0x0472: ih */
-       0x80f9c70e,
-       0xf90188fe,
-       0xf990f980,
-       0xf9b0f9a0,
-       0xf9e0f9d0,
-       0x4a04bdf0,
-       0xaacf0200,
-       0x04abc400,
-       0x0d1f0bf4,
-       0x1a004e24,
-       0x4f00eecf,
-       0xffcf1900,
-       0x00047e00,
-       0x40010e00,
-       0x0ef61d00,
-/* 0x04af: ih_no_fifo */
-       0x4004bd00,
-       0x0af60100,
-       0xfc04bd00,
-       0xfce0fcf0,
-       0xfcb0fcd0,
-       0xfc90fca0,
-       0x0088fe80,
-       0x32f480fc,
-/* 0x04cf: hub_barrier_done */
-       0x0f01f800,
-       0x040e9801,
-       0xb204febb,
-       0x94188eff,
-       0x008f7e40,
-/* 0x04e3: ctx_redswitch */
-       0x0f00f800,
-       0x85008020,
-       0x000ff601,
-       0x080e04bd,
-/* 0x04f0: ctx_redswitch_delay */
-       0xf401e2b6,
-       0xf5f1fd1b,
-       0xf5f10800,
-       0x00800200,
-       0x0ff60185,
-       0xf804bd00,
-/* 0x0509: ctx_xfer */
-       0x81008000,
-       0x000ff602,
-       0x11f404bd,
-       0x04e37e07,
-/* 0x0519: ctx_xfer_not_load */
-       0x02167e00,
-       0x8024bd00,
-       0xf60247fc,
-       0x04bd0002,
-       0xb6012cf0,
-       0xfc800320,
-       0x02f6024a,
-       0xf004bd00,
-       0xa5f001ac,
-       0x00008b02,
-       0x040c9850,
-       0xbb0fc4b6,
-       0x0c9800bc,
-       0x010d9800,
-       0x3d7e000e,
-       0xacf00001,
-       0x40008b01,
-       0x040c9850,
-       0xbb0fc4b6,
-       0x0c9800bc,
-       0x020d9801,
-       0x4e060f98,
-       0x3d7e0800,
-       0xacf00001,
-       0x04a5f001,
-       0x5030008b,
-       0xb6040c98,
-       0xbcbb0fc4,
-       0x020c9800,
-       0x98030d98,
-       0x004e080f,
-       0x013d7e02,
-       0x020a7e00,
-       0x0601f400,
-/* 0x05a3: ctx_xfer_post */
-       0x7e0712f4,
-/* 0x05a7: ctx_xfer_done */
-       0x7e000227,
-       0xf80004cf,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-};
diff --git a/drivers/gpu/drm/nouveau/core/engine/graph/fuc/gpcnv108.fuc5 b/drivers/gpu/drm/nouveau/core/engine/graph/fuc/gpcnv108.fuc5
deleted file mode 100644 (file)
index bd30262..0000000
+++ /dev/null
@@ -1,42 +0,0 @@
-/*
- * Copyright 2013 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 <bskeggs@redhat.com>
- */
-
-#define NV_PGRAPH_GPCX_UNK__SIZE                                     0x00000001
-
-#define CHIPSET GK208
-#include "macros.fuc"
-
-.section #nv108_grgpc_data
-#define INCLUDE_DATA
-#include "com.fuc"
-#include "gpc.fuc"
-#undef INCLUDE_DATA
-
-.section #nv108_grgpc_code
-#define INCLUDE_CODE
-bra #init
-#include "com.fuc"
-#include "gpc.fuc"
-.align 256
-#undef INCLUDE_CODE
diff --git a/drivers/gpu/drm/nouveau/core/engine/graph/fuc/gpcnv108.fuc5.h b/drivers/gpu/drm/nouveau/core/engine/graph/fuc/gpcnv108.fuc5.h
deleted file mode 100644 (file)
index 3192270..0000000
+++ /dev/null
@@ -1,473 +0,0 @@
-uint32_t nv108_grgpc_data[] = {
-/* 0x0000: gpc_mmio_list_head */
-       0x0000006c,
-/* 0x0004: gpc_mmio_list_tail */
-/* 0x0004: tpc_mmio_list_head */
-       0x0000006c,
-/* 0x0008: tpc_mmio_list_tail */
-/* 0x0008: unk_mmio_list_head */
-       0x0000006c,
-/* 0x000c: unk_mmio_list_tail */
-       0x0000006c,
-/* 0x0010: gpc_id */
-       0x00000000,
-/* 0x0014: tpc_count */
-       0x00000000,
-/* 0x0018: tpc_mask */
-       0x00000000,
-/* 0x001c: unk_count */
-       0x00000000,
-/* 0x0020: unk_mask */
-       0x00000000,
-/* 0x0024: cmd_queue */
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-};
-
-uint32_t nv108_grgpc_code[] = {
-       0x03140ef5,
-/* 0x0004: queue_put */
-       0x9800d898,
-       0x86f001d9,
-       0xf489a408,
-       0x020f0b1b,
-       0x0002f87e,
-/* 0x001a: queue_put_next */
-       0x98c400f8,
-       0x0384b607,
-       0xb6008dbb,
-       0x8eb50880,
-       0x018fb500,
-       0xf00190b6,
-       0xd9b50f94,
-/* 0x0037: queue_get */
-       0xf400f801,
-       0xd8980131,
-       0x01d99800,
-       0x0bf489a4,
-       0x0789c421,
-       0xbb0394b6,
-       0x90b6009d,
-       0x009e9808,
-       0xb6019f98,
-       0x84f00180,
-       0x00d8b50f,
-/* 0x0063: queue_get_done */
-       0xf80132f4,
-/* 0x0065: nv_rd32 */
-       0xf0ecb200,
-       0x00801fc9,
-       0x0cf601ca,
-/* 0x0073: nv_rd32_wait */
-       0x8c04bd00,
-       0xcf01ca00,
-       0xccc800cc,
-       0xf61bf41f,
-       0xec7e060a,
-       0x008f0000,
-       0xffcf01cb,
-/* 0x008f: nv_wr32 */
-       0x8000f800,
-       0xf601cc00,
-       0x04bd000f,
-       0xc9f0ecb2,
-       0x1ec9f01f,
-       0x01ca0080,
-       0xbd000cf6,
-/* 0x00a9: nv_wr32_wait */
-       0xca008c04,
-       0x00cccf01,
-       0xf41fccc8,
-       0x00f8f61b,
-/* 0x00b8: wait_donez */
-       0x99f094bd,
-       0x37008000,
-       0x0009f602,
-       0x008004bd,
-       0x0af60206,
-/* 0x00cf: wait_donez_ne */
-       0x8804bd00,
-       0xcf010000,
-       0x8aff0088,
-       0xf61bf488,
-       0x99f094bd,
-       0x17008000,
-       0x0009f602,
-       0x00f804bd,
-/* 0x00ec: wait_doneo */
-       0x99f094bd,
-       0x37008000,
-       0x0009f602,
-       0x008004bd,
-       0x0af60206,
-/* 0x0103: wait_doneo_e */
-       0x8804bd00,
-       0xcf010000,
-       0x8aff0088,
-       0xf60bf488,
-       0x99f094bd,
-       0x17008000,
-       0x0009f602,
-       0x00f804bd,
-/* 0x0120: mmctx_size */
-/* 0x0122: nv_mmctx_size_loop */
-       0xe89894bd,
-       0x1a85b600,
-       0xb60180b6,
-       0x98bb0284,
-       0x04e0b600,
-       0x1bf4efa4,
-       0xf89fb2ec,
-/* 0x013d: mmctx_xfer */
-       0xf094bd00,
-       0x00800199,
-       0x09f60237,
-       0xbd04bd00,
-       0x05bbfd94,
-       0x800f0bf4,
-       0xf601c400,
-       0x04bd000b,
-/* 0x015f: mmctx_base_disabled */
-       0xfd0099f0,
-       0x0bf405ee,
-       0xc6008018,
-       0x000ef601,
-       0x008004bd,
-       0x0ff601c7,
-       0xf004bd00,
-/* 0x017a: mmctx_multi_disabled */
-       0xabc80199,
-       0x10b4b600,
-       0xc80cb9f0,
-       0xe4b601ae,
-       0x05befd11,
-       0x01c50080,
-       0xbd000bf6,
-/* 0x0195: mmctx_exec_loop */
-/* 0x0195: mmctx_wait_free */
-       0xc5008e04,
-       0x00eecf01,
-       0xf41fe4f0,
-       0xce98f60b,
-       0x05e9fd00,
-       0x01c80080,
-       0xbd000ef6,
-       0x04c0b604,
-       0x1bf4cda4,
-       0x02abc8df,
-/* 0x01bf: mmctx_fini_wait */
-       0x8b1c1bf4,
-       0xcf01c500,
-       0xb4f000bb,
-       0x10b4b01f,
-       0x0af31bf4,
-       0x00b87e05,
-       0x250ef400,
-/* 0x01d8: mmctx_stop */
-       0xb600abc8,
-       0xb9f010b4,
-       0x12b9f00c,
-       0x01c50080,
-       0xbd000bf6,
-/* 0x01ed: mmctx_stop_wait */
-       0xc5008b04,
-       0x00bbcf01,
-       0xf412bbc8,
-/* 0x01fa: mmctx_done */
-       0x94bdf61b,
-       0x800199f0,
-       0xf6021700,
-       0x04bd0009,
-/* 0x020a: strand_wait */
-       0xa0f900f8,
-       0xb87e020a,
-       0xa0fc0000,
-/* 0x0216: strand_pre */
-       0x0c0900f8,
-       0x024afc80,
-       0xbd0009f6,
-       0x020a7e04,
-/* 0x0227: strand_post */
-       0x0900f800,
-       0x4afc800d,
-       0x0009f602,
-       0x0a7e04bd,
-       0x00f80002,
-/* 0x0238: strand_set */
-       0xfc800f0c,
-       0x0cf6024f,
-       0x0c04bd00,
-       0x4afc800b,
-       0x000cf602,
-       0xfc8004bd,
-       0x0ef6024f,
-       0x0c04bd00,
-       0x4afc800a,
-       0x000cf602,
-       0x0a7e04bd,
-       0x00f80002,
-/* 0x0268: strand_ctx_init */
-       0x99f094bd,
-       0x37008003,
-       0x0009f602,
-       0x167e04bd,
-       0x030e0002,
-       0x0002387e,
-       0xfc80c4bd,
-       0x0cf60247,
-       0x0c04bd00,
-       0x4afc8001,
-       0x000cf602,
-       0x0a7e04bd,
-       0x0c920002,
-       0x46fc8001,
-       0x000cf602,
-       0x020c04bd,
-       0x024afc80,
-       0xbd000cf6,
-       0x020a7e04,
-       0x02277e00,
-       0x42008800,
-       0x20008902,
-       0x0099cf02,
-/* 0x02c7: ctx_init_strand_loop */
-       0xf608fe95,
-       0x8ef6008e,
-       0x808acf40,
-       0xb606a5b6,
-       0xeabb01a0,
-       0x0480b600,
-       0xf40192b6,
-       0xe4b6e81b,
-       0xf2efbc08,
-       0x99f094bd,
-       0x17008003,
-       0x0009f602,
-       0x00f804bd,
-/* 0x02f8: error */
-       0xffb2e0f9,
-       0x4098148e,
-       0x00008f7e,
-       0xffb2010f,
-       0x409c1c8e,
-       0x00008f7e,
-       0x00f8e0fc,
-/* 0x0314: init */
-       0x004104bd,
-       0x0011cf42,
-       0x010911e7,
-       0xfe0814b6,
-       0x02020014,
-       0xf6120040,
-       0x04bd0002,
-       0xfe047241,
-       0x00400010,
-       0x0000f607,
-       0x040204bd,
-       0xf6040040,
-       0x04bd0002,
-       0x821031f4,
-       0xcf018200,
-       0x01030022,
-       0xbb1f24f0,
-       0x32b60432,
-       0x0502b501,
-       0x820603b5,
-       0xcf018600,
-       0x02b50022,
-       0x0c308e04,
-       0xbd24bd50,
-/* 0x0377: init_unk_loop */
-       0x7e44bd34,
-       0xb0000065,
-       0x0bf400f6,
-       0xbb010f0e,
-       0x4ffd04f2,
-       0x0130b605,
-/* 0x038c: init_unk_next */
-       0xb60120b6,
-       0x26b004e0,
-       0xe21bf401,
-/* 0x0398: init_unk_done */
-       0xb50703b5,
-       0x00820804,
-       0x22cf0201,
-       0x9534bd00,
-       0x00800825,
-       0x05f601c0,
-       0x8004bd00,
-       0xf601c100,
-       0x04bd0005,
-       0x98000e98,
-       0x207e010f,
-       0x2fbb0001,
-       0x003fbb00,
-       0x98010e98,
-       0x207e020f,
-       0x0e980001,
-       0x00effd05,
-       0xbb002ebb,
-       0x0e98003e,
-       0x030f9802,
-       0x0001207e,
-       0xfd070e98,
-       0x2ebb00ef,
-       0x003ebb00,
-       0x800235b6,
-       0xf601d300,
-       0x04bd0003,
-       0xb60825b6,
-       0x20b60635,
-       0x0130b601,
-       0xb60824b6,
-       0x2fb20834,
-       0x0002687e,
-       0x80003fbb,
-       0xf6020100,
-       0x04bd0003,
-       0x29f024bd,
-       0x3000801f,
-       0x0002f602,
-/* 0x0436: main */
-       0x31f404bd,
-       0x0028f400,
-       0x377e240d,
-       0x01f40000,
-       0x04e4b0f4,
-       0xfe1d18f4,
-       0x06020181,
-       0x12fd20bd,
-       0x01e4b604,
-       0xfe051efd,
-       0x097e0018,
-       0x0ef40005,
-/* 0x0465: main_not_ctx_xfer */
-       0x10ef94d4,
-       0x7e01f5f0,
-       0xf40002f8,
-/* 0x0472: ih */
-       0x80f9c70e,
-       0xf90188fe,
-       0xf990f980,
-       0xf9b0f9a0,
-       0xf9e0f9d0,
-       0x4a04bdf0,
-       0xaacf0200,
-       0x04abc400,
-       0x0d1f0bf4,
-       0x1a004e24,
-       0x4f00eecf,
-       0xffcf1900,
-       0x00047e00,
-       0x40010e00,
-       0x0ef61d00,
-/* 0x04af: ih_no_fifo */
-       0x4004bd00,
-       0x0af60100,
-       0xfc04bd00,
-       0xfce0fcf0,
-       0xfcb0fcd0,
-       0xfc90fca0,
-       0x0088fe80,
-       0x32f480fc,
-/* 0x04cf: hub_barrier_done */
-       0x0f01f800,
-       0x040e9801,
-       0xb204febb,
-       0x94188eff,
-       0x008f7e40,
-/* 0x04e3: ctx_redswitch */
-       0x0f00f800,
-       0x85008020,
-       0x000ff601,
-       0x080e04bd,
-/* 0x04f0: ctx_redswitch_delay */
-       0xf401e2b6,
-       0xf5f1fd1b,
-       0xf5f10800,
-       0x00800200,
-       0x0ff60185,
-       0xf804bd00,
-/* 0x0509: ctx_xfer */
-       0x81008000,
-       0x000ff602,
-       0x11f404bd,
-       0x04e37e07,
-/* 0x0519: ctx_xfer_not_load */
-       0x02167e00,
-       0x8024bd00,
-       0xf60247fc,
-       0x04bd0002,
-       0xb6012cf0,
-       0xfc800320,
-       0x02f6024a,
-       0xf004bd00,
-       0xa5f001ac,
-       0x00008b02,
-       0x040c9850,
-       0xbb0fc4b6,
-       0x0c9800bc,
-       0x010d9800,
-       0x3d7e000e,
-       0xacf00001,
-       0x40008b01,
-       0x040c9850,
-       0xbb0fc4b6,
-       0x0c9800bc,
-       0x020d9801,
-       0x4e060f98,
-       0x3d7e0800,
-       0xacf00001,
-       0x04a5f001,
-       0x5030008b,
-       0xb6040c98,
-       0xbcbb0fc4,
-       0x020c9800,
-       0x98030d98,
-       0x004e080f,
-       0x013d7e02,
-       0x020a7e00,
-       0x0601f400,
-/* 0x05a3: ctx_xfer_post */
-       0x7e0712f4,
-/* 0x05a7: ctx_xfer_done */
-       0x7e000227,
-       0xf80004cf,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-};
diff --git a/drivers/gpu/drm/nouveau/core/engine/graph/fuc/gpcnvc0.fuc b/drivers/gpu/drm/nouveau/core/engine/graph/fuc/gpcnvc0.fuc
deleted file mode 100644 (file)
index 5ae06a2..0000000
+++ /dev/null
@@ -1,42 +0,0 @@
-/*
- * Copyright 2013 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 <bskeggs@redhat.com>
- */
-
-#define NV_PGRAPH_GPCX_UNK__SIZE                                     0x00000000
-
-#define CHIPSET GF100
-#include "macros.fuc"
-
-.section #nvc0_grgpc_data
-#define INCLUDE_DATA
-#include "com.fuc"
-#include "gpc.fuc"
-#undef INCLUDE_DATA
-
-.section #nvc0_grgpc_code
-#define INCLUDE_CODE
-bra #init
-#include "com.fuc"
-#include "gpc.fuc"
-.align 256
-#undef INCLUDE_CODE
diff --git a/drivers/gpu/drm/nouveau/core/engine/graph/fuc/gpcnvc0.fuc.h b/drivers/gpu/drm/nouveau/core/engine/graph/fuc/gpcnvc0.fuc.h
deleted file mode 100644 (file)
index 325cc7b..0000000
+++ /dev/null
@@ -1,530 +0,0 @@
-uint32_t nvc0_grgpc_data[] = {
-/* 0x0000: gpc_mmio_list_head */
-       0x00000064,
-/* 0x0004: gpc_mmio_list_tail */
-/* 0x0004: tpc_mmio_list_head */
-       0x00000064,
-/* 0x0008: tpc_mmio_list_tail */
-/* 0x0008: unk_mmio_list_head */
-       0x00000064,
-/* 0x000c: unk_mmio_list_tail */
-       0x00000064,
-/* 0x0010: gpc_id */
-       0x00000000,
-/* 0x0014: tpc_count */
-       0x00000000,
-/* 0x0018: tpc_mask */
-       0x00000000,
-/* 0x001c: cmd_queue */
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-};
-
-uint32_t nvc0_grgpc_code[] = {
-       0x03a10ef5,
-/* 0x0004: queue_put */
-       0x9800d898,
-       0x86f001d9,
-       0x0489b808,
-       0xf00c1bf4,
-       0x21f502f7,
-       0x00f8037e,
-/* 0x001c: queue_put_next */
-       0xb60798c4,
-       0x8dbb0384,
-       0x0880b600,
-       0x80008e80,
-       0x90b6018f,
-       0x0f94f001,
-       0xf801d980,
-/* 0x0039: queue_get */
-       0x0131f400,
-       0x9800d898,
-       0x89b801d9,
-       0x210bf404,
-       0xb60789c4,
-       0x9dbb0394,
-       0x0890b600,
-       0x98009e98,
-       0x80b6019f,
-       0x0f84f001,
-       0xf400d880,
-/* 0x0066: queue_get_done */
-       0x00f80132,
-/* 0x0068: nv_rd32 */
-       0xf002ecb9,
-       0x07f11fc9,
-       0x03f0ca00,
-       0x000cd001,
-/* 0x007a: nv_rd32_wait */
-       0xc7f104bd,
-       0xc3f0ca00,
-       0x00cccf01,
-       0xf41fccc8,
-       0xa7f0f31b,
-       0x1021f506,
-       0x00f7f101,
-       0x01f3f0cb,
-       0xf800ffcf,
-/* 0x009d: nv_wr32 */
-       0x0007f100,
-       0x0103f0cc,
-       0xbd000fd0,
-       0x02ecb904,
-       0xf01fc9f0,
-       0x07f11ec9,
-       0x03f0ca00,
-       0x000cd001,
-/* 0x00be: nv_wr32_wait */
-       0xc7f104bd,
-       0xc3f0ca00,
-       0x00cccf01,
-       0xf41fccc8,
-       0x00f8f31b,
-/* 0x00d0: wait_donez */
-       0x99f094bd,
-       0x0007f100,
-       0x0203f00f,
-       0xbd0009d0,
-       0x0007f104,
-       0x0203f006,
-       0xbd000ad0,
-/* 0x00ed: wait_donez_ne */
-       0x0087f104,
-       0x0183f000,
-       0xff0088cf,
-       0x1bf4888a,
-       0xf094bdf3,
-       0x07f10099,
-       0x03f01700,
-       0x0009d002,
-       0x00f804bd,
-/* 0x0110: wait_doneo */
-       0x99f094bd,
-       0x0007f100,
-       0x0203f00f,
-       0xbd0009d0,
-       0x0007f104,
-       0x0203f006,
-       0xbd000ad0,
-/* 0x012d: wait_doneo_e */
-       0x0087f104,
-       0x0183f000,
-       0xff0088cf,
-       0x0bf4888a,
-       0xf094bdf3,
-       0x07f10099,
-       0x03f01700,
-       0x0009d002,
-       0x00f804bd,
-/* 0x0150: mmctx_size */
-/* 0x0152: nv_mmctx_size_loop */
-       0xe89894bd,
-       0x1a85b600,
-       0xb60180b6,
-       0x98bb0284,
-       0x04e0b600,
-       0xf404efb8,
-       0x9fb9eb1b,
-/* 0x016f: mmctx_xfer */
-       0xbd00f802,
-       0x0199f094,
-       0x0f0007f1,
-       0xd00203f0,
-       0x04bd0009,
-       0xbbfd94bd,
-       0x120bf405,
-       0xc40007f1,
-       0xd00103f0,
-       0x04bd000b,
-/* 0x0197: mmctx_base_disabled */
-       0xfd0099f0,
-       0x0bf405ee,
-       0x0007f11e,
-       0x0103f0c6,
-       0xbd000ed0,
-       0x0007f104,
-       0x0103f0c7,
-       0xbd000fd0,
-       0x0199f004,
-/* 0x01b8: mmctx_multi_disabled */
-       0xb600abc8,
-       0xb9f010b4,
-       0x01aec80c,
-       0xfd11e4b6,
-       0x07f105be,
-       0x03f0c500,
-       0x000bd001,
-/* 0x01d6: mmctx_exec_loop */
-/* 0x01d6: mmctx_wait_free */
-       0xe7f104bd,
-       0xe3f0c500,
-       0x00eecf01,
-       0xf41fe4f0,
-       0xce98f30b,
-       0x05e9fd00,
-       0xc80007f1,
-       0xd00103f0,
-       0x04bd000e,
-       0xb804c0b6,
-       0x1bf404cd,
-       0x02abc8d8,
-/* 0x0207: mmctx_fini_wait */
-       0xf11f1bf4,
-       0xf0c500b7,
-       0xbbcf01b3,
-       0x1fb4f000,
-       0xf410b4b0,
-       0xa7f0f01b,
-       0xd021f405,
-/* 0x0223: mmctx_stop */
-       0xc82b0ef4,
-       0xb4b600ab,
-       0x0cb9f010,
-       0xf112b9f0,
-       0xf0c50007,
-       0x0bd00103,
-/* 0x023b: mmctx_stop_wait */
-       0xf104bd00,
-       0xf0c500b7,
-       0xbbcf01b3,
-       0x12bbc800,
-/* 0x024b: mmctx_done */
-       0xbdf31bf4,
-       0x0199f094,
-       0x170007f1,
-       0xd00203f0,
-       0x04bd0009,
-/* 0x025e: strand_wait */
-       0xa0f900f8,
-       0xf402a7f0,
-       0xa0fcd021,
-/* 0x026a: strand_pre */
-       0x97f000f8,
-       0xfc07f10c,
-       0x0203f04a,
-       0xbd0009d0,
-       0x5e21f504,
-/* 0x027f: strand_post */
-       0xf000f802,
-       0x07f10d97,
-       0x03f04afc,
-       0x0009d002,
-       0x21f504bd,
-       0x00f8025e,
-/* 0x0294: strand_set */
-       0xf10fc7f0,
-       0xf04ffc07,
-       0x0cd00203,
-       0xf004bd00,
-       0x07f10bc7,
-       0x03f04afc,
-       0x000cd002,
-       0x07f104bd,
-       0x03f04ffc,
-       0x000ed002,
-       0xc7f004bd,
-       0xfc07f10a,
-       0x0203f04a,
-       0xbd000cd0,
-       0x5e21f504,
-/* 0x02d3: strand_ctx_init */
-       0xbd00f802,
-       0x0399f094,
-       0x0f0007f1,
-       0xd00203f0,
-       0x04bd0009,
-       0x026a21f5,
-       0xf503e7f0,
-       0xbd029421,
-       0xfc07f1c4,
-       0x0203f047,
-       0xbd000cd0,
-       0x01c7f004,
-       0x4afc07f1,
-       0xd00203f0,
-       0x04bd000c,
-       0x025e21f5,
-       0xf1010c92,
-       0xf046fc07,
-       0x0cd00203,
-       0xf004bd00,
-       0x07f102c7,
-       0x03f04afc,
-       0x000cd002,
-       0x21f504bd,
-       0x21f5025e,
-       0x87f1027f,
-       0x83f04200,
-       0x0097f102,
-       0x0293f020,
-       0x950099cf,
-/* 0x034a: ctx_init_strand_loop */
-       0x8ed008fe,
-       0x408ed000,
-       0xb6808acf,
-       0xa0b606a5,
-       0x00eabb01,
-       0xb60480b6,
-       0x1bf40192,
-       0x08e4b6e8,
-       0xbdf2efbc,
-       0x0399f094,
-       0x170007f1,
-       0xd00203f0,
-       0x04bd0009,
-/* 0x037e: error */
-       0xe0f900f8,
-       0xf102ffb9,
-       0xf09814e7,
-       0x21f440e3,
-       0x01f7f09d,
-       0xf102ffb9,
-       0xf09c1ce7,
-       0x21f440e3,
-       0xf8e0fc9d,
-/* 0x03a1: init */
-       0xf104bd00,
-       0xf0420017,
-       0x11cf0013,
-       0x0911e700,
-       0x0814b601,
-       0xf00014fe,
-       0x07f10227,
-       0x03f01200,
-       0x0002d000,
-       0x17f104bd,
-       0x10fe04e6,
-       0x0007f100,
-       0x0003f007,
-       0xbd0000d0,
-       0x0427f004,
-       0x040007f1,
-       0xd00003f0,
-       0x04bd0002,
-       0xf11031f4,
-       0xf0820027,
-       0x22cf0123,
-       0x0137f000,
-       0xbb1f24f0,
-       0x32b60432,
-       0x05028001,
-       0xf1060380,
-       0xf0860027,
-       0x22cf0123,
-       0x04028000,
-       0x010027f1,
-       0xcf0223f0,
-       0x34bd0022,
-       0xf1082595,
-       0xf0c00007,
-       0x05d00103,
-       0xf104bd00,
-       0xf0c10007,
-       0x05d00103,
-       0x9804bd00,
-       0x0f98000e,
-       0x5021f501,
-       0x002fbb01,
-       0x98003fbb,
-       0x0f98010e,
-       0x5021f502,
-       0x050e9801,
-       0xbb00effd,
-       0x3ebb002e,
-       0x0235b600,
-       0xd30007f1,
-       0xd00103f0,
-       0x04bd0003,
-       0xb60825b6,
-       0x20b60635,
-       0x0130b601,
-       0xb60824b6,
-       0x2fb90834,
-       0xd321f502,
-       0x003fbb02,
-       0x010007f1,
-       0xd00203f0,
-       0x04bd0003,
-       0x29f024bd,
-       0x0007f11f,
-       0x0203f008,
-       0xbd0002d0,
-/* 0x04a9: main */
-       0x0031f404,
-       0xf00028f4,
-       0x21f41cd7,
-       0xf401f439,
-       0xf404e4b0,
-       0x81fe1e18,
-       0x0627f001,
-       0x12fd20bd,
-       0x01e4b604,
-       0xfe051efd,
-       0x21f50018,
-       0x0ef4059e,
-/* 0x04d9: main_not_ctx_xfer */
-       0x10ef94d3,
-       0xf501f5f0,
-       0xf4037e21,
-/* 0x04e6: ih */
-       0x80f9c60e,
-       0xf90188fe,
-       0xf990f980,
-       0xf9b0f9a0,
-       0xf9e0f9d0,
-       0xf104bdf0,
-       0xf00200a7,
-       0xaacf00a3,
-       0x04abc400,
-       0xf02c0bf4,
-       0xe7f11cd7,
-       0xe3f01a00,
-       0x00eecf00,
-       0x1900f7f1,
-       0xcf00f3f0,
-       0x21f400ff,
-       0x01e7f004,
-       0x1d0007f1,
-       0xd00003f0,
-       0x04bd000e,
-/* 0x0534: ih_no_fifo */
-       0x010007f1,
-       0xd00003f0,
-       0x04bd000a,
-       0xe0fcf0fc,
-       0xb0fcd0fc,
-       0x90fca0fc,
-       0x88fe80fc,
-       0xf480fc00,
-       0x01f80032,
-/* 0x0558: hub_barrier_done */
-       0x9801f7f0,
-       0xfebb040e,
-       0x02ffb904,
-       0x9418e7f1,
-       0xf440e3f0,
-       0x00f89d21,
-/* 0x0570: ctx_redswitch */
-       0xf120f7f0,
-       0xf0850007,
-       0x0fd00103,
-       0xf004bd00,
-/* 0x0582: ctx_redswitch_delay */
-       0xe2b608e7,
-       0xfd1bf401,
-       0x0800f5f1,
-       0x0200f5f1,
-       0x850007f1,
-       0xd00103f0,
-       0x04bd000f,
-/* 0x059e: ctx_xfer */
-       0x07f100f8,
-       0x03f08100,
-       0x000fd002,
-       0x11f404bd,
-       0x7021f507,
-/* 0x05b1: ctx_xfer_not_load */
-       0x6a21f505,
-       0xf124bd02,
-       0xf047fc07,
-       0x02d00203,
-       0xf004bd00,
-       0x20b6012c,
-       0xfc07f103,
-       0x0203f04a,
-       0xbd0002d0,
-       0x01acf004,
-       0xf102a5f0,
-       0xf00000b7,
-       0x0c9850b3,
-       0x0fc4b604,
-       0x9800bcbb,
-       0x0d98000c,
-       0x00e7f001,
-       0x016f21f5,
-       0xf001acf0,
-       0xb7f104a5,
-       0xb3f04000,
-       0x040c9850,
-       0xbb0fc4b6,
-       0x0c9800bc,
-       0x020d9801,
-       0xf1060f98,
-       0xf50800e7,
-       0xf5016f21,
-       0xf4025e21,
-       0x12f40601,
-/* 0x0629: ctx_xfer_post */
-       0x7f21f507,
-/* 0x062d: ctx_xfer_done */
-       0x5821f502,
-       0x0000f805,
-       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,
-};
diff --git a/drivers/gpu/drm/nouveau/core/engine/graph/fuc/gpcnvd7.fuc b/drivers/gpu/drm/nouveau/core/engine/graph/fuc/gpcnvd7.fuc
deleted file mode 100644 (file)
index c2f754e..0000000
+++ /dev/null
@@ -1,42 +0,0 @@
-/*
- * Copyright 2013 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 <bskeggs@redhat.com>
- */
-
-#define NV_PGRAPH_GPCX_UNK__SIZE                                     0x00000001
-
-#define CHIPSET GF117
-#include "macros.fuc"
-
-.section #nvd7_grgpc_data
-#define INCLUDE_DATA
-#include "com.fuc"
-#include "gpc.fuc"
-#undef INCLUDE_DATA
-
-.section #nvd7_grgpc_code
-#define INCLUDE_CODE
-bra #init
-#include "com.fuc"
-#include "gpc.fuc"
-.align 256
-#undef INCLUDE_CODE
diff --git a/drivers/gpu/drm/nouveau/core/engine/graph/fuc/gpcnvd7.fuc.h b/drivers/gpu/drm/nouveau/core/engine/graph/fuc/gpcnvd7.fuc.h
deleted file mode 100644 (file)
index d1504a4..0000000
+++ /dev/null
@@ -1,537 +0,0 @@
-uint32_t nvd7_grgpc_data[] = {
-/* 0x0000: gpc_mmio_list_head */
-       0x0000006c,
-/* 0x0004: gpc_mmio_list_tail */
-/* 0x0004: tpc_mmio_list_head */
-       0x0000006c,
-/* 0x0008: tpc_mmio_list_tail */
-/* 0x0008: unk_mmio_list_head */
-       0x0000006c,
-/* 0x000c: unk_mmio_list_tail */
-       0x0000006c,
-/* 0x0010: gpc_id */
-       0x00000000,
-/* 0x0014: tpc_count */
-       0x00000000,
-/* 0x0018: tpc_mask */
-       0x00000000,
-/* 0x001c: unk_count */
-       0x00000000,
-/* 0x0020: unk_mask */
-       0x00000000,
-/* 0x0024: cmd_queue */
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-};
-
-uint32_t nvd7_grgpc_code[] = {
-       0x03a10ef5,
-/* 0x0004: queue_put */
-       0x9800d898,
-       0x86f001d9,
-       0x0489b808,
-       0xf00c1bf4,
-       0x21f502f7,
-       0x00f8037e,
-/* 0x001c: queue_put_next */
-       0xb60798c4,
-       0x8dbb0384,
-       0x0880b600,
-       0x80008e80,
-       0x90b6018f,
-       0x0f94f001,
-       0xf801d980,
-/* 0x0039: queue_get */
-       0x0131f400,
-       0x9800d898,
-       0x89b801d9,
-       0x210bf404,
-       0xb60789c4,
-       0x9dbb0394,
-       0x0890b600,
-       0x98009e98,
-       0x80b6019f,
-       0x0f84f001,
-       0xf400d880,
-/* 0x0066: queue_get_done */
-       0x00f80132,
-/* 0x0068: nv_rd32 */
-       0xf002ecb9,
-       0x07f11fc9,
-       0x03f0ca00,
-       0x000cd001,
-/* 0x007a: nv_rd32_wait */
-       0xc7f104bd,
-       0xc3f0ca00,
-       0x00cccf01,
-       0xf41fccc8,
-       0xa7f0f31b,
-       0x1021f506,
-       0x00f7f101,
-       0x01f3f0cb,
-       0xf800ffcf,
-/* 0x009d: nv_wr32 */
-       0x0007f100,
-       0x0103f0cc,
-       0xbd000fd0,
-       0x02ecb904,
-       0xf01fc9f0,
-       0x07f11ec9,
-       0x03f0ca00,
-       0x000cd001,
-/* 0x00be: nv_wr32_wait */
-       0xc7f104bd,
-       0xc3f0ca00,
-       0x00cccf01,
-       0xf41fccc8,
-       0x00f8f31b,
-/* 0x00d0: wait_donez */
-       0x99f094bd,
-       0x0007f100,
-       0x0203f00f,
-       0xbd0009d0,
-       0x0007f104,
-       0x0203f006,
-       0xbd000ad0,
-/* 0x00ed: wait_donez_ne */
-       0x0087f104,
-       0x0183f000,
-       0xff0088cf,
-       0x1bf4888a,
-       0xf094bdf3,
-       0x07f10099,
-       0x03f01700,
-       0x0009d002,
-       0x00f804bd,
-/* 0x0110: wait_doneo */
-       0x99f094bd,
-       0x0007f100,
-       0x0203f00f,
-       0xbd0009d0,
-       0x0007f104,
-       0x0203f006,
-       0xbd000ad0,
-/* 0x012d: wait_doneo_e */
-       0x0087f104,
-       0x0183f000,
-       0xff0088cf,
-       0x0bf4888a,
-       0xf094bdf3,
-       0x07f10099,
-       0x03f01700,
-       0x0009d002,
-       0x00f804bd,
-/* 0x0150: mmctx_size */
-/* 0x0152: nv_mmctx_size_loop */
-       0xe89894bd,
-       0x1a85b600,
-       0xb60180b6,
-       0x98bb0284,
-       0x04e0b600,
-       0xf404efb8,
-       0x9fb9eb1b,
-/* 0x016f: mmctx_xfer */
-       0xbd00f802,
-       0x0199f094,
-       0x0f0007f1,
-       0xd00203f0,
-       0x04bd0009,
-       0xbbfd94bd,
-       0x120bf405,
-       0xc40007f1,
-       0xd00103f0,
-       0x04bd000b,
-/* 0x0197: mmctx_base_disabled */
-       0xfd0099f0,
-       0x0bf405ee,
-       0x0007f11e,
-       0x0103f0c6,
-       0xbd000ed0,
-       0x0007f104,
-       0x0103f0c7,
-       0xbd000fd0,
-       0x0199f004,
-/* 0x01b8: mmctx_multi_disabled */
-       0xb600abc8,
-       0xb9f010b4,
-       0x01aec80c,
-       0xfd11e4b6,
-       0x07f105be,
-       0x03f0c500,
-       0x000bd001,
-/* 0x01d6: mmctx_exec_loop */
-/* 0x01d6: mmctx_wait_free */
-       0xe7f104bd,
-       0xe3f0c500,
-       0x00eecf01,
-       0xf41fe4f0,
-       0xce98f30b,
-       0x05e9fd00,
-       0xc80007f1,
-       0xd00103f0,
-       0x04bd000e,
-       0xb804c0b6,
-       0x1bf404cd,
-       0x02abc8d8,
-/* 0x0207: mmctx_fini_wait */
-       0xf11f1bf4,
-       0xf0c500b7,
-       0xbbcf01b3,
-       0x1fb4f000,
-       0xf410b4b0,
-       0xa7f0f01b,
-       0xd021f405,
-/* 0x0223: mmctx_stop */
-       0xc82b0ef4,
-       0xb4b600ab,
-       0x0cb9f010,
-       0xf112b9f0,
-       0xf0c50007,
-       0x0bd00103,
-/* 0x023b: mmctx_stop_wait */
-       0xf104bd00,
-       0xf0c500b7,
-       0xbbcf01b3,
-       0x12bbc800,
-/* 0x024b: mmctx_done */
-       0xbdf31bf4,
-       0x0199f094,
-       0x170007f1,
-       0xd00203f0,
-       0x04bd0009,
-/* 0x025e: strand_wait */
-       0xa0f900f8,
-       0xf402a7f0,
-       0xa0fcd021,
-/* 0x026a: strand_pre */
-       0x97f000f8,
-       0xfc07f10c,
-       0x0203f04a,
-       0xbd0009d0,
-       0x5e21f504,
-/* 0x027f: strand_post */
-       0xf000f802,
-       0x07f10d97,
-       0x03f04afc,
-       0x0009d002,
-       0x21f504bd,
-       0x00f8025e,
-/* 0x0294: strand_set */
-       0xf10fc7f0,
-       0xf04ffc07,
-       0x0cd00203,
-       0xf004bd00,
-       0x07f10bc7,
-       0x03f04afc,
-       0x000cd002,
-       0x07f104bd,
-       0x03f04ffc,
-       0x000ed002,
-       0xc7f004bd,
-       0xfc07f10a,
-       0x0203f04a,
-       0xbd000cd0,
-       0x5e21f504,
-/* 0x02d3: strand_ctx_init */
-       0xbd00f802,
-       0x0399f094,
-       0x0f0007f1,
-       0xd00203f0,
-       0x04bd0009,
-       0x026a21f5,
-       0xf503e7f0,
-       0xbd029421,
-       0xfc07f1c4,
-       0x0203f047,
-       0xbd000cd0,
-       0x01c7f004,
-       0x4afc07f1,
-       0xd00203f0,
-       0x04bd000c,
-       0x025e21f5,
-       0xf1010c92,
-       0xf046fc07,
-       0x0cd00203,
-       0xf004bd00,
-       0x07f102c7,
-       0x03f04afc,
-       0x000cd002,
-       0x21f504bd,
-       0x21f5025e,
-       0x87f1027f,
-       0x83f04200,
-       0x0097f102,
-       0x0293f020,
-       0x950099cf,
-/* 0x034a: ctx_init_strand_loop */
-       0x8ed008fe,
-       0x408ed000,
-       0xb6808acf,
-       0xa0b606a5,
-       0x00eabb01,
-       0xb60480b6,
-       0x1bf40192,
-       0x08e4b6e8,
-       0xbdf2efbc,
-       0x0399f094,
-       0x170007f1,
-       0xd00203f0,
-       0x04bd0009,
-/* 0x037e: error */
-       0xe0f900f8,
-       0xf102ffb9,
-       0xf09814e7,
-       0x21f440e3,
-       0x01f7f09d,
-       0xf102ffb9,
-       0xf09c1ce7,
-       0x21f440e3,
-       0xf8e0fc9d,
-/* 0x03a1: init */
-       0xf104bd00,
-       0xf0420017,
-       0x11cf0013,
-       0x0911e700,
-       0x0814b601,
-       0xf00014fe,
-       0x07f10227,
-       0x03f01200,
-       0x0002d000,
-       0x17f104bd,
-       0x10fe0530,
-       0x0007f100,
-       0x0003f007,
-       0xbd0000d0,
-       0x0427f004,
-       0x040007f1,
-       0xd00003f0,
-       0x04bd0002,
-       0xf11031f4,
-       0xf0820027,
-       0x22cf0123,
-       0x0137f000,
-       0xbb1f24f0,
-       0x32b60432,
-       0x05028001,
-       0xf1060380,
-       0xf0860027,
-       0x22cf0123,
-       0x04028000,
-       0x0c30e7f1,
-       0xbd50e3f0,
-       0xbd34bd24,
-/* 0x0421: init_unk_loop */
-       0x6821f444,
-       0xf400f6b0,
-       0xf7f00f0b,
-       0x04f2bb01,
-       0xb6054ffd,
-/* 0x0436: init_unk_next */
-       0x20b60130,
-       0x04e0b601,
-       0xf40126b0,
-/* 0x0442: init_unk_done */
-       0x0380e21b,
-       0x08048007,
-       0x010027f1,
-       0xcf0223f0,
-       0x34bd0022,
-       0xf1082595,
-       0xf0c00007,
-       0x05d00103,
-       0xf104bd00,
-       0xf0c10007,
-       0x05d00103,
-       0x9804bd00,
-       0x0f98000e,
-       0x5021f501,
-       0x002fbb01,
-       0x98003fbb,
-       0x0f98010e,
-       0x5021f502,
-       0x050e9801,
-       0xbb00effd,
-       0x3ebb002e,
-       0x020e9800,
-       0xf5030f98,
-       0x98015021,
-       0xeffd070e,
-       0x002ebb00,
-       0xb6003ebb,
-       0x07f10235,
-       0x03f0d300,
-       0x0003d001,
-       0x25b604bd,
-       0x0635b608,
-       0xb60120b6,
-       0x24b60130,
-       0x0834b608,
-       0xf5022fb9,
-       0xbb02d321,
-       0x07f1003f,
-       0x03f00100,
-       0x0003d002,
-       0x24bd04bd,
-       0xf11f29f0,
-       0xf0080007,
-       0x02d00203,
-/* 0x04f3: main */
-       0xf404bd00,
-       0x28f40031,
-       0x24d7f000,
-       0xf43921f4,
-       0xe4b0f401,
-       0x1e18f404,
-       0xf00181fe,
-       0x20bd0627,
-       0xb60412fd,
-       0x1efd01e4,
-       0x0018fe05,
-       0x05e821f5,
-/* 0x0523: main_not_ctx_xfer */
-       0x94d30ef4,
-       0xf5f010ef,
-       0x7e21f501,
-       0xc60ef403,
-/* 0x0530: ih */
-       0x88fe80f9,
-       0xf980f901,
-       0xf9a0f990,
-       0xf9d0f9b0,
-       0xbdf0f9e0,
-       0x00a7f104,
-       0x00a3f002,
-       0xc400aacf,
-       0x0bf404ab,
-       0x24d7f02c,
-       0x1a00e7f1,
-       0xcf00e3f0,
-       0xf7f100ee,
-       0xf3f01900,
-       0x00ffcf00,
-       0xf00421f4,
-       0x07f101e7,
-       0x03f01d00,
-       0x000ed000,
-/* 0x057e: ih_no_fifo */
-       0x07f104bd,
-       0x03f00100,
-       0x000ad000,
-       0xf0fc04bd,
-       0xd0fce0fc,
-       0xa0fcb0fc,
-       0x80fc90fc,
-       0xfc0088fe,
-       0x0032f480,
-/* 0x05a2: hub_barrier_done */
-       0xf7f001f8,
-       0x040e9801,
-       0xb904febb,
-       0xe7f102ff,
-       0xe3f09418,
-       0x9d21f440,
-/* 0x05ba: ctx_redswitch */
-       0xf7f000f8,
-       0x0007f120,
-       0x0103f085,
-       0xbd000fd0,
-       0x08e7f004,
-/* 0x05cc: ctx_redswitch_delay */
-       0xf401e2b6,
-       0xf5f1fd1b,
-       0xf5f10800,
-       0x07f10200,
-       0x03f08500,
-       0x000fd001,
-       0x00f804bd,
-/* 0x05e8: ctx_xfer */
-       0x810007f1,
-       0xd00203f0,
-       0x04bd000f,
-       0xf50711f4,
-/* 0x05fb: ctx_xfer_not_load */
-       0xf505ba21,
-       0xbd026a21,
-       0xfc07f124,
-       0x0203f047,
-       0xbd0002d0,
-       0x012cf004,
-       0xf10320b6,
-       0xf04afc07,
-       0x02d00203,
-       0xf004bd00,
-       0xa5f001ac,
-       0x00b7f102,
-       0x50b3f000,
-       0xb6040c98,
-       0xbcbb0fc4,
-       0x000c9800,
-       0xf0010d98,
-       0x21f500e7,
-       0xacf0016f,
-       0x00b7f101,
-       0x50b3f040,
-       0xb6040c98,
-       0xbcbb0fc4,
-       0x010c9800,
-       0x98020d98,
-       0xe7f1060f,
-       0x21f50800,
-       0xacf0016f,
-       0x04a5f001,
-       0x3000b7f1,
-       0x9850b3f0,
-       0xc4b6040c,
-       0x00bcbb0f,
-       0x98020c98,
-       0x0f98030d,
-       0x00e7f108,
-       0x6f21f502,
-       0x5e21f501,
-       0x0601f402,
-/* 0x0697: ctx_xfer_post */
-       0xf50712f4,
-/* 0x069b: ctx_xfer_done */
-       0xf5027f21,
-       0xf805a221,
-       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/drivers/gpu/drm/nouveau/core/engine/graph/fuc/gpcnve0.fuc b/drivers/gpu/drm/nouveau/core/engine/graph/fuc/gpcnve0.fuc
deleted file mode 100644 (file)
index 6b906cd..0000000
+++ /dev/null
@@ -1,42 +0,0 @@
-/*
- * Copyright 2013 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 <bskeggs@redhat.com>
- */
-
-#define NV_PGRAPH_GPCX_UNK__SIZE                                     0x00000001
-
-#define CHIPSET GK100
-#include "macros.fuc"
-
-.section #nve0_grgpc_data
-#define INCLUDE_DATA
-#include "com.fuc"
-#include "gpc.fuc"
-#undef INCLUDE_DATA
-
-.section #nve0_grgpc_code
-#define INCLUDE_CODE
-bra #init
-#include "com.fuc"
-#include "gpc.fuc"
-.align 256
-#undef INCLUDE_CODE
diff --git a/drivers/gpu/drm/nouveau/core/engine/graph/fuc/gpcnve0.fuc.h b/drivers/gpu/drm/nouveau/core/engine/graph/fuc/gpcnve0.fuc.h
deleted file mode 100644 (file)
index 855b220..0000000
+++ /dev/null
@@ -1,537 +0,0 @@
-uint32_t nve0_grgpc_data[] = {
-/* 0x0000: gpc_mmio_list_head */
-       0x0000006c,
-/* 0x0004: gpc_mmio_list_tail */
-/* 0x0004: tpc_mmio_list_head */
-       0x0000006c,
-/* 0x0008: tpc_mmio_list_tail */
-/* 0x0008: unk_mmio_list_head */
-       0x0000006c,
-/* 0x000c: unk_mmio_list_tail */
-       0x0000006c,
-/* 0x0010: gpc_id */
-       0x00000000,
-/* 0x0014: tpc_count */
-       0x00000000,
-/* 0x0018: tpc_mask */
-       0x00000000,
-/* 0x001c: unk_count */
-       0x00000000,
-/* 0x0020: unk_mask */
-       0x00000000,
-/* 0x0024: cmd_queue */
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-};
-
-uint32_t nve0_grgpc_code[] = {
-       0x03a10ef5,
-/* 0x0004: queue_put */
-       0x9800d898,
-       0x86f001d9,
-       0x0489b808,
-       0xf00c1bf4,
-       0x21f502f7,
-       0x00f8037e,
-/* 0x001c: queue_put_next */
-       0xb60798c4,
-       0x8dbb0384,
-       0x0880b600,
-       0x80008e80,
-       0x90b6018f,
-       0x0f94f001,
-       0xf801d980,
-/* 0x0039: queue_get */
-       0x0131f400,
-       0x9800d898,
-       0x89b801d9,
-       0x210bf404,
-       0xb60789c4,
-       0x9dbb0394,
-       0x0890b600,
-       0x98009e98,
-       0x80b6019f,
-       0x0f84f001,
-       0xf400d880,
-/* 0x0066: queue_get_done */
-       0x00f80132,
-/* 0x0068: nv_rd32 */
-       0xf002ecb9,
-       0x07f11fc9,
-       0x03f0ca00,
-       0x000cd001,
-/* 0x007a: nv_rd32_wait */
-       0xc7f104bd,
-       0xc3f0ca00,
-       0x00cccf01,
-       0xf41fccc8,
-       0xa7f0f31b,
-       0x1021f506,
-       0x00f7f101,
-       0x01f3f0cb,
-       0xf800ffcf,
-/* 0x009d: nv_wr32 */
-       0x0007f100,
-       0x0103f0cc,
-       0xbd000fd0,
-       0x02ecb904,
-       0xf01fc9f0,
-       0x07f11ec9,
-       0x03f0ca00,
-       0x000cd001,
-/* 0x00be: nv_wr32_wait */
-       0xc7f104bd,
-       0xc3f0ca00,
-       0x00cccf01,
-       0xf41fccc8,
-       0x00f8f31b,
-/* 0x00d0: wait_donez */
-       0x99f094bd,
-       0x0007f100,
-       0x0203f00f,
-       0xbd0009d0,
-       0x0007f104,
-       0x0203f006,
-       0xbd000ad0,
-/* 0x00ed: wait_donez_ne */
-       0x0087f104,
-       0x0183f000,
-       0xff0088cf,
-       0x1bf4888a,
-       0xf094bdf3,
-       0x07f10099,
-       0x03f01700,
-       0x0009d002,
-       0x00f804bd,
-/* 0x0110: wait_doneo */
-       0x99f094bd,
-       0x0007f100,
-       0x0203f00f,
-       0xbd0009d0,
-       0x0007f104,
-       0x0203f006,
-       0xbd000ad0,
-/* 0x012d: wait_doneo_e */
-       0x0087f104,
-       0x0183f000,
-       0xff0088cf,
-       0x0bf4888a,
-       0xf094bdf3,
-       0x07f10099,
-       0x03f01700,
-       0x0009d002,
-       0x00f804bd,
-/* 0x0150: mmctx_size */
-/* 0x0152: nv_mmctx_size_loop */
-       0xe89894bd,
-       0x1a85b600,
-       0xb60180b6,
-       0x98bb0284,
-       0x04e0b600,
-       0xf404efb8,
-       0x9fb9eb1b,
-/* 0x016f: mmctx_xfer */
-       0xbd00f802,
-       0x0199f094,
-       0x0f0007f1,
-       0xd00203f0,
-       0x04bd0009,
-       0xbbfd94bd,
-       0x120bf405,
-       0xc40007f1,
-       0xd00103f0,
-       0x04bd000b,
-/* 0x0197: mmctx_base_disabled */
-       0xfd0099f0,
-       0x0bf405ee,
-       0x0007f11e,
-       0x0103f0c6,
-       0xbd000ed0,
-       0x0007f104,
-       0x0103f0c7,
-       0xbd000fd0,
-       0x0199f004,
-/* 0x01b8: mmctx_multi_disabled */
-       0xb600abc8,
-       0xb9f010b4,
-       0x01aec80c,
-       0xfd11e4b6,
-       0x07f105be,
-       0x03f0c500,
-       0x000bd001,
-/* 0x01d6: mmctx_exec_loop */
-/* 0x01d6: mmctx_wait_free */
-       0xe7f104bd,
-       0xe3f0c500,
-       0x00eecf01,
-       0xf41fe4f0,
-       0xce98f30b,
-       0x05e9fd00,
-       0xc80007f1,
-       0xd00103f0,
-       0x04bd000e,
-       0xb804c0b6,
-       0x1bf404cd,
-       0x02abc8d8,
-/* 0x0207: mmctx_fini_wait */
-       0xf11f1bf4,
-       0xf0c500b7,
-       0xbbcf01b3,
-       0x1fb4f000,
-       0xf410b4b0,
-       0xa7f0f01b,
-       0xd021f405,
-/* 0x0223: mmctx_stop */
-       0xc82b0ef4,
-       0xb4b600ab,
-       0x0cb9f010,
-       0xf112b9f0,
-       0xf0c50007,
-       0x0bd00103,
-/* 0x023b: mmctx_stop_wait */
-       0xf104bd00,
-       0xf0c500b7,
-       0xbbcf01b3,
-       0x12bbc800,
-/* 0x024b: mmctx_done */
-       0xbdf31bf4,
-       0x0199f094,
-       0x170007f1,
-       0xd00203f0,
-       0x04bd0009,
-/* 0x025e: strand_wait */
-       0xa0f900f8,
-       0xf402a7f0,
-       0xa0fcd021,
-/* 0x026a: strand_pre */
-       0x97f000f8,
-       0xfc07f10c,
-       0x0203f04a,
-       0xbd0009d0,
-       0x5e21f504,
-/* 0x027f: strand_post */
-       0xf000f802,
-       0x07f10d97,
-       0x03f04afc,
-       0x0009d002,
-       0x21f504bd,
-       0x00f8025e,
-/* 0x0294: strand_set */
-       0xf10fc7f0,
-       0xf04ffc07,
-       0x0cd00203,
-       0xf004bd00,
-       0x07f10bc7,
-       0x03f04afc,
-       0x000cd002,
-       0x07f104bd,
-       0x03f04ffc,
-       0x000ed002,
-       0xc7f004bd,
-       0xfc07f10a,
-       0x0203f04a,
-       0xbd000cd0,
-       0x5e21f504,
-/* 0x02d3: strand_ctx_init */
-       0xbd00f802,
-       0x0399f094,
-       0x0f0007f1,
-       0xd00203f0,
-       0x04bd0009,
-       0x026a21f5,
-       0xf503e7f0,
-       0xbd029421,
-       0xfc07f1c4,
-       0x0203f047,
-       0xbd000cd0,
-       0x01c7f004,
-       0x4afc07f1,
-       0xd00203f0,
-       0x04bd000c,
-       0x025e21f5,
-       0xf1010c92,
-       0xf046fc07,
-       0x0cd00203,
-       0xf004bd00,
-       0x07f102c7,
-       0x03f04afc,
-       0x000cd002,
-       0x21f504bd,
-       0x21f5025e,
-       0x87f1027f,
-       0x83f04200,
-       0x0097f102,
-       0x0293f020,
-       0x950099cf,
-/* 0x034a: ctx_init_strand_loop */
-       0x8ed008fe,
-       0x408ed000,
-       0xb6808acf,
-       0xa0b606a5,
-       0x00eabb01,
-       0xb60480b6,
-       0x1bf40192,
-       0x08e4b6e8,
-       0xbdf2efbc,
-       0x0399f094,
-       0x170007f1,
-       0xd00203f0,
-       0x04bd0009,
-/* 0x037e: error */
-       0xe0f900f8,
-       0xf102ffb9,
-       0xf09814e7,
-       0x21f440e3,
-       0x01f7f09d,
-       0xf102ffb9,
-       0xf09c1ce7,
-       0x21f440e3,
-       0xf8e0fc9d,
-/* 0x03a1: init */
-       0xf104bd00,
-       0xf0420017,
-       0x11cf0013,
-       0x0911e700,
-       0x0814b601,
-       0xf00014fe,
-       0x07f10227,
-       0x03f01200,
-       0x0002d000,
-       0x17f104bd,
-       0x10fe0530,
-       0x0007f100,
-       0x0003f007,
-       0xbd0000d0,
-       0x0427f004,
-       0x040007f1,
-       0xd00003f0,
-       0x04bd0002,
-       0xf11031f4,
-       0xf0820027,
-       0x22cf0123,
-       0x0137f000,
-       0xbb1f24f0,
-       0x32b60432,
-       0x05028001,
-       0xf1060380,
-       0xf0860027,
-       0x22cf0123,
-       0x04028000,
-       0x0c30e7f1,
-       0xbd50e3f0,
-       0xbd34bd24,
-/* 0x0421: init_unk_loop */
-       0x6821f444,
-       0xf400f6b0,
-       0xf7f00f0b,
-       0x04f2bb01,
-       0xb6054ffd,
-/* 0x0436: init_unk_next */
-       0x20b60130,
-       0x04e0b601,
-       0xf40126b0,
-/* 0x0442: init_unk_done */
-       0x0380e21b,
-       0x08048007,
-       0x010027f1,
-       0xcf0223f0,
-       0x34bd0022,
-       0xf1082595,
-       0xf0c00007,
-       0x05d00103,
-       0xf104bd00,
-       0xf0c10007,
-       0x05d00103,
-       0x9804bd00,
-       0x0f98000e,
-       0x5021f501,
-       0x002fbb01,
-       0x98003fbb,
-       0x0f98010e,
-       0x5021f502,
-       0x050e9801,
-       0xbb00effd,
-       0x3ebb002e,
-       0x020e9800,
-       0xf5030f98,
-       0x98015021,
-       0xeffd070e,
-       0x002ebb00,
-       0xb6003ebb,
-       0x07f10235,
-       0x03f0d300,
-       0x0003d001,
-       0x25b604bd,
-       0x0635b608,
-       0xb60120b6,
-       0x24b60130,
-       0x0834b608,
-       0xf5022fb9,
-       0xbb02d321,
-       0x07f1003f,
-       0x03f00100,
-       0x0003d002,
-       0x24bd04bd,
-       0xf11f29f0,
-       0xf0080007,
-       0x02d00203,
-/* 0x04f3: main */
-       0xf404bd00,
-       0x28f40031,
-       0x24d7f000,
-       0xf43921f4,
-       0xe4b0f401,
-       0x1e18f404,
-       0xf00181fe,
-       0x20bd0627,
-       0xb60412fd,
-       0x1efd01e4,
-       0x0018fe05,
-       0x05e821f5,
-/* 0x0523: main_not_ctx_xfer */
-       0x94d30ef4,
-       0xf5f010ef,
-       0x7e21f501,
-       0xc60ef403,
-/* 0x0530: ih */
-       0x88fe80f9,
-       0xf980f901,
-       0xf9a0f990,
-       0xf9d0f9b0,
-       0xbdf0f9e0,
-       0x00a7f104,
-       0x00a3f002,
-       0xc400aacf,
-       0x0bf404ab,
-       0x24d7f02c,
-       0x1a00e7f1,
-       0xcf00e3f0,
-       0xf7f100ee,
-       0xf3f01900,
-       0x00ffcf00,
-       0xf00421f4,
-       0x07f101e7,
-       0x03f01d00,
-       0x000ed000,
-/* 0x057e: ih_no_fifo */
-       0x07f104bd,
-       0x03f00100,
-       0x000ad000,
-       0xf0fc04bd,
-       0xd0fce0fc,
-       0xa0fcb0fc,
-       0x80fc90fc,
-       0xfc0088fe,
-       0x0032f480,
-/* 0x05a2: hub_barrier_done */
-       0xf7f001f8,
-       0x040e9801,
-       0xb904febb,
-       0xe7f102ff,
-       0xe3f09418,
-       0x9d21f440,
-/* 0x05ba: ctx_redswitch */
-       0xf7f000f8,
-       0x0007f120,
-       0x0103f085,
-       0xbd000fd0,
-       0x08e7f004,
-/* 0x05cc: ctx_redswitch_delay */
-       0xf401e2b6,
-       0xf5f1fd1b,
-       0xf5f10800,
-       0x07f10200,
-       0x03f08500,
-       0x000fd001,
-       0x00f804bd,
-/* 0x05e8: ctx_xfer */
-       0x810007f1,
-       0xd00203f0,
-       0x04bd000f,
-       0xf50711f4,
-/* 0x05fb: ctx_xfer_not_load */
-       0xf505ba21,
-       0xbd026a21,
-       0xfc07f124,
-       0x0203f047,
-       0xbd0002d0,
-       0x012cf004,
-       0xf10320b6,
-       0xf04afc07,
-       0x02d00203,
-       0xf004bd00,
-       0xa5f001ac,
-       0x00b7f102,
-       0x50b3f000,
-       0xb6040c98,
-       0xbcbb0fc4,
-       0x000c9800,
-       0xf0010d98,
-       0x21f500e7,
-       0xacf0016f,
-       0x00b7f101,
-       0x50b3f040,
-       0xb6040c98,
-       0xbcbb0fc4,
-       0x010c9800,
-       0x98020d98,
-       0xe7f1060f,
-       0x21f50800,
-       0xacf0016f,
-       0x04a5f001,
-       0x3000b7f1,
-       0x9850b3f0,
-       0xc4b6040c,
-       0x00bcbb0f,
-       0x98020c98,
-       0x0f98030d,
-       0x00e7f108,
-       0x6f21f502,
-       0x5e21f501,
-       0x0601f402,
-/* 0x0697: ctx_xfer_post */
-       0xf50712f4,
-/* 0x069b: ctx_xfer_done */
-       0xf5027f21,
-       0xf805a221,
-       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/drivers/gpu/drm/nouveau/core/engine/graph/fuc/gpcnvf0.fuc b/drivers/gpu/drm/nouveau/core/engine/graph/fuc/gpcnvf0.fuc
deleted file mode 100644 (file)
index 90bbe52..0000000
+++ /dev/null
@@ -1,42 +0,0 @@
-/*
- * Copyright 2013 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 <bskeggs@redhat.com>
- */
-
-#define NV_PGRAPH_GPCX_UNK__SIZE                                     0x00000002
-
-#define CHIPSET GK110
-#include "macros.fuc"
-
-.section #nvf0_grgpc_data
-#define INCLUDE_DATA
-#include "com.fuc"
-#include "gpc.fuc"
-#undef INCLUDE_DATA
-
-.section #nvf0_grgpc_code
-#define INCLUDE_CODE
-bra #init
-#include "com.fuc"
-#include "gpc.fuc"
-.align 256
-#undef INCLUDE_CODE
diff --git a/drivers/gpu/drm/nouveau/core/engine/graph/fuc/gpcnvf0.fuc.h b/drivers/gpu/drm/nouveau/core/engine/graph/fuc/gpcnvf0.fuc.h
deleted file mode 100644 (file)
index 1b80319..0000000
+++ /dev/null
@@ -1,537 +0,0 @@
-uint32_t nvf0_grgpc_data[] = {
-/* 0x0000: gpc_mmio_list_head */
-       0x0000006c,
-/* 0x0004: gpc_mmio_list_tail */
-/* 0x0004: tpc_mmio_list_head */
-       0x0000006c,
-/* 0x0008: tpc_mmio_list_tail */
-/* 0x0008: unk_mmio_list_head */
-       0x0000006c,
-/* 0x000c: unk_mmio_list_tail */
-       0x0000006c,
-/* 0x0010: gpc_id */
-       0x00000000,
-/* 0x0014: tpc_count */
-       0x00000000,
-/* 0x0018: tpc_mask */
-       0x00000000,
-/* 0x001c: unk_count */
-       0x00000000,
-/* 0x0020: unk_mask */
-       0x00000000,
-/* 0x0024: cmd_queue */
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-};
-
-uint32_t nvf0_grgpc_code[] = {
-       0x03a10ef5,
-/* 0x0004: queue_put */
-       0x9800d898,
-       0x86f001d9,
-       0x0489b808,
-       0xf00c1bf4,
-       0x21f502f7,
-       0x00f8037e,
-/* 0x001c: queue_put_next */
-       0xb60798c4,
-       0x8dbb0384,
-       0x0880b600,
-       0x80008e80,
-       0x90b6018f,
-       0x0f94f001,
-       0xf801d980,
-/* 0x0039: queue_get */
-       0x0131f400,
-       0x9800d898,
-       0x89b801d9,
-       0x210bf404,
-       0xb60789c4,
-       0x9dbb0394,
-       0x0890b600,
-       0x98009e98,
-       0x80b6019f,
-       0x0f84f001,
-       0xf400d880,
-/* 0x0066: queue_get_done */
-       0x00f80132,
-/* 0x0068: nv_rd32 */
-       0xf002ecb9,
-       0x07f11fc9,
-       0x03f0ca00,
-       0x000cd001,
-/* 0x007a: nv_rd32_wait */
-       0xc7f104bd,
-       0xc3f0ca00,
-       0x00cccf01,
-       0xf41fccc8,
-       0xa7f0f31b,
-       0x1021f506,
-       0x00f7f101,
-       0x01f3f0cb,
-       0xf800ffcf,
-/* 0x009d: nv_wr32 */
-       0x0007f100,
-       0x0103f0cc,
-       0xbd000fd0,
-       0x02ecb904,
-       0xf01fc9f0,
-       0x07f11ec9,
-       0x03f0ca00,
-       0x000cd001,
-/* 0x00be: nv_wr32_wait */
-       0xc7f104bd,
-       0xc3f0ca00,
-       0x00cccf01,
-       0xf41fccc8,
-       0x00f8f31b,
-/* 0x00d0: wait_donez */
-       0x99f094bd,
-       0x0007f100,
-       0x0203f037,
-       0xbd0009d0,
-       0x0007f104,
-       0x0203f006,
-       0xbd000ad0,
-/* 0x00ed: wait_donez_ne */
-       0x0087f104,
-       0x0183f000,
-       0xff0088cf,
-       0x1bf4888a,
-       0xf094bdf3,
-       0x07f10099,
-       0x03f01700,
-       0x0009d002,
-       0x00f804bd,
-/* 0x0110: wait_doneo */
-       0x99f094bd,
-       0x0007f100,
-       0x0203f037,
-       0xbd0009d0,
-       0x0007f104,
-       0x0203f006,
-       0xbd000ad0,
-/* 0x012d: wait_doneo_e */
-       0x0087f104,
-       0x0183f000,
-       0xff0088cf,
-       0x0bf4888a,
-       0xf094bdf3,
-       0x07f10099,
-       0x03f01700,
-       0x0009d002,
-       0x00f804bd,
-/* 0x0150: mmctx_size */
-/* 0x0152: nv_mmctx_size_loop */
-       0xe89894bd,
-       0x1a85b600,
-       0xb60180b6,
-       0x98bb0284,
-       0x04e0b600,
-       0xf404efb8,
-       0x9fb9eb1b,
-/* 0x016f: mmctx_xfer */
-       0xbd00f802,
-       0x0199f094,
-       0x370007f1,
-       0xd00203f0,
-       0x04bd0009,
-       0xbbfd94bd,
-       0x120bf405,
-       0xc40007f1,
-       0xd00103f0,
-       0x04bd000b,
-/* 0x0197: mmctx_base_disabled */
-       0xfd0099f0,
-       0x0bf405ee,
-       0x0007f11e,
-       0x0103f0c6,
-       0xbd000ed0,
-       0x0007f104,
-       0x0103f0c7,
-       0xbd000fd0,
-       0x0199f004,
-/* 0x01b8: mmctx_multi_disabled */
-       0xb600abc8,
-       0xb9f010b4,
-       0x01aec80c,
-       0xfd11e4b6,
-       0x07f105be,
-       0x03f0c500,
-       0x000bd001,
-/* 0x01d6: mmctx_exec_loop */
-/* 0x01d6: mmctx_wait_free */
-       0xe7f104bd,
-       0xe3f0c500,
-       0x00eecf01,
-       0xf41fe4f0,
-       0xce98f30b,
-       0x05e9fd00,
-       0xc80007f1,
-       0xd00103f0,
-       0x04bd000e,
-       0xb804c0b6,
-       0x1bf404cd,
-       0x02abc8d8,
-/* 0x0207: mmctx_fini_wait */
-       0xf11f1bf4,
-       0xf0c500b7,
-       0xbbcf01b3,
-       0x1fb4f000,
-       0xf410b4b0,
-       0xa7f0f01b,
-       0xd021f405,
-/* 0x0223: mmctx_stop */
-       0xc82b0ef4,
-       0xb4b600ab,
-       0x0cb9f010,
-       0xf112b9f0,
-       0xf0c50007,
-       0x0bd00103,
-/* 0x023b: mmctx_stop_wait */
-       0xf104bd00,
-       0xf0c500b7,
-       0xbbcf01b3,
-       0x12bbc800,
-/* 0x024b: mmctx_done */
-       0xbdf31bf4,
-       0x0199f094,
-       0x170007f1,
-       0xd00203f0,
-       0x04bd0009,
-/* 0x025e: strand_wait */
-       0xa0f900f8,
-       0xf402a7f0,
-       0xa0fcd021,
-/* 0x026a: strand_pre */
-       0x97f000f8,
-       0xfc07f10c,
-       0x0203f04a,
-       0xbd0009d0,
-       0x5e21f504,
-/* 0x027f: strand_post */
-       0xf000f802,
-       0x07f10d97,
-       0x03f04afc,
-       0x0009d002,
-       0x21f504bd,
-       0x00f8025e,
-/* 0x0294: strand_set */
-       0xf10fc7f0,
-       0xf04ffc07,
-       0x0cd00203,
-       0xf004bd00,
-       0x07f10bc7,
-       0x03f04afc,
-       0x000cd002,
-       0x07f104bd,
-       0x03f04ffc,
-       0x000ed002,
-       0xc7f004bd,
-       0xfc07f10a,
-       0x0203f04a,
-       0xbd000cd0,
-       0x5e21f504,
-/* 0x02d3: strand_ctx_init */
-       0xbd00f802,
-       0x0399f094,
-       0x370007f1,
-       0xd00203f0,
-       0x04bd0009,
-       0x026a21f5,
-       0xf503e7f0,
-       0xbd029421,
-       0xfc07f1c4,
-       0x0203f047,
-       0xbd000cd0,
-       0x01c7f004,
-       0x4afc07f1,
-       0xd00203f0,
-       0x04bd000c,
-       0x025e21f5,
-       0xf1010c92,
-       0xf046fc07,
-       0x0cd00203,
-       0xf004bd00,
-       0x07f102c7,
-       0x03f04afc,
-       0x000cd002,
-       0x21f504bd,
-       0x21f5025e,
-       0x87f1027f,
-       0x83f04200,
-       0x0097f102,
-       0x0293f020,
-       0x950099cf,
-/* 0x034a: ctx_init_strand_loop */
-       0x8ed008fe,
-       0x408ed000,
-       0xb6808acf,
-       0xa0b606a5,
-       0x00eabb01,
-       0xb60480b6,
-       0x1bf40192,
-       0x08e4b6e8,
-       0xbdf2efbc,
-       0x0399f094,
-       0x170007f1,
-       0xd00203f0,
-       0x04bd0009,
-/* 0x037e: error */
-       0xe0f900f8,
-       0xf102ffb9,
-       0xf09814e7,
-       0x21f440e3,
-       0x01f7f09d,
-       0xf102ffb9,
-       0xf09c1ce7,
-       0x21f440e3,
-       0xf8e0fc9d,
-/* 0x03a1: init */
-       0xf104bd00,
-       0xf0420017,
-       0x11cf0013,
-       0x0911e700,
-       0x0814b601,
-       0xf00014fe,
-       0x07f10227,
-       0x03f01200,
-       0x0002d000,
-       0x17f104bd,
-       0x10fe0530,
-       0x0007f100,
-       0x0003f007,
-       0xbd0000d0,
-       0x0427f004,
-       0x040007f1,
-       0xd00003f0,
-       0x04bd0002,
-       0xf11031f4,
-       0xf0820027,
-       0x22cf0123,
-       0x0137f000,
-       0xbb1f24f0,
-       0x32b60432,
-       0x05028001,
-       0xf1060380,
-       0xf0860027,
-       0x22cf0123,
-       0x04028000,
-       0x0c30e7f1,
-       0xbd50e3f0,
-       0xbd34bd24,
-/* 0x0421: init_unk_loop */
-       0x6821f444,
-       0xf400f6b0,
-       0xf7f00f0b,
-       0x04f2bb01,
-       0xb6054ffd,
-/* 0x0436: init_unk_next */
-       0x20b60130,
-       0x04e0b601,
-       0xf40226b0,
-/* 0x0442: init_unk_done */
-       0x0380e21b,
-       0x08048007,
-       0x010027f1,
-       0xcf0223f0,
-       0x34bd0022,
-       0xf1082595,
-       0xf0c00007,
-       0x05d00103,
-       0xf104bd00,
-       0xf0c10007,
-       0x05d00103,
-       0x9804bd00,
-       0x0f98000e,
-       0x5021f501,
-       0x002fbb01,
-       0x98003fbb,
-       0x0f98010e,
-       0x5021f502,
-       0x050e9801,
-       0xbb00effd,
-       0x3ebb002e,
-       0x020e9800,
-       0xf5030f98,
-       0x98015021,
-       0xeffd070e,
-       0x002ebb00,
-       0xb6003ebb,
-       0x07f10235,
-       0x03f0d300,
-       0x0003d001,
-       0x25b604bd,
-       0x0635b608,
-       0xb60120b6,
-       0x24b60130,
-       0x0834b608,
-       0xf5022fb9,
-       0xbb02d321,
-       0x07f1003f,
-       0x03f00100,
-       0x0003d002,
-       0x24bd04bd,
-       0xf11f29f0,
-       0xf0300007,
-       0x02d00203,
-/* 0x04f3: main */
-       0xf404bd00,
-       0x28f40031,
-       0x24d7f000,
-       0xf43921f4,
-       0xe4b0f401,
-       0x1e18f404,
-       0xf00181fe,
-       0x20bd0627,
-       0xb60412fd,
-       0x1efd01e4,
-       0x0018fe05,
-       0x05e821f5,
-/* 0x0523: main_not_ctx_xfer */
-       0x94d30ef4,
-       0xf5f010ef,
-       0x7e21f501,
-       0xc60ef403,
-/* 0x0530: ih */
-       0x88fe80f9,
-       0xf980f901,
-       0xf9a0f990,
-       0xf9d0f9b0,
-       0xbdf0f9e0,
-       0x00a7f104,
-       0x00a3f002,
-       0xc400aacf,
-       0x0bf404ab,
-       0x24d7f02c,
-       0x1a00e7f1,
-       0xcf00e3f0,
-       0xf7f100ee,
-       0xf3f01900,
-       0x00ffcf00,
-       0xf00421f4,
-       0x07f101e7,
-       0x03f01d00,
-       0x000ed000,
-/* 0x057e: ih_no_fifo */
-       0x07f104bd,
-       0x03f00100,
-       0x000ad000,
-       0xf0fc04bd,
-       0xd0fce0fc,
-       0xa0fcb0fc,
-       0x80fc90fc,
-       0xfc0088fe,
-       0x0032f480,
-/* 0x05a2: hub_barrier_done */
-       0xf7f001f8,
-       0x040e9801,
-       0xb904febb,
-       0xe7f102ff,
-       0xe3f09418,
-       0x9d21f440,
-/* 0x05ba: ctx_redswitch */
-       0xf7f000f8,
-       0x0007f120,
-       0x0103f085,
-       0xbd000fd0,
-       0x08e7f004,
-/* 0x05cc: ctx_redswitch_delay */
-       0xf401e2b6,
-       0xf5f1fd1b,
-       0xf5f10800,
-       0x07f10200,
-       0x03f08500,
-       0x000fd001,
-       0x00f804bd,
-/* 0x05e8: ctx_xfer */
-       0x810007f1,
-       0xd00203f0,
-       0x04bd000f,
-       0xf50711f4,
-/* 0x05fb: ctx_xfer_not_load */
-       0xf505ba21,
-       0xbd026a21,
-       0xfc07f124,
-       0x0203f047,
-       0xbd0002d0,
-       0x012cf004,
-       0xf10320b6,
-       0xf04afc07,
-       0x02d00203,
-       0xf004bd00,
-       0xa5f001ac,
-       0x00b7f102,
-       0x50b3f000,
-       0xb6040c98,
-       0xbcbb0fc4,
-       0x000c9800,
-       0xf0010d98,
-       0x21f500e7,
-       0xacf0016f,
-       0x00b7f101,
-       0x50b3f040,
-       0xb6040c98,
-       0xbcbb0fc4,
-       0x010c9800,
-       0x98020d98,
-       0xe7f1060f,
-       0x21f50800,
-       0xacf0016f,
-       0x04a5f001,
-       0x3000b7f1,
-       0x9850b3f0,
-       0xc4b6040c,
-       0x00bcbb0f,
-       0x98020c98,
-       0x0f98030d,
-       0x00e7f108,
-       0x6f21f502,
-       0x5e21f501,
-       0x0601f402,
-/* 0x0697: ctx_xfer_post */
-       0xf50712f4,
-/* 0x069b: ctx_xfer_done */
-       0xf5027f21,
-       0xf805a221,
-       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/drivers/gpu/drm/nouveau/core/engine/graph/fuc/hub.fuc b/drivers/gpu/drm/nouveau/core/engine/graph/fuc/hub.fuc
deleted file mode 100644 (file)
index b4ad18b..0000000
+++ /dev/null
@@ -1,696 +0,0 @@
-/* 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
- */
-
-#ifdef INCLUDE_DATA
-hub_mmio_list_head:    .b32 #hub_mmio_list_base
-hub_mmio_list_tail:    .b32 #hub_mmio_list_next
-
-gpc_count:             .b32 0
-rop_count:             .b32 0
-cmd_queue:             queue_init
-
-ctx_current:           .b32 0
-
-.align 256
-chan_data:
-chan_mmio_count:       .b32 0
-chan_mmio_address:     .b32 0
-
-.align 256
-xfer_data:             .skip 256
-
-hub_mmio_list_base:
-.b32 0x0417e91c // 0x17e91c, 2
-hub_mmio_list_next:
-#endif
-
-#ifdef INCLUDE_CODE
-// reports an exception to the host
-//
-// In: $r15 error code (see os.h)
-//
-error:
-       nv_iowr(NV_PGRAPH_FECS_CC_SCRATCH_VAL(5), 0, $r15)
-       mov $r15 1
-       nv_iowr(NV_PGRAPH_FECS_INTR_UP_SET, 0, $r15)
-       ret
-
-// HUB fuc initialisation, executed by triggering ucode start, will
-// fall through to main loop after completion.
-//
-// Output:
-//   CC_SCRATCH[0]:
-//          31:31: set to signal completion
-//   CC_SCRATCH[1]:
-//           31:0: total PGRAPH context size
-//
-init:
-       clear b32 $r0
-       mov $xdbase $r0
-
-       // setup stack
-       nv_iord($r1, NV_PGRAPH_FECS_CAPS, 0)
-       extr $r1 $r1 9:17
-       shl b32 $r1 8
-       mov $sp $r1
-
-       // enable fifo access
-       mov $r2 NV_PGRAPH_FECS_ACCESS_FIFO
-       nv_iowr(NV_PGRAPH_FECS_ACCESS, 0, $r2)
-
-       // setup i0 handler, and route all interrupts to it
-       mov $r1 #ih
-       mov $iv0 $r1
-
-       clear b32 $r2
-       nv_iowr(NV_PGRAPH_FECS_INTR_ROUTE, 0, $r2)
-
-       // route HUB_CHSW_PULSE to fuc interrupt 8
-       mov $r2 0x2003          // { HUB_CHSW_PULSE, ZERO } -> intr 8
-       nv_iowr(NV_PGRAPH_FECS_IROUTE, 0, $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          // { 0x04, ZERO } -> intr 9
-       nv_iowr(NV_PGRAPH_FECS_IROUTE, 1, $r2)
-       mov $r2 0x200b          // { HUB_FIRMWARE_MTHD, ZERO } -> intr 10
-       nv_iowr(NV_PGRAPH_FECS_IROUTE, 2, $r2)
-       mov $r2 0x200c          // { 0x0c, ZERO } -> intr 15
-       nv_iowr(NV_PGRAPH_FECS_IROUTE, 7, $r2)
-
-       // enable all INTR_UP interrupts
-       sub b32 $r3 $r0 1
-       nv_iowr(NV_PGRAPH_FECS_INTR_UP_EN, 0, $r3)
-
-       // enable fifo, ctxsw, 9, fwmthd, 15 interrupts
-       imm32($r2, 0x8704)
-       nv_iowr(NV_PGRAPH_FECS_INTR_EN_SET, 0, $r2)
-
-       // fifo level triggered, rest edge
-       mov $r2 NV_PGRAPH_FECS_INTR_MODE_FIFO_LEVEL
-       nv_iowr(NV_PGRAPH_FECS_INTR_MODE, 0, $r2)
-
-       // enable interrupts
-       bset $flags ie0
-
-       // fetch enabled GPC/ROP counts
-       nv_rd32($r14, 0x409604)
-       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
-       nv_iowr(NV_PGRAPH_FECS_BAR_MASK0, 0, $r1)
-       nv_iowr(NV_PGRAPH_FECS_BAR_MASK1, 0, $r1)
-
-       // context size calculation, reserve first 256 bytes for use by fuc
-       mov $r1 256
-
-       //
-       mov $r15 2
-       call(ctx_4170s)
-       call(ctx_4170w)
-       mov $r15 0x10
-       call(ctx_86c)
-
-       // calculate size of mmio context data
-       ld b32 $r14 D[$r0 + #hub_mmio_list_head]
-       ld b32 $r15 D[$r0 + #hub_mmio_list_tail]
-       call(mmctx_size)
-
-       // set mmctx base addresses now so we don't have to do it later,
-       // they don't (currently) ever change
-       shr b32 $r4 $r1 8
-       nv_iowr(NV_PGRAPH_FECS_MMCTX_SAVE_SWBASE, 0, $r4)
-       nv_iowr(NV_PGRAPH_FECS_MMCTX_LOAD_SWBASE, 0, $r4)
-       add b32 $r3 0x1300
-       add b32 $r1 $r15
-       shr b32 $r15 2
-       nv_iowr(NV_PGRAPH_FECS_MMCTX_LOAD_COUNT, 0, $r15) // wtf??
-
-       // 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]
-       imm32($r4, 0x502000)
-       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 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
-
-       //
-       mov $r15 0
-       call(ctx_86c)
-       mov $r15 0
-       call(ctx_4170s)
-
-       // save context size, and tell host we're ready
-       nv_iowr(NV_PGRAPH_FECS_CC_SCRATCH_VAL(1), 0, $r1)
-       clear b32 $r1
-       bset $r1 31
-       nv_iowr(NV_PGRAPH_FECS_CC_SCRATCH_SET(0), 0, $r1)
-
-// 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)
-               nv_iord($r1, NV_PGRAPH_FECS_CHAN_ADDR, 0)
-               nv_iord($r2, NV_PGRAPH_FECS_CHAN_NEXT, 0)
-
-               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
-                               nv_iowr(NV_PGRAPH_FECS_CHAN_ADDR, 0, $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 $r2 NV_PGRAPH_FECS_CHSW_ACK
-               nv_iowr(NV_PGRAPH_FECS_CHSW, 0, $r2)
-               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:
-       clear b32 $r2
-       bset $r2 31
-       nv_iowr(NV_PGRAPH_FECS_CC_SCRATCH_SET(0), 0, $r2)
-       bra #main
-
-// interrupt handler
-ih:
-       push $r8
-       mov $r8 $flags
-       push $r8
-       push $r9
-       push $r10
-       push $r11
-       push $r13
-       push $r14
-       push $r15
-       clear b32 $r0
-
-       // incoming fifo command?
-       nv_iord($r10, NV_PGRAPH_FECS_INTR, 0)
-       and $r11 $r10 NV_PGRAPH_FECS_INTR_FIFO
-       bra e #ih_no_fifo
-               // queue incoming fifo command for later processing
-               mov $r13 #cmd_queue
-               nv_iord($r14, NV_PGRAPH_FECS_FIFO_CMD, 0)
-               nv_iord($r15, NV_PGRAPH_FECS_FIFO_DATA, 0)
-               call(queue_put)
-               add b32 $r11 0x400
-               mov $r14 1
-               nv_iowr(NV_PGRAPH_FECS_FIFO_ACK, 0, $r14)
-
-       // context switch request?
-       ih_no_fifo:
-       and $r11 $r10 NV_PGRAPH_FECS_INTR_CHSW
-       bra e #ih_no_ctxsw
-               // enqueue a context switch for later processing
-               mov $r13 #cmd_queue
-               mov $r14 0x4001
-               call(queue_put)
-
-       // firmware method?
-       ih_no_ctxsw:
-       and $r11 $r10 NV_PGRAPH_FECS_INTR_FWMTHD
-       bra e #ih_no_fwmthd
-               // none we handle; report to host and ack
-               nv_rd32($r15, NV_PGRAPH_TRAPPED_DATA_LO)
-               nv_iowr(NV_PGRAPH_FECS_CC_SCRATCH_VAL(4), 0, $r15)
-               nv_rd32($r15, NV_PGRAPH_TRAPPED_ADDR)
-               nv_iowr(NV_PGRAPH_FECS_CC_SCRATCH_VAL(3), 0, $r15)
-               extr $r14 $r15 16:18
-               shl b32 $r14 $r14 2
-               imm32($r15, NV_PGRAPH_FE_OBJECT_TABLE(0))
-               add b32 $r14 $r15
-               call(nv_rd32)
-               nv_iowr(NV_PGRAPH_FECS_CC_SCRATCH_VAL(2), 0, $r15)
-               mov $r15 E_BAD_FWMTHD
-               call(error)
-               mov $r11 0x100
-               nv_wr32(0x400144, $r11)
-
-       // anything we didn't handle, bring it to the host's attention
-       ih_no_fwmthd:
-       mov $r11 0x504 // FIFO | CHSW | FWMTHD
-       not b32 $r11
-       and $r11 $r10 $r11
-       bra e #ih_no_other
-               nv_iowr(NV_PGRAPH_FECS_INTR_UP_SET, 0, $r11)
-
-       // ack, and wake up main()
-       ih_no_other:
-       nv_iowr(NV_PGRAPH_FECS_INTR_ACK, 0, $r10)
-
-       pop $r15
-       pop $r14
-       pop $r13
-       pop $r11
-       pop $r10
-       pop $r9
-       pop $r8
-       mov $flags $r8
-       pop $r8
-       bclr $flags $p0
-       iret
-
-#if CHIPSET < GK100
-// Not real sure, but, MEM_CMD 7 will hang forever if this isn't done
-ctx_4160s:
-       mov $r15 1
-       nv_wr32(0x404160, $r15)
-       ctx_4160s_wait:
-               nv_rd32($r15, 0x404160)
-               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:
-       clear b32 $r15
-       nv_wr32(0x404160, $r15)
-       ret
-#endif
-
-// Again, not real sure
-//
-// In: $r15 value to set 0x404170 to
-//
-ctx_4170s:
-       or $r15 0x10
-       nv_wr32(0x404170, $r15)
-       ret
-
-// Waits for a ctx_4170s() call to complete
-//
-ctx_4170w:
-       nv_rd32($r15, 0x404170)
-       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 NV_PGRAPH_FECS_RED_SWITCH_ENABLE_GPC
-       or  $r14 NV_PGRAPH_FECS_RED_SWITCH_POWER_ROP
-       or  $r14 NV_PGRAPH_FECS_RED_SWITCH_POWER_GPC
-       or  $r14 NV_PGRAPH_FECS_RED_SWITCH_POWER_MAIN
-       nv_iowr(NV_PGRAPH_FECS_RED_SWITCH, 0, $r14)
-       mov $r15 8
-       ctx_redswitch_delay:
-               sub b32 $r15 1
-               bra ne #ctx_redswitch_delay
-       or  $r14 NV_PGRAPH_FECS_RED_SWITCH_ENABLE_ROP
-       or  $r14 NV_PGRAPH_FECS_RED_SWITCH_ENABLE_MAIN
-       nv_iowr(NV_PGRAPH_FECS_RED_SWITCH, 0, $r14)
-       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:
-       nv_iowr(NV_PGRAPH_FECS_UNK86C, 0, $r15)
-       nv_wr32(0x408a14, $r15)
-       nv_wr32(NV_PGRAPH_GPCX_GPCCS_UNK86C, $r15)
-       ret
-
-// In: $r15 NV_PGRAPH_FECS_MEM_CMD_*
-ctx_mem:
-       nv_iowr(NV_PGRAPH_FECS_MEM_CMD, 0, $r15)
-       ctx_mem_wait:
-               nv_iord($r15, NV_PGRAPH_FECS_MEM_CMD, 0)
-               or $r15 $r15
-               bra ne #ctx_mem_wait
-       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)
-       clear b32 $r15
-       nv_iowr(0x409a24, 0, $r15)
-       nv_iowr(NV_PGRAPH_FECS_CHAN_NEXT, 0, $r2)
-       nv_iowr(NV_PGRAPH_FECS_MEM_CHAN, 0, $r2)
-       mov $r15 NV_PGRAPH_FECS_MEM_CMD_LOAD_CHAN
-       call(ctx_mem)
-       nv_iowr(NV_PGRAPH_FECS_CHAN_ADDR, 0, $r2)
-
-       // 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)
-       nv_iowr(NV_PGRAPH_FECS_MEM_BASE, 0, $r2)
-       imm32($r2, NV_PGRAPH_FECS_MEM_TARGET_UNK31)
-       or  $r2 NV_PGRAPH_FECS_MEM_TARGET_AS_VRAM
-       nv_iowr(NV_PGRAPH_FECS_MEM_TARGET, 0, $r2)
-       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)
-       nv_iowr(NV_PGRAPH_FECS_MEM_BASE, 0, $r1)
-       mov $r2 NV_PGRAPH_FECS_MEM_TARGET_AS_VM
-       nv_iowr(NV_PGRAPH_FECS_MEM_TARGET, 0, $r2)
-       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:
-#if CHIPSET < GK100
-       call(ctx_4160s)
-#endif
-       call(ctx_load)
-       mov $r10 12                     // DONE_UNK12
-       call(wait_donez)
-       mov $r15 5 // MEM_CMD 5 ???
-       call(ctx_mem)
-#if CHIPSET < GK100
-       call(ctx_4160c)
-#endif
-       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]
-       nv_iowr(NV_PGRAPH_FECS_MEM_BASE, 0, $r3)
-
-       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]
-       nv_iowr(NV_PGRAPH_FECS_MEM_BASE, 0, $r3)
-
-       // 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:
-       // according to mwk, some kind of wait for idle
-       mov $r14 4
-       nv_iowr(0x409c08, 0, $r14)
-       ctx_xfer_idle:
-               nv_iord($r14, 0x409c00, 0)
-               and $r14 0x2000
-               bra ne #ctx_xfer_idle
-
-       bra not $p1 #ctx_xfer_pre
-       bra $p2 #ctx_xfer_pre_load
-       ctx_xfer_pre:
-               mov $r15 0x10
-               call(ctx_86c)
-#if CHIPSET < GK100
-               call(ctx_4160s)
-#endif
-               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]
-
-       clear b32 $r2
-       nv_iowr(NV_PGRAPH_FECS_BAR, 0, $r2)
-
-       nv_wr32(0x41a500, $r1)  // GPC_BCAST_WRCMD_DATA = ctx pointer
-       xbit $r15 $flags $p1
-       xbit $r2 $flags $p2
-       shl b32 $r2 1
-       or $r15 $r2
-       nv_wr32(0x41a504, $r15) // GPC_BCAST_WRCMD_CMD = GPC_XFER(type)
-
-       // strands
-       call(strand_pre)
-       clear b32 $r2
-       nv_iowr(NV_PGRAPH_FECS_STRAND_SELECT, 0x3f, $r2)
-       xbit $r2 $flags $p1     // SAVE/LOAD
-       add b32 $r2 NV_PGRAPH_FECS_STRAND_CMD_SAVE
-       nv_iowr(NV_PGRAPH_FECS_STRAND_CMD, 0x3f, $r2)
-
-       // 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 $r15 5 // MEM_CMD 5 ???
-               call(ctx_mem)
-
-       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:
-#if CHIPSET < GK100
-               call(ctx_4160c)
-#endif
-
-       ctx_xfer_done:
-       ret
-#endif
diff --git a/drivers/gpu/drm/nouveau/core/engine/graph/fuc/hubgm107.fuc5 b/drivers/gpu/drm/nouveau/core/engine/graph/fuc/hubgm107.fuc5
deleted file mode 100644 (file)
index 27591b3..0000000
+++ /dev/null
@@ -1,40 +0,0 @@
-/*
- * Copyright 2013 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 <bskeggs@redhat.com>
- */
-
-#define CHIPSET GK208
-#include "macros.fuc"
-
-.section #gm107_grhub_data
-#define INCLUDE_DATA
-#include "com.fuc"
-#include "hub.fuc"
-#undef INCLUDE_DATA
-
-.section #gm107_grhub_code
-#define INCLUDE_CODE
-bra #init
-#include "com.fuc"
-#include "hub.fuc"
-.align 256
-#undef INCLUDE_CODE
diff --git a/drivers/gpu/drm/nouveau/core/engine/graph/fuc/hubgm107.fuc5.h b/drivers/gpu/drm/nouveau/core/engine/graph/fuc/hubgm107.fuc5.h
deleted file mode 100644 (file)
index 5f953c5..0000000
+++ /dev/null
@@ -1,916 +0,0 @@
-uint32_t gm107_grhub_data[] = {
-/* 0x0000: hub_mmio_list_head */
-       0x00000300,
-/* 0x0004: hub_mmio_list_tail */
-       0x00000304,
-/* 0x0008: gpc_count */
-       0x00000000,
-/* 0x000c: rop_count */
-       0x00000000,
-/* 0x0010: cmd_queue */
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-/* 0x0058: ctx_current */
-       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,
-/* 0x0100: chan_data */
-/* 0x0100: chan_mmio_count */
-       0x00000000,
-/* 0x0104: chan_mmio_address */
-       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,
-/* 0x0200: xfer_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,
-/* 0x0300: hub_mmio_list_base */
-       0x0417e91c,
-};
-
-uint32_t gm107_grhub_code[] = {
-       0x030e0ef5,
-/* 0x0004: queue_put */
-       0x9800d898,
-       0x86f001d9,
-       0xf489a408,
-       0x020f0b1b,
-       0x0002f87e,
-/* 0x001a: queue_put_next */
-       0x98c400f8,
-       0x0384b607,
-       0xb6008dbb,
-       0x8eb50880,
-       0x018fb500,
-       0xf00190b6,
-       0xd9b50f94,
-/* 0x0037: queue_get */
-       0xf400f801,
-       0xd8980131,
-       0x01d99800,
-       0x0bf489a4,
-       0x0789c421,
-       0xbb0394b6,
-       0x90b6009d,
-       0x009e9808,
-       0xb6019f98,
-       0x84f00180,
-       0x00d8b50f,
-/* 0x0063: queue_get_done */
-       0xf80132f4,
-/* 0x0065: nv_rd32 */
-       0xf0ecb200,
-       0x00801fc9,
-       0x0cf601ca,
-/* 0x0073: nv_rd32_wait */
-       0x8c04bd00,
-       0xcf01ca00,
-       0xccc800cc,
-       0xf61bf41f,
-       0xec7e060a,
-       0x008f0000,
-       0xffcf01cb,
-/* 0x008f: nv_wr32 */
-       0x8000f800,
-       0xf601cc00,
-       0x04bd000f,
-       0xc9f0ecb2,
-       0x1ec9f01f,
-       0x01ca0080,
-       0xbd000cf6,
-/* 0x00a9: nv_wr32_wait */
-       0xca008c04,
-       0x00cccf01,
-       0xf41fccc8,
-       0x00f8f61b,
-/* 0x00b8: wait_donez */
-       0x99f094bd,
-       0x37008000,
-       0x0009f602,
-       0x008004bd,
-       0x0af60206,
-/* 0x00cf: wait_donez_ne */
-       0x8804bd00,
-       0xcf010000,
-       0x8aff0088,
-       0xf61bf488,
-       0x99f094bd,
-       0x17008000,
-       0x0009f602,
-       0x00f804bd,
-/* 0x00ec: wait_doneo */
-       0x99f094bd,
-       0x37008000,
-       0x0009f602,
-       0x008004bd,
-       0x0af60206,
-/* 0x0103: wait_doneo_e */
-       0x8804bd00,
-       0xcf010000,
-       0x8aff0088,
-       0xf60bf488,
-       0x99f094bd,
-       0x17008000,
-       0x0009f602,
-       0x00f804bd,
-/* 0x0120: mmctx_size */
-/* 0x0122: nv_mmctx_size_loop */
-       0xe89894bd,
-       0x1a85b600,
-       0xb60180b6,
-       0x98bb0284,
-       0x04e0b600,
-       0x1bf4efa4,
-       0xf89fb2ec,
-/* 0x013d: mmctx_xfer */
-       0xf094bd00,
-       0x00800199,
-       0x09f60237,
-       0xbd04bd00,
-       0x05bbfd94,
-       0x800f0bf4,
-       0xf601c400,
-       0x04bd000b,
-/* 0x015f: mmctx_base_disabled */
-       0xfd0099f0,
-       0x0bf405ee,
-       0xc6008018,
-       0x000ef601,
-       0x008004bd,
-       0x0ff601c7,
-       0xf004bd00,
-/* 0x017a: mmctx_multi_disabled */
-       0xabc80199,
-       0x10b4b600,
-       0xc80cb9f0,
-       0xe4b601ae,
-       0x05befd11,
-       0x01c50080,
-       0xbd000bf6,
-/* 0x0195: mmctx_exec_loop */
-/* 0x0195: mmctx_wait_free */
-       0xc5008e04,
-       0x00eecf01,
-       0xf41fe4f0,
-       0xce98f60b,
-       0x05e9fd00,
-       0x01c80080,
-       0xbd000ef6,
-       0x04c0b604,
-       0x1bf4cda4,
-       0x02abc8df,
-/* 0x01bf: mmctx_fini_wait */
-       0x8b1c1bf4,
-       0xcf01c500,
-       0xb4f000bb,
-       0x10b4b01f,
-       0x0af31bf4,
-       0x00b87e05,
-       0x250ef400,
-/* 0x01d8: mmctx_stop */
-       0xb600abc8,
-       0xb9f010b4,
-       0x12b9f00c,
-       0x01c50080,
-       0xbd000bf6,
-/* 0x01ed: mmctx_stop_wait */
-       0xc5008b04,
-       0x00bbcf01,
-       0xf412bbc8,
-/* 0x01fa: mmctx_done */
-       0x94bdf61b,
-       0x800199f0,
-       0xf6021700,
-       0x04bd0009,
-/* 0x020a: strand_wait */
-       0xa0f900f8,
-       0xb87e020a,
-       0xa0fc0000,
-/* 0x0216: strand_pre */
-       0x0c0900f8,
-       0x024afc80,
-       0xbd0009f6,
-       0x020a7e04,
-/* 0x0227: strand_post */
-       0x0900f800,
-       0x4afc800d,
-       0x0009f602,
-       0x0a7e04bd,
-       0x00f80002,
-/* 0x0238: strand_set */
-       0xfc800f0c,
-       0x0cf6024f,
-       0x0c04bd00,
-       0x4afc800b,
-       0x000cf602,
-       0xfc8004bd,
-       0x0ef6024f,
-       0x0c04bd00,
-       0x4afc800a,
-       0x000cf602,
-       0x0a7e04bd,
-       0x00f80002,
-/* 0x0268: strand_ctx_init */
-       0x99f094bd,
-       0x37008003,
-       0x0009f602,
-       0x167e04bd,
-       0x030e0002,
-       0x0002387e,
-       0xfc80c4bd,
-       0x0cf60247,
-       0x0c04bd00,
-       0x4afc8001,
-       0x000cf602,
-       0x0a7e04bd,
-       0x0c920002,
-       0x46fc8001,
-       0x000cf602,
-       0x020c04bd,
-       0x024afc80,
-       0xbd000cf6,
-       0x020a7e04,
-       0x02277e00,
-       0x42008800,
-       0x20008902,
-       0x0099cf02,
-/* 0x02c7: ctx_init_strand_loop */
-       0xf608fe95,
-       0x8ef6008e,
-       0x808acf40,
-       0xb606a5b6,
-       0xeabb01a0,
-       0x0480b600,
-       0xf40192b6,
-       0xe4b6e81b,
-       0xf2efbc08,
-       0x99f094bd,
-       0x17008003,
-       0x0009f602,
-       0x00f804bd,
-/* 0x02f8: error */
-       0x02050080,
-       0xbd000ff6,
-       0x80010f04,
-       0xf6030700,
-       0x04bd000f,
-/* 0x030e: init */
-       0x04bd00f8,
-       0x410007fe,
-       0x11cf4200,
-       0x0911e700,
-       0x0814b601,
-       0x020014fe,
-       0x12004002,
-       0xbd0002f6,
-       0x05c94104,
-       0xbd0010fe,
-       0x07004024,
-       0xbd0002f6,
-       0x20034204,
-       0x01010080,
-       0xbd0002f6,
-       0x20044204,
-       0x01010480,
-       0xbd0002f6,
-       0x200b4204,
-       0x01010880,
-       0xbd0002f6,
-       0x200c4204,
-       0x01011c80,
-       0xbd0002f6,
-       0x01039204,
-       0x03090080,
-       0xbd0003f6,
-       0x87044204,
-       0xf6040040,
-       0x04bd0002,
-       0x00400402,
-       0x0002f603,
-       0x31f404bd,
-       0x96048e10,
-       0x00657e40,
-       0xc7feb200,
-       0x01b590f1,
-       0x1ff4f003,
-       0x01020fb5,
-       0x041fbb01,
-       0x800112b6,
-       0xf6010300,
-       0x04bd0001,
-       0x01040080,
-       0xbd0001f6,
-       0x01004104,
-       0xa87e020f,
-       0xb77e0006,
-       0x100f0006,
-       0x0006f97e,
-       0x98000e98,
-       0x207e010f,
-       0x14950001,
-       0xc0008008,
-       0x0004f601,
-       0x008004bd,
-       0x04f601c1,
-       0xb704bd00,
-       0xbb130030,
-       0xf5b6001f,
-       0xd3008002,
-       0x000ff601,
-       0x15b604bd,
-       0x0110b608,
-       0xb20814b6,
-       0x02687e1f,
-       0x001fbb00,
-       0x84020398,
-/* 0x041f: init_gpc */
-       0xb8502000,
-       0x0008044e,
-       0x8f7e1fb2,
-       0x4eb80000,
-       0xbd00010c,
-       0x008f7ef4,
-       0x044eb800,
-       0x8f7e0001,
-       0x4eb80000,
-       0x0f000100,
-       0x008f7e02,
-       0x004eb800,
-/* 0x044e: init_gpc_wait */
-       0x657e0008,
-       0xffc80000,
-       0xf90bf41f,
-       0x08044eb8,
-       0x00657e00,
-       0x001fbb00,
-       0x800040b7,
-       0xf40132b6,
-       0x000fb41b,
-       0x0006f97e,
-       0xa87e000f,
-       0x00800006,
-       0x01f60201,
-       0xbd04bd00,
-       0x1f19f014,
-       0x02300080,
-       0xbd0001f6,
-/* 0x0491: main */
-       0x0031f404,
-       0x0d0028f4,
-       0x00377e10,
-       0xf401f400,
-       0x4001e4b1,
-       0x00c71bf5,
-       0x99f094bd,
-       0x37008004,
-       0x0009f602,
-       0x008104bd,
-       0x11cf02c0,
-       0xc1008200,
-       0x0022cf02,
-       0xf41f13c8,
-       0x23c8770b,
-       0x550bf41f,
-       0x12b220f9,
-       0x99f094bd,
-       0x37008007,
-       0x0009f602,
-       0x32f404bd,
-       0x0231f401,
-       0x00087c7e,
-       0x99f094bd,
-       0x17008007,
-       0x0009f602,
-       0x20fc04bd,
-       0x99f094bd,
-       0x37008006,
-       0x0009f602,
-       0x31f404bd,
-       0x087c7e01,
-       0xf094bd00,
-       0x00800699,
-       0x09f60217,
-       0xf404bd00,
-/* 0x0522: chsw_prev_no_next */
-       0x20f92f0e,
-       0x32f412b2,
-       0x0232f401,
-       0x00087c7e,
-       0x008020fc,
-       0x02f602c0,
-       0xf404bd00,
-/* 0x053e: chsw_no_prev */
-       0x23c8130e,
-       0x0d0bf41f,
-       0xf40131f4,
-       0x7c7e0232,
-/* 0x054e: chsw_done */
-       0x01020008,
-       0x02c30080,
-       0xbd0002f6,
-       0xf094bd04,
-       0x00800499,
-       0x09f60217,
-       0xf504bd00,
-/* 0x056b: main_not_ctx_switch */
-       0xb0ff2a0e,
-       0x1bf401e4,
-       0x7ef2b20c,
-       0xf400081c,
-/* 0x057a: main_not_ctx_chan */
-       0xe4b0400e,
-       0x2c1bf402,
-       0x99f094bd,
-       0x37008007,
-       0x0009f602,
-       0x32f404bd,
-       0x0232f401,
-       0x00087c7e,
-       0x99f094bd,
-       0x17008007,
-       0x0009f602,
-       0x0ef404bd,
-/* 0x05a9: main_not_ctx_save */
-       0x10ef9411,
-       0x7e01f5f0,
-       0xf50002f8,
-/* 0x05b7: main_done */
-       0xbdfede0e,
-       0x1f29f024,
-       0x02300080,
-       0xbd0002f6,
-       0xcc0ef504,
-/* 0x05c9: ih */
-       0xfe80f9fe,
-       0x80f90188,
-       0xa0f990f9,
-       0xd0f9b0f9,
-       0xf0f9e0f9,
-       0x004a04bd,
-       0x00aacf02,
-       0xf404abc4,
-       0x100d230b,
-       0xcf1a004e,
-       0x004f00ee,
-       0x00ffcf19,
-       0x0000047e,
-       0x0400b0b7,
-       0x0040010e,
-       0x000ef61d,
-/* 0x060a: ih_no_fifo */
-       0xabe404bd,
-       0x0bf40100,
-       0x4e100d0c,
-       0x047e4001,
-/* 0x061a: ih_no_ctxsw */
-       0xabe40000,
-       0x0bf40400,
-       0x07088e56,
-       0x00657e40,
-       0x80ffb200,
-       0xf6020400,
-       0x04bd000f,
-       0x4007048e,
-       0x0000657e,
-       0x0080ffb2,
-       0x0ff60203,
-       0xc704bd00,
-       0xee9450fe,
-       0x07008f02,
-       0x00efbb40,
-       0x0000657e,
-       0x02020080,
-       0xbd000ff6,
-       0x7e030f04,
-       0x4b0002f8,
-       0xbfb20100,
-       0x4001448e,
-       0x00008f7e,
-/* 0x0674: ih_no_fwmthd */
-       0xbd05044b,
-       0xb4abffb0,
-       0x800c0bf4,
-       0xf6030700,
-       0x04bd000b,
-/* 0x0688: ih_no_other */
-       0xf6010040,
-       0x04bd000a,
-       0xe0fcf0fc,
-       0xb0fcd0fc,
-       0x90fca0fc,
-       0x88fe80fc,
-       0xf480fc00,
-       0x01f80032,
-/* 0x06a8: ctx_4170s */
-       0xb210f5f0,
-       0x41708eff,
-       0x008f7e40,
-/* 0x06b7: ctx_4170w */
-       0x8e00f800,
-       0x7e404170,
-       0xb2000065,
-       0x10f4f0ff,
-       0xf8f31bf4,
-/* 0x06c9: ctx_redswitch */
-       0x02004e00,
-       0xf040e5f0,
-       0xe5f020e5,
-       0x85008010,
-       0x000ef601,
-       0x080f04bd,
-/* 0x06e0: ctx_redswitch_delay */
-       0xf401f2b6,
-       0xe5f1fd1b,
-       0xe5f10400,
-       0x00800100,
-       0x0ef60185,
-       0xf804bd00,
-/* 0x06f9: ctx_86c */
-       0x23008000,
-       0x000ff602,
-       0xffb204bd,
-       0x408a148e,
-       0x00008f7e,
-       0x8c8effb2,
-       0x8f7e41a8,
-       0x00f80000,
-/* 0x0718: ctx_mem */
-       0x02840080,
-       0xbd000ff6,
-/* 0x0721: ctx_mem_wait */
-       0x84008f04,
-       0x00ffcf02,
-       0xf405fffd,
-       0x00f8f61b,
-/* 0x0730: ctx_load */
-       0x99f094bd,
-       0x37008005,
-       0x0009f602,
-       0x0c0a04bd,
-       0x0000b87e,
-       0x0080f4bd,
-       0x0ff60289,
-       0x8004bd00,
-       0xf602c100,
-       0x04bd0002,
-       0x02830080,
-       0xbd0002f6,
-       0x7e070f04,
-       0x80000718,
-       0xf602c000,
-       0x04bd0002,
-       0xf0000bfe,
-       0x24b61f2a,
-       0x0220b604,
-       0x99f094bd,
-       0x37008008,
-       0x0009f602,
-       0x008004bd,
-       0x02f60281,
-       0xd204bd00,
-       0x80000000,
-       0x800225f0,
-       0xf6028800,
-       0x04bd0002,
-       0x00421001,
-       0x0223f002,
-       0xf80512fa,
-       0xf094bd03,
-       0x00800899,
-       0x09f60217,
-       0x9804bd00,
-       0x14b68101,
-       0x80029818,
-       0xfd0825b6,
-       0x01b50512,
-       0xf094bd16,
-       0x00800999,
-       0x09f60237,
-       0x8004bd00,
-       0xf6028100,
-       0x04bd0001,
-       0x00800102,
-       0x02f60288,
-       0x4104bd00,
-       0x13f00100,
-       0x0501fa06,
-       0x94bd03f8,
-       0x800999f0,
-       0xf6021700,
-       0x04bd0009,
-       0x99f094bd,
-       0x17008005,
-       0x0009f602,
-       0x00f804bd,
-/* 0x081c: ctx_chan */
-       0x0007307e,
-       0xb87e0c0a,
-       0x050f0000,
-       0x0007187e,
-/* 0x082e: ctx_mmio_exec */
-       0x039800f8,
-       0x81008041,
-       0x0003f602,
-       0x34bd04bd,
-/* 0x083c: ctx_mmio_loop */
-       0xf4ff34c4,
-       0x00450e1b,
-       0x0653f002,
-       0xf80535fa,
-/* 0x084d: ctx_mmio_pull */
-       0x804e9803,
-       0x7e814f98,
-       0xb600008f,
-       0x12b60830,
-       0xdf1bf401,
-/* 0x0860: ctx_mmio_done */
-       0x80160398,
-       0xf6028100,
-       0x04bd0003,
-       0x414000b5,
-       0x13f00100,
-       0x0601fa06,
-       0x00f803f8,
-/* 0x087c: ctx_xfer */
-       0x0080040e,
-       0x0ef60302,
-/* 0x0887: ctx_xfer_idle */
-       0x8e04bd00,
-       0xcf030000,
-       0xe4f100ee,
-       0x1bf42000,
-       0x0611f4f5,
-/* 0x089b: ctx_xfer_pre */
-       0x0f0c02f4,
-       0x06f97e10,
-       0x1b11f400,
-/* 0x08a4: ctx_xfer_pre_load */
-       0xa87e020f,
-       0xb77e0006,
-       0xc97e0006,
-       0xf4bd0006,
-       0x0006a87e,
-       0x0007307e,
-/* 0x08bc: ctx_xfer_exec */
-       0xbd160198,
-       0x05008024,
-       0x0002f601,
-       0x1fb204bd,
-       0x41a5008e,
-       0x00008f7e,
-       0xf001fcf0,
-       0x24b6022c,
-       0x05f2fd01,
-       0x048effb2,
-       0x8f7e41a5,
-       0x167e0000,
-       0x24bd0002,
-       0x0247fc80,
-       0xbd0002f6,
-       0x012cf004,
-       0x800320b6,
-       0xf6024afc,
-       0x04bd0002,
-       0xf001acf0,
-       0x000b06a5,
-       0x98000c98,
-       0x000e010d,
-       0x00013d7e,
-       0xec7e080a,
-       0x0a7e0000,
-       0x01f40002,
-       0x7e0c0a12,
-       0x0f0000b8,
-       0x07187e05,
-       0x2d02f400,
-/* 0x0938: ctx_xfer_post */
-       0xa87e020f,
-       0xf4bd0006,
-       0x0006f97e,
-       0x0002277e,
-       0x0006b77e,
-       0xa87ef4bd,
-       0x11f40006,
-       0x40019810,
-       0xf40511fd,
-       0x2e7e070b,
-/* 0x0962: ctx_xfer_no_post_mmio */
-/* 0x0962: ctx_xfer_done */
-       0x00f80008,
-       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/drivers/gpu/drm/nouveau/core/engine/graph/fuc/hubnv108.fuc5 b/drivers/gpu/drm/nouveau/core/engine/graph/fuc/hubnv108.fuc5
deleted file mode 100644 (file)
index 7c5d256..0000000
+++ /dev/null
@@ -1,40 +0,0 @@
-/*
- * Copyright 2013 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 <bskeggs@redhat.com>
- */
-
-#define CHIPSET GK208
-#include "macros.fuc"
-
-.section #nv108_grhub_data
-#define INCLUDE_DATA
-#include "com.fuc"
-#include "hub.fuc"
-#undef INCLUDE_DATA
-
-.section #nv108_grhub_code
-#define INCLUDE_CODE
-bra #init
-#include "com.fuc"
-#include "hub.fuc"
-.align 256
-#undef INCLUDE_CODE
diff --git a/drivers/gpu/drm/nouveau/core/engine/graph/fuc/hubnv108.fuc5.h b/drivers/gpu/drm/nouveau/core/engine/graph/fuc/hubnv108.fuc5.h
deleted file mode 100644 (file)
index e49b5a8..0000000
+++ /dev/null
@@ -1,916 +0,0 @@
-uint32_t nv108_grhub_data[] = {
-/* 0x0000: hub_mmio_list_head */
-       0x00000300,
-/* 0x0004: hub_mmio_list_tail */
-       0x00000304,
-/* 0x0008: gpc_count */
-       0x00000000,
-/* 0x000c: rop_count */
-       0x00000000,
-/* 0x0010: cmd_queue */
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-/* 0x0058: ctx_current */
-       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,
-/* 0x0100: chan_data */
-/* 0x0100: chan_mmio_count */
-       0x00000000,
-/* 0x0104: chan_mmio_address */
-       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,
-/* 0x0200: xfer_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,
-/* 0x0300: hub_mmio_list_base */
-       0x0417e91c,
-};
-
-uint32_t nv108_grhub_code[] = {
-       0x030e0ef5,
-/* 0x0004: queue_put */
-       0x9800d898,
-       0x86f001d9,
-       0xf489a408,
-       0x020f0b1b,
-       0x0002f87e,
-/* 0x001a: queue_put_next */
-       0x98c400f8,
-       0x0384b607,
-       0xb6008dbb,
-       0x8eb50880,
-       0x018fb500,
-       0xf00190b6,
-       0xd9b50f94,
-/* 0x0037: queue_get */
-       0xf400f801,
-       0xd8980131,
-       0x01d99800,
-       0x0bf489a4,
-       0x0789c421,
-       0xbb0394b6,
-       0x90b6009d,
-       0x009e9808,
-       0xb6019f98,
-       0x84f00180,
-       0x00d8b50f,
-/* 0x0063: queue_get_done */
-       0xf80132f4,
-/* 0x0065: nv_rd32 */
-       0xf0ecb200,
-       0x00801fc9,
-       0x0cf601ca,
-/* 0x0073: nv_rd32_wait */
-       0x8c04bd00,
-       0xcf01ca00,
-       0xccc800cc,
-       0xf61bf41f,
-       0xec7e060a,
-       0x008f0000,
-       0xffcf01cb,
-/* 0x008f: nv_wr32 */
-       0x8000f800,
-       0xf601cc00,
-       0x04bd000f,
-       0xc9f0ecb2,
-       0x1ec9f01f,
-       0x01ca0080,
-       0xbd000cf6,
-/* 0x00a9: nv_wr32_wait */
-       0xca008c04,
-       0x00cccf01,
-       0xf41fccc8,
-       0x00f8f61b,
-/* 0x00b8: wait_donez */
-       0x99f094bd,
-       0x37008000,
-       0x0009f602,
-       0x008004bd,
-       0x0af60206,
-/* 0x00cf: wait_donez_ne */
-       0x8804bd00,
-       0xcf010000,
-       0x8aff0088,
-       0xf61bf488,
-       0x99f094bd,
-       0x17008000,
-       0x0009f602,
-       0x00f804bd,
-/* 0x00ec: wait_doneo */
-       0x99f094bd,
-       0x37008000,
-       0x0009f602,
-       0x008004bd,
-       0x0af60206,
-/* 0x0103: wait_doneo_e */
-       0x8804bd00,
-       0xcf010000,
-       0x8aff0088,
-       0xf60bf488,
-       0x99f094bd,
-       0x17008000,
-       0x0009f602,
-       0x00f804bd,
-/* 0x0120: mmctx_size */
-/* 0x0122: nv_mmctx_size_loop */
-       0xe89894bd,
-       0x1a85b600,
-       0xb60180b6,
-       0x98bb0284,
-       0x04e0b600,
-       0x1bf4efa4,
-       0xf89fb2ec,
-/* 0x013d: mmctx_xfer */
-       0xf094bd00,
-       0x00800199,
-       0x09f60237,
-       0xbd04bd00,
-       0x05bbfd94,
-       0x800f0bf4,
-       0xf601c400,
-       0x04bd000b,
-/* 0x015f: mmctx_base_disabled */
-       0xfd0099f0,
-       0x0bf405ee,
-       0xc6008018,
-       0x000ef601,
-       0x008004bd,
-       0x0ff601c7,
-       0xf004bd00,
-/* 0x017a: mmctx_multi_disabled */
-       0xabc80199,
-       0x10b4b600,
-       0xc80cb9f0,
-       0xe4b601ae,
-       0x05befd11,
-       0x01c50080,
-       0xbd000bf6,
-/* 0x0195: mmctx_exec_loop */
-/* 0x0195: mmctx_wait_free */
-       0xc5008e04,
-       0x00eecf01,
-       0xf41fe4f0,
-       0xce98f60b,
-       0x05e9fd00,
-       0x01c80080,
-       0xbd000ef6,
-       0x04c0b604,
-       0x1bf4cda4,
-       0x02abc8df,
-/* 0x01bf: mmctx_fini_wait */
-       0x8b1c1bf4,
-       0xcf01c500,
-       0xb4f000bb,
-       0x10b4b01f,
-       0x0af31bf4,
-       0x00b87e05,
-       0x250ef400,
-/* 0x01d8: mmctx_stop */
-       0xb600abc8,
-       0xb9f010b4,
-       0x12b9f00c,
-       0x01c50080,
-       0xbd000bf6,
-/* 0x01ed: mmctx_stop_wait */
-       0xc5008b04,
-       0x00bbcf01,
-       0xf412bbc8,
-/* 0x01fa: mmctx_done */
-       0x94bdf61b,
-       0x800199f0,
-       0xf6021700,
-       0x04bd0009,
-/* 0x020a: strand_wait */
-       0xa0f900f8,
-       0xb87e020a,
-       0xa0fc0000,
-/* 0x0216: strand_pre */
-       0x0c0900f8,
-       0x024afc80,
-       0xbd0009f6,
-       0x020a7e04,
-/* 0x0227: strand_post */
-       0x0900f800,
-       0x4afc800d,
-       0x0009f602,
-       0x0a7e04bd,
-       0x00f80002,
-/* 0x0238: strand_set */
-       0xfc800f0c,
-       0x0cf6024f,
-       0x0c04bd00,
-       0x4afc800b,
-       0x000cf602,
-       0xfc8004bd,
-       0x0ef6024f,
-       0x0c04bd00,
-       0x4afc800a,
-       0x000cf602,
-       0x0a7e04bd,
-       0x00f80002,
-/* 0x0268: strand_ctx_init */
-       0x99f094bd,
-       0x37008003,
-       0x0009f602,
-       0x167e04bd,
-       0x030e0002,
-       0x0002387e,
-       0xfc80c4bd,
-       0x0cf60247,
-       0x0c04bd00,
-       0x4afc8001,
-       0x000cf602,
-       0x0a7e04bd,
-       0x0c920002,
-       0x46fc8001,
-       0x000cf602,
-       0x020c04bd,
-       0x024afc80,
-       0xbd000cf6,
-       0x020a7e04,
-       0x02277e00,
-       0x42008800,
-       0x20008902,
-       0x0099cf02,
-/* 0x02c7: ctx_init_strand_loop */
-       0xf608fe95,
-       0x8ef6008e,
-       0x808acf40,
-       0xb606a5b6,
-       0xeabb01a0,
-       0x0480b600,
-       0xf40192b6,
-       0xe4b6e81b,
-       0xf2efbc08,
-       0x99f094bd,
-       0x17008003,
-       0x0009f602,
-       0x00f804bd,
-/* 0x02f8: error */
-       0x02050080,
-       0xbd000ff6,
-       0x80010f04,
-       0xf6030700,
-       0x04bd000f,
-/* 0x030e: init */
-       0x04bd00f8,
-       0x410007fe,
-       0x11cf4200,
-       0x0911e700,
-       0x0814b601,
-       0x020014fe,
-       0x12004002,
-       0xbd0002f6,
-       0x05c94104,
-       0xbd0010fe,
-       0x07004024,
-       0xbd0002f6,
-       0x20034204,
-       0x01010080,
-       0xbd0002f6,
-       0x20044204,
-       0x01010480,
-       0xbd0002f6,
-       0x200b4204,
-       0x01010880,
-       0xbd0002f6,
-       0x200c4204,
-       0x01011c80,
-       0xbd0002f6,
-       0x01039204,
-       0x03090080,
-       0xbd0003f6,
-       0x87044204,
-       0xf6040040,
-       0x04bd0002,
-       0x00400402,
-       0x0002f603,
-       0x31f404bd,
-       0x96048e10,
-       0x00657e40,
-       0xc7feb200,
-       0x01b590f1,
-       0x1ff4f003,
-       0x01020fb5,
-       0x041fbb01,
-       0x800112b6,
-       0xf6010300,
-       0x04bd0001,
-       0x01040080,
-       0xbd0001f6,
-       0x01004104,
-       0xa87e020f,
-       0xb77e0006,
-       0x100f0006,
-       0x0006f97e,
-       0x98000e98,
-       0x207e010f,
-       0x14950001,
-       0xc0008008,
-       0x0004f601,
-       0x008004bd,
-       0x04f601c1,
-       0xb704bd00,
-       0xbb130030,
-       0xf5b6001f,
-       0xd3008002,
-       0x000ff601,
-       0x15b604bd,
-       0x0110b608,
-       0xb20814b6,
-       0x02687e1f,
-       0x001fbb00,
-       0x84020398,
-/* 0x041f: init_gpc */
-       0xb8502000,
-       0x0008044e,
-       0x8f7e1fb2,
-       0x4eb80000,
-       0xbd00010c,
-       0x008f7ef4,
-       0x044eb800,
-       0x8f7e0001,
-       0x4eb80000,
-       0x0f000100,
-       0x008f7e02,
-       0x004eb800,
-/* 0x044e: init_gpc_wait */
-       0x657e0008,
-       0xffc80000,
-       0xf90bf41f,
-       0x08044eb8,
-       0x00657e00,
-       0x001fbb00,
-       0x800040b7,
-       0xf40132b6,
-       0x000fb41b,
-       0x0006f97e,
-       0xa87e000f,
-       0x00800006,
-       0x01f60201,
-       0xbd04bd00,
-       0x1f19f014,
-       0x02300080,
-       0xbd0001f6,
-/* 0x0491: main */
-       0x0031f404,
-       0x0d0028f4,
-       0x00377e10,
-       0xf401f400,
-       0x4001e4b1,
-       0x00c71bf5,
-       0x99f094bd,
-       0x37008004,
-       0x0009f602,
-       0x008104bd,
-       0x11cf02c0,
-       0xc1008200,
-       0x0022cf02,
-       0xf41f13c8,
-       0x23c8770b,
-       0x550bf41f,
-       0x12b220f9,
-       0x99f094bd,
-       0x37008007,
-       0x0009f602,
-       0x32f404bd,
-       0x0231f401,
-       0x00087c7e,
-       0x99f094bd,
-       0x17008007,
-       0x0009f602,
-       0x20fc04bd,
-       0x99f094bd,
-       0x37008006,
-       0x0009f602,
-       0x31f404bd,
-       0x087c7e01,
-       0xf094bd00,
-       0x00800699,
-       0x09f60217,
-       0xf404bd00,
-/* 0x0522: chsw_prev_no_next */
-       0x20f92f0e,
-       0x32f412b2,
-       0x0232f401,
-       0x00087c7e,
-       0x008020fc,
-       0x02f602c0,
-       0xf404bd00,
-/* 0x053e: chsw_no_prev */
-       0x23c8130e,
-       0x0d0bf41f,
-       0xf40131f4,
-       0x7c7e0232,
-/* 0x054e: chsw_done */
-       0x01020008,
-       0x02c30080,
-       0xbd0002f6,
-       0xf094bd04,
-       0x00800499,
-       0x09f60217,
-       0xf504bd00,
-/* 0x056b: main_not_ctx_switch */
-       0xb0ff2a0e,
-       0x1bf401e4,
-       0x7ef2b20c,
-       0xf400081c,
-/* 0x057a: main_not_ctx_chan */
-       0xe4b0400e,
-       0x2c1bf402,
-       0x99f094bd,
-       0x37008007,
-       0x0009f602,
-       0x32f404bd,
-       0x0232f401,
-       0x00087c7e,
-       0x99f094bd,
-       0x17008007,
-       0x0009f602,
-       0x0ef404bd,
-/* 0x05a9: main_not_ctx_save */
-       0x10ef9411,
-       0x7e01f5f0,
-       0xf50002f8,
-/* 0x05b7: main_done */
-       0xbdfede0e,
-       0x1f29f024,
-       0x02300080,
-       0xbd0002f6,
-       0xcc0ef504,
-/* 0x05c9: ih */
-       0xfe80f9fe,
-       0x80f90188,
-       0xa0f990f9,
-       0xd0f9b0f9,
-       0xf0f9e0f9,
-       0x004a04bd,
-       0x00aacf02,
-       0xf404abc4,
-       0x100d230b,
-       0xcf1a004e,
-       0x004f00ee,
-       0x00ffcf19,
-       0x0000047e,
-       0x0400b0b7,
-       0x0040010e,
-       0x000ef61d,
-/* 0x060a: ih_no_fifo */
-       0xabe404bd,
-       0x0bf40100,
-       0x4e100d0c,
-       0x047e4001,
-/* 0x061a: ih_no_ctxsw */
-       0xabe40000,
-       0x0bf40400,
-       0x07088e56,
-       0x00657e40,
-       0x80ffb200,
-       0xf6020400,
-       0x04bd000f,
-       0x4007048e,
-       0x0000657e,
-       0x0080ffb2,
-       0x0ff60203,
-       0xc704bd00,
-       0xee9450fe,
-       0x07008f02,
-       0x00efbb40,
-       0x0000657e,
-       0x02020080,
-       0xbd000ff6,
-       0x7e030f04,
-       0x4b0002f8,
-       0xbfb20100,
-       0x4001448e,
-       0x00008f7e,
-/* 0x0674: ih_no_fwmthd */
-       0xbd05044b,
-       0xb4abffb0,
-       0x800c0bf4,
-       0xf6030700,
-       0x04bd000b,
-/* 0x0688: ih_no_other */
-       0xf6010040,
-       0x04bd000a,
-       0xe0fcf0fc,
-       0xb0fcd0fc,
-       0x90fca0fc,
-       0x88fe80fc,
-       0xf480fc00,
-       0x01f80032,
-/* 0x06a8: ctx_4170s */
-       0xb210f5f0,
-       0x41708eff,
-       0x008f7e40,
-/* 0x06b7: ctx_4170w */
-       0x8e00f800,
-       0x7e404170,
-       0xb2000065,
-       0x10f4f0ff,
-       0xf8f31bf4,
-/* 0x06c9: ctx_redswitch */
-       0x02004e00,
-       0xf040e5f0,
-       0xe5f020e5,
-       0x85008010,
-       0x000ef601,
-       0x080f04bd,
-/* 0x06e0: ctx_redswitch_delay */
-       0xf401f2b6,
-       0xe5f1fd1b,
-       0xe5f10400,
-       0x00800100,
-       0x0ef60185,
-       0xf804bd00,
-/* 0x06f9: ctx_86c */
-       0x23008000,
-       0x000ff602,
-       0xffb204bd,
-       0x408a148e,
-       0x00008f7e,
-       0x8c8effb2,
-       0x8f7e41a8,
-       0x00f80000,
-/* 0x0718: ctx_mem */
-       0x02840080,
-       0xbd000ff6,
-/* 0x0721: ctx_mem_wait */
-       0x84008f04,
-       0x00ffcf02,
-       0xf405fffd,
-       0x00f8f61b,
-/* 0x0730: ctx_load */
-       0x99f094bd,
-       0x37008005,
-       0x0009f602,
-       0x0c0a04bd,
-       0x0000b87e,
-       0x0080f4bd,
-       0x0ff60289,
-       0x8004bd00,
-       0xf602c100,
-       0x04bd0002,
-       0x02830080,
-       0xbd0002f6,
-       0x7e070f04,
-       0x80000718,
-       0xf602c000,
-       0x04bd0002,
-       0xf0000bfe,
-       0x24b61f2a,
-       0x0220b604,
-       0x99f094bd,
-       0x37008008,
-       0x0009f602,
-       0x008004bd,
-       0x02f60281,
-       0xd204bd00,
-       0x80000000,
-       0x800225f0,
-       0xf6028800,
-       0x04bd0002,
-       0x00421001,
-       0x0223f002,
-       0xf80512fa,
-       0xf094bd03,
-       0x00800899,
-       0x09f60217,
-       0x9804bd00,
-       0x14b68101,
-       0x80029818,
-       0xfd0825b6,
-       0x01b50512,
-       0xf094bd16,
-       0x00800999,
-       0x09f60237,
-       0x8004bd00,
-       0xf6028100,
-       0x04bd0001,
-       0x00800102,
-       0x02f60288,
-       0x4104bd00,
-       0x13f00100,
-       0x0501fa06,
-       0x94bd03f8,
-       0x800999f0,
-       0xf6021700,
-       0x04bd0009,
-       0x99f094bd,
-       0x17008005,
-       0x0009f602,
-       0x00f804bd,
-/* 0x081c: ctx_chan */
-       0x0007307e,
-       0xb87e0c0a,
-       0x050f0000,
-       0x0007187e,
-/* 0x082e: ctx_mmio_exec */
-       0x039800f8,
-       0x81008041,
-       0x0003f602,
-       0x34bd04bd,
-/* 0x083c: ctx_mmio_loop */
-       0xf4ff34c4,
-       0x00450e1b,
-       0x0653f002,
-       0xf80535fa,
-/* 0x084d: ctx_mmio_pull */
-       0x804e9803,
-       0x7e814f98,
-       0xb600008f,
-       0x12b60830,
-       0xdf1bf401,
-/* 0x0860: ctx_mmio_done */
-       0x80160398,
-       0xf6028100,
-       0x04bd0003,
-       0x414000b5,
-       0x13f00100,
-       0x0601fa06,
-       0x00f803f8,
-/* 0x087c: ctx_xfer */
-       0x0080040e,
-       0x0ef60302,
-/* 0x0887: ctx_xfer_idle */
-       0x8e04bd00,
-       0xcf030000,
-       0xe4f100ee,
-       0x1bf42000,
-       0x0611f4f5,
-/* 0x089b: ctx_xfer_pre */
-       0x0f0c02f4,
-       0x06f97e10,
-       0x1b11f400,
-/* 0x08a4: ctx_xfer_pre_load */
-       0xa87e020f,
-       0xb77e0006,
-       0xc97e0006,
-       0xf4bd0006,
-       0x0006a87e,
-       0x0007307e,
-/* 0x08bc: ctx_xfer_exec */
-       0xbd160198,
-       0x05008024,
-       0x0002f601,
-       0x1fb204bd,
-       0x41a5008e,
-       0x00008f7e,
-       0xf001fcf0,
-       0x24b6022c,
-       0x05f2fd01,
-       0x048effb2,
-       0x8f7e41a5,
-       0x167e0000,
-       0x24bd0002,
-       0x0247fc80,
-       0xbd0002f6,
-       0x012cf004,
-       0x800320b6,
-       0xf6024afc,
-       0x04bd0002,
-       0xf001acf0,
-       0x000b06a5,
-       0x98000c98,
-       0x000e010d,
-       0x00013d7e,
-       0xec7e080a,
-       0x0a7e0000,
-       0x01f40002,
-       0x7e0c0a12,
-       0x0f0000b8,
-       0x07187e05,
-       0x2d02f400,
-/* 0x0938: ctx_xfer_post */
-       0xa87e020f,
-       0xf4bd0006,
-       0x0006f97e,
-       0x0002277e,
-       0x0006b77e,
-       0xa87ef4bd,
-       0x11f40006,
-       0x40019810,
-       0xf40511fd,
-       0x2e7e070b,
-/* 0x0962: ctx_xfer_no_post_mmio */
-/* 0x0962: ctx_xfer_done */
-       0x00f80008,
-       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/drivers/gpu/drm/nouveau/core/engine/graph/fuc/hubnvc0.fuc b/drivers/gpu/drm/nouveau/core/engine/graph/fuc/hubnvc0.fuc
deleted file mode 100644 (file)
index 3ff52ba..0000000
+++ /dev/null
@@ -1,40 +0,0 @@
-/*
- * Copyright 2013 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 <bskeggs@redhat.com>
- */
-
-#define CHIPSET GF100
-#include "macros.fuc"
-
-.section #nvc0_grhub_data
-#define INCLUDE_DATA
-#include "com.fuc"
-#include "hub.fuc"
-#undef INCLUDE_DATA
-
-.section #nvc0_grhub_code
-#define INCLUDE_CODE
-bra #init
-#include "com.fuc"
-#include "hub.fuc"
-.align 256
-#undef INCLUDE_CODE
diff --git a/drivers/gpu/drm/nouveau/core/engine/graph/fuc/hubnvc0.fuc.h b/drivers/gpu/drm/nouveau/core/engine/graph/fuc/hubnvc0.fuc.h
deleted file mode 100644 (file)
index 92dfe6a..0000000
+++ /dev/null
@@ -1,1047 +0,0 @@
-uint32_t nvc0_grhub_data[] = {
-/* 0x0000: hub_mmio_list_head */
-       0x00000300,
-/* 0x0004: hub_mmio_list_tail */
-       0x00000304,
-/* 0x0008: gpc_count */
-       0x00000000,
-/* 0x000c: rop_count */
-       0x00000000,
-/* 0x0010: cmd_queue */
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-/* 0x0058: ctx_current */
-       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,
-/* 0x0100: chan_data */
-/* 0x0100: chan_mmio_count */
-       0x00000000,
-/* 0x0104: chan_mmio_address */
-       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,
-/* 0x0200: xfer_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,
-/* 0x0300: hub_mmio_list_base */
-       0x0417e91c,
-};
-
-uint32_t nvc0_grhub_code[] = {
-       0x039b0ef5,
-/* 0x0004: queue_put */
-       0x9800d898,
-       0x86f001d9,
-       0x0489b808,
-       0xf00c1bf4,
-       0x21f502f7,
-       0x00f8037e,
-/* 0x001c: queue_put_next */
-       0xb60798c4,
-       0x8dbb0384,
-       0x0880b600,
-       0x80008e80,
-       0x90b6018f,
-       0x0f94f001,
-       0xf801d980,
-/* 0x0039: queue_get */
-       0x0131f400,
-       0x9800d898,
-       0x89b801d9,
-       0x210bf404,
-       0xb60789c4,
-       0x9dbb0394,
-       0x0890b600,
-       0x98009e98,
-       0x80b6019f,
-       0x0f84f001,
-       0xf400d880,
-/* 0x0066: queue_get_done */
-       0x00f80132,
-/* 0x0068: nv_rd32 */
-       0xf002ecb9,
-       0x07f11fc9,
-       0x03f0ca00,
-       0x000cd001,
-/* 0x007a: nv_rd32_wait */
-       0xc7f104bd,
-       0xc3f0ca00,
-       0x00cccf01,
-       0xf41fccc8,
-       0xa7f0f31b,
-       0x1021f506,
-       0x00f7f101,
-       0x01f3f0cb,
-       0xf800ffcf,
-/* 0x009d: nv_wr32 */
-       0x0007f100,
-       0x0103f0cc,
-       0xbd000fd0,
-       0x02ecb904,
-       0xf01fc9f0,
-       0x07f11ec9,
-       0x03f0ca00,
-       0x000cd001,
-/* 0x00be: nv_wr32_wait */
-       0xc7f104bd,
-       0xc3f0ca00,
-       0x00cccf01,
-       0xf41fccc8,
-       0x00f8f31b,
-/* 0x00d0: wait_donez */
-       0x99f094bd,
-       0x0007f100,
-       0x0203f00f,
-       0xbd0009d0,
-       0x0007f104,
-       0x0203f006,
-       0xbd000ad0,
-/* 0x00ed: wait_donez_ne */
-       0x0087f104,
-       0x0183f000,
-       0xff0088cf,
-       0x1bf4888a,
-       0xf094bdf3,
-       0x07f10099,
-       0x03f01700,
-       0x0009d002,
-       0x00f804bd,
-/* 0x0110: wait_doneo */
-       0x99f094bd,
-       0x0007f100,
-       0x0203f00f,
-       0xbd0009d0,
-       0x0007f104,
-       0x0203f006,
-       0xbd000ad0,
-/* 0x012d: wait_doneo_e */
-       0x0087f104,
-       0x0183f000,
-       0xff0088cf,
-       0x0bf4888a,
-       0xf094bdf3,
-       0x07f10099,
-       0x03f01700,
-       0x0009d002,
-       0x00f804bd,
-/* 0x0150: mmctx_size */
-/* 0x0152: nv_mmctx_size_loop */
-       0xe89894bd,
-       0x1a85b600,
-       0xb60180b6,
-       0x98bb0284,
-       0x04e0b600,
-       0xf404efb8,
-       0x9fb9eb1b,
-/* 0x016f: mmctx_xfer */
-       0xbd00f802,
-       0x0199f094,
-       0x0f0007f1,
-       0xd00203f0,
-       0x04bd0009,
-       0xbbfd94bd,
-       0x120bf405,
-       0xc40007f1,
-       0xd00103f0,
-       0x04bd000b,
-/* 0x0197: mmctx_base_disabled */
-       0xfd0099f0,
-       0x0bf405ee,
-       0x0007f11e,
-       0x0103f0c6,
-       0xbd000ed0,
-       0x0007f104,
-       0x0103f0c7,
-       0xbd000fd0,
-       0x0199f004,
-/* 0x01b8: mmctx_multi_disabled */
-       0xb600abc8,
-       0xb9f010b4,
-       0x01aec80c,
-       0xfd11e4b6,
-       0x07f105be,
-       0x03f0c500,
-       0x000bd001,
-/* 0x01d6: mmctx_exec_loop */
-/* 0x01d6: mmctx_wait_free */
-       0xe7f104bd,
-       0xe3f0c500,
-       0x00eecf01,
-       0xf41fe4f0,
-       0xce98f30b,
-       0x05e9fd00,
-       0xc80007f1,
-       0xd00103f0,
-       0x04bd000e,
-       0xb804c0b6,
-       0x1bf404cd,
-       0x02abc8d8,
-/* 0x0207: mmctx_fini_wait */
-       0xf11f1bf4,
-       0xf0c500b7,
-       0xbbcf01b3,
-       0x1fb4f000,
-       0xf410b4b0,
-       0xa7f0f01b,
-       0xd021f405,
-/* 0x0223: mmctx_stop */
-       0xc82b0ef4,
-       0xb4b600ab,
-       0x0cb9f010,
-       0xf112b9f0,
-       0xf0c50007,
-       0x0bd00103,
-/* 0x023b: mmctx_stop_wait */
-       0xf104bd00,
-       0xf0c500b7,
-       0xbbcf01b3,
-       0x12bbc800,
-/* 0x024b: mmctx_done */
-       0xbdf31bf4,
-       0x0199f094,
-       0x170007f1,
-       0xd00203f0,
-       0x04bd0009,
-/* 0x025e: strand_wait */
-       0xa0f900f8,
-       0xf402a7f0,
-       0xa0fcd021,
-/* 0x026a: strand_pre */
-       0x97f000f8,
-       0xfc07f10c,
-       0x0203f04a,
-       0xbd0009d0,
-       0x5e21f504,
-/* 0x027f: strand_post */
-       0xf000f802,
-       0x07f10d97,
-       0x03f04afc,
-       0x0009d002,
-       0x21f504bd,
-       0x00f8025e,
-/* 0x0294: strand_set */
-       0xf10fc7f0,
-       0xf04ffc07,
-       0x0cd00203,
-       0xf004bd00,
-       0x07f10bc7,
-       0x03f04afc,
-       0x000cd002,
-       0x07f104bd,
-       0x03f04ffc,
-       0x000ed002,
-       0xc7f004bd,
-       0xfc07f10a,
-       0x0203f04a,
-       0xbd000cd0,
-       0x5e21f504,
-/* 0x02d3: strand_ctx_init */
-       0xbd00f802,
-       0x0399f094,
-       0x0f0007f1,
-       0xd00203f0,
-       0x04bd0009,
-       0x026a21f5,
-       0xf503e7f0,
-       0xbd029421,
-       0xfc07f1c4,
-       0x0203f047,
-       0xbd000cd0,
-       0x01c7f004,
-       0x4afc07f1,
-       0xd00203f0,
-       0x04bd000c,
-       0x025e21f5,
-       0xf1010c92,
-       0xf046fc07,
-       0x0cd00203,
-       0xf004bd00,
-       0x07f102c7,
-       0x03f04afc,
-       0x000cd002,
-       0x21f504bd,
-       0x21f5025e,
-       0x87f1027f,
-       0x83f04200,
-       0x0097f102,
-       0x0293f020,
-       0x950099cf,
-/* 0x034a: ctx_init_strand_loop */
-       0x8ed008fe,
-       0x408ed000,
-       0xb6808acf,
-       0xa0b606a5,
-       0x00eabb01,
-       0xb60480b6,
-       0x1bf40192,
-       0x08e4b6e8,
-       0xbdf2efbc,
-       0x0399f094,
-       0x170007f1,
-       0xd00203f0,
-       0x04bd0009,
-/* 0x037e: error */
-       0x07f100f8,
-       0x03f00500,
-       0x000fd002,
-       0xf7f004bd,
-       0x0007f101,
-       0x0303f007,
-       0xbd000fd0,
-/* 0x039b: init */
-       0xbd00f804,
-       0x0007fe04,
-       0x420017f1,
-       0xcf0013f0,
-       0x11e70011,
-       0x14b60109,
-       0x0014fe08,
-       0xf10227f0,
-       0xf0120007,
-       0x02d00003,
-       0xf104bd00,
-       0xfe06c817,
-       0x24bd0010,
-       0x070007f1,
-       0xd00003f0,
-       0x04bd0002,
-       0x200327f1,
-       0x010007f1,
-       0xd00103f0,
-       0x04bd0002,
-       0x200427f1,
-       0x010407f1,
-       0xd00103f0,
-       0x04bd0002,
-       0x200b27f1,
-       0x010807f1,
-       0xd00103f0,
-       0x04bd0002,
-       0x200c27f1,
-       0x011c07f1,
-       0xd00103f0,
-       0x04bd0002,
-       0xf1010392,
-       0xf0090007,
-       0x03d00303,
-       0xf104bd00,
-       0xf0870427,
-       0x07f10023,
-       0x03f00400,
-       0x0002d000,
-       0x27f004bd,
-       0x0007f104,
-       0x0003f003,
-       0xbd0002d0,
-       0x1031f404,
-       0x9604e7f1,
-       0xf440e3f0,
-       0xfeb96821,
-       0x90f1c702,
-       0xf0030180,
-       0x0f801ff4,
-       0x0117f002,
-       0xb6041fbb,
-       0x07f10112,
-       0x03f00300,
-       0x0001d001,
-       0x07f104bd,
-       0x03f00400,
-       0x0001d001,
-       0x17f104bd,
-       0xf7f00100,
-       0x0d21f502,
-       0x1f21f508,
-       0x10f7f008,
-       0x086c21f5,
-       0x98000e98,
-       0x21f5010f,
-       0x14950150,
-       0x0007f108,
-       0x0103f0c0,
-       0xbd0004d0,
-       0x0007f104,
-       0x0103f0c1,
-       0xbd0004d0,
-       0x0030b704,
-       0x001fbb13,
-       0xf102f5b6,
-       0xf0d30007,
-       0x0fd00103,
-       0xb604bd00,
-       0x10b60815,
-       0x0814b601,
-       0xf5021fb9,
-       0xbb02d321,
-       0x0398001f,
-       0x0047f102,
-       0x5043f020,
-/* 0x04f4: init_gpc */
-       0x08044ea0,
-       0xf4021fb9,
-       0x4ea09d21,
-       0xf4bd010c,
-       0xa09d21f4,
-       0xf401044e,
-       0x4ea09d21,
-       0xf7f00100,
-       0x9d21f402,
-       0x08004ea0,
-/* 0x051c: init_gpc_wait */
-       0xc86821f4,
-       0x0bf41fff,
-       0x044ea0fa,
-       0x6821f408,
-       0xb7001fbb,
-       0xb6800040,
-       0x1bf40132,
-       0x00f7f0be,
-       0x086c21f5,
-       0xf500f7f0,
-       0xf1080d21,
-       0xf0010007,
-       0x01d00203,
-       0xbd04bd00,
-       0x1f19f014,
-       0x080007f1,
-       0xd00203f0,
-       0x04bd0001,
-/* 0x0564: main */
-       0xf40031f4,
-       0xd7f00028,
-       0x3921f410,
-       0xb1f401f4,
-       0xf54001e4,
-       0xbd00e91b,
-       0x0499f094,
-       0x0f0007f1,
-       0xd00203f0,
-       0x04bd0009,
-       0xc00017f1,
-       0xcf0213f0,
-       0x27f10011,
-       0x23f0c100,
-       0x0022cf02,
-       0xf51f13c8,
-       0xc800890b,
-       0x0bf41f23,
-       0xb920f962,
-       0x94bd0212,
-       0xf10799f0,
-       0xf00f0007,
-       0x09d00203,
-       0xf404bd00,
-       0x31f40132,
-       0x4021f502,
-       0xf094bd0a,
-       0x07f10799,
-       0x03f01700,
-       0x0009d002,
-       0x20fc04bd,
-       0x99f094bd,
-       0x0007f106,
-       0x0203f00f,
-       0xbd0009d0,
-       0x0131f404,
-       0x0a4021f5,
-       0x99f094bd,
-       0x0007f106,
-       0x0203f017,
-       0xbd0009d0,
-       0x330ef404,
-/* 0x060c: chsw_prev_no_next */
-       0x12b920f9,
-       0x0132f402,
-       0xf50232f4,
-       0xfc0a4021,
-       0x0007f120,
-       0x0203f0c0,
-       0xbd0002d0,
-       0x130ef404,
-/* 0x062c: chsw_no_prev */
-       0xf41f23c8,
-       0x31f40d0b,
-       0x0232f401,
-       0x0a4021f5,
-/* 0x063c: chsw_done */
-       0xf10127f0,
-       0xf0c30007,
-       0x02d00203,
-       0xbd04bd00,
-       0x0499f094,
-       0x170007f1,
-       0xd00203f0,
-       0x04bd0009,
-       0xff080ef5,
-/* 0x0660: main_not_ctx_switch */
-       0xf401e4b0,
-       0xf2b90d1b,
-       0xd021f502,
-       0x460ef409,
-/* 0x0670: main_not_ctx_chan */
-       0xf402e4b0,
-       0x94bd321b,
-       0xf10799f0,
-       0xf00f0007,
-       0x09d00203,
-       0xf404bd00,
-       0x32f40132,
-       0x4021f502,
-       0xf094bd0a,
-       0x07f10799,
-       0x03f01700,
-       0x0009d002,
-       0x0ef404bd,
-/* 0x06a5: main_not_ctx_save */
-       0x10ef9411,
-       0xf501f5f0,
-       0xf5037e21,
-/* 0x06b3: main_done */
-       0xbdfeb50e,
-       0x1f29f024,
-       0x080007f1,
-       0xd00203f0,
-       0x04bd0002,
-       0xfea00ef5,
-/* 0x06c8: ih */
-       0x88fe80f9,
-       0xf980f901,
-       0xf9a0f990,
-       0xf9d0f9b0,
-       0xbdf0f9e0,
-       0x00a7f104,
-       0x00a3f002,
-       0xc400aacf,
-       0x0bf404ab,
-       0x10d7f030,
-       0x1a00e7f1,
-       0xcf00e3f0,
-       0xf7f100ee,
-       0xf3f01900,
-       0x00ffcf00,
-       0xb70421f4,
-       0xf00400b0,
-       0x07f101e7,
-       0x03f01d00,
-       0x000ed000,
-/* 0x071a: ih_no_fifo */
-       0xabe404bd,
-       0x0bf40100,
-       0x10d7f00d,
-       0x4001e7f1,
-/* 0x072b: ih_no_ctxsw */
-       0xe40421f4,
-       0xf40400ab,
-       0xe7f16c0b,
-       0xe3f00708,
-       0x6821f440,
-       0xf102ffb9,
-       0xf0040007,
-       0x0fd00203,
-       0xf104bd00,
-       0xf00704e7,
-       0x21f440e3,
-       0x02ffb968,
-       0x030007f1,
-       0xd00203f0,
-       0x04bd000f,
-       0x9450fec7,
-       0xf7f102ee,
-       0xf3f00700,
-       0x00efbb40,
-       0xf16821f4,
-       0xf0020007,
-       0x0fd00203,
-       0xf004bd00,
-       0x21f503f7,
-       0xb7f1037e,
-       0xbfb90100,
-       0x44e7f102,
-       0x40e3f001,
-/* 0x079b: ih_no_fwmthd */
-       0xf19d21f4,
-       0xbd0504b7,
-       0xb4abffb0,
-       0xf10f0bf4,
-       0xf0070007,
-       0x0bd00303,
-/* 0x07b3: ih_no_other */
-       0xf104bd00,
-       0xf0010007,
-       0x0ad00003,
-       0xfc04bd00,
-       0xfce0fcf0,
-       0xfcb0fcd0,
-       0xfc90fca0,
-       0x0088fe80,
-       0x32f480fc,
-/* 0x07d7: ctx_4160s */
-       0xf001f800,
-       0xffb901f7,
-       0x60e7f102,
-       0x40e3f041,
-/* 0x07e7: ctx_4160s_wait */
-       0xf19d21f4,
-       0xf04160e7,
-       0x21f440e3,
-       0x02ffb968,
-       0xf404ffc8,
-       0x00f8f00b,
-/* 0x07fc: ctx_4160c */
-       0xffb9f4bd,
-       0x60e7f102,
-       0x40e3f041,
-       0xf89d21f4,
-/* 0x080d: ctx_4170s */
-       0x10f5f000,
-       0xf102ffb9,
-       0xf04170e7,
-       0x21f440e3,
-/* 0x081f: ctx_4170w */
-       0xf100f89d,
-       0xf04170e7,
-       0x21f440e3,
-       0x02ffb968,
-       0xf410f4f0,
-       0x00f8f01b,
-/* 0x0834: ctx_redswitch */
-       0x0200e7f1,
-       0xf040e5f0,
-       0xe5f020e5,
-       0x0007f110,
-       0x0103f085,
-       0xbd000ed0,
-       0x08f7f004,
-/* 0x0850: ctx_redswitch_delay */
-       0xf401f2b6,
-       0xe5f1fd1b,
-       0xe5f10400,
-       0x07f10100,
-       0x03f08500,
-       0x000ed001,
-       0x00f804bd,
-/* 0x086c: ctx_86c */
-       0x1b0007f1,
-       0xd00203f0,
-       0x04bd000f,
-       0xf102ffb9,
-       0xf08a14e7,
-       0x21f440e3,
-       0x02ffb99d,
-       0xa86ce7f1,
-       0xf441e3f0,
-       0x00f89d21,
-/* 0x0894: ctx_mem */
-       0x840007f1,
-       0xd00203f0,
-       0x04bd000f,
-/* 0x08a0: ctx_mem_wait */
-       0x8400f7f1,
-       0xcf02f3f0,
-       0xfffd00ff,
-       0xf31bf405,
-/* 0x08b2: ctx_load */
-       0x94bd00f8,
-       0xf10599f0,
-       0xf00f0007,
-       0x09d00203,
-       0xf004bd00,
-       0x21f40ca7,
-       0xf1f4bdd0,
-       0xf0890007,
-       0x0fd00203,
-       0xf104bd00,
-       0xf0c10007,
-       0x02d00203,
-       0xf104bd00,
-       0xf0830007,
-       0x02d00203,
-       0xf004bd00,
-       0x21f507f7,
-       0x07f10894,
-       0x03f0c000,
-       0x0002d002,
-       0x0bfe04bd,
-       0x1f2af000,
-       0xb60424b6,
-       0x94bd0220,
-       0xf10899f0,
-       0xf00f0007,
-       0x09d00203,
-       0xf104bd00,
-       0xf0810007,
-       0x02d00203,
-       0xf104bd00,
-       0xf1000027,
-       0xf0800023,
-       0x07f10225,
-       0x03f08800,
-       0x0002d002,
-       0x17f004bd,
-       0x0027f110,
-       0x0223f002,
-       0xf80512fa,
-       0xf094bd03,
-       0x07f10899,
-       0x03f01700,
-       0x0009d002,
-       0x019804bd,
-       0x1814b681,
-       0xb6800298,
-       0x12fd0825,
-       0x16018005,
-       0x99f094bd,
-       0x0007f109,
-       0x0203f00f,
-       0xbd0009d0,
-       0x0007f104,
-       0x0203f081,
-       0xbd0001d0,
-       0x0127f004,
-       0x880007f1,
-       0xd00203f0,
-       0x04bd0002,
-       0x010017f1,
-       0xfa0613f0,
-       0x03f80501,
-       0x99f094bd,
-       0x0007f109,
-       0x0203f017,
-       0xbd0009d0,
-       0xf094bd04,
-       0x07f10599,
-       0x03f01700,
-       0x0009d002,
-       0x00f804bd,
-/* 0x09d0: ctx_chan */
-       0x07d721f5,
-       0x08b221f5,
-       0xf40ca7f0,
-       0xf7f0d021,
-       0x9421f505,
-       0xfc21f508,
-/* 0x09eb: ctx_mmio_exec */
-       0x9800f807,
-       0x07f14103,
-       0x03f08100,
-       0x0003d002,
-       0x34bd04bd,
-/* 0x09fc: ctx_mmio_loop */
-       0xf4ff34c4,
-       0x57f10f1b,
-       0x53f00200,
-       0x0535fa06,
-/* 0x0a0e: ctx_mmio_pull */
-       0x4e9803f8,
-       0x814f9880,
-       0xb69d21f4,
-       0x12b60830,
-       0xdf1bf401,
-/* 0x0a20: ctx_mmio_done */
-       0xf1160398,
-       0xf0810007,
-       0x03d00203,
-       0x8004bd00,
-       0x17f14000,
-       0x13f00100,
-       0x0601fa06,
-       0x00f803f8,
-/* 0x0a40: ctx_xfer */
-       0xf104e7f0,
-       0xf0020007,
-       0x0ed00303,
-/* 0x0a4f: ctx_xfer_idle */
-       0xf104bd00,
-       0xf00000e7,
-       0xeecf03e3,
-       0x00e4f100,
-       0xf21bf420,
-       0xf40611f4,
-/* 0x0a66: ctx_xfer_pre */
-       0xf7f01102,
-       0x6c21f510,
-       0xd721f508,
-       0x1c11f407,
-/* 0x0a74: ctx_xfer_pre_load */
-       0xf502f7f0,
-       0xf5080d21,
-       0xf5081f21,
-       0xbd083421,
-       0x0d21f5f4,
-       0xb221f508,
-/* 0x0a8d: ctx_xfer_exec */
-       0x16019808,
-       0x07f124bd,
-       0x03f00500,
-       0x0002d001,
-       0x1fb904bd,
-       0x00e7f102,
-       0x41e3f0a5,
-       0xf09d21f4,
-       0x2cf001fc,
-       0x0124b602,
-       0xb905f2fd,
-       0xe7f102ff,
-       0xe3f0a504,
-       0x9d21f441,
-       0x026a21f5,
-       0x07f124bd,
-       0x03f047fc,
-       0x0002d002,
-       0x2cf004bd,
-       0x0320b601,
-       0x4afc07f1,
-       0xd00203f0,
-       0x04bd0002,
-       0xf001acf0,
-       0xb7f006a5,
-       0x000c9800,
-       0xf0010d98,
-       0x21f500e7,
-       0xa7f0016f,
-       0x1021f508,
-       0x5e21f501,
-       0x1301f402,
-       0xf40ca7f0,
-       0xf7f0d021,
-       0x9421f505,
-       0x3202f408,
-/* 0x0b1c: ctx_xfer_post */
-       0xf502f7f0,
-       0xbd080d21,
-       0x6c21f5f4,
-       0x7f21f508,
-       0x1f21f502,
-       0xf5f4bd08,
-       0xf4080d21,
-       0x01981011,
-       0x0511fd40,
-       0xf5070bf4,
-/* 0x0b47: ctx_xfer_no_post_mmio */
-       0xf509eb21,
-/* 0x0b4b: ctx_xfer_done */
-       0xf807fc21,
-       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,
-};
diff --git a/drivers/gpu/drm/nouveau/core/engine/graph/fuc/hubnvd7.fuc b/drivers/gpu/drm/nouveau/core/engine/graph/fuc/hubnvd7.fuc
deleted file mode 100644 (file)
index afbe03a..0000000
+++ /dev/null
@@ -1,40 +0,0 @@
-/*
- * Copyright 2013 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 <bskeggs@redhat.com>
- */
-
-#define CHIPSET GF117
-#include "macros.fuc"
-
-.section #nvd7_grhub_data
-#define INCLUDE_DATA
-#include "com.fuc"
-#include "hub.fuc"
-#undef INCLUDE_DATA
-
-.section #nvd7_grhub_code
-#define INCLUDE_CODE
-bra #init
-#include "com.fuc"
-#include "hub.fuc"
-.align 256
-#undef INCLUDE_CODE
diff --git a/drivers/gpu/drm/nouveau/core/engine/graph/fuc/hubnvd7.fuc.h b/drivers/gpu/drm/nouveau/core/engine/graph/fuc/hubnvd7.fuc.h
deleted file mode 100644 (file)
index 62b0c76..0000000
+++ /dev/null
@@ -1,1047 +0,0 @@
-uint32_t nvd7_grhub_data[] = {
-/* 0x0000: hub_mmio_list_head */
-       0x00000300,
-/* 0x0004: hub_mmio_list_tail */
-       0x00000304,
-/* 0x0008: gpc_count */
-       0x00000000,
-/* 0x000c: rop_count */
-       0x00000000,
-/* 0x0010: cmd_queue */
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-/* 0x0058: ctx_current */
-       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,
-/* 0x0100: chan_data */
-/* 0x0100: chan_mmio_count */
-       0x00000000,
-/* 0x0104: chan_mmio_address */
-       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,
-/* 0x0200: xfer_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,
-/* 0x0300: hub_mmio_list_base */
-       0x0417e91c,
-};
-
-uint32_t nvd7_grhub_code[] = {
-       0x039b0ef5,
-/* 0x0004: queue_put */
-       0x9800d898,
-       0x86f001d9,
-       0x0489b808,
-       0xf00c1bf4,
-       0x21f502f7,
-       0x00f8037e,
-/* 0x001c: queue_put_next */
-       0xb60798c4,
-       0x8dbb0384,
-       0x0880b600,
-       0x80008e80,
-       0x90b6018f,
-       0x0f94f001,
-       0xf801d980,
-/* 0x0039: queue_get */
-       0x0131f400,
-       0x9800d898,
-       0x89b801d9,
-       0x210bf404,
-       0xb60789c4,
-       0x9dbb0394,
-       0x0890b600,
-       0x98009e98,
-       0x80b6019f,
-       0x0f84f001,
-       0xf400d880,
-/* 0x0066: queue_get_done */
-       0x00f80132,
-/* 0x0068: nv_rd32 */
-       0xf002ecb9,
-       0x07f11fc9,
-       0x03f0ca00,
-       0x000cd001,
-/* 0x007a: nv_rd32_wait */
-       0xc7f104bd,
-       0xc3f0ca00,
-       0x00cccf01,
-       0xf41fccc8,
-       0xa7f0f31b,
-       0x1021f506,
-       0x00f7f101,
-       0x01f3f0cb,
-       0xf800ffcf,
-/* 0x009d: nv_wr32 */
-       0x0007f100,
-       0x0103f0cc,
-       0xbd000fd0,
-       0x02ecb904,
-       0xf01fc9f0,
-       0x07f11ec9,
-       0x03f0ca00,
-       0x000cd001,
-/* 0x00be: nv_wr32_wait */
-       0xc7f104bd,
-       0xc3f0ca00,
-       0x00cccf01,
-       0xf41fccc8,
-       0x00f8f31b,
-/* 0x00d0: wait_donez */
-       0x99f094bd,
-       0x0007f100,
-       0x0203f00f,
-       0xbd0009d0,
-       0x0007f104,
-       0x0203f006,
-       0xbd000ad0,
-/* 0x00ed: wait_donez_ne */
-       0x0087f104,
-       0x0183f000,
-       0xff0088cf,
-       0x1bf4888a,
-       0xf094bdf3,
-       0x07f10099,
-       0x03f01700,
-       0x0009d002,
-       0x00f804bd,
-/* 0x0110: wait_doneo */
-       0x99f094bd,
-       0x0007f100,
-       0x0203f00f,
-       0xbd0009d0,
-       0x0007f104,
-       0x0203f006,
-       0xbd000ad0,
-/* 0x012d: wait_doneo_e */
-       0x0087f104,
-       0x0183f000,
-       0xff0088cf,
-       0x0bf4888a,
-       0xf094bdf3,
-       0x07f10099,
-       0x03f01700,
-       0x0009d002,
-       0x00f804bd,
-/* 0x0150: mmctx_size */
-/* 0x0152: nv_mmctx_size_loop */
-       0xe89894bd,
-       0x1a85b600,
-       0xb60180b6,
-       0x98bb0284,
-       0x04e0b600,
-       0xf404efb8,
-       0x9fb9eb1b,
-/* 0x016f: mmctx_xfer */
-       0xbd00f802,
-       0x0199f094,
-       0x0f0007f1,
-       0xd00203f0,
-       0x04bd0009,
-       0xbbfd94bd,
-       0x120bf405,
-       0xc40007f1,
-       0xd00103f0,
-       0x04bd000b,
-/* 0x0197: mmctx_base_disabled */
-       0xfd0099f0,
-       0x0bf405ee,
-       0x0007f11e,
-       0x0103f0c6,
-       0xbd000ed0,
-       0x0007f104,
-       0x0103f0c7,
-       0xbd000fd0,
-       0x0199f004,
-/* 0x01b8: mmctx_multi_disabled */
-       0xb600abc8,
-       0xb9f010b4,
-       0x01aec80c,
-       0xfd11e4b6,
-       0x07f105be,
-       0x03f0c500,
-       0x000bd001,
-/* 0x01d6: mmctx_exec_loop */
-/* 0x01d6: mmctx_wait_free */
-       0xe7f104bd,
-       0xe3f0c500,
-       0x00eecf01,
-       0xf41fe4f0,
-       0xce98f30b,
-       0x05e9fd00,
-       0xc80007f1,
-       0xd00103f0,
-       0x04bd000e,
-       0xb804c0b6,
-       0x1bf404cd,
-       0x02abc8d8,
-/* 0x0207: mmctx_fini_wait */
-       0xf11f1bf4,
-       0xf0c500b7,
-       0xbbcf01b3,
-       0x1fb4f000,
-       0xf410b4b0,
-       0xa7f0f01b,
-       0xd021f405,
-/* 0x0223: mmctx_stop */
-       0xc82b0ef4,
-       0xb4b600ab,
-       0x0cb9f010,
-       0xf112b9f0,
-       0xf0c50007,
-       0x0bd00103,
-/* 0x023b: mmctx_stop_wait */
-       0xf104bd00,
-       0xf0c500b7,
-       0xbbcf01b3,
-       0x12bbc800,
-/* 0x024b: mmctx_done */
-       0xbdf31bf4,
-       0x0199f094,
-       0x170007f1,
-       0xd00203f0,
-       0x04bd0009,
-/* 0x025e: strand_wait */
-       0xa0f900f8,
-       0xf402a7f0,
-       0xa0fcd021,
-/* 0x026a: strand_pre */
-       0x97f000f8,
-       0xfc07f10c,
-       0x0203f04a,
-       0xbd0009d0,
-       0x5e21f504,
-/* 0x027f: strand_post */
-       0xf000f802,
-       0x07f10d97,
-       0x03f04afc,
-       0x0009d002,
-       0x21f504bd,
-       0x00f8025e,
-/* 0x0294: strand_set */
-       0xf10fc7f0,
-       0xf04ffc07,
-       0x0cd00203,
-       0xf004bd00,
-       0x07f10bc7,
-       0x03f04afc,
-       0x000cd002,
-       0x07f104bd,
-       0x03f04ffc,
-       0x000ed002,
-       0xc7f004bd,
-       0xfc07f10a,
-       0x0203f04a,
-       0xbd000cd0,
-       0x5e21f504,
-/* 0x02d3: strand_ctx_init */
-       0xbd00f802,
-       0x0399f094,
-       0x0f0007f1,
-       0xd00203f0,
-       0x04bd0009,
-       0x026a21f5,
-       0xf503e7f0,
-       0xbd029421,
-       0xfc07f1c4,
-       0x0203f047,
-       0xbd000cd0,
-       0x01c7f004,
-       0x4afc07f1,
-       0xd00203f0,
-       0x04bd000c,
-       0x025e21f5,
-       0xf1010c92,
-       0xf046fc07,
-       0x0cd00203,
-       0xf004bd00,
-       0x07f102c7,
-       0x03f04afc,
-       0x000cd002,
-       0x21f504bd,
-       0x21f5025e,
-       0x87f1027f,
-       0x83f04200,
-       0x0097f102,
-       0x0293f020,
-       0x950099cf,
-/* 0x034a: ctx_init_strand_loop */
-       0x8ed008fe,
-       0x408ed000,
-       0xb6808acf,
-       0xa0b606a5,
-       0x00eabb01,
-       0xb60480b6,
-       0x1bf40192,
-       0x08e4b6e8,
-       0xbdf2efbc,
-       0x0399f094,
-       0x170007f1,
-       0xd00203f0,
-       0x04bd0009,
-/* 0x037e: error */
-       0x07f100f8,
-       0x03f00500,
-       0x000fd002,
-       0xf7f004bd,
-       0x0007f101,
-       0x0303f007,
-       0xbd000fd0,
-/* 0x039b: init */
-       0xbd00f804,
-       0x0007fe04,
-       0x420017f1,
-       0xcf0013f0,
-       0x11e70011,
-       0x14b60109,
-       0x0014fe08,
-       0xf10227f0,
-       0xf0120007,
-       0x02d00003,
-       0xf104bd00,
-       0xfe06c817,
-       0x24bd0010,
-       0x070007f1,
-       0xd00003f0,
-       0x04bd0002,
-       0x200327f1,
-       0x010007f1,
-       0xd00103f0,
-       0x04bd0002,
-       0x200427f1,
-       0x010407f1,
-       0xd00103f0,
-       0x04bd0002,
-       0x200b27f1,
-       0x010807f1,
-       0xd00103f0,
-       0x04bd0002,
-       0x200c27f1,
-       0x011c07f1,
-       0xd00103f0,
-       0x04bd0002,
-       0xf1010392,
-       0xf0090007,
-       0x03d00303,
-       0xf104bd00,
-       0xf0870427,
-       0x07f10023,
-       0x03f00400,
-       0x0002d000,
-       0x27f004bd,
-       0x0007f104,
-       0x0003f003,
-       0xbd0002d0,
-       0x1031f404,
-       0x9604e7f1,
-       0xf440e3f0,
-       0xfeb96821,
-       0x90f1c702,
-       0xf0030180,
-       0x0f801ff4,
-       0x0117f002,
-       0xb6041fbb,
-       0x07f10112,
-       0x03f00300,
-       0x0001d001,
-       0x07f104bd,
-       0x03f00400,
-       0x0001d001,
-       0x17f104bd,
-       0xf7f00100,
-       0x0d21f502,
-       0x1f21f508,
-       0x10f7f008,
-       0x086c21f5,
-       0x98000e98,
-       0x21f5010f,
-       0x14950150,
-       0x0007f108,
-       0x0103f0c0,
-       0xbd0004d0,
-       0x0007f104,
-       0x0103f0c1,
-       0xbd0004d0,
-       0x0030b704,
-       0x001fbb13,
-       0xf102f5b6,
-       0xf0d30007,
-       0x0fd00103,
-       0xb604bd00,
-       0x10b60815,
-       0x0814b601,
-       0xf5021fb9,
-       0xbb02d321,
-       0x0398001f,
-       0x0047f102,
-       0x5043f020,
-/* 0x04f4: init_gpc */
-       0x08044ea0,
-       0xf4021fb9,
-       0x4ea09d21,
-       0xf4bd010c,
-       0xa09d21f4,
-       0xf401044e,
-       0x4ea09d21,
-       0xf7f00100,
-       0x9d21f402,
-       0x08004ea0,
-/* 0x051c: init_gpc_wait */
-       0xc86821f4,
-       0x0bf41fff,
-       0x044ea0fa,
-       0x6821f408,
-       0xb7001fbb,
-       0xb6800040,
-       0x1bf40132,
-       0x00f7f0be,
-       0x086c21f5,
-       0xf500f7f0,
-       0xf1080d21,
-       0xf0010007,
-       0x01d00203,
-       0xbd04bd00,
-       0x1f19f014,
-       0x080007f1,
-       0xd00203f0,
-       0x04bd0001,
-/* 0x0564: main */
-       0xf40031f4,
-       0xd7f00028,
-       0x3921f410,
-       0xb1f401f4,
-       0xf54001e4,
-       0xbd00e91b,
-       0x0499f094,
-       0x0f0007f1,
-       0xd00203f0,
-       0x04bd0009,
-       0xc00017f1,
-       0xcf0213f0,
-       0x27f10011,
-       0x23f0c100,
-       0x0022cf02,
-       0xf51f13c8,
-       0xc800890b,
-       0x0bf41f23,
-       0xb920f962,
-       0x94bd0212,
-       0xf10799f0,
-       0xf00f0007,
-       0x09d00203,
-       0xf404bd00,
-       0x31f40132,
-       0x4021f502,
-       0xf094bd0a,
-       0x07f10799,
-       0x03f01700,
-       0x0009d002,
-       0x20fc04bd,
-       0x99f094bd,
-       0x0007f106,
-       0x0203f00f,
-       0xbd0009d0,
-       0x0131f404,
-       0x0a4021f5,
-       0x99f094bd,
-       0x0007f106,
-       0x0203f017,
-       0xbd0009d0,
-       0x330ef404,
-/* 0x060c: chsw_prev_no_next */
-       0x12b920f9,
-       0x0132f402,
-       0xf50232f4,
-       0xfc0a4021,
-       0x0007f120,
-       0x0203f0c0,
-       0xbd0002d0,
-       0x130ef404,
-/* 0x062c: chsw_no_prev */
-       0xf41f23c8,
-       0x31f40d0b,
-       0x0232f401,
-       0x0a4021f5,
-/* 0x063c: chsw_done */
-       0xf10127f0,
-       0xf0c30007,
-       0x02d00203,
-       0xbd04bd00,
-       0x0499f094,
-       0x170007f1,
-       0xd00203f0,
-       0x04bd0009,
-       0xff080ef5,
-/* 0x0660: main_not_ctx_switch */
-       0xf401e4b0,
-       0xf2b90d1b,
-       0xd021f502,
-       0x460ef409,
-/* 0x0670: main_not_ctx_chan */
-       0xf402e4b0,
-       0x94bd321b,
-       0xf10799f0,
-       0xf00f0007,
-       0x09d00203,
-       0xf404bd00,
-       0x32f40132,
-       0x4021f502,
-       0xf094bd0a,
-       0x07f10799,
-       0x03f01700,
-       0x0009d002,
-       0x0ef404bd,
-/* 0x06a5: main_not_ctx_save */
-       0x10ef9411,
-       0xf501f5f0,
-       0xf5037e21,
-/* 0x06b3: main_done */
-       0xbdfeb50e,
-       0x1f29f024,
-       0x080007f1,
-       0xd00203f0,
-       0x04bd0002,
-       0xfea00ef5,
-/* 0x06c8: ih */
-       0x88fe80f9,
-       0xf980f901,
-       0xf9a0f990,
-       0xf9d0f9b0,
-       0xbdf0f9e0,
-       0x00a7f104,
-       0x00a3f002,
-       0xc400aacf,
-       0x0bf404ab,
-       0x10d7f030,
-       0x1a00e7f1,
-       0xcf00e3f0,
-       0xf7f100ee,
-       0xf3f01900,
-       0x00ffcf00,
-       0xb70421f4,
-       0xf00400b0,
-       0x07f101e7,
-       0x03f01d00,
-       0x000ed000,
-/* 0x071a: ih_no_fifo */
-       0xabe404bd,
-       0x0bf40100,
-       0x10d7f00d,
-       0x4001e7f1,
-/* 0x072b: ih_no_ctxsw */
-       0xe40421f4,
-       0xf40400ab,
-       0xe7f16c0b,
-       0xe3f00708,
-       0x6821f440,
-       0xf102ffb9,
-       0xf0040007,
-       0x0fd00203,
-       0xf104bd00,
-       0xf00704e7,
-       0x21f440e3,
-       0x02ffb968,
-       0x030007f1,
-       0xd00203f0,
-       0x04bd000f,
-       0x9450fec7,
-       0xf7f102ee,
-       0xf3f00700,
-       0x00efbb40,
-       0xf16821f4,
-       0xf0020007,
-       0x0fd00203,
-       0xf004bd00,
-       0x21f503f7,
-       0xb7f1037e,
-       0xbfb90100,
-       0x44e7f102,
-       0x40e3f001,
-/* 0x079b: ih_no_fwmthd */
-       0xf19d21f4,
-       0xbd0504b7,
-       0xb4abffb0,
-       0xf10f0bf4,
-       0xf0070007,
-       0x0bd00303,
-/* 0x07b3: ih_no_other */
-       0xf104bd00,
-       0xf0010007,
-       0x0ad00003,
-       0xfc04bd00,
-       0xfce0fcf0,
-       0xfcb0fcd0,
-       0xfc90fca0,
-       0x0088fe80,
-       0x32f480fc,
-/* 0x07d7: ctx_4160s */
-       0xf001f800,
-       0xffb901f7,
-       0x60e7f102,
-       0x40e3f041,
-/* 0x07e7: ctx_4160s_wait */
-       0xf19d21f4,
-       0xf04160e7,
-       0x21f440e3,
-       0x02ffb968,
-       0xf404ffc8,
-       0x00f8f00b,
-/* 0x07fc: ctx_4160c */
-       0xffb9f4bd,
-       0x60e7f102,
-       0x40e3f041,
-       0xf89d21f4,
-/* 0x080d: ctx_4170s */
-       0x10f5f000,
-       0xf102ffb9,
-       0xf04170e7,
-       0x21f440e3,
-/* 0x081f: ctx_4170w */
-       0xf100f89d,
-       0xf04170e7,
-       0x21f440e3,
-       0x02ffb968,
-       0xf410f4f0,
-       0x00f8f01b,
-/* 0x0834: ctx_redswitch */
-       0x0200e7f1,
-       0xf040e5f0,
-       0xe5f020e5,
-       0x0007f110,
-       0x0103f085,
-       0xbd000ed0,
-       0x08f7f004,
-/* 0x0850: ctx_redswitch_delay */
-       0xf401f2b6,
-       0xe5f1fd1b,
-       0xe5f10400,
-       0x07f10100,
-       0x03f08500,
-       0x000ed001,
-       0x00f804bd,
-/* 0x086c: ctx_86c */
-       0x1b0007f1,
-       0xd00203f0,
-       0x04bd000f,
-       0xf102ffb9,
-       0xf08a14e7,
-       0x21f440e3,
-       0x02ffb99d,
-       0xa86ce7f1,
-       0xf441e3f0,
-       0x00f89d21,
-/* 0x0894: ctx_mem */
-       0x840007f1,
-       0xd00203f0,
-       0x04bd000f,
-/* 0x08a0: ctx_mem_wait */
-       0x8400f7f1,
-       0xcf02f3f0,
-       0xfffd00ff,
-       0xf31bf405,
-/* 0x08b2: ctx_load */
-       0x94bd00f8,
-       0xf10599f0,
-       0xf00f0007,
-       0x09d00203,
-       0xf004bd00,
-       0x21f40ca7,
-       0xf1f4bdd0,
-       0xf0890007,
-       0x0fd00203,
-       0xf104bd00,
-       0xf0c10007,
-       0x02d00203,
-       0xf104bd00,
-       0xf0830007,
-       0x02d00203,
-       0xf004bd00,
-       0x21f507f7,
-       0x07f10894,
-       0x03f0c000,
-       0x0002d002,
-       0x0bfe04bd,
-       0x1f2af000,
-       0xb60424b6,
-       0x94bd0220,
-       0xf10899f0,
-       0xf00f0007,
-       0x09d00203,
-       0xf104bd00,
-       0xf0810007,
-       0x02d00203,
-       0xf104bd00,
-       0xf1000027,
-       0xf0800023,
-       0x07f10225,
-       0x03f08800,
-       0x0002d002,
-       0x17f004bd,
-       0x0027f110,
-       0x0223f002,
-       0xf80512fa,
-       0xf094bd03,
-       0x07f10899,
-       0x03f01700,
-       0x0009d002,
-       0x019804bd,
-       0x1814b681,
-       0xb6800298,
-       0x12fd0825,
-       0x16018005,
-       0x99f094bd,
-       0x0007f109,
-       0x0203f00f,
-       0xbd0009d0,
-       0x0007f104,
-       0x0203f081,
-       0xbd0001d0,
-       0x0127f004,
-       0x880007f1,
-       0xd00203f0,
-       0x04bd0002,
-       0x010017f1,
-       0xfa0613f0,
-       0x03f80501,
-       0x99f094bd,
-       0x0007f109,
-       0x0203f017,
-       0xbd0009d0,
-       0xf094bd04,
-       0x07f10599,
-       0x03f01700,
-       0x0009d002,
-       0x00f804bd,
-/* 0x09d0: ctx_chan */
-       0x07d721f5,
-       0x08b221f5,
-       0xf40ca7f0,
-       0xf7f0d021,
-       0x9421f505,
-       0xfc21f508,
-/* 0x09eb: ctx_mmio_exec */
-       0x9800f807,
-       0x07f14103,
-       0x03f08100,
-       0x0003d002,
-       0x34bd04bd,
-/* 0x09fc: ctx_mmio_loop */
-       0xf4ff34c4,
-       0x57f10f1b,
-       0x53f00200,
-       0x0535fa06,
-/* 0x0a0e: ctx_mmio_pull */
-       0x4e9803f8,
-       0x814f9880,
-       0xb69d21f4,
-       0x12b60830,
-       0xdf1bf401,
-/* 0x0a20: ctx_mmio_done */
-       0xf1160398,
-       0xf0810007,
-       0x03d00203,
-       0x8004bd00,
-       0x17f14000,
-       0x13f00100,
-       0x0601fa06,
-       0x00f803f8,
-/* 0x0a40: ctx_xfer */
-       0xf104e7f0,
-       0xf0020007,
-       0x0ed00303,
-/* 0x0a4f: ctx_xfer_idle */
-       0xf104bd00,
-       0xf00000e7,
-       0xeecf03e3,
-       0x00e4f100,
-       0xf21bf420,
-       0xf40611f4,
-/* 0x0a66: ctx_xfer_pre */
-       0xf7f01102,
-       0x6c21f510,
-       0xd721f508,
-       0x1c11f407,
-/* 0x0a74: ctx_xfer_pre_load */
-       0xf502f7f0,
-       0xf5080d21,
-       0xf5081f21,
-       0xbd083421,
-       0x0d21f5f4,
-       0xb221f508,
-/* 0x0a8d: ctx_xfer_exec */
-       0x16019808,
-       0x07f124bd,
-       0x03f00500,
-       0x0002d001,
-       0x1fb904bd,
-       0x00e7f102,
-       0x41e3f0a5,
-       0xf09d21f4,
-       0x2cf001fc,
-       0x0124b602,
-       0xb905f2fd,
-       0xe7f102ff,
-       0xe3f0a504,
-       0x9d21f441,
-       0x026a21f5,
-       0x07f124bd,
-       0x03f047fc,
-       0x0002d002,
-       0x2cf004bd,
-       0x0320b601,
-       0x4afc07f1,
-       0xd00203f0,
-       0x04bd0002,
-       0xf001acf0,
-       0xb7f006a5,
-       0x000c9800,
-       0xf0010d98,
-       0x21f500e7,
-       0xa7f0016f,
-       0x1021f508,
-       0x5e21f501,
-       0x1301f402,
-       0xf40ca7f0,
-       0xf7f0d021,
-       0x9421f505,
-       0x3202f408,
-/* 0x0b1c: ctx_xfer_post */
-       0xf502f7f0,
-       0xbd080d21,
-       0x6c21f5f4,
-       0x7f21f508,
-       0x1f21f502,
-       0xf5f4bd08,
-       0xf4080d21,
-       0x01981011,
-       0x0511fd40,
-       0xf5070bf4,
-/* 0x0b47: ctx_xfer_no_post_mmio */
-       0xf509eb21,
-/* 0x0b4b: ctx_xfer_done */
-       0xf807fc21,
-       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,
-};
diff --git a/drivers/gpu/drm/nouveau/core/engine/graph/fuc/hubnve0.fuc b/drivers/gpu/drm/nouveau/core/engine/graph/fuc/hubnve0.fuc
deleted file mode 100644 (file)
index d4840f1..0000000
+++ /dev/null
@@ -1,40 +0,0 @@
-/*
- * Copyright 2013 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 <bskeggs@redhat.com>
- */
-
-#define CHIPSET GK100
-#include "macros.fuc"
-
-.section #nve0_grhub_data
-#define INCLUDE_DATA
-#include "com.fuc"
-#include "hub.fuc"
-#undef INCLUDE_DATA
-
-.section #nve0_grhub_code
-#define INCLUDE_CODE
-bra #init
-#include "com.fuc"
-#include "hub.fuc"
-.align 256
-#undef INCLUDE_CODE
diff --git a/drivers/gpu/drm/nouveau/core/engine/graph/fuc/hubnve0.fuc.h b/drivers/gpu/drm/nouveau/core/engine/graph/fuc/hubnve0.fuc.h
deleted file mode 100644 (file)
index 51c3797..0000000
+++ /dev/null
@@ -1,1044 +0,0 @@
-uint32_t nve0_grhub_data[] = {
-/* 0x0000: hub_mmio_list_head */
-       0x00000300,
-/* 0x0004: hub_mmio_list_tail */
-       0x00000304,
-/* 0x0008: gpc_count */
-       0x00000000,
-/* 0x000c: rop_count */
-       0x00000000,
-/* 0x0010: cmd_queue */
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-/* 0x0058: ctx_current */
-       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,
-/* 0x0100: chan_data */
-/* 0x0100: chan_mmio_count */
-       0x00000000,
-/* 0x0104: chan_mmio_address */
-       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,
-/* 0x0200: xfer_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,
-/* 0x0300: hub_mmio_list_base */
-       0x0417e91c,
-};
-
-uint32_t nve0_grhub_code[] = {
-       0x039b0ef5,
-/* 0x0004: queue_put */
-       0x9800d898,
-       0x86f001d9,
-       0x0489b808,
-       0xf00c1bf4,
-       0x21f502f7,
-       0x00f8037e,
-/* 0x001c: queue_put_next */
-       0xb60798c4,
-       0x8dbb0384,
-       0x0880b600,
-       0x80008e80,
-       0x90b6018f,
-       0x0f94f001,
-       0xf801d980,
-/* 0x0039: queue_get */
-       0x0131f400,
-       0x9800d898,
-       0x89b801d9,
-       0x210bf404,
-       0xb60789c4,
-       0x9dbb0394,
-       0x0890b600,
-       0x98009e98,
-       0x80b6019f,
-       0x0f84f001,
-       0xf400d880,
-/* 0x0066: queue_get_done */
-       0x00f80132,
-/* 0x0068: nv_rd32 */
-       0xf002ecb9,
-       0x07f11fc9,
-       0x03f0ca00,
-       0x000cd001,
-/* 0x007a: nv_rd32_wait */
-       0xc7f104bd,
-       0xc3f0ca00,
-       0x00cccf01,
-       0xf41fccc8,
-       0xa7f0f31b,
-       0x1021f506,
-       0x00f7f101,
-       0x01f3f0cb,
-       0xf800ffcf,
-/* 0x009d: nv_wr32 */
-       0x0007f100,
-       0x0103f0cc,
-       0xbd000fd0,
-       0x02ecb904,
-       0xf01fc9f0,
-       0x07f11ec9,
-       0x03f0ca00,
-       0x000cd001,
-/* 0x00be: nv_wr32_wait */
-       0xc7f104bd,
-       0xc3f0ca00,
-       0x00cccf01,
-       0xf41fccc8,
-       0x00f8f31b,
-/* 0x00d0: wait_donez */
-       0x99f094bd,
-       0x0007f100,
-       0x0203f00f,
-       0xbd0009d0,
-       0x0007f104,
-       0x0203f006,
-       0xbd000ad0,
-/* 0x00ed: wait_donez_ne */
-       0x0087f104,
-       0x0183f000,
-       0xff0088cf,
-       0x1bf4888a,
-       0xf094bdf3,
-       0x07f10099,
-       0x03f01700,
-       0x0009d002,
-       0x00f804bd,
-/* 0x0110: wait_doneo */
-       0x99f094bd,
-       0x0007f100,
-       0x0203f00f,
-       0xbd0009d0,
-       0x0007f104,
-       0x0203f006,
-       0xbd000ad0,
-/* 0x012d: wait_doneo_e */
-       0x0087f104,
-       0x0183f000,
-       0xff0088cf,
-       0x0bf4888a,
-       0xf094bdf3,
-       0x07f10099,
-       0x03f01700,
-       0x0009d002,
-       0x00f804bd,
-/* 0x0150: mmctx_size */
-/* 0x0152: nv_mmctx_size_loop */
-       0xe89894bd,
-       0x1a85b600,
-       0xb60180b6,
-       0x98bb0284,
-       0x04e0b600,
-       0xf404efb8,
-       0x9fb9eb1b,
-/* 0x016f: mmctx_xfer */
-       0xbd00f802,
-       0x0199f094,
-       0x0f0007f1,
-       0xd00203f0,
-       0x04bd0009,
-       0xbbfd94bd,
-       0x120bf405,
-       0xc40007f1,
-       0xd00103f0,
-       0x04bd000b,
-/* 0x0197: mmctx_base_disabled */
-       0xfd0099f0,
-       0x0bf405ee,
-       0x0007f11e,
-       0x0103f0c6,
-       0xbd000ed0,
-       0x0007f104,
-       0x0103f0c7,
-       0xbd000fd0,
-       0x0199f004,
-/* 0x01b8: mmctx_multi_disabled */
-       0xb600abc8,
-       0xb9f010b4,
-       0x01aec80c,
-       0xfd11e4b6,
-       0x07f105be,
-       0x03f0c500,
-       0x000bd001,
-/* 0x01d6: mmctx_exec_loop */
-/* 0x01d6: mmctx_wait_free */
-       0xe7f104bd,
-       0xe3f0c500,
-       0x00eecf01,
-       0xf41fe4f0,
-       0xce98f30b,
-       0x05e9fd00,
-       0xc80007f1,
-       0xd00103f0,
-       0x04bd000e,
-       0xb804c0b6,
-       0x1bf404cd,
-       0x02abc8d8,
-/* 0x0207: mmctx_fini_wait */
-       0xf11f1bf4,
-       0xf0c500b7,
-       0xbbcf01b3,
-       0x1fb4f000,
-       0xf410b4b0,
-       0xa7f0f01b,
-       0xd021f405,
-/* 0x0223: mmctx_stop */
-       0xc82b0ef4,
-       0xb4b600ab,
-       0x0cb9f010,
-       0xf112b9f0,
-       0xf0c50007,
-       0x0bd00103,
-/* 0x023b: mmctx_stop_wait */
-       0xf104bd00,
-       0xf0c500b7,
-       0xbbcf01b3,
-       0x12bbc800,
-/* 0x024b: mmctx_done */
-       0xbdf31bf4,
-       0x0199f094,
-       0x170007f1,
-       0xd00203f0,
-       0x04bd0009,
-/* 0x025e: strand_wait */
-       0xa0f900f8,
-       0xf402a7f0,
-       0xa0fcd021,
-/* 0x026a: strand_pre */
-       0x97f000f8,
-       0xfc07f10c,
-       0x0203f04a,
-       0xbd0009d0,
-       0x5e21f504,
-/* 0x027f: strand_post */
-       0xf000f802,
-       0x07f10d97,
-       0x03f04afc,
-       0x0009d002,
-       0x21f504bd,
-       0x00f8025e,
-/* 0x0294: strand_set */
-       0xf10fc7f0,
-       0xf04ffc07,
-       0x0cd00203,
-       0xf004bd00,
-       0x07f10bc7,
-       0x03f04afc,
-       0x000cd002,
-       0x07f104bd,
-       0x03f04ffc,
-       0x000ed002,
-       0xc7f004bd,
-       0xfc07f10a,
-       0x0203f04a,
-       0xbd000cd0,
-       0x5e21f504,
-/* 0x02d3: strand_ctx_init */
-       0xbd00f802,
-       0x0399f094,
-       0x0f0007f1,
-       0xd00203f0,
-       0x04bd0009,
-       0x026a21f5,
-       0xf503e7f0,
-       0xbd029421,
-       0xfc07f1c4,
-       0x0203f047,
-       0xbd000cd0,
-       0x01c7f004,
-       0x4afc07f1,
-       0xd00203f0,
-       0x04bd000c,
-       0x025e21f5,
-       0xf1010c92,
-       0xf046fc07,
-       0x0cd00203,
-       0xf004bd00,
-       0x07f102c7,
-       0x03f04afc,
-       0x000cd002,
-       0x21f504bd,
-       0x21f5025e,
-       0x87f1027f,
-       0x83f04200,
-       0x0097f102,
-       0x0293f020,
-       0x950099cf,
-/* 0x034a: ctx_init_strand_loop */
-       0x8ed008fe,
-       0x408ed000,
-       0xb6808acf,
-       0xa0b606a5,
-       0x00eabb01,
-       0xb60480b6,
-       0x1bf40192,
-       0x08e4b6e8,
-       0xbdf2efbc,
-       0x0399f094,
-       0x170007f1,
-       0xd00203f0,
-       0x04bd0009,
-/* 0x037e: error */
-       0x07f100f8,
-       0x03f00500,
-       0x000fd002,
-       0xf7f004bd,
-       0x0007f101,
-       0x0303f007,
-       0xbd000fd0,
-/* 0x039b: init */
-       0xbd00f804,
-       0x0007fe04,
-       0x420017f1,
-       0xcf0013f0,
-       0x11e70011,
-       0x14b60109,
-       0x0014fe08,
-       0xf10227f0,
-       0xf0120007,
-       0x02d00003,
-       0xf104bd00,
-       0xfe06c817,
-       0x24bd0010,
-       0x070007f1,
-       0xd00003f0,
-       0x04bd0002,
-       0x200327f1,
-       0x010007f1,
-       0xd00103f0,
-       0x04bd0002,
-       0x200427f1,
-       0x010407f1,
-       0xd00103f0,
-       0x04bd0002,
-       0x200b27f1,
-       0x010807f1,
-       0xd00103f0,
-       0x04bd0002,
-       0x200c27f1,
-       0x011c07f1,
-       0xd00103f0,
-       0x04bd0002,
-       0xf1010392,
-       0xf0090007,
-       0x03d00303,
-       0xf104bd00,
-       0xf0870427,
-       0x07f10023,
-       0x03f00400,
-       0x0002d000,
-       0x27f004bd,
-       0x0007f104,
-       0x0003f003,
-       0xbd0002d0,
-       0x1031f404,
-       0x9604e7f1,
-       0xf440e3f0,
-       0xfeb96821,
-       0x90f1c702,
-       0xf0030180,
-       0x0f801ff4,
-       0x0117f002,
-       0xb6041fbb,
-       0x07f10112,
-       0x03f00300,
-       0x0001d001,
-       0x07f104bd,
-       0x03f00400,
-       0x0001d001,
-       0x17f104bd,
-       0xf7f00100,
-       0xd721f502,
-       0xe921f507,
-       0x10f7f007,
-       0x083621f5,
-       0x98000e98,
-       0x21f5010f,
-       0x14950150,
-       0x0007f108,
-       0x0103f0c0,
-       0xbd0004d0,
-       0x0007f104,
-       0x0103f0c1,
-       0xbd0004d0,
-       0x0030b704,
-       0x001fbb13,
-       0xf102f5b6,
-       0xf0d30007,
-       0x0fd00103,
-       0xb604bd00,
-       0x10b60815,
-       0x0814b601,
-       0xf5021fb9,
-       0xbb02d321,
-       0x0398001f,
-       0x0047f102,
-       0x5043f020,
-/* 0x04f4: init_gpc */
-       0x08044ea0,
-       0xf4021fb9,
-       0x4ea09d21,
-       0xf4bd010c,
-       0xa09d21f4,
-       0xf401044e,
-       0x4ea09d21,
-       0xf7f00100,
-       0x9d21f402,
-       0x08004ea0,
-/* 0x051c: init_gpc_wait */
-       0xc86821f4,
-       0x0bf41fff,
-       0x044ea0fa,
-       0x6821f408,
-       0xb7001fbb,
-       0xb6800040,
-       0x1bf40132,
-       0x00f7f0be,
-       0x083621f5,
-       0xf500f7f0,
-       0xf107d721,
-       0xf0010007,
-       0x01d00203,
-       0xbd04bd00,
-       0x1f19f014,
-       0x080007f1,
-       0xd00203f0,
-       0x04bd0001,
-/* 0x0564: main */
-       0xf40031f4,
-       0xd7f00028,
-       0x3921f410,
-       0xb1f401f4,
-       0xf54001e4,
-       0xbd00e91b,
-       0x0499f094,
-       0x0f0007f1,
-       0xd00203f0,
-       0x04bd0009,
-       0xc00017f1,
-       0xcf0213f0,
-       0x27f10011,
-       0x23f0c100,
-       0x0022cf02,
-       0xf51f13c8,
-       0xc800890b,
-       0x0bf41f23,
-       0xb920f962,
-       0x94bd0212,
-       0xf10799f0,
-       0xf00f0007,
-       0x09d00203,
-       0xf404bd00,
-       0x31f40132,
-       0x0221f502,
-       0xf094bd0a,
-       0x07f10799,
-       0x03f01700,
-       0x0009d002,
-       0x20fc04bd,
-       0x99f094bd,
-       0x0007f106,
-       0x0203f00f,
-       0xbd0009d0,
-       0x0131f404,
-       0x0a0221f5,
-       0x99f094bd,
-       0x0007f106,
-       0x0203f017,
-       0xbd0009d0,
-       0x330ef404,
-/* 0x060c: chsw_prev_no_next */
-       0x12b920f9,
-       0x0132f402,
-       0xf50232f4,
-       0xfc0a0221,
-       0x0007f120,
-       0x0203f0c0,
-       0xbd0002d0,
-       0x130ef404,
-/* 0x062c: chsw_no_prev */
-       0xf41f23c8,
-       0x31f40d0b,
-       0x0232f401,
-       0x0a0221f5,
-/* 0x063c: chsw_done */
-       0xf10127f0,
-       0xf0c30007,
-       0x02d00203,
-       0xbd04bd00,
-       0x0499f094,
-       0x170007f1,
-       0xd00203f0,
-       0x04bd0009,
-       0xff080ef5,
-/* 0x0660: main_not_ctx_switch */
-       0xf401e4b0,
-       0xf2b90d1b,
-       0x9a21f502,
-       0x460ef409,
-/* 0x0670: main_not_ctx_chan */
-       0xf402e4b0,
-       0x94bd321b,
-       0xf10799f0,
-       0xf00f0007,
-       0x09d00203,
-       0xf404bd00,
-       0x32f40132,
-       0x0221f502,
-       0xf094bd0a,
-       0x07f10799,
-       0x03f01700,
-       0x0009d002,
-       0x0ef404bd,
-/* 0x06a5: main_not_ctx_save */
-       0x10ef9411,
-       0xf501f5f0,
-       0xf5037e21,
-/* 0x06b3: main_done */
-       0xbdfeb50e,
-       0x1f29f024,
-       0x080007f1,
-       0xd00203f0,
-       0x04bd0002,
-       0xfea00ef5,
-/* 0x06c8: ih */
-       0x88fe80f9,
-       0xf980f901,
-       0xf9a0f990,
-       0xf9d0f9b0,
-       0xbdf0f9e0,
-       0x00a7f104,
-       0x00a3f002,
-       0xc400aacf,
-       0x0bf404ab,
-       0x10d7f030,
-       0x1a00e7f1,
-       0xcf00e3f0,
-       0xf7f100ee,
-       0xf3f01900,
-       0x00ffcf00,
-       0xb70421f4,
-       0xf00400b0,
-       0x07f101e7,
-       0x03f01d00,
-       0x000ed000,
-/* 0x071a: ih_no_fifo */
-       0xabe404bd,
-       0x0bf40100,
-       0x10d7f00d,
-       0x4001e7f1,
-/* 0x072b: ih_no_ctxsw */
-       0xe40421f4,
-       0xf40400ab,
-       0xe7f16c0b,
-       0xe3f00708,
-       0x6821f440,
-       0xf102ffb9,
-       0xf0040007,
-       0x0fd00203,
-       0xf104bd00,
-       0xf00704e7,
-       0x21f440e3,
-       0x02ffb968,
-       0x030007f1,
-       0xd00203f0,
-       0x04bd000f,
-       0x9450fec7,
-       0xf7f102ee,
-       0xf3f00700,
-       0x00efbb40,
-       0xf16821f4,
-       0xf0020007,
-       0x0fd00203,
-       0xf004bd00,
-       0x21f503f7,
-       0xb7f1037e,
-       0xbfb90100,
-       0x44e7f102,
-       0x40e3f001,
-/* 0x079b: ih_no_fwmthd */
-       0xf19d21f4,
-       0xbd0504b7,
-       0xb4abffb0,
-       0xf10f0bf4,
-       0xf0070007,
-       0x0bd00303,
-/* 0x07b3: ih_no_other */
-       0xf104bd00,
-       0xf0010007,
-       0x0ad00003,
-       0xfc04bd00,
-       0xfce0fcf0,
-       0xfcb0fcd0,
-       0xfc90fca0,
-       0x0088fe80,
-       0x32f480fc,
-/* 0x07d7: ctx_4170s */
-       0xf001f800,
-       0xffb910f5,
-       0x70e7f102,
-       0x40e3f041,
-       0xf89d21f4,
-/* 0x07e9: ctx_4170w */
-       0x70e7f100,
-       0x40e3f041,
-       0xb96821f4,
-       0xf4f002ff,
-       0xf01bf410,
-/* 0x07fe: ctx_redswitch */
-       0xe7f100f8,
-       0xe5f00200,
-       0x20e5f040,
-       0xf110e5f0,
-       0xf0850007,
-       0x0ed00103,
-       0xf004bd00,
-/* 0x081a: ctx_redswitch_delay */
-       0xf2b608f7,
-       0xfd1bf401,
-       0x0400e5f1,
-       0x0100e5f1,
-       0x850007f1,
-       0xd00103f0,
-       0x04bd000e,
-/* 0x0836: ctx_86c */
-       0x07f100f8,
-       0x03f01b00,
-       0x000fd002,
-       0xffb904bd,
-       0x14e7f102,
-       0x40e3f08a,
-       0xb99d21f4,
-       0xe7f102ff,
-       0xe3f0a86c,
-       0x9d21f441,
-/* 0x085e: ctx_mem */
-       0x07f100f8,
-       0x03f08400,
-       0x000fd002,
-/* 0x086a: ctx_mem_wait */
-       0xf7f104bd,
-       0xf3f08400,
-       0x00ffcf02,
-       0xf405fffd,
-       0x00f8f31b,
-/* 0x087c: ctx_load */
-       0x99f094bd,
-       0x0007f105,
-       0x0203f00f,
-       0xbd0009d0,
-       0x0ca7f004,
-       0xbdd021f4,
-       0x0007f1f4,
-       0x0203f089,
-       0xbd000fd0,
-       0x0007f104,
-       0x0203f0c1,
-       0xbd0002d0,
-       0x0007f104,
-       0x0203f083,
-       0xbd0002d0,
-       0x07f7f004,
-       0x085e21f5,
-       0xc00007f1,
-       0xd00203f0,
-       0x04bd0002,
-       0xf0000bfe,
-       0x24b61f2a,
-       0x0220b604,
-       0x99f094bd,
-       0x0007f108,
-       0x0203f00f,
-       0xbd0009d0,
-       0x0007f104,
-       0x0203f081,
-       0xbd0002d0,
-       0x0027f104,
-       0x0023f100,
-       0x0225f080,
-       0x880007f1,
-       0xd00203f0,
-       0x04bd0002,
-       0xf11017f0,
-       0xf0020027,
-       0x12fa0223,
-       0xbd03f805,
-       0x0899f094,
-       0x170007f1,
-       0xd00203f0,
-       0x04bd0009,
-       0xb6810198,
-       0x02981814,
-       0x0825b680,
-       0x800512fd,
-       0x94bd1601,
-       0xf10999f0,
-       0xf00f0007,
-       0x09d00203,
-       0xf104bd00,
-       0xf0810007,
-       0x01d00203,
-       0xf004bd00,
-       0x07f10127,
-       0x03f08800,
-       0x0002d002,
-       0x17f104bd,
-       0x13f00100,
-       0x0501fa06,
-       0x94bd03f8,
-       0xf10999f0,
-       0xf0170007,
-       0x09d00203,
-       0xbd04bd00,
-       0x0599f094,
-       0x170007f1,
-       0xd00203f0,
-       0x04bd0009,
-/* 0x099a: ctx_chan */
-       0x21f500f8,
-       0xa7f0087c,
-       0xd021f40c,
-       0xf505f7f0,
-       0xf8085e21,
-/* 0x09ad: ctx_mmio_exec */
-       0x41039800,
-       0x810007f1,
-       0xd00203f0,
-       0x04bd0003,
-/* 0x09be: ctx_mmio_loop */
-       0x34c434bd,
-       0x0f1bf4ff,
-       0x020057f1,
-       0xfa0653f0,
-       0x03f80535,
-/* 0x09d0: ctx_mmio_pull */
-       0x98804e98,
-       0x21f4814f,
-       0x0830b69d,
-       0xf40112b6,
-/* 0x09e2: ctx_mmio_done */
-       0x0398df1b,
-       0x0007f116,
-       0x0203f081,
-       0xbd0003d0,
-       0x40008004,
-       0x010017f1,
-       0xfa0613f0,
-       0x03f80601,
-/* 0x0a02: ctx_xfer */
-       0xe7f000f8,
-       0x0007f104,
-       0x0303f002,
-       0xbd000ed0,
-/* 0x0a11: ctx_xfer_idle */
-       0x00e7f104,
-       0x03e3f000,
-       0xf100eecf,
-       0xf42000e4,
-       0x11f4f21b,
-       0x0d02f406,
-/* 0x0a28: ctx_xfer_pre */
-       0xf510f7f0,
-       0xf4083621,
-/* 0x0a32: ctx_xfer_pre_load */
-       0xf7f01c11,
-       0xd721f502,
-       0xe921f507,
-       0xfe21f507,
-       0xf5f4bd07,
-       0xf507d721,
-/* 0x0a4b: ctx_xfer_exec */
-       0x98087c21,
-       0x24bd1601,
-       0x050007f1,
-       0xd00103f0,
-       0x04bd0002,
-       0xf1021fb9,
-       0xf0a500e7,
-       0x21f441e3,
-       0x01fcf09d,
-       0xb6022cf0,
-       0xf2fd0124,
-       0x02ffb905,
-       0xa504e7f1,
-       0xf441e3f0,
-       0x21f59d21,
-       0x24bd026a,
-       0x47fc07f1,
-       0xd00203f0,
-       0x04bd0002,
-       0xb6012cf0,
-       0x07f10320,
-       0x03f04afc,
-       0x0002d002,
-       0xacf004bd,
-       0x06a5f001,
-       0x9800b7f0,
-       0x0d98000c,
-       0x00e7f001,
-       0x016f21f5,
-       0xf508a7f0,
-       0xf5011021,
-       0xf4025e21,
-       0xa7f01301,
-       0xd021f40c,
-       0xf505f7f0,
-       0xf4085e21,
-/* 0x0ada: ctx_xfer_post */
-       0xf7f02e02,
-       0xd721f502,
-       0xf5f4bd07,
-       0xf5083621,
-       0xf5027f21,
-       0xbd07e921,
-       0xd721f5f4,
-       0x1011f407,
-       0xfd400198,
-       0x0bf40511,
-       0xad21f507,
-/* 0x0b05: ctx_xfer_no_post_mmio */
-/* 0x0b05: ctx_xfer_done */
-       0x0000f809,
-       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,
-};
diff --git a/drivers/gpu/drm/nouveau/core/engine/graph/fuc/hubnvf0.fuc b/drivers/gpu/drm/nouveau/core/engine/graph/fuc/hubnvf0.fuc
deleted file mode 100644 (file)
index ec42ed2..0000000
+++ /dev/null
@@ -1,40 +0,0 @@
-/*
- * Copyright 2013 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 <bskeggs@redhat.com>
- */
-
-#define CHIPSET GK110
-#include "macros.fuc"
-
-.section #nvf0_grhub_data
-#define INCLUDE_DATA
-#include "com.fuc"
-#include "hub.fuc"
-#undef INCLUDE_DATA
-
-.section #nvf0_grhub_code
-#define INCLUDE_CODE
-bra #init
-#include "com.fuc"
-#include "hub.fuc"
-.align 256
-#undef INCLUDE_CODE
diff --git a/drivers/gpu/drm/nouveau/core/engine/graph/fuc/hubnvf0.fuc.h b/drivers/gpu/drm/nouveau/core/engine/graph/fuc/hubnvf0.fuc.h
deleted file mode 100644 (file)
index a0af4b7..0000000
+++ /dev/null
@@ -1,1044 +0,0 @@
-uint32_t nvf0_grhub_data[] = {
-/* 0x0000: hub_mmio_list_head */
-       0x00000300,
-/* 0x0004: hub_mmio_list_tail */
-       0x00000304,
-/* 0x0008: gpc_count */
-       0x00000000,
-/* 0x000c: rop_count */
-       0x00000000,
-/* 0x0010: cmd_queue */
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-/* 0x0058: ctx_current */
-       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,
-/* 0x0100: chan_data */
-/* 0x0100: chan_mmio_count */
-       0x00000000,
-/* 0x0104: chan_mmio_address */
-       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,
-/* 0x0200: xfer_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,
-/* 0x0300: hub_mmio_list_base */
-       0x0417e91c,
-};
-
-uint32_t nvf0_grhub_code[] = {
-       0x039b0ef5,
-/* 0x0004: queue_put */
-       0x9800d898,
-       0x86f001d9,
-       0x0489b808,
-       0xf00c1bf4,
-       0x21f502f7,
-       0x00f8037e,
-/* 0x001c: queue_put_next */
-       0xb60798c4,
-       0x8dbb0384,
-       0x0880b600,
-       0x80008e80,
-       0x90b6018f,
-       0x0f94f001,
-       0xf801d980,
-/* 0x0039: queue_get */
-       0x0131f400,
-       0x9800d898,
-       0x89b801d9,
-       0x210bf404,
-       0xb60789c4,
-       0x9dbb0394,
-       0x0890b600,
-       0x98009e98,
-       0x80b6019f,
-       0x0f84f001,
-       0xf400d880,
-/* 0x0066: queue_get_done */
-       0x00f80132,
-/* 0x0068: nv_rd32 */
-       0xf002ecb9,
-       0x07f11fc9,
-       0x03f0ca00,
-       0x000cd001,
-/* 0x007a: nv_rd32_wait */
-       0xc7f104bd,
-       0xc3f0ca00,
-       0x00cccf01,
-       0xf41fccc8,
-       0xa7f0f31b,
-       0x1021f506,
-       0x00f7f101,
-       0x01f3f0cb,
-       0xf800ffcf,
-/* 0x009d: nv_wr32 */
-       0x0007f100,
-       0x0103f0cc,
-       0xbd000fd0,
-       0x02ecb904,
-       0xf01fc9f0,
-       0x07f11ec9,
-       0x03f0ca00,
-       0x000cd001,
-/* 0x00be: nv_wr32_wait */
-       0xc7f104bd,
-       0xc3f0ca00,
-       0x00cccf01,
-       0xf41fccc8,
-       0x00f8f31b,
-/* 0x00d0: wait_donez */
-       0x99f094bd,
-       0x0007f100,
-       0x0203f037,
-       0xbd0009d0,
-       0x0007f104,
-       0x0203f006,
-       0xbd000ad0,
-/* 0x00ed: wait_donez_ne */
-       0x0087f104,
-       0x0183f000,
-       0xff0088cf,
-       0x1bf4888a,
-       0xf094bdf3,
-       0x07f10099,
-       0x03f01700,
-       0x0009d002,
-       0x00f804bd,
-/* 0x0110: wait_doneo */
-       0x99f094bd,
-       0x0007f100,
-       0x0203f037,
-       0xbd0009d0,
-       0x0007f104,
-       0x0203f006,
-       0xbd000ad0,
-/* 0x012d: wait_doneo_e */
-       0x0087f104,
-       0x0183f000,
-       0xff0088cf,
-       0x0bf4888a,
-       0xf094bdf3,
-       0x07f10099,
-       0x03f01700,
-       0x0009d002,
-       0x00f804bd,
-/* 0x0150: mmctx_size */
-/* 0x0152: nv_mmctx_size_loop */
-       0xe89894bd,
-       0x1a85b600,
-       0xb60180b6,
-       0x98bb0284,
-       0x04e0b600,
-       0xf404efb8,
-       0x9fb9eb1b,
-/* 0x016f: mmctx_xfer */
-       0xbd00f802,
-       0x0199f094,
-       0x370007f1,
-       0xd00203f0,
-       0x04bd0009,
-       0xbbfd94bd,
-       0x120bf405,
-       0xc40007f1,
-       0xd00103f0,
-       0x04bd000b,
-/* 0x0197: mmctx_base_disabled */
-       0xfd0099f0,
-       0x0bf405ee,
-       0x0007f11e,
-       0x0103f0c6,
-       0xbd000ed0,
-       0x0007f104,
-       0x0103f0c7,
-       0xbd000fd0,
-       0x0199f004,
-/* 0x01b8: mmctx_multi_disabled */
-       0xb600abc8,
-       0xb9f010b4,
-       0x01aec80c,
-       0xfd11e4b6,
-       0x07f105be,
-       0x03f0c500,
-       0x000bd001,
-/* 0x01d6: mmctx_exec_loop */
-/* 0x01d6: mmctx_wait_free */
-       0xe7f104bd,
-       0xe3f0c500,
-       0x00eecf01,
-       0xf41fe4f0,
-       0xce98f30b,
-       0x05e9fd00,
-       0xc80007f1,
-       0xd00103f0,
-       0x04bd000e,
-       0xb804c0b6,
-       0x1bf404cd,
-       0x02abc8d8,
-/* 0x0207: mmctx_fini_wait */
-       0xf11f1bf4,
-       0xf0c500b7,
-       0xbbcf01b3,
-       0x1fb4f000,
-       0xf410b4b0,
-       0xa7f0f01b,
-       0xd021f405,
-/* 0x0223: mmctx_stop */
-       0xc82b0ef4,
-       0xb4b600ab,
-       0x0cb9f010,
-       0xf112b9f0,
-       0xf0c50007,
-       0x0bd00103,
-/* 0x023b: mmctx_stop_wait */
-       0xf104bd00,
-       0xf0c500b7,
-       0xbbcf01b3,
-       0x12bbc800,
-/* 0x024b: mmctx_done */
-       0xbdf31bf4,
-       0x0199f094,
-       0x170007f1,
-       0xd00203f0,
-       0x04bd0009,
-/* 0x025e: strand_wait */
-       0xa0f900f8,
-       0xf402a7f0,
-       0xa0fcd021,
-/* 0x026a: strand_pre */
-       0x97f000f8,
-       0xfc07f10c,
-       0x0203f04a,
-       0xbd0009d0,
-       0x5e21f504,
-/* 0x027f: strand_post */
-       0xf000f802,
-       0x07f10d97,
-       0x03f04afc,
-       0x0009d002,
-       0x21f504bd,
-       0x00f8025e,
-/* 0x0294: strand_set */
-       0xf10fc7f0,
-       0xf04ffc07,
-       0x0cd00203,
-       0xf004bd00,
-       0x07f10bc7,
-       0x03f04afc,
-       0x000cd002,
-       0x07f104bd,
-       0x03f04ffc,
-       0x000ed002,
-       0xc7f004bd,
-       0xfc07f10a,
-       0x0203f04a,
-       0xbd000cd0,
-       0x5e21f504,
-/* 0x02d3: strand_ctx_init */
-       0xbd00f802,
-       0x0399f094,
-       0x370007f1,
-       0xd00203f0,
-       0x04bd0009,
-       0x026a21f5,
-       0xf503e7f0,
-       0xbd029421,
-       0xfc07f1c4,
-       0x0203f047,
-       0xbd000cd0,
-       0x01c7f004,
-       0x4afc07f1,
-       0xd00203f0,
-       0x04bd000c,
-       0x025e21f5,
-       0xf1010c92,
-       0xf046fc07,
-       0x0cd00203,
-       0xf004bd00,
-       0x07f102c7,
-       0x03f04afc,
-       0x000cd002,
-       0x21f504bd,
-       0x21f5025e,
-       0x87f1027f,
-       0x83f04200,
-       0x0097f102,
-       0x0293f020,
-       0x950099cf,
-/* 0x034a: ctx_init_strand_loop */
-       0x8ed008fe,
-       0x408ed000,
-       0xb6808acf,
-       0xa0b606a5,
-       0x00eabb01,
-       0xb60480b6,
-       0x1bf40192,
-       0x08e4b6e8,
-       0xbdf2efbc,
-       0x0399f094,
-       0x170007f1,
-       0xd00203f0,
-       0x04bd0009,
-/* 0x037e: error */
-       0x07f100f8,
-       0x03f00500,
-       0x000fd002,
-       0xf7f004bd,
-       0x0007f101,
-       0x0303f007,
-       0xbd000fd0,
-/* 0x039b: init */
-       0xbd00f804,
-       0x0007fe04,
-       0x420017f1,
-       0xcf0013f0,
-       0x11e70011,
-       0x14b60109,
-       0x0014fe08,
-       0xf10227f0,
-       0xf0120007,
-       0x02d00003,
-       0xf104bd00,
-       0xfe06c817,
-       0x24bd0010,
-       0x070007f1,
-       0xd00003f0,
-       0x04bd0002,
-       0x200327f1,
-       0x010007f1,
-       0xd00103f0,
-       0x04bd0002,
-       0x200427f1,
-       0x010407f1,
-       0xd00103f0,
-       0x04bd0002,
-       0x200b27f1,
-       0x010807f1,
-       0xd00103f0,
-       0x04bd0002,
-       0x200c27f1,
-       0x011c07f1,
-       0xd00103f0,
-       0x04bd0002,
-       0xf1010392,
-       0xf0090007,
-       0x03d00303,
-       0xf104bd00,
-       0xf0870427,
-       0x07f10023,
-       0x03f00400,
-       0x0002d000,
-       0x27f004bd,
-       0x0007f104,
-       0x0003f003,
-       0xbd0002d0,
-       0x1031f404,
-       0x9604e7f1,
-       0xf440e3f0,
-       0xfeb96821,
-       0x90f1c702,
-       0xf0030180,
-       0x0f801ff4,
-       0x0117f002,
-       0xb6041fbb,
-       0x07f10112,
-       0x03f00300,
-       0x0001d001,
-       0x07f104bd,
-       0x03f00400,
-       0x0001d001,
-       0x17f104bd,
-       0xf7f00100,
-       0xd721f502,
-       0xe921f507,
-       0x10f7f007,
-       0x083621f5,
-       0x98000e98,
-       0x21f5010f,
-       0x14950150,
-       0x0007f108,
-       0x0103f0c0,
-       0xbd0004d0,
-       0x0007f104,
-       0x0103f0c1,
-       0xbd0004d0,
-       0x0030b704,
-       0x001fbb13,
-       0xf102f5b6,
-       0xf0d30007,
-       0x0fd00103,
-       0xb604bd00,
-       0x10b60815,
-       0x0814b601,
-       0xf5021fb9,
-       0xbb02d321,
-       0x0398001f,
-       0x0047f102,
-       0x5043f020,
-/* 0x04f4: init_gpc */
-       0x08044ea0,
-       0xf4021fb9,
-       0x4ea09d21,
-       0xf4bd010c,
-       0xa09d21f4,
-       0xf401044e,
-       0x4ea09d21,
-       0xf7f00100,
-       0x9d21f402,
-       0x08004ea0,
-/* 0x051c: init_gpc_wait */
-       0xc86821f4,
-       0x0bf41fff,
-       0x044ea0fa,
-       0x6821f408,
-       0xb7001fbb,
-       0xb6800040,
-       0x1bf40132,
-       0x00f7f0be,
-       0x083621f5,
-       0xf500f7f0,
-       0xf107d721,
-       0xf0010007,
-       0x01d00203,
-       0xbd04bd00,
-       0x1f19f014,
-       0x300007f1,
-       0xd00203f0,
-       0x04bd0001,
-/* 0x0564: main */
-       0xf40031f4,
-       0xd7f00028,
-       0x3921f410,
-       0xb1f401f4,
-       0xf54001e4,
-       0xbd00e91b,
-       0x0499f094,
-       0x370007f1,
-       0xd00203f0,
-       0x04bd0009,
-       0xc00017f1,
-       0xcf0213f0,
-       0x27f10011,
-       0x23f0c100,
-       0x0022cf02,
-       0xf51f13c8,
-       0xc800890b,
-       0x0bf41f23,
-       0xb920f962,
-       0x94bd0212,
-       0xf10799f0,
-       0xf0370007,
-       0x09d00203,
-       0xf404bd00,
-       0x31f40132,
-       0x0221f502,
-       0xf094bd0a,
-       0x07f10799,
-       0x03f01700,
-       0x0009d002,
-       0x20fc04bd,
-       0x99f094bd,
-       0x0007f106,
-       0x0203f037,
-       0xbd0009d0,
-       0x0131f404,
-       0x0a0221f5,
-       0x99f094bd,
-       0x0007f106,
-       0x0203f017,
-       0xbd0009d0,
-       0x330ef404,
-/* 0x060c: chsw_prev_no_next */
-       0x12b920f9,
-       0x0132f402,
-       0xf50232f4,
-       0xfc0a0221,
-       0x0007f120,
-       0x0203f0c0,
-       0xbd0002d0,
-       0x130ef404,
-/* 0x062c: chsw_no_prev */
-       0xf41f23c8,
-       0x31f40d0b,
-       0x0232f401,
-       0x0a0221f5,
-/* 0x063c: chsw_done */
-       0xf10127f0,
-       0xf0c30007,
-       0x02d00203,
-       0xbd04bd00,
-       0x0499f094,
-       0x170007f1,
-       0xd00203f0,
-       0x04bd0009,
-       0xff080ef5,
-/* 0x0660: main_not_ctx_switch */
-       0xf401e4b0,
-       0xf2b90d1b,
-       0x9a21f502,
-       0x460ef409,
-/* 0x0670: main_not_ctx_chan */
-       0xf402e4b0,
-       0x94bd321b,
-       0xf10799f0,
-       0xf0370007,
-       0x09d00203,
-       0xf404bd00,
-       0x32f40132,
-       0x0221f502,
-       0xf094bd0a,
-       0x07f10799,
-       0x03f01700,
-       0x0009d002,
-       0x0ef404bd,
-/* 0x06a5: main_not_ctx_save */
-       0x10ef9411,
-       0xf501f5f0,
-       0xf5037e21,
-/* 0x06b3: main_done */
-       0xbdfeb50e,
-       0x1f29f024,
-       0x300007f1,
-       0xd00203f0,
-       0x04bd0002,
-       0xfea00ef5,
-/* 0x06c8: ih */
-       0x88fe80f9,
-       0xf980f901,
-       0xf9a0f990,
-       0xf9d0f9b0,
-       0xbdf0f9e0,
-       0x00a7f104,
-       0x00a3f002,
-       0xc400aacf,
-       0x0bf404ab,
-       0x10d7f030,
-       0x1a00e7f1,
-       0xcf00e3f0,
-       0xf7f100ee,
-       0xf3f01900,
-       0x00ffcf00,
-       0xb70421f4,
-       0xf00400b0,
-       0x07f101e7,
-       0x03f01d00,
-       0x000ed000,
-/* 0x071a: ih_no_fifo */
-       0xabe404bd,
-       0x0bf40100,
-       0x10d7f00d,
-       0x4001e7f1,
-/* 0x072b: ih_no_ctxsw */
-       0xe40421f4,
-       0xf40400ab,
-       0xe7f16c0b,
-       0xe3f00708,
-       0x6821f440,
-       0xf102ffb9,
-       0xf0040007,
-       0x0fd00203,
-       0xf104bd00,
-       0xf00704e7,
-       0x21f440e3,
-       0x02ffb968,
-       0x030007f1,
-       0xd00203f0,
-       0x04bd000f,
-       0x9450fec7,
-       0xf7f102ee,
-       0xf3f00700,
-       0x00efbb40,
-       0xf16821f4,
-       0xf0020007,
-       0x0fd00203,
-       0xf004bd00,
-       0x21f503f7,
-       0xb7f1037e,
-       0xbfb90100,
-       0x44e7f102,
-       0x40e3f001,
-/* 0x079b: ih_no_fwmthd */
-       0xf19d21f4,
-       0xbd0504b7,
-       0xb4abffb0,
-       0xf10f0bf4,
-       0xf0070007,
-       0x0bd00303,
-/* 0x07b3: ih_no_other */
-       0xf104bd00,
-       0xf0010007,
-       0x0ad00003,
-       0xfc04bd00,
-       0xfce0fcf0,
-       0xfcb0fcd0,
-       0xfc90fca0,
-       0x0088fe80,
-       0x32f480fc,
-/* 0x07d7: ctx_4170s */
-       0xf001f800,
-       0xffb910f5,
-       0x70e7f102,
-       0x40e3f041,
-       0xf89d21f4,
-/* 0x07e9: ctx_4170w */
-       0x70e7f100,
-       0x40e3f041,
-       0xb96821f4,
-       0xf4f002ff,
-       0xf01bf410,
-/* 0x07fe: ctx_redswitch */
-       0xe7f100f8,
-       0xe5f00200,
-       0x20e5f040,
-       0xf110e5f0,
-       0xf0850007,
-       0x0ed00103,
-       0xf004bd00,
-/* 0x081a: ctx_redswitch_delay */
-       0xf2b608f7,
-       0xfd1bf401,
-       0x0400e5f1,
-       0x0100e5f1,
-       0x850007f1,
-       0xd00103f0,
-       0x04bd000e,
-/* 0x0836: ctx_86c */
-       0x07f100f8,
-       0x03f02300,
-       0x000fd002,
-       0xffb904bd,
-       0x14e7f102,
-       0x40e3f08a,
-       0xb99d21f4,
-       0xe7f102ff,
-       0xe3f0a88c,
-       0x9d21f441,
-/* 0x085e: ctx_mem */
-       0x07f100f8,
-       0x03f08400,
-       0x000fd002,
-/* 0x086a: ctx_mem_wait */
-       0xf7f104bd,
-       0xf3f08400,
-       0x00ffcf02,
-       0xf405fffd,
-       0x00f8f31b,
-/* 0x087c: ctx_load */
-       0x99f094bd,
-       0x0007f105,
-       0x0203f037,
-       0xbd0009d0,
-       0x0ca7f004,
-       0xbdd021f4,
-       0x0007f1f4,
-       0x0203f089,
-       0xbd000fd0,
-       0x0007f104,
-       0x0203f0c1,
-       0xbd0002d0,
-       0x0007f104,
-       0x0203f083,
-       0xbd0002d0,
-       0x07f7f004,
-       0x085e21f5,
-       0xc00007f1,
-       0xd00203f0,
-       0x04bd0002,
-       0xf0000bfe,
-       0x24b61f2a,
-       0x0220b604,
-       0x99f094bd,
-       0x0007f108,
-       0x0203f037,
-       0xbd0009d0,
-       0x0007f104,
-       0x0203f081,
-       0xbd0002d0,
-       0x0027f104,
-       0x0023f100,
-       0x0225f080,
-       0x880007f1,
-       0xd00203f0,
-       0x04bd0002,
-       0xf11017f0,
-       0xf0020027,
-       0x12fa0223,
-       0xbd03f805,
-       0x0899f094,
-       0x170007f1,
-       0xd00203f0,
-       0x04bd0009,
-       0xb6810198,
-       0x02981814,
-       0x0825b680,
-       0x800512fd,
-       0x94bd1601,
-       0xf10999f0,
-       0xf0370007,
-       0x09d00203,
-       0xf104bd00,
-       0xf0810007,
-       0x01d00203,
-       0xf004bd00,
-       0x07f10127,
-       0x03f08800,
-       0x0002d002,
-       0x17f104bd,
-       0x13f00100,
-       0x0501fa06,
-       0x94bd03f8,
-       0xf10999f0,
-       0xf0170007,
-       0x09d00203,
-       0xbd04bd00,
-       0x0599f094,
-       0x170007f1,
-       0xd00203f0,
-       0x04bd0009,
-/* 0x099a: ctx_chan */
-       0x21f500f8,
-       0xa7f0087c,
-       0xd021f40c,
-       0xf505f7f0,
-       0xf8085e21,
-/* 0x09ad: ctx_mmio_exec */
-       0x41039800,
-       0x810007f1,
-       0xd00203f0,
-       0x04bd0003,
-/* 0x09be: ctx_mmio_loop */
-       0x34c434bd,
-       0x0f1bf4ff,
-       0x020057f1,
-       0xfa0653f0,
-       0x03f80535,
-/* 0x09d0: ctx_mmio_pull */
-       0x98804e98,
-       0x21f4814f,
-       0x0830b69d,
-       0xf40112b6,
-/* 0x09e2: ctx_mmio_done */
-       0x0398df1b,
-       0x0007f116,
-       0x0203f081,
-       0xbd0003d0,
-       0x40008004,
-       0x010017f1,
-       0xfa0613f0,
-       0x03f80601,
-/* 0x0a02: ctx_xfer */
-       0xe7f000f8,
-       0x0007f104,
-       0x0303f002,
-       0xbd000ed0,
-/* 0x0a11: ctx_xfer_idle */
-       0x00e7f104,
-       0x03e3f000,
-       0xf100eecf,
-       0xf42000e4,
-       0x11f4f21b,
-       0x0d02f406,
-/* 0x0a28: ctx_xfer_pre */
-       0xf510f7f0,
-       0xf4083621,
-/* 0x0a32: ctx_xfer_pre_load */
-       0xf7f01c11,
-       0xd721f502,
-       0xe921f507,
-       0xfe21f507,
-       0xf5f4bd07,
-       0xf507d721,
-/* 0x0a4b: ctx_xfer_exec */
-       0x98087c21,
-       0x24bd1601,
-       0x050007f1,
-       0xd00103f0,
-       0x04bd0002,
-       0xf1021fb9,
-       0xf0a500e7,
-       0x21f441e3,
-       0x01fcf09d,
-       0xb6022cf0,
-       0xf2fd0124,
-       0x02ffb905,
-       0xa504e7f1,
-       0xf441e3f0,
-       0x21f59d21,
-       0x24bd026a,
-       0x47fc07f1,
-       0xd00203f0,
-       0x04bd0002,
-       0xb6012cf0,
-       0x07f10320,
-       0x03f04afc,
-       0x0002d002,
-       0xacf004bd,
-       0x06a5f001,
-       0x9800b7f0,
-       0x0d98000c,
-       0x00e7f001,
-       0x016f21f5,
-       0xf508a7f0,
-       0xf5011021,
-       0xf4025e21,
-       0xa7f01301,
-       0xd021f40c,
-       0xf505f7f0,
-       0xf4085e21,
-/* 0x0ada: ctx_xfer_post */
-       0xf7f02e02,
-       0xd721f502,
-       0xf5f4bd07,
-       0xf5083621,
-       0xf5027f21,
-       0xbd07e921,
-       0xd721f5f4,
-       0x1011f407,
-       0xfd400198,
-       0x0bf40511,
-       0xad21f507,
-/* 0x0b05: ctx_xfer_no_post_mmio */
-/* 0x0b05: ctx_xfer_done */
-       0x0000f809,
-       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,
-};
diff --git a/drivers/gpu/drm/nouveau/core/engine/graph/fuc/macros.fuc b/drivers/gpu/drm/nouveau/core/engine/graph/fuc/macros.fuc
deleted file mode 100644 (file)
index 2a0b0f8..0000000
+++ /dev/null
@@ -1,229 +0,0 @@
-/*
- * Copyright 2013 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 <bskeggs@redhat.com>
- */
-
-#include "os.h"
-
-#define GF100 0xc0
-#define GF117 0xd7
-#define GK100 0xe0
-#define GK110 0xf0
-#define GK208 0x108
-
-#define NV_PGRAPH_TRAPPED_ADDR                                         0x400704
-#define NV_PGRAPH_TRAPPED_DATA_LO                                      0x400708
-#define NV_PGRAPH_TRAPPED_DATA_HI                                      0x40070c
-
-#define NV_PGRAPH_FE_OBJECT_TABLE(n)                        ((n) * 4 + 0x400700)
-
-#define NV_PGRAPH_FECS_INTR_ACK                                        0x409004
-#define NV_PGRAPH_FECS_INTR                                            0x409008
-#define NV_PGRAPH_FECS_INTR_FWMTHD                                   0x00000400
-#define NV_PGRAPH_FECS_INTR_CHSW                                     0x00000100
-#define NV_PGRAPH_FECS_INTR_FIFO                                     0x00000004
-#define NV_PGRAPH_FECS_INTR_MODE                                       0x40900c
-#define NV_PGRAPH_FECS_INTR_MODE_FIFO                                0x00000004
-#define NV_PGRAPH_FECS_INTR_MODE_FIFO_LEVEL                          0x00000004
-#define NV_PGRAPH_FECS_INTR_MODE_FIFO_EDGE                           0x00000000
-#define NV_PGRAPH_FECS_INTR_EN_SET                                     0x409010
-#define NV_PGRAPH_FECS_INTR_EN_SET_FIFO                              0x00000004
-#define NV_PGRAPH_FECS_INTR_ROUTE                                      0x40901c
-#define NV_PGRAPH_FECS_ACCESS                                          0x409048
-#define NV_PGRAPH_FECS_ACCESS_FIFO                                   0x00000002
-#define NV_PGRAPH_FECS_FIFO_DATA                                       0x409064
-#define NV_PGRAPH_FECS_FIFO_CMD                                        0x409068
-#define NV_PGRAPH_FECS_FIFO_ACK                                        0x409074
-#define NV_PGRAPH_FECS_CAPS                                            0x409108
-#define NV_PGRAPH_FECS_SIGNAL                                          0x409400
-#define NV_PGRAPH_FECS_IROUTE                                          0x409404
-#define NV_PGRAPH_FECS_BAR_MASK0                                       0x40940c
-#define NV_PGRAPH_FECS_BAR_MASK1                                       0x409410
-#define NV_PGRAPH_FECS_BAR                                             0x409414
-#define NV_PGRAPH_FECS_BAR_SET                                         0x409418
-#define NV_PGRAPH_FECS_RED_SWITCH                                      0x409614
-#define NV_PGRAPH_FECS_RED_SWITCH_ENABLE_ROP                         0x00000400
-#define NV_PGRAPH_FECS_RED_SWITCH_ENABLE_GPC                         0x00000200
-#define NV_PGRAPH_FECS_RED_SWITCH_ENABLE_MAIN                        0x00000100
-#define NV_PGRAPH_FECS_RED_SWITCH_POWER_ROP                          0x00000040
-#define NV_PGRAPH_FECS_RED_SWITCH_POWER_GPC                          0x00000020
-#define NV_PGRAPH_FECS_RED_SWITCH_POWER_MAIN                         0x00000010
-#define NV_PGRAPH_FECS_RED_SWITCH_PAUSE_GPC                          0x00000002
-#define NV_PGRAPH_FECS_RED_SWITCH_PAUSE_MAIN                         0x00000001
-#define NV_PGRAPH_FECS_MMCTX_SAVE_SWBASE                               0x409700
-#define NV_PGRAPH_FECS_MMCTX_LOAD_SWBASE                               0x409704
-#define NV_PGRAPH_FECS_MMCTX_LOAD_COUNT                                0x40974c
-#define NV_PGRAPH_FECS_MMCTX_SAVE_SWBASE                               0x409700
-#define NV_PGRAPH_FECS_MMCTX_LOAD_SWBASE                               0x409704
-#define NV_PGRAPH_FECS_MMCTX_BASE                                      0x409710
-#define NV_PGRAPH_FECS_MMCTX_CTRL                                      0x409714
-#define NV_PGRAPH_FECS_MMCTX_MULTI_STRIDE                              0x409718
-#define NV_PGRAPH_FECS_MMCTX_MULTI_MASK                                0x40971c
-#define NV_PGRAPH_FECS_MMCTX_QUEUE                                     0x409720
-#define NV_PGRAPH_FECS_MMIO_CTRL                                       0x409728
-#define NV_PGRAPH_FECS_MMIO_RDVAL                                      0x40972c
-#define NV_PGRAPH_FECS_MMIO_WRVAL                                      0x409730
-#define NV_PGRAPH_FECS_MMCTX_LOAD_COUNT                                0x40974c
-#if CHIPSET < GK110
-#define NV_PGRAPH_FECS_CC_SCRATCH_VAL(n)                    ((n) * 4 + 0x409800)
-#define NV_PGRAPH_FECS_CC_SCRATCH_SET(n)                    ((n) * 4 + 0x409820)
-#define NV_PGRAPH_FECS_CC_SCRATCH_CLR(n)                    ((n) * 4 + 0x409840)
-#define NV_PGRAPH_FECS_UNK86C                                          0x40986c
-#else
-#define NV_PGRAPH_FECS_CC_SCRATCH_VAL(n)                    ((n) * 4 + 0x409800)
-#define NV_PGRAPH_FECS_CC_SCRATCH_CLR(n)                    ((n) * 4 + 0x409840)
-#define NV_PGRAPH_FECS_UNK86C                                          0x40988c
-#define NV_PGRAPH_FECS_CC_SCRATCH_SET(n)                    ((n) * 4 + 0x4098c0)
-#endif
-#define NV_PGRAPH_FECS_STRANDS_CNT                                     0x409880
-#define NV_PGRAPH_FECS_STRAND_SAVE_SWBASE                              0x409908
-#define NV_PGRAPH_FECS_STRAND_LOAD_SWBASE                              0x40990c
-#define NV_PGRAPH_FECS_STRAND_WORDS                                    0x409910
-#define NV_PGRAPH_FECS_STRAND_DATA                                     0x409918
-#define NV_PGRAPH_FECS_STRAND_SELECT                                   0x40991c
-#define NV_PGRAPH_FECS_STRAND_CMD                                      0x409928
-#define NV_PGRAPH_FECS_STRAND_CMD_SEEK                               0x00000001
-#define NV_PGRAPH_FECS_STRAND_CMD_GET_INFO                           0x00000002
-#define NV_PGRAPH_FECS_STRAND_CMD_SAVE                               0x00000003
-#define NV_PGRAPH_FECS_STRAND_CMD_LOAD                               0x00000004
-#define NV_PGRAPH_FECS_STRAND_CMD_ACTIVATE_FILTER                    0x0000000a
-#define NV_PGRAPH_FECS_STRAND_CMD_DEACTIVATE_FILTER                  0x0000000b
-#define NV_PGRAPH_FECS_STRAND_CMD_ENABLE                             0x0000000c
-#define NV_PGRAPH_FECS_STRAND_CMD_DISABLE                            0x0000000d
-#define NV_PGRAPH_FECS_STRAND_FILTER                                   0x40993c
-#define NV_PGRAPH_FECS_MEM_BASE                                        0x409a04
-#define NV_PGRAPH_FECS_MEM_CHAN                                        0x409a0c
-#define NV_PGRAPH_FECS_MEM_CMD                                         0x409a10
-#define NV_PGRAPH_FECS_MEM_CMD_LOAD_CHAN                             0x00000007
-#define NV_PGRAPH_FECS_MEM_TARGET                                      0x409a20
-#define NV_PGRAPH_FECS_MEM_TARGET_UNK31                              0x80000000
-#define NV_PGRAPH_FECS_MEM_TARGET_AS                                 0x0000001f
-#define NV_PGRAPH_FECS_MEM_TARGET_AS_VM                              0x00000001
-#define NV_PGRAPH_FECS_MEM_TARGET_AS_VRAM                            0x00000002
-#define NV_PGRAPH_FECS_CHAN_ADDR                                       0x409b00
-#define NV_PGRAPH_FECS_CHAN_NEXT                                       0x409b04
-#define NV_PGRAPH_FECS_CHSW                                            0x409b0c
-#define NV_PGRAPH_FECS_CHSW_ACK                                      0x00000001
-#define NV_PGRAPH_FECS_INTR_UP_SET                                     0x409c1c
-#define NV_PGRAPH_FECS_INTR_UP_EN                                      0x409c24
-
-#define NV_PGRAPH_GPCX_GPCCS_INTR_ACK                                  0x41a004
-#define NV_PGRAPH_GPCX_GPCCS_INTR                                      0x41a008
-#define NV_PGRAPH_GPCX_GPCCS_INTR_FIFO                               0x00000004
-#define NV_PGRAPH_GPCX_GPCCS_INTR_EN_SET                               0x41a010
-#define NV_PGRAPH_GPCX_GPCCS_INTR_EN_SET_FIFO                        0x00000004
-#define NV_PGRAPH_GPCX_GPCCS_INTR_ROUTE                                0x41a01c
-#define NV_PGRAPH_GPCX_GPCCS_ACCESS                                    0x41a048
-#define NV_PGRAPH_GPCX_GPCCS_ACCESS_FIFO                             0x00000002
-#define NV_PGRAPH_GPCX_GPCCS_FIFO_DATA                                 0x41a064
-#define NV_PGRAPH_GPCX_GPCCS_FIFO_CMD                                  0x41a068
-#define NV_PGRAPH_GPCX_GPCCS_FIFO_ACK                                  0x41a074
-#define NV_PGRAPH_GPCX_GPCCS_UNITS                                     0x41a608
-#define NV_PGRAPH_GPCX_GPCCS_CAPS                                      0x41a108
-#define NV_PGRAPH_GPCX_GPCCS_RED_SWITCH                                0x41a614
-#define NV_PGRAPH_GPCX_GPCCS_RED_SWITCH_UNK11                        0x00000800
-#define NV_PGRAPH_GPCX_GPCCS_RED_SWITCH_ENABLE                       0x00000200
-#define NV_PGRAPH_GPCX_GPCCS_RED_SWITCH_POWER                        0x00000020
-#define NV_PGRAPH_GPCX_GPCCS_RED_SWITCH_PAUSE                        0x00000002
-#define NV_PGRAPH_GPCX_GPCCS_MYINDEX                                   0x41a618
-#define NV_PGRAPH_GPCX_GPCCS_MMCTX_SAVE_SWBASE                         0x41a700
-#define NV_PGRAPH_GPCX_GPCCS_MMCTX_LOAD_SWBASE                         0x41a704
-#define NV_PGRAPH_GPCX_GPCCS_MMCTX_LOAD_COUNT                          0x41a74c
-#if CHIPSET < GK110
-#define NV_PGRAPH_GPCX_GPCCS_CC_SCRATCH_VAL(n)              ((n) * 4 + 0x41a800)
-#define NV_PGRAPH_GPCX_GPCCS_CC_SCRATCH_SET(n)              ((n) * 4 + 0x41a820)
-#define NV_PGRAPH_GPCX_GPCCS_CC_SCRATCH_CLR(n)              ((n) * 4 + 0x41a840)
-#define NV_PGRAPH_GPCX_GPCCS_UNK86C                                    0x41a86c
-#else
-#define NV_PGRAPH_GPCX_GPCCS_CC_SCRATCH_VAL(n)              ((n) * 4 + 0x41a800)
-#define NV_PGRAPH_GPCX_GPCCS_CC_SCRATCH_CLR(n)              ((n) * 4 + 0x41a840)
-#define NV_PGRAPH_GPCX_GPCCS_UNK86C                                    0x41a88c
-#define NV_PGRAPH_GPCX_GPCCS_CC_SCRATCH_SET(n)              ((n) * 4 + 0x41a8c0)
-#endif
-#define NV_PGRAPH_GPCX_GPCCS_STRAND_SELECT                             0x41a91c
-#define NV_PGRAPH_GPCX_GPCCS_STRAND_CMD                                0x41a928
-#define NV_PGRAPH_GPCX_GPCCS_STRAND_CMD_SAVE                         0x00000003
-#define NV_PGRAPH_GPCX_GPCCS_STRAND_CMD_LOAD                         0x00000004
-#define NV_PGRAPH_GPCX_GPCCS_MEM_BASE                                  0x41aa04
-
-#define mmctx_data(r,c) .b32 (((c - 1) << 26) | r)
-#define queue_init      .skip 72 // (2 * 4) + ((8 * 4) * 2)
-
-#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
-
-#if CHIPSET < GK208
-#define imm32(reg,val) /*
-*/     movw reg  ((val) & 0x0000ffff) /*
-*/     sethi reg ((val) & 0xffff0000)
-#else
-#define imm32(reg,val) /*
-*/     mov reg (val)
-#endif
-
-#define nv_mkio(rv,r,i) /*
-*/     imm32(rv, (((r) & 0xffc) << 6) | ((i) << 2))
-
-#define hash #
-#define fn(a) a
-#if CHIPSET < GK208
-#define call(a) call fn(hash)a
-#else
-#define call(a) lcall fn(hash)a
-#endif
-
-#define nv_iord(rv,r,i) /*
-*/     nv_mkio(rv,r,i) /*
-*/     iord rv I[rv]
-
-#define nv_iowr(r,i,rv) /*
-*/     nv_mkio($r0,r,i) /*
-*/     iowr I[$r0] rv /*
-*/     clear b32 $r0
-
-#define nv_rd32(reg,addr) /*
-*/     imm32($r14, addr) /*
-*/     call(nv_rd32) /*
-*/     mov b32 reg $r15
-
-#define nv_wr32(addr,reg) /*
-*/     mov b32 $r15 reg /*
-*/     imm32($r14, addr) /*
-*/     call(nv_wr32)
-
-#define trace_set(bit) /*
-*/     clear b32 $r9 /*
-*/     bset $r9 bit /*
-*/     nv_iowr(NV_PGRAPH_FECS_CC_SCRATCH_SET(7), 0, $r9)
-
-#define trace_clr(bit) /*
-*/     clear b32 $r9 /*
-*/     bset $r9 bit /*
-*/     nv_iowr(NV_PGRAPH_FECS_CC_SCRATCH_CLR(7), 0, $r9)
diff --git a/drivers/gpu/drm/nouveau/core/engine/graph/fuc/os.h b/drivers/gpu/drm/nouveau/core/engine/graph/fuc/os.h
deleted file mode 100644 (file)
index 1718ae4..0000000
+++ /dev/null
@@ -1,8 +0,0 @@
-#ifndef __NVKM_GRAPH_OS_H__
-#define __NVKM_GRAPH_OS_H__
-
-#define E_BAD_COMMAND  0x00000001
-#define E_CMD_OVERFLOW 0x00000002
-#define E_BAD_FWMTHD   0x00000003
-
-#endif
diff --git a/drivers/gpu/drm/nouveau/core/engine/graph/gk110b.c b/drivers/gpu/drm/nouveau/core/engine/graph/gk110b.c
deleted file mode 100644 (file)
index d07b19d..0000000
+++ /dev/null
@@ -1,117 +0,0 @@
-/*
- * Copyright 2013 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 <bskeggs@redhat.com>
- */
-
-#include "nvc0.h"
-#include "ctxnvc0.h"
-
-/*******************************************************************************
- * PGRAPH register lists
- ******************************************************************************/
-
-static const struct nvc0_graph_init
-gk110b_graph_init_l1c_0[] = {
-       { 0x419c98,   1, 0x04, 0x00000000 },
-       { 0x419ca8,   1, 0x04, 0x00000000 },
-       { 0x419cb0,   1, 0x04, 0x09000000 },
-       { 0x419cb4,   1, 0x04, 0x00000000 },
-       { 0x419cb8,   1, 0x04, 0x00b08bea },
-       { 0x419c84,   1, 0x04, 0x00010384 },
-       { 0x419cbc,   1, 0x04, 0x281b3646 },
-       { 0x419cc0,   2, 0x04, 0x00000000 },
-       { 0x419c80,   1, 0x04, 0x00020230 },
-       { 0x419ccc,   2, 0x04, 0x00000000 },
-       {}
-};
-
-static const struct nvc0_graph_init
-gk110b_graph_init_sm_0[] = {
-       { 0x419e00,   1, 0x04, 0x00000080 },
-       { 0x419ea0,   1, 0x04, 0x00000000 },
-       { 0x419ee4,   1, 0x04, 0x00000000 },
-       { 0x419ea4,   1, 0x04, 0x00000100 },
-       { 0x419ea8,   1, 0x04, 0x00000000 },
-       { 0x419eb4,   1, 0x04, 0x00000000 },
-       { 0x419ebc,   2, 0x04, 0x00000000 },
-       { 0x419edc,   1, 0x04, 0x00000000 },
-       { 0x419f00,   1, 0x04, 0x00000000 },
-       { 0x419ed0,   1, 0x04, 0x00002616 },
-       { 0x419f74,   1, 0x04, 0x00015555 },
-       { 0x419f80,   4, 0x04, 0x00000000 },
-       {}
-};
-
-static const struct nvc0_graph_pack
-gk110b_graph_pack_mmio[] = {
-       { nve4_graph_init_main_0 },
-       { nvf0_graph_init_fe_0 },
-       { nvc0_graph_init_pri_0 },
-       { nvc0_graph_init_rstr2d_0 },
-       { nvd9_graph_init_pd_0 },
-       { nvf0_graph_init_ds_0 },
-       { nvc0_graph_init_scc_0 },
-       { nvf0_graph_init_sked_0 },
-       { nvf0_graph_init_cwd_0 },
-       { nvd9_graph_init_prop_0 },
-       { nvc1_graph_init_gpc_unk_0 },
-       { nvc0_graph_init_setup_0 },
-       { nvc0_graph_init_crstr_0 },
-       { nvc1_graph_init_setup_1 },
-       { nvc0_graph_init_zcull_0 },
-       { nvd9_graph_init_gpm_0 },
-       { nvf0_graph_init_gpc_unk_1 },
-       { nvc0_graph_init_gcc_0 },
-       { nve4_graph_init_tpccs_0 },
-       { nvf0_graph_init_tex_0 },
-       { nve4_graph_init_pe_0 },
-       { gk110b_graph_init_l1c_0 },
-       { nvc0_graph_init_mpc_0 },
-       { gk110b_graph_init_sm_0 },
-       { nvd7_graph_init_pes_0 },
-       { nvd7_graph_init_wwdx_0 },
-       { nvd7_graph_init_cbm_0 },
-       { nve4_graph_init_be_0 },
-       { nvc0_graph_init_fe_1 },
-       {}
-};
-
-/*******************************************************************************
- * PGRAPH engine/subdev functions
- ******************************************************************************/
-
-struct nouveau_oclass *
-gk110b_graph_oclass = &(struct nvc0_graph_oclass) {
-       .base.handle = NV_ENGINE(GR, 0xf1),
-       .base.ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nvc0_graph_ctor,
-               .dtor = nvc0_graph_dtor,
-               .init = nve4_graph_init,
-               .fini = nvf0_graph_fini,
-       },
-       .cclass = &gk110b_grctx_oclass,
-       .sclass =  nvf0_graph_sclass,
-       .mmio = gk110b_graph_pack_mmio,
-       .fecs.ucode = &nvf0_graph_fecs_ucode,
-       .gpccs.ucode = &nvf0_graph_gpccs_ucode,
-       .ppc_nr = 2,
-}.base;
diff --git a/drivers/gpu/drm/nouveau/core/engine/graph/gk20a.c b/drivers/gpu/drm/nouveau/core/engine/graph/gk20a.c
deleted file mode 100644 (file)
index 7d0abe9..0000000
+++ /dev/null
@@ -1,48 +0,0 @@
-/*
- * Copyright (c) 2014, NVIDIA CORPORATION. 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 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 "nvc0.h"
-#include "ctxnvc0.h"
-
-static struct nouveau_oclass
-gk20a_graph_sclass[] = {
-       { 0x902d, &nouveau_object_ofuncs },
-       { 0xa040, &nouveau_object_ofuncs },
-       { KEPLER_C, &nvc0_fermi_ofuncs, nvc0_graph_9097_omthds },
-       { KEPLER_COMPUTE_A, &nouveau_object_ofuncs, nvc0_graph_90c0_omthds },
-       {}
-};
-
-struct nouveau_oclass *
-gk20a_graph_oclass = &(struct nvc0_graph_oclass) {
-       .base.handle = NV_ENGINE(GR, 0xea),
-       .base.ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nvc0_graph_ctor,
-               .dtor = nvc0_graph_dtor,
-               .init = nve4_graph_init,
-               .fini = _nouveau_graph_fini,
-       },
-       .cclass = &gk20a_grctx_oclass,
-       .sclass = gk20a_graph_sclass,
-       .mmio = nve4_graph_pack_mmio,
-       .ppc_nr = 1,
-}.base;
diff --git a/drivers/gpu/drm/nouveau/core/engine/graph/gm107.c b/drivers/gpu/drm/nouveau/core/engine/graph/gm107.c
deleted file mode 100644 (file)
index 4bdbdab..0000000
+++ /dev/null
@@ -1,469 +0,0 @@
-/*
- * Copyright 2013 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 <bskeggs@redhat.com>
- */
-
-#include <subdev/bios.h>
-#include <subdev/bios/P0260.h>
-
-#include "nvc0.h"
-#include "ctxnvc0.h"
-
-/*******************************************************************************
- * Graphics object classes
- ******************************************************************************/
-
-static struct nouveau_oclass
-gm107_graph_sclass[] = {
-       { 0x902d, &nouveau_object_ofuncs },
-       { 0xa140, &nouveau_object_ofuncs },
-       { MAXWELL_A, &nvc0_fermi_ofuncs, nvc0_graph_9097_omthds },
-       { MAXWELL_COMPUTE_A, &nouveau_object_ofuncs, nvc0_graph_90c0_omthds },
-       {}
-};
-
-/*******************************************************************************
- * PGRAPH register lists
- ******************************************************************************/
-
-static const struct nvc0_graph_init
-gm107_graph_init_main_0[] = {
-       { 0x400080,   1, 0x04, 0x003003c2 },
-       { 0x400088,   1, 0x04, 0x0001bfe7 },
-       { 0x40008c,   1, 0x04, 0x00060000 },
-       { 0x400090,   1, 0x04, 0x00000030 },
-       { 0x40013c,   1, 0x04, 0x003901f3 },
-       { 0x400140,   1, 0x04, 0x00000100 },
-       { 0x400144,   1, 0x04, 0x00000000 },
-       { 0x400148,   1, 0x04, 0x00000110 },
-       { 0x400138,   1, 0x04, 0x00000000 },
-       { 0x400130,   2, 0x04, 0x00000000 },
-       { 0x400124,   1, 0x04, 0x00000002 },
-       {}
-};
-
-static const struct nvc0_graph_init
-gm107_graph_init_ds_0[] = {
-       { 0x405844,   1, 0x04, 0x00ffffff },
-       { 0x405850,   1, 0x04, 0x00000000 },
-       { 0x405900,   1, 0x04, 0x00000000 },
-       { 0x405908,   1, 0x04, 0x00000000 },
-       {}
-};
-
-static const struct nvc0_graph_init
-gm107_graph_init_scc_0[] = {
-       { 0x40803c,   1, 0x04, 0x00000010 },
-       {}
-};
-
-static const struct nvc0_graph_init
-gm107_graph_init_sked_0[] = {
-       { 0x407010,   1, 0x04, 0x00000000 },
-       { 0x407040,   1, 0x04, 0x40440424 },
-       { 0x407048,   1, 0x04, 0x0000000a },
-       {}
-};
-
-static const struct nvc0_graph_init
-gm107_graph_init_prop_0[] = {
-       { 0x418408,   1, 0x04, 0x00000000 },
-       { 0x4184a0,   1, 0x04, 0x00000000 },
-       {}
-};
-
-static const struct nvc0_graph_init
-gm107_graph_init_setup_1[] = {
-       { 0x4188c8,   2, 0x04, 0x00000000 },
-       { 0x4188d0,   1, 0x04, 0x00010000 },
-       { 0x4188d4,   1, 0x04, 0x00010201 },
-       {}
-};
-
-static const struct nvc0_graph_init
-gm107_graph_init_zcull_0[] = {
-       { 0x418910,   1, 0x04, 0x00010001 },
-       { 0x418914,   1, 0x04, 0x00000301 },
-       { 0x418918,   1, 0x04, 0x00800000 },
-       { 0x418930,   2, 0x04, 0x00000000 },
-       { 0x418980,   1, 0x04, 0x77777770 },
-       { 0x418984,   3, 0x04, 0x77777777 },
-       {}
-};
-
-static const struct nvc0_graph_init
-gm107_graph_init_gpc_unk_1[] = {
-       { 0x418d00,   1, 0x04, 0x00000000 },
-       { 0x418f00,   1, 0x04, 0x00000400 },
-       { 0x418f08,   1, 0x04, 0x00000000 },
-       { 0x418e08,   1, 0x04, 0x00000000 },
-       {}
-};
-
-static const struct nvc0_graph_init
-gm107_graph_init_tpccs_0[] = {
-       { 0x419dc4,   1, 0x04, 0x00000000 },
-       { 0x419dc8,   1, 0x04, 0x00000501 },
-       { 0x419dd0,   1, 0x04, 0x00000000 },
-       { 0x419dd4,   1, 0x04, 0x00000100 },
-       { 0x419dd8,   1, 0x04, 0x00000001 },
-       { 0x419ddc,   1, 0x04, 0x00000002 },
-       { 0x419de0,   1, 0x04, 0x00000001 },
-       { 0x419d0c,   1, 0x04, 0x00000000 },
-       { 0x419d10,   1, 0x04, 0x00000014 },
-       {}
-};
-
-static const struct nvc0_graph_init
-gm107_graph_init_tex_0[] = {
-       { 0x419ab0,   1, 0x04, 0x00000000 },
-       { 0x419ab8,   1, 0x04, 0x000000e7 },
-       { 0x419abc,   1, 0x04, 0x00000000 },
-       { 0x419acc,   1, 0x04, 0x000000ff },
-       { 0x419ac0,   1, 0x04, 0x00000000 },
-       { 0x419aa8,   2, 0x04, 0x00000000 },
-       { 0x419ad0,   2, 0x04, 0x00000000 },
-       { 0x419ae0,   2, 0x04, 0x00000000 },
-       { 0x419af0,   4, 0x04, 0x00000000 },
-       {}
-};
-
-static const struct nvc0_graph_init
-gm107_graph_init_pe_0[] = {
-       { 0x419900,   1, 0x04, 0x000000ff },
-       { 0x41980c,   1, 0x04, 0x00000010 },
-       { 0x419844,   1, 0x04, 0x00000000 },
-       { 0x419838,   1, 0x04, 0x000000ff },
-       { 0x419850,   1, 0x04, 0x00000004 },
-       { 0x419854,   2, 0x04, 0x00000000 },
-       { 0x419894,   3, 0x04, 0x00100401 },
-       {}
-};
-
-static const struct nvc0_graph_init
-gm107_graph_init_l1c_0[] = {
-       { 0x419c98,   1, 0x04, 0x00000000 },
-       { 0x419cc0,   2, 0x04, 0x00000000 },
-       {}
-};
-
-static const struct nvc0_graph_init
-gm107_graph_init_sm_0[] = {
-       { 0x419e30,   1, 0x04, 0x000000ff },
-       { 0x419e00,   1, 0x04, 0x00000000 },
-       { 0x419ea0,   1, 0x04, 0x00000000 },
-       { 0x419ee4,   1, 0x04, 0x00000000 },
-       { 0x419ea4,   1, 0x04, 0x00000100 },
-       { 0x419ea8,   1, 0x04, 0x01000000 },
-       { 0x419ee8,   1, 0x04, 0x00000091 },
-       { 0x419eb4,   1, 0x04, 0x00000000 },
-       { 0x419ebc,   2, 0x04, 0x00000000 },
-       { 0x419edc,   1, 0x04, 0x000c1810 },
-       { 0x419ed8,   1, 0x04, 0x00000000 },
-       { 0x419ee0,   1, 0x04, 0x00000000 },
-       { 0x419f74,   1, 0x04, 0x00005155 },
-       { 0x419f80,   4, 0x04, 0x00000000 },
-       {}
-};
-
-static const struct nvc0_graph_init
-gm107_graph_init_l1c_1[] = {
-       { 0x419ccc,   2, 0x04, 0x00000000 },
-       { 0x419c80,   1, 0x04, 0x3f006022 },
-       { 0x419c88,   1, 0x04, 0x00000000 },
-       {}
-};
-
-static const struct nvc0_graph_init
-gm107_graph_init_pes_0[] = {
-       { 0x41be50,   1, 0x04, 0x000000ff },
-       { 0x41be04,   1, 0x04, 0x00000000 },
-       { 0x41be08,   1, 0x04, 0x00000004 },
-       { 0x41be0c,   1, 0x04, 0x00000008 },
-       { 0x41be10,   1, 0x04, 0x0e3b8bc7 },
-       { 0x41be14,   2, 0x04, 0x00000000 },
-       { 0x41be3c,   5, 0x04, 0x00100401 },
-       {}
-};
-
-static const struct nvc0_graph_init
-gm107_graph_init_wwdx_0[] = {
-       { 0x41bfd4,   1, 0x04, 0x00800000 },
-       { 0x41bfdc,   1, 0x04, 0x00000000 },
-       {}
-};
-
-static const struct nvc0_graph_init
-gm107_graph_init_cbm_0[] = {
-       { 0x41becc,   1, 0x04, 0x00000000 },
-       {}
-};
-
-static const struct nvc0_graph_init
-gm107_graph_init_be_0[] = {
-       { 0x408890,   1, 0x04, 0x000000ff },
-       { 0x40880c,   1, 0x04, 0x00000000 },
-       { 0x408850,   1, 0x04, 0x00000004 },
-       { 0x408878,   1, 0x04, 0x00c81603 },
-       { 0x40887c,   1, 0x04, 0x80543432 },
-       { 0x408880,   1, 0x04, 0x0010581e },
-       { 0x408884,   1, 0x04, 0x00001205 },
-       { 0x408974,   1, 0x04, 0x000000ff },
-       { 0x408910,   9, 0x04, 0x00000000 },
-       { 0x408950,   1, 0x04, 0x00000000 },
-       { 0x408954,   1, 0x04, 0x0000ffff },
-       { 0x408958,   1, 0x04, 0x00000034 },
-       { 0x40895c,   1, 0x04, 0x8531a003 },
-       { 0x408960,   1, 0x04, 0x0561985a },
-       { 0x408964,   1, 0x04, 0x04e15c4f },
-       { 0x408968,   1, 0x04, 0x02808833 },
-       { 0x40896c,   1, 0x04, 0x01f02438 },
-       { 0x408970,   1, 0x04, 0x00012c00 },
-       { 0x408984,   1, 0x04, 0x00000000 },
-       { 0x408988,   1, 0x04, 0x08040201 },
-       { 0x40898c,   1, 0x04, 0x80402010 },
-       {}
-};
-
-static const struct nvc0_graph_init
-gm107_graph_init_sm_1[] = {
-       { 0x419e5c,   1, 0x04, 0x00000000 },
-       { 0x419e58,   1, 0x04, 0x00000000 },
-       {}
-};
-
-static const struct nvc0_graph_pack
-gm107_graph_pack_mmio[] = {
-       { gm107_graph_init_main_0 },
-       { nvf0_graph_init_fe_0 },
-       { nvc0_graph_init_pri_0 },
-       { nvc0_graph_init_rstr2d_0 },
-       { nvc0_graph_init_pd_0 },
-       { gm107_graph_init_ds_0 },
-       { gm107_graph_init_scc_0 },
-       { gm107_graph_init_sked_0 },
-       { nvf0_graph_init_cwd_0 },
-       { gm107_graph_init_prop_0 },
-       { nv108_graph_init_gpc_unk_0 },
-       { nvc0_graph_init_setup_0 },
-       { nvc0_graph_init_crstr_0 },
-       { gm107_graph_init_setup_1 },
-       { gm107_graph_init_zcull_0 },
-       { nvc0_graph_init_gpm_0 },
-       { gm107_graph_init_gpc_unk_1 },
-       { nvc0_graph_init_gcc_0 },
-       { gm107_graph_init_tpccs_0 },
-       { gm107_graph_init_tex_0 },
-       { gm107_graph_init_pe_0 },
-       { gm107_graph_init_l1c_0 },
-       { nvc0_graph_init_mpc_0 },
-       { gm107_graph_init_sm_0 },
-       { gm107_graph_init_l1c_1 },
-       { gm107_graph_init_pes_0 },
-       { gm107_graph_init_wwdx_0 },
-       { gm107_graph_init_cbm_0 },
-       { gm107_graph_init_be_0 },
-       { gm107_graph_init_sm_1 },
-       {}
-};
-
-/*******************************************************************************
- * PGRAPH engine/subdev functions
- ******************************************************************************/
-
-static void
-gm107_graph_init_bios(struct nvc0_graph_priv *priv)
-{
-       static const struct {
-               u32 ctrl;
-               u32 data;
-       } regs[] = {
-               { 0x419ed8, 0x419ee0 },
-               { 0x419ad0, 0x419ad4 },
-               { 0x419ae0, 0x419ae4 },
-               { 0x419af0, 0x419af4 },
-               { 0x419af8, 0x419afc },
-       };
-       struct nouveau_bios *bios = nouveau_bios(priv);
-       struct nvbios_P0260E infoE;
-       struct nvbios_P0260X infoX;
-       int E = -1, X;
-       u8 ver, hdr;
-
-       while (nvbios_P0260Ep(bios, ++E, &ver, &hdr, &infoE)) {
-               if (X = -1, E < ARRAY_SIZE(regs)) {
-                       nv_wr32(priv, regs[E].ctrl, infoE.data);
-                       while (nvbios_P0260Xp(bios, ++X, &ver, &hdr, &infoX))
-                               nv_wr32(priv, regs[E].data, infoX.data);
-               }
-       }
-}
-
-int
-gm107_graph_init(struct nouveau_object *object)
-{
-       struct nvc0_graph_oclass *oclass = (void *)object->oclass;
-       struct nvc0_graph_priv *priv = (void *)object;
-       const u32 magicgpc918 = DIV_ROUND_UP(0x00800000, priv->tpc_total);
-       u32 data[TPC_MAX / 8] = {};
-       u8  tpcnr[GPC_MAX];
-       int gpc, tpc, ppc, rop;
-       int ret, i;
-
-       ret = nouveau_graph_init(&priv->base);
-       if (ret)
-               return ret;
-
-       nv_wr32(priv, GPC_BCAST(0x0880), 0x00000000);
-       nv_wr32(priv, GPC_BCAST(0x0890), 0x00000000);
-       nv_wr32(priv, GPC_BCAST(0x0894), 0x00000000);
-       nv_wr32(priv, GPC_BCAST(0x08b4), priv->unk4188b4->addr >> 8);
-       nv_wr32(priv, GPC_BCAST(0x08b8), priv->unk4188b8->addr >> 8);
-
-       nvc0_graph_mmio(priv, oclass->mmio);
-
-       gm107_graph_init_bios(priv);
-
-       nv_wr32(priv, GPC_UNIT(0, 0x3018), 0x00000001);
-
-       memset(data, 0x00, sizeof(data));
-       memcpy(tpcnr, priv->tpc_nr, sizeof(priv->tpc_nr));
-       for (i = 0, gpc = -1; i < priv->tpc_total; i++) {
-               do {
-                       gpc = (gpc + 1) % priv->gpc_nr;
-               } while (!tpcnr[gpc]);
-               tpc = priv->tpc_nr[gpc] - tpcnr[gpc]--;
-
-               data[i / 8] |= tpc << ((i % 8) * 4);
-       }
-
-       nv_wr32(priv, GPC_BCAST(0x0980), data[0]);
-       nv_wr32(priv, GPC_BCAST(0x0984), data[1]);
-       nv_wr32(priv, GPC_BCAST(0x0988), data[2]);
-       nv_wr32(priv, GPC_BCAST(0x098c), data[3]);
-
-       for (gpc = 0; gpc < priv->gpc_nr; gpc++) {
-               nv_wr32(priv, GPC_UNIT(gpc, 0x0914),
-                       priv->magic_not_rop_nr << 8 | priv->tpc_nr[gpc]);
-               nv_wr32(priv, GPC_UNIT(gpc, 0x0910), 0x00040000 |
-                       priv->tpc_total);
-               nv_wr32(priv, GPC_UNIT(gpc, 0x0918), magicgpc918);
-       }
-
-       nv_wr32(priv, GPC_BCAST(0x3fd4), magicgpc918);
-       nv_wr32(priv, GPC_BCAST(0x08ac), nv_rd32(priv, 0x100800));
-
-       nv_wr32(priv, 0x400500, 0x00010001);
-
-       nv_wr32(priv, 0x400100, 0xffffffff);
-       nv_wr32(priv, 0x40013c, 0xffffffff);
-       nv_wr32(priv, 0x400124, 0x00000002);
-       nv_wr32(priv, 0x409c24, 0x000e0000);
-
-       nv_wr32(priv, 0x404000, 0xc0000000);
-       nv_wr32(priv, 0x404600, 0xc0000000);
-       nv_wr32(priv, 0x408030, 0xc0000000);
-       nv_wr32(priv, 0x404490, 0xc0000000);
-       nv_wr32(priv, 0x406018, 0xc0000000);
-       nv_wr32(priv, 0x407020, 0x40000000);
-       nv_wr32(priv, 0x405840, 0xc0000000);
-       nv_wr32(priv, 0x405844, 0x00ffffff);
-       nv_mask(priv, 0x419cc0, 0x00000008, 0x00000008);
-
-       for (gpc = 0; gpc < priv->gpc_nr; gpc++) {
-               for (ppc = 0; ppc < 2 /* priv->ppc_nr[gpc] */; ppc++)
-                       nv_wr32(priv, PPC_UNIT(gpc, ppc, 0x038), 0xc0000000);
-               nv_wr32(priv, GPC_UNIT(gpc, 0x0420), 0xc0000000);
-               nv_wr32(priv, GPC_UNIT(gpc, 0x0900), 0xc0000000);
-               nv_wr32(priv, GPC_UNIT(gpc, 0x1028), 0xc0000000);
-               nv_wr32(priv, GPC_UNIT(gpc, 0x0824), 0xc0000000);
-               for (tpc = 0; tpc < priv->tpc_nr[gpc]; tpc++) {
-                       nv_wr32(priv, TPC_UNIT(gpc, tpc, 0x508), 0xffffffff);
-                       nv_wr32(priv, TPC_UNIT(gpc, tpc, 0x50c), 0xffffffff);
-                       nv_wr32(priv, TPC_UNIT(gpc, tpc, 0x224), 0xc0000000);
-                       nv_wr32(priv, TPC_UNIT(gpc, tpc, 0x48c), 0xc0000000);
-                       nv_wr32(priv, TPC_UNIT(gpc, tpc, 0x084), 0xc0000000);
-                       nv_wr32(priv, TPC_UNIT(gpc, tpc, 0x430), 0xc0000000);
-                       nv_wr32(priv, TPC_UNIT(gpc, tpc, 0x644), 0x00dffffe);
-                       nv_wr32(priv, TPC_UNIT(gpc, tpc, 0x64c), 0x00000005);
-               }
-               nv_wr32(priv, GPC_UNIT(gpc, 0x2c90), 0xffffffff);
-               nv_wr32(priv, GPC_UNIT(gpc, 0x2c94), 0xffffffff);
-       }
-
-       for (rop = 0; rop < priv->rop_nr; rop++) {
-               nv_wr32(priv, ROP_UNIT(rop, 0x144), 0x40000000);
-               nv_wr32(priv, ROP_UNIT(rop, 0x070), 0x40000000);
-               nv_wr32(priv, ROP_UNIT(rop, 0x204), 0xffffffff);
-               nv_wr32(priv, ROP_UNIT(rop, 0x208), 0xffffffff);
-       }
-
-       nv_wr32(priv, 0x400108, 0xffffffff);
-       nv_wr32(priv, 0x400138, 0xffffffff);
-       nv_wr32(priv, 0x400118, 0xffffffff);
-       nv_wr32(priv, 0x400130, 0xffffffff);
-       nv_wr32(priv, 0x40011c, 0xffffffff);
-       nv_wr32(priv, 0x400134, 0xffffffff);
-
-       nv_wr32(priv, 0x400054, 0x2c350f63);
-
-       nvc0_graph_zbc_init(priv);
-
-       return nvc0_graph_init_ctxctl(priv);
-}
-
-#include "fuc/hubgm107.fuc5.h"
-
-static struct nvc0_graph_ucode
-gm107_graph_fecs_ucode = {
-       .code.data = gm107_grhub_code,
-       .code.size = sizeof(gm107_grhub_code),
-       .data.data = gm107_grhub_data,
-       .data.size = sizeof(gm107_grhub_data),
-};
-
-#include "fuc/gpcgm107.fuc5.h"
-
-static struct nvc0_graph_ucode
-gm107_graph_gpccs_ucode = {
-       .code.data = gm107_grgpc_code,
-       .code.size = sizeof(gm107_grgpc_code),
-       .data.data = gm107_grgpc_data,
-       .data.size = sizeof(gm107_grgpc_data),
-};
-
-struct nouveau_oclass *
-gm107_graph_oclass = &(struct nvc0_graph_oclass) {
-       .base.handle = NV_ENGINE(GR, 0x07),
-       .base.ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nvc0_graph_ctor,
-               .dtor = nvc0_graph_dtor,
-               .init = gm107_graph_init,
-               .fini = _nouveau_graph_fini,
-       },
-       .cclass = &gm107_grctx_oclass,
-       .sclass =  gm107_graph_sclass,
-       .mmio = gm107_graph_pack_mmio,
-       .fecs.ucode = 0 ? &gm107_graph_fecs_ucode : NULL,
-       .gpccs.ucode = &gm107_graph_gpccs_ucode,
-       .ppc_nr = 2,
-}.base;
diff --git a/drivers/gpu/drm/nouveau/core/engine/graph/nv04.c b/drivers/gpu/drm/nouveau/core/engine/graph/nv04.c
deleted file mode 100644 (file)
index f70e2f6..0000000
+++ /dev/null
@@ -1,1388 +0,0 @@
-/*
- * Copyright 2007 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
- * 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 <core/client.h>
-#include <core/os.h>
-#include <core/handle.h>
-#include <core/namedb.h>
-
-#include <subdev/fb.h>
-#include <subdev/instmem.h>
-#include <subdev/timer.h>
-
-#include <engine/fifo.h>
-#include <engine/graph.h>
-
-#include "regs.h"
-
-static u32
-nv04_graph_ctx_regs[] = {
-       0x0040053c,
-       0x00400544,
-       0x00400540,
-       0x00400548,
-       NV04_PGRAPH_CTX_SWITCH1,
-       NV04_PGRAPH_CTX_SWITCH2,
-       NV04_PGRAPH_CTX_SWITCH3,
-       NV04_PGRAPH_CTX_SWITCH4,
-       NV04_PGRAPH_CTX_CACHE1,
-       NV04_PGRAPH_CTX_CACHE2,
-       NV04_PGRAPH_CTX_CACHE3,
-       NV04_PGRAPH_CTX_CACHE4,
-       0x00400184,
-       0x004001a4,
-       0x004001c4,
-       0x004001e4,
-       0x00400188,
-       0x004001a8,
-       0x004001c8,
-       0x004001e8,
-       0x0040018c,
-       0x004001ac,
-       0x004001cc,
-       0x004001ec,
-       0x00400190,
-       0x004001b0,
-       0x004001d0,
-       0x004001f0,
-       0x00400194,
-       0x004001b4,
-       0x004001d4,
-       0x004001f4,
-       0x00400198,
-       0x004001b8,
-       0x004001d8,
-       0x004001f8,
-       0x0040019c,
-       0x004001bc,
-       0x004001dc,
-       0x004001fc,
-       0x00400174,
-       NV04_PGRAPH_DMA_START_0,
-       NV04_PGRAPH_DMA_START_1,
-       NV04_PGRAPH_DMA_LENGTH,
-       NV04_PGRAPH_DMA_MISC,
-       NV04_PGRAPH_DMA_PITCH,
-       NV04_PGRAPH_BOFFSET0,
-       NV04_PGRAPH_BBASE0,
-       NV04_PGRAPH_BLIMIT0,
-       NV04_PGRAPH_BOFFSET1,
-       NV04_PGRAPH_BBASE1,
-       NV04_PGRAPH_BLIMIT1,
-       NV04_PGRAPH_BOFFSET2,
-       NV04_PGRAPH_BBASE2,
-       NV04_PGRAPH_BLIMIT2,
-       NV04_PGRAPH_BOFFSET3,
-       NV04_PGRAPH_BBASE3,
-       NV04_PGRAPH_BLIMIT3,
-       NV04_PGRAPH_BOFFSET4,
-       NV04_PGRAPH_BBASE4,
-       NV04_PGRAPH_BLIMIT4,
-       NV04_PGRAPH_BOFFSET5,
-       NV04_PGRAPH_BBASE5,
-       NV04_PGRAPH_BLIMIT5,
-       NV04_PGRAPH_BPITCH0,
-       NV04_PGRAPH_BPITCH1,
-       NV04_PGRAPH_BPITCH2,
-       NV04_PGRAPH_BPITCH3,
-       NV04_PGRAPH_BPITCH4,
-       NV04_PGRAPH_SURFACE,
-       NV04_PGRAPH_STATE,
-       NV04_PGRAPH_BSWIZZLE2,
-       NV04_PGRAPH_BSWIZZLE5,
-       NV04_PGRAPH_BPIXEL,
-       NV04_PGRAPH_NOTIFY,
-       NV04_PGRAPH_PATT_COLOR0,
-       NV04_PGRAPH_PATT_COLOR1,
-       NV04_PGRAPH_PATT_COLORRAM+0x00,
-       NV04_PGRAPH_PATT_COLORRAM+0x04,
-       NV04_PGRAPH_PATT_COLORRAM+0x08,
-       NV04_PGRAPH_PATT_COLORRAM+0x0c,
-       NV04_PGRAPH_PATT_COLORRAM+0x10,
-       NV04_PGRAPH_PATT_COLORRAM+0x14,
-       NV04_PGRAPH_PATT_COLORRAM+0x18,
-       NV04_PGRAPH_PATT_COLORRAM+0x1c,
-       NV04_PGRAPH_PATT_COLORRAM+0x20,
-       NV04_PGRAPH_PATT_COLORRAM+0x24,
-       NV04_PGRAPH_PATT_COLORRAM+0x28,
-       NV04_PGRAPH_PATT_COLORRAM+0x2c,
-       NV04_PGRAPH_PATT_COLORRAM+0x30,
-       NV04_PGRAPH_PATT_COLORRAM+0x34,
-       NV04_PGRAPH_PATT_COLORRAM+0x38,
-       NV04_PGRAPH_PATT_COLORRAM+0x3c,
-       NV04_PGRAPH_PATT_COLORRAM+0x40,
-       NV04_PGRAPH_PATT_COLORRAM+0x44,
-       NV04_PGRAPH_PATT_COLORRAM+0x48,
-       NV04_PGRAPH_PATT_COLORRAM+0x4c,
-       NV04_PGRAPH_PATT_COLORRAM+0x50,
-       NV04_PGRAPH_PATT_COLORRAM+0x54,
-       NV04_PGRAPH_PATT_COLORRAM+0x58,
-       NV04_PGRAPH_PATT_COLORRAM+0x5c,
-       NV04_PGRAPH_PATT_COLORRAM+0x60,
-       NV04_PGRAPH_PATT_COLORRAM+0x64,
-       NV04_PGRAPH_PATT_COLORRAM+0x68,
-       NV04_PGRAPH_PATT_COLORRAM+0x6c,
-       NV04_PGRAPH_PATT_COLORRAM+0x70,
-       NV04_PGRAPH_PATT_COLORRAM+0x74,
-       NV04_PGRAPH_PATT_COLORRAM+0x78,
-       NV04_PGRAPH_PATT_COLORRAM+0x7c,
-       NV04_PGRAPH_PATT_COLORRAM+0x80,
-       NV04_PGRAPH_PATT_COLORRAM+0x84,
-       NV04_PGRAPH_PATT_COLORRAM+0x88,
-       NV04_PGRAPH_PATT_COLORRAM+0x8c,
-       NV04_PGRAPH_PATT_COLORRAM+0x90,
-       NV04_PGRAPH_PATT_COLORRAM+0x94,
-       NV04_PGRAPH_PATT_COLORRAM+0x98,
-       NV04_PGRAPH_PATT_COLORRAM+0x9c,
-       NV04_PGRAPH_PATT_COLORRAM+0xa0,
-       NV04_PGRAPH_PATT_COLORRAM+0xa4,
-       NV04_PGRAPH_PATT_COLORRAM+0xa8,
-       NV04_PGRAPH_PATT_COLORRAM+0xac,
-       NV04_PGRAPH_PATT_COLORRAM+0xb0,
-       NV04_PGRAPH_PATT_COLORRAM+0xb4,
-       NV04_PGRAPH_PATT_COLORRAM+0xb8,
-       NV04_PGRAPH_PATT_COLORRAM+0xbc,
-       NV04_PGRAPH_PATT_COLORRAM+0xc0,
-       NV04_PGRAPH_PATT_COLORRAM+0xc4,
-       NV04_PGRAPH_PATT_COLORRAM+0xc8,
-       NV04_PGRAPH_PATT_COLORRAM+0xcc,
-       NV04_PGRAPH_PATT_COLORRAM+0xd0,
-       NV04_PGRAPH_PATT_COLORRAM+0xd4,
-       NV04_PGRAPH_PATT_COLORRAM+0xd8,
-       NV04_PGRAPH_PATT_COLORRAM+0xdc,
-       NV04_PGRAPH_PATT_COLORRAM+0xe0,
-       NV04_PGRAPH_PATT_COLORRAM+0xe4,
-       NV04_PGRAPH_PATT_COLORRAM+0xe8,
-       NV04_PGRAPH_PATT_COLORRAM+0xec,
-       NV04_PGRAPH_PATT_COLORRAM+0xf0,
-       NV04_PGRAPH_PATT_COLORRAM+0xf4,
-       NV04_PGRAPH_PATT_COLORRAM+0xf8,
-       NV04_PGRAPH_PATT_COLORRAM+0xfc,
-       NV04_PGRAPH_PATTERN,
-       0x0040080c,
-       NV04_PGRAPH_PATTERN_SHAPE,
-       0x00400600,
-       NV04_PGRAPH_ROP3,
-       NV04_PGRAPH_CHROMA,
-       NV04_PGRAPH_BETA_AND,
-       NV04_PGRAPH_BETA_PREMULT,
-       NV04_PGRAPH_CONTROL0,
-       NV04_PGRAPH_CONTROL1,
-       NV04_PGRAPH_CONTROL2,
-       NV04_PGRAPH_BLEND,
-       NV04_PGRAPH_STORED_FMT,
-       NV04_PGRAPH_SOURCE_COLOR,
-       0x00400560,
-       0x00400568,
-       0x00400564,
-       0x0040056c,
-       0x00400400,
-       0x00400480,
-       0x00400404,
-       0x00400484,
-       0x00400408,
-       0x00400488,
-       0x0040040c,
-       0x0040048c,
-       0x00400410,
-       0x00400490,
-       0x00400414,
-       0x00400494,
-       0x00400418,
-       0x00400498,
-       0x0040041c,
-       0x0040049c,
-       0x00400420,
-       0x004004a0,
-       0x00400424,
-       0x004004a4,
-       0x00400428,
-       0x004004a8,
-       0x0040042c,
-       0x004004ac,
-       0x00400430,
-       0x004004b0,
-       0x00400434,
-       0x004004b4,
-       0x00400438,
-       0x004004b8,
-       0x0040043c,
-       0x004004bc,
-       0x00400440,
-       0x004004c0,
-       0x00400444,
-       0x004004c4,
-       0x00400448,
-       0x004004c8,
-       0x0040044c,
-       0x004004cc,
-       0x00400450,
-       0x004004d0,
-       0x00400454,
-       0x004004d4,
-       0x00400458,
-       0x004004d8,
-       0x0040045c,
-       0x004004dc,
-       0x00400460,
-       0x004004e0,
-       0x00400464,
-       0x004004e4,
-       0x00400468,
-       0x004004e8,
-       0x0040046c,
-       0x004004ec,
-       0x00400470,
-       0x004004f0,
-       0x00400474,
-       0x004004f4,
-       0x00400478,
-       0x004004f8,
-       0x0040047c,
-       0x004004fc,
-       0x00400534,
-       0x00400538,
-       0x00400514,
-       0x00400518,
-       0x0040051c,
-       0x00400520,
-       0x00400524,
-       0x00400528,
-       0x0040052c,
-       0x00400530,
-       0x00400d00,
-       0x00400d40,
-       0x00400d80,
-       0x00400d04,
-       0x00400d44,
-       0x00400d84,
-       0x00400d08,
-       0x00400d48,
-       0x00400d88,
-       0x00400d0c,
-       0x00400d4c,
-       0x00400d8c,
-       0x00400d10,
-       0x00400d50,
-       0x00400d90,
-       0x00400d14,
-       0x00400d54,
-       0x00400d94,
-       0x00400d18,
-       0x00400d58,
-       0x00400d98,
-       0x00400d1c,
-       0x00400d5c,
-       0x00400d9c,
-       0x00400d20,
-       0x00400d60,
-       0x00400da0,
-       0x00400d24,
-       0x00400d64,
-       0x00400da4,
-       0x00400d28,
-       0x00400d68,
-       0x00400da8,
-       0x00400d2c,
-       0x00400d6c,
-       0x00400dac,
-       0x00400d30,
-       0x00400d70,
-       0x00400db0,
-       0x00400d34,
-       0x00400d74,
-       0x00400db4,
-       0x00400d38,
-       0x00400d78,
-       0x00400db8,
-       0x00400d3c,
-       0x00400d7c,
-       0x00400dbc,
-       0x00400590,
-       0x00400594,
-       0x00400598,
-       0x0040059c,
-       0x004005a8,
-       0x004005ac,
-       0x004005b0,
-       0x004005b4,
-       0x004005c0,
-       0x004005c4,
-       0x004005c8,
-       0x004005cc,
-       0x004005d0,
-       0x004005d4,
-       0x004005d8,
-       0x004005dc,
-       0x004005e0,
-       NV04_PGRAPH_PASSTHRU_0,
-       NV04_PGRAPH_PASSTHRU_1,
-       NV04_PGRAPH_PASSTHRU_2,
-       NV04_PGRAPH_DVD_COLORFMT,
-       NV04_PGRAPH_SCALED_FORMAT,
-       NV04_PGRAPH_MISC24_0,
-       NV04_PGRAPH_MISC24_1,
-       NV04_PGRAPH_MISC24_2,
-       0x00400500,
-       0x00400504,
-       NV04_PGRAPH_VALID1,
-       NV04_PGRAPH_VALID2,
-       NV04_PGRAPH_DEBUG_3
-};
-
-struct nv04_graph_priv {
-       struct nouveau_graph base;
-       struct nv04_graph_chan *chan[16];
-       spinlock_t lock;
-};
-
-struct nv04_graph_chan {
-       struct nouveau_object base;
-       int chid;
-       u32 nv04[ARRAY_SIZE(nv04_graph_ctx_regs)];
-};
-
-
-static inline struct nv04_graph_priv *
-nv04_graph_priv(struct nv04_graph_chan *chan)
-{
-       return (void *)nv_object(chan)->engine;
-}
-
-/*******************************************************************************
- * Graphics object classes
- ******************************************************************************/
-
-/*
- * Software methods, why they are needed, and how they all work:
- *
- * NV04 and NV05 keep most of the state in PGRAPH context itself, but some
- * 2d engine settings are kept inside the grobjs themselves. The grobjs are
- * 3 words long on both. grobj format on NV04 is:
- *
- * word 0:
- *  - bits 0-7: class
- *  - bit 12: color key active
- *  - bit 13: clip rect active
- *  - bit 14: if set, destination surface is swizzled and taken from buffer 5
- *            [set by NV04_SWIZZLED_SURFACE], otherwise it's linear and taken
- *            from buffer 0 [set by NV04_CONTEXT_SURFACES_2D or
- *            NV03_CONTEXT_SURFACE_DST].
- *  - bits 15-17: 2d operation [aka patch config]
- *  - bit 24: patch valid [enables rendering using this object]
- *  - bit 25: surf3d valid [for tex_tri and multitex_tri only]
- * word 1:
- *  - bits 0-1: mono format
- *  - bits 8-13: color format
- *  - bits 16-31: DMA_NOTIFY instance
- * word 2:
- *  - bits 0-15: DMA_A instance
- *  - bits 16-31: DMA_B instance
- *
- * On NV05 it's:
- *
- * word 0:
- *  - bits 0-7: class
- *  - bit 12: color key active
- *  - bit 13: clip rect active
- *  - bit 14: if set, destination surface is swizzled and taken from buffer 5
- *            [set by NV04_SWIZZLED_SURFACE], otherwise it's linear and taken
- *            from buffer 0 [set by NV04_CONTEXT_SURFACES_2D or
- *            NV03_CONTEXT_SURFACE_DST].
- *  - bits 15-17: 2d operation [aka patch config]
- *  - bits 20-22: dither mode
- *  - bit 24: patch valid [enables rendering using this object]
- *  - bit 25: surface_dst/surface_color/surf2d/surf3d valid
- *  - bit 26: surface_src/surface_zeta valid
- *  - bit 27: pattern valid
- *  - bit 28: rop valid
- *  - bit 29: beta1 valid
- *  - bit 30: beta4 valid
- * word 1:
- *  - bits 0-1: mono format
- *  - bits 8-13: color format
- *  - bits 16-31: DMA_NOTIFY instance
- * word 2:
- *  - bits 0-15: DMA_A instance
- *  - bits 16-31: DMA_B instance
- *
- * NV05 will set/unset the relevant valid bits when you poke the relevant
- * object-binding methods with object of the proper type, or with the NULL
- * type. It'll only allow rendering using the grobj if all needed objects
- * are bound. The needed set of objects depends on selected operation: for
- * example rop object is needed by ROP_AND, but not by SRCCOPY_AND.
- *
- * NV04 doesn't have these methods implemented at all, and doesn't have the
- * relevant bits in grobj. Instead, it'll allow rendering whenever bit 24
- * is set. So we have to emulate them in software, internally keeping the
- * same bits as NV05 does. Since grobjs are aligned to 16 bytes on nv04,
- * but the last word isn't actually used for anything, we abuse it for this
- * purpose.
- *
- * Actually, NV05 can optionally check bit 24 too, but we disable this since
- * there's no use for it.
- *
- * For unknown reasons, NV04 implements surf3d binding in hardware as an
- * exception. Also for unknown reasons, NV04 doesn't implement the clipping
- * methods on the surf3d object, so we have to emulate them too.
- */
-
-static void
-nv04_graph_set_ctx1(struct nouveau_object *object, u32 mask, u32 value)
-{
-       struct nv04_graph_priv *priv = (void *)object->engine;
-       int subc = (nv_rd32(priv, NV04_PGRAPH_TRAPPED_ADDR) >> 13) & 0x7;
-       u32 tmp;
-
-       tmp  = nv_ro32(object, 0x00);
-       tmp &= ~mask;
-       tmp |= value;
-       nv_wo32(object, 0x00, tmp);
-
-       nv_wr32(priv, NV04_PGRAPH_CTX_SWITCH1, tmp);
-       nv_wr32(priv, NV04_PGRAPH_CTX_CACHE1 + (subc<<2), tmp);
-}
-
-static void
-nv04_graph_set_ctx_val(struct nouveau_object *object, u32 mask, u32 value)
-{
-       int class, op, valid = 1;
-       u32 tmp, ctx1;
-
-       ctx1 = nv_ro32(object, 0x00);
-       class = ctx1 & 0xff;
-       op = (ctx1 >> 15) & 7;
-
-       tmp = nv_ro32(object, 0x0c);
-       tmp &= ~mask;
-       tmp |= value;
-       nv_wo32(object, 0x0c, tmp);
-
-       /* check for valid surf2d/surf_dst/surf_color */
-       if (!(tmp & 0x02000000))
-               valid = 0;
-       /* check for valid surf_src/surf_zeta */
-       if ((class == 0x1f || class == 0x48) && !(tmp & 0x04000000))
-               valid = 0;
-
-       switch (op) {
-       /* SRCCOPY_AND, SRCCOPY: no extra objects required */
-       case 0:
-       case 3:
-               break;
-       /* ROP_AND: requires pattern and rop */
-       case 1:
-               if (!(tmp & 0x18000000))
-                       valid = 0;
-               break;
-       /* BLEND_AND: requires beta1 */
-       case 2:
-               if (!(tmp & 0x20000000))
-                       valid = 0;
-               break;
-       /* SRCCOPY_PREMULT, BLEND_PREMULT: beta4 required */
-       case 4:
-       case 5:
-               if (!(tmp & 0x40000000))
-                       valid = 0;
-               break;
-       }
-
-       nv04_graph_set_ctx1(object, 0x01000000, valid << 24);
-}
-
-static int
-nv04_graph_mthd_set_operation(struct nouveau_object *object, u32 mthd,
-                             void *args, u32 size)
-{
-       u32 class = nv_ro32(object, 0) & 0xff;
-       u32 data = *(u32 *)args;
-       if (data > 5)
-               return 1;
-       /* Old versions of the objects only accept first three operations. */
-       if (data > 2 && class < 0x40)
-               return 1;
-       nv04_graph_set_ctx1(object, 0x00038000, data << 15);
-       /* changing operation changes set of objects needed for validation */
-       nv04_graph_set_ctx_val(object, 0, 0);
-       return 0;
-}
-
-static int
-nv04_graph_mthd_surf3d_clip_h(struct nouveau_object *object, u32 mthd,
-                             void *args, u32 size)
-{
-       struct nv04_graph_priv *priv = (void *)object->engine;
-       u32 data = *(u32 *)args;
-       u32 min = data & 0xffff, max;
-       u32 w = data >> 16;
-       if (min & 0x8000)
-               /* too large */
-               return 1;
-       if (w & 0x8000)
-               /* yes, it accepts negative for some reason. */
-               w |= 0xffff0000;
-       max = min + w;
-       max &= 0x3ffff;
-       nv_wr32(priv, 0x40053c, min);
-       nv_wr32(priv, 0x400544, max);
-       return 0;
-}
-
-static int
-nv04_graph_mthd_surf3d_clip_v(struct nouveau_object *object, u32 mthd,
-                             void *args, u32 size)
-{
-       struct nv04_graph_priv *priv = (void *)object->engine;
-       u32 data = *(u32 *)args;
-       u32 min = data & 0xffff, max;
-       u32 w = data >> 16;
-       if (min & 0x8000)
-               /* too large */
-               return 1;
-       if (w & 0x8000)
-               /* yes, it accepts negative for some reason. */
-               w |= 0xffff0000;
-       max = min + w;
-       max &= 0x3ffff;
-       nv_wr32(priv, 0x400540, min);
-       nv_wr32(priv, 0x400548, max);
-       return 0;
-}
-
-static u16
-nv04_graph_mthd_bind_class(struct nouveau_object *object, u32 *args, u32 size)
-{
-       struct nouveau_instmem *imem = nouveau_instmem(object);
-       u32 inst = *(u32 *)args << 4;
-       return nv_ro32(imem, inst);
-}
-
-static int
-nv04_graph_mthd_bind_surf2d(struct nouveau_object *object, u32 mthd,
-                           void *args, u32 size)
-{
-       switch (nv04_graph_mthd_bind_class(object, args, size)) {
-       case 0x30:
-               nv04_graph_set_ctx1(object, 0x00004000, 0);
-               nv04_graph_set_ctx_val(object, 0x02000000, 0);
-               return 0;
-       case 0x42:
-               nv04_graph_set_ctx1(object, 0x00004000, 0);
-               nv04_graph_set_ctx_val(object, 0x02000000, 0x02000000);
-               return 0;
-       }
-       return 1;
-}
-
-static int
-nv04_graph_mthd_bind_surf2d_swzsurf(struct nouveau_object *object, u32 mthd,
-                                   void *args, u32 size)
-{
-       switch (nv04_graph_mthd_bind_class(object, args, size)) {
-       case 0x30:
-               nv04_graph_set_ctx1(object, 0x00004000, 0);
-               nv04_graph_set_ctx_val(object, 0x02000000, 0);
-               return 0;
-       case 0x42:
-               nv04_graph_set_ctx1(object, 0x00004000, 0);
-               nv04_graph_set_ctx_val(object, 0x02000000, 0x02000000);
-               return 0;
-       case 0x52:
-               nv04_graph_set_ctx1(object, 0x00004000, 0x00004000);
-               nv04_graph_set_ctx_val(object, 0x02000000, 0x02000000);
-               return 0;
-       }
-       return 1;
-}
-
-static int
-nv01_graph_mthd_bind_patt(struct nouveau_object *object, u32 mthd,
-                         void *args, u32 size)
-{
-       switch (nv04_graph_mthd_bind_class(object, args, size)) {
-       case 0x30:
-               nv04_graph_set_ctx_val(object, 0x08000000, 0);
-               return 0;
-       case 0x18:
-               nv04_graph_set_ctx_val(object, 0x08000000, 0x08000000);
-               return 0;
-       }
-       return 1;
-}
-
-static int
-nv04_graph_mthd_bind_patt(struct nouveau_object *object, u32 mthd,
-                         void *args, u32 size)
-{
-       switch (nv04_graph_mthd_bind_class(object, args, size)) {
-       case 0x30:
-               nv04_graph_set_ctx_val(object, 0x08000000, 0);
-               return 0;
-       case 0x44:
-               nv04_graph_set_ctx_val(object, 0x08000000, 0x08000000);
-               return 0;
-       }
-       return 1;
-}
-
-static int
-nv04_graph_mthd_bind_rop(struct nouveau_object *object, u32 mthd,
-                        void *args, u32 size)
-{
-       switch (nv04_graph_mthd_bind_class(object, args, size)) {
-       case 0x30:
-               nv04_graph_set_ctx_val(object, 0x10000000, 0);
-               return 0;
-       case 0x43:
-               nv04_graph_set_ctx_val(object, 0x10000000, 0x10000000);
-               return 0;
-       }
-       return 1;
-}
-
-static int
-nv04_graph_mthd_bind_beta1(struct nouveau_object *object, u32 mthd,
-                          void *args, u32 size)
-{
-       switch (nv04_graph_mthd_bind_class(object, args, size)) {
-       case 0x30:
-               nv04_graph_set_ctx_val(object, 0x20000000, 0);
-               return 0;
-       case 0x12:
-               nv04_graph_set_ctx_val(object, 0x20000000, 0x20000000);
-               return 0;
-       }
-       return 1;
-}
-
-static int
-nv04_graph_mthd_bind_beta4(struct nouveau_object *object, u32 mthd,
-                          void *args, u32 size)
-{
-       switch (nv04_graph_mthd_bind_class(object, args, size)) {
-       case 0x30:
-               nv04_graph_set_ctx_val(object, 0x40000000, 0);
-               return 0;
-       case 0x72:
-               nv04_graph_set_ctx_val(object, 0x40000000, 0x40000000);
-               return 0;
-       }
-       return 1;
-}
-
-static int
-nv04_graph_mthd_bind_surf_dst(struct nouveau_object *object, u32 mthd,
-                             void *args, u32 size)
-{
-       switch (nv04_graph_mthd_bind_class(object, args, size)) {
-       case 0x30:
-               nv04_graph_set_ctx_val(object, 0x02000000, 0);
-               return 0;
-       case 0x58:
-               nv04_graph_set_ctx_val(object, 0x02000000, 0x02000000);
-               return 0;
-       }
-       return 1;
-}
-
-static int
-nv04_graph_mthd_bind_surf_src(struct nouveau_object *object, u32 mthd,
-                             void *args, u32 size)
-{
-       switch (nv04_graph_mthd_bind_class(object, args, size)) {
-       case 0x30:
-               nv04_graph_set_ctx_val(object, 0x04000000, 0);
-               return 0;
-       case 0x59:
-               nv04_graph_set_ctx_val(object, 0x04000000, 0x04000000);
-               return 0;
-       }
-       return 1;
-}
-
-static int
-nv04_graph_mthd_bind_surf_color(struct nouveau_object *object, u32 mthd,
-                               void *args, u32 size)
-{
-       switch (nv04_graph_mthd_bind_class(object, args, size)) {
-       case 0x30:
-               nv04_graph_set_ctx_val(object, 0x02000000, 0);
-               return 0;
-       case 0x5a:
-               nv04_graph_set_ctx_val(object, 0x02000000, 0x02000000);
-               return 0;
-       }
-       return 1;
-}
-
-static int
-nv04_graph_mthd_bind_surf_zeta(struct nouveau_object *object, u32 mthd,
-                              void *args, u32 size)
-{
-       switch (nv04_graph_mthd_bind_class(object, args, size)) {
-       case 0x30:
-               nv04_graph_set_ctx_val(object, 0x04000000, 0);
-               return 0;
-       case 0x5b:
-               nv04_graph_set_ctx_val(object, 0x04000000, 0x04000000);
-               return 0;
-       }
-       return 1;
-}
-
-static int
-nv01_graph_mthd_bind_clip(struct nouveau_object *object, u32 mthd,
-                         void *args, u32 size)
-{
-       switch (nv04_graph_mthd_bind_class(object, args, size)) {
-       case 0x30:
-               nv04_graph_set_ctx1(object, 0x2000, 0);
-               return 0;
-       case 0x19:
-               nv04_graph_set_ctx1(object, 0x2000, 0x2000);
-               return 0;
-       }
-       return 1;
-}
-
-static int
-nv01_graph_mthd_bind_chroma(struct nouveau_object *object, u32 mthd,
-                           void *args, u32 size)
-{
-       switch (nv04_graph_mthd_bind_class(object, args, size)) {
-       case 0x30:
-               nv04_graph_set_ctx1(object, 0x1000, 0);
-               return 0;
-       /* Yes, for some reason even the old versions of objects
-        * accept 0x57 and not 0x17. Consistency be damned.
-        */
-       case 0x57:
-               nv04_graph_set_ctx1(object, 0x1000, 0x1000);
-               return 0;
-       }
-       return 1;
-}
-
-static struct nouveau_omthds
-nv03_graph_gdi_omthds[] = {
-       { 0x0184, 0x0184, nv01_graph_mthd_bind_patt },
-       { 0x0188, 0x0188, nv04_graph_mthd_bind_rop },
-       { 0x018c, 0x018c, nv04_graph_mthd_bind_beta1 },
-       { 0x0190, 0x0190, nv04_graph_mthd_bind_surf_dst },
-       { 0x02fc, 0x02fc, nv04_graph_mthd_set_operation },
-       {}
-};
-
-static struct nouveau_omthds
-nv04_graph_gdi_omthds[] = {
-       { 0x0188, 0x0188, nv04_graph_mthd_bind_patt },
-       { 0x018c, 0x018c, nv04_graph_mthd_bind_rop },
-       { 0x0190, 0x0190, nv04_graph_mthd_bind_beta1 },
-       { 0x0194, 0x0194, nv04_graph_mthd_bind_beta4 },
-       { 0x0198, 0x0198, nv04_graph_mthd_bind_surf2d },
-       { 0x02fc, 0x02fc, nv04_graph_mthd_set_operation },
-       {}
-};
-
-static struct nouveau_omthds
-nv01_graph_blit_omthds[] = {
-       { 0x0184, 0x0184, nv01_graph_mthd_bind_chroma },
-       { 0x0188, 0x0188, nv01_graph_mthd_bind_clip },
-       { 0x018c, 0x018c, nv01_graph_mthd_bind_patt },
-       { 0x0190, 0x0190, nv04_graph_mthd_bind_rop },
-       { 0x0194, 0x0194, nv04_graph_mthd_bind_beta1 },
-       { 0x0198, 0x0198, nv04_graph_mthd_bind_surf_dst },
-       { 0x019c, 0x019c, nv04_graph_mthd_bind_surf_src },
-       { 0x02fc, 0x02fc, nv04_graph_mthd_set_operation },
-       {}
-};
-
-static struct nouveau_omthds
-nv04_graph_blit_omthds[] = {
-       { 0x0184, 0x0184, nv01_graph_mthd_bind_chroma },
-       { 0x0188, 0x0188, nv01_graph_mthd_bind_clip },
-       { 0x018c, 0x018c, nv04_graph_mthd_bind_patt },
-       { 0x0190, 0x0190, nv04_graph_mthd_bind_rop },
-       { 0x0194, 0x0194, nv04_graph_mthd_bind_beta1 },
-       { 0x0198, 0x0198, nv04_graph_mthd_bind_beta4 },
-       { 0x019c, 0x019c, nv04_graph_mthd_bind_surf2d },
-       { 0x02fc, 0x02fc, nv04_graph_mthd_set_operation },
-       {}
-};
-
-static struct nouveau_omthds
-nv04_graph_iifc_omthds[] = {
-       { 0x0188, 0x0188, nv01_graph_mthd_bind_chroma },
-       { 0x018c, 0x018c, nv01_graph_mthd_bind_clip },
-       { 0x0190, 0x0190, nv04_graph_mthd_bind_patt },
-       { 0x0194, 0x0194, nv04_graph_mthd_bind_rop },
-       { 0x0198, 0x0198, nv04_graph_mthd_bind_beta1 },
-       { 0x019c, 0x019c, nv04_graph_mthd_bind_beta4 },
-       { 0x01a0, 0x01a0, nv04_graph_mthd_bind_surf2d_swzsurf },
-       { 0x03e4, 0x03e4, nv04_graph_mthd_set_operation },
-       {}
-};
-
-static struct nouveau_omthds
-nv01_graph_ifc_omthds[] = {
-       { 0x0184, 0x0184, nv01_graph_mthd_bind_chroma },
-       { 0x0188, 0x0188, nv01_graph_mthd_bind_clip },
-       { 0x018c, 0x018c, nv01_graph_mthd_bind_patt },
-       { 0x0190, 0x0190, nv04_graph_mthd_bind_rop },
-       { 0x0194, 0x0194, nv04_graph_mthd_bind_beta1 },
-       { 0x0198, 0x0198, nv04_graph_mthd_bind_surf_dst },
-       { 0x02fc, 0x02fc, nv04_graph_mthd_set_operation },
-       {}
-};
-
-static struct nouveau_omthds
-nv04_graph_ifc_omthds[] = {
-       { 0x0184, 0x0184, nv01_graph_mthd_bind_chroma },
-       { 0x0188, 0x0188, nv01_graph_mthd_bind_clip },
-       { 0x018c, 0x018c, nv04_graph_mthd_bind_patt },
-       { 0x0190, 0x0190, nv04_graph_mthd_bind_rop },
-       { 0x0194, 0x0194, nv04_graph_mthd_bind_beta1 },
-       { 0x0198, 0x0198, nv04_graph_mthd_bind_beta4 },
-       { 0x019c, 0x019c, nv04_graph_mthd_bind_surf2d },
-       { 0x02fc, 0x02fc, nv04_graph_mthd_set_operation },
-       {}
-};
-
-static struct nouveau_omthds
-nv03_graph_sifc_omthds[] = {
-       { 0x0184, 0x0184, nv01_graph_mthd_bind_chroma },
-       { 0x0188, 0x0188, nv01_graph_mthd_bind_patt },
-       { 0x018c, 0x018c, nv04_graph_mthd_bind_rop },
-       { 0x0190, 0x0190, nv04_graph_mthd_bind_beta1 },
-       { 0x0194, 0x0194, nv04_graph_mthd_bind_surf_dst },
-       { 0x02fc, 0x02fc, nv04_graph_mthd_set_operation },
-       {}
-};
-
-static struct nouveau_omthds
-nv04_graph_sifc_omthds[] = {
-       { 0x0184, 0x0184, nv01_graph_mthd_bind_chroma },
-       { 0x0188, 0x0188, nv04_graph_mthd_bind_patt },
-       { 0x018c, 0x018c, nv04_graph_mthd_bind_rop },
-       { 0x0190, 0x0190, nv04_graph_mthd_bind_beta1 },
-       { 0x0194, 0x0194, nv04_graph_mthd_bind_beta4 },
-       { 0x0198, 0x0198, nv04_graph_mthd_bind_surf2d },
-       { 0x02fc, 0x02fc, nv04_graph_mthd_set_operation },
-       {}
-};
-
-static struct nouveau_omthds
-nv03_graph_sifm_omthds[] = {
-       { 0x0188, 0x0188, nv01_graph_mthd_bind_patt },
-       { 0x018c, 0x018c, nv04_graph_mthd_bind_rop },
-       { 0x0190, 0x0190, nv04_graph_mthd_bind_beta1 },
-       { 0x0194, 0x0194, nv04_graph_mthd_bind_surf_dst },
-       { 0x0304, 0x0304, nv04_graph_mthd_set_operation },
-       {}
-};
-
-static struct nouveau_omthds
-nv04_graph_sifm_omthds[] = {
-       { 0x0188, 0x0188, nv04_graph_mthd_bind_patt },
-       { 0x018c, 0x018c, nv04_graph_mthd_bind_rop },
-       { 0x0190, 0x0190, nv04_graph_mthd_bind_beta1 },
-       { 0x0194, 0x0194, nv04_graph_mthd_bind_beta4 },
-       { 0x0198, 0x0198, nv04_graph_mthd_bind_surf2d },
-       { 0x0304, 0x0304, nv04_graph_mthd_set_operation },
-       {}
-};
-
-static struct nouveau_omthds
-nv04_graph_surf3d_omthds[] = {
-       { 0x02f8, 0x02f8, nv04_graph_mthd_surf3d_clip_h },
-       { 0x02fc, 0x02fc, nv04_graph_mthd_surf3d_clip_v },
-       {}
-};
-
-static struct nouveau_omthds
-nv03_graph_ttri_omthds[] = {
-       { 0x0188, 0x0188, nv01_graph_mthd_bind_clip },
-       { 0x018c, 0x018c, nv04_graph_mthd_bind_surf_color },
-       { 0x0190, 0x0190, nv04_graph_mthd_bind_surf_zeta },
-       {}
-};
-
-static struct nouveau_omthds
-nv01_graph_prim_omthds[] = {
-       { 0x0184, 0x0184, nv01_graph_mthd_bind_clip },
-       { 0x0188, 0x0188, nv01_graph_mthd_bind_patt },
-       { 0x018c, 0x018c, nv04_graph_mthd_bind_rop },
-       { 0x0190, 0x0190, nv04_graph_mthd_bind_beta1 },
-       { 0x0194, 0x0194, nv04_graph_mthd_bind_surf_dst },
-       { 0x02fc, 0x02fc, nv04_graph_mthd_set_operation },
-       {}
-};
-
-static struct nouveau_omthds
-nv04_graph_prim_omthds[] = {
-       { 0x0184, 0x0184, nv01_graph_mthd_bind_clip },
-       { 0x0188, 0x0188, nv04_graph_mthd_bind_patt },
-       { 0x018c, 0x018c, nv04_graph_mthd_bind_rop },
-       { 0x0190, 0x0190, nv04_graph_mthd_bind_beta1 },
-       { 0x0194, 0x0194, nv04_graph_mthd_bind_beta4 },
-       { 0x0198, 0x0198, nv04_graph_mthd_bind_surf2d },
-       { 0x02fc, 0x02fc, nv04_graph_mthd_set_operation },
-       {}
-};
-
-static int
-nv04_graph_object_ctor(struct nouveau_object *parent,
-                      struct nouveau_object *engine,
-                      struct nouveau_oclass *oclass, void *data, u32 size,
-                      struct nouveau_object **pobject)
-{
-       struct nouveau_gpuobj *obj;
-       int ret;
-
-       ret = nouveau_gpuobj_create(parent, engine, oclass, 0, parent,
-                                   16, 16, 0, &obj);
-       *pobject = nv_object(obj);
-       if (ret)
-               return ret;
-
-       nv_wo32(obj, 0x00, nv_mclass(obj));
-#ifdef __BIG_ENDIAN
-       nv_mo32(obj, 0x00, 0x00080000, 0x00080000);
-#endif
-       nv_wo32(obj, 0x04, 0x00000000);
-       nv_wo32(obj, 0x08, 0x00000000);
-       nv_wo32(obj, 0x0c, 0x00000000);
-       return 0;
-}
-
-struct nouveau_ofuncs
-nv04_graph_ofuncs = {
-       .ctor = nv04_graph_object_ctor,
-       .dtor = _nouveau_gpuobj_dtor,
-       .init = _nouveau_gpuobj_init,
-       .fini = _nouveau_gpuobj_fini,
-       .rd32 = _nouveau_gpuobj_rd32,
-       .wr32 = _nouveau_gpuobj_wr32,
-};
-
-static struct nouveau_oclass
-nv04_graph_sclass[] = {
-       { 0x0012, &nv04_graph_ofuncs }, /* beta1 */
-       { 0x0017, &nv04_graph_ofuncs }, /* chroma */
-       { 0x0018, &nv04_graph_ofuncs }, /* pattern (nv01) */
-       { 0x0019, &nv04_graph_ofuncs }, /* clip */
-       { 0x001c, &nv04_graph_ofuncs, nv01_graph_prim_omthds }, /* line */
-       { 0x001d, &nv04_graph_ofuncs, nv01_graph_prim_omthds }, /* tri */
-       { 0x001e, &nv04_graph_ofuncs, nv01_graph_prim_omthds }, /* rect */
-       { 0x001f, &nv04_graph_ofuncs, nv01_graph_blit_omthds },
-       { 0x0021, &nv04_graph_ofuncs, nv01_graph_ifc_omthds },
-       { 0x0030, &nv04_graph_ofuncs }, /* null */
-       { 0x0036, &nv04_graph_ofuncs, nv03_graph_sifc_omthds },
-       { 0x0037, &nv04_graph_ofuncs, nv03_graph_sifm_omthds },
-       { 0x0038, &nv04_graph_ofuncs }, /* dvd subpicture */
-       { 0x0039, &nv04_graph_ofuncs }, /* m2mf */
-       { 0x0042, &nv04_graph_ofuncs }, /* surf2d */
-       { 0x0043, &nv04_graph_ofuncs }, /* rop */
-       { 0x0044, &nv04_graph_ofuncs }, /* pattern */
-       { 0x0048, &nv04_graph_ofuncs, nv03_graph_ttri_omthds },
-       { 0x004a, &nv04_graph_ofuncs, nv04_graph_gdi_omthds },
-       { 0x004b, &nv04_graph_ofuncs, nv03_graph_gdi_omthds },
-       { 0x0052, &nv04_graph_ofuncs }, /* swzsurf */
-       { 0x0053, &nv04_graph_ofuncs, nv04_graph_surf3d_omthds },
-       { 0x0054, &nv04_graph_ofuncs }, /* ttri */
-       { 0x0055, &nv04_graph_ofuncs }, /* mtri */
-       { 0x0057, &nv04_graph_ofuncs }, /* chroma */
-       { 0x0058, &nv04_graph_ofuncs }, /* surf_dst */
-       { 0x0059, &nv04_graph_ofuncs }, /* surf_src */
-       { 0x005a, &nv04_graph_ofuncs }, /* surf_color */
-       { 0x005b, &nv04_graph_ofuncs }, /* surf_zeta */
-       { 0x005c, &nv04_graph_ofuncs, nv04_graph_prim_omthds }, /* line */
-       { 0x005d, &nv04_graph_ofuncs, nv04_graph_prim_omthds }, /* tri */
-       { 0x005e, &nv04_graph_ofuncs, nv04_graph_prim_omthds }, /* rect */
-       { 0x005f, &nv04_graph_ofuncs, nv04_graph_blit_omthds },
-       { 0x0060, &nv04_graph_ofuncs, nv04_graph_iifc_omthds },
-       { 0x0061, &nv04_graph_ofuncs, nv04_graph_ifc_omthds },
-       { 0x0064, &nv04_graph_ofuncs }, /* iifc (nv05) */
-       { 0x0065, &nv04_graph_ofuncs }, /* ifc (nv05) */
-       { 0x0066, &nv04_graph_ofuncs }, /* sifc (nv05) */
-       { 0x0072, &nv04_graph_ofuncs }, /* beta4 */
-       { 0x0076, &nv04_graph_ofuncs, nv04_graph_sifc_omthds },
-       { 0x0077, &nv04_graph_ofuncs, nv04_graph_sifm_omthds },
-       {},
-};
-
-/*******************************************************************************
- * PGRAPH context
- ******************************************************************************/
-
-static struct nv04_graph_chan *
-nv04_graph_channel(struct nv04_graph_priv *priv)
-{
-       struct nv04_graph_chan *chan = NULL;
-       if (nv_rd32(priv, NV04_PGRAPH_CTX_CONTROL) & 0x00010000) {
-               int chid = nv_rd32(priv, NV04_PGRAPH_CTX_USER) >> 24;
-               if (chid < ARRAY_SIZE(priv->chan))
-                       chan = priv->chan[chid];
-       }
-       return chan;
-}
-
-static int
-nv04_graph_load_context(struct nv04_graph_chan *chan, int chid)
-{
-       struct nv04_graph_priv *priv = nv04_graph_priv(chan);
-       int i;
-
-       for (i = 0; i < ARRAY_SIZE(nv04_graph_ctx_regs); i++)
-               nv_wr32(priv, nv04_graph_ctx_regs[i], chan->nv04[i]);
-
-       nv_wr32(priv, NV04_PGRAPH_CTX_CONTROL, 0x10010100);
-       nv_mask(priv, NV04_PGRAPH_CTX_USER, 0xff000000, chid << 24);
-       nv_mask(priv, NV04_PGRAPH_FFINTFC_ST2, 0xfff00000, 0x00000000);
-       return 0;
-}
-
-static int
-nv04_graph_unload_context(struct nv04_graph_chan *chan)
-{
-       struct nv04_graph_priv *priv = nv04_graph_priv(chan);
-       int i;
-
-       for (i = 0; i < ARRAY_SIZE(nv04_graph_ctx_regs); i++)
-               chan->nv04[i] = nv_rd32(priv, nv04_graph_ctx_regs[i]);
-
-       nv_wr32(priv, NV04_PGRAPH_CTX_CONTROL, 0x10000000);
-       nv_mask(priv, NV04_PGRAPH_CTX_USER, 0xff000000, 0x0f000000);
-       return 0;
-}
-
-static void
-nv04_graph_context_switch(struct nv04_graph_priv *priv)
-{
-       struct nv04_graph_chan *prev = NULL;
-       struct nv04_graph_chan *next = NULL;
-       unsigned long flags;
-       int chid;
-
-       spin_lock_irqsave(&priv->lock, flags);
-       nv04_graph_idle(priv);
-
-       /* If previous context is valid, we need to save it */
-       prev = nv04_graph_channel(priv);
-       if (prev)
-               nv04_graph_unload_context(prev);
-
-       /* load context for next channel */
-       chid = (nv_rd32(priv, NV04_PGRAPH_TRAPPED_ADDR) >> 24) & 0x0f;
-       next = priv->chan[chid];
-       if (next)
-               nv04_graph_load_context(next, chid);
-
-       spin_unlock_irqrestore(&priv->lock, flags);
-}
-
-static u32 *ctx_reg(struct nv04_graph_chan *chan, u32 reg)
-{
-       int i;
-
-       for (i = 0; i < ARRAY_SIZE(nv04_graph_ctx_regs); i++) {
-               if (nv04_graph_ctx_regs[i] == reg)
-                       return &chan->nv04[i];
-       }
-
-       return NULL;
-}
-
-static int
-nv04_graph_context_ctor(struct nouveau_object *parent,
-                       struct nouveau_object *engine,
-                       struct nouveau_oclass *oclass, void *data, u32 size,
-                       struct nouveau_object **pobject)
-{
-       struct nouveau_fifo_chan *fifo = (void *)parent;
-       struct nv04_graph_priv *priv = (void *)engine;
-       struct nv04_graph_chan *chan;
-       unsigned long flags;
-       int ret;
-
-       ret = nouveau_object_create(parent, engine, oclass, 0, &chan);
-       *pobject = nv_object(chan);
-       if (ret)
-               return ret;
-
-       spin_lock_irqsave(&priv->lock, flags);
-       if (priv->chan[fifo->chid]) {
-               *pobject = nv_object(priv->chan[fifo->chid]);
-               atomic_inc(&(*pobject)->refcount);
-               spin_unlock_irqrestore(&priv->lock, flags);
-               nouveau_object_destroy(&chan->base);
-               return 1;
-       }
-
-       *ctx_reg(chan, NV04_PGRAPH_DEBUG_3) = 0xfad4ff31;
-
-       priv->chan[fifo->chid] = chan;
-       chan->chid = fifo->chid;
-       spin_unlock_irqrestore(&priv->lock, flags);
-       return 0;
-}
-
-static void
-nv04_graph_context_dtor(struct nouveau_object *object)
-{
-       struct nv04_graph_priv *priv = (void *)object->engine;
-       struct nv04_graph_chan *chan = (void *)object;
-       unsigned long flags;
-
-       spin_lock_irqsave(&priv->lock, flags);
-       priv->chan[chan->chid] = NULL;
-       spin_unlock_irqrestore(&priv->lock, flags);
-
-       nouveau_object_destroy(&chan->base);
-}
-
-static int
-nv04_graph_context_fini(struct nouveau_object *object, bool suspend)
-{
-       struct nv04_graph_priv *priv = (void *)object->engine;
-       struct nv04_graph_chan *chan = (void *)object;
-       unsigned long flags;
-
-       spin_lock_irqsave(&priv->lock, flags);
-       nv_mask(priv, NV04_PGRAPH_FIFO, 0x00000001, 0x00000000);
-       if (nv04_graph_channel(priv) == chan)
-               nv04_graph_unload_context(chan);
-       nv_mask(priv, NV04_PGRAPH_FIFO, 0x00000001, 0x00000001);
-       spin_unlock_irqrestore(&priv->lock, flags);
-
-       return nouveau_object_fini(&chan->base, suspend);
-}
-
-static struct nouveau_oclass
-nv04_graph_cclass = {
-       .handle = NV_ENGCTX(GR, 0x04),
-       .ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nv04_graph_context_ctor,
-               .dtor = nv04_graph_context_dtor,
-               .init = nouveau_object_init,
-               .fini = nv04_graph_context_fini,
-       },
-};
-
-/*******************************************************************************
- * PGRAPH engine/subdev functions
- ******************************************************************************/
-
-bool
-nv04_graph_idle(void *obj)
-{
-       struct nouveau_graph *graph = nouveau_graph(obj);
-       u32 mask = 0xffffffff;
-
-       if (nv_device(obj)->card_type == NV_40)
-               mask &= ~NV40_PGRAPH_STATUS_SYNC_STALL;
-
-       if (!nv_wait(graph, NV04_PGRAPH_STATUS, mask, 0)) {
-               nv_error(graph, "idle timed out with status 0x%08x\n",
-                        nv_rd32(graph, NV04_PGRAPH_STATUS));
-               return false;
-       }
-
-       return true;
-}
-
-static const struct nouveau_bitfield
-nv04_graph_intr_name[] = {
-       { NV_PGRAPH_INTR_NOTIFY, "NOTIFY" },
-       {}
-};
-
-static const struct nouveau_bitfield
-nv04_graph_nstatus[] = {
-       { 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" },
-       {}
-};
-
-const struct nouveau_bitfield
-nv04_graph_nsource[] = {
-       { 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
-nv04_graph_intr(struct nouveau_subdev *subdev)
-{
-       struct nv04_graph_priv *priv = (void *)subdev;
-       struct nv04_graph_chan *chan = NULL;
-       struct nouveau_namedb *namedb = NULL;
-       struct nouveau_handle *handle = NULL;
-       u32 stat = nv_rd32(priv, NV03_PGRAPH_INTR);
-       u32 nsource = nv_rd32(priv, NV03_PGRAPH_NSOURCE);
-       u32 nstatus = nv_rd32(priv, NV03_PGRAPH_NSTATUS);
-       u32 addr = nv_rd32(priv, NV04_PGRAPH_TRAPPED_ADDR);
-       u32 chid = (addr & 0x0f000000) >> 24;
-       u32 subc = (addr & 0x0000e000) >> 13;
-       u32 mthd = (addr & 0x00001ffc);
-       u32 data = nv_rd32(priv, NV04_PGRAPH_TRAPPED_DATA);
-       u32 class = nv_rd32(priv, 0x400180 + subc * 4) & 0xff;
-       u32 inst = (nv_rd32(priv, 0x40016c) & 0xffff) << 4;
-       u32 show = stat;
-       unsigned long flags;
-
-       spin_lock_irqsave(&priv->lock, flags);
-       chan = priv->chan[chid];
-       if (chan)
-               namedb = (void *)nv_pclass(nv_object(chan), NV_NAMEDB_CLASS);
-       spin_unlock_irqrestore(&priv->lock, flags);
-
-       if (stat & NV_PGRAPH_INTR_NOTIFY) {
-               if (chan && (nsource & NV03_PGRAPH_NSOURCE_ILLEGAL_MTHD)) {
-                       handle = nouveau_namedb_get_vinst(namedb, inst);
-                       if (handle && !nv_call(handle->object, mthd, data))
-                               show &= ~NV_PGRAPH_INTR_NOTIFY;
-               }
-       }
-
-       if (stat & NV_PGRAPH_INTR_CONTEXT_SWITCH) {
-               nv_wr32(priv, NV03_PGRAPH_INTR, NV_PGRAPH_INTR_CONTEXT_SWITCH);
-               stat &= ~NV_PGRAPH_INTR_CONTEXT_SWITCH;
-               show &= ~NV_PGRAPH_INTR_CONTEXT_SWITCH;
-               nv04_graph_context_switch(priv);
-       }
-
-       nv_wr32(priv, NV03_PGRAPH_INTR, stat);
-       nv_wr32(priv, NV04_PGRAPH_FIFO, 0x00000001);
-
-       if (show) {
-               nv_error(priv, "%s", "");
-               nouveau_bitfield_print(nv04_graph_intr_name, show);
-               pr_cont(" nsource:");
-               nouveau_bitfield_print(nv04_graph_nsource, nsource);
-               pr_cont(" nstatus:");
-               nouveau_bitfield_print(nv04_graph_nstatus, nstatus);
-               pr_cont("\n");
-               nv_error(priv,
-                        "ch %d [%s] subc %d class 0x%04x mthd 0x%04x data 0x%08x\n",
-                        chid, nouveau_client_name(chan), subc, class, mthd,
-                        data);
-       }
-
-       nouveau_namedb_put(handle);
-}
-
-static int
-nv04_graph_ctor(struct nouveau_object *parent, struct nouveau_object *engine,
-               struct nouveau_oclass *oclass, void *data, u32 size,
-               struct nouveau_object **pobject)
-{
-       struct nv04_graph_priv *priv;
-       int ret;
-
-       ret = nouveau_graph_create(parent, engine, oclass, true, &priv);
-       *pobject = nv_object(priv);
-       if (ret)
-               return ret;
-
-       nv_subdev(priv)->unit = 0x00001000;
-       nv_subdev(priv)->intr = nv04_graph_intr;
-       nv_engine(priv)->cclass = &nv04_graph_cclass;
-       nv_engine(priv)->sclass = nv04_graph_sclass;
-       spin_lock_init(&priv->lock);
-       return 0;
-}
-
-static int
-nv04_graph_init(struct nouveau_object *object)
-{
-       struct nouveau_engine *engine = nv_engine(object);
-       struct nv04_graph_priv *priv = (void *)engine;
-       int ret;
-
-       ret = nouveau_graph_init(&priv->base);
-       if (ret)
-               return ret;
-
-       /* Enable PGRAPH interrupts */
-       nv_wr32(priv, NV03_PGRAPH_INTR, 0xFFFFFFFF);
-       nv_wr32(priv, NV03_PGRAPH_INTR_EN, 0xFFFFFFFF);
-
-       nv_wr32(priv, NV04_PGRAPH_VALID1, 0);
-       nv_wr32(priv, NV04_PGRAPH_VALID2, 0);
-       /*nv_wr32(priv, NV04_PGRAPH_DEBUG_0, 0x000001FF);
-       nv_wr32(priv, NV04_PGRAPH_DEBUG_0, 0x001FFFFF);*/
-       nv_wr32(priv, NV04_PGRAPH_DEBUG_0, 0x1231c000);
-       /*1231C000 blob, 001 haiku*/
-       /*V_WRITE(NV04_PGRAPH_DEBUG_1, 0xf2d91100);*/
-       nv_wr32(priv, NV04_PGRAPH_DEBUG_1, 0x72111100);
-       /*0x72111100 blob , 01 haiku*/
-       /*nv_wr32(priv, NV04_PGRAPH_DEBUG_2, 0x11d5f870);*/
-       nv_wr32(priv, NV04_PGRAPH_DEBUG_2, 0x11d5f071);
-       /*haiku same*/
-
-       /*nv_wr32(priv, NV04_PGRAPH_DEBUG_3, 0xfad4ff31);*/
-       nv_wr32(priv, NV04_PGRAPH_DEBUG_3, 0xf0d4ff31);
-       /*haiku and blob 10d4*/
-
-       nv_wr32(priv, NV04_PGRAPH_STATE        , 0xFFFFFFFF);
-       nv_wr32(priv, NV04_PGRAPH_CTX_CONTROL  , 0x10000100);
-       nv_mask(priv, NV04_PGRAPH_CTX_USER, 0xff000000, 0x0f000000);
-
-       /* These don't belong here, they're part of a per-channel context */
-       nv_wr32(priv, NV04_PGRAPH_PATTERN_SHAPE, 0x00000000);
-       nv_wr32(priv, NV04_PGRAPH_BETA_AND     , 0xFFFFFFFF);
-       return 0;
-}
-
-struct nouveau_oclass
-nv04_graph_oclass = {
-       .handle = NV_ENGINE(GR, 0x04),
-       .ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nv04_graph_ctor,
-               .dtor = _nouveau_graph_dtor,
-               .init = nv04_graph_init,
-               .fini = _nouveau_graph_fini,
-       },
-};
diff --git a/drivers/gpu/drm/nouveau/core/engine/graph/nv10.c b/drivers/gpu/drm/nouveau/core/engine/graph/nv10.c
deleted file mode 100644 (file)
index 2b12b09..0000000
+++ /dev/null
@@ -1,1319 +0,0 @@
-/*
- * Copyright 2007 Matthieu CASTET <castet.matthieu@free.fr>
- * 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 <core/client.h>
-#include <core/os.h>
-#include <core/handle.h>
-
-#include <subdev/fb.h>
-
-#include <engine/fifo.h>
-#include <engine/graph.h>
-
-#include "regs.h"
-
-struct pipe_state {
-       u32 pipe_0x0000[0x040/4];
-       u32 pipe_0x0040[0x010/4];
-       u32 pipe_0x0200[0x0c0/4];
-       u32 pipe_0x4400[0x080/4];
-       u32 pipe_0x6400[0x3b0/4];
-       u32 pipe_0x6800[0x2f0/4];
-       u32 pipe_0x6c00[0x030/4];
-       u32 pipe_0x7000[0x130/4];
-       u32 pipe_0x7400[0x0c0/4];
-       u32 pipe_0x7800[0x0c0/4];
-};
-
-static int nv10_graph_ctx_regs[] = {
-       NV10_PGRAPH_CTX_SWITCH(0),
-       NV10_PGRAPH_CTX_SWITCH(1),
-       NV10_PGRAPH_CTX_SWITCH(2),
-       NV10_PGRAPH_CTX_SWITCH(3),
-       NV10_PGRAPH_CTX_SWITCH(4),
-       NV10_PGRAPH_CTX_CACHE(0, 0),
-       NV10_PGRAPH_CTX_CACHE(0, 1),
-       NV10_PGRAPH_CTX_CACHE(0, 2),
-       NV10_PGRAPH_CTX_CACHE(0, 3),
-       NV10_PGRAPH_CTX_CACHE(0, 4),
-       NV10_PGRAPH_CTX_CACHE(1, 0),
-       NV10_PGRAPH_CTX_CACHE(1, 1),
-       NV10_PGRAPH_CTX_CACHE(1, 2),
-       NV10_PGRAPH_CTX_CACHE(1, 3),
-       NV10_PGRAPH_CTX_CACHE(1, 4),
-       NV10_PGRAPH_CTX_CACHE(2, 0),
-       NV10_PGRAPH_CTX_CACHE(2, 1),
-       NV10_PGRAPH_CTX_CACHE(2, 2),
-       NV10_PGRAPH_CTX_CACHE(2, 3),
-       NV10_PGRAPH_CTX_CACHE(2, 4),
-       NV10_PGRAPH_CTX_CACHE(3, 0),
-       NV10_PGRAPH_CTX_CACHE(3, 1),
-       NV10_PGRAPH_CTX_CACHE(3, 2),
-       NV10_PGRAPH_CTX_CACHE(3, 3),
-       NV10_PGRAPH_CTX_CACHE(3, 4),
-       NV10_PGRAPH_CTX_CACHE(4, 0),
-       NV10_PGRAPH_CTX_CACHE(4, 1),
-       NV10_PGRAPH_CTX_CACHE(4, 2),
-       NV10_PGRAPH_CTX_CACHE(4, 3),
-       NV10_PGRAPH_CTX_CACHE(4, 4),
-       NV10_PGRAPH_CTX_CACHE(5, 0),
-       NV10_PGRAPH_CTX_CACHE(5, 1),
-       NV10_PGRAPH_CTX_CACHE(5, 2),
-       NV10_PGRAPH_CTX_CACHE(5, 3),
-       NV10_PGRAPH_CTX_CACHE(5, 4),
-       NV10_PGRAPH_CTX_CACHE(6, 0),
-       NV10_PGRAPH_CTX_CACHE(6, 1),
-       NV10_PGRAPH_CTX_CACHE(6, 2),
-       NV10_PGRAPH_CTX_CACHE(6, 3),
-       NV10_PGRAPH_CTX_CACHE(6, 4),
-       NV10_PGRAPH_CTX_CACHE(7, 0),
-       NV10_PGRAPH_CTX_CACHE(7, 1),
-       NV10_PGRAPH_CTX_CACHE(7, 2),
-       NV10_PGRAPH_CTX_CACHE(7, 3),
-       NV10_PGRAPH_CTX_CACHE(7, 4),
-       NV10_PGRAPH_CTX_USER,
-       NV04_PGRAPH_DMA_START_0,
-       NV04_PGRAPH_DMA_START_1,
-       NV04_PGRAPH_DMA_LENGTH,
-       NV04_PGRAPH_DMA_MISC,
-       NV10_PGRAPH_DMA_PITCH,
-       NV04_PGRAPH_BOFFSET0,
-       NV04_PGRAPH_BBASE0,
-       NV04_PGRAPH_BLIMIT0,
-       NV04_PGRAPH_BOFFSET1,
-       NV04_PGRAPH_BBASE1,
-       NV04_PGRAPH_BLIMIT1,
-       NV04_PGRAPH_BOFFSET2,
-       NV04_PGRAPH_BBASE2,
-       NV04_PGRAPH_BLIMIT2,
-       NV04_PGRAPH_BOFFSET3,
-       NV04_PGRAPH_BBASE3,
-       NV04_PGRAPH_BLIMIT3,
-       NV04_PGRAPH_BOFFSET4,
-       NV04_PGRAPH_BBASE4,
-       NV04_PGRAPH_BLIMIT4,
-       NV04_PGRAPH_BOFFSET5,
-       NV04_PGRAPH_BBASE5,
-       NV04_PGRAPH_BLIMIT5,
-       NV04_PGRAPH_BPITCH0,
-       NV04_PGRAPH_BPITCH1,
-       NV04_PGRAPH_BPITCH2,
-       NV04_PGRAPH_BPITCH3,
-       NV04_PGRAPH_BPITCH4,
-       NV10_PGRAPH_SURFACE,
-       NV10_PGRAPH_STATE,
-       NV04_PGRAPH_BSWIZZLE2,
-       NV04_PGRAPH_BSWIZZLE5,
-       NV04_PGRAPH_BPIXEL,
-       NV10_PGRAPH_NOTIFY,
-       NV04_PGRAPH_PATT_COLOR0,
-       NV04_PGRAPH_PATT_COLOR1,
-       NV04_PGRAPH_PATT_COLORRAM, /* 64 values from 0x400900 to 0x4009fc */
-       0x00400904,
-       0x00400908,
-       0x0040090c,
-       0x00400910,
-       0x00400914,
-       0x00400918,
-       0x0040091c,
-       0x00400920,
-       0x00400924,
-       0x00400928,
-       0x0040092c,
-       0x00400930,
-       0x00400934,
-       0x00400938,
-       0x0040093c,
-       0x00400940,
-       0x00400944,
-       0x00400948,
-       0x0040094c,
-       0x00400950,
-       0x00400954,
-       0x00400958,
-       0x0040095c,
-       0x00400960,
-       0x00400964,
-       0x00400968,
-       0x0040096c,
-       0x00400970,
-       0x00400974,
-       0x00400978,
-       0x0040097c,
-       0x00400980,
-       0x00400984,
-       0x00400988,
-       0x0040098c,
-       0x00400990,
-       0x00400994,
-       0x00400998,
-       0x0040099c,
-       0x004009a0,
-       0x004009a4,
-       0x004009a8,
-       0x004009ac,
-       0x004009b0,
-       0x004009b4,
-       0x004009b8,
-       0x004009bc,
-       0x004009c0,
-       0x004009c4,
-       0x004009c8,
-       0x004009cc,
-       0x004009d0,
-       0x004009d4,
-       0x004009d8,
-       0x004009dc,
-       0x004009e0,
-       0x004009e4,
-       0x004009e8,
-       0x004009ec,
-       0x004009f0,
-       0x004009f4,
-       0x004009f8,
-       0x004009fc,
-       NV04_PGRAPH_PATTERN,    /* 2 values from 0x400808 to 0x40080c */
-       0x0040080c,
-       NV04_PGRAPH_PATTERN_SHAPE,
-       NV03_PGRAPH_MONO_COLOR0,
-       NV04_PGRAPH_ROP3,
-       NV04_PGRAPH_CHROMA,
-       NV04_PGRAPH_BETA_AND,
-       NV04_PGRAPH_BETA_PREMULT,
-       0x00400e70,
-       0x00400e74,
-       0x00400e78,
-       0x00400e7c,
-       0x00400e80,
-       0x00400e84,
-       0x00400e88,
-       0x00400e8c,
-       0x00400ea0,
-       0x00400ea4,
-       0x00400ea8,
-       0x00400e90,
-       0x00400e94,
-       0x00400e98,
-       0x00400e9c,
-       NV10_PGRAPH_WINDOWCLIP_HORIZONTAL, /* 8 values from 0x400f00-0x400f1c */
-       NV10_PGRAPH_WINDOWCLIP_VERTICAL,   /* 8 values from 0x400f20-0x400f3c */
-       0x00400f04,
-       0x00400f24,
-       0x00400f08,
-       0x00400f28,
-       0x00400f0c,
-       0x00400f2c,
-       0x00400f10,
-       0x00400f30,
-       0x00400f14,
-       0x00400f34,
-       0x00400f18,
-       0x00400f38,
-       0x00400f1c,
-       0x00400f3c,
-       NV10_PGRAPH_XFMODE0,
-       NV10_PGRAPH_XFMODE1,
-       NV10_PGRAPH_GLOBALSTATE0,
-       NV10_PGRAPH_GLOBALSTATE1,
-       NV04_PGRAPH_STORED_FMT,
-       NV04_PGRAPH_SOURCE_COLOR,
-       NV03_PGRAPH_ABS_X_RAM,  /* 32 values from 0x400400 to 0x40047c */
-       NV03_PGRAPH_ABS_Y_RAM,  /* 32 values from 0x400480 to 0x4004fc */
-       0x00400404,
-       0x00400484,
-       0x00400408,
-       0x00400488,
-       0x0040040c,
-       0x0040048c,
-       0x00400410,
-       0x00400490,
-       0x00400414,
-       0x00400494,
-       0x00400418,
-       0x00400498,
-       0x0040041c,
-       0x0040049c,
-       0x00400420,
-       0x004004a0,
-       0x00400424,
-       0x004004a4,
-       0x00400428,
-       0x004004a8,
-       0x0040042c,
-       0x004004ac,
-       0x00400430,
-       0x004004b0,
-       0x00400434,
-       0x004004b4,
-       0x00400438,
-       0x004004b8,
-       0x0040043c,
-       0x004004bc,
-       0x00400440,
-       0x004004c0,
-       0x00400444,
-       0x004004c4,
-       0x00400448,
-       0x004004c8,
-       0x0040044c,
-       0x004004cc,
-       0x00400450,
-       0x004004d0,
-       0x00400454,
-       0x004004d4,
-       0x00400458,
-       0x004004d8,
-       0x0040045c,
-       0x004004dc,
-       0x00400460,
-       0x004004e0,
-       0x00400464,
-       0x004004e4,
-       0x00400468,
-       0x004004e8,
-       0x0040046c,
-       0x004004ec,
-       0x00400470,
-       0x004004f0,
-       0x00400474,
-       0x004004f4,
-       0x00400478,
-       0x004004f8,
-       0x0040047c,
-       0x004004fc,
-       NV03_PGRAPH_ABS_UCLIP_XMIN,
-       NV03_PGRAPH_ABS_UCLIP_XMAX,
-       NV03_PGRAPH_ABS_UCLIP_YMIN,
-       NV03_PGRAPH_ABS_UCLIP_YMAX,
-       0x00400550,
-       0x00400558,
-       0x00400554,
-       0x0040055c,
-       NV03_PGRAPH_ABS_UCLIPA_XMIN,
-       NV03_PGRAPH_ABS_UCLIPA_XMAX,
-       NV03_PGRAPH_ABS_UCLIPA_YMIN,
-       NV03_PGRAPH_ABS_UCLIPA_YMAX,
-       NV03_PGRAPH_ABS_ICLIP_XMAX,
-       NV03_PGRAPH_ABS_ICLIP_YMAX,
-       NV03_PGRAPH_XY_LOGIC_MISC0,
-       NV03_PGRAPH_XY_LOGIC_MISC1,
-       NV03_PGRAPH_XY_LOGIC_MISC2,
-       NV03_PGRAPH_XY_LOGIC_MISC3,
-       NV03_PGRAPH_CLIPX_0,
-       NV03_PGRAPH_CLIPX_1,
-       NV03_PGRAPH_CLIPY_0,
-       NV03_PGRAPH_CLIPY_1,
-       NV10_PGRAPH_COMBINER0_IN_ALPHA,
-       NV10_PGRAPH_COMBINER1_IN_ALPHA,
-       NV10_PGRAPH_COMBINER0_IN_RGB,
-       NV10_PGRAPH_COMBINER1_IN_RGB,
-       NV10_PGRAPH_COMBINER_COLOR0,
-       NV10_PGRAPH_COMBINER_COLOR1,
-       NV10_PGRAPH_COMBINER0_OUT_ALPHA,
-       NV10_PGRAPH_COMBINER1_OUT_ALPHA,
-       NV10_PGRAPH_COMBINER0_OUT_RGB,
-       NV10_PGRAPH_COMBINER1_OUT_RGB,
-       NV10_PGRAPH_COMBINER_FINAL0,
-       NV10_PGRAPH_COMBINER_FINAL1,
-       0x00400e00,
-       0x00400e04,
-       0x00400e08,
-       0x00400e0c,
-       0x00400e10,
-       0x00400e14,
-       0x00400e18,
-       0x00400e1c,
-       0x00400e20,
-       0x00400e24,
-       0x00400e28,
-       0x00400e2c,
-       0x00400e30,
-       0x00400e34,
-       0x00400e38,
-       0x00400e3c,
-       NV04_PGRAPH_PASSTHRU_0,
-       NV04_PGRAPH_PASSTHRU_1,
-       NV04_PGRAPH_PASSTHRU_2,
-       NV10_PGRAPH_DIMX_TEXTURE,
-       NV10_PGRAPH_WDIMX_TEXTURE,
-       NV10_PGRAPH_DVD_COLORFMT,
-       NV10_PGRAPH_SCALED_FORMAT,
-       NV04_PGRAPH_MISC24_0,
-       NV04_PGRAPH_MISC24_1,
-       NV04_PGRAPH_MISC24_2,
-       NV03_PGRAPH_X_MISC,
-       NV03_PGRAPH_Y_MISC,
-       NV04_PGRAPH_VALID1,
-       NV04_PGRAPH_VALID2,
-};
-
-static int nv17_graph_ctx_regs[] = {
-       NV10_PGRAPH_DEBUG_4,
-       0x004006b0,
-       0x00400eac,
-       0x00400eb0,
-       0x00400eb4,
-       0x00400eb8,
-       0x00400ebc,
-       0x00400ec0,
-       0x00400ec4,
-       0x00400ec8,
-       0x00400ecc,
-       0x00400ed0,
-       0x00400ed4,
-       0x00400ed8,
-       0x00400edc,
-       0x00400ee0,
-       0x00400a00,
-       0x00400a04,
-};
-
-struct nv10_graph_priv {
-       struct nouveau_graph base;
-       struct nv10_graph_chan *chan[32];
-       spinlock_t lock;
-};
-
-struct nv10_graph_chan {
-       struct nouveau_object base;
-       int chid;
-       int nv10[ARRAY_SIZE(nv10_graph_ctx_regs)];
-       int nv17[ARRAY_SIZE(nv17_graph_ctx_regs)];
-       struct pipe_state pipe_state;
-       u32 lma_window[4];
-};
-
-
-static inline struct nv10_graph_priv *
-nv10_graph_priv(struct nv10_graph_chan *chan)
-{
-       return (void *)nv_object(chan)->engine;
-}
-
-/*******************************************************************************
- * Graphics object classes
- ******************************************************************************/
-
-#define PIPE_SAVE(priv, state, addr)                                   \
-       do {                                                            \
-               int __i;                                                \
-               nv_wr32(priv, NV10_PGRAPH_PIPE_ADDRESS, addr);          \
-               for (__i = 0; __i < ARRAY_SIZE(state); __i++)           \
-                       state[__i] = nv_rd32(priv, NV10_PGRAPH_PIPE_DATA); \
-       } while (0)
-
-#define PIPE_RESTORE(priv, state, addr)                                        \
-       do {                                                            \
-               int __i;                                                \
-               nv_wr32(priv, NV10_PGRAPH_PIPE_ADDRESS, addr);          \
-               for (__i = 0; __i < ARRAY_SIZE(state); __i++)           \
-                       nv_wr32(priv, NV10_PGRAPH_PIPE_DATA, state[__i]); \
-       } while (0)
-
-static struct nouveau_oclass
-nv10_graph_sclass[] = {
-       { 0x0012, &nv04_graph_ofuncs }, /* beta1 */
-       { 0x0019, &nv04_graph_ofuncs }, /* clip */
-       { 0x0030, &nv04_graph_ofuncs }, /* null */
-       { 0x0039, &nv04_graph_ofuncs }, /* m2mf */
-       { 0x0043, &nv04_graph_ofuncs }, /* rop */
-       { 0x0044, &nv04_graph_ofuncs }, /* pattern */
-       { 0x004a, &nv04_graph_ofuncs }, /* gdi */
-       { 0x0052, &nv04_graph_ofuncs }, /* swzsurf */
-       { 0x005f, &nv04_graph_ofuncs }, /* blit */
-       { 0x0062, &nv04_graph_ofuncs }, /* surf2d */
-       { 0x0072, &nv04_graph_ofuncs }, /* beta4 */
-       { 0x0089, &nv04_graph_ofuncs }, /* sifm */
-       { 0x008a, &nv04_graph_ofuncs }, /* ifc */
-       { 0x009f, &nv04_graph_ofuncs }, /* blit */
-       { 0x0093, &nv04_graph_ofuncs }, /* surf3d */
-       { 0x0094, &nv04_graph_ofuncs }, /* ttri */
-       { 0x0095, &nv04_graph_ofuncs }, /* mtri */
-       { 0x0056, &nv04_graph_ofuncs }, /* celcius */
-       {},
-};
-
-static struct nouveau_oclass
-nv15_graph_sclass[] = {
-       { 0x0012, &nv04_graph_ofuncs }, /* beta1 */
-       { 0x0019, &nv04_graph_ofuncs }, /* clip */
-       { 0x0030, &nv04_graph_ofuncs }, /* null */
-       { 0x0039, &nv04_graph_ofuncs }, /* m2mf */
-       { 0x0043, &nv04_graph_ofuncs }, /* rop */
-       { 0x0044, &nv04_graph_ofuncs }, /* pattern */
-       { 0x004a, &nv04_graph_ofuncs }, /* gdi */
-       { 0x0052, &nv04_graph_ofuncs }, /* swzsurf */
-       { 0x005f, &nv04_graph_ofuncs }, /* blit */
-       { 0x0062, &nv04_graph_ofuncs }, /* surf2d */
-       { 0x0072, &nv04_graph_ofuncs }, /* beta4 */
-       { 0x0089, &nv04_graph_ofuncs }, /* sifm */
-       { 0x008a, &nv04_graph_ofuncs }, /* ifc */
-       { 0x009f, &nv04_graph_ofuncs }, /* blit */
-       { 0x0093, &nv04_graph_ofuncs }, /* surf3d */
-       { 0x0094, &nv04_graph_ofuncs }, /* ttri */
-       { 0x0095, &nv04_graph_ofuncs }, /* mtri */
-       { 0x0096, &nv04_graph_ofuncs }, /* celcius */
-       {},
-};
-
-static int
-nv17_graph_mthd_lma_window(struct nouveau_object *object, u32 mthd,
-                          void *args, u32 size)
-{
-       struct nv10_graph_chan *chan = (void *)object->parent;
-       struct nv10_graph_priv *priv = nv10_graph_priv(chan);
-       struct pipe_state *pipe = &chan->pipe_state;
-       u32 pipe_0x0040[1], pipe_0x64c0[8], pipe_0x6a80[3], pipe_0x6ab0[3];
-       u32 xfmode0, xfmode1;
-       u32 data = *(u32 *)args;
-       int i;
-
-       chan->lma_window[(mthd - 0x1638) / 4] = data;
-
-       if (mthd != 0x1644)
-               return 0;
-
-       nv04_graph_idle(priv);
-
-       PIPE_SAVE(priv, pipe_0x0040, 0x0040);
-       PIPE_SAVE(priv, pipe->pipe_0x0200, 0x0200);
-
-       PIPE_RESTORE(priv, chan->lma_window, 0x6790);
-
-       nv04_graph_idle(priv);
-
-       xfmode0 = nv_rd32(priv, NV10_PGRAPH_XFMODE0);
-       xfmode1 = nv_rd32(priv, NV10_PGRAPH_XFMODE1);
-
-       PIPE_SAVE(priv, pipe->pipe_0x4400, 0x4400);
-       PIPE_SAVE(priv, pipe_0x64c0, 0x64c0);
-       PIPE_SAVE(priv, pipe_0x6ab0, 0x6ab0);
-       PIPE_SAVE(priv, pipe_0x6a80, 0x6a80);
-
-       nv04_graph_idle(priv);
-
-       nv_wr32(priv, NV10_PGRAPH_XFMODE0, 0x10000000);
-       nv_wr32(priv, NV10_PGRAPH_XFMODE1, 0x00000000);
-       nv_wr32(priv, NV10_PGRAPH_PIPE_ADDRESS, 0x000064c0);
-       for (i = 0; i < 4; i++)
-               nv_wr32(priv, NV10_PGRAPH_PIPE_DATA, 0x3f800000);
-       for (i = 0; i < 4; i++)
-               nv_wr32(priv, NV10_PGRAPH_PIPE_DATA, 0x00000000);
-
-       nv_wr32(priv, NV10_PGRAPH_PIPE_ADDRESS, 0x00006ab0);
-       for (i = 0; i < 3; i++)
-               nv_wr32(priv, NV10_PGRAPH_PIPE_DATA, 0x3f800000);
-
-       nv_wr32(priv, NV10_PGRAPH_PIPE_ADDRESS, 0x00006a80);
-       for (i = 0; i < 3; i++)
-               nv_wr32(priv, NV10_PGRAPH_PIPE_DATA, 0x00000000);
-
-       nv_wr32(priv, NV10_PGRAPH_PIPE_ADDRESS, 0x00000040);
-       nv_wr32(priv, NV10_PGRAPH_PIPE_DATA, 0x00000008);
-
-       PIPE_RESTORE(priv, pipe->pipe_0x0200, 0x0200);
-
-       nv04_graph_idle(priv);
-
-       PIPE_RESTORE(priv, pipe_0x0040, 0x0040);
-
-       nv_wr32(priv, NV10_PGRAPH_XFMODE0, xfmode0);
-       nv_wr32(priv, NV10_PGRAPH_XFMODE1, xfmode1);
-
-       PIPE_RESTORE(priv, pipe_0x64c0, 0x64c0);
-       PIPE_RESTORE(priv, pipe_0x6ab0, 0x6ab0);
-       PIPE_RESTORE(priv, pipe_0x6a80, 0x6a80);
-       PIPE_RESTORE(priv, pipe->pipe_0x4400, 0x4400);
-
-       nv_wr32(priv, NV10_PGRAPH_PIPE_ADDRESS, 0x000000c0);
-       nv_wr32(priv, NV10_PGRAPH_PIPE_DATA, 0x00000000);
-
-       nv04_graph_idle(priv);
-
-       return 0;
-}
-
-static int
-nv17_graph_mthd_lma_enable(struct nouveau_object *object, u32 mthd,
-                          void *args, u32 size)
-{
-       struct nv10_graph_chan *chan = (void *)object->parent;
-       struct nv10_graph_priv *priv = nv10_graph_priv(chan);
-
-       nv04_graph_idle(priv);
-
-       nv_mask(priv, NV10_PGRAPH_DEBUG_4, 0x00000100, 0x00000100);
-       nv_mask(priv, 0x4006b0, 0x08000000, 0x08000000);
-       return 0;
-}
-
-static struct nouveau_omthds
-nv17_celcius_omthds[] = {
-       { 0x1638, 0x1638, nv17_graph_mthd_lma_window },
-       { 0x163c, 0x163c, nv17_graph_mthd_lma_window },
-       { 0x1640, 0x1640, nv17_graph_mthd_lma_window },
-       { 0x1644, 0x1644, nv17_graph_mthd_lma_window },
-       { 0x1658, 0x1658, nv17_graph_mthd_lma_enable },
-       {}
-};
-
-static struct nouveau_oclass
-nv17_graph_sclass[] = {
-       { 0x0012, &nv04_graph_ofuncs }, /* beta1 */
-       { 0x0019, &nv04_graph_ofuncs }, /* clip */
-       { 0x0030, &nv04_graph_ofuncs }, /* null */
-       { 0x0039, &nv04_graph_ofuncs }, /* m2mf */
-       { 0x0043, &nv04_graph_ofuncs }, /* rop */
-       { 0x0044, &nv04_graph_ofuncs }, /* pattern */
-       { 0x004a, &nv04_graph_ofuncs }, /* gdi */
-       { 0x0052, &nv04_graph_ofuncs }, /* swzsurf */
-       { 0x005f, &nv04_graph_ofuncs }, /* blit */
-       { 0x0062, &nv04_graph_ofuncs }, /* surf2d */
-       { 0x0072, &nv04_graph_ofuncs }, /* beta4 */
-       { 0x0089, &nv04_graph_ofuncs }, /* sifm */
-       { 0x008a, &nv04_graph_ofuncs }, /* ifc */
-       { 0x009f, &nv04_graph_ofuncs }, /* blit */
-       { 0x0093, &nv04_graph_ofuncs }, /* surf3d */
-       { 0x0094, &nv04_graph_ofuncs }, /* ttri */
-       { 0x0095, &nv04_graph_ofuncs }, /* mtri */
-       { 0x0099, &nv04_graph_ofuncs, nv17_celcius_omthds },
-       {},
-};
-
-/*******************************************************************************
- * PGRAPH context
- ******************************************************************************/
-
-static struct nv10_graph_chan *
-nv10_graph_channel(struct nv10_graph_priv *priv)
-{
-       struct nv10_graph_chan *chan = NULL;
-       if (nv_rd32(priv, 0x400144) & 0x00010000) {
-               int chid = nv_rd32(priv, 0x400148) >> 24;
-               if (chid < ARRAY_SIZE(priv->chan))
-                       chan = priv->chan[chid];
-       }
-       return chan;
-}
-
-static void
-nv10_graph_save_pipe(struct nv10_graph_chan *chan)
-{
-       struct nv10_graph_priv *priv = nv10_graph_priv(chan);
-       struct pipe_state *pipe = &chan->pipe_state;
-
-       PIPE_SAVE(priv, pipe->pipe_0x4400, 0x4400);
-       PIPE_SAVE(priv, pipe->pipe_0x0200, 0x0200);
-       PIPE_SAVE(priv, pipe->pipe_0x6400, 0x6400);
-       PIPE_SAVE(priv, pipe->pipe_0x6800, 0x6800);
-       PIPE_SAVE(priv, pipe->pipe_0x6c00, 0x6c00);
-       PIPE_SAVE(priv, pipe->pipe_0x7000, 0x7000);
-       PIPE_SAVE(priv, pipe->pipe_0x7400, 0x7400);
-       PIPE_SAVE(priv, pipe->pipe_0x7800, 0x7800);
-       PIPE_SAVE(priv, pipe->pipe_0x0040, 0x0040);
-       PIPE_SAVE(priv, pipe->pipe_0x0000, 0x0000);
-}
-
-static void
-nv10_graph_load_pipe(struct nv10_graph_chan *chan)
-{
-       struct nv10_graph_priv *priv = nv10_graph_priv(chan);
-       struct pipe_state *pipe = &chan->pipe_state;
-       u32 xfmode0, xfmode1;
-       int i;
-
-       nv04_graph_idle(priv);
-       /* XXX check haiku comments */
-       xfmode0 = nv_rd32(priv, NV10_PGRAPH_XFMODE0);
-       xfmode1 = nv_rd32(priv, NV10_PGRAPH_XFMODE1);
-       nv_wr32(priv, NV10_PGRAPH_XFMODE0, 0x10000000);
-       nv_wr32(priv, NV10_PGRAPH_XFMODE1, 0x00000000);
-       nv_wr32(priv, NV10_PGRAPH_PIPE_ADDRESS, 0x000064c0);
-       for (i = 0; i < 4; i++)
-               nv_wr32(priv, NV10_PGRAPH_PIPE_DATA, 0x3f800000);
-       for (i = 0; i < 4; i++)
-               nv_wr32(priv, NV10_PGRAPH_PIPE_DATA, 0x00000000);
-
-       nv_wr32(priv, NV10_PGRAPH_PIPE_ADDRESS, 0x00006ab0);
-       for (i = 0; i < 3; i++)
-               nv_wr32(priv, NV10_PGRAPH_PIPE_DATA, 0x3f800000);
-
-       nv_wr32(priv, NV10_PGRAPH_PIPE_ADDRESS, 0x00006a80);
-       for (i = 0; i < 3; i++)
-               nv_wr32(priv, NV10_PGRAPH_PIPE_DATA, 0x00000000);
-
-       nv_wr32(priv, NV10_PGRAPH_PIPE_ADDRESS, 0x00000040);
-       nv_wr32(priv, NV10_PGRAPH_PIPE_DATA, 0x00000008);
-
-
-       PIPE_RESTORE(priv, pipe->pipe_0x0200, 0x0200);
-       nv04_graph_idle(priv);
-
-       /* restore XFMODE */
-       nv_wr32(priv, NV10_PGRAPH_XFMODE0, xfmode0);
-       nv_wr32(priv, NV10_PGRAPH_XFMODE1, xfmode1);
-       PIPE_RESTORE(priv, pipe->pipe_0x6400, 0x6400);
-       PIPE_RESTORE(priv, pipe->pipe_0x6800, 0x6800);
-       PIPE_RESTORE(priv, pipe->pipe_0x6c00, 0x6c00);
-       PIPE_RESTORE(priv, pipe->pipe_0x7000, 0x7000);
-       PIPE_RESTORE(priv, pipe->pipe_0x7400, 0x7400);
-       PIPE_RESTORE(priv, pipe->pipe_0x7800, 0x7800);
-       PIPE_RESTORE(priv, pipe->pipe_0x4400, 0x4400);
-       PIPE_RESTORE(priv, pipe->pipe_0x0000, 0x0000);
-       PIPE_RESTORE(priv, pipe->pipe_0x0040, 0x0040);
-       nv04_graph_idle(priv);
-}
-
-static void
-nv10_graph_create_pipe(struct nv10_graph_chan *chan)
-{
-       struct nv10_graph_priv *priv = nv10_graph_priv(chan);
-       struct pipe_state *pipe_state = &chan->pipe_state;
-       u32 *pipe_state_addr;
-       int i;
-#define PIPE_INIT(addr) \
-       do { \
-               pipe_state_addr = pipe_state->pipe_##addr; \
-       } while (0)
-#define PIPE_INIT_END(addr) \
-       do { \
-               u32 *__end_addr = pipe_state->pipe_##addr + \
-                               ARRAY_SIZE(pipe_state->pipe_##addr); \
-               if (pipe_state_addr != __end_addr) \
-                       nv_error(priv, "incomplete pipe init for 0x%x :  %p/%p\n", \
-                               addr, pipe_state_addr, __end_addr); \
-       } while (0)
-#define NV_WRITE_PIPE_INIT(value) *(pipe_state_addr++) = value
-
-       PIPE_INIT(0x0200);
-       for (i = 0; i < 48; i++)
-               NV_WRITE_PIPE_INIT(0x00000000);
-       PIPE_INIT_END(0x0200);
-
-       PIPE_INIT(0x6400);
-       for (i = 0; i < 211; i++)
-               NV_WRITE_PIPE_INIT(0x00000000);
-       NV_WRITE_PIPE_INIT(0x3f800000);
-       NV_WRITE_PIPE_INIT(0x40000000);
-       NV_WRITE_PIPE_INIT(0x40000000);
-       NV_WRITE_PIPE_INIT(0x40000000);
-       NV_WRITE_PIPE_INIT(0x40000000);
-       NV_WRITE_PIPE_INIT(0x00000000);
-       NV_WRITE_PIPE_INIT(0x00000000);
-       NV_WRITE_PIPE_INIT(0x3f800000);
-       NV_WRITE_PIPE_INIT(0x00000000);
-       NV_WRITE_PIPE_INIT(0x3f000000);
-       NV_WRITE_PIPE_INIT(0x3f000000);
-       NV_WRITE_PIPE_INIT(0x00000000);
-       NV_WRITE_PIPE_INIT(0x00000000);
-       NV_WRITE_PIPE_INIT(0x00000000);
-       NV_WRITE_PIPE_INIT(0x00000000);
-       NV_WRITE_PIPE_INIT(0x3f800000);
-       NV_WRITE_PIPE_INIT(0x00000000);
-       NV_WRITE_PIPE_INIT(0x00000000);
-       NV_WRITE_PIPE_INIT(0x00000000);
-       NV_WRITE_PIPE_INIT(0x00000000);
-       NV_WRITE_PIPE_INIT(0x00000000);
-       NV_WRITE_PIPE_INIT(0x3f800000);
-       NV_WRITE_PIPE_INIT(0x3f800000);
-       NV_WRITE_PIPE_INIT(0x3f800000);
-       NV_WRITE_PIPE_INIT(0x3f800000);
-       PIPE_INIT_END(0x6400);
-
-       PIPE_INIT(0x6800);
-       for (i = 0; i < 162; i++)
-               NV_WRITE_PIPE_INIT(0x00000000);
-       NV_WRITE_PIPE_INIT(0x3f800000);
-       for (i = 0; i < 25; i++)
-               NV_WRITE_PIPE_INIT(0x00000000);
-       PIPE_INIT_END(0x6800);
-
-       PIPE_INIT(0x6c00);
-       NV_WRITE_PIPE_INIT(0x00000000);
-       NV_WRITE_PIPE_INIT(0x00000000);
-       NV_WRITE_PIPE_INIT(0x00000000);
-       NV_WRITE_PIPE_INIT(0x00000000);
-       NV_WRITE_PIPE_INIT(0xbf800000);
-       NV_WRITE_PIPE_INIT(0x00000000);
-       NV_WRITE_PIPE_INIT(0x00000000);
-       NV_WRITE_PIPE_INIT(0x00000000);
-       NV_WRITE_PIPE_INIT(0x00000000);
-       NV_WRITE_PIPE_INIT(0x00000000);
-       NV_WRITE_PIPE_INIT(0x00000000);
-       NV_WRITE_PIPE_INIT(0x00000000);
-       PIPE_INIT_END(0x6c00);
-
-       PIPE_INIT(0x7000);
-       NV_WRITE_PIPE_INIT(0x00000000);
-       NV_WRITE_PIPE_INIT(0x00000000);
-       NV_WRITE_PIPE_INIT(0x00000000);
-       NV_WRITE_PIPE_INIT(0x00000000);
-       NV_WRITE_PIPE_INIT(0x00000000);
-       NV_WRITE_PIPE_INIT(0x00000000);
-       NV_WRITE_PIPE_INIT(0x00000000);
-       NV_WRITE_PIPE_INIT(0x00000000);
-       NV_WRITE_PIPE_INIT(0x00000000);
-       NV_WRITE_PIPE_INIT(0x00000000);
-       NV_WRITE_PIPE_INIT(0x00000000);
-       NV_WRITE_PIPE_INIT(0x00000000);
-       NV_WRITE_PIPE_INIT(0x7149f2ca);
-       NV_WRITE_PIPE_INIT(0x00000000);
-       NV_WRITE_PIPE_INIT(0x00000000);
-       NV_WRITE_PIPE_INIT(0x00000000);
-       NV_WRITE_PIPE_INIT(0x7149f2ca);
-       NV_WRITE_PIPE_INIT(0x00000000);
-       NV_WRITE_PIPE_INIT(0x00000000);
-       NV_WRITE_PIPE_INIT(0x00000000);
-       NV_WRITE_PIPE_INIT(0x7149f2ca);
-       NV_WRITE_PIPE_INIT(0x00000000);
-       NV_WRITE_PIPE_INIT(0x00000000);
-       NV_WRITE_PIPE_INIT(0x00000000);
-       NV_WRITE_PIPE_INIT(0x7149f2ca);
-       NV_WRITE_PIPE_INIT(0x00000000);
-       NV_WRITE_PIPE_INIT(0x00000000);
-       NV_WRITE_PIPE_INIT(0x00000000);
-       NV_WRITE_PIPE_INIT(0x7149f2ca);
-       NV_WRITE_PIPE_INIT(0x00000000);
-       NV_WRITE_PIPE_INIT(0x00000000);
-       NV_WRITE_PIPE_INIT(0x00000000);
-       NV_WRITE_PIPE_INIT(0x7149f2ca);
-       NV_WRITE_PIPE_INIT(0x00000000);
-       NV_WRITE_PIPE_INIT(0x00000000);
-       NV_WRITE_PIPE_INIT(0x00000000);
-       NV_WRITE_PIPE_INIT(0x7149f2ca);
-       NV_WRITE_PIPE_INIT(0x00000000);
-       NV_WRITE_PIPE_INIT(0x00000000);
-       NV_WRITE_PIPE_INIT(0x00000000);
-       NV_WRITE_PIPE_INIT(0x7149f2ca);
-       for (i = 0; i < 35; i++)
-               NV_WRITE_PIPE_INIT(0x00000000);
-       PIPE_INIT_END(0x7000);
-
-       PIPE_INIT(0x7400);
-       for (i = 0; i < 48; i++)
-               NV_WRITE_PIPE_INIT(0x00000000);
-       PIPE_INIT_END(0x7400);
-
-       PIPE_INIT(0x7800);
-       for (i = 0; i < 48; i++)
-               NV_WRITE_PIPE_INIT(0x00000000);
-       PIPE_INIT_END(0x7800);
-
-       PIPE_INIT(0x4400);
-       for (i = 0; i < 32; i++)
-               NV_WRITE_PIPE_INIT(0x00000000);
-       PIPE_INIT_END(0x4400);
-
-       PIPE_INIT(0x0000);
-       for (i = 0; i < 16; i++)
-               NV_WRITE_PIPE_INIT(0x00000000);
-       PIPE_INIT_END(0x0000);
-
-       PIPE_INIT(0x0040);
-       for (i = 0; i < 4; i++)
-               NV_WRITE_PIPE_INIT(0x00000000);
-       PIPE_INIT_END(0x0040);
-
-#undef PIPE_INIT
-#undef PIPE_INIT_END
-#undef NV_WRITE_PIPE_INIT
-}
-
-static int
-nv10_graph_ctx_regs_find_offset(struct nv10_graph_priv *priv, int reg)
-{
-       int i;
-       for (i = 0; i < ARRAY_SIZE(nv10_graph_ctx_regs); i++) {
-               if (nv10_graph_ctx_regs[i] == reg)
-                       return i;
-       }
-       nv_error(priv, "unknow offset nv10_ctx_regs %d\n", reg);
-       return -1;
-}
-
-static int
-nv17_graph_ctx_regs_find_offset(struct nv10_graph_priv *priv, int reg)
-{
-       int i;
-       for (i = 0; i < ARRAY_SIZE(nv17_graph_ctx_regs); i++) {
-               if (nv17_graph_ctx_regs[i] == reg)
-                       return i;
-       }
-       nv_error(priv, "unknow offset nv17_ctx_regs %d\n", reg);
-       return -1;
-}
-
-static void
-nv10_graph_load_dma_vtxbuf(struct nv10_graph_chan *chan, int chid, u32 inst)
-{
-       struct nv10_graph_priv *priv = nv10_graph_priv(chan);
-       u32 st2, st2_dl, st2_dh, fifo_ptr, fifo[0x60/4];
-       u32 ctx_user, ctx_switch[5];
-       int i, subchan = -1;
-
-       /* NV10TCL_DMA_VTXBUF (method 0x18c) modifies hidden state
-        * that cannot be restored via MMIO. Do it through the FIFO
-        * instead.
-        */
-
-       /* Look for a celsius object */
-       for (i = 0; i < 8; i++) {
-               int class = nv_rd32(priv, NV10_PGRAPH_CTX_CACHE(i, 0)) & 0xfff;
-
-               if (class == 0x56 || class == 0x96 || class == 0x99) {
-                       subchan = i;
-                       break;
-               }
-       }
-
-       if (subchan < 0 || !inst)
-               return;
-
-       /* Save the current ctx object */
-       ctx_user = nv_rd32(priv, NV10_PGRAPH_CTX_USER);
-       for (i = 0; i < 5; i++)
-               ctx_switch[i] = nv_rd32(priv, NV10_PGRAPH_CTX_SWITCH(i));
-
-       /* Save the FIFO state */
-       st2 = nv_rd32(priv, NV10_PGRAPH_FFINTFC_ST2);
-       st2_dl = nv_rd32(priv, NV10_PGRAPH_FFINTFC_ST2_DL);
-       st2_dh = nv_rd32(priv, NV10_PGRAPH_FFINTFC_ST2_DH);
-       fifo_ptr = nv_rd32(priv, NV10_PGRAPH_FFINTFC_FIFO_PTR);
-
-       for (i = 0; i < ARRAY_SIZE(fifo); i++)
-               fifo[i] = nv_rd32(priv, 0x4007a0 + 4 * i);
-
-       /* Switch to the celsius subchannel */
-       for (i = 0; i < 5; i++)
-               nv_wr32(priv, NV10_PGRAPH_CTX_SWITCH(i),
-                       nv_rd32(priv, NV10_PGRAPH_CTX_CACHE(subchan, i)));
-       nv_mask(priv, NV10_PGRAPH_CTX_USER, 0xe000, subchan << 13);
-
-       /* Inject NV10TCL_DMA_VTXBUF */
-       nv_wr32(priv, NV10_PGRAPH_FFINTFC_FIFO_PTR, 0);
-       nv_wr32(priv, NV10_PGRAPH_FFINTFC_ST2,
-               0x2c000000 | chid << 20 | subchan << 16 | 0x18c);
-       nv_wr32(priv, NV10_PGRAPH_FFINTFC_ST2_DL, inst);
-       nv_mask(priv, NV10_PGRAPH_CTX_CONTROL, 0, 0x10000);
-       nv_mask(priv, NV04_PGRAPH_FIFO, 0x00000001, 0x00000001);
-       nv_mask(priv, NV04_PGRAPH_FIFO, 0x00000001, 0x00000000);
-
-       /* Restore the FIFO state */
-       for (i = 0; i < ARRAY_SIZE(fifo); i++)
-               nv_wr32(priv, 0x4007a0 + 4 * i, fifo[i]);
-
-       nv_wr32(priv, NV10_PGRAPH_FFINTFC_FIFO_PTR, fifo_ptr);
-       nv_wr32(priv, NV10_PGRAPH_FFINTFC_ST2, st2);
-       nv_wr32(priv, NV10_PGRAPH_FFINTFC_ST2_DL, st2_dl);
-       nv_wr32(priv, NV10_PGRAPH_FFINTFC_ST2_DH, st2_dh);
-
-       /* Restore the current ctx object */
-       for (i = 0; i < 5; i++)
-               nv_wr32(priv, NV10_PGRAPH_CTX_SWITCH(i), ctx_switch[i]);
-       nv_wr32(priv, NV10_PGRAPH_CTX_USER, ctx_user);
-}
-
-static int
-nv10_graph_load_context(struct nv10_graph_chan *chan, int chid)
-{
-       struct nv10_graph_priv *priv = nv10_graph_priv(chan);
-       u32 inst;
-       int i;
-
-       for (i = 0; i < ARRAY_SIZE(nv10_graph_ctx_regs); i++)
-               nv_wr32(priv, nv10_graph_ctx_regs[i], chan->nv10[i]);
-
-       if (nv_device(priv)->card_type >= NV_11 &&
-           nv_device(priv)->chipset >= 0x17) {
-               for (i = 0; i < ARRAY_SIZE(nv17_graph_ctx_regs); i++)
-                       nv_wr32(priv, nv17_graph_ctx_regs[i], chan->nv17[i]);
-       }
-
-       nv10_graph_load_pipe(chan);
-
-       inst = nv_rd32(priv, NV10_PGRAPH_GLOBALSTATE1) & 0xffff;
-       nv10_graph_load_dma_vtxbuf(chan, chid, inst);
-
-       nv_wr32(priv, NV10_PGRAPH_CTX_CONTROL, 0x10010100);
-       nv_mask(priv, NV10_PGRAPH_CTX_USER, 0xff000000, chid << 24);
-       nv_mask(priv, NV10_PGRAPH_FFINTFC_ST2, 0x30000000, 0x00000000);
-       return 0;
-}
-
-static int
-nv10_graph_unload_context(struct nv10_graph_chan *chan)
-{
-       struct nv10_graph_priv *priv = nv10_graph_priv(chan);
-       int i;
-
-       for (i = 0; i < ARRAY_SIZE(nv10_graph_ctx_regs); i++)
-               chan->nv10[i] = nv_rd32(priv, nv10_graph_ctx_regs[i]);
-
-       if (nv_device(priv)->card_type >= NV_11 &&
-           nv_device(priv)->chipset >= 0x17) {
-               for (i = 0; i < ARRAY_SIZE(nv17_graph_ctx_regs); i++)
-                       chan->nv17[i] = nv_rd32(priv, nv17_graph_ctx_regs[i]);
-       }
-
-       nv10_graph_save_pipe(chan);
-
-       nv_wr32(priv, NV10_PGRAPH_CTX_CONTROL, 0x10000000);
-       nv_mask(priv, NV10_PGRAPH_CTX_USER, 0xff000000, 0x1f000000);
-       return 0;
-}
-
-static void
-nv10_graph_context_switch(struct nv10_graph_priv *priv)
-{
-       struct nv10_graph_chan *prev = NULL;
-       struct nv10_graph_chan *next = NULL;
-       unsigned long flags;
-       int chid;
-
-       spin_lock_irqsave(&priv->lock, flags);
-       nv04_graph_idle(priv);
-
-       /* If previous context is valid, we need to save it */
-       prev = nv10_graph_channel(priv);
-       if (prev)
-               nv10_graph_unload_context(prev);
-
-       /* load context for next channel */
-       chid = (nv_rd32(priv, NV04_PGRAPH_TRAPPED_ADDR) >> 20) & 0x1f;
-       next = priv->chan[chid];
-       if (next)
-               nv10_graph_load_context(next, chid);
-
-       spin_unlock_irqrestore(&priv->lock, flags);
-}
-
-#define NV_WRITE_CTX(reg, val) do { \
-       int offset = nv10_graph_ctx_regs_find_offset(priv, reg); \
-       if (offset > 0) \
-               chan->nv10[offset] = val; \
-       } while (0)
-
-#define NV17_WRITE_CTX(reg, val) do { \
-       int offset = nv17_graph_ctx_regs_find_offset(priv, reg); \
-       if (offset > 0) \
-               chan->nv17[offset] = val; \
-       } while (0)
-
-static int
-nv10_graph_context_ctor(struct nouveau_object *parent,
-                       struct nouveau_object *engine,
-                       struct nouveau_oclass *oclass, void *data, u32 size,
-                       struct nouveau_object **pobject)
-{
-       struct nouveau_fifo_chan *fifo = (void *)parent;
-       struct nv10_graph_priv *priv = (void *)engine;
-       struct nv10_graph_chan *chan;
-       unsigned long flags;
-       int ret;
-
-       ret = nouveau_object_create(parent, engine, oclass, 0, &chan);
-       *pobject = nv_object(chan);
-       if (ret)
-               return ret;
-
-       spin_lock_irqsave(&priv->lock, flags);
-       if (priv->chan[fifo->chid]) {
-               *pobject = nv_object(priv->chan[fifo->chid]);
-               atomic_inc(&(*pobject)->refcount);
-               spin_unlock_irqrestore(&priv->lock, flags);
-               nouveau_object_destroy(&chan->base);
-               return 1;
-       }
-
-       NV_WRITE_CTX(0x00400e88, 0x08000000);
-       NV_WRITE_CTX(0x00400e9c, 0x4b7fffff);
-       NV_WRITE_CTX(NV03_PGRAPH_XY_LOGIC_MISC0, 0x0001ffff);
-       NV_WRITE_CTX(0x00400e10, 0x00001000);
-       NV_WRITE_CTX(0x00400e14, 0x00001000);
-       NV_WRITE_CTX(0x00400e30, 0x00080008);
-       NV_WRITE_CTX(0x00400e34, 0x00080008);
-       if (nv_device(priv)->card_type >= NV_11 &&
-           nv_device(priv)->chipset >= 0x17) {
-               /* is it really needed ??? */
-               NV17_WRITE_CTX(NV10_PGRAPH_DEBUG_4,
-                                       nv_rd32(priv, NV10_PGRAPH_DEBUG_4));
-               NV17_WRITE_CTX(0x004006b0, nv_rd32(priv, 0x004006b0));
-               NV17_WRITE_CTX(0x00400eac, 0x0fff0000);
-               NV17_WRITE_CTX(0x00400eb0, 0x0fff0000);
-               NV17_WRITE_CTX(0x00400ec0, 0x00000080);
-               NV17_WRITE_CTX(0x00400ed0, 0x00000080);
-       }
-       NV_WRITE_CTX(NV10_PGRAPH_CTX_USER, chan->chid << 24);
-
-       nv10_graph_create_pipe(chan);
-
-       priv->chan[fifo->chid] = chan;
-       chan->chid = fifo->chid;
-       spin_unlock_irqrestore(&priv->lock, flags);
-       return 0;
-}
-
-static void
-nv10_graph_context_dtor(struct nouveau_object *object)
-{
-       struct nv10_graph_priv *priv = (void *)object->engine;
-       struct nv10_graph_chan *chan = (void *)object;
-       unsigned long flags;
-
-       spin_lock_irqsave(&priv->lock, flags);
-       priv->chan[chan->chid] = NULL;
-       spin_unlock_irqrestore(&priv->lock, flags);
-
-       nouveau_object_destroy(&chan->base);
-}
-
-static int
-nv10_graph_context_fini(struct nouveau_object *object, bool suspend)
-{
-       struct nv10_graph_priv *priv = (void *)object->engine;
-       struct nv10_graph_chan *chan = (void *)object;
-       unsigned long flags;
-
-       spin_lock_irqsave(&priv->lock, flags);
-       nv_mask(priv, NV04_PGRAPH_FIFO, 0x00000001, 0x00000000);
-       if (nv10_graph_channel(priv) == chan)
-               nv10_graph_unload_context(chan);
-       nv_mask(priv, NV04_PGRAPH_FIFO, 0x00000001, 0x00000001);
-       spin_unlock_irqrestore(&priv->lock, flags);
-
-       return nouveau_object_fini(&chan->base, suspend);
-}
-
-static struct nouveau_oclass
-nv10_graph_cclass = {
-       .handle = NV_ENGCTX(GR, 0x10),
-       .ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nv10_graph_context_ctor,
-               .dtor = nv10_graph_context_dtor,
-               .init = nouveau_object_init,
-               .fini = nv10_graph_context_fini,
-       },
-};
-
-/*******************************************************************************
- * PGRAPH engine/subdev functions
- ******************************************************************************/
-
-static void
-nv10_graph_tile_prog(struct nouveau_engine *engine, int i)
-{
-       struct nouveau_fb_tile *tile = &nouveau_fb(engine)->tile.region[i];
-       struct nouveau_fifo *pfifo = nouveau_fifo(engine);
-       struct nv10_graph_priv *priv = (void *)engine;
-       unsigned long flags;
-
-       pfifo->pause(pfifo, &flags);
-       nv04_graph_idle(priv);
-
-       nv_wr32(priv, NV10_PGRAPH_TLIMIT(i), tile->limit);
-       nv_wr32(priv, NV10_PGRAPH_TSIZE(i), tile->pitch);
-       nv_wr32(priv, NV10_PGRAPH_TILE(i), tile->addr);
-
-       pfifo->start(pfifo, &flags);
-}
-
-const struct nouveau_bitfield nv10_graph_intr_name[] = {
-       { NV_PGRAPH_INTR_NOTIFY, "NOTIFY" },
-       { NV_PGRAPH_INTR_ERROR,  "ERROR"  },
-       {}
-};
-
-const struct nouveau_bitfield nv10_graph_nstatus[] = {
-       { 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 void
-nv10_graph_intr(struct nouveau_subdev *subdev)
-{
-       struct nv10_graph_priv *priv = (void *)subdev;
-       struct nv10_graph_chan *chan = NULL;
-       struct nouveau_namedb *namedb = NULL;
-       struct nouveau_handle *handle = NULL;
-       u32 stat = nv_rd32(priv, NV03_PGRAPH_INTR);
-       u32 nsource = nv_rd32(priv, NV03_PGRAPH_NSOURCE);
-       u32 nstatus = nv_rd32(priv, NV03_PGRAPH_NSTATUS);
-       u32 addr = nv_rd32(priv, NV04_PGRAPH_TRAPPED_ADDR);
-       u32 chid = (addr & 0x01f00000) >> 20;
-       u32 subc = (addr & 0x00070000) >> 16;
-       u32 mthd = (addr & 0x00001ffc);
-       u32 data = nv_rd32(priv, NV04_PGRAPH_TRAPPED_DATA);
-       u32 class = nv_rd32(priv, 0x400160 + subc * 4) & 0xfff;
-       u32 show = stat;
-       unsigned long flags;
-
-       spin_lock_irqsave(&priv->lock, flags);
-       chan = priv->chan[chid];
-       if (chan)
-               namedb = (void *)nv_pclass(nv_object(chan), NV_NAMEDB_CLASS);
-       spin_unlock_irqrestore(&priv->lock, flags);
-
-       if (stat & NV_PGRAPH_INTR_ERROR) {
-               if (chan && (nsource & NV03_PGRAPH_NSOURCE_ILLEGAL_MTHD)) {
-                       handle = nouveau_namedb_get_class(namedb, class);
-                       if (handle && !nv_call(handle->object, mthd, data))
-                               show &= ~NV_PGRAPH_INTR_ERROR;
-               }
-       }
-
-       if (stat & NV_PGRAPH_INTR_CONTEXT_SWITCH) {
-               nv_wr32(priv, NV03_PGRAPH_INTR, NV_PGRAPH_INTR_CONTEXT_SWITCH);
-               stat &= ~NV_PGRAPH_INTR_CONTEXT_SWITCH;
-               show &= ~NV_PGRAPH_INTR_CONTEXT_SWITCH;
-               nv10_graph_context_switch(priv);
-       }
-
-       nv_wr32(priv, NV03_PGRAPH_INTR, stat);
-       nv_wr32(priv, NV04_PGRAPH_FIFO, 0x00000001);
-
-       if (show) {
-               nv_error(priv, "%s", "");
-               nouveau_bitfield_print(nv10_graph_intr_name, show);
-               pr_cont(" nsource:");
-               nouveau_bitfield_print(nv04_graph_nsource, nsource);
-               pr_cont(" nstatus:");
-               nouveau_bitfield_print(nv10_graph_nstatus, nstatus);
-               pr_cont("\n");
-               nv_error(priv,
-                        "ch %d [%s] subc %d class 0x%04x mthd 0x%04x data 0x%08x\n",
-                        chid, nouveau_client_name(chan), subc, class, mthd,
-                        data);
-       }
-
-       nouveau_namedb_put(handle);
-}
-
-static int
-nv10_graph_ctor(struct nouveau_object *parent, struct nouveau_object *engine,
-               struct nouveau_oclass *oclass, void *data, u32 size,
-               struct nouveau_object **pobject)
-{
-       struct nv10_graph_priv *priv;
-       int ret;
-
-       ret = nouveau_graph_create(parent, engine, oclass, true, &priv);
-       *pobject = nv_object(priv);
-       if (ret)
-               return ret;
-
-       nv_subdev(priv)->unit = 0x00001000;
-       nv_subdev(priv)->intr = nv10_graph_intr;
-       nv_engine(priv)->cclass = &nv10_graph_cclass;
-
-       if (nv_device(priv)->chipset <= 0x10)
-               nv_engine(priv)->sclass = nv10_graph_sclass;
-       else
-       if (nv_device(priv)->chipset <  0x17 ||
-           nv_device(priv)->card_type < NV_11)
-               nv_engine(priv)->sclass = nv15_graph_sclass;
-       else
-               nv_engine(priv)->sclass = nv17_graph_sclass;
-
-       nv_engine(priv)->tile_prog = nv10_graph_tile_prog;
-       spin_lock_init(&priv->lock);
-       return 0;
-}
-
-static void
-nv10_graph_dtor(struct nouveau_object *object)
-{
-       struct nv10_graph_priv *priv = (void *)object;
-       nouveau_graph_destroy(&priv->base);
-}
-
-static int
-nv10_graph_init(struct nouveau_object *object)
-{
-       struct nouveau_engine *engine = nv_engine(object);
-       struct nouveau_fb *pfb = nouveau_fb(object);
-       struct nv10_graph_priv *priv = (void *)engine;
-       int ret, i;
-
-       ret = nouveau_graph_init(&priv->base);
-       if (ret)
-               return ret;
-
-       nv_wr32(priv, NV03_PGRAPH_INTR   , 0xFFFFFFFF);
-       nv_wr32(priv, NV03_PGRAPH_INTR_EN, 0xFFFFFFFF);
-
-       nv_wr32(priv, NV04_PGRAPH_DEBUG_0, 0xFFFFFFFF);
-       nv_wr32(priv, NV04_PGRAPH_DEBUG_0, 0x00000000);
-       nv_wr32(priv, NV04_PGRAPH_DEBUG_1, 0x00118700);
-       /* nv_wr32(priv, NV04_PGRAPH_DEBUG_2, 0x24E00810); */ /* 0x25f92ad9 */
-       nv_wr32(priv, NV04_PGRAPH_DEBUG_2, 0x25f92ad9);
-       nv_wr32(priv, NV04_PGRAPH_DEBUG_3, 0x55DE0830 | (1 << 29) | (1 << 31));
-
-       if (nv_device(priv)->card_type >= NV_11 &&
-           nv_device(priv)->chipset >= 0x17) {
-               nv_wr32(priv, NV10_PGRAPH_DEBUG_4, 0x1f000000);
-               nv_wr32(priv, 0x400a10, 0x03ff3fb6);
-               nv_wr32(priv, 0x400838, 0x002f8684);
-               nv_wr32(priv, 0x40083c, 0x00115f3f);
-               nv_wr32(priv, 0x4006b0, 0x40000020);
-       } else {
-               nv_wr32(priv, NV10_PGRAPH_DEBUG_4, 0x00000000);
-       }
-
-       /* Turn all the tiling regions off. */
-       for (i = 0; i < pfb->tile.regions; i++)
-               engine->tile_prog(engine, i);
-
-       nv_wr32(priv, NV10_PGRAPH_CTX_SWITCH(0), 0x00000000);
-       nv_wr32(priv, NV10_PGRAPH_CTX_SWITCH(1), 0x00000000);
-       nv_wr32(priv, NV10_PGRAPH_CTX_SWITCH(2), 0x00000000);
-       nv_wr32(priv, NV10_PGRAPH_CTX_SWITCH(3), 0x00000000);
-       nv_wr32(priv, NV10_PGRAPH_CTX_SWITCH(4), 0x00000000);
-       nv_wr32(priv, NV10_PGRAPH_STATE, 0xFFFFFFFF);
-
-       nv_mask(priv, NV10_PGRAPH_CTX_USER, 0xff000000, 0x1f000000);
-       nv_wr32(priv, NV10_PGRAPH_CTX_CONTROL, 0x10000100);
-       nv_wr32(priv, NV10_PGRAPH_FFINTFC_ST2, 0x08000000);
-       return 0;
-}
-
-static int
-nv10_graph_fini(struct nouveau_object *object, bool suspend)
-{
-       struct nv10_graph_priv *priv = (void *)object;
-       return nouveau_graph_fini(&priv->base, suspend);
-}
-
-struct nouveau_oclass
-nv10_graph_oclass = {
-       .handle = NV_ENGINE(GR, 0x10),
-       .ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nv10_graph_ctor,
-               .dtor = nv10_graph_dtor,
-               .init = nv10_graph_init,
-               .fini = nv10_graph_fini,
-       },
-};
diff --git a/drivers/gpu/drm/nouveau/core/engine/graph/nv108.c b/drivers/gpu/drm/nouveau/core/engine/graph/nv108.c
deleted file mode 100644 (file)
index 2b0e8f4..0000000
+++ /dev/null
@@ -1,224 +0,0 @@
-/*
- * Copyright 2013 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 <bskeggs@redhat.com>
- */
-
-#include "nvc0.h"
-#include "ctxnvc0.h"
-
-/*******************************************************************************
- * Graphics object classes
- ******************************************************************************/
-
-static struct nouveau_oclass
-nv108_graph_sclass[] = {
-       { 0x902d, &nouveau_object_ofuncs },
-       { 0xa140, &nouveau_object_ofuncs },
-       { KEPLER_B, &nvc0_fermi_ofuncs },
-       { 0xa1c0, &nouveau_object_ofuncs },
-       {}
-};
-
-/*******************************************************************************
- * PGRAPH register lists
- ******************************************************************************/
-
-static const struct nvc0_graph_init
-nv108_graph_init_main_0[] = {
-       { 0x400080,   1, 0x04, 0x003083c2 },
-       { 0x400088,   1, 0x04, 0x0001bfe7 },
-       { 0x40008c,   1, 0x04, 0x00000000 },
-       { 0x400090,   1, 0x04, 0x00000030 },
-       { 0x40013c,   1, 0x04, 0x003901f7 },
-       { 0x400140,   1, 0x04, 0x00000100 },
-       { 0x400144,   1, 0x04, 0x00000000 },
-       { 0x400148,   1, 0x04, 0x00000110 },
-       { 0x400138,   1, 0x04, 0x00000000 },
-       { 0x400130,   2, 0x04, 0x00000000 },
-       { 0x400124,   1, 0x04, 0x00000002 },
-       {}
-};
-
-static const struct nvc0_graph_init
-nv108_graph_init_ds_0[] = {
-       { 0x405844,   1, 0x04, 0x00ffffff },
-       { 0x405850,   1, 0x04, 0x00000000 },
-       { 0x405900,   1, 0x04, 0x00000000 },
-       { 0x405908,   1, 0x04, 0x00000000 },
-       { 0x405928,   2, 0x04, 0x00000000 },
-       {}
-};
-
-const struct nvc0_graph_init
-nv108_graph_init_gpc_unk_0[] = {
-       { 0x418604,   1, 0x04, 0x00000000 },
-       { 0x418680,   1, 0x04, 0x00000000 },
-       { 0x418714,   1, 0x04, 0x00000000 },
-       { 0x418384,   2, 0x04, 0x00000000 },
-       {}
-};
-
-static const struct nvc0_graph_init
-nv108_graph_init_setup_1[] = {
-       { 0x4188c8,   2, 0x04, 0x00000000 },
-       { 0x4188d0,   1, 0x04, 0x00010000 },
-       { 0x4188d4,   1, 0x04, 0x00000201 },
-       {}
-};
-
-static const struct nvc0_graph_init
-nv108_graph_init_tex_0[] = {
-       { 0x419ab0,   1, 0x04, 0x00000000 },
-       { 0x419ac8,   1, 0x04, 0x00000000 },
-       { 0x419ab8,   1, 0x04, 0x000000e7 },
-       { 0x419abc,   2, 0x04, 0x00000000 },
-       { 0x419ab4,   1, 0x04, 0x00000000 },
-       { 0x419aa8,   2, 0x04, 0x00000000 },
-       {}
-};
-
-static const struct nvc0_graph_init
-nv108_graph_init_l1c_0[] = {
-       { 0x419c98,   1, 0x04, 0x00000000 },
-       { 0x419ca8,   1, 0x04, 0x00000000 },
-       { 0x419cb0,   1, 0x04, 0x01000000 },
-       { 0x419cb4,   1, 0x04, 0x00000000 },
-       { 0x419cb8,   1, 0x04, 0x00b08bea },
-       { 0x419c84,   1, 0x04, 0x00010384 },
-       { 0x419cbc,   1, 0x04, 0x281b3646 },
-       { 0x419cc0,   2, 0x04, 0x00000000 },
-       { 0x419c80,   1, 0x04, 0x00000230 },
-       { 0x419ccc,   2, 0x04, 0x00000000 },
-       {}
-};
-
-static const struct nvc0_graph_pack
-nv108_graph_pack_mmio[] = {
-       { nv108_graph_init_main_0 },
-       { nvf0_graph_init_fe_0 },
-       { nvc0_graph_init_pri_0 },
-       { nvc0_graph_init_rstr2d_0 },
-       { nvd9_graph_init_pd_0 },
-       { nv108_graph_init_ds_0 },
-       { nvc0_graph_init_scc_0 },
-       { nvf0_graph_init_sked_0 },
-       { nvf0_graph_init_cwd_0 },
-       { nvd9_graph_init_prop_0 },
-       { nv108_graph_init_gpc_unk_0 },
-       { nvc0_graph_init_setup_0 },
-       { nvc0_graph_init_crstr_0 },
-       { nv108_graph_init_setup_1 },
-       { nvc0_graph_init_zcull_0 },
-       { nvd9_graph_init_gpm_0 },
-       { nvf0_graph_init_gpc_unk_1 },
-       { nvc0_graph_init_gcc_0 },
-       { nve4_graph_init_tpccs_0 },
-       { nv108_graph_init_tex_0 },
-       { nve4_graph_init_pe_0 },
-       { nv108_graph_init_l1c_0 },
-       { nvc0_graph_init_mpc_0 },
-       { nvf0_graph_init_sm_0 },
-       { nvd7_graph_init_pes_0 },
-       { nvd7_graph_init_wwdx_0 },
-       { nvd7_graph_init_cbm_0 },
-       { nve4_graph_init_be_0 },
-       { nvc0_graph_init_fe_1 },
-       {}
-};
-
-/*******************************************************************************
- * PGRAPH engine/subdev functions
- ******************************************************************************/
-
-static int
-nv108_graph_fini(struct nouveau_object *object, bool suspend)
-{
-       struct nvc0_graph_priv *priv = (void *)object;
-       static const struct {
-               u32 addr;
-               u32 data;
-       } magic[] = {
-               { 0x020520, 0xfffffffc },
-               { 0x020524, 0xfffffffe },
-               { 0x020524, 0xfffffffc },
-               { 0x020524, 0xfffffff8 },
-               { 0x020524, 0xffffffe0 },
-               { 0x020530, 0xfffffffe },
-               { 0x02052c, 0xfffffffa },
-               { 0x02052c, 0xfffffff0 },
-               { 0x02052c, 0xffffffc0 },
-               { 0x02052c, 0xffffff00 },
-               { 0x02052c, 0xfffffc00 },
-               { 0x02052c, 0xfffcfc00 },
-               { 0x02052c, 0xfff0fc00 },
-               { 0x02052c, 0xff80fc00 },
-               { 0x020528, 0xfffffffe },
-               { 0x020528, 0xfffffffc },
-       };
-       int i;
-
-       nv_mask(priv, 0x000200, 0x08001000, 0x00000000);
-       nv_mask(priv, 0x0206b4, 0x00000000, 0x00000000);
-       for (i = 0; i < ARRAY_SIZE(magic); i++) {
-               nv_wr32(priv, magic[i].addr, magic[i].data);
-               nv_wait(priv, magic[i].addr, 0x80000000, 0x00000000);
-       }
-
-       return nouveau_graph_fini(&priv->base, suspend);
-}
-
-#include "fuc/hubnv108.fuc5.h"
-
-static struct nvc0_graph_ucode
-nv108_graph_fecs_ucode = {
-       .code.data = nv108_grhub_code,
-       .code.size = sizeof(nv108_grhub_code),
-       .data.data = nv108_grhub_data,
-       .data.size = sizeof(nv108_grhub_data),
-};
-
-#include "fuc/gpcnv108.fuc5.h"
-
-static struct nvc0_graph_ucode
-nv108_graph_gpccs_ucode = {
-       .code.data = nv108_grgpc_code,
-       .code.size = sizeof(nv108_grgpc_code),
-       .data.data = nv108_grgpc_data,
-       .data.size = sizeof(nv108_grgpc_data),
-};
-
-struct nouveau_oclass *
-nv108_graph_oclass = &(struct nvc0_graph_oclass) {
-       .base.handle = NV_ENGINE(GR, 0x08),
-       .base.ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nvc0_graph_ctor,
-               .dtor = nvc0_graph_dtor,
-               .init = nve4_graph_init,
-               .fini = nv108_graph_fini,
-       },
-       .cclass = &nv108_grctx_oclass,
-       .sclass =  nv108_graph_sclass,
-       .mmio = nv108_graph_pack_mmio,
-       .fecs.ucode = &nv108_graph_fecs_ucode,
-       .gpccs.ucode = &nv108_graph_gpccs_ucode,
-       .ppc_nr = 1,
-}.base;
diff --git a/drivers/gpu/drm/nouveau/core/engine/graph/nv20.c b/drivers/gpu/drm/nouveau/core/engine/graph/nv20.c
deleted file mode 100644 (file)
index ceb9c74..0000000
+++ /dev/null
@@ -1,383 +0,0 @@
-#include <core/client.h>
-#include <core/os.h>
-#include <core/engctx.h>
-#include <core/handle.h>
-#include <core/enum.h>
-
-#include <subdev/timer.h>
-#include <subdev/fb.h>
-
-#include <engine/graph.h>
-#include <engine/fifo.h>
-
-#include "nv20.h"
-#include "regs.h"
-
-/*******************************************************************************
- * Graphics object classes
- ******************************************************************************/
-
-static struct nouveau_oclass
-nv20_graph_sclass[] = {
-       { 0x0012, &nv04_graph_ofuncs, NULL }, /* beta1 */
-       { 0x0019, &nv04_graph_ofuncs, NULL }, /* clip */
-       { 0x0030, &nv04_graph_ofuncs, NULL }, /* null */
-       { 0x0039, &nv04_graph_ofuncs, NULL }, /* m2mf */
-       { 0x0043, &nv04_graph_ofuncs, NULL }, /* rop */
-       { 0x0044, &nv04_graph_ofuncs, NULL }, /* patt */
-       { 0x004a, &nv04_graph_ofuncs, NULL }, /* gdi */
-       { 0x0062, &nv04_graph_ofuncs, NULL }, /* surf2d */
-       { 0x0072, &nv04_graph_ofuncs, NULL }, /* beta4 */
-       { 0x0089, &nv04_graph_ofuncs, NULL }, /* sifm */
-       { 0x008a, &nv04_graph_ofuncs, NULL }, /* ifc */
-       { 0x0096, &nv04_graph_ofuncs, NULL }, /* celcius */
-       { 0x0097, &nv04_graph_ofuncs, NULL }, /* kelvin */
-       { 0x009e, &nv04_graph_ofuncs, NULL }, /* swzsurf */
-       { 0x009f, &nv04_graph_ofuncs, NULL }, /* imageblit */
-       {},
-};
-
-/*******************************************************************************
- * PGRAPH context
- ******************************************************************************/
-
-static int
-nv20_graph_context_ctor(struct nouveau_object *parent,
-                       struct nouveau_object *engine,
-                       struct nouveau_oclass *oclass, void *data, u32 size,
-                       struct nouveau_object **pobject)
-{
-       struct nv20_graph_chan *chan;
-       int ret, i;
-
-       ret = nouveau_graph_context_create(parent, engine, oclass, NULL,
-                                          0x37f0, 16, NVOBJ_FLAG_ZERO_ALLOC,
-                                          &chan);
-       *pobject = nv_object(chan);
-       if (ret)
-               return ret;
-
-       chan->chid = nouveau_fifo_chan(parent)->chid;
-
-       nv_wo32(chan, 0x0000, 0x00000001 | (chan->chid << 24));
-       nv_wo32(chan, 0x033c, 0xffff0000);
-       nv_wo32(chan, 0x03a0, 0x0fff0000);
-       nv_wo32(chan, 0x03a4, 0x0fff0000);
-       nv_wo32(chan, 0x047c, 0x00000101);
-       nv_wo32(chan, 0x0490, 0x00000111);
-       nv_wo32(chan, 0x04a8, 0x44400000);
-       for (i = 0x04d4; i <= 0x04e0; i += 4)
-               nv_wo32(chan, i, 0x00030303);
-       for (i = 0x04f4; i <= 0x0500; i += 4)
-               nv_wo32(chan, i, 0x00080000);
-       for (i = 0x050c; i <= 0x0518; i += 4)
-               nv_wo32(chan, i, 0x01012000);
-       for (i = 0x051c; i <= 0x0528; i += 4)
-               nv_wo32(chan, i, 0x000105b8);
-       for (i = 0x052c; i <= 0x0538; i += 4)
-               nv_wo32(chan, i, 0x00080008);
-       for (i = 0x055c; i <= 0x0598; i += 4)
-               nv_wo32(chan, i, 0x07ff0000);
-       nv_wo32(chan, 0x05a4, 0x4b7fffff);
-       nv_wo32(chan, 0x05fc, 0x00000001);
-       nv_wo32(chan, 0x0604, 0x00004000);
-       nv_wo32(chan, 0x0610, 0x00000001);
-       nv_wo32(chan, 0x0618, 0x00040000);
-       nv_wo32(chan, 0x061c, 0x00010000);
-       for (i = 0x1c1c; i <= 0x248c; i += 16) {
-               nv_wo32(chan, (i + 0), 0x10700ff9);
-               nv_wo32(chan, (i + 4), 0x0436086c);
-               nv_wo32(chan, (i + 8), 0x000c001b);
-       }
-       nv_wo32(chan, 0x281c, 0x3f800000);
-       nv_wo32(chan, 0x2830, 0x3f800000);
-       nv_wo32(chan, 0x285c, 0x40000000);
-       nv_wo32(chan, 0x2860, 0x3f800000);
-       nv_wo32(chan, 0x2864, 0x3f000000);
-       nv_wo32(chan, 0x286c, 0x40000000);
-       nv_wo32(chan, 0x2870, 0x3f800000);
-       nv_wo32(chan, 0x2878, 0xbf800000);
-       nv_wo32(chan, 0x2880, 0xbf800000);
-       nv_wo32(chan, 0x34a4, 0x000fe000);
-       nv_wo32(chan, 0x3530, 0x000003f8);
-       nv_wo32(chan, 0x3540, 0x002fe000);
-       for (i = 0x355c; i <= 0x3578; i += 4)
-               nv_wo32(chan, i, 0x001c527c);
-       return 0;
-}
-
-int
-nv20_graph_context_init(struct nouveau_object *object)
-{
-       struct nv20_graph_priv *priv = (void *)object->engine;
-       struct nv20_graph_chan *chan = (void *)object;
-       int ret;
-
-       ret = nouveau_graph_context_init(&chan->base);
-       if (ret)
-               return ret;
-
-       nv_wo32(priv->ctxtab, chan->chid * 4, nv_gpuobj(chan)->addr >> 4);
-       return 0;
-}
-
-int
-nv20_graph_context_fini(struct nouveau_object *object, bool suspend)
-{
-       struct nv20_graph_priv *priv = (void *)object->engine;
-       struct nv20_graph_chan *chan = (void *)object;
-       int chid = -1;
-
-       nv_mask(priv, 0x400720, 0x00000001, 0x00000000);
-       if (nv_rd32(priv, 0x400144) & 0x00010000)
-               chid = (nv_rd32(priv, 0x400148) & 0x1f000000) >> 24;
-       if (chan->chid == chid) {
-               nv_wr32(priv, 0x400784, nv_gpuobj(chan)->addr >> 4);
-               nv_wr32(priv, 0x400788, 0x00000002);
-               nv_wait(priv, 0x400700, 0xffffffff, 0x00000000);
-               nv_wr32(priv, 0x400144, 0x10000000);
-               nv_mask(priv, 0x400148, 0xff000000, 0x1f000000);
-       }
-       nv_mask(priv, 0x400720, 0x00000001, 0x00000001);
-
-       nv_wo32(priv->ctxtab, chan->chid * 4, 0x00000000);
-       return nouveau_graph_context_fini(&chan->base, suspend);
-}
-
-static struct nouveau_oclass
-nv20_graph_cclass = {
-       .handle = NV_ENGCTX(GR, 0x20),
-       .ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nv20_graph_context_ctor,
-               .dtor = _nouveau_graph_context_dtor,
-               .init = nv20_graph_context_init,
-               .fini = nv20_graph_context_fini,
-               .rd32 = _nouveau_graph_context_rd32,
-               .wr32 = _nouveau_graph_context_wr32,
-       },
-};
-
-/*******************************************************************************
- * PGRAPH engine/subdev functions
- ******************************************************************************/
-
-void
-nv20_graph_tile_prog(struct nouveau_engine *engine, int i)
-{
-       struct nouveau_fb_tile *tile = &nouveau_fb(engine)->tile.region[i];
-       struct nouveau_fifo *pfifo = nouveau_fifo(engine);
-       struct nv20_graph_priv *priv = (void *)engine;
-       unsigned long flags;
-
-       pfifo->pause(pfifo, &flags);
-       nv04_graph_idle(priv);
-
-       nv_wr32(priv, NV20_PGRAPH_TLIMIT(i), tile->limit);
-       nv_wr32(priv, NV20_PGRAPH_TSIZE(i), tile->pitch);
-       nv_wr32(priv, NV20_PGRAPH_TILE(i), tile->addr);
-
-       nv_wr32(priv, NV10_PGRAPH_RDI_INDEX, 0x00EA0030 + 4 * i);
-       nv_wr32(priv, NV10_PGRAPH_RDI_DATA, tile->limit);
-       nv_wr32(priv, NV10_PGRAPH_RDI_INDEX, 0x00EA0050 + 4 * i);
-       nv_wr32(priv, NV10_PGRAPH_RDI_DATA, tile->pitch);
-       nv_wr32(priv, NV10_PGRAPH_RDI_INDEX, 0x00EA0010 + 4 * i);
-       nv_wr32(priv, NV10_PGRAPH_RDI_DATA, tile->addr);
-
-       if (nv_device(engine)->chipset != 0x34) {
-               nv_wr32(priv, NV20_PGRAPH_ZCOMP(i), tile->zcomp);
-               nv_wr32(priv, NV10_PGRAPH_RDI_INDEX, 0x00ea0090 + 4 * i);
-               nv_wr32(priv, NV10_PGRAPH_RDI_DATA, tile->zcomp);
-       }
-
-       pfifo->start(pfifo, &flags);
-}
-
-void
-nv20_graph_intr(struct nouveau_subdev *subdev)
-{
-       struct nouveau_engine *engine = nv_engine(subdev);
-       struct nouveau_object *engctx;
-       struct nouveau_handle *handle;
-       struct nv20_graph_priv *priv = (void *)subdev;
-       u32 stat = nv_rd32(priv, NV03_PGRAPH_INTR);
-       u32 nsource = nv_rd32(priv, NV03_PGRAPH_NSOURCE);
-       u32 nstatus = nv_rd32(priv, NV03_PGRAPH_NSTATUS);
-       u32 addr = nv_rd32(priv, NV04_PGRAPH_TRAPPED_ADDR);
-       u32 chid = (addr & 0x01f00000) >> 20;
-       u32 subc = (addr & 0x00070000) >> 16;
-       u32 mthd = (addr & 0x00001ffc);
-       u32 data = nv_rd32(priv, NV04_PGRAPH_TRAPPED_DATA);
-       u32 class = nv_rd32(priv, 0x400160 + subc * 4) & 0xfff;
-       u32 show = stat;
-
-       engctx = nouveau_engctx_get(engine, chid);
-       if (stat & NV_PGRAPH_INTR_ERROR) {
-               if (nsource & NV03_PGRAPH_NSOURCE_ILLEGAL_MTHD) {
-                       handle = nouveau_handle_get_class(engctx, class);
-                       if (handle && !nv_call(handle->object, mthd, data))
-                               show &= ~NV_PGRAPH_INTR_ERROR;
-                       nouveau_handle_put(handle);
-               }
-       }
-
-       nv_wr32(priv, NV03_PGRAPH_INTR, stat);
-       nv_wr32(priv, NV04_PGRAPH_FIFO, 0x00000001);
-
-       if (show) {
-               nv_error(priv, "%s", "");
-               nouveau_bitfield_print(nv10_graph_intr_name, show);
-               pr_cont(" nsource:");
-               nouveau_bitfield_print(nv04_graph_nsource, nsource);
-               pr_cont(" nstatus:");
-               nouveau_bitfield_print(nv10_graph_nstatus, nstatus);
-               pr_cont("\n");
-               nv_error(priv,
-                        "ch %d [%s] subc %d class 0x%04x mthd 0x%04x data 0x%08x\n",
-                        chid, nouveau_client_name(engctx), subc, class, mthd,
-                        data);
-       }
-
-       nouveau_engctx_put(engctx);
-}
-
-static int
-nv20_graph_ctor(struct nouveau_object *parent, struct nouveau_object *engine,
-              struct nouveau_oclass *oclass, void *data, u32 size,
-              struct nouveau_object **pobject)
-{
-       struct nv20_graph_priv *priv;
-       int ret;
-
-       ret = nouveau_graph_create(parent, engine, oclass, true, &priv);
-       *pobject = nv_object(priv);
-       if (ret)
-               return ret;
-
-       ret = nouveau_gpuobj_new(nv_object(priv), NULL, 32 * 4, 16,
-                                NVOBJ_FLAG_ZERO_ALLOC, &priv->ctxtab);
-       if (ret)
-               return ret;
-
-       nv_subdev(priv)->unit = 0x00001000;
-       nv_subdev(priv)->intr = nv20_graph_intr;
-       nv_engine(priv)->cclass = &nv20_graph_cclass;
-       nv_engine(priv)->sclass = nv20_graph_sclass;
-       nv_engine(priv)->tile_prog = nv20_graph_tile_prog;
-       return 0;
-}
-
-void
-nv20_graph_dtor(struct nouveau_object *object)
-{
-       struct nv20_graph_priv *priv = (void *)object;
-       nouveau_gpuobj_ref(NULL, &priv->ctxtab);
-       nouveau_graph_destroy(&priv->base);
-}
-
-int
-nv20_graph_init(struct nouveau_object *object)
-{
-       struct nouveau_engine *engine = nv_engine(object);
-       struct nv20_graph_priv *priv = (void *)engine;
-       struct nouveau_fb *pfb = nouveau_fb(object);
-       u32 tmp, vramsz;
-       int ret, i;
-
-       ret = nouveau_graph_init(&priv->base);
-       if (ret)
-               return ret;
-
-       nv_wr32(priv, NV20_PGRAPH_CHANNEL_CTX_TABLE, priv->ctxtab->addr >> 4);
-
-       if (nv_device(priv)->chipset == 0x20) {
-               nv_wr32(priv, NV10_PGRAPH_RDI_INDEX, 0x003d0000);
-               for (i = 0; i < 15; i++)
-                       nv_wr32(priv, NV10_PGRAPH_RDI_DATA, 0x00000000);
-               nv_wait(priv, 0x400700, 0xffffffff, 0x00000000);
-       } else {
-               nv_wr32(priv, NV10_PGRAPH_RDI_INDEX, 0x02c80000);
-               for (i = 0; i < 32; i++)
-                       nv_wr32(priv, NV10_PGRAPH_RDI_DATA, 0x00000000);
-               nv_wait(priv, 0x400700, 0xffffffff, 0x00000000);
-       }
-
-       nv_wr32(priv, NV03_PGRAPH_INTR   , 0xFFFFFFFF);
-       nv_wr32(priv, NV03_PGRAPH_INTR_EN, 0xFFFFFFFF);
-
-       nv_wr32(priv, NV04_PGRAPH_DEBUG_0, 0xFFFFFFFF);
-       nv_wr32(priv, NV04_PGRAPH_DEBUG_0, 0x00000000);
-       nv_wr32(priv, NV04_PGRAPH_DEBUG_1, 0x00118700);
-       nv_wr32(priv, NV04_PGRAPH_DEBUG_3, 0xF3CE0475); /* 0x4 = auto ctx switch */
-       nv_wr32(priv, NV10_PGRAPH_DEBUG_4, 0x00000000);
-       nv_wr32(priv, 0x40009C           , 0x00000040);
-
-       if (nv_device(priv)->chipset >= 0x25) {
-               nv_wr32(priv, 0x400890, 0x00a8cfff);
-               nv_wr32(priv, 0x400610, 0x304B1FB6);
-               nv_wr32(priv, 0x400B80, 0x1cbd3883);
-               nv_wr32(priv, 0x400B84, 0x44000000);
-               nv_wr32(priv, 0x400098, 0x40000080);
-               nv_wr32(priv, 0x400B88, 0x000000ff);
-
-       } else {
-               nv_wr32(priv, 0x400880, 0x0008c7df);
-               nv_wr32(priv, 0x400094, 0x00000005);
-               nv_wr32(priv, 0x400B80, 0x45eae20e);
-               nv_wr32(priv, 0x400B84, 0x24000000);
-               nv_wr32(priv, 0x400098, 0x00000040);
-               nv_wr32(priv, NV10_PGRAPH_RDI_INDEX, 0x00E00038);
-               nv_wr32(priv, NV10_PGRAPH_RDI_DATA , 0x00000030);
-               nv_wr32(priv, NV10_PGRAPH_RDI_INDEX, 0x00E10038);
-               nv_wr32(priv, NV10_PGRAPH_RDI_DATA , 0x00000030);
-       }
-
-       /* Turn all the tiling regions off. */
-       for (i = 0; i < pfb->tile.regions; i++)
-               engine->tile_prog(engine, i);
-
-       nv_wr32(priv, 0x4009a0, nv_rd32(priv, 0x100324));
-       nv_wr32(priv, NV10_PGRAPH_RDI_INDEX, 0x00EA000C);
-       nv_wr32(priv, NV10_PGRAPH_RDI_DATA, nv_rd32(priv, 0x100324));
-
-       nv_wr32(priv, NV10_PGRAPH_CTX_CONTROL, 0x10000100);
-       nv_wr32(priv, NV10_PGRAPH_STATE      , 0xFFFFFFFF);
-
-       tmp = nv_rd32(priv, NV10_PGRAPH_SURFACE) & 0x0007ff00;
-       nv_wr32(priv, NV10_PGRAPH_SURFACE, tmp);
-       tmp = nv_rd32(priv, NV10_PGRAPH_SURFACE) | 0x00020100;
-       nv_wr32(priv, NV10_PGRAPH_SURFACE, tmp);
-
-       /* begin RAM config */
-       vramsz = nv_device_resource_len(nv_device(priv), 0) - 1;
-       nv_wr32(priv, 0x4009A4, nv_rd32(priv, 0x100200));
-       nv_wr32(priv, 0x4009A8, nv_rd32(priv, 0x100204));
-       nv_wr32(priv, NV10_PGRAPH_RDI_INDEX, 0x00EA0000);
-       nv_wr32(priv, NV10_PGRAPH_RDI_DATA , nv_rd32(priv, 0x100200));
-       nv_wr32(priv, NV10_PGRAPH_RDI_INDEX, 0x00EA0004);
-       nv_wr32(priv, NV10_PGRAPH_RDI_DATA , nv_rd32(priv, 0x100204));
-       nv_wr32(priv, 0x400820, 0);
-       nv_wr32(priv, 0x400824, 0);
-       nv_wr32(priv, 0x400864, vramsz - 1);
-       nv_wr32(priv, 0x400868, vramsz - 1);
-
-       /* interesting.. the below overwrites some of the tile setup above.. */
-       nv_wr32(priv, 0x400B20, 0x00000000);
-       nv_wr32(priv, 0x400B04, 0xFFFFFFFF);
-
-       nv_wr32(priv, NV03_PGRAPH_ABS_UCLIP_XMIN, 0);
-       nv_wr32(priv, NV03_PGRAPH_ABS_UCLIP_YMIN, 0);
-       nv_wr32(priv, NV03_PGRAPH_ABS_UCLIP_XMAX, 0x7fff);
-       nv_wr32(priv, NV03_PGRAPH_ABS_UCLIP_YMAX, 0x7fff);
-       return 0;
-}
-
-struct nouveau_oclass
-nv20_graph_oclass = {
-       .handle = NV_ENGINE(GR, 0x20),
-       .ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nv20_graph_ctor,
-               .dtor = nv20_graph_dtor,
-               .init = nv20_graph_init,
-               .fini = _nouveau_graph_fini,
-       },
-};
diff --git a/drivers/gpu/drm/nouveau/core/engine/graph/nv20.h b/drivers/gpu/drm/nouveau/core/engine/graph/nv20.h
deleted file mode 100644 (file)
index 2bea731..0000000
+++ /dev/null
@@ -1,31 +0,0 @@
-#ifndef __NV20_GRAPH_H__
-#define __NV20_GRAPH_H__
-
-#include <core/enum.h>
-
-#include <engine/graph.h>
-#include <engine/fifo.h>
-
-struct nv20_graph_priv {
-       struct nouveau_graph base;
-       struct nouveau_gpuobj *ctxtab;
-};
-
-struct nv20_graph_chan {
-       struct nouveau_graph_chan base;
-       int chid;
-};
-
-extern struct nouveau_oclass nv25_graph_sclass[];
-int  nv20_graph_context_init(struct nouveau_object *);
-int  nv20_graph_context_fini(struct nouveau_object *, bool);
-
-void nv20_graph_tile_prog(struct nouveau_engine *, int);
-void nv20_graph_intr(struct nouveau_subdev *);
-
-void nv20_graph_dtor(struct nouveau_object *);
-int  nv20_graph_init(struct nouveau_object *);
-
-int  nv30_graph_init(struct nouveau_object *);
-
-#endif
diff --git a/drivers/gpu/drm/nouveau/core/engine/graph/nv25.c b/drivers/gpu/drm/nouveau/core/engine/graph/nv25.c
deleted file mode 100644 (file)
index f8a6fdd..0000000
+++ /dev/null
@@ -1,166 +0,0 @@
-#include <core/os.h>
-#include <core/engctx.h>
-#include <core/enum.h>
-
-#include <subdev/timer.h>
-#include <subdev/fb.h>
-
-#include <engine/graph.h>
-
-#include "nv20.h"
-#include "regs.h"
-
-/*******************************************************************************
- * Graphics object classes
- ******************************************************************************/
-
-struct nouveau_oclass
-nv25_graph_sclass[] = {
-       { 0x0012, &nv04_graph_ofuncs, NULL }, /* beta1 */
-       { 0x0019, &nv04_graph_ofuncs, NULL }, /* clip */
-       { 0x0030, &nv04_graph_ofuncs, NULL }, /* null */
-       { 0x0039, &nv04_graph_ofuncs, NULL }, /* m2mf */
-       { 0x0043, &nv04_graph_ofuncs, NULL }, /* rop */
-       { 0x0044, &nv04_graph_ofuncs, NULL }, /* patt */
-       { 0x004a, &nv04_graph_ofuncs, NULL }, /* gdi */
-       { 0x0062, &nv04_graph_ofuncs, NULL }, /* surf2d */
-       { 0x0072, &nv04_graph_ofuncs, NULL }, /* beta4 */
-       { 0x0089, &nv04_graph_ofuncs, NULL }, /* sifm */
-       { 0x008a, &nv04_graph_ofuncs, NULL }, /* ifc */
-       { 0x0096, &nv04_graph_ofuncs, NULL }, /* celcius */
-       { 0x009e, &nv04_graph_ofuncs, NULL }, /* swzsurf */
-       { 0x009f, &nv04_graph_ofuncs, NULL }, /* imageblit */
-       { 0x0597, &nv04_graph_ofuncs, NULL }, /* kelvin */
-       {},
-};
-
-/*******************************************************************************
- * PGRAPH context
- ******************************************************************************/
-
-static int
-nv25_graph_context_ctor(struct nouveau_object *parent,
-                       struct nouveau_object *engine,
-                       struct nouveau_oclass *oclass, void *data, u32 size,
-                       struct nouveau_object **pobject)
-{
-       struct nv20_graph_chan *chan;
-       int ret, i;
-
-       ret = nouveau_graph_context_create(parent, engine, oclass, NULL, 0x3724,
-                                          16, NVOBJ_FLAG_ZERO_ALLOC, &chan);
-       *pobject = nv_object(chan);
-       if (ret)
-               return ret;
-
-       chan->chid = nouveau_fifo_chan(parent)->chid;
-
-       nv_wo32(chan, 0x0028, 0x00000001 | (chan->chid << 24));
-       nv_wo32(chan, 0x035c, 0xffff0000);
-       nv_wo32(chan, 0x03c0, 0x0fff0000);
-       nv_wo32(chan, 0x03c4, 0x0fff0000);
-       nv_wo32(chan, 0x049c, 0x00000101);
-       nv_wo32(chan, 0x04b0, 0x00000111);
-       nv_wo32(chan, 0x04c8, 0x00000080);
-       nv_wo32(chan, 0x04cc, 0xffff0000);
-       nv_wo32(chan, 0x04d0, 0x00000001);
-       nv_wo32(chan, 0x04e4, 0x44400000);
-       nv_wo32(chan, 0x04fc, 0x4b800000);
-       for (i = 0x0510; i <= 0x051c; i += 4)
-               nv_wo32(chan, i, 0x00030303);
-       for (i = 0x0530; i <= 0x053c; i += 4)
-               nv_wo32(chan, i, 0x00080000);
-       for (i = 0x0548; i <= 0x0554; i += 4)
-               nv_wo32(chan, i, 0x01012000);
-       for (i = 0x0558; i <= 0x0564; i += 4)
-               nv_wo32(chan, i, 0x000105b8);
-       for (i = 0x0568; i <= 0x0574; i += 4)
-               nv_wo32(chan, i, 0x00080008);
-       for (i = 0x0598; i <= 0x05d4; i += 4)
-               nv_wo32(chan, i, 0x07ff0000);
-       nv_wo32(chan, 0x05e0, 0x4b7fffff);
-       nv_wo32(chan, 0x0620, 0x00000080);
-       nv_wo32(chan, 0x0624, 0x30201000);
-       nv_wo32(chan, 0x0628, 0x70605040);
-       nv_wo32(chan, 0x062c, 0xb0a09080);
-       nv_wo32(chan, 0x0630, 0xf0e0d0c0);
-       nv_wo32(chan, 0x0664, 0x00000001);
-       nv_wo32(chan, 0x066c, 0x00004000);
-       nv_wo32(chan, 0x0678, 0x00000001);
-       nv_wo32(chan, 0x0680, 0x00040000);
-       nv_wo32(chan, 0x0684, 0x00010000);
-       for (i = 0x1b04; i <= 0x2374; i += 16) {
-               nv_wo32(chan, (i + 0), 0x10700ff9);
-               nv_wo32(chan, (i + 4), 0x0436086c);
-               nv_wo32(chan, (i + 8), 0x000c001b);
-       }
-       nv_wo32(chan, 0x2704, 0x3f800000);
-       nv_wo32(chan, 0x2718, 0x3f800000);
-       nv_wo32(chan, 0x2744, 0x40000000);
-       nv_wo32(chan, 0x2748, 0x3f800000);
-       nv_wo32(chan, 0x274c, 0x3f000000);
-       nv_wo32(chan, 0x2754, 0x40000000);
-       nv_wo32(chan, 0x2758, 0x3f800000);
-       nv_wo32(chan, 0x2760, 0xbf800000);
-       nv_wo32(chan, 0x2768, 0xbf800000);
-       nv_wo32(chan, 0x308c, 0x000fe000);
-       nv_wo32(chan, 0x3108, 0x000003f8);
-       nv_wo32(chan, 0x3468, 0x002fe000);
-       for (i = 0x3484; i <= 0x34a0; i += 4)
-               nv_wo32(chan, i, 0x001c527c);
-       return 0;
-}
-
-static struct nouveau_oclass
-nv25_graph_cclass = {
-       .handle = NV_ENGCTX(GR, 0x25),
-       .ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nv25_graph_context_ctor,
-               .dtor = _nouveau_graph_context_dtor,
-               .init = nv20_graph_context_init,
-               .fini = nv20_graph_context_fini,
-               .rd32 = _nouveau_graph_context_rd32,
-               .wr32 = _nouveau_graph_context_wr32,
-       },
-};
-
-/*******************************************************************************
- * PGRAPH engine/subdev functions
- ******************************************************************************/
-
-static int
-nv25_graph_ctor(struct nouveau_object *parent, struct nouveau_object *engine,
-              struct nouveau_oclass *oclass, void *data, u32 size,
-              struct nouveau_object **pobject)
-{
-       struct nv20_graph_priv *priv;
-       int ret;
-
-       ret = nouveau_graph_create(parent, engine, oclass, true, &priv);
-       *pobject = nv_object(priv);
-       if (ret)
-               return ret;
-
-       ret = nouveau_gpuobj_new(nv_object(priv), NULL, 32 * 4, 16,
-                                NVOBJ_FLAG_ZERO_ALLOC, &priv->ctxtab);
-       if (ret)
-               return ret;
-
-       nv_subdev(priv)->unit = 0x00001000;
-       nv_subdev(priv)->intr = nv20_graph_intr;
-       nv_engine(priv)->cclass = &nv25_graph_cclass;
-       nv_engine(priv)->sclass = nv25_graph_sclass;
-       nv_engine(priv)->tile_prog = nv20_graph_tile_prog;
-       return 0;
-}
-
-struct nouveau_oclass
-nv25_graph_oclass = {
-       .handle = NV_ENGINE(GR, 0x25),
-       .ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nv25_graph_ctor,
-               .dtor = nv20_graph_dtor,
-               .init = nv20_graph_init,
-               .fini = _nouveau_graph_fini,
-       },
-};
diff --git a/drivers/gpu/drm/nouveau/core/engine/graph/nv2a.c b/drivers/gpu/drm/nouveau/core/engine/graph/nv2a.c
deleted file mode 100644 (file)
index 5de9caa..0000000
+++ /dev/null
@@ -1,133 +0,0 @@
-#include <core/os.h>
-#include <core/engctx.h>
-#include <core/enum.h>
-
-#include <subdev/timer.h>
-#include <subdev/fb.h>
-
-#include <engine/graph.h>
-
-#include "nv20.h"
-#include "regs.h"
-
-/*******************************************************************************
- * PGRAPH context
- ******************************************************************************/
-
-static int
-nv2a_graph_context_ctor(struct nouveau_object *parent,
-                       struct nouveau_object *engine,
-                       struct nouveau_oclass *oclass, void *data, u32 size,
-                       struct nouveau_object **pobject)
-{
-       struct nv20_graph_chan *chan;
-       int ret, i;
-
-       ret = nouveau_graph_context_create(parent, engine, oclass, NULL, 0x36b0,
-                                          16, NVOBJ_FLAG_ZERO_ALLOC, &chan);
-       *pobject = nv_object(chan);
-       if (ret)
-               return ret;
-
-       chan->chid = nouveau_fifo_chan(parent)->chid;
-
-       nv_wo32(chan, 0x0000, 0x00000001 | (chan->chid << 24));
-       nv_wo32(chan, 0x033c, 0xffff0000);
-       nv_wo32(chan, 0x03a0, 0x0fff0000);
-       nv_wo32(chan, 0x03a4, 0x0fff0000);
-       nv_wo32(chan, 0x047c, 0x00000101);
-       nv_wo32(chan, 0x0490, 0x00000111);
-       nv_wo32(chan, 0x04a8, 0x44400000);
-       for (i = 0x04d4; i <= 0x04e0; i += 4)
-               nv_wo32(chan, i, 0x00030303);
-       for (i = 0x04f4; i <= 0x0500; i += 4)
-               nv_wo32(chan, i, 0x00080000);
-       for (i = 0x050c; i <= 0x0518; i += 4)
-               nv_wo32(chan, i, 0x01012000);
-       for (i = 0x051c; i <= 0x0528; i += 4)
-               nv_wo32(chan, i, 0x000105b8);
-       for (i = 0x052c; i <= 0x0538; i += 4)
-               nv_wo32(chan, i, 0x00080008);
-       for (i = 0x055c; i <= 0x0598; i += 4)
-               nv_wo32(chan, i, 0x07ff0000);
-       nv_wo32(chan, 0x05a4, 0x4b7fffff);
-       nv_wo32(chan, 0x05fc, 0x00000001);
-       nv_wo32(chan, 0x0604, 0x00004000);
-       nv_wo32(chan, 0x0610, 0x00000001);
-       nv_wo32(chan, 0x0618, 0x00040000);
-       nv_wo32(chan, 0x061c, 0x00010000);
-       for (i = 0x1a9c; i <= 0x22fc; i += 16) { /*XXX: check!! */
-               nv_wo32(chan, (i + 0), 0x10700ff9);
-               nv_wo32(chan, (i + 4), 0x0436086c);
-               nv_wo32(chan, (i + 8), 0x000c001b);
-       }
-       nv_wo32(chan, 0x269c, 0x3f800000);
-       nv_wo32(chan, 0x26b0, 0x3f800000);
-       nv_wo32(chan, 0x26dc, 0x40000000);
-       nv_wo32(chan, 0x26e0, 0x3f800000);
-       nv_wo32(chan, 0x26e4, 0x3f000000);
-       nv_wo32(chan, 0x26ec, 0x40000000);
-       nv_wo32(chan, 0x26f0, 0x3f800000);
-       nv_wo32(chan, 0x26f8, 0xbf800000);
-       nv_wo32(chan, 0x2700, 0xbf800000);
-       nv_wo32(chan, 0x3024, 0x000fe000);
-       nv_wo32(chan, 0x30a0, 0x000003f8);
-       nv_wo32(chan, 0x33fc, 0x002fe000);
-       for (i = 0x341c; i <= 0x3438; i += 4)
-               nv_wo32(chan, i, 0x001c527c);
-       return 0;
-}
-
-static struct nouveau_oclass
-nv2a_graph_cclass = {
-       .handle = NV_ENGCTX(GR, 0x2a),
-       .ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nv2a_graph_context_ctor,
-               .dtor = _nouveau_graph_context_dtor,
-               .init = nv20_graph_context_init,
-               .fini = nv20_graph_context_fini,
-               .rd32 = _nouveau_graph_context_rd32,
-               .wr32 = _nouveau_graph_context_wr32,
-       },
-};
-
-/*******************************************************************************
- * PGRAPH engine/subdev functions
- ******************************************************************************/
-
-static int
-nv2a_graph_ctor(struct nouveau_object *parent, struct nouveau_object *engine,
-              struct nouveau_oclass *oclass, void *data, u32 size,
-              struct nouveau_object **pobject)
-{
-       struct nv20_graph_priv *priv;
-       int ret;
-
-       ret = nouveau_graph_create(parent, engine, oclass, true, &priv);
-       *pobject = nv_object(priv);
-       if (ret)
-               return ret;
-
-       ret = nouveau_gpuobj_new(nv_object(priv), NULL, 32 * 4, 16,
-                                NVOBJ_FLAG_ZERO_ALLOC, &priv->ctxtab);
-       if (ret)
-               return ret;
-
-       nv_subdev(priv)->unit = 0x00001000;
-       nv_subdev(priv)->intr = nv20_graph_intr;
-       nv_engine(priv)->cclass = &nv2a_graph_cclass;
-       nv_engine(priv)->sclass = nv25_graph_sclass;
-       nv_engine(priv)->tile_prog = nv20_graph_tile_prog;
-       return 0;
-}
-
-struct nouveau_oclass
-nv2a_graph_oclass = {
-       .handle = NV_ENGINE(GR, 0x2a),
-       .ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nv2a_graph_ctor,
-               .dtor = nv20_graph_dtor,
-               .init = nv20_graph_init,
-               .fini = _nouveau_graph_fini,
-       },
-};
diff --git a/drivers/gpu/drm/nouveau/core/engine/graph/nv30.c b/drivers/gpu/drm/nouveau/core/engine/graph/nv30.c
deleted file mode 100644 (file)
index 2f9dbc7..0000000
+++ /dev/null
@@ -1,237 +0,0 @@
-#include <core/os.h>
-#include <core/engctx.h>
-#include <core/enum.h>
-
-#include <subdev/timer.h>
-#include <subdev/fb.h>
-
-#include <engine/graph.h>
-
-#include "nv20.h"
-#include "regs.h"
-
-/*******************************************************************************
- * Graphics object classes
- ******************************************************************************/
-
-static struct nouveau_oclass
-nv30_graph_sclass[] = {
-       { 0x0012, &nv04_graph_ofuncs, NULL }, /* beta1 */
-       { 0x0019, &nv04_graph_ofuncs, NULL }, /* clip */
-       { 0x0030, &nv04_graph_ofuncs, NULL }, /* null */
-       { 0x0039, &nv04_graph_ofuncs, NULL }, /* m2mf */
-       { 0x0043, &nv04_graph_ofuncs, NULL }, /* rop */
-       { 0x0044, &nv04_graph_ofuncs, NULL }, /* patt */
-       { 0x004a, &nv04_graph_ofuncs, NULL }, /* gdi */
-       { 0x0062, &nv04_graph_ofuncs, NULL }, /* surf2d */
-       { 0x0072, &nv04_graph_ofuncs, NULL }, /* beta4 */
-       { 0x0089, &nv04_graph_ofuncs, NULL }, /* sifm */
-       { 0x008a, &nv04_graph_ofuncs, NULL }, /* ifc */
-       { 0x009f, &nv04_graph_ofuncs, NULL }, /* imageblit */
-       { 0x0362, &nv04_graph_ofuncs, NULL }, /* surf2d (nv30) */
-       { 0x0389, &nv04_graph_ofuncs, NULL }, /* sifm (nv30) */
-       { 0x038a, &nv04_graph_ofuncs, NULL }, /* ifc (nv30) */
-       { 0x039e, &nv04_graph_ofuncs, NULL }, /* swzsurf (nv30) */
-       { 0x0397, &nv04_graph_ofuncs, NULL }, /* rankine */
-       {},
-};
-
-/*******************************************************************************
- * PGRAPH context
- ******************************************************************************/
-
-static int
-nv30_graph_context_ctor(struct nouveau_object *parent,
-                       struct nouveau_object *engine,
-                       struct nouveau_oclass *oclass, void *data, u32 size,
-                       struct nouveau_object **pobject)
-{
-       struct nv20_graph_chan *chan;
-       int ret, i;
-
-       ret = nouveau_graph_context_create(parent, engine, oclass, NULL, 0x5f48,
-                                          16, NVOBJ_FLAG_ZERO_ALLOC, &chan);
-       *pobject = nv_object(chan);
-       if (ret)
-               return ret;
-
-       chan->chid = nouveau_fifo_chan(parent)->chid;
-
-       nv_wo32(chan, 0x0028, 0x00000001 | (chan->chid << 24));
-       nv_wo32(chan, 0x0410, 0x00000101);
-       nv_wo32(chan, 0x0424, 0x00000111);
-       nv_wo32(chan, 0x0428, 0x00000060);
-       nv_wo32(chan, 0x0444, 0x00000080);
-       nv_wo32(chan, 0x0448, 0xffff0000);
-       nv_wo32(chan, 0x044c, 0x00000001);
-       nv_wo32(chan, 0x0460, 0x44400000);
-       nv_wo32(chan, 0x048c, 0xffff0000);
-       for (i = 0x04e0; i < 0x04e8; i += 4)
-               nv_wo32(chan, i, 0x0fff0000);
-       nv_wo32(chan, 0x04ec, 0x00011100);
-       for (i = 0x0508; i < 0x0548; i += 4)
-               nv_wo32(chan, i, 0x07ff0000);
-       nv_wo32(chan, 0x0550, 0x4b7fffff);
-       nv_wo32(chan, 0x058c, 0x00000080);
-       nv_wo32(chan, 0x0590, 0x30201000);
-       nv_wo32(chan, 0x0594, 0x70605040);
-       nv_wo32(chan, 0x0598, 0xb8a89888);
-       nv_wo32(chan, 0x059c, 0xf8e8d8c8);
-       nv_wo32(chan, 0x05b0, 0xb0000000);
-       for (i = 0x0600; i < 0x0640; i += 4)
-               nv_wo32(chan, i, 0x00010588);
-       for (i = 0x0640; i < 0x0680; i += 4)
-               nv_wo32(chan, i, 0x00030303);
-       for (i = 0x06c0; i < 0x0700; i += 4)
-               nv_wo32(chan, i, 0x0008aae4);
-       for (i = 0x0700; i < 0x0740; i += 4)
-               nv_wo32(chan, i, 0x01012000);
-       for (i = 0x0740; i < 0x0780; i += 4)
-               nv_wo32(chan, i, 0x00080008);
-       nv_wo32(chan, 0x085c, 0x00040000);
-       nv_wo32(chan, 0x0860, 0x00010000);
-       for (i = 0x0864; i < 0x0874; i += 4)
-               nv_wo32(chan, i, 0x00040004);
-       for (i = 0x1f18; i <= 0x3088 ; i += 16) {
-               nv_wo32(chan, i + 0, 0x10700ff9);
-               nv_wo32(chan, i + 1, 0x0436086c);
-               nv_wo32(chan, i + 2, 0x000c001b);
-       }
-       for (i = 0x30b8; i < 0x30c8; i += 4)
-               nv_wo32(chan, i, 0x0000ffff);
-       nv_wo32(chan, 0x344c, 0x3f800000);
-       nv_wo32(chan, 0x3808, 0x3f800000);
-       nv_wo32(chan, 0x381c, 0x3f800000);
-       nv_wo32(chan, 0x3848, 0x40000000);
-       nv_wo32(chan, 0x384c, 0x3f800000);
-       nv_wo32(chan, 0x3850, 0x3f000000);
-       nv_wo32(chan, 0x3858, 0x40000000);
-       nv_wo32(chan, 0x385c, 0x3f800000);
-       nv_wo32(chan, 0x3864, 0xbf800000);
-       nv_wo32(chan, 0x386c, 0xbf800000);
-       return 0;
-}
-
-static struct nouveau_oclass
-nv30_graph_cclass = {
-       .handle = NV_ENGCTX(GR, 0x30),
-       .ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nv30_graph_context_ctor,
-               .dtor = _nouveau_graph_context_dtor,
-               .init = nv20_graph_context_init,
-               .fini = nv20_graph_context_fini,
-               .rd32 = _nouveau_graph_context_rd32,
-               .wr32 = _nouveau_graph_context_wr32,
-       },
-};
-
-/*******************************************************************************
- * PGRAPH engine/subdev functions
- ******************************************************************************/
-
-static int
-nv30_graph_ctor(struct nouveau_object *parent, struct nouveau_object *engine,
-              struct nouveau_oclass *oclass, void *data, u32 size,
-              struct nouveau_object **pobject)
-{
-       struct nv20_graph_priv *priv;
-       int ret;
-
-       ret = nouveau_graph_create(parent, engine, oclass, true, &priv);
-       *pobject = nv_object(priv);
-       if (ret)
-               return ret;
-
-       ret = nouveau_gpuobj_new(nv_object(priv), NULL, 32 * 4, 16,
-                                NVOBJ_FLAG_ZERO_ALLOC, &priv->ctxtab);
-       if (ret)
-               return ret;
-
-       nv_subdev(priv)->unit = 0x00001000;
-       nv_subdev(priv)->intr = nv20_graph_intr;
-       nv_engine(priv)->cclass = &nv30_graph_cclass;
-       nv_engine(priv)->sclass = nv30_graph_sclass;
-       nv_engine(priv)->tile_prog = nv20_graph_tile_prog;
-       return 0;
-}
-
-int
-nv30_graph_init(struct nouveau_object *object)
-{
-       struct nouveau_engine *engine = nv_engine(object);
-       struct nv20_graph_priv *priv = (void *)engine;
-       struct nouveau_fb *pfb = nouveau_fb(object);
-       int ret, i;
-
-       ret = nouveau_graph_init(&priv->base);
-       if (ret)
-               return ret;
-
-       nv_wr32(priv, NV20_PGRAPH_CHANNEL_CTX_TABLE, priv->ctxtab->addr >> 4);
-
-       nv_wr32(priv, NV03_PGRAPH_INTR   , 0xFFFFFFFF);
-       nv_wr32(priv, NV03_PGRAPH_INTR_EN, 0xFFFFFFFF);
-
-       nv_wr32(priv, NV04_PGRAPH_DEBUG_0, 0xFFFFFFFF);
-       nv_wr32(priv, NV04_PGRAPH_DEBUG_0, 0x00000000);
-       nv_wr32(priv, NV04_PGRAPH_DEBUG_1, 0x401287c0);
-       nv_wr32(priv, 0x400890, 0x01b463ff);
-       nv_wr32(priv, NV04_PGRAPH_DEBUG_3, 0xf2de0475);
-       nv_wr32(priv, NV10_PGRAPH_DEBUG_4, 0x00008000);
-       nv_wr32(priv, NV04_PGRAPH_LIMIT_VIOL_PIX, 0xf04bdff6);
-       nv_wr32(priv, 0x400B80, 0x1003d888);
-       nv_wr32(priv, 0x400B84, 0x0c000000);
-       nv_wr32(priv, 0x400098, 0x00000000);
-       nv_wr32(priv, 0x40009C, 0x0005ad00);
-       nv_wr32(priv, 0x400B88, 0x62ff00ff); /* suspiciously like PGRAPH_DEBUG_2 */
-       nv_wr32(priv, 0x4000a0, 0x00000000);
-       nv_wr32(priv, 0x4000a4, 0x00000008);
-       nv_wr32(priv, 0x4008a8, 0xb784a400);
-       nv_wr32(priv, 0x400ba0, 0x002f8685);
-       nv_wr32(priv, 0x400ba4, 0x00231f3f);
-       nv_wr32(priv, 0x4008a4, 0x40000020);
-
-       if (nv_device(priv)->chipset == 0x34) {
-               nv_wr32(priv, NV10_PGRAPH_RDI_INDEX, 0x00EA0004);
-               nv_wr32(priv, NV10_PGRAPH_RDI_DATA , 0x00200201);
-               nv_wr32(priv, NV10_PGRAPH_RDI_INDEX, 0x00EA0008);
-               nv_wr32(priv, NV10_PGRAPH_RDI_DATA , 0x00000008);
-               nv_wr32(priv, NV10_PGRAPH_RDI_INDEX, 0x00EA0000);
-               nv_wr32(priv, NV10_PGRAPH_RDI_DATA , 0x00000032);
-               nv_wr32(priv, NV10_PGRAPH_RDI_INDEX, 0x00E00004);
-               nv_wr32(priv, NV10_PGRAPH_RDI_DATA , 0x00000002);
-       }
-
-       nv_wr32(priv, 0x4000c0, 0x00000016);
-
-       /* Turn all the tiling regions off. */
-       for (i = 0; i < pfb->tile.regions; i++)
-               engine->tile_prog(engine, i);
-
-       nv_wr32(priv, NV10_PGRAPH_CTX_CONTROL, 0x10000100);
-       nv_wr32(priv, NV10_PGRAPH_STATE      , 0xFFFFFFFF);
-       nv_wr32(priv, 0x0040075c             , 0x00000001);
-
-       /* begin RAM config */
-       /* vramsz = pci_resource_len(priv->dev->pdev, 0) - 1; */
-       nv_wr32(priv, 0x4009A4, nv_rd32(priv, 0x100200));
-       nv_wr32(priv, 0x4009A8, nv_rd32(priv, 0x100204));
-       if (nv_device(priv)->chipset != 0x34) {
-               nv_wr32(priv, 0x400750, 0x00EA0000);
-               nv_wr32(priv, 0x400754, nv_rd32(priv, 0x100200));
-               nv_wr32(priv, 0x400750, 0x00EA0004);
-               nv_wr32(priv, 0x400754, nv_rd32(priv, 0x100204));
-       }
-       return 0;
-}
-
-struct nouveau_oclass
-nv30_graph_oclass = {
-       .handle = NV_ENGINE(GR, 0x30),
-       .ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nv30_graph_ctor,
-               .dtor = nv20_graph_dtor,
-               .init = nv30_graph_init,
-               .fini = _nouveau_graph_fini,
-       },
-};
diff --git a/drivers/gpu/drm/nouveau/core/engine/graph/nv34.c b/drivers/gpu/drm/nouveau/core/engine/graph/nv34.c
deleted file mode 100644 (file)
index 34dd26c..0000000
+++ /dev/null
@@ -1,167 +0,0 @@
-#include <core/os.h>
-#include <core/engctx.h>
-#include <core/enum.h>
-
-#include <subdev/timer.h>
-#include <subdev/fb.h>
-
-#include <engine/graph.h>
-
-#include "nv20.h"
-#include "regs.h"
-
-/*******************************************************************************
- * Graphics object classes
- ******************************************************************************/
-
-static struct nouveau_oclass
-nv34_graph_sclass[] = {
-       { 0x0012, &nv04_graph_ofuncs, NULL }, /* beta1 */
-       { 0x0019, &nv04_graph_ofuncs, NULL }, /* clip */
-       { 0x0030, &nv04_graph_ofuncs, NULL }, /* null */
-       { 0x0039, &nv04_graph_ofuncs, NULL }, /* m2mf */
-       { 0x0043, &nv04_graph_ofuncs, NULL }, /* rop */
-       { 0x0044, &nv04_graph_ofuncs, NULL }, /* patt */
-       { 0x004a, &nv04_graph_ofuncs, NULL }, /* gdi */
-       { 0x0062, &nv04_graph_ofuncs, NULL }, /* surf2d */
-       { 0x0072, &nv04_graph_ofuncs, NULL }, /* beta4 */
-       { 0x0089, &nv04_graph_ofuncs, NULL }, /* sifm */
-       { 0x008a, &nv04_graph_ofuncs, NULL }, /* ifc */
-       { 0x009f, &nv04_graph_ofuncs, NULL }, /* imageblit */
-       { 0x0362, &nv04_graph_ofuncs, NULL }, /* surf2d (nv30) */
-       { 0x0389, &nv04_graph_ofuncs, NULL }, /* sifm (nv30) */
-       { 0x038a, &nv04_graph_ofuncs, NULL }, /* ifc (nv30) */
-       { 0x039e, &nv04_graph_ofuncs, NULL }, /* swzsurf (nv30) */
-       { 0x0697, &nv04_graph_ofuncs, NULL }, /* rankine */
-       {},
-};
-
-/*******************************************************************************
- * PGRAPH context
- ******************************************************************************/
-
-static int
-nv34_graph_context_ctor(struct nouveau_object *parent,
-                       struct nouveau_object *engine,
-                       struct nouveau_oclass *oclass, void *data, u32 size,
-                       struct nouveau_object **pobject)
-{
-       struct nv20_graph_chan *chan;
-       int ret, i;
-
-       ret = nouveau_graph_context_create(parent, engine, oclass, NULL, 0x46dc,
-                                          16, NVOBJ_FLAG_ZERO_ALLOC, &chan);
-       *pobject = nv_object(chan);
-       if (ret)
-               return ret;
-
-       chan->chid = nouveau_fifo_chan(parent)->chid;
-
-       nv_wo32(chan, 0x0028, 0x00000001 | (chan->chid << 24));
-       nv_wo32(chan, 0x040c, 0x01000101);
-       nv_wo32(chan, 0x0420, 0x00000111);
-       nv_wo32(chan, 0x0424, 0x00000060);
-       nv_wo32(chan, 0x0440, 0x00000080);
-       nv_wo32(chan, 0x0444, 0xffff0000);
-       nv_wo32(chan, 0x0448, 0x00000001);
-       nv_wo32(chan, 0x045c, 0x44400000);
-       nv_wo32(chan, 0x0480, 0xffff0000);
-       for (i = 0x04d4; i < 0x04dc; i += 4)
-               nv_wo32(chan, i, 0x0fff0000);
-       nv_wo32(chan, 0x04e0, 0x00011100);
-       for (i = 0x04fc; i < 0x053c; i += 4)
-               nv_wo32(chan, i, 0x07ff0000);
-       nv_wo32(chan, 0x0544, 0x4b7fffff);
-       nv_wo32(chan, 0x057c, 0x00000080);
-       nv_wo32(chan, 0x0580, 0x30201000);
-       nv_wo32(chan, 0x0584, 0x70605040);
-       nv_wo32(chan, 0x0588, 0xb8a89888);
-       nv_wo32(chan, 0x058c, 0xf8e8d8c8);
-       nv_wo32(chan, 0x05a0, 0xb0000000);
-       for (i = 0x05f0; i < 0x0630; i += 4)
-               nv_wo32(chan, i, 0x00010588);
-       for (i = 0x0630; i < 0x0670; i += 4)
-               nv_wo32(chan, i, 0x00030303);
-       for (i = 0x06b0; i < 0x06f0; i += 4)
-               nv_wo32(chan, i, 0x0008aae4);
-       for (i = 0x06f0; i < 0x0730; i += 4)
-               nv_wo32(chan, i, 0x01012000);
-       for (i = 0x0730; i < 0x0770; i += 4)
-               nv_wo32(chan, i, 0x00080008);
-       nv_wo32(chan, 0x0850, 0x00040000);
-       nv_wo32(chan, 0x0854, 0x00010000);
-       for (i = 0x0858; i < 0x0868; i += 4)
-               nv_wo32(chan, i, 0x00040004);
-       for (i = 0x15ac; i <= 0x271c ; i += 16) {
-               nv_wo32(chan, i + 0, 0x10700ff9);
-               nv_wo32(chan, i + 1, 0x0436086c);
-               nv_wo32(chan, i + 2, 0x000c001b);
-       }
-       for (i = 0x274c; i < 0x275c; i += 4)
-               nv_wo32(chan, i, 0x0000ffff);
-       nv_wo32(chan, 0x2ae0, 0x3f800000);
-       nv_wo32(chan, 0x2e9c, 0x3f800000);
-       nv_wo32(chan, 0x2eb0, 0x3f800000);
-       nv_wo32(chan, 0x2edc, 0x40000000);
-       nv_wo32(chan, 0x2ee0, 0x3f800000);
-       nv_wo32(chan, 0x2ee4, 0x3f000000);
-       nv_wo32(chan, 0x2eec, 0x40000000);
-       nv_wo32(chan, 0x2ef0, 0x3f800000);
-       nv_wo32(chan, 0x2ef8, 0xbf800000);
-       nv_wo32(chan, 0x2f00, 0xbf800000);
-       return 0;
-}
-
-static struct nouveau_oclass
-nv34_graph_cclass = {
-       .handle = NV_ENGCTX(GR, 0x34),
-       .ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nv34_graph_context_ctor,
-               .dtor = _nouveau_graph_context_dtor,
-               .init = nv20_graph_context_init,
-               .fini = nv20_graph_context_fini,
-               .rd32 = _nouveau_graph_context_rd32,
-               .wr32 = _nouveau_graph_context_wr32,
-       },
-};
-
-/*******************************************************************************
- * PGRAPH engine/subdev functions
- ******************************************************************************/
-
-static int
-nv34_graph_ctor(struct nouveau_object *parent, struct nouveau_object *engine,
-              struct nouveau_oclass *oclass, void *data, u32 size,
-              struct nouveau_object **pobject)
-{
-       struct nv20_graph_priv *priv;
-       int ret;
-
-       ret = nouveau_graph_create(parent, engine, oclass, true, &priv);
-       *pobject = nv_object(priv);
-       if (ret)
-               return ret;
-
-       ret = nouveau_gpuobj_new(nv_object(priv), NULL, 32 * 4, 16,
-                                NVOBJ_FLAG_ZERO_ALLOC, &priv->ctxtab);
-       if (ret)
-               return ret;
-
-       nv_subdev(priv)->unit = 0x00001000;
-       nv_subdev(priv)->intr = nv20_graph_intr;
-       nv_engine(priv)->cclass = &nv34_graph_cclass;
-       nv_engine(priv)->sclass = nv34_graph_sclass;
-       nv_engine(priv)->tile_prog = nv20_graph_tile_prog;
-       return 0;
-}
-
-struct nouveau_oclass
-nv34_graph_oclass = {
-       .handle = NV_ENGINE(GR, 0x34),
-       .ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nv34_graph_ctor,
-               .dtor = nv20_graph_dtor,
-               .init = nv30_graph_init,
-               .fini = _nouveau_graph_fini,
-       },
-};
diff --git a/drivers/gpu/drm/nouveau/core/engine/graph/nv35.c b/drivers/gpu/drm/nouveau/core/engine/graph/nv35.c
deleted file mode 100644 (file)
index 2fb5756..0000000
+++ /dev/null
@@ -1,165 +0,0 @@
-#include <core/os.h>
-#include <core/engctx.h>
-#include <core/enum.h>
-
-#include <subdev/timer.h>
-#include <subdev/fb.h>
-
-#include "nv20.h"
-#include "regs.h"
-
-/*******************************************************************************
- * Graphics object classes
- ******************************************************************************/
-
-static struct nouveau_oclass
-nv35_graph_sclass[] = {
-       { 0x0012, &nv04_graph_ofuncs, NULL }, /* beta1 */
-       { 0x0019, &nv04_graph_ofuncs, NULL }, /* clip */
-       { 0x0030, &nv04_graph_ofuncs, NULL }, /* null */
-       { 0x0039, &nv04_graph_ofuncs, NULL }, /* m2mf */
-       { 0x0043, &nv04_graph_ofuncs, NULL }, /* rop */
-       { 0x0044, &nv04_graph_ofuncs, NULL }, /* patt */
-       { 0x004a, &nv04_graph_ofuncs, NULL }, /* gdi */
-       { 0x0062, &nv04_graph_ofuncs, NULL }, /* surf2d */
-       { 0x0072, &nv04_graph_ofuncs, NULL }, /* beta4 */
-       { 0x0089, &nv04_graph_ofuncs, NULL }, /* sifm */
-       { 0x008a, &nv04_graph_ofuncs, NULL }, /* ifc */
-       { 0x009f, &nv04_graph_ofuncs, NULL }, /* imageblit */
-       { 0x0362, &nv04_graph_ofuncs, NULL }, /* surf2d (nv30) */
-       { 0x0389, &nv04_graph_ofuncs, NULL }, /* sifm (nv30) */
-       { 0x038a, &nv04_graph_ofuncs, NULL }, /* ifc (nv30) */
-       { 0x039e, &nv04_graph_ofuncs, NULL }, /* swzsurf (nv30) */
-       { 0x0497, &nv04_graph_ofuncs, NULL }, /* rankine */
-       {},
-};
-
-/*******************************************************************************
- * PGRAPH context
- ******************************************************************************/
-
-static int
-nv35_graph_context_ctor(struct nouveau_object *parent,
-                       struct nouveau_object *engine,
-                       struct nouveau_oclass *oclass, void *data, u32 size,
-                       struct nouveau_object **pobject)
-{
-       struct nv20_graph_chan *chan;
-       int ret, i;
-
-       ret = nouveau_graph_context_create(parent, engine, oclass, NULL, 0x577c,
-                                          16, NVOBJ_FLAG_ZERO_ALLOC, &chan);
-       *pobject = nv_object(chan);
-       if (ret)
-               return ret;
-
-       chan->chid = nouveau_fifo_chan(parent)->chid;
-
-       nv_wo32(chan, 0x0028, 0x00000001 | (chan->chid << 24));
-       nv_wo32(chan, 0x040c, 0x00000101);
-       nv_wo32(chan, 0x0420, 0x00000111);
-       nv_wo32(chan, 0x0424, 0x00000060);
-       nv_wo32(chan, 0x0440, 0x00000080);
-       nv_wo32(chan, 0x0444, 0xffff0000);
-       nv_wo32(chan, 0x0448, 0x00000001);
-       nv_wo32(chan, 0x045c, 0x44400000);
-       nv_wo32(chan, 0x0488, 0xffff0000);
-       for (i = 0x04dc; i < 0x04e4; i += 4)
-               nv_wo32(chan, i, 0x0fff0000);
-       nv_wo32(chan, 0x04e8, 0x00011100);
-       for (i = 0x0504; i < 0x0544; i += 4)
-               nv_wo32(chan, i, 0x07ff0000);
-       nv_wo32(chan, 0x054c, 0x4b7fffff);
-       nv_wo32(chan, 0x0588, 0x00000080);
-       nv_wo32(chan, 0x058c, 0x30201000);
-       nv_wo32(chan, 0x0590, 0x70605040);
-       nv_wo32(chan, 0x0594, 0xb8a89888);
-       nv_wo32(chan, 0x0598, 0xf8e8d8c8);
-       nv_wo32(chan, 0x05ac, 0xb0000000);
-       for (i = 0x0604; i < 0x0644; i += 4)
-               nv_wo32(chan, i, 0x00010588);
-       for (i = 0x0644; i < 0x0684; i += 4)
-               nv_wo32(chan, i, 0x00030303);
-       for (i = 0x06c4; i < 0x0704; i += 4)
-               nv_wo32(chan, i, 0x0008aae4);
-       for (i = 0x0704; i < 0x0744; i += 4)
-               nv_wo32(chan, i, 0x01012000);
-       for (i = 0x0744; i < 0x0784; i += 4)
-               nv_wo32(chan, i, 0x00080008);
-       nv_wo32(chan, 0x0860, 0x00040000);
-       nv_wo32(chan, 0x0864, 0x00010000);
-       for (i = 0x0868; i < 0x0878; i += 4)
-               nv_wo32(chan, i, 0x00040004);
-       for (i = 0x1f1c; i <= 0x308c ; i += 16) {
-               nv_wo32(chan, i + 0, 0x10700ff9);
-               nv_wo32(chan, i + 4, 0x0436086c);
-               nv_wo32(chan, i + 8, 0x000c001b);
-       }
-       for (i = 0x30bc; i < 0x30cc; i += 4)
-               nv_wo32(chan, i, 0x0000ffff);
-       nv_wo32(chan, 0x3450, 0x3f800000);
-       nv_wo32(chan, 0x380c, 0x3f800000);
-       nv_wo32(chan, 0x3820, 0x3f800000);
-       nv_wo32(chan, 0x384c, 0x40000000);
-       nv_wo32(chan, 0x3850, 0x3f800000);
-       nv_wo32(chan, 0x3854, 0x3f000000);
-       nv_wo32(chan, 0x385c, 0x40000000);
-       nv_wo32(chan, 0x3860, 0x3f800000);
-       nv_wo32(chan, 0x3868, 0xbf800000);
-       nv_wo32(chan, 0x3870, 0xbf800000);
-       return 0;
-}
-
-static struct nouveau_oclass
-nv35_graph_cclass = {
-       .handle = NV_ENGCTX(GR, 0x35),
-       .ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nv35_graph_context_ctor,
-               .dtor = _nouveau_graph_context_dtor,
-               .init = nv20_graph_context_init,
-               .fini = nv20_graph_context_fini,
-               .rd32 = _nouveau_graph_context_rd32,
-               .wr32 = _nouveau_graph_context_wr32,
-       },
-};
-
-/*******************************************************************************
- * PGRAPH engine/subdev functions
- ******************************************************************************/
-
-static int
-nv35_graph_ctor(struct nouveau_object *parent, struct nouveau_object *engine,
-              struct nouveau_oclass *oclass, void *data, u32 size,
-              struct nouveau_object **pobject)
-{
-       struct nv20_graph_priv *priv;
-       int ret;
-
-       ret = nouveau_graph_create(parent, engine, oclass, true, &priv);
-       *pobject = nv_object(priv);
-       if (ret)
-               return ret;
-
-       ret = nouveau_gpuobj_new(nv_object(priv), NULL, 32 * 4, 16,
-                                NVOBJ_FLAG_ZERO_ALLOC, &priv->ctxtab);
-       if (ret)
-               return ret;
-
-       nv_subdev(priv)->unit = 0x00001000;
-       nv_subdev(priv)->intr = nv20_graph_intr;
-       nv_engine(priv)->cclass = &nv35_graph_cclass;
-       nv_engine(priv)->sclass = nv35_graph_sclass;
-       nv_engine(priv)->tile_prog = nv20_graph_tile_prog;
-       return 0;
-}
-
-struct nouveau_oclass
-nv35_graph_oclass = {
-       .handle = NV_ENGINE(GR, 0x35),
-       .ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nv35_graph_ctor,
-               .dtor = nv20_graph_dtor,
-               .init = nv30_graph_init,
-               .fini = _nouveau_graph_fini,
-       },
-};
diff --git a/drivers/gpu/drm/nouveau/core/engine/graph/nv40.c b/drivers/gpu/drm/nouveau/core/engine/graph/nv40.c
deleted file mode 100644 (file)
index 4f40117..0000000
+++ /dev/null
@@ -1,536 +0,0 @@
-/*
- * Copyright 2012 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 <core/client.h>
-#include <core/os.h>
-#include <core/handle.h>
-#include <core/engctx.h>
-
-#include <subdev/fb.h>
-#include <subdev/timer.h>
-
-#include <engine/graph.h>
-#include <engine/fifo.h>
-
-#include "nv40.h"
-#include "regs.h"
-
-struct nv40_graph_priv {
-       struct nouveau_graph base;
-       u32 size;
-};
-
-struct nv40_graph_chan {
-       struct nouveau_graph_chan base;
-};
-
-static u64
-nv40_graph_units(struct nouveau_graph *graph)
-{
-       struct nv40_graph_priv *priv = (void *)graph;
-
-       return nv_rd32(priv, 0x1540);
-}
-
-/*******************************************************************************
- * Graphics object classes
- ******************************************************************************/
-
-static int
-nv40_graph_object_ctor(struct nouveau_object *parent,
-                      struct nouveau_object *engine,
-                      struct nouveau_oclass *oclass, void *data, u32 size,
-                      struct nouveau_object **pobject)
-{
-       struct nouveau_gpuobj *obj;
-       int ret;
-
-       ret = nouveau_gpuobj_create(parent, engine, oclass, 0, parent,
-                                   20, 16, 0, &obj);
-       *pobject = nv_object(obj);
-       if (ret)
-               return ret;
-
-       nv_wo32(obj, 0x00, nv_mclass(obj));
-       nv_wo32(obj, 0x04, 0x00000000);
-       nv_wo32(obj, 0x08, 0x00000000);
-#ifdef __BIG_ENDIAN
-       nv_mo32(obj, 0x08, 0x01000000, 0x01000000);
-#endif
-       nv_wo32(obj, 0x0c, 0x00000000);
-       nv_wo32(obj, 0x10, 0x00000000);
-       return 0;
-}
-
-static struct nouveau_ofuncs
-nv40_graph_ofuncs = {
-       .ctor = nv40_graph_object_ctor,
-       .dtor = _nouveau_gpuobj_dtor,
-       .init = _nouveau_gpuobj_init,
-       .fini = _nouveau_gpuobj_fini,
-       .rd32 = _nouveau_gpuobj_rd32,
-       .wr32 = _nouveau_gpuobj_wr32,
-};
-
-static struct nouveau_oclass
-nv40_graph_sclass[] = {
-       { 0x0012, &nv40_graph_ofuncs, NULL }, /* beta1 */
-       { 0x0019, &nv40_graph_ofuncs, NULL }, /* clip */
-       { 0x0030, &nv40_graph_ofuncs, NULL }, /* null */
-       { 0x0039, &nv40_graph_ofuncs, NULL }, /* m2mf */
-       { 0x0043, &nv40_graph_ofuncs, NULL }, /* rop */
-       { 0x0044, &nv40_graph_ofuncs, NULL }, /* patt */
-       { 0x004a, &nv40_graph_ofuncs, NULL }, /* gdi */
-       { 0x0062, &nv40_graph_ofuncs, NULL }, /* surf2d */
-       { 0x0072, &nv40_graph_ofuncs, NULL }, /* beta4 */
-       { 0x0089, &nv40_graph_ofuncs, NULL }, /* sifm */
-       { 0x008a, &nv40_graph_ofuncs, NULL }, /* ifc */
-       { 0x009f, &nv40_graph_ofuncs, NULL }, /* imageblit */
-       { 0x3062, &nv40_graph_ofuncs, NULL }, /* surf2d (nv40) */
-       { 0x3089, &nv40_graph_ofuncs, NULL }, /* sifm (nv40) */
-       { 0x309e, &nv40_graph_ofuncs, NULL }, /* swzsurf (nv40) */
-       { 0x4097, &nv40_graph_ofuncs, NULL }, /* curie */
-       {},
-};
-
-static struct nouveau_oclass
-nv44_graph_sclass[] = {
-       { 0x0012, &nv40_graph_ofuncs, NULL }, /* beta1 */
-       { 0x0019, &nv40_graph_ofuncs, NULL }, /* clip */
-       { 0x0030, &nv40_graph_ofuncs, NULL }, /* null */
-       { 0x0039, &nv40_graph_ofuncs, NULL }, /* m2mf */
-       { 0x0043, &nv40_graph_ofuncs, NULL }, /* rop */
-       { 0x0044, &nv40_graph_ofuncs, NULL }, /* patt */
-       { 0x004a, &nv40_graph_ofuncs, NULL }, /* gdi */
-       { 0x0062, &nv40_graph_ofuncs, NULL }, /* surf2d */
-       { 0x0072, &nv40_graph_ofuncs, NULL }, /* beta4 */
-       { 0x0089, &nv40_graph_ofuncs, NULL }, /* sifm */
-       { 0x008a, &nv40_graph_ofuncs, NULL }, /* ifc */
-       { 0x009f, &nv40_graph_ofuncs, NULL }, /* imageblit */
-       { 0x3062, &nv40_graph_ofuncs, NULL }, /* surf2d (nv40) */
-       { 0x3089, &nv40_graph_ofuncs, NULL }, /* sifm (nv40) */
-       { 0x309e, &nv40_graph_ofuncs, NULL }, /* swzsurf (nv40) */
-       { 0x4497, &nv40_graph_ofuncs, NULL }, /* curie */
-       {},
-};
-
-/*******************************************************************************
- * PGRAPH context
- ******************************************************************************/
-
-static int
-nv40_graph_context_ctor(struct nouveau_object *parent,
-                       struct nouveau_object *engine,
-                       struct nouveau_oclass *oclass, void *data, u32 size,
-                       struct nouveau_object **pobject)
-{
-       struct nv40_graph_priv *priv = (void *)engine;
-       struct nv40_graph_chan *chan;
-       int ret;
-
-       ret = nouveau_graph_context_create(parent, engine, oclass, NULL,
-                                          priv->size, 16,
-                                          NVOBJ_FLAG_ZERO_ALLOC, &chan);
-       *pobject = nv_object(chan);
-       if (ret)
-               return ret;
-
-       nv40_grctx_fill(nv_device(priv), nv_gpuobj(chan));
-       nv_wo32(chan, 0x00000, nv_gpuobj(chan)->addr >> 4);
-       return 0;
-}
-
-static int
-nv40_graph_context_fini(struct nouveau_object *object, bool suspend)
-{
-       struct nv40_graph_priv *priv = (void *)object->engine;
-       struct nv40_graph_chan *chan = (void *)object;
-       u32 inst = 0x01000000 | nv_gpuobj(chan)->addr >> 4;
-       int ret = 0;
-
-       nv_mask(priv, 0x400720, 0x00000001, 0x00000000);
-
-       if (nv_rd32(priv, 0x40032c) == inst) {
-               if (suspend) {
-                       nv_wr32(priv, 0x400720, 0x00000000);
-                       nv_wr32(priv, 0x400784, inst);
-                       nv_mask(priv, 0x400310, 0x00000020, 0x00000020);
-                       nv_mask(priv, 0x400304, 0x00000001, 0x00000001);
-                       if (!nv_wait(priv, 0x400300, 0x00000001, 0x00000000)) {
-                               u32 insn = nv_rd32(priv, 0x400308);
-                               nv_warn(priv, "ctxprog timeout 0x%08x\n", insn);
-                               ret = -EBUSY;
-                       }
-               }
-
-               nv_mask(priv, 0x40032c, 0x01000000, 0x00000000);
-       }
-
-       if (nv_rd32(priv, 0x400330) == inst)
-               nv_mask(priv, 0x400330, 0x01000000, 0x00000000);
-
-       nv_mask(priv, 0x400720, 0x00000001, 0x00000001);
-       return ret;
-}
-
-static struct nouveau_oclass
-nv40_graph_cclass = {
-       .handle = NV_ENGCTX(GR, 0x40),
-       .ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nv40_graph_context_ctor,
-               .dtor = _nouveau_graph_context_dtor,
-               .init = _nouveau_graph_context_init,
-               .fini = nv40_graph_context_fini,
-               .rd32 = _nouveau_graph_context_rd32,
-               .wr32 = _nouveau_graph_context_wr32,
-       },
-};
-
-/*******************************************************************************
- * PGRAPH engine/subdev functions
- ******************************************************************************/
-
-static void
-nv40_graph_tile_prog(struct nouveau_engine *engine, int i)
-{
-       struct nouveau_fb_tile *tile = &nouveau_fb(engine)->tile.region[i];
-       struct nouveau_fifo *pfifo = nouveau_fifo(engine);
-       struct nv40_graph_priv *priv = (void *)engine;
-       unsigned long flags;
-
-       pfifo->pause(pfifo, &flags);
-       nv04_graph_idle(priv);
-
-       switch (nv_device(priv)->chipset) {
-       case 0x40:
-       case 0x41:
-       case 0x42:
-       case 0x43:
-       case 0x45:
-       case 0x4e:
-               nv_wr32(priv, NV20_PGRAPH_TSIZE(i), tile->pitch);
-               nv_wr32(priv, NV20_PGRAPH_TLIMIT(i), tile->limit);
-               nv_wr32(priv, NV20_PGRAPH_TILE(i), tile->addr);
-               nv_wr32(priv, NV40_PGRAPH_TSIZE1(i), tile->pitch);
-               nv_wr32(priv, NV40_PGRAPH_TLIMIT1(i), tile->limit);
-               nv_wr32(priv, NV40_PGRAPH_TILE1(i), tile->addr);
-               switch (nv_device(priv)->chipset) {
-               case 0x40:
-               case 0x45:
-                       nv_wr32(priv, NV20_PGRAPH_ZCOMP(i), tile->zcomp);
-                       nv_wr32(priv, NV40_PGRAPH_ZCOMP1(i), tile->zcomp);
-                       break;
-               case 0x41:
-               case 0x42:
-               case 0x43:
-                       nv_wr32(priv, NV41_PGRAPH_ZCOMP0(i), tile->zcomp);
-                       nv_wr32(priv, NV41_PGRAPH_ZCOMP1(i), tile->zcomp);
-                       break;
-               default:
-                       break;
-               }
-               break;
-       case 0x44:
-       case 0x4a:
-               nv_wr32(priv, NV20_PGRAPH_TSIZE(i), tile->pitch);
-               nv_wr32(priv, NV20_PGRAPH_TLIMIT(i), tile->limit);
-               nv_wr32(priv, NV20_PGRAPH_TILE(i), tile->addr);
-               break;
-       case 0x46:
-       case 0x4c:
-       case 0x47:
-       case 0x49:
-       case 0x4b:
-       case 0x63:
-       case 0x67:
-       case 0x68:
-               nv_wr32(priv, NV47_PGRAPH_TSIZE(i), tile->pitch);
-               nv_wr32(priv, NV47_PGRAPH_TLIMIT(i), tile->limit);
-               nv_wr32(priv, NV47_PGRAPH_TILE(i), tile->addr);
-               nv_wr32(priv, NV40_PGRAPH_TSIZE1(i), tile->pitch);
-               nv_wr32(priv, NV40_PGRAPH_TLIMIT1(i), tile->limit);
-               nv_wr32(priv, NV40_PGRAPH_TILE1(i), tile->addr);
-               switch (nv_device(priv)->chipset) {
-               case 0x47:
-               case 0x49:
-               case 0x4b:
-                       nv_wr32(priv, NV47_PGRAPH_ZCOMP0(i), tile->zcomp);
-                       nv_wr32(priv, NV47_PGRAPH_ZCOMP1(i), tile->zcomp);
-                       break;
-               default:
-                       break;
-               }
-               break;
-       default:
-               break;
-       }
-
-       pfifo->start(pfifo, &flags);
-}
-
-static void
-nv40_graph_intr(struct nouveau_subdev *subdev)
-{
-       struct nouveau_fifo *pfifo = nouveau_fifo(subdev);
-       struct nouveau_engine *engine = nv_engine(subdev);
-       struct nouveau_object *engctx;
-       struct nouveau_handle *handle = NULL;
-       struct nv40_graph_priv *priv = (void *)subdev;
-       u32 stat = nv_rd32(priv, NV03_PGRAPH_INTR);
-       u32 nsource = nv_rd32(priv, NV03_PGRAPH_NSOURCE);
-       u32 nstatus = nv_rd32(priv, NV03_PGRAPH_NSTATUS);
-       u32 inst = nv_rd32(priv, 0x40032c) & 0x000fffff;
-       u32 addr = nv_rd32(priv, NV04_PGRAPH_TRAPPED_ADDR);
-       u32 subc = (addr & 0x00070000) >> 16;
-       u32 mthd = (addr & 0x00001ffc);
-       u32 data = nv_rd32(priv, NV04_PGRAPH_TRAPPED_DATA);
-       u32 class = nv_rd32(priv, 0x400160 + subc * 4) & 0xffff;
-       u32 show = stat;
-       int chid;
-
-       engctx = nouveau_engctx_get(engine, inst);
-       chid   = pfifo->chid(pfifo, engctx);
-
-       if (stat & NV_PGRAPH_INTR_ERROR) {
-               if (nsource & NV03_PGRAPH_NSOURCE_ILLEGAL_MTHD) {
-                       handle = nouveau_handle_get_class(engctx, class);
-                       if (handle && !nv_call(handle->object, mthd, data))
-                               show &= ~NV_PGRAPH_INTR_ERROR;
-                       nouveau_handle_put(handle);
-               }
-
-               if (nsource & NV03_PGRAPH_NSOURCE_DMA_VTX_PROTECTION) {
-                       nv_mask(priv, 0x402000, 0, 0);
-               }
-       }
-
-       nv_wr32(priv, NV03_PGRAPH_INTR, stat);
-       nv_wr32(priv, NV04_PGRAPH_FIFO, 0x00000001);
-
-       if (show) {
-               nv_error(priv, "%s", "");
-               nouveau_bitfield_print(nv10_graph_intr_name, show);
-               pr_cont(" nsource:");
-               nouveau_bitfield_print(nv04_graph_nsource, nsource);
-               pr_cont(" nstatus:");
-               nouveau_bitfield_print(nv10_graph_nstatus, nstatus);
-               pr_cont("\n");
-               nv_error(priv,
-                        "ch %d [0x%08x %s] subc %d class 0x%04x mthd 0x%04x data 0x%08x\n",
-                        chid, inst << 4, nouveau_client_name(engctx), subc,
-                        class, mthd, data);
-       }
-
-       nouveau_engctx_put(engctx);
-}
-
-static int
-nv40_graph_ctor(struct nouveau_object *parent, struct nouveau_object *engine,
-              struct nouveau_oclass *oclass, void *data, u32 size,
-              struct nouveau_object **pobject)
-{
-       struct nv40_graph_priv *priv;
-       int ret;
-
-       ret = nouveau_graph_create(parent, engine, oclass, true, &priv);
-       *pobject = nv_object(priv);
-       if (ret)
-               return ret;
-
-       nv_subdev(priv)->unit = 0x00001000;
-       nv_subdev(priv)->intr = nv40_graph_intr;
-       nv_engine(priv)->cclass = &nv40_graph_cclass;
-       if (nv44_graph_class(priv))
-               nv_engine(priv)->sclass = nv44_graph_sclass;
-       else
-               nv_engine(priv)->sclass = nv40_graph_sclass;
-       nv_engine(priv)->tile_prog = nv40_graph_tile_prog;
-
-       priv->base.units = nv40_graph_units;
-       return 0;
-}
-
-static int
-nv40_graph_init(struct nouveau_object *object)
-{
-       struct nouveau_engine *engine = nv_engine(object);
-       struct nouveau_fb *pfb = nouveau_fb(object);
-       struct nv40_graph_priv *priv = (void *)engine;
-       int ret, i, j;
-       u32 vramsz;
-
-       ret = nouveau_graph_init(&priv->base);
-       if (ret)
-               return ret;
-
-       /* generate and upload context program */
-       ret = nv40_grctx_init(nv_device(priv), &priv->size);
-       if (ret)
-               return ret;
-
-       /* No context present currently */
-       nv_wr32(priv, NV40_PGRAPH_CTXCTL_CUR, 0x00000000);
-
-       nv_wr32(priv, NV03_PGRAPH_INTR   , 0xFFFFFFFF);
-       nv_wr32(priv, NV40_PGRAPH_INTR_EN, 0xFFFFFFFF);
-
-       nv_wr32(priv, NV04_PGRAPH_DEBUG_0, 0xFFFFFFFF);
-       nv_wr32(priv, NV04_PGRAPH_DEBUG_0, 0x00000000);
-       nv_wr32(priv, NV04_PGRAPH_DEBUG_1, 0x401287c0);
-       nv_wr32(priv, NV04_PGRAPH_DEBUG_3, 0xe0de8055);
-       nv_wr32(priv, NV10_PGRAPH_DEBUG_4, 0x00008000);
-       nv_wr32(priv, NV04_PGRAPH_LIMIT_VIOL_PIX, 0x00be3c5f);
-
-       nv_wr32(priv, NV10_PGRAPH_CTX_CONTROL, 0x10010100);
-       nv_wr32(priv, NV10_PGRAPH_STATE      , 0xFFFFFFFF);
-
-       j = nv_rd32(priv, 0x1540) & 0xff;
-       if (j) {
-               for (i = 0; !(j & 1); j >>= 1, i++)
-                       ;
-               nv_wr32(priv, 0x405000, i);
-       }
-
-       if (nv_device(priv)->chipset == 0x40) {
-               nv_wr32(priv, 0x4009b0, 0x83280fff);
-               nv_wr32(priv, 0x4009b4, 0x000000a0);
-       } else {
-               nv_wr32(priv, 0x400820, 0x83280eff);
-               nv_wr32(priv, 0x400824, 0x000000a0);
-       }
-
-       switch (nv_device(priv)->chipset) {
-       case 0x40:
-       case 0x45:
-               nv_wr32(priv, 0x4009b8, 0x0078e366);
-               nv_wr32(priv, 0x4009bc, 0x0000014c);
-               break;
-       case 0x41:
-       case 0x42: /* pciid also 0x00Cx */
-       /* case 0x0120: XXX (pciid) */
-               nv_wr32(priv, 0x400828, 0x007596ff);
-               nv_wr32(priv, 0x40082c, 0x00000108);
-               break;
-       case 0x43:
-               nv_wr32(priv, 0x400828, 0x0072cb77);
-               nv_wr32(priv, 0x40082c, 0x00000108);
-               break;
-       case 0x44:
-       case 0x46: /* G72 */
-       case 0x4a:
-       case 0x4c: /* G7x-based C51 */
-       case 0x4e:
-               nv_wr32(priv, 0x400860, 0);
-               nv_wr32(priv, 0x400864, 0);
-               break;
-       case 0x47: /* G70 */
-       case 0x49: /* G71 */
-       case 0x4b: /* G73 */
-               nv_wr32(priv, 0x400828, 0x07830610);
-               nv_wr32(priv, 0x40082c, 0x0000016A);
-               break;
-       default:
-               break;
-       }
-
-       nv_wr32(priv, 0x400b38, 0x2ffff800);
-       nv_wr32(priv, 0x400b3c, 0x00006000);
-
-       /* Tiling related stuff. */
-       switch (nv_device(priv)->chipset) {
-       case 0x44:
-       case 0x4a:
-               nv_wr32(priv, 0x400bc4, 0x1003d888);
-               nv_wr32(priv, 0x400bbc, 0xb7a7b500);
-               break;
-       case 0x46:
-               nv_wr32(priv, 0x400bc4, 0x0000e024);
-               nv_wr32(priv, 0x400bbc, 0xb7a7b520);
-               break;
-       case 0x4c:
-       case 0x4e:
-       case 0x67:
-               nv_wr32(priv, 0x400bc4, 0x1003d888);
-               nv_wr32(priv, 0x400bbc, 0xb7a7b540);
-               break;
-       default:
-               break;
-       }
-
-       /* Turn all the tiling regions off. */
-       for (i = 0; i < pfb->tile.regions; i++)
-               engine->tile_prog(engine, i);
-
-       /* begin RAM config */
-       vramsz = nv_device_resource_len(nv_device(priv), 0) - 1;
-       switch (nv_device(priv)->chipset) {
-       case 0x40:
-               nv_wr32(priv, 0x4009A4, nv_rd32(priv, 0x100200));
-               nv_wr32(priv, 0x4009A8, nv_rd32(priv, 0x100204));
-               nv_wr32(priv, 0x4069A4, nv_rd32(priv, 0x100200));
-               nv_wr32(priv, 0x4069A8, nv_rd32(priv, 0x100204));
-               nv_wr32(priv, 0x400820, 0);
-               nv_wr32(priv, 0x400824, 0);
-               nv_wr32(priv, 0x400864, vramsz);
-               nv_wr32(priv, 0x400868, vramsz);
-               break;
-       default:
-               switch (nv_device(priv)->chipset) {
-               case 0x41:
-               case 0x42:
-               case 0x43:
-               case 0x45:
-               case 0x4e:
-               case 0x44:
-               case 0x4a:
-                       nv_wr32(priv, 0x4009F0, nv_rd32(priv, 0x100200));
-                       nv_wr32(priv, 0x4009F4, nv_rd32(priv, 0x100204));
-                       break;
-               default:
-                       nv_wr32(priv, 0x400DF0, nv_rd32(priv, 0x100200));
-                       nv_wr32(priv, 0x400DF4, nv_rd32(priv, 0x100204));
-                       break;
-               }
-               nv_wr32(priv, 0x4069F0, nv_rd32(priv, 0x100200));
-               nv_wr32(priv, 0x4069F4, nv_rd32(priv, 0x100204));
-               nv_wr32(priv, 0x400840, 0);
-               nv_wr32(priv, 0x400844, 0);
-               nv_wr32(priv, 0x4008A0, vramsz);
-               nv_wr32(priv, 0x4008A4, vramsz);
-               break;
-       }
-
-       return 0;
-}
-
-struct nouveau_oclass
-nv40_graph_oclass = {
-       .handle = NV_ENGINE(GR, 0x40),
-       .ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nv40_graph_ctor,
-               .dtor = _nouveau_graph_dtor,
-               .init = nv40_graph_init,
-               .fini = _nouveau_graph_fini,
-       },
-};
diff --git a/drivers/gpu/drm/nouveau/core/engine/graph/nv40.h b/drivers/gpu/drm/nouveau/core/engine/graph/nv40.h
deleted file mode 100644 (file)
index ad82093..0000000
+++ /dev/null
@@ -1,24 +0,0 @@
-#ifndef __NV40_GRAPH_H__
-#define __NV40_GRAPH_H__
-
-#include <core/device.h>
-#include <core/gpuobj.h>
-
-/* returns 1 if device is one of the nv4x using the 0x4497 object class,
- * helpful to determine a number of other hardware features
- */
-static inline int
-nv44_graph_class(void *priv)
-{
-       struct nouveau_device *device = nv_device(priv);
-
-       if ((device->chipset & 0xf0) == 0x60)
-               return 1;
-
-       return !(0x0baf & (1 << (device->chipset & 0x0f)));
-}
-
-int  nv40_grctx_init(struct nouveau_device *, u32 *size);
-void nv40_grctx_fill(struct nouveau_device *, struct nouveau_gpuobj *);
-
-#endif
diff --git a/drivers/gpu/drm/nouveau/core/engine/graph/nv50.c b/drivers/gpu/drm/nouveau/core/engine/graph/nv50.c
deleted file mode 100644 (file)
index 38e0aa2..0000000
+++ /dev/null
@@ -1,1009 +0,0 @@
-/*
- * Copyright 2012 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 <core/os.h>
-#include <core/client.h>
-#include <core/handle.h>
-#include <core/engctx.h>
-#include <core/enum.h>
-
-#include <subdev/fb.h>
-#include <subdev/vm.h>
-#include <subdev/timer.h>
-
-#include <engine/fifo.h>
-#include <engine/graph.h>
-
-#include "nv50.h"
-
-struct nv50_graph_priv {
-       struct nouveau_graph base;
-       spinlock_t lock;
-       u32 size;
-};
-
-struct nv50_graph_chan {
-       struct nouveau_graph_chan base;
-};
-
-static u64
-nv50_graph_units(struct nouveau_graph *graph)
-{
-       struct nv50_graph_priv *priv = (void *)graph;
-
-       return nv_rd32(priv, 0x1540);
-}
-
-/*******************************************************************************
- * Graphics object classes
- ******************************************************************************/
-
-static int
-nv50_graph_object_ctor(struct nouveau_object *parent,
-                      struct nouveau_object *engine,
-                      struct nouveau_oclass *oclass, void *data, u32 size,
-                      struct nouveau_object **pobject)
-{
-       struct nouveau_gpuobj *obj;
-       int ret;
-
-       ret = nouveau_gpuobj_create(parent, engine, oclass, 0, parent,
-                                   16, 16, 0, &obj);
-       *pobject = nv_object(obj);
-       if (ret)
-               return ret;
-
-       nv_wo32(obj, 0x00, nv_mclass(obj));
-       nv_wo32(obj, 0x04, 0x00000000);
-       nv_wo32(obj, 0x08, 0x00000000);
-       nv_wo32(obj, 0x0c, 0x00000000);
-       return 0;
-}
-
-static struct nouveau_ofuncs
-nv50_graph_ofuncs = {
-       .ctor = nv50_graph_object_ctor,
-       .dtor = _nouveau_gpuobj_dtor,
-       .init = _nouveau_gpuobj_init,
-       .fini = _nouveau_gpuobj_fini,
-       .rd32 = _nouveau_gpuobj_rd32,
-       .wr32 = _nouveau_gpuobj_wr32,
-};
-
-static struct nouveau_oclass
-nv50_graph_sclass[] = {
-       { 0x0030, &nv50_graph_ofuncs },
-       { 0x502d, &nv50_graph_ofuncs },
-       { 0x5039, &nv50_graph_ofuncs },
-       { 0x5097, &nv50_graph_ofuncs },
-       { 0x50c0, &nv50_graph_ofuncs },
-       {}
-};
-
-static struct nouveau_oclass
-nv84_graph_sclass[] = {
-       { 0x0030, &nv50_graph_ofuncs },
-       { 0x502d, &nv50_graph_ofuncs },
-       { 0x5039, &nv50_graph_ofuncs },
-       { 0x50c0, &nv50_graph_ofuncs },
-       { 0x8297, &nv50_graph_ofuncs },
-       {}
-};
-
-static struct nouveau_oclass
-nva0_graph_sclass[] = {
-       { 0x0030, &nv50_graph_ofuncs },
-       { 0x502d, &nv50_graph_ofuncs },
-       { 0x5039, &nv50_graph_ofuncs },
-       { 0x50c0, &nv50_graph_ofuncs },
-       { 0x8397, &nv50_graph_ofuncs },
-       {}
-};
-
-static struct nouveau_oclass
-nva3_graph_sclass[] = {
-       { 0x0030, &nv50_graph_ofuncs },
-       { 0x502d, &nv50_graph_ofuncs },
-       { 0x5039, &nv50_graph_ofuncs },
-       { 0x50c0, &nv50_graph_ofuncs },
-       { 0x8597, &nv50_graph_ofuncs },
-       { 0x85c0, &nv50_graph_ofuncs },
-       {}
-};
-
-static struct nouveau_oclass
-nvaf_graph_sclass[] = {
-       { 0x0030, &nv50_graph_ofuncs },
-       { 0x502d, &nv50_graph_ofuncs },
-       { 0x5039, &nv50_graph_ofuncs },
-       { 0x50c0, &nv50_graph_ofuncs },
-       { 0x85c0, &nv50_graph_ofuncs },
-       { 0x8697, &nv50_graph_ofuncs },
-       {}
-};
-
-/*******************************************************************************
- * PGRAPH context
- ******************************************************************************/
-
-static int
-nv50_graph_context_ctor(struct nouveau_object *parent,
-                       struct nouveau_object *engine,
-                       struct nouveau_oclass *oclass, void *data, u32 size,
-                       struct nouveau_object **pobject)
-{
-       struct nv50_graph_priv *priv = (void *)engine;
-       struct nv50_graph_chan *chan;
-       int ret;
-
-       ret = nouveau_graph_context_create(parent, engine, oclass, NULL,
-                                          priv->size, 0,
-                                          NVOBJ_FLAG_ZERO_ALLOC, &chan);
-       *pobject = nv_object(chan);
-       if (ret)
-               return ret;
-
-       nv50_grctx_fill(nv_device(priv), nv_gpuobj(chan));
-       return 0;
-}
-
-static struct nouveau_oclass
-nv50_graph_cclass = {
-       .handle = NV_ENGCTX(GR, 0x50),
-       .ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nv50_graph_context_ctor,
-               .dtor = _nouveau_graph_context_dtor,
-               .init = _nouveau_graph_context_init,
-               .fini = _nouveau_graph_context_fini,
-               .rd32 = _nouveau_graph_context_rd32,
-               .wr32 = _nouveau_graph_context_wr32,
-       },
-};
-
-/*******************************************************************************
- * PGRAPH engine/subdev functions
- ******************************************************************************/
-
-static const struct nouveau_bitfield nv50_pgraph_status[] = {
-       { 0x00000001, "BUSY" }, /* set when any bit is set */
-       { 0x00000002, "DISPATCH" },
-       { 0x00000004, "UNK2" },
-       { 0x00000008, "UNK3" },
-       { 0x00000010, "UNK4" },
-       { 0x00000020, "UNK5" },
-       { 0x00000040, "M2MF" },
-       { 0x00000080, "UNK7" },
-       { 0x00000100, "CTXPROG" },
-       { 0x00000200, "VFETCH" },
-       { 0x00000400, "CCACHE_PREGEOM" },
-       { 0x00000800, "STRMOUT_VATTR_POSTGEOM" },
-       { 0x00001000, "VCLIP" },
-       { 0x00002000, "RATTR_APLANE" },
-       { 0x00004000, "TRAST" },
-       { 0x00008000, "CLIPID" },
-       { 0x00010000, "ZCULL" },
-       { 0x00020000, "ENG2D" },
-       { 0x00040000, "RMASK" },
-       { 0x00080000, "TPC_RAST" },
-       { 0x00100000, "TPC_PROP" },
-       { 0x00200000, "TPC_TEX" },
-       { 0x00400000, "TPC_GEOM" },
-       { 0x00800000, "TPC_MP" },
-       { 0x01000000, "ROP" },
-       {}
-};
-
-static const char *const nv50_pgraph_vstatus_0[] = {
-       "VFETCH", "CCACHE", "PREGEOM", "POSTGEOM", "VATTR", "STRMOUT", "VCLIP",
-       NULL
-};
-
-static const char *const nv50_pgraph_vstatus_1[] = {
-       "TPC_RAST", "TPC_PROP", "TPC_TEX", "TPC_GEOM", "TPC_MP", NULL
-};
-
-static const char *const nv50_pgraph_vstatus_2[] = {
-       "RATTR", "APLANE", "TRAST", "CLIPID", "ZCULL", "ENG2D", "RMASK",
-       "ROP", NULL
-};
-
-static void nouveau_pgraph_vstatus_print(struct nv50_graph_priv *priv, int r,
-               const char *const units[], u32 status)
-{
-       int i;
-
-       nv_error(priv, "PGRAPH_VSTATUS%d: 0x%08x", r, status);
-
-       for (i = 0; units[i] && status; i++) {
-               if ((status & 7) == 1)
-                       pr_cont(" %s", units[i]);
-               status >>= 3;
-       }
-       if (status)
-               pr_cont(" (invalid: 0x%x)", status);
-       pr_cont("\n");
-}
-
-static int
-nv84_graph_tlb_flush(struct nouveau_engine *engine)
-{
-       struct nouveau_timer *ptimer = nouveau_timer(engine);
-       struct nv50_graph_priv *priv = (void *)engine;
-       bool idle, timeout = false;
-       unsigned long flags;
-       u64 start;
-       u32 tmp;
-
-       spin_lock_irqsave(&priv->lock, flags);
-       nv_mask(priv, 0x400500, 0x00000001, 0x00000000);
-
-       start = ptimer->read(ptimer);
-       do {
-               idle = true;
-
-               for (tmp = nv_rd32(priv, 0x400380); tmp && idle; tmp >>= 3) {
-                       if ((tmp & 7) == 1)
-                               idle = false;
-               }
-
-               for (tmp = nv_rd32(priv, 0x400384); tmp && idle; tmp >>= 3) {
-                       if ((tmp & 7) == 1)
-                               idle = false;
-               }
-
-               for (tmp = nv_rd32(priv, 0x400388); tmp && idle; tmp >>= 3) {
-                       if ((tmp & 7) == 1)
-                               idle = false;
-               }
-       } while (!idle &&
-                !(timeout = ptimer->read(ptimer) - start > 2000000000));
-
-       if (timeout) {
-               nv_error(priv, "PGRAPH TLB flush idle timeout fail\n");
-
-               tmp = nv_rd32(priv, 0x400700);
-               nv_error(priv, "PGRAPH_STATUS  : 0x%08x", tmp);
-               nouveau_bitfield_print(nv50_pgraph_status, tmp);
-               pr_cont("\n");
-
-               nouveau_pgraph_vstatus_print(priv, 0, nv50_pgraph_vstatus_0,
-                               nv_rd32(priv, 0x400380));
-               nouveau_pgraph_vstatus_print(priv, 1, nv50_pgraph_vstatus_1,
-                               nv_rd32(priv, 0x400384));
-               nouveau_pgraph_vstatus_print(priv, 2, nv50_pgraph_vstatus_2,
-                               nv_rd32(priv, 0x400388));
-       }
-
-
-       nv_wr32(priv, 0x100c80, 0x00000001);
-       if (!nv_wait(priv, 0x100c80, 0x00000001, 0x00000000))
-               nv_error(priv, "vm flush timeout\n");
-       nv_mask(priv, 0x400500, 0x00000001, 0x00000001);
-       spin_unlock_irqrestore(&priv->lock, flags);
-       return timeout ? -EBUSY : 0;
-}
-
-static const struct nouveau_bitfield nv50_mp_exec_errors[] = {
-       { 0x01, "STACK_UNDERFLOW" },
-       { 0x02, "STACK_MISMATCH" },
-       { 0x04, "QUADON_ACTIVE" },
-       { 0x08, "TIMEOUT" },
-       { 0x10, "INVALID_OPCODE" },
-       { 0x20, "PM_OVERFLOW" },
-       { 0x40, "BREAKPOINT" },
-       {}
-};
-
-static const struct nouveau_bitfield nv50_mpc_traps[] = {
-       { 0x0000001, "LOCAL_LIMIT_READ" },
-       { 0x0000010, "LOCAL_LIMIT_WRITE" },
-       { 0x0000040, "STACK_LIMIT" },
-       { 0x0000100, "GLOBAL_LIMIT_READ" },
-       { 0x0001000, "GLOBAL_LIMIT_WRITE" },
-       { 0x0010000, "MP0" },
-       { 0x0020000, "MP1" },
-       { 0x0040000, "GLOBAL_LIMIT_RED" },
-       { 0x0400000, "GLOBAL_LIMIT_ATOM" },
-       { 0x4000000, "MP2" },
-       {}
-};
-
-static const struct nouveau_bitfield nv50_tex_traps[] = {
-       { 0x00000001, "" }, /* any bit set? */
-       { 0x00000002, "FAULT" },
-       { 0x00000004, "STORAGE_TYPE_MISMATCH" },
-       { 0x00000008, "LINEAR_MISMATCH" },
-       { 0x00000020, "WRONG_MEMTYPE" },
-       {}
-};
-
-static const struct nouveau_bitfield nv50_graph_trap_m2mf[] = {
-       { 0x00000001, "NOTIFY" },
-       { 0x00000002, "IN" },
-       { 0x00000004, "OUT" },
-       {}
-};
-
-static const struct nouveau_bitfield nv50_graph_trap_vfetch[] = {
-       { 0x00000001, "FAULT" },
-       {}
-};
-
-static const struct nouveau_bitfield nv50_graph_trap_strmout[] = {
-       { 0x00000001, "FAULT" },
-       {}
-};
-
-static const struct nouveau_bitfield nv50_graph_trap_ccache[] = {
-       { 0x00000001, "FAULT" },
-       {}
-};
-
-/* There must be a *lot* of these. Will take some time to gather them up. */
-const struct nouveau_enum nv50_data_error_names[] = {
-       { 0x00000003, "INVALID_OPERATION", NULL },
-       { 0x00000004, "INVALID_VALUE", NULL },
-       { 0x00000005, "INVALID_ENUM", NULL },
-       { 0x00000008, "INVALID_OBJECT", NULL },
-       { 0x00000009, "READ_ONLY_OBJECT", NULL },
-       { 0x0000000a, "SUPERVISOR_OBJECT", NULL },
-       { 0x0000000b, "INVALID_ADDRESS_ALIGNMENT", NULL },
-       { 0x0000000c, "INVALID_BITFIELD", NULL },
-       { 0x0000000d, "BEGIN_END_ACTIVE", NULL },
-       { 0x0000000e, "SEMANTIC_COLOR_BACK_OVER_LIMIT", NULL },
-       { 0x0000000f, "VIEWPORT_ID_NEEDS_GP", NULL },
-       { 0x00000010, "RT_DOUBLE_BIND", NULL },
-       { 0x00000011, "RT_TYPES_MISMATCH", NULL },
-       { 0x00000012, "RT_LINEAR_WITH_ZETA", NULL },
-       { 0x00000015, "FP_TOO_FEW_REGS", NULL },
-       { 0x00000016, "ZETA_FORMAT_CSAA_MISMATCH", NULL },
-       { 0x00000017, "RT_LINEAR_WITH_MSAA", NULL },
-       { 0x00000018, "FP_INTERPOLANT_START_OVER_LIMIT", NULL },
-       { 0x00000019, "SEMANTIC_LAYER_OVER_LIMIT", NULL },
-       { 0x0000001a, "RT_INVALID_ALIGNMENT", NULL },
-       { 0x0000001b, "SAMPLER_OVER_LIMIT", NULL },
-       { 0x0000001c, "TEXTURE_OVER_LIMIT", NULL },
-       { 0x0000001e, "GP_TOO_MANY_OUTPUTS", NULL },
-       { 0x0000001f, "RT_BPP128_WITH_MS8", NULL },
-       { 0x00000021, "Z_OUT_OF_BOUNDS", NULL },
-       { 0x00000023, "XY_OUT_OF_BOUNDS", NULL },
-       { 0x00000024, "VP_ZERO_INPUTS", NULL },
-       { 0x00000027, "CP_MORE_PARAMS_THAN_SHARED", NULL },
-       { 0x00000028, "CP_NO_REG_SPACE_STRIPED", NULL },
-       { 0x00000029, "CP_NO_REG_SPACE_PACKED", NULL },
-       { 0x0000002a, "CP_NOT_ENOUGH_WARPS", NULL },
-       { 0x0000002b, "CP_BLOCK_SIZE_MISMATCH", NULL },
-       { 0x0000002c, "CP_NOT_ENOUGH_LOCAL_WARPS", NULL },
-       { 0x0000002d, "CP_NOT_ENOUGH_STACK_WARPS", NULL },
-       { 0x0000002e, "CP_NO_BLOCKDIM_LATCH", NULL },
-       { 0x00000031, "ENG2D_FORMAT_MISMATCH", NULL },
-       { 0x0000003f, "PRIMITIVE_ID_NEEDS_GP", NULL },
-       { 0x00000044, "SEMANTIC_VIEWPORT_OVER_LIMIT", NULL },
-       { 0x00000045, "SEMANTIC_COLOR_FRONT_OVER_LIMIT", NULL },
-       { 0x00000046, "LAYER_ID_NEEDS_GP", NULL },
-       { 0x00000047, "SEMANTIC_CLIP_OVER_LIMIT", NULL },
-       { 0x00000048, "SEMANTIC_PTSZ_OVER_LIMIT", NULL },
-       {}
-};
-
-static const struct nouveau_bitfield nv50_graph_intr_name[] = {
-       { 0x00000001, "NOTIFY" },
-       { 0x00000002, "COMPUTE_QUERY" },
-       { 0x00000010, "ILLEGAL_MTHD" },
-       { 0x00000020, "ILLEGAL_CLASS" },
-       { 0x00000040, "DOUBLE_NOTIFY" },
-       { 0x00001000, "CONTEXT_SWITCH" },
-       { 0x00010000, "BUFFER_NOTIFY" },
-       { 0x00100000, "DATA_ERROR" },
-       { 0x00200000, "TRAP" },
-       { 0x01000000, "SINGLE_STEP" },
-       {}
-};
-
-static const struct nouveau_bitfield nv50_graph_trap_prop[] = {
-       { 0x00000004, "SURF_WIDTH_OVERRUN" },
-       { 0x00000008, "SURF_HEIGHT_OVERRUN" },
-       { 0x00000010, "DST2D_FAULT" },
-       { 0x00000020, "ZETA_FAULT" },
-       { 0x00000040, "RT_FAULT" },
-       { 0x00000080, "CUDA_FAULT" },
-       { 0x00000100, "DST2D_STORAGE_TYPE_MISMATCH" },
-       { 0x00000200, "ZETA_STORAGE_TYPE_MISMATCH" },
-       { 0x00000400, "RT_STORAGE_TYPE_MISMATCH" },
-       { 0x00000800, "DST2D_LINEAR_MISMATCH" },
-       { 0x00001000, "RT_LINEAR_MISMATCH" },
-       {}
-};
-
-static void
-nv50_priv_prop_trap(struct nv50_graph_priv *priv,
-                   u32 ustatus_addr, u32 ustatus, u32 tp)
-{
-       u32 e0c = nv_rd32(priv, ustatus_addr + 0x04);
-       u32 e10 = nv_rd32(priv, ustatus_addr + 0x08);
-       u32 e14 = nv_rd32(priv, ustatus_addr + 0x0c);
-       u32 e18 = nv_rd32(priv, ustatus_addr + 0x10);
-       u32 e1c = nv_rd32(priv, ustatus_addr + 0x14);
-       u32 e20 = nv_rd32(priv, ustatus_addr + 0x18);
-       u32 e24 = nv_rd32(priv, ustatus_addr + 0x1c);
-
-       /* CUDA memory: l[], g[] or stack. */
-       if (ustatus & 0x00000080) {
-               if (e18 & 0x80000000) {
-                       /* g[] read fault? */
-                       nv_error(priv, "TRAP_PROP - TP %d - CUDA_FAULT - Global read fault at address %02x%08x\n",
-                                        tp, e14, e10 | ((e18 >> 24) & 0x1f));
-                       e18 &= ~0x1f000000;
-               } else if (e18 & 0xc) {
-                       /* g[] write fault? */
-                       nv_error(priv, "TRAP_PROP - TP %d - CUDA_FAULT - Global write fault at address %02x%08x\n",
-                                tp, e14, e10 | ((e18 >> 7) & 0x1f));
-                       e18 &= ~0x00000f80;
-               } else {
-                       nv_error(priv, "TRAP_PROP - TP %d - Unknown CUDA fault at address %02x%08x\n",
-                                tp, e14, e10);
-               }
-               ustatus &= ~0x00000080;
-       }
-       if (ustatus) {
-               nv_error(priv, "TRAP_PROP - TP %d -", tp);
-               nouveau_bitfield_print(nv50_graph_trap_prop, ustatus);
-               pr_cont(" - Address %02x%08x\n", e14, e10);
-       }
-       nv_error(priv, "TRAP_PROP - TP %d - e0c: %08x, e18: %08x, e1c: %08x, e20: %08x, e24: %08x\n",
-                tp, e0c, e18, e1c, e20, e24);
-}
-
-static void
-nv50_priv_mp_trap(struct nv50_graph_priv *priv, int tpid, int display)
-{
-       u32 units = nv_rd32(priv, 0x1540);
-       u32 addr, mp10, status, pc, oplow, ophigh;
-       int i;
-       int mps = 0;
-       for (i = 0; i < 4; i++) {
-               if (!(units & 1 << (i+24)))
-                       continue;
-               if (nv_device(priv)->chipset < 0xa0)
-                       addr = 0x408200 + (tpid << 12) + (i << 7);
-               else
-                       addr = 0x408100 + (tpid << 11) + (i << 7);
-               mp10 = nv_rd32(priv, addr + 0x10);
-               status = nv_rd32(priv, addr + 0x14);
-               if (!status)
-                       continue;
-               if (display) {
-                       nv_rd32(priv, addr + 0x20);
-                       pc = nv_rd32(priv, addr + 0x24);
-                       oplow = nv_rd32(priv, addr + 0x70);
-                       ophigh = nv_rd32(priv, addr + 0x74);
-                       nv_error(priv, "TRAP_MP_EXEC - "
-                                       "TP %d MP %d:", tpid, i);
-                       nouveau_bitfield_print(nv50_mp_exec_errors, status);
-                       pr_cont(" at %06x warp %d, opcode %08x %08x\n",
-                                       pc&0xffffff, pc >> 24,
-                                       oplow, ophigh);
-               }
-               nv_wr32(priv, addr + 0x10, mp10);
-               nv_wr32(priv, addr + 0x14, 0);
-               mps++;
-       }
-       if (!mps && display)
-               nv_error(priv, "TRAP_MP_EXEC - TP %d: "
-                               "No MPs claiming errors?\n", tpid);
-}
-
-static void
-nv50_priv_tp_trap(struct nv50_graph_priv *priv, int type, u32 ustatus_old,
-               u32 ustatus_new, int display, const char *name)
-{
-       int tps = 0;
-       u32 units = nv_rd32(priv, 0x1540);
-       int i, r;
-       u32 ustatus_addr, ustatus;
-       for (i = 0; i < 16; i++) {
-               if (!(units & (1 << i)))
-                       continue;
-               if (nv_device(priv)->chipset < 0xa0)
-                       ustatus_addr = ustatus_old + (i << 12);
-               else
-                       ustatus_addr = ustatus_new + (i << 11);
-               ustatus = nv_rd32(priv, ustatus_addr) & 0x7fffffff;
-               if (!ustatus)
-                       continue;
-               tps++;
-               switch (type) {
-               case 6: /* texture error... unknown for now */
-                       if (display) {
-                               nv_error(priv, "magic set %d:\n", i);
-                               for (r = ustatus_addr + 4; r <= ustatus_addr + 0x10; r += 4)
-                                       nv_error(priv, "\t0x%08x: 0x%08x\n", r,
-                                               nv_rd32(priv, r));
-                               if (ustatus) {
-                                       nv_error(priv, "%s - TP%d:", name, i);
-                                       nouveau_bitfield_print(nv50_tex_traps,
-                                                              ustatus);
-                                       pr_cont("\n");
-                                       ustatus = 0;
-                               }
-                       }
-                       break;
-               case 7: /* MP error */
-                       if (ustatus & 0x04030000) {
-                               nv50_priv_mp_trap(priv, i, display);
-                               ustatus &= ~0x04030000;
-                       }
-                       if (ustatus && display) {
-                               nv_error(priv, "%s - TP%d:", name, i);
-                               nouveau_bitfield_print(nv50_mpc_traps, ustatus);
-                               pr_cont("\n");
-                               ustatus = 0;
-                       }
-                       break;
-               case 8: /* PROP error */
-                       if (display)
-                               nv50_priv_prop_trap(
-                                               priv, ustatus_addr, ustatus, i);
-                       ustatus = 0;
-                       break;
-               }
-               if (ustatus) {
-                       if (display)
-                               nv_error(priv, "%s - TP%d: Unhandled ustatus 0x%08x\n", name, i, ustatus);
-               }
-               nv_wr32(priv, ustatus_addr, 0xc0000000);
-       }
-
-       if (!tps && display)
-               nv_warn(priv, "%s - No TPs claiming errors?\n", name);
-}
-
-static int
-nv50_graph_trap_handler(struct nv50_graph_priv *priv, u32 display,
-                       int chid, u64 inst, struct nouveau_object *engctx)
-{
-       u32 status = nv_rd32(priv, 0x400108);
-       u32 ustatus;
-
-       if (!status && display) {
-               nv_error(priv, "TRAP: no units reporting traps?\n");
-               return 1;
-       }
-
-       /* 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(priv, 0x400804) & 0x7fffffff;
-               if (!ustatus && display) {
-                       nv_error(priv, "TRAP_DISPATCH - no ustatus?\n");
-               }
-
-               nv_wr32(priv, 0x400500, 0x00000000);
-
-               /* Known to be triggered by screwed up NOTIFY and COND... */
-               if (ustatus & 0x00000001) {
-                       u32 addr = nv_rd32(priv, 0x400808);
-                       u32 subc = (addr & 0x00070000) >> 16;
-                       u32 mthd = (addr & 0x00001ffc);
-                       u32 datal = nv_rd32(priv, 0x40080c);
-                       u32 datah = nv_rd32(priv, 0x400810);
-                       u32 class = nv_rd32(priv, 0x400814);
-                       u32 r848 = nv_rd32(priv, 0x400848);
-
-                       nv_error(priv, "TRAP DISPATCH_FAULT\n");
-                       if (display && (addr & 0x80000000)) {
-                               nv_error(priv,
-                                        "ch %d [0x%010llx %s] subc %d class 0x%04x mthd 0x%04x data 0x%08x%08x 400808 0x%08x 400848 0x%08x\n",
-                                        chid, inst,
-                                        nouveau_client_name(engctx), subc,
-                                        class, mthd, datah, datal, addr, r848);
-                       } else
-                       if (display) {
-                               nv_error(priv, "no stuck command?\n");
-                       }
-
-                       nv_wr32(priv, 0x400808, 0);
-                       nv_wr32(priv, 0x4008e8, nv_rd32(priv, 0x4008e8) & 3);
-                       nv_wr32(priv, 0x400848, 0);
-                       ustatus &= ~0x00000001;
-               }
-
-               if (ustatus & 0x00000002) {
-                       u32 addr = nv_rd32(priv, 0x40084c);
-                       u32 subc = (addr & 0x00070000) >> 16;
-                       u32 mthd = (addr & 0x00001ffc);
-                       u32 data = nv_rd32(priv, 0x40085c);
-                       u32 class = nv_rd32(priv, 0x400814);
-
-                       nv_error(priv, "TRAP DISPATCH_QUERY\n");
-                       if (display && (addr & 0x80000000)) {
-                               nv_error(priv,
-                                        "ch %d [0x%010llx %s] subc %d class 0x%04x mthd 0x%04x data 0x%08x 40084c 0x%08x\n",
-                                        chid, inst,
-                                        nouveau_client_name(engctx), subc,
-                                        class, mthd, data, addr);
-                       } else
-                       if (display) {
-                               nv_error(priv, "no stuck command?\n");
-                       }
-
-                       nv_wr32(priv, 0x40084c, 0);
-                       ustatus &= ~0x00000002;
-               }
-
-               if (ustatus && display) {
-                       nv_error(priv, "TRAP_DISPATCH (unknown "
-                                     "0x%08x)\n", ustatus);
-               }
-
-               nv_wr32(priv, 0x400804, 0xc0000000);
-               nv_wr32(priv, 0x400108, 0x001);
-               status &= ~0x001;
-               if (!status)
-                       return 0;
-       }
-
-       /* M2MF: Memory to memory copy engine. */
-       if (status & 0x002) {
-               u32 ustatus = nv_rd32(priv, 0x406800) & 0x7fffffff;
-               if (display) {
-                       nv_error(priv, "TRAP_M2MF");
-                       nouveau_bitfield_print(nv50_graph_trap_m2mf, ustatus);
-                       pr_cont("\n");
-                       nv_error(priv, "TRAP_M2MF %08x %08x %08x %08x\n",
-                               nv_rd32(priv, 0x406804), nv_rd32(priv, 0x406808),
-                               nv_rd32(priv, 0x40680c), nv_rd32(priv, 0x406810));
-
-               }
-
-               /* No sane way found yet -- just reset the bugger. */
-               nv_wr32(priv, 0x400040, 2);
-               nv_wr32(priv, 0x400040, 0);
-               nv_wr32(priv, 0x406800, 0xc0000000);
-               nv_wr32(priv, 0x400108, 0x002);
-               status &= ~0x002;
-       }
-
-       /* VFETCH: Fetches data from vertex buffers. */
-       if (status & 0x004) {
-               u32 ustatus = nv_rd32(priv, 0x400c04) & 0x7fffffff;
-               if (display) {
-                       nv_error(priv, "TRAP_VFETCH");
-                       nouveau_bitfield_print(nv50_graph_trap_vfetch, ustatus);
-                       pr_cont("\n");
-                       nv_error(priv, "TRAP_VFETCH %08x %08x %08x %08x\n",
-                               nv_rd32(priv, 0x400c00), nv_rd32(priv, 0x400c08),
-                               nv_rd32(priv, 0x400c0c), nv_rd32(priv, 0x400c10));
-               }
-
-               nv_wr32(priv, 0x400c04, 0xc0000000);
-               nv_wr32(priv, 0x400108, 0x004);
-               status &= ~0x004;
-       }
-
-       /* STRMOUT: DirectX streamout / OpenGL transform feedback. */
-       if (status & 0x008) {
-               ustatus = nv_rd32(priv, 0x401800) & 0x7fffffff;
-               if (display) {
-                       nv_error(priv, "TRAP_STRMOUT");
-                       nouveau_bitfield_print(nv50_graph_trap_strmout, ustatus);
-                       pr_cont("\n");
-                       nv_error(priv, "TRAP_STRMOUT %08x %08x %08x %08x\n",
-                               nv_rd32(priv, 0x401804), nv_rd32(priv, 0x401808),
-                               nv_rd32(priv, 0x40180c), nv_rd32(priv, 0x401810));
-
-               }
-
-               /* No sane way found yet -- just reset the bugger. */
-               nv_wr32(priv, 0x400040, 0x80);
-               nv_wr32(priv, 0x400040, 0);
-               nv_wr32(priv, 0x401800, 0xc0000000);
-               nv_wr32(priv, 0x400108, 0x008);
-               status &= ~0x008;
-       }
-
-       /* CCACHE: Handles code and c[] caches and fills them. */
-       if (status & 0x010) {
-               ustatus = nv_rd32(priv, 0x405018) & 0x7fffffff;
-               if (display) {
-                       nv_error(priv, "TRAP_CCACHE");
-                       nouveau_bitfield_print(nv50_graph_trap_ccache, ustatus);
-                       pr_cont("\n");
-                       nv_error(priv, "TRAP_CCACHE %08x %08x %08x %08x"
-                                    " %08x %08x %08x\n",
-                               nv_rd32(priv, 0x405000), nv_rd32(priv, 0x405004),
-                               nv_rd32(priv, 0x405008), nv_rd32(priv, 0x40500c),
-                               nv_rd32(priv, 0x405010), nv_rd32(priv, 0x405014),
-                               nv_rd32(priv, 0x40501c));
-
-               }
-
-               nv_wr32(priv, 0x405018, 0xc0000000);
-               nv_wr32(priv, 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) {
-               ustatus = nv_rd32(priv, 0x402000) & 0x7fffffff;
-               if (display)
-                       nv_error(priv, "TRAP_UNKC04 0x%08x\n", ustatus);
-               nv_wr32(priv, 0x402000, 0xc0000000);
-               /* no status modifiction on purpose */
-       }
-
-       /* TEXTURE: CUDA texturing units */
-       if (status & 0x040) {
-               nv50_priv_tp_trap(priv, 6, 0x408900, 0x408600, display,
-                                   "TRAP_TEXTURE");
-               nv_wr32(priv, 0x400108, 0x040);
-               status &= ~0x040;
-       }
-
-       /* MP: CUDA execution engines. */
-       if (status & 0x080) {
-               nv50_priv_tp_trap(priv, 7, 0x408314, 0x40831c, display,
-                                   "TRAP_MP");
-               nv_wr32(priv, 0x400108, 0x080);
-               status &= ~0x080;
-       }
-
-       /* PROP:  Handles TP-initiated uncached memory accesses:
-        * l[], g[], stack, 2d surfaces, render targets. */
-       if (status & 0x100) {
-               nv50_priv_tp_trap(priv, 8, 0x408e08, 0x408708, display,
-                                   "TRAP_PROP");
-               nv_wr32(priv, 0x400108, 0x100);
-               status &= ~0x100;
-       }
-
-       if (status) {
-               if (display)
-                       nv_error(priv, "TRAP: unknown 0x%08x\n", status);
-               nv_wr32(priv, 0x400108, status);
-       }
-
-       return 1;
-}
-
-static void
-nv50_graph_intr(struct nouveau_subdev *subdev)
-{
-       struct nouveau_fifo *pfifo = nouveau_fifo(subdev);
-       struct nouveau_engine *engine = nv_engine(subdev);
-       struct nouveau_object *engctx;
-       struct nouveau_handle *handle = NULL;
-       struct nv50_graph_priv *priv = (void *)subdev;
-       u32 stat = nv_rd32(priv, 0x400100);
-       u32 inst = nv_rd32(priv, 0x40032c) & 0x0fffffff;
-       u32 addr = nv_rd32(priv, 0x400704);
-       u32 subc = (addr & 0x00070000) >> 16;
-       u32 mthd = (addr & 0x00001ffc);
-       u32 data = nv_rd32(priv, 0x400708);
-       u32 class = nv_rd32(priv, 0x400814);
-       u32 show = stat, show_bitfield = stat;
-       int chid;
-
-       engctx = nouveau_engctx_get(engine, inst);
-       chid   = pfifo->chid(pfifo, engctx);
-
-       if (stat & 0x00000010) {
-               handle = nouveau_handle_get_class(engctx, class);
-               if (handle && !nv_call(handle->object, mthd, data))
-                       show &= ~0x00000010;
-               nouveau_handle_put(handle);
-       }
-
-       if (show & 0x00100000) {
-               u32 ecode = nv_rd32(priv, 0x400110);
-               nv_error(priv, "DATA_ERROR ");
-               nouveau_enum_print(nv50_data_error_names, ecode);
-               pr_cont("\n");
-               show_bitfield &= ~0x00100000;
-       }
-
-       if (stat & 0x00200000) {
-               if (!nv50_graph_trap_handler(priv, show, chid, (u64)inst << 12,
-                               engctx))
-                       show &= ~0x00200000;
-               show_bitfield &= ~0x00200000;
-       }
-
-       nv_wr32(priv, 0x400100, stat);
-       nv_wr32(priv, 0x400500, 0x00010001);
-
-       if (show) {
-               show &= show_bitfield;
-               if (show) {
-                       nv_error(priv, "%s", "");
-                       nouveau_bitfield_print(nv50_graph_intr_name, show);
-                       pr_cont("\n");
-               }
-               nv_error(priv,
-                        "ch %d [0x%010llx %s] subc %d class 0x%04x mthd 0x%04x data 0x%08x\n",
-                        chid, (u64)inst << 12, nouveau_client_name(engctx),
-                        subc, class, mthd, data);
-       }
-
-       if (nv_rd32(priv, 0x400824) & (1 << 31))
-               nv_wr32(priv, 0x400824, nv_rd32(priv, 0x400824) & ~(1 << 31));
-
-       nouveau_engctx_put(engctx);
-}
-
-static int
-nv50_graph_ctor(struct nouveau_object *parent, struct nouveau_object *engine,
-              struct nouveau_oclass *oclass, void *data, u32 size,
-              struct nouveau_object **pobject)
-{
-       struct nv50_graph_priv *priv;
-       int ret;
-
-       ret = nouveau_graph_create(parent, engine, oclass, true, &priv);
-       *pobject = nv_object(priv);
-       if (ret)
-               return ret;
-
-       nv_subdev(priv)->unit = 0x00201000;
-       nv_subdev(priv)->intr = nv50_graph_intr;
-       nv_engine(priv)->cclass = &nv50_graph_cclass;
-
-       priv->base.units = nv50_graph_units;
-
-       switch (nv_device(priv)->chipset) {
-       case 0x50:
-               nv_engine(priv)->sclass = nv50_graph_sclass;
-               break;
-       case 0x84:
-       case 0x86:
-       case 0x92:
-       case 0x94:
-       case 0x96:
-       case 0x98:
-               nv_engine(priv)->sclass = nv84_graph_sclass;
-               break;
-       case 0xa0:
-       case 0xaa:
-       case 0xac:
-               nv_engine(priv)->sclass = nva0_graph_sclass;
-               break;
-       case 0xa3:
-       case 0xa5:
-       case 0xa8:
-               nv_engine(priv)->sclass = nva3_graph_sclass;
-               break;
-       case 0xaf:
-               nv_engine(priv)->sclass = nvaf_graph_sclass;
-               break;
-
-       }
-
-       /* unfortunate hw bug workaround... */
-       if (nv_device(priv)->chipset != 0x50 &&
-           nv_device(priv)->chipset != 0xac)
-               nv_engine(priv)->tlb_flush = nv84_graph_tlb_flush;
-
-       spin_lock_init(&priv->lock);
-       return 0;
-}
-
-static int
-nv50_graph_init(struct nouveau_object *object)
-{
-       struct nv50_graph_priv *priv = (void *)object;
-       int ret, units, i;
-
-       ret = nouveau_graph_init(&priv->base);
-       if (ret)
-               return ret;
-
-       /* NV_PGRAPH_DEBUG_3_HW_CTX_SWITCH_ENABLED */
-       nv_wr32(priv, 0x40008c, 0x00000004);
-
-       /* reset/enable traps and interrupts */
-       nv_wr32(priv, 0x400804, 0xc0000000);
-       nv_wr32(priv, 0x406800, 0xc0000000);
-       nv_wr32(priv, 0x400c04, 0xc0000000);
-       nv_wr32(priv, 0x401800, 0xc0000000);
-       nv_wr32(priv, 0x405018, 0xc0000000);
-       nv_wr32(priv, 0x402000, 0xc0000000);
-
-       units = nv_rd32(priv, 0x001540);
-       for (i = 0; i < 16; i++) {
-               if (!(units & (1 << i)))
-                       continue;
-
-               if (nv_device(priv)->chipset < 0xa0) {
-                       nv_wr32(priv, 0x408900 + (i << 12), 0xc0000000);
-                       nv_wr32(priv, 0x408e08 + (i << 12), 0xc0000000);
-                       nv_wr32(priv, 0x408314 + (i << 12), 0xc0000000);
-               } else {
-                       nv_wr32(priv, 0x408600 + (i << 11), 0xc0000000);
-                       nv_wr32(priv, 0x408708 + (i << 11), 0xc0000000);
-                       nv_wr32(priv, 0x40831c + (i << 11), 0xc0000000);
-               }
-       }
-
-       nv_wr32(priv, 0x400108, 0xffffffff);
-       nv_wr32(priv, 0x400138, 0xffffffff);
-       nv_wr32(priv, 0x400100, 0xffffffff);
-       nv_wr32(priv, 0x40013c, 0xffffffff);
-       nv_wr32(priv, 0x400500, 0x00010001);
-
-       /* upload context program, initialise ctxctl defaults */
-       ret = nv50_grctx_init(nv_device(priv), &priv->size);
-       if (ret)
-               return ret;
-
-       nv_wr32(priv, 0x400824, 0x00000000);
-       nv_wr32(priv, 0x400828, 0x00000000);
-       nv_wr32(priv, 0x40082c, 0x00000000);
-       nv_wr32(priv, 0x400830, 0x00000000);
-       nv_wr32(priv, 0x40032c, 0x00000000);
-       nv_wr32(priv, 0x400330, 0x00000000);
-
-       /* some unknown zcull magic */
-       switch (nv_device(priv)->chipset & 0xf0) {
-       case 0x50:
-       case 0x80:
-       case 0x90:
-               nv_wr32(priv, 0x402ca8, 0x00000800);
-               break;
-       case 0xa0:
-       default:
-               if (nv_device(priv)->chipset == 0xa0 ||
-                   nv_device(priv)->chipset == 0xaa ||
-                   nv_device(priv)->chipset == 0xac) {
-                       nv_wr32(priv, 0x402ca8, 0x00000802);
-               } else {
-                       nv_wr32(priv, 0x402cc0, 0x00000000);
-                       nv_wr32(priv, 0x402ca8, 0x00000002);
-               }
-
-               break;
-       }
-
-       /* zero out zcull regions */
-       for (i = 0; i < 8; i++) {
-               nv_wr32(priv, 0x402c20 + (i * 0x10), 0x00000000);
-               nv_wr32(priv, 0x402c24 + (i * 0x10), 0x00000000);
-               nv_wr32(priv, 0x402c28 + (i * 0x10), 0x00000000);
-               nv_wr32(priv, 0x402c2c + (i * 0x10), 0x00000000);
-       }
-       return 0;
-}
-
-struct nouveau_oclass
-nv50_graph_oclass = {
-       .handle = NV_ENGINE(GR, 0x50),
-       .ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nv50_graph_ctor,
-               .dtor = _nouveau_graph_dtor,
-               .init = nv50_graph_init,
-               .fini = _nouveau_graph_fini,
-       },
-};
diff --git a/drivers/gpu/drm/nouveau/core/engine/graph/nv50.h b/drivers/gpu/drm/nouveau/core/engine/graph/nv50.h
deleted file mode 100644 (file)
index 0505fb4..0000000
+++ /dev/null
@@ -1,7 +0,0 @@
-#ifndef __NV50_GRAPH_H__
-#define __NV50_GRAPH_H__
-
-int  nv50_grctx_init(struct nouveau_device *, u32 *size);
-void nv50_grctx_fill(struct nouveau_device *, struct nouveau_gpuobj *);
-
-#endif
diff --git a/drivers/gpu/drm/nouveau/core/engine/graph/nvc0.c b/drivers/gpu/drm/nouveau/core/engine/graph/nvc0.c
deleted file mode 100644 (file)
index 17251e4..0000000
+++ /dev/null
@@ -1,1667 +0,0 @@
-/*
- * Copyright 2012 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 "nvc0.h"
-#include "ctxnvc0.h"
-
-/*******************************************************************************
- * Zero Bandwidth Clear
- ******************************************************************************/
-
-static void
-nvc0_graph_zbc_clear_color(struct nvc0_graph_priv *priv, int zbc)
-{
-       if (priv->zbc_color[zbc].format) {
-               nv_wr32(priv, 0x405804, priv->zbc_color[zbc].ds[0]);
-               nv_wr32(priv, 0x405808, priv->zbc_color[zbc].ds[1]);
-               nv_wr32(priv, 0x40580c, priv->zbc_color[zbc].ds[2]);
-               nv_wr32(priv, 0x405810, priv->zbc_color[zbc].ds[3]);
-       }
-       nv_wr32(priv, 0x405814, priv->zbc_color[zbc].format);
-       nv_wr32(priv, 0x405820, zbc);
-       nv_wr32(priv, 0x405824, 0x00000004); /* TRIGGER | WRITE | COLOR */
-}
-
-static int
-nvc0_graph_zbc_color_get(struct nvc0_graph_priv *priv, int format,
-                        const u32 ds[4], const u32 l2[4])
-{
-       struct nouveau_ltc *ltc = nouveau_ltc(priv);
-       int zbc = -ENOSPC, i;
-
-       for (i = ltc->zbc_min; i <= ltc->zbc_max; i++) {
-               if (priv->zbc_color[i].format) {
-                       if (priv->zbc_color[i].format != format)
-                               continue;
-                       if (memcmp(priv->zbc_color[i].ds, ds, sizeof(
-                                  priv->zbc_color[i].ds)))
-                               continue;
-                       if (memcmp(priv->zbc_color[i].l2, l2, sizeof(
-                                  priv->zbc_color[i].l2))) {
-                               WARN_ON(1);
-                               return -EINVAL;
-                       }
-                       return i;
-               } else {
-                       zbc = (zbc < 0) ? i : zbc;
-               }
-       }
-
-       if (zbc < 0)
-               return zbc;
-
-       memcpy(priv->zbc_color[zbc].ds, ds, sizeof(priv->zbc_color[zbc].ds));
-       memcpy(priv->zbc_color[zbc].l2, l2, sizeof(priv->zbc_color[zbc].l2));
-       priv->zbc_color[zbc].format = format;
-       ltc->zbc_color_get(ltc, zbc, l2);
-       nvc0_graph_zbc_clear_color(priv, zbc);
-       return zbc;
-}
-
-static void
-nvc0_graph_zbc_clear_depth(struct nvc0_graph_priv *priv, int zbc)
-{
-       if (priv->zbc_depth[zbc].format)
-               nv_wr32(priv, 0x405818, priv->zbc_depth[zbc].ds);
-       nv_wr32(priv, 0x40581c, priv->zbc_depth[zbc].format);
-       nv_wr32(priv, 0x405820, zbc);
-       nv_wr32(priv, 0x405824, 0x00000005); /* TRIGGER | WRITE | DEPTH */
-}
-
-static int
-nvc0_graph_zbc_depth_get(struct nvc0_graph_priv *priv, int format,
-                        const u32 ds, const u32 l2)
-{
-       struct nouveau_ltc *ltc = nouveau_ltc(priv);
-       int zbc = -ENOSPC, i;
-
-       for (i = ltc->zbc_min; i <= ltc->zbc_max; i++) {
-               if (priv->zbc_depth[i].format) {
-                       if (priv->zbc_depth[i].format != format)
-                               continue;
-                       if (priv->zbc_depth[i].ds != ds)
-                               continue;
-                       if (priv->zbc_depth[i].l2 != l2) {
-                               WARN_ON(1);
-                               return -EINVAL;
-                       }
-                       return i;
-               } else {
-                       zbc = (zbc < 0) ? i : zbc;
-               }
-       }
-
-       if (zbc < 0)
-               return zbc;
-
-       priv->zbc_depth[zbc].format = format;
-       priv->zbc_depth[zbc].ds = ds;
-       priv->zbc_depth[zbc].l2 = l2;
-       ltc->zbc_depth_get(ltc, zbc, l2);
-       nvc0_graph_zbc_clear_depth(priv, zbc);
-       return zbc;
-}
-
-/*******************************************************************************
- * Graphics object classes
- ******************************************************************************/
-
-static int
-nvc0_fermi_mthd_zbc_color(struct nouveau_object *object, void *data, u32 size)
-{
-       struct nvc0_graph_priv *priv = (void *)object->engine;
-       union {
-               struct fermi_a_zbc_color_v0 v0;
-       } *args = data;
-       int ret;
-
-       if (nvif_unpack(args->v0, 0, 0, false)) {
-               switch (args->v0.format) {
-               case FERMI_A_ZBC_COLOR_V0_FMT_ZERO:
-               case FERMI_A_ZBC_COLOR_V0_FMT_UNORM_ONE:
-               case FERMI_A_ZBC_COLOR_V0_FMT_RF32_GF32_BF32_AF32:
-               case FERMI_A_ZBC_COLOR_V0_FMT_R16_G16_B16_A16:
-               case FERMI_A_ZBC_COLOR_V0_FMT_RN16_GN16_BN16_AN16:
-               case FERMI_A_ZBC_COLOR_V0_FMT_RS16_GS16_BS16_AS16:
-               case FERMI_A_ZBC_COLOR_V0_FMT_RU16_GU16_BU16_AU16:
-               case FERMI_A_ZBC_COLOR_V0_FMT_RF16_GF16_BF16_AF16:
-               case FERMI_A_ZBC_COLOR_V0_FMT_A8R8G8B8:
-               case FERMI_A_ZBC_COLOR_V0_FMT_A8RL8GL8BL8:
-               case FERMI_A_ZBC_COLOR_V0_FMT_A2B10G10R10:
-               case FERMI_A_ZBC_COLOR_V0_FMT_AU2BU10GU10RU10:
-               case FERMI_A_ZBC_COLOR_V0_FMT_A8B8G8R8:
-               case FERMI_A_ZBC_COLOR_V0_FMT_A8BL8GL8RL8:
-               case FERMI_A_ZBC_COLOR_V0_FMT_AN8BN8GN8RN8:
-               case FERMI_A_ZBC_COLOR_V0_FMT_AS8BS8GS8RS8:
-               case FERMI_A_ZBC_COLOR_V0_FMT_AU8BU8GU8RU8:
-               case FERMI_A_ZBC_COLOR_V0_FMT_A2R10G10B10:
-               case FERMI_A_ZBC_COLOR_V0_FMT_BF10GF11RF11:
-                       ret = nvc0_graph_zbc_color_get(priv, args->v0.format,
-                                                            args->v0.ds,
-                                                            args->v0.l2);
-                       if (ret >= 0) {
-                               args->v0.index = ret;
-                               return 0;
-                       }
-                       break;
-               default:
-                       return -EINVAL;
-               }
-       }
-
-       return ret;
-}
-
-static int
-nvc0_fermi_mthd_zbc_depth(struct nouveau_object *object, void *data, u32 size)
-{
-       struct nvc0_graph_priv *priv = (void *)object->engine;
-       union {
-               struct fermi_a_zbc_depth_v0 v0;
-       } *args = data;
-       int ret;
-
-       if (nvif_unpack(args->v0, 0, 0, false)) {
-               switch (args->v0.format) {
-               case FERMI_A_ZBC_DEPTH_V0_FMT_FP32:
-                       ret = nvc0_graph_zbc_depth_get(priv, args->v0.format,
-                                                            args->v0.ds,
-                                                            args->v0.l2);
-                       return (ret >= 0) ? 0 : -ENOSPC;
-               default:
-                       return -EINVAL;
-               }
-       }
-
-       return ret;
-}
-
-static int
-nvc0_fermi_mthd(struct nouveau_object *object, u32 mthd, void *data, u32 size)
-{
-       switch (mthd) {
-       case FERMI_A_ZBC_COLOR:
-               return nvc0_fermi_mthd_zbc_color(object, data, size);
-       case FERMI_A_ZBC_DEPTH:
-               return nvc0_fermi_mthd_zbc_depth(object, data, size);
-       default:
-               break;
-       }
-       return -EINVAL;
-}
-
-struct nouveau_ofuncs
-nvc0_fermi_ofuncs = {
-       .ctor = _nouveau_object_ctor,
-       .dtor = nouveau_object_destroy,
-       .init = nouveau_object_init,
-       .fini = nouveau_object_fini,
-       .mthd = nvc0_fermi_mthd,
-};
-
-static int
-nvc0_graph_set_shader_exceptions(struct nouveau_object *object, u32 mthd,
-                                void *pdata, u32 size)
-{
-       struct nvc0_graph_priv *priv = (void *)nv_engine(object);
-       if (size >= sizeof(u32)) {
-               u32 data = *(u32 *)pdata ? 0xffffffff : 0x00000000;
-               nv_wr32(priv, 0x419e44, data);
-               nv_wr32(priv, 0x419e4c, data);
-               return 0;
-       }
-       return -EINVAL;
-}
-
-struct nouveau_omthds
-nvc0_graph_9097_omthds[] = {
-       { 0x1528, 0x1528, nvc0_graph_set_shader_exceptions },
-       {}
-};
-
-struct nouveau_omthds
-nvc0_graph_90c0_omthds[] = {
-       { 0x1528, 0x1528, nvc0_graph_set_shader_exceptions },
-       {}
-};
-
-struct nouveau_oclass
-nvc0_graph_sclass[] = {
-       { 0x902d, &nouveau_object_ofuncs },
-       { 0x9039, &nouveau_object_ofuncs },
-       { FERMI_A, &nvc0_fermi_ofuncs, nvc0_graph_9097_omthds },
-       { FERMI_COMPUTE_A, &nouveau_object_ofuncs, nvc0_graph_90c0_omthds },
-       {}
-};
-
-/*******************************************************************************
- * PGRAPH context
- ******************************************************************************/
-
-int
-nvc0_graph_context_ctor(struct nouveau_object *parent,
-                       struct nouveau_object *engine,
-                       struct nouveau_oclass *oclass, void *args, u32 size,
-                       struct nouveau_object **pobject)
-{
-       struct nouveau_vm *vm = nouveau_client(parent)->vm;
-       struct nvc0_graph_priv *priv = (void *)engine;
-       struct nvc0_graph_data *data = priv->mmio_data;
-       struct nvc0_graph_mmio *mmio = priv->mmio_list;
-       struct nvc0_graph_chan *chan;
-       int ret, i;
-
-       /* allocate memory for context, and fill with default values */
-       ret = nouveau_graph_context_create(parent, engine, oclass, NULL,
-                                          priv->size, 0x100,
-                                          NVOBJ_FLAG_ZERO_ALLOC, &chan);
-       *pobject = nv_object(chan);
-       if (ret)
-               return ret;
-
-       /* allocate memory for a "mmio list" buffer that's used by the HUB
-        * fuc to modify some per-context register settings on first load
-        * of the context.
-        */
-       ret = nouveau_gpuobj_new(nv_object(chan), NULL, 0x1000, 0x100, 0,
-                               &chan->mmio);
-       if (ret)
-               return ret;
-
-       ret = nouveau_gpuobj_map_vm(nv_gpuobj(chan->mmio), vm,
-                                   NV_MEM_ACCESS_RW | NV_MEM_ACCESS_SYS,
-                                   &chan->mmio_vma);
-       if (ret)
-               return ret;
-
-       /* allocate buffers referenced by mmio list */
-       for (i = 0; data->size && i < ARRAY_SIZE(priv->mmio_data); i++) {
-               ret = nouveau_gpuobj_new(nv_object(chan), NULL, data->size,
-                                        data->align, 0, &chan->data[i].mem);
-               if (ret)
-                       return ret;
-
-               ret = nouveau_gpuobj_map_vm(chan->data[i].mem, vm, data->access,
-                                          &chan->data[i].vma);
-               if (ret)
-                       return ret;
-
-               data++;
-       }
-
-       /* finally, fill in the mmio list and point the context at it */
-       for (i = 0; mmio->addr && i < ARRAY_SIZE(priv->mmio_list); i++) {
-               u32 addr = mmio->addr;
-               u32 data = mmio->data;
-
-               if (mmio->buffer >= 0) {
-                       u64 info = chan->data[mmio->buffer].vma.offset;
-                       data |= info >> mmio->shift;
-               }
-
-               nv_wo32(chan->mmio, chan->mmio_nr++ * 4, addr);
-               nv_wo32(chan->mmio, chan->mmio_nr++ * 4, data);
-               mmio++;
-       }
-
-       for (i = 0; i < priv->size; i += 4)
-               nv_wo32(chan, i, priv->data[i / 4]);
-
-       if (!priv->firmware) {
-               nv_wo32(chan, 0x00, chan->mmio_nr / 2);
-               nv_wo32(chan, 0x04, chan->mmio_vma.offset >> 8);
-       } else {
-               nv_wo32(chan, 0xf4, 0);
-               nv_wo32(chan, 0xf8, 0);
-               nv_wo32(chan, 0x10, chan->mmio_nr / 2);
-               nv_wo32(chan, 0x14, lower_32_bits(chan->mmio_vma.offset));
-               nv_wo32(chan, 0x18, upper_32_bits(chan->mmio_vma.offset));
-               nv_wo32(chan, 0x1c, 1);
-               nv_wo32(chan, 0x20, 0);
-               nv_wo32(chan, 0x28, 0);
-               nv_wo32(chan, 0x2c, 0);
-       }
-
-       return 0;
-}
-
-void
-nvc0_graph_context_dtor(struct nouveau_object *object)
-{
-       struct nvc0_graph_chan *chan = (void *)object;
-       int i;
-
-       for (i = 0; i < ARRAY_SIZE(chan->data); i++) {
-               nouveau_gpuobj_unmap(&chan->data[i].vma);
-               nouveau_gpuobj_ref(NULL, &chan->data[i].mem);
-       }
-
-       nouveau_gpuobj_unmap(&chan->mmio_vma);
-       nouveau_gpuobj_ref(NULL, &chan->mmio);
-
-       nouveau_graph_context_destroy(&chan->base);
-}
-
-/*******************************************************************************
- * PGRAPH register lists
- ******************************************************************************/
-
-const struct nvc0_graph_init
-nvc0_graph_init_main_0[] = {
-       { 0x400080,   1, 0x04, 0x003083c2 },
-       { 0x400088,   1, 0x04, 0x00006fe7 },
-       { 0x40008c,   1, 0x04, 0x00000000 },
-       { 0x400090,   1, 0x04, 0x00000030 },
-       { 0x40013c,   1, 0x04, 0x013901f7 },
-       { 0x400140,   1, 0x04, 0x00000100 },
-       { 0x400144,   1, 0x04, 0x00000000 },
-       { 0x400148,   1, 0x04, 0x00000110 },
-       { 0x400138,   1, 0x04, 0x00000000 },
-       { 0x400130,   2, 0x04, 0x00000000 },
-       { 0x400124,   1, 0x04, 0x00000002 },
-       {}
-};
-
-const struct nvc0_graph_init
-nvc0_graph_init_fe_0[] = {
-       { 0x40415c,   1, 0x04, 0x00000000 },
-       { 0x404170,   1, 0x04, 0x00000000 },
-       {}
-};
-
-const struct nvc0_graph_init
-nvc0_graph_init_pri_0[] = {
-       { 0x404488,   2, 0x04, 0x00000000 },
-       {}
-};
-
-const struct nvc0_graph_init
-nvc0_graph_init_rstr2d_0[] = {
-       { 0x407808,   1, 0x04, 0x00000000 },
-       {}
-};
-
-const struct nvc0_graph_init
-nvc0_graph_init_pd_0[] = {
-       { 0x406024,   1, 0x04, 0x00000000 },
-       {}
-};
-
-const struct nvc0_graph_init
-nvc0_graph_init_ds_0[] = {
-       { 0x405844,   1, 0x04, 0x00ffffff },
-       { 0x405850,   1, 0x04, 0x00000000 },
-       { 0x405908,   1, 0x04, 0x00000000 },
-       {}
-};
-
-const struct nvc0_graph_init
-nvc0_graph_init_scc_0[] = {
-       { 0x40803c,   1, 0x04, 0x00000000 },
-       {}
-};
-
-const struct nvc0_graph_init
-nvc0_graph_init_prop_0[] = {
-       { 0x4184a0,   1, 0x04, 0x00000000 },
-       {}
-};
-
-const struct nvc0_graph_init
-nvc0_graph_init_gpc_unk_0[] = {
-       { 0x418604,   1, 0x04, 0x00000000 },
-       { 0x418680,   1, 0x04, 0x00000000 },
-       { 0x418714,   1, 0x04, 0x80000000 },
-       { 0x418384,   1, 0x04, 0x00000000 },
-       {}
-};
-
-const struct nvc0_graph_init
-nvc0_graph_init_setup_0[] = {
-       { 0x418814,   3, 0x04, 0x00000000 },
-       {}
-};
-
-const struct nvc0_graph_init
-nvc0_graph_init_crstr_0[] = {
-       { 0x418b04,   1, 0x04, 0x00000000 },
-       {}
-};
-
-const struct nvc0_graph_init
-nvc0_graph_init_setup_1[] = {
-       { 0x4188c8,   1, 0x04, 0x80000000 },
-       { 0x4188cc,   1, 0x04, 0x00000000 },
-       { 0x4188d0,   1, 0x04, 0x00010000 },
-       { 0x4188d4,   1, 0x04, 0x00000001 },
-       {}
-};
-
-const struct nvc0_graph_init
-nvc0_graph_init_zcull_0[] = {
-       { 0x418910,   1, 0x04, 0x00010001 },
-       { 0x418914,   1, 0x04, 0x00000301 },
-       { 0x418918,   1, 0x04, 0x00800000 },
-       { 0x418980,   1, 0x04, 0x77777770 },
-       { 0x418984,   3, 0x04, 0x77777777 },
-       {}
-};
-
-const struct nvc0_graph_init
-nvc0_graph_init_gpm_0[] = {
-       { 0x418c04,   1, 0x04, 0x00000000 },
-       { 0x418c88,   1, 0x04, 0x00000000 },
-       {}
-};
-
-const struct nvc0_graph_init
-nvc0_graph_init_gpc_unk_1[] = {
-       { 0x418d00,   1, 0x04, 0x00000000 },
-       { 0x418f08,   1, 0x04, 0x00000000 },
-       { 0x418e00,   1, 0x04, 0x00000050 },
-       { 0x418e08,   1, 0x04, 0x00000000 },
-       {}
-};
-
-const struct nvc0_graph_init
-nvc0_graph_init_gcc_0[] = {
-       { 0x41900c,   1, 0x04, 0x00000000 },
-       { 0x419018,   1, 0x04, 0x00000000 },
-       {}
-};
-
-const struct nvc0_graph_init
-nvc0_graph_init_tpccs_0[] = {
-       { 0x419d08,   2, 0x04, 0x00000000 },
-       { 0x419d10,   1, 0x04, 0x00000014 },
-       {}
-};
-
-const struct nvc0_graph_init
-nvc0_graph_init_tex_0[] = {
-       { 0x419ab0,   1, 0x04, 0x00000000 },
-       { 0x419ab8,   1, 0x04, 0x000000e7 },
-       { 0x419abc,   2, 0x04, 0x00000000 },
-       {}
-};
-
-const struct nvc0_graph_init
-nvc0_graph_init_pe_0[] = {
-       { 0x41980c,   3, 0x04, 0x00000000 },
-       { 0x419844,   1, 0x04, 0x00000000 },
-       { 0x41984c,   1, 0x04, 0x00005bc5 },
-       { 0x419850,   4, 0x04, 0x00000000 },
-       {}
-};
-
-const struct nvc0_graph_init
-nvc0_graph_init_l1c_0[] = {
-       { 0x419c98,   1, 0x04, 0x00000000 },
-       { 0x419ca8,   1, 0x04, 0x80000000 },
-       { 0x419cb4,   1, 0x04, 0x00000000 },
-       { 0x419cb8,   1, 0x04, 0x00008bf4 },
-       { 0x419cbc,   1, 0x04, 0x28137606 },
-       { 0x419cc0,   2, 0x04, 0x00000000 },
-       {}
-};
-
-const struct nvc0_graph_init
-nvc0_graph_init_wwdx_0[] = {
-       { 0x419bd4,   1, 0x04, 0x00800000 },
-       { 0x419bdc,   1, 0x04, 0x00000000 },
-       {}
-};
-
-const struct nvc0_graph_init
-nvc0_graph_init_tpccs_1[] = {
-       { 0x419d2c,   1, 0x04, 0x00000000 },
-       {}
-};
-
-const struct nvc0_graph_init
-nvc0_graph_init_mpc_0[] = {
-       { 0x419c0c,   1, 0x04, 0x00000000 },
-       {}
-};
-
-static const struct nvc0_graph_init
-nvc0_graph_init_sm_0[] = {
-       { 0x419e00,   1, 0x04, 0x00000000 },
-       { 0x419ea0,   1, 0x04, 0x00000000 },
-       { 0x419ea4,   1, 0x04, 0x00000100 },
-       { 0x419ea8,   1, 0x04, 0x00001100 },
-       { 0x419eac,   1, 0x04, 0x11100702 },
-       { 0x419eb0,   1, 0x04, 0x00000003 },
-       { 0x419eb4,   4, 0x04, 0x00000000 },
-       { 0x419ec8,   1, 0x04, 0x06060618 },
-       { 0x419ed0,   1, 0x04, 0x0eff0e38 },
-       { 0x419ed4,   1, 0x04, 0x011104f1 },
-       { 0x419edc,   1, 0x04, 0x00000000 },
-       { 0x419f00,   1, 0x04, 0x00000000 },
-       { 0x419f2c,   1, 0x04, 0x00000000 },
-       {}
-};
-
-const struct nvc0_graph_init
-nvc0_graph_init_be_0[] = {
-       { 0x40880c,   1, 0x04, 0x00000000 },
-       { 0x408910,   9, 0x04, 0x00000000 },
-       { 0x408950,   1, 0x04, 0x00000000 },
-       { 0x408954,   1, 0x04, 0x0000ffff },
-       { 0x408984,   1, 0x04, 0x00000000 },
-       { 0x408988,   1, 0x04, 0x08040201 },
-       { 0x40898c,   1, 0x04, 0x80402010 },
-       {}
-};
-
-const struct nvc0_graph_init
-nvc0_graph_init_fe_1[] = {
-       { 0x4040f0,   1, 0x04, 0x00000000 },
-       {}
-};
-
-const struct nvc0_graph_init
-nvc0_graph_init_pe_1[] = {
-       { 0x419880,   1, 0x04, 0x00000002 },
-       {}
-};
-
-static const struct nvc0_graph_pack
-nvc0_graph_pack_mmio[] = {
-       { nvc0_graph_init_main_0 },
-       { nvc0_graph_init_fe_0 },
-       { nvc0_graph_init_pri_0 },
-       { nvc0_graph_init_rstr2d_0 },
-       { nvc0_graph_init_pd_0 },
-       { nvc0_graph_init_ds_0 },
-       { nvc0_graph_init_scc_0 },
-       { nvc0_graph_init_prop_0 },
-       { nvc0_graph_init_gpc_unk_0 },
-       { nvc0_graph_init_setup_0 },
-       { nvc0_graph_init_crstr_0 },
-       { nvc0_graph_init_setup_1 },
-       { nvc0_graph_init_zcull_0 },
-       { nvc0_graph_init_gpm_0 },
-       { nvc0_graph_init_gpc_unk_1 },
-       { nvc0_graph_init_gcc_0 },
-       { nvc0_graph_init_tpccs_0 },
-       { nvc0_graph_init_tex_0 },
-       { nvc0_graph_init_pe_0 },
-       { nvc0_graph_init_l1c_0 },
-       { nvc0_graph_init_wwdx_0 },
-       { nvc0_graph_init_tpccs_1 },
-       { nvc0_graph_init_mpc_0 },
-       { nvc0_graph_init_sm_0 },
-       { nvc0_graph_init_be_0 },
-       { nvc0_graph_init_fe_1 },
-       { nvc0_graph_init_pe_1 },
-       {}
-};
-
-/*******************************************************************************
- * PGRAPH engine/subdev functions
- ******************************************************************************/
-
-void
-nvc0_graph_zbc_init(struct nvc0_graph_priv *priv)
-{
-       const u32  zero[] = { 0x00000000, 0x00000000, 0x00000000, 0x00000000,
-                             0x00000000, 0x00000000, 0x00000000, 0x00000000 };
-       const u32   one[] = { 0x3f800000, 0x3f800000, 0x3f800000, 0x3f800000,
-                             0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff };
-       const u32 f32_0[] = { 0x00000000, 0x00000000, 0x00000000, 0x00000000,
-                             0x00000000, 0x00000000, 0x00000000, 0x00000000 };
-       const u32 f32_1[] = { 0x3f800000, 0x3f800000, 0x3f800000, 0x3f800000,
-                             0x3f800000, 0x3f800000, 0x3f800000, 0x3f800000 };
-       struct nouveau_ltc *ltc = nouveau_ltc(priv);
-       int index;
-
-       if (!priv->zbc_color[0].format) {
-               nvc0_graph_zbc_color_get(priv, 1,  & zero[0],   &zero[4]);
-               nvc0_graph_zbc_color_get(priv, 2,  &  one[0],    &one[4]);
-               nvc0_graph_zbc_color_get(priv, 4,  &f32_0[0],  &f32_0[4]);
-               nvc0_graph_zbc_color_get(priv, 4,  &f32_1[0],  &f32_1[4]);
-               nvc0_graph_zbc_depth_get(priv, 1, 0x00000000, 0x00000000);
-               nvc0_graph_zbc_depth_get(priv, 1, 0x3f800000, 0x3f800000);
-       }
-
-       for (index = ltc->zbc_min; index <= ltc->zbc_max; index++)
-               nvc0_graph_zbc_clear_color(priv, index);
-       for (index = ltc->zbc_min; index <= ltc->zbc_max; index++)
-               nvc0_graph_zbc_clear_depth(priv, index);
-}
-
-void
-nvc0_graph_mmio(struct nvc0_graph_priv *priv, const struct nvc0_graph_pack *p)
-{
-       const struct nvc0_graph_pack *pack;
-       const struct nvc0_graph_init *init;
-
-       pack_for_each_init(init, pack, p) {
-               u32 next = init->addr + init->count * init->pitch;
-               u32 addr = init->addr;
-               while (addr < next) {
-                       nv_wr32(priv, addr, init->data);
-                       addr += init->pitch;
-               }
-       }
-}
-
-void
-nvc0_graph_icmd(struct nvc0_graph_priv *priv, const struct nvc0_graph_pack *p)
-{
-       const struct nvc0_graph_pack *pack;
-       const struct nvc0_graph_init *init;
-       u32 data = 0;
-
-       nv_wr32(priv, 0x400208, 0x80000000);
-
-       pack_for_each_init(init, pack, p) {
-               u32 next = init->addr + init->count * init->pitch;
-               u32 addr = init->addr;
-
-               if ((pack == p && init == p->init) || data != init->data) {
-                       nv_wr32(priv, 0x400204, init->data);
-                       data = init->data;
-               }
-
-               while (addr < next) {
-                       nv_wr32(priv, 0x400200, addr);
-                       nv_wait(priv, 0x400700, 0x00000002, 0x00000000);
-                       addr += init->pitch;
-               }
-       }
-
-       nv_wr32(priv, 0x400208, 0x00000000);
-}
-
-void
-nvc0_graph_mthd(struct nvc0_graph_priv *priv, const struct nvc0_graph_pack *p)
-{
-       const struct nvc0_graph_pack *pack;
-       const struct nvc0_graph_init *init;
-       u32 data = 0;
-
-       pack_for_each_init(init, pack, p) {
-               u32 ctrl = 0x80000000 | pack->type;
-               u32 next = init->addr + init->count * init->pitch;
-               u32 addr = init->addr;
-
-               if ((pack == p && init == p->init) || data != init->data) {
-                       nv_wr32(priv, 0x40448c, init->data);
-                       data = init->data;
-               }
-
-               while (addr < next) {
-                       nv_wr32(priv, 0x404488, ctrl | (addr << 14));
-                       addr += init->pitch;
-               }
-       }
-}
-
-u64
-nvc0_graph_units(struct nouveau_graph *graph)
-{
-       struct nvc0_graph_priv *priv = (void *)graph;
-       u64 cfg;
-
-       cfg  = (u32)priv->gpc_nr;
-       cfg |= (u32)priv->tpc_total << 8;
-       cfg |= (u64)priv->rop_nr << 32;
-
-       return cfg;
-}
-
-static const struct nouveau_enum nve0_sked_error[] = {
-       { 7, "CONSTANT_BUFFER_SIZE" },
-       { 9, "LOCAL_MEMORY_SIZE_POS" },
-       { 10, "LOCAL_MEMORY_SIZE_NEG" },
-       { 11, "WARP_CSTACK_SIZE" },
-       { 12, "TOTAL_TEMP_SIZE" },
-       { 13, "REGISTER_COUNT" },
-       { 18, "TOTAL_THREADS" },
-       { 20, "PROGRAM_OFFSET" },
-       { 21, "SHARED_MEMORY_SIZE" },
-       { 25, "SHARED_CONFIG_TOO_SMALL" },
-       { 26, "TOTAL_REGISTER_COUNT" },
-       {}
-};
-
-static const struct nouveau_enum nvc0_gpc_rop_error[] = {
-       { 1, "RT_PITCH_OVERRUN" },
-       { 4, "RT_WIDTH_OVERRUN" },
-       { 5, "RT_HEIGHT_OVERRUN" },
-       { 7, "ZETA_STORAGE_TYPE_MISMATCH" },
-       { 8, "RT_STORAGE_TYPE_MISMATCH" },
-       { 10, "RT_LINEAR_MISMATCH" },
-       {}
-};
-
-static void
-nvc0_graph_trap_gpc_rop(struct nvc0_graph_priv *priv, int gpc)
-{
-       u32 trap[4];
-       int i;
-
-       trap[0] = nv_rd32(priv, GPC_UNIT(gpc, 0x0420));
-       trap[1] = nv_rd32(priv, GPC_UNIT(gpc, 0x0434));
-       trap[2] = nv_rd32(priv, GPC_UNIT(gpc, 0x0438));
-       trap[3] = nv_rd32(priv, GPC_UNIT(gpc, 0x043c));
-
-       nv_error(priv, "GPC%d/PROP trap:", gpc);
-       for (i = 0; i <= 29; ++i) {
-               if (!(trap[0] & (1 << i)))
-                       continue;
-               pr_cont(" ");
-               nouveau_enum_print(nvc0_gpc_rop_error, i);
-       }
-       pr_cont("\n");
-
-       nv_error(priv, "x = %u, y = %u, format = %x, storage type = %x\n",
-                trap[1] & 0xffff, trap[1] >> 16, (trap[2] >> 8) & 0x3f,
-                trap[3] & 0xff);
-       nv_wr32(priv, GPC_UNIT(gpc, 0x0420), 0xc0000000);
-}
-
-static const struct nouveau_enum nvc0_mp_warp_error[] = {
-       { 0x00, "NO_ERROR" },
-       { 0x01, "STACK_MISMATCH" },
-       { 0x05, "MISALIGNED_PC" },
-       { 0x08, "MISALIGNED_GPR" },
-       { 0x09, "INVALID_OPCODE" },
-       { 0x0d, "GPR_OUT_OF_BOUNDS" },
-       { 0x0e, "MEM_OUT_OF_BOUNDS" },
-       { 0x0f, "UNALIGNED_MEM_ACCESS" },
-       { 0x11, "INVALID_PARAM" },
-       {}
-};
-
-static const struct nouveau_bitfield nvc0_mp_global_error[] = {
-       { 0x00000004, "MULTIPLE_WARP_ERRORS" },
-       { 0x00000008, "OUT_OF_STACK_SPACE" },
-       {}
-};
-
-static void
-nvc0_graph_trap_mp(struct nvc0_graph_priv *priv, int gpc, int tpc)
-{
-       u32 werr = nv_rd32(priv, TPC_UNIT(gpc, tpc, 0x648));
-       u32 gerr = nv_rd32(priv, TPC_UNIT(gpc, tpc, 0x650));
-
-       nv_error(priv, "GPC%i/TPC%i/MP trap:", gpc, tpc);
-       nouveau_bitfield_print(nvc0_mp_global_error, gerr);
-       if (werr) {
-               pr_cont(" ");
-               nouveau_enum_print(nvc0_mp_warp_error, werr & 0xffff);
-       }
-       pr_cont("\n");
-
-       nv_wr32(priv, TPC_UNIT(gpc, tpc, 0x648), 0x00000000);
-       nv_wr32(priv, TPC_UNIT(gpc, tpc, 0x650), gerr);
-}
-
-static void
-nvc0_graph_trap_tpc(struct nvc0_graph_priv *priv, int gpc, int tpc)
-{
-       u32 stat = nv_rd32(priv, TPC_UNIT(gpc, tpc, 0x0508));
-
-       if (stat & 0x00000001) {
-               u32 trap = nv_rd32(priv, TPC_UNIT(gpc, tpc, 0x0224));
-               nv_error(priv, "GPC%d/TPC%d/TEX: 0x%08x\n", gpc, tpc, trap);
-               nv_wr32(priv, TPC_UNIT(gpc, tpc, 0x0224), 0xc0000000);
-               stat &= ~0x00000001;
-       }
-
-       if (stat & 0x00000002) {
-               nvc0_graph_trap_mp(priv, gpc, tpc);
-               stat &= ~0x00000002;
-       }
-
-       if (stat & 0x00000004) {
-               u32 trap = nv_rd32(priv, TPC_UNIT(gpc, tpc, 0x0084));
-               nv_error(priv, "GPC%d/TPC%d/POLY: 0x%08x\n", gpc, tpc, trap);
-               nv_wr32(priv, TPC_UNIT(gpc, tpc, 0x0084), 0xc0000000);
-               stat &= ~0x00000004;
-       }
-
-       if (stat & 0x00000008) {
-               u32 trap = nv_rd32(priv, TPC_UNIT(gpc, tpc, 0x048c));
-               nv_error(priv, "GPC%d/TPC%d/L1C: 0x%08x\n", gpc, tpc, trap);
-               nv_wr32(priv, TPC_UNIT(gpc, tpc, 0x048c), 0xc0000000);
-               stat &= ~0x00000008;
-       }
-
-       if (stat) {
-               nv_error(priv, "GPC%d/TPC%d/0x%08x: unknown\n", gpc, tpc, stat);
-       }
-}
-
-static void
-nvc0_graph_trap_gpc(struct nvc0_graph_priv *priv, int gpc)
-{
-       u32 stat = nv_rd32(priv, GPC_UNIT(gpc, 0x2c90));
-       int tpc;
-
-       if (stat & 0x00000001) {
-               nvc0_graph_trap_gpc_rop(priv, gpc);
-               stat &= ~0x00000001;
-       }
-
-       if (stat & 0x00000002) {
-               u32 trap = nv_rd32(priv, GPC_UNIT(gpc, 0x0900));
-               nv_error(priv, "GPC%d/ZCULL: 0x%08x\n", gpc, trap);
-               nv_wr32(priv, GPC_UNIT(gpc, 0x0900), 0xc0000000);
-               stat &= ~0x00000002;
-       }
-
-       if (stat & 0x00000004) {
-               u32 trap = nv_rd32(priv, GPC_UNIT(gpc, 0x1028));
-               nv_error(priv, "GPC%d/CCACHE: 0x%08x\n", gpc, trap);
-               nv_wr32(priv, GPC_UNIT(gpc, 0x1028), 0xc0000000);
-               stat &= ~0x00000004;
-       }
-
-       if (stat & 0x00000008) {
-               u32 trap = nv_rd32(priv, GPC_UNIT(gpc, 0x0824));
-               nv_error(priv, "GPC%d/ESETUP: 0x%08x\n", gpc, trap);
-               nv_wr32(priv, GPC_UNIT(gpc, 0x0824), 0xc0000000);
-               stat &= ~0x00000009;
-       }
-
-       for (tpc = 0; tpc < priv->tpc_nr[gpc]; tpc++) {
-               u32 mask = 0x00010000 << tpc;
-               if (stat & mask) {
-                       nvc0_graph_trap_tpc(priv, gpc, tpc);
-                       nv_wr32(priv, GPC_UNIT(gpc, 0x2c90), mask);
-                       stat &= ~mask;
-               }
-       }
-
-       if (stat) {
-               nv_error(priv, "GPC%d/0x%08x: unknown\n", gpc, stat);
-       }
-}
-
-static void
-nvc0_graph_trap_intr(struct nvc0_graph_priv *priv)
-{
-       u32 trap = nv_rd32(priv, 0x400108);
-       int rop, gpc, i;
-
-       if (trap & 0x00000001) {
-               u32 stat = nv_rd32(priv, 0x404000);
-               nv_error(priv, "DISPATCH 0x%08x\n", stat);
-               nv_wr32(priv, 0x404000, 0xc0000000);
-               nv_wr32(priv, 0x400108, 0x00000001);
-               trap &= ~0x00000001;
-       }
-
-       if (trap & 0x00000002) {
-               u32 stat = nv_rd32(priv, 0x404600);
-               nv_error(priv, "M2MF 0x%08x\n", stat);
-               nv_wr32(priv, 0x404600, 0xc0000000);
-               nv_wr32(priv, 0x400108, 0x00000002);
-               trap &= ~0x00000002;
-       }
-
-       if (trap & 0x00000008) {
-               u32 stat = nv_rd32(priv, 0x408030);
-               nv_error(priv, "CCACHE 0x%08x\n", stat);
-               nv_wr32(priv, 0x408030, 0xc0000000);
-               nv_wr32(priv, 0x400108, 0x00000008);
-               trap &= ~0x00000008;
-       }
-
-       if (trap & 0x00000010) {
-               u32 stat = nv_rd32(priv, 0x405840);
-               nv_error(priv, "SHADER 0x%08x\n", stat);
-               nv_wr32(priv, 0x405840, 0xc0000000);
-               nv_wr32(priv, 0x400108, 0x00000010);
-               trap &= ~0x00000010;
-       }
-
-       if (trap & 0x00000040) {
-               u32 stat = nv_rd32(priv, 0x40601c);
-               nv_error(priv, "UNK6 0x%08x\n", stat);
-               nv_wr32(priv, 0x40601c, 0xc0000000);
-               nv_wr32(priv, 0x400108, 0x00000040);
-               trap &= ~0x00000040;
-       }
-
-       if (trap & 0x00000080) {
-               u32 stat = nv_rd32(priv, 0x404490);
-               nv_error(priv, "MACRO 0x%08x\n", stat);
-               nv_wr32(priv, 0x404490, 0xc0000000);
-               nv_wr32(priv, 0x400108, 0x00000080);
-               trap &= ~0x00000080;
-       }
-
-       if (trap & 0x00000100) {
-               u32 stat = nv_rd32(priv, 0x407020);
-
-               nv_error(priv, "SKED:");
-               for (i = 0; i <= 29; ++i) {
-                       if (!(stat & (1 << i)))
-                               continue;
-                       pr_cont(" ");
-                       nouveau_enum_print(nve0_sked_error, i);
-               }
-               pr_cont("\n");
-
-               if (stat & 0x3fffffff)
-                       nv_wr32(priv, 0x407020, 0x40000000);
-               nv_wr32(priv, 0x400108, 0x00000100);
-               trap &= ~0x00000100;
-       }
-
-       if (trap & 0x01000000) {
-               u32 stat = nv_rd32(priv, 0x400118);
-               for (gpc = 0; stat && gpc < priv->gpc_nr; gpc++) {
-                       u32 mask = 0x00000001 << gpc;
-                       if (stat & mask) {
-                               nvc0_graph_trap_gpc(priv, gpc);
-                               nv_wr32(priv, 0x400118, mask);
-                               stat &= ~mask;
-                       }
-               }
-               nv_wr32(priv, 0x400108, 0x01000000);
-               trap &= ~0x01000000;
-       }
-
-       if (trap & 0x02000000) {
-               for (rop = 0; rop < priv->rop_nr; rop++) {
-                       u32 statz = nv_rd32(priv, ROP_UNIT(rop, 0x070));
-                       u32 statc = nv_rd32(priv, ROP_UNIT(rop, 0x144));
-                       nv_error(priv, "ROP%d 0x%08x 0x%08x\n",
-                                rop, statz, statc);
-                       nv_wr32(priv, ROP_UNIT(rop, 0x070), 0xc0000000);
-                       nv_wr32(priv, ROP_UNIT(rop, 0x144), 0xc0000000);
-               }
-               nv_wr32(priv, 0x400108, 0x02000000);
-               trap &= ~0x02000000;
-       }
-
-       if (trap) {
-               nv_error(priv, "TRAP UNHANDLED 0x%08x\n", trap);
-               nv_wr32(priv, 0x400108, trap);
-       }
-}
-
-static void
-nvc0_graph_ctxctl_debug_unit(struct nvc0_graph_priv *priv, u32 base)
-{
-       nv_error(priv, "%06x - done 0x%08x\n", base,
-                nv_rd32(priv, base + 0x400));
-       nv_error(priv, "%06x - stat 0x%08x 0x%08x 0x%08x 0x%08x\n", base,
-                nv_rd32(priv, base + 0x800), nv_rd32(priv, base + 0x804),
-                nv_rd32(priv, base + 0x808), nv_rd32(priv, base + 0x80c));
-       nv_error(priv, "%06x - stat 0x%08x 0x%08x 0x%08x 0x%08x\n", base,
-                nv_rd32(priv, base + 0x810), nv_rd32(priv, base + 0x814),
-                nv_rd32(priv, base + 0x818), nv_rd32(priv, base + 0x81c));
-}
-
-void
-nvc0_graph_ctxctl_debug(struct nvc0_graph_priv *priv)
-{
-       u32 gpcnr = nv_rd32(priv, 0x409604) & 0xffff;
-       u32 gpc;
-
-       nvc0_graph_ctxctl_debug_unit(priv, 0x409000);
-       for (gpc = 0; gpc < gpcnr; gpc++)
-               nvc0_graph_ctxctl_debug_unit(priv, 0x502000 + (gpc * 0x8000));
-}
-
-static void
-nvc0_graph_ctxctl_isr(struct nvc0_graph_priv *priv)
-{
-       u32 stat = nv_rd32(priv, 0x409c18);
-
-       if (stat & 0x00000001) {
-               u32 code = nv_rd32(priv, 0x409814);
-               if (code == E_BAD_FWMTHD) {
-                       u32 class = nv_rd32(priv, 0x409808);
-                       u32  addr = nv_rd32(priv, 0x40980c);
-                       u32  subc = (addr & 0x00070000) >> 16;
-                       u32  mthd = (addr & 0x00003ffc);
-                       u32  data = nv_rd32(priv, 0x409810);
-
-                       nv_error(priv, "FECS MTHD subc %d class 0x%04x "
-                                      "mthd 0x%04x data 0x%08x\n",
-                                subc, class, mthd, data);
-
-                       nv_wr32(priv, 0x409c20, 0x00000001);
-                       stat &= ~0x00000001;
-               } else {
-                       nv_error(priv, "FECS ucode error %d\n", code);
-               }
-       }
-
-       if (stat & 0x00080000) {
-               nv_error(priv, "FECS watchdog timeout\n");
-               nvc0_graph_ctxctl_debug(priv);
-               nv_wr32(priv, 0x409c20, 0x00080000);
-               stat &= ~0x00080000;
-       }
-
-       if (stat) {
-               nv_error(priv, "FECS 0x%08x\n", stat);
-               nvc0_graph_ctxctl_debug(priv);
-               nv_wr32(priv, 0x409c20, stat);
-       }
-}
-
-static void
-nvc0_graph_intr(struct nouveau_subdev *subdev)
-{
-       struct nouveau_fifo *pfifo = nouveau_fifo(subdev);
-       struct nouveau_engine *engine = nv_engine(subdev);
-       struct nouveau_object *engctx;
-       struct nouveau_handle *handle;
-       struct nvc0_graph_priv *priv = (void *)subdev;
-       u64 inst = nv_rd32(priv, 0x409b00) & 0x0fffffff;
-       u32 stat = nv_rd32(priv, 0x400100);
-       u32 addr = nv_rd32(priv, 0x400704);
-       u32 mthd = (addr & 0x00003ffc);
-       u32 subc = (addr & 0x00070000) >> 16;
-       u32 data = nv_rd32(priv, 0x400708);
-       u32 code = nv_rd32(priv, 0x400110);
-       u32 class = nv_rd32(priv, 0x404200 + (subc * 4));
-       int chid;
-
-       engctx = nouveau_engctx_get(engine, inst);
-       chid   = pfifo->chid(pfifo, engctx);
-
-       if (stat & 0x00000010) {
-               handle = nouveau_handle_get_class(engctx, class);
-               if (!handle || nv_call(handle->object, mthd, data)) {
-                       nv_error(priv,
-                                "ILLEGAL_MTHD ch %d [0x%010llx %s] subc %d class 0x%04x mthd 0x%04x data 0x%08x\n",
-                                chid, inst << 12, nouveau_client_name(engctx),
-                                subc, class, mthd, data);
-               }
-               nouveau_handle_put(handle);
-               nv_wr32(priv, 0x400100, 0x00000010);
-               stat &= ~0x00000010;
-       }
-
-       if (stat & 0x00000020) {
-               nv_error(priv,
-                        "ILLEGAL_CLASS ch %d [0x%010llx %s] subc %d class 0x%04x mthd 0x%04x data 0x%08x\n",
-                        chid, inst << 12, nouveau_client_name(engctx), subc,
-                        class, mthd, data);
-               nv_wr32(priv, 0x400100, 0x00000020);
-               stat &= ~0x00000020;
-       }
-
-       if (stat & 0x00100000) {
-               nv_error(priv, "DATA_ERROR [");
-               nouveau_enum_print(nv50_data_error_names, code);
-               pr_cont("] ch %d [0x%010llx %s] subc %d class 0x%04x mthd 0x%04x data 0x%08x\n",
-                       chid, inst << 12, nouveau_client_name(engctx), subc,
-                       class, mthd, data);
-               nv_wr32(priv, 0x400100, 0x00100000);
-               stat &= ~0x00100000;
-       }
-
-       if (stat & 0x00200000) {
-               nv_error(priv, "TRAP ch %d [0x%010llx %s]\n", chid, inst << 12,
-                        nouveau_client_name(engctx));
-               nvc0_graph_trap_intr(priv);
-               nv_wr32(priv, 0x400100, 0x00200000);
-               stat &= ~0x00200000;
-       }
-
-       if (stat & 0x00080000) {
-               nvc0_graph_ctxctl_isr(priv);
-               nv_wr32(priv, 0x400100, 0x00080000);
-               stat &= ~0x00080000;
-       }
-
-       if (stat) {
-               nv_error(priv, "unknown stat 0x%08x\n", stat);
-               nv_wr32(priv, 0x400100, stat);
-       }
-
-       nv_wr32(priv, 0x400500, 0x00010001);
-       nouveau_engctx_put(engctx);
-}
-
-void
-nvc0_graph_init_fw(struct nvc0_graph_priv *priv, u32 fuc_base,
-                  struct nvc0_graph_fuc *code, struct nvc0_graph_fuc *data)
-{
-       int i;
-
-       nv_wr32(priv, fuc_base + 0x01c0, 0x01000000);
-       for (i = 0; i < data->size / 4; i++)
-               nv_wr32(priv, fuc_base + 0x01c4, data->data[i]);
-
-       nv_wr32(priv, fuc_base + 0x0180, 0x01000000);
-       for (i = 0; i < code->size / 4; i++) {
-               if ((i & 0x3f) == 0)
-                       nv_wr32(priv, fuc_base + 0x0188, i >> 6);
-               nv_wr32(priv, fuc_base + 0x0184, code->data[i]);
-       }
-
-       /* code must be padded to 0x40 words */
-       for (; i & 0x3f; i++)
-               nv_wr32(priv, fuc_base + 0x0184, 0);
-}
-
-static void
-nvc0_graph_init_csdata(struct nvc0_graph_priv *priv,
-                      const struct nvc0_graph_pack *pack,
-                      u32 falcon, u32 starstar, u32 base)
-{
-       const struct nvc0_graph_pack *iter;
-       const struct nvc0_graph_init *init;
-       u32 addr = ~0, prev = ~0, xfer = 0;
-       u32 star, temp;
-
-       nv_wr32(priv, falcon + 0x01c0, 0x02000000 + starstar);
-       star = nv_rd32(priv, falcon + 0x01c4);
-       temp = nv_rd32(priv, falcon + 0x01c4);
-       if (temp > star)
-               star = temp;
-       nv_wr32(priv, falcon + 0x01c0, 0x01000000 + star);
-
-       pack_for_each_init(init, iter, pack) {
-               u32 head = init->addr - base;
-               u32 tail = head + init->count * init->pitch;
-               while (head < tail) {
-                       if (head != prev + 4 || xfer >= 32) {
-                               if (xfer) {
-                                       u32 data = ((--xfer << 26) | addr);
-                                       nv_wr32(priv, falcon + 0x01c4, data);
-                                       star += 4;
-                               }
-                               addr = head;
-                               xfer = 0;
-                       }
-                       prev = head;
-                       xfer = xfer + 1;
-                       head = head + init->pitch;
-               }
-       }
-
-       nv_wr32(priv, falcon + 0x01c4, (--xfer << 26) | addr);
-       nv_wr32(priv, falcon + 0x01c0, 0x01000004 + starstar);
-       nv_wr32(priv, falcon + 0x01c4, star + 4);
-}
-
-int
-nvc0_graph_init_ctxctl(struct nvc0_graph_priv *priv)
-{
-       struct nvc0_graph_oclass *oclass = (void *)nv_object(priv)->oclass;
-       struct nvc0_grctx_oclass *cclass = (void *)nv_engine(priv)->cclass;
-       int i;
-
-       if (priv->firmware) {
-               /* load fuc microcode */
-               nouveau_mc(priv)->unk260(nouveau_mc(priv), 0);
-               nvc0_graph_init_fw(priv, 0x409000, &priv->fuc409c,
-                                                  &priv->fuc409d);
-               nvc0_graph_init_fw(priv, 0x41a000, &priv->fuc41ac,
-                                                  &priv->fuc41ad);
-               nouveau_mc(priv)->unk260(nouveau_mc(priv), 1);
-
-               /* start both of them running */
-               nv_wr32(priv, 0x409840, 0xffffffff);
-               nv_wr32(priv, 0x41a10c, 0x00000000);
-               nv_wr32(priv, 0x40910c, 0x00000000);
-               nv_wr32(priv, 0x41a100, 0x00000002);
-               nv_wr32(priv, 0x409100, 0x00000002);
-               if (!nv_wait(priv, 0x409800, 0x00000001, 0x00000001))
-                       nv_warn(priv, "0x409800 wait failed\n");
-
-               nv_wr32(priv, 0x409840, 0xffffffff);
-               nv_wr32(priv, 0x409500, 0x7fffffff);
-               nv_wr32(priv, 0x409504, 0x00000021);
-
-               nv_wr32(priv, 0x409840, 0xffffffff);
-               nv_wr32(priv, 0x409500, 0x00000000);
-               nv_wr32(priv, 0x409504, 0x00000010);
-               if (!nv_wait_ne(priv, 0x409800, 0xffffffff, 0x00000000)) {
-                       nv_error(priv, "fuc09 req 0x10 timeout\n");
-                       return -EBUSY;
-               }
-               priv->size = nv_rd32(priv, 0x409800);
-
-               nv_wr32(priv, 0x409840, 0xffffffff);
-               nv_wr32(priv, 0x409500, 0x00000000);
-               nv_wr32(priv, 0x409504, 0x00000016);
-               if (!nv_wait_ne(priv, 0x409800, 0xffffffff, 0x00000000)) {
-                       nv_error(priv, "fuc09 req 0x16 timeout\n");
-                       return -EBUSY;
-               }
-
-               nv_wr32(priv, 0x409840, 0xffffffff);
-               nv_wr32(priv, 0x409500, 0x00000000);
-               nv_wr32(priv, 0x409504, 0x00000025);
-               if (!nv_wait_ne(priv, 0x409800, 0xffffffff, 0x00000000)) {
-                       nv_error(priv, "fuc09 req 0x25 timeout\n");
-                       return -EBUSY;
-               }
-
-               if (nv_device(priv)->chipset >= 0xe0) {
-                       nv_wr32(priv, 0x409800, 0x00000000);
-                       nv_wr32(priv, 0x409500, 0x00000001);
-                       nv_wr32(priv, 0x409504, 0x00000030);
-                       if (!nv_wait_ne(priv, 0x409800, 0xffffffff, 0x00000000)) {
-                               nv_error(priv, "fuc09 req 0x30 timeout\n");
-                               return -EBUSY;
-                       }
-
-                       nv_wr32(priv, 0x409810, 0xb00095c8);
-                       nv_wr32(priv, 0x409800, 0x00000000);
-                       nv_wr32(priv, 0x409500, 0x00000001);
-                       nv_wr32(priv, 0x409504, 0x00000031);
-                       if (!nv_wait_ne(priv, 0x409800, 0xffffffff, 0x00000000)) {
-                               nv_error(priv, "fuc09 req 0x31 timeout\n");
-                               return -EBUSY;
-                       }
-
-                       nv_wr32(priv, 0x409810, 0x00080420);
-                       nv_wr32(priv, 0x409800, 0x00000000);
-                       nv_wr32(priv, 0x409500, 0x00000001);
-                       nv_wr32(priv, 0x409504, 0x00000032);
-                       if (!nv_wait_ne(priv, 0x409800, 0xffffffff, 0x00000000)) {
-                               nv_error(priv, "fuc09 req 0x32 timeout\n");
-                               return -EBUSY;
-                       }
-
-                       nv_wr32(priv, 0x409614, 0x00000070);
-                       nv_wr32(priv, 0x409614, 0x00000770);
-                       nv_wr32(priv, 0x40802c, 0x00000001);
-               }
-
-               if (priv->data == NULL) {
-                       int ret = nvc0_grctx_generate(priv);
-                       if (ret) {
-                               nv_error(priv, "failed to construct context\n");
-                               return ret;
-                       }
-               }
-
-               return 0;
-       } else
-       if (!oclass->fecs.ucode) {
-               return -ENOSYS;
-       }
-
-       /* load HUB microcode */
-       nouveau_mc(priv)->unk260(nouveau_mc(priv), 0);
-       nv_wr32(priv, 0x4091c0, 0x01000000);
-       for (i = 0; i < oclass->fecs.ucode->data.size / 4; i++)
-               nv_wr32(priv, 0x4091c4, oclass->fecs.ucode->data.data[i]);
-
-       nv_wr32(priv, 0x409180, 0x01000000);
-       for (i = 0; i < oclass->fecs.ucode->code.size / 4; i++) {
-               if ((i & 0x3f) == 0)
-                       nv_wr32(priv, 0x409188, i >> 6);
-               nv_wr32(priv, 0x409184, oclass->fecs.ucode->code.data[i]);
-       }
-
-       /* load GPC microcode */
-       nv_wr32(priv, 0x41a1c0, 0x01000000);
-       for (i = 0; i < oclass->gpccs.ucode->data.size / 4; i++)
-               nv_wr32(priv, 0x41a1c4, oclass->gpccs.ucode->data.data[i]);
-
-       nv_wr32(priv, 0x41a180, 0x01000000);
-       for (i = 0; i < oclass->gpccs.ucode->code.size / 4; i++) {
-               if ((i & 0x3f) == 0)
-                       nv_wr32(priv, 0x41a188, i >> 6);
-               nv_wr32(priv, 0x41a184, oclass->gpccs.ucode->code.data[i]);
-       }
-       nouveau_mc(priv)->unk260(nouveau_mc(priv), 1);
-
-       /* load register lists */
-       nvc0_graph_init_csdata(priv, cclass->hub, 0x409000, 0x000, 0x000000);
-       nvc0_graph_init_csdata(priv, cclass->gpc, 0x41a000, 0x000, 0x418000);
-       nvc0_graph_init_csdata(priv, cclass->tpc, 0x41a000, 0x004, 0x419800);
-       nvc0_graph_init_csdata(priv, cclass->ppc, 0x41a000, 0x008, 0x41be00);
-
-       /* start HUB ucode running, it'll init the GPCs */
-       nv_wr32(priv, 0x40910c, 0x00000000);
-       nv_wr32(priv, 0x409100, 0x00000002);
-       if (!nv_wait(priv, 0x409800, 0x80000000, 0x80000000)) {
-               nv_error(priv, "HUB_INIT timed out\n");
-               nvc0_graph_ctxctl_debug(priv);
-               return -EBUSY;
-       }
-
-       priv->size = nv_rd32(priv, 0x409804);
-       if (priv->data == NULL) {
-               int ret = nvc0_grctx_generate(priv);
-               if (ret) {
-                       nv_error(priv, "failed to construct context\n");
-                       return ret;
-               }
-       }
-
-       return 0;
-}
-
-int
-nvc0_graph_init(struct nouveau_object *object)
-{
-       struct nvc0_graph_oclass *oclass = (void *)object->oclass;
-       struct nvc0_graph_priv *priv = (void *)object;
-       const u32 magicgpc918 = DIV_ROUND_UP(0x00800000, priv->tpc_total);
-       u32 data[TPC_MAX / 8] = {};
-       u8  tpcnr[GPC_MAX];
-       int gpc, tpc, rop;
-       int ret, i;
-
-       ret = nouveau_graph_init(&priv->base);
-       if (ret)
-               return ret;
-
-       nv_wr32(priv, GPC_BCAST(0x0880), 0x00000000);
-       nv_wr32(priv, GPC_BCAST(0x08a4), 0x00000000);
-       nv_wr32(priv, GPC_BCAST(0x0888), 0x00000000);
-       nv_wr32(priv, GPC_BCAST(0x088c), 0x00000000);
-       nv_wr32(priv, GPC_BCAST(0x0890), 0x00000000);
-       nv_wr32(priv, GPC_BCAST(0x0894), 0x00000000);
-       nv_wr32(priv, GPC_BCAST(0x08b4), priv->unk4188b4->addr >> 8);
-       nv_wr32(priv, GPC_BCAST(0x08b8), priv->unk4188b8->addr >> 8);
-
-       nvc0_graph_mmio(priv, oclass->mmio);
-
-       memcpy(tpcnr, priv->tpc_nr, sizeof(priv->tpc_nr));
-       for (i = 0, gpc = -1; i < priv->tpc_total; i++) {
-               do {
-                       gpc = (gpc + 1) % priv->gpc_nr;
-               } while (!tpcnr[gpc]);
-               tpc = priv->tpc_nr[gpc] - tpcnr[gpc]--;
-
-               data[i / 8] |= tpc << ((i % 8) * 4);
-       }
-
-       nv_wr32(priv, GPC_BCAST(0x0980), data[0]);
-       nv_wr32(priv, GPC_BCAST(0x0984), data[1]);
-       nv_wr32(priv, GPC_BCAST(0x0988), data[2]);
-       nv_wr32(priv, GPC_BCAST(0x098c), data[3]);
-
-       for (gpc = 0; gpc < priv->gpc_nr; gpc++) {
-               nv_wr32(priv, GPC_UNIT(gpc, 0x0914),
-                       priv->magic_not_rop_nr << 8 | priv->tpc_nr[gpc]);
-               nv_wr32(priv, GPC_UNIT(gpc, 0x0910), 0x00040000 |
-                       priv->tpc_total);
-               nv_wr32(priv, GPC_UNIT(gpc, 0x0918), magicgpc918);
-       }
-
-       if (nv_device(priv)->chipset != 0xd7)
-               nv_wr32(priv, GPC_BCAST(0x1bd4), magicgpc918);
-       else
-               nv_wr32(priv, GPC_BCAST(0x3fd4), magicgpc918);
-
-       nv_wr32(priv, GPC_BCAST(0x08ac), nv_rd32(priv, 0x100800));
-
-       nv_wr32(priv, 0x400500, 0x00010001);
-
-       nv_wr32(priv, 0x400100, 0xffffffff);
-       nv_wr32(priv, 0x40013c, 0xffffffff);
-
-       nv_wr32(priv, 0x409c24, 0x000f0000);
-       nv_wr32(priv, 0x404000, 0xc0000000);
-       nv_wr32(priv, 0x404600, 0xc0000000);
-       nv_wr32(priv, 0x408030, 0xc0000000);
-       nv_wr32(priv, 0x40601c, 0xc0000000);
-       nv_wr32(priv, 0x404490, 0xc0000000);
-       nv_wr32(priv, 0x406018, 0xc0000000);
-       nv_wr32(priv, 0x405840, 0xc0000000);
-       nv_wr32(priv, 0x405844, 0x00ffffff);
-       nv_mask(priv, 0x419cc0, 0x00000008, 0x00000008);
-       nv_mask(priv, 0x419eb4, 0x00001000, 0x00001000);
-
-       for (gpc = 0; gpc < priv->gpc_nr; gpc++) {
-               nv_wr32(priv, GPC_UNIT(gpc, 0x0420), 0xc0000000);
-               nv_wr32(priv, GPC_UNIT(gpc, 0x0900), 0xc0000000);
-               nv_wr32(priv, GPC_UNIT(gpc, 0x1028), 0xc0000000);
-               nv_wr32(priv, GPC_UNIT(gpc, 0x0824), 0xc0000000);
-               for (tpc = 0; tpc < priv->tpc_nr[gpc]; tpc++) {
-                       nv_wr32(priv, TPC_UNIT(gpc, tpc, 0x508), 0xffffffff);
-                       nv_wr32(priv, TPC_UNIT(gpc, tpc, 0x50c), 0xffffffff);
-                       nv_wr32(priv, TPC_UNIT(gpc, tpc, 0x224), 0xc0000000);
-                       nv_wr32(priv, TPC_UNIT(gpc, tpc, 0x48c), 0xc0000000);
-                       nv_wr32(priv, TPC_UNIT(gpc, tpc, 0x084), 0xc0000000);
-                       nv_wr32(priv, TPC_UNIT(gpc, tpc, 0x644), 0x001ffffe);
-                       nv_wr32(priv, TPC_UNIT(gpc, tpc, 0x64c), 0x0000000f);
-               }
-               nv_wr32(priv, GPC_UNIT(gpc, 0x2c90), 0xffffffff);
-               nv_wr32(priv, GPC_UNIT(gpc, 0x2c94), 0xffffffff);
-       }
-
-       for (rop = 0; rop < priv->rop_nr; rop++) {
-               nv_wr32(priv, ROP_UNIT(rop, 0x144), 0xc0000000);
-               nv_wr32(priv, ROP_UNIT(rop, 0x070), 0xc0000000);
-               nv_wr32(priv, ROP_UNIT(rop, 0x204), 0xffffffff);
-               nv_wr32(priv, ROP_UNIT(rop, 0x208), 0xffffffff);
-       }
-
-       nv_wr32(priv, 0x400108, 0xffffffff);
-       nv_wr32(priv, 0x400138, 0xffffffff);
-       nv_wr32(priv, 0x400118, 0xffffffff);
-       nv_wr32(priv, 0x400130, 0xffffffff);
-       nv_wr32(priv, 0x40011c, 0xffffffff);
-       nv_wr32(priv, 0x400134, 0xffffffff);
-
-       nv_wr32(priv, 0x400054, 0x34ce3464);
-
-       nvc0_graph_zbc_init(priv);
-
-       return nvc0_graph_init_ctxctl(priv);
-}
-
-static void
-nvc0_graph_dtor_fw(struct nvc0_graph_fuc *fuc)
-{
-       kfree(fuc->data);
-       fuc->data = NULL;
-}
-
-int
-nvc0_graph_ctor_fw(struct nvc0_graph_priv *priv, const char *fwname,
-                  struct nvc0_graph_fuc *fuc)
-{
-       struct nouveau_device *device = nv_device(priv);
-       const struct firmware *fw;
-       char f[32];
-       int ret;
-
-       snprintf(f, sizeof(f), "nouveau/nv%02x_%s", device->chipset, fwname);
-       ret = request_firmware(&fw, f, nv_device_base(device));
-       if (ret) {
-               snprintf(f, sizeof(f), "nouveau/%s", fwname);
-               ret = request_firmware(&fw, f, nv_device_base(device));
-               if (ret) {
-                       nv_error(priv, "failed to load %s\n", fwname);
-                       return ret;
-               }
-       }
-
-       fuc->size = fw->size;
-       fuc->data = kmemdup(fw->data, fuc->size, GFP_KERNEL);
-       release_firmware(fw);
-       return (fuc->data != NULL) ? 0 : -ENOMEM;
-}
-
-void
-nvc0_graph_dtor(struct nouveau_object *object)
-{
-       struct nvc0_graph_priv *priv = (void *)object;
-
-       kfree(priv->data);
-
-       nvc0_graph_dtor_fw(&priv->fuc409c);
-       nvc0_graph_dtor_fw(&priv->fuc409d);
-       nvc0_graph_dtor_fw(&priv->fuc41ac);
-       nvc0_graph_dtor_fw(&priv->fuc41ad);
-
-       nouveau_gpuobj_ref(NULL, &priv->unk4188b8);
-       nouveau_gpuobj_ref(NULL, &priv->unk4188b4);
-
-       nouveau_graph_destroy(&priv->base);
-}
-
-int
-nvc0_graph_ctor(struct nouveau_object *parent, struct nouveau_object *engine,
-               struct nouveau_oclass *bclass, void *data, u32 size,
-               struct nouveau_object **pobject)
-{
-       struct nvc0_graph_oclass *oclass = (void *)bclass;
-       struct nouveau_device *device = nv_device(parent);
-       struct nvc0_graph_priv *priv;
-       bool use_ext_fw, enable;
-       int ret, i, j;
-
-       use_ext_fw = nouveau_boolopt(device->cfgopt, "NvGrUseFW",
-                                    oclass->fecs.ucode == NULL);
-       enable = use_ext_fw || oclass->fecs.ucode != NULL;
-
-       ret = nouveau_graph_create(parent, engine, bclass, enable, &priv);
-       *pobject = nv_object(priv);
-       if (ret)
-               return ret;
-
-       nv_subdev(priv)->unit = 0x08001000;
-       nv_subdev(priv)->intr = nvc0_graph_intr;
-
-       priv->base.units = nvc0_graph_units;
-
-       if (use_ext_fw) {
-               nv_info(priv, "using external firmware\n");
-               if (nvc0_graph_ctor_fw(priv, "fuc409c", &priv->fuc409c) ||
-                   nvc0_graph_ctor_fw(priv, "fuc409d", &priv->fuc409d) ||
-                   nvc0_graph_ctor_fw(priv, "fuc41ac", &priv->fuc41ac) ||
-                   nvc0_graph_ctor_fw(priv, "fuc41ad", &priv->fuc41ad))
-                       return -ENODEV;
-               priv->firmware = true;
-       }
-
-       ret = nouveau_gpuobj_new(nv_object(priv), NULL, 0x1000, 256, 0,
-                               &priv->unk4188b4);
-       if (ret)
-               return ret;
-
-       ret = nouveau_gpuobj_new(nv_object(priv), NULL, 0x1000, 256, 0,
-                               &priv->unk4188b8);
-       if (ret)
-               return ret;
-
-       for (i = 0; i < 0x1000; i += 4) {
-               nv_wo32(priv->unk4188b4, i, 0x00000010);
-               nv_wo32(priv->unk4188b8, i, 0x00000010);
-       }
-
-       priv->rop_nr = (nv_rd32(priv, 0x409604) & 0x001f0000) >> 16;
-       priv->gpc_nr =  nv_rd32(priv, 0x409604) & 0x0000001f;
-       for (i = 0; i < priv->gpc_nr; i++) {
-               priv->tpc_nr[i]  = nv_rd32(priv, GPC_UNIT(i, 0x2608));
-               priv->tpc_total += priv->tpc_nr[i];
-               priv->ppc_nr[i]  = oclass->ppc_nr;
-               for (j = 0; j < priv->ppc_nr[i]; j++) {
-                       u8 mask = nv_rd32(priv, GPC_UNIT(i, 0x0c30 + (j * 4)));
-                       priv->ppc_tpc_nr[i][j] = hweight8(mask);
-               }
-       }
-
-       /*XXX: these need figuring out... though it might not even matter */
-       switch (nv_device(priv)->chipset) {
-       case 0xc0:
-               if (priv->tpc_total == 11) { /* 465, 3/4/4/0, 4 */
-                       priv->magic_not_rop_nr = 0x07;
-               } else
-               if (priv->tpc_total == 14) { /* 470, 3/3/4/4, 5 */
-                       priv->magic_not_rop_nr = 0x05;
-               } else
-               if (priv->tpc_total == 15) { /* 480, 3/4/4/4, 6 */
-                       priv->magic_not_rop_nr = 0x06;
-               }
-               break;
-       case 0xc3: /* 450, 4/0/0/0, 2 */
-               priv->magic_not_rop_nr = 0x03;
-               break;
-       case 0xc4: /* 460, 3/4/0/0, 4 */
-               priv->magic_not_rop_nr = 0x01;
-               break;
-       case 0xc1: /* 2/0/0/0, 1 */
-               priv->magic_not_rop_nr = 0x01;
-               break;
-       case 0xc8: /* 4/4/3/4, 5 */
-               priv->magic_not_rop_nr = 0x06;
-               break;
-       case 0xce: /* 4/4/0/0, 4 */
-               priv->magic_not_rop_nr = 0x03;
-               break;
-       case 0xcf: /* 4/0/0/0, 3 */
-               priv->magic_not_rop_nr = 0x03;
-               break;
-       case 0xd7:
-       case 0xd9: /* 1/0/0/0, 1 */
-               priv->magic_not_rop_nr = 0x01;
-               break;
-       }
-
-       nv_engine(priv)->cclass = *oclass->cclass;
-       nv_engine(priv)->sclass =  oclass->sclass;
-       return 0;
-}
-
-#include "fuc/hubnvc0.fuc.h"
-
-struct nvc0_graph_ucode
-nvc0_graph_fecs_ucode = {
-       .code.data = nvc0_grhub_code,
-       .code.size = sizeof(nvc0_grhub_code),
-       .data.data = nvc0_grhub_data,
-       .data.size = sizeof(nvc0_grhub_data),
-};
-
-#include "fuc/gpcnvc0.fuc.h"
-
-struct nvc0_graph_ucode
-nvc0_graph_gpccs_ucode = {
-       .code.data = nvc0_grgpc_code,
-       .code.size = sizeof(nvc0_grgpc_code),
-       .data.data = nvc0_grgpc_data,
-       .data.size = sizeof(nvc0_grgpc_data),
-};
-
-struct nouveau_oclass *
-nvc0_graph_oclass = &(struct nvc0_graph_oclass) {
-       .base.handle = NV_ENGINE(GR, 0xc0),
-       .base.ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nvc0_graph_ctor,
-               .dtor = nvc0_graph_dtor,
-               .init = nvc0_graph_init,
-               .fini = _nouveau_graph_fini,
-       },
-       .cclass = &nvc0_grctx_oclass,
-       .sclass =  nvc0_graph_sclass,
-       .mmio = nvc0_graph_pack_mmio,
-       .fecs.ucode = &nvc0_graph_fecs_ucode,
-       .gpccs.ucode = &nvc0_graph_gpccs_ucode,
-}.base;
diff --git a/drivers/gpu/drm/nouveau/core/engine/graph/nvc0.h b/drivers/gpu/drm/nouveau/core/engine/graph/nvc0.h
deleted file mode 100644 (file)
index 7ed9e89..0000000
+++ /dev/null
@@ -1,270 +0,0 @@
-/*
- * 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 __NVC0_GRAPH_H__
-#define __NVC0_GRAPH_H__
-
-#include <core/client.h>
-#include <core/handle.h>
-#include <core/gpuobj.h>
-#include <core/option.h>
-
-#include <nvif/unpack.h>
-#include <nvif/class.h>
-
-#include <subdev/fb.h>
-#include <subdev/vm.h>
-#include <subdev/bar.h>
-#include <subdev/timer.h>
-#include <subdev/mc.h>
-#include <subdev/ltc.h>
-
-#include <engine/fifo.h>
-#include <engine/graph.h>
-
-#include "fuc/os.h"
-
-#define GPC_MAX 32
-#define TPC_MAX (GPC_MAX * 8)
-
-#define ROP_BCAST(r)      (0x408800 + (r))
-#define ROP_UNIT(u, r)    (0x410000 + (u) * 0x400 + (r))
-#define GPC_BCAST(r)      (0x418000 + (r))
-#define GPC_UNIT(t, r)    (0x500000 + (t) * 0x8000 + (r))
-#define PPC_UNIT(t, m, r) (0x503000 + (t) * 0x8000 + (m) * 0x200 + (r))
-#define TPC_UNIT(t, m, r) (0x504000 + (t) * 0x8000 + (m) * 0x800 + (r))
-
-struct nvc0_graph_data {
-       u32 size;
-       u32 align;
-       u32 access;
-};
-
-struct nvc0_graph_mmio {
-       u32 addr;
-       u32 data;
-       u32 shift;
-       int buffer;
-};
-
-struct nvc0_graph_fuc {
-       u32 *data;
-       u32  size;
-};
-
-struct nvc0_graph_zbc_color {
-       u32 format;
-       u32 ds[4];
-       u32 l2[4];
-};
-
-struct nvc0_graph_zbc_depth {
-       u32 format;
-       u32 ds;
-       u32 l2;
-};
-
-struct nvc0_graph_priv {
-       struct nouveau_graph base;
-
-       struct nvc0_graph_fuc fuc409c;
-       struct nvc0_graph_fuc fuc409d;
-       struct nvc0_graph_fuc fuc41ac;
-       struct nvc0_graph_fuc fuc41ad;
-       bool firmware;
-
-       struct nvc0_graph_zbc_color zbc_color[NOUVEAU_LTC_MAX_ZBC_CNT];
-       struct nvc0_graph_zbc_depth zbc_depth[NOUVEAU_LTC_MAX_ZBC_CNT];
-
-       u8 rop_nr;
-       u8 gpc_nr;
-       u8 tpc_nr[GPC_MAX];
-       u8 tpc_total;
-       u8 ppc_nr[GPC_MAX];
-       u8 ppc_tpc_nr[GPC_MAX][4];
-
-       struct nouveau_gpuobj *unk4188b4;
-       struct nouveau_gpuobj *unk4188b8;
-
-       struct nvc0_graph_data mmio_data[4];
-       struct nvc0_graph_mmio mmio_list[4096/8];
-       u32  size;
-       u32 *data;
-
-       u8 magic_not_rop_nr;
-};
-
-struct nvc0_graph_chan {
-       struct nouveau_graph_chan base;
-
-       struct nouveau_gpuobj *mmio;
-       struct nouveau_vma mmio_vma;
-       int mmio_nr;
-       struct {
-               struct nouveau_gpuobj *mem;
-               struct nouveau_vma vma;
-       } data[4];
-};
-
-int  nvc0_graph_context_ctor(struct nouveau_object *, struct nouveau_object *,
-                            struct nouveau_oclass *, void *, u32,
-                            struct nouveau_object **);
-void nvc0_graph_context_dtor(struct nouveau_object *);
-
-void nvc0_graph_ctxctl_debug(struct nvc0_graph_priv *);
-
-u64  nvc0_graph_units(struct nouveau_graph *);
-int  nvc0_graph_ctor(struct nouveau_object *, struct nouveau_object *,
-                    struct nouveau_oclass *, void *data, u32 size,
-                    struct nouveau_object **);
-void nvc0_graph_dtor(struct nouveau_object *);
-int  nvc0_graph_init(struct nouveau_object *);
-void nvc0_graph_zbc_init(struct nvc0_graph_priv *);
-
-int  nve4_graph_fini(struct nouveau_object *, bool);
-int  nve4_graph_init(struct nouveau_object *);
-
-int  nvf0_graph_fini(struct nouveau_object *, bool);
-
-extern struct nouveau_ofuncs nvc0_fermi_ofuncs;
-
-extern struct nouveau_oclass nvc0_graph_sclass[];
-extern struct nouveau_omthds nvc0_graph_9097_omthds[];
-extern struct nouveau_omthds nvc0_graph_90c0_omthds[];
-extern struct nouveau_oclass nvc8_graph_sclass[];
-extern struct nouveau_oclass nvf0_graph_sclass[];
-
-struct nvc0_graph_init {
-       u32 addr;
-       u8  count;
-       u8  pitch;
-       u32 data;
-};
-
-struct nvc0_graph_pack {
-       const struct nvc0_graph_init *init;
-       u32 type;
-};
-
-#define pack_for_each_init(init, pack, head)                                   \
-       for (pack = head; pack && pack->init; pack++)                          \
-                 for (init = pack->init; init && init->count; init++)
-
-struct nvc0_graph_ucode {
-       struct nvc0_graph_fuc code;
-       struct nvc0_graph_fuc data;
-};
-
-extern struct nvc0_graph_ucode nvc0_graph_fecs_ucode;
-extern struct nvc0_graph_ucode nvc0_graph_gpccs_ucode;
-
-extern struct nvc0_graph_ucode nvf0_graph_fecs_ucode;
-extern struct nvc0_graph_ucode nvf0_graph_gpccs_ucode;
-
-struct nvc0_graph_oclass {
-       struct nouveau_oclass base;
-       struct nouveau_oclass **cclass;
-       struct nouveau_oclass *sclass;
-       const struct nvc0_graph_pack *mmio;
-       struct {
-               struct nvc0_graph_ucode *ucode;
-       } fecs;
-       struct {
-               struct nvc0_graph_ucode *ucode;
-       } gpccs;
-       int ppc_nr;
-};
-
-void nvc0_graph_mmio(struct nvc0_graph_priv *, const struct nvc0_graph_pack *);
-void nvc0_graph_icmd(struct nvc0_graph_priv *, const struct nvc0_graph_pack *);
-void nvc0_graph_mthd(struct nvc0_graph_priv *, const struct nvc0_graph_pack *);
-int  nvc0_graph_init_ctxctl(struct nvc0_graph_priv *);
-
-/* register init value lists */
-
-extern const struct nvc0_graph_init nvc0_graph_init_main_0[];
-extern const struct nvc0_graph_init nvc0_graph_init_fe_0[];
-extern const struct nvc0_graph_init nvc0_graph_init_pri_0[];
-extern const struct nvc0_graph_init nvc0_graph_init_rstr2d_0[];
-extern const struct nvc0_graph_init nvc0_graph_init_pd_0[];
-extern const struct nvc0_graph_init nvc0_graph_init_ds_0[];
-extern const struct nvc0_graph_init nvc0_graph_init_scc_0[];
-extern const struct nvc0_graph_init nvc0_graph_init_prop_0[];
-extern const struct nvc0_graph_init nvc0_graph_init_gpc_unk_0[];
-extern const struct nvc0_graph_init nvc0_graph_init_setup_0[];
-extern const struct nvc0_graph_init nvc0_graph_init_crstr_0[];
-extern const struct nvc0_graph_init nvc0_graph_init_setup_1[];
-extern const struct nvc0_graph_init nvc0_graph_init_zcull_0[];
-extern const struct nvc0_graph_init nvc0_graph_init_gpm_0[];
-extern const struct nvc0_graph_init nvc0_graph_init_gpc_unk_1[];
-extern const struct nvc0_graph_init nvc0_graph_init_gcc_0[];
-extern const struct nvc0_graph_init nvc0_graph_init_tpccs_0[];
-extern const struct nvc0_graph_init nvc0_graph_init_tex_0[];
-extern const struct nvc0_graph_init nvc0_graph_init_pe_0[];
-extern const struct nvc0_graph_init nvc0_graph_init_l1c_0[];
-extern const struct nvc0_graph_init nvc0_graph_init_wwdx_0[];
-extern const struct nvc0_graph_init nvc0_graph_init_tpccs_1[];
-extern const struct nvc0_graph_init nvc0_graph_init_mpc_0[];
-extern const struct nvc0_graph_init nvc0_graph_init_be_0[];
-extern const struct nvc0_graph_init nvc0_graph_init_fe_1[];
-extern const struct nvc0_graph_init nvc0_graph_init_pe_1[];
-
-extern const struct nvc0_graph_init nvc4_graph_init_ds_0[];
-extern const struct nvc0_graph_init nvc4_graph_init_tex_0[];
-extern const struct nvc0_graph_init nvc4_graph_init_sm_0[];
-
-extern const struct nvc0_graph_init nvc1_graph_init_gpc_unk_0[];
-extern const struct nvc0_graph_init nvc1_graph_init_setup_1[];
-
-extern const struct nvc0_graph_init nvd9_graph_init_pd_0[];
-extern const struct nvc0_graph_init nvd9_graph_init_ds_0[];
-extern const struct nvc0_graph_init nvd9_graph_init_prop_0[];
-extern const struct nvc0_graph_init nvd9_graph_init_gpm_0[];
-extern const struct nvc0_graph_init nvd9_graph_init_gpc_unk_1[];
-extern const struct nvc0_graph_init nvd9_graph_init_tex_0[];
-extern const struct nvc0_graph_init nvd9_graph_init_sm_0[];
-extern const struct nvc0_graph_init nvd9_graph_init_fe_1[];
-
-extern const struct nvc0_graph_init nvd7_graph_init_pes_0[];
-extern const struct nvc0_graph_init nvd7_graph_init_wwdx_0[];
-extern const struct nvc0_graph_init nvd7_graph_init_cbm_0[];
-
-extern const struct nvc0_graph_init nve4_graph_init_main_0[];
-extern const struct nvc0_graph_init nve4_graph_init_tpccs_0[];
-extern const struct nvc0_graph_init nve4_graph_init_pe_0[];
-extern const struct nvc0_graph_init nve4_graph_init_be_0[];
-extern const struct nvc0_graph_pack nve4_graph_pack_mmio[];
-
-extern const struct nvc0_graph_init nvf0_graph_init_fe_0[];
-extern const struct nvc0_graph_init nvf0_graph_init_ds_0[];
-extern const struct nvc0_graph_init nvf0_graph_init_sked_0[];
-extern const struct nvc0_graph_init nvf0_graph_init_cwd_0[];
-extern const struct nvc0_graph_init nvf0_graph_init_gpc_unk_1[];
-extern const struct nvc0_graph_init nvf0_graph_init_tex_0[];
-extern const struct nvc0_graph_init nvf0_graph_init_sm_0[];
-
-extern const struct nvc0_graph_init nv108_graph_init_gpc_unk_0[];
-
-
-#endif
diff --git a/drivers/gpu/drm/nouveau/core/engine/graph/nvc1.c b/drivers/gpu/drm/nouveau/core/engine/graph/nvc1.c
deleted file mode 100644 (file)
index 93d58e5..0000000
+++ /dev/null
@@ -1,133 +0,0 @@
-/*
- * Copyright 2013 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 <bskeggs@redhat.com>
- */
-
-#include "nvc0.h"
-#include "ctxnvc0.h"
-
-/*******************************************************************************
- * Graphics object classes
- ******************************************************************************/
-
-static struct nouveau_oclass
-nvc1_graph_sclass[] = {
-       { 0x902d, &nouveau_object_ofuncs },
-       { 0x9039, &nouveau_object_ofuncs },
-       { FERMI_A, &nvc0_fermi_ofuncs, nvc0_graph_9097_omthds },
-       { FERMI_B, &nvc0_fermi_ofuncs, nvc0_graph_9097_omthds },
-       { FERMI_COMPUTE_A, &nouveau_object_ofuncs, nvc0_graph_90c0_omthds },
-       {}
-};
-
-/*******************************************************************************
- * PGRAPH register lists
- ******************************************************************************/
-
-const struct nvc0_graph_init
-nvc1_graph_init_gpc_unk_0[] = {
-       { 0x418604,   1, 0x04, 0x00000000 },
-       { 0x418680,   1, 0x04, 0x00000000 },
-       { 0x418714,   1, 0x04, 0x00000000 },
-       { 0x418384,   1, 0x04, 0x00000000 },
-       {}
-};
-
-const struct nvc0_graph_init
-nvc1_graph_init_setup_1[] = {
-       { 0x4188c8,   2, 0x04, 0x00000000 },
-       { 0x4188d0,   1, 0x04, 0x00010000 },
-       { 0x4188d4,   1, 0x04, 0x00000001 },
-       {}
-};
-
-static const struct nvc0_graph_init
-nvc1_graph_init_gpc_unk_1[] = {
-       { 0x418d00,   1, 0x04, 0x00000000 },
-       { 0x418f08,   1, 0x04, 0x00000000 },
-       { 0x418e00,   1, 0x04, 0x00000003 },
-       { 0x418e08,   1, 0x04, 0x00000000 },
-       {}
-};
-
-static const struct nvc0_graph_init
-nvc1_graph_init_pe_0[] = {
-       { 0x41980c,   1, 0x04, 0x00000010 },
-       { 0x419810,   1, 0x04, 0x00000000 },
-       { 0x419814,   1, 0x04, 0x00000004 },
-       { 0x419844,   1, 0x04, 0x00000000 },
-       { 0x41984c,   1, 0x04, 0x00005bc5 },
-       { 0x419850,   4, 0x04, 0x00000000 },
-       { 0x419880,   1, 0x04, 0x00000002 },
-       {}
-};
-
-static const struct nvc0_graph_pack
-nvc1_graph_pack_mmio[] = {
-       { nvc0_graph_init_main_0 },
-       { nvc0_graph_init_fe_0 },
-       { nvc0_graph_init_pri_0 },
-       { nvc0_graph_init_rstr2d_0 },
-       { nvc0_graph_init_pd_0 },
-       { nvc4_graph_init_ds_0 },
-       { nvc0_graph_init_scc_0 },
-       { nvc0_graph_init_prop_0 },
-       { nvc1_graph_init_gpc_unk_0 },
-       { nvc0_graph_init_setup_0 },
-       { nvc0_graph_init_crstr_0 },
-       { nvc1_graph_init_setup_1 },
-       { nvc0_graph_init_zcull_0 },
-       { nvc0_graph_init_gpm_0 },
-       { nvc1_graph_init_gpc_unk_1 },
-       { nvc0_graph_init_gcc_0 },
-       { nvc0_graph_init_tpccs_0 },
-       { nvc4_graph_init_tex_0 },
-       { nvc1_graph_init_pe_0 },
-       { nvc0_graph_init_l1c_0 },
-       { nvc0_graph_init_wwdx_0 },
-       { nvc0_graph_init_tpccs_1 },
-       { nvc0_graph_init_mpc_0 },
-       { nvc4_graph_init_sm_0 },
-       { nvc0_graph_init_be_0 },
-       { nvc0_graph_init_fe_1 },
-       {}
-};
-
-/*******************************************************************************
- * PGRAPH engine/subdev functions
- ******************************************************************************/
-
-struct nouveau_oclass *
-nvc1_graph_oclass = &(struct nvc0_graph_oclass) {
-       .base.handle = NV_ENGINE(GR, 0xc1),
-       .base.ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nvc0_graph_ctor,
-               .dtor = nvc0_graph_dtor,
-               .init = nvc0_graph_init,
-               .fini = _nouveau_graph_fini,
-       },
-       .cclass = &nvc1_grctx_oclass,
-       .sclass = nvc1_graph_sclass,
-       .mmio = nvc1_graph_pack_mmio,
-       .fecs.ucode = &nvc0_graph_fecs_ucode,
-       .gpccs.ucode = &nvc0_graph_gpccs_ucode,
-}.base;
diff --git a/drivers/gpu/drm/nouveau/core/engine/graph/nvc4.c b/drivers/gpu/drm/nouveau/core/engine/graph/nvc4.c
deleted file mode 100644 (file)
index e82e70c..0000000
+++ /dev/null
@@ -1,128 +0,0 @@
-/*
- * Copyright 2013 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 <bskeggs@redhat.com>
- */
-
-#include "nvc0.h"
-#include "ctxnvc0.h"
-
-/*******************************************************************************
- * PGRAPH register lists
- ******************************************************************************/
-
-const struct nvc0_graph_init
-nvc4_graph_init_ds_0[] = {
-       { 0x405844,   1, 0x04, 0x00ffffff },
-       { 0x405850,   1, 0x04, 0x00000000 },
-       { 0x405900,   1, 0x04, 0x00002834 },
-       { 0x405908,   1, 0x04, 0x00000000 },
-       {}
-};
-
-const struct nvc0_graph_init
-nvc4_graph_init_tex_0[] = {
-       { 0x419ab0,   1, 0x04, 0x00000000 },
-       { 0x419ac8,   1, 0x04, 0x00000000 },
-       { 0x419ab8,   1, 0x04, 0x000000e7 },
-       { 0x419abc,   2, 0x04, 0x00000000 },
-       {}
-};
-
-static const struct nvc0_graph_init
-nvc4_graph_init_pe_0[] = {
-       { 0x41980c,   3, 0x04, 0x00000000 },
-       { 0x419844,   1, 0x04, 0x00000000 },
-       { 0x41984c,   1, 0x04, 0x00005bc5 },
-       { 0x419850,   4, 0x04, 0x00000000 },
-       { 0x419880,   1, 0x04, 0x00000002 },
-       {}
-};
-
-const struct nvc0_graph_init
-nvc4_graph_init_sm_0[] = {
-       { 0x419e00,   1, 0x04, 0x00000000 },
-       { 0x419ea0,   1, 0x04, 0x00000000 },
-       { 0x419ea4,   1, 0x04, 0x00000100 },
-       { 0x419ea8,   1, 0x04, 0x00001100 },
-       { 0x419eac,   1, 0x04, 0x11100702 },
-       { 0x419eb0,   1, 0x04, 0x00000003 },
-       { 0x419eb4,   4, 0x04, 0x00000000 },
-       { 0x419ec8,   1, 0x04, 0x0e063818 },
-       { 0x419ecc,   1, 0x04, 0x0e060e06 },
-       { 0x419ed0,   1, 0x04, 0x00003818 },
-       { 0x419ed4,   1, 0x04, 0x011104f1 },
-       { 0x419edc,   1, 0x04, 0x00000000 },
-       { 0x419f00,   1, 0x04, 0x00000000 },
-       { 0x419f2c,   1, 0x04, 0x00000000 },
-       {}
-};
-
-static const struct nvc0_graph_pack
-nvc4_graph_pack_mmio[] = {
-       { nvc0_graph_init_main_0 },
-       { nvc0_graph_init_fe_0 },
-       { nvc0_graph_init_pri_0 },
-       { nvc0_graph_init_rstr2d_0 },
-       { nvc0_graph_init_pd_0 },
-       { nvc4_graph_init_ds_0 },
-       { nvc0_graph_init_scc_0 },
-       { nvc0_graph_init_prop_0 },
-       { nvc0_graph_init_gpc_unk_0 },
-       { nvc0_graph_init_setup_0 },
-       { nvc0_graph_init_crstr_0 },
-       { nvc0_graph_init_setup_1 },
-       { nvc0_graph_init_zcull_0 },
-       { nvc0_graph_init_gpm_0 },
-       { nvc0_graph_init_gpc_unk_1 },
-       { nvc0_graph_init_gcc_0 },
-       { nvc0_graph_init_tpccs_0 },
-       { nvc4_graph_init_tex_0 },
-       { nvc4_graph_init_pe_0 },
-       { nvc0_graph_init_l1c_0 },
-       { nvc0_graph_init_wwdx_0 },
-       { nvc0_graph_init_tpccs_1 },
-       { nvc0_graph_init_mpc_0 },
-       { nvc4_graph_init_sm_0 },
-       { nvc0_graph_init_be_0 },
-       { nvc0_graph_init_fe_1 },
-       {}
-};
-
-/*******************************************************************************
- * PGRAPH engine/subdev functions
- ******************************************************************************/
-
-struct nouveau_oclass *
-nvc4_graph_oclass = &(struct nvc0_graph_oclass) {
-       .base.handle = NV_ENGINE(GR, 0xc3),
-       .base.ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nvc0_graph_ctor,
-               .dtor = nvc0_graph_dtor,
-               .init = nvc0_graph_init,
-               .fini = _nouveau_graph_fini,
-       },
-       .cclass = &nvc4_grctx_oclass,
-       .sclass = nvc0_graph_sclass,
-       .mmio = nvc4_graph_pack_mmio,
-       .fecs.ucode = &nvc0_graph_fecs_ucode,
-       .gpccs.ucode = &nvc0_graph_gpccs_ucode,
-}.base;
diff --git a/drivers/gpu/drm/nouveau/core/engine/graph/nvc8.c b/drivers/gpu/drm/nouveau/core/engine/graph/nvc8.c
deleted file mode 100644 (file)
index 692e1ed..0000000
+++ /dev/null
@@ -1,115 +0,0 @@
-/*
- * Copyright 2013 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 <bskeggs@redhat.com>
- */
-
-#include "nvc0.h"
-#include "ctxnvc0.h"
-
-/*******************************************************************************
- * Graphics object classes
- ******************************************************************************/
-
-struct nouveau_oclass
-nvc8_graph_sclass[] = {
-       { 0x902d, &nouveau_object_ofuncs },
-       { 0x9039, &nouveau_object_ofuncs },
-       { FERMI_A, &nvc0_fermi_ofuncs, nvc0_graph_9097_omthds },
-       { FERMI_B, &nvc0_fermi_ofuncs, nvc0_graph_9097_omthds },
-       { FERMI_C, &nvc0_fermi_ofuncs, nvc0_graph_9097_omthds },
-       { FERMI_COMPUTE_A, &nouveau_object_ofuncs, nvc0_graph_90c0_omthds },
-       {}
-};
-
-/*******************************************************************************
- * PGRAPH register lists
- ******************************************************************************/
-
-static const struct nvc0_graph_init
-nvc8_graph_init_sm_0[] = {
-       { 0x419e00,   1, 0x04, 0x00000000 },
-       { 0x419ea0,   1, 0x04, 0x00000000 },
-       { 0x419ea4,   1, 0x04, 0x00000100 },
-       { 0x419ea8,   1, 0x04, 0x00001100 },
-       { 0x419eac,   1, 0x04, 0x11100f02 },
-       { 0x419eb0,   1, 0x04, 0x00000003 },
-       { 0x419eb4,   4, 0x04, 0x00000000 },
-       { 0x419ec8,   1, 0x04, 0x06060618 },
-       { 0x419ed0,   1, 0x04, 0x0eff0e38 },
-       { 0x419ed4,   1, 0x04, 0x011104f1 },
-       { 0x419edc,   1, 0x04, 0x00000000 },
-       { 0x419f00,   1, 0x04, 0x00000000 },
-       { 0x419f2c,   1, 0x04, 0x00000000 },
-       {}
-};
-
-static const struct nvc0_graph_pack
-nvc8_graph_pack_mmio[] = {
-       { nvc0_graph_init_main_0 },
-       { nvc0_graph_init_fe_0 },
-       { nvc0_graph_init_pri_0 },
-       { nvc0_graph_init_rstr2d_0 },
-       { nvc0_graph_init_pd_0 },
-       { nvc0_graph_init_ds_0 },
-       { nvc0_graph_init_scc_0 },
-       { nvc0_graph_init_prop_0 },
-       { nvc0_graph_init_gpc_unk_0 },
-       { nvc0_graph_init_setup_0 },
-       { nvc0_graph_init_crstr_0 },
-       { nvc1_graph_init_setup_1 },
-       { nvc0_graph_init_zcull_0 },
-       { nvc0_graph_init_gpm_0 },
-       { nvc0_graph_init_gpc_unk_1 },
-       { nvc0_graph_init_gcc_0 },
-       { nvc0_graph_init_tpccs_0 },
-       { nvc0_graph_init_tex_0 },
-       { nvc0_graph_init_pe_0 },
-       { nvc0_graph_init_l1c_0 },
-       { nvc0_graph_init_wwdx_0 },
-       { nvc0_graph_init_tpccs_1 },
-       { nvc0_graph_init_mpc_0 },
-       { nvc8_graph_init_sm_0 },
-       { nvc0_graph_init_be_0 },
-       { nvc0_graph_init_fe_1 },
-       { nvc0_graph_init_pe_1 },
-       {}
-};
-
-/*******************************************************************************
- * PGRAPH engine/subdev functions
- ******************************************************************************/
-
-struct nouveau_oclass *
-nvc8_graph_oclass = &(struct nvc0_graph_oclass) {
-       .base.handle = NV_ENGINE(GR, 0xc8),
-       .base.ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nvc0_graph_ctor,
-               .dtor = nvc0_graph_dtor,
-               .init = nvc0_graph_init,
-               .fini = _nouveau_graph_fini,
-       },
-       .cclass = &nvc8_grctx_oclass,
-       .sclass = nvc8_graph_sclass,
-       .mmio = nvc8_graph_pack_mmio,
-       .fecs.ucode = &nvc0_graph_fecs_ucode,
-       .gpccs.ucode = &nvc0_graph_gpccs_ucode,
-}.base;
diff --git a/drivers/gpu/drm/nouveau/core/engine/graph/nvd7.c b/drivers/gpu/drm/nouveau/core/engine/graph/nvd7.c
deleted file mode 100644 (file)
index 41e8445..0000000
+++ /dev/null
@@ -1,137 +0,0 @@
-/*
- * Copyright 2013 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 <bskeggs@redhat.com>
- */
-
-#include "nvc0.h"
-#include "ctxnvc0.h"
-
-/*******************************************************************************
- * PGRAPH register lists
- ******************************************************************************/
-
-static const struct nvc0_graph_init
-nvd7_graph_init_pe_0[] = {
-       { 0x41980c,   1, 0x04, 0x00000010 },
-       { 0x419844,   1, 0x04, 0x00000000 },
-       { 0x41984c,   1, 0x04, 0x00005bc8 },
-       { 0x419850,   3, 0x04, 0x00000000 },
-       {}
-};
-
-const struct nvc0_graph_init
-nvd7_graph_init_pes_0[] = {
-       { 0x41be04,   1, 0x04, 0x00000000 },
-       { 0x41be08,   1, 0x04, 0x00000004 },
-       { 0x41be0c,   1, 0x04, 0x00000000 },
-       { 0x41be10,   1, 0x04, 0x003b8bc7 },
-       { 0x41be14,   2, 0x04, 0x00000000 },
-       {}
-};
-
-const struct nvc0_graph_init
-nvd7_graph_init_wwdx_0[] = {
-       { 0x41bfd4,   1, 0x04, 0x00800000 },
-       { 0x41bfdc,   1, 0x04, 0x00000000 },
-       { 0x41bff8,   2, 0x04, 0x00000000 },
-       {}
-};
-
-const struct nvc0_graph_init
-nvd7_graph_init_cbm_0[] = {
-       { 0x41becc,   1, 0x04, 0x00000000 },
-       { 0x41bee8,   2, 0x04, 0x00000000 },
-       {}
-};
-
-static const struct nvc0_graph_pack
-nvd7_graph_pack_mmio[] = {
-       { nvc0_graph_init_main_0 },
-       { nvc0_graph_init_fe_0 },
-       { nvc0_graph_init_pri_0 },
-       { nvc0_graph_init_rstr2d_0 },
-       { nvd9_graph_init_pd_0 },
-       { nvd9_graph_init_ds_0 },
-       { nvc0_graph_init_scc_0 },
-       { nvd9_graph_init_prop_0 },
-       { nvc1_graph_init_gpc_unk_0 },
-       { nvc0_graph_init_setup_0 },
-       { nvc0_graph_init_crstr_0 },
-       { nvc1_graph_init_setup_1 },
-       { nvc0_graph_init_zcull_0 },
-       { nvd9_graph_init_gpm_0 },
-       { nvd9_graph_init_gpc_unk_1 },
-       { nvc0_graph_init_gcc_0 },
-       { nvc0_graph_init_tpccs_0 },
-       { nvd9_graph_init_tex_0 },
-       { nvd7_graph_init_pe_0 },
-       { nvc0_graph_init_l1c_0 },
-       { nvc0_graph_init_mpc_0 },
-       { nvd9_graph_init_sm_0 },
-       { nvd7_graph_init_pes_0 },
-       { nvd7_graph_init_wwdx_0 },
-       { nvd7_graph_init_cbm_0 },
-       { nvc0_graph_init_be_0 },
-       { nvd9_graph_init_fe_1 },
-       {}
-};
-
-/*******************************************************************************
- * PGRAPH engine/subdev functions
- ******************************************************************************/
-
-#include "fuc/hubnvd7.fuc.h"
-
-struct nvc0_graph_ucode
-nvd7_graph_fecs_ucode = {
-       .code.data = nvd7_grhub_code,
-       .code.size = sizeof(nvd7_grhub_code),
-       .data.data = nvd7_grhub_data,
-       .data.size = sizeof(nvd7_grhub_data),
-};
-
-#include "fuc/gpcnvd7.fuc.h"
-
-struct nvc0_graph_ucode
-nvd7_graph_gpccs_ucode = {
-       .code.data = nvd7_grgpc_code,
-       .code.size = sizeof(nvd7_grgpc_code),
-       .data.data = nvd7_grgpc_data,
-       .data.size = sizeof(nvd7_grgpc_data),
-};
-
-struct nouveau_oclass *
-nvd7_graph_oclass = &(struct nvc0_graph_oclass) {
-       .base.handle = NV_ENGINE(GR, 0xd7),
-       .base.ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nvc0_graph_ctor,
-               .dtor = nvc0_graph_dtor,
-               .init = nvc0_graph_init,
-               .fini = _nouveau_graph_fini,
-       },
-       .cclass = &nvd7_grctx_oclass,
-       .sclass = nvc8_graph_sclass,
-       .mmio = nvd7_graph_pack_mmio,
-       .fecs.ucode = &nvd7_graph_fecs_ucode,
-       .gpccs.ucode = &nvd7_graph_gpccs_ucode,
-       .ppc_nr = 1,
-}.base;
diff --git a/drivers/gpu/drm/nouveau/core/engine/graph/nvd9.c b/drivers/gpu/drm/nouveau/core/engine/graph/nvd9.c
deleted file mode 100644 (file)
index 00fdf20..0000000
+++ /dev/null
@@ -1,191 +0,0 @@
-/*
- * Copyright 2013 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 <bskeggs@redhat.com>
- */
-
-#include "nvc0.h"
-#include "ctxnvc0.h"
-
-/*******************************************************************************
- * PGRAPH register lists
- ******************************************************************************/
-
-const struct nvc0_graph_init
-nvd9_graph_init_pd_0[] = {
-       { 0x406024,   1, 0x04, 0x00000000 },
-       { 0x4064f0,   3, 0x04, 0x00000000 },
-       {}
-};
-
-const struct nvc0_graph_init
-nvd9_graph_init_ds_0[] = {
-       { 0x405844,   1, 0x04, 0x00ffffff },
-       { 0x405850,   1, 0x04, 0x00000000 },
-       { 0x405900,   1, 0x04, 0x00002834 },
-       { 0x405908,   1, 0x04, 0x00000000 },
-       { 0x405928,   2, 0x04, 0x00000000 },
-       {}
-};
-
-const struct nvc0_graph_init
-nvd9_graph_init_prop_0[] = {
-       { 0x418408,   1, 0x04, 0x00000000 },
-       { 0x4184a0,   3, 0x04, 0x00000000 },
-       {}
-};
-
-const struct nvc0_graph_init
-nvd9_graph_init_gpm_0[] = {
-       { 0x418c04,   1, 0x04, 0x00000000 },
-       { 0x418c64,   2, 0x04, 0x00000000 },
-       { 0x418c88,   1, 0x04, 0x00000000 },
-       { 0x418cb4,   2, 0x04, 0x00000000 },
-       {}
-};
-
-const struct nvc0_graph_init
-nvd9_graph_init_gpc_unk_1[] = {
-       { 0x418d00,   1, 0x04, 0x00000000 },
-       { 0x418d28,   2, 0x04, 0x00000000 },
-       { 0x418f00,   1, 0x04, 0x00000000 },
-       { 0x418f08,   1, 0x04, 0x00000000 },
-       { 0x418f20,   2, 0x04, 0x00000000 },
-       { 0x418e00,   1, 0x04, 0x00000003 },
-       { 0x418e08,   1, 0x04, 0x00000000 },
-       { 0x418e1c,   2, 0x04, 0x00000000 },
-       {}
-};
-
-const struct nvc0_graph_init
-nvd9_graph_init_tex_0[] = {
-       { 0x419ab0,   1, 0x04, 0x00000000 },
-       { 0x419ac8,   1, 0x04, 0x00000000 },
-       { 0x419ab8,   1, 0x04, 0x000000e7 },
-       { 0x419abc,   2, 0x04, 0x00000000 },
-       { 0x419ab4,   1, 0x04, 0x00000000 },
-       {}
-};
-
-static const struct nvc0_graph_init
-nvd9_graph_init_pe_0[] = {
-       { 0x41980c,   1, 0x04, 0x00000010 },
-       { 0x419810,   1, 0x04, 0x00000000 },
-       { 0x419814,   1, 0x04, 0x00000004 },
-       { 0x419844,   1, 0x04, 0x00000000 },
-       { 0x41984c,   1, 0x04, 0x0000a918 },
-       { 0x419850,   4, 0x04, 0x00000000 },
-       { 0x419880,   1, 0x04, 0x00000002 },
-       {}
-};
-
-static const struct nvc0_graph_init
-nvd9_graph_init_wwdx_0[] = {
-       { 0x419bd4,   1, 0x04, 0x00800000 },
-       { 0x419bdc,   1, 0x04, 0x00000000 },
-       { 0x419bf8,   2, 0x04, 0x00000000 },
-       {}
-};
-
-static const struct nvc0_graph_init
-nvd9_graph_init_tpccs_1[] = {
-       { 0x419d2c,   1, 0x04, 0x00000000 },
-       { 0x419d48,   2, 0x04, 0x00000000 },
-       {}
-};
-
-const struct nvc0_graph_init
-nvd9_graph_init_sm_0[] = {
-       { 0x419e00,   1, 0x04, 0x00000000 },
-       { 0x419ea0,   1, 0x04, 0x00000000 },
-       { 0x419ea4,   1, 0x04, 0x00000100 },
-       { 0x419ea8,   1, 0x04, 0x02001100 },
-       { 0x419eac,   1, 0x04, 0x11100702 },
-       { 0x419eb0,   1, 0x04, 0x00000003 },
-       { 0x419eb4,   4, 0x04, 0x00000000 },
-       { 0x419ec8,   1, 0x04, 0x0e063818 },
-       { 0x419ecc,   1, 0x04, 0x0e060e06 },
-       { 0x419ed0,   1, 0x04, 0x00003818 },
-       { 0x419ed4,   1, 0x04, 0x011104f1 },
-       { 0x419edc,   1, 0x04, 0x00000000 },
-       { 0x419f00,   1, 0x04, 0x00000000 },
-       { 0x419f2c,   1, 0x04, 0x00000000 },
-       {}
-};
-
-const struct nvc0_graph_init
-nvd9_graph_init_fe_1[] = {
-       { 0x40402c,   1, 0x04, 0x00000000 },
-       { 0x4040f0,   1, 0x04, 0x00000000 },
-       { 0x404174,   1, 0x04, 0x00000000 },
-       {}
-};
-
-static const struct nvc0_graph_pack
-nvd9_graph_pack_mmio[] = {
-       { nvc0_graph_init_main_0 },
-       { nvc0_graph_init_fe_0 },
-       { nvc0_graph_init_pri_0 },
-       { nvc0_graph_init_rstr2d_0 },
-       { nvd9_graph_init_pd_0 },
-       { nvd9_graph_init_ds_0 },
-       { nvc0_graph_init_scc_0 },
-       { nvd9_graph_init_prop_0 },
-       { nvc1_graph_init_gpc_unk_0 },
-       { nvc0_graph_init_setup_0 },
-       { nvc0_graph_init_crstr_0 },
-       { nvc1_graph_init_setup_1 },
-       { nvc0_graph_init_zcull_0 },
-       { nvd9_graph_init_gpm_0 },
-       { nvd9_graph_init_gpc_unk_1 },
-       { nvc0_graph_init_gcc_0 },
-       { nvc0_graph_init_tpccs_0 },
-       { nvd9_graph_init_tex_0 },
-       { nvd9_graph_init_pe_0 },
-       { nvc0_graph_init_l1c_0 },
-       { nvd9_graph_init_wwdx_0 },
-       { nvd9_graph_init_tpccs_1 },
-       { nvc0_graph_init_mpc_0 },
-       { nvd9_graph_init_sm_0 },
-       { nvc0_graph_init_be_0 },
-       { nvd9_graph_init_fe_1 },
-       {}
-};
-
-/*******************************************************************************
- * PGRAPH engine/subdev functions
- ******************************************************************************/
-
-struct nouveau_oclass *
-nvd9_graph_oclass = &(struct nvc0_graph_oclass) {
-       .base.handle = NV_ENGINE(GR, 0xd9),
-       .base.ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nvc0_graph_ctor,
-               .dtor = nvc0_graph_dtor,
-               .init = nvc0_graph_init,
-               .fini = _nouveau_graph_fini,
-       },
-       .cclass = &nvd9_grctx_oclass,
-       .sclass = nvc8_graph_sclass,
-       .mmio = nvd9_graph_pack_mmio,
-       .fecs.ucode = &nvc0_graph_fecs_ucode,
-       .gpccs.ucode = &nvc0_graph_gpccs_ucode,
-}.base;
diff --git a/drivers/gpu/drm/nouveau/core/engine/graph/nve4.c b/drivers/gpu/drm/nouveau/core/engine/graph/nve4.c
deleted file mode 100644 (file)
index 0c71f5c..0000000
+++ /dev/null
@@ -1,347 +0,0 @@
-/*
- * Copyright 2013 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 <bskeggs@redhat.com>
- */
-
-#include <subdev/pwr.h>
-
-#include "nvc0.h"
-#include "ctxnvc0.h"
-
-/*******************************************************************************
- * Graphics object classes
- ******************************************************************************/
-
-static struct nouveau_oclass
-nve4_graph_sclass[] = {
-       { 0x902d, &nouveau_object_ofuncs },
-       { 0xa040, &nouveau_object_ofuncs },
-       { KEPLER_A, &nvc0_fermi_ofuncs, nvc0_graph_9097_omthds },
-       { KEPLER_COMPUTE_A, &nouveau_object_ofuncs, nvc0_graph_90c0_omthds },
-       {}
-};
-
-/*******************************************************************************
- * PGRAPH register lists
- ******************************************************************************/
-
-const struct nvc0_graph_init
-nve4_graph_init_main_0[] = {
-       { 0x400080,   1, 0x04, 0x003083c2 },
-       { 0x400088,   1, 0x04, 0x0001ffe7 },
-       { 0x40008c,   1, 0x04, 0x00000000 },
-       { 0x400090,   1, 0x04, 0x00000030 },
-       { 0x40013c,   1, 0x04, 0x003901f7 },
-       { 0x400140,   1, 0x04, 0x00000100 },
-       { 0x400144,   1, 0x04, 0x00000000 },
-       { 0x400148,   1, 0x04, 0x00000110 },
-       { 0x400138,   1, 0x04, 0x00000000 },
-       { 0x400130,   2, 0x04, 0x00000000 },
-       { 0x400124,   1, 0x04, 0x00000002 },
-       {}
-};
-
-static const struct nvc0_graph_init
-nve4_graph_init_ds_0[] = {
-       { 0x405844,   1, 0x04, 0x00ffffff },
-       { 0x405850,   1, 0x04, 0x00000000 },
-       { 0x405900,   1, 0x04, 0x0000ff34 },
-       { 0x405908,   1, 0x04, 0x00000000 },
-       { 0x405928,   2, 0x04, 0x00000000 },
-       {}
-};
-
-static const struct nvc0_graph_init
-nve4_graph_init_sked_0[] = {
-       { 0x407010,   1, 0x04, 0x00000000 },
-       {}
-};
-
-static const struct nvc0_graph_init
-nve4_graph_init_cwd_0[] = {
-       { 0x405b50,   1, 0x04, 0x00000000 },
-       {}
-};
-
-static const struct nvc0_graph_init
-nve4_graph_init_gpc_unk_1[] = {
-       { 0x418d00,   1, 0x04, 0x00000000 },
-       { 0x418d28,   2, 0x04, 0x00000000 },
-       { 0x418f00,   1, 0x04, 0x00000000 },
-       { 0x418f08,   1, 0x04, 0x00000000 },
-       { 0x418f20,   2, 0x04, 0x00000000 },
-       { 0x418e00,   1, 0x04, 0x00000060 },
-       { 0x418e08,   1, 0x04, 0x00000000 },
-       { 0x418e1c,   2, 0x04, 0x00000000 },
-       {}
-};
-
-const struct nvc0_graph_init
-nve4_graph_init_tpccs_0[] = {
-       { 0x419d0c,   1, 0x04, 0x00000000 },
-       { 0x419d10,   1, 0x04, 0x00000014 },
-       {}
-};
-
-const struct nvc0_graph_init
-nve4_graph_init_pe_0[] = {
-       { 0x41980c,   1, 0x04, 0x00000010 },
-       { 0x419844,   1, 0x04, 0x00000000 },
-       { 0x419850,   1, 0x04, 0x00000004 },
-       { 0x419854,   2, 0x04, 0x00000000 },
-       {}
-};
-
-static const struct nvc0_graph_init
-nve4_graph_init_l1c_0[] = {
-       { 0x419c98,   1, 0x04, 0x00000000 },
-       { 0x419ca8,   1, 0x04, 0x00000000 },
-       { 0x419cb0,   1, 0x04, 0x01000000 },
-       { 0x419cb4,   1, 0x04, 0x00000000 },
-       { 0x419cb8,   1, 0x04, 0x00b08bea },
-       { 0x419c84,   1, 0x04, 0x00010384 },
-       { 0x419cbc,   1, 0x04, 0x28137646 },
-       { 0x419cc0,   2, 0x04, 0x00000000 },
-       { 0x419c80,   1, 0x04, 0x00020232 },
-       {}
-};
-
-static const struct nvc0_graph_init
-nve4_graph_init_sm_0[] = {
-       { 0x419e00,   1, 0x04, 0x00000000 },
-       { 0x419ea0,   1, 0x04, 0x00000000 },
-       { 0x419ee4,   1, 0x04, 0x00000000 },
-       { 0x419ea4,   1, 0x04, 0x00000100 },
-       { 0x419ea8,   1, 0x04, 0x00000000 },
-       { 0x419eb4,   4, 0x04, 0x00000000 },
-       { 0x419edc,   1, 0x04, 0x00000000 },
-       { 0x419f00,   1, 0x04, 0x00000000 },
-       { 0x419f74,   1, 0x04, 0x00000555 },
-       {}
-};
-
-const struct nvc0_graph_init
-nve4_graph_init_be_0[] = {
-       { 0x40880c,   1, 0x04, 0x00000000 },
-       { 0x408850,   1, 0x04, 0x00000004 },
-       { 0x408910,   9, 0x04, 0x00000000 },
-       { 0x408950,   1, 0x04, 0x00000000 },
-       { 0x408954,   1, 0x04, 0x0000ffff },
-       { 0x408958,   1, 0x04, 0x00000034 },
-       { 0x408984,   1, 0x04, 0x00000000 },
-       { 0x408988,   1, 0x04, 0x08040201 },
-       { 0x40898c,   1, 0x04, 0x80402010 },
-       {}
-};
-
-const struct nvc0_graph_pack
-nve4_graph_pack_mmio[] = {
-       { nve4_graph_init_main_0 },
-       { nvc0_graph_init_fe_0 },
-       { nvc0_graph_init_pri_0 },
-       { nvc0_graph_init_rstr2d_0 },
-       { nvd9_graph_init_pd_0 },
-       { nve4_graph_init_ds_0 },
-       { nvc0_graph_init_scc_0 },
-       { nve4_graph_init_sked_0 },
-       { nve4_graph_init_cwd_0 },
-       { nvd9_graph_init_prop_0 },
-       { nvc1_graph_init_gpc_unk_0 },
-       { nvc0_graph_init_setup_0 },
-       { nvc0_graph_init_crstr_0 },
-       { nvc1_graph_init_setup_1 },
-       { nvc0_graph_init_zcull_0 },
-       { nvd9_graph_init_gpm_0 },
-       { nve4_graph_init_gpc_unk_1 },
-       { nvc0_graph_init_gcc_0 },
-       { nve4_graph_init_tpccs_0 },
-       { nvd9_graph_init_tex_0 },
-       { nve4_graph_init_pe_0 },
-       { nve4_graph_init_l1c_0 },
-       { nvc0_graph_init_mpc_0 },
-       { nve4_graph_init_sm_0 },
-       { nvd7_graph_init_pes_0 },
-       { nvd7_graph_init_wwdx_0 },
-       { nvd7_graph_init_cbm_0 },
-       { nve4_graph_init_be_0 },
-       { nvc0_graph_init_fe_1 },
-       {}
-};
-
-/*******************************************************************************
- * PGRAPH engine/subdev functions
- ******************************************************************************/
-
-int
-nve4_graph_init(struct nouveau_object *object)
-{
-       struct nvc0_graph_oclass *oclass = (void *)object->oclass;
-       struct nvc0_graph_priv *priv = (void *)object;
-       struct nouveau_pwr *ppwr = nouveau_pwr(priv);
-       const u32 magicgpc918 = DIV_ROUND_UP(0x00800000, priv->tpc_total);
-       u32 data[TPC_MAX / 8] = {};
-       u8  tpcnr[GPC_MAX];
-       int gpc, tpc, rop;
-       int ret, i;
-
-       if (ppwr)
-               ppwr->pgob(ppwr, false);
-
-       ret = nouveau_graph_init(&priv->base);
-       if (ret)
-               return ret;
-
-       nv_wr32(priv, GPC_BCAST(0x0880), 0x00000000);
-       nv_wr32(priv, GPC_BCAST(0x08a4), 0x00000000);
-       nv_wr32(priv, GPC_BCAST(0x0888), 0x00000000);
-       nv_wr32(priv, GPC_BCAST(0x088c), 0x00000000);
-       nv_wr32(priv, GPC_BCAST(0x0890), 0x00000000);
-       nv_wr32(priv, GPC_BCAST(0x0894), 0x00000000);
-       nv_wr32(priv, GPC_BCAST(0x08b4), priv->unk4188b4->addr >> 8);
-       nv_wr32(priv, GPC_BCAST(0x08b8), priv->unk4188b8->addr >> 8);
-
-       nvc0_graph_mmio(priv, oclass->mmio);
-
-       nv_wr32(priv, GPC_UNIT(0, 0x3018), 0x00000001);
-
-       memset(data, 0x00, sizeof(data));
-       memcpy(tpcnr, priv->tpc_nr, sizeof(priv->tpc_nr));
-       for (i = 0, gpc = -1; i < priv->tpc_total; i++) {
-               do {
-                       gpc = (gpc + 1) % priv->gpc_nr;
-               } while (!tpcnr[gpc]);
-               tpc = priv->tpc_nr[gpc] - tpcnr[gpc]--;
-
-               data[i / 8] |= tpc << ((i % 8) * 4);
-       }
-
-       nv_wr32(priv, GPC_BCAST(0x0980), data[0]);
-       nv_wr32(priv, GPC_BCAST(0x0984), data[1]);
-       nv_wr32(priv, GPC_BCAST(0x0988), data[2]);
-       nv_wr32(priv, GPC_BCAST(0x098c), data[3]);
-
-       for (gpc = 0; gpc < priv->gpc_nr; gpc++) {
-               nv_wr32(priv, GPC_UNIT(gpc, 0x0914),
-                       priv->magic_not_rop_nr << 8 | priv->tpc_nr[gpc]);
-               nv_wr32(priv, GPC_UNIT(gpc, 0x0910), 0x00040000 |
-                       priv->tpc_total);
-               nv_wr32(priv, GPC_UNIT(gpc, 0x0918), magicgpc918);
-       }
-
-       nv_wr32(priv, GPC_BCAST(0x3fd4), magicgpc918);
-       nv_wr32(priv, GPC_BCAST(0x08ac), nv_rd32(priv, 0x100800));
-
-       nv_wr32(priv, 0x400500, 0x00010001);
-
-       nv_wr32(priv, 0x400100, 0xffffffff);
-       nv_wr32(priv, 0x40013c, 0xffffffff);
-
-       nv_wr32(priv, 0x409ffc, 0x00000000);
-       nv_wr32(priv, 0x409c14, 0x00003e3e);
-       nv_wr32(priv, 0x409c24, 0x000f0001);
-       nv_wr32(priv, 0x404000, 0xc0000000);
-       nv_wr32(priv, 0x404600, 0xc0000000);
-       nv_wr32(priv, 0x408030, 0xc0000000);
-       nv_wr32(priv, 0x404490, 0xc0000000);
-       nv_wr32(priv, 0x406018, 0xc0000000);
-       nv_wr32(priv, 0x407020, 0x40000000);
-       nv_wr32(priv, 0x405840, 0xc0000000);
-       nv_wr32(priv, 0x405844, 0x00ffffff);
-       nv_mask(priv, 0x419cc0, 0x00000008, 0x00000008);
-       nv_mask(priv, 0x419eb4, 0x00001000, 0x00001000);
-
-       for (gpc = 0; gpc < priv->gpc_nr; gpc++) {
-               nv_wr32(priv, GPC_UNIT(gpc, 0x3038), 0xc0000000);
-               nv_wr32(priv, GPC_UNIT(gpc, 0x0420), 0xc0000000);
-               nv_wr32(priv, GPC_UNIT(gpc, 0x0900), 0xc0000000);
-               nv_wr32(priv, GPC_UNIT(gpc, 0x1028), 0xc0000000);
-               nv_wr32(priv, GPC_UNIT(gpc, 0x0824), 0xc0000000);
-               for (tpc = 0; tpc < priv->tpc_nr[gpc]; tpc++) {
-                       nv_wr32(priv, TPC_UNIT(gpc, tpc, 0x508), 0xffffffff);
-                       nv_wr32(priv, TPC_UNIT(gpc, tpc, 0x50c), 0xffffffff);
-                       nv_wr32(priv, TPC_UNIT(gpc, tpc, 0x224), 0xc0000000);
-                       nv_wr32(priv, TPC_UNIT(gpc, tpc, 0x48c), 0xc0000000);
-                       nv_wr32(priv, TPC_UNIT(gpc, tpc, 0x084), 0xc0000000);
-                       nv_wr32(priv, TPC_UNIT(gpc, tpc, 0x644), 0x001ffffe);
-                       nv_wr32(priv, TPC_UNIT(gpc, tpc, 0x64c), 0x0000000f);
-               }
-               nv_wr32(priv, GPC_UNIT(gpc, 0x2c90), 0xffffffff);
-               nv_wr32(priv, GPC_UNIT(gpc, 0x2c94), 0xffffffff);
-       }
-
-       for (rop = 0; rop < priv->rop_nr; rop++) {
-               nv_wr32(priv, ROP_UNIT(rop, 0x144), 0xc0000000);
-               nv_wr32(priv, ROP_UNIT(rop, 0x070), 0xc0000000);
-               nv_wr32(priv, ROP_UNIT(rop, 0x204), 0xffffffff);
-               nv_wr32(priv, ROP_UNIT(rop, 0x208), 0xffffffff);
-       }
-
-       nv_wr32(priv, 0x400108, 0xffffffff);
-       nv_wr32(priv, 0x400138, 0xffffffff);
-       nv_wr32(priv, 0x400118, 0xffffffff);
-       nv_wr32(priv, 0x400130, 0xffffffff);
-       nv_wr32(priv, 0x40011c, 0xffffffff);
-       nv_wr32(priv, 0x400134, 0xffffffff);
-
-       nv_wr32(priv, 0x400054, 0x34ce3464);
-
-       nvc0_graph_zbc_init(priv);
-
-       return nvc0_graph_init_ctxctl(priv);
-}
-
-#include "fuc/hubnve0.fuc.h"
-
-static struct nvc0_graph_ucode
-nve4_graph_fecs_ucode = {
-       .code.data = nve0_grhub_code,
-       .code.size = sizeof(nve0_grhub_code),
-       .data.data = nve0_grhub_data,
-       .data.size = sizeof(nve0_grhub_data),
-};
-
-#include "fuc/gpcnve0.fuc.h"
-
-static struct nvc0_graph_ucode
-nve4_graph_gpccs_ucode = {
-       .code.data = nve0_grgpc_code,
-       .code.size = sizeof(nve0_grgpc_code),
-       .data.data = nve0_grgpc_data,
-       .data.size = sizeof(nve0_grgpc_data),
-};
-
-struct nouveau_oclass *
-nve4_graph_oclass = &(struct nvc0_graph_oclass) {
-       .base.handle = NV_ENGINE(GR, 0xe4),
-       .base.ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nvc0_graph_ctor,
-               .dtor = nvc0_graph_dtor,
-               .init = nve4_graph_init,
-               .fini = _nouveau_graph_fini,
-       },
-       .cclass = &nve4_grctx_oclass,
-       .sclass = nve4_graph_sclass,
-       .mmio = nve4_graph_pack_mmio,
-       .fecs.ucode = &nve4_graph_fecs_ucode,
-       .gpccs.ucode = &nve4_graph_gpccs_ucode,
-       .ppc_nr = 1,
-}.base;
diff --git a/drivers/gpu/drm/nouveau/core/engine/graph/nvf0.c b/drivers/gpu/drm/nouveau/core/engine/graph/nvf0.c
deleted file mode 100644 (file)
index c306c0f..0000000
+++ /dev/null
@@ -1,245 +0,0 @@
-/*
- * Copyright 2013 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 <bskeggs@redhat.com>
- */
-
-#include "nvc0.h"
-#include "ctxnvc0.h"
-
-/*******************************************************************************
- * Graphics object classes
- ******************************************************************************/
-
-struct nouveau_oclass
-nvf0_graph_sclass[] = {
-       { 0x902d, &nouveau_object_ofuncs },
-       { 0xa140, &nouveau_object_ofuncs },
-       { KEPLER_B, &nvc0_fermi_ofuncs, nvc0_graph_9097_omthds },
-       { KEPLER_COMPUTE_B, &nouveau_object_ofuncs, nvc0_graph_90c0_omthds },
-       {}
-};
-
-/*******************************************************************************
- * PGRAPH register lists
- ******************************************************************************/
-
-const struct nvc0_graph_init
-nvf0_graph_init_fe_0[] = {
-       { 0x40415c,   1, 0x04, 0x00000000 },
-       { 0x404170,   1, 0x04, 0x00000000 },
-       { 0x4041b4,   1, 0x04, 0x00000000 },
-       {}
-};
-
-const struct nvc0_graph_init
-nvf0_graph_init_ds_0[] = {
-       { 0x405844,   1, 0x04, 0x00ffffff },
-       { 0x405850,   1, 0x04, 0x00000000 },
-       { 0x405900,   1, 0x04, 0x0000ff00 },
-       { 0x405908,   1, 0x04, 0x00000000 },
-       { 0x405928,   2, 0x04, 0x00000000 },
-       {}
-};
-
-const struct nvc0_graph_init
-nvf0_graph_init_sked_0[] = {
-       { 0x407010,   1, 0x04, 0x00000000 },
-       { 0x407040,   1, 0x04, 0x80440424 },
-       { 0x407048,   1, 0x04, 0x0000000a },
-       {}
-};
-
-const struct nvc0_graph_init
-nvf0_graph_init_cwd_0[] = {
-       { 0x405b44,   1, 0x04, 0x00000000 },
-       { 0x405b50,   1, 0x04, 0x00000000 },
-       {}
-};
-
-const struct nvc0_graph_init
-nvf0_graph_init_gpc_unk_1[] = {
-       { 0x418d00,   1, 0x04, 0x00000000 },
-       { 0x418d28,   2, 0x04, 0x00000000 },
-       { 0x418f00,   1, 0x04, 0x00000400 },
-       { 0x418f08,   1, 0x04, 0x00000000 },
-       { 0x418f20,   2, 0x04, 0x00000000 },
-       { 0x418e00,   1, 0x04, 0x00000000 },
-       { 0x418e08,   1, 0x04, 0x00000000 },
-       { 0x418e1c,   2, 0x04, 0x00000000 },
-       {}
-};
-
-const struct nvc0_graph_init
-nvf0_graph_init_tex_0[] = {
-       { 0x419ab0,   1, 0x04, 0x00000000 },
-       { 0x419ac8,   1, 0x04, 0x00000000 },
-       { 0x419ab8,   1, 0x04, 0x000000e7 },
-       { 0x419aec,   1, 0x04, 0x00000000 },
-       { 0x419abc,   2, 0x04, 0x00000000 },
-       { 0x419ab4,   1, 0x04, 0x00000000 },
-       { 0x419aa8,   2, 0x04, 0x00000000 },
-       {}
-};
-
-static const struct nvc0_graph_init
-nvf0_graph_init_l1c_0[] = {
-       { 0x419c98,   1, 0x04, 0x00000000 },
-       { 0x419ca8,   1, 0x04, 0x00000000 },
-       { 0x419cb0,   1, 0x04, 0x01000000 },
-       { 0x419cb4,   1, 0x04, 0x00000000 },
-       { 0x419cb8,   1, 0x04, 0x00b08bea },
-       { 0x419c84,   1, 0x04, 0x00010384 },
-       { 0x419cbc,   1, 0x04, 0x281b3646 },
-       { 0x419cc0,   2, 0x04, 0x00000000 },
-       { 0x419c80,   1, 0x04, 0x00020230 },
-       { 0x419ccc,   2, 0x04, 0x00000000 },
-       {}
-};
-
-const struct nvc0_graph_init
-nvf0_graph_init_sm_0[] = {
-       { 0x419e00,   1, 0x04, 0x00000080 },
-       { 0x419ea0,   1, 0x04, 0x00000000 },
-       { 0x419ee4,   1, 0x04, 0x00000000 },
-       { 0x419ea4,   1, 0x04, 0x00000100 },
-       { 0x419ea8,   1, 0x04, 0x00000000 },
-       { 0x419eb4,   1, 0x04, 0x00000000 },
-       { 0x419ebc,   2, 0x04, 0x00000000 },
-       { 0x419edc,   1, 0x04, 0x00000000 },
-       { 0x419f00,   1, 0x04, 0x00000000 },
-       { 0x419ed0,   1, 0x04, 0x00003234 },
-       { 0x419f74,   1, 0x04, 0x00015555 },
-       { 0x419f80,   4, 0x04, 0x00000000 },
-       {}
-};
-
-static const struct nvc0_graph_pack
-nvf0_graph_pack_mmio[] = {
-       { nve4_graph_init_main_0 },
-       { nvf0_graph_init_fe_0 },
-       { nvc0_graph_init_pri_0 },
-       { nvc0_graph_init_rstr2d_0 },
-       { nvd9_graph_init_pd_0 },
-       { nvf0_graph_init_ds_0 },
-       { nvc0_graph_init_scc_0 },
-       { nvf0_graph_init_sked_0 },
-       { nvf0_graph_init_cwd_0 },
-       { nvd9_graph_init_prop_0 },
-       { nvc1_graph_init_gpc_unk_0 },
-       { nvc0_graph_init_setup_0 },
-       { nvc0_graph_init_crstr_0 },
-       { nvc1_graph_init_setup_1 },
-       { nvc0_graph_init_zcull_0 },
-       { nvd9_graph_init_gpm_0 },
-       { nvf0_graph_init_gpc_unk_1 },
-       { nvc0_graph_init_gcc_0 },
-       { nve4_graph_init_tpccs_0 },
-       { nvf0_graph_init_tex_0 },
-       { nve4_graph_init_pe_0 },
-       { nvf0_graph_init_l1c_0 },
-       { nvc0_graph_init_mpc_0 },
-       { nvf0_graph_init_sm_0 },
-       { nvd7_graph_init_pes_0 },
-       { nvd7_graph_init_wwdx_0 },
-       { nvd7_graph_init_cbm_0 },
-       { nve4_graph_init_be_0 },
-       { nvc0_graph_init_fe_1 },
-       {}
-};
-
-/*******************************************************************************
- * PGRAPH engine/subdev functions
- ******************************************************************************/
-
-int
-nvf0_graph_fini(struct nouveau_object *object, bool suspend)
-{
-       struct nvc0_graph_priv *priv = (void *)object;
-       static const struct {
-               u32 addr;
-               u32 data;
-       } magic[] = {
-               { 0x020520, 0xfffffffc },
-               { 0x020524, 0xfffffffe },
-               { 0x020524, 0xfffffffc },
-               { 0x020524, 0xfffffff8 },
-               { 0x020524, 0xffffffe0 },
-               { 0x020530, 0xfffffffe },
-               { 0x02052c, 0xfffffffa },
-               { 0x02052c, 0xfffffff0 },
-               { 0x02052c, 0xffffffc0 },
-               { 0x02052c, 0xffffff00 },
-               { 0x02052c, 0xfffffc00 },
-               { 0x02052c, 0xfffcfc00 },
-               { 0x02052c, 0xfff0fc00 },
-               { 0x02052c, 0xff80fc00 },
-               { 0x020528, 0xfffffffe },
-               { 0x020528, 0xfffffffc },
-       };
-       int i;
-
-       nv_mask(priv, 0x000200, 0x08001000, 0x00000000);
-       nv_mask(priv, 0x0206b4, 0x00000000, 0x00000000);
-       for (i = 0; i < ARRAY_SIZE(magic); i++) {
-               nv_wr32(priv, magic[i].addr, magic[i].data);
-               nv_wait(priv, magic[i].addr, 0x80000000, 0x00000000);
-       }
-
-       return nouveau_graph_fini(&priv->base, suspend);
-}
-
-#include "fuc/hubnvf0.fuc.h"
-
-struct nvc0_graph_ucode
-nvf0_graph_fecs_ucode = {
-       .code.data = nvf0_grhub_code,
-       .code.size = sizeof(nvf0_grhub_code),
-       .data.data = nvf0_grhub_data,
-       .data.size = sizeof(nvf0_grhub_data),
-};
-
-#include "fuc/gpcnvf0.fuc.h"
-
-struct nvc0_graph_ucode
-nvf0_graph_gpccs_ucode = {
-       .code.data = nvf0_grgpc_code,
-       .code.size = sizeof(nvf0_grgpc_code),
-       .data.data = nvf0_grgpc_data,
-       .data.size = sizeof(nvf0_grgpc_data),
-};
-
-struct nouveau_oclass *
-nvf0_graph_oclass = &(struct nvc0_graph_oclass) {
-       .base.handle = NV_ENGINE(GR, 0xf0),
-       .base.ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nvc0_graph_ctor,
-               .dtor = nvc0_graph_dtor,
-               .init = nve4_graph_init,
-               .fini = nvf0_graph_fini,
-       },
-       .cclass = &nvf0_grctx_oclass,
-       .sclass =  nvf0_graph_sclass,
-       .mmio = nvf0_graph_pack_mmio,
-       .fecs.ucode = &nvf0_graph_fecs_ucode,
-       .gpccs.ucode = &nvf0_graph_gpccs_ucode,
-       .ppc_nr = 2,
-}.base;
diff --git a/drivers/gpu/drm/nouveau/core/engine/graph/regs.h b/drivers/gpu/drm/nouveau/core/engine/graph/regs.h
deleted file mode 100644 (file)
index fde8e24..0000000
+++ /dev/null
@@ -1,274 +0,0 @@
-#ifndef __NOUVEAU_GRAPH_REGS_H__
-#define __NOUVEAU_GRAPH_REGS_H__
-
-#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 NV40_PGRAPH_STATUS_SYNC_STALL                  0x00004000
-#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 NV20_PGRAPH_ZCOMP(i)                               (0x00400980 + 4*(i))
-#define NV41_PGRAPH_ZCOMP0(i)                              (0x004009c0 + 4*(i))
-#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 NV47_PGRAPH_ZCOMP0(i)                              (0x00400e00 + 4*(i))
-#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 NV47_PGRAPH_ZCOMP1(i)                              (0x004068c0 + 4*(i))
-#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))
-#define NV40_PGRAPH_ZCOMP1(i)                              (0x00406980 + 4*(i))
-#define NV41_PGRAPH_ZCOMP1(i)                              (0x004069c0 + 4*(i))
-
-#endif
diff --git a/drivers/gpu/drm/nouveau/core/engine/mpeg/nv31.c b/drivers/gpu/drm/nouveau/core/engine/mpeg/nv31.c
deleted file mode 100644 (file)
index d88c700..0000000
+++ /dev/null
@@ -1,309 +0,0 @@
-/*
- * Copyright 2012 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 <core/client.h>
-#include <core/os.h>
-#include <core/engctx.h>
-#include <core/handle.h>
-
-#include <subdev/fb.h>
-#include <subdev/timer.h>
-#include <subdev/instmem.h>
-
-#include <engine/fifo.h>
-#include <engine/mpeg.h>
-#include <engine/mpeg/nv31.h>
-
-/*******************************************************************************
- * MPEG object classes
- ******************************************************************************/
-
-static int
-nv31_mpeg_object_ctor(struct nouveau_object *parent,
-                     struct nouveau_object *engine,
-                     struct nouveau_oclass *oclass, void *data, u32 size,
-                     struct nouveau_object **pobject)
-{
-       struct nouveau_gpuobj *obj;
-       int ret;
-
-       ret = nouveau_gpuobj_create(parent, engine, oclass, 0, parent,
-                                   20, 16, 0, &obj);
-       *pobject = nv_object(obj);
-       if (ret)
-               return ret;
-
-       nv_wo32(obj, 0x00, nv_mclass(obj));
-       nv_wo32(obj, 0x04, 0x00000000);
-       nv_wo32(obj, 0x08, 0x00000000);
-       nv_wo32(obj, 0x0c, 0x00000000);
-       return 0;
-}
-
-static int
-nv31_mpeg_mthd_dma(struct nouveau_object *object, u32 mthd, void *arg, u32 len)
-{
-       struct nouveau_instmem *imem = nouveau_instmem(object);
-       struct nv31_mpeg_priv *priv = (void *)object->engine;
-       u32 inst = *(u32 *)arg << 4;
-       u32 dma0 = nv_ro32(imem, inst + 0);
-       u32 dma1 = nv_ro32(imem, inst + 4);
-       u32 dma2 = nv_ro32(imem, inst + 8);
-       u32 base = (dma2 & 0xfffff000) | (dma0 >> 20);
-       u32 size = dma1 + 1;
-
-       /* only allow linear DMA objects */
-       if (!(dma0 & 0x00002000))
-               return -EINVAL;
-
-       if (mthd == 0x0190) {
-               /* DMA_CMD */
-               nv_mask(priv, 0x00b300, 0x00010000, (dma0 & 0x00030000) ? 0x00010000 : 0);
-               nv_wr32(priv, 0x00b334, base);
-               nv_wr32(priv, 0x00b324, size);
-       } else
-       if (mthd == 0x01a0) {
-               /* DMA_DATA */
-               nv_mask(priv, 0x00b300, 0x00020000, (dma0 & 0x00030000) ? 0x00020000 : 0);
-               nv_wr32(priv, 0x00b360, base);
-               nv_wr32(priv, 0x00b364, size);
-       } else {
-               /* DMA_IMAGE, VRAM only */
-               if (dma0 & 0x00030000)
-                       return -EINVAL;
-
-               nv_wr32(priv, 0x00b370, base);
-               nv_wr32(priv, 0x00b374, size);
-       }
-
-       return 0;
-}
-
-struct nouveau_ofuncs
-nv31_mpeg_ofuncs = {
-       .ctor = nv31_mpeg_object_ctor,
-       .dtor = _nouveau_gpuobj_dtor,
-       .init = _nouveau_gpuobj_init,
-       .fini = _nouveau_gpuobj_fini,
-       .rd32 = _nouveau_gpuobj_rd32,
-       .wr32 = _nouveau_gpuobj_wr32,
-};
-
-static struct nouveau_omthds
-nv31_mpeg_omthds[] = {
-       { 0x0190, 0x0190, nv31_mpeg_mthd_dma },
-       { 0x01a0, 0x01a0, nv31_mpeg_mthd_dma },
-       { 0x01b0, 0x01b0, nv31_mpeg_mthd_dma },
-       {}
-};
-
-struct nouveau_oclass
-nv31_mpeg_sclass[] = {
-       { 0x3174, &nv31_mpeg_ofuncs, nv31_mpeg_omthds },
-       {}
-};
-
-/*******************************************************************************
- * PMPEG context
- ******************************************************************************/
-
-static int
-nv31_mpeg_context_ctor(struct nouveau_object *parent,
-                      struct nouveau_object *engine,
-                      struct nouveau_oclass *oclass, void *data, u32 size,
-                      struct nouveau_object **pobject)
-{
-       struct nv31_mpeg_priv *priv = (void *)engine;
-       struct nv31_mpeg_chan *chan;
-       unsigned long flags;
-       int ret;
-
-       ret = nouveau_object_create(parent, engine, oclass, 0, &chan);
-       *pobject = nv_object(chan);
-       if (ret)
-               return ret;
-
-       spin_lock_irqsave(&nv_engine(priv)->lock, flags);
-       if (priv->chan) {
-               spin_unlock_irqrestore(&nv_engine(priv)->lock, flags);
-               nouveau_object_destroy(&chan->base);
-               *pobject = NULL;
-               return -EBUSY;
-       }
-       priv->chan = chan;
-       spin_unlock_irqrestore(&nv_engine(priv)->lock, flags);
-       return 0;
-}
-
-static void
-nv31_mpeg_context_dtor(struct nouveau_object *object)
-{
-       struct nv31_mpeg_priv *priv = (void *)object->engine;
-       struct nv31_mpeg_chan *chan = (void *)object;
-       unsigned long flags;
-
-       spin_lock_irqsave(&nv_engine(priv)->lock, flags);
-       priv->chan = NULL;
-       spin_unlock_irqrestore(&nv_engine(priv)->lock, flags);
-       nouveau_object_destroy(&chan->base);
-}
-
-struct nouveau_oclass
-nv31_mpeg_cclass = {
-       .handle = NV_ENGCTX(MPEG, 0x31),
-       .ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nv31_mpeg_context_ctor,
-               .dtor = nv31_mpeg_context_dtor,
-               .init = nouveau_object_init,
-               .fini = nouveau_object_fini,
-       },
-};
-
-/*******************************************************************************
- * PMPEG engine/subdev functions
- ******************************************************************************/
-
-void
-nv31_mpeg_tile_prog(struct nouveau_engine *engine, int i)
-{
-       struct nouveau_fb_tile *tile = &nouveau_fb(engine)->tile.region[i];
-       struct nv31_mpeg_priv *priv = (void *)engine;
-
-       nv_wr32(priv, 0x00b008 + (i * 0x10), tile->pitch);
-       nv_wr32(priv, 0x00b004 + (i * 0x10), tile->limit);
-       nv_wr32(priv, 0x00b000 + (i * 0x10), tile->addr);
-}
-
-void
-nv31_mpeg_intr(struct nouveau_subdev *subdev)
-{
-       struct nv31_mpeg_priv *priv = (void *)subdev;
-       struct nouveau_fifo *pfifo = nouveau_fifo(subdev);
-       struct nouveau_handle *handle;
-       struct nouveau_object *engctx;
-       u32 stat = nv_rd32(priv, 0x00b100);
-       u32 type = nv_rd32(priv, 0x00b230);
-       u32 mthd = nv_rd32(priv, 0x00b234);
-       u32 data = nv_rd32(priv, 0x00b238);
-       u32 show = stat;
-       unsigned long flags;
-
-       spin_lock_irqsave(&nv_engine(priv)->lock, flags);
-       engctx = nv_object(priv->chan);
-
-       if (stat & 0x01000000) {
-               /* happens on initial binding of the object */
-               if (type == 0x00000020 && mthd == 0x0000) {
-                       nv_mask(priv, 0x00b308, 0x00000000, 0x00000000);
-                       show &= ~0x01000000;
-               }
-
-               if (type == 0x00000010 && engctx) {
-                       handle = nouveau_handle_get_class(engctx, 0x3174);
-                       if (handle && !nv_call(handle->object, mthd, data))
-                               show &= ~0x01000000;
-                       nouveau_handle_put(handle);
-               }
-       }
-
-       nv_wr32(priv, 0x00b100, stat);
-       nv_wr32(priv, 0x00b230, 0x00000001);
-
-       if (show) {
-               nv_error(priv, "ch %d [%s] 0x%08x 0x%08x 0x%08x 0x%08x\n",
-                        pfifo->chid(pfifo, engctx),
-                        nouveau_client_name(engctx), stat, type, mthd, data);
-       }
-
-       spin_unlock_irqrestore(&nv_engine(priv)->lock, flags);
-}
-
-static int
-nv31_mpeg_ctor(struct nouveau_object *parent, struct nouveau_object *engine,
-              struct nouveau_oclass *oclass, void *data, u32 size,
-              struct nouveau_object **pobject)
-{
-       struct nv31_mpeg_priv *priv;
-       int ret;
-
-       ret = nouveau_mpeg_create(parent, engine, oclass, &priv);
-       *pobject = nv_object(priv);
-       if (ret)
-               return ret;
-
-       nv_subdev(priv)->unit = 0x00000002;
-       nv_subdev(priv)->intr = nv31_mpeg_intr;
-       nv_engine(priv)->cclass = &nv31_mpeg_cclass;
-       nv_engine(priv)->sclass = nv31_mpeg_sclass;
-       nv_engine(priv)->tile_prog = nv31_mpeg_tile_prog;
-       return 0;
-}
-
-int
-nv31_mpeg_init(struct nouveau_object *object)
-{
-       struct nouveau_engine *engine = nv_engine(object);
-       struct nv31_mpeg_priv *priv = (void *)object;
-       struct nouveau_fb *pfb = nouveau_fb(object);
-       int ret, i;
-
-       ret = nouveau_mpeg_init(&priv->base);
-       if (ret)
-               return ret;
-
-       /* VPE init */
-       nv_wr32(priv, 0x00b0e0, 0x00000020); /* nvidia: rd 0x01, wr 0x20 */
-       nv_wr32(priv, 0x00b0e8, 0x00000020); /* nvidia: rd 0x01, wr 0x20 */
-
-       for (i = 0; i < pfb->tile.regions; i++)
-               engine->tile_prog(engine, i);
-
-       /* PMPEG init */
-       nv_wr32(priv, 0x00b32c, 0x00000000);
-       nv_wr32(priv, 0x00b314, 0x00000100);
-       nv_wr32(priv, 0x00b220, 0x00000031);
-       nv_wr32(priv, 0x00b300, 0x02001ec1);
-       nv_mask(priv, 0x00b32c, 0x00000001, 0x00000001);
-
-       nv_wr32(priv, 0x00b100, 0xffffffff);
-       nv_wr32(priv, 0x00b140, 0xffffffff);
-
-       if (!nv_wait(priv, 0x00b200, 0x00000001, 0x00000000)) {
-               nv_error(priv, "timeout 0x%08x\n", nv_rd32(priv, 0x00b200));
-               return -EBUSY;
-       }
-
-       return 0;
-}
-
-struct nouveau_oclass
-nv31_mpeg_oclass = {
-       .handle = NV_ENGINE(MPEG, 0x31),
-       .ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nv31_mpeg_ctor,
-               .dtor = _nouveau_mpeg_dtor,
-               .init = nv31_mpeg_init,
-               .fini = _nouveau_mpeg_fini,
-       },
-};
diff --git a/drivers/gpu/drm/nouveau/core/engine/mpeg/nv31.h b/drivers/gpu/drm/nouveau/core/engine/mpeg/nv31.h
deleted file mode 100644 (file)
index d08629d..0000000
+++ /dev/null
@@ -1,15 +0,0 @@
-#ifndef __NV31_MPEG_H__
-#define __NV31_MPEG_H__
-
-#include <engine/mpeg.h>
-
-struct nv31_mpeg_chan {
-       struct nouveau_object base;
-};
-
-struct nv31_mpeg_priv {
-       struct nouveau_mpeg base;
-       struct nv31_mpeg_chan *chan;
-};
-
-#endif
diff --git a/drivers/gpu/drm/nouveau/core/engine/mpeg/nv40.c b/drivers/gpu/drm/nouveau/core/engine/mpeg/nv40.c
deleted file mode 100644 (file)
index bdb2f20..0000000
+++ /dev/null
@@ -1,141 +0,0 @@
-/*
- * Copyright 2012 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 <core/os.h>
-#include <core/engctx.h>
-
-#include <subdev/fb.h>
-#include <subdev/timer.h>
-#include <subdev/instmem.h>
-
-#include <engine/mpeg.h>
-#include <engine/mpeg/nv31.h>
-
-/*******************************************************************************
- * MPEG object classes
- ******************************************************************************/
-
-static int
-nv40_mpeg_mthd_dma(struct nouveau_object *object, u32 mthd, void *arg, u32 len)
-{
-       struct nouveau_instmem *imem = nouveau_instmem(object);
-       struct nv31_mpeg_priv *priv = (void *)object->engine;
-       u32 inst = *(u32 *)arg << 4;
-       u32 dma0 = nv_ro32(imem, inst + 0);
-       u32 dma1 = nv_ro32(imem, inst + 4);
-       u32 dma2 = nv_ro32(imem, inst + 8);
-       u32 base = (dma2 & 0xfffff000) | (dma0 >> 20);
-       u32 size = dma1 + 1;
-
-       /* only allow linear DMA objects */
-       if (!(dma0 & 0x00002000))
-               return -EINVAL;
-
-       if (mthd == 0x0190) {
-               /* DMA_CMD */
-               nv_mask(priv, 0x00b300, 0x00030000, (dma0 & 0x00030000));
-               nv_wr32(priv, 0x00b334, base);
-               nv_wr32(priv, 0x00b324, size);
-       } else
-       if (mthd == 0x01a0) {
-               /* DMA_DATA */
-               nv_mask(priv, 0x00b300, 0x000c0000, (dma0 & 0x00030000) << 2);
-               nv_wr32(priv, 0x00b360, base);
-               nv_wr32(priv, 0x00b364, size);
-       } else {
-               /* DMA_IMAGE, VRAM only */
-               if (dma0 & 0x00030000)
-                       return -EINVAL;
-
-               nv_wr32(priv, 0x00b370, base);
-               nv_wr32(priv, 0x00b374, size);
-       }
-
-       return 0;
-}
-
-static struct nouveau_omthds
-nv40_mpeg_omthds[] = {
-       { 0x0190, 0x0190, nv40_mpeg_mthd_dma },
-       { 0x01a0, 0x01a0, nv40_mpeg_mthd_dma },
-       { 0x01b0, 0x01b0, nv40_mpeg_mthd_dma },
-       {}
-};
-
-struct nouveau_oclass
-nv40_mpeg_sclass[] = {
-       { 0x3174, &nv31_mpeg_ofuncs, nv40_mpeg_omthds },
-       {}
-};
-
-/*******************************************************************************
- * PMPEG engine/subdev functions
- ******************************************************************************/
-
-static void
-nv40_mpeg_intr(struct nouveau_subdev *subdev)
-{
-       struct nv31_mpeg_priv *priv = (void *)subdev;
-       u32 stat;
-
-       if ((stat = nv_rd32(priv, 0x00b100)))
-               nv31_mpeg_intr(subdev);
-
-       if ((stat = nv_rd32(priv, 0x00b800))) {
-               nv_error(priv, "PMSRCH 0x%08x\n", stat);
-               nv_wr32(priv, 0x00b800, stat);
-       }
-}
-
-static int
-nv40_mpeg_ctor(struct nouveau_object *parent, struct nouveau_object *engine,
-              struct nouveau_oclass *oclass, void *data, u32 size,
-              struct nouveau_object **pobject)
-{
-       struct nv31_mpeg_priv *priv;
-       int ret;
-
-       ret = nouveau_mpeg_create(parent, engine, oclass, &priv);
-       *pobject = nv_object(priv);
-       if (ret)
-               return ret;
-
-       nv_subdev(priv)->unit = 0x00000002;
-       nv_subdev(priv)->intr = nv40_mpeg_intr;
-       nv_engine(priv)->cclass = &nv31_mpeg_cclass;
-       nv_engine(priv)->sclass = nv40_mpeg_sclass;
-       nv_engine(priv)->tile_prog = nv31_mpeg_tile_prog;
-       return 0;
-}
-
-struct nouveau_oclass
-nv40_mpeg_oclass = {
-       .handle = NV_ENGINE(MPEG, 0x40),
-       .ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nv40_mpeg_ctor,
-               .dtor = _nouveau_mpeg_dtor,
-               .init = nv31_mpeg_init,
-               .fini = _nouveau_mpeg_fini,
-       },
-};
diff --git a/drivers/gpu/drm/nouveau/core/engine/mpeg/nv44.c b/drivers/gpu/drm/nouveau/core/engine/mpeg/nv44.c
deleted file mode 100644 (file)
index 72c7f33..0000000
+++ /dev/null
@@ -1,193 +0,0 @@
-/*
- * Copyright 2012 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 <core/os.h>
-#include <core/client.h>
-#include <core/engctx.h>
-#include <core/handle.h>
-
-#include <subdev/fb.h>
-#include <subdev/timer.h>
-#include <subdev/instmem.h>
-
-#include <engine/fifo.h>
-#include <engine/mpeg.h>
-
-struct nv44_mpeg_priv {
-       struct nouveau_mpeg base;
-};
-
-struct nv44_mpeg_chan {
-       struct nouveau_mpeg_chan base;
-};
-
-/*******************************************************************************
- * PMPEG context
- ******************************************************************************/
-
-static int
-nv44_mpeg_context_ctor(struct nouveau_object *parent,
-                      struct nouveau_object *engine,
-                      struct nouveau_oclass *oclass, void *data, u32 size,
-                      struct nouveau_object **pobject)
-{
-       struct nv44_mpeg_chan *chan;
-       int ret;
-
-       ret = nouveau_mpeg_context_create(parent, engine, oclass, NULL,
-                                         264 * 4, 16,
-                                         NVOBJ_FLAG_ZERO_ALLOC, &chan);
-       *pobject = nv_object(chan);
-       if (ret)
-               return ret;
-
-       nv_wo32(&chan->base.base, 0x78, 0x02001ec1);
-       return 0;
-}
-
-static int
-nv44_mpeg_context_fini(struct nouveau_object *object, bool suspend)
-{
-
-       struct nv44_mpeg_priv *priv = (void *)object->engine;
-       struct nv44_mpeg_chan *chan = (void *)object;
-       u32 inst = 0x80000000 | nv_gpuobj(chan)->addr >> 4;
-
-       nv_mask(priv, 0x00b32c, 0x00000001, 0x00000000);
-       if (nv_rd32(priv, 0x00b318) == inst)
-               nv_mask(priv, 0x00b318, 0x80000000, 0x00000000);
-       nv_mask(priv, 0x00b32c, 0x00000001, 0x00000001);
-       return 0;
-}
-
-static struct nouveau_oclass
-nv44_mpeg_cclass = {
-       .handle = NV_ENGCTX(MPEG, 0x44),
-       .ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nv44_mpeg_context_ctor,
-               .dtor = _nouveau_mpeg_context_dtor,
-               .init = _nouveau_mpeg_context_init,
-               .fini = nv44_mpeg_context_fini,
-               .rd32 = _nouveau_mpeg_context_rd32,
-               .wr32 = _nouveau_mpeg_context_wr32,
-       },
-};
-
-/*******************************************************************************
- * PMPEG engine/subdev functions
- ******************************************************************************/
-
-static void
-nv44_mpeg_intr(struct nouveau_subdev *subdev)
-{
-       struct nouveau_fifo *pfifo = nouveau_fifo(subdev);
-       struct nouveau_engine *engine = nv_engine(subdev);
-       struct nouveau_object *engctx;
-       struct nouveau_handle *handle;
-       struct nv44_mpeg_priv *priv = (void *)subdev;
-       u32 inst = nv_rd32(priv, 0x00b318) & 0x000fffff;
-       u32 stat = nv_rd32(priv, 0x00b100);
-       u32 type = nv_rd32(priv, 0x00b230);
-       u32 mthd = nv_rd32(priv, 0x00b234);
-       u32 data = nv_rd32(priv, 0x00b238);
-       u32 show = stat;
-       int chid;
-
-       engctx = nouveau_engctx_get(engine, inst);
-       chid   = pfifo->chid(pfifo, engctx);
-
-       if (stat & 0x01000000) {
-               /* happens on initial binding of the object */
-               if (type == 0x00000020 && mthd == 0x0000) {
-                       nv_mask(priv, 0x00b308, 0x00000000, 0x00000000);
-                       show &= ~0x01000000;
-               }
-
-               if (type == 0x00000010) {
-                       handle = nouveau_handle_get_class(engctx, 0x3174);
-                       if (handle && !nv_call(handle->object, mthd, data))
-                               show &= ~0x01000000;
-                       nouveau_handle_put(handle);
-               }
-       }
-
-       nv_wr32(priv, 0x00b100, stat);
-       nv_wr32(priv, 0x00b230, 0x00000001);
-
-       if (show) {
-               nv_error(priv,
-                        "ch %d [0x%08x %s] 0x%08x 0x%08x 0x%08x 0x%08x\n",
-                        chid, inst << 4, nouveau_client_name(engctx), stat,
-                        type, mthd, data);
-       }
-
-       nouveau_engctx_put(engctx);
-}
-
-static void
-nv44_mpeg_me_intr(struct nouveau_subdev *subdev)
-{
-       struct nv44_mpeg_priv *priv = (void *)subdev;
-       u32 stat;
-
-       if ((stat = nv_rd32(priv, 0x00b100)))
-               nv44_mpeg_intr(subdev);
-
-       if ((stat = nv_rd32(priv, 0x00b800))) {
-               nv_error(priv, "PMSRCH 0x%08x\n", stat);
-               nv_wr32(priv, 0x00b800, stat);
-       }
-}
-
-static int
-nv44_mpeg_ctor(struct nouveau_object *parent, struct nouveau_object *engine,
-              struct nouveau_oclass *oclass, void *data, u32 size,
-              struct nouveau_object **pobject)
-{
-       struct nv44_mpeg_priv *priv;
-       int ret;
-
-       ret = nouveau_mpeg_create(parent, engine, oclass, &priv);
-       *pobject = nv_object(priv);
-       if (ret)
-               return ret;
-
-       nv_subdev(priv)->unit = 0x00000002;
-       nv_subdev(priv)->intr = nv44_mpeg_me_intr;
-       nv_engine(priv)->cclass = &nv44_mpeg_cclass;
-       nv_engine(priv)->sclass = nv40_mpeg_sclass;
-       nv_engine(priv)->tile_prog = nv31_mpeg_tile_prog;
-       return 0;
-}
-
-struct nouveau_oclass
-nv44_mpeg_oclass = {
-       .handle = NV_ENGINE(MPEG, 0x44),
-       .ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nv44_mpeg_ctor,
-               .dtor = _nouveau_mpeg_dtor,
-               .init = nv31_mpeg_init,
-               .fini = _nouveau_mpeg_fini,
-       },
-};
diff --git a/drivers/gpu/drm/nouveau/core/engine/mpeg/nv50.c b/drivers/gpu/drm/nouveau/core/engine/mpeg/nv50.c
deleted file mode 100644 (file)
index cae33f8..0000000
+++ /dev/null
@@ -1,230 +0,0 @@
-/*
- * Copyright 2012 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 <core/os.h>
-#include <core/engctx.h>
-
-#include <subdev/vm.h>
-#include <subdev/bar.h>
-#include <subdev/timer.h>
-
-#include <engine/mpeg.h>
-
-struct nv50_mpeg_priv {
-       struct nouveau_mpeg base;
-};
-
-struct nv50_mpeg_chan {
-       struct nouveau_mpeg_chan base;
-};
-
-/*******************************************************************************
- * MPEG object classes
- ******************************************************************************/
-
-static int
-nv50_mpeg_object_ctor(struct nouveau_object *parent,
-                     struct nouveau_object *engine,
-                     struct nouveau_oclass *oclass, void *data, u32 size,
-                     struct nouveau_object **pobject)
-{
-       struct nouveau_gpuobj *obj;
-       int ret;
-
-       ret = nouveau_gpuobj_create(parent, engine, oclass, 0, parent,
-                                   16, 16, 0, &obj);
-       *pobject = nv_object(obj);
-       if (ret)
-               return ret;
-
-       nv_wo32(obj, 0x00, nv_mclass(obj));
-       nv_wo32(obj, 0x04, 0x00000000);
-       nv_wo32(obj, 0x08, 0x00000000);
-       nv_wo32(obj, 0x0c, 0x00000000);
-       return 0;
-}
-
-struct nouveau_ofuncs
-nv50_mpeg_ofuncs = {
-       .ctor = nv50_mpeg_object_ctor,
-       .dtor = _nouveau_gpuobj_dtor,
-       .init = _nouveau_gpuobj_init,
-       .fini = _nouveau_gpuobj_fini,
-       .rd32 = _nouveau_gpuobj_rd32,
-       .wr32 = _nouveau_gpuobj_wr32,
-};
-
-static struct nouveau_oclass
-nv50_mpeg_sclass[] = {
-       { 0x3174, &nv50_mpeg_ofuncs },
-       {}
-};
-
-/*******************************************************************************
- * PMPEG context
- ******************************************************************************/
-
-int
-nv50_mpeg_context_ctor(struct nouveau_object *parent,
-                      struct nouveau_object *engine,
-                      struct nouveau_oclass *oclass, void *data, u32 size,
-                      struct nouveau_object **pobject)
-{
-       struct nouveau_bar *bar = nouveau_bar(parent);
-       struct nv50_mpeg_chan *chan;
-       int ret;
-
-       ret = nouveau_mpeg_context_create(parent, engine, oclass, NULL, 128 * 4,
-                                         0, NVOBJ_FLAG_ZERO_ALLOC, &chan);
-       *pobject = nv_object(chan);
-       if (ret)
-               return ret;
-
-       nv_wo32(chan, 0x0070, 0x00801ec1);
-       nv_wo32(chan, 0x007c, 0x0000037c);
-       bar->flush(bar);
-       return 0;
-}
-
-static struct nouveau_oclass
-nv50_mpeg_cclass = {
-       .handle = NV_ENGCTX(MPEG, 0x50),
-       .ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nv50_mpeg_context_ctor,
-               .dtor = _nouveau_mpeg_context_dtor,
-               .init = _nouveau_mpeg_context_init,
-               .fini = _nouveau_mpeg_context_fini,
-               .rd32 = _nouveau_mpeg_context_rd32,
-               .wr32 = _nouveau_mpeg_context_wr32,
-       },
-};
-
-/*******************************************************************************
- * PMPEG engine/subdev functions
- ******************************************************************************/
-
-void
-nv50_mpeg_intr(struct nouveau_subdev *subdev)
-{
-       struct nv50_mpeg_priv *priv = (void *)subdev;
-       u32 stat = nv_rd32(priv, 0x00b100);
-       u32 type = nv_rd32(priv, 0x00b230);
-       u32 mthd = nv_rd32(priv, 0x00b234);
-       u32 data = nv_rd32(priv, 0x00b238);
-       u32 show = stat;
-
-       if (stat & 0x01000000) {
-               /* happens on initial binding of the object */
-               if (type == 0x00000020 && mthd == 0x0000) {
-                       nv_wr32(priv, 0x00b308, 0x00000100);
-                       show &= ~0x01000000;
-               }
-       }
-
-       if (show) {
-               nv_info(priv, "0x%08x 0x%08x 0x%08x 0x%08x\n",
-                       stat, type, mthd, data);
-       }
-
-       nv_wr32(priv, 0x00b100, stat);
-       nv_wr32(priv, 0x00b230, 0x00000001);
-}
-
-static void
-nv50_vpe_intr(struct nouveau_subdev *subdev)
-{
-       struct nv50_mpeg_priv *priv = (void *)subdev;
-
-       if (nv_rd32(priv, 0x00b100))
-               nv50_mpeg_intr(subdev);
-
-       if (nv_rd32(priv, 0x00b800)) {
-               u32 stat = nv_rd32(priv, 0x00b800);
-               nv_info(priv, "PMSRCH: 0x%08x\n", stat);
-               nv_wr32(priv, 0xb800, stat);
-       }
-}
-
-static int
-nv50_mpeg_ctor(struct nouveau_object *parent, struct nouveau_object *engine,
-              struct nouveau_oclass *oclass, void *data, u32 size,
-              struct nouveau_object **pobject)
-{
-       struct nv50_mpeg_priv *priv;
-       int ret;
-
-       ret = nouveau_mpeg_create(parent, engine, oclass, &priv);
-       *pobject = nv_object(priv);
-       if (ret)
-               return ret;
-
-       nv_subdev(priv)->unit = 0x00400002;
-       nv_subdev(priv)->intr = nv50_vpe_intr;
-       nv_engine(priv)->cclass = &nv50_mpeg_cclass;
-       nv_engine(priv)->sclass = nv50_mpeg_sclass;
-       return 0;
-}
-
-int
-nv50_mpeg_init(struct nouveau_object *object)
-{
-       struct nv50_mpeg_priv *priv = (void *)object;
-       int ret;
-
-       ret = nouveau_mpeg_init(&priv->base);
-       if (ret)
-               return ret;
-
-       nv_wr32(priv, 0x00b32c, 0x00000000);
-       nv_wr32(priv, 0x00b314, 0x00000100);
-       nv_wr32(priv, 0x00b0e0, 0x0000001a);
-
-       nv_wr32(priv, 0x00b220, 0x00000044);
-       nv_wr32(priv, 0x00b300, 0x00801ec1);
-       nv_wr32(priv, 0x00b390, 0x00000000);
-       nv_wr32(priv, 0x00b394, 0x00000000);
-       nv_wr32(priv, 0x00b398, 0x00000000);
-       nv_mask(priv, 0x00b32c, 0x00000001, 0x00000001);
-
-       nv_wr32(priv, 0x00b100, 0xffffffff);
-       nv_wr32(priv, 0x00b140, 0xffffffff);
-
-       if (!nv_wait(priv, 0x00b200, 0x00000001, 0x00000000)) {
-               nv_error(priv, "timeout 0x%08x\n", nv_rd32(priv, 0x00b200));
-               return -EBUSY;
-       }
-
-       return 0;
-}
-
-struct nouveau_oclass
-nv50_mpeg_oclass = {
-       .handle = NV_ENGINE(MPEG, 0x50),
-       .ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nv50_mpeg_ctor,
-               .dtor = _nouveau_mpeg_dtor,
-               .init = nv50_mpeg_init,
-               .fini = _nouveau_mpeg_fini,
-       },
-};
diff --git a/drivers/gpu/drm/nouveau/core/engine/mpeg/nv84.c b/drivers/gpu/drm/nouveau/core/engine/mpeg/nv84.c
deleted file mode 100644 (file)
index e9cc8b1..0000000
+++ /dev/null
@@ -1,102 +0,0 @@
-/*
- * Copyright 2012 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 <core/os.h>
-#include <core/engctx.h>
-
-#include <subdev/vm.h>
-#include <subdev/bar.h>
-#include <subdev/timer.h>
-
-#include <engine/mpeg.h>
-
-struct nv84_mpeg_priv {
-       struct nouveau_mpeg base;
-};
-
-struct nv84_mpeg_chan {
-       struct nouveau_mpeg_chan base;
-};
-
-/*******************************************************************************
- * MPEG object classes
- ******************************************************************************/
-
-static struct nouveau_oclass
-nv84_mpeg_sclass[] = {
-       { 0x8274, &nv50_mpeg_ofuncs },
-       {}
-};
-
-/*******************************************************************************
- * PMPEG context
- ******************************************************************************/
-
-static struct nouveau_oclass
-nv84_mpeg_cclass = {
-       .handle = NV_ENGCTX(MPEG, 0x84),
-       .ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nv50_mpeg_context_ctor,
-               .dtor = _nouveau_mpeg_context_dtor,
-               .init = _nouveau_mpeg_context_init,
-               .fini = _nouveau_mpeg_context_fini,
-               .rd32 = _nouveau_mpeg_context_rd32,
-               .wr32 = _nouveau_mpeg_context_wr32,
-       },
-};
-
-/*******************************************************************************
- * PMPEG engine/subdev functions
- ******************************************************************************/
-
-static int
-nv84_mpeg_ctor(struct nouveau_object *parent, struct nouveau_object *engine,
-              struct nouveau_oclass *oclass, void *data, u32 size,
-              struct nouveau_object **pobject)
-{
-       struct nv84_mpeg_priv *priv;
-       int ret;
-
-       ret = nouveau_mpeg_create(parent, engine, oclass, &priv);
-       *pobject = nv_object(priv);
-       if (ret)
-               return ret;
-
-       nv_subdev(priv)->unit = 0x00000002;
-       nv_subdev(priv)->intr = nv50_mpeg_intr;
-       nv_engine(priv)->cclass = &nv84_mpeg_cclass;
-       nv_engine(priv)->sclass = nv84_mpeg_sclass;
-       return 0;
-}
-
-struct nouveau_oclass
-nv84_mpeg_oclass = {
-       .handle = NV_ENGINE(MPEG, 0x84),
-       .ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nv84_mpeg_ctor,
-               .dtor = _nouveau_mpeg_dtor,
-               .init = nv50_mpeg_init,
-               .fini = _nouveau_mpeg_fini,
-       },
-};
diff --git a/drivers/gpu/drm/nouveau/core/engine/perfmon/base.c b/drivers/gpu/drm/nouveau/core/engine/perfmon/base.c
deleted file mode 100644 (file)
index 6301381..0000000
+++ /dev/null
@@ -1,483 +0,0 @@
-/*
- * Copyright 2013 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 <core/client.h>
-#include <core/option.h>
-#include <nvif/unpack.h>
-#include <nvif/class.h>
-#include <nvif/ioctl.h>
-
-#include <subdev/clock.h>
-
-#include "priv.h"
-
-#define QUAD_MASK 0x0f
-#define QUAD_FREE 0x01
-
-static struct nouveau_perfsig *
-nouveau_perfsig_find_(struct nouveau_perfdom *dom, const char *name, u32 size)
-{
-       char path[64];
-       int i;
-
-       if (name[0] != '/') {
-               for (i = 0; i < dom->signal_nr; i++) {
-                       if ( dom->signal[i].name &&
-                           !strncmp(name, dom->signal[i].name, size))
-                               return &dom->signal[i];
-               }
-       } else {
-               for (i = 0; i < dom->signal_nr; i++) {
-                       snprintf(path, sizeof(path), "/%s/%02x", dom->name, i);
-                       if (!strncmp(name, path, size))
-                               return &dom->signal[i];
-               }
-       }
-
-       return NULL;
-}
-
-struct nouveau_perfsig *
-nouveau_perfsig_find(struct nouveau_perfmon *ppm, const char *name, u32 size,
-                    struct nouveau_perfdom **pdom)
-{
-       struct nouveau_perfdom *dom = *pdom;
-       struct nouveau_perfsig *sig;
-
-       if (dom == NULL) {
-               list_for_each_entry(dom, &ppm->domains, head) {
-                       sig = nouveau_perfsig_find_(dom, name, size);
-                       if (sig) {
-                               *pdom = dom;
-                               return sig;
-                       }
-               }
-
-               return NULL;
-       }
-
-       return nouveau_perfsig_find_(dom, name, size);
-}
-
-struct nouveau_perfctr *
-nouveau_perfsig_wrap(struct nouveau_perfmon *ppm, const char *name,
-                    struct nouveau_perfdom **pdom)
-{
-       struct nouveau_perfsig *sig;
-       struct nouveau_perfctr *ctr;
-
-       sig = nouveau_perfsig_find(ppm, name, strlen(name), pdom);
-       if (!sig)
-               return NULL;
-
-       ctr = kzalloc(sizeof(*ctr), GFP_KERNEL);
-       if (ctr) {
-               ctr->signal[0] = sig;
-               ctr->logic_op = 0xaaaa;
-       }
-
-       return ctr;
-}
-
-/*******************************************************************************
- * Perfmon object classes
- ******************************************************************************/
-static int
-nouveau_perfctr_query(struct nouveau_object *object, void *data, u32 size)
-{
-       union {
-               struct nvif_perfctr_query_v0 v0;
-       } *args = data;
-       struct nouveau_device *device = nv_device(object);
-       struct nouveau_perfmon *ppm = (void *)object->engine;
-       struct nouveau_perfdom *dom = NULL, *chk;
-       const bool all = nouveau_boolopt(device->cfgopt, "NvPmShowAll", false);
-       const bool raw = nouveau_boolopt(device->cfgopt, "NvPmUnnamed", all);
-       const char *name;
-       int tmp = 0, di, si;
-       int ret;
-
-       nv_ioctl(object, "perfctr query size %d\n", size);
-       if (nvif_unpack(args->v0, 0, 0, false)) {
-               nv_ioctl(object, "perfctr query vers %d iter %08x\n",
-                        args->v0.version, args->v0.iter);
-               di = (args->v0.iter & 0xff000000) >> 24;
-               si = (args->v0.iter & 0x00ffffff) - 1;
-       } else
-               return ret;
-
-       list_for_each_entry(chk, &ppm->domains, head) {
-               if (tmp++ == di) {
-                       dom = chk;
-                       break;
-               }
-       }
-
-       if (dom == NULL || si >= (int)dom->signal_nr)
-               return -EINVAL;
-
-       if (si >= 0) {
-               if (raw || !(name = dom->signal[si].name)) {
-                       snprintf(args->v0.name, sizeof(args->v0.name),
-                                "/%s/%02x", dom->name, si);
-               } else {
-                       strncpy(args->v0.name, name, sizeof(args->v0.name));
-               }
-       }
-
-       do {
-               while (++si < dom->signal_nr) {
-                       if (all || dom->signal[si].name) {
-                               args->v0.iter = (di << 24) | ++si;
-                               return 0;
-                       }
-               }
-               si = -1;
-               di = di + 1;
-               dom = list_entry(dom->head.next, typeof(*dom), head);
-       } while (&dom->head != &ppm->domains);
-
-       args->v0.iter = 0xffffffff;
-       return 0;
-}
-
-static int
-nouveau_perfctr_sample(struct nouveau_object *object, void *data, u32 size)
-{
-       union {
-               struct nvif_perfctr_sample none;
-       } *args = data;
-       struct nouveau_perfmon *ppm = (void *)object->engine;
-       struct nouveau_perfctr *ctr, *tmp;
-       struct nouveau_perfdom *dom;
-       int ret;
-
-       nv_ioctl(object, "perfctr sample size %d\n", size);
-       if (nvif_unvers(args->none)) {
-               nv_ioctl(object, "perfctr sample\n");
-       } else
-               return ret;
-       ppm->sequence++;
-
-       list_for_each_entry(dom, &ppm->domains, head) {
-               /* sample previous batch of counters */
-               if (dom->quad != QUAD_MASK) {
-                       dom->func->next(ppm, dom);
-                       tmp = NULL;
-                       while (!list_empty(&dom->list)) {
-                               ctr = list_first_entry(&dom->list,
-                                                       typeof(*ctr), head);
-                               if (ctr->slot < 0) break;
-                               if ( tmp && tmp == ctr) break;
-                               if (!tmp) tmp = ctr;
-                               dom->func->read(ppm, dom, ctr);
-                               ctr->slot  = -1;
-                               list_move_tail(&ctr->head, &dom->list);
-                       }
-               }
-
-               dom->quad = QUAD_MASK;
-
-               /* setup next batch of counters for sampling */
-               list_for_each_entry(ctr, &dom->list, head) {
-                       ctr->slot = ffs(dom->quad) - 1;
-                       if (ctr->slot < 0)
-                               break;
-                       dom->quad &= ~(QUAD_FREE << ctr->slot);
-                       dom->func->init(ppm, dom, ctr);
-               }
-
-               if (dom->quad != QUAD_MASK)
-                       dom->func->next(ppm, dom);
-       }
-
-       return 0;
-}
-
-static int
-nouveau_perfctr_read(struct nouveau_object *object, void *data, u32 size)
-{
-       union {
-               struct nvif_perfctr_read_v0 v0;
-       } *args = data;
-       struct nouveau_perfctr *ctr = (void *)object;
-       int ret;
-
-       nv_ioctl(object, "perfctr read size %d\n", size);
-       if (nvif_unpack(args->v0, 0, 0, false)) {
-               nv_ioctl(object, "perfctr read vers %d\n", args->v0.version);
-       } else
-               return ret;
-
-       if (!ctr->clk)
-               return -EAGAIN;
-
-       args->v0.clk = ctr->clk;
-       args->v0.ctr = ctr->ctr;
-       return 0;
-}
-
-static int
-nouveau_perfctr_mthd(struct nouveau_object *object, u32 mthd,
-                    void *data, u32 size)
-{
-       switch (mthd) {
-       case NVIF_PERFCTR_V0_QUERY:
-               return nouveau_perfctr_query(object, data, size);
-       case NVIF_PERFCTR_V0_SAMPLE:
-               return nouveau_perfctr_sample(object, data, size);
-       case NVIF_PERFCTR_V0_READ:
-               return nouveau_perfctr_read(object, data, size);
-       default:
-               break;
-       }
-       return -EINVAL;
-}
-
-static void
-nouveau_perfctr_dtor(struct nouveau_object *object)
-{
-       struct nouveau_perfctr *ctr = (void *)object;
-       if (ctr->head.next)
-               list_del(&ctr->head);
-       nouveau_object_destroy(&ctr->base);
-}
-
-static int
-nouveau_perfctr_ctor(struct nouveau_object *parent,
-                    struct nouveau_object *engine,
-                    struct nouveau_oclass *oclass, void *data, u32 size,
-                    struct nouveau_object **pobject)
-{
-       union {
-               struct nvif_perfctr_v0 v0;
-       } *args = data;
-       struct nouveau_perfmon *ppm = (void *)engine;
-       struct nouveau_perfdom *dom = NULL;
-       struct nouveau_perfsig *sig[4] = {};
-       struct nouveau_perfctr *ctr;
-       int ret, i;
-
-       nv_ioctl(parent, "create perfctr size %d\n", size);
-       if (nvif_unpack(args->v0, 0, 0, false)) {
-               nv_ioctl(parent, "create perfctr vers %d logic_op %04x\n",
-                        args->v0.version, args->v0.logic_op);
-       } else
-               return ret;
-
-       for (i = 0; i < ARRAY_SIZE(args->v0.name) && args->v0.name[i][0]; i++) {
-               sig[i] = nouveau_perfsig_find(ppm, args->v0.name[i],
-                                             strnlen(args->v0.name[i],
-                                             sizeof(args->v0.name[i])),
-                                             &dom);
-               if (!sig[i])
-                       return -EINVAL;
-       }
-
-       ret = nouveau_object_create(parent, engine, oclass, 0, &ctr);
-       *pobject = nv_object(ctr);
-       if (ret)
-               return ret;
-
-       ctr->slot = -1;
-       ctr->logic_op = args->v0.logic_op;
-       ctr->signal[0] = sig[0];
-       ctr->signal[1] = sig[1];
-       ctr->signal[2] = sig[2];
-       ctr->signal[3] = sig[3];
-       if (dom)
-               list_add_tail(&ctr->head, &dom->list);
-       return 0;
-}
-
-static struct nouveau_ofuncs
-nouveau_perfctr_ofuncs = {
-       .ctor = nouveau_perfctr_ctor,
-       .dtor = nouveau_perfctr_dtor,
-       .init = nouveau_object_init,
-       .fini = nouveau_object_fini,
-       .mthd = nouveau_perfctr_mthd,
-};
-
-struct nouveau_oclass
-nouveau_perfmon_sclass[] = {
-       { .handle = NVIF_IOCTL_NEW_V0_PERFCTR,
-         .ofuncs = &nouveau_perfctr_ofuncs,
-       },
-       {},
-};
-
-/*******************************************************************************
- * PPM context
- ******************************************************************************/
-static void
-nouveau_perfctx_dtor(struct nouveau_object *object)
-{
-       struct nouveau_perfmon *ppm = (void *)object->engine;
-       mutex_lock(&nv_subdev(ppm)->mutex);
-       nouveau_engctx_destroy(&ppm->context->base);
-       ppm->context = NULL;
-       mutex_unlock(&nv_subdev(ppm)->mutex);
-}
-
-static int
-nouveau_perfctx_ctor(struct nouveau_object *parent,
-                    struct nouveau_object *engine,
-                    struct nouveau_oclass *oclass, void *data, u32 size,
-                    struct nouveau_object **pobject)
-{
-       struct nouveau_perfmon *ppm = (void *)engine;
-       struct nouveau_perfctx *ctx;
-       int ret;
-
-       ret = nouveau_engctx_create(parent, engine, oclass, NULL,
-                                   0, 0, 0, &ctx);
-       *pobject = nv_object(ctx);
-       if (ret)
-               return ret;
-
-       mutex_lock(&nv_subdev(ppm)->mutex);
-       if (ppm->context == NULL)
-               ppm->context = ctx;
-       mutex_unlock(&nv_subdev(ppm)->mutex);
-
-       if (ctx != ppm->context)
-               return -EBUSY;
-
-       return 0;
-}
-
-struct nouveau_oclass
-nouveau_perfmon_cclass = {
-       .handle = NV_ENGCTX(PERFMON, 0x00),
-       .ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nouveau_perfctx_ctor,
-               .dtor = nouveau_perfctx_dtor,
-               .init = _nouveau_engctx_init,
-               .fini = _nouveau_engctx_fini,
-       },
-};
-
-/*******************************************************************************
- * PPM engine/subdev functions
- ******************************************************************************/
-int
-nouveau_perfdom_new(struct nouveau_perfmon *ppm, const char *name, u32 mask,
-                   u32 base, u32 size_unit, u32 size_domain,
-                   const struct nouveau_specdom *spec)
-{
-       const struct nouveau_specdom *sdom;
-       const struct nouveau_specsig *ssig;
-       struct nouveau_perfdom *dom;
-       int i;
-
-       for (i = 0; i == 0 || mask; i++) {
-               u32 addr = base + (i * size_unit);
-               if (i && !(mask & (1 << i)))
-                       continue;
-
-               sdom = spec;
-               while (sdom->signal_nr) {
-                       dom = kzalloc(sizeof(*dom) + sdom->signal_nr *
-                                     sizeof(*dom->signal), GFP_KERNEL);
-                       if (!dom)
-                               return -ENOMEM;
-
-                       if (mask) {
-                               snprintf(dom->name, sizeof(dom->name),
-                                        "%s/%02x/%02x", name, i,
-                                        (int)(sdom - spec));
-                       } else {
-                               snprintf(dom->name, sizeof(dom->name),
-                                        "%s/%02x", name, (int)(sdom - spec));
-                       }
-
-                       list_add_tail(&dom->head, &ppm->domains);
-                       INIT_LIST_HEAD(&dom->list);
-                       dom->func = sdom->func;
-                       dom->addr = addr;
-                       dom->quad = QUAD_MASK;
-                       dom->signal_nr = sdom->signal_nr;
-
-                       ssig = (sdom++)->signal;
-                       while (ssig->name) {
-                               dom->signal[ssig->signal].name = ssig->name;
-                               ssig++;
-                       }
-
-                       addr += size_domain;
-               }
-
-               mask &= ~(1 << i);
-       }
-
-       return 0;
-}
-
-int
-_nouveau_perfmon_fini(struct nouveau_object *object, bool suspend)
-{
-       struct nouveau_perfmon *ppm = (void *)object;
-       return nouveau_engine_fini(&ppm->base, suspend);
-}
-
-int
-_nouveau_perfmon_init(struct nouveau_object *object)
-{
-       struct nouveau_perfmon *ppm = (void *)object;
-       return nouveau_engine_init(&ppm->base);
-}
-
-void
-_nouveau_perfmon_dtor(struct nouveau_object *object)
-{
-       struct nouveau_perfmon *ppm = (void *)object;
-       struct nouveau_perfdom *dom, *tmp;
-
-       list_for_each_entry_safe(dom, tmp, &ppm->domains, head) {
-               list_del(&dom->head);
-               kfree(dom);
-       }
-
-       nouveau_engine_destroy(&ppm->base);
-}
-
-int
-nouveau_perfmon_create_(struct nouveau_object *parent,
-                       struct nouveau_object *engine,
-                       struct nouveau_oclass *oclass,
-                       int length, void **pobject)
-{
-       struct nouveau_perfmon *ppm;
-       int ret;
-
-       ret = nouveau_engine_create_(parent, engine, oclass, true, "PPM",
-                                    "perfmon", length, pobject);
-       ppm = *pobject;
-       if (ret)
-               return ret;
-
-       INIT_LIST_HEAD(&ppm->domains);
-       return 0;
-}
diff --git a/drivers/gpu/drm/nouveau/core/engine/perfmon/daemon.c b/drivers/gpu/drm/nouveau/core/engine/perfmon/daemon.c
deleted file mode 100644 (file)
index 50696cc..0000000
+++ /dev/null
@@ -1,109 +0,0 @@
-/*
- * Copyright 2013 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 "priv.h"
-
-static void
-pwr_perfctr_init(struct nouveau_perfmon *ppm, struct nouveau_perfdom *dom,
-                struct nouveau_perfctr *ctr)
-{
-       u32 mask = 0x00000000;
-       u32 ctrl = 0x00000001;
-       int i;
-
-       for (i = 0; i < ARRAY_SIZE(ctr->signal) && ctr->signal[i]; i++)
-               mask |= 1 << (ctr->signal[i] - dom->signal);
-
-       nv_wr32(ppm, 0x10a504 + (ctr->slot * 0x10), mask);
-       nv_wr32(ppm, 0x10a50c + (ctr->slot * 0x10), ctrl);
-       nv_wr32(ppm, 0x10a50c + (ppm->last * 0x10), 0x00000003);
-}
-
-static void
-pwr_perfctr_read(struct nouveau_perfmon *ppm, struct nouveau_perfdom *dom,
-                struct nouveau_perfctr *ctr)
-{
-       ctr->ctr = ppm->pwr[ctr->slot];
-       ctr->clk = ppm->pwr[ppm->last];
-}
-
-static void
-pwr_perfctr_next(struct nouveau_perfmon *ppm, struct nouveau_perfdom *dom)
-{
-       int i;
-
-       for (i = 0; i <= ppm->last; i++) {
-               ppm->pwr[i] = nv_rd32(ppm, 0x10a508 + (i * 0x10));
-               nv_wr32(ppm, 0x10a508 + (i * 0x10), 0x80000000);
-       }
-}
-
-static const struct nouveau_funcdom
-pwr_perfctr_func = {
-       .init = pwr_perfctr_init,
-       .read = pwr_perfctr_read,
-       .next = pwr_perfctr_next,
-};
-
-const struct nouveau_specdom
-nva3_perfmon_pwr[] = {
-       { 0x20, (const struct nouveau_specsig[]) {
-                       { 0x00, "pwr_gr_idle" },
-                       { 0x04, "pwr_bsp_idle" },
-                       { 0x05, "pwr_vp_idle" },
-                       { 0x06, "pwr_ppp_idle" },
-                       { 0x13, "pwr_ce0_idle" },
-                       {}
-               }, &pwr_perfctr_func },
-       {}
-};
-
-const struct nouveau_specdom
-nvc0_perfmon_pwr[] = {
-       { 0x20, (const struct nouveau_specsig[]) {
-                       { 0x00, "pwr_gr_idle" },
-                       { 0x04, "pwr_bsp_idle" },
-                       { 0x05, "pwr_vp_idle" },
-                       { 0x06, "pwr_ppp_idle" },
-                       { 0x13, "pwr_ce0_idle" },
-                       { 0x14, "pwr_ce1_idle" },
-                       {}
-               }, &pwr_perfctr_func },
-       {}
-};
-
-const struct nouveau_specdom
-nve0_perfmon_pwr[] = {
-       { 0x20, (const struct nouveau_specsig[]) {
-                       { 0x00, "pwr_gr_idle" },
-                       { 0x04, "pwr_bsp_idle" },
-                       { 0x05, "pwr_vp_idle" },
-                       { 0x06, "pwr_ppp_idle" },
-                       { 0x13, "pwr_ce0_idle" },
-                       { 0x14, "pwr_ce1_idle" },
-                       { 0x15, "pwr_ce2_idle" },
-                       {}
-               }, &pwr_perfctr_func },
-       {}
-};
diff --git a/drivers/gpu/drm/nouveau/core/engine/perfmon/nv40.c b/drivers/gpu/drm/nouveau/core/engine/perfmon/nv40.c
deleted file mode 100644 (file)
index b2a1078..0000000
+++ /dev/null
@@ -1,143 +0,0 @@
-/*
- * Copyright 2013 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 "nv40.h"
-
-/*******************************************************************************
- * Perfmon object classes
- ******************************************************************************/
-
-/*******************************************************************************
- * PPM context
- ******************************************************************************/
-
-/*******************************************************************************
- * PPM engine/subdev functions
- ******************************************************************************/
-
-static void
-nv40_perfctr_init(struct nouveau_perfmon *ppm, struct nouveau_perfdom *dom,
-                 struct nouveau_perfctr *ctr)
-{
-       struct nv40_perfmon_priv *priv = (void *)ppm;
-       struct nv40_perfmon_cntr *cntr = (void *)ctr;
-       u32 log = ctr->logic_op;
-       u32 src = 0x00000000;
-       int i;
-
-       for (i = 0; i < 4 && ctr->signal[i]; i++)
-               src |= (ctr->signal[i] - dom->signal) << (i * 8);
-
-       nv_wr32(priv, 0x00a7c0 + dom->addr, 0x00000001);
-       nv_wr32(priv, 0x00a400 + dom->addr + (cntr->base.slot * 0x40), src);
-       nv_wr32(priv, 0x00a420 + dom->addr + (cntr->base.slot * 0x40), log);
-}
-
-static void
-nv40_perfctr_read(struct nouveau_perfmon *ppm, struct nouveau_perfdom *dom,
-                 struct nouveau_perfctr *ctr)
-{
-       struct nv40_perfmon_priv *priv = (void *)ppm;
-       struct nv40_perfmon_cntr *cntr = (void *)ctr;
-
-       switch (cntr->base.slot) {
-       case 0: cntr->base.ctr = nv_rd32(priv, 0x00a700 + dom->addr); break;
-       case 1: cntr->base.ctr = nv_rd32(priv, 0x00a6c0 + dom->addr); break;
-       case 2: cntr->base.ctr = nv_rd32(priv, 0x00a680 + dom->addr); break;
-       case 3: cntr->base.ctr = nv_rd32(priv, 0x00a740 + dom->addr); break;
-       }
-       cntr->base.clk = nv_rd32(priv, 0x00a600 + dom->addr);
-}
-
-static void
-nv40_perfctr_next(struct nouveau_perfmon *ppm, struct nouveau_perfdom *dom)
-{
-       struct nv40_perfmon_priv *priv = (void *)ppm;
-       if (priv->sequence != ppm->sequence) {
-               nv_wr32(priv, 0x400084, 0x00000020);
-               priv->sequence = ppm->sequence;
-       }
-}
-
-const struct nouveau_funcdom
-nv40_perfctr_func = {
-       .init = nv40_perfctr_init,
-       .read = nv40_perfctr_read,
-       .next = nv40_perfctr_next,
-};
-
-static const struct nouveau_specdom
-nv40_perfmon[] = {
-       { 0x20, (const struct nouveau_specsig[]) {
-                       {}
-               }, &nv40_perfctr_func },
-       { 0x20, (const struct nouveau_specsig[]) {
-                       {}
-               }, &nv40_perfctr_func },
-       { 0x20, (const struct nouveau_specsig[]) {
-                       {}
-               }, &nv40_perfctr_func },
-       { 0x20, (const struct nouveau_specsig[]) {
-                       {}
-               }, &nv40_perfctr_func },
-       { 0x20, (const struct nouveau_specsig[]) {
-                       {}
-               }, &nv40_perfctr_func },
-       {}
-};
-
-int
-nv40_perfmon_ctor(struct nouveau_object *parent, struct nouveau_object *engine,
-                 struct nouveau_oclass *oclass, void *data, u32 size,
-                 struct nouveau_object **pobject)
-{
-       struct nv40_perfmon_oclass *mclass = (void *)oclass;
-       struct nv40_perfmon_priv *priv;
-       int ret;
-
-       ret = nouveau_perfmon_create(parent, engine, oclass, &priv);
-       *pobject = nv_object(priv);
-       if (ret)
-               return ret;
-
-       ret = nouveau_perfdom_new(&priv->base, "pm", 0, 0, 0, 4, mclass->doms);
-       if (ret)
-               return ret;
-
-       nv_engine(priv)->cclass = &nouveau_perfmon_cclass;
-       nv_engine(priv)->sclass =  nouveau_perfmon_sclass;
-       return 0;
-}
-
-struct nouveau_oclass *
-nv40_perfmon_oclass = &(struct nv40_perfmon_oclass) {
-       .base.handle = NV_ENGINE(PERFMON, 0x40),
-       .base.ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nv40_perfmon_ctor,
-               .dtor = _nouveau_perfmon_dtor,
-               .init = _nouveau_perfmon_init,
-               .fini = _nouveau_perfmon_fini,
-       },
-       .doms = nv40_perfmon,
-}.base;
diff --git a/drivers/gpu/drm/nouveau/core/engine/perfmon/nv40.h b/drivers/gpu/drm/nouveau/core/engine/perfmon/nv40.h
deleted file mode 100644 (file)
index 1b5792d..0000000
+++ /dev/null
@@ -1,26 +0,0 @@
-#ifndef __NVKM_PM_NV40_H__
-#define __NVKM_PM_NV40_H__
-
-#include "priv.h"
-
-struct nv40_perfmon_oclass {
-       struct nouveau_oclass base;
-       const struct nouveau_specdom *doms;
-};
-
-struct nv40_perfmon_priv {
-       struct nouveau_perfmon base;
-       u32 sequence;
-};
-
-int nv40_perfmon_ctor(struct nouveau_object *, struct nouveau_object *,
-                     struct nouveau_oclass *, void *data, u32 size,
-                     struct nouveau_object **pobject);
-
-struct nv40_perfmon_cntr {
-       struct nouveau_perfctr base;
-};
-
-extern const struct nouveau_funcdom nv40_perfctr_func;
-
-#endif
diff --git a/drivers/gpu/drm/nouveau/core/engine/perfmon/nv50.c b/drivers/gpu/drm/nouveau/core/engine/perfmon/nv50.c
deleted file mode 100644 (file)
index 9421769..0000000
+++ /dev/null
@@ -1,70 +0,0 @@
-/*
- * Copyright 2013 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 "nv40.h"
-
-/*******************************************************************************
- * Perfmon object classes
- ******************************************************************************/
-
-/*******************************************************************************
- * PPM context
- ******************************************************************************/
-
-/*******************************************************************************
- * PPM engine/subdev functions
- ******************************************************************************/
-
-static const struct nouveau_specdom
-nv50_perfmon[] = {
-       { 0x040, (const struct nouveau_specsig[]) {
-                       {}
-               }, &nv40_perfctr_func },
-       { 0x100, (const struct nouveau_specsig[]) {
-                       { 0xc8, "gr_idle" },
-                       {}
-               }, &nv40_perfctr_func },
-       { 0x100, (const struct nouveau_specsig[]) {
-                       {}
-               }, &nv40_perfctr_func },
-       { 0x020, (const struct nouveau_specsig[]) {
-                       {}
-               }, &nv40_perfctr_func },
-       { 0x040, (const struct nouveau_specsig[]) {
-                       {}
-               }, &nv40_perfctr_func },
-       {}
-};
-
-struct nouveau_oclass *
-nv50_perfmon_oclass = &(struct nv40_perfmon_oclass) {
-       .base.handle = NV_ENGINE(PERFMON, 0x50),
-       .base.ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nv40_perfmon_ctor,
-               .dtor = _nouveau_perfmon_dtor,
-               .init = _nouveau_perfmon_init,
-               .fini = _nouveau_perfmon_fini,
-       },
-       .doms = nv50_perfmon,
-}.base;
diff --git a/drivers/gpu/drm/nouveau/core/engine/perfmon/nv84.c b/drivers/gpu/drm/nouveau/core/engine/perfmon/nv84.c
deleted file mode 100644 (file)
index 9232c7f..0000000
+++ /dev/null
@@ -1,78 +0,0 @@
-/*
- * Copyright 2013 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 "nv40.h"
-
-/*******************************************************************************
- * Perfmon object classes
- ******************************************************************************/
-
-/*******************************************************************************
- * PPM context
- ******************************************************************************/
-
-/*******************************************************************************
- * PPM engine/subdev functions
- ******************************************************************************/
-
-static const struct nouveau_specdom
-nv84_perfmon[] = {
-       { 0x20, (const struct nouveau_specsig[]) {
-                       {}
-               }, &nv40_perfctr_func },
-       { 0x20, (const struct nouveau_specsig[]) {
-                       {}
-               }, &nv40_perfctr_func },
-       { 0x20, (const struct nouveau_specsig[]) {
-                       {}
-               }, &nv40_perfctr_func },
-       { 0x20, (const struct nouveau_specsig[]) {
-                       {}
-               }, &nv40_perfctr_func },
-       { 0x20, (const struct nouveau_specsig[]) {
-                       {}
-               }, &nv40_perfctr_func },
-       { 0x20, (const struct nouveau_specsig[]) {
-                       {}
-               }, &nv40_perfctr_func },
-       { 0x20, (const struct nouveau_specsig[]) {
-                       {}
-               }, &nv40_perfctr_func },
-       { 0x20, (const struct nouveau_specsig[]) {
-                       {}
-               }, &nv40_perfctr_func },
-       {}
-};
-
-struct nouveau_oclass *
-nv84_perfmon_oclass = &(struct nv40_perfmon_oclass) {
-       .base.handle = NV_ENGINE(PERFMON, 0x84),
-       .base.ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nv40_perfmon_ctor,
-               .dtor = _nouveau_perfmon_dtor,
-               .init = _nouveau_perfmon_init,
-               .fini = _nouveau_perfmon_fini,
-       },
-       .doms = nv84_perfmon,
-}.base;
diff --git a/drivers/gpu/drm/nouveau/core/engine/perfmon/nva3.c b/drivers/gpu/drm/nouveau/core/engine/perfmon/nva3.c
deleted file mode 100644 (file)
index 6197ebd..0000000
+++ /dev/null
@@ -1,96 +0,0 @@
-/*
- * Copyright 2013 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 "nv40.h"
-
-/*******************************************************************************
- * Perfmon object classes
- ******************************************************************************/
-
-/*******************************************************************************
- * PPM context
- ******************************************************************************/
-
-/*******************************************************************************
- * PPM engine/subdev functions
- ******************************************************************************/
-
-static const struct nouveau_specdom
-nva3_perfmon[] = {
-       { 0x20, (const struct nouveau_specsig[]) {
-                       {}
-               }, &nv40_perfctr_func },
-       { 0x20, (const struct nouveau_specsig[]) {
-                       {}
-               }, &nv40_perfctr_func },
-       { 0x20, (const struct nouveau_specsig[]) {
-                       {}
-               }, &nv40_perfctr_func },
-       { 0x20, (const struct nouveau_specsig[]) {
-                       {}
-               }, &nv40_perfctr_func },
-       { 0x20, (const struct nouveau_specsig[]) {
-                       {}
-               }, &nv40_perfctr_func },
-       { 0x20, (const struct nouveau_specsig[]) {
-                       {}
-               }, &nv40_perfctr_func },
-       { 0x20, (const struct nouveau_specsig[]) {
-                       {}
-               }, &nv40_perfctr_func },
-       { 0x20, (const struct nouveau_specsig[]) {
-                       {}
-               }, &nv40_perfctr_func },
-       {}
-};
-
-static int
-nva3_perfmon_ctor(struct nouveau_object *parent, struct nouveau_object *engine,
-                 struct nouveau_oclass *oclass, void *data, u32 size,
-                 struct nouveau_object **object)
-{
-       int ret = nv40_perfmon_ctor(parent, engine, oclass, data, size, object);
-       if (ret == 0) {
-               struct nv40_perfmon_priv *priv = (void *)*object;
-               ret = nouveau_perfdom_new(&priv->base, "pwr", 0, 0, 0, 0,
-                                          nva3_perfmon_pwr);
-               if (ret)
-                       return ret;
-
-               priv->base.last = 3;
-       }
-       return ret;
-}
-
-struct nouveau_oclass *
-nva3_perfmon_oclass = &(struct nv40_perfmon_oclass) {
-       .base.handle = NV_ENGINE(PERFMON, 0xa3),
-       .base.ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nva3_perfmon_ctor,
-               .dtor = _nouveau_perfmon_dtor,
-               .init = _nouveau_perfmon_init,
-               .fini = _nouveau_perfmon_fini,
-       },
-       .doms = nva3_perfmon,
-}.base;
diff --git a/drivers/gpu/drm/nouveau/core/engine/perfmon/nvc0.c b/drivers/gpu/drm/nouveau/core/engine/perfmon/nvc0.c
deleted file mode 100644 (file)
index 74b2410..0000000
+++ /dev/null
@@ -1,173 +0,0 @@
-/*
- * Copyright 2013 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 "nvc0.h"
-
-/*******************************************************************************
- * Perfmon object classes
- ******************************************************************************/
-
-/*******************************************************************************
- * PPM context
- ******************************************************************************/
-
-/*******************************************************************************
- * PPM engine/subdev functions
- ******************************************************************************/
-
-static const struct nouveau_specdom
-nvc0_perfmon_hub[] = {
-       {}
-};
-
-static const struct nouveau_specdom
-nvc0_perfmon_gpc[] = {
-       {}
-};
-
-static const struct nouveau_specdom
-nvc0_perfmon_part[] = {
-       {}
-};
-
-static void
-nvc0_perfctr_init(struct nouveau_perfmon *ppm, struct nouveau_perfdom *dom,
-                 struct nouveau_perfctr *ctr)
-{
-       struct nvc0_perfmon_priv *priv = (void *)ppm;
-       struct nvc0_perfmon_cntr *cntr = (void *)ctr;
-       u32 log = ctr->logic_op;
-       u32 src = 0x00000000;
-       int i;
-
-       for (i = 0; i < 4 && ctr->signal[i]; i++)
-               src |= (ctr->signal[i] - dom->signal) << (i * 8);
-
-       nv_wr32(priv, dom->addr + 0x09c, 0x00040002);
-       nv_wr32(priv, dom->addr + 0x100, 0x00000000);
-       nv_wr32(priv, dom->addr + 0x040 + (cntr->base.slot * 0x08), src);
-       nv_wr32(priv, dom->addr + 0x044 + (cntr->base.slot * 0x08), log);
-}
-
-static void
-nvc0_perfctr_read(struct nouveau_perfmon *ppm, struct nouveau_perfdom *dom,
-                 struct nouveau_perfctr *ctr)
-{
-       struct nvc0_perfmon_priv *priv = (void *)ppm;
-       struct nvc0_perfmon_cntr *cntr = (void *)ctr;
-
-       switch (cntr->base.slot) {
-       case 0: cntr->base.ctr = nv_rd32(priv, dom->addr + 0x08c); break;
-       case 1: cntr->base.ctr = nv_rd32(priv, dom->addr + 0x088); break;
-       case 2: cntr->base.ctr = nv_rd32(priv, dom->addr + 0x080); break;
-       case 3: cntr->base.ctr = nv_rd32(priv, dom->addr + 0x090); break;
-       }
-       cntr->base.clk = nv_rd32(priv, dom->addr + 0x070);
-}
-
-static void
-nvc0_perfctr_next(struct nouveau_perfmon *ppm, struct nouveau_perfdom *dom)
-{
-       struct nvc0_perfmon_priv *priv = (void *)ppm;
-       nv_wr32(priv, dom->addr + 0x06c, dom->signal_nr - 0x40 + 0x27);
-       nv_wr32(priv, dom->addr + 0x0ec, 0x00000011);
-}
-
-const struct nouveau_funcdom
-nvc0_perfctr_func = {
-       .init = nvc0_perfctr_init,
-       .read = nvc0_perfctr_read,
-       .next = nvc0_perfctr_next,
-};
-
-int
-nvc0_perfmon_fini(struct nouveau_object *object, bool suspend)
-{
-       struct nvc0_perfmon_priv *priv = (void *)object;
-       nv_mask(priv, 0x000200, 0x10000000, 0x00000000);
-       nv_mask(priv, 0x000200, 0x10000000, 0x10000000);
-       return nouveau_perfmon_fini(&priv->base, suspend);
-}
-
-static int
-nvc0_perfmon_ctor(struct nouveau_object *parent, struct nouveau_object *engine,
-                 struct nouveau_oclass *oclass, void *data, u32 size,
-                 struct nouveau_object **pobject)
-{
-       struct nvc0_perfmon_priv *priv;
-       u32 mask;
-       int ret;
-
-       ret = nouveau_perfmon_create(parent, engine, oclass, &priv);
-       *pobject = nv_object(priv);
-       if (ret)
-               return ret;
-
-       ret = nouveau_perfdom_new(&priv->base, "pwr", 0, 0, 0, 0,
-                                  nvc0_perfmon_pwr);
-       if (ret)
-               return ret;
-
-       /* HUB */
-       ret = nouveau_perfdom_new(&priv->base, "hub", 0, 0x1b0000, 0, 0x200,
-                                  nvc0_perfmon_hub);
-       if (ret)
-               return ret;
-
-       /* GPC */
-       mask  = (1 << nv_rd32(priv, 0x022430)) - 1;
-       mask &= ~nv_rd32(priv, 0x022504);
-       mask &= ~nv_rd32(priv, 0x022584);
-
-       ret = nouveau_perfdom_new(&priv->base, "gpc", mask, 0x180000,
-                                 0x1000, 0x200, nvc0_perfmon_gpc);
-       if (ret)
-               return ret;
-
-       /* PART */
-       mask  = (1 << nv_rd32(priv, 0x022438)) - 1;
-       mask &= ~nv_rd32(priv, 0x022548);
-       mask &= ~nv_rd32(priv, 0x0225c8);
-
-       ret = nouveau_perfdom_new(&priv->base, "part", mask, 0x1a0000,
-                                 0x1000, 0x200, nvc0_perfmon_part);
-       if (ret)
-               return ret;
-
-       nv_engine(priv)->cclass = &nouveau_perfmon_cclass;
-       nv_engine(priv)->sclass =  nouveau_perfmon_sclass;
-       priv->base.last = 7;
-       return 0;
-}
-
-struct nouveau_oclass
-nvc0_perfmon_oclass = {
-       .handle = NV_ENGINE(PERFMON, 0xc0),
-       .ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nvc0_perfmon_ctor,
-               .dtor = _nouveau_perfmon_dtor,
-               .init = _nouveau_perfmon_init,
-               .fini = nvc0_perfmon_fini,
-       },
-};
diff --git a/drivers/gpu/drm/nouveau/core/engine/perfmon/nvc0.h b/drivers/gpu/drm/nouveau/core/engine/perfmon/nvc0.h
deleted file mode 100644 (file)
index f66bca4..0000000
+++ /dev/null
@@ -1,17 +0,0 @@
-#ifndef __NVKM_PM_NVC0_H__
-#define __NVKM_PM_NVC0_H__
-
-#include "priv.h"
-
-struct nvc0_perfmon_priv {
-       struct nouveau_perfmon base;
-};
-
-struct nvc0_perfmon_cntr {
-       struct nouveau_perfctr base;
-};
-
-extern const struct nouveau_funcdom nvc0_perfctr_func;
-int nvc0_perfmon_fini(struct nouveau_object *, bool);
-
-#endif
diff --git a/drivers/gpu/drm/nouveau/core/engine/perfmon/nve0.c b/drivers/gpu/drm/nouveau/core/engine/perfmon/nve0.c
deleted file mode 100644 (file)
index 71d718c..0000000
+++ /dev/null
@@ -1,162 +0,0 @@
-/*
- * Copyright 2013 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 "nvc0.h"
-
-/*******************************************************************************
- * Perfmon object classes
- ******************************************************************************/
-
-/*******************************************************************************
- * PPM context
- ******************************************************************************/
-
-/*******************************************************************************
- * PPM engine/subdev functions
- ******************************************************************************/
-
-static const struct nouveau_specdom
-nve0_perfmon_hub[] = {
-       { 0x60, (const struct nouveau_specsig[]) {
-                       { 0x47, "hub00_user_0" },
-                       {}
-               }, &nvc0_perfctr_func },
-       { 0x40, (const struct nouveau_specsig[]) {
-                       { 0x27, "hub01_user_0" },
-                       {}
-               }, &nvc0_perfctr_func },
-       { 0x60, (const struct nouveau_specsig[]) {
-                       { 0x47, "hub02_user_0" },
-                       {}
-               }, &nvc0_perfctr_func },
-       { 0x60, (const struct nouveau_specsig[]) {
-                       { 0x47, "hub03_user_0" },
-                       {}
-               }, &nvc0_perfctr_func },
-       { 0x40, (const struct nouveau_specsig[]) {
-                       { 0x03, "host_mmio_rd" },
-                       { 0x27, "hub04_user_0" },
-                       {}
-               }, &nvc0_perfctr_func },
-       { 0x60, (const struct nouveau_specsig[]) {
-                       { 0x47, "hub05_user_0" },
-                       {}
-               }, &nvc0_perfctr_func },
-       { 0xc0, (const struct nouveau_specsig[]) {
-                       { 0x74, "host_fb_rd3x" },
-                       { 0x75, "host_fb_rd3x_2" },
-                       { 0xa7, "hub06_user_0" },
-                       {}
-               }, &nvc0_perfctr_func },
-       { 0x60, (const struct nouveau_specsig[]) {
-                       { 0x47, "hub07_user_0" },
-                       {}
-               }, &nvc0_perfctr_func },
-       {}
-};
-
-static const struct nouveau_specdom
-nve0_perfmon_gpc[] = {
-       { 0xe0, (const struct nouveau_specsig[]) {
-                       { 0xc7, "gpc00_user_0" },
-                       {}
-               }, &nvc0_perfctr_func },
-       {}
-};
-
-static const struct nouveau_specdom
-nve0_perfmon_part[] = {
-       { 0x60, (const struct nouveau_specsig[]) {
-                       { 0x47, "part00_user_0" },
-                       {}
-               }, &nvc0_perfctr_func },
-       { 0x60, (const struct nouveau_specsig[]) {
-                       { 0x47, "part01_user_0" },
-                       {}
-               }, &nvc0_perfctr_func },
-       {}
-};
-
-static int
-nve0_perfmon_ctor(struct nouveau_object *parent, struct nouveau_object *engine,
-                 struct nouveau_oclass *oclass, void *data, u32 size,
-                 struct nouveau_object **pobject)
-{
-       struct nvc0_perfmon_priv *priv;
-       u32 mask;
-       int ret;
-
-       ret = nouveau_perfmon_create(parent, engine, oclass, &priv);
-       *pobject = nv_object(priv);
-       if (ret)
-               return ret;
-
-       /* PDAEMON */
-       ret = nouveau_perfdom_new(&priv->base, "pwr", 0, 0, 0, 0,
-                                  nve0_perfmon_pwr);
-       if (ret)
-               return ret;
-
-       /* HUB */
-       ret = nouveau_perfdom_new(&priv->base, "hub", 0, 0x1b0000, 0, 0x200,
-                                  nve0_perfmon_hub);
-       if (ret)
-               return ret;
-
-       /* GPC */
-       mask  = (1 << nv_rd32(priv, 0x022430)) - 1;
-       mask &= ~nv_rd32(priv, 0x022504);
-       mask &= ~nv_rd32(priv, 0x022584);
-
-       ret = nouveau_perfdom_new(&priv->base, "gpc", mask, 0x180000,
-                                 0x1000, 0x200, nve0_perfmon_gpc);
-       if (ret)
-               return ret;
-
-       /* PART */
-       mask  = (1 << nv_rd32(priv, 0x022438)) - 1;
-       mask &= ~nv_rd32(priv, 0x022548);
-       mask &= ~nv_rd32(priv, 0x0225c8);
-
-       ret = nouveau_perfdom_new(&priv->base, "part", mask, 0x1a0000,
-                                 0x1000, 0x200, nve0_perfmon_part);
-       if (ret)
-               return ret;
-
-       nv_engine(priv)->cclass = &nouveau_perfmon_cclass;
-       nv_engine(priv)->sclass =  nouveau_perfmon_sclass;
-       priv->base.last = 7;
-       return 0;
-}
-
-struct nouveau_oclass
-nve0_perfmon_oclass = {
-       .handle = NV_ENGINE(PERFMON, 0xe0),
-       .ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nve0_perfmon_ctor,
-               .dtor = _nouveau_perfmon_dtor,
-               .init = _nouveau_perfmon_init,
-               .fini = nvc0_perfmon_fini,
-       },
-};
diff --git a/drivers/gpu/drm/nouveau/core/engine/perfmon/nvf0.c b/drivers/gpu/drm/nouveau/core/engine/perfmon/nvf0.c
deleted file mode 100644 (file)
index 47256f7..0000000
+++ /dev/null
@@ -1,71 +0,0 @@
-/*
- * Copyright 2013 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 "nvc0.h"
-
-/*******************************************************************************
- * Perfmon object classes
- ******************************************************************************/
-
-/*******************************************************************************
- * PPM context
- ******************************************************************************/
-
-/*******************************************************************************
- * PPM engine/subdev functions
- ******************************************************************************/
-
-static int
-nvf0_perfmon_ctor(struct nouveau_object *parent, struct nouveau_object *engine,
-                 struct nouveau_oclass *oclass, void *data, u32 size,
-                 struct nouveau_object **pobject)
-{
-       struct nvc0_perfmon_priv *priv;
-       int ret;
-
-       ret = nouveau_perfmon_create(parent, engine, oclass, &priv);
-       *pobject = nv_object(priv);
-       if (ret)
-               return ret;
-
-       ret = nouveau_perfdom_new(&priv->base, "pwr", 0, 0, 0, 0,
-                                  nve0_perfmon_pwr);
-       if (ret)
-               return ret;
-
-       nv_engine(priv)->cclass = &nouveau_perfmon_cclass;
-       nv_engine(priv)->sclass =  nouveau_perfmon_sclass;
-       return 0;
-}
-
-struct nouveau_oclass
-nvf0_perfmon_oclass = {
-       .handle = NV_ENGINE(PERFMON, 0xf0),
-       .ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nvf0_perfmon_ctor,
-               .dtor = _nouveau_perfmon_dtor,
-               .init = _nouveau_perfmon_init,
-               .fini = nvc0_perfmon_fini,
-       },
-};
diff --git a/drivers/gpu/drm/nouveau/core/engine/perfmon/priv.h b/drivers/gpu/drm/nouveau/core/engine/perfmon/priv.h
deleted file mode 100644 (file)
index 0ac8714..0000000
+++ /dev/null
@@ -1,91 +0,0 @@
-#ifndef __NVKM_PERFMON_PRIV_H__
-#define __NVKM_PERFMON_PRIV_H__
-
-#include <engine/perfmon.h>
-
-struct nouveau_perfctr {
-       struct nouveau_object base;
-       struct list_head head;
-       struct nouveau_perfsig *signal[4];
-       int slot;
-       u32 logic_op;
-       u32 clk;
-       u32 ctr;
-};
-
-extern struct nouveau_oclass nouveau_perfmon_sclass[];
-
-struct nouveau_perfctx {
-       struct nouveau_engctx base;
-};
-
-extern struct nouveau_oclass nouveau_perfmon_cclass;
-
-struct nouveau_specsig {
-       u8 signal;
-       const char *name;
-};
-
-struct nouveau_perfsig {
-       const char *name;
-};
-
-struct nouveau_perfdom;
-struct nouveau_perfctr *
-nouveau_perfsig_wrap(struct nouveau_perfmon *, const char *,
-                    struct nouveau_perfdom **);
-
-struct nouveau_specdom {
-       u16 signal_nr;
-       const struct nouveau_specsig *signal;
-       const struct nouveau_funcdom *func;
-};
-
-extern const struct nouveau_specdom nva3_perfmon_pwr[];
-extern const struct nouveau_specdom nvc0_perfmon_pwr[];
-extern const struct nouveau_specdom nve0_perfmon_pwr[];
-
-struct nouveau_perfdom {
-       struct list_head head;
-       struct list_head list;
-       const struct nouveau_funcdom *func;
-       char name[32];
-       u32 addr;
-       u8  quad;
-       u32 signal_nr;
-       struct nouveau_perfsig signal[];
-};
-
-struct nouveau_funcdom {
-       void (*init)(struct nouveau_perfmon *, struct nouveau_perfdom *,
-                    struct nouveau_perfctr *);
-       void (*read)(struct nouveau_perfmon *, struct nouveau_perfdom *,
-                    struct nouveau_perfctr *);
-       void (*next)(struct nouveau_perfmon *, struct nouveau_perfdom *);
-};
-
-int nouveau_perfdom_new(struct nouveau_perfmon *, const char *, u32,
-                       u32, u32, u32, const struct nouveau_specdom *);
-
-#define nouveau_perfmon_create(p,e,o,d)                                        \
-       nouveau_perfmon_create_((p), (e), (o), sizeof(**d), (void **)d)
-#define nouveau_perfmon_dtor(p) ({                                             \
-       struct nouveau_perfmon *c = (p);                                       \
-       _nouveau_perfmon_dtor(nv_object(c));                                   \
-})
-#define nouveau_perfmon_init(p) ({                                             \
-       struct nouveau_perfmon *c = (p);                                       \
-       _nouveau_perfmon_init(nv_object(c));                                   \
-})
-#define nouveau_perfmon_fini(p,s) ({                                           \
-       struct nouveau_perfmon *c = (p);                                       \
-       _nouveau_perfmon_fini(nv_object(c), (s));                              \
-})
-
-int nouveau_perfmon_create_(struct nouveau_object *, struct nouveau_object *,
-                           struct nouveau_oclass *, int, void **);
-void _nouveau_perfmon_dtor(struct nouveau_object *);
-int  _nouveau_perfmon_init(struct nouveau_object *);
-int  _nouveau_perfmon_fini(struct nouveau_object *, bool);
-
-#endif
diff --git a/drivers/gpu/drm/nouveau/core/engine/ppp/nv98.c b/drivers/gpu/drm/nouveau/core/engine/ppp/nv98.c
deleted file mode 100644 (file)
index 13bf31c..0000000
+++ /dev/null
@@ -1,110 +0,0 @@
-/*
- * Copyright 2012 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, Maarten Lankhorst, Ilia Mirkin
- */
-
-#include <engine/falcon.h>
-#include <engine/ppp.h>
-
-struct nv98_ppp_priv {
-       struct nouveau_falcon base;
-};
-
-/*******************************************************************************
- * PPP object classes
- ******************************************************************************/
-
-static struct nouveau_oclass
-nv98_ppp_sclass[] = {
-       { 0x88b3, &nouveau_object_ofuncs },
-       { 0x85b3, &nouveau_object_ofuncs },
-       {},
-};
-
-/*******************************************************************************
- * PPPP context
- ******************************************************************************/
-
-static struct nouveau_oclass
-nv98_ppp_cclass = {
-       .handle = NV_ENGCTX(PPP, 0x98),
-       .ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = _nouveau_falcon_context_ctor,
-               .dtor = _nouveau_falcon_context_dtor,
-               .init = _nouveau_falcon_context_init,
-               .fini = _nouveau_falcon_context_fini,
-               .rd32 = _nouveau_falcon_context_rd32,
-               .wr32 = _nouveau_falcon_context_wr32,
-       },
-};
-
-/*******************************************************************************
- * PPPP engine/subdev functions
- ******************************************************************************/
-
-static int
-nv98_ppp_init(struct nouveau_object *object)
-{
-       struct nv98_ppp_priv *priv = (void *)object;
-       int ret;
-
-       ret = nouveau_falcon_init(&priv->base);
-       if (ret)
-               return ret;
-
-       nv_wr32(priv, 0x086010, 0x0000ffd2);
-       nv_wr32(priv, 0x08601c, 0x0000fff2);
-       return 0;
-}
-
-static int
-nv98_ppp_ctor(struct nouveau_object *parent, struct nouveau_object *engine,
-             struct nouveau_oclass *oclass, void *data, u32 size,
-             struct nouveau_object **pobject)
-{
-       struct nv98_ppp_priv *priv;
-       int ret;
-
-       ret = nouveau_falcon_create(parent, engine, oclass, 0x086000, true,
-                                   "PPPP", "ppp", &priv);
-       *pobject = nv_object(priv);
-       if (ret)
-               return ret;
-
-       nv_subdev(priv)->unit = 0x00400002;
-       nv_engine(priv)->cclass = &nv98_ppp_cclass;
-       nv_engine(priv)->sclass = nv98_ppp_sclass;
-       return 0;
-}
-
-struct nouveau_oclass
-nv98_ppp_oclass = {
-       .handle = NV_ENGINE(PPP, 0x98),
-       .ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nv98_ppp_ctor,
-               .dtor = _nouveau_falcon_dtor,
-               .init = nv98_ppp_init,
-               .fini = _nouveau_falcon_fini,
-               .rd32 = _nouveau_falcon_rd32,
-               .wr32 = _nouveau_falcon_wr32,
-       },
-};
diff --git a/drivers/gpu/drm/nouveau/core/engine/ppp/nvc0.c b/drivers/gpu/drm/nouveau/core/engine/ppp/nvc0.c
deleted file mode 100644 (file)
index 73719aa..0000000
+++ /dev/null
@@ -1,110 +0,0 @@
-/*
- * Copyright 2012 Maarten Lankhorst
- *
- * 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: Maarten Lankhorst
- */
-
-#include <engine/falcon.h>
-#include <engine/ppp.h>
-
-struct nvc0_ppp_priv {
-       struct nouveau_falcon base;
-};
-
-/*******************************************************************************
- * PPP object classes
- ******************************************************************************/
-
-static struct nouveau_oclass
-nvc0_ppp_sclass[] = {
-       { 0x90b3, &nouveau_object_ofuncs },
-       {},
-};
-
-/*******************************************************************************
- * PPPP context
- ******************************************************************************/
-
-static struct nouveau_oclass
-nvc0_ppp_cclass = {
-       .handle = NV_ENGCTX(PPP, 0xc0),
-       .ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = _nouveau_falcon_context_ctor,
-               .dtor = _nouveau_falcon_context_dtor,
-               .init = _nouveau_falcon_context_init,
-               .fini = _nouveau_falcon_context_fini,
-               .rd32 = _nouveau_falcon_context_rd32,
-               .wr32 = _nouveau_falcon_context_wr32,
-       },
-};
-
-/*******************************************************************************
- * PPPP engine/subdev functions
- ******************************************************************************/
-
-static int
-nvc0_ppp_init(struct nouveau_object *object)
-{
-       struct nvc0_ppp_priv *priv = (void *)object;
-       int ret;
-
-       ret = nouveau_falcon_init(&priv->base);
-       if (ret)
-               return ret;
-
-       nv_wr32(priv, 0x086010, 0x0000fff2);
-       nv_wr32(priv, 0x08601c, 0x0000fff2);
-       return 0;
-}
-
-static int
-nvc0_ppp_ctor(struct nouveau_object *parent, struct nouveau_object *engine,
-             struct nouveau_oclass *oclass, void *data, u32 size,
-             struct nouveau_object **pobject)
-{
-       struct nvc0_ppp_priv *priv;
-       int ret;
-
-       ret = nouveau_falcon_create(parent, engine, oclass, 0x086000, true,
-                                   "PPPP", "ppp", &priv);
-       *pobject = nv_object(priv);
-       if (ret)
-               return ret;
-
-       nv_subdev(priv)->unit = 0x00000002;
-       nv_subdev(priv)->intr = nouveau_falcon_intr;
-       nv_engine(priv)->cclass = &nvc0_ppp_cclass;
-       nv_engine(priv)->sclass = nvc0_ppp_sclass;
-       return 0;
-}
-
-struct nouveau_oclass
-nvc0_ppp_oclass = {
-       .handle = NV_ENGINE(PPP, 0xc0),
-       .ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nvc0_ppp_ctor,
-               .dtor = _nouveau_falcon_dtor,
-               .init = nvc0_ppp_init,
-               .fini = _nouveau_falcon_fini,
-               .rd32 = _nouveau_falcon_rd32,
-               .wr32 = _nouveau_falcon_wr32,
-       },
-};
diff --git a/drivers/gpu/drm/nouveau/core/engine/software/nv04.c b/drivers/gpu/drm/nouveau/core/engine/software/nv04.c
deleted file mode 100644 (file)
index 64df15c..0000000
+++ /dev/null
@@ -1,146 +0,0 @@
-/*
- * Copyright 2012 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 <core/os.h>
-#include <core/engctx.h>
-
-#include <engine/software.h>
-#include <engine/fifo.h>
-
-struct nv04_software_priv {
-       struct nouveau_software base;
-};
-
-struct nv04_software_chan {
-       struct nouveau_software_chan base;
-};
-
-/*******************************************************************************
- * software object classes
- ******************************************************************************/
-
-static int
-nv04_software_set_ref(struct nouveau_object *object, u32 mthd,
-                     void *data, u32 size)
-{
-       struct nouveau_object *channel = (void *)nv_engctx(object->parent);
-       struct nouveau_fifo_chan *fifo = (void *)channel->parent;
-       atomic_set(&fifo->refcnt, *(u32*)data);
-       return 0;
-}
-
-static int
-nv04_software_flip(struct nouveau_object *object, u32 mthd,
-                  void *args, u32 size)
-{
-       struct nv04_software_chan *chan = (void *)nv_engctx(object->parent);
-       if (chan->base.flip)
-               return chan->base.flip(chan->base.flip_data);
-       return -EINVAL;
-}
-
-static struct nouveau_omthds
-nv04_software_omthds[] = {
-       { 0x0150, 0x0150, nv04_software_set_ref },
-       { 0x0500, 0x0500, nv04_software_flip },
-       {}
-};
-
-static struct nouveau_oclass
-nv04_software_sclass[] = {
-       { 0x006e, &nouveau_object_ofuncs, nv04_software_omthds },
-       {}
-};
-
-/*******************************************************************************
- * software context
- ******************************************************************************/
-
-static int
-nv04_software_context_ctor(struct nouveau_object *parent,
-                     struct nouveau_object *engine,
-                     struct nouveau_oclass *oclass, void *data, u32 size,
-                     struct nouveau_object **pobject)
-{
-       struct nv04_software_chan *chan;
-       int ret;
-
-       ret = nouveau_software_context_create(parent, engine, oclass, &chan);
-       *pobject = nv_object(chan);
-       if (ret)
-               return ret;
-
-       return 0;
-}
-
-static struct nouveau_oclass
-nv04_software_cclass = {
-       .handle = NV_ENGCTX(SW, 0x04),
-       .ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nv04_software_context_ctor,
-               .dtor = _nouveau_software_context_dtor,
-               .init = _nouveau_software_context_init,
-               .fini = _nouveau_software_context_fini,
-       },
-};
-
-/*******************************************************************************
- * software engine/subdev functions
- ******************************************************************************/
-
-void
-nv04_software_intr(struct nouveau_subdev *subdev)
-{
-       nv_mask(subdev, 0x000100, 0x80000000, 0x00000000);
-}
-
-static int
-nv04_software_ctor(struct nouveau_object *parent, struct nouveau_object *engine,
-             struct nouveau_oclass *oclass, void *data, u32 size,
-             struct nouveau_object **pobject)
-{
-       struct nv04_software_priv *priv;
-       int ret;
-
-       ret = nouveau_software_create(parent, engine, oclass, &priv);
-       *pobject = nv_object(priv);
-       if (ret)
-               return ret;
-
-       nv_engine(priv)->cclass = &nv04_software_cclass;
-       nv_engine(priv)->sclass = nv04_software_sclass;
-       nv_subdev(priv)->intr = nv04_software_intr;
-       return 0;
-}
-
-struct nouveau_oclass *
-nv04_software_oclass = &(struct nouveau_oclass) {
-       .handle = NV_ENGINE(SW, 0x04),
-       .ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nv04_software_ctor,
-               .dtor = _nouveau_software_dtor,
-               .init = _nouveau_software_init,
-               .fini = _nouveau_software_fini,
-       },
-};
diff --git a/drivers/gpu/drm/nouveau/core/engine/software/nv10.c b/drivers/gpu/drm/nouveau/core/engine/software/nv10.c
deleted file mode 100644 (file)
index f54a225..0000000
+++ /dev/null
@@ -1,128 +0,0 @@
-/*
- * Copyright 2012 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 <core/os.h>
-#include <core/engctx.h>
-
-#include <engine/software.h>
-
-struct nv10_software_priv {
-       struct nouveau_software base;
-};
-
-struct nv10_software_chan {
-       struct nouveau_software_chan base;
-};
-
-/*******************************************************************************
- * software object classes
- ******************************************************************************/
-
-static int
-nv10_software_flip(struct nouveau_object *object, u32 mthd,
-                  void *args, u32 size)
-{
-       struct nv10_software_chan *chan = (void *)nv_engctx(object->parent);
-       if (chan->base.flip)
-               return chan->base.flip(chan->base.flip_data);
-       return -EINVAL;
-}
-
-static struct nouveau_omthds
-nv10_software_omthds[] = {
-       { 0x0500, 0x0500, nv10_software_flip },
-       {}
-};
-
-static struct nouveau_oclass
-nv10_software_sclass[] = {
-       { 0x016e, &nouveau_object_ofuncs, nv10_software_omthds },
-       {}
-};
-
-/*******************************************************************************
- * software context
- ******************************************************************************/
-
-static int
-nv10_software_context_ctor(struct nouveau_object *parent,
-                     struct nouveau_object *engine,
-                     struct nouveau_oclass *oclass, void *data, u32 size,
-                     struct nouveau_object **pobject)
-{
-       struct nv10_software_chan *chan;
-       int ret;
-
-       ret = nouveau_software_context_create(parent, engine, oclass, &chan);
-       *pobject = nv_object(chan);
-       if (ret)
-               return ret;
-
-       return 0;
-}
-
-static struct nouveau_oclass
-nv10_software_cclass = {
-       .handle = NV_ENGCTX(SW, 0x04),
-       .ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nv10_software_context_ctor,
-               .dtor = _nouveau_software_context_dtor,
-               .init = _nouveau_software_context_init,
-               .fini = _nouveau_software_context_fini,
-       },
-};
-
-/*******************************************************************************
- * software engine/subdev functions
- ******************************************************************************/
-
-static int
-nv10_software_ctor(struct nouveau_object *parent, struct nouveau_object *engine,
-             struct nouveau_oclass *oclass, void *data, u32 size,
-             struct nouveau_object **pobject)
-{
-       struct nv10_software_priv *priv;
-       int ret;
-
-       ret = nouveau_software_create(parent, engine, oclass, &priv);
-       *pobject = nv_object(priv);
-       if (ret)
-               return ret;
-
-       nv_engine(priv)->cclass = &nv10_software_cclass;
-       nv_engine(priv)->sclass = nv10_software_sclass;
-       nv_subdev(priv)->intr = nv04_software_intr;
-       return 0;
-}
-
-struct nouveau_oclass *
-nv10_software_oclass = &(struct nouveau_oclass) {
-       .handle = NV_ENGINE(SW, 0x10),
-       .ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nv10_software_ctor,
-               .dtor = _nouveau_software_dtor,
-               .init = _nouveau_software_init,
-               .fini = _nouveau_software_fini,
-       },
-};
diff --git a/drivers/gpu/drm/nouveau/core/engine/software/nv50.c b/drivers/gpu/drm/nouveau/core/engine/software/nv50.c
deleted file mode 100644 (file)
index a0fec20..0000000
+++ /dev/null
@@ -1,241 +0,0 @@
-/*
- * Copyright 2012 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 <core/os.h>
-#include <core/engctx.h>
-#include <core/namedb.h>
-#include <core/handle.h>
-#include <core/gpuobj.h>
-#include <core/event.h>
-#include <nvif/event.h>
-
-#include <subdev/bar.h>
-
-#include <engine/disp.h>
-
-#include "nv50.h"
-
-/*******************************************************************************
- * software object classes
- ******************************************************************************/
-
-static int
-nv50_software_mthd_dma_vblsem(struct nouveau_object *object, u32 mthd,
-                             void *args, u32 size)
-{
-       struct nv50_software_chan *chan = (void *)nv_engctx(object->parent);
-       struct nouveau_fifo_chan *fifo = (void *)nv_object(chan)->parent;
-       struct nouveau_handle *handle;
-       int ret = -EINVAL;
-
-       handle = nouveau_namedb_get(nv_namedb(fifo), *(u32 *)args);
-       if (!handle)
-               return -ENOENT;
-
-       if (nv_iclass(handle->object, NV_GPUOBJ_CLASS)) {
-               struct nouveau_gpuobj *gpuobj = nv_gpuobj(handle->object);
-               chan->vblank.ctxdma = gpuobj->node->offset >> 4;
-               ret = 0;
-       }
-       nouveau_namedb_put(handle);
-       return ret;
-}
-
-static int
-nv50_software_mthd_vblsem_offset(struct nouveau_object *object, u32 mthd,
-                                void *args, u32 size)
-{
-       struct nv50_software_chan *chan = (void *)nv_engctx(object->parent);
-       chan->vblank.offset = *(u32 *)args;
-       return 0;
-}
-
-int
-nv50_software_mthd_vblsem_value(struct nouveau_object *object, u32 mthd,
-                               void *args, u32 size)
-{
-       struct nv50_software_chan *chan = (void *)nv_engctx(object->parent);
-       chan->vblank.value = *(u32 *)args;
-       return 0;
-}
-
-int
-nv50_software_mthd_vblsem_release(struct nouveau_object *object, u32 mthd,
-                                 void *args, u32 size)
-{
-       struct nv50_software_chan *chan = (void *)nv_engctx(object->parent);
-       u32 head = *(u32 *)args;
-       if (head >= nouveau_disp(chan)->vblank.index_nr)
-               return -EINVAL;
-
-       nvkm_notify_get(&chan->vblank.notify[head]);
-       return 0;
-}
-
-int
-nv50_software_mthd_flip(struct nouveau_object *object, u32 mthd,
-                       void *args, u32 size)
-{
-       struct nv50_software_chan *chan = (void *)nv_engctx(object->parent);
-       if (chan->base.flip)
-               return chan->base.flip(chan->base.flip_data);
-       return -EINVAL;
-}
-
-static struct nouveau_omthds
-nv50_software_omthds[] = {
-       { 0x018c, 0x018c, nv50_software_mthd_dma_vblsem },
-       { 0x0400, 0x0400, nv50_software_mthd_vblsem_offset },
-       { 0x0404, 0x0404, nv50_software_mthd_vblsem_value },
-       { 0x0408, 0x0408, nv50_software_mthd_vblsem_release },
-       { 0x0500, 0x0500, nv50_software_mthd_flip },
-       {}
-};
-
-static struct nouveau_oclass
-nv50_software_sclass[] = {
-       { 0x506e, &nouveau_object_ofuncs, nv50_software_omthds },
-       {}
-};
-
-/*******************************************************************************
- * software context
- ******************************************************************************/
-
-static int
-nv50_software_vblsem_release(struct nvkm_notify *notify)
-{
-       struct nv50_software_chan *chan =
-               container_of(notify, typeof(*chan), vblank.notify[notify->index]);
-       struct nv50_software_priv *priv = (void *)nv_object(chan)->engine;
-       struct nouveau_bar *bar = nouveau_bar(priv);
-
-       nv_wr32(priv, 0x001704, chan->vblank.channel);
-       nv_wr32(priv, 0x001710, 0x80000000 | chan->vblank.ctxdma);
-       bar->flush(bar);
-
-       if (nv_device(priv)->chipset == 0x50) {
-               nv_wr32(priv, 0x001570, chan->vblank.offset);
-               nv_wr32(priv, 0x001574, chan->vblank.value);
-       } else {
-               nv_wr32(priv, 0x060010, chan->vblank.offset);
-               nv_wr32(priv, 0x060014, chan->vblank.value);
-       }
-
-       return NVKM_NOTIFY_DROP;
-}
-
-void
-nv50_software_context_dtor(struct nouveau_object *object)
-{
-       struct nv50_software_chan *chan = (void *)object;
-       int i;
-
-       for (i = 0; i < ARRAY_SIZE(chan->vblank.notify); i++)
-               nvkm_notify_fini(&chan->vblank.notify[i]);
-
-       nouveau_software_context_destroy(&chan->base);
-}
-
-int
-nv50_software_context_ctor(struct nouveau_object *parent,
-                          struct nouveau_object *engine,
-                          struct nouveau_oclass *oclass, void *data, u32 size,
-                          struct nouveau_object **pobject)
-{
-       struct nouveau_disp *pdisp = nouveau_disp(parent);
-       struct nv50_software_cclass *pclass = (void *)oclass;
-       struct nv50_software_chan *chan;
-       int ret, i;
-
-       ret = nouveau_software_context_create(parent, engine, oclass, &chan);
-       *pobject = nv_object(chan);
-       if (ret)
-               return ret;
-
-       for (i = 0; pdisp && i < pdisp->vblank.index_nr; i++) {
-               ret = nvkm_notify_init(NULL, &pdisp->vblank, pclass->vblank,
-                                      false,
-                                      &(struct nvif_notify_head_req_v0) {
-                                       .head = i,
-                                      },
-                                      sizeof(struct nvif_notify_head_req_v0),
-                                      sizeof(struct nvif_notify_head_rep_v0),
-                                      &chan->vblank.notify[i]);
-               if (ret)
-                       return ret;
-       }
-
-       chan->vblank.channel = nv_gpuobj(parent->parent)->addr >> 12;
-       return 0;
-}
-
-static struct nv50_software_cclass
-nv50_software_cclass = {
-       .base.handle = NV_ENGCTX(SW, 0x50),
-       .base.ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nv50_software_context_ctor,
-               .dtor = nv50_software_context_dtor,
-               .init = _nouveau_software_context_init,
-               .fini = _nouveau_software_context_fini,
-       },
-       .vblank = nv50_software_vblsem_release,
-};
-
-/*******************************************************************************
- * software engine/subdev functions
- ******************************************************************************/
-
-int
-nv50_software_ctor(struct nouveau_object *parent, struct nouveau_object *engine,
-                  struct nouveau_oclass *oclass, void *data, u32 size,
-                  struct nouveau_object **pobject)
-{
-       struct nv50_software_oclass *pclass = (void *)oclass;
-       struct nv50_software_priv *priv;
-       int ret;
-
-       ret = nouveau_software_create(parent, engine, oclass, &priv);
-       *pobject = nv_object(priv);
-       if (ret)
-               return ret;
-
-       nv_engine(priv)->cclass = pclass->cclass;
-       nv_engine(priv)->sclass = pclass->sclass;
-       nv_subdev(priv)->intr = nv04_software_intr;
-       return 0;
-}
-
-struct nouveau_oclass *
-nv50_software_oclass = &(struct nv50_software_oclass) {
-       .base.handle = NV_ENGINE(SW, 0x50),
-       .base.ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nv50_software_ctor,
-               .dtor = _nouveau_software_dtor,
-               .init = _nouveau_software_init,
-               .fini = _nouveau_software_fini,
-       },
-       .cclass = &nv50_software_cclass.base,
-       .sclass =  nv50_software_sclass,
-}.base;
diff --git a/drivers/gpu/drm/nouveau/core/engine/software/nv50.h b/drivers/gpu/drm/nouveau/core/engine/software/nv50.h
deleted file mode 100644 (file)
index 41542e7..0000000
+++ /dev/null
@@ -1,46 +0,0 @@
-#ifndef __NVKM_SW_NV50_H__
-#define __NVKM_SW_NV50_H__
-
-#include <engine/software.h>
-
-struct nv50_software_oclass {
-       struct nouveau_oclass base;
-       struct nouveau_oclass *cclass;
-       struct nouveau_oclass *sclass;
-};
-
-struct nv50_software_priv {
-       struct nouveau_software base;
-};
-
-int  nv50_software_ctor(struct nouveau_object *, struct nouveau_object *,
-                       struct nouveau_oclass *, void *, u32,
-                       struct nouveau_object **);
-
-struct nv50_software_cclass {
-       struct nouveau_oclass base;
-       int (*vblank)(struct nvkm_notify *);
-};
-
-struct nv50_software_chan {
-       struct nouveau_software_chan base;
-       struct {
-               struct nvkm_notify notify[4];
-               u32 channel;
-               u32 ctxdma;
-               u64 offset;
-               u32 value;
-       } vblank;
-};
-
-int  nv50_software_context_ctor(struct nouveau_object *,
-                               struct nouveau_object *,
-                               struct nouveau_oclass *, void *, u32,
-                               struct nouveau_object **);
-void nv50_software_context_dtor(struct nouveau_object *);
-
-int nv50_software_mthd_vblsem_value(struct nouveau_object *, u32, void *, u32);
-int nv50_software_mthd_vblsem_release(struct nouveau_object *, u32, void *, u32);
-int nv50_software_mthd_flip(struct nouveau_object *, u32, void *, u32);
-
-#endif
diff --git a/drivers/gpu/drm/nouveau/core/engine/software/nvc0.c b/drivers/gpu/drm/nouveau/core/engine/software/nvc0.c
deleted file mode 100644 (file)
index 6af370d..0000000
+++ /dev/null
@@ -1,149 +0,0 @@
-/*
- * Copyright 2012 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 <core/os.h>
-#include <core/engctx.h>
-#include <core/event.h>
-
-#include <subdev/bar.h>
-
-#include <engine/software.h>
-#include <engine/disp.h>
-
-#include "nv50.h"
-
-/*******************************************************************************
- * software object classes
- ******************************************************************************/
-
-static int
-nvc0_software_mthd_vblsem_offset(struct nouveau_object *object, u32 mthd,
-                                void *args, u32 size)
-{
-       struct nv50_software_chan *chan = (void *)nv_engctx(object->parent);
-       u64 data = *(u32 *)args;
-       if (mthd == 0x0400) {
-               chan->vblank.offset &= 0x00ffffffffULL;
-               chan->vblank.offset |= data << 32;
-       } else {
-               chan->vblank.offset &= 0xff00000000ULL;
-               chan->vblank.offset |= data;
-       }
-       return 0;
-}
-
-static int
-nvc0_software_mthd_mp_control(struct nouveau_object *object, u32 mthd,
-                              void *args, u32 size)
-{
-       struct nv50_software_chan *chan = (void *)nv_engctx(object->parent);
-       struct nv50_software_priv *priv = (void *)nv_object(chan)->engine;
-       u32 data = *(u32 *)args;
-
-       switch (mthd) {
-       case 0x600:
-               nv_wr32(priv, 0x419e00, data); /* MP.PM_UNK000 */
-               break;
-       case 0x644:
-               if (data & ~0x1ffffe)
-                       return -EINVAL;
-               nv_wr32(priv, 0x419e44, data); /* MP.TRAP_WARP_ERROR_EN */
-               break;
-       case 0x6ac:
-               nv_wr32(priv, 0x419eac, data); /* MP.PM_UNK0AC */
-               break;
-       default:
-               return -EINVAL;
-       }
-       return 0;
-}
-
-static struct nouveau_omthds
-nvc0_software_omthds[] = {
-       { 0x0400, 0x0400, nvc0_software_mthd_vblsem_offset },
-       { 0x0404, 0x0404, nvc0_software_mthd_vblsem_offset },
-       { 0x0408, 0x0408, nv50_software_mthd_vblsem_value },
-       { 0x040c, 0x040c, nv50_software_mthd_vblsem_release },
-       { 0x0500, 0x0500, nv50_software_mthd_flip },
-       { 0x0600, 0x0600, nvc0_software_mthd_mp_control },
-       { 0x0644, 0x0644, nvc0_software_mthd_mp_control },
-       { 0x06ac, 0x06ac, nvc0_software_mthd_mp_control },
-       {}
-};
-
-static struct nouveau_oclass
-nvc0_software_sclass[] = {
-       { 0x906e, &nouveau_object_ofuncs, nvc0_software_omthds },
-       {}
-};
-
-/*******************************************************************************
- * software context
- ******************************************************************************/
-
-static int
-nvc0_software_vblsem_release(struct nvkm_notify *notify)
-{
-       struct nv50_software_chan *chan =
-               container_of(notify, typeof(*chan), vblank.notify[notify->index]);
-       struct nv50_software_priv *priv = (void *)nv_object(chan)->engine;
-       struct nouveau_bar *bar = nouveau_bar(priv);
-
-       nv_wr32(priv, 0x001718, 0x80000000 | chan->vblank.channel);
-       bar->flush(bar);
-       nv_wr32(priv, 0x06000c, upper_32_bits(chan->vblank.offset));
-       nv_wr32(priv, 0x060010, lower_32_bits(chan->vblank.offset));
-       nv_wr32(priv, 0x060014, chan->vblank.value);
-
-       return NVKM_NOTIFY_DROP;
-}
-
-static struct nv50_software_cclass
-nvc0_software_cclass = {
-       .base.handle = NV_ENGCTX(SW, 0xc0),
-       .base.ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nv50_software_context_ctor,
-               .dtor = nv50_software_context_dtor,
-               .init = _nouveau_software_context_init,
-               .fini = _nouveau_software_context_fini,
-       },
-       .vblank = nvc0_software_vblsem_release,
-};
-
-/*******************************************************************************
- * software engine/subdev functions
- ******************************************************************************/
-
-struct nouveau_oclass *
-nvc0_software_oclass = &(struct nv50_software_oclass) {
-       .base.handle = NV_ENGINE(SW, 0xc0),
-       .base.ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nv50_software_ctor,
-               .dtor = _nouveau_software_dtor,
-               .init = _nouveau_software_init,
-               .fini = _nouveau_software_fini,
-       },
-       .cclass = &nvc0_software_cclass.base,
-       .sclass =  nvc0_software_sclass,
-}.base;
diff --git a/drivers/gpu/drm/nouveau/core/engine/vp/nv84.c b/drivers/gpu/drm/nouveau/core/engine/vp/nv84.c
deleted file mode 100644 (file)
index fd6272b..0000000
+++ /dev/null
@@ -1,92 +0,0 @@
-/*
- * Copyright 2012 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, Ilia Mirkin
- */
-
-#include <engine/xtensa.h>
-#include <engine/vp.h>
-
-/*******************************************************************************
- * VP object classes
- ******************************************************************************/
-
-static struct nouveau_oclass
-nv84_vp_sclass[] = {
-       { 0x7476, &nouveau_object_ofuncs },
-       {},
-};
-
-/*******************************************************************************
- * PVP context
- ******************************************************************************/
-
-static struct nouveau_oclass
-nv84_vp_cclass = {
-       .handle = NV_ENGCTX(VP, 0x84),
-       .ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = _nouveau_xtensa_engctx_ctor,
-               .dtor = _nouveau_engctx_dtor,
-               .init = _nouveau_engctx_init,
-               .fini = _nouveau_engctx_fini,
-               .rd32 = _nouveau_engctx_rd32,
-               .wr32 = _nouveau_engctx_wr32,
-       },
-};
-
-/*******************************************************************************
- * PVP engine/subdev functions
- ******************************************************************************/
-
-static int
-nv84_vp_ctor(struct nouveau_object *parent, struct nouveau_object *engine,
-            struct nouveau_oclass *oclass, void *data, u32 size,
-            struct nouveau_object **pobject)
-{
-       struct nouveau_xtensa *priv;
-       int ret;
-
-       ret = nouveau_xtensa_create(parent, engine, oclass, 0xf000, true,
-                                   "PVP", "vp", &priv);
-       *pobject = nv_object(priv);
-       if (ret)
-               return ret;
-
-       nv_subdev(priv)->unit = 0x01020000;
-       nv_engine(priv)->cclass = &nv84_vp_cclass;
-       nv_engine(priv)->sclass = nv84_vp_sclass;
-       priv->fifo_val = 0x111;
-       priv->unkd28 = 0x9c544;
-       return 0;
-}
-
-struct nouveau_oclass
-nv84_vp_oclass = {
-       .handle = NV_ENGINE(VP, 0x84),
-       .ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nv84_vp_ctor,
-               .dtor = _nouveau_xtensa_dtor,
-               .init = _nouveau_xtensa_init,
-               .fini = _nouveau_xtensa_fini,
-               .rd32 = _nouveau_xtensa_rd32,
-               .wr32 = _nouveau_xtensa_wr32,
-       },
-};
diff --git a/drivers/gpu/drm/nouveau/core/engine/vp/nv98.c b/drivers/gpu/drm/nouveau/core/engine/vp/nv98.c
deleted file mode 100644 (file)
index fc9ae0f..0000000
+++ /dev/null
@@ -1,110 +0,0 @@
-/*
- * Copyright 2012 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, Maarten Lankhorst, Ilia Mirkin
- */
-
-#include <engine/falcon.h>
-#include <engine/vp.h>
-
-struct nv98_vp_priv {
-       struct nouveau_falcon base;
-};
-
-/*******************************************************************************
- * VP object classes
- ******************************************************************************/
-
-static struct nouveau_oclass
-nv98_vp_sclass[] = {
-       { 0x88b2, &nouveau_object_ofuncs },
-       { 0x85b2, &nouveau_object_ofuncs },
-       {},
-};
-
-/*******************************************************************************
- * PVP context
- ******************************************************************************/
-
-static struct nouveau_oclass
-nv98_vp_cclass = {
-       .handle = NV_ENGCTX(VP, 0x98),
-       .ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = _nouveau_falcon_context_ctor,
-               .dtor = _nouveau_falcon_context_dtor,
-               .init = _nouveau_falcon_context_init,
-               .fini = _nouveau_falcon_context_fini,
-               .rd32 = _nouveau_falcon_context_rd32,
-               .wr32 = _nouveau_falcon_context_wr32,
-       },
-};
-
-/*******************************************************************************
- * PVP engine/subdev functions
- ******************************************************************************/
-
-static int
-nv98_vp_init(struct nouveau_object *object)
-{
-       struct nv98_vp_priv *priv = (void *)object;
-       int ret;
-
-       ret = nouveau_falcon_init(&priv->base);
-       if (ret)
-               return ret;
-
-       nv_wr32(priv, 0x085010, 0x0000ffd2);
-       nv_wr32(priv, 0x08501c, 0x0000fff2);
-       return 0;
-}
-
-static int
-nv98_vp_ctor(struct nouveau_object *parent, struct nouveau_object *engine,
-            struct nouveau_oclass *oclass, void *data, u32 size,
-            struct nouveau_object **pobject)
-{
-       struct nv98_vp_priv *priv;
-       int ret;
-
-       ret = nouveau_falcon_create(parent, engine, oclass, 0x085000, true,
-                                   "PVP", "vp", &priv);
-       *pobject = nv_object(priv);
-       if (ret)
-               return ret;
-
-       nv_subdev(priv)->unit = 0x01020000;
-       nv_engine(priv)->cclass = &nv98_vp_cclass;
-       nv_engine(priv)->sclass = nv98_vp_sclass;
-       return 0;
-}
-
-struct nouveau_oclass
-nv98_vp_oclass = {
-       .handle = NV_ENGINE(VP, 0x98),
-       .ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nv98_vp_ctor,
-               .dtor = _nouveau_falcon_dtor,
-               .init = nv98_vp_init,
-               .fini = _nouveau_falcon_fini,
-               .rd32 = _nouveau_falcon_rd32,
-               .wr32 = _nouveau_falcon_wr32,
-       },
-};
diff --git a/drivers/gpu/drm/nouveau/core/engine/vp/nvc0.c b/drivers/gpu/drm/nouveau/core/engine/vp/nvc0.c
deleted file mode 100644 (file)
index ac1f62a..0000000
+++ /dev/null
@@ -1,110 +0,0 @@
-/*
- * Copyright 2012 Maarten Lankhorst
- *
- * 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: Maarten Lankhorst
- */
-
-#include <engine/falcon.h>
-#include <engine/vp.h>
-
-struct nvc0_vp_priv {
-       struct nouveau_falcon base;
-};
-
-/*******************************************************************************
- * VP object classes
- ******************************************************************************/
-
-static struct nouveau_oclass
-nvc0_vp_sclass[] = {
-       { 0x90b2, &nouveau_object_ofuncs },
-       {},
-};
-
-/*******************************************************************************
- * PVP context
- ******************************************************************************/
-
-static struct nouveau_oclass
-nvc0_vp_cclass = {
-       .handle = NV_ENGCTX(VP, 0xc0),
-       .ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = _nouveau_falcon_context_ctor,
-               .dtor = _nouveau_falcon_context_dtor,
-               .init = _nouveau_falcon_context_init,
-               .fini = _nouveau_falcon_context_fini,
-               .rd32 = _nouveau_falcon_context_rd32,
-               .wr32 = _nouveau_falcon_context_wr32,
-       },
-};
-
-/*******************************************************************************
- * PVP engine/subdev functions
- ******************************************************************************/
-
-static int
-nvc0_vp_init(struct nouveau_object *object)
-{
-       struct nvc0_vp_priv *priv = (void *)object;
-       int ret;
-
-       ret = nouveau_falcon_init(&priv->base);
-       if (ret)
-               return ret;
-
-       nv_wr32(priv, 0x085010, 0x0000fff2);
-       nv_wr32(priv, 0x08501c, 0x0000fff2);
-       return 0;
-}
-
-static int
-nvc0_vp_ctor(struct nouveau_object *parent, struct nouveau_object *engine,
-            struct nouveau_oclass *oclass, void *data, u32 size,
-            struct nouveau_object **pobject)
-{
-       struct nvc0_vp_priv *priv;
-       int ret;
-
-       ret = nouveau_falcon_create(parent, engine, oclass, 0x085000, true,
-                                   "PVP", "vp", &priv);
-       *pobject = nv_object(priv);
-       if (ret)
-               return ret;
-
-       nv_subdev(priv)->unit = 0x00020000;
-       nv_subdev(priv)->intr = nouveau_falcon_intr;
-       nv_engine(priv)->cclass = &nvc0_vp_cclass;
-       nv_engine(priv)->sclass = nvc0_vp_sclass;
-       return 0;
-}
-
-struct nouveau_oclass
-nvc0_vp_oclass = {
-       .handle = NV_ENGINE(VP, 0xc0),
-       .ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nvc0_vp_ctor,
-               .dtor = _nouveau_falcon_dtor,
-               .init = nvc0_vp_init,
-               .fini = _nouveau_falcon_fini,
-               .rd32 = _nouveau_falcon_rd32,
-               .wr32 = _nouveau_falcon_wr32,
-       },
-};
diff --git a/drivers/gpu/drm/nouveau/core/engine/vp/nve0.c b/drivers/gpu/drm/nouveau/core/engine/vp/nve0.c
deleted file mode 100644 (file)
index d4c3108..0000000
+++ /dev/null
@@ -1,110 +0,0 @@
-/*
- * Copyright 2012 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 <engine/falcon.h>
-#include <engine/vp.h>
-
-struct nve0_vp_priv {
-       struct nouveau_falcon base;
-};
-
-/*******************************************************************************
- * VP object classes
- ******************************************************************************/
-
-static struct nouveau_oclass
-nve0_vp_sclass[] = {
-       { 0x95b2, &nouveau_object_ofuncs },
-       {},
-};
-
-/*******************************************************************************
- * PVP context
- ******************************************************************************/
-
-static struct nouveau_oclass
-nve0_vp_cclass = {
-       .handle = NV_ENGCTX(VP, 0xe0),
-       .ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = _nouveau_falcon_context_ctor,
-               .dtor = _nouveau_falcon_context_dtor,
-               .init = _nouveau_falcon_context_init,
-               .fini = _nouveau_falcon_context_fini,
-               .rd32 = _nouveau_falcon_context_rd32,
-               .wr32 = _nouveau_falcon_context_wr32,
-       },
-};
-
-/*******************************************************************************
- * PVP engine/subdev functions
- ******************************************************************************/
-
-static int
-nve0_vp_init(struct nouveau_object *object)
-{
-       struct nve0_vp_priv *priv = (void *)object;
-       int ret;
-
-       ret = nouveau_falcon_init(&priv->base);
-       if (ret)
-               return ret;
-
-       nv_wr32(priv, 0x085010, 0x0000fff2);
-       nv_wr32(priv, 0x08501c, 0x0000fff2);
-       return 0;
-}
-
-static int
-nve0_vp_ctor(struct nouveau_object *parent, struct nouveau_object *engine,
-            struct nouveau_oclass *oclass, void *data, u32 size,
-            struct nouveau_object **pobject)
-{
-       struct nve0_vp_priv *priv;
-       int ret;
-
-       ret = nouveau_falcon_create(parent, engine, oclass, 0x085000, true,
-                                   "PVP", "vp", &priv);
-       *pobject = nv_object(priv);
-       if (ret)
-               return ret;
-
-       nv_subdev(priv)->unit = 0x00020000;
-       nv_subdev(priv)->intr = nouveau_falcon_intr;
-       nv_engine(priv)->cclass = &nve0_vp_cclass;
-       nv_engine(priv)->sclass = nve0_vp_sclass;
-       return 0;
-}
-
-struct nouveau_oclass
-nve0_vp_oclass = {
-       .handle = NV_ENGINE(VP, 0xe0),
-       .ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nve0_vp_ctor,
-               .dtor = _nouveau_falcon_dtor,
-               .init = nve0_vp_init,
-               .fini = _nouveau_falcon_fini,
-               .rd32 = _nouveau_falcon_rd32,
-               .wr32 = _nouveau_falcon_wr32,
-       },
-};
diff --git a/drivers/gpu/drm/nouveau/core/engine/xtensa.c b/drivers/gpu/drm/nouveau/core/engine/xtensa.c
deleted file mode 100644 (file)
index 9238475..0000000
+++ /dev/null
@@ -1,176 +0,0 @@
-/*
- * Copyright 2013 Ilia Mirkin
- *
- * 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.
- */
-
-#include <engine/xtensa.h>
-
-u32
-_nouveau_xtensa_rd32(struct nouveau_object *object, u64 addr)
-{
-       struct nouveau_xtensa *xtensa = (void *)object;
-       return nv_rd32(xtensa, xtensa->addr + addr);
-}
-
-void
-_nouveau_xtensa_wr32(struct nouveau_object *object, u64 addr, u32 data)
-{
-       struct nouveau_xtensa *xtensa = (void *)object;
-       nv_wr32(xtensa, xtensa->addr + addr, data);
-}
-
-int
-_nouveau_xtensa_engctx_ctor(struct nouveau_object *parent,
-                           struct nouveau_object *engine,
-                           struct nouveau_oclass *oclass, void *data, u32 size,
-                           struct nouveau_object **pobject)
-{
-       struct nouveau_engctx *engctx;
-       int ret;
-
-       ret = nouveau_engctx_create(parent, engine, oclass, NULL,
-                                   0x10000, 0x1000,
-                                   NVOBJ_FLAG_ZERO_ALLOC, &engctx);
-       *pobject = nv_object(engctx);
-       return ret;
-}
-
-void
-_nouveau_xtensa_intr(struct nouveau_subdev *subdev)
-{
-       struct nouveau_xtensa *xtensa = (void *)subdev;
-       u32 unk104 = nv_ro32(xtensa, 0xd04);
-       u32 intr = nv_ro32(xtensa, 0xc20);
-       u32 chan = nv_ro32(xtensa, 0xc28);
-       u32 unk10c = nv_ro32(xtensa, 0xd0c);
-
-       if (intr & 0x10)
-               nv_warn(xtensa, "Watchdog interrupt, engine hung.\n");
-       nv_wo32(xtensa, 0xc20, intr);
-       intr = nv_ro32(xtensa, 0xc20);
-       if (unk104 == 0x10001 && unk10c == 0x200 && chan && !intr) {
-               nv_debug(xtensa, "Enabling FIFO_CTRL\n");
-               nv_mask(xtensa, xtensa->addr + 0xd94, 0, xtensa->fifo_val);
-       }
-}
-
-int
-nouveau_xtensa_create_(struct nouveau_object *parent,
-                      struct nouveau_object *engine,
-                      struct nouveau_oclass *oclass, u32 addr, bool enable,
-                      const char *iname, const char *fname,
-                      int length, void **pobject)
-{
-       struct nouveau_xtensa *xtensa;
-       int ret;
-
-       ret = nouveau_engine_create_(parent, engine, oclass, enable, iname,
-                                    fname, length, pobject);
-       xtensa = *pobject;
-       if (ret)
-               return ret;
-
-       nv_subdev(xtensa)->intr = _nouveau_xtensa_intr;
-
-       xtensa->addr = addr;
-
-       return 0;
-}
-
-int
-_nouveau_xtensa_init(struct nouveau_object *object)
-{
-       struct nouveau_device *device = nv_device(object);
-       struct nouveau_xtensa *xtensa = (void *)object;
-       const struct firmware *fw;
-       char name[32];
-       int i, ret;
-       u32 tmp;
-
-       ret = nouveau_engine_init(&xtensa->base);
-       if (ret)
-               return ret;
-
-       if (!xtensa->gpu_fw) {
-               snprintf(name, sizeof(name), "nouveau/nv84_xuc%03x",
-                        xtensa->addr >> 12);
-
-               ret = request_firmware(&fw, name, nv_device_base(device));
-               if (ret) {
-                       nv_warn(xtensa, "unable to load firmware %s\n", name);
-                       return ret;
-               }
-
-               if (fw->size > 0x40000) {
-                       nv_warn(xtensa, "firmware %s too large\n", name);
-                       release_firmware(fw);
-                       return -EINVAL;
-               }
-
-               ret = nouveau_gpuobj_new(object, NULL, 0x40000, 0x1000, 0,
-                                        &xtensa->gpu_fw);
-               if (ret) {
-                       release_firmware(fw);
-                       return ret;
-               }
-
-               nv_debug(xtensa, "Loading firmware to address: 0x%llx\n",
-                        xtensa->gpu_fw->addr);
-
-               for (i = 0; i < fw->size / 4; i++)
-                       nv_wo32(xtensa->gpu_fw, i * 4, *((u32 *)fw->data + i));
-               release_firmware(fw);
-       }
-
-       nv_wo32(xtensa, 0xd10, 0x1fffffff); /* ?? */
-       nv_wo32(xtensa, 0xd08, 0x0fffffff); /* ?? */
-
-       nv_wo32(xtensa, 0xd28, xtensa->unkd28); /* ?? */
-       nv_wo32(xtensa, 0xc20, 0x3f); /* INTR */
-       nv_wo32(xtensa, 0xd84, 0x3f); /* INTR_EN */
-
-       nv_wo32(xtensa, 0xcc0, xtensa->gpu_fw->addr >> 8); /* XT_REGION_BASE */
-       nv_wo32(xtensa, 0xcc4, 0x1c); /* XT_REGION_SETUP */
-       nv_wo32(xtensa, 0xcc8, xtensa->gpu_fw->size >> 8); /* XT_REGION_LIMIT */
-
-       tmp = nv_rd32(xtensa, 0x0);
-       nv_wo32(xtensa, 0xde0, tmp); /* SCRATCH_H2X */
-
-       nv_wo32(xtensa, 0xce8, 0xf); /* XT_REGION_SETUP */
-
-       nv_wo32(xtensa, 0xc20, 0x3f); /* INTR */
-       nv_wo32(xtensa, 0xd84, 0x3f); /* INTR_EN */
-
-       return 0;
-}
-
-int
-_nouveau_xtensa_fini(struct nouveau_object *object, bool suspend)
-{
-       struct nouveau_xtensa *xtensa = (void *)object;
-
-       nv_wo32(xtensa, 0xd84, 0); /* INTR_EN */
-       nv_wo32(xtensa, 0xd94, 0); /* FIFO_CTRL */
-
-       if (!suspend)
-               nouveau_gpuobj_ref(NULL, &xtensa->gpu_fw);
-
-       return nouveau_engine_fini(&xtensa->base, suspend);
-}
diff --git a/drivers/gpu/drm/nouveau/core/include/core/client.h b/drivers/gpu/drm/nouveau/core/include/core/client.h
deleted file mode 100644 (file)
index b0ce9f6..0000000
+++ /dev/null
@@ -1,57 +0,0 @@
-#ifndef __NOUVEAU_CLIENT_H__
-#define __NOUVEAU_CLIENT_H__
-
-#include <core/namedb.h>
-
-struct nouveau_client {
-       struct nouveau_namedb base;
-       struct nouveau_handle *root;
-       struct nouveau_object *device;
-       char name[32];
-       u32 debug;
-       struct nouveau_vm *vm;
-       bool super;
-       void *data;
-
-       int (*ntfy)(const void *, u32, const void *, u32);
-       struct nvkm_client_notify *notify[16];
-};
-
-static inline struct nouveau_client *
-nv_client(void *obj)
-{
-#if CONFIG_NOUVEAU_DEBUG >= NV_DBG_PARANOIA
-       if (unlikely(!nv_iclass(obj, NV_CLIENT_CLASS)))
-               nv_assert("BAD CAST -> NvClient, %08x", nv_hclass(obj));
-#endif
-       return obj;
-}
-
-static inline struct nouveau_client *
-nouveau_client(void *obj)
-{
-       struct nouveau_object *client = nv_object(obj);
-       while (client && !(nv_iclass(client, NV_CLIENT_CLASS)))
-               client = client->parent;
-       return (void *)client;
-}
-
-#define nouveau_client_create(n,c,oc,od,d)                                     \
-       nouveau_client_create_((n), (c), (oc), (od), sizeof(**d), (void **)d)
-
-int  nouveau_client_create_(const char *name, u64 device, const char *cfg,
-                           const char *dbg, int, void **);
-#define nouveau_client_destroy(p)                                              \
-       nouveau_namedb_destroy(&(p)->base)
-
-int  nouveau_client_init(struct nouveau_client *);
-int  nouveau_client_fini(struct nouveau_client *, bool suspend);
-const char *nouveau_client_name(void *obj);
-
-int nvkm_client_notify_new(struct nouveau_object *, struct nvkm_event *,
-                          void *data, u32 size);
-int nvkm_client_notify_del(struct nouveau_client *, int index);
-int nvkm_client_notify_get(struct nouveau_client *, int index);
-int nvkm_client_notify_put(struct nouveau_client *, int index);
-
-#endif
diff --git a/drivers/gpu/drm/nouveau/core/include/core/debug.h b/drivers/gpu/drm/nouveau/core/include/core/debug.h
deleted file mode 100644 (file)
index 8092e2e..0000000
+++ /dev/null
@@ -1,20 +0,0 @@
-#ifndef __NOUVEAU_DEBUG_H__
-#define __NOUVEAU_DEBUG_H__
-
-extern int nv_info_debug_level;
-
-#define NV_DBG_FATAL    0
-#define NV_DBG_ERROR    1
-#define NV_DBG_WARN     2
-#define NV_DBG_INFO     nv_info_debug_level
-#define NV_DBG_DEBUG    4
-#define NV_DBG_TRACE    5
-#define NV_DBG_PARANOIA 6
-#define NV_DBG_SPAM     7
-
-#define NV_DBG_INFO_NORMAL 3
-#define NV_DBG_INFO_SILENT NV_DBG_DEBUG
-
-#define nv_debug_level(a) nv_info_debug_level = NV_DBG_INFO_##a
-
-#endif
diff --git a/drivers/gpu/drm/nouveau/core/include/core/device.h b/drivers/gpu/drm/nouveau/core/include/core/device.h
deleted file mode 100644 (file)
index 2ec2e50..0000000
+++ /dev/null
@@ -1,184 +0,0 @@
-#ifndef __NOUVEAU_DEVICE_H__
-#define __NOUVEAU_DEVICE_H__
-
-#include <core/object.h>
-#include <core/subdev.h>
-#include <core/engine.h>
-#include <core/event.h>
-
-enum nv_subdev_type {
-       NVDEV_ENGINE_DEVICE,
-       NVDEV_SUBDEV_VBIOS,
-
-       /* All subdevs from DEVINIT to DEVINIT_LAST will be created before
-        * *any* of them are initialised.  This subdev category is used
-        * for any subdevs that the VBIOS init table parsing may call out
-        * to during POST.
-        */
-       NVDEV_SUBDEV_DEVINIT,
-       NVDEV_SUBDEV_IBUS,
-       NVDEV_SUBDEV_GPIO,
-       NVDEV_SUBDEV_I2C,
-       NVDEV_SUBDEV_DEVINIT_LAST = NVDEV_SUBDEV_I2C,
-
-       /* This grouping of subdevs are initialised right after they've
-        * been created, and are allowed to assume any subdevs in the
-        * list above them exist and have been initialised.
-        */
-       NVDEV_SUBDEV_FUSE,
-       NVDEV_SUBDEV_MXM,
-       NVDEV_SUBDEV_MC,
-       NVDEV_SUBDEV_BUS,
-       NVDEV_SUBDEV_TIMER,
-       NVDEV_SUBDEV_FB,
-       NVDEV_SUBDEV_LTC,
-       NVDEV_SUBDEV_INSTMEM,
-       NVDEV_SUBDEV_VM,
-       NVDEV_SUBDEV_BAR,
-       NVDEV_SUBDEV_PWR,
-       NVDEV_SUBDEV_VOLT,
-       NVDEV_SUBDEV_THERM,
-       NVDEV_SUBDEV_CLOCK,
-
-       NVDEV_ENGINE_FIRST,
-       NVDEV_ENGINE_DMAOBJ = NVDEV_ENGINE_FIRST,
-       NVDEV_ENGINE_IFB,
-       NVDEV_ENGINE_FIFO,
-       NVDEV_ENGINE_SW,
-       NVDEV_ENGINE_GR,
-       NVDEV_ENGINE_MPEG,
-       NVDEV_ENGINE_ME,
-       NVDEV_ENGINE_VP,
-       NVDEV_ENGINE_CRYPT,
-       NVDEV_ENGINE_BSP,
-       NVDEV_ENGINE_PPP,
-       NVDEV_ENGINE_COPY0,
-       NVDEV_ENGINE_COPY1,
-       NVDEV_ENGINE_COPY2,
-       NVDEV_ENGINE_VIC,
-       NVDEV_ENGINE_VENC,
-       NVDEV_ENGINE_DISP,
-       NVDEV_ENGINE_PERFMON,
-
-       NVDEV_SUBDEV_NR,
-};
-
-struct nouveau_device {
-       struct nouveau_engine base;
-       struct list_head head;
-
-       struct pci_dev *pdev;
-       struct platform_device *platformdev;
-       u64 handle;
-
-       struct nvkm_event event;
-
-       const char *cfgopt;
-       const char *dbgopt;
-       const char *name;
-       const char *cname;
-       u64 disable_mask;
-
-       enum {
-               NV_04    = 0x04,
-               NV_10    = 0x10,
-               NV_11    = 0x11,
-               NV_20    = 0x20,
-               NV_30    = 0x30,
-               NV_40    = 0x40,
-               NV_50    = 0x50,
-               NV_C0    = 0xc0,
-               NV_E0    = 0xe0,
-               GM100    = 0x110,
-       } card_type;
-       u32 chipset;
-       u8  chiprev;
-       u32 crystal;
-
-       struct nouveau_oclass *oclass[NVDEV_SUBDEV_NR];
-       struct nouveau_object *subdev[NVDEV_SUBDEV_NR];
-
-       struct {
-               struct notifier_block nb;
-       } acpi;
-};
-
-int nouveau_device_list(u64 *name, int size);
-
-static inline struct nouveau_device *
-nv_device(void *obj)
-{
-       struct nouveau_object *object = nv_object(obj);
-       struct nouveau_object *device = object;
-
-       if (device->engine)
-               device = device->engine;
-       if (device->parent)
-               device = device->parent;
-
-#if CONFIG_NOUVEAU_DEBUG >= NV_DBG_PARANOIA
-       if (unlikely(!nv_iclass(device, NV_SUBDEV_CLASS) ||
-                    (nv_hclass(device) & 0xff) != NVDEV_ENGINE_DEVICE)) {
-               nv_assert("BAD CAST -> NvDevice, 0x%08x 0x%08x",
-                         nv_hclass(object), nv_hclass(device));
-       }
-#endif
-
-       return (void *)device;
-}
-
-static inline struct nouveau_subdev *
-nouveau_subdev(void *obj, int sub)
-{
-       if (nv_device(obj)->subdev[sub])
-               return nv_subdev(nv_device(obj)->subdev[sub]);
-       return NULL;
-}
-
-static inline struct nouveau_engine *
-nouveau_engine(void *obj, int sub)
-{
-       struct nouveau_subdev *subdev = nouveau_subdev(obj, sub);
-       if (subdev && nv_iclass(subdev, NV_ENGINE_CLASS))
-               return nv_engine(subdev);
-       return NULL;
-}
-
-static inline bool
-nv_device_match(struct nouveau_object *object, u16 dev, u16 ven, u16 sub)
-{
-       struct nouveau_device *device = nv_device(object);
-       return device->pdev->device == dev &&
-              device->pdev->subsystem_vendor == ven &&
-              device->pdev->subsystem_device == sub;
-}
-
-static inline bool
-nv_device_is_pci(struct nouveau_device *device)
-{
-       return device->pdev != NULL;
-}
-
-static inline bool
-nv_device_is_cpu_coherent(struct nouveau_device *device)
-{
-       return (!IS_ENABLED(CONFIG_ARM) && nv_device_is_pci(device));
-}
-
-static inline struct device *
-nv_device_base(struct nouveau_device *device)
-{
-       return nv_device_is_pci(device) ? &device->pdev->dev :
-                                         &device->platformdev->dev;
-}
-
-resource_size_t
-nv_device_resource_start(struct nouveau_device *device, unsigned int bar);
-
-resource_size_t
-nv_device_resource_len(struct nouveau_device *device, unsigned int bar);
-
-int
-nv_device_get_irq(struct nouveau_device *device, bool stall);
-
-#endif
diff --git a/drivers/gpu/drm/nouveau/core/include/core/engctx.h b/drivers/gpu/drm/nouveau/core/include/core/engctx.h
deleted file mode 100644 (file)
index 2fd48b5..0000000
+++ /dev/null
@@ -1,54 +0,0 @@
-#ifndef __NOUVEAU_ENGCTX_H__
-#define __NOUVEAU_ENGCTX_H__
-
-#include <core/object.h>
-#include <core/gpuobj.h>
-
-#include <subdev/vm.h>
-
-#define NV_ENGCTX_(eng,var) (NV_ENGCTX_CLASS | ((var) << 8) | (eng))
-#define NV_ENGCTX(name,var)  NV_ENGCTX_(NVDEV_ENGINE_##name, (var))
-
-struct nouveau_engctx {
-       struct nouveau_gpuobj base;
-       struct nouveau_vma vma;
-       struct list_head head;
-       unsigned long save;
-       u64 addr;
-};
-
-static inline struct nouveau_engctx *
-nv_engctx(void *obj)
-{
-#if CONFIG_NOUVEAU_DEBUG >= NV_DBG_PARANOIA
-       if (unlikely(!nv_iclass(obj, NV_ENGCTX_CLASS)))
-               nv_assert("BAD CAST -> NvEngCtx, %08x", nv_hclass(obj));
-#endif
-       return obj;
-}
-
-#define nouveau_engctx_create(p,e,c,g,s,a,f,d)                                 \
-       nouveau_engctx_create_((p), (e), (c), (g), (s), (a), (f),              \
-                              sizeof(**d), (void **)d)
-
-int  nouveau_engctx_create_(struct nouveau_object *, struct nouveau_object *,
-                           struct nouveau_oclass *, struct nouveau_object *,
-                           u32 size, u32 align, u32 flags,
-                           int length, void **data);
-void nouveau_engctx_destroy(struct nouveau_engctx *);
-int  nouveau_engctx_init(struct nouveau_engctx *);
-int  nouveau_engctx_fini(struct nouveau_engctx *, bool suspend);
-
-int  _nouveau_engctx_ctor(struct nouveau_object *, struct nouveau_object *,
-                         struct nouveau_oclass *, void *, u32,
-                         struct nouveau_object **);
-void _nouveau_engctx_dtor(struct nouveau_object *);
-int  _nouveau_engctx_init(struct nouveau_object *);
-int  _nouveau_engctx_fini(struct nouveau_object *, bool suspend);
-#define _nouveau_engctx_rd32 _nouveau_gpuobj_rd32
-#define _nouveau_engctx_wr32 _nouveau_gpuobj_wr32
-
-struct nouveau_object *nouveau_engctx_get(struct nouveau_engine *, u64 addr);
-void nouveau_engctx_put(struct nouveau_object *);
-
-#endif
diff --git a/drivers/gpu/drm/nouveau/core/include/core/engine.h b/drivers/gpu/drm/nouveau/core/include/core/engine.h
deleted file mode 100644 (file)
index 666d06d..0000000
+++ /dev/null
@@ -1,57 +0,0 @@
-#ifndef __NOUVEAU_ENGINE_H__
-#define __NOUVEAU_ENGINE_H__
-
-#include <core/object.h>
-#include <core/subdev.h>
-
-#define NV_ENGINE_(eng,var) (NV_ENGINE_CLASS | ((var) << 8) | (eng))
-#define NV_ENGINE(name,var)  NV_ENGINE_(NVDEV_ENGINE_##name, (var))
-
-struct nouveau_engine {
-       struct nouveau_subdev base;
-       struct nouveau_oclass *cclass;
-       struct nouveau_oclass *sclass;
-
-       struct list_head contexts;
-       spinlock_t lock;
-
-       void (*tile_prog)(struct nouveau_engine *, int region);
-       int  (*tlb_flush)(struct nouveau_engine *);
-};
-
-static inline struct nouveau_engine *
-nv_engine(void *obj)
-{
-#if CONFIG_NOUVEAU_DEBUG >= NV_DBG_PARANOIA
-       if (unlikely(!nv_iclass(obj, NV_ENGINE_CLASS)))
-               nv_assert("BAD CAST -> NvEngine, %08x", nv_hclass(obj));
-#endif
-       return obj;
-}
-
-static inline int
-nv_engidx(struct nouveau_object *object)
-{
-       return nv_subidx(object);
-}
-
-#define nouveau_engine_create(p,e,c,d,i,f,r)                                   \
-       nouveau_engine_create_((p), (e), (c), (d), (i), (f),                   \
-                              sizeof(**r),(void **)r)
-
-#define nouveau_engine_destroy(p)                                              \
-       nouveau_subdev_destroy(&(p)->base)
-#define nouveau_engine_init(p)                                                 \
-       nouveau_subdev_init(&(p)->base)
-#define nouveau_engine_fini(p,s)                                               \
-       nouveau_subdev_fini(&(p)->base, (s))
-
-int nouveau_engine_create_(struct nouveau_object *, struct nouveau_object *,
-                          struct nouveau_oclass *, bool, const char *,
-                          const char *, int, void **);
-
-#define _nouveau_engine_dtor _nouveau_subdev_dtor
-#define _nouveau_engine_init _nouveau_subdev_init
-#define _nouveau_engine_fini _nouveau_subdev_fini
-
-#endif
diff --git a/drivers/gpu/drm/nouveau/core/include/core/enum.h b/drivers/gpu/drm/nouveau/core/include/core/enum.h
deleted file mode 100644 (file)
index 4fc62bb..0000000
+++ /dev/null
@@ -1,24 +0,0 @@
-#ifndef __NOUVEAU_ENUM_H__
-#define __NOUVEAU_ENUM_H__
-
-struct nouveau_enum {
-       u32 value;
-       const char *name;
-       const void *data;
-       u32 data2;
-};
-
-const struct nouveau_enum *
-nouveau_enum_find(const struct nouveau_enum *, u32 value);
-
-const struct nouveau_enum *
-nouveau_enum_print(const struct nouveau_enum *en, u32 value);
-
-struct nouveau_bitfield {
-       u32 mask;
-       const char *name;
-};
-
-void nouveau_bitfield_print(const struct nouveau_bitfield *, u32 value);
-
-#endif
diff --git a/drivers/gpu/drm/nouveau/core/include/core/event.h b/drivers/gpu/drm/nouveau/core/include/core/event.h
deleted file mode 100644 (file)
index 9287652..0000000
+++ /dev/null
@@ -1,35 +0,0 @@
-#ifndef __NVKM_EVENT_H__
-#define __NVKM_EVENT_H__
-
-#include <core/notify.h>
-
-struct nvkm_event_func {
-       int  (*ctor)(struct nouveau_object *, void *data, u32 size,
-                    struct nvkm_notify *);
-       void (*send)(void *data, u32 size, struct nvkm_notify *);
-       void (*init)(struct nvkm_event *, int type, int index);
-       void (*fini)(struct nvkm_event *, int type, int index);
-};
-
-struct nvkm_event {
-       const struct nvkm_event_func *func;
-
-       int types_nr;
-       int index_nr;
-
-       spinlock_t refs_lock;
-       spinlock_t list_lock;
-       struct list_head list;
-       int *refs;
-};
-
-int  nvkm_event_init(const struct nvkm_event_func *func,
-                    int types_nr, int index_nr,
-                    struct nvkm_event *);
-void nvkm_event_fini(struct nvkm_event *);
-void nvkm_event_get(struct nvkm_event *, u32 types, int index);
-void nvkm_event_put(struct nvkm_event *, u32 types, int index);
-void nvkm_event_send(struct nvkm_event *, u32 types, int index,
-                    void *data, u32 size);
-
-#endif
diff --git a/drivers/gpu/drm/nouveau/core/include/core/gpuobj.h b/drivers/gpu/drm/nouveau/core/include/core/gpuobj.h
deleted file mode 100644 (file)
index b3b9ce4..0000000
+++ /dev/null
@@ -1,71 +0,0 @@
-#ifndef __NOUVEAU_GPUOBJ_H__
-#define __NOUVEAU_GPUOBJ_H__
-
-#include <core/object.h>
-#include <core/device.h>
-#include <core/parent.h>
-#include <core/mm.h>
-
-struct nouveau_vma;
-struct nouveau_vm;
-
-#define NVOBJ_FLAG_ZERO_ALLOC 0x00000001
-#define NVOBJ_FLAG_ZERO_FREE  0x00000002
-#define NVOBJ_FLAG_HEAP       0x00000004
-
-struct nouveau_gpuobj {
-       struct nouveau_object base;
-       struct nouveau_object *parent;
-       struct nouveau_mm_node *node;
-       struct nouveau_mm heap;
-
-       u32 flags;
-       u64 addr;
-       u32 size;
-};
-
-static inline struct nouveau_gpuobj *
-nv_gpuobj(void *obj)
-{
-#if CONFIG_NOUVEAU_DEBUG >= NV_DBG_PARANOIA
-       if (unlikely(!nv_iclass(obj, NV_GPUOBJ_CLASS)))
-               nv_assert("BAD CAST -> NvGpuObj, %08x", nv_hclass(obj));
-#endif
-       return obj;
-}
-
-#define nouveau_gpuobj_create(p,e,c,v,g,s,a,f,d)                               \
-       nouveau_gpuobj_create_((p), (e), (c), (v), (g), (s), (a), (f),         \
-                              sizeof(**d), (void **)d)
-#define nouveau_gpuobj_init(p) nouveau_object_init(&(p)->base)
-#define nouveau_gpuobj_fini(p,s) nouveau_object_fini(&(p)->base, (s))
-int  nouveau_gpuobj_create_(struct nouveau_object *, struct nouveau_object *,
-                           struct nouveau_oclass *, u32 pclass,
-                           struct nouveau_object *, u32 size, u32 align,
-                           u32 flags, int length, void **);
-void nouveau_gpuobj_destroy(struct nouveau_gpuobj *);
-
-int nouveau_gpuobj_new(struct nouveau_object *, struct nouveau_object *,
-                      u32 size, u32 align, u32 flags,
-                      struct nouveau_gpuobj **);
-int nouveau_gpuobj_dup(struct nouveau_object *, struct nouveau_gpuobj *,
-                      struct nouveau_gpuobj **);
-
-int nouveau_gpuobj_map(struct nouveau_gpuobj *, u32 acc, struct nouveau_vma *);
-int nouveau_gpuobj_map_vm(struct nouveau_gpuobj *, struct nouveau_vm *,
-                         u32 access, struct nouveau_vma *);
-void nouveau_gpuobj_unmap(struct nouveau_vma *);
-
-static inline void
-nouveau_gpuobj_ref(struct nouveau_gpuobj *obj, struct nouveau_gpuobj **ref)
-{
-       nouveau_object_ref(&obj->base, (struct nouveau_object **)ref);
-}
-
-void _nouveau_gpuobj_dtor(struct nouveau_object *);
-int  _nouveau_gpuobj_init(struct nouveau_object *);
-int  _nouveau_gpuobj_fini(struct nouveau_object *, bool);
-u32  _nouveau_gpuobj_rd32(struct nouveau_object *, u64);
-void _nouveau_gpuobj_wr32(struct nouveau_object *, u64, u32);
-
-#endif
diff --git a/drivers/gpu/drm/nouveau/core/include/core/handle.h b/drivers/gpu/drm/nouveau/core/include/core/handle.h
deleted file mode 100644 (file)
index d22a591..0000000
+++ /dev/null
@@ -1,34 +0,0 @@
-#ifndef __NOUVEAU_HANDLE_H__
-#define __NOUVEAU_HANDLE_H__
-
-struct nouveau_handle {
-       struct nouveau_namedb *namedb;
-       struct list_head node;
-
-       struct list_head head;
-       struct list_head tree;
-       u32 name;
-       u32 priv;
-
-       u8  route;
-       u64 token;
-
-       struct nouveau_handle *parent;
-       struct nouveau_object *object;
-};
-
-int  nouveau_handle_create(struct nouveau_object *, u32 parent, u32 handle,
-                          struct nouveau_object *, struct nouveau_handle **);
-void nouveau_handle_destroy(struct nouveau_handle *);
-int  nouveau_handle_init(struct nouveau_handle *);
-int  nouveau_handle_fini(struct nouveau_handle *, bool suspend);
-
-struct nouveau_object *
-nouveau_handle_ref(struct nouveau_object *, u32 name);
-
-struct nouveau_handle *nouveau_handle_get_class(struct nouveau_object *, u16);
-struct nouveau_handle *nouveau_handle_get_vinst(struct nouveau_object *, u64);
-struct nouveau_handle *nouveau_handle_get_cinst(struct nouveau_object *, u32);
-void nouveau_handle_put(struct nouveau_handle *);
-
-#endif
diff --git a/drivers/gpu/drm/nouveau/core/include/core/ioctl.h b/drivers/gpu/drm/nouveau/core/include/core/ioctl.h
deleted file mode 100644 (file)
index ac7935c..0000000
+++ /dev/null
@@ -1,6 +0,0 @@
-#ifndef __NVKM_IOCTL_H__
-#define __NVKM_IOCTL_H__
-
-int nvkm_ioctl(struct nouveau_client *, bool, void *, u32, void **);
-
-#endif
diff --git a/drivers/gpu/drm/nouveau/core/include/core/mm.h b/drivers/gpu/drm/nouveau/core/include/core/mm.h
deleted file mode 100644 (file)
index bfe6931..0000000
+++ /dev/null
@@ -1,40 +0,0 @@
-#ifndef __NOUVEAU_MM_H__
-#define __NOUVEAU_MM_H__
-
-struct nouveau_mm_node {
-       struct list_head nl_entry;
-       struct list_head fl_entry;
-       struct list_head rl_entry;
-
-#define NVKM_MM_HEAP_ANY 0x00
-       u8  heap;
-#define NVKM_MM_TYPE_NONE 0x00
-#define NVKM_MM_TYPE_HOLE 0xff
-       u8  type;
-       u32 offset;
-       u32 length;
-};
-
-struct nouveau_mm {
-       struct list_head nodes;
-       struct list_head free;
-
-       u32 block_size;
-       int heap_nodes;
-};
-
-static inline bool
-nouveau_mm_initialised(struct nouveau_mm *mm)
-{
-       return mm->block_size != 0;
-}
-
-int  nouveau_mm_init(struct nouveau_mm *, u32 offset, u32 length, u32 block);
-int  nouveau_mm_fini(struct nouveau_mm *);
-int  nouveau_mm_head(struct nouveau_mm *, u8 heap, u8 type, u32 size_max,
-                    u32 size_min, u32 align, struct nouveau_mm_node **);
-int  nouveau_mm_tail(struct nouveau_mm *, u8 heap, u8 type, u32 size_max,
-                    u32 size_min, u32 align, struct nouveau_mm_node **);
-void nouveau_mm_free(struct nouveau_mm *, struct nouveau_mm_node **);
-
-#endif
diff --git a/drivers/gpu/drm/nouveau/core/include/core/namedb.h b/drivers/gpu/drm/nouveau/core/include/core/namedb.h
deleted file mode 100644 (file)
index f5b5fd8..0000000
+++ /dev/null
@@ -1,56 +0,0 @@
-#ifndef __NOUVEAU_NAMEDB_H__
-#define __NOUVEAU_NAMEDB_H__
-
-#include <core/parent.h>
-
-struct nouveau_handle;
-
-struct nouveau_namedb {
-       struct nouveau_parent base;
-       rwlock_t lock;
-       struct list_head list;
-};
-
-static inline struct nouveau_namedb *
-nv_namedb(void *obj)
-{
-#if CONFIG_NOUVEAU_DEBUG >= NV_DBG_PARANOIA
-       if (unlikely(!nv_iclass(obj, NV_NAMEDB_CLASS)))
-               nv_assert("BAD CAST -> NvNameDB, %08x", nv_hclass(obj));
-#endif
-       return obj;
-}
-
-#define nouveau_namedb_create(p,e,c,v,s,m,d)                                   \
-       nouveau_namedb_create_((p), (e), (c), (v), (s), (m),                   \
-                              sizeof(**d), (void **)d)
-#define nouveau_namedb_init(p)                                                 \
-       nouveau_parent_init(&(p)->base)
-#define nouveau_namedb_fini(p,s)                                               \
-       nouveau_parent_fini(&(p)->base, (s))
-#define nouveau_namedb_destroy(p)                                              \
-       nouveau_parent_destroy(&(p)->base)
-
-int  nouveau_namedb_create_(struct nouveau_object *, struct nouveau_object *,
-                           struct nouveau_oclass *, u32 pclass,
-                           struct nouveau_oclass *, u64 engcls,
-                           int size, void **);
-
-int  _nouveau_namedb_ctor(struct nouveau_object *, struct nouveau_object *,
-                         struct nouveau_oclass *, void *, u32,
-                         struct nouveau_object **);
-#define _nouveau_namedb_dtor _nouveau_parent_dtor
-#define _nouveau_namedb_init _nouveau_parent_init
-#define _nouveau_namedb_fini _nouveau_parent_fini
-
-int  nouveau_namedb_insert(struct nouveau_namedb *, u32 name,
-                          struct nouveau_object *, struct nouveau_handle *);
-void nouveau_namedb_remove(struct nouveau_handle *);
-
-struct nouveau_handle *nouveau_namedb_get(struct nouveau_namedb *, u32);
-struct nouveau_handle *nouveau_namedb_get_class(struct nouveau_namedb *, u16);
-struct nouveau_handle *nouveau_namedb_get_vinst(struct nouveau_namedb *, u64);
-struct nouveau_handle *nouveau_namedb_get_cinst(struct nouveau_namedb *, u32);
-void nouveau_namedb_put(struct nouveau_handle *);
-
-#endif
diff --git a/drivers/gpu/drm/nouveau/core/include/core/notify.h b/drivers/gpu/drm/nouveau/core/include/core/notify.h
deleted file mode 100644 (file)
index a7c3c5f..0000000
+++ /dev/null
@@ -1,37 +0,0 @@
-#ifndef __NVKM_NOTIFY_H__
-#define __NVKM_NOTIFY_H__
-
-struct nvkm_notify {
-       struct nvkm_event *event;
-       struct list_head head;
-#define NVKM_NOTIFY_USER 0
-#define NVKM_NOTIFY_WORK 1
-       unsigned long flags;
-       int block;
-#define NVKM_NOTIFY_DROP 0
-#define NVKM_NOTIFY_KEEP 1
-       int (*func)(struct nvkm_notify *);
-
-       /* set by nvkm_event ctor */
-       u32 types;
-       int index;
-       u32 size;
-
-       struct work_struct work;
-       /* this is const for a *very* good reason - the data might be on the
-        * stack from an irq handler.  if you're not core/notify.c then you
-        * should probably think twice before casting it away...
-        */
-       const void *data;
-};
-
-int  nvkm_notify_init(struct nouveau_object *, struct nvkm_event *,
-                     int (*func)(struct nvkm_notify *), bool work,
-                     void *data, u32 size, u32 reply,
-                     struct nvkm_notify *);
-void nvkm_notify_fini(struct nvkm_notify *);
-void nvkm_notify_get(struct nvkm_notify *);
-void nvkm_notify_put(struct nvkm_notify *);
-void nvkm_notify_send(struct nvkm_notify *, void *data, u32 size);
-
-#endif
diff --git a/drivers/gpu/drm/nouveau/core/include/core/object.h b/drivers/gpu/drm/nouveau/core/include/core/object.h
deleted file mode 100644 (file)
index 2e2afa5..0000000
+++ /dev/null
@@ -1,206 +0,0 @@
-#ifndef __NOUVEAU_OBJECT_H__
-#define __NOUVEAU_OBJECT_H__
-
-#include <core/os.h>
-#include <core/printk.h>
-
-#define NV_PARENT_CLASS 0x80000000
-#define NV_NAMEDB_CLASS 0x40000000
-#define NV_CLIENT_CLASS 0x20000000
-#define NV_SUBDEV_CLASS 0x10000000
-#define NV_ENGINE_CLASS 0x08000000
-#define NV_MEMOBJ_CLASS 0x04000000
-#define NV_GPUOBJ_CLASS 0x02000000
-#define NV_ENGCTX_CLASS 0x01000000
-#define NV_OBJECT_CLASS 0x0000ffff
-
-struct nouveau_object {
-       struct nouveau_oclass *oclass;
-       struct nouveau_object *parent;
-       struct nouveau_object *engine;
-       atomic_t refcount;
-       atomic_t usecount;
-#if CONFIG_NOUVEAU_DEBUG >= NV_DBG_PARANOIA
-#define NOUVEAU_OBJECT_MAGIC 0x75ef0bad
-       struct list_head list;
-       u32 _magic;
-#endif
-};
-
-static inline struct nouveau_object *
-nv_object(void *obj)
-{
-#if CONFIG_NOUVEAU_DEBUG >= NV_DBG_PARANOIA
-       if (likely(obj)) {
-               struct nouveau_object *object = obj;
-               if (unlikely(object->_magic != NOUVEAU_OBJECT_MAGIC))
-                       nv_assert("BAD CAST -> NvObject, invalid magic");
-       }
-#endif
-       return obj;
-}
-
-#define nouveau_object_create(p,e,c,s,d)                                       \
-       nouveau_object_create_((p), (e), (c), (s), sizeof(**d), (void **)d)
-int  nouveau_object_create_(struct nouveau_object *, struct nouveau_object *,
-                           struct nouveau_oclass *, u32, int size, void **);
-void nouveau_object_destroy(struct nouveau_object *);
-int  nouveau_object_init(struct nouveau_object *);
-int  nouveau_object_fini(struct nouveau_object *, bool suspend);
-
-int _nouveau_object_ctor(struct nouveau_object *, struct nouveau_object *,
-                        struct nouveau_oclass *, void *, u32,
-                        struct nouveau_object **);
-
-extern struct nouveau_ofuncs nouveau_object_ofuncs;
-
-/* Don't allocate dynamically, because lockdep needs lock_class_keys to be in
- * ".data". */
-struct nouveau_oclass {
-       u32 handle;
-       struct nouveau_ofuncs * const ofuncs;
-       struct nouveau_omthds * const omthds;
-       struct lock_class_key lock_class_key;
-};
-
-#define nv_oclass(o)    nv_object(o)->oclass
-#define nv_hclass(o)    nv_oclass(o)->handle
-#define nv_iclass(o,i) (nv_hclass(o) & (i))
-#define nv_mclass(o)    nv_iclass(o, NV_OBJECT_CLASS)
-
-static inline struct nouveau_object *
-nv_pclass(struct nouveau_object *parent, u32 oclass)
-{
-       while (parent && !nv_iclass(parent, oclass))
-               parent = parent->parent;
-       return parent;
-}
-
-struct nouveau_omthds {
-       u32 start;
-       u32 limit;
-       int (*call)(struct nouveau_object *, u32, void *, u32);
-};
-
-struct nvkm_event;
-struct nouveau_ofuncs {
-       int  (*ctor)(struct nouveau_object *, struct nouveau_object *,
-                    struct nouveau_oclass *, void *data, u32 size,
-                    struct nouveau_object **);
-       void (*dtor)(struct nouveau_object *);
-       int  (*init)(struct nouveau_object *);
-       int  (*fini)(struct nouveau_object *, bool suspend);
-       int  (*mthd)(struct nouveau_object *, u32, void *, u32);
-       int  (*ntfy)(struct nouveau_object *, u32, struct nvkm_event **);
-       int  (* map)(struct nouveau_object *, u64 *, u32 *);
-       u8   (*rd08)(struct nouveau_object *, u64 offset);
-       u16  (*rd16)(struct nouveau_object *, u64 offset);
-       u32  (*rd32)(struct nouveau_object *, u64 offset);
-       void (*wr08)(struct nouveau_object *, u64 offset, u8 data);
-       void (*wr16)(struct nouveau_object *, u64 offset, u16 data);
-       void (*wr32)(struct nouveau_object *, u64 offset, u32 data);
-};
-
-static inline struct nouveau_ofuncs *
-nv_ofuncs(void *obj)
-{
-       return nv_oclass(obj)->ofuncs;
-}
-
-int  nouveau_object_ctor(struct nouveau_object *, struct nouveau_object *,
-                        struct nouveau_oclass *, void *, u32,
-                        struct nouveau_object **);
-void nouveau_object_ref(struct nouveau_object *, struct nouveau_object **);
-int nouveau_object_inc(struct nouveau_object *);
-int nouveau_object_dec(struct nouveau_object *, bool suspend);
-
-void nouveau_object_debug(void);
-
-static inline int
-nv_exec(void *obj, u32 mthd, void *data, u32 size)
-{
-       struct nouveau_omthds *method = nv_oclass(obj)->omthds;
-
-       while (method && method->call) {
-               if (mthd >= method->start && mthd <= method->limit)
-                       return method->call(obj, mthd, data, size);
-               method++;
-       }
-
-       return -EINVAL;
-}
-
-static inline int
-nv_call(void *obj, u32 mthd, u32 data)
-{
-       return nv_exec(obj, mthd, &data, sizeof(data));
-}
-
-static inline u8
-nv_ro08(void *obj, u64 addr)
-{
-       u8 data = nv_ofuncs(obj)->rd08(obj, addr);
-       nv_spam(obj, "nv_ro08 0x%08llx 0x%02x\n", addr, data);
-       return data;
-}
-
-static inline u16
-nv_ro16(void *obj, u64 addr)
-{
-       u16 data = nv_ofuncs(obj)->rd16(obj, addr);
-       nv_spam(obj, "nv_ro16 0x%08llx 0x%04x\n", addr, data);
-       return data;
-}
-
-static inline u32
-nv_ro32(void *obj, u64 addr)
-{
-       u32 data = nv_ofuncs(obj)->rd32(obj, addr);
-       nv_spam(obj, "nv_ro32 0x%08llx 0x%08x\n", addr, data);
-       return data;
-}
-
-static inline void
-nv_wo08(void *obj, u64 addr, u8 data)
-{
-       nv_spam(obj, "nv_wo08 0x%08llx 0x%02x\n", addr, data);
-       nv_ofuncs(obj)->wr08(obj, addr, data);
-}
-
-static inline void
-nv_wo16(void *obj, u64 addr, u16 data)
-{
-       nv_spam(obj, "nv_wo16 0x%08llx 0x%04x\n", addr, data);
-       nv_ofuncs(obj)->wr16(obj, addr, data);
-}
-
-static inline void
-nv_wo32(void *obj, u64 addr, u32 data)
-{
-       nv_spam(obj, "nv_wo32 0x%08llx 0x%08x\n", addr, data);
-       nv_ofuncs(obj)->wr32(obj, addr, data);
-}
-
-static inline u32
-nv_mo32(void *obj, u64 addr, u32 mask, u32 data)
-{
-       u32 temp = nv_ro32(obj, addr);
-       nv_wo32(obj, addr, (temp & ~mask) | data);
-       return temp;
-}
-
-static inline int
-nv_memcmp(void *obj, u32 addr, const char *str, u32 len)
-{
-       unsigned char c1, c2;
-
-       while (len--) {
-               c1 = nv_ro08(obj, addr++);
-               c2 = *(str++);
-               if (c1 != c2)
-                       return c1 - c2;
-       }
-       return 0;
-}
-
-#endif
diff --git a/drivers/gpu/drm/nouveau/core/include/core/option.h b/drivers/gpu/drm/nouveau/core/include/core/option.h
deleted file mode 100644 (file)
index ed05584..0000000
+++ /dev/null
@@ -1,20 +0,0 @@
-#ifndef __NOUVEAU_OPTION_H__
-#define __NOUVEAU_OPTION_H__
-
-#include <core/os.h>
-
-const char *nouveau_stropt(const char *optstr, const char *opt, int *len);
-bool nouveau_boolopt(const char *optstr, const char *opt, bool value);
-
-int nouveau_dbgopt(const char *optstr, const char *sub);
-
-/* compares unterminated string 'str' with zero-terminated string 'cmp' */
-static inline int
-strncasecmpz(const char *str, const char *cmp, size_t len)
-{
-       if (strlen(cmp) != len)
-               return len;
-       return strncasecmp(str, cmp, len);
-}
-
-#endif
diff --git a/drivers/gpu/drm/nouveau/core/include/core/parent.h b/drivers/gpu/drm/nouveau/core/include/core/parent.h
deleted file mode 100644 (file)
index 12da418..0000000
+++ /dev/null
@@ -1,62 +0,0 @@
-#ifndef __NOUVEAU_PARENT_H__
-#define __NOUVEAU_PARENT_H__
-
-#include <core/device.h>
-#include <core/object.h>
-
-struct nouveau_sclass {
-       struct nouveau_sclass *sclass;
-       struct nouveau_engine *engine;
-       struct nouveau_oclass *oclass;
-};
-
-struct nouveau_parent {
-       struct nouveau_object base;
-
-       struct nouveau_sclass *sclass;
-       u64 engine;
-
-       int  (*context_attach)(struct nouveau_object *,
-                              struct nouveau_object *);
-       int  (*context_detach)(struct nouveau_object *, bool suspend,
-                              struct nouveau_object *);
-
-       int  (*object_attach)(struct nouveau_object *parent,
-                             struct nouveau_object *object, u32 name);
-       void (*object_detach)(struct nouveau_object *parent, int cookie);
-};
-
-static inline struct nouveau_parent *
-nv_parent(void *obj)
-{
-#if CONFIG_NOUVEAU_DEBUG >= NV_DBG_PARANOIA
-       if (unlikely(!(nv_iclass(obj, NV_PARENT_CLASS))))
-               nv_assert("BAD CAST -> NvParent, %08x", nv_hclass(obj));
-#endif
-       return obj;
-}
-
-#define nouveau_parent_create(p,e,c,v,s,m,d)                                   \
-       nouveau_parent_create_((p), (e), (c), (v), (s), (m),                   \
-                              sizeof(**d), (void **)d)
-#define nouveau_parent_init(p)                                                 \
-       nouveau_object_init(&(p)->base)
-#define nouveau_parent_fini(p,s)                                               \
-       nouveau_object_fini(&(p)->base, (s))
-
-int  nouveau_parent_create_(struct nouveau_object *, struct nouveau_object *,
-                           struct nouveau_oclass *, u32 pclass,
-                           struct nouveau_oclass *, u64 engcls,
-                           int size, void **);
-void nouveau_parent_destroy(struct nouveau_parent *);
-
-void _nouveau_parent_dtor(struct nouveau_object *);
-#define _nouveau_parent_init nouveau_object_init
-#define _nouveau_parent_fini nouveau_object_fini
-
-int nouveau_parent_sclass(struct nouveau_object *, u16 handle,
-                         struct nouveau_object **pengine,
-                         struct nouveau_oclass **poclass);
-int nouveau_parent_lclass(struct nouveau_object *, u32 *, int);
-
-#endif
diff --git a/drivers/gpu/drm/nouveau/core/include/core/printk.h b/drivers/gpu/drm/nouveau/core/include/core/printk.h
deleted file mode 100644 (file)
index 451b6ed..0000000
+++ /dev/null
@@ -1,32 +0,0 @@
-#ifndef __NOUVEAU_PRINTK_H__
-#define __NOUVEAU_PRINTK_H__
-
-#include <core/os.h>
-#include <core/debug.h>
-
-struct nouveau_object;
-
-void __printf(3, 4)
-nv_printk_(struct nouveau_object *, int, const char *, ...);
-
-#define nv_printk(o,l,f,a...) do {                                             \
-       if (NV_DBG_##l <= CONFIG_NOUVEAU_DEBUG)                                \
-               nv_printk_(nv_object(o), NV_DBG_##l, f, ##a);                  \
-} while(0)
-
-#define nv_fatal(o,f,a...) nv_printk((o), FATAL, f, ##a)
-#define nv_error(o,f,a...) nv_printk((o), ERROR, f, ##a)
-#define nv_warn(o,f,a...) nv_printk((o), WARN, f, ##a)
-#define nv_info(o,f,a...) nv_printk((o), INFO, f, ##a)
-#define nv_debug(o,f,a...) nv_printk((o), DEBUG, f, ##a)
-#define nv_trace(o,f,a...) nv_printk((o), TRACE, f, ##a)
-#define nv_spam(o,f,a...) nv_printk((o), SPAM, f, ##a)
-#define nv_ioctl(o,f,a...) nv_trace(nouveau_client(o), "ioctl: "f, ##a)
-
-#define nv_assert(f,a...) do {                                                 \
-       if (NV_DBG_FATAL <= CONFIG_NOUVEAU_DEBUG)                              \
-               nv_printk_(NULL, NV_DBG_FATAL, f "\n", ##a);                   \
-       BUG_ON(1);                                                             \
-} while(0)
-
-#endif
diff --git a/drivers/gpu/drm/nouveau/core/include/core/ramht.h b/drivers/gpu/drm/nouveau/core/include/core/ramht.h
deleted file mode 100644 (file)
index 47e4cac..0000000
+++ /dev/null
@@ -1,23 +0,0 @@
-#ifndef __NOUVEAU_RAMHT_H__
-#define __NOUVEAU_RAMHT_H__
-
-#include <core/gpuobj.h>
-
-struct nouveau_ramht {
-       struct nouveau_gpuobj base;
-       int bits;
-};
-
-int  nouveau_ramht_insert(struct nouveau_ramht *, int chid,
-                         u32 handle, u32 context);
-void nouveau_ramht_remove(struct nouveau_ramht *, int cookie);
-int  nouveau_ramht_new(struct nouveau_object *, struct nouveau_object *,
-                      u32 size, u32 align, struct nouveau_ramht **);
-
-static inline void
-nouveau_ramht_ref(struct nouveau_ramht *obj, struct nouveau_ramht **ref)
-{
-       nouveau_gpuobj_ref(&obj->base, (struct nouveau_gpuobj **)ref);
-}
-
-#endif
diff --git a/drivers/gpu/drm/nouveau/core/include/core/subdev.h b/drivers/gpu/drm/nouveau/core/include/core/subdev.h
deleted file mode 100644 (file)
index e9632e9..0000000
+++ /dev/null
@@ -1,118 +0,0 @@
-#ifndef __NOUVEAU_SUBDEV_H__
-#define __NOUVEAU_SUBDEV_H__
-
-#include <core/object.h>
-
-#define NV_SUBDEV_(sub,var) (NV_SUBDEV_CLASS | ((var) << 8) | (sub))
-#define NV_SUBDEV(name,var)  NV_SUBDEV_(NVDEV_SUBDEV_##name, (var))
-
-struct nouveau_subdev {
-       struct nouveau_object base;
-       struct mutex mutex;
-       const char *name;
-       void __iomem *mmio;
-       u32 debug;
-       u32 unit;
-
-       void (*intr)(struct nouveau_subdev *);
-};
-
-static inline struct nouveau_subdev *
-nv_subdev(void *obj)
-{
-#if CONFIG_NOUVEAU_DEBUG >= NV_DBG_PARANOIA
-       if (unlikely(!nv_iclass(obj, NV_SUBDEV_CLASS)))
-               nv_assert("BAD CAST -> NvSubDev, %08x", nv_hclass(obj));
-#endif
-       return obj;
-}
-
-static inline int
-nv_subidx(struct nouveau_object *object)
-{
-       return nv_hclass(nv_subdev(object)) & 0xff;
-}
-
-#define nouveau_subdev_create(p,e,o,v,s,f,d)                                   \
-       nouveau_subdev_create_((p), (e), (o), (v), (s), (f),                   \
-                              sizeof(**d),(void **)d)
-
-int  nouveau_subdev_create_(struct nouveau_object *, struct nouveau_object *,
-                           struct nouveau_oclass *, u32 pclass,
-                           const char *sname, const char *fname,
-                           int size, void **);
-void nouveau_subdev_destroy(struct nouveau_subdev *);
-int  nouveau_subdev_init(struct nouveau_subdev *);
-int  nouveau_subdev_fini(struct nouveau_subdev *, bool suspend);
-void nouveau_subdev_reset(struct nouveau_object *);
-
-void _nouveau_subdev_dtor(struct nouveau_object *);
-int  _nouveau_subdev_init(struct nouveau_object *);
-int  _nouveau_subdev_fini(struct nouveau_object *, bool suspend);
-
-#define s_printk(s,l,f,a...) do {                                              \
-       if ((s)->debug >= OS_DBG_##l) {                                        \
-               nv_printk((s)->base.parent, (s)->name, l, f, ##a);             \
-       }                                                                      \
-} while(0)
-
-static inline u8
-nv_rd08(void *obj, u32 addr)
-{
-       struct nouveau_subdev *subdev = nv_subdev(obj);
-       u8 data = ioread8(subdev->mmio + addr);
-       nv_spam(subdev, "nv_rd08 0x%06x 0x%02x\n", addr, data);
-       return data;
-}
-
-static inline u16
-nv_rd16(void *obj, u32 addr)
-{
-       struct nouveau_subdev *subdev = nv_subdev(obj);
-       u16 data = ioread16_native(subdev->mmio + addr);
-       nv_spam(subdev, "nv_rd16 0x%06x 0x%04x\n", addr, data);
-       return data;
-}
-
-static inline u32
-nv_rd32(void *obj, u32 addr)
-{
-       struct nouveau_subdev *subdev = nv_subdev(obj);
-       u32 data = ioread32_native(subdev->mmio + addr);
-       nv_spam(subdev, "nv_rd32 0x%06x 0x%08x\n", addr, data);
-       return data;
-}
-
-static inline void
-nv_wr08(void *obj, u32 addr, u8 data)
-{
-       struct nouveau_subdev *subdev = nv_subdev(obj);
-       nv_spam(subdev, "nv_wr08 0x%06x 0x%02x\n", addr, data);
-       iowrite8(data, subdev->mmio + addr);
-}
-
-static inline void
-nv_wr16(void *obj, u32 addr, u16 data)
-{
-       struct nouveau_subdev *subdev = nv_subdev(obj);
-       nv_spam(subdev, "nv_wr16 0x%06x 0x%04x\n", addr, data);
-       iowrite16_native(data, subdev->mmio + addr);
-}
-
-static inline void
-nv_wr32(void *obj, u32 addr, u32 data)
-{
-       struct nouveau_subdev *subdev = nv_subdev(obj);
-       nv_spam(subdev, "nv_wr32 0x%06x 0x%08x\n", addr, data);
-       iowrite32_native(data, subdev->mmio + addr);
-}
-
-static inline u32
-nv_mask(void *obj, u32 addr, u32 mask, u32 data)
-{
-       u32 temp = nv_rd32(obj, addr);
-       nv_wr32(obj, addr, (temp & ~mask) | data);
-       return temp;
-}
-
-#endif
diff --git a/drivers/gpu/drm/nouveau/core/include/engine/bsp.h b/drivers/gpu/drm/nouveau/core/include/engine/bsp.h
deleted file mode 100644 (file)
index 67662e2..0000000
+++ /dev/null
@@ -1,9 +0,0 @@
-#ifndef __NOUVEAU_BSP_H__
-#define __NOUVEAU_BSP_H__
-
-extern struct nouveau_oclass nv84_bsp_oclass;
-extern struct nouveau_oclass nv98_bsp_oclass;
-extern struct nouveau_oclass nvc0_bsp_oclass;
-extern struct nouveau_oclass nve0_bsp_oclass;
-
-#endif
diff --git a/drivers/gpu/drm/nouveau/core/include/engine/copy.h b/drivers/gpu/drm/nouveau/core/include/engine/copy.h
deleted file mode 100644 (file)
index 316a28a..0000000
+++ /dev/null
@@ -1,13 +0,0 @@
-#ifndef __NOUVEAU_COPY_H__
-#define __NOUVEAU_COPY_H__
-
-void nva3_copy_intr(struct nouveau_subdev *);
-
-extern struct nouveau_oclass nva3_copy_oclass;
-extern struct nouveau_oclass nvc0_copy0_oclass;
-extern struct nouveau_oclass nvc0_copy1_oclass;
-extern struct nouveau_oclass nve0_copy0_oclass;
-extern struct nouveau_oclass nve0_copy1_oclass;
-extern struct nouveau_oclass nve0_copy2_oclass;
-
-#endif
diff --git a/drivers/gpu/drm/nouveau/core/include/engine/crypt.h b/drivers/gpu/drm/nouveau/core/include/engine/crypt.h
deleted file mode 100644 (file)
index db97561..0000000
+++ /dev/null
@@ -1,7 +0,0 @@
-#ifndef __NOUVEAU_CRYPT_H__
-#define __NOUVEAU_CRYPT_H__
-
-extern struct nouveau_oclass nv84_crypt_oclass;
-extern struct nouveau_oclass nv98_crypt_oclass;
-
-#endif
diff --git a/drivers/gpu/drm/nouveau/core/include/engine/device.h b/drivers/gpu/drm/nouveau/core/include/engine/device.h
deleted file mode 100644 (file)
index 672d3c8..0000000
+++ /dev/null
@@ -1,33 +0,0 @@
-#ifndef __NOUVEAU_SUBDEV_DEVICE_H__
-#define __NOUVEAU_SUBDEV_DEVICE_H__
-
-#include <core/device.h>
-
-struct platform_device;
-
-enum nv_bus_type {
-       NOUVEAU_BUS_PCI,
-       NOUVEAU_BUS_PLATFORM,
-};
-
-#define nouveau_device_create(p,t,n,s,c,d,u)                                   \
-       nouveau_device_create_((void *)(p), (t), (n), (s), (c), (d),           \
-                              sizeof(**u), (void **)u)
-
-int  nouveau_device_create_(void *, enum nv_bus_type type, u64 name,
-                           const char *sname, const char *cfg, const char *dbg,
-                           int, void **);
-
-int nv04_identify(struct nouveau_device *);
-int nv10_identify(struct nouveau_device *);
-int nv20_identify(struct nouveau_device *);
-int nv30_identify(struct nouveau_device *);
-int nv40_identify(struct nouveau_device *);
-int nv50_identify(struct nouveau_device *);
-int nvc0_identify(struct nouveau_device *);
-int nve0_identify(struct nouveau_device *);
-int gm100_identify(struct nouveau_device *);
-
-struct nouveau_device *nouveau_device_find(u64 name);
-
-#endif
diff --git a/drivers/gpu/drm/nouveau/core/include/engine/disp.h b/drivers/gpu/drm/nouveau/core/include/engine/disp.h
deleted file mode 100644 (file)
index fc307f1..0000000
+++ /dev/null
@@ -1,36 +0,0 @@
-#ifndef __NOUVEAU_DISP_H__
-#define __NOUVEAU_DISP_H__
-
-#include <core/object.h>
-#include <core/engine.h>
-#include <core/device.h>
-#include <core/event.h>
-
-struct nouveau_disp {
-       struct nouveau_engine base;
-
-       struct list_head outp;
-
-       struct nvkm_event hpd;
-       struct nvkm_event vblank;
-};
-
-static inline struct nouveau_disp *
-nouveau_disp(void *obj)
-{
-       return (void *)nv_device(obj)->subdev[NVDEV_ENGINE_DISP];
-}
-
-extern struct nouveau_oclass *nv04_disp_oclass;
-extern struct nouveau_oclass *nv50_disp_oclass;
-extern struct nouveau_oclass *nv84_disp_oclass;
-extern struct nouveau_oclass *nva0_disp_oclass;
-extern struct nouveau_oclass *nv94_disp_oclass;
-extern struct nouveau_oclass *nva3_disp_oclass;
-extern struct nouveau_oclass *nvd0_disp_oclass;
-extern struct nouveau_oclass *nve0_disp_oclass;
-extern struct nouveau_oclass *nvf0_disp_oclass;
-extern struct nouveau_oclass *gm107_disp_oclass;
-extern struct nouveau_oclass *gm204_disp_oclass;
-
-#endif
diff --git a/drivers/gpu/drm/nouveau/core/include/engine/dmaobj.h b/drivers/gpu/drm/nouveau/core/include/engine/dmaobj.h
deleted file mode 100644 (file)
index 1b283a7..0000000
+++ /dev/null
@@ -1,31 +0,0 @@
-#ifndef __NOUVEAU_DMAOBJ_H__
-#define __NOUVEAU_DMAOBJ_H__
-
-#include <core/object.h>
-#include <core/engine.h>
-
-struct nouveau_gpuobj;
-
-struct nouveau_dmaobj {
-       struct nouveau_object base;
-       u32 target;
-       u32 access;
-       u64 start;
-       u64 limit;
-};
-
-struct nouveau_dmaeng {
-       struct nouveau_engine base;
-
-       /* creates a "physical" dma object from a struct nouveau_dmaobj */
-       int (*bind)(struct nouveau_dmaobj *dmaobj,
-                   struct nouveau_object *parent,
-                   struct nouveau_gpuobj **);
-};
-
-extern struct nouveau_oclass *nv04_dmaeng_oclass;
-extern struct nouveau_oclass *nv50_dmaeng_oclass;
-extern struct nouveau_oclass *nvc0_dmaeng_oclass;
-extern struct nouveau_oclass *nvd0_dmaeng_oclass;
-
-#endif
diff --git a/drivers/gpu/drm/nouveau/core/include/engine/falcon.h b/drivers/gpu/drm/nouveau/core/include/engine/falcon.h
deleted file mode 100644 (file)
index 181aa7d..0000000
+++ /dev/null
@@ -1,83 +0,0 @@
-#ifndef __NOUVEAU_FALCON_H__
-#define __NOUVEAU_FALCON_H__
-
-#include <core/engine.h>
-#include <core/engctx.h>
-#include <core/gpuobj.h>
-
-struct nouveau_falcon_chan {
-       struct nouveau_engctx base;
-};
-
-#define nouveau_falcon_context_create(p,e,c,g,s,a,f,d)                         \
-       nouveau_engctx_create((p), (e), (c), (g), (s), (a), (f), (d))
-#define nouveau_falcon_context_destroy(d)                                      \
-       nouveau_engctx_destroy(&(d)->base)
-#define nouveau_falcon_context_init(d)                                         \
-       nouveau_engctx_init(&(d)->base)
-#define nouveau_falcon_context_fini(d,s)                                       \
-       nouveau_engctx_fini(&(d)->base, (s))
-
-#define _nouveau_falcon_context_ctor _nouveau_engctx_ctor
-#define _nouveau_falcon_context_dtor _nouveau_engctx_dtor
-#define _nouveau_falcon_context_init _nouveau_engctx_init
-#define _nouveau_falcon_context_fini _nouveau_engctx_fini
-#define _nouveau_falcon_context_rd32 _nouveau_engctx_rd32
-#define _nouveau_falcon_context_wr32 _nouveau_engctx_wr32
-
-struct nouveau_falcon_data {
-       bool external;
-};
-
-struct nouveau_falcon {
-       struct nouveau_engine base;
-
-       u32 addr;
-       u8  version;
-       u8  secret;
-
-       struct nouveau_gpuobj *core;
-       bool external;
-
-       struct {
-               u32 limit;
-               u32 *data;
-               u32  size;
-       } code;
-
-       struct {
-               u32 limit;
-               u32 *data;
-               u32  size;
-       } data;
-};
-
-#define nv_falcon(priv) (&(priv)->base)
-
-#define nouveau_falcon_create(p,e,c,b,d,i,f,r)                                 \
-       nouveau_falcon_create_((p), (e), (c), (b), (d), (i), (f),              \
-                              sizeof(**r),(void **)r)
-#define nouveau_falcon_destroy(p)                                              \
-       nouveau_engine_destroy(&(p)->base)
-#define nouveau_falcon_init(p) ({                                              \
-       struct nouveau_falcon *falcon = (p);                                   \
-       _nouveau_falcon_init(nv_object(falcon));                               \
-})
-#define nouveau_falcon_fini(p,s) ({                                            \
-       struct nouveau_falcon *falcon = (p);                                   \
-       _nouveau_falcon_fini(nv_object(falcon), (s));                          \
-})
-
-int nouveau_falcon_create_(struct nouveau_object *, struct nouveau_object *,
-                          struct nouveau_oclass *, u32, bool, const char *,
-                          const char *, int, void **);
-
-void nouveau_falcon_intr(struct nouveau_subdev *subdev);
-
-#define _nouveau_falcon_dtor _nouveau_engine_dtor
-int  _nouveau_falcon_init(struct nouveau_object *);
-int  _nouveau_falcon_fini(struct nouveau_object *, bool);
-u32  _nouveau_falcon_rd32(struct nouveau_object *, u64);
-void _nouveau_falcon_wr32(struct nouveau_object *, u64, u32);
-
-#endif
diff --git a/drivers/gpu/drm/nouveau/core/include/engine/fifo.h b/drivers/gpu/drm/nouveau/core/include/engine/fifo.h
deleted file mode 100644 (file)
index 2007453..0000000
+++ /dev/null
@@ -1,126 +0,0 @@
-#ifndef __NOUVEAU_FIFO_H__
-#define __NOUVEAU_FIFO_H__
-
-#include <core/namedb.h>
-#include <core/gpuobj.h>
-#include <core/engine.h>
-#include <core/event.h>
-
-struct nouveau_fifo_chan {
-       struct nouveau_namedb base;
-       struct nouveau_dmaobj *pushdma;
-       struct nouveau_gpuobj *pushgpu;
-       void __iomem *user;
-       u64 addr;
-       u32 size;
-       u16 chid;
-       atomic_t refcnt; /* NV04_NVSW_SET_REF */
-};
-
-static inline struct nouveau_fifo_chan *
-nouveau_fifo_chan(void *obj)
-{
-       return (void *)nv_namedb(obj);
-}
-
-#define nouveau_fifo_channel_create(p,e,c,b,a,s,n,m,d)                         \
-       nouveau_fifo_channel_create_((p), (e), (c), (b), (a), (s), (n),        \
-                                    (m), sizeof(**d), (void **)d)
-#define nouveau_fifo_channel_init(p)                                           \
-       nouveau_namedb_init(&(p)->base)
-#define nouveau_fifo_channel_fini(p,s)                                         \
-       nouveau_namedb_fini(&(p)->base, (s))
-
-int  nouveau_fifo_channel_create_(struct nouveau_object *,
-                                 struct nouveau_object *,
-                                 struct nouveau_oclass *,
-                                 int bar, u32 addr, u32 size, u32 push,
-                                 u64 engmask, int len, void **);
-void nouveau_fifo_channel_destroy(struct nouveau_fifo_chan *);
-
-#define _nouveau_fifo_channel_init _nouveau_namedb_init
-#define _nouveau_fifo_channel_fini _nouveau_namedb_fini
-
-void _nouveau_fifo_channel_dtor(struct nouveau_object *);
-int  _nouveau_fifo_channel_map(struct nouveau_object *, u64 *, u32 *);
-u32  _nouveau_fifo_channel_rd32(struct nouveau_object *, u64);
-void _nouveau_fifo_channel_wr32(struct nouveau_object *, u64, u32);
-int  _nouveau_fifo_channel_ntfy(struct nouveau_object *, u32, struct nvkm_event **);
-
-struct nouveau_fifo_base {
-       struct nouveau_gpuobj base;
-};
-
-#define nouveau_fifo_context_create(p,e,c,g,s,a,f,d)                           \
-       nouveau_gpuobj_create((p), (e), (c), 0, (g), (s), (a), (f), (d))
-#define nouveau_fifo_context_destroy(p)                                        \
-       nouveau_gpuobj_destroy(&(p)->base)
-#define nouveau_fifo_context_init(p)                                           \
-       nouveau_gpuobj_init(&(p)->base)
-#define nouveau_fifo_context_fini(p,s)                                         \
-       nouveau_gpuobj_fini(&(p)->base, (s))
-
-#define _nouveau_fifo_context_dtor _nouveau_gpuobj_dtor
-#define _nouveau_fifo_context_init _nouveau_gpuobj_init
-#define _nouveau_fifo_context_fini _nouveau_gpuobj_fini
-#define _nouveau_fifo_context_rd32 _nouveau_gpuobj_rd32
-#define _nouveau_fifo_context_wr32 _nouveau_gpuobj_wr32
-
-struct nouveau_fifo {
-       struct nouveau_engine base;
-
-       struct nvkm_event cevent; /* channel creation event */
-       struct nvkm_event uevent; /* async user trigger */
-
-       struct nouveau_object **channel;
-       spinlock_t lock;
-       u16 min;
-       u16 max;
-
-       int  (*chid)(struct nouveau_fifo *, struct nouveau_object *);
-       void (*pause)(struct nouveau_fifo *, unsigned long *);
-       void (*start)(struct nouveau_fifo *, unsigned long *);
-};
-
-static inline struct nouveau_fifo *
-nouveau_fifo(void *obj)
-{
-       return (void *)nv_device(obj)->subdev[NVDEV_ENGINE_FIFO];
-}
-
-#define nouveau_fifo_create(o,e,c,fc,lc,d)                                     \
-       nouveau_fifo_create_((o), (e), (c), (fc), (lc), sizeof(**d), (void **)d)
-#define nouveau_fifo_init(p)                                                   \
-       nouveau_engine_init(&(p)->base)
-#define nouveau_fifo_fini(p,s)                                                 \
-       nouveau_engine_fini(&(p)->base, (s))
-
-int nouveau_fifo_create_(struct nouveau_object *, struct nouveau_object *,
-                        struct nouveau_oclass *, int min, int max,
-                        int size, void **);
-void nouveau_fifo_destroy(struct nouveau_fifo *);
-const char *
-nouveau_client_name_for_fifo_chid(struct nouveau_fifo *fifo, u32 chid);
-
-#define _nouveau_fifo_init _nouveau_engine_init
-#define _nouveau_fifo_fini _nouveau_engine_fini
-
-extern struct nouveau_oclass *nv04_fifo_oclass;
-extern struct nouveau_oclass *nv10_fifo_oclass;
-extern struct nouveau_oclass *nv17_fifo_oclass;
-extern struct nouveau_oclass *nv40_fifo_oclass;
-extern struct nouveau_oclass *nv50_fifo_oclass;
-extern struct nouveau_oclass *nv84_fifo_oclass;
-extern struct nouveau_oclass *nvc0_fifo_oclass;
-extern struct nouveau_oclass *nve0_fifo_oclass;
-extern struct nouveau_oclass *gk20a_fifo_oclass;
-extern struct nouveau_oclass *nv108_fifo_oclass;
-
-int  nouveau_fifo_uevent_ctor(struct nouveau_object *, void *, u32,
-                             struct nvkm_notify *);
-void nouveau_fifo_uevent(struct nouveau_fifo *);
-
-void nv04_fifo_intr(struct nouveau_subdev *);
-int  nv04_fifo_context_attach(struct nouveau_object *, struct nouveau_object *);
-
-#endif
diff --git a/drivers/gpu/drm/nouveau/core/include/engine/graph.h b/drivers/gpu/drm/nouveau/core/include/engine/graph.h
deleted file mode 100644 (file)
index d505557..0000000
+++ /dev/null
@@ -1,86 +0,0 @@
-#ifndef __NOUVEAU_GRAPH_H__
-#define __NOUVEAU_GRAPH_H__
-
-#include <core/engine.h>
-#include <core/engctx.h>
-#include <core/enum.h>
-
-struct nouveau_graph_chan {
-       struct nouveau_engctx base;
-};
-
-#define nouveau_graph_context_create(p,e,c,g,s,a,f,d)                          \
-       nouveau_engctx_create((p), (e), (c), (g), (s), (a), (f), (d))
-#define nouveau_graph_context_destroy(d)                                       \
-       nouveau_engctx_destroy(&(d)->base)
-#define nouveau_graph_context_init(d)                                          \
-       nouveau_engctx_init(&(d)->base)
-#define nouveau_graph_context_fini(d,s)                                        \
-       nouveau_engctx_fini(&(d)->base, (s))
-
-#define _nouveau_graph_context_dtor _nouveau_engctx_dtor
-#define _nouveau_graph_context_init _nouveau_engctx_init
-#define _nouveau_graph_context_fini _nouveau_engctx_fini
-#define _nouveau_graph_context_rd32 _nouveau_engctx_rd32
-#define _nouveau_graph_context_wr32 _nouveau_engctx_wr32
-
-struct nouveau_graph {
-       struct nouveau_engine base;
-
-       /* Returns chipset-specific counts of units packed into an u64.
-        */
-       u64 (*units)(struct nouveau_graph *);
-};
-
-static inline struct nouveau_graph *
-nouveau_graph(void *obj)
-{
-       return (void *)nv_device(obj)->subdev[NVDEV_ENGINE_GR];
-}
-
-#define nouveau_graph_create(p,e,c,y,d)                                        \
-       nouveau_engine_create((p), (e), (c), (y), "PGRAPH", "graphics", (d))
-#define nouveau_graph_destroy(d)                                               \
-       nouveau_engine_destroy(&(d)->base)
-#define nouveau_graph_init(d)                                                  \
-       nouveau_engine_init(&(d)->base)
-#define nouveau_graph_fini(d,s)                                                \
-       nouveau_engine_fini(&(d)->base, (s))
-
-#define _nouveau_graph_dtor _nouveau_engine_dtor
-#define _nouveau_graph_init _nouveau_engine_init
-#define _nouveau_graph_fini _nouveau_engine_fini
-
-extern struct nouveau_oclass nv04_graph_oclass;
-extern struct nouveau_oclass nv10_graph_oclass;
-extern struct nouveau_oclass nv20_graph_oclass;
-extern struct nouveau_oclass nv25_graph_oclass;
-extern struct nouveau_oclass nv2a_graph_oclass;
-extern struct nouveau_oclass nv30_graph_oclass;
-extern struct nouveau_oclass nv34_graph_oclass;
-extern struct nouveau_oclass nv35_graph_oclass;
-extern struct nouveau_oclass nv40_graph_oclass;
-extern struct nouveau_oclass nv50_graph_oclass;
-extern struct nouveau_oclass *nvc0_graph_oclass;
-extern struct nouveau_oclass *nvc1_graph_oclass;
-extern struct nouveau_oclass *nvc4_graph_oclass;
-extern struct nouveau_oclass *nvc8_graph_oclass;
-extern struct nouveau_oclass *nvd7_graph_oclass;
-extern struct nouveau_oclass *nvd9_graph_oclass;
-extern struct nouveau_oclass *nve4_graph_oclass;
-extern struct nouveau_oclass *gk20a_graph_oclass;
-extern struct nouveau_oclass *nvf0_graph_oclass;
-extern struct nouveau_oclass *gk110b_graph_oclass;
-extern struct nouveau_oclass *nv108_graph_oclass;
-extern struct nouveau_oclass *gm107_graph_oclass;
-
-extern const struct nouveau_bitfield nv04_graph_nsource[];
-extern struct nouveau_ofuncs nv04_graph_ofuncs;
-bool nv04_graph_idle(void *obj);
-
-extern const struct nouveau_bitfield nv10_graph_intr_name[];
-extern const struct nouveau_bitfield nv10_graph_nstatus[];
-
-extern const struct nouveau_enum nv50_data_error_names[];
-
-#endif
diff --git a/drivers/gpu/drm/nouveau/core/include/engine/mpeg.h b/drivers/gpu/drm/nouveau/core/include/engine/mpeg.h
deleted file mode 100644 (file)
index 9b0d938..0000000
+++ /dev/null
@@ -1,63 +0,0 @@
-#ifndef __NOUVEAU_MPEG_H__
-#define __NOUVEAU_MPEG_H__
-
-#include <core/engine.h>
-#include <core/engctx.h>
-
-struct nouveau_mpeg_chan {
-       struct nouveau_engctx base;
-};
-
-#define nouveau_mpeg_context_create(p,e,c,g,s,a,f,d)                           \
-       nouveau_engctx_create((p), (e), (c), (g), (s), (a), (f), (d))
-#define nouveau_mpeg_context_destroy(d)                                        \
-       nouveau_engctx_destroy(&(d)->base)
-#define nouveau_mpeg_context_init(d)                                           \
-       nouveau_engctx_init(&(d)->base)
-#define nouveau_mpeg_context_fini(d,s)                                         \
-       nouveau_engctx_fini(&(d)->base, (s))
-
-#define _nouveau_mpeg_context_dtor _nouveau_engctx_dtor
-#define _nouveau_mpeg_context_init _nouveau_engctx_init
-#define _nouveau_mpeg_context_fini _nouveau_engctx_fini
-#define _nouveau_mpeg_context_rd32 _nouveau_engctx_rd32
-#define _nouveau_mpeg_context_wr32 _nouveau_engctx_wr32
-
-struct nouveau_mpeg {
-       struct nouveau_engine base;
-};
-
-#define nouveau_mpeg_create(p,e,c,d)                                           \
-       nouveau_engine_create((p), (e), (c), true, "PMPEG", "mpeg", (d))
-#define nouveau_mpeg_destroy(d)                                                \
-       nouveau_engine_destroy(&(d)->base)
-#define nouveau_mpeg_init(d)                                                   \
-       nouveau_engine_init(&(d)->base)
-#define nouveau_mpeg_fini(d,s)                                                 \
-       nouveau_engine_fini(&(d)->base, (s))
-
-#define _nouveau_mpeg_dtor _nouveau_engine_dtor
-#define _nouveau_mpeg_init _nouveau_engine_init
-#define _nouveau_mpeg_fini _nouveau_engine_fini
-
-extern struct nouveau_oclass nv31_mpeg_oclass;
-extern struct nouveau_oclass nv40_mpeg_oclass;
-extern struct nouveau_oclass nv44_mpeg_oclass;
-extern struct nouveau_oclass nv50_mpeg_oclass;
-extern struct nouveau_oclass nv84_mpeg_oclass;
-extern struct nouveau_ofuncs nv31_mpeg_ofuncs;
-extern struct nouveau_oclass nv31_mpeg_cclass;
-extern struct nouveau_oclass nv31_mpeg_sclass[];
-extern struct nouveau_oclass nv40_mpeg_sclass[];
-void nv31_mpeg_intr(struct nouveau_subdev *);
-void nv31_mpeg_tile_prog(struct nouveau_engine *, int);
-int  nv31_mpeg_init(struct nouveau_object *);
-
-extern struct nouveau_ofuncs nv50_mpeg_ofuncs;
-int  nv50_mpeg_context_ctor(struct nouveau_object *, struct nouveau_object *,
-                           struct nouveau_oclass *, void *, u32,
-                           struct nouveau_object **);
-void nv50_mpeg_intr(struct nouveau_subdev *);
-int  nv50_mpeg_init(struct nouveau_object *);
-
-#endif
diff --git a/drivers/gpu/drm/nouveau/core/include/engine/perfmon.h b/drivers/gpu/drm/nouveau/core/include/engine/perfmon.h
deleted file mode 100644 (file)
index 88cc812..0000000
+++ /dev/null
@@ -1,38 +0,0 @@
-#ifndef __NVKM_PERFMON_H__
-#define __NVKM_PERFMON_H__
-
-#include <core/device.h>
-#include <core/engine.h>
-#include <core/engctx.h>
-
-struct nouveau_perfdom;
-struct nouveau_perfctr;
-struct nouveau_perfmon {
-       struct nouveau_engine base;
-
-       struct nouveau_perfctx *context;
-       void *profile_data;
-
-       struct list_head domains;
-       u32 sequence;
-
-       /*XXX: temp for daemon backend */
-       u32 pwr[8];
-       u32 last;
-};
-
-static inline struct nouveau_perfmon *
-nouveau_perfmon(void *obj)
-{
-       return (void *)nv_device(obj)->subdev[NVDEV_ENGINE_PERFMON];
-}
-
-extern struct nouveau_oclass *nv40_perfmon_oclass;
-extern struct nouveau_oclass *nv50_perfmon_oclass;
-extern struct nouveau_oclass *nv84_perfmon_oclass;
-extern struct nouveau_oclass *nva3_perfmon_oclass;
-extern struct nouveau_oclass nvc0_perfmon_oclass;
-extern struct nouveau_oclass nve0_perfmon_oclass;
-extern struct nouveau_oclass nvf0_perfmon_oclass;
-
-#endif
diff --git a/drivers/gpu/drm/nouveau/core/include/engine/ppp.h b/drivers/gpu/drm/nouveau/core/include/engine/ppp.h
deleted file mode 100644 (file)
index 0a66781..0000000
+++ /dev/null
@@ -1,7 +0,0 @@
-#ifndef __NOUVEAU_PPP_H__
-#define __NOUVEAU_PPP_H__
-
-extern struct nouveau_oclass nv98_ppp_oclass;
-extern struct nouveau_oclass nvc0_ppp_oclass;
-
-#endif
diff --git a/drivers/gpu/drm/nouveau/core/include/engine/software.h b/drivers/gpu/drm/nouveau/core/include/engine/software.h
deleted file mode 100644 (file)
index 23a462b..0000000
+++ /dev/null
@@ -1,51 +0,0 @@
-#ifndef __NOUVEAU_SOFTWARE_H__
-#define __NOUVEAU_SOFTWARE_H__
-
-#include <core/engine.h>
-#include <core/engctx.h>
-
-struct nouveau_software_chan {
-       struct nouveau_engctx base;
-
-       int (*flip)(void *);
-       void *flip_data;
-};
-
-#define nouveau_software_context_create(p,e,c,d)                               \
-       nouveau_engctx_create((p), (e), (c), (p), 0, 0, 0, (d))
-#define nouveau_software_context_destroy(d)                                    \
-       nouveau_engctx_destroy(&(d)->base)
-#define nouveau_software_context_init(d)                                       \
-       nouveau_engctx_init(&(d)->base)
-#define nouveau_software_context_fini(d,s)                                     \
-       nouveau_engctx_fini(&(d)->base, (s))
-
-#define _nouveau_software_context_dtor _nouveau_engctx_dtor
-#define _nouveau_software_context_init _nouveau_engctx_init
-#define _nouveau_software_context_fini _nouveau_engctx_fini
-
-struct nouveau_software {
-       struct nouveau_engine base;
-};
-
-#define nouveau_software_create(p,e,c,d)                                       \
-       nouveau_engine_create((p), (e), (c), true, "SW", "software", (d))
-#define nouveau_software_destroy(d)                                            \
-       nouveau_engine_destroy(&(d)->base)
-#define nouveau_software_init(d)                                               \
-       nouveau_engine_init(&(d)->base)
-#define nouveau_software_fini(d,s)                                             \
-       nouveau_engine_fini(&(d)->base, (s))
-
-#define _nouveau_software_dtor _nouveau_engine_dtor
-#define _nouveau_software_init _nouveau_engine_init
-#define _nouveau_software_fini _nouveau_engine_fini
-
-extern struct nouveau_oclass *nv04_software_oclass;
-extern struct nouveau_oclass *nv10_software_oclass;
-extern struct nouveau_oclass *nv50_software_oclass;
-extern struct nouveau_oclass *nvc0_software_oclass;
-
-void nv04_software_intr(struct nouveau_subdev *);
-
-#endif
diff --git a/drivers/gpu/drm/nouveau/core/include/engine/vp.h b/drivers/gpu/drm/nouveau/core/include/engine/vp.h
deleted file mode 100644 (file)
index 39baebe..0000000
+++ /dev/null
@@ -1,9 +0,0 @@
-#ifndef __NOUVEAU_VP_H__
-#define __NOUVEAU_VP_H__
-
-extern struct nouveau_oclass nv84_vp_oclass;
-extern struct nouveau_oclass nv98_vp_oclass;
-extern struct nouveau_oclass nvc0_vp_oclass;
-extern struct nouveau_oclass nve0_vp_oclass;
-
-#endif
diff --git a/drivers/gpu/drm/nouveau/core/include/engine/xtensa.h b/drivers/gpu/drm/nouveau/core/include/engine/xtensa.h
deleted file mode 100644 (file)
index 306100f..0000000
+++ /dev/null
@@ -1,38 +0,0 @@
-#ifndef __NOUVEAU_XTENSA_H__
-#define __NOUVEAU_XTENSA_H__
-
-#include <core/engine.h>
-#include <core/engctx.h>
-#include <core/gpuobj.h>
-
-struct nouveau_xtensa {
-       struct nouveau_engine base;
-
-       u32 addr;
-       struct nouveau_gpuobj *gpu_fw;
-       u32 fifo_val;
-       u32 unkd28;
-};
-
-#define nouveau_xtensa_create(p,e,c,b,d,i,f,r)                         \
-       nouveau_xtensa_create_((p), (e), (c), (b), (d), (i), (f),       \
-                              sizeof(**r),(void **)r)
-
-int _nouveau_xtensa_engctx_ctor(struct nouveau_object *,
-                               struct nouveau_object *,
-                               struct nouveau_oclass *, void *, u32,
-                               struct nouveau_object **);
-
-void _nouveau_xtensa_intr(struct nouveau_subdev *);
-int nouveau_xtensa_create_(struct nouveau_object *,
-                          struct nouveau_object *,
-                          struct nouveau_oclass *, u32, bool,
-                          const char *, const char *,
-                          int, void **);
-#define _nouveau_xtensa_dtor _nouveau_engine_dtor
-int _nouveau_xtensa_init(struct nouveau_object *);
-int _nouveau_xtensa_fini(struct nouveau_object *, bool);
-u32  _nouveau_xtensa_rd32(struct nouveau_object *, u64);
-void _nouveau_xtensa_wr32(struct nouveau_object *, u64, u32);
-
-#endif
diff --git a/drivers/gpu/drm/nouveau/core/include/nvif/class.h b/drivers/gpu/drm/nouveau/core/include/nvif/class.h
deleted file mode 120000 (symlink)
index f1ac485..0000000
+++ /dev/null
@@ -1 +0,0 @@
-../../../nvif/class.h
\ No newline at end of file
diff --git a/drivers/gpu/drm/nouveau/core/include/nvif/event.h b/drivers/gpu/drm/nouveau/core/include/nvif/event.h
deleted file mode 120000 (symlink)
index 1b79853..0000000
+++ /dev/null
@@ -1 +0,0 @@
-../../../nvif/event.h
\ No newline at end of file
diff --git a/drivers/gpu/drm/nouveau/core/include/nvif/ioctl.h b/drivers/gpu/drm/nouveau/core/include/nvif/ioctl.h
deleted file mode 120000 (symlink)
index 8569c86..0000000
+++ /dev/null
@@ -1 +0,0 @@
-../../../nvif/ioctl.h
\ No newline at end of file
diff --git a/drivers/gpu/drm/nouveau/core/include/nvif/unpack.h b/drivers/gpu/drm/nouveau/core/include/nvif/unpack.h
deleted file mode 120000 (symlink)
index 69d9929..0000000
+++ /dev/null
@@ -1 +0,0 @@
-../../../nvif/unpack.h
\ No newline at end of file
diff --git a/drivers/gpu/drm/nouveau/core/include/subdev/bar.h b/drivers/gpu/drm/nouveau/core/include/subdev/bar.h
deleted file mode 100644 (file)
index 257ddf6..0000000
+++ /dev/null
@@ -1,37 +0,0 @@
-#ifndef __NOUVEAU_BAR_H__
-#define __NOUVEAU_BAR_H__
-
-#include <core/subdev.h>
-#include <core/device.h>
-
-struct nouveau_mem;
-struct nouveau_vma;
-
-struct nouveau_bar {
-       struct nouveau_subdev base;
-
-       int (*alloc)(struct nouveau_bar *, struct nouveau_object *,
-                    struct nouveau_mem *, struct nouveau_object **);
-
-       int (*kmap)(struct nouveau_bar *, struct nouveau_mem *,
-                   u32 flags, struct nouveau_vma *);
-       int (*umap)(struct nouveau_bar *, struct nouveau_mem *,
-                   u32 flags, struct nouveau_vma *);
-       void (*unmap)(struct nouveau_bar *, struct nouveau_vma *);
-       void (*flush)(struct nouveau_bar *);
-
-       /* whether the BAR supports to be ioremapped WC or should be uncached */
-       bool iomap_uncached;
-};
-
-static inline struct nouveau_bar *
-nouveau_bar(void *obj)
-{
-       return (void *)nv_device(obj)->subdev[NVDEV_SUBDEV_BAR];
-}
-
-extern struct nouveau_oclass nv50_bar_oclass;
-extern struct nouveau_oclass nvc0_bar_oclass;
-extern struct nouveau_oclass gk20a_bar_oclass;
-
-#endif
diff --git a/drivers/gpu/drm/nouveau/core/include/subdev/bios.h b/drivers/gpu/drm/nouveau/core/include/subdev/bios.h
deleted file mode 100644 (file)
index 5bd1ca8..0000000
+++ /dev/null
@@ -1,35 +0,0 @@
-#ifndef __NOUVEAU_BIOS_H__
-#define __NOUVEAU_BIOS_H__
-
-#include <core/subdev.h>
-#include <core/device.h>
-
-struct nouveau_bios {
-       struct nouveau_subdev base;
-       u32 size;
-       u8 *data;
-
-       u32 bmp_offset;
-       u32 bit_offset;
-
-       struct {
-               u8 major;
-               u8 chip;
-               u8 minor;
-               u8 micro;
-               u8 patch;
-       } version;
-};
-
-static inline struct nouveau_bios *
-nouveau_bios(void *obj)
-{
-       return (void *)nv_device(obj)->subdev[NVDEV_SUBDEV_VBIOS];
-}
-
-u8  nvbios_checksum(const u8 *data, int size);
-u16 nvbios_findstr(const u8 *data, int size, const char *str, int len);
-
-extern struct nouveau_oclass nouveau_bios_oclass;
-
-#endif
diff --git a/drivers/gpu/drm/nouveau/core/include/subdev/bios/M0203.h b/drivers/gpu/drm/nouveau/core/include/subdev/bios/M0203.h
deleted file mode 100644 (file)
index 1f84d36..0000000
+++ /dev/null
@@ -1,31 +0,0 @@
-#ifndef __NVBIOS_M0203_H__
-#define __NVBIOS_M0203_H__
-
-struct nvbios_M0203T {
-#define M0203T_TYPE_RAMCFG 0x00
-       u8  type;
-       u16 pointer;
-};
-
-u32 nvbios_M0203Te(struct nouveau_bios *, u8 *ver, u8 *hdr, u8 *cnt, u8 *len);
-u32 nvbios_M0203Tp(struct nouveau_bios *, u8 *ver, u8 *hdr, u8 *cnt, u8 *len,
-                  struct nvbios_M0203T *);
-
-struct nvbios_M0203E {
-#define M0203E_TYPE_DDR2  0x0
-#define M0203E_TYPE_DDR3  0x1
-#define M0203E_TYPE_GDDR3 0x2
-#define M0203E_TYPE_GDDR5 0x3
-#define M0203E_TYPE_SKIP  0xf
-       u8 type;
-       u8 strap;
-       u8 group;
-};
-
-u32 nvbios_M0203Ee(struct nouveau_bios *, int idx, u8 *ver, u8 *hdr);
-u32 nvbios_M0203Ep(struct nouveau_bios *, int idx, u8 *ver, u8 *hdr,
-                  struct nvbios_M0203E *);
-u32 nvbios_M0203Em(struct nouveau_bios *, u8 ramcfg, u8 *ver, u8 *hdr,
-                  struct nvbios_M0203E *);
-
-#endif
diff --git a/drivers/gpu/drm/nouveau/core/include/subdev/bios/M0205.h b/drivers/gpu/drm/nouveau/core/include/subdev/bios/M0205.h
deleted file mode 100644 (file)
index e171120..0000000
+++ /dev/null
@@ -1,32 +0,0 @@
-#ifndef __NVBIOS_M0205_H__
-#define __NVBIOS_M0205_H__
-
-struct nvbios_M0205T {
-       u16 freq;
-};
-
-u32 nvbios_M0205Te(struct nouveau_bios *,
-                  u8 *ver, u8 *hdr, u8 *cnt, u8 *len, u8 *snr, u8 *ssz);
-u32 nvbios_M0205Tp(struct nouveau_bios *,
-                  u8 *ver, u8 *hdr, u8 *cnt, u8 *len, u8 *snr, u8 *ssz,
-                  struct nvbios_M0205T *);
-
-struct nvbios_M0205E {
-       u8 type;
-};
-
-u32 nvbios_M0205Ee(struct nouveau_bios *, int idx,
-                  u8 *ver, u8 *hdr, u8 *cnt, u8 *len);
-u32 nvbios_M0205Ep(struct nouveau_bios *, int idx,
-                  u8 *ver, u8 *hdr, u8 *cnt, u8 *len,
-                  struct nvbios_M0205E *);
-
-struct nvbios_M0205S {
-       u8 data;
-};
-
-u32 nvbios_M0205Se(struct nouveau_bios *, int ent, int idx, u8 *ver, u8 *hdr);
-u32 nvbios_M0205Sp(struct nouveau_bios *, int ent, int idx, u8 *ver, u8 *hdr,
-                  struct nvbios_M0205S *);
-
-#endif
diff --git a/drivers/gpu/drm/nouveau/core/include/subdev/bios/M0209.h b/drivers/gpu/drm/nouveau/core/include/subdev/bios/M0209.h
deleted file mode 100644 (file)
index 67dc50d..0000000
+++ /dev/null
@@ -1,30 +0,0 @@
-#ifndef __NVBIOS_M0209_H__
-#define __NVBIOS_M0209_H__
-
-u32 nvbios_M0209Te(struct nouveau_bios *,
-                  u8 *ver, u8 *hdr, u8 *cnt, u8 *len, u8 *snr, u8 *ssz);
-
-struct nvbios_M0209E {
-       u8 v00_40;
-       u8 bits;
-       u8 modulo;
-       u8 v02_40;
-       u8 v02_07;
-       u8 v03;
-};
-
-u32 nvbios_M0209Ee(struct nouveau_bios *, int idx,
-                  u8 *ver, u8 *hdr, u8 *cnt, u8 *len);
-u32 nvbios_M0209Ep(struct nouveau_bios *, int idx,
-                  u8 *ver, u8 *hdr, u8 *cnt, u8 *len,
-                  struct nvbios_M0209E *);
-
-struct nvbios_M0209S {
-       u32 data[0x200];
-};
-
-u32 nvbios_M0209Se(struct nouveau_bios *, int ent, int idx, u8 *ver, u8 *hdr);
-u32 nvbios_M0209Sp(struct nouveau_bios *, int ent, int idx, u8 *ver, u8 *hdr,
-                  struct nvbios_M0209S *);
-
-#endif
diff --git a/drivers/gpu/drm/nouveau/core/include/subdev/bios/P0260.h b/drivers/gpu/drm/nouveau/core/include/subdev/bios/P0260.h
deleted file mode 100644 (file)
index bba01ab..0000000
+++ /dev/null
@@ -1,23 +0,0 @@
-#ifndef __NVBIOS_P0260_H__
-#define __NVBIOS_P0260_H__
-
-u32 nvbios_P0260Te(struct nouveau_bios *,
-                  u8 *ver, u8 *hdr, u8 *cnt, u8 *len, u8 *xnr, u8 *xsz);
-
-struct nvbios_P0260E {
-       u32 data;
-};
-
-u32 nvbios_P0260Ee(struct nouveau_bios *, int idx, u8 *ver, u8 *hdr);
-u32 nvbios_P0260Ep(struct nouveau_bios *, int idx, u8 *ver, u8 *hdr,
-                  struct nvbios_P0260E *);
-
-struct nvbios_P0260X {
-       u32 data;
-};
-
-u32 nvbios_P0260Xe(struct nouveau_bios *, int idx, u8 *ver, u8 *hdr);
-u32 nvbios_P0260Xp(struct nouveau_bios *, int idx, u8 *ver, u8 *hdr,
-                  struct nvbios_P0260X *);
-
-#endif
diff --git a/drivers/gpu/drm/nouveau/core/include/subdev/bios/bit.h b/drivers/gpu/drm/nouveau/core/include/subdev/bios/bit.h
deleted file mode 100644 (file)
index 73f060b..0000000
+++ /dev/null
@@ -1,13 +0,0 @@
-#ifndef __NVBIOS_BIT_H__
-#define __NVBIOS_BIT_H__
-
-struct bit_entry {
-       u8  id;
-       u8  version;
-       u16 length;
-       u16 offset;
-};
-
-int bit_entry(struct nouveau_bios *, u8 id, struct bit_entry *);
-
-#endif
diff --git a/drivers/gpu/drm/nouveau/core/include/subdev/bios/bmp.h b/drivers/gpu/drm/nouveau/core/include/subdev/bios/bmp.h
deleted file mode 100644 (file)
index 10e4dbc..0000000
+++ /dev/null
@@ -1,39 +0,0 @@
-#ifndef __NVBIOS_BMP_H__
-#define __NVBIOS_BMP_H__
-
-static inline u16
-bmp_version(struct nouveau_bios *bios)
-{
-       if (bios->bmp_offset) {
-               return nv_ro08(bios, bios->bmp_offset + 5) << 8 |
-                      nv_ro08(bios, bios->bmp_offset + 6);
-       }
-
-       return 0x0000;
-}
-
-static inline u16
-bmp_mem_init_table(struct nouveau_bios *bios)
-{
-       if (bmp_version(bios) >= 0x0300)
-               return nv_ro16(bios, bios->bmp_offset + 24);
-       return 0x0000;
-}
-
-static inline u16
-bmp_sdr_seq_table(struct nouveau_bios *bios)
-{
-       if (bmp_version(bios) >= 0x0300)
-               return nv_ro16(bios, bios->bmp_offset + 26);
-       return 0x0000;
-}
-
-static inline u16
-bmp_ddr_seq_table(struct nouveau_bios *bios)
-{
-       if (bmp_version(bios) >= 0x0300)
-               return nv_ro16(bios, bios->bmp_offset + 28);
-       return 0x0000;
-}
-
-#endif
diff --git a/drivers/gpu/drm/nouveau/core/include/subdev/bios/boost.h b/drivers/gpu/drm/nouveau/core/include/subdev/bios/boost.h
deleted file mode 100644 (file)
index 662b207..0000000
+++ /dev/null
@@ -1,29 +0,0 @@
-#ifndef __NVBIOS_BOOST_H__
-#define __NVBIOS_BOOST_H__
-
-u16 nvbios_boostTe(struct nouveau_bios *, u8 *, u8 *, u8 *, u8 *, u8 *, u8 *);
-
-struct nvbios_boostE {
-       u8  pstate;
-       u32 min;
-       u32 max;
-};
-
-u16 nvbios_boostEe(struct nouveau_bios *, int idx, u8 *, u8 *, u8 *, u8 *);
-u16 nvbios_boostEp(struct nouveau_bios *, int idx, u8 *, u8 *, u8 *, u8 *,
-                  struct nvbios_boostE *);
-u16 nvbios_boostEm(struct nouveau_bios *, u8, u8 *, u8 *, u8 *, u8 *,
-                  struct nvbios_boostE *);
-
-struct nvbios_boostS {
-       u8  domain;
-       u8  percent;
-       u32 min;
-       u32 max;
-};
-
-u16 nvbios_boostSe(struct nouveau_bios *, int, u16, u8 *, u8 *, u8, u8);
-u16 nvbios_boostSp(struct nouveau_bios *, int, u16, u8 *, u8 *, u8, u8,
-                  struct nvbios_boostS *);
-
-#endif
diff --git a/drivers/gpu/drm/nouveau/core/include/subdev/bios/conn.h b/drivers/gpu/drm/nouveau/core/include/subdev/bios/conn.h
deleted file mode 100644 (file)
index f3930c2..0000000
+++ /dev/null
@@ -1,46 +0,0 @@
-#ifndef __NVBIOS_CONN_H__
-#define __NVBIOS_CONN_H__
-
-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_DMS59_0 = 0x38,
-       DCB_CONNECTOR_DMS59_1 = 0x39,
-       DCB_CONNECTOR_LVDS = 0x40,
-       DCB_CONNECTOR_LVDS_SPWG = 0x41,
-       DCB_CONNECTOR_DP = 0x46,
-       DCB_CONNECTOR_eDP = 0x47,
-       DCB_CONNECTOR_HDMI_0 = 0x60,
-       DCB_CONNECTOR_HDMI_1 = 0x61,
-       DCB_CONNECTOR_HDMI_C = 0x63,
-       DCB_CONNECTOR_DMS59_DP0 = 0x64,
-       DCB_CONNECTOR_DMS59_DP1 = 0x65,
-       DCB_CONNECTOR_NONE = 0xff
-};
-
-struct nvbios_connT {
-};
-
-u32 nvbios_connTe(struct nouveau_bios *bios, u8 *ver, u8 *hdr, u8 *cnt, u8 *len);
-u32 nvbios_connTp(struct nouveau_bios *bios, u8 *ver, u8 *hdr, u8 *cnt, u8 *len,
-                 struct nvbios_connT *info);
-
-struct nvbios_connE {
-       u8 type;
-       u8 location;
-       u8 hpd;
-       u8 dp;
-       u8 di;
-       u8 sr;
-       u8 lcdid;
-};
-
-u32 nvbios_connEe(struct nouveau_bios *bios, u8 idx, u8 *ver, u8 *hdr);
-u32 nvbios_connEp(struct nouveau_bios *bios, u8 idx, u8 *ver, u8 *hdr,
-                 struct nvbios_connE *info);
-
-#endif
diff --git a/drivers/gpu/drm/nouveau/core/include/subdev/bios/cstep.h b/drivers/gpu/drm/nouveau/core/include/subdev/bios/cstep.h
deleted file mode 100644 (file)
index a80a438..0000000
+++ /dev/null
@@ -1,28 +0,0 @@
-#ifndef __NVBIOS_CSTEP_H__
-#define __NVBIOS_CSTEP_H__
-
-u16 nvbios_cstepTe(struct nouveau_bios *,
-                  u8 *ver, u8 *hdr, u8 *cnt, u8 *len, u8 *xnr, u8 *xsz);
-
-struct nvbios_cstepE {
-       u8  pstate;
-       u8  index;
-};
-
-u16 nvbios_cstepEe(struct nouveau_bios *, int idx, u8 *ver, u8 *hdr);
-u16 nvbios_cstepEp(struct nouveau_bios *, int idx, u8 *ver, u8 *hdr,
-                  struct nvbios_cstepE *);
-u16 nvbios_cstepEm(struct nouveau_bios *, u8 pstate, u8 *ver, u8 *hdr,
-                  struct nvbios_cstepE *);
-
-struct nvbios_cstepX {
-       u32 freq;
-       u8  unkn[2];
-       u8  voltage;
-};
-
-u16 nvbios_cstepXe(struct nouveau_bios *, int idx, u8 *ver, u8 *hdr);
-u16 nvbios_cstepXp(struct nouveau_bios *, int idx, u8 *ver, u8 *hdr,
-                  struct nvbios_cstepX *);
-
-#endif
diff --git a/drivers/gpu/drm/nouveau/core/include/subdev/bios/dcb.h b/drivers/gpu/drm/nouveau/core/include/subdev/bios/dcb.h
deleted file mode 100644 (file)
index 123270e..0000000
+++ /dev/null
@@ -1,69 +0,0 @@
-#ifndef __NVBIOS_DCB_H__
-#define __NVBIOS_DCB_H__
-
-struct nouveau_bios;
-
-enum dcb_output_type {
-       DCB_OUTPUT_ANALOG       = 0x0,
-       DCB_OUTPUT_TV           = 0x1,
-       DCB_OUTPUT_TMDS         = 0x2,
-       DCB_OUTPUT_LVDS         = 0x3,
-       DCB_OUTPUT_DP           = 0x6,
-       DCB_OUTPUT_EOL          = 0xe,
-       DCB_OUTPUT_UNUSED       = 0xf,
-       DCB_OUTPUT_ANY = -1,
-};
-
-struct dcb_output {
-       int index;      /* may not be raw dcb index if merging has happened */
-       u16 hasht;
-       u16 hashm;
-       enum dcb_output_type type;
-       uint8_t i2c_index;
-       uint8_t heads;
-       uint8_t connector;
-       uint8_t bus;
-       uint8_t location;
-       uint8_t or;
-       uint8_t link;
-       bool duallink_possible;
-       uint8_t extdev;
-       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;
-};
-
-u16 dcb_table(struct nouveau_bios *, u8 *ver, u8 *hdr, u8 *ent, u8 *len);
-u16 dcb_outp(struct nouveau_bios *, u8 idx, u8 *ver, u8 *len);
-u16 dcb_outp_parse(struct nouveau_bios *, u8 idx, u8 *, u8 *,
-                  struct dcb_output *);
-u16 dcb_outp_match(struct nouveau_bios *, u16 type, u16 mask, u8 *, u8 *,
-                  struct dcb_output *);
-int dcb_outp_foreach(struct nouveau_bios *, void *data, int (*exec)
-                    (struct nouveau_bios *, void *, int index, u16 entry));
-
-#endif
diff --git a/drivers/gpu/drm/nouveau/core/include/subdev/bios/disp.h b/drivers/gpu/drm/nouveau/core/include/subdev/bios/disp.h
deleted file mode 100644 (file)
index c35937e..0000000
+++ /dev/null
@@ -1,48 +0,0 @@
-#ifndef __NVBIOS_DISP_H__
-#define __NVBIOS_DISP_H__
-
-u16 nvbios_disp_table(struct nouveau_bios *,
-                     u8 *ver, u8 *hdr, u8 *cnt, u8 *len, u8 *sub);
-
-struct nvbios_disp {
-       u16 data;
-};
-
-u16 nvbios_disp_entry(struct nouveau_bios *, u8 idx,
-                     u8 *ver, u8 *hdr__, u8 *sub);
-u16 nvbios_disp_parse(struct nouveau_bios *, u8 idx,
-                     u8 *ver, u8 *hdr__, u8 *sub,
-                     struct nvbios_disp *);
-
-struct nvbios_outp {
-       u16 type;
-       u16 mask;
-       u16 script[3];
-};
-
-u16 nvbios_outp_entry(struct nouveau_bios *, u8 idx,
-                     u8 *ver, u8 *hdr, u8 *cnt, u8 *len);
-u16 nvbios_outp_parse(struct nouveau_bios *, u8 idx,
-                     u8 *ver, u8 *hdr, u8 *cnt, u8 *len,
-                     struct nvbios_outp *);
-u16 nvbios_outp_match(struct nouveau_bios *, u16 type, u16 mask,
-                     u8 *ver, u8 *hdr, u8 *cnt, u8 *len,
-                     struct nvbios_outp *);
-
-
-struct nvbios_ocfg {
-       u16 match;
-       u16 clkcmp[2];
-};
-
-u16 nvbios_ocfg_entry(struct nouveau_bios *, u16 outp, u8 idx,
-                     u8 *ver, u8 *hdr, u8 *cnt, u8 *len);
-u16 nvbios_ocfg_parse(struct nouveau_bios *, u16 outp, u8 idx,
-                     u8 *ver, u8 *hdr, u8 *cnt, u8 *len,
-                     struct nvbios_ocfg *);
-u16 nvbios_ocfg_match(struct nouveau_bios *, u16 outp, u16 type,
-                     u8 *ver, u8 *hdr, u8 *cnt, u8 *len,
-                     struct nvbios_ocfg *);
-u16 nvbios_oclk_match(struct nouveau_bios *, u16 cmp, u32 khz);
-
-#endif
diff --git a/drivers/gpu/drm/nouveau/core/include/subdev/bios/dp.h b/drivers/gpu/drm/nouveau/core/include/subdev/bios/dp.h
deleted file mode 100644 (file)
index 728206e..0000000
+++ /dev/null
@@ -1,35 +0,0 @@
-#ifndef __NVBIOS_DP_H__
-#define __NVBIOS_DP_H__
-
-struct nvbios_dpout {
-       u16 type;
-       u16 mask;
-       u8  flags;
-       u32 script[5];
-       u32 lnkcmp;
-};
-
-u16 nvbios_dpout_parse(struct nouveau_bios *, u8 idx,
-                      u8 *ver, u8 *hdr, u8 *cnt, u8 *len,
-                      struct nvbios_dpout *);
-u16 nvbios_dpout_match(struct nouveau_bios *, u16 type, u16 mask,
-                      u8 *ver, u8 *hdr, u8 *cnt, u8 *len,
-                      struct nvbios_dpout *);
-
-struct nvbios_dpcfg {
-       u8 pc;
-       u8 dc;
-       u8 pe;
-       u8 tx_pu;
-};
-
-u16
-nvbios_dpcfg_parse(struct nouveau_bios *, u16 outp, u8 idx,
-                  u8 *ver, u8 *hdr, u8 *cnt, u8 *len,
-                  struct nvbios_dpcfg *);
-u16
-nvbios_dpcfg_match(struct nouveau_bios *, u16 outp, u8 pc, u8 vs, u8 pe,
-                  u8 *ver, u8 *hdr, u8 *cnt, u8 *len,
-                  struct nvbios_dpcfg *);
-
-#endif
diff --git a/drivers/gpu/drm/nouveau/core/include/subdev/bios/extdev.h b/drivers/gpu/drm/nouveau/core/include/subdev/bios/extdev.h
deleted file mode 100644 (file)
index 949fee3..0000000
+++ /dev/null
@@ -1,30 +0,0 @@
-#ifndef __NVBIOS_EXTDEV_H__
-#define __NVBIOS_EXTDEV_H__
-
-struct nouveau_bios;
-
-enum nvbios_extdev_type {
-       NVBIOS_EXTDEV_LM89              = 0x02,
-       NVBIOS_EXTDEV_VT1103M           = 0x40,
-       NVBIOS_EXTDEV_PX3540            = 0x41,
-       NVBIOS_EXTDEV_VT1105M           = 0x42, /* or close enough... */
-       NVBIOS_EXTDEV_ADT7473           = 0x70, /* can also be a LM64 */
-       NVBIOS_EXTDEV_HDCP_EEPROM       = 0x90,
-       NVBIOS_EXTDEV_NONE              = 0xff,
-};
-
-struct nvbios_extdev_func {
-       u8 type;
-       u8 addr;
-       u8 bus;
-};
-
-int
-nvbios_extdev_parse(struct nouveau_bios *, int, struct nvbios_extdev_func *);
-
-int
-nvbios_extdev_find(struct nouveau_bios *, enum nvbios_extdev_type,
-                  struct nvbios_extdev_func *);
-
-
-#endif
diff --git a/drivers/gpu/drm/nouveau/core/include/subdev/bios/fan.h b/drivers/gpu/drm/nouveau/core/include/subdev/bios/fan.h
deleted file mode 100644 (file)
index 119d087..0000000
+++ /dev/null
@@ -1,8 +0,0 @@
-#ifndef __NVBIOS_FAN_H__
-#define __NVBIOS_FAN_H__
-
-#include <subdev/bios/therm.h>
-
-u16 nvbios_fan_parse(struct nouveau_bios *bios, struct nvbios_therm_fan *fan);
-
-#endif
diff --git a/drivers/gpu/drm/nouveau/core/include/subdev/bios/gpio.h b/drivers/gpu/drm/nouveau/core/include/subdev/bios/gpio.h
deleted file mode 100644 (file)
index c7b2e58..0000000
+++ /dev/null
@@ -1,48 +0,0 @@
-#ifndef __NVBIOS_GPIO_H__
-#define __NVBIOS_GPIO_H__
-
-enum dcb_gpio_func_name {
-       DCB_GPIO_PANEL_POWER = 0x01,
-       DCB_GPIO_TVDAC0 = 0x0c,
-       DCB_GPIO_TVDAC1 = 0x2d,
-       DCB_GPIO_FAN = 0x09,
-       DCB_GPIO_FAN_SENSE = 0x3d,
-       DCB_GPIO_UNUSED = 0xff,
-       DCB_GPIO_VID0 = 0x04,
-       DCB_GPIO_VID1 = 0x05,
-       DCB_GPIO_VID2 = 0x06,
-       DCB_GPIO_VID3 = 0x1a,
-       DCB_GPIO_VID4 = 0x73,
-       DCB_GPIO_VID5 = 0x74,
-       DCB_GPIO_VID6 = 0x75,
-       DCB_GPIO_VID7 = 0x76,
-};
-
-#define DCB_GPIO_LOG_DIR     0x02
-#define DCB_GPIO_LOG_DIR_OUT 0x00
-#define DCB_GPIO_LOG_DIR_IN  0x02
-#define DCB_GPIO_LOG_VAL     0x01
-#define DCB_GPIO_LOG_VAL_LO  0x00
-#define DCB_GPIO_LOG_VAL_HI  0x01
-
-struct dcb_gpio_func {
-       u8 func;
-       u8 line;
-       u8 log[2];
-
-       /* so far, "param" seems to only have an influence on PWM-related
-        * GPIOs such as FAN_CONTROL and PANEL_BACKLIGHT_LEVEL.
-        * if param equals 1, hardware PWM is available
-        * if param equals 0, the host should toggle the GPIO itself
-        */
-       u8 param;
-};
-
-u16 dcb_gpio_table(struct nouveau_bios *, u8 *ver, u8 *hdr, u8 *cnt, u8 *len);
-u16 dcb_gpio_entry(struct nouveau_bios *, int idx, int ent, u8 *ver, u8 *len);
-u16 dcb_gpio_parse(struct nouveau_bios *, int idx, int ent, u8 *ver, u8 *len,
-                  struct dcb_gpio_func *);
-u16 dcb_gpio_match(struct nouveau_bios *, int idx, u8 func, u8 line,
-                  u8 *ver, u8 *len, struct dcb_gpio_func *);
-
-#endif
diff --git a/drivers/gpu/drm/nouveau/core/include/subdev/bios/i2c.h b/drivers/gpu/drm/nouveau/core/include/subdev/bios/i2c.h
deleted file mode 100644 (file)
index c9bb112..0000000
+++ /dev/null
@@ -1,29 +0,0 @@
-#ifndef __NVBIOS_I2C_H__
-#define __NVBIOS_I2C_H__
-
-struct nouveau_bios;
-
-enum dcb_i2c_type {
-       /* matches bios type field prior to ccb 4.1 */
-       DCB_I2C_NV04_BIT = 0x00,
-       DCB_I2C_NV4E_BIT = 0x04,
-       DCB_I2C_NVIO_BIT = 0x05,
-       DCB_I2C_NVIO_AUX = 0x06,
-       /* made up - mostly */
-       DCB_I2C_PMGR     = 0x80,
-       DCB_I2C_UNUSED   = 0xff
-};
-
-struct dcb_i2c_entry {
-       enum dcb_i2c_type type;
-       u8 drive;
-       u8 sense;
-       u8 share;
-       u8 auxch;
-};
-
-u16 dcb_i2c_table(struct nouveau_bios *, u8 *ver, u8 *hdr, u8 *cnt, u8 *len);
-u16 dcb_i2c_entry(struct nouveau_bios *, u8 index, u8 *ver, u8 *len);
-int dcb_i2c_parse(struct nouveau_bios *, u8 index, struct dcb_i2c_entry *);
-
-#endif
diff --git a/drivers/gpu/drm/nouveau/core/include/subdev/bios/image.h b/drivers/gpu/drm/nouveau/core/include/subdev/bios/image.h
deleted file mode 100644 (file)
index 3348b45..0000000
+++ /dev/null
@@ -1,13 +0,0 @@
-#ifndef __NVBIOS_IMAGE_H__
-#define __NVBIOS_IMAGE_H__
-
-struct nvbios_image {
-       u32  base;
-       u32  size;
-       u8   type;
-       bool last;
-};
-
-bool nvbios_image(struct nouveau_bios *, int, struct nvbios_image *);
-
-#endif
diff --git a/drivers/gpu/drm/nouveau/core/include/subdev/bios/init.h b/drivers/gpu/drm/nouveau/core/include/subdev/bios/init.h
deleted file mode 100644 (file)
index ca2f6bf..0000000
+++ /dev/null
@@ -1,22 +0,0 @@
-#ifndef __NVBIOS_INIT_H__
-#define __NVBIOS_INIT_H__
-
-struct nvbios_init {
-       struct nouveau_subdev *subdev;
-       struct nouveau_bios *bios;
-       u16 offset;
-       struct dcb_output *outp;
-       int crtc;
-
-       /* internal state used during parsing */
-       u8 execute;
-       u32 nested;
-       u16 repeat;
-       u16 repend;
-       u32 ramcfg;
-};
-
-int nvbios_exec(struct nvbios_init *);
-int nvbios_init(struct nouveau_subdev *, bool execute);
-
-#endif
diff --git a/drivers/gpu/drm/nouveau/core/include/subdev/bios/mxm.h b/drivers/gpu/drm/nouveau/core/include/subdev/bios/mxm.h
deleted file mode 100644 (file)
index 5572e60..0000000
+++ /dev/null
@@ -1,9 +0,0 @@
-#ifndef __NVBIOS_MXM_H__
-#define __NVBIOS_MXM_H__
-
-u16 mxm_table(struct nouveau_bios *, u8 *ver, u8 *hdr);
-
-u8  mxm_sor_map(struct nouveau_bios *, u8 conn);
-u8  mxm_ddc_map(struct nouveau_bios *, u8 port);
-
-#endif
diff --git a/drivers/gpu/drm/nouveau/core/include/subdev/bios/npde.h b/drivers/gpu/drm/nouveau/core/include/subdev/bios/npde.h
deleted file mode 100644 (file)
index b18413d..0000000
+++ /dev/null
@@ -1,12 +0,0 @@
-#ifndef __NVBIOS_NPDE_H__
-#define __NVBIOS_NPDE_H__
-
-struct nvbios_npdeT {
-       u32 image_size;
-       bool last;
-};
-
-u32 nvbios_npdeTe(struct nouveau_bios *, u32);
-u32 nvbios_npdeTp(struct nouveau_bios *, u32, struct nvbios_npdeT *);
-
-#endif
diff --git a/drivers/gpu/drm/nouveau/core/include/subdev/bios/pcir.h b/drivers/gpu/drm/nouveau/core/include/subdev/bios/pcir.h
deleted file mode 100644 (file)
index 3d634a0..0000000
+++ /dev/null
@@ -1,18 +0,0 @@
-#ifndef __NVBIOS_PCIR_H__
-#define __NVBIOS_PCIR_H__
-
-struct nvbios_pcirT {
-       u16 vendor_id;
-       u16 device_id;
-       u8  class_code[3];
-       u32 image_size;
-       u16 image_rev;
-       u8  image_type;
-       bool last;
-};
-
-u32 nvbios_pcirTe(struct nouveau_bios *, u32, u8 *ver, u16 *hdr);
-u32 nvbios_pcirTp(struct nouveau_bios *, u32, u8 *ver, u16 *hdr,
-                 struct nvbios_pcirT *);
-
-#endif
diff --git a/drivers/gpu/drm/nouveau/core/include/subdev/bios/perf.h b/drivers/gpu/drm/nouveau/core/include/subdev/bios/perf.h
deleted file mode 100644 (file)
index 16ff06e..0000000
+++ /dev/null
@@ -1,47 +0,0 @@
-#ifndef __NVBIOS_PERF_H__
-#define __NVBIOS_PERF_H__
-
-struct nouveau_bios;
-
-u16 nvbios_perf_table(struct nouveau_bios *, u8 *ver, u8 *hdr,
-                     u8 *cnt, u8 *len, u8 *snr, u8 *ssz);
-
-struct nvbios_perfE {
-       u8  pstate;
-       u8  fanspeed;
-       u8  voltage;
-       u32 core;
-       u32 shader;
-       u32 memory;
-       u32 vdec;
-       u32 disp;
-       u32 script;
-};
-
-u16 nvbios_perf_entry(struct nouveau_bios *, int idx,
-                     u8 *ver, u8 *hdr, u8 *cnt, u8 *len);
-u16 nvbios_perfEp(struct nouveau_bios *, int idx,
-                 u8 *ver, u8 *hdr, u8 *cnt, u8 *len, struct nvbios_perfE *);
-
-struct nvbios_perfS {
-       union {
-               struct {
-                       u32 freq;
-               } v40;
-       };
-};
-
-u32 nvbios_perfSe(struct nouveau_bios *, u32 data, int idx,
-                 u8 *ver, u8 *hdr, u8 cnt, u8 len);
-u32 nvbios_perfSp(struct nouveau_bios *, u32 data, int idx,
-                 u8 *ver, u8 *hdr, u8 cnt, u8 len, struct nvbios_perfS *);
-
-struct nvbios_perf_fan {
-       u32 pwm_divisor;
-};
-
-int
-nvbios_perf_fan_parse(struct nouveau_bios *, struct nvbios_perf_fan *);
-
-
-#endif
diff --git a/drivers/gpu/drm/nouveau/core/include/subdev/bios/pll.h b/drivers/gpu/drm/nouveau/core/include/subdev/bios/pll.h
deleted file mode 100644 (file)
index b2f3d4d..0000000
+++ /dev/null
@@ -1,79 +0,0 @@
-#ifndef __NVBIOS_PLL_H__
-#define __NVBIOS_PLL_H__
-
-/*XXX: kill me */
-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;
-};
-
-struct nouveau_bios;
-
-/* 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 nvbios_pll_type {
-       PLL_CORE   = 0x01,
-       PLL_SHADER = 0x02,
-       PLL_UNK03  = 0x03,
-       PLL_MEMORY = 0x04,
-       PLL_VDEC   = 0x05,
-       PLL_UNK40  = 0x40,
-       PLL_UNK41  = 0x41,
-       PLL_UNK42  = 0x42,
-       PLL_VPLL0  = 0x80,
-       PLL_VPLL1  = 0x81,
-       PLL_VPLL2  = 0x82,
-       PLL_VPLL3  = 0x83,
-       PLL_MAX    = 0xff
-};
-
-struct nvbios_pll {
-       enum nvbios_pll_type type;
-       u32 reg;
-       u32 refclk;
-
-       u8 min_p;
-       u8 max_p;
-       u8 bias_p;
-
-       /*
-        * 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
-        */
-       u8 max_p_usable;
-
-       struct {
-               u32 min_freq;
-               u32 max_freq;
-               u32 min_inputfreq;
-               u32 max_inputfreq;
-               u8  min_m;
-               u8  max_m;
-               u8  min_n;
-               u8  max_n;
-       } vco1, vco2;
-};
-
-int nvbios_pll_parse(struct nouveau_bios *, u32 type, struct nvbios_pll *);
-
-#endif
diff --git a/drivers/gpu/drm/nouveau/core/include/subdev/bios/pmu.h b/drivers/gpu/drm/nouveau/core/include/subdev/bios/pmu.h
deleted file mode 100644 (file)
index 9de593d..0000000
+++ /dev/null
@@ -1,37 +0,0 @@
-#ifndef __NVBIOS_PMU_H__
-#define __NVBIOS_PMU_H__
-
-struct nvbios_pmuT {
-};
-
-u32 nvbios_pmuTe(struct nouveau_bios *, u8 *ver, u8 *hdr, u8 *cnt, u8 *len);
-u32 nvbios_pmuTp(struct nouveau_bios *, u8 *ver, u8 *hdr, u8 *cnt, u8 *len,
-                struct nvbios_pmuT *);
-
-struct nvbios_pmuE {
-       u8  type;
-       u32 data;
-};
-
-u32 nvbios_pmuEe(struct nouveau_bios *, int idx, u8 *ver, u8 *hdr);
-u32 nvbios_pmuEp(struct nouveau_bios *, int idx, u8 *ver, u8 *hdr,
-                struct nvbios_pmuE *);
-
-struct nvbios_pmuR {
-       u32 boot_addr_pmu;
-       u32 boot_addr;
-       u32 boot_size;
-       u32 code_addr_pmu;
-       u32 code_addr;
-       u32 code_size;
-       u32 init_addr_pmu;
-
-       u32 data_addr_pmu;
-       u32 data_addr;
-       u32 data_size;
-       u32 args_addr_pmu;
-};
-
-bool nvbios_pmuRm(struct nouveau_bios *, u8 type, struct nvbios_pmuR *);
-
-#endif
diff --git a/drivers/gpu/drm/nouveau/core/include/subdev/bios/ramcfg.h b/drivers/gpu/drm/nouveau/core/include/subdev/bios/ramcfg.h
deleted file mode 100644 (file)
index 4a0e0ce..0000000
+++ /dev/null
@@ -1,145 +0,0 @@
-#ifndef __NVBIOS_RAMCFG_H__
-#define __NVBIOS_RAMCFG_H__
-
-struct nouveau_bios;
-
-struct nvbios_ramcfg {
-       unsigned rammap_ver;
-       unsigned rammap_hdr;
-       unsigned rammap_min;
-       unsigned rammap_max;
-       union {
-               struct {
-                       unsigned rammap_10_04_02:1;
-                       unsigned rammap_10_04_08:1;
-               };
-               struct {
-                       unsigned rammap_11_08_01:1;
-                       unsigned rammap_11_08_0c:2;
-                       unsigned rammap_11_08_10:1;
-                       unsigned rammap_11_09_01ff:9;
-                       unsigned rammap_11_0a_03fe:9;
-                       unsigned rammap_11_0a_0400:1;
-                       unsigned rammap_11_0a_0800:1;
-                       unsigned rammap_11_0b_01f0:5;
-                       unsigned rammap_11_0b_0200:1;
-                       unsigned rammap_11_0b_0400:1;
-                       unsigned rammap_11_0b_0800:1;
-                       unsigned rammap_11_0d:8;
-                       unsigned rammap_11_0e:8;
-                       unsigned rammap_11_0f:8;
-                       unsigned rammap_11_11_0c:2;
-               };
-       };
-
-       unsigned ramcfg_ver;
-       unsigned ramcfg_hdr;
-       unsigned ramcfg_timing;
-       union {
-               struct {
-                       unsigned ramcfg_10_02_01:1;
-                       unsigned ramcfg_10_02_02:1;
-                       unsigned ramcfg_10_02_04:1;
-                       unsigned ramcfg_10_02_08:1;
-                       unsigned ramcfg_10_02_10:1;
-                       unsigned ramcfg_10_02_20:1;
-                       unsigned ramcfg_10_DLLoff:1;
-                       unsigned ramcfg_10_03_0f:4;
-                       unsigned ramcfg_10_04_01:1;
-                       unsigned ramcfg_10_05:8;
-                       unsigned ramcfg_10_06:8;
-                       unsigned ramcfg_10_07:8;
-                       unsigned ramcfg_10_08:8;
-                       unsigned ramcfg_10_09_0f:4;
-                       unsigned ramcfg_10_09_f0:4;
-               };
-               struct {
-                       unsigned ramcfg_11_01_01:1;
-                       unsigned ramcfg_11_01_02:1;
-                       unsigned ramcfg_11_01_04:1;
-                       unsigned ramcfg_11_01_08:1;
-                       unsigned ramcfg_11_01_10:1;
-                       unsigned ramcfg_11_01_20:1;
-                       unsigned ramcfg_11_01_40:1;
-                       unsigned ramcfg_11_01_80:1;
-                       unsigned ramcfg_11_02_03:2;
-                       unsigned ramcfg_11_02_04:1;
-                       unsigned ramcfg_11_02_08:1;
-                       unsigned ramcfg_11_02_10:1;
-                       unsigned ramcfg_11_02_40:1;
-                       unsigned ramcfg_11_02_80:1;
-                       unsigned ramcfg_11_03_0f:4;
-                       unsigned ramcfg_11_03_30:2;
-                       unsigned ramcfg_11_03_c0:2;
-                       unsigned ramcfg_11_03_f0:4;
-                       unsigned ramcfg_11_04:8;
-                       unsigned ramcfg_11_06:8;
-                       unsigned ramcfg_11_07_02:1;
-                       unsigned ramcfg_11_07_04:1;
-                       unsigned ramcfg_11_07_08:1;
-                       unsigned ramcfg_11_07_10:1;
-                       unsigned ramcfg_11_07_40:1;
-                       unsigned ramcfg_11_07_80:1;
-                       unsigned ramcfg_11_08_01:1;
-                       unsigned ramcfg_11_08_02:1;
-                       unsigned ramcfg_11_08_04:1;
-                       unsigned ramcfg_11_08_08:1;
-                       unsigned ramcfg_11_08_10:1;
-                       unsigned ramcfg_11_08_20:1;
-                       unsigned ramcfg_11_09:8;
-               };
-       };
-
-       unsigned timing_ver;
-       unsigned timing_hdr;
-       unsigned timing[11];
-       union {
-               struct {
-                       unsigned timing_10_WR:8;
-                       unsigned timing_10_WTR:8;
-                       unsigned timing_10_CL:8;
-                       unsigned timing_10_RC:8;
-                       /*empty: 4 */
-                       unsigned timing_10_RFC:8;        /* Byte 5 */
-                       /*empty: 6 */
-                       unsigned timing_10_RAS:8;        /* Byte 7 */
-                       /*empty: 8 */
-                       unsigned timing_10_RP:8;         /* Byte 9 */
-                       unsigned timing_10_RCDRD:8;
-                       unsigned timing_10_RCDWR:8;
-                       unsigned timing_10_RRD:8;
-                       unsigned timing_10_13:8;
-                       unsigned timing_10_ODT:3;
-                       /* empty: 15 */
-                       unsigned timing_10_16:8;
-                       /* empty: 17 */
-                       unsigned timing_10_18:8;
-                       unsigned timing_10_CWL:8;
-                       unsigned timing_10_20:8;
-                       unsigned timing_10_21:8;
-                       /* empty: 22, 23 */
-                       unsigned timing_10_24:8;
-               };
-               struct {
-                       unsigned timing_20_2e_03:2;
-                       unsigned timing_20_2e_30:2;
-                       unsigned timing_20_2e_c0:2;
-                       unsigned timing_20_2f_03:2;
-                       unsigned timing_20_2c_003f:6;
-                       unsigned timing_20_2c_1fc0:7;
-                       unsigned timing_20_30_f8:5;
-                       unsigned timing_20_30_07:3;
-                       unsigned timing_20_31_0007:3;
-                       unsigned timing_20_31_0078:4;
-                       unsigned timing_20_31_0780:4;
-                       unsigned timing_20_31_0800:1;
-                       unsigned timing_20_31_7000:3;
-                       unsigned timing_20_31_8000:1;
-               };
-       };
-};
-
-u8 nvbios_ramcfg_count(struct nouveau_bios *);
-u8 nvbios_ramcfg_index(struct nouveau_subdev *);
-
-#endif
diff --git a/drivers/gpu/drm/nouveau/core/include/subdev/bios/rammap.h b/drivers/gpu/drm/nouveau/core/include/subdev/bios/rammap.h
deleted file mode 100644 (file)
index 47e021d..0000000
+++ /dev/null
@@ -1,26 +0,0 @@
-#ifndef __NVBIOS_RAMMAP_H__
-#define __NVBIOS_RAMMAP_H__
-
-struct nvbios_ramcfg;
-
-u32 nvbios_rammapTe(struct nouveau_bios *, u8 *ver, u8 *hdr,
-                   u8 *cnt, u8 *len, u8 *snr, u8 *ssz);
-
-u32 nvbios_rammapEe(struct nouveau_bios *, int idx,
-                   u8 *ver, u8 *hdr, u8 *cnt, u8 *len);
-u32 nvbios_rammapEp(struct nouveau_bios *, int idx,
-                   u8 *ver, u8 *hdr, u8 *cnt, u8 *len,
-                   struct nvbios_ramcfg *);
-u32 nvbios_rammapEm(struct nouveau_bios *, u16 mhz,
-                   u8 *ver, u8 *hdr, u8 *cnt, u8 *len,
-                   struct nvbios_ramcfg *);
-
-u32 nvbios_rammapSe(struct nouveau_bios *, u32 data,
-                   u8 ever, u8 ehdr, u8 ecnt, u8 elen, int idx,
-                   u8 *ver, u8 *hdr);
-u32 nvbios_rammapSp(struct nouveau_bios *, u32 data,
-                   u8 ever, u8 ehdr, u8 ecnt, u8 elen, int idx,
-                   u8 *ver, u8 *hdr,
-                   struct nvbios_ramcfg *);
-
-#endif
diff --git a/drivers/gpu/drm/nouveau/core/include/subdev/bios/therm.h b/drivers/gpu/drm/nouveau/core/include/subdev/bios/therm.h
deleted file mode 100644 (file)
index 295d093..0000000
+++ /dev/null
@@ -1,77 +0,0 @@
-#ifndef __NVBIOS_THERM_H__
-#define __NVBIOS_THERM_H__
-
-struct nouveau_bios;
-
-struct nvbios_therm_threshold {
-       u8 temp;
-       u8 hysteresis;
-};
-
-struct nvbios_therm_sensor {
-       /* diode */
-       s16 slope_mult;
-       s16 slope_div;
-       s16 offset_num;
-       s16 offset_den;
-       s8 offset_constant;
-
-       /* thresholds */
-       struct nvbios_therm_threshold thrs_fan_boost;
-       struct nvbios_therm_threshold thrs_down_clock;
-       struct nvbios_therm_threshold thrs_critical;
-       struct nvbios_therm_threshold thrs_shutdown;
-};
-
-enum nvbios_therm_fan_type {
-       NVBIOS_THERM_FAN_UNK = 0,
-       NVBIOS_THERM_FAN_TOGGLE = 1,
-       NVBIOS_THERM_FAN_PWM = 2,
-};
-
-/* no vbios have more than 6 */
-#define NOUVEAU_TEMP_FAN_TRIP_MAX 10
-struct nouveau_therm_trip_point {
-       int fan_duty;
-       int temp;
-       int hysteresis;
-};
-
-enum nvbios_therm_fan_mode {
-       NVBIOS_THERM_FAN_TRIP = 0,
-       NVBIOS_THERM_FAN_LINEAR = 1,
-       NVBIOS_THERM_FAN_OTHER = 2,
-};
-
-struct nvbios_therm_fan {
-       enum nvbios_therm_fan_type type;
-
-       u32 pwm_freq;
-
-       u8 min_duty;
-       u8 max_duty;
-
-       u16 bump_period;
-       u16 slow_down_period;
-
-       enum nvbios_therm_fan_mode fan_mode;
-       struct nouveau_therm_trip_point trip[NOUVEAU_TEMP_FAN_TRIP_MAX];
-       u8 nr_fan_trip;
-       u8 linear_min_temp;
-       u8 linear_max_temp;
-};
-
-enum nvbios_therm_domain {
-       NVBIOS_THERM_DOMAIN_CORE,
-       NVBIOS_THERM_DOMAIN_AMBIENT,
-};
-
-int
-nvbios_therm_sensor_parse(struct nouveau_bios *, enum nvbios_therm_domain,
-                         struct nvbios_therm_sensor *);
-
-int
-nvbios_therm_fan_parse(struct nouveau_bios *, struct nvbios_therm_fan *);
-
-
-#endif
diff --git a/drivers/gpu/drm/nouveau/core/include/subdev/bios/timing.h b/drivers/gpu/drm/nouveau/core/include/subdev/bios/timing.h
deleted file mode 100644 (file)
index 76d914b..0000000
+++ /dev/null
@@ -1,14 +0,0 @@
-#ifndef __NVBIOS_TIMING_H__
-#define __NVBIOS_TIMING_H__
-
-struct nvbios_ramcfg;
-
-u16 nvbios_timingTe(struct nouveau_bios *,
-                   u8 *ver, u8 *hdr, u8 *cnt, u8 *len, u8 *snr, u8 *ssz);
-u16 nvbios_timingEe(struct nouveau_bios *, int idx,
-                   u8 *ver, u8 *hdr, u8 *cnt, u8 *len);
-u16 nvbios_timingEp(struct nouveau_bios *, int idx,
-                   u8 *ver, u8 *hdr, u8 *cnt, u8 *len,
-                   struct nvbios_ramcfg *);
-
-#endif
diff --git a/drivers/gpu/drm/nouveau/core/include/subdev/bios/vmap.h b/drivers/gpu/drm/nouveau/core/include/subdev/bios/vmap.h
deleted file mode 100644 (file)
index ad5a8f2..0000000
+++ /dev/null
@@ -1,25 +0,0 @@
-#ifndef __NVBIOS_VMAP_H__
-#define __NVBIOS_VMAP_H__
-
-struct nouveau_bios;
-
-struct nvbios_vmap {
-};
-
-u16 nvbios_vmap_table(struct nouveau_bios *, u8 *ver, u8 *hdr, u8 *cnt, u8 *len);
-u16 nvbios_vmap_parse(struct nouveau_bios *, u8 *ver, u8 *hdr, u8 *cnt, u8 *len,
-                     struct nvbios_vmap *);
-
-struct nvbios_vmap_entry {
-       u8  unk0;
-       u8  link;
-       u32 min;
-       u32 max;
-       s32 arg[6];
-};
-
-u16 nvbios_vmap_entry(struct nouveau_bios *, int idx, u8 *ver, u8 *len);
-u16 nvbios_vmap_entry_parse(struct nouveau_bios *, int idx, u8 *ver, u8 *len,
-                           struct nvbios_vmap_entry *);
-
-#endif
diff --git a/drivers/gpu/drm/nouveau/core/include/subdev/bios/volt.h b/drivers/gpu/drm/nouveau/core/include/subdev/bios/volt.h
deleted file mode 100644 (file)
index 6a11dcd..0000000
+++ /dev/null
@@ -1,27 +0,0 @@
-#ifndef __NVBIOS_VOLT_H__
-#define __NVBIOS_VOLT_H__
-
-struct nouveau_bios;
-
-struct nvbios_volt {
-       u8  vidmask;
-       u32 min;
-       u32 max;
-       u32 base;
-       s16 step;
-};
-
-u16 nvbios_volt_table(struct nouveau_bios *, u8 *ver, u8 *hdr, u8 *cnt, u8 *len);
-u16 nvbios_volt_parse(struct nouveau_bios *, u8 *ver, u8 *hdr, u8 *cnt, u8 *len,
-                     struct nvbios_volt *);
-
-struct nvbios_volt_entry {
-       u32 voltage;
-       u8  vid;
-};
-
-u16 nvbios_volt_entry(struct nouveau_bios *, int idx, u8 *ver, u8 *len);
-u16 nvbios_volt_entry_parse(struct nouveau_bios *, int idx, u8 *ver, u8 *len,
-                           struct nvbios_volt_entry *);
-
-#endif
diff --git a/drivers/gpu/drm/nouveau/core/include/subdev/bios/xpio.h b/drivers/gpu/drm/nouveau/core/include/subdev/bios/xpio.h
deleted file mode 100644 (file)
index 360baab..0000000
+++ /dev/null
@@ -1,19 +0,0 @@
-#ifndef __NVBIOS_XPIO_H__
-#define __NVBIOS_XPIO_H__
-
-#define NVBIOS_XPIO_FLAG_AUX  0x10
-#define NVBIOS_XPIO_FLAG_AUX0 0x00
-#define NVBIOS_XPIO_FLAG_AUX1 0x10
-
-struct nvbios_xpio {
-       u8 type;
-       u8 addr;
-       u8 flags;
-};
-
-u16 dcb_xpio_table(struct nouveau_bios *, u8 idx,
-                  u8 *ver, u8 *hdr, u8 *cnt, u8 *len);
-u16 dcb_xpio_parse(struct nouveau_bios *, u8 idx,
-                  u8 *ver, u8 *hdr, u8 *cnt, u8 *len, struct nvbios_xpio *);
-
-#endif
diff --git a/drivers/gpu/drm/nouveau/core/include/subdev/bus.h b/drivers/gpu/drm/nouveau/core/include/subdev/bus.h
deleted file mode 100644 (file)
index 697f7ce..0000000
+++ /dev/null
@@ -1,53 +0,0 @@
-#ifndef __NOUVEAU_BUS_H__
-#define __NOUVEAU_BUS_H__
-
-#include <core/subdev.h>
-#include <core/device.h>
-
-struct nouveau_bus_intr {
-       u32 stat;
-       u32 unit;
-};
-
-struct nouveau_bus {
-       struct nouveau_subdev base;
-       int (*hwsq_exec)(struct nouveau_bus *, u32 *, u32);
-       u32 hwsq_size;
-};
-
-static inline struct nouveau_bus *
-nouveau_bus(void *obj)
-{
-       return (void *)nv_device(obj)->subdev[NVDEV_SUBDEV_BUS];
-}
-
-#define nouveau_bus_create(p, e, o, d)                                         \
-       nouveau_subdev_create_((p), (e), (o), 0, "PBUS", "master",             \
-                              sizeof(**d), (void **)d)
-#define nouveau_bus_destroy(p)                                                 \
-       nouveau_subdev_destroy(&(p)->base)
-#define nouveau_bus_init(p)                                                    \
-       nouveau_subdev_init(&(p)->base)
-#define nouveau_bus_fini(p, s)                                                 \
-       nouveau_subdev_fini(&(p)->base, (s))
-
-#define _nouveau_bus_dtor _nouveau_subdev_dtor
-#define _nouveau_bus_init _nouveau_subdev_init
-#define _nouveau_bus_fini _nouveau_subdev_fini
-
-extern struct nouveau_oclass *nv04_bus_oclass;
-extern struct nouveau_oclass *nv31_bus_oclass;
-extern struct nouveau_oclass *nv50_bus_oclass;
-extern struct nouveau_oclass *nv94_bus_oclass;
-extern struct nouveau_oclass *nvc0_bus_oclass;
-
-/* interface to sequencer */
-struct nouveau_hwsq;
-int  nouveau_hwsq_init(struct nouveau_bus *, struct nouveau_hwsq **);
-int  nouveau_hwsq_fini(struct nouveau_hwsq **, bool exec);
-void nouveau_hwsq_wr32(struct nouveau_hwsq *, u32 addr, u32 data);
-void nouveau_hwsq_setf(struct nouveau_hwsq *, u8 flag, int data);
-void nouveau_hwsq_wait(struct nouveau_hwsq *, u8 flag, u8 data);
-void nouveau_hwsq_nsec(struct nouveau_hwsq *, u32 nsec);
-
-#endif
diff --git a/drivers/gpu/drm/nouveau/core/include/subdev/clock.h b/drivers/gpu/drm/nouveau/core/include/subdev/clock.h
deleted file mode 100644 (file)
index 36ed035..0000000
+++ /dev/null
@@ -1,166 +0,0 @@
-#ifndef __NOUVEAU_CLOCK_H__
-#define __NOUVEAU_CLOCK_H__
-
-#include <core/device.h>
-#include <core/subdev.h>
-
-struct nouveau_pll_vals;
-struct nvbios_pll;
-
-enum nv_clk_src {
-       nv_clk_src_crystal,
-       nv_clk_src_href,
-
-       nv_clk_src_hclk,
-       nv_clk_src_hclkm3,
-       nv_clk_src_hclkm3d2,
-       nv_clk_src_hclkm2d3, /* NVAA */
-       nv_clk_src_hclkm4, /* NVAA */
-       nv_clk_src_cclk, /* NVAA */
-
-       nv_clk_src_host,
-
-       nv_clk_src_sppll0,
-       nv_clk_src_sppll1,
-
-       nv_clk_src_mpllsrcref,
-       nv_clk_src_mpllsrc,
-       nv_clk_src_mpll,
-       nv_clk_src_mdiv,
-
-       nv_clk_src_core,
-       nv_clk_src_core_intm,
-       nv_clk_src_shader,
-
-       nv_clk_src_mem,
-
-       nv_clk_src_gpc,
-       nv_clk_src_rop,
-       nv_clk_src_hubk01,
-       nv_clk_src_hubk06,
-       nv_clk_src_hubk07,
-       nv_clk_src_copy,
-       nv_clk_src_daemon,
-       nv_clk_src_disp,
-       nv_clk_src_vdec,
-
-       nv_clk_src_dom6,
-
-       nv_clk_src_max,
-};
-
-struct nouveau_cstate {
-       struct list_head head;
-       u8  voltage;
-       u32 domain[nv_clk_src_max];
-};
-
-struct nouveau_pstate {
-       struct list_head head;
-       struct list_head list; /* c-states */
-       struct nouveau_cstate base;
-       u8 pstate;
-       u8 fanspeed;
-};
-
-struct nouveau_clock {
-       struct nouveau_subdev base;
-
-       struct nouveau_clocks *domains;
-       struct nouveau_pstate bstate;
-
-       struct list_head states;
-       int state_nr;
-
-       struct work_struct work;
-       wait_queue_head_t wait;
-       atomic_t waiting;
-
-       struct nvkm_notify pwrsrc_ntfy;
-       int pwrsrc;
-       int pstate; /* current */
-       int ustate_ac; /* user-requested (-1 disabled, -2 perfmon) */
-       int ustate_dc; /* user-requested (-1 disabled, -2 perfmon) */
-       int astate; /* perfmon adjustment (base) */
-       int tstate; /* thermal adjustment (max-) */
-       int dstate; /* display adjustment (min+) */
-
-       bool allow_reclock;
-
-       int  (*read)(struct nouveau_clock *, enum nv_clk_src);
-       int  (*calc)(struct nouveau_clock *, struct nouveau_cstate *);
-       int  (*prog)(struct nouveau_clock *);
-       void (*tidy)(struct nouveau_clock *);
-
-       /*XXX: die, these are here *only* to support the completely
-        *     bat-shit insane what-was-nouveau_hw.c code
-        */
-       int (*pll_calc)(struct nouveau_clock *, struct nvbios_pll *,
-                       int clk, struct nouveau_pll_vals *pv);
-       int (*pll_prog)(struct nouveau_clock *, u32 reg1,
-                       struct nouveau_pll_vals *pv);
-};
-
-static inline struct nouveau_clock *
-nouveau_clock(void *obj)
-{
-       return (void *)nv_device(obj)->subdev[NVDEV_SUBDEV_CLOCK];
-}
-
-struct nouveau_clocks {
-       enum nv_clk_src name;
-       u8 bios; /* 0xff for none */
-#define NVKM_CLK_DOM_FLAG_CORE 0x01
-       u8 flags;
-       const char *mname;
-       int mdiv;
-};
-
-#define nouveau_clock_create(p,e,o,i,r,s,n,d)                                  \
-       nouveau_clock_create_((p), (e), (o), (i), (r), (s), (n), sizeof(**d),  \
-                             (void **)d)
-#define nouveau_clock_destroy(p) ({                                            \
-       struct nouveau_clock *clk = (p);                                       \
-       _nouveau_clock_dtor(nv_object(clk));                                   \
-})
-#define nouveau_clock_init(p) ({                                               \
-       struct nouveau_clock *clk = (p);                                       \
-       _nouveau_clock_init(nv_object(clk));                                   \
-})
-#define nouveau_clock_fini(p,s) ({                                             \
-       struct nouveau_clock *clk = (p);                                       \
-       _nouveau_clock_fini(nv_object(clk), (s));                              \
-})
-
-int  nouveau_clock_create_(struct nouveau_object *, struct nouveau_object *,
-                          struct nouveau_oclass *,
-                          struct nouveau_clocks *, struct nouveau_pstate *,
-                          int, bool, int, void **);
-void _nouveau_clock_dtor(struct nouveau_object *);
-int  _nouveau_clock_init(struct nouveau_object *);
-int  _nouveau_clock_fini(struct nouveau_object *, bool);
-
-extern struct nouveau_oclass nv04_clock_oclass;
-extern struct nouveau_oclass nv40_clock_oclass;
-extern struct nouveau_oclass *nv50_clock_oclass;
-extern struct nouveau_oclass *nv84_clock_oclass;
-extern struct nouveau_oclass *nvaa_clock_oclass;
-extern struct nouveau_oclass nva3_clock_oclass;
-extern struct nouveau_oclass nvc0_clock_oclass;
-extern struct nouveau_oclass nve0_clock_oclass;
-extern struct nouveau_oclass gk20a_clock_oclass;
-
-int nv04_clock_pll_set(struct nouveau_clock *, u32 type, u32 freq);
-int nv04_clock_pll_calc(struct nouveau_clock *, struct nvbios_pll *,
-                       int clk, struct nouveau_pll_vals *);
-int nv04_clock_pll_prog(struct nouveau_clock *, u32 reg1,
-                       struct nouveau_pll_vals *);
-int nva3_clock_pll_calc(struct nouveau_clock *, struct nvbios_pll *,
-                       int clk, struct nouveau_pll_vals *);
-
-int nouveau_clock_ustate(struct nouveau_clock *, int req, int pwr);
-int nouveau_clock_astate(struct nouveau_clock *, int req, int rel);
-int nouveau_clock_dstate(struct nouveau_clock *, int req, int rel);
-int nouveau_clock_tstate(struct nouveau_clock *, int req, int rel);
-
-#endif
diff --git a/drivers/gpu/drm/nouveau/core/include/subdev/devinit.h b/drivers/gpu/drm/nouveau/core/include/subdev/devinit.h
deleted file mode 100644 (file)
index e007a9d..0000000
+++ /dev/null
@@ -1,35 +0,0 @@
-#ifndef __NOUVEAU_DEVINIT_H__
-#define __NOUVEAU_DEVINIT_H__
-
-#include <core/subdev.h>
-#include <core/device.h>
-
-struct nouveau_devinit {
-       struct nouveau_subdev base;
-       bool post;
-       void (*meminit)(struct nouveau_devinit *);
-       int  (*pll_set)(struct nouveau_devinit *, u32 type, u32 freq);
-       u32  (*mmio)(struct nouveau_devinit *, u32 addr);
-};
-
-static inline struct nouveau_devinit *
-nouveau_devinit(void *obj)
-{
-       return (void *)nv_device(obj)->subdev[NVDEV_SUBDEV_DEVINIT];
-}
-
-extern struct nouveau_oclass *nv04_devinit_oclass;
-extern struct nouveau_oclass *nv05_devinit_oclass;
-extern struct nouveau_oclass *nv10_devinit_oclass;
-extern struct nouveau_oclass *nv1a_devinit_oclass;
-extern struct nouveau_oclass *nv20_devinit_oclass;
-extern struct nouveau_oclass *nv50_devinit_oclass;
-extern struct nouveau_oclass *nv84_devinit_oclass;
-extern struct nouveau_oclass *nv98_devinit_oclass;
-extern struct nouveau_oclass *nva3_devinit_oclass;
-extern struct nouveau_oclass *nvaf_devinit_oclass;
-extern struct nouveau_oclass *nvc0_devinit_oclass;
-extern struct nouveau_oclass *gm107_devinit_oclass;
-extern struct nouveau_oclass *gm204_devinit_oclass;
-
-#endif
diff --git a/drivers/gpu/drm/nouveau/core/include/subdev/fb.h b/drivers/gpu/drm/nouveau/core/include/subdev/fb.h
deleted file mode 100644 (file)
index 8d0032f..0000000
+++ /dev/null
@@ -1,159 +0,0 @@
-#ifndef __NOUVEAU_FB_H__
-#define __NOUVEAU_FB_H__
-
-#include <core/subdev.h>
-#include <core/device.h>
-#include <core/mm.h>
-
-#include <subdev/vm.h>
-
-/* memory type/access flags, do not match hardware values */
-#define NV_MEM_ACCESS_RO  1
-#define NV_MEM_ACCESS_WO  2
-#define NV_MEM_ACCESS_RW (NV_MEM_ACCESS_RO | NV_MEM_ACCESS_WO)
-#define NV_MEM_ACCESS_SYS 4
-#define NV_MEM_ACCESS_VM  8
-#define NV_MEM_ACCESS_NOSNOOP 16
-
-#define NV_MEM_TARGET_VRAM        0
-#define NV_MEM_TARGET_PCI         1
-#define NV_MEM_TARGET_PCI_NOSNOOP 2
-#define NV_MEM_TARGET_VM          3
-#define NV_MEM_TARGET_GART        4
-
-#define NV_MEM_TYPE_VM 0x7f
-#define NV_MEM_COMP_VM 0x03
-
-struct nouveau_mem {
-       struct drm_device *dev;
-
-       struct nouveau_vma bar_vma;
-       struct nouveau_vma vma[2];
-       u8  page_shift;
-
-       struct nouveau_mm_node *tag;
-       struct list_head regions;
-       dma_addr_t *pages;
-       u32 memtype;
-       u64 offset;
-       u64 size;
-       struct sg_table *sg;
-};
-
-struct nouveau_fb_tile {
-       struct nouveau_mm_node *tag;
-       u32 addr;
-       u32 limit;
-       u32 pitch;
-       u32 zcomp;
-};
-
-struct nouveau_fb {
-       struct nouveau_subdev base;
-
-       bool (*memtype_valid)(struct nouveau_fb *, u32 memtype);
-
-       struct nouveau_ram *ram;
-
-       struct nouveau_mm vram;
-       struct nouveau_mm tags;
-
-       struct {
-               struct nouveau_fb_tile region[16];
-               int regions;
-               void (*init)(struct nouveau_fb *, int i, u32 addr, u32 size,
-                            u32 pitch, u32 flags, struct nouveau_fb_tile *);
-               void (*comp)(struct nouveau_fb *, int i, u32 size, u32 flags,
-                            struct nouveau_fb_tile *);
-               void (*fini)(struct nouveau_fb *, int i,
-                            struct nouveau_fb_tile *);
-               void (*prog)(struct nouveau_fb *, int i,
-                            struct nouveau_fb_tile *);
-       } tile;
-};
-
-static inline struct nouveau_fb *
-nouveau_fb(void *obj)
-{
-       /* fbram uses this before device subdev pointer is valid */
-       if (nv_iclass(obj, NV_SUBDEV_CLASS) &&
-           nv_subidx(obj) == NVDEV_SUBDEV_FB)
-               return obj;
-
-       return (void *)nv_device(obj)->subdev[NVDEV_SUBDEV_FB];
-}
-
-extern struct nouveau_oclass *nv04_fb_oclass;
-extern struct nouveau_oclass *nv10_fb_oclass;
-extern struct nouveau_oclass *nv1a_fb_oclass;
-extern struct nouveau_oclass *nv20_fb_oclass;
-extern struct nouveau_oclass *nv25_fb_oclass;
-extern struct nouveau_oclass *nv30_fb_oclass;
-extern struct nouveau_oclass *nv35_fb_oclass;
-extern struct nouveau_oclass *nv36_fb_oclass;
-extern struct nouveau_oclass *nv40_fb_oclass;
-extern struct nouveau_oclass *nv41_fb_oclass;
-extern struct nouveau_oclass *nv44_fb_oclass;
-extern struct nouveau_oclass *nv46_fb_oclass;
-extern struct nouveau_oclass *nv47_fb_oclass;
-extern struct nouveau_oclass *nv49_fb_oclass;
-extern struct nouveau_oclass *nv4e_fb_oclass;
-extern struct nouveau_oclass *nv50_fb_oclass;
-extern struct nouveau_oclass *nv84_fb_oclass;
-extern struct nouveau_oclass *nva3_fb_oclass;
-extern struct nouveau_oclass *nvaa_fb_oclass;
-extern struct nouveau_oclass *nvaf_fb_oclass;
-extern struct nouveau_oclass *nvc0_fb_oclass;
-extern struct nouveau_oclass *nve0_fb_oclass;
-extern struct nouveau_oclass *gk20a_fb_oclass;
-extern struct nouveau_oclass *gm107_fb_oclass;
-
-#include <subdev/bios/ramcfg.h>
-
-struct nouveau_ram_data {
-       struct list_head head;
-       struct nvbios_ramcfg bios;
-       u32 freq;
-};
-
-struct nouveau_ram {
-       struct nouveau_object base;
-       enum {
-               NV_MEM_TYPE_UNKNOWN = 0,
-               NV_MEM_TYPE_STOLEN,
-               NV_MEM_TYPE_SGRAM,
-               NV_MEM_TYPE_SDRAM,
-               NV_MEM_TYPE_DDR1,
-               NV_MEM_TYPE_DDR2,
-               NV_MEM_TYPE_DDR3,
-               NV_MEM_TYPE_GDDR2,
-               NV_MEM_TYPE_GDDR3,
-               NV_MEM_TYPE_GDDR4,
-               NV_MEM_TYPE_GDDR5
-       } type;
-       u64 stolen;
-       u64 size;
-       u32 tags;
-
-       int ranks;
-       int parts;
-       int part_mask;
-
-       int  (*get)(struct nouveau_fb *, u64 size, u32 align,
-                   u32 size_nc, u32 type, struct nouveau_mem **);
-       void (*put)(struct nouveau_fb *, struct nouveau_mem **);
-
-       int  (*calc)(struct nouveau_fb *, u32 freq);
-       int  (*prog)(struct nouveau_fb *);
-       void (*tidy)(struct nouveau_fb *);
-       u32 freq;
-       u32 mr[16];
-       u32 mr1_nuts;
-
-       struct nouveau_ram_data *next;
-       struct nouveau_ram_data former;
-       struct nouveau_ram_data xition;
-       struct nouveau_ram_data target;
-};
-
-#endif
diff --git a/drivers/gpu/drm/nouveau/core/include/subdev/fb/regsnv04.h b/drivers/gpu/drm/nouveau/core/include/subdev/fb/regsnv04.h
deleted file mode 100644 (file)
index 0f7fc0c..0000000
+++ /dev/null
@@ -1,21 +0,0 @@
-#ifndef __NOUVEAU_FB_REGS_04_H__
-#define __NOUVEAU_FB_REGS_04_H__
-
-#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
-
-#endif
diff --git a/drivers/gpu/drm/nouveau/core/include/subdev/fuse.h b/drivers/gpu/drm/nouveau/core/include/subdev/fuse.h
deleted file mode 100644 (file)
index 2b1ddb2..0000000
+++ /dev/null
@@ -1,30 +0,0 @@
-#ifndef __NOUVEAU_FUSE_H__
-#define __NOUVEAU_FUSE_H__
-
-#include <core/subdev.h>
-#include <core/device.h>
-
-struct nouveau_fuse {
-       struct nouveau_subdev base;
-};
-
-static inline struct nouveau_fuse *
-nouveau_fuse(void *obj)
-{
-       return (void *)nv_device(obj)->subdev[NVDEV_SUBDEV_FUSE];
-}
-
-#define nouveau_fuse_create(p, e, o, d)                                        \
-       nouveau_fuse_create_((p), (e), (o), sizeof(**d), (void **)d)
-
-int  nouveau_fuse_create_(struct nouveau_object *, struct nouveau_object *,
-                         struct nouveau_oclass *, int, void **);
-void _nouveau_fuse_dtor(struct nouveau_object *);
-int  _nouveau_fuse_init(struct nouveau_object *);
-#define _nouveau_fuse_fini _nouveau_subdev_fini
-
-extern struct nouveau_oclass g80_fuse_oclass;
-extern struct nouveau_oclass gf100_fuse_oclass;
-extern struct nouveau_oclass gm107_fuse_oclass;
-
-#endif
diff --git a/drivers/gpu/drm/nouveau/core/include/subdev/gpio.h b/drivers/gpu/drm/nouveau/core/include/subdev/gpio.h
deleted file mode 100644 (file)
index f855140..0000000
+++ /dev/null
@@ -1,47 +0,0 @@
-#ifndef __NOUVEAU_GPIO_H__
-#define __NOUVEAU_GPIO_H__
-
-#include <core/subdev.h>
-#include <core/device.h>
-#include <core/event.h>
-
-#include <subdev/bios.h>
-#include <subdev/bios/gpio.h>
-
-struct nvkm_gpio_ntfy_req {
-#define NVKM_GPIO_HI                                                       0x01
-#define NVKM_GPIO_LO                                                       0x02
-#define NVKM_GPIO_TOGGLED                                                  0x03
-       u8 mask;
-       u8 line;
-};
-
-struct nvkm_gpio_ntfy_rep {
-       u8 mask;
-};
-
-struct nouveau_gpio {
-       struct nouveau_subdev base;
-
-       struct nvkm_event event;
-
-       void (*reset)(struct nouveau_gpio *, u8 func);
-       int  (*find)(struct nouveau_gpio *, int idx, u8 tag, u8 line,
-                    struct dcb_gpio_func *);
-       int  (*set)(struct nouveau_gpio *, int idx, u8 tag, u8 line, int state);
-       int  (*get)(struct nouveau_gpio *, int idx, u8 tag, u8 line);
-};
-
-static inline struct nouveau_gpio *
-nouveau_gpio(void *obj)
-{
-       return (void *)nv_device(obj)->subdev[NVDEV_SUBDEV_GPIO];
-}
-
-extern struct nouveau_oclass *nv10_gpio_oclass;
-extern struct nouveau_oclass *nv50_gpio_oclass;
-extern struct nouveau_oclass *nv94_gpio_oclass;
-extern struct nouveau_oclass *nvd0_gpio_oclass;
-extern struct nouveau_oclass *nve0_gpio_oclass;
-
-#endif
diff --git a/drivers/gpu/drm/nouveau/core/include/subdev/i2c.h b/drivers/gpu/drm/nouveau/core/include/subdev/i2c.h
deleted file mode 100644 (file)
index d94ccac..0000000
+++ /dev/null
@@ -1,136 +0,0 @@
-#ifndef __NOUVEAU_I2C_H__
-#define __NOUVEAU_I2C_H__
-
-#include <core/subdev.h>
-#include <core/device.h>
-
-#include <subdev/bios.h>
-#include <subdev/bios/i2c.h>
-
-#define NV_I2C_PORT(n)    (0x00 + (n))
-#define NV_I2C_AUX(n)     (0x10 + (n))
-#define NV_I2C_EXT(n)     (0x20 + (n))
-#define NV_I2C_DEFAULT(n) (0x80 + (n))
-
-#define NV_I2C_TYPE_DCBI2C(n) (0x0000 | (n))
-#define NV_I2C_TYPE_EXTDDC(e) (0x0005 | (e) << 8)
-#define NV_I2C_TYPE_EXTAUX(e) (0x0006 | (e) << 8)
-
-struct nvkm_i2c_ntfy_req {
-#define NVKM_I2C_PLUG                                                      0x01
-#define NVKM_I2C_UNPLUG                                                    0x02
-#define NVKM_I2C_IRQ                                                       0x04
-#define NVKM_I2C_DONE                                                      0x08
-#define NVKM_I2C_ANY                                                       0x0f
-       u8 mask;
-       u8 port;
-};
-
-struct nvkm_i2c_ntfy_rep {
-       u8 mask;
-};
-
-struct nouveau_i2c_port {
-       struct nouveau_object base;
-       struct i2c_adapter adapter;
-       struct mutex mutex;
-
-       struct list_head head;
-       u8  index;
-       int aux;
-
-       const struct nouveau_i2c_func *func;
-};
-
-struct nouveau_i2c_func {
-       void (*drive_scl)(struct nouveau_i2c_port *, int);
-       void (*drive_sda)(struct nouveau_i2c_port *, int);
-       int  (*sense_scl)(struct nouveau_i2c_port *);
-       int  (*sense_sda)(struct nouveau_i2c_port *);
-
-       int  (*aux)(struct nouveau_i2c_port *, bool, u8, u32, u8 *, u8);
-       int  (*pattern)(struct nouveau_i2c_port *, int pattern);
-       int  (*lnk_ctl)(struct nouveau_i2c_port *, int nr, int bw, bool enh);
-       int  (*drv_ctl)(struct nouveau_i2c_port *, int lane, int sw, int pe);
-};
-
-struct nouveau_i2c_board_info {
-       struct i2c_board_info dev;
-       u8 udelay; /* set to 0 to use the standard delay */
-};
-
-struct nouveau_i2c {
-       struct nouveau_subdev base;
-       struct nvkm_event event;
-
-       struct nouveau_i2c_port *(*find)(struct nouveau_i2c *, u8 index);
-       struct nouveau_i2c_port *(*find_type)(struct nouveau_i2c *, u16 type);
-       int  (*acquire_pad)(struct nouveau_i2c_port *, unsigned long timeout);
-       void (*release_pad)(struct nouveau_i2c_port *);
-       int  (*acquire)(struct nouveau_i2c_port *, unsigned long timeout);
-       void (*release)(struct nouveau_i2c_port *);
-       int (*identify)(struct nouveau_i2c *, int index,
-                       const char *what, struct nouveau_i2c_board_info *,
-                       bool (*match)(struct nouveau_i2c_port *,
-                                     struct i2c_board_info *, void *), void *);
-
-       wait_queue_head_t wait;
-       struct list_head ports;
-};
-
-static inline struct nouveau_i2c *
-nouveau_i2c(void *obj)
-{
-       return (void *)nv_device(obj)->subdev[NVDEV_SUBDEV_I2C];
-}
-
-extern struct nouveau_oclass *nv04_i2c_oclass;
-extern struct nouveau_oclass *nv4e_i2c_oclass;
-extern struct nouveau_oclass *nv50_i2c_oclass;
-extern struct nouveau_oclass *nv94_i2c_oclass;
-extern struct nouveau_oclass *nvd0_i2c_oclass;
-extern struct nouveau_oclass *gf117_i2c_oclass;
-extern struct nouveau_oclass *nve0_i2c_oclass;
-extern struct nouveau_oclass *gm204_i2c_oclass;
-
-static inline int
-nv_rdi2cr(struct nouveau_i2c_port *port, u8 addr, u8 reg)
-{
-       u8 val;
-       struct i2c_msg msgs[] = {
-               { .addr = addr, .flags = 0, .len = 1, .buf = &reg },
-               { .addr = addr, .flags = I2C_M_RD, .len = 1, .buf = &val },
-       };
-
-       int ret = i2c_transfer(&port->adapter, msgs, 2);
-       if (ret != 2)
-               return -EIO;
-
-       return val;
-}
-
-static inline int
-nv_wri2cr(struct nouveau_i2c_port *port, u8 addr, u8 reg, u8 val)
-{
-       u8 buf[2] = { reg, val };
-       struct i2c_msg msgs[] = {
-               { .addr = addr, .flags = 0, .len = 2, .buf = buf },
-       };
-
-       int ret = i2c_transfer(&port->adapter, msgs, 1);
-       if (ret != 1)
-               return -EIO;
-
-       return 0;
-}
-
-static inline bool
-nv_probe_i2c(struct nouveau_i2c_port *port, u8 addr)
-{
-       return nv_rdi2cr(port, addr, 0) >= 0;
-}
-
-int nv_rdaux(struct nouveau_i2c_port *, u32 addr, u8 *data, u8 size);
-int nv_wraux(struct nouveau_i2c_port *, u32 addr, u8 *data, u8 size);
-
-#endif
diff --git a/drivers/gpu/drm/nouveau/core/include/subdev/ibus.h b/drivers/gpu/drm/nouveau/core/include/subdev/ibus.h
deleted file mode 100644 (file)
index 31df634..0000000
+++ /dev/null
@@ -1,35 +0,0 @@
-#ifndef __NOUVEAU_IBUS_H__
-#define __NOUVEAU_IBUS_H__
-
-#include <core/subdev.h>
-#include <core/device.h>
-
-struct nouveau_ibus {
-       struct nouveau_subdev base;
-};
-
-static inline struct nouveau_ibus *
-nouveau_ibus(void *obj)
-{
-       return (void *)nv_device(obj)->subdev[NVDEV_SUBDEV_IBUS];
-}
-
-#define nouveau_ibus_create(p,e,o,d)                                           \
-       nouveau_subdev_create_((p), (e), (o), 0, "PIBUS", "ibus",              \
-                              sizeof(**d), (void **)d)
-#define nouveau_ibus_destroy(p)                                                \
-       nouveau_subdev_destroy(&(p)->base)
-#define nouveau_ibus_init(p)                                                   \
-       nouveau_subdev_init(&(p)->base)
-#define nouveau_ibus_fini(p,s)                                                 \
-       nouveau_subdev_fini(&(p)->base, (s))
-
-#define _nouveau_ibus_dtor _nouveau_subdev_dtor
-#define _nouveau_ibus_init _nouveau_subdev_init
-#define _nouveau_ibus_fini _nouveau_subdev_fini
-
-extern struct nouveau_oclass nvc0_ibus_oclass;
-extern struct nouveau_oclass nve0_ibus_oclass;
-extern struct nouveau_oclass gk20a_ibus_oclass;
-
-#endif
diff --git a/drivers/gpu/drm/nouveau/core/include/subdev/instmem.h b/drivers/gpu/drm/nouveau/core/include/subdev/instmem.h
deleted file mode 100644 (file)
index c1df26f..0000000
+++ /dev/null
@@ -1,52 +0,0 @@
-#ifndef __NOUVEAU_INSTMEM_H__
-#define __NOUVEAU_INSTMEM_H__
-
-#include <core/subdev.h>
-#include <core/device.h>
-#include <core/mm.h>
-
-struct nouveau_instobj {
-       struct nouveau_object base;
-       struct list_head head;
-       u32 *suspend;
-       u64 addr;
-       u32 size;
-};
-
-static inline struct nouveau_instobj *
-nv_memobj(void *obj)
-{
-#if CONFIG_NOUVEAU_DEBUG >= NV_DBG_PARANOIA
-       if (unlikely(!nv_iclass(obj, NV_MEMOBJ_CLASS)))
-               nv_assert("BAD CAST -> NvMemObj, %08x", nv_hclass(obj));
-#endif
-       return obj;
-}
-
-struct nouveau_instmem {
-       struct nouveau_subdev base;
-       struct list_head list;
-
-       u32 reserved;
-       int (*alloc)(struct nouveau_instmem *, struct nouveau_object *,
-                    u32 size, u32 align, struct nouveau_object **);
-};
-
-static inline struct nouveau_instmem *
-nouveau_instmem(void *obj)
-{
-       /* nv04/nv40 impls need to create objects in their constructor,
-        * which is before the subdev pointer is valid
-        */
-       if (nv_iclass(obj, NV_SUBDEV_CLASS) &&
-           nv_subidx(obj) == NVDEV_SUBDEV_INSTMEM)
-               return obj;
-
-       return (void *)nv_device(obj)->subdev[NVDEV_SUBDEV_INSTMEM];
-}
-
-extern struct nouveau_oclass *nv04_instmem_oclass;
-extern struct nouveau_oclass *nv40_instmem_oclass;
-extern struct nouveau_oclass *nv50_instmem_oclass;
-
-#endif
diff --git a/drivers/gpu/drm/nouveau/core/include/subdev/ltc.h b/drivers/gpu/drm/nouveau/core/include/subdev/ltc.h
deleted file mode 100644 (file)
index b909a73..0000000
+++ /dev/null
@@ -1,35 +0,0 @@
-#ifndef __NOUVEAU_LTC_H__
-#define __NOUVEAU_LTC_H__
-
-#include <core/subdev.h>
-#include <core/device.h>
-
-#define NOUVEAU_LTC_MAX_ZBC_CNT 16
-
-struct nouveau_mm_node;
-
-struct nouveau_ltc {
-       struct nouveau_subdev base;
-
-       int  (*tags_alloc)(struct nouveau_ltc *, u32 count,
-                          struct nouveau_mm_node **);
-       void (*tags_free)(struct nouveau_ltc *, struct nouveau_mm_node **);
-       void (*tags_clear)(struct nouveau_ltc *, u32 first, u32 count);
-
-       int zbc_min;
-       int zbc_max;
-       int (*zbc_color_get)(struct nouveau_ltc *, int index, const u32[4]);
-       int (*zbc_depth_get)(struct nouveau_ltc *, int index, const u32);
-};
-
-static inline struct nouveau_ltc *
-nouveau_ltc(void *obj)
-{
-       return (void *)nv_device(obj)->subdev[NVDEV_SUBDEV_LTC];
-}
-
-extern struct nouveau_oclass *gf100_ltc_oclass;
-extern struct nouveau_oclass *gk104_ltc_oclass;
-extern struct nouveau_oclass *gm107_ltc_oclass;
-
-#endif
diff --git a/drivers/gpu/drm/nouveau/core/include/subdev/mc.h b/drivers/gpu/drm/nouveau/core/include/subdev/mc.h
deleted file mode 100644 (file)
index 568e4df..0000000
+++ /dev/null
@@ -1,31 +0,0 @@
-#ifndef __NOUVEAU_MC_H__
-#define __NOUVEAU_MC_H__
-
-#include <core/subdev.h>
-#include <core/device.h>
-
-struct nouveau_mc {
-       struct nouveau_subdev base;
-       bool use_msi;
-       unsigned int irq;
-       void (*unk260)(struct nouveau_mc *, u32);
-};
-
-static inline struct nouveau_mc *
-nouveau_mc(void *obj)
-{
-       return (void *)nv_device(obj)->subdev[NVDEV_SUBDEV_MC];
-}
-
-extern struct nouveau_oclass *nv04_mc_oclass;
-extern struct nouveau_oclass *nv40_mc_oclass;
-extern struct nouveau_oclass *nv44_mc_oclass;
-extern struct nouveau_oclass *nv4c_mc_oclass;
-extern struct nouveau_oclass *nv50_mc_oclass;
-extern struct nouveau_oclass *nv94_mc_oclass;
-extern struct nouveau_oclass *nv98_mc_oclass;
-extern struct nouveau_oclass *nvc0_mc_oclass;
-extern struct nouveau_oclass *nvc3_mc_oclass;
-extern struct nouveau_oclass *gk20a_mc_oclass;
-
-#endif
diff --git a/drivers/gpu/drm/nouveau/core/include/subdev/mxm.h b/drivers/gpu/drm/nouveau/core/include/subdev/mxm.h
deleted file mode 100644 (file)
index b93b152..0000000
+++ /dev/null
@@ -1,37 +0,0 @@
-#ifndef __NOUVEAU_MXM_H__
-#define __NOUVEAU_MXM_H__
-
-#include <core/subdev.h>
-#include <core/device.h>
-
-#define MXM_SANITISE_DCB 0x00000001
-
-struct nouveau_mxm {
-       struct nouveau_subdev base;
-       u32 action;
-       u8 *mxms;
-};
-
-static inline struct nouveau_mxm *
-nouveau_mxm(void *obj)
-{
-       return (void *)nv_device(obj)->subdev[NVDEV_SUBDEV_MXM];
-}
-
-#define nouveau_mxm_create(p,e,o,d)                                            \
-       nouveau_mxm_create_((p), (e), (o), sizeof(**d), (void **)d)
-#define nouveau_mxm_init(p)                                                    \
-       nouveau_subdev_init(&(p)->base)
-#define nouveau_mxm_fini(p,s)                                                  \
-       nouveau_subdev_fini(&(p)->base, (s))
-int  nouveau_mxm_create_(struct nouveau_object *, struct nouveau_object *,
-                        struct nouveau_oclass *, int, void **);
-void nouveau_mxm_destroy(struct nouveau_mxm *);
-
-#define _nouveau_mxm_dtor _nouveau_subdev_dtor
-#define _nouveau_mxm_init _nouveau_subdev_init
-#define _nouveau_mxm_fini _nouveau_subdev_fini
-
-extern struct nouveau_oclass nv50_mxm_oclass;
-
-#endif
diff --git a/drivers/gpu/drm/nouveau/core/include/subdev/pwr.h b/drivers/gpu/drm/nouveau/core/include/subdev/pwr.h
deleted file mode 100644 (file)
index f2427bf..0000000
+++ /dev/null
@@ -1,56 +0,0 @@
-#ifndef __NOUVEAU_PWR_H__
-#define __NOUVEAU_PWR_H__
-
-#include <core/subdev.h>
-#include <core/device.h>
-
-struct nouveau_pwr {
-       struct nouveau_subdev base;
-
-       struct {
-               u32 base;
-               u32 size;
-       } send;
-
-       struct {
-               u32 base;
-               u32 size;
-
-               struct work_struct work;
-               wait_queue_head_t wait;
-               u32 process;
-               u32 message;
-               u32 data[2];
-       } recv;
-
-       int  (*message)(struct nouveau_pwr *, u32[2], u32, u32, u32, u32);
-       void (*pgob)(struct nouveau_pwr *, bool);
-};
-
-static inline struct nouveau_pwr *
-nouveau_pwr(void *obj)
-{
-       return (void *)nv_device(obj)->subdev[NVDEV_SUBDEV_PWR];
-}
-
-extern struct nouveau_oclass *nva3_pwr_oclass;
-extern struct nouveau_oclass *nvc0_pwr_oclass;
-extern struct nouveau_oclass *nvd0_pwr_oclass;
-extern struct nouveau_oclass *gk104_pwr_oclass;
-extern struct nouveau_oclass *nv108_pwr_oclass;
-
-/* interface to MEMX process running on PPWR */
-struct nouveau_memx;
-int  nouveau_memx_init(struct nouveau_pwr *, struct nouveau_memx **);
-int  nouveau_memx_fini(struct nouveau_memx **, bool exec);
-void nouveau_memx_wr32(struct nouveau_memx *, u32 addr, u32 data);
-void nouveau_memx_wait(struct nouveau_memx *,
-                      u32 addr, u32 mask, u32 data, u32 nsec);
-void nouveau_memx_nsec(struct nouveau_memx *, u32 nsec);
-void nouveau_memx_wait_vblank(struct nouveau_memx *);
-void nouveau_memx_train(struct nouveau_memx *);
-int  nouveau_memx_train_result(struct nouveau_pwr *, u32 *, int);
-void nouveau_memx_block(struct nouveau_memx *);
-void nouveau_memx_unblock(struct nouveau_memx *);
-
-#endif
diff --git a/drivers/gpu/drm/nouveau/core/include/subdev/therm.h b/drivers/gpu/drm/nouveau/core/include/subdev/therm.h
deleted file mode 100644 (file)
index a437597..0000000
+++ /dev/null
@@ -1,83 +0,0 @@
-#ifndef __NOUVEAU_THERM_H__
-#define __NOUVEAU_THERM_H__
-
-#include <core/device.h>
-#include <core/subdev.h>
-
-enum nouveau_therm_fan_mode {
-       NOUVEAU_THERM_CTRL_NONE = 0,
-       NOUVEAU_THERM_CTRL_MANUAL = 1,
-       NOUVEAU_THERM_CTRL_AUTO = 2,
-};
-
-enum nouveau_therm_attr_type {
-       NOUVEAU_THERM_ATTR_FAN_MIN_DUTY = 0,
-       NOUVEAU_THERM_ATTR_FAN_MAX_DUTY = 1,
-       NOUVEAU_THERM_ATTR_FAN_MODE = 2,
-
-       NOUVEAU_THERM_ATTR_THRS_FAN_BOOST = 10,
-       NOUVEAU_THERM_ATTR_THRS_FAN_BOOST_HYST = 11,
-       NOUVEAU_THERM_ATTR_THRS_DOWN_CLK = 12,
-       NOUVEAU_THERM_ATTR_THRS_DOWN_CLK_HYST = 13,
-       NOUVEAU_THERM_ATTR_THRS_CRITICAL = 14,
-       NOUVEAU_THERM_ATTR_THRS_CRITICAL_HYST = 15,
-       NOUVEAU_THERM_ATTR_THRS_SHUTDOWN = 16,
-       NOUVEAU_THERM_ATTR_THRS_SHUTDOWN_HYST = 17,
-};
-
-struct nouveau_therm {
-       struct nouveau_subdev base;
-
-       int (*pwm_ctrl)(struct nouveau_therm *, int line, bool);
-       int (*pwm_get)(struct nouveau_therm *, int line, u32 *, u32 *);
-       int (*pwm_set)(struct nouveau_therm *, int line, u32, u32);
-       int (*pwm_clock)(struct nouveau_therm *, int line);
-
-       int (*fan_get)(struct nouveau_therm *);
-       int (*fan_set)(struct nouveau_therm *, int);
-       int (*fan_sense)(struct nouveau_therm *);
-
-       int (*temp_get)(struct nouveau_therm *);
-
-       int (*attr_get)(struct nouveau_therm *, enum nouveau_therm_attr_type);
-       int (*attr_set)(struct nouveau_therm *,
-                       enum nouveau_therm_attr_type, int);
-};
-
-static inline struct nouveau_therm *
-nouveau_therm(void *obj)
-{
-       return (void *)nv_device(obj)->subdev[NVDEV_SUBDEV_THERM];
-}
-
-#define nouveau_therm_create(p,e,o,d)                                          \
-       nouveau_therm_create_((p), (e), (o), sizeof(**d), (void **)d)
-#define nouveau_therm_destroy(p) ({                                            \
-       struct nouveau_therm *therm = (p);                                     \
-        _nouveau_therm_dtor(nv_object(therm));                                 \
-})
-#define nouveau_therm_init(p) ({                                               \
-       struct nouveau_therm *therm = (p);                                     \
-        _nouveau_therm_init(nv_object(therm));                                 \
-})
-#define nouveau_therm_fini(p,s) ({                                             \
-       struct nouveau_therm *therm = (p);                                     \
-        _nouveau_therm_init(nv_object(therm), (s));                            \
-})
-
-int  nouveau_therm_create_(struct nouveau_object *, struct nouveau_object *,
-                          struct nouveau_oclass *, int, void **);
-void _nouveau_therm_dtor(struct nouveau_object *);
-int  _nouveau_therm_init(struct nouveau_object *);
-int  _nouveau_therm_fini(struct nouveau_object *, bool);
-
-int  nouveau_therm_cstate(struct nouveau_therm *, int, int);
-
-extern struct nouveau_oclass nv40_therm_oclass;
-extern struct nouveau_oclass nv50_therm_oclass;
-extern struct nouveau_oclass nv84_therm_oclass;
-extern struct nouveau_oclass nva3_therm_oclass;
-extern struct nouveau_oclass nvd0_therm_oclass;
-extern struct nouveau_oclass gm107_therm_oclass;
-
-#endif
diff --git a/drivers/gpu/drm/nouveau/core/include/subdev/timer.h b/drivers/gpu/drm/nouveau/core/include/subdev/timer.h
deleted file mode 100644 (file)
index db9be80..0000000
+++ /dev/null
@@ -1,64 +0,0 @@
-#ifndef __NOUVEAU_TIMER_H__
-#define __NOUVEAU_TIMER_H__
-
-#include <core/subdev.h>
-#include <core/device.h>
-
-struct nouveau_alarm {
-       struct list_head head;
-       u64 timestamp;
-       void (*func)(struct nouveau_alarm *);
-};
-
-static inline void
-nouveau_alarm_init(struct nouveau_alarm *alarm,
-                  void (*func)(struct nouveau_alarm *))
-{
-       INIT_LIST_HEAD(&alarm->head);
-       alarm->func = func;
-}
-
-bool nouveau_timer_wait_eq(void *, u64 nsec, u32 addr, u32 mask, u32 data);
-bool nouveau_timer_wait_ne(void *, u64 nsec, u32 addr, u32 mask, u32 data);
-bool nouveau_timer_wait_cb(void *, u64 nsec, bool (*func)(void *), void *data);
-void nouveau_timer_alarm(void *, u32 nsec, struct nouveau_alarm *);
-void nouveau_timer_alarm_cancel(void *, struct nouveau_alarm *);
-
-#define NV_WAIT_DEFAULT 2000000000ULL
-#define nv_wait(o,a,m,v)                                                       \
-       nouveau_timer_wait_eq((o), NV_WAIT_DEFAULT, (a), (m), (v))
-#define nv_wait_ne(o,a,m,v)                                                    \
-       nouveau_timer_wait_ne((o), NV_WAIT_DEFAULT, (a), (m), (v))
-#define nv_wait_cb(o,c,d)                                                      \
-       nouveau_timer_wait_cb((o), NV_WAIT_DEFAULT, (c), (d))
-
-struct nouveau_timer {
-       struct nouveau_subdev base;
-       u64  (*read)(struct nouveau_timer *);
-       void (*alarm)(struct nouveau_timer *, u64 time, struct nouveau_alarm *);
-       void (*alarm_cancel)(struct nouveau_timer *, struct nouveau_alarm *);
-};
-
-static inline struct nouveau_timer *
-nouveau_timer(void *obj)
-{
-       return (void *)nv_device(obj)->subdev[NVDEV_SUBDEV_TIMER];
-}
-
-#define nouveau_timer_create(p,e,o,d)                                          \
-       nouveau_subdev_create_((p), (e), (o), 0, "PTIMER", "timer",            \
-                              sizeof(**d), (void **)d)
-#define nouveau_timer_destroy(p)                                               \
-       nouveau_subdev_destroy(&(p)->base)
-#define nouveau_timer_init(p)                                                  \
-       nouveau_subdev_init(&(p)->base)
-#define nouveau_timer_fini(p,s)                                                \
-       nouveau_subdev_fini(&(p)->base, (s))
-
-int nouveau_timer_create_(struct nouveau_object *, struct nouveau_engine *,
-                         struct nouveau_oclass *, int size, void **);
-
-extern struct nouveau_oclass nv04_timer_oclass;
-extern struct nouveau_oclass gk20a_timer_oclass;
-
-#endif
diff --git a/drivers/gpu/drm/nouveau/core/include/subdev/vga.h b/drivers/gpu/drm/nouveau/core/include/subdev/vga.h
deleted file mode 100644 (file)
index fee09ad..0000000
+++ /dev/null
@@ -1,30 +0,0 @@
-#ifndef __NOUVEAU_VGA_H__
-#define __NOUVEAU_VGA_H__
-
-#include <core/os.h>
-
-/* access to various legacy io ports */
-u8   nv_rdport(void *obj, int head, u16 port);
-void nv_wrport(void *obj, int head, u16 port, u8 value);
-
-/* VGA Sequencer */
-u8   nv_rdvgas(void *obj, int head, u8 index);
-void nv_wrvgas(void *obj, int head, u8 index, u8 value);
-
-/* VGA Graphics */
-u8   nv_rdvgag(void *obj, int head, u8 index);
-void nv_wrvgag(void *obj, int head, u8 index, u8 value);
-
-/* VGA CRTC */
-u8   nv_rdvgac(void *obj, int head, u8 index);
-void nv_wrvgac(void *obj, int head, u8 index, u8 value);
-
-/* VGA indexed port access dispatcher */
-u8   nv_rdvgai(void *obj, int head, u16 port, u8 index);
-void nv_wrvgai(void *obj, int head, u16 port, u8 index, u8 value);
-
-bool nv_lockvgac(void *obj, bool lock);
-u8   nv_rdvgaowner(void *obj);
-void nv_wrvgaowner(void *obj, u8);
-
-#endif
diff --git a/drivers/gpu/drm/nouveau/core/include/subdev/vm.h b/drivers/gpu/drm/nouveau/core/include/subdev/vm.h
deleted file mode 100644 (file)
index c950903..0000000
+++ /dev/null
@@ -1,135 +0,0 @@
-/*
- * 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_VM_H__
-#define __NOUVEAU_VM_H__
-
-#include <core/object.h>
-#include <core/subdev.h>
-#include <core/device.h>
-#include <core/mm.h>
-
-struct nouveau_vm_pgt {
-       struct nouveau_gpuobj *obj[2];
-       u32 refcount[2];
-};
-
-struct nouveau_vm_pgd {
-       struct list_head head;
-       struct nouveau_gpuobj *obj;
-};
-
-struct nouveau_gpuobj;
-struct nouveau_mem;
-
-struct nouveau_vma {
-       struct list_head head;
-       int refcount;
-       struct nouveau_vm *vm;
-       struct nouveau_mm_node *node;
-       u64 offset;
-       u32 access;
-};
-
-struct nouveau_vm {
-       struct nouveau_vmmgr *vmm;
-       struct nouveau_mm mm;
-       struct kref refcount;
-
-       struct list_head pgd_list;
-       atomic_t engref[NVDEV_SUBDEV_NR];
-
-       struct nouveau_vm_pgt *pgt;
-       u32 fpde;
-       u32 lpde;
-};
-
-struct nouveau_vmmgr {
-       struct nouveau_subdev base;
-
-       u64 limit;
-       u8  dma_bits;
-       u32 pgt_bits;
-       u8  spg_shift;
-       u8  lpg_shift;
-
-       int  (*create)(struct nouveau_vmmgr *, u64 offset, u64 length,
-                      u64 mm_offset, struct nouveau_vm **);
-
-       void (*map_pgt)(struct nouveau_gpuobj *pgd, u32 pde,
-                       struct nouveau_gpuobj *pgt[2]);
-       void (*map)(struct nouveau_vma *, struct nouveau_gpuobj *,
-                   struct nouveau_mem *, u32 pte, u32 cnt,
-                   u64 phys, u64 delta);
-       void (*map_sg)(struct nouveau_vma *, struct nouveau_gpuobj *,
-                      struct nouveau_mem *, u32 pte, u32 cnt, dma_addr_t *);
-       void (*unmap)(struct nouveau_gpuobj *pgt, u32 pte, u32 cnt);
-       void (*flush)(struct nouveau_vm *);
-};
-
-static inline struct nouveau_vmmgr *
-nouveau_vmmgr(void *obj)
-{
-       return (void *)nv_device(obj)->subdev[NVDEV_SUBDEV_VM];
-}
-
-#define nouveau_vmmgr_create(p,e,o,i,f,d)                                      \
-       nouveau_subdev_create((p), (e), (o), 0, (i), (f), (d))
-#define nouveau_vmmgr_destroy(p)                                               \
-       nouveau_subdev_destroy(&(p)->base)
-#define nouveau_vmmgr_init(p)                                                  \
-       nouveau_subdev_init(&(p)->base)
-#define nouveau_vmmgr_fini(p,s)                                                \
-       nouveau_subdev_fini(&(p)->base, (s))
-
-#define _nouveau_vmmgr_dtor _nouveau_subdev_dtor
-#define _nouveau_vmmgr_init _nouveau_subdev_init
-#define _nouveau_vmmgr_fini _nouveau_subdev_fini
-
-extern struct nouveau_oclass nv04_vmmgr_oclass;
-extern struct nouveau_oclass nv41_vmmgr_oclass;
-extern struct nouveau_oclass nv44_vmmgr_oclass;
-extern struct nouveau_oclass nv50_vmmgr_oclass;
-extern struct nouveau_oclass nvc0_vmmgr_oclass;
-
-int  nv04_vm_create(struct nouveau_vmmgr *, u64, u64, u64,
-                   struct nouveau_vm **);
-void nv04_vmmgr_dtor(struct nouveau_object *);
-
-/* nouveau_vm.c */
-int  nouveau_vm_create(struct nouveau_vmmgr *, u64 offset, u64 length,
-                      u64 mm_offset, u32 block, struct nouveau_vm **);
-int  nouveau_vm_new(struct nouveau_device *, u64 offset, u64 length,
-                   u64 mm_offset, struct nouveau_vm **);
-int  nouveau_vm_ref(struct nouveau_vm *, struct nouveau_vm **,
-                   struct nouveau_gpuobj *pgd);
-int  nouveau_vm_get(struct nouveau_vm *, u64 size, u32 page_shift,
-                   u32 access, struct nouveau_vma *);
-void nouveau_vm_put(struct nouveau_vma *);
-void nouveau_vm_map(struct nouveau_vma *, struct nouveau_mem *);
-void nouveau_vm_map_at(struct nouveau_vma *, u64 offset, struct nouveau_mem *);
-void nouveau_vm_unmap(struct nouveau_vma *);
-void nouveau_vm_unmap_at(struct nouveau_vma *, u64 offset, u64 length);
-
-#endif
diff --git a/drivers/gpu/drm/nouveau/core/include/subdev/volt.h b/drivers/gpu/drm/nouveau/core/include/subdev/volt.h
deleted file mode 100644 (file)
index 67db5e5..0000000
+++ /dev/null
@@ -1,61 +0,0 @@
-#ifndef __NOUVEAU_VOLT_H__
-#define __NOUVEAU_VOLT_H__
-
-#include <core/subdev.h>
-#include <core/device.h>
-
-struct nouveau_voltage {
-       u32 uv;
-       u8  id;
-};
-
-struct nouveau_volt {
-       struct nouveau_subdev base;
-
-       int (*vid_get)(struct nouveau_volt *);
-       int (*get)(struct nouveau_volt *);
-       int (*vid_set)(struct nouveau_volt *, u8 vid);
-       int (*set)(struct nouveau_volt *, u32 uv);
-       int (*set_id)(struct nouveau_volt *, u8 id, int condition);
-
-       u8 vid_mask;
-       u8 vid_nr;
-       struct {
-               u32 uv;
-               u8 vid;
-       } vid[256];
-};
-
-static inline struct nouveau_volt *
-nouveau_volt(void *obj)
-{
-       return (void *)nv_device(obj)->subdev[NVDEV_SUBDEV_VOLT];
-}
-
-#define nouveau_volt_create(p, e, o, d)                                        \
-       nouveau_volt_create_((p), (e), (o), sizeof(**d), (void **)d)
-#define nouveau_volt_destroy(p) ({                                             \
-       struct nouveau_volt *v = (p);                                          \
-       _nouveau_volt_dtor(nv_object(v));                                      \
-})
-#define nouveau_volt_init(p) ({                                                \
-       struct nouveau_volt *v = (p);                                          \
-       _nouveau_volt_init(nv_object(v));                                      \
-})
-#define nouveau_volt_fini(p,s)                                                 \
-       nouveau_subdev_fini((p), (s))
-
-int  nouveau_volt_create_(struct nouveau_object *, struct nouveau_object *,
-                         struct nouveau_oclass *, int, void **);
-void _nouveau_volt_dtor(struct nouveau_object *);
-int  _nouveau_volt_init(struct nouveau_object *);
-#define _nouveau_volt_fini _nouveau_subdev_fini
-
-extern struct nouveau_oclass nv40_volt_oclass;
-extern struct nouveau_oclass gk20a_volt_oclass;
-
-int nouveau_voltgpio_init(struct nouveau_volt *);
-int nouveau_voltgpio_get(struct nouveau_volt *);
-int nouveau_voltgpio_set(struct nouveau_volt *, u8);
-
-#endif
diff --git a/drivers/gpu/drm/nouveau/core/os.h b/drivers/gpu/drm/nouveau/core/os.h
deleted file mode 100644 (file)
index bdd05ee..0000000
+++ /dev/null
@@ -1,44 +0,0 @@
-#ifndef __NOUVEAU_OS_H__
-#define __NOUVEAU_OS_H__
-
-#include <linux/types.h>
-#include <linux/slab.h>
-#include <linux/mutex.h>
-#include <linux/pci.h>
-#include <linux/platform_device.h>
-#include <linux/printk.h>
-#include <linux/bitops.h>
-#include <linux/firmware.h>
-#include <linux/module.h>
-#include <linux/i2c.h>
-#include <linux/i2c-algo-bit.h>
-#include <linux/delay.h>
-#include <linux/io-mapping.h>
-#include <linux/acpi.h>
-#include <linux/vmalloc.h>
-#include <linux/dmi.h>
-#include <linux/reboot.h>
-#include <linux/interrupt.h>
-#include <linux/log2.h>
-#include <linux/pm_runtime.h>
-#include <linux/power_supply.h>
-#include <linux/clk.h>
-#include <linux/regulator/consumer.h>
-
-#include <asm/unaligned.h>
-
-#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 */
-
-#endif
diff --git a/drivers/gpu/drm/nouveau/core/subdev/bar/base.c b/drivers/gpu/drm/nouveau/core/subdev/bar/base.c
deleted file mode 100644 (file)
index b1adc69..0000000
+++ /dev/null
@@ -1,149 +0,0 @@
-/*
- * Copyright 2012 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 <core/object.h>
-
-#include <subdev/fb.h>
-#include <subdev/vm.h>
-
-#include "priv.h"
-
-struct nouveau_barobj {
-       struct nouveau_object base;
-       struct nouveau_vma vma;
-       void __iomem *iomem;
-};
-
-static int
-nouveau_barobj_ctor(struct nouveau_object *parent,
-                   struct nouveau_object *engine,
-                   struct nouveau_oclass *oclass, void *data, u32 size,
-                   struct nouveau_object **pobject)
-{
-       struct nouveau_device *device = nv_device(parent);
-       struct nouveau_bar *bar = (void *)engine;
-       struct nouveau_mem *mem = data;
-       struct nouveau_barobj *barobj;
-       int ret;
-
-       ret = nouveau_object_create(parent, engine, oclass, 0, &barobj);
-       *pobject = nv_object(barobj);
-       if (ret)
-               return ret;
-
-       ret = bar->kmap(bar, mem, NV_MEM_ACCESS_RW, &barobj->vma);
-       if (ret)
-               return ret;
-
-       barobj->iomem = ioremap(nv_device_resource_start(device, 3) +
-                               (u32)barobj->vma.offset, mem->size << 12);
-       if (!barobj->iomem) {
-               nv_warn(bar, "PRAMIN ioremap failed\n");
-               return -ENOMEM;
-       }
-
-       return 0;
-}
-
-static void
-nouveau_barobj_dtor(struct nouveau_object *object)
-{
-       struct nouveau_bar *bar = (void *)object->engine;
-       struct nouveau_barobj *barobj = (void *)object;
-       if (barobj->vma.node) {
-               if (barobj->iomem)
-                       iounmap(barobj->iomem);
-               bar->unmap(bar, &barobj->vma);
-       }
-       nouveau_object_destroy(&barobj->base);
-}
-
-static u32
-nouveau_barobj_rd32(struct nouveau_object *object, u64 addr)
-{
-       struct nouveau_barobj *barobj = (void *)object;
-       return ioread32_native(barobj->iomem + addr);
-}
-
-static void
-nouveau_barobj_wr32(struct nouveau_object *object, u64 addr, u32 data)
-{
-       struct nouveau_barobj *barobj = (void *)object;
-       iowrite32_native(data, barobj->iomem + addr);
-}
-
-static struct nouveau_oclass
-nouveau_barobj_oclass = {
-       .ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nouveau_barobj_ctor,
-               .dtor = nouveau_barobj_dtor,
-               .init = nouveau_object_init,
-               .fini = nouveau_object_fini,
-               .rd32 = nouveau_barobj_rd32,
-               .wr32 = nouveau_barobj_wr32,
-       },
-};
-
-int
-nouveau_bar_alloc(struct nouveau_bar *bar, struct nouveau_object *parent,
-                 struct nouveau_mem *mem, struct nouveau_object **pobject)
-{
-       struct nouveau_object *engine = nv_object(bar);
-       struct nouveau_object *gpuobj;
-       int ret = nouveau_object_ctor(parent, engine, &nouveau_barobj_oclass,
-                                     mem, 0, &gpuobj);
-       if (ret == 0)
-               *pobject = gpuobj;
-       return ret;
-}
-
-int
-nouveau_bar_create_(struct nouveau_object *parent,
-                   struct nouveau_object *engine,
-                   struct nouveau_oclass *oclass, int length, void **pobject)
-{
-       struct nouveau_bar *bar;
-       int ret;
-
-       ret = nouveau_subdev_create_(parent, engine, oclass, 0, "BARCTL",
-                                    "bar", length, pobject);
-       bar = *pobject;
-       if (ret)
-               return ret;
-
-       return 0;
-}
-
-void
-nouveau_bar_destroy(struct nouveau_bar *bar)
-{
-       nouveau_subdev_destroy(&bar->base);
-}
-
-void
-_nouveau_bar_dtor(struct nouveau_object *object)
-{
-       struct nouveau_bar *bar = (void *)object;
-       nouveau_bar_destroy(bar);
-}
diff --git a/drivers/gpu/drm/nouveau/core/subdev/bar/gk20a.c b/drivers/gpu/drm/nouveau/core/subdev/bar/gk20a.c
deleted file mode 100644 (file)
index bf877af..0000000
+++ /dev/null
@@ -1,54 +0,0 @@
-/*
- * Copyright (c) 2014, NVIDIA CORPORATION. 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 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 <subdev/bar.h>
-
-#include "priv.h"
-
-int
-gk20a_bar_ctor(struct nouveau_object *parent, struct nouveau_object *engine,
-              struct nouveau_oclass *oclass, void *data, u32 size,
-              struct nouveau_object **pobject)
-{
-       struct nouveau_bar *bar;
-       int ret;
-
-       ret = nvc0_bar_ctor(parent, engine, oclass, data, size, pobject);
-       if (ret)
-               return ret;
-
-       bar = (struct nouveau_bar *)*pobject;
-       bar->iomap_uncached = true;
-
-       return 0;
-}
-
-struct nouveau_oclass
-gk20a_bar_oclass = {
-       .handle = NV_SUBDEV(BAR, 0xea),
-       .ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = gk20a_bar_ctor,
-               .dtor = nvc0_bar_dtor,
-               .init = nvc0_bar_init,
-               .fini = _nouveau_bar_fini,
-       },
-};
diff --git a/drivers/gpu/drm/nouveau/core/subdev/bar/nv50.c b/drivers/gpu/drm/nouveau/core/subdev/bar/nv50.c
deleted file mode 100644 (file)
index f748ba4..0000000
+++ /dev/null
@@ -1,273 +0,0 @@
-/*
- * Copyright 2012 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 <core/gpuobj.h>
-
-#include <subdev/timer.h>
-#include <subdev/fb.h>
-#include <subdev/vm.h>
-
-#include "priv.h"
-
-struct nv50_bar_priv {
-       struct nouveau_bar base;
-       spinlock_t lock;
-       struct nouveau_gpuobj *mem;
-       struct nouveau_gpuobj *pad;
-       struct nouveau_gpuobj *pgd;
-       struct nouveau_vm *bar1_vm;
-       struct nouveau_gpuobj *bar1;
-       struct nouveau_vm *bar3_vm;
-       struct nouveau_gpuobj *bar3;
-};
-
-static int
-nv50_bar_kmap(struct nouveau_bar *bar, struct nouveau_mem *mem,
-             u32 flags, struct nouveau_vma *vma)
-{
-       struct nv50_bar_priv *priv = (void *)bar;
-       int ret;
-
-       ret = nouveau_vm_get(priv->bar3_vm, mem->size << 12, 12, flags, vma);
-       if (ret)
-               return ret;
-
-       nouveau_vm_map(vma, mem);
-       return 0;
-}
-
-static int
-nv50_bar_umap(struct nouveau_bar *bar, struct nouveau_mem *mem,
-             u32 flags, struct nouveau_vma *vma)
-{
-       struct nv50_bar_priv *priv = (void *)bar;
-       int ret;
-
-       ret = nouveau_vm_get(priv->bar1_vm, mem->size << 12, 12, flags, vma);
-       if (ret)
-               return ret;
-
-       nouveau_vm_map(vma, mem);
-       return 0;
-}
-
-static void
-nv50_bar_unmap(struct nouveau_bar *bar, struct nouveau_vma *vma)
-{
-       nouveau_vm_unmap(vma);
-       nouveau_vm_put(vma);
-}
-
-static void
-nv50_bar_flush(struct nouveau_bar *bar)
-{
-       struct nv50_bar_priv *priv = (void *)bar;
-       unsigned long flags;
-       spin_lock_irqsave(&priv->lock, flags);
-       nv_wr32(priv, 0x00330c, 0x00000001);
-       if (!nv_wait(priv, 0x00330c, 0x00000002, 0x00000000))
-               nv_warn(priv, "flush timeout\n");
-       spin_unlock_irqrestore(&priv->lock, flags);
-}
-
-void
-nv84_bar_flush(struct nouveau_bar *bar)
-{
-       struct nv50_bar_priv *priv = (void *)bar;
-       unsigned long flags;
-       spin_lock_irqsave(&priv->lock, flags);
-       nv_wr32(bar, 0x070000, 0x00000001);
-       if (!nv_wait(priv, 0x070000, 0x00000002, 0x00000000))
-               nv_warn(priv, "flush timeout\n");
-       spin_unlock_irqrestore(&priv->lock, flags);
-}
-
-static int
-nv50_bar_ctor(struct nouveau_object *parent, struct nouveau_object *engine,
-             struct nouveau_oclass *oclass, void *data, u32 size,
-             struct nouveau_object **pobject)
-{
-       struct nouveau_device *device = nv_device(parent);
-       struct nouveau_object *heap;
-       struct nouveau_vm *vm;
-       struct nv50_bar_priv *priv;
-       u64 start, limit;
-       int ret;
-
-       ret = nouveau_bar_create(parent, engine, oclass, &priv);
-       *pobject = nv_object(priv);
-       if (ret)
-               return ret;
-
-       ret = nouveau_gpuobj_new(nv_object(priv), NULL, 0x20000, 0,
-                                NVOBJ_FLAG_HEAP, &priv->mem);
-       heap = nv_object(priv->mem);
-       if (ret)
-               return ret;
-
-       ret = nouveau_gpuobj_new(nv_object(priv), heap,
-                               (device->chipset == 0x50) ? 0x1400 : 0x0200,
-                                0, 0, &priv->pad);
-       if (ret)
-               return ret;
-
-       ret = nouveau_gpuobj_new(nv_object(priv), heap, 0x4000, 0,
-                                0, &priv->pgd);
-       if (ret)
-               return ret;
-
-       /* BAR3 */
-       start = 0x0100000000ULL;
-       limit = start + nv_device_resource_len(device, 3);
-
-       ret = nouveau_vm_new(device, start, limit, start, &vm);
-       if (ret)
-               return ret;
-
-       atomic_inc(&vm->engref[NVDEV_SUBDEV_BAR]);
-
-       ret = nouveau_gpuobj_new(nv_object(priv), heap,
-                                ((limit-- - start) >> 12) * 8, 0x1000,
-                                NVOBJ_FLAG_ZERO_ALLOC, &vm->pgt[0].obj[0]);
-       vm->pgt[0].refcount[0] = 1;
-       if (ret)
-               return ret;
-
-       ret = nouveau_vm_ref(vm, &priv->bar3_vm, priv->pgd);
-       nouveau_vm_ref(NULL, &vm, NULL);
-       if (ret)
-               return ret;
-
-       ret = nouveau_gpuobj_new(nv_object(priv), heap, 24, 16, 0, &priv->bar3);
-       if (ret)
-               return ret;
-
-       nv_wo32(priv->bar3, 0x00, 0x7fc00000);
-       nv_wo32(priv->bar3, 0x04, lower_32_bits(limit));
-       nv_wo32(priv->bar3, 0x08, lower_32_bits(start));
-       nv_wo32(priv->bar3, 0x0c, upper_32_bits(limit) << 24 |
-                                 upper_32_bits(start));
-       nv_wo32(priv->bar3, 0x10, 0x00000000);
-       nv_wo32(priv->bar3, 0x14, 0x00000000);
-
-       /* BAR1 */
-       start = 0x0000000000ULL;
-       limit = start + nv_device_resource_len(device, 1);
-
-       ret = nouveau_vm_new(device, start, limit--, start, &vm);
-       if (ret)
-               return ret;
-
-       atomic_inc(&vm->engref[NVDEV_SUBDEV_BAR]);
-
-       ret = nouveau_vm_ref(vm, &priv->bar1_vm, priv->pgd);
-       nouveau_vm_ref(NULL, &vm, NULL);
-       if (ret)
-               return ret;
-
-       ret = nouveau_gpuobj_new(nv_object(priv), heap, 24, 16, 0, &priv->bar1);
-       if (ret)
-               return ret;
-
-       nv_wo32(priv->bar1, 0x00, 0x7fc00000);
-       nv_wo32(priv->bar1, 0x04, lower_32_bits(limit));
-       nv_wo32(priv->bar1, 0x08, lower_32_bits(start));
-       nv_wo32(priv->bar1, 0x0c, upper_32_bits(limit) << 24 |
-                                 upper_32_bits(start));
-       nv_wo32(priv->bar1, 0x10, 0x00000000);
-       nv_wo32(priv->bar1, 0x14, 0x00000000);
-
-       priv->base.alloc = nouveau_bar_alloc;
-       priv->base.kmap = nv50_bar_kmap;
-       priv->base.umap = nv50_bar_umap;
-       priv->base.unmap = nv50_bar_unmap;
-       if (device->chipset == 0x50)
-               priv->base.flush = nv50_bar_flush;
-       else
-               priv->base.flush = nv84_bar_flush;
-       spin_lock_init(&priv->lock);
-       return 0;
-}
-
-static void
-nv50_bar_dtor(struct nouveau_object *object)
-{
-       struct nv50_bar_priv *priv = (void *)object;
-       nouveau_gpuobj_ref(NULL, &priv->bar1);
-       nouveau_vm_ref(NULL, &priv->bar1_vm, priv->pgd);
-       nouveau_gpuobj_ref(NULL, &priv->bar3);
-       if (priv->bar3_vm) {
-               nouveau_gpuobj_ref(NULL, &priv->bar3_vm->pgt[0].obj[0]);
-               nouveau_vm_ref(NULL, &priv->bar3_vm, priv->pgd);
-       }
-       nouveau_gpuobj_ref(NULL, &priv->pgd);
-       nouveau_gpuobj_ref(NULL, &priv->pad);
-       nouveau_gpuobj_ref(NULL, &priv->mem);
-       nouveau_bar_destroy(&priv->base);
-}
-
-static int
-nv50_bar_init(struct nouveau_object *object)
-{
-       struct nv50_bar_priv *priv = (void *)object;
-       int ret, i;
-
-       ret = nouveau_bar_init(&priv->base);
-       if (ret)
-               return ret;
-
-       nv_mask(priv, 0x000200, 0x00000100, 0x00000000);
-       nv_mask(priv, 0x000200, 0x00000100, 0x00000100);
-       nv_wr32(priv, 0x100c80, 0x00060001);
-       if (!nv_wait(priv, 0x100c80, 0x00000001, 0x00000000)) {
-               nv_error(priv, "vm flush timeout\n");
-               return -EBUSY;
-       }
-
-       nv_wr32(priv, 0x001704, 0x00000000 | priv->mem->addr >> 12);
-       nv_wr32(priv, 0x001704, 0x40000000 | priv->mem->addr >> 12);
-       nv_wr32(priv, 0x001708, 0x80000000 | priv->bar1->node->offset >> 4);
-       nv_wr32(priv, 0x00170c, 0x80000000 | priv->bar3->node->offset >> 4);
-       for (i = 0; i < 8; i++)
-               nv_wr32(priv, 0x001900 + (i * 4), 0x00000000);
-       return 0;
-}
-
-static int
-nv50_bar_fini(struct nouveau_object *object, bool suspend)
-{
-       struct nv50_bar_priv *priv = (void *)object;
-       return nouveau_bar_fini(&priv->base, suspend);
-}
-
-struct nouveau_oclass
-nv50_bar_oclass = {
-       .handle = NV_SUBDEV(BAR, 0x50),
-       .ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nv50_bar_ctor,
-               .dtor = nv50_bar_dtor,
-               .init = nv50_bar_init,
-               .fini = nv50_bar_fini,
-       },
-};
diff --git a/drivers/gpu/drm/nouveau/core/subdev/bar/nvc0.c b/drivers/gpu/drm/nouveau/core/subdev/bar/nvc0.c
deleted file mode 100644 (file)
index 05a278b..0000000
+++ /dev/null
@@ -1,220 +0,0 @@
-/*
- * Copyright 2012 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 <core/gpuobj.h>
-
-#include <subdev/timer.h>
-#include <subdev/fb.h>
-#include <subdev/vm.h>
-
-#include "priv.h"
-
-struct nvc0_bar_priv_vm {
-       struct nouveau_gpuobj *mem;
-       struct nouveau_gpuobj *pgd;
-       struct nouveau_vm *vm;
-};
-
-struct nvc0_bar_priv {
-       struct nouveau_bar base;
-       spinlock_t lock;
-       struct nvc0_bar_priv_vm bar[2];
-};
-
-static int
-nvc0_bar_kmap(struct nouveau_bar *bar, struct nouveau_mem *mem,
-             u32 flags, struct nouveau_vma *vma)
-{
-       struct nvc0_bar_priv *priv = (void *)bar;
-       int ret;
-
-       ret = nouveau_vm_get(priv->bar[0].vm, mem->size << 12, 12, flags, vma);
-       if (ret)
-               return ret;
-
-       nouveau_vm_map(vma, mem);
-       return 0;
-}
-
-static int
-nvc0_bar_umap(struct nouveau_bar *bar, struct nouveau_mem *mem,
-             u32 flags, struct nouveau_vma *vma)
-{
-       struct nvc0_bar_priv *priv = (void *)bar;
-       int ret;
-
-       ret = nouveau_vm_get(priv->bar[1].vm, mem->size << 12,
-                            mem->page_shift, flags, vma);
-       if (ret)
-               return ret;
-
-       nouveau_vm_map(vma, mem);
-       return 0;
-}
-
-static void
-nvc0_bar_unmap(struct nouveau_bar *bar, struct nouveau_vma *vma)
-{
-       nouveau_vm_unmap(vma);
-       nouveau_vm_put(vma);
-}
-
-static int
-nvc0_bar_init_vm(struct nvc0_bar_priv *priv, struct nvc0_bar_priv_vm *bar_vm,
-                int bar_nr)
-{
-       struct nouveau_device *device = nv_device(&priv->base);
-       struct nouveau_vm *vm;
-       resource_size_t bar_len;
-       int ret;
-
-       ret = nouveau_gpuobj_new(nv_object(priv), NULL, 0x1000, 0, 0,
-                               &bar_vm->mem);
-       if (ret)
-               return ret;
-
-       ret = nouveau_gpuobj_new(nv_object(priv), NULL, 0x8000, 0, 0,
-                               &bar_vm->pgd);
-       if (ret)
-               return ret;
-
-       bar_len = nv_device_resource_len(device, bar_nr);
-
-       ret = nouveau_vm_new(device, 0, bar_len, 0, &vm);
-       if (ret)
-               return ret;
-
-       atomic_inc(&vm->engref[NVDEV_SUBDEV_BAR]);
-
-       /*
-        * Bootstrap page table lookup.
-        */
-       if (bar_nr == 3) {
-               ret = nouveau_gpuobj_new(nv_object(priv), NULL,
-                                        (bar_len >> 12) * 8, 0x1000,
-                                        NVOBJ_FLAG_ZERO_ALLOC,
-                                       &vm->pgt[0].obj[0]);
-               vm->pgt[0].refcount[0] = 1;
-               if (ret)
-                       return ret;
-       }
-
-       ret = nouveau_vm_ref(vm, &bar_vm->vm, bar_vm->pgd);
-       nouveau_vm_ref(NULL, &vm, NULL);
-       if (ret)
-               return ret;
-
-       nv_wo32(bar_vm->mem, 0x0200, lower_32_bits(bar_vm->pgd->addr));
-       nv_wo32(bar_vm->mem, 0x0204, upper_32_bits(bar_vm->pgd->addr));
-       nv_wo32(bar_vm->mem, 0x0208, lower_32_bits(bar_len - 1));
-       nv_wo32(bar_vm->mem, 0x020c, upper_32_bits(bar_len - 1));
-
-       return 0;
-}
-
-int
-nvc0_bar_ctor(struct nouveau_object *parent, struct nouveau_object *engine,
-             struct nouveau_oclass *oclass, void *data, u32 size,
-             struct nouveau_object **pobject)
-{
-       struct nouveau_device *device = nv_device(parent);
-       struct nvc0_bar_priv *priv;
-       bool has_bar3 = nv_device_resource_len(device, 3) != 0;
-       int ret;
-
-       ret = nouveau_bar_create(parent, engine, oclass, &priv);
-       *pobject = nv_object(priv);
-       if (ret)
-               return ret;
-
-       /* BAR3 */
-       if (has_bar3) {
-               ret = nvc0_bar_init_vm(priv, &priv->bar[0], 3);
-               if (ret)
-                       return ret;
-               priv->base.alloc = nouveau_bar_alloc;
-               priv->base.kmap = nvc0_bar_kmap;
-       }
-
-       /* BAR1 */
-       ret = nvc0_bar_init_vm(priv, &priv->bar[1], 1);
-       if (ret)
-               return ret;
-
-       priv->base.umap = nvc0_bar_umap;
-       priv->base.unmap = nvc0_bar_unmap;
-       priv->base.flush = nv84_bar_flush;
-       spin_lock_init(&priv->lock);
-       return 0;
-}
-
-void
-nvc0_bar_dtor(struct nouveau_object *object)
-{
-       struct nvc0_bar_priv *priv = (void *)object;
-
-       nouveau_vm_ref(NULL, &priv->bar[1].vm, priv->bar[1].pgd);
-       nouveau_gpuobj_ref(NULL, &priv->bar[1].pgd);
-       nouveau_gpuobj_ref(NULL, &priv->bar[1].mem);
-
-       if (priv->bar[0].vm) {
-               nouveau_gpuobj_ref(NULL, &priv->bar[0].vm->pgt[0].obj[0]);
-               nouveau_vm_ref(NULL, &priv->bar[0].vm, priv->bar[0].pgd);
-       }
-       nouveau_gpuobj_ref(NULL, &priv->bar[0].pgd);
-       nouveau_gpuobj_ref(NULL, &priv->bar[0].mem);
-
-       nouveau_bar_destroy(&priv->base);
-}
-
-int
-nvc0_bar_init(struct nouveau_object *object)
-{
-       struct nvc0_bar_priv *priv = (void *)object;
-       int ret;
-
-       ret = nouveau_bar_init(&priv->base);
-       if (ret)
-               return ret;
-
-       nv_mask(priv, 0x000200, 0x00000100, 0x00000000);
-       nv_mask(priv, 0x000200, 0x00000100, 0x00000100);
-
-       nv_wr32(priv, 0x001704, 0x80000000 | priv->bar[1].mem->addr >> 12);
-       if (priv->bar[0].mem)
-               nv_wr32(priv, 0x001714,
-                       0xc0000000 | priv->bar[0].mem->addr >> 12);
-       return 0;
-}
-
-struct nouveau_oclass
-nvc0_bar_oclass = {
-       .handle = NV_SUBDEV(BAR, 0xc0),
-       .ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nvc0_bar_ctor,
-               .dtor = nvc0_bar_dtor,
-               .init = nvc0_bar_init,
-               .fini = _nouveau_bar_fini,
-       },
-};
diff --git a/drivers/gpu/drm/nouveau/core/subdev/bar/priv.h b/drivers/gpu/drm/nouveau/core/subdev/bar/priv.h
deleted file mode 100644 (file)
index 3ee8b14..0000000
+++ /dev/null
@@ -1,32 +0,0 @@
-#ifndef __NVKM_BAR_PRIV_H__
-#define __NVKM_BAR_PRIV_H__
-
-#include <subdev/bar.h>
-
-#define nouveau_bar_create(p,e,o,d)                                            \
-       nouveau_bar_create_((p), (e), (o), sizeof(**d), (void **)d)
-#define nouveau_bar_init(p)                                                    \
-       nouveau_subdev_init(&(p)->base)
-#define nouveau_bar_fini(p,s)                                                  \
-       nouveau_subdev_fini(&(p)->base, (s))
-
-int nouveau_bar_create_(struct nouveau_object *, struct nouveau_object *,
-                       struct nouveau_oclass *, int, void **);
-void nouveau_bar_destroy(struct nouveau_bar *);
-
-void _nouveau_bar_dtor(struct nouveau_object *);
-#define _nouveau_bar_init _nouveau_subdev_init
-#define _nouveau_bar_fini _nouveau_subdev_fini
-
-int  nouveau_bar_alloc(struct nouveau_bar *, struct nouveau_object *,
-                      struct nouveau_mem *, struct nouveau_object **);
-
-void nv84_bar_flush(struct nouveau_bar *);
-
-int nvc0_bar_ctor(struct nouveau_object *, struct nouveau_object *,
-                 struct nouveau_oclass *, void *, u32,
-                 struct nouveau_object **);
-void nvc0_bar_dtor(struct nouveau_object *);
-int nvc0_bar_init(struct nouveau_object *);
-
-#endif
diff --git a/drivers/gpu/drm/nouveau/core/subdev/bios/M0203.c b/drivers/gpu/drm/nouveau/core/subdev/bios/M0203.c
deleted file mode 100644 (file)
index 28906b1..0000000
+++ /dev/null
@@ -1,129 +0,0 @@
-/*
- * Copyright 2014 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 <subdev/bios.h>
-#include <subdev/bios/bit.h>
-#include <subdev/bios/M0203.h>
-
-u32
-nvbios_M0203Te(struct nouveau_bios *bios, u8 *ver, u8 *hdr, u8 *cnt, u8 *len)
-{
-       struct bit_entry bit_M;
-       u32 data = 0x00000000;
-
-       if (!bit_entry(bios, 'M', &bit_M)) {
-               if (bit_M.version == 2 && bit_M.length > 0x04)
-                       data = nv_ro16(bios, bit_M.offset + 0x03);
-               if (data) {
-                       *ver = nv_ro08(bios, data + 0x00);
-                       switch (*ver) {
-                       case 0x10:
-                               *hdr = nv_ro08(bios, data + 0x01);
-                               *len = nv_ro08(bios, data + 0x02);
-                               *cnt = nv_ro08(bios, data + 0x03);
-                               return data;
-                       default:
-                               break;
-                       }
-               }
-       }
-
-       return 0x00000000;
-}
-
-u32
-nvbios_M0203Tp(struct nouveau_bios *bios, u8 *ver, u8 *hdr, u8 *cnt, u8 *len,
-              struct nvbios_M0203T *info)
-{
-       u32 data = nvbios_M0203Te(bios, ver, hdr, cnt, len);
-       memset(info, 0x00, sizeof(*info));
-       switch (!!data * *ver) {
-       case 0x10:
-               info->type    = nv_ro08(bios, data + 0x04);
-               info->pointer = nv_ro16(bios, data + 0x05);
-               break;
-       default:
-               break;
-       }
-       return data;
-}
-
-u32
-nvbios_M0203Ee(struct nouveau_bios *bios, int idx, u8 *ver, u8 *hdr)
-{
-       u8  cnt, len;
-       u32 data = nvbios_M0203Te(bios, ver, hdr, &cnt, &len);
-       if (data && idx < cnt) {
-               data = data + *hdr + idx * len;
-               *hdr = len;
-               return data;
-       }
-       return 0x00000000;
-}
-
-u32
-nvbios_M0203Ep(struct nouveau_bios *bios, int idx, u8 *ver, u8 *hdr,
-              struct nvbios_M0203E *info)
-{
-       u32 data = nvbios_M0203Ee(bios, idx, ver, hdr);
-       memset(info, 0x00, sizeof(*info));
-       switch (!!data * *ver) {
-       case 0x10:
-               info->type  = (nv_ro08(bios, data + 0x00) & 0x0f) >> 0;
-               info->strap = (nv_ro08(bios, data + 0x00) & 0xf0) >> 4;
-               info->group = (nv_ro08(bios, data + 0x01) & 0x0f) >> 0;
-               return data;
-       default:
-               break;
-       }
-       return 0x00000000;
-}
-
-u32
-nvbios_M0203Em(struct nouveau_bios *bios, u8 ramcfg, u8 *ver, u8 *hdr,
-              struct nvbios_M0203E *info)
-{
-       struct nvbios_M0203T M0203T;
-       u8  cnt, len, idx = 0xff;
-       u32 data;
-
-       if (!nvbios_M0203Tp(bios, ver, hdr, &cnt, &len, &M0203T)) {
-               nv_warn(bios, "M0203T not found\n");
-               return 0x00000000;
-       }
-
-       while ((data = nvbios_M0203Ep(bios, ++idx, ver, hdr, info))) {
-               switch (M0203T.type) {
-               case M0203T_TYPE_RAMCFG:
-                       if (info->strap != ramcfg)
-                               continue;
-                       return data;
-               default:
-                       nv_warn(bios, "M0203T type %02x\n", M0203T.type);
-                       return 0x00000000;
-               }
-       }
-
-       return data;
-}
diff --git a/drivers/gpu/drm/nouveau/core/subdev/bios/M0205.c b/drivers/gpu/drm/nouveau/core/subdev/bios/M0205.c
deleted file mode 100644 (file)
index ac9617c..0000000
+++ /dev/null
@@ -1,136 +0,0 @@
-/*
- * Copyright 2013 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 <subdev/bios.h>
-#include <subdev/bios/bit.h>
-#include <subdev/bios/M0205.h>
-
-u32
-nvbios_M0205Te(struct nouveau_bios *bios,
-              u8 *ver, u8 *hdr, u8 *cnt, u8 *len, u8 *snr, u8 *ssz)
-{
-       struct bit_entry bit_M;
-       u32 data = 0x00000000;
-
-       if (!bit_entry(bios, 'M', &bit_M)) {
-               if (bit_M.version == 2 && bit_M.length > 0x08)
-                       data = nv_ro32(bios, bit_M.offset + 0x05);
-               if (data) {
-                       *ver = nv_ro08(bios, data + 0x00);
-                       switch (*ver) {
-                       case 0x10:
-                               *hdr = nv_ro08(bios, data + 0x01);
-                               *len = nv_ro08(bios, data + 0x02);
-                               *ssz = nv_ro08(bios, data + 0x03);
-                               *snr = nv_ro08(bios, data + 0x04);
-                               *cnt = nv_ro08(bios, data + 0x05);
-                               return data;
-                       default:
-                               break;
-                       }
-               }
-       }
-
-       return 0x00000000;
-}
-
-u32
-nvbios_M0205Tp(struct nouveau_bios *bios,
-              u8 *ver, u8 *hdr, u8 *cnt, u8 *len, u8 *snr, u8 *ssz,
-              struct nvbios_M0205T *info)
-{
-       u32 data = nvbios_M0205Te(bios, ver, hdr, cnt, len, snr, ssz);
-       memset(info, 0x00, sizeof(*info));
-       switch (!!data * *ver) {
-       case 0x10:
-               info->freq = nv_ro16(bios, data + 0x06);
-               break;
-       default:
-               break;
-       }
-       return data;
-}
-
-u32
-nvbios_M0205Ee(struct nouveau_bios *bios, int idx,
-              u8 *ver, u8 *hdr, u8 *cnt, u8 *len)
-{
-       u8  snr, ssz;
-       u32 data = nvbios_M0205Te(bios, ver, hdr, cnt, len, &snr, &ssz);
-       if (data && idx < *cnt) {
-               data = data + *hdr + idx * (*len + (snr * ssz));
-               *hdr = *len;
-               *cnt = snr;
-               *len = ssz;
-               return data;
-       }
-       return 0x00000000;
-}
-
-u32
-nvbios_M0205Ep(struct nouveau_bios *bios, int idx,
-              u8 *ver, u8 *hdr, u8 *cnt, u8 *len,
-              struct nvbios_M0205E *info)
-{
-       u32 data = nvbios_M0205Ee(bios, idx, ver, hdr, cnt, len);
-       memset(info, 0x00, sizeof(*info));
-       switch (!!data * *ver) {
-       case 0x10:
-               info->type = nv_ro08(bios, data + 0x00) & 0x0f;
-               return data;
-       default:
-               break;
-       }
-       return 0x00000000;
-}
-
-u32
-nvbios_M0205Se(struct nouveau_bios *bios, int ent, int idx, u8 *ver, u8 *hdr)
-{
-
-       u8  cnt, len;
-       u32 data = nvbios_M0205Ee(bios, ent, ver, hdr, &cnt, &len);
-       if (data && idx < cnt) {
-               data = data + *hdr + idx * len;
-               *hdr = len;
-               return data;
-       }
-       return 0x00000000;
-}
-
-u32
-nvbios_M0205Sp(struct nouveau_bios *bios, int ent, int idx, u8 *ver, u8 *hdr,
-              struct nvbios_M0205S *info)
-{
-       u32 data = nvbios_M0205Se(bios, ent, idx, ver, hdr);
-       memset(info, 0x00, sizeof(*info));
-       switch (!!data * *ver) {
-       case 0x10:
-               info->data = nv_ro08(bios, data + 0x00);
-               return data;
-       default:
-               break;
-       }
-       return 0x00000000;
-}
diff --git a/drivers/gpu/drm/nouveau/core/subdev/bios/M0209.c b/drivers/gpu/drm/nouveau/core/subdev/bios/M0209.c
deleted file mode 100644 (file)
index b142a51..0000000
+++ /dev/null
@@ -1,137 +0,0 @@
-/*
- * Copyright 2013 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 <subdev/bios.h>
-#include <subdev/bios/bit.h>
-#include <subdev/bios/M0209.h>
-
-u32
-nvbios_M0209Te(struct nouveau_bios *bios,
-              u8 *ver, u8 *hdr, u8 *cnt, u8 *len, u8 *snr, u8 *ssz)
-{
-       struct bit_entry bit_M;
-       u32 data = 0x00000000;
-
-       if (!bit_entry(bios, 'M', &bit_M)) {
-               if (bit_M.version == 2 && bit_M.length > 0x0c)
-                       data = nv_ro32(bios, bit_M.offset + 0x09);
-               if (data) {
-                       *ver = nv_ro08(bios, data + 0x00);
-                       switch (*ver) {
-                       case 0x10:
-                               *hdr = nv_ro08(bios, data + 0x01);
-                               *len = nv_ro08(bios, data + 0x02);
-                               *ssz = nv_ro08(bios, data + 0x03);
-                               *snr = 1;
-                               *cnt = nv_ro08(bios, data + 0x04);
-                               return data;
-                       default:
-                               break;
-                       }
-               }
-       }
-
-       return 0x00000000;
-}
-
-u32
-nvbios_M0209Ee(struct nouveau_bios *bios, int idx,
-              u8 *ver, u8 *hdr, u8 *cnt, u8 *len)
-{
-       u8  snr, ssz;
-       u32 data = nvbios_M0209Te(bios, ver, hdr, cnt, len, &snr, &ssz);
-       if (data && idx < *cnt) {
-               data = data + *hdr + idx * (*len + (snr * ssz));
-               *hdr = *len;
-               *cnt = snr;
-               *len = ssz;
-               return data;
-       }
-       return 0x00000000;
-}
-
-u32
-nvbios_M0209Ep(struct nouveau_bios *bios, int idx,
-              u8 *ver, u8 *hdr, u8 *cnt, u8 *len,
-              struct nvbios_M0209E *info)
-{
-       u32 data = nvbios_M0209Ee(bios, idx, ver, hdr, cnt, len);
-       memset(info, 0x00, sizeof(*info));
-       switch (!!data * *ver) {
-       case 0x10:
-               info->v00_40 = (nv_ro08(bios, data + 0x00) & 0x40) >> 6;
-               info->bits   =  nv_ro08(bios, data + 0x00) & 0x3f;
-               info->modulo =  nv_ro08(bios, data + 0x01);
-               info->v02_40 = (nv_ro08(bios, data + 0x02) & 0x40) >> 6;
-               info->v02_07 =  nv_ro08(bios, data + 0x02) & 0x07;
-               info->v03    =  nv_ro08(bios, data + 0x03);
-               return data;
-       default:
-               break;
-       }
-       return 0x00000000;
-}
-
-u32
-nvbios_M0209Se(struct nouveau_bios *bios, int ent, int idx, u8 *ver, u8 *hdr)
-{
-
-       u8  cnt, len;
-       u32 data = nvbios_M0209Ee(bios, ent, ver, hdr, &cnt, &len);
-       if (data && idx < cnt) {
-               data = data + *hdr + idx * len;
-               *hdr = len;
-               return data;
-       }
-       return 0x00000000;
-}
-
-u32
-nvbios_M0209Sp(struct nouveau_bios *bios, int ent, int idx, u8 *ver, u8 *hdr,
-              struct nvbios_M0209S *info)
-{
-       struct nvbios_M0209E M0209E;
-       u8  cnt, len;
-       u32 data = nvbios_M0209Ep(bios, ent, ver, hdr, &cnt, &len, &M0209E);
-       if (data) {
-               u32 i, data = nvbios_M0209Se(bios, ent, idx, ver, hdr);
-               memset(info, 0x00, sizeof(*info));
-               switch (!!data * *ver) {
-               case 0x10:
-                       for (i = 0; i < ARRAY_SIZE(info->data); i++) {
-                               u32 bits = (i % M0209E.modulo) * M0209E.bits;
-                               u32 mask = (1ULL << M0209E.bits) - 1;
-                               u16  off = bits / 8;
-                               u8   mod = bits % 8;
-                               info->data[i] = nv_ro32(bios, data + off);
-                               info->data[i] = info->data[i] >> mod;
-                               info->data[i] = info->data[i] & mask;
-                       }
-                       return data;
-               default:
-                       break;
-               }
-       }
-       return 0x00000000;
-}
diff --git a/drivers/gpu/drm/nouveau/core/subdev/bios/P0260.c b/drivers/gpu/drm/nouveau/core/subdev/bios/P0260.c
deleted file mode 100644 (file)
index 199f4e5..0000000
+++ /dev/null
@@ -1,109 +0,0 @@
-/*
- * Copyright 2013 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 <subdev/bios.h>
-#include <subdev/bios/bit.h>
-#include <subdev/bios/ramcfg.h>
-#include <subdev/bios/P0260.h>
-
-u32
-nvbios_P0260Te(struct nouveau_bios *bios,
-              u8 *ver, u8 *hdr, u8 *cnt, u8 *len, u8 *xnr, u8 *xsz)
-{
-       struct bit_entry bit_P;
-       u32 data = 0x00000000;
-
-       if (!bit_entry(bios, 'P', &bit_P)) {
-               if (bit_P.version == 2 && bit_P.length > 0x63)
-                       data = nv_ro32(bios, bit_P.offset + 0x60);
-               if (data) {
-                       *ver = nv_ro08(bios, data + 0);
-                       switch (*ver) {
-                       case 0x10:
-                               *hdr = nv_ro08(bios, data + 1);
-                               *cnt = nv_ro08(bios, data + 2);
-                               *len = 4;
-                               *xnr = nv_ro08(bios, data + 3);
-                               *xsz = 4;
-                               return data;
-                       default:
-                               break;
-                       }
-               }
-       }
-
-       return 0x00000000;
-}
-
-u32
-nvbios_P0260Ee(struct nouveau_bios *bios, int idx, u8 *ver, u8 *len)
-{
-       u8  hdr, cnt, xnr, xsz;
-       u32 data = nvbios_P0260Te(bios, ver, &hdr, &cnt, len, &xnr, &xsz);
-       if (data && idx < cnt)
-               return data + hdr + (idx * *len);
-       return 0x00000000;
-}
-
-u32
-nvbios_P0260Ep(struct nouveau_bios *bios, int idx, u8 *ver, u8 *len,
-              struct nvbios_P0260E *info)
-{
-       u32 data = nvbios_P0260Ee(bios, idx, ver, len);
-       memset(info, 0x00, sizeof(*info));
-       switch (!!data * *ver) {
-       case 0x10:
-               info->data = nv_ro32(bios, data);
-               return data;
-       default:
-               break;
-       }
-       return 0x00000000;
-}
-
-u32
-nvbios_P0260Xe(struct nouveau_bios *bios, int idx, u8 *ver, u8 *xsz)
-{
-       u8  hdr, cnt, len, xnr;
-       u32 data = nvbios_P0260Te(bios, ver, &hdr, &cnt, &len, &xnr, xsz);
-       if (data && idx < xnr)
-               return data + hdr + (cnt * len) + (idx * *xsz);
-       return 0x00000000;
-}
-
-u32
-nvbios_P0260Xp(struct nouveau_bios *bios, int idx, u8 *ver, u8 *hdr,
-              struct nvbios_P0260X *info)
-{
-       u32 data = nvbios_P0260Xe(bios, idx, ver, hdr);
-       memset(info, 0x00, sizeof(*info));
-       switch (!!data * *ver) {
-       case 0x10:
-               info->data = nv_ro32(bios, data);
-               return data;
-       default:
-               break;
-       }
-       return 0x00000000;
-}
diff --git a/drivers/gpu/drm/nouveau/core/subdev/bios/base.c b/drivers/gpu/drm/nouveau/core/subdev/bios/base.c
deleted file mode 100644 (file)
index 7df3a27..0000000
+++ /dev/null
@@ -1,213 +0,0 @@
-/*
- * Copyright 2012 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 <core/object.h>
-#include <core/device.h>
-#include <core/subdev.h>
-#include <core/option.h>
-
-#include <subdev/bios.h>
-#include <subdev/bios/bmp.h>
-#include <subdev/bios/bit.h>
-
-#include "priv.h"
-
-u8
-nvbios_checksum(const u8 *data, int size)
-{
-       u8 sum = 0;
-       while (size--)
-               sum += *data++;
-       return sum;
-}
-
-u16
-nvbios_findstr(const u8 *data, int size, const char *str, int len)
-{
-       int i, j;
-
-       for (i = 0; i <= (size - len); i++) {
-               for (j = 0; j < len; j++)
-                       if ((char)data[i + j] != str[j])
-                               break;
-               if (j == len)
-                       return i;
-       }
-
-       return 0;
-}
-
-int
-nvbios_extend(struct nouveau_bios *bios, u32 length)
-{
-       if (bios->size < length) {
-               u8 *prev = bios->data;
-               if (!(bios->data = kmalloc(length, GFP_KERNEL))) {
-                       bios->data = prev;
-                       return -ENOMEM;
-               }
-               memcpy(bios->data, prev, bios->size);
-               bios->size = length;
-               kfree(prev);
-               return 1;
-       }
-       return 0;
-}
-
-static u8
-nouveau_bios_rd08(struct nouveau_object *object, u64 addr)
-{
-       struct nouveau_bios *bios = (void *)object;
-       return bios->data[addr];
-}
-
-static u16
-nouveau_bios_rd16(struct nouveau_object *object, u64 addr)
-{
-       struct nouveau_bios *bios = (void *)object;
-       return get_unaligned_le16(&bios->data[addr]);
-}
-
-static u32
-nouveau_bios_rd32(struct nouveau_object *object, u64 addr)
-{
-       struct nouveau_bios *bios = (void *)object;
-       return get_unaligned_le32(&bios->data[addr]);
-}
-
-static void
-nouveau_bios_wr08(struct nouveau_object *object, u64 addr, u8 data)
-{
-       struct nouveau_bios *bios = (void *)object;
-       bios->data[addr] = data;
-}
-
-static void
-nouveau_bios_wr16(struct nouveau_object *object, u64 addr, u16 data)
-{
-       struct nouveau_bios *bios = (void *)object;
-       put_unaligned_le16(data, &bios->data[addr]);
-}
-
-static void
-nouveau_bios_wr32(struct nouveau_object *object, u64 addr, u32 data)
-{
-       struct nouveau_bios *bios = (void *)object;
-       put_unaligned_le32(data, &bios->data[addr]);
-}
-
-static int
-nouveau_bios_ctor(struct nouveau_object *parent,
-                 struct nouveau_object *engine,
-                 struct nouveau_oclass *oclass, void *data, u32 size,
-                 struct nouveau_object **pobject)
-{
-       struct nouveau_bios *bios;
-       struct bit_entry bit_i;
-       int ret;
-
-       ret = nouveau_subdev_create(parent, engine, oclass, 0,
-                                   "VBIOS", "bios", &bios);
-       *pobject = nv_object(bios);
-       if (ret)
-               return ret;
-
-       ret = nvbios_shadow(bios);
-       if (ret)
-               return ret;
-
-       /* detect type of vbios we're dealing with */
-       bios->bmp_offset = nvbios_findstr(bios->data, bios->size,
-                                         "\xff\x7f""NV\0", 5);
-       if (bios->bmp_offset) {
-               nv_info(bios, "BMP version %x.%x\n",
-                       bmp_version(bios) >> 8,
-                       bmp_version(bios) & 0xff);
-       }
-
-       bios->bit_offset = nvbios_findstr(bios->data, bios->size,
-                                         "\xff\xb8""BIT", 5);
-       if (bios->bit_offset)
-               nv_info(bios, "BIT signature found\n");
-
-       /* determine the vbios version number */
-       if (!bit_entry(bios, 'i', &bit_i) && bit_i.length >= 4) {
-               bios->version.major = nv_ro08(bios, bit_i.offset + 3);
-               bios->version.chip  = nv_ro08(bios, bit_i.offset + 2);
-               bios->version.minor = nv_ro08(bios, bit_i.offset + 1);
-               bios->version.micro = nv_ro08(bios, bit_i.offset + 0);
-               bios->version.patch = nv_ro08(bios, bit_i.offset + 4);
-       } else
-       if (bmp_version(bios)) {
-               bios->version.major = nv_ro08(bios, bios->bmp_offset + 13);
-               bios->version.chip  = nv_ro08(bios, bios->bmp_offset + 12);
-               bios->version.minor = nv_ro08(bios, bios->bmp_offset + 11);
-               bios->version.micro = nv_ro08(bios, bios->bmp_offset + 10);
-       }
-
-       nv_info(bios, "version %02x.%02x.%02x.%02x.%02x\n",
-               bios->version.major, bios->version.chip,
-               bios->version.minor, bios->version.micro, bios->version.patch);
-
-       return 0;
-}
-
-static void
-nouveau_bios_dtor(struct nouveau_object *object)
-{
-       struct nouveau_bios *bios = (void *)object;
-       kfree(bios->data);
-       nouveau_subdev_destroy(&bios->base);
-}
-
-static int
-nouveau_bios_init(struct nouveau_object *object)
-{
-       struct nouveau_bios *bios = (void *)object;
-       return nouveau_subdev_init(&bios->base);
-}
-
-static int
-nouveau_bios_fini(struct nouveau_object *object, bool suspend)
-{
-       struct nouveau_bios *bios = (void *)object;
-       return nouveau_subdev_fini(&bios->base, suspend);
-}
-
-struct nouveau_oclass
-nouveau_bios_oclass = {
-       .handle = NV_SUBDEV(VBIOS, 0x00),
-       .ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nouveau_bios_ctor,
-               .dtor = nouveau_bios_dtor,
-               .init = nouveau_bios_init,
-               .fini = nouveau_bios_fini,
-               .rd08 = nouveau_bios_rd08,
-               .rd16 = nouveau_bios_rd16,
-               .rd32 = nouveau_bios_rd32,
-               .wr08 = nouveau_bios_wr08,
-               .wr16 = nouveau_bios_wr16,
-               .wr32 = nouveau_bios_wr32,
-       },
-};
diff --git a/drivers/gpu/drm/nouveau/core/subdev/bios/bit.c b/drivers/gpu/drm/nouveau/core/subdev/bios/bit.c
deleted file mode 100644 (file)
index 1d03a3f..0000000
+++ /dev/null
@@ -1,52 +0,0 @@
-/*
- * Copyright 2012 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 "core/object.h"
-
-#include "subdev/bios.h"
-#include "subdev/bios/bit.h"
-
-int
-bit_entry(struct nouveau_bios *bios, u8 id, struct bit_entry *bit)
-{
-       if (likely(bios->bit_offset)) {
-               u8  entries = nv_ro08(bios, bios->bit_offset + 10);
-               u32 entry   = bios->bit_offset + 12;
-               while (entries--) {
-                       if (nv_ro08(bios, entry + 0) == id) {
-                               bit->id      = nv_ro08(bios, entry + 0);
-                               bit->version = nv_ro08(bios, entry + 1);
-                               bit->length  = nv_ro16(bios, entry + 2);
-                               bit->offset  = nv_ro16(bios, entry + 4);
-                               return 0;
-                       }
-
-                       entry += nv_ro08(bios, bios->bit_offset + 9);
-               }
-
-               return -ENOENT;
-       }
-
-       return -EINVAL;
-}
diff --git a/drivers/gpu/drm/nouveau/core/subdev/bios/boost.c b/drivers/gpu/drm/nouveau/core/subdev/bios/boost.c
deleted file mode 100644 (file)
index c1835e5..0000000
+++ /dev/null
@@ -1,127 +0,0 @@
-/*
- * Copyright 2013 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 <subdev/bios.h>
-#include <subdev/bios/bit.h>
-#include <subdev/bios/boost.h>
-
-u16
-nvbios_boostTe(struct nouveau_bios *bios,
-              u8 *ver, u8 *hdr, u8 *cnt, u8 *len, u8 *snr, u8 *ssz)
-{
-       struct bit_entry bit_P;
-       u16 boost = 0x0000;
-
-       if (!bit_entry(bios, 'P', &bit_P)) {
-               if (bit_P.version == 2)
-                       boost = nv_ro16(bios, bit_P.offset + 0x30);
-
-               if (boost) {
-                       *ver = nv_ro08(bios, boost + 0);
-                       switch (*ver) {
-                       case 0x11:
-                               *hdr = nv_ro08(bios, boost + 1);
-                               *cnt = nv_ro08(bios, boost + 5);
-                               *len = nv_ro08(bios, boost + 2);
-                               *snr = nv_ro08(bios, boost + 4);
-                               *ssz = nv_ro08(bios, boost + 3);
-                               return boost;
-                       default:
-                               break;
-                       }
-               }
-       }
-
-       return 0x0000;
-}
-
-u16
-nvbios_boostEe(struct nouveau_bios *bios, int idx,
-              u8 *ver, u8 *hdr, u8 *cnt, u8 *len)
-{
-       u8  snr, ssz;
-       u16 data = nvbios_boostTe(bios, ver, hdr, cnt, len, &snr, &ssz);
-       if (data && idx < *cnt) {
-               data = data + *hdr + (idx * (*len + (snr * ssz)));
-               *hdr = *len;
-               *cnt = snr;
-               *len = ssz;
-               return data;
-       }
-       return 0x0000;
-}
-
-u16
-nvbios_boostEp(struct nouveau_bios *bios, int idx,
-              u8 *ver, u8 *hdr, u8 *cnt, u8 *len, struct nvbios_boostE *info)
-{
-       u16 data = nvbios_boostEe(bios, idx, ver, hdr, cnt, len);
-       memset(info, 0x00, sizeof(*info));
-       if (data) {
-               info->pstate = (nv_ro16(bios, data + 0x00) & 0x01e0) >> 5;
-               info->min    =  nv_ro16(bios, data + 0x02) * 1000;
-               info->max    =  nv_ro16(bios, data + 0x04) * 1000;
-       }
-       return data;
-}
-
-u16
-nvbios_boostEm(struct nouveau_bios *bios, u8 pstate,
-              u8 *ver, u8 *hdr, u8 *cnt, u8 *len, struct nvbios_boostE *info)
-{
-       u32 data, idx = 0;
-       while ((data = nvbios_boostEp(bios, idx++, ver, hdr, cnt, len, info))) {
-               if (info->pstate == pstate)
-                       break;
-       }
-       return data;
-}
-
-u16
-nvbios_boostSe(struct nouveau_bios *bios, int idx,
-              u16 data, u8 *ver, u8 *hdr, u8 cnt, u8 len)
-{
-       if (data && idx < cnt) {
-               data = data + *hdr + (idx * len);
-               *hdr = len;
-               return data;
-       }
-       return 0x0000;
-}
-
-u16
-nvbios_boostSp(struct nouveau_bios *bios, int idx,
-              u16 data, u8 *ver, u8 *hdr, u8 cnt, u8 len,
-              struct nvbios_boostS *info)
-{
-       data = nvbios_boostSe(bios, idx, data, ver, hdr, cnt, len);
-       memset(info, 0x00, sizeof(*info));
-       if (data) {
-               info->domain  = nv_ro08(bios, data + 0x00);
-               info->percent = nv_ro08(bios, data + 0x01);
-               info->min     = nv_ro16(bios, data + 0x02) * 1000;
-               info->max     = nv_ro16(bios, data + 0x04) * 1000;
-       }
-       return data;
-}
diff --git a/drivers/gpu/drm/nouveau/core/subdev/bios/conn.c b/drivers/gpu/drm/nouveau/core/subdev/bios/conn.c
deleted file mode 100644 (file)
index 2ede3bc..0000000
+++ /dev/null
@@ -1,100 +0,0 @@
-/*
- * Copyright 2012 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 <core/device.h>
-
-#include <subdev/bios.h>
-#include <subdev/bios/dcb.h>
-#include <subdev/bios/conn.h>
-
-u32
-nvbios_connTe(struct nouveau_bios *bios, u8 *ver, u8 *hdr, u8 *cnt, u8 *len)
-{
-       u32 dcb = dcb_table(bios, ver, hdr, cnt, len);
-       if (dcb && *ver >= 0x30 && *hdr >= 0x16) {
-               u32 data = nv_ro16(bios, dcb + 0x14);
-               if (data) {
-                       *ver = nv_ro08(bios, data + 0);
-                       *hdr = nv_ro08(bios, data + 1);
-                       *cnt = nv_ro08(bios, data + 2);
-                       *len = nv_ro08(bios, data + 3);
-                       return data;
-               }
-       }
-       return 0x00000000;
-}
-
-u32
-nvbios_connTp(struct nouveau_bios *bios, u8 *ver, u8 *hdr, u8 *cnt, u8 *len,
-             struct nvbios_connT *info)
-{
-       u32 data = nvbios_connTe(bios, ver, hdr, cnt, len);
-       memset(info, 0x00, sizeof(*info));
-       switch (!!data * *ver) {
-       case 0x30:
-       case 0x40:
-               return data;
-       default:
-               break;
-       }
-       return 0x00000000;
-}
-
-u32
-nvbios_connEe(struct nouveau_bios *bios, u8 idx, u8 *ver, u8 *len)
-{
-       u8  hdr, cnt;
-       u32 data = nvbios_connTe(bios, ver, &hdr, &cnt, len);
-       if (data && idx < cnt)
-               return data + hdr + (idx * *len);
-       return 0x00000000;
-}
-
-u32
-nvbios_connEp(struct nouveau_bios *bios, u8 idx, u8 *ver, u8 *len,
-             struct nvbios_connE *info)
-{
-       u32 data = nvbios_connEe(bios, idx, ver, len);
-       memset(info, 0x00, sizeof(*info));
-       switch (!!data * *ver) {
-       case 0x30:
-       case 0x40:
-               info->type     =  nv_ro08(bios, data + 0x00);
-               info->location =  nv_ro08(bios, data + 0x01) & 0x0f;
-               info->hpd      = (nv_ro08(bios, data + 0x01) & 0x30) >> 4;
-               info->dp       = (nv_ro08(bios, data + 0x01) & 0xc0) >> 6;
-               if (*len < 4)
-                       return data;
-               info->hpd     |= (nv_ro08(bios, data + 0x02) & 0x03) << 2;
-               info->dp      |=  nv_ro08(bios, data + 0x02) & 0x0c;
-               info->di       = (nv_ro08(bios, data + 0x02) & 0xf0) >> 4;
-               info->hpd     |= (nv_ro08(bios, data + 0x03) & 0x07) << 4;
-               info->sr       = (nv_ro08(bios, data + 0x03) & 0x08) >> 3;
-               info->lcdid    = (nv_ro08(bios, data + 0x03) & 0x70) >> 4;
-               return data;
-       default:
-               break;
-       }
-       return 0x00000000;
-}
diff --git a/drivers/gpu/drm/nouveau/core/subdev/bios/cstep.c b/drivers/gpu/drm/nouveau/core/subdev/bios/cstep.c
deleted file mode 100644 (file)
index d3b1532..0000000
+++ /dev/null
@@ -1,123 +0,0 @@
-/*
- * Copyright 2013 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 <subdev/bios.h>
-#include <subdev/bios/bit.h>
-#include <subdev/bios/cstep.h>
-
-u16
-nvbios_cstepTe(struct nouveau_bios *bios,
-              u8 *ver, u8 *hdr, u8 *cnt, u8 *len, u8 *xnr, u8 *xsz)
-{
-       struct bit_entry bit_P;
-       u16 cstep = 0x0000;
-
-       if (!bit_entry(bios, 'P', &bit_P)) {
-               if (bit_P.version == 2)
-                       cstep = nv_ro16(bios, bit_P.offset + 0x34);
-
-               if (cstep) {
-                       *ver = nv_ro08(bios, cstep + 0);
-                       switch (*ver) {
-                       case 0x10:
-                               *hdr = nv_ro08(bios, cstep + 1);
-                               *cnt = nv_ro08(bios, cstep + 3);
-                               *len = nv_ro08(bios, cstep + 2);
-                               *xnr = nv_ro08(bios, cstep + 5);
-                               *xsz = nv_ro08(bios, cstep + 4);
-                               return cstep;
-                       default:
-                               break;
-                       }
-               }
-       }
-
-       return 0x0000;
-}
-
-u16
-nvbios_cstepEe(struct nouveau_bios *bios, int idx, u8 *ver, u8 *hdr)
-{
-       u8  cnt, len, xnr, xsz;
-       u16 data = nvbios_cstepTe(bios, ver, hdr, &cnt, &len, &xnr, &xsz);
-       if (data && idx < cnt) {
-               data = data + *hdr + (idx * len);
-               *hdr = len;
-               return data;
-       }
-       return 0x0000;
-}
-
-u16
-nvbios_cstepEp(struct nouveau_bios *bios, int idx, u8 *ver, u8 *hdr,
-              struct nvbios_cstepE *info)
-{
-       u16 data = nvbios_cstepEe(bios, idx, ver, hdr);
-       memset(info, 0x00, sizeof(*info));
-       if (data) {
-               info->pstate = (nv_ro16(bios, data + 0x00) & 0x01e0) >> 5;
-               info->index   = nv_ro08(bios, data + 0x03);
-       }
-       return data;
-}
-
-u16
-nvbios_cstepEm(struct nouveau_bios *bios, u8 pstate, u8 *ver, u8 *hdr,
-              struct nvbios_cstepE *info)
-{
-       u32 data, idx = 0;
-       while ((data = nvbios_cstepEp(bios, idx++, ver, hdr, info))) {
-               if (info->pstate == pstate)
-                       break;
-       }
-       return data;
-}
-
-u16
-nvbios_cstepXe(struct nouveau_bios *bios, int idx, u8 *ver, u8 *hdr)
-{
-       u8  cnt, len, xnr, xsz;
-       u16 data = nvbios_cstepTe(bios, ver, hdr, &cnt, &len, &xnr, &xsz);
-       if (data && idx < xnr) {
-               data = data + *hdr + (cnt * len) + (idx * xsz);
-               *hdr = xsz;
-               return data;
-       }
-       return 0x0000;
-}
-
-u16
-nvbios_cstepXp(struct nouveau_bios *bios, int idx, u8 *ver, u8 *hdr,
-              struct nvbios_cstepX *info)
-{
-       u16 data = nvbios_cstepXe(bios, idx, ver, hdr);
-       memset(info, 0x00, sizeof(*info));
-       if (data) {
-               info->freq    = nv_ro16(bios, data + 0x00) * 1000;
-               info->unkn[0] = nv_ro08(bios, data + 0x02);
-               info->unkn[1] = nv_ro08(bios, data + 0x03);
-               info->voltage = nv_ro08(bios, data + 0x04);
-       }
-       return data;
-}
diff --git a/drivers/gpu/drm/nouveau/core/subdev/bios/dcb.c b/drivers/gpu/drm/nouveau/core/subdev/bios/dcb.c
deleted file mode 100644 (file)
index 96099af..0000000
+++ /dev/null
@@ -1,235 +0,0 @@
-/*
- * Copyright 2012 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 "core/device.h"
-
-#include "subdev/bios.h"
-#include "subdev/bios/dcb.h"
-
-u16
-dcb_table(struct nouveau_bios *bios, u8 *ver, u8 *hdr, u8 *cnt, u8 *len)
-{
-       struct nouveau_device *device = nv_device(bios);
-       u16 dcb = 0x0000;
-
-       if (device->card_type > NV_04)
-               dcb = nv_ro16(bios, 0x36);
-       if (!dcb) {
-               nv_warn(bios, "DCB table not found\n");
-               return dcb;
-       }
-
-       *ver = nv_ro08(bios, dcb);
-
-       if (*ver >= 0x42) {
-               nv_warn(bios, "DCB version 0x%02x unknown\n", *ver);
-               return 0x0000;
-       } else
-       if (*ver >= 0x30) {
-               if (nv_ro32(bios, dcb + 6) == 0x4edcbdcb) {
-                       *hdr = nv_ro08(bios, dcb + 1);
-                       *cnt = nv_ro08(bios, dcb + 2);
-                       *len = nv_ro08(bios, dcb + 3);
-                       return dcb;
-               }
-       } else
-       if (*ver >= 0x20) {
-               if (nv_ro32(bios, dcb + 4) == 0x4edcbdcb) {
-                       u16 i2c = nv_ro16(bios, dcb + 2);
-                       *hdr = 8;
-                       *cnt = (i2c - dcb) / 8;
-                       *len = 8;
-                       return dcb;
-               }
-       } else
-       if (*ver >= 0x15) {
-               if (!nv_memcmp(bios, dcb - 7, "DEV_REC", 7)) {
-                       u16 i2c = nv_ro16(bios, dcb + 2);
-                       *hdr = 4;
-                       *cnt = (i2c - dcb) / 10;
-                       *len = 10;
-                       return dcb;
-               }
-       } 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_warn(bios, "DCB contains no useful data\n");
-               return 0x0000;
-       }
-
-       nv_warn(bios, "DCB header validation failed\n");
-       return 0x0000;
-}
-
-u16
-dcb_outp(struct nouveau_bios *bios, u8 idx, u8 *ver, u8 *len)
-{
-       u8  hdr, cnt;
-       u16 dcb = dcb_table(bios, ver, &hdr, &cnt, len);
-       if (dcb && idx < cnt)
-               return dcb + hdr + (idx * *len);
-       return 0x0000;
-}
-
-static inline u16
-dcb_outp_hasht(struct dcb_output *outp)
-{
-       return (outp->extdev << 8) | (outp->location << 4) | outp->type;
-}
-
-static inline u16
-dcb_outp_hashm(struct dcb_output *outp)
-{
-       return (outp->heads << 8) | (outp->link << 6) | outp->or;
-}
-
-u16
-dcb_outp_parse(struct nouveau_bios *bios, u8 idx, u8 *ver, u8 *len,
-              struct dcb_output *outp)
-{
-       u16 dcb = dcb_outp(bios, idx, ver, len);
-       memset(outp, 0x00, sizeof(*outp));
-       if (dcb) {
-               if (*ver >= 0x20) {
-                       u32 conn = nv_ro32(bios, dcb + 0x00);
-                       outp->or        = (conn & 0x0f000000) >> 24;
-                       outp->location  = (conn & 0x00300000) >> 20;
-                       outp->bus       = (conn & 0x000f0000) >> 16;
-                       outp->connector = (conn & 0x0000f000) >> 12;
-                       outp->heads     = (conn & 0x00000f00) >> 8;
-                       outp->i2c_index = (conn & 0x000000f0) >> 4;
-                       outp->type      = (conn & 0x0000000f);
-                       outp->link      = 0;
-               } else {
-                       dcb = 0x0000;
-               }
-
-               if (*ver >= 0x40) {
-                       u32 conf = nv_ro32(bios, dcb + 0x04);
-                       switch (outp->type) {
-                       case DCB_OUTPUT_DP:
-                               switch (conf & 0x00e00000) {
-                               case 0x00000000:
-                                       outp->dpconf.link_bw = 0x06;
-                                       break;
-                               case 0x00200000:
-                                       outp->dpconf.link_bw = 0x0a;
-                                       break;
-                               case 0x00400000:
-                               default:
-                                       outp->dpconf.link_bw = 0x14;
-                                       break;
-                               }
-
-                               outp->dpconf.link_nr = (conf & 0x0f000000) >> 24;
-                               if (*ver < 0x41) {
-                                       switch (outp->dpconf.link_nr) {
-                                       case 0x0f:
-                                               outp->dpconf.link_nr = 4;
-                                               break;
-                                       case 0x03:
-                                               outp->dpconf.link_nr = 2;
-                                               break;
-                                       case 0x01:
-                                       default:
-                                               outp->dpconf.link_nr = 1;
-                                               break;
-                                       }
-                               }
-
-                               /* fall-through... */
-                       case DCB_OUTPUT_TMDS:
-                       case DCB_OUTPUT_LVDS:
-                               outp->link = (conf & 0x00000030) >> 4;
-                               outp->sorconf.link = outp->link; /*XXX*/
-                               outp->extdev = 0x00;
-                               if (outp->location != 0)
-                                       outp->extdev = (conf & 0x0000ff00) >> 8;
-                               break;
-                       default:
-                               break;
-                       }
-               }
-
-               outp->hasht = dcb_outp_hasht(outp);
-               outp->hashm = dcb_outp_hashm(outp);
-       }
-       return dcb;
-}
-
-u16
-dcb_outp_match(struct nouveau_bios *bios, u16 type, u16 mask,
-              u8 *ver, u8 *len, struct dcb_output *outp)
-{
-       u16 dcb, idx = 0;
-       while ((dcb = dcb_outp_parse(bios, idx++, ver, len, outp))) {
-               if ((dcb_outp_hasht(outp) & 0x00ff) == (type & 0x00ff)) {
-                       if ((dcb_outp_hashm(outp) & mask) == mask)
-                               break;
-               }
-       }
-       return dcb;
-}
-
-int
-dcb_outp_foreach(struct nouveau_bios *bios, void *data,
-                int (*exec)(struct nouveau_bios *, void *, int, u16))
-{
-       int ret, idx = -1;
-       u8  ver, len;
-       u16 outp;
-
-       while ((outp = dcb_outp(bios, ++idx, &ver, &len))) {
-               if (nv_ro32(bios, outp) == 0x00000000)
-                       break; /* seen on an NV11 with DCB v1.5 */
-               if (nv_ro32(bios, outp) == 0xffffffff)
-                       break; /* seen on an NV17 with DCB v2.0 */
-
-               if (nv_ro08(bios, outp) == DCB_OUTPUT_UNUSED)
-                       continue;
-               if (nv_ro08(bios, outp) == DCB_OUTPUT_EOL)
-                       break;
-
-               ret = exec(bios, data, idx, outp);
-               if (ret)
-                       return ret;
-       }
-
-       return 0;
-}
diff --git a/drivers/gpu/drm/nouveau/core/subdev/bios/disp.c b/drivers/gpu/drm/nouveau/core/subdev/bios/disp.c
deleted file mode 100644 (file)
index 51f3555..0000000
+++ /dev/null
@@ -1,179 +0,0 @@
-/*
- * Copyright 2012 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 <subdev/bios.h>
-#include <subdev/bios/bit.h>
-#include <subdev/bios/disp.h>
-
-u16
-nvbios_disp_table(struct nouveau_bios *bios,
-                 u8 *ver, u8 *hdr, u8 *cnt, u8 *len, u8 *sub)
-{
-       struct bit_entry U;
-
-       if (!bit_entry(bios, 'U', &U)) {
-               if (U.version == 1) {
-                       u16 data = nv_ro16(bios, U.offset);
-                       if (data) {
-                               *ver = nv_ro08(bios, data + 0x00);
-                               switch (*ver) {
-                               case 0x20:
-                               case 0x21:
-                               case 0x22:
-                                       *hdr = nv_ro08(bios, data + 0x01);
-                                       *len = nv_ro08(bios, data + 0x02);
-                                       *cnt = nv_ro08(bios, data + 0x03);
-                                       *sub = nv_ro08(bios, data + 0x04);
-                                       return data;
-                               default:
-                                       break;
-                               }
-                       }
-               }
-       }
-
-       return 0x0000;
-}
-
-u16
-nvbios_disp_entry(struct nouveau_bios *bios, u8 idx,
-                 u8 *ver, u8 *len, u8 *sub)
-{
-       u8  hdr, cnt;
-       u16 data = nvbios_disp_table(bios, ver, &hdr, &cnt, len, sub);
-       if (data && idx < cnt)
-               return data + hdr + (idx * *len);
-       *ver = 0x00;
-       return 0x0000;
-}
-
-u16
-nvbios_disp_parse(struct nouveau_bios *bios, u8 idx,
-                 u8 *ver, u8 *len, u8 *sub,
-                 struct nvbios_disp *info)
-{
-       u16 data = nvbios_disp_entry(bios, idx, ver, len, sub);
-       if (data && *len >= 2) {
-               info->data = nv_ro16(bios, data + 0);
-               return data;
-       }
-       return 0x0000;
-}
-
-u16
-nvbios_outp_entry(struct nouveau_bios *bios, u8 idx,
-                 u8 *ver, u8 *hdr, u8 *cnt, u8 *len)
-{
-       struct nvbios_disp info;
-       u16 data = nvbios_disp_parse(bios, idx, ver, len, hdr, &info);
-       if (data) {
-               *cnt = nv_ro08(bios, info.data + 0x05);
-               *len = 0x06;
-               data = info.data;
-       }
-       return data;
-}
-
-u16
-nvbios_outp_parse(struct nouveau_bios *bios, u8 idx,
-                 u8 *ver, u8 *hdr, u8 *cnt, u8 *len,
-                 struct nvbios_outp *info)
-{
-       u16 data = nvbios_outp_entry(bios, idx, ver, hdr, cnt, len);
-       if (data && *hdr >= 0x0a) {
-               info->type      = nv_ro16(bios, data + 0x00);
-               info->mask      = nv_ro32(bios, data + 0x02);
-               if (*ver <= 0x20) /* match any link */
-                       info->mask |= 0x00c0;
-               info->script[0] = nv_ro16(bios, data + 0x06);
-               info->script[1] = nv_ro16(bios, data + 0x08);
-               info->script[2] = 0x0000;
-               if (*hdr >= 0x0c)
-                       info->script[2] = nv_ro16(bios, data + 0x0a);
-               return data;
-       }
-       return 0x0000;
-}
-
-u16
-nvbios_outp_match(struct nouveau_bios *bios, u16 type, u16 mask,
-                 u8 *ver, u8 *hdr, u8 *cnt, u8 *len,
-                 struct nvbios_outp *info)
-{
-       u16 data, idx = 0;
-       while ((data = nvbios_outp_parse(bios, idx++, ver, hdr, cnt, len, info)) || *ver) {
-               if (data && info->type == type) {
-                       if ((info->mask & mask) == mask)
-                               break;
-               }
-       }
-       return data;
-}
-
-u16
-nvbios_ocfg_entry(struct nouveau_bios *bios, u16 outp, u8 idx,
-                 u8 *ver, u8 *hdr, u8 *cnt, u8 *len)
-{
-       if (idx < *cnt)
-               return outp + *hdr + (idx * *len);
-       return 0x0000;
-}
-
-u16
-nvbios_ocfg_parse(struct nouveau_bios *bios, u16 outp, u8 idx,
-                 u8 *ver, u8 *hdr, u8 *cnt, u8 *len,
-                 struct nvbios_ocfg *info)
-{
-       u16 data = nvbios_ocfg_entry(bios, outp, idx, ver, hdr, cnt, len);
-       if (data) {
-               info->match     = nv_ro16(bios, data + 0x00);
-               info->clkcmp[0] = nv_ro16(bios, data + 0x02);
-               info->clkcmp[1] = nv_ro16(bios, data + 0x04);
-       }
-       return data;
-}
-
-u16
-nvbios_ocfg_match(struct nouveau_bios *bios, u16 outp, u16 type,
-                 u8 *ver, u8 *hdr, u8 *cnt, u8 *len,
-                 struct nvbios_ocfg *info)
-{
-       u16 data, idx = 0;
-       while ((data = nvbios_ocfg_parse(bios, outp, idx++, ver, hdr, cnt, len, info))) {
-               if (info->match == type)
-                       break;
-       }
-       return data;
-}
-
-u16
-nvbios_oclk_match(struct nouveau_bios *bios, u16 cmp, u32 khz)
-{
-       while (cmp) {
-               if (khz / 10 >= nv_ro16(bios, cmp + 0x00))
-                       return  nv_ro16(bios, cmp + 0x02);
-               cmp += 0x04;
-       }
-       return 0x0000;
-}
diff --git a/drivers/gpu/drm/nouveau/core/subdev/bios/dp.c b/drivers/gpu/drm/nouveau/core/subdev/bios/dp.c
deleted file mode 100644 (file)
index cef53f8..0000000
+++ /dev/null
@@ -1,217 +0,0 @@
-/*
- * Copyright 2012 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 "subdev/bios.h"
-#include "subdev/bios/bit.h"
-#include "subdev/bios/dp.h"
-
-static u16
-nvbios_dp_table(struct nouveau_bios *bios, u8 *ver, u8 *hdr, u8 *cnt, u8 *len)
-{
-       struct bit_entry d;
-
-       if (!bit_entry(bios, 'd', &d)) {
-               if (d.version == 1 && d.length >= 2) {
-                       u16 data = nv_ro16(bios, d.offset);
-                       if (data) {
-                               *ver = nv_ro08(bios, data + 0x00);
-                               switch (*ver) {
-                               case 0x21:
-                               case 0x30:
-                               case 0x40:
-                               case 0x41:
-                                       *hdr = nv_ro08(bios, data + 0x01);
-                                       *len = nv_ro08(bios, data + 0x02);
-                                       *cnt = nv_ro08(bios, data + 0x03);
-                                       return data;
-                               default:
-                                       break;
-                               }
-                       }
-               }
-       }
-
-       return 0x0000;
-}
-
-static u16
-nvbios_dpout_entry(struct nouveau_bios *bios, u8 idx,
-                  u8 *ver, u8 *hdr, u8 *cnt, u8 *len)
-{
-       u16 data = nvbios_dp_table(bios, ver, hdr, cnt, len);
-       if (data && idx < *cnt) {
-               u16 outp = nv_ro16(bios, data + *hdr + idx * *len);
-               switch (*ver * !!outp) {
-               case 0x21:
-               case 0x30:
-                       *hdr = nv_ro08(bios, data + 0x04);
-                       *len = nv_ro08(bios, data + 0x05);
-                       *cnt = nv_ro08(bios, outp + 0x04);
-                       break;
-               case 0x40:
-               case 0x41:
-                       *hdr = nv_ro08(bios, data + 0x04);
-                       *cnt = 0;
-                       *len = 0;
-                       break;
-               default:
-                       break;
-               }
-               return outp;
-       }
-       *ver = 0x00;
-       return 0x0000;
-}
-
-u16
-nvbios_dpout_parse(struct nouveau_bios *bios, u8 idx,
-                  u8 *ver, u8 *hdr, u8 *cnt, u8 *len,
-                  struct nvbios_dpout *info)
-{
-       u16 data = nvbios_dpout_entry(bios, idx, ver, hdr, cnt, len);
-       memset(info, 0x00, sizeof(*info));
-       if (data && *ver) {
-               info->type = nv_ro16(bios, data + 0x00);
-               info->mask = nv_ro16(bios, data + 0x02);
-               switch (*ver) {
-               case 0x21:
-               case 0x30:
-                       info->flags     = nv_ro08(bios, data + 0x05);
-                       info->script[0] = nv_ro16(bios, data + 0x06);
-                       info->script[1] = nv_ro16(bios, data + 0x08);
-                       info->lnkcmp    = nv_ro16(bios, data + 0x0a);
-                       if (*len >= 0x0f) {
-                               info->script[2] = nv_ro16(bios, data + 0x0c);
-                               info->script[3] = nv_ro16(bios, data + 0x0e);
-                       }
-                       if (*len >= 0x11)
-                               info->script[4] = nv_ro16(bios, data + 0x10);
-                       break;
-               case 0x40:
-               case 0x41:
-                       info->flags     = nv_ro08(bios, data + 0x04);
-                       info->script[0] = nv_ro16(bios, data + 0x05);
-                       info->script[1] = nv_ro16(bios, data + 0x07);
-                       info->lnkcmp    = nv_ro16(bios, data + 0x09);
-                       info->script[2] = nv_ro16(bios, data + 0x0b);
-                       info->script[3] = nv_ro16(bios, data + 0x0d);
-                       info->script[4] = nv_ro16(bios, data + 0x0f);
-                       break;
-               default:
-                       data = 0x0000;
-                       break;
-               }
-       }
-       return data;
-}
-
-u16
-nvbios_dpout_match(struct nouveau_bios *bios, u16 type, u16 mask,
-                  u8 *ver, u8 *hdr, u8 *cnt, u8 *len,
-                  struct nvbios_dpout *info)
-{
-       u16 data, idx = 0;
-       while ((data = nvbios_dpout_parse(bios, idx++, ver, hdr, cnt, len, info)) || *ver) {
-               if (data && info->type == type) {
-                       if ((info->mask & mask) == mask)
-                               break;
-               }
-       }
-       return data;
-}
-
-static u16
-nvbios_dpcfg_entry(struct nouveau_bios *bios, u16 outp, u8 idx,
-                  u8 *ver, u8 *hdr, u8 *cnt, u8 *len)
-{
-       if (*ver >= 0x40) {
-               outp = nvbios_dp_table(bios, ver, hdr, cnt, len);
-               *hdr = *hdr + (*len * * cnt);
-               *len = nv_ro08(bios, outp + 0x06);
-               *cnt = nv_ro08(bios, outp + 0x07);
-       }
-
-       if (idx < *cnt)
-               return outp + *hdr + (idx * *len);
-
-       return 0x0000;
-}
-
-u16
-nvbios_dpcfg_parse(struct nouveau_bios *bios, u16 outp, u8 idx,
-                  u8 *ver, u8 *hdr, u8 *cnt, u8 *len,
-                  struct nvbios_dpcfg *info)
-{
-       u16 data = nvbios_dpcfg_entry(bios, outp, idx, ver, hdr, cnt, len);
-       memset(info, 0x00, sizeof(*info));
-       if (data) {
-               switch (*ver) {
-               case 0x21:
-                       info->dc    = nv_ro08(bios, data + 0x02);
-                       info->pe    = nv_ro08(bios, data + 0x03);
-                       info->tx_pu = nv_ro08(bios, data + 0x04);
-                       break;
-               case 0x30:
-               case 0x40:
-               case 0x41:
-                       info->pc    = nv_ro08(bios, data + 0x00);
-                       info->dc    = nv_ro08(bios, data + 0x01);
-                       info->pe    = nv_ro08(bios, data + 0x02);
-                       info->tx_pu = nv_ro08(bios, data + 0x03) & 0x0f;
-                       break;
-               default:
-                       data = 0x0000;
-                       break;
-               }
-       }
-       return data;
-}
-
-u16
-nvbios_dpcfg_match(struct nouveau_bios *bios, u16 outp, u8 pc, u8 vs, u8 pe,
-                  u8 *ver, u8 *hdr, u8 *cnt, u8 *len,
-                  struct nvbios_dpcfg *info)
-{
-       u8 idx = 0xff;
-       u16 data;
-
-       if (*ver >= 0x30) {
-               /*XXX: there's a second set of these on at least 4.1, that
-                *     i've witnessed nvidia using instead of the first
-                *     on gm204.  figure out what/why
-                */
-               const u8 vsoff[] = { 0, 4, 7, 9 };
-               idx = (pc * 10) + vsoff[vs] + pe;
-       } else {
-               while ((data = nvbios_dpcfg_entry(bios, outp, ++idx,
-                                                 ver, hdr, cnt, len))) {
-                       if (nv_ro08(bios, data + 0x00) == vs &&
-                           nv_ro08(bios, data + 0x01) == pe)
-                               break;
-               }
-       }
-
-       return nvbios_dpcfg_parse(bios, outp, idx, ver, hdr, cnt, len, info);
-}
diff --git a/drivers/gpu/drm/nouveau/core/subdev/bios/extdev.c b/drivers/gpu/drm/nouveau/core/subdev/bios/extdev.c
deleted file mode 100644 (file)
index 49285d4..0000000
+++ /dev/null
@@ -1,100 +0,0 @@
-/*
- * Copyright 2012 Nouveau Community
- *
- * 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 <subdev/bios.h>
-#include <subdev/bios/dcb.h>
-#include <subdev/bios/extdev.h>
-
-static u16
-extdev_table(struct nouveau_bios *bios, u8 *ver, u8 *hdr, u8 *len, u8 *cnt)
-{
-       u8  dcb_ver, dcb_hdr, dcb_cnt, dcb_len;
-       u16 dcb, extdev = 0;
-
-       dcb = dcb_table(bios, &dcb_ver, &dcb_hdr, &dcb_cnt, &dcb_len);
-       if (!dcb || (dcb_ver != 0x30 && dcb_ver != 0x40))
-               return 0x0000;
-
-       extdev = nv_ro16(bios, dcb + 18);
-       if (!extdev)
-               return 0x0000;
-
-       *ver = nv_ro08(bios, extdev + 0);
-       *hdr = nv_ro08(bios, extdev + 1);
-       *cnt = nv_ro08(bios, extdev + 2);
-       *len = nv_ro08(bios, extdev + 3);
-
-       return extdev + *hdr;
-}
-
-static u16
-nvbios_extdev_entry(struct nouveau_bios *bios, int idx, u8 *ver, u8 *len)
-{
-       u8 hdr, cnt;
-       u16 extdev = extdev_table(bios, ver, &hdr, len, &cnt);
-       if (extdev && idx < cnt)
-               return extdev + idx * *len;
-       return 0x0000;
-}
-
-static void
-extdev_parse_entry(struct nouveau_bios *bios, u16 offset,
-                         struct nvbios_extdev_func *entry)
-{
-       entry->type = nv_ro08(bios, offset + 0);
-       entry->addr = nv_ro08(bios, offset + 1);
-       entry->bus = (nv_ro08(bios, offset + 2) >> 4) & 1;
-}
-
-int
-nvbios_extdev_parse(struct nouveau_bios *bios, int idx,
-                   struct nvbios_extdev_func *func)
-{
-       u8 ver, len;
-       u16 entry;
-
-       if (!(entry = nvbios_extdev_entry(bios, idx, &ver, &len)))
-               return -EINVAL;
-
-       extdev_parse_entry(bios, entry, func);
-
-       return 0;
-}
-
-int
-nvbios_extdev_find(struct nouveau_bios *bios, enum nvbios_extdev_type type,
-                  struct nvbios_extdev_func *func)
-{
-       u8 ver, len, i;
-       u16 entry;
-
-       i = 0;
-       while ((entry = nvbios_extdev_entry(bios, i++, &ver, &len))) {
-               extdev_parse_entry(bios, entry, func);
-               if (func->type == type)
-                       return 0;
-       }
-
-       return -EINVAL;
-}
diff --git a/drivers/gpu/drm/nouveau/core/subdev/bios/fan.c b/drivers/gpu/drm/nouveau/core/subdev/bios/fan.c
deleted file mode 100644 (file)
index e419892..0000000
+++ /dev/null
@@ -1,93 +0,0 @@
-/*
- * Copyright 2014 Martin Peres
- *
- * 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 <subdev/bios.h>
-#include <subdev/bios/bit.h>
-#include <subdev/bios/fan.h>
-
-u16
-nvbios_fan_table(struct nouveau_bios *bios, u8 *ver, u8 *hdr, u8 *cnt, u8 *len)
-{
-       struct bit_entry bit_P;
-       u16 fan = 0x0000;
-
-       if (!bit_entry(bios, 'P', &bit_P)) {
-               if (bit_P.version == 2 && bit_P.length >= 0x5a)
-                       fan = nv_ro16(bios, bit_P.offset + 0x58);
-
-               if (fan) {
-                       *ver = nv_ro08(bios, fan + 0);
-                       switch (*ver) {
-                       case 0x10:
-                               *hdr = nv_ro08(bios, fan + 1);
-                               *len = nv_ro08(bios, fan + 2);
-                               *cnt = nv_ro08(bios, fan + 3);
-                               return fan;
-                       default:
-                               break;
-                       }
-               }
-       }
-
-       return 0x0000;
-}
-
-u16
-nvbios_fan_entry(struct nouveau_bios *bios, int idx, u8 *ver, u8 *hdr,
-                u8 *cnt, u8 *len)
-{
-       u16 data = nvbios_fan_table(bios, ver, hdr, cnt, len);
-       if (data && idx < *cnt)
-               return data + *hdr + (idx * (*len));
-       return 0x0000;
-}
-
-u16
-nvbios_fan_parse(struct nouveau_bios *bios, struct nvbios_therm_fan *fan)
-{
-       u8 ver, hdr, cnt, len;
-
-       u16 data = nvbios_fan_entry(bios, 0, &ver, &hdr, &cnt, &len);
-       if (data) {
-               u8 type = nv_ro08(bios, data + 0x00);
-               switch (type) {
-               case 0:
-                       fan->type = NVBIOS_THERM_FAN_TOGGLE;
-                       break;
-               case 1:
-               case 2:
-                       /* TODO: Understand the difference between the two! */
-                       fan->type = NVBIOS_THERM_FAN_PWM;
-                       break;
-               default:
-                       fan->type = NVBIOS_THERM_FAN_UNK;
-               }
-
-               fan->min_duty = nv_ro08(bios, data + 0x02);
-               fan->max_duty = nv_ro08(bios, data + 0x03);
-
-               fan->pwm_freq = nv_ro32(bios, data + 0x0b) & 0xffffff;
-       }
-       return data;
-}
diff --git a/drivers/gpu/drm/nouveau/core/subdev/bios/gpio.c b/drivers/gpu/drm/nouveau/core/subdev/bios/gpio.c
deleted file mode 100644 (file)
index 172a4f9..0000000
+++ /dev/null
@@ -1,150 +0,0 @@
-/*
- * Copyright 2012 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 <subdev/bios.h>
-#include <subdev/bios/dcb.h>
-#include <subdev/bios/gpio.h>
-#include <subdev/bios/xpio.h>
-
-u16
-dcb_gpio_table(struct nouveau_bios *bios, u8 *ver, u8 *hdr, u8 *cnt, u8 *len)
-{
-       u16 data = 0x0000;
-       u16 dcb = dcb_table(bios, ver, hdr, cnt, len);
-       if (dcb) {
-               if (*ver >= 0x30 && *hdr >= 0x0c)
-                       data = nv_ro16(bios, dcb + 0x0a);
-               else
-               if (*ver >= 0x22 && nv_ro08(bios, dcb - 1) >= 0x13)
-                       data = nv_ro16(bios, dcb - 0x0f);
-
-               if (data) {
-                       *ver = nv_ro08(bios, data + 0x00);
-                       if (*ver < 0x30) {
-                               *hdr = 3;
-                               *cnt = nv_ro08(bios, data + 0x02);
-                               *len = nv_ro08(bios, data + 0x01);
-                       } else
-                       if (*ver <= 0x41) {
-                               *hdr = nv_ro08(bios, data + 0x01);
-                               *cnt = nv_ro08(bios, data + 0x02);
-                               *len = nv_ro08(bios, data + 0x03);
-                       } else {
-                               data = 0x0000;
-                       }
-               }
-       }
-       return data;
-}
-
-u16
-dcb_gpio_entry(struct nouveau_bios *bios, int idx, int ent, u8 *ver, u8 *len)
-{
-       u8  hdr, cnt, xver; /* use gpio version for xpio entry parsing */
-       u16 gpio;
-
-       if (!idx--)
-               gpio = dcb_gpio_table(bios, ver, &hdr, &cnt, len);
-       else
-               gpio = dcb_xpio_table(bios, idx, &xver, &hdr, &cnt, len);
-
-       if (gpio && ent < cnt)
-               return gpio + hdr + (ent * *len);
-       return 0x0000;
-}
-
-u16
-dcb_gpio_parse(struct nouveau_bios *bios, int idx, int ent, u8 *ver, u8 *len,
-              struct dcb_gpio_func *gpio)
-{
-       u16 data = dcb_gpio_entry(bios, idx, ent, ver, len);
-       if (data) {
-               if (*ver < 0x40) {
-                       u16 info = nv_ro16(bios, data);
-                       *gpio = (struct dcb_gpio_func) {
-                               .line = (info & 0x001f) >> 0,
-                               .func = (info & 0x07e0) >> 5,
-                               .log[0] = (info & 0x1800) >> 11,
-                               .log[1] = (info & 0x6000) >> 13,
-                               .param = !!(info & 0x8000),
-                       };
-               } else
-               if (*ver < 0x41) {
-                       u32 info = nv_ro32(bios, data);
-                       *gpio = (struct dcb_gpio_func) {
-                               .line = (info & 0x0000001f) >> 0,
-                               .func = (info & 0x0000ff00) >> 8,
-                               .log[0] = (info & 0x18000000) >> 27,
-                               .log[1] = (info & 0x60000000) >> 29,
-                               .param = !!(info & 0x80000000),
-                       };
-               } else {
-                       u32 info = nv_ro32(bios, data + 0);
-                       u8 info1 = nv_ro32(bios, data + 4);
-                       *gpio = (struct dcb_gpio_func) {
-                               .line = (info & 0x0000003f) >> 0,
-                               .func = (info & 0x0000ff00) >> 8,
-                               .log[0] = (info1 & 0x30) >> 4,
-                               .log[1] = (info1 & 0xc0) >> 6,
-                               .param = !!(info & 0x80000000),
-                       };
-               }
-       }
-
-       return data;
-}
-
-u16
-dcb_gpio_match(struct nouveau_bios *bios, int idx, u8 func, u8 line,
-              u8 *ver, u8 *len, struct dcb_gpio_func *gpio)
-{
-       u8  hdr, cnt, i = 0;
-       u16 data;
-
-       while ((data = dcb_gpio_parse(bios, idx, i++, ver, len, gpio))) {
-               if ((line == 0xff || line == gpio->line) &&
-                   (func == 0xff || func == gpio->func))
-                       return data;
-       }
-
-       /* DCB 2.2, fixed TVDAC GPIO data */
-       if ((data = dcb_table(bios, ver, &hdr, &cnt, len))) {
-               if (*ver >= 0x22 && *ver < 0x30 && func == DCB_GPIO_TVDAC0) {
-                       u8 conf = nv_ro08(bios, data - 5);
-                       u8 addr = nv_ro08(bios, data - 4);
-                       if (conf & 0x01) {
-                               *gpio = (struct dcb_gpio_func) {
-                                       .func = DCB_GPIO_TVDAC0,
-                                       .line = addr >> 4,
-                                       .log[0] = !!(conf & 0x02),
-                                       .log[1] =  !(conf & 0x02),
-                               };
-                               *ver = 0x00;
-                               return data;
-                       }
-               }
-       }
-
-       return 0x0000;
-}
diff --git a/drivers/gpu/drm/nouveau/core/subdev/bios/i2c.c b/drivers/gpu/drm/nouveau/core/subdev/bios/i2c.c
deleted file mode 100644 (file)
index 282320b..0000000
+++ /dev/null
@@ -1,161 +0,0 @@
-/*
- * Copyright 2012 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 "subdev/bios.h"
-#include "subdev/bios/dcb.h"
-#include "subdev/bios/i2c.h"
-
-u16
-dcb_i2c_table(struct nouveau_bios *bios, u8 *ver, u8 *hdr, u8 *cnt, u8 *len)
-{
-       u16 i2c = 0x0000;
-       u16 dcb = dcb_table(bios, ver, hdr, cnt, len);
-       if (dcb) {
-               if (*ver >= 0x15)
-                       i2c = nv_ro16(bios, dcb + 2);
-               if (*ver >= 0x30)
-                       i2c = nv_ro16(bios, dcb + 4);
-       }
-
-       if (i2c && *ver >= 0x42) {
-               nv_warn(bios, "ccb %02x not supported\n", *ver);
-               return 0x0000;
-       }
-
-       if (i2c && *ver >= 0x30) {
-               *ver = nv_ro08(bios, i2c + 0);
-               *hdr = nv_ro08(bios, i2c + 1);
-               *cnt = nv_ro08(bios, i2c + 2);
-               *len = nv_ro08(bios, i2c + 3);
-       } else {
-               *ver = *ver; /* use DCB version */
-               *hdr = 0;
-               *cnt = 16;
-               *len = 4;
-       }
-
-       return i2c;
-}
-
-u16
-dcb_i2c_entry(struct nouveau_bios *bios, u8 idx, u8 *ver, u8 *len)
-{
-       u8  hdr, cnt;
-       u16 i2c = dcb_i2c_table(bios, ver, &hdr, &cnt, len);
-       if (i2c && idx < cnt)
-               return i2c + hdr + (idx * *len);
-       return 0x0000;
-}
-
-int
-dcb_i2c_parse(struct nouveau_bios *bios, u8 idx, struct dcb_i2c_entry *info)
-{
-       u8  ver, len;
-       u16 ent = dcb_i2c_entry(bios, idx, &ver, &len);
-       if (ent) {
-               if (ver >= 0x41) {
-                       if (!(nv_ro32(bios, ent) & 0x80000000))
-                               info->type = DCB_I2C_UNUSED;
-                       else
-                               info->type = DCB_I2C_PMGR;
-               } else
-               if (ver >= 0x30) {
-                       info->type = nv_ro08(bios, ent + 0x03);
-               } else {
-                       info->type = nv_ro08(bios, ent + 0x03) & 0x07;
-                       if (info->type == 0x07)
-                               info->type = DCB_I2C_UNUSED;
-               }
-
-               info->drive = DCB_I2C_UNUSED;
-               info->sense = DCB_I2C_UNUSED;
-               info->share = DCB_I2C_UNUSED;
-               info->auxch = DCB_I2C_UNUSED;
-
-               switch (info->type) {
-               case DCB_I2C_NV04_BIT:
-                       info->drive = nv_ro08(bios, ent + 0);
-                       info->sense = nv_ro08(bios, ent + 1);
-                       return 0;
-               case DCB_I2C_NV4E_BIT:
-                       info->drive = nv_ro08(bios, ent + 1);
-                       return 0;
-               case DCB_I2C_NVIO_BIT:
-                       info->drive = nv_ro08(bios, ent + 0) & 0x0f;
-                       if (nv_ro08(bios, ent + 1) & 0x01)
-                               info->share = nv_ro08(bios, ent + 1) >> 1;
-                       return 0;
-               case DCB_I2C_NVIO_AUX:
-                       info->auxch = nv_ro08(bios, ent + 0) & 0x0f;
-                       if (nv_ro08(bios, ent + 1) & 0x01)
-                                       info->share = info->auxch;
-                       return 0;
-               case DCB_I2C_PMGR:
-                       info->drive = (nv_ro16(bios, ent + 0) & 0x01f) >> 0;
-                       if (info->drive == 0x1f)
-                               info->drive = DCB_I2C_UNUSED;
-                       info->auxch = (nv_ro16(bios, ent + 0) & 0x3e0) >> 5;
-                       if (info->auxch == 0x1f)
-                               info->auxch = DCB_I2C_UNUSED;
-                       info->share = info->auxch;
-                       return 0;
-               case DCB_I2C_UNUSED:
-                       return 0;
-               default:
-                       nv_warn(bios, "unknown i2c type %d\n", info->type);
-                       info->type = DCB_I2C_UNUSED;
-                       return 0;
-               }
-       }
-
-       if (bios->bmp_offset && idx < 2) {
-               /* BMP (from v4.0 has i2c info in the structure, it's in a
-                * fixed location on earlier VBIOS
-                */
-               if (nv_ro08(bios, bios->bmp_offset + 5) < 4)
-                       ent = 0x0048;
-               else
-                       ent = 0x0036 + bios->bmp_offset;
-
-               if (idx == 0) {
-                       info->drive = nv_ro08(bios, ent + 4);
-                       if (!info->drive) info->drive = 0x3f;
-                       info->sense = nv_ro08(bios, ent + 5);
-                       if (!info->sense) info->sense = 0x3e;
-               } else
-               if (idx == 1) {
-                       info->drive = nv_ro08(bios, ent + 6);
-                       if (!info->drive) info->drive = 0x37;
-                       info->sense = nv_ro08(bios, ent + 7);
-                       if (!info->sense) info->sense = 0x36;
-               }
-
-               info->type  = DCB_I2C_NV04_BIT;
-               info->share = DCB_I2C_UNUSED;
-               return 0;
-       }
-
-       return -ENOENT;
-}
diff --git a/drivers/gpu/drm/nouveau/core/subdev/bios/image.c b/drivers/gpu/drm/nouveau/core/subdev/bios/image.c
deleted file mode 100644 (file)
index 373f9a5..0000000
+++ /dev/null
@@ -1,78 +0,0 @@
-/*
- * Copyright 2014 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 <bskeggs@redhat.com>
- */
-
-#include <subdev/bios.h>
-#include <subdev/bios/image.h>
-#include <subdev/bios/pcir.h>
-#include <subdev/bios/npde.h>
-
-static bool
-nvbios_imagen(struct nouveau_bios *bios, struct nvbios_image *image)
-{
-       struct nvbios_pcirT pcir;
-       struct nvbios_npdeT npde;
-       u8  ver;
-       u16 hdr;
-       u32 data;
-
-       switch ((data = nv_ro16(bios, image->base + 0x00))) {
-       case 0xaa55:
-       case 0xbb77:
-       case 0x4e56: /* NV */
-               break;
-       default:
-               nv_debug(bios, "%08x: ROM signature (%04x) unknown\n",
-                        image->base, data);
-               return false;
-       }
-
-       if (!(data = nvbios_pcirTp(bios, image->base, &ver, &hdr, &pcir)))
-               return false;
-       image->size = pcir.image_size;
-       image->type = pcir.image_type;
-       image->last = pcir.last;
-
-       if (image->type != 0x70) {
-               if (!(data = nvbios_npdeTp(bios, image->base, &npde)))
-                       return true;
-               image->size = npde.image_size;
-               image->last = npde.last;
-       } else {
-               image->last = true;
-       }
-
-       return true;
-}
-
-bool
-nvbios_image(struct nouveau_bios *bios, int idx, struct nvbios_image *image)
-{
-       memset(image, 0x00, sizeof(*image));
-       do {
-               image->base += image->size;
-               if (image->last || !nvbios_imagen(bios, image))
-                       return false;
-       } while(idx--);
-       return true;
-}
diff --git a/drivers/gpu/drm/nouveau/core/subdev/bios/init.c b/drivers/gpu/drm/nouveau/core/subdev/bios/init.c
deleted file mode 100644 (file)
index c6579ef..0000000
+++ /dev/null
@@ -1,2227 +0,0 @@
-#include <core/engine.h>
-#include <core/device.h>
-
-#include <subdev/bios.h>
-#include <subdev/bios/bmp.h>
-#include <subdev/bios/bit.h>
-#include <subdev/bios/conn.h>
-#include <subdev/bios/dcb.h>
-#include <subdev/bios/dp.h>
-#include <subdev/bios/gpio.h>
-#include <subdev/bios/init.h>
-#include <subdev/bios/ramcfg.h>
-#include <subdev/devinit.h>
-#include <subdev/i2c.h>
-#include <subdev/vga.h>
-#include <subdev/gpio.h>
-
-#define bioslog(lvl, fmt, args...) do {                                        \
-       nv_printk(init->bios, lvl, "0x%04x[%c]: "fmt, init->offset,            \
-                 init_exec(init) ? '0' + (init->nested - 1) : ' ', ##args);   \
-} while(0)
-#define cont(fmt, args...) do {                                                \
-       if (nv_subdev(init->bios)->debug >= NV_DBG_TRACE)                      \
-               printk(fmt, ##args);                                           \
-} while(0)
-#define trace(fmt, args...) bioslog(TRACE, fmt, ##args)
-#define warn(fmt, args...) bioslog(WARN, fmt, ##args)
-#define error(fmt, args...) bioslog(ERROR, fmt, ##args)
-
-/******************************************************************************
- * init parser control flow helpers
- *****************************************************************************/
-
-static inline bool
-init_exec(struct nvbios_init *init)
-{
-       return (init->execute == 1) || ((init->execute & 5) == 5);
-}
-
-static inline void
-init_exec_set(struct nvbios_init *init, bool exec)
-{
-       if (exec) init->execute &= 0xfd;
-       else      init->execute |= 0x02;
-}
-
-static inline void
-init_exec_inv(struct nvbios_init *init)
-{
-       init->execute ^= 0x02;
-}
-
-static inline void
-init_exec_force(struct nvbios_init *init, bool exec)
-{
-       if (exec) init->execute |= 0x04;
-       else      init->execute &= 0xfb;
-}
-
-/******************************************************************************
- * init parser wrappers for normal register/i2c/whatever accessors
- *****************************************************************************/
-
-static inline int
-init_or(struct nvbios_init *init)
-{
-       if (init_exec(init)) {
-               if (init->outp)
-                       return ffs(init->outp->or) - 1;
-               error("script needs OR!!\n");
-       }
-       return 0;
-}
-
-static inline int
-init_link(struct nvbios_init *init)
-{
-       if (init_exec(init)) {
-               if (init->outp)
-                       return !(init->outp->sorconf.link & 1);
-               error("script needs OR link\n");
-       }
-       return 0;
-}
-
-static inline int
-init_crtc(struct nvbios_init *init)
-{
-       if (init_exec(init)) {
-               if (init->crtc >= 0)
-                       return init->crtc;
-               error("script needs crtc\n");
-       }
-       return 0;
-}
-
-static u8
-init_conn(struct nvbios_init *init)
-{
-       struct nouveau_bios *bios = init->bios;
-       struct nvbios_connE connE;
-       u8  ver, hdr;
-       u32 conn;
-
-       if (init_exec(init)) {
-               if (init->outp) {
-                       conn = init->outp->connector;
-                       conn = nvbios_connEp(bios, conn, &ver, &hdr, &connE);
-                       if (conn)
-                               return connE.type;
-               }
-
-               error("script needs connector type\n");
-       }
-
-       return 0xff;
-}
-
-static inline u32
-init_nvreg(struct nvbios_init *init, u32 reg)
-{
-       struct nouveau_devinit *devinit = nouveau_devinit(init->bios);
-
-       /* C51 (at least) sometimes has the lower bits set which the VBIOS
-        * interprets to mean that access needs to go through certain IO
-        * ports instead.  The NVIDIA binary driver has been seen to access
-        * these through the NV register address, so lets assume we can
-        * do the same
-        */
-       reg &= ~0x00000003;
-
-       /* GF8+ display scripts need register addresses mangled a bit to
-        * select a specific CRTC/OR
-        */
-       if (nv_device(init->bios)->card_type >= NV_50) {
-               if (reg & 0x80000000) {
-                       reg += init_crtc(init) * 0x800;
-                       reg &= ~0x80000000;
-               }
-
-               if (reg & 0x40000000) {
-                       reg += init_or(init) * 0x800;
-                       reg &= ~0x40000000;
-                       if (reg & 0x20000000) {
-                               reg += init_link(init) * 0x80;
-                               reg &= ~0x20000000;
-                       }
-               }
-       }
-
-       if (reg & ~0x00fffffc)
-               warn("unknown bits in register 0x%08x\n", reg);
-
-       if (devinit->mmio)
-               reg = devinit->mmio(devinit, reg);
-       return reg;
-}
-
-static u32
-init_rd32(struct nvbios_init *init, u32 reg)
-{
-       reg = init_nvreg(init, reg);
-       if (reg != ~0 && init_exec(init))
-               return nv_rd32(init->subdev, reg);
-       return 0x00000000;
-}
-
-static void
-init_wr32(struct nvbios_init *init, u32 reg, u32 val)
-{
-       reg = init_nvreg(init, reg);
-       if (reg != ~0 && init_exec(init))
-               nv_wr32(init->subdev, reg, val);
-}
-
-static u32
-init_mask(struct nvbios_init *init, u32 reg, u32 mask, u32 val)
-{
-       reg = init_nvreg(init, reg);
-       if (reg != ~0 && init_exec(init)) {
-               u32 tmp = nv_rd32(init->subdev, reg);
-               nv_wr32(init->subdev, reg, (tmp & ~mask) | val);
-               return tmp;
-       }
-       return 0x00000000;
-}
-
-static u8
-init_rdport(struct nvbios_init *init, u16 port)
-{
-       if (init_exec(init))
-               return nv_rdport(init->subdev, init->crtc, port);
-       return 0x00;
-}
-
-static void
-init_wrport(struct nvbios_init *init, u16 port, u8 value)
-{
-       if (init_exec(init))
-               nv_wrport(init->subdev, init->crtc, port, value);
-}
-
-static u8
-init_rdvgai(struct nvbios_init *init, u16 port, u8 index)
-{
-       struct nouveau_subdev *subdev = init->subdev;
-       if (init_exec(init)) {
-               int head = init->crtc < 0 ? 0 : init->crtc;
-               return nv_rdvgai(subdev, head, port, index);
-       }
-       return 0x00;
-}
-
-static void
-init_wrvgai(struct nvbios_init *init, u16 port, u8 index, u8 value)
-{
-       /* force head 0 for updates to cr44, it only exists on first head */
-       if (nv_device(init->subdev)->card_type < NV_50) {
-               if (port == 0x03d4 && index == 0x44)
-                       init->crtc = 0;
-       }
-
-       if (init_exec(init)) {
-               int head = init->crtc < 0 ? 0 : init->crtc;
-               nv_wrvgai(init->subdev, head, port, index, value);
-       }
-
-       /* select head 1 if cr44 write selected it */
-       if (nv_device(init->subdev)->card_type < NV_50) {
-               if (port == 0x03d4 && index == 0x44 && value == 3)
-                       init->crtc = 1;
-       }
-}
-
-static struct nouveau_i2c_port *
-init_i2c(struct nvbios_init *init, int index)
-{
-       struct nouveau_i2c *i2c = nouveau_i2c(init->bios);
-
-       if (index == 0xff) {
-               index = NV_I2C_DEFAULT(0);
-               if (init->outp && init->outp->i2c_upper_default)
-                       index = NV_I2C_DEFAULT(1);
-       } else
-       if (index < 0) {
-               if (!init->outp) {
-                       if (init_exec(init))
-                               error("script needs output for i2c\n");
-                       return NULL;
-               }
-
-               if (index == -2 && init->outp->location) {
-                       index = NV_I2C_TYPE_EXTAUX(init->outp->extdev);
-                       return i2c->find_type(i2c, index);
-               }
-
-               index = init->outp->i2c_index;
-               if (init->outp->type == DCB_OUTPUT_DP)
-                       index += NV_I2C_AUX(0);
-       }
-
-       return i2c->find(i2c, index);
-}
-
-static int
-init_rdi2cr(struct nvbios_init *init, u8 index, u8 addr, u8 reg)
-{
-       struct nouveau_i2c_port *port = init_i2c(init, index);
-       if (port && init_exec(init))
-               return nv_rdi2cr(port, addr, reg);
-       return -ENODEV;
-}
-
-static int
-init_wri2cr(struct nvbios_init *init, u8 index, u8 addr, u8 reg, u8 val)
-{
-       struct nouveau_i2c_port *port = init_i2c(init, index);
-       if (port && init_exec(init))
-               return nv_wri2cr(port, addr, reg, val);
-       return -ENODEV;
-}
-
-static u8
-init_rdauxr(struct nvbios_init *init, u32 addr)
-{
-       struct nouveau_i2c_port *port = init_i2c(init, -2);
-       u8 data;
-
-       if (port && init_exec(init)) {
-               int ret = nv_rdaux(port, addr, &data, 1);
-               if (ret == 0)
-                       return data;
-               trace("auxch read failed with %d\n", ret);
-       }
-
-       return 0x00;
-}
-
-static int
-init_wrauxr(struct nvbios_init *init, u32 addr, u8 data)
-{
-       struct nouveau_i2c_port *port = init_i2c(init, -2);
-       if (port && init_exec(init)) {
-               int ret = nv_wraux(port, addr, &data, 1);
-               if (ret)
-                       trace("auxch write failed with %d\n", ret);
-               return ret;
-       }
-       return -ENODEV;
-}
-
-static void
-init_prog_pll(struct nvbios_init *init, u32 id, u32 freq)
-{
-       struct nouveau_devinit *devinit = nouveau_devinit(init->bios);
-       if (devinit->pll_set && init_exec(init)) {
-               int ret = devinit->pll_set(devinit, id, freq);
-               if (ret)
-                       warn("failed to prog pll 0x%08x to %dkHz\n", id, freq);
-       }
-}
-
-/******************************************************************************
- * parsing of bios structures that are required to execute init tables
- *****************************************************************************/
-
-static u16
-init_table(struct nouveau_bios *bios, u16 *len)
-{
-       struct bit_entry bit_I;
-
-       if (!bit_entry(bios, 'I', &bit_I)) {
-               *len = bit_I.length;
-               return bit_I.offset;
-       }
-
-       if (bmp_version(bios) >= 0x0510) {
-               *len = 14;
-               return bios->bmp_offset + 75;
-       }
-
-       return 0x0000;
-}
-
-static u16
-init_table_(struct nvbios_init *init, u16 offset, const char *name)
-{
-       struct nouveau_bios *bios = init->bios;
-       u16 len, data = init_table(bios, &len);
-       if (data) {
-               if (len >= offset + 2) {
-                       data = nv_ro16(bios, data + offset);
-                       if (data)
-                               return data;
-
-                       warn("%s pointer invalid\n", name);
-                       return 0x0000;
-               }
-
-               warn("init data too short for %s pointer", name);
-               return 0x0000;
-       }
-
-       warn("init data not found\n");
-       return 0x0000;
-}
-
-#define init_script_table(b) init_table_((b), 0x00, "script table")
-#define init_macro_index_table(b) init_table_((b), 0x02, "macro index table")
-#define init_macro_table(b) init_table_((b), 0x04, "macro table")
-#define init_condition_table(b) init_table_((b), 0x06, "condition table")
-#define init_io_condition_table(b) init_table_((b), 0x08, "io condition table")
-#define init_io_flag_condition_table(b) init_table_((b), 0x0a, "io flag conditon table")
-#define init_function_table(b) init_table_((b), 0x0c, "function table")
-#define init_xlat_table(b) init_table_((b), 0x10, "xlat table");
-
-static u16
-init_script(struct nouveau_bios *bios, int index)
-{
-       struct nvbios_init init = { .bios = bios };
-       u16 bmp_ver = bmp_version(bios), data;
-
-       if (bmp_ver && bmp_ver < 0x0510) {
-               if (index > 1 || bmp_ver < 0x0100)
-                       return 0x0000;
-
-               data = bios->bmp_offset + (bmp_ver < 0x0200 ? 14 : 18);
-               return nv_ro16(bios, data + (index * 2));
-       }
-
-       data = init_script_table(&init);
-       if (data)
-               return nv_ro16(bios, data + (index * 2));
-
-       return 0x0000;
-}
-
-static u16
-init_unknown_script(struct nouveau_bios *bios)
-{
-       u16 len, data = init_table(bios, &len);
-       if (data && len >= 16)
-               return nv_ro16(bios, data + 14);
-       return 0x0000;
-}
-
-static u8
-init_ram_restrict_group_count(struct nvbios_init *init)
-{
-       return nvbios_ramcfg_count(init->bios);
-}
-
-static u8
-init_ram_restrict(struct nvbios_init *init)
-{
-       /* This appears to be the behaviour of the VBIOS parser, and *is*
-        * important to cache the NV_PEXTDEV_BOOT0 on later chipsets to
-        * avoid fucking up the memory controller (somehow) by reading it
-        * on every INIT_RAM_RESTRICT_ZM_GROUP opcode.
-        *
-        * Preserving the non-caching behaviour on earlier chipsets just
-        * in case *not* re-reading the strap causes similar breakage.
-        */
-       if (!init->ramcfg || init->bios->version.major < 0x70)
-               init->ramcfg = 0x80000000 | nvbios_ramcfg_index(init->subdev);
-       return (init->ramcfg & 0x7fffffff);
-}
-
-static u8
-init_xlat_(struct nvbios_init *init, u8 index, u8 offset)
-{
-       struct nouveau_bios *bios = init->bios;
-       u16 table = init_xlat_table(init);
-       if (table) {
-               u16 data = nv_ro16(bios, table + (index * 2));
-               if (data)
-                       return nv_ro08(bios, data + offset);
-               warn("xlat table pointer %d invalid\n", index);
-       }
-       return 0x00;
-}
-
-/******************************************************************************
- * utility functions used by various init opcode handlers
- *****************************************************************************/
-
-static bool
-init_condition_met(struct nvbios_init *init, u8 cond)
-{
-       struct nouveau_bios *bios = init->bios;
-       u16 table = init_condition_table(init);
-       if (table) {
-               u32 reg = nv_ro32(bios, table + (cond * 12) + 0);
-               u32 msk = nv_ro32(bios, table + (cond * 12) + 4);
-               u32 val = nv_ro32(bios, table + (cond * 12) + 8);
-               trace("\t[0x%02x] (R[0x%06x] & 0x%08x) == 0x%08x\n",
-                     cond, reg, msk, val);
-               return (init_rd32(init, reg) & msk) == val;
-       }
-       return false;
-}
-
-static bool
-init_io_condition_met(struct nvbios_init *init, u8 cond)
-{
-       struct nouveau_bios *bios = init->bios;
-       u16 table = init_io_condition_table(init);
-       if (table) {
-               u16 port = nv_ro16(bios, table + (cond * 5) + 0);
-               u8 index = nv_ro08(bios, table + (cond * 5) + 2);
-               u8  mask = nv_ro08(bios, table + (cond * 5) + 3);
-               u8 value = nv_ro08(bios, table + (cond * 5) + 4);
-               trace("\t[0x%02x] (0x%04x[0x%02x] & 0x%02x) == 0x%02x\n",
-                     cond, port, index, mask, value);
-               return (init_rdvgai(init, port, index) & mask) == value;
-       }
-       return false;
-}
-
-static bool
-init_io_flag_condition_met(struct nvbios_init *init, u8 cond)
-{
-       struct nouveau_bios *bios = init->bios;
-       u16 table = init_io_flag_condition_table(init);
-       if (table) {
-               u16 port = nv_ro16(bios, table + (cond * 9) + 0);
-               u8 index = nv_ro08(bios, table + (cond * 9) + 2);
-               u8  mask = nv_ro08(bios, table + (cond * 9) + 3);
-               u8 shift = nv_ro08(bios, table + (cond * 9) + 4);
-               u16 data = nv_ro16(bios, table + (cond * 9) + 5);
-               u8 dmask = nv_ro08(bios, table + (cond * 9) + 7);
-               u8 value = nv_ro08(bios, table + (cond * 9) + 8);
-               u8 ioval = (init_rdvgai(init, port, index) & mask) >> shift;
-               return (nv_ro08(bios, data + ioval) & dmask) == value;
-       }
-       return false;
-}
-
-static inline u32
-init_shift(u32 data, u8 shift)
-{
-       if (shift < 0x80)
-               return data >> shift;
-       return data << (0x100 - shift);
-}
-
-static u32
-init_tmds_reg(struct nvbios_init *init, u8 tmds)
-{
-       /* 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.
-        */
-
-       const int pramdac_offset[13] = {
-               0, 0, 0x8, 0, 0x2000, 0, 0, 0, 0x2008, 0, 0, 0, 0x2000 };
-       const u32 pramdac_table[4] = {
-               0x6808b0, 0x6808b8, 0x6828b0, 0x6828b8 };
-
-       if (tmds >= 0x80) {
-               if (init->outp) {
-                       u32 dacoffset = pramdac_offset[init->outp->or];
-                       if (tmds == 0x81)
-                               dacoffset ^= 8;
-                       return 0x6808b0 + dacoffset;
-               }
-
-               if (init_exec(init))
-                       error("tmds opcodes need dcb\n");
-       } else {
-               if (tmds < ARRAY_SIZE(pramdac_table))
-                       return pramdac_table[tmds];
-
-               error("tmds selector 0x%02x unknown\n", tmds);
-       }
-
-       return 0;
-}
-
-/******************************************************************************
- * init opcode handlers
- *****************************************************************************/
-
-/**
- * init_reserved - stub for various unknown/unused single-byte opcodes
- *
- */
-static void
-init_reserved(struct nvbios_init *init)
-{
-       u8 opcode = nv_ro08(init->bios, init->offset);
-       u8 length, i;
-
-       switch (opcode) {
-       case 0xaa:
-               length = 4;
-               break;
-       default:
-               length = 1;
-               break;
-       }
-
-       trace("RESERVED 0x%02x\t", opcode);
-       for (i = 1; i < length; i++)
-               cont(" 0x%02x", nv_ro08(init->bios, init->offset + i));
-       cont("\n");
-       init->offset += length;
-}
-
-/**
- * INIT_DONE - opcode 0x71
- *
- */
-static void
-init_done(struct nvbios_init *init)
-{
-       trace("DONE\n");
-       init->offset = 0x0000;
-}
-
-/**
- * INIT_IO_RESTRICT_PROG - opcode 0x32
- *
- */
-static void
-init_io_restrict_prog(struct nvbios_init *init)
-{
-       struct nouveau_bios *bios = init->bios;
-       u16 port = nv_ro16(bios, init->offset + 1);
-       u8 index = nv_ro08(bios, init->offset + 3);
-       u8  mask = nv_ro08(bios, init->offset + 4);
-       u8 shift = nv_ro08(bios, init->offset + 5);
-       u8 count = nv_ro08(bios, init->offset + 6);
-       u32  reg = nv_ro32(bios, init->offset + 7);
-       u8 conf, i;
-
-       trace("IO_RESTRICT_PROG\tR[0x%06x] = "
-             "((0x%04x[0x%02x] & 0x%02x) >> %d) [{\n",
-             reg, port, index, mask, shift);
-       init->offset += 11;
-
-       conf = (init_rdvgai(init, port, index) & mask) >> shift;
-       for (i = 0; i < count; i++) {
-               u32 data = nv_ro32(bios, init->offset);
-
-               if (i == conf) {
-                       trace("\t0x%08x *\n", data);
-                       init_wr32(init, reg, data);
-               } else {
-                       trace("\t0x%08x\n", data);
-               }
-
-               init->offset += 4;
-       }
-       trace("}]\n");
-}
-
-/**
- * INIT_REPEAT - opcode 0x33
- *
- */
-static void
-init_repeat(struct nvbios_init *init)
-{
-       struct nouveau_bios *bios = init->bios;
-       u8 count = nv_ro08(bios, init->offset + 1);
-       u16 repeat = init->repeat;
-
-       trace("REPEAT\t0x%02x\n", count);
-       init->offset += 2;
-
-       init->repeat = init->offset;
-       init->repend = init->offset;
-       while (count--) {
-               init->offset = init->repeat;
-               nvbios_exec(init);
-               if (count)
-                       trace("REPEAT\t0x%02x\n", count);
-       }
-       init->offset = init->repend;
-       init->repeat = repeat;
-}
-
-/**
- * INIT_IO_RESTRICT_PLL - opcode 0x34
- *
- */
-static void
-init_io_restrict_pll(struct nvbios_init *init)
-{
-       struct nouveau_bios *bios = init->bios;
-       u16 port = nv_ro16(bios, init->offset + 1);
-       u8 index = nv_ro08(bios, init->offset + 3);
-       u8  mask = nv_ro08(bios, init->offset + 4);
-       u8 shift = nv_ro08(bios, init->offset + 5);
-       s8  iofc = nv_ro08(bios, init->offset + 6);
-       u8 count = nv_ro08(bios, init->offset + 7);
-       u32  reg = nv_ro32(bios, init->offset + 8);
-       u8 conf, i;
-
-       trace("IO_RESTRICT_PLL\tR[0x%06x] =PLL= "
-             "((0x%04x[0x%02x] & 0x%02x) >> 0x%02x) IOFCOND 0x%02x [{\n",
-             reg, port, index, mask, shift, iofc);
-       init->offset += 12;
-
-       conf = (init_rdvgai(init, port, index) & mask) >> shift;
-       for (i = 0; i < count; i++) {
-               u32 freq = nv_ro16(bios, init->offset) * 10;
-
-               if (i == conf) {
-                       trace("\t%dkHz *\n", freq);
-                       if (iofc > 0 && init_io_flag_condition_met(init, iofc))
-                               freq *= 2;
-                       init_prog_pll(init, reg, freq);
-               } else {
-                       trace("\t%dkHz\n", freq);
-               }
-
-               init->offset += 2;
-       }
-       trace("}]\n");
-}
-
-/**
- * INIT_END_REPEAT - opcode 0x36
- *
- */
-static void
-init_end_repeat(struct nvbios_init *init)
-{
-       trace("END_REPEAT\n");
-       init->offset += 1;
-
-       if (init->repeat) {
-               init->repend = init->offset;
-               init->offset = 0;
-       }
-}
-
-/**
- * INIT_COPY - opcode 0x37
- *
- */
-static void
-init_copy(struct nvbios_init *init)
-{
-       struct nouveau_bios *bios = init->bios;
-       u32  reg = nv_ro32(bios, init->offset + 1);
-       u8 shift = nv_ro08(bios, init->offset + 5);
-       u8 smask = nv_ro08(bios, init->offset + 6);
-       u16 port = nv_ro16(bios, init->offset + 7);
-       u8 index = nv_ro08(bios, init->offset + 9);
-       u8  mask = nv_ro08(bios, init->offset + 10);
-       u8  data;
-
-       trace("COPY\t0x%04x[0x%02x] &= 0x%02x |= "
-             "((R[0x%06x] %s 0x%02x) & 0x%02x)\n",
-             port, index, mask, reg, (shift & 0x80) ? "<<" : ">>",
-             (shift & 0x80) ? (0x100 - shift) : shift, smask);
-       init->offset += 11;
-
-       data  = init_rdvgai(init, port, index) & mask;
-       data |= init_shift(init_rd32(init, reg), shift) & smask;
-       init_wrvgai(init, port, index, data);
-}
-
-/**
- * INIT_NOT - opcode 0x38
- *
- */
-static void
-init_not(struct nvbios_init *init)
-{
-       trace("NOT\n");
-       init->offset += 1;
-       init_exec_inv(init);
-}
-
-/**
- * INIT_IO_FLAG_CONDITION - opcode 0x39
- *
- */
-static void
-init_io_flag_condition(struct nvbios_init *init)
-{
-       struct nouveau_bios *bios = init->bios;
-       u8 cond = nv_ro08(bios, init->offset + 1);
-
-       trace("IO_FLAG_CONDITION\t0x%02x\n", cond);
-       init->offset += 2;
-
-       if (!init_io_flag_condition_met(init, cond))
-               init_exec_set(init, false);
-}
-
-/**
- * INIT_DP_CONDITION - opcode 0x3a
- *
- */
-static void
-init_dp_condition(struct nvbios_init *init)
-{
-       struct nouveau_bios *bios = init->bios;
-       struct nvbios_dpout info;
-       u8  cond = nv_ro08(bios, init->offset + 1);
-       u8  unkn = nv_ro08(bios, init->offset + 2);
-       u8  ver, hdr, cnt, len;
-       u16 data;
-
-       trace("DP_CONDITION\t0x%02x 0x%02x\n", cond, unkn);
-       init->offset += 3;
-
-       switch (cond) {
-       case 0:
-               if (init_conn(init) != DCB_CONNECTOR_eDP)
-                       init_exec_set(init, false);
-               break;
-       case 1:
-       case 2:
-               if ( init->outp &&
-                   (data = nvbios_dpout_match(bios, DCB_OUTPUT_DP,
-                                              (init->outp->or << 0) |
-                                              (init->outp->sorconf.link << 6),
-                                              &ver, &hdr, &cnt, &len, &info)))
-               {
-                       if (!(info.flags & cond))
-                               init_exec_set(init, false);
-                       break;
-               }
-
-               if (init_exec(init))
-                       warn("script needs dp output table data\n");
-               break;
-       case 5:
-               if (!(init_rdauxr(init, 0x0d) & 1))
-                       init_exec_set(init, false);
-               break;
-       default:
-               warn("unknown dp condition 0x%02x\n", cond);
-               break;
-       }
-}
-
-/**
- * INIT_IO_MASK_OR - opcode 0x3b
- *
- */
-static void
-init_io_mask_or(struct nvbios_init *init)
-{
-       struct nouveau_bios *bios = init->bios;
-       u8 index = nv_ro08(bios, init->offset + 1);
-       u8    or = init_or(init);
-       u8  data;
-
-       trace("IO_MASK_OR\t0x03d4[0x%02x] &= ~(1 << 0x%02x)\n", index, or);
-       init->offset += 2;
-
-       data = init_rdvgai(init, 0x03d4, index);
-       init_wrvgai(init, 0x03d4, index, data &= ~(1 << or));
-}
-
-/**
- * INIT_IO_OR - opcode 0x3c
- *
- */
-static void
-init_io_or(struct nvbios_init *init)
-{
-       struct nouveau_bios *bios = init->bios;
-       u8 index = nv_ro08(bios, init->offset + 1);
-       u8    or = init_or(init);
-       u8  data;
-
-       trace("IO_OR\t0x03d4[0x%02x] |= (1 << 0x%02x)\n", index, or);
-       init->offset += 2;
-
-       data = init_rdvgai(init, 0x03d4, index);
-       init_wrvgai(init, 0x03d4, index, data | (1 << or));
-}
-
-/**
- * INIT_ANDN_REG - opcode 0x47
- *
- */
-static void
-init_andn_reg(struct nvbios_init *init)
-{
-       struct nouveau_bios *bios = init->bios;
-       u32  reg = nv_ro32(bios, init->offset + 1);
-       u32 mask = nv_ro32(bios, init->offset + 5);
-
-       trace("ANDN_REG\tR[0x%06x] &= ~0x%08x\n", reg, mask);
-       init->offset += 9;
-
-       init_mask(init, reg, mask, 0);
-}
-
-/**
- * INIT_OR_REG - opcode 0x48
- *
- */
-static void
-init_or_reg(struct nvbios_init *init)
-{
-       struct nouveau_bios *bios = init->bios;
-       u32  reg = nv_ro32(bios, init->offset + 1);
-       u32 mask = nv_ro32(bios, init->offset + 5);
-
-       trace("OR_REG\tR[0x%06x] |= 0x%08x\n", reg, mask);
-       init->offset += 9;
-
-       init_mask(init, reg, 0, mask);
-}
-
-/**
- * INIT_INDEX_ADDRESS_LATCHED - opcode 0x49
- *
- */
-static void
-init_idx_addr_latched(struct nvbios_init *init)
-{
-       struct nouveau_bios *bios = init->bios;
-       u32 creg = nv_ro32(bios, init->offset + 1);
-       u32 dreg = nv_ro32(bios, init->offset + 5);
-       u32 mask = nv_ro32(bios, init->offset + 9);
-       u32 data = nv_ro32(bios, init->offset + 13);
-       u8 count = nv_ro08(bios, init->offset + 17);
-
-       trace("INDEX_ADDRESS_LATCHED\tR[0x%06x] : R[0x%06x]\n", creg, dreg);
-       trace("\tCTRL &= 0x%08x |= 0x%08x\n", mask, data);
-       init->offset += 18;
-
-       while (count--) {
-               u8 iaddr = nv_ro08(bios, init->offset + 0);
-               u8 idata = nv_ro08(bios, init->offset + 1);
-
-               trace("\t[0x%02x] = 0x%02x\n", iaddr, idata);
-               init->offset += 2;
-
-               init_wr32(init, dreg, idata);
-               init_mask(init, creg, ~mask, data | iaddr);
-       }
-}
-
-/**
- * INIT_IO_RESTRICT_PLL2 - opcode 0x4a
- *
- */
-static void
-init_io_restrict_pll2(struct nvbios_init *init)
-{
-       struct nouveau_bios *bios = init->bios;
-       u16 port = nv_ro16(bios, init->offset + 1);
-       u8 index = nv_ro08(bios, init->offset + 3);
-       u8  mask = nv_ro08(bios, init->offset + 4);
-       u8 shift = nv_ro08(bios, init->offset + 5);
-       u8 count = nv_ro08(bios, init->offset + 6);
-       u32  reg = nv_ro32(bios, init->offset + 7);
-       u8  conf, i;
-
-       trace("IO_RESTRICT_PLL2\t"
-             "R[0x%06x] =PLL= ((0x%04x[0x%02x] & 0x%02x) >> 0x%02x) [{\n",
-             reg, port, index, mask, shift);
-       init->offset += 11;
-
-       conf = (init_rdvgai(init, port, index) & mask) >> shift;
-       for (i = 0; i < count; i++) {
-               u32 freq = nv_ro32(bios, init->offset);
-               if (i == conf) {
-                       trace("\t%dkHz *\n", freq);
-                       init_prog_pll(init, reg, freq);
-               } else {
-                       trace("\t%dkHz\n", freq);
-               }
-               init->offset += 4;
-       }
-       trace("}]\n");
-}
-
-/**
- * INIT_PLL2 - opcode 0x4b
- *
- */
-static void
-init_pll2(struct nvbios_init *init)
-{
-       struct nouveau_bios *bios = init->bios;
-       u32  reg = nv_ro32(bios, init->offset + 1);
-       u32 freq = nv_ro32(bios, init->offset + 5);
-
-       trace("PLL2\tR[0x%06x] =PLL= %dkHz\n", reg, freq);
-       init->offset += 9;
-
-       init_prog_pll(init, reg, freq);
-}
-
-/**
- * INIT_I2C_BYTE - opcode 0x4c
- *
- */
-static void
-init_i2c_byte(struct nvbios_init *init)
-{
-       struct nouveau_bios *bios = init->bios;
-       u8 index = nv_ro08(bios, init->offset + 1);
-       u8  addr = nv_ro08(bios, init->offset + 2) >> 1;
-       u8 count = nv_ro08(bios, init->offset + 3);
-
-       trace("I2C_BYTE\tI2C[0x%02x][0x%02x]\n", index, addr);
-       init->offset += 4;
-
-       while (count--) {
-               u8  reg = nv_ro08(bios, init->offset + 0);
-               u8 mask = nv_ro08(bios, init->offset + 1);
-               u8 data = nv_ro08(bios, init->offset + 2);
-               int val;
-
-               trace("\t[0x%02x] &= 0x%02x |= 0x%02x\n", reg, mask, data);
-               init->offset += 3;
-
-               val = init_rdi2cr(init, index, addr, reg);
-               if (val < 0)
-                       continue;
-               init_wri2cr(init, index, addr, reg, (val & mask) | data);
-       }
-}
-
-/**
- * INIT_ZM_I2C_BYTE - opcode 0x4d
- *
- */
-static void
-init_zm_i2c_byte(struct nvbios_init *init)
-{
-       struct nouveau_bios *bios = init->bios;
-       u8 index = nv_ro08(bios, init->offset + 1);
-       u8  addr = nv_ro08(bios, init->offset + 2) >> 1;
-       u8 count = nv_ro08(bios, init->offset + 3);
-
-       trace("ZM_I2C_BYTE\tI2C[0x%02x][0x%02x]\n", index, addr);
-       init->offset += 4;
-
-       while (count--) {
-               u8  reg = nv_ro08(bios, init->offset + 0);
-               u8 data = nv_ro08(bios, init->offset + 1);
-
-               trace("\t[0x%02x] = 0x%02x\n", reg, data);
-               init->offset += 2;
-
-               init_wri2cr(init, index, addr, reg, data);
-       }
-
-}
-
-/**
- * INIT_ZM_I2C - opcode 0x4e
- *
- */
-static void
-init_zm_i2c(struct nvbios_init *init)
-{
-       struct nouveau_bios *bios = init->bios;
-       u8 index = nv_ro08(bios, init->offset + 1);
-       u8  addr = nv_ro08(bios, init->offset + 2) >> 1;
-       u8 count = nv_ro08(bios, init->offset + 3);
-       u8 data[256], i;
-
-       trace("ZM_I2C\tI2C[0x%02x][0x%02x]\n", index, addr);
-       init->offset += 4;
-
-       for (i = 0; i < count; i++) {
-               data[i] = nv_ro08(bios, init->offset);
-               trace("\t0x%02x\n", data[i]);
-               init->offset++;
-       }
-
-       if (init_exec(init)) {
-               struct nouveau_i2c_port *port = init_i2c(init, index);
-               struct i2c_msg msg = {
-                       .addr = addr, .flags = 0, .len = count, .buf = data,
-               };
-               int ret;
-
-               if (port && (ret = i2c_transfer(&port->adapter, &msg, 1)) != 1)
-                       warn("i2c wr failed, %d\n", ret);
-       }
-}
-
-/**
- * INIT_TMDS - opcode 0x4f
- *
- */
-static void
-init_tmds(struct nvbios_init *init)
-{
-       struct nouveau_bios *bios = init->bios;
-       u8 tmds = nv_ro08(bios, init->offset + 1);
-       u8 addr = nv_ro08(bios, init->offset + 2);
-       u8 mask = nv_ro08(bios, init->offset + 3);
-       u8 data = nv_ro08(bios, init->offset + 4);
-       u32 reg = init_tmds_reg(init, tmds);
-
-       trace("TMDS\tT[0x%02x][0x%02x] &= 0x%02x |= 0x%02x\n",
-             tmds, addr, mask, data);
-       init->offset += 5;
-
-       if (reg == 0)
-               return;
-
-       init_wr32(init, reg + 0, addr | 0x00010000);
-       init_wr32(init, reg + 4, data | (init_rd32(init, reg + 4) & mask));
-       init_wr32(init, reg + 0, addr);
-}
-
-/**
- * INIT_ZM_TMDS_GROUP - opcode 0x50
- *
- */
-static void
-init_zm_tmds_group(struct nvbios_init *init)
-{
-       struct nouveau_bios *bios = init->bios;
-       u8  tmds = nv_ro08(bios, init->offset + 1);
-       u8 count = nv_ro08(bios, init->offset + 2);
-       u32  reg = init_tmds_reg(init, tmds);
-
-       trace("TMDS_ZM_GROUP\tT[0x%02x]\n", tmds);
-       init->offset += 3;
-
-       while (count--) {
-               u8 addr = nv_ro08(bios, init->offset + 0);
-               u8 data = nv_ro08(bios, init->offset + 1);
-
-               trace("\t[0x%02x] = 0x%02x\n", addr, data);
-               init->offset += 2;
-
-               init_wr32(init, reg + 4, data);
-               init_wr32(init, reg + 0, addr);
-       }
-}
-
-/**
- * INIT_CR_INDEX_ADDRESS_LATCHED - opcode 0x51
- *
- */
-static void
-init_cr_idx_adr_latch(struct nvbios_init *init)
-{
-       struct nouveau_bios *bios = init->bios;
-       u8 addr0 = nv_ro08(bios, init->offset + 1);
-       u8 addr1 = nv_ro08(bios, init->offset + 2);
-       u8  base = nv_ro08(bios, init->offset + 3);
-       u8 count = nv_ro08(bios, init->offset + 4);
-       u8 save0;
-
-       trace("CR_INDEX_ADDR C[%02x] C[%02x]\n", addr0, addr1);
-       init->offset += 5;
-
-       save0 = init_rdvgai(init, 0x03d4, addr0);
-       while (count--) {
-               u8 data = nv_ro08(bios, init->offset);
-
-               trace("\t\t[0x%02x] = 0x%02x\n", base, data);
-               init->offset += 1;
-
-               init_wrvgai(init, 0x03d4, addr0, base++);
-               init_wrvgai(init, 0x03d4, addr1, data);
-       }
-       init_wrvgai(init, 0x03d4, addr0, save0);
-}
-
-/**
- * INIT_CR - opcode 0x52
- *
- */
-static void
-init_cr(struct nvbios_init *init)
-{
-       struct nouveau_bios *bios = init->bios;
-       u8 addr = nv_ro08(bios, init->offset + 1);
-       u8 mask = nv_ro08(bios, init->offset + 2);
-       u8 data = nv_ro08(bios, init->offset + 3);
-       u8 val;
-
-       trace("CR\t\tC[0x%02x] &= 0x%02x |= 0x%02x\n", addr, mask, data);
-       init->offset += 4;
-
-       val = init_rdvgai(init, 0x03d4, addr) & mask;
-       init_wrvgai(init, 0x03d4, addr, val | data);
-}
-
-/**
- * INIT_ZM_CR - opcode 0x53
- *
- */
-static void
-init_zm_cr(struct nvbios_init *init)
-{
-       struct nouveau_bios *bios = init->bios;
-       u8 addr = nv_ro08(bios, init->offset + 1);
-       u8 data = nv_ro08(bios, init->offset + 2);
-
-       trace("ZM_CR\tC[0x%02x] = 0x%02x\n", addr,  data);
-       init->offset += 3;
-
-       init_wrvgai(init, 0x03d4, addr, data);
-}
-
-/**
- * INIT_ZM_CR_GROUP - opcode 0x54
- *
- */
-static void
-init_zm_cr_group(struct nvbios_init *init)
-{
-       struct nouveau_bios *bios = init->bios;
-       u8 count = nv_ro08(bios, init->offset + 1);
-
-       trace("ZM_CR_GROUP\n");
-       init->offset += 2;
-
-       while (count--) {
-               u8 addr = nv_ro08(bios, init->offset + 0);
-               u8 data = nv_ro08(bios, init->offset + 1);
-
-               trace("\t\tC[0x%02x] = 0x%02x\n", addr, data);
-               init->offset += 2;
-
-               init_wrvgai(init, 0x03d4, addr, data);
-       }
-}
-
-/**
- * INIT_CONDITION_TIME - opcode 0x56
- *
- */
-static void
-init_condition_time(struct nvbios_init *init)
-{
-       struct nouveau_bios *bios = init->bios;
-       u8  cond = nv_ro08(bios, init->offset + 1);
-       u8 retry = nv_ro08(bios, init->offset + 2);
-       u8  wait = min((u16)retry * 50, 100);
-
-       trace("CONDITION_TIME\t0x%02x 0x%02x\n", cond, retry);
-       init->offset += 3;
-
-       if (!init_exec(init))
-               return;
-
-       while (wait--) {
-               if (init_condition_met(init, cond))
-                       return;
-               mdelay(20);
-       }
-
-       init_exec_set(init, false);
-}
-
-/**
- * INIT_LTIME - opcode 0x57
- *
- */
-static void
-init_ltime(struct nvbios_init *init)
-{
-       struct nouveau_bios *bios = init->bios;
-       u16 msec = nv_ro16(bios, init->offset + 1);
-
-       trace("LTIME\t0x%04x\n", msec);
-       init->offset += 3;
-
-       if (init_exec(init))
-               mdelay(msec);
-}
-
-/**
- * INIT_ZM_REG_SEQUENCE - opcode 0x58
- *
- */
-static void
-init_zm_reg_sequence(struct nvbios_init *init)
-{
-       struct nouveau_bios *bios = init->bios;
-       u32 base = nv_ro32(bios, init->offset + 1);
-       u8 count = nv_ro08(bios, init->offset + 5);
-
-       trace("ZM_REG_SEQUENCE\t0x%02x\n", count);
-       init->offset += 6;
-
-       while (count--) {
-               u32 data = nv_ro32(bios, init->offset);
-
-               trace("\t\tR[0x%06x] = 0x%08x\n", base, data);
-               init->offset += 4;
-
-               init_wr32(init, base, data);
-               base += 4;
-       }
-}
-
-/**
- * INIT_SUB_DIRECT - opcode 0x5b
- *
- */
-static void
-init_sub_direct(struct nvbios_init *init)
-{
-       struct nouveau_bios *bios = init->bios;
-       u16 addr = nv_ro16(bios, init->offset + 1);
-       u16 save;
-
-       trace("SUB_DIRECT\t0x%04x\n", addr);
-
-       if (init_exec(init)) {
-               save = init->offset;
-               init->offset = addr;
-               if (nvbios_exec(init)) {
-                       error("error parsing sub-table\n");
-                       return;
-               }
-               init->offset = save;
-       }
-
-       init->offset += 3;
-}
-
-/**
- * INIT_JUMP - opcode 0x5c
- *
- */
-static void
-init_jump(struct nvbios_init *init)
-{
-       struct nouveau_bios *bios = init->bios;
-       u16 offset = nv_ro16(bios, init->offset + 1);
-
-       trace("JUMP\t0x%04x\n", offset);
-
-       if (init_exec(init))
-               init->offset = offset;
-       else
-               init->offset += 3;
-}
-
-/**
- * INIT_I2C_IF - opcode 0x5e
- *
- */
-static void
-init_i2c_if(struct nvbios_init *init)
-{
-       struct nouveau_bios *bios = init->bios;
-       u8 index = nv_ro08(bios, init->offset + 1);
-       u8  addr = nv_ro08(bios, init->offset + 2);
-       u8   reg = nv_ro08(bios, init->offset + 3);
-       u8  mask = nv_ro08(bios, init->offset + 4);
-       u8  data = nv_ro08(bios, init->offset + 5);
-       u8 value;
-
-       trace("I2C_IF\tI2C[0x%02x][0x%02x][0x%02x] & 0x%02x == 0x%02x\n",
-             index, addr, reg, mask, data);
-       init->offset += 6;
-       init_exec_force(init, true);
-
-       value = init_rdi2cr(init, index, addr, reg);
-       if ((value & mask) != data)
-               init_exec_set(init, false);
-
-       init_exec_force(init, false);
-}
-
-/**
- * INIT_COPY_NV_REG - opcode 0x5f
- *
- */
-static void
-init_copy_nv_reg(struct nvbios_init *init)
-{
-       struct nouveau_bios *bios = init->bios;
-       u32  sreg = nv_ro32(bios, init->offset + 1);
-       u8  shift = nv_ro08(bios, init->offset + 5);
-       u32 smask = nv_ro32(bios, init->offset + 6);
-       u32  sxor = nv_ro32(bios, init->offset + 10);
-       u32  dreg = nv_ro32(bios, init->offset + 14);
-       u32 dmask = nv_ro32(bios, init->offset + 18);
-       u32 data;
-
-       trace("COPY_NV_REG\tR[0x%06x] &= 0x%08x |= "
-             "((R[0x%06x] %s 0x%02x) & 0x%08x ^ 0x%08x)\n",
-             dreg, dmask, sreg, (shift & 0x80) ? "<<" : ">>",
-             (shift & 0x80) ? (0x100 - shift) : shift, smask, sxor);
-       init->offset += 22;
-
-       data = init_shift(init_rd32(init, sreg), shift);
-       init_mask(init, dreg, ~dmask, (data & smask) ^ sxor);
-}
-
-/**
- * INIT_ZM_INDEX_IO - opcode 0x62
- *
- */
-static void
-init_zm_index_io(struct nvbios_init *init)
-{
-       struct nouveau_bios *bios = init->bios;
-       u16 port = nv_ro16(bios, init->offset + 1);
-       u8 index = nv_ro08(bios, init->offset + 3);
-       u8  data = nv_ro08(bios, init->offset + 4);
-
-       trace("ZM_INDEX_IO\tI[0x%04x][0x%02x] = 0x%02x\n", port, index, data);
-       init->offset += 5;
-
-       init_wrvgai(init, port, index, data);
-}
-
-/**
- * INIT_COMPUTE_MEM - opcode 0x63
- *
- */
-static void
-init_compute_mem(struct nvbios_init *init)
-{
-       struct nouveau_devinit *devinit = nouveau_devinit(init->bios);
-
-       trace("COMPUTE_MEM\n");
-       init->offset += 1;
-
-       init_exec_force(init, true);
-       if (init_exec(init) && devinit->meminit)
-               devinit->meminit(devinit);
-       init_exec_force(init, false);
-}
-
-/**
- * INIT_RESET - opcode 0x65
- *
- */
-static void
-init_reset(struct nvbios_init *init)
-{
-       struct nouveau_bios *bios = init->bios;
-       u32   reg = nv_ro32(bios, init->offset + 1);
-       u32 data1 = nv_ro32(bios, init->offset + 5);
-       u32 data2 = nv_ro32(bios, init->offset + 9);
-       u32 savepci19;
-
-       trace("RESET\tR[0x%08x] = 0x%08x, 0x%08x", reg, data1, data2);
-       init->offset += 13;
-       init_exec_force(init, true);
-
-       savepci19 = init_mask(init, 0x00184c, 0x00000f00, 0x00000000);
-       init_wr32(init, reg, data1);
-       udelay(10);
-       init_wr32(init, reg, data2);
-       init_wr32(init, 0x00184c, savepci19);
-       init_mask(init, 0x001850, 0x00000001, 0x00000000);
-
-       init_exec_force(init, false);
-}
-
-/**
- * INIT_CONFIGURE_MEM - opcode 0x66
- *
- */
-static u16
-init_configure_mem_clk(struct nvbios_init *init)
-{
-       u16 mdata = bmp_mem_init_table(init->bios);
-       if (mdata)
-               mdata += (init_rdvgai(init, 0x03d4, 0x3c) >> 4) * 66;
-       return mdata;
-}
-
-static void
-init_configure_mem(struct nvbios_init *init)
-{
-       struct nouveau_bios *bios = init->bios;
-       u16 mdata, sdata;
-       u32 addr, data;
-
-       trace("CONFIGURE_MEM\n");
-       init->offset += 1;
-
-       if (bios->version.major > 2) {
-               init_done(init);
-               return;
-       }
-       init_exec_force(init, true);
-
-       mdata = init_configure_mem_clk(init);
-       sdata = bmp_sdr_seq_table(bios);
-       if (nv_ro08(bios, mdata) & 0x01)
-               sdata = bmp_ddr_seq_table(bios);
-       mdata += 6; /* skip to data */
-
-       data = init_rdvgai(init, 0x03c4, 0x01);
-       init_wrvgai(init, 0x03c4, 0x01, data | 0x20);
-
-       for (; (addr = nv_ro32(bios, sdata)) != 0xffffffff; sdata += 4) {
-               switch (addr) {
-               case 0x10021c: /* CKE_NORMAL */
-               case 0x1002d0: /* CMD_REFRESH */
-               case 0x1002d4: /* CMD_PRECHARGE */
-                       data = 0x00000001;
-                       break;
-               default:
-                       data = nv_ro32(bios, mdata);
-                       mdata += 4;
-                       if (data == 0xffffffff)
-                               continue;
-                       break;
-               }
-
-               init_wr32(init, addr, data);
-       }
-
-       init_exec_force(init, false);
-}
-
-/**
- * INIT_CONFIGURE_CLK - opcode 0x67
- *
- */
-static void
-init_configure_clk(struct nvbios_init *init)
-{
-       struct nouveau_bios *bios = init->bios;
-       u16 mdata, clock;
-
-       trace("CONFIGURE_CLK\n");
-       init->offset += 1;
-
-       if (bios->version.major > 2) {
-               init_done(init);
-               return;
-       }
-       init_exec_force(init, true);
-
-       mdata = init_configure_mem_clk(init);
-
-       /* NVPLL */
-       clock = nv_ro16(bios, mdata + 4) * 10;
-       init_prog_pll(init, 0x680500, clock);
-
-       /* MPLL */
-       clock = nv_ro16(bios, mdata + 2) * 10;
-       if (nv_ro08(bios, mdata) & 0x01)
-               clock *= 2;
-       init_prog_pll(init, 0x680504, clock);
-
-       init_exec_force(init, false);
-}
-
-/**
- * INIT_CONFIGURE_PREINIT - opcode 0x68
- *
- */
-static void
-init_configure_preinit(struct nvbios_init *init)
-{
-       struct nouveau_bios *bios = init->bios;
-       u32 strap;
-
-       trace("CONFIGURE_PREINIT\n");
-       init->offset += 1;
-
-       if (bios->version.major > 2) {
-               init_done(init);
-               return;
-       }
-       init_exec_force(init, true);
-
-       strap = init_rd32(init, 0x101000);
-       strap = ((strap << 2) & 0xf0) | ((strap & 0x40) >> 6);
-       init_wrvgai(init, 0x03d4, 0x3c, strap);
-
-       init_exec_force(init, false);
-}
-
-/**
- * INIT_IO - opcode 0x69
- *
- */
-static void
-init_io(struct nvbios_init *init)
-{
-       struct nouveau_bios *bios = init->bios;
-       u16 port = nv_ro16(bios, init->offset + 1);
-       u8  mask = nv_ro16(bios, init->offset + 3);
-       u8  data = nv_ro16(bios, init->offset + 4);
-       u8 value;
-
-       trace("IO\t\tI[0x%04x] &= 0x%02x |= 0x%02x\n", port, mask, data);
-       init->offset += 5;
-
-       /* ummm.. yes.. should really figure out wtf this is and why it's
-        * needed some day..  it's almost certainly wrong, but, it also
-        * somehow makes things work...
-        */
-       if (nv_device(init->bios)->card_type >= NV_50 &&
-           port == 0x03c3 && data == 0x01) {
-               init_mask(init, 0x614100, 0xf0800000, 0x00800000);
-               init_mask(init, 0x00e18c, 0x00020000, 0x00020000);
-               init_mask(init, 0x614900, 0xf0800000, 0x00800000);
-               init_mask(init, 0x000200, 0x40000000, 0x00000000);
-               mdelay(10);
-               init_mask(init, 0x00e18c, 0x00020000, 0x00000000);
-               init_mask(init, 0x000200, 0x40000000, 0x40000000);
-               init_wr32(init, 0x614100, 0x00800018);
-               init_wr32(init, 0x614900, 0x00800018);
-               mdelay(10);
-               init_wr32(init, 0x614100, 0x10000018);
-               init_wr32(init, 0x614900, 0x10000018);
-       }
-
-       value = init_rdport(init, port) & mask;
-       init_wrport(init, port, data | value);
-}
-
-/**
- * INIT_SUB - opcode 0x6b
- *
- */
-static void
-init_sub(struct nvbios_init *init)
-{
-       struct nouveau_bios *bios = init->bios;
-       u8 index = nv_ro08(bios, init->offset + 1);
-       u16 addr, save;
-
-       trace("SUB\t0x%02x\n", index);
-
-       addr = init_script(bios, index);
-       if (addr && init_exec(init)) {
-               save = init->offset;
-               init->offset = addr;
-               if (nvbios_exec(init)) {
-                       error("error parsing sub-table\n");
-                       return;
-               }
-               init->offset = save;
-       }
-
-       init->offset += 2;
-}
-
-/**
- * INIT_RAM_CONDITION - opcode 0x6d
- *
- */
-static void
-init_ram_condition(struct nvbios_init *init)
-{
-       struct nouveau_bios *bios = init->bios;
-       u8  mask = nv_ro08(bios, init->offset + 1);
-       u8 value = nv_ro08(bios, init->offset + 2);
-
-       trace("RAM_CONDITION\t"
-             "(R[0x100000] & 0x%02x) == 0x%02x\n", mask, value);
-       init->offset += 3;
-
-       if ((init_rd32(init, 0x100000) & mask) != value)
-               init_exec_set(init, false);
-}
-
-/**
- * INIT_NV_REG - opcode 0x6e
- *
- */
-static void
-init_nv_reg(struct nvbios_init *init)
-{
-       struct nouveau_bios *bios = init->bios;
-       u32  reg = nv_ro32(bios, init->offset + 1);
-       u32 mask = nv_ro32(bios, init->offset + 5);
-       u32 data = nv_ro32(bios, init->offset + 9);
-
-       trace("NV_REG\tR[0x%06x] &= 0x%08x |= 0x%08x\n", reg, mask, data);
-       init->offset += 13;
-
-       init_mask(init, reg, ~mask, data);
-}
-
-/**
- * INIT_MACRO - opcode 0x6f
- *
- */
-static void
-init_macro(struct nvbios_init *init)
-{
-       struct nouveau_bios *bios = init->bios;
-       u8  macro = nv_ro08(bios, init->offset + 1);
-       u16 table;
-
-       trace("MACRO\t0x%02x\n", macro);
-
-       table = init_macro_table(init);
-       if (table) {
-               u32 addr = nv_ro32(bios, table + (macro * 8) + 0);
-               u32 data = nv_ro32(bios, table + (macro * 8) + 4);
-               trace("\t\tR[0x%06x] = 0x%08x\n", addr, data);
-               init_wr32(init, addr, data);
-       }
-
-       init->offset += 2;
-}
-
-/**
- * INIT_RESUME - opcode 0x72
- *
- */
-static void
-init_resume(struct nvbios_init *init)
-{
-       trace("RESUME\n");
-       init->offset += 1;
-       init_exec_set(init, true);
-}
-
-/**
- * INIT_TIME - opcode 0x74
- *
- */
-static void
-init_time(struct nvbios_init *init)
-{
-       struct nouveau_bios *bios = init->bios;
-       u16 usec = nv_ro16(bios, init->offset + 1);
-
-       trace("TIME\t0x%04x\n", usec);
-       init->offset += 3;
-
-       if (init_exec(init)) {
-               if (usec < 1000)
-                       udelay(usec);
-               else
-                       mdelay((usec + 900) / 1000);
-       }
-}
-
-/**
- * INIT_CONDITION - opcode 0x75
- *
- */
-static void
-init_condition(struct nvbios_init *init)
-{
-       struct nouveau_bios *bios = init->bios;
-       u8 cond = nv_ro08(bios, init->offset + 1);
-
-       trace("CONDITION\t0x%02x\n", cond);
-       init->offset += 2;
-
-       if (!init_condition_met(init, cond))
-               init_exec_set(init, false);
-}
-
-/**
- * INIT_IO_CONDITION - opcode 0x76
- *
- */
-static void
-init_io_condition(struct nvbios_init *init)
-{
-       struct nouveau_bios *bios = init->bios;
-       u8 cond = nv_ro08(bios, init->offset + 1);
-
-       trace("IO_CONDITION\t0x%02x\n", cond);
-       init->offset += 2;
-
-       if (!init_io_condition_met(init, cond))
-               init_exec_set(init, false);
-}
-
-/**
- * INIT_INDEX_IO - opcode 0x78
- *
- */
-static void
-init_index_io(struct nvbios_init *init)
-{
-       struct nouveau_bios *bios = init->bios;
-       u16 port = nv_ro16(bios, init->offset + 1);
-       u8 index = nv_ro16(bios, init->offset + 3);
-       u8  mask = nv_ro08(bios, init->offset + 4);
-       u8  data = nv_ro08(bios, init->offset + 5);
-       u8 value;
-
-       trace("INDEX_IO\tI[0x%04x][0x%02x] &= 0x%02x |= 0x%02x\n",
-             port, index, mask, data);
-       init->offset += 6;
-
-       value = init_rdvgai(init, port, index) & mask;
-       init_wrvgai(init, port, index, data | value);
-}
-
-/**
- * INIT_PLL - opcode 0x79
- *
- */
-static void
-init_pll(struct nvbios_init *init)
-{
-       struct nouveau_bios *bios = init->bios;
-       u32  reg = nv_ro32(bios, init->offset + 1);
-       u32 freq = nv_ro16(bios, init->offset + 5) * 10;
-
-       trace("PLL\tR[0x%06x] =PLL= %dkHz\n", reg, freq);
-       init->offset += 7;
-
-       init_prog_pll(init, reg, freq);
-}
-
-/**
- * INIT_ZM_REG - opcode 0x7a
- *
- */
-static void
-init_zm_reg(struct nvbios_init *init)
-{
-       struct nouveau_bios *bios = init->bios;
-       u32 addr = nv_ro32(bios, init->offset + 1);
-       u32 data = nv_ro32(bios, init->offset + 5);
-
-       trace("ZM_REG\tR[0x%06x] = 0x%08x\n", addr, data);
-       init->offset += 9;
-
-       if (addr == 0x000200)
-               data |= 0x00000001;
-
-       init_wr32(init, addr, data);
-}
-
-/**
- * INIT_RAM_RESTRICT_PLL - opcde 0x87
- *
- */
-static void
-init_ram_restrict_pll(struct nvbios_init *init)
-{
-       struct nouveau_bios *bios = init->bios;
-       u8  type = nv_ro08(bios, init->offset + 1);
-       u8 count = init_ram_restrict_group_count(init);
-       u8 strap = init_ram_restrict(init);
-       u8 cconf;
-
-       trace("RAM_RESTRICT_PLL\t0x%02x\n", type);
-       init->offset += 2;
-
-       for (cconf = 0; cconf < count; cconf++) {
-               u32 freq = nv_ro32(bios, init->offset);
-
-               if (cconf == strap) {
-                       trace("%dkHz *\n", freq);
-                       init_prog_pll(init, type, freq);
-               } else {
-                       trace("%dkHz\n", freq);
-               }
-
-               init->offset += 4;
-       }
-}
-
-/**
- * INIT_GPIO - opcode 0x8e
- *
- */
-static void
-init_gpio(struct nvbios_init *init)
-{
-       struct nouveau_gpio *gpio = nouveau_gpio(init->bios);
-
-       trace("GPIO\n");
-       init->offset += 1;
-
-       if (init_exec(init) && gpio && gpio->reset)
-               gpio->reset(gpio, DCB_GPIO_UNUSED);
-}
-
-/**
- * INIT_RAM_RESTRICT_ZM_GROUP - opcode 0x8f
- *
- */
-static void
-init_ram_restrict_zm_reg_group(struct nvbios_init *init)
-{
-       struct nouveau_bios *bios = init->bios;
-       u32 addr = nv_ro32(bios, init->offset + 1);
-       u8  incr = nv_ro08(bios, init->offset + 5);
-       u8   num = nv_ro08(bios, init->offset + 6);
-       u8 count = init_ram_restrict_group_count(init);
-       u8 index = init_ram_restrict(init);
-       u8 i, j;
-
-       trace("RAM_RESTRICT_ZM_REG_GROUP\t"
-             "R[0x%08x] 0x%02x 0x%02x\n", addr, incr, num);
-       init->offset += 7;
-
-       for (i = 0; i < num; i++) {
-               trace("\tR[0x%06x] = {\n", addr);
-               for (j = 0; j < count; j++) {
-                       u32 data = nv_ro32(bios, init->offset);
-
-                       if (j == index) {
-                               trace("\t\t0x%08x *\n", data);
-                               init_wr32(init, addr, data);
-                       } else {
-                               trace("\t\t0x%08x\n", data);
-                       }
-
-                       init->offset += 4;
-               }
-               trace("\t}\n");
-               addr += incr;
-       }
-}
-
-/**
- * INIT_COPY_ZM_REG - opcode 0x90
- *
- */
-static void
-init_copy_zm_reg(struct nvbios_init *init)
-{
-       struct nouveau_bios *bios = init->bios;
-       u32 sreg = nv_ro32(bios, init->offset + 1);
-       u32 dreg = nv_ro32(bios, init->offset + 5);
-
-       trace("COPY_ZM_REG\tR[0x%06x] = R[0x%06x]\n", dreg, sreg);
-       init->offset += 9;
-
-       init_wr32(init, dreg, init_rd32(init, sreg));
-}
-
-/**
- * INIT_ZM_REG_GROUP - opcode 0x91
- *
- */
-static void
-init_zm_reg_group(struct nvbios_init *init)
-{
-       struct nouveau_bios *bios = init->bios;
-       u32 addr = nv_ro32(bios, init->offset + 1);
-       u8 count = nv_ro08(bios, init->offset + 5);
-
-       trace("ZM_REG_GROUP\tR[0x%06x] =\n", addr);
-       init->offset += 6;
-
-       while (count--) {
-               u32 data = nv_ro32(bios, init->offset);
-               trace("\t0x%08x\n", data);
-               init_wr32(init, addr, data);
-               init->offset += 4;
-       }
-}
-
-/**
- * INIT_XLAT - opcode 0x96
- *
- */
-static void
-init_xlat(struct nvbios_init *init)
-{
-       struct nouveau_bios *bios = init->bios;
-       u32 saddr = nv_ro32(bios, init->offset + 1);
-       u8 sshift = nv_ro08(bios, init->offset + 5);
-       u8  smask = nv_ro08(bios, init->offset + 6);
-       u8  index = nv_ro08(bios, init->offset + 7);
-       u32 daddr = nv_ro32(bios, init->offset + 8);
-       u32 dmask = nv_ro32(bios, init->offset + 12);
-       u8  shift = nv_ro08(bios, init->offset + 16);
-       u32 data;
-
-       trace("INIT_XLAT\tR[0x%06x] &= 0x%08x |= "
-             "(X%02x((R[0x%06x] %s 0x%02x) & 0x%02x) << 0x%02x)\n",
-             daddr, dmask, index, saddr, (sshift & 0x80) ? "<<" : ">>",
-             (sshift & 0x80) ? (0x100 - sshift) : sshift, smask, shift);
-       init->offset += 17;
-
-       data = init_shift(init_rd32(init, saddr), sshift) & smask;
-       data = init_xlat_(init, index, data) << shift;
-       init_mask(init, daddr, ~dmask, data);
-}
-
-/**
- * INIT_ZM_MASK_ADD - opcode 0x97
- *
- */
-static void
-init_zm_mask_add(struct nvbios_init *init)
-{
-       struct nouveau_bios *bios = init->bios;
-       u32 addr = nv_ro32(bios, init->offset + 1);
-       u32 mask = nv_ro32(bios, init->offset + 5);
-       u32  add = nv_ro32(bios, init->offset + 9);
-       u32 data;
-
-       trace("ZM_MASK_ADD\tR[0x%06x] &= 0x%08x += 0x%08x\n", addr, mask, add);
-       init->offset += 13;
-
-       data =  init_rd32(init, addr);
-       data = (data & mask) | ((data + add) & ~mask);
-       init_wr32(init, addr, data);
-}
-
-/**
- * INIT_AUXCH - opcode 0x98
- *
- */
-static void
-init_auxch(struct nvbios_init *init)
-{
-       struct nouveau_bios *bios = init->bios;
-       u32 addr = nv_ro32(bios, init->offset + 1);
-       u8 count = nv_ro08(bios, init->offset + 5);
-
-       trace("AUXCH\tAUX[0x%08x] 0x%02x\n", addr, count);
-       init->offset += 6;
-
-       while (count--) {
-               u8 mask = nv_ro08(bios, init->offset + 0);
-               u8 data = nv_ro08(bios, init->offset + 1);
-               trace("\tAUX[0x%08x] &= 0x%02x |= 0x%02x\n", addr, mask, data);
-               mask = init_rdauxr(init, addr) & mask;
-               init_wrauxr(init, addr, mask | data);
-               init->offset += 2;
-       }
-}
-
-/**
- * INIT_AUXCH - opcode 0x99
- *
- */
-static void
-init_zm_auxch(struct nvbios_init *init)
-{
-       struct nouveau_bios *bios = init->bios;
-       u32 addr = nv_ro32(bios, init->offset + 1);
-       u8 count = nv_ro08(bios, init->offset + 5);
-
-       trace("ZM_AUXCH\tAUX[0x%08x] 0x%02x\n", addr, count);
-       init->offset += 6;
-
-       while (count--) {
-               u8 data = nv_ro08(bios, init->offset + 0);
-               trace("\tAUX[0x%08x] = 0x%02x\n", addr, data);
-               init_wrauxr(init, addr, data);
-               init->offset += 1;
-       }
-}
-
-/**
- * INIT_I2C_LONG_IF - opcode 0x9a
- *
- */
-static void
-init_i2c_long_if(struct nvbios_init *init)
-{
-       struct nouveau_bios *bios = init->bios;
-       u8 index = nv_ro08(bios, init->offset + 1);
-       u8  addr = nv_ro08(bios, init->offset + 2) >> 1;
-       u8 reglo = nv_ro08(bios, init->offset + 3);
-       u8 reghi = nv_ro08(bios, init->offset + 4);
-       u8  mask = nv_ro08(bios, init->offset + 5);
-       u8  data = nv_ro08(bios, init->offset + 6);
-       struct nouveau_i2c_port *port;
-
-       trace("I2C_LONG_IF\t"
-             "I2C[0x%02x][0x%02x][0x%02x%02x] & 0x%02x == 0x%02x\n",
-             index, addr, reglo, reghi, mask, data);
-       init->offset += 7;
-
-       port = init_i2c(init, index);
-       if (port) {
-               u8 i[2] = { reghi, reglo };
-               u8 o[1] = {};
-               struct i2c_msg msg[] = {
-                       { .addr = addr, .flags = 0, .len = 2, .buf = i },
-                       { .addr = addr, .flags = I2C_M_RD, .len = 1, .buf = o }
-               };
-               int ret;
-
-               ret = i2c_transfer(&port->adapter, msg, 2);
-               if (ret == 2 && ((o[0] & mask) == data))
-                       return;
-       }
-
-       init_exec_set(init, false);
-}
-
-/**
- * INIT_GPIO_NE - opcode 0xa9
- *
- */
-static void
-init_gpio_ne(struct nvbios_init *init)
-{
-       struct nouveau_bios *bios = init->bios;
-       struct nouveau_gpio *gpio = nouveau_gpio(bios);
-       struct dcb_gpio_func func;
-       u8 count = nv_ro08(bios, init->offset + 1);
-       u8 idx = 0, ver, len;
-       u16 data, i;
-
-       trace("GPIO_NE\t");
-       init->offset += 2;
-
-       for (i = init->offset; i < init->offset + count; i++)
-               cont("0x%02x ", nv_ro08(bios, i));
-       cont("\n");
-
-       while ((data = dcb_gpio_parse(bios, 0, idx++, &ver, &len, &func))) {
-               if (func.func != DCB_GPIO_UNUSED) {
-                       for (i = init->offset; i < init->offset + count; i++) {
-                               if (func.func == nv_ro08(bios, i))
-                                       break;
-                       }
-
-                       trace("\tFUNC[0x%02x]", func.func);
-                       if (i == (init->offset + count)) {
-                               cont(" *");
-                               if (init_exec(init) && gpio && gpio->reset)
-                                       gpio->reset(gpio, func.func);
-                       }
-                       cont("\n");
-               }
-       }
-
-       init->offset += count;
-}
-
-static struct nvbios_init_opcode {
-       void (*exec)(struct nvbios_init *);
-} init_opcode[] = {
-       [0x32] = { init_io_restrict_prog },
-       [0x33] = { init_repeat },
-       [0x34] = { init_io_restrict_pll },
-       [0x36] = { init_end_repeat },
-       [0x37] = { init_copy },
-       [0x38] = { init_not },
-       [0x39] = { init_io_flag_condition },
-       [0x3a] = { init_dp_condition },
-       [0x3b] = { init_io_mask_or },
-       [0x3c] = { init_io_or },
-       [0x47] = { init_andn_reg },
-       [0x48] = { init_or_reg },
-       [0x49] = { init_idx_addr_latched },
-       [0x4a] = { init_io_restrict_pll2 },
-       [0x4b] = { init_pll2 },
-       [0x4c] = { init_i2c_byte },
-       [0x4d] = { init_zm_i2c_byte },
-       [0x4e] = { init_zm_i2c },
-       [0x4f] = { init_tmds },
-       [0x50] = { init_zm_tmds_group },
-       [0x51] = { init_cr_idx_adr_latch },
-       [0x52] = { init_cr },
-       [0x53] = { init_zm_cr },
-       [0x54] = { init_zm_cr_group },
-       [0x56] = { init_condition_time },
-       [0x57] = { init_ltime },
-       [0x58] = { init_zm_reg_sequence },
-       [0x5b] = { init_sub_direct },
-       [0x5c] = { init_jump },
-       [0x5e] = { init_i2c_if },
-       [0x5f] = { init_copy_nv_reg },
-       [0x62] = { init_zm_index_io },
-       [0x63] = { init_compute_mem },
-       [0x65] = { init_reset },
-       [0x66] = { init_configure_mem },
-       [0x67] = { init_configure_clk },
-       [0x68] = { init_configure_preinit },
-       [0x69] = { init_io },
-       [0x6b] = { init_sub },
-       [0x6d] = { init_ram_condition },
-       [0x6e] = { init_nv_reg },
-       [0x6f] = { init_macro },
-       [0x71] = { init_done },
-       [0x72] = { init_resume },
-       [0x74] = { init_time },
-       [0x75] = { init_condition },
-       [0x76] = { init_io_condition },
-       [0x78] = { init_index_io },
-       [0x79] = { init_pll },
-       [0x7a] = { init_zm_reg },
-       [0x87] = { init_ram_restrict_pll },
-       [0x8c] = { init_reserved },
-       [0x8d] = { init_reserved },
-       [0x8e] = { init_gpio },
-       [0x8f] = { init_ram_restrict_zm_reg_group },
-       [0x90] = { init_copy_zm_reg },
-       [0x91] = { init_zm_reg_group },
-       [0x92] = { init_reserved },
-       [0x96] = { init_xlat },
-       [0x97] = { init_zm_mask_add },
-       [0x98] = { init_auxch },
-       [0x99] = { init_zm_auxch },
-       [0x9a] = { init_i2c_long_if },
-       [0xa9] = { init_gpio_ne },
-       [0xaa] = { init_reserved },
-};
-
-#define init_opcode_nr (sizeof(init_opcode) / sizeof(init_opcode[0]))
-
-int
-nvbios_exec(struct nvbios_init *init)
-{
-       init->nested++;
-       while (init->offset) {
-               u8 opcode = nv_ro08(init->bios, init->offset);
-               if (opcode >= init_opcode_nr || !init_opcode[opcode].exec) {
-                       error("unknown opcode 0x%02x\n", opcode);
-                       return -EINVAL;
-               }
-
-               init_opcode[opcode].exec(init);
-       }
-       init->nested--;
-       return 0;
-}
-
-int
-nvbios_init(struct nouveau_subdev *subdev, bool execute)
-{
-       struct nouveau_bios *bios = nouveau_bios(subdev);
-       int ret = 0;
-       int i = -1;
-       u16 data;
-
-       if (execute)
-               nv_info(bios, "running init tables\n");
-       while (!ret && (data = (init_script(bios, ++i)))) {
-               struct nvbios_init init = {
-                       .subdev = subdev,
-                       .bios = bios,
-                       .offset = data,
-                       .outp = NULL,
-                       .crtc = -1,
-                       .execute = execute ? 1 : 0,
-               };
-
-               ret = nvbios_exec(&init);
-       }
-
-       /* the vbios parser will run this right after the normal init
-        * tables, whereas the binary driver appears to run it later.
-        */
-       if (!ret && (data = init_unknown_script(bios))) {
-               struct nvbios_init init = {
-                       .subdev = subdev,
-                       .bios = bios,
-                       .offset = data,
-                       .outp = NULL,
-                       .crtc = -1,
-                       .execute = execute ? 1 : 0,
-               };
-
-               ret = nvbios_exec(&init);
-       }
-
-       return ret;
-}
diff --git a/drivers/gpu/drm/nouveau/core/subdev/bios/mxm.c b/drivers/gpu/drm/nouveau/core/subdev/bios/mxm.c
deleted file mode 100644 (file)
index 2610b11..0000000
+++ /dev/null
@@ -1,135 +0,0 @@
-/*
- * Copyright 2012 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 <subdev/bios.h>
-#include <subdev/bios/bit.h>
-#include <subdev/bios/mxm.h>
-
-u16
-mxm_table(struct nouveau_bios *bios, u8 *ver, u8 *hdr)
-{
-       struct bit_entry x;
-
-       if (bit_entry(bios, 'x', &x)) {
-               nv_debug(bios, "BIT 'x' table not present\n");
-               return 0x0000;
-       }
-
-       *ver = x.version;
-       *hdr = x.length;
-       if (*ver != 1 || *hdr < 3) {
-               nv_warn(bios, "BIT 'x' table %d/%d unknown\n", *ver, *hdr);
-               return 0x0000;
-       }
-
-       return x.offset;
-}
-
-/* These map MXM v2.x digital connection values to the appropriate SOR/link,
- * hopefully they're correct for all boards within the same chipset...
- *
- * MXM v3.x VBIOS are nicer and provide pointers to these tables.
- */
-static u8 nv84_sor_map[16] = {
-       0x00, 0x12, 0x22, 0x11, 0x32, 0x31, 0x11, 0x31,
-       0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00
-};
-
-static u8 nv92_sor_map[16] = {
-       0x00, 0x12, 0x22, 0x11, 0x32, 0x31, 0x11, 0x31,
-       0x11, 0x31, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00
-};
-
-static u8 nv94_sor_map[16] = {
-       0x00, 0x14, 0x24, 0x11, 0x34, 0x31, 0x11, 0x31,
-       0x11, 0x31, 0x12, 0x00, 0x00, 0x00, 0x00, 0x00
-};
-
-static u8 nv98_sor_map[16] = {
-       0x00, 0x14, 0x12, 0x11, 0x00, 0x31, 0x11, 0x31,
-       0x11, 0x31, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00
-};
-
-u8
-mxm_sor_map(struct nouveau_bios *bios, u8 conn)
-{
-       u8  ver, hdr;
-       u16 mxm = mxm_table(bios, &ver, &hdr);
-       if (mxm && hdr >= 6) {
-               u16 map = nv_ro16(bios, mxm + 4);
-               if (map) {
-                       ver = nv_ro08(bios, map);
-                       if (ver == 0x10) {
-                               if (conn < nv_ro08(bios, map + 3)) {
-                                       map += nv_ro08(bios, map + 1);
-                                       map += conn;
-                                       return nv_ro08(bios, map);
-                               }
-
-                               return 0x00;
-                       }
-
-                       nv_warn(bios, "unknown sor map v%02x\n", ver);
-               }
-       }
-
-       if (bios->version.chip == 0x84 || bios->version.chip == 0x86)
-               return nv84_sor_map[conn];
-       if (bios->version.chip == 0x92)
-               return nv92_sor_map[conn];
-       if (bios->version.chip == 0x94 || bios->version.chip == 0x96)
-               return nv94_sor_map[conn];
-       if (bios->version.chip == 0x98)
-               return nv98_sor_map[conn];
-
-       nv_warn(bios, "missing sor map\n");
-       return 0x00;
-}
-
-u8
-mxm_ddc_map(struct nouveau_bios *bios, u8 port)
-{
-       u8  ver, hdr;
-       u16 mxm = mxm_table(bios, &ver, &hdr);
-       if (mxm && hdr >= 8) {
-               u16 map = nv_ro16(bios, mxm + 6);
-               if (map) {
-                       ver = nv_ro08(bios, map);
-                       if (ver == 0x10) {
-                               if (port < nv_ro08(bios, map + 3)) {
-                                       map += nv_ro08(bios, map + 1);
-                                       map += port;
-                                       return nv_ro08(bios, map);
-                               }
-
-                               return 0x00;
-                       }
-
-                       nv_warn(bios, "unknown ddc map v%02x\n", ver);
-               }
-       }
-
-       /* v2.x: directly write port as dcb i2cidx */
-       return (port << 4) | port;
-}
diff --git a/drivers/gpu/drm/nouveau/core/subdev/bios/npde.c b/drivers/gpu/drm/nouveau/core/subdev/bios/npde.c
deleted file mode 100644 (file)
index d694716..0000000
+++ /dev/null
@@ -1,59 +0,0 @@
-/*
- * Copyright 2014 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 <bskeggs@redhat.com>
- */
-
-#include <subdev/bios.h>
-#include <subdev/bios/npde.h>
-#include <subdev/bios/pcir.h>
-
-u32
-nvbios_npdeTe(struct nouveau_bios *bios, u32 base)
-{
-       struct nvbios_pcirT pcir;
-       u8  ver; u16 hdr;
-       u32 data = nvbios_pcirTp(bios, base, &ver, &hdr, &pcir);
-       if (data = (data + hdr + 0x0f) & ~0x0f, data) {
-               switch (nv_ro32(bios, data + 0x00)) {
-               case 0x4544504e: /* NPDE */
-                       break;
-               default:
-                       nv_debug(bios, "%08x: NPDE signature (%08x) unknown\n",
-                                data, nv_ro32(bios, data + 0x00));
-                       data = 0;
-                       break;
-               }
-       }
-       return data;
-}
-
-u32
-nvbios_npdeTp(struct nouveau_bios *bios, u32 base, struct nvbios_npdeT *info)
-{
-       u32 data = nvbios_npdeTe(bios, base);
-       memset(info, 0x00, sizeof(*info));
-       if (data) {
-               info->image_size = nv_ro16(bios, data + 0x08) * 512;
-               info->last = nv_ro08(bios, data + 0x0a) & 0x80;
-       }
-       return data;
-}
diff --git a/drivers/gpu/drm/nouveau/core/subdev/bios/pcir.c b/drivers/gpu/drm/nouveau/core/subdev/bios/pcir.c
deleted file mode 100644 (file)
index 91dae26..0000000
+++ /dev/null
@@ -1,69 +0,0 @@
-/*
- * Copyright 2014 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 <bskeggs@redhat.com>
- */
-
-#include <subdev/bios.h>
-#include <subdev/bios/pcir.h>
-
-u32
-nvbios_pcirTe(struct nouveau_bios *bios, u32 base, u8 *ver, u16 *hdr)
-{
-       u32 data = nv_ro16(bios, base + 0x18);
-       if (data) {
-               data += base;
-               switch (nv_ro32(bios, data + 0x00)) {
-               case 0x52494350: /* PCIR */
-               case 0x53494752: /* RGIS */
-               case 0x5344504e: /* NPDS */
-                       *hdr = nv_ro16(bios, data + 0x0a);
-                       *ver = nv_ro08(bios, data + 0x0c);
-                       break;
-               default:
-                       nv_debug(bios, "%08x: PCIR signature (%08x) unknown\n",
-                                data, nv_ro32(bios, data + 0x00));
-                       data = 0;
-                       break;
-               }
-       }
-       return data;
-}
-
-u32
-nvbios_pcirTp(struct nouveau_bios *bios, u32 base, u8 *ver, u16 *hdr,
-             struct nvbios_pcirT *info)
-{
-       u32 data = nvbios_pcirTe(bios, base, ver, hdr);
-       memset(info, 0x00, sizeof(*info));
-       if (data) {
-               info->vendor_id = nv_ro16(bios, data + 0x04);
-               info->device_id = nv_ro16(bios, data + 0x06);
-               info->class_code[0] = nv_ro08(bios, data + 0x0d);
-               info->class_code[1] = nv_ro08(bios, data + 0x0e);
-               info->class_code[2] = nv_ro08(bios, data + 0x0f);
-               info->image_size = nv_ro16(bios, data + 0x10) * 512;
-               info->image_rev = nv_ro16(bios, data + 0x12);
-               info->image_type = nv_ro08(bios, data + 0x14);
-               info->last = nv_ro08(bios, data + 0x15) & 0x80;
-       }
-       return data;
-}
diff --git a/drivers/gpu/drm/nouveau/core/subdev/bios/perf.c b/drivers/gpu/drm/nouveau/core/subdev/bios/perf.c
deleted file mode 100644 (file)
index 675e221..0000000
+++ /dev/null
@@ -1,201 +0,0 @@
-/*
- * Copyright 2012 Nouveau Community
- *
- * 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 <subdev/bios.h>
-#include <subdev/bios/bit.h>
-#include <subdev/bios/perf.h>
-
-u16
-nvbios_perf_table(struct nouveau_bios *bios, u8 *ver, u8 *hdr,
-                 u8 *cnt, u8 *len, u8 *snr, u8 *ssz)
-{
-       struct bit_entry bit_P;
-       u16 perf = 0x0000;
-
-       if (!bit_entry(bios, 'P', &bit_P)) {
-               if (bit_P.version <= 2) {
-                       perf = nv_ro16(bios, bit_P.offset + 0);
-                       if (perf) {
-                               *ver = nv_ro08(bios, perf + 0);
-                               *hdr = nv_ro08(bios, perf + 1);
-                               if (*ver >= 0x40 && *ver < 0x41) {
-                                       *cnt = nv_ro08(bios, perf + 5);
-                                       *len = nv_ro08(bios, perf + 2);
-                                       *snr = nv_ro08(bios, perf + 4);
-                                       *ssz = nv_ro08(bios, perf + 3);
-                                       return perf;
-                               } else
-                               if (*ver >= 0x20 && *ver < 0x40) {
-                                       *cnt = nv_ro08(bios, perf + 2);
-                                       *len = nv_ro08(bios, perf + 3);
-                                       *snr = nv_ro08(bios, perf + 4);
-                                       *ssz = nv_ro08(bios, perf + 5);
-                                       return perf;
-                               }
-                       }
-               }
-       }
-
-       if (bios->bmp_offset) {
-               if (nv_ro08(bios, bios->bmp_offset + 6) >= 0x25) {
-                       perf = nv_ro16(bios, bios->bmp_offset + 0x94);
-                       if (perf) {
-                               *hdr = nv_ro08(bios, perf + 0);
-                               *ver = nv_ro08(bios, perf + 1);
-                               *cnt = nv_ro08(bios, perf + 2);
-                               *len = nv_ro08(bios, perf + 3);
-                               *snr = 0;
-                               *ssz = 0;
-                               return perf;
-                       }
-               }
-       }
-
-       return 0x0000;
-}
-
-u16
-nvbios_perf_entry(struct nouveau_bios *bios, int idx,
-                 u8 *ver, u8 *hdr, u8 *cnt, u8 *len)
-{
-       u8  snr, ssz;
-       u16 perf = nvbios_perf_table(bios, ver, hdr, cnt, len, &snr, &ssz);
-       if (perf && idx < *cnt) {
-               perf = perf + *hdr + (idx * (*len + (snr * ssz)));
-               *hdr = *len;
-               *cnt = snr;
-               *len = ssz;
-               return perf;
-       }
-       return 0x0000;
-}
-
-u16
-nvbios_perfEp(struct nouveau_bios *bios, int idx,
-             u8 *ver, u8 *hdr, u8 *cnt, u8 *len,
-             struct nvbios_perfE *info)
-{
-       u16 perf = nvbios_perf_entry(bios, idx, ver, hdr, cnt, len);
-       memset(info, 0x00, sizeof(*info));
-       info->pstate = nv_ro08(bios, perf + 0x00);
-       switch (!!perf * *ver) {
-       case 0x12:
-       case 0x13:
-       case 0x14:
-               info->core     = nv_ro32(bios, perf + 0x01) * 10;
-               info->memory   = nv_ro32(bios, perf + 0x05) * 20;
-               info->fanspeed = nv_ro08(bios, perf + 0x37);
-               if (*hdr > 0x38)
-                       info->voltage = nv_ro08(bios, perf + 0x38);
-               break;
-       case 0x21:
-       case 0x23:
-       case 0x24:
-               info->fanspeed = nv_ro08(bios, perf + 0x04);
-               info->voltage  = nv_ro08(bios, perf + 0x05);
-               info->shader   = nv_ro16(bios, perf + 0x06) * 1000;
-               info->core     = info->shader + (signed char)
-                                nv_ro08(bios, perf + 0x08) * 1000;
-               switch (nv_device(bios)->chipset) {
-               case 0x49:
-               case 0x4b:
-                       info->memory = nv_ro16(bios, perf + 0x0b) * 1000;
-                       break;
-               default:
-                       info->memory = nv_ro16(bios, perf + 0x0b) * 2000;
-                       break;
-               }
-               break;
-       case 0x25:
-               info->fanspeed = nv_ro08(bios, perf + 0x04);
-               info->voltage  = nv_ro08(bios, perf + 0x05);
-               info->core     = nv_ro16(bios, perf + 0x06) * 1000;
-               info->shader   = nv_ro16(bios, perf + 0x0a) * 1000;
-               info->memory   = nv_ro16(bios, perf + 0x0c) * 1000;
-               break;
-       case 0x30:
-               info->script   = nv_ro16(bios, perf + 0x02);
-       case 0x35:
-               info->fanspeed = nv_ro08(bios, perf + 0x06);
-               info->voltage  = nv_ro08(bios, perf + 0x07);
-               info->core     = nv_ro16(bios, perf + 0x08) * 1000;
-               info->shader   = nv_ro16(bios, perf + 0x0a) * 1000;
-               info->memory   = nv_ro16(bios, perf + 0x0c) * 1000;
-               info->vdec     = nv_ro16(bios, perf + 0x10) * 1000;
-               info->disp     = nv_ro16(bios, perf + 0x14) * 1000;
-               break;
-       case 0x40:
-               info->voltage  = nv_ro08(bios, perf + 0x02);
-               break;
-       default:
-               return 0x0000;
-       }
-       return perf;
-}
-
-u32
-nvbios_perfSe(struct nouveau_bios *bios, u32 perfE, int idx,
-             u8 *ver, u8 *hdr, u8 cnt, u8 len)
-{
-       u32 data = 0x00000000;
-       if (idx < cnt) {
-               data = perfE + *hdr + (idx * len);
-               *hdr = len;
-       }
-       return data;
-}
-
-u32
-nvbios_perfSp(struct nouveau_bios *bios, u32 perfE, int idx,
-             u8 *ver, u8 *hdr, u8 cnt, u8 len,
-             struct nvbios_perfS *info)
-{
-       u32 data = nvbios_perfSe(bios, perfE, idx, ver, hdr, cnt, len);
-       memset(info, 0x00, sizeof(*info));
-       switch (!!data * *ver) {
-       case 0x40:
-               info->v40.freq = (nv_ro16(bios, data + 0x00) & 0x3fff) * 1000;
-               break;
-       default:
-               break;
-       }
-       return data;
-}
-
-int
-nvbios_perf_fan_parse(struct nouveau_bios *bios,
-                     struct nvbios_perf_fan *fan)
-{
-       u8  ver, hdr, cnt, len, snr, ssz;
-       u16 perf = nvbios_perf_table(bios, &ver, &hdr, &cnt, &len, &snr, &ssz);
-       if (!perf)
-               return -ENODEV;
-
-       if (ver >= 0x20 && ver < 0x40 && hdr > 6)
-               fan->pwm_divisor = nv_ro16(bios, perf + 6);
-       else
-               fan->pwm_divisor = 0;
-
-       return 0;
-}
diff --git a/drivers/gpu/drm/nouveau/core/subdev/bios/pll.c b/drivers/gpu/drm/nouveau/core/subdev/bios/pll.c
deleted file mode 100644 (file)
index 1f76de5..0000000
+++ /dev/null
@@ -1,416 +0,0 @@
-/*
- * 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.
- */
-
-#include <subdev/vga.h>
-#include <subdev/bios.h>
-#include <subdev/bios/bit.h>
-#include <subdev/bios/bmp.h>
-#include <subdev/bios/pll.h>
-
-struct pll_mapping {
-       u8  type;
-       u32 reg;
-};
-
-static struct pll_mapping
-nv04_pll_mapping[] = {
-       { PLL_CORE  , 0x680500 },
-       { PLL_MEMORY, 0x680504 },
-       { PLL_VPLL0 , 0x680508 },
-       { PLL_VPLL1 , 0x680520 },
-       {}
-};
-
-static struct pll_mapping
-nv40_pll_mapping[] = {
-       { PLL_CORE  , 0x004000 },
-       { PLL_MEMORY, 0x004020 },
-       { PLL_VPLL0 , 0x680508 },
-       { PLL_VPLL1 , 0x680520 },
-       {}
-};
-
-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_VDEC  , 0x004030 },
-       { PLL_UNK41 , 0x00e818 },
-       { PLL_VPLL0 , 0x614100 },
-       { PLL_VPLL1 , 0x614900 },
-       {}
-};
-
-static u16
-pll_limits_table(struct nouveau_bios *bios, u8 *ver, u8 *hdr, u8 *cnt, u8 *len)
-{
-       struct bit_entry bit_C;
-
-       if (!bit_entry(bios, 'C', &bit_C) && bit_C.length >= 10) {
-               u16 data = nv_ro16(bios, bit_C.offset + 8);
-               if (data) {
-                       *ver = nv_ro08(bios, data + 0);
-                       *hdr = nv_ro08(bios, data + 1);
-                       *len = nv_ro08(bios, data + 2);
-                       *cnt = nv_ro08(bios, data + 3);
-                       return data;
-               }
-       }
-
-       if (bmp_version(bios) >= 0x0524) {
-               u16 data = nv_ro16(bios, bios->bmp_offset + 142);
-               if (data) {
-                       *ver = nv_ro08(bios, data + 0);
-                       *hdr = 1;
-                       *cnt = 1;
-                       *len = 0x18;
-                       return data;
-               }
-       }
-
-       *ver = 0x00;
-       return 0x0000;
-}
-
-static struct pll_mapping *
-pll_map(struct nouveau_bios *bios)
-{
-       switch (nv_device(bios)->card_type) {
-       case NV_04:
-       case NV_10:
-       case NV_11:
-       case NV_20:
-       case NV_30:
-               return nv04_pll_mapping;
-               break;
-       case NV_40:
-               return nv40_pll_mapping;
-       case NV_50:
-               if (nv_device(bios)->chipset == 0x50)
-                       return nv50_pll_mapping;
-               else
-               if (nv_device(bios)->chipset <  0xa3 ||
-                   nv_device(bios)->chipset == 0xaa ||
-                   nv_device(bios)->chipset == 0xac)
-                       return nv84_pll_mapping;
-       default:
-               return NULL;
-       }
-}
-
-static u16
-pll_map_reg(struct nouveau_bios *bios, u32 reg, u32 *type, u8 *ver, u8 *len)
-{
-       struct pll_mapping *map;
-       u8  hdr, cnt;
-       u16 data;
-
-       data = pll_limits_table(bios, ver, &hdr, &cnt, len);
-       if (data && *ver >= 0x30) {
-               data += hdr;
-               while (cnt--) {
-                       if (nv_ro32(bios, data + 3) == reg) {
-                               *type = nv_ro08(bios, data + 0);
-                               return data;
-                       }
-                       data += *len;
-               }
-               return 0x0000;
-       }
-
-       map = pll_map(bios);
-       while (map->reg) {
-               if (map->reg == reg && *ver >= 0x20) {
-                       u16 addr = (data += hdr);
-                       *type = map->type;
-                       while (cnt--) {
-                               if (nv_ro32(bios, data) == map->reg)
-                                       return data;
-                               data += *len;
-                       }
-                       return addr;
-               } else
-               if (map->reg == reg) {
-                       *type = map->type;
-                       return data + 1;
-               }
-               map++;
-       }
-
-       return 0x0000;
-}
-
-static u16
-pll_map_type(struct nouveau_bios *bios, u8 type, u32 *reg, u8 *ver, u8 *len)
-{
-       struct pll_mapping *map;
-       u8  hdr, cnt;
-       u16 data;
-
-       data = pll_limits_table(bios, ver, &hdr, &cnt, len);
-       if (data && *ver >= 0x30) {
-               data += hdr;
-               while (cnt--) {
-                       if (nv_ro08(bios, data + 0) == type) {
-                               *reg = nv_ro32(bios, data + 3);
-                               return data;
-                       }
-                       data += *len;
-               }
-               return 0x0000;
-       }
-
-       map = pll_map(bios);
-       while (map->reg) {
-               if (map->type == type && *ver >= 0x20) {
-                       u16 addr = (data += hdr);
-                       *reg = map->reg;
-                       while (cnt--) {
-                               if (nv_ro32(bios, data) == map->reg)
-                                       return data;
-                               data += *len;
-                       }
-                       return addr;
-               } else
-               if (map->type == type) {
-                       *reg = map->reg;
-                       return data + 1;
-               }
-               map++;
-       }
-
-       return 0x0000;
-}
-
-int
-nvbios_pll_parse(struct nouveau_bios *bios, u32 type, struct nvbios_pll *info)
-{
-       u8  ver, len;
-       u32 reg = type;
-       u16 data;
-
-       if (type > PLL_MAX) {
-               reg  = type;
-               data = pll_map_reg(bios, reg, &type, &ver, &len);
-       } else {
-               data = pll_map_type(bios, type, &reg, &ver, &len);
-       }
-
-       if (ver && !data)
-               return -ENOENT;
-
-       memset(info, 0, sizeof(*info));
-       info->type = type;
-       info->reg = reg;
-
-       switch (ver) {
-       case 0x00:
-               break;
-       case 0x10:
-       case 0x11:
-               info->vco1.min_freq = nv_ro32(bios, data + 0);
-               info->vco1.max_freq = nv_ro32(bios, data + 4);
-               info->vco2.min_freq = nv_ro32(bios, data + 8);
-               info->vco2.max_freq = nv_ro32(bios, data + 12);
-               info->vco1.min_inputfreq = nv_ro32(bios, data + 16);
-               info->vco2.min_inputfreq = nv_ro32(bios, data + 20);
-               info->vco1.max_inputfreq = INT_MAX;
-               info->vco2.max_inputfreq = INT_MAX;
-
-               info->max_p = 0x7;
-               info->max_p_usable = 0x6;
-
-               /* these values taken from nv30/31/36 */
-               switch (bios->version.chip) {
-               case 0x36:
-                       info->vco1.min_n = 0x5;
-                       break;
-               default:
-                       info->vco1.min_n = 0x1;
-                       break;
-               }
-               info->vco1.max_n = 0xff;
-               info->vco1.min_m = 0x1;
-               info->vco1.max_m = 0xd;
-
-               /*
-                * 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
-                */
-               info->vco2.min_n = 0x4;
-               switch (bios->version.chip) {
-               case 0x30:
-               case 0x35:
-                       info->vco2.max_n = 0x1f;
-                       break;
-               default:
-                       info->vco2.max_n = 0x28;
-                       break;
-               }
-               info->vco2.min_m = 0x1;
-               info->vco2.max_m = 0x4;
-               break;
-       case 0x20:
-       case 0x21:
-               info->vco1.min_freq = nv_ro16(bios, data + 4) * 1000;
-               info->vco1.max_freq = nv_ro16(bios, data + 6) * 1000;
-               info->vco2.min_freq = nv_ro16(bios, data + 8) * 1000;
-               info->vco2.max_freq = nv_ro16(bios, data + 10) * 1000;
-               info->vco1.min_inputfreq = nv_ro16(bios, data + 12) * 1000;
-               info->vco2.min_inputfreq = nv_ro16(bios, data + 14) * 1000;
-               info->vco1.max_inputfreq = nv_ro16(bios, data + 16) * 1000;
-               info->vco2.max_inputfreq = nv_ro16(bios, data + 18) * 1000;
-               info->vco1.min_n = nv_ro08(bios, data + 20);
-               info->vco1.max_n = nv_ro08(bios, data + 21);
-               info->vco1.min_m = nv_ro08(bios, data + 22);
-               info->vco1.max_m = nv_ro08(bios, data + 23);
-               info->vco2.min_n = nv_ro08(bios, data + 24);
-               info->vco2.max_n = nv_ro08(bios, data + 25);
-               info->vco2.min_m = nv_ro08(bios, data + 26);
-               info->vco2.max_m = nv_ro08(bios, data + 27);
-
-               info->max_p = nv_ro08(bios, data + 29);
-               info->max_p_usable = info->max_p;
-               if (bios->version.chip < 0x60)
-                       info->max_p_usable = 0x6;
-               info->bias_p = nv_ro08(bios, data + 30);
-
-               if (len > 0x22)
-                       info->refclk = nv_ro32(bios, data + 31);
-               break;
-       case 0x30:
-               data = nv_ro16(bios, data + 1);
-
-               info->vco1.min_freq = nv_ro16(bios, data + 0) * 1000;
-               info->vco1.max_freq = nv_ro16(bios, data + 2) * 1000;
-               info->vco2.min_freq = nv_ro16(bios, data + 4) * 1000;
-               info->vco2.max_freq = nv_ro16(bios, data + 6) * 1000;
-               info->vco1.min_inputfreq = nv_ro16(bios, data + 8) * 1000;
-               info->vco2.min_inputfreq = nv_ro16(bios, data + 10) * 1000;
-               info->vco1.max_inputfreq = nv_ro16(bios, data + 12) * 1000;
-               info->vco2.max_inputfreq = nv_ro16(bios, data + 14) * 1000;
-               info->vco1.min_n = nv_ro08(bios, data + 16);
-               info->vco1.max_n = nv_ro08(bios, data + 17);
-               info->vco1.min_m = nv_ro08(bios, data + 18);
-               info->vco1.max_m = nv_ro08(bios, data + 19);
-               info->vco2.min_n = nv_ro08(bios, data + 20);
-               info->vco2.max_n = nv_ro08(bios, data + 21);
-               info->vco2.min_m = nv_ro08(bios, data + 22);
-               info->vco2.max_m = nv_ro08(bios, data + 23);
-               info->max_p_usable = info->max_p = nv_ro08(bios, data + 25);
-               info->bias_p = nv_ro08(bios, data + 27);
-               info->refclk = nv_ro32(bios, data + 28);
-               break;
-       case 0x40:
-               info->refclk = nv_ro16(bios, data + 9) * 1000;
-               data = nv_ro16(bios, data + 1);
-
-               info->vco1.min_freq = nv_ro16(bios, data + 0) * 1000;
-               info->vco1.max_freq = nv_ro16(bios, data + 2) * 1000;
-               info->vco1.min_inputfreq = nv_ro16(bios, data + 4) * 1000;
-               info->vco1.max_inputfreq = nv_ro16(bios, data + 6) * 1000;
-               info->vco1.min_m = nv_ro08(bios, data + 8);
-               info->vco1.max_m = nv_ro08(bios, data + 9);
-               info->vco1.min_n = nv_ro08(bios, data + 10);
-               info->vco1.max_n = nv_ro08(bios, data + 11);
-               info->min_p = nv_ro08(bios, data + 12);
-               info->max_p = nv_ro08(bios, data + 13);
-               break;
-       default:
-               nv_error(bios, "unknown pll limits version 0x%02x\n", ver);
-               return -EINVAL;
-       }
-
-       if (!info->refclk) {
-               info->refclk = nv_device(bios)->crystal;
-               if (bios->version.chip == 0x51) {
-                       u32 sel_clk = nv_rd32(bios, 0x680524);
-                       if ((info->reg == 0x680508 && sel_clk & 0x20) ||
-                           (info->reg == 0x680520 && sel_clk & 0x80)) {
-                               if (nv_rdvgac(bios, 0, 0x27) < 0xa3)
-                                       info->refclk = 200000;
-                               else
-                                       info->refclk = 25000;
-                       }
-               }
-       }
-
-       /*
-        * 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 (!info->vco1.max_freq) {
-               info->vco1.max_freq = nv_ro32(bios, bios->bmp_offset + 67);
-               info->vco1.min_freq = nv_ro32(bios, bios->bmp_offset + 71);
-               if (bmp_version(bios) < 0x0506) {
-                       info->vco1.max_freq = 256000;
-                       info->vco1.min_freq = 128000;
-               }
-
-               info->vco1.min_inputfreq = 0;
-               info->vco1.max_inputfreq = INT_MAX;
-               info->vco1.min_n = 0x1;
-               info->vco1.max_n = 0xff;
-               info->vco1.min_m = 0x1;
-
-               if (nv_device(bios)->crystal == 13500) {
-                       /* nv05 does this, nv11 doesn't, nv10 unknown */
-                       if (bios->version.chip < 0x11)
-                               info->vco1.min_m = 0x7;
-                       info->vco1.max_m = 0xd;
-               } else {
-                       if (bios->version.chip < 0x11)
-                               info->vco1.min_m = 0x8;
-                       info->vco1.max_m = 0xe;
-               }
-
-               if (bios->version.chip <  0x17 ||
-                   bios->version.chip == 0x1a ||
-                   bios->version.chip == 0x20)
-                       info->max_p = 4;
-               else
-                       info->max_p = 5;
-               info->max_p_usable = info->max_p;
-       }
-
-       return 0;
-}
diff --git a/drivers/gpu/drm/nouveau/core/subdev/bios/pmu.c b/drivers/gpu/drm/nouveau/core/subdev/bios/pmu.c
deleted file mode 100644 (file)
index 66c56ba..0000000
+++ /dev/null
@@ -1,135 +0,0 @@
-/*
- * Copyright 2014 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 <bskeggs@redhat.com>
- */
-
-#include <subdev/bios.h>
-#include <subdev/bios/bit.h>
-#include <subdev/bios/image.h>
-#include <subdev/bios/pmu.h>
-
-static u32
-weirdo_pointer(struct nouveau_bios *bios, u32 data)
-{
-       struct nvbios_image image;
-       int idx = 0;
-       if (nvbios_image(bios, idx++, &image)) {
-               data -= image.size;
-               while (nvbios_image(bios, idx++, &image)) {
-                       if (image.type == 0xe0)
-                               return image.base + data;
-               }
-       }
-       return 0;
-}
-
-u32
-nvbios_pmuTe(struct nouveau_bios *bios, u8 *ver, u8 *hdr, u8 *cnt, u8 *len)
-{
-       struct bit_entry bit_p;
-       u32 data = 0;
-
-       if (!bit_entry(bios, 'p', &bit_p)) {
-               if (bit_p.version == 2 && bit_p.length >= 4)
-                       data = nv_ro32(bios, bit_p.offset + 0x00);
-               if ((data = weirdo_pointer(bios, data))) {
-                       *ver = nv_ro08(bios, data + 0x00); /* maybe? */
-                       *hdr = nv_ro08(bios, data + 0x01);
-                       *len = nv_ro08(bios, data + 0x02);
-                       *cnt = nv_ro08(bios, data + 0x03);
-               }
-       }
-
-       return data;
-}
-
-u32
-nvbios_pmuTp(struct nouveau_bios *bios, u8 *ver, u8 *hdr, u8 *cnt, u8 *len,
-            struct nvbios_pmuT *info)
-{
-       u32 data = nvbios_pmuTe(bios, ver, hdr, cnt, len);
-       memset(info, 0x00, sizeof(*info));
-       switch (!!data * *ver) {
-       default:
-               break;
-       }
-       return data;
-}
-
-u32
-nvbios_pmuEe(struct nouveau_bios *bios, int idx, u8 *ver, u8 *hdr)
-{
-       u8  cnt, len;
-       u32 data = nvbios_pmuTe(bios, ver, hdr, &cnt, &len);
-       if (data && idx < cnt) {
-               data = data + *hdr + (idx * len);
-               *hdr = len;
-               return data;
-       }
-       return 0;
-}
-
-u32
-nvbios_pmuEp(struct nouveau_bios *bios, int idx, u8 *ver, u8 *hdr,
-            struct nvbios_pmuE *info)
-{
-       u32 data = nvbios_pmuEe(bios, idx, ver, hdr);
-       memset(info, 0x00, sizeof(*info));
-       switch (!!data * *ver) {
-       default:
-               info->type = nv_ro08(bios, data + 0x00);
-               info->data = nv_ro32(bios, data + 0x02);
-               break;
-       }
-       return data;
-}
-
-bool
-nvbios_pmuRm(struct nouveau_bios *bios, u8 type, struct nvbios_pmuR *info)
-{
-       struct nvbios_pmuE pmuE;
-       u8  ver, hdr, idx = 0;
-       u32 data;
-       memset(info, 0x00, sizeof(*info));
-       while ((data = nvbios_pmuEp(bios, idx++, &ver, &hdr, &pmuE))) {
-               if ( pmuE.type == type &&
-                   (data = weirdo_pointer(bios, pmuE.data))) {
-                       info->init_addr_pmu = nv_ro32(bios, data + 0x08);
-                       info->args_addr_pmu = nv_ro32(bios, data + 0x0c);
-                       info->boot_addr     = data + 0x30;
-                       info->boot_addr_pmu = nv_ro32(bios, data + 0x10) +
-                                             nv_ro32(bios, data + 0x18);
-                       info->boot_size     = nv_ro32(bios, data + 0x1c) -
-                                             nv_ro32(bios, data + 0x18);
-                       info->code_addr     = info->boot_addr + info->boot_size;
-                       info->code_addr_pmu = info->boot_addr_pmu +
-                                             info->boot_size;
-                       info->code_size     = nv_ro32(bios, data + 0x20);
-                       info->data_addr     = data + 0x30 +
-                                             nv_ro32(bios, data + 0x24);
-                       info->data_addr_pmu = nv_ro32(bios, data + 0x28);
-                       info->data_size     = nv_ro32(bios, data + 0x2c);
-                       return true;
-               }
-       }
-       return false;
-}
diff --git a/drivers/gpu/drm/nouveau/core/subdev/bios/priv.h b/drivers/gpu/drm/nouveau/core/subdev/bios/priv.h
deleted file mode 100644 (file)
index 187d225..0000000
+++ /dev/null
@@ -1,25 +0,0 @@
-#ifndef __NVKM_BIOS_PRIV_H__
-#define __NVKM_BIOS_PRIV_H__
-
-#include <subdev/bios.h>
-
-struct nvbios_source {
-       const char *name;
-       void *(*init)(struct nouveau_bios *, const char *);
-       void  (*fini)(void *);
-       u32   (*read)(void *, u32 offset, u32 length, struct nouveau_bios *);
-       bool rw;
-};
-
-int nvbios_extend(struct nouveau_bios *, u32 length);
-int nvbios_shadow(struct nouveau_bios *);
-
-extern const struct nvbios_source nvbios_rom;
-extern const struct nvbios_source nvbios_ramin;
-extern const struct nvbios_source nvbios_acpi_fast;
-extern const struct nvbios_source nvbios_acpi_slow;
-extern const struct nvbios_source nvbios_pcirom;
-extern const struct nvbios_source nvbios_platform;
-extern const struct nvbios_source nvbios_of;
-
-#endif
diff --git a/drivers/gpu/drm/nouveau/core/subdev/bios/ramcfg.c b/drivers/gpu/drm/nouveau/core/subdev/bios/ramcfg.c
deleted file mode 100644 (file)
index 1623c8d..0000000
+++ /dev/null
@@ -1,79 +0,0 @@
-/*
- * Copyright 2013 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 <bskeggs@redhat.com>
- */
-
-#include <subdev/bios.h>
-#include <subdev/bios/bit.h>
-#include <subdev/bios/ramcfg.h>
-#include <subdev/bios/M0203.h>
-
-static u8
-nvbios_ramcfg_strap(struct nouveau_subdev *subdev)
-{
-       return (nv_rd32(subdev, 0x101000) & 0x0000003c) >> 2;
-}
-
-u8
-nvbios_ramcfg_count(struct nouveau_bios *bios)
-{
-       struct bit_entry bit_M;
-
-       if (!bit_entry(bios, 'M', &bit_M)) {
-               if (bit_M.version == 1 && bit_M.length >= 5)
-                       return nv_ro08(bios, bit_M.offset + 2);
-               if (bit_M.version == 2 && bit_M.length >= 3)
-                       return nv_ro08(bios, bit_M.offset + 0);
-       }
-
-       return 0x00;
-}
-
-u8
-nvbios_ramcfg_index(struct nouveau_subdev *subdev)
-{
-       struct nouveau_bios *bios = nouveau_bios(subdev);
-       u8 strap = nvbios_ramcfg_strap(subdev);
-       u32 xlat = 0x00000000;
-       struct bit_entry bit_M;
-       struct nvbios_M0203E M0203E;
-       u8 ver, hdr;
-
-       if (!bit_entry(bios, 'M', &bit_M)) {
-               if (bit_M.version == 1 && bit_M.length >= 5)
-                       xlat = nv_ro16(bios, bit_M.offset + 3);
-               if (bit_M.version == 2 && bit_M.length >= 3) {
-                       /*XXX: is M ever shorter than this?
-                        *     if not - what is xlat used for now?
-                        *     also - sigh..
-                        */
-                       if (bit_M.length >= 7 &&
-                           nvbios_M0203Em(bios, strap, &ver, &hdr, &M0203E))
-                               return M0203E.group;
-                       xlat = nv_ro16(bios, bit_M.offset + 1);
-               }
-       }
-
-       if (xlat)
-               strap = nv_ro08(bios, xlat + strap);
-       return strap;
-}
diff --git a/drivers/gpu/drm/nouveau/core/subdev/bios/rammap.c b/drivers/gpu/drm/nouveau/core/subdev/bios/rammap.c
deleted file mode 100644 (file)
index c568522..0000000
+++ /dev/null
@@ -1,216 +0,0 @@
-/*
- * Copyright 2013 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 <subdev/bios.h>
-#include <subdev/bios/bit.h>
-#include <subdev/bios/ramcfg.h>
-#include <subdev/bios/rammap.h>
-
-u32
-nvbios_rammapTe(struct nouveau_bios *bios, u8 *ver, u8 *hdr,
-               u8 *cnt, u8 *len, u8 *snr, u8 *ssz)
-{
-       struct bit_entry bit_P;
-       u16 rammap = 0x0000;
-
-       if (!bit_entry(bios, 'P', &bit_P)) {
-               if (bit_P.version == 2)
-                       rammap = nv_ro16(bios, bit_P.offset + 4);
-
-               if (rammap) {
-                       *ver = nv_ro08(bios, rammap + 0);
-                       switch (*ver) {
-                       case 0x10:
-                       case 0x11:
-                               *hdr = nv_ro08(bios, rammap + 1);
-                               *cnt = nv_ro08(bios, rammap + 5);
-                               *len = nv_ro08(bios, rammap + 2);
-                               *snr = nv_ro08(bios, rammap + 4);
-                               *ssz = nv_ro08(bios, rammap + 3);
-                               return rammap;
-                       default:
-                               break;
-                       }
-               }
-       }
-
-       return 0x0000;
-}
-
-u32
-nvbios_rammapEe(struct nouveau_bios *bios, int idx,
-               u8 *ver, u8 *hdr, u8 *cnt, u8 *len)
-{
-       u8  snr, ssz;
-       u16 rammap = nvbios_rammapTe(bios, ver, hdr, cnt, len, &snr, &ssz);
-       if (rammap && idx < *cnt) {
-               rammap = rammap + *hdr + (idx * (*len + (snr * ssz)));
-               *hdr = *len;
-               *cnt = snr;
-               *len = ssz;
-               return rammap;
-       }
-       return 0x0000;
-}
-
-u32
-nvbios_rammapEp(struct nouveau_bios *bios, int idx,
-               u8 *ver, u8 *hdr, u8 *cnt, u8 *len,
-               struct nvbios_ramcfg *p)
-{
-       u32 data = nvbios_rammapEe(bios, idx, ver, hdr, cnt, len), temp;
-       memset(p, 0x00, sizeof(*p));
-       p->rammap_ver = *ver;
-       p->rammap_hdr = *hdr;
-       switch (!!data * *ver) {
-       case 0x10:
-               p->rammap_min      =  nv_ro16(bios, data + 0x00);
-               p->rammap_max      =  nv_ro16(bios, data + 0x02);
-               p->rammap_10_04_02 = (nv_ro08(bios, data + 0x04) & 0x02) >> 1;
-               p->rammap_10_04_08 = (nv_ro08(bios, data + 0x04) & 0x08) >> 3;
-               break;
-       case 0x11:
-               p->rammap_min      =  nv_ro16(bios, data + 0x00);
-               p->rammap_max      =  nv_ro16(bios, data + 0x02);
-               p->rammap_11_08_01 = (nv_ro08(bios, data + 0x08) & 0x01) >> 0;
-               p->rammap_11_08_0c = (nv_ro08(bios, data + 0x08) & 0x0c) >> 2;
-               p->rammap_11_08_10 = (nv_ro08(bios, data + 0x08) & 0x10) >> 4;
-               temp = nv_ro32(bios, data + 0x09);
-               p->rammap_11_09_01ff = (temp & 0x000001ff) >> 0;
-               p->rammap_11_0a_03fe = (temp & 0x0003fe00) >> 9;
-               p->rammap_11_0a_0400 = (temp & 0x00040000) >> 18;
-               p->rammap_11_0a_0800 = (temp & 0x00080000) >> 19;
-               p->rammap_11_0b_01f0 = (temp & 0x01f00000) >> 20;
-               p->rammap_11_0b_0200 = (temp & 0x02000000) >> 25;
-               p->rammap_11_0b_0400 = (temp & 0x04000000) >> 26;
-               p->rammap_11_0b_0800 = (temp & 0x08000000) >> 27;
-               p->rammap_11_0d    =  nv_ro08(bios, data + 0x0d);
-               p->rammap_11_0e    =  nv_ro08(bios, data + 0x0e);
-               p->rammap_11_0f    =  nv_ro08(bios, data + 0x0f);
-               p->rammap_11_11_0c = (nv_ro08(bios, data + 0x11) & 0x0c) >> 2;
-               break;
-       default:
-               data = 0;
-               break;
-       }
-       return data;
-}
-
-u32
-nvbios_rammapEm(struct nouveau_bios *bios, u16 mhz,
-               u8 *ver, u8 *hdr, u8 *cnt, u8 *len,
-               struct nvbios_ramcfg *info)
-{
-       int idx = 0;
-       u32 data;
-       while ((data = nvbios_rammapEp(bios, idx++, ver, hdr, cnt, len, info))) {
-               if (mhz >= info->rammap_min && mhz <= info->rammap_max)
-                       break;
-       }
-       return data;
-}
-
-u32
-nvbios_rammapSe(struct nouveau_bios *bios, u32 data,
-               u8 ever, u8 ehdr, u8 ecnt, u8 elen, int idx,
-               u8 *ver, u8 *hdr)
-{
-       if (idx < ecnt) {
-               data = data + ehdr + (idx * elen);
-               *ver = ever;
-               *hdr = elen;
-               return data;
-       }
-       return 0;
-}
-
-u32
-nvbios_rammapSp(struct nouveau_bios *bios, u32 data,
-               u8 ever, u8 ehdr, u8 ecnt, u8 elen, int idx,
-               u8 *ver, u8 *hdr, struct nvbios_ramcfg *p)
-{
-       data = nvbios_rammapSe(bios, data, ever, ehdr, ecnt, elen, idx, ver, hdr);
-       p->ramcfg_ver = *ver;
-       p->ramcfg_hdr = *hdr;
-       switch (!!data * *ver) {
-       case 0x10:
-               p->ramcfg_timing   =  nv_ro08(bios, data + 0x01);
-               p->ramcfg_10_02_01 = (nv_ro08(bios, data + 0x02) & 0x01) >> 0;
-               p->ramcfg_10_02_02 = (nv_ro08(bios, data + 0x02) & 0x02) >> 1;
-               p->ramcfg_10_02_04 = (nv_ro08(bios, data + 0x02) & 0x04) >> 2;
-               p->ramcfg_10_02_08 = (nv_ro08(bios, data + 0x02) & 0x08) >> 3;
-               p->ramcfg_10_02_10 = (nv_ro08(bios, data + 0x02) & 0x10) >> 4;
-               p->ramcfg_10_02_20 = (nv_ro08(bios, data + 0x02) & 0x20) >> 5;
-               p->ramcfg_10_DLLoff = (nv_ro08(bios, data + 0x02) & 0x40) >> 6;
-               p->ramcfg_10_03_0f = (nv_ro08(bios, data + 0x03) & 0x0f) >> 0;
-               p->ramcfg_10_04_01 = (nv_ro08(bios, data + 0x04) & 0x01) >> 0;
-               p->ramcfg_10_05    = (nv_ro08(bios, data + 0x05) & 0xff) >> 0;
-               p->ramcfg_10_06    = (nv_ro08(bios, data + 0x06) & 0xff) >> 0;
-               p->ramcfg_10_07    = (nv_ro08(bios, data + 0x07) & 0xff) >> 0;
-               p->ramcfg_10_08    = (nv_ro08(bios, data + 0x08) & 0xff) >> 0;
-               p->ramcfg_10_09_0f = (nv_ro08(bios, data + 0x09) & 0x0f) >> 0;
-               p->ramcfg_10_09_f0 = (nv_ro08(bios, data + 0x09) & 0xf0) >> 4;
-               break;
-       case 0x11:
-               p->ramcfg_timing   =  nv_ro08(bios, data + 0x00);
-               p->ramcfg_11_01_01 = (nv_ro08(bios, data + 0x01) & 0x01) >> 0;
-               p->ramcfg_11_01_02 = (nv_ro08(bios, data + 0x01) & 0x02) >> 1;
-               p->ramcfg_11_01_04 = (nv_ro08(bios, data + 0x01) & 0x04) >> 2;
-               p->ramcfg_11_01_08 = (nv_ro08(bios, data + 0x01) & 0x08) >> 3;
-               p->ramcfg_11_01_10 = (nv_ro08(bios, data + 0x01) & 0x10) >> 4;
-               p->ramcfg_11_01_20 = (nv_ro08(bios, data + 0x01) & 0x20) >> 5;
-               p->ramcfg_11_01_40 = (nv_ro08(bios, data + 0x01) & 0x40) >> 6;
-               p->ramcfg_11_01_80 = (nv_ro08(bios, data + 0x01) & 0x80) >> 7;
-               p->ramcfg_11_02_03 = (nv_ro08(bios, data + 0x02) & 0x03) >> 0;
-               p->ramcfg_11_02_04 = (nv_ro08(bios, data + 0x02) & 0x04) >> 2;
-               p->ramcfg_11_02_08 = (nv_ro08(bios, data + 0x02) & 0x08) >> 3;
-               p->ramcfg_11_02_10 = (nv_ro08(bios, data + 0x02) & 0x10) >> 4;
-               p->ramcfg_11_02_40 = (nv_ro08(bios, data + 0x02) & 0x40) >> 6;
-               p->ramcfg_11_02_80 = (nv_ro08(bios, data + 0x02) & 0x80) >> 7;
-               p->ramcfg_11_03_0f = (nv_ro08(bios, data + 0x03) & 0x0f) >> 0;
-               p->ramcfg_11_03_30 = (nv_ro08(bios, data + 0x03) & 0x30) >> 4;
-               p->ramcfg_11_03_c0 = (nv_ro08(bios, data + 0x03) & 0xc0) >> 6;
-               p->ramcfg_11_03_f0 = (nv_ro08(bios, data + 0x03) & 0xf0) >> 4;
-               p->ramcfg_11_04    = (nv_ro08(bios, data + 0x04) & 0xff) >> 0;
-               p->ramcfg_11_06    = (nv_ro08(bios, data + 0x06) & 0xff) >> 0;
-               p->ramcfg_11_07_02 = (nv_ro08(bios, data + 0x07) & 0x02) >> 1;
-               p->ramcfg_11_07_04 = (nv_ro08(bios, data + 0x07) & 0x04) >> 2;
-               p->ramcfg_11_07_08 = (nv_ro08(bios, data + 0x07) & 0x08) >> 3;
-               p->ramcfg_11_07_10 = (nv_ro08(bios, data + 0x07) & 0x10) >> 4;
-               p->ramcfg_11_07_40 = (nv_ro08(bios, data + 0x07) & 0x40) >> 6;
-               p->ramcfg_11_07_80 = (nv_ro08(bios, data + 0x07) & 0x80) >> 7;
-               p->ramcfg_11_08_01 = (nv_ro08(bios, data + 0x08) & 0x01) >> 0;
-               p->ramcfg_11_08_02 = (nv_ro08(bios, data + 0x08) & 0x02) >> 1;
-               p->ramcfg_11_08_04 = (nv_ro08(bios, data + 0x08) & 0x04) >> 2;
-               p->ramcfg_11_08_08 = (nv_ro08(bios, data + 0x08) & 0x08) >> 3;
-               p->ramcfg_11_08_10 = (nv_ro08(bios, data + 0x08) & 0x10) >> 4;
-               p->ramcfg_11_08_20 = (nv_ro08(bios, data + 0x08) & 0x20) >> 5;
-               p->ramcfg_11_09    = (nv_ro08(bios, data + 0x09) & 0xff) >> 0;
-               break;
-       default:
-               data = 0;
-               break;
-       }
-       return data;
-}
diff --git a/drivers/gpu/drm/nouveau/core/subdev/bios/shadow.c b/drivers/gpu/drm/nouveau/core/subdev/bios/shadow.c
deleted file mode 100644 (file)
index bb9e001..0000000
+++ /dev/null
@@ -1,270 +0,0 @@
-/*
- * Copyright 2014 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 <bskeggs@redhat.com>
- */
-
-#include "priv.h"
-#include <core/option.h>
-#include <subdev/bios/image.h>
-
-struct shadow {
-       struct nouveau_oclass base;
-       u32 skip;
-       const struct nvbios_source *func;
-       void *data;
-       u32 size;
-       int score;
-};
-
-static bool
-shadow_fetch(struct nouveau_bios *bios, u32 upto)
-{
-       struct shadow *mthd = (void *)nv_object(bios)->oclass;
-       const u32 limit = (upto + 3) & ~3;
-       const u32 start = bios->size;
-       void *data = mthd->data;
-       if (nvbios_extend(bios, limit) > 0) {
-               u32 read = mthd->func->read(data, start, limit - start, bios);
-               bios->size = start + read;
-       }
-       return bios->size >= limit;
-}
-
-static u8
-shadow_rd08(struct nouveau_object *object, u64 addr)
-{
-       struct nouveau_bios *bios = (void *)object;
-       if (shadow_fetch(bios, addr + 1))
-               return bios->data[addr];
-       return 0x00;
-}
-
-static u16
-shadow_rd16(struct nouveau_object *object, u64 addr)
-{
-       struct nouveau_bios *bios = (void *)object;
-       if (shadow_fetch(bios, addr + 2))
-               return get_unaligned_le16(&bios->data[addr]);
-       return 0x0000;
-}
-
-static u32
-shadow_rd32(struct nouveau_object *object, u64 addr)
-{
-       struct nouveau_bios *bios = (void *)object;
-       if (shadow_fetch(bios, addr + 4))
-               return get_unaligned_le32(&bios->data[addr]);
-       return 0x00000000;
-}
-
-static struct nouveau_oclass
-shadow_class = {
-       .handle = NV_SUBDEV(VBIOS, 0x00),
-       .ofuncs = &(struct nouveau_ofuncs) {
-               .rd08 = shadow_rd08,
-               .rd16 = shadow_rd16,
-               .rd32 = shadow_rd32,
-       },
-};
-
-static int
-shadow_image(struct nouveau_bios *bios, int idx, struct shadow *mthd)
-{
-       struct nvbios_image image;
-       int score = 1;
-
-       if (!nvbios_image(bios, idx, &image)) {
-               nv_debug(bios, "image %d invalid\n", idx);
-               return 0;
-       }
-       nv_debug(bios, "%08x: type %02x, %d bytes\n",
-                image.base, image.type, image.size);
-
-       if (!shadow_fetch(bios, image.size)) {
-               nv_debug(bios, "%08x: fetch failed\n", image.base);
-               return 0;
-       }
-
-       switch (image.type) {
-       case 0x00:
-               if (nvbios_checksum(&bios->data[image.base], image.size)) {
-                       nv_debug(bios, "%08x: checksum failed\n", image.base);
-                       if (mthd->func->rw)
-                               score += 1;
-                       score += 1;
-               } else {
-                       score += 3;
-               }
-               break;
-       default:
-               score += 3;
-               break;
-       }
-
-       if (!image.last)
-               score += shadow_image(bios, idx + 1, mthd);
-       return score;
-}
-
-static int
-shadow_score(struct nouveau_bios *bios, struct shadow *mthd)
-{
-       struct nouveau_oclass *oclass = nv_object(bios)->oclass;
-       int score;
-       nv_object(bios)->oclass = &mthd->base;
-       score = shadow_image(bios, 0, mthd);
-       nv_object(bios)->oclass = oclass;
-       return score;
-
-}
-
-static int
-shadow_method(struct nouveau_bios *bios, struct shadow *mthd, const char *name)
-{
-       const struct nvbios_source *func = mthd->func;
-       if (func->name) {
-               nv_debug(bios, "trying %s...\n", name ? name : func->name);
-               if (func->init) {
-                       mthd->data = func->init(bios, name);
-                       if (IS_ERR(mthd->data)) {
-                               mthd->data = NULL;
-                               return 0;
-                       }
-               }
-               mthd->score = shadow_score(bios, mthd);
-               if (func->fini)
-                       func->fini(mthd->data);
-               nv_debug(bios, "scored %d\n", mthd->score);
-               mthd->data = bios->data;
-               mthd->size = bios->size;
-               bios->data  = NULL;
-               bios->size  = 0;
-       }
-       return mthd->score;
-}
-
-static u32
-shadow_fw_read(void *data, u32 offset, u32 length, struct nouveau_bios *bios)
-{
-       const struct firmware *fw = data;
-       if (offset + length <= fw->size) {
-               memcpy(bios->data + offset, fw->data + offset, length);
-               return length;
-       }
-       return 0;
-}
-
-static void *
-shadow_fw_init(struct nouveau_bios *bios, const char *name)
-{
-       struct device *dev = &nv_device(bios)->pdev->dev;
-       const struct firmware *fw;
-       int ret = request_firmware(&fw, name, dev);
-       if (ret)
-               return ERR_PTR(-ENOENT);
-       return (void *)fw;
-}
-
-static const struct nvbios_source
-shadow_fw = {
-       .name = "firmware",
-       .init = shadow_fw_init,
-       .fini = (void(*)(void *))release_firmware,
-       .read = shadow_fw_read,
-       .rw = false,
-};
-
-int
-nvbios_shadow(struct nouveau_bios *bios)
-{
-       struct shadow mthds[] = {
-               { shadow_class, 0, &nvbios_of },
-               { shadow_class, 0, &nvbios_ramin },
-               { shadow_class, 0, &nvbios_rom },
-               { shadow_class, 0, &nvbios_acpi_fast },
-               { shadow_class, 4, &nvbios_acpi_slow },
-               { shadow_class, 1, &nvbios_pcirom },
-               { shadow_class, 1, &nvbios_platform },
-               { shadow_class }
-       }, *mthd = mthds, *best = NULL;
-       const char *optarg;
-       char *source;
-       int optlen;
-
-       /* handle user-specified bios source */
-       optarg = nouveau_stropt(nv_device(bios)->cfgopt, "NvBios", &optlen);
-       source = optarg ? kstrndup(optarg, optlen, GFP_KERNEL) : NULL;
-       if (source) {
-               /* try to match one of the built-in methods */
-               for (mthd = mthds; mthd->func; mthd++) {
-                       if (mthd->func->name &&
-                           !strcasecmp(source, mthd->func->name)) {
-                               best = mthd;
-                               if (shadow_method(bios, mthd, NULL))
-                                       break;
-                       }
-               }
-
-               /* otherwise, attempt to load as firmware */
-               if (!best && (best = mthd)) {
-                       mthd->func = &shadow_fw;
-                       shadow_method(bios, mthd, source);
-                       mthd->func = NULL;
-               }
-
-               if (!best->score) {
-                       nv_error(bios, "%s invalid\n", source);
-                       kfree(source);
-                       source = NULL;
-               }
-       }
-
-       /* scan all potential bios sources, looking for best image */
-       if (!best || !best->score) {
-               for (mthd = mthds, best = mthd; mthd->func; mthd++) {
-                       if (!mthd->skip || best->score < mthd->skip) {
-                               if (shadow_method(bios, mthd, NULL)) {
-                                       if (mthd->score > best->score)
-                                               best = mthd;
-                               }
-                       }
-               }
-       }
-
-       /* cleanup the ones we didn't use */
-       for (mthd = mthds; mthd->func; mthd++) {
-               if (mthd != best)
-                       kfree(mthd->data);
-       }
-
-       if (!best->score) {
-               nv_fatal(bios, "unable to locate usable image\n");
-               return -EINVAL;
-       }
-
-       nv_info(bios, "using image from %s\n", best->func ?
-               best->func->name : source);
-       bios->data = best->data;
-       bios->size = best->size;
-       kfree(source);
-       return 0;
-}
diff --git a/drivers/gpu/drm/nouveau/core/subdev/bios/shadowacpi.c b/drivers/gpu/drm/nouveau/core/subdev/bios/shadowacpi.c
deleted file mode 100644 (file)
index bc130c1..0000000
+++ /dev/null
@@ -1,111 +0,0 @@
-/*
- * Copyright 2012 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.
- *
- */
-
-#include "priv.h"
-
-#if defined(CONFIG_ACPI) && defined(CONFIG_X86)
-int nouveau_acpi_get_bios_chunk(uint8_t *bios, int offset, int len);
-bool nouveau_acpi_rom_supported(struct pci_dev *pdev);
-#else
-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;
-}
-#endif
-
-/* This version of the shadow function disobeys the ACPI spec and tries
- * to fetch in units of more than 4KiB at a time.  This is a LOT faster
- * on some systems, such as Lenovo W530.
- */
-static u32
-acpi_read_fast(void *data, u32 offset, u32 length, struct nouveau_bios *bios)
-{
-       u32 limit = (offset + length + 0xfff) & ~0xfff;
-       u32 start = offset & ~0x00000fff;
-       u32 fetch = limit - start;
-
-       if (nvbios_extend(bios, limit) > 0) {
-               int ret = nouveau_acpi_get_bios_chunk(bios->data, start, fetch);
-               if (ret == fetch)
-                       return fetch;
-       }
-
-       return 0;
-}
-
-/* Other systems, such as the one in fdo#55948, will report a success
- * but only return 4KiB of data.  The common bios fetching logic will
- * detect an invalid image, and fall back to this version of the read
- * function.
- */
-static u32
-acpi_read_slow(void *data, u32 offset, u32 length, struct nouveau_bios *bios)
-{
-       u32 limit = (offset + length + 0xfff) & ~0xfff;
-       u32 start = offset & ~0xfff;
-       u32 fetch = 0;
-
-       if (nvbios_extend(bios, limit) > 0) {
-               while (start + fetch < limit) {
-                       int ret = nouveau_acpi_get_bios_chunk(bios->data,
-                                                             start + fetch,
-                                                             0x1000);
-                       if (ret != 0x1000)
-                               break;
-                       fetch += 0x1000;
-               }
-       }
-
-       return fetch;
-}
-
-static void *
-acpi_init(struct nouveau_bios *bios, const char *name)
-{
-       if (!nouveau_acpi_rom_supported(nv_device(bios)->pdev))
-               return ERR_PTR(-ENODEV);
-       return NULL;
-}
-
-const struct nvbios_source
-nvbios_acpi_fast = {
-       .name = "ACPI",
-       .init = acpi_init,
-       .read = acpi_read_fast,
-       .rw = false,
-};
-
-const struct nvbios_source
-nvbios_acpi_slow = {
-       .name = "ACPI",
-       .init = acpi_init,
-       .read = acpi_read_slow,
-       .rw = false,
-};
diff --git a/drivers/gpu/drm/nouveau/core/subdev/bios/shadowof.c b/drivers/gpu/drm/nouveau/core/subdev/bios/shadowof.c
deleted file mode 100644 (file)
index 3abe487..0000000
+++ /dev/null
@@ -1,71 +0,0 @@
-/*
- * Copyright 2012 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.
- *
- */
-
-#include "priv.h"
-
-#if defined(__powerpc__)
-struct priv {
-       const void __iomem *data;
-       int size;
-};
-
-static u32
-of_read(void *data, u32 offset, u32 length, struct nouveau_bios *bios)
-{
-       struct priv *priv = data;
-       if (offset + length <= priv->size) {
-               memcpy_fromio(bios->data + offset, priv->data + offset, length);
-               return length;
-       }
-       return 0;
-}
-
-static void *
-of_init(struct nouveau_bios *bios, const char *name)
-{
-       struct pci_dev *pdev = nv_device(bios)->pdev;
-       struct device_node *dn;
-       struct priv *priv;
-       if (!(dn = pci_device_to_OF_node(pdev)))
-               return ERR_PTR(-ENODEV);
-       if (!(priv = kzalloc(sizeof(*priv), GFP_KERNEL)))
-               return ERR_PTR(-ENOMEM);
-       if ((priv->data = of_get_property(dn, "NVDA,BMP", &priv->size)))
-               return priv;
-       kfree(priv);
-       return ERR_PTR(-EINVAL);
-}
-
-const struct nvbios_source
-nvbios_of = {
-       .name = "OpenFirmware",
-       .init = of_init,
-       .fini = (void(*)(void *))kfree,
-       .read = of_read,
-       .rw = false,
-};
-#else
-const struct nvbios_source
-nvbios_of = {
-};
-#endif
diff --git a/drivers/gpu/drm/nouveau/core/subdev/bios/shadowpci.c b/drivers/gpu/drm/nouveau/core/subdev/bios/shadowpci.c
deleted file mode 100644 (file)
index 1d0389c..0000000
+++ /dev/null
@@ -1,108 +0,0 @@
-/*
- * Copyright 2012 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.
- *
- */
-
-#include "priv.h"
-
-struct priv {
-       struct pci_dev *pdev;
-       void __iomem *rom;
-       size_t size;
-};
-
-static u32
-pcirom_read(void *data, u32 offset, u32 length, struct nouveau_bios *bios)
-{
-       struct priv *priv = data;
-       if (offset + length <= priv->size) {
-               memcpy_fromio(bios->data + offset, priv->rom + offset, length);
-               return length;
-       }
-       return 0;
-}
-
-static void
-pcirom_fini(void *data)
-{
-       struct priv *priv = data;
-       pci_unmap_rom(priv->pdev, priv->rom);
-       pci_disable_rom(priv->pdev);
-       kfree(priv);
-}
-
-static void *
-pcirom_init(struct nouveau_bios *bios, const char *name)
-{
-       struct pci_dev *pdev = nv_device(bios)->pdev;
-       struct priv *priv = NULL;
-       int ret;
-
-       if (!(ret = pci_enable_rom(pdev))) {
-               if (ret = -ENOMEM,
-                   (priv = kmalloc(sizeof(*priv), GFP_KERNEL))) {
-                       if (ret = -EFAULT,
-                           (priv->rom = pci_map_rom(pdev, &priv->size))) {
-                               priv->pdev = pdev;
-                               return priv;
-                       }
-                       kfree(priv);
-               }
-               pci_disable_rom(pdev);
-       }
-
-       return ERR_PTR(ret);
-}
-
-const struct nvbios_source
-nvbios_pcirom = {
-       .name = "PCIROM",
-       .init = pcirom_init,
-       .fini = pcirom_fini,
-       .read = pcirom_read,
-       .rw = true,
-};
-
-static void *
-platform_init(struct nouveau_bios *bios, const char *name)
-{
-       struct pci_dev *pdev = nv_device(bios)->pdev;
-       struct priv *priv;
-       int ret = -ENOMEM;
-
-       if ((priv = kmalloc(sizeof(*priv), GFP_KERNEL))) {
-               if (ret = -ENODEV,
-                   (priv->rom = pci_platform_rom(pdev, &priv->size)))
-                       return priv;
-               kfree(priv);
-       }
-
-       return ERR_PTR(ret);
-}
-
-const struct nvbios_source
-nvbios_platform = {
-       .name = "PLATFORM",
-       .init = platform_init,
-       .fini = (void(*)(void *))kfree,
-       .read = pcirom_read,
-       .rw = true,
-};
diff --git a/drivers/gpu/drm/nouveau/core/subdev/bios/shadowramin.c b/drivers/gpu/drm/nouveau/core/subdev/bios/shadowramin.c
deleted file mode 100644 (file)
index a7a890f..0000000
+++ /dev/null
@@ -1,114 +0,0 @@
-/*
- * Copyright 2012 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.
- *
- */
-
-#include "priv.h"
-
-struct priv {
-       struct nouveau_bios *bios;
-       u32 bar0;
-};
-
-static u32
-pramin_read(void *data, u32 offset, u32 length, struct nouveau_bios *bios)
-{
-       u32 i;
-       if (offset + length <= 0x00100000) {
-               for (i = offset; i < offset + length; i += 4)
-                       *(u32 *)&bios->data[i] = nv_rd32(bios, 0x700000 + i);
-               return length;
-       }
-       return 0;
-}
-
-static void
-pramin_fini(void *data)
-{
-       struct priv *priv = data;
-       if (priv) {
-               nv_wr32(priv->bios, 0x001700, priv->bar0);
-               kfree(priv);
-       }
-}
-
-static void *
-pramin_init(struct nouveau_bios *bios, const char *name)
-{
-       struct priv *priv = NULL;
-       u64 addr = 0;
-
-       /* PRAMIN always potentially available prior to nv50 */
-       if (nv_device(bios)->card_type < NV_50)
-               return NULL;
-
-       /* we can't get the bios image pointer without PDISP */
-       if (nv_device(bios)->card_type >= GM100)
-               addr = nv_rd32(bios, 0x021c04);
-       else
-       if (nv_device(bios)->card_type >= NV_C0)
-               addr = nv_rd32(bios, 0x022500);
-       if (addr & 0x00000001) {
-               nv_debug(bios, "... display disabled\n");
-               return ERR_PTR(-ENODEV);
-       }
-
-       /* check that the window is enabled and in vram, particularly
-        * important as we don't want to be touching vram on an
-        * uninitialised board
-        */
-       addr = nv_rd32(bios, 0x619f04);
-       if (!(addr & 0x00000008)) {
-               nv_debug(bios, "... not enabled\n");
-               return ERR_PTR(-ENODEV);
-       }
-       if ( (addr & 0x00000003) != 1) {
-               nv_debug(bios, "... not in vram\n");
-               return ERR_PTR(-ENODEV);
-       }
-
-       /* some alternate method inherited from xf86-video-nv... */
-       addr = (addr & 0xffffff00) << 8;
-       if (!addr) {
-               addr  = (u64)nv_rd32(bios, 0x001700) << 16;
-               addr += 0xf0000;
-       }
-
-       /* modify bar0 PRAMIN window to cover the bios image */
-       if (!(priv = kmalloc(sizeof(*priv), GFP_KERNEL))) {
-               nv_error(bios, "... out of memory\n");
-               return ERR_PTR(-ENOMEM);
-       }
-
-       priv->bios = bios;
-       priv->bar0 = nv_rd32(bios, 0x001700);
-       nv_wr32(bios, 0x001700, addr >> 16);
-       return priv;
-}
-
-const struct nvbios_source
-nvbios_ramin = {
-       .name = "PRAMIN",
-       .init = pramin_init,
-       .fini = pramin_fini,
-       .read = pramin_read,
-       .rw = true,
-};
diff --git a/drivers/gpu/drm/nouveau/core/subdev/bios/shadowrom.c b/drivers/gpu/drm/nouveau/core/subdev/bios/shadowrom.c
deleted file mode 100644 (file)
index b7992bc..0000000
+++ /dev/null
@@ -1,69 +0,0 @@
-/*
- * Copyright 2012 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.
- *
- */
-
-#include "priv.h"
-
-static u32
-prom_read(void *data, u32 offset, u32 length, struct nouveau_bios *bios)
-{
-       u32 i;
-       if (offset + length <= 0x00100000) {
-               for (i = offset; i < offset + length; i += 4)
-                       *(u32 *)&bios->data[i] = nv_rd32(bios, 0x300000 + i);
-               return length;
-       }
-       return 0;
-}
-
-static void
-prom_fini(void *data)
-{
-       struct nouveau_bios *bios = data;
-       if (nv_device(bios)->card_type < NV_50)
-               nv_mask(bios, 0x001850, 0x00000001, 0x00000001);
-       else
-               nv_mask(bios, 0x088050, 0x00000001, 0x00000001);
-}
-
-static void *
-prom_init(struct nouveau_bios *bios, const char *name)
-{
-       if (nv_device(bios)->card_type < NV_50) {
-               if (nv_device(bios)->card_type == NV_40 &&
-                   nv_device(bios)->chipset >= 0x4c)
-                       return ERR_PTR(-ENODEV);
-               nv_mask(bios, 0x001850, 0x00000001, 0x00000000);
-       } else {
-               nv_mask(bios, 0x088050, 0x00000001, 0x00000000);
-       }
-       return bios;
-}
-
-const struct nvbios_source
-nvbios_rom = {
-       .name = "PROM",
-       .init = prom_init,
-       .fini = prom_fini,
-       .read = prom_read,
-       .rw = false,
-};
diff --git a/drivers/gpu/drm/nouveau/core/subdev/bios/therm.c b/drivers/gpu/drm/nouveau/core/subdev/bios/therm.c
deleted file mode 100644 (file)
index d158540..0000000
+++ /dev/null
@@ -1,215 +0,0 @@
-/*
- * Copyright 2012 Nouveau Community
- *
- * 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 <subdev/bios.h>
-#include <subdev/bios/bit.h>
-#include <subdev/bios/therm.h>
-
-static u16
-therm_table(struct nouveau_bios *bios, u8 *ver, u8 *hdr, u8 *len, u8 *cnt)
-{
-       struct bit_entry bit_P;
-       u16 therm = 0;
-
-       if (!bit_entry(bios, 'P', &bit_P)) {
-               if (bit_P.version == 1)
-                       therm = nv_ro16(bios, bit_P.offset + 12);
-               else if (bit_P.version == 2)
-                       therm = nv_ro16(bios, bit_P.offset + 16);
-               else
-                       nv_error(bios,
-                               "unknown offset for thermal in BIT P %d\n",
-                               bit_P.version);
-       }
-
-       /* exit now if we haven't found the thermal table */
-       if (!therm)
-               return 0x0000;
-
-       *ver = nv_ro08(bios, therm + 0);
-       *hdr = nv_ro08(bios, therm + 1);
-       *len = nv_ro08(bios, therm + 2);
-       *cnt = nv_ro08(bios, therm + 3);
-
-       return therm + nv_ro08(bios, therm + 1);
-}
-
-static u16
-nvbios_therm_entry(struct nouveau_bios *bios, int idx, u8 *ver, u8 *len)
-{
-       u8 hdr, cnt;
-       u16 therm = therm_table(bios, ver, &hdr, len, &cnt);
-       if (therm && idx < cnt)
-               return therm + idx * *len;
-       return 0x0000;
-}
-
-int
-nvbios_therm_sensor_parse(struct nouveau_bios *bios,
-                         enum nvbios_therm_domain domain,
-                         struct nvbios_therm_sensor *sensor)
-{
-       s8 thrs_section, sensor_section, offset;
-       u8 ver, len, i;
-       u16 entry;
-
-       /* we only support the core domain for now */
-       if (domain != NVBIOS_THERM_DOMAIN_CORE)
-               return -EINVAL;
-
-       /* Read the entries from the table */
-       thrs_section = 0;
-       sensor_section = -1;
-       i = 0;
-       while ((entry = nvbios_therm_entry(bios, i++, &ver, &len))) {
-               s16 value = nv_ro16(bios, entry + 1);
-
-               switch (nv_ro08(bios, entry + 0)) {
-               case 0x0:
-                       thrs_section = value;
-                       if (value > 0)
-                               return 0; /* we do not try to support ambient */
-                       break;
-               case 0x01:
-                       sensor_section++;
-                       if (sensor_section == 0) {
-                               offset = ((s8) nv_ro08(bios, entry + 2)) / 2;
-                               sensor->offset_constant = offset;
-                       }
-                       break;
-
-               case 0x04:
-                       if (thrs_section == 0) {
-                               sensor->thrs_critical.temp = (value & 0xff0) >> 4;
-                               sensor->thrs_critical.hysteresis = value & 0xf;
-                       }
-                       break;
-
-               case 0x07:
-                       if (thrs_section == 0) {
-                               sensor->thrs_down_clock.temp = (value & 0xff0) >> 4;
-                               sensor->thrs_down_clock.hysteresis = value & 0xf;
-                       }
-                       break;
-
-               case 0x08:
-                       if (thrs_section == 0) {
-                               sensor->thrs_fan_boost.temp = (value & 0xff0) >> 4;
-                               sensor->thrs_fan_boost.hysteresis = value & 0xf;
-                       }
-                       break;
-
-               case 0x10:
-                       if (sensor_section == 0)
-                               sensor->offset_num = value;
-                       break;
-
-               case 0x11:
-                       if (sensor_section == 0)
-                               sensor->offset_den = value;
-                       break;
-
-               case 0x12:
-                       if (sensor_section == 0)
-                               sensor->slope_mult = value;
-                       break;
-
-               case 0x13:
-                       if (sensor_section == 0)
-                               sensor->slope_div = value;
-                       break;
-               case 0x32:
-                       if (thrs_section == 0) {
-                               sensor->thrs_shutdown.temp = (value & 0xff0) >> 4;
-                               sensor->thrs_shutdown.hysteresis = value & 0xf;
-                       }
-                       break;
-               }
-       }
-
-       return 0;
-}
-
-int
-nvbios_therm_fan_parse(struct nouveau_bios *bios,
-                         struct nvbios_therm_fan *fan)
-{
-       struct nouveau_therm_trip_point *cur_trip = NULL;
-       u8 ver, len, i;
-       u16 entry;
-
-       uint8_t duty_lut[] = { 0, 0, 25, 0, 40, 0, 50, 0,
-                               75, 0, 85, 0, 100, 0, 100, 0 };
-
-       i = 0;
-       fan->nr_fan_trip = 0;
-       fan->fan_mode = NVBIOS_THERM_FAN_OTHER;
-       while ((entry = nvbios_therm_entry(bios, i++, &ver, &len))) {
-               s16 value = nv_ro16(bios, entry + 1);
-
-               switch (nv_ro08(bios, entry + 0)) {
-               case 0x22:
-                       fan->min_duty = value & 0xff;
-                       fan->max_duty = (value & 0xff00) >> 8;
-                       break;
-               case 0x24:
-                       fan->nr_fan_trip++;
-                       if (fan->fan_mode > NVBIOS_THERM_FAN_TRIP)
-                               fan->fan_mode = NVBIOS_THERM_FAN_TRIP;
-                       cur_trip = &fan->trip[fan->nr_fan_trip - 1];
-                       cur_trip->hysteresis = value & 0xf;
-                       cur_trip->temp = (value & 0xff0) >> 4;
-                       cur_trip->fan_duty = duty_lut[(value & 0xf000) >> 12];
-                       break;
-               case 0x25:
-                       cur_trip = &fan->trip[fan->nr_fan_trip - 1];
-                       cur_trip->fan_duty = value;
-                       break;
-               case 0x26:
-                       if (!fan->pwm_freq)
-                               fan->pwm_freq = value;
-                       break;
-               case 0x3b:
-                       fan->bump_period = value;
-                       break;
-               case 0x3c:
-                       fan->slow_down_period = value;
-                       break;
-               case 0x46:
-                       if (fan->fan_mode > NVBIOS_THERM_FAN_LINEAR)
-                               fan->fan_mode = NVBIOS_THERM_FAN_LINEAR;
-                       fan->linear_min_temp = nv_ro08(bios, entry + 1);
-                       fan->linear_max_temp = nv_ro08(bios, entry + 2);
-                       break;
-               }
-       }
-
-       /* starting from fermi, fan management is always linear */
-       if (nv_device(bios)->card_type >= NV_C0 &&
-               fan->fan_mode == NVBIOS_THERM_FAN_OTHER) {
-               fan->fan_mode = NVBIOS_THERM_FAN_LINEAR;
-       }
-
-       return 0;
-}
diff --git a/drivers/gpu/drm/nouveau/core/subdev/bios/timing.c b/drivers/gpu/drm/nouveau/core/subdev/bios/timing.c
deleted file mode 100644 (file)
index 8521eca..0000000
+++ /dev/null
@@ -1,169 +0,0 @@
-/*
- * Copyright 2013 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 <subdev/bios.h>
-#include <subdev/bios/bit.h>
-#include <subdev/bios/ramcfg.h>
-#include <subdev/bios/timing.h>
-
-u16
-nvbios_timingTe(struct nouveau_bios *bios,
-               u8 *ver, u8 *hdr, u8 *cnt, u8 *len, u8 *snr, u8 *ssz)
-{
-       struct bit_entry bit_P;
-       u16 timing = 0x0000;
-
-       if (!bit_entry(bios, 'P', &bit_P)) {
-               if (bit_P.version == 1)
-                       timing = nv_ro16(bios, bit_P.offset + 4);
-               else
-               if (bit_P.version == 2)
-                       timing = nv_ro16(bios, bit_P.offset + 8);
-
-               if (timing) {
-                       *ver = nv_ro08(bios, timing + 0);
-                       switch (*ver) {
-                       case 0x10:
-                               *hdr = nv_ro08(bios, timing + 1);
-                               *cnt = nv_ro08(bios, timing + 2);
-                               *len = nv_ro08(bios, timing + 3);
-                               *snr = 0;
-                               *ssz = 0;
-                               return timing;
-                       case 0x20:
-                               *hdr = nv_ro08(bios, timing + 1);
-                               *cnt = nv_ro08(bios, timing + 5);
-                               *len = nv_ro08(bios, timing + 2);
-                               *snr = nv_ro08(bios, timing + 4);
-                               *ssz = nv_ro08(bios, timing + 3);
-                               return timing;
-                       default:
-                               break;
-                       }
-               }
-       }
-
-       return 0x0000;
-}
-
-u16
-nvbios_timingEe(struct nouveau_bios *bios, int idx,
-               u8 *ver, u8 *hdr, u8 *cnt, u8 *len)
-{
-       u8  snr, ssz;
-       u16 timing = nvbios_timingTe(bios, ver, hdr, cnt, len, &snr, &ssz);
-       if (timing && idx < *cnt) {
-               timing += *hdr + idx * (*len + (snr * ssz));
-               *hdr = *len;
-               *cnt = snr;
-               *len = ssz;
-               return timing;
-       }
-       return 0x0000;
-}
-
-u16
-nvbios_timingEp(struct nouveau_bios *bios, int idx,
-               u8 *ver, u8 *hdr, u8 *cnt, u8 *len,
-               struct nvbios_ramcfg *p)
-{
-       u16 data = nvbios_timingEe(bios, idx, ver, hdr, cnt, len), temp;
-       p->timing_ver = *ver;
-       p->timing_hdr = *hdr;
-       switch (!!data * *ver) {
-       case 0x10:
-               p->timing_10_WR    = nv_ro08(bios, data + 0x00);
-               p->timing_10_WTR   = nv_ro08(bios, data + 0x01);
-               p->timing_10_CL    = nv_ro08(bios, data + 0x02);
-               p->timing_10_RC    = nv_ro08(bios, data + 0x03);
-               p->timing_10_RFC   = nv_ro08(bios, data + 0x05);
-               p->timing_10_RAS   = nv_ro08(bios, data + 0x07);
-               p->timing_10_RP    = nv_ro08(bios, data + 0x09);
-               p->timing_10_RCDRD = nv_ro08(bios, data + 0x0a);
-               p->timing_10_RCDWR = nv_ro08(bios, data + 0x0b);
-               p->timing_10_RRD   = nv_ro08(bios, data + 0x0c);
-               p->timing_10_13    = nv_ro08(bios, data + 0x0d);
-               p->timing_10_ODT   = nv_ro08(bios, data + 0x0e) & 0x07;
-
-               p->timing_10_24  = 0xff;
-               p->timing_10_21  = 0;
-               p->timing_10_20  = 0;
-               p->timing_10_CWL = 0;
-               p->timing_10_18  = 0;
-               p->timing_10_16  = 0;
-
-               switch (min_t(u8, *hdr, 25)) {
-               case 25:
-                       p->timing_10_24  = nv_ro08(bios, data + 0x18);
-               case 24:
-               case 23:
-               case 22:
-                       p->timing_10_21  = nv_ro08(bios, data + 0x15);
-               case 21:
-                       p->timing_10_20  = nv_ro08(bios, data + 0x14);
-               case 20:
-                       p->timing_10_CWL = nv_ro08(bios, data + 0x13);
-               case 19:
-                       p->timing_10_18  = nv_ro08(bios, data + 0x12);
-               case 18:
-               case 17:
-                       p->timing_10_16  = nv_ro08(bios, data + 0x10);
-               }
-
-               break;
-       case 0x20:
-               p->timing[0] = nv_ro32(bios, data + 0x00);
-               p->timing[1] = nv_ro32(bios, data + 0x04);
-               p->timing[2] = nv_ro32(bios, data + 0x08);
-               p->timing[3] = nv_ro32(bios, data + 0x0c);
-               p->timing[4] = nv_ro32(bios, data + 0x10);
-               p->timing[5] = nv_ro32(bios, data + 0x14);
-               p->timing[6] = nv_ro32(bios, data + 0x18);
-               p->timing[7] = nv_ro32(bios, data + 0x1c);
-               p->timing[8] = nv_ro32(bios, data + 0x20);
-               p->timing[9] = nv_ro32(bios, data + 0x24);
-               p->timing[10] = nv_ro32(bios, data + 0x28);
-               p->timing_20_2e_03 = (nv_ro08(bios, data + 0x2e) & 0x03) >> 0;
-               p->timing_20_2e_30 = (nv_ro08(bios, data + 0x2e) & 0x30) >> 4;
-               p->timing_20_2e_c0 = (nv_ro08(bios, data + 0x2e) & 0xc0) >> 6;
-               p->timing_20_2f_03 = (nv_ro08(bios, data + 0x2f) & 0x03) >> 0;
-               temp = nv_ro16(bios, data + 0x2c);
-               p->timing_20_2c_003f = (temp & 0x003f) >> 0;
-               p->timing_20_2c_1fc0 = (temp & 0x1fc0) >> 6;
-               p->timing_20_30_07 = (nv_ro08(bios, data + 0x30) & 0x07) >> 0;
-               p->timing_20_30_f8 = (nv_ro08(bios, data + 0x30) & 0xf8) >> 3;
-               temp = nv_ro16(bios, data + 0x31);
-               p->timing_20_31_0007 = (temp & 0x0007) >> 0;
-               p->timing_20_31_0078 = (temp & 0x0078) >> 3;
-               p->timing_20_31_0780 = (temp & 0x0780) >> 7;
-               p->timing_20_31_0800 = (temp & 0x0800) >> 11;
-               p->timing_20_31_7000 = (temp & 0x7000) >> 12;
-               p->timing_20_31_8000 = (temp & 0x8000) >> 15;
-               break;
-       default:
-               data = 0;
-               break;
-       }
-       return data;
-}
diff --git a/drivers/gpu/drm/nouveau/core/subdev/bios/vmap.c b/drivers/gpu/drm/nouveau/core/subdev/bios/vmap.c
deleted file mode 100644 (file)
index f343a1b..0000000
+++ /dev/null
@@ -1,112 +0,0 @@
-/*
- * Copyright 2012 Nouveau Community
- *
- * 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 <subdev/bios.h>
-#include <subdev/bios/bit.h>
-#include <subdev/bios/vmap.h>
-
-u16
-nvbios_vmap_table(struct nouveau_bios *bios, u8 *ver, u8 *hdr, u8 *cnt, u8 *len)
-{
-       struct bit_entry bit_P;
-       u16 vmap = 0x0000;
-
-       if (!bit_entry(bios, 'P', &bit_P)) {
-               if (bit_P.version == 2) {
-                       vmap = nv_ro16(bios, bit_P.offset + 0x20);
-                       if (vmap) {
-                               *ver = nv_ro08(bios, vmap + 0);
-                               switch (*ver) {
-                               case 0x10:
-                               case 0x20:
-                                       *hdr = nv_ro08(bios, vmap + 1);
-                                       *cnt = nv_ro08(bios, vmap + 3);
-                                       *len = nv_ro08(bios, vmap + 2);
-                                       return vmap;
-                               default:
-                                       break;
-                               }
-                       }
-               }
-       }
-
-       return 0x0000;
-}
-
-u16
-nvbios_vmap_parse(struct nouveau_bios *bios, u8 *ver, u8 *hdr, u8 *cnt, u8 *len,
-                 struct nvbios_vmap *info)
-{
-       u16 vmap = nvbios_vmap_table(bios, ver, hdr, cnt, len);
-       memset(info, 0x00, sizeof(*info));
-       switch (!!vmap * *ver) {
-       case 0x10:
-       case 0x20:
-               break;
-       }
-       return vmap;
-}
-
-u16
-nvbios_vmap_entry(struct nouveau_bios *bios, int idx, u8 *ver, u8 *len)
-{
-       u8  hdr, cnt;
-       u16 vmap = nvbios_vmap_table(bios, ver, &hdr, &cnt, len);
-       if (vmap && idx < cnt) {
-               vmap = vmap + hdr + (idx * *len);
-               return vmap;
-       }
-       return 0x0000;
-}
-
-u16
-nvbios_vmap_entry_parse(struct nouveau_bios *bios, int idx, u8 *ver, u8 *len,
-                       struct nvbios_vmap_entry *info)
-{
-       u16 vmap = nvbios_vmap_entry(bios, idx, ver, len);
-       memset(info, 0x00, sizeof(*info));
-       switch (!!vmap * *ver) {
-       case 0x10:
-               info->link   = 0xff;
-               info->min    = nv_ro32(bios, vmap + 0x00);
-               info->max    = nv_ro32(bios, vmap + 0x04);
-               info->arg[0] = nv_ro32(bios, vmap + 0x08);
-               info->arg[1] = nv_ro32(bios, vmap + 0x0c);
-               info->arg[2] = nv_ro32(bios, vmap + 0x10);
-               break;
-       case 0x20:
-               info->unk0   = nv_ro08(bios, vmap + 0x00);
-               info->link   = nv_ro08(bios, vmap + 0x01);
-               info->min    = nv_ro32(bios, vmap + 0x02);
-               info->max    = nv_ro32(bios, vmap + 0x06);
-               info->arg[0] = nv_ro32(bios, vmap + 0x0a);
-               info->arg[1] = nv_ro32(bios, vmap + 0x0e);
-               info->arg[2] = nv_ro32(bios, vmap + 0x12);
-               info->arg[3] = nv_ro32(bios, vmap + 0x16);
-               info->arg[4] = nv_ro32(bios, vmap + 0x1a);
-               info->arg[5] = nv_ro32(bios, vmap + 0x1e);
-               break;
-       }
-       return vmap;
-}
diff --git a/drivers/gpu/drm/nouveau/core/subdev/bios/volt.c b/drivers/gpu/drm/nouveau/core/subdev/bios/volt.c
deleted file mode 100644 (file)
index bb590de..0000000
+++ /dev/null
@@ -1,137 +0,0 @@
-/*
- * Copyright 2012 Nouveau Community
- *
- * 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 <subdev/bios.h>
-#include <subdev/bios/bit.h>
-#include <subdev/bios/volt.h>
-
-u16
-nvbios_volt_table(struct nouveau_bios *bios, u8 *ver, u8 *hdr, u8 *cnt, u8 *len)
-{
-       struct bit_entry bit_P;
-       u16 volt = 0x0000;
-
-       if (!bit_entry(bios, 'P', &bit_P)) {
-               if (bit_P.version == 2)
-                       volt = nv_ro16(bios, bit_P.offset + 0x0c);
-               else
-               if (bit_P.version == 1)
-                       volt = nv_ro16(bios, bit_P.offset + 0x10);
-
-               if (volt) {
-                       *ver = nv_ro08(bios, volt + 0);
-                       switch (*ver) {
-                       case 0x12:
-                               *hdr = 5;
-                               *cnt = nv_ro08(bios, volt + 2);
-                               *len = nv_ro08(bios, volt + 1);
-                               return volt;
-                       case 0x20:
-                               *hdr = nv_ro08(bios, volt + 1);
-                               *cnt = nv_ro08(bios, volt + 2);
-                               *len = nv_ro08(bios, volt + 3);
-                               return volt;
-                       case 0x30:
-                       case 0x40:
-                       case 0x50:
-                               *hdr = nv_ro08(bios, volt + 1);
-                               *cnt = nv_ro08(bios, volt + 3);
-                               *len = nv_ro08(bios, volt + 2);
-                               return volt;
-                       }
-               }
-       }
-
-       return 0x0000;
-}
-
-u16
-nvbios_volt_parse(struct nouveau_bios *bios, u8 *ver, u8 *hdr, u8 *cnt, u8 *len,
-                 struct nvbios_volt *info)
-{
-       u16 volt = nvbios_volt_table(bios, ver, hdr, cnt, len);
-       memset(info, 0x00, sizeof(*info));
-       switch (!!volt * *ver) {
-       case 0x12:
-               info->vidmask = nv_ro08(bios, volt + 0x04);
-               break;
-       case 0x20:
-               info->vidmask = nv_ro08(bios, volt + 0x05);
-               break;
-       case 0x30:
-               info->vidmask = nv_ro08(bios, volt + 0x04);
-               break;
-       case 0x40:
-               info->base    = nv_ro32(bios, volt + 0x04);
-               info->step    = nv_ro16(bios, volt + 0x08);
-               info->vidmask = nv_ro08(bios, volt + 0x0b);
-               /*XXX*/
-               info->min     = 0;
-               info->max     = info->base;
-               break;
-       case 0x50:
-               info->vidmask = nv_ro08(bios, volt + 0x06);
-               info->min     = nv_ro32(bios, volt + 0x0a);
-               info->max     = nv_ro32(bios, volt + 0x0e);
-               info->base    = nv_ro32(bios, volt + 0x12) & 0x00ffffff;
-               info->step    = nv_ro16(bios, volt + 0x16);
-               break;
-       }
-       return volt;
-}
-
-u16
-nvbios_volt_entry(struct nouveau_bios *bios, int idx, u8 *ver, u8 *len)
-{
-       u8  hdr, cnt;
-       u16 volt = nvbios_volt_table(bios, ver, &hdr, &cnt, len);
-       if (volt && idx < cnt) {
-               volt = volt + hdr + (idx * *len);
-               return volt;
-       }
-       return 0x0000;
-}
-
-u16
-nvbios_volt_entry_parse(struct nouveau_bios *bios, int idx, u8 *ver, u8 *len,
-                       struct nvbios_volt_entry *info)
-{
-       u16 volt = nvbios_volt_entry(bios, idx, ver, len);
-       memset(info, 0x00, sizeof(*info));
-       switch (!!volt * *ver) {
-       case 0x12:
-       case 0x20:
-               info->voltage = nv_ro08(bios, volt + 0x00) * 10000;
-               info->vid     = nv_ro08(bios, volt + 0x01);
-               break;
-       case 0x30:
-               info->voltage = nv_ro08(bios, volt + 0x00) * 10000;
-               info->vid     = nv_ro08(bios, volt + 0x01) >> 2;
-               break;
-       case 0x40:
-       case 0x50:
-               break;
-       }
-       return volt;
-}
diff --git a/drivers/gpu/drm/nouveau/core/subdev/bios/xpio.c b/drivers/gpu/drm/nouveau/core/subdev/bios/xpio.c
deleted file mode 100644 (file)
index e9b8e5d..0000000
+++ /dev/null
@@ -1,76 +0,0 @@
-/*
- * Copyright 2012 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 <subdev/bios.h>
-#include <subdev/bios/gpio.h>
-#include <subdev/bios/xpio.h>
-
-static u16
-dcb_xpiod_table(struct nouveau_bios *bios, u8 *ver, u8 *hdr, u8 *cnt, u8 *len)
-{
-       u16 data = dcb_gpio_table(bios, ver, hdr, cnt, len);
-       if (data && *ver >= 0x40 && *hdr >= 0x06) {
-               u16 xpio = nv_ro16(bios, data + 0x04);
-               if (xpio) {
-                       *ver = nv_ro08(bios, data + 0x00);
-                       *hdr = nv_ro08(bios, data + 0x01);
-                       *cnt = nv_ro08(bios, data + 0x02);
-                       *len = nv_ro08(bios, data + 0x03);
-                       return xpio;
-               }
-       }
-       return 0x0000;
-}
-
-u16
-dcb_xpio_table(struct nouveau_bios *bios, u8 idx,
-              u8 *ver, u8 *hdr, u8 *cnt, u8 *len)
-{
-       u16 data = dcb_xpiod_table(bios, ver, hdr, cnt, len);
-       if (data && idx < *cnt) {
-               u16 xpio = nv_ro16(bios, data + *hdr + (idx * *len));
-               if (xpio) {
-                       *ver = nv_ro08(bios, data + 0x00);
-                       *hdr = nv_ro08(bios, data + 0x01);
-                       *cnt = nv_ro08(bios, data + 0x02);
-                       *len = nv_ro08(bios, data + 0x03);
-                       return xpio;
-               }
-       }
-       return 0x0000;
-}
-
-u16
-dcb_xpio_parse(struct nouveau_bios *bios, u8 idx,
-              u8 *ver, u8 *hdr, u8 *cnt, u8 *len,
-              struct nvbios_xpio *info)
-{
-       u16 data = dcb_xpio_table(bios, idx, ver, hdr, cnt, len);
-       if (data && *len >= 6) {
-               info->type = nv_ro08(bios, data + 0x04);
-               info->addr = nv_ro08(bios, data + 0x05);
-               info->flags = nv_ro08(bios, data + 0x06);
-       }
-       return 0x0000;
-}
diff --git a/drivers/gpu/drm/nouveau/core/subdev/bus/hwsq.c b/drivers/gpu/drm/nouveau/core/subdev/bus/hwsq.c
deleted file mode 100644 (file)
index f757470..0000000
+++ /dev/null
@@ -1,145 +0,0 @@
-/*
- * Copyright 2013 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 <bskeggs@redhat.com>
- */
-
-#include <subdev/timer.h>
-#include <subdev/bus.h>
-
-struct nouveau_hwsq {
-       struct nouveau_bus *pbus;
-       u32 addr;
-       u32 data;
-       struct {
-               u8 data[512];
-               u8 size;
-       } c;
-};
-
-static void
-hwsq_cmd(struct nouveau_hwsq *hwsq, int size, u8 data[])
-{
-       memcpy(&hwsq->c.data[hwsq->c.size], data, size * sizeof(data[0]));
-       hwsq->c.size += size;
-}
-
-int
-nouveau_hwsq_init(struct nouveau_bus *pbus, struct nouveau_hwsq **phwsq)
-{
-       struct nouveau_hwsq *hwsq;
-
-       hwsq = *phwsq = kmalloc(sizeof(*hwsq), GFP_KERNEL);
-       if (hwsq) {
-               hwsq->pbus = pbus;
-               hwsq->addr = ~0;
-               hwsq->data = ~0;
-               memset(hwsq->c.data, 0x7f, sizeof(hwsq->c.data));
-               hwsq->c.size = 0;
-       }
-
-       return hwsq ? 0 : -ENOMEM;
-}
-
-int
-nouveau_hwsq_fini(struct nouveau_hwsq **phwsq, bool exec)
-{
-       struct nouveau_hwsq *hwsq = *phwsq;
-       int ret = 0, i;
-       if (hwsq) {
-               struct nouveau_bus *pbus = hwsq->pbus;
-               hwsq->c.size = (hwsq->c.size + 4) / 4;
-               if (hwsq->c.size <= pbus->hwsq_size) {
-                       if (exec)
-                               ret = pbus->hwsq_exec(pbus, (u32 *)hwsq->c.data,
-                                                     hwsq->c.size);
-                       if (ret)
-                               nv_error(pbus, "hwsq exec failed: %d\n", ret);
-               } else {
-                       nv_error(pbus, "hwsq ucode too large\n");
-                       ret = -ENOSPC;
-               }
-
-               for (i = 0; ret && i < hwsq->c.size; i++)
-                       nv_error(pbus, "\t0x%08x\n", ((u32 *)hwsq->c.data)[i]);
-
-               *phwsq = NULL;
-               kfree(hwsq);
-       }
-       return ret;
-}
-
-void
-nouveau_hwsq_wr32(struct nouveau_hwsq *hwsq, u32 addr, u32 data)
-{
-       nv_debug(hwsq->pbus, "R[%06x] = 0x%08x\n", addr, data);
-
-       if (hwsq->data != data) {
-               if ((data & 0xffff0000) != (hwsq->data & 0xffff0000)) {
-                       hwsq_cmd(hwsq, 5, (u8[]){ 0xe2, data, data >> 8,
-                                                 data >> 16, data >> 24 });
-               } else {
-                       hwsq_cmd(hwsq, 3, (u8[]){ 0x42, data, data >> 8 });
-               }
-       }
-
-       if ((addr & 0xffff0000) != (hwsq->addr & 0xffff0000)) {
-               hwsq_cmd(hwsq, 5, (u8[]){ 0xe0, addr, addr >> 8,
-                                         addr >> 16, addr >> 24 });
-       } else {
-               hwsq_cmd(hwsq, 3, (u8[]){ 0x40, addr, addr >> 8 });
-       }
-
-       hwsq->addr = addr;
-       hwsq->data = data;
-}
-
-void
-nouveau_hwsq_setf(struct nouveau_hwsq *hwsq, u8 flag, int data)
-{
-       nv_debug(hwsq->pbus, " FLAG[%02x] = %d\n", flag, data);
-       flag += 0x80;
-       if (data >= 0)
-               flag += 0x20;
-       if (data >= 1)
-               flag += 0x20;
-       hwsq_cmd(hwsq, 1, (u8[]){ flag });
-}
-
-void
-nouveau_hwsq_wait(struct nouveau_hwsq *hwsq, u8 flag, u8 data)
-{
-       nv_debug(hwsq->pbus, " WAIT[%02x] = %d\n", flag, data);
-       hwsq_cmd(hwsq, 3, (u8[]){ 0x5f, flag, data });
-}
-
-void
-nouveau_hwsq_nsec(struct nouveau_hwsq *hwsq, u32 nsec)
-{
-       u8 shift = 0, usec = nsec / 1000;
-       while (usec & ~3) {
-               usec >>= 2;
-               shift++;
-       }
-
-       nv_debug(hwsq->pbus, "    DELAY = %d ns\n", nsec);
-       hwsq_cmd(hwsq, 1, (u8[]){ 0x00 | (shift << 2) | usec });
-}
diff --git a/drivers/gpu/drm/nouveau/core/subdev/bus/hwsq.h b/drivers/gpu/drm/nouveau/core/subdev/bus/hwsq.h
deleted file mode 100644 (file)
index 12176f9..0000000
+++ /dev/null
@@ -1,113 +0,0 @@
-#ifndef __NVKM_BUS_HWSQ_H__
-#define __NVKM_BUS_HWSQ_H__
-
-#include <subdev/bus.h>
-
-struct hwsq {
-       struct nouveau_subdev *subdev;
-       struct nouveau_hwsq *hwsq;
-       int sequence;
-};
-
-struct hwsq_reg {
-       int sequence;
-       bool force;
-       u32 addr[2];
-       u32 data;
-};
-
-static inline struct hwsq_reg
-hwsq_reg2(u32 addr1, u32 addr2)
-{
-       return (struct hwsq_reg) {
-               .sequence = 0,
-               .force = 0,
-               .addr = { addr1, addr2 },
-               .data = 0xdeadbeef,
-       };
-}
-
-static inline struct hwsq_reg
-hwsq_reg(u32 addr)
-{
-       return hwsq_reg2(addr, addr);
-}
-
-static inline int
-hwsq_init(struct hwsq *ram, struct nouveau_subdev *subdev)
-{
-       struct nouveau_bus *pbus = nouveau_bus(subdev);
-       int ret;
-
-       ret = nouveau_hwsq_init(pbus, &ram->hwsq);
-       if (ret)
-               return ret;
-
-       ram->sequence++;
-       ram->subdev = subdev;
-       return 0;
-}
-
-static inline int
-hwsq_exec(struct hwsq *ram, bool exec)
-{
-       int ret = 0;
-       if (ram->subdev) {
-               ret = nouveau_hwsq_fini(&ram->hwsq, exec);
-               ram->subdev = NULL;
-       }
-       return ret;
-}
-
-static inline u32
-hwsq_rd32(struct hwsq *ram, struct hwsq_reg *reg)
-{
-       if (reg->sequence != ram->sequence)
-               reg->data = nv_rd32(ram->subdev, reg->addr[0]);
-       return reg->data;
-}
-
-static inline void
-hwsq_wr32(struct hwsq *ram, struct hwsq_reg *reg, u32 data)
-{
-       reg->sequence = ram->sequence;
-       reg->data = data;
-       if (reg->addr[0] != reg->addr[1])
-               nouveau_hwsq_wr32(ram->hwsq, reg->addr[1], reg->data);
-       nouveau_hwsq_wr32(ram->hwsq, reg->addr[0], reg->data);
-}
-
-static inline void
-hwsq_nuke(struct hwsq *ram, struct hwsq_reg *reg)
-{
-       reg->force = true;
-}
-
-static inline u32
-hwsq_mask(struct hwsq *ram, struct hwsq_reg *reg, u32 mask, u32 data)
-{
-       u32 temp = hwsq_rd32(ram, reg);
-       if (temp != ((temp & ~mask) | data) || reg->force)
-               hwsq_wr32(ram, reg, (temp & ~mask) | data);
-       return temp;
-}
-
-static inline void
-hwsq_setf(struct hwsq *ram, u8 flag, int data)
-{
-       nouveau_hwsq_setf(ram->hwsq, flag, data);
-}
-
-static inline void
-hwsq_wait(struct hwsq *ram, u8 flag, u8 data)
-{
-       nouveau_hwsq_wait(ram->hwsq, flag, data);
-}
-
-static inline void
-hwsq_nsec(struct hwsq *ram, u32 nsec)
-{
-       nouveau_hwsq_nsec(ram->hwsq, nsec);
-}
-
-#endif
diff --git a/drivers/gpu/drm/nouveau/core/subdev/bus/nv04.c b/drivers/gpu/drm/nouveau/core/subdev/bus/nv04.c
deleted file mode 100644 (file)
index 23921b5..0000000
+++ /dev/null
@@ -1,95 +0,0 @@
-/*
- * Copyright 2012 Nouveau Community
- *
- * 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 <martin.peres@labri.fr>
- *          Ben Skeggs
- */
-
-#include "nv04.h"
-
-static void
-nv04_bus_intr(struct nouveau_subdev *subdev)
-{
-       struct nouveau_bus *pbus = nouveau_bus(subdev);
-       u32 stat = nv_rd32(pbus, 0x001100) & nv_rd32(pbus, 0x001140);
-
-       if (stat & 0x00000001) {
-               nv_error(pbus, "BUS ERROR\n");
-               stat &= ~0x00000001;
-               nv_wr32(pbus, 0x001100, 0x00000001);
-       }
-
-       if (stat & 0x00000110) {
-               subdev = nouveau_subdev(subdev, NVDEV_SUBDEV_GPIO);
-               if (subdev && subdev->intr)
-                       subdev->intr(subdev);
-               stat &= ~0x00000110;
-               nv_wr32(pbus, 0x001100, 0x00000110);
-       }
-
-       if (stat) {
-               nv_error(pbus, "unknown intr 0x%08x\n", stat);
-               nv_mask(pbus, 0x001140, stat, 0x00000000);
-       }
-}
-
-static int
-nv04_bus_init(struct nouveau_object *object)
-{
-       struct nv04_bus_priv *priv = (void *)object;
-
-       nv_wr32(priv, 0x001100, 0xffffffff);
-       nv_wr32(priv, 0x001140, 0x00000111);
-
-       return nouveau_bus_init(&priv->base);
-}
-
-int
-nv04_bus_ctor(struct nouveau_object *parent, struct nouveau_object *engine,
-             struct nouveau_oclass *oclass, void *data, u32 size,
-             struct nouveau_object **pobject)
-{
-       struct nv04_bus_impl *impl = (void *)oclass;
-       struct nv04_bus_priv *priv;
-       int ret;
-
-       ret = nouveau_bus_create(parent, engine, oclass, &priv);
-       *pobject = nv_object(priv);
-       if (ret)
-               return ret;
-
-       nv_subdev(priv)->intr = impl->intr;
-       priv->base.hwsq_exec = impl->hwsq_exec;
-       priv->base.hwsq_size = impl->hwsq_size;
-       return 0;
-}
-
-struct nouveau_oclass *
-nv04_bus_oclass = &(struct nv04_bus_impl) {
-       .base.handle = NV_SUBDEV(BUS, 0x04),
-       .base.ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nv04_bus_ctor,
-               .dtor = _nouveau_bus_dtor,
-               .init = nv04_bus_init,
-               .fini = _nouveau_bus_fini,
-       },
-       .intr = nv04_bus_intr,
-}.base;
diff --git a/drivers/gpu/drm/nouveau/core/subdev/bus/nv04.h b/drivers/gpu/drm/nouveau/core/subdev/bus/nv04.h
deleted file mode 100644 (file)
index 4d76024..0000000
+++ /dev/null
@@ -1,23 +0,0 @@
-#ifndef __NVKM_BUS_NV04_H__
-#define __NVKM_BUS_NV04_H__
-
-#include <subdev/bus.h>
-
-struct nv04_bus_priv {
-       struct nouveau_bus base;
-};
-
-int  nv04_bus_ctor(struct nouveau_object *, struct nouveau_object *,
-                  struct nouveau_oclass *, void *, u32,
-                  struct nouveau_object **);
-int  nv50_bus_init(struct nouveau_object *);
-void nv50_bus_intr(struct nouveau_subdev *);
-
-struct nv04_bus_impl {
-       struct nouveau_oclass base;
-       void (*intr)(struct nouveau_subdev *);
-       int  (*hwsq_exec)(struct nouveau_bus *, u32 *, u32);
-       u32  hwsq_size;
-};
-
-#endif
diff --git a/drivers/gpu/drm/nouveau/core/subdev/bus/nv31.c b/drivers/gpu/drm/nouveau/core/subdev/bus/nv31.c
deleted file mode 100644 (file)
index 94da46f..0000000
+++ /dev/null
@@ -1,92 +0,0 @@
-/*
- * Copyright 2012 Nouveau Community
- *
- * 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 <martin.peres@labri.fr>
- *          Ben Skeggs
- */
-
-#include "nv04.h"
-
-static void
-nv31_bus_intr(struct nouveau_subdev *subdev)
-{
-       struct nouveau_bus *pbus = nouveau_bus(subdev);
-       u32 stat = nv_rd32(pbus, 0x001100) & nv_rd32(pbus, 0x001140);
-       u32 gpio = nv_rd32(pbus, 0x001104) & nv_rd32(pbus, 0x001144);
-
-       if (gpio) {
-               subdev = nouveau_subdev(pbus, NVDEV_SUBDEV_GPIO);
-               if (subdev && subdev->intr)
-                       subdev->intr(subdev);
-       }
-
-       if (stat & 0x00000008) {  /* NV41- */
-               u32 addr = nv_rd32(pbus, 0x009084);
-               u32 data = nv_rd32(pbus, 0x009088);
-
-               nv_error(pbus, "MMIO %s of 0x%08x FAULT at 0x%06x\n",
-                        (addr & 0x00000002) ? "write" : "read", data,
-                        (addr & 0x00fffffc));
-
-               stat &= ~0x00000008;
-               nv_wr32(pbus, 0x001100, 0x00000008);
-       }
-
-       if (stat & 0x00070000) {
-               subdev = nouveau_subdev(pbus, NVDEV_SUBDEV_THERM);
-               if (subdev && subdev->intr)
-                       subdev->intr(subdev);
-               stat &= ~0x00070000;
-               nv_wr32(pbus, 0x001100, 0x00070000);
-       }
-
-       if (stat) {
-               nv_error(pbus, "unknown intr 0x%08x\n", stat);
-               nv_mask(pbus, 0x001140, stat, 0x00000000);
-       }
-}
-
-static int
-nv31_bus_init(struct nouveau_object *object)
-{
-       struct nv04_bus_priv *priv = (void *)object;
-       int ret;
-
-       ret = nouveau_bus_init(&priv->base);
-       if (ret)
-               return ret;
-
-       nv_wr32(priv, 0x001100, 0xffffffff);
-       nv_wr32(priv, 0x001140, 0x00070008);
-       return 0;
-}
-
-struct nouveau_oclass *
-nv31_bus_oclass = &(struct nv04_bus_impl) {
-       .base.handle = NV_SUBDEV(BUS, 0x31),
-       .base.ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nv04_bus_ctor,
-               .dtor = _nouveau_bus_dtor,
-               .init = nv31_bus_init,
-               .fini = _nouveau_bus_fini,
-       },
-       .intr = nv31_bus_intr,
-}.base;
diff --git a/drivers/gpu/drm/nouveau/core/subdev/bus/nv50.c b/drivers/gpu/drm/nouveau/core/subdev/bus/nv50.c
deleted file mode 100644 (file)
index 11918f7..0000000
+++ /dev/null
@@ -1,105 +0,0 @@
-/*
- * Copyright 2012 Nouveau Community
- *
- * 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 <martin.peres@labri.fr>
- *          Ben Skeggs
- */
-
-#include <subdev/timer.h>
-
-#include "nv04.h"
-
-static int
-nv50_bus_hwsq_exec(struct nouveau_bus *pbus, u32 *data, u32 size)
-{
-       struct nv50_bus_priv *priv = (void *)pbus;
-       int i;
-
-       nv_mask(pbus, 0x001098, 0x00000008, 0x00000000);
-       nv_wr32(pbus, 0x001304, 0x00000000);
-       for (i = 0; i < size; i++)
-               nv_wr32(priv, 0x001400 + (i * 4), data[i]);
-       nv_mask(pbus, 0x001098, 0x00000018, 0x00000018);
-       nv_wr32(pbus, 0x00130c, 0x00000003);
-
-       return nv_wait(pbus, 0x001308, 0x00000100, 0x00000000) ? 0 : -ETIMEDOUT;
-}
-
-void
-nv50_bus_intr(struct nouveau_subdev *subdev)
-{
-       struct nouveau_bus *pbus = nouveau_bus(subdev);
-       u32 stat = nv_rd32(pbus, 0x001100) & nv_rd32(pbus, 0x001140);
-
-       if (stat & 0x00000008) {
-               u32 addr = nv_rd32(pbus, 0x009084);
-               u32 data = nv_rd32(pbus, 0x009088);
-
-               nv_error(pbus, "MMIO %s of 0x%08x FAULT at 0x%06x\n",
-                        (addr & 0x00000002) ? "write" : "read", data,
-                        (addr & 0x00fffffc));
-
-               stat &= ~0x00000008;
-               nv_wr32(pbus, 0x001100, 0x00000008);
-       }
-
-       if (stat & 0x00010000) {
-               subdev = nouveau_subdev(pbus, NVDEV_SUBDEV_THERM);
-               if (subdev && subdev->intr)
-                       subdev->intr(subdev);
-               stat &= ~0x00010000;
-               nv_wr32(pbus, 0x001100, 0x00010000);
-       }
-
-       if (stat) {
-               nv_error(pbus, "unknown intr 0x%08x\n", stat);
-               nv_mask(pbus, 0x001140, stat, 0);
-       }
-}
-
-int
-nv50_bus_init(struct nouveau_object *object)
-{
-       struct nv04_bus_priv *priv = (void *)object;
-       int ret;
-
-       ret = nouveau_bus_init(&priv->base);
-       if (ret)
-               return ret;
-
-       nv_wr32(priv, 0x001100, 0xffffffff);
-       nv_wr32(priv, 0x001140, 0x00010008);
-       return 0;
-}
-
-struct nouveau_oclass *
-nv50_bus_oclass = &(struct nv04_bus_impl) {
-       .base.handle = NV_SUBDEV(BUS, 0x50),
-       .base.ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nv04_bus_ctor,
-               .dtor = _nouveau_bus_dtor,
-               .init = nv50_bus_init,
-               .fini = _nouveau_bus_fini,
-       },
-       .intr = nv50_bus_intr,
-       .hwsq_exec = nv50_bus_hwsq_exec,
-       .hwsq_size = 64,
-}.base;
diff --git a/drivers/gpu/drm/nouveau/core/subdev/bus/nv94.c b/drivers/gpu/drm/nouveau/core/subdev/bus/nv94.c
deleted file mode 100644 (file)
index d365905..0000000
+++ /dev/null
@@ -1,59 +0,0 @@
-/*
- * Copyright 2012 Nouveau Community
- *
- * 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 <martin.peres@labri.fr>
- *          Ben Skeggs
- */
-
-#include <subdev/timer.h>
-
-#include "nv04.h"
-
-static int
-nv94_bus_hwsq_exec(struct nouveau_bus *pbus, u32 *data, u32 size)
-{
-       struct nv50_bus_priv *priv = (void *)pbus;
-       int i;
-
-       nv_mask(pbus, 0x001098, 0x00000008, 0x00000000);
-       nv_wr32(pbus, 0x001304, 0x00000000);
-       nv_wr32(pbus, 0x001318, 0x00000000);
-       for (i = 0; i < size; i++)
-               nv_wr32(priv, 0x080000 + (i * 4), data[i]);
-       nv_mask(pbus, 0x001098, 0x00000018, 0x00000018);
-       nv_wr32(pbus, 0x00130c, 0x00000001);
-
-       return nv_wait(pbus, 0x001308, 0x00000100, 0x00000000) ? 0 : -ETIMEDOUT;
-}
-
-struct nouveau_oclass *
-nv94_bus_oclass = &(struct nv04_bus_impl) {
-       .base.handle = NV_SUBDEV(BUS, 0x94),
-       .base.ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nv04_bus_ctor,
-               .dtor = _nouveau_bus_dtor,
-               .init = nv50_bus_init,
-               .fini = _nouveau_bus_fini,
-       },
-       .intr = nv50_bus_intr,
-       .hwsq_exec = nv94_bus_hwsq_exec,
-       .hwsq_size = 128,
-}.base;
diff --git a/drivers/gpu/drm/nouveau/core/subdev/bus/nvc0.c b/drivers/gpu/drm/nouveau/core/subdev/bus/nvc0.c
deleted file mode 100644 (file)
index 73839d7..0000000
+++ /dev/null
@@ -1,81 +0,0 @@
-/*
- * Copyright 2012 Nouveau Community
- *
- * 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 <martin.peres@labri.fr>
- *          Ben Skeggs
- */
-
-#include "nv04.h"
-
-static void
-nvc0_bus_intr(struct nouveau_subdev *subdev)
-{
-       struct nouveau_bus *pbus = nouveau_bus(subdev);
-       u32 stat = nv_rd32(pbus, 0x001100) & nv_rd32(pbus, 0x001140);
-
-       if (stat & 0x0000000e) {
-               u32 addr = nv_rd32(pbus, 0x009084);
-               u32 data = nv_rd32(pbus, 0x009088);
-
-               nv_error(pbus, "MMIO %s of 0x%08x FAULT at 0x%06x [ %s%s%s]\n",
-                        (addr & 0x00000002) ? "write" : "read", data,
-                        (addr & 0x00fffffc),
-                        (stat & 0x00000002) ? "!ENGINE " : "",
-                        (stat & 0x00000004) ? "IBUS " : "",
-                        (stat & 0x00000008) ? "TIMEOUT " : "");
-
-               nv_wr32(pbus, 0x009084, 0x00000000);
-               nv_wr32(pbus, 0x001100, (stat & 0x0000000e));
-               stat &= ~0x0000000e;
-       }
-
-       if (stat) {
-               nv_error(pbus, "unknown intr 0x%08x\n", stat);
-               nv_mask(pbus, 0x001140, stat, 0x00000000);
-       }
-}
-
-static int
-nvc0_bus_init(struct nouveau_object *object)
-{
-       struct nv04_bus_priv *priv = (void *)object;
-       int ret;
-
-       ret = nouveau_bus_init(&priv->base);
-       if (ret)
-               return ret;
-
-       nv_wr32(priv, 0x001100, 0xffffffff);
-       nv_wr32(priv, 0x001140, 0x0000000e);
-       return 0;
-}
-
-struct nouveau_oclass *
-nvc0_bus_oclass = &(struct nv04_bus_impl) {
-       .base.handle = NV_SUBDEV(BUS, 0xc0),
-       .base.ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nv04_bus_ctor,
-               .dtor = _nouveau_bus_dtor,
-               .init = nvc0_bus_init,
-               .fini = _nouveau_bus_fini,
-       },
-       .intr = nvc0_bus_intr,
-}.base;
diff --git a/drivers/gpu/drm/nouveau/core/subdev/clock/base.c b/drivers/gpu/drm/nouveau/core/subdev/clock/base.c
deleted file mode 100644 (file)
index e51b72d..0000000
+++ /dev/null
@@ -1,597 +0,0 @@
-/*
- * Copyright 2013 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 <core/option.h>
-
-#include <subdev/clock.h>
-#include <subdev/therm.h>
-#include <subdev/volt.h>
-#include <subdev/fb.h>
-
-#include <subdev/bios.h>
-#include <subdev/bios/boost.h>
-#include <subdev/bios/cstep.h>
-#include <subdev/bios/perf.h>
-
-/******************************************************************************
- * misc
- *****************************************************************************/
-static u32
-nouveau_clock_adjust(struct nouveau_clock *clk, bool adjust,
-                    u8 pstate, u8 domain, u32 input)
-{
-       struct nouveau_bios *bios = nouveau_bios(clk);
-       struct nvbios_boostE boostE;
-       u8  ver, hdr, cnt, len;
-       u16 data;
-
-       data = nvbios_boostEm(bios, pstate, &ver, &hdr, &cnt, &len, &boostE);
-       if (data) {
-               struct nvbios_boostS boostS;
-               u8  idx = 0, sver, shdr;
-               u16 subd;
-
-               input = max(boostE.min, input);
-               input = min(boostE.max, input);
-               do {
-                       sver = ver;
-                       shdr = hdr;
-                       subd = nvbios_boostSp(bios, idx++, data, &sver, &shdr,
-                                             cnt, len, &boostS);
-                       if (subd && boostS.domain == domain) {
-                               if (adjust)
-                                       input = input * boostS.percent / 100;
-                               input = max(boostS.min, input);
-                               input = min(boostS.max, input);
-                               break;
-                       }
-               } while (subd);
-       }
-
-       return input;
-}
-
-/******************************************************************************
- * C-States
- *****************************************************************************/
-static int
-nouveau_cstate_prog(struct nouveau_clock *clk,
-                   struct nouveau_pstate *pstate, int cstatei)
-{
-       struct nouveau_therm *ptherm = nouveau_therm(clk);
-       struct nouveau_volt *volt = nouveau_volt(clk);
-       struct nouveau_cstate *cstate;
-       int ret;
-
-       if (!list_empty(&pstate->list)) {
-               cstate = list_entry(pstate->list.prev, typeof(*cstate), head);
-       } else {
-               cstate = &pstate->base;
-       }
-
-       if (ptherm) {
-               ret = nouveau_therm_cstate(ptherm, pstate->fanspeed, +1);
-               if (ret && ret != -ENODEV) {
-                       nv_error(clk, "failed to raise fan speed: %d\n", ret);
-                       return ret;
-               }
-       }
-
-       if (volt) {
-               ret = volt->set_id(volt, cstate->voltage, +1);
-               if (ret && ret != -ENODEV) {
-                       nv_error(clk, "failed to raise voltage: %d\n", ret);
-                       return ret;
-               }
-       }
-
-       ret = clk->calc(clk, cstate);
-       if (ret == 0) {
-               ret = clk->prog(clk);
-               clk->tidy(clk);
-       }
-
-       if (volt) {
-               ret = volt->set_id(volt, cstate->voltage, -1);
-               if (ret && ret != -ENODEV)
-                       nv_error(clk, "failed to lower voltage: %d\n", ret);
-       }
-
-       if (ptherm) {
-               ret = nouveau_therm_cstate(ptherm, pstate->fanspeed, -1);
-               if (ret && ret != -ENODEV)
-                       nv_error(clk, "failed to lower fan speed: %d\n", ret);
-       }
-
-       return 0;
-}
-
-static void
-nouveau_cstate_del(struct nouveau_cstate *cstate)
-{
-       list_del(&cstate->head);
-       kfree(cstate);
-}
-
-static int
-nouveau_cstate_new(struct nouveau_clock *clk, int idx,
-                  struct nouveau_pstate *pstate)
-{
-       struct nouveau_bios *bios = nouveau_bios(clk);
-       struct nouveau_clocks *domain = clk->domains;
-       struct nouveau_cstate *cstate = NULL;
-       struct nvbios_cstepX cstepX;
-       u8  ver, hdr;
-       u16 data;
-
-       data = nvbios_cstepXp(bios, idx, &ver, &hdr, &cstepX);
-       if (!data)
-               return -ENOENT;
-
-       cstate = kzalloc(sizeof(*cstate), GFP_KERNEL);
-       if (!cstate)
-               return -ENOMEM;
-
-       *cstate = pstate->base;
-       cstate->voltage = cstepX.voltage;
-
-       while (domain && domain->name != nv_clk_src_max) {
-               if (domain->flags & NVKM_CLK_DOM_FLAG_CORE) {
-                       u32 freq = nouveau_clock_adjust(clk, true,
-                                                       pstate->pstate,
-                                                       domain->bios,
-                                                       cstepX.freq);
-                       cstate->domain[domain->name] = freq;
-               }
-               domain++;
-       }
-
-       list_add(&cstate->head, &pstate->list);
-       return 0;
-}
-
-/******************************************************************************
- * P-States
- *****************************************************************************/
-static int
-nouveau_pstate_prog(struct nouveau_clock *clk, int pstatei)
-{
-       struct nouveau_fb *pfb = nouveau_fb(clk);
-       struct nouveau_pstate *pstate;
-       int ret, idx = 0;
-
-       list_for_each_entry(pstate, &clk->states, head) {
-               if (idx++ == pstatei)
-                       break;
-       }
-
-       nv_debug(clk, "setting performance state %d\n", pstatei);
-       clk->pstate = pstatei;
-
-       if (pfb->ram->calc) {
-               int khz = pstate->base.domain[nv_clk_src_mem];
-               do {
-                       ret = pfb->ram->calc(pfb, khz);
-                       if (ret == 0)
-                               ret = pfb->ram->prog(pfb);
-               } while (ret > 0);
-               pfb->ram->tidy(pfb);
-       }
-
-       return nouveau_cstate_prog(clk, pstate, 0);
-}
-
-static void
-nouveau_pstate_work(struct work_struct *work)
-{
-       struct nouveau_clock *clk = container_of(work, typeof(*clk), work);
-       int pstate;
-
-       if (!atomic_xchg(&clk->waiting, 0))
-               return;
-       clk->pwrsrc = power_supply_is_system_supplied();
-
-       nv_trace(clk, "P %d PWR %d U(AC) %d U(DC) %d A %d T %d D %d\n",
-                clk->pstate, clk->pwrsrc, clk->ustate_ac, clk->ustate_dc,
-                clk->astate, clk->tstate, clk->dstate);
-
-       pstate = clk->pwrsrc ? clk->ustate_ac : clk->ustate_dc;
-       if (clk->state_nr && pstate != -1) {
-               pstate = (pstate < 0) ? clk->astate : pstate;
-               pstate = min(pstate, clk->state_nr - 1 - clk->tstate);
-               pstate = max(pstate, clk->dstate);
-       } else {
-               pstate = clk->pstate = -1;
-       }
-
-       nv_trace(clk, "-> %d\n", pstate);
-       if (pstate != clk->pstate) {
-               int ret = nouveau_pstate_prog(clk, pstate);
-               if (ret) {
-                       nv_error(clk, "error setting pstate %d: %d\n",
-                                pstate, ret);
-               }
-       }
-
-       wake_up_all(&clk->wait);
-       nvkm_notify_get(&clk->pwrsrc_ntfy);
-}
-
-static int
-nouveau_pstate_calc(struct nouveau_clock *clk, bool wait)
-{
-       atomic_set(&clk->waiting, 1);
-       schedule_work(&clk->work);
-       if (wait)
-               wait_event(clk->wait, !atomic_read(&clk->waiting));
-       return 0;
-}
-
-static void
-nouveau_pstate_info(struct nouveau_clock *clk, struct nouveau_pstate *pstate)
-{
-       struct nouveau_clocks *clock = clk->domains - 1;
-       struct nouveau_cstate *cstate;
-       char info[3][32] = { "", "", "" };
-       char name[4] = "--";
-       int i = -1;
-
-       if (pstate->pstate != 0xff)
-               snprintf(name, sizeof(name), "%02x", pstate->pstate);
-
-       while ((++clock)->name != nv_clk_src_max) {
-               u32 lo = pstate->base.domain[clock->name];
-               u32 hi = lo;
-               if (hi == 0)
-                       continue;
-
-               nv_debug(clk, "%02x: %10d KHz\n", clock->name, lo);
-               list_for_each_entry(cstate, &pstate->list, head) {
-                       u32 freq = cstate->domain[clock->name];
-                       lo = min(lo, freq);
-                       hi = max(hi, freq);
-                       nv_debug(clk, "%10d KHz\n", freq);
-               }
-
-               if (clock->mname && ++i < ARRAY_SIZE(info)) {
-                       lo /= clock->mdiv;
-                       hi /= clock->mdiv;
-                       if (lo == hi) {
-                               snprintf(info[i], sizeof(info[i]), "%s %d MHz",
-                                        clock->mname, lo);
-                       } else {
-                               snprintf(info[i], sizeof(info[i]),
-                                        "%s %d-%d MHz", clock->mname, lo, hi);
-                       }
-               }
-       }
-
-       nv_info(clk, "%s: %s %s %s\n", name, info[0], info[1], info[2]);
-}
-
-static void
-nouveau_pstate_del(struct nouveau_pstate *pstate)
-{
-       struct nouveau_cstate *cstate, *temp;
-
-       list_for_each_entry_safe(cstate, temp, &pstate->list, head) {
-               nouveau_cstate_del(cstate);
-       }
-
-       list_del(&pstate->head);
-       kfree(pstate);
-}
-
-static int
-nouveau_pstate_new(struct nouveau_clock *clk, int idx)
-{
-       struct nouveau_bios *bios = nouveau_bios(clk);
-       struct nouveau_clocks *domain = clk->domains - 1;
-       struct nouveau_pstate *pstate;
-       struct nouveau_cstate *cstate;
-       struct nvbios_cstepE cstepE;
-       struct nvbios_perfE perfE;
-       u8  ver, hdr, cnt, len;
-       u16 data;
-
-       data = nvbios_perfEp(bios, idx, &ver, &hdr, &cnt, &len, &perfE);
-       if (!data)
-               return -EINVAL;
-       if (perfE.pstate == 0xff)
-               return 0;
-
-       pstate = kzalloc(sizeof(*pstate), GFP_KERNEL);
-       cstate = &pstate->base;
-       if (!pstate)
-               return -ENOMEM;
-
-       INIT_LIST_HEAD(&pstate->list);
-
-       pstate->pstate = perfE.pstate;
-       pstate->fanspeed = perfE.fanspeed;
-       cstate->voltage = perfE.voltage;
-       cstate->domain[nv_clk_src_core] = perfE.core;
-       cstate->domain[nv_clk_src_shader] = perfE.shader;
-       cstate->domain[nv_clk_src_mem] = perfE.memory;
-       cstate->domain[nv_clk_src_vdec] = perfE.vdec;
-       cstate->domain[nv_clk_src_dom6] = perfE.disp;
-
-       while (ver >= 0x40 && (++domain)->name != nv_clk_src_max) {
-               struct nvbios_perfS perfS;
-               u8  sver = ver, shdr = hdr;
-               u32 perfSe = nvbios_perfSp(bios, data, domain->bios,
-                                         &sver, &shdr, cnt, len, &perfS);
-               if (perfSe == 0 || sver != 0x40)
-                       continue;
-
-               if (domain->flags & NVKM_CLK_DOM_FLAG_CORE) {
-                       perfS.v40.freq = nouveau_clock_adjust(clk, false,
-                                                             pstate->pstate,
-                                                             domain->bios,
-                                                             perfS.v40.freq);
-               }
-
-               cstate->domain[domain->name] = perfS.v40.freq;
-       }
-
-       data = nvbios_cstepEm(bios, pstate->pstate, &ver, &hdr, &cstepE);
-       if (data) {
-               int idx = cstepE.index;
-               do {
-                       nouveau_cstate_new(clk, idx, pstate);
-               } while(idx--);
-       }
-
-       nouveau_pstate_info(clk, pstate);
-       list_add_tail(&pstate->head, &clk->states);
-       clk->state_nr++;
-       return 0;
-}
-
-/******************************************************************************
- * Adjustment triggers
- *****************************************************************************/
-static int
-nouveau_clock_ustate_update(struct nouveau_clock *clk, int req)
-{
-       struct nouveau_pstate *pstate;
-       int i = 0;
-
-       if (!clk->allow_reclock)
-               return -ENOSYS;
-
-       if (req != -1 && req != -2) {
-               list_for_each_entry(pstate, &clk->states, head) {
-                       if (pstate->pstate == req)
-                               break;
-                       i++;
-               }
-
-               if (pstate->pstate != req)
-                       return -EINVAL;
-               req = i;
-       }
-
-       return req + 2;
-}
-
-static int
-nouveau_clock_nstate(struct nouveau_clock *clk, const char *mode, int arglen)
-{
-       int ret = 1;
-
-       if (strncasecmpz(mode, "disabled", arglen)) {
-               char save = mode[arglen];
-               long v;
-
-               ((char *)mode)[arglen] = '\0';
-               if (!kstrtol(mode, 0, &v)) {
-                       ret = nouveau_clock_ustate_update(clk, v);
-                       if (ret < 0)
-                               ret = 1;
-               }
-               ((char *)mode)[arglen] = save;
-       }
-
-       return ret - 2;
-}
-
-int
-nouveau_clock_ustate(struct nouveau_clock *clk, int req, int pwr)
-{
-       int ret = nouveau_clock_ustate_update(clk, req);
-       if (ret >= 0) {
-               if (ret -= 2, pwr) clk->ustate_ac = ret;
-               else               clk->ustate_dc = ret;
-               return nouveau_pstate_calc(clk, true);
-       }
-       return ret;
-}
-
-int
-nouveau_clock_astate(struct nouveau_clock *clk, int req, int rel)
-{
-       if (!rel) clk->astate  = req;
-       if ( rel) clk->astate += rel;
-       clk->astate = min(clk->astate, clk->state_nr - 1);
-       clk->astate = max(clk->astate, 0);
-       return nouveau_pstate_calc(clk, true);
-}
-
-int
-nouveau_clock_tstate(struct nouveau_clock *clk, int req, int rel)
-{
-       if (!rel) clk->tstate  = req;
-       if ( rel) clk->tstate += rel;
-       clk->tstate = min(clk->tstate, 0);
-       clk->tstate = max(clk->tstate, -(clk->state_nr - 1));
-       return nouveau_pstate_calc(clk, true);
-}
-
-int
-nouveau_clock_dstate(struct nouveau_clock *clk, int req, int rel)
-{
-       if (!rel) clk->dstate  = req;
-       if ( rel) clk->dstate += rel;
-       clk->dstate = min(clk->dstate, clk->state_nr - 1);
-       clk->dstate = max(clk->dstate, 0);
-       return nouveau_pstate_calc(clk, true);
-}
-
-static int
-nouveau_clock_pwrsrc(struct nvkm_notify *notify)
-{
-       struct nouveau_clock *clk =
-               container_of(notify, typeof(*clk), pwrsrc_ntfy);
-       nouveau_pstate_calc(clk, false);
-       return NVKM_NOTIFY_DROP;
-}
-
-/******************************************************************************
- * subdev base class implementation
- *****************************************************************************/
-
-int
-_nouveau_clock_fini(struct nouveau_object *object, bool suspend)
-{
-       struct nouveau_clock *clk = (void *)object;
-       nvkm_notify_put(&clk->pwrsrc_ntfy);
-       return nouveau_subdev_fini(&clk->base, suspend);
-}
-
-int
-_nouveau_clock_init(struct nouveau_object *object)
-{
-       struct nouveau_clock *clk = (void *)object;
-       struct nouveau_clocks *clock = clk->domains;
-       int ret;
-
-       ret = nouveau_subdev_init(&clk->base);
-       if (ret)
-               return ret;
-
-       memset(&clk->bstate, 0x00, sizeof(clk->bstate));
-       INIT_LIST_HEAD(&clk->bstate.list);
-       clk->bstate.pstate = 0xff;
-
-       while (clock->name != nv_clk_src_max) {
-               ret = clk->read(clk, clock->name);
-               if (ret < 0) {
-                       nv_error(clk, "%02x freq unknown\n", clock->name);
-                       return ret;
-               }
-               clk->bstate.base.domain[clock->name] = ret;
-               clock++;
-       }
-
-       nouveau_pstate_info(clk, &clk->bstate);
-
-       clk->astate = clk->state_nr - 1;
-       clk->tstate = 0;
-       clk->dstate = 0;
-       clk->pstate = -1;
-       nouveau_pstate_calc(clk, true);
-       return 0;
-}
-
-void
-_nouveau_clock_dtor(struct nouveau_object *object)
-{
-       struct nouveau_clock *clk = (void *)object;
-       struct nouveau_pstate *pstate, *temp;
-
-       nvkm_notify_fini(&clk->pwrsrc_ntfy);
-
-       list_for_each_entry_safe(pstate, temp, &clk->states, head) {
-               nouveau_pstate_del(pstate);
-       }
-
-       nouveau_subdev_destroy(&clk->base);
-}
-
-int
-nouveau_clock_create_(struct nouveau_object *parent,
-                     struct nouveau_object *engine,
-                     struct nouveau_oclass *oclass,
-                     struct nouveau_clocks *clocks,
-                     struct nouveau_pstate *pstates, int nb_pstates,
-                     bool allow_reclock,
-                     int length, void **object)
-{
-       struct nouveau_device *device = nv_device(parent);
-       struct nouveau_clock *clk;
-       int ret, idx, arglen;
-       const char *mode;
-
-       ret = nouveau_subdev_create_(parent, engine, oclass, 0, "CLK",
-                                    "clock", length, object);
-       clk = *object;
-       if (ret)
-               return ret;
-
-       INIT_LIST_HEAD(&clk->states);
-       clk->domains = clocks;
-       clk->ustate_ac = -1;
-       clk->ustate_dc = -1;
-
-       INIT_WORK(&clk->work, nouveau_pstate_work);
-       init_waitqueue_head(&clk->wait);
-       atomic_set(&clk->waiting, 0);
-
-       /* If no pstates are provided, try and fetch them from the BIOS */
-       if (!pstates) {
-               idx = 0;
-               do {
-                       ret = nouveau_pstate_new(clk, idx++);
-               } while (ret == 0);
-       } else {
-               for (idx = 0; idx < nb_pstates; idx++)
-                       list_add_tail(&pstates[idx].head, &clk->states);
-               clk->state_nr = nb_pstates;
-       }
-
-       clk->allow_reclock = allow_reclock;
-
-       ret = nvkm_notify_init(NULL, &device->event, nouveau_clock_pwrsrc, true,
-                              NULL, 0, 0, &clk->pwrsrc_ntfy);
-       if (ret)
-               return ret;
-
-       mode = nouveau_stropt(device->cfgopt, "NvClkMode", &arglen);
-       if (mode) {
-               clk->ustate_ac = nouveau_clock_nstate(clk, mode, arglen);
-               clk->ustate_dc = nouveau_clock_nstate(clk, mode, arglen);
-       }
-
-       mode = nouveau_stropt(device->cfgopt, "NvClkModeAC", &arglen);
-       if (mode)
-               clk->ustate_ac = nouveau_clock_nstate(clk, mode, arglen);
-
-       mode = nouveau_stropt(device->cfgopt, "NvClkModeDC", &arglen);
-       if (mode)
-               clk->ustate_dc = nouveau_clock_nstate(clk, mode, arglen);
-
-
-       return 0;
-}
diff --git a/drivers/gpu/drm/nouveau/core/subdev/clock/gk20a.c b/drivers/gpu/drm/nouveau/core/subdev/clock/gk20a.c
deleted file mode 100644 (file)
index fb4fad3..0000000
+++ /dev/null
@@ -1,680 +0,0 @@
-/*
- * Copyright (c) 2014, NVIDIA CORPORATION. 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 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.
- *
- * Shamelessly ripped off from ChromeOS's gk20a/clk_pllg.c
- *
- */
-
-#define MHZ (1000 * 1000)
-
-#define MASK(w)        ((1 << w) - 1)
-
-#define SYS_GPCPLL_CFG_BASE                    0x00137000
-#define GPC_BCASE_GPCPLL_CFG_BASE              0x00132800
-
-#define GPCPLL_CFG             (SYS_GPCPLL_CFG_BASE + 0)
-#define GPCPLL_CFG_ENABLE      BIT(0)
-#define GPCPLL_CFG_IDDQ                BIT(1)
-#define GPCPLL_CFG_LOCK_DET_OFF        BIT(4)
-#define GPCPLL_CFG_LOCK                BIT(17)
-
-#define GPCPLL_COEFF           (SYS_GPCPLL_CFG_BASE + 4)
-#define GPCPLL_COEFF_M_SHIFT   0
-#define GPCPLL_COEFF_M_WIDTH   8
-#define GPCPLL_COEFF_N_SHIFT   8
-#define GPCPLL_COEFF_N_WIDTH   8
-#define GPCPLL_COEFF_P_SHIFT   16
-#define GPCPLL_COEFF_P_WIDTH   6
-
-#define GPCPLL_CFG2                    (SYS_GPCPLL_CFG_BASE + 0xc)
-#define GPCPLL_CFG2_SETUP2_SHIFT       16
-#define GPCPLL_CFG2_PLL_STEPA_SHIFT    24
-
-#define GPCPLL_CFG3                    (SYS_GPCPLL_CFG_BASE + 0x18)
-#define GPCPLL_CFG3_PLL_STEPB_SHIFT    16
-
-#define GPCPLL_NDIV_SLOWDOWN                   (SYS_GPCPLL_CFG_BASE + 0x1c)
-#define GPCPLL_NDIV_SLOWDOWN_NDIV_LO_SHIFT     0
-#define GPCPLL_NDIV_SLOWDOWN_NDIV_MID_SHIFT    8
-#define GPCPLL_NDIV_SLOWDOWN_STEP_SIZE_LO2MID_SHIFT    16
-#define GPCPLL_NDIV_SLOWDOWN_SLOWDOWN_USING_PLL_SHIFT  22
-#define GPCPLL_NDIV_SLOWDOWN_EN_DYNRAMP_SHIFT  31
-
-#define SEL_VCO                                (SYS_GPCPLL_CFG_BASE + 0x100)
-#define SEL_VCO_GPC2CLK_OUT_SHIFT      0
-
-#define GPC2CLK_OUT                    (SYS_GPCPLL_CFG_BASE + 0x250)
-#define GPC2CLK_OUT_SDIV14_INDIV4_WIDTH        1
-#define GPC2CLK_OUT_SDIV14_INDIV4_SHIFT        31
-#define GPC2CLK_OUT_SDIV14_INDIV4_MODE 1
-#define GPC2CLK_OUT_VCODIV_WIDTH       6
-#define GPC2CLK_OUT_VCODIV_SHIFT       8
-#define GPC2CLK_OUT_VCODIV1            0
-#define GPC2CLK_OUT_VCODIV_MASK                (MASK(GPC2CLK_OUT_VCODIV_WIDTH) << \
-                                       GPC2CLK_OUT_VCODIV_SHIFT)
-#define        GPC2CLK_OUT_BYPDIV_WIDTH        6
-#define GPC2CLK_OUT_BYPDIV_SHIFT       0
-#define GPC2CLK_OUT_BYPDIV31           0x3c
-#define GPC2CLK_OUT_INIT_MASK  ((MASK(GPC2CLK_OUT_SDIV14_INDIV4_WIDTH) << \
-               GPC2CLK_OUT_SDIV14_INDIV4_SHIFT)\
-               | (MASK(GPC2CLK_OUT_VCODIV_WIDTH) << GPC2CLK_OUT_VCODIV_SHIFT)\
-               | (MASK(GPC2CLK_OUT_BYPDIV_WIDTH) << GPC2CLK_OUT_BYPDIV_SHIFT))
-#define GPC2CLK_OUT_INIT_VAL   ((GPC2CLK_OUT_SDIV14_INDIV4_MODE << \
-               GPC2CLK_OUT_SDIV14_INDIV4_SHIFT) \
-               | (GPC2CLK_OUT_VCODIV1 << GPC2CLK_OUT_VCODIV_SHIFT) \
-               | (GPC2CLK_OUT_BYPDIV31 << GPC2CLK_OUT_BYPDIV_SHIFT))
-
-#define GPC_BCAST_NDIV_SLOWDOWN_DEBUG  (GPC_BCASE_GPCPLL_CFG_BASE + 0xa0)
-#define GPC_BCAST_NDIV_SLOWDOWN_DEBUG_PLL_DYNRAMP_DONE_SYNCED_SHIFT    24
-#define GPC_BCAST_NDIV_SLOWDOWN_DEBUG_PLL_DYNRAMP_DONE_SYNCED_MASK \
-           (0x1 << GPC_BCAST_NDIV_SLOWDOWN_DEBUG_PLL_DYNRAMP_DONE_SYNCED_SHIFT)
-
-#include <subdev/clock.h>
-#include <subdev/timer.h>
-
-#ifdef __KERNEL__
-#include <nouveau_platform.h>
-#endif
-
-static const u8 pl_to_div[] = {
-/* PL:   0, 1, 2, 3, 4, 5, 6,  7,  8,  9, 10, 11, 12, 13, 14 */
-/* p: */ 1, 2, 3, 4, 5, 6, 8, 10, 12, 16, 12, 16, 20, 24, 32,
-};
-
-/* All frequencies in Mhz */
-struct gk20a_clk_pllg_params {
-       u32 min_vco, max_vco;
-       u32 min_u, max_u;
-       u32 min_m, max_m;
-       u32 min_n, max_n;
-       u32 min_pl, max_pl;
-};
-
-static const struct gk20a_clk_pllg_params gk20a_pllg_params = {
-       .min_vco = 1000, .max_vco = 2064,
-       .min_u = 12, .max_u = 38,
-       .min_m = 1, .max_m = 255,
-       .min_n = 8, .max_n = 255,
-       .min_pl = 1, .max_pl = 32,
-};
-
-struct gk20a_clock_priv {
-       struct nouveau_clock base;
-       const struct gk20a_clk_pllg_params *params;
-       u32 m, n, pl;
-       u32 parent_rate;
-};
-#define to_gk20a_clock(base) container_of(base, struct gk20a_clock_priv, base)
-
-static void
-gk20a_pllg_read_mnp(struct gk20a_clock_priv *priv)
-{
-       u32 val;
-
-       val = nv_rd32(priv, GPCPLL_COEFF);
-       priv->m = (val >> GPCPLL_COEFF_M_SHIFT) & MASK(GPCPLL_COEFF_M_WIDTH);
-       priv->n = (val >> GPCPLL_COEFF_N_SHIFT) & MASK(GPCPLL_COEFF_N_WIDTH);
-       priv->pl = (val >> GPCPLL_COEFF_P_SHIFT) & MASK(GPCPLL_COEFF_P_WIDTH);
-}
-
-static u32
-gk20a_pllg_calc_rate(struct gk20a_clock_priv *priv)
-{
-       u32 rate;
-       u32 divider;
-
-       rate = priv->parent_rate * priv->n;
-       divider = priv->m * pl_to_div[priv->pl];
-       do_div(rate, divider);
-
-       return rate / 2;
-}
-
-static int
-gk20a_pllg_calc_mnp(struct gk20a_clock_priv *priv, unsigned long rate)
-{
-       u32 target_clk_f, ref_clk_f, target_freq;
-       u32 min_vco_f, max_vco_f;
-       u32 low_pl, high_pl, best_pl;
-       u32 target_vco_f, vco_f;
-       u32 best_m, best_n;
-       u32 u_f;
-       u32 m, n, n2;
-       u32 delta, lwv, best_delta = ~0;
-       u32 pl;
-
-       target_clk_f = rate * 2 / MHZ;
-       ref_clk_f = priv->parent_rate / MHZ;
-
-       max_vco_f = priv->params->max_vco;
-       min_vco_f = priv->params->min_vco;
-       best_m = priv->params->max_m;
-       best_n = priv->params->min_n;
-       best_pl = priv->params->min_pl;
-
-       target_vco_f = target_clk_f + target_clk_f / 50;
-       if (max_vco_f < target_vco_f)
-               max_vco_f = target_vco_f;
-
-       /* min_pl <= high_pl <= max_pl */
-       high_pl = (max_vco_f + target_vco_f - 1) / target_vco_f;
-       high_pl = min(high_pl, priv->params->max_pl);
-       high_pl = max(high_pl, priv->params->min_pl);
-
-       /* min_pl <= low_pl <= max_pl */
-       low_pl = min_vco_f / target_vco_f;
-       low_pl = min(low_pl, priv->params->max_pl);
-       low_pl = max(low_pl, priv->params->min_pl);
-
-       /* Find Indices of high_pl and low_pl */
-       for (pl = 0; pl < ARRAY_SIZE(pl_to_div) - 1; pl++) {
-               if (pl_to_div[pl] >= low_pl) {
-                       low_pl = pl;
-                       break;
-               }
-       }
-       for (pl = 0; pl < ARRAY_SIZE(pl_to_div) - 1; pl++) {
-               if (pl_to_div[pl] >= high_pl) {
-                       high_pl = pl;
-                       break;
-               }
-       }
-
-       nv_debug(priv, "low_PL %d(div%d), high_PL %d(div%d)", low_pl,
-                pl_to_div[low_pl], high_pl, pl_to_div[high_pl]);
-
-       /* Select lowest possible VCO */
-       for (pl = low_pl; pl <= high_pl; pl++) {
-               target_vco_f = target_clk_f * pl_to_div[pl];
-               for (m = priv->params->min_m; m <= priv->params->max_m; m++) {
-                       u_f = ref_clk_f / m;
-
-                       if (u_f < priv->params->min_u)
-                               break;
-                       if (u_f > priv->params->max_u)
-                               continue;
-
-                       n = (target_vco_f * m) / ref_clk_f;
-                       n2 = ((target_vco_f * m) + (ref_clk_f - 1)) / ref_clk_f;
-
-                       if (n > priv->params->max_n)
-                               break;
-
-                       for (; n <= n2; n++) {
-                               if (n < priv->params->min_n)
-                                       continue;
-                               if (n > priv->params->max_n)
-                                       break;
-
-                               vco_f = ref_clk_f * n / m;
-
-                               if (vco_f >= min_vco_f && vco_f <= max_vco_f) {
-                                       lwv = (vco_f + (pl_to_div[pl] / 2))
-                                               / pl_to_div[pl];
-                                       delta = abs(lwv - target_clk_f);
-
-                                       if (delta < best_delta) {
-                                               best_delta = delta;
-                                               best_m = m;
-                                               best_n = n;
-                                               best_pl = pl;
-
-                                               if (best_delta == 0)
-                                                       goto found_match;
-                                       }
-                               }
-                       }
-               }
-       }
-
-found_match:
-       WARN_ON(best_delta == ~0);
-
-       if (best_delta != 0)
-               nv_debug(priv, "no best match for target @ %dMHz on gpc_pll",
-                        target_clk_f);
-
-       priv->m = best_m;
-       priv->n = best_n;
-       priv->pl = best_pl;
-
-       target_freq = gk20a_pllg_calc_rate(priv) / MHZ;
-
-       nv_debug(priv, "actual target freq %d MHz, M %d, N %d, PL %d(div%d)\n",
-                target_freq, priv->m, priv->n, priv->pl, pl_to_div[priv->pl]);
-
-       return 0;
-}
-
-static int
-gk20a_pllg_slide(struct gk20a_clock_priv *priv, u32 n)
-{
-       u32 val;
-       int ramp_timeout;
-
-       /* get old coefficients */
-       val = nv_rd32(priv, GPCPLL_COEFF);
-       /* do nothing if NDIV is the same */
-       if (n == ((val >> GPCPLL_COEFF_N_SHIFT) & MASK(GPCPLL_COEFF_N_WIDTH)))
-               return 0;
-
-       /* setup */
-       nv_mask(priv, GPCPLL_CFG2, 0xff << GPCPLL_CFG2_PLL_STEPA_SHIFT,
-               0x2b << GPCPLL_CFG2_PLL_STEPA_SHIFT);
-       nv_mask(priv, GPCPLL_CFG3, 0xff << GPCPLL_CFG3_PLL_STEPB_SHIFT,
-               0xb << GPCPLL_CFG3_PLL_STEPB_SHIFT);
-
-       /* pll slowdown mode */
-       nv_mask(priv, GPCPLL_NDIV_SLOWDOWN,
-               BIT(GPCPLL_NDIV_SLOWDOWN_SLOWDOWN_USING_PLL_SHIFT),
-               BIT(GPCPLL_NDIV_SLOWDOWN_SLOWDOWN_USING_PLL_SHIFT));
-
-       /* new ndiv ready for ramp */
-       val = nv_rd32(priv, GPCPLL_COEFF);
-       val &= ~(MASK(GPCPLL_COEFF_N_WIDTH) << GPCPLL_COEFF_N_SHIFT);
-       val |= (n & MASK(GPCPLL_COEFF_N_WIDTH)) << GPCPLL_COEFF_N_SHIFT;
-       udelay(1);
-       nv_wr32(priv, GPCPLL_COEFF, val);
-
-       /* dynamic ramp to new ndiv */
-       val = nv_rd32(priv, GPCPLL_NDIV_SLOWDOWN);
-       val |= 0x1 << GPCPLL_NDIV_SLOWDOWN_EN_DYNRAMP_SHIFT;
-       udelay(1);
-       nv_wr32(priv, GPCPLL_NDIV_SLOWDOWN, val);
-
-       for (ramp_timeout = 500; ramp_timeout > 0; ramp_timeout--) {
-               udelay(1);
-               val = nv_rd32(priv, GPC_BCAST_NDIV_SLOWDOWN_DEBUG);
-               if (val & GPC_BCAST_NDIV_SLOWDOWN_DEBUG_PLL_DYNRAMP_DONE_SYNCED_MASK)
-                       break;
-       }
-
-       /* exit slowdown mode */
-       nv_mask(priv, GPCPLL_NDIV_SLOWDOWN,
-               BIT(GPCPLL_NDIV_SLOWDOWN_SLOWDOWN_USING_PLL_SHIFT) |
-               BIT(GPCPLL_NDIV_SLOWDOWN_EN_DYNRAMP_SHIFT), 0);
-       nv_rd32(priv, GPCPLL_NDIV_SLOWDOWN);
-
-       if (ramp_timeout <= 0) {
-               nv_error(priv, "gpcpll dynamic ramp timeout\n");
-               return -ETIMEDOUT;
-       }
-
-       return 0;
-}
-
-static void
-_gk20a_pllg_enable(struct gk20a_clock_priv *priv)
-{
-       nv_mask(priv, GPCPLL_CFG, GPCPLL_CFG_ENABLE, GPCPLL_CFG_ENABLE);
-       nv_rd32(priv, GPCPLL_CFG);
-}
-
-static void
-_gk20a_pllg_disable(struct gk20a_clock_priv *priv)
-{
-       nv_mask(priv, GPCPLL_CFG, GPCPLL_CFG_ENABLE, 0);
-       nv_rd32(priv, GPCPLL_CFG);
-}
-
-static int
-_gk20a_pllg_program_mnp(struct gk20a_clock_priv *priv, bool allow_slide)
-{
-       u32 val, cfg;
-       u32 m_old, pl_old, n_lo;
-
-       /* get old coefficients */
-       val = nv_rd32(priv, GPCPLL_COEFF);
-       m_old = (val >> GPCPLL_COEFF_M_SHIFT) & MASK(GPCPLL_COEFF_M_WIDTH);
-       pl_old = (val >> GPCPLL_COEFF_P_SHIFT) & MASK(GPCPLL_COEFF_P_WIDTH);
-
-       /* do NDIV slide if there is no change in M and PL */
-       cfg = nv_rd32(priv, GPCPLL_CFG);
-       if (allow_slide && priv->m == m_old && priv->pl == pl_old &&
-           (cfg & GPCPLL_CFG_ENABLE)) {
-               return gk20a_pllg_slide(priv, priv->n);
-       }
-
-       /* slide down to NDIV_LO */
-       n_lo = DIV_ROUND_UP(m_old * priv->params->min_vco,
-                           priv->parent_rate / MHZ);
-       if (allow_slide && (cfg & GPCPLL_CFG_ENABLE)) {
-               int ret = gk20a_pllg_slide(priv, n_lo);
-
-               if (ret)
-                       return ret;
-       }
-
-       /* split FO-to-bypass jump in halfs by setting out divider 1:2 */
-       nv_mask(priv, GPC2CLK_OUT, GPC2CLK_OUT_VCODIV_MASK,
-               0x2 << GPC2CLK_OUT_VCODIV_SHIFT);
-
-       /* put PLL in bypass before programming it */
-       val = nv_rd32(priv, SEL_VCO);
-       val &= ~(BIT(SEL_VCO_GPC2CLK_OUT_SHIFT));
-       udelay(2);
-       nv_wr32(priv, SEL_VCO, val);
-
-       /* get out from IDDQ */
-       val = nv_rd32(priv, GPCPLL_CFG);
-       if (val & GPCPLL_CFG_IDDQ) {
-               val &= ~GPCPLL_CFG_IDDQ;
-               nv_wr32(priv, GPCPLL_CFG, val);
-               nv_rd32(priv, GPCPLL_CFG);
-               udelay(2);
-       }
-
-       _gk20a_pllg_disable(priv);
-
-       nv_debug(priv, "%s: m=%d n=%d pl=%d\n", __func__, priv->m, priv->n,
-                priv->pl);
-
-       n_lo = DIV_ROUND_UP(priv->m * priv->params->min_vco,
-                           priv->parent_rate / MHZ);
-       val = priv->m << GPCPLL_COEFF_M_SHIFT;
-       val |= (allow_slide ? n_lo : priv->n) << GPCPLL_COEFF_N_SHIFT;
-       val |= priv->pl << GPCPLL_COEFF_P_SHIFT;
-       nv_wr32(priv, GPCPLL_COEFF, val);
-
-       _gk20a_pllg_enable(priv);
-
-       val = nv_rd32(priv, GPCPLL_CFG);
-       if (val & GPCPLL_CFG_LOCK_DET_OFF) {
-               val &= ~GPCPLL_CFG_LOCK_DET_OFF;
-               nv_wr32(priv, GPCPLL_CFG, val);
-       }
-
-       if (!nouveau_timer_wait_eq(priv, 300000, GPCPLL_CFG, GPCPLL_CFG_LOCK,
-                                  GPCPLL_CFG_LOCK)) {
-               nv_error(priv, "%s: timeout waiting for pllg lock\n", __func__);
-               return -ETIMEDOUT;
-       }
-
-       /* switch to VCO mode */
-       nv_mask(priv, SEL_VCO, 0, BIT(SEL_VCO_GPC2CLK_OUT_SHIFT));
-
-       /* restore out divider 1:1 */
-       val = nv_rd32(priv, GPC2CLK_OUT);
-       val &= ~GPC2CLK_OUT_VCODIV_MASK;
-       udelay(2);
-       nv_wr32(priv, GPC2CLK_OUT, val);
-
-       /* slide up to new NDIV */
-       return allow_slide ? gk20a_pllg_slide(priv, priv->n) : 0;
-}
-
-static int
-gk20a_pllg_program_mnp(struct gk20a_clock_priv *priv)
-{
-       int err;
-
-       err = _gk20a_pllg_program_mnp(priv, true);
-       if (err)
-               err = _gk20a_pllg_program_mnp(priv, false);
-
-       return err;
-}
-
-static void
-gk20a_pllg_disable(struct gk20a_clock_priv *priv)
-{
-       u32 val;
-
-       /* slide to VCO min */
-       val = nv_rd32(priv, GPCPLL_CFG);
-       if (val & GPCPLL_CFG_ENABLE) {
-               u32 coeff, m, n_lo;
-
-               coeff = nv_rd32(priv, GPCPLL_COEFF);
-               m = (coeff >> GPCPLL_COEFF_M_SHIFT) & MASK(GPCPLL_COEFF_M_WIDTH);
-               n_lo = DIV_ROUND_UP(m * priv->params->min_vco,
-                                   priv->parent_rate / MHZ);
-               gk20a_pllg_slide(priv, n_lo);
-       }
-
-       /* put PLL in bypass before disabling it */
-       nv_mask(priv, SEL_VCO, BIT(SEL_VCO_GPC2CLK_OUT_SHIFT), 0);
-
-       _gk20a_pllg_disable(priv);
-}
-
-#define GK20A_CLK_GPC_MDIV 1000
-
-static struct nouveau_clocks
-gk20a_domains[] = {
-       { nv_clk_src_crystal, 0xff },
-       { nv_clk_src_gpc, 0xff, 0, "core", GK20A_CLK_GPC_MDIV },
-       { nv_clk_src_max }
-};
-
-static struct nouveau_pstate
-gk20a_pstates[] = {
-       {
-               .base = {
-                       .domain[nv_clk_src_gpc] = 72000,
-                       .voltage = 0,
-               },
-       },
-       {
-               .base = {
-                       .domain[nv_clk_src_gpc] = 108000,
-                       .voltage = 1,
-               },
-       },
-       {
-               .base = {
-                       .domain[nv_clk_src_gpc] = 180000,
-                       .voltage = 2,
-               },
-       },
-       {
-               .base = {
-                       .domain[nv_clk_src_gpc] = 252000,
-                       .voltage = 3,
-               },
-       },
-       {
-               .base = {
-                       .domain[nv_clk_src_gpc] = 324000,
-                       .voltage = 4,
-               },
-       },
-       {
-               .base = {
-                       .domain[nv_clk_src_gpc] = 396000,
-                       .voltage = 5,
-               },
-       },
-       {
-               .base = {
-                       .domain[nv_clk_src_gpc] = 468000,
-                       .voltage = 6,
-               },
-       },
-       {
-               .base = {
-                       .domain[nv_clk_src_gpc] = 540000,
-                       .voltage = 7,
-               },
-       },
-       {
-               .base = {
-                       .domain[nv_clk_src_gpc] = 612000,
-                       .voltage = 8,
-               },
-       },
-       {
-               .base = {
-                       .domain[nv_clk_src_gpc] = 648000,
-                       .voltage = 9,
-               },
-       },
-       {
-               .base = {
-                       .domain[nv_clk_src_gpc] = 684000,
-                       .voltage = 10,
-               },
-       },
-       {
-               .base = {
-                       .domain[nv_clk_src_gpc] = 708000,
-                       .voltage = 11,
-               },
-       },
-       {
-               .base = {
-                       .domain[nv_clk_src_gpc] = 756000,
-                       .voltage = 12,
-               },
-       },
-       {
-               .base = {
-                       .domain[nv_clk_src_gpc] = 804000,
-                       .voltage = 13,
-               },
-       },
-       {
-               .base = {
-                       .domain[nv_clk_src_gpc] = 852000,
-                       .voltage = 14,
-               },
-       },
-};
-
-static int
-gk20a_clock_read(struct nouveau_clock *clk, enum nv_clk_src src)
-{
-       struct gk20a_clock_priv *priv = (void *)clk;
-
-       switch (src) {
-       case nv_clk_src_crystal:
-               return nv_device(clk)->crystal;
-       case nv_clk_src_gpc:
-               gk20a_pllg_read_mnp(priv);
-               return gk20a_pllg_calc_rate(priv) / GK20A_CLK_GPC_MDIV;
-       default:
-               nv_error(clk, "invalid clock source %d\n", src);
-               return -EINVAL;
-       }
-}
-
-static int
-gk20a_clock_calc(struct nouveau_clock *clk, struct nouveau_cstate *cstate)
-{
-       struct gk20a_clock_priv *priv = (void *)clk;
-
-       return gk20a_pllg_calc_mnp(priv, cstate->domain[nv_clk_src_gpc] *
-                                        GK20A_CLK_GPC_MDIV);
-}
-
-static int
-gk20a_clock_prog(struct nouveau_clock *clk)
-{
-       struct gk20a_clock_priv *priv = (void *)clk;
-
-       return gk20a_pllg_program_mnp(priv);
-}
-
-static void
-gk20a_clock_tidy(struct nouveau_clock *clk)
-{
-}
-
-static int
-gk20a_clock_fini(struct nouveau_object *object, bool suspend)
-{
-       struct gk20a_clock_priv *priv = (void *)object;
-       int ret;
-
-       ret = nouveau_clock_fini(&priv->base, false);
-
-       gk20a_pllg_disable(priv);
-
-       return ret;
-}
-
-static int
-gk20a_clock_init(struct nouveau_object *object)
-{
-       struct gk20a_clock_priv *priv = (void *)object;
-       int ret;
-
-       nv_mask(priv, GPC2CLK_OUT, GPC2CLK_OUT_INIT_MASK, GPC2CLK_OUT_INIT_VAL);
-
-       ret = nouveau_clock_init(&priv->base);
-       if (ret)
-               return ret;
-
-       ret = gk20a_clock_prog(&priv->base);
-       if (ret) {
-               nv_error(priv, "cannot initialize clock\n");
-               return ret;
-       }
-
-       return 0;
-}
-
-static int
-gk20a_clock_ctor(struct nouveau_object *parent,  struct nouveau_object *engine,
-                struct nouveau_oclass *oclass, void *data, u32 size,
-                struct nouveau_object **pobject)
-{
-       struct gk20a_clock_priv *priv;
-       struct nouveau_platform_device *plat;
-       int ret;
-       int i;
-
-       /* Finish initializing the pstates */
-       for (i = 0; i < ARRAY_SIZE(gk20a_pstates); i++) {
-               INIT_LIST_HEAD(&gk20a_pstates[i].list);
-               gk20a_pstates[i].pstate = i + 1;
-       }
-
-       ret = nouveau_clock_create(parent, engine, oclass, gk20a_domains,
-                       gk20a_pstates, ARRAY_SIZE(gk20a_pstates), true, &priv);
-       *pobject = nv_object(priv);
-       if (ret)
-               return ret;
-
-       priv->params = &gk20a_pllg_params;
-
-       plat = nv_device_to_platform(nv_device(parent));
-       priv->parent_rate = clk_get_rate(plat->gpu->clk);
-       nv_info(priv, "parent clock rate: %d Mhz\n", priv->parent_rate / MHZ);
-
-       priv->base.read = gk20a_clock_read;
-       priv->base.calc = gk20a_clock_calc;
-       priv->base.prog = gk20a_clock_prog;
-       priv->base.tidy = gk20a_clock_tidy;
-
-       return 0;
-}
-
-struct nouveau_oclass
-gk20a_clock_oclass = {
-       .handle = NV_SUBDEV(CLOCK, 0xea),
-       .ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = gk20a_clock_ctor,
-               .dtor = _nouveau_subdev_dtor,
-               .init = gk20a_clock_init,
-               .fini = gk20a_clock_fini,
-       },
-};
diff --git a/drivers/gpu/drm/nouveau/core/subdev/clock/nv04.c b/drivers/gpu/drm/nouveau/core/subdev/clock/nv04.c
deleted file mode 100644 (file)
index 4c48232..0000000
+++ /dev/null
@@ -1,105 +0,0 @@
-/*
- * Copyright 2012 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 <subdev/bios.h>
-#include <subdev/bios/pll.h>
-#include <subdev/clock.h>
-#include <subdev/devinit/nv04.h>
-
-#include "pll.h"
-
-struct nv04_clock_priv {
-       struct nouveau_clock base;
-};
-
-int
-nv04_clock_pll_calc(struct nouveau_clock *clock, struct nvbios_pll *info,
-                   int clk, struct nouveau_pll_vals *pv)
-{
-       int N1, M1, N2, M2, P;
-       int ret = nv04_pll_calc(nv_subdev(clock), info, clk, &N1, &M1, &N2, &M2, &P);
-       if (ret) {
-               pv->refclk = info->refclk;
-               pv->N1 = N1;
-               pv->M1 = M1;
-               pv->N2 = N2;
-               pv->M2 = M2;
-               pv->log2P = P;
-       }
-       return ret;
-}
-
-int
-nv04_clock_pll_prog(struct nouveau_clock *clk, u32 reg1,
-                   struct nouveau_pll_vals *pv)
-{
-       struct nouveau_devinit *devinit = nouveau_devinit(clk);
-       int cv = nouveau_bios(clk)->version.chip;
-
-       if (cv == 0x30 || cv == 0x31 || cv == 0x35 || cv == 0x36 ||
-           cv >= 0x40) {
-               if (reg1 > 0x405c)
-                       setPLL_double_highregs(devinit, reg1, pv);
-               else
-                       setPLL_double_lowregs(devinit, reg1, pv);
-       } else
-               setPLL_single(devinit, reg1, pv);
-
-       return 0;
-}
-
-static struct nouveau_clocks
-nv04_domain[] = {
-       { nv_clk_src_max }
-};
-
-static int
-nv04_clock_ctor(struct nouveau_object *parent, struct nouveau_object *engine,
-               struct nouveau_oclass *oclass, void *data, u32 size,
-               struct nouveau_object **pobject)
-{
-       struct nv04_clock_priv *priv;
-       int ret;
-
-       ret = nouveau_clock_create(parent, engine, oclass, nv04_domain, NULL, 0,
-                                  false, &priv);
-       *pobject = nv_object(priv);
-       if (ret)
-               return ret;
-
-       priv->base.pll_calc = nv04_clock_pll_calc;
-       priv->base.pll_prog = nv04_clock_pll_prog;
-       return 0;
-}
-
-struct nouveau_oclass
-nv04_clock_oclass = {
-       .handle = NV_SUBDEV(CLOCK, 0x04),
-       .ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nv04_clock_ctor,
-               .dtor = _nouveau_clock_dtor,
-               .init = _nouveau_clock_init,
-               .fini = _nouveau_clock_fini,
-       },
-};
diff --git a/drivers/gpu/drm/nouveau/core/subdev/clock/nv40.c b/drivers/gpu/drm/nouveau/core/subdev/clock/nv40.c
deleted file mode 100644 (file)
index 08368fe..0000000
+++ /dev/null
@@ -1,240 +0,0 @@
-/*
- * Copyright 2012 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 <subdev/clock.h>
-#include <subdev/bios.h>
-#include <subdev/bios/pll.h>
-
-#include "pll.h"
-
-struct nv40_clock_priv {
-       struct nouveau_clock base;
-       u32 ctrl;
-       u32 npll_ctrl;
-       u32 npll_coef;
-       u32 spll;
-};
-
-static struct nouveau_clocks
-nv40_domain[] = {
-       { nv_clk_src_crystal, 0xff },
-       { nv_clk_src_href   , 0xff },
-       { nv_clk_src_core   , 0xff, 0, "core", 1000 },
-       { nv_clk_src_shader , 0xff, 0, "shader", 1000 },
-       { nv_clk_src_mem    , 0xff, 0, "memory", 1000 },
-       { nv_clk_src_max }
-};
-
-static u32
-read_pll_1(struct nv40_clock_priv *priv, u32 reg)
-{
-       u32 ctrl = nv_rd32(priv, reg + 0x00);
-       int P = (ctrl & 0x00070000) >> 16;
-       int N = (ctrl & 0x0000ff00) >> 8;
-       int M = (ctrl & 0x000000ff) >> 0;
-       u32 ref = 27000, clk = 0;
-
-       if (ctrl & 0x80000000)
-               clk = ref * N / M;
-
-       return clk >> P;
-}
-
-static u32
-read_pll_2(struct nv40_clock_priv *priv, u32 reg)
-{
-       u32 ctrl = nv_rd32(priv, reg + 0x00);
-       u32 coef = nv_rd32(priv, reg + 0x04);
-       int N2 = (coef & 0xff000000) >> 24;
-       int M2 = (coef & 0x00ff0000) >> 16;
-       int N1 = (coef & 0x0000ff00) >> 8;
-       int M1 = (coef & 0x000000ff) >> 0;
-       int P = (ctrl & 0x00070000) >> 16;
-       u32 ref = 27000, clk = 0;
-
-       if ((ctrl & 0x80000000) && M1) {
-               clk = ref * N1 / M1;
-               if ((ctrl & 0x40000100) == 0x40000000) {
-                       if (M2)
-                               clk = clk * N2 / M2;
-                       else
-                               clk = 0;
-               }
-       }
-
-       return clk >> P;
-}
-
-static u32
-read_clk(struct nv40_clock_priv *priv, u32 src)
-{
-       switch (src) {
-       case 3:
-               return read_pll_2(priv, 0x004000);
-       case 2:
-               return read_pll_1(priv, 0x004008);
-       default:
-               break;
-       }
-
-       return 0;
-}
-
-static int
-nv40_clock_read(struct nouveau_clock *clk, enum nv_clk_src src)
-{
-       struct nv40_clock_priv *priv = (void *)clk;
-       u32 mast = nv_rd32(priv, 0x00c040);
-
-       switch (src) {
-       case nv_clk_src_crystal:
-               return nv_device(priv)->crystal;
-       case nv_clk_src_href:
-               return 100000; /*XXX: PCIE/AGP differ*/
-       case nv_clk_src_core:
-               return read_clk(priv, (mast & 0x00000003) >> 0);
-       case nv_clk_src_shader:
-               return read_clk(priv, (mast & 0x00000030) >> 4);
-       case nv_clk_src_mem:
-               return read_pll_2(priv, 0x4020);
-       default:
-               break;
-       }
-
-       nv_debug(priv, "unknown clock source %d 0x%08x\n", src, mast);
-       return -EINVAL;
-}
-
-static int
-nv40_clock_calc_pll(struct nv40_clock_priv *priv, u32 reg, u32 clk,
-                   int *N1, int *M1, int *N2, int *M2, int *log2P)
-{
-       struct nouveau_bios *bios = nouveau_bios(priv);
-       struct nvbios_pll pll;
-       int ret;
-
-       ret = nvbios_pll_parse(bios, reg, &pll);
-       if (ret)
-               return ret;
-
-       if (clk < pll.vco1.max_freq)
-               pll.vco2.max_freq = 0;
-
-       ret = nv04_pll_calc(nv_subdev(priv), &pll, clk, N1, M1, N2, M2, log2P);
-       if (ret == 0)
-               return -ERANGE;
-       return ret;
-}
-
-static int
-nv40_clock_calc(struct nouveau_clock *clk, struct nouveau_cstate *cstate)
-{
-       struct nv40_clock_priv *priv = (void *)clk;
-       int gclk = cstate->domain[nv_clk_src_core];
-       int sclk = cstate->domain[nv_clk_src_shader];
-       int N1, M1, N2, M2, log2P;
-       int ret;
-
-       /* core/geometric clock */
-       ret = nv40_clock_calc_pll(priv, 0x004000, gclk,
-                                &N1, &M1, &N2, &M2, &log2P);
-       if (ret < 0)
-               return ret;
-
-       if (N2 == M2) {
-               priv->npll_ctrl = 0x80000100 | (log2P << 16);
-               priv->npll_coef = (N1 << 8) | M1;
-       } else {
-               priv->npll_ctrl = 0xc0000000 | (log2P << 16);
-               priv->npll_coef = (N2 << 24) | (M2 << 16) | (N1 << 8) | M1;
-       }
-
-       /* use the second pll for shader/rop clock, if it differs from core */
-       if (sclk && sclk != gclk) {
-               ret = nv40_clock_calc_pll(priv, 0x004008, sclk,
-                                        &N1, &M1, NULL, NULL, &log2P);
-               if (ret < 0)
-                       return ret;
-
-               priv->spll = 0xc0000000 | (log2P << 16) | (N1 << 8) | M1;
-               priv->ctrl = 0x00000223;
-       } else {
-               priv->spll = 0x00000000;
-               priv->ctrl = 0x00000333;
-       }
-
-       return 0;
-}
-
-static int
-nv40_clock_prog(struct nouveau_clock *clk)
-{
-       struct nv40_clock_priv *priv = (void *)clk;
-       nv_mask(priv, 0x00c040, 0x00000333, 0x00000000);
-       nv_wr32(priv, 0x004004, priv->npll_coef);
-       nv_mask(priv, 0x004000, 0xc0070100, priv->npll_ctrl);
-       nv_mask(priv, 0x004008, 0xc007ffff, priv->spll);
-       mdelay(5);
-       nv_mask(priv, 0x00c040, 0x00000333, priv->ctrl);
-       return 0;
-}
-
-static void
-nv40_clock_tidy(struct nouveau_clock *clk)
-{
-}
-
-static int
-nv40_clock_ctor(struct nouveau_object *parent, struct nouveau_object *engine,
-               struct nouveau_oclass *oclass, void *data, u32 size,
-               struct nouveau_object **pobject)
-{
-       struct nv40_clock_priv *priv;
-       int ret;
-
-       ret = nouveau_clock_create(parent, engine, oclass, nv40_domain, NULL, 0,
-                                  true, &priv);
-       *pobject = nv_object(priv);
-       if (ret)
-               return ret;
-
-       priv->base.pll_calc = nv04_clock_pll_calc;
-       priv->base.pll_prog = nv04_clock_pll_prog;
-       priv->base.read = nv40_clock_read;
-       priv->base.calc = nv40_clock_calc;
-       priv->base.prog = nv40_clock_prog;
-       priv->base.tidy = nv40_clock_tidy;
-       return 0;
-}
-
-struct nouveau_oclass
-nv40_clock_oclass = {
-       .handle = NV_SUBDEV(CLOCK, 0x40),
-       .ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nv40_clock_ctor,
-               .dtor = _nouveau_clock_dtor,
-               .init = _nouveau_clock_init,
-               .fini = _nouveau_clock_fini,
-       },
-};
diff --git a/drivers/gpu/drm/nouveau/core/subdev/clock/nv50.c b/drivers/gpu/drm/nouveau/core/subdev/clock/nv50.c
deleted file mode 100644 (file)
index 5070ebc..0000000
+++ /dev/null
@@ -1,559 +0,0 @@
-/*
- * Copyright 2012 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 <subdev/bios.h>
-#include <subdev/bios/pll.h>
-
-#include "nv50.h"
-#include "pll.h"
-#include "seq.h"
-
-static u32
-read_div(struct nv50_clock_priv *priv)
-{
-       switch (nv_device(priv)->chipset) {
-       case 0x50: /* it exists, but only has bit 31, not the dividers.. */
-       case 0x84:
-       case 0x86:
-       case 0x98:
-       case 0xa0:
-               return nv_rd32(priv, 0x004700);
-       case 0x92:
-       case 0x94:
-       case 0x96:
-               return nv_rd32(priv, 0x004800);
-       default:
-               return 0x00000000;
-       }
-}
-
-static u32
-read_pll_src(struct nv50_clock_priv *priv, u32 base)
-{
-       struct nouveau_clock *clk = &priv->base;
-       u32 coef, ref = clk->read(clk, nv_clk_src_crystal);
-       u32 rsel = nv_rd32(priv, 0x00e18c);
-       int P, N, M, id;
-
-       switch (nv_device(priv)->chipset) {
-       case 0x50:
-       case 0xa0:
-               switch (base) {
-               case 0x4020:
-               case 0x4028: id = !!(rsel & 0x00000004); break;
-               case 0x4008: id = !!(rsel & 0x00000008); break;
-               case 0x4030: id = 0; break;
-               default:
-                       nv_error(priv, "ref: bad pll 0x%06x\n", base);
-                       return 0;
-               }
-
-               coef = nv_rd32(priv, 0x00e81c + (id * 0x0c));
-               ref *=  (coef & 0x01000000) ? 2 : 4;
-               P    =  (coef & 0x00070000) >> 16;
-               N    = ((coef & 0x0000ff00) >> 8) + 1;
-               M    = ((coef & 0x000000ff) >> 0) + 1;
-               break;
-       case 0x84:
-       case 0x86:
-       case 0x92:
-               coef = nv_rd32(priv, 0x00e81c);
-               P    = (coef & 0x00070000) >> 16;
-               N    = (coef & 0x0000ff00) >> 8;
-               M    = (coef & 0x000000ff) >> 0;
-               break;
-       case 0x94:
-       case 0x96:
-       case 0x98:
-               rsel = nv_rd32(priv, 0x00c050);
-               switch (base) {
-               case 0x4020: rsel = (rsel & 0x00000003) >> 0; break;
-               case 0x4008: rsel = (rsel & 0x0000000c) >> 2; break;
-               case 0x4028: rsel = (rsel & 0x00001800) >> 11; break;
-               case 0x4030: rsel = 3; break;
-               default:
-                       nv_error(priv, "ref: bad pll 0x%06x\n", base);
-                       return 0;
-               }
-
-               switch (rsel) {
-               case 0: id = 1; break;
-               case 1: return clk->read(clk, nv_clk_src_crystal);
-               case 2: return clk->read(clk, nv_clk_src_href);
-               case 3: id = 0; break;
-               }
-
-               coef =  nv_rd32(priv, 0x00e81c + (id * 0x28));
-               P    = (nv_rd32(priv, 0x00e824 + (id * 0x28)) >> 16) & 7;
-               P   += (coef & 0x00070000) >> 16;
-               N    = (coef & 0x0000ff00) >> 8;
-               M    = (coef & 0x000000ff) >> 0;
-               break;
-       default:
-               BUG_ON(1);
-       }
-
-       if (M)
-               return (ref * N / M) >> P;
-       return 0;
-}
-
-static u32
-read_pll_ref(struct nv50_clock_priv *priv, u32 base)
-{
-       struct nouveau_clock *clk = &priv->base;
-       u32 src, mast = nv_rd32(priv, 0x00c040);
-
-       switch (base) {
-       case 0x004028:
-               src = !!(mast & 0x00200000);
-               break;
-       case 0x004020:
-               src = !!(mast & 0x00400000);
-               break;
-       case 0x004008:
-               src = !!(mast & 0x00010000);
-               break;
-       case 0x004030:
-               src = !!(mast & 0x02000000);
-               break;
-       case 0x00e810:
-               return clk->read(clk, nv_clk_src_crystal);
-       default:
-               nv_error(priv, "bad pll 0x%06x\n", base);
-               return 0;
-       }
-
-       if (src)
-               return clk->read(clk, nv_clk_src_href);
-       return read_pll_src(priv, base);
-}
-
-static u32
-read_pll(struct nv50_clock_priv *priv, u32 base)
-{
-       struct nouveau_clock *clk = &priv->base;
-       u32 mast = nv_rd32(priv, 0x00c040);
-       u32 ctrl = nv_rd32(priv, base + 0);
-       u32 coef = nv_rd32(priv, base + 4);
-       u32 ref = read_pll_ref(priv, base);
-       u32 freq = 0;
-       int N1, N2, M1, M2;
-
-       if (base == 0x004028 && (mast & 0x00100000)) {
-               /* wtf, appears to only disable post-divider on nva0 */
-               if (nv_device(priv)->chipset != 0xa0)
-                       return clk->read(clk, nv_clk_src_dom6);
-       }
-
-       N2 = (coef & 0xff000000) >> 24;
-       M2 = (coef & 0x00ff0000) >> 16;
-       N1 = (coef & 0x0000ff00) >> 8;
-       M1 = (coef & 0x000000ff);
-       if ((ctrl & 0x80000000) && M1) {
-               freq = ref * N1 / M1;
-               if ((ctrl & 0x40000100) == 0x40000000) {
-                       if (M2)
-                               freq = freq * N2 / M2;
-                       else
-                               freq = 0;
-               }
-       }
-
-       return freq;
-}
-
-static int
-nv50_clock_read(struct nouveau_clock *clk, enum nv_clk_src src)
-{
-       struct nv50_clock_priv *priv = (void *)clk;
-       u32 mast = nv_rd32(priv, 0x00c040);
-       u32 P = 0;
-
-       switch (src) {
-       case nv_clk_src_crystal:
-               return nv_device(priv)->crystal;
-       case nv_clk_src_href:
-               return 100000; /* PCIE reference clock */
-       case nv_clk_src_hclk:
-               return div_u64((u64)clk->read(clk, nv_clk_src_href) * 27778, 10000);
-       case nv_clk_src_hclkm3:
-               return clk->read(clk, nv_clk_src_hclk) * 3;
-       case nv_clk_src_hclkm3d2:
-               return clk->read(clk, nv_clk_src_hclk) * 3 / 2;
-       case nv_clk_src_host:
-               switch (mast & 0x30000000) {
-               case 0x00000000: return clk->read(clk, nv_clk_src_href);
-               case 0x10000000: break;
-               case 0x20000000: /* !0x50 */
-               case 0x30000000: return clk->read(clk, nv_clk_src_hclk);
-               }
-               break;
-       case nv_clk_src_core:
-               if (!(mast & 0x00100000))
-                       P = (nv_rd32(priv, 0x004028) & 0x00070000) >> 16;
-               switch (mast & 0x00000003) {
-               case 0x00000000: return clk->read(clk, nv_clk_src_crystal) >> P;
-               case 0x00000001: return clk->read(clk, nv_clk_src_dom6);
-               case 0x00000002: return read_pll(priv, 0x004020) >> P;
-               case 0x00000003: return read_pll(priv, 0x004028) >> P;
-               }
-               break;
-       case nv_clk_src_shader:
-               P = (nv_rd32(priv, 0x004020) & 0x00070000) >> 16;
-               switch (mast & 0x00000030) {
-               case 0x00000000:
-                       if (mast & 0x00000080)
-                               return clk->read(clk, nv_clk_src_host) >> P;
-                       return clk->read(clk, nv_clk_src_crystal) >> P;
-               case 0x00000010: break;
-               case 0x00000020: return read_pll(priv, 0x004028) >> P;
-               case 0x00000030: return read_pll(priv, 0x004020) >> P;
-               }
-               break;
-       case nv_clk_src_mem:
-               P = (nv_rd32(priv, 0x004008) & 0x00070000) >> 16;
-               if (nv_rd32(priv, 0x004008) & 0x00000200) {
-                       switch (mast & 0x0000c000) {
-                       case 0x00000000:
-                               return clk->read(clk, nv_clk_src_crystal) >> P;
-                       case 0x00008000:
-                       case 0x0000c000:
-                               return clk->read(clk, nv_clk_src_href) >> P;
-                       }
-               } else {
-                       return read_pll(priv, 0x004008) >> P;
-               }
-               break;
-       case nv_clk_src_vdec:
-               P = (read_div(priv) & 0x00000700) >> 8;
-               switch (nv_device(priv)->chipset) {
-               case 0x84:
-               case 0x86:
-               case 0x92:
-               case 0x94:
-               case 0x96:
-               case 0xa0:
-                       switch (mast & 0x00000c00) {
-                       case 0x00000000:
-                               if (nv_device(priv)->chipset == 0xa0) /* wtf?? */
-                                       return clk->read(clk, nv_clk_src_core) >> P;
-                               return clk->read(clk, nv_clk_src_crystal) >> P;
-                       case 0x00000400:
-                               return 0;
-                       case 0x00000800:
-                               if (mast & 0x01000000)
-                                       return read_pll(priv, 0x004028) >> P;
-                               return read_pll(priv, 0x004030) >> P;
-                       case 0x00000c00:
-                               return clk->read(clk, nv_clk_src_core) >> P;
-                       }
-                       break;
-               case 0x98:
-                       switch (mast & 0x00000c00) {
-                       case 0x00000000:
-                               return clk->read(clk, nv_clk_src_core) >> P;
-                       case 0x00000400:
-                               return 0;
-                       case 0x00000800:
-                               return clk->read(clk, nv_clk_src_hclkm3d2) >> P;
-                       case 0x00000c00:
-                               return clk->read(clk, nv_clk_src_mem) >> P;
-                       }
-                       break;
-               }
-               break;
-       case nv_clk_src_dom6:
-               switch (nv_device(priv)->chipset) {
-               case 0x50:
-               case 0xa0:
-                       return read_pll(priv, 0x00e810) >> 2;
-               case 0x84:
-               case 0x86:
-               case 0x92:
-               case 0x94:
-               case 0x96:
-               case 0x98:
-                       P = (read_div(priv) & 0x00000007) >> 0;
-                       switch (mast & 0x0c000000) {
-                       case 0x00000000: return clk->read(clk, nv_clk_src_href);
-                       case 0x04000000: break;
-                       case 0x08000000: return clk->read(clk, nv_clk_src_hclk);
-                       case 0x0c000000:
-                               return clk->read(clk, nv_clk_src_hclkm3) >> P;
-                       }
-                       break;
-               default:
-                       break;
-               }
-       default:
-               break;
-       }
-
-       nv_debug(priv, "unknown clock source %d 0x%08x\n", src, mast);
-       return -EINVAL;
-}
-
-static u32
-calc_pll(struct nv50_clock_priv *priv, u32 reg, u32 clk, int *N, int *M, int *P)
-{
-       struct nouveau_bios *bios = nouveau_bios(priv);
-       struct nvbios_pll pll;
-       int ret;
-
-       ret = nvbios_pll_parse(bios, reg, &pll);
-       if (ret)
-               return 0;
-
-       pll.vco2.max_freq = 0;
-       pll.refclk = read_pll_ref(priv, reg);
-       if (!pll.refclk)
-               return 0;
-
-       return nv04_pll_calc(nv_subdev(priv), &pll, clk, N, M, NULL, NULL, P);
-}
-
-static inline u32
-calc_div(u32 src, u32 target, int *div)
-{
-       u32 clk0 = src, clk1 = src;
-       for (*div = 0; *div <= 7; (*div)++) {
-               if (clk0 <= target) {
-                       clk1 = clk0 << (*div ? 1 : 0);
-                       break;
-               }
-               clk0 >>= 1;
-       }
-
-       if (target - clk0 <= clk1 - target)
-               return clk0;
-       (*div)--;
-       return clk1;
-}
-
-static inline u32
-clk_same(u32 a, u32 b)
-{
-       return ((a / 1000) == (b / 1000));
-}
-
-static int
-nv50_clock_calc(struct nouveau_clock *clk, struct nouveau_cstate *cstate)
-{
-       struct nv50_clock_priv *priv = (void *)clk;
-       struct nv50_clock_hwsq *hwsq = &priv->hwsq;
-       const int shader = cstate->domain[nv_clk_src_shader];
-       const int core = cstate->domain[nv_clk_src_core];
-       const int vdec = cstate->domain[nv_clk_src_vdec];
-       const int dom6 = cstate->domain[nv_clk_src_dom6];
-       u32 mastm = 0, mastv = 0;
-       u32 divsm = 0, divsv = 0;
-       int N, M, P1, P2;
-       int freq, out;
-
-       /* prepare a hwsq script from which we'll perform the reclock */
-       out = clk_init(hwsq, nv_subdev(clk));
-       if (out)
-               return out;
-
-       clk_wr32(hwsq, fifo, 0x00000001); /* block fifo */
-       clk_nsec(hwsq, 8000);
-       clk_setf(hwsq, 0x10, 0x00); /* disable fb */
-       clk_wait(hwsq, 0x00, 0x01); /* wait for fb disabled */
-
-       /* vdec: avoid modifying xpll until we know exactly how the other
-        * clock domains work, i suspect at least some of them can also be
-        * tied to xpll...
-        */
-       if (vdec) {
-               /* see how close we can get using nvclk as a source */
-               freq = calc_div(core, vdec, &P1);
-
-               /* see how close we can get using xpll/hclk as a source */
-               if (nv_device(priv)->chipset != 0x98)
-                       out = read_pll(priv, 0x004030);
-               else
-                       out = clk->read(clk, nv_clk_src_hclkm3d2);
-               out = calc_div(out, vdec, &P2);
-
-               /* select whichever gets us closest */
-               if (abs(vdec - freq) <= abs(vdec - out)) {
-                       if (nv_device(priv)->chipset != 0x98)
-                               mastv |= 0x00000c00;
-                       divsv |= P1 << 8;
-               } else {
-                       mastv |= 0x00000800;
-                       divsv |= P2 << 8;
-               }
-
-               mastm |= 0x00000c00;
-               divsm |= 0x00000700;
-       }
-
-       /* dom6: nfi what this is, but we're limited to various combinations
-        * of the host clock frequency
-        */
-       if (dom6) {
-               if (clk_same(dom6, clk->read(clk, nv_clk_src_href))) {
-                       mastv |= 0x00000000;
-               } else
-               if (clk_same(dom6, clk->read(clk, nv_clk_src_hclk))) {
-                       mastv |= 0x08000000;
-               } else {
-                       freq = clk->read(clk, nv_clk_src_hclk) * 3;
-                       freq = calc_div(freq, dom6, &P1);
-
-                       mastv |= 0x0c000000;
-                       divsv |= P1;
-               }
-
-               mastm |= 0x0c000000;
-               divsm |= 0x00000007;
-       }
-
-       /* vdec/dom6: switch to "safe" clocks temporarily, update dividers
-        * and then switch to target clocks
-        */
-       clk_mask(hwsq, mast, mastm, 0x00000000);
-       clk_mask(hwsq, divs, divsm, divsv);
-       clk_mask(hwsq, mast, mastm, mastv);
-
-       /* core/shader: disconnect nvclk/sclk from their PLLs (nvclk to dom6,
-        * sclk to hclk) before reprogramming
-        */
-       if (nv_device(priv)->chipset < 0x92)
-               clk_mask(hwsq, mast, 0x001000b0, 0x00100080);
-       else
-               clk_mask(hwsq, mast, 0x000000b3, 0x00000081);
-
-       /* core: for the moment at least, always use nvpll */
-       freq = calc_pll(priv, 0x4028, core, &N, &M, &P1);
-       if (freq == 0)
-               return -ERANGE;
-
-       clk_mask(hwsq, nvpll[0], 0xc03f0100,
-                                0x80000000 | (P1 << 19) | (P1 << 16));
-       clk_mask(hwsq, nvpll[1], 0x0000ffff, (N << 8) | M);
-
-       /* shader: tie to nvclk if possible, otherwise use spll.  have to be
-        * very careful that the shader clock is at least twice the core, or
-        * some chipsets will be very unhappy.  i expect most or all of these
-        * cases will be handled by tying to nvclk, but it's possible there's
-        * corners
-        */
-       if (P1-- && shader == (core << 1)) {
-               clk_mask(hwsq, spll[0], 0xc03f0100, (P1 << 19) | (P1 << 16));
-               clk_mask(hwsq, mast, 0x00100033, 0x00000023);
-       } else {
-               freq = calc_pll(priv, 0x4020, shader, &N, &M, &P1);
-               if (freq == 0)
-                       return -ERANGE;
-
-               clk_mask(hwsq, spll[0], 0xc03f0100,
-                                       0x80000000 | (P1 << 19) | (P1 << 16));
-               clk_mask(hwsq, spll[1], 0x0000ffff, (N << 8) | M);
-               clk_mask(hwsq, mast, 0x00100033, 0x00000033);
-       }
-
-       /* restore normal operation */
-       clk_setf(hwsq, 0x10, 0x01); /* enable fb */
-       clk_wait(hwsq, 0x00, 0x00); /* wait for fb enabled */
-       clk_wr32(hwsq, fifo, 0x00000000); /* un-block fifo */
-       return 0;
-}
-
-static int
-nv50_clock_prog(struct nouveau_clock *clk)
-{
-       struct nv50_clock_priv *priv = (void *)clk;
-       return clk_exec(&priv->hwsq, true);
-}
-
-static void
-nv50_clock_tidy(struct nouveau_clock *clk)
-{
-       struct nv50_clock_priv *priv = (void *)clk;
-       clk_exec(&priv->hwsq, false);
-}
-
-int
-nv50_clock_ctor(struct nouveau_object *parent, struct nouveau_object *engine,
-               struct nouveau_oclass *oclass, void *data, u32 size,
-               struct nouveau_object **pobject)
-{
-       struct nv50_clock_oclass *pclass = (void *)oclass;
-       struct nv50_clock_priv *priv;
-       int ret;
-
-       ret = nouveau_clock_create(parent, engine, oclass, pclass->domains,
-                                  NULL, 0, false, &priv);
-       *pobject = nv_object(priv);
-       if (ret)
-               return ret;
-
-       priv->hwsq.r_fifo = hwsq_reg(0x002504);
-       priv->hwsq.r_spll[0] = hwsq_reg(0x004020);
-       priv->hwsq.r_spll[1] = hwsq_reg(0x004024);
-       priv->hwsq.r_nvpll[0] = hwsq_reg(0x004028);
-       priv->hwsq.r_nvpll[1] = hwsq_reg(0x00402c);
-       switch (nv_device(priv)->chipset) {
-       case 0x92:
-       case 0x94:
-       case 0x96:
-               priv->hwsq.r_divs = hwsq_reg(0x004800);
-               break;
-       default:
-               priv->hwsq.r_divs = hwsq_reg(0x004700);
-               break;
-       }
-       priv->hwsq.r_mast = hwsq_reg(0x00c040);
-
-       priv->base.read = nv50_clock_read;
-       priv->base.calc = nv50_clock_calc;
-       priv->base.prog = nv50_clock_prog;
-       priv->base.tidy = nv50_clock_tidy;
-       return 0;
-}
-
-static struct nouveau_clocks
-nv50_domains[] = {
-       { nv_clk_src_crystal, 0xff },
-       { nv_clk_src_href   , 0xff },
-       { nv_clk_src_core   , 0xff, 0, "core", 1000 },
-       { nv_clk_src_shader , 0xff, 0, "shader", 1000 },
-       { nv_clk_src_mem    , 0xff, 0, "memory", 1000 },
-       { nv_clk_src_max }
-};
-
-struct nouveau_oclass *
-nv50_clock_oclass = &(struct nv50_clock_oclass) {
-       .base.handle = NV_SUBDEV(CLOCK, 0x50),
-       .base.ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nv50_clock_ctor,
-               .dtor = _nouveau_clock_dtor,
-               .init = _nouveau_clock_init,
-               .fini = _nouveau_clock_fini,
-       },
-       .domains = nv50_domains,
-}.base;
diff --git a/drivers/gpu/drm/nouveau/core/subdev/clock/nv50.h b/drivers/gpu/drm/nouveau/core/subdev/clock/nv50.h
deleted file mode 100644 (file)
index f10917d..0000000
+++ /dev/null
@@ -1,31 +0,0 @@
-#ifndef __NVKM_CLK_NV50_H__
-#define __NVKM_CLK_NV50_H__
-
-#include <subdev/bus.h>
-#include <subdev/bus/hwsq.h>
-#include <subdev/clock.h>
-
-struct nv50_clock_hwsq {
-       struct hwsq base;
-       struct hwsq_reg r_fifo;
-       struct hwsq_reg r_spll[2];
-       struct hwsq_reg r_nvpll[2];
-       struct hwsq_reg r_divs;
-       struct hwsq_reg r_mast;
-};
-
-struct nv50_clock_priv {
-       struct nouveau_clock base;
-       struct nv50_clock_hwsq hwsq;
-};
-
-int  nv50_clock_ctor(struct nouveau_object *, struct nouveau_object *,
-                    struct nouveau_oclass *, void *, u32,
-                    struct nouveau_object **);
-
-struct nv50_clock_oclass {
-       struct nouveau_oclass base;
-       struct nouveau_clocks *domains;
-};
-
-#endif
diff --git a/drivers/gpu/drm/nouveau/core/subdev/clock/nv84.c b/drivers/gpu/drm/nouveau/core/subdev/clock/nv84.c
deleted file mode 100644 (file)
index b0b7c14..0000000
+++ /dev/null
@@ -1,48 +0,0 @@
-/*
- * Copyright 2013 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 <bskeggs@redhat.com>
- */
-
-#include "nv50.h"
-
-static struct nouveau_clocks
-nv84_domains[] = {
-       { nv_clk_src_crystal, 0xff },
-       { nv_clk_src_href   , 0xff },
-       { nv_clk_src_core   , 0xff, 0, "core", 1000 },
-       { nv_clk_src_shader , 0xff, 0, "shader", 1000 },
-       { nv_clk_src_mem    , 0xff, 0, "memory", 1000 },
-       { nv_clk_src_vdec   , 0xff },
-       { nv_clk_src_max }
-};
-
-struct nouveau_oclass *
-nv84_clock_oclass = &(struct nv50_clock_oclass) {
-       .base.handle = NV_SUBDEV(CLOCK, 0x84),
-       .base.ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nv50_clock_ctor,
-               .dtor = _nouveau_clock_dtor,
-               .init = _nouveau_clock_init,
-               .fini = _nouveau_clock_fini,
-       },
-       .domains = nv84_domains,
-}.base;
diff --git a/drivers/gpu/drm/nouveau/core/subdev/clock/nva3.c b/drivers/gpu/drm/nouveau/core/subdev/clock/nva3.c
deleted file mode 100644 (file)
index 07ad012..0000000
+++ /dev/null
@@ -1,534 +0,0 @@
-/*
- * Copyright 2012 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
- *          Roy Spliet
- */
-
-#include <engine/fifo.h>
-#include <subdev/bios.h>
-#include <subdev/bios/pll.h>
-#include <subdev/timer.h>
-
-#include "pll.h"
-
-#include "nva3.h"
-
-struct nva3_clock_priv {
-       struct nouveau_clock base;
-       struct nva3_clock_info eng[nv_clk_src_max];
-};
-
-static u32 read_clk(struct nva3_clock_priv *, int, bool);
-static u32 read_pll(struct nva3_clock_priv *, int, u32);
-
-static u32
-read_vco(struct nva3_clock_priv *priv, int clk)
-{
-       u32 sctl = nv_rd32(priv, 0x4120 + (clk * 4));
-
-       switch (sctl & 0x00000030) {
-       case 0x00000000:
-               return nv_device(priv)->crystal;
-       case 0x00000020:
-               return read_pll(priv, 0x41, 0x00e820);
-       case 0x00000030:
-               return read_pll(priv, 0x42, 0x00e8a0);
-       default:
-               return 0;
-       }
-}
-
-static u32
-read_clk(struct nva3_clock_priv *priv, int clk, bool ignore_en)
-{
-       u32 sctl, sdiv, sclk;
-
-       /* refclk for the 0xe8xx plls is a fixed frequency */
-       if (clk >= 0x40) {
-               if (nv_device(priv)->chipset == 0xaf) {
-                       /* no joke.. seriously.. sigh.. */
-                       return nv_rd32(priv, 0x00471c) * 1000;
-               }
-
-               return nv_device(priv)->crystal;
-       }
-
-       sctl = nv_rd32(priv, 0x4120 + (clk * 4));
-       if (!ignore_en && !(sctl & 0x00000100))
-               return 0;
-
-       /* out_alt */
-       if (sctl & 0x00000400)
-               return 108000;
-
-       /* vco_out */
-       switch (sctl & 0x00003000) {
-       case 0x00000000:
-               if (!(sctl & 0x00000200))
-                       return nv_device(priv)->crystal;
-               return 0;
-       case 0x00002000:
-               if (sctl & 0x00000040)
-                       return 108000;
-               return 100000;
-       case 0x00003000:
-               /* vco_enable */
-               if (!(sctl & 0x00000001))
-                       return 0;
-
-               sclk = read_vco(priv, clk);
-               sdiv = ((sctl & 0x003f0000) >> 16) + 2;
-               return (sclk * 2) / sdiv;
-       default:
-               return 0;
-       }
-}
-
-static u32
-read_pll(struct nva3_clock_priv *priv, int clk, u32 pll)
-{
-       u32 ctrl = nv_rd32(priv, pll + 0);
-       u32 sclk = 0, P = 1, N = 1, M = 1;
-
-       if (!(ctrl & 0x00000008)) {
-               if (ctrl & 0x00000001) {
-                       u32 coef = nv_rd32(priv, pll + 4);
-                       M = (coef & 0x000000ff) >> 0;
-                       N = (coef & 0x0000ff00) >> 8;
-                       P = (coef & 0x003f0000) >> 16;
-
-                       /* no post-divider on these..
-                        * XXX: it looks more like two post-"dividers" that
-                        * cross each other out in the default RPLL config */
-                       if ((pll & 0x00ff00) == 0x00e800)
-                               P = 1;
-
-                       sclk = read_clk(priv, 0x00 + clk, false);
-               }
-       } else {
-               sclk = read_clk(priv, 0x10 + clk, false);
-       }
-
-       if (M * P)
-               return sclk * N / (M * P);
-       return 0;
-}
-
-static int
-nva3_clock_read(struct nouveau_clock *clk, enum nv_clk_src src)
-{
-       struct nva3_clock_priv *priv = (void *)clk;
-       u32 hsrc;
-
-       switch (src) {
-       case nv_clk_src_crystal:
-               return nv_device(priv)->crystal;
-       case nv_clk_src_core:
-       case nv_clk_src_core_intm:
-               return read_pll(priv, 0x00, 0x4200);
-       case nv_clk_src_shader:
-               return read_pll(priv, 0x01, 0x4220);
-       case nv_clk_src_mem:
-               return read_pll(priv, 0x02, 0x4000);
-       case nv_clk_src_disp:
-               return read_clk(priv, 0x20, false);
-       case nv_clk_src_vdec:
-               return read_clk(priv, 0x21, false);
-       case nv_clk_src_daemon:
-               return read_clk(priv, 0x25, false);
-       case nv_clk_src_host:
-               hsrc = (nv_rd32(priv, 0xc040) & 0x30000000) >> 28;
-               switch (hsrc) {
-               case 0:
-                       return read_clk(priv, 0x1d, false);
-               case 2:
-               case 3:
-                       return 277000;
-               default:
-                       nv_error(clk, "unknown HOST clock source %d\n", hsrc);
-                       return -EINVAL;
-               }
-       default:
-               nv_error(clk, "invalid clock source %d\n", src);
-               return -EINVAL;
-       }
-
-       return 0;
-}
-
-int
-nva3_clk_info(struct nouveau_clock *clock, int clk, u32 khz,
-               struct nva3_clock_info *info)
-{
-       struct nva3_clock_priv *priv = (void *)clock;
-       u32 oclk, sclk, sdiv, diff;
-
-       info->clk = 0;
-
-       switch (khz) {
-       case 27000:
-               info->clk = 0x00000100;
-               return khz;
-       case 100000:
-               info->clk = 0x00002100;
-               return khz;
-       case 108000:
-               info->clk = 0x00002140;
-               return khz;
-       default:
-               sclk = read_vco(priv, clk);
-               sdiv = min((sclk * 2) / khz, (u32)65);
-               oclk = (sclk * 2) / sdiv;
-               diff = ((khz + 3000) - oclk);
-
-               /* When imprecise, play it safe and aim for a clock lower than
-                * desired rather than higher */
-               if (diff < 0) {
-                       sdiv++;
-                       oclk = (sclk * 2) / sdiv;
-               }
-
-               /* divider can go as low as 2, limited here because NVIDIA
-                * and the VBIOS on my NVA8 seem to prefer using the PLL
-                * for 810MHz - is there a good reason?
-                * XXX: PLLs with refclk 810MHz?  */
-               if (sdiv > 4) {
-                       info->clk = (((sdiv - 2) << 16) | 0x00003100);
-                       return oclk;
-               }
-
-               break;
-       }
-
-       return -ERANGE;
-}
-
-int
-nva3_pll_info(struct nouveau_clock *clock, int clk, u32 pll, u32 khz,
-               struct nva3_clock_info *info)
-{
-       struct nouveau_bios *bios = nouveau_bios(clock);
-       struct nva3_clock_priv *priv = (void *)clock;
-       struct nvbios_pll limits;
-       int P, N, M, diff;
-       int ret;
-
-       info->pll = 0;
-
-       /* If we can get a within [-2, 3) MHz of a divider, we'll disable the
-        * PLL and use the divider instead. */
-       ret = nva3_clk_info(clock, clk, khz, info);
-       diff = khz - ret;
-       if (!pll || (diff >= -2000 && diff < 3000)) {
-               goto out;
-       }
-
-       /* Try with PLL */
-       ret = nvbios_pll_parse(bios, pll, &limits);
-       if (ret)
-               return ret;
-
-       ret = nva3_clk_info(clock, clk - 0x10, limits.refclk, info);
-       if (ret != limits.refclk)
-               return -EINVAL;
-
-       ret = nva3_pll_calc(nv_subdev(priv), &limits, khz, &N, NULL, &M, &P);
-       if (ret >= 0) {
-               info->pll = (P << 16) | (N << 8) | M;
-       }
-
-out:
-       info->fb_delay = max(((khz + 7566) / 15133), (u32) 18);
-
-       return ret ? ret : -ERANGE;
-}
-
-static int
-calc_clk(struct nva3_clock_priv *priv, struct nouveau_cstate *cstate,
-        int clk, u32 pll, int idx)
-{
-       int ret = nva3_pll_info(&priv->base, clk, pll, cstate->domain[idx],
-                                 &priv->eng[idx]);
-       if (ret >= 0)
-               return 0;
-       return ret;
-}
-
-static int
-calc_host(struct nva3_clock_priv *priv, struct nouveau_cstate *cstate)
-{
-       int ret = 0;
-       u32 kHz = cstate->domain[nv_clk_src_host];
-       struct nva3_clock_info *info = &priv->eng[nv_clk_src_host];
-
-       if (kHz == 277000) {
-               info->clk = 0;
-               info->host_out = NVA3_HOST_277;
-               return 0;
-       }
-
-       info->host_out = NVA3_HOST_CLK;
-
-       ret = nva3_clk_info(&priv->base, 0x1d, kHz, info);
-       if (ret >= 0)
-               return 0;
-       return ret;
-}
-
-int
-nva3_clock_pre(struct nouveau_clock *clk, unsigned long *flags)
-{
-       struct nouveau_fifo *pfifo = nouveau_fifo(clk);
-
-       /* halt and idle execution engines */
-       nv_mask(clk, 0x020060, 0x00070000, 0x00000000);
-       nv_mask(clk, 0x002504, 0x00000001, 0x00000001);
-       /* Wait until the interrupt handler is finished */
-       if (!nv_wait(clk, 0x000100, 0xffffffff, 0x00000000))
-               return -EBUSY;
-
-       if (pfifo)
-               pfifo->pause(pfifo, flags);
-
-       if (!nv_wait(clk, 0x002504, 0x00000010, 0x00000010))
-               return -EIO;
-       if (!nv_wait(clk, 0x00251c, 0x0000003f, 0x0000003f))
-               return -EIO;
-
-       return 0;
-}
-
-void
-nva3_clock_post(struct nouveau_clock *clk, unsigned long *flags)
-{
-       struct nouveau_fifo *pfifo = nouveau_fifo(clk);
-
-       if (pfifo && flags)
-               pfifo->start(pfifo, flags);
-
-       nv_mask(clk, 0x002504, 0x00000001, 0x00000000);
-       nv_mask(clk, 0x020060, 0x00070000, 0x00040000);
-}
-
-static void
-disable_clk_src(struct nva3_clock_priv *priv, u32 src)
-{
-       nv_mask(priv, src, 0x00000100, 0x00000000);
-       nv_mask(priv, src, 0x00000001, 0x00000000);
-}
-
-static void
-prog_pll(struct nva3_clock_priv *priv, int clk, u32 pll, int idx)
-{
-       struct nva3_clock_info *info = &priv->eng[idx];
-       const u32 src0 = 0x004120 + (clk * 4);
-       const u32 src1 = 0x004160 + (clk * 4);
-       const u32 ctrl = pll + 0;
-       const u32 coef = pll + 4;
-       u32 bypass;
-
-       if (info->pll) {
-               /* Always start from a non-PLL clock */
-               bypass = nv_rd32(priv, ctrl)  & 0x00000008;
-               if (!bypass) {
-                       nv_mask(priv, src1, 0x00000101, 0x00000101);
-                       nv_mask(priv, ctrl, 0x00000008, 0x00000008);
-                       udelay(20);
-               }
-
-               nv_mask(priv, src0, 0x003f3141, 0x00000101 | info->clk);
-               nv_wr32(priv, coef, info->pll);
-               nv_mask(priv, ctrl, 0x00000015, 0x00000015);
-               nv_mask(priv, ctrl, 0x00000010, 0x00000000);
-               if (!nv_wait(priv, ctrl, 0x00020000, 0x00020000)) {
-                       nv_mask(priv, ctrl, 0x00000010, 0x00000010);
-                       nv_mask(priv, src0, 0x00000101, 0x00000000);
-                       return;
-               }
-               nv_mask(priv, ctrl, 0x00000010, 0x00000010);
-               nv_mask(priv, ctrl, 0x00000008, 0x00000000);
-               disable_clk_src(priv, src1);
-       } else {
-               nv_mask(priv, src1, 0x003f3141, 0x00000101 | info->clk);
-               nv_mask(priv, ctrl, 0x00000018, 0x00000018);
-               udelay(20);
-               nv_mask(priv, ctrl, 0x00000001, 0x00000000);
-               disable_clk_src(priv, src0);
-       }
-}
-
-static void
-prog_clk(struct nva3_clock_priv *priv, int clk, int idx)
-{
-       struct nva3_clock_info *info = &priv->eng[idx];
-       nv_mask(priv, 0x004120 + (clk * 4), 0x003f3141, 0x00000101 | info->clk);
-}
-
-static void
-prog_host(struct nva3_clock_priv *priv)
-{
-       struct nva3_clock_info *info = &priv->eng[nv_clk_src_host];
-       u32 hsrc = (nv_rd32(priv, 0xc040));
-
-       switch (info->host_out) {
-       case NVA3_HOST_277:
-               if ((hsrc & 0x30000000) == 0) {
-                       nv_wr32(priv, 0xc040, hsrc | 0x20000000);
-                       disable_clk_src(priv, 0x4194);
-               }
-               break;
-       case NVA3_HOST_CLK:
-               prog_clk(priv, 0x1d, nv_clk_src_host);
-               if ((hsrc & 0x30000000) >= 0x20000000) {
-                       nv_wr32(priv, 0xc040, hsrc & ~0x30000000);
-               }
-               break;
-       default:
-               break;
-       }
-
-       /* This seems to be a clock gating factor on idle, always set to 64 */
-       nv_wr32(priv, 0xc044, 0x3e);
-}
-
-static void
-prog_core(struct nva3_clock_priv *priv, int idx)
-{
-       struct nva3_clock_info *info = &priv->eng[idx];
-       u32 fb_delay = nv_rd32(priv, 0x10002c);
-
-       if (fb_delay < info->fb_delay)
-               nv_wr32(priv, 0x10002c, info->fb_delay);
-
-       prog_pll(priv, 0x00, 0x004200, idx);
-
-       if (fb_delay > info->fb_delay)
-               nv_wr32(priv, 0x10002c, info->fb_delay);
-}
-
-static int
-nva3_clock_calc(struct nouveau_clock *clk, struct nouveau_cstate *cstate)
-{
-       struct nva3_clock_priv *priv = (void *)clk;
-       struct nva3_clock_info *core = &priv->eng[nv_clk_src_core];
-       int ret;
-
-       if ((ret = calc_clk(priv, cstate, 0x10, 0x4200, nv_clk_src_core)) ||
-           (ret = calc_clk(priv, cstate, 0x11, 0x4220, nv_clk_src_shader)) ||
-           (ret = calc_clk(priv, cstate, 0x20, 0x0000, nv_clk_src_disp)) ||
-           (ret = calc_clk(priv, cstate, 0x21, 0x0000, nv_clk_src_vdec)) ||
-           (ret = calc_host(priv, cstate)))
-               return ret;
-
-       /* XXX: Should be reading the highest bit in the VBIOS clock to decide
-        * whether to use a PLL or not... but using a PLL defeats the purpose */
-       if (core->pll) {
-               ret = nva3_clk_info(clk, 0x10,
-                               cstate->domain[nv_clk_src_core_intm],
-                               &priv->eng[nv_clk_src_core_intm]);
-               if (ret < 0)
-                       return ret;
-       }
-
-       return 0;
-}
-
-static int
-nva3_clock_prog(struct nouveau_clock *clk)
-{
-       struct nva3_clock_priv *priv = (void *)clk;
-       struct nva3_clock_info *core = &priv->eng[nv_clk_src_core];
-       int ret = 0;
-       unsigned long flags;
-       unsigned long *f = &flags;
-
-       ret = nva3_clock_pre(clk, f);
-       if (ret)
-               goto out;
-
-       if (core->pll)
-               prog_core(priv, nv_clk_src_core_intm);
-
-       prog_core(priv,  nv_clk_src_core);
-       prog_pll(priv, 0x01, 0x004220, nv_clk_src_shader);
-       prog_clk(priv, 0x20, nv_clk_src_disp);
-       prog_clk(priv, 0x21, nv_clk_src_vdec);
-       prog_host(priv);
-
-out:
-       if (ret == -EBUSY)
-               f = NULL;
-
-       nva3_clock_post(clk, f);
-
-       return ret;
-}
-
-static void
-nva3_clock_tidy(struct nouveau_clock *clk)
-{
-}
-
-static struct nouveau_clocks
-nva3_domain[] = {
-       { nv_clk_src_crystal  , 0xff },
-       { nv_clk_src_core     , 0x00, 0, "core", 1000 },
-       { nv_clk_src_shader   , 0x01, 0, "shader", 1000 },
-       { nv_clk_src_mem      , 0x02, 0, "memory", 1000 },
-       { nv_clk_src_vdec     , 0x03 },
-       { nv_clk_src_disp     , 0x04 },
-       { nv_clk_src_host     , 0x05 },
-       { nv_clk_src_core_intm, 0x06 },
-       { nv_clk_src_max }
-};
-
-static int
-nva3_clock_ctor(struct nouveau_object *parent, struct nouveau_object *engine,
-               struct nouveau_oclass *oclass, void *data, u32 size,
-               struct nouveau_object **pobject)
-{
-       struct nva3_clock_priv *priv;
-       int ret;
-
-       ret = nouveau_clock_create(parent, engine, oclass, nva3_domain, NULL, 0,
-                                  true, &priv);
-       *pobject = nv_object(priv);
-       if (ret)
-               return ret;
-
-       priv->base.read = nva3_clock_read;
-       priv->base.calc = nva3_clock_calc;
-       priv->base.prog = nva3_clock_prog;
-       priv->base.tidy = nva3_clock_tidy;
-       return 0;
-}
-
-struct nouveau_oclass
-nva3_clock_oclass = {
-       .handle = NV_SUBDEV(CLOCK, 0xa3),
-       .ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nva3_clock_ctor,
-               .dtor = _nouveau_clock_dtor,
-               .init = _nouveau_clock_init,
-               .fini = _nouveau_clock_fini,
-       },
-};
diff --git a/drivers/gpu/drm/nouveau/core/subdev/clock/nva3.h b/drivers/gpu/drm/nouveau/core/subdev/clock/nva3.h
deleted file mode 100644 (file)
index a45a103..0000000
+++ /dev/null
@@ -1,20 +0,0 @@
-#ifndef __NVKM_CLK_NVA3_H__
-#define __NVKM_CLK_NVA3_H__
-
-#include <subdev/clock.h>
-
-struct nva3_clock_info {
-       u32 clk;
-       u32 pll;
-       enum {
-               NVA3_HOST_277,
-               NVA3_HOST_CLK,
-       } host_out;
-       u32 fb_delay;
-};
-
-int nva3_pll_info(struct nouveau_clock *, int, u32, u32,
-                   struct nva3_clock_info *);
-int nva3_clock_pre(struct nouveau_clock *clk, unsigned long *flags);
-void nva3_clock_post(struct nouveau_clock *clk, unsigned long *flags);
-#endif
diff --git a/drivers/gpu/drm/nouveau/core/subdev/clock/nvaa.c b/drivers/gpu/drm/nouveau/core/subdev/clock/nvaa.c
deleted file mode 100644 (file)
index 54aeab8..0000000
+++ /dev/null
@@ -1,435 +0,0 @@
-/*
- * Copyright 2012 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 <engine/fifo.h>
-#include <subdev/bios.h>
-#include <subdev/bios/pll.h>
-#include <subdev/timer.h>
-#include <subdev/clock.h>
-
-#include "nva3.h"
-#include "pll.h"
-
-struct nvaa_clock_priv {
-       struct nouveau_clock base;
-       enum nv_clk_src csrc, ssrc, vsrc;
-       u32 cctrl, sctrl;
-       u32 ccoef, scoef;
-       u32 cpost, spost;
-       u32 vdiv;
-};
-
-static u32
-read_div(struct nouveau_clock *clk)
-{
-       return nv_rd32(clk, 0x004600);
-}
-
-static u32
-read_pll(struct nouveau_clock *clk, u32 base)
-{
-       u32 ctrl = nv_rd32(clk, base + 0);
-       u32 coef = nv_rd32(clk, base + 4);
-       u32 ref = clk->read(clk, nv_clk_src_href);
-       u32 post_div = 0;
-       u32 clock = 0;
-       int N1, M1;
-
-       switch (base){
-       case 0x4020:
-               post_div = 1 << ((nv_rd32(clk, 0x4070) & 0x000f0000) >> 16);
-               break;
-       case 0x4028:
-               post_div = (nv_rd32(clk, 0x4040) & 0x000f0000) >> 16;
-               break;
-       default:
-               break;
-       }
-
-       N1 = (coef & 0x0000ff00) >> 8;
-       M1 = (coef & 0x000000ff);
-       if ((ctrl & 0x80000000) && M1) {
-               clock = ref * N1 / M1;
-               clock = clock / post_div;
-       }
-
-       return clock;
-}
-
-static int
-nvaa_clock_read(struct nouveau_clock *clk, enum nv_clk_src src)
-{
-       struct nvaa_clock_priv *priv = (void *)clk;
-       u32 mast = nv_rd32(clk, 0x00c054);
-       u32 P = 0;
-
-       switch (src) {
-       case nv_clk_src_crystal:
-               return nv_device(priv)->crystal;
-       case nv_clk_src_href:
-               return 100000; /* PCIE reference clock */
-       case nv_clk_src_hclkm4:
-               return clk->read(clk, nv_clk_src_href) * 4;
-       case nv_clk_src_hclkm2d3:
-               return clk->read(clk, nv_clk_src_href) * 2 / 3;
-       case nv_clk_src_host:
-               switch (mast & 0x000c0000) {
-               case 0x00000000: return clk->read(clk, nv_clk_src_hclkm2d3);
-               case 0x00040000: break;
-               case 0x00080000: return clk->read(clk, nv_clk_src_hclkm4);
-               case 0x000c0000: return clk->read(clk, nv_clk_src_cclk);
-               }
-               break;
-       case nv_clk_src_core:
-               P = (nv_rd32(clk, 0x004028) & 0x00070000) >> 16;
-
-               switch (mast & 0x00000003) {
-               case 0x00000000: return clk->read(clk, nv_clk_src_crystal) >> P;
-               case 0x00000001: return 0;
-               case 0x00000002: return clk->read(clk, nv_clk_src_hclkm4) >> P;
-               case 0x00000003: return read_pll(clk, 0x004028) >> P;
-               }
-               break;
-       case nv_clk_src_cclk:
-               if ((mast & 0x03000000) != 0x03000000)
-                       return clk->read(clk, nv_clk_src_core);
-
-               if ((mast & 0x00000200) == 0x00000000)
-                       return clk->read(clk, nv_clk_src_core);
-
-               switch (mast & 0x00000c00) {
-               case 0x00000000: return clk->read(clk, nv_clk_src_href);
-               case 0x00000400: return clk->read(clk, nv_clk_src_hclkm4);
-               case 0x00000800: return clk->read(clk, nv_clk_src_hclkm2d3);
-               default: return 0;
-               }
-       case nv_clk_src_shader:
-               P = (nv_rd32(clk, 0x004020) & 0x00070000) >> 16;
-               switch (mast & 0x00000030) {
-               case 0x00000000:
-                       if (mast & 0x00000040)
-                               return clk->read(clk, nv_clk_src_href) >> P;
-                       return clk->read(clk, nv_clk_src_crystal) >> P;
-               case 0x00000010: break;
-               case 0x00000020: return read_pll(clk, 0x004028) >> P;
-               case 0x00000030: return read_pll(clk, 0x004020) >> P;
-               }
-               break;
-       case nv_clk_src_mem:
-               return 0;
-               break;
-       case nv_clk_src_vdec:
-               P = (read_div(clk) & 0x00000700) >> 8;
-
-               switch (mast & 0x00400000) {
-               case 0x00400000:
-                       return clk->read(clk, nv_clk_src_core) >> P;
-                       break;
-               default:
-                       return 500000 >> P;
-                       break;
-               }
-               break;
-       default:
-               break;
-       }
-
-       nv_debug(priv, "unknown clock source %d 0x%08x\n", src, mast);
-       return 0;
-}
-
-static u32
-calc_pll(struct nvaa_clock_priv *priv, u32 reg,
-        u32 clock, int *N, int *M, int *P)
-{
-       struct nouveau_bios *bios = nouveau_bios(priv);
-       struct nvbios_pll pll;
-       struct nouveau_clock *clk = &priv->base;
-       int ret;
-
-       ret = nvbios_pll_parse(bios, reg, &pll);
-       if (ret)
-               return 0;
-
-       pll.vco2.max_freq = 0;
-       pll.refclk = clk->read(clk, nv_clk_src_href);
-       if (!pll.refclk)
-               return 0;
-
-       return nv04_pll_calc(nv_subdev(priv), &pll, clock, N, M, NULL, NULL, P);
-}
-
-static inline u32
-calc_P(u32 src, u32 target, int *div)
-{
-       u32 clk0 = src, clk1 = src;
-       for (*div = 0; *div <= 7; (*div)++) {
-               if (clk0 <= target) {
-                       clk1 = clk0 << (*div ? 1 : 0);
-                       break;
-               }
-               clk0 >>= 1;
-       }
-
-       if (target - clk0 <= clk1 - target)
-               return clk0;
-       (*div)--;
-       return clk1;
-}
-
-static int
-nvaa_clock_calc(struct nouveau_clock *clk, struct nouveau_cstate *cstate)
-{
-       struct nvaa_clock_priv *priv = (void *)clk;
-       const int shader = cstate->domain[nv_clk_src_shader];
-       const int core = cstate->domain[nv_clk_src_core];
-       const int vdec = cstate->domain[nv_clk_src_vdec];
-       u32 out = 0, clock = 0;
-       int N, M, P1, P2 = 0;
-       int divs = 0;
-
-       /* cclk: find suitable source, disable PLL if we can */
-       if (core < clk->read(clk, nv_clk_src_hclkm4))
-               out = calc_P(clk->read(clk, nv_clk_src_hclkm4), core, &divs);
-
-       /* Calculate clock * 2, so shader clock can use it too */
-       clock = calc_pll(priv, 0x4028, (core << 1), &N, &M, &P1);
-
-       if (abs(core - out) <=
-           abs(core - (clock >> 1))) {
-               priv->csrc = nv_clk_src_hclkm4;
-               priv->cctrl = divs << 16;
-       } else {
-               /* NVCTRL is actually used _after_ NVPOST, and after what we
-                * call NVPLL. To make matters worse, NVPOST is an integer
-                * divider instead of a right-shift number. */
-               if(P1 > 2) {
-                       P2 = P1 - 2;
-                       P1 = 2;
-               }
-
-               priv->csrc = nv_clk_src_core;
-               priv->ccoef = (N << 8) | M;
-
-               priv->cctrl = (P2 + 1) << 16;
-               priv->cpost = (1 << P1) << 16;
-       }
-
-       /* sclk: nvpll + divisor, href or spll */
-       out = 0;
-       if (shader == clk->read(clk, nv_clk_src_href)) {
-               priv->ssrc = nv_clk_src_href;
-       } else {
-               clock = calc_pll(priv, 0x4020, shader, &N, &M, &P1);
-               if (priv->csrc == nv_clk_src_core) {
-                       out = calc_P((core << 1), shader, &divs);
-               }
-
-               if (abs(shader - out) <=
-                   abs(shader - clock) &&
-                  (divs + P2) <= 7) {
-                       priv->ssrc = nv_clk_src_core;
-                       priv->sctrl = (divs + P2) << 16;
-               } else {
-                       priv->ssrc = nv_clk_src_shader;
-                       priv->scoef = (N << 8) | M;
-                       priv->sctrl = P1 << 16;
-               }
-       }
-
-       /* vclk */
-       out = calc_P(core, vdec, &divs);
-       clock = calc_P(500000, vdec, &P1);
-       if(abs(vdec - out) <=
-          abs(vdec - clock)) {
-               priv->vsrc = nv_clk_src_cclk;
-               priv->vdiv = divs << 16;
-       } else {
-               priv->vsrc = nv_clk_src_vdec;
-               priv->vdiv = P1 << 16;
-       }
-
-       /* Print strategy! */
-       nv_debug(priv, "nvpll: %08x %08x %08x\n",
-                       priv->ccoef, priv->cpost, priv->cctrl);
-       nv_debug(priv, " spll: %08x %08x %08x\n",
-                       priv->scoef, priv->spost, priv->sctrl);
-       nv_debug(priv, " vdiv: %08x\n", priv->vdiv);
-       if (priv->csrc == nv_clk_src_hclkm4)
-               nv_debug(priv, "core: hrefm4\n");
-       else
-               nv_debug(priv, "core: nvpll\n");
-
-       if (priv->ssrc == nv_clk_src_hclkm4)
-               nv_debug(priv, "shader: hrefm4\n");
-       else if (priv->ssrc == nv_clk_src_core)
-               nv_debug(priv, "shader: nvpll\n");
-       else
-               nv_debug(priv, "shader: spll\n");
-
-       if (priv->vsrc == nv_clk_src_hclkm4)
-               nv_debug(priv, "vdec: 500MHz\n");
-       else
-               nv_debug(priv, "vdec: core\n");
-
-       return 0;
-}
-
-static int
-nvaa_clock_prog(struct nouveau_clock *clk)
-{
-       struct nvaa_clock_priv *priv = (void *)clk;
-       u32 pllmask = 0, mast;
-       unsigned long flags;
-       unsigned long *f = &flags;
-       int ret = 0;
-
-       ret = nva3_clock_pre(clk, f);
-       if (ret)
-               goto out;
-
-       /* First switch to safe clocks: href */
-       mast = nv_mask(clk, 0xc054, 0x03400e70, 0x03400640);
-       mast &= ~0x00400e73;
-       mast |= 0x03000000;
-
-       switch (priv->csrc) {
-       case nv_clk_src_hclkm4:
-               nv_mask(clk, 0x4028, 0x00070000, priv->cctrl);
-               mast |= 0x00000002;
-               break;
-       case nv_clk_src_core:
-               nv_wr32(clk, 0x402c, priv->ccoef);
-               nv_wr32(clk, 0x4028, 0x80000000 | priv->cctrl);
-               nv_wr32(clk, 0x4040, priv->cpost);
-               pllmask |= (0x3 << 8);
-               mast |= 0x00000003;
-               break;
-       default:
-               nv_warn(priv,"Reclocking failed: unknown core clock\n");
-               goto resume;
-       }
-
-       switch (priv->ssrc) {
-       case nv_clk_src_href:
-               nv_mask(clk, 0x4020, 0x00070000, 0x00000000);
-               /* mast |= 0x00000000; */
-               break;
-       case nv_clk_src_core:
-               nv_mask(clk, 0x4020, 0x00070000, priv->sctrl);
-               mast |= 0x00000020;
-               break;
-       case nv_clk_src_shader:
-               nv_wr32(clk, 0x4024, priv->scoef);
-               nv_wr32(clk, 0x4020, 0x80000000 | priv->sctrl);
-               nv_wr32(clk, 0x4070, priv->spost);
-               pllmask |= (0x3 << 12);
-               mast |= 0x00000030;
-               break;
-       default:
-               nv_warn(priv,"Reclocking failed: unknown sclk clock\n");
-               goto resume;
-       }
-
-       if (!nv_wait(clk, 0x004080, pllmask, pllmask)) {
-               nv_warn(priv,"Reclocking failed: unstable PLLs\n");
-               goto resume;
-       }
-
-       switch (priv->vsrc) {
-       case nv_clk_src_cclk:
-               mast |= 0x00400000;
-       default:
-               nv_wr32(clk, 0x4600, priv->vdiv);
-       }
-
-       nv_wr32(clk, 0xc054, mast);
-
-resume:
-       /* Disable some PLLs and dividers when unused */
-       if (priv->csrc != nv_clk_src_core) {
-               nv_wr32(clk, 0x4040, 0x00000000);
-               nv_mask(clk, 0x4028, 0x80000000, 0x00000000);
-       }
-
-       if (priv->ssrc != nv_clk_src_shader) {
-               nv_wr32(clk, 0x4070, 0x00000000);
-               nv_mask(clk, 0x4020, 0x80000000, 0x00000000);
-       }
-
-out:
-       if (ret == -EBUSY)
-               f = NULL;
-
-       nva3_clock_post(clk, f);
-
-       return ret;
-}
-
-static void
-nvaa_clock_tidy(struct nouveau_clock *clk)
-{
-}
-
-static struct nouveau_clocks
-nvaa_domains[] = {
-       { nv_clk_src_crystal, 0xff },
-       { nv_clk_src_href   , 0xff },
-       { nv_clk_src_core   , 0xff, 0, "core", 1000 },
-       { nv_clk_src_shader , 0xff, 0, "shader", 1000 },
-       { nv_clk_src_vdec   , 0xff, 0, "vdec", 1000 },
-       { nv_clk_src_max }
-};
-
-static int
-nvaa_clock_ctor(struct nouveau_object *parent, struct nouveau_object *engine,
-               struct nouveau_oclass *oclass, void *data, u32 size,
-               struct nouveau_object **pobject)
-{
-       struct nvaa_clock_priv *priv;
-       int ret;
-
-       ret = nouveau_clock_create(parent, engine, oclass, nvaa_domains, NULL,
-                                  0, true, &priv);
-       *pobject = nv_object(priv);
-       if (ret)
-               return ret;
-
-       priv->base.read = nvaa_clock_read;
-       priv->base.calc = nvaa_clock_calc;
-       priv->base.prog = nvaa_clock_prog;
-       priv->base.tidy = nvaa_clock_tidy;
-       return 0;
-}
-
-struct nouveau_oclass *
-nvaa_clock_oclass = &(struct nouveau_oclass) {
-       .handle = NV_SUBDEV(CLOCK, 0xaa),
-       .ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nvaa_clock_ctor,
-               .dtor = _nouveau_clock_dtor,
-               .init = _nouveau_clock_init,
-               .fini = _nouveau_clock_fini,
-       },
-};
diff --git a/drivers/gpu/drm/nouveau/core/subdev/clock/nvc0.c b/drivers/gpu/drm/nouveau/core/subdev/clock/nvc0.c
deleted file mode 100644 (file)
index 1234aba..0000000
+++ /dev/null
@@ -1,462 +0,0 @@
-/*
- * Copyright 2012 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 <subdev/clock.h>
-#include <subdev/bios.h>
-#include <subdev/bios/pll.h>
-#include <subdev/timer.h>
-
-#include "pll.h"
-
-struct nvc0_clock_info {
-       u32 freq;
-       u32 ssel;
-       u32 mdiv;
-       u32 dsrc;
-       u32 ddiv;
-       u32 coef;
-};
-
-struct nvc0_clock_priv {
-       struct nouveau_clock base;
-       struct nvc0_clock_info eng[16];
-};
-
-static u32 read_div(struct nvc0_clock_priv *, int, u32, u32);
-
-static u32
-read_vco(struct nvc0_clock_priv *priv, u32 dsrc)
-{
-       struct nouveau_clock *clk = &priv->base;
-       u32 ssrc = nv_rd32(priv, dsrc);
-       if (!(ssrc & 0x00000100))
-               return clk->read(clk, nv_clk_src_sppll0);
-       return clk->read(clk, nv_clk_src_sppll1);
-}
-
-static u32
-read_pll(struct nvc0_clock_priv *priv, u32 pll)
-{
-       struct nouveau_clock *clk = &priv->base;
-       u32 ctrl = nv_rd32(priv, pll + 0x00);
-       u32 coef = nv_rd32(priv, pll + 0x04);
-       u32 P = (coef & 0x003f0000) >> 16;
-       u32 N = (coef & 0x0000ff00) >> 8;
-       u32 M = (coef & 0x000000ff) >> 0;
-       u32 sclk;
-
-       if (!(ctrl & 0x00000001))
-               return 0;
-
-       switch (pll) {
-       case 0x00e800:
-       case 0x00e820:
-               sclk = nv_device(priv)->crystal;
-               P = 1;
-               break;
-       case 0x132000:
-               sclk = clk->read(clk, nv_clk_src_mpllsrc);
-               break;
-       case 0x132020:
-               sclk = clk->read(clk, nv_clk_src_mpllsrcref);
-               break;
-       case 0x137000:
-       case 0x137020:
-       case 0x137040:
-       case 0x1370e0:
-               sclk = read_div(priv, (pll & 0xff) / 0x20, 0x137120, 0x137140);
-               break;
-       default:
-               return 0;
-       }
-
-       return sclk * N / M / P;
-}
-
-static u32
-read_div(struct nvc0_clock_priv *priv, int doff, u32 dsrc, u32 dctl)
-{
-       u32 ssrc = nv_rd32(priv, dsrc + (doff * 4));
-       u32 sctl = nv_rd32(priv, dctl + (doff * 4));
-
-       switch (ssrc & 0x00000003) {
-       case 0:
-               if ((ssrc & 0x00030000) != 0x00030000)
-                       return nv_device(priv)->crystal;
-               return 108000;
-       case 2:
-               return 100000;
-       case 3:
-               if (sctl & 0x80000000) {
-                       u32 sclk = read_vco(priv, dsrc + (doff * 4));
-                       u32 sdiv = (sctl & 0x0000003f) + 2;
-                       return (sclk * 2) / sdiv;
-               }
-
-               return read_vco(priv, dsrc + (doff * 4));
-       default:
-               return 0;
-       }
-}
-
-static u32
-read_clk(struct nvc0_clock_priv *priv, int clk)
-{
-       u32 sctl = nv_rd32(priv, 0x137250 + (clk * 4));
-       u32 ssel = nv_rd32(priv, 0x137100);
-       u32 sclk, sdiv;
-
-       if (ssel & (1 << clk)) {
-               if (clk < 7)
-                       sclk = read_pll(priv, 0x137000 + (clk * 0x20));
-               else
-                       sclk = read_pll(priv, 0x1370e0);
-               sdiv = ((sctl & 0x00003f00) >> 8) + 2;
-       } else {
-               sclk = read_div(priv, clk, 0x137160, 0x1371d0);
-               sdiv = ((sctl & 0x0000003f) >> 0) + 2;
-       }
-
-       if (sctl & 0x80000000)
-               return (sclk * 2) / sdiv;
-
-       return sclk;
-}
-
-static int
-nvc0_clock_read(struct nouveau_clock *clk, enum nv_clk_src src)
-{
-       struct nouveau_device *device = nv_device(clk);
-       struct nvc0_clock_priv *priv = (void *)clk;
-
-       switch (src) {
-       case nv_clk_src_crystal:
-               return device->crystal;
-       case nv_clk_src_href:
-               return 100000;
-       case nv_clk_src_sppll0:
-               return read_pll(priv, 0x00e800);
-       case nv_clk_src_sppll1:
-               return read_pll(priv, 0x00e820);
-
-       case nv_clk_src_mpllsrcref:
-               return read_div(priv, 0, 0x137320, 0x137330);
-       case nv_clk_src_mpllsrc:
-               return read_pll(priv, 0x132020);
-       case nv_clk_src_mpll:
-               return read_pll(priv, 0x132000);
-       case nv_clk_src_mdiv:
-               return read_div(priv, 0, 0x137300, 0x137310);
-       case nv_clk_src_mem:
-               if (nv_rd32(priv, 0x1373f0) & 0x00000002)
-                       return clk->read(clk, nv_clk_src_mpll);
-               return clk->read(clk, nv_clk_src_mdiv);
-
-       case nv_clk_src_gpc:
-               return read_clk(priv, 0x00);
-       case nv_clk_src_rop:
-               return read_clk(priv, 0x01);
-       case nv_clk_src_hubk07:
-               return read_clk(priv, 0x02);
-       case nv_clk_src_hubk06:
-               return read_clk(priv, 0x07);
-       case nv_clk_src_hubk01:
-               return read_clk(priv, 0x08);
-       case nv_clk_src_copy:
-               return read_clk(priv, 0x09);
-       case nv_clk_src_daemon:
-               return read_clk(priv, 0x0c);
-       case nv_clk_src_vdec:
-               return read_clk(priv, 0x0e);
-       default:
-               nv_error(clk, "invalid clock source %d\n", src);
-               return -EINVAL;
-       }
-}
-
-static u32
-calc_div(struct nvc0_clock_priv *priv, int clk, u32 ref, u32 freq, u32 *ddiv)
-{
-       u32 div = min((ref * 2) / freq, (u32)65);
-       if (div < 2)
-               div = 2;
-
-       *ddiv = div - 2;
-       return (ref * 2) / div;
-}
-
-static u32
-calc_src(struct nvc0_clock_priv *priv, int clk, u32 freq, u32 *dsrc, u32 *ddiv)
-{
-       u32 sclk;
-
-       /* use one of the fixed frequencies if possible */
-       *ddiv = 0x00000000;
-       switch (freq) {
-       case  27000:
-       case 108000:
-               *dsrc = 0x00000000;
-               if (freq == 108000)
-                       *dsrc |= 0x00030000;
-               return freq;
-       case 100000:
-               *dsrc = 0x00000002;
-               return freq;
-       default:
-               *dsrc = 0x00000003;
-               break;
-       }
-
-       /* otherwise, calculate the closest divider */
-       sclk = read_vco(priv, 0x137160 + (clk * 4));
-       if (clk < 7)
-               sclk = calc_div(priv, clk, sclk, freq, ddiv);
-       return sclk;
-}
-
-static u32
-calc_pll(struct nvc0_clock_priv *priv, int clk, u32 freq, u32 *coef)
-{
-       struct nouveau_bios *bios = nouveau_bios(priv);
-       struct nvbios_pll limits;
-       int N, M, P, ret;
-
-       ret = nvbios_pll_parse(bios, 0x137000 + (clk * 0x20), &limits);
-       if (ret)
-               return 0;
-
-       limits.refclk = read_div(priv, clk, 0x137120, 0x137140);
-       if (!limits.refclk)
-               return 0;
-
-       ret = nva3_pll_calc(nv_subdev(priv), &limits, freq, &N, NULL, &M, &P);
-       if (ret <= 0)
-               return 0;
-
-       *coef = (P << 16) | (N << 8) | M;
-       return ret;
-}
-
-static int
-calc_clk(struct nvc0_clock_priv *priv,
-        struct nouveau_cstate *cstate, int clk, int dom)
-{
-       struct nvc0_clock_info *info = &priv->eng[clk];
-       u32 freq = cstate->domain[dom];
-       u32 src0, div0, div1D, div1P = 0;
-       u32 clk0, clk1 = 0;
-
-       /* invalid clock domain */
-       if (!freq)
-               return 0;
-
-       /* first possible path, using only dividers */
-       clk0 = calc_src(priv, clk, freq, &src0, &div0);
-       clk0 = calc_div(priv, clk, clk0, freq, &div1D);
-
-       /* see if we can get any closer using PLLs */
-       if (clk0 != freq && (0x00004387 & (1 << clk))) {
-               if (clk <= 7)
-                       clk1 = calc_pll(priv, clk, freq, &info->coef);
-               else
-                       clk1 = cstate->domain[nv_clk_src_hubk06];
-               clk1 = calc_div(priv, clk, clk1, freq, &div1P);
-       }
-
-       /* select the method which gets closest to target freq */
-       if (abs((int)freq - clk0) <= abs((int)freq - clk1)) {
-               info->dsrc = src0;
-               if (div0) {
-                       info->ddiv |= 0x80000000;
-                       info->ddiv |= div0 << 8;
-                       info->ddiv |= div0;
-               }
-               if (div1D) {
-                       info->mdiv |= 0x80000000;
-                       info->mdiv |= div1D;
-               }
-               info->ssel = info->coef = 0;
-               info->freq = clk0;
-       } else {
-               if (div1P) {
-                       info->mdiv |= 0x80000000;
-                       info->mdiv |= div1P << 8;
-               }
-               info->ssel = (1 << clk);
-               info->freq = clk1;
-       }
-
-       return 0;
-}
-
-static int
-nvc0_clock_calc(struct nouveau_clock *clk, struct nouveau_cstate *cstate)
-{
-       struct nvc0_clock_priv *priv = (void *)clk;
-       int ret;
-
-       if ((ret = calc_clk(priv, cstate, 0x00, nv_clk_src_gpc)) ||
-           (ret = calc_clk(priv, cstate, 0x01, nv_clk_src_rop)) ||
-           (ret = calc_clk(priv, cstate, 0x02, nv_clk_src_hubk07)) ||
-           (ret = calc_clk(priv, cstate, 0x07, nv_clk_src_hubk06)) ||
-           (ret = calc_clk(priv, cstate, 0x08, nv_clk_src_hubk01)) ||
-           (ret = calc_clk(priv, cstate, 0x09, nv_clk_src_copy)) ||
-           (ret = calc_clk(priv, cstate, 0x0c, nv_clk_src_daemon)) ||
-           (ret = calc_clk(priv, cstate, 0x0e, nv_clk_src_vdec)))
-               return ret;
-
-       return 0;
-}
-
-static void
-nvc0_clock_prog_0(struct nvc0_clock_priv *priv, int clk)
-{
-       struct nvc0_clock_info *info = &priv->eng[clk];
-       if (clk < 7 && !info->ssel) {
-               nv_mask(priv, 0x1371d0 + (clk * 0x04), 0x80003f3f, info->ddiv);
-               nv_wr32(priv, 0x137160 + (clk * 0x04), info->dsrc);
-       }
-}
-
-static void
-nvc0_clock_prog_1(struct nvc0_clock_priv *priv, int clk)
-{
-       nv_mask(priv, 0x137100, (1 << clk), 0x00000000);
-       nv_wait(priv, 0x137100, (1 << clk), 0x00000000);
-}
-
-static void
-nvc0_clock_prog_2(struct nvc0_clock_priv *priv, int clk)
-{
-       struct nvc0_clock_info *info = &priv->eng[clk];
-       const u32 addr = 0x137000 + (clk * 0x20);
-       if (clk <= 7) {
-               nv_mask(priv, addr + 0x00, 0x00000004, 0x00000000);
-               nv_mask(priv, addr + 0x00, 0x00000001, 0x00000000);
-               if (info->coef) {
-                       nv_wr32(priv, addr + 0x04, info->coef);
-                       nv_mask(priv, addr + 0x00, 0x00000001, 0x00000001);
-                       nv_wait(priv, addr + 0x00, 0x00020000, 0x00020000);
-                       nv_mask(priv, addr + 0x00, 0x00020004, 0x00000004);
-               }
-       }
-}
-
-static void
-nvc0_clock_prog_3(struct nvc0_clock_priv *priv, int clk)
-{
-       struct nvc0_clock_info *info = &priv->eng[clk];
-       if (info->ssel) {
-               nv_mask(priv, 0x137100, (1 << clk), info->ssel);
-               nv_wait(priv, 0x137100, (1 << clk), info->ssel);
-       }
-}
-
-static void
-nvc0_clock_prog_4(struct nvc0_clock_priv *priv, int clk)
-{
-       struct nvc0_clock_info *info = &priv->eng[clk];
-       nv_mask(priv, 0x137250 + (clk * 0x04), 0x00003f3f, info->mdiv);
-}
-
-static int
-nvc0_clock_prog(struct nouveau_clock *clk)
-{
-       struct nvc0_clock_priv *priv = (void *)clk;
-       struct {
-               void (*exec)(struct nvc0_clock_priv *, int);
-       } stage[] = {
-               { nvc0_clock_prog_0 }, /* div programming */
-               { nvc0_clock_prog_1 }, /* select div mode */
-               { nvc0_clock_prog_2 }, /* (maybe) program pll */
-               { nvc0_clock_prog_3 }, /* (maybe) select pll mode */
-               { nvc0_clock_prog_4 }, /* final divider */
-       };
-       int i, j;
-
-       for (i = 0; i < ARRAY_SIZE(stage); i++) {
-               for (j = 0; j < ARRAY_SIZE(priv->eng); j++) {
-                       if (!priv->eng[j].freq)
-                               continue;
-                       stage[i].exec(priv, j);
-               }
-       }
-
-       return 0;
-}
-
-static void
-nvc0_clock_tidy(struct nouveau_clock *clk)
-{
-       struct nvc0_clock_priv *priv = (void *)clk;
-       memset(priv->eng, 0x00, sizeof(priv->eng));
-}
-
-static struct nouveau_clocks
-nvc0_domain[] = {
-       { nv_clk_src_crystal, 0xff },
-       { nv_clk_src_href   , 0xff },
-       { nv_clk_src_hubk06 , 0x00 },
-       { nv_clk_src_hubk01 , 0x01 },
-       { nv_clk_src_copy   , 0x02 },
-       { nv_clk_src_gpc    , 0x03, 0, "core", 2000 },
-       { nv_clk_src_rop    , 0x04 },
-       { nv_clk_src_mem    , 0x05, 0, "memory", 1000 },
-       { nv_clk_src_vdec   , 0x06 },
-       { nv_clk_src_daemon , 0x0a },
-       { nv_clk_src_hubk07 , 0x0b },
-       { nv_clk_src_max }
-};
-
-static int
-nvc0_clock_ctor(struct nouveau_object *parent, struct nouveau_object *engine,
-               struct nouveau_oclass *oclass, void *data, u32 size,
-               struct nouveau_object **pobject)
-{
-       struct nvc0_clock_priv *priv;
-       int ret;
-
-       ret = nouveau_clock_create(parent, engine, oclass, nvc0_domain, NULL, 0,
-                                  false, &priv);
-       *pobject = nv_object(priv);
-       if (ret)
-               return ret;
-
-       priv->base.read = nvc0_clock_read;
-       priv->base.calc = nvc0_clock_calc;
-       priv->base.prog = nvc0_clock_prog;
-       priv->base.tidy = nvc0_clock_tidy;
-       return 0;
-}
-
-struct nouveau_oclass
-nvc0_clock_oclass = {
-       .handle = NV_SUBDEV(CLOCK, 0xc0),
-       .ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nvc0_clock_ctor,
-               .dtor = _nouveau_clock_dtor,
-               .init = _nouveau_clock_init,
-               .fini = _nouveau_clock_fini,
-       },
-};
diff --git a/drivers/gpu/drm/nouveau/core/subdev/clock/nve0.c b/drivers/gpu/drm/nouveau/core/subdev/clock/nve0.c
deleted file mode 100644 (file)
index 7eccad5..0000000
+++ /dev/null
@@ -1,500 +0,0 @@
-/*
- * Copyright 2013 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 <subdev/clock.h>
-#include <subdev/timer.h>
-#include <subdev/bios.h>
-#include <subdev/bios/pll.h>
-
-#include "pll.h"
-
-struct nve0_clock_info {
-       u32 freq;
-       u32 ssel;
-       u32 mdiv;
-       u32 dsrc;
-       u32 ddiv;
-       u32 coef;
-};
-
-struct nve0_clock_priv {
-       struct nouveau_clock base;
-       struct nve0_clock_info eng[16];
-};
-
-static u32 read_div(struct nve0_clock_priv *, int, u32, u32);
-static u32 read_pll(struct nve0_clock_priv *, u32);
-
-static u32
-read_vco(struct nve0_clock_priv *priv, u32 dsrc)
-{
-       u32 ssrc = nv_rd32(priv, dsrc);
-       if (!(ssrc & 0x00000100))
-               return read_pll(priv, 0x00e800);
-       return read_pll(priv, 0x00e820);
-}
-
-static u32
-read_pll(struct nve0_clock_priv *priv, u32 pll)
-{
-       u32 ctrl = nv_rd32(priv, pll + 0x00);
-       u32 coef = nv_rd32(priv, pll + 0x04);
-       u32 P = (coef & 0x003f0000) >> 16;
-       u32 N = (coef & 0x0000ff00) >> 8;
-       u32 M = (coef & 0x000000ff) >> 0;
-       u32 sclk;
-       u16 fN = 0xf000;
-
-       if (!(ctrl & 0x00000001))
-               return 0;
-
-       switch (pll) {
-       case 0x00e800:
-       case 0x00e820:
-               sclk = nv_device(priv)->crystal;
-               P = 1;
-               break;
-       case 0x132000:
-               sclk = read_pll(priv, 0x132020);
-               P = (coef & 0x10000000) ? 2 : 1;
-               break;
-       case 0x132020:
-               sclk = read_div(priv, 0, 0x137320, 0x137330);
-               fN   = nv_rd32(priv, pll + 0x10) >> 16;
-               break;
-       case 0x137000:
-       case 0x137020:
-       case 0x137040:
-       case 0x1370e0:
-               sclk = read_div(priv, (pll & 0xff) / 0x20, 0x137120, 0x137140);
-               break;
-       default:
-               return 0;
-       }
-
-       if (P == 0)
-               P = 1;
-
-       sclk = (sclk * N) + (((u16)(fN + 4096) * sclk) >> 13);
-       return sclk / (M * P);
-}
-
-static u32
-read_div(struct nve0_clock_priv *priv, int doff, u32 dsrc, u32 dctl)
-{
-       u32 ssrc = nv_rd32(priv, dsrc + (doff * 4));
-       u32 sctl = nv_rd32(priv, dctl + (doff * 4));
-
-       switch (ssrc & 0x00000003) {
-       case 0:
-               if ((ssrc & 0x00030000) != 0x00030000)
-                       return nv_device(priv)->crystal;
-               return 108000;
-       case 2:
-               return 100000;
-       case 3:
-               if (sctl & 0x80000000) {
-                       u32 sclk = read_vco(priv, dsrc + (doff * 4));
-                       u32 sdiv = (sctl & 0x0000003f) + 2;
-                       return (sclk * 2) / sdiv;
-               }
-
-               return read_vco(priv, dsrc + (doff * 4));
-       default:
-               return 0;
-       }
-}
-
-static u32
-read_mem(struct nve0_clock_priv *priv)
-{
-       switch (nv_rd32(priv, 0x1373f4) & 0x0000000f) {
-       case 1: return read_pll(priv, 0x132020);
-       case 2: return read_pll(priv, 0x132000);
-       default:
-               return 0;
-       }
-}
-
-static u32
-read_clk(struct nve0_clock_priv *priv, int clk)
-{
-       u32 sctl = nv_rd32(priv, 0x137250 + (clk * 4));
-       u32 sclk, sdiv;
-
-       if (clk < 7) {
-               u32 ssel = nv_rd32(priv, 0x137100);
-               if (ssel & (1 << clk)) {
-                       sclk = read_pll(priv, 0x137000 + (clk * 0x20));
-                       sdiv = 1;
-               } else {
-                       sclk = read_div(priv, clk, 0x137160, 0x1371d0);
-                       sdiv = 0;
-               }
-       } else {
-               u32 ssrc = nv_rd32(priv, 0x137160 + (clk * 0x04));
-               if ((ssrc & 0x00000003) == 0x00000003) {
-                       sclk = read_div(priv, clk, 0x137160, 0x1371d0);
-                       if (ssrc & 0x00000100) {
-                               if (ssrc & 0x40000000)
-                                       sclk = read_pll(priv, 0x1370e0);
-                               sdiv = 1;
-                       } else {
-                               sdiv = 0;
-                       }
-               } else {
-                       sclk = read_div(priv, clk, 0x137160, 0x1371d0);
-                       sdiv = 0;
-               }
-       }
-
-       if (sctl & 0x80000000) {
-               if (sdiv)
-                       sdiv = ((sctl & 0x00003f00) >> 8) + 2;
-               else
-                       sdiv = ((sctl & 0x0000003f) >> 0) + 2;
-               return (sclk * 2) / sdiv;
-       }
-
-       return sclk;
-}
-
-static int
-nve0_clock_read(struct nouveau_clock *clk, enum nv_clk_src src)
-{
-       struct nouveau_device *device = nv_device(clk);
-       struct nve0_clock_priv *priv = (void *)clk;
-
-       switch (src) {
-       case nv_clk_src_crystal:
-               return device->crystal;
-       case nv_clk_src_href:
-               return 100000;
-       case nv_clk_src_mem:
-               return read_mem(priv);
-       case nv_clk_src_gpc:
-               return read_clk(priv, 0x00);
-       case nv_clk_src_rop:
-               return read_clk(priv, 0x01);
-       case nv_clk_src_hubk07:
-               return read_clk(priv, 0x02);
-       case nv_clk_src_hubk06:
-               return read_clk(priv, 0x07);
-       case nv_clk_src_hubk01:
-               return read_clk(priv, 0x08);
-       case nv_clk_src_daemon:
-               return read_clk(priv, 0x0c);
-       case nv_clk_src_vdec:
-               return read_clk(priv, 0x0e);
-       default:
-               nv_error(clk, "invalid clock source %d\n", src);
-               return -EINVAL;
-       }
-}
-
-static u32
-calc_div(struct nve0_clock_priv *priv, int clk, u32 ref, u32 freq, u32 *ddiv)
-{
-       u32 div = min((ref * 2) / freq, (u32)65);
-       if (div < 2)
-               div = 2;
-
-       *ddiv = div - 2;
-       return (ref * 2) / div;
-}
-
-static u32
-calc_src(struct nve0_clock_priv *priv, int clk, u32 freq, u32 *dsrc, u32 *ddiv)
-{
-       u32 sclk;
-
-       /* use one of the fixed frequencies if possible */
-       *ddiv = 0x00000000;
-       switch (freq) {
-       case  27000:
-       case 108000:
-               *dsrc = 0x00000000;
-               if (freq == 108000)
-                       *dsrc |= 0x00030000;
-               return freq;
-       case 100000:
-               *dsrc = 0x00000002;
-               return freq;
-       default:
-               *dsrc = 0x00000003;
-               break;
-       }
-
-       /* otherwise, calculate the closest divider */
-       sclk = read_vco(priv, 0x137160 + (clk * 4));
-       if (clk < 7)
-               sclk = calc_div(priv, clk, sclk, freq, ddiv);
-       return sclk;
-}
-
-static u32
-calc_pll(struct nve0_clock_priv *priv, int clk, u32 freq, u32 *coef)
-{
-       struct nouveau_bios *bios = nouveau_bios(priv);
-       struct nvbios_pll limits;
-       int N, M, P, ret;
-
-       ret = nvbios_pll_parse(bios, 0x137000 + (clk * 0x20), &limits);
-       if (ret)
-               return 0;
-
-       limits.refclk = read_div(priv, clk, 0x137120, 0x137140);
-       if (!limits.refclk)
-               return 0;
-
-       ret = nva3_pll_calc(nv_subdev(priv), &limits, freq, &N, NULL, &M, &P);
-       if (ret <= 0)
-               return 0;
-
-       *coef = (P << 16) | (N << 8) | M;
-       return ret;
-}
-
-static int
-calc_clk(struct nve0_clock_priv *priv,
-        struct nouveau_cstate *cstate, int clk, int dom)
-{
-       struct nve0_clock_info *info = &priv->eng[clk];
-       u32 freq = cstate->domain[dom];
-       u32 src0, div0, div1D, div1P = 0;
-       u32 clk0, clk1 = 0;
-
-       /* invalid clock domain */
-       if (!freq)
-               return 0;
-
-       /* first possible path, using only dividers */
-       clk0 = calc_src(priv, clk, freq, &src0, &div0);
-       clk0 = calc_div(priv, clk, clk0, freq, &div1D);
-
-       /* see if we can get any closer using PLLs */
-       if (clk0 != freq && (0x0000ff87 & (1 << clk))) {
-               if (clk <= 7)
-                       clk1 = calc_pll(priv, clk, freq, &info->coef);
-               else
-                       clk1 = cstate->domain[nv_clk_src_hubk06];
-               clk1 = calc_div(priv, clk, clk1, freq, &div1P);
-       }
-
-       /* select the method which gets closest to target freq */
-       if (abs((int)freq - clk0) <= abs((int)freq - clk1)) {
-               info->dsrc = src0;
-               if (div0) {
-                       info->ddiv |= 0x80000000;
-                       info->ddiv |= div0;
-               }
-               if (div1D) {
-                       info->mdiv |= 0x80000000;
-                       info->mdiv |= div1D;
-               }
-               info->ssel = 0;
-               info->freq = clk0;
-       } else {
-               if (div1P) {
-                       info->mdiv |= 0x80000000;
-                       info->mdiv |= div1P << 8;
-               }
-               info->ssel = (1 << clk);
-               info->dsrc = 0x40000100;
-               info->freq = clk1;
-       }
-
-       return 0;
-}
-
-static int
-nve0_clock_calc(struct nouveau_clock *clk, struct nouveau_cstate *cstate)
-{
-       struct nve0_clock_priv *priv = (void *)clk;
-       int ret;
-
-       if ((ret = calc_clk(priv, cstate, 0x00, nv_clk_src_gpc)) ||
-           (ret = calc_clk(priv, cstate, 0x01, nv_clk_src_rop)) ||
-           (ret = calc_clk(priv, cstate, 0x02, nv_clk_src_hubk07)) ||
-           (ret = calc_clk(priv, cstate, 0x07, nv_clk_src_hubk06)) ||
-           (ret = calc_clk(priv, cstate, 0x08, nv_clk_src_hubk01)) ||
-           (ret = calc_clk(priv, cstate, 0x0c, nv_clk_src_daemon)) ||
-           (ret = calc_clk(priv, cstate, 0x0e, nv_clk_src_vdec)))
-               return ret;
-
-       return 0;
-}
-
-static void
-nve0_clock_prog_0(struct nve0_clock_priv *priv, int clk)
-{
-       struct nve0_clock_info *info = &priv->eng[clk];
-       if (!info->ssel) {
-               nv_mask(priv, 0x1371d0 + (clk * 0x04), 0x8000003f, info->ddiv);
-               nv_wr32(priv, 0x137160 + (clk * 0x04), info->dsrc);
-       }
-}
-
-static void
-nve0_clock_prog_1_0(struct nve0_clock_priv *priv, int clk)
-{
-       nv_mask(priv, 0x137100, (1 << clk), 0x00000000);
-       nv_wait(priv, 0x137100, (1 << clk), 0x00000000);
-}
-
-static void
-nve0_clock_prog_1_1(struct nve0_clock_priv *priv, int clk)
-{
-       nv_mask(priv, 0x137160 + (clk * 0x04), 0x00000100, 0x00000000);
-}
-
-static void
-nve0_clock_prog_2(struct nve0_clock_priv *priv, int clk)
-{
-       struct nve0_clock_info *info = &priv->eng[clk];
-       const u32 addr = 0x137000 + (clk * 0x20);
-       nv_mask(priv, addr + 0x00, 0x00000004, 0x00000000);
-       nv_mask(priv, addr + 0x00, 0x00000001, 0x00000000);
-       if (info->coef) {
-               nv_wr32(priv, addr + 0x04, info->coef);
-               nv_mask(priv, addr + 0x00, 0x00000001, 0x00000001);
-               nv_wait(priv, addr + 0x00, 0x00020000, 0x00020000);
-               nv_mask(priv, addr + 0x00, 0x00020004, 0x00000004);
-       }
-}
-
-static void
-nve0_clock_prog_3(struct nve0_clock_priv *priv, int clk)
-{
-       struct nve0_clock_info *info = &priv->eng[clk];
-       if (info->ssel)
-               nv_mask(priv, 0x137250 + (clk * 0x04), 0x00003f00, info->mdiv);
-       else
-               nv_mask(priv, 0x137250 + (clk * 0x04), 0x0000003f, info->mdiv);
-}
-
-static void
-nve0_clock_prog_4_0(struct nve0_clock_priv *priv, int clk)
-{
-       struct nve0_clock_info *info = &priv->eng[clk];
-       if (info->ssel) {
-               nv_mask(priv, 0x137100, (1 << clk), info->ssel);
-               nv_wait(priv, 0x137100, (1 << clk), info->ssel);
-       }
-}
-
-static void
-nve0_clock_prog_4_1(struct nve0_clock_priv *priv, int clk)
-{
-       struct nve0_clock_info *info = &priv->eng[clk];
-       if (info->ssel) {
-               nv_mask(priv, 0x137160 + (clk * 0x04), 0x40000000, 0x40000000);
-               nv_mask(priv, 0x137160 + (clk * 0x04), 0x00000100, 0x00000100);
-       }
-}
-
-static int
-nve0_clock_prog(struct nouveau_clock *clk)
-{
-       struct nve0_clock_priv *priv = (void *)clk;
-       struct {
-               u32 mask;
-               void (*exec)(struct nve0_clock_priv *, int);
-       } stage[] = {
-               { 0x007f, nve0_clock_prog_0   }, /* div programming */
-               { 0x007f, nve0_clock_prog_1_0 }, /* select div mode */
-               { 0xff80, nve0_clock_prog_1_1 },
-               { 0x00ff, nve0_clock_prog_2   }, /* (maybe) program pll */
-               { 0xff80, nve0_clock_prog_3   }, /* final divider */
-               { 0x007f, nve0_clock_prog_4_0 }, /* (maybe) select pll mode */
-               { 0xff80, nve0_clock_prog_4_1 },
-       };
-       int i, j;
-
-       for (i = 0; i < ARRAY_SIZE(stage); i++) {
-               for (j = 0; j < ARRAY_SIZE(priv->eng); j++) {
-                       if (!(stage[i].mask & (1 << j)))
-                               continue;
-                       if (!priv->eng[j].freq)
-                               continue;
-                       stage[i].exec(priv, j);
-               }
-       }
-
-       return 0;
-}
-
-static void
-nve0_clock_tidy(struct nouveau_clock *clk)
-{
-       struct nve0_clock_priv *priv = (void *)clk;
-       memset(priv->eng, 0x00, sizeof(priv->eng));
-}
-
-static struct nouveau_clocks
-nve0_domain[] = {
-       { nv_clk_src_crystal, 0xff },
-       { nv_clk_src_href   , 0xff },
-       { nv_clk_src_gpc    , 0x00, NVKM_CLK_DOM_FLAG_CORE, "core", 2000 },
-       { nv_clk_src_hubk07 , 0x01, NVKM_CLK_DOM_FLAG_CORE },
-       { nv_clk_src_rop    , 0x02, NVKM_CLK_DOM_FLAG_CORE },
-       { nv_clk_src_mem    , 0x03, 0, "memory", 500 },
-       { nv_clk_src_hubk06 , 0x04, NVKM_CLK_DOM_FLAG_CORE },
-       { nv_clk_src_hubk01 , 0x05 },
-       { nv_clk_src_vdec   , 0x06 },
-       { nv_clk_src_daemon , 0x07 },
-       { nv_clk_src_max }
-};
-
-static int
-nve0_clock_ctor(struct nouveau_object *parent, struct nouveau_object *engine,
-               struct nouveau_oclass *oclass, void *data, u32 size,
-               struct nouveau_object **pobject)
-{
-       struct nve0_clock_priv *priv;
-       int ret;
-
-       ret = nouveau_clock_create(parent, engine, oclass, nve0_domain, NULL, 0,
-                                  true, &priv);
-       *pobject = nv_object(priv);
-       if (ret)
-               return ret;
-
-       priv->base.read = nve0_clock_read;
-       priv->base.calc = nve0_clock_calc;
-       priv->base.prog = nve0_clock_prog;
-       priv->base.tidy = nve0_clock_tidy;
-       return 0;
-}
-
-struct nouveau_oclass
-nve0_clock_oclass = {
-       .handle = NV_SUBDEV(CLOCK, 0xe0),
-       .ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nve0_clock_ctor,
-               .dtor = _nouveau_clock_dtor,
-               .init = _nouveau_clock_init,
-               .fini = _nouveau_clock_fini,
-       },
-};
diff --git a/drivers/gpu/drm/nouveau/core/subdev/clock/pll.h b/drivers/gpu/drm/nouveau/core/subdev/clock/pll.h
deleted file mode 100644 (file)
index 445b14c..0000000
+++ /dev/null
@@ -1,9 +0,0 @@
-#ifndef __NOUVEAU_PLL_H__
-#define __NOUVEAU_PLL_H__
-
-int nv04_pll_calc(struct nouveau_subdev *, struct nvbios_pll *, u32 freq,
-                 int *N1, int *M1, int *N2, int *M2, int *P);
-int nva3_pll_calc(struct nouveau_subdev *, struct nvbios_pll *, u32 freq,
-                 int *N, int *fN, int *M, int *P);
-
-#endif
diff --git a/drivers/gpu/drm/nouveau/core/subdev/clock/pllnv04.c b/drivers/gpu/drm/nouveau/core/subdev/clock/pllnv04.c
deleted file mode 100644 (file)
index b47d543..0000000
+++ /dev/null
@@ -1,246 +0,0 @@
-/*
- * 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 <subdev/bios.h>
-#include <subdev/bios/pll.h>
-
-#include "pll.h"
-
-static int
-getMNP_single(struct nouveau_subdev *subdev, struct nvbios_pll *info, int clk,
-             int *pN, int *pM, int *pP)
-{
-       /* 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 nouveau_bios *bios = nouveau_bios(subdev);
-       int minvco = info->vco1.min_freq, maxvco = info->vco1.max_freq;
-       int minM = info->vco1.min_m, maxM = info->vco1.max_m;
-       int minN = info->vco1.min_n, maxN = info->vco1.max_n;
-       int minU = info->vco1.min_inputfreq;
-       int maxU = info->vco1.max_inputfreq;
-       int minP = info->min_p;
-       int maxP = info->max_p_usable;
-       int crystal = info->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 (bios->version.major < 0x60) {
-               int cv = bios->version.chip;
-               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 = 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 = 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;
-                               *pN = N;
-                               *pM = M;
-                               *pP = thisP;
-                               if (delta == 0) /* except this one */
-                                       return bestclk;
-                       }
-               }
-       }
-
-       return bestclk;
-}
-
-static int
-getMNP_double(struct nouveau_subdev *subdev, struct nvbios_pll *info, int clk,
-             int *pN1, int *pM1, int *pN2, int *pM2, int *pP)
-{
-       /* 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
-        */
-       int chip_version = nouveau_bios(subdev)->version.chip;
-       int minvco1 = info->vco1.min_freq, maxvco1 = info->vco1.max_freq;
-       int minvco2 = info->vco2.min_freq, maxvco2 = info->vco2.max_freq;
-       int minU1 = info->vco1.min_inputfreq, minU2 = info->vco2.min_inputfreq;
-       int maxU1 = info->vco1.max_inputfreq, maxU2 = info->vco2.max_inputfreq;
-       int minM1 = info->vco1.min_m, maxM1 = info->vco1.max_m;
-       int minN1 = info->vco1.min_n, maxN1 = info->vco1.max_n;
-       int minM2 = info->vco2.min_m, maxM2 = info->vco2.max_m;
-       int minN2 = info->vco2.min_n, maxN2 = info->vco2.max_n;
-       int maxlog2P = info->max_p_usable;
-       int crystal = info->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;
-                                       *pN1 = N1;
-                                       *pM1 = M1;
-                                       *pN2 = N2;
-                                       *pM2 = M2;
-                                       *pP = log2P;
-                                       if (delta == 0) /* except this one */
-                                               return bestclk;
-                               }
-                       }
-               }
-       }
-
-       return bestclk;
-}
-
-int
-nv04_pll_calc(struct nouveau_subdev *subdev, struct nvbios_pll *info, u32 freq,
-             int *N1, int *M1, int *N2, int *M2, int *P)
-{
-       int ret;
-
-       if (!info->vco2.max_freq || !N2) {
-               ret = getMNP_single(subdev, info, freq, N1, M1, P);
-               if (N2) {
-                       *N2 = 1;
-                       *M2 = 1;
-               }
-       } else {
-               ret = getMNP_double(subdev, info, freq, N1, M1, N2, M2, P);
-       }
-
-       if (!ret)
-               nv_error(subdev, "unable to compute acceptable pll values\n");
-       return ret;
-}
diff --git a/drivers/gpu/drm/nouveau/core/subdev/clock/pllnva3.c b/drivers/gpu/drm/nouveau/core/subdev/clock/pllnva3.c
deleted file mode 100644 (file)
index 8eca457..0000000
+++ /dev/null
@@ -1,89 +0,0 @@
-/*
- * 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 <subdev/clock.h>
-#include <subdev/bios.h>
-#include <subdev/bios/pll.h>
-
-#include "pll.h"
-
-int
-nva3_pll_calc(struct nouveau_subdev *subdev, struct nvbios_pll *info,
-             u32 freq, int *pN, int *pfN, int *pM, int *P)
-{
-       u32 best_err = ~0, err;
-       int M, lM, hM, N, fN;
-
-       *P = info->vco1.max_freq / freq;
-       if (*P > info->max_p)
-               *P = info->max_p;
-       if (*P < info->min_p)
-               *P = info->min_p;
-
-       lM = (info->refclk + info->vco1.max_inputfreq) / info->vco1.max_inputfreq;
-       lM = max(lM, (int)info->vco1.min_m);
-       hM = (info->refclk + info->vco1.min_inputfreq) / info->vco1.min_inputfreq;
-       hM = min(hM, (int)info->vco1.max_m);
-       lM = min(lM, hM);
-
-       for (M = lM; M <= hM; M++) {
-               u32 tmp = freq * *P * M;
-               N  = tmp / info->refclk;
-               fN = tmp % info->refclk;
-
-               if (!pfN) {
-                       if (fN >= info->refclk / 2)
-                               N++;
-               } else {
-                       if (fN <  info->refclk / 2)
-                               N--;
-                       fN = tmp - (N * info->refclk);
-               }
-
-               if (N < info->vco1.min_n)
-                       continue;
-               if (N > info->vco1.max_n)
-                       break;
-
-               err = abs(freq - (info->refclk * N / M / *P));
-               if (err < best_err) {
-                       best_err = err;
-                       *pN = N;
-                       *pM = M;
-               }
-
-               if (pfN) {
-                       *pfN = ((fN << 13) + info->refclk / 2) / info->refclk;
-                       *pfN = (*pfN - 4096) & 0xffff;
-                       return freq;
-               }
-       }
-
-       if (unlikely(best_err == ~0)) {
-               nv_error(subdev, "unable to find matching pll values\n");
-               return -EINVAL;
-       }
-
-       return info->refclk * *pN / *pM / *P;
-}
diff --git a/drivers/gpu/drm/nouveau/core/subdev/clock/seq.h b/drivers/gpu/drm/nouveau/core/subdev/clock/seq.h
deleted file mode 100644 (file)
index fb33f06..0000000
+++ /dev/null
@@ -1,17 +0,0 @@
-#ifndef __NVKM_CLK_SEQ_H__
-#define __NVKM_CLK_SEQ_H__
-
-#include <subdev/bus.h>
-#include <subdev/bus/hwsq.h>
-
-#define clk_init(s,p)       hwsq_init(&(s)->base, (p))
-#define clk_exec(s,e)       hwsq_exec(&(s)->base, (e))
-#define clk_have(s,r)       ((s)->r_##r.addr != 0x000000)
-#define clk_rd32(s,r)       hwsq_rd32(&(s)->base, &(s)->r_##r)
-#define clk_wr32(s,r,d)     hwsq_wr32(&(s)->base, &(s)->r_##r, (d))
-#define clk_mask(s,r,m,d)   hwsq_mask(&(s)->base, &(s)->r_##r, (m), (d))
-#define clk_setf(s,f,d)     hwsq_setf(&(s)->base, (f), (d))
-#define clk_wait(s,f,d)     hwsq_wait(&(s)->base, (f), (d))
-#define clk_nsec(s,n)       hwsq_nsec(&(s)->base, (n))
-
-#endif
diff --git a/drivers/gpu/drm/nouveau/core/subdev/devinit/base.c b/drivers/gpu/drm/nouveau/core/subdev/devinit/base.c
deleted file mode 100644 (file)
index 0e45cee..0000000
+++ /dev/null
@@ -1,99 +0,0 @@
-/*
- * Copyright 2012 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 <core/option.h>
-
-#include <subdev/vga.h>
-
-#include "priv.h"
-
-int
-_nouveau_devinit_fini(struct nouveau_object *object, bool suspend)
-{
-       struct nouveau_devinit *devinit = (void *)object;
-
-       /* force full reinit on resume */
-       if (suspend)
-               devinit->post = true;
-
-       /* unlock the extended vga crtc regs */
-       nv_lockvgac(devinit, false);
-
-       return nouveau_subdev_fini(&devinit->base, suspend);
-}
-
-int
-_nouveau_devinit_init(struct nouveau_object *object)
-{
-       struct nouveau_devinit_impl *impl = (void *)object->oclass;
-       struct nouveau_devinit *devinit = (void *)object;
-       int ret;
-
-       ret = nouveau_subdev_init(&devinit->base);
-       if (ret)
-               return ret;
-
-       ret = impl->post(&devinit->base, devinit->post);
-       if (ret)
-               return ret;
-
-       if (impl->disable)
-               nv_device(devinit)->disable_mask |= impl->disable(devinit);
-       return 0;
-}
-
-void
-_nouveau_devinit_dtor(struct nouveau_object *object)
-{
-       struct nouveau_devinit *devinit = (void *)object;
-
-       /* lock crtc regs */
-       nv_lockvgac(devinit, true);
-
-       nouveau_subdev_destroy(&devinit->base);
-}
-
-int
-nouveau_devinit_create_(struct nouveau_object *parent,
-                       struct nouveau_object *engine,
-                       struct nouveau_oclass *oclass,
-                       int size, void **pobject)
-{
-       struct nouveau_devinit_impl *impl = (void *)oclass;
-       struct nouveau_device *device = nv_device(parent);
-       struct nouveau_devinit *devinit;
-       int ret;
-
-       ret = nouveau_subdev_create_(parent, engine, oclass, 0, "DEVINIT",
-                                    "init", size, pobject);
-       devinit = *pobject;
-       if (ret)
-               return ret;
-
-       devinit->post = nouveau_boolopt(device->cfgopt, "NvForcePost", false);
-       devinit->meminit = impl->meminit;
-       devinit->pll_set = impl->pll_set;
-       devinit->mmio    = impl->mmio;
-       return 0;
-}
diff --git a/drivers/gpu/drm/nouveau/core/subdev/devinit/fbmem.h b/drivers/gpu/drm/nouveau/core/subdev/devinit/fbmem.h
deleted file mode 100644 (file)
index 6103484..0000000
+++ /dev/null
@@ -1,86 +0,0 @@
-/*
- * 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.
- *
- */
-
-#include <core/device.h>
-
-#include <subdev/fb/regsnv04.h>
-
-#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_SCRAMBLE(i)                         (0x00100400 + 4 * (i))
-
-#define NV10_PFB_REFCTRL                                       0x00100210
-#      define NV10_PFB_REFCTRL_VALID_1                         (1 << 31)
-
-static inline struct io_mapping *
-fbmem_init(struct nouveau_device *dev)
-{
-       return io_mapping_create_wc(nv_device_resource_start(dev, 1),
-                                   nv_device_resource_len(dev, 1));
-}
-
-static inline void
-fbmem_fini(struct io_mapping *fb)
-{
-       io_mapping_free(fb);
-}
-
-static inline u32
-fbmem_peek(struct io_mapping *fb, u32 off)
-{
-       u8 __iomem *p = io_mapping_map_atomic_wc(fb, off & PAGE_MASK);
-       u32 val = ioread32(p + (off & ~PAGE_MASK));
-       io_mapping_unmap_atomic(p);
-       return val;
-}
-
-static inline void
-fbmem_poke(struct io_mapping *fb, u32 off, u32 val)
-{
-       u8 __iomem *p = io_mapping_map_atomic_wc(fb, off & PAGE_MASK);
-       iowrite32(val, p + (off & ~PAGE_MASK));
-       wmb();
-       io_mapping_unmap_atomic(p);
-}
-
-static inline bool
-fbmem_readback(struct io_mapping *fb, u32 off, u32 val)
-{
-       fbmem_poke(fb, off, val);
-       return val == fbmem_peek(fb, off);
-}
diff --git a/drivers/gpu/drm/nouveau/core/subdev/devinit/gm107.c b/drivers/gpu/drm/nouveau/core/subdev/devinit/gm107.c
deleted file mode 100644 (file)
index 4ba43d6..0000000
+++ /dev/null
@@ -1,57 +0,0 @@
-/*
- * Copyright 2013 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 "nv50.h"
-
-u64
-gm107_devinit_disable(struct nouveau_devinit *devinit)
-{
-       struct nv50_devinit_priv *priv = (void *)devinit;
-       u32 r021c00 = nv_rd32(priv, 0x021c00);
-       u32 r021c04 = nv_rd32(priv, 0x021c04);
-       u64 disable = 0ULL;
-
-       if (r021c00 & 0x00000001)
-               disable |= (1ULL << NVDEV_ENGINE_COPY0);
-       if (r021c00 & 0x00000004)
-               disable |= (1ULL << NVDEV_ENGINE_COPY2);
-       if (r021c04 & 0x00000001)
-               disable |= (1ULL << NVDEV_ENGINE_DISP);
-
-       return disable;
-}
-
-struct nouveau_oclass *
-gm107_devinit_oclass = &(struct nouveau_devinit_impl) {
-       .base.handle = NV_SUBDEV(DEVINIT, 0x07),
-       .base.ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nv50_devinit_ctor,
-               .dtor = _nouveau_devinit_dtor,
-               .init = nv50_devinit_init,
-               .fini = _nouveau_devinit_fini,
-       },
-       .pll_set = nvc0_devinit_pll_set,
-       .disable = gm107_devinit_disable,
-       .post = nvbios_init,
-}.base;
diff --git a/drivers/gpu/drm/nouveau/core/subdev/devinit/gm204.c b/drivers/gpu/drm/nouveau/core/subdev/devinit/gm204.c
deleted file mode 100644 (file)
index e44a866..0000000
+++ /dev/null
@@ -1,173 +0,0 @@
-/*
- * Copyright 2013 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 <subdev/bios.h>
-#include <subdev/bios/bit.h>
-#include <subdev/bios/pmu.h>
-
-#include "nv50.h"
-
-static void
-pmu_code(struct nv50_devinit_priv *priv, u32 pmu, u32 img, u32 len, bool sec)
-{
-       struct nouveau_bios *bios = nouveau_bios(priv);
-       int i;
-
-       nv_wr32(priv, 0x10a180, 0x01000000 | (sec ? 0x10000000 : 0) | pmu);
-       for (i = 0; i < len; i += 4) {
-               if ((i & 0xff) == 0)
-                       nv_wr32(priv, 0x10a188, (pmu + i) >> 8);
-               nv_wr32(priv, 0x10a184, nv_ro32(bios, img + i));
-       }
-
-       while (i & 0xff) {
-               nv_wr32(priv, 0x10a184, 0x00000000);
-               i += 4;
-       }
-}
-
-static void
-pmu_data(struct nv50_devinit_priv *priv, u32 pmu, u32 img, u32 len)
-{
-       struct nouveau_bios *bios = nouveau_bios(priv);
-       int i;
-
-       nv_wr32(priv, 0x10a1c0, 0x01000000 | pmu);
-       for (i = 0; i < len; i += 4)
-               nv_wr32(priv, 0x10a1c4, nv_ro32(bios, img + i));
-}
-
-static u32
-pmu_args(struct nv50_devinit_priv *priv, u32 argp, u32 argi)
-{
-       nv_wr32(priv, 0x10a1c0, argp);
-       nv_wr32(priv, 0x10a1c0, nv_rd32(priv, 0x10a1c4) + argi);
-       return nv_rd32(priv, 0x10a1c4);
-}
-
-static void
-pmu_exec(struct nv50_devinit_priv *priv, u32 init_addr)
-{
-       nv_wr32(priv, 0x10a104, init_addr);
-       nv_wr32(priv, 0x10a10c, 0x00000000);
-       nv_wr32(priv, 0x10a100, 0x00000002);
-}
-
-static int
-pmu_load(struct nv50_devinit_priv *priv, u8 type, bool post,
-        u32 *init_addr_pmu, u32 *args_addr_pmu)
-{
-       struct nouveau_bios *bios = nouveau_bios(priv);
-       struct nvbios_pmuR pmu;
-
-       if (!nvbios_pmuRm(bios, type, &pmu)) {
-               nv_error(priv, "VBIOS PMU fuc %02x not found\n", type);
-               return -EINVAL;
-       }
-
-       if (!post)
-               return 0;
-
-       pmu_code(priv, pmu.boot_addr_pmu, pmu.boot_addr, pmu.boot_size, false);
-       pmu_code(priv, pmu.code_addr_pmu, pmu.code_addr, pmu.code_size, true);
-       pmu_data(priv, pmu.data_addr_pmu, pmu.data_addr, pmu.data_size);
-
-       if (init_addr_pmu) {
-               *init_addr_pmu = pmu.init_addr_pmu;
-               *args_addr_pmu = pmu.args_addr_pmu;
-               return 0;
-       }
-
-       return pmu_exec(priv, pmu.init_addr_pmu), 0;
-}
-
-static int
-gm204_devinit_post(struct nouveau_subdev *subdev, bool post)
-{
-       struct nv50_devinit_priv *priv = (void *)nouveau_devinit(subdev);
-       struct nouveau_bios *bios = nouveau_bios(priv);
-       struct bit_entry bit_I;
-       u32 init, args;
-       int ret;
-
-       if (bit_entry(bios, 'I', &bit_I) || bit_I.version != 1 ||
-                                           bit_I.length < 0x1c) {
-               nv_error(priv, "VBIOS PMU init data not found\n");
-               return -EINVAL;
-       }
-
-       /* reset PMU and load init table parser ucode */
-       if (post) {
-               nv_mask(priv, 0x000200, 0x00002000, 0x00000000);
-               nv_mask(priv, 0x000200, 0x00002000, 0x00002000);
-               nv_rd32(priv, 0x000200);
-               while (nv_rd32(priv, 0x10a10c) & 0x00000006) {
-               }
-       }
-
-       ret = pmu_load(priv, 0x04, post, &init, &args);
-       if (ret)
-               return ret;
-
-       /* upload first chunk of init data */
-       if (post) {
-               u32 pmu = pmu_args(priv, args + 0x08, 0x08);
-               u32 img = nv_ro16(bios, bit_I.offset + 0x14);
-               u32 len = nv_ro16(bios, bit_I.offset + 0x16);
-               pmu_data(priv, pmu, img, len);
-       }
-
-       /* upload second chunk of init data */
-       if (post) {
-               u32 pmu = pmu_args(priv, args + 0x08, 0x10);
-               u32 img = nv_ro16(bios, bit_I.offset + 0x18);
-               u32 len = nv_ro16(bios, bit_I.offset + 0x1a);
-               pmu_data(priv, pmu, img, len);
-       }
-
-       /* execute init tables */
-       if (post) {
-               nv_wr32(priv, 0x10a040, 0x00005000);
-               pmu_exec(priv, init);
-               while (!(nv_rd32(priv, 0x10a040) & 0x00002000)) {
-               }
-       }
-
-       /* load and execute some other ucode image (bios therm?) */
-       return pmu_load(priv, 0x01, post, NULL, NULL);
-}
-
-struct nouveau_oclass *
-gm204_devinit_oclass = &(struct nouveau_devinit_impl) {
-       .base.handle = NV_SUBDEV(DEVINIT, 0x07),
-       .base.ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nv50_devinit_ctor,
-               .dtor = _nouveau_devinit_dtor,
-               .init = nv50_devinit_init,
-               .fini = _nouveau_devinit_fini,
-       },
-       .pll_set = nvc0_devinit_pll_set,
-       .disable = gm107_devinit_disable,
-       .post = gm204_devinit_post,
-}.base;
diff --git a/drivers/gpu/drm/nouveau/core/subdev/devinit/nv04.c b/drivers/gpu/drm/nouveau/core/subdev/devinit/nv04.c
deleted file mode 100644 (file)
index 65651c5..0000000
+++ /dev/null
@@ -1,468 +0,0 @@
-/*
- * 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.
- *
- */
-
-#include <subdev/vga.h>
-
-#include "fbmem.h"
-#include "nv04.h"
-
-static void
-nv04_devinit_meminit(struct nouveau_devinit *devinit)
-{
-       struct nv04_devinit_priv *priv = (void *)devinit;
-       u32 patt = 0xdeadbeef;
-       struct io_mapping *fb;
-       int i;
-
-       /* Map the framebuffer aperture */
-       fb = fbmem_init(nv_device(priv));
-       if (!fb) {
-               nv_error(priv, "failed to map fb\n");
-               return;
-       }
-
-       /* Sequencer and refresh off */
-       nv_wrvgas(priv, 0, 1, nv_rdvgas(priv, 0, 1) | 0x20);
-       nv_mask(priv, NV04_PFB_DEBUG_0, 0, NV04_PFB_DEBUG_0_REFRESH_OFF);
-
-       nv_mask(priv, 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++)
-               fbmem_poke(fb, 4 * i, patt);
-
-       fbmem_poke(fb, 0x400000, patt + 1);
-
-       if (fbmem_peek(fb, 0) == patt + 1) {
-               nv_mask(priv, NV04_PFB_BOOT_0,
-                             NV04_PFB_BOOT_0_RAM_TYPE,
-                             NV04_PFB_BOOT_0_RAM_TYPE_SDRAM_16MBIT);
-               nv_mask(priv, NV04_PFB_DEBUG_0,
-                             NV04_PFB_DEBUG_0_REFRESH_OFF, 0);
-
-               for (i = 0; i < 4; i++)
-                       fbmem_poke(fb, 4 * i, patt);
-
-               if ((fbmem_peek(fb, 0xc) & 0xffff) != (patt & 0xffff))
-                       nv_mask(priv, 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 ((fbmem_peek(fb, 0xc) & 0xffff0000) != (patt & 0xffff0000)) {
-               nv_mask(priv, 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 (fbmem_peek(fb, 0) != patt) {
-               if (fbmem_readback(fb, 0x800000, patt))
-                       nv_mask(priv, NV04_PFB_BOOT_0,
-                                     NV04_PFB_BOOT_0_RAM_AMOUNT,
-                                     NV04_PFB_BOOT_0_RAM_AMOUNT_8MB);
-               else
-                       nv_mask(priv, NV04_PFB_BOOT_0,
-                                     NV04_PFB_BOOT_0_RAM_AMOUNT,
-                                     NV04_PFB_BOOT_0_RAM_AMOUNT_4MB);
-
-               nv_mask(priv, NV04_PFB_BOOT_0, NV04_PFB_BOOT_0_RAM_TYPE,
-                             NV04_PFB_BOOT_0_RAM_TYPE_SGRAM_8MBIT);
-       } else
-       if (!fbmem_readback(fb, 0x800000, patt)) {
-               nv_mask(priv, NV04_PFB_BOOT_0, NV04_PFB_BOOT_0_RAM_AMOUNT,
-                             NV04_PFB_BOOT_0_RAM_AMOUNT_8MB);
-
-       }
-
-       /* Refresh on, sequencer on */
-       nv_mask(priv, NV04_PFB_DEBUG_0, NV04_PFB_DEBUG_0_REFRESH_OFF, 0);
-       nv_wrvgas(priv, 0, 1, nv_rdvgas(priv, 0, 1) & ~0x20);
-       fbmem_fini(fb);
-}
-
-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 0x680520:
-               shift += 4;
-       case 0x680508:
-               shift += 4;
-       case 0x680504:
-               shift += 4;
-       case 0x680500:
-               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;
-}
-
-void
-setPLL_single(struct nouveau_devinit *devinit, u32 reg,
-             struct nouveau_pll_vals *pv)
-{
-       int chip_version = nouveau_bios(devinit)->version.chip;
-       uint32_t oldpll = nv_rd32(devinit, 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 = nv_rd32(devinit, 0x001584);
-               nv_wr32(devinit, 0x001584,
-                       (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 */
-               nv_wr32(devinit, reg, pv->log2P << 16 | (oldpll & 0xffff));
-       else
-               /* downclock -- write new NM first */
-               nv_wr32(devinit, reg, (oldpll & 0xffff0000) | pv->NM1);
-
-       if ((chip_version < 0x17 || chip_version == 0x1a) &&
-           chip_version != 0x11)
-               /* wait a bit on older chips */
-               msleep(64);
-       nv_rd32(devinit, reg);
-
-       /* then write the other half as well */
-       nv_wr32(devinit, reg, pll);
-
-       if (shift_powerctrl_1 >= 0)
-               nv_wr32(devinit, 0x001584, saved_powerctrl_1);
-}
-
-static uint32_t
-new_ramdac580(uint32_t reg1, bool ss, uint32_t ramdac580)
-{
-       bool head_a = (reg1 == 0x680508);
-
-       if (ss) /* single stage pll mode */
-               ramdac580 |= head_a ? 0x00000100 : 0x10000000;
-       else
-               ramdac580 &= head_a ? 0xfffffeff : 0xefffffff;
-
-       return ramdac580;
-}
-
-void
-setPLL_double_highregs(struct nouveau_devinit *devinit, u32 reg1,
-                      struct nouveau_pll_vals *pv)
-{
-       int chip_version = nouveau_bios(devinit)->version.chip;
-       bool nv3035 = chip_version == 0x30 || chip_version == 0x35;
-       uint32_t reg2 = reg1 + ((reg1 == 0x680520) ? 0x5c : 0x70);
-       uint32_t oldpll1 = nv_rd32(devinit, reg1);
-       uint32_t oldpll2 = !nv3035 ? nv_rd32(devinit, 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 >= 0x680508) { /* !nv40 */
-               oldramdac580 = nv_rd32(devinit, 0x680580);
-               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 = nv_rd32(devinit, 0x001584);
-               nv_wr32(devinit, 0x001584,
-                       (saved_powerctrl_1 & ~(0xf << shift_powerctrl_1)) |
-                       1 << shift_powerctrl_1);
-       }
-
-       if (chip_version >= 0x40) {
-               int shift_c040 = 14;
-
-               switch (reg1) {
-               case 0x680504:
-                       shift_c040 += 2;
-               case 0x680500:
-                       shift_c040 += 2;
-               case 0x680520:
-                       shift_c040 += 2;
-               case 0x680508:
-                       shift_c040 += 2;
-               }
-
-               savedc040 = nv_rd32(devinit, 0xc040);
-               if (shift_c040 != 14)
-                       nv_wr32(devinit, 0xc040, savedc040 & ~(3 << shift_c040));
-       }
-
-       if (oldramdac580 != ramdac580)
-               nv_wr32(devinit, 0x680580, ramdac580);
-
-       if (!nv3035)
-               nv_wr32(devinit, reg2, pll2);
-       nv_wr32(devinit, reg1, pll1);
-
-       if (shift_powerctrl_1 >= 0)
-               nv_wr32(devinit, 0x001584, saved_powerctrl_1);
-       if (chip_version >= 0x40)
-               nv_wr32(devinit, 0xc040, savedc040);
-}
-
-void
-setPLL_double_lowregs(struct nouveau_devinit *devinit, u32 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 = nv_rd32(devinit, 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 (nv_rd32(devinit, NMNMreg) == NMNM && (oldPval & 0xc0070000) == Pval)
-               return;
-
-       if (Preg == 0x4000)
-               maskc040 = ~0x333;
-       if (Preg == 0x4058)
-               maskc040 = ~(0xc << 24);
-
-       if (mpll) {
-               struct nvbios_pll info;
-               uint8_t Pval2;
-
-               if (nvbios_pll_parse(nouveau_bios(devinit), Preg, &info))
-                       return;
-
-               Pval2 = pv->log2P + info.bias_p;
-               if (Pval2 > info.max_p)
-                       Pval2 = info.max_p;
-               Pval |= 1 << 28 | Pval2 << 20;
-
-               saved4600 = nv_rd32(devinit, 0x4600);
-               nv_wr32(devinit, 0x4600, saved4600 | 8 << 28);
-       }
-       if (single_stage)
-               Pval |= mpll ? 1 << 12 : 1 << 8;
-
-       nv_wr32(devinit, Preg, oldPval | 1 << 28);
-       nv_wr32(devinit, Preg, Pval & ~(4 << 28));
-       if (mpll) {
-               Pval |= 8 << 20;
-               nv_wr32(devinit, 0x4020, Pval & ~(0xc << 28));
-               nv_wr32(devinit, 0x4038, Pval & ~(0xc << 28));
-       }
-
-       savedc040 = nv_rd32(devinit, 0xc040);
-       nv_wr32(devinit, 0xc040, savedc040 & maskc040);
-
-       nv_wr32(devinit, NMNMreg, NMNM);
-       if (NMNMreg == 0x4024)
-               nv_wr32(devinit, 0x403c, NMNM);
-
-       nv_wr32(devinit, Preg, Pval);
-       if (mpll) {
-               Pval &= ~(8 << 20);
-               nv_wr32(devinit, 0x4020, Pval);
-               nv_wr32(devinit, 0x4038, Pval);
-               nv_wr32(devinit, 0x4600, saved4600);
-       }
-
-       nv_wr32(devinit, 0xc040, savedc040);
-
-       if (mpll) {
-               nv_wr32(devinit, 0x4020, Pval & ~(1 << 28));
-               nv_wr32(devinit, 0x4038, Pval & ~(1 << 28));
-       }
-}
-
-int
-nv04_devinit_pll_set(struct nouveau_devinit *devinit, u32 type, u32 freq)
-{
-       struct nouveau_bios *bios = nouveau_bios(devinit);
-       struct nouveau_pll_vals pv;
-       struct nvbios_pll info;
-       int cv = bios->version.chip;
-       int N1, M1, N2, M2, P;
-       int ret;
-
-       ret = nvbios_pll_parse(bios, type > 0x405c ? type : type - 4, &info);
-       if (ret)
-               return ret;
-
-       ret = nv04_pll_calc(nv_subdev(devinit), &info, freq,
-                          &N1, &M1, &N2, &M2, &P);
-       if (!ret)
-               return -EINVAL;
-
-       pv.refclk = info.refclk;
-       pv.N1 = N1;
-       pv.M1 = M1;
-       pv.N2 = N2;
-       pv.M2 = M2;
-       pv.log2P = P;
-
-       if (cv == 0x30 || cv == 0x31 || cv == 0x35 || cv == 0x36 ||
-           cv >= 0x40) {
-               if (type > 0x405c)
-                       setPLL_double_highregs(devinit, type, &pv);
-               else
-                       setPLL_double_lowregs(devinit, type, &pv);
-       } else
-               setPLL_single(devinit, type, &pv);
-
-       return 0;
-}
-
-int
-nv04_devinit_fini(struct nouveau_object *object, bool suspend)
-{
-       struct nv04_devinit_priv *priv = (void *)object;
-       int ret;
-
-       /* make i2c busses accessible */
-       nv_mask(priv, 0x000200, 0x00000001, 0x00000001);
-
-       ret = nouveau_devinit_fini(&priv->base, suspend);
-       if (ret)
-               return ret;
-
-       /* unslave crtcs */
-       if (priv->owner < 0)
-               priv->owner = nv_rdvgaowner(priv);
-       nv_wrvgaowner(priv, 0);
-
-       return 0;
-}
-
-int
-nv04_devinit_init(struct nouveau_object *object)
-{
-       struct nv04_devinit_priv *priv = (void *)object;
-
-       if (!priv->base.post) {
-               u32 htotal = nv_rdvgac(priv, 0, 0x06);
-               htotal |= (nv_rdvgac(priv, 0, 0x07) & 0x01) << 8;
-               htotal |= (nv_rdvgac(priv, 0, 0x07) & 0x20) << 4;
-               htotal |= (nv_rdvgac(priv, 0, 0x25) & 0x01) << 10;
-               htotal |= (nv_rdvgac(priv, 0, 0x41) & 0x01) << 11;
-               if (!htotal) {
-                       nv_info(priv, "adaptor not initialised\n");
-                       priv->base.post = true;
-               }
-       }
-
-       return nouveau_devinit_init(&priv->base);
-}
-
-void
-nv04_devinit_dtor(struct nouveau_object *object)
-{
-       struct nv04_devinit_priv *priv = (void *)object;
-
-       /* restore vga owner saved at first init */
-       nv_wrvgaowner(priv, priv->owner);
-
-       nouveau_devinit_destroy(&priv->base);
-}
-
-int
-nv04_devinit_ctor(struct nouveau_object *parent, struct nouveau_object *engine,
-                 struct nouveau_oclass *oclass, void *data, u32 size,
-                 struct nouveau_object **pobject)
-{
-       struct nv04_devinit_priv *priv;
-       int ret;
-
-       ret = nouveau_devinit_create(parent, engine, oclass, &priv);
-       *pobject = nv_object(priv);
-       if (ret)
-               return ret;
-
-       priv->owner = -1;
-       return 0;
-}
-
-struct nouveau_oclass *
-nv04_devinit_oclass = &(struct nouveau_devinit_impl) {
-       .base.handle = NV_SUBDEV(DEVINIT, 0x04),
-       .base.ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nv04_devinit_ctor,
-               .dtor = nv04_devinit_dtor,
-               .init = nv04_devinit_init,
-               .fini = nv04_devinit_fini,
-       },
-       .meminit = nv04_devinit_meminit,
-       .pll_set = nv04_devinit_pll_set,
-       .post = nvbios_init,
-}.base;
diff --git a/drivers/gpu/drm/nouveau/core/subdev/devinit/nv04.h b/drivers/gpu/drm/nouveau/core/subdev/devinit/nv04.h
deleted file mode 100644 (file)
index 23470a5..0000000
+++ /dev/null
@@ -1,23 +0,0 @@
-#ifndef __NVKM_DEVINIT_NV04_H__
-#define __NVKM_DEVINIT_NV04_H__
-
-#include "priv.h"
-
-struct nv04_devinit_priv {
-       struct nouveau_devinit base;
-       u8 owner;
-};
-
-int  nv04_devinit_ctor(struct nouveau_object *, struct nouveau_object *,
-                      struct nouveau_oclass *, void *, u32,
-                      struct nouveau_object **);
-void nv04_devinit_dtor(struct nouveau_object *);
-int  nv04_devinit_init(struct nouveau_object *);
-int  nv04_devinit_fini(struct nouveau_object *, bool);
-int  nv04_devinit_pll_set(struct nouveau_devinit *, u32, u32);
-
-void setPLL_single(struct nouveau_devinit *, u32, struct nouveau_pll_vals *);
-void setPLL_double_highregs(struct nouveau_devinit *, u32, struct nouveau_pll_vals *);
-void setPLL_double_lowregs(struct nouveau_devinit *, u32, struct nouveau_pll_vals *);
-
-#endif
diff --git a/drivers/gpu/drm/nouveau/core/subdev/devinit/nv05.c b/drivers/gpu/drm/nouveau/core/subdev/devinit/nv05.c
deleted file mode 100644 (file)
index a2007a3..0000000
+++ /dev/null
@@ -1,140 +0,0 @@
-/*
- * 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.
- *
- */
-
-#include <subdev/bios.h>
-#include <subdev/bios/bmp.h>
-#include <subdev/vga.h>
-
-#include "fbmem.h"
-#include "nv04.h"
-
-static void
-nv05_devinit_meminit(struct nouveau_devinit *devinit)
-{
-       static const u8 default_config_tab[][2] = {
-               { 0x24, 0x00 },
-               { 0x28, 0x00 },
-               { 0x24, 0x01 },
-               { 0x1f, 0x00 },
-               { 0x0f, 0x00 },
-               { 0x17, 0x00 },
-               { 0x06, 0x00 },
-               { 0x00, 0x00 }
-       };
-       struct nv04_devinit_priv *priv = (void *)devinit;
-       struct nouveau_bios *bios = nouveau_bios(priv);
-       struct io_mapping *fb;
-       u32 patt = 0xdeadbeef;
-       u16 data;
-       u8 strap, ramcfg[2];
-       int i, v;
-
-       /* Map the framebuffer aperture */
-       fb = fbmem_init(nv_device(priv));
-       if (!fb) {
-               nv_error(priv, "failed to map fb\n");
-               return;
-       }
-
-       strap = (nv_rd32(priv, 0x101000) & 0x0000003c) >> 2;
-       if ((data = bmp_mem_init_table(bios))) {
-               ramcfg[0] = nv_ro08(bios, data + 2 * strap + 0);
-               ramcfg[1] = nv_ro08(bios, data + 2 * strap + 1);
-       } else {
-               ramcfg[0] = default_config_tab[strap][0];
-               ramcfg[1] = default_config_tab[strap][1];
-       }
-
-       /* Sequencer off */
-       nv_wrvgas(priv, 0, 1, nv_rdvgas(priv, 0, 1) | 0x20);
-
-       if (nv_rd32(priv, NV04_PFB_BOOT_0) & NV04_PFB_BOOT_0_UMA_ENABLE)
-               goto out;
-
-       nv_mask(priv, NV04_PFB_DEBUG_0, NV04_PFB_DEBUG_0_REFRESH_OFF, 0);
-
-       /* If present load the hardcoded scrambling table */
-       if (data) {
-               for (i = 0, data += 0x10; i < 8; i++, data += 4) {
-                       u32 scramble = nv_ro32(bios, data);
-                       nv_wr32(priv, NV04_PFB_SCRAMBLE(i), scramble);
-               }
-       }
-
-       /* Set memory type/width/length defaults depending on the straps */
-       nv_mask(priv, NV04_PFB_BOOT_0, 0x3f, ramcfg[0]);
-
-       if (ramcfg[1] & 0x80)
-               nv_mask(priv, NV04_PFB_CFG0, 0, NV04_PFB_CFG0_SCRAMBLE);
-
-       nv_mask(priv, NV04_PFB_CFG1, 0x700001, (ramcfg[1] & 1) << 20);
-       nv_mask(priv, NV04_PFB_CFG1, 0, 1);
-
-       /* Probe memory bus width */
-       for (i = 0; i < 4; i++)
-               fbmem_poke(fb, 4 * i, patt);
-
-       if (fbmem_peek(fb, 0xc) != patt)
-               nv_mask(priv, NV04_PFB_BOOT_0,
-                         NV04_PFB_BOOT_0_RAM_WIDTH_128, 0);
-
-       /* Probe memory length */
-       v = nv_rd32(priv, NV04_PFB_BOOT_0) & NV04_PFB_BOOT_0_RAM_AMOUNT;
-
-       if (v == NV04_PFB_BOOT_0_RAM_AMOUNT_32MB &&
-           (!fbmem_readback(fb, 0x1000000, ++patt) ||
-            !fbmem_readback(fb, 0, ++patt)))
-               nv_mask(priv, 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 &&
-           !fbmem_readback(fb, 0x800000, ++patt))
-               nv_mask(priv, NV04_PFB_BOOT_0, NV04_PFB_BOOT_0_RAM_AMOUNT,
-                         NV04_PFB_BOOT_0_RAM_AMOUNT_8MB);
-
-       if (!fbmem_readback(fb, 0x400000, ++patt))
-               nv_mask(priv, NV04_PFB_BOOT_0, NV04_PFB_BOOT_0_RAM_AMOUNT,
-                         NV04_PFB_BOOT_0_RAM_AMOUNT_4MB);
-
-out:
-       /* Sequencer on */
-       nv_wrvgas(priv, 0, 1, nv_rdvgas(priv, 0, 1) & ~0x20);
-       fbmem_fini(fb);
-}
-
-struct nouveau_oclass *
-nv05_devinit_oclass = &(struct nouveau_devinit_impl) {
-       .base.handle = NV_SUBDEV(DEVINIT, 0x05),
-       .base.ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nv04_devinit_ctor,
-               .dtor = nv04_devinit_dtor,
-               .init = nv04_devinit_init,
-               .fini = nv04_devinit_fini,
-       },
-       .meminit = nv05_devinit_meminit,
-       .pll_set = nv04_devinit_pll_set,
-       .post = nvbios_init,
-}.base;
diff --git a/drivers/gpu/drm/nouveau/core/subdev/devinit/nv10.c b/drivers/gpu/drm/nouveau/core/subdev/devinit/nv10.c
deleted file mode 100644 (file)
index 178b46f..0000000
+++ /dev/null
@@ -1,111 +0,0 @@
-/*
- * 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.
- *
- */
-
-#include <subdev/vga.h>
-
-#include "fbmem.h"
-#include "nv04.h"
-
-static void
-nv10_devinit_meminit(struct nouveau_devinit *devinit)
-{
-       struct nv04_devinit_priv *priv = (void *)devinit;
-       static const int mem_width[] = { 0x10, 0x00, 0x20 };
-       int mem_width_count;
-       uint32_t patt = 0xdeadbeef;
-       struct io_mapping *fb;
-       int i, j, k;
-
-       if (nv_device(priv)->card_type >= NV_11 &&
-           nv_device(priv)->chipset >= 0x17)
-               mem_width_count = 3;
-       else
-               mem_width_count = 2;
-
-       /* Map the framebuffer aperture */
-       fb = fbmem_init(nv_device(priv));
-       if (!fb) {
-               nv_error(priv, "failed to map fb\n");
-               return;
-       }
-
-       nv_wr32(priv, NV10_PFB_REFCTRL, NV10_PFB_REFCTRL_VALID_1);
-
-       /* Probe memory bus width */
-       for (i = 0; i < mem_width_count; i++) {
-               nv_mask(priv, NV04_PFB_CFG0, 0x30, mem_width[i]);
-
-               for (j = 0; j < 4; j++) {
-                       for (k = 0; k < 4; k++)
-                               fbmem_poke(fb, 0x1c, 0);
-
-                       fbmem_poke(fb, 0x1c, patt);
-                       fbmem_poke(fb, 0x3c, 0);
-
-                       if (fbmem_peek(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 = nv_rd32(priv, 0x10020c) - 0x100000;
-
-               fbmem_poke(fb, off, patt);
-               fbmem_poke(fb, 0, 0);
-
-               fbmem_peek(fb, 0);
-               fbmem_peek(fb, 0);
-               fbmem_peek(fb, 0);
-               fbmem_peek(fb, 0);
-
-               if (fbmem_peek(fb, off) == patt)
-                       goto amount_found;
-       }
-
-       /* IC missing - disable the upper half memory space. */
-       nv_mask(priv, NV04_PFB_CFG0, 0x1000, 0);
-
-amount_found:
-       fbmem_fini(fb);
-}
-
-struct nouveau_oclass *
-nv10_devinit_oclass = &(struct nouveau_devinit_impl) {
-       .base.handle = NV_SUBDEV(DEVINIT, 0x10),
-       .base.ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nv04_devinit_ctor,
-               .dtor = nv04_devinit_dtor,
-               .init = nv04_devinit_init,
-               .fini = nv04_devinit_fini,
-       },
-       .meminit = nv10_devinit_meminit,
-       .pll_set = nv04_devinit_pll_set,
-       .post = nvbios_init,
-}.base;
diff --git a/drivers/gpu/drm/nouveau/core/subdev/devinit/nv1a.c b/drivers/gpu/drm/nouveau/core/subdev/devinit/nv1a.c
deleted file mode 100644 (file)
index 995dd97..0000000
+++ /dev/null
@@ -1,38 +0,0 @@
-/*
- * Copyright 2012 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 "nv04.h"
-
-struct nouveau_oclass *
-nv1a_devinit_oclass = &(struct nouveau_devinit_impl) {
-       .base.handle = NV_SUBDEV(DEVINIT, 0x1a),
-       .base.ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nv04_devinit_ctor,
-               .dtor = nv04_devinit_dtor,
-               .init = nv04_devinit_init,
-               .fini = nv04_devinit_fini,
-       },
-       .pll_set = nv04_devinit_pll_set,
-       .post = nvbios_init,
-}.base;
diff --git a/drivers/gpu/drm/nouveau/core/subdev/devinit/nv20.c b/drivers/gpu/drm/nouveau/core/subdev/devinit/nv20.c
deleted file mode 100644 (file)
index 915089f..0000000
+++ /dev/null
@@ -1,75 +0,0 @@
-/*
- * 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.
- *
- */
-
-#include "nv04.h"
-#include "fbmem.h"
-
-static void
-nv20_devinit_meminit(struct nouveau_devinit *devinit)
-{
-       struct nv04_devinit_priv *priv = (void *)devinit;
-       struct nouveau_device *device = nv_device(priv);
-       uint32_t mask = (device->chipset >= 0x25 ? 0x300 : 0x900);
-       uint32_t amount, off;
-       struct io_mapping *fb;
-
-       /* Map the framebuffer aperture */
-       fb = fbmem_init(nv_device(priv));
-       if (!fb) {
-               nv_error(priv, "failed to map fb\n");
-               return;
-       }
-
-       nv_wr32(priv, NV10_PFB_REFCTRL, NV10_PFB_REFCTRL_VALID_1);
-
-       /* Allow full addressing */
-       nv_mask(priv, NV04_PFB_CFG0, 0, mask);
-
-       amount = nv_rd32(priv, 0x10020c);
-       for (off = amount; off > 0x2000000; off -= 0x2000000)
-               fbmem_poke(fb, off - 4, off);
-
-       amount = nv_rd32(priv, 0x10020c);
-       if (amount != fbmem_peek(fb, amount - 4))
-               /* IC missing - disable the upper half memory space. */
-               nv_mask(priv, NV04_PFB_CFG0, mask, 0);
-
-       fbmem_fini(fb);
-}
-
-struct nouveau_oclass *
-nv20_devinit_oclass = &(struct nouveau_devinit_impl) {
-       .base.handle = NV_SUBDEV(DEVINIT, 0x20),
-       .base.ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nv04_devinit_ctor,
-               .dtor = nv04_devinit_dtor,
-               .init = nv04_devinit_init,
-               .fini = nv04_devinit_fini,
-       },
-       .meminit = nv20_devinit_meminit,
-       .pll_set = nv04_devinit_pll_set,
-       .post = nvbios_init,
-}.base;
diff --git a/drivers/gpu/drm/nouveau/core/subdev/devinit/nv50.c b/drivers/gpu/drm/nouveau/core/subdev/devinit/nv50.c
deleted file mode 100644 (file)
index 968334d..0000000
+++ /dev/null
@@ -1,173 +0,0 @@
-/*
- * Copyright 2013 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 <subdev/bios.h>
-#include <subdev/bios/dcb.h>
-#include <subdev/bios/disp.h>
-#include <subdev/bios/init.h>
-#include <subdev/ibus.h>
-#include <subdev/vga.h>
-
-#include "nv50.h"
-
-int
-nv50_devinit_pll_set(struct nouveau_devinit *devinit, u32 type, u32 freq)
-{
-       struct nv50_devinit_priv *priv = (void *)devinit;
-       struct nouveau_bios *bios = nouveau_bios(priv);
-       struct nvbios_pll info;
-       int N1, M1, N2, M2, P;
-       int ret;
-
-       ret = nvbios_pll_parse(bios, type, &info);
-       if (ret) {
-               nv_error(devinit, "failed to retrieve pll data, %d\n", ret);
-               return ret;
-       }
-
-       ret = nv04_pll_calc(nv_subdev(devinit), &info, freq, &N1, &M1, &N2, &M2, &P);
-       if (!ret) {
-               nv_error(devinit, "failed pll calculation\n");
-               return ret;
-       }
-
-       switch (info.type) {
-       case PLL_VPLL0:
-       case PLL_VPLL1:
-               nv_wr32(priv, info.reg + 0, 0x10000611);
-               nv_mask(priv, info.reg + 4, 0x00ff00ff, (M1 << 16) | N1);
-               nv_mask(priv, info.reg + 8, 0x7fff00ff, (P  << 28) |
-                                                       (M2 << 16) | N2);
-               break;
-       case PLL_MEMORY:
-               nv_mask(priv, info.reg + 0, 0x01ff0000, (P << 22) |
-                                                       (info.bias_p << 19) |
-                                                       (P << 16));
-               nv_wr32(priv, info.reg + 4, (N1 << 8) | M1);
-               break;
-       default:
-               nv_mask(priv, info.reg + 0, 0x00070000, (P << 16));
-               nv_wr32(priv, info.reg + 4, (N1 << 8) | M1);
-               break;
-       }
-
-       return 0;
-}
-
-static u64
-nv50_devinit_disable(struct nouveau_devinit *devinit)
-{
-       struct nv50_devinit_priv *priv = (void *)devinit;
-       u32 r001540 = nv_rd32(priv, 0x001540);
-       u64 disable = 0ULL;
-
-       if (!(r001540 & 0x40000000))
-               disable |= (1ULL << NVDEV_ENGINE_MPEG);
-
-       return disable;
-}
-
-int
-nv50_devinit_init(struct nouveau_object *object)
-{
-       struct nouveau_bios *bios = nouveau_bios(object);
-       struct nouveau_ibus *ibus = nouveau_ibus(object);
-       struct nv50_devinit_priv *priv = (void *)object;
-       struct nvbios_outp info;
-       struct dcb_output outp;
-       u8  ver = 0xff, hdr, cnt, len;
-       int ret, i = 0;
-
-       if (!priv->base.post) {
-               if (!nv_rdvgac(priv, 0, 0x00) &&
-                   !nv_rdvgac(priv, 0, 0x1a)) {
-                       nv_info(priv, "adaptor not initialised\n");
-                       priv->base.post = true;
-               }
-       }
-
-       /* some boards appear to require certain priv register timeouts
-        * to be bumped before runing devinit scripts.  not a clue why
-        * the vbios engineers didn't make the scripts just work...
-        */
-       if (priv->base.post && ibus)
-               nv_ofuncs(ibus)->init(nv_object(ibus));
-
-       ret = nouveau_devinit_init(&priv->base);
-       if (ret)
-               return ret;
-
-       /* if we ran the init tables, we have to execute the first script
-        * pointer of each dcb entry's display encoder table in order
-        * to properly initialise each encoder.
-        */
-       while (priv->base.post && dcb_outp_parse(bios, i, &ver, &hdr, &outp)) {
-               if (nvbios_outp_match(bios, outp.hasht, outp.hashm,
-                                    &ver, &hdr, &cnt, &len, &info)) {
-                       struct nvbios_init init = {
-                               .subdev = nv_subdev(priv),
-                               .bios = bios,
-                               .offset = info.script[0],
-                               .outp = &outp,
-                               .crtc = -1,
-                               .execute = 1,
-                       };
-
-                       nvbios_exec(&init);
-               }
-               i++;
-       }
-
-       return 0;
-}
-
-int
-nv50_devinit_ctor(struct nouveau_object *parent, struct nouveau_object *engine,
-                 struct nouveau_oclass *oclass, void *data, u32 size,
-                 struct nouveau_object **pobject)
-{
-       struct nv50_devinit_priv *priv;
-       int ret;
-
-       ret = nouveau_devinit_create(parent, engine, oclass, &priv);
-       *pobject = nv_object(priv);
-       if (ret)
-               return ret;
-
-       return 0;
-}
-
-struct nouveau_oclass *
-nv50_devinit_oclass = &(struct nouveau_devinit_impl) {
-       .base.handle = NV_SUBDEV(DEVINIT, 0x50),
-       .base.ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nv50_devinit_ctor,
-               .dtor = _nouveau_devinit_dtor,
-               .init = nv50_devinit_init,
-               .fini = _nouveau_devinit_fini,
-       },
-       .pll_set = nv50_devinit_pll_set,
-       .disable = nv50_devinit_disable,
-       .post = nvbios_init,
-}.base;
diff --git a/drivers/gpu/drm/nouveau/core/subdev/devinit/nv50.h b/drivers/gpu/drm/nouveau/core/subdev/devinit/nv50.h
deleted file mode 100644 (file)
index f412bb7..0000000
+++ /dev/null
@@ -1,23 +0,0 @@
-#ifndef __NVKM_DEVINIT_NV50_H__
-#define __NVKM_DEVINIT_NV50_H__
-
-#include "priv.h"
-
-struct nv50_devinit_priv {
-       struct nouveau_devinit base;
-       u32 r001540;
-};
-
-int  nv50_devinit_ctor(struct nouveau_object *, struct nouveau_object *,
-                      struct nouveau_oclass *, void *, u32,
-                      struct nouveau_object **);
-int  nv50_devinit_init(struct nouveau_object *);
-int  nv50_devinit_pll_set(struct nouveau_devinit *, u32, u32);
-
-int  nva3_devinit_pll_set(struct nouveau_devinit *, u32, u32);
-
-int  nvc0_devinit_pll_set(struct nouveau_devinit *, u32, u32);
-
-u64  gm107_devinit_disable(struct nouveau_devinit *);
-
-#endif
diff --git a/drivers/gpu/drm/nouveau/core/subdev/devinit/nv84.c b/drivers/gpu/drm/nouveau/core/subdev/devinit/nv84.c
deleted file mode 100644 (file)
index a7c80de..0000000
+++ /dev/null
@@ -1,64 +0,0 @@
-/*
- * Copyright 2013 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 "nv50.h"
-
-static u64
-nv84_devinit_disable(struct nouveau_devinit *devinit)
-{
-       struct nv50_devinit_priv *priv = (void *)devinit;
-       u32 r001540 = nv_rd32(priv, 0x001540);
-       u32 r00154c = nv_rd32(priv, 0x00154c);
-       u64 disable = 0ULL;
-
-       if (!(r001540 & 0x40000000)) {
-               disable |= (1ULL << NVDEV_ENGINE_MPEG);
-               disable |= (1ULL << NVDEV_ENGINE_VP);
-               disable |= (1ULL << NVDEV_ENGINE_BSP);
-               disable |= (1ULL << NVDEV_ENGINE_CRYPT);
-       }
-
-       if (!(r00154c & 0x00000004))
-               disable |= (1ULL << NVDEV_ENGINE_DISP);
-       if (!(r00154c & 0x00000020))
-               disable |= (1ULL << NVDEV_ENGINE_BSP);
-       if (!(r00154c & 0x00000040))
-               disable |= (1ULL << NVDEV_ENGINE_CRYPT);
-
-       return disable;
-}
-
-struct nouveau_oclass *
-nv84_devinit_oclass = &(struct nouveau_devinit_impl) {
-       .base.handle = NV_SUBDEV(DEVINIT, 0x84),
-       .base.ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nv50_devinit_ctor,
-               .dtor = _nouveau_devinit_dtor,
-               .init = nv50_devinit_init,
-               .fini = _nouveau_devinit_fini,
-       },
-       .pll_set = nv50_devinit_pll_set,
-       .disable = nv84_devinit_disable,
-       .post = nvbios_init,
-}.base;
diff --git a/drivers/gpu/drm/nouveau/core/subdev/devinit/nv98.c b/drivers/gpu/drm/nouveau/core/subdev/devinit/nv98.c
deleted file mode 100644 (file)
index a773253..0000000
+++ /dev/null
@@ -1,63 +0,0 @@
-/*
- * Copyright 2013 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 "nv50.h"
-
-static u64
-nv98_devinit_disable(struct nouveau_devinit *devinit)
-{
-       struct nv50_devinit_priv *priv = (void *)devinit;
-       u32 r001540 = nv_rd32(priv, 0x001540);
-       u32 r00154c = nv_rd32(priv, 0x00154c);
-       u64 disable = 0ULL;
-
-       if (!(r001540 & 0x40000000)) {
-               disable |= (1ULL << NVDEV_ENGINE_VP);
-               disable |= (1ULL << NVDEV_ENGINE_BSP);
-               disable |= (1ULL << NVDEV_ENGINE_PPP);
-       }
-
-       if (!(r00154c & 0x00000004))
-               disable |= (1ULL << NVDEV_ENGINE_DISP);
-       if (!(r00154c & 0x00000020))
-               disable |= (1ULL << NVDEV_ENGINE_BSP);
-       if (!(r00154c & 0x00000040))
-               disable |= (1ULL << NVDEV_ENGINE_CRYPT);
-
-       return disable;
-}
-
-struct nouveau_oclass *
-nv98_devinit_oclass = &(struct nouveau_devinit_impl) {
-       .base.handle = NV_SUBDEV(DEVINIT, 0x98),
-       .base.ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nv50_devinit_ctor,
-               .dtor = _nouveau_devinit_dtor,
-               .init = nv50_devinit_init,
-               .fini = _nouveau_devinit_fini,
-       },
-       .pll_set = nv50_devinit_pll_set,
-       .disable = nv98_devinit_disable,
-       .post = nvbios_init,
-}.base;
diff --git a/drivers/gpu/drm/nouveau/core/subdev/devinit/nva3.c b/drivers/gpu/drm/nouveau/core/subdev/devinit/nva3.c
deleted file mode 100644 (file)
index b9cd9e5..0000000
+++ /dev/null
@@ -1,146 +0,0 @@
-/*
- * Copyright 2013 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 "nv50.h"
-
-int
-nva3_devinit_pll_set(struct nouveau_devinit *devinit, u32 type, u32 freq)
-{
-       struct nv50_devinit_priv *priv = (void *)devinit;
-       struct nouveau_bios *bios = nouveau_bios(priv);
-       struct nvbios_pll info;
-       int N, fN, M, P;
-       int ret;
-
-       ret = nvbios_pll_parse(bios, type, &info);
-       if (ret)
-               return ret;
-
-       ret = nva3_pll_calc(nv_subdev(devinit), &info, freq, &N, &fN, &M, &P);
-       if (ret < 0)
-               return ret;
-
-       switch (info.type) {
-       case PLL_VPLL0:
-       case PLL_VPLL1:
-               nv_wr32(priv, info.reg + 0, 0x50000610);
-               nv_mask(priv, info.reg + 4, 0x003fffff,
-                                           (P << 16) | (M << 8) | N);
-               nv_wr32(priv, info.reg + 8, fN);
-               break;
-       default:
-               nv_warn(priv, "0x%08x/%dKhz unimplemented\n", type, freq);
-               ret = -EINVAL;
-               break;
-       }
-
-       return ret;
-}
-
-static u64
-nva3_devinit_disable(struct nouveau_devinit *devinit)
-{
-       struct nv50_devinit_priv *priv = (void *)devinit;
-       u32 r001540 = nv_rd32(priv, 0x001540);
-       u32 r00154c = nv_rd32(priv, 0x00154c);
-       u64 disable = 0ULL;
-
-       if (!(r001540 & 0x40000000)) {
-               disable |= (1ULL << NVDEV_ENGINE_VP);
-               disable |= (1ULL << NVDEV_ENGINE_PPP);
-       }
-
-       if (!(r00154c & 0x00000004))
-               disable |= (1ULL << NVDEV_ENGINE_DISP);
-       if (!(r00154c & 0x00000020))
-               disable |= (1ULL << NVDEV_ENGINE_BSP);
-       if (!(r00154c & 0x00000200))
-               disable |= (1ULL << NVDEV_ENGINE_COPY0);
-
-       return disable;
-}
-
-static u32
-nva3_devinit_mmio_part[] = {
-       0x100720, 0x1008bc, 4,
-       0x100a20, 0x100adc, 4,
-       0x100d80, 0x100ddc, 4,
-       0x110000, 0x110f9c, 4,
-       0x111000, 0x11103c, 8,
-       0x111080, 0x1110fc, 4,
-       0x111120, 0x1111fc, 4,
-       0x111300, 0x1114bc, 4,
-       0,
-};
-
-static u32
-nva3_devinit_mmio(struct nouveau_devinit *devinit, u32 addr)
-{
-       struct nv50_devinit_priv *priv = (void *)devinit;
-       u32 *mmio = nva3_devinit_mmio_part;
-
-       /* the init tables on some boards have INIT_RAM_RESTRICT_ZM_REG_GROUP
-        * instructions which touch registers that may not even exist on
-        * some configurations (Quadro 400), which causes the register
-        * interface to screw up for some amount of time after attempting to
-        * write to one of these, and results in all sorts of things going
-        * horribly wrong.
-        *
-        * the binary driver avoids touching these registers at all, however,
-        * the video bios doesn't care and does what the scripts say.  it's
-        * presumed that the io-port access to priv registers isn't effected
-        * by the screw-up bug mentioned above.
-        *
-        * really, a new opcode should've been invented to handle these
-        * requirements, but whatever, it's too late for that now.
-        */
-       while (mmio[0]) {
-               if (addr >= mmio[0] && addr <= mmio[1]) {
-                       u32 part = (addr / mmio[2]) & 7;
-                       if (!priv->r001540)
-                               priv->r001540 = nv_rd32(priv, 0x001540);
-                       if (part >= hweight8((priv->r001540 >> 16) & 0xff))
-                               return ~0;
-                       return addr;
-               }
-               mmio += 3;
-       }
-
-       return addr;
-}
-
-struct nouveau_oclass *
-nva3_devinit_oclass = &(struct nouveau_devinit_impl) {
-       .base.handle = NV_SUBDEV(DEVINIT, 0xa3),
-       .base.ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nv50_devinit_ctor,
-               .dtor = _nouveau_devinit_dtor,
-               .init = nv50_devinit_init,
-               .fini = _nouveau_devinit_fini,
-       },
-       .pll_set = nva3_devinit_pll_set,
-       .disable = nva3_devinit_disable,
-       .mmio    = nva3_devinit_mmio,
-       .post = nvbios_init,
-}.base;
diff --git a/drivers/gpu/drm/nouveau/core/subdev/devinit/nvaf.c b/drivers/gpu/drm/nouveau/core/subdev/devinit/nvaf.c
deleted file mode 100644 (file)
index 3729846..0000000
+++ /dev/null
@@ -1,64 +0,0 @@
-/*
- * Copyright 2013 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 "nv50.h"
-
-static u64
-nvaf_devinit_disable(struct nouveau_devinit *devinit)
-{
-       struct nv50_devinit_priv *priv = (void *)devinit;
-       u32 r001540 = nv_rd32(priv, 0x001540);
-       u32 r00154c = nv_rd32(priv, 0x00154c);
-       u64 disable = 0;
-
-       if (!(r001540 & 0x40000000)) {
-               disable |= (1ULL << NVDEV_ENGINE_VP);
-               disable |= (1ULL << NVDEV_ENGINE_PPP);
-       }
-
-       if (!(r00154c & 0x00000004))
-               disable |= (1ULL << NVDEV_ENGINE_DISP);
-       if (!(r00154c & 0x00000020))
-               disable |= (1ULL << NVDEV_ENGINE_BSP);
-       if (!(r00154c & 0x00000040))
-               disable |= (1ULL << NVDEV_ENGINE_VIC);
-       if (!(r00154c & 0x00000200))
-               disable |= (1ULL << NVDEV_ENGINE_COPY0);
-
-       return disable;
-}
-
-struct nouveau_oclass *
-nvaf_devinit_oclass = &(struct nouveau_devinit_impl) {
-       .base.handle = NV_SUBDEV(DEVINIT, 0xaf),
-       .base.ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nv50_devinit_ctor,
-               .dtor = _nouveau_devinit_dtor,
-               .init = nv50_devinit_init,
-               .fini = _nouveau_devinit_fini,
-       },
-       .pll_set = nva3_devinit_pll_set,
-       .disable = nvaf_devinit_disable,
-       .post = nvbios_init,
-}.base;
diff --git a/drivers/gpu/drm/nouveau/core/subdev/devinit/nvc0.c b/drivers/gpu/drm/nouveau/core/subdev/devinit/nvc0.c
deleted file mode 100644 (file)
index 80bd7f5..0000000
+++ /dev/null
@@ -1,119 +0,0 @@
-/*
- * Copyright 2013 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 "nv50.h"
-
-int
-nvc0_devinit_pll_set(struct nouveau_devinit *devinit, u32 type, u32 freq)
-{
-       struct nv50_devinit_priv *priv = (void *)devinit;
-       struct nouveau_bios *bios = nouveau_bios(priv);
-       struct nvbios_pll info;
-       int N, fN, M, P;
-       int ret;
-
-       ret = nvbios_pll_parse(bios, type, &info);
-       if (ret)
-               return ret;
-
-       ret = nva3_pll_calc(nv_subdev(devinit), &info, freq, &N, &fN, &M, &P);
-       if (ret < 0)
-               return ret;
-
-       switch (info.type) {
-       case PLL_VPLL0:
-       case PLL_VPLL1:
-       case PLL_VPLL2:
-       case PLL_VPLL3:
-               nv_mask(priv, info.reg + 0x0c, 0x00000000, 0x00000100);
-               nv_wr32(priv, info.reg + 0x04, (P << 16) | (N << 8) | M);
-               nv_wr32(priv, info.reg + 0x10, fN << 16);
-               break;
-       default:
-               nv_warn(priv, "0x%08x/%dKhz unimplemented\n", type, freq);
-               ret = -EINVAL;
-               break;
-       }
-
-       return ret;
-}
-
-static u64
-nvc0_devinit_disable(struct nouveau_devinit *devinit)
-{
-       struct nv50_devinit_priv *priv = (void *)devinit;
-       u32 r022500 = nv_rd32(priv, 0x022500);
-       u64 disable = 0ULL;
-
-       if (r022500 & 0x00000001)
-               disable |= (1ULL << NVDEV_ENGINE_DISP);
-
-       if (r022500 & 0x00000002) {
-               disable |= (1ULL << NVDEV_ENGINE_VP);
-               disable |= (1ULL << NVDEV_ENGINE_PPP);
-       }
-
-       if (r022500 & 0x00000004)
-               disable |= (1ULL << NVDEV_ENGINE_BSP);
-       if (r022500 & 0x00000008)
-               disable |= (1ULL << NVDEV_ENGINE_VENC);
-       if (r022500 & 0x00000100)
-               disable |= (1ULL << NVDEV_ENGINE_COPY0);
-       if (r022500 & 0x00000200)
-               disable |= (1ULL << NVDEV_ENGINE_COPY1);
-
-       return disable;
-}
-
-static int
-nvc0_devinit_ctor(struct nouveau_object *parent, struct nouveau_object *engine,
-                 struct nouveau_oclass *oclass, void *data, u32 size,
-                 struct nouveau_object **pobject)
-{
-       struct nv50_devinit_priv *priv;
-       int ret;
-
-       ret = nouveau_devinit_create(parent, engine, oclass, &priv);
-       *pobject = nv_object(priv);
-       if (ret)
-               return ret;
-
-       if (nv_rd32(priv, 0x022500) & 0x00000001)
-               priv->base.post = true;
-       return 0;
-}
-
-struct nouveau_oclass *
-nvc0_devinit_oclass = &(struct nouveau_devinit_impl) {
-       .base.handle = NV_SUBDEV(DEVINIT, 0xc0),
-       .base.ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nvc0_devinit_ctor,
-               .dtor = _nouveau_devinit_dtor,
-               .init = nv50_devinit_init,
-               .fini = _nouveau_devinit_fini,
-       },
-       .pll_set = nvc0_devinit_pll_set,
-       .disable = nvc0_devinit_disable,
-       .post = nvbios_init,
-}.base;
diff --git a/drivers/gpu/drm/nouveau/core/subdev/devinit/priv.h b/drivers/gpu/drm/nouveau/core/subdev/devinit/priv.h
deleted file mode 100644 (file)
index cbcd518..0000000
+++ /dev/null
@@ -1,40 +0,0 @@
-#ifndef __NVKM_DEVINIT_PRIV_H__
-#define __NVKM_DEVINIT_PRIV_H__
-
-#include <subdev/bios.h>
-#include <subdev/bios/pll.h>
-#include <subdev/bios/init.h>
-#include <subdev/clock/pll.h>
-#include <subdev/devinit.h>
-
-struct nouveau_devinit_impl {
-       struct nouveau_oclass base;
-       void (*meminit)(struct nouveau_devinit *);
-       int  (*pll_set)(struct nouveau_devinit *, u32 type, u32 freq);
-       u64  (*disable)(struct nouveau_devinit *);
-       u32  (*mmio)(struct nouveau_devinit *, u32);
-       int  (*post)(struct nouveau_subdev *, bool);
-};
-
-#define nouveau_devinit_create(p,e,o,d)                                        \
-       nouveau_devinit_create_((p), (e), (o), sizeof(**d), (void **)d)
-#define nouveau_devinit_destroy(p) ({                                          \
-       struct nouveau_devinit *d = (p);                                       \
-       _nouveau_devinit_dtor(nv_object(d));                                   \
-})
-#define nouveau_devinit_init(p) ({                                             \
-       struct nouveau_devinit *d = (p);                                       \
-       _nouveau_devinit_init(nv_object(d));                                   \
-})
-#define nouveau_devinit_fini(p,s) ({                                           \
-       struct nouveau_devinit *d = (p);                                       \
-       _nouveau_devinit_fini(nv_object(d), (s));                              \
-})
-
-int nouveau_devinit_create_(struct nouveau_object *, struct nouveau_object *,
-                           struct nouveau_oclass *, int, void **);
-void _nouveau_devinit_dtor(struct nouveau_object *);
-int _nouveau_devinit_init(struct nouveau_object *);
-int _nouveau_devinit_fini(struct nouveau_object *, bool suspend);
-
-#endif
diff --git a/drivers/gpu/drm/nouveau/core/subdev/fb/base.c b/drivers/gpu/drm/nouveau/core/subdev/fb/base.c
deleted file mode 100644 (file)
index c866148..0000000
+++ /dev/null
@@ -1,159 +0,0 @@
-/*
- * Copyright 2012 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 <subdev/bios.h>
-#include <subdev/bios/M0203.h>
-
-#include "priv.h"
-
-int
-nouveau_fb_bios_memtype(struct nouveau_bios *bios)
-{
-       const u8 ramcfg = (nv_rd32(bios, 0x101000) & 0x0000003c) >> 2;
-       struct nvbios_M0203E M0203E;
-       u8 ver, hdr;
-
-       if (nvbios_M0203Em(bios, ramcfg, &ver, &hdr, &M0203E)) {
-               switch (M0203E.type) {
-               case M0203E_TYPE_DDR2 : return NV_MEM_TYPE_DDR2;
-               case M0203E_TYPE_DDR3 : return NV_MEM_TYPE_DDR3;
-               case M0203E_TYPE_GDDR3: return NV_MEM_TYPE_GDDR3;
-               case M0203E_TYPE_GDDR5: return NV_MEM_TYPE_GDDR5;
-               default:
-                       nv_warn(bios, "M0203E type %02x\n", M0203E.type);
-                       return NV_MEM_TYPE_UNKNOWN;
-               }
-       }
-
-       nv_warn(bios, "M0203E not matched!\n");
-       return NV_MEM_TYPE_UNKNOWN;
-}
-
-int
-_nouveau_fb_fini(struct nouveau_object *object, bool suspend)
-{
-       struct nouveau_fb *pfb = (void *)object;
-       int ret;
-
-       ret = nv_ofuncs(pfb->ram)->fini(nv_object(pfb->ram), suspend);
-       if (ret && suspend)
-               return ret;
-
-       return nouveau_subdev_fini(&pfb->base, suspend);
-}
-
-int
-_nouveau_fb_init(struct nouveau_object *object)
-{
-       struct nouveau_fb *pfb = (void *)object;
-       int ret, i;
-
-       ret = nouveau_subdev_init(&pfb->base);
-       if (ret)
-               return ret;
-
-       ret = nv_ofuncs(pfb->ram)->init(nv_object(pfb->ram));
-       if (ret)
-               return ret;
-
-       for (i = 0; i < pfb->tile.regions; i++)
-               pfb->tile.prog(pfb, i, &pfb->tile.region[i]);
-
-       return 0;
-}
-
-void
-_nouveau_fb_dtor(struct nouveau_object *object)
-{
-       struct nouveau_fb *pfb = (void *)object;
-       int i;
-
-       for (i = 0; i < pfb->tile.regions; i++)
-               pfb->tile.fini(pfb, i, &pfb->tile.region[i]);
-       nouveau_mm_fini(&pfb->tags);
-       nouveau_mm_fini(&pfb->vram);
-
-       nouveau_object_ref(NULL, (struct nouveau_object **)&pfb->ram);
-       nouveau_subdev_destroy(&pfb->base);
-}
-
-int
-nouveau_fb_create_(struct nouveau_object *parent, struct nouveau_object *engine,
-                  struct nouveau_oclass *oclass, int length, void **pobject)
-{
-       struct nouveau_fb_impl *impl = (void *)oclass;
-       static const char *name[] = {
-               [NV_MEM_TYPE_UNKNOWN] = "unknown",
-               [NV_MEM_TYPE_STOLEN ] = "stolen system memory",
-               [NV_MEM_TYPE_SGRAM  ] = "SGRAM",
-               [NV_MEM_TYPE_SDRAM  ] = "SDRAM",
-               [NV_MEM_TYPE_DDR1   ] = "DDR1",
-               [NV_MEM_TYPE_DDR2   ] = "DDR2",
-               [NV_MEM_TYPE_DDR3   ] = "DDR3",
-               [NV_MEM_TYPE_GDDR2  ] = "GDDR2",
-               [NV_MEM_TYPE_GDDR3  ] = "GDDR3",
-               [NV_MEM_TYPE_GDDR4  ] = "GDDR4",
-               [NV_MEM_TYPE_GDDR5  ] = "GDDR5",
-       };
-       struct nouveau_object *ram;
-       struct nouveau_fb *pfb;
-       int ret;
-
-       ret = nouveau_subdev_create_(parent, engine, oclass, 0, "PFB", "fb",
-                                    length, pobject);
-       pfb = *pobject;
-       if (ret)
-               return ret;
-
-       pfb->memtype_valid = impl->memtype;
-
-       ret = nouveau_object_ctor(nv_object(pfb), nv_object(pfb),
-                                 impl->ram, NULL, 0, &ram);
-       if (ret) {
-               nv_fatal(pfb, "error detecting memory configuration!!\n");
-               return ret;
-       }
-
-       atomic_dec(&ram->parent->refcount);
-       atomic_dec(&ram->engine->refcount);
-       pfb->ram = (void *)ram;
-
-       if (!nouveau_mm_initialised(&pfb->vram)) {
-               ret = nouveau_mm_init(&pfb->vram, 0, pfb->ram->size >> 12, 1);
-               if (ret)
-                       return ret;
-       }
-
-       if (!nouveau_mm_initialised(&pfb->tags)) {
-               ret = nouveau_mm_init(&pfb->tags, 0, pfb->ram->tags ?
-                                    ++pfb->ram->tags : 0, 1);
-               if (ret)
-                       return ret;
-       }
-
-       nv_info(pfb, "RAM type: %s\n", name[pfb->ram->type]);
-       nv_info(pfb, "RAM size: %d MiB\n", (int)(pfb->ram->size >> 20));
-       nv_info(pfb, "   ZCOMP: %d tags\n", pfb->ram->tags);
-       return 0;
-}
diff --git a/drivers/gpu/drm/nouveau/core/subdev/fb/gddr3.c b/drivers/gpu/drm/nouveau/core/subdev/fb/gddr3.c
deleted file mode 100644 (file)
index d85a25d..0000000
+++ /dev/null
@@ -1,117 +0,0 @@
-/*
- * Copyright 2013 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 <bskeggs@redhat.com>
- *         Roy Spliet <rspliet@eclipso.eu>
- */
-
-#include <subdev/bios.h>
-#include "priv.h"
-
-struct ramxlat {
-       int id;
-       u8 enc;
-};
-
-static inline int
-ramxlat(const struct ramxlat *xlat, int id)
-{
-       while (xlat->id >= 0) {
-               if (xlat->id == id)
-                       return xlat->enc;
-               xlat++;
-       }
-       return -EINVAL;
-}
-
-static const struct ramxlat
-ramgddr3_cl_lo[] = {
-       { 7, 7 }, { 8, 0 }, { 9, 1 }, { 10, 2 }, { 11, 3 },
-       /* the below are mentioned in some, but not all, gddr3 docs */
-       { 12, 4 }, { 13, 5 }, { 14, 6 },
-       /* XXX: Per Samsung docs, are these used? They overlap with Qimonda */
-       /* { 4, 4 }, { 5, 5 }, { 6, 6 }, { 12, 8 }, { 13, 9 }, { 14, 10 },
-        * { 15, 11 }, */
-       { -1 }
-};
-
-static const struct ramxlat
-ramgddr3_cl_hi[] = {
-       { 10, 2 }, { 11, 3 }, { 12, 4 }, { 13, 5 }, { 14, 6 }, { 15, 7 },
-       { 16, 0 }, { 17, 1 },
-       { -1 }
-};
-
-static const struct ramxlat
-ramgddr3_wr_lo[] = {
-       { 5, 2 }, { 7, 4 }, { 8, 5 }, { 9, 6 }, { 10, 7 },
-       { 11, 0 },
-       /* the below are mentioned in some, but not all, gddr3 docs */
-       { 4, 1 }, { 6, 3 }, { 12, 1 }, { 13 , 2 },
-       { -1 }
-};
-
-int
-nouveau_gddr3_calc(struct nouveau_ram *ram)
-{
-       int CL, WR, CWL, DLL = 0, ODT = 0, hi;
-
-       switch (ram->next->bios.timing_ver) {
-       case 0x10:
-               CWL = ram->next->bios.timing_10_CWL;
-               CL  = ram->next->bios.timing_10_CL;
-               WR  = ram->next->bios.timing_10_WR;
-               DLL = !ram->next->bios.ramcfg_10_DLLoff;
-               ODT = ram->next->bios.timing_10_ODT;
-               break;
-       case 0x20:
-               CWL = (ram->next->bios.timing[1] & 0x00000f80) >> 7;
-               CL  = (ram->next->bios.timing[1] & 0x0000001f) >> 0;
-               WR  = (ram->next->bios.timing[2] & 0x007f0000) >> 16;
-               /* XXX: Get these values from the VBIOS instead */
-               DLL = !(ram->mr[1] & 0x1);
-               ODT =  (ram->mr[1] & 0x004) >> 2 |
-                      (ram->mr[1] & 0x040) >> 5 |
-                      (ram->mr[1] & 0x200) >> 7;
-               break;
-       default:
-               return -ENOSYS;
-       }
-
-       hi = ram->mr[2] & 0x1;
-       CL  = ramxlat(hi ? ramgddr3_cl_hi : ramgddr3_cl_lo, CL);
-       WR  = ramxlat(ramgddr3_wr_lo, WR);
-       if (CL < 0 || CWL < 1 || CWL > 7 || WR < 0)
-               return -EINVAL;
-
-       ram->mr[0] &= ~0xf74;
-       ram->mr[0] |= (CWL & 0x07) << 9;
-       ram->mr[0] |= (CL & 0x07) << 4;
-       ram->mr[0] |= (CL & 0x08) >> 1;
-
-       ram->mr[1] &= ~0x3fc;
-       ram->mr[1] |= (ODT & 0x03) << 2;
-       ram->mr[1] |= (ODT & 0x03) << 8;
-       ram->mr[1] |= (WR  & 0x03) << 4;
-       ram->mr[1] |= (WR  & 0x04) << 5;
-       ram->mr[1] |= !DLL << 6;
-       return 0;
-}
diff --git a/drivers/gpu/drm/nouveau/core/subdev/fb/gddr5.c b/drivers/gpu/drm/nouveau/core/subdev/fb/gddr5.c
deleted file mode 100644 (file)
index 7fbbe05..0000000
+++ /dev/null
@@ -1,122 +0,0 @@
-/*
- * Copyright 2013 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 <bskeggs@redhat.com>
- */
-
-#include <subdev/bios.h>
-#include "priv.h"
-
-/* binary driver only executes this path if the condition (a) is true
- * for any configuration (combination of rammap+ramcfg+timing) that
- * can be reached on a given card.  for now, we will execute the branch
- * unconditionally in the hope that a "false everywhere" in the bios
- * tables doesn't actually mean "don't touch this".
- */
-#define NOTE00(a) 1
-
-int
-nouveau_gddr5_calc(struct nouveau_ram *ram, bool nuts)
-{
-       int pd, lf, xd, vh, vr, vo, l3;
-       int WL, CL, WR, at[2], dt, ds;
-       int rq = ram->freq < 1000000; /* XXX */
-
-       switch (ram->next->bios.ramcfg_ver) {
-       case 0x11:
-               pd =  ram->next->bios.ramcfg_11_01_80;
-               lf =  ram->next->bios.ramcfg_11_01_40;
-               xd = !ram->next->bios.ramcfg_11_01_20;
-               vh =  ram->next->bios.ramcfg_11_02_10;
-               vr =  ram->next->bios.ramcfg_11_02_04;
-               vo =  ram->next->bios.ramcfg_11_06;
-               l3 = !ram->next->bios.ramcfg_11_07_02;
-               break;
-       default:
-               return -ENOSYS;
-       }
-
-       switch (ram->next->bios.timing_ver) {
-       case 0x20:
-               WL = (ram->next->bios.timing[1] & 0x00000f80) >> 7;
-               CL = (ram->next->bios.timing[1] & 0x0000001f);
-               WR = (ram->next->bios.timing[2] & 0x007f0000) >> 16;
-               at[0] = ram->next->bios.timing_20_2e_c0;
-               at[1] = ram->next->bios.timing_20_2e_30;
-               dt =  ram->next->bios.timing_20_2e_03;
-               ds =  ram->next->bios.timing_20_2f_03;
-               break;
-       default:
-               return -ENOSYS;
-       }
-
-       if (WL < 1 || WL > 7 || CL < 5 || CL > 36 || WR < 4 || WR > 35)
-               return -EINVAL;
-       CL -= 5;
-       WR -= 4;
-
-       ram->mr[0] &= ~0xf7f;
-       ram->mr[0] |= (WR & 0x0f) << 8;
-       ram->mr[0] |= (CL & 0x0f) << 3;
-       ram->mr[0] |= (WL & 0x07) << 0;
-
-       ram->mr[1] &= ~0x0bf;
-       ram->mr[1] |= (xd & 0x01) << 7;
-       ram->mr[1] |= (at[0] & 0x03) << 4;
-       ram->mr[1] |= (dt & 0x03) << 2;
-       ram->mr[1] |= (ds & 0x03) << 0;
-
-       /* this seems wrong, alternate field used for the broadcast
-        * on nuts vs non-nuts configs..  meh, it matches for now.
-        */
-       ram->mr1_nuts = ram->mr[1];
-       if (nuts) {
-               ram->mr[1] &= ~0x030;
-               ram->mr[1] |= (at[1] & 0x03) << 4;
-       }
-
-       ram->mr[3] &= ~0x020;
-       ram->mr[3] |= (rq & 0x01) << 5;
-
-       ram->mr[5] &= ~0x004;
-       ram->mr[5] |= (l3 << 2);
-
-       if (!vo)
-               vo = (ram->mr[6] & 0xff0) >> 4;
-       if (ram->mr[6] & 0x001)
-               pd = 1; /* binary driver does this.. bug? */
-       ram->mr[6] &= ~0xff1;
-       ram->mr[6] |= (vo & 0xff) << 4;
-       ram->mr[6] |= (pd & 0x01) << 0;
-
-       if (NOTE00(vr)) {
-               ram->mr[7] &= ~0x300;
-               ram->mr[7] |= (vr & 0x03) << 8;
-       }
-       ram->mr[7] &= ~0x088;
-       ram->mr[7] |= (vh & 0x01) << 7;
-       ram->mr[7] |= (lf & 0x01) << 3;
-
-       ram->mr[8] &= ~0x003;
-       ram->mr[8] |= (WR & 0x10) >> 3;
-       ram->mr[8] |= (CL & 0x10) >> 4;
-       return 0;
-}
diff --git a/drivers/gpu/drm/nouveau/core/subdev/fb/gk20a.c b/drivers/gpu/drm/nouveau/core/subdev/fb/gk20a.c
deleted file mode 100644 (file)
index fde42e4..0000000
+++ /dev/null
@@ -1,70 +0,0 @@
-/*
- * Copyright (c) 2014, NVIDIA CORPORATION. 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 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 "nvc0.h"
-
-struct gk20a_fb_priv {
-       struct nouveau_fb base;
-};
-
-static int
-gk20a_fb_init(struct nouveau_object *object)
-{
-       struct gk20a_fb_priv *priv = (void *)object;
-       int ret;
-
-       ret = nouveau_fb_init(&priv->base);
-       if (ret)
-               return ret;
-
-       nv_mask(priv, 0x100c80, 0x00000001, 0x00000000); /* 128KiB lpg */
-       return 0;
-}
-
-static int
-gk20a_fb_ctor(struct nouveau_object *parent, struct nouveau_object *engine,
-            struct nouveau_oclass *oclass, void *data, u32 size,
-            struct nouveau_object **pobject)
-{
-       struct gk20a_fb_priv *priv;
-       int ret;
-
-       ret = nouveau_fb_create(parent, engine, oclass, &priv);
-       *pobject = nv_object(priv);
-       if (ret)
-               return ret;
-
-       return 0;
-}
-
-struct nouveau_oclass *
-gk20a_fb_oclass = &(struct nouveau_fb_impl) {
-       .base.handle = NV_SUBDEV(FB, 0xea),
-       .base.ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = gk20a_fb_ctor,
-               .dtor = _nouveau_fb_dtor,
-               .init = gk20a_fb_init,
-               .fini = _nouveau_fb_fini,
-       },
-       .memtype = nvc0_fb_memtype_valid,
-       .ram = &gk20a_ram_oclass,
-}.base;
diff --git a/drivers/gpu/drm/nouveau/core/subdev/fb/gm107.c b/drivers/gpu/drm/nouveau/core/subdev/fb/gm107.c
deleted file mode 100644 (file)
index c4840ae..0000000
+++ /dev/null
@@ -1,38 +0,0 @@
-/*
- * Copyright 2012 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 "nvc0.h"
-
-struct nouveau_oclass *
-gm107_fb_oclass = &(struct nouveau_fb_impl) {
-       .base.handle = NV_SUBDEV(FB, 0x07),
-       .base.ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nvc0_fb_ctor,
-               .dtor = nvc0_fb_dtor,
-               .init = nvc0_fb_init,
-               .fini = _nouveau_fb_fini,
-       },
-       .memtype = nvc0_fb_memtype_valid,
-       .ram = &gm107_ram_oclass,
-}.base;
diff --git a/drivers/gpu/drm/nouveau/core/subdev/fb/nv04.c b/drivers/gpu/drm/nouveau/core/subdev/fb/nv04.c
deleted file mode 100644 (file)
index 8309fe3..0000000
+++ /dev/null
@@ -1,89 +0,0 @@
-/*
- * Copyright 2012 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 "nv04.h"
-
-#define NV04_PFB_CFG0                                          0x00100200
-
-bool
-nv04_fb_memtype_valid(struct nouveau_fb *pfb, u32 tile_flags)
-{
-       if (!(tile_flags & 0xff00))
-               return true;
-
-       return false;
-}
-
-static int
-nv04_fb_init(struct nouveau_object *object)
-{
-       struct nv04_fb_priv *priv = (void *)object;
-       int ret;
-
-       ret = nouveau_fb_init(&priv->base);
-       if (ret)
-               return ret;
-
-       /* This is what the DDX did for NV_ARCH_04, but a mmio-trace shows
-        * nvidia reading PFB_CFG_0, then writing back its original value.
-        * (which was 0x701114 in this case)
-        */
-       nv_wr32(priv, NV04_PFB_CFG0, 0x1114);
-       return 0;
-}
-
-int
-nv04_fb_ctor(struct nouveau_object *parent, struct nouveau_object *engine,
-            struct nouveau_oclass *oclass, void *data, u32 size,
-            struct nouveau_object **pobject)
-{
-       struct nv04_fb_impl *impl = (void *)oclass;
-       struct nv04_fb_priv *priv;
-       int ret;
-
-       ret = nouveau_fb_create(parent, engine, oclass, &priv);
-       *pobject = nv_object(priv);
-       if (ret)
-               return ret;
-
-       priv->base.tile.regions = impl->tile.regions;
-       priv->base.tile.init = impl->tile.init;
-       priv->base.tile.comp = impl->tile.comp;
-       priv->base.tile.fini = impl->tile.fini;
-       priv->base.tile.prog = impl->tile.prog;
-       return 0;
-}
-
-struct nouveau_oclass *
-nv04_fb_oclass = &(struct nv04_fb_impl) {
-       .base.base.handle = NV_SUBDEV(FB, 0x04),
-       .base.base.ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nv04_fb_ctor,
-               .dtor = _nouveau_fb_dtor,
-               .init = nv04_fb_init,
-               .fini = _nouveau_fb_fini,
-       },
-       .base.memtype = nv04_fb_memtype_valid,
-       .base.ram = &nv04_ram_oclass,
-}.base.base;
diff --git a/drivers/gpu/drm/nouveau/core/subdev/fb/nv04.h b/drivers/gpu/drm/nouveau/core/subdev/fb/nv04.h
deleted file mode 100644 (file)
index 06ce71f..0000000
+++ /dev/null
@@ -1,55 +0,0 @@
-#ifndef __NVKM_FB_NV04_H__
-#define __NVKM_FB_NV04_H__
-
-#include "priv.h"
-
-struct nv04_fb_priv {
-       struct nouveau_fb base;
-};
-
-int  nv04_fb_ctor(struct nouveau_object *, struct nouveau_object *,
-                 struct nouveau_oclass *, void *, u32,
-                 struct nouveau_object **);
-
-struct nv04_fb_impl {
-       struct nouveau_fb_impl base;
-       struct {
-               int regions;
-               void (*init)(struct nouveau_fb *, int i, u32 addr, u32 size,
-                            u32 pitch, u32 flags, struct nouveau_fb_tile *);
-               void (*comp)(struct nouveau_fb *, int i, u32 size, u32 flags,
-                            struct nouveau_fb_tile *);
-               void (*fini)(struct nouveau_fb *, int i,
-                            struct nouveau_fb_tile *);
-               void (*prog)(struct nouveau_fb *, int i,
-                            struct nouveau_fb_tile *);
-       } tile;
-};
-
-void nv10_fb_tile_init(struct nouveau_fb *, int i, u32 addr, u32 size,
-                      u32 pitch, u32 flags, struct nouveau_fb_tile *);
-void nv10_fb_tile_fini(struct nouveau_fb *, int i, struct nouveau_fb_tile *);
-void nv10_fb_tile_prog(struct nouveau_fb *, int, struct nouveau_fb_tile *);
-
-void nv20_fb_tile_init(struct nouveau_fb *, int i, u32 addr, u32 size,
-                      u32 pitch, u32 flags, struct nouveau_fb_tile *);
-void nv20_fb_tile_fini(struct nouveau_fb *, int i, struct nouveau_fb_tile *);
-void nv20_fb_tile_prog(struct nouveau_fb *, int, struct nouveau_fb_tile *);
-
-int  nv30_fb_init(struct nouveau_object *);
-void nv30_fb_tile_init(struct nouveau_fb *, int i, u32 addr, u32 size,
-                      u32 pitch, u32 flags, struct nouveau_fb_tile *);
-
-void nv40_fb_tile_comp(struct nouveau_fb *, int i, u32 size, u32 flags,
-                      struct nouveau_fb_tile *);
-
-int  nv41_fb_init(struct nouveau_object *);
-void nv41_fb_tile_prog(struct nouveau_fb *, int, struct nouveau_fb_tile *);
-
-int  nv44_fb_init(struct nouveau_object *);
-void nv44_fb_tile_prog(struct nouveau_fb *, int, struct nouveau_fb_tile *);
-
-void nv46_fb_tile_init(struct nouveau_fb *, int i, u32 addr, u32 size,
-                      u32 pitch, u32 flags, struct nouveau_fb_tile *);
-
-#endif
diff --git a/drivers/gpu/drm/nouveau/core/subdev/fb/nv10.c b/drivers/gpu/drm/nouveau/core/subdev/fb/nv10.c
deleted file mode 100644 (file)
index ffb7ec6..0000000
+++ /dev/null
@@ -1,71 +0,0 @@
-/*
- * 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.
- *
- */
-
-#include "nv04.h"
-
-void
-nv10_fb_tile_init(struct nouveau_fb *pfb, int i, u32 addr, u32 size, u32 pitch,
-                 u32 flags, struct nouveau_fb_tile *tile)
-{
-       tile->addr  = 0x80000000 | addr;
-       tile->limit = max(1u, addr + size) - 1;
-       tile->pitch = pitch;
-}
-
-void
-nv10_fb_tile_fini(struct nouveau_fb *pfb, int i, struct nouveau_fb_tile *tile)
-{
-       tile->addr  = 0;
-       tile->limit = 0;
-       tile->pitch = 0;
-       tile->zcomp = 0;
-}
-
-void
-nv10_fb_tile_prog(struct nouveau_fb *pfb, int i, struct nouveau_fb_tile *tile)
-{
-       nv_wr32(pfb, 0x100244 + (i * 0x10), tile->limit);
-       nv_wr32(pfb, 0x100248 + (i * 0x10), tile->pitch);
-       nv_wr32(pfb, 0x100240 + (i * 0x10), tile->addr);
-       nv_rd32(pfb, 0x100240 + (i * 0x10));
-}
-
-struct nouveau_oclass *
-nv10_fb_oclass = &(struct nv04_fb_impl) {
-       .base.base.handle = NV_SUBDEV(FB, 0x10),
-       .base.base.ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nv04_fb_ctor,
-               .dtor = _nouveau_fb_dtor,
-               .init = _nouveau_fb_init,
-               .fini = _nouveau_fb_fini,
-       },
-       .base.memtype = nv04_fb_memtype_valid,
-       .base.ram = &nv10_ram_oclass,
-       .tile.regions = 8,
-       .tile.init = nv10_fb_tile_init,
-       .tile.fini = nv10_fb_tile_fini,
-       .tile.prog = nv10_fb_tile_prog,
-}.base.base;
diff --git a/drivers/gpu/drm/nouveau/core/subdev/fb/nv1a.c b/drivers/gpu/drm/nouveau/core/subdev/fb/nv1a.c
deleted file mode 100644 (file)
index 265d125..0000000
+++ /dev/null
@@ -1,44 +0,0 @@
-/*
- * 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.
- *
- */
-
-#include "nv04.h"
-
-struct nouveau_oclass *
-nv1a_fb_oclass = &(struct nv04_fb_impl) {
-       .base.base.handle = NV_SUBDEV(FB, 0x1a),
-       .base.base.ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nv04_fb_ctor,
-               .dtor = _nouveau_fb_dtor,
-               .init = _nouveau_fb_init,
-               .fini = _nouveau_fb_fini,
-       },
-       .base.memtype = nv04_fb_memtype_valid,
-       .base.ram = &nv1a_ram_oclass,
-       .tile.regions = 8,
-       .tile.init = nv10_fb_tile_init,
-       .tile.fini = nv10_fb_tile_fini,
-       .tile.prog = nv10_fb_tile_prog,
-}.base.base;
diff --git a/drivers/gpu/drm/nouveau/core/subdev/fb/nv20.c b/drivers/gpu/drm/nouveau/core/subdev/fb/nv20.c
deleted file mode 100644 (file)
index 2209ade..0000000
+++ /dev/null
@@ -1,95 +0,0 @@
-/*
- * 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.
- *
- */
-
-#include "nv04.h"
-
-void
-nv20_fb_tile_init(struct nouveau_fb *pfb, int i, u32 addr, u32 size, u32 pitch,
-                 u32 flags, struct nouveau_fb_tile *tile)
-{
-       tile->addr  = 0x00000001 | addr;
-       tile->limit = max(1u, addr + size) - 1;
-       tile->pitch = pitch;
-       if (flags & 4) {
-               pfb->tile.comp(pfb, i, size, flags, tile);
-               tile->addr |= 2;
-       }
-}
-
-static void
-nv20_fb_tile_comp(struct nouveau_fb *pfb, int i, u32 size, u32 flags,
-                 struct nouveau_fb_tile *tile)
-{
-       u32 tiles = DIV_ROUND_UP(size, 0x40);
-       u32 tags  = round_up(tiles / pfb->ram->parts, 0x40);
-       if (!nouveau_mm_head(&pfb->tags, 0, 1, tags, tags, 1, &tile->tag)) {
-               if (!(flags & 2)) tile->zcomp = 0x00000000; /* Z16 */
-               else              tile->zcomp = 0x04000000; /* Z24S8 */
-               tile->zcomp |= tile->tag->offset;
-               tile->zcomp |= 0x80000000; /* enable */
-#ifdef __BIG_ENDIAN
-               tile->zcomp |= 0x08000000;
-#endif
-       }
-}
-
-void
-nv20_fb_tile_fini(struct nouveau_fb *pfb, int i, struct nouveau_fb_tile *tile)
-{
-       tile->addr  = 0;
-       tile->limit = 0;
-       tile->pitch = 0;
-       tile->zcomp = 0;
-       nouveau_mm_free(&pfb->tags, &tile->tag);
-}
-
-void
-nv20_fb_tile_prog(struct nouveau_fb *pfb, int i, struct nouveau_fb_tile *tile)
-{
-       nv_wr32(pfb, 0x100244 + (i * 0x10), tile->limit);
-       nv_wr32(pfb, 0x100248 + (i * 0x10), tile->pitch);
-       nv_wr32(pfb, 0x100240 + (i * 0x10), tile->addr);
-       nv_rd32(pfb, 0x100240 + (i * 0x10));
-       nv_wr32(pfb, 0x100300 + (i * 0x04), tile->zcomp);
-}
-
-struct nouveau_oclass *
-nv20_fb_oclass = &(struct nv04_fb_impl) {
-       .base.base.handle = NV_SUBDEV(FB, 0x20),
-       .base.base.ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nv04_fb_ctor,
-               .dtor = _nouveau_fb_dtor,
-               .init = _nouveau_fb_init,
-               .fini = _nouveau_fb_fini,
-       },
-       .base.memtype = nv04_fb_memtype_valid,
-       .base.ram = &nv20_ram_oclass,
-       .tile.regions = 8,
-       .tile.init = nv20_fb_tile_init,
-       .tile.comp = nv20_fb_tile_comp,
-       .tile.fini = nv20_fb_tile_fini,
-       .tile.prog = nv20_fb_tile_prog,
-}.base.base;
diff --git a/drivers/gpu/drm/nouveau/core/subdev/fb/nv25.c b/drivers/gpu/drm/nouveau/core/subdev/fb/nv25.c
deleted file mode 100644 (file)
index e2a66c3..0000000
+++ /dev/null
@@ -1,61 +0,0 @@
-/*
- * 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.
- *
- */
-
-#include "nv04.h"
-
-static void
-nv25_fb_tile_comp(struct nouveau_fb *pfb, int i, u32 size, u32 flags,
-                 struct nouveau_fb_tile *tile)
-{
-       u32 tiles = DIV_ROUND_UP(size, 0x40);
-       u32 tags  = round_up(tiles / pfb->ram->parts, 0x40);
-       if (!nouveau_mm_head(&pfb->tags, 0, 1, tags, tags, 1, &tile->tag)) {
-               if (!(flags & 2)) tile->zcomp = 0x00100000; /* Z16 */
-               else              tile->zcomp = 0x00200000; /* Z24S8 */
-               tile->zcomp |= tile->tag->offset;
-#ifdef __BIG_ENDIAN
-               tile->zcomp |= 0x01000000;
-#endif
-       }
-}
-
-struct nouveau_oclass *
-nv25_fb_oclass = &(struct nv04_fb_impl) {
-       .base.base.handle = NV_SUBDEV(FB, 0x25),
-       .base.base.ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nv04_fb_ctor,
-               .dtor = _nouveau_fb_dtor,
-               .init = _nouveau_fb_init,
-               .fini = _nouveau_fb_fini,
-       },
-       .base.memtype = nv04_fb_memtype_valid,
-       .base.ram = &nv20_ram_oclass,
-       .tile.regions = 8,
-       .tile.init = nv20_fb_tile_init,
-       .tile.comp = nv25_fb_tile_comp,
-       .tile.fini = nv20_fb_tile_fini,
-       .tile.prog = nv20_fb_tile_prog,
-}.base.base;
diff --git a/drivers/gpu/drm/nouveau/core/subdev/fb/nv30.c b/drivers/gpu/drm/nouveau/core/subdev/fb/nv30.c
deleted file mode 100644 (file)
index cbec402..0000000
+++ /dev/null
@@ -1,139 +0,0 @@
-/*
- * 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.
- *
- */
-
-#include "nv04.h"
-
-void
-nv30_fb_tile_init(struct nouveau_fb *pfb, int i, u32 addr, u32 size, u32 pitch,
-                 u32 flags, struct nouveau_fb_tile *tile)
-{
-       /* for performance, select alternate bank offset for zeta */
-       if (!(flags & 4)) {
-               tile->addr = (0 << 4);
-       } else {
-               if (pfb->tile.comp) /* z compression */
-                       pfb->tile.comp(pfb, i, size, flags, tile);
-               tile->addr = (1 << 4);
-       }
-
-       tile->addr |= 0x00000001; /* enable */
-       tile->addr |= addr;
-       tile->limit = max(1u, addr + size) - 1;
-       tile->pitch = pitch;
-}
-
-static void
-nv30_fb_tile_comp(struct nouveau_fb *pfb, int i, u32 size, u32 flags,
-                 struct nouveau_fb_tile *tile)
-{
-       u32 tiles = DIV_ROUND_UP(size, 0x40);
-       u32 tags  = round_up(tiles / pfb->ram->parts, 0x40);
-       if (!nouveau_mm_head(&pfb->tags, 0, 1, tags, tags, 1, &tile->tag)) {
-               if (flags & 2) tile->zcomp |= 0x01000000; /* Z16 */
-               else           tile->zcomp |= 0x02000000; /* Z24S8 */
-               tile->zcomp |= ((tile->tag->offset           ) >> 6);
-               tile->zcomp |= ((tile->tag->offset + tags - 1) >> 6) << 12;
-#ifdef __BIG_ENDIAN
-               tile->zcomp |= 0x10000000;
-#endif
-       }
-}
-
-static int
-calc_bias(struct nv04_fb_priv *priv, int k, int i, int j)
-{
-       struct nouveau_device *device = nv_device(priv);
-       int b = (device->chipset > 0x30 ?
-                nv_rd32(priv, 0x122c + 0x10 * k + 0x4 * j) >> (4 * (i ^ 1)) :
-                0) & 0xf;
-
-       return 2 * (b & 0x8 ? b - 0x10 : b);
-}
-
-static int
-calc_ref(struct nv04_fb_priv *priv, int l, int k, int i)
-{
-       int j, x = 0;
-
-       for (j = 0; j < 4; j++) {
-               int m = (l >> (8 * i) & 0xff) + calc_bias(priv, k, i, j);
-
-               x |= (0x80 | clamp(m, 0, 0x1f)) << (8 * j);
-       }
-
-       return x;
-}
-
-int
-nv30_fb_init(struct nouveau_object *object)
-{
-       struct nouveau_device *device = nv_device(object);
-       struct nv04_fb_priv *priv = (void *)object;
-       int ret, i, j;
-
-       ret = nouveau_fb_init(&priv->base);
-       if (ret)
-               return ret;
-
-       /* Init the memory timing regs at 0x10037c/0x1003ac */
-       if (device->chipset == 0x30 ||
-           device->chipset == 0x31 ||
-           device->chipset == 0x35) {
-               /* Related to ROP count */
-               int n = (device->chipset == 0x31 ? 2 : 4);
-               int l = nv_rd32(priv, 0x1003d0);
-
-               for (i = 0; i < n; i++) {
-                       for (j = 0; j < 3; j++)
-                               nv_wr32(priv, 0x10037c + 0xc * i + 0x4 * j,
-                                       calc_ref(priv, l, 0, j));
-
-                       for (j = 0; j < 2; j++)
-                               nv_wr32(priv, 0x1003ac + 0x8 * i + 0x4 * j,
-                                       calc_ref(priv, l, 1, j));
-               }
-       }
-
-       return 0;
-}
-
-struct nouveau_oclass *
-nv30_fb_oclass = &(struct nv04_fb_impl) {
-       .base.base.handle = NV_SUBDEV(FB, 0x30),
-       .base.base.ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nv04_fb_ctor,
-               .dtor = _nouveau_fb_dtor,
-               .init = nv30_fb_init,
-               .fini = _nouveau_fb_fini,
-       },
-       .base.memtype = nv04_fb_memtype_valid,
-       .base.ram = &nv20_ram_oclass,
-       .tile.regions = 8,
-       .tile.init = nv30_fb_tile_init,
-       .tile.comp = nv30_fb_tile_comp,
-       .tile.fini = nv20_fb_tile_fini,
-       .tile.prog = nv20_fb_tile_prog,
-}.base.base;
diff --git a/drivers/gpu/drm/nouveau/core/subdev/fb/nv35.c b/drivers/gpu/drm/nouveau/core/subdev/fb/nv35.c
deleted file mode 100644 (file)
index b2cf8c6..0000000
+++ /dev/null
@@ -1,62 +0,0 @@
-/*
- * 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.
- *
- */
-
-#include "nv04.h"
-
-static void
-nv35_fb_tile_comp(struct nouveau_fb *pfb, int i, u32 size, u32 flags,
-                 struct nouveau_fb_tile *tile)
-{
-       u32 tiles = DIV_ROUND_UP(size, 0x40);
-       u32 tags  = round_up(tiles / pfb->ram->parts, 0x40);
-       if (!nouveau_mm_head(&pfb->tags, 0, 1, tags, tags, 1, &tile->tag)) {
-               if (flags & 2) tile->zcomp |= 0x04000000; /* Z16 */
-               else           tile->zcomp |= 0x08000000; /* Z24S8 */
-               tile->zcomp |= ((tile->tag->offset           ) >> 6);
-               tile->zcomp |= ((tile->tag->offset + tags - 1) >> 6) << 13;
-#ifdef __BIG_ENDIAN
-               tile->zcomp |= 0x40000000;
-#endif
-       }
-}
-
-struct nouveau_oclass *
-nv35_fb_oclass = &(struct nv04_fb_impl) {
-       .base.base.handle = NV_SUBDEV(FB, 0x35),
-       .base.base.ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nv04_fb_ctor,
-               .dtor = _nouveau_fb_dtor,
-               .init = nv30_fb_init,
-               .fini = _nouveau_fb_fini,
-       },
-       .base.memtype = nv04_fb_memtype_valid,
-       .base.ram = &nv20_ram_oclass,
-       .tile.regions = 8,
-       .tile.init = nv30_fb_tile_init,
-       .tile.comp = nv35_fb_tile_comp,
-       .tile.fini = nv20_fb_tile_fini,
-       .tile.prog = nv20_fb_tile_prog,
-}.base.base;
diff --git a/drivers/gpu/drm/nouveau/core/subdev/fb/nv36.c b/drivers/gpu/drm/nouveau/core/subdev/fb/nv36.c
deleted file mode 100644 (file)
index b4cdae2..0000000
+++ /dev/null
@@ -1,62 +0,0 @@
-/*
- * 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.
- *
- */
-
-#include "nv04.h"
-
-static void
-nv36_fb_tile_comp(struct nouveau_fb *pfb, int i, u32 size, u32 flags,
-                 struct nouveau_fb_tile *tile)
-{
-       u32 tiles = DIV_ROUND_UP(size, 0x40);
-       u32 tags  = round_up(tiles / pfb->ram->parts, 0x40);
-       if (!nouveau_mm_head(&pfb->tags, 0, 1, tags, tags, 1, &tile->tag)) {
-               if (flags & 2) tile->zcomp |= 0x10000000; /* Z16 */
-               else           tile->zcomp |= 0x20000000; /* Z24S8 */
-               tile->zcomp |= ((tile->tag->offset           ) >> 6);
-               tile->zcomp |= ((tile->tag->offset + tags - 1) >> 6) << 14;
-#ifdef __BIG_ENDIAN
-               tile->zcomp |= 0x80000000;
-#endif
-       }
-}
-
-struct nouveau_oclass *
-nv36_fb_oclass = &(struct nv04_fb_impl) {
-       .base.base.handle = NV_SUBDEV(FB, 0x36),
-       .base.base.ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nv04_fb_ctor,
-               .dtor = _nouveau_fb_dtor,
-               .init = nv30_fb_init,
-               .fini = _nouveau_fb_fini,
-       },
-       .base.memtype = nv04_fb_memtype_valid,
-       .base.ram = &nv20_ram_oclass,
-       .tile.regions = 8,
-       .tile.init = nv30_fb_tile_init,
-       .tile.comp = nv36_fb_tile_comp,
-       .tile.fini = nv20_fb_tile_fini,
-       .tile.prog = nv20_fb_tile_prog,
-}.base.base;
diff --git a/drivers/gpu/drm/nouveau/core/subdev/fb/nv40.c b/drivers/gpu/drm/nouveau/core/subdev/fb/nv40.c
deleted file mode 100644 (file)
index 5281425..0000000
+++ /dev/null
@@ -1,76 +0,0 @@
-/*
- * 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.
- *
- */
-
-#include "nv04.h"
-
-void
-nv40_fb_tile_comp(struct nouveau_fb *pfb, int i, u32 size, u32 flags,
-                 struct nouveau_fb_tile *tile)
-{
-       u32 tiles = DIV_ROUND_UP(size, 0x80);
-       u32 tags  = round_up(tiles / pfb->ram->parts, 0x100);
-       if ( (flags & 2) &&
-           !nouveau_mm_head(&pfb->tags, 0, 1, tags, tags, 1, &tile->tag)) {
-               tile->zcomp  = 0x28000000; /* Z24S8_SPLIT_GRAD */
-               tile->zcomp |= ((tile->tag->offset           ) >> 8);
-               tile->zcomp |= ((tile->tag->offset + tags - 1) >> 8) << 13;
-#ifdef __BIG_ENDIAN
-               tile->zcomp |= 0x40000000;
-#endif
-       }
-}
-
-static int
-nv40_fb_init(struct nouveau_object *object)
-{
-       struct nv04_fb_priv *priv = (void *)object;
-       int ret;
-
-       ret = nouveau_fb_init(&priv->base);
-       if (ret)
-               return ret;
-
-       nv_mask(priv, 0x10033c, 0x00008000, 0x00000000);
-       return 0;
-}
-
-struct nouveau_oclass *
-nv40_fb_oclass = &(struct nv04_fb_impl) {
-       .base.base.handle = NV_SUBDEV(FB, 0x40),
-       .base.base.ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nv04_fb_ctor,
-               .dtor = _nouveau_fb_dtor,
-               .init = nv40_fb_init,
-               .fini = _nouveau_fb_fini,
-       },
-       .base.memtype = nv04_fb_memtype_valid,
-       .base.ram = &nv40_ram_oclass,
-       .tile.regions = 8,
-       .tile.init = nv30_fb_tile_init,
-       .tile.comp = nv40_fb_tile_comp,
-       .tile.fini = nv20_fb_tile_fini,
-       .tile.prog = nv20_fb_tile_prog,
-}.base.base;
diff --git a/drivers/gpu/drm/nouveau/core/subdev/fb/nv40.h b/drivers/gpu/drm/nouveau/core/subdev/fb/nv40.h
deleted file mode 100644 (file)
index 581f808..0000000
+++ /dev/null
@@ -1,17 +0,0 @@
-#ifndef __NVKM_FB_NV40_H__
-#define __NVKM_FB_NV40_H__
-
-#include "priv.h"
-
-struct nv40_ram {
-       struct nouveau_ram base;
-       u32 ctrl;
-       u32 coef;
-};
-
-
-int  nv40_ram_calc(struct nouveau_fb *, u32);
-int  nv40_ram_prog(struct nouveau_fb *);
-void nv40_ram_tidy(struct nouveau_fb *);
-
-#endif
diff --git a/drivers/gpu/drm/nouveau/core/subdev/fb/nv41.c b/drivers/gpu/drm/nouveau/core/subdev/fb/nv41.c
deleted file mode 100644 (file)
index b239a86..0000000
+++ /dev/null
@@ -1,69 +0,0 @@
-/*
- * 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.
- *
- */
-
-#include "nv04.h"
-
-void
-nv41_fb_tile_prog(struct nouveau_fb *pfb, int i, struct nouveau_fb_tile *tile)
-{
-       nv_wr32(pfb, 0x100604 + (i * 0x10), tile->limit);
-       nv_wr32(pfb, 0x100608 + (i * 0x10), tile->pitch);
-       nv_wr32(pfb, 0x100600 + (i * 0x10), tile->addr);
-       nv_rd32(pfb, 0x100600 + (i * 0x10));
-       nv_wr32(pfb, 0x100700 + (i * 0x04), tile->zcomp);
-}
-
-int
-nv41_fb_init(struct nouveau_object *object)
-{
-       struct nv04_fb_priv *priv = (void *)object;
-       int ret;
-
-       ret = nouveau_fb_init(&priv->base);
-       if (ret)
-               return ret;
-
-       nv_wr32(priv, 0x100800, 0x00000001);
-       return 0;
-}
-
-struct nouveau_oclass *
-nv41_fb_oclass = &(struct nv04_fb_impl) {
-       .base.base.handle = NV_SUBDEV(FB, 0x41),
-       .base.base.ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nv04_fb_ctor,
-               .dtor = _nouveau_fb_dtor,
-               .init = nv41_fb_init,
-               .fini = _nouveau_fb_fini,
-       },
-       .base.memtype = nv04_fb_memtype_valid,
-       .base.ram = &nv41_ram_oclass,
-       .tile.regions = 12,
-       .tile.init = nv30_fb_tile_init,
-       .tile.comp = nv40_fb_tile_comp,
-       .tile.fini = nv20_fb_tile_fini,
-       .tile.prog = nv41_fb_tile_prog,
-}.base.base;
diff --git a/drivers/gpu/drm/nouveau/core/subdev/fb/nv44.c b/drivers/gpu/drm/nouveau/core/subdev/fb/nv44.c
deleted file mode 100644 (file)
index d847820..0000000
+++ /dev/null
@@ -1,78 +0,0 @@
-/*
- * 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.
- *
- */
-
-#include "nv04.h"
-
-static void
-nv44_fb_tile_init(struct nouveau_fb *pfb, int i, u32 addr, u32 size, u32 pitch,
-                 u32 flags, struct nouveau_fb_tile *tile)
-{
-       tile->addr  = 0x00000001; /* mode = vram */
-       tile->addr |= addr;
-       tile->limit = max(1u, addr + size) - 1;
-       tile->pitch = pitch;
-}
-
-void
-nv44_fb_tile_prog(struct nouveau_fb *pfb, int i, struct nouveau_fb_tile *tile)
-{
-       nv_wr32(pfb, 0x100604 + (i * 0x10), tile->limit);
-       nv_wr32(pfb, 0x100608 + (i * 0x10), tile->pitch);
-       nv_wr32(pfb, 0x100600 + (i * 0x10), tile->addr);
-       nv_rd32(pfb, 0x100600 + (i * 0x10));
-}
-
-int
-nv44_fb_init(struct nouveau_object *object)
-{
-       struct nv04_fb_priv *priv = (void *)object;
-       int ret;
-
-       ret = nouveau_fb_init(&priv->base);
-       if (ret)
-               return ret;
-
-       nv_wr32(priv, 0x100850, 0x80000000);
-       nv_wr32(priv, 0x100800, 0x00000001);
-       return 0;
-}
-
-struct nouveau_oclass *
-nv44_fb_oclass = &(struct nv04_fb_impl) {
-       .base.base.handle = NV_SUBDEV(FB, 0x44),
-       .base.base.ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nv04_fb_ctor,
-               .dtor = _nouveau_fb_dtor,
-               .init = nv44_fb_init,
-               .fini = _nouveau_fb_fini,
-       },
-       .base.memtype = nv04_fb_memtype_valid,
-       .base.ram = &nv44_ram_oclass,
-       .tile.regions = 12,
-       .tile.init = nv44_fb_tile_init,
-       .tile.fini = nv20_fb_tile_fini,
-       .tile.prog = nv44_fb_tile_prog,
-}.base.base;
diff --git a/drivers/gpu/drm/nouveau/core/subdev/fb/nv46.c b/drivers/gpu/drm/nouveau/core/subdev/fb/nv46.c
deleted file mode 100644 (file)
index a5b7751..0000000
+++ /dev/null
@@ -1,58 +0,0 @@
-/*
- * 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.
- *
- */
-
-#include "nv04.h"
-
-void
-nv46_fb_tile_init(struct nouveau_fb *pfb, int i, u32 addr, u32 size, u32 pitch,
-                 u32 flags, struct nouveau_fb_tile *tile)
-{
-       /* for performance, select alternate bank offset for zeta */
-       if (!(flags & 4)) tile->addr = (0 << 3);
-       else              tile->addr = (1 << 3);
-
-       tile->addr |= 0x00000001; /* mode = vram */
-       tile->addr |= addr;
-       tile->limit = max(1u, addr + size) - 1;
-       tile->pitch = pitch;
-}
-
-struct nouveau_oclass *
-nv46_fb_oclass = &(struct nv04_fb_impl) {
-       .base.base.handle = NV_SUBDEV(FB, 0x46),
-       .base.base.ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nv04_fb_ctor,
-               .dtor = _nouveau_fb_dtor,
-               .init = nv44_fb_init,
-               .fini = _nouveau_fb_fini,
-       },
-       .base.memtype = nv04_fb_memtype_valid,
-       .base.ram = &nv44_ram_oclass,
-       .tile.regions = 15,
-       .tile.init = nv46_fb_tile_init,
-       .tile.fini = nv20_fb_tile_fini,
-       .tile.prog = nv44_fb_tile_prog,
-}.base.base;
diff --git a/drivers/gpu/drm/nouveau/core/subdev/fb/nv47.c b/drivers/gpu/drm/nouveau/core/subdev/fb/nv47.c
deleted file mode 100644 (file)
index 3bea142..0000000
+++ /dev/null
@@ -1,45 +0,0 @@
-/*
- * 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.
- *
- */
-
-#include "nv04.h"
-
-struct nouveau_oclass *
-nv47_fb_oclass = &(struct nv04_fb_impl) {
-       .base.base.handle = NV_SUBDEV(FB, 0x47),
-       .base.base.ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nv04_fb_ctor,
-               .dtor = _nouveau_fb_dtor,
-               .init = nv41_fb_init,
-               .fini = _nouveau_fb_fini,
-       },
-       .base.memtype = nv04_fb_memtype_valid,
-       .base.ram = &nv41_ram_oclass,
-       .tile.regions = 15,
-       .tile.init = nv30_fb_tile_init,
-       .tile.comp = nv40_fb_tile_comp,
-       .tile.fini = nv20_fb_tile_fini,
-       .tile.prog = nv41_fb_tile_prog,
-}.base.base;
diff --git a/drivers/gpu/drm/nouveau/core/subdev/fb/nv49.c b/drivers/gpu/drm/nouveau/core/subdev/fb/nv49.c
deleted file mode 100644 (file)
index 666cbd5..0000000
+++ /dev/null
@@ -1,45 +0,0 @@
-/*
- * 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.
- *
- */
-
-#include "nv04.h"
-
-struct nouveau_oclass *
-nv49_fb_oclass = &(struct nv04_fb_impl) {
-       .base.base.handle = NV_SUBDEV(FB, 0x49),
-       .base.base.ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nv04_fb_ctor,
-               .dtor = _nouveau_fb_dtor,
-               .init = nv41_fb_init,
-               .fini = _nouveau_fb_fini,
-       },
-       .base.memtype = nv04_fb_memtype_valid,
-       .base.ram = &nv49_ram_oclass,
-       .tile.regions = 15,
-       .tile.init = nv30_fb_tile_init,
-       .tile.comp = nv40_fb_tile_comp,
-       .tile.fini = nv20_fb_tile_fini,
-       .tile.prog = nv41_fb_tile_prog,
-}.base.base;
diff --git a/drivers/gpu/drm/nouveau/core/subdev/fb/nv4e.c b/drivers/gpu/drm/nouveau/core/subdev/fb/nv4e.c
deleted file mode 100644 (file)
index 42e64f3..0000000
+++ /dev/null
@@ -1,44 +0,0 @@
-/*
- * 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.
- *
- */
-
-#include "nv04.h"
-
-struct nouveau_oclass *
-nv4e_fb_oclass = &(struct nv04_fb_impl) {
-       .base.base.handle = NV_SUBDEV(FB, 0x4e),
-       .base.base.ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nv04_fb_ctor,
-               .dtor = _nouveau_fb_dtor,
-               .init = nv44_fb_init,
-               .fini = _nouveau_fb_fini,
-       },
-       .base.memtype = nv04_fb_memtype_valid,
-       .base.ram = &nv4e_ram_oclass,
-       .tile.regions = 12,
-       .tile.init = nv46_fb_tile_init,
-       .tile.fini = nv20_fb_tile_fini,
-       .tile.prog = nv44_fb_tile_prog,
-}.base.base;
diff --git a/drivers/gpu/drm/nouveau/core/subdev/fb/nv50.c b/drivers/gpu/drm/nouveau/core/subdev/fb/nv50.c
deleted file mode 100644 (file)
index 4150b0d..0000000
+++ /dev/null
@@ -1,316 +0,0 @@
-/*
- * Copyright 2012 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 <core/client.h>
-#include <core/enum.h>
-#include <core/engctx.h>
-#include <core/object.h>
-
-#include <subdev/bios.h>
-
-#include "nv50.h"
-
-int
-nv50_fb_memtype[0x80] = {
-       1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
-       1, 1, 1, 1, 0, 0, 0, 0, 2, 2, 2, 2, 0, 0, 0, 0,
-       1, 1, 1, 1, 1, 1, 1, 0, 2, 2, 2, 2, 2, 2, 2, 0,
-       0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
-       1, 1, 1, 1, 1, 1, 1, 2, 2, 2, 2, 2, 2, 2, 0, 0,
-       0, 0, 0, 0, 1, 1, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0,
-       1, 1, 1, 1, 1, 1, 1, 0, 1, 1, 1, 1, 2, 2, 2, 2,
-       1, 0, 2, 0, 1, 0, 2, 0, 1, 1, 2, 2, 1, 1, 0, 0
-};
-
-bool
-nv50_fb_memtype_valid(struct nouveau_fb *pfb, u32 memtype)
-{
-       return nv50_fb_memtype[(memtype & 0xff00) >> 8] != 0;
-}
-
-static const struct nouveau_enum vm_dispatch_subclients[] = {
-       { 0x00000000, "GRCTX", NULL },
-       { 0x00000001, "NOTIFY", NULL },
-       { 0x00000002, "QUERY", NULL },
-       { 0x00000003, "COND", NULL },
-       { 0x00000004, "M2M_IN", NULL },
-       { 0x00000005, "M2M_OUT", NULL },
-       { 0x00000006, "M2M_NOTIFY", NULL },
-       {}
-};
-
-static const struct nouveau_enum vm_ccache_subclients[] = {
-       { 0x00000000, "CB", NULL },
-       { 0x00000001, "TIC", NULL },
-       { 0x00000002, "TSC", NULL },
-       {}
-};
-
-static const struct nouveau_enum vm_prop_subclients[] = {
-       { 0x00000000, "RT0", NULL },
-       { 0x00000001, "RT1", NULL },
-       { 0x00000002, "RT2", NULL },
-       { 0x00000003, "RT3", NULL },
-       { 0x00000004, "RT4", NULL },
-       { 0x00000005, "RT5", NULL },
-       { 0x00000006, "RT6", NULL },
-       { 0x00000007, "RT7", NULL },
-       { 0x00000008, "ZETA", NULL },
-       { 0x00000009, "LOCAL", NULL },
-       { 0x0000000a, "GLOBAL", NULL },
-       { 0x0000000b, "STACK", NULL },
-       { 0x0000000c, "DST2D", NULL },
-       {}
-};
-
-static const struct nouveau_enum vm_pfifo_subclients[] = {
-       { 0x00000000, "PUSHBUF", NULL },
-       { 0x00000001, "SEMAPHORE", NULL },
-       {}
-};
-
-static const struct nouveau_enum vm_bar_subclients[] = {
-       { 0x00000000, "FB", NULL },
-       { 0x00000001, "IN", NULL },
-       {}
-};
-
-static const struct nouveau_enum vm_client[] = {
-       { 0x00000000, "STRMOUT", NULL },
-       { 0x00000003, "DISPATCH", vm_dispatch_subclients },
-       { 0x00000004, "PFIFO_WRITE", NULL },
-       { 0x00000005, "CCACHE", vm_ccache_subclients },
-       { 0x00000006, "PPPP", NULL },
-       { 0x00000007, "CLIPID", NULL },
-       { 0x00000008, "PFIFO_READ", NULL },
-       { 0x00000009, "VFETCH", NULL },
-       { 0x0000000a, "TEXTURE", NULL },
-       { 0x0000000b, "PROP", vm_prop_subclients },
-       { 0x0000000c, "PVP", NULL },
-       { 0x0000000d, "PBSP", NULL },
-       { 0x0000000e, "PCRYPT", NULL },
-       { 0x0000000f, "PCOUNTER", NULL },
-       { 0x00000011, "PDAEMON", NULL },
-       {}
-};
-
-static const struct nouveau_enum vm_engine[] = {
-       { 0x00000000, "PGRAPH", NULL, NVDEV_ENGINE_GR },
-       { 0x00000001, "PVP", NULL, NVDEV_ENGINE_VP },
-       { 0x00000004, "PEEPHOLE", NULL },
-       { 0x00000005, "PFIFO", vm_pfifo_subclients, NVDEV_ENGINE_FIFO },
-       { 0x00000006, "BAR", vm_bar_subclients },
-       { 0x00000008, "PPPP", NULL, NVDEV_ENGINE_PPP },
-       { 0x00000008, "PMPEG", NULL, NVDEV_ENGINE_MPEG },
-       { 0x00000009, "PBSP", NULL, NVDEV_ENGINE_BSP },
-       { 0x0000000a, "PCRYPT", NULL, NVDEV_ENGINE_CRYPT },
-       { 0x0000000b, "PCOUNTER", NULL },
-       { 0x0000000c, "SEMAPHORE_BG", NULL },
-       { 0x0000000d, "PCOPY", NULL, NVDEV_ENGINE_COPY0 },
-       { 0x0000000e, "PDAEMON", NULL },
-       {}
-};
-
-static const struct nouveau_enum vm_fault[] = {
-       { 0x00000000, "PT_NOT_PRESENT", NULL },
-       { 0x00000001, "PT_TOO_SHORT", NULL },
-       { 0x00000002, "PAGE_NOT_PRESENT", NULL },
-       { 0x00000003, "PAGE_SYSTEM_ONLY", NULL },
-       { 0x00000004, "PAGE_READ_ONLY", NULL },
-       { 0x00000006, "NULL_DMAOBJ", NULL },
-       { 0x00000007, "WRONG_MEMTYPE", NULL },
-       { 0x0000000b, "VRAM_LIMIT", NULL },
-       { 0x0000000f, "DMAOBJ_LIMIT", NULL },
-       {}
-};
-
-static void
-nv50_fb_intr(struct nouveau_subdev *subdev)
-{
-       struct nouveau_device *device = nv_device(subdev);
-       struct nouveau_engine *engine;
-       struct nv50_fb_priv *priv = (void *)subdev;
-       const struct nouveau_enum *en, *cl;
-       struct nouveau_object *engctx = NULL;
-       u32 trap[6], idx, chan;
-       u8 st0, st1, st2, st3;
-       int i;
-
-       idx = nv_rd32(priv, 0x100c90);
-       if (!(idx & 0x80000000))
-               return;
-       idx &= 0x00ffffff;
-
-       for (i = 0; i < 6; i++) {
-               nv_wr32(priv, 0x100c90, idx | i << 24);
-               trap[i] = nv_rd32(priv, 0x100c94);
-       }
-       nv_wr32(priv, 0x100c90, idx | 0x80000000);
-
-       /* decode status bits into something more useful */
-       if (device->chipset  < 0xa3 ||
-           device->chipset == 0xaa || device->chipset == 0xac) {
-               st0 = (trap[0] & 0x0000000f) >> 0;
-               st1 = (trap[0] & 0x000000f0) >> 4;
-               st2 = (trap[0] & 0x00000f00) >> 8;
-               st3 = (trap[0] & 0x0000f000) >> 12;
-       } else {
-               st0 = (trap[0] & 0x000000ff) >> 0;
-               st1 = (trap[0] & 0x0000ff00) >> 8;
-               st2 = (trap[0] & 0x00ff0000) >> 16;
-               st3 = (trap[0] & 0xff000000) >> 24;
-       }
-       chan = (trap[2] << 16) | trap[1];
-
-       en = nouveau_enum_find(vm_engine, st0);
-
-       if (en && en->data2) {
-               const struct nouveau_enum *orig_en = en;
-               while (en->name && en->value == st0 && en->data2) {
-                       engine = nouveau_engine(subdev, en->data2);
-                       if (engine) {
-                               engctx = nouveau_engctx_get(engine, chan);
-                               if (engctx)
-                                       break;
-                       }
-                       en++;
-               }
-               if (!engctx)
-                       en = orig_en;
-       }
-
-       nv_error(priv, "trapped %s at 0x%02x%04x%04x on channel 0x%08x [%s] ",
-                (trap[5] & 0x00000100) ? "read" : "write",
-                trap[5] & 0xff, trap[4] & 0xffff, trap[3] & 0xffff, chan,
-                nouveau_client_name(engctx));
-
-       nouveau_engctx_put(engctx);
-
-       if (en)
-               pr_cont("%s/", en->name);
-       else
-               pr_cont("%02x/", st0);
-
-       cl = nouveau_enum_find(vm_client, st2);
-       if (cl)
-               pr_cont("%s/", cl->name);
-       else
-               pr_cont("%02x/", st2);
-
-       if      (cl && cl->data) cl = nouveau_enum_find(cl->data, st3);
-       else if (en && en->data) cl = nouveau_enum_find(en->data, st3);
-       else                     cl = NULL;
-       if (cl)
-               pr_cont("%s", cl->name);
-       else
-               pr_cont("%02x", st3);
-
-       pr_cont(" reason: ");
-       en = nouveau_enum_find(vm_fault, st1);
-       if (en)
-               pr_cont("%s\n", en->name);
-       else
-               pr_cont("0x%08x\n", st1);
-}
-
-int
-nv50_fb_ctor(struct nouveau_object *parent, struct nouveau_object *engine,
-            struct nouveau_oclass *oclass, void *data, u32 size,
-            struct nouveau_object **pobject)
-{
-       struct nouveau_device *device = nv_device(parent);
-       struct nv50_fb_priv *priv;
-       int ret;
-
-       ret = nouveau_fb_create(parent, engine, oclass, &priv);
-       *pobject = nv_object(priv);
-       if (ret)
-               return ret;
-
-       priv->r100c08_page = alloc_page(GFP_KERNEL | __GFP_ZERO);
-       if (priv->r100c08_page) {
-               priv->r100c08 = dma_map_page(nv_device_base(device),
-                                            priv->r100c08_page, 0, PAGE_SIZE,
-                                            DMA_BIDIRECTIONAL);
-               if (dma_mapping_error(nv_device_base(device), priv->r100c08))
-                       return -EFAULT;
-       } else {
-               nv_warn(priv, "failed 0x100c08 page alloc\n");
-       }
-
-       nv_subdev(priv)->intr = nv50_fb_intr;
-       return 0;
-}
-
-void
-nv50_fb_dtor(struct nouveau_object *object)
-{
-       struct nouveau_device *device = nv_device(object);
-       struct nv50_fb_priv *priv = (void *)object;
-
-       if (priv->r100c08_page) {
-               dma_unmap_page(nv_device_base(device), priv->r100c08, PAGE_SIZE,
-                              DMA_BIDIRECTIONAL);
-               __free_page(priv->r100c08_page);
-       }
-
-       nouveau_fb_destroy(&priv->base);
-}
-
-int
-nv50_fb_init(struct nouveau_object *object)
-{
-       struct nv50_fb_impl *impl = (void *)object->oclass;
-       struct nv50_fb_priv *priv = (void *)object;
-       int ret;
-
-       ret = nouveau_fb_init(&priv->base);
-       if (ret)
-               return ret;
-
-       /* Not a clue what this is exactly.  Without pointing it at a
-        * scratch page, VRAM->GART blits with M2MF (as in DDX DFS)
-        * cause IOMMU "read from address 0" errors (rh#561267)
-        */
-       nv_wr32(priv, 0x100c08, priv->r100c08 >> 8);
-
-       /* This is needed to get meaningful information from 100c90
-        * on traps. No idea what these values mean exactly. */
-       nv_wr32(priv, 0x100c90, impl->trap);
-       return 0;
-}
-
-struct nouveau_oclass *
-nv50_fb_oclass = &(struct nv50_fb_impl) {
-       .base.base.handle = NV_SUBDEV(FB, 0x50),
-       .base.base.ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nv50_fb_ctor,
-               .dtor = nv50_fb_dtor,
-               .init = nv50_fb_init,
-               .fini = _nouveau_fb_fini,
-       },
-       .base.memtype = nv50_fb_memtype_valid,
-       .base.ram = &nv50_ram_oclass,
-       .trap = 0x000707ff,
-}.base.base;
diff --git a/drivers/gpu/drm/nouveau/core/subdev/fb/nv50.h b/drivers/gpu/drm/nouveau/core/subdev/fb/nv50.h
deleted file mode 100644 (file)
index c5e5a88..0000000
+++ /dev/null
@@ -1,33 +0,0 @@
-#ifndef __NVKM_FB_NV50_H__
-#define __NVKM_FB_NV50_H__
-
-#include "priv.h"
-
-struct nv50_fb_priv {
-       struct nouveau_fb base;
-       struct page *r100c08_page;
-       dma_addr_t r100c08;
-};
-
-int  nv50_fb_ctor(struct nouveau_object *, struct nouveau_object *,
-                 struct nouveau_oclass *, void *, u32,
-                 struct nouveau_object **);
-void nv50_fb_dtor(struct nouveau_object *);
-int  nv50_fb_init(struct nouveau_object *);
-
-struct nv50_fb_impl {
-       struct nouveau_fb_impl base;
-       u32 trap;
-};
-
-#define nv50_ram_create(p,e,o,d)                                               \
-       nv50_ram_create_((p), (e), (o), sizeof(**d), (void **)d)
-int  nv50_ram_create_(struct nouveau_object *, struct nouveau_object *,
-                     struct nouveau_oclass *, int, void **);
-int  nv50_ram_get(struct nouveau_fb *, u64 size, u32 align, u32 ncmin,
-                 u32 memtype, struct nouveau_mem **);
-void nv50_ram_put(struct nouveau_fb *, struct nouveau_mem **);
-void __nv50_ram_put(struct nouveau_fb *, struct nouveau_mem *);
-extern int nv50_fb_memtype[0x80];
-
-#endif
diff --git a/drivers/gpu/drm/nouveau/core/subdev/fb/nv84.c b/drivers/gpu/drm/nouveau/core/subdev/fb/nv84.c
deleted file mode 100644 (file)
index cf0e767..0000000
+++ /dev/null
@@ -1,39 +0,0 @@
-/*
- * Copyright 2012 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 "nv50.h"
-
-struct nouveau_oclass *
-nv84_fb_oclass = &(struct nv50_fb_impl) {
-       .base.base.handle = NV_SUBDEV(FB, 0x84),
-       .base.base.ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nv50_fb_ctor,
-               .dtor = nv50_fb_dtor,
-               .init = nv50_fb_init,
-               .fini = _nouveau_fb_fini,
-       },
-       .base.memtype = nv50_fb_memtype_valid,
-       .base.ram = &nv50_ram_oclass,
-       .trap = 0x001d07ff,
-}.base.base;
diff --git a/drivers/gpu/drm/nouveau/core/subdev/fb/nva3.c b/drivers/gpu/drm/nouveau/core/subdev/fb/nva3.c
deleted file mode 100644 (file)
index dab6e1c..0000000
+++ /dev/null
@@ -1,39 +0,0 @@
-/*
- * Copyright 2012 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 "nv50.h"
-
-struct nouveau_oclass *
-nva3_fb_oclass = &(struct nv50_fb_impl) {
-       .base.base.handle = NV_SUBDEV(FB, 0xa3),
-       .base.base.ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nv50_fb_ctor,
-               .dtor = nv50_fb_dtor,
-               .init = nv50_fb_init,
-               .fini = _nouveau_fb_fini,
-       },
-       .base.memtype = nv50_fb_memtype_valid,
-       .base.ram = &nva3_ram_oclass,
-       .trap = 0x000d0fff,
-}.base.base;
diff --git a/drivers/gpu/drm/nouveau/core/subdev/fb/nvaa.c b/drivers/gpu/drm/nouveau/core/subdev/fb/nvaa.c
deleted file mode 100644 (file)
index cba8e68..0000000
+++ /dev/null
@@ -1,39 +0,0 @@
-/*
- * Copyright 2012 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 "nv50.h"
-
-struct nouveau_oclass *
-nvaa_fb_oclass = &(struct nv50_fb_impl) {
-       .base.base.handle = NV_SUBDEV(FB, 0xaa),
-       .base.base.ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nv50_fb_ctor,
-               .dtor = nv50_fb_dtor,
-               .init = nv50_fb_init,
-               .fini = _nouveau_fb_fini,
-       },
-       .base.memtype = nv50_fb_memtype_valid,
-       .base.ram = &nvaa_ram_oclass,
-       .trap = 0x001d07ff,
-}.base.base;
diff --git a/drivers/gpu/drm/nouveau/core/subdev/fb/nvaf.c b/drivers/gpu/drm/nouveau/core/subdev/fb/nvaf.c
deleted file mode 100644 (file)
index 5423faa..0000000
+++ /dev/null
@@ -1,39 +0,0 @@
-/*
- * Copyright 2012 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 "nv50.h"
-
-struct nouveau_oclass *
-nvaf_fb_oclass = &(struct nv50_fb_impl) {
-       .base.base.handle = NV_SUBDEV(FB, 0xaf),
-       .base.base.ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nv50_fb_ctor,
-               .dtor = nv50_fb_dtor,
-               .init = nv50_fb_init,
-               .fini = _nouveau_fb_fini,
-       },
-       .base.memtype = nv50_fb_memtype_valid,
-       .base.ram = &nvaa_ram_oclass,
-       .trap = 0x089d1fff,
-}.base.base;
diff --git a/drivers/gpu/drm/nouveau/core/subdev/fb/nvc0.c b/drivers/gpu/drm/nouveau/core/subdev/fb/nvc0.c
deleted file mode 100644 (file)
index 32f28dc..0000000
+++ /dev/null
@@ -1,120 +0,0 @@
-/*
- * Copyright 2012 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 "nvc0.h"
-
-extern const u8 nvc0_pte_storage_type_map[256];
-
-bool
-nvc0_fb_memtype_valid(struct nouveau_fb *pfb, u32 tile_flags)
-{
-       u8 memtype = (tile_flags & 0x0000ff00) >> 8;
-       return likely((nvc0_pte_storage_type_map[memtype] != 0xff));
-}
-
-static void
-nvc0_fb_intr(struct nouveau_subdev *subdev)
-{
-       struct nvc0_fb_priv *priv = (void *)subdev;
-       u32 intr = nv_rd32(priv, 0x000100);
-       if (intr & 0x08000000) {
-               nv_debug(priv, "PFFB intr\n");
-               intr &= ~0x08000000;
-       }
-       if (intr & 0x00002000) {
-               nv_debug(priv, "PBFB intr\n");
-               intr &= ~0x00002000;
-       }
-}
-
-int
-nvc0_fb_init(struct nouveau_object *object)
-{
-       struct nvc0_fb_priv *priv = (void *)object;
-       int ret;
-
-       ret = nouveau_fb_init(&priv->base);
-       if (ret)
-               return ret;
-
-       if (priv->r100c10_page)
-               nv_wr32(priv, 0x100c10, priv->r100c10 >> 8);
-       nv_mask(priv, 0x100c80, 0x00000001, 0x00000000); /* 128KiB lpg */
-       return 0;
-}
-
-void
-nvc0_fb_dtor(struct nouveau_object *object)
-{
-       struct nouveau_device *device = nv_device(object);
-       struct nvc0_fb_priv *priv = (void *)object;
-
-       if (priv->r100c10_page) {
-               dma_unmap_page(nv_device_base(device), priv->r100c10, PAGE_SIZE,
-                              DMA_BIDIRECTIONAL);
-               __free_page(priv->r100c10_page);
-       }
-
-       nouveau_fb_destroy(&priv->base);
-}
-
-int
-nvc0_fb_ctor(struct nouveau_object *parent, struct nouveau_object *engine,
-            struct nouveau_oclass *oclass, void *data, u32 size,
-            struct nouveau_object **pobject)
-{
-       struct nouveau_device *device = nv_device(parent);
-       struct nvc0_fb_priv *priv;
-       int ret;
-
-       ret = nouveau_fb_create(parent, engine, oclass, &priv);
-       *pobject = nv_object(priv);
-       if (ret)
-               return ret;
-
-       priv->r100c10_page = alloc_page(GFP_KERNEL | __GFP_ZERO);
-       if (priv->r100c10_page) {
-               priv->r100c10 = dma_map_page(nv_device_base(device),
-                                            priv->r100c10_page, 0, PAGE_SIZE,
-                                            DMA_BIDIRECTIONAL);
-               if (dma_mapping_error(nv_device_base(device), priv->r100c10))
-                       return -EFAULT;
-       }
-
-       nv_subdev(priv)->intr = nvc0_fb_intr;
-       return 0;
-}
-
-struct nouveau_oclass *
-nvc0_fb_oclass = &(struct nouveau_fb_impl) {
-       .base.handle = NV_SUBDEV(FB, 0xc0),
-       .base.ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nvc0_fb_ctor,
-               .dtor = nvc0_fb_dtor,
-               .init = nvc0_fb_init,
-               .fini = _nouveau_fb_fini,
-       },
-       .memtype = nvc0_fb_memtype_valid,
-       .ram = &nvc0_ram_oclass,
-}.base;
diff --git a/drivers/gpu/drm/nouveau/core/subdev/fb/nvc0.h b/drivers/gpu/drm/nouveau/core/subdev/fb/nvc0.h
deleted file mode 100644 (file)
index 705a06d..0000000
+++ /dev/null
@@ -1,31 +0,0 @@
-#ifndef __NVKM_RAM_NVC0_H__
-#define __NVKM_RAM_NVC0_H__
-
-#include "priv.h"
-#include "nv50.h"
-
-struct nvc0_fb_priv {
-       struct nouveau_fb base;
-       struct page *r100c10_page;
-       dma_addr_t r100c10;
-};
-
-int  nvc0_fb_ctor(struct nouveau_object *, struct nouveau_object *,
-                 struct nouveau_oclass *, void *, u32,
-                 struct nouveau_object **);
-void nvc0_fb_dtor(struct nouveau_object *);
-int  nvc0_fb_init(struct nouveau_object *);
-bool nvc0_fb_memtype_valid(struct nouveau_fb *, u32);
-
-
-#define nvc0_ram_create(p,e,o,m,d)                                             \
-       nvc0_ram_create_((p), (e), (o), (m), sizeof(**d), (void **)d)
-int  nvc0_ram_create_(struct nouveau_object *, struct nouveau_object *,
-                     struct nouveau_oclass *, u32, int, void **);
-int  nvc0_ram_get(struct nouveau_fb *, u64, u32, u32, u32,
-                 struct nouveau_mem **);
-void nvc0_ram_put(struct nouveau_fb *, struct nouveau_mem **);
-
-int  nve0_ram_init(struct nouveau_object*);
-
-#endif
diff --git a/drivers/gpu/drm/nouveau/core/subdev/fb/nve0.c b/drivers/gpu/drm/nouveau/core/subdev/fb/nve0.c
deleted file mode 100644 (file)
index 595db50..0000000
+++ /dev/null
@@ -1,38 +0,0 @@
-/*
- * Copyright 2012 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 "nvc0.h"
-
-struct nouveau_oclass *
-nve0_fb_oclass = &(struct nouveau_fb_impl) {
-       .base.handle = NV_SUBDEV(FB, 0xe0),
-       .base.ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nvc0_fb_ctor,
-               .dtor = nvc0_fb_dtor,
-               .init = nvc0_fb_init,
-               .fini = _nouveau_fb_fini,
-       },
-       .memtype = nvc0_fb_memtype_valid,
-       .ram = &nve0_ram_oclass,
-}.base;
diff --git a/drivers/gpu/drm/nouveau/core/subdev/fb/priv.h b/drivers/gpu/drm/nouveau/core/subdev/fb/priv.h
deleted file mode 100644 (file)
index 283863f..0000000
+++ /dev/null
@@ -1,76 +0,0 @@
-#ifndef __NVKM_FB_PRIV_H__
-#define __NVKM_FB_PRIV_H__
-
-#include <subdev/fb.h>
-
-#define nouveau_ram_create(p,e,o,d)                                            \
-       nouveau_object_create_((p), (e), (o), 0, sizeof(**d), (void **)d)
-#define nouveau_ram_destroy(p)                                                 \
-       nouveau_object_destroy(&(p)->base)
-#define nouveau_ram_init(p)                                                    \
-       nouveau_object_init(&(p)->base)
-#define nouveau_ram_fini(p,s)                                                  \
-       nouveau_object_fini(&(p)->base, (s))
-
-#define nouveau_ram_create_(p,e,o,s,d)                                         \
-       nouveau_object_create_((p), (e), (o), 0, (s), (void **)d)
-#define _nouveau_ram_dtor nouveau_object_destroy
-#define _nouveau_ram_init nouveau_object_init
-#define _nouveau_ram_fini nouveau_object_fini
-
-extern struct nouveau_oclass nv04_ram_oclass;
-extern struct nouveau_oclass nv10_ram_oclass;
-extern struct nouveau_oclass nv1a_ram_oclass;
-extern struct nouveau_oclass nv20_ram_oclass;
-extern struct nouveau_oclass nv40_ram_oclass;
-extern struct nouveau_oclass nv41_ram_oclass;
-extern struct nouveau_oclass nv44_ram_oclass;
-extern struct nouveau_oclass nv49_ram_oclass;
-extern struct nouveau_oclass nv4e_ram_oclass;
-extern struct nouveau_oclass nv50_ram_oclass;
-extern struct nouveau_oclass nva3_ram_oclass;
-extern struct nouveau_oclass nvaa_ram_oclass;
-extern struct nouveau_oclass nvc0_ram_oclass;
-extern struct nouveau_oclass nve0_ram_oclass;
-extern struct nouveau_oclass gk20a_ram_oclass;
-extern struct nouveau_oclass gm107_ram_oclass;
-
-int nouveau_sddr2_calc(struct nouveau_ram *ram);
-int nouveau_sddr3_calc(struct nouveau_ram *ram);
-int nouveau_gddr3_calc(struct nouveau_ram *ram);
-int nouveau_gddr5_calc(struct nouveau_ram *ram, bool nuts);
-
-#define nouveau_fb_create(p,e,c,d)                                             \
-       nouveau_fb_create_((p), (e), (c), sizeof(**d), (void **)d)
-#define nouveau_fb_destroy(p) ({                                               \
-       struct nouveau_fb *pfb = (p);                                          \
-       _nouveau_fb_dtor(nv_object(pfb));                                      \
-})
-#define nouveau_fb_init(p) ({                                                  \
-       struct nouveau_fb *pfb = (p);                                          \
-       _nouveau_fb_init(nv_object(pfb));                                      \
-})
-#define nouveau_fb_fini(p,s) ({                                                \
-       struct nouveau_fb *pfb = (p);                                          \
-       _nouveau_fb_fini(nv_object(pfb), (s));                                 \
-})
-
-int nouveau_fb_create_(struct nouveau_object *, struct nouveau_object *,
-                      struct nouveau_oclass *, int, void **);
-void _nouveau_fb_dtor(struct nouveau_object *);
-int  _nouveau_fb_init(struct nouveau_object *);
-int  _nouveau_fb_fini(struct nouveau_object *, bool);
-
-struct nouveau_fb_impl {
-       struct nouveau_oclass base;
-       struct nouveau_oclass *ram;
-       bool (*memtype)(struct nouveau_fb *, u32);
-};
-
-bool nv04_fb_memtype_valid(struct nouveau_fb *, u32 memtype);
-bool nv50_fb_memtype_valid(struct nouveau_fb *, u32 memtype);
-
-struct nouveau_bios;
-int  nouveau_fb_bios_memtype(struct nouveau_bios *);
-
-#endif
diff --git a/drivers/gpu/drm/nouveau/core/subdev/fb/ramfuc.h b/drivers/gpu/drm/nouveau/core/subdev/fb/ramfuc.h
deleted file mode 100644 (file)
index 0ac7256..0000000
+++ /dev/null
@@ -1,184 +0,0 @@
-#ifndef __NVKM_FBRAM_FUC_H__
-#define __NVKM_FBRAM_FUC_H__
-
-#include <subdev/pwr.h>
-
-struct ramfuc {
-       struct nouveau_memx *memx;
-       struct nouveau_fb *pfb;
-       int sequence;
-};
-
-struct ramfuc_reg {
-       int sequence;
-       bool force;
-       u32 addr;
-       u32 stride; /* in bytes */
-       u32 mask;
-       u32 data;
-};
-
-static inline struct ramfuc_reg
-ramfuc_stride(u32 addr, u32 stride, u32 mask)
-{
-       return (struct ramfuc_reg) {
-               .sequence = 0,
-               .addr = addr,
-               .stride = stride,
-               .mask = mask,
-               .data = 0xdeadbeef,
-       };
-}
-
-static inline struct ramfuc_reg
-ramfuc_reg2(u32 addr1, u32 addr2)
-{
-       return (struct ramfuc_reg) {
-               .sequence = 0,
-               .addr = addr1,
-               .stride = addr2 - addr1,
-               .mask = 0x3,
-               .data = 0xdeadbeef,
-       };
-}
-
-static noinline struct ramfuc_reg
-ramfuc_reg(u32 addr)
-{
-       return (struct ramfuc_reg) {
-               .sequence = 0,
-               .addr = addr,
-               .stride = 0,
-               .mask = 0x1,
-               .data = 0xdeadbeef,
-       };
-}
-
-static inline int
-ramfuc_init(struct ramfuc *ram, struct nouveau_fb *pfb)
-{
-       struct nouveau_pwr *ppwr = nouveau_pwr(pfb);
-       int ret;
-
-       ret = nouveau_memx_init(ppwr, &ram->memx);
-       if (ret)
-               return ret;
-
-       ram->sequence++;
-       ram->pfb = pfb;
-       return 0;
-}
-
-static inline int
-ramfuc_exec(struct ramfuc *ram, bool exec)
-{
-       int ret = 0;
-       if (ram->pfb) {
-               ret = nouveau_memx_fini(&ram->memx, exec);
-               ram->pfb = NULL;
-       }
-       return ret;
-}
-
-static inline u32
-ramfuc_rd32(struct ramfuc *ram, struct ramfuc_reg *reg)
-{
-       if (reg->sequence != ram->sequence)
-               reg->data = nv_rd32(ram->pfb, reg->addr);
-       return reg->data;
-}
-
-static inline void
-ramfuc_wr32(struct ramfuc *ram, struct ramfuc_reg *reg, u32 data)
-{
-       unsigned int mask, off = 0;
-
-       reg->sequence = ram->sequence;
-       reg->data = data;
-
-       for (mask = reg->mask; mask > 0; mask = (mask & ~1) >> 1) {
-               if (mask & 1) {
-                       nouveau_memx_wr32(ram->memx, reg->addr+off, reg->data);
-               }
-
-               off += reg->stride;
-       }
-}
-
-static inline void
-ramfuc_nuke(struct ramfuc *ram, struct ramfuc_reg *reg)
-{
-       reg->force = true;
-}
-
-static inline u32
-ramfuc_mask(struct ramfuc *ram, struct ramfuc_reg *reg, u32 mask, u32 data)
-{
-       u32 temp = ramfuc_rd32(ram, reg);
-       if (temp != ((temp & ~mask) | data) || reg->force) {
-               ramfuc_wr32(ram, reg, (temp & ~mask) | data);
-               reg->force = false;
-       }
-       return temp;
-}
-
-static inline void
-ramfuc_wait(struct ramfuc *ram, u32 addr, u32 mask, u32 data, u32 nsec)
-{
-       nouveau_memx_wait(ram->memx, addr, mask, data, nsec);
-}
-
-static inline void
-ramfuc_nsec(struct ramfuc *ram, u32 nsec)
-{
-       nouveau_memx_nsec(ram->memx, nsec);
-}
-
-static inline void
-ramfuc_wait_vblank(struct ramfuc *ram)
-{
-       nouveau_memx_wait_vblank(ram->memx);
-}
-
-static inline void
-ramfuc_train(struct ramfuc *ram)
-{
-       nouveau_memx_train(ram->memx);
-}
-
-static inline int
-ramfuc_train_result(struct nouveau_fb *pfb, u32 *result, u32 rsize)
-{
-       struct nouveau_pwr *ppwr = nouveau_pwr(pfb);
-
-       return nouveau_memx_train_result(ppwr, result, rsize);
-}
-
-static inline void
-ramfuc_block(struct ramfuc *ram)
-{
-       nouveau_memx_block(ram->memx);
-}
-
-static inline void
-ramfuc_unblock(struct ramfuc *ram)
-{
-       nouveau_memx_unblock(ram->memx);
-}
-
-#define ram_init(s,p)        ramfuc_init(&(s)->base, (p))
-#define ram_exec(s,e)        ramfuc_exec(&(s)->base, (e))
-#define ram_have(s,r)        ((s)->r_##r.addr != 0x000000)
-#define ram_rd32(s,r)        ramfuc_rd32(&(s)->base, &(s)->r_##r)
-#define ram_wr32(s,r,d)      ramfuc_wr32(&(s)->base, &(s)->r_##r, (d))
-#define ram_nuke(s,r)        ramfuc_nuke(&(s)->base, &(s)->r_##r)
-#define ram_mask(s,r,m,d)    ramfuc_mask(&(s)->base, &(s)->r_##r, (m), (d))
-#define ram_wait(s,r,m,d,n)  ramfuc_wait(&(s)->base, (r), (m), (d), (n))
-#define ram_nsec(s,n)        ramfuc_nsec(&(s)->base, (n))
-#define ram_wait_vblank(s)   ramfuc_wait_vblank(&(s)->base)
-#define ram_train(s)         ramfuc_train(&(s)->base)
-#define ram_train_result(s,r,l) ramfuc_train_result((s), (r), (l))
-#define ram_block(s)         ramfuc_block(&(s)->base)
-#define ram_unblock(s)       ramfuc_unblock(&(s)->base)
-
-#endif
diff --git a/drivers/gpu/drm/nouveau/core/subdev/fb/ramgk20a.c b/drivers/gpu/drm/nouveau/core/subdev/fb/ramgk20a.c
deleted file mode 100644 (file)
index 4d77d75..0000000
+++ /dev/null
@@ -1,152 +0,0 @@
-/*
- * Copyright (c) 2014, NVIDIA CORPORATION. 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 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 "priv.h"
-
-#include <subdev/fb.h>
-
-struct gk20a_mem {
-       struct nouveau_mem base;
-       void *cpuaddr;
-       dma_addr_t handle;
-};
-#define to_gk20a_mem(m) container_of(m, struct gk20a_mem, base)
-
-static void
-gk20a_ram_put(struct nouveau_fb *pfb, struct nouveau_mem **pmem)
-{
-       struct device *dev = nv_device_base(nv_device(pfb));
-       struct gk20a_mem *mem = to_gk20a_mem(*pmem);
-
-       *pmem = NULL;
-       if (unlikely(mem == NULL))
-               return;
-
-       if (likely(mem->cpuaddr))
-               dma_free_coherent(dev, mem->base.size << PAGE_SHIFT,
-                                 mem->cpuaddr, mem->handle);
-
-       kfree(mem->base.pages);
-       kfree(mem);
-}
-
-static int
-gk20a_ram_get(struct nouveau_fb *pfb, u64 size, u32 align, u32 ncmin,
-            u32 memtype, struct nouveau_mem **pmem)
-{
-       struct device *dev = nv_device_base(nv_device(pfb));
-       struct gk20a_mem *mem;
-       u32 type = memtype & 0xff;
-       u32 npages, order;
-       int i;
-
-       nv_debug(pfb, "%s: size: %llx align: %x, ncmin: %x\n", __func__, size,
-                align, ncmin);
-
-       npages = size >> PAGE_SHIFT;
-       if (npages == 0)
-               npages = 1;
-
-       if (align == 0)
-               align = PAGE_SIZE;
-       align >>= PAGE_SHIFT;
-
-       /* round alignment to the next power of 2, if needed */
-       order = fls(align);
-       if ((align & (align - 1)) == 0)
-               order--;
-       align = BIT(order);
-
-       /* ensure returned address is correctly aligned */
-       npages = max(align, npages);
-
-       mem = kzalloc(sizeof(*mem), GFP_KERNEL);
-       if (!mem)
-               return -ENOMEM;
-
-       mem->base.size = npages;
-       mem->base.memtype = type;
-
-       mem->base.pages = kzalloc(sizeof(dma_addr_t) * npages, GFP_KERNEL);
-       if (!mem->base.pages) {
-               kfree(mem);
-               return -ENOMEM;
-       }
-
-       *pmem = &mem->base;
-
-       mem->cpuaddr = dma_alloc_coherent(dev, npages << PAGE_SHIFT,
-                                         &mem->handle, GFP_KERNEL);
-       if (!mem->cpuaddr) {
-               nv_error(pfb, "%s: cannot allocate memory!\n", __func__);
-               gk20a_ram_put(pfb, pmem);
-               return -ENOMEM;
-       }
-
-       align <<= PAGE_SHIFT;
-
-       /* alignment check */
-       if (unlikely(mem->handle & (align - 1)))
-               nv_warn(pfb, "memory not aligned as requested: %pad (0x%x)\n",
-                       &mem->handle, align);
-
-       nv_debug(pfb, "alloc size: 0x%x, align: 0x%x, paddr: %pad, vaddr: %p\n",
-                npages << PAGE_SHIFT, align, &mem->handle, mem->cpuaddr);
-
-       for (i = 0; i < npages; i++)
-               mem->base.pages[i] = mem->handle + (PAGE_SIZE * i);
-
-       mem->base.offset = (u64)mem->base.pages[0];
-
-       return 0;
-}
-
-static int
-gk20a_ram_ctor(struct nouveau_object *parent, struct nouveau_object *engine,
-             struct nouveau_oclass *oclass, void *data, u32 datasize,
-             struct nouveau_object **pobject)
-{
-       struct nouveau_ram *ram;
-       int ret;
-
-       ret = nouveau_ram_create(parent, engine, oclass, &ram);
-       *pobject = nv_object(ram);
-       if (ret)
-               return ret;
-       ram->type = NV_MEM_TYPE_STOLEN;
-       ram->size = get_num_physpages() << PAGE_SHIFT;
-
-       ram->get = gk20a_ram_get;
-       ram->put = gk20a_ram_put;
-
-       return 0;
-}
-
-struct nouveau_oclass
-gk20a_ram_oclass = {
-       .ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = gk20a_ram_ctor,
-               .dtor = _nouveau_ram_dtor,
-               .init = _nouveau_ram_init,
-               .fini = _nouveau_ram_fini,
-       },
-};
diff --git a/drivers/gpu/drm/nouveau/core/subdev/fb/ramgm107.c b/drivers/gpu/drm/nouveau/core/subdev/fb/ramgm107.c
deleted file mode 100644 (file)
index 4c63635..0000000
+++ /dev/null
@@ -1,56 +0,0 @@
-/*
- * Copyright 2013 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 "nvc0.h"
-
-struct gm107_ram {
-       struct nouveau_ram base;
-};
-
-static int
-gm107_ram_ctor(struct nouveau_object *parent, struct nouveau_object *engine,
-              struct nouveau_oclass *oclass, void *data, u32 size,
-              struct nouveau_object **pobject)
-{
-       struct gm107_ram *ram;
-       int ret;
-
-       ret = nvc0_ram_create(parent, engine, oclass, 0x021c14, &ram);
-       *pobject = nv_object(ram);
-       if (ret)
-               return ret;
-
-       return 0;
-}
-
-struct nouveau_oclass
-gm107_ram_oclass = {
-       .handle = 0,
-       .ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = gm107_ram_ctor,
-               .dtor = _nouveau_ram_dtor,
-               .init = nve0_ram_init,
-               .fini = _nouveau_ram_fini,
-       }
-};
diff --git a/drivers/gpu/drm/nouveau/core/subdev/fb/ramnv04.c b/drivers/gpu/drm/nouveau/core/subdev/fb/ramnv04.c
deleted file mode 100644 (file)
index 1972268..0000000
+++ /dev/null
@@ -1,80 +0,0 @@
-/*
- * Copyright 2013 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 <subdev/fb/regsnv04.h>
-
-#include "priv.h"
-
-static int
-nv04_ram_create(struct nouveau_object *parent, struct nouveau_object *engine,
-               struct nouveau_oclass *oclass, void *data, u32 size,
-               struct nouveau_object **pobject)
-{
-       struct nouveau_fb *pfb = nouveau_fb(parent);
-       struct nouveau_ram *ram;
-       u32 boot0 = nv_rd32(pfb, NV04_PFB_BOOT_0);
-       int ret;
-
-       ret = nouveau_ram_create(parent, engine, oclass, &ram);
-       *pobject = nv_object(ram);
-       if (ret)
-               return ret;
-
-       if (boot0 & 0x00000100) {
-               ram->size  = ((boot0 >> 12) & 0xf) * 2 + 2;
-               ram->size *= 1024 * 1024;
-       } else {
-               switch (boot0 & NV04_PFB_BOOT_0_RAM_AMOUNT) {
-               case NV04_PFB_BOOT_0_RAM_AMOUNT_32MB:
-                       ram->size = 32 * 1024 * 1024;
-                       break;
-               case NV04_PFB_BOOT_0_RAM_AMOUNT_16MB:
-                       ram->size = 16 * 1024 * 1024;
-                       break;
-               case NV04_PFB_BOOT_0_RAM_AMOUNT_8MB:
-                       ram->size = 8 * 1024 * 1024;
-                       break;
-               case NV04_PFB_BOOT_0_RAM_AMOUNT_4MB:
-                       ram->size = 4 * 1024 * 1024;
-                       break;
-               }
-       }
-
-       if ((boot0 & 0x00000038) <= 0x10)
-               ram->type = NV_MEM_TYPE_SGRAM;
-       else
-               ram->type = NV_MEM_TYPE_SDRAM;
-       return 0;
-}
-
-struct nouveau_oclass
-nv04_ram_oclass = {
-       .handle = 0,
-       .ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nv04_ram_create,
-               .dtor = _nouveau_ram_dtor,
-               .init = _nouveau_ram_init,
-               .fini = _nouveau_ram_fini,
-       }
-};
diff --git a/drivers/gpu/drm/nouveau/core/subdev/fb/ramnv10.c b/drivers/gpu/drm/nouveau/core/subdev/fb/ramnv10.c
deleted file mode 100644 (file)
index 8311f37..0000000
+++ /dev/null
@@ -1,61 +0,0 @@
-/*
- * Copyright 2013 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 "priv.h"
-
-static int
-nv10_ram_create(struct nouveau_object *parent, struct nouveau_object *engine,
-               struct nouveau_oclass *oclass, void *data, u32 size,
-               struct nouveau_object **pobject)
-{
-       struct nouveau_fb *pfb = nouveau_fb(parent);
-       struct nouveau_ram *ram;
-       u32 cfg0 = nv_rd32(pfb, 0x100200);
-       int ret;
-
-       ret = nouveau_ram_create(parent, engine, oclass, &ram);
-       *pobject = nv_object(ram);
-       if (ret)
-               return ret;
-
-       if (cfg0 & 0x00000001)
-               ram->type = NV_MEM_TYPE_DDR1;
-       else
-               ram->type = NV_MEM_TYPE_SDRAM;
-
-       ram->size = nv_rd32(pfb, 0x10020c) & 0xff000000;
-       return 0;
-}
-
-
-struct nouveau_oclass
-nv10_ram_oclass = {
-       .handle = 0,
-       .ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nv10_ram_create,
-               .dtor = _nouveau_ram_dtor,
-               .init = _nouveau_ram_init,
-               .fini = _nouveau_ram_fini,
-       }
-};
diff --git a/drivers/gpu/drm/nouveau/core/subdev/fb/ramnv1a.c b/drivers/gpu/drm/nouveau/core/subdev/fb/ramnv1a.c
deleted file mode 100644 (file)
index d0caddf..0000000
+++ /dev/null
@@ -1,71 +0,0 @@
-/*
- * Copyright 2013 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 "priv.h"
-
-static int
-nv1a_ram_create(struct nouveau_object *parent, struct nouveau_object *engine,
-               struct nouveau_oclass *oclass, void *data, u32 size,
-               struct nouveau_object **pobject)
-{
-       struct nouveau_fb *pfb = nouveau_fb(parent);
-       struct nouveau_ram *ram;
-       struct pci_dev *bridge;
-       u32 mem, mib;
-       int ret;
-
-       bridge = pci_get_bus_and_slot(0, PCI_DEVFN(0, 1));
-       if (!bridge) {
-               nv_fatal(pfb, "no bridge device\n");
-               return -ENODEV;
-       }
-
-       ret = nouveau_ram_create(parent, engine, oclass, &ram);
-       *pobject = nv_object(ram);
-       if (ret)
-               return ret;
-
-       if (nv_device(pfb)->chipset == 0x1a) {
-               pci_read_config_dword(bridge, 0x7c, &mem);
-               mib = ((mem >> 6) & 31) + 1;
-       } else {
-               pci_read_config_dword(bridge, 0x84, &mem);
-               mib = ((mem >> 4) & 127) + 1;
-       }
-
-       ram->type = NV_MEM_TYPE_STOLEN;
-       ram->size = mib * 1024 * 1024;
-       return 0;
-}
-
-struct nouveau_oclass
-nv1a_ram_oclass = {
-       .handle = 0,
-       .ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nv1a_ram_create,
-               .dtor = _nouveau_ram_dtor,
-               .init = _nouveau_ram_init,
-               .fini = _nouveau_ram_fini,
-       }
-};
diff --git a/drivers/gpu/drm/nouveau/core/subdev/fb/ramnv20.c b/drivers/gpu/drm/nouveau/core/subdev/fb/ramnv20.c
deleted file mode 100644 (file)
index fdc11bb..0000000
+++ /dev/null
@@ -1,63 +0,0 @@
-/*
- * Copyright 2013 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 "priv.h"
-
-static int
-nv20_ram_create(struct nouveau_object *parent, struct nouveau_object *engine,
-               struct nouveau_oclass *oclass, void *data, u32 size,
-               struct nouveau_object **pobject)
-{
-       struct nouveau_fb *pfb = nouveau_fb(parent);
-       struct nouveau_ram *ram;
-       u32 pbus1218 = nv_rd32(pfb, 0x001218);
-       int ret;
-
-       ret = nouveau_ram_create(parent, engine, oclass, &ram);
-       *pobject = nv_object(ram);
-       if (ret)
-               return ret;
-
-       switch (pbus1218 & 0x00000300) {
-       case 0x00000000: ram->type = NV_MEM_TYPE_SDRAM; break;
-       case 0x00000100: ram->type = NV_MEM_TYPE_DDR1; break;
-       case 0x00000200: ram->type = NV_MEM_TYPE_GDDR3; break;
-       case 0x00000300: ram->type = NV_MEM_TYPE_GDDR2; break;
-       }
-       ram->size  = (nv_rd32(pfb, 0x10020c) & 0xff000000);
-       ram->parts = (nv_rd32(pfb, 0x100200) & 0x00000003) + 1;
-       ram->tags  = nv_rd32(pfb, 0x100320);
-       return 0;
-}
-
-struct nouveau_oclass
-nv20_ram_oclass = {
-       .handle = 0,
-       .ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nv20_ram_create,
-               .dtor = _nouveau_ram_dtor,
-               .init = _nouveau_ram_init,
-               .fini = _nouveau_ram_fini,
-       }
-};
diff --git a/drivers/gpu/drm/nouveau/core/subdev/fb/ramnv40.c b/drivers/gpu/drm/nouveau/core/subdev/fb/ramnv40.c
deleted file mode 100644 (file)
index 7648beb..0000000
+++ /dev/null
@@ -1,215 +0,0 @@
-/*
- * Copyright 2013 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 <subdev/bios.h>
-#include <subdev/bios/bit.h>
-#include <subdev/bios/pll.h>
-#include <subdev/bios/init.h>
-#include <subdev/clock.h>
-#include <subdev/clock/pll.h>
-#include <subdev/timer.h>
-
-#include <engine/fifo.h>
-
-#include "nv40.h"
-
-int
-nv40_ram_calc(struct nouveau_fb *pfb, u32 freq)
-{
-       struct nouveau_bios *bios = nouveau_bios(pfb);
-       struct nv40_ram *ram = (void *)pfb->ram;
-       struct nvbios_pll pll;
-       int N1, M1, N2, M2;
-       int log2P, ret;
-
-       ret = nvbios_pll_parse(bios, 0x04, &pll);
-       if (ret) {
-               nv_error(pfb, "mclk pll data not found\n");
-               return ret;
-       }
-
-       ret = nv04_pll_calc(nv_subdev(pfb), &pll, freq,
-                           &N1, &M1, &N2, &M2, &log2P);
-       if (ret < 0)
-               return ret;
-
-       ram->ctrl  = 0x80000000 | (log2P << 16);
-       ram->ctrl |= min(pll.bias_p + log2P, (int)pll.max_p) << 20;
-       if (N2 == M2) {
-               ram->ctrl |= 0x00000100;
-               ram->coef  = (N1 << 8) | M1;
-       } else {
-               ram->ctrl |= 0x40000000;
-               ram->coef  = (N2 << 24) | (M2 << 16) | (N1 << 8) | M1;
-       }
-
-       return 0;
-}
-
-int
-nv40_ram_prog(struct nouveau_fb *pfb)
-{
-       struct nouveau_bios *bios = nouveau_bios(pfb);
-       struct nv40_ram *ram = (void *)pfb->ram;
-       struct bit_entry M;
-       u32 crtc_mask = 0;
-       u8  sr1[2];
-       int i;
-
-       /* determine which CRTCs are active, fetch VGA_SR1 for each */
-       for (i = 0; i < 2; i++) {
-               u32 vbl = nv_rd32(pfb, 0x600808 + (i * 0x2000));
-               u32 cnt = 0;
-               do {
-                       if (vbl != nv_rd32(pfb, 0x600808 + (i * 0x2000))) {
-                               nv_wr08(pfb, 0x0c03c4 + (i * 0x2000), 0x01);
-                               sr1[i] = nv_rd08(pfb, 0x0c03c5 + (i * 0x2000));
-                               if (!(sr1[i] & 0x20))
-                                       crtc_mask |= (1 << i);
-                               break;
-                       }
-                       udelay(1);
-               } while (cnt++ < 32);
-       }
-
-       /* wait for vblank start on active crtcs, disable memory access */
-       for (i = 0; i < 2; i++) {
-               if (!(crtc_mask & (1 << i)))
-                       continue;
-               nv_wait(pfb, 0x600808 + (i * 0x2000), 0x00010000, 0x00000000);
-               nv_wait(pfb, 0x600808 + (i * 0x2000), 0x00010000, 0x00010000);
-               nv_wr08(pfb, 0x0c03c4 + (i * 0x2000), 0x01);
-               nv_wr08(pfb, 0x0c03c5 + (i * 0x2000), sr1[i] | 0x20);
-       }
-
-       /* prepare ram for reclocking */
-       nv_wr32(pfb, 0x1002d4, 0x00000001); /* precharge */
-       nv_wr32(pfb, 0x1002d0, 0x00000001); /* refresh */
-       nv_wr32(pfb, 0x1002d0, 0x00000001); /* refresh */
-       nv_mask(pfb, 0x100210, 0x80000000, 0x00000000); /* no auto refresh */
-       nv_wr32(pfb, 0x1002dc, 0x00000001); /* enable self-refresh */
-
-       /* change the PLL of each memory partition */
-       nv_mask(pfb, 0x00c040, 0x0000c000, 0x00000000);
-       switch (nv_device(pfb)->chipset) {
-       case 0x40:
-       case 0x45:
-       case 0x41:
-       case 0x42:
-       case 0x47:
-               nv_mask(pfb, 0x004044, 0xc0771100, ram->ctrl);
-               nv_mask(pfb, 0x00402c, 0xc0771100, ram->ctrl);
-               nv_wr32(pfb, 0x004048, ram->coef);
-               nv_wr32(pfb, 0x004030, ram->coef);
-       case 0x43:
-       case 0x49:
-       case 0x4b:
-               nv_mask(pfb, 0x004038, 0xc0771100, ram->ctrl);
-               nv_wr32(pfb, 0x00403c, ram->coef);
-       default:
-               nv_mask(pfb, 0x004020, 0xc0771100, ram->ctrl);
-               nv_wr32(pfb, 0x004024, ram->coef);
-               break;
-       }
-       udelay(100);
-       nv_mask(pfb, 0x00c040, 0x0000c000, 0x0000c000);
-
-       /* re-enable normal operation of memory controller */
-       nv_wr32(pfb, 0x1002dc, 0x00000000);
-       nv_mask(pfb, 0x100210, 0x80000000, 0x80000000);
-       udelay(100);
-
-       /* execute memory reset script from vbios */
-       if (!bit_entry(bios, 'M', &M)) {
-               struct nvbios_init init = {
-                       .subdev = nv_subdev(pfb),
-                       .bios = bios,
-                       .offset = nv_ro16(bios, M.offset + 0x00),
-                       .execute = 1,
-               };
-
-               nvbios_exec(&init);
-       }
-
-       /* make sure we're in vblank (hopefully the same one as before), and
-        * then re-enable crtc memory access
-        */
-       for (i = 0; i < 2; i++) {
-               if (!(crtc_mask & (1 << i)))
-                       continue;
-               nv_wait(pfb, 0x600808 + (i * 0x2000), 0x00010000, 0x00010000);
-               nv_wr08(pfb, 0x0c03c4 + (i * 0x2000), 0x01);
-               nv_wr08(pfb, 0x0c03c5 + (i * 0x2000), sr1[i]);
-       }
-
-       return 0;
-}
-
-void
-nv40_ram_tidy(struct nouveau_fb *pfb)
-{
-}
-
-static int
-nv40_ram_create(struct nouveau_object *parent, struct nouveau_object *engine,
-               struct nouveau_oclass *oclass, void *data, u32 size,
-               struct nouveau_object **pobject)
-{
-       struct nouveau_fb *pfb = nouveau_fb(parent);
-       struct nv40_ram *ram;
-       u32 pbus1218 = nv_rd32(pfb, 0x001218);
-       int ret;
-
-       ret = nouveau_ram_create(parent, engine, oclass, &ram);
-       *pobject = nv_object(ram);
-       if (ret)
-               return ret;
-
-       switch (pbus1218 & 0x00000300) {
-       case 0x00000000: ram->base.type = NV_MEM_TYPE_SDRAM; break;
-       case 0x00000100: ram->base.type = NV_MEM_TYPE_DDR1; break;
-       case 0x00000200: ram->base.type = NV_MEM_TYPE_GDDR3; break;
-       case 0x00000300: ram->base.type = NV_MEM_TYPE_DDR2; break;
-       }
-
-       ram->base.size  =  nv_rd32(pfb, 0x10020c) & 0xff000000;
-       ram->base.parts = (nv_rd32(pfb, 0x100200) & 0x00000003) + 1;
-       ram->base.tags  =  nv_rd32(pfb, 0x100320);
-       ram->base.calc = nv40_ram_calc;
-       ram->base.prog = nv40_ram_prog;
-       ram->base.tidy = nv40_ram_tidy;
-       return 0;
-}
-
-
-struct nouveau_oclass
-nv40_ram_oclass = {
-       .handle = 0,
-       .ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nv40_ram_create,
-               .dtor = _nouveau_ram_dtor,
-               .init = _nouveau_ram_init,
-               .fini = _nouveau_ram_fini,
-       }
-};
diff --git a/drivers/gpu/drm/nouveau/core/subdev/fb/ramnv41.c b/drivers/gpu/drm/nouveau/core/subdev/fb/ramnv41.c
deleted file mode 100644 (file)
index d64498a..0000000
+++ /dev/null
@@ -1,67 +0,0 @@
-/*
- * Copyright 2013 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 "nv40.h"
-
-static int
-nv41_ram_create(struct nouveau_object *parent, struct nouveau_object *engine,
-               struct nouveau_oclass *oclass, void *data, u32 size,
-               struct nouveau_object **pobject)
-{
-       struct nouveau_fb *pfb = nouveau_fb(parent);
-       struct nv40_ram *ram;
-       u32 pfb474 = nv_rd32(pfb, 0x100474);
-       int ret;
-
-       ret = nouveau_ram_create(parent, engine, oclass, &ram);
-       *pobject = nv_object(ram);
-       if (ret)
-               return ret;
-
-       if (pfb474 & 0x00000004)
-               ram->base.type = NV_MEM_TYPE_GDDR3;
-       if (pfb474 & 0x00000002)
-               ram->base.type = NV_MEM_TYPE_DDR2;
-       if (pfb474 & 0x00000001)
-               ram->base.type = NV_MEM_TYPE_DDR1;
-
-       ram->base.size  =  nv_rd32(pfb, 0x10020c) & 0xff000000;
-       ram->base.parts = (nv_rd32(pfb, 0x100200) & 0x00000003) + 1;
-       ram->base.tags  =  nv_rd32(pfb, 0x100320);
-       ram->base.calc = nv40_ram_calc;
-       ram->base.prog = nv40_ram_prog;
-       ram->base.tidy = nv40_ram_tidy;
-       return 0;
-}
-
-struct nouveau_oclass
-nv41_ram_oclass = {
-       .handle = 0,
-       .ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nv41_ram_create,
-               .dtor = _nouveau_ram_dtor,
-               .init = _nouveau_ram_init,
-               .fini = _nouveau_ram_fini,
-       }
-};
diff --git a/drivers/gpu/drm/nouveau/core/subdev/fb/ramnv44.c b/drivers/gpu/drm/nouveau/core/subdev/fb/ramnv44.c
deleted file mode 100644 (file)
index 089acac..0000000
+++ /dev/null
@@ -1,65 +0,0 @@
-/*
- * Copyright 2013 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 "nv40.h"
-
-static int
-nv44_ram_create(struct nouveau_object *parent, struct nouveau_object *engine,
-               struct nouveau_oclass *oclass, void *data, u32 size,
-               struct nouveau_object **pobject)
-{
-       struct nouveau_fb *pfb = nouveau_fb(parent);
-       struct nv40_ram *ram;
-       u32 pfb474 = nv_rd32(pfb, 0x100474);
-       int ret;
-
-       ret = nouveau_ram_create(parent, engine, oclass, &ram);
-       *pobject = nv_object(ram);
-       if (ret)
-               return ret;
-
-       if (pfb474 & 0x00000004)
-               ram->base.type = NV_MEM_TYPE_GDDR3;
-       if (pfb474 & 0x00000002)
-               ram->base.type = NV_MEM_TYPE_DDR2;
-       if (pfb474 & 0x00000001)
-               ram->base.type = NV_MEM_TYPE_DDR1;
-
-       ram->base.size = nv_rd32(pfb, 0x10020c) & 0xff000000;
-       ram->base.calc = nv40_ram_calc;
-       ram->base.prog = nv40_ram_prog;
-       ram->base.tidy = nv40_ram_tidy;
-       return 0;
-}
-
-struct nouveau_oclass
-nv44_ram_oclass = {
-       .handle = 0,
-       .ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nv44_ram_create,
-               .dtor = _nouveau_ram_dtor,
-               .init = _nouveau_ram_init,
-               .fini = _nouveau_ram_fini,
-       }
-};
diff --git a/drivers/gpu/drm/nouveau/core/subdev/fb/ramnv49.c b/drivers/gpu/drm/nouveau/core/subdev/fb/ramnv49.c
deleted file mode 100644 (file)
index baa013a..0000000
+++ /dev/null
@@ -1,67 +0,0 @@
-/*
- * Copyright 2013 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 "nv40.h"
-
-static int
-nv49_ram_create(struct nouveau_object *parent, struct nouveau_object *engine,
-               struct nouveau_oclass *oclass, void *data, u32 size,
-               struct nouveau_object **pobject)
-{
-       struct nouveau_fb *pfb = nouveau_fb(parent);
-       struct nv40_ram *ram;
-       u32 pfb914 = nv_rd32(pfb, 0x100914);
-       int ret;
-
-       ret = nouveau_ram_create(parent, engine, oclass, &ram);
-       *pobject = nv_object(ram);
-       if (ret)
-               return ret;
-
-       switch (pfb914 & 0x00000003) {
-       case 0x00000000: ram->base.type = NV_MEM_TYPE_DDR1; break;
-       case 0x00000001: ram->base.type = NV_MEM_TYPE_DDR2; break;
-       case 0x00000002: ram->base.type = NV_MEM_TYPE_GDDR3; break;
-       case 0x00000003: break;
-       }
-
-       ram->base.size  =  nv_rd32(pfb, 0x10020c) & 0xff000000;
-       ram->base.parts = (nv_rd32(pfb, 0x100200) & 0x00000003) + 1;
-       ram->base.tags  =  nv_rd32(pfb, 0x100320);
-       ram->base.calc = nv40_ram_calc;
-       ram->base.prog = nv40_ram_prog;
-       ram->base.tidy = nv40_ram_tidy;
-       return 0;
-}
-
-struct nouveau_oclass
-nv49_ram_oclass = {
-       .handle = 0,
-       .ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nv49_ram_create,
-               .dtor = _nouveau_ram_dtor,
-               .init = _nouveau_ram_init,
-               .fini = _nouveau_ram_fini,
-       }
-};
diff --git a/drivers/gpu/drm/nouveau/core/subdev/fb/ramnv4e.c b/drivers/gpu/drm/nouveau/core/subdev/fb/ramnv4e.c
deleted file mode 100644 (file)
index 63a6aab..0000000
+++ /dev/null
@@ -1,55 +0,0 @@
-/*
- * Copyright 2013 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 "priv.h"
-
-static int
-nv4e_ram_create(struct nouveau_object *parent, struct nouveau_object *engine,
-               struct nouveau_oclass *oclass, void *data, u32 size,
-               struct nouveau_object **pobject)
-{
-       struct nouveau_fb *pfb = nouveau_fb(parent);
-       struct nouveau_ram *ram;
-       int ret;
-
-       ret = nouveau_ram_create(parent, engine, oclass, &ram);
-       *pobject = nv_object(ram);
-       if (ret)
-               return ret;
-
-       ram->size = nv_rd32(pfb, 0x10020c) & 0xff000000;
-       ram->type = NV_MEM_TYPE_STOLEN;
-       return 0;
-}
-
-struct nouveau_oclass
-nv4e_ram_oclass = {
-       .handle = 0,
-       .ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nv4e_ram_create,
-               .dtor = _nouveau_ram_dtor,
-               .init = _nouveau_ram_init,
-               .fini = _nouveau_ram_fini,
-       }
-};
diff --git a/drivers/gpu/drm/nouveau/core/subdev/fb/ramnv50.c b/drivers/gpu/drm/nouveau/core/subdev/fb/ramnv50.c
deleted file mode 100644 (file)
index 64a983c..0000000
+++ /dev/null
@@ -1,470 +0,0 @@
-/*
- * Copyright 2013 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 <subdev/bios.h>
-#include <subdev/bios/bit.h>
-#include <subdev/bios/pll.h>
-#include <subdev/bios/perf.h>
-#include <subdev/bios/timing.h>
-#include <subdev/clock/pll.h>
-#include <subdev/fb.h>
-
-#include <core/option.h>
-#include <core/mm.h>
-
-#include "ramseq.h"
-
-#include "nv50.h"
-
-struct nv50_ramseq {
-       struct hwsq base;
-       struct hwsq_reg r_0x002504;
-       struct hwsq_reg r_0x004008;
-       struct hwsq_reg r_0x00400c;
-       struct hwsq_reg r_0x00c040;
-       struct hwsq_reg r_0x100210;
-       struct hwsq_reg r_0x1002d0;
-       struct hwsq_reg r_0x1002d4;
-       struct hwsq_reg r_0x1002dc;
-       struct hwsq_reg r_0x100da0[8];
-       struct hwsq_reg r_0x100e20;
-       struct hwsq_reg r_0x100e24;
-       struct hwsq_reg r_0x611200;
-       struct hwsq_reg r_timing[9];
-       struct hwsq_reg r_mr[4];
-};
-
-struct nv50_ram {
-       struct nouveau_ram base;
-       struct nv50_ramseq hwsq;
-};
-
-#define QFX5800NVA0 1
-
-static int
-nv50_ram_calc(struct nouveau_fb *pfb, u32 freq)
-{
-       struct nouveau_bios *bios = nouveau_bios(pfb);
-       struct nv50_ram *ram = (void *)pfb->ram;
-       struct nv50_ramseq *hwsq = &ram->hwsq;
-       struct nvbios_perfE perfE;
-       struct nvbios_pll mpll;
-       struct {
-               u32 data;
-               u8  size;
-       } ramcfg, timing;
-       u8  ver, hdr, cnt, len, strap;
-       int N1, M1, N2, M2, P;
-       int ret, i;
-
-       /* lookup closest matching performance table entry for frequency */
-       i = 0;
-       do {
-               ramcfg.data = nvbios_perfEp(bios, i++, &ver, &hdr, &cnt,
-                                          &ramcfg.size, &perfE);
-               if (!ramcfg.data || (ver < 0x25 || ver >= 0x40) ||
-                   (ramcfg.size < 2)) {
-                       nv_error(pfb, "invalid/missing perftab entry\n");
-                       return -EINVAL;
-               }
-       } while (perfE.memory < freq);
-
-       /* locate specific data set for the attached memory */
-       strap = nvbios_ramcfg_index(nv_subdev(pfb));
-       if (strap >= cnt) {
-               nv_error(pfb, "invalid ramcfg strap\n");
-               return -EINVAL;
-       }
-
-       ramcfg.data += hdr + (strap * ramcfg.size);
-
-       /* lookup memory timings, if bios says they're present */
-       strap = nv_ro08(bios, ramcfg.data + 0x01);
-       if (strap != 0xff) {
-               timing.data = nvbios_timingEe(bios, strap, &ver, &hdr,
-                                            &cnt, &len);
-               if (!timing.data || ver != 0x10 || hdr < 0x12) {
-                       nv_error(pfb, "invalid/missing timing entry "
-                                "%02x %04x %02x %02x\n",
-                                strap, timing.data, ver, hdr);
-                       return -EINVAL;
-               }
-       } else {
-               timing.data = 0;
-       }
-
-       ret = ram_init(hwsq, nv_subdev(pfb));
-       if (ret)
-               return ret;
-
-       ram_wait(hwsq, 0x01, 0x00); /* wait for !vblank */
-       ram_wait(hwsq, 0x01, 0x01); /* wait for vblank */
-       ram_wr32(hwsq, 0x611200, 0x00003300);
-       ram_wr32(hwsq, 0x002504, 0x00000001); /* block fifo */
-       ram_nsec(hwsq, 8000);
-       ram_setf(hwsq, 0x10, 0x00); /* disable fb */
-       ram_wait(hwsq, 0x00, 0x01); /* wait for fb disabled */
-
-       ram_wr32(hwsq, 0x1002d4, 0x00000001); /* precharge */
-       ram_wr32(hwsq, 0x1002d0, 0x00000001); /* refresh */
-       ram_wr32(hwsq, 0x1002d0, 0x00000001); /* refresh */
-       ram_wr32(hwsq, 0x100210, 0x00000000); /* disable auto-refresh */
-       ram_wr32(hwsq, 0x1002dc, 0x00000001); /* enable self-refresh */
-
-       ret = nvbios_pll_parse(bios, 0x004008, &mpll);
-       mpll.vco2.max_freq = 0;
-       if (ret == 0) {
-               ret = nv04_pll_calc(nv_subdev(pfb), &mpll, freq,
-                                  &N1, &M1, &N2, &M2, &P);
-               if (ret == 0)
-                       ret = -EINVAL;
-       }
-
-       if (ret < 0)
-               return ret;
-
-       ram_mask(hwsq, 0x00c040, 0xc000c000, 0x0000c000);
-       ram_mask(hwsq, 0x004008, 0x00000200, 0x00000200);
-       ram_mask(hwsq, 0x00400c, 0x0000ffff, (N1 << 8) | M1);
-       ram_mask(hwsq, 0x004008, 0x81ff0000, 0x80000000 | (mpll.bias_p << 19) |
-                                            (P << 22) | (P << 16));
-#if QFX5800NVA0
-       for (i = 0; i < 8; i++)
-               ram_mask(hwsq, 0x100da0[i], 0x00000000, 0x00000000); /*XXX*/
-#endif
-       ram_nsec(hwsq, 96000); /*XXX*/
-       ram_mask(hwsq, 0x004008, 0x00002200, 0x00002000);
-
-       ram_wr32(hwsq, 0x1002dc, 0x00000000); /* disable self-refresh */
-       ram_wr32(hwsq, 0x100210, 0x80000000); /* enable auto-refresh */
-
-       ram_nsec(hwsq, 12000);
-
-       switch (ram->base.type) {
-       case NV_MEM_TYPE_DDR2:
-               ram_nuke(hwsq, mr[0]); /* force update */
-               ram_mask(hwsq, mr[0], 0x000, 0x000);
-               break;
-       case NV_MEM_TYPE_GDDR3:
-               ram_mask(hwsq, mr[2], 0x000, 0x000);
-               ram_nuke(hwsq, mr[0]); /* force update */
-               ram_mask(hwsq, mr[0], 0x000, 0x000);
-               break;
-       default:
-               break;
-       }
-
-       ram_mask(hwsq, timing[3], 0x00000000, 0x00000000); /*XXX*/
-       ram_mask(hwsq, timing[1], 0x00000000, 0x00000000); /*XXX*/
-       ram_mask(hwsq, timing[6], 0x00000000, 0x00000000); /*XXX*/
-       ram_mask(hwsq, timing[7], 0x00000000, 0x00000000); /*XXX*/
-       ram_mask(hwsq, timing[8], 0x00000000, 0x00000000); /*XXX*/
-       ram_mask(hwsq, timing[0], 0x00000000, 0x00000000); /*XXX*/
-       ram_mask(hwsq, timing[2], 0x00000000, 0x00000000); /*XXX*/
-       ram_mask(hwsq, timing[4], 0x00000000, 0x00000000); /*XXX*/
-       ram_mask(hwsq, timing[5], 0x00000000, 0x00000000); /*XXX*/
-
-       ram_mask(hwsq, timing[0], 0x00000000, 0x00000000); /*XXX*/
-
-#if QFX5800NVA0
-       ram_nuke(hwsq, 0x100e24);
-       ram_mask(hwsq, 0x100e24, 0x00000000, 0x00000000);
-       ram_nuke(hwsq, 0x100e20);
-       ram_mask(hwsq, 0x100e20, 0x00000000, 0x00000000);
-#endif
-
-       ram_mask(hwsq, mr[0], 0x100, 0x100);
-       ram_mask(hwsq, mr[0], 0x100, 0x000);
-
-       ram_setf(hwsq, 0x10, 0x01); /* enable fb */
-       ram_wait(hwsq, 0x00, 0x00); /* wait for fb enabled */
-       ram_wr32(hwsq, 0x611200, 0x00003330);
-       ram_wr32(hwsq, 0x002504, 0x00000000); /* un-block fifo */
-       return 0;
-}
-
-static int
-nv50_ram_prog(struct nouveau_fb *pfb)
-{
-       struct nouveau_device *device = nv_device(pfb);
-       struct nv50_ram *ram = (void *)pfb->ram;
-       struct nv50_ramseq *hwsq = &ram->hwsq;
-
-       ram_exec(hwsq, nouveau_boolopt(device->cfgopt, "NvMemExec", true));
-       return 0;
-}
-
-static void
-nv50_ram_tidy(struct nouveau_fb *pfb)
-{
-       struct nv50_ram *ram = (void *)pfb->ram;
-       struct nv50_ramseq *hwsq = &ram->hwsq;
-       ram_exec(hwsq, false);
-}
-
-void
-__nv50_ram_put(struct nouveau_fb *pfb, struct nouveau_mem *mem)
-{
-       struct nouveau_mm_node *this;
-
-       while (!list_empty(&mem->regions)) {
-               this = list_first_entry(&mem->regions, typeof(*this), rl_entry);
-
-               list_del(&this->rl_entry);
-               nouveau_mm_free(&pfb->vram, &this);
-       }
-
-       nouveau_mm_free(&pfb->tags, &mem->tag);
-}
-
-void
-nv50_ram_put(struct nouveau_fb *pfb, struct nouveau_mem **pmem)
-{
-       struct nouveau_mem *mem = *pmem;
-
-       *pmem = NULL;
-       if (unlikely(mem == NULL))
-               return;
-
-       mutex_lock(&pfb->base.mutex);
-       __nv50_ram_put(pfb, mem);
-       mutex_unlock(&pfb->base.mutex);
-
-       kfree(mem);
-}
-
-int
-nv50_ram_get(struct nouveau_fb *pfb, u64 size, u32 align, u32 ncmin,
-            u32 memtype, struct nouveau_mem **pmem)
-{
-       struct nouveau_mm *heap = &pfb->vram;
-       struct nouveau_mm *tags = &pfb->tags;
-       struct nouveau_mm_node *r;
-       struct nouveau_mem *mem;
-       int comp = (memtype & 0x300) >> 8;
-       int type = (memtype & 0x07f);
-       int back = (memtype & 0x800);
-       int min, max, ret;
-
-       max = (size >> 12);
-       min = ncmin ? (ncmin >> 12) : max;
-       align >>= 12;
-
-       mem = kzalloc(sizeof(*mem), GFP_KERNEL);
-       if (!mem)
-               return -ENOMEM;
-
-       mutex_lock(&pfb->base.mutex);
-       if (comp) {
-               if (align == 16) {
-                       int n = (max >> 4) * comp;
-
-                       ret = nouveau_mm_head(tags, 0, 1, n, n, 1, &mem->tag);
-                       if (ret)
-                               mem->tag = NULL;
-               }
-
-               if (unlikely(!mem->tag))
-                       comp = 0;
-       }
-
-       INIT_LIST_HEAD(&mem->regions);
-       mem->memtype = (comp << 7) | type;
-       mem->size = max;
-
-       type = nv50_fb_memtype[type];
-       do {
-               if (back)
-                       ret = nouveau_mm_tail(heap, 0, type, max, min, align, &r);
-               else
-                       ret = nouveau_mm_head(heap, 0, type, max, min, align, &r);
-               if (ret) {
-                       mutex_unlock(&pfb->base.mutex);
-                       pfb->ram->put(pfb, &mem);
-                       return ret;
-               }
-
-               list_add_tail(&r->rl_entry, &mem->regions);
-               max -= r->length;
-       } while (max);
-       mutex_unlock(&pfb->base.mutex);
-
-       r = list_first_entry(&mem->regions, struct nouveau_mm_node, rl_entry);
-       mem->offset = (u64)r->offset << 12;
-       *pmem = mem;
-       return 0;
-}
-
-static u32
-nv50_fb_vram_rblock(struct nouveau_fb *pfb, struct nouveau_ram *ram)
-{
-       int colbits, rowbitsa, rowbitsb, banks;
-       u64 rowsize, predicted;
-       u32 r0, r4, rt, rblock_size;
-
-       r0 = nv_rd32(pfb, 0x100200);
-       r4 = nv_rd32(pfb, 0x100204);
-       rt = nv_rd32(pfb, 0x100250);
-       nv_debug(pfb, "memcfg 0x%08x 0x%08x 0x%08x 0x%08x\n", r0, r4, rt,
-                       nv_rd32(pfb, 0x001540));
-
-       colbits  =  (r4 & 0x0000f000) >> 12;
-       rowbitsa = ((r4 & 0x000f0000) >> 16) + 8;
-       rowbitsb = ((r4 & 0x00f00000) >> 20) + 8;
-       banks    = 1 << (((r4 & 0x03000000) >> 24) + 2);
-
-       rowsize = ram->parts * banks * (1 << colbits) * 8;
-       predicted = rowsize << rowbitsa;
-       if (r0 & 0x00000004)
-               predicted += rowsize << rowbitsb;
-
-       if (predicted != ram->size) {
-               nv_warn(pfb, "memory controller reports %d MiB VRAM\n",
-                       (u32)(ram->size >> 20));
-       }
-
-       rblock_size = rowsize;
-       if (rt & 1)
-               rblock_size *= 3;
-
-       nv_debug(pfb, "rblock %d bytes\n", rblock_size);
-       return rblock_size;
-}
-
-int
-nv50_ram_create_(struct nouveau_object *parent, struct nouveau_object *engine,
-                struct nouveau_oclass *oclass, int length, void **pobject)
-{
-       const u32 rsvd_head = ( 256 * 1024) >> 12; /* vga memory */
-       const u32 rsvd_tail = (1024 * 1024) >> 12; /* vbios etc */
-       struct nouveau_bios *bios = nouveau_bios(parent);
-       struct nouveau_fb *pfb = nouveau_fb(parent);
-       struct nouveau_ram *ram;
-       int ret;
-
-       ret = nouveau_ram_create_(parent, engine, oclass, length, pobject);
-       ram = *pobject;
-       if (ret)
-               return ret;
-
-       ram->size = nv_rd32(pfb, 0x10020c);
-       ram->size = (ram->size & 0xffffff00) | ((ram->size & 0x000000ff) << 32);
-
-       ram->part_mask = (nv_rd32(pfb, 0x001540) & 0x00ff0000) >> 16;
-       ram->parts = hweight8(ram->part_mask);
-
-       switch (nv_rd32(pfb, 0x100714) & 0x00000007) {
-       case 0: ram->type = NV_MEM_TYPE_DDR1; break;
-       case 1:
-               if (nouveau_fb_bios_memtype(bios) == NV_MEM_TYPE_DDR3)
-                       ram->type = NV_MEM_TYPE_DDR3;
-               else
-                       ram->type = NV_MEM_TYPE_DDR2;
-               break;
-       case 2: ram->type = NV_MEM_TYPE_GDDR3; break;
-       case 3: ram->type = NV_MEM_TYPE_GDDR4; break;
-       case 4: ram->type = NV_MEM_TYPE_GDDR5; break;
-       default:
-               break;
-       }
-
-       ret = nouveau_mm_init(&pfb->vram, rsvd_head, (ram->size >> 12) -
-                             (rsvd_head + rsvd_tail),
-                             nv50_fb_vram_rblock(pfb, ram) >> 12);
-       if (ret)
-               return ret;
-
-       ram->ranks = (nv_rd32(pfb, 0x100200) & 0x4) ? 2 : 1;
-       ram->tags  =  nv_rd32(pfb, 0x100320);
-       ram->get = nv50_ram_get;
-       ram->put = nv50_ram_put;
-       return 0;
-}
-
-static int
-nv50_ram_ctor(struct nouveau_object *parent, struct nouveau_object *engine,
-             struct nouveau_oclass *oclass, void *data, u32 datasize,
-             struct nouveau_object **pobject)
-{
-       struct nv50_ram *ram;
-       int ret, i;
-
-       ret = nv50_ram_create(parent, engine, oclass, &ram);
-       *pobject = nv_object(ram);
-       if (ret)
-               return ret;
-
-       switch (ram->base.type) {
-       case NV_MEM_TYPE_DDR2:
-       case NV_MEM_TYPE_GDDR3:
-               ram->base.calc = nv50_ram_calc;
-               ram->base.prog = nv50_ram_prog;
-               ram->base.tidy = nv50_ram_tidy;
-               break;
-       default:
-               nv_warn(ram, "reclocking of this ram type unsupported\n");
-               return 0;
-       }
-
-       ram->hwsq.r_0x002504 = hwsq_reg(0x002504);
-       ram->hwsq.r_0x00c040 = hwsq_reg(0x00c040);
-       ram->hwsq.r_0x004008 = hwsq_reg(0x004008);
-       ram->hwsq.r_0x00400c = hwsq_reg(0x00400c);
-       ram->hwsq.r_0x100210 = hwsq_reg(0x100210);
-       ram->hwsq.r_0x1002d0 = hwsq_reg(0x1002d0);
-       ram->hwsq.r_0x1002d4 = hwsq_reg(0x1002d4);
-       ram->hwsq.r_0x1002dc = hwsq_reg(0x1002dc);
-       for (i = 0; i < 8; i++)
-               ram->hwsq.r_0x100da0[i] = hwsq_reg(0x100da0 + (i * 0x04));
-       ram->hwsq.r_0x100e20 = hwsq_reg(0x100e20);
-       ram->hwsq.r_0x100e24 = hwsq_reg(0x100e24);
-       ram->hwsq.r_0x611200 = hwsq_reg(0x611200);
-
-       for (i = 0; i < 9; i++)
-               ram->hwsq.r_timing[i] = hwsq_reg(0x100220 + (i * 0x04));
-
-       if (ram->base.ranks > 1) {
-               ram->hwsq.r_mr[0] = hwsq_reg2(0x1002c0, 0x1002c8);
-               ram->hwsq.r_mr[1] = hwsq_reg2(0x1002c4, 0x1002cc);
-               ram->hwsq.r_mr[2] = hwsq_reg2(0x1002e0, 0x1002e8);
-               ram->hwsq.r_mr[3] = hwsq_reg2(0x1002e4, 0x1002ec);
-       } else {
-               ram->hwsq.r_mr[0] = hwsq_reg(0x1002c0);
-               ram->hwsq.r_mr[1] = hwsq_reg(0x1002c4);
-               ram->hwsq.r_mr[2] = hwsq_reg(0x1002e0);
-               ram->hwsq.r_mr[3] = hwsq_reg(0x1002e4);
-       }
-
-       return 0;
-}
-
-struct nouveau_oclass
-nv50_ram_oclass = {
-       .ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nv50_ram_ctor,
-               .dtor = _nouveau_ram_dtor,
-               .init = _nouveau_ram_init,
-               .fini = _nouveau_ram_fini,
-       }
-};
diff --git a/drivers/gpu/drm/nouveau/core/subdev/fb/ramnva3.c b/drivers/gpu/drm/nouveau/core/subdev/fb/ramnva3.c
deleted file mode 100644 (file)
index 3b38a53..0000000
+++ /dev/null
@@ -1,1024 +0,0 @@
-/*
- * Copyright 2013 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
- *         Roy Spliet <rspliet@eclipso.eu>
- */
-
-#include <subdev/bios.h>
-#include <subdev/bios/bit.h>
-#include <subdev/bios/pll.h>
-#include <subdev/bios/rammap.h>
-#include <subdev/bios/M0205.h>
-#include <subdev/bios/timing.h>
-
-#include <subdev/clock/nva3.h>
-#include <subdev/clock/pll.h>
-
-#include <subdev/gpio.h>
-
-#include <subdev/timer.h>
-
-#include <engine/fifo.h>
-
-#include <core/option.h>
-
-#include "ramfuc.h"
-
-#include "nv50.h"
-
-/* XXX: Remove when memx gains GPIO support */
-extern int nv50_gpio_location(int line, u32 *reg, u32 *shift);
-
-struct nva3_ramfuc {
-       struct ramfuc base;
-       struct ramfuc_reg r_0x001610;
-       struct ramfuc_reg r_0x001700;
-       struct ramfuc_reg r_0x002504;
-       struct ramfuc_reg r_0x004000;
-       struct ramfuc_reg r_0x004004;
-       struct ramfuc_reg r_0x004018;
-       struct ramfuc_reg r_0x004128;
-       struct ramfuc_reg r_0x004168;
-       struct ramfuc_reg r_0x100080;
-       struct ramfuc_reg r_0x100200;
-       struct ramfuc_reg r_0x100210;
-       struct ramfuc_reg r_0x100220[9];
-       struct ramfuc_reg r_0x100264;
-       struct ramfuc_reg r_0x1002d0;
-       struct ramfuc_reg r_0x1002d4;
-       struct ramfuc_reg r_0x1002dc;
-       struct ramfuc_reg r_0x10053c;
-       struct ramfuc_reg r_0x1005a0;
-       struct ramfuc_reg r_0x1005a4;
-       struct ramfuc_reg r_0x100700;
-       struct ramfuc_reg r_0x100714;
-       struct ramfuc_reg r_0x100718;
-       struct ramfuc_reg r_0x10071c;
-       struct ramfuc_reg r_0x100720;
-       struct ramfuc_reg r_0x100760;
-       struct ramfuc_reg r_0x1007a0;
-       struct ramfuc_reg r_0x1007e0;
-       struct ramfuc_reg r_0x100da0;
-       struct ramfuc_reg r_0x10f804;
-       struct ramfuc_reg r_0x1110e0;
-       struct ramfuc_reg r_0x111100;
-       struct ramfuc_reg r_0x111104;
-       struct ramfuc_reg r_0x1111e0;
-       struct ramfuc_reg r_0x111400;
-       struct ramfuc_reg r_0x611200;
-       struct ramfuc_reg r_mr[4];
-       struct ramfuc_reg r_gpioFBVREF;
-};
-
-struct nva3_ltrain {
-       enum {
-               NVA3_TRAIN_UNKNOWN,
-               NVA3_TRAIN_UNSUPPORTED,
-               NVA3_TRAIN_ONCE,
-               NVA3_TRAIN_EXEC,
-               NVA3_TRAIN_DONE
-       } state;
-       u32 r_100720;
-       u32 r_1111e0;
-       u32 r_111400;
-       struct nouveau_mem *mem;
-};
-
-struct nva3_ram {
-       struct nouveau_ram base;
-       struct nva3_ramfuc fuc;
-       struct nva3_ltrain ltrain;
-};
-
-void
-nva3_link_train_calc(u32 *vals, struct nva3_ltrain *train)
-{
-       int i, lo, hi;
-       u8 median[8], bins[4] = {0, 0, 0, 0}, bin = 0, qty = 0;
-
-       for (i = 0; i < 8; i++) {
-               for (lo = 0; lo < 0x40; lo++) {
-                       if (!(vals[lo] & 0x80000000))
-                               continue;
-                       if (vals[lo] & (0x101 << i))
-                               break;
-               }
-
-               if (lo == 0x40)
-                       return;
-
-               for (hi = lo + 1; hi < 0x40; hi++) {
-                       if (!(vals[lo] & 0x80000000))
-                               continue;
-                       if (!(vals[hi] & (0x101 << i))) {
-                               hi--;
-                               break;
-                       }
-               }
-
-               median[i] = ((hi - lo) >> 1) + lo;
-               bins[(median[i] & 0xf0) >> 4]++;
-               median[i] += 0x30;
-       }
-
-       /* Find the best value for 0x1111e0 */
-       for (i = 0; i < 4; i++) {
-               if (bins[i] > qty) {
-                       bin = i + 3;
-                       qty = bins[i];
-               }
-       }
-
-       train->r_100720 = 0;
-       for (i = 0; i < 8; i++) {
-               median[i] = max(median[i], (u8) (bin << 4));
-               median[i] = min(median[i], (u8) ((bin << 4) | 0xf));
-
-               train->r_100720 |= ((median[i] & 0x0f) << (i << 2));
-       }
-
-       train->r_1111e0 = 0x02000000 | (bin * 0x101);
-       train->r_111400 = 0x0;
-}
-
-/*
- * Link training for (at least) DDR3
- */
-int
-nva3_link_train(struct nouveau_fb *pfb)
-{
-       struct nouveau_bios *bios = nouveau_bios(pfb);
-       struct nva3_ram *ram = (void *)pfb->ram;
-       struct nouveau_clock *clk = nouveau_clock(pfb);
-       struct nva3_ltrain *train = &ram->ltrain;
-       struct nouveau_device *device = nv_device(pfb);
-       struct nva3_ramfuc *fuc = &ram->fuc;
-       u32 *result, r1700;
-       int ret, i;
-       struct nvbios_M0205T M0205T = { 0 };
-       u8 ver, hdr, cnt, len, snr, ssz;
-       unsigned int clk_current;
-       unsigned long flags;
-       unsigned long *f = &flags;
-
-       if (nouveau_boolopt(device->cfgopt, "NvMemExec", true) != true)
-               return -ENOSYS;
-
-       /* XXX: Multiple partitions? */
-       result = kmalloc(64 * sizeof(u32), GFP_KERNEL);
-       if (!result)
-               return -ENOMEM;
-
-       train->state = NVA3_TRAIN_EXEC;
-
-       /* Clock speeds for training and back */
-       nvbios_M0205Tp(bios, &ver, &hdr, &cnt, &len, &snr, &ssz, &M0205T);
-       if (M0205T.freq == 0)
-               return -ENOENT;
-
-       clk_current = clk->read(clk, nv_clk_src_mem);
-
-       ret = nva3_clock_pre(clk, f);
-       if (ret)
-               goto out;
-
-       /* First: clock up/down */
-       ret = ram->base.calc(pfb, (u32) M0205T.freq * 1000);
-       if (ret)
-               goto out;
-
-       /* Do this *after* calc, eliminates write in script */
-       nv_wr32(pfb, 0x111400, 0x00000000);
-       /* XXX: Magic writes that improve train reliability? */
-       nv_mask(pfb, 0x100674, 0x0000ffff, 0x00000000);
-       nv_mask(pfb, 0x1005e4, 0x0000ffff, 0x00000000);
-       nv_mask(pfb, 0x100b0c, 0x000000ff, 0x00000000);
-       nv_wr32(pfb, 0x100c04, 0x00000400);
-
-       /* Now the training script */
-       r1700 = ram_rd32(fuc, 0x001700);
-
-       ram_mask(fuc, 0x100200, 0x00000800, 0x00000000);
-       ram_wr32(fuc, 0x611200, 0x3300);
-       ram_wait_vblank(fuc);
-       ram_wait(fuc, 0x611200, 0x00000003, 0x00000000, 500000);
-       ram_mask(fuc, 0x001610, 0x00000083, 0x00000003);
-       ram_mask(fuc, 0x100080, 0x00000020, 0x00000000);
-       ram_mask(fuc, 0x10f804, 0x80000000, 0x00000000);
-       ram_wr32(fuc, 0x001700, 0x00000000);
-
-       ram_train(fuc);
-
-       /* Reset */
-       ram_mask(fuc, 0x10f804, 0x80000000, 0x80000000);
-       ram_wr32(fuc, 0x10053c, 0x0);
-       ram_wr32(fuc, 0x100720, train->r_100720);
-       ram_wr32(fuc, 0x1111e0, train->r_1111e0);
-       ram_wr32(fuc, 0x111400, train->r_111400);
-       ram_nuke(fuc, 0x100080);
-       ram_mask(fuc, 0x100080, 0x00000020, 0x00000020);
-       ram_nsec(fuc, 1000);
-
-       ram_wr32(fuc, 0x001700, r1700);
-       ram_mask(fuc, 0x001610, 0x00000083, 0x00000080);
-       ram_wr32(fuc, 0x611200, 0x3330);
-       ram_mask(fuc, 0x100200, 0x00000800, 0x00000800);
-
-       ram_exec(fuc, true);
-
-       ram->base.calc(pfb, clk_current);
-       ram_exec(fuc, true);
-
-       /* Post-processing, avoids flicker */
-       nv_mask(pfb, 0x616308, 0x10, 0x10);
-       nv_mask(pfb, 0x616b08, 0x10, 0x10);
-
-       nva3_clock_post(clk, f);
-
-       ram_train_result(pfb, result, 64);
-       for (i = 0; i < 64; i++)
-               nv_debug(pfb, "Train: %08x", result[i]);
-       nva3_link_train_calc(result, train);
-
-       nv_debug(pfb, "Train: %08x %08x %08x", train->r_100720,
-                       train->r_1111e0, train->r_111400);
-
-       kfree(result);
-
-       train->state = NVA3_TRAIN_DONE;
-
-       return ret;
-
-out:
-       if(ret == -EBUSY)
-               f = NULL;
-
-       train->state = NVA3_TRAIN_UNSUPPORTED;
-
-       nva3_clock_post(clk, f);
-       return ret;
-}
-
-int
-nva3_link_train_init(struct nouveau_fb *pfb)
-{
-       static const u32 pattern[16] = {
-               0xaaaaaaaa, 0xcccccccc, 0xdddddddd, 0xeeeeeeee,
-               0x00000000, 0x11111111, 0x44444444, 0xdddddddd,
-               0x33333333, 0x55555555, 0x77777777, 0x66666666,
-               0x99999999, 0x88888888, 0xeeeeeeee, 0xbbbbbbbb,
-       };
-       struct nouveau_bios *bios = nouveau_bios(pfb);
-       struct nva3_ram *ram = (void *)pfb->ram;
-       struct nva3_ltrain *train = &ram->ltrain;
-       struct nouveau_mem *mem;
-       struct nvbios_M0205E M0205E;
-       u8 ver, hdr, cnt, len;
-       u32 r001700;
-       int ret, i = 0;
-
-       train->state = NVA3_TRAIN_UNSUPPORTED;
-
-       /* We support type "5"
-        * XXX: training pattern table appears to be unused for this routine */
-       if (!nvbios_M0205Ep(bios, i, &ver, &hdr, &cnt, &len, &M0205E))
-               return -ENOENT;
-
-       if (M0205E.type != 5)
-               return 0;
-
-       train->state = NVA3_TRAIN_ONCE;
-
-       ret = pfb->ram->get(pfb, 0x8000, 0x10000, 0, 0x800, &ram->ltrain.mem);
-       if (ret)
-               return ret;
-
-       mem = ram->ltrain.mem;
-
-       nv_wr32(pfb, 0x100538, 0x10000000 | (mem->offset >> 16));
-       nv_wr32(pfb, 0x1005a8, 0x0000ffff);
-       nv_mask(pfb, 0x10f800, 0x00000001, 0x00000001);
-
-       for (i = 0; i < 0x30; i++) {
-               nv_wr32(pfb, 0x10f8c0, (i << 8) | i);
-               nv_wr32(pfb, 0x10f900, pattern[i % 16]);
-       }
-
-       for (i = 0; i < 0x30; i++) {
-               nv_wr32(pfb, 0x10f8e0, (i << 8) | i);
-               nv_wr32(pfb, 0x10f920, pattern[i % 16]);
-       }
-
-       /* And upload the pattern */
-       r001700 = nv_rd32(pfb, 0x1700);
-       nv_wr32(pfb, 0x1700, mem->offset >> 16);
-       for (i = 0; i < 16; i++)
-               nv_wr32(pfb, 0x700000 + (i << 2), pattern[i]);
-       for (i = 0; i < 16; i++)
-               nv_wr32(pfb, 0x700100 + (i << 2), pattern[i]);
-       nv_wr32(pfb, 0x1700, r001700);
-
-       train->r_100720 = nv_rd32(pfb, 0x100720);
-       train->r_1111e0 = nv_rd32(pfb, 0x1111e0);
-       train->r_111400 = nv_rd32(pfb, 0x111400);
-
-       return 0;
-}
-
-void
-nva3_link_train_fini(struct nouveau_fb *pfb)
-{
-       struct nva3_ram *ram = (void *)pfb->ram;
-
-       if (ram->ltrain.mem)
-               pfb->ram->put(pfb, &ram->ltrain.mem);
-}
-
-/*
- * RAM reclocking
- */
-#define T(t) cfg->timing_10_##t
-static int
-nva3_ram_timing_calc(struct nouveau_fb *pfb, u32 *timing)
-{
-       struct nva3_ram *ram = (void *)pfb->ram;
-       struct nvbios_ramcfg *cfg = &ram->base.target.bios;
-       int tUNK_base, tUNK_40_0, prevCL;
-       u32 cur2, cur3, cur7, cur8;
-
-       cur2 = nv_rd32(pfb, 0x100228);
-       cur3 = nv_rd32(pfb, 0x10022c);
-       cur7 = nv_rd32(pfb, 0x10023c);
-       cur8 = nv_rd32(pfb, 0x100240);
-
-
-       switch ((!T(CWL)) * ram->base.type) {
-       case NV_MEM_TYPE_DDR2:
-               T(CWL) = T(CL) - 1;
-               break;
-       case NV_MEM_TYPE_GDDR3:
-               T(CWL) = ((cur2 & 0xff000000) >> 24) + 1;
-               break;
-       }
-
-       prevCL = (cur3 & 0x000000ff) + 1;
-       tUNK_base = ((cur7 & 0x00ff0000) >> 16) - prevCL;
-
-       timing[0] = (T(RP) << 24 | T(RAS) << 16 | T(RFC) << 8 | T(RC));
-       timing[1] = (T(WR) + 1 + T(CWL)) << 24 |
-                   max_t(u8,T(18), 1) << 16 |
-                   (T(WTR) + 1 + T(CWL)) << 8 |
-                   (5 + T(CL) - T(CWL));
-       timing[2] = (T(CWL) - 1) << 24 |
-                   (T(RRD) << 16) |
-                   (T(RCDWR) << 8) |
-                   T(RCDRD);
-       timing[3] = (cur3 & 0x00ff0000) |
-                   (0x30 + T(CL)) << 24 |
-                   (0xb + T(CL)) << 8 |
-                   (T(CL) - 1);
-       timing[4] = T(20) << 24 |
-                   T(21) << 16 |
-                   T(13) << 8 |
-                   T(13);
-       timing[5] = T(RFC) << 24 |
-                   max_t(u8,T(RCDRD), T(RCDWR)) << 16 |
-                   max_t(u8, (T(CWL) + 6), (T(CL) + 2)) << 8 |
-                   T(RP);
-       timing[6] = (0x5a + T(CL)) << 16 |
-                   max_t(u8, 1, (6 - T(CL) + T(CWL))) << 8 |
-                   (0x50 + T(CL) - T(CWL));
-       timing[7] = (cur7 & 0xff000000) |
-                   ((tUNK_base + T(CL)) << 16) |
-                   0x202;
-       timing[8] = cur8 & 0xffffff00;
-
-       switch (ram->base.type) {
-       case NV_MEM_TYPE_DDR2:
-       case NV_MEM_TYPE_GDDR3:
-               tUNK_40_0 = prevCL - (cur8 & 0xff);
-               if (tUNK_40_0 > 0)
-                       timing[8] |= T(CL);
-               break;
-       default:
-               break;
-       }
-
-       nv_debug(pfb, "Entry: 220: %08x %08x %08x %08x\n",
-                       timing[0], timing[1], timing[2], timing[3]);
-       nv_debug(pfb, "  230: %08x %08x %08x %08x\n",
-                       timing[4], timing[5], timing[6], timing[7]);
-       nv_debug(pfb, "  240: %08x\n", timing[8]);
-       return 0;
-}
-#undef T
-
-static void
-nouveau_sddr2_dll_reset(struct nva3_ramfuc *fuc)
-{
-       ram_mask(fuc, mr[0], 0x100, 0x100);
-       ram_nsec(fuc, 1000);
-       ram_mask(fuc, mr[0], 0x100, 0x000);
-       ram_nsec(fuc, 1000);
-}
-
-static void
-nouveau_sddr3_dll_disable(struct nva3_ramfuc *fuc, u32 *mr)
-{
-       u32 mr1_old = ram_rd32(fuc, mr[1]);
-
-       if (!(mr1_old & 0x1)) {
-               ram_wr32(fuc, 0x1002d4, 0x00000001);
-               ram_wr32(fuc, mr[1], mr[1]);
-               ram_nsec(fuc, 1000);
-       }
-}
-
-static void
-nouveau_gddr3_dll_disable(struct nva3_ramfuc *fuc, u32 *mr)
-{
-       u32 mr1_old = ram_rd32(fuc, mr[1]);
-
-       if (!(mr1_old & 0x40)) {
-               ram_wr32(fuc, mr[1], mr[1]);
-               ram_nsec(fuc, 1000);
-       }
-}
-
-static void
-nva3_ram_lock_pll(struct nva3_ramfuc *fuc, struct nva3_clock_info *mclk)
-{
-       ram_wr32(fuc, 0x004004, mclk->pll);
-       ram_mask(fuc, 0x004000, 0x00000001, 0x00000001);
-       ram_mask(fuc, 0x004000, 0x00000010, 0x00000000);
-       ram_wait(fuc, 0x004000, 0x00020000, 0x00020000, 64000);
-       ram_mask(fuc, 0x004000, 0x00000010, 0x00000010);
-}
-
-static void
-nva3_ram_fbvref(struct nva3_ramfuc *fuc, u32 val)
-{
-       struct nouveau_gpio *gpio = nouveau_gpio(fuc->base.pfb);
-       struct dcb_gpio_func func;
-       u32 reg, sh, gpio_val;
-       int ret;
-
-       if (gpio->get(gpio, 0, 0x2e, DCB_GPIO_UNUSED) != val) {
-               ret = gpio->find(gpio, 0, 0x2e, DCB_GPIO_UNUSED, &func);
-               if (ret)
-                       return;
-
-               nv50_gpio_location(func.line, &reg, &sh);
-               gpio_val = ram_rd32(fuc, gpioFBVREF);
-               if (gpio_val & (8 << sh))
-                       val = !val;
-
-               ram_mask(fuc, gpioFBVREF, (0x3 << sh), ((val | 0x2) << sh));
-               ram_nsec(fuc, 20000);
-       }
-}
-
-static int
-nva3_ram_calc(struct nouveau_fb *pfb, u32 freq)
-{
-       struct nouveau_bios *bios = nouveau_bios(pfb);
-       struct nva3_ram *ram = (void *)pfb->ram;
-       struct nva3_ramfuc *fuc = &ram->fuc;
-       struct nva3_ltrain *train = &ram->ltrain;
-       struct nva3_clock_info mclk;
-       struct nouveau_ram_data *next;
-       u8  ver, hdr, cnt, len, strap;
-       u32 data;
-       u32 r004018, r100760, r100da0, r111100, ctrl;
-       u32 unk714, unk718, unk71c;
-       int ret, i;
-       u32 timing[9];
-       bool pll2pll;
-
-       next = &ram->base.target;
-       next->freq = freq;
-       ram->base.next = next;
-
-       if (ram->ltrain.state == NVA3_TRAIN_ONCE)
-               nva3_link_train(pfb);
-
-       /* lookup memory config data relevant to the target frequency */
-       i = 0;
-       data = nvbios_rammapEm(bios, freq / 1000, &ver, &hdr, &cnt, &len,
-                                     &next->bios);
-       if (!data || ver != 0x10 || hdr < 0x05) {
-               nv_error(pfb, "invalid/missing rammap entry\n");
-               return -EINVAL;
-       }
-
-       /* locate specific data set for the attached memory */
-       strap = nvbios_ramcfg_index(nv_subdev(pfb));
-       if (strap >= cnt) {
-               nv_error(pfb, "invalid ramcfg strap\n");
-               return -EINVAL;
-       }
-
-       data = nvbios_rammapSp(bios, data, ver, hdr, cnt, len, strap,
-                              &ver, &hdr, &next->bios);
-       if (!data || ver != 0x10 || hdr < 0x09) {
-               nv_error(pfb, "invalid/missing ramcfg entry\n");
-               return -EINVAL;
-       }
-
-       /* lookup memory timings, if bios says they're present */
-       if (next->bios.ramcfg_timing != 0xff) {
-               data = nvbios_timingEp(bios, next->bios.ramcfg_timing,
-                                      &ver, &hdr, &cnt, &len,
-                                      &next->bios);
-               if (!data || ver != 0x10 || hdr < 0x17) {
-                       nv_error(pfb, "invalid/missing timing entry\n");
-                       return -EINVAL;
-               }
-       }
-
-       ret = nva3_pll_info(nouveau_clock(pfb), 0x12, 0x4000, freq, &mclk);
-       if (ret < 0) {
-               nv_error(pfb, "failed mclk calculation\n");
-               return ret;
-       }
-
-       nva3_ram_timing_calc(pfb, timing);
-
-       ret = ram_init(fuc, pfb);
-       if (ret)
-               return ret;
-
-       /* Determine ram-specific MR values */
-       ram->base.mr[0] = ram_rd32(fuc, mr[0]);
-       ram->base.mr[1] = ram_rd32(fuc, mr[1]);
-       ram->base.mr[2] = ram_rd32(fuc, mr[2]);
-
-       switch (ram->base.type) {
-       case NV_MEM_TYPE_DDR2:
-               ret = nouveau_sddr2_calc(&ram->base);
-               break;
-       case NV_MEM_TYPE_DDR3:
-               ret = nouveau_sddr3_calc(&ram->base);
-               break;
-       case NV_MEM_TYPE_GDDR3:
-               ret = nouveau_gddr3_calc(&ram->base);
-               break;
-       default:
-               ret = -ENOSYS;
-               break;
-       }
-
-       if (ret)
-               return ret;
-
-       /* XXX: where the fuck does 750MHz come from? */
-       if (freq <= 750000) {
-               r004018 = 0x10000000;
-               r100760 = 0x22222222;
-               r100da0 = 0x00000010;
-       } else {
-               r004018 = 0x00000000;
-               r100760 = 0x00000000;
-               r100da0 = 0x00000000;
-       }
-
-       if (!next->bios.ramcfg_10_DLLoff)
-               r004018 |= 0x00004000;
-
-       /* pll2pll requires to switch to a safe clock first */
-       ctrl = ram_rd32(fuc, 0x004000);
-       pll2pll = (!(ctrl & 0x00000008)) && mclk.pll;
-
-       /* Pre, NVIDIA does this outside the script */
-       if (next->bios.ramcfg_10_02_10) {
-               ram_mask(fuc, 0x111104, 0x00000600, 0x00000000);
-       } else {
-               ram_mask(fuc, 0x111100, 0x40000000, 0x40000000);
-               ram_mask(fuc, 0x111104, 0x00000180, 0x00000000);
-       }
-       /* Always disable this bit during reclock */
-       ram_mask(fuc, 0x100200, 0x00000800, 0x00000000);
-
-       /* If switching from non-pll to pll, lock before disabling FB */
-       if (mclk.pll && !pll2pll) {
-               ram_mask(fuc, 0x004128, 0x003f3141, mclk.clk | 0x00000101);
-               nva3_ram_lock_pll(fuc, &mclk);
-       }
-
-       /* Start with disabling some CRTCs and PFIFO? */
-       ram_wait_vblank(fuc);
-       ram_wr32(fuc, 0x611200, 0x3300);
-       ram_mask(fuc, 0x002504, 0x1, 0x1);
-       ram_nsec(fuc, 10000);
-       ram_wait(fuc, 0x002504, 0x10, 0x10, 20000); /* XXX: or longer? */
-       ram_block(fuc);
-       ram_nsec(fuc, 2000);
-
-       if (!next->bios.ramcfg_10_02_10) {
-               if (ram->base.type == NV_MEM_TYPE_GDDR3)
-                       ram_mask(fuc, 0x111100, 0x04020000, 0x00020000);
-               else
-                       ram_mask(fuc, 0x111100, 0x04020000, 0x04020000);
-       }
-
-       /* If we're disabling the DLL, do it now */
-       switch (next->bios.ramcfg_10_DLLoff * ram->base.type) {
-       case NV_MEM_TYPE_DDR3:
-               nouveau_sddr3_dll_disable(fuc, ram->base.mr);
-               break;
-       case NV_MEM_TYPE_GDDR3:
-               nouveau_gddr3_dll_disable(fuc, ram->base.mr);
-               break;
-       }
-
-       if (fuc->r_gpioFBVREF.addr && next->bios.timing_10_ODT)
-               nva3_ram_fbvref(fuc, 0);
-
-       /* Brace RAM for impact */
-       ram_wr32(fuc, 0x1002d4, 0x00000001);
-       ram_wr32(fuc, 0x1002d0, 0x00000001);
-       ram_wr32(fuc, 0x1002d0, 0x00000001);
-       ram_wr32(fuc, 0x100210, 0x00000000);
-       ram_wr32(fuc, 0x1002dc, 0x00000001);
-       ram_nsec(fuc, 2000);
-
-       if (nv_device(pfb)->chipset == 0xa3 && freq <= 500000)
-               ram_mask(fuc, 0x100700, 0x00000006, 0x00000006);
-
-       /* Fiddle with clocks */
-       /* There's 4 scenario's
-        * pll->pll: first switch to a 324MHz clock, set up new PLL, switch
-        * clk->pll: Set up new PLL, switch
-        * pll->clk: Set up clock, switch
-        * clk->clk: Overwrite ctrl and other bits, switch */
-
-       /* Switch to regular clock - 324MHz */
-       if (pll2pll) {
-               ram_mask(fuc, 0x004000, 0x00000004, 0x00000004);
-               ram_mask(fuc, 0x004168, 0x003f3141, 0x00083101);
-               ram_mask(fuc, 0x004000, 0x00000008, 0x00000008);
-               ram_mask(fuc, 0x1110e0, 0x00088000, 0x00088000);
-               ram_wr32(fuc, 0x004018, 0x00001000);
-               nva3_ram_lock_pll(fuc, &mclk);
-       }
-
-       if (mclk.pll) {
-               ram_mask(fuc, 0x004000, 0x00000105, 0x00000105);
-               ram_wr32(fuc, 0x004018, 0x00001000 | r004018);
-               ram_wr32(fuc, 0x100da0, r100da0);
-       } else {
-               ram_mask(fuc, 0x004168, 0x003f3141, mclk.clk | 0x00000101);
-               ram_mask(fuc, 0x004000, 0x00000108, 0x00000008);
-               ram_mask(fuc, 0x1110e0, 0x00088000, 0x00088000);
-               ram_wr32(fuc, 0x004018, 0x00009000 | r004018);
-               ram_wr32(fuc, 0x100da0, r100da0);
-       }
-       ram_nsec(fuc, 20000);
-
-       if (next->bios.rammap_10_04_08) {
-               ram_wr32(fuc, 0x1005a0, next->bios.ramcfg_10_06 << 16 |
-                                       next->bios.ramcfg_10_05 << 8 |
-                                       next->bios.ramcfg_10_05);
-               ram_wr32(fuc, 0x1005a4, next->bios.ramcfg_10_08 << 8 |
-                                       next->bios.ramcfg_10_07);
-               ram_wr32(fuc, 0x10f804, next->bios.ramcfg_10_09_f0 << 20 |
-                                       next->bios.ramcfg_10_03_0f << 16 |
-                                       next->bios.ramcfg_10_09_0f |
-                                       0x80000000);
-               ram_mask(fuc, 0x10053c, 0x00001000, 0x00000000);
-       } else {
-               if (train->state == NVA3_TRAIN_DONE) {
-                       ram_wr32(fuc, 0x100080, 0x1020);
-                       ram_mask(fuc, 0x111400, 0xffffffff, train->r_111400);
-                       ram_mask(fuc, 0x1111e0, 0xffffffff, train->r_1111e0);
-                       ram_mask(fuc, 0x100720, 0xffffffff, train->r_100720);
-               }
-               ram_mask(fuc, 0x10053c, 0x00001000, 0x00001000);
-               ram_mask(fuc, 0x10f804, 0x80000000, 0x00000000);
-               ram_mask(fuc, 0x100760, 0x22222222, r100760);
-               ram_mask(fuc, 0x1007a0, 0x22222222, r100760);
-               ram_mask(fuc, 0x1007e0, 0x22222222, r100760);
-       }
-
-       if (nv_device(pfb)->chipset == 0xa3 && freq > 500000) {
-               ram_mask(fuc, 0x100700, 0x00000006, 0x00000000);
-       }
-
-       /* Final switch */
-       if (mclk.pll) {
-               ram_mask(fuc, 0x1110e0, 0x00088000, 0x00011000);
-               ram_mask(fuc, 0x004000, 0x00000008, 0x00000000);
-       }
-
-       ram_wr32(fuc, 0x1002dc, 0x00000000);
-       ram_wr32(fuc, 0x1002d4, 0x00000001);
-       ram_wr32(fuc, 0x100210, 0x80000000);
-       ram_nsec(fuc, 2000);
-
-       /* Set RAM MR parameters and timings */
-       for (i = 2; i >= 0; i--) {
-               if (ram_rd32(fuc, mr[i]) != ram->base.mr[i]) {
-                       ram_wr32(fuc, mr[i], ram->base.mr[i]);
-                       ram_nsec(fuc, 1000);
-               }
-       }
-
-       ram_wr32(fuc, 0x100220[3], timing[3]);
-       ram_wr32(fuc, 0x100220[1], timing[1]);
-       ram_wr32(fuc, 0x100220[6], timing[6]);
-       ram_wr32(fuc, 0x100220[7], timing[7]);
-       ram_wr32(fuc, 0x100220[2], timing[2]);
-       ram_wr32(fuc, 0x100220[4], timing[4]);
-       ram_wr32(fuc, 0x100220[5], timing[5]);
-       ram_wr32(fuc, 0x100220[0], timing[0]);
-       ram_wr32(fuc, 0x100220[8], timing[8]);
-
-       /* Misc */
-       ram_mask(fuc, 0x100200, 0x00001000, !next->bios.ramcfg_10_02_08 << 12);
-
-       /* XXX: A lot of "chipset"/"ram type" specific stuff...? */
-       unk714  = ram_rd32(fuc, 0x100714) & ~0xf0000130;
-       unk718  = ram_rd32(fuc, 0x100718) & ~0x00000100;
-       unk71c  = ram_rd32(fuc, 0x10071c) & ~0x00000100;
-       r111100 = ram_rd32(fuc, 0x111100) & ~0x3a800000;
-
-       if (next->bios.ramcfg_10_02_04) {
-               switch (ram->base.type) {
-               case NV_MEM_TYPE_DDR3:
-                       if (nv_device(pfb)->chipset != 0xa8)
-                               r111100 |= 0x00000004;
-                       /* no break */
-               case NV_MEM_TYPE_DDR2:
-                       r111100 |= 0x08000000;
-                       break;
-               default:
-                       break;
-               }
-       } else {
-               switch (ram->base.type) {
-               case NV_MEM_TYPE_DDR2:
-                       r111100 |= 0x1a800000;
-                       unk714  |= 0x00000010;
-                       break;
-               case NV_MEM_TYPE_DDR3:
-                       if (nv_device(pfb)->chipset == 0xa8) {
-                               r111100 |=  0x08000000;
-                       } else {
-                               r111100 &= ~0x00000004;
-                               r111100 |=  0x12800000;
-                       }
-                       unk714  |= 0x00000010;
-                       break;
-               case NV_MEM_TYPE_GDDR3:
-                       r111100 |= 0x30000000;
-                       unk714  |= 0x00000020;
-                       break;
-               default:
-                       break;
-               }
-       }
-
-       unk714 |= (next->bios.ramcfg_10_04_01) << 8;
-
-       if (next->bios.ramcfg_10_02_20)
-               unk714 |= 0xf0000000;
-       if (next->bios.ramcfg_10_02_02)
-               unk718 |= 0x00000100;
-       if (next->bios.ramcfg_10_02_01)
-               unk71c |= 0x00000100;
-       if (next->bios.timing_10_24 != 0xff) {
-               unk718 &= ~0xf0000000;
-               unk718 |= next->bios.timing_10_24 << 28;
-       }
-       if (next->bios.ramcfg_10_02_10)
-               r111100 &= ~0x04020000;
-
-       ram_mask(fuc, 0x100714, 0xffffffff, unk714);
-       ram_mask(fuc, 0x10071c, 0xffffffff, unk71c);
-       ram_mask(fuc, 0x100718, 0xffffffff, unk718);
-       ram_mask(fuc, 0x111100, 0xffffffff, r111100);
-
-       if (fuc->r_gpioFBVREF.addr && !next->bios.timing_10_ODT)
-               nva3_ram_fbvref(fuc, 1);
-
-       /* Reset DLL */
-       if (!next->bios.ramcfg_10_DLLoff)
-               nouveau_sddr2_dll_reset(fuc);
-
-       if (ram->base.type == NV_MEM_TYPE_GDDR3) {
-               ram_nsec(fuc, 31000);
-       } else {
-               ram_nsec(fuc, 14000);
-       }
-
-       if (ram->base.type == NV_MEM_TYPE_DDR3) {
-               ram_wr32(fuc, 0x100264, 0x1);
-               ram_nsec(fuc, 2000);
-       }
-
-       ram_nuke(fuc, 0x100700);
-       ram_mask(fuc, 0x100700, 0x01000000, 0x01000000);
-       ram_mask(fuc, 0x100700, 0x01000000, 0x00000000);
-
-       /* Re-enable FB */
-       ram_unblock(fuc);
-       ram_wr32(fuc, 0x611200, 0x3330);
-
-       /* Post fiddlings */
-       if (next->bios.rammap_10_04_02)
-               ram_mask(fuc, 0x100200, 0x00000800, 0x00000800);
-       if (next->bios.ramcfg_10_02_10) {
-               ram_mask(fuc, 0x111104, 0x00000180, 0x00000180);
-               ram_mask(fuc, 0x111100, 0x40000000, 0x00000000);
-       } else {
-               ram_mask(fuc, 0x111104, 0x00000600, 0x00000600);
-       }
-
-       if (mclk.pll) {
-               ram_mask(fuc, 0x004168, 0x00000001, 0x00000000);
-               ram_mask(fuc, 0x004168, 0x00000100, 0x00000000);
-       } else {
-               ram_mask(fuc, 0x004000, 0x00000001, 0x00000000);
-               ram_mask(fuc, 0x004128, 0x00000001, 0x00000000);
-               ram_mask(fuc, 0x004128, 0x00000100, 0x00000000);
-       }
-
-       return 0;
-}
-
-static int
-nva3_ram_prog(struct nouveau_fb *pfb)
-{
-       struct nouveau_device *device = nv_device(pfb);
-       struct nva3_ram *ram = (void *)pfb->ram;
-       struct nva3_ramfuc *fuc = &ram->fuc;
-       bool exec = nouveau_boolopt(device->cfgopt, "NvMemExec", true);
-
-       if (exec) {
-               nv_mask(pfb, 0x001534, 0x2, 0x2);
-
-               ram_exec(fuc, true);
-
-               /* Post-processing, avoids flicker */
-               nv_mask(pfb, 0x002504, 0x1, 0x0);
-               nv_mask(pfb, 0x001534, 0x2, 0x0);
-
-               nv_mask(pfb, 0x616308, 0x10, 0x10);
-               nv_mask(pfb, 0x616b08, 0x10, 0x10);
-       } else {
-               ram_exec(fuc, false);
-       }
-       return 0;
-}
-
-static void
-nva3_ram_tidy(struct nouveau_fb *pfb)
-{
-       struct nva3_ram *ram = (void *)pfb->ram;
-       struct nva3_ramfuc *fuc = &ram->fuc;
-       ram_exec(fuc, false);
-}
-
-static int
-nva3_ram_init(struct nouveau_object *object)
-{
-       struct nouveau_fb *pfb = (void *)object->parent;
-       struct nva3_ram   *ram = (void *)object;
-       int ret;
-
-       ret = nouveau_ram_init(&ram->base);
-       if (ret)
-               return ret;
-
-       nva3_link_train_init(pfb);
-
-       return 0;
-}
-
-static int
-nva3_ram_fini(struct nouveau_object *object, bool suspend)
-{
-       struct nouveau_fb *pfb = (void *)object->parent;
-
-       if (!suspend)
-               nva3_link_train_fini(pfb);
-
-       return 0;
-}
-
-static int
-nva3_ram_ctor(struct nouveau_object *parent, struct nouveau_object *engine,
-             struct nouveau_oclass *oclass, void *data, u32 datasize,
-             struct nouveau_object **pobject)
-{
-       struct nouveau_fb *pfb = nouveau_fb(parent);
-       struct nouveau_gpio *gpio = nouveau_gpio(pfb);
-       struct dcb_gpio_func func;
-       struct nva3_ram *ram;
-       int ret, i;
-       u32 reg, shift;
-
-       ret = nv50_ram_create(parent, engine, oclass, &ram);
-       *pobject = nv_object(ram);
-       if (ret)
-               return ret;
-
-       switch (ram->base.type) {
-       case NV_MEM_TYPE_DDR2:
-       case NV_MEM_TYPE_DDR3:
-       case NV_MEM_TYPE_GDDR3:
-               ram->base.calc = nva3_ram_calc;
-               ram->base.prog = nva3_ram_prog;
-               ram->base.tidy = nva3_ram_tidy;
-               break;
-       default:
-               nv_warn(ram, "reclocking of this ram type unsupported\n");
-               return 0;
-       }
-
-       ram->fuc.r_0x001610 = ramfuc_reg(0x001610);
-       ram->fuc.r_0x001700 = ramfuc_reg(0x001700);
-       ram->fuc.r_0x002504 = ramfuc_reg(0x002504);
-       ram->fuc.r_0x004000 = ramfuc_reg(0x004000);
-       ram->fuc.r_0x004004 = ramfuc_reg(0x004004);
-       ram->fuc.r_0x004018 = ramfuc_reg(0x004018);
-       ram->fuc.r_0x004128 = ramfuc_reg(0x004128);
-       ram->fuc.r_0x004168 = ramfuc_reg(0x004168);
-       ram->fuc.r_0x100080 = ramfuc_reg(0x100080);
-       ram->fuc.r_0x100200 = ramfuc_reg(0x100200);
-       ram->fuc.r_0x100210 = ramfuc_reg(0x100210);
-       for (i = 0; i < 9; i++)
-               ram->fuc.r_0x100220[i] = ramfuc_reg(0x100220 + (i * 4));
-       ram->fuc.r_0x100264 = ramfuc_reg(0x100264);
-       ram->fuc.r_0x1002d0 = ramfuc_reg(0x1002d0);
-       ram->fuc.r_0x1002d4 = ramfuc_reg(0x1002d4);
-       ram->fuc.r_0x1002dc = ramfuc_reg(0x1002dc);
-       ram->fuc.r_0x10053c = ramfuc_reg(0x10053c);
-       ram->fuc.r_0x1005a0 = ramfuc_reg(0x1005a0);
-       ram->fuc.r_0x1005a4 = ramfuc_reg(0x1005a4);
-       ram->fuc.r_0x100700 = ramfuc_reg(0x100700);
-       ram->fuc.r_0x100714 = ramfuc_reg(0x100714);
-       ram->fuc.r_0x100718 = ramfuc_reg(0x100718);
-       ram->fuc.r_0x10071c = ramfuc_reg(0x10071c);
-       ram->fuc.r_0x100720 = ramfuc_reg(0x100720);
-       ram->fuc.r_0x100760 = ramfuc_stride(0x100760, 4, ram->base.part_mask);
-       ram->fuc.r_0x1007a0 = ramfuc_stride(0x1007a0, 4, ram->base.part_mask);
-       ram->fuc.r_0x1007e0 = ramfuc_stride(0x1007e0, 4, ram->base.part_mask);
-       ram->fuc.r_0x100da0 = ramfuc_stride(0x100da0, 4, ram->base.part_mask);
-       ram->fuc.r_0x10f804 = ramfuc_reg(0x10f804);
-       ram->fuc.r_0x1110e0 = ramfuc_stride(0x1110e0, 4, ram->base.part_mask);
-       ram->fuc.r_0x111100 = ramfuc_reg(0x111100);
-       ram->fuc.r_0x111104 = ramfuc_reg(0x111104);
-       ram->fuc.r_0x1111e0 = ramfuc_reg(0x1111e0);
-       ram->fuc.r_0x111400 = ramfuc_reg(0x111400);
-       ram->fuc.r_0x611200 = ramfuc_reg(0x611200);
-
-       if (ram->base.ranks > 1) {
-               ram->fuc.r_mr[0] = ramfuc_reg2(0x1002c0, 0x1002c8);
-               ram->fuc.r_mr[1] = ramfuc_reg2(0x1002c4, 0x1002cc);
-               ram->fuc.r_mr[2] = ramfuc_reg2(0x1002e0, 0x1002e8);
-               ram->fuc.r_mr[3] = ramfuc_reg2(0x1002e4, 0x1002ec);
-       } else {
-               ram->fuc.r_mr[0] = ramfuc_reg(0x1002c0);
-               ram->fuc.r_mr[1] = ramfuc_reg(0x1002c4);
-               ram->fuc.r_mr[2] = ramfuc_reg(0x1002e0);
-               ram->fuc.r_mr[3] = ramfuc_reg(0x1002e4);
-       }
-
-       ret = gpio->find(gpio, 0, 0x2e, DCB_GPIO_UNUSED, &func);
-       if (ret == 0) {
-               nv50_gpio_location(func.line, &reg, &shift);
-               ram->fuc.r_gpioFBVREF = ramfuc_reg(reg);
-       }
-
-       return 0;
-}
-
-struct nouveau_oclass
-nva3_ram_oclass = {
-       .ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nva3_ram_ctor,
-               .dtor = _nouveau_ram_dtor,
-               .init = nva3_ram_init,
-               .fini = nva3_ram_fini,
-       },
-};
diff --git a/drivers/gpu/drm/nouveau/core/subdev/fb/ramnvaa.c b/drivers/gpu/drm/nouveau/core/subdev/fb/ramnvaa.c
deleted file mode 100644 (file)
index 033a8e9..0000000
+++ /dev/null
@@ -1,103 +0,0 @@
-/*
- * Copyright 2013 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 "nv50.h"
-
-struct nvaa_ram_priv {
-       struct nouveau_ram base;
-       u64 poller_base;
-};
-
-static int
-nvaa_ram_ctor(struct nouveau_object *parent, struct nouveau_object *engine,
-             struct nouveau_oclass *oclass, void *data, u32 datasize,
-             struct nouveau_object **pobject)
-{
-       u32 rsvd_head = ( 256 * 1024); /* vga memory */
-       u32 rsvd_tail = (1024 * 1024); /* vbios etc */
-       struct nouveau_fb *pfb = nouveau_fb(parent);
-       struct nvaa_ram_priv *priv;
-       int ret;
-
-       ret = nouveau_ram_create(parent, engine, oclass, &priv);
-       *pobject = nv_object(priv);
-       if (ret)
-               return ret;
-
-       priv->base.type   = NV_MEM_TYPE_STOLEN;
-       priv->base.stolen = (u64)nv_rd32(pfb, 0x100e10) << 12;
-       priv->base.size   = (u64)nv_rd32(pfb, 0x100e14) << 12;
-
-       rsvd_tail += 0x1000;
-       priv->poller_base = priv->base.size - rsvd_tail;
-
-       ret = nouveau_mm_init(&pfb->vram, rsvd_head >> 12,
-                             (priv->base.size  - (rsvd_head + rsvd_tail)) >> 12,
-                             1);
-       if (ret)
-               return ret;
-
-       priv->base.get = nv50_ram_get;
-       priv->base.put = nv50_ram_put;
-       return 0;
-}
-
-static int
-nvaa_ram_init(struct nouveau_object *object)
-{
-       struct nouveau_fb *pfb = nouveau_fb(object);
-       struct nvaa_ram_priv *priv = (void *)object;
-       int ret;
-       u64 dniso, hostnb, flush;
-
-       ret = nouveau_ram_init(&priv->base);
-       if (ret)
-               return ret;
-
-       dniso  = ((priv->base.size - (priv->poller_base + 0x00)) >> 5) - 1;
-       hostnb = ((priv->base.size - (priv->poller_base + 0x20)) >> 5) - 1;
-       flush  = ((priv->base.size - (priv->poller_base + 0x40)) >> 5) - 1;
-
-       /* Enable NISO poller for various clients and set their associated
-        * read address, only for MCP77/78 and MCP79/7A. (fd#25701)
-        */
-       nv_wr32(pfb, 0x100c18, dniso);
-       nv_mask(pfb, 0x100c14, 0x00000000, 0x00000001);
-       nv_wr32(pfb, 0x100c1c, hostnb);
-       nv_mask(pfb, 0x100c14, 0x00000000, 0x00000002);
-       nv_wr32(pfb, 0x100c24, flush);
-       nv_mask(pfb, 0x100c14, 0x00000000, 0x00010000);
-
-       return 0;
-}
-
-struct nouveau_oclass
-nvaa_ram_oclass = {
-       .ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nvaa_ram_ctor,
-               .dtor = _nouveau_ram_dtor,
-               .init = nvaa_ram_init,
-               .fini = _nouveau_ram_fini,
-       },
-};
diff --git a/drivers/gpu/drm/nouveau/core/subdev/fb/ramnvc0.c b/drivers/gpu/drm/nouveau/core/subdev/fb/ramnvc0.c
deleted file mode 100644 (file)
index 735cb95..0000000
+++ /dev/null
@@ -1,733 +0,0 @@
-/*
- * Copyright 2013 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 <subdev/bios.h>
-#include <subdev/bios/pll.h>
-#include <subdev/bios/rammap.h>
-#include <subdev/bios/timing.h>
-#include <subdev/ltc.h>
-
-#include <subdev/clock.h>
-#include <subdev/clock/pll.h>
-
-#include <core/option.h>
-
-#include "ramfuc.h"
-
-#include "nvc0.h"
-
-struct nvc0_ramfuc {
-       struct ramfuc base;
-
-       struct ramfuc_reg r_0x10fe20;
-       struct ramfuc_reg r_0x10fe24;
-       struct ramfuc_reg r_0x137320;
-       struct ramfuc_reg r_0x137330;
-
-       struct ramfuc_reg r_0x132000;
-       struct ramfuc_reg r_0x132004;
-       struct ramfuc_reg r_0x132100;
-
-       struct ramfuc_reg r_0x137390;
-
-       struct ramfuc_reg r_0x10f290;
-       struct ramfuc_reg r_0x10f294;
-       struct ramfuc_reg r_0x10f298;
-       struct ramfuc_reg r_0x10f29c;
-       struct ramfuc_reg r_0x10f2a0;
-
-       struct ramfuc_reg r_0x10f300;
-       struct ramfuc_reg r_0x10f338;
-       struct ramfuc_reg r_0x10f340;
-       struct ramfuc_reg r_0x10f344;
-       struct ramfuc_reg r_0x10f348;
-
-       struct ramfuc_reg r_0x10f910;
-       struct ramfuc_reg r_0x10f914;
-
-       struct ramfuc_reg r_0x100b0c;
-       struct ramfuc_reg r_0x10f050;
-       struct ramfuc_reg r_0x10f090;
-       struct ramfuc_reg r_0x10f200;
-       struct ramfuc_reg r_0x10f210;
-       struct ramfuc_reg r_0x10f310;
-       struct ramfuc_reg r_0x10f314;
-       struct ramfuc_reg r_0x10f610;
-       struct ramfuc_reg r_0x10f614;
-       struct ramfuc_reg r_0x10f800;
-       struct ramfuc_reg r_0x10f808;
-       struct ramfuc_reg r_0x10f824;
-       struct ramfuc_reg r_0x10f830;
-       struct ramfuc_reg r_0x10f988;
-       struct ramfuc_reg r_0x10f98c;
-       struct ramfuc_reg r_0x10f990;
-       struct ramfuc_reg r_0x10f998;
-       struct ramfuc_reg r_0x10f9b0;
-       struct ramfuc_reg r_0x10f9b4;
-       struct ramfuc_reg r_0x10fb04;
-       struct ramfuc_reg r_0x10fb08;
-       struct ramfuc_reg r_0x137300;
-       struct ramfuc_reg r_0x137310;
-       struct ramfuc_reg r_0x137360;
-       struct ramfuc_reg r_0x1373ec;
-       struct ramfuc_reg r_0x1373f0;
-       struct ramfuc_reg r_0x1373f8;
-
-       struct ramfuc_reg r_0x61c140;
-       struct ramfuc_reg r_0x611200;
-
-       struct ramfuc_reg r_0x13d8f4;
-};
-
-struct nvc0_ram {
-       struct nouveau_ram base;
-       struct nvc0_ramfuc fuc;
-       struct nvbios_pll refpll;
-       struct nvbios_pll mempll;
-};
-
-static void
-nvc0_ram_train(struct nvc0_ramfuc *fuc, u32 magic)
-{
-       struct nvc0_ram *ram = container_of(fuc, typeof(*ram), fuc);
-       struct nouveau_fb *pfb = nouveau_fb(ram);
-       u32 part = nv_rd32(pfb, 0x022438), i;
-       u32 mask = nv_rd32(pfb, 0x022554);
-       u32 addr = 0x110974;
-
-       ram_wr32(fuc, 0x10f910, magic);
-       ram_wr32(fuc, 0x10f914, magic);
-
-       for (i = 0; (magic & 0x80000000) && i < part; addr += 0x1000, i++) {
-               if (mask & (1 << i))
-                       continue;
-               ram_wait(fuc, addr, 0x0000000f, 0x00000000, 500000);
-       }
-}
-
-static int
-nvc0_ram_calc(struct nouveau_fb *pfb, u32 freq)
-{
-       struct nouveau_clock *clk = nouveau_clock(pfb);
-       struct nouveau_bios *bios = nouveau_bios(pfb);
-       struct nvc0_ram *ram = (void *)pfb->ram;
-       struct nvc0_ramfuc *fuc = &ram->fuc;
-       struct nvbios_ramcfg cfg;
-       u8  ver, cnt, len, strap;
-       struct {
-               u32 data;
-               u8  size;
-       } rammap, ramcfg, timing;
-       int ref, div, out;
-       int from, mode;
-       int N1, M1, P;
-       int ret;
-
-       /* lookup memory config data relevant to the target frequency */
-       rammap.data = nvbios_rammapEm(bios, freq / 1000, &ver, &rammap.size,
-                                    &cnt, &ramcfg.size, &cfg);
-       if (!rammap.data || ver != 0x10 || rammap.size < 0x0e) {
-               nv_error(pfb, "invalid/missing rammap entry\n");
-               return -EINVAL;
-       }
-
-       /* locate specific data set for the attached memory */
-       strap = nvbios_ramcfg_index(nv_subdev(pfb));
-       if (strap >= cnt) {
-               nv_error(pfb, "invalid ramcfg strap\n");
-               return -EINVAL;
-       }
-
-       ramcfg.data = rammap.data + rammap.size + (strap * ramcfg.size);
-       if (!ramcfg.data || ver != 0x10 || ramcfg.size < 0x0e) {
-               nv_error(pfb, "invalid/missing ramcfg entry\n");
-               return -EINVAL;
-       }
-
-       /* lookup memory timings, if bios says they're present */
-       strap = nv_ro08(bios, ramcfg.data + 0x01);
-       if (strap != 0xff) {
-               timing.data = nvbios_timingEe(bios, strap, &ver, &timing.size,
-                                            &cnt, &len);
-               if (!timing.data || ver != 0x10 || timing.size < 0x19) {
-                       nv_error(pfb, "invalid/missing timing entry\n");
-                       return -EINVAL;
-               }
-       } else {
-               timing.data = 0;
-       }
-
-       ret = ram_init(fuc, pfb);
-       if (ret)
-               return ret;
-
-       /* determine current mclk configuration */
-       from = !!(ram_rd32(fuc, 0x1373f0) & 0x00000002); /*XXX: ok? */
-
-       /* determine target mclk configuration */
-       if (!(ram_rd32(fuc, 0x137300) & 0x00000100))
-               ref = clk->read(clk, nv_clk_src_sppll0);
-       else
-               ref = clk->read(clk, nv_clk_src_sppll1);
-       div = max(min((ref * 2) / freq, (u32)65), (u32)2) - 2;
-       out = (ref * 2) / (div + 2);
-       mode = freq != out;
-
-       ram_mask(fuc, 0x137360, 0x00000002, 0x00000000);
-
-       if ((ram_rd32(fuc, 0x132000) & 0x00000002) || 0 /*XXX*/) {
-               ram_nuke(fuc, 0x132000);
-               ram_mask(fuc, 0x132000, 0x00000002, 0x00000002);
-               ram_mask(fuc, 0x132000, 0x00000002, 0x00000000);
-       }
-
-       if (mode == 1) {
-               ram_nuke(fuc, 0x10fe20);
-               ram_mask(fuc, 0x10fe20, 0x00000002, 0x00000002);
-               ram_mask(fuc, 0x10fe20, 0x00000002, 0x00000000);
-       }
-
-// 0x00020034 // 0x0000000a
-       ram_wr32(fuc, 0x132100, 0x00000001);
-
-       if (mode == 1 && from == 0) {
-               /* calculate refpll */
-               ret = nva3_pll_calc(nv_subdev(pfb), &ram->refpll,
-                                   ram->mempll.refclk, &N1, NULL, &M1, &P);
-               if (ret <= 0) {
-                       nv_error(pfb, "unable to calc refpll\n");
-                       return ret ? ret : -ERANGE;
-               }
-
-               ram_wr32(fuc, 0x10fe20, 0x20010000);
-               ram_wr32(fuc, 0x137320, 0x00000003);
-               ram_wr32(fuc, 0x137330, 0x81200006);
-               ram_wr32(fuc, 0x10fe24, (P << 16) | (N1 << 8) | M1);
-               ram_wr32(fuc, 0x10fe20, 0x20010001);
-               ram_wait(fuc, 0x137390, 0x00020000, 0x00020000, 64000);
-
-               /* calculate mempll */
-               ret = nva3_pll_calc(nv_subdev(pfb), &ram->mempll, freq,
-                                  &N1, NULL, &M1, &P);
-               if (ret <= 0) {
-                       nv_error(pfb, "unable to calc refpll\n");
-                       return ret ? ret : -ERANGE;
-               }
-
-               ram_wr32(fuc, 0x10fe20, 0x20010005);
-               ram_wr32(fuc, 0x132004, (P << 16) | (N1 << 8) | M1);
-               ram_wr32(fuc, 0x132000, 0x18010101);
-               ram_wait(fuc, 0x137390, 0x00000002, 0x00000002, 64000);
-       } else
-       if (mode == 0) {
-               ram_wr32(fuc, 0x137300, 0x00000003);
-       }
-
-       if (from == 0) {
-               ram_nuke(fuc, 0x10fb04);
-               ram_mask(fuc, 0x10fb04, 0x0000ffff, 0x00000000);
-               ram_nuke(fuc, 0x10fb08);
-               ram_mask(fuc, 0x10fb08, 0x0000ffff, 0x00000000);
-               ram_wr32(fuc, 0x10f988, 0x2004ff00);
-               ram_wr32(fuc, 0x10f98c, 0x003fc040);
-               ram_wr32(fuc, 0x10f990, 0x20012001);
-               ram_wr32(fuc, 0x10f998, 0x00011a00);
-               ram_wr32(fuc, 0x13d8f4, 0x00000000);
-       } else {
-               ram_wr32(fuc, 0x10f988, 0x20010000);
-               ram_wr32(fuc, 0x10f98c, 0x00000000);
-               ram_wr32(fuc, 0x10f990, 0x20012001);
-               ram_wr32(fuc, 0x10f998, 0x00010a00);
-       }
-
-       if (from == 0) {
-// 0x00020039 // 0x000000ba
-       }
-
-// 0x0002003a // 0x00000002
-       ram_wr32(fuc, 0x100b0c, 0x00080012);
-// 0x00030014 // 0x00000000 // 0x02b5f070
-// 0x00030014 // 0x00010000 // 0x02b5f070
-       ram_wr32(fuc, 0x611200, 0x00003300);
-// 0x00020034 // 0x0000000a
-// 0x00030020 // 0x00000001 // 0x00000000
-
-       ram_mask(fuc, 0x10f200, 0x00000800, 0x00000000);
-       ram_wr32(fuc, 0x10f210, 0x00000000);
-       ram_nsec(fuc, 1000);
-       if (mode == 0)
-               nvc0_ram_train(fuc, 0x000c1001);
-       ram_wr32(fuc, 0x10f310, 0x00000001);
-       ram_nsec(fuc, 1000);
-       ram_wr32(fuc, 0x10f090, 0x00000061);
-       ram_wr32(fuc, 0x10f090, 0xc000007f);
-       ram_nsec(fuc, 1000);
-
-       if (from == 0) {
-               ram_wr32(fuc, 0x10f824, 0x00007fd4);
-       } else {
-               ram_wr32(fuc, 0x1373ec, 0x00020404);
-       }
-
-       if (mode == 0) {
-               ram_mask(fuc, 0x10f808, 0x00080000, 0x00000000);
-               ram_mask(fuc, 0x10f200, 0x00008000, 0x00008000);
-               ram_wr32(fuc, 0x10f830, 0x41500010);
-               ram_mask(fuc, 0x10f830, 0x01000000, 0x00000000);
-               ram_mask(fuc, 0x132100, 0x00000100, 0x00000100);
-               ram_wr32(fuc, 0x10f050, 0xff000090);
-               ram_wr32(fuc, 0x1373ec, 0x00020f0f);
-               ram_wr32(fuc, 0x1373f0, 0x00000003);
-               ram_wr32(fuc, 0x137310, 0x81201616);
-               ram_wr32(fuc, 0x132100, 0x00000001);
-// 0x00020039 // 0x000000ba
-               ram_wr32(fuc, 0x10f830, 0x00300017);
-               ram_wr32(fuc, 0x1373f0, 0x00000001);
-               ram_wr32(fuc, 0x10f824, 0x00007e77);
-               ram_wr32(fuc, 0x132000, 0x18030001);
-               ram_wr32(fuc, 0x10f090, 0x4000007e);
-               ram_nsec(fuc, 2000);
-               ram_wr32(fuc, 0x10f314, 0x00000001);
-               ram_wr32(fuc, 0x10f210, 0x80000000);
-               ram_wr32(fuc, 0x10f338, 0x00300220);
-               ram_wr32(fuc, 0x10f300, 0x0000011d);
-               ram_nsec(fuc, 1000);
-               ram_wr32(fuc, 0x10f290, 0x02060505);
-               ram_wr32(fuc, 0x10f294, 0x34208288);
-               ram_wr32(fuc, 0x10f298, 0x44050411);
-               ram_wr32(fuc, 0x10f29c, 0x0000114c);
-               ram_wr32(fuc, 0x10f2a0, 0x42e10069);
-               ram_wr32(fuc, 0x10f614, 0x40044f77);
-               ram_wr32(fuc, 0x10f610, 0x40044f77);
-               ram_wr32(fuc, 0x10f344, 0x00600009);
-               ram_nsec(fuc, 1000);
-               ram_wr32(fuc, 0x10f348, 0x00700008);
-               ram_wr32(fuc, 0x61c140, 0x19240000);
-               ram_wr32(fuc, 0x10f830, 0x00300017);
-               nvc0_ram_train(fuc, 0x80021001);
-               nvc0_ram_train(fuc, 0x80081001);
-               ram_wr32(fuc, 0x10f340, 0x00500004);
-               ram_nsec(fuc, 1000);
-               ram_wr32(fuc, 0x10f830, 0x01300017);
-               ram_wr32(fuc, 0x10f830, 0x00300017);
-// 0x00030020 // 0x00000000 // 0x00000000
-// 0x00020034 // 0x0000000b
-               ram_wr32(fuc, 0x100b0c, 0x00080028);
-               ram_wr32(fuc, 0x611200, 0x00003330);
-       } else {
-               ram_wr32(fuc, 0x10f800, 0x00001800);
-               ram_wr32(fuc, 0x13d8f4, 0x00000000);
-               ram_wr32(fuc, 0x1373ec, 0x00020404);
-               ram_wr32(fuc, 0x1373f0, 0x00000003);
-               ram_wr32(fuc, 0x10f830, 0x40700010);
-               ram_wr32(fuc, 0x10f830, 0x40500010);
-               ram_wr32(fuc, 0x13d8f4, 0x00000000);
-               ram_wr32(fuc, 0x1373f8, 0x00000000);
-               ram_wr32(fuc, 0x132100, 0x00000101);
-               ram_wr32(fuc, 0x137310, 0x89201616);
-               ram_wr32(fuc, 0x10f050, 0xff000090);
-               ram_wr32(fuc, 0x1373ec, 0x00030404);
-               ram_wr32(fuc, 0x1373f0, 0x00000002);
-       // 0x00020039 // 0x00000011
-               ram_wr32(fuc, 0x132100, 0x00000001);
-               ram_wr32(fuc, 0x1373f8, 0x00002000);
-               ram_nsec(fuc, 2000);
-               ram_wr32(fuc, 0x10f808, 0x7aaa0050);
-               ram_wr32(fuc, 0x10f830, 0x00500010);
-               ram_wr32(fuc, 0x10f200, 0x00ce1000);
-               ram_wr32(fuc, 0x10f090, 0x4000007e);
-               ram_nsec(fuc, 2000);
-               ram_wr32(fuc, 0x10f314, 0x00000001);
-               ram_wr32(fuc, 0x10f210, 0x80000000);
-               ram_wr32(fuc, 0x10f338, 0x00300200);
-               ram_wr32(fuc, 0x10f300, 0x0000084d);
-               ram_nsec(fuc, 1000);
-               ram_wr32(fuc, 0x10f290, 0x0b343825);
-               ram_wr32(fuc, 0x10f294, 0x3483028e);
-               ram_wr32(fuc, 0x10f298, 0x440c0600);
-               ram_wr32(fuc, 0x10f29c, 0x0000214c);
-               ram_wr32(fuc, 0x10f2a0, 0x42e20069);
-               ram_wr32(fuc, 0x10f200, 0x00ce0000);
-               ram_wr32(fuc, 0x10f614, 0x60044e77);
-               ram_wr32(fuc, 0x10f610, 0x60044e77);
-               ram_wr32(fuc, 0x10f340, 0x00500000);
-               ram_nsec(fuc, 1000);
-               ram_wr32(fuc, 0x10f344, 0x00600228);
-               ram_nsec(fuc, 1000);
-               ram_wr32(fuc, 0x10f348, 0x00700000);
-               ram_wr32(fuc, 0x13d8f4, 0x00000000);
-               ram_wr32(fuc, 0x61c140, 0x09a40000);
-
-               nvc0_ram_train(fuc, 0x800e1008);
-
-               ram_nsec(fuc, 1000);
-               ram_wr32(fuc, 0x10f800, 0x00001804);
-       // 0x00030020 // 0x00000000 // 0x00000000
-       // 0x00020034 // 0x0000000b
-               ram_wr32(fuc, 0x13d8f4, 0x00000000);
-               ram_wr32(fuc, 0x100b0c, 0x00080028);
-               ram_wr32(fuc, 0x611200, 0x00003330);
-               ram_nsec(fuc, 100000);
-               ram_wr32(fuc, 0x10f9b0, 0x05313f41);
-               ram_wr32(fuc, 0x10f9b4, 0x00002f50);
-
-               nvc0_ram_train(fuc, 0x010c1001);
-       }
-
-       ram_mask(fuc, 0x10f200, 0x00000800, 0x00000800);
-// 0x00020016 // 0x00000000
-
-       if (mode == 0)
-               ram_mask(fuc, 0x132000, 0x00000001, 0x00000000);
-       return 0;
-}
-
-static int
-nvc0_ram_prog(struct nouveau_fb *pfb)
-{
-       struct nouveau_device *device = nv_device(pfb);
-       struct nvc0_ram *ram = (void *)pfb->ram;
-       struct nvc0_ramfuc *fuc = &ram->fuc;
-       ram_exec(fuc, nouveau_boolopt(device->cfgopt, "NvMemExec", true));
-       return 0;
-}
-
-static void
-nvc0_ram_tidy(struct nouveau_fb *pfb)
-{
-       struct nvc0_ram *ram = (void *)pfb->ram;
-       struct nvc0_ramfuc *fuc = &ram->fuc;
-       ram_exec(fuc, false);
-}
-
-extern const u8 nvc0_pte_storage_type_map[256];
-
-void
-nvc0_ram_put(struct nouveau_fb *pfb, struct nouveau_mem **pmem)
-{
-       struct nouveau_ltc *ltc = nouveau_ltc(pfb);
-       struct nouveau_mem *mem = *pmem;
-
-       *pmem = NULL;
-       if (unlikely(mem == NULL))
-               return;
-
-       mutex_lock(&pfb->base.mutex);
-       if (mem->tag)
-               ltc->tags_free(ltc, &mem->tag);
-       __nv50_ram_put(pfb, mem);
-       mutex_unlock(&pfb->base.mutex);
-
-       kfree(mem);
-}
-
-int
-nvc0_ram_get(struct nouveau_fb *pfb, u64 size, u32 align, u32 ncmin,
-            u32 memtype, struct nouveau_mem **pmem)
-{
-       struct nouveau_mm *mm = &pfb->vram;
-       struct nouveau_mm_node *r;
-       struct nouveau_mem *mem;
-       int type = (memtype & 0x0ff);
-       int back = (memtype & 0x800);
-       const bool comp = nvc0_pte_storage_type_map[type] != type;
-       int ret;
-
-       size  >>= 12;
-       align >>= 12;
-       ncmin >>= 12;
-       if (!ncmin)
-               ncmin = size;
-
-       mem = kzalloc(sizeof(*mem), GFP_KERNEL);
-       if (!mem)
-               return -ENOMEM;
-
-       INIT_LIST_HEAD(&mem->regions);
-       mem->size = size;
-
-       mutex_lock(&pfb->base.mutex);
-       if (comp) {
-               struct nouveau_ltc *ltc = nouveau_ltc(pfb);
-
-               /* compression only works with lpages */
-               if (align == (1 << (17 - 12))) {
-                       int n = size >> 5;
-                       ltc->tags_alloc(ltc, n, &mem->tag);
-               }
-
-               if (unlikely(!mem->tag))
-                       type = nvc0_pte_storage_type_map[type];
-       }
-       mem->memtype = type;
-
-       do {
-               if (back)
-                       ret = nouveau_mm_tail(mm, 0, 1, size, ncmin, align, &r);
-               else
-                       ret = nouveau_mm_head(mm, 0, 1, size, ncmin, align, &r);
-               if (ret) {
-                       mutex_unlock(&pfb->base.mutex);
-                       pfb->ram->put(pfb, &mem);
-                       return ret;
-               }
-
-               list_add_tail(&r->rl_entry, &mem->regions);
-               size -= r->length;
-       } while (size);
-       mutex_unlock(&pfb->base.mutex);
-
-       r = list_first_entry(&mem->regions, struct nouveau_mm_node, rl_entry);
-       mem->offset = (u64)r->offset << 12;
-       *pmem = mem;
-       return 0;
-}
-
-int
-nvc0_ram_create_(struct nouveau_object *parent, struct nouveau_object *engine,
-                struct nouveau_oclass *oclass, u32 maskaddr, int size,
-                void **pobject)
-{
-       struct nouveau_fb *pfb = nouveau_fb(parent);
-       struct nouveau_bios *bios = nouveau_bios(pfb);
-       struct nouveau_ram *ram;
-       const u32 rsvd_head = ( 256 * 1024) >> 12; /* vga memory */
-       const u32 rsvd_tail = (1024 * 1024) >> 12; /* vbios etc */
-       u32 parts = nv_rd32(pfb, 0x022438);
-       u32 pmask = nv_rd32(pfb, maskaddr);
-       u32 bsize = nv_rd32(pfb, 0x10f20c);
-       u32 offset, length;
-       bool uniform = true;
-       int ret, part;
-
-       ret = nouveau_ram_create_(parent, engine, oclass, size, pobject);
-       ram = *pobject;
-       if (ret)
-               return ret;
-
-       nv_debug(pfb, "0x100800: 0x%08x\n", nv_rd32(pfb, 0x100800));
-       nv_debug(pfb, "parts 0x%08x mask 0x%08x\n", parts, pmask);
-
-       ram->type = nouveau_fb_bios_memtype(bios);
-       ram->ranks = (nv_rd32(pfb, 0x10f200) & 0x00000004) ? 2 : 1;
-
-       /* read amount of vram attached to each memory controller */
-       for (part = 0; part < parts; part++) {
-               if (!(pmask & (1 << part))) {
-                       u32 psize = nv_rd32(pfb, 0x11020c + (part * 0x1000));
-                       if (psize != bsize) {
-                               if (psize < bsize)
-                                       bsize = psize;
-                               uniform = false;
-                       }
-
-                       nv_debug(pfb, "%d: mem_amount 0x%08x\n", part, psize);
-                       ram->size += (u64)psize << 20;
-               }
-       }
-
-       /* if all controllers have the same amount attached, there's no holes */
-       if (uniform) {
-               offset = rsvd_head;
-               length = (ram->size >> 12) - rsvd_head - rsvd_tail;
-               ret = nouveau_mm_init(&pfb->vram, offset, length, 1);
-       } else {
-               /* otherwise, address lowest common amount from 0GiB */
-               ret = nouveau_mm_init(&pfb->vram, rsvd_head,
-                                     (bsize << 8) * parts - rsvd_head, 1);
-               if (ret)
-                       return ret;
-
-               /* and the rest starting from (8GiB + common_size) */
-               offset = (0x0200000000ULL >> 12) + (bsize << 8);
-               length = (ram->size >> 12) - ((bsize * parts) << 8) - rsvd_tail;
-
-               ret = nouveau_mm_init(&pfb->vram, offset, length, 1);
-               if (ret)
-                       nouveau_mm_fini(&pfb->vram);
-       }
-
-       if (ret)
-               return ret;
-
-       ram->get = nvc0_ram_get;
-       ram->put = nvc0_ram_put;
-       return 0;
-}
-
-static int
-nvc0_ram_init(struct nouveau_object *object)
-{
-       struct nouveau_fb *pfb = (void *)object->parent;
-       struct nvc0_ram   *ram = (void *)object;
-       int ret, i;
-
-       ret = nouveau_ram_init(&ram->base);
-       if (ret)
-               return ret;
-
-       /* prepare for ddr link training, and load training patterns */
-       switch (ram->base.type) {
-       case NV_MEM_TYPE_GDDR5: {
-               static const u8  train0[] = {
-                       0x00, 0xff, 0x55, 0xaa, 0x33, 0xcc,
-                       0x00, 0xff, 0xff, 0x00, 0xff, 0x00,
-               };
-               static const u32 train1[] = {
-                       0x00000000, 0xffffffff,
-                       0x55555555, 0xaaaaaaaa,
-                       0x33333333, 0xcccccccc,
-                       0xf0f0f0f0, 0x0f0f0f0f,
-                       0x00ff00ff, 0xff00ff00,
-                       0x0000ffff, 0xffff0000,
-               };
-
-               for (i = 0; i < 0x30; i++) {
-                       nv_wr32(pfb, 0x10f968, 0x00000000 | (i << 8));
-                       nv_wr32(pfb, 0x10f96c, 0x00000000 | (i << 8));
-                       nv_wr32(pfb, 0x10f920, 0x00000100 | train0[i % 12]);
-                       nv_wr32(pfb, 0x10f924, 0x00000100 | train0[i % 12]);
-                       nv_wr32(pfb, 0x10f918,              train1[i % 12]);
-                       nv_wr32(pfb, 0x10f91c,              train1[i % 12]);
-                       nv_wr32(pfb, 0x10f920, 0x00000000 | train0[i % 12]);
-                       nv_wr32(pfb, 0x10f924, 0x00000000 | train0[i % 12]);
-                       nv_wr32(pfb, 0x10f918,              train1[i % 12]);
-                       nv_wr32(pfb, 0x10f91c,              train1[i % 12]);
-               }
-       }       break;
-       default:
-               break;
-       }
-
-       return 0;
-}
-
-static int
-nvc0_ram_ctor(struct nouveau_object *parent, struct nouveau_object *engine,
-             struct nouveau_oclass *oclass, void *data, u32 size,
-             struct nouveau_object **pobject)
-{
-       struct nouveau_bios *bios = nouveau_bios(parent);
-       struct nvc0_ram *ram;
-       int ret;
-
-       ret = nvc0_ram_create(parent, engine, oclass, 0x022554, &ram);
-       *pobject = nv_object(ram);
-       if (ret)
-               return ret;
-
-       ret = nvbios_pll_parse(bios, 0x0c, &ram->refpll);
-       if (ret) {
-               nv_error(ram, "mclk refpll data not found\n");
-               return ret;
-       }
-
-       ret = nvbios_pll_parse(bios, 0x04, &ram->mempll);
-       if (ret) {
-               nv_error(ram, "mclk pll data not found\n");
-               return ret;
-       }
-
-       switch (ram->base.type) {
-       case NV_MEM_TYPE_GDDR5:
-               ram->base.calc = nvc0_ram_calc;
-               ram->base.prog = nvc0_ram_prog;
-               ram->base.tidy = nvc0_ram_tidy;
-               break;
-       default:
-               nv_warn(ram, "reclocking of this ram type unsupported\n");
-               return 0;
-       }
-
-       ram->fuc.r_0x10fe20 = ramfuc_reg(0x10fe20);
-       ram->fuc.r_0x10fe24 = ramfuc_reg(0x10fe24);
-       ram->fuc.r_0x137320 = ramfuc_reg(0x137320);
-       ram->fuc.r_0x137330 = ramfuc_reg(0x137330);
-
-       ram->fuc.r_0x132000 = ramfuc_reg(0x132000);
-       ram->fuc.r_0x132004 = ramfuc_reg(0x132004);
-       ram->fuc.r_0x132100 = ramfuc_reg(0x132100);
-
-       ram->fuc.r_0x137390 = ramfuc_reg(0x137390);
-
-       ram->fuc.r_0x10f290 = ramfuc_reg(0x10f290);
-       ram->fuc.r_0x10f294 = ramfuc_reg(0x10f294);
-       ram->fuc.r_0x10f298 = ramfuc_reg(0x10f298);
-       ram->fuc.r_0x10f29c = ramfuc_reg(0x10f29c);
-       ram->fuc.r_0x10f2a0 = ramfuc_reg(0x10f2a0);
-
-       ram->fuc.r_0x10f300 = ramfuc_reg(0x10f300);
-       ram->fuc.r_0x10f338 = ramfuc_reg(0x10f338);
-       ram->fuc.r_0x10f340 = ramfuc_reg(0x10f340);
-       ram->fuc.r_0x10f344 = ramfuc_reg(0x10f344);
-       ram->fuc.r_0x10f348 = ramfuc_reg(0x10f348);
-
-       ram->fuc.r_0x10f910 = ramfuc_reg(0x10f910);
-       ram->fuc.r_0x10f914 = ramfuc_reg(0x10f914);
-
-       ram->fuc.r_0x100b0c = ramfuc_reg(0x100b0c);
-       ram->fuc.r_0x10f050 = ramfuc_reg(0x10f050);
-       ram->fuc.r_0x10f090 = ramfuc_reg(0x10f090);
-       ram->fuc.r_0x10f200 = ramfuc_reg(0x10f200);
-       ram->fuc.r_0x10f210 = ramfuc_reg(0x10f210);
-       ram->fuc.r_0x10f310 = ramfuc_reg(0x10f310);
-       ram->fuc.r_0x10f314 = ramfuc_reg(0x10f314);
-       ram->fuc.r_0x10f610 = ramfuc_reg(0x10f610);
-       ram->fuc.r_0x10f614 = ramfuc_reg(0x10f614);
-       ram->fuc.r_0x10f800 = ramfuc_reg(0x10f800);
-       ram->fuc.r_0x10f808 = ramfuc_reg(0x10f808);
-       ram->fuc.r_0x10f824 = ramfuc_reg(0x10f824);
-       ram->fuc.r_0x10f830 = ramfuc_reg(0x10f830);
-       ram->fuc.r_0x10f988 = ramfuc_reg(0x10f988);
-       ram->fuc.r_0x10f98c = ramfuc_reg(0x10f98c);
-       ram->fuc.r_0x10f990 = ramfuc_reg(0x10f990);
-       ram->fuc.r_0x10f998 = ramfuc_reg(0x10f998);
-       ram->fuc.r_0x10f9b0 = ramfuc_reg(0x10f9b0);
-       ram->fuc.r_0x10f9b4 = ramfuc_reg(0x10f9b4);
-       ram->fuc.r_0x10fb04 = ramfuc_reg(0x10fb04);
-       ram->fuc.r_0x10fb08 = ramfuc_reg(0x10fb08);
-       ram->fuc.r_0x137310 = ramfuc_reg(0x137300);
-       ram->fuc.r_0x137310 = ramfuc_reg(0x137310);
-       ram->fuc.r_0x137360 = ramfuc_reg(0x137360);
-       ram->fuc.r_0x1373ec = ramfuc_reg(0x1373ec);
-       ram->fuc.r_0x1373f0 = ramfuc_reg(0x1373f0);
-       ram->fuc.r_0x1373f8 = ramfuc_reg(0x1373f8);
-
-       ram->fuc.r_0x61c140 = ramfuc_reg(0x61c140);
-       ram->fuc.r_0x611200 = ramfuc_reg(0x611200);
-
-       ram->fuc.r_0x13d8f4 = ramfuc_reg(0x13d8f4);
-       return 0;
-}
-
-struct nouveau_oclass
-nvc0_ram_oclass = {
-       .handle = 0,
-       .ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nvc0_ram_ctor,
-               .dtor = _nouveau_ram_dtor,
-               .init = nvc0_ram_init,
-               .fini = _nouveau_ram_fini,
-       }
-};
diff --git a/drivers/gpu/drm/nouveau/core/subdev/fb/ramnve0.c b/drivers/gpu/drm/nouveau/core/subdev/fb/ramnve0.c
deleted file mode 100644 (file)
index 6bae474..0000000
+++ /dev/null
@@ -1,1646 +0,0 @@
-/*
- * Copyright 2013 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 <subdev/gpio.h>
-
-#include <subdev/bios.h>
-#include <subdev/bios/pll.h>
-#include <subdev/bios/init.h>
-#include <subdev/bios/rammap.h>
-#include <subdev/bios/timing.h>
-#include <subdev/bios/M0205.h>
-#include <subdev/bios/M0209.h>
-
-#include <subdev/clock.h>
-#include <subdev/clock/pll.h>
-
-#include <subdev/timer.h>
-
-#include <core/option.h>
-
-#include "nvc0.h"
-
-#include "ramfuc.h"
-
-struct nve0_ramfuc {
-       struct ramfuc base;
-
-       struct nvbios_pll refpll;
-       struct nvbios_pll mempll;
-
-       struct ramfuc_reg r_gpioMV;
-       u32 r_funcMV[2];
-       struct ramfuc_reg r_gpio2E;
-       u32 r_func2E[2];
-       struct ramfuc_reg r_gpiotrig;
-
-       struct ramfuc_reg r_0x132020;
-       struct ramfuc_reg r_0x132028;
-       struct ramfuc_reg r_0x132024;
-       struct ramfuc_reg r_0x132030;
-       struct ramfuc_reg r_0x132034;
-       struct ramfuc_reg r_0x132000;
-       struct ramfuc_reg r_0x132004;
-       struct ramfuc_reg r_0x132040;
-
-       struct ramfuc_reg r_0x10f248;
-       struct ramfuc_reg r_0x10f290;
-       struct ramfuc_reg r_0x10f294;
-       struct ramfuc_reg r_0x10f298;
-       struct ramfuc_reg r_0x10f29c;
-       struct ramfuc_reg r_0x10f2a0;
-       struct ramfuc_reg r_0x10f2a4;
-       struct ramfuc_reg r_0x10f2a8;
-       struct ramfuc_reg r_0x10f2ac;
-       struct ramfuc_reg r_0x10f2cc;
-       struct ramfuc_reg r_0x10f2e8;
-       struct ramfuc_reg r_0x10f250;
-       struct ramfuc_reg r_0x10f24c;
-       struct ramfuc_reg r_0x10fec4;
-       struct ramfuc_reg r_0x10fec8;
-       struct ramfuc_reg r_0x10f604;
-       struct ramfuc_reg r_0x10f614;
-       struct ramfuc_reg r_0x10f610;
-       struct ramfuc_reg r_0x100770;
-       struct ramfuc_reg r_0x100778;
-       struct ramfuc_reg r_0x10f224;
-
-       struct ramfuc_reg r_0x10f870;
-       struct ramfuc_reg r_0x10f698;
-       struct ramfuc_reg r_0x10f694;
-       struct ramfuc_reg r_0x10f6b8;
-       struct ramfuc_reg r_0x10f808;
-       struct ramfuc_reg r_0x10f670;
-       struct ramfuc_reg r_0x10f60c;
-       struct ramfuc_reg r_0x10f830;
-       struct ramfuc_reg r_0x1373ec;
-       struct ramfuc_reg r_0x10f800;
-       struct ramfuc_reg r_0x10f82c;
-
-       struct ramfuc_reg r_0x10f978;
-       struct ramfuc_reg r_0x10f910;
-       struct ramfuc_reg r_0x10f914;
-
-       struct ramfuc_reg r_mr[16]; /* MR0 - MR8, MR15 */
-
-       struct ramfuc_reg r_0x62c000;
-
-       struct ramfuc_reg r_0x10f200;
-
-       struct ramfuc_reg r_0x10f210;
-       struct ramfuc_reg r_0x10f310;
-       struct ramfuc_reg r_0x10f314;
-       struct ramfuc_reg r_0x10f318;
-       struct ramfuc_reg r_0x10f090;
-       struct ramfuc_reg r_0x10f69c;
-       struct ramfuc_reg r_0x10f824;
-       struct ramfuc_reg r_0x1373f0;
-       struct ramfuc_reg r_0x1373f4;
-       struct ramfuc_reg r_0x137320;
-       struct ramfuc_reg r_0x10f65c;
-       struct ramfuc_reg r_0x10f6bc;
-       struct ramfuc_reg r_0x100710;
-       struct ramfuc_reg r_0x100750;
-};
-
-struct nve0_ram {
-       struct nouveau_ram base;
-       struct nve0_ramfuc fuc;
-
-       struct list_head cfg;
-       u32 parts;
-       u32 pmask;
-       u32 pnuts;
-
-       struct nvbios_ramcfg diff;
-       int from;
-       int mode;
-       int N1, fN1, M1, P1;
-       int N2, M2, P2;
-};
-
-/*******************************************************************************
- * GDDR5
- ******************************************************************************/
-static void
-nve0_ram_train(struct nve0_ramfuc *fuc, u32 mask, u32 data)
-{
-       struct nve0_ram *ram = container_of(fuc, typeof(*ram), fuc);
-       u32 addr = 0x110974, i;
-
-       ram_mask(fuc, 0x10f910, mask, data);
-       ram_mask(fuc, 0x10f914, mask, data);
-
-       for (i = 0; (data & 0x80000000) && i < ram->parts; addr += 0x1000, i++) {
-               if (ram->pmask & (1 << i))
-                       continue;
-               ram_wait(fuc, addr, 0x0000000f, 0x00000000, 500000);
-       }
-}
-
-static void
-r1373f4_init(struct nve0_ramfuc *fuc)
-{
-       struct nve0_ram *ram = container_of(fuc, typeof(*ram), fuc);
-       const u32 mcoef = ((--ram->P2 << 28) | (ram->N2 << 8) | ram->M2);
-       const u32 rcoef = ((  ram->P1 << 16) | (ram->N1 << 8) | ram->M1);
-       const u32 runk0 = ram->fN1 << 16;
-       const u32 runk1 = ram->fN1;
-
-       if (ram->from == 2) {
-               ram_mask(fuc, 0x1373f4, 0x00000000, 0x00001100);
-               ram_mask(fuc, 0x1373f4, 0x00000000, 0x00000010);
-       } else {
-               ram_mask(fuc, 0x1373f4, 0x00000000, 0x00010010);
-       }
-
-       ram_mask(fuc, 0x1373f4, 0x00000003, 0x00000000);
-       ram_mask(fuc, 0x1373f4, 0x00000010, 0x00000000);
-
-       /* (re)program refpll, if required */
-       if ((ram_rd32(fuc, 0x132024) & 0xffffffff) != rcoef ||
-           (ram_rd32(fuc, 0x132034) & 0x0000ffff) != runk1) {
-               ram_mask(fuc, 0x132000, 0x00000001, 0x00000000);
-               ram_mask(fuc, 0x132020, 0x00000001, 0x00000000);
-               ram_wr32(fuc, 0x137320, 0x00000000);
-               ram_mask(fuc, 0x132030, 0xffff0000, runk0);
-               ram_mask(fuc, 0x132034, 0x0000ffff, runk1);
-               ram_wr32(fuc, 0x132024, rcoef);
-               ram_mask(fuc, 0x132028, 0x00080000, 0x00080000);
-               ram_mask(fuc, 0x132020, 0x00000001, 0x00000001);
-               ram_wait(fuc, 0x137390, 0x00020000, 0x00020000, 64000);
-               ram_mask(fuc, 0x132028, 0x00080000, 0x00000000);
-       }
-
-       /* (re)program mempll, if required */
-       if (ram->mode == 2) {
-               ram_mask(fuc, 0x1373f4, 0x00010000, 0x00000000);
-               ram_mask(fuc, 0x132000, 0x80000000, 0x80000000);
-               ram_mask(fuc, 0x132000, 0x00000001, 0x00000000);
-               ram_mask(fuc, 0x132004, 0x103fffff, mcoef);
-               ram_mask(fuc, 0x132000, 0x00000001, 0x00000001);
-               ram_wait(fuc, 0x137390, 0x00000002, 0x00000002, 64000);
-               ram_mask(fuc, 0x1373f4, 0x00000000, 0x00001100);
-       } else {
-               ram_mask(fuc, 0x1373f4, 0x00000000, 0x00010100);
-       }
-
-       ram_mask(fuc, 0x1373f4, 0x00000000, 0x00000010);
-}
-
-static void
-r1373f4_fini(struct nve0_ramfuc *fuc)
-{
-       struct nve0_ram *ram = container_of(fuc, typeof(*ram), fuc);
-       struct nouveau_ram_data *next = ram->base.next;
-       u8 v0 = next->bios.ramcfg_11_03_c0;
-       u8 v1 = next->bios.ramcfg_11_03_30;
-       u32 tmp;
-
-       tmp = ram_rd32(fuc, 0x1373ec) & ~0x00030000;
-       ram_wr32(fuc, 0x1373ec, tmp | (v1 << 16));
-       ram_mask(fuc, 0x1373f0, (~ram->mode & 3), 0x00000000);
-       if (ram->mode == 2) {
-               ram_mask(fuc, 0x1373f4, 0x00000003, 0x000000002);
-               ram_mask(fuc, 0x1373f4, 0x00001100, 0x000000000);
-       } else {
-               ram_mask(fuc, 0x1373f4, 0x00000003, 0x000000001);
-               ram_mask(fuc, 0x1373f4, 0x00010000, 0x000000000);
-       }
-       ram_mask(fuc, 0x10f800, 0x00000030, (v0 ^ v1) << 4);
-}
-
-static void
-nve0_ram_nuts(struct nve0_ram *ram, struct ramfuc_reg *reg,
-             u32 _mask, u32 _data, u32 _copy)
-{
-       struct nve0_fb_priv *priv = (void *)nouveau_fb(ram);
-       struct ramfuc *fuc = &ram->fuc.base;
-       u32 addr = 0x110000 + (reg->addr & 0xfff);
-       u32 mask = _mask | _copy;
-       u32 data = (_data & _mask) | (reg->data & _copy);
-       u32 i;
-
-       for (i = 0; i < 16; i++, addr += 0x1000) {
-               if (ram->pnuts & (1 << i)) {
-                       u32 prev = nv_rd32(priv, addr);
-                       u32 next = (prev & ~mask) | data;
-                       nouveau_memx_wr32(fuc->memx, addr, next);
-               }
-       }
-}
-#define ram_nuts(s,r,m,d,c)                                                    \
-       nve0_ram_nuts((s), &(s)->fuc.r_##r, (m), (d), (c))
-
-static int
-nve0_ram_calc_gddr5(struct nouveau_fb *pfb, u32 freq)
-{
-       struct nve0_ram *ram = (void *)pfb->ram;
-       struct nve0_ramfuc *fuc = &ram->fuc;
-       struct nouveau_ram_data *next = ram->base.next;
-       int vc = !next->bios.ramcfg_11_02_08;
-       int mv = !next->bios.ramcfg_11_02_04;
-       u32 mask, data;
-
-       ram_mask(fuc, 0x10f808, 0x40000000, 0x40000000);
-       ram_block(fuc);
-       ram_wr32(fuc, 0x62c000, 0x0f0f0000);
-
-       /* MR1: turn termination on early, for some reason.. */
-       if ((ram->base.mr[1] & 0x03c) != 0x030) {
-               ram_mask(fuc, mr[1], 0x03c, ram->base.mr[1] & 0x03c);
-               ram_nuts(ram, mr[1], 0x03c, ram->base.mr1_nuts & 0x03c, 0x000);
-       }
-
-       if (vc == 1 && ram_have(fuc, gpio2E)) {
-               u32 temp  = ram_mask(fuc, gpio2E, 0x3000, fuc->r_func2E[1]);
-               if (temp != ram_rd32(fuc, gpio2E)) {
-                       ram_wr32(fuc, gpiotrig, 1);
-                       ram_nsec(fuc, 20000);
-               }
-       }
-
-       ram_mask(fuc, 0x10f200, 0x00000800, 0x00000000);
-
-       nve0_ram_train(fuc, 0x01020000, 0x000c0000);
-
-       ram_wr32(fuc, 0x10f210, 0x00000000); /* REFRESH_AUTO = 0 */
-       ram_nsec(fuc, 1000);
-       ram_wr32(fuc, 0x10f310, 0x00000001); /* REFRESH */
-       ram_nsec(fuc, 1000);
-
-       ram_mask(fuc, 0x10f200, 0x80000000, 0x80000000);
-       ram_wr32(fuc, 0x10f314, 0x00000001); /* PRECHARGE */
-       ram_mask(fuc, 0x10f200, 0x80000000, 0x00000000);
-       ram_wr32(fuc, 0x10f090, 0x00000061);
-       ram_wr32(fuc, 0x10f090, 0xc000007f);
-       ram_nsec(fuc, 1000);
-
-       ram_wr32(fuc, 0x10f698, 0x00000000);
-       ram_wr32(fuc, 0x10f69c, 0x00000000);
-
-       /*XXX: there does appear to be some kind of condition here, simply
-        *     modifying these bits in the vbios from the default pl0
-        *     entries shows no change.  however, the data does appear to
-        *     be correct and may be required for the transition back
-        */
-       mask = 0x800f07e0;
-       data = 0x00030000;
-       if (ram_rd32(fuc, 0x10f978) & 0x00800000)
-               data |= 0x00040000;
-
-       if (1) {
-               data |= 0x800807e0;
-               switch (next->bios.ramcfg_11_03_c0) {
-               case 3: data &= ~0x00000040; break;
-               case 2: data &= ~0x00000100; break;
-               case 1: data &= ~0x80000000; break;
-               case 0: data &= ~0x00000400; break;
-               }
-
-               switch (next->bios.ramcfg_11_03_30) {
-               case 3: data &= ~0x00000020; break;
-               case 2: data &= ~0x00000080; break;
-               case 1: data &= ~0x00080000; break;
-               case 0: data &= ~0x00000200; break;
-               }
-       }
-
-       if (next->bios.ramcfg_11_02_80)
-               mask |= 0x03000000;
-       if (next->bios.ramcfg_11_02_40)
-               mask |= 0x00002000;
-       if (next->bios.ramcfg_11_07_10)
-               mask |= 0x00004000;
-       if (next->bios.ramcfg_11_07_08)
-               mask |= 0x00000003;
-       else {
-               mask |= 0x34000000;
-               if (ram_rd32(fuc, 0x10f978) & 0x00800000)
-                       mask |= 0x40000000;
-       }
-       ram_mask(fuc, 0x10f824, mask, data);
-
-       ram_mask(fuc, 0x132040, 0x00010000, 0x00000000);
-
-       if (ram->from == 2 && ram->mode != 2) {
-               ram_mask(fuc, 0x10f808, 0x00080000, 0x00000000);
-               ram_mask(fuc, 0x10f200, 0x18008000, 0x00008000);
-               ram_mask(fuc, 0x10f800, 0x00000000, 0x00000004);
-               ram_mask(fuc, 0x10f830, 0x00008000, 0x01040010);
-               ram_mask(fuc, 0x10f830, 0x01000000, 0x00000000);
-               r1373f4_init(fuc);
-               ram_mask(fuc, 0x1373f0, 0x00000002, 0x00000001);
-               r1373f4_fini(fuc);
-               ram_mask(fuc, 0x10f830, 0x00c00000, 0x00240001);
-       } else
-       if (ram->from != 2 && ram->mode != 2) {
-               r1373f4_init(fuc);
-               r1373f4_fini(fuc);
-       }
-
-       if (ram_have(fuc, gpioMV)) {
-               u32 temp  = ram_mask(fuc, gpioMV, 0x3000, fuc->r_funcMV[mv]);
-               if (temp != ram_rd32(fuc, gpioMV)) {
-                       ram_wr32(fuc, gpiotrig, 1);
-                       ram_nsec(fuc, 64000);
-               }
-       }
-
-       if (next->bios.ramcfg_11_02_40 ||
-           next->bios.ramcfg_11_07_10) {
-               ram_mask(fuc, 0x132040, 0x00010000, 0x00010000);
-               ram_nsec(fuc, 20000);
-       }
-
-       if (ram->from != 2 && ram->mode == 2) {
-               if (0 /*XXX: Titan */)
-                       ram_mask(fuc, 0x10f200, 0x18000000, 0x18000000);
-               ram_mask(fuc, 0x10f800, 0x00000004, 0x00000000);
-               ram_mask(fuc, 0x1373f0, 0x00000000, 0x00000002);
-               ram_mask(fuc, 0x10f830, 0x00800001, 0x00408010);
-               r1373f4_init(fuc);
-               r1373f4_fini(fuc);
-               ram_mask(fuc, 0x10f808, 0x00000000, 0x00080000);
-               ram_mask(fuc, 0x10f200, 0x00808000, 0x00800000);
-       } else
-       if (ram->from == 2 && ram->mode == 2) {
-               ram_mask(fuc, 0x10f800, 0x00000004, 0x00000000);
-               r1373f4_init(fuc);
-               r1373f4_fini(fuc);
-       }
-
-       if (ram->mode != 2) /*XXX*/ {
-               if (next->bios.ramcfg_11_07_40)
-                       ram_mask(fuc, 0x10f670, 0x80000000, 0x80000000);
-       }
-
-       ram_wr32(fuc, 0x10f65c, 0x00000011 * next->bios.rammap_11_11_0c);
-       ram_wr32(fuc, 0x10f6b8, 0x01010101 * next->bios.ramcfg_11_09);
-       ram_wr32(fuc, 0x10f6bc, 0x01010101 * next->bios.ramcfg_11_09);
-
-       if (!next->bios.ramcfg_11_07_08 && !next->bios.ramcfg_11_07_04) {
-               ram_wr32(fuc, 0x10f698, 0x01010101 * next->bios.ramcfg_11_04);
-               ram_wr32(fuc, 0x10f69c, 0x01010101 * next->bios.ramcfg_11_04);
-       } else
-       if (!next->bios.ramcfg_11_07_08) {
-               ram_wr32(fuc, 0x10f698, 0x00000000);
-               ram_wr32(fuc, 0x10f69c, 0x00000000);
-       }
-
-       if (ram->mode != 2) {
-               u32 data = 0x01000100 * next->bios.ramcfg_11_04;
-               ram_nuke(fuc, 0x10f694);
-               ram_mask(fuc, 0x10f694, 0xff00ff00, data);
-       }
-
-       if (ram->mode == 2 && next->bios.ramcfg_11_08_10)
-               data = 0x00000080;
-       else
-               data = 0x00000000;
-       ram_mask(fuc, 0x10f60c, 0x00000080, data);
-
-       mask = 0x00070000;
-       data = 0x00000000;
-       if (!next->bios.ramcfg_11_02_80)
-               data |= 0x03000000;
-       if (!next->bios.ramcfg_11_02_40)
-               data |= 0x00002000;
-       if (!next->bios.ramcfg_11_07_10)
-               data |= 0x00004000;
-       if (!next->bios.ramcfg_11_07_08)
-               data |= 0x00000003;
-       else
-               data |= 0x74000000;
-       ram_mask(fuc, 0x10f824, mask, data);
-
-       if (next->bios.ramcfg_11_01_08)
-               data = 0x00000000;
-       else
-               data = 0x00001000;
-       ram_mask(fuc, 0x10f200, 0x00001000, data);
-
-       if (ram_rd32(fuc, 0x10f670) & 0x80000000) {
-               ram_nsec(fuc, 10000);
-               ram_mask(fuc, 0x10f670, 0x80000000, 0x00000000);
-       }
-
-       if (next->bios.ramcfg_11_08_01)
-               data = 0x00100000;
-       else
-               data = 0x00000000;
-       ram_mask(fuc, 0x10f82c, 0x00100000, data);
-
-       data = 0x00000000;
-       if (next->bios.ramcfg_11_08_08)
-               data |= 0x00002000;
-       if (next->bios.ramcfg_11_08_04)
-               data |= 0x00001000;
-       if (next->bios.ramcfg_11_08_02)
-               data |= 0x00004000;
-       ram_mask(fuc, 0x10f830, 0x00007000, data);
-
-       /* PFB timing */
-       ram_mask(fuc, 0x10f248, 0xffffffff, next->bios.timing[10]);
-       ram_mask(fuc, 0x10f290, 0xffffffff, next->bios.timing[0]);
-       ram_mask(fuc, 0x10f294, 0xffffffff, next->bios.timing[1]);
-       ram_mask(fuc, 0x10f298, 0xffffffff, next->bios.timing[2]);
-       ram_mask(fuc, 0x10f29c, 0xffffffff, next->bios.timing[3]);
-       ram_mask(fuc, 0x10f2a0, 0xffffffff, next->bios.timing[4]);
-       ram_mask(fuc, 0x10f2a4, 0xffffffff, next->bios.timing[5]);
-       ram_mask(fuc, 0x10f2a8, 0xffffffff, next->bios.timing[6]);
-       ram_mask(fuc, 0x10f2ac, 0xffffffff, next->bios.timing[7]);
-       ram_mask(fuc, 0x10f2cc, 0xffffffff, next->bios.timing[8]);
-       ram_mask(fuc, 0x10f2e8, 0xffffffff, next->bios.timing[9]);
-
-       data = mask = 0x00000000;
-       if (ram->diff.ramcfg_11_08_20) {
-               if (next->bios.ramcfg_11_08_20)
-                       data |= 0x01000000;
-               mask |= 0x01000000;
-       }
-       ram_mask(fuc, 0x10f200, mask, data);
-
-       data = mask = 0x00000000;
-       if (ram->diff.ramcfg_11_02_03) {
-               data |= next->bios.ramcfg_11_02_03 << 8;
-               mask |= 0x00000300;
-       }
-       if (ram->diff.ramcfg_11_01_10) {
-               if (next->bios.ramcfg_11_01_10)
-                       data |= 0x70000000;
-               mask |= 0x70000000;
-       }
-       ram_mask(fuc, 0x10f604, mask, data);
-
-       data = mask = 0x00000000;
-       if (ram->diff.timing_20_30_07) {
-               data |= next->bios.timing_20_30_07 << 28;
-               mask |= 0x70000000;
-       }
-       if (ram->diff.ramcfg_11_01_01) {
-               if (next->bios.ramcfg_11_01_01)
-                       data |= 0x00000100;
-               mask |= 0x00000100;
-       }
-       ram_mask(fuc, 0x10f614, mask, data);
-
-       data = mask = 0x00000000;
-       if (ram->diff.timing_20_30_07) {
-               data |= next->bios.timing_20_30_07 << 28;
-               mask |= 0x70000000;
-       }
-       if (ram->diff.ramcfg_11_01_02) {
-               if (next->bios.ramcfg_11_01_02)
-                       data |= 0x00000100;
-               mask |= 0x00000100;
-       }
-       ram_mask(fuc, 0x10f610, mask, data);
-
-       mask = 0x33f00000;
-       data = 0x00000000;
-       if (!next->bios.ramcfg_11_01_04)
-               data |= 0x20200000;
-       if (!next->bios.ramcfg_11_07_80)
-               data |= 0x12800000;
-       /*XXX: see note above about there probably being some condition
-        *     for the 10f824 stuff that uses ramcfg 3...
-        */
-       if (next->bios.ramcfg_11_03_f0) {
-               if (next->bios.rammap_11_08_0c) {
-                       if (!next->bios.ramcfg_11_07_80)
-                               mask |= 0x00000020;
-                       else
-                               data |= 0x00000020;
-                       mask |= 0x00000004;
-               }
-       } else {
-               mask |= 0x40000020;
-               data |= 0x00000004;
-       }
-
-       ram_mask(fuc, 0x10f808, mask, data);
-
-       ram_wr32(fuc, 0x10f870, 0x11111111 * next->bios.ramcfg_11_03_0f);
-
-       data = mask = 0x00000000;
-       if (ram->diff.ramcfg_11_02_03) {
-               data |= next->bios.ramcfg_11_02_03;
-               mask |= 0x00000003;
-       }
-       if (ram->diff.ramcfg_11_01_10) {
-               if (next->bios.ramcfg_11_01_10)
-                       data |= 0x00000004;
-               mask |= 0x00000004;
-       }
-
-       if ((ram_mask(fuc, 0x100770, mask, data) & mask & 4) != (data & 4)) {
-               ram_mask(fuc, 0x100750, 0x00000008, 0x00000008);
-               ram_wr32(fuc, 0x100710, 0x00000000);
-               ram_wait(fuc, 0x100710, 0x80000000, 0x80000000, 200000);
-       }
-
-       data = next->bios.timing_20_30_07 << 8;
-       if (next->bios.ramcfg_11_01_01)
-               data |= 0x80000000;
-       ram_mask(fuc, 0x100778, 0x00000700, data);
-
-       ram_mask(fuc, 0x10f250, 0x000003f0, next->bios.timing_20_2c_003f << 4);
-       data = (next->bios.timing[10] & 0x7f000000) >> 24;
-       if (data < next->bios.timing_20_2c_1fc0)
-               data = next->bios.timing_20_2c_1fc0;
-       ram_mask(fuc, 0x10f24c, 0x7f000000, data << 24);
-       ram_mask(fuc, 0x10f224, 0x001f0000, next->bios.timing_20_30_f8 << 16);
-
-       ram_mask(fuc, 0x10fec4, 0x041e0f07, next->bios.timing_20_31_0800 << 26 |
-                                           next->bios.timing_20_31_0780 << 17 |
-                                           next->bios.timing_20_31_0078 << 8 |
-                                           next->bios.timing_20_31_0007);
-       ram_mask(fuc, 0x10fec8, 0x00000027, next->bios.timing_20_31_8000 << 5 |
-                                           next->bios.timing_20_31_7000);
-
-       ram_wr32(fuc, 0x10f090, 0x4000007e);
-       ram_nsec(fuc, 2000);
-       ram_wr32(fuc, 0x10f314, 0x00000001); /* PRECHARGE */
-       ram_wr32(fuc, 0x10f310, 0x00000001); /* REFRESH */
-       ram_wr32(fuc, 0x10f210, 0x80000000); /* REFRESH_AUTO = 1 */
-
-       if (next->bios.ramcfg_11_08_10 && (ram->mode == 2) /*XXX*/) {
-               u32 temp = ram_mask(fuc, 0x10f294, 0xff000000, 0x24000000);
-               nve0_ram_train(fuc, 0xbc0e0000, 0xa4010000); /*XXX*/
-               ram_nsec(fuc, 1000);
-               ram_wr32(fuc, 0x10f294, temp);
-       }
-
-       ram_mask(fuc, mr[3], 0xfff, ram->base.mr[3]);
-       ram_wr32(fuc, mr[0], ram->base.mr[0]);
-       ram_mask(fuc, mr[8], 0xfff, ram->base.mr[8]);
-       ram_nsec(fuc, 1000);
-       ram_mask(fuc, mr[1], 0xfff, ram->base.mr[1]);
-       ram_mask(fuc, mr[5], 0xfff, ram->base.mr[5] & ~0x004); /* LP3 later */
-       ram_mask(fuc, mr[6], 0xfff, ram->base.mr[6]);
-       ram_mask(fuc, mr[7], 0xfff, ram->base.mr[7]);
-
-       if (vc == 0 && ram_have(fuc, gpio2E)) {
-               u32 temp  = ram_mask(fuc, gpio2E, 0x3000, fuc->r_func2E[0]);
-               if (temp != ram_rd32(fuc, gpio2E)) {
-                       ram_wr32(fuc, gpiotrig, 1);
-                       ram_nsec(fuc, 20000);
-               }
-       }
-
-       ram_mask(fuc, 0x10f200, 0x80000000, 0x80000000);
-       ram_wr32(fuc, 0x10f318, 0x00000001); /* NOP? */
-       ram_mask(fuc, 0x10f200, 0x80000000, 0x00000000);
-       ram_nsec(fuc, 1000);
-       ram_nuts(ram, 0x10f200, 0x18808800, 0x00000000, 0x18808800);
-
-       data  = ram_rd32(fuc, 0x10f978);
-       data &= ~0x00046144;
-       data |=  0x0000000b;
-       if (!next->bios.ramcfg_11_07_08) {
-               if (!next->bios.ramcfg_11_07_04)
-                       data |= 0x0000200c;
-               else
-                       data |= 0x00000000;
-       } else {
-               data |= 0x00040044;
-       }
-       ram_wr32(fuc, 0x10f978, data);
-
-       if (ram->mode == 1) {
-               data = ram_rd32(fuc, 0x10f830) | 0x00000001;
-               ram_wr32(fuc, 0x10f830, data);
-       }
-
-       if (!next->bios.ramcfg_11_07_08) {
-               data = 0x88020000;
-               if ( next->bios.ramcfg_11_07_04)
-                       data |= 0x10000000;
-               if (!next->bios.rammap_11_08_10)
-                       data |= 0x00080000;
-       } else {
-               data = 0xa40e0000;
-       }
-       nve0_ram_train(fuc, 0xbc0f0000, data);
-       if (1) /* XXX: not always? */
-               ram_nsec(fuc, 1000);
-
-       if (ram->mode == 2) { /*XXX*/
-               ram_mask(fuc, 0x10f800, 0x00000004, 0x00000004);
-       }
-
-       /* LP3 */
-       if (ram_mask(fuc, mr[5], 0x004, ram->base.mr[5]) != ram->base.mr[5])
-               ram_nsec(fuc, 1000);
-
-       if (ram->mode != 2) {
-               ram_mask(fuc, 0x10f830, 0x01000000, 0x01000000);
-               ram_mask(fuc, 0x10f830, 0x01000000, 0x00000000);
-       }
-
-       if (next->bios.ramcfg_11_07_02)
-               nve0_ram_train(fuc, 0x80020000, 0x01000000);
-
-       ram_unblock(fuc);
-       ram_wr32(fuc, 0x62c000, 0x0f0f0f00);
-
-       if (next->bios.rammap_11_08_01)
-               data = 0x00000800;
-       else
-               data = 0x00000000;
-       ram_mask(fuc, 0x10f200, 0x00000800, data);
-       ram_nuts(ram, 0x10f200, 0x18808800, data, 0x18808800);
-       return 0;
-}
-
-/*******************************************************************************
- * DDR3
- ******************************************************************************/
-
-static int
-nve0_ram_calc_sddr3(struct nouveau_fb *pfb, u32 freq)
-{
-       struct nve0_ram *ram = (void *)pfb->ram;
-       struct nve0_ramfuc *fuc = &ram->fuc;
-       const u32 rcoef = ((  ram->P1 << 16) | (ram->N1 << 8) | ram->M1);
-       const u32 runk0 = ram->fN1 << 16;
-       const u32 runk1 = ram->fN1;
-       struct nouveau_ram_data *next = ram->base.next;
-       int vc = !next->bios.ramcfg_11_02_08;
-       int mv = !next->bios.ramcfg_11_02_04;
-       u32 mask, data;
-
-       ram_mask(fuc, 0x10f808, 0x40000000, 0x40000000);
-       ram_block(fuc);
-       ram_wr32(fuc, 0x62c000, 0x0f0f0000);
-
-       if (vc == 1 && ram_have(fuc, gpio2E)) {
-               u32 temp  = ram_mask(fuc, gpio2E, 0x3000, fuc->r_func2E[1]);
-               if (temp != ram_rd32(fuc, gpio2E)) {
-                       ram_wr32(fuc, gpiotrig, 1);
-                       ram_nsec(fuc, 20000);
-               }
-       }
-
-       ram_mask(fuc, 0x10f200, 0x00000800, 0x00000000);
-       if (next->bios.ramcfg_11_03_f0)
-               ram_mask(fuc, 0x10f808, 0x04000000, 0x04000000);
-
-       ram_wr32(fuc, 0x10f314, 0x00000001); /* PRECHARGE */
-       ram_wr32(fuc, 0x10f210, 0x00000000); /* REFRESH_AUTO = 0 */
-       ram_wr32(fuc, 0x10f310, 0x00000001); /* REFRESH */
-       ram_mask(fuc, 0x10f200, 0x80000000, 0x80000000);
-       ram_wr32(fuc, 0x10f310, 0x00000001); /* REFRESH */
-       ram_mask(fuc, 0x10f200, 0x80000000, 0x00000000);
-       ram_nsec(fuc, 1000);
-
-       ram_wr32(fuc, 0x10f090, 0x00000060);
-       ram_wr32(fuc, 0x10f090, 0xc000007e);
-
-       /*XXX: there does appear to be some kind of condition here, simply
-        *     modifying these bits in the vbios from the default pl0
-        *     entries shows no change.  however, the data does appear to
-        *     be correct and may be required for the transition back
-        */
-       mask = 0x00010000;
-       data = 0x00010000;
-
-       if (1) {
-               mask |= 0x800807e0;
-               data |= 0x800807e0;
-               switch (next->bios.ramcfg_11_03_c0) {
-               case 3: data &= ~0x00000040; break;
-               case 2: data &= ~0x00000100; break;
-               case 1: data &= ~0x80000000; break;
-               case 0: data &= ~0x00000400; break;
-               }
-
-               switch (next->bios.ramcfg_11_03_30) {
-               case 3: data &= ~0x00000020; break;
-               case 2: data &= ~0x00000080; break;
-               case 1: data &= ~0x00080000; break;
-               case 0: data &= ~0x00000200; break;
-               }
-       }
-
-       if (next->bios.ramcfg_11_02_80)
-               mask |= 0x03000000;
-       if (next->bios.ramcfg_11_02_40)
-               mask |= 0x00002000;
-       if (next->bios.ramcfg_11_07_10)
-               mask |= 0x00004000;
-       if (next->bios.ramcfg_11_07_08)
-               mask |= 0x00000003;
-       else
-               mask |= 0x14000000;
-       ram_mask(fuc, 0x10f824, mask, data);
-
-       ram_mask(fuc, 0x132040, 0x00010000, 0x00000000);
-
-       ram_mask(fuc, 0x1373f4, 0x00000000, 0x00010010);
-       data  = ram_rd32(fuc, 0x1373ec) & ~0x00030000;
-       data |= next->bios.ramcfg_11_03_30 << 16;
-       ram_wr32(fuc, 0x1373ec, data);
-       ram_mask(fuc, 0x1373f4, 0x00000003, 0x00000000);
-       ram_mask(fuc, 0x1373f4, 0x00000010, 0x00000000);
-
-       /* (re)program refpll, if required */
-       if ((ram_rd32(fuc, 0x132024) & 0xffffffff) != rcoef ||
-           (ram_rd32(fuc, 0x132034) & 0x0000ffff) != runk1) {
-               ram_mask(fuc, 0x132000, 0x00000001, 0x00000000);
-               ram_mask(fuc, 0x132020, 0x00000001, 0x00000000);
-               ram_wr32(fuc, 0x137320, 0x00000000);
-               ram_mask(fuc, 0x132030, 0xffff0000, runk0);
-               ram_mask(fuc, 0x132034, 0x0000ffff, runk1);
-               ram_wr32(fuc, 0x132024, rcoef);
-               ram_mask(fuc, 0x132028, 0x00080000, 0x00080000);
-               ram_mask(fuc, 0x132020, 0x00000001, 0x00000001);
-               ram_wait(fuc, 0x137390, 0x00020000, 0x00020000, 64000);
-               ram_mask(fuc, 0x132028, 0x00080000, 0x00000000);
-       }
-
-       ram_mask(fuc, 0x1373f4, 0x00000010, 0x00000010);
-       ram_mask(fuc, 0x1373f4, 0x00000003, 0x00000001);
-       ram_mask(fuc, 0x1373f4, 0x00010000, 0x00000000);
-
-       if (ram_have(fuc, gpioMV)) {
-               u32 temp  = ram_mask(fuc, gpioMV, 0x3000, fuc->r_funcMV[mv]);
-               if (temp != ram_rd32(fuc, gpioMV)) {
-                       ram_wr32(fuc, gpiotrig, 1);
-                       ram_nsec(fuc, 64000);
-               }
-       }
-
-       if (next->bios.ramcfg_11_02_40 ||
-           next->bios.ramcfg_11_07_10) {
-               ram_mask(fuc, 0x132040, 0x00010000, 0x00010000);
-               ram_nsec(fuc, 20000);
-       }
-
-       if (ram->mode != 2) /*XXX*/ {
-               if (next->bios.ramcfg_11_07_40)
-                       ram_mask(fuc, 0x10f670, 0x80000000, 0x80000000);
-       }
-
-       ram_wr32(fuc, 0x10f65c, 0x00000011 * next->bios.rammap_11_11_0c);
-       ram_wr32(fuc, 0x10f6b8, 0x01010101 * next->bios.ramcfg_11_09);
-       ram_wr32(fuc, 0x10f6bc, 0x01010101 * next->bios.ramcfg_11_09);
-
-       mask = 0x00010000;
-       data = 0x00000000;
-       if (!next->bios.ramcfg_11_02_80)
-               data |= 0x03000000;
-       if (!next->bios.ramcfg_11_02_40)
-               data |= 0x00002000;
-       if (!next->bios.ramcfg_11_07_10)
-               data |= 0x00004000;
-       if (!next->bios.ramcfg_11_07_08)
-               data |= 0x00000003;
-       else
-               data |= 0x14000000;
-       ram_mask(fuc, 0x10f824, mask, data);
-       ram_nsec(fuc, 1000);
-
-       if (next->bios.ramcfg_11_08_01)
-               data = 0x00100000;
-       else
-               data = 0x00000000;
-       ram_mask(fuc, 0x10f82c, 0x00100000, data);
-
-       /* PFB timing */
-       ram_mask(fuc, 0x10f248, 0xffffffff, next->bios.timing[10]);
-       ram_mask(fuc, 0x10f290, 0xffffffff, next->bios.timing[0]);
-       ram_mask(fuc, 0x10f294, 0xffffffff, next->bios.timing[1]);
-       ram_mask(fuc, 0x10f298, 0xffffffff, next->bios.timing[2]);
-       ram_mask(fuc, 0x10f29c, 0xffffffff, next->bios.timing[3]);
-       ram_mask(fuc, 0x10f2a0, 0xffffffff, next->bios.timing[4]);
-       ram_mask(fuc, 0x10f2a4, 0xffffffff, next->bios.timing[5]);
-       ram_mask(fuc, 0x10f2a8, 0xffffffff, next->bios.timing[6]);
-       ram_mask(fuc, 0x10f2ac, 0xffffffff, next->bios.timing[7]);
-       ram_mask(fuc, 0x10f2cc, 0xffffffff, next->bios.timing[8]);
-       ram_mask(fuc, 0x10f2e8, 0xffffffff, next->bios.timing[9]);
-
-       mask = 0x33f00000;
-       data = 0x00000000;
-       if (!next->bios.ramcfg_11_01_04)
-               data |= 0x20200000;
-       if (!next->bios.ramcfg_11_07_80)
-               data |= 0x12800000;
-       /*XXX: see note above about there probably being some condition
-        *     for the 10f824 stuff that uses ramcfg 3...
-        */
-       if (next->bios.ramcfg_11_03_f0) {
-               if (next->bios.rammap_11_08_0c) {
-                       if (!next->bios.ramcfg_11_07_80)
-                               mask |= 0x00000020;
-                       else
-                               data |= 0x00000020;
-                       mask |= 0x08000004;
-               }
-               data |= 0x04000000;
-       } else {
-               mask |= 0x44000020;
-               data |= 0x08000004;
-       }
-
-       ram_mask(fuc, 0x10f808, mask, data);
-
-       ram_wr32(fuc, 0x10f870, 0x11111111 * next->bios.ramcfg_11_03_0f);
-
-       ram_mask(fuc, 0x10f250, 0x000003f0, next->bios.timing_20_2c_003f << 4);
-
-       data = (next->bios.timing[10] & 0x7f000000) >> 24;
-       if (data < next->bios.timing_20_2c_1fc0)
-               data = next->bios.timing_20_2c_1fc0;
-       ram_mask(fuc, 0x10f24c, 0x7f000000, data << 24);
-
-       ram_mask(fuc, 0x10f224, 0x001f0000, next->bios.timing_20_30_f8 << 16);
-
-       ram_wr32(fuc, 0x10f090, 0x4000007f);
-       ram_nsec(fuc, 1000);
-
-       ram_wr32(fuc, 0x10f314, 0x00000001); /* PRECHARGE */
-       ram_wr32(fuc, 0x10f310, 0x00000001); /* REFRESH */
-       ram_wr32(fuc, 0x10f210, 0x80000000); /* REFRESH_AUTO = 1 */
-       ram_nsec(fuc, 1000);
-
-       ram_nuke(fuc, mr[0]);
-       ram_mask(fuc, mr[0], 0x100, 0x100);
-       ram_mask(fuc, mr[0], 0x100, 0x000);
-
-       ram_mask(fuc, mr[2], 0xfff, ram->base.mr[2]);
-       ram_wr32(fuc, mr[0], ram->base.mr[0]);
-       ram_nsec(fuc, 1000);
-
-       ram_nuke(fuc, mr[0]);
-       ram_mask(fuc, mr[0], 0x100, 0x100);
-       ram_mask(fuc, mr[0], 0x100, 0x000);
-
-       if (vc == 0 && ram_have(fuc, gpio2E)) {
-               u32 temp  = ram_mask(fuc, gpio2E, 0x3000, fuc->r_func2E[0]);
-               if (temp != ram_rd32(fuc, gpio2E)) {
-                       ram_wr32(fuc, gpiotrig, 1);
-                       ram_nsec(fuc, 20000);
-               }
-       }
-
-       if (ram->mode != 2) {
-               ram_mask(fuc, 0x10f830, 0x01000000, 0x01000000);
-               ram_mask(fuc, 0x10f830, 0x01000000, 0x00000000);
-       }
-
-       ram_mask(fuc, 0x10f200, 0x80000000, 0x80000000);
-       ram_wr32(fuc, 0x10f318, 0x00000001); /* NOP? */
-       ram_mask(fuc, 0x10f200, 0x80000000, 0x00000000);
-       ram_nsec(fuc, 1000);
-
-       ram_unblock(fuc);
-       ram_wr32(fuc, 0x62c000, 0x0f0f0f00);
-
-       if (next->bios.rammap_11_08_01)
-               data = 0x00000800;
-       else
-               data = 0x00000000;
-       ram_mask(fuc, 0x10f200, 0x00000800, data);
-       return 0;
-}
-
-/*******************************************************************************
- * main hooks
- ******************************************************************************/
-
-static int
-nve0_ram_calc_data(struct nouveau_fb *pfb, u32 khz,
-                  struct nouveau_ram_data *data)
-{
-       struct nve0_ram *ram = (void *)pfb->ram;
-       struct nouveau_ram_data *cfg;
-       u32 mhz = khz / 1000;
-
-       list_for_each_entry(cfg, &ram->cfg, head) {
-               if (mhz >= cfg->bios.rammap_min &&
-                   mhz <= cfg->bios.rammap_max) {
-                       *data = *cfg;
-                       data->freq = khz;
-                       return 0;
-               }
-       }
-
-       nv_error(ram, "ramcfg data for %dMHz not found\n", mhz);
-       return -EINVAL;
-}
-
-static int
-nve0_ram_calc_xits(struct nouveau_fb *pfb, struct nouveau_ram_data *next)
-{
-       struct nve0_ram *ram = (void *)pfb->ram;
-       struct nve0_ramfuc *fuc = &ram->fuc;
-       int refclk, i;
-       int ret;
-
-       ret = ram_init(fuc, pfb);
-       if (ret)
-               return ret;
-
-       ram->mode = (next->freq > fuc->refpll.vco1.max_freq) ? 2 : 1;
-       ram->from = ram_rd32(fuc, 0x1373f4) & 0x0000000f;
-
-       /* XXX: this is *not* what nvidia do.  on fermi nvidia generally
-        * select, based on some unknown condition, one of the two possible
-        * reference frequencies listed in the vbios table for mempll and
-        * program refpll to that frequency.
-        *
-        * so far, i've seen very weird values being chosen by nvidia on
-        * kepler boards, no idea how/why they're chosen.
-        */
-       refclk = next->freq;
-       if (ram->mode == 2)
-               refclk = fuc->mempll.refclk;
-
-       /* calculate refpll coefficients */
-       ret = nva3_pll_calc(nv_subdev(pfb), &fuc->refpll, refclk, &ram->N1,
-                          &ram->fN1, &ram->M1, &ram->P1);
-       fuc->mempll.refclk = ret;
-       if (ret <= 0) {
-               nv_error(pfb, "unable to calc refpll\n");
-               return -EINVAL;
-       }
-
-       /* calculate mempll coefficients, if we're using it */
-       if (ram->mode == 2) {
-               /* post-divider doesn't work... the reg takes the values but
-                * appears to completely ignore it.  there *is* a bit at
-                * bit 28 that appears to divide the clock by 2 if set.
-                */
-               fuc->mempll.min_p = 1;
-               fuc->mempll.max_p = 2;
-
-               ret = nva3_pll_calc(nv_subdev(pfb), &fuc->mempll, next->freq,
-                                  &ram->N2, NULL, &ram->M2, &ram->P2);
-               if (ret <= 0) {
-                       nv_error(pfb, "unable to calc mempll\n");
-                       return -EINVAL;
-               }
-       }
-
-       for (i = 0; i < ARRAY_SIZE(fuc->r_mr); i++) {
-               if (ram_have(fuc, mr[i]))
-                       ram->base.mr[i] = ram_rd32(fuc, mr[i]);
-       }
-       ram->base.freq = next->freq;
-
-       switch (ram->base.type) {
-       case NV_MEM_TYPE_DDR3:
-               ret = nouveau_sddr3_calc(&ram->base);
-               if (ret == 0)
-                       ret = nve0_ram_calc_sddr3(pfb, next->freq);
-               break;
-       case NV_MEM_TYPE_GDDR5:
-               ret = nouveau_gddr5_calc(&ram->base, ram->pnuts != 0);
-               if (ret == 0)
-                       ret = nve0_ram_calc_gddr5(pfb, next->freq);
-               break;
-       default:
-               ret = -ENOSYS;
-               break;
-       }
-
-       return ret;
-}
-
-static int
-nve0_ram_calc(struct nouveau_fb *pfb, u32 freq)
-{
-       struct nouveau_clock *clk = nouveau_clock(pfb);
-       struct nve0_ram *ram = (void *)pfb->ram;
-       struct nouveau_ram_data *xits = &ram->base.xition;
-       struct nouveau_ram_data *copy;
-       int ret;
-
-       if (ram->base.next == NULL) {
-               ret = nve0_ram_calc_data(pfb, clk->read(clk, nv_clk_src_mem),
-                                       &ram->base.former);
-               if (ret)
-                       return ret;
-
-               ret = nve0_ram_calc_data(pfb, freq, &ram->base.target);
-               if (ret)
-                       return ret;
-
-               if (ram->base.target.freq < ram->base.former.freq) {
-                       *xits = ram->base.target;
-                       copy = &ram->base.former;
-               } else {
-                       *xits = ram->base.former;
-                       copy = &ram->base.target;
-               }
-
-               xits->bios.ramcfg_11_02_04 = copy->bios.ramcfg_11_02_04;
-               xits->bios.ramcfg_11_02_03 = copy->bios.ramcfg_11_02_03;
-               xits->bios.timing_20_30_07 = copy->bios.timing_20_30_07;
-
-               ram->base.next = &ram->base.target;
-               if (memcmp(xits, &ram->base.former, sizeof(xits->bios)))
-                       ram->base.next = &ram->base.xition;
-       } else {
-               BUG_ON(ram->base.next != &ram->base.xition);
-               ram->base.next = &ram->base.target;
-       }
-
-       return nve0_ram_calc_xits(pfb, ram->base.next);
-}
-
-static void
-nve0_ram_prog_0(struct nouveau_fb *pfb, u32 freq)
-{
-       struct nve0_ram *ram = (void *)pfb->ram;
-       struct nouveau_ram_data *cfg;
-       u32 mhz = freq / 1000;
-       u32 mask, data;
-
-       list_for_each_entry(cfg, &ram->cfg, head) {
-               if (mhz >= cfg->bios.rammap_min &&
-                   mhz <= cfg->bios.rammap_max)
-                       break;
-       }
-
-       if (&cfg->head == &ram->cfg)
-               return;
-
-       if (mask = 0, data = 0, ram->diff.rammap_11_0a_03fe) {
-               data |= cfg->bios.rammap_11_0a_03fe << 12;
-               mask |= 0x001ff000;
-       }
-       if (ram->diff.rammap_11_09_01ff) {
-               data |= cfg->bios.rammap_11_09_01ff;
-               mask |= 0x000001ff;
-       }
-       nv_mask(pfb, 0x10f468, mask, data);
-
-       if (mask = 0, data = 0, ram->diff.rammap_11_0a_0400) {
-               data |= cfg->bios.rammap_11_0a_0400;
-               mask |= 0x00000001;
-       }
-       nv_mask(pfb, 0x10f420, mask, data);
-
-       if (mask = 0, data = 0, ram->diff.rammap_11_0a_0800) {
-               data |= cfg->bios.rammap_11_0a_0800;
-               mask |= 0x00000001;
-       }
-       nv_mask(pfb, 0x10f430, mask, data);
-
-       if (mask = 0, data = 0, ram->diff.rammap_11_0b_01f0) {
-               data |= cfg->bios.rammap_11_0b_01f0;
-               mask |= 0x0000001f;
-       }
-       nv_mask(pfb, 0x10f400, mask, data);
-
-       if (mask = 0, data = 0, ram->diff.rammap_11_0b_0200) {
-               data |= cfg->bios.rammap_11_0b_0200 << 9;
-               mask |= 0x00000200;
-       }
-       nv_mask(pfb, 0x10f410, mask, data);
-
-       if (mask = 0, data = 0, ram->diff.rammap_11_0d) {
-               data |= cfg->bios.rammap_11_0d << 16;
-               mask |= 0x00ff0000;
-       }
-       if (ram->diff.rammap_11_0f) {
-               data |= cfg->bios.rammap_11_0f << 8;
-               mask |= 0x0000ff00;
-       }
-       nv_mask(pfb, 0x10f440, mask, data);
-
-       if (mask = 0, data = 0, ram->diff.rammap_11_0e) {
-               data |= cfg->bios.rammap_11_0e << 8;
-               mask |= 0x0000ff00;
-       }
-       if (ram->diff.rammap_11_0b_0800) {
-               data |= cfg->bios.rammap_11_0b_0800 << 7;
-               mask |= 0x00000080;
-       }
-       if (ram->diff.rammap_11_0b_0400) {
-               data |= cfg->bios.rammap_11_0b_0400 << 5;
-               mask |= 0x00000020;
-       }
-       nv_mask(pfb, 0x10f444, mask, data);
-}
-
-static int
-nve0_ram_prog(struct nouveau_fb *pfb)
-{
-       struct nouveau_device *device = nv_device(pfb);
-       struct nve0_ram *ram = (void *)pfb->ram;
-       struct nve0_ramfuc *fuc = &ram->fuc;
-       struct nouveau_ram_data *next = ram->base.next;
-
-       if (!nouveau_boolopt(device->cfgopt, "NvMemExec", true)) {
-               ram_exec(fuc, false);
-               return (ram->base.next == &ram->base.xition);
-       }
-
-       nve0_ram_prog_0(pfb, 1000);
-       ram_exec(fuc, true);
-       nve0_ram_prog_0(pfb, next->freq);
-
-       return (ram->base.next == &ram->base.xition);
-}
-
-static void
-nve0_ram_tidy(struct nouveau_fb *pfb)
-{
-       struct nve0_ram *ram = (void *)pfb->ram;
-       struct nve0_ramfuc *fuc = &ram->fuc;
-       ram->base.next = NULL;
-       ram_exec(fuc, false);
-}
-
-struct nve0_ram_train {
-       u16 mask;
-       struct nvbios_M0209S remap;
-       struct nvbios_M0209S type00;
-       struct nvbios_M0209S type01;
-       struct nvbios_M0209S type04;
-       struct nvbios_M0209S type06;
-       struct nvbios_M0209S type07;
-       struct nvbios_M0209S type08;
-       struct nvbios_M0209S type09;
-};
-
-static int
-nve0_ram_train_type(struct nouveau_fb *pfb, int i, u8 ramcfg,
-                   struct nve0_ram_train *train)
-{
-       struct nouveau_bios *bios = nouveau_bios(pfb);
-       struct nvbios_M0205E M0205E;
-       struct nvbios_M0205S M0205S;
-       struct nvbios_M0209E M0209E;
-       struct nvbios_M0209S *remap = &train->remap;
-       struct nvbios_M0209S *value;
-       u8  ver, hdr, cnt, len;
-       u32 data;
-
-       /* determine type of data for this index */
-       if (!(data = nvbios_M0205Ep(bios, i, &ver, &hdr, &cnt, &len, &M0205E)))
-               return -ENOENT;
-
-       switch (M0205E.type) {
-       case 0x00: value = &train->type00; break;
-       case 0x01: value = &train->type01; break;
-       case 0x04: value = &train->type04; break;
-       case 0x06: value = &train->type06; break;
-       case 0x07: value = &train->type07; break;
-       case 0x08: value = &train->type08; break;
-       case 0x09: value = &train->type09; break;
-       default:
-               return 0;
-       }
-
-       /* training data index determined by ramcfg strap */
-       if (!(data = nvbios_M0205Sp(bios, i, ramcfg, &ver, &hdr, &M0205S)))
-               return -EINVAL;
-       i = M0205S.data;
-
-       /* training data format information */
-       if (!(data = nvbios_M0209Ep(bios, i, &ver, &hdr, &cnt, &len, &M0209E)))
-               return -EINVAL;
-
-       /* ... and the raw data */
-       if (!(data = nvbios_M0209Sp(bios, i, 0, &ver, &hdr, value)))
-               return -EINVAL;
-
-       if (M0209E.v02_07 == 2) {
-               /* of course! why wouldn't we have a pointer to another entry
-                * in the same table, and use the first one as an array of
-                * remap indices...
-                */
-               if (!(data = nvbios_M0209Sp(bios, M0209E.v03, 0, &ver, &hdr,
-                                           remap)))
-                       return -EINVAL;
-
-               for (i = 0; i < ARRAY_SIZE(value->data); i++)
-                       value->data[i] = remap->data[value->data[i]];
-       } else
-       if (M0209E.v02_07 != 1)
-               return -EINVAL;
-
-       train->mask |= 1 << M0205E.type;
-       return 0;
-}
-
-static int
-nve0_ram_train_init_0(struct nouveau_fb *pfb, struct nve0_ram_train *train)
-{
-       int i, j;
-
-       if ((train->mask & 0x03d3) != 0x03d3) {
-               nv_warn(pfb, "missing link training data\n");
-               return -EINVAL;
-       }
-
-       for (i = 0; i < 0x30; i++) {
-               for (j = 0; j < 8; j += 4) {
-                       nv_wr32(pfb, 0x10f968 + j, 0x00000000 | (i << 8));
-                       nv_wr32(pfb, 0x10f920 + j, 0x00000000 |
-                                                  train->type08.data[i] << 4 |
-                                                  train->type06.data[i]);
-                       nv_wr32(pfb, 0x10f918 + j, train->type00.data[i]);
-                       nv_wr32(pfb, 0x10f920 + j, 0x00000100 |
-                                                  train->type09.data[i] << 4 |
-                                                  train->type07.data[i]);
-                       nv_wr32(pfb, 0x10f918 + j, train->type01.data[i]);
-               }
-       }
-
-       for (j = 0; j < 8; j += 4) {
-               for (i = 0; i < 0x100; i++) {
-                       nv_wr32(pfb, 0x10f968 + j, i);
-                       nv_wr32(pfb, 0x10f900 + j, train->type04.data[i]);
-               }
-       }
-
-       return 0;
-}
-
-static int
-nve0_ram_train_init(struct nouveau_fb *pfb)
-{
-       u8 ramcfg = nvbios_ramcfg_index(nv_subdev(pfb));
-       struct nve0_ram_train *train;
-       int ret = -ENOMEM, i;
-
-       if ((train = kzalloc(sizeof(*train), GFP_KERNEL))) {
-               for (i = 0; i < 0x100; i++) {
-                       ret = nve0_ram_train_type(pfb, i, ramcfg, train);
-                       if (ret && ret != -ENOENT)
-                               break;
-               }
-       }
-
-       switch (pfb->ram->type) {
-       case NV_MEM_TYPE_GDDR5:
-               ret = nve0_ram_train_init_0(pfb, train);
-               break;
-       default:
-               ret = 0;
-               break;
-       }
-
-       kfree(train);
-       return ret;
-}
-
-int
-nve0_ram_init(struct nouveau_object *object)
-{
-       struct nouveau_fb *pfb = (void *)object->parent;
-       struct nve0_ram *ram   = (void *)object;
-       struct nouveau_bios *bios = nouveau_bios(pfb);
-       u8  ver, hdr, cnt, len, snr, ssz;
-       u32 data, save;
-       int ret, i;
-
-       ret = nouveau_ram_init(&ram->base);
-       if (ret)
-               return ret;
-
-       /* run a bunch of tables from rammap table.  there's actually
-        * individual pointers for each rammap entry too, but, nvidia
-        * seem to just run the last two entries' scripts early on in
-        * their init, and never again.. we'll just run 'em all once
-        * for now.
-        *
-        * i strongly suspect that each script is for a separate mode
-        * (likely selected by 0x10f65c's lower bits?), and the
-        * binary driver skips the one that's already been setup by
-        * the init tables.
-        */
-       data = nvbios_rammapTe(bios, &ver, &hdr, &cnt, &len, &snr, &ssz);
-       if (!data || hdr < 0x15)
-               return -EINVAL;
-
-       cnt  = nv_ro08(bios, data + 0x14); /* guess at count */
-       data = nv_ro32(bios, data + 0x10); /* guess u32... */
-       save = nv_rd32(pfb, 0x10f65c) & 0x000000f0;
-       for (i = 0; i < cnt; i++, data += 4) {
-               if (i != save >> 4) {
-                       nv_mask(pfb, 0x10f65c, 0x000000f0, i << 4);
-                       nvbios_exec(&(struct nvbios_init) {
-                                       .subdev = nv_subdev(pfb),
-                                       .bios = bios,
-                                       .offset = nv_ro32(bios, data),
-                                       .execute = 1,
-                                   });
-               }
-       }
-       nv_mask(pfb, 0x10f65c, 0x000000f0, save);
-       nv_mask(pfb, 0x10f584, 0x11000000, 0x00000000);
-       nv_wr32(pfb, 0x10ecc0, 0xffffffff);
-       nv_mask(pfb, 0x10f160, 0x00000010, 0x00000010);
-
-       return nve0_ram_train_init(pfb);
-}
-
-static int
-nve0_ram_ctor_data(struct nve0_ram *ram, u8 ramcfg, int i)
-{
-       struct nouveau_fb *pfb = (void *)nv_object(ram)->parent;
-       struct nouveau_bios *bios = nouveau_bios(pfb);
-       struct nouveau_ram_data *cfg;
-       struct nvbios_ramcfg *d = &ram->diff;
-       struct nvbios_ramcfg *p, *n;
-       u8  ver, hdr, cnt, len;
-       u32 data;
-       int ret;
-
-       if (!(cfg = kmalloc(sizeof(*cfg), GFP_KERNEL)))
-               return -ENOMEM;
-       p = &list_last_entry(&ram->cfg, typeof(*cfg), head)->bios;
-       n = &cfg->bios;
-
-       /* memory config data for a range of target frequencies */
-       data = nvbios_rammapEp(bios, i, &ver, &hdr, &cnt, &len, &cfg->bios);
-       if (ret = -ENOENT, !data)
-               goto done;
-       if (ret = -ENOSYS, ver != 0x11 || hdr < 0x12)
-               goto done;
-
-       /* ... and a portion specific to the attached memory */
-       data = nvbios_rammapSp(bios, data, ver, hdr, cnt, len, ramcfg,
-                              &ver, &hdr, &cfg->bios);
-       if (ret = -EINVAL, !data)
-               goto done;
-       if (ret = -ENOSYS, ver != 0x11 || hdr < 0x0a)
-               goto done;
-
-       /* lookup memory timings, if bios says they're present */
-       if (cfg->bios.ramcfg_timing != 0xff) {
-               data = nvbios_timingEp(bios, cfg->bios.ramcfg_timing,
-                                      &ver, &hdr, &cnt, &len,
-                                      &cfg->bios);
-               if (ret = -EINVAL, !data)
-                       goto done;
-               if (ret = -ENOSYS, ver != 0x20 || hdr < 0x33)
-                       goto done;
-       }
-
-       list_add_tail(&cfg->head, &ram->cfg);
-       if (ret = 0, i == 0)
-               goto done;
-
-       d->rammap_11_0a_03fe |= p->rammap_11_0a_03fe != n->rammap_11_0a_03fe;
-       d->rammap_11_09_01ff |= p->rammap_11_09_01ff != n->rammap_11_09_01ff;
-       d->rammap_11_0a_0400 |= p->rammap_11_0a_0400 != n->rammap_11_0a_0400;
-       d->rammap_11_0a_0800 |= p->rammap_11_0a_0800 != n->rammap_11_0a_0800;
-       d->rammap_11_0b_01f0 |= p->rammap_11_0b_01f0 != n->rammap_11_0b_01f0;
-       d->rammap_11_0b_0200 |= p->rammap_11_0b_0200 != n->rammap_11_0b_0200;
-       d->rammap_11_0d |= p->rammap_11_0d != n->rammap_11_0d;
-       d->rammap_11_0f |= p->rammap_11_0f != n->rammap_11_0f;
-       d->rammap_11_0e |= p->rammap_11_0e != n->rammap_11_0e;
-       d->rammap_11_0b_0800 |= p->rammap_11_0b_0800 != n->rammap_11_0b_0800;
-       d->rammap_11_0b_0400 |= p->rammap_11_0b_0400 != n->rammap_11_0b_0400;
-       d->ramcfg_11_01_01 |= p->ramcfg_11_01_01 != n->ramcfg_11_01_01;
-       d->ramcfg_11_01_02 |= p->ramcfg_11_01_02 != n->ramcfg_11_01_02;
-       d->ramcfg_11_01_10 |= p->ramcfg_11_01_10 != n->ramcfg_11_01_10;
-       d->ramcfg_11_02_03 |= p->ramcfg_11_02_03 != n->ramcfg_11_02_03;
-       d->ramcfg_11_08_20 |= p->ramcfg_11_08_20 != n->ramcfg_11_08_20;
-       d->timing_20_30_07 |= p->timing_20_30_07 != n->timing_20_30_07;
-done:
-       if (ret)
-               kfree(cfg);
-       return ret;
-}
-
-static void
-nve0_ram_dtor(struct nouveau_object *object)
-{
-       struct nve0_ram *ram = (void *)object;
-       struct nouveau_ram_data *cfg, *tmp;
-
-       list_for_each_entry_safe(cfg, tmp, &ram->cfg, head) {
-               kfree(cfg);
-       }
-
-       nouveau_ram_destroy(&ram->base);
-}
-
-static int
-nve0_ram_ctor(struct nouveau_object *parent, struct nouveau_object *engine,
-             struct nouveau_oclass *oclass, void *data, u32 size,
-             struct nouveau_object **pobject)
-{
-       struct nouveau_fb *pfb = nouveau_fb(parent);
-       struct nouveau_bios *bios = nouveau_bios(pfb);
-       struct nouveau_gpio *gpio = nouveau_gpio(pfb);
-       struct dcb_gpio_func func;
-       struct nve0_ram *ram;
-       int ret, i;
-       u8  ramcfg = nvbios_ramcfg_index(nv_subdev(pfb));
-       u32 tmp;
-
-       ret = nvc0_ram_create(parent, engine, oclass, 0x022554, &ram);
-       *pobject = nv_object(ram);
-       if (ret)
-               return ret;
-
-       INIT_LIST_HEAD(&ram->cfg);
-
-       switch (ram->base.type) {
-       case NV_MEM_TYPE_DDR3:
-       case NV_MEM_TYPE_GDDR5:
-               ram->base.calc = nve0_ram_calc;
-               ram->base.prog = nve0_ram_prog;
-               ram->base.tidy = nve0_ram_tidy;
-               break;
-       default:
-               nv_warn(pfb, "reclocking of this RAM type is unsupported\n");
-               break;
-       }
-
-       /* calculate a mask of differently configured memory partitions,
-        * because, of course reclocking wasn't complicated enough
-        * already without having to treat some of them differently to
-        * the others....
-        */
-       ram->parts = nv_rd32(pfb, 0x022438);
-       ram->pmask = nv_rd32(pfb, 0x022554);
-       ram->pnuts = 0;
-       for (i = 0, tmp = 0; i < ram->parts; i++) {
-               if (!(ram->pmask & (1 << i))) {
-                       u32 cfg1 = nv_rd32(pfb, 0x110204 + (i * 0x1000));
-                       if (tmp && tmp != cfg1) {
-                               ram->pnuts |= (1 << i);
-                               continue;
-                       }
-                       tmp = cfg1;
-               }
-       }
-
-       /* parse bios data for all rammap table entries up-front, and
-        * build information on whether certain fields differ between
-        * any of the entries.
-        *
-        * the binary driver appears to completely ignore some fields
-        * when all entries contain the same value.  at first, it was
-        * hoped that these were mere optimisations and the bios init
-        * tables had configured as per the values here, but there is
-        * evidence now to suggest that this isn't the case and we do
-        * need to treat this condition as a "don't touch" indicator.
-        */
-       for (i = 0; !ret; i++) {
-               ret = nve0_ram_ctor_data(ram, ramcfg, i);
-               if (ret && ret != -ENOENT) {
-                       nv_error(pfb, "failed to parse ramcfg data\n");
-                       return ret;
-               }
-       }
-
-       /* parse bios data for both pll's */
-       ret = nvbios_pll_parse(bios, 0x0c, &ram->fuc.refpll);
-       if (ret) {
-               nv_error(pfb, "mclk refpll data not found\n");
-               return ret;
-       }
-
-       ret = nvbios_pll_parse(bios, 0x04, &ram->fuc.mempll);
-       if (ret) {
-               nv_error(pfb, "mclk pll data not found\n");
-               return ret;
-       }
-
-       /* lookup memory voltage gpios */
-       ret = gpio->find(gpio, 0, 0x18, DCB_GPIO_UNUSED, &func);
-       if (ret == 0) {
-               ram->fuc.r_gpioMV = ramfuc_reg(0x00d610 + (func.line * 0x04));
-               ram->fuc.r_funcMV[0] = (func.log[0] ^ 2) << 12;
-               ram->fuc.r_funcMV[1] = (func.log[1] ^ 2) << 12;
-       }
-
-       ret = gpio->find(gpio, 0, 0x2e, DCB_GPIO_UNUSED, &func);
-       if (ret == 0) {
-               ram->fuc.r_gpio2E = ramfuc_reg(0x00d610 + (func.line * 0x04));
-               ram->fuc.r_func2E[0] = (func.log[0] ^ 2) << 12;
-               ram->fuc.r_func2E[1] = (func.log[1] ^ 2) << 12;
-       }
-
-       ram->fuc.r_gpiotrig = ramfuc_reg(0x00d604);
-
-       ram->fuc.r_0x132020 = ramfuc_reg(0x132020);
-       ram->fuc.r_0x132028 = ramfuc_reg(0x132028);
-       ram->fuc.r_0x132024 = ramfuc_reg(0x132024);
-       ram->fuc.r_0x132030 = ramfuc_reg(0x132030);
-       ram->fuc.r_0x132034 = ramfuc_reg(0x132034);
-       ram->fuc.r_0x132000 = ramfuc_reg(0x132000);
-       ram->fuc.r_0x132004 = ramfuc_reg(0x132004);
-       ram->fuc.r_0x132040 = ramfuc_reg(0x132040);
-
-       ram->fuc.r_0x10f248 = ramfuc_reg(0x10f248);
-       ram->fuc.r_0x10f290 = ramfuc_reg(0x10f290);
-       ram->fuc.r_0x10f294 = ramfuc_reg(0x10f294);
-       ram->fuc.r_0x10f298 = ramfuc_reg(0x10f298);
-       ram->fuc.r_0x10f29c = ramfuc_reg(0x10f29c);
-       ram->fuc.r_0x10f2a0 = ramfuc_reg(0x10f2a0);
-       ram->fuc.r_0x10f2a4 = ramfuc_reg(0x10f2a4);
-       ram->fuc.r_0x10f2a8 = ramfuc_reg(0x10f2a8);
-       ram->fuc.r_0x10f2ac = ramfuc_reg(0x10f2ac);
-       ram->fuc.r_0x10f2cc = ramfuc_reg(0x10f2cc);
-       ram->fuc.r_0x10f2e8 = ramfuc_reg(0x10f2e8);
-       ram->fuc.r_0x10f250 = ramfuc_reg(0x10f250);
-       ram->fuc.r_0x10f24c = ramfuc_reg(0x10f24c);
-       ram->fuc.r_0x10fec4 = ramfuc_reg(0x10fec4);
-       ram->fuc.r_0x10fec8 = ramfuc_reg(0x10fec8);
-       ram->fuc.r_0x10f604 = ramfuc_reg(0x10f604);
-       ram->fuc.r_0x10f614 = ramfuc_reg(0x10f614);
-       ram->fuc.r_0x10f610 = ramfuc_reg(0x10f610);
-       ram->fuc.r_0x100770 = ramfuc_reg(0x100770);
-       ram->fuc.r_0x100778 = ramfuc_reg(0x100778);
-       ram->fuc.r_0x10f224 = ramfuc_reg(0x10f224);
-
-       ram->fuc.r_0x10f870 = ramfuc_reg(0x10f870);
-       ram->fuc.r_0x10f698 = ramfuc_reg(0x10f698);
-       ram->fuc.r_0x10f694 = ramfuc_reg(0x10f694);
-       ram->fuc.r_0x10f6b8 = ramfuc_reg(0x10f6b8);
-       ram->fuc.r_0x10f808 = ramfuc_reg(0x10f808);
-       ram->fuc.r_0x10f670 = ramfuc_reg(0x10f670);
-       ram->fuc.r_0x10f60c = ramfuc_reg(0x10f60c);
-       ram->fuc.r_0x10f830 = ramfuc_reg(0x10f830);
-       ram->fuc.r_0x1373ec = ramfuc_reg(0x1373ec);
-       ram->fuc.r_0x10f800 = ramfuc_reg(0x10f800);
-       ram->fuc.r_0x10f82c = ramfuc_reg(0x10f82c);
-
-       ram->fuc.r_0x10f978 = ramfuc_reg(0x10f978);
-       ram->fuc.r_0x10f910 = ramfuc_reg(0x10f910);
-       ram->fuc.r_0x10f914 = ramfuc_reg(0x10f914);
-
-       switch (ram->base.type) {
-       case NV_MEM_TYPE_GDDR5:
-               ram->fuc.r_mr[0] = ramfuc_reg(0x10f300);
-               ram->fuc.r_mr[1] = ramfuc_reg(0x10f330);
-               ram->fuc.r_mr[2] = ramfuc_reg(0x10f334);
-               ram->fuc.r_mr[3] = ramfuc_reg(0x10f338);
-               ram->fuc.r_mr[4] = ramfuc_reg(0x10f33c);
-               ram->fuc.r_mr[5] = ramfuc_reg(0x10f340);
-               ram->fuc.r_mr[6] = ramfuc_reg(0x10f344);
-               ram->fuc.r_mr[7] = ramfuc_reg(0x10f348);
-               ram->fuc.r_mr[8] = ramfuc_reg(0x10f354);
-               ram->fuc.r_mr[15] = ramfuc_reg(0x10f34c);
-               break;
-       case NV_MEM_TYPE_DDR3:
-               ram->fuc.r_mr[0] = ramfuc_reg(0x10f300);
-               ram->fuc.r_mr[2] = ramfuc_reg(0x10f320);
-               break;
-       default:
-               break;
-       }
-
-       ram->fuc.r_0x62c000 = ramfuc_reg(0x62c000);
-       ram->fuc.r_0x10f200 = ramfuc_reg(0x10f200);
-       ram->fuc.r_0x10f210 = ramfuc_reg(0x10f210);
-       ram->fuc.r_0x10f310 = ramfuc_reg(0x10f310);
-       ram->fuc.r_0x10f314 = ramfuc_reg(0x10f314);
-       ram->fuc.r_0x10f318 = ramfuc_reg(0x10f318);
-       ram->fuc.r_0x10f090 = ramfuc_reg(0x10f090);
-       ram->fuc.r_0x10f69c = ramfuc_reg(0x10f69c);
-       ram->fuc.r_0x10f824 = ramfuc_reg(0x10f824);
-       ram->fuc.r_0x1373f0 = ramfuc_reg(0x1373f0);
-       ram->fuc.r_0x1373f4 = ramfuc_reg(0x1373f4);
-       ram->fuc.r_0x137320 = ramfuc_reg(0x137320);
-       ram->fuc.r_0x10f65c = ramfuc_reg(0x10f65c);
-       ram->fuc.r_0x10f6bc = ramfuc_reg(0x10f6bc);
-       ram->fuc.r_0x100710 = ramfuc_reg(0x100710);
-       ram->fuc.r_0x100750 = ramfuc_reg(0x100750);
-       return 0;
-}
-
-struct nouveau_oclass
-nve0_ram_oclass = {
-       .handle = 0,
-       .ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nve0_ram_ctor,
-               .dtor = nve0_ram_dtor,
-               .init = nve0_ram_init,
-               .fini = _nouveau_ram_fini,
-       }
-};
diff --git a/drivers/gpu/drm/nouveau/core/subdev/fb/ramseq.h b/drivers/gpu/drm/nouveau/core/subdev/fb/ramseq.h
deleted file mode 100644 (file)
index 571077e..0000000
+++ /dev/null
@@ -1,18 +0,0 @@
-#ifndef __NVKM_FBRAM_SEQ_H__
-#define __NVKM_FBRAM_SEQ_H__
-
-#include <subdev/bus.h>
-#include <subdev/bus/hwsq.h>
-
-#define ram_init(s,p)       hwsq_init(&(s)->base, (p))
-#define ram_exec(s,e)       hwsq_exec(&(s)->base, (e))
-#define ram_have(s,r)       ((s)->r_##r.addr != 0x000000)
-#define ram_rd32(s,r)       hwsq_rd32(&(s)->base, &(s)->r_##r)
-#define ram_wr32(s,r,d)     hwsq_wr32(&(s)->base, &(s)->r_##r, (d))
-#define ram_nuke(s,r)       hwsq_nuke(&(s)->base, &(s)->r_##r)
-#define ram_mask(s,r,m,d)   hwsq_mask(&(s)->base, &(s)->r_##r, (m), (d))
-#define ram_setf(s,f,d)     hwsq_setf(&(s)->base, (f), (d))
-#define ram_wait(s,f,d)     hwsq_wait(&(s)->base, (f), (d))
-#define ram_nsec(s,n)       hwsq_nsec(&(s)->base, (n))
-
-#endif
diff --git a/drivers/gpu/drm/nouveau/core/subdev/fb/sddr2.c b/drivers/gpu/drm/nouveau/core/subdev/fb/sddr2.c
deleted file mode 100644 (file)
index 252575f..0000000
+++ /dev/null
@@ -1,94 +0,0 @@
-/*
- * Copyright 2014 Roy Spliet
- *
- * 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: Roy Spliet <rspliet@eclipso.eu>
- *          Ben Skeggs
- */
-
-#include "priv.h"
-
-struct ramxlat {
-       int id;
-       u8 enc;
-};
-
-static inline int
-ramxlat(const struct ramxlat *xlat, int id)
-{
-       while (xlat->id >= 0) {
-               if (xlat->id == id)
-                       return xlat->enc;
-               xlat++;
-       }
-       return -EINVAL;
-}
-
-static const struct ramxlat
-ramddr2_cl[] = {
-       { 2, 2 }, { 3, 3 }, { 4, 4 }, { 5, 5 }, { 6, 6 },
-       /* The following are available in some, but not all DDR2 docs */
-       { 7, 7 },
-       { -1 }
-};
-
-static const struct ramxlat
-ramddr2_wr[] = {
-       { 2, 1 }, { 3, 2 }, { 4, 3 }, { 5, 4 }, { 6, 5 },
-       /* The following are available in some, but not all DDR2 docs */
-       { 7, 6 },
-       { -1 }
-};
-
-int
-nouveau_sddr2_calc(struct nouveau_ram *ram)
-{
-       int CL, WR, DLL = 0, ODT = 0;
-
-       switch (ram->next->bios.timing_ver) {
-       case 0x10:
-               CL  = ram->next->bios.timing_10_CL;
-               WR  = ram->next->bios.timing_10_WR;
-               DLL = !ram->next->bios.ramcfg_10_DLLoff;
-               ODT = ram->next->bios.timing_10_ODT & 3;
-               break;
-       case 0x20:
-               CL  = (ram->next->bios.timing[1] & 0x0000001f);
-               WR  = (ram->next->bios.timing[2] & 0x007f0000) >> 16;
-               break;
-       default:
-               return -ENOSYS;
-       }
-
-       CL  = ramxlat(ramddr2_cl, CL);
-       WR  = ramxlat(ramddr2_wr, WR);
-       if (CL < 0 || WR < 0)
-               return -EINVAL;
-
-       ram->mr[0] &= ~0xf70;
-       ram->mr[0] |= (WR & 0x07) << 9;
-       ram->mr[0] |= (CL & 0x07) << 4;
-
-       ram->mr[1] &= ~0x045;
-       ram->mr[1] |= (ODT & 0x1) << 2;
-       ram->mr[1] |= (ODT & 0x2) << 5;
-       ram->mr[1] |= !DLL;
-       return 0;
-}
diff --git a/drivers/gpu/drm/nouveau/core/subdev/fb/sddr3.c b/drivers/gpu/drm/nouveau/core/subdev/fb/sddr3.c
deleted file mode 100644 (file)
index a2dca48..0000000
+++ /dev/null
@@ -1,120 +0,0 @@
-/*
- * Copyright 2013 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 <bskeggs@redhat.com>
- *         Roy Spliet <rspliet@eclipso.eu>
- */
-
-#include "priv.h"
-
-struct ramxlat {
-       int id;
-       u8 enc;
-};
-
-static inline int
-ramxlat(const struct ramxlat *xlat, int id)
-{
-       while (xlat->id >= 0) {
-               if (xlat->id == id)
-                       return xlat->enc;
-               xlat++;
-       }
-       return -EINVAL;
-}
-
-static const struct ramxlat
-ramddr3_cl[] = {
-       { 5, 2 }, { 6, 4 }, { 7, 6 }, { 8, 8 }, { 9, 10 }, { 10, 12 },
-       { 11, 14 },
-       /* the below are mentioned in some, but not all, ddr3 docs */
-       { 12, 1 }, { 13, 3 }, { 14, 5 },
-       { -1 }
-};
-
-static const struct ramxlat
-ramddr3_wr[] = {
-       { 5, 1 }, { 6, 2 }, { 7, 3 }, { 8, 4 }, { 10, 5 }, { 12, 6 },
-       /* the below are mentioned in some, but not all, ddr3 docs */
-       { 14, 7 }, { 16, 0 },
-       { -1 }
-};
-
-static const struct ramxlat
-ramddr3_cwl[] = {
-       { 5, 0 }, { 6, 1 }, { 7, 2 }, { 8, 3 },
-       /* the below are mentioned in some, but not all, ddr3 docs */
-       { 9, 4 },
-       { -1 }
-};
-
-int
-nouveau_sddr3_calc(struct nouveau_ram *ram)
-{
-       int CWL, CL, WR, DLL = 0, ODT = 0;
-
-       switch (ram->next->bios.timing_ver) {
-       case 0x10:
-               if (ram->next->bios.timing_hdr < 0x17) {
-                       /* XXX: NV50: Get CWL from the timing register */
-                       return -ENOSYS;
-               }
-               CWL = ram->next->bios.timing_10_CWL;
-               CL  = ram->next->bios.timing_10_CL;
-               WR  = ram->next->bios.timing_10_WR;
-               DLL = !ram->next->bios.ramcfg_10_DLLoff;
-               ODT = ram->next->bios.timing_10_ODT;
-               break;
-       case 0x20:
-               CWL = (ram->next->bios.timing[1] & 0x00000f80) >> 7;
-               CL  = (ram->next->bios.timing[1] & 0x0000001f) >> 0;
-               WR  = (ram->next->bios.timing[2] & 0x007f0000) >> 16;
-               /* XXX: Get these values from the VBIOS instead */
-               DLL = !(ram->mr[1] & 0x1);
-               ODT =   (ram->mr[1] & 0x004) >> 2 |
-                       (ram->mr[1] & 0x040) >> 5 |
-                       (ram->mr[1] & 0x200) >> 7;
-               break;
-       default:
-               return -ENOSYS;
-       }
-
-       CWL = ramxlat(ramddr3_cwl, CWL);
-       CL  = ramxlat(ramddr3_cl, CL);
-       WR  = ramxlat(ramddr3_wr, WR);
-       if (CL < 0 || CWL < 0 || WR < 0)
-               return -EINVAL;
-
-       ram->mr[0] &= ~0xf74;
-       ram->mr[0] |= (WR & 0x07) << 9;
-       ram->mr[0] |= (CL & 0x0e) << 3;
-       ram->mr[0] |= (CL & 0x01) << 2;
-
-       ram->mr[1] &= ~0x245;
-       ram->mr[1] |= (ODT & 0x1) << 2;
-       ram->mr[1] |= (ODT & 0x2) << 5;
-       ram->mr[1] |= (ODT & 0x4) << 7;
-       ram->mr[1] |= !DLL;
-
-       ram->mr[2] &= ~0x038;
-       ram->mr[2] |= (CWL & 0x07) << 3;
-       return 0;
-}
diff --git a/drivers/gpu/drm/nouveau/core/subdev/fuse/base.c b/drivers/gpu/drm/nouveau/core/subdev/fuse/base.c
deleted file mode 100644 (file)
index 9e8e921..0000000
+++ /dev/null
@@ -1,54 +0,0 @@
-/*
- * Copyright 2014 Martin Peres
- *
- * 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 <subdev/fuse.h>
-
-int
-_nouveau_fuse_init(struct nouveau_object *object)
-{
-       struct nouveau_fuse *fuse = (void *)object;
-       return nouveau_subdev_init(&fuse->base);
-}
-
-void
-_nouveau_fuse_dtor(struct nouveau_object *object)
-{
-       struct nouveau_fuse *fuse = (void *)object;
-       nouveau_subdev_destroy(&fuse->base);
-}
-
-int
-nouveau_fuse_create_(struct nouveau_object *parent,
-                    struct nouveau_object *engine,
-                    struct nouveau_oclass *oclass, int length, void **pobject)
-{
-       struct nouveau_fuse *fuse;
-       int ret;
-
-       ret = nouveau_subdev_create_(parent, engine, oclass, 0, "FUSE",
-                                    "fuse", length, pobject);
-       fuse = *pobject;
-
-       return ret;
-}
diff --git a/drivers/gpu/drm/nouveau/core/subdev/fuse/g80.c b/drivers/gpu/drm/nouveau/core/subdev/fuse/g80.c
deleted file mode 100644 (file)
index a374ade..0000000
+++ /dev/null
@@ -1,81 +0,0 @@
-/*
- * Copyright 2014 Martin Peres
- *
- * 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 "priv.h"
-
-struct g80_fuse_priv {
-       struct nouveau_fuse base;
-
-       spinlock_t fuse_enable_lock;
-};
-
-static u32
-g80_fuse_rd32(struct nouveau_object *object, u64 addr)
-{
-       struct g80_fuse_priv *priv = (void *)object;
-       unsigned long flags;
-       u32 fuse_enable, val;
-
-       spin_lock_irqsave(&priv->fuse_enable_lock, flags);
-
-       /* racy if another part of nouveau start writing to this reg */
-       fuse_enable = nv_mask(priv, 0x1084, 0x800, 0x800);
-       val = nv_rd32(priv, 0x21000 + addr);
-       nv_wr32(priv, 0x1084, fuse_enable);
-
-       spin_unlock_irqrestore(&priv->fuse_enable_lock, flags);
-
-       return val;
-}
-
-
-static int
-g80_fuse_ctor(struct nouveau_object *parent, struct nouveau_object *engine,
-              struct nouveau_oclass *oclass, void *data, u32 size,
-              struct nouveau_object **pobject)
-{
-       struct g80_fuse_priv *priv;
-       int ret;
-
-       ret = nouveau_fuse_create(parent, engine, oclass, &priv);
-       *pobject = nv_object(priv);
-       if (ret)
-               return ret;
-
-       spin_lock_init(&priv->fuse_enable_lock);
-
-       return 0;
-}
-
-struct nouveau_oclass
-g80_fuse_oclass = {
-       .handle = NV_SUBDEV(FUSE, 0x50),
-       .ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = g80_fuse_ctor,
-               .dtor = _nouveau_fuse_dtor,
-               .init = _nouveau_fuse_init,
-               .fini = _nouveau_fuse_fini,
-               .rd32 = g80_fuse_rd32,
-       },
-};
diff --git a/drivers/gpu/drm/nouveau/core/subdev/fuse/gf100.c b/drivers/gpu/drm/nouveau/core/subdev/fuse/gf100.c
deleted file mode 100644 (file)
index 5ed03f5..0000000
+++ /dev/null
@@ -1,83 +0,0 @@
-/*
- * Copyright 2014 Martin Peres
- *
- * 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 "priv.h"
-
-struct gf100_fuse_priv {
-       struct nouveau_fuse base;
-
-       spinlock_t fuse_enable_lock;
-};
-
-static u32
-gf100_fuse_rd32(struct nouveau_object *object, u64 addr)
-{
-       struct gf100_fuse_priv *priv = (void *)object;
-       unsigned long flags;
-       u32 fuse_enable, unk, val;
-
-       spin_lock_irqsave(&priv->fuse_enable_lock, flags);
-
-       /* racy if another part of nouveau start writing to these regs */
-       fuse_enable = nv_mask(priv, 0x22400, 0x800, 0x800);
-       unk = nv_mask(priv, 0x21000, 0x1, 0x1);
-       val = nv_rd32(priv, 0x21100 + addr);
-       nv_wr32(priv, 0x21000, unk);
-       nv_wr32(priv, 0x22400, fuse_enable);
-
-       spin_unlock_irqrestore(&priv->fuse_enable_lock, flags);
-
-       return val;
-}
-
-
-static int
-gf100_fuse_ctor(struct nouveau_object *parent, struct nouveau_object *engine,
-              struct nouveau_oclass *oclass, void *data, u32 size,
-              struct nouveau_object **pobject)
-{
-       struct gf100_fuse_priv *priv;
-       int ret;
-
-       ret = nouveau_fuse_create(parent, engine, oclass, &priv);
-       *pobject = nv_object(priv);
-       if (ret)
-               return ret;
-
-       spin_lock_init(&priv->fuse_enable_lock);
-
-       return 0;
-}
-
-struct nouveau_oclass
-gf100_fuse_oclass = {
-       .handle = NV_SUBDEV(FUSE, 0xC0),
-       .ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = gf100_fuse_ctor,
-               .dtor = _nouveau_fuse_dtor,
-               .init = _nouveau_fuse_init,
-               .fini = _nouveau_fuse_fini,
-               .rd32 = gf100_fuse_rd32,
-       },
-};
diff --git a/drivers/gpu/drm/nouveau/core/subdev/fuse/gm107.c b/drivers/gpu/drm/nouveau/core/subdev/fuse/gm107.c
deleted file mode 100644 (file)
index 4f1a636..0000000
+++ /dev/null
@@ -1,66 +0,0 @@
-/*
- * Copyright 2014 Martin Peres
- *
- * 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 "priv.h"
-
-struct gm107_fuse_priv {
-       struct nouveau_fuse base;
-};
-
-static u32
-gm107_fuse_rd32(struct nouveau_object *object, u64 addr)
-{
-       struct gf100_fuse_priv *priv = (void *)object;
-
-       return nv_rd32(priv, 0x21100 + addr);
-}
-
-
-static int
-gm107_fuse_ctor(struct nouveau_object *parent, struct nouveau_object *engine,
-              struct nouveau_oclass *oclass, void *data, u32 size,
-              struct nouveau_object **pobject)
-{
-       struct gm107_fuse_priv *priv;
-       int ret;
-
-       ret = nouveau_fuse_create(parent, engine, oclass, &priv);
-       *pobject = nv_object(priv);
-       if (ret)
-               return ret;
-
-       return 0;
-}
-
-struct nouveau_oclass
-gm107_fuse_oclass = {
-       .handle = NV_SUBDEV(FUSE, 0x117),
-       .ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = gm107_fuse_ctor,
-               .dtor = _nouveau_fuse_dtor,
-               .init = _nouveau_fuse_init,
-               .fini = _nouveau_fuse_fini,
-               .rd32 = gm107_fuse_rd32,
-       },
-};
diff --git a/drivers/gpu/drm/nouveau/core/subdev/fuse/priv.h b/drivers/gpu/drm/nouveau/core/subdev/fuse/priv.h
deleted file mode 100644 (file)
index d208541..0000000
+++ /dev/null
@@ -1,9 +0,0 @@
-#ifndef __NVKM_FUSE_PRIV_H__
-#define __NVKM_FUSE_PRIV_H__
-
-#include <subdev/fuse.h>
-
-int _nouveau_fuse_init(struct nouveau_object *object);
-void _nouveau_fuse_dtor(struct nouveau_object *object);
-
-#endif
diff --git a/drivers/gpu/drm/nouveau/core/subdev/gpio/base.c b/drivers/gpu/drm/nouveau/core/subdev/gpio/base.c
deleted file mode 100644 (file)
index 7ad99b7..0000000
+++ /dev/null
@@ -1,255 +0,0 @@
-/*
- * 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 <subdev/bios.h>
-#include <subdev/bios/gpio.h>
-
-#include "priv.h"
-
-static int
-nouveau_gpio_drive(struct nouveau_gpio *gpio,
-                  int idx, int line, int dir, int out)
-{
-       const struct nouveau_gpio_impl *impl = (void *)nv_object(gpio)->oclass;
-       return impl->drive ? impl->drive(gpio, line, dir, out) : -ENODEV;
-}
-
-static int
-nouveau_gpio_sense(struct nouveau_gpio *gpio, int idx, int line)
-{
-       const struct nouveau_gpio_impl *impl = (void *)nv_object(gpio)->oclass;
-       return impl->sense ? impl->sense(gpio, line) : -ENODEV;
-}
-
-static int
-nouveau_gpio_find(struct nouveau_gpio *gpio, int idx, u8 tag, u8 line,
-                 struct dcb_gpio_func *func)
-{
-       struct nouveau_bios *bios = nouveau_bios(gpio);
-       u8  ver, len;
-       u16 data;
-
-       if (line == 0xff && tag == 0xff)
-               return -EINVAL;
-
-       data = dcb_gpio_match(bios, idx, tag, line, &ver, &len, func);
-       if (data)
-               return 0;
-
-       /* Apple iMac G4 NV18 */
-       if (nv_device_match(nv_object(gpio), 0x0189, 0x10de, 0x0010)) {
-               if (tag == DCB_GPIO_TVDAC0) {
-                       *func = (struct dcb_gpio_func) {
-                               .func = DCB_GPIO_TVDAC0,
-                               .line = 4,
-                               .log[0] = 0,
-                               .log[1] = 1,
-                       };
-                       return 0;
-               }
-       }
-
-       return -ENOENT;
-}
-
-static int
-nouveau_gpio_set(struct nouveau_gpio *gpio, int idx, u8 tag, u8 line, int state)
-{
-       struct dcb_gpio_func func;
-       int ret;
-
-       ret = nouveau_gpio_find(gpio, idx, tag, line, &func);
-       if (ret == 0) {
-               int dir = !!(func.log[state] & 0x02);
-               int out = !!(func.log[state] & 0x01);
-               ret = nouveau_gpio_drive(gpio, idx, func.line, dir, out);
-       }
-
-       return ret;
-}
-
-static int
-nouveau_gpio_get(struct nouveau_gpio *gpio, int idx, u8 tag, u8 line)
-{
-       struct dcb_gpio_func func;
-       int ret;
-
-       ret = nouveau_gpio_find(gpio, idx, tag, line, &func);
-       if (ret == 0) {
-               ret = nouveau_gpio_sense(gpio, idx, func.line);
-               if (ret >= 0)
-                       ret = (ret == (func.log[1] & 1));
-       }
-
-       return ret;
-}
-
-static void
-nouveau_gpio_intr_fini(struct nvkm_event *event, int type, int index)
-{
-       struct nouveau_gpio *gpio = container_of(event, typeof(*gpio), event);
-       const struct nouveau_gpio_impl *impl = (void *)nv_object(gpio)->oclass;
-       impl->intr_mask(gpio, type, 1 << index, 0);
-}
-
-static void
-nouveau_gpio_intr_init(struct nvkm_event *event, int type, int index)
-{
-       struct nouveau_gpio *gpio = container_of(event, typeof(*gpio), event);
-       const struct nouveau_gpio_impl *impl = (void *)nv_object(gpio)->oclass;
-       impl->intr_mask(gpio, type, 1 << index, 1 << index);
-}
-
-static int
-nouveau_gpio_intr_ctor(struct nouveau_object *object, void *data, u32 size,
-                      struct nvkm_notify *notify)
-{
-       struct nvkm_gpio_ntfy_req *req = data;
-       if (!WARN_ON(size != sizeof(*req))) {
-               notify->size  = sizeof(struct nvkm_gpio_ntfy_rep);
-               notify->types = req->mask;
-               notify->index = req->line;
-               return 0;
-       }
-       return -EINVAL;
-}
-
-static void
-nouveau_gpio_intr(struct nouveau_subdev *subdev)
-{
-       struct nouveau_gpio *gpio = nouveau_gpio(subdev);
-       const struct nouveau_gpio_impl *impl = (void *)nv_object(gpio)->oclass;
-       u32 hi, lo, i;
-
-       impl->intr_stat(gpio, &hi, &lo);
-
-       for (i = 0; (hi | lo) && i < impl->lines; i++) {
-               struct nvkm_gpio_ntfy_rep rep = {
-                       .mask = (NVKM_GPIO_HI * !!(hi & (1 << i))) |
-                               (NVKM_GPIO_LO * !!(lo & (1 << i))),
-               };
-               nvkm_event_send(&gpio->event, rep.mask, i, &rep, sizeof(rep));
-       }
-}
-
-static const struct nvkm_event_func
-nouveau_gpio_intr_func = {
-       .ctor = nouveau_gpio_intr_ctor,
-       .init = nouveau_gpio_intr_init,
-       .fini = nouveau_gpio_intr_fini,
-};
-
-int
-_nouveau_gpio_fini(struct nouveau_object *object, bool suspend)
-{
-       const struct nouveau_gpio_impl *impl = (void *)object->oclass;
-       struct nouveau_gpio *gpio = nouveau_gpio(object);
-       u32 mask = (1 << impl->lines) - 1;
-
-       impl->intr_mask(gpio, NVKM_GPIO_TOGGLED, mask, 0);
-       impl->intr_stat(gpio, &mask, &mask);
-
-       return nouveau_subdev_fini(&gpio->base, suspend);
-}
-
-static struct dmi_system_id gpio_reset_ids[] = {
-       {
-               .ident = "Apple Macbook 10,1",
-               .matches = {
-                       DMI_MATCH(DMI_SYS_VENDOR, "Apple Inc."),
-                       DMI_MATCH(DMI_PRODUCT_NAME, "MacBookPro10,1"),
-               }
-       },
-       { }
-};
-
-int
-_nouveau_gpio_init(struct nouveau_object *object)
-{
-       struct nouveau_gpio *gpio = nouveau_gpio(object);
-       int ret;
-
-       ret = nouveau_subdev_init(&gpio->base);
-       if (ret)
-               return ret;
-
-       if (gpio->reset && dmi_check_system(gpio_reset_ids))
-               gpio->reset(gpio, DCB_GPIO_UNUSED);
-
-       return ret;
-}
-
-void
-_nouveau_gpio_dtor(struct nouveau_object *object)
-{
-       struct nouveau_gpio *gpio = (void *)object;
-       nvkm_event_fini(&gpio->event);
-       nouveau_subdev_destroy(&gpio->base);
-}
-
-int
-nouveau_gpio_create_(struct nouveau_object *parent,
-                    struct nouveau_object *engine,
-                    struct nouveau_oclass *oclass,
-                    int length, void **pobject)
-{
-       const struct nouveau_gpio_impl *impl = (void *)oclass;
-       struct nouveau_gpio *gpio;
-       int ret;
-
-       ret = nouveau_subdev_create_(parent, engine, oclass, 0, "GPIO", "gpio",
-                                    length, pobject);
-       gpio = *pobject;
-       if (ret)
-               return ret;
-
-       gpio->find = nouveau_gpio_find;
-       gpio->set  = nouveau_gpio_set;
-       gpio->get  = nouveau_gpio_get;
-       gpio->reset = impl->reset;
-
-       ret = nvkm_event_init(&nouveau_gpio_intr_func, 2, impl->lines,
-                             &gpio->event);
-       if (ret)
-               return ret;
-
-       nv_subdev(gpio)->intr = nouveau_gpio_intr;
-       return 0;
-}
-
-int
-_nouveau_gpio_ctor(struct nouveau_object *parent, struct nouveau_object *engine,
-                  struct nouveau_oclass *oclass, void *data, u32 size,
-                  struct nouveau_object **pobject)
-{
-       struct nouveau_gpio *gpio;
-       int ret;
-
-       ret = nouveau_gpio_create(parent, engine, oclass, &gpio);
-       *pobject = nv_object(gpio);
-       if (ret)
-               return ret;
-
-       return 0;
-}
diff --git a/drivers/gpu/drm/nouveau/core/subdev/gpio/nv10.c b/drivers/gpu/drm/nouveau/core/subdev/gpio/nv10.c
deleted file mode 100644 (file)
index 27ad23e..0000000
+++ /dev/null
@@ -1,116 +0,0 @@
-/*
- * 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 "priv.h"
-
-static int
-nv10_gpio_sense(struct nouveau_gpio *gpio, int line)
-{
-       if (line < 2) {
-               line = line * 16;
-               line = nv_rd32(gpio, 0x600818) >> line;
-               return !!(line & 0x0100);
-       } else
-       if (line < 10) {
-               line = (line - 2) * 4;
-               line = nv_rd32(gpio, 0x60081c) >> line;
-               return !!(line & 0x04);
-       } else
-       if (line < 14) {
-               line = (line - 10) * 4;
-               line = nv_rd32(gpio, 0x600850) >> line;
-               return !!(line & 0x04);
-       }
-
-       return -EINVAL;
-}
-
-static int
-nv10_gpio_drive(struct nouveau_gpio *gpio, int line, int dir, int out)
-{
-       u32 reg, mask, data;
-
-       if (line < 2) {
-               line = line * 16;
-               reg  = 0x600818;
-               mask = 0x00000011;
-               data = (dir << 4) | out;
-       } else
-       if (line < 10) {
-               line = (line - 2) * 4;
-               reg  = 0x60081c;
-               mask = 0x00000003;
-               data = (dir << 1) | out;
-       } else
-       if (line < 14) {
-               line = (line - 10) * 4;
-               reg  = 0x600850;
-               mask = 0x00000003;
-               data = (dir << 1) | out;
-       } else {
-               return -EINVAL;
-       }
-
-       nv_mask(gpio, reg, mask << line, data << line);
-       return 0;
-}
-
-static void
-nv10_gpio_intr_stat(struct nouveau_gpio *gpio, u32 *hi, u32 *lo)
-{
-       u32 intr = nv_rd32(gpio, 0x001104);
-       u32 stat = nv_rd32(gpio, 0x001144) & intr;
-       *lo = (stat & 0xffff0000) >> 16;
-       *hi = (stat & 0x0000ffff);
-       nv_wr32(gpio, 0x001104, intr);
-}
-
-static void
-nv10_gpio_intr_mask(struct nouveau_gpio *gpio, u32 type, u32 mask, u32 data)
-{
-       u32 inte = nv_rd32(gpio, 0x001144);
-       if (type & NVKM_GPIO_LO)
-               inte = (inte & ~(mask << 16)) | (data << 16);
-       if (type & NVKM_GPIO_HI)
-               inte = (inte & ~mask) | data;
-       nv_wr32(gpio, 0x001144, inte);
-}
-
-struct nouveau_oclass *
-nv10_gpio_oclass = &(struct nouveau_gpio_impl) {
-       .base.handle = NV_SUBDEV(GPIO, 0x10),
-       .base.ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = _nouveau_gpio_ctor,
-               .dtor = _nouveau_gpio_dtor,
-               .init = _nouveau_gpio_init,
-               .fini = _nouveau_gpio_fini,
-       },
-       .lines = 16,
-       .intr_stat = nv10_gpio_intr_stat,
-       .intr_mask = nv10_gpio_intr_mask,
-       .drive = nv10_gpio_drive,
-       .sense = nv10_gpio_sense,
-}.base;
diff --git a/drivers/gpu/drm/nouveau/core/subdev/gpio/nv50.c b/drivers/gpu/drm/nouveau/core/subdev/gpio/nv50.c
deleted file mode 100644 (file)
index 2e30d5a..0000000
+++ /dev/null
@@ -1,129 +0,0 @@
-/*
- * Copyright 2012 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 "priv.h"
-
-void
-nv50_gpio_reset(struct nouveau_gpio *gpio, u8 match)
-{
-       struct nouveau_bios *bios = nouveau_bios(gpio);
-       u8 ver, len;
-       u16 entry;
-       int ent = -1;
-
-       while ((entry = dcb_gpio_entry(bios, 0, ++ent, &ver, &len))) {
-               static const u32 regs[] = { 0xe100, 0xe28c };
-               u32 data = nv_ro32(bios, entry);
-               u8  line =   (data & 0x0000001f);
-               u8  func =   (data & 0x0000ff00) >> 8;
-               u8  defs = !!(data & 0x01000000);
-               u8  unk0 = !!(data & 0x02000000);
-               u8  unk1 = !!(data & 0x04000000);
-               u32 val = (unk1 << 16) | unk0;
-               u32 reg = regs[line >> 4];
-               u32 lsh = line & 0x0f;
-
-               if ( func  == DCB_GPIO_UNUSED ||
-                   (match != DCB_GPIO_UNUSED && match != func))
-                       continue;
-
-               gpio->set(gpio, 0, func, line, defs);
-
-               nv_mask(gpio, reg, 0x00010001 << lsh, val << lsh);
-       }
-}
-
-int
-nv50_gpio_location(int line, u32 *reg, u32 *shift)
-{
-       const u32 nv50_gpio_reg[4] = { 0xe104, 0xe108, 0xe280, 0xe284 };
-
-       if (line >= 32)
-               return -EINVAL;
-
-       *reg = nv50_gpio_reg[line >> 3];
-       *shift = (line & 7) << 2;
-       return 0;
-}
-
-int
-nv50_gpio_drive(struct nouveau_gpio *gpio, int line, int dir, int out)
-{
-       u32 reg, shift;
-
-       if (nv50_gpio_location(line, &reg, &shift))
-               return -EINVAL;
-
-       nv_mask(gpio, reg, 3 << shift, (((dir ^ 1) << 1) | out) << shift);
-       return 0;
-}
-
-int
-nv50_gpio_sense(struct nouveau_gpio *gpio, int line)
-{
-       u32 reg, shift;
-
-       if (nv50_gpio_location(line, &reg, &shift))
-               return -EINVAL;
-
-       return !!(nv_rd32(gpio, reg) & (4 << shift));
-}
-
-static void
-nv50_gpio_intr_stat(struct nouveau_gpio *gpio, u32 *hi, u32 *lo)
-{
-       u32 intr = nv_rd32(gpio, 0x00e054);
-       u32 stat = nv_rd32(gpio, 0x00e050) & intr;
-       *lo = (stat & 0xffff0000) >> 16;
-       *hi = (stat & 0x0000ffff);
-       nv_wr32(gpio, 0x00e054, intr);
-}
-
-static void
-nv50_gpio_intr_mask(struct nouveau_gpio *gpio, u32 type, u32 mask, u32 data)
-{
-       u32 inte = nv_rd32(gpio, 0x00e050);
-       if (type & NVKM_GPIO_LO)
-               inte = (inte & ~(mask << 16)) | (data << 16);
-       if (type & NVKM_GPIO_HI)
-               inte = (inte & ~mask) | data;
-       nv_wr32(gpio, 0x00e050, inte);
-}
-
-struct nouveau_oclass *
-nv50_gpio_oclass = &(struct nouveau_gpio_impl) {
-       .base.handle = NV_SUBDEV(GPIO, 0x50),
-       .base.ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = _nouveau_gpio_ctor,
-               .dtor = _nouveau_gpio_dtor,
-               .init = _nouveau_gpio_init,
-               .fini = _nouveau_gpio_fini,
-       },
-       .lines = 16,
-       .intr_stat = nv50_gpio_intr_stat,
-       .intr_mask = nv50_gpio_intr_mask,
-       .drive = nv50_gpio_drive,
-       .sense = nv50_gpio_sense,
-       .reset = nv50_gpio_reset,
-}.base;
diff --git a/drivers/gpu/drm/nouveau/core/subdev/gpio/nv94.c b/drivers/gpu/drm/nouveau/core/subdev/gpio/nv94.c
deleted file mode 100644 (file)
index cae404c..0000000
+++ /dev/null
@@ -1,74 +0,0 @@
-/*
- * Copyright 2012 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 "priv.h"
-
-void
-nv94_gpio_intr_stat(struct nouveau_gpio *gpio, u32 *hi, u32 *lo)
-{
-       u32 intr0 = nv_rd32(gpio, 0x00e054);
-       u32 intr1 = nv_rd32(gpio, 0x00e074);
-       u32 stat0 = nv_rd32(gpio, 0x00e050) & intr0;
-       u32 stat1 = nv_rd32(gpio, 0x00e070) & intr1;
-       *lo = (stat1 & 0xffff0000) | (stat0 >> 16);
-       *hi = (stat1 << 16) | (stat0 & 0x0000ffff);
-       nv_wr32(gpio, 0x00e054, intr0);
-       nv_wr32(gpio, 0x00e074, intr1);
-}
-
-void
-nv94_gpio_intr_mask(struct nouveau_gpio *gpio, u32 type, u32 mask, u32 data)
-{
-       u32 inte0 = nv_rd32(gpio, 0x00e050);
-       u32 inte1 = nv_rd32(gpio, 0x00e070);
-       if (type & NVKM_GPIO_LO)
-               inte0 = (inte0 & ~(mask << 16)) | (data << 16);
-       if (type & NVKM_GPIO_HI)
-               inte0 = (inte0 & ~(mask & 0xffff)) | (data & 0xffff);
-       mask >>= 16;
-       data >>= 16;
-       if (type & NVKM_GPIO_LO)
-               inte1 = (inte1 & ~(mask << 16)) | (data << 16);
-       if (type & NVKM_GPIO_HI)
-               inte1 = (inte1 & ~mask) | data;
-       nv_wr32(gpio, 0x00e050, inte0);
-       nv_wr32(gpio, 0x00e070, inte1);
-}
-
-struct nouveau_oclass *
-nv94_gpio_oclass = &(struct nouveau_gpio_impl) {
-       .base.handle = NV_SUBDEV(GPIO, 0x94),
-       .base.ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = _nouveau_gpio_ctor,
-               .dtor = _nouveau_gpio_dtor,
-               .init = _nouveau_gpio_init,
-               .fini = _nouveau_gpio_fini,
-       },
-       .lines = 32,
-       .intr_stat = nv94_gpio_intr_stat,
-       .intr_mask = nv94_gpio_intr_mask,
-       .drive = nv50_gpio_drive,
-       .sense = nv50_gpio_sense,
-       .reset = nv50_gpio_reset,
-}.base;
diff --git a/drivers/gpu/drm/nouveau/core/subdev/gpio/nvd0.c b/drivers/gpu/drm/nouveau/core/subdev/gpio/nvd0.c
deleted file mode 100644 (file)
index 480d6d2..0000000
+++ /dev/null
@@ -1,85 +0,0 @@
-/*
- * Copyright 2012 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 "priv.h"
-
-void
-nvd0_gpio_reset(struct nouveau_gpio *gpio, u8 match)
-{
-       struct nouveau_bios *bios = nouveau_bios(gpio);
-       u8 ver, len;
-       u16 entry;
-       int ent = -1;
-
-       while ((entry = dcb_gpio_entry(bios, 0, ++ent, &ver, &len))) {
-               u32 data = nv_ro32(bios, entry);
-               u8  line =   (data & 0x0000003f);
-               u8  defs = !!(data & 0x00000080);
-               u8  func =   (data & 0x0000ff00) >> 8;
-               u8  unk0 =   (data & 0x00ff0000) >> 16;
-               u8  unk1 =   (data & 0x1f000000) >> 24;
-
-               if ( func  == DCB_GPIO_UNUSED ||
-                   (match != DCB_GPIO_UNUSED && match != func))
-                       continue;
-
-               gpio->set(gpio, 0, func, line, defs);
-
-               nv_mask(gpio, 0x00d610 + (line * 4), 0xff, unk0);
-               if (unk1--)
-                       nv_mask(gpio, 0x00d740 + (unk1 * 4), 0xff, line);
-       }
-}
-
-int
-nvd0_gpio_drive(struct nouveau_gpio *gpio, int line, int dir, int out)
-{
-       u32 data = ((dir ^ 1) << 13) | (out << 12);
-       nv_mask(gpio, 0x00d610 + (line * 4), 0x00003000, data);
-       nv_mask(gpio, 0x00d604, 0x00000001, 0x00000001); /* update? */
-       return 0;
-}
-
-int
-nvd0_gpio_sense(struct nouveau_gpio *gpio, int line)
-{
-       return !!(nv_rd32(gpio, 0x00d610 + (line * 4)) & 0x00004000);
-}
-
-struct nouveau_oclass *
-nvd0_gpio_oclass = &(struct nouveau_gpio_impl) {
-       .base.handle = NV_SUBDEV(GPIO, 0xd0),
-       .base.ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = _nouveau_gpio_ctor,
-               .dtor = _nouveau_gpio_dtor,
-               .init = _nouveau_gpio_init,
-               .fini = _nouveau_gpio_fini,
-       },
-       .lines = 32,
-       .intr_stat = nv94_gpio_intr_stat,
-       .intr_mask = nv94_gpio_intr_mask,
-       .drive = nvd0_gpio_drive,
-       .sense = nvd0_gpio_sense,
-       .reset = nvd0_gpio_reset,
-}.base;
diff --git a/drivers/gpu/drm/nouveau/core/subdev/gpio/nve0.c b/drivers/gpu/drm/nouveau/core/subdev/gpio/nve0.c
deleted file mode 100644 (file)
index e1145b4..0000000
+++ /dev/null
@@ -1,74 +0,0 @@
-/*
- * Copyright 2012 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 "priv.h"
-
-static void
-nve0_gpio_intr_stat(struct nouveau_gpio *gpio, u32 *hi, u32 *lo)
-{
-       u32 intr0 = nv_rd32(gpio, 0x00dc00);
-       u32 intr1 = nv_rd32(gpio, 0x00dc80);
-       u32 stat0 = nv_rd32(gpio, 0x00dc08) & intr0;
-       u32 stat1 = nv_rd32(gpio, 0x00dc88) & intr1;
-       *lo = (stat1 & 0xffff0000) | (stat0 >> 16);
-       *hi = (stat1 << 16) | (stat0 & 0x0000ffff);
-       nv_wr32(gpio, 0x00dc00, intr0);
-       nv_wr32(gpio, 0x00dc80, intr1);
-}
-
-void
-nve0_gpio_intr_mask(struct nouveau_gpio *gpio, u32 type, u32 mask, u32 data)
-{
-       u32 inte0 = nv_rd32(gpio, 0x00dc08);
-       u32 inte1 = nv_rd32(gpio, 0x00dc88);
-       if (type & NVKM_GPIO_LO)
-               inte0 = (inte0 & ~(mask << 16)) | (data << 16);
-       if (type & NVKM_GPIO_HI)
-               inte0 = (inte0 & ~(mask & 0xffff)) | (data & 0xffff);
-       mask >>= 16;
-       data >>= 16;
-       if (type & NVKM_GPIO_LO)
-               inte1 = (inte1 & ~(mask << 16)) | (data << 16);
-       if (type & NVKM_GPIO_HI)
-               inte1 = (inte1 & ~mask) | data;
-       nv_wr32(gpio, 0x00dc08, inte0);
-       nv_wr32(gpio, 0x00dc88, inte1);
-}
-
-struct nouveau_oclass *
-nve0_gpio_oclass = &(struct nouveau_gpio_impl) {
-       .base.handle = NV_SUBDEV(GPIO, 0xe0),
-       .base.ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = _nouveau_gpio_ctor,
-               .dtor = _nouveau_gpio_dtor,
-               .init = _nouveau_gpio_init,
-               .fini = _nouveau_gpio_fini,
-       },
-       .lines = 32,
-       .intr_stat = nve0_gpio_intr_stat,
-       .intr_mask = nve0_gpio_intr_mask,
-       .drive = nvd0_gpio_drive,
-       .sense = nvd0_gpio_sense,
-       .reset = nvd0_gpio_reset,
-}.base;
diff --git a/drivers/gpu/drm/nouveau/core/subdev/gpio/priv.h b/drivers/gpu/drm/nouveau/core/subdev/gpio/priv.h
deleted file mode 100644 (file)
index bff98b8..0000000
+++ /dev/null
@@ -1,67 +0,0 @@
-#ifndef __NVKM_GPIO_H__
-#define __NVKM_GPIO_H__
-
-#include <subdev/gpio.h>
-
-#define nouveau_gpio_create(p,e,o,d)                                           \
-       nouveau_gpio_create_((p), (e), (o), sizeof(**d), (void **)d)
-#define nouveau_gpio_destroy(p) ({                                             \
-       struct nouveau_gpio *gpio = (p);                                       \
-       _nouveau_gpio_dtor(nv_object(gpio));                                   \
-})
-#define nouveau_gpio_init(p) ({                                                \
-       struct nouveau_gpio *gpio = (p);                                       \
-       _nouveau_gpio_init(nv_object(gpio));                                   \
-})
-#define nouveau_gpio_fini(p,s) ({                                              \
-       struct nouveau_gpio *gpio = (p);                                       \
-       _nouveau_gpio_fini(nv_object(gpio), (s));                              \
-})
-
-int  nouveau_gpio_create_(struct nouveau_object *, struct nouveau_object *,
-                         struct nouveau_oclass *, int, void **);
-int  _nouveau_gpio_ctor(struct nouveau_object *, struct nouveau_object *,
-                       struct nouveau_oclass *, void *, u32,
-                       struct nouveau_object **);
-void _nouveau_gpio_dtor(struct nouveau_object *);
-int  _nouveau_gpio_init(struct nouveau_object *);
-int  _nouveau_gpio_fini(struct nouveau_object *, bool);
-
-struct nouveau_gpio_impl {
-       struct nouveau_oclass base;
-       int lines;
-
-       /* read and ack pending interrupts, returning only data
-        * for lines that have not been masked off, while still
-        * performing the ack for anything that was pending.
-        */
-       void (*intr_stat)(struct nouveau_gpio *, u32 *, u32 *);
-
-       /* mask on/off interrupts for hi/lo transitions on a
-        * given set of gpio lines
-        */
-       void (*intr_mask)(struct nouveau_gpio *, u32, u32, u32);
-
-       /* configure gpio direction and output value */
-       int  (*drive)(struct nouveau_gpio *, int line, int dir, int out);
-
-       /* sense current state of given gpio line */
-       int  (*sense)(struct nouveau_gpio *, int line);
-
-       /*XXX*/
-       void (*reset)(struct nouveau_gpio *, u8);
-};
-
-void nv50_gpio_reset(struct nouveau_gpio *, u8);
-int  nv50_gpio_drive(struct nouveau_gpio *, int, int, int);
-int  nv50_gpio_sense(struct nouveau_gpio *, int);
-
-void nv94_gpio_intr_stat(struct nouveau_gpio *, u32 *, u32 *);
-void nv94_gpio_intr_mask(struct nouveau_gpio *, u32, u32, u32);
-
-void nvd0_gpio_reset(struct nouveau_gpio *, u8);
-int  nvd0_gpio_drive(struct nouveau_gpio *, int, int, int);
-int  nvd0_gpio_sense(struct nouveau_gpio *, int);
-
-
-#endif
diff --git a/drivers/gpu/drm/nouveau/core/subdev/i2c/anx9805.c b/drivers/gpu/drm/nouveau/core/subdev/i2c/anx9805.c
deleted file mode 100644 (file)
index 2c2731a..0000000
+++ /dev/null
@@ -1,292 +0,0 @@
-/*
- * Copyright 2013 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 <bskeggs@redhat.com>
- */
-
-#include "port.h"
-
-struct anx9805_i2c_port {
-       struct nouveau_i2c_port base;
-       u32 addr;
-       u32 ctrl;
-};
-
-static int
-anx9805_train(struct nouveau_i2c_port *port, int link_nr, int link_bw, bool enh)
-{
-       struct anx9805_i2c_port *chan = (void *)port;
-       struct nouveau_i2c_port *mast = (void *)nv_object(chan)->parent;
-       u8 tmp, i;
-
-       DBG("ANX9805 train %d 0x%02x %d\n", link_nr, link_bw, enh);
-
-       nv_wri2cr(mast, chan->addr, 0xa0, link_bw);
-       nv_wri2cr(mast, chan->addr, 0xa1, link_nr | (enh ? 0x80 : 0x00));
-       nv_wri2cr(mast, chan->addr, 0xa2, 0x01);
-       nv_wri2cr(mast, chan->addr, 0xa8, 0x01);
-
-       i = 0;
-       while ((tmp = nv_rdi2cr(mast, chan->addr, 0xa8)) & 0x01) {
-               mdelay(5);
-               if (i++ == 100) {
-                       nv_error(port, "link training timed out\n");
-                       return -ETIMEDOUT;
-               }
-       }
-
-       if (tmp & 0x70) {
-               nv_error(port, "link training failed: 0x%02x\n", tmp);
-               return -EIO;
-       }
-
-       return 1;
-}
-
-static int
-anx9805_aux(struct nouveau_i2c_port *port, bool retry,
-           u8 type, u32 addr, u8 *data, u8 size)
-{
-       struct anx9805_i2c_port *chan = (void *)port;
-       struct nouveau_i2c_port *mast = (void *)nv_object(chan)->parent;
-       int i, ret = -ETIMEDOUT;
-       u8 buf[16] = {};
-       u8 tmp;
-
-       DBG("%02x %05x %d\n", type, addr, size);
-
-       tmp = nv_rdi2cr(mast, chan->ctrl, 0x07) & ~0x04;
-       nv_wri2cr(mast, chan->ctrl, 0x07, tmp | 0x04);
-       nv_wri2cr(mast, chan->ctrl, 0x07, tmp);
-       nv_wri2cr(mast, chan->ctrl, 0xf7, 0x01);
-
-       nv_wri2cr(mast, chan->addr, 0xe4, 0x80);
-       if (!(type & 1)) {
-               memcpy(buf, data, size);
-               DBG("%16ph", buf);
-               for (i = 0; i < size; i++)
-                       nv_wri2cr(mast, chan->addr, 0xf0 + i, buf[i]);
-       }
-       nv_wri2cr(mast, chan->addr, 0xe5, ((size - 1) << 4) | type);
-       nv_wri2cr(mast, chan->addr, 0xe6, (addr & 0x000ff) >>  0);
-       nv_wri2cr(mast, chan->addr, 0xe7, (addr & 0x0ff00) >>  8);
-       nv_wri2cr(mast, chan->addr, 0xe8, (addr & 0xf0000) >> 16);
-       nv_wri2cr(mast, chan->addr, 0xe9, 0x01);
-
-       i = 0;
-       while ((tmp = nv_rdi2cr(mast, chan->addr, 0xe9)) & 0x01) {
-               mdelay(5);
-               if (i++ == 32)
-                       goto done;
-       }
-
-       if ((tmp = nv_rdi2cr(mast, chan->ctrl, 0xf7)) & 0x01) {
-               ret = -EIO;
-               goto done;
-       }
-
-       if (type & 1) {
-               for (i = 0; i < size; i++)
-                       buf[i] = nv_rdi2cr(mast, chan->addr, 0xf0 + i);
-               DBG("%16ph", buf);
-               memcpy(data, buf, size);
-       }
-
-       ret = 0;
-done:
-       nv_wri2cr(mast, chan->ctrl, 0xf7, 0x01);
-       return ret;
-}
-
-static const struct nouveau_i2c_func
-anx9805_aux_func = {
-       .aux = anx9805_aux,
-       .lnk_ctl = anx9805_train,
-};
-
-static int
-anx9805_aux_chan_ctor(struct nouveau_object *parent,
-                     struct nouveau_object *engine,
-                     struct nouveau_oclass *oclass, void *data, u32 index,
-                     struct nouveau_object **pobject)
-{
-       struct nouveau_i2c_port *mast = (void *)parent;
-       struct anx9805_i2c_port *chan;
-       int ret;
-
-       ret = nouveau_i2c_port_create(parent, engine, oclass, index,
-                                     &nouveau_i2c_aux_algo, &anx9805_aux_func,
-                                     &chan);
-       *pobject = nv_object(chan);
-       if (ret)
-               return ret;
-
-       switch ((oclass->handle & 0xff00) >> 8) {
-       case 0x0d:
-               chan->addr = 0x38;
-               chan->ctrl = 0x39;
-               break;
-       case 0x0e:
-               chan->addr = 0x3c;
-               chan->ctrl = 0x3b;
-               break;
-       default:
-               BUG_ON(1);
-       }
-
-       if (mast->adapter.algo == &i2c_bit_algo) {
-               struct i2c_algo_bit_data *algo = mast->adapter.algo_data;
-               algo->udelay = max(algo->udelay, 40);
-       }
-       return 0;
-}
-
-static struct nouveau_ofuncs
-anx9805_aux_ofuncs = {
-       .ctor =  anx9805_aux_chan_ctor,
-       .dtor = _nouveau_i2c_port_dtor,
-       .init = _nouveau_i2c_port_init,
-       .fini = _nouveau_i2c_port_fini,
-};
-
-static int
-anx9805_xfer(struct i2c_adapter *adap, struct i2c_msg *msgs, int num)
-{
-       struct anx9805_i2c_port *port = adap->algo_data;
-       struct nouveau_i2c_port *mast = (void *)nv_object(port)->parent;
-       struct i2c_msg *msg = msgs;
-       int ret = -ETIMEDOUT;
-       int i, j, cnt = num;
-       u8 seg = 0x00, off = 0x00, tmp;
-
-       tmp = nv_rdi2cr(mast, port->ctrl, 0x07) & ~0x10;
-       nv_wri2cr(mast, port->ctrl, 0x07, tmp | 0x10);
-       nv_wri2cr(mast, port->ctrl, 0x07, tmp);
-       nv_wri2cr(mast, port->addr, 0x43, 0x05);
-       mdelay(5);
-
-       while (cnt--) {
-               if ( (msg->flags & I2C_M_RD) && msg->addr == 0x50) {
-                       nv_wri2cr(mast, port->addr, 0x40, msg->addr << 1);
-                       nv_wri2cr(mast, port->addr, 0x41, seg);
-                       nv_wri2cr(mast, port->addr, 0x42, off);
-                       nv_wri2cr(mast, port->addr, 0x44, msg->len);
-                       nv_wri2cr(mast, port->addr, 0x45, 0x00);
-                       nv_wri2cr(mast, port->addr, 0x43, 0x01);
-                       for (i = 0; i < msg->len; i++) {
-                               j = 0;
-                               while (nv_rdi2cr(mast, port->addr, 0x46) & 0x10) {
-                                       mdelay(5);
-                                       if (j++ == 32)
-                                               goto done;
-                               }
-                               msg->buf[i] = nv_rdi2cr(mast, port->addr, 0x47);
-                       }
-               } else
-               if (!(msg->flags & I2C_M_RD)) {
-                       if (msg->addr == 0x50 && msg->len == 0x01) {
-                               off = msg->buf[0];
-                       } else
-                       if (msg->addr == 0x30 && msg->len == 0x01) {
-                               seg = msg->buf[0];
-                       } else
-                               goto done;
-               } else {
-                       goto done;
-               }
-               msg++;
-       }
-
-       ret = num;
-done:
-       nv_wri2cr(mast, port->addr, 0x43, 0x00);
-       return ret;
-}
-
-static u32
-anx9805_func(struct i2c_adapter *adap)
-{
-       return I2C_FUNC_I2C | I2C_FUNC_SMBUS_EMUL;
-}
-
-static const struct i2c_algorithm
-anx9805_i2c_algo = {
-       .master_xfer = anx9805_xfer,
-       .functionality = anx9805_func
-};
-
-static const struct nouveau_i2c_func
-anx9805_i2c_func = {
-};
-
-static int
-anx9805_ddc_port_ctor(struct nouveau_object *parent,
-                     struct nouveau_object *engine,
-                     struct nouveau_oclass *oclass, void *data, u32 index,
-                     struct nouveau_object **pobject)
-{
-       struct nouveau_i2c_port *mast = (void *)parent;
-       struct anx9805_i2c_port *port;
-       int ret;
-
-       ret = nouveau_i2c_port_create(parent, engine, oclass, index,
-                                     &anx9805_i2c_algo, &anx9805_i2c_func,
-                                     &port);
-       *pobject = nv_object(port);
-       if (ret)
-               return ret;
-
-       switch ((oclass->handle & 0xff00) >> 8) {
-       case 0x0d:
-               port->addr = 0x3d;
-               port->ctrl = 0x39;
-               break;
-       case 0x0e:
-               port->addr = 0x3f;
-               port->ctrl = 0x3b;
-               break;
-       default:
-               BUG_ON(1);
-       }
-
-       if (mast->adapter.algo == &i2c_bit_algo) {
-               struct i2c_algo_bit_data *algo = mast->adapter.algo_data;
-               algo->udelay = max(algo->udelay, 40);
-       }
-       return 0;
-}
-
-static struct nouveau_ofuncs
-anx9805_ddc_ofuncs = {
-       .ctor =  anx9805_ddc_port_ctor,
-       .dtor = _nouveau_i2c_port_dtor,
-       .init = _nouveau_i2c_port_init,
-       .fini = _nouveau_i2c_port_fini,
-};
-
-struct nouveau_oclass
-nouveau_anx9805_sclass[] = {
-       { .handle = NV_I2C_TYPE_EXTDDC(0x0d), .ofuncs = &anx9805_ddc_ofuncs },
-       { .handle = NV_I2C_TYPE_EXTAUX(0x0d), .ofuncs = &anx9805_aux_ofuncs },
-       { .handle = NV_I2C_TYPE_EXTDDC(0x0e), .ofuncs = &anx9805_ddc_ofuncs },
-       { .handle = NV_I2C_TYPE_EXTAUX(0x0e), .ofuncs = &anx9805_aux_ofuncs },
-       {}
-};
diff --git a/drivers/gpu/drm/nouveau/core/subdev/i2c/aux.c b/drivers/gpu/drm/nouveau/core/subdev/i2c/aux.c
deleted file mode 100644 (file)
index 02eb42b..0000000
+++ /dev/null
@@ -1,114 +0,0 @@
-/*
- * 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 "priv.h"
-
-int
-nv_rdaux(struct nouveau_i2c_port *port, u32 addr, u8 *data, u8 size)
-{
-       struct nouveau_i2c *i2c = nouveau_i2c(port);
-       if (port->func->aux) {
-               int ret = i2c->acquire(port, 0);
-               if (ret == 0) {
-                       ret = port->func->aux(port, true, 9, addr, data, size);
-                       i2c->release(port);
-               }
-               return ret;
-       }
-       return -ENODEV;
-}
-
-int
-nv_wraux(struct nouveau_i2c_port *port, u32 addr, u8 *data, u8 size)
-{
-       struct nouveau_i2c *i2c = nouveau_i2c(port);
-       if (port->func->aux) {
-               int ret = i2c->acquire(port, 0);
-               if (ret == 0) {
-                       ret = port->func->aux(port, true, 8, addr, data, size);
-                       i2c->release(port);
-               }
-               return ret;
-       }
-       return -ENODEV;
-}
-
-static int
-aux_xfer(struct i2c_adapter *adap, struct i2c_msg *msgs, int num)
-{
-       struct nouveau_i2c_port *port = adap->algo_data;
-       struct nouveau_i2c *i2c = nouveau_i2c(port);
-       struct i2c_msg *msg = msgs;
-       int ret, mcnt = num;
-
-       if (!port->func->aux)
-               return -ENODEV;
-
-       ret = i2c->acquire(port, 0);
-       if (ret)
-               return ret;
-
-       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 = 1;
-                       else
-                               cmd = 0;
-
-                       if (mcnt || remaining > 16)
-                               cmd |= 4; /* MOT */
-
-                       ret = port->func->aux(port, true, cmd, msg->addr, ptr, cnt);
-                       if (ret < 0) {
-                               i2c->release(port);
-                               return ret;
-                       }
-
-                       ptr += cnt;
-                       remaining -= cnt;
-               }
-
-               msg++;
-       }
-
-       i2c->release(port);
-       return num;
-}
-
-static u32
-aux_func(struct i2c_adapter *adap)
-{
-       return I2C_FUNC_I2C | I2C_FUNC_SMBUS_EMUL;
-}
-
-const struct i2c_algorithm nouveau_i2c_aux_algo = {
-       .master_xfer = aux_xfer,
-       .functionality = aux_func
-};
diff --git a/drivers/gpu/drm/nouveau/core/subdev/i2c/base.c b/drivers/gpu/drm/nouveau/core/subdev/i2c/base.c
deleted file mode 100644 (file)
index 0dc605d..0000000
+++ /dev/null
@@ -1,634 +0,0 @@
-/*
- * Copyright 2013 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 <core/option.h>
-#include <core/object.h>
-#include <core/event.h>
-
-#include <subdev/bios.h>
-#include <subdev/bios/dcb.h>
-#include <subdev/bios/i2c.h>
-#include <subdev/vga.h>
-
-#include "priv.h"
-#include "pad.h"
-
-/******************************************************************************
- * interface to linux i2c bit-banging algorithm
- *****************************************************************************/
-
-#ifdef CONFIG_NOUVEAU_I2C_INTERNAL_DEFAULT
-#define CSTMSEL true
-#else
-#define CSTMSEL false
-#endif
-
-static int
-nouveau_i2c_pre_xfer(struct i2c_adapter *adap)
-{
-       struct i2c_algo_bit_data *bit = adap->algo_data;
-       struct nouveau_i2c_port *port = bit->data;
-       return nouveau_i2c(port)->acquire(port, bit->timeout);
-}
-
-static void
-nouveau_i2c_post_xfer(struct i2c_adapter *adap)
-{
-       struct i2c_algo_bit_data *bit = adap->algo_data;
-       struct nouveau_i2c_port *port = bit->data;
-       return nouveau_i2c(port)->release(port);
-}
-
-static void
-nouveau_i2c_setscl(void *data, int state)
-{
-       struct nouveau_i2c_port *port = data;
-       port->func->drive_scl(port, state);
-}
-
-static void
-nouveau_i2c_setsda(void *data, int state)
-{
-       struct nouveau_i2c_port *port = data;
-       port->func->drive_sda(port, state);
-}
-
-static int
-nouveau_i2c_getscl(void *data)
-{
-       struct nouveau_i2c_port *port = data;
-       return port->func->sense_scl(port);
-}
-
-static int
-nouveau_i2c_getsda(void *data)
-{
-       struct nouveau_i2c_port *port = data;
-       return port->func->sense_sda(port);
-}
-
-/******************************************************************************
- * base i2c "port" class implementation
- *****************************************************************************/
-
-int
-_nouveau_i2c_port_fini(struct nouveau_object *object, bool suspend)
-{
-       struct nouveau_i2c_port *port = (void *)object;
-       struct nvkm_i2c_pad *pad = nvkm_i2c_pad(port);
-       nv_ofuncs(pad)->fini(nv_object(pad), suspend);
-       return nouveau_object_fini(&port->base, suspend);
-}
-
-void
-_nouveau_i2c_port_dtor(struct nouveau_object *object)
-{
-       struct nouveau_i2c_port *port = (void *)object;
-       i2c_del_adapter(&port->adapter);
-       nouveau_object_destroy(&port->base);
-}
-
-int
-nouveau_i2c_port_create_(struct nouveau_object *parent,
-                        struct nouveau_object *engine,
-                        struct nouveau_oclass *oclass, u8 index,
-                        const struct i2c_algorithm *algo,
-                        const struct nouveau_i2c_func *func,
-                        int size, void **pobject)
-{
-       struct nouveau_device *device = nv_device(engine);
-       struct nouveau_i2c *i2c = (void *)engine;
-       struct nouveau_i2c_port *port;
-       int ret;
-
-       ret = nouveau_object_create_(parent, engine, oclass, 0, size, pobject);
-       port = *pobject;
-       if (ret)
-               return ret;
-
-       snprintf(port->adapter.name, sizeof(port->adapter.name),
-                "nouveau-%s-%d", device->name, index);
-       port->adapter.owner = THIS_MODULE;
-       port->adapter.dev.parent = nv_device_base(device);
-       port->index = index;
-       port->aux = -1;
-       port->func = func;
-       mutex_init(&port->mutex);
-
-       if ( algo == &nouveau_i2c_bit_algo &&
-           !nouveau_boolopt(device->cfgopt, "NvI2C", CSTMSEL)) {
-               struct i2c_algo_bit_data *bit;
-
-               bit = kzalloc(sizeof(*bit), GFP_KERNEL);
-               if (!bit)
-                       return -ENOMEM;
-
-               bit->udelay = 10;
-               bit->timeout = usecs_to_jiffies(2200);
-               bit->data = port;
-               bit->pre_xfer = nouveau_i2c_pre_xfer;
-               bit->post_xfer = nouveau_i2c_post_xfer;
-               bit->setsda = nouveau_i2c_setsda;
-               bit->setscl = nouveau_i2c_setscl;
-               bit->getsda = nouveau_i2c_getsda;
-               bit->getscl = nouveau_i2c_getscl;
-
-               port->adapter.algo_data = bit;
-               ret = i2c_bit_add_bus(&port->adapter);
-       } else {
-               port->adapter.algo_data = port;
-               port->adapter.algo = algo;
-               ret = i2c_add_adapter(&port->adapter);
-       }
-
-       if (ret == 0)
-               list_add_tail(&port->head, &i2c->ports);
-       return ret;
-}
-
-/******************************************************************************
- * base i2c subdev class implementation
- *****************************************************************************/
-
-static struct nouveau_i2c_port *
-nouveau_i2c_find(struct nouveau_i2c *i2c, u8 index)
-{
-       struct nouveau_bios *bios = nouveau_bios(i2c);
-       struct nouveau_i2c_port *port;
-
-       if (index == NV_I2C_DEFAULT(0) ||
-           index == NV_I2C_DEFAULT(1)) {
-               u8  ver, hdr, cnt, len;
-               u16 i2c = dcb_i2c_table(bios, &ver, &hdr, &cnt, &len);
-               if (i2c && ver >= 0x30) {
-                       u8 auxidx = nv_ro08(bios, i2c + 4);
-                       if (index == NV_I2C_DEFAULT(0))
-                               index = (auxidx & 0x0f) >> 0;
-                       else
-                               index = (auxidx & 0xf0) >> 4;
-               } else {
-                       index = 2;
-               }
-       }
-
-       list_for_each_entry(port, &i2c->ports, head) {
-               if (port->index == index)
-                       return port;
-       }
-
-       return NULL;
-}
-
-static struct nouveau_i2c_port *
-nouveau_i2c_find_type(struct nouveau_i2c *i2c, u16 type)
-{
-       struct nouveau_i2c_port *port;
-
-       list_for_each_entry(port, &i2c->ports, head) {
-               if (nv_hclass(port) == type)
-                       return port;
-       }
-
-       return NULL;
-}
-
-static void
-nouveau_i2c_release_pad(struct nouveau_i2c_port *port)
-{
-       struct nvkm_i2c_pad *pad = nvkm_i2c_pad(port);
-       struct nouveau_i2c *i2c = nouveau_i2c(port);
-
-       if (atomic_dec_and_test(&nv_object(pad)->usecount)) {
-               nv_ofuncs(pad)->fini(nv_object(pad), false);
-               wake_up_all(&i2c->wait);
-       }
-}
-
-static int
-nouveau_i2c_try_acquire_pad(struct nouveau_i2c_port *port)
-{
-       struct nvkm_i2c_pad *pad = nvkm_i2c_pad(port);
-
-       if (atomic_add_return(1, &nv_object(pad)->usecount) != 1) {
-               struct nouveau_object *owner = (void *)pad->port;
-               do {
-                       if (owner == (void *)port)
-                               return 0;
-                       owner = owner->parent;
-               } while(owner);
-               nouveau_i2c_release_pad(port);
-               return -EBUSY;
-       }
-
-       pad->next = port;
-       nv_ofuncs(pad)->init(nv_object(pad));
-       return 0;
-}
-
-static int
-nouveau_i2c_acquire_pad(struct nouveau_i2c_port *port, unsigned long timeout)
-{
-       struct nouveau_i2c *i2c = nouveau_i2c(port);
-
-       if (timeout) {
-               if (wait_event_timeout(i2c->wait,
-                                      nouveau_i2c_try_acquire_pad(port) == 0,
-                                      timeout) == 0)
-                       return -EBUSY;
-       } else {
-               wait_event(i2c->wait, nouveau_i2c_try_acquire_pad(port) == 0);
-       }
-
-       return 0;
-}
-
-static void
-nouveau_i2c_release(struct nouveau_i2c_port *port)
-__releases(pad->mutex)
-{
-       nouveau_i2c(port)->release_pad(port);
-       mutex_unlock(&port->mutex);
-}
-
-static int
-nouveau_i2c_acquire(struct nouveau_i2c_port *port, unsigned long timeout)
-__acquires(pad->mutex)
-{
-       int ret;
-       mutex_lock(&port->mutex);
-       if ((ret = nouveau_i2c(port)->acquire_pad(port, timeout)))
-               mutex_unlock(&port->mutex);
-       return ret;
-}
-
-static int
-nouveau_i2c_identify(struct nouveau_i2c *i2c, int index, const char *what,
-                    struct nouveau_i2c_board_info *info,
-                    bool (*match)(struct nouveau_i2c_port *,
-                                  struct i2c_board_info *, void *), void *data)
-{
-       struct nouveau_i2c_port *port = nouveau_i2c_find(i2c, index);
-       int i;
-
-       if (!port) {
-               nv_debug(i2c, "no bus when probing %s on %d\n", what, index);
-               return -ENODEV;
-       }
-
-       nv_debug(i2c, "probing %ss on bus: %d\n", what, port->index);
-       for (i = 0; info[i].dev.addr; i++) {
-               u8 orig_udelay = 0;
-
-               if ((port->adapter.algo == &i2c_bit_algo) &&
-                   (info[i].udelay != 0)) {
-                       struct i2c_algo_bit_data *algo = port->adapter.algo_data;
-                       nv_debug(i2c, "using custom udelay %d instead of %d\n",
-                                info[i].udelay, algo->udelay);
-                       orig_udelay = algo->udelay;
-                       algo->udelay = info[i].udelay;
-               }
-
-               if (nv_probe_i2c(port, info[i].dev.addr) &&
-                   (!match || match(port, &info[i].dev, data))) {
-                       nv_info(i2c, "detected %s: %s\n", what,
-                               info[i].dev.type);
-                       return i;
-               }
-
-               if (orig_udelay) {
-                       struct i2c_algo_bit_data *algo = port->adapter.algo_data;
-                       algo->udelay = orig_udelay;
-               }
-       }
-
-       nv_debug(i2c, "no devices found.\n");
-       return -ENODEV;
-}
-
-static void
-nouveau_i2c_intr_fini(struct nvkm_event *event, int type, int index)
-{
-       struct nouveau_i2c *i2c = container_of(event, typeof(*i2c), event);
-       struct nouveau_i2c_port *port = i2c->find(i2c, index);
-       const struct nouveau_i2c_impl *impl = (void *)nv_object(i2c)->oclass;
-       if (port && port->aux >= 0)
-               impl->aux_mask(i2c, type, 1 << port->aux, 0);
-}
-
-static void
-nouveau_i2c_intr_init(struct nvkm_event *event, int type, int index)
-{
-       struct nouveau_i2c *i2c = container_of(event, typeof(*i2c), event);
-       struct nouveau_i2c_port *port = i2c->find(i2c, index);
-       const struct nouveau_i2c_impl *impl = (void *)nv_object(i2c)->oclass;
-       if (port && port->aux >= 0)
-               impl->aux_mask(i2c, type, 1 << port->aux, 1 << port->aux);
-}
-
-static int
-nouveau_i2c_intr_ctor(struct nouveau_object *object, void *data, u32 size,
-                     struct nvkm_notify *notify)
-{
-       struct nvkm_i2c_ntfy_req *req = data;
-       if (!WARN_ON(size != sizeof(*req))) {
-               notify->size  = sizeof(struct nvkm_i2c_ntfy_rep);
-               notify->types = req->mask;
-               notify->index = req->port;
-               return 0;
-       }
-       return -EINVAL;
-}
-
-static void
-nouveau_i2c_intr(struct nouveau_subdev *subdev)
-{
-       struct nouveau_i2c_impl *impl = (void *)nv_oclass(subdev);
-       struct nouveau_i2c *i2c = nouveau_i2c(subdev);
-       struct nouveau_i2c_port *port;
-       u32 hi, lo, rq, tx, e;
-
-       if (impl->aux_stat) {
-               impl->aux_stat(i2c, &hi, &lo, &rq, &tx);
-               if (hi || lo || rq || tx) {
-                       list_for_each_entry(port, &i2c->ports, head) {
-                               if (e = 0, port->aux < 0)
-                                       continue;
-
-                               if (hi & (1 << port->aux)) e |= NVKM_I2C_PLUG;
-                               if (lo & (1 << port->aux)) e |= NVKM_I2C_UNPLUG;
-                               if (rq & (1 << port->aux)) e |= NVKM_I2C_IRQ;
-                               if (tx & (1 << port->aux)) e |= NVKM_I2C_DONE;
-                               if (e) {
-                                       struct nvkm_i2c_ntfy_rep rep = {
-                                               .mask = e,
-                                       };
-                                       nvkm_event_send(&i2c->event, rep.mask,
-                                                       port->index, &rep,
-                                                       sizeof(rep));
-                               }
-                       }
-               }
-       }
-}
-
-static const struct nvkm_event_func
-nouveau_i2c_intr_func = {
-       .ctor = nouveau_i2c_intr_ctor,
-       .init = nouveau_i2c_intr_init,
-       .fini = nouveau_i2c_intr_fini,
-};
-
-int
-_nouveau_i2c_fini(struct nouveau_object *object, bool suspend)
-{
-       struct nouveau_i2c_impl *impl = (void *)nv_oclass(object);
-       struct nouveau_i2c *i2c = (void *)object;
-       struct nouveau_i2c_port *port;
-       u32 mask;
-       int ret;
-
-       list_for_each_entry(port, &i2c->ports, head) {
-               ret = nv_ofuncs(port)->fini(nv_object(port), suspend);
-               if (ret && suspend)
-                       goto fail;
-       }
-
-       if ((mask = (1 << impl->aux) - 1), impl->aux_stat) {
-               impl->aux_mask(i2c, NVKM_I2C_ANY, mask, 0);
-               impl->aux_stat(i2c, &mask, &mask, &mask, &mask);
-       }
-
-       return nouveau_subdev_fini(&i2c->base, suspend);
-fail:
-       list_for_each_entry_continue_reverse(port, &i2c->ports, head) {
-               nv_ofuncs(port)->init(nv_object(port));
-       }
-
-       return ret;
-}
-
-int
-_nouveau_i2c_init(struct nouveau_object *object)
-{
-       struct nouveau_i2c *i2c = (void *)object;
-       struct nouveau_i2c_port *port;
-       int ret;
-
-       ret = nouveau_subdev_init(&i2c->base);
-       if (ret == 0) {
-               list_for_each_entry(port, &i2c->ports, head) {
-                       ret = nv_ofuncs(port)->init(nv_object(port));
-                       if (ret)
-                               goto fail;
-               }
-       }
-
-       return ret;
-fail:
-       list_for_each_entry_continue_reverse(port, &i2c->ports, head) {
-               nv_ofuncs(port)->fini(nv_object(port), false);
-       }
-
-       return ret;
-}
-
-void
-_nouveau_i2c_dtor(struct nouveau_object *object)
-{
-       struct nouveau_i2c *i2c = (void *)object;
-       struct nouveau_i2c_port *port, *temp;
-
-       nvkm_event_fini(&i2c->event);
-
-       list_for_each_entry_safe(port, temp, &i2c->ports, head) {
-               nouveau_object_ref(NULL, (struct nouveau_object **)&port);
-       }
-
-       nouveau_subdev_destroy(&i2c->base);
-}
-
-static struct nouveau_oclass *
-nouveau_i2c_extdev_sclass[] = {
-       nouveau_anx9805_sclass,
-};
-
-static void
-nouveau_i2c_create_port(struct nouveau_i2c *i2c, int index, u8 type,
-                       struct dcb_i2c_entry *info)
-{
-       const struct nouveau_i2c_impl *impl = (void *)nv_oclass(i2c);
-       struct nouveau_oclass *oclass;
-       struct nouveau_object *parent;
-       struct nouveau_object *object;
-       int ret, pad;
-
-       if (info->share != DCB_I2C_UNUSED) {
-               pad    = info->share;
-               oclass = impl->pad_s;
-       } else {
-               if (type != DCB_I2C_NVIO_AUX)
-                       pad = 0x100 + info->drive;
-               else
-                       pad = 0x100 + info->auxch;
-               oclass = impl->pad_x;
-       }
-
-       ret = nouveau_object_ctor(NULL, nv_object(i2c), oclass, NULL, pad,
-                                &parent);
-       if (ret < 0)
-               return;
-
-       oclass = impl->sclass;
-       do {
-               ret = -EINVAL;
-               if (oclass->handle == type) {
-                       ret = nouveau_object_ctor(parent, nv_object(i2c),
-                                                 oclass, info, index,
-                                                &object);
-               }
-       } while (ret && (++oclass)->handle);
-
-       nouveau_object_ref(NULL, &parent);
-}
-
-int
-nouveau_i2c_create_(struct nouveau_object *parent,
-                   struct nouveau_object *engine,
-                   struct nouveau_oclass *oclass,
-                   int length, void **pobject)
-{
-       struct nouveau_bios *bios = nouveau_bios(parent);
-       struct nouveau_i2c *i2c;
-       struct nouveau_object *object;
-       struct dcb_i2c_entry info;
-       int ret, i, j, index = -1;
-       struct dcb_output outp;
-       u8  ver, hdr;
-       u32 data;
-
-       ret = nouveau_subdev_create(parent, engine, oclass, 0,
-                                   "I2C", "i2c", &i2c);
-       *pobject = nv_object(i2c);
-       if (ret)
-               return ret;
-
-       nv_subdev(i2c)->intr = nouveau_i2c_intr;
-       i2c->find = nouveau_i2c_find;
-       i2c->find_type = nouveau_i2c_find_type;
-       i2c->acquire_pad = nouveau_i2c_acquire_pad;
-       i2c->release_pad = nouveau_i2c_release_pad;
-       i2c->acquire = nouveau_i2c_acquire;
-       i2c->release = nouveau_i2c_release;
-       i2c->identify = nouveau_i2c_identify;
-       init_waitqueue_head(&i2c->wait);
-       INIT_LIST_HEAD(&i2c->ports);
-
-       while (!dcb_i2c_parse(bios, ++index, &info)) {
-               switch (info.type) {
-               case DCB_I2C_NV04_BIT:
-               case DCB_I2C_NV4E_BIT:
-               case DCB_I2C_NVIO_BIT:
-                       nouveau_i2c_create_port(i2c, NV_I2C_PORT(index),
-                                               info.type, &info);
-                       break;
-               case DCB_I2C_NVIO_AUX:
-                       nouveau_i2c_create_port(i2c, NV_I2C_AUX(index),
-                                               info.type, &info);
-                       break;
-               case DCB_I2C_PMGR:
-                       if (info.drive != DCB_I2C_UNUSED) {
-                               nouveau_i2c_create_port(i2c, NV_I2C_PORT(index),
-                                                       DCB_I2C_NVIO_BIT,
-                                                       &info);
-                       }
-                       if (info.auxch != DCB_I2C_UNUSED) {
-                               nouveau_i2c_create_port(i2c, NV_I2C_AUX(index),
-                                                       DCB_I2C_NVIO_AUX,
-                                                       &info);
-                       }
-                       break;
-               case DCB_I2C_UNUSED:
-               default:
-                       continue;
-               }
-       }
-
-       /* in addition to the busses specified in the i2c table, there
-        * may be ddc/aux channels hiding behind external tmds/dp/etc
-        * transmitters.
-        */
-       index = NV_I2C_EXT(0);
-       i = -1;
-       while ((data = dcb_outp_parse(bios, ++i, &ver, &hdr, &outp))) {
-               if (!outp.location || !outp.extdev)
-                       continue;
-
-               switch (outp.type) {
-               case DCB_OUTPUT_TMDS:
-                       info.type = NV_I2C_TYPE_EXTDDC(outp.extdev);
-                       break;
-               case DCB_OUTPUT_DP:
-                       info.type = NV_I2C_TYPE_EXTAUX(outp.extdev);
-                       break;
-               default:
-                       continue;
-               }
-
-               ret = -ENODEV;
-               j = -1;
-               while (ret && ++j < ARRAY_SIZE(nouveau_i2c_extdev_sclass)) {
-                       parent = nv_object(i2c->find(i2c, outp.i2c_index));
-                       oclass = nouveau_i2c_extdev_sclass[j];
-                       do {
-                               if (oclass->handle != info.type)
-                                       continue;
-                               ret = nouveau_object_ctor(parent, *pobject,
-                                                         oclass, NULL,
-                                                         index++, &object);
-                       } while (ret && (++oclass)->handle);
-               }
-       }
-
-       ret = nvkm_event_init(&nouveau_i2c_intr_func, 4, index, &i2c->event);
-       if (ret)
-               return ret;
-
-       return 0;
-}
-
-int
-_nouveau_i2c_ctor(struct nouveau_object *parent, struct nouveau_object *engine,
-                 struct nouveau_oclass *oclass, void *data, u32 size,
-                 struct nouveau_object **pobject)
-{
-       struct nouveau_i2c *i2c;
-       int ret;
-
-       ret = nouveau_i2c_create(parent, engine, oclass, &i2c);
-       *pobject = nv_object(i2c);
-       if (ret)
-               return ret;
-
-       return 0;
-}
diff --git a/drivers/gpu/drm/nouveau/core/subdev/i2c/bit.c b/drivers/gpu/drm/nouveau/core/subdev/i2c/bit.c
deleted file mode 100644 (file)
index 813ffc9..0000000
+++ /dev/null
@@ -1,234 +0,0 @@
-/*
- * Copyright 2012 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 "priv.h"
-
-#ifdef CONFIG_NOUVEAU_I2C_INTERNAL
-#define T_TIMEOUT  2200000
-#define T_RISEFALL 1000
-#define T_HOLD     5000
-
-static inline void
-i2c_drive_scl(struct nouveau_i2c_port *port, int state)
-{
-       port->func->drive_scl(port, state);
-}
-
-static inline void
-i2c_drive_sda(struct nouveau_i2c_port *port, int state)
-{
-       port->func->drive_sda(port, state);
-}
-
-static inline int
-i2c_sense_scl(struct nouveau_i2c_port *port)
-{
-       return port->func->sense_scl(port);
-}
-
-static inline int
-i2c_sense_sda(struct nouveau_i2c_port *port)
-{
-       return port->func->sense_sda(port);
-}
-
-static void
-i2c_delay(struct nouveau_i2c_port *port, u32 nsec)
-{
-       udelay((nsec + 500) / 1000);
-}
-
-static bool
-i2c_raise_scl(struct nouveau_i2c_port *port)
-{
-       u32 timeout = T_TIMEOUT / T_RISEFALL;
-
-       i2c_drive_scl(port, 1);
-       do {
-               i2c_delay(port, T_RISEFALL);
-       } while (!i2c_sense_scl(port) && --timeout);
-
-       return timeout != 0;
-}
-
-static int
-i2c_start(struct nouveau_i2c_port *port)
-{
-       int ret = 0;
-
-       if (!i2c_sense_scl(port) ||
-           !i2c_sense_sda(port)) {
-               i2c_drive_scl(port, 0);
-               i2c_drive_sda(port, 1);
-               if (!i2c_raise_scl(port))
-                       ret = -EBUSY;
-       }
-
-       i2c_drive_sda(port, 0);
-       i2c_delay(port, T_HOLD);
-       i2c_drive_scl(port, 0);
-       i2c_delay(port, T_HOLD);
-       return ret;
-}
-
-static void
-i2c_stop(struct nouveau_i2c_port *port)
-{
-       i2c_drive_scl(port, 0);
-       i2c_drive_sda(port, 0);
-       i2c_delay(port, T_RISEFALL);
-
-       i2c_drive_scl(port, 1);
-       i2c_delay(port, T_HOLD);
-       i2c_drive_sda(port, 1);
-       i2c_delay(port, T_HOLD);
-}
-
-static int
-i2c_bitw(struct nouveau_i2c_port *port, int sda)
-{
-       i2c_drive_sda(port, sda);
-       i2c_delay(port, T_RISEFALL);
-
-       if (!i2c_raise_scl(port))
-               return -ETIMEDOUT;
-       i2c_delay(port, T_HOLD);
-
-       i2c_drive_scl(port, 0);
-       i2c_delay(port, T_HOLD);
-       return 0;
-}
-
-static int
-i2c_bitr(struct nouveau_i2c_port *port)
-{
-       int sda;
-
-       i2c_drive_sda(port, 1);
-       i2c_delay(port, T_RISEFALL);
-
-       if (!i2c_raise_scl(port))
-               return -ETIMEDOUT;
-       i2c_delay(port, T_HOLD);
-
-       sda = i2c_sense_sda(port);
-
-       i2c_drive_scl(port, 0);
-       i2c_delay(port, T_HOLD);
-       return sda;
-}
-
-static int
-i2c_get_byte(struct nouveau_i2c_port *port, u8 *byte, bool last)
-{
-       int i, bit;
-
-       *byte = 0;
-       for (i = 7; i >= 0; i--) {
-               bit = i2c_bitr(port);
-               if (bit < 0)
-                       return bit;
-               *byte |= bit << i;
-       }
-
-       return i2c_bitw(port, last ? 1 : 0);
-}
-
-static int
-i2c_put_byte(struct nouveau_i2c_port *port, u8 byte)
-{
-       int i, ret;
-       for (i = 7; i >= 0; i--) {
-               ret = i2c_bitw(port, !!(byte & (1 << i)));
-               if (ret < 0)
-                       return ret;
-       }
-
-       ret = i2c_bitr(port);
-       if (ret == 1) /* nack */
-               ret = -EIO;
-       return ret;
-}
-
-static int
-i2c_addr(struct nouveau_i2c_port *port, struct i2c_msg *msg)
-{
-       u32 addr = msg->addr << 1;
-       if (msg->flags & I2C_M_RD)
-               addr |= 1;
-       return i2c_put_byte(port, addr);
-}
-
-static int
-i2c_bit_xfer(struct i2c_adapter *adap, struct i2c_msg *msgs, int num)
-{
-       struct nouveau_i2c_port *port = adap->algo_data;
-       struct i2c_msg *msg = msgs;
-       int ret = 0, mcnt = num;
-
-       ret = nouveau_i2c(port)->acquire(port, nsecs_to_jiffies(T_TIMEOUT));
-       if (ret)
-               return ret;
-
-       while (!ret && mcnt--) {
-               u8 remaining = msg->len;
-               u8 *ptr = msg->buf;
-
-               ret = i2c_start(port);
-               if (ret == 0)
-                       ret = i2c_addr(port, msg);
-
-               if (msg->flags & I2C_M_RD) {
-                       while (!ret && remaining--)
-                               ret = i2c_get_byte(port, ptr++, !remaining);
-               } else {
-                       while (!ret && remaining--)
-                               ret = i2c_put_byte(port, *ptr++);
-               }
-
-               msg++;
-       }
-
-       i2c_stop(port);
-       nouveau_i2c(port)->release(port);
-       return (ret < 0) ? ret : num;
-}
-#else
-static int
-i2c_bit_xfer(struct i2c_adapter *adap, struct i2c_msg *msgs, int num)
-{
-       return -ENODEV;
-}
-#endif
-
-static u32
-i2c_bit_func(struct i2c_adapter *adap)
-{
-       return I2C_FUNC_I2C | I2C_FUNC_SMBUS_EMUL;
-}
-
-const struct i2c_algorithm nouveau_i2c_bit_algo = {
-       .master_xfer = i2c_bit_xfer,
-       .functionality = i2c_bit_func
-};
diff --git a/drivers/gpu/drm/nouveau/core/subdev/i2c/gf117.c b/drivers/gpu/drm/nouveau/core/subdev/i2c/gf117.c
deleted file mode 100644 (file)
index fa891c3..0000000
+++ /dev/null
@@ -1,39 +0,0 @@
-/*
- * Copyright 2012 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 "nv50.h"
-
-struct nouveau_oclass *
-gf117_i2c_oclass = &(struct nouveau_i2c_impl) {
-       .base.handle = NV_SUBDEV(I2C, 0xd7),
-       .base.ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = _nouveau_i2c_ctor,
-               .dtor = _nouveau_i2c_dtor,
-               .init = _nouveau_i2c_init,
-               .fini = _nouveau_i2c_fini,
-       },
-       .sclass = nvd0_i2c_sclass,
-       .pad_x = &nv04_i2c_pad_oclass,
-       .pad_s = &nv04_i2c_pad_oclass,
-}.base;
diff --git a/drivers/gpu/drm/nouveau/core/subdev/i2c/gm204.c b/drivers/gpu/drm/nouveau/core/subdev/i2c/gm204.c
deleted file mode 100644 (file)
index 06a2b87..0000000
+++ /dev/null
@@ -1,221 +0,0 @@
-/*
- * Copyright 2012 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 "nv50.h"
-
-#define AUX_DBG(fmt, args...) nv_debug(aux, "AUXCH(%d): " fmt, ch, ##args)
-#define AUX_ERR(fmt, args...) nv_error(aux, "AUXCH(%d): " fmt, ch, ##args)
-
-static void
-auxch_fini(struct nouveau_i2c *aux, int ch)
-{
-       nv_mask(aux, 0x00d954 + (ch * 0x50), 0x00310000, 0x00000000);
-}
-
-static int
-auxch_init(struct nouveau_i2c *aux, int ch)
-{
-       const u32 unksel = 1; /* nfi which to use, or if it matters.. */
-       const u32 ureq = unksel ? 0x00100000 : 0x00200000;
-       const u32 urep = unksel ? 0x01000000 : 0x02000000;
-       u32 ctrl, timeout;
-
-       /* wait up to 1ms for any previous transaction to be done... */
-       timeout = 1000;
-       do {
-               ctrl = nv_rd32(aux, 0x00d954 + (ch * 0x50));
-               udelay(1);
-               if (!timeout--) {
-                       AUX_ERR("begin idle timeout 0x%08x\n", ctrl);
-                       return -EBUSY;
-               }
-       } while (ctrl & 0x03010000);
-
-       /* set some magic, and wait up to 1ms for it to appear */
-       nv_mask(aux, 0x00d954 + (ch * 0x50), 0x00300000, ureq);
-       timeout = 1000;
-       do {
-               ctrl = nv_rd32(aux, 0x00d954 + (ch * 0x50));
-               udelay(1);
-               if (!timeout--) {
-                       AUX_ERR("magic wait 0x%08x\n", ctrl);
-                       auxch_fini(aux, ch);
-                       return -EBUSY;
-               }
-       } while ((ctrl & 0x03000000) != urep);
-
-       return 0;
-}
-
-int
-gm204_aux(struct nouveau_i2c_port *base, bool retry,
-        u8 type, u32 addr, u8 *data, u8 size)
-{
-       struct nouveau_i2c *aux = nouveau_i2c(base);
-       struct nv50_i2c_port *port = (void *)base;
-       u32 ctrl, stat, timeout, retries;
-       u32 xbuf[4] = {};
-       int ch = port->addr;
-       int ret, i;
-
-       AUX_DBG("%d: 0x%08x %d\n", type, addr, size);
-
-       ret = auxch_init(aux, ch);
-       if (ret)
-               goto out;
-
-       stat = nv_rd32(aux, 0x00d958 + (ch * 0x50));
-       if (!(stat & 0x10000000)) {
-               AUX_DBG("sink not detected\n");
-               ret = -ENXIO;
-               goto out;
-       }
-
-       if (!(type & 1)) {
-               memcpy(xbuf, data, size);
-               for (i = 0; i < 16; i += 4) {
-                       AUX_DBG("wr 0x%08x\n", xbuf[i / 4]);
-                       nv_wr32(aux, 0x00d930 + (ch * 0x50) + i, xbuf[i / 4]);
-               }
-       }
-
-       ctrl  = nv_rd32(aux, 0x00d954 + (ch * 0x50));
-       ctrl &= ~0x0001f0ff;
-       ctrl |= type << 12;
-       ctrl |= size - 1;
-       nv_wr32(aux, 0x00d950 + (ch * 0x50), addr);
-
-       /* (maybe) retry transaction a number of times on failure... */
-       for (retries = 0; !ret && retries < 32; retries++) {
-               /* reset, and delay a while if this is a retry */
-               nv_wr32(aux, 0x00d954 + (ch * 0x50), 0x80000000 | ctrl);
-               nv_wr32(aux, 0x00d954 + (ch * 0x50), 0x00000000 | ctrl);
-               if (retries)
-                       udelay(400);
-
-               /* transaction request, wait up to 1ms for it to complete */
-               nv_wr32(aux, 0x00d954 + (ch * 0x50), 0x00010000 | ctrl);
-
-               timeout = 1000;
-               do {
-                       ctrl = nv_rd32(aux, 0x00d954 + (ch * 0x50));
-                       udelay(1);
-                       if (!timeout--) {
-                               AUX_ERR("tx req timeout 0x%08x\n", ctrl);
-                               ret = -EIO;
-                               goto out;
-                       }
-               } while (ctrl & 0x00010000);
-               ret = 1;
-
-               /* read status, and check if transaction completed ok */
-               stat = nv_mask(aux, 0x00d958 + (ch * 0x50), 0, 0);
-               if ((stat & 0x000f0000) == 0x00080000 ||
-                   (stat & 0x000f0000) == 0x00020000)
-                       ret = retry ? 0 : 1;
-               if ((stat & 0x00000100))
-                       ret = -ETIMEDOUT;
-               if ((stat & 0x00000e00))
-                       ret = -EIO;
-
-               AUX_DBG("%02d 0x%08x 0x%08x\n", retries, ctrl, stat);
-       }
-
-       if (type & 1) {
-               for (i = 0; i < 16; i += 4) {
-                       xbuf[i / 4] = nv_rd32(aux, 0x00d940 + (ch * 0x50) + i);
-                       AUX_DBG("rd 0x%08x\n", xbuf[i / 4]);
-               }
-               memcpy(data, xbuf, size);
-       }
-
-out:
-       auxch_fini(aux, ch);
-       return ret < 0 ? ret : (stat & 0x000f0000) >> 16;
-}
-
-static const struct nouveau_i2c_func
-gm204_aux_func = {
-       .aux       = gm204_aux,
-};
-
-int
-gm204_aux_port_ctor(struct nouveau_object *parent,
-                   struct nouveau_object *engine,
-                   struct nouveau_oclass *oclass, void *data, u32 index,
-                   struct nouveau_object **pobject)
-{
-       struct dcb_i2c_entry *info = data;
-       struct nv50_i2c_port *port;
-       int ret;
-
-       ret = nouveau_i2c_port_create(parent, engine, oclass, index,
-                                     &nouveau_i2c_aux_algo, &gm204_aux_func,
-                                     &port);
-       *pobject = nv_object(port);
-       if (ret)
-               return ret;
-
-       port->base.aux = info->auxch;
-       port->addr = info->auxch;
-       return 0;
-}
-
-struct nouveau_oclass
-gm204_i2c_sclass[] = {
-       { .handle = NV_I2C_TYPE_DCBI2C(DCB_I2C_NVIO_BIT),
-         .ofuncs = &(struct nouveau_ofuncs) {
-                 .ctor = nvd0_i2c_port_ctor,
-                 .dtor = _nouveau_i2c_port_dtor,
-                 .init = nv50_i2c_port_init,
-                 .fini = _nouveau_i2c_port_fini,
-         },
-       },
-       { .handle = NV_I2C_TYPE_DCBI2C(DCB_I2C_NVIO_AUX),
-         .ofuncs = &(struct nouveau_ofuncs) {
-                 .ctor = gm204_aux_port_ctor,
-                 .dtor = _nouveau_i2c_port_dtor,
-                 .init = _nouveau_i2c_port_init,
-                 .fini = _nouveau_i2c_port_fini,
-         },
-       },
-       {}
-};
-
-struct nouveau_oclass *
-gm204_i2c_oclass = &(struct nouveau_i2c_impl) {
-       .base.handle = NV_SUBDEV(I2C, 0x24),
-       .base.ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = _nouveau_i2c_ctor,
-               .dtor = _nouveau_i2c_dtor,
-               .init = _nouveau_i2c_init,
-               .fini = _nouveau_i2c_fini,
-       },
-       .sclass = gm204_i2c_sclass,
-       .pad_x = &nv04_i2c_pad_oclass,
-       .pad_s = &gm204_i2c_pad_oclass,
-       .aux = 8,
-       .aux_stat = nve0_aux_stat,
-       .aux_mask = nve0_aux_mask,
-}.base;
diff --git a/drivers/gpu/drm/nouveau/core/subdev/i2c/nv04.c b/drivers/gpu/drm/nouveau/core/subdev/i2c/nv04.c
deleted file mode 100644 (file)
index b1725bd..0000000
+++ /dev/null
@@ -1,130 +0,0 @@
-/*
- * Copyright 2012 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 <subdev/vga.h>
-
-#include "priv.h"
-
-struct nv04_i2c_priv {
-       struct nouveau_i2c base;
-};
-
-struct nv04_i2c_port {
-       struct nouveau_i2c_port base;
-       u8 drive;
-       u8 sense;
-};
-
-static void
-nv04_i2c_drive_scl(struct nouveau_i2c_port *base, int state)
-{
-       struct nv04_i2c_priv *priv = (void *)nv_object(base)->engine;
-       struct nv04_i2c_port *port = (void *)base;
-       u8 val = nv_rdvgac(priv, 0, port->drive);
-       if (state) val |= 0x20;
-       else       val &= 0xdf;
-       nv_wrvgac(priv, 0, port->drive, val | 0x01);
-}
-
-static void
-nv04_i2c_drive_sda(struct nouveau_i2c_port *base, int state)
-{
-       struct nv04_i2c_priv *priv = (void *)nv_object(base)->engine;
-       struct nv04_i2c_port *port = (void *)base;
-       u8 val = nv_rdvgac(priv, 0, port->drive);
-       if (state) val |= 0x10;
-       else       val &= 0xef;
-       nv_wrvgac(priv, 0, port->drive, val | 0x01);
-}
-
-static int
-nv04_i2c_sense_scl(struct nouveau_i2c_port *base)
-{
-       struct nv04_i2c_priv *priv = (void *)nv_object(base)->engine;
-       struct nv04_i2c_port *port = (void *)base;
-       return !!(nv_rdvgac(priv, 0, port->sense) & 0x04);
-}
-
-static int
-nv04_i2c_sense_sda(struct nouveau_i2c_port *base)
-{
-       struct nv04_i2c_priv *priv = (void *)nv_object(base)->engine;
-       struct nv04_i2c_port *port = (void *)base;
-       return !!(nv_rdvgac(priv, 0, port->sense) & 0x08);
-}
-
-static const struct nouveau_i2c_func
-nv04_i2c_func = {
-       .drive_scl = nv04_i2c_drive_scl,
-       .drive_sda = nv04_i2c_drive_sda,
-       .sense_scl = nv04_i2c_sense_scl,
-       .sense_sda = nv04_i2c_sense_sda,
-};
-
-static int
-nv04_i2c_port_ctor(struct nouveau_object *parent, struct nouveau_object *engine,
-                  struct nouveau_oclass *oclass, void *data, u32 index,
-                  struct nouveau_object **pobject)
-{
-       struct dcb_i2c_entry *info = data;
-       struct nv04_i2c_port *port;
-       int ret;
-
-       ret = nouveau_i2c_port_create(parent, engine, oclass, index,
-                                     &nouveau_i2c_bit_algo, &nv04_i2c_func,
-                                     &port);
-       *pobject = nv_object(port);
-       if (ret)
-               return ret;
-
-       port->drive = info->drive;
-       port->sense = info->sense;
-       return 0;
-}
-
-static struct nouveau_oclass
-nv04_i2c_sclass[] = {
-       { .handle = NV_I2C_TYPE_DCBI2C(DCB_I2C_NV04_BIT),
-         .ofuncs = &(struct nouveau_ofuncs) {
-                 .ctor = nv04_i2c_port_ctor,
-                 .dtor = _nouveau_i2c_port_dtor,
-                 .init = _nouveau_i2c_port_init,
-                 .fini = _nouveau_i2c_port_fini,
-         },
-       },
-       {}
-};
-
-struct nouveau_oclass *
-nv04_i2c_oclass = &(struct nouveau_i2c_impl) {
-       .base.handle = NV_SUBDEV(I2C, 0x04),
-       .base.ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = _nouveau_i2c_ctor,
-               .dtor = _nouveau_i2c_dtor,
-               .init = _nouveau_i2c_init,
-               .fini = _nouveau_i2c_fini,
-       },
-       .sclass = nv04_i2c_sclass,
-       .pad_x = &nv04_i2c_pad_oclass,
-}.base;
diff --git a/drivers/gpu/drm/nouveau/core/subdev/i2c/nv4e.c b/drivers/gpu/drm/nouveau/core/subdev/i2c/nv4e.c
deleted file mode 100644 (file)
index f16c87c..0000000
+++ /dev/null
@@ -1,122 +0,0 @@
-/*
- * Copyright 2012 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 <subdev/vga.h>
-
-#include "priv.h"
-
-struct nv4e_i2c_priv {
-       struct nouveau_i2c base;
-};
-
-struct nv4e_i2c_port {
-       struct nouveau_i2c_port base;
-       u32 addr;
-};
-
-static void
-nv4e_i2c_drive_scl(struct nouveau_i2c_port *base, int state)
-{
-       struct nv4e_i2c_priv *priv = (void *)nv_object(base)->engine;
-       struct nv4e_i2c_port *port = (void *)base;
-       nv_mask(priv, port->addr, 0x2f, state ? 0x21 : 0x01);
-}
-
-static void
-nv4e_i2c_drive_sda(struct nouveau_i2c_port *base, int state)
-{
-       struct nv4e_i2c_priv *priv = (void *)nv_object(base)->engine;
-       struct nv4e_i2c_port *port = (void *)base;
-       nv_mask(priv, port->addr, 0x1f, state ? 0x11 : 0x01);
-}
-
-static int
-nv4e_i2c_sense_scl(struct nouveau_i2c_port *base)
-{
-       struct nv4e_i2c_priv *priv = (void *)nv_object(base)->engine;
-       struct nv4e_i2c_port *port = (void *)base;
-       return !!(nv_rd32(priv, port->addr) & 0x00040000);
-}
-
-static int
-nv4e_i2c_sense_sda(struct nouveau_i2c_port *base)
-{
-       struct nv4e_i2c_priv *priv = (void *)nv_object(base)->engine;
-       struct nv4e_i2c_port *port = (void *)base;
-       return !!(nv_rd32(priv, port->addr) & 0x00080000);
-}
-
-static const struct nouveau_i2c_func
-nv4e_i2c_func = {
-       .drive_scl = nv4e_i2c_drive_scl,
-       .drive_sda = nv4e_i2c_drive_sda,
-       .sense_scl = nv4e_i2c_sense_scl,
-       .sense_sda = nv4e_i2c_sense_sda,
-};
-
-static int
-nv4e_i2c_port_ctor(struct nouveau_object *parent, struct nouveau_object *engine,
-                  struct nouveau_oclass *oclass, void *data, u32 index,
-                  struct nouveau_object **pobject)
-{
-       struct dcb_i2c_entry *info = data;
-       struct nv4e_i2c_port *port;
-       int ret;
-
-       ret = nouveau_i2c_port_create(parent, engine, oclass, index,
-                                     &nouveau_i2c_bit_algo, &nv4e_i2c_func,
-                                     &port);
-       *pobject = nv_object(port);
-       if (ret)
-               return ret;
-
-       port->addr = 0x600800 + info->drive;
-       return 0;
-}
-
-static struct nouveau_oclass
-nv4e_i2c_sclass[] = {
-       { .handle = NV_I2C_TYPE_DCBI2C(DCB_I2C_NV4E_BIT),
-         .ofuncs = &(struct nouveau_ofuncs) {
-                 .ctor = nv4e_i2c_port_ctor,
-                 .dtor = _nouveau_i2c_port_dtor,
-                 .init = _nouveau_i2c_port_init,
-                 .fini = _nouveau_i2c_port_fini,
-         },
-       },
-       {}
-};
-
-struct nouveau_oclass *
-nv4e_i2c_oclass = &(struct nouveau_i2c_impl) {
-       .base.handle = NV_SUBDEV(I2C, 0x4e),
-       .base.ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = _nouveau_i2c_ctor,
-               .dtor = _nouveau_i2c_dtor,
-               .init = _nouveau_i2c_init,
-               .fini = _nouveau_i2c_fini,
-       },
-       .sclass = nv4e_i2c_sclass,
-       .pad_x = &nv04_i2c_pad_oclass,
-}.base;
diff --git a/drivers/gpu/drm/nouveau/core/subdev/i2c/nv50.c b/drivers/gpu/drm/nouveau/core/subdev/i2c/nv50.c
deleted file mode 100644 (file)
index 7b8756d..0000000
+++ /dev/null
@@ -1,135 +0,0 @@
-/*
- * Copyright 2012 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 "nv50.h"
-
-void
-nv50_i2c_drive_scl(struct nouveau_i2c_port *base, int state)
-{
-       struct nv50_i2c_priv *priv = (void *)nv_object(base)->engine;
-       struct nv50_i2c_port *port = (void *)base;
-       if (state) port->state |= 0x01;
-       else       port->state &= 0xfe;
-       nv_wr32(priv, port->addr, port->state);
-}
-
-void
-nv50_i2c_drive_sda(struct nouveau_i2c_port *base, int state)
-{
-       struct nv50_i2c_priv *priv = (void *)nv_object(base)->engine;
-       struct nv50_i2c_port *port = (void *)base;
-       if (state) port->state |= 0x02;
-       else       port->state &= 0xfd;
-       nv_wr32(priv, port->addr, port->state);
-}
-
-int
-nv50_i2c_sense_scl(struct nouveau_i2c_port *base)
-{
-       struct nv50_i2c_priv *priv = (void *)nv_object(base)->engine;
-       struct nv50_i2c_port *port = (void *)base;
-       return !!(nv_rd32(priv, port->addr) & 0x00000001);
-}
-
-int
-nv50_i2c_sense_sda(struct nouveau_i2c_port *base)
-{
-       struct nv50_i2c_priv *priv = (void *)nv_object(base)->engine;
-       struct nv50_i2c_port *port = (void *)base;
-       return !!(nv_rd32(priv, port->addr) & 0x00000002);
-}
-
-static const struct nouveau_i2c_func
-nv50_i2c_func = {
-       .drive_scl = nv50_i2c_drive_scl,
-       .drive_sda = nv50_i2c_drive_sda,
-       .sense_scl = nv50_i2c_sense_scl,
-       .sense_sda = nv50_i2c_sense_sda,
-};
-
-const u32 nv50_i2c_addr[] = {
-       0x00e138, 0x00e150, 0x00e168, 0x00e180,
-       0x00e254, 0x00e274, 0x00e764, 0x00e780,
-       0x00e79c, 0x00e7b8
-};
-const int nv50_i2c_addr_nr = ARRAY_SIZE(nv50_i2c_addr);
-
-static int
-nv50_i2c_port_ctor(struct nouveau_object *parent, struct nouveau_object *engine,
-                  struct nouveau_oclass *oclass, void *data, u32 index,
-                  struct nouveau_object **pobject)
-{
-       struct dcb_i2c_entry *info = data;
-       struct nv50_i2c_port *port;
-       int ret;
-
-       ret = nouveau_i2c_port_create(parent, engine, oclass, index,
-                                     &nouveau_i2c_bit_algo, &nv50_i2c_func,
-                                     &port);
-       *pobject = nv_object(port);
-       if (ret)
-               return ret;
-
-       if (info->drive >= nv50_i2c_addr_nr)
-               return -EINVAL;
-
-       port->state = 0x00000007;
-       port->addr = nv50_i2c_addr[info->drive];
-       return 0;
-}
-
-int
-nv50_i2c_port_init(struct nouveau_object *object)
-{
-       struct nv50_i2c_priv *priv = (void *)object->engine;
-       struct nv50_i2c_port *port = (void *)object;
-       nv_wr32(priv, port->addr, port->state);
-       return nouveau_i2c_port_init(&port->base);
-}
-
-static struct nouveau_oclass
-nv50_i2c_sclass[] = {
-       { .handle = NV_I2C_TYPE_DCBI2C(DCB_I2C_NVIO_BIT),
-         .ofuncs = &(struct nouveau_ofuncs) {
-                 .ctor = nv50_i2c_port_ctor,
-                 .dtor = _nouveau_i2c_port_dtor,
-                 .init = nv50_i2c_port_init,
-                 .fini = _nouveau_i2c_port_fini,
-         },
-       },
-       {}
-};
-
-struct nouveau_oclass *
-nv50_i2c_oclass = &(struct nouveau_i2c_impl) {
-       .base.handle = NV_SUBDEV(I2C, 0x50),
-       .base.ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = _nouveau_i2c_ctor,
-               .dtor = _nouveau_i2c_dtor,
-               .init = _nouveau_i2c_init,
-               .fini = _nouveau_i2c_fini,
-       },
-       .sclass = nv50_i2c_sclass,
-       .pad_x = &nv04_i2c_pad_oclass,
-}.base;
diff --git a/drivers/gpu/drm/nouveau/core/subdev/i2c/nv50.h b/drivers/gpu/drm/nouveau/core/subdev/i2c/nv50.h
deleted file mode 100644 (file)
index 9ef9656..0000000
+++ /dev/null
@@ -1,34 +0,0 @@
-#ifndef __NV50_I2C_H__
-#define __NV50_I2C_H__
-
-#include "priv.h"
-
-struct nv50_i2c_priv {
-       struct nouveau_i2c base;
-};
-
-struct nv50_i2c_port {
-       struct nouveau_i2c_port base;
-       u32 addr;
-       u32 state;
-};
-
-extern const u32 nv50_i2c_addr[];
-extern const int nv50_i2c_addr_nr;
-int  nv50_i2c_port_init(struct nouveau_object *);
-int  nv50_i2c_sense_scl(struct nouveau_i2c_port *);
-int  nv50_i2c_sense_sda(struct nouveau_i2c_port *);
-void nv50_i2c_drive_scl(struct nouveau_i2c_port *, int state);
-void nv50_i2c_drive_sda(struct nouveau_i2c_port *, int state);
-
-int  nv94_aux_port_ctor(struct nouveau_object *, struct nouveau_object *,
-                       struct nouveau_oclass *, void *, u32,
-                       struct nouveau_object **);
-void nv94_i2c_acquire(struct nouveau_i2c_port *);
-void nv94_i2c_release(struct nouveau_i2c_port *);
-
-int  nvd0_i2c_port_ctor(struct nouveau_object *, struct nouveau_object *,
-                       struct nouveau_oclass *, void *, u32,
-                       struct nouveau_object **);
-
-#endif
diff --git a/drivers/gpu/drm/nouveau/core/subdev/i2c/nv94.c b/drivers/gpu/drm/nouveau/core/subdev/i2c/nv94.c
deleted file mode 100644 (file)
index e383ee8..0000000
+++ /dev/null
@@ -1,282 +0,0 @@
-/*
- * Copyright 2012 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 "nv50.h"
-
-void
-nv94_aux_stat(struct nouveau_i2c *i2c, u32 *hi, u32 *lo, u32 *rq, u32 *tx)
-{
-       u32 intr = nv_rd32(i2c, 0x00e06c);
-       u32 stat = nv_rd32(i2c, 0x00e068) & intr, i;
-       for (i = 0, *hi = *lo = *rq = *tx = 0; i < 8; i++) {
-               if ((stat & (1 << (i * 4)))) *hi |= 1 << i;
-               if ((stat & (2 << (i * 4)))) *lo |= 1 << i;
-               if ((stat & (4 << (i * 4)))) *rq |= 1 << i;
-               if ((stat & (8 << (i * 4)))) *tx |= 1 << i;
-       }
-       nv_wr32(i2c, 0x00e06c, intr);
-}
-
-void
-nv94_aux_mask(struct nouveau_i2c *i2c, u32 type, u32 mask, u32 data)
-{
-       u32 temp = nv_rd32(i2c, 0x00e068), i;
-       for (i = 0; i < 8; i++) {
-               if (mask & (1 << i)) {
-                       if (!(data & (1 << i))) {
-                               temp &= ~(type << (i * 4));
-                               continue;
-                       }
-                       temp |= type << (i * 4);
-               }
-       }
-       nv_wr32(i2c, 0x00e068, temp);
-}
-
-#define AUX_DBG(fmt, args...) nv_debug(aux, "AUXCH(%d): " fmt, ch, ##args)
-#define AUX_ERR(fmt, args...) nv_error(aux, "AUXCH(%d): " fmt, ch, ##args)
-
-static void
-auxch_fini(struct nouveau_i2c *aux, int ch)
-{
-       nv_mask(aux, 0x00e4e4 + (ch * 0x50), 0x00310000, 0x00000000);
-}
-
-static int
-auxch_init(struct nouveau_i2c *aux, int ch)
-{
-       const u32 unksel = 1; /* nfi which to use, or if it matters.. */
-       const u32 ureq = unksel ? 0x00100000 : 0x00200000;
-       const u32 urep = unksel ? 0x01000000 : 0x02000000;
-       u32 ctrl, timeout;
-
-       /* wait up to 1ms for any previous transaction to be done... */
-       timeout = 1000;
-       do {
-               ctrl = nv_rd32(aux, 0x00e4e4 + (ch * 0x50));
-               udelay(1);
-               if (!timeout--) {
-                       AUX_ERR("begin idle timeout 0x%08x\n", ctrl);
-                       return -EBUSY;
-               }
-       } while (ctrl & 0x03010000);
-
-       /* set some magic, and wait up to 1ms for it to appear */
-       nv_mask(aux, 0x00e4e4 + (ch * 0x50), 0x00300000, ureq);
-       timeout = 1000;
-       do {
-               ctrl = nv_rd32(aux, 0x00e4e4 + (ch * 0x50));
-               udelay(1);
-               if (!timeout--) {
-                       AUX_ERR("magic wait 0x%08x\n", ctrl);
-                       auxch_fini(aux, ch);
-                       return -EBUSY;
-               }
-       } while ((ctrl & 0x03000000) != urep);
-
-       return 0;
-}
-
-int
-nv94_aux(struct nouveau_i2c_port *base, bool retry,
-        u8 type, u32 addr, u8 *data, u8 size)
-{
-       struct nouveau_i2c *aux = nouveau_i2c(base);
-       struct nv50_i2c_port *port = (void *)base;
-       u32 ctrl, stat, timeout, retries;
-       u32 xbuf[4] = {};
-       int ch = port->addr;
-       int ret, i;
-
-       AUX_DBG("%d: 0x%08x %d\n", type, addr, size);
-
-       ret = auxch_init(aux, ch);
-       if (ret)
-               goto out;
-
-       stat = nv_rd32(aux, 0x00e4e8 + (ch * 0x50));
-       if (!(stat & 0x10000000)) {
-               AUX_DBG("sink not detected\n");
-               ret = -ENXIO;
-               goto out;
-       }
-
-       if (!(type & 1)) {
-               memcpy(xbuf, data, size);
-               for (i = 0; i < 16; i += 4) {
-                       AUX_DBG("wr 0x%08x\n", xbuf[i / 4]);
-                       nv_wr32(aux, 0x00e4c0 + (ch * 0x50) + i, xbuf[i / 4]);
-               }
-       }
-
-       ctrl  = nv_rd32(aux, 0x00e4e4 + (ch * 0x50));
-       ctrl &= ~0x0001f0ff;
-       ctrl |= type << 12;
-       ctrl |= size - 1;
-       nv_wr32(aux, 0x00e4e0 + (ch * 0x50), addr);
-
-       /* (maybe) retry transaction a number of times on failure... */
-       for (retries = 0; !ret && retries < 32; retries++) {
-               /* reset, and delay a while if this is a retry */
-               nv_wr32(aux, 0x00e4e4 + (ch * 0x50), 0x80000000 | ctrl);
-               nv_wr32(aux, 0x00e4e4 + (ch * 0x50), 0x00000000 | ctrl);
-               if (retries)
-                       udelay(400);
-
-               /* transaction request, wait up to 1ms for it to complete */
-               nv_wr32(aux, 0x00e4e4 + (ch * 0x50), 0x00010000 | ctrl);
-
-               timeout = 1000;
-               do {
-                       ctrl = nv_rd32(aux, 0x00e4e4 + (ch * 0x50));
-                       udelay(1);
-                       if (!timeout--) {
-                               AUX_ERR("tx req timeout 0x%08x\n", ctrl);
-                               ret = -EIO;
-                               goto out;
-                       }
-               } while (ctrl & 0x00010000);
-               ret = 1;
-
-               /* read status, and check if transaction completed ok */
-               stat = nv_mask(aux, 0x00e4e8 + (ch * 0x50), 0, 0);
-               if ((stat & 0x000f0000) == 0x00080000 ||
-                   (stat & 0x000f0000) == 0x00020000)
-                       ret = retry ? 0 : 1;
-               if ((stat & 0x00000100))
-                       ret = -ETIMEDOUT;
-               if ((stat & 0x00000e00))
-                       ret = -EIO;
-
-               AUX_DBG("%02d 0x%08x 0x%08x\n", retries, ctrl, stat);
-       }
-
-       if (type & 1) {
-               for (i = 0; i < 16; i += 4) {
-                       xbuf[i / 4] = nv_rd32(aux, 0x00e4d0 + (ch * 0x50) + i);
-                       AUX_DBG("rd 0x%08x\n", xbuf[i / 4]);
-               }
-               memcpy(data, xbuf, size);
-       }
-
-out:
-       auxch_fini(aux, ch);
-       return ret < 0 ? ret : (stat & 0x000f0000) >> 16;
-}
-
-static const struct nouveau_i2c_func
-nv94_i2c_func = {
-       .drive_scl = nv50_i2c_drive_scl,
-       .drive_sda = nv50_i2c_drive_sda,
-       .sense_scl = nv50_i2c_sense_scl,
-       .sense_sda = nv50_i2c_sense_sda,
-};
-
-static int
-nv94_i2c_port_ctor(struct nouveau_object *parent, struct nouveau_object *engine,
-                  struct nouveau_oclass *oclass, void *data, u32 index,
-                  struct nouveau_object **pobject)
-{
-       struct dcb_i2c_entry *info = data;
-       struct nv50_i2c_port *port;
-       int ret;
-
-       ret = nouveau_i2c_port_create(parent, engine, oclass, index,
-                                     &nouveau_i2c_bit_algo, &nv94_i2c_func,
-                                     &port);
-       *pobject = nv_object(port);
-       if (ret)
-               return ret;
-
-       if (info->drive >= nv50_i2c_addr_nr)
-               return -EINVAL;
-
-       port->state = 7;
-       port->addr = nv50_i2c_addr[info->drive];
-       return 0;
-}
-
-static const struct nouveau_i2c_func
-nv94_aux_func = {
-       .aux       = nv94_aux,
-};
-
-int
-nv94_aux_port_ctor(struct nouveau_object *parent, struct nouveau_object *engine,
-                  struct nouveau_oclass *oclass, void *data, u32 index,
-                  struct nouveau_object **pobject)
-{
-       struct dcb_i2c_entry *info = data;
-       struct nv50_i2c_port *port;
-       int ret;
-
-       ret = nouveau_i2c_port_create(parent, engine, oclass, index,
-                                     &nouveau_i2c_aux_algo, &nv94_aux_func,
-                                     &port);
-       *pobject = nv_object(port);
-       if (ret)
-               return ret;
-
-       port->base.aux = info->auxch;
-       port->addr = info->auxch;
-       return 0;
-}
-
-static struct nouveau_oclass
-nv94_i2c_sclass[] = {
-       { .handle = NV_I2C_TYPE_DCBI2C(DCB_I2C_NVIO_BIT),
-         .ofuncs = &(struct nouveau_ofuncs) {
-                 .ctor = nv94_i2c_port_ctor,
-                 .dtor = _nouveau_i2c_port_dtor,
-                 .init = nv50_i2c_port_init,
-                 .fini = _nouveau_i2c_port_fini,
-         },
-       },
-       { .handle = NV_I2C_TYPE_DCBI2C(DCB_I2C_NVIO_AUX),
-         .ofuncs = &(struct nouveau_ofuncs) {
-                 .ctor = nv94_aux_port_ctor,
-                 .dtor = _nouveau_i2c_port_dtor,
-                 .init = _nouveau_i2c_port_init,
-                 .fini = _nouveau_i2c_port_fini,
-         },
-       },
-       {}
-};
-
-struct nouveau_oclass *
-nv94_i2c_oclass = &(struct nouveau_i2c_impl) {
-       .base.handle = NV_SUBDEV(I2C, 0x94),
-       .base.ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = _nouveau_i2c_ctor,
-               .dtor = _nouveau_i2c_dtor,
-               .init = _nouveau_i2c_init,
-               .fini = _nouveau_i2c_fini,
-       },
-       .sclass = nv94_i2c_sclass,
-       .pad_x = &nv04_i2c_pad_oclass,
-       .pad_s = &nv94_i2c_pad_oclass,
-       .aux = 4,
-       .aux_stat = nv94_aux_stat,
-       .aux_mask = nv94_aux_mask,
-}.base;
diff --git a/drivers/gpu/drm/nouveau/core/subdev/i2c/nvd0.c b/drivers/gpu/drm/nouveau/core/subdev/i2c/nvd0.c
deleted file mode 100644 (file)
index fd99380..0000000
+++ /dev/null
@@ -1,108 +0,0 @@
-/*
- * Copyright 2012 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 "nv50.h"
-
-static int
-nvd0_i2c_sense_scl(struct nouveau_i2c_port *base)
-{
-       struct nv50_i2c_priv *priv = (void *)nv_object(base)->engine;
-       struct nv50_i2c_port *port = (void *)base;
-       return !!(nv_rd32(priv, port->addr) & 0x00000010);
-}
-
-static int
-nvd0_i2c_sense_sda(struct nouveau_i2c_port *base)
-{
-       struct nv50_i2c_priv *priv = (void *)nv_object(base)->engine;
-       struct nv50_i2c_port *port = (void *)base;
-       return !!(nv_rd32(priv, port->addr) & 0x00000020);
-}
-
-static const struct nouveau_i2c_func
-nvd0_i2c_func = {
-       .drive_scl = nv50_i2c_drive_scl,
-       .drive_sda = nv50_i2c_drive_sda,
-       .sense_scl = nvd0_i2c_sense_scl,
-       .sense_sda = nvd0_i2c_sense_sda,
-};
-
-int
-nvd0_i2c_port_ctor(struct nouveau_object *parent, struct nouveau_object *engine,
-                  struct nouveau_oclass *oclass, void *data, u32 index,
-                  struct nouveau_object **pobject)
-{
-       struct dcb_i2c_entry *info = data;
-       struct nv50_i2c_port *port;
-       int ret;
-
-       ret = nouveau_i2c_port_create(parent, engine, oclass, index,
-                                     &nouveau_i2c_bit_algo, &nvd0_i2c_func,
-                                     &port);
-       *pobject = nv_object(port);
-       if (ret)
-               return ret;
-
-       port->state = 0x00000007;
-       port->addr = 0x00d014 + (info->drive * 0x20);
-       return 0;
-}
-
-struct nouveau_oclass
-nvd0_i2c_sclass[] = {
-       { .handle = NV_I2C_TYPE_DCBI2C(DCB_I2C_NVIO_BIT),
-         .ofuncs = &(struct nouveau_ofuncs) {
-                 .ctor = nvd0_i2c_port_ctor,
-                 .dtor = _nouveau_i2c_port_dtor,
-                 .init = nv50_i2c_port_init,
-                 .fini = _nouveau_i2c_port_fini,
-         },
-       },
-       { .handle = NV_I2C_TYPE_DCBI2C(DCB_I2C_NVIO_AUX),
-         .ofuncs = &(struct nouveau_ofuncs) {
-                 .ctor = nv94_aux_port_ctor,
-                 .dtor = _nouveau_i2c_port_dtor,
-                 .init = _nouveau_i2c_port_init,
-                 .fini = _nouveau_i2c_port_fini,
-         },
-       },
-       {}
-};
-
-struct nouveau_oclass *
-nvd0_i2c_oclass = &(struct nouveau_i2c_impl) {
-       .base.handle = NV_SUBDEV(I2C, 0xd0),
-       .base.ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = _nouveau_i2c_ctor,
-               .dtor = _nouveau_i2c_dtor,
-               .init = _nouveau_i2c_init,
-               .fini = _nouveau_i2c_fini,
-       },
-       .sclass = nvd0_i2c_sclass,
-       .pad_x = &nv04_i2c_pad_oclass,
-       .pad_s = &nv94_i2c_pad_oclass,
-       .aux = 4,
-       .aux_stat = nv94_aux_stat,
-       .aux_mask = nv94_aux_mask,
-}.base;
diff --git a/drivers/gpu/drm/nouveau/core/subdev/i2c/nve0.c b/drivers/gpu/drm/nouveau/core/subdev/i2c/nve0.c
deleted file mode 100644 (file)
index 25fe5c2..0000000
+++ /dev/null
@@ -1,72 +0,0 @@
-/*
- * Copyright 2012 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 "nv50.h"
-
-void
-nve0_aux_stat(struct nouveau_i2c *i2c, u32 *hi, u32 *lo, u32 *rq, u32 *tx)
-{
-       u32 intr = nv_rd32(i2c, 0x00dc60);
-       u32 stat = nv_rd32(i2c, 0x00dc68) & intr, i;
-       for (i = 0, *hi = *lo = *rq = *tx = 0; i < 8; i++) {
-               if ((stat & (1 << (i * 4)))) *hi |= 1 << i;
-               if ((stat & (2 << (i * 4)))) *lo |= 1 << i;
-               if ((stat & (4 << (i * 4)))) *rq |= 1 << i;
-               if ((stat & (8 << (i * 4)))) *tx |= 1 << i;
-       }
-       nv_wr32(i2c, 0x00dc60, intr);
-}
-
-void
-nve0_aux_mask(struct nouveau_i2c *i2c, u32 type, u32 mask, u32 data)
-{
-       u32 temp = nv_rd32(i2c, 0x00dc68), i;
-       for (i = 0; i < 8; i++) {
-               if (mask & (1 << i)) {
-                       if (!(data & (1 << i))) {
-                               temp &= ~(type << (i * 4));
-                               continue;
-                       }
-                       temp |= type << (i * 4);
-               }
-       }
-       nv_wr32(i2c, 0x00dc68, temp);
-}
-
-struct nouveau_oclass *
-nve0_i2c_oclass = &(struct nouveau_i2c_impl) {
-       .base.handle = NV_SUBDEV(I2C, 0xe0),
-       .base.ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = _nouveau_i2c_ctor,
-               .dtor = _nouveau_i2c_dtor,
-               .init = _nouveau_i2c_init,
-               .fini = _nouveau_i2c_fini,
-       },
-       .sclass = nvd0_i2c_sclass,
-       .pad_x = &nv04_i2c_pad_oclass,
-       .pad_s = &nv94_i2c_pad_oclass,
-       .aux = 4,
-       .aux_stat = nve0_aux_stat,
-       .aux_mask = nve0_aux_mask,
-}.base;
diff --git a/drivers/gpu/drm/nouveau/core/subdev/i2c/pad.c b/drivers/gpu/drm/nouveau/core/subdev/i2c/pad.c
deleted file mode 100644 (file)
index e9e4124..0000000
+++ /dev/null
@@ -1,84 +0,0 @@
-/*
- * Copyright 2014 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 "pad.h"
-
-int
-_nvkm_i2c_pad_fini(struct nouveau_object *object, bool suspend)
-{
-       struct nvkm_i2c_pad *pad = (void *)object;
-       DBG("-> NULL\n");
-       pad->port = NULL;
-       return nouveau_object_fini(&pad->base, suspend);
-}
-
-int
-_nvkm_i2c_pad_init(struct nouveau_object *object)
-{
-       struct nvkm_i2c_pad *pad = (void *)object;
-       DBG("-> PORT:%02x\n", pad->next->index);
-       pad->port = pad->next;
-       return nouveau_object_init(&pad->base);
-}
-
-int
-nvkm_i2c_pad_create_(struct nouveau_object *parent,
-                    struct nouveau_object *engine,
-                    struct nouveau_oclass *oclass, int index,
-                    int size, void **pobject)
-{
-       struct nouveau_i2c *i2c = (void *)engine;
-       struct nouveau_i2c_port *port;
-       struct nvkm_i2c_pad *pad;
-       int ret;
-
-       list_for_each_entry(port, &i2c->ports, head) {
-               pad = nvkm_i2c_pad(port);
-               if (pad->index == index) {
-                       atomic_inc(&nv_object(pad)->refcount);
-                       *pobject = pad;
-                       return 1;
-               }
-       }
-
-       ret = nouveau_object_create_(parent, engine, oclass, 0, size, pobject);
-       pad = *pobject;
-       if (ret)
-               return ret;
-
-       pad->index = index;
-       return 0;
-}
-
-int
-_nvkm_i2c_pad_ctor(struct nouveau_object *parent, struct nouveau_object *engine,
-                  struct nouveau_oclass *oclass, void *data, u32 index,
-                  struct nouveau_object **pobject)
-{
-       struct nvkm_i2c_pad *pad;
-       int ret;
-       ret = nvkm_i2c_pad_create(parent, engine, oclass, index, &pad);
-       *pobject = nv_object(pad);
-       return ret;
-}
diff --git a/drivers/gpu/drm/nouveau/core/subdev/i2c/pad.h b/drivers/gpu/drm/nouveau/core/subdev/i2c/pad.h
deleted file mode 100644 (file)
index 452ac10..0000000
+++ /dev/null
@@ -1,58 +0,0 @@
-#ifndef __NVKM_I2C_PAD_H__
-#define __NVKM_I2C_PAD_H__
-
-#include "priv.h"
-
-struct nvkm_i2c_pad {
-       struct nouveau_object base;
-       int index;
-       struct nouveau_i2c_port *port;
-       struct nouveau_i2c_port *next;
-};
-
-static inline struct nvkm_i2c_pad *
-nvkm_i2c_pad(struct nouveau_i2c_port *port)
-{
-       struct nouveau_object *pad = nv_object(port);
-       while (pad->parent)
-               pad = pad->parent;
-       return (void *)pad;
-}
-
-#define nvkm_i2c_pad_create(p,e,o,i,d)                                         \
-       nvkm_i2c_pad_create_((p), (e), (o), (i), sizeof(**d), (void **)d)
-#define nvkm_i2c_pad_destroy(p) ({                                             \
-       struct nvkm_i2c_pad *_p = (p);                                         \
-       _nvkm_i2c_pad_dtor(nv_object(_p));                                     \
-})
-#define nvkm_i2c_pad_init(p) ({                                                \
-       struct nvkm_i2c_pad *_p = (p);                                         \
-       _nvkm_i2c_pad_init(nv_object(_p));                                     \
-})
-#define nvkm_i2c_pad_fini(p,s) ({                                              \
-       struct nvkm_i2c_pad *_p = (p);                                         \
-       _nvkm_i2c_pad_fini(nv_object(_p), (s));                                \
-})
-
-int nvkm_i2c_pad_create_(struct nouveau_object *, struct nouveau_object *,
-                        struct nouveau_oclass *, int index, int, void **);
-
-int _nvkm_i2c_pad_ctor(struct nouveau_object *, struct nouveau_object *,
-                      struct nouveau_oclass *, void *, u32,
-                      struct nouveau_object **);
-#define _nvkm_i2c_pad_dtor nouveau_object_destroy
-int _nvkm_i2c_pad_init(struct nouveau_object *);
-int _nvkm_i2c_pad_fini(struct nouveau_object *, bool);
-
-#ifndef MSG
-#define MSG(l,f,a...) do {                                                     \
-       struct nvkm_i2c_pad *_pad = (void *)pad;                               \
-       nv_##l(nv_object(_pad)->engine, "PAD:%c:%02x: "f,                      \
-              _pad->index >= 0x100 ? 'X' : 'S',                               \
-              _pad->index >= 0x100 ? _pad->index - 0x100 : _pad->index, ##a); \
-} while(0)
-#define DBG(f,a...) MSG(debug, f, ##a)
-#define ERR(f,a...) MSG(error, f, ##a)
-#endif
-
-#endif
diff --git a/drivers/gpu/drm/nouveau/core/subdev/i2c/padgm204.c b/drivers/gpu/drm/nouveau/core/subdev/i2c/padgm204.c
deleted file mode 100644 (file)
index f0e6fbb..0000000
+++ /dev/null
@@ -1,86 +0,0 @@
-/*
- * Copyright 2014 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 "pad.h"
-
-struct gm204_i2c_pad {
-       struct nvkm_i2c_pad base;
-       int addr;
-};
-
-static int
-gm204_i2c_pad_fini(struct nouveau_object *object, bool suspend)
-{
-       struct nouveau_i2c *i2c = (void *)object->engine;
-       struct gm204_i2c_pad *pad = (void *)object;
-       nv_mask(i2c, 0x00d97c + pad->addr, 0x00000001, 0x00000001);
-       return nvkm_i2c_pad_fini(&pad->base, suspend);
-}
-
-static int
-gm204_i2c_pad_init(struct nouveau_object *object)
-{
-       struct nouveau_i2c *i2c = (void *)object->engine;
-       struct gm204_i2c_pad *pad = (void *)object;
-
-       switch (nv_oclass(pad->base.next)->handle) {
-       case NV_I2C_TYPE_DCBI2C(DCB_I2C_NVIO_AUX):
-               nv_mask(i2c, 0x00d970 + pad->addr, 0x0000c003, 0x00000002);
-               break;
-       case NV_I2C_TYPE_DCBI2C(DCB_I2C_NVIO_BIT):
-       default:
-               nv_mask(i2c, 0x00d970 + pad->addr, 0x0000c003, 0x0000c001);
-               break;
-       }
-
-       nv_mask(i2c, 0x00d97c + pad->addr, 0x00000001, 0x00000000);
-       return nvkm_i2c_pad_init(&pad->base);
-}
-
-static int
-gm204_i2c_pad_ctor(struct nouveau_object *parent, struct nouveau_object *engine,
-                 struct nouveau_oclass *oclass, void *data, u32 index,
-                 struct nouveau_object **pobject)
-{
-       struct gm204_i2c_pad *pad;
-       int ret;
-
-       ret = nvkm_i2c_pad_create(parent, engine, oclass, index, &pad);
-       *pobject = nv_object(pad);
-       if (ret)
-               return ret;
-
-       pad->addr = index * 0x50;;
-       return 0;
-}
-
-struct nouveau_oclass
-gm204_i2c_pad_oclass = {
-       .ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = gm204_i2c_pad_ctor,
-               .dtor = _nvkm_i2c_pad_dtor,
-               .init = gm204_i2c_pad_init,
-               .fini = gm204_i2c_pad_fini,
-       },
-};
diff --git a/drivers/gpu/drm/nouveau/core/subdev/i2c/padnv04.c b/drivers/gpu/drm/nouveau/core/subdev/i2c/padnv04.c
deleted file mode 100644 (file)
index 2c4b612..0000000
+++ /dev/null
@@ -1,35 +0,0 @@
-/*
- * Copyright 2014 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 "pad.h"
-
-struct nouveau_oclass
-nv04_i2c_pad_oclass = {
-       .ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = _nvkm_i2c_pad_ctor,
-               .dtor = _nvkm_i2c_pad_dtor,
-               .init = _nvkm_i2c_pad_init,
-               .fini = _nvkm_i2c_pad_fini,
-       },
-};
diff --git a/drivers/gpu/drm/nouveau/core/subdev/i2c/padnv94.c b/drivers/gpu/drm/nouveau/core/subdev/i2c/padnv94.c
deleted file mode 100644 (file)
index 0dc6753..0000000
+++ /dev/null
@@ -1,86 +0,0 @@
-/*
- * Copyright 2014 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 "pad.h"
-
-struct nv94_i2c_pad {
-       struct nvkm_i2c_pad base;
-       int addr;
-};
-
-static int
-nv94_i2c_pad_fini(struct nouveau_object *object, bool suspend)
-{
-       struct nouveau_i2c *i2c = (void *)object->engine;
-       struct nv94_i2c_pad *pad = (void *)object;
-       nv_mask(i2c, 0x00e50c + pad->addr, 0x00000001, 0x00000001);
-       return nvkm_i2c_pad_fini(&pad->base, suspend);
-}
-
-static int
-nv94_i2c_pad_init(struct nouveau_object *object)
-{
-       struct nouveau_i2c *i2c = (void *)object->engine;
-       struct nv94_i2c_pad *pad = (void *)object;
-
-       switch (nv_oclass(pad->base.next)->handle) {
-       case NV_I2C_TYPE_DCBI2C(DCB_I2C_NVIO_AUX):
-               nv_mask(i2c, 0x00e500 + pad->addr, 0x0000c003, 0x00000002);
-               break;
-       case NV_I2C_TYPE_DCBI2C(DCB_I2C_NVIO_BIT):
-       default:
-               nv_mask(i2c, 0x00e500 + pad->addr, 0x0000c003, 0x0000c001);
-               break;
-       }
-
-       nv_mask(i2c, 0x00e50c + pad->addr, 0x00000001, 0x00000000);
-       return nvkm_i2c_pad_init(&pad->base);
-}
-
-static int
-nv94_i2c_pad_ctor(struct nouveau_object *parent, struct nouveau_object *engine,
-                 struct nouveau_oclass *oclass, void *data, u32 index,
-                 struct nouveau_object **pobject)
-{
-       struct nv94_i2c_pad *pad;
-       int ret;
-
-       ret = nvkm_i2c_pad_create(parent, engine, oclass, index, &pad);
-       *pobject = nv_object(pad);
-       if (ret)
-               return ret;
-
-       pad->addr = index * 0x50;;
-       return 0;
-}
-
-struct nouveau_oclass
-nv94_i2c_pad_oclass = {
-       .ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nv94_i2c_pad_ctor,
-               .dtor = _nvkm_i2c_pad_dtor,
-               .init = nv94_i2c_pad_init,
-               .fini = nv94_i2c_pad_fini,
-       },
-};
diff --git a/drivers/gpu/drm/nouveau/core/subdev/i2c/port.h b/drivers/gpu/drm/nouveau/core/subdev/i2c/port.h
deleted file mode 100644 (file)
index a8ff6e0..0000000
+++ /dev/null
@@ -1,15 +0,0 @@
-#ifndef __NVKM_I2C_PORT_H__
-#define __NVKM_I2C_PORT_H__
-
-#include "priv.h"
-
-#ifndef MSG
-#define MSG(l,f,a...) do {                                                     \
-       struct nouveau_i2c_port *_port = (void *)port;                         \
-       nv_##l(nv_object(_port)->engine, "PORT:%02x: "f, _port->index, ##a);   \
-} while(0)
-#define DBG(f,a...) MSG(debug, f, ##a)
-#define ERR(f,a...) MSG(error, f, ##a)
-#endif
-
-#endif
diff --git a/drivers/gpu/drm/nouveau/core/subdev/i2c/priv.h b/drivers/gpu/drm/nouveau/core/subdev/i2c/priv.h
deleted file mode 100644 (file)
index 4fe7ae3..0000000
+++ /dev/null
@@ -1,89 +0,0 @@
-#ifndef __NVKM_I2C_H__
-#define __NVKM_I2C_H__
-
-#include <subdev/i2c.h>
-
-extern struct nouveau_oclass nv04_i2c_pad_oclass;
-extern struct nouveau_oclass nv94_i2c_pad_oclass;
-extern struct nouveau_oclass gm204_i2c_pad_oclass;
-
-#define nouveau_i2c_port_create(p,e,o,i,a,f,d)                                 \
-       nouveau_i2c_port_create_((p), (e), (o), (i), (a), (f),                 \
-                                sizeof(**d), (void **)d)
-#define nouveau_i2c_port_destroy(p) ({                                         \
-       struct nouveau_i2c_port *port = (p);                                   \
-       _nouveau_i2c_port_dtor(nv_object(i2c));                                \
-})
-#define nouveau_i2c_port_init(p)                                               \
-       nouveau_object_init(&(p)->base)
-#define nouveau_i2c_port_fini(p,s)                                             \
-       nouveau_object_fini(&(p)->base, (s))
-
-int nouveau_i2c_port_create_(struct nouveau_object *, struct nouveau_object *,
-                            struct nouveau_oclass *, u8,
-                            const struct i2c_algorithm *,
-                            const struct nouveau_i2c_func *,
-                            int, void **);
-void _nouveau_i2c_port_dtor(struct nouveau_object *);
-#define _nouveau_i2c_port_init nouveau_object_init
-int  _nouveau_i2c_port_fini(struct nouveau_object *, bool);
-
-#define nouveau_i2c_create(p,e,o,d)                                            \
-       nouveau_i2c_create_((p), (e), (o), sizeof(**d), (void **)d)
-#define nouveau_i2c_destroy(p) ({                                              \
-       struct nouveau_i2c *i2c = (p);                                         \
-       _nouveau_i2c_dtor(nv_object(i2c));                                     \
-})
-#define nouveau_i2c_init(p) ({                                                 \
-       struct nouveau_i2c *i2c = (p);                                         \
-       _nouveau_i2c_init(nv_object(i2c));                                     \
-})
-#define nouveau_i2c_fini(p,s) ({                                               \
-       struct nouveau_i2c *i2c = (p);                                         \
-       _nouveau_i2c_fini(nv_object(i2c), (s));                                \
-})
-
-int nouveau_i2c_create_(struct nouveau_object *, struct nouveau_object *,
-                       struct nouveau_oclass *, int, void **);
-int  _nouveau_i2c_ctor(struct nouveau_object *, struct nouveau_object *,
-                      struct nouveau_oclass *, void *, u32,
-                      struct nouveau_object **);
-void _nouveau_i2c_dtor(struct nouveau_object *);
-int  _nouveau_i2c_init(struct nouveau_object *);
-int  _nouveau_i2c_fini(struct nouveau_object *, bool);
-
-extern struct nouveau_oclass nouveau_anx9805_sclass[];
-extern struct nouveau_oclass nvd0_i2c_sclass[];
-
-extern const struct i2c_algorithm nouveau_i2c_bit_algo;
-extern const struct i2c_algorithm nouveau_i2c_aux_algo;
-
-struct nouveau_i2c_impl {
-       struct nouveau_oclass base;
-
-       /* supported i2c port classes */
-       struct nouveau_oclass *sclass;
-       struct nouveau_oclass *pad_x;
-       struct nouveau_oclass *pad_s;
-
-       /* number of native dp aux channels present */
-       int aux;
-
-       /* read and ack pending interrupts, returning only data
-        * for ports that have not been masked off, while still
-        * performing the ack for anything that was pending.
-        */
-       void (*aux_stat)(struct nouveau_i2c *, u32 *, u32 *, u32 *, u32 *);
-
-       /* mask on/off interrupt types for a given set of auxch
-        */
-       void (*aux_mask)(struct nouveau_i2c *, u32, u32, u32);
-};
-
-void nv94_aux_stat(struct nouveau_i2c *, u32 *, u32 *, u32 *, u32 *);
-void nv94_aux_mask(struct nouveau_i2c *, u32, u32, u32);
-
-void nve0_aux_stat(struct nouveau_i2c *, u32 *, u32 *, u32 *, u32 *);
-void nve0_aux_mask(struct nouveau_i2c *, u32, u32, u32);
-
-#endif
diff --git a/drivers/gpu/drm/nouveau/core/subdev/ibus/gk20a.c b/drivers/gpu/drm/nouveau/core/subdev/ibus/gk20a.c
deleted file mode 100644 (file)
index 245f0eb..0000000
+++ /dev/null
@@ -1,103 +0,0 @@
-/*
- * Copyright (c) 2014, NVIDIA CORPORATION. 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 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 <subdev/ibus.h>
-#include <subdev/timer.h>
-
-struct gk20a_ibus_priv {
-       struct nouveau_ibus base;
-};
-
-static void
-gk20a_ibus_init_priv_ring(struct gk20a_ibus_priv *priv)
-{
-       nv_mask(priv, 0x137250, 0x3f, 0);
-
-       nv_mask(priv, 0x000200, 0x20, 0);
-       usleep_range(20, 30);
-       nv_mask(priv, 0x000200, 0x20, 0x20);
-
-       nv_wr32(priv, 0x12004c, 0x4);
-       nv_wr32(priv, 0x122204, 0x2);
-       nv_rd32(priv, 0x122204);
-}
-
-static void
-gk20a_ibus_intr(struct nouveau_subdev *subdev)
-{
-       struct gk20a_ibus_priv *priv = (void *)subdev;
-       u32 status0 = nv_rd32(priv, 0x120058);
-
-       if (status0 & 0x7) {
-               nv_debug(priv, "resetting priv ring\n");
-               gk20a_ibus_init_priv_ring(priv);
-       }
-
-       /* Acknowledge interrupt */
-       nv_mask(priv, 0x12004c, 0x2, 0x2);
-
-       if (!nv_wait(subdev, 0x12004c, 0x3f, 0x00))
-               nv_warn(priv, "timeout waiting for ringmaster ack\n");
-}
-
-static int
-gk20a_ibus_init(struct nouveau_object *object)
-{
-       struct gk20a_ibus_priv *priv = (void *)object;
-       int ret;
-
-       ret = _nouveau_ibus_init(object);
-       if (ret)
-               return ret;
-
-       gk20a_ibus_init_priv_ring(priv);
-
-       return 0;
-}
-
-static int
-gk20a_ibus_ctor(struct nouveau_object *parent, struct nouveau_object *engine,
-              struct nouveau_oclass *oclass, void *data, u32 size,
-              struct nouveau_object **pobject)
-{
-       struct gk20a_ibus_priv *priv;
-       int ret;
-
-       ret = nouveau_ibus_create(parent, engine, oclass, &priv);
-       *pobject = nv_object(priv);
-       if (ret)
-               return ret;
-
-       nv_subdev(priv)->intr = gk20a_ibus_intr;
-       return 0;
-}
-
-struct nouveau_oclass
-gk20a_ibus_oclass = {
-       .handle = NV_SUBDEV(IBUS, 0xea),
-       .ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = gk20a_ibus_ctor,
-               .dtor = _nouveau_ibus_dtor,
-               .init = gk20a_ibus_init,
-               .fini = _nouveau_ibus_fini,
-       },
-};
diff --git a/drivers/gpu/drm/nouveau/core/subdev/ibus/nvc0.c b/drivers/gpu/drm/nouveau/core/subdev/ibus/nvc0.c
deleted file mode 100644 (file)
index 4e977ff..0000000
+++ /dev/null
@@ -1,123 +0,0 @@
-/*
- * Copyright 2012 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 <subdev/ibus.h>
-
-struct nvc0_ibus_priv {
-       struct nouveau_ibus base;
-};
-
-static void
-nvc0_ibus_intr_hub(struct nvc0_ibus_priv *priv, int i)
-{
-       u32 addr = nv_rd32(priv, 0x122120 + (i * 0x0400));
-       u32 data = nv_rd32(priv, 0x122124 + (i * 0x0400));
-       u32 stat = nv_rd32(priv, 0x122128 + (i * 0x0400));
-       nv_error(priv, "HUB%d: 0x%06x 0x%08x (0x%08x)\n", i, addr, data, stat);
-       nv_mask(priv, 0x122128 + (i * 0x0400), 0x00000200, 0x00000000);
-}
-
-static void
-nvc0_ibus_intr_rop(struct nvc0_ibus_priv *priv, int i)
-{
-       u32 addr = nv_rd32(priv, 0x124120 + (i * 0x0400));
-       u32 data = nv_rd32(priv, 0x124124 + (i * 0x0400));
-       u32 stat = nv_rd32(priv, 0x124128 + (i * 0x0400));
-       nv_error(priv, "ROP%d: 0x%06x 0x%08x (0x%08x)\n", i, addr, data, stat);
-       nv_mask(priv, 0x124128 + (i * 0x0400), 0x00000200, 0x00000000);
-}
-
-static void
-nvc0_ibus_intr_gpc(struct nvc0_ibus_priv *priv, int i)
-{
-       u32 addr = nv_rd32(priv, 0x128120 + (i * 0x0400));
-       u32 data = nv_rd32(priv, 0x128124 + (i * 0x0400));
-       u32 stat = nv_rd32(priv, 0x128128 + (i * 0x0400));
-       nv_error(priv, "GPC%d: 0x%06x 0x%08x (0x%08x)\n", i, addr, data, stat);
-       nv_mask(priv, 0x128128 + (i * 0x0400), 0x00000200, 0x00000000);
-}
-
-static void
-nvc0_ibus_intr(struct nouveau_subdev *subdev)
-{
-       struct nvc0_ibus_priv *priv = (void *)subdev;
-       u32 intr0 = nv_rd32(priv, 0x121c58);
-       u32 intr1 = nv_rd32(priv, 0x121c5c);
-       u32 hubnr = nv_rd32(priv, 0x121c70);
-       u32 ropnr = nv_rd32(priv, 0x121c74);
-       u32 gpcnr = nv_rd32(priv, 0x121c78);
-       u32 i;
-
-       for (i = 0; (intr0 & 0x0000ff00) && i < hubnr; i++) {
-               u32 stat = 0x00000100 << i;
-               if (intr0 & stat) {
-                       nvc0_ibus_intr_hub(priv, i);
-                       intr0 &= ~stat;
-               }
-       }
-
-       for (i = 0; (intr0 & 0xffff0000) && i < ropnr; i++) {
-               u32 stat = 0x00010000 << i;
-               if (intr0 & stat) {
-                       nvc0_ibus_intr_rop(priv, i);
-                       intr0 &= ~stat;
-               }
-       }
-
-       for (i = 0; intr1 && i < gpcnr; i++) {
-               u32 stat = 0x00000001 << i;
-               if (intr1 & stat) {
-                       nvc0_ibus_intr_gpc(priv, i);
-                       intr1 &= ~stat;
-               }
-       }
-}
-
-static int
-nvc0_ibus_ctor(struct nouveau_object *parent, struct nouveau_object *engine,
-              struct nouveau_oclass *oclass, void *data, u32 size,
-              struct nouveau_object **pobject)
-{
-       struct nvc0_ibus_priv *priv;
-       int ret;
-
-       ret = nouveau_ibus_create(parent, engine, oclass, &priv);
-       *pobject = nv_object(priv);
-       if (ret)
-               return ret;
-
-       nv_subdev(priv)->intr = nvc0_ibus_intr;
-       return 0;
-}
-
-struct nouveau_oclass
-nvc0_ibus_oclass = {
-       .handle = NV_SUBDEV(IBUS, 0xc0),
-       .ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nvc0_ibus_ctor,
-               .dtor = _nouveau_ibus_dtor,
-               .init = _nouveau_ibus_init,
-               .fini = _nouveau_ibus_fini,
-       },
-};
diff --git a/drivers/gpu/drm/nouveau/core/subdev/ibus/nve0.c b/drivers/gpu/drm/nouveau/core/subdev/ibus/nve0.c
deleted file mode 100644 (file)
index ebef970..0000000
+++ /dev/null
@@ -1,140 +0,0 @@
-/*
- * Copyright 2012 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 <subdev/ibus.h>
-
-struct nve0_ibus_priv {
-       struct nouveau_ibus base;
-};
-
-static void
-nve0_ibus_intr_hub(struct nve0_ibus_priv *priv, int i)
-{
-       u32 addr = nv_rd32(priv, 0x122120 + (i * 0x0800));
-       u32 data = nv_rd32(priv, 0x122124 + (i * 0x0800));
-       u32 stat = nv_rd32(priv, 0x122128 + (i * 0x0800));
-       nv_error(priv, "HUB%d: 0x%06x 0x%08x (0x%08x)\n", i, addr, data, stat);
-       nv_mask(priv, 0x122128 + (i * 0x0800), 0x00000200, 0x00000000);
-}
-
-static void
-nve0_ibus_intr_rop(struct nve0_ibus_priv *priv, int i)
-{
-       u32 addr = nv_rd32(priv, 0x124120 + (i * 0x0800));
-       u32 data = nv_rd32(priv, 0x124124 + (i * 0x0800));
-       u32 stat = nv_rd32(priv, 0x124128 + (i * 0x0800));
-       nv_error(priv, "ROP%d: 0x%06x 0x%08x (0x%08x)\n", i, addr, data, stat);
-       nv_mask(priv, 0x124128 + (i * 0x0800), 0x00000200, 0x00000000);
-}
-
-static void
-nve0_ibus_intr_gpc(struct nve0_ibus_priv *priv, int i)
-{
-       u32 addr = nv_rd32(priv, 0x128120 + (i * 0x0800));
-       u32 data = nv_rd32(priv, 0x128124 + (i * 0x0800));
-       u32 stat = nv_rd32(priv, 0x128128 + (i * 0x0800));
-       nv_error(priv, "GPC%d: 0x%06x 0x%08x (0x%08x)\n", i, addr, data, stat);
-       nv_mask(priv, 0x128128 + (i * 0x0800), 0x00000200, 0x00000000);
-}
-
-static void
-nve0_ibus_intr(struct nouveau_subdev *subdev)
-{
-       struct nve0_ibus_priv *priv = (void *)subdev;
-       u32 intr0 = nv_rd32(priv, 0x120058);
-       u32 intr1 = nv_rd32(priv, 0x12005c);
-       u32 hubnr = nv_rd32(priv, 0x120070);
-       u32 ropnr = nv_rd32(priv, 0x120074);
-       u32 gpcnr = nv_rd32(priv, 0x120078);
-       u32 i;
-
-       for (i = 0; (intr0 & 0x0000ff00) && i < hubnr; i++) {
-               u32 stat = 0x00000100 << i;
-               if (intr0 & stat) {
-                       nve0_ibus_intr_hub(priv, i);
-                       intr0 &= ~stat;
-               }
-       }
-
-       for (i = 0; (intr0 & 0xffff0000) && i < ropnr; i++) {
-               u32 stat = 0x00010000 << i;
-               if (intr0 & stat) {
-                       nve0_ibus_intr_rop(priv, i);
-                       intr0 &= ~stat;
-               }
-       }
-
-       for (i = 0; intr1 && i < gpcnr; i++) {
-               u32 stat = 0x00000001 << i;
-               if (intr1 & stat) {
-                       nve0_ibus_intr_gpc(priv, i);
-                       intr1 &= ~stat;
-               }
-       }
-}
-
-static int
-nve0_ibus_init(struct nouveau_object *object)
-{
-       struct nve0_ibus_priv *priv = (void *)object;
-       int ret = nouveau_ibus_init(&priv->base);
-       if (ret == 0) {
-               nv_mask(priv, 0x122318, 0x0003ffff, 0x00001000);
-               nv_mask(priv, 0x12231c, 0x0003ffff, 0x00000200);
-               nv_mask(priv, 0x122310, 0x0003ffff, 0x00000800);
-               nv_mask(priv, 0x122348, 0x0003ffff, 0x00000100);
-               nv_mask(priv, 0x1223b0, 0x0003ffff, 0x00000fff);
-               nv_mask(priv, 0x122348, 0x0003ffff, 0x00000200);
-               nv_mask(priv, 0x122358, 0x0003ffff, 0x00002880);
-       }
-       return ret;
-}
-
-static int
-nve0_ibus_ctor(struct nouveau_object *parent, struct nouveau_object *engine,
-              struct nouveau_oclass *oclass, void *data, u32 size,
-              struct nouveau_object **pobject)
-{
-       struct nve0_ibus_priv *priv;
-       int ret;
-
-       ret = nouveau_ibus_create(parent, engine, oclass, &priv);
-       *pobject = nv_object(priv);
-       if (ret)
-               return ret;
-
-       nv_subdev(priv)->intr = nve0_ibus_intr;
-       return 0;
-}
-
-struct nouveau_oclass
-nve0_ibus_oclass = {
-       .handle = NV_SUBDEV(IBUS, 0xe0),
-       .ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nve0_ibus_ctor,
-               .dtor = _nouveau_ibus_dtor,
-               .init = nve0_ibus_init,
-               .fini = _nouveau_ibus_fini,
-       },
-};
diff --git a/drivers/gpu/drm/nouveau/core/subdev/instmem/base.c b/drivers/gpu/drm/nouveau/core/subdev/instmem/base.c
deleted file mode 100644 (file)
index 14706d9..0000000
+++ /dev/null
@@ -1,157 +0,0 @@
-/*
- * Copyright 2012 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 "priv.h"
-
-/******************************************************************************
- * instmem object base implementation
- *****************************************************************************/
-
-void
-_nouveau_instobj_dtor(struct nouveau_object *object)
-{
-       struct nouveau_instmem *imem = (void *)object->engine;
-       struct nouveau_instobj *iobj = (void *)object;
-
-       mutex_lock(&nv_subdev(imem)->mutex);
-       list_del(&iobj->head);
-       mutex_unlock(&nv_subdev(imem)->mutex);
-
-       return nouveau_object_destroy(&iobj->base);
-}
-
-int
-nouveau_instobj_create_(struct nouveau_object *parent,
-                       struct nouveau_object *engine,
-                       struct nouveau_oclass *oclass,
-                       int length, void **pobject)
-{
-       struct nouveau_instmem *imem = (void *)engine;
-       struct nouveau_instobj *iobj;
-       int ret;
-
-       ret = nouveau_object_create_(parent, engine, oclass, NV_MEMOBJ_CLASS,
-                                    length, pobject);
-       iobj = *pobject;
-       if (ret)
-               return ret;
-
-       mutex_lock(&imem->base.mutex);
-       list_add(&iobj->head, &imem->list);
-       mutex_unlock(&imem->base.mutex);
-       return 0;
-}
-
-/******************************************************************************
- * instmem subdev base implementation
- *****************************************************************************/
-
-static int
-nouveau_instmem_alloc(struct nouveau_instmem *imem,
-                     struct nouveau_object *parent, u32 size, u32 align,
-                     struct nouveau_object **pobject)
-{
-       struct nouveau_object *engine = nv_object(imem);
-       struct nouveau_instmem_impl *impl = (void *)engine->oclass;
-       struct nouveau_instobj_args args = { .size = size, .align = align };
-       return nouveau_object_ctor(parent, engine, impl->instobj, &args,
-                                  sizeof(args), pobject);
-}
-
-int
-_nouveau_instmem_fini(struct nouveau_object *object, bool suspend)
-{
-       struct nouveau_instmem *imem = (void *)object;
-       struct nouveau_instobj *iobj;
-       int i, ret = 0;
-
-       if (suspend) {
-               mutex_lock(&imem->base.mutex);
-
-               list_for_each_entry(iobj, &imem->list, head) {
-                       iobj->suspend = vmalloc(iobj->size);
-                       if (!iobj->suspend) {
-                               ret = -ENOMEM;
-                               break;
-                       }
-
-                       for (i = 0; i < iobj->size; i += 4)
-                               iobj->suspend[i / 4] = nv_ro32(iobj, i);
-               }
-
-               mutex_unlock(&imem->base.mutex);
-
-               if (ret)
-                       return ret;
-       }
-
-       return nouveau_subdev_fini(&imem->base, suspend);
-}
-
-int
-_nouveau_instmem_init(struct nouveau_object *object)
-{
-       struct nouveau_instmem *imem = (void *)object;
-       struct nouveau_instobj *iobj;
-       int ret, i;
-
-       ret = nouveau_subdev_init(&imem->base);
-       if (ret)
-               return ret;
-
-       mutex_lock(&imem->base.mutex);
-
-       list_for_each_entry(iobj, &imem->list, head) {
-               if (iobj->suspend) {
-                       for (i = 0; i < iobj->size; i += 4)
-                               nv_wo32(iobj, i, iobj->suspend[i / 4]);
-                       vfree(iobj->suspend);
-                       iobj->suspend = NULL;
-               }
-       }
-
-       mutex_unlock(&imem->base.mutex);
-
-       return 0;
-}
-
-int
-nouveau_instmem_create_(struct nouveau_object *parent,
-                       struct nouveau_object *engine,
-                       struct nouveau_oclass *oclass,
-                       int length, void **pobject)
-{
-       struct nouveau_instmem *imem;
-       int ret;
-
-       ret = nouveau_subdev_create_(parent, engine, oclass, 0,
-                                    "INSTMEM", "instmem", length, pobject);
-       imem = *pobject;
-       if (ret)
-               return ret;
-
-       INIT_LIST_HEAD(&imem->list);
-       imem->alloc = nouveau_instmem_alloc;
-       return 0;
-}
diff --git a/drivers/gpu/drm/nouveau/core/subdev/instmem/nv04.c b/drivers/gpu/drm/nouveau/core/subdev/instmem/nv04.c
deleted file mode 100644 (file)
index e8b1401..0000000
+++ /dev/null
@@ -1,182 +0,0 @@
-/*
- * Copyright 2012 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 "nv04.h"
-
-/******************************************************************************
- * instmem object implementation
- *****************************************************************************/
-
-static u32
-nv04_instobj_rd32(struct nouveau_object *object, u64 addr)
-{
-       struct nv04_instobj_priv *node = (void *)object;
-       return nv_ro32(object->engine, node->mem->offset + addr);
-}
-
-static void
-nv04_instobj_wr32(struct nouveau_object *object, u64 addr, u32 data)
-{
-       struct nv04_instobj_priv *node = (void *)object;
-       nv_wo32(object->engine, node->mem->offset + addr, data);
-}
-
-static void
-nv04_instobj_dtor(struct nouveau_object *object)
-{
-       struct nv04_instmem_priv *priv = (void *)object->engine;
-       struct nv04_instobj_priv *node = (void *)object;
-       nouveau_mm_free(&priv->heap, &node->mem);
-       nouveau_instobj_destroy(&node->base);
-}
-
-static int
-nv04_instobj_ctor(struct nouveau_object *parent, struct nouveau_object *engine,
-                 struct nouveau_oclass *oclass, void *data, u32 size,
-                 struct nouveau_object **pobject)
-{
-       struct nv04_instmem_priv *priv = (void *)engine;
-       struct nv04_instobj_priv *node;
-       struct nouveau_instobj_args *args = data;
-       int ret;
-
-       if (!args->align)
-               args->align = 1;
-
-       ret = nouveau_instobj_create(parent, engine, oclass, &node);
-       *pobject = nv_object(node);
-       if (ret)
-               return ret;
-
-       ret = nouveau_mm_head(&priv->heap, 0, 1, args->size, args->size,
-                             args->align, &node->mem);
-       if (ret)
-               return ret;
-
-       node->base.addr = node->mem->offset;
-       node->base.size = node->mem->length;
-       return 0;
-}
-
-struct nouveau_instobj_impl
-nv04_instobj_oclass = {
-       .base.ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nv04_instobj_ctor,
-               .dtor = nv04_instobj_dtor,
-               .init = _nouveau_instobj_init,
-               .fini = _nouveau_instobj_fini,
-               .rd32 = nv04_instobj_rd32,
-               .wr32 = nv04_instobj_wr32,
-       },
-};
-
-/******************************************************************************
- * instmem subdev implementation
- *****************************************************************************/
-
-static u32
-nv04_instmem_rd32(struct nouveau_object *object, u64 addr)
-{
-       return nv_rd32(object, 0x700000 + addr);
-}
-
-static void
-nv04_instmem_wr32(struct nouveau_object *object, u64 addr, u32 data)
-{
-       return nv_wr32(object, 0x700000 + addr, data);
-}
-
-void
-nv04_instmem_dtor(struct nouveau_object *object)
-{
-       struct nv04_instmem_priv *priv = (void *)object;
-       nouveau_gpuobj_ref(NULL, &priv->ramfc);
-       nouveau_gpuobj_ref(NULL, &priv->ramro);
-       nouveau_ramht_ref(NULL, &priv->ramht);
-       nouveau_gpuobj_ref(NULL, &priv->vbios);
-       nouveau_mm_fini(&priv->heap);
-       if (priv->iomem)
-               iounmap(priv->iomem);
-       nouveau_instmem_destroy(&priv->base);
-}
-
-static int
-nv04_instmem_ctor(struct nouveau_object *parent, struct nouveau_object *engine,
-                 struct nouveau_oclass *oclass, void *data, u32 size,
-                 struct nouveau_object **pobject)
-{
-       struct nv04_instmem_priv *priv;
-       int ret;
-
-       ret = nouveau_instmem_create(parent, engine, oclass, &priv);
-       *pobject = nv_object(priv);
-       if (ret)
-               return ret;
-
-       /* PRAMIN aperture maps over the end of VRAM, reserve it */
-       priv->base.reserved = 512 * 1024;
-
-       ret = nouveau_mm_init(&priv->heap, 0, priv->base.reserved, 1);
-       if (ret)
-               return ret;
-
-       /* 0x00000-0x10000: reserve for probable vbios image */
-       ret = nouveau_gpuobj_new(nv_object(priv), NULL, 0x10000, 0, 0,
-                               &priv->vbios);
-       if (ret)
-               return ret;
-
-       /* 0x10000-0x18000: reserve for RAMHT */
-       ret = nouveau_ramht_new(nv_object(priv), NULL, 0x08000, 0, &priv->ramht);
-       if (ret)
-               return ret;
-
-       /* 0x18000-0x18800: reserve for RAMFC (enough for 32 nv30 channels) */
-       ret = nouveau_gpuobj_new(nv_object(priv), NULL, 0x00800, 0,
-                                NVOBJ_FLAG_ZERO_ALLOC, &priv->ramfc);
-       if (ret)
-               return ret;
-
-       /* 0x18800-0x18a00: reserve for RAMRO */
-       ret = nouveau_gpuobj_new(nv_object(priv), NULL, 0x00200, 0, 0,
-                               &priv->ramro);
-       if (ret)
-               return ret;
-
-       return 0;
-}
-
-struct nouveau_oclass *
-nv04_instmem_oclass = &(struct nouveau_instmem_impl) {
-       .base.handle = NV_SUBDEV(INSTMEM, 0x04),
-       .base.ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nv04_instmem_ctor,
-               .dtor = nv04_instmem_dtor,
-               .init = _nouveau_instmem_init,
-               .fini = _nouveau_instmem_fini,
-               .rd32 = nv04_instmem_rd32,
-               .wr32 = nv04_instmem_wr32,
-       },
-       .instobj = &nv04_instobj_oclass.base,
-}.base;
diff --git a/drivers/gpu/drm/nouveau/core/subdev/instmem/nv04.h b/drivers/gpu/drm/nouveau/core/subdev/instmem/nv04.h
deleted file mode 100644 (file)
index 095fbc6..0000000
+++ /dev/null
@@ -1,40 +0,0 @@
-#ifndef __NV04_INSTMEM_H__
-#define __NV04_INSTMEM_H__
-
-#include <core/gpuobj.h>
-#include <core/ramht.h>
-#include <core/mm.h>
-
-#include "priv.h"
-
-extern struct nouveau_instobj_impl nv04_instobj_oclass;
-
-struct nv04_instmem_priv {
-       struct nouveau_instmem base;
-
-       void __iomem *iomem;
-       struct nouveau_mm heap;
-
-       struct nouveau_gpuobj *vbios;
-       struct nouveau_ramht  *ramht;
-       struct nouveau_gpuobj *ramro;
-       struct nouveau_gpuobj *ramfc;
-};
-
-static inline struct nv04_instmem_priv *
-nv04_instmem(void *obj)
-{
-       return (void *)nouveau_instmem(obj);
-}
-
-struct nv04_instobj_priv {
-       struct nouveau_instobj base;
-       struct nouveau_mm_node *mem;
-};
-
-void nv04_instmem_dtor(struct nouveau_object *);
-
-int nv04_instmem_alloc(struct nouveau_instmem *, struct nouveau_object *,
-                      u32 size, u32 align, struct nouveau_object **pobject);
-
-#endif
diff --git a/drivers/gpu/drm/nouveau/core/subdev/instmem/nv40.c b/drivers/gpu/drm/nouveau/core/subdev/instmem/nv40.c
deleted file mode 100644 (file)
index 8803809..0000000
+++ /dev/null
@@ -1,137 +0,0 @@
-/*
- * Copyright 2012 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 <engine/graph/nv40.h>
-
-#include "nv04.h"
-
-/******************************************************************************
- * instmem subdev implementation
- *****************************************************************************/
-
-static u32
-nv40_instmem_rd32(struct nouveau_object *object, u64 addr)
-{
-       struct nv04_instmem_priv *priv = (void *)object;
-       return ioread32_native(priv->iomem + addr);
-}
-
-static void
-nv40_instmem_wr32(struct nouveau_object *object, u64 addr, u32 data)
-{
-       struct nv04_instmem_priv *priv = (void *)object;
-       iowrite32_native(data, priv->iomem + addr);
-}
-
-static int
-nv40_instmem_ctor(struct nouveau_object *parent, struct nouveau_object *engine,
-                 struct nouveau_oclass *oclass, void *data, u32 size,
-                 struct nouveau_object **pobject)
-{
-       struct nouveau_device *device = nv_device(parent);
-       struct nv04_instmem_priv *priv;
-       int ret, bar, vs;
-
-       ret = nouveau_instmem_create(parent, engine, oclass, &priv);
-       *pobject = nv_object(priv);
-       if (ret)
-               return ret;
-
-       /* map bar */
-       if (nv_device_resource_len(device, 2))
-               bar = 2;
-       else
-               bar = 3;
-
-       priv->iomem = ioremap(nv_device_resource_start(device, bar),
-                             nv_device_resource_len(device, bar));
-       if (!priv->iomem) {
-               nv_error(priv, "unable to map PRAMIN BAR\n");
-               return -EFAULT;
-       }
-
-       /* PRAMIN aperture maps over the end of vram, reserve enough space
-        * to fit graphics contexts for every channel, the magics come
-        * from engine/graph/nv40.c
-        */
-       vs = hweight8((nv_rd32(priv, 0x001540) & 0x0000ff00) >> 8);
-       if      (device->chipset == 0x40) priv->base.reserved = 0x6aa0 * vs;
-       else if (device->chipset  < 0x43) priv->base.reserved = 0x4f00 * vs;
-       else if (nv44_graph_class(priv))  priv->base.reserved = 0x4980 * vs;
-       else                              priv->base.reserved = 0x4a40 * vs;
-       priv->base.reserved += 16 * 1024;
-       priv->base.reserved *= 32;              /* per-channel */
-       priv->base.reserved += 512 * 1024;      /* pci(e)gart table */
-       priv->base.reserved += 512 * 1024;      /* object storage */
-
-       priv->base.reserved = round_up(priv->base.reserved, 4096);
-
-       ret = nouveau_mm_init(&priv->heap, 0, priv->base.reserved, 1);
-       if (ret)
-               return ret;
-
-       /* 0x00000-0x10000: reserve for probable vbios image */
-       ret = nouveau_gpuobj_new(nv_object(priv), NULL, 0x10000, 0, 0,
-                               &priv->vbios);
-       if (ret)
-               return ret;
-
-       /* 0x10000-0x18000: reserve for RAMHT */
-       ret = nouveau_ramht_new(nv_object(priv), NULL, 0x08000, 0,
-                              &priv->ramht);
-       if (ret)
-               return ret;
-
-       /* 0x18000-0x18200: reserve for RAMRO
-        * 0x18200-0x20000: padding
-        */
-       ret = nouveau_gpuobj_new(nv_object(priv), NULL, 0x08000, 0, 0,
-                               &priv->ramro);
-       if (ret)
-               return ret;
-
-       /* 0x20000-0x21000: reserve for RAMFC
-        * 0x21000-0x40000: padding and some unknown crap
-        */
-       ret = nouveau_gpuobj_new(nv_object(priv), NULL, 0x20000, 0,
-                                NVOBJ_FLAG_ZERO_ALLOC, &priv->ramfc);
-       if (ret)
-               return ret;
-
-       return 0;
-}
-
-struct nouveau_oclass *
-nv40_instmem_oclass = &(struct nouveau_instmem_impl) {
-       .base.handle = NV_SUBDEV(INSTMEM, 0x40),
-       .base.ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nv40_instmem_ctor,
-               .dtor = nv04_instmem_dtor,
-               .init = _nouveau_instmem_init,
-               .fini = _nouveau_instmem_fini,
-               .rd32 = nv40_instmem_rd32,
-               .wr32 = nv40_instmem_wr32,
-       },
-       .instobj = &nv04_instobj_oclass.base,
-}.base;
diff --git a/drivers/gpu/drm/nouveau/core/subdev/instmem/nv50.c b/drivers/gpu/drm/nouveau/core/subdev/instmem/nv50.c
deleted file mode 100644 (file)
index 7cb3b09..0000000
+++ /dev/null
@@ -1,171 +0,0 @@
-/*
- * Copyright 2012 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 <subdev/fb.h>
-#include <core/mm.h>
-
-#include "priv.h"
-
-struct nv50_instmem_priv {
-       struct nouveau_instmem base;
-       spinlock_t lock;
-       u64 addr;
-};
-
-struct nv50_instobj_priv {
-       struct nouveau_instobj base;
-       struct nouveau_mem *mem;
-};
-
-/******************************************************************************
- * instmem object implementation
- *****************************************************************************/
-
-static u32
-nv50_instobj_rd32(struct nouveau_object *object, u64 offset)
-{
-       struct nv50_instmem_priv *priv = (void *)object->engine;
-       struct nv50_instobj_priv *node = (void *)object;
-       unsigned long flags;
-       u64 base = (node->mem->offset + offset) & 0xffffff00000ULL;
-       u64 addr = (node->mem->offset + offset) & 0x000000fffffULL;
-       u32 data;
-
-       spin_lock_irqsave(&priv->lock, flags);
-       if (unlikely(priv->addr != base)) {
-               nv_wr32(priv, 0x001700, base >> 16);
-               priv->addr = base;
-       }
-       data = nv_rd32(priv, 0x700000 + addr);
-       spin_unlock_irqrestore(&priv->lock, flags);
-       return data;
-}
-
-static void
-nv50_instobj_wr32(struct nouveau_object *object, u64 offset, u32 data)
-{
-       struct nv50_instmem_priv *priv = (void *)object->engine;
-       struct nv50_instobj_priv *node = (void *)object;
-       unsigned long flags;
-       u64 base = (node->mem->offset + offset) & 0xffffff00000ULL;
-       u64 addr = (node->mem->offset + offset) & 0x000000fffffULL;
-
-       spin_lock_irqsave(&priv->lock, flags);
-       if (unlikely(priv->addr != base)) {
-               nv_wr32(priv, 0x001700, base >> 16);
-               priv->addr = base;
-       }
-       nv_wr32(priv, 0x700000 + addr, data);
-       spin_unlock_irqrestore(&priv->lock, flags);
-}
-
-static void
-nv50_instobj_dtor(struct nouveau_object *object)
-{
-       struct nv50_instobj_priv *node = (void *)object;
-       struct nouveau_fb *pfb = nouveau_fb(object);
-       pfb->ram->put(pfb, &node->mem);
-       nouveau_instobj_destroy(&node->base);
-}
-
-static int
-nv50_instobj_ctor(struct nouveau_object *parent, struct nouveau_object *engine,
-                 struct nouveau_oclass *oclass, void *data, u32 size,
-                 struct nouveau_object **pobject)
-{
-       struct nouveau_fb *pfb = nouveau_fb(parent);
-       struct nouveau_instobj_args *args = data;
-       struct nv50_instobj_priv *node;
-       int ret;
-
-       args->size  = max((args->size  + 4095) & ~4095, (u32)4096);
-       args->align = max((args->align + 4095) & ~4095, (u32)4096);
-
-       ret = nouveau_instobj_create(parent, engine, oclass, &node);
-       *pobject = nv_object(node);
-       if (ret)
-               return ret;
-
-       ret = pfb->ram->get(pfb, args->size, args->align, 0, 0x800, &node->mem);
-       if (ret)
-               return ret;
-
-       node->base.addr = node->mem->offset;
-       node->base.size = node->mem->size << 12;
-       node->mem->page_shift = 12;
-       return 0;
-}
-
-static struct nouveau_instobj_impl
-nv50_instobj_oclass = {
-       .base.ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nv50_instobj_ctor,
-               .dtor = nv50_instobj_dtor,
-               .init = _nouveau_instobj_init,
-               .fini = _nouveau_instobj_fini,
-               .rd32 = nv50_instobj_rd32,
-               .wr32 = nv50_instobj_wr32,
-       },
-};
-
-/******************************************************************************
- * instmem subdev implementation
- *****************************************************************************/
-
-static int
-nv50_instmem_fini(struct nouveau_object *object, bool suspend)
-{
-       struct nv50_instmem_priv *priv = (void *)object;
-       priv->addr = ~0ULL;
-       return nouveau_instmem_fini(&priv->base, suspend);
-}
-
-static int
-nv50_instmem_ctor(struct nouveau_object *parent, struct nouveau_object *engine,
-                 struct nouveau_oclass *oclass, void *data, u32 size,
-                 struct nouveau_object **pobject)
-{
-       struct nv50_instmem_priv *priv;
-       int ret;
-
-       ret = nouveau_instmem_create(parent, engine, oclass, &priv);
-       *pobject = nv_object(priv);
-       if (ret)
-               return ret;
-
-       spin_lock_init(&priv->lock);
-       return 0;
-}
-
-struct nouveau_oclass *
-nv50_instmem_oclass = &(struct nouveau_instmem_impl) {
-       .base.handle = NV_SUBDEV(INSTMEM, 0x50),
-       .base.ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nv50_instmem_ctor,
-               .dtor = _nouveau_instmem_dtor,
-               .init = _nouveau_instmem_init,
-               .fini = nv50_instmem_fini,
-       },
-       .instobj = &nv50_instobj_oclass.base,
-}.base;
diff --git a/drivers/gpu/drm/nouveau/core/subdev/instmem/priv.h b/drivers/gpu/drm/nouveau/core/subdev/instmem/priv.h
deleted file mode 100644 (file)
index 8d67ded..0000000
+++ /dev/null
@@ -1,56 +0,0 @@
-#ifndef __NVKM_INSTMEM_PRIV_H__
-#define __NVKM_INSTMEM_PRIV_H__
-
-#include <subdev/instmem.h>
-
-struct nouveau_instobj_impl {
-       struct nouveau_oclass base;
-};
-
-struct nouveau_instobj_args {
-       u32 size;
-       u32 align;
-};
-
-#define nouveau_instobj_create(p,e,o,d)                                        \
-       nouveau_instobj_create_((p), (e), (o), sizeof(**d), (void **)d)
-#define nouveau_instobj_destroy(p) ({                                          \
-       struct nouveau_instobj *iobj = (p);                                    \
-       _nouveau_instobj_dtor(nv_object(iobj));                                \
-})
-#define nouveau_instobj_init(p)                                                \
-       nouveau_object_init(&(p)->base)
-#define nouveau_instobj_fini(p,s)                                              \
-       nouveau_object_fini(&(p)->base, (s))
-
-int  nouveau_instobj_create_(struct nouveau_object *, struct nouveau_object *,
-                            struct nouveau_oclass *, int, void **);
-void _nouveau_instobj_dtor(struct nouveau_object *);
-#define _nouveau_instobj_init nouveau_object_init
-#define _nouveau_instobj_fini nouveau_object_fini
-
-struct nouveau_instmem_impl {
-       struct nouveau_oclass base;
-       struct nouveau_oclass *instobj;
-};
-
-#define nouveau_instmem_create(p,e,o,d)                                        \
-       nouveau_instmem_create_((p), (e), (o), sizeof(**d), (void **)d)
-#define nouveau_instmem_destroy(p)                                             \
-       nouveau_subdev_destroy(&(p)->base)
-#define nouveau_instmem_init(p) ({                                             \
-       struct nouveau_instmem *imem = (p);                                    \
-       _nouveau_instmem_init(nv_object(imem));                                \
-})
-#define nouveau_instmem_fini(p,s) ({                                           \
-       struct nouveau_instmem *imem = (p);                                    \
-       _nouveau_instmem_fini(nv_object(imem), (s));                           \
-})
-
-int nouveau_instmem_create_(struct nouveau_object *, struct nouveau_object *,
-                           struct nouveau_oclass *, int, void **);
-#define _nouveau_instmem_dtor _nouveau_subdev_dtor
-int _nouveau_instmem_init(struct nouveau_object *);
-int _nouveau_instmem_fini(struct nouveau_object *, bool);
-
-#endif
diff --git a/drivers/gpu/drm/nouveau/core/subdev/ltc/base.c b/drivers/gpu/drm/nouveau/core/subdev/ltc/base.c
deleted file mode 100644 (file)
index 7fa3315..0000000
+++ /dev/null
@@ -1,126 +0,0 @@
-/*
- * Copyright 2014 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 <bskeggs@redhat.com>
- */
-
-#include "priv.h"
-
-static int
-nvkm_ltc_tags_alloc(struct nouveau_ltc *ltc, u32 n,
-                   struct nouveau_mm_node **pnode)
-{
-       struct nvkm_ltc_priv *priv = (void *)ltc;
-       int ret;
-
-       ret = nouveau_mm_head(&priv->tags, 0, 1, n, n, 1, pnode);
-       if (ret)
-               *pnode = NULL;
-
-       return ret;
-}
-
-static void
-nvkm_ltc_tags_free(struct nouveau_ltc *ltc, struct nouveau_mm_node **pnode)
-{
-       struct nvkm_ltc_priv *priv = (void *)ltc;
-       nouveau_mm_free(&priv->tags, pnode);
-}
-
-static void
-nvkm_ltc_tags_clear(struct nouveau_ltc *ltc, u32 first, u32 count)
-{
-       const struct nvkm_ltc_impl *impl = (void *)nv_oclass(ltc);
-       struct nvkm_ltc_priv *priv = (void *)ltc;
-       const u32 limit = first + count - 1;
-
-       BUG_ON((first > limit) || (limit >= priv->num_tags));
-
-       impl->cbc_clear(priv, first, limit);
-       impl->cbc_wait(priv);
-}
-
-static int
-nvkm_ltc_zbc_color_get(struct nouveau_ltc *ltc, int index, const u32 color[4])
-{
-       const struct nvkm_ltc_impl *impl = (void *)nv_oclass(ltc);
-       struct nvkm_ltc_priv *priv = (void *)ltc;
-       memcpy(priv->zbc_color[index], color, sizeof(priv->zbc_color[index]));
-       impl->zbc_clear_color(priv, index, color);
-       return index;
-}
-
-static int
-nvkm_ltc_zbc_depth_get(struct nouveau_ltc *ltc, int index, const u32 depth)
-{
-       const struct nvkm_ltc_impl *impl = (void *)nv_oclass(ltc);
-       struct nvkm_ltc_priv *priv = (void *)ltc;
-       priv->zbc_depth[index] = depth;
-       impl->zbc_clear_depth(priv, index, depth);
-       return index;
-}
-
-int
-_nvkm_ltc_init(struct nouveau_object *object)
-{
-       const struct nvkm_ltc_impl *impl = (void *)nv_oclass(object);
-       struct nvkm_ltc_priv *priv = (void *)object;
-       int ret, i;
-
-       ret = nouveau_subdev_init(&priv->base.base);
-       if (ret)
-               return ret;
-
-       for (i = priv->base.zbc_min; i <= priv->base.zbc_max; i++) {
-               impl->zbc_clear_color(priv, i, priv->zbc_color[i]);
-               impl->zbc_clear_depth(priv, i, priv->zbc_depth[i]);
-       }
-
-       return 0;
-}
-
-int
-nvkm_ltc_create_(struct nouveau_object *parent, struct nouveau_object *engine,
-                struct nouveau_oclass *oclass, int length, void **pobject)
-{
-       const struct nvkm_ltc_impl *impl = (void *)oclass;
-       struct nvkm_ltc_priv *priv;
-       int ret;
-
-       ret = nouveau_subdev_create_(parent, engine, oclass, 0, "PLTCG",
-                                    "l2c", length, pobject);
-       priv = *pobject;
-       if (ret)
-               return ret;
-
-       memset(priv->zbc_color, 0x00, sizeof(priv->zbc_color));
-       memset(priv->zbc_depth, 0x00, sizeof(priv->zbc_depth));
-
-       priv->base.base.intr = impl->intr;
-       priv->base.tags_alloc = nvkm_ltc_tags_alloc;
-       priv->base.tags_free = nvkm_ltc_tags_free;
-       priv->base.tags_clear = nvkm_ltc_tags_clear;
-       priv->base.zbc_min = 1; /* reserve 0 for disabled */
-       priv->base.zbc_max = min(impl->zbc, NOUVEAU_LTC_MAX_ZBC_CNT) - 1;
-       priv->base.zbc_color_get = nvkm_ltc_zbc_color_get;
-       priv->base.zbc_depth_get = nvkm_ltc_zbc_depth_get;
-       return 0;
-}
diff --git a/drivers/gpu/drm/nouveau/core/subdev/ltc/gf100.c b/drivers/gpu/drm/nouveau/core/subdev/ltc/gf100.c
deleted file mode 100644 (file)
index 2db0977..0000000
+++ /dev/null
@@ -1,236 +0,0 @@
-/*
- * Copyright 2012 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 <subdev/fb.h>
-#include <subdev/timer.h>
-
-#include "priv.h"
-
-void
-gf100_ltc_cbc_clear(struct nvkm_ltc_priv *priv, u32 start, u32 limit)
-{
-       nv_wr32(priv, 0x17e8cc, start);
-       nv_wr32(priv, 0x17e8d0, limit);
-       nv_wr32(priv, 0x17e8c8, 0x00000004);
-}
-
-void
-gf100_ltc_cbc_wait(struct nvkm_ltc_priv *priv)
-{
-       int c, s;
-       for (c = 0; c < priv->ltc_nr; c++) {
-               for (s = 0; s < priv->lts_nr; s++)
-                       nv_wait(priv, 0x1410c8 + c * 0x2000 + s * 0x400, ~0, 0);
-       }
-}
-
-void
-gf100_ltc_zbc_clear_color(struct nvkm_ltc_priv *priv, int i, const u32 color[4])
-{
-       nv_mask(priv, 0x17ea44, 0x0000000f, i);
-       nv_wr32(priv, 0x17ea48, color[0]);
-       nv_wr32(priv, 0x17ea4c, color[1]);
-       nv_wr32(priv, 0x17ea50, color[2]);
-       nv_wr32(priv, 0x17ea54, color[3]);
-}
-
-void
-gf100_ltc_zbc_clear_depth(struct nvkm_ltc_priv *priv, int i, const u32 depth)
-{
-       nv_mask(priv, 0x17ea44, 0x0000000f, i);
-       nv_wr32(priv, 0x17ea58, depth);
-}
-
-static const struct nouveau_bitfield
-gf100_ltc_lts_intr_name[] = {
-       { 0x00000001, "IDLE_ERROR_IQ" },
-       { 0x00000002, "IDLE_ERROR_CBC" },
-       { 0x00000004, "IDLE_ERROR_TSTG" },
-       { 0x00000008, "IDLE_ERROR_DSTG" },
-       { 0x00000010, "EVICTED_CB" },
-       { 0x00000020, "ILLEGAL_COMPSTAT" },
-       { 0x00000040, "BLOCKLINEAR_CB" },
-       { 0x00000100, "ECC_SEC_ERROR" },
-       { 0x00000200, "ECC_DED_ERROR" },
-       { 0x00000400, "DEBUG" },
-       { 0x00000800, "ATOMIC_TO_Z" },
-       { 0x00001000, "ILLEGAL_ATOMIC" },
-       { 0x00002000, "BLKACTIVITY_ERR" },
-       {}
-};
-
-static void
-gf100_ltc_lts_intr(struct nvkm_ltc_priv *priv, int ltc, int lts)
-{
-       u32 base = 0x141000 + (ltc * 0x2000) + (lts * 0x400);
-       u32 intr = nv_rd32(priv, base + 0x020);
-       u32 stat = intr & 0x0000ffff;
-
-       if (stat) {
-               nv_info(priv, "LTC%d_LTS%d:", ltc, lts);
-               nouveau_bitfield_print(gf100_ltc_lts_intr_name, stat);
-               pr_cont("\n");
-       }
-
-       nv_wr32(priv, base + 0x020, intr);
-}
-
-void
-gf100_ltc_intr(struct nouveau_subdev *subdev)
-{
-       struct nvkm_ltc_priv *priv = (void *)subdev;
-       u32 mask;
-
-       mask = nv_rd32(priv, 0x00017c);
-       while (mask) {
-               u32 lts, ltc = __ffs(mask);
-               for (lts = 0; lts < priv->lts_nr; lts++)
-                       gf100_ltc_lts_intr(priv, ltc, lts);
-               mask &= ~(1 << ltc);
-       }
-}
-
-static int
-gf100_ltc_init(struct nouveau_object *object)
-{
-       struct nvkm_ltc_priv *priv = (void *)object;
-       u32 lpg128 = !(nv_rd32(priv, 0x100c80) & 0x00000001);
-       int ret;
-
-       ret = nvkm_ltc_init(priv);
-       if (ret)
-               return ret;
-
-       nv_mask(priv, 0x17e820, 0x00100000, 0x00000000); /* INTR_EN &= ~0x10 */
-       nv_wr32(priv, 0x17e8d8, priv->ltc_nr);
-       nv_wr32(priv, 0x17e8d4, priv->tag_base);
-       nv_mask(priv, 0x17e8c0, 0x00000002, lpg128 ? 0x00000002 : 0x00000000);
-       return 0;
-}
-
-void
-gf100_ltc_dtor(struct nouveau_object *object)
-{
-       struct nouveau_fb *pfb = nouveau_fb(object);
-       struct nvkm_ltc_priv *priv = (void *)object;
-
-       nouveau_mm_fini(&priv->tags);
-       nouveau_mm_free(&pfb->vram, &priv->tag_ram);
-
-       nvkm_ltc_destroy(priv);
-}
-
-/* TODO: Figure out tag memory details and drop the over-cautious allocation.
- */
-int
-gf100_ltc_init_tag_ram(struct nouveau_fb *pfb, struct nvkm_ltc_priv *priv)
-{
-       u32 tag_size, tag_margin, tag_align;
-       int ret;
-
-       /* tags for 1/4 of VRAM should be enough (8192/4 per GiB of VRAM) */
-       priv->num_tags = (pfb->ram->size >> 17) / 4;
-       if (priv->num_tags > (1 << 17))
-               priv->num_tags = 1 << 17; /* we have 17 bits in PTE */
-       priv->num_tags = (priv->num_tags + 63) & ~63; /* round up to 64 */
-
-       tag_align = priv->ltc_nr * 0x800;
-       tag_margin = (tag_align < 0x6000) ? 0x6000 : tag_align;
-
-       /* 4 part 4 sub: 0x2000 bytes for 56 tags */
-       /* 3 part 4 sub: 0x6000 bytes for 168 tags */
-       /*
-        * About 147 bytes per tag. Let's be safe and allocate x2, which makes
-        * 0x4980 bytes for 64 tags, and round up to 0x6000 bytes for 64 tags.
-        *
-        * For 4 GiB of memory we'll have 8192 tags which makes 3 MiB, < 0.1 %.
-        */
-       tag_size  = (priv->num_tags / 64) * 0x6000 + tag_margin;
-       tag_size += tag_align;
-       tag_size  = (tag_size + 0xfff) >> 12; /* round up */
-
-       ret = nouveau_mm_tail(&pfb->vram, 1, 1, tag_size, tag_size, 1,
-                             &priv->tag_ram);
-       if (ret) {
-               priv->num_tags = 0;
-       } else {
-               u64 tag_base = ((u64)priv->tag_ram->offset << 12) + tag_margin;
-
-               tag_base += tag_align - 1;
-               ret = do_div(tag_base, tag_align);
-
-               priv->tag_base = tag_base;
-       }
-
-       ret = nouveau_mm_init(&priv->tags, 0, priv->num_tags, 1);
-       return ret;
-}
-
-int
-gf100_ltc_ctor(struct nouveau_object *parent, struct nouveau_object *engine,
-              struct nouveau_oclass *oclass, void *data, u32 size,
-              struct nouveau_object **pobject)
-{
-       struct nouveau_fb *pfb = nouveau_fb(parent);
-       struct nvkm_ltc_priv *priv;
-       u32 parts, mask;
-       int ret, i;
-
-       ret = nvkm_ltc_create(parent, engine, oclass, &priv);
-       *pobject = nv_object(priv);
-       if (ret)
-               return ret;
-
-       parts = nv_rd32(priv, 0x022438);
-       mask = nv_rd32(priv, 0x022554);
-       for (i = 0; i < parts; i++) {
-               if (!(mask & (1 << i)))
-                       priv->ltc_nr++;
-       }
-       priv->lts_nr = nv_rd32(priv, 0x17e8dc) >> 28;
-
-       ret = gf100_ltc_init_tag_ram(pfb, priv);
-       if (ret)
-               return ret;
-
-       nv_subdev(priv)->intr = gf100_ltc_intr;
-       return 0;
-}
-
-struct nouveau_oclass *
-gf100_ltc_oclass = &(struct nvkm_ltc_impl) {
-       .base.handle = NV_SUBDEV(LTC, 0xc0),
-       .base.ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = gf100_ltc_ctor,
-               .dtor = gf100_ltc_dtor,
-               .init = gf100_ltc_init,
-               .fini = _nvkm_ltc_fini,
-       },
-       .intr = gf100_ltc_intr,
-       .cbc_clear = gf100_ltc_cbc_clear,
-       .cbc_wait = gf100_ltc_cbc_wait,
-       .zbc = 16,
-       .zbc_clear_color = gf100_ltc_zbc_clear_color,
-       .zbc_clear_depth = gf100_ltc_zbc_clear_depth,
-}.base;
diff --git a/drivers/gpu/drm/nouveau/core/subdev/ltc/gk104.c b/drivers/gpu/drm/nouveau/core/subdev/ltc/gk104.c
deleted file mode 100644 (file)
index b39b5d0..0000000
+++ /dev/null
@@ -1,60 +0,0 @@
-/*
- * Copyright 2012 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 "priv.h"
-
-static int
-gk104_ltc_init(struct nouveau_object *object)
-{
-       struct nvkm_ltc_priv *priv = (void *)object;
-       u32 lpg128 = !(nv_rd32(priv, 0x100c80) & 0x00000001);
-       int ret;
-
-       ret = nvkm_ltc_init(priv);
-       if (ret)
-               return ret;
-
-       nv_wr32(priv, 0x17e8d8, priv->ltc_nr);
-       nv_wr32(priv, 0x17e000, priv->ltc_nr);
-       nv_wr32(priv, 0x17e8d4, priv->tag_base);
-       nv_mask(priv, 0x17e8c0, 0x00000002, lpg128 ? 0x00000002 : 0x00000000);
-       return 0;
-}
-
-struct nouveau_oclass *
-gk104_ltc_oclass = &(struct nvkm_ltc_impl) {
-       .base.handle = NV_SUBDEV(LTC, 0xe4),
-       .base.ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = gf100_ltc_ctor,
-               .dtor = gf100_ltc_dtor,
-               .init = gk104_ltc_init,
-               .fini = _nvkm_ltc_fini,
-       },
-       .intr = gf100_ltc_intr,
-       .cbc_clear = gf100_ltc_cbc_clear,
-       .cbc_wait = gf100_ltc_cbc_wait,
-       .zbc = 16,
-       .zbc_clear_color = gf100_ltc_zbc_clear_color,
-       .zbc_clear_depth = gf100_ltc_zbc_clear_depth,
-}.base;
diff --git a/drivers/gpu/drm/nouveau/core/subdev/ltc/gm107.c b/drivers/gpu/drm/nouveau/core/subdev/ltc/gm107.c
deleted file mode 100644 (file)
index 89fc423..0000000
+++ /dev/null
@@ -1,154 +0,0 @@
-/*
- * Copyright 2014 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 <subdev/fb.h>
-#include <subdev/timer.h>
-
-#include "priv.h"
-
-static void
-gm107_ltc_cbc_clear(struct nvkm_ltc_priv *priv, u32 start, u32 limit)
-{
-       nv_wr32(priv, 0x17e270, start);
-       nv_wr32(priv, 0x17e274, limit);
-       nv_wr32(priv, 0x17e26c, 0x00000004);
-}
-
-static void
-gm107_ltc_cbc_wait(struct nvkm_ltc_priv *priv)
-{
-       int c, s;
-       for (c = 0; c < priv->ltc_nr; c++) {
-               for (s = 0; s < priv->lts_nr; s++)
-                       nv_wait(priv, 0x14046c + c * 0x2000 + s * 0x200, ~0, 0);
-       }
-}
-
-static void
-gm107_ltc_zbc_clear_color(struct nvkm_ltc_priv *priv, int i, const u32 color[4])
-{
-       nv_mask(priv, 0x17e338, 0x0000000f, i);
-       nv_wr32(priv, 0x17e33c, color[0]);
-       nv_wr32(priv, 0x17e340, color[1]);
-       nv_wr32(priv, 0x17e344, color[2]);
-       nv_wr32(priv, 0x17e348, color[3]);
-}
-
-static void
-gm107_ltc_zbc_clear_depth(struct nvkm_ltc_priv *priv, int i, const u32 depth)
-{
-       nv_mask(priv, 0x17e338, 0x0000000f, i);
-       nv_wr32(priv, 0x17e34c, depth);
-}
-
-static void
-gm107_ltc_lts_isr(struct nvkm_ltc_priv *priv, int ltc, int lts)
-{
-       u32 base = 0x140000 + (ltc * 0x2000) + (lts * 0x400);
-       u32 stat = nv_rd32(priv, base + 0x00c);
-
-       if (stat) {
-               nv_info(priv, "LTC%d_LTS%d: 0x%08x\n", ltc, lts, stat);
-               nv_wr32(priv, base + 0x00c, stat);
-       }
-}
-
-static void
-gm107_ltc_intr(struct nouveau_subdev *subdev)
-{
-       struct nvkm_ltc_priv *priv = (void *)subdev;
-       u32 mask;
-
-       mask = nv_rd32(priv, 0x00017c);
-       while (mask) {
-               u32 lts, ltc = __ffs(mask);
-               for (lts = 0; lts < priv->lts_nr; lts++)
-                       gm107_ltc_lts_isr(priv, ltc, lts);
-               mask &= ~(1 << ltc);
-       }
-}
-
-static int
-gm107_ltc_init(struct nouveau_object *object)
-{
-       struct nvkm_ltc_priv *priv = (void *)object;
-       u32 lpg128 = !(nv_rd32(priv, 0x100c80) & 0x00000001);
-       int ret;
-
-       ret = nvkm_ltc_init(priv);
-       if (ret)
-               return ret;
-
-       nv_wr32(priv, 0x17e27c, priv->ltc_nr);
-       nv_wr32(priv, 0x17e278, priv->tag_base);
-       nv_mask(priv, 0x17e264, 0x00000002, lpg128 ? 0x00000002 : 0x00000000);
-       return 0;
-}
-
-static int
-gm107_ltc_ctor(struct nouveau_object *parent, struct nouveau_object *engine,
-              struct nouveau_oclass *oclass, void *data, u32 size,
-              struct nouveau_object **pobject)
-{
-       struct nouveau_fb *pfb = nouveau_fb(parent);
-       struct nvkm_ltc_priv *priv;
-       u32 parts, mask;
-       int ret, i;
-
-       ret = nvkm_ltc_create(parent, engine, oclass, &priv);
-       *pobject = nv_object(priv);
-       if (ret)
-               return ret;
-
-       parts = nv_rd32(priv, 0x022438);
-       mask = nv_rd32(priv, 0x021c14);
-       for (i = 0; i < parts; i++) {
-               if (!(mask & (1 << i)))
-                       priv->ltc_nr++;
-       }
-       priv->lts_nr = nv_rd32(priv, 0x17e280) >> 28;
-
-       ret = gf100_ltc_init_tag_ram(pfb, priv);
-       if (ret)
-               return ret;
-
-       return 0;
-}
-
-struct nouveau_oclass *
-gm107_ltc_oclass = &(struct nvkm_ltc_impl) {
-       .base.handle = NV_SUBDEV(LTC, 0xff),
-       .base.ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = gm107_ltc_ctor,
-               .dtor = gf100_ltc_dtor,
-               .init = gm107_ltc_init,
-               .fini = _nvkm_ltc_fini,
-       },
-       .intr = gm107_ltc_intr,
-       .cbc_clear = gm107_ltc_cbc_clear,
-       .cbc_wait = gm107_ltc_cbc_wait,
-       .zbc = 16,
-       .zbc_clear_color = gm107_ltc_zbc_clear_color,
-       .zbc_clear_depth = gm107_ltc_zbc_clear_depth,
-}.base;
diff --git a/drivers/gpu/drm/nouveau/core/subdev/ltc/priv.h b/drivers/gpu/drm/nouveau/core/subdev/ltc/priv.h
deleted file mode 100644 (file)
index 41f179d..0000000
+++ /dev/null
@@ -1,71 +0,0 @@
-#ifndef __NVKM_LTC_PRIV_H__
-#define __NVKM_LTC_PRIV_H__
-
-#include <subdev/ltc.h>
-#include <subdev/fb.h>
-
-#include <core/enum.h>
-
-struct nvkm_ltc_priv {
-       struct nouveau_ltc base;
-       u32 ltc_nr;
-       u32 lts_nr;
-
-       u32 num_tags;
-       u32 tag_base;
-       struct nouveau_mm tags;
-       struct nouveau_mm_node *tag_ram;
-
-       u32 zbc_color[NOUVEAU_LTC_MAX_ZBC_CNT][4];
-       u32 zbc_depth[NOUVEAU_LTC_MAX_ZBC_CNT];
-};
-
-#define nvkm_ltc_create(p,e,o,d)                                               \
-       nvkm_ltc_create_((p), (e), (o), sizeof(**d), (void **)d)
-#define nvkm_ltc_destroy(p) ({                                                 \
-       struct nvkm_ltc_priv *_priv = (p);                                     \
-       _nvkm_ltc_dtor(nv_object(_priv));                                      \
-})
-#define nvkm_ltc_init(p) ({                                                    \
-       struct nvkm_ltc_priv *_priv = (p);                                     \
-       _nvkm_ltc_init(nv_object(_priv));                                      \
-})
-#define nvkm_ltc_fini(p,s) ({                                                  \
-       struct nvkm_ltc_priv *_priv = (p);                                     \
-       _nvkm_ltc_fini(nv_object(_priv), (s));                                 \
-})
-
-int  nvkm_ltc_create_(struct nouveau_object *, struct nouveau_object *,
-                     struct nouveau_oclass *, int, void **);
-
-#define _nvkm_ltc_dtor _nouveau_subdev_dtor
-int _nvkm_ltc_init(struct nouveau_object *);
-#define _nvkm_ltc_fini _nouveau_subdev_fini
-
-int  gf100_ltc_ctor(struct nouveau_object *, struct nouveau_object *,
-                   struct nouveau_oclass *, void *, u32,
-                   struct nouveau_object **);
-void gf100_ltc_dtor(struct nouveau_object *);
-int  gf100_ltc_init_tag_ram(struct nouveau_fb *, struct nvkm_ltc_priv *);
-int  gf100_ltc_tags_alloc(struct nouveau_ltc *, u32, struct nouveau_mm_node **);
-void gf100_ltc_tags_free(struct nouveau_ltc *, struct nouveau_mm_node **);
-
-struct nvkm_ltc_impl {
-       struct nouveau_oclass base;
-       void (*intr)(struct nouveau_subdev *);
-
-       void (*cbc_clear)(struct nvkm_ltc_priv *, u32 start, u32 limit);
-       void (*cbc_wait)(struct nvkm_ltc_priv *);
-
-       int zbc;
-       void (*zbc_clear_color)(struct nvkm_ltc_priv *, int, const u32[4]);
-       void (*zbc_clear_depth)(struct nvkm_ltc_priv *, int, const u32);
-};
-
-void gf100_ltc_intr(struct nouveau_subdev *);
-void gf100_ltc_cbc_clear(struct nvkm_ltc_priv *, u32, u32);
-void gf100_ltc_cbc_wait(struct nvkm_ltc_priv *);
-void gf100_ltc_zbc_clear_color(struct nvkm_ltc_priv *, int, const u32[4]);
-void gf100_ltc_zbc_clear_depth(struct nvkm_ltc_priv *, int, const u32);
-
-#endif
diff --git a/drivers/gpu/drm/nouveau/core/subdev/mc/base.c b/drivers/gpu/drm/nouveau/core/subdev/mc/base.c
deleted file mode 100644 (file)
index ca7cee3..0000000
+++ /dev/null
@@ -1,169 +0,0 @@
-/*
- * Copyright 2012 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 "priv.h"
-#include <core/option.h>
-
-static inline void
-nouveau_mc_unk260(struct nouveau_mc *pmc, u32 data)
-{
-       const struct nouveau_mc_oclass *impl = (void *)nv_oclass(pmc);
-       if (impl->unk260)
-               impl->unk260(pmc, data);
-}
-
-static inline u32
-nouveau_mc_intr_mask(struct nouveau_mc *pmc)
-{
-       u32 intr = nv_rd32(pmc, 0x000100);
-       if (intr == 0xffffffff) /* likely fallen off the bus */
-               intr = 0x00000000;
-       return intr;
-}
-
-static irqreturn_t
-nouveau_mc_intr(int irq, void *arg)
-{
-       struct nouveau_mc *pmc = arg;
-       const struct nouveau_mc_oclass *oclass = (void *)nv_object(pmc)->oclass;
-       const struct nouveau_mc_intr *map = oclass->intr;
-       struct nouveau_subdev *unit;
-       u32 intr;
-
-       nv_wr32(pmc, 0x000140, 0x00000000);
-       nv_rd32(pmc, 0x000140);
-       intr = nouveau_mc_intr_mask(pmc);
-       if (pmc->use_msi)
-               oclass->msi_rearm(pmc);
-
-       if (intr) {
-               u32 stat = intr = nouveau_mc_intr_mask(pmc);
-               while (map->stat) {
-                       if (intr & map->stat) {
-                               unit = nouveau_subdev(pmc, map->unit);
-                               if (unit && unit->intr)
-                                       unit->intr(unit);
-                               stat &= ~map->stat;
-                       }
-                       map++;
-               }
-
-               if (stat)
-                       nv_error(pmc, "unknown intr 0x%08x\n", stat);
-       }
-
-       nv_wr32(pmc, 0x000140, 0x00000001);
-       return intr ? IRQ_HANDLED : IRQ_NONE;
-}
-
-int
-_nouveau_mc_fini(struct nouveau_object *object, bool suspend)
-{
-       struct nouveau_mc *pmc = (void *)object;
-       nv_wr32(pmc, 0x000140, 0x00000000);
-       return nouveau_subdev_fini(&pmc->base, suspend);
-}
-
-int
-_nouveau_mc_init(struct nouveau_object *object)
-{
-       struct nouveau_mc *pmc = (void *)object;
-       int ret = nouveau_subdev_init(&pmc->base);
-       if (ret)
-               return ret;
-       nv_wr32(pmc, 0x000140, 0x00000001);
-       return 0;
-}
-
-void
-_nouveau_mc_dtor(struct nouveau_object *object)
-{
-       struct nouveau_device *device = nv_device(object);
-       struct nouveau_mc *pmc = (void *)object;
-       free_irq(pmc->irq, pmc);
-       if (pmc->use_msi)
-               pci_disable_msi(device->pdev);
-       nouveau_subdev_destroy(&pmc->base);
-}
-
-int
-nouveau_mc_create_(struct nouveau_object *parent, struct nouveau_object *engine,
-                  struct nouveau_oclass *bclass, int length, void **pobject)
-{
-       const struct nouveau_mc_oclass *oclass = (void *)bclass;
-       struct nouveau_device *device = nv_device(parent);
-       struct nouveau_mc *pmc;
-       int ret;
-
-       ret = nouveau_subdev_create_(parent, engine, bclass, 0, "PMC",
-                                    "master", length, pobject);
-       pmc = *pobject;
-       if (ret)
-               return ret;
-
-       pmc->unk260 = nouveau_mc_unk260;
-
-       if (nv_device_is_pci(device))
-               switch (device->pdev->device & 0x0ff0) {
-               case 0x00f0:
-               case 0x02e0:
-                       /* BR02? NFI how these would be handled yet exactly */
-                       break;
-               default:
-                       switch (device->chipset) {
-                       case 0xaa:
-                               /* reported broken, nv also disable it */
-                               break;
-                       default:
-                               pmc->use_msi = true;
-                               break;
-               }
-
-               pmc->use_msi = nouveau_boolopt(device->cfgopt, "NvMSI",
-                                              pmc->use_msi);
-
-               if (pmc->use_msi && oclass->msi_rearm) {
-                       pmc->use_msi = pci_enable_msi(device->pdev) == 0;
-                       if (pmc->use_msi) {
-                               nv_info(pmc, "MSI interrupts enabled\n");
-                               oclass->msi_rearm(pmc);
-                       }
-               } else {
-                       pmc->use_msi = false;
-               }
-       }
-
-       ret = nv_device_get_irq(device, true);
-       if (ret < 0)
-               return ret;
-       pmc->irq = ret;
-
-       ret = request_irq(pmc->irq, nouveau_mc_intr, IRQF_SHARED, "nouveau",
-                         pmc);
-
-       if (ret < 0)
-               return ret;
-
-       return 0;
-}
diff --git a/drivers/gpu/drm/nouveau/core/subdev/mc/gk20a.c b/drivers/gpu/drm/nouveau/core/subdev/mc/gk20a.c
deleted file mode 100644 (file)
index b8d6cb4..0000000
+++ /dev/null
@@ -1,38 +0,0 @@
-/*
- * Copyright 2012 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 "nv04.h"
-
-struct nouveau_oclass *
-gk20a_mc_oclass = &(struct nouveau_mc_oclass) {
-       .base.handle = NV_SUBDEV(MC, 0xea),
-       .base.ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nv04_mc_ctor,
-               .dtor = _nouveau_mc_dtor,
-               .init = nv50_mc_init,
-               .fini = _nouveau_mc_fini,
-       },
-       .intr = nvc0_mc_intr,
-       .msi_rearm = nv40_mc_msi_rearm,
-}.base;
diff --git a/drivers/gpu/drm/nouveau/core/subdev/mc/nv04.c b/drivers/gpu/drm/nouveau/core/subdev/mc/nv04.c
deleted file mode 100644 (file)
index 2d787e4..0000000
+++ /dev/null
@@ -1,79 +0,0 @@
-/*
- * Copyright 2012 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 "nv04.h"
-
-const struct nouveau_mc_intr
-nv04_mc_intr[] = {
-       { 0x00000001, NVDEV_ENGINE_MPEG },      /* NV17- MPEG/ME */
-       { 0x00000100, NVDEV_ENGINE_FIFO },
-       { 0x00001000, NVDEV_ENGINE_GR },
-       { 0x00010000, NVDEV_ENGINE_DISP },
-       { 0x00020000, NVDEV_ENGINE_VP },        /* NV40- */
-       { 0x00100000, NVDEV_SUBDEV_TIMER },
-       { 0x01000000, NVDEV_ENGINE_DISP },      /* NV04- PCRTC0 */
-       { 0x02000000, NVDEV_ENGINE_DISP },      /* NV11- PCRTC1 */
-       { 0x10000000, NVDEV_SUBDEV_BUS },
-       { 0x80000000, NVDEV_ENGINE_SW },
-       {}
-};
-
-int
-nv04_mc_init(struct nouveau_object *object)
-{
-       struct nv04_mc_priv *priv = (void *)object;
-
-       nv_wr32(priv, 0x000200, 0xffffffff); /* everything enabled */
-       nv_wr32(priv, 0x001850, 0x00000001); /* disable rom access */
-
-       return nouveau_mc_init(&priv->base);
-}
-
-int
-nv04_mc_ctor(struct nouveau_object *parent, struct nouveau_object *engine,
-            struct nouveau_oclass *oclass, void *data, u32 size,
-            struct nouveau_object **pobject)
-{
-       struct nv04_mc_priv *priv;
-       int ret;
-
-       ret = nouveau_mc_create(parent, engine, oclass, &priv);
-       *pobject = nv_object(priv);
-       if (ret)
-               return ret;
-
-       return 0;
-}
-
-struct nouveau_oclass *
-nv04_mc_oclass = &(struct nouveau_mc_oclass) {
-       .base.handle = NV_SUBDEV(MC, 0x04),
-       .base.ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nv04_mc_ctor,
-               .dtor = _nouveau_mc_dtor,
-               .init = nv04_mc_init,
-               .fini = _nouveau_mc_fini,
-       },
-       .intr = nv04_mc_intr,
-}.base;
diff --git a/drivers/gpu/drm/nouveau/core/subdev/mc/nv04.h b/drivers/gpu/drm/nouveau/core/subdev/mc/nv04.h
deleted file mode 100644 (file)
index 4d9ea46..0000000
+++ /dev/null
@@ -1,22 +0,0 @@
-#ifndef __NVKM_MC_NV04_H__
-#define __NVKM_MC_NV04_H__
-
-#include "priv.h"
-
-struct nv04_mc_priv {
-       struct nouveau_mc base;
-};
-
-int  nv04_mc_ctor(struct nouveau_object *, struct nouveau_object *,
-                 struct nouveau_oclass *, void *, u32,
-                 struct nouveau_object **);
-
-extern const struct nouveau_mc_intr nv04_mc_intr[];
-int  nv04_mc_init(struct nouveau_object *);
-void nv40_mc_msi_rearm(struct nouveau_mc *);
-int  nv44_mc_init(struct nouveau_object *object);
-int  nv50_mc_init(struct nouveau_object *);
-extern const struct nouveau_mc_intr nv50_mc_intr[];
-extern const struct nouveau_mc_intr nvc0_mc_intr[];
-
-#endif
diff --git a/drivers/gpu/drm/nouveau/core/subdev/mc/nv40.c b/drivers/gpu/drm/nouveau/core/subdev/mc/nv40.c
deleted file mode 100644 (file)
index 5b1faec..0000000
+++ /dev/null
@@ -1,45 +0,0 @@
-/*
- * Copyright 2012 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 "nv04.h"
-
-void
-nv40_mc_msi_rearm(struct nouveau_mc *pmc)
-{
-       struct nv04_mc_priv *priv = (void *)pmc;
-       nv_wr08(priv, 0x088068, 0xff);
-}
-
-struct nouveau_oclass *
-nv40_mc_oclass = &(struct nouveau_mc_oclass) {
-       .base.handle = NV_SUBDEV(MC, 0x40),
-       .base.ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nv04_mc_ctor,
-               .dtor = _nouveau_mc_dtor,
-               .init = nv04_mc_init,
-               .fini = _nouveau_mc_fini,
-       },
-       .intr = nv04_mc_intr,
-       .msi_rearm = nv40_mc_msi_rearm,
-}.base;
diff --git a/drivers/gpu/drm/nouveau/core/subdev/mc/nv44.c b/drivers/gpu/drm/nouveau/core/subdev/mc/nv44.c
deleted file mode 100644 (file)
index cc4d0d2..0000000
+++ /dev/null
@@ -1,54 +0,0 @@
-/*
- * Copyright 2012 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 "nv04.h"
-
-int
-nv44_mc_init(struct nouveau_object *object)
-{
-       struct nv04_mc_priv *priv = (void *)object;
-       u32 tmp = nv_rd32(priv, 0x10020c);
-
-       nv_wr32(priv, 0x000200, 0xffffffff); /* everything enabled */
-
-       nv_wr32(priv, 0x001700, tmp);
-       nv_wr32(priv, 0x001704, 0);
-       nv_wr32(priv, 0x001708, 0);
-       nv_wr32(priv, 0x00170c, tmp);
-
-       return nouveau_mc_init(&priv->base);
-}
-
-struct nouveau_oclass *
-nv44_mc_oclass = &(struct nouveau_mc_oclass) {
-       .base.handle = NV_SUBDEV(MC, 0x44),
-       .base.ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nv04_mc_ctor,
-               .dtor = _nouveau_mc_dtor,
-               .init = nv44_mc_init,
-               .fini = _nouveau_mc_fini,
-       },
-       .intr = nv04_mc_intr,
-       .msi_rearm = nv40_mc_msi_rearm,
-}.base;
diff --git a/drivers/gpu/drm/nouveau/core/subdev/mc/nv4c.c b/drivers/gpu/drm/nouveau/core/subdev/mc/nv4c.c
deleted file mode 100644 (file)
index 165401c..0000000
+++ /dev/null
@@ -1,37 +0,0 @@
-/*
- * Copyright 2014 Ilia Mirkin
- *
- * 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: Ilia Mirkin
- */
-
-#include "nv04.h"
-
-struct nouveau_oclass *
-nv4c_mc_oclass = &(struct nouveau_mc_oclass) {
-       .base.handle = NV_SUBDEV(MC, 0x4c),
-       .base.ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nv04_mc_ctor,
-               .dtor = _nouveau_mc_dtor,
-               .init = nv44_mc_init,
-               .fini = _nouveau_mc_fini,
-       },
-       .intr = nv04_mc_intr,
-}.base;
diff --git a/drivers/gpu/drm/nouveau/core/subdev/mc/nv50.c b/drivers/gpu/drm/nouveau/core/subdev/mc/nv50.c
deleted file mode 100644 (file)
index 9ca93e2..0000000
+++ /dev/null
@@ -1,71 +0,0 @@
-/*
- * Copyright 2012 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 "nv04.h"
-
-const struct nouveau_mc_intr
-nv50_mc_intr[] = {
-       { 0x04000000, NVDEV_ENGINE_DISP },  /* DISP before FIFO, so pageflip-timestamping works! */
-       { 0x00000001, NVDEV_ENGINE_MPEG },
-       { 0x00000100, NVDEV_ENGINE_FIFO },
-       { 0x00001000, NVDEV_ENGINE_GR },
-       { 0x00004000, NVDEV_ENGINE_CRYPT },     /* NV84- */
-       { 0x00008000, NVDEV_ENGINE_BSP },       /* NV84- */
-       { 0x00020000, NVDEV_ENGINE_VP },        /* NV84- */
-       { 0x00100000, NVDEV_SUBDEV_TIMER },
-       { 0x00200000, NVDEV_SUBDEV_GPIO },      /* PMGR->GPIO */
-       { 0x00200000, NVDEV_SUBDEV_I2C },       /* PMGR->I2C/AUX */
-       { 0x10000000, NVDEV_SUBDEV_BUS },
-       { 0x80000000, NVDEV_ENGINE_SW },
-       { 0x0002d101, NVDEV_SUBDEV_FB },
-       {},
-};
-
-static void
-nv50_mc_msi_rearm(struct nouveau_mc *pmc)
-{
-       struct nouveau_device *device = nv_device(pmc);
-       pci_write_config_byte(device->pdev, 0x68, 0xff);
-}
-
-int
-nv50_mc_init(struct nouveau_object *object)
-{
-       struct nv04_mc_priv *priv = (void *)object;
-       nv_wr32(priv, 0x000200, 0xffffffff); /* everything on */
-       return nouveau_mc_init(&priv->base);
-}
-
-struct nouveau_oclass *
-nv50_mc_oclass = &(struct nouveau_mc_oclass) {
-       .base.handle = NV_SUBDEV(MC, 0x50),
-       .base.ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nv04_mc_ctor,
-               .dtor = _nouveau_mc_dtor,
-               .init = nv50_mc_init,
-               .fini = _nouveau_mc_fini,
-       },
-       .intr = nv50_mc_intr,
-       .msi_rearm = nv50_mc_msi_rearm,
-}.base;
diff --git a/drivers/gpu/drm/nouveau/core/subdev/mc/nv94.c b/drivers/gpu/drm/nouveau/core/subdev/mc/nv94.c
deleted file mode 100644 (file)
index 5f45411..0000000
+++ /dev/null
@@ -1,38 +0,0 @@
-/*
- * Copyright 2012 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 "nv04.h"
-
-struct nouveau_oclass *
-nv94_mc_oclass = &(struct nouveau_mc_oclass) {
-       .base.handle = NV_SUBDEV(MC, 0x94),
-       .base.ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nv04_mc_ctor,
-               .dtor = _nouveau_mc_dtor,
-               .init = nv50_mc_init,
-               .fini = _nouveau_mc_fini,
-       },
-       .intr = nv50_mc_intr,
-       .msi_rearm = nv40_mc_msi_rearm,
-}.base;
diff --git a/drivers/gpu/drm/nouveau/core/subdev/mc/nv98.c b/drivers/gpu/drm/nouveau/core/subdev/mc/nv98.c
deleted file mode 100644 (file)
index 3c76d90..0000000
+++ /dev/null
@@ -1,59 +0,0 @@
-/*
- * Copyright 2012 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 "nv04.h"
-
-static const struct nouveau_mc_intr
-nv98_mc_intr[] = {
-       { 0x04000000, NVDEV_ENGINE_DISP },  /* DISP first, so pageflip timestamps work */
-       { 0x00000001, NVDEV_ENGINE_PPP },
-       { 0x00000100, NVDEV_ENGINE_FIFO },
-       { 0x00001000, NVDEV_ENGINE_GR },
-       { 0x00004000, NVDEV_ENGINE_CRYPT },     /* NV84:NVA3 */
-       { 0x00008000, NVDEV_ENGINE_BSP },
-       { 0x00020000, NVDEV_ENGINE_VP },
-       { 0x00040000, NVDEV_SUBDEV_PWR },       /* NVA3:NVC0 */
-       { 0x00080000, NVDEV_SUBDEV_THERM },     /* NVA3:NVC0 */
-       { 0x00100000, NVDEV_SUBDEV_TIMER },
-       { 0x00200000, NVDEV_SUBDEV_GPIO },      /* PMGR->GPIO */
-       { 0x00200000, NVDEV_SUBDEV_I2C },       /* PMGR->I2C/AUX */
-       { 0x00400000, NVDEV_ENGINE_COPY0 },     /* NVA3-     */
-       { 0x10000000, NVDEV_SUBDEV_BUS },
-       { 0x80000000, NVDEV_ENGINE_SW },
-       { 0x0042d101, NVDEV_SUBDEV_FB },
-       {},
-};
-
-struct nouveau_oclass *
-nv98_mc_oclass = &(struct nouveau_mc_oclass) {
-       .base.handle = NV_SUBDEV(MC, 0x98),
-       .base.ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nv04_mc_ctor,
-               .dtor = _nouveau_mc_dtor,
-               .init = nv50_mc_init,
-               .fini = _nouveau_mc_fini,
-       },
-       .intr = nv98_mc_intr,
-       .msi_rearm = nv40_mc_msi_rearm,
-}.base;
diff --git a/drivers/gpu/drm/nouveau/core/subdev/mc/nvc0.c b/drivers/gpu/drm/nouveau/core/subdev/mc/nvc0.c
deleted file mode 100644 (file)
index 15d41dc..0000000
+++ /dev/null
@@ -1,77 +0,0 @@
-/*
- * Copyright 2012 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 "nv04.h"
-
-const struct nouveau_mc_intr
-nvc0_mc_intr[] = {
-       { 0x04000000, NVDEV_ENGINE_DISP },  /* DISP first, so pageflip timestamps work. */
-       { 0x00000001, NVDEV_ENGINE_PPP },
-       { 0x00000020, NVDEV_ENGINE_COPY0 },
-       { 0x00000040, NVDEV_ENGINE_COPY1 },
-       { 0x00000080, NVDEV_ENGINE_COPY2 },
-       { 0x00000100, NVDEV_ENGINE_FIFO },
-       { 0x00001000, NVDEV_ENGINE_GR },
-       { 0x00002000, NVDEV_SUBDEV_FB },
-       { 0x00008000, NVDEV_ENGINE_BSP },
-       { 0x00040000, NVDEV_SUBDEV_THERM },
-       { 0x00020000, NVDEV_ENGINE_VP },
-       { 0x00100000, NVDEV_SUBDEV_TIMER },
-       { 0x00200000, NVDEV_SUBDEV_GPIO },      /* PMGR->GPIO */
-       { 0x00200000, NVDEV_SUBDEV_I2C },       /* PMGR->I2C/AUX */
-       { 0x01000000, NVDEV_SUBDEV_PWR },
-       { 0x02000000, NVDEV_SUBDEV_LTC },
-       { 0x08000000, NVDEV_SUBDEV_FB },
-       { 0x10000000, NVDEV_SUBDEV_BUS },
-       { 0x40000000, NVDEV_SUBDEV_IBUS },
-       { 0x80000000, NVDEV_ENGINE_SW },
-       {},
-};
-
-static void
-nvc0_mc_msi_rearm(struct nouveau_mc *pmc)
-{
-       struct nv04_mc_priv *priv = (void *)pmc;
-       nv_wr32(priv, 0x088704, 0x00000000);
-}
-
-void
-nvc0_mc_unk260(struct nouveau_mc *pmc, u32 data)
-{
-       nv_wr32(pmc, 0x000260, data);
-}
-
-struct nouveau_oclass *
-nvc0_mc_oclass = &(struct nouveau_mc_oclass) {
-       .base.handle = NV_SUBDEV(MC, 0xc0),
-       .base.ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nv04_mc_ctor,
-               .dtor = _nouveau_mc_dtor,
-               .init = nv50_mc_init,
-               .fini = _nouveau_mc_fini,
-       },
-       .intr = nvc0_mc_intr,
-       .msi_rearm = nvc0_mc_msi_rearm,
-       .unk260 = nvc0_mc_unk260,
-}.base;
diff --git a/drivers/gpu/drm/nouveau/core/subdev/mc/nvc3.c b/drivers/gpu/drm/nouveau/core/subdev/mc/nvc3.c
deleted file mode 100644 (file)
index 68b5f61..0000000
+++ /dev/null
@@ -1,39 +0,0 @@
-/*
- * Copyright 2012 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 "nv04.h"
-
-struct nouveau_oclass *
-nvc3_mc_oclass = &(struct nouveau_mc_oclass) {
-       .base.handle = NV_SUBDEV(MC, 0xc3),
-       .base.ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nv04_mc_ctor,
-               .dtor = _nouveau_mc_dtor,
-               .init = nv50_mc_init,
-               .fini = _nouveau_mc_fini,
-       },
-       .intr = nvc0_mc_intr,
-       .msi_rearm = nv40_mc_msi_rearm,
-       .unk260 = nvc0_mc_unk260,
-}.base;
diff --git a/drivers/gpu/drm/nouveau/core/subdev/mc/priv.h b/drivers/gpu/drm/nouveau/core/subdev/mc/priv.h
deleted file mode 100644 (file)
index 911e663..0000000
+++ /dev/null
@@ -1,38 +0,0 @@
-#ifndef __NVKM_MC_PRIV_H__
-#define __NVKM_MC_PRIV_H__
-
-#include <subdev/mc.h>
-
-#define nouveau_mc_create(p,e,o,d)                                             \
-       nouveau_mc_create_((p), (e), (o), sizeof(**d), (void **)d)
-#define nouveau_mc_destroy(p) ({                                               \
-       struct nouveau_mc *pmc = (p); _nouveau_mc_dtor(nv_object(pmc));        \
-})
-#define nouveau_mc_init(p) ({                                                  \
-       struct nouveau_mc *pmc = (p); _nouveau_mc_init(nv_object(pmc));        \
-})
-#define nouveau_mc_fini(p,s) ({                                                \
-       struct nouveau_mc *pmc = (p); _nouveau_mc_fini(nv_object(pmc), (s));   \
-})
-
-int  nouveau_mc_create_(struct nouveau_object *, struct nouveau_object *,
-                       struct nouveau_oclass *, int, void **);
-void _nouveau_mc_dtor(struct nouveau_object *);
-int  _nouveau_mc_init(struct nouveau_object *);
-int  _nouveau_mc_fini(struct nouveau_object *, bool);
-
-struct nouveau_mc_intr {
-       u32 stat;
-       u32 unit;
-};
-
-struct nouveau_mc_oclass {
-       struct nouveau_oclass base;
-       const struct nouveau_mc_intr *intr;
-       void (*msi_rearm)(struct nouveau_mc *);
-       void (*unk260)(struct nouveau_mc *, u32);
-};
-
-void nvc0_mc_unk260(struct nouveau_mc *, u32);
-
-#endif
diff --git a/drivers/gpu/drm/nouveau/core/subdev/mxm/base.c b/drivers/gpu/drm/nouveau/core/subdev/mxm/base.c
deleted file mode 100644 (file)
index 51fcf79..0000000
+++ /dev/null
@@ -1,274 +0,0 @@
-/*
- * 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 <core/option.h>
-
-#include <subdev/i2c.h>
-#include <subdev/mxm.h>
-#include <subdev/bios.h>
-#include <subdev/bios/mxm.h>
-
-#include "mxms.h"
-
-static bool
-mxm_shadow_rom_fetch(struct nouveau_i2c_port *i2c, u8 addr,
-                    u8 offset, u8 size, u8 *data)
-{
-       struct i2c_msg msgs[] = {
-               { .addr = addr, .flags = 0, .len = 1, .buf = &offset },
-               { .addr = addr, .flags = I2C_M_RD, .len = size, .buf = data, },
-       };
-
-       return i2c_transfer(&i2c->adapter, msgs, 2) == 2;
-}
-
-static bool
-mxm_shadow_rom(struct nouveau_mxm *mxm, u8 version)
-{
-       struct nouveau_bios *bios = nouveau_bios(mxm);
-       struct nouveau_i2c *i2c = nouveau_i2c(mxm);
-       struct nouveau_i2c_port *port = NULL;
-       u8 i2cidx, mxms[6], addr, size;
-
-       i2cidx = mxm_ddc_map(bios, 1 /* LVDS_DDC */) & 0x0f;
-       if (i2cidx < 0x0f)
-               port = i2c->find(i2c, i2cidx);
-       if (!port)
-               return false;
-
-       addr = 0x54;
-       if (!mxm_shadow_rom_fetch(port, addr, 0, 6, mxms)) {
-               addr = 0x56;
-               if (!mxm_shadow_rom_fetch(port, addr, 0, 6, mxms))
-                       return false;
-       }
-
-       mxm->mxms = mxms;
-       size = mxms_headerlen(mxm) + mxms_structlen(mxm);
-       mxm->mxms = kmalloc(size, GFP_KERNEL);
-
-       if (mxm->mxms &&
-           mxm_shadow_rom_fetch(port, addr, 0, size, mxm->mxms))
-               return true;
-
-       kfree(mxm->mxms);
-       mxm->mxms = NULL;
-       return false;
-}
-
-#if defined(CONFIG_ACPI)
-static bool
-mxm_shadow_dsm(struct nouveau_mxm *mxm, u8 version)
-{
-       struct nouveau_device *device = nv_device(mxm);
-       static char muid[] = {
-               0x00, 0xA4, 0x04, 0x40, 0x7D, 0x91, 0xF2, 0x4C,
-               0xB8, 0x9C, 0x79, 0xB6, 0x2F, 0xD5, 0x56, 0x65
-       };
-       u32 mxms_args[] = { 0x00000000 };
-       union acpi_object argv4 = {
-               .buffer.type = ACPI_TYPE_BUFFER,
-               .buffer.length = sizeof(mxms_args),
-               .buffer.pointer = (char *)mxms_args,
-       };
-       union acpi_object *obj;
-       acpi_handle handle;
-       int rev;
-
-       handle = ACPI_HANDLE(nv_device_base(device));
-       if (!handle)
-               return false;
-
-       /*
-        * spec says this can be zero to mean "highest revision", but
-        * of course there's at least one bios out there which fails
-        * unless you pass in exactly the version it supports..
-        */
-       rev = (version & 0xf0) << 4 | (version & 0x0f);
-       obj = acpi_evaluate_dsm(handle, muid, rev, 0x00000010, &argv4);
-       if (!obj) {
-               nv_debug(mxm, "DSM MXMS failed\n");
-               return false;
-       }
-
-       if (obj->type == ACPI_TYPE_BUFFER) {
-               mxm->mxms = kmemdup(obj->buffer.pointer,
-                                        obj->buffer.length, GFP_KERNEL);
-       } else if (obj->type == ACPI_TYPE_INTEGER) {
-               nv_debug(mxm, "DSM MXMS returned 0x%llx\n", obj->integer.value);
-       }
-
-       ACPI_FREE(obj);
-       return mxm->mxms != NULL;
-}
-#endif
-
-#if defined(CONFIG_ACPI_WMI) || defined(CONFIG_ACPI_WMI_MODULE)
-
-#define WMI_WMMX_GUID "F6CB5C3C-9CAE-4EBD-B577-931EA32A2CC0"
-
-static u8
-wmi_wmmx_mxmi(struct nouveau_mxm *mxm, u8 version)
-{
-       u32 mxmi_args[] = { 0x494D584D /* MXMI */, version, 0 };
-       struct acpi_buffer args = { sizeof(mxmi_args), mxmi_args };
-       struct acpi_buffer retn = { ACPI_ALLOCATE_BUFFER, NULL };
-       union acpi_object *obj;
-       acpi_status status;
-
-       status = wmi_evaluate_method(WMI_WMMX_GUID, 0, 0, &args, &retn);
-       if (ACPI_FAILURE(status)) {
-               nv_debug(mxm, "WMMX MXMI returned %d\n", status);
-               return 0x00;
-       }
-
-       obj = retn.pointer;
-       if (obj->type == ACPI_TYPE_INTEGER) {
-               version = obj->integer.value;
-               nv_debug(mxm, "WMMX MXMI version %d.%d\n",
-                            (version >> 4), version & 0x0f);
-       } else {
-               version = 0;
-               nv_debug(mxm, "WMMX MXMI returned non-integer\n");
-       }
-
-       kfree(obj);
-       return version;
-}
-
-static bool
-mxm_shadow_wmi(struct nouveau_mxm *mxm, u8 version)
-{
-       u32 mxms_args[] = { 0x534D584D /* MXMS */, version, 0 };
-       struct acpi_buffer args = { sizeof(mxms_args), mxms_args };
-       struct acpi_buffer retn = { ACPI_ALLOCATE_BUFFER, NULL };
-       union acpi_object *obj;
-       acpi_status status;
-
-       if (!wmi_has_guid(WMI_WMMX_GUID)) {
-               nv_debug(mxm, "WMMX GUID not found\n");
-               return false;
-       }
-
-       mxms_args[1] = wmi_wmmx_mxmi(mxm, 0x00);
-       if (!mxms_args[1])
-               mxms_args[1] = wmi_wmmx_mxmi(mxm, version);
-       if (!mxms_args[1])
-               return false;
-
-       status = wmi_evaluate_method(WMI_WMMX_GUID, 0, 0, &args, &retn);
-       if (ACPI_FAILURE(status)) {
-               nv_debug(mxm, "WMMX MXMS returned %d\n", status);
-               return false;
-       }
-
-       obj = retn.pointer;
-       if (obj->type == ACPI_TYPE_BUFFER) {
-               mxm->mxms = kmemdup(obj->buffer.pointer,
-                                        obj->buffer.length, GFP_KERNEL);
-       }
-
-       kfree(obj);
-       return mxm->mxms != NULL;
-}
-#endif
-
-static struct mxm_shadow_h {
-       const char *name;
-       bool (*exec)(struct nouveau_mxm *, u8 version);
-} _mxm_shadow[] = {
-       { "ROM", mxm_shadow_rom },
-#if defined(CONFIG_ACPI)
-       { "DSM", mxm_shadow_dsm },
-#endif
-#if defined(CONFIG_ACPI_WMI) || defined(CONFIG_ACPI_WMI_MODULE)
-       { "WMI", mxm_shadow_wmi },
-#endif
-       {}
-};
-
-static int
-mxm_shadow(struct nouveau_mxm *mxm, u8 version)
-{
-       struct mxm_shadow_h *shadow = _mxm_shadow;
-       do {
-               nv_debug(mxm, "checking %s\n", shadow->name);
-               if (shadow->exec(mxm, version)) {
-                       if (mxms_valid(mxm))
-                               return 0;
-                       kfree(mxm->mxms);
-                       mxm->mxms = NULL;
-               }
-       } while ((++shadow)->name);
-       return -ENOENT;
-}
-
-int
-nouveau_mxm_create_(struct nouveau_object *parent,
-                   struct nouveau_object *engine,
-                   struct nouveau_oclass *oclass, int length, void **pobject)
-{
-       struct nouveau_device *device = nv_device(parent);
-       struct nouveau_bios *bios = nouveau_bios(device);
-       struct nouveau_mxm *mxm;
-       u8  ver, len;
-       u16 data;
-       int ret;
-
-       ret = nouveau_subdev_create_(parent, engine, oclass, 0, "MXM", "mxm",
-                                    length, pobject);
-       mxm = *pobject;
-       if (ret)
-               return ret;
-
-       data = mxm_table(bios, &ver, &len);
-       if (!data || !(ver = nv_ro08(bios, data))) {
-               nv_debug(mxm, "no VBIOS data, nothing to do\n");
-               return 0;
-       }
-
-       nv_info(mxm, "BIOS version %d.%d\n", ver >> 4, ver & 0x0f);
-
-       if (mxm_shadow(mxm, ver)) {
-               nv_info(mxm, "failed to locate valid SIS\n");
-#if 0
-               /* we should, perhaps, fall back to some kind of limited
-                * mode here if the x86 vbios hasn't already done the
-                * work for us (so we prevent loading with completely
-                * whacked vbios tables).
-                */
-               return -EINVAL;
-#else
-               return 0;
-#endif
-       }
-
-       nv_info(mxm, "MXMS Version %d.%d\n",
-               mxms_version(mxm) >> 8, mxms_version(mxm) & 0xff);
-       mxms_foreach(mxm, 0, NULL, NULL);
-
-       if (nouveau_boolopt(device->cfgopt, "NvMXMDCB", true))
-               mxm->action |= MXM_SANITISE_DCB;
-       return 0;
-}
diff --git a/drivers/gpu/drm/nouveau/core/subdev/mxm/mxms.c b/drivers/gpu/drm/nouveau/core/subdev/mxm/mxms.c
deleted file mode 100644 (file)
index 4bde7f7..0000000
+++ /dev/null
@@ -1,193 +0,0 @@
-/*
- * Copyright 2012 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 <subdev/mxm.h>
-#include "mxms.h"
-
-#define ROM16(x) le16_to_cpu(*(u16 *)&(x))
-#define ROM32(x) le32_to_cpu(*(u32 *)&(x))
-
-static u8 *
-mxms_data(struct nouveau_mxm *mxm)
-{
-       return mxm->mxms;
-
-}
-
-u16
-mxms_version(struct nouveau_mxm *mxm)
-{
-       u8 *mxms = mxms_data(mxm);
-       u16 version = (mxms[4] << 8) | mxms[5];
-       switch (version ) {
-       case 0x0200:
-       case 0x0201:
-       case 0x0300:
-               return version;
-       default:
-               break;
-       }
-
-       nv_debug(mxm, "unknown version %d.%d\n", mxms[4], mxms[5]);
-       return 0x0000;
-}
-
-u16
-mxms_headerlen(struct nouveau_mxm *mxm)
-{
-       return 8;
-}
-
-u16
-mxms_structlen(struct nouveau_mxm *mxm)
-{
-       return *(u16 *)&mxms_data(mxm)[6];
-}
-
-bool
-mxms_checksum(struct nouveau_mxm *mxm)
-{
-       u16 size = mxms_headerlen(mxm) + mxms_structlen(mxm);
-       u8 *mxms = mxms_data(mxm), sum = 0;
-       while (size--)
-               sum += *mxms++;
-       if (sum) {
-               nv_debug(mxm, "checksum invalid\n");
-               return false;
-       }
-       return true;
-}
-
-bool
-mxms_valid(struct nouveau_mxm *mxm)
-{
-       u8 *mxms = mxms_data(mxm);
-       if (*(u32 *)mxms != 0x5f4d584d) {
-               nv_debug(mxm, "signature invalid\n");
-               return false;
-       }
-
-       if (!mxms_version(mxm) || !mxms_checksum(mxm))
-               return false;
-
-       return true;
-}
-
-bool
-mxms_foreach(struct nouveau_mxm *mxm, u8 types,
-            bool (*exec)(struct nouveau_mxm *, u8 *, void *), void *info)
-{
-       u8 *mxms = mxms_data(mxm);
-       u8 *desc = mxms + mxms_headerlen(mxm);
-       u8 *fini = desc + mxms_structlen(mxm) - 1;
-       while (desc < fini) {
-               u8 type = desc[0] & 0x0f;
-               u8 headerlen = 0;
-               u8 recordlen = 0;
-               u8 entries = 0;
-
-               switch (type) {
-               case 0: /* Output Device Structure */
-                       if (mxms_version(mxm) >= 0x0300)
-                               headerlen = 8;
-                       else
-                               headerlen = 6;
-                       break;
-               case 1: /* System Cooling Capability Structure */
-               case 2: /* Thermal Structure */
-               case 3: /* Input Power Structure */
-                       headerlen = 4;
-                       break;
-               case 4: /* GPIO Device Structure */
-                       headerlen = 4;
-                       recordlen = 2;
-                       entries   = (ROM32(desc[0]) & 0x01f00000) >> 20;
-                       break;
-               case 5: /* Vendor Specific Structure */
-                       headerlen = 8;
-                       break;
-               case 6: /* Backlight Control Structure */
-                       if (mxms_version(mxm) >= 0x0300) {
-                               headerlen = 4;
-                               recordlen = 8;
-                               entries   = (desc[1] & 0xf0) >> 4;
-                       } else {
-                               headerlen = 8;
-                       }
-                       break;
-               case 7: /* Fan Control Structure */
-                       headerlen = 8;
-                       recordlen = 4;
-                       entries   = desc[1] & 0x07;
-                       break;
-               default:
-                       nv_debug(mxm, "unknown descriptor type %d\n", type);
-                       return false;
-               }
-
-               if (nv_subdev(mxm)->debug >= NV_DBG_DEBUG && (exec == NULL)) {
-                       static const char * mxms_desc_name[] = {
-                               "ODS", "SCCS", "TS", "IPS",
-                               "GSD", "VSS", "BCS", "FCS",
-                       };
-                       u8 *dump = desc;
-                       int i, j;
-
-                       nv_debug(mxm, "%4s: ", mxms_desc_name[type]);
-                       for (j = headerlen - 1; j >= 0; j--)
-                               pr_cont("%02x", dump[j]);
-                       pr_cont("\n");
-                       dump += headerlen;
-
-                       for (i = 0; i < entries; i++, dump += recordlen) {
-                               nv_debug(mxm, "      ");
-                               for (j = recordlen - 1; j >= 0; j--)
-                                       pr_cont("%02x", dump[j]);
-                               pr_cont("\n");
-                       }
-               }
-
-               if (types & (1 << type)) {
-                       if (!exec(mxm, desc, info))
-                               return false;
-               }
-
-               desc += headerlen + (entries * recordlen);
-       }
-
-       return true;
-}
-
-void
-mxms_output_device(struct nouveau_mxm *mxm, u8 *pdata, struct mxms_odev *desc)
-{
-       u64 data = ROM32(pdata[0]);
-       if (mxms_version(mxm) >= 0x0300)
-               data |= (u64)ROM16(pdata[4]) << 32;
-
-       desc->outp_type = (data & 0x00000000000000f0ULL) >> 4;
-       desc->ddc_port  = (data & 0x0000000000000f00ULL) >> 8;
-       desc->conn_type = (data & 0x000000000001f000ULL) >> 12;
-       desc->dig_conn  = (data & 0x0000000000780000ULL) >> 19;
-}
diff --git a/drivers/gpu/drm/nouveau/core/subdev/mxm/mxms.h b/drivers/gpu/drm/nouveau/core/subdev/mxm/mxms.h
deleted file mode 100644 (file)
index 5e0be0c..0000000
+++ /dev/null
@@ -1,22 +0,0 @@
-#ifndef __NVMXM_MXMS_H__
-#define __NVMXM_MXMS_H__
-
-struct mxms_odev {
-       u8 outp_type;
-       u8 conn_type;
-       u8 ddc_port;
-       u8 dig_conn;
-};
-
-void mxms_output_device(struct nouveau_mxm *, u8 *, struct mxms_odev *);
-
-u16  mxms_version(struct nouveau_mxm *);
-u16  mxms_headerlen(struct nouveau_mxm *);
-u16  mxms_structlen(struct nouveau_mxm *);
-bool mxms_checksum(struct nouveau_mxm *);
-bool mxms_valid(struct nouveau_mxm *);
-
-bool mxms_foreach(struct nouveau_mxm *, u8,
-                 bool (*)(struct nouveau_mxm *, u8 *, void *), void *);
-
-#endif
diff --git a/drivers/gpu/drm/nouveau/core/subdev/mxm/nv50.c b/drivers/gpu/drm/nouveau/core/subdev/mxm/nv50.c
deleted file mode 100644 (file)
index fcaabe8..0000000
+++ /dev/null
@@ -1,233 +0,0 @@
-/*
- * 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 <subdev/mxm.h>
-#include <subdev/bios.h>
-#include <subdev/bios/conn.h>
-#include <subdev/bios/dcb.h>
-#include <subdev/bios/mxm.h>
-
-#include "mxms.h"
-
-struct nv50_mxm_priv {
-       struct nouveau_mxm base;
-};
-
-struct context {
-       u32 *outp;
-       struct mxms_odev desc;
-};
-
-static bool
-mxm_match_tmds_partner(struct nouveau_mxm *mxm, u8 *data, void *info)
-{
-       struct context *ctx = info;
-       struct mxms_odev desc;
-
-       mxms_output_device(mxm, data, &desc);
-       if (desc.outp_type == 2 &&
-           desc.dig_conn == ctx->desc.dig_conn)
-               return false;
-       return true;
-}
-
-static bool
-mxm_match_dcb(struct nouveau_mxm *mxm, u8 *data, void *info)
-{
-       struct nouveau_bios *bios = nouveau_bios(mxm);
-       struct context *ctx = info;
-       u64 desc = *(u64 *)data;
-
-       mxms_output_device(mxm, data, &ctx->desc);
-
-       /* match dcb encoder type to mxm-ods device type */
-       if ((ctx->outp[0] & 0x0000000f) != ctx->desc.outp_type)
-               return true;
-
-       /* digital output, have some extra stuff to match here, there's a
-        * table in the vbios that provides a mapping from the mxm digital
-        * connection enum values to SOR/link
-        */
-       if ((desc & 0x00000000000000f0) >= 0x20) {
-               /* check against sor index */
-               u8 link = mxm_sor_map(bios, ctx->desc.dig_conn);
-               if ((ctx->outp[0] & 0x0f000000) != (link & 0x0f) << 24)
-                       return true;
-
-               /* check dcb entry has a compatible link field */
-               link = (link & 0x30) >> 4;
-               if ((link & ((ctx->outp[1] & 0x00000030) >> 4)) != link)
-                       return true;
-       }
-
-       /* mark this descriptor accounted for by setting invalid device type,
-        * except of course some manufactures don't follow specs properly and
-        * we need to avoid killing off the TMDS function on DP connectors
-        * if MXM-SIS is missing an entry for it.
-        */
-       data[0] &= ~0xf0;
-       if (ctx->desc.outp_type == 6 && ctx->desc.conn_type == 6 &&
-           mxms_foreach(mxm, 0x01, mxm_match_tmds_partner, ctx)) {
-               data[0] |= 0x20; /* modify descriptor to match TMDS now */
-       } else {
-               data[0] |= 0xf0;
-       }
-
-       return false;
-}
-
-static int
-mxm_dcb_sanitise_entry(struct nouveau_bios *bios, void *data, int idx, u16 pdcb)
-{
-       struct nouveau_mxm *mxm = data;
-       struct context ctx = { .outp = (u32 *)(bios->data + pdcb) };
-       u8 type, i2cidx, link, ver, len;
-       u8 *conn;
-
-       /* look for an output device structure that matches this dcb entry.
-        * if one isn't found, disable it.
-        */
-       if (mxms_foreach(mxm, 0x01, mxm_match_dcb, &ctx)) {
-               nv_debug(mxm, "disable %d: 0x%08x 0x%08x\n",
-                       idx, ctx.outp[0], ctx.outp[1]);
-               ctx.outp[0] |= 0x0000000f;
-               return 0;
-       }
-
-       /* modify the output's ddc/aux port, there's a pointer to a table
-        * with the mapping from mxm ddc/aux port to dcb i2c_index in the
-        * vbios mxm table
-        */
-       i2cidx = mxm_ddc_map(bios, ctx.desc.ddc_port);
-       if ((ctx.outp[0] & 0x0000000f) != DCB_OUTPUT_DP)
-               i2cidx = (i2cidx & 0x0f) << 4;
-       else
-               i2cidx = (i2cidx & 0xf0);
-
-       if (i2cidx != 0xf0) {
-               ctx.outp[0] &= ~0x000000f0;
-               ctx.outp[0] |= i2cidx;
-       }
-
-       /* override dcb sorconf.link, based on what mxm data says */
-       switch (ctx.desc.outp_type) {
-       case 0x00: /* Analog CRT */
-       case 0x01: /* Analog TV/HDTV */
-               break;
-       default:
-               link = mxm_sor_map(bios, ctx.desc.dig_conn) & 0x30;
-               ctx.outp[1] &= ~0x00000030;
-               ctx.outp[1] |= link;
-               break;
-       }
-
-       /* we may need to fixup various other vbios tables based on what
-        * the descriptor says the connector type should be.
-        *
-        * in a lot of cases, the vbios tables will claim DVI-I is possible,
-        * and the mxm data says the connector is really HDMI.  another
-        * common example is DP->eDP.
-        */
-       conn  = bios->data;
-       conn += nvbios_connEe(bios, (ctx.outp[0] & 0x0000f000) >> 12, &ver, &len);
-       type  = conn[0];
-       switch (ctx.desc.conn_type) {
-       case 0x01: /* LVDS */
-               ctx.outp[1] |= 0x00000004; /* use_power_scripts */
-               /* XXX: modify default link width in LVDS table */
-               break;
-       case 0x02: /* HDMI */
-               type = DCB_CONNECTOR_HDMI_1;
-               break;
-       case 0x03: /* DVI-D */
-               type = DCB_CONNECTOR_DVI_D;
-               break;
-       case 0x0e: /* eDP, falls through to DPint */
-               ctx.outp[1] |= 0x00010000;
-       case 0x07: /* DP internal, wtf is this?? HP8670w */
-               ctx.outp[1] |= 0x00000004; /* use_power_scripts? */
-               type = DCB_CONNECTOR_eDP;
-               break;
-       default:
-               break;
-       }
-
-       if (mxms_version(mxm) >= 0x0300)
-               conn[0] = type;
-
-       return 0;
-}
-
-static bool
-mxm_show_unmatched(struct nouveau_mxm *mxm, u8 *data, void *info)
-{
-       u64 desc = *(u64 *)data;
-       if ((desc & 0xf0) != 0xf0)
-       nv_info(mxm, "unmatched output device 0x%016llx\n", desc);
-       return true;
-}
-
-static void
-mxm_dcb_sanitise(struct nouveau_mxm *mxm)
-{
-       struct nouveau_bios *bios = nouveau_bios(mxm);
-       u8  ver, hdr, cnt, len;
-       u16 dcb = dcb_table(bios, &ver, &hdr, &cnt, &len);
-       if (dcb == 0x0000 || ver != 0x40) {
-               nv_debug(mxm, "unsupported DCB version\n");
-               return;
-       }
-
-       dcb_outp_foreach(bios, mxm, mxm_dcb_sanitise_entry);
-       mxms_foreach(mxm, 0x01, mxm_show_unmatched, NULL);
-}
-
-static int
-nv50_mxm_ctor(struct nouveau_object *parent, struct nouveau_object *engine,
-             struct nouveau_oclass *oclass, void *data, u32 size,
-             struct nouveau_object **pobject)
-{
-       struct nv50_mxm_priv *priv;
-       int ret;
-
-       ret = nouveau_mxm_create(parent, engine, oclass, &priv);
-       *pobject = nv_object(priv);
-       if (ret)
-               return ret;
-
-       if (priv->base.action & MXM_SANITISE_DCB)
-               mxm_dcb_sanitise(&priv->base);
-       return 0;
-}
-
-struct nouveau_oclass
-nv50_mxm_oclass = {
-       .handle = NV_SUBDEV(MXM, 0x50),
-       .ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nv50_mxm_ctor,
-               .dtor = _nouveau_mxm_dtor,
-               .init = _nouveau_mxm_init,
-               .fini = _nouveau_mxm_fini,
-       },
-};
diff --git a/drivers/gpu/drm/nouveau/core/subdev/pwr/base.c b/drivers/gpu/drm/nouveau/core/subdev/pwr/base.c
deleted file mode 100644 (file)
index 0ab55f2..0000000
+++ /dev/null
@@ -1,272 +0,0 @@
-/*
- * Copyright 2013 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 <subdev/timer.h>
-
-#include "priv.h"
-
-static void
-nouveau_pwr_pgob(struct nouveau_pwr *ppwr, bool enable)
-{
-       const struct nvkm_pwr_impl *impl = (void *)nv_oclass(ppwr);
-       if (impl->pgob)
-               impl->pgob(ppwr, enable);
-}
-
-static int
-nouveau_pwr_send(struct nouveau_pwr *ppwr, u32 reply[2],
-                u32 process, u32 message, u32 data0, u32 data1)
-{
-       struct nouveau_subdev *subdev = nv_subdev(ppwr);
-       u32 addr;
-
-       /* wait for a free slot in the fifo */
-       addr  = nv_rd32(ppwr, 0x10a4a0);
-       if (!nv_wait_ne(ppwr, 0x10a4b0, 0xffffffff, addr ^ 8))
-               return -EBUSY;
-
-       /* we currently only support a single process at a time waiting
-        * on a synchronous reply, take the PPWR mutex and tell the
-        * receive handler what we're waiting for
-        */
-       if (reply) {
-               mutex_lock(&subdev->mutex);
-               ppwr->recv.message = message;
-               ppwr->recv.process = process;
-       }
-
-       /* acquire data segment access */
-       do {
-               nv_wr32(ppwr, 0x10a580, 0x00000001);
-       } while (nv_rd32(ppwr, 0x10a580) != 0x00000001);
-
-       /* write the packet */
-       nv_wr32(ppwr, 0x10a1c0, 0x01000000 | (((addr & 0x07) << 4) +
-                               ppwr->send.base));
-       nv_wr32(ppwr, 0x10a1c4, process);
-       nv_wr32(ppwr, 0x10a1c4, message);
-       nv_wr32(ppwr, 0x10a1c4, data0);
-       nv_wr32(ppwr, 0x10a1c4, data1);
-       nv_wr32(ppwr, 0x10a4a0, (addr + 1) & 0x0f);
-
-       /* release data segment access */
-       nv_wr32(ppwr, 0x10a580, 0x00000000);
-
-       /* wait for reply, if requested */
-       if (reply) {
-               wait_event(ppwr->recv.wait, (ppwr->recv.process == 0));
-               reply[0] = ppwr->recv.data[0];
-               reply[1] = ppwr->recv.data[1];
-               mutex_unlock(&subdev->mutex);
-       }
-
-       return 0;
-}
-
-static void
-nouveau_pwr_recv(struct work_struct *work)
-{
-       struct nouveau_pwr *ppwr =
-               container_of(work, struct nouveau_pwr, recv.work);
-       u32 process, message, data0, data1;
-
-       /* nothing to do if GET == PUT */
-       u32 addr =  nv_rd32(ppwr, 0x10a4cc);
-       if (addr == nv_rd32(ppwr, 0x10a4c8))
-               return;
-
-       /* acquire data segment access */
-       do {
-               nv_wr32(ppwr, 0x10a580, 0x00000002);
-       } while (nv_rd32(ppwr, 0x10a580) != 0x00000002);
-
-       /* read the packet */
-       nv_wr32(ppwr, 0x10a1c0, 0x02000000 | (((addr & 0x07) << 4) +
-                               ppwr->recv.base));
-       process = nv_rd32(ppwr, 0x10a1c4);
-       message = nv_rd32(ppwr, 0x10a1c4);
-       data0   = nv_rd32(ppwr, 0x10a1c4);
-       data1   = nv_rd32(ppwr, 0x10a1c4);
-       nv_wr32(ppwr, 0x10a4cc, (addr + 1) & 0x0f);
-
-       /* release data segment access */
-       nv_wr32(ppwr, 0x10a580, 0x00000000);
-
-       /* wake process if it's waiting on a synchronous reply */
-       if (ppwr->recv.process) {
-               if (process == ppwr->recv.process &&
-                   message == ppwr->recv.message) {
-                       ppwr->recv.data[0] = data0;
-                       ppwr->recv.data[1] = data1;
-                       ppwr->recv.process = 0;
-                       wake_up(&ppwr->recv.wait);
-                       return;
-               }
-       }
-
-       /* right now there's no other expected responses from the engine,
-        * so assume that any unexpected message is an error.
-        */
-       nv_warn(ppwr, "%c%c%c%c 0x%08x 0x%08x 0x%08x 0x%08x\n",
-               (char)((process & 0x000000ff) >>  0),
-               (char)((process & 0x0000ff00) >>  8),
-               (char)((process & 0x00ff0000) >> 16),
-               (char)((process & 0xff000000) >> 24),
-               process, message, data0, data1);
-}
-
-static void
-nouveau_pwr_intr(struct nouveau_subdev *subdev)
-{
-       struct nouveau_pwr *ppwr = (void *)subdev;
-       u32 disp = nv_rd32(ppwr, 0x10a01c);
-       u32 intr = nv_rd32(ppwr, 0x10a008) & disp & ~(disp >> 16);
-
-       if (intr & 0x00000020) {
-               u32 stat = nv_rd32(ppwr, 0x10a16c);
-               if (stat & 0x80000000) {
-                       nv_error(ppwr, "UAS fault at 0x%06x addr 0x%08x\n",
-                                stat & 0x00ffffff, nv_rd32(ppwr, 0x10a168));
-                       nv_wr32(ppwr, 0x10a16c, 0x00000000);
-                       intr &= ~0x00000020;
-               }
-       }
-
-       if (intr & 0x00000040) {
-               schedule_work(&ppwr->recv.work);
-               nv_wr32(ppwr, 0x10a004, 0x00000040);
-               intr &= ~0x00000040;
-       }
-
-       if (intr & 0x00000080) {
-               nv_info(ppwr, "wr32 0x%06x 0x%08x\n", nv_rd32(ppwr, 0x10a7a0),
-                                                     nv_rd32(ppwr, 0x10a7a4));
-               nv_wr32(ppwr, 0x10a004, 0x00000080);
-               intr &= ~0x00000080;
-       }
-
-       if (intr) {
-               nv_error(ppwr, "intr 0x%08x\n", intr);
-               nv_wr32(ppwr, 0x10a004, intr);
-       }
-}
-
-int
-_nouveau_pwr_fini(struct nouveau_object *object, bool suspend)
-{
-       struct nouveau_pwr *ppwr = (void *)object;
-
-       nv_wr32(ppwr, 0x10a014, 0x00000060);
-       flush_work(&ppwr->recv.work);
-
-       return nouveau_subdev_fini(&ppwr->base, suspend);
-}
-
-int
-_nouveau_pwr_init(struct nouveau_object *object)
-{
-       const struct nvkm_pwr_impl *impl = (void *)object->oclass;
-       struct nouveau_pwr *ppwr = (void *)object;
-       int ret, i;
-
-       ret = nouveau_subdev_init(&ppwr->base);
-       if (ret)
-               return ret;
-
-       nv_subdev(ppwr)->intr = nouveau_pwr_intr;
-       ppwr->message = nouveau_pwr_send;
-       ppwr->pgob = nouveau_pwr_pgob;
-
-       /* prevent previous ucode from running, wait for idle, reset */
-       nv_wr32(ppwr, 0x10a014, 0x0000ffff); /* INTR_EN_CLR = ALL */
-       nv_wait(ppwr, 0x10a04c, 0xffffffff, 0x00000000);
-       nv_mask(ppwr, 0x000200, 0x00002000, 0x00000000);
-       nv_mask(ppwr, 0x000200, 0x00002000, 0x00002000);
-       nv_rd32(ppwr, 0x000200);
-       nv_wait(ppwr, 0x10a10c, 0x00000006, 0x00000000);
-
-       /* upload data segment */
-       nv_wr32(ppwr, 0x10a1c0, 0x01000000);
-       for (i = 0; i < impl->data.size / 4; i++)
-               nv_wr32(ppwr, 0x10a1c4, impl->data.data[i]);
-
-       /* upload code segment */
-       nv_wr32(ppwr, 0x10a180, 0x01000000);
-       for (i = 0; i < impl->code.size / 4; i++) {
-               if ((i & 0x3f) == 0)
-                       nv_wr32(ppwr, 0x10a188, i >> 6);
-               nv_wr32(ppwr, 0x10a184, impl->code.data[i]);
-       }
-
-       /* start it running */
-       nv_wr32(ppwr, 0x10a10c, 0x00000000);
-       nv_wr32(ppwr, 0x10a104, 0x00000000);
-       nv_wr32(ppwr, 0x10a100, 0x00000002);
-
-       /* wait for valid host->pwr ring configuration */
-       if (!nv_wait_ne(ppwr, 0x10a4d0, 0xffffffff, 0x00000000))
-               return -EBUSY;
-       ppwr->send.base = nv_rd32(ppwr, 0x10a4d0) & 0x0000ffff;
-       ppwr->send.size = nv_rd32(ppwr, 0x10a4d0) >> 16;
-
-       /* wait for valid pwr->host ring configuration */
-       if (!nv_wait_ne(ppwr, 0x10a4dc, 0xffffffff, 0x00000000))
-               return -EBUSY;
-       ppwr->recv.base = nv_rd32(ppwr, 0x10a4dc) & 0x0000ffff;
-       ppwr->recv.size = nv_rd32(ppwr, 0x10a4dc) >> 16;
-
-       nv_wr32(ppwr, 0x10a010, 0x000000e0);
-       return 0;
-}
-
-int
-nouveau_pwr_create_(struct nouveau_object *parent,
-                   struct nouveau_object *engine,
-                   struct nouveau_oclass *oclass, int length, void **pobject)
-{
-       struct nouveau_pwr *ppwr;
-       int ret;
-
-       ret = nouveau_subdev_create_(parent, engine, oclass, 0, "PPWR",
-                                    "pwr", length, pobject);
-       ppwr = *pobject;
-       if (ret)
-               return ret;
-
-       INIT_WORK(&ppwr->recv.work, nouveau_pwr_recv);
-       init_waitqueue_head(&ppwr->recv.wait);
-       return 0;
-}
-
-int
-_nouveau_pwr_ctor(struct nouveau_object *parent,
-                 struct nouveau_object *engine,
-                 struct nouveau_oclass *oclass, void *data, u32 size,
-                 struct nouveau_object **pobject)
-{
-       struct nouveau_pwr *ppwr;
-       int ret = nouveau_pwr_create(parent, engine, oclass, &ppwr);
-       *pobject = nv_object(ppwr);
-       return ret;
-}
diff --git a/drivers/gpu/drm/nouveau/core/subdev/pwr/fuc/arith.fuc b/drivers/gpu/drm/nouveau/core/subdev/pwr/fuc/arith.fuc
deleted file mode 100644 (file)
index 214a6d9..0000000
+++ /dev/null
@@ -1,94 +0,0 @@
-/*
- * Copyright 2014 Martin Peres <martin.peres@free.fr>
- *
- * 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 folloing 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
- */
-
-/******************************************************************************
- * arith data segment
- *****************************************************************************/
-#ifdef INCLUDE_PROC
-#endif
-
-#ifdef INCLUDE_DATA
-#endif
-
-/******************************************************************************
- * arith code segment
- *****************************************************************************/
-#ifdef INCLUDE_CODE
-
-// does a 32x32 -> 64 multiplication
-//
-// A * B = A_lo * B_lo
-//        + ( A_hi * B_lo ) << 16
-//        + ( A_lo * B_hi ) << 16
-//        + ( A_hi * B_hi ) << 32
-//
-// $r15 - current
-// $r14 - A
-// $r13 - B
-// $r12 - mul_lo (return)
-// $r11 - mul_hi (return)
-// $r0  - zero
-mulu32_32_64:
-       push $r1 // A_hi
-       push $r2 // B_hi
-       push $r3 // tmp0
-       push $r4 // tmp1
-
-       shr b32 $r1 $r14 16
-       shr b32 $r2 $r13 16
-
-       clear b32 $r12
-       clear b32 $r11
-
-       // A_lo * B_lo
-       mulu $r12 $r14 $r13
-
-       // ( A_hi * B_lo ) << 16
-       mulu $r3 $r1 $r13 // tmp0 = A_hi * B_lo
-       mov b32 $r4 $r3
-       and $r3 0xffff // tmp0 = tmp0_lo
-       shl b32 $r3 16
-       shr b32 $r4 16 // tmp1 = tmp0_hi
-       add b32 $r12 $r3
-       adc b32 $r11 $r4
-
-       // ( A_lo * B_hi ) << 16
-       mulu $r3 $r14 $r2 // tmp0 = A_lo * B_hi
-       mov b32 $r4 $r3
-       and $r3 0xffff // tmp0 = tmp0_lo
-       shl b32 $r3 16
-       shr b32 $r4 16 // tmp1 = tmp0_hi
-       add b32 $r12 $r3
-       adc b32 $r11 $r4
-
-       // ( A_hi * B_hi ) << 32
-       mulu $r3 $r1 $r2 // tmp0 = A_hi * B_hi
-       add b32 $r11 $r3
-
-       pop $r4
-       pop $r3
-       pop $r2
-       pop $r1
-       ret
-#endif
diff --git a/drivers/gpu/drm/nouveau/core/subdev/pwr/fuc/host.fuc b/drivers/gpu/drm/nouveau/core/subdev/pwr/fuc/host.fuc
deleted file mode 100644 (file)
index c2bb616..0000000
+++ /dev/null
@@ -1,151 +0,0 @@
-/*
- * Copyright 2013 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
- */
-
-#ifdef INCLUDE_PROC
-process(PROC_HOST, #host_init, #host_recv)
-#endif
-
-/******************************************************************************
- * HOST data segment
- *****************************************************************************/
-#ifdef INCLUDE_DATA
-// HOST (R)FIFO packet format
-.equ #fifo_process 0x00
-.equ #fifo_message 0x04
-.equ #fifo_data0   0x08
-.equ #fifo_data1   0x0c
-
-// HOST HOST->PWR queue description
-.equ #fifo_qlen 4 // log2(size of queue entry in bytes)
-.equ #fifo_qnum 3 // log2(max number of entries in queue)
-.equ #fifo_qmaskb (1 << #fifo_qnum) // max number of entries in queue
-.equ #fifo_qmaskp (#fifo_qmaskb - 1)
-.equ #fifo_qmaskf ((#fifo_qmaskb << 1) - 1)
-.equ #fifo_qsize  (1 << (#fifo_qlen + #fifo_qnum))
-fifo_queue: .skip 128 // #fifo_qsize
-
-// HOST PWR->HOST queue description
-.equ #rfifo_qlen 4 // log2(size of queue entry in bytes)
-.equ #rfifo_qnum 3 // log2(max number of entries in queue)
-.equ #rfifo_qmaskb (1 << #rfifo_qnum) // max number of entries in queue
-.equ #rfifo_qmaskp (#rfifo_qmaskb - 1)
-.equ #rfifo_qmaskf ((#rfifo_qmaskb << 1) - 1)
-.equ #rfifo_qsize  (1 << (#rfifo_qlen + #rfifo_qnum))
-rfifo_queue: .skip 128 // #rfifo_qsize
-#endif
-
-/******************************************************************************
- * HOST code segment
- *****************************************************************************/
-#ifdef INCLUDE_CODE
-// HOST->PWR comms - dequeue message(s) for process(es) from FIFO
-//
-// $r15 - current (host)
-// $r0  - zero
-host_send:
-       nv_iord($r1, NV_PPWR_FIFO_GET(0))
-       nv_iord($r2, NV_PPWR_FIFO_PUT(0))
-       cmp b32 $r1 $r2
-       bra e #host_send_done
-               // calculate address of message
-               and $r14 $r1 #fifo_qmaskp
-               shl b32 $r14 $r14 #fifo_qlen
-               add b32 $r14 #fifo_queue
-
-               // read message data, and pass to appropriate process
-               ld b32 $r11 D[$r14 + #fifo_data1]
-               ld b32 $r12 D[$r14 + #fifo_data0]
-               ld b32 $r13 D[$r14 + #fifo_message]
-               ld b32 $r14 D[$r14 + #fifo_process]
-               call(send)
-
-               // increment GET
-               add b32 $r1 0x1
-               and $r14 $r1 #fifo_qmaskf
-               nv_iowr(NV_PPWR_FIFO_GET(0), $r14)
-               bra #host_send
-       host_send_done:
-       ret
-
-// PWR->HOST comms - enqueue message for HOST to RFIFO
-//
-// $r15 - current (host)
-// $r14 - process
-// $r13 - message
-// $r12 - message data 0
-// $r11 - message data 1
-// $r0  - zero
-host_recv:
-       // message from intr handler == HOST->PWR comms pending
-       mov $r1 (PROC_KERN & 0x0000ffff)
-       sethi $r1 (PROC_KERN & 0xffff0000)
-       cmp b32 $r14 $r1
-       bra e #host_send
-
-       // wait for space in RFIFO
-       host_recv_wait:
-       nv_iord($r1, NV_PPWR_RFIFO_GET)
-       nv_iord($r2, NV_PPWR_RFIFO_PUT)
-       xor $r1 #rfifo_qmaskb
-       cmp b32 $r1 $r2
-       bra e #host_recv_wait
-
-       and $r3 $r2 #rfifo_qmaskp
-       shl b32 $r3 #rfifo_qlen
-       add b32 $r3 #rfifo_queue
-
-       // enqueue message
-       st b32 D[$r3 + #fifo_data1] $r11
-       st b32 D[$r3 + #fifo_data0] $r12
-       st b32 D[$r3 + #fifo_message] $r13
-       st b32 D[$r3 + #fifo_process] $r14
-
-       add b32 $r2 0x1
-       and $r2 #rfifo_qmaskf
-       nv_iowr(NV_PPWR_RFIFO_PUT, $r2)
-
-       // notify host of pending message
-       mov $r2 NV_PPWR_INTR_TRIGGER_USER0
-       nv_iowr(NV_PPWR_INTR_TRIGGER, $r2)
-       ret
-
-// $r15 - current (host)
-// $r0  - zero
-host_init:
-       // store each fifo's base/size in H2D/D2H scratch regs
-       mov $r1 #fifo_qsize
-       shl b32 $r1 16
-       or $r1 #fifo_queue
-       nv_iowr(NV_PPWR_H2D, $r1);
-
-       mov $r1 #rfifo_qsize
-       shl b32 $r1 16
-       or $r1 #rfifo_queue
-       nv_iowr(NV_PPWR_D2H, $r1);
-
-       // enable fifo subintr for first fifo
-       mov $r1 1
-       nv_iowr(NV_PPWR_FIFO_INTR_EN, $r1)
-       ret
-#endif
diff --git a/drivers/gpu/drm/nouveau/core/subdev/pwr/fuc/i2c_.fuc b/drivers/gpu/drm/nouveau/core/subdev/pwr/fuc/i2c_.fuc
deleted file mode 100644 (file)
index 757dda7..0000000
+++ /dev/null
@@ -1,393 +0,0 @@
-/*
- * Copyright 2013 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 T_TIMEOUT  2200000
-#define T_RISEFALL 1000
-#define T_HOLD     5000
-
-#ifdef INCLUDE_PROC
-process(PROC_I2C_, #i2c_init, #i2c_recv)
-#endif
-
-/******************************************************************************
- * I2C_ data segment
- *****************************************************************************/
-#ifdef INCLUDE_DATA
-i2c_scl_map:
-.b32 NV_PPWR_OUTPUT_I2C_0_SCL
-.b32 NV_PPWR_OUTPUT_I2C_1_SCL
-.b32 NV_PPWR_OUTPUT_I2C_2_SCL
-.b32 NV_PPWR_OUTPUT_I2C_3_SCL
-.b32 NV_PPWR_OUTPUT_I2C_4_SCL
-.b32 NV_PPWR_OUTPUT_I2C_5_SCL
-.b32 NV_PPWR_OUTPUT_I2C_6_SCL
-.b32 NV_PPWR_OUTPUT_I2C_7_SCL
-.b32 NV_PPWR_OUTPUT_I2C_8_SCL
-.b32 NV_PPWR_OUTPUT_I2C_9_SCL
-i2c_sda_map:
-.b32 NV_PPWR_OUTPUT_I2C_0_SDA
-.b32 NV_PPWR_OUTPUT_I2C_1_SDA
-.b32 NV_PPWR_OUTPUT_I2C_2_SDA
-.b32 NV_PPWR_OUTPUT_I2C_3_SDA
-.b32 NV_PPWR_OUTPUT_I2C_4_SDA
-.b32 NV_PPWR_OUTPUT_I2C_5_SDA
-.b32 NV_PPWR_OUTPUT_I2C_6_SDA
-.b32 NV_PPWR_OUTPUT_I2C_7_SDA
-.b32 NV_PPWR_OUTPUT_I2C_8_SDA
-.b32 NV_PPWR_OUTPUT_I2C_9_SDA
-#if NVKM_PPWR_CHIPSET < GF119
-i2c_ctrl:
-.b32 0x00e138
-.b32 0x00e150
-.b32 0x00e168
-.b32 0x00e180
-.b32 0x00e254
-.b32 0x00e274
-.b32 0x00e764
-.b32 0x00e780
-.b32 0x00e79c
-.b32 0x00e7b8
-#endif
-#endif
-
-/******************************************************************************
- * I2C_ code segment
- *****************************************************************************/
-#ifdef INCLUDE_CODE
-
-// $r3  - value
-// $r2  - sda line
-// $r1  - scl line
-// $r0  - zero
-i2c_drive_scl:
-       cmp b32 $r3 0
-       bra e #i2c_drive_scl_lo
-       nv_iowr(NV_PPWR_OUTPUT_SET, $r1)
-       ret
-       i2c_drive_scl_lo:
-       nv_iowr(NV_PPWR_OUTPUT_CLR, $r1)
-       ret
-
-i2c_drive_sda:
-       cmp b32 $r3 0
-       bra e #i2c_drive_sda_lo
-       nv_iowr(NV_PPWR_OUTPUT_SET, $r2)
-       ret
-       i2c_drive_sda_lo:
-       nv_iowr(NV_PPWR_OUTPUT_CLR, $r2)
-       ret
-
-i2c_sense_scl:
-       bclr $flags $p1
-       nv_iord($r3, NV_PPWR_INPUT)
-       and $r3 $r1
-       bra z #i2c_sense_scl_done
-               bset $flags $p1
-       i2c_sense_scl_done:
-       ret
-
-i2c_sense_sda:
-       bclr $flags $p1
-       nv_iord($r3, NV_PPWR_INPUT)
-       and $r3 $r2
-       bra z #i2c_sense_sda_done
-               bset $flags $p1
-       i2c_sense_sda_done:
-       ret
-
-#define i2c_drive_scl(v) /*
-*/     mov $r3 (v) /*
-*/     call(i2c_drive_scl)
-#define i2c_drive_sda(v) /*
-*/     mov $r3 (v) /*
-*/     call(i2c_drive_sda)
-#define i2c_sense_scl() /*
-*/     call(i2c_sense_scl)
-#define i2c_sense_sda() /*
-*/     call(i2c_sense_sda)
-#define i2c_delay(v) /*
-*/     mov $r14 (v) /*
-*/     call(nsec)
-
-#define i2c_trace_init() /*
-*/     imm32($r6, 0x10000000) /*
-*/     sub b32 $r7 $r6 1 /*
-*/
-#define i2c_trace_down() /*
-*/     shr b32 $r6 4 /*
-*/     push $r5 /*
-*/     shl b32 $r5 $r6 4 /*
-*/     sub b32 $r5 $r6 /*
-*/     not b32 $r5 /*
-*/     and $r7 $r5 /*
-*/     pop $r5 /*
-*/
-#define i2c_trace_exit() /*
-*/     shl b32 $r6 4 /*
-*/
-#define i2c_trace_next() /*
-*/     add b32 $r7 $r6 /*
-*/
-#define i2c_trace_call(func) /*
-*/     i2c_trace_next() /*
-*/     i2c_trace_down() /*
-*/     call(func) /*
-*/     i2c_trace_exit() /*
-*/
-
-i2c_raise_scl:
-       push $r4
-       mov $r4 (T_TIMEOUT / T_RISEFALL)
-       i2c_drive_scl(1)
-       i2c_raise_scl_wait:
-               i2c_delay(T_RISEFALL)
-               i2c_sense_scl()
-               bra $p1 #i2c_raise_scl_done
-               sub b32 $r4 1
-               bra nz #i2c_raise_scl_wait
-       i2c_raise_scl_done:
-       pop $r4
-       ret
-
-i2c_start:
-       i2c_sense_scl()
-       bra not $p1 #i2c_start_rep
-       i2c_sense_sda()
-       bra not $p1 #i2c_start_rep
-       bra #i2c_start_send
-       i2c_start_rep:
-               i2c_drive_scl(0)
-               i2c_drive_sda(1)
-               i2c_trace_call(i2c_raise_scl)
-               bra not $p1 #i2c_start_out
-       i2c_start_send:
-       i2c_drive_sda(0)
-       i2c_delay(T_HOLD)
-       i2c_drive_scl(0)
-       i2c_delay(T_HOLD)
-       i2c_start_out:
-       ret
-
-i2c_stop:
-       i2c_drive_scl(0)
-       i2c_drive_sda(0)
-       i2c_delay(T_RISEFALL)
-       i2c_drive_scl(1)
-       i2c_delay(T_HOLD)
-       i2c_drive_sda(1)
-       i2c_delay(T_HOLD)
-       ret
-
-// $r3  - value
-// $r2  - sda line
-// $r1  - scl line
-// $r0  - zero
-i2c_bitw:
-       call(i2c_drive_sda)
-       i2c_delay(T_RISEFALL)
-       i2c_trace_call(i2c_raise_scl)
-       bra not $p1 #i2c_bitw_out
-       i2c_delay(T_HOLD)
-       i2c_drive_scl(0)
-       i2c_delay(T_HOLD)
-       i2c_bitw_out:
-       ret
-
-// $r3  - value (out)
-// $r2  - sda line
-// $r1  - scl line
-// $r0  - zero
-i2c_bitr:
-       i2c_drive_sda(1)
-       i2c_delay(T_RISEFALL)
-       i2c_trace_call(i2c_raise_scl)
-       bra not $p1 #i2c_bitr_done
-       i2c_sense_sda()
-       i2c_drive_scl(0)
-       i2c_delay(T_HOLD)
-       xbit $r3 $flags $p1
-       bset $flags $p1
-       i2c_bitr_done:
-       ret
-
-i2c_get_byte:
-       mov $r5 0
-       mov $r4 8
-       i2c_get_byte_next:
-               shl b32 $r5 1
-               i2c_trace_call(i2c_bitr)
-               bra not $p1 #i2c_get_byte_done
-               or $r5 $r3
-               sub b32 $r4 1
-               bra nz #i2c_get_byte_next
-       mov $r3 1
-       i2c_trace_call(i2c_bitw)
-       i2c_get_byte_done:
-       ret
-
-i2c_put_byte:
-       mov $r4 8
-       i2c_put_byte_next:
-               sub b32 $r4 1
-               xbit $r3 $r5 $r4
-               i2c_trace_call(i2c_bitw)
-               bra not $p1 #i2c_put_byte_done
-               cmp b32 $r4 0
-               bra ne #i2c_put_byte_next
-       i2c_trace_call(i2c_bitr)
-       bra not $p1 #i2c_put_byte_done
-       i2c_trace_next()
-       cmp b32 $r3 1
-       bra ne #i2c_put_byte_done
-       bclr $flags $p1 // nack
-       i2c_put_byte_done:
-       ret
-
-i2c_addr:
-       i2c_trace_call(i2c_start)
-       bra not $p1 #i2c_addr_done
-       extr $r3 $r12 I2C__MSG_DATA0_ADDR
-       shl b32 $r3 1
-       or $r5 $r3
-       i2c_trace_call(i2c_put_byte)
-       i2c_addr_done:
-       ret
-
-i2c_acquire_addr:
-       extr $r14 $r12 I2C__MSG_DATA0_PORT
-#if NVKM_PPWR_CHIPSET < GF119
-       shl b32 $r14 2
-       add b32 $r14 #i2c_ctrl
-       ld b32 $r14 D[$r14]
-#else
-       shl b32 $r14 5
-       add b32 $r14 0x00d014
-#endif
-       ret
-
-i2c_acquire:
-       call(i2c_acquire_addr)
-       call(rd32)
-       bset $r13 3
-       call(wr32)
-       ret
-
-i2c_release:
-       call(i2c_acquire_addr)
-       call(rd32)
-       bclr $r13 3
-       call(wr32)
-       ret
-
-// description
-//
-// $r15 - current (i2c)
-// $r14 - sender process name
-// $r13 - message
-// $r12 - data0
-// $r11 - data1
-// $r0  - zero
-i2c_recv:
-       bclr $flags $p1
-       extr $r1 $r12 I2C__MSG_DATA0_PORT
-       shl b32 $r1 2
-       cmp b32 $r1 (#i2c_sda_map - #i2c_scl_map)
-       bra ge #i2c_recv_done
-       add b32 $r3 $r1 #i2c_sda_map
-       ld b32 $r2 D[$r3]
-       add b32 $r3 $r1 #i2c_scl_map
-       ld b32 $r1 D[$r3]
-
-       bset $flags $p2
-       push $r13
-       push $r14
-
-       push $r13
-       i2c_trace_init()
-       i2c_trace_call(i2c_acquire)
-       pop $r13
-
-       cmp b32 $r13 I2C__MSG_RD08
-       bra ne #i2c_recv_not_rd08
-               mov $r5 0
-               i2c_trace_call(i2c_addr)
-               bra not $p1 #i2c_recv_done
-               extr $r5 $r12 I2C__MSG_DATA0_RD08_REG
-               i2c_trace_call(i2c_put_byte)
-               bra not $p1 #i2c_recv_done
-               mov $r5 1
-               i2c_trace_call(i2c_addr)
-               bra not $p1 #i2c_recv_done
-               i2c_trace_call(i2c_get_byte)
-               bra not $p1 #i2c_recv_done
-               ins $r11 $r5 I2C__MSG_DATA1_RD08_VAL
-               i2c_trace_call(i2c_stop)
-               mov b32 $r11 $r5
-               clear b32 $r7
-               bra #i2c_recv_done
-
-       i2c_recv_not_rd08:
-       cmp b32 $r13 I2C__MSG_WR08
-       bra ne #i2c_recv_not_wr08
-               mov $r5 0
-               call(i2c_addr)
-               bra not $p1 #i2c_recv_done
-               extr $r5 $r12 I2C__MSG_DATA0_WR08_REG
-               call(i2c_put_byte)
-               bra not $p1 #i2c_recv_done
-               mov $r5 0
-               call(i2c_addr)
-               bra not $p1 #i2c_recv_done
-               extr $r5 $r11 I2C__MSG_DATA1_WR08_VAL
-               call(i2c_put_byte)
-               bra not $p1 #i2c_recv_done
-               call(i2c_stop)
-               clear b32 $r7
-               extr $r5 $r12 I2C__MSG_DATA0_WR08_SYNC
-               bra nz #i2c_recv_done
-               bclr $flags $p2
-               bra #i2c_recv_done
-
-       i2c_recv_not_wr08:
-
-       i2c_recv_done:
-       extr $r14 $r12 I2C__MSG_DATA0_PORT
-       call(i2c_release)
-
-       pop $r14
-       pop $r13
-       bra not $p2 #i2c_recv_exit
-       mov b32 $r12 $r7
-       call(send)
-
-       i2c_recv_exit:
-       ret
-
-// description
-//
-// $r15 - current (i2c)
-// $r0  - zero
-i2c_init:
-       ret
-#endif
diff --git a/drivers/gpu/drm/nouveau/core/subdev/pwr/fuc/idle.fuc b/drivers/gpu/drm/nouveau/core/subdev/pwr/fuc/idle.fuc
deleted file mode 100644 (file)
index 98f1c37..0000000
+++ /dev/null
@@ -1,84 +0,0 @@
-/*
- * Copyright 2013 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
- */
-
-#ifdef INCLUDE_PROC
-process(PROC_IDLE, #idle, #idle_recv)
-#endif
-
-/******************************************************************************
- * IDLE data segment
- *****************************************************************************/
-#ifdef INCLUDE_DATA
-#endif
-
-/******************************************************************************
- * IDLE code segment
- *****************************************************************************/
-#ifdef INCLUDE_CODE
-// description
-//
-// $r15 - current (idle)
-// $r14 - message
-// $r0  - zero
-idle_recv:
-       ret
-
-// description
-//
-// $r15 - current (idle)
-// $r0  - zero
-idle:
-       // set our "no interrupt has occurred during our execution" flag
-       bset $flags $p0
-
-       // count IDLE invocations for debugging purposes
-       nv_iord($r1, NV_PPWR_DSCRATCH(1))
-       add b32 $r1 1
-       nv_iowr(NV_PPWR_DSCRATCH(1), $r1)
-
-       // keep looping while there's pending messages for any process
-       idle_loop:
-       mov $r1 #proc_list_head
-       bclr $flags $p2
-       idle_proc:
-               // process the process' messages until there's none left
-               idle_proc_exec:
-                       push $r1
-                       mov b32 $r14 $r1
-                       call(recv)
-                       pop $r1
-                       bra not $p1 #idle_proc_next
-                       bset $flags $p2
-                       bra #idle_proc_exec
-               // next process!
-               idle_proc_next:
-               add b32 $r1 #proc_size
-               cmp b32 $r1 $r15
-               bra ne #idle_proc
-       bra $p2 #idle_loop
-
-       // sleep if no interrupts have occurred
-       sleep $p0
-       bra #idle
-#endif
diff --git a/drivers/gpu/drm/nouveau/core/subdev/pwr/fuc/kernel.fuc b/drivers/gpu/drm/nouveau/core/subdev/pwr/fuc/kernel.fuc
deleted file mode 100644 (file)
index 5cf5be6..0000000
+++ /dev/null
@@ -1,556 +0,0 @@
-/*
- * Copyright 2013 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
- */
-
-/******************************************************************************
- * kernel data segment
- *****************************************************************************/
-#ifdef INCLUDE_PROC
-proc_kern:
-process(PROC_KERN, 0, 0)
-proc_list_head:
-#endif
-
-#ifdef INCLUDE_DATA
-proc_list_tail:
-time_prev: .b32 0
-time_next: .b32 0
-#endif
-
-/******************************************************************************
- * kernel code segment
- *****************************************************************************/
-#ifdef INCLUDE_CODE
-       bra #init
-
-// read nv register
-//
-// $r15 - current
-// $r14 - addr
-// $r13 - data (return)
-// $r0  - zero
-rd32:
-       nv_iowr(NV_PPWR_MMIO_ADDR, $r14)
-       mov $r13 NV_PPWR_MMIO_CTRL_OP_RD
-       sethi $r13 NV_PPWR_MMIO_CTRL_TRIGGER
-       nv_iowr(NV_PPWR_MMIO_CTRL, $r13)
-       rd32_wait:
-               nv_iord($r13, NV_PPWR_MMIO_CTRL)
-               and $r13 NV_PPWR_MMIO_CTRL_STATUS
-               bra nz #rd32_wait
-       nv_iord($r13, NV_PPWR_MMIO_DATA)
-       ret
-
-// write nv register
-//
-// $r15 - current
-// $r14 - addr
-// $r13 - data
-// $r0  - zero
-wr32:
-       nv_iowr(NV_PPWR_MMIO_ADDR, $r14)
-       nv_iowr(NV_PPWR_MMIO_DATA, $r13)
-       mov $r13 NV_PPWR_MMIO_CTRL_OP_WR
-       or $r13 NV_PPWR_MMIO_CTRL_MASK_B32_0
-       sethi $r13 NV_PPWR_MMIO_CTRL_TRIGGER
-
-#ifdef NVKM_FALCON_MMIO_TRAP
-       push $r13
-       mov $r13 NV_PPWR_INTR_TRIGGER_USER1
-       nv_iowr(NV_PPWR_INTR_TRIGGER, $r13)
-       wr32_host:
-               nv_iord($r13, NV_PPWR_INTR)
-               and $r13 NV_PPWR_INTR_USER1
-               bra nz #wr32_host
-       pop $r13
-#endif
-
-       nv_iowr(NV_PPWR_MMIO_CTRL, $r13)
-       wr32_wait:
-               nv_iord($r13, NV_PPWR_MMIO_CTRL)
-               and $r13 NV_PPWR_MMIO_CTRL_STATUS
-               bra nz #wr32_wait
-       ret
-
-// busy-wait for a period of time
-//
-// $r15 - current
-// $r14 - ns
-// $r0  - zero
-nsec:
-       push $r9
-       push $r8
-       nv_iord($r8, NV_PPWR_TIMER_LOW)
-       nsec_loop:
-               nv_iord($r9, NV_PPWR_TIMER_LOW)
-               sub b32 $r9 $r8
-               cmp b32 $r9 $r14
-               bra l #nsec_loop
-       pop $r8
-       pop $r9
-       ret
-
-// busy-wait for a period of time
-//
-// $r15 - current
-// $r14 - addr
-// $r13 - mask
-// $r12 - data
-// $r11 - timeout (ns)
-// $r0  - zero
-wait:
-       push $r9
-       push $r8
-       nv_iord($r8, NV_PPWR_TIMER_LOW)
-       wait_loop:
-               nv_rd32($r10, $r14)
-               and $r10 $r13
-               cmp b32 $r10 $r12
-               bra e #wait_done
-               nv_iord($r9, NV_PPWR_TIMER_LOW)
-               sub b32 $r9 $r8
-               cmp b32 $r9 $r11
-               bra l #wait_loop
-       wait_done:
-       pop $r8
-       pop $r9
-       ret
-
-// $r15 - current (kern)
-// $r14 - process
-// $r8  - NV_PPWR_INTR
-intr_watchdog:
-       // read process' timer status, skip if not enabled
-       ld b32 $r9 D[$r14 + #proc_time]
-       cmp b32 $r9 0
-       bra z #intr_watchdog_next_proc
-
-       // subtract last timer's value from process' timer,
-       // if it's <= 0 then the timer has expired
-       ld b32 $r10 D[$r0 + #time_prev]
-       sub b32 $r9 $r10
-       bra g #intr_watchdog_next_time
-               mov $r13 KMSG_ALARM
-               call(send_proc)
-               clear b32 $r9
-               bra #intr_watchdog_next_proc
-
-       // otherwise, update the next timer's value if this
-       // process' timer is the soonest
-       intr_watchdog_next_time:
-               // ... or if there's no next timer yet
-               ld b32 $r10 D[$r0 + #time_next]
-               cmp b32 $r10 0
-               bra z #intr_watchdog_next_time_set
-
-               cmp b32 $r9 $r10
-               bra g #intr_watchdog_next_proc
-               intr_watchdog_next_time_set:
-               st b32 D[$r0 + #time_next] $r9
-
-       // update process' timer status, and advance
-       intr_watchdog_next_proc:
-       st b32 D[$r14 + #proc_time] $r9
-       add b32 $r14 #proc_size
-       cmp b32 $r14 #proc_list_tail
-       bra ne #intr_watchdog
-       ret
-
-intr:
-       push $r0
-       clear b32 $r0
-       push $r8
-       push $r9
-       push $r10
-       push $r11
-       push $r12
-       push $r13
-       push $r14
-       push $r15
-       mov $r15 #proc_kern
-       mov $r8 $flags
-       push $r8
-
-       nv_iord($r8, NV_PPWR_DSCRATCH(0))
-       add b32 $r8 1
-       nv_iowr(NV_PPWR_DSCRATCH(0), $r8)
-
-       nv_iord($r8, NV_PPWR_INTR)
-       and $r9 $r8 NV_PPWR_INTR_WATCHDOG
-       bra z #intr_skip_watchdog
-               st b32 D[$r0 + #time_next] $r0
-               mov $r14 #proc_list_head
-               call(intr_watchdog)
-               ld b32 $r9 D[$r0 + #time_next]
-               cmp b32 $r9 0
-               bra z #intr_skip_watchdog
-                       nv_iowr(NV_PPWR_WATCHDOG_TIME, $r9)
-                       st b32 D[$r0 + #time_prev] $r9
-
-       intr_skip_watchdog:
-       and $r9 $r8 NV_PPWR_INTR_SUBINTR
-       bra z #intr_skip_subintr
-               nv_iord($r9, NV_PPWR_SUBINTR)
-               and $r10 $r9 NV_PPWR_SUBINTR_FIFO
-               bra z #intr_subintr_skip_fifo
-                       nv_iord($r12, NV_PPWR_FIFO_INTR)
-                       push $r12
-                       mov $r14 (PROC_HOST & 0x0000ffff)
-                       sethi $r14 (PROC_HOST & 0xffff0000)
-                       mov $r13 KMSG_FIFO
-                       call(send)
-                       pop $r12
-                       nv_iowr(NV_PPWR_FIFO_INTR, $r12)
-               intr_subintr_skip_fifo:
-               nv_iowr(NV_PPWR_SUBINTR, $r9)
-
-       intr_skip_subintr:
-       and $r9 $r8 NV_PPWR_INTR_PAUSE
-       bra z #intr_skip_pause
-               and $r10 0xffbf
-
-       intr_skip_pause:
-       and $r9 $r8 NV_PPWR_INTR_USER0
-       bra z #intr_skip_user0
-               and $r10 0xffbf
-
-       intr_skip_user0:
-       nv_iowr(NV_PPWR_INTR_ACK, $r8)
-       pop $r8
-       mov $flags $r8
-       pop $r15
-       pop $r14
-       pop $r13
-       pop $r12
-       pop $r11
-       pop $r10
-       pop $r9
-       pop $r8
-       pop $r0
-       bclr $flags $p0
-       iret
-
-// calculate the number of ticks in the specified nanoseconds delay
-//
-// $r15 - current
-// $r14 - ns
-// $r14 - ticks (return)
-// $r0  - zero
-ticks_from_ns:
-       push $r12
-       push $r11
-
-       /* try not losing precision (multiply then divide) */
-       imm32($r13, HW_TICKS_PER_US)
-       call #mulu32_32_64
-
-       /* use an immeditate, it's ok because HW_TICKS_PER_US < 16 bits */
-       div $r12 $r12 1000
-
-       /* check if there wasn't any overflow */
-       cmpu b32 $r11 0
-       bra e #ticks_from_ns_quit
-
-       /* let's divide then multiply, too bad for the precision! */
-       div $r14 $r14 1000
-       imm32($r13, HW_TICKS_PER_US)
-       call #mulu32_32_64
-
-       /* this cannot overflow as long as HW_TICKS_PER_US < 1000 */
-
-ticks_from_ns_quit:
-       mov b32 $r14 $r12
-       pop $r11
-       pop $r12
-       ret
-
-// calculate the number of ticks in the specified microsecond delay
-//
-// $r15 - current
-// $r14 - us
-// $r14 - ticks (return)
-// $r0  - zero
-ticks_from_us:
-       push $r12
-       push $r11
-
-       /* simply multiply $us by HW_TICKS_PER_US */
-       imm32($r13, HW_TICKS_PER_US)
-       call #mulu32_32_64
-       mov b32 $r14 $r12
-
-       /* check if there wasn't any overflow */
-       cmpu b32 $r11 0
-       bra e #ticks_from_us_quit
-
-       /* Overflow! */
-       clear b32 $r14
-
-ticks_from_us_quit:
-       pop $r11
-       pop $r12
-       ret
-
-// calculate the number of ticks in the specified microsecond delay
-//
-// $r15 - current
-// $r14 - ticks
-// $r14 - us (return)
-// $r0  - zero
-ticks_to_us:
-       /* simply divide $ticks by HW_TICKS_PER_US */
-       imm32($r13, HW_TICKS_PER_US)
-       div $r14 $r14 $r13
-
-       ret
-
-// request the current process be sent a message after a timeout expires
-//
-// $r15 - current
-// $r14 - ticks (make sure it is < 2^31 to avoid any possible overflow)
-// $r0  - zero
-timer:
-       push $r9
-       push $r8
-
-       // interrupts off to prevent racing with timer isr
-       bclr $flags ie0
-
-       // if current process already has a timer set, bail
-       ld b32 $r8 D[$r15 + #proc_time]
-       cmp b32 $r8 0
-       bra g #timer_done
-
-       // halt watchdog timer temporarily
-       clear b32 $r8
-       nv_iowr(NV_PPWR_WATCHDOG_ENABLE, $r8)
-
-       // find out how much time elapsed since the last update
-       // of the watchdog and add this time to the wanted ticks
-       nv_iord($r8, NV_PPWR_WATCHDOG_TIME)
-       ld b32 $r9 D[$r0 + #time_prev]
-       sub b32 $r9 $r8
-       add b32 $r14 $r9
-       st b32 D[$r15 + #proc_time] $r14
-
-       // check for a pending interrupt.  if there's one already
-       // pending, we can just bail since the timer isr will
-       // queue the next soonest right after it's done
-       nv_iord($r8, NV_PPWR_INTR)
-       and $r8 NV_PPWR_INTR_WATCHDOG
-       bra nz #timer_enable
-
-       // update the watchdog if this timer should expire first,
-       // or if there's no timeout already set
-       nv_iord($r8, NV_PPWR_WATCHDOG_TIME)
-       cmp b32 $r14 $r0
-       bra e #timer_reset
-       cmp b32 $r14 $r8
-       bra g #timer_enable
-               timer_reset:
-               nv_iowr(NV_PPWR_WATCHDOG_TIME, $r14)
-               st b32 D[$r0 + #time_prev] $r14
-
-       // re-enable the watchdog timer
-       timer_enable:
-       mov $r8 1
-       nv_iowr(NV_PPWR_WATCHDOG_ENABLE, $r8)
-
-       // interrupts back on
-       timer_done:
-       bset $flags ie0
-
-       pop $r8
-       pop $r9
-       ret
-
-// send message to another process
-//
-// $r15 - current
-// $r14 - process
-// $r13 - message
-// $r12 - message data 0
-// $r11 - message data 1
-// $r0  - zero
-send_proc:
-       push $r8
-       push $r9
-       // check for space in queue
-       ld b32 $r8 D[$r14 + #proc_qget]
-       ld b32 $r9 D[$r14 + #proc_qput]
-       xor $r8 #proc_qmaskb
-       cmp b32 $r8 $r9
-       bra e #send_done
-
-       // enqueue message
-       and $r8 $r9 #proc_qmaskp
-       shl b32 $r8 $r8 #proc_qlen
-       add b32 $r8 #proc_queue
-       add b32 $r8 $r14
-
-       ld b32 $r10 D[$r15 + #proc_id]
-       st b32 D[$r8 + #msg_process] $r10
-       st b32 D[$r8 + #msg_message] $r13
-       st b32 D[$r8 + #msg_data0] $r12
-       st b32 D[$r8 + #msg_data1] $r11
-
-       // increment PUT
-       add b32 $r9 1
-       and $r9 #proc_qmaskf
-       st b32 D[$r14 + #proc_qput] $r9
-       bset $flags $p2
-       send_done:
-       pop $r9
-       pop $r8
-       ret
-
-// lookup process structure by its name
-//
-// $r15 - current
-// $r14 - process name
-// $r0  - zero
-//
-// $r14 - process
-// $p1  - success
-find:
-       push $r8
-       mov $r8 #proc_list_head
-       bset $flags $p1
-       find_loop:
-               ld b32 $r10 D[$r8 + #proc_id]
-               cmp b32 $r10 $r14
-               bra e #find_done
-               add b32 $r8 #proc_size
-               cmp b32 $r8 #proc_list_tail
-               bra ne #find_loop
-               bclr $flags $p1
-       find_done:
-       mov b32 $r14 $r8
-       pop $r8
-       ret
-
-// send message to another process
-//
-// $r15 - current
-// $r14 - process id
-// $r13 - message
-// $r12 - message data 0
-// $r11 - message data 1
-// $r0  - zero
-send:
-       call(find)
-       bra $p1 #send_proc
-       ret
-
-// process single message for a given process
-//
-// $r15 - current
-// $r14 - process
-// $r0  - zero
-recv:
-       push $r9
-       push $r8
-
-       ld b32 $r8 D[$r14 + #proc_qget]
-       ld b32 $r9 D[$r14 + #proc_qput]
-       bclr $flags $p1
-       cmp b32 $r8 $r9
-       bra e #recv_done
-               // dequeue message
-               and $r9 $r8 #proc_qmaskp
-               add b32 $r8 1
-               and $r8 #proc_qmaskf
-               st b32 D[$r14 + #proc_qget] $r8
-               ld b32 $r10 D[$r14 + #proc_recv]
-
-               push $r15
-               mov $r15 $flags
-               push $r15
-               mov b32 $r15 $r14
-
-               shl b32 $r9 $r9 #proc_qlen
-               add b32 $r14 $r9
-               add b32 $r14 #proc_queue
-               ld b32 $r11 D[$r14 + #msg_data1]
-               ld b32 $r12 D[$r14 + #msg_data0]
-               ld b32 $r13 D[$r14 + #msg_message]
-               ld b32 $r14 D[$r14 + #msg_process]
-
-               // process it
-               call $r10
-               pop $r15
-               mov $flags $r15
-               bset $flags $p1
-               pop $r15
-       recv_done:
-       pop $r8
-       pop $r9
-       ret
-
-init:
-       // setup stack
-       nv_iord($r1, NV_PPWR_CAPS)
-       extr $r1 $r1 9:17
-       shl b32 $r1 8
-       mov $sp $r1
-
-#ifdef NVKM_FALCON_MMIO_UAS
-       // somehow allows the magic "access mmio via D[]" stuff that's
-       // used by the nv_rd32/nv_wr32 macros to work
-       mov $r1 0x0010
-       sethi $r1 NV_PPWR_UAS_CONFIG_ENABLE
-       nv_iowrs(NV_PPWR_UAS_CONFIG, $r1)
-#endif
-
-       // route all interrupts except user0/1 and pause to fuc
-       mov $r1 0x00e0
-       sethi $r1 0x00000000
-       nv_iowr(NV_PPWR_INTR_ROUTE, $r1)
-
-       // enable watchdog and subintr intrs
-       mov $r1 NV_PPWR_INTR_EN_CLR_MASK
-       nv_iowr(NV_PPWR_INTR_EN_CLR, $r1)
-       mov $r1 NV_PPWR_INTR_EN_SET_WATCHDOG
-       or $r1 NV_PPWR_INTR_EN_SET_SUBINTR
-       nv_iowr(NV_PPWR_INTR_EN_SET, $r1)
-
-       // enable interrupts globally
-       mov $r1 #intr
-       sethi $r1 0x00000000
-       mov $iv0 $r1
-       bset $flags ie0
-
-       // enable watchdog timer
-       mov $r1 1
-       nv_iowr(NV_PPWR_WATCHDOG_ENABLE, $r1)
-
-       // bootstrap processes, idle process will be last, and not return
-       mov $r15 #proc_list_head
-       init_proc:
-               ld b32 $r1 D[$r15 + #proc_init]
-               cmp b32 $r1 0
-               bra z #init_proc
-               call $r1
-               add b32 $r15 #proc_size
-               bra #init_proc
-#endif
diff --git a/drivers/gpu/drm/nouveau/core/subdev/pwr/fuc/macros.fuc b/drivers/gpu/drm/nouveau/core/subdev/pwr/fuc/macros.fuc
deleted file mode 100644 (file)
index 96fc984..0000000
+++ /dev/null
@@ -1,272 +0,0 @@
-/*
- * Copyright 2013 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 GT215 0xa3
-#define GF100 0xc0
-#define GF119 0xd9
-#define GK208 0x108
-
-#include "os.h"
-
-// IO addresses
-#define NV_PPWR_INTR_TRIGGER                                             0x0000
-#define NV_PPWR_INTR_TRIGGER_USER1                                   0x00000080
-#define NV_PPWR_INTR_TRIGGER_USER0                                   0x00000040
-#define NV_PPWR_INTR_ACK                                                 0x0004
-#define NV_PPWR_INTR_ACK_SUBINTR                                     0x00000800
-#define NV_PPWR_INTR_ACK_WATCHDOG                                    0x00000002
-#define NV_PPWR_INTR                                                     0x0008
-#define NV_PPWR_INTR_SUBINTR                                         0x00000800
-#define NV_PPWR_INTR_USER1                                           0x00000080
-#define NV_PPWR_INTR_USER0                                           0x00000040
-#define NV_PPWR_INTR_PAUSE                                           0x00000020
-#define NV_PPWR_INTR_WATCHDOG                                        0x00000002
-#define NV_PPWR_INTR_EN_SET                                              0x0010
-#define NV_PPWR_INTR_EN_SET_SUBINTR                                  0x00000800
-#define NV_PPWR_INTR_EN_SET_WATCHDOG                                 0x00000002
-#define NV_PPWR_INTR_EN_CLR                                              0x0014
-#define NV_PPWR_INTR_EN_CLR_MASK                    /* fuck i hate envyas */ -1
-#define NV_PPWR_INTR_ROUTE                                               0x001c
-#define NV_PPWR_TIMER_LOW                                                0x002c
-#define NV_PPWR_WATCHDOG_TIME                                            0x0034
-#define NV_PPWR_WATCHDOG_ENABLE                                          0x0038
-#define NV_PPWR_CAPS                                                     0x0108
-#define NV_PPWR_UAS_CONFIG                                               0x0164
-#define NV_PPWR_UAS_CONFIG_ENABLE                                    0x00010000
-#if NVKM_PPWR_CHIPSET >= GK208
-#define NV_PPWR_DSCRATCH(i)                                   (4 * (i) + 0x0450)
-#endif
-#define NV_PPWR_FIFO_PUT(i)                                   (4 * (i) + 0x04a0)
-#define NV_PPWR_FIFO_GET(i)                                   (4 * (i) + 0x04b0)
-#define NV_PPWR_FIFO_INTR                                                0x04c0
-#define NV_PPWR_FIFO_INTR_EN                                             0x04c4
-#define NV_PPWR_RFIFO_PUT                                                0x04c8
-#define NV_PPWR_RFIFO_GET                                                0x04cc
-#define NV_PPWR_H2D                                                      0x04d0
-#define NV_PPWR_D2H                                                      0x04dc
-#if NVKM_PPWR_CHIPSET < GK208
-#define NV_PPWR_DSCRATCH(i)                                   (4 * (i) + 0x05d0)
-#endif
-#define NV_PPWR_SUBINTR                                                  0x0688
-#define NV_PPWR_SUBINTR_FIFO                                         0x00000002
-#define NV_PPWR_MMIO_ADDR                                                0x07a0
-#define NV_PPWR_MMIO_DATA                                                0x07a4
-#define NV_PPWR_MMIO_CTRL                                                0x07ac
-#define NV_PPWR_MMIO_CTRL_TRIGGER                                    0x00010000
-#define NV_PPWR_MMIO_CTRL_STATUS                                     0x00007000
-#define NV_PPWR_MMIO_CTRL_STATUS_IDLE                                0x00000000
-#define NV_PPWR_MMIO_CTRL_MASK                                       0x000000f0
-#define NV_PPWR_MMIO_CTRL_MASK_B32_0                                 0x000000f0
-#define NV_PPWR_MMIO_CTRL_OP                                         0x00000003
-#define NV_PPWR_MMIO_CTRL_OP_RD                                      0x00000001
-#define NV_PPWR_MMIO_CTRL_OP_WR                                      0x00000002
-#define NV_PPWR_OUTPUT                                                   0x07c0
-#define NV_PPWR_OUTPUT_FB_PAUSE                                      0x00000004
-#if NVKM_PPWR_CHIPSET < GF119
-#define NV_PPWR_OUTPUT_I2C_3_SCL                                     0x00000100
-#define NV_PPWR_OUTPUT_I2C_3_SDA                                     0x00000200
-#define NV_PPWR_OUTPUT_I2C_0_SCL                                     0x00001000
-#define NV_PPWR_OUTPUT_I2C_0_SDA                                     0x00002000
-#define NV_PPWR_OUTPUT_I2C_1_SCL                                     0x00004000
-#define NV_PPWR_OUTPUT_I2C_1_SDA                                     0x00008000
-#define NV_PPWR_OUTPUT_I2C_2_SCL                                     0x00010000
-#define NV_PPWR_OUTPUT_I2C_2_SDA                                     0x00020000
-#define NV_PPWR_OUTPUT_I2C_4_SCL                                     0x00040000
-#define NV_PPWR_OUTPUT_I2C_4_SDA                                     0x00080000
-#define NV_PPWR_OUTPUT_I2C_5_SCL                                     0x00100000
-#define NV_PPWR_OUTPUT_I2C_5_SDA                                     0x00200000
-#define NV_PPWR_OUTPUT_I2C_6_SCL                                     0x00400000
-#define NV_PPWR_OUTPUT_I2C_6_SDA                                     0x00800000
-#define NV_PPWR_OUTPUT_I2C_7_SCL                                     0x01000000
-#define NV_PPWR_OUTPUT_I2C_7_SDA                                     0x02000000
-#define NV_PPWR_OUTPUT_I2C_8_SCL                                     0x04000000
-#define NV_PPWR_OUTPUT_I2C_8_SDA                                     0x08000000
-#define NV_PPWR_OUTPUT_I2C_9_SCL                                     0x10000000
-#define NV_PPWR_OUTPUT_I2C_9_SDA                                     0x20000000
-#else
-#define NV_PPWR_OUTPUT_I2C_0_SCL                                     0x00000400
-#define NV_PPWR_OUTPUT_I2C_1_SCL                                     0x00000800
-#define NV_PPWR_OUTPUT_I2C_2_SCL                                     0x00001000
-#define NV_PPWR_OUTPUT_I2C_3_SCL                                     0x00002000
-#define NV_PPWR_OUTPUT_I2C_4_SCL                                     0x00004000
-#define NV_PPWR_OUTPUT_I2C_5_SCL                                     0x00008000
-#define NV_PPWR_OUTPUT_I2C_6_SCL                                     0x00010000
-#define NV_PPWR_OUTPUT_I2C_7_SCL                                     0x00020000
-#define NV_PPWR_OUTPUT_I2C_8_SCL                                     0x00040000
-#define NV_PPWR_OUTPUT_I2C_9_SCL                                     0x00080000
-#define NV_PPWR_OUTPUT_I2C_0_SDA                                     0x00100000
-#define NV_PPWR_OUTPUT_I2C_1_SDA                                     0x00200000
-#define NV_PPWR_OUTPUT_I2C_2_SDA                                     0x00400000
-#define NV_PPWR_OUTPUT_I2C_3_SDA                                     0x00800000
-#define NV_PPWR_OUTPUT_I2C_4_SDA                                     0x01000000
-#define NV_PPWR_OUTPUT_I2C_5_SDA                                     0x02000000
-#define NV_PPWR_OUTPUT_I2C_6_SDA                                     0x04000000
-#define NV_PPWR_OUTPUT_I2C_7_SDA                                     0x08000000
-#define NV_PPWR_OUTPUT_I2C_8_SDA                                     0x10000000
-#define NV_PPWR_OUTPUT_I2C_9_SDA                                     0x20000000
-#endif
-#define NV_PPWR_INPUT                                                    0x07c4
-#define NV_PPWR_OUTPUT_SET                                               0x07e0
-#define NV_PPWR_OUTPUT_SET_FB_PAUSE                                  0x00000004
-#define NV_PPWR_OUTPUT_CLR                                               0x07e4
-#define NV_PPWR_OUTPUT_CLR_FB_PAUSE                                  0x00000004
-
-// Inter-process message format
-.equ #msg_process 0x00 /* send() target, recv() sender */
-.equ #msg_message 0x04
-.equ #msg_data0   0x08
-.equ #msg_data1   0x0c
-
-// Kernel message IDs
-#define KMSG_FIFO  0x00000000
-#define KMSG_ALARM 0x00000001
-
-// Process message queue description
-.equ #proc_qlen 4 // log2(size of queue entry in bytes)
-.equ #proc_qnum 2 // log2(max number of entries in queue)
-.equ #proc_qmaskb (1 << #proc_qnum) // max number of entries in queue
-.equ #proc_qmaskp (#proc_qmaskb - 1)
-.equ #proc_qmaskf ((#proc_qmaskb << 1) - 1)
-.equ #proc_qsize  (1 << (#proc_qlen + #proc_qnum))
-
-// Process table entry
-.equ #proc_id    0x00
-.equ #proc_init  0x04
-.equ #proc_recv  0x08
-.equ #proc_time  0x0c
-.equ #proc_qput  0x10
-.equ #proc_qget  0x14
-.equ #proc_queue 0x18
-.equ #proc_size (0x18 + #proc_qsize)
-
-#define process(id,init,recv) /*
-*/     .b32 id /*
-*/     .b32 init /*
-*/     .b32 recv /*
-*/     .b32 0 /*
-*/     .b32 0 /*
-*/     .b32 0 /*
-*/     .skip 64
-
-#if NV_PPWR_CHIPSET < GK208
-#define imm32(reg,val) /*
-*/     movw reg  ((val) & 0x0000ffff) /*
-*/     sethi reg ((val) & 0xffff0000)
-#else
-#define imm32(reg,val) /*
-*/     mov reg (val)
-#endif
-
-#ifndef NVKM_FALCON_UNSHIFTED_IO
-#define nv_iord(reg,ior) /*
-*/     mov reg ior /*
-*/     shl b32 reg 6 /*
-*/     iord reg I[reg + 0x000]
-#else
-#define nv_iord(reg,ior) /*
-*/     mov reg ior /*
-*/     iord reg I[reg + 0x000]
-#endif
-
-#ifndef NVKM_FALCON_UNSHIFTED_IO
-#define nv_iowr(ior,reg) /*
-*/     mov $r0 ior /*
-*/     shl b32 $r0 6 /*
-*/     iowr I[$r0 + 0x000] reg /*
-*/     clear b32 $r0
-#else
-#define nv_iowr(ior,reg) /*
-*/     mov $r0 ior /*
-*/     iowr I[$r0 + 0x000] reg /*
-*/     clear b32 $r0
-#endif
-
-#ifndef NVKM_FALCON_UNSHIFTED_IO
-#define nv_iowrs(ior,reg) /*
-*/     mov $r0 ior /*
-*/     shl b32 $r0 6 /*
-*/     iowrs I[$r0 + 0x000] reg /*
-*/     clear b32 $r0
-#else
-#define nv_iowrs(ior,reg) /*
-*/     mov $r0 ior /*
-*/     iowrs I[$r0 + 0x000] reg /*
-*/     clear b32 $r0
-#endif
-
-#define hash #
-#define fn(a) a
-#ifndef NVKM_FALCON_PC24
-#define call(a) call fn(hash)a
-#else
-#define call(a) lcall fn(hash)a
-#endif
-
-#ifndef NVKM_FALCON_MMIO_UAS
-#define nv_rd32(reg,addr) /*
-*/     mov b32 $r14 addr /*
-*/     call(rd32) /*
-*/     mov b32 reg $r13
-#else
-#define nv_rd32(reg,addr) /*
-*/     sethi $r0 0x14000000 /*
-*/     or $r0 addr /*
-*/     ld b32 reg D[$r0] /*
-*/     clear b32 $r0
-#endif
-
-#if !defined(NVKM_FALCON_MMIO_UAS) || defined(NVKM_FALCON_MMIO_TRAP)
-#define nv_wr32(addr,reg) /*
-*/     push addr /*
-*/     push reg /*
-*/     pop $r13 /*
-*/     pop $r14 /*
-*/     call(wr32)
-#else
-#define nv_wr32(addr,reg) /*
-*/     sethi $r0 0x14000000 /*
-*/     or $r0 addr /*
-*/     st b32 D[$r0] reg /*
-*/     clear b32 $r0
-#endif
-
-#define st(size, addr, reg) /*
-*/     movw $r0 addr /*
-*/     st size D[$r0] reg /*
-*/     clear b32 $r0
-
-#define ld(size, reg, addr) /*
-*/     movw $r0 addr /*
-*/     ld size reg D[$r0] /*
-*/     clear b32 $r0
-
-// does a 64+64 -> 64 unsigned addition (C = A + B)
-#define addu64(reg_a_c_hi, reg_a_c_lo, b_hi, b_lo) /*
-*/    add b32 reg_a_c_lo b_lo /*
-*/    adc b32 reg_a_c_hi b_hi
-
-// does a 64+64 -> 64 substraction (C = A - B)
-#define subu64(reg_a_c_hi, reg_a_c_lo, b_hi, b_lo) /*
-*/    sub b32 reg_a_c_lo b_lo /*
-*/    sbb b32 reg_a_c_hi b_hi
diff --git a/drivers/gpu/drm/nouveau/core/subdev/pwr/fuc/memx.fuc b/drivers/gpu/drm/nouveau/core/subdev/pwr/fuc/memx.fuc
deleted file mode 100644 (file)
index ec03f9a..0000000
+++ /dev/null
@@ -1,447 +0,0 @@
-/*
- * Copyright 2013 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
- */
-
-#ifdef INCLUDE_PROC
-process(PROC_MEMX, #memx_init, #memx_recv)
-#endif
-
-/******************************************************************************
- * MEMX data segment
- *****************************************************************************/
-#ifdef INCLUDE_DATA
-.equ #memx_opcode 0
-.equ #memx_header 2
-.equ #memx_length 4
-.equ #memx_func   8
-
-#define handler(cmd,hdr,len,func) /*
-*/     .b16 MEMX_##cmd /*
-*/     .b16 hdr /*
-*/     .b16 len /*
-*/      .b16 0 /*
-*/     .b32 func
-
-memx_func_head:
-handler(ENTER , 0x0000, 0x0000, #memx_func_enter)
-memx_func_next:
-handler(LEAVE , 0x0000, 0x0000, #memx_func_leave)
-handler(WR32  , 0x0000, 0x0002, #memx_func_wr32)
-handler(WAIT  , 0x0004, 0x0000, #memx_func_wait)
-handler(DELAY , 0x0001, 0x0000, #memx_func_delay)
-handler(VBLANK, 0x0001, 0x0000, #memx_func_wait_vblank)
-handler(TRAIN , 0x0000, 0x0000, #memx_func_train)
-memx_func_tail:
-
-.equ #memx_func_size #memx_func_next - #memx_func_head
-.equ #memx_func_num (#memx_func_tail - #memx_func_head) / #memx_func_size
-
-memx_ts_start:
-.b32 0
-memx_ts_end:
-.b32 0
-
-memx_data_head:
-.skip 0x0800
-memx_data_tail:
-
-memx_train_head:
-.skip 0x0100
-memx_train_tail:
-#endif
-
-/******************************************************************************
- * MEMX code segment
- *****************************************************************************/
-#ifdef INCLUDE_CODE
-// description
-//
-// $r15 - current (memx)
-// $r4  - packet length
-// $r3  - opcode desciption
-// $r0  - zero
-memx_func_enter:
-#if NVKM_PPWR_CHIPSET == GT215
-       movw $r8 0x1610
-       nv_rd32($r7, $r8)
-       imm32($r6, 0xfffffffc)
-       and $r7 $r6
-       movw $r6 0x2
-       or $r7 $r6
-       nv_wr32($r8, $r7)
-#else
-       movw $r6 0x001620
-       imm32($r7, ~0x00000aa2);
-       nv_rd32($r8, $r6)
-       and $r8 $r7
-       nv_wr32($r6, $r8)
-
-       imm32($r7, ~0x00000001)
-       nv_rd32($r8, $r6)
-       and $r8 $r7
-       nv_wr32($r6, $r8)
-
-       movw $r6 0x0026f0
-       nv_rd32($r8, $r6)
-       and $r8 $r7
-       nv_wr32($r6, $r8)
-#endif
-
-       mov $r6 NV_PPWR_OUTPUT_SET_FB_PAUSE
-       nv_iowr(NV_PPWR_OUTPUT_SET, $r6)
-       memx_func_enter_wait:
-               nv_iord($r6, NV_PPWR_OUTPUT)
-               and $r6 NV_PPWR_OUTPUT_FB_PAUSE
-               bra z #memx_func_enter_wait
-
-       nv_iord($r6, NV_PPWR_TIMER_LOW)
-       st b32 D[$r0 + #memx_ts_start] $r6
-       ret
-
-// description
-//
-// $r15 - current (memx)
-// $r4  - packet length
-// $r3  - opcode desciption
-// $r0  - zero
-memx_func_leave:
-       nv_iord($r6, NV_PPWR_TIMER_LOW)
-       st b32 D[$r0 + #memx_ts_end] $r6
-
-       mov $r6 NV_PPWR_OUTPUT_CLR_FB_PAUSE
-       nv_iowr(NV_PPWR_OUTPUT_CLR, $r6)
-       memx_func_leave_wait:
-               nv_iord($r6, NV_PPWR_OUTPUT)
-               and $r6 NV_PPWR_OUTPUT_FB_PAUSE
-               bra nz #memx_func_leave_wait
-
-#if NVKM_PPWR_CHIPSET == GT215
-       movw $r8 0x1610
-       nv_rd32($r7, $r8)
-       imm32($r6, 0xffffffcc)
-       and $r7 $r6
-       nv_wr32($r8, $r7)
-#else
-       movw $r6 0x0026f0
-       imm32($r7, 0x00000001)
-       nv_rd32($r8, $r6)
-       or $r8 $r7
-       nv_wr32($r6, $r8)
-
-       movw $r6 0x001620
-       nv_rd32($r8, $r6)
-       or $r8 $r7
-       nv_wr32($r6, $r8)
-
-       imm32($r7, 0x00000aa2);
-       nv_rd32($r8, $r6)
-       or $r8 $r7
-       nv_wr32($r6, $r8)
-#endif
-       ret
-
-#if NVKM_PPWR_CHIPSET < GF119
-// description
-//
-// $r15 - current (memx)
-// $r4  - packet length
-//     +00: head to wait for vblank on
-// $r3  - opcode desciption
-// $r0  - zero
-memx_func_wait_vblank:
-       ld b32 $r6 D[$r1 + 0x00]
-       cmp b32 $r6 0x0
-       bra z #memx_func_wait_vblank_head0
-       cmp b32 $r6 0x1
-       bra z #memx_func_wait_vblank_head1
-       bra #memx_func_wait_vblank_fini
-
-       memx_func_wait_vblank_head1:
-       movw $r7 0x20
-       bra #memx_func_wait_vblank_0
-
-       memx_func_wait_vblank_head0:
-       movw $r7 0x8
-
-       memx_func_wait_vblank_0:
-               nv_iord($r6, NV_PPWR_INPUT)
-               and $r6 $r7
-               bra nz #memx_func_wait_vblank_0
-
-       memx_func_wait_vblank_1:
-               nv_iord($r6, NV_PPWR_INPUT)
-               and $r6 $r7
-               bra z #memx_func_wait_vblank_1
-
-       memx_func_wait_vblank_fini:
-       add b32 $r1 0x4
-       ret
-
-#else
-
-// XXX: currently no-op
-//
-// $r15 - current (memx)
-// $r4  - packet length
-//     +00: head to wait for vblank on
-// $r3  - opcode desciption
-// $r0  - zero
-memx_func_wait_vblank:
-       add b32 $r1 0x4
-       ret
-
-#endif
-
-// description
-//
-// $r15 - current (memx)
-// $r4  - packet length
-//     +00*n: addr
-//     +04*n: data
-// $r3  - opcode desciption
-// $r0  - zero
-memx_func_wr32:
-       ld b32 $r6 D[$r1 + 0x00]
-       ld b32 $r5 D[$r1 + 0x04]
-       add b32 $r1 0x08
-       nv_wr32($r6, $r5)
-       sub b32 $r4 0x02
-       bra nz #memx_func_wr32
-       ret
-
-// description
-//
-// $r15 - current (memx)
-// $r4  - packet length
-//     +00: addr
-//     +04: mask
-//     +08: data
-//     +0c: timeout (ns)
-// $r3  - opcode desciption
-// $r0  - zero
-memx_func_wait:
-       nv_iord($r8, NV_PPWR_TIMER_LOW)
-       ld b32 $r14 D[$r1 + 0x00]
-       ld b32 $r13 D[$r1 + 0x04]
-       ld b32 $r12 D[$r1 + 0x08]
-       ld b32 $r11 D[$r1 + 0x0c]
-       add b32 $r1 0x10
-       call(wait)
-       ret
-
-// description
-//
-// $r15 - current (memx)
-// $r4  - packet length
-//     +00: time (ns)
-// $r3  - opcode desciption
-// $r0  - zero
-memx_func_delay:
-       ld b32 $r14 D[$r1 + 0x00]
-       add b32 $r1 0x04
-       call(nsec)
-       ret
-
-// description
-//
-// $r15 - current (memx)
-// $r4  - packet length
-// $r3  - opcode desciption
-// $r0  - zero
-memx_func_train:
-#if NVKM_PPWR_CHIPSET == GT215
-// $r5 - outer loop counter
-// $r6 - inner loop counter
-// $r7 - entry counter (#memx_train_head + $r7)
-       movw $r5 0x3
-       movw $r7 0x0
-
-// Read random memory to wake up... things
-       imm32($r9, 0x700000)
-       nv_rd32($r8,$r9)
-       movw $r14 0x2710
-       call(nsec)
-
-       memx_func_train_loop_outer:
-               mulu $r8 $r5 0x101
-               sethi $r8 0x02000000
-               imm32($r9, 0x1111e0)
-               nv_wr32($r9, $r8)
-               push $r5
-
-               movw $r6 0x0
-               memx_func_train_loop_inner:
-                       movw $r8 0x1111
-                       mulu $r9 $r6 $r8
-                       shl b32 $r8 $r9 0x10
-                       or $r8 $r9
-                       imm32($r9, 0x100720)
-                       nv_wr32($r9, $r8)
-
-                       imm32($r9, 0x100080)
-                       nv_rd32($r8, $r9)
-                       or $r8 $r8 0x20
-                       nv_wr32($r9, $r8)
-
-                       imm32($r9, 0x10053c)
-                       imm32($r8, 0x80003002)
-                       nv_wr32($r9, $r8)
-
-                       imm32($r14, 0x100560)
-                       imm32($r13, 0x80000000)
-                       add b32 $r12 $r13 0
-                       imm32($r11, 0x001e8480)
-                       call(wait)
-
-                       // $r5 - inner inner loop counter
-                       // $r9 - result
-                       movw $r5 0
-                       imm32($r9, 0x8300ffff)
-                       memx_func_train_loop_4x:
-                               imm32($r10, 0x100080)
-                               nv_rd32($r8, $r10)
-                               imm32($r11, 0xffffffdf)
-                               and $r8 $r11
-                               nv_wr32($r10, $r8)
-
-                               imm32($r10, 0x10053c)
-                               imm32($r8, 0x80003002)
-                               nv_wr32($r10, $r8)
-
-                               imm32($r14, 0x100560)
-                               imm32($r13, 0x80000000)
-                               mov b32 $r12 $r13
-                               imm32($r11, 0x00002710)
-                               call(wait)
-
-                               nv_rd32($r13, $r14)
-                               and $r9 $r9 $r13
-
-                               add b32 $r5 1
-                               cmp b16 $r5 0x4
-                               bra l #memx_func_train_loop_4x
-
-                       add b32 $r10 $r7 #memx_train_head
-                       st b32 D[$r10 + 0] $r9
-                       add b32 $r6 1
-                       add b32 $r7 4
-
-                       cmp b16 $r6 0x10
-                       bra l #memx_func_train_loop_inner
-
-               pop $r5
-               add b32 $r5 1
-               cmp b16 $r5 7
-               bra l #memx_func_train_loop_outer
-
-#endif
-       ret
-
-// description
-//
-// $r15 - current (memx)
-// $r14 - sender process name
-// $r13 - message (exec)
-// $r12 - head of script
-// $r11 - tail of script
-// $r0  - zero
-memx_exec:
-       push $r14
-       push $r13
-       mov b32 $r1 $r12
-       mov b32 $r2 $r11
-
-       memx_exec_next:
-               // fetch the packet header
-               ld b32 $r3 D[$r1]
-               add b32 $r1 4
-               extr $r4 $r3 16:31
-               extr $r3 $r3 0:15
-
-               // execute the opcode handler
-               sub b32 $r3 1
-               mulu $r3 #memx_func_size
-               ld b32 $r5 D[$r3 + #memx_func_head + #memx_func]
-               call $r5
-
-               // keep going, if we haven't reached the end
-               cmp b32 $r1 $r2
-               bra l #memx_exec_next
-
-       // send completion reply
-       ld b32 $r11 D[$r0 + #memx_ts_start]
-       ld b32 $r12 D[$r0 + #memx_ts_end]
-       sub b32 $r12 $r11
-       nv_iord($r11, NV_PPWR_INPUT)
-       pop $r13
-       pop $r14
-       call(send)
-       ret
-
-// description
-//
-// $r15 - current (memx)
-// $r14 - sender process name
-// $r13 - message
-// $r12 - data0
-// $r11 - data1
-// $r0  - zero
-memx_info:
-       cmp b16 $r12 0x1
-       bra e #memx_info_train
-
-       memx_info_data:
-       mov $r12 #memx_data_head
-       mov $r11 #memx_data_tail - #memx_data_head
-       bra #memx_info_send
-
-       memx_info_train:
-       mov $r12 #memx_train_head
-       mov $r11 #memx_train_tail - #memx_train_head
-
-       memx_info_send:
-       call(send)
-       ret
-
-// description
-//
-// $r15 - current (memx)
-// $r14 - sender process name
-// $r13 - message
-// $r12 - data0
-// $r11 - data1
-// $r0  - zero
-memx_recv:
-       cmp b32 $r13 MEMX_MSG_EXEC
-       bra e #memx_exec
-       cmp b32 $r13 MEMX_MSG_INFO
-       bra e #memx_info
-       ret
-
-// description
-//
-// $r15 - current (memx)
-// $r0  - zero
-memx_init:
-       ret
-#endif
diff --git a/drivers/gpu/drm/nouveau/core/subdev/pwr/fuc/nv108.fuc b/drivers/gpu/drm/nouveau/core/subdev/pwr/fuc/nv108.fuc
deleted file mode 100644 (file)
index b439519..0000000
+++ /dev/null
@@ -1,70 +0,0 @@
-/*
- * Copyright 2013 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 NVKM_PPWR_CHIPSET GK208
-#define HW_TICKS_PER_US 324
-
-#define NVKM_FALCON_PC24
-#define NVKM_FALCON_UNSHIFTED_IO
-//#define NVKM_FALCON_MMIO_UAS
-//#define NVKM_FALCON_MMIO_TRAP
-
-#include "macros.fuc"
-
-.section #nv108_pwr_data
-#define INCLUDE_PROC
-#include "kernel.fuc"
-#include "arith.fuc"
-#include "host.fuc"
-#include "memx.fuc"
-#include "perf.fuc"
-#include "i2c_.fuc"
-#include "test.fuc"
-#include "idle.fuc"
-#undef INCLUDE_PROC
-
-#define INCLUDE_DATA
-#include "kernel.fuc"
-#include "arith.fuc"
-#include "host.fuc"
-#include "memx.fuc"
-#include "perf.fuc"
-#include "i2c_.fuc"
-#include "test.fuc"
-#include "idle.fuc"
-#undef INCLUDE_DATA
-.align 256
-
-.section #nv108_pwr_code
-#define INCLUDE_CODE
-#include "kernel.fuc"
-#include "arith.fuc"
-#include "host.fuc"
-#include "memx.fuc"
-#include "perf.fuc"
-#include "i2c_.fuc"
-#include "test.fuc"
-#include "idle.fuc"
-#undef INCLUDE_CODE
-.align 256
diff --git a/drivers/gpu/drm/nouveau/core/subdev/pwr/fuc/nv108.fuc.h b/drivers/gpu/drm/nouveau/core/subdev/pwr/fuc/nv108.fuc.h
deleted file mode 100644 (file)
index 713e11e..0000000
+++ /dev/null
@@ -1,1731 +0,0 @@
-uint32_t nv108_pwr_data[] = {
-/* 0x0000: proc_kern */
-       0x52544e49,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-/* 0x0058: proc_list_head */
-       0x54534f48,
-       0x00000453,
-       0x00000404,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x584d454d,
-       0x0000062d,
-       0x0000061f,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x46524550,
-       0x00000631,
-       0x0000062f,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x5f433249,
-       0x00000a35,
-       0x000008dc,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x54534554,
-       0x00000a56,
-       0x00000a37,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x454c4449,
-       0x00000a61,
-       0x00000a5f,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-/* 0x0268: proc_list_tail */
-/* 0x0268: time_prev */
-       0x00000000,
-/* 0x026c: time_next */
-       0x00000000,
-/* 0x0270: fifo_queue */
-       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,
-/* 0x02f0: rfifo_queue */
-       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,
-/* 0x0370: memx_func_head */
-       0x00000001,
-       0x00000000,
-       0x00000483,
-/* 0x037c: memx_func_next */
-       0x00000002,
-       0x00000000,
-       0x00000500,
-       0x00000003,
-       0x00000002,
-       0x00000580,
-       0x00040004,
-       0x00000000,
-       0x0000059d,
-       0x00010005,
-       0x00000000,
-       0x000005b7,
-       0x00010006,
-       0x00000000,
-       0x0000057b,
-       0x00000007,
-       0x00000000,
-       0x000005c3,
-/* 0x03c4: memx_func_tail */
-/* 0x03c4: memx_ts_start */
-       0x00000000,
-/* 0x03c8: memx_ts_end */
-       0x00000000,
-/* 0x03cc: memx_data_head */
-       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,
-       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,
-       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,
-       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,
-       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,
-       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,
-       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,
-       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,
-/* 0x0bcc: memx_data_tail */
-/* 0x0bcc: memx_train_head */
-       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,
-/* 0x0ccc: memx_train_tail */
-/* 0x0ccc: i2c_scl_map */
-       0x00000400,
-       0x00000800,
-       0x00001000,
-       0x00002000,
-       0x00004000,
-       0x00008000,
-       0x00010000,
-       0x00020000,
-       0x00040000,
-       0x00080000,
-/* 0x0cf4: i2c_sda_map */
-       0x00100000,
-       0x00200000,
-       0x00400000,
-       0x00800000,
-       0x01000000,
-       0x02000000,
-       0x04000000,
-       0x08000000,
-       0x10000000,
-       0x20000000,
-       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,
-};
-
-uint32_t nv108_pwr_code[] = {
-       0x031c0ef5,
-/* 0x0004: rd32 */
-       0xf607a040,
-       0x04bd000e,
-       0xd3f0010d,
-       0x07ac4001,
-       0xbd000df6,
-/* 0x0019: rd32_wait */
-       0x07ac4d04,
-       0xf100ddcf,
-       0xf47000d4,
-       0xa44df61b,
-       0x00ddcf07,
-/* 0x002e: wr32 */
-       0xa04000f8,
-       0x000ef607,
-       0xa44004bd,
-       0x000df607,
-       0x020d04bd,
-       0xf0f0d5f0,
-       0xac4001d3,
-       0x000df607,
-/* 0x004e: wr32_wait */
-       0xac4d04bd,
-       0x00ddcf07,
-       0x7000d4f1,
-       0xf8f61bf4,
-/* 0x005d: nsec */
-       0xf990f900,
-       0xcf2c0880,
-/* 0x0066: nsec_loop */
-       0x2c090088,
-       0xbb0099cf,
-       0x9ea60298,
-       0xfcf61ef4,
-       0xf890fc80,
-/* 0x0079: wait */
-       0xf990f900,
-       0xcf2c0880,
-/* 0x0082: wait_loop */
-       0xeeb20088,
-       0x0000047e,
-       0xadfddab2,
-       0xf4aca604,
-       0x2c09100b,
-       0xbb0099cf,
-       0x9ba60298,
-/* 0x009f: wait_done */
-       0xfce61ef4,
-       0xf890fc80,
-/* 0x00a5: intr_watchdog */
-       0x03e99800,
-       0xf40096b0,
-       0x0a98280b,
-       0x029abb9a,
-       0x0d0e1cf4,
-       0x02617e01,
-       0xf494bd00,
-/* 0x00c2: intr_watchdog_next_time */
-       0x0a98140e,
-       0x00a6b09b,
-       0xa6080bf4,
-       0x061cf49a,
-/* 0x00d0: intr_watchdog_next_time_set */
-/* 0x00d3: intr_watchdog_next_proc */
-       0xb59b09b5,
-       0xe0b603e9,
-       0x68e6b158,
-       0xc81bf402,
-/* 0x00e2: intr */
-       0x00f900f8,
-       0x80f904bd,
-       0xa0f990f9,
-       0xc0f9b0f9,
-       0xe0f9d0f9,
-       0x000ff0f9,
-       0xf90188fe,
-       0x04504880,
-       0xb60088cf,
-       0x50400180,
-       0x0008f604,
-       0x080804bd,
-       0xc40088cf,
-       0x0bf40289,
-       0x9b00b51f,
-       0xa57e580e,
-       0x09980000,
-       0x0096b09b,
-       0x000d0bf4,
-       0x0009f634,
-       0x09b504bd,
-/* 0x0135: intr_skip_watchdog */
-       0x0089e49a,
-       0x360bf408,
-       0xcf068849,
-       0x9ac40099,
-       0x220bf402,
-       0xcf04c04c,
-       0xc0f900cc,
-       0xf14f484e,
-       0x0d5453e3,
-       0x02c27e00,
-       0x40c0fc00,
-       0x0cf604c0,
-/* 0x0167: intr_subintr_skip_fifo */
-       0x4004bd00,
-       0x09f60688,
-/* 0x016f: intr_skip_subintr */
-       0xc404bd00,
-       0x0bf42089,
-       0xbfa4f107,
-/* 0x0179: intr_skip_pause */
-       0x4089c4ff,
-       0xf1070bf4,
-/* 0x0183: intr_skip_user0 */
-       0x00ffbfa4,
-       0x0008f604,
-       0x80fc04bd,
-       0xfc0088fe,
-       0xfce0fcf0,
-       0xfcc0fcd0,
-       0xfca0fcb0,
-       0xfc80fc90,
-       0x0032f400,
-/* 0x01a6: ticks_from_ns */
-       0xc0f901f8,
-       0xd7f1b0f9,
-       0xd3f00144,
-       0x7721f500,
-       0xe8ccec03,
-       0x00b4b003,
-       0xec120bf4,
-       0xf103e8ee,
-       0xf00144d7,
-       0x21f500d3,
-/* 0x01ce: ticks_from_ns_quit */
-       0xceb20377,
-       0xc0fcb0fc,
-/* 0x01d6: ticks_from_us */
-       0xc0f900f8,
-       0xd7f1b0f9,
-       0xd3f00144,
-       0x7721f500,
-       0xb0ceb203,
-       0x0bf400b4,
-/* 0x01ef: ticks_from_us_quit */
-       0xfce4bd05,
-       0xf8c0fcb0,
-/* 0x01f5: ticks_to_us */
-       0x44d7f100,
-       0x00d3f001,
-       0xf8ecedff,
-/* 0x0201: timer */
-       0xf990f900,
-       0x1032f480,
-       0xb003f898,
-       0x1cf40086,
-       0x0084bd4a,
-       0x0008f638,
-       0x340804bd,
-       0x980088cf,
-       0x98bb9a09,
-       0x00e9bb02,
-       0x0803feb5,
-       0x0088cf08,
-       0xf40284f0,
-       0x34081c1b,
-       0xa60088cf,
-       0x080bf4e0,
-       0x1cf4e8a6,
-/* 0x0245: timer_reset */
-       0xf634000d,
-       0x04bd000e,
-/* 0x024f: timer_enable */
-       0x089a0eb5,
-       0xf6380001,
-       0x04bd0008,
-/* 0x0258: timer_done */
-       0xfc1031f4,
-       0xf890fc80,
-/* 0x0261: send_proc */
-       0xf980f900,
-       0x05e89890,
-       0xf004e998,
-       0x89a60486,
-       0xc42a0bf4,
-       0x88940398,
-       0x1880b604,
-       0x98008ebb,
-       0x8ab500fa,
-       0x018db500,
-       0xb5028cb5,
-       0x90b6038b,
-       0x0794f001,
-       0xf404e9b5,
-/* 0x029a: send_done */
-       0x90fc0231,
-       0x00f880fc,
-/* 0x02a0: find */
-       0x580880f9,
-/* 0x02a7: find_loop */
-       0x980131f4,
-       0xaea6008a,
-       0xb6100bf4,
-       0x86b15880,
-       0x1bf40268,
-       0x0132f4f1,
-/* 0x02bc: find_done */
-       0x80fc8eb2,
-/* 0x02c2: send */
-       0xa07e00f8,
-       0x01f40002,
-/* 0x02cb: recv */
-       0xf900f89b,
-       0x9880f990,
-       0xe99805e8,
-       0x0132f404,
-       0x0bf489a6,
-       0x0389c43c,
-       0xf00180b6,
-       0xe8b50784,
-       0x02ea9805,
-       0x8ffef0f9,
-       0xb2f0f901,
-       0x049994ef,
-       0xb600e9bb,
-       0xeb9818e0,
-       0x02ec9803,
-       0x9801ed98,
-       0xa5f900ee,
-       0xf8fef0fc,
-       0x0131f400,
-/* 0x0316: recv_done */
-       0x80fcf0fc,
-       0x00f890fc,
-/* 0x031c: init */
-       0xcf010841,
-       0x11e70011,
-       0x14b60109,
-       0x0014fe08,
-       0xf000e041,
-       0x1c000013,
-       0xbd0001f6,
-       0x00ff0104,
-       0x0001f614,
-       0x020104bd,
-       0x080015f1,
-       0x01f61000,
-       0x4104bd00,
-       0x13f000e2,
-       0x0010fe00,
-       0x011031f4,
-       0xf6380001,
-       0x04bd0001,
-/* 0x0366: init_proc */
-       0xf198580f,
-       0x0016b001,
-       0xf9fa0bf4,
-       0x58f0b615,
-/* 0x0377: mulu32_32_64 */
-       0xf9f20ef4,
-       0xf920f910,
-       0x9540f930,
-       0xd29510e1,
-       0xbdc4bd10,
-       0xc0edffb4,
-       0xb2301dff,
-       0xff34f134,
-       0x1034b6ff,
-       0xbb1045b6,
-       0xb4bb00c3,
-       0x30e2ff01,
-       0x34f134b2,
-       0x34b6ffff,
-       0x1045b610,
-       0xbb00c3bb,
-       0x12ff01b4,
-       0x00b3bb30,
-       0x30fc40fc,
-       0x10fc20fc,
-/* 0x03c6: host_send */
-       0xb04100f8,
-       0x0011cf04,
-       0xcf04a042,
-       0x12a60022,
-       0xc42e0bf4,
-       0xee94071e,
-       0x70e0b704,
-       0x03eb9802,
-       0x9802ec98,
-       0xee9801ed,
-       0x02c27e00,
-       0x0110b600,
-       0x400f1ec4,
-       0x0ef604b0,
-       0xf404bd00,
-/* 0x0402: host_send_done */
-       0x00f8c70e,
-/* 0x0404: host_recv */
-       0xf14e4941,
-       0xa6525413,
-       0xb90bf4e1,
-/* 0x0410: host_recv_wait */
-       0xcf04cc41,
-       0xc8420011,
-       0x0022cf04,
-       0xa60816f0,
-       0xef0bf412,
-       0xb60723c4,
-       0x30b70434,
-       0x3bb502f0,
-       0x023cb503,
-       0xb5013db5,
-       0x20b6003e,
-       0x0f24f001,
-       0xf604c840,
-       0x04bd0002,
-       0x00004002,
-       0xbd0002f6,
-/* 0x0453: host_init */
-       0x4100f804,
-       0x14b60080,
-       0x7015f110,
-       0x04d04002,
-       0xbd0001f6,
-       0x00804104,
-       0xf11014b6,
-       0x4002f015,
-       0x01f604dc,
-       0x0104bd00,
-       0x04c44001,
-       0xbd0001f6,
-/* 0x0483: memx_func_enter */
-       0xf100f804,
-       0xf1162067,
-       0xf1f55d77,
-       0xb2ffff73,
-       0x00047e6e,
-       0xfdd8b200,
-       0x60f90487,
-       0xd0fc80f9,
-       0x2e7ee0fc,
-       0x77f10000,
-       0x73f1fffe,
-       0x6eb2ffff,
-       0x0000047e,
-       0x87fdd8b2,
-       0xf960f904,
-       0xfcd0fc80,
-       0x002e7ee0,
-       0xf067f100,
-       0x7e6eb226,
-       0xb2000004,
-       0x0487fdd8,
-       0x80f960f9,
-       0xe0fcd0fc,
-       0x00002e7e,
-       0xe0400406,
-       0x0006f607,
-/* 0x04ea: memx_func_enter_wait */
-       0xc04604bd,
-       0x0066cf07,
-       0xf40464f0,
-       0x2c06f70b,
-       0xb50066cf,
-       0x00f8f106,
-/* 0x0500: memx_func_leave */
-       0x66cf2c06,
-       0xf206b500,
-       0xe4400406,
-       0x0006f607,
-/* 0x0512: memx_func_leave_wait */
-       0xc04604bd,
-       0x0066cf07,
-       0xf40464f0,
-       0x67f1f71b,
-       0x77f126f0,
-       0x73f00001,
-       0x7e6eb200,
-       0xb2000004,
-       0x0587fdd8,
-       0x80f960f9,
-       0xe0fcd0fc,
-       0x00002e7e,
-       0x162067f1,
-       0x047e6eb2,
-       0xd8b20000,
-       0xf90587fd,
-       0xfc80f960,
-       0x7ee0fcd0,
-       0xf100002e,
-       0xf00aa277,
-       0x6eb20073,
-       0x0000047e,
-       0x87fdd8b2,
-       0xf960f905,
-       0xfcd0fc80,
-       0x002e7ee0,
-/* 0x057b: memx_func_wait_vblank */
-       0xb600f800,
-       0x00f80410,
-/* 0x0580: memx_func_wr32 */
-       0x98001698,
-       0x10b60115,
-       0xf960f908,
-       0xfcd0fc50,
-       0x002e7ee0,
-       0x0242b600,
-       0xf8e81bf4,
-/* 0x059d: memx_func_wait */
-       0xcf2c0800,
-       0x1e980088,
-       0x011d9800,
-       0x98021c98,
-       0x10b6031b,
-       0x00797e10,
-/* 0x05b7: memx_func_delay */
-       0x9800f800,
-       0x10b6001e,
-       0x005d7e04,
-/* 0x05c3: memx_func_train */
-       0xf800f800,
-/* 0x05c5: memx_exec */
-       0xf9e0f900,
-       0xb2c1b2d0,
-/* 0x05cd: memx_exec_next */
-       0x001398b2,
-       0xe70410b6,
-       0xe701f034,
-       0xb601e033,
-       0x30f00132,
-       0xde35980c,
-       0x12a655f9,
-       0x98e51ef4,
-       0x0c98f10b,
-       0x02cbbbf2,
-       0xcf07c44b,
-       0xd0fc00bb,
-       0xc27ee0fc,
-       0x00f80002,
-/* 0x0604: memx_info */
-       0xf401c670,
-/* 0x060a: memx_info_data */
-       0xcc4c0c0b,
-       0x08004b03,
-/* 0x0613: memx_info_train */
-       0x4c090ef4,
-       0x004b0bcc,
-/* 0x0619: memx_info_send */
-       0x02c27e01,
-/* 0x061f: memx_recv */
-       0xb000f800,
-       0x0bf401d6,
-       0x00d6b0a3,
-       0xf8dc0bf4,
-/* 0x062d: memx_init */
-/* 0x062f: perf_recv */
-       0xf800f800,
-/* 0x0631: perf_init */
-/* 0x0633: i2c_drive_scl */
-       0xb000f800,
-       0x0bf40036,
-       0x07e0400d,
-       0xbd0001f6,
-/* 0x0643: i2c_drive_scl_lo */
-       0x4000f804,
-       0x01f607e4,
-       0xf804bd00,
-/* 0x064d: i2c_drive_sda */
-       0x0036b000,
-       0x400d0bf4,
-       0x02f607e0,
-       0xf804bd00,
-/* 0x065d: i2c_drive_sda_lo */
-       0x07e44000,
-       0xbd0002f6,
-/* 0x0667: i2c_sense_scl */
-       0xf400f804,
-       0xc4430132,
-       0x0033cf07,
-       0xf40431fd,
-       0x31f4060b,
-/* 0x0679: i2c_sense_scl_done */
-/* 0x067b: i2c_sense_sda */
-       0xf400f801,
-       0xc4430132,
-       0x0033cf07,
-       0xf40432fd,
-       0x31f4060b,
-/* 0x068d: i2c_sense_sda_done */
-/* 0x068f: i2c_raise_scl */
-       0xf900f801,
-       0x08984440,
-       0x337e0103,
-/* 0x069a: i2c_raise_scl_wait */
-       0xe84e0006,
-       0x005d7e03,
-       0x06677e00,
-       0x0901f400,
-       0xf40142b6,
-/* 0x06ae: i2c_raise_scl_done */
-       0x40fcef1b,
-/* 0x06b2: i2c_start */
-       0x677e00f8,
-       0x11f40006,
-       0x067b7e0d,
-       0x0611f400,
-/* 0x06c3: i2c_start_rep */
-       0x032e0ef4,
-       0x06337e00,
-       0x7e010300,
-       0xbb00064d,
-       0x65b60076,
-       0x9450f904,
-       0x56bb0465,
-       0xfd50bd02,
-       0x50fc0475,
-       0x00068f7e,
-       0xf40464b6,
-/* 0x06ee: i2c_start_send */
-       0x00031d11,
-       0x00064d7e,
-       0x7e13884e,
-       0x0300005d,
-       0x06337e00,
-       0x13884e00,
-       0x00005d7e,
-/* 0x0708: i2c_start_out */
-/* 0x070a: i2c_stop */
-       0x000300f8,
-       0x0006337e,
-       0x4d7e0003,
-       0xe84e0006,
-       0x005d7e03,
-       0x7e010300,
-       0x4e000633,
-       0x5d7e1388,
-       0x01030000,
-       0x00064d7e,
-       0x7e13884e,
-       0xf800005d,
-/* 0x0739: i2c_bitw */
-       0x064d7e00,
-       0x03e84e00,
-       0x00005d7e,
-       0xb60076bb,
-       0x50f90465,
-       0xbb046594,
-       0x50bd0256,
-       0xfc0475fd,
-       0x068f7e50,
-       0x0464b600,
-       0x4e1711f4,
-       0x5d7e1388,
-       0x00030000,
-       0x0006337e,
-       0x7e13884e,
-/* 0x0777: i2c_bitw_out */
-       0xf800005d,
-/* 0x0779: i2c_bitr */
-       0x7e010300,
-       0x4e00064d,
-       0x5d7e03e8,
-       0x76bb0000,
-       0x0465b600,
-       0x659450f9,
-       0x0256bb04,
-       0x75fd50bd,
-       0x7e50fc04,
-       0xb600068f,
-       0x11f40464,
-       0x067b7e1a,
-       0x7e000300,
-       0x4e000633,
-       0x5d7e1388,
-       0x3cf00000,
-       0x0131f401,
-/* 0x07bc: i2c_bitr_done */
-/* 0x07be: i2c_get_byte */
-       0x000500f8,
-/* 0x07c2: i2c_get_byte_next */
-       0x54b60804,
-       0x0076bb01,
-       0xf90465b6,
-       0x04659450,
-       0xbd0256bb,
-       0x0475fd50,
-       0x797e50fc,
-       0x64b60007,
-       0x2a11f404,
-       0xb60553fd,
-       0x1bf40142,
-       0xbb0103d8,
-       0x65b60076,
-       0x9450f904,
-       0x56bb0465,
-       0xfd50bd02,
-       0x50fc0475,
-       0x0007397e,
-/* 0x080b: i2c_get_byte_done */
-       0xf80464b6,
-/* 0x080d: i2c_put_byte */
-/* 0x080f: i2c_put_byte_next */
-       0xb6080400,
-       0x54ff0142,
-       0x0076bb38,
-       0xf90465b6,
-       0x04659450,
-       0xbd0256bb,
-       0x0475fd50,
-       0x397e50fc,
-       0x64b60007,
-       0x3411f404,
-       0xf40046b0,
-       0x76bbd81b,
-       0x0465b600,
-       0x659450f9,
-       0x0256bb04,
-       0x75fd50bd,
-       0x7e50fc04,
-       0xb6000779,
-       0x11f40464,
-       0x0076bb0f,
-       0xf40136b0,
-       0x32f4061b,
-/* 0x0865: i2c_put_byte_done */
-/* 0x0867: i2c_addr */
-       0xbb00f801,
-       0x65b60076,
-       0x9450f904,
-       0x56bb0465,
-       0xfd50bd02,
-       0x50fc0475,
-       0x0006b27e,
-       0xf40464b6,
-       0xc3e72911,
-       0x34b6012e,
-       0x0553fd01,
-       0xb60076bb,
-       0x50f90465,
-       0xbb046594,
-       0x50bd0256,
-       0xfc0475fd,
-       0x080d7e50,
-       0x0464b600,
-/* 0x08ac: i2c_addr_done */
-/* 0x08ae: i2c_acquire_addr */
-       0xcec700f8,
-       0x05e4b6f8,
-       0xd014e0b7,
-/* 0x08ba: i2c_acquire */
-       0xae7e00f8,
-       0x047e0008,
-       0xd9f00000,
-       0x002e7e03,
-/* 0x08cb: i2c_release */
-       0x7e00f800,
-       0x7e0008ae,
-       0xf0000004,
-       0x2e7e03da,
-       0x00f80000,
-/* 0x08dc: i2c_recv */
-       0xc70132f4,
-       0x14b6f8c1,
-       0x2816b002,
-       0x01371ff5,
-       0x0cf413b8,
-       0x00329800,
-       0x0ccc13b8,
-       0x00319800,
-       0xf90231f4,
-       0xf9e0f9d0,
-       0x0067f1d0,
-       0x0063f100,
-       0x01679210,
-       0xb60076bb,
-       0x50f90465,
-       0xbb046594,
-       0x50bd0256,
-       0xfc0475fd,
-       0x08ba7e50,
-       0x0464b600,
-       0xd6b0d0fc,
-       0xb01bf500,
-       0xbb000500,
-       0x65b60076,
-       0x9450f904,
-       0x56bb0465,
-       0xfd50bd02,
-       0x50fc0475,
-       0x0008677e,
-       0xf50464b6,
-       0xc700cc11,
-       0x76bbe0c5,
-       0x0465b600,
-       0x659450f9,
-       0x0256bb04,
-       0x75fd50bd,
-       0x7e50fc04,
-       0xb600080d,
-       0x11f50464,
-       0x010500a9,
-       0xb60076bb,
-       0x50f90465,
-       0xbb046594,
-       0x50bd0256,
-       0xfc0475fd,
-       0x08677e50,
-       0x0464b600,
-       0x008711f5,
-       0xb60076bb,
-       0x50f90465,
-       0xbb046594,
-       0x50bd0256,
-       0xfc0475fd,
-       0x07be7e50,
-       0x0464b600,
-       0xcb6711f4,
-       0x76bbe05b,
-       0x0465b600,
-       0x659450f9,
-       0x0256bb04,
-       0x75fd50bd,
-       0x7e50fc04,
-       0xb600070a,
-       0x5bb20464,
-       0x0ef474bd,
-/* 0x09e1: i2c_recv_not_rd08 */
-       0x01d6b041,
-       0x053b1bf4,
-       0x08677e00,
-       0x3211f400,
-       0x7ee0c5c7,
-       0xf400080d,
-       0x00052811,
-       0x0008677e,
-       0xc71f11f4,
-       0x0d7ee0b5,
-       0x11f40008,
-       0x070a7e15,
-       0xc774bd00,
-       0x1bf408c5,
-       0x0232f409,
-/* 0x0a1f: i2c_recv_not_wr08 */
-/* 0x0a1f: i2c_recv_done */
-       0xc7030ef4,
-       0xcb7ef8ce,
-       0xe0fc0008,
-       0x12f4d0fc,
-       0x7e7cb209,
-/* 0x0a33: i2c_recv_exit */
-       0xf80002c2,
-/* 0x0a35: i2c_init */
-/* 0x0a37: test_recv */
-       0x4100f800,
-       0x11cf0458,
-       0x0110b600,
-       0xf6045840,
-       0x04bd0001,
-       0xd900e7f1,
-       0x134fe3f1,
-       0x0002017e,
-/* 0x0a56: test_init */
-       0x004e00f8,
-       0x02017e08,
-/* 0x0a5f: idle_recv */
-       0xf800f800,
-/* 0x0a61: idle */
-       0x0031f400,
-       0xcf045441,
-       0x10b60011,
-       0x04544001,
-       0xbd0001f6,
-/* 0x0a75: idle_loop */
-       0xf4580104,
-/* 0x0a7a: idle_proc */
-/* 0x0a7a: idle_proc_exec */
-       0x10f90232,
-       0xcb7e1eb2,
-       0x10fc0002,
-       0xf40911f4,
-       0x0ef40231,
-/* 0x0a8d: idle_proc_next */
-       0x5810b6f0,
-       0x1bf41fa6,
-       0xe002f4e8,
-       0xf40028f4,
-       0x0000c60e,
-       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/drivers/gpu/drm/nouveau/core/subdev/pwr/fuc/nva3.fuc b/drivers/gpu/drm/nouveau/core/subdev/pwr/fuc/nva3.fuc
deleted file mode 100644 (file)
index daa06c1..0000000
+++ /dev/null
@@ -1,70 +0,0 @@
-/*
- * Copyright 2013 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 NVKM_PPWR_CHIPSET GT215
-#define HW_TICKS_PER_US 203 // should be 202.5
-
-//#define NVKM_FALCON_PC24
-//#define NVKM_FALCON_UNSHIFTED_IO
-//#define NVKM_FALCON_MMIO_UAS
-//#define NVKM_FALCON_MMIO_TRAP
-
-#include "macros.fuc"
-
-.section #nva3_pwr_data
-#define INCLUDE_PROC
-#include "kernel.fuc"
-#include "arith.fuc"
-#include "host.fuc"
-#include "memx.fuc"
-#include "perf.fuc"
-#include "i2c_.fuc"
-#include "test.fuc"
-#include "idle.fuc"
-#undef INCLUDE_PROC
-
-#define INCLUDE_DATA
-#include "kernel.fuc"
-#include "arith.fuc"
-#include "host.fuc"
-#include "memx.fuc"
-#include "perf.fuc"
-#include "i2c_.fuc"
-#include "test.fuc"
-#include "idle.fuc"
-#undef INCLUDE_DATA
-.align 256
-
-.section #nva3_pwr_code
-#define INCLUDE_CODE
-#include "kernel.fuc"
-#include "arith.fuc"
-#include "host.fuc"
-#include "memx.fuc"
-#include "perf.fuc"
-#include "i2c_.fuc"
-#include "test.fuc"
-#include "idle.fuc"
-#undef INCLUDE_CODE
-.align 256
diff --git a/drivers/gpu/drm/nouveau/core/subdev/pwr/fuc/nva3.fuc.h b/drivers/gpu/drm/nouveau/core/subdev/pwr/fuc/nva3.fuc.h
deleted file mode 100644 (file)
index d1f9b6c..0000000
+++ /dev/null
@@ -1,1868 +0,0 @@
-uint32_t nva3_pwr_data[] = {
-/* 0x0000: proc_kern */
-       0x52544e49,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-/* 0x0058: proc_list_head */
-       0x54534f48,
-       0x00000512,
-       0x000004af,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x584d454d,
-       0x00000842,
-       0x00000834,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x46524550,
-       0x00000846,
-       0x00000844,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x5f433249,
-       0x00000c76,
-       0x00000b19,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x54534554,
-       0x00000c9f,
-       0x00000c78,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x454c4449,
-       0x00000cab,
-       0x00000ca9,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-/* 0x0268: proc_list_tail */
-/* 0x0268: time_prev */
-       0x00000000,
-/* 0x026c: time_next */
-       0x00000000,
-/* 0x0270: fifo_queue */
-       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,
-/* 0x02f0: rfifo_queue */
-       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,
-/* 0x0370: memx_func_head */
-       0x00000001,
-       0x00000000,
-       0x00000551,
-/* 0x037c: memx_func_next */
-       0x00000002,
-       0x00000000,
-       0x000005a8,
-       0x00000003,
-       0x00000002,
-       0x0000063a,
-       0x00040004,
-       0x00000000,
-       0x00000656,
-       0x00010005,
-       0x00000000,
-       0x00000673,
-       0x00010006,
-       0x00000000,
-       0x000005f8,
-       0x00000007,
-       0x00000000,
-       0x0000067e,
-/* 0x03c4: memx_func_tail */
-/* 0x03c4: memx_ts_start */
-       0x00000000,
-/* 0x03c8: memx_ts_end */
-       0x00000000,
-/* 0x03cc: memx_data_head */
-       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,
-       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,
-       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,
-       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,
-       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,
-       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,
-       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,
-       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,
-/* 0x0bcc: memx_data_tail */
-/* 0x0bcc: memx_train_head */
-       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,
-/* 0x0ccc: memx_train_tail */
-/* 0x0ccc: i2c_scl_map */
-       0x00001000,
-       0x00004000,
-       0x00010000,
-       0x00000100,
-       0x00040000,
-       0x00100000,
-       0x00400000,
-       0x01000000,
-       0x04000000,
-       0x10000000,
-/* 0x0cf4: i2c_sda_map */
-       0x00002000,
-       0x00008000,
-       0x00020000,
-       0x00000200,
-       0x00080000,
-       0x00200000,
-       0x00800000,
-       0x02000000,
-       0x08000000,
-       0x20000000,
-/* 0x0d1c: i2c_ctrl */
-       0x0000e138,
-       0x0000e150,
-       0x0000e168,
-       0x0000e180,
-       0x0000e254,
-       0x0000e274,
-       0x0000e764,
-       0x0000e780,
-       0x0000e79c,
-       0x0000e7b8,
-       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,
-};
-
-uint32_t nva3_pwr_code[] = {
-       0x039e0ef5,
-/* 0x0004: rd32 */
-       0x07a007f1,
-       0xd00604b6,
-       0x04bd000e,
-       0xf001d7f0,
-       0x07f101d3,
-       0x04b607ac,
-       0x000dd006,
-/* 0x0022: rd32_wait */
-       0xd7f104bd,
-       0xd4b607ac,
-       0x00ddcf06,
-       0x7000d4f1,
-       0xf1f21bf4,
-       0xb607a4d7,
-       0xddcf06d4,
-/* 0x003f: wr32 */
-       0xf100f800,
-       0xb607a007,
-       0x0ed00604,
-       0xf104bd00,
-       0xb607a407,
-       0x0dd00604,
-       0xf004bd00,
-       0xd5f002d7,
-       0x01d3f0f0,
-       0x07ac07f1,
-       0xd00604b6,
-       0x04bd000d,
-/* 0x006c: wr32_wait */
-       0x07acd7f1,
-       0xcf06d4b6,
-       0xd4f100dd,
-       0x1bf47000,
-/* 0x007f: nsec */
-       0xf900f8f2,
-       0xf080f990,
-       0x84b62c87,
-       0x0088cf06,
-/* 0x008c: nsec_loop */
-       0xb62c97f0,
-       0x99cf0694,
-       0x0298bb00,
-       0xf4069eb8,
-       0x80fcf11e,
-       0x00f890fc,
-/* 0x00a4: wait */
-       0x80f990f9,
-       0xb62c87f0,
-       0x88cf0684,
-/* 0x00b1: wait_loop */
-       0x02eeb900,
-       0xb90421f4,
-       0xadfd02da,
-       0x06acb804,
-       0xf0150bf4,
-       0x94b62c97,
-       0x0099cf06,
-       0xb80298bb,
-       0x1ef4069b,
-/* 0x00d5: wait_done */
-       0xfc80fcdf,
-/* 0x00db: intr_watchdog */
-       0x9800f890,
-       0x96b003e9,
-       0x2a0bf400,
-       0xbb9a0a98,
-       0x1cf4029a,
-       0x01d7f00f,
-       0x02dd21f5,
-       0x0ef494bd,
-/* 0x00f9: intr_watchdog_next_time */
-       0x9b0a9815,
-       0xf400a6b0,
-       0x9ab8090b,
-       0x061cf406,
-/* 0x0108: intr_watchdog_next_time_set */
-/* 0x010b: intr_watchdog_next_proc */
-       0x809b0980,
-       0xe0b603e9,
-       0x68e6b158,
-       0xc61bf402,
-/* 0x011a: intr */
-       0x00f900f8,
-       0x80f904bd,
-       0xa0f990f9,
-       0xc0f9b0f9,
-       0xe0f9d0f9,
-       0xf7f0f0f9,
-       0x0188fe00,
-       0x87f180f9,
-       0x84b605d0,
-       0x0088cf06,
-       0xf10180b6,
-       0xb605d007,
-       0x08d00604,
-       0xf004bd00,
-       0x84b60887,
-       0x0088cf06,
-       0xf40289c4,
-       0x0080230b,
-       0x58e7f09b,
-       0x98db21f4,
-       0x96b09b09,
-       0x110bf400,
-       0xb63407f0,
-       0x09d00604,
-       0x8004bd00,
-/* 0x017e: intr_skip_watchdog */
-       0x89e49a09,
-       0x0bf40800,
-       0x8897f148,
-       0x0694b606,
-       0xc40099cf,
-       0x0bf4029a,
-       0xc0c7f12c,
-       0x06c4b604,
-       0xf900cccf,
-       0x48e7f1c0,
-       0x53e3f14f,
-       0x00d7f054,
-       0x034221f5,
-       0x07f1c0fc,
-       0x04b604c0,
-       0x000cd006,
-/* 0x01be: intr_subintr_skip_fifo */
-       0x07f104bd,
-       0x04b60688,
-       0x0009d006,
-/* 0x01ca: intr_skip_subintr */
-       0x89c404bd,
-       0x070bf420,
-       0xffbfa4f1,
-/* 0x01d4: intr_skip_pause */
-       0xf44089c4,
-       0xa4f1070b,
-/* 0x01de: intr_skip_user0 */
-       0x07f0ffbf,
-       0x0604b604,
-       0xbd0008d0,
-       0xfe80fc04,
-       0xf0fc0088,
-       0xd0fce0fc,
-       0xb0fcc0fc,
-       0x90fca0fc,
-       0x00fc80fc,
-       0xf80032f4,
-/* 0x0205: ticks_from_ns */
-       0xf9c0f901,
-       0xcbd7f1b0,
-       0x00d3f000,
-       0x041321f5,
-       0x03e8ccec,
-       0xf400b4b0,
-       0xeeec120b,
-       0xd7f103e8,
-       0xd3f000cb,
-       0x1321f500,
-/* 0x022d: ticks_from_ns_quit */
-       0x02ceb904,
-       0xc0fcb0fc,
-/* 0x0236: ticks_from_us */
-       0xc0f900f8,
-       0xd7f1b0f9,
-       0xd3f000cb,
-       0x1321f500,
-       0x02ceb904,
-       0xf400b4b0,
-       0xe4bd050b,
-/* 0x0250: ticks_from_us_quit */
-       0xc0fcb0fc,
-/* 0x0256: ticks_to_us */
-       0xd7f100f8,
-       0xd3f000cb,
-       0xecedff00,
-/* 0x0262: timer */
-       0x90f900f8,
-       0x32f480f9,
-       0x03f89810,
-       0xf40086b0,
-       0x84bd651c,
-       0xb63807f0,
-       0x08d00604,
-       0xf004bd00,
-       0x84b63487,
-       0x0088cf06,
-       0xbb9a0998,
-       0xe9bb0298,
-       0x03fe8000,
-       0xb60887f0,
-       0x88cf0684,
-       0x0284f000,
-       0xf0261bf4,
-       0x84b63487,
-       0x0088cf06,
-       0xf406e0b8,
-       0xe8b8090b,
-       0x111cf406,
-/* 0x02b8: timer_reset */
-       0xb63407f0,
-       0x0ed00604,
-       0x8004bd00,
-/* 0x02c6: timer_enable */
-       0x87f09a0e,
-       0x3807f001,
-       0xd00604b6,
-       0x04bd0008,
-/* 0x02d4: timer_done */
-       0xfc1031f4,
-       0xf890fc80,
-/* 0x02dd: send_proc */
-       0xf980f900,
-       0x05e89890,
-       0xf004e998,
-       0x89b80486,
-       0x2a0bf406,
-       0x940398c4,
-       0x80b60488,
-       0x008ebb18,
-       0x8000fa98,
-       0x8d80008a,
-       0x028c8001,
-       0xb6038b80,
-       0x94f00190,
-       0x04e98007,
-/* 0x0317: send_done */
-       0xfc0231f4,
-       0xf880fc90,
-/* 0x031d: find */
-       0xf080f900,
-       0x31f45887,
-/* 0x0325: find_loop */
-       0x008a9801,
-       0xf406aeb8,
-       0x80b6100b,
-       0x6886b158,
-       0xf01bf402,
-/* 0x033b: find_done */
-       0xb90132f4,
-       0x80fc028e,
-/* 0x0342: send */
-       0x21f500f8,
-       0x01f4031d,
-/* 0x034b: recv */
-       0xf900f897,
-       0x9880f990,
-       0xe99805e8,
-       0x0132f404,
-       0xf40689b8,
-       0x89c43d0b,
-       0x0180b603,
-       0x800784f0,
-       0xea9805e8,
-       0xfef0f902,
-       0xf0f9018f,
-       0x9402efb9,
-       0xe9bb0499,
-       0x18e0b600,
-       0x9803eb98,
-       0xed9802ec,
-       0x00ee9801,
-       0xf0fca5f9,
-       0xf400f8fe,
-       0xf0fc0131,
-/* 0x0398: recv_done */
-       0x90fc80fc,
-/* 0x039e: init */
-       0x17f100f8,
-       0x14b60108,
-       0x0011cf06,
-       0x010911e7,
-       0xfe0814b6,
-       0x17f10014,
-       0x13f000e0,
-       0x1c07f000,
-       0xd00604b6,
-       0x04bd0001,
-       0xf0ff17f0,
-       0x04b61407,
-       0x0001d006,
-       0x17f004bd,
-       0x0015f102,
-       0x1007f008,
-       0xd00604b6,
-       0x04bd0001,
-       0x011a17f1,
-       0xfe0013f0,
-       0x31f40010,
-       0x0117f010,
-       0xb63807f0,
-       0x01d00604,
-       0xf004bd00,
-/* 0x0402: init_proc */
-       0xf19858f7,
-       0x0016b001,
-       0xf9fa0bf4,
-       0x58f0b615,
-/* 0x0413: mulu32_32_64 */
-       0xf9f20ef4,
-       0xf920f910,
-       0x9540f930,
-       0xd29510e1,
-       0xbdc4bd10,
-       0xc0edffb4,
-       0xb9301dff,
-       0x34f10234,
-       0x34b6ffff,
-       0x1045b610,
-       0xbb00c3bb,
-       0xe2ff01b4,
-       0x0234b930,
-       0xffff34f1,
-       0xb61034b6,
-       0xc3bb1045,
-       0x01b4bb00,
-       0xbb3012ff,
-       0x40fc00b3,
-       0x20fc30fc,
-       0x00f810fc,
-/* 0x0464: host_send */
-       0x04b017f1,
-       0xcf0614b6,
-       0x27f10011,
-       0x24b604a0,
-       0x0022cf06,
-       0xf40612b8,
-       0x1ec4320b,
-       0x04ee9407,
-       0x0270e0b7,
-       0x9803eb98,
-       0xed9802ec,
-       0x00ee9801,
-       0x034221f5,
-       0xc40110b6,
-       0x07f10f1e,
-       0x04b604b0,
-       0x000ed006,
-       0x0ef404bd,
-/* 0x04ad: host_send_done */
-/* 0x04af: host_recv */
-       0xf100f8ba,
-       0xf14e4917,
-       0xb8525413,
-       0x0bf406e1,
-/* 0x04bd: host_recv_wait */
-       0xcc17f1aa,
-       0x0614b604,
-       0xf10011cf,
-       0xb604c827,
-       0x22cf0624,
-       0x0816f000,
-       0xf40612b8,
-       0x23c4e60b,
-       0x0434b607,
-       0x02f030b7,
-       0x80033b80,
-       0x3d80023c,
-       0x003e8001,
-       0xf00120b6,
-       0x07f10f24,
-       0x04b604c8,
-       0x0002d006,
-       0x27f004bd,
-       0x0007f040,
-       0xd00604b6,
-       0x04bd0002,
-/* 0x0512: host_init */
-       0x17f100f8,
-       0x14b60080,
-       0x7015f110,
-       0xd007f102,
-       0x0604b604,
-       0xbd0001d0,
-       0x8017f104,
-       0x1014b600,
-       0x02f015f1,
-       0x04dc07f1,
-       0xd00604b6,
-       0x04bd0001,
-       0xf10117f0,
-       0xb604c407,
-       0x01d00604,
-       0xf804bd00,
-/* 0x0551: memx_func_enter */
-       0x1087f100,
-       0x028eb916,
-       0xb90421f4,
-       0x67f102d7,
-       0x63f1fffc,
-       0x76fdffff,
-       0x0267f104,
-       0x0576fd00,
-       0x70f980f9,
-       0xe0fcd0fc,
-       0xf03f21f4,
-       0x07f10467,
-       0x04b607e0,
-       0x0006d006,
-/* 0x058a: memx_func_enter_wait */
-       0x67f104bd,
-       0x64b607c0,
-       0x0066cf06,
-       0xf40464f0,
-       0x67f0f30b,
-       0x0664b62c,
-       0x800066cf,
-       0x00f8f106,
-/* 0x05a8: memx_func_leave */
-       0xb62c67f0,
-       0x66cf0664,
-       0xf2068000,
-       0xf10467f0,
-       0xb607e407,
-       0x06d00604,
-/* 0x05c3: memx_func_leave_wait */
-       0xf104bd00,
-       0xb607c067,
-       0x66cf0664,
-       0x0464f000,
-       0xf1f31bf4,
-       0xb9161087,
-       0x21f4028e,
-       0x02d7b904,
-       0xffcc67f1,
-       0xffff63f1,
-       0xf90476fd,
-       0xfc70f980,
-       0xf4e0fcd0,
-       0x00f83f21,
-/* 0x05f8: memx_func_wait_vblank */
-       0xb0001698,
-       0x0bf40066,
-       0x0166b013,
-       0xf4060bf4,
-/* 0x060a: memx_func_wait_vblank_head1 */
-       0x77f12e0e,
-       0x0ef40020,
-/* 0x0611: memx_func_wait_vblank_head0 */
-       0x0877f107,
-/* 0x0615: memx_func_wait_vblank_0 */
-       0xc467f100,
-       0x0664b607,
-       0xfd0066cf,
-       0x1bf40467,
-/* 0x0625: memx_func_wait_vblank_1 */
-       0xc467f1f3,
-       0x0664b607,
-       0xfd0066cf,
-       0x0bf40467,
-/* 0x0635: memx_func_wait_vblank_fini */
-       0x0410b6f3,
-/* 0x063a: memx_func_wr32 */
-       0x169800f8,
-       0x01159800,
-       0xf90810b6,
-       0xfc50f960,
-       0xf4e0fcd0,
-       0x42b63f21,
-       0xe91bf402,
-/* 0x0656: memx_func_wait */
-       0x87f000f8,
-       0x0684b62c,
-       0x980088cf,
-       0x1d98001e,
-       0x021c9801,
-       0xb6031b98,
-       0x21f41010,
-/* 0x0673: memx_func_delay */
-       0x9800f8a4,
-       0x10b6001e,
-       0x7f21f404,
-/* 0x067e: memx_func_train */
-       0x57f100f8,
-       0x77f10003,
-       0x97f10000,
-       0x93f00000,
-       0x029eb970,
-       0xb90421f4,
-       0xe7f102d8,
-       0x21f42710,
-/* 0x069d: memx_func_train_loop_outer */
-       0x0158e07f,
-       0x0083f101,
-       0xe097f102,
-       0x1193f011,
-       0x80f990f9,
-       0xe0fcd0fc,
-       0xf93f21f4,
-       0x0067f150,
-/* 0x06bd: memx_func_train_loop_inner */
-       0x1187f100,
-       0x9068ff11,
-       0xfd109894,
-       0x97f10589,
-       0x93f00720,
-       0xf990f910,
-       0xfcd0fc80,
-       0x3f21f4e0,
-       0x008097f1,
-       0xb91093f0,
-       0x21f4029e,
-       0x02d8b904,
-       0xf92088c5,
-       0xfc80f990,
-       0xf4e0fcd0,
-       0x97f13f21,
-       0x93f0053c,
-       0x0287f110,
-       0x0083f130,
-       0xf990f980,
-       0xfcd0fc80,
-       0x3f21f4e0,
-       0x0560e7f1,
-       0xf110e3f0,
-       0xf10000d7,
-       0x908000d3,
-       0xb7f100dc,
-       0xb3f08480,
-       0xa421f41e,
-       0x000057f1,
-       0xffff97f1,
-       0x830093f1,
-/* 0x073c: memx_func_train_loop_4x */
-       0x0080a7f1,
-       0xb910a3f0,
-       0x21f402ae,
-       0x02d8b904,
-       0xffdfb7f1,
-       0xffffb3f1,
-       0xf9048bfd,
-       0xfc80f9a0,
-       0xf4e0fcd0,
-       0xa7f13f21,
-       0xa3f0053c,
-       0x0287f110,
-       0x0083f130,
-       0xf9a0f980,
-       0xfcd0fc80,
-       0x3f21f4e0,
-       0x0560e7f1,
-       0xf110e3f0,
-       0xf10000d7,
-       0xb98000d3,
-       0xb7f102dc,
-       0xb3f02710,
-       0xa421f400,
-       0xf402eeb9,
-       0xddb90421,
-       0x949dff02,
-       0x700150b6,
-       0x1ef40456,
-       0xcc7aa092,
-       0x00a9800b,
-       0xb60160b6,
-       0x66700470,
-       0x001ef510,
-       0xb650fcff,
-       0x56700150,
-       0xd41ef507,
-/* 0x07cf: memx_exec */
-       0xf900f8fe,
-       0xb9d0f9e0,
-       0xb2b902c1,
-/* 0x07d9: memx_exec_next */
-       0x00139802,
-       0xe70410b6,
-       0xe701f034,
-       0xb601e033,
-       0x30f00132,
-       0xde35980c,
-       0x12b855f9,
-       0xe41ef406,
-       0x98f10b98,
-       0xcbbbf20c,
-       0xc4b7f102,
-       0x06b4b607,
-       0xfc00bbcf,
-       0xf5e0fcd0,
-       0xf8034221,
-/* 0x0815: memx_info */
-       0x01c67000,
-/* 0x081b: memx_info_data */
-       0xf10e0bf4,
-       0xf103ccc7,
-       0xf40800b7,
-/* 0x0826: memx_info_train */
-       0xc7f10b0e,
-       0xb7f10bcc,
-/* 0x082e: memx_info_send */
-       0x21f50100,
-       0x00f80342,
-/* 0x0834: memx_recv */
-       0xf401d6b0,
-       0xd6b0980b,
-       0xd80bf400,
-/* 0x0842: memx_init */
-       0x00f800f8,
-/* 0x0844: perf_recv */
-/* 0x0846: perf_init */
-       0x00f800f8,
-/* 0x0848: i2c_drive_scl */
-       0xf40036b0,
-       0x07f1110b,
-       0x04b607e0,
-       0x0001d006,
-       0x00f804bd,
-/* 0x085c: i2c_drive_scl_lo */
-       0x07e407f1,
-       0xd00604b6,
-       0x04bd0001,
-/* 0x086a: i2c_drive_sda */
-       0x36b000f8,
-       0x110bf400,
-       0x07e007f1,
-       0xd00604b6,
-       0x04bd0002,
-/* 0x087e: i2c_drive_sda_lo */
-       0x07f100f8,
-       0x04b607e4,
-       0x0002d006,
-       0x00f804bd,
-/* 0x088c: i2c_sense_scl */
-       0xf10132f4,
-       0xb607c437,
-       0x33cf0634,
-       0x0431fd00,
-       0xf4060bf4,
-/* 0x08a2: i2c_sense_scl_done */
-       0x00f80131,
-/* 0x08a4: i2c_sense_sda */
-       0xf10132f4,
-       0xb607c437,
-       0x33cf0634,
-       0x0432fd00,
-       0xf4060bf4,
-/* 0x08ba: i2c_sense_sda_done */
-       0x00f80131,
-/* 0x08bc: i2c_raise_scl */
-       0x47f140f9,
-       0x37f00898,
-       0x4821f501,
-/* 0x08c9: i2c_raise_scl_wait */
-       0xe8e7f108,
-       0x7f21f403,
-       0x088c21f5,
-       0xb60901f4,
-       0x1bf40142,
-/* 0x08dd: i2c_raise_scl_done */
-       0xf840fcef,
-/* 0x08e1: i2c_start */
-       0x8c21f500,
-       0x0d11f408,
-       0x08a421f5,
-       0xf40611f4,
-/* 0x08f2: i2c_start_rep */
-       0x37f0300e,
-       0x4821f500,
-       0x0137f008,
-       0x086a21f5,
-       0xb60076bb,
-       0x50f90465,
-       0xbb046594,
-       0x50bd0256,
-       0xfc0475fd,
-       0xbc21f550,
-       0x0464b608,
-/* 0x091f: i2c_start_send */
-       0xf01f11f4,
-       0x21f50037,
-       0xe7f1086a,
-       0x21f41388,
-       0x0037f07f,
-       0x084821f5,
-       0x1388e7f1,
-/* 0x093b: i2c_start_out */
-       0xf87f21f4,
-/* 0x093d: i2c_stop */
-       0x0037f000,
-       0x084821f5,
-       0xf50037f0,
-       0xf1086a21,
-       0xf403e8e7,
-       0x37f07f21,
-       0x4821f501,
-       0x88e7f108,
-       0x7f21f413,
-       0xf50137f0,
-       0xf1086a21,
-       0xf41388e7,
-       0x00f87f21,
-/* 0x0970: i2c_bitw */
-       0x086a21f5,
-       0x03e8e7f1,
-       0xbb7f21f4,
-       0x65b60076,
-       0x9450f904,
-       0x56bb0465,
-       0xfd50bd02,
-       0x50fc0475,
-       0x08bc21f5,
-       0xf40464b6,
-       0xe7f11811,
-       0x21f41388,
-       0x0037f07f,
-       0x084821f5,
-       0x1388e7f1,
-/* 0x09af: i2c_bitw_out */
-       0xf87f21f4,
-/* 0x09b1: i2c_bitr */
-       0x0137f000,
-       0x086a21f5,
-       0x03e8e7f1,
-       0xbb7f21f4,
-       0x65b60076,
-       0x9450f904,
-       0x56bb0465,
-       0xfd50bd02,
-       0x50fc0475,
-       0x08bc21f5,
-       0xf40464b6,
-       0x21f51b11,
-       0x37f008a4,
-       0x4821f500,
-       0x88e7f108,
-       0x7f21f413,
-       0xf4013cf0,
-/* 0x09f6: i2c_bitr_done */
-       0x00f80131,
-/* 0x09f8: i2c_get_byte */
-       0xf00057f0,
-/* 0x09fe: i2c_get_byte_next */
-       0x54b60847,
-       0x0076bb01,
-       0xf90465b6,
-       0x04659450,
-       0xbd0256bb,
-       0x0475fd50,
-       0x21f550fc,
-       0x64b609b1,
-       0x2b11f404,
-       0xb60553fd,
-       0x1bf40142,
-       0x0137f0d8,
-       0xb60076bb,
-       0x50f90465,
-       0xbb046594,
-       0x50bd0256,
-       0xfc0475fd,
-       0x7021f550,
-       0x0464b609,
-/* 0x0a48: i2c_get_byte_done */
-/* 0x0a4a: i2c_put_byte */
-       0x47f000f8,
-/* 0x0a4d: i2c_put_byte_next */
-       0x0142b608,
-       0xbb3854ff,
-       0x65b60076,
-       0x9450f904,
-       0x56bb0465,
-       0xfd50bd02,
-       0x50fc0475,
-       0x097021f5,
-       0xf40464b6,
-       0x46b03411,
-       0xd81bf400,
-       0xb60076bb,
-       0x50f90465,
-       0xbb046594,
-       0x50bd0256,
-       0xfc0475fd,
-       0xb121f550,
-       0x0464b609,
-       0xbb0f11f4,
-       0x36b00076,
-       0x061bf401,
-/* 0x0aa3: i2c_put_byte_done */
-       0xf80132f4,
-/* 0x0aa5: i2c_addr */
-       0x0076bb00,
-       0xf90465b6,
-       0x04659450,
-       0xbd0256bb,
-       0x0475fd50,
-       0x21f550fc,
-       0x64b608e1,
-       0x2911f404,
-       0x012ec3e7,
-       0xfd0134b6,
-       0x76bb0553,
-       0x0465b600,
-       0x659450f9,
-       0x0256bb04,
-       0x75fd50bd,
-       0xf550fc04,
-       0xb60a4a21,
-/* 0x0aea: i2c_addr_done */
-       0x00f80464,
-/* 0x0aec: i2c_acquire_addr */
-       0xb6f8cec7,
-       0xe0b702e4,
-       0xee980d1c,
-/* 0x0afb: i2c_acquire */
-       0xf500f800,
-       0xf40aec21,
-       0xd9f00421,
-       0x3f21f403,
-/* 0x0b0a: i2c_release */
-       0x21f500f8,
-       0x21f40aec,
-       0x03daf004,
-       0xf83f21f4,
-/* 0x0b19: i2c_recv */
-       0x0132f400,
-       0xb6f8c1c7,
-       0x16b00214,
-       0x3a1ff528,
-       0xf413a001,
-       0x0032980c,
-       0x0ccc13a0,
-       0xf4003198,
-       0xd0f90231,
-       0xd0f9e0f9,
-       0x000067f1,
-       0x100063f1,
-       0xbb016792,
-       0x65b60076,
-       0x9450f904,
-       0x56bb0465,
-       0xfd50bd02,
-       0x50fc0475,
-       0x0afb21f5,
-       0xfc0464b6,
-       0x00d6b0d0,
-       0x00b31bf5,
-       0xbb0057f0,
-       0x65b60076,
-       0x9450f904,
-       0x56bb0465,
-       0xfd50bd02,
-       0x50fc0475,
-       0x0aa521f5,
-       0xf50464b6,
-       0xc700d011,
-       0x76bbe0c5,
-       0x0465b600,
-       0x659450f9,
-       0x0256bb04,
-       0x75fd50bd,
-       0xf550fc04,
-       0xb60a4a21,
-       0x11f50464,
-       0x57f000ad,
-       0x0076bb01,
-       0xf90465b6,
-       0x04659450,
-       0xbd0256bb,
-       0x0475fd50,
-       0x21f550fc,
-       0x64b60aa5,
-       0x8a11f504,
-       0x0076bb00,
-       0xf90465b6,
-       0x04659450,
-       0xbd0256bb,
-       0x0475fd50,
-       0x21f550fc,
-       0x64b609f8,
-       0x6a11f404,
-       0xbbe05bcb,
-       0x65b60076,
-       0x9450f904,
-       0x56bb0465,
-       0xfd50bd02,
-       0x50fc0475,
-       0x093d21f5,
-       0xb90464b6,
-       0x74bd025b,
-/* 0x0c1f: i2c_recv_not_rd08 */
-       0xb0430ef4,
-       0x1bf401d6,
-       0x0057f03d,
-       0x0aa521f5,
-       0xc73311f4,
-       0x21f5e0c5,
-       0x11f40a4a,
-       0x0057f029,
-       0x0aa521f5,
-       0xc71f11f4,
-       0x21f5e0b5,
-       0x11f40a4a,
-       0x3d21f515,
-       0xc774bd09,
-       0x1bf408c5,
-       0x0232f409,
-/* 0x0c5f: i2c_recv_not_wr08 */
-/* 0x0c5f: i2c_recv_done */
-       0xc7030ef4,
-       0x21f5f8ce,
-       0xe0fc0b0a,
-       0x12f4d0fc,
-       0x027cb90a,
-       0x034221f5,
-/* 0x0c74: i2c_recv_exit */
-/* 0x0c76: i2c_init */
-       0x00f800f8,
-/* 0x0c78: test_recv */
-       0x05d817f1,
-       0xcf0614b6,
-       0x10b60011,
-       0xd807f101,
-       0x0604b605,
-       0xbd0001d0,
-       0x00e7f104,
-       0x4fe3f1d9,
-       0x6221f513,
-/* 0x0c9f: test_init */
-       0xf100f802,
-       0xf50800e7,
-       0xf8026221,
-/* 0x0ca9: idle_recv */
-/* 0x0cab: idle */
-       0xf400f800,
-       0x17f10031,
-       0x14b605d4,
-       0x0011cf06,
-       0xf10110b6,
-       0xb605d407,
-       0x01d00604,
-/* 0x0cc7: idle_loop */
-       0xf004bd00,
-       0x32f45817,
-/* 0x0ccd: idle_proc */
-/* 0x0ccd: idle_proc_exec */
-       0xb910f902,
-       0x21f5021e,
-       0x10fc034b,
-       0xf40911f4,
-       0x0ef40231,
-/* 0x0ce1: idle_proc_next */
-       0x5810b6ef,
-       0xf4061fb8,
-       0x02f4e61b,
-       0x0028f4dd,
-       0x00bb0ef4,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-};
diff --git a/drivers/gpu/drm/nouveau/core/subdev/pwr/fuc/nvc0.fuc b/drivers/gpu/drm/nouveau/core/subdev/pwr/fuc/nvc0.fuc
deleted file mode 100644 (file)
index 21bf8cc..0000000
+++ /dev/null
@@ -1,70 +0,0 @@
-/*
- * Copyright 2013 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 NVKM_PPWR_CHIPSET GF100
-#define HW_TICKS_PER_US 203 // should be 202.5
-
-//#define NVKM_FALCON_PC24
-//#define NVKM_FALCON_UNSHIFTED_IO
-//#define NVKM_FALCON_MMIO_UAS
-//#define NVKM_FALCON_MMIO_TRAP
-
-#include "macros.fuc"
-
-.section #nvc0_pwr_data
-#define INCLUDE_PROC
-#include "kernel.fuc"
-#include "arith.fuc"
-#include "host.fuc"
-#include "memx.fuc"
-#include "perf.fuc"
-#include "i2c_.fuc"
-#include "test.fuc"
-#include "idle.fuc"
-#undef INCLUDE_PROC
-
-#define INCLUDE_DATA
-#include "kernel.fuc"
-#include "arith.fuc"
-#include "host.fuc"
-#include "memx.fuc"
-#include "perf.fuc"
-#include "i2c_.fuc"
-#include "test.fuc"
-#include "idle.fuc"
-#undef INCLUDE_DATA
-.align 256
-
-.section #nvc0_pwr_code
-#define INCLUDE_CODE
-#include "kernel.fuc"
-#include "arith.fuc"
-#include "host.fuc"
-#include "memx.fuc"
-#include "perf.fuc"
-#include "i2c_.fuc"
-#include "test.fuc"
-#include "idle.fuc"
-#undef INCLUDE_CODE
-.align 256
diff --git a/drivers/gpu/drm/nouveau/core/subdev/pwr/fuc/nvc0.fuc.h b/drivers/gpu/drm/nouveau/core/subdev/pwr/fuc/nvc0.fuc.h
deleted file mode 100644 (file)
index 90221d9..0000000
+++ /dev/null
@@ -1,1865 +0,0 @@
-uint32_t nvc0_pwr_data[] = {
-/* 0x0000: proc_kern */
-       0x52544e49,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-/* 0x0058: proc_list_head */
-       0x54534f48,
-       0x00000512,
-       0x000004af,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x584d454d,
-       0x0000075e,
-       0x00000750,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x46524550,
-       0x00000762,
-       0x00000760,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x5f433249,
-       0x00000b92,
-       0x00000a35,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x54534554,
-       0x00000bbb,
-       0x00000b94,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x454c4449,
-       0x00000bc7,
-       0x00000bc5,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-/* 0x0268: proc_list_tail */
-/* 0x0268: time_prev */
-       0x00000000,
-/* 0x026c: time_next */
-       0x00000000,
-/* 0x0270: fifo_queue */
-       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,
-/* 0x02f0: rfifo_queue */
-       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,
-/* 0x0370: memx_func_head */
-       0x00000001,
-       0x00000000,
-       0x00000551,
-/* 0x037c: memx_func_next */
-       0x00000002,
-       0x00000000,
-       0x000005db,
-       0x00000003,
-       0x00000002,
-       0x000006a5,
-       0x00040004,
-       0x00000000,
-       0x000006c1,
-       0x00010005,
-       0x00000000,
-       0x000006de,
-       0x00010006,
-       0x00000000,
-       0x00000663,
-       0x00000007,
-       0x00000000,
-       0x000006e9,
-/* 0x03c4: memx_func_tail */
-/* 0x03c4: memx_ts_start */
-       0x00000000,
-/* 0x03c8: memx_ts_end */
-       0x00000000,
-/* 0x03cc: memx_data_head */
-       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,
-       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,
-       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,
-       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,
-       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,
-       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,
-       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,
-       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,
-/* 0x0bcc: memx_data_tail */
-/* 0x0bcc: memx_train_head */
-       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,
-/* 0x0ccc: memx_train_tail */
-/* 0x0ccc: i2c_scl_map */
-       0x00001000,
-       0x00004000,
-       0x00010000,
-       0x00000100,
-       0x00040000,
-       0x00100000,
-       0x00400000,
-       0x01000000,
-       0x04000000,
-       0x10000000,
-/* 0x0cf4: i2c_sda_map */
-       0x00002000,
-       0x00008000,
-       0x00020000,
-       0x00000200,
-       0x00080000,
-       0x00200000,
-       0x00800000,
-       0x02000000,
-       0x08000000,
-       0x20000000,
-/* 0x0d1c: i2c_ctrl */
-       0x0000e138,
-       0x0000e150,
-       0x0000e168,
-       0x0000e180,
-       0x0000e254,
-       0x0000e274,
-       0x0000e764,
-       0x0000e780,
-       0x0000e79c,
-       0x0000e7b8,
-       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,
-};
-
-uint32_t nvc0_pwr_code[] = {
-       0x039e0ef5,
-/* 0x0004: rd32 */
-       0x07a007f1,
-       0xd00604b6,
-       0x04bd000e,
-       0xf001d7f0,
-       0x07f101d3,
-       0x04b607ac,
-       0x000dd006,
-/* 0x0022: rd32_wait */
-       0xd7f104bd,
-       0xd4b607ac,
-       0x00ddcf06,
-       0x7000d4f1,
-       0xf1f21bf4,
-       0xb607a4d7,
-       0xddcf06d4,
-/* 0x003f: wr32 */
-       0xf100f800,
-       0xb607a007,
-       0x0ed00604,
-       0xf104bd00,
-       0xb607a407,
-       0x0dd00604,
-       0xf004bd00,
-       0xd5f002d7,
-       0x01d3f0f0,
-       0x07ac07f1,
-       0xd00604b6,
-       0x04bd000d,
-/* 0x006c: wr32_wait */
-       0x07acd7f1,
-       0xcf06d4b6,
-       0xd4f100dd,
-       0x1bf47000,
-/* 0x007f: nsec */
-       0xf900f8f2,
-       0xf080f990,
-       0x84b62c87,
-       0x0088cf06,
-/* 0x008c: nsec_loop */
-       0xb62c97f0,
-       0x99cf0694,
-       0x0298bb00,
-       0xf4069eb8,
-       0x80fcf11e,
-       0x00f890fc,
-/* 0x00a4: wait */
-       0x80f990f9,
-       0xb62c87f0,
-       0x88cf0684,
-/* 0x00b1: wait_loop */
-       0x02eeb900,
-       0xb90421f4,
-       0xadfd02da,
-       0x06acb804,
-       0xf0150bf4,
-       0x94b62c97,
-       0x0099cf06,
-       0xb80298bb,
-       0x1ef4069b,
-/* 0x00d5: wait_done */
-       0xfc80fcdf,
-/* 0x00db: intr_watchdog */
-       0x9800f890,
-       0x96b003e9,
-       0x2a0bf400,
-       0xbb9a0a98,
-       0x1cf4029a,
-       0x01d7f00f,
-       0x02dd21f5,
-       0x0ef494bd,
-/* 0x00f9: intr_watchdog_next_time */
-       0x9b0a9815,
-       0xf400a6b0,
-       0x9ab8090b,
-       0x061cf406,
-/* 0x0108: intr_watchdog_next_time_set */
-/* 0x010b: intr_watchdog_next_proc */
-       0x809b0980,
-       0xe0b603e9,
-       0x68e6b158,
-       0xc61bf402,
-/* 0x011a: intr */
-       0x00f900f8,
-       0x80f904bd,
-       0xa0f990f9,
-       0xc0f9b0f9,
-       0xe0f9d0f9,
-       0xf7f0f0f9,
-       0x0188fe00,
-       0x87f180f9,
-       0x84b605d0,
-       0x0088cf06,
-       0xf10180b6,
-       0xb605d007,
-       0x08d00604,
-       0xf004bd00,
-       0x84b60887,
-       0x0088cf06,
-       0xf40289c4,
-       0x0080230b,
-       0x58e7f09b,
-       0x98db21f4,
-       0x96b09b09,
-       0x110bf400,
-       0xb63407f0,
-       0x09d00604,
-       0x8004bd00,
-/* 0x017e: intr_skip_watchdog */
-       0x89e49a09,
-       0x0bf40800,
-       0x8897f148,
-       0x0694b606,
-       0xc40099cf,
-       0x0bf4029a,
-       0xc0c7f12c,
-       0x06c4b604,
-       0xf900cccf,
-       0x48e7f1c0,
-       0x53e3f14f,
-       0x00d7f054,
-       0x034221f5,
-       0x07f1c0fc,
-       0x04b604c0,
-       0x000cd006,
-/* 0x01be: intr_subintr_skip_fifo */
-       0x07f104bd,
-       0x04b60688,
-       0x0009d006,
-/* 0x01ca: intr_skip_subintr */
-       0x89c404bd,
-       0x070bf420,
-       0xffbfa4f1,
-/* 0x01d4: intr_skip_pause */
-       0xf44089c4,
-       0xa4f1070b,
-/* 0x01de: intr_skip_user0 */
-       0x07f0ffbf,
-       0x0604b604,
-       0xbd0008d0,
-       0xfe80fc04,
-       0xf0fc0088,
-       0xd0fce0fc,
-       0xb0fcc0fc,
-       0x90fca0fc,
-       0x00fc80fc,
-       0xf80032f4,
-/* 0x0205: ticks_from_ns */
-       0xf9c0f901,
-       0xcbd7f1b0,
-       0x00d3f000,
-       0x041321f5,
-       0x03e8ccec,
-       0xf400b4b0,
-       0xeeec120b,
-       0xd7f103e8,
-       0xd3f000cb,
-       0x1321f500,
-/* 0x022d: ticks_from_ns_quit */
-       0x02ceb904,
-       0xc0fcb0fc,
-/* 0x0236: ticks_from_us */
-       0xc0f900f8,
-       0xd7f1b0f9,
-       0xd3f000cb,
-       0x1321f500,
-       0x02ceb904,
-       0xf400b4b0,
-       0xe4bd050b,
-/* 0x0250: ticks_from_us_quit */
-       0xc0fcb0fc,
-/* 0x0256: ticks_to_us */
-       0xd7f100f8,
-       0xd3f000cb,
-       0xecedff00,
-/* 0x0262: timer */
-       0x90f900f8,
-       0x32f480f9,
-       0x03f89810,
-       0xf40086b0,
-       0x84bd651c,
-       0xb63807f0,
-       0x08d00604,
-       0xf004bd00,
-       0x84b63487,
-       0x0088cf06,
-       0xbb9a0998,
-       0xe9bb0298,
-       0x03fe8000,
-       0xb60887f0,
-       0x88cf0684,
-       0x0284f000,
-       0xf0261bf4,
-       0x84b63487,
-       0x0088cf06,
-       0xf406e0b8,
-       0xe8b8090b,
-       0x111cf406,
-/* 0x02b8: timer_reset */
-       0xb63407f0,
-       0x0ed00604,
-       0x8004bd00,
-/* 0x02c6: timer_enable */
-       0x87f09a0e,
-       0x3807f001,
-       0xd00604b6,
-       0x04bd0008,
-/* 0x02d4: timer_done */
-       0xfc1031f4,
-       0xf890fc80,
-/* 0x02dd: send_proc */
-       0xf980f900,
-       0x05e89890,
-       0xf004e998,
-       0x89b80486,
-       0x2a0bf406,
-       0x940398c4,
-       0x80b60488,
-       0x008ebb18,
-       0x8000fa98,
-       0x8d80008a,
-       0x028c8001,
-       0xb6038b80,
-       0x94f00190,
-       0x04e98007,
-/* 0x0317: send_done */
-       0xfc0231f4,
-       0xf880fc90,
-/* 0x031d: find */
-       0xf080f900,
-       0x31f45887,
-/* 0x0325: find_loop */
-       0x008a9801,
-       0xf406aeb8,
-       0x80b6100b,
-       0x6886b158,
-       0xf01bf402,
-/* 0x033b: find_done */
-       0xb90132f4,
-       0x80fc028e,
-/* 0x0342: send */
-       0x21f500f8,
-       0x01f4031d,
-/* 0x034b: recv */
-       0xf900f897,
-       0x9880f990,
-       0xe99805e8,
-       0x0132f404,
-       0xf40689b8,
-       0x89c43d0b,
-       0x0180b603,
-       0x800784f0,
-       0xea9805e8,
-       0xfef0f902,
-       0xf0f9018f,
-       0x9402efb9,
-       0xe9bb0499,
-       0x18e0b600,
-       0x9803eb98,
-       0xed9802ec,
-       0x00ee9801,
-       0xf0fca5f9,
-       0xf400f8fe,
-       0xf0fc0131,
-/* 0x0398: recv_done */
-       0x90fc80fc,
-/* 0x039e: init */
-       0x17f100f8,
-       0x14b60108,
-       0x0011cf06,
-       0x010911e7,
-       0xfe0814b6,
-       0x17f10014,
-       0x13f000e0,
-       0x1c07f000,
-       0xd00604b6,
-       0x04bd0001,
-       0xf0ff17f0,
-       0x04b61407,
-       0x0001d006,
-       0x17f004bd,
-       0x0015f102,
-       0x1007f008,
-       0xd00604b6,
-       0x04bd0001,
-       0x011a17f1,
-       0xfe0013f0,
-       0x31f40010,
-       0x0117f010,
-       0xb63807f0,
-       0x01d00604,
-       0xf004bd00,
-/* 0x0402: init_proc */
-       0xf19858f7,
-       0x0016b001,
-       0xf9fa0bf4,
-       0x58f0b615,
-/* 0x0413: mulu32_32_64 */
-       0xf9f20ef4,
-       0xf920f910,
-       0x9540f930,
-       0xd29510e1,
-       0xbdc4bd10,
-       0xc0edffb4,
-       0xb9301dff,
-       0x34f10234,
-       0x34b6ffff,
-       0x1045b610,
-       0xbb00c3bb,
-       0xe2ff01b4,
-       0x0234b930,
-       0xffff34f1,
-       0xb61034b6,
-       0xc3bb1045,
-       0x01b4bb00,
-       0xbb3012ff,
-       0x40fc00b3,
-       0x20fc30fc,
-       0x00f810fc,
-/* 0x0464: host_send */
-       0x04b017f1,
-       0xcf0614b6,
-       0x27f10011,
-       0x24b604a0,
-       0x0022cf06,
-       0xf40612b8,
-       0x1ec4320b,
-       0x04ee9407,
-       0x0270e0b7,
-       0x9803eb98,
-       0xed9802ec,
-       0x00ee9801,
-       0x034221f5,
-       0xc40110b6,
-       0x07f10f1e,
-       0x04b604b0,
-       0x000ed006,
-       0x0ef404bd,
-/* 0x04ad: host_send_done */
-/* 0x04af: host_recv */
-       0xf100f8ba,
-       0xf14e4917,
-       0xb8525413,
-       0x0bf406e1,
-/* 0x04bd: host_recv_wait */
-       0xcc17f1aa,
-       0x0614b604,
-       0xf10011cf,
-       0xb604c827,
-       0x22cf0624,
-       0x0816f000,
-       0xf40612b8,
-       0x23c4e60b,
-       0x0434b607,
-       0x02f030b7,
-       0x80033b80,
-       0x3d80023c,
-       0x003e8001,
-       0xf00120b6,
-       0x07f10f24,
-       0x04b604c8,
-       0x0002d006,
-       0x27f004bd,
-       0x0007f040,
-       0xd00604b6,
-       0x04bd0002,
-/* 0x0512: host_init */
-       0x17f100f8,
-       0x14b60080,
-       0x7015f110,
-       0xd007f102,
-       0x0604b604,
-       0xbd0001d0,
-       0x8017f104,
-       0x1014b600,
-       0x02f015f1,
-       0x04dc07f1,
-       0xd00604b6,
-       0x04bd0001,
-       0xf10117f0,
-       0xb604c407,
-       0x01d00604,
-       0xf804bd00,
-/* 0x0551: memx_func_enter */
-       0x2067f100,
-       0x5d77f116,
-       0xff73f1f5,
-       0x026eb9ff,
-       0xb90421f4,
-       0x87fd02d8,
-       0xf960f904,
-       0xfcd0fc80,
-       0x3f21f4e0,
-       0xfffe77f1,
-       0xffff73f1,
-       0xf4026eb9,
-       0xd8b90421,
-       0x0487fd02,
-       0x80f960f9,
-       0xe0fcd0fc,
-       0xf13f21f4,
-       0xb926f067,
-       0x21f4026e,
-       0x02d8b904,
-       0xf90487fd,
-       0xfc80f960,
-       0xf4e0fcd0,
-       0x67f03f21,
-       0xe007f104,
-       0x0604b607,
-       0xbd0006d0,
-/* 0x05bd: memx_func_enter_wait */
-       0xc067f104,
-       0x0664b607,
-       0xf00066cf,
-       0x0bf40464,
-       0x2c67f0f3,
-       0xcf0664b6,
-       0x06800066,
-/* 0x05db: memx_func_leave */
-       0xf000f8f1,
-       0x64b62c67,
-       0x0066cf06,
-       0xf0f20680,
-       0x07f10467,
-       0x04b607e4,
-       0x0006d006,
-/* 0x05f6: memx_func_leave_wait */
-       0x67f104bd,
-       0x64b607c0,
-       0x0066cf06,
-       0xf40464f0,
-       0x67f1f31b,
-       0x77f126f0,
-       0x73f00001,
-       0x026eb900,
-       0xb90421f4,
-       0x87fd02d8,
-       0xf960f905,
-       0xfcd0fc80,
-       0x3f21f4e0,
-       0x162067f1,
-       0xf4026eb9,
-       0xd8b90421,
-       0x0587fd02,
-       0x80f960f9,
-       0xe0fcd0fc,
-       0xf13f21f4,
-       0xf00aa277,
-       0x6eb90073,
-       0x0421f402,
-       0xfd02d8b9,
-       0x60f90587,
-       0xd0fc80f9,
-       0x21f4e0fc,
-/* 0x0663: memx_func_wait_vblank */
-       0x9800f83f,
-       0x66b00016,
-       0x130bf400,
-       0xf40166b0,
-       0x0ef4060b,
-/* 0x0675: memx_func_wait_vblank_head1 */
-       0x2077f12e,
-       0x070ef400,
-/* 0x067c: memx_func_wait_vblank_head0 */
-       0x000877f1,
-/* 0x0680: memx_func_wait_vblank_0 */
-       0x07c467f1,
-       0xcf0664b6,
-       0x67fd0066,
-       0xf31bf404,
-/* 0x0690: memx_func_wait_vblank_1 */
-       0x07c467f1,
-       0xcf0664b6,
-       0x67fd0066,
-       0xf30bf404,
-/* 0x06a0: memx_func_wait_vblank_fini */
-       0xf80410b6,
-/* 0x06a5: memx_func_wr32 */
-       0x00169800,
-       0xb6011598,
-       0x60f90810,
-       0xd0fc50f9,
-       0x21f4e0fc,
-       0x0242b63f,
-       0xf8e91bf4,
-/* 0x06c1: memx_func_wait */
-       0x2c87f000,
-       0xcf0684b6,
-       0x1e980088,
-       0x011d9800,
-       0x98021c98,
-       0x10b6031b,
-       0xa421f410,
-/* 0x06de: memx_func_delay */
-       0x1e9800f8,
-       0x0410b600,
-       0xf87f21f4,
-/* 0x06e9: memx_func_train */
-/* 0x06eb: memx_exec */
-       0xf900f800,
-       0xb9d0f9e0,
-       0xb2b902c1,
-/* 0x06f5: memx_exec_next */
-       0x00139802,
-       0xe70410b6,
-       0xe701f034,
-       0xb601e033,
-       0x30f00132,
-       0xde35980c,
-       0x12b855f9,
-       0xe41ef406,
-       0x98f10b98,
-       0xcbbbf20c,
-       0xc4b7f102,
-       0x06b4b607,
-       0xfc00bbcf,
-       0xf5e0fcd0,
-       0xf8034221,
-/* 0x0731: memx_info */
-       0x01c67000,
-/* 0x0737: memx_info_data */
-       0xf10e0bf4,
-       0xf103ccc7,
-       0xf40800b7,
-/* 0x0742: memx_info_train */
-       0xc7f10b0e,
-       0xb7f10bcc,
-/* 0x074a: memx_info_send */
-       0x21f50100,
-       0x00f80342,
-/* 0x0750: memx_recv */
-       0xf401d6b0,
-       0xd6b0980b,
-       0xd80bf400,
-/* 0x075e: memx_init */
-       0x00f800f8,
-/* 0x0760: perf_recv */
-/* 0x0762: perf_init */
-       0x00f800f8,
-/* 0x0764: i2c_drive_scl */
-       0xf40036b0,
-       0x07f1110b,
-       0x04b607e0,
-       0x0001d006,
-       0x00f804bd,
-/* 0x0778: i2c_drive_scl_lo */
-       0x07e407f1,
-       0xd00604b6,
-       0x04bd0001,
-/* 0x0786: i2c_drive_sda */
-       0x36b000f8,
-       0x110bf400,
-       0x07e007f1,
-       0xd00604b6,
-       0x04bd0002,
-/* 0x079a: i2c_drive_sda_lo */
-       0x07f100f8,
-       0x04b607e4,
-       0x0002d006,
-       0x00f804bd,
-/* 0x07a8: i2c_sense_scl */
-       0xf10132f4,
-       0xb607c437,
-       0x33cf0634,
-       0x0431fd00,
-       0xf4060bf4,
-/* 0x07be: i2c_sense_scl_done */
-       0x00f80131,
-/* 0x07c0: i2c_sense_sda */
-       0xf10132f4,
-       0xb607c437,
-       0x33cf0634,
-       0x0432fd00,
-       0xf4060bf4,
-/* 0x07d6: i2c_sense_sda_done */
-       0x00f80131,
-/* 0x07d8: i2c_raise_scl */
-       0x47f140f9,
-       0x37f00898,
-       0x6421f501,
-/* 0x07e5: i2c_raise_scl_wait */
-       0xe8e7f107,
-       0x7f21f403,
-       0x07a821f5,
-       0xb60901f4,
-       0x1bf40142,
-/* 0x07f9: i2c_raise_scl_done */
-       0xf840fcef,
-/* 0x07fd: i2c_start */
-       0xa821f500,
-       0x0d11f407,
-       0x07c021f5,
-       0xf40611f4,
-/* 0x080e: i2c_start_rep */
-       0x37f0300e,
-       0x6421f500,
-       0x0137f007,
-       0x078621f5,
-       0xb60076bb,
-       0x50f90465,
-       0xbb046594,
-       0x50bd0256,
-       0xfc0475fd,
-       0xd821f550,
-       0x0464b607,
-/* 0x083b: i2c_start_send */
-       0xf01f11f4,
-       0x21f50037,
-       0xe7f10786,
-       0x21f41388,
-       0x0037f07f,
-       0x076421f5,
-       0x1388e7f1,
-/* 0x0857: i2c_start_out */
-       0xf87f21f4,
-/* 0x0859: i2c_stop */
-       0x0037f000,
-       0x076421f5,
-       0xf50037f0,
-       0xf1078621,
-       0xf403e8e7,
-       0x37f07f21,
-       0x6421f501,
-       0x88e7f107,
-       0x7f21f413,
-       0xf50137f0,
-       0xf1078621,
-       0xf41388e7,
-       0x00f87f21,
-/* 0x088c: i2c_bitw */
-       0x078621f5,
-       0x03e8e7f1,
-       0xbb7f21f4,
-       0x65b60076,
-       0x9450f904,
-       0x56bb0465,
-       0xfd50bd02,
-       0x50fc0475,
-       0x07d821f5,
-       0xf40464b6,
-       0xe7f11811,
-       0x21f41388,
-       0x0037f07f,
-       0x076421f5,
-       0x1388e7f1,
-/* 0x08cb: i2c_bitw_out */
-       0xf87f21f4,
-/* 0x08cd: i2c_bitr */
-       0x0137f000,
-       0x078621f5,
-       0x03e8e7f1,
-       0xbb7f21f4,
-       0x65b60076,
-       0x9450f904,
-       0x56bb0465,
-       0xfd50bd02,
-       0x50fc0475,
-       0x07d821f5,
-       0xf40464b6,
-       0x21f51b11,
-       0x37f007c0,
-       0x6421f500,
-       0x88e7f107,
-       0x7f21f413,
-       0xf4013cf0,
-/* 0x0912: i2c_bitr_done */
-       0x00f80131,
-/* 0x0914: i2c_get_byte */
-       0xf00057f0,
-/* 0x091a: i2c_get_byte_next */
-       0x54b60847,
-       0x0076bb01,
-       0xf90465b6,
-       0x04659450,
-       0xbd0256bb,
-       0x0475fd50,
-       0x21f550fc,
-       0x64b608cd,
-       0x2b11f404,
-       0xb60553fd,
-       0x1bf40142,
-       0x0137f0d8,
-       0xb60076bb,
-       0x50f90465,
-       0xbb046594,
-       0x50bd0256,
-       0xfc0475fd,
-       0x8c21f550,
-       0x0464b608,
-/* 0x0964: i2c_get_byte_done */
-/* 0x0966: i2c_put_byte */
-       0x47f000f8,
-/* 0x0969: i2c_put_byte_next */
-       0x0142b608,
-       0xbb3854ff,
-       0x65b60076,
-       0x9450f904,
-       0x56bb0465,
-       0xfd50bd02,
-       0x50fc0475,
-       0x088c21f5,
-       0xf40464b6,
-       0x46b03411,
-       0xd81bf400,
-       0xb60076bb,
-       0x50f90465,
-       0xbb046594,
-       0x50bd0256,
-       0xfc0475fd,
-       0xcd21f550,
-       0x0464b608,
-       0xbb0f11f4,
-       0x36b00076,
-       0x061bf401,
-/* 0x09bf: i2c_put_byte_done */
-       0xf80132f4,
-/* 0x09c1: i2c_addr */
-       0x0076bb00,
-       0xf90465b6,
-       0x04659450,
-       0xbd0256bb,
-       0x0475fd50,
-       0x21f550fc,
-       0x64b607fd,
-       0x2911f404,
-       0x012ec3e7,
-       0xfd0134b6,
-       0x76bb0553,
-       0x0465b600,
-       0x659450f9,
-       0x0256bb04,
-       0x75fd50bd,
-       0xf550fc04,
-       0xb6096621,
-/* 0x0a06: i2c_addr_done */
-       0x00f80464,
-/* 0x0a08: i2c_acquire_addr */
-       0xb6f8cec7,
-       0xe0b702e4,
-       0xee980d1c,
-/* 0x0a17: i2c_acquire */
-       0xf500f800,
-       0xf40a0821,
-       0xd9f00421,
-       0x3f21f403,
-/* 0x0a26: i2c_release */
-       0x21f500f8,
-       0x21f40a08,
-       0x03daf004,
-       0xf83f21f4,
-/* 0x0a35: i2c_recv */
-       0x0132f400,
-       0xb6f8c1c7,
-       0x16b00214,
-       0x3a1ff528,
-       0xf413a001,
-       0x0032980c,
-       0x0ccc13a0,
-       0xf4003198,
-       0xd0f90231,
-       0xd0f9e0f9,
-       0x000067f1,
-       0x100063f1,
-       0xbb016792,
-       0x65b60076,
-       0x9450f904,
-       0x56bb0465,
-       0xfd50bd02,
-       0x50fc0475,
-       0x0a1721f5,
-       0xfc0464b6,
-       0x00d6b0d0,
-       0x00b31bf5,
-       0xbb0057f0,
-       0x65b60076,
-       0x9450f904,
-       0x56bb0465,
-       0xfd50bd02,
-       0x50fc0475,
-       0x09c121f5,
-       0xf50464b6,
-       0xc700d011,
-       0x76bbe0c5,
-       0x0465b600,
-       0x659450f9,
-       0x0256bb04,
-       0x75fd50bd,
-       0xf550fc04,
-       0xb6096621,
-       0x11f50464,
-       0x57f000ad,
-       0x0076bb01,
-       0xf90465b6,
-       0x04659450,
-       0xbd0256bb,
-       0x0475fd50,
-       0x21f550fc,
-       0x64b609c1,
-       0x8a11f504,
-       0x0076bb00,
-       0xf90465b6,
-       0x04659450,
-       0xbd0256bb,
-       0x0475fd50,
-       0x21f550fc,
-       0x64b60914,
-       0x6a11f404,
-       0xbbe05bcb,
-       0x65b60076,
-       0x9450f904,
-       0x56bb0465,
-       0xfd50bd02,
-       0x50fc0475,
-       0x085921f5,
-       0xb90464b6,
-       0x74bd025b,
-/* 0x0b3b: i2c_recv_not_rd08 */
-       0xb0430ef4,
-       0x1bf401d6,
-       0x0057f03d,
-       0x09c121f5,
-       0xc73311f4,
-       0x21f5e0c5,
-       0x11f40966,
-       0x0057f029,
-       0x09c121f5,
-       0xc71f11f4,
-       0x21f5e0b5,
-       0x11f40966,
-       0x5921f515,
-       0xc774bd08,
-       0x1bf408c5,
-       0x0232f409,
-/* 0x0b7b: i2c_recv_not_wr08 */
-/* 0x0b7b: i2c_recv_done */
-       0xc7030ef4,
-       0x21f5f8ce,
-       0xe0fc0a26,
-       0x12f4d0fc,
-       0x027cb90a,
-       0x034221f5,
-/* 0x0b90: i2c_recv_exit */
-/* 0x0b92: i2c_init */
-       0x00f800f8,
-/* 0x0b94: test_recv */
-       0x05d817f1,
-       0xcf0614b6,
-       0x10b60011,
-       0xd807f101,
-       0x0604b605,
-       0xbd0001d0,
-       0x00e7f104,
-       0x4fe3f1d9,
-       0x6221f513,
-/* 0x0bbb: test_init */
-       0xf100f802,
-       0xf50800e7,
-       0xf8026221,
-/* 0x0bc5: idle_recv */
-/* 0x0bc7: idle */
-       0xf400f800,
-       0x17f10031,
-       0x14b605d4,
-       0x0011cf06,
-       0xf10110b6,
-       0xb605d407,
-       0x01d00604,
-/* 0x0be3: idle_loop */
-       0xf004bd00,
-       0x32f45817,
-/* 0x0be9: idle_proc */
-/* 0x0be9: idle_proc_exec */
-       0xb910f902,
-       0x21f5021e,
-       0x10fc034b,
-       0xf40911f4,
-       0x0ef40231,
-/* 0x0bfd: idle_proc_next */
-       0x5810b6ef,
-       0xf4061fb8,
-       0x02f4e61b,
-       0x0028f4dd,
-       0x00bb0ef4,
-       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,
-};
diff --git a/drivers/gpu/drm/nouveau/core/subdev/pwr/fuc/nvd0.fuc b/drivers/gpu/drm/nouveau/core/subdev/pwr/fuc/nvd0.fuc
deleted file mode 100644 (file)
index b854432..0000000
+++ /dev/null
@@ -1,70 +0,0 @@
-/*
- * Copyright 2013 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 NVKM_PPWR_CHIPSET GF119
-#define HW_TICKS_PER_US 324
-
-//#define NVKM_FALCON_PC24
-#define NVKM_FALCON_UNSHIFTED_IO
-//#define NVKM_FALCON_MMIO_UAS
-//#define NVKM_FALCON_MMIO_TRAP
-
-#include "macros.fuc"
-
-.section #nvd0_pwr_data
-#define INCLUDE_PROC
-#include "kernel.fuc"
-#include "arith.fuc"
-#include "host.fuc"
-#include "memx.fuc"
-#include "perf.fuc"
-#include "i2c_.fuc"
-#include "test.fuc"
-#include "idle.fuc"
-#undef INCLUDE_PROC
-
-#define INCLUDE_DATA
-#include "kernel.fuc"
-#include "arith.fuc"
-#include "host.fuc"
-#include "memx.fuc"
-#include "perf.fuc"
-#include "i2c_.fuc"
-#include "test.fuc"
-#include "idle.fuc"
-#undef INCLUDE_DATA
-.align 256
-
-.section #nvd0_pwr_code
-#define INCLUDE_CODE
-#include "kernel.fuc"
-#include "arith.fuc"
-#include "host.fuc"
-#include "memx.fuc"
-#include "perf.fuc"
-#include "i2c_.fuc"
-#include "test.fuc"
-#include "idle.fuc"
-#undef INCLUDE_CODE
-.align 256
diff --git a/drivers/gpu/drm/nouveau/core/subdev/pwr/fuc/nvd0.fuc.h b/drivers/gpu/drm/nouveau/core/subdev/pwr/fuc/nvd0.fuc.h
deleted file mode 100644 (file)
index 7e16aab..0000000
+++ /dev/null
@@ -1,1795 +0,0 @@
-uint32_t nvd0_pwr_data[] = {
-/* 0x0000: proc_kern */
-       0x52544e49,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-/* 0x0058: proc_list_head */
-       0x54534f48,
-       0x0000049d,
-       0x00000446,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x584d454d,
-       0x0000068b,
-       0x0000067d,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x46524550,
-       0x0000068f,
-       0x0000068d,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x5f433249,
-       0x00000aaa,
-       0x0000094d,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x54534554,
-       0x00000acd,
-       0x00000aac,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x454c4449,
-       0x00000ad9,
-       0x00000ad7,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-       0x00000000,
-/* 0x0268: proc_list_tail */
-/* 0x0268: time_prev */
-       0x00000000,
-/* 0x026c: time_next */
-       0x00000000,
-/* 0x0270: fifo_queue */
-       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,
-/* 0x02f0: rfifo_queue */
-       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,
-/* 0x0370: memx_func_head */
-       0x00000001,
-       0x00000000,
-       0x000004d3,
-/* 0x037c: memx_func_next */
-       0x00000002,
-       0x00000000,
-       0x00000554,
-       0x00000003,
-       0x00000002,
-       0x000005d8,
-       0x00040004,
-       0x00000000,
-       0x000005f4,
-       0x00010005,
-       0x00000000,
-       0x0000060e,
-       0x00010006,
-       0x00000000,
-       0x000005d3,
-       0x00000007,
-       0x00000000,
-       0x00000619,
-/* 0x03c4: memx_func_tail */
-/* 0x03c4: memx_ts_start */
-       0x00000000,
-/* 0x03c8: memx_ts_end */
-       0x00000000,
-/* 0x03cc: memx_data_head */
-       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,
-       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,
-       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,
-       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,
-       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,
-       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,
-       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,
-       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,
-/* 0x0bcc: memx_data_tail */
-/* 0x0bcc: memx_train_head */
-       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,
-/* 0x0ccc: memx_train_tail */
-/* 0x0ccc: i2c_scl_map */
-       0x00000400,
-       0x00000800,
-       0x00001000,
-       0x00002000,
-       0x00004000,
-       0x00008000,
-       0x00010000,
-       0x00020000,
-       0x00040000,
-       0x00080000,
-/* 0x0cf4: i2c_sda_map */
-       0x00100000,
-       0x00200000,
-       0x00400000,
-       0x00800000,
-       0x01000000,
-       0x02000000,
-       0x04000000,
-       0x08000000,
-       0x10000000,
-       0x20000000,
-       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,
-};
-
-uint32_t nvd0_pwr_code[] = {
-       0x034d0ef5,
-/* 0x0004: rd32 */
-       0x07a007f1,
-       0xbd000ed0,
-       0x01d7f004,
-       0xf101d3f0,
-       0xd007ac07,
-       0x04bd000d,
-/* 0x001c: rd32_wait */
-       0x07acd7f1,
-       0xf100ddcf,
-       0xf47000d4,
-       0xd7f1f51b,
-       0xddcf07a4,
-/* 0x0033: wr32 */
-       0xf100f800,
-       0xd007a007,
-       0x04bd000e,
-       0x07a407f1,
-       0xbd000dd0,
-       0x02d7f004,
-       0xf0f0d5f0,
-       0x07f101d3,
-       0x0dd007ac,
-/* 0x0057: wr32_wait */
-       0xf104bd00,
-       0xcf07acd7,
-       0xd4f100dd,
-       0x1bf47000,
-/* 0x0067: nsec */
-       0xf900f8f5,
-       0xf080f990,
-       0x88cf2c87,
-/* 0x0071: nsec_loop */
-       0x2c97f000,
-       0xbb0099cf,
-       0x9eb80298,
-       0xf41ef406,
-       0x90fc80fc,
-/* 0x0086: wait */
-       0x90f900f8,
-       0x87f080f9,
-       0x0088cf2c,
-/* 0x0090: wait_loop */
-       0xf402eeb9,
-       0xdab90421,
-       0x04adfd02,
-       0xf406acb8,
-       0x97f0120b,
-       0x0099cf2c,
-       0xb80298bb,
-       0x1ef4069b,
-/* 0x00b1: wait_done */
-       0xfc80fce2,
-/* 0x00b7: intr_watchdog */
-       0x9800f890,
-       0x96b003e9,
-       0x2a0bf400,
-       0xbb9a0a98,
-       0x1cf4029a,
-       0x01d7f00f,
-       0x028c21f5,
-       0x0ef494bd,
-/* 0x00d5: intr_watchdog_next_time */
-       0x9b0a9815,
-       0xf400a6b0,
-       0x9ab8090b,
-       0x061cf406,
-/* 0x00e4: intr_watchdog_next_time_set */
-/* 0x00e7: intr_watchdog_next_proc */
-       0x809b0980,
-       0xe0b603e9,
-       0x68e6b158,
-       0xc61bf402,
-/* 0x00f6: intr */
-       0x00f900f8,
-       0x80f904bd,
-       0xa0f990f9,
-       0xc0f9b0f9,
-       0xe0f9d0f9,
-       0xf7f0f0f9,
-       0x0188fe00,
-       0x87f180f9,
-       0x88cf05d0,
-       0x0180b600,
-       0x05d007f1,
-       0xbd0008d0,
-       0x0887f004,
-       0xc40088cf,
-       0x0bf40289,
-       0x9b008020,
-       0xf458e7f0,
-       0x0998b721,
-       0x0096b09b,
-       0xf00e0bf4,
-       0x09d03407,
-       0x8004bd00,
-/* 0x014e: intr_skip_watchdog */
-       0x89e49a09,
-       0x0bf40800,
-       0x8897f13c,
-       0x0099cf06,
-       0xf4029ac4,
-       0xc7f1260b,
-       0xcccf04c0,
-       0xf1c0f900,
-       0xf14f48e7,
-       0xf05453e3,
-       0x21f500d7,
-       0xc0fc02f1,
-       0x04c007f1,
-       0xbd000cd0,
-/* 0x0185: intr_subintr_skip_fifo */
-       0x8807f104,
-       0x0009d006,
-/* 0x018e: intr_skip_subintr */
-       0x89c404bd,
-       0x070bf420,
-       0xffbfa4f1,
-/* 0x0198: intr_skip_pause */
-       0xf44089c4,
-       0xa4f1070b,
-/* 0x01a2: intr_skip_user0 */
-       0x07f0ffbf,
-       0x0008d004,
-       0x80fc04bd,
-       0xfc0088fe,
-       0xfce0fcf0,
-       0xfcc0fcd0,
-       0xfca0fcb0,
-       0xfc80fc90,
-       0x0032f400,
-/* 0x01c6: ticks_from_ns */
-       0xc0f901f8,
-       0xd7f1b0f9,
-       0xd3f00144,
-       0xb321f500,
-       0xe8ccec03,
-       0x00b4b003,
-       0xec120bf4,
-       0xf103e8ee,
-       0xf00144d7,
-       0x21f500d3,
-/* 0x01ee: ticks_from_ns_quit */
-       0xceb903b3,
-       0xfcb0fc02,
-/* 0x01f7: ticks_from_us */
-       0xf900f8c0,
-       0xf1b0f9c0,
-       0xf00144d7,
-       0x21f500d3,
-       0xceb903b3,
-       0x00b4b002,
-       0xbd050bf4,
-/* 0x0211: ticks_from_us_quit */
-       0xfcb0fce4,
-/* 0x0217: ticks_to_us */
-       0xf100f8c0,
-       0xf00144d7,
-       0xedff00d3,
-/* 0x0223: timer */
-       0xf900f8ec,
-       0xf480f990,
-       0xf8981032,
-       0x0086b003,
-       0xbd531cf4,
-       0x3807f084,
-       0xbd0008d0,
-       0x3487f004,
-       0x980088cf,
-       0x98bb9a09,
-       0x00e9bb02,
-       0xf003fe80,
-       0x88cf0887,
-       0x0284f000,
-       0xf0201bf4,
-       0x88cf3487,
-       0x06e0b800,
-       0xb8090bf4,
-       0x1cf406e8,
-/* 0x026d: timer_reset */
-       0x3407f00e,
-       0xbd000ed0,
-       0x9a0e8004,
-/* 0x0278: timer_enable */
-       0xf00187f0,
-       0x08d03807,
-/* 0x0283: timer_done */
-       0xf404bd00,
-       0x80fc1031,
-       0x00f890fc,
-/* 0x028c: send_proc */
-       0x90f980f9,
-       0x9805e898,
-       0x86f004e9,
-       0x0689b804,
-       0xc42a0bf4,
-       0x88940398,
-       0x1880b604,
-       0x98008ebb,
-       0x8a8000fa,
-       0x018d8000,
-       0x80028c80,
-       0x90b6038b,
-       0x0794f001,
-       0xf404e980,
-/* 0x02c6: send_done */
-       0x90fc0231,
-       0x00f880fc,
-/* 0x02cc: find */
-       0x87f080f9,
-       0x0131f458,
-/* 0x02d4: find_loop */
-       0xb8008a98,
-       0x0bf406ae,
-       0x5880b610,
-       0x026886b1,
-       0xf4f01bf4,
-/* 0x02ea: find_done */
-       0x8eb90132,
-       0xf880fc02,
-/* 0x02f1: send */
-       0xcc21f500,
-       0x9701f402,
-/* 0x02fa: recv */
-       0x90f900f8,
-       0xe89880f9,
-       0x04e99805,
-       0xb80132f4,
-       0x0bf40689,
-       0x0389c43d,
-       0xf00180b6,
-       0xe8800784,
-       0x02ea9805,
-       0x8ffef0f9,
-       0xb9f0f901,
-       0x999402ef,
-       0x00e9bb04,
-       0x9818e0b6,
-       0xec9803eb,
-       0x01ed9802,
-       0xf900ee98,
-       0xfef0fca5,
-       0x31f400f8,
-/* 0x0347: recv_done */
-       0xfcf0fc01,
-       0xf890fc80,
-/* 0x034d: init */
-       0x0817f100,
-       0x0011cf01,
-       0x010911e7,
-       0xfe0814b6,
-       0x17f10014,
-       0x13f000e0,
-       0x1c07f000,
-       0xbd0001d0,
-       0xff17f004,
-       0xd01407f0,
-       0x04bd0001,
-       0xf10217f0,
-       0xf0080015,
-       0x01d01007,
-       0xf104bd00,
-       0xf000f617,
-       0x10fe0013,
-       0x1031f400,
-       0xf00117f0,
-       0x01d03807,
-       0xf004bd00,
-/* 0x03a2: init_proc */
-       0xf19858f7,
-       0x0016b001,
-       0xf9fa0bf4,
-       0x58f0b615,
-/* 0x03b3: mulu32_32_64 */
-       0xf9f20ef4,
-       0xf920f910,
-       0x9540f930,
-       0xd29510e1,
-       0xbdc4bd10,
-       0xc0edffb4,
-       0xb9301dff,
-       0x34f10234,
-       0x34b6ffff,
-       0x1045b610,
-       0xbb00c3bb,
-       0xe2ff01b4,
-       0x0234b930,
-       0xffff34f1,
-       0xb61034b6,
-       0xc3bb1045,
-       0x01b4bb00,
-       0xbb3012ff,
-       0x40fc00b3,
-       0x20fc30fc,
-       0x00f810fc,
-/* 0x0404: host_send */
-       0x04b017f1,
-       0xf10011cf,
-       0xcf04a027,
-       0x12b80022,
-       0x2f0bf406,
-       0x94071ec4,
-       0xe0b704ee,
-       0xeb980270,
-       0x02ec9803,
-       0x9801ed98,
-       0x21f500ee,
-       0x10b602f1,
-       0x0f1ec401,
-       0x04b007f1,
-       0xbd000ed0,
-       0xc30ef404,
-/* 0x0444: host_send_done */
-/* 0x0446: host_recv */
-       0x17f100f8,
-       0x13f14e49,
-       0xe1b85254,
-       0xb30bf406,
-/* 0x0454: host_recv_wait */
-       0x04cc17f1,
-       0xf10011cf,
-       0xcf04c827,
-       0x16f00022,
-       0x0612b808,
-       0xc4ec0bf4,
-       0x34b60723,
-       0xf030b704,
-       0x033b8002,
-       0x80023c80,
-       0x3e80013d,
-       0x0120b600,
-       0xf10f24f0,
-       0xd004c807,
-       0x04bd0002,
-       0xf04027f0,
-       0x02d00007,
-       0xf804bd00,
-/* 0x049d: host_init */
-       0x8017f100,
-       0x1014b600,
-       0x027015f1,
-       0x04d007f1,
-       0xbd0001d0,
-       0x8017f104,
-       0x1014b600,
-       0x02f015f1,
-       0x04dc07f1,
-       0xbd0001d0,
-       0x0117f004,
-       0x04c407f1,
-       0xbd0001d0,
-/* 0x04d3: memx_func_enter */
-       0xf100f804,
-       0xf1162067,
-       0xf1f55d77,
-       0xb9ffff73,
-       0x21f4026e,
-       0x02d8b904,
-       0xf90487fd,
-       0xfc80f960,
-       0xf4e0fcd0,
-       0x77f13321,
-       0x73f1fffe,
-       0x6eb9ffff,
-       0x0421f402,
-       0xfd02d8b9,
-       0x60f90487,
-       0xd0fc80f9,
-       0x21f4e0fc,
-       0xf067f133,
-       0x026eb926,
-       0xb90421f4,
-       0x87fd02d8,
-       0xf960f904,
-       0xfcd0fc80,
-       0x3321f4e0,
-       0xf10467f0,
-       0xd007e007,
-       0x04bd0006,
-/* 0x053c: memx_func_enter_wait */
-       0x07c067f1,
-       0xf00066cf,
-       0x0bf40464,
-       0x2c67f0f6,
-       0x800066cf,
-       0x00f8f106,
-/* 0x0554: memx_func_leave */
-       0xcf2c67f0,
-       0x06800066,
-       0x0467f0f2,
-       0x07e407f1,
-       0xbd0006d0,
-/* 0x0569: memx_func_leave_wait */
-       0xc067f104,
-       0x0066cf07,
-       0xf40464f0,
-       0x67f1f61b,
-       0x77f126f0,
-       0x73f00001,
-       0x026eb900,
-       0xb90421f4,
-       0x87fd02d8,
-       0xf960f905,
-       0xfcd0fc80,
-       0x3321f4e0,
-       0x162067f1,
-       0xf4026eb9,
-       0xd8b90421,
-       0x0587fd02,
-       0x80f960f9,
-       0xe0fcd0fc,
-       0xf13321f4,
-       0xf00aa277,
-       0x6eb90073,
-       0x0421f402,
-       0xfd02d8b9,
-       0x60f90587,
-       0xd0fc80f9,
-       0x21f4e0fc,
-/* 0x05d3: memx_func_wait_vblank */
-       0xb600f833,
-       0x00f80410,
-/* 0x05d8: memx_func_wr32 */
-       0x98001698,
-       0x10b60115,
-       0xf960f908,
-       0xfcd0fc50,
-       0x3321f4e0,
-       0xf40242b6,
-       0x00f8e91b,
-/* 0x05f4: memx_func_wait */
-       0xcf2c87f0,
-       0x1e980088,
-       0x011d9800,
-       0x98021c98,
-       0x10b6031b,
-       0x8621f410,
-/* 0x060e: memx_func_delay */
-       0x1e9800f8,
-       0x0410b600,
-       0xf86721f4,
-/* 0x0619: memx_func_train */
-/* 0x061b: memx_exec */
-       0xf900f800,
-       0xb9d0f9e0,
-       0xb2b902c1,
-/* 0x0625: memx_exec_next */
-       0x00139802,
-       0xe70410b6,
-       0xe701f034,
-       0xb601e033,
-       0x30f00132,
-       0xde35980c,
-       0x12b855f9,
-       0xe41ef406,
-       0x98f10b98,
-       0xcbbbf20c,
-       0xc4b7f102,
-       0x00bbcf07,
-       0xe0fcd0fc,
-       0x02f121f5,
-/* 0x065e: memx_info */
-       0xc67000f8,
-       0x0e0bf401,
-/* 0x0664: memx_info_data */
-       0x03ccc7f1,
-       0x0800b7f1,
-/* 0x066f: memx_info_train */
-       0xf10b0ef4,
-       0xf10bccc7,
-/* 0x0677: memx_info_send */
-       0xf50100b7,
-       0xf802f121,
-/* 0x067d: memx_recv */
-       0x01d6b000,
-       0xb09b0bf4,
-       0x0bf400d6,
-/* 0x068b: memx_init */
-       0xf800f8d8,
-/* 0x068d: perf_recv */
-/* 0x068f: perf_init */
-       0xf800f800,
-/* 0x0691: i2c_drive_scl */
-       0x0036b000,
-       0xf10e0bf4,
-       0xd007e007,
-       0x04bd0001,
-/* 0x06a2: i2c_drive_scl_lo */
-       0x07f100f8,
-       0x01d007e4,
-       0xf804bd00,
-/* 0x06ad: i2c_drive_sda */
-       0x0036b000,
-       0xf10e0bf4,
-       0xd007e007,
-       0x04bd0002,
-/* 0x06be: i2c_drive_sda_lo */
-       0x07f100f8,
-       0x02d007e4,
-       0xf804bd00,
-/* 0x06c9: i2c_sense_scl */
-       0x0132f400,
-       0x07c437f1,
-       0xfd0033cf,
-       0x0bf40431,
-       0x0131f406,
-/* 0x06dc: i2c_sense_scl_done */
-/* 0x06de: i2c_sense_sda */
-       0x32f400f8,
-       0xc437f101,
-       0x0033cf07,
-       0xf40432fd,
-       0x31f4060b,
-/* 0x06f1: i2c_sense_sda_done */
-/* 0x06f3: i2c_raise_scl */
-       0xf900f801,
-       0x9847f140,
-       0x0137f008,
-       0x069121f5,
-/* 0x0700: i2c_raise_scl_wait */
-       0x03e8e7f1,
-       0xf56721f4,
-       0xf406c921,
-       0x42b60901,
-       0xef1bf401,
-/* 0x0714: i2c_raise_scl_done */
-       0x00f840fc,
-/* 0x0718: i2c_start */
-       0x06c921f5,
-       0xf50d11f4,
-       0xf406de21,
-       0x0ef40611,
-/* 0x0729: i2c_start_rep */
-       0x0037f030,
-       0x069121f5,
-       0xf50137f0,
-       0xbb06ad21,
-       0x65b60076,
-       0x9450f904,
-       0x56bb0465,
-       0xfd50bd02,
-       0x50fc0475,
-       0x06f321f5,
-       0xf40464b6,
-/* 0x0756: i2c_start_send */
-       0x37f01f11,
-       0xad21f500,
-       0x88e7f106,
-       0x6721f413,
-       0xf50037f0,
-       0xf1069121,
-       0xf41388e7,
-/* 0x0772: i2c_start_out */
-       0x00f86721,
-/* 0x0774: i2c_stop */
-       0xf50037f0,
-       0xf0069121,
-       0x21f50037,
-       0xe7f106ad,
-       0x21f403e8,
-       0x0137f067,
-       0x069121f5,
-       0x1388e7f1,
-       0xf06721f4,
-       0x21f50137,
-       0xe7f106ad,
-       0x21f41388,
-/* 0x07a7: i2c_bitw */
-       0xf500f867,
-       0xf106ad21,
-       0xf403e8e7,
-       0x76bb6721,
-       0x0465b600,
-       0x659450f9,
-       0x0256bb04,
-       0x75fd50bd,
-       0xf550fc04,
-       0xb606f321,
-       0x11f40464,
-       0x88e7f118,
-       0x6721f413,
-       0xf50037f0,
-       0xf1069121,
-       0xf41388e7,
-/* 0x07e6: i2c_bitw_out */
-       0x00f86721,
-/* 0x07e8: i2c_bitr */
-       0xf50137f0,
-       0xf106ad21,
-       0xf403e8e7,
-       0x76bb6721,
-       0x0465b600,
-       0x659450f9,
-       0x0256bb04,
-       0x75fd50bd,
-       0xf550fc04,
-       0xb606f321,
-       0x11f40464,
-       0xde21f51b,
-       0x0037f006,
-       0x069121f5,
-       0x1388e7f1,
-       0xf06721f4,
-       0x31f4013c,
-/* 0x082d: i2c_bitr_done */
-/* 0x082f: i2c_get_byte */
-       0xf000f801,
-       0x47f00057,
-/* 0x0835: i2c_get_byte_next */
-       0x0154b608,
-       0xb60076bb,
-       0x50f90465,
-       0xbb046594,
-       0x50bd0256,
-       0xfc0475fd,
-       0xe821f550,
-       0x0464b607,
-       0xfd2b11f4,
-       0x42b60553,
-       0xd81bf401,
-       0xbb0137f0,
-       0x65b60076,
-       0x9450f904,
-       0x56bb0465,
-       0xfd50bd02,
-       0x50fc0475,
-       0x07a721f5,
-/* 0x087f: i2c_get_byte_done */
-       0xf80464b6,
-/* 0x0881: i2c_put_byte */
-       0x0847f000,
-/* 0x0884: i2c_put_byte_next */
-       0xff0142b6,
-       0x76bb3854,
-       0x0465b600,
-       0x659450f9,
-       0x0256bb04,
-       0x75fd50bd,
-       0xf550fc04,
-       0xb607a721,
-       0x11f40464,
-       0x0046b034,
-       0xbbd81bf4,
-       0x65b60076,
-       0x9450f904,
-       0x56bb0465,
-       0xfd50bd02,
-       0x50fc0475,
-       0x07e821f5,
-       0xf40464b6,
-       0x76bb0f11,
-       0x0136b000,
-       0xf4061bf4,
-/* 0x08da: i2c_put_byte_done */
-       0x00f80132,
-/* 0x08dc: i2c_addr */
-       0xb60076bb,
-       0x50f90465,
-       0xbb046594,
-       0x50bd0256,
-       0xfc0475fd,
-       0x1821f550,
-       0x0464b607,
-       0xe72911f4,
-       0xb6012ec3,
-       0x53fd0134,
-       0x0076bb05,
-       0xf90465b6,
-       0x04659450,
-       0xbd0256bb,
-       0x0475fd50,
-       0x21f550fc,
-       0x64b60881,
-/* 0x0921: i2c_addr_done */
-/* 0x0923: i2c_acquire_addr */
-       0xc700f804,
-       0xe4b6f8ce,
-       0x14e0b705,
-/* 0x092f: i2c_acquire */
-       0xf500f8d0,
-       0xf4092321,
-       0xd9f00421,
-       0x3321f403,
-/* 0x093e: i2c_release */
-       0x21f500f8,
-       0x21f40923,
-       0x03daf004,
-       0xf83321f4,
-/* 0x094d: i2c_recv */
-       0x0132f400,
-       0xb6f8c1c7,
-       0x16b00214,
-       0x3a1ff528,
-       0xf413a001,
-       0x0032980c,
-       0x0ccc13a0,
-       0xf4003198,
-       0xd0f90231,
-       0xd0f9e0f9,
-       0x000067f1,
-       0x100063f1,
-       0xbb016792,
-       0x65b60076,
-       0x9450f904,
-       0x56bb0465,
-       0xfd50bd02,
-       0x50fc0475,
-       0x092f21f5,
-       0xfc0464b6,
-       0x00d6b0d0,
-       0x00b31bf5,
-       0xbb0057f0,
-       0x65b60076,
-       0x9450f904,
-       0x56bb0465,
-       0xfd50bd02,
-       0x50fc0475,
-       0x08dc21f5,
-       0xf50464b6,
-       0xc700d011,
-       0x76bbe0c5,
-       0x0465b600,
-       0x659450f9,
-       0x0256bb04,
-       0x75fd50bd,
-       0xf550fc04,
-       0xb6088121,
-       0x11f50464,
-       0x57f000ad,
-       0x0076bb01,
-       0xf90465b6,
-       0x04659450,
-       0xbd0256bb,
-       0x0475fd50,
-       0x21f550fc,
-       0x64b608dc,
-       0x8a11f504,
-       0x0076bb00,
-       0xf90465b6,
-       0x04659450,
-       0xbd0256bb,
-       0x0475fd50,
-       0x21f550fc,
-       0x64b6082f,
-       0x6a11f404,
-       0xbbe05bcb,
-       0x65b60076,
-       0x9450f904,
-       0x56bb0465,
-       0xfd50bd02,
-       0x50fc0475,
-       0x077421f5,
-       0xb90464b6,
-       0x74bd025b,
-/* 0x0a53: i2c_recv_not_rd08 */
-       0xb0430ef4,
-       0x1bf401d6,
-       0x0057f03d,
-       0x08dc21f5,
-       0xc73311f4,
-       0x21f5e0c5,
-       0x11f40881,
-       0x0057f029,
-       0x08dc21f5,
-       0xc71f11f4,
-       0x21f5e0b5,
-       0x11f40881,
-       0x7421f515,
-       0xc774bd07,
-       0x1bf408c5,
-       0x0232f409,
-/* 0x0a93: i2c_recv_not_wr08 */
-/* 0x0a93: i2c_recv_done */
-       0xc7030ef4,
-       0x21f5f8ce,
-       0xe0fc093e,
-       0x12f4d0fc,
-       0x027cb90a,
-       0x02f121f5,
-/* 0x0aa8: i2c_recv_exit */
-/* 0x0aaa: i2c_init */
-       0x00f800f8,
-/* 0x0aac: test_recv */
-       0x05d817f1,
-       0xb60011cf,
-       0x07f10110,
-       0x01d005d8,
-       0xf104bd00,
-       0xf1d900e7,
-       0xf5134fe3,
-       0xf8022321,
-/* 0x0acd: test_init */
-       0x00e7f100,
-       0x2321f508,
-/* 0x0ad7: idle_recv */
-       0xf800f802,
-/* 0x0ad9: idle */
-       0x0031f400,
-       0x05d417f1,
-       0xb60011cf,
-       0x07f10110,
-       0x01d005d4,
-/* 0x0aef: idle_loop */
-       0xf004bd00,
-       0x32f45817,
-/* 0x0af5: idle_proc */
-/* 0x0af5: idle_proc_exec */
-       0xb910f902,
-       0x21f5021e,
-       0x10fc02fa,
-       0xf40911f4,
-       0x0ef40231,
-/* 0x0b09: idle_proc_next */
-       0x5810b6ef,
-       0xf4061fb8,
-       0x02f4e61b,
-       0x0028f4dd,
-       0x00c10ef4,
-       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,
-};
diff --git a/drivers/gpu/drm/nouveau/core/subdev/pwr/fuc/os.h b/drivers/gpu/drm/nouveau/core/subdev/pwr/fuc/os.h
deleted file mode 100644 (file)
index c8b06cb..0000000
+++ /dev/null
@@ -1,52 +0,0 @@
-#ifndef __NVKM_PWR_OS_H__
-#define __NVKM_PWR_OS_H__
-
-/* Process names */
-#define PROC_KERN 0x52544e49
-#define PROC_IDLE 0x454c4449
-#define PROC_HOST 0x54534f48
-#define PROC_MEMX 0x584d454d
-#define PROC_PERF 0x46524550
-#define PROC_I2C_ 0x5f433249
-#define PROC_TEST 0x54534554
-
-/* KERN: message identifiers */
-#define KMSG_FIFO   0x00000000
-#define KMSG_ALARM  0x00000001
-
-/* MEMX: message identifiers */
-#define MEMX_MSG_INFO 0
-#define MEMX_MSG_EXEC 1
-
-/* MEMX: info types */
-#define MEMX_INFO_DATA  0
-#define MEMX_INFO_TRAIN 1
-
-/* MEMX: script opcode definitions */
-#define MEMX_ENTER  1
-#define MEMX_LEAVE  2
-#define MEMX_WR32   3
-#define MEMX_WAIT   4
-#define MEMX_DELAY  5
-#define MEMX_VBLANK 6
-#define MEMX_TRAIN  7
-
-/* I2C_: message identifiers */
-#define I2C__MSG_RD08 0
-#define I2C__MSG_WR08 1
-
-#define I2C__MSG_DATA0_PORT 24:31
-#define I2C__MSG_DATA0_ADDR 14:23
-
-#define I2C__MSG_DATA0_RD08_PORT I2C__MSG_DATA0_PORT
-#define I2C__MSG_DATA0_RD08_ADDR I2C__MSG_DATA0_ADDR
-#define I2C__MSG_DATA0_RD08_REG 0:7
-#define I2C__MSG_DATA1_RD08_VAL 0:7
-
-#define I2C__MSG_DATA0_WR08_PORT I2C__MSG_DATA0_PORT
-#define I2C__MSG_DATA0_WR08_ADDR I2C__MSG_DATA0_ADDR
-#define I2C__MSG_DATA0_WR08_SYNC 8:8
-#define I2C__MSG_DATA0_WR08_REG 0:7
-#define I2C__MSG_DATA1_WR08_VAL 0:7
-
-#endif
diff --git a/drivers/gpu/drm/nouveau/core/subdev/pwr/fuc/perf.fuc b/drivers/gpu/drm/nouveau/core/subdev/pwr/fuc/perf.fuc
deleted file mode 100644 (file)
index 38eadf7..0000000
+++ /dev/null
@@ -1,57 +0,0 @@
-/*
- * Copyright 2013 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
- */
-
-#ifdef INCLUDE_PROC
-process(PROC_PERF, #perf_init, #perf_recv)
-#endif
-
-/******************************************************************************
- * PERF data segment
- *****************************************************************************/
-#ifdef INCLUDE_DATA
-#endif
-
-/******************************************************************************
- * PERF code segment
- *****************************************************************************/
-#ifdef INCLUDE_CODE
-
-// description
-//
-// $r15 - current (perf)
-// $r14 - sender process name
-// $r13 - message
-// $r12 - data0
-// $r11 - data1
-// $r0  - zero
-perf_recv:
-       ret
-
-// description
-//
-// $r15 - current (perf)
-// $r0  - zero
-perf_init:
-       ret
-#endif
diff --git a/drivers/gpu/drm/nouveau/core/subdev/pwr/fuc/test.fuc b/drivers/gpu/drm/nouveau/core/subdev/pwr/fuc/test.fuc
deleted file mode 100644 (file)
index 0c3a71b..0000000
+++ /dev/null
@@ -1,64 +0,0 @@
-/*
- * Copyright 2013 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
- */
-
-#ifdef INCLUDE_PROC
-process(PROC_TEST, #test_init, #test_recv)
-#endif
-
-/******************************************************************************
- * TEST data segment
- *****************************************************************************/
-#ifdef INCLUDE_DATA
-#endif
-
-/******************************************************************************
- * TEST code segment
- *****************************************************************************/
-#ifdef INCLUDE_CODE
-// description
-//
-// $r15 - current (test)
-// $r14 - sender process name
-// $r13 - message
-// $r12 - data0
-// $r11 - data1
-// $r0  - zero
-test_recv:
-       nv_iord($r1, NV_PPWR_DSCRATCH(2))
-       add b32 $r1 1
-       nv_iowr(NV_PPWR_DSCRATCH(2), $r1)
-       mov $r14 -0x2700 /* 0xd900, envyas grrr! */
-       sethi $r14 0x134f0000
-       call(timer)
-       ret
-
-// description
-//
-// $r15 - current (test)
-// $r0  - zero
-test_init:
-       mov $r14 0x800
-       call(timer)
-       ret
-#endif
diff --git a/drivers/gpu/drm/nouveau/core/subdev/pwr/gk104.c b/drivers/gpu/drm/nouveau/core/subdev/pwr/gk104.c
deleted file mode 100644 (file)
index d766129..0000000
+++ /dev/null
@@ -1,69 +0,0 @@
-/*
- * Copyright 2013 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 "priv.h"
-
-#define nvd0_pwr_code gk104_pwr_code
-#define nvd0_pwr_data gk104_pwr_data
-#include "fuc/nvd0.fuc.h"
-
-static void
-gk104_pwr_pgob(struct nouveau_pwr *ppwr, bool enable)
-{
-       nv_mask(ppwr, 0x000200, 0x00001000, 0x00000000);
-       nv_rd32(ppwr, 0x000200);
-       nv_mask(ppwr, 0x000200, 0x08000000, 0x08000000);
-       msleep(50);
-
-       nv_mask(ppwr, 0x10a78c, 0x00000002, 0x00000002);
-       nv_mask(ppwr, 0x10a78c, 0x00000001, 0x00000001);
-       nv_mask(ppwr, 0x10a78c, 0x00000001, 0x00000000);
-
-       nv_mask(ppwr, 0x020004, 0xc0000000, enable ? 0xc0000000 : 0x40000000);
-       msleep(50);
-
-       nv_mask(ppwr, 0x10a78c, 0x00000002, 0x00000000);
-       nv_mask(ppwr, 0x10a78c, 0x00000001, 0x00000001);
-       nv_mask(ppwr, 0x10a78c, 0x00000001, 0x00000000);
-
-       nv_mask(ppwr, 0x000200, 0x08000000, 0x00000000);
-       nv_mask(ppwr, 0x000200, 0x00001000, 0x00001000);
-       nv_rd32(ppwr, 0x000200);
-}
-
-struct nouveau_oclass *
-gk104_pwr_oclass = &(struct nvkm_pwr_impl) {
-       .base.handle = NV_SUBDEV(PWR, 0xe4),
-       .base.ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = _nouveau_pwr_ctor,
-               .dtor = _nouveau_pwr_dtor,
-               .init = _nouveau_pwr_init,
-               .fini = _nouveau_pwr_fini,
-       },
-       .code.data = gk104_pwr_code,
-       .code.size = sizeof(gk104_pwr_code),
-       .data.data = gk104_pwr_data,
-       .data.size = sizeof(gk104_pwr_data),
-       .pgob = gk104_pwr_pgob,
-}.base;
diff --git a/drivers/gpu/drm/nouveau/core/subdev/pwr/memx.c b/drivers/gpu/drm/nouveau/core/subdev/pwr/memx.c
deleted file mode 100644 (file)
index 7a9299d..0000000
+++ /dev/null
@@ -1,201 +0,0 @@
-#ifndef __NVKM_PWR_MEMX_H__
-#define __NVKM_PWR_MEMX_H__
-
-#include "priv.h"
-
-struct nouveau_memx {
-       struct nouveau_pwr *ppwr;
-       u32 base;
-       u32 size;
-       struct {
-               u32 mthd;
-               u32 size;
-               u32 data[64];
-       } c;
-};
-
-static void
-memx_out(struct nouveau_memx *memx)
-{
-       struct nouveau_pwr *ppwr = memx->ppwr;
-       int i;
-
-       if (memx->c.mthd) {
-               nv_wr32(ppwr, 0x10a1c4, (memx->c.size << 16) | memx->c.mthd);
-               for (i = 0; i < memx->c.size; i++)
-                       nv_wr32(ppwr, 0x10a1c4, memx->c.data[i]);
-               memx->c.mthd = 0;
-               memx->c.size = 0;
-       }
-}
-
-static void
-memx_cmd(struct nouveau_memx *memx, u32 mthd, u32 size, u32 data[])
-{
-       if ((memx->c.size + size >= ARRAY_SIZE(memx->c.data)) ||
-           (memx->c.mthd && memx->c.mthd != mthd))
-               memx_out(memx);
-       memcpy(&memx->c.data[memx->c.size], data, size * sizeof(data[0]));
-       memx->c.size += size;
-       memx->c.mthd  = mthd;
-}
-
-int
-nouveau_memx_init(struct nouveau_pwr *ppwr, struct nouveau_memx **pmemx)
-{
-       struct nouveau_memx *memx;
-       u32 reply[2];
-       int ret;
-
-       ret = ppwr->message(ppwr, reply, PROC_MEMX, MEMX_MSG_INFO,
-                                       MEMX_INFO_DATA, 0);
-       if (ret)
-               return ret;
-
-       memx = *pmemx = kzalloc(sizeof(*memx), GFP_KERNEL);
-       if (!memx)
-               return -ENOMEM;
-       memx->ppwr = ppwr;
-       memx->base = reply[0];
-       memx->size = reply[1];
-
-       /* acquire data segment access */
-       do {
-               nv_wr32(ppwr, 0x10a580, 0x00000003);
-       } while (nv_rd32(ppwr, 0x10a580) != 0x00000003);
-       nv_wr32(ppwr, 0x10a1c0, 0x01000000 | memx->base);
-
-       return 0;
-}
-
-int
-nouveau_memx_fini(struct nouveau_memx **pmemx, bool exec)
-{
-       struct nouveau_memx *memx = *pmemx;
-       struct nouveau_pwr *ppwr = memx->ppwr;
-       u32 finish, reply[2];
-
-       /* flush the cache... */
-       memx_out(memx);
-
-       /* release data segment access */
-       finish = nv_rd32(ppwr, 0x10a1c0) & 0x00ffffff;
-       nv_wr32(ppwr, 0x10a580, 0x00000000);
-
-       /* call MEMX process to execute the script, and wait for reply */
-       if (exec) {
-               ppwr->message(ppwr, reply, PROC_MEMX, MEMX_MSG_EXEC,
-                                memx->base, finish);
-       }
-
-       nv_debug(memx->ppwr, "Exec took %uns, PPWR_IN %08x\n",
-                reply[0], reply[1]);
-       kfree(memx);
-       return 0;
-}
-
-void
-nouveau_memx_wr32(struct nouveau_memx *memx, u32 addr, u32 data)
-{
-       nv_debug(memx->ppwr, "R[%06x] = 0x%08x\n", addr, data);
-       memx_cmd(memx, MEMX_WR32, 2, (u32[]){ addr, data });
-}
-
-void
-nouveau_memx_wait(struct nouveau_memx *memx,
-                 u32 addr, u32 mask, u32 data, u32 nsec)
-{
-       nv_debug(memx->ppwr, "R[%06x] & 0x%08x == 0x%08x, %d us\n",
-                               addr, mask, data, nsec);
-       memx_cmd(memx, MEMX_WAIT, 4, (u32[]){ addr, mask, data, nsec });
-       memx_out(memx); /* fuc can't handle multiple */
-}
-
-void
-nouveau_memx_nsec(struct nouveau_memx *memx, u32 nsec)
-{
-       nv_debug(memx->ppwr, "    DELAY = %d ns\n", nsec);
-       memx_cmd(memx, MEMX_DELAY, 1, (u32[]){ nsec });
-       memx_out(memx); /* fuc can't handle multiple */
-}
-
-void
-nouveau_memx_wait_vblank(struct nouveau_memx *memx)
-{
-       struct nouveau_pwr *ppwr = memx->ppwr;
-       u32 heads, x, y, px = 0;
-       int i, head_sync;
-
-       if (nv_device(ppwr)->chipset < 0xd0) {
-               heads = nv_rd32(ppwr, 0x610050);
-               for (i = 0; i < 2; i++) {
-                       /* Heuristic: sync to head with biggest resolution */
-                       if (heads & (2 << (i << 3))) {
-                               x = nv_rd32(ppwr, 0x610b40 + (0x540 * i));
-                               y = (x & 0xffff0000) >> 16;
-                               x &= 0x0000ffff;
-                               if ((x * y) > px) {
-                                       px = (x * y);
-                                       head_sync = i;
-                               }
-                       }
-               }
-       }
-
-       if (px == 0) {
-               nv_debug(memx->ppwr, "WAIT VBLANK !NO ACTIVE HEAD\n");
-               return;
-       }
-
-       nv_debug(memx->ppwr, "WAIT VBLANK HEAD%d\n", head_sync);
-       memx_cmd(memx, MEMX_VBLANK, 1, (u32[]){ head_sync });
-       memx_out(memx); /* fuc can't handle multiple */
-}
-
-void
-nouveau_memx_train(struct nouveau_memx *memx)
-{
-       nv_debug(memx->ppwr, "   MEM TRAIN\n");
-       memx_cmd(memx, MEMX_TRAIN, 0, NULL);
-}
-
-int
-nouveau_memx_train_result(struct nouveau_pwr *ppwr, u32 *res, int rsize)
-{
-       u32 reply[2], base, size, i;
-       int ret;
-
-       ret = ppwr->message(ppwr, reply, PROC_MEMX, MEMX_MSG_INFO,
-                                       MEMX_INFO_TRAIN, 0);
-       if (ret)
-               return ret;
-
-       base = reply[0];
-       size = reply[1] >> 2;
-       if (size > rsize)
-               return -ENOMEM;
-
-       /* read the packet */
-       nv_wr32(ppwr, 0x10a1c0, 0x02000000 | base);
-
-       for (i = 0; i < size; i++)
-               res[i] = nv_rd32(ppwr, 0x10a1c4);
-
-       return 0;
-}
-
-void
-nouveau_memx_block(struct nouveau_memx *memx)
-{
-       nv_debug(memx->ppwr, "   HOST BLOCKED\n");
-       memx_cmd(memx, MEMX_ENTER, 0, NULL);
-}
-
-void
-nouveau_memx_unblock(struct nouveau_memx *memx)
-{
-       nv_debug(memx->ppwr, "   HOST UNBLOCKED\n");
-       memx_cmd(memx, MEMX_LEAVE, 0, NULL);
-}
-
-#endif
diff --git a/drivers/gpu/drm/nouveau/core/subdev/pwr/nv108.c b/drivers/gpu/drm/nouveau/core/subdev/pwr/nv108.c
deleted file mode 100644 (file)
index 04ff7c3..0000000
+++ /dev/null
@@ -1,41 +0,0 @@
-/*
- * Copyright 2013 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 "priv.h"
-#include "fuc/nv108.fuc.h"
-
-struct nouveau_oclass *
-nv108_pwr_oclass = &(struct nvkm_pwr_impl) {
-       .base.handle = NV_SUBDEV(PWR, 0x00),
-       .base.ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = _nouveau_pwr_ctor,
-               .dtor = _nouveau_pwr_dtor,
-               .init = _nouveau_pwr_init,
-               .fini = _nouveau_pwr_fini,
-       },
-       .code.data = nv108_pwr_code,
-       .code.size = sizeof(nv108_pwr_code),
-       .data.data = nv108_pwr_data,
-       .data.size = sizeof(nv108_pwr_data),
-}.base;
diff --git a/drivers/gpu/drm/nouveau/core/subdev/pwr/nva3.c b/drivers/gpu/drm/nouveau/core/subdev/pwr/nva3.c
deleted file mode 100644 (file)
index 998d530..0000000
+++ /dev/null
@@ -1,50 +0,0 @@
-/*
- * Copyright 2013 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 "priv.h"
-#include "fuc/nva3.fuc.h"
-
-static int
-nva3_pwr_init(struct nouveau_object *object)
-{
-       struct nouveau_pwr *ppwr = (void *)object;
-       nv_mask(ppwr, 0x022210, 0x00000001, 0x00000000);
-       nv_mask(ppwr, 0x022210, 0x00000001, 0x00000001);
-       return nouveau_pwr_init(ppwr);
-}
-
-struct nouveau_oclass *
-nva3_pwr_oclass = &(struct nvkm_pwr_impl) {
-       .base.handle = NV_SUBDEV(PWR, 0xa3),
-       .base.ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = _nouveau_pwr_ctor,
-               .dtor = _nouveau_pwr_dtor,
-               .init = nva3_pwr_init,
-               .fini = _nouveau_pwr_fini,
-       },
-       .code.data = nva3_pwr_code,
-       .code.size = sizeof(nva3_pwr_code),
-       .data.data = nva3_pwr_data,
-       .data.size = sizeof(nva3_pwr_data),
-}.base;
diff --git a/drivers/gpu/drm/nouveau/core/subdev/pwr/nvc0.c b/drivers/gpu/drm/nouveau/core/subdev/pwr/nvc0.c
deleted file mode 100644 (file)
index 9a773e6..0000000
+++ /dev/null
@@ -1,41 +0,0 @@
-/*
- * Copyright 2013 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 "priv.h"
-#include "fuc/nvc0.fuc.h"
-
-struct nouveau_oclass *
-nvc0_pwr_oclass = &(struct nvkm_pwr_impl) {
-       .base.handle = NV_SUBDEV(PWR, 0xc0),
-       .base.ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = _nouveau_pwr_ctor,
-               .dtor = _nouveau_pwr_dtor,
-               .init = _nouveau_pwr_init,
-               .fini = _nouveau_pwr_fini,
-       },
-       .code.data = nvc0_pwr_code,
-       .code.size = sizeof(nvc0_pwr_code),
-       .data.data = nvc0_pwr_data,
-       .data.size = sizeof(nvc0_pwr_data),
-}.base;
diff --git a/drivers/gpu/drm/nouveau/core/subdev/pwr/nvd0.c b/drivers/gpu/drm/nouveau/core/subdev/pwr/nvd0.c
deleted file mode 100644 (file)
index 2b29be5..0000000
+++ /dev/null
@@ -1,41 +0,0 @@
-/*
- * Copyright 2013 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 "priv.h"
-#include "fuc/nvd0.fuc.h"
-
-struct nouveau_oclass *
-nvd0_pwr_oclass = &(struct nvkm_pwr_impl) {
-       .base.handle = NV_SUBDEV(PWR, 0xd0),
-       .base.ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = _nouveau_pwr_ctor,
-               .dtor = _nouveau_pwr_dtor,
-               .init = _nouveau_pwr_init,
-               .fini = _nouveau_pwr_fini,
-       },
-       .code.data = nvd0_pwr_code,
-       .code.size = sizeof(nvd0_pwr_code),
-       .data.data = nvd0_pwr_data,
-       .data.size = sizeof(nvd0_pwr_data),
-}.base;
diff --git a/drivers/gpu/drm/nouveau/core/subdev/pwr/priv.h b/drivers/gpu/drm/nouveau/core/subdev/pwr/priv.h
deleted file mode 100644 (file)
index 3814a34..0000000
+++ /dev/null
@@ -1,44 +0,0 @@
-#ifndef __NVKM_PWR_PRIV_H__
-#define __NVKM_PWR_PRIV_H__
-
-#include <subdev/pwr.h>
-#include <subdev/pwr/fuc/os.h>
-
-#define nouveau_pwr_create(p, e, o, d)                                         \
-       nouveau_pwr_create_((p), (e), (o), sizeof(**d), (void **)d)
-#define nouveau_pwr_destroy(p)                                                 \
-       nouveau_subdev_destroy(&(p)->base)
-#define nouveau_pwr_init(p) ({                                                 \
-       struct nouveau_pwr *_ppwr = (p);                                       \
-       _nouveau_pwr_init(nv_object(_ppwr));                                   \
-})
-#define nouveau_pwr_fini(p,s) ({                                               \
-       struct nouveau_pwr *_ppwr = (p);                                       \
-       _nouveau_pwr_fini(nv_object(_ppwr), (s));                              \
-})
-
-int nouveau_pwr_create_(struct nouveau_object *, struct nouveau_object *,
-                       struct nouveau_oclass *, int, void **);
-
-int _nouveau_pwr_ctor(struct nouveau_object *, struct nouveau_object *,
-                     struct nouveau_oclass *, void *, u32,
-                     struct nouveau_object **);
-#define _nouveau_pwr_dtor _nouveau_subdev_dtor
-int _nouveau_pwr_init(struct nouveau_object *);
-int _nouveau_pwr_fini(struct nouveau_object *, bool);
-
-struct nvkm_pwr_impl {
-       struct nouveau_oclass base;
-       struct {
-               u32 *data;
-               u32  size;
-       } code;
-       struct {
-               u32 *data;
-               u32  size;
-       } data;
-
-       void (*pgob)(struct nouveau_pwr *, bool);
-};
-
-#endif
diff --git a/drivers/gpu/drm/nouveau/core/subdev/therm/base.c b/drivers/gpu/drm/nouveau/core/subdev/therm/base.c
deleted file mode 100644 (file)
index 9ad01da..0000000
+++ /dev/null
@@ -1,374 +0,0 @@
-/*
- * Copyright 2012 The Nouveau community
- *
- * 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 <core/object.h>
-#include <core/device.h>
-
-#include <subdev/bios.h>
-
-#include "priv.h"
-
-static int
-nouveau_therm_update_trip(struct nouveau_therm *therm)
-{
-       struct nouveau_therm_priv *priv = (void *)therm;
-       struct nouveau_therm_trip_point *trip = priv->fan->bios.trip,
-                                       *cur_trip = NULL,
-                                       *last_trip = priv->last_trip;
-       u8  temp = therm->temp_get(therm);
-       u16 duty, i;
-
-       /* look for the trip point corresponding to the current temperature */
-       cur_trip = NULL;
-       for (i = 0; i < priv->fan->bios.nr_fan_trip; i++) {
-               if (temp >= trip[i].temp)
-                       cur_trip = &trip[i];
-       }
-
-       /* account for the hysteresis cycle */
-       if (last_trip && temp <= (last_trip->temp) &&
-           temp > (last_trip->temp - last_trip->hysteresis))
-               cur_trip = last_trip;
-
-       if (cur_trip) {
-               duty = cur_trip->fan_duty;
-               priv->last_trip = cur_trip;
-       } else {
-               duty = 0;
-               priv->last_trip = NULL;
-       }
-
-       return duty;
-}
-
-static int
-nouveau_therm_update_linear(struct nouveau_therm *therm)
-{
-       struct nouveau_therm_priv *priv = (void *)therm;
-       u8  linear_min_temp = priv->fan->bios.linear_min_temp;
-       u8  linear_max_temp = priv->fan->bios.linear_max_temp;
-       u8  temp = therm->temp_get(therm);
-       u16 duty;
-
-       /* handle the non-linear part first */
-       if (temp < linear_min_temp)
-               return priv->fan->bios.min_duty;
-       else if (temp > linear_max_temp)
-               return priv->fan->bios.max_duty;
-
-       /* we are in the linear zone */
-       duty  = (temp - linear_min_temp);
-       duty *= (priv->fan->bios.max_duty - priv->fan->bios.min_duty);
-       duty /= (linear_max_temp - linear_min_temp);
-       duty += priv->fan->bios.min_duty;
-
-       return duty;
-}
-
-static void
-nouveau_therm_update(struct nouveau_therm *therm, int mode)
-{
-       struct nouveau_timer *ptimer = nouveau_timer(therm);
-       struct nouveau_therm_priv *priv = (void *)therm;
-       unsigned long flags;
-       bool immd = true;
-       bool poll = true;
-       int duty = -1;
-
-       spin_lock_irqsave(&priv->lock, flags);
-       if (mode < 0)
-               mode = priv->mode;
-       priv->mode = mode;
-
-       switch (mode) {
-       case NOUVEAU_THERM_CTRL_MANUAL:
-               ptimer->alarm_cancel(ptimer, &priv->alarm);
-               duty = nouveau_therm_fan_get(therm);
-               if (duty < 0)
-                       duty = 100;
-               poll = false;
-               break;
-       case NOUVEAU_THERM_CTRL_AUTO:
-               switch(priv->fan->bios.fan_mode) {
-               case NVBIOS_THERM_FAN_TRIP:
-                       duty = nouveau_therm_update_trip(therm);
-                       break;
-               case NVBIOS_THERM_FAN_LINEAR:
-                       duty = nouveau_therm_update_linear(therm);
-                       break;
-               case NVBIOS_THERM_FAN_OTHER:
-                       if (priv->cstate)
-                               duty = priv->cstate;
-                       poll = false;
-                       break;
-               }
-               immd = false;
-               break;
-       case NOUVEAU_THERM_CTRL_NONE:
-       default:
-               ptimer->alarm_cancel(ptimer, &priv->alarm);
-               poll = false;
-       }
-
-       if (list_empty(&priv->alarm.head) && poll)
-               ptimer->alarm(ptimer, 1000000000ULL, &priv->alarm);
-       spin_unlock_irqrestore(&priv->lock, flags);
-
-       if (duty >= 0) {
-               nv_debug(therm, "FAN target request: %d%%\n", duty);
-               nouveau_therm_fan_set(therm, immd, duty);
-       }
-}
-
-int
-nouveau_therm_cstate(struct nouveau_therm *ptherm, int fan, int dir)
-{
-       struct nouveau_therm_priv *priv = (void *)ptherm;
-       if (!dir || (dir < 0 && fan < priv->cstate) ||
-                   (dir > 0 && fan > priv->cstate)) {
-               nv_debug(ptherm, "default fan speed -> %d%%\n", fan);
-               priv->cstate = fan;
-               nouveau_therm_update(ptherm, -1);
-       }
-       return 0;
-}
-
-static void
-nouveau_therm_alarm(struct nouveau_alarm *alarm)
-{
-       struct nouveau_therm_priv *priv =
-              container_of(alarm, struct nouveau_therm_priv, alarm);
-       nouveau_therm_update(&priv->base, -1);
-}
-
-int
-nouveau_therm_fan_mode(struct nouveau_therm *therm, int mode)
-{
-       struct nouveau_therm_priv *priv = (void *)therm;
-       struct nouveau_device *device = nv_device(therm);
-       static const char *name[] = {
-               "disabled",
-               "manual",
-               "automatic"
-       };
-
-       /* The default PPWR ucode on fermi interferes with fan management */
-       if ((mode >= ARRAY_SIZE(name)) ||
-           (mode != NOUVEAU_THERM_CTRL_NONE && device->card_type >= NV_C0 &&
-            !nouveau_subdev(device, NVDEV_SUBDEV_PWR)))
-               return -EINVAL;
-
-       /* do not allow automatic fan management if the thermal sensor is
-        * not available */
-       if (mode == NOUVEAU_THERM_CTRL_AUTO && therm->temp_get(therm) < 0)
-               return -EINVAL;
-
-       if (priv->mode == mode)
-               return 0;
-
-       nv_info(therm, "fan management: %s\n", name[mode]);
-       nouveau_therm_update(therm, mode);
-       return 0;
-}
-
-int
-nouveau_therm_attr_get(struct nouveau_therm *therm,
-                      enum nouveau_therm_attr_type type)
-{
-       struct nouveau_therm_priv *priv = (void *)therm;
-
-       switch (type) {
-       case NOUVEAU_THERM_ATTR_FAN_MIN_DUTY:
-               return priv->fan->bios.min_duty;
-       case NOUVEAU_THERM_ATTR_FAN_MAX_DUTY:
-               return priv->fan->bios.max_duty;
-       case NOUVEAU_THERM_ATTR_FAN_MODE:
-               return priv->mode;
-       case NOUVEAU_THERM_ATTR_THRS_FAN_BOOST:
-               return priv->bios_sensor.thrs_fan_boost.temp;
-       case NOUVEAU_THERM_ATTR_THRS_FAN_BOOST_HYST:
-               return priv->bios_sensor.thrs_fan_boost.hysteresis;
-       case NOUVEAU_THERM_ATTR_THRS_DOWN_CLK:
-               return priv->bios_sensor.thrs_down_clock.temp;
-       case NOUVEAU_THERM_ATTR_THRS_DOWN_CLK_HYST:
-               return priv->bios_sensor.thrs_down_clock.hysteresis;
-       case NOUVEAU_THERM_ATTR_THRS_CRITICAL:
-               return priv->bios_sensor.thrs_critical.temp;
-       case NOUVEAU_THERM_ATTR_THRS_CRITICAL_HYST:
-               return priv->bios_sensor.thrs_critical.hysteresis;
-       case NOUVEAU_THERM_ATTR_THRS_SHUTDOWN:
-               return priv->bios_sensor.thrs_shutdown.temp;
-       case NOUVEAU_THERM_ATTR_THRS_SHUTDOWN_HYST:
-               return priv->bios_sensor.thrs_shutdown.hysteresis;
-       }
-
-       return -EINVAL;
-}
-
-int
-nouveau_therm_attr_set(struct nouveau_therm *therm,
-                      enum nouveau_therm_attr_type type, int value)
-{
-       struct nouveau_therm_priv *priv = (void *)therm;
-
-       switch (type) {
-       case NOUVEAU_THERM_ATTR_FAN_MIN_DUTY:
-               if (value < 0)
-                       value = 0;
-               if (value > priv->fan->bios.max_duty)
-                       value = priv->fan->bios.max_duty;
-               priv->fan->bios.min_duty = value;
-               return 0;
-       case NOUVEAU_THERM_ATTR_FAN_MAX_DUTY:
-               if (value < 0)
-                       value = 0;
-               if (value < priv->fan->bios.min_duty)
-                       value = priv->fan->bios.min_duty;
-               priv->fan->bios.max_duty = value;
-               return 0;
-       case NOUVEAU_THERM_ATTR_FAN_MODE:
-               return nouveau_therm_fan_mode(therm, value);
-       case NOUVEAU_THERM_ATTR_THRS_FAN_BOOST:
-               priv->bios_sensor.thrs_fan_boost.temp = value;
-               priv->sensor.program_alarms(therm);
-               return 0;
-       case NOUVEAU_THERM_ATTR_THRS_FAN_BOOST_HYST:
-               priv->bios_sensor.thrs_fan_boost.hysteresis = value;
-               priv->sensor.program_alarms(therm);
-               return 0;
-       case NOUVEAU_THERM_ATTR_THRS_DOWN_CLK:
-               priv->bios_sensor.thrs_down_clock.temp = value;
-               priv->sensor.program_alarms(therm);
-               return 0;
-       case NOUVEAU_THERM_ATTR_THRS_DOWN_CLK_HYST:
-               priv->bios_sensor.thrs_down_clock.hysteresis = value;
-               priv->sensor.program_alarms(therm);
-               return 0;
-       case NOUVEAU_THERM_ATTR_THRS_CRITICAL:
-               priv->bios_sensor.thrs_critical.temp = value;
-               priv->sensor.program_alarms(therm);
-               return 0;
-       case NOUVEAU_THERM_ATTR_THRS_CRITICAL_HYST:
-               priv->bios_sensor.thrs_critical.hysteresis = value;
-               priv->sensor.program_alarms(therm);
-               return 0;
-       case NOUVEAU_THERM_ATTR_THRS_SHUTDOWN:
-               priv->bios_sensor.thrs_shutdown.temp = value;
-               priv->sensor.program_alarms(therm);
-               return 0;
-       case NOUVEAU_THERM_ATTR_THRS_SHUTDOWN_HYST:
-               priv->bios_sensor.thrs_shutdown.hysteresis = value;
-               priv->sensor.program_alarms(therm);
-               return 0;
-       }
-
-       return -EINVAL;
-}
-
-int
-_nouveau_therm_init(struct nouveau_object *object)
-{
-       struct nouveau_therm *therm = (void *)object;
-       struct nouveau_therm_priv *priv = (void *)therm;
-       int ret;
-
-       ret = nouveau_subdev_init(&therm->base);
-       if (ret)
-               return ret;
-
-       if (priv->suspend >= 0) {
-               /* restore the pwm value only when on manual or auto mode */
-               if (priv->suspend > 0)
-                       nouveau_therm_fan_set(therm, true, priv->fan->percent);
-
-               nouveau_therm_fan_mode(therm, priv->suspend);
-       }
-       nouveau_therm_sensor_init(therm);
-       nouveau_therm_fan_init(therm);
-       return 0;
-}
-
-int
-_nouveau_therm_fini(struct nouveau_object *object, bool suspend)
-{
-       struct nouveau_therm *therm = (void *)object;
-       struct nouveau_therm_priv *priv = (void *)therm;
-
-       nouveau_therm_fan_fini(therm, suspend);
-       nouveau_therm_sensor_fini(therm, suspend);
-       if (suspend) {
-               priv->suspend = priv->mode;
-               priv->mode = NOUVEAU_THERM_CTRL_NONE;
-       }
-
-       return nouveau_subdev_fini(&therm->base, suspend);
-}
-
-int
-nouveau_therm_create_(struct nouveau_object *parent,
-                     struct nouveau_object *engine,
-                     struct nouveau_oclass *oclass,
-                     int length, void **pobject)
-{
-       struct nouveau_therm_priv *priv;
-       int ret;
-
-       ret = nouveau_subdev_create_(parent, engine, oclass, 0, "PTHERM",
-                                    "therm", length, pobject);
-       priv = *pobject;
-       if (ret)
-               return ret;
-
-       nouveau_alarm_init(&priv->alarm, nouveau_therm_alarm);
-       spin_lock_init(&priv->lock);
-       spin_lock_init(&priv->sensor.alarm_program_lock);
-
-       priv->base.fan_get = nouveau_therm_fan_user_get;
-       priv->base.fan_set = nouveau_therm_fan_user_set;
-       priv->base.fan_sense = nouveau_therm_fan_sense;
-       priv->base.attr_get = nouveau_therm_attr_get;
-       priv->base.attr_set = nouveau_therm_attr_set;
-       priv->mode = priv->suspend = -1; /* undefined */
-       return 0;
-}
-
-int
-nouveau_therm_preinit(struct nouveau_therm *therm)
-{
-       nouveau_therm_sensor_ctor(therm);
-       nouveau_therm_ic_ctor(therm);
-       nouveau_therm_fan_ctor(therm);
-
-       nouveau_therm_fan_mode(therm, NOUVEAU_THERM_CTRL_AUTO);
-       nouveau_therm_sensor_preinit(therm);
-       return 0;
-}
-
-void
-_nouveau_therm_dtor(struct nouveau_object *object)
-{
-       struct nouveau_therm_priv *priv = (void *)object;
-       kfree(priv->fan);
-       nouveau_subdev_destroy(&priv->base.base);
-}
diff --git a/drivers/gpu/drm/nouveau/core/subdev/therm/fan.c b/drivers/gpu/drm/nouveau/core/subdev/therm/fan.c
deleted file mode 100644 (file)
index 3656d60..0000000
+++ /dev/null
@@ -1,287 +0,0 @@
-/*
- * Copyright 2012 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
- *         Martin Peres
- */
-
-#include "priv.h"
-
-#include <core/object.h>
-#include <core/device.h>
-
-#include <subdev/gpio.h>
-#include <subdev/timer.h>
-
-#include <subdev/bios/fan.h>
-
-static int
-nouveau_fan_update(struct nouveau_fan *fan, bool immediate, int target)
-{
-       struct nouveau_therm *therm = fan->parent;
-       struct nouveau_therm_priv *priv = (void *)therm;
-       struct nouveau_timer *ptimer = nouveau_timer(priv);
-       unsigned long flags;
-       int ret = 0;
-       int duty;
-
-       /* update target fan speed, restricting to allowed range */
-       spin_lock_irqsave(&fan->lock, flags);
-       if (target < 0)
-               target = fan->percent;
-       target = max_t(u8, target, fan->bios.min_duty);
-       target = min_t(u8, target, fan->bios.max_duty);
-       if (fan->percent != target) {
-               nv_debug(therm, "FAN target: %d\n", target);
-               fan->percent = target;
-       }
-
-       /* check that we're not already at the target duty cycle */
-       duty = fan->get(therm);
-       if (duty == target) {
-               spin_unlock_irqrestore(&fan->lock, flags);
-               return 0;
-       }
-
-       /* smooth out the fanspeed increase/decrease */
-       if (!immediate && duty >= 0) {
-               /* the constant "3" is a rough approximation taken from
-                * nvidia's behaviour.
-                * it is meant to bump the fan speed more incrementally
-                */
-               if (duty < target)
-                       duty = min(duty + 3, target);
-               else if (duty > target)
-                       duty = max(duty - 3, target);
-       } else {
-               duty = target;
-       }
-
-       nv_debug(therm, "FAN update: %d\n", duty);
-       ret = fan->set(therm, duty);
-       if (ret) {
-               spin_unlock_irqrestore(&fan->lock, flags);
-               return ret;
-       }
-
-       /* fan speed updated, drop the fan lock before grabbing the
-        * alarm-scheduling lock and risking a deadlock
-        */
-       spin_unlock_irqrestore(&fan->lock, flags);
-
-       /* schedule next fan update, if not at target speed already */
-       if (list_empty(&fan->alarm.head) && target != duty) {
-               u16 bump_period = fan->bios.bump_period;
-               u16 slow_down_period = fan->bios.slow_down_period;
-               u64 delay;
-
-               if (duty > target)
-                       delay = slow_down_period;
-               else if (duty == target)
-                       delay = min(bump_period, slow_down_period) ;
-               else
-                       delay = bump_period;
-
-               ptimer->alarm(ptimer, delay * 1000 * 1000, &fan->alarm);
-       }
-
-       return ret;
-}
-
-static void
-nouveau_fan_alarm(struct nouveau_alarm *alarm)
-{
-       struct nouveau_fan *fan = container_of(alarm, struct nouveau_fan, alarm);
-       nouveau_fan_update(fan, false, -1);
-}
-
-int
-nouveau_therm_fan_get(struct nouveau_therm *therm)
-{
-       struct nouveau_therm_priv *priv = (void *)therm;
-       return priv->fan->get(therm);
-}
-
-int
-nouveau_therm_fan_set(struct nouveau_therm *therm, bool immediate, int percent)
-{
-       struct nouveau_therm_priv *priv = (void *)therm;
-       return nouveau_fan_update(priv->fan, immediate, percent);
-}
-
-int
-nouveau_therm_fan_sense(struct nouveau_therm *therm)
-{
-       struct nouveau_therm_priv *priv = (void *)therm;
-       struct nouveau_timer *ptimer = nouveau_timer(therm);
-       struct nouveau_gpio *gpio = nouveau_gpio(therm);
-       u32 cycles, cur, prev;
-       u64 start, end, tach;
-
-       if (priv->fan->tach.func == DCB_GPIO_UNUSED)
-               return -ENODEV;
-
-       /* Time a complete rotation and extrapolate to RPM:
-        * When the fan spins, it changes the value of GPIO FAN_SENSE.
-        * We get 4 changes (0 -> 1 -> 0 -> 1) per complete rotation.
-        */
-       start = ptimer->read(ptimer);
-       prev = gpio->get(gpio, 0, priv->fan->tach.func, priv->fan->tach.line);
-       cycles = 0;
-       do {
-               usleep_range(500, 1000); /* supports 0 < rpm < 7500 */
-
-               cur = gpio->get(gpio, 0, priv->fan->tach.func, priv->fan->tach.line);
-               if (prev != cur) {
-                       if (!start)
-                               start = ptimer->read(ptimer);
-                       cycles++;
-                       prev = cur;
-               }
-       } while (cycles < 5 && ptimer->read(ptimer) - start < 250000000);
-       end = ptimer->read(ptimer);
-
-       if (cycles == 5) {
-               tach = (u64)60000000000ULL;
-               do_div(tach, (end - start));
-               return tach;
-       } else
-               return 0;
-}
-
-int
-nouveau_therm_fan_user_get(struct nouveau_therm *therm)
-{
-       return nouveau_therm_fan_get(therm);
-}
-
-int
-nouveau_therm_fan_user_set(struct nouveau_therm *therm, int percent)
-{
-       struct nouveau_therm_priv *priv = (void *)therm;
-
-       if (priv->mode != NOUVEAU_THERM_CTRL_MANUAL)
-               return -EINVAL;
-
-       return nouveau_therm_fan_set(therm, true, percent);
-}
-
-static void
-nouveau_therm_fan_set_defaults(struct nouveau_therm *therm)
-{
-       struct nouveau_therm_priv *priv = (void *)therm;
-
-       priv->fan->bios.pwm_freq = 0;
-       priv->fan->bios.min_duty = 0;
-       priv->fan->bios.max_duty = 100;
-       priv->fan->bios.bump_period = 500;
-       priv->fan->bios.slow_down_period = 2000;
-       priv->fan->bios.linear_min_temp = 40;
-       priv->fan->bios.linear_max_temp = 85;
-}
-
-static void
-nouveau_therm_fan_safety_checks(struct nouveau_therm *therm)
-{
-       struct nouveau_therm_priv *priv = (void *)therm;
-
-       if (priv->fan->bios.min_duty > 100)
-               priv->fan->bios.min_duty = 100;
-       if (priv->fan->bios.max_duty > 100)
-               priv->fan->bios.max_duty = 100;
-
-       if (priv->fan->bios.min_duty > priv->fan->bios.max_duty)
-               priv->fan->bios.min_duty = priv->fan->bios.max_duty;
-}
-
-int
-nouveau_therm_fan_init(struct nouveau_therm *therm)
-{
-       return 0;
-}
-
-int
-nouveau_therm_fan_fini(struct nouveau_therm *therm, bool suspend)
-{
-       struct nouveau_therm_priv *priv = (void *)therm;
-       struct nouveau_timer *ptimer = nouveau_timer(therm);
-
-       if (suspend)
-               ptimer->alarm_cancel(ptimer, &priv->fan->alarm);
-       return 0;
-}
-
-int
-nouveau_therm_fan_ctor(struct nouveau_therm *therm)
-{
-       struct nouveau_therm_priv *priv = (void *)therm;
-       struct nouveau_gpio *gpio = nouveau_gpio(therm);
-       struct nouveau_bios *bios = nouveau_bios(therm);
-       struct dcb_gpio_func func;
-       int ret;
-
-       /* attempt to locate a drivable fan, and determine control method */
-       ret = gpio->find(gpio, 0, DCB_GPIO_FAN, 0xff, &func);
-       if (ret == 0) {
-               /* FIXME: is this really the place to perform such checks ? */
-               if (func.line != 16 && func.log[0] & DCB_GPIO_LOG_DIR_IN) {
-                       nv_debug(therm, "GPIO_FAN is in input mode\n");
-                       ret = -EINVAL;
-               } else {
-                       ret = nouveau_fanpwm_create(therm, &func);
-                       if (ret != 0)
-                               ret = nouveau_fantog_create(therm, &func);
-               }
-       }
-
-       /* no controllable fan found, create a dummy fan module */
-       if (ret != 0) {
-               ret = nouveau_fannil_create(therm);
-               if (ret)
-                       return ret;
-       }
-
-       nv_info(therm, "FAN control: %s\n", priv->fan->type);
-
-       /* read the current speed, it is useful when resuming */
-       priv->fan->percent = nouveau_therm_fan_get(therm);
-
-       /* attempt to detect a tachometer connection */
-       ret = gpio->find(gpio, 0, DCB_GPIO_FAN_SENSE, 0xff, &priv->fan->tach);
-       if (ret)
-               priv->fan->tach.func = DCB_GPIO_UNUSED;
-
-       /* initialise fan bump/slow update handling */
-       priv->fan->parent = therm;
-       nouveau_alarm_init(&priv->fan->alarm, nouveau_fan_alarm);
-       spin_lock_init(&priv->fan->lock);
-
-       /* other random init... */
-       nouveau_therm_fan_set_defaults(therm);
-       nvbios_perf_fan_parse(bios, &priv->fan->perf);
-       if (!nvbios_fan_parse(bios, &priv->fan->bios)) {
-               nv_debug(therm, "parsing the fan table failed\n");
-               if (nvbios_therm_fan_parse(bios, &priv->fan->bios))
-                       nv_error(therm, "parsing both fan tables failed\n");
-       }
-       nouveau_therm_fan_safety_checks(therm);
-       return 0;
-}
diff --git a/drivers/gpu/drm/nouveau/core/subdev/therm/fannil.c b/drivers/gpu/drm/nouveau/core/subdev/therm/fannil.c
deleted file mode 100644 (file)
index b78c182..0000000
+++ /dev/null
@@ -1,54 +0,0 @@
-/*
- * Copyright 2012 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 "priv.h"
-
-static int
-nouveau_fannil_get(struct nouveau_therm *therm)
-{
-       return -ENODEV;
-}
-
-static int
-nouveau_fannil_set(struct nouveau_therm *therm, int percent)
-{
-       return -ENODEV;
-}
-
-int
-nouveau_fannil_create(struct nouveau_therm *therm)
-{
-       struct nouveau_therm_priv *tpriv = (void *)therm;
-       struct nouveau_fan *priv;
-
-       priv = kzalloc(sizeof(*priv), GFP_KERNEL);
-       tpriv->fan = priv;
-       if (!priv)
-               return -ENOMEM;
-
-       priv->type = "none / external";
-       priv->get = nouveau_fannil_get;
-       priv->set = nouveau_fannil_set;
-       return 0;
-}
diff --git a/drivers/gpu/drm/nouveau/core/subdev/therm/fanpwm.c b/drivers/gpu/drm/nouveau/core/subdev/therm/fanpwm.c
deleted file mode 100644 (file)
index c629d7f..0000000
+++ /dev/null
@@ -1,113 +0,0 @@
-/*
- * Copyright 2012 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
- *         Martin Peres
- */
-
-#include <core/option.h>
-#include <subdev/gpio.h>
-#include <subdev/bios.h>
-#include <subdev/bios/fan.h>
-
-#include "priv.h"
-
-struct nouveau_fanpwm_priv {
-       struct nouveau_fan base;
-       struct dcb_gpio_func func;
-};
-
-static int
-nouveau_fanpwm_get(struct nouveau_therm *therm)
-{
-       struct nouveau_therm_priv *tpriv = (void *)therm;
-       struct nouveau_fanpwm_priv *priv = (void *)tpriv->fan;
-       struct nouveau_gpio *gpio = nouveau_gpio(therm);
-       int card_type = nv_device(therm)->card_type;
-       u32 divs, duty;
-       int ret;
-
-       ret = therm->pwm_get(therm, priv->func.line, &divs, &duty);
-       if (ret == 0 && divs) {
-               divs = max(divs, duty);
-               if (card_type <= NV_40 || (priv->func.log[0] & 1))
-                       duty = divs - duty;
-               return (duty * 100) / divs;
-       }
-
-       return gpio->get(gpio, 0, priv->func.func, priv->func.line) * 100;
-}
-
-static int
-nouveau_fanpwm_set(struct nouveau_therm *therm, int percent)
-{
-       struct nouveau_therm_priv *tpriv = (void *)therm;
-       struct nouveau_fanpwm_priv *priv = (void *)tpriv->fan;
-       int card_type = nv_device(therm)->card_type;
-       u32 divs, duty;
-       int ret;
-
-       divs = priv->base.perf.pwm_divisor;
-       if (priv->base.bios.pwm_freq) {
-               divs = 1;
-               if (therm->pwm_clock)
-                       divs = therm->pwm_clock(therm, priv->func.line);
-               divs /= priv->base.bios.pwm_freq;
-       }
-
-       duty = ((divs * percent) + 99) / 100;
-       if (card_type <= NV_40 || (priv->func.log[0] & 1))
-               duty = divs - duty;
-
-       ret = therm->pwm_set(therm, priv->func.line, divs, duty);
-       if (ret == 0)
-               ret = therm->pwm_ctrl(therm, priv->func.line, true);
-       return ret;
-}
-
-int
-nouveau_fanpwm_create(struct nouveau_therm *therm, struct dcb_gpio_func *func)
-{
-       struct nouveau_device *device = nv_device(therm);
-       struct nouveau_therm_priv *tpriv = (void *)therm;
-       struct nouveau_bios *bios = nouveau_bios(therm);
-       struct nouveau_fanpwm_priv *priv;
-       struct nvbios_therm_fan fan;
-       u32 divs, duty;
-
-       nvbios_fan_parse(bios, &fan);
-
-       if (!nouveau_boolopt(device->cfgopt, "NvFanPWM", func->param) ||
-           !therm->pwm_ctrl || fan.type == NVBIOS_THERM_FAN_TOGGLE ||
-            therm->pwm_get(therm, func->line, &divs, &duty) == -ENODEV)
-               return -ENODEV;
-
-       priv = kzalloc(sizeof(*priv), GFP_KERNEL);
-       tpriv->fan = &priv->base;
-       if (!priv)
-               return -ENOMEM;
-
-       priv->base.type = "PWM";
-       priv->base.get = nouveau_fanpwm_get;
-       priv->base.set = nouveau_fanpwm_set;
-       priv->func = *func;
-       return 0;
-}
diff --git a/drivers/gpu/drm/nouveau/core/subdev/therm/fantog.c b/drivers/gpu/drm/nouveau/core/subdev/therm/fantog.c
deleted file mode 100644 (file)
index f69dab1..0000000
+++ /dev/null
@@ -1,122 +0,0 @@
-/*
- * Copyright 2012 The Nouveau community
- *
- * 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 "priv.h"
-
-#include <core/object.h>
-#include <core/device.h>
-
-#include <subdev/gpio.h>
-#include <subdev/timer.h>
-
-struct nouveau_fantog_priv {
-       struct nouveau_fan base;
-       struct nouveau_alarm alarm;
-       spinlock_t lock;
-       u32 period_us;
-       u32 percent;
-       struct dcb_gpio_func func;
-};
-
-static void
-nouveau_fantog_update(struct nouveau_fantog_priv *priv, int percent)
-{
-       struct nouveau_therm_priv *tpriv = (void *)priv->base.parent;
-       struct nouveau_timer *ptimer = nouveau_timer(tpriv);
-       struct nouveau_gpio *gpio = nouveau_gpio(tpriv);
-       unsigned long flags;
-       int duty;
-
-       spin_lock_irqsave(&priv->lock, flags);
-       if (percent < 0)
-               percent = priv->percent;
-       priv->percent = percent;
-
-       duty = !gpio->get(gpio, 0, DCB_GPIO_FAN, 0xff);
-       gpio->set(gpio, 0, DCB_GPIO_FAN, 0xff, duty);
-
-       if (list_empty(&priv->alarm.head) && percent != (duty * 100)) {
-               u64 next_change = (percent * priv->period_us) / 100;
-               if (!duty)
-                       next_change = priv->period_us - next_change;
-               ptimer->alarm(ptimer, next_change * 1000, &priv->alarm);
-       }
-       spin_unlock_irqrestore(&priv->lock, flags);
-}
-
-static void
-nouveau_fantog_alarm(struct nouveau_alarm *alarm)
-{
-       struct nouveau_fantog_priv *priv =
-              container_of(alarm, struct nouveau_fantog_priv, alarm);
-       nouveau_fantog_update(priv, -1);
-}
-
-static int
-nouveau_fantog_get(struct nouveau_therm *therm)
-{
-       struct nouveau_therm_priv *tpriv = (void *)therm;
-       struct nouveau_fantog_priv *priv = (void *)tpriv->fan;
-       return priv->percent;
-}
-
-static int
-nouveau_fantog_set(struct nouveau_therm *therm, int percent)
-{
-       struct nouveau_therm_priv *tpriv = (void *)therm;
-       struct nouveau_fantog_priv *priv = (void *)tpriv->fan;
-       if (therm->pwm_ctrl)
-               therm->pwm_ctrl(therm, priv->func.line, false);
-       nouveau_fantog_update(priv, percent);
-       return 0;
-}
-
-int
-nouveau_fantog_create(struct nouveau_therm *therm, struct dcb_gpio_func *func)
-{
-       struct nouveau_therm_priv *tpriv = (void *)therm;
-       struct nouveau_fantog_priv *priv;
-       int ret;
-
-       if (therm->pwm_ctrl) {
-               ret = therm->pwm_ctrl(therm, func->line, false);
-               if (ret)
-                       return ret;
-       }
-
-       priv = kzalloc(sizeof(*priv), GFP_KERNEL);
-       tpriv->fan = &priv->base;
-       if (!priv)
-               return -ENOMEM;
-
-       priv->base.type = "toggle";
-       priv->base.get = nouveau_fantog_get;
-       priv->base.set = nouveau_fantog_set;
-       nouveau_alarm_init(&priv->alarm, nouveau_fantog_alarm);
-       priv->period_us = 100000; /* 10Hz */
-       priv->percent = 100;
-       priv->func = *func;
-       spin_lock_init(&priv->lock);
-       return 0;
-}
diff --git a/drivers/gpu/drm/nouveau/core/subdev/therm/gm107.c b/drivers/gpu/drm/nouveau/core/subdev/therm/gm107.c
deleted file mode 100644 (file)
index 668cf33..0000000
+++ /dev/null
@@ -1,93 +0,0 @@
-/*
- * Copyright 2014 Martin Peres
- *
- * 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 "priv.h"
-
-struct gm107_therm_priv {
-       struct nouveau_therm_priv base;
-};
-
-static int
-gm107_fan_pwm_ctrl(struct nouveau_therm *therm, int line, bool enable)
-{
-       /* nothing to do, it seems hardwired */
-       return 0;
-}
-
-static int
-gm107_fan_pwm_get(struct nouveau_therm *therm, int line, u32 *divs, u32 *duty)
-{
-       *divs = nv_rd32(therm, 0x10eb20) & 0x1fff;
-       *duty = nv_rd32(therm, 0x10eb24) & 0x1fff;
-       return 0;
-}
-
-static int
-gm107_fan_pwm_set(struct nouveau_therm *therm, int line, u32 divs, u32 duty)
-{
-       nv_mask(therm, 0x10eb10, 0x1fff, divs); /* keep the high bits */
-       nv_wr32(therm, 0x10eb14, duty | 0x80000000);
-       return 0;
-}
-
-static int
-gm107_fan_pwm_clock(struct nouveau_therm *therm, int line)
-{
-       return nv_device(therm)->crystal * 1000;
-}
-
-static int
-gm107_therm_ctor(struct nouveau_object *parent,
-               struct nouveau_object *engine,
-               struct nouveau_oclass *oclass, void *data, u32 size,
-               struct nouveau_object **pobject)
-{
-       struct gm107_therm_priv *priv;
-       int ret;
-
-       ret = nouveau_therm_create(parent, engine, oclass, &priv);
-       *pobject = nv_object(priv);
-       if (ret)
-               return ret;
-
-       priv->base.base.pwm_ctrl = gm107_fan_pwm_ctrl;
-       priv->base.base.pwm_get = gm107_fan_pwm_get;
-       priv->base.base.pwm_set = gm107_fan_pwm_set;
-       priv->base.base.pwm_clock = gm107_fan_pwm_clock;
-       priv->base.base.temp_get = nv84_temp_get;
-       priv->base.base.fan_sense = nva3_therm_fan_sense;
-       priv->base.sensor.program_alarms = nouveau_therm_program_alarms_polling;
-       return nouveau_therm_preinit(&priv->base.base);
-}
-
-struct nouveau_oclass
-gm107_therm_oclass = {
-       .handle = NV_SUBDEV(THERM, 0x117),
-       .ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = gm107_therm_ctor,
-               .dtor = _nouveau_therm_dtor,
-               .init = nvd0_therm_init,
-               .fini = nv84_therm_fini,
-       },
-};
diff --git a/drivers/gpu/drm/nouveau/core/subdev/therm/ic.c b/drivers/gpu/drm/nouveau/core/subdev/therm/ic.c
deleted file mode 100644 (file)
index ca9ad9f..0000000
+++ /dev/null
@@ -1,121 +0,0 @@
-/*
- * Copyright 2012 Nouveau community
- *
- * 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 "priv.h"
-
-#include <subdev/i2c.h>
-#include <subdev/bios/extdev.h>
-
-static bool
-probe_monitoring_device(struct nouveau_i2c_port *i2c,
-                       struct i2c_board_info *info, void *data)
-{
-       struct nouveau_therm_priv *priv = data;
-       struct nvbios_therm_sensor *sensor = &priv->bios_sensor;
-       struct i2c_client *client;
-
-       request_module("%s%s", I2C_MODULE_PREFIX, info->type);
-
-       client = i2c_new_device(&i2c->adapter, info);
-       if (!client)
-               return false;
-
-       if (!client->dev.driver ||
-           to_i2c_driver(client->dev.driver)->detect(client, info)) {
-               i2c_unregister_device(client);
-               return false;
-       }
-
-       nv_info(priv,
-               "Found an %s at address 0x%x (controlled by lm_sensors, "
-               "temp offset %+i C)\n",
-               info->type, info->addr, sensor->offset_constant);
-       priv->ic = client;
-
-       return true;
-}
-
-static struct nouveau_i2c_board_info
-nv_board_infos[] = {
-       { { I2C_BOARD_INFO("w83l785ts", 0x2d) }, 0 },
-       { { I2C_BOARD_INFO("w83781d", 0x2d) }, 0  },
-       { { I2C_BOARD_INFO("adt7473", 0x2e) }, 40  },
-       { { I2C_BOARD_INFO("adt7473", 0x2d) }, 40  },
-       { { I2C_BOARD_INFO("adt7473", 0x2c) }, 40  },
-       { { I2C_BOARD_INFO("f75375", 0x2e) }, 0  },
-       { { I2C_BOARD_INFO("lm99", 0x4c) }, 0  },
-       { { I2C_BOARD_INFO("lm90", 0x4c) }, 0  },
-       { { I2C_BOARD_INFO("lm90", 0x4d) }, 0  },
-       { { I2C_BOARD_INFO("adm1021", 0x18) }, 0  },
-       { { I2C_BOARD_INFO("adm1021", 0x19) }, 0  },
-       { { I2C_BOARD_INFO("adm1021", 0x1a) }, 0  },
-       { { I2C_BOARD_INFO("adm1021", 0x29) }, 0  },
-       { { I2C_BOARD_INFO("adm1021", 0x2a) }, 0  },
-       { { I2C_BOARD_INFO("adm1021", 0x2b) }, 0  },
-       { { I2C_BOARD_INFO("adm1021", 0x4c) }, 0  },
-       { { I2C_BOARD_INFO("adm1021", 0x4d) }, 0  },
-       { { I2C_BOARD_INFO("adm1021", 0x4e) }, 0  },
-       { { I2C_BOARD_INFO("lm63", 0x18) }, 0  },
-       { { I2C_BOARD_INFO("lm63", 0x4e) }, 0  },
-       { }
-};
-
-void
-nouveau_therm_ic_ctor(struct nouveau_therm *therm)
-{
-       struct nouveau_therm_priv *priv = (void *)therm;
-       struct nouveau_bios *bios = nouveau_bios(therm);
-       struct nouveau_i2c *i2c = nouveau_i2c(therm);
-       struct nvbios_extdev_func extdev_entry;
-
-       if (!nvbios_extdev_find(bios, NVBIOS_EXTDEV_LM89, &extdev_entry)) {
-               struct nouveau_i2c_board_info board[] = {
-                 { { I2C_BOARD_INFO("lm90", extdev_entry.addr >> 1) }, 0},
-                 { }
-               };
-
-               i2c->identify(i2c, NV_I2C_DEFAULT(0), "monitoring device",
-                             board, probe_monitoring_device, therm);
-               if (priv->ic)
-                       return;
-       }
-
-       if (!nvbios_extdev_find(bios, NVBIOS_EXTDEV_ADT7473, &extdev_entry)) {
-               struct nouveau_i2c_board_info board[] = {
-                 { { I2C_BOARD_INFO("adt7473", extdev_entry.addr >> 1) }, 20 },
-                 { }
-               };
-
-               i2c->identify(i2c, NV_I2C_DEFAULT(0), "monitoring device",
-                             board, probe_monitoring_device, therm);
-               if (priv->ic)
-                       return;
-       }
-
-       /* The vbios doesn't provide the address of an exisiting monitoring
-          device. Let's try our static list.
-        */
-       i2c->identify(i2c, NV_I2C_DEFAULT(0), "monitoring device",
-                     nv_board_infos, probe_monitoring_device, therm);
-}
diff --git a/drivers/gpu/drm/nouveau/core/subdev/therm/nv40.c b/drivers/gpu/drm/nouveau/core/subdev/therm/nv40.c
deleted file mode 100644 (file)
index 002e51b..0000000
+++ /dev/null
@@ -1,224 +0,0 @@
-/*
- * Copyright 2012 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
- *         Martin Peres
- */
-
-#include "priv.h"
-
-struct nv40_therm_priv {
-       struct nouveau_therm_priv base;
-};
-
-enum nv40_sensor_style { INVALID_STYLE = -1, OLD_STYLE = 0, NEW_STYLE = 1 };
-
-static enum nv40_sensor_style
-nv40_sensor_style(struct nouveau_therm *therm)
-{
-       struct nouveau_device *device = nv_device(therm);
-
-       switch (device->chipset) {
-       case 0x43:
-       case 0x44:
-       case 0x4a:
-       case 0x47:
-               return OLD_STYLE;
-
-       case 0x46:
-       case 0x49:
-       case 0x4b:
-       case 0x4e:
-       case 0x4c:
-       case 0x67:
-       case 0x68:
-       case 0x63:
-               return NEW_STYLE;
-       default:
-               return INVALID_STYLE;
-       }
-}
-
-static int
-nv40_sensor_setup(struct nouveau_therm *therm)
-{
-       enum nv40_sensor_style style = nv40_sensor_style(therm);
-
-       /* enable ADC readout and disable the ALARM threshold */
-       if (style == NEW_STYLE) {
-               nv_mask(therm, 0x15b8, 0x80000000, 0);
-               nv_wr32(therm, 0x15b0, 0x80003fff);
-               mdelay(20); /* wait for the temperature to stabilize */
-               return nv_rd32(therm, 0x15b4) & 0x3fff;
-       } else if (style == OLD_STYLE) {
-               nv_wr32(therm, 0x15b0, 0xff);
-               mdelay(20); /* wait for the temperature to stabilize */
-               return nv_rd32(therm, 0x15b4) & 0xff;
-       } else
-               return -ENODEV;
-}
-
-static int
-nv40_temp_get(struct nouveau_therm *therm)
-{
-       struct nouveau_therm_priv *priv = (void *)therm;
-       struct nvbios_therm_sensor *sensor = &priv->bios_sensor;
-       enum nv40_sensor_style style = nv40_sensor_style(therm);
-       int core_temp;
-
-       if (style == NEW_STYLE) {
-               nv_wr32(therm, 0x15b0, 0x80003fff);
-               core_temp = nv_rd32(therm, 0x15b4) & 0x3fff;
-       } else if (style == OLD_STYLE) {
-               nv_wr32(therm, 0x15b0, 0xff);
-               core_temp = nv_rd32(therm, 0x15b4) & 0xff;
-       } else
-               return -ENODEV;
-
-       /* if the slope or the offset is unset, do no use the sensor */
-       if (!sensor->slope_div || !sensor->slope_mult ||
-           !sensor->offset_num || !sensor->offset_den)
-           return -ENODEV;
-
-       core_temp = core_temp * sensor->slope_mult / sensor->slope_div;
-       core_temp = core_temp + sensor->offset_num / sensor->offset_den;
-       core_temp = core_temp + sensor->offset_constant - 8;
-
-       /* reserve negative temperatures for errors */
-       if (core_temp < 0)
-               core_temp = 0;
-
-       return core_temp;
-}
-
-static int
-nv40_fan_pwm_ctrl(struct nouveau_therm *therm, int line, bool enable)
-{
-       u32 mask = enable ? 0x80000000 : 0x0000000;
-       if      (line == 2) nv_mask(therm, 0x0010f0, 0x80000000, mask);
-       else if (line == 9) nv_mask(therm, 0x0015f4, 0x80000000, mask);
-       else {
-               nv_error(therm, "unknown pwm ctrl for gpio %d\n", line);
-               return -ENODEV;
-       }
-       return 0;
-}
-
-static int
-nv40_fan_pwm_get(struct nouveau_therm *therm, int line, u32 *divs, u32 *duty)
-{
-       if (line == 2) {
-               u32 reg = nv_rd32(therm, 0x0010f0);
-               if (reg & 0x80000000) {
-                       *duty = (reg & 0x7fff0000) >> 16;
-                       *divs = (reg & 0x00007fff);
-                       return 0;
-               }
-       } else
-       if (line == 9) {
-               u32 reg = nv_rd32(therm, 0x0015f4);
-               if (reg & 0x80000000) {
-                       *divs = nv_rd32(therm, 0x0015f8);
-                       *duty = (reg & 0x7fffffff);
-                       return 0;
-               }
-       } else {
-               nv_error(therm, "unknown pwm ctrl for gpio %d\n", line);
-               return -ENODEV;
-       }
-
-       return -EINVAL;
-}
-
-static int
-nv40_fan_pwm_set(struct nouveau_therm *therm, int line, u32 divs, u32 duty)
-{
-       if (line == 2) {
-               nv_mask(therm, 0x0010f0, 0x7fff7fff, (duty << 16) | divs);
-       } else
-       if (line == 9) {
-               nv_wr32(therm, 0x0015f8, divs);
-               nv_mask(therm, 0x0015f4, 0x7fffffff, duty);
-       } else {
-               nv_error(therm, "unknown pwm ctrl for gpio %d\n", line);
-               return -ENODEV;
-       }
-
-       return 0;
-}
-
-void
-nv40_therm_intr(struct nouveau_subdev *subdev)
-{
-       struct nouveau_therm *therm = nouveau_therm(subdev);
-       uint32_t stat = nv_rd32(therm, 0x1100);
-
-       /* traitement */
-
-       /* ack all IRQs */
-       nv_wr32(therm, 0x1100, 0x70000);
-
-       nv_error(therm, "THERM received an IRQ: stat = %x\n", stat);
-}
-
-static int
-nv40_therm_ctor(struct nouveau_object *parent,
-               struct nouveau_object *engine,
-               struct nouveau_oclass *oclass, void *data, u32 size,
-               struct nouveau_object **pobject)
-{
-       struct nv40_therm_priv *priv;
-       int ret;
-
-       ret = nouveau_therm_create(parent, engine, oclass, &priv);
-       *pobject = nv_object(priv);
-       if (ret)
-               return ret;
-
-       priv->base.base.pwm_ctrl = nv40_fan_pwm_ctrl;
-       priv->base.base.pwm_get = nv40_fan_pwm_get;
-       priv->base.base.pwm_set = nv40_fan_pwm_set;
-       priv->base.base.temp_get = nv40_temp_get;
-       priv->base.sensor.program_alarms = nouveau_therm_program_alarms_polling;
-       nv_subdev(priv)->intr = nv40_therm_intr;
-       return nouveau_therm_preinit(&priv->base.base);
-}
-
-static int
-nv40_therm_init(struct nouveau_object *object)
-{
-       struct nouveau_therm *therm = (void *)object;
-
-       nv40_sensor_setup(therm);
-
-       return _nouveau_therm_init(object);
-}
-
-struct nouveau_oclass
-nv40_therm_oclass = {
-       .handle = NV_SUBDEV(THERM, 0x40),
-       .ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nv40_therm_ctor,
-               .dtor = _nouveau_therm_dtor,
-               .init = nv40_therm_init,
-               .fini = _nouveau_therm_fini,
-       },
-};
diff --git a/drivers/gpu/drm/nouveau/core/subdev/therm/nv50.c b/drivers/gpu/drm/nouveau/core/subdev/therm/nv50.c
deleted file mode 100644 (file)
index 321db92..0000000
+++ /dev/null
@@ -1,197 +0,0 @@
-/*
- * Copyright 2012 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
- *         Martin Peres
- */
-
-#include "priv.h"
-
-struct nv50_therm_priv {
-       struct nouveau_therm_priv base;
-};
-
-static int
-pwm_info(struct nouveau_therm *therm, int *line, int *ctrl, int *indx)
-{
-       if (*line == 0x04) {
-               *ctrl = 0x00e100;
-               *line = 4;
-               *indx = 0;
-       } else
-       if (*line == 0x09) {
-               *ctrl = 0x00e100;
-               *line = 9;
-               *indx = 1;
-       } else
-       if (*line == 0x10) {
-               *ctrl = 0x00e28c;
-               *line = 0;
-               *indx = 0;
-       } else {
-               nv_error(therm, "unknown pwm ctrl for gpio %d\n", *line);
-               return -ENODEV;
-       }
-
-       return 0;
-}
-
-int
-nv50_fan_pwm_ctrl(struct nouveau_therm *therm, int line, bool enable)
-{
-       u32 data = enable ? 0x00000001 : 0x00000000;
-       int ctrl, id, ret = pwm_info(therm, &line, &ctrl, &id);
-       if (ret == 0)
-               nv_mask(therm, ctrl, 0x00010001 << line, data << line);
-       return ret;
-}
-
-int
-nv50_fan_pwm_get(struct nouveau_therm *therm, int line, u32 *divs, u32 *duty)
-{
-       int ctrl, id, ret = pwm_info(therm, &line, &ctrl, &id);
-       if (ret)
-               return ret;
-
-       if (nv_rd32(therm, ctrl) & (1 << line)) {
-               *divs = nv_rd32(therm, 0x00e114 + (id * 8));
-               *duty = nv_rd32(therm, 0x00e118 + (id * 8));
-               return 0;
-       }
-
-       return -EINVAL;
-}
-
-int
-nv50_fan_pwm_set(struct nouveau_therm *therm, int line, u32 divs, u32 duty)
-{
-       int ctrl, id, ret = pwm_info(therm, &line, &ctrl, &id);
-       if (ret)
-               return ret;
-
-       nv_wr32(therm, 0x00e114 + (id * 8), divs);
-       nv_wr32(therm, 0x00e118 + (id * 8), duty | 0x80000000);
-       return 0;
-}
-
-int
-nv50_fan_pwm_clock(struct nouveau_therm *therm, int line)
-{
-       int chipset = nv_device(therm)->chipset;
-       int crystal = nv_device(therm)->crystal;
-       int pwm_clock;
-
-       /* determine the PWM source clock */
-       if (chipset > 0x50 && chipset < 0x94) {
-               u8 pwm_div = nv_rd32(therm, 0x410c);
-               if (nv_rd32(therm, 0xc040) & 0x800000) {
-                       /* Use the HOST clock (100 MHz)
-                       * Where does this constant(2.4) comes from? */
-                       pwm_clock = (100000000 >> pwm_div) * 10 / 24;
-               } else {
-                       /* Where does this constant(20) comes from? */
-                       pwm_clock = (crystal * 1000) >> pwm_div;
-                       pwm_clock /= 20;
-               }
-       } else {
-               pwm_clock = (crystal * 1000) / 20;
-       }
-
-       return pwm_clock;
-}
-
-static void
-nv50_sensor_setup(struct nouveau_therm *therm)
-{
-       nv_mask(therm, 0x20010, 0x40000000, 0x0);
-       mdelay(20); /* wait for the temperature to stabilize */
-}
-
-static int
-nv50_temp_get(struct nouveau_therm *therm)
-{
-       struct nouveau_therm_priv *priv = (void *)therm;
-       struct nvbios_therm_sensor *sensor = &priv->bios_sensor;
-       int core_temp;
-
-       core_temp = nv_rd32(therm, 0x20014) & 0x3fff;
-
-       /* if the slope or the offset is unset, do no use the sensor */
-       if (!sensor->slope_div || !sensor->slope_mult ||
-           !sensor->offset_num || !sensor->offset_den)
-           return -ENODEV;
-
-       core_temp = core_temp * sensor->slope_mult / sensor->slope_div;
-       core_temp = core_temp + sensor->offset_num / sensor->offset_den;
-       core_temp = core_temp + sensor->offset_constant - 8;
-
-       /* reserve negative temperatures for errors */
-       if (core_temp < 0)
-               core_temp = 0;
-
-       return core_temp;
-}
-
-static int
-nv50_therm_ctor(struct nouveau_object *parent,
-               struct nouveau_object *engine,
-               struct nouveau_oclass *oclass, void *data, u32 size,
-               struct nouveau_object **pobject)
-{
-       struct nv50_therm_priv *priv;
-       int ret;
-
-       ret = nouveau_therm_create(parent, engine, oclass, &priv);
-       *pobject = nv_object(priv);
-       if (ret)
-               return ret;
-
-       priv->base.base.pwm_ctrl = nv50_fan_pwm_ctrl;
-       priv->base.base.pwm_get = nv50_fan_pwm_get;
-       priv->base.base.pwm_set = nv50_fan_pwm_set;
-       priv->base.base.pwm_clock = nv50_fan_pwm_clock;
-       priv->base.base.temp_get = nv50_temp_get;
-       priv->base.sensor.program_alarms = nouveau_therm_program_alarms_polling;
-       nv_subdev(priv)->intr = nv40_therm_intr;
-
-       return nouveau_therm_preinit(&priv->base.base);
-}
-
-static int
-nv50_therm_init(struct nouveau_object *object)
-{
-       struct nouveau_therm *therm = (void *)object;
-
-       nv50_sensor_setup(therm);
-
-       return _nouveau_therm_init(object);
-}
-
-struct nouveau_oclass
-nv50_therm_oclass = {
-       .handle = NV_SUBDEV(THERM, 0x50),
-       .ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nv50_therm_ctor,
-               .dtor = _nouveau_therm_dtor,
-               .init = nv50_therm_init,
-               .fini = _nouveau_therm_fini,
-       },
-};
diff --git a/drivers/gpu/drm/nouveau/core/subdev/therm/nv84.c b/drivers/gpu/drm/nouveau/core/subdev/therm/nv84.c
deleted file mode 100644 (file)
index 14e2e09..0000000
+++ /dev/null
@@ -1,268 +0,0 @@
-/*
- * Copyright 2012 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
- *         Martin Peres
- */
-
-#include "priv.h"
-#include <subdev/fuse.h>
-
-struct nv84_therm_priv {
-       struct nouveau_therm_priv base;
-};
-
-int
-nv84_temp_get(struct nouveau_therm *therm)
-{
-       struct nouveau_fuse *fuse = nouveau_fuse(therm);
-
-       if (nv_ro32(fuse, 0x1a8) == 1)
-               return nv_rd32(therm, 0x20400);
-       else
-               return -ENODEV;
-}
-
-void
-nv84_sensor_setup(struct nouveau_therm *therm)
-{
-       struct nouveau_fuse *fuse = nouveau_fuse(therm);
-
-       /* enable temperature reading for cards with insane defaults */
-       if (nv_ro32(fuse, 0x1a8) == 1) {
-               nv_mask(therm, 0x20008, 0x80008000, 0x80000000);
-               nv_mask(therm, 0x2000c, 0x80000003, 0x00000000);
-               mdelay(20); /* wait for the temperature to stabilize */
-       }
-}
-
-static void
-nv84_therm_program_alarms(struct nouveau_therm *therm)
-{
-       struct nouveau_therm_priv *priv = (void *)therm;
-       struct nvbios_therm_sensor *sensor = &priv->bios_sensor;
-       unsigned long flags;
-
-       spin_lock_irqsave(&priv->sensor.alarm_program_lock, flags);
-
-       /* enable RISING and FALLING IRQs for shutdown, THRS 0, 1, 2 and 4 */
-       nv_wr32(therm, 0x20000, 0x000003ff);
-
-       /* shutdown: The computer should be shutdown when reached */
-       nv_wr32(therm, 0x20484, sensor->thrs_shutdown.hysteresis);
-       nv_wr32(therm, 0x20480, sensor->thrs_shutdown.temp);
-
-       /* THRS_1 : fan boost*/
-       nv_wr32(therm, 0x204c4, sensor->thrs_fan_boost.temp);
-
-       /* THRS_2 : critical */
-       nv_wr32(therm, 0x204c0, sensor->thrs_critical.temp);
-
-       /* THRS_4 : down clock */
-       nv_wr32(therm, 0x20414, sensor->thrs_down_clock.temp);
-       spin_unlock_irqrestore(&priv->sensor.alarm_program_lock, flags);
-
-       nv_debug(therm,
-                "Programmed thresholds [ %d(%d), %d(%d), %d(%d), %d(%d) ]\n",
-                sensor->thrs_fan_boost.temp, sensor->thrs_fan_boost.hysteresis,
-                sensor->thrs_down_clock.temp,
-                sensor->thrs_down_clock.hysteresis,
-                sensor->thrs_critical.temp, sensor->thrs_critical.hysteresis,
-                sensor->thrs_shutdown.temp, sensor->thrs_shutdown.hysteresis);
-
-}
-
-/* must be called with alarm_program_lock taken ! */
-static void
-nv84_therm_threshold_hyst_emulation(struct nouveau_therm *therm,
-                                  uint32_t thrs_reg, u8 status_bit,
-                                  const struct nvbios_therm_threshold *thrs,
-                                  enum nouveau_therm_thrs thrs_name)
-{
-       enum nouveau_therm_thrs_direction direction;
-       enum nouveau_therm_thrs_state prev_state, new_state;
-       int temp, cur;
-
-       prev_state = nouveau_therm_sensor_get_threshold_state(therm, thrs_name);
-       temp = nv_rd32(therm, thrs_reg);
-
-       /* program the next threshold */
-       if (temp == thrs->temp) {
-               nv_wr32(therm, thrs_reg, thrs->temp - thrs->hysteresis);
-               new_state = NOUVEAU_THERM_THRS_HIGHER;
-       } else {
-               nv_wr32(therm, thrs_reg, thrs->temp);
-               new_state = NOUVEAU_THERM_THRS_LOWER;
-       }
-
-       /* fix the state (in case someone reprogrammed the alarms) */
-       cur = therm->temp_get(therm);
-       if (new_state == NOUVEAU_THERM_THRS_LOWER && cur > thrs->temp)
-               new_state = NOUVEAU_THERM_THRS_HIGHER;
-       else if (new_state == NOUVEAU_THERM_THRS_HIGHER &&
-               cur < thrs->temp - thrs->hysteresis)
-               new_state = NOUVEAU_THERM_THRS_LOWER;
-       nouveau_therm_sensor_set_threshold_state(therm, thrs_name, new_state);
-
-       /* find the direction */
-       if (prev_state < new_state)
-               direction = NOUVEAU_THERM_THRS_RISING;
-       else if (prev_state > new_state)
-               direction = NOUVEAU_THERM_THRS_FALLING;
-       else
-               return;
-
-       /* advertise a change in direction */
-       nouveau_therm_sensor_event(therm, thrs_name, direction);
-}
-
-static void
-nv84_therm_intr(struct nouveau_subdev *subdev)
-{
-       struct nouveau_therm *therm = nouveau_therm(subdev);
-       struct nouveau_therm_priv *priv = (void *)therm;
-       struct nvbios_therm_sensor *sensor = &priv->bios_sensor;
-       unsigned long flags;
-       uint32_t intr;
-
-       spin_lock_irqsave(&priv->sensor.alarm_program_lock, flags);
-
-       intr = nv_rd32(therm, 0x20100) & 0x3ff;
-
-       /* THRS_4: downclock */
-       if (intr & 0x002) {
-               nv84_therm_threshold_hyst_emulation(therm, 0x20414, 24,
-                                                 &sensor->thrs_down_clock,
-                                                 NOUVEAU_THERM_THRS_DOWNCLOCK);
-               intr &= ~0x002;
-       }
-
-       /* shutdown */
-       if (intr & 0x004) {
-               nv84_therm_threshold_hyst_emulation(therm, 0x20480, 20,
-                                                  &sensor->thrs_shutdown,
-                                                  NOUVEAU_THERM_THRS_SHUTDOWN);
-               intr &= ~0x004;
-       }
-
-       /* THRS_1 : fan boost */
-       if (intr & 0x008) {
-               nv84_therm_threshold_hyst_emulation(therm, 0x204c4, 21,
-                                                  &sensor->thrs_fan_boost,
-                                                  NOUVEAU_THERM_THRS_FANBOOST);
-               intr &= ~0x008;
-       }
-
-       /* THRS_2 : critical */
-       if (intr & 0x010) {
-               nv84_therm_threshold_hyst_emulation(therm, 0x204c0, 22,
-                                                  &sensor->thrs_critical,
-                                                  NOUVEAU_THERM_THRS_CRITICAL);
-               intr &= ~0x010;
-       }
-
-       if (intr)
-               nv_error(therm, "unhandled intr 0x%08x\n", intr);
-
-       /* ACK everything */
-       nv_wr32(therm, 0x20100, 0xffffffff);
-       nv_wr32(therm, 0x1100, 0x10000); /* PBUS */
-
-       spin_unlock_irqrestore(&priv->sensor.alarm_program_lock, flags);
-}
-
-static int
-nv84_therm_init(struct nouveau_object *object)
-{
-       struct nv84_therm_priv *priv = (void *)object;
-       int ret;
-
-       ret = nouveau_therm_init(&priv->base.base);
-       if (ret)
-               return ret;
-
-       nv84_sensor_setup(&priv->base.base);
-
-       return 0;
-}
-
-static int
-nv84_therm_ctor(struct nouveau_object *parent,
-               struct nouveau_object *engine,
-               struct nouveau_oclass *oclass, void *data, u32 size,
-               struct nouveau_object **pobject)
-{
-       struct nv84_therm_priv *priv;
-       int ret;
-
-       ret = nouveau_therm_create(parent, engine, oclass, &priv);
-       *pobject = nv_object(priv);
-       if (ret)
-               return ret;
-
-       priv->base.base.pwm_ctrl = nv50_fan_pwm_ctrl;
-       priv->base.base.pwm_get = nv50_fan_pwm_get;
-       priv->base.base.pwm_set = nv50_fan_pwm_set;
-       priv->base.base.pwm_clock = nv50_fan_pwm_clock;
-       priv->base.base.temp_get = nv84_temp_get;
-       priv->base.sensor.program_alarms = nv84_therm_program_alarms;
-       nv_subdev(priv)->intr = nv84_therm_intr;
-
-       /* init the thresholds */
-       nouveau_therm_sensor_set_threshold_state(&priv->base.base,
-                                                NOUVEAU_THERM_THRS_SHUTDOWN,
-                                                NOUVEAU_THERM_THRS_LOWER);
-       nouveau_therm_sensor_set_threshold_state(&priv->base.base,
-                                                NOUVEAU_THERM_THRS_FANBOOST,
-                                                NOUVEAU_THERM_THRS_LOWER);
-       nouveau_therm_sensor_set_threshold_state(&priv->base.base,
-                                                NOUVEAU_THERM_THRS_CRITICAL,
-                                                NOUVEAU_THERM_THRS_LOWER);
-       nouveau_therm_sensor_set_threshold_state(&priv->base.base,
-                                                NOUVEAU_THERM_THRS_DOWNCLOCK,
-                                                NOUVEAU_THERM_THRS_LOWER);
-
-       return nouveau_therm_preinit(&priv->base.base);
-}
-
-int
-nv84_therm_fini(struct nouveau_object *object, bool suspend)
-{
-       /* Disable PTherm IRQs */
-       nv_wr32(object, 0x20000, 0x00000000);
-
-       /* ACK all PTherm IRQs */
-       nv_wr32(object, 0x20100, 0xffffffff);
-       nv_wr32(object, 0x1100, 0x10000); /* PBUS */
-
-       return _nouveau_therm_fini(object, suspend);
-}
-
-struct nouveau_oclass
-nv84_therm_oclass = {
-       .handle = NV_SUBDEV(THERM, 0x84),
-       .ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nv84_therm_ctor,
-               .dtor = _nouveau_therm_dtor,
-               .init = nv84_therm_init,
-               .fini = nv84_therm_fini,
-       },
-};
diff --git a/drivers/gpu/drm/nouveau/core/subdev/therm/nva3.c b/drivers/gpu/drm/nouveau/core/subdev/therm/nva3.c
deleted file mode 100644 (file)
index 7893357..0000000
+++ /dev/null
@@ -1,101 +0,0 @@
-/*
- * Copyright 2012 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 <subdev/gpio.h>
-
-#include "priv.h"
-
-struct nva3_therm_priv {
-       struct nouveau_therm_priv base;
-};
-
-int
-nva3_therm_fan_sense(struct nouveau_therm *therm)
-{
-       u32 tach = nv_rd32(therm, 0x00e728) & 0x0000ffff;
-       u32 ctrl = nv_rd32(therm, 0x00e720);
-       if (ctrl & 0x00000001)
-               return tach * 60 / 2;
-       return -ENODEV;
-}
-
-static int
-nva3_therm_init(struct nouveau_object *object)
-{
-       struct nva3_therm_priv *priv = (void *)object;
-       struct dcb_gpio_func *tach = &priv->base.fan->tach;
-       int ret;
-
-       ret = nouveau_therm_init(&priv->base.base);
-       if (ret)
-               return ret;
-
-       nv84_sensor_setup(&priv->base.base);
-
-       /* enable fan tach, count revolutions per-second */
-       nv_mask(priv, 0x00e720, 0x00000003, 0x00000002);
-       if (tach->func != DCB_GPIO_UNUSED) {
-               nv_wr32(priv, 0x00e724, nv_device(priv)->crystal * 1000);
-               nv_mask(priv, 0x00e720, 0x001f0000, tach->line << 16);
-               nv_mask(priv, 0x00e720, 0x00000001, 0x00000001);
-       }
-       nv_mask(priv, 0x00e720, 0x00000002, 0x00000000);
-
-       return 0;
-}
-
-static int
-nva3_therm_ctor(struct nouveau_object *parent,
-               struct nouveau_object *engine,
-               struct nouveau_oclass *oclass, void *data, u32 size,
-               struct nouveau_object **pobject)
-{
-       struct nva3_therm_priv *priv;
-       int ret;
-
-       ret = nouveau_therm_create(parent, engine, oclass, &priv);
-       *pobject = nv_object(priv);
-       if (ret)
-               return ret;
-
-       priv->base.base.pwm_ctrl = nv50_fan_pwm_ctrl;
-       priv->base.base.pwm_get = nv50_fan_pwm_get;
-       priv->base.base.pwm_set = nv50_fan_pwm_set;
-       priv->base.base.pwm_clock = nv50_fan_pwm_clock;
-       priv->base.base.temp_get = nv84_temp_get;
-       priv->base.base.fan_sense = nva3_therm_fan_sense;
-       priv->base.sensor.program_alarms = nouveau_therm_program_alarms_polling;
-       return nouveau_therm_preinit(&priv->base.base);
-}
-
-struct nouveau_oclass
-nva3_therm_oclass = {
-       .handle = NV_SUBDEV(THERM, 0xa3),
-       .ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nva3_therm_ctor,
-               .dtor = _nouveau_therm_dtor,
-               .init = nva3_therm_init,
-               .fini = nv84_therm_fini,
-       },
-};
diff --git a/drivers/gpu/drm/nouveau/core/subdev/therm/nvd0.c b/drivers/gpu/drm/nouveau/core/subdev/therm/nvd0.c
deleted file mode 100644 (file)
index b70f7cc..0000000
+++ /dev/null
@@ -1,174 +0,0 @@
-/*
- * Copyright 2012 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 "priv.h"
-
-struct nvd0_therm_priv {
-       struct nouveau_therm_priv base;
-};
-
-static int
-pwm_info(struct nouveau_therm *therm, int line)
-{
-       u32 gpio = nv_rd32(therm, 0x00d610 + (line * 0x04));
-
-       switch (gpio & 0x000000c0) {
-       case 0x00000000: /* normal mode, possibly pwm forced off by us */
-       case 0x00000040: /* nvio special */
-               switch (gpio & 0x0000001f) {
-               case 0x00: return 2;
-               case 0x19: return 1;
-               case 0x1c: return 0;
-               case 0x1e: return 2;
-               default:
-                       break;
-               }
-       default:
-               break;
-       }
-
-       nv_error(therm, "GPIO %d unknown PWM: 0x%08x\n", line, gpio);
-       return -ENODEV;
-}
-
-static int
-nvd0_fan_pwm_ctrl(struct nouveau_therm *therm, int line, bool enable)
-{
-       u32 data = enable ? 0x00000040 : 0x00000000;
-       int indx = pwm_info(therm, line);
-       if (indx < 0)
-               return indx;
-       else if (indx < 2)
-               nv_mask(therm, 0x00d610 + (line * 0x04), 0x000000c0, data);
-       /* nothing to do for indx == 2, it seems hardwired to PTHERM */
-       return 0;
-}
-
-static int
-nvd0_fan_pwm_get(struct nouveau_therm *therm, int line, u32 *divs, u32 *duty)
-{
-       int indx = pwm_info(therm, line);
-       if (indx < 0)
-               return indx;
-       else if (indx < 2) {
-               if (nv_rd32(therm, 0x00d610 + (line * 0x04)) & 0x00000040) {
-                       *divs = nv_rd32(therm, 0x00e114 + (indx * 8));
-                       *duty = nv_rd32(therm, 0x00e118 + (indx * 8));
-                       return 0;
-               }
-       } else if (indx == 2) {
-               *divs = nv_rd32(therm, 0x0200d8) & 0x1fff;
-               *duty = nv_rd32(therm, 0x0200dc) & 0x1fff;
-               return 0;
-       }
-
-       return -EINVAL;
-}
-
-static int
-nvd0_fan_pwm_set(struct nouveau_therm *therm, int line, u32 divs, u32 duty)
-{
-       int indx = pwm_info(therm, line);
-       if (indx < 0)
-               return indx;
-       else if (indx < 2) {
-               nv_wr32(therm, 0x00e114 + (indx * 8), divs);
-               nv_wr32(therm, 0x00e118 + (indx * 8), duty | 0x80000000);
-       } else if (indx == 2) {
-               nv_mask(therm, 0x0200d8, 0x1fff, divs); /* keep the high bits */
-               nv_wr32(therm, 0x0200dc, duty | 0x40000000);
-       }
-       return 0;
-}
-
-static int
-nvd0_fan_pwm_clock(struct nouveau_therm *therm, int line)
-{
-       int indx = pwm_info(therm, line);
-       if (indx < 0)
-               return 0;
-       else if (indx < 2)
-               return (nv_device(therm)->crystal * 1000) / 20;
-       else
-               return nv_device(therm)->crystal * 1000 / 10;
-}
-
-int
-nvd0_therm_init(struct nouveau_object *object)
-{
-       struct nvd0_therm_priv *priv = (void *)object;
-       int ret;
-
-       ret = nouveau_therm_init(&priv->base.base);
-       if (ret)
-               return ret;
-
-       /* enable fan tach, count revolutions per-second */
-       nv_mask(priv, 0x00e720, 0x00000003, 0x00000002);
-       if (priv->base.fan->tach.func != DCB_GPIO_UNUSED) {
-               nv_mask(priv, 0x00d79c, 0x000000ff, priv->base.fan->tach.line);
-               nv_wr32(priv, 0x00e724, nv_device(priv)->crystal * 1000);
-               nv_mask(priv, 0x00e720, 0x00000001, 0x00000001);
-       }
-       nv_mask(priv, 0x00e720, 0x00000002, 0x00000000);
-
-       return 0;
-}
-
-static int
-nvd0_therm_ctor(struct nouveau_object *parent,
-               struct nouveau_object *engine,
-               struct nouveau_oclass *oclass, void *data, u32 size,
-               struct nouveau_object **pobject)
-{
-       struct nvd0_therm_priv *priv;
-       int ret;
-
-       ret = nouveau_therm_create(parent, engine, oclass, &priv);
-       *pobject = nv_object(priv);
-       if (ret)
-               return ret;
-
-       nv84_sensor_setup(&priv->base.base);
-
-       priv->base.base.pwm_ctrl = nvd0_fan_pwm_ctrl;
-       priv->base.base.pwm_get = nvd0_fan_pwm_get;
-       priv->base.base.pwm_set = nvd0_fan_pwm_set;
-       priv->base.base.pwm_clock = nvd0_fan_pwm_clock;
-       priv->base.base.temp_get = nv84_temp_get;
-       priv->base.base.fan_sense = nva3_therm_fan_sense;
-       priv->base.sensor.program_alarms = nouveau_therm_program_alarms_polling;
-       return nouveau_therm_preinit(&priv->base.base);
-}
-
-struct nouveau_oclass
-nvd0_therm_oclass = {
-       .handle = NV_SUBDEV(THERM, 0xd0),
-       .ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nvd0_therm_ctor,
-               .dtor = _nouveau_therm_dtor,
-               .init = nvd0_therm_init,
-               .fini = nv84_therm_fini,
-       },
-};
diff --git a/drivers/gpu/drm/nouveau/core/subdev/therm/priv.h b/drivers/gpu/drm/nouveau/core/subdev/therm/priv.h
deleted file mode 100644 (file)
index 7dba8c2..0000000
+++ /dev/null
@@ -1,159 +0,0 @@
-#ifndef __NVTHERM_PRIV_H__
-#define __NVTHERM_PRIV_H__
-
-/*
- * Copyright 2012 The Nouveau community
- *
- * 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 <subdev/therm.h>
-
-#include <subdev/bios/extdev.h>
-#include <subdev/bios/gpio.h>
-#include <subdev/bios/perf.h>
-#include <subdev/bios/therm.h>
-#include <subdev/timer.h>
-
-struct nouveau_fan {
-       struct nouveau_therm *parent;
-       const char *type;
-
-       struct nvbios_therm_fan bios;
-       struct nvbios_perf_fan perf;
-
-       struct nouveau_alarm alarm;
-       spinlock_t lock;
-       int percent;
-
-       int (*get)(struct nouveau_therm *therm);
-       int (*set)(struct nouveau_therm *therm, int percent);
-
-       struct dcb_gpio_func tach;
-};
-
-enum nouveau_therm_thrs_direction {
-       NOUVEAU_THERM_THRS_FALLING = 0,
-       NOUVEAU_THERM_THRS_RISING = 1
-};
-
-enum nouveau_therm_thrs_state {
-       NOUVEAU_THERM_THRS_LOWER = 0,
-       NOUVEAU_THERM_THRS_HIGHER = 1
-};
-
-enum nouveau_therm_thrs {
-       NOUVEAU_THERM_THRS_FANBOOST = 0,
-       NOUVEAU_THERM_THRS_DOWNCLOCK = 1,
-       NOUVEAU_THERM_THRS_CRITICAL = 2,
-       NOUVEAU_THERM_THRS_SHUTDOWN = 3,
-       NOUVEAU_THERM_THRS_NR
-};
-
-struct nouveau_therm_priv {
-       struct nouveau_therm base;
-
-       /* automatic thermal management */
-       struct nouveau_alarm alarm;
-       spinlock_t lock;
-       struct nouveau_therm_trip_point *last_trip;
-       int mode;
-       int cstate;
-       int suspend;
-
-       /* bios */
-       struct nvbios_therm_sensor bios_sensor;
-
-       /* fan priv */
-       struct nouveau_fan *fan;
-
-       /* alarms priv */
-       struct {
-               spinlock_t alarm_program_lock;
-               struct nouveau_alarm therm_poll_alarm;
-               enum nouveau_therm_thrs_state alarm_state[NOUVEAU_THERM_THRS_NR];
-               void (*program_alarms)(struct nouveau_therm *);
-       } sensor;
-
-       /* what should be done if the card overheats */
-       struct {
-               void (*downclock)(struct nouveau_therm *, bool active);
-               void (*pause)(struct nouveau_therm *, bool active);
-       } emergency;
-
-       /* ic */
-       struct i2c_client *ic;
-};
-
-int nouveau_therm_fan_mode(struct nouveau_therm *therm, int mode);
-int nouveau_therm_attr_get(struct nouveau_therm *therm,
-                      enum nouveau_therm_attr_type type);
-int nouveau_therm_attr_set(struct nouveau_therm *therm,
-                      enum nouveau_therm_attr_type type, int value);
-
-void nouveau_therm_ic_ctor(struct nouveau_therm *therm);
-
-int nouveau_therm_sensor_ctor(struct nouveau_therm *therm);
-
-int nouveau_therm_fan_ctor(struct nouveau_therm *therm);
-int nouveau_therm_fan_init(struct nouveau_therm *therm);
-int nouveau_therm_fan_fini(struct nouveau_therm *therm, bool suspend);
-int nouveau_therm_fan_get(struct nouveau_therm *therm);
-int nouveau_therm_fan_set(struct nouveau_therm *therm, bool now, int percent);
-int nouveau_therm_fan_user_get(struct nouveau_therm *therm);
-int nouveau_therm_fan_user_set(struct nouveau_therm *therm, int percent);
-
-int nouveau_therm_fan_sense(struct nouveau_therm *therm);
-
-int nouveau_therm_preinit(struct nouveau_therm *);
-
-int nouveau_therm_sensor_init(struct nouveau_therm *therm);
-int nouveau_therm_sensor_fini(struct nouveau_therm *therm, bool suspend);
-void nouveau_therm_sensor_preinit(struct nouveau_therm *);
-void nouveau_therm_sensor_set_threshold_state(struct nouveau_therm *therm,
-                                            enum nouveau_therm_thrs thrs,
-                                            enum nouveau_therm_thrs_state st);
-enum nouveau_therm_thrs_state
-nouveau_therm_sensor_get_threshold_state(struct nouveau_therm *therm,
-                                        enum nouveau_therm_thrs thrs);
-void nouveau_therm_sensor_event(struct nouveau_therm *therm,
-                               enum nouveau_therm_thrs thrs,
-                               enum nouveau_therm_thrs_direction dir);
-void nouveau_therm_program_alarms_polling(struct nouveau_therm *therm);
-
-void nv40_therm_intr(struct nouveau_subdev *);
-int nv50_fan_pwm_ctrl(struct nouveau_therm *, int, bool);
-int nv50_fan_pwm_get(struct nouveau_therm *, int, u32 *, u32 *);
-int nv50_fan_pwm_set(struct nouveau_therm *, int, u32, u32);
-int nv50_fan_pwm_clock(struct nouveau_therm *, int);
-int nv84_temp_get(struct nouveau_therm *therm);
-void nv84_sensor_setup(struct nouveau_therm *therm);
-int nv84_therm_fini(struct nouveau_object *object, bool suspend);
-
-int nva3_therm_fan_sense(struct nouveau_therm *);
-
-int nvd0_therm_init(struct nouveau_object *object);
-
-int nouveau_fanpwm_create(struct nouveau_therm *, struct dcb_gpio_func *);
-int nouveau_fantog_create(struct nouveau_therm *, struct dcb_gpio_func *);
-int nouveau_fannil_create(struct nouveau_therm *);
-
-#endif
diff --git a/drivers/gpu/drm/nouveau/core/subdev/therm/temp.c b/drivers/gpu/drm/nouveau/core/subdev/therm/temp.c
deleted file mode 100644 (file)
index 6212537..0000000
+++ /dev/null
@@ -1,264 +0,0 @@
-/*
- * Copyright 2012 The Nouveau community
- *
- * 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 "priv.h"
-
-#include <core/object.h>
-#include <core/device.h>
-
-#include <subdev/bios.h>
-
-static void
-nouveau_therm_temp_set_defaults(struct nouveau_therm *therm)
-{
-       struct nouveau_therm_priv *priv = (void *)therm;
-
-       priv->bios_sensor.offset_constant = 0;
-
-       priv->bios_sensor.thrs_fan_boost.temp = 90;
-       priv->bios_sensor.thrs_fan_boost.hysteresis = 3;
-
-       priv->bios_sensor.thrs_down_clock.temp = 95;
-       priv->bios_sensor.thrs_down_clock.hysteresis = 3;
-
-       priv->bios_sensor.thrs_critical.temp = 105;
-       priv->bios_sensor.thrs_critical.hysteresis = 5;
-
-       priv->bios_sensor.thrs_shutdown.temp = 135;
-       priv->bios_sensor.thrs_shutdown.hysteresis = 5; /*not that it matters */
-}
-
-
-static void
-nouveau_therm_temp_safety_checks(struct nouveau_therm *therm)
-{
-       struct nouveau_therm_priv *priv = (void *)therm;
-       struct nvbios_therm_sensor *s = &priv->bios_sensor;
-
-       /* enforce a minimum hysteresis on thresholds */
-       s->thrs_fan_boost.hysteresis = max_t(u8, s->thrs_fan_boost.hysteresis, 2);
-       s->thrs_down_clock.hysteresis = max_t(u8, s->thrs_down_clock.hysteresis, 2);
-       s->thrs_critical.hysteresis = max_t(u8, s->thrs_critical.hysteresis, 2);
-       s->thrs_shutdown.hysteresis = max_t(u8, s->thrs_shutdown.hysteresis, 2);
-}
-
-/* must be called with alarm_program_lock taken ! */
-void nouveau_therm_sensor_set_threshold_state(struct nouveau_therm *therm,
-                                            enum nouveau_therm_thrs thrs,
-                                            enum nouveau_therm_thrs_state st)
-{
-       struct nouveau_therm_priv *priv = (void *)therm;
-       priv->sensor.alarm_state[thrs] = st;
-}
-
-/* must be called with alarm_program_lock taken ! */
-enum nouveau_therm_thrs_state
-nouveau_therm_sensor_get_threshold_state(struct nouveau_therm *therm,
-                                        enum nouveau_therm_thrs thrs)
-{
-       struct nouveau_therm_priv *priv = (void *)therm;
-       return priv->sensor.alarm_state[thrs];
-}
-
-static void
-nv_poweroff_work(struct work_struct *work)
-{
-       orderly_poweroff(true);
-       kfree(work);
-}
-
-void nouveau_therm_sensor_event(struct nouveau_therm *therm,
-                               enum nouveau_therm_thrs thrs,
-                               enum nouveau_therm_thrs_direction dir)
-{
-       struct nouveau_therm_priv *priv = (void *)therm;
-       bool active;
-       const char *thresolds[] = {
-               "fanboost", "downclock", "critical", "shutdown"
-       };
-       int temperature = therm->temp_get(therm);
-
-       if (thrs < 0 || thrs > 3)
-               return;
-
-       if (dir == NOUVEAU_THERM_THRS_FALLING)
-               nv_info(therm, "temperature (%i C) went below the '%s' threshold\n",
-                       temperature, thresolds[thrs]);
-       else
-               nv_info(therm, "temperature (%i C) hit the '%s' threshold\n",
-                       temperature, thresolds[thrs]);
-
-       active = (dir == NOUVEAU_THERM_THRS_RISING);
-       switch (thrs) {
-       case NOUVEAU_THERM_THRS_FANBOOST:
-               if (active) {
-                       nouveau_therm_fan_set(therm, true, 100);
-                       nouveau_therm_fan_mode(therm, NOUVEAU_THERM_CTRL_AUTO);
-               }
-               break;
-       case NOUVEAU_THERM_THRS_DOWNCLOCK:
-               if (priv->emergency.downclock)
-                       priv->emergency.downclock(therm, active);
-               break;
-       case NOUVEAU_THERM_THRS_CRITICAL:
-               if (priv->emergency.pause)
-                       priv->emergency.pause(therm, active);
-               break;
-       case NOUVEAU_THERM_THRS_SHUTDOWN:
-               if (active) {
-                       struct work_struct *work;
-
-                       work = kmalloc(sizeof(*work), GFP_ATOMIC);
-                       if (work) {
-                               INIT_WORK(work, nv_poweroff_work);
-                               schedule_work(work);
-                       }
-               }
-               break;
-       case NOUVEAU_THERM_THRS_NR:
-               break;
-       }
-
-}
-
-/* must be called with alarm_program_lock taken ! */
-static void
-nouveau_therm_threshold_hyst_polling(struct nouveau_therm *therm,
-                                  const struct nvbios_therm_threshold *thrs,
-                                  enum nouveau_therm_thrs thrs_name)
-{
-       enum nouveau_therm_thrs_direction direction;
-       enum nouveau_therm_thrs_state prev_state, new_state;
-       int temp = therm->temp_get(therm);
-
-       prev_state = nouveau_therm_sensor_get_threshold_state(therm, thrs_name);
-
-       if (temp >= thrs->temp && prev_state == NOUVEAU_THERM_THRS_LOWER) {
-               direction = NOUVEAU_THERM_THRS_RISING;
-               new_state = NOUVEAU_THERM_THRS_HIGHER;
-       } else if (temp <= thrs->temp - thrs->hysteresis &&
-                       prev_state == NOUVEAU_THERM_THRS_HIGHER) {
-               direction = NOUVEAU_THERM_THRS_FALLING;
-               new_state = NOUVEAU_THERM_THRS_LOWER;
-       } else
-               return; /* nothing to do */
-
-       nouveau_therm_sensor_set_threshold_state(therm, thrs_name, new_state);
-       nouveau_therm_sensor_event(therm, thrs_name, direction);
-}
-
-static void
-alarm_timer_callback(struct nouveau_alarm *alarm)
-{
-       struct nouveau_therm_priv *priv =
-       container_of(alarm, struct nouveau_therm_priv, sensor.therm_poll_alarm);
-       struct nvbios_therm_sensor *sensor = &priv->bios_sensor;
-       struct nouveau_timer *ptimer = nouveau_timer(priv);
-       struct nouveau_therm *therm = &priv->base;
-       unsigned long flags;
-
-       spin_lock_irqsave(&priv->sensor.alarm_program_lock, flags);
-
-       nouveau_therm_threshold_hyst_polling(therm, &sensor->thrs_fan_boost,
-                                            NOUVEAU_THERM_THRS_FANBOOST);
-
-       nouveau_therm_threshold_hyst_polling(therm, &sensor->thrs_down_clock,
-                                            NOUVEAU_THERM_THRS_DOWNCLOCK);
-
-       nouveau_therm_threshold_hyst_polling(therm, &sensor->thrs_critical,
-                                            NOUVEAU_THERM_THRS_CRITICAL);
-
-       nouveau_therm_threshold_hyst_polling(therm, &sensor->thrs_shutdown,
-                                            NOUVEAU_THERM_THRS_SHUTDOWN);
-
-       spin_unlock_irqrestore(&priv->sensor.alarm_program_lock, flags);
-
-       /* schedule the next poll in one second */
-       if (therm->temp_get(therm) >= 0 && list_empty(&alarm->head))
-               ptimer->alarm(ptimer, 1000000000ULL, alarm);
-}
-
-void
-nouveau_therm_program_alarms_polling(struct nouveau_therm *therm)
-{
-       struct nouveau_therm_priv *priv = (void *)therm;
-       struct nvbios_therm_sensor *sensor = &priv->bios_sensor;
-
-       nv_debug(therm,
-                "programmed thresholds [ %d(%d), %d(%d), %d(%d), %d(%d) ]\n",
-                sensor->thrs_fan_boost.temp, sensor->thrs_fan_boost.hysteresis,
-                sensor->thrs_down_clock.temp,
-                sensor->thrs_down_clock.hysteresis,
-                sensor->thrs_critical.temp, sensor->thrs_critical.hysteresis,
-                sensor->thrs_shutdown.temp, sensor->thrs_shutdown.hysteresis);
-
-       alarm_timer_callback(&priv->sensor.therm_poll_alarm);
-}
-
-int
-nouveau_therm_sensor_init(struct nouveau_therm *therm)
-{
-       struct nouveau_therm_priv *priv = (void *)therm;
-       priv->sensor.program_alarms(therm);
-       return 0;
-}
-
-int
-nouveau_therm_sensor_fini(struct nouveau_therm *therm, bool suspend)
-{
-       struct nouveau_therm_priv *priv = (void *)therm;
-       struct nouveau_timer *ptimer = nouveau_timer(therm);
-
-       if (suspend)
-               ptimer->alarm_cancel(ptimer, &priv->sensor.therm_poll_alarm);
-       return 0;
-}
-
-void
-nouveau_therm_sensor_preinit(struct nouveau_therm *therm)
-{
-       const char *sensor_avail = "yes";
-
-       if (therm->temp_get(therm) < 0)
-               sensor_avail = "no";
-
-       nv_info(therm, "internal sensor: %s\n", sensor_avail);
-}
-
-int
-nouveau_therm_sensor_ctor(struct nouveau_therm *therm)
-{
-       struct nouveau_therm_priv *priv = (void *)therm;
-       struct nouveau_bios *bios = nouveau_bios(therm);
-
-       nouveau_alarm_init(&priv->sensor.therm_poll_alarm, alarm_timer_callback);
-
-       nouveau_therm_temp_set_defaults(therm);
-       if (nvbios_therm_sensor_parse(bios, NVBIOS_THERM_DOMAIN_CORE,
-                                     &priv->bios_sensor))
-               nv_error(therm, "nvbios_therm_sensor_parse failed\n");
-       nouveau_therm_temp_safety_checks(therm);
-
-       return 0;
-}
diff --git a/drivers/gpu/drm/nouveau/core/subdev/timer/base.c b/drivers/gpu/drm/nouveau/core/subdev/timer/base.c
deleted file mode 100644 (file)
index cf8a0e0..0000000
+++ /dev/null
@@ -1,94 +0,0 @@
-/*
- * Copyright 2012 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 "subdev/timer.h"
-
-bool
-nouveau_timer_wait_eq(void *obj, u64 nsec, u32 addr, u32 mask, u32 data)
-{
-       struct nouveau_timer *ptimer = nouveau_timer(obj);
-       u64 time0;
-
-       time0 = ptimer->read(ptimer);
-       do {
-               if (nv_iclass(obj, NV_SUBDEV_CLASS)) {
-                       if ((nv_rd32(obj, addr) & mask) == data)
-                               return true;
-               } else {
-                       if ((nv_ro32(obj, addr) & mask) == data)
-                               return true;
-               }
-       } while (ptimer->read(ptimer) - time0 < nsec);
-
-       return false;
-}
-
-bool
-nouveau_timer_wait_ne(void *obj, u64 nsec, u32 addr, u32 mask, u32 data)
-{
-       struct nouveau_timer *ptimer = nouveau_timer(obj);
-       u64 time0;
-
-       time0 = ptimer->read(ptimer);
-       do {
-               if (nv_iclass(obj, NV_SUBDEV_CLASS)) {
-                       if ((nv_rd32(obj, addr) & mask) != data)
-                               return true;
-               } else {
-                       if ((nv_ro32(obj, addr) & mask) != data)
-                               return true;
-               }
-       } while (ptimer->read(ptimer) - time0 < nsec);
-
-       return false;
-}
-
-bool
-nouveau_timer_wait_cb(void *obj, u64 nsec, bool (*func)(void *), void *data)
-{
-       struct nouveau_timer *ptimer = nouveau_timer(obj);
-       u64 time0;
-
-       time0 = ptimer->read(ptimer);
-       do {
-               if (func(data) == true)
-                       return true;
-       } while (ptimer->read(ptimer) - time0 < nsec);
-
-       return false;
-}
-
-void
-nouveau_timer_alarm(void *obj, u32 nsec, struct nouveau_alarm *alarm)
-{
-       struct nouveau_timer *ptimer = nouveau_timer(obj);
-       ptimer->alarm(ptimer, nsec, alarm);
-}
-
-void
-nouveau_timer_alarm_cancel(void *obj, struct nouveau_alarm *alarm)
-{
-       struct nouveau_timer *ptimer = nouveau_timer(obj);
-       ptimer->alarm_cancel(ptimer, alarm);
-}
diff --git a/drivers/gpu/drm/nouveau/core/subdev/timer/gk20a.c b/drivers/gpu/drm/nouveau/core/subdev/timer/gk20a.c
deleted file mode 100644 (file)
index 37484db..0000000
+++ /dev/null
@@ -1,57 +0,0 @@
-/*
- * Copyright 2012 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 "nv04.h"
-
-static int
-gk20a_timer_init(struct nouveau_object *object)
-{
-       struct nv04_timer_priv *priv = (void *)object;
-       u32 hi = upper_32_bits(priv->suspend_time);
-       u32 lo = lower_32_bits(priv->suspend_time);
-       int ret;
-
-       ret = nouveau_timer_init(&priv->base);
-       if (ret)
-               return ret;
-
-       nv_debug(priv, "time low        : 0x%08x\n", lo);
-       nv_debug(priv, "time high       : 0x%08x\n", hi);
-
-       /* restore the time before suspend */
-       nv_wr32(priv, NV04_PTIMER_TIME_1, hi);
-       nv_wr32(priv, NV04_PTIMER_TIME_0, lo);
-       return 0;
-}
-
-struct nouveau_oclass
-gk20a_timer_oclass = {
-       .handle = NV_SUBDEV(TIMER, 0xff),
-       .ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nv04_timer_ctor,
-               .dtor = nv04_timer_dtor,
-               .init = gk20a_timer_init,
-               .fini = nv04_timer_fini,
-       }
-};
diff --git a/drivers/gpu/drm/nouveau/core/subdev/timer/nv04.c b/drivers/gpu/drm/nouveau/core/subdev/timer/nv04.c
deleted file mode 100644 (file)
index 240ed0b..0000000
+++ /dev/null
@@ -1,264 +0,0 @@
-/*
- * Copyright 2012 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 "nv04.h"
-
-static u64
-nv04_timer_read(struct nouveau_timer *ptimer)
-{
-       struct nv04_timer_priv *priv = (void *)ptimer;
-       u32 hi, lo;
-
-       do {
-               hi = nv_rd32(priv, NV04_PTIMER_TIME_1);
-               lo = nv_rd32(priv, NV04_PTIMER_TIME_0);
-       } while (hi != nv_rd32(priv, NV04_PTIMER_TIME_1));
-
-       return ((u64)hi << 32 | lo);
-}
-
-static void
-nv04_timer_alarm_trigger(struct nouveau_timer *ptimer)
-{
-       struct nv04_timer_priv *priv = (void *)ptimer;
-       struct nouveau_alarm *alarm, *atemp;
-       unsigned long flags;
-       LIST_HEAD(exec);
-
-       /* move any due alarms off the pending list */
-       spin_lock_irqsave(&priv->lock, flags);
-       list_for_each_entry_safe(alarm, atemp, &priv->alarms, head) {
-               if (alarm->timestamp <= ptimer->read(ptimer))
-                       list_move_tail(&alarm->head, &exec);
-       }
-
-       /* reschedule interrupt for next alarm time */
-       if (!list_empty(&priv->alarms)) {
-               alarm = list_first_entry(&priv->alarms, typeof(*alarm), head);
-               nv_wr32(priv, NV04_PTIMER_ALARM_0, alarm->timestamp);
-               nv_wr32(priv, NV04_PTIMER_INTR_EN_0, 0x00000001);
-       } else {
-               nv_wr32(priv, NV04_PTIMER_INTR_EN_0, 0x00000000);
-       }
-       spin_unlock_irqrestore(&priv->lock, flags);
-
-       /* execute any pending alarm handlers */
-       list_for_each_entry_safe(alarm, atemp, &exec, head) {
-               list_del_init(&alarm->head);
-               alarm->func(alarm);
-       }
-}
-
-static void
-nv04_timer_alarm(struct nouveau_timer *ptimer, u64 time,
-                struct nouveau_alarm *alarm)
-{
-       struct nv04_timer_priv *priv = (void *)ptimer;
-       struct nouveau_alarm *list;
-       unsigned long flags;
-
-       alarm->timestamp = ptimer->read(ptimer) + time;
-
-       /* append new alarm to list, in soonest-alarm-first order */
-       spin_lock_irqsave(&priv->lock, flags);
-       if (!time) {
-               if (!list_empty(&alarm->head))
-                       list_del(&alarm->head);
-       } else {
-               list_for_each_entry(list, &priv->alarms, head) {
-                       if (list->timestamp > alarm->timestamp)
-                               break;
-               }
-               list_add_tail(&alarm->head, &list->head);
-       }
-       spin_unlock_irqrestore(&priv->lock, flags);
-
-       /* process pending alarms */
-       nv04_timer_alarm_trigger(ptimer);
-}
-
-static void
-nv04_timer_alarm_cancel(struct nouveau_timer *ptimer,
-                       struct nouveau_alarm *alarm)
-{
-       struct nv04_timer_priv *priv = (void *)ptimer;
-       unsigned long flags;
-       spin_lock_irqsave(&priv->lock, flags);
-       list_del_init(&alarm->head);
-       spin_unlock_irqrestore(&priv->lock, flags);
-}
-
-static void
-nv04_timer_intr(struct nouveau_subdev *subdev)
-{
-       struct nv04_timer_priv *priv = (void *)subdev;
-       u32 stat = nv_rd32(priv, NV04_PTIMER_INTR_0);
-
-       if (stat & 0x00000001) {
-               nv04_timer_alarm_trigger(&priv->base);
-               nv_wr32(priv, NV04_PTIMER_INTR_0, 0x00000001);
-               stat &= ~0x00000001;
-       }
-
-       if (stat) {
-               nv_error(priv, "unknown stat 0x%08x\n", stat);
-               nv_wr32(priv, NV04_PTIMER_INTR_0, stat);
-       }
-}
-
-int
-nv04_timer_fini(struct nouveau_object *object, bool suspend)
-{
-       struct nv04_timer_priv *priv = (void *)object;
-       if (suspend)
-               priv->suspend_time = nv04_timer_read(&priv->base);
-       nv_wr32(priv, NV04_PTIMER_INTR_EN_0, 0x00000000);
-       return nouveau_timer_fini(&priv->base, suspend);
-}
-
-static int
-nv04_timer_init(struct nouveau_object *object)
-{
-       struct nouveau_device *device = nv_device(object);
-       struct nv04_timer_priv *priv = (void *)object;
-       u32 m = 1, f, n, d, lo, hi;
-       int ret;
-
-       ret = nouveau_timer_init(&priv->base);
-       if (ret)
-               return ret;
-
-       /* aim for 31.25MHz, which gives us nanosecond timestamps */
-       d = 1000000 / 32;
-
-       /* determine base clock for timer source */
-#if 0 /*XXX*/
-       if (device->chipset < 0x40) {
-               n = nouveau_hw_get_clock(device, PLL_CORE);
-       } else
-#endif
-       if (device->chipset <= 0x40) {
-               /*XXX: figure this out */
-               f = -1;
-               n = 0;
-       } else {
-               f = device->crystal;
-               n = f;
-               while (n < (d * 2)) {
-                       n += (n / m);
-                       m++;
-               }
-
-               nv_wr32(priv, 0x009220, m - 1);
-       }
-
-       if (!n) {
-               nv_warn(priv, "unknown input clock freq\n");
-               if (!nv_rd32(priv, NV04_PTIMER_NUMERATOR) ||
-                   !nv_rd32(priv, NV04_PTIMER_DENOMINATOR)) {
-                       nv_wr32(priv, NV04_PTIMER_NUMERATOR, 1);
-                       nv_wr32(priv, NV04_PTIMER_DENOMINATOR, 1);
-               }
-               return 0;
-       }
-
-       /* reduce ratio to acceptable values */
-       while (((n % 5) == 0) && ((d % 5) == 0)) {
-               n /= 5;
-               d /= 5;
-       }
-
-       while (((n % 2) == 0) && ((d % 2) == 0)) {
-               n /= 2;
-               d /= 2;
-       }
-
-       while (n > 0xffff || d > 0xffff) {
-               n >>= 1;
-               d >>= 1;
-       }
-
-       /* restore the time before suspend */
-       lo = priv->suspend_time;
-       hi = (priv->suspend_time >> 32);
-
-       nv_debug(priv, "input frequency : %dHz\n", f);
-       nv_debug(priv, "input multiplier: %d\n", m);
-       nv_debug(priv, "numerator       : 0x%08x\n", n);
-       nv_debug(priv, "denominator     : 0x%08x\n", d);
-       nv_debug(priv, "timer frequency : %dHz\n", (f * m) * d / n);
-       nv_debug(priv, "time low        : 0x%08x\n", lo);
-       nv_debug(priv, "time high       : 0x%08x\n", hi);
-
-       nv_wr32(priv, NV04_PTIMER_NUMERATOR, n);
-       nv_wr32(priv, NV04_PTIMER_DENOMINATOR, d);
-       nv_wr32(priv, NV04_PTIMER_INTR_0, 0xffffffff);
-       nv_wr32(priv, NV04_PTIMER_INTR_EN_0, 0x00000000);
-       nv_wr32(priv, NV04_PTIMER_TIME_1, hi);
-       nv_wr32(priv, NV04_PTIMER_TIME_0, lo);
-
-       return 0;
-}
-
-void
-nv04_timer_dtor(struct nouveau_object *object)
-{
-       struct nv04_timer_priv *priv = (void *)object;
-       return nouveau_timer_destroy(&priv->base);
-}
-
-int
-nv04_timer_ctor(struct nouveau_object *parent, struct nouveau_object *engine,
-               struct nouveau_oclass *oclass, void *data, u32 size,
-               struct nouveau_object **pobject)
-{
-       struct nv04_timer_priv *priv;
-       int ret;
-
-       ret = nouveau_timer_create(parent, engine, oclass, &priv);
-       *pobject = nv_object(priv);
-       if (ret)
-               return ret;
-
-       priv->base.base.intr = nv04_timer_intr;
-       priv->base.read = nv04_timer_read;
-       priv->base.alarm = nv04_timer_alarm;
-       priv->base.alarm_cancel = nv04_timer_alarm_cancel;
-       priv->suspend_time = 0;
-
-       INIT_LIST_HEAD(&priv->alarms);
-       spin_lock_init(&priv->lock);
-       return 0;
-}
-
-struct nouveau_oclass
-nv04_timer_oclass = {
-       .handle = NV_SUBDEV(TIMER, 0x04),
-       .ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nv04_timer_ctor,
-               .dtor = nv04_timer_dtor,
-               .init = nv04_timer_init,
-               .fini = nv04_timer_fini,
-       }
-};
diff --git a/drivers/gpu/drm/nouveau/core/subdev/timer/nv04.h b/drivers/gpu/drm/nouveau/core/subdev/timer/nv04.h
deleted file mode 100644 (file)
index 4bc1526..0000000
+++ /dev/null
@@ -1,27 +0,0 @@
-#ifndef __NVKM_TIMER_NV04_H__
-#define __NVKM_TIMER_NV04_H__
-
-#include "priv.h"
-
-#define NV04_PTIMER_INTR_0      0x009100
-#define NV04_PTIMER_INTR_EN_0   0x009140
-#define NV04_PTIMER_NUMERATOR   0x009200
-#define NV04_PTIMER_DENOMINATOR 0x009210
-#define NV04_PTIMER_TIME_0      0x009400
-#define NV04_PTIMER_TIME_1      0x009410
-#define NV04_PTIMER_ALARM_0     0x009420
-
-struct nv04_timer_priv {
-       struct nouveau_timer base;
-       struct list_head alarms;
-       spinlock_t lock;
-       u64 suspend_time;
-};
-
-int  nv04_timer_ctor(struct nouveau_object *, struct nouveau_object *,
-                    struct nouveau_oclass *, void *, u32,
-                    struct nouveau_object **);
-void nv04_timer_dtor(struct nouveau_object *);
-int  nv04_timer_fini(struct nouveau_object *, bool);
-
-#endif
diff --git a/drivers/gpu/drm/nouveau/core/subdev/timer/priv.h b/drivers/gpu/drm/nouveau/core/subdev/timer/priv.h
deleted file mode 100644 (file)
index 799dae3..0000000
+++ /dev/null
@@ -1,6 +0,0 @@
-#ifndef __NVKM_TIMER_PRIV_H__
-#define __NVKM_TIMER_PRIV_H__
-
-#include <subdev/timer.h>
-
-#endif
diff --git a/drivers/gpu/drm/nouveau/core/subdev/vm/base.c b/drivers/gpu/drm/nouveau/core/subdev/vm/base.c
deleted file mode 100644 (file)
index f75a683..0000000
+++ /dev/null
@@ -1,483 +0,0 @@
-/*
- * 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 <core/gpuobj.h>
-#include <core/mm.h>
-
-#include <subdev/fb.h>
-#include <subdev/vm.h>
-
-void
-nouveau_vm_map_at(struct nouveau_vma *vma, u64 delta, struct nouveau_mem *node)
-{
-       struct nouveau_vm *vm = vma->vm;
-       struct nouveau_vmmgr *vmm = vm->vmm;
-       struct nouveau_mm_node *r;
-       int big = vma->node->type != vmm->spg_shift;
-       u32 offset = vma->node->offset + (delta >> 12);
-       u32 bits = vma->node->type - 12;
-       u32 pde  = (offset >> vmm->pgt_bits) - vm->fpde;
-       u32 pte  = (offset & ((1 << vmm->pgt_bits) - 1)) >> bits;
-       u32 max  = 1 << (vmm->pgt_bits - bits);
-       u32 end, len;
-
-       delta = 0;
-       list_for_each_entry(r, &node->regions, rl_entry) {
-               u64 phys = (u64)r->offset << 12;
-               u32 num  = r->length >> bits;
-
-               while (num) {
-                       struct nouveau_gpuobj *pgt = vm->pgt[pde].obj[big];
-
-                       end = (pte + num);
-                       if (unlikely(end >= max))
-                               end = max;
-                       len = end - pte;
-
-                       vmm->map(vma, pgt, node, pte, len, phys, delta);
-
-                       num -= len;
-                       pte += len;
-                       if (unlikely(end >= max)) {
-                               phys += len << (bits + 12);
-                               pde++;
-                               pte = 0;
-                       }
-
-                       delta += (u64)len << vma->node->type;
-               }
-       }
-
-       vmm->flush(vm);
-}
-
-static void
-nouveau_vm_map_sg_table(struct nouveau_vma *vma, u64 delta, u64 length,
-                       struct nouveau_mem *mem)
-{
-       struct nouveau_vm *vm = vma->vm;
-       struct nouveau_vmmgr *vmm = vm->vmm;
-       int big = vma->node->type != vmm->spg_shift;
-       u32 offset = vma->node->offset + (delta >> 12);
-       u32 bits = vma->node->type - 12;
-       u32 num  = length >> vma->node->type;
-       u32 pde  = (offset >> vmm->pgt_bits) - vm->fpde;
-       u32 pte  = (offset & ((1 << vmm->pgt_bits) - 1)) >> bits;
-       u32 max  = 1 << (vmm->pgt_bits - bits);
-       unsigned m, sglen;
-       u32 end, len;
-       int i;
-       struct scatterlist *sg;
-
-       for_each_sg(mem->sg->sgl, sg, mem->sg->nents, i) {
-               struct nouveau_gpuobj *pgt = vm->pgt[pde].obj[big];
-               sglen = sg_dma_len(sg) >> PAGE_SHIFT;
-
-               end = pte + sglen;
-               if (unlikely(end >= max))
-                       end = max;
-               len = end - pte;
-
-               for (m = 0; m < len; m++) {
-                       dma_addr_t addr = sg_dma_address(sg) + (m << PAGE_SHIFT);
-
-                       vmm->map_sg(vma, pgt, mem, pte, 1, &addr);
-                       num--;
-                       pte++;
-
-                       if (num == 0)
-                               goto finish;
-               }
-               if (unlikely(end >= max)) {
-                       pde++;
-                       pte = 0;
-               }
-               if (m < sglen) {
-                       for (; m < sglen; m++) {
-                               dma_addr_t addr = sg_dma_address(sg) + (m << PAGE_SHIFT);
-
-                               vmm->map_sg(vma, pgt, mem, pte, 1, &addr);
-                               num--;
-                               pte++;
-                               if (num == 0)
-                                       goto finish;
-                       }
-               }
-
-       }
-finish:
-       vmm->flush(vm);
-}
-
-static void
-nouveau_vm_map_sg(struct nouveau_vma *vma, u64 delta, u64 length,
-                 struct nouveau_mem *mem)
-{
-       struct nouveau_vm *vm = vma->vm;
-       struct nouveau_vmmgr *vmm = vm->vmm;
-       dma_addr_t *list = mem->pages;
-       int big = vma->node->type != vmm->spg_shift;
-       u32 offset = vma->node->offset + (delta >> 12);
-       u32 bits = vma->node->type - 12;
-       u32 num  = length >> vma->node->type;
-       u32 pde  = (offset >> vmm->pgt_bits) - vm->fpde;
-       u32 pte  = (offset & ((1 << vmm->pgt_bits) - 1)) >> bits;
-       u32 max  = 1 << (vmm->pgt_bits - bits);
-       u32 end, len;
-
-       while (num) {
-               struct nouveau_gpuobj *pgt = vm->pgt[pde].obj[big];
-
-               end = (pte + num);
-               if (unlikely(end >= max))
-                       end = max;
-               len = end - pte;
-
-               vmm->map_sg(vma, pgt, mem, pte, len, list);
-
-               num  -= len;
-               pte  += len;
-               list += len;
-               if (unlikely(end >= max)) {
-                       pde++;
-                       pte = 0;
-               }
-       }
-
-       vmm->flush(vm);
-}
-
-void
-nouveau_vm_map(struct nouveau_vma *vma, struct nouveau_mem *node)
-{
-       if (node->sg)
-               nouveau_vm_map_sg_table(vma, 0, node->size << 12, node);
-       else
-       if (node->pages)
-               nouveau_vm_map_sg(vma, 0, node->size << 12, node);
-       else
-               nouveau_vm_map_at(vma, 0, node);
-}
-
-void
-nouveau_vm_unmap_at(struct nouveau_vma *vma, u64 delta, u64 length)
-{
-       struct nouveau_vm *vm = vma->vm;
-       struct nouveau_vmmgr *vmm = vm->vmm;
-       int big = vma->node->type != vmm->spg_shift;
-       u32 offset = vma->node->offset + (delta >> 12);
-       u32 bits = vma->node->type - 12;
-       u32 num  = length >> vma->node->type;
-       u32 pde  = (offset >> vmm->pgt_bits) - vm->fpde;
-       u32 pte  = (offset & ((1 << vmm->pgt_bits) - 1)) >> bits;
-       u32 max  = 1 << (vmm->pgt_bits - bits);
-       u32 end, len;
-
-       while (num) {
-               struct nouveau_gpuobj *pgt = vm->pgt[pde].obj[big];
-
-               end = (pte + num);
-               if (unlikely(end >= max))
-                       end = max;
-               len = end - pte;
-
-               vmm->unmap(pgt, pte, len);
-
-               num -= len;
-               pte += len;
-               if (unlikely(end >= max)) {
-                       pde++;
-                       pte = 0;
-               }
-       }
-
-       vmm->flush(vm);
-}
-
-void
-nouveau_vm_unmap(struct nouveau_vma *vma)
-{
-       nouveau_vm_unmap_at(vma, 0, (u64)vma->node->length << 12);
-}
-
-static void
-nouveau_vm_unmap_pgt(struct nouveau_vm *vm, int big, u32 fpde, u32 lpde)
-{
-       struct nouveau_vmmgr *vmm = vm->vmm;
-       struct nouveau_vm_pgd *vpgd;
-       struct nouveau_vm_pgt *vpgt;
-       struct nouveau_gpuobj *pgt;
-       u32 pde;
-
-       for (pde = fpde; pde <= lpde; pde++) {
-               vpgt = &vm->pgt[pde - vm->fpde];
-               if (--vpgt->refcount[big])
-                       continue;
-
-               pgt = vpgt->obj[big];
-               vpgt->obj[big] = NULL;
-
-               list_for_each_entry(vpgd, &vm->pgd_list, head) {
-                       vmm->map_pgt(vpgd->obj, pde, vpgt->obj);
-               }
-
-               mutex_unlock(&nv_subdev(vmm)->mutex);
-               nouveau_gpuobj_ref(NULL, &pgt);
-               mutex_lock(&nv_subdev(vmm)->mutex);
-       }
-}
-
-static int
-nouveau_vm_map_pgt(struct nouveau_vm *vm, u32 pde, u32 type)
-{
-       struct nouveau_vmmgr *vmm = vm->vmm;
-       struct nouveau_vm_pgt *vpgt = &vm->pgt[pde - vm->fpde];
-       struct nouveau_vm_pgd *vpgd;
-       struct nouveau_gpuobj *pgt;
-       int big = (type != vmm->spg_shift);
-       u32 pgt_size;
-       int ret;
-
-       pgt_size  = (1 << (vmm->pgt_bits + 12)) >> type;
-       pgt_size *= 8;
-
-       mutex_unlock(&nv_subdev(vmm)->mutex);
-       ret = nouveau_gpuobj_new(nv_object(vm->vmm), NULL, pgt_size, 0x1000,
-                                NVOBJ_FLAG_ZERO_ALLOC, &pgt);
-       mutex_lock(&nv_subdev(vmm)->mutex);
-       if (unlikely(ret))
-               return ret;
-
-       /* someone beat us to filling the PDE while we didn't have the lock */
-       if (unlikely(vpgt->refcount[big]++)) {
-               mutex_unlock(&nv_subdev(vmm)->mutex);
-               nouveau_gpuobj_ref(NULL, &pgt);
-               mutex_lock(&nv_subdev(vmm)->mutex);
-               return 0;
-       }
-
-       vpgt->obj[big] = pgt;
-       list_for_each_entry(vpgd, &vm->pgd_list, head) {
-               vmm->map_pgt(vpgd->obj, pde, vpgt->obj);
-       }
-
-       return 0;
-}
-
-int
-nouveau_vm_get(struct nouveau_vm *vm, u64 size, u32 page_shift,
-              u32 access, struct nouveau_vma *vma)
-{
-       struct nouveau_vmmgr *vmm = vm->vmm;
-       u32 align = (1 << page_shift) >> 12;
-       u32 msize = size >> 12;
-       u32 fpde, lpde, pde;
-       int ret;
-
-       mutex_lock(&nv_subdev(vmm)->mutex);
-       ret = nouveau_mm_head(&vm->mm, 0, page_shift, msize, msize, align,
-                            &vma->node);
-       if (unlikely(ret != 0)) {
-               mutex_unlock(&nv_subdev(vmm)->mutex);
-               return ret;
-       }
-
-       fpde = (vma->node->offset >> vmm->pgt_bits);
-       lpde = (vma->node->offset + vma->node->length - 1) >> vmm->pgt_bits;
-
-       for (pde = fpde; pde <= lpde; pde++) {
-               struct nouveau_vm_pgt *vpgt = &vm->pgt[pde - vm->fpde];
-               int big = (vma->node->type != vmm->spg_shift);
-
-               if (likely(vpgt->refcount[big])) {
-                       vpgt->refcount[big]++;
-                       continue;
-               }
-
-               ret = nouveau_vm_map_pgt(vm, pde, vma->node->type);
-               if (ret) {
-                       if (pde != fpde)
-                               nouveau_vm_unmap_pgt(vm, big, fpde, pde - 1);
-                       nouveau_mm_free(&vm->mm, &vma->node);
-                       mutex_unlock(&nv_subdev(vmm)->mutex);
-                       return ret;
-               }
-       }
-       mutex_unlock(&nv_subdev(vmm)->mutex);
-
-       vma->vm = NULL;
-       nouveau_vm_ref(vm, &vma->vm, NULL);
-       vma->offset = (u64)vma->node->offset << 12;
-       vma->access = access;
-       return 0;
-}
-
-void
-nouveau_vm_put(struct nouveau_vma *vma)
-{
-       struct nouveau_vm *vm = vma->vm;
-       struct nouveau_vmmgr *vmm = vm->vmm;
-       u32 fpde, lpde;
-
-       if (unlikely(vma->node == NULL))
-               return;
-       fpde = (vma->node->offset >> vmm->pgt_bits);
-       lpde = (vma->node->offset + vma->node->length - 1) >> vmm->pgt_bits;
-
-       mutex_lock(&nv_subdev(vmm)->mutex);
-       nouveau_vm_unmap_pgt(vm, vma->node->type != vmm->spg_shift, fpde, lpde);
-       nouveau_mm_free(&vm->mm, &vma->node);
-       mutex_unlock(&nv_subdev(vmm)->mutex);
-
-       nouveau_vm_ref(NULL, &vma->vm, NULL);
-}
-
-int
-nouveau_vm_create(struct nouveau_vmmgr *vmm, u64 offset, u64 length,
-                 u64 mm_offset, u32 block, struct nouveau_vm **pvm)
-{
-       struct nouveau_vm *vm;
-       u64 mm_length = (offset + length) - mm_offset;
-       int ret;
-
-       vm = kzalloc(sizeof(*vm), GFP_KERNEL);
-       if (!vm)
-               return -ENOMEM;
-
-       INIT_LIST_HEAD(&vm->pgd_list);
-       vm->vmm = vmm;
-       kref_init(&vm->refcount);
-       vm->fpde = offset >> (vmm->pgt_bits + 12);
-       vm->lpde = (offset + length - 1) >> (vmm->pgt_bits + 12);
-
-       vm->pgt  = vzalloc((vm->lpde - vm->fpde + 1) * sizeof(*vm->pgt));
-       if (!vm->pgt) {
-               kfree(vm);
-               return -ENOMEM;
-       }
-
-       ret = nouveau_mm_init(&vm->mm, mm_offset >> 12, mm_length >> 12,
-                             block >> 12);
-       if (ret) {
-               vfree(vm->pgt);
-               kfree(vm);
-               return ret;
-       }
-
-       *pvm = vm;
-
-       return 0;
-}
-
-int
-nouveau_vm_new(struct nouveau_device *device, u64 offset, u64 length,
-              u64 mm_offset, struct nouveau_vm **pvm)
-{
-       struct nouveau_vmmgr *vmm = nouveau_vmmgr(device);
-       return vmm->create(vmm, offset, length, mm_offset, pvm);
-}
-
-static int
-nouveau_vm_link(struct nouveau_vm *vm, struct nouveau_gpuobj *pgd)
-{
-       struct nouveau_vmmgr *vmm = vm->vmm;
-       struct nouveau_vm_pgd *vpgd;
-       int i;
-
-       if (!pgd)
-               return 0;
-
-       vpgd = kzalloc(sizeof(*vpgd), GFP_KERNEL);
-       if (!vpgd)
-               return -ENOMEM;
-
-       nouveau_gpuobj_ref(pgd, &vpgd->obj);
-
-       mutex_lock(&nv_subdev(vmm)->mutex);
-       for (i = vm->fpde; i <= vm->lpde; i++)
-               vmm->map_pgt(pgd, i, vm->pgt[i - vm->fpde].obj);
-       list_add(&vpgd->head, &vm->pgd_list);
-       mutex_unlock(&nv_subdev(vmm)->mutex);
-       return 0;
-}
-
-static void
-nouveau_vm_unlink(struct nouveau_vm *vm, struct nouveau_gpuobj *mpgd)
-{
-       struct nouveau_vmmgr *vmm = vm->vmm;
-       struct nouveau_vm_pgd *vpgd, *tmp;
-       struct nouveau_gpuobj *pgd = NULL;
-
-       if (!mpgd)
-               return;
-
-       mutex_lock(&nv_subdev(vmm)->mutex);
-       list_for_each_entry_safe(vpgd, tmp, &vm->pgd_list, head) {
-               if (vpgd->obj == mpgd) {
-                       pgd = vpgd->obj;
-                       list_del(&vpgd->head);
-                       kfree(vpgd);
-                       break;
-               }
-       }
-       mutex_unlock(&nv_subdev(vmm)->mutex);
-
-       nouveau_gpuobj_ref(NULL, &pgd);
-}
-
-static void
-nouveau_vm_del(struct kref *kref)
-{
-       struct nouveau_vm *vm = container_of(kref, typeof(*vm), refcount);
-       struct nouveau_vm_pgd *vpgd, *tmp;
-
-       list_for_each_entry_safe(vpgd, tmp, &vm->pgd_list, head) {
-               nouveau_vm_unlink(vm, vpgd->obj);
-       }
-
-       nouveau_mm_fini(&vm->mm);
-       vfree(vm->pgt);
-       kfree(vm);
-}
-
-int
-nouveau_vm_ref(struct nouveau_vm *ref, struct nouveau_vm **ptr,
-              struct nouveau_gpuobj *pgd)
-{
-       if (ref) {
-               int ret = nouveau_vm_link(ref, pgd);
-               if (ret)
-                       return ret;
-
-               kref_get(&ref->refcount);
-       }
-
-       if (*ptr) {
-               nouveau_vm_unlink(*ptr, pgd);
-               kref_put(&(*ptr)->refcount, nouveau_vm_del);
-       }
-
-       *ptr = ref;
-       return 0;
-}
diff --git a/drivers/gpu/drm/nouveau/core/subdev/vm/nv04.c b/drivers/gpu/drm/nouveau/core/subdev/vm/nv04.c
deleted file mode 100644 (file)
index ed45437..0000000
+++ /dev/null
@@ -1,151 +0,0 @@
-/*
- * Copyright 2012 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 <core/gpuobj.h>
-
-#include "nv04.h"
-
-#define NV04_PDMA_SIZE (128 * 1024 * 1024)
-#define NV04_PDMA_PAGE (  4 * 1024)
-
-/*******************************************************************************
- * VM map/unmap callbacks
- ******************************************************************************/
-
-static void
-nv04_vm_map_sg(struct nouveau_vma *vma, struct nouveau_gpuobj *pgt,
-              struct nouveau_mem *mem, u32 pte, u32 cnt, dma_addr_t *list)
-{
-       pte = 0x00008 + (pte * 4);
-       while (cnt) {
-               u32 page = PAGE_SIZE / NV04_PDMA_PAGE;
-               u32 phys = (u32)*list++;
-               while (cnt && page--) {
-                       nv_wo32(pgt, pte, phys | 3);
-                       phys += NV04_PDMA_PAGE;
-                       pte += 4;
-                       cnt -= 1;
-               }
-       }
-}
-
-static void
-nv04_vm_unmap(struct nouveau_gpuobj *pgt, u32 pte, u32 cnt)
-{
-       pte = 0x00008 + (pte * 4);
-       while (cnt--) {
-               nv_wo32(pgt, pte, 0x00000000);
-               pte += 4;
-       }
-}
-
-static void
-nv04_vm_flush(struct nouveau_vm *vm)
-{
-}
-
-/*******************************************************************************
- * VM object
- ******************************************************************************/
-
-int
-nv04_vm_create(struct nouveau_vmmgr *vmm, u64 offset, u64 length, u64 mmstart,
-              struct nouveau_vm **pvm)
-{
-       return -EINVAL;
-}
-
-/*******************************************************************************
- * VMMGR subdev
- ******************************************************************************/
-
-static int
-nv04_vmmgr_ctor(struct nouveau_object *parent, struct nouveau_object *engine,
-               struct nouveau_oclass *oclass, void *data, u32 size,
-               struct nouveau_object **pobject)
-{
-       struct nv04_vmmgr_priv *priv;
-       struct nouveau_gpuobj *dma;
-       int ret;
-
-       ret = nouveau_vmmgr_create(parent, engine, oclass, "PCIGART",
-                                  "pcigart", &priv);
-       *pobject = nv_object(priv);
-       if (ret)
-               return ret;
-
-       priv->base.create = nv04_vm_create;
-       priv->base.limit = NV04_PDMA_SIZE;
-       priv->base.dma_bits = 32;
-       priv->base.pgt_bits = 32 - 12;
-       priv->base.spg_shift = 12;
-       priv->base.lpg_shift = 12;
-       priv->base.map_sg = nv04_vm_map_sg;
-       priv->base.unmap = nv04_vm_unmap;
-       priv->base.flush = nv04_vm_flush;
-
-       ret = nouveau_vm_create(&priv->base, 0, NV04_PDMA_SIZE, 0, 4096,
-                               &priv->vm);
-       if (ret)
-               return ret;
-
-       ret = nouveau_gpuobj_new(nv_object(priv), NULL,
-                                (NV04_PDMA_SIZE / NV04_PDMA_PAGE) * 4 +
-                                8, 16, NVOBJ_FLAG_ZERO_ALLOC,
-                                &priv->vm->pgt[0].obj[0]);
-       dma = priv->vm->pgt[0].obj[0];
-       priv->vm->pgt[0].refcount[0] = 1;
-       if (ret)
-               return ret;
-
-       nv_wo32(dma, 0x00000, 0x0002103d); /* PCI, RW, PT, !LN */
-       nv_wo32(dma, 0x00004, NV04_PDMA_SIZE - 1);
-       return 0;
-}
-
-void
-nv04_vmmgr_dtor(struct nouveau_object *object)
-{
-       struct nv04_vmmgr_priv *priv = (void *)object;
-       if (priv->vm) {
-               nouveau_gpuobj_ref(NULL, &priv->vm->pgt[0].obj[0]);
-               nouveau_vm_ref(NULL, &priv->vm, NULL);
-       }
-       if (priv->nullp) {
-               pci_free_consistent(nv_device(priv)->pdev, 16 * 1024,
-                                   priv->nullp, priv->null);
-       }
-       nouveau_vmmgr_destroy(&priv->base);
-}
-
-struct nouveau_oclass
-nv04_vmmgr_oclass = {
-       .handle = NV_SUBDEV(VM, 0x04),
-       .ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nv04_vmmgr_ctor,
-               .dtor = nv04_vmmgr_dtor,
-               .init = _nouveau_vmmgr_init,
-               .fini = _nouveau_vmmgr_fini,
-       },
-};
diff --git a/drivers/gpu/drm/nouveau/core/subdev/vm/nv04.h b/drivers/gpu/drm/nouveau/core/subdev/vm/nv04.h
deleted file mode 100644 (file)
index ec42d4b..0000000
+++ /dev/null
@@ -1,19 +0,0 @@
-#ifndef __NV04_VMMGR_PRIV__
-#define __NV04_VMMGR_PRIV__
-
-#include <subdev/vm.h>
-
-struct nv04_vmmgr_priv {
-       struct nouveau_vmmgr base;
-       struct nouveau_vm *vm;
-       dma_addr_t null;
-       void *nullp;
-};
-
-static inline struct nv04_vmmgr_priv *
-nv04_vmmgr(void *obj)
-{
-       return (void *)nouveau_vmmgr(obj);
-}
-
-#endif
diff --git a/drivers/gpu/drm/nouveau/core/subdev/vm/nv41.c b/drivers/gpu/drm/nouveau/core/subdev/vm/nv41.c
deleted file mode 100644 (file)
index 064c762..0000000
+++ /dev/null
@@ -1,159 +0,0 @@
-/*
- * Copyright 2012 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 <core/gpuobj.h>
-#include <core/option.h>
-
-#include <subdev/timer.h>
-#include <subdev/vm.h>
-
-#include "nv04.h"
-
-#define NV41_GART_SIZE (512 * 1024 * 1024)
-#define NV41_GART_PAGE (  4 * 1024)
-
-/*******************************************************************************
- * VM map/unmap callbacks
- ******************************************************************************/
-
-static void
-nv41_vm_map_sg(struct nouveau_vma *vma, struct nouveau_gpuobj *pgt,
-              struct nouveau_mem *mem, u32 pte, u32 cnt, dma_addr_t *list)
-{
-       pte = pte * 4;
-       while (cnt) {
-               u32 page = PAGE_SIZE / NV41_GART_PAGE;
-               u64 phys = (u64)*list++;
-               while (cnt && page--) {
-                       nv_wo32(pgt, pte, (phys >> 7) | 1);
-                       phys += NV41_GART_PAGE;
-                       pte += 4;
-                       cnt -= 1;
-               }
-       }
-}
-
-static void
-nv41_vm_unmap(struct nouveau_gpuobj *pgt, u32 pte, u32 cnt)
-{
-       pte = pte * 4;
-       while (cnt--) {
-               nv_wo32(pgt, pte, 0x00000000);
-               pte += 4;
-       }
-}
-
-static void
-nv41_vm_flush(struct nouveau_vm *vm)
-{
-       struct nv04_vmmgr_priv *priv = (void *)vm->vmm;
-
-       mutex_lock(&nv_subdev(priv)->mutex);
-       nv_wr32(priv, 0x100810, 0x00000022);
-       if (!nv_wait(priv, 0x100810, 0x00000020, 0x00000020)) {
-               nv_warn(priv, "flush timeout, 0x%08x\n",
-                       nv_rd32(priv, 0x100810));
-       }
-       nv_wr32(priv, 0x100810, 0x00000000);
-       mutex_unlock(&nv_subdev(priv)->mutex);
-}
-
-/*******************************************************************************
- * VMMGR subdev
- ******************************************************************************/
-
-static int
-nv41_vmmgr_ctor(struct nouveau_object *parent, struct nouveau_object *engine,
-               struct nouveau_oclass *oclass, void *data, u32 size,
-               struct nouveau_object **pobject)
-{
-       struct nouveau_device *device = nv_device(parent);
-       struct nv04_vmmgr_priv *priv;
-       int ret;
-
-       if (pci_find_capability(device->pdev, PCI_CAP_ID_AGP) ||
-           !nouveau_boolopt(device->cfgopt, "NvPCIE", true)) {
-               return nouveau_object_ctor(parent, engine, &nv04_vmmgr_oclass,
-                                          data, size, pobject);
-       }
-
-       ret = nouveau_vmmgr_create(parent, engine, oclass, "PCIEGART",
-                                  "pciegart", &priv);
-       *pobject = nv_object(priv);
-       if (ret)
-               return ret;
-
-       priv->base.create = nv04_vm_create;
-       priv->base.limit = NV41_GART_SIZE;
-       priv->base.dma_bits = 39;
-       priv->base.pgt_bits = 32 - 12;
-       priv->base.spg_shift = 12;
-       priv->base.lpg_shift = 12;
-       priv->base.map_sg = nv41_vm_map_sg;
-       priv->base.unmap = nv41_vm_unmap;
-       priv->base.flush = nv41_vm_flush;
-
-       ret = nouveau_vm_create(&priv->base, 0, NV41_GART_SIZE, 0, 4096,
-                               &priv->vm);
-       if (ret)
-               return ret;
-
-       ret = nouveau_gpuobj_new(nv_object(priv), NULL,
-                               (NV41_GART_SIZE / NV41_GART_PAGE) * 4,
-                                16, NVOBJ_FLAG_ZERO_ALLOC,
-                                &priv->vm->pgt[0].obj[0]);
-       priv->vm->pgt[0].refcount[0] = 1;
-       if (ret)
-               return ret;
-
-       return 0;
-}
-
-static int
-nv41_vmmgr_init(struct nouveau_object *object)
-{
-       struct nv04_vmmgr_priv *priv = (void *)object;
-       struct nouveau_gpuobj *dma = priv->vm->pgt[0].obj[0];
-       int ret;
-
-       ret = nouveau_vmmgr_init(&priv->base);
-       if (ret)
-               return ret;
-
-       nv_wr32(priv, 0x100800, dma->addr | 0x00000002);
-       nv_mask(priv, 0x10008c, 0x00000100, 0x00000100);
-       nv_wr32(priv, 0x100820, 0x00000000);
-       return 0;
-}
-
-struct nouveau_oclass
-nv41_vmmgr_oclass = {
-       .handle = NV_SUBDEV(VM, 0x41),
-       .ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nv41_vmmgr_ctor,
-               .dtor = nv04_vmmgr_dtor,
-               .init = nv41_vmmgr_init,
-               .fini = _nouveau_vmmgr_fini,
-       },
-};
diff --git a/drivers/gpu/drm/nouveau/core/subdev/vm/nv44.c b/drivers/gpu/drm/nouveau/core/subdev/vm/nv44.c
deleted file mode 100644 (file)
index fae1f67..0000000
+++ /dev/null
@@ -1,249 +0,0 @@
-/*
- * Copyright 2012 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 <core/gpuobj.h>
-#include <core/option.h>
-
-#include <subdev/timer.h>
-#include <subdev/vm.h>
-
-#include "nv04.h"
-
-#define NV44_GART_SIZE (512 * 1024 * 1024)
-#define NV44_GART_PAGE (  4 * 1024)
-
-/*******************************************************************************
- * VM map/unmap callbacks
- ******************************************************************************/
-
-static void
-nv44_vm_fill(struct nouveau_gpuobj *pgt, dma_addr_t null,
-            dma_addr_t *list, u32 pte, u32 cnt)
-{
-       u32 base = (pte << 2) & ~0x0000000f;
-       u32 tmp[4];
-
-       tmp[0] = nv_ro32(pgt, base + 0x0);
-       tmp[1] = nv_ro32(pgt, base + 0x4);
-       tmp[2] = nv_ro32(pgt, base + 0x8);
-       tmp[3] = nv_ro32(pgt, base + 0xc);
-
-       while (cnt--) {
-               u32 addr = list ? (*list++ >> 12) : (null >> 12);
-               switch (pte++ & 0x3) {
-               case 0:
-                       tmp[0] &= ~0x07ffffff;
-                       tmp[0] |= addr;
-                       break;
-               case 1:
-                       tmp[0] &= ~0xf8000000;
-                       tmp[0] |= addr << 27;
-                       tmp[1] &= ~0x003fffff;
-                       tmp[1] |= addr >> 5;
-                       break;
-               case 2:
-                       tmp[1] &= ~0xffc00000;
-                       tmp[1] |= addr << 22;
-                       tmp[2] &= ~0x0001ffff;
-                       tmp[2] |= addr >> 10;
-                       break;
-               case 3:
-                       tmp[2] &= ~0xfffe0000;
-                       tmp[2] |= addr << 17;
-                       tmp[3] &= ~0x00000fff;
-                       tmp[3] |= addr >> 15;
-                       break;
-               }
-       }
-
-       nv_wo32(pgt, base + 0x0, tmp[0]);
-       nv_wo32(pgt, base + 0x4, tmp[1]);
-       nv_wo32(pgt, base + 0x8, tmp[2]);
-       nv_wo32(pgt, base + 0xc, tmp[3] | 0x40000000);
-}
-
-static void
-nv44_vm_map_sg(struct nouveau_vma *vma, struct nouveau_gpuobj *pgt,
-              struct nouveau_mem *mem, u32 pte, u32 cnt, dma_addr_t *list)
-{
-       struct nv04_vmmgr_priv *priv = (void *)vma->vm->vmm;
-       u32 tmp[4];
-       int i;
-
-       if (pte & 3) {
-               u32  max = 4 - (pte & 3);
-               u32 part = (cnt > max) ? max : cnt;
-               nv44_vm_fill(pgt, priv->null, list, pte, part);
-               pte  += part;
-               list += part;
-               cnt  -= part;
-       }
-
-       while (cnt >= 4) {
-               for (i = 0; i < 4; i++)
-                       tmp[i] = *list++ >> 12;
-               nv_wo32(pgt, pte++ * 4, tmp[0] >>  0 | tmp[1] << 27);
-               nv_wo32(pgt, pte++ * 4, tmp[1] >>  5 | tmp[2] << 22);
-               nv_wo32(pgt, pte++ * 4, tmp[2] >> 10 | tmp[3] << 17);
-               nv_wo32(pgt, pte++ * 4, tmp[3] >> 15 | 0x40000000);
-               cnt -= 4;
-       }
-
-       if (cnt)
-               nv44_vm_fill(pgt, priv->null, list, pte, cnt);
-}
-
-static void
-nv44_vm_unmap(struct nouveau_gpuobj *pgt, u32 pte, u32 cnt)
-{
-       struct nv04_vmmgr_priv *priv = (void *)nouveau_vmmgr(pgt);
-
-       if (pte & 3) {
-               u32  max = 4 - (pte & 3);
-               u32 part = (cnt > max) ? max : cnt;
-               nv44_vm_fill(pgt, priv->null, NULL, pte, part);
-               pte  += part;
-               cnt  -= part;
-       }
-
-       while (cnt >= 4) {
-               nv_wo32(pgt, pte++ * 4, 0x00000000);
-               nv_wo32(pgt, pte++ * 4, 0x00000000);
-               nv_wo32(pgt, pte++ * 4, 0x00000000);
-               nv_wo32(pgt, pte++ * 4, 0x00000000);
-               cnt -= 4;
-       }
-
-       if (cnt)
-               nv44_vm_fill(pgt, priv->null, NULL, pte, cnt);
-}
-
-static void
-nv44_vm_flush(struct nouveau_vm *vm)
-{
-       struct nv04_vmmgr_priv *priv = (void *)vm->vmm;
-       nv_wr32(priv, 0x100814, priv->base.limit - NV44_GART_PAGE);
-       nv_wr32(priv, 0x100808, 0x00000020);
-       if (!nv_wait(priv, 0x100808, 0x00000001, 0x00000001))
-               nv_error(priv, "timeout: 0x%08x\n", nv_rd32(priv, 0x100808));
-       nv_wr32(priv, 0x100808, 0x00000000);
-}
-
-/*******************************************************************************
- * VMMGR subdev
- ******************************************************************************/
-
-static int
-nv44_vmmgr_ctor(struct nouveau_object *parent, struct nouveau_object *engine,
-               struct nouveau_oclass *oclass, void *data, u32 size,
-               struct nouveau_object **pobject)
-{
-       struct nouveau_device *device = nv_device(parent);
-       struct nv04_vmmgr_priv *priv;
-       int ret;
-
-       if (pci_find_capability(device->pdev, PCI_CAP_ID_AGP) ||
-           !nouveau_boolopt(device->cfgopt, "NvPCIE", true)) {
-               return nouveau_object_ctor(parent, engine, &nv04_vmmgr_oclass,
-                                          data, size, pobject);
-       }
-
-       ret = nouveau_vmmgr_create(parent, engine, oclass, "PCIEGART",
-                                  "pciegart", &priv);
-       *pobject = nv_object(priv);
-       if (ret)
-               return ret;
-
-       priv->base.create = nv04_vm_create;
-       priv->base.limit = NV44_GART_SIZE;
-       priv->base.dma_bits = 39;
-       priv->base.pgt_bits = 32 - 12;
-       priv->base.spg_shift = 12;
-       priv->base.lpg_shift = 12;
-       priv->base.map_sg = nv44_vm_map_sg;
-       priv->base.unmap = nv44_vm_unmap;
-       priv->base.flush = nv44_vm_flush;
-
-       priv->nullp = pci_alloc_consistent(device->pdev, 16 * 1024, &priv->null);
-       if (!priv->nullp) {
-               nv_error(priv, "unable to allocate dummy pages\n");
-               return -ENOMEM;
-       }
-
-       ret = nouveau_vm_create(&priv->base, 0, NV44_GART_SIZE, 0, 4096,
-                               &priv->vm);
-       if (ret)
-               return ret;
-
-       ret = nouveau_gpuobj_new(nv_object(priv), NULL,
-                               (NV44_GART_SIZE / NV44_GART_PAGE) * 4,
-                                512 * 1024, NVOBJ_FLAG_ZERO_ALLOC,
-                                &priv->vm->pgt[0].obj[0]);
-       priv->vm->pgt[0].refcount[0] = 1;
-       if (ret)
-               return ret;
-
-       return 0;
-}
-
-static int
-nv44_vmmgr_init(struct nouveau_object *object)
-{
-       struct nv04_vmmgr_priv *priv = (void *)object;
-       struct nouveau_gpuobj *gart = priv->vm->pgt[0].obj[0];
-       u32 addr;
-       int ret;
-
-       ret = nouveau_vmmgr_init(&priv->base);
-       if (ret)
-               return ret;
-
-       /* calculate vram address of this PRAMIN block, object must be
-        * allocated on 512KiB alignment, and not exceed a total size
-        * of 512KiB for this to work correctly
-        */
-       addr  = nv_rd32(priv, 0x10020c);
-       addr -= ((gart->addr >> 19) + 1) << 19;
-
-       nv_wr32(priv, 0x100850, 0x80000000);
-       nv_wr32(priv, 0x100818, priv->null);
-       nv_wr32(priv, 0x100804, NV44_GART_SIZE);
-       nv_wr32(priv, 0x100850, 0x00008000);
-       nv_mask(priv, 0x10008c, 0x00000200, 0x00000200);
-       nv_wr32(priv, 0x100820, 0x00000000);
-       nv_wr32(priv, 0x10082c, 0x00000001);
-       nv_wr32(priv, 0x100800, addr | 0x00000010);
-       return 0;
-}
-
-struct nouveau_oclass
-nv44_vmmgr_oclass = {
-       .handle = NV_SUBDEV(VM, 0x44),
-       .ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nv44_vmmgr_ctor,
-               .dtor = nv04_vmmgr_dtor,
-               .init = nv44_vmmgr_init,
-               .fini = _nouveau_vmmgr_fini,
-       },
-};
diff --git a/drivers/gpu/drm/nouveau/core/subdev/vm/nv50.c b/drivers/gpu/drm/nouveau/core/subdev/vm/nv50.c
deleted file mode 100644 (file)
index a4aa81a..0000000
+++ /dev/null
@@ -1,240 +0,0 @@
-/*
- * 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 <core/device.h>
-#include <core/gpuobj.h>
-
-#include <subdev/timer.h>
-#include <subdev/fb.h>
-#include <subdev/bar.h>
-#include <subdev/vm.h>
-
-struct nv50_vmmgr_priv {
-       struct nouveau_vmmgr base;
-};
-
-static void
-nv50_vm_map_pgt(struct nouveau_gpuobj *pgd, u32 pde,
-               struct nouveau_gpuobj *pgt[2])
-{
-       u64 phys = 0xdeadcafe00000000ULL;
-       u32 coverage = 0;
-
-       if (pgt[0]) {
-               phys = 0x00000003 | pgt[0]->addr; /* present, 4KiB pages */
-               coverage = (pgt[0]->size >> 3) << 12;
-       } else
-       if (pgt[1]) {
-               phys = 0x00000001 | pgt[1]->addr; /* present */
-               coverage = (pgt[1]->size >> 3) << 16;
-       }
-
-       if (phys & 1) {
-               if (coverage <= 32 * 1024 * 1024)
-                       phys |= 0x60;
-               else if (coverage <= 64 * 1024 * 1024)
-                       phys |= 0x40;
-               else if (coverage <= 128 * 1024 * 1024)
-                       phys |= 0x20;
-       }
-
-       nv_wo32(pgd, (pde * 8) + 0, lower_32_bits(phys));
-       nv_wo32(pgd, (pde * 8) + 4, upper_32_bits(phys));
-}
-
-static inline u64
-vm_addr(struct nouveau_vma *vma, u64 phys, u32 memtype, u32 target)
-{
-       phys |= 1; /* present */
-       phys |= (u64)memtype << 40;
-       phys |= target << 4;
-       if (vma->access & NV_MEM_ACCESS_SYS)
-               phys |= (1 << 6);
-       if (!(vma->access & NV_MEM_ACCESS_WO))
-               phys |= (1 << 3);
-       return phys;
-}
-
-static void
-nv50_vm_map(struct nouveau_vma *vma, struct nouveau_gpuobj *pgt,
-           struct nouveau_mem *mem, u32 pte, u32 cnt, u64 phys, u64 delta)
-{
-       u32 comp = (mem->memtype & 0x180) >> 7;
-       u32 block, target;
-       int i;
-
-       /* IGPs don't have real VRAM, re-target to stolen system memory */
-       target = 0;
-       if (nouveau_fb(vma->vm->vmm)->ram->stolen) {
-               phys += nouveau_fb(vma->vm->vmm)->ram->stolen;
-               target = 3;
-       }
-
-       phys  = vm_addr(vma, phys, mem->memtype, target);
-       pte <<= 3;
-       cnt <<= 3;
-
-       while (cnt) {
-               u32 offset_h = upper_32_bits(phys);
-               u32 offset_l = lower_32_bits(phys);
-
-               for (i = 7; i >= 0; i--) {
-                       block = 1 << (i + 3);
-                       if (cnt >= block && !(pte & (block - 1)))
-                               break;
-               }
-               offset_l |= (i << 7);
-
-               phys += block << (vma->node->type - 3);
-               cnt  -= block;
-               if (comp) {
-                       u32 tag = mem->tag->offset + ((delta >> 16) * comp);
-                       offset_h |= (tag << 17);
-                       delta    += block << (vma->node->type - 3);
-               }
-
-               while (block) {
-                       nv_wo32(pgt, pte + 0, offset_l);
-                       nv_wo32(pgt, pte + 4, offset_h);
-                       pte += 8;
-                       block -= 8;
-               }
-       }
-}
-
-static void
-nv50_vm_map_sg(struct nouveau_vma *vma, struct nouveau_gpuobj *pgt,
-              struct nouveau_mem *mem, u32 pte, u32 cnt, dma_addr_t *list)
-{
-       u32 target = (vma->access & NV_MEM_ACCESS_NOSNOOP) ? 3 : 2;
-       pte <<= 3;
-       while (cnt--) {
-               u64 phys = vm_addr(vma, (u64)*list++, mem->memtype, target);
-               nv_wo32(pgt, pte + 0, lower_32_bits(phys));
-               nv_wo32(pgt, pte + 4, upper_32_bits(phys));
-               pte += 8;
-       }
-}
-
-static void
-nv50_vm_unmap(struct nouveau_gpuobj *pgt, u32 pte, u32 cnt)
-{
-       pte <<= 3;
-       while (cnt--) {
-               nv_wo32(pgt, pte + 0, 0x00000000);
-               nv_wo32(pgt, pte + 4, 0x00000000);
-               pte += 8;
-       }
-}
-
-static void
-nv50_vm_flush(struct nouveau_vm *vm)
-{
-       struct nv50_vmmgr_priv *priv = (void *)vm->vmm;
-       struct nouveau_bar *bar = nouveau_bar(priv);
-       struct nouveau_engine *engine;
-       int i, vme;
-
-       bar->flush(bar);
-
-       mutex_lock(&nv_subdev(priv)->mutex);
-       for (i = 0; i < NVDEV_SUBDEV_NR; i++) {
-               if (!atomic_read(&vm->engref[i]))
-                       continue;
-
-               /* unfortunate hw bug workaround... */
-               engine = nouveau_engine(priv, i);
-               if (engine && engine->tlb_flush) {
-                       engine->tlb_flush(engine);
-                       continue;
-               }
-
-               switch (i) {
-               case NVDEV_ENGINE_GR   : vme = 0x00; break;
-               case NVDEV_ENGINE_VP   : vme = 0x01; break;
-               case NVDEV_SUBDEV_BAR  : vme = 0x06; break;
-               case NVDEV_ENGINE_PPP  :
-               case NVDEV_ENGINE_MPEG : vme = 0x08; break;
-               case NVDEV_ENGINE_BSP  : vme = 0x09; break;
-               case NVDEV_ENGINE_CRYPT: vme = 0x0a; break;
-               case NVDEV_ENGINE_COPY0: vme = 0x0d; break;
-               default:
-                       continue;
-               }
-
-               nv_wr32(priv, 0x100c80, (vme << 16) | 1);
-               if (!nv_wait(priv, 0x100c80, 0x00000001, 0x00000000))
-                       nv_error(priv, "vm flush timeout: engine %d\n", vme);
-       }
-       mutex_unlock(&nv_subdev(priv)->mutex);
-}
-
-static int
-nv50_vm_create(struct nouveau_vmmgr *vmm, u64 offset, u64 length,
-              u64 mm_offset, struct nouveau_vm **pvm)
-{
-       u32 block = (1 << (vmm->pgt_bits + 12));
-       if (block > length)
-               block = length;
-
-       return nouveau_vm_create(vmm, offset, length, mm_offset, block, pvm);
-}
-
-static int
-nv50_vmmgr_ctor(struct nouveau_object *parent, struct nouveau_object *engine,
-               struct nouveau_oclass *oclass, void *data, u32 size,
-               struct nouveau_object **pobject)
-{
-       struct nv50_vmmgr_priv *priv;
-       int ret;
-
-       ret = nouveau_vmmgr_create(parent, engine, oclass, "VM", "vm", &priv);
-       *pobject = nv_object(priv);
-       if (ret)
-               return ret;
-
-       priv->base.limit = 1ULL << 40;
-       priv->base.dma_bits = 40;
-       priv->base.pgt_bits  = 29 - 12;
-       priv->base.spg_shift = 12;
-       priv->base.lpg_shift = 16;
-       priv->base.create = nv50_vm_create;
-       priv->base.map_pgt = nv50_vm_map_pgt;
-       priv->base.map = nv50_vm_map;
-       priv->base.map_sg = nv50_vm_map_sg;
-       priv->base.unmap = nv50_vm_unmap;
-       priv->base.flush = nv50_vm_flush;
-       return 0;
-}
-
-struct nouveau_oclass
-nv50_vmmgr_oclass = {
-       .handle = NV_SUBDEV(VM, 0x50),
-       .ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nv50_vmmgr_ctor,
-               .dtor = _nouveau_vmmgr_dtor,
-               .init = _nouveau_vmmgr_init,
-               .fini = _nouveau_vmmgr_fini,
-       },
-};
diff --git a/drivers/gpu/drm/nouveau/core/subdev/vm/nvc0.c b/drivers/gpu/drm/nouveau/core/subdev/vm/nvc0.c
deleted file mode 100644 (file)
index 2d09887..0000000
+++ /dev/null
@@ -1,242 +0,0 @@
-/*
- * 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 <core/device.h>
-#include <core/gpuobj.h>
-
-#include <subdev/timer.h>
-#include <subdev/fb.h>
-#include <subdev/vm.h>
-#include <subdev/ltc.h>
-#include <subdev/bar.h>
-
-struct nvc0_vmmgr_priv {
-       struct nouveau_vmmgr base;
-};
-
-
-/* Map from compressed to corresponding uncompressed storage type.
- * The value 0xff represents an invalid storage type.
- */
-const u8 nvc0_pte_storage_type_map[256] =
-{
-       0x00, 0x01, 0x01, 0x01, 0x01, 0x01, 0xff, 0x01, /* 0x00 */
-       0x01, 0x01, 0x01, 0xff, 0xff, 0xff, 0xff, 0xff,
-       0xff, 0x11, 0xff, 0xff, 0xff, 0xff, 0xff, 0x11, /* 0x10 */
-       0x11, 0x11, 0x11, 0xff, 0xff, 0xff, 0xff, 0xff,
-       0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0x26, 0x27, /* 0x20 */
-       0x28, 0x29, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
-       0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, /* 0x30 */
-       0xff, 0xff, 0x26, 0x27, 0x28, 0x29, 0x26, 0x27,
-       0x28, 0x29, 0xff, 0xff, 0xff, 0xff, 0x46, 0xff, /* 0x40 */
-       0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
-       0xff, 0x46, 0x46, 0x46, 0x46, 0xff, 0xff, 0xff, /* 0x50 */
-       0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
-       0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, /* 0x60 */
-       0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
-       0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, /* 0x70 */
-       0xff, 0xff, 0xff, 0x7b, 0xff, 0xff, 0xff, 0xff,
-       0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0x7b, 0x7b, /* 0x80 */
-       0x7b, 0x7b, 0xff, 0x8b, 0x8c, 0x8d, 0x8e, 0xff,
-       0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, /* 0x90 */
-       0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
-       0xff, 0xff, 0xff, 0x8b, 0x8c, 0x8d, 0x8e, 0xa7, /* 0xa0 */
-       0xa8, 0xa9, 0xaa, 0xff, 0xff, 0xff, 0xff, 0xff,
-       0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, /* 0xb0 */
-       0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xa7,
-       0xa8, 0xa9, 0xaa, 0xc3, 0xff, 0xff, 0xff, 0xff, /* 0xc0 */
-       0xff, 0xff, 0xff, 0xff, 0xfe, 0xfe, 0xc3, 0xc3,
-       0xc3, 0xc3, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, /* 0xd0 */
-       0xfe, 0xff, 0xff, 0xfe, 0xff, 0xfe, 0xff, 0xfe,
-       0xfe, 0xff, 0xfe, 0xfe, 0xfe, 0xfe, 0xfe, 0xff, /* 0xe0 */
-       0xff, 0xfe, 0xff, 0xfe, 0xff, 0xfe, 0xfe, 0xff,
-       0xfe, 0xfe, 0xfe, 0xfe, 0xfe, 0xfe, 0xfe, 0xfe, /* 0xf0 */
-       0xfe, 0xfe, 0xfe, 0xfe, 0xff, 0xfd, 0xfe, 0xff
-};
-
-
-static void
-nvc0_vm_map_pgt(struct nouveau_gpuobj *pgd, u32 index,
-               struct nouveau_gpuobj *pgt[2])
-{
-       u32 pde[2] = { 0, 0 };
-
-       if (pgt[0])
-               pde[1] = 0x00000001 | (pgt[0]->addr >> 8);
-       if (pgt[1])
-               pde[0] = 0x00000001 | (pgt[1]->addr >> 8);
-
-       nv_wo32(pgd, (index * 8) + 0, pde[0]);
-       nv_wo32(pgd, (index * 8) + 4, pde[1]);
-}
-
-static inline u64
-nvc0_vm_addr(struct nouveau_vma *vma, u64 phys, u32 memtype, u32 target)
-{
-       phys >>= 8;
-
-       phys |= 0x00000001; /* present */
-       if (vma->access & NV_MEM_ACCESS_SYS)
-               phys |= 0x00000002;
-
-       phys |= ((u64)target  << 32);
-       phys |= ((u64)memtype << 36);
-
-       return phys;
-}
-
-static void
-nvc0_vm_map(struct nouveau_vma *vma, struct nouveau_gpuobj *pgt,
-           struct nouveau_mem *mem, u32 pte, u32 cnt, u64 phys, u64 delta)
-{
-       u64 next = 1 << (vma->node->type - 8);
-
-       phys  = nvc0_vm_addr(vma, phys, mem->memtype, 0);
-       pte <<= 3;
-
-       if (mem->tag) {
-               struct nouveau_ltc *ltc =
-                       nouveau_ltc(vma->vm->vmm->base.base.parent);
-               u32 tag = mem->tag->offset + (delta >> 17);
-               phys |= (u64)tag << (32 + 12);
-               next |= (u64)1   << (32 + 12);
-               ltc->tags_clear(ltc, tag, cnt);
-       }
-
-       while (cnt--) {
-               nv_wo32(pgt, pte + 0, lower_32_bits(phys));
-               nv_wo32(pgt, pte + 4, upper_32_bits(phys));
-               phys += next;
-               pte  += 8;
-       }
-}
-
-static void
-nvc0_vm_map_sg(struct nouveau_vma *vma, struct nouveau_gpuobj *pgt,
-              struct nouveau_mem *mem, u32 pte, u32 cnt, dma_addr_t *list)
-{
-       u32 target = (vma->access & NV_MEM_ACCESS_NOSNOOP) ? 7 : 5;
-       /* compressed storage types are invalid for system memory */
-       u32 memtype = nvc0_pte_storage_type_map[mem->memtype & 0xff];
-
-       pte <<= 3;
-       while (cnt--) {
-               u64 phys = nvc0_vm_addr(vma, *list++, memtype, target);
-               nv_wo32(pgt, pte + 0, lower_32_bits(phys));
-               nv_wo32(pgt, pte + 4, upper_32_bits(phys));
-               pte += 8;
-       }
-}
-
-static void
-nvc0_vm_unmap(struct nouveau_gpuobj *pgt, u32 pte, u32 cnt)
-{
-       pte <<= 3;
-       while (cnt--) {
-               nv_wo32(pgt, pte + 0, 0x00000000);
-               nv_wo32(pgt, pte + 4, 0x00000000);
-               pte += 8;
-       }
-}
-
-static void
-nvc0_vm_flush(struct nouveau_vm *vm)
-{
-       struct nvc0_vmmgr_priv *priv = (void *)vm->vmm;
-       struct nouveau_bar *bar = nouveau_bar(priv);
-       struct nouveau_vm_pgd *vpgd;
-       u32 type;
-
-       bar->flush(bar);
-
-       type = 0x00000001; /* PAGE_ALL */
-       if (atomic_read(&vm->engref[NVDEV_SUBDEV_BAR]))
-               type |= 0x00000004; /* HUB_ONLY */
-
-       mutex_lock(&nv_subdev(priv)->mutex);
-       list_for_each_entry(vpgd, &vm->pgd_list, head) {
-               /* looks like maybe a "free flush slots" counter, the
-                * faster you write to 0x100cbc to more it decreases
-                */
-               if (!nv_wait_ne(priv, 0x100c80, 0x00ff0000, 0x00000000)) {
-                       nv_error(priv, "vm timeout 0: 0x%08x %d\n",
-                                nv_rd32(priv, 0x100c80), type);
-               }
-
-               nv_wr32(priv, 0x100cb8, vpgd->obj->addr >> 8);
-               nv_wr32(priv, 0x100cbc, 0x80000000 | type);
-
-               /* wait for flush to be queued? */
-               if (!nv_wait(priv, 0x100c80, 0x00008000, 0x00008000)) {
-                       nv_error(priv, "vm timeout 1: 0x%08x %d\n",
-                                nv_rd32(priv, 0x100c80), type);
-               }
-       }
-       mutex_unlock(&nv_subdev(priv)->mutex);
-}
-
-static int
-nvc0_vm_create(struct nouveau_vmmgr *vmm, u64 offset, u64 length,
-              u64 mm_offset, struct nouveau_vm **pvm)
-{
-       return nouveau_vm_create(vmm, offset, length, mm_offset, 4096, pvm);
-}
-
-static int
-nvc0_vmmgr_ctor(struct nouveau_object *parent, struct nouveau_object *engine,
-               struct nouveau_oclass *oclass, void *data, u32 size,
-               struct nouveau_object **pobject)
-{
-       struct nvc0_vmmgr_priv *priv;
-       int ret;
-
-       ret = nouveau_vmmgr_create(parent, engine, oclass, "VM", "vm", &priv);
-       *pobject = nv_object(priv);
-       if (ret)
-               return ret;
-
-       priv->base.limit = 1ULL << 40;
-       priv->base.dma_bits = 40;
-       priv->base.pgt_bits  = 27 - 12;
-       priv->base.spg_shift = 12;
-       priv->base.lpg_shift = 17;
-       priv->base.create = nvc0_vm_create;
-       priv->base.map_pgt = nvc0_vm_map_pgt;
-       priv->base.map = nvc0_vm_map;
-       priv->base.map_sg = nvc0_vm_map_sg;
-       priv->base.unmap = nvc0_vm_unmap;
-       priv->base.flush = nvc0_vm_flush;
-       return 0;
-}
-
-struct nouveau_oclass
-nvc0_vmmgr_oclass = {
-       .handle = NV_SUBDEV(VM, 0xc0),
-       .ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nvc0_vmmgr_ctor,
-               .dtor = _nouveau_vmmgr_dtor,
-               .init = _nouveau_vmmgr_init,
-               .fini = _nouveau_vmmgr_fini,
-       },
-};
diff --git a/drivers/gpu/drm/nouveau/core/subdev/volt/base.c b/drivers/gpu/drm/nouveau/core/subdev/volt/base.c
deleted file mode 100644 (file)
index 26ccd8d..0000000
+++ /dev/null
@@ -1,207 +0,0 @@
-/*
- * Copyright 2013 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 <subdev/volt.h>
-
-#include <subdev/bios.h>
-#include <subdev/bios/vmap.h>
-#include <subdev/bios/volt.h>
-
-static int
-nouveau_volt_get(struct nouveau_volt *volt)
-{
-       if (volt->vid_get) {
-               int ret = volt->vid_get(volt), i;
-               if (ret >= 0) {
-                       for (i = 0; i < volt->vid_nr; i++) {
-                               if (volt->vid[i].vid == ret)
-                                       return volt->vid[i].uv;
-                       }
-                       ret = -EINVAL;
-               }
-               return ret;
-       }
-       return -ENODEV;
-}
-
-static int
-nouveau_volt_set(struct nouveau_volt *volt, u32 uv)
-{
-       if (volt->vid_set) {
-               int i, ret = -EINVAL;
-               for (i = 0; i < volt->vid_nr; i++) {
-                       if (volt->vid[i].uv == uv) {
-                               ret = volt->vid_set(volt, volt->vid[i].vid);
-                               nv_debug(volt, "set %duv: %d\n", uv, ret);
-                               break;
-                       }
-               }
-               return ret;
-       }
-       return -ENODEV;
-}
-
-static int
-nouveau_volt_map(struct nouveau_volt *volt, u8 id)
-{
-       struct nouveau_bios *bios = nouveau_bios(volt);
-       struct nvbios_vmap_entry info;
-       u8  ver, len;
-       u16 vmap;
-
-       vmap = nvbios_vmap_entry_parse(bios, id, &ver, &len, &info);
-       if (vmap) {
-               if (info.link != 0xff) {
-                       int ret = nouveau_volt_map(volt, info.link);
-                       if (ret < 0)
-                               return ret;
-                       info.min += ret;
-               }
-               return info.min;
-       }
-
-       return id ? id * 10000 : -ENODEV;
-}
-
-static int
-nouveau_volt_set_id(struct nouveau_volt *volt, u8 id, int condition)
-{
-       int ret = nouveau_volt_map(volt, id);
-       if (ret >= 0) {
-               int prev = nouveau_volt_get(volt);
-               if (!condition || prev < 0 ||
-                   (condition < 0 && ret < prev) ||
-                   (condition > 0 && ret > prev)) {
-                       ret = nouveau_volt_set(volt, ret);
-               } else {
-                       ret = 0;
-               }
-       }
-       return ret;
-}
-
-static void nouveau_volt_parse_bios(struct nouveau_bios *bios,
-               struct nouveau_volt *volt)
-{
-       struct nvbios_volt_entry ivid;
-       struct nvbios_volt info;
-       u8  ver, hdr, cnt, len;
-       u16 data;
-       int i;
-
-       data = nvbios_volt_parse(bios, &ver, &hdr, &cnt, &len, &info);
-       if (data && info.vidmask && info.base && info.step) {
-               for (i = 0; i < info.vidmask + 1; i++) {
-                       if (info.base >= info.min &&
-                               info.base <= info.max) {
-                               volt->vid[volt->vid_nr].uv = info.base;
-                               volt->vid[volt->vid_nr].vid = i;
-                               volt->vid_nr++;
-                       }
-                       info.base += info.step;
-               }
-               volt->vid_mask = info.vidmask;
-       } else if (data && info.vidmask) {
-               for (i = 0; i < cnt; i++) {
-                       data = nvbios_volt_entry_parse(bios, i, &ver, &hdr,
-                                                         &ivid);
-                       if (data) {
-                               volt->vid[volt->vid_nr].uv = ivid.voltage;
-                               volt->vid[volt->vid_nr].vid = ivid.vid;
-                               volt->vid_nr++;
-                       }
-               }
-               volt->vid_mask = info.vidmask;
-       }
-}
-
-int
-_nouveau_volt_init(struct nouveau_object *object)
-{
-       struct nouveau_volt *volt = (void *)object;
-       int ret;
-
-       ret = nouveau_subdev_init(&volt->base);
-       if (ret)
-               return ret;
-
-       ret = volt->get(volt);
-       if (ret < 0) {
-               if (ret != -ENODEV)
-                       nv_debug(volt, "current voltage unknown\n");
-               return 0;
-       }
-
-       nv_info(volt, "GPU voltage: %duv\n", ret);
-       return 0;
-}
-
-void
-_nouveau_volt_dtor(struct nouveau_object *object)
-{
-       struct nouveau_volt *volt = (void *)object;
-       nouveau_subdev_destroy(&volt->base);
-}
-
-int
-nouveau_volt_create_(struct nouveau_object *parent,
-                    struct nouveau_object *engine,
-                    struct nouveau_oclass *oclass, int length, void **pobject)
-{
-       struct nouveau_bios *bios = nouveau_bios(parent);
-       struct nouveau_volt *volt;
-       int ret, i;
-
-       ret = nouveau_subdev_create_(parent, engine, oclass, 0, "VOLT",
-                                    "voltage", length, pobject);
-       volt = *pobject;
-       if (ret)
-               return ret;
-
-       volt->get = nouveau_volt_get;
-       volt->set = nouveau_volt_set;
-       volt->set_id = nouveau_volt_set_id;
-
-       /* Assuming the non-bios device should build the voltage table later */
-       if (bios)
-               nouveau_volt_parse_bios(bios, volt);
-
-       if (volt->vid_nr) {
-               for (i = 0; i < volt->vid_nr; i++) {
-                       nv_debug(volt, "VID %02x: %duv\n",
-                                volt->vid[i].vid, volt->vid[i].uv);
-               }
-
-               /*XXX: this is an assumption.. there probably exists boards
-                * out there with i2c-connected voltage controllers too..
-                */
-               ret = nouveau_voltgpio_init(volt);
-               if (ret == 0) {
-                       volt->vid_get = nouveau_voltgpio_get;
-                       volt->vid_set = nouveau_voltgpio_set;
-               }
-       }
-
-       return ret;
-}
diff --git a/drivers/gpu/drm/nouveau/core/subdev/volt/gk20a.c b/drivers/gpu/drm/nouveau/core/subdev/volt/gk20a.c
deleted file mode 100644 (file)
index 717368e..0000000
+++ /dev/null
@@ -1,199 +0,0 @@
-/*
- * Copyright (c) 2014, NVIDIA CORPORATION. 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 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.
- */
-
-#ifdef __KERNEL__
-#include <nouveau_platform.h>
-#endif
-#include <subdev/volt.h>
-
-struct cvb_coef {
-       int c0;
-       int c1;
-       int c2;
-       int c3;
-       int c4;
-       int c5;
-};
-
-struct gk20a_volt_priv {
-       struct nouveau_volt base;
-       struct regulator *vdd;
-};
-
-const struct cvb_coef gk20a_cvb_coef[] = {
-       /* MHz,        c0,     c1,   c2,    c3,     c4,   c5 */
-       /*  72 */ { 1209886, -36468,  515,   417, -13123,  203},
-       /* 108 */ { 1130804, -27659,  296,   298, -10834,  221},
-       /* 180 */ { 1162871, -27110,  247,   238, -10681,  268},
-       /* 252 */ { 1220458, -28654,  247,   179, -10376,  298},
-       /* 324 */ { 1280953, -30204,  247,   119,  -9766,  304},
-       /* 396 */ { 1344547, -31777,  247,   119,  -8545,  292},
-       /* 468 */ { 1420168, -34227,  269,    60,  -7172,  256},
-       /* 540 */ { 1490757, -35955,  274,    60,  -5188,  197},
-       /* 612 */ { 1599112, -42583,  398,     0,  -1831,  119},
-       /* 648 */ { 1366986, -16459, -274,     0,  -3204,   72},
-       /* 684 */ { 1391884, -17078, -274,   -60,  -1526,   30},
-       /* 708 */ { 1415522, -17497, -274,   -60,   -458,    0},
-       /* 756 */ { 1464061, -18331, -274,  -119,   1831,  -72},
-       /* 804 */ { 1524225, -20064, -254,  -119,   4272, -155},
-       /* 852 */ { 1608418, -21643, -269,     0,    763,  -48},
-};
-
-/**
- * cvb_mv = ((c2 * speedo / s_scale + c1) * speedo / s_scale + c0)
- */
-static inline int
-gk20a_volt_get_cvb_voltage(int speedo, int s_scale,
-               const struct cvb_coef *coef)
-{
-       int mv;
-
-       mv = DIV_ROUND_CLOSEST(coef->c2 * speedo, s_scale);
-       mv = DIV_ROUND_CLOSEST((mv + coef->c1) * speedo, s_scale) + coef->c0;
-       return mv;
-}
-
-/**
- * cvb_t_mv =
- * ((c2 * speedo / s_scale + c1) * speedo / s_scale + c0) +
- * ((c3 * speedo / s_scale + c4 + c5 * T / t_scale) * T / t_scale)
- */
-static inline int
-gk20a_volt_get_cvb_t_voltage(int speedo, int temp, int s_scale, int t_scale,
-               const struct cvb_coef *coef)
-{
-       int cvb_mv, mv;
-
-       cvb_mv = gk20a_volt_get_cvb_voltage(speedo, s_scale, coef);
-
-       mv = DIV_ROUND_CLOSEST(coef->c3 * speedo, s_scale) + coef->c4 +
-               DIV_ROUND_CLOSEST(coef->c5 * temp, t_scale);
-       mv = DIV_ROUND_CLOSEST(mv * temp, t_scale) + cvb_mv;
-       return mv;
-}
-
-static int
-gk20a_volt_calc_voltage(const struct cvb_coef *coef, int speedo)
-{
-       int mv;
-
-       mv = gk20a_volt_get_cvb_t_voltage(speedo, -10, 100, 10, coef);
-       mv = DIV_ROUND_UP(mv, 1000);
-
-       return mv * 1000;
-}
-
-static int
-gk20a_volt_vid_get(struct nouveau_volt *volt)
-{
-       struct gk20a_volt_priv *priv = (void *)volt;
-       int i, uv;
-
-       uv = regulator_get_voltage(priv->vdd);
-
-       for (i = 0; i < volt->vid_nr; i++)
-               if (volt->vid[i].uv >= uv)
-                       return i;
-
-       return -EINVAL;
-}
-
-static int
-gk20a_volt_vid_set(struct nouveau_volt *volt, u8 vid)
-{
-       struct gk20a_volt_priv *priv = (void *)volt;
-
-       nv_debug(volt, "set voltage as %duv\n", volt->vid[vid].uv);
-       return regulator_set_voltage(priv->vdd, volt->vid[vid].uv, 1200000);
-}
-
-static int
-gk20a_volt_set_id(struct nouveau_volt *volt, u8 id, int condition)
-{
-       struct gk20a_volt_priv *priv = (void *)volt;
-       int prev_uv = regulator_get_voltage(priv->vdd);
-       int target_uv = volt->vid[id].uv;
-       int ret;
-
-       nv_debug(volt, "prev=%d, target=%d, condition=%d\n",
-                       prev_uv, target_uv, condition);
-       if (!condition ||
-               (condition < 0 && target_uv < prev_uv) ||
-               (condition > 0 && target_uv > prev_uv)) {
-               ret = gk20a_volt_vid_set(volt, volt->vid[id].vid);
-       } else {
-               ret = 0;
-       }
-
-       return ret;
-}
-
-static int
-gk20a_volt_ctor(struct nouveau_object *parent, struct nouveau_object *engine,
-              struct nouveau_oclass *oclass, void *data, u32 size,
-              struct nouveau_object **pobject)
-{
-       struct gk20a_volt_priv *priv;
-       struct nouveau_volt *volt;
-       struct nouveau_platform_device *plat;
-       int i, ret, uv;
-
-       ret = nouveau_volt_create(parent, engine, oclass, &priv);
-       *pobject = nv_object(priv);
-       if (ret)
-               return ret;
-
-       volt = &priv->base;
-
-       plat = nv_device_to_platform(nv_device(parent));
-
-       uv = regulator_get_voltage(plat->gpu->vdd);
-       nv_info(priv, "The default voltage is %duV\n", uv);
-
-       priv->vdd = plat->gpu->vdd;
-       priv->base.vid_get = gk20a_volt_vid_get;
-       priv->base.vid_set = gk20a_volt_vid_set;
-       priv->base.set_id = gk20a_volt_set_id;
-
-       volt->vid_nr = ARRAY_SIZE(gk20a_cvb_coef);
-       nv_debug(priv, "%s - vid_nr = %d\n", __func__, volt->vid_nr);
-       for (i = 0; i < volt->vid_nr; i++) {
-               volt->vid[i].vid = i;
-               volt->vid[i].uv = gk20a_volt_calc_voltage(&gk20a_cvb_coef[i],
-                                       plat->gpu_speedo);
-               nv_debug(priv, "%2d: vid=%d, uv=%d\n", i, volt->vid[i].vid,
-                                       volt->vid[i].uv);
-       }
-
-       return 0;
-}
-
-struct nouveau_oclass
-gk20a_volt_oclass = {
-       .handle = NV_SUBDEV(VOLT, 0xea),
-       .ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = gk20a_volt_ctor,
-               .dtor = _nouveau_volt_dtor,
-               .init = _nouveau_volt_init,
-               .fini = _nouveau_volt_fini,
-       },
-};
diff --git a/drivers/gpu/drm/nouveau/core/subdev/volt/gpio.c b/drivers/gpu/drm/nouveau/core/subdev/volt/gpio.c
deleted file mode 100644 (file)
index 755fa91..0000000
+++ /dev/null
@@ -1,96 +0,0 @@
-/*
- * Copyright 2013 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 <subdev/volt.h>
-#include <subdev/gpio.h>
-#include <subdev/bios/gpio.h>
-
-static const u8 tags[] = {
-       DCB_GPIO_VID0, DCB_GPIO_VID1, DCB_GPIO_VID2, DCB_GPIO_VID3,
-       DCB_GPIO_VID4, DCB_GPIO_VID5, DCB_GPIO_VID6, DCB_GPIO_VID7,
-};
-
-int
-nouveau_voltgpio_get(struct nouveau_volt *volt)
-{
-       struct nouveau_gpio *gpio = nouveau_gpio(volt);
-       u8 vid = 0;
-       int i;
-
-       for (i = 0; i < ARRAY_SIZE(tags); i++) {
-               if (volt->vid_mask & (1 << i)) {
-                       int ret = gpio->get(gpio, 0, tags[i], 0xff);
-                       if (ret < 0)
-                               return ret;
-                       vid |= ret << i;
-               }
-       }
-
-       return vid;
-}
-
-int
-nouveau_voltgpio_set(struct nouveau_volt *volt, u8 vid)
-{
-       struct nouveau_gpio *gpio = nouveau_gpio(volt);
-       int i;
-
-       for (i = 0; i < ARRAY_SIZE(tags); i++, vid >>= 1) {
-               if (volt->vid_mask & (1 << i)) {
-                       int ret = gpio->set(gpio, 0, tags[i], 0xff, vid & 1);
-                       if (ret < 0)
-                               return ret;
-               }
-       }
-
-       return 0;
-}
-
-int
-nouveau_voltgpio_init(struct nouveau_volt *volt)
-{
-       struct nouveau_gpio *gpio = nouveau_gpio(volt);
-       struct dcb_gpio_func func;
-       int i;
-
-       /* check we have gpio function info for each vid bit.  on some
-        * boards (ie. nvs295) the vid mask has more bits than there
-        * are valid gpio functions... from traces, nvidia appear to
-        * just touch the existing ones, so let's mask off the invalid
-        * bits and continue with life
-        */
-       for (i = 0; i < ARRAY_SIZE(tags); i++) {
-               if (volt->vid_mask & (1 << i)) {
-                       int ret = gpio->find(gpio, 0, tags[i], 0xff, &func);
-                       if (ret) {
-                               if (ret != -ENOENT)
-                                       return ret;
-                               nv_debug(volt, "VID bit %d has no GPIO\n", i);
-                               volt->vid_mask &= ~(1 << i);
-                       }
-               }
-       }
-
-       return 0;
-}
diff --git a/drivers/gpu/drm/nouveau/core/subdev/volt/nv40.c b/drivers/gpu/drm/nouveau/core/subdev/volt/nv40.c
deleted file mode 100644 (file)
index 87d5358..0000000
+++ /dev/null
@@ -1,56 +0,0 @@
-/*
- * Copyright 2013 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 <subdev/volt.h>
-
-struct nv40_volt_priv {
-       struct nouveau_volt base;
-};
-
-static int
-nv40_volt_ctor(struct nouveau_object *parent, struct nouveau_object *engine,
-              struct nouveau_oclass *oclass, void *data, u32 size,
-              struct nouveau_object **pobject)
-{
-       struct nv40_volt_priv *priv;
-       int ret;
-
-       ret = nouveau_volt_create(parent, engine, oclass, &priv);
-       *pobject = nv_object(priv);
-       if (ret)
-               return ret;
-
-       return 0;
-}
-
-struct nouveau_oclass
-nv40_volt_oclass = {
-       .handle = NV_SUBDEV(VOLT, 0x40),
-       .ofuncs = &(struct nouveau_ofuncs) {
-               .ctor = nv40_volt_ctor,
-               .dtor = _nouveau_volt_dtor,
-               .init = _nouveau_volt_init,
-               .fini = _nouveau_volt_fini,
-       },
-};
diff --git a/drivers/gpu/drm/nouveau/dispnv04/Kbuild b/drivers/gpu/drm/nouveau/dispnv04/Kbuild
new file mode 100644 (file)
index 0000000..424a489
--- /dev/null
@@ -0,0 +1,11 @@
+nouveau-y += dispnv04/arb.o
+nouveau-y += dispnv04/crtc.o
+nouveau-y += dispnv04/cursor.o
+nouveau-y += dispnv04/dac.o
+nouveau-y += dispnv04/dfp.o
+nouveau-y += dispnv04/disp.o
+nouveau-y += dispnv04/hw.o
+nouveau-y += dispnv04/overlay.o
+nouveau-y += dispnv04/tvmodesnv17.o
+nouveau-y += dispnv04/tvnv04.o
+nouveau-y += dispnv04/tvnv17.o
diff --git a/drivers/gpu/drm/nouveau/dispnv04/Makefile b/drivers/gpu/drm/nouveau/dispnv04/Makefile
deleted file mode 100644 (file)
index 424a489..0000000
+++ /dev/null
@@ -1,11 +0,0 @@
-nouveau-y += dispnv04/arb.o
-nouveau-y += dispnv04/crtc.o
-nouveau-y += dispnv04/cursor.o
-nouveau-y += dispnv04/dac.o
-nouveau-y += dispnv04/dfp.o
-nouveau-y += dispnv04/disp.o
-nouveau-y += dispnv04/hw.o
-nouveau-y += dispnv04/overlay.o
-nouveau-y += dispnv04/tvmodesnv17.o
-nouveau-y += dispnv04/tvnv04.o
-nouveau-y += dispnv04/tvnv17.o
index 38402ade68351f9ecab27eed823c0a6d131a75b5..542bb266a0ab8ee8f9cdfadce188d25c7605c0b4 100644 (file)
@@ -41,7 +41,7 @@
 #include "disp.h"
 
 #include <subdev/bios/pll.h>
-#include <subdev/clock.h>
+#include <subdev/clk.h>
 
 static int
 nv04_crtc_mode_set_base(struct drm_crtc *crtc, int x, int y,
@@ -112,12 +112,12 @@ static void nv_crtc_calc_state_ext(struct drm_crtc *crtc, struct drm_display_mod
 {
        struct drm_device *dev = crtc->dev;
        struct nouveau_drm *drm = nouveau_drm(dev);
-       struct nouveau_bios *bios = nvkm_bios(&drm->device);
-       struct nouveau_clock *clk = nvkm_clock(&drm->device);
+       struct nvkm_bios *bios = nvxx_bios(&drm->device);
+       struct nvkm_clk *clk = nvxx_clk(&drm->device);
        struct nouveau_crtc *nv_crtc = nouveau_crtc(crtc);
        struct nv04_mode_state *state = &nv04_display(dev)->mode_reg;
        struct nv04_crtc_reg *regp = &state->crtc_reg[nv_crtc->index];
-       struct nouveau_pll_vals *pv = &regp->pllvals;
+       struct nvkm_pll_vals *pv = &regp->pllvals;
        struct nvbios_pll pll_lim;
 
        if (nvbios_pll_parse(bios, nv_crtc->index ? PLL_VPLL1 : PLL_VPLL0,
index 2d8056cde9968d88ecbc5fca7832c3c354855d15..d7b495a5f30cff0100a8343ea18e7e8ea0ec404a 100644 (file)
@@ -66,7 +66,7 @@ int nv04_dac_output_offset(struct drm_encoder *encoder)
 static int sample_load_twice(struct drm_device *dev, bool sense[2])
 {
        struct nvif_device *device = &nouveau_drm(dev)->device;
-       struct nouveau_timer *ptimer = nvkm_timer(device);
+       struct nvkm_timer *ptimer = nvxx_timer(device);
        int i;
 
        for (i = 0; i < 2; i++) {
@@ -80,17 +80,17 @@ static int sample_load_twice(struct drm_device *dev, bool sense[2])
                 * use a 10ms timeout (guards against crtc being inactive, in
                 * which case blank state would never change)
                 */
-               if (!nouveau_timer_wait_eq(ptimer, 10000000,
-                                          NV_PRMCIO_INP0__COLOR,
-                                          0x00000001, 0x00000000))
+               if (!nvkm_timer_wait_eq(ptimer, 10000000,
+                                       NV_PRMCIO_INP0__COLOR,
+                                       0x00000001, 0x00000000))
                        return -EBUSY;
-               if (!nouveau_timer_wait_eq(ptimer, 10000000,
-                                          NV_PRMCIO_INP0__COLOR,
-                                          0x00000001, 0x00000001))
+               if (!nvkm_timer_wait_eq(ptimer, 10000000,
+                                       NV_PRMCIO_INP0__COLOR,
+                                       0x00000001, 0x00000001))
                        return -EBUSY;
-               if (!nouveau_timer_wait_eq(ptimer, 10000000,
-                                          NV_PRMCIO_INP0__COLOR,
-                                          0x00000001, 0x00000000))
+               if (!nvkm_timer_wait_eq(ptimer, 10000000,
+                                       NV_PRMCIO_INP0__COLOR,
+                                       0x00000001, 0x00000000))
                        return -EBUSY;
 
                udelay(100);
@@ -232,7 +232,7 @@ uint32_t nv17_dac_sample_load(struct drm_encoder *encoder)
        struct drm_device *dev = encoder->dev;
        struct nouveau_drm *drm = nouveau_drm(dev);
        struct nvif_device *device = &nouveau_drm(dev)->device;
-       struct nouveau_gpio *gpio = nvkm_gpio(device);
+       struct nvkm_gpio *gpio = nvxx_gpio(device);
        struct dcb_output *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,
index 42a5435259f7ae1b8939ab569078966def1d24e9..f6ca343fd34a9b2db0f51258ef1c0d99b576ab0e 100644 (file)
@@ -623,9 +623,9 @@ static void nv04_tmds_slave_init(struct drm_encoder *encoder)
        struct drm_device *dev = encoder->dev;
        struct dcb_output *dcb = nouveau_encoder(encoder)->dcb;
        struct nouveau_drm *drm = nouveau_drm(dev);
-       struct nouveau_i2c *i2c = nvkm_i2c(&drm->device);
-       struct nouveau_i2c_port *port = i2c->find(i2c, 2);
-       struct nouveau_i2c_board_info info[] = {
+       struct nvkm_i2c *i2c = nvxx_i2c(&drm->device);
+       struct nvkm_i2c_port *port = i2c->find(i2c, 2);
+       struct nvkm_i2c_board_info info[] = {
                {
                    {
                        .type = "sil164",
index 3d0afa1c6cff15eb487029f0170213846f806acb..f96237ef2a6b336dfc15da387c8059d8c751d31a 100644 (file)
 #include "nouveau_encoder.h"
 #include "nouveau_connector.h"
 
-int
-nv04_display_early_init(struct drm_device *dev)
-{
-       /* ensure vblank interrupts are off, they can't be enabled until
-        * drm_vblank has been initialised
-        */
-       NVWriteCRTC(dev, 0, NV_PCRTC_INTR_EN_0, 0);
-       if (nv_two_heads(dev))
-               NVWriteCRTC(dev, 1, NV_PCRTC_INTR_EN_0, 0);
-
-       return 0;
-}
-
-void
-nv04_display_late_takedown(struct drm_device *dev)
-{
-}
-
 int
 nv04_display_create(struct drm_device *dev)
 {
        struct nouveau_drm *drm = nouveau_drm(dev);
-       struct nouveau_i2c *i2c = nvkm_i2c(&drm->device);
+       struct nvkm_i2c *i2c = nvxx_i2c(&drm->device);
        struct dcb_table *dcb = &drm->vbios.dcb;
        struct drm_connector *connector, *ct;
        struct drm_encoder *encoder;
index 17b899d9aba3c9978a15ca664de1c5f4a5c7884f..c910c5d5c662f266b9cf25a9616786a98d4c09ac 100644 (file)
@@ -36,7 +36,7 @@ struct nv04_crtc_reg {
 
        /* PRAMDAC regs */
        uint32_t nv10_cursync;
-       struct nouveau_pll_vals pllvals;
+       struct nvkm_pll_vals pllvals;
        uint32_t ramdac_gen_ctrl;
        uint32_t ramdac_630;
        uint32_t ramdac_634;
@@ -90,8 +90,6 @@ nv04_display(struct drm_device *dev)
 }
 
 /* nv04_display.c */
-int nv04_display_early_init(struct drm_device *);
-void nv04_display_late_takedown(struct drm_device *);
 int nv04_display_create(struct drm_device *);
 void nv04_display_destroy(struct drm_device *);
 int nv04_display_init(struct drm_device *);
@@ -172,7 +170,7 @@ nouveau_bios_run_init_table(struct drm_device *dev, u16 table,
                            struct dcb_output *outp, int crtc)
 {
        struct nouveau_drm *drm = nouveau_drm(dev);
-       struct nouveau_bios *bios = nvkm_bios(&drm->device);
+       struct nvkm_bios *bios = nvxx_bios(&drm->device);
        struct nvbios_init init = {
                .subdev = nv_subdev(bios),
                .bios = bios,
index 3d4c1930076882c5280ee81f573ea11e624a95f7..42e07afc4c2b21841a5287024569e36d00ada17f 100644 (file)
@@ -130,7 +130,7 @@ NVBlankScreen(struct drm_device *dev, int head, bool blank)
 
 static void
 nouveau_hw_decode_pll(struct drm_device *dev, uint32_t reg1, uint32_t pll1,
-                     uint32_t pll2, struct nouveau_pll_vals *pllvals)
+                     uint32_t pll2, struct nvkm_pll_vals *pllvals)
 {
        struct nouveau_drm *drm = nouveau_drm(dev);
 
@@ -162,11 +162,11 @@ nouveau_hw_decode_pll(struct drm_device *dev, uint32_t reg1, uint32_t pll1,
 
 int
 nouveau_hw_get_pllvals(struct drm_device *dev, enum nvbios_pll_type plltype,
-                      struct nouveau_pll_vals *pllvals)
+                      struct nvkm_pll_vals *pllvals)
 {
        struct nouveau_drm *drm = nouveau_drm(dev);
        struct nvif_device *device = &drm->device;
-       struct nouveau_bios *bios = nvkm_bios(device);
+       struct nvkm_bios *bios = nvxx_bios(device);
        uint32_t reg1, pll1, pll2 = 0;
        struct nvbios_pll pll_lim;
        int ret;
@@ -202,7 +202,7 @@ nouveau_hw_get_pllvals(struct drm_device *dev, enum nvbios_pll_type plltype,
 }
 
 int
-nouveau_hw_pllvals_to_clk(struct nouveau_pll_vals *pv)
+nouveau_hw_pllvals_to_clk(struct nvkm_pll_vals *pv)
 {
        /* Avoid divide by zero if called at an inappropriate time */
        if (!pv->M1 || !pv->M2)
@@ -214,7 +214,7 @@ nouveau_hw_pllvals_to_clk(struct nouveau_pll_vals *pv)
 int
 nouveau_hw_get_clock(struct drm_device *dev, enum nvbios_pll_type plltype)
 {
-       struct nouveau_pll_vals pllvals;
+       struct nvkm_pll_vals pllvals;
        int ret;
 
        if (plltype == PLL_MEMORY &&
@@ -253,10 +253,10 @@ nouveau_hw_fix_bad_vpll(struct drm_device *dev, int head)
 
        struct nouveau_drm *drm = nouveau_drm(dev);
        struct nvif_device *device = &drm->device;
-       struct nouveau_clock *clk = nvkm_clock(device);
-       struct nouveau_bios *bios = nvkm_bios(device);
+       struct nvkm_clk *clk = nvxx_clk(device);
+       struct nvkm_bios *bios = nvxx_bios(device);
        struct nvbios_pll pll_lim;
-       struct nouveau_pll_vals pv;
+       struct nvkm_pll_vals pv;
        enum nvbios_pll_type pll = head ? PLL_VPLL1 : PLL_VPLL0;
 
        if (nvbios_pll_parse(bios, pll, &pll_lim))
@@ -463,7 +463,7 @@ nv_load_state_ramdac(struct drm_device *dev, int head,
                     struct nv04_mode_state *state)
 {
        struct nouveau_drm *drm = nouveau_drm(dev);
-       struct nouveau_clock *clk = nvkm_clock(&drm->device);
+       struct nvkm_clk *clk = nvxx_clk(&drm->device);
        struct nv04_crtc_reg *regp = &state->crtc_reg[head];
        uint32_t pllreg = head ? NV_RAMDAC_VPLL2 : NV_PRAMDAC_VPLL_COEFF;
        int i;
@@ -661,7 +661,7 @@ nv_load_state_ext(struct drm_device *dev, int head,
 {
        struct nouveau_drm *drm = nouveau_drm(dev);
        struct nvif_device *device = &drm->device;
-       struct nouveau_timer *ptimer = nvkm_timer(device);
+       struct nvkm_timer *ptimer = nvxx_timer(device);
        struct nv04_crtc_reg *regp = &state->crtc_reg[head];
        uint32_t reg900;
        int i;
@@ -741,8 +741,8 @@ nv_load_state_ext(struct drm_device *dev, int head,
                if (drm->device.info.family < NV_DEVICE_INFO_V0_KELVIN) {
                        /* Not waiting for vertical retrace before modifying
                           CRE_53/CRE_54 causes lockups. */
-                       nouveau_timer_wait_eq(ptimer, 650000000, NV_PRMCIO_INP0__COLOR, 0x8, 0x8);
-                       nouveau_timer_wait_eq(ptimer, 650000000, NV_PRMCIO_INP0__COLOR, 0x8, 0x0);
+                       nvkm_timer_wait_eq(ptimer, 650000000, NV_PRMCIO_INP0__COLOR, 0x8, 0x8);
+                       nvkm_timer_wait_eq(ptimer, 650000000, NV_PRMCIO_INP0__COLOR, 0x8, 0x0);
                }
 
                wr_cio_state(dev, head, regp, NV_CIO_CRE_42);
index 7f53c571f31fba18c0606915de89f69139cebe4e..6c796178bf0cf1360f2857fc7abb9a07cb73fadd 100644 (file)
@@ -42,8 +42,8 @@ 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);
 int nouveau_hw_get_pllvals(struct drm_device *, enum nvbios_pll_type plltype,
-                          struct nouveau_pll_vals *pllvals);
-int nouveau_hw_pllvals_to_clk(struct nouveau_pll_vals *pllvals);
+                          struct nvkm_pll_vals *pllvals);
+int nouveau_hw_pllvals_to_clk(struct nvkm_pll_vals *pllvals);
 int nouveau_hw_get_clock(struct drm_device *, enum nvbios_pll_type plltype);
 void nouveau_hw_save_vga_fonts(struct drm_device *, bool save);
 void nouveau_hw_save_state(struct drm_device *, int head,
index 8061d8d0ce79aa8223dd7d67d67cf2619d8c4ab6..d9664b37def17f01247fcbe676d7aec69f34e794 100644 (file)
@@ -35,7 +35,7 @@
 
 #include <drm/i2c/ch7006.h>
 
-static struct nouveau_i2c_board_info nv04_tv_encoder_info[] = {
+static struct nvkm_i2c_board_info nv04_tv_encoder_info[] = {
        {
                {
                        I2C_BOARD_INFO("ch7006", 0x75),
@@ -54,7 +54,7 @@ static struct nouveau_i2c_board_info nv04_tv_encoder_info[] = {
 int nv04_tv_identify(struct drm_device *dev, int i2c_index)
 {
        struct nouveau_drm *drm = nouveau_drm(dev);
-       struct nouveau_i2c *i2c = nvkm_i2c(&drm->device);
+       struct nvkm_i2c *i2c = nvxx_i2c(&drm->device);
 
        return i2c->identify(i2c, i2c_index, "TV encoder",
                             nv04_tv_encoder_info, NULL, NULL);
@@ -204,8 +204,8 @@ nv04_tv_create(struct drm_connector *connector, struct dcb_output *entry)
        struct drm_encoder *encoder;
        struct drm_device *dev = connector->dev;
        struct nouveau_drm *drm = nouveau_drm(dev);
-       struct nouveau_i2c *i2c = nvkm_i2c(&drm->device);
-       struct nouveau_i2c_port *port = i2c->find(i2c, entry->i2c_index);
+       struct nvkm_i2c *i2c = nvxx_i2c(&drm->device);
+       struct nvkm_i2c_port *port = i2c->find(i2c, entry->i2c_index);
        int type, ret;
 
        /* Ensure that we can talk to this encoder */
index 72d2ab04db4718457d9cdd975ab63ddc4d9436ab..731d74efc1e5714badb1ca2baaf9ff2cf67e1c7f 100644 (file)
@@ -46,7 +46,7 @@ static uint32_t nv42_tv_sample_load(struct drm_encoder *encoder)
 {
        struct drm_device *dev = encoder->dev;
        struct nouveau_drm *drm = nouveau_drm(dev);
-       struct nouveau_gpio *gpio = nvkm_gpio(&drm->device);
+       struct nvkm_gpio *gpio = nvxx_gpio(&drm->device);
        uint32_t testval, regoffset = nv04_dac_output_offset(encoder);
        uint32_t gpio0, gpio1, fp_htotal, fp_hsync_start, fp_hsync_end,
                fp_control, test_ctrl, dacclk, ctv_14, ctv_1c, ctv_6c;
@@ -133,14 +133,14 @@ get_tv_detect_quirks(struct drm_device *dev, uint32_t *pin_mask)
        struct nvif_device *device = &drm->device;
 
        /* Zotac FX5200 */
-       if (nv_device_match(nvkm_object(device), 0x0322, 0x19da, 0x1035) ||
-           nv_device_match(nvkm_object(device), 0x0322, 0x19da, 0x2035)) {
+       if (nv_device_match(nvxx_object(device), 0x0322, 0x19da, 0x1035) ||
+           nv_device_match(nvxx_object(device), 0x0322, 0x19da, 0x2035)) {
                *pin_mask = 0xc;
                return false;
        }
 
        /* MSI nForce2 IGP */
-       if (nv_device_match(nvkm_object(device), 0x01f0, 0x1462, 0x5710)) {
+       if (nv_device_match(nvxx_object(device), 0x01f0, 0x1462, 0x5710)) {
                *pin_mask = 0xc;
                return false;
        }
@@ -370,7 +370,7 @@ static void  nv17_tv_dpms(struct drm_encoder *encoder, int mode)
 {
        struct drm_device *dev = encoder->dev;
        struct nouveau_drm *drm = nouveau_drm(dev);
-       struct nouveau_gpio *gpio = nvkm_gpio(&drm->device);
+       struct nvkm_gpio *gpio = nvxx_gpio(&drm->device);
        struct nv17_tv_state *regs = &to_tv_enc(encoder)->state;
        struct nv17_tv_norm_params *tv_norm = get_tv_norm(encoder);
 
diff --git a/drivers/gpu/drm/nouveau/include/nvif/class.h b/drivers/gpu/drm/nouveau/include/nvif/class.h
new file mode 100644 (file)
index 0000000..5ad17fc
--- /dev/null
@@ -0,0 +1,573 @@
+#ifndef __NVIF_CLASS_H__
+#define __NVIF_CLASS_H__
+
+/*******************************************************************************
+ * class identifiers
+ ******************************************************************************/
+
+/* the below match nvidia-assigned (either in hw, or sw) class numbers */
+#define NV_DEVICE                                                    0x00000080
+
+#define NV_DMA_FROM_MEMORY                                           0x00000002
+#define NV_DMA_TO_MEMORY                                             0x00000003
+#define NV_DMA_IN_MEMORY                                             0x0000003d
+
+#define NV04_DISP                                                    0x00000046
+
+#define NV03_CHANNEL_DMA                                             0x0000006b
+#define NV10_CHANNEL_DMA                                             0x0000006e
+#define NV17_CHANNEL_DMA                                             0x0000176e
+#define NV40_CHANNEL_DMA                                             0x0000406e
+#define NV50_CHANNEL_DMA                                             0x0000506e
+#define G82_CHANNEL_DMA                                              0x0000826e
+
+#define NV50_CHANNEL_GPFIFO                                          0x0000506f
+#define G82_CHANNEL_GPFIFO                                           0x0000826f
+#define FERMI_CHANNEL_GPFIFO                                         0x0000906f
+#define KEPLER_CHANNEL_GPFIFO_A                                      0x0000a06f
+
+#define NV50_DISP                                                    0x00005070
+#define G82_DISP                                                     0x00008270
+#define GT200_DISP                                                   0x00008370
+#define GT214_DISP                                                   0x00008570
+#define GT206_DISP                                                   0x00008870
+#define GF110_DISP                                                   0x00009070
+#define GK104_DISP                                                   0x00009170
+#define GK110_DISP                                                   0x00009270
+#define GM107_DISP                                                   0x00009470
+#define GM204_DISP                                                   0x00009570
+
+#define NV50_DISP_CURSOR                                             0x0000507a
+#define G82_DISP_CURSOR                                              0x0000827a
+#define GT214_DISP_CURSOR                                            0x0000857a
+#define GF110_DISP_CURSOR                                            0x0000907a
+#define GK104_DISP_CURSOR                                            0x0000917a
+
+#define NV50_DISP_OVERLAY                                            0x0000507b
+#define G82_DISP_OVERLAY                                             0x0000827b
+#define GT214_DISP_OVERLAY                                           0x0000857b
+#define GF110_DISP_OVERLAY                                           0x0000907b
+#define GK104_DISP_OVERLAY                                           0x0000917b
+
+#define NV50_DISP_BASE_CHANNEL_DMA                                   0x0000507c
+#define G82_DISP_BASE_CHANNEL_DMA                                    0x0000827c
+#define GT200_DISP_BASE_CHANNEL_DMA                                  0x0000837c
+#define GT214_DISP_BASE_CHANNEL_DMA                                  0x0000857c
+#define GF110_DISP_BASE_CHANNEL_DMA                                  0x0000907c
+#define GK104_DISP_BASE_CHANNEL_DMA                                  0x0000917c
+#define GK110_DISP_BASE_CHANNEL_DMA                                  0x0000927c
+
+#define NV50_DISP_CORE_CHANNEL_DMA                                   0x0000507d
+#define G82_DISP_CORE_CHANNEL_DMA                                    0x0000827d
+#define GT200_DISP_CORE_CHANNEL_DMA                                  0x0000837d
+#define GT214_DISP_CORE_CHANNEL_DMA                                  0x0000857d
+#define GT206_DISP_CORE_CHANNEL_DMA                                  0x0000887d
+#define GF110_DISP_CORE_CHANNEL_DMA                                  0x0000907d
+#define GK104_DISP_CORE_CHANNEL_DMA                                  0x0000917d
+#define GK110_DISP_CORE_CHANNEL_DMA                                  0x0000927d
+#define GM107_DISP_CORE_CHANNEL_DMA                                  0x0000947d
+#define GM204_DISP_CORE_CHANNEL_DMA                                  0x0000957d
+
+#define NV50_DISP_OVERLAY_CHANNEL_DMA                                0x0000507e
+#define G82_DISP_OVERLAY_CHANNEL_DMA                                 0x0000827e
+#define GT200_DISP_OVERLAY_CHANNEL_DMA                               0x0000837e
+#define GT214_DISP_OVERLAY_CHANNEL_DMA                               0x0000857e
+#define GF110_DISP_OVERLAY_CONTROL_DMA                               0x0000907e
+#define GK104_DISP_OVERLAY_CONTROL_DMA                               0x0000917e
+
+#define FERMI_A                                                      0x00009097
+#define FERMI_B                                                      0x00009197
+#define FERMI_C                                                      0x00009297
+
+#define KEPLER_A                                                     0x0000a097
+#define KEPLER_B                                                     0x0000a197
+#define KEPLER_C                                                     0x0000a297
+
+#define MAXWELL_A                                                    0x0000b097
+
+#define FERMI_COMPUTE_A                                              0x000090c0
+#define FERMI_COMPUTE_B                                              0x000091c0
+
+#define KEPLER_COMPUTE_A                                             0x0000a0c0
+#define KEPLER_COMPUTE_B                                             0x0000a1c0
+
+#define MAXWELL_COMPUTE_A                                            0x0000b0c0
+
+
+/*******************************************************************************
+ * client
+ ******************************************************************************/
+
+#define NV_CLIENT_DEVLIST                                                  0x00
+
+struct nv_client_devlist_v0 {
+       __u8  version;
+       __u8  count;
+       __u8  pad02[6];
+       __u64 device[];
+};
+
+
+/*******************************************************************************
+ * device
+ ******************************************************************************/
+
+struct nv_device_v0 {
+       __u8  version;
+       __u8  pad01[7];
+       __u64 device;   /* device identifier, ~0 for client default */
+#define NV_DEVICE_V0_DISABLE_IDENTIFY                     0x0000000000000001ULL
+#define NV_DEVICE_V0_DISABLE_MMIO                         0x0000000000000002ULL
+#define NV_DEVICE_V0_DISABLE_VBIOS                        0x0000000000000004ULL
+#define NV_DEVICE_V0_DISABLE_CORE                         0x0000000000000008ULL
+#define NV_DEVICE_V0_DISABLE_DISP                         0x0000000000010000ULL
+#define NV_DEVICE_V0_DISABLE_FIFO                         0x0000000000020000ULL
+#define NV_DEVICE_V0_DISABLE_GR                           0x0000000100000000ULL
+#define NV_DEVICE_V0_DISABLE_MPEG                         0x0000000200000000ULL
+#define NV_DEVICE_V0_DISABLE_ME                           0x0000000400000000ULL
+#define NV_DEVICE_V0_DISABLE_VP                           0x0000000800000000ULL
+#define NV_DEVICE_V0_DISABLE_CIPHER                       0x0000001000000000ULL
+#define NV_DEVICE_V0_DISABLE_BSP                          0x0000002000000000ULL
+#define NV_DEVICE_V0_DISABLE_MSPPP                        0x0000004000000000ULL
+#define NV_DEVICE_V0_DISABLE_CE0                          0x0000008000000000ULL
+#define NV_DEVICE_V0_DISABLE_CE1                          0x0000010000000000ULL
+#define NV_DEVICE_V0_DISABLE_VIC                          0x0000020000000000ULL
+#define NV_DEVICE_V0_DISABLE_MSENC                        0x0000040000000000ULL
+#define NV_DEVICE_V0_DISABLE_CE2                          0x0000080000000000ULL
+#define NV_DEVICE_V0_DISABLE_MSVLD                        0x0000100000000000ULL
+#define NV_DEVICE_V0_DISABLE_SEC                          0x0000200000000000ULL
+#define NV_DEVICE_V0_DISABLE_MSPDEC                       0x0000400000000000ULL
+       __u64 disable;  /* disable particular subsystems */
+       __u64 debug0;   /* as above, but *internal* ids, and *NOT* ABI */
+};
+
+#define NV_DEVICE_V0_INFO                                                  0x00
+
+struct nv_device_info_v0 {
+       __u8  version;
+#define NV_DEVICE_INFO_V0_IGP                                              0x00
+#define NV_DEVICE_INFO_V0_PCI                                              0x01
+#define NV_DEVICE_INFO_V0_AGP                                              0x02
+#define NV_DEVICE_INFO_V0_PCIE                                             0x03
+#define NV_DEVICE_INFO_V0_SOC                                              0x04
+       __u8  platform;
+       __u16 chipset;  /* from NV_PMC_BOOT_0 */
+       __u8  revision; /* from NV_PMC_BOOT_0 */
+#define NV_DEVICE_INFO_V0_TNT                                              0x01
+#define NV_DEVICE_INFO_V0_CELSIUS                                          0x02
+#define NV_DEVICE_INFO_V0_KELVIN                                           0x03
+#define NV_DEVICE_INFO_V0_RANKINE                                          0x04
+#define NV_DEVICE_INFO_V0_CURIE                                            0x05
+#define NV_DEVICE_INFO_V0_TESLA                                            0x06
+#define NV_DEVICE_INFO_V0_FERMI                                            0x07
+#define NV_DEVICE_INFO_V0_KEPLER                                           0x08
+#define NV_DEVICE_INFO_V0_MAXWELL                                          0x09
+       __u8  family;
+       __u8  pad06[2];
+       __u64 ram_size;
+       __u64 ram_user;
+};
+
+
+/*******************************************************************************
+ * context dma
+ ******************************************************************************/
+
+struct nv_dma_v0 {
+       __u8  version;
+#define NV_DMA_V0_TARGET_VM                                                0x00
+#define NV_DMA_V0_TARGET_VRAM                                              0x01
+#define NV_DMA_V0_TARGET_PCI                                               0x02
+#define NV_DMA_V0_TARGET_PCI_US                                            0x03
+#define NV_DMA_V0_TARGET_AGP                                               0x04
+       __u8  target;
+#define NV_DMA_V0_ACCESS_VM                                                0x00
+#define NV_DMA_V0_ACCESS_RD                                                0x01
+#define NV_DMA_V0_ACCESS_WR                                                0x02
+#define NV_DMA_V0_ACCESS_RDWR                 (NV_DMA_V0_ACCESS_RD | NV_DMA_V0_ACCESS_WR)
+       __u8  access;
+       __u8  pad03[5];
+       __u64 start;
+       __u64 limit;
+       /* ... chipset-specific class data */
+};
+
+struct nv50_dma_v0 {
+       __u8  version;
+#define NV50_DMA_V0_PRIV_VM                                                0x00
+#define NV50_DMA_V0_PRIV_US                                                0x01
+#define NV50_DMA_V0_PRIV__S                                                0x02
+       __u8  priv;
+#define NV50_DMA_V0_PART_VM                                                0x00
+#define NV50_DMA_V0_PART_256                                               0x01
+#define NV50_DMA_V0_PART_1KB                                               0x02
+       __u8  part;
+#define NV50_DMA_V0_COMP_NONE                                              0x00
+#define NV50_DMA_V0_COMP_1                                                 0x01
+#define NV50_DMA_V0_COMP_2                                                 0x02
+#define NV50_DMA_V0_COMP_VM                                                0x03
+       __u8  comp;
+#define NV50_DMA_V0_KIND_PITCH                                             0x00
+#define NV50_DMA_V0_KIND_VM                                                0x7f
+       __u8  kind;
+       __u8  pad05[3];
+};
+
+struct gf100_dma_v0 {
+       __u8  version;
+#define GF100_DMA_V0_PRIV_VM                                               0x00
+#define GF100_DMA_V0_PRIV_US                                               0x01
+#define GF100_DMA_V0_PRIV__S                                               0x02
+       __u8  priv;
+#define GF100_DMA_V0_KIND_PITCH                                            0x00
+#define GF100_DMA_V0_KIND_VM                                               0xff
+       __u8  kind;
+       __u8  pad03[5];
+};
+
+struct gf110_dma_v0 {
+       __u8  version;
+#define GF110_DMA_V0_PAGE_LP                                               0x00
+#define GF110_DMA_V0_PAGE_SP                                               0x01
+       __u8  page;
+#define GF110_DMA_V0_KIND_PITCH                                            0x00
+#define GF110_DMA_V0_KIND_VM                                               0xff
+       __u8  kind;
+       __u8  pad03[5];
+};
+
+
+/*******************************************************************************
+ * perfmon
+ ******************************************************************************/
+
+struct nvif_perfctr_v0 {
+       __u8  version;
+       __u8  pad01[1];
+       __u16 logic_op;
+       __u8  pad04[4];
+       char  name[4][64];
+};
+
+#define NVIF_PERFCTR_V0_QUERY                                              0x00
+#define NVIF_PERFCTR_V0_SAMPLE                                             0x01
+#define NVIF_PERFCTR_V0_READ                                               0x02
+
+struct nvif_perfctr_query_v0 {
+       __u8  version;
+       __u8  pad01[3];
+       __u32 iter;
+       char  name[64];
+};
+
+struct nvif_perfctr_sample {
+};
+
+struct nvif_perfctr_read_v0 {
+       __u8  version;
+       __u8  pad01[7];
+       __u32 ctr;
+       __u32 clk;
+};
+
+
+/*******************************************************************************
+ * device control
+ ******************************************************************************/
+
+#define NVIF_CONTROL_PSTATE_INFO                                           0x00
+#define NVIF_CONTROL_PSTATE_ATTR                                           0x01
+#define NVIF_CONTROL_PSTATE_USER                                           0x02
+
+struct nvif_control_pstate_info_v0 {
+       __u8  version;
+       __u8  count; /* out: number of power states */
+#define NVIF_CONTROL_PSTATE_INFO_V0_USTATE_DISABLE                         (-1)
+#define NVIF_CONTROL_PSTATE_INFO_V0_USTATE_PERFMON                         (-2)
+       __s8  ustate_ac; /* out: target pstate index */
+       __s8  ustate_dc; /* out: target pstate index */
+       __s8  pwrsrc; /* out: current power source */
+#define NVIF_CONTROL_PSTATE_INFO_V0_PSTATE_UNKNOWN                         (-1)
+#define NVIF_CONTROL_PSTATE_INFO_V0_PSTATE_PERFMON                         (-2)
+       __s8  pstate; /* out: current pstate index */
+       __u8  pad06[2];
+};
+
+struct nvif_control_pstate_attr_v0 {
+       __u8  version;
+#define NVIF_CONTROL_PSTATE_ATTR_V0_STATE_CURRENT                          (-1)
+       __s8  state; /*  in: index of pstate to query
+                     * out: pstate identifier
+                     */
+       __u8  index; /*  in: index of attribute to query
+                     * out: index of next attribute, or 0 if no more
+                     */
+       __u8  pad03[5];
+       __u32 min;
+       __u32 max;
+       char  name[32];
+       char  unit[16];
+};
+
+struct nvif_control_pstate_user_v0 {
+       __u8  version;
+#define NVIF_CONTROL_PSTATE_USER_V0_STATE_UNKNOWN                          (-1)
+#define NVIF_CONTROL_PSTATE_USER_V0_STATE_PERFMON                          (-2)
+       __s8  ustate; /*  in: pstate identifier */
+       __s8  pwrsrc; /*  in: target power source */
+       __u8  pad03[5];
+};
+
+
+/*******************************************************************************
+ * DMA FIFO channels
+ ******************************************************************************/
+
+struct nv03_channel_dma_v0 {
+       __u8  version;
+       __u8  chid;
+       __u8  pad02[2];
+       __u32 pushbuf;
+       __u64 offset;
+};
+
+#define G82_CHANNEL_DMA_V0_NTFY_UEVENT                                     0x00
+
+/*******************************************************************************
+ * GPFIFO channels
+ ******************************************************************************/
+
+struct nv50_channel_gpfifo_v0 {
+       __u8  version;
+       __u8  chid;
+       __u8  pad01[6];
+       __u32 pushbuf;
+       __u32 ilength;
+       __u64 ioffset;
+};
+
+struct kepler_channel_gpfifo_a_v0 {
+       __u8  version;
+#define KEPLER_CHANNEL_GPFIFO_A_V0_ENGINE_GR                               0x01
+#define KEPLER_CHANNEL_GPFIFO_A_V0_ENGINE_MSPDEC                           0x02
+#define KEPLER_CHANNEL_GPFIFO_A_V0_ENGINE_MSPPP                            0x04
+#define KEPLER_CHANNEL_GPFIFO_A_V0_ENGINE_MSVLD                            0x08
+#define KEPLER_CHANNEL_GPFIFO_A_V0_ENGINE_CE0                              0x10
+#define KEPLER_CHANNEL_GPFIFO_A_V0_ENGINE_CE1                              0x20
+#define KEPLER_CHANNEL_GPFIFO_A_V0_ENGINE_ENC                              0x40
+       __u8  engine;
+       __u16 chid;
+       __u8  pad04[4];
+       __u32 pushbuf;
+       __u32 ilength;
+       __u64 ioffset;
+};
+
+/*******************************************************************************
+ * legacy display
+ ******************************************************************************/
+
+#define NV04_DISP_NTFY_VBLANK                                              0x00
+#define NV04_DISP_NTFY_CONN                                                0x01
+
+struct nv04_disp_mthd_v0 {
+       __u8  version;
+#define NV04_DISP_SCANOUTPOS                                               0x00
+       __u8  method;
+       __u8  head;
+       __u8  pad03[5];
+};
+
+struct nv04_disp_scanoutpos_v0 {
+       __u8  version;
+       __u8  pad01[7];
+       __s64 time[2];
+       __u16 vblanks;
+       __u16 vblanke;
+       __u16 vtotal;
+       __u16 vline;
+       __u16 hblanks;
+       __u16 hblanke;
+       __u16 htotal;
+       __u16 hline;
+};
+
+/*******************************************************************************
+ * display
+ ******************************************************************************/
+
+#define NV50_DISP_MTHD                                                     0x00
+
+struct nv50_disp_mthd_v0 {
+       __u8  version;
+#define NV50_DISP_SCANOUTPOS                                               0x00
+       __u8  method;
+       __u8  head;
+       __u8  pad03[5];
+};
+
+struct nv50_disp_mthd_v1 {
+       __u8  version;
+#define NV50_DISP_MTHD_V1_DAC_PWR                                          0x10
+#define NV50_DISP_MTHD_V1_DAC_LOAD                                         0x11
+#define NV50_DISP_MTHD_V1_SOR_PWR                                          0x20
+#define NV50_DISP_MTHD_V1_SOR_HDA_ELD                                      0x21
+#define NV50_DISP_MTHD_V1_SOR_HDMI_PWR                                     0x22
+#define NV50_DISP_MTHD_V1_SOR_LVDS_SCRIPT                                  0x23
+#define NV50_DISP_MTHD_V1_SOR_DP_PWR                                       0x24
+#define NV50_DISP_MTHD_V1_PIOR_PWR                                         0x30
+       __u8  method;
+       __u16 hasht;
+       __u16 hashm;
+       __u8  pad06[2];
+};
+
+struct nv50_disp_dac_pwr_v0 {
+       __u8  version;
+       __u8  state;
+       __u8  data;
+       __u8  vsync;
+       __u8  hsync;
+       __u8  pad05[3];
+};
+
+struct nv50_disp_dac_load_v0 {
+       __u8  version;
+       __u8  load;
+       __u8  pad02[2];
+       __u32 data;
+};
+
+struct nv50_disp_sor_pwr_v0 {
+       __u8  version;
+       __u8  state;
+       __u8  pad02[6];
+};
+
+struct nv50_disp_sor_hda_eld_v0 {
+       __u8  version;
+       __u8  pad01[7];
+       __u8  data[];
+};
+
+struct nv50_disp_sor_hdmi_pwr_v0 {
+       __u8  version;
+       __u8  state;
+       __u8  max_ac_packet;
+       __u8  rekey;
+       __u8  pad04[4];
+};
+
+struct nv50_disp_sor_lvds_script_v0 {
+       __u8  version;
+       __u8  pad01[1];
+       __u16 script;
+       __u8  pad04[4];
+};
+
+struct nv50_disp_sor_dp_pwr_v0 {
+       __u8  version;
+       __u8  state;
+       __u8  pad02[6];
+};
+
+struct nv50_disp_pior_pwr_v0 {
+       __u8  version;
+       __u8  state;
+       __u8  type;
+       __u8  pad03[5];
+};
+
+/* core */
+struct nv50_disp_core_channel_dma_v0 {
+       __u8  version;
+       __u8  pad01[3];
+       __u32 pushbuf;
+};
+
+#define NV50_DISP_CORE_CHANNEL_DMA_V0_NTFY_UEVENT                          0x00
+
+/* cursor immediate */
+struct nv50_disp_cursor_v0 {
+       __u8  version;
+       __u8  head;
+       __u8  pad02[6];
+};
+
+#define NV50_DISP_CURSOR_V0_NTFY_UEVENT                                    0x00
+
+/* base */
+struct nv50_disp_base_channel_dma_v0 {
+       __u8  version;
+       __u8  pad01[2];
+       __u8  head;
+       __u32 pushbuf;
+};
+
+#define NV50_DISP_BASE_CHANNEL_DMA_V0_NTFY_UEVENT                          0x00
+
+/* overlay */
+struct nv50_disp_overlay_channel_dma_v0 {
+       __u8  version;
+       __u8  pad01[2];
+       __u8  head;
+       __u32 pushbuf;
+};
+
+#define NV50_DISP_OVERLAY_CHANNEL_DMA_V0_NTFY_UEVENT                       0x00
+
+/* overlay immediate */
+struct nv50_disp_overlay_v0 {
+       __u8  version;
+       __u8  head;
+       __u8  pad02[6];
+};
+
+#define NV50_DISP_OVERLAY_V0_NTFY_UEVENT                                   0x00
+
+/*******************************************************************************
+ * fermi
+ ******************************************************************************/
+
+#define FERMI_A_ZBC_COLOR                                                  0x00
+#define FERMI_A_ZBC_DEPTH                                                  0x01
+
+struct fermi_a_zbc_color_v0 {
+       __u8  version;
+#define FERMI_A_ZBC_COLOR_V0_FMT_ZERO                                      0x01
+#define FERMI_A_ZBC_COLOR_V0_FMT_UNORM_ONE                                 0x02
+#define FERMI_A_ZBC_COLOR_V0_FMT_RF32_GF32_BF32_AF32                       0x04
+#define FERMI_A_ZBC_COLOR_V0_FMT_R16_G16_B16_A16                           0x08
+#define FERMI_A_ZBC_COLOR_V0_FMT_RN16_GN16_BN16_AN16                       0x0c
+#define FERMI_A_ZBC_COLOR_V0_FMT_RS16_GS16_BS16_AS16                       0x10
+#define FERMI_A_ZBC_COLOR_V0_FMT_RU16_GU16_BU16_AU16                       0x14
+#define FERMI_A_ZBC_COLOR_V0_FMT_RF16_GF16_BF16_AF16                       0x16
+#define FERMI_A_ZBC_COLOR_V0_FMT_A8R8G8B8                                  0x18
+#define FERMI_A_ZBC_COLOR_V0_FMT_A8RL8GL8BL8                               0x1c
+#define FERMI_A_ZBC_COLOR_V0_FMT_A2B10G10R10                               0x20
+#define FERMI_A_ZBC_COLOR_V0_FMT_AU2BU10GU10RU10                           0x24
+#define FERMI_A_ZBC_COLOR_V0_FMT_A8B8G8R8                                  0x28
+#define FERMI_A_ZBC_COLOR_V0_FMT_A8BL8GL8RL8                               0x2c
+#define FERMI_A_ZBC_COLOR_V0_FMT_AN8BN8GN8RN8                              0x30
+#define FERMI_A_ZBC_COLOR_V0_FMT_AS8BS8GS8RS8                              0x34
+#define FERMI_A_ZBC_COLOR_V0_FMT_AU8BU8GU8RU8                              0x38
+#define FERMI_A_ZBC_COLOR_V0_FMT_A2R10G10B10                               0x3c
+#define FERMI_A_ZBC_COLOR_V0_FMT_BF10GF11RF11                              0x40
+       __u8  format;
+       __u8  index;
+       __u8  pad03[5];
+       __u32 ds[4];
+       __u32 l2[4];
+};
+
+struct fermi_a_zbc_depth_v0 {
+       __u8  version;
+#define FERMI_A_ZBC_DEPTH_V0_FMT_FP32                                      0x01
+       __u8  format;
+       __u8  index;
+       __u8  pad03[5];
+       __u32 ds;
+       __u32 l2;
+};
+
+#endif
diff --git a/drivers/gpu/drm/nouveau/include/nvif/client.h b/drivers/gpu/drm/nouveau/include/nvif/client.h
new file mode 100644 (file)
index 0000000..eca648e
--- /dev/null
@@ -0,0 +1,39 @@
+#ifndef __NVIF_CLIENT_H__
+#define __NVIF_CLIENT_H__
+
+#include <nvif/object.h>
+
+struct nvif_client {
+       struct nvif_object base;
+       struct nvif_object *object; /*XXX: hack for nvif_object() */
+       const struct nvif_driver *driver;
+       bool super;
+};
+
+static inline struct nvif_client *
+nvif_client(struct nvif_object *object)
+{
+       while (object && object->parent != object)
+               object = object->parent;
+       return (void *)object;
+}
+
+int  nvif_client_init(void (*dtor)(struct nvif_client *), const char *,
+                     const char *, u64, const char *, const char *,
+                     struct nvif_client *);
+void nvif_client_fini(struct nvif_client *);
+int  nvif_client_new(const char *, const char *, u64, const char *,
+                    const char *, struct nvif_client **);
+void nvif_client_ref(struct nvif_client *, struct nvif_client **);
+int  nvif_client_ioctl(struct nvif_client *, void *, u32);
+int  nvif_client_suspend(struct nvif_client *);
+int  nvif_client_resume(struct nvif_client *);
+
+/*XXX*/
+#include <core/client.h>
+#define nvxx_client(a) ({ \
+       struct nvif_client *_client = nvif_client(nvif_object(a)); \
+       nvkm_client(_client->base.priv); \
+})
+
+#endif
diff --git a/drivers/gpu/drm/nouveau/include/nvif/device.h b/drivers/gpu/drm/nouveau/include/nvif/device.h
new file mode 100644 (file)
index 0000000..88553a7
--- /dev/null
@@ -0,0 +1,61 @@
+#ifndef __NVIF_DEVICE_H__
+#define __NVIF_DEVICE_H__
+
+#include <nvif/object.h>
+#include <nvif/class.h>
+
+struct nvif_device {
+       struct nvif_object base;
+       struct nvif_object *object; /*XXX: hack for nvif_object() */
+       struct nv_device_info_v0 info;
+};
+
+static inline struct nvif_device *
+nvif_device(struct nvif_object *object)
+{
+       while (object && object->oclass != 0x0080 /*XXX: NV_DEVICE_CLASS*/ )
+               object = object->parent;
+       return (void *)object;
+}
+
+int  nvif_device_init(struct nvif_object *, void (*dtor)(struct nvif_device *),
+                     u32 handle, u32 oclass, void *, u32,
+                     struct nvif_device *);
+void nvif_device_fini(struct nvif_device *);
+int  nvif_device_new(struct nvif_object *, u32 handle, u32 oclass,
+                    void *, u32, struct nvif_device **);
+void nvif_device_ref(struct nvif_device *, struct nvif_device **);
+
+/*XXX*/
+#include <subdev/bios.h>
+#include <subdev/fb.h>
+#include <subdev/mmu.h>
+#include <subdev/bar.h>
+#include <subdev/gpio.h>
+#include <subdev/clk.h>
+#include <subdev/i2c.h>
+#include <subdev/timer.h>
+#include <subdev/therm.h>
+
+#define nvxx_device(a) nv_device(nvxx_object((a)))
+#define nvxx_bios(a) nvkm_bios(nvxx_device(a))
+#define nvxx_fb(a) nvkm_fb(nvxx_device(a))
+#define nvxx_mmu(a) nvkm_mmu(nvxx_device(a))
+#define nvxx_bar(a) nvkm_bar(nvxx_device(a))
+#define nvxx_gpio(a) nvkm_gpio(nvxx_device(a))
+#define nvxx_clk(a) nvkm_clk(nvxx_device(a))
+#define nvxx_i2c(a) nvkm_i2c(nvxx_device(a))
+#define nvxx_timer(a) nvkm_timer(nvxx_device(a))
+#define nvxx_wait(a,b,c,d) nv_wait(nvxx_timer(a), (b), (c), (d))
+#define nvxx_wait_cb(a,b,c) nv_wait_cb(nvxx_timer(a), (b), (c))
+#define nvxx_therm(a) nvkm_therm(nvxx_device(a))
+
+#include <core/device.h>
+#include <engine/fifo.h>
+#include <engine/gr.h>
+#include <engine/sw.h>
+
+#define nvxx_fifo(a) nvkm_fifo(nvxx_device(a))
+#define nvxx_fifo_chan(a) ((struct nvkm_fifo_chan *)nvxx_object(a))
+#define nvxx_gr(a) ((struct nvkm_gr *)nvkm_engine(nvxx_object(a), NVDEV_ENGINE_GR))
+#endif
diff --git a/drivers/gpu/drm/nouveau/include/nvif/driver.h b/drivers/gpu/drm/nouveau/include/nvif/driver.h
new file mode 100644 (file)
index 0000000..8bd39e6
--- /dev/null
@@ -0,0 +1,22 @@
+#ifndef __NVIF_DRIVER_H__
+#define __NVIF_DRIVER_H__
+
+struct nvif_driver {
+       const char *name;
+       int (*init)(const char *name, u64 device, const char *cfg,
+                   const char *dbg, void **priv);
+       void (*fini)(void *priv);
+       int (*suspend)(void *priv);
+       int (*resume)(void *priv);
+       int (*ioctl)(void *priv, bool super, void *data, u32 size, void **hack);
+       void __iomem *(*map)(void *priv, u64 handle, u32 size);
+       void (*unmap)(void *priv, void __iomem *ptr, u32 size);
+       bool keep;
+};
+
+extern const struct nvif_driver nvif_driver_nvkm;
+extern const struct nvif_driver nvif_driver_drm;
+extern const struct nvif_driver nvif_driver_lib;
+extern const struct nvif_driver nvif_driver_null;
+
+#endif
diff --git a/drivers/gpu/drm/nouveau/include/nvif/event.h b/drivers/gpu/drm/nouveau/include/nvif/event.h
new file mode 100644 (file)
index 0000000..2176449
--- /dev/null
@@ -0,0 +1,62 @@
+#ifndef __NVIF_EVENT_H__
+#define __NVIF_EVENT_H__
+
+struct nvif_notify_req_v0 {
+       __u8  version;
+       __u8  reply;
+       __u8  pad02[5];
+#define NVIF_NOTIFY_V0_ROUTE_NVIF                                          0x00
+       __u8  route;
+       __u64 token;    /* must be unique */
+       __u8  data[];   /* request data (below) */
+};
+
+struct nvif_notify_rep_v0 {
+       __u8  version;
+       __u8  pad01[6];
+       __u8  route;
+       __u64 token;
+       __u8  data[];   /* reply data (below) */
+};
+
+struct nvif_notify_head_req_v0 {
+       /* nvif_notify_req ... */
+       __u8  version;
+       __u8  head;
+       __u8  pad02[6];
+};
+
+struct nvif_notify_head_rep_v0 {
+       /* nvif_notify_rep ... */
+       __u8  version;
+       __u8  pad01[7];
+};
+
+struct nvif_notify_conn_req_v0 {
+       /* nvif_notify_req ... */
+       __u8  version;
+#define NVIF_NOTIFY_CONN_V0_PLUG                                           0x01
+#define NVIF_NOTIFY_CONN_V0_UNPLUG                                         0x02
+#define NVIF_NOTIFY_CONN_V0_IRQ                                            0x04
+#define NVIF_NOTIFY_CONN_V0_ANY                                            0x07
+       __u8  mask;
+       __u8  conn;
+       __u8  pad03[5];
+};
+
+struct nvif_notify_conn_rep_v0 {
+       /* nvif_notify_rep ... */
+       __u8  version;
+       __u8  mask;
+       __u8  pad02[6];
+};
+
+struct nvif_notify_uevent_req {
+       /* nvif_notify_req ... */
+};
+
+struct nvif_notify_uevent_rep {
+       /* nvif_notify_rep ... */
+};
+
+#endif
diff --git a/drivers/gpu/drm/nouveau/include/nvif/ioctl.h b/drivers/gpu/drm/nouveau/include/nvif/ioctl.h
new file mode 100644 (file)
index 0000000..4cd8e32
--- /dev/null
@@ -0,0 +1,128 @@
+#ifndef __NVIF_IOCTL_H__
+#define __NVIF_IOCTL_H__
+
+struct nvif_ioctl_v0 {
+       __u8  version;
+#define NVIF_IOCTL_V0_OWNER_NVIF                                           0x00
+#define NVIF_IOCTL_V0_OWNER_ANY                                            0xff
+       __u8  owner;
+#define NVIF_IOCTL_V0_NOP                                                  0x00
+#define NVIF_IOCTL_V0_SCLASS                                               0x01
+#define NVIF_IOCTL_V0_NEW                                                  0x02
+#define NVIF_IOCTL_V0_DEL                                                  0x03
+#define NVIF_IOCTL_V0_MTHD                                                 0x04
+#define NVIF_IOCTL_V0_RD                                                   0x05
+#define NVIF_IOCTL_V0_WR                                                   0x06
+#define NVIF_IOCTL_V0_MAP                                                  0x07
+#define NVIF_IOCTL_V0_UNMAP                                                0x08
+#define NVIF_IOCTL_V0_NTFY_NEW                                             0x09
+#define NVIF_IOCTL_V0_NTFY_DEL                                             0x0a
+#define NVIF_IOCTL_V0_NTFY_GET                                             0x0b
+#define NVIF_IOCTL_V0_NTFY_PUT                                             0x0c
+       __u8  type;
+       __u8  path_nr;
+#define NVIF_IOCTL_V0_ROUTE_NVIF                                           0x00
+#define NVIF_IOCTL_V0_ROUTE_HIDDEN                                         0xff
+       __u8  pad04[3];
+       __u8  route;
+       __u64 token;
+       __u32 path[8];          /* in reverse */
+       __u8  data[];           /* ioctl data (below) */
+};
+
+struct nvif_ioctl_nop {
+};
+
+struct nvif_ioctl_sclass_v0 {
+       /* nvif_ioctl ... */
+       __u8  version;
+       __u8  count;
+       __u8  pad02[6];
+       __u32 oclass[];
+};
+
+struct nvif_ioctl_new_v0 {
+       /* nvif_ioctl ... */
+       __u8  version;
+       __u8  pad01[6];
+       __u8  route;
+       __u64 token;
+       __u32 handle;
+/* these class numbers are made up by us, and not nvidia-assigned */
+#define NVIF_IOCTL_NEW_V0_PERFCTR                                    0x0000ffff
+#define NVIF_IOCTL_NEW_V0_CONTROL                                    0x0000fffe
+       __u32 oclass;
+       __u8  data[];           /* class data (class.h) */
+};
+
+struct nvif_ioctl_del {
+};
+
+struct nvif_ioctl_rd_v0 {
+       /* nvif_ioctl ... */
+       __u8  version;
+       __u8  size;
+       __u8  pad02[2];
+       __u32 data;
+       __u64 addr;
+};
+
+struct nvif_ioctl_wr_v0 {
+       /* nvif_ioctl ... */
+       __u8  version;
+       __u8  size;
+       __u8  pad02[2];
+       __u32 data;
+       __u64 addr;
+};
+
+struct nvif_ioctl_map_v0 {
+       /* nvif_ioctl ... */
+       __u8  version;
+       __u8  pad01[3];
+       __u32 length;
+       __u64 handle;
+};
+
+struct nvif_ioctl_unmap {
+};
+
+struct nvif_ioctl_ntfy_new_v0 {
+       /* nvif_ioctl ... */
+       __u8  version;
+       __u8  event;
+       __u8  index;
+       __u8  pad03[5];
+       __u8  data[];           /* event request data (event.h) */
+};
+
+struct nvif_ioctl_ntfy_del_v0 {
+       /* nvif_ioctl ... */
+       __u8  version;
+       __u8  index;
+       __u8  pad02[6];
+};
+
+struct nvif_ioctl_ntfy_get_v0 {
+       /* nvif_ioctl ... */
+       __u8  version;
+       __u8  index;
+       __u8  pad02[6];
+};
+
+struct nvif_ioctl_ntfy_put_v0 {
+       /* nvif_ioctl ... */
+       __u8  version;
+       __u8  index;
+       __u8  pad02[6];
+};
+
+struct nvif_ioctl_mthd_v0 {
+       /* nvif_ioctl ... */
+       __u8  version;
+       __u8  method;
+       __u8  pad02[6];
+       __u8  data[];           /* method data (class.h) */
+};
+
+#endif
diff --git a/drivers/gpu/drm/nouveau/include/nvif/list.h b/drivers/gpu/drm/nouveau/include/nvif/list.h
new file mode 100644 (file)
index 0000000..8af5d14
--- /dev/null
@@ -0,0 +1,353 @@
+/*
+ * Copyright © 2010 Intel Corporation
+ * Copyright © 2010 Francisco Jerez <currojerez@riseup.net>
+ *
+ * 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.
+ *
+ */
+
+/* Modified by Ben Skeggs <bskeggs@redhat.com> to match kernel list APIs */
+
+#ifndef _XORG_LIST_H_
+#define _XORG_LIST_H_
+
+/**
+ * @file Classic doubly-link circular list implementation.
+ * For real usage examples of the linked list, see the file test/list.c
+ *
+ * Example:
+ * We need to keep a list of struct foo in the parent struct bar, i.e. what
+ * we want is something like this.
+ *
+ *     struct bar {
+ *          ...
+ *          struct foo *list_of_foos; -----> struct foo {}, struct foo {}, struct foo{}
+ *          ...
+ *     }
+ *
+ * We need one list head in bar and a list element in all list_of_foos (both are of
+ * data type 'struct list_head').
+ *
+ *     struct bar {
+ *          ...
+ *          struct list_head list_of_foos;
+ *          ...
+ *     }
+ *
+ *     struct foo {
+ *          ...
+ *          struct list_head entry;
+ *          ...
+ *     }
+ *
+ * Now we initialize the list head:
+ *
+ *     struct bar bar;
+ *     ...
+ *     INIT_LIST_HEAD(&bar.list_of_foos);
+ *
+ * Then we create the first element and add it to this list:
+ *
+ *     struct foo *foo = malloc(...);
+ *     ....
+ *     list_add(&foo->entry, &bar.list_of_foos);
+ *
+ * Repeat the above for each element you want to add to the list. Deleting
+ * works with the element itself.
+ *      list_del(&foo->entry);
+ *      free(foo);
+ *
+ * Note: calling list_del(&bar.list_of_foos) will set bar.list_of_foos to an empty
+ * list again.
+ *
+ * Looping through the list requires a 'struct foo' as iterator and the
+ * name of the field the subnodes use.
+ *
+ * struct foo *iterator;
+ * list_for_each_entry(iterator, &bar.list_of_foos, entry) {
+ *      if (iterator->something == ...)
+ *             ...
+ * }
+ *
+ * Note: You must not call list_del() on the iterator if you continue the
+ * loop. You need to run the safe for-each loop instead:
+ *
+ * struct foo *iterator, *next;
+ * list_for_each_entry_safe(iterator, next, &bar.list_of_foos, entry) {
+ *      if (...)
+ *              list_del(&iterator->entry);
+ * }
+ *
+ */
+
+/**
+ * The linkage struct for list nodes. This struct must be part of your
+ * to-be-linked struct. struct list_head is required for both the head of the
+ * list and for each list node.
+ *
+ * Position and name of the struct list_head field is irrelevant.
+ * There are no requirements that elements of a list are of the same type.
+ * There are no requirements for a list head, any struct list_head can be a list
+ * head.
+ */
+struct list_head {
+    struct list_head *next, *prev;
+};
+
+/**
+ * Initialize the list as an empty list.
+ *
+ * Example:
+ * INIT_LIST_HEAD(&bar->list_of_foos);
+ *
+ * @param The list to initialized.
+ */
+#define LIST_HEAD_INIT(name) { &(name), &(name) }
+
+#define LIST_HEAD(name) \
+       struct list_head name = LIST_HEAD_INIT(name)
+
+static inline void
+INIT_LIST_HEAD(struct list_head *list)
+{
+    list->next = list->prev = list;
+}
+
+static inline void
+__list_add(struct list_head *entry,
+                struct list_head *prev, struct list_head *next)
+{
+    next->prev = entry;
+    entry->next = next;
+    entry->prev = prev;
+    prev->next = entry;
+}
+
+/**
+ * Insert a new element after the given list head. The new element does not
+ * need to be initialised as empty list.
+ * The list changes from:
+ *      head → some element → ...
+ * to
+ *      head → new element → older element → ...
+ *
+ * Example:
+ * struct foo *newfoo = malloc(...);
+ * list_add(&newfoo->entry, &bar->list_of_foos);
+ *
+ * @param entry The new element to prepend to the list.
+ * @param head The existing list.
+ */
+static inline void
+list_add(struct list_head *entry, struct list_head *head)
+{
+    __list_add(entry, head, head->next);
+}
+
+/**
+ * Append a new element to the end of the list given with this list head.
+ *
+ * The list changes from:
+ *      head → some element → ... → lastelement
+ * to
+ *      head → some element → ... → lastelement → new element
+ *
+ * Example:
+ * struct foo *newfoo = malloc(...);
+ * list_add_tail(&newfoo->entry, &bar->list_of_foos);
+ *
+ * @param entry The new element to prepend to the list.
+ * @param head The existing list.
+ */
+static inline void
+list_add_tail(struct list_head *entry, struct list_head *head)
+{
+    __list_add(entry, head->prev, head);
+}
+
+static inline void
+__list_del(struct list_head *prev, struct list_head *next)
+{
+    next->prev = prev;
+    prev->next = next;
+}
+
+/**
+ * Remove the element from the list it is in. Using this function will reset
+ * the pointers to/from this element so it is removed from the list. It does
+ * NOT free the element itself or manipulate it otherwise.
+ *
+ * Using list_del on a pure list head (like in the example at the top of
+ * this file) will NOT remove the first element from
+ * the list but rather reset the list as empty list.
+ *
+ * Example:
+ * list_del(&foo->entry);
+ *
+ * @param entry The element to remove.
+ */
+static inline void
+list_del(struct list_head *entry)
+{
+    __list_del(entry->prev, entry->next);
+}
+
+static inline void
+list_del_init(struct list_head *entry)
+{
+    __list_del(entry->prev, entry->next);
+    INIT_LIST_HEAD(entry);
+}
+
+static inline void list_move_tail(struct list_head *list,
+                                 struct list_head *head)
+{
+       __list_del(list->prev, list->next);
+       list_add_tail(list, head);
+}
+
+/**
+ * Check if the list is empty.
+ *
+ * Example:
+ * list_empty(&bar->list_of_foos);
+ *
+ * @return True if the list contains one or more elements or False otherwise.
+ */
+static inline bool
+list_empty(struct list_head *head)
+{
+    return head->next == head;
+}
+
+/**
+ * Returns a pointer to the container of this list element.
+ *
+ * Example:
+ * struct foo* f;
+ * f = container_of(&foo->entry, struct foo, entry);
+ * assert(f == foo);
+ *
+ * @param ptr Pointer to the struct list_head.
+ * @param type Data type of the list element.
+ * @param member Member name of the struct list_head field in the list element.
+ * @return A pointer to the data struct containing the list head.
+ */
+#ifndef container_of
+#define container_of(ptr, type, member) \
+    (type *)((char *)(ptr) - (char *) &((type *)0)->member)
+#endif
+
+/**
+ * Alias of container_of
+ */
+#define list_entry(ptr, type, member) \
+    container_of(ptr, type, member)
+
+/**
+ * Retrieve the first list entry for the given list pointer.
+ *
+ * Example:
+ * struct foo *first;
+ * first = list_first_entry(&bar->list_of_foos, struct foo, list_of_foos);
+ *
+ * @param ptr The list head
+ * @param type Data type of the list element to retrieve
+ * @param member Member name of the struct list_head field in the list element.
+ * @return A pointer to the first list element.
+ */
+#define list_first_entry(ptr, type, member) \
+    list_entry((ptr)->next, type, member)
+
+/**
+ * Retrieve the last list entry for the given listpointer.
+ *
+ * Example:
+ * struct foo *first;
+ * first = list_last_entry(&bar->list_of_foos, struct foo, list_of_foos);
+ *
+ * @param ptr The list head
+ * @param type Data type of the list element to retrieve
+ * @param member Member name of the struct list_head field in the list element.
+ * @return A pointer to the last list element.
+ */
+#define list_last_entry(ptr, type, member) \
+    list_entry((ptr)->prev, type, member)
+
+#define __container_of(ptr, sample, member)                            \
+    (void *)container_of((ptr), typeof(*(sample)), member)
+
+/**
+ * Loop through the list given by head and set pos to struct in the list.
+ *
+ * Example:
+ * struct foo *iterator;
+ * list_for_each_entry(iterator, &bar->list_of_foos, entry) {
+ *      [modify iterator]
+ * }
+ *
+ * This macro is not safe for node deletion. Use list_for_each_entry_safe
+ * instead.
+ *
+ * @param pos Iterator variable of the type of the list elements.
+ * @param head List head
+ * @param member Member name of the struct list_head in the list elements.
+ *
+ */
+#define list_for_each_entry(pos, head, member)                         \
+    for (pos = __container_of((head)->next, pos, member);              \
+        &pos->member != (head);                                        \
+        pos = __container_of(pos->member.next, pos, member))
+
+/**
+ * Loop through the list, keeping a backup pointer to the element. This
+ * macro allows for the deletion of a list element while looping through the
+ * list.
+ *
+ * See list_for_each_entry for more details.
+ */
+#define list_for_each_entry_safe(pos, tmp, head, member)               \
+    for (pos = __container_of((head)->next, pos, member),              \
+        tmp = __container_of(pos->member.next, pos, member);           \
+        &pos->member != (head);                                        \
+        pos = tmp, tmp = __container_of(pos->member.next, tmp, member))
+
+
+#define list_for_each_entry_reverse(pos, head, member)                 \
+       for (pos = __container_of((head)->prev, pos, member);           \
+            &pos->member != (head);                                    \
+            pos = __container_of(pos->member.prev, pos, member))
+
+#define list_for_each_entry_continue(pos, head, member)                        \
+       for (pos = __container_of(pos->member.next, pos, member);       \
+            &pos->member != (head);                                    \
+            pos = __container_of(pos->member.next, pos, member))
+
+#define list_for_each_entry_continue_reverse(pos, head, member)                \
+       for (pos = __container_of(pos->member.prev, pos, member);       \
+            &pos->member != (head);                                    \
+            pos = __container_of(pos->member.prev, pos, member))
+
+#define list_for_each_entry_from(pos, head, member)                    \
+       for (;                                                          \
+            &pos->member != (head);                                    \
+            pos = __container_of(pos->member.next, pos, member))
+
+#endif
diff --git a/drivers/gpu/drm/nouveau/include/nvif/notify.h b/drivers/gpu/drm/nouveau/include/nvif/notify.h
new file mode 100644 (file)
index 0000000..9ebfa3b
--- /dev/null
@@ -0,0 +1,39 @@
+#ifndef __NVIF_NOTIFY_H__
+#define __NVIF_NOTIFY_H__
+
+struct nvif_notify {
+       struct nvif_object *object;
+       int index;
+
+#define NVIF_NOTIFY_USER 0
+#define NVIF_NOTIFY_WORK 1
+       unsigned long flags;
+       atomic_t putcnt;
+       void (*dtor)(struct nvif_notify *);
+#define NVIF_NOTIFY_DROP 0
+#define NVIF_NOTIFY_KEEP 1
+       int  (*func)(struct nvif_notify *);
+
+       /* this is const for a *very* good reason - the data might be on the
+        * stack from an irq handler.  if you're not nvif/notify.c then you
+        * should probably think twice before casting it away...
+        */
+       const void *data;
+       u32 size;
+       struct work_struct work;
+};
+
+int  nvif_notify_init(struct nvif_object *, void (*dtor)(struct nvif_notify *),
+                     int (*func)(struct nvif_notify *), bool work, u8 type,
+                     void *data, u32 size, u32 reply, struct nvif_notify *);
+int  nvif_notify_fini(struct nvif_notify *);
+int  nvif_notify_get(struct nvif_notify *);
+int  nvif_notify_put(struct nvif_notify *);
+int  nvif_notify(const void *, u32, const void *, u32);
+
+int  nvif_notify_new(struct nvif_object *, int (*func)(struct nvif_notify *),
+                    bool work, u8 type, void *data, u32 size, u32 reply,
+                    struct nvif_notify **);
+void nvif_notify_ref(struct nvif_notify *, struct nvif_notify **);
+
+#endif
diff --git a/drivers/gpu/drm/nouveau/include/nvif/object.h b/drivers/gpu/drm/nouveau/include/nvif/object.h
new file mode 100644 (file)
index 0000000..04c8747
--- /dev/null
@@ -0,0 +1,75 @@
+#ifndef __NVIF_OBJECT_H__
+#define __NVIF_OBJECT_H__
+
+#include <nvif/os.h>
+
+struct nvif_object {
+       struct nvif_object *parent;
+       struct nvif_object *object; /*XXX: hack for nvif_object() */
+       struct kref refcount;
+       u32 handle;
+       u32 oclass;
+       void *data;
+       u32   size;
+       void *priv; /*XXX: hack */
+       void (*dtor)(struct nvif_object *);
+       struct {
+               void __iomem *ptr;
+               u32 size;
+       } map;
+};
+
+int  nvif_object_init(struct nvif_object *, void (*dtor)(struct nvif_object *),
+                     u32 handle, u32 oclass, void *, u32,
+                     struct nvif_object *);
+void nvif_object_fini(struct nvif_object *);
+int  nvif_object_new(struct nvif_object *, u32 handle, u32 oclass,
+                    void *, u32, struct nvif_object **);
+void nvif_object_ref(struct nvif_object *, struct nvif_object **);
+int  nvif_object_ioctl(struct nvif_object *, void *, u32, void **);
+int  nvif_object_sclass(struct nvif_object *, u32 *, int);
+u32  nvif_object_rd(struct nvif_object *, int, u64);
+void nvif_object_wr(struct nvif_object *, int, u64, u32);
+int  nvif_object_mthd(struct nvif_object *, u32, void *, u32);
+int  nvif_object_map(struct nvif_object *);
+void nvif_object_unmap(struct nvif_object *);
+
+#define nvif_object(a) (a)->object
+
+#define ioread8_native ioread8
+#define iowrite8_native iowrite8
+#define nvif_rd(a,b,c) ({                                                      \
+       struct nvif_object *_object = nvif_object(a);                          \
+       u32 _data;                                                             \
+       if (likely(_object->map.ptr))                                          \
+               _data = ioread##b##_native((u8 __iomem *)_object->map.ptr + (c));      \
+       else                                                                   \
+               _data = nvif_object_rd(_object, (b) / 8, (c));                 \
+       _data;                                                                 \
+})
+#define nvif_wr(a,b,c,d) ({                                                    \
+       struct nvif_object *_object = nvif_object(a);                          \
+       if (likely(_object->map.ptr))                                          \
+               iowrite##b##_native((d), (u8 __iomem *)_object->map.ptr + (c));        \
+       else                                                                   \
+               nvif_object_wr(_object, (b) / 8, (c), (d));                    \
+})
+#define nvif_rd08(a,b) ({ u8  _v = nvif_rd((a), 8, (b)); _v; })
+#define nvif_rd16(a,b) ({ u16 _v = nvif_rd((a), 16, (b)); _v; })
+#define nvif_rd32(a,b) ({ u32 _v = nvif_rd((a), 32, (b)); _v; })
+#define nvif_wr08(a,b,c) nvif_wr((a), 8, (b), (u8)(c))
+#define nvif_wr16(a,b,c) nvif_wr((a), 16, (b), (u16)(c))
+#define nvif_wr32(a,b,c) nvif_wr((a), 32, (b), (u32)(c))
+#define nvif_mask(a,b,c,d) ({                                                  \
+       u32 _v = nvif_rd32(nvif_object(a), (b));                               \
+       nvif_wr32(nvif_object(a), (b), (_v & ~(c)) | (d));                     \
+       _v;                                                                    \
+})
+
+#define nvif_mthd(a,b,c,d) nvif_object_mthd(nvif_object(a), (b), (c), (d))
+
+/*XXX*/
+#include <core/object.h>
+#define nvxx_object(a) ((struct nvkm_object *)nvif_object(a)->priv)
+
+#endif
diff --git a/drivers/gpu/drm/nouveau/include/nvif/os.h b/drivers/gpu/drm/nouveau/include/nvif/os.h
new file mode 100644 (file)
index 0000000..bdd05ee
--- /dev/null
@@ -0,0 +1,44 @@
+#ifndef __NOUVEAU_OS_H__
+#define __NOUVEAU_OS_H__
+
+#include <linux/types.h>
+#include <linux/slab.h>
+#include <linux/mutex.h>
+#include <linux/pci.h>
+#include <linux/platform_device.h>
+#include <linux/printk.h>
+#include <linux/bitops.h>
+#include <linux/firmware.h>
+#include <linux/module.h>
+#include <linux/i2c.h>
+#include <linux/i2c-algo-bit.h>
+#include <linux/delay.h>
+#include <linux/io-mapping.h>
+#include <linux/acpi.h>
+#include <linux/vmalloc.h>
+#include <linux/dmi.h>
+#include <linux/reboot.h>
+#include <linux/interrupt.h>
+#include <linux/log2.h>
+#include <linux/pm_runtime.h>
+#include <linux/power_supply.h>
+#include <linux/clk.h>
+#include <linux/regulator/consumer.h>
+
+#include <asm/unaligned.h>
+
+#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 */
+
+#endif
diff --git a/drivers/gpu/drm/nouveau/include/nvif/unpack.h b/drivers/gpu/drm/nouveau/include/nvif/unpack.h
new file mode 100644 (file)
index 0000000..5933188
--- /dev/null
@@ -0,0 +1,24 @@
+#ifndef __NVIF_UNPACK_H__
+#define __NVIF_UNPACK_H__
+
+#define nvif_unvers(d) ({                                                      \
+       ret = (size == sizeof(d)) ? 0 : -ENOSYS;                               \
+       (ret == 0);                                                            \
+})
+
+#define nvif_unpack(d,vl,vh,m) ({                                              \
+       if ((vl) == 0 || ret == -ENOSYS) {                                     \
+               int _size = sizeof(d);                                         \
+               if (_size <= size && (d).version >= (vl) &&                    \
+                                    (d).version <= (vh)) {                    \
+                       data = (u8 *)data + _size;                             \
+                       size = size - _size;                                   \
+                       ret = ((m) || !size) ? 0 : -E2BIG;                     \
+               } else {                                                       \
+                       ret = -ENOSYS;                                         \
+               }                                                              \
+       }                                                                      \
+       (ret == 0);                                                            \
+})
+
+#endif
diff --git a/drivers/gpu/drm/nouveau/include/nvkm/core/client.h b/drivers/gpu/drm/nouveau/include/nvkm/core/client.h
new file mode 100644 (file)
index 0000000..a35b382
--- /dev/null
@@ -0,0 +1,55 @@
+#ifndef __NVKM_CLIENT_H__
+#define __NVKM_CLIENT_H__
+#include <core/namedb.h>
+
+struct nvkm_client {
+       struct nvkm_namedb namedb;
+       struct nvkm_handle *root;
+       struct nvkm_object *device;
+       char name[32];
+       u32 debug;
+       struct nvkm_vm *vm;
+       bool super;
+       void *data;
+
+       int (*ntfy)(const void *, u32, const void *, u32);
+       struct nvkm_client_notify *notify[16];
+};
+
+static inline struct nvkm_client *
+nv_client(void *obj)
+{
+#if CONFIG_NOUVEAU_DEBUG >= NV_DBG_PARANOIA
+       if (unlikely(!nv_iclass(obj, NV_CLIENT_CLASS)))
+               nv_assert("BAD CAST -> NvClient, %08x", nv_hclass(obj));
+#endif
+       return obj;
+}
+
+static inline struct nvkm_client *
+nvkm_client(void *obj)
+{
+       struct nvkm_object *client = nv_object(obj);
+       while (client && !(nv_iclass(client, NV_CLIENT_CLASS)))
+               client = client->parent;
+       return (void *)client;
+}
+
+#define nvkm_client_create(n,c,oc,od,d)                                     \
+       nvkm_client_create_((n), (c), (oc), (od), sizeof(**d), (void **)d)
+
+int  nvkm_client_create_(const char *name, u64 device, const char *cfg,
+                           const char *dbg, int, void **);
+#define nvkm_client_destroy(p)                                              \
+       nvkm_namedb_destroy(&(p)->base)
+
+int  nvkm_client_init(struct nvkm_client *);
+int  nvkm_client_fini(struct nvkm_client *, bool suspend);
+const char *nvkm_client_name(void *obj);
+
+int nvkm_client_notify_new(struct nvkm_object *, struct nvkm_event *,
+                          void *data, u32 size);
+int nvkm_client_notify_del(struct nvkm_client *, int index);
+int nvkm_client_notify_get(struct nvkm_client *, int index);
+int nvkm_client_notify_put(struct nvkm_client *, int index);
+#endif
diff --git a/drivers/gpu/drm/nouveau/include/nvkm/core/debug.h b/drivers/gpu/drm/nouveau/include/nvkm/core/debug.h
new file mode 100644 (file)
index 0000000..d07cb86
--- /dev/null
@@ -0,0 +1,18 @@
+#ifndef __NVKM_DEBUG_H__
+#define __NVKM_DEBUG_H__
+extern int nv_info_debug_level;
+
+#define NV_DBG_FATAL    0
+#define NV_DBG_ERROR    1
+#define NV_DBG_WARN     2
+#define NV_DBG_INFO     nv_info_debug_level
+#define NV_DBG_DEBUG    4
+#define NV_DBG_TRACE    5
+#define NV_DBG_PARANOIA 6
+#define NV_DBG_SPAM     7
+
+#define NV_DBG_INFO_NORMAL 3
+#define NV_DBG_INFO_SILENT NV_DBG_DEBUG
+
+#define nv_debug_level(a) nv_info_debug_level = NV_DBG_INFO_##a
+#endif
diff --git a/drivers/gpu/drm/nouveau/include/nvkm/core/device.h b/drivers/gpu/drm/nouveau/include/nvkm/core/device.h
new file mode 100644 (file)
index 0000000..333db33
--- /dev/null
@@ -0,0 +1,101 @@
+#ifndef __NVKM_DEVICE_H__
+#define __NVKM_DEVICE_H__
+#include <core/engine.h>
+#include <core/event.h>
+
+struct nvkm_device {
+       struct nvkm_engine engine;
+       struct list_head head;
+
+       struct pci_dev *pdev;
+       struct platform_device *platformdev;
+       u64 handle;
+
+       struct nvkm_event event;
+
+       const char *cfgopt;
+       const char *dbgopt;
+       const char *name;
+       const char *cname;
+       u64 disable_mask;
+
+       enum {
+               NV_04    = 0x04,
+               NV_10    = 0x10,
+               NV_11    = 0x11,
+               NV_20    = 0x20,
+               NV_30    = 0x30,
+               NV_40    = 0x40,
+               NV_50    = 0x50,
+               NV_C0    = 0xc0,
+               NV_E0    = 0xe0,
+               GM100    = 0x110,
+       } card_type;
+       u32 chipset;
+       u8  chiprev;
+       u32 crystal;
+
+       struct nvkm_oclass *oclass[NVDEV_SUBDEV_NR];
+       struct nvkm_object *subdev[NVDEV_SUBDEV_NR];
+
+       struct {
+               struct notifier_block nb;
+       } acpi;
+};
+
+struct nvkm_device *nvkm_device_find(u64 name);
+int nvkm_device_list(u64 *name, int size);
+
+struct nvkm_device *nv_device(void *obj);
+
+static inline bool
+nv_device_match(struct nvkm_object *object, u16 dev, u16 ven, u16 sub)
+{
+       struct nvkm_device *device = nv_device(object);
+       return device->pdev->device == dev &&
+              device->pdev->subsystem_vendor == ven &&
+              device->pdev->subsystem_device == sub;
+}
+
+static inline bool
+nv_device_is_pci(struct nvkm_device *device)
+{
+       return device->pdev != NULL;
+}
+
+static inline bool
+nv_device_is_cpu_coherent(struct nvkm_device *device)
+{
+       return (!IS_ENABLED(CONFIG_ARM) && nv_device_is_pci(device));
+}
+
+static inline struct device *
+nv_device_base(struct nvkm_device *device)
+{
+       return nv_device_is_pci(device) ? &device->pdev->dev :
+                                         &device->platformdev->dev;
+}
+
+resource_size_t
+nv_device_resource_start(struct nvkm_device *device, unsigned int bar);
+
+resource_size_t
+nv_device_resource_len(struct nvkm_device *device, unsigned int bar);
+
+int
+nv_device_get_irq(struct nvkm_device *device, bool stall);
+
+struct platform_device;
+
+enum nv_bus_type {
+       NVKM_BUS_PCI,
+       NVKM_BUS_PLATFORM,
+};
+
+#define nvkm_device_create(p,t,n,s,c,d,u)                                   \
+       nvkm_device_create_((void *)(p), (t), (n), (s), (c), (d),           \
+                              sizeof(**u), (void **)u)
+int  nvkm_device_create_(void *, enum nv_bus_type type, u64 name,
+                           const char *sname, const char *cfg, const char *dbg,
+                           int, void **);
+#endif
diff --git a/drivers/gpu/drm/nouveau/include/nvkm/core/devidx.h b/drivers/gpu/drm/nouveau/include/nvkm/core/devidx.h
new file mode 100644 (file)
index 0000000..60c5888
--- /dev/null
@@ -0,0 +1,62 @@
+#ifndef __NVKM_DEVIDX_H__
+#define __NVKM_DEVIDX_H__
+enum nvkm_devidx {
+       NVDEV_ENGINE_DEVICE,
+       NVDEV_SUBDEV_VBIOS,
+
+       /* All subdevs from DEVINIT to DEVINIT_LAST will be created before
+        * *any* of them are initialised.  This subdev category is used
+        * for any subdevs that the VBIOS init table parsing may call out
+        * to during POST.
+        */
+       NVDEV_SUBDEV_DEVINIT,
+       NVDEV_SUBDEV_IBUS,
+       NVDEV_SUBDEV_GPIO,
+       NVDEV_SUBDEV_I2C,
+       NVDEV_SUBDEV_DEVINIT_LAST = NVDEV_SUBDEV_I2C,
+
+       /* This grouping of subdevs are initialised right after they've
+        * been created, and are allowed to assume any subdevs in the
+        * list above them exist and have been initialised.
+        */
+       NVDEV_SUBDEV_FUSE,
+       NVDEV_SUBDEV_MXM,
+       NVDEV_SUBDEV_MC,
+       NVDEV_SUBDEV_BUS,
+       NVDEV_SUBDEV_TIMER,
+       NVDEV_SUBDEV_FB,
+       NVDEV_SUBDEV_LTC,
+       NVDEV_SUBDEV_INSTMEM,
+       NVDEV_SUBDEV_MMU,
+       NVDEV_SUBDEV_BAR,
+       NVDEV_SUBDEV_PMU,
+       NVDEV_SUBDEV_VOLT,
+       NVDEV_SUBDEV_THERM,
+       NVDEV_SUBDEV_CLK,
+
+       NVDEV_ENGINE_FIRST,
+       NVDEV_ENGINE_DMAOBJ = NVDEV_ENGINE_FIRST,
+       NVDEV_ENGINE_IFB,
+       NVDEV_ENGINE_FIFO,
+       NVDEV_ENGINE_SW,
+       NVDEV_ENGINE_GR,
+       NVDEV_ENGINE_MPEG,
+       NVDEV_ENGINE_ME,
+       NVDEV_ENGINE_VP,
+       NVDEV_ENGINE_CIPHER,
+       NVDEV_ENGINE_BSP,
+       NVDEV_ENGINE_MSPPP,
+       NVDEV_ENGINE_CE0,
+       NVDEV_ENGINE_CE1,
+       NVDEV_ENGINE_CE2,
+       NVDEV_ENGINE_VIC,
+       NVDEV_ENGINE_MSENC,
+       NVDEV_ENGINE_DISP,
+       NVDEV_ENGINE_PM,
+       NVDEV_ENGINE_MSVLD,
+       NVDEV_ENGINE_SEC,
+       NVDEV_ENGINE_MSPDEC,
+
+       NVDEV_SUBDEV_NR,
+};
+#endif
diff --git a/drivers/gpu/drm/nouveau/include/nvkm/core/engctx.h b/drivers/gpu/drm/nouveau/include/nvkm/core/engctx.h
new file mode 100644 (file)
index 0000000..1bf2e8e
--- /dev/null
@@ -0,0 +1,51 @@
+#ifndef __NVKM_ENGCTX_H__
+#define __NVKM_ENGCTX_H__
+#include <core/gpuobj.h>
+
+#include <subdev/mmu.h>
+
+#define NV_ENGCTX_(eng,var) (NV_ENGCTX_CLASS | ((var) << 8) | (eng))
+#define NV_ENGCTX(name,var)  NV_ENGCTX_(NVDEV_ENGINE_##name, (var))
+
+struct nvkm_engctx {
+       struct nvkm_gpuobj gpuobj;
+       struct nvkm_vma vma;
+       struct list_head head;
+       unsigned long save;
+       u64 addr;
+};
+
+static inline struct nvkm_engctx *
+nv_engctx(void *obj)
+{
+#if CONFIG_NOUVEAU_DEBUG >= NV_DBG_PARANOIA
+       if (unlikely(!nv_iclass(obj, NV_ENGCTX_CLASS)))
+               nv_assert("BAD CAST -> NvEngCtx, %08x", nv_hclass(obj));
+#endif
+       return obj;
+}
+
+#define nvkm_engctx_create(p,e,c,g,s,a,f,d)                                 \
+       nvkm_engctx_create_((p), (e), (c), (g), (s), (a), (f),              \
+                              sizeof(**d), (void **)d)
+
+int  nvkm_engctx_create_(struct nvkm_object *, struct nvkm_object *,
+                           struct nvkm_oclass *, struct nvkm_object *,
+                           u32 size, u32 align, u32 flags,
+                           int length, void **data);
+void nvkm_engctx_destroy(struct nvkm_engctx *);
+int  nvkm_engctx_init(struct nvkm_engctx *);
+int  nvkm_engctx_fini(struct nvkm_engctx *, bool suspend);
+
+int  _nvkm_engctx_ctor(struct nvkm_object *, struct nvkm_object *,
+                         struct nvkm_oclass *, void *, u32,
+                         struct nvkm_object **);
+void _nvkm_engctx_dtor(struct nvkm_object *);
+int  _nvkm_engctx_init(struct nvkm_object *);
+int  _nvkm_engctx_fini(struct nvkm_object *, bool suspend);
+#define _nvkm_engctx_rd32 _nvkm_gpuobj_rd32
+#define _nvkm_engctx_wr32 _nvkm_gpuobj_wr32
+
+struct nvkm_object *nvkm_engctx_get(struct nvkm_engine *, u64 addr);
+void nvkm_engctx_put(struct nvkm_object *);
+#endif
diff --git a/drivers/gpu/drm/nouveau/include/nvkm/core/engine.h b/drivers/gpu/drm/nouveau/include/nvkm/core/engine.h
new file mode 100644 (file)
index 0000000..faf0fd2
--- /dev/null
@@ -0,0 +1,56 @@
+#ifndef __NVKM_ENGINE_H__
+#define __NVKM_ENGINE_H__
+#include <core/subdev.h>
+
+#define NV_ENGINE_(eng,var) (NV_ENGINE_CLASS | ((var) << 8) | (eng))
+#define NV_ENGINE(name,var)  NV_ENGINE_(NVDEV_ENGINE_##name, (var))
+
+struct nvkm_engine {
+       struct nvkm_subdev subdev;
+       struct nvkm_oclass *cclass;
+       struct nvkm_oclass *sclass;
+
+       struct list_head contexts;
+       spinlock_t lock;
+
+       void (*tile_prog)(struct nvkm_engine *, int region);
+       int  (*tlb_flush)(struct nvkm_engine *);
+};
+
+static inline struct nvkm_engine *
+nv_engine(void *obj)
+{
+#if CONFIG_NOUVEAU_DEBUG >= NV_DBG_PARANOIA
+       if (unlikely(!nv_iclass(obj, NV_ENGINE_CLASS)))
+               nv_assert("BAD CAST -> NvEngine, %08x", nv_hclass(obj));
+#endif
+       return obj;
+}
+
+static inline int
+nv_engidx(struct nvkm_engine *engine)
+{
+       return nv_subidx(&engine->subdev);
+}
+
+struct nvkm_engine *nvkm_engine(void *obj, int idx);
+
+#define nvkm_engine_create(p,e,c,d,i,f,r)                                   \
+       nvkm_engine_create_((p), (e), (c), (d), (i), (f),                   \
+                              sizeof(**r),(void **)r)
+
+#define nvkm_engine_destroy(p)                                              \
+       nvkm_subdev_destroy(&(p)->subdev)
+#define nvkm_engine_init(p)                                                 \
+       nvkm_subdev_init(&(p)->subdev)
+#define nvkm_engine_fini(p,s)                                               \
+       nvkm_subdev_fini(&(p)->subdev, (s))
+
+int nvkm_engine_create_(struct nvkm_object *, struct nvkm_object *,
+                          struct nvkm_oclass *, bool, const char *,
+                          const char *, int, void **);
+
+#define _nvkm_engine_dtor _nvkm_subdev_dtor
+#define _nvkm_engine_init _nvkm_subdev_init
+#define _nvkm_engine_fini _nvkm_subdev_fini
+#endif
diff --git a/drivers/gpu/drm/nouveau/include/nvkm/core/enum.h b/drivers/gpu/drm/nouveau/include/nvkm/core/enum.h
new file mode 100644 (file)
index 0000000..e76f76f
--- /dev/null
@@ -0,0 +1,21 @@
+#ifndef __NVKM_ENUM_H__
+#define __NVKM_ENUM_H__
+#include <core/os.h>
+
+struct nvkm_enum {
+       u32 value;
+       const char *name;
+       const void *data;
+       u32 data2;
+};
+
+const struct nvkm_enum *nvkm_enum_find(const struct nvkm_enum *, u32 value);
+const struct nvkm_enum *nvkm_enum_print(const struct nvkm_enum *, u32 value);
+
+struct nvkm_bitfield {
+       u32 mask;
+       const char *name;
+};
+
+void nvkm_bitfield_print(const struct nvkm_bitfield *, u32 value);
+#endif
diff --git a/drivers/gpu/drm/nouveau/include/nvkm/core/event.h b/drivers/gpu/drm/nouveau/include/nvkm/core/event.h
new file mode 100644 (file)
index 0000000..b98fe2d
--- /dev/null
@@ -0,0 +1,34 @@
+#ifndef __NVKM_EVENT_H__
+#define __NVKM_EVENT_H__
+#include <core/os.h>
+struct nvkm_notify;
+struct nvkm_object;
+
+struct nvkm_event {
+       const struct nvkm_event_func *func;
+
+       int types_nr;
+       int index_nr;
+
+       spinlock_t refs_lock;
+       spinlock_t list_lock;
+       struct list_head list;
+       int *refs;
+};
+
+struct nvkm_event_func {
+       int  (*ctor)(struct nvkm_object *, void *data, u32 size,
+                    struct nvkm_notify *);
+       void (*send)(void *data, u32 size, struct nvkm_notify *);
+       void (*init)(struct nvkm_event *, int type, int index);
+       void (*fini)(struct nvkm_event *, int type, int index);
+};
+
+int  nvkm_event_init(const struct nvkm_event_func *func, int types_nr,
+                    int index_nr, struct nvkm_event *);
+void nvkm_event_fini(struct nvkm_event *);
+void nvkm_event_get(struct nvkm_event *, u32 types, int index);
+void nvkm_event_put(struct nvkm_event *, u32 types, int index);
+void nvkm_event_send(struct nvkm_event *, u32 types, int index,
+                    void *data, u32 size);
+#endif
diff --git a/drivers/gpu/drm/nouveau/include/nvkm/core/gpuobj.h b/drivers/gpu/drm/nouveau/include/nvkm/core/gpuobj.h
new file mode 100644 (file)
index 0000000..e0187e7
--- /dev/null
@@ -0,0 +1,64 @@
+#ifndef __NVKM_GPUOBJ_H__
+#define __NVKM_GPUOBJ_H__
+#include <core/object.h>
+#include <core/mm.h>
+struct nvkm_vma;
+struct nvkm_vm;
+
+#define NVOBJ_FLAG_ZERO_ALLOC 0x00000001
+#define NVOBJ_FLAG_ZERO_FREE  0x00000002
+#define NVOBJ_FLAG_HEAP       0x00000004
+
+struct nvkm_gpuobj {
+       struct nvkm_object object;
+       struct nvkm_object *parent;
+       struct nvkm_mm_node *node;
+       struct nvkm_mm heap;
+
+       u32 flags;
+       u64 addr;
+       u32 size;
+};
+
+static inline struct nvkm_gpuobj *
+nv_gpuobj(void *obj)
+{
+#if CONFIG_NOUVEAU_DEBUG >= NV_DBG_PARANOIA
+       if (unlikely(!nv_iclass(obj, NV_GPUOBJ_CLASS)))
+               nv_assert("BAD CAST -> NvGpuObj, %08x", nv_hclass(obj));
+#endif
+       return obj;
+}
+
+#define nvkm_gpuobj_create(p,e,c,v,g,s,a,f,d)                               \
+       nvkm_gpuobj_create_((p), (e), (c), (v), (g), (s), (a), (f),         \
+                              sizeof(**d), (void **)d)
+#define nvkm_gpuobj_init(p) nvkm_object_init(&(p)->object)
+#define nvkm_gpuobj_fini(p,s) nvkm_object_fini(&(p)->object, (s))
+int  nvkm_gpuobj_create_(struct nvkm_object *, struct nvkm_object *,
+                           struct nvkm_oclass *, u32 pclass,
+                           struct nvkm_object *, u32 size, u32 align,
+                           u32 flags, int length, void **);
+void nvkm_gpuobj_destroy(struct nvkm_gpuobj *);
+
+int  nvkm_gpuobj_new(struct nvkm_object *, struct nvkm_object *, u32 size,
+                    u32 align, u32 flags, struct nvkm_gpuobj **);
+int  nvkm_gpuobj_dup(struct nvkm_object *, struct nvkm_gpuobj *,
+                    struct nvkm_gpuobj **);
+int  nvkm_gpuobj_map(struct nvkm_gpuobj *, u32 acc, struct nvkm_vma *);
+int  nvkm_gpuobj_map_vm(struct nvkm_gpuobj *, struct nvkm_vm *, u32 access,
+                       struct nvkm_vma *);
+void nvkm_gpuobj_unmap(struct nvkm_vma *);
+
+static inline void
+nvkm_gpuobj_ref(struct nvkm_gpuobj *obj, struct nvkm_gpuobj **ref)
+{
+       nvkm_object_ref(&obj->object, (struct nvkm_object **)ref);
+}
+
+void _nvkm_gpuobj_dtor(struct nvkm_object *);
+int  _nvkm_gpuobj_init(struct nvkm_object *);
+int  _nvkm_gpuobj_fini(struct nvkm_object *, bool);
+u32  _nvkm_gpuobj_rd32(struct nvkm_object *, u64);
+void _nvkm_gpuobj_wr32(struct nvkm_object *, u64, u32);
+#endif
diff --git a/drivers/gpu/drm/nouveau/include/nvkm/core/handle.h b/drivers/gpu/drm/nouveau/include/nvkm/core/handle.h
new file mode 100644 (file)
index 0000000..67f384d
--- /dev/null
@@ -0,0 +1,34 @@
+#ifndef __NVKM_HANDLE_H__
+#define __NVKM_HANDLE_H__
+#include <core/os.h>
+struct nvkm_object;
+
+struct nvkm_handle {
+       struct nvkm_namedb *namedb;
+       struct list_head node;
+
+       struct list_head head;
+       struct list_head tree;
+       u32 name;
+       u32 priv;
+
+       u8  route;
+       u64 token;
+
+       struct nvkm_handle *parent;
+       struct nvkm_object *object;
+};
+
+int  nvkm_handle_create(struct nvkm_object *, u32 parent, u32 handle,
+                       struct nvkm_object *, struct nvkm_handle **);
+void nvkm_handle_destroy(struct nvkm_handle *);
+int  nvkm_handle_init(struct nvkm_handle *);
+int  nvkm_handle_fini(struct nvkm_handle *, bool suspend);
+
+struct nvkm_object *nvkm_handle_ref(struct nvkm_object *, u32 name);
+
+struct nvkm_handle *nvkm_handle_get_class(struct nvkm_object *, u16);
+struct nvkm_handle *nvkm_handle_get_vinst(struct nvkm_object *, u64);
+struct nvkm_handle *nvkm_handle_get_cinst(struct nvkm_object *, u32);
+void nvkm_handle_put(struct nvkm_handle *);
+#endif
diff --git a/drivers/gpu/drm/nouveau/include/nvkm/core/ioctl.h b/drivers/gpu/drm/nouveau/include/nvkm/core/ioctl.h
new file mode 100644 (file)
index 0000000..88971eb
--- /dev/null
@@ -0,0 +1,7 @@
+#ifndef __NVKM_IOCTL_H__
+#define __NVKM_IOCTL_H__
+#include <core/os.h>
+struct nvkm_client;
+
+int nvkm_ioctl(struct nvkm_client *, bool, void *, u32, void **);
+#endif
diff --git a/drivers/gpu/drm/nouveau/include/nvkm/core/mm.h b/drivers/gpu/drm/nouveau/include/nvkm/core/mm.h
new file mode 100644 (file)
index 0000000..096eb1a
--- /dev/null
@@ -0,0 +1,40 @@
+#ifndef __NVKM_MM_H__
+#define __NVKM_MM_H__
+#include <core/os.h>
+
+struct nvkm_mm_node {
+       struct list_head nl_entry;
+       struct list_head fl_entry;
+       struct list_head rl_entry;
+
+#define NVKM_MM_HEAP_ANY 0x00
+       u8  heap;
+#define NVKM_MM_TYPE_NONE 0x00
+#define NVKM_MM_TYPE_HOLE 0xff
+       u8  type;
+       u32 offset;
+       u32 length;
+};
+
+struct nvkm_mm {
+       struct list_head nodes;
+       struct list_head free;
+
+       u32 block_size;
+       int heap_nodes;
+};
+
+static inline bool
+nvkm_mm_initialised(struct nvkm_mm *mm)
+{
+       return mm->block_size != 0;
+}
+
+int  nvkm_mm_init(struct nvkm_mm *, u32 offset, u32 length, u32 block);
+int  nvkm_mm_fini(struct nvkm_mm *);
+int  nvkm_mm_head(struct nvkm_mm *, u8 heap, u8 type, u32 size_max,
+                 u32 size_min, u32 align, struct nvkm_mm_node **);
+int  nvkm_mm_tail(struct nvkm_mm *, u8 heap, u8 type, u32 size_max,
+                 u32 size_min, u32 align, struct nvkm_mm_node **);
+void nvkm_mm_free(struct nvkm_mm *, struct nvkm_mm_node **);
+#endif
diff --git a/drivers/gpu/drm/nouveau/include/nvkm/core/namedb.h b/drivers/gpu/drm/nouveau/include/nvkm/core/namedb.h
new file mode 100644 (file)
index 0000000..4cfe16f
--- /dev/null
@@ -0,0 +1,53 @@
+#ifndef __NVKM_NAMEDB_H__
+#define __NVKM_NAMEDB_H__
+#include <core/parent.h>
+struct nvkm_handle;
+
+struct nvkm_namedb {
+       struct nvkm_parent parent;
+       rwlock_t lock;
+       struct list_head list;
+};
+
+static inline struct nvkm_namedb *
+nv_namedb(void *obj)
+{
+#if CONFIG_NOUVEAU_DEBUG >= NV_DBG_PARANOIA
+       if (unlikely(!nv_iclass(obj, NV_NAMEDB_CLASS)))
+               nv_assert("BAD CAST -> NvNameDB, %08x", nv_hclass(obj));
+#endif
+       return obj;
+}
+
+#define nvkm_namedb_create(p,e,c,v,s,m,d)                                   \
+       nvkm_namedb_create_((p), (e), (c), (v), (s), (m),                   \
+                              sizeof(**d), (void **)d)
+#define nvkm_namedb_init(p)                                                 \
+       nvkm_parent_init(&(p)->parent)
+#define nvkm_namedb_fini(p,s)                                               \
+       nvkm_parent_fini(&(p)->parent, (s))
+#define nvkm_namedb_destroy(p)                                              \
+       nvkm_parent_destroy(&(p)->parent)
+
+int  nvkm_namedb_create_(struct nvkm_object *, struct nvkm_object *,
+                           struct nvkm_oclass *, u32 pclass,
+                           struct nvkm_oclass *, u64 engcls,
+                           int size, void **);
+
+int  _nvkm_namedb_ctor(struct nvkm_object *, struct nvkm_object *,
+                         struct nvkm_oclass *, void *, u32,
+                         struct nvkm_object **);
+#define _nvkm_namedb_dtor _nvkm_parent_dtor
+#define _nvkm_namedb_init _nvkm_parent_init
+#define _nvkm_namedb_fini _nvkm_parent_fini
+
+int  nvkm_namedb_insert(struct nvkm_namedb *, u32 name, struct nvkm_object *,
+                       struct nvkm_handle *);
+void nvkm_namedb_remove(struct nvkm_handle *);
+
+struct nvkm_handle *nvkm_namedb_get(struct nvkm_namedb *, u32);
+struct nvkm_handle *nvkm_namedb_get_class(struct nvkm_namedb *, u16);
+struct nvkm_handle *nvkm_namedb_get_vinst(struct nvkm_namedb *, u64);
+struct nvkm_handle *nvkm_namedb_get_cinst(struct nvkm_namedb *, u32);
+void nvkm_namedb_put(struct nvkm_handle *);
+#endif
diff --git a/drivers/gpu/drm/nouveau/include/nvkm/core/notify.h b/drivers/gpu/drm/nouveau/include/nvkm/core/notify.h
new file mode 100644 (file)
index 0000000..753d08c
--- /dev/null
@@ -0,0 +1,38 @@
+#ifndef __NVKM_NOTIFY_H__
+#define __NVKM_NOTIFY_H__
+#include <core/os.h>
+struct nvkm_object;
+
+struct nvkm_notify {
+       struct nvkm_event *event;
+       struct list_head head;
+#define NVKM_NOTIFY_USER 0
+#define NVKM_NOTIFY_WORK 1
+       unsigned long flags;
+       int block;
+#define NVKM_NOTIFY_DROP 0
+#define NVKM_NOTIFY_KEEP 1
+       int (*func)(struct nvkm_notify *);
+
+       /* set by nvkm_event ctor */
+       u32 types;
+       int index;
+       u32 size;
+
+       struct work_struct work;
+       /* this is const for a *very* good reason - the data might be on the
+        * stack from an irq handler.  if you're not core/notify.c then you
+        * should probably think twice before casting it away...
+        */
+       const void *data;
+};
+
+int  nvkm_notify_init(struct nvkm_object *, struct nvkm_event *,
+                     int (*func)(struct nvkm_notify *), bool work,
+                     void *data, u32 size, u32 reply,
+                     struct nvkm_notify *);
+void nvkm_notify_fini(struct nvkm_notify *);
+void nvkm_notify_get(struct nvkm_notify *);
+void nvkm_notify_put(struct nvkm_notify *);
+void nvkm_notify_send(struct nvkm_notify *, void *data, u32 size);
+#endif
diff --git a/drivers/gpu/drm/nouveau/include/nvkm/core/object.h b/drivers/gpu/drm/nouveau/include/nvkm/core/object.h
new file mode 100644 (file)
index 0000000..6e3cd39
--- /dev/null
@@ -0,0 +1,203 @@
+#ifndef __NVKM_OBJECT_H__
+#define __NVKM_OBJECT_H__
+#include <core/os.h>
+#include <core/printk.h>
+
+#define NV_PARENT_CLASS 0x80000000
+#define NV_NAMEDB_CLASS 0x40000000
+#define NV_CLIENT_CLASS 0x20000000
+#define NV_SUBDEV_CLASS 0x10000000
+#define NV_ENGINE_CLASS 0x08000000
+#define NV_MEMOBJ_CLASS 0x04000000
+#define NV_GPUOBJ_CLASS 0x02000000
+#define NV_ENGCTX_CLASS 0x01000000
+#define NV_OBJECT_CLASS 0x0000ffff
+
+struct nvkm_object {
+       struct nvkm_oclass *oclass;
+       struct nvkm_object *parent;
+       struct nvkm_engine *engine;
+       atomic_t refcount;
+       atomic_t usecount;
+#if CONFIG_NOUVEAU_DEBUG >= NV_DBG_PARANOIA
+#define NVKM_OBJECT_MAGIC 0x75ef0bad
+       struct list_head list;
+       u32 _magic;
+#endif
+};
+
+static inline struct nvkm_object *
+nv_object(void *obj)
+{
+#if CONFIG_NOUVEAU_DEBUG >= NV_DBG_PARANOIA
+       if (likely(obj)) {
+               struct nvkm_object *object = obj;
+               if (unlikely(object->_magic != NVKM_OBJECT_MAGIC))
+                       nv_assert("BAD CAST -> NvObject, invalid magic");
+       }
+#endif
+       return obj;
+}
+
+#define nvkm_object_create(p,e,c,s,d)                                       \
+       nvkm_object_create_((p), (e), (c), (s), sizeof(**d), (void **)d)
+int  nvkm_object_create_(struct nvkm_object *, struct nvkm_object *,
+                           struct nvkm_oclass *, u32, int size, void **);
+void nvkm_object_destroy(struct nvkm_object *);
+int  nvkm_object_init(struct nvkm_object *);
+int  nvkm_object_fini(struct nvkm_object *, bool suspend);
+
+int _nvkm_object_ctor(struct nvkm_object *, struct nvkm_object *,
+                        struct nvkm_oclass *, void *, u32,
+                        struct nvkm_object **);
+
+extern struct nvkm_ofuncs nvkm_object_ofuncs;
+
+/* Don't allocate dynamically, because lockdep needs lock_class_keys to be in
+ * ".data". */
+struct nvkm_oclass {
+       u32 handle;
+       struct nvkm_ofuncs * const ofuncs;
+       struct nvkm_omthds * const omthds;
+       struct lock_class_key lock_class_key;
+};
+
+#define nv_oclass(o)    nv_object(o)->oclass
+#define nv_hclass(o)    nv_oclass(o)->handle
+#define nv_iclass(o,i) (nv_hclass(o) & (i))
+#define nv_mclass(o)    nv_iclass(o, NV_OBJECT_CLASS)
+
+static inline struct nvkm_object *
+nv_pclass(struct nvkm_object *parent, u32 oclass)
+{
+       while (parent && !nv_iclass(parent, oclass))
+               parent = parent->parent;
+       return parent;
+}
+
+struct nvkm_omthds {
+       u32 start;
+       u32 limit;
+       int (*call)(struct nvkm_object *, u32, void *, u32);
+};
+
+struct nvkm_event;
+struct nvkm_ofuncs {
+       int  (*ctor)(struct nvkm_object *, struct nvkm_object *,
+                    struct nvkm_oclass *, void *data, u32 size,
+                    struct nvkm_object **);
+       void (*dtor)(struct nvkm_object *);
+       int  (*init)(struct nvkm_object *);
+       int  (*fini)(struct nvkm_object *, bool suspend);
+       int  (*mthd)(struct nvkm_object *, u32, void *, u32);
+       int  (*ntfy)(struct nvkm_object *, u32, struct nvkm_event **);
+       int  (* map)(struct nvkm_object *, u64 *, u32 *);
+       u8   (*rd08)(struct nvkm_object *, u64 offset);
+       u16  (*rd16)(struct nvkm_object *, u64 offset);
+       u32  (*rd32)(struct nvkm_object *, u64 offset);
+       void (*wr08)(struct nvkm_object *, u64 offset, u8 data);
+       void (*wr16)(struct nvkm_object *, u64 offset, u16 data);
+       void (*wr32)(struct nvkm_object *, u64 offset, u32 data);
+};
+
+static inline struct nvkm_ofuncs *
+nv_ofuncs(void *obj)
+{
+       return nv_oclass(obj)->ofuncs;
+}
+
+int  nvkm_object_ctor(struct nvkm_object *, struct nvkm_object *,
+                     struct nvkm_oclass *, void *, u32,
+                     struct nvkm_object **);
+void nvkm_object_ref(struct nvkm_object *, struct nvkm_object **);
+int  nvkm_object_inc(struct nvkm_object *);
+int  nvkm_object_dec(struct nvkm_object *, bool suspend);
+void nvkm_object_debug(void);
+
+static inline int
+nv_exec(void *obj, u32 mthd, void *data, u32 size)
+{
+       struct nvkm_omthds *method = nv_oclass(obj)->omthds;
+
+       while (method && method->call) {
+               if (mthd >= method->start && mthd <= method->limit)
+                       return method->call(obj, mthd, data, size);
+               method++;
+       }
+
+       return -EINVAL;
+}
+
+static inline int
+nv_call(void *obj, u32 mthd, u32 data)
+{
+       return nv_exec(obj, mthd, &data, sizeof(data));
+}
+
+static inline u8
+nv_ro08(void *obj, u64 addr)
+{
+       u8 data = nv_ofuncs(obj)->rd08(obj, addr);
+       nv_spam(obj, "nv_ro08 0x%08llx 0x%02x\n", addr, data);
+       return data;
+}
+
+static inline u16
+nv_ro16(void *obj, u64 addr)
+{
+       u16 data = nv_ofuncs(obj)->rd16(obj, addr);
+       nv_spam(obj, "nv_ro16 0x%08llx 0x%04x\n", addr, data);
+       return data;
+}
+
+static inline u32
+nv_ro32(void *obj, u64 addr)
+{
+       u32 data = nv_ofuncs(obj)->rd32(obj, addr);
+       nv_spam(obj, "nv_ro32 0x%08llx 0x%08x\n", addr, data);
+       return data;
+}
+
+static inline void
+nv_wo08(void *obj, u64 addr, u8 data)
+{
+       nv_spam(obj, "nv_wo08 0x%08llx 0x%02x\n", addr, data);
+       nv_ofuncs(obj)->wr08(obj, addr, data);
+}
+
+static inline void
+nv_wo16(void *obj, u64 addr, u16 data)
+{
+       nv_spam(obj, "nv_wo16 0x%08llx 0x%04x\n", addr, data);
+       nv_ofuncs(obj)->wr16(obj, addr, data);
+}
+
+static inline void
+nv_wo32(void *obj, u64 addr, u32 data)
+{
+       nv_spam(obj, "nv_wo32 0x%08llx 0x%08x\n", addr, data);
+       nv_ofuncs(obj)->wr32(obj, addr, data);
+}
+
+static inline u32
+nv_mo32(void *obj, u64 addr, u32 mask, u32 data)
+{
+       u32 temp = nv_ro32(obj, addr);
+       nv_wo32(obj, addr, (temp & ~mask) | data);
+       return temp;
+}
+
+static inline int
+nv_memcmp(void *obj, u32 addr, const char *str, u32 len)
+{
+       unsigned char c1, c2;
+
+       while (len--) {
+               c1 = nv_ro08(obj, addr++);
+               c2 = *(str++);
+               if (c1 != c2)
+                       return c1 - c2;
+       }
+       return 0;
+}
+#endif
diff --git a/drivers/gpu/drm/nouveau/include/nvkm/core/option.h b/drivers/gpu/drm/nouveau/include/nvkm/core/option.h
new file mode 100644 (file)
index 0000000..532bfa8
--- /dev/null
@@ -0,0 +1,17 @@
+#ifndef __NVKM_OPTION_H__
+#define __NVKM_OPTION_H__
+#include <core/os.h>
+
+const char *nvkm_stropt(const char *optstr, const char *opt, int *len);
+bool nvkm_boolopt(const char *optstr, const char *opt, bool value);
+int  nvkm_dbgopt(const char *optstr, const char *sub);
+
+/* compares unterminated string 'str' with zero-terminated string 'cmp' */
+static inline int
+strncasecmpz(const char *str, const char *cmp, size_t len)
+{
+       if (strlen(cmp) != len)
+               return len;
+       return strncasecmp(str, cmp, len);
+}
+#endif
diff --git a/drivers/gpu/drm/nouveau/include/nvkm/core/os.h b/drivers/gpu/drm/nouveau/include/nvkm/core/os.h
new file mode 100644 (file)
index 0000000..cd57e23
--- /dev/null
@@ -0,0 +1,4 @@
+#ifndef __NVKM_OS_H__
+#define __NVKM_OS_H__
+#include <nvif/os.h>
+#endif
diff --git a/drivers/gpu/drm/nouveau/include/nvkm/core/parent.h b/drivers/gpu/drm/nouveau/include/nvkm/core/parent.h
new file mode 100644 (file)
index 0000000..837e4fe
--- /dev/null
@@ -0,0 +1,58 @@
+#ifndef __NVKM_PARENT_H__
+#define __NVKM_PARENT_H__
+#include <core/object.h>
+
+struct nvkm_sclass {
+       struct nvkm_sclass *sclass;
+       struct nvkm_engine *engine;
+       struct nvkm_oclass *oclass;
+};
+
+struct nvkm_parent {
+       struct nvkm_object object;
+
+       struct nvkm_sclass *sclass;
+       u64 engine;
+
+       int  (*context_attach)(struct nvkm_object *, struct nvkm_object *);
+       int  (*context_detach)(struct nvkm_object *, bool suspend,
+                              struct nvkm_object *);
+
+       int  (*object_attach)(struct nvkm_object *parent,
+                             struct nvkm_object *object, u32 name);
+       void (*object_detach)(struct nvkm_object *parent, int cookie);
+};
+
+static inline struct nvkm_parent *
+nv_parent(void *obj)
+{
+#if CONFIG_NOUVEAU_DEBUG >= NV_DBG_PARANOIA
+       if (unlikely(!(nv_iclass(obj, NV_PARENT_CLASS))))
+               nv_assert("BAD CAST -> NvParent, %08x", nv_hclass(obj));
+#endif
+       return obj;
+}
+
+#define nvkm_parent_create(p,e,c,v,s,m,d)                                   \
+       nvkm_parent_create_((p), (e), (c), (v), (s), (m),                   \
+                              sizeof(**d), (void **)d)
+#define nvkm_parent_init(p)                                                 \
+       nvkm_object_init(&(p)->object)
+#define nvkm_parent_fini(p,s)                                               \
+       nvkm_object_fini(&(p)->object, (s))
+
+int  nvkm_parent_create_(struct nvkm_object *, struct nvkm_object *,
+                           struct nvkm_oclass *, u32 pclass,
+                           struct nvkm_oclass *, u64 engcls,
+                           int size, void **);
+void nvkm_parent_destroy(struct nvkm_parent *);
+
+void _nvkm_parent_dtor(struct nvkm_object *);
+#define _nvkm_parent_init nvkm_object_init
+#define _nvkm_parent_fini nvkm_object_fini
+
+int nvkm_parent_sclass(struct nvkm_object *, u16 handle,
+                      struct nvkm_object **pengine,
+                      struct nvkm_oclass **poclass);
+int nvkm_parent_lclass(struct nvkm_object *, u32 *, int);
+#endif
diff --git a/drivers/gpu/drm/nouveau/include/nvkm/core/printk.h b/drivers/gpu/drm/nouveau/include/nvkm/core/printk.h
new file mode 100644 (file)
index 0000000..8364817
--- /dev/null
@@ -0,0 +1,29 @@
+#ifndef __NVKM_PRINTK_H__
+#define __NVKM_PRINTK_H__
+#include <core/os.h>
+#include <core/debug.h>
+struct nvkm_object;
+
+void __printf(3, 4)
+nv_printk_(struct nvkm_object *, int, const char *, ...);
+
+#define nv_printk(o,l,f,a...) do {                                             \
+       if (NV_DBG_##l <= CONFIG_NOUVEAU_DEBUG)                                \
+               nv_printk_(nv_object(o), NV_DBG_##l, f, ##a);                  \
+} while(0)
+
+#define nv_fatal(o,f,a...) nv_printk((o), FATAL, f, ##a)
+#define nv_error(o,f,a...) nv_printk((o), ERROR, f, ##a)
+#define nv_warn(o,f,a...) nv_printk((o), WARN, f, ##a)
+#define nv_info(o,f,a...) nv_printk((o), INFO, f, ##a)
+#define nv_debug(o,f,a...) nv_printk((o), DEBUG, f, ##a)
+#define nv_trace(o,f,a...) nv_printk((o), TRACE, f, ##a)
+#define nv_spam(o,f,a...) nv_printk((o), SPAM, f, ##a)
+#define nv_ioctl(o,f,a...) nv_trace(nvkm_client(o), "ioctl: "f, ##a)
+
+#define nv_assert(f,a...) do {                                                 \
+       if (NV_DBG_FATAL <= CONFIG_NOUVEAU_DEBUG)                              \
+               nv_printk_(NULL, NV_DBG_FATAL, f "\n", ##a);                   \
+       BUG_ON(1);                                                             \
+} while(0)
+#endif
diff --git a/drivers/gpu/drm/nouveau/include/nvkm/core/ramht.h b/drivers/gpu/drm/nouveau/include/nvkm/core/ramht.h
new file mode 100644 (file)
index 0000000..cc132ea
--- /dev/null
@@ -0,0 +1,20 @@
+#ifndef __NVKM_RAMHT_H__
+#define __NVKM_RAMHT_H__
+#include <core/gpuobj.h>
+
+struct nvkm_ramht {
+       struct nvkm_gpuobj gpuobj;
+       int bits;
+};
+
+int  nvkm_ramht_insert(struct nvkm_ramht *, int chid, u32 handle, u32 context);
+void nvkm_ramht_remove(struct nvkm_ramht *, int cookie);
+int  nvkm_ramht_new(struct nvkm_object *, struct nvkm_object *, u32 size,
+                   u32 align, struct nvkm_ramht **);
+
+static inline void
+nvkm_ramht_ref(struct nvkm_ramht *obj, struct nvkm_ramht **ref)
+{
+       nvkm_gpuobj_ref(&obj->gpuobj, (struct nvkm_gpuobj **)ref);
+}
+#endif
diff --git a/drivers/gpu/drm/nouveau/include/nvkm/core/subdev.h b/drivers/gpu/drm/nouveau/include/nvkm/core/subdev.h
new file mode 100644 (file)
index 0000000..6fdc391
--- /dev/null
@@ -0,0 +1,119 @@
+#ifndef __NVKM_SUBDEV_H__
+#define __NVKM_SUBDEV_H__
+#include <core/object.h>
+#include <core/devidx.h>
+
+#define NV_SUBDEV_(sub,var) (NV_SUBDEV_CLASS | ((var) << 8) | (sub))
+#define NV_SUBDEV(name,var)  NV_SUBDEV_(NVDEV_SUBDEV_##name, (var))
+
+struct nvkm_subdev {
+       struct nvkm_object object;
+       struct mutex mutex;
+       const char *name;
+       void __iomem *mmio;
+       u32 debug;
+       u32 unit;
+
+       void (*intr)(struct nvkm_subdev *);
+};
+
+static inline struct nvkm_subdev *
+nv_subdev(void *obj)
+{
+#if CONFIG_NOUVEAU_DEBUG >= NV_DBG_PARANOIA
+       if (unlikely(!nv_iclass(obj, NV_SUBDEV_CLASS)))
+               nv_assert("BAD CAST -> NvSubDev, %08x", nv_hclass(obj));
+#endif
+       return obj;
+}
+
+static inline int
+nv_subidx(struct nvkm_subdev *subdev)
+{
+       return nv_hclass(subdev) & 0xff;
+}
+
+struct nvkm_subdev *nvkm_subdev(void *obj, int idx);
+
+#define nvkm_subdev_create(p,e,o,v,s,f,d)                                   \
+       nvkm_subdev_create_((p), (e), (o), (v), (s), (f),                   \
+                              sizeof(**d),(void **)d)
+
+int  nvkm_subdev_create_(struct nvkm_object *, struct nvkm_object *,
+                           struct nvkm_oclass *, u32 pclass,
+                           const char *sname, const char *fname,
+                           int size, void **);
+void nvkm_subdev_destroy(struct nvkm_subdev *);
+int  nvkm_subdev_init(struct nvkm_subdev *);
+int  nvkm_subdev_fini(struct nvkm_subdev *, bool suspend);
+void nvkm_subdev_reset(struct nvkm_object *);
+
+void _nvkm_subdev_dtor(struct nvkm_object *);
+int  _nvkm_subdev_init(struct nvkm_object *);
+int  _nvkm_subdev_fini(struct nvkm_object *, bool suspend);
+
+#define s_printk(s,l,f,a...) do {                                              \
+       if ((s)->debug >= OS_DBG_##l) {                                        \
+               nv_printk((s)->base.parent, (s)->name, l, f, ##a);             \
+       }                                                                      \
+} while(0)
+
+static inline u8
+nv_rd08(void *obj, u32 addr)
+{
+       struct nvkm_subdev *subdev = nv_subdev(obj);
+       u8 data = ioread8(subdev->mmio + addr);
+       nv_spam(subdev, "nv_rd08 0x%06x 0x%02x\n", addr, data);
+       return data;
+}
+
+static inline u16
+nv_rd16(void *obj, u32 addr)
+{
+       struct nvkm_subdev *subdev = nv_subdev(obj);
+       u16 data = ioread16_native(subdev->mmio + addr);
+       nv_spam(subdev, "nv_rd16 0x%06x 0x%04x\n", addr, data);
+       return data;
+}
+
+static inline u32
+nv_rd32(void *obj, u32 addr)
+{
+       struct nvkm_subdev *subdev = nv_subdev(obj);
+       u32 data = ioread32_native(subdev->mmio + addr);
+       nv_spam(subdev, "nv_rd32 0x%06x 0x%08x\n", addr, data);
+       return data;
+}
+
+static inline void
+nv_wr08(void *obj, u32 addr, u8 data)
+{
+       struct nvkm_subdev *subdev = nv_subdev(obj);
+       nv_spam(subdev, "nv_wr08 0x%06x 0x%02x\n", addr, data);
+       iowrite8(data, subdev->mmio + addr);
+}
+
+static inline void
+nv_wr16(void *obj, u32 addr, u16 data)
+{
+       struct nvkm_subdev *subdev = nv_subdev(obj);
+       nv_spam(subdev, "nv_wr16 0x%06x 0x%04x\n", addr, data);
+       iowrite16_native(data, subdev->mmio + addr);
+}
+
+static inline void
+nv_wr32(void *obj, u32 addr, u32 data)
+{
+       struct nvkm_subdev *subdev = nv_subdev(obj);
+       nv_spam(subdev, "nv_wr32 0x%06x 0x%08x\n", addr, data);
+       iowrite32_native(data, subdev->mmio + addr);
+}
+
+static inline u32
+nv_mask(void *obj, u32 addr, u32 mask, u32 data)
+{
+       u32 temp = nv_rd32(obj, addr);
+       nv_wr32(obj, addr, (temp & ~mask) | data);
+       return temp;
+}
+#endif
diff --git a/drivers/gpu/drm/nouveau/include/nvkm/engine/bsp.h b/drivers/gpu/drm/nouveau/include/nvkm/engine/bsp.h
new file mode 100644 (file)
index 0000000..e489bee
--- /dev/null
@@ -0,0 +1,5 @@
+#ifndef __NVKM_BSP_H__
+#define __NVKM_BSP_H__
+#include <core/engine.h>
+extern struct nvkm_oclass g84_bsp_oclass;
+#endif
diff --git a/drivers/gpu/drm/nouveau/include/nvkm/engine/ce.h b/drivers/gpu/drm/nouveau/include/nvkm/engine/ce.h
new file mode 100644 (file)
index 0000000..7e29c52
--- /dev/null
@@ -0,0 +1,13 @@
+#ifndef __NVKM_CE_H__
+#define __NVKM_CE_H__
+#include <core/engine.h>
+
+void gt215_ce_intr(struct nvkm_subdev *);
+
+extern struct nvkm_oclass gt215_ce_oclass;
+extern struct nvkm_oclass gf100_ce0_oclass;
+extern struct nvkm_oclass gf100_ce1_oclass;
+extern struct nvkm_oclass gk104_ce0_oclass;
+extern struct nvkm_oclass gk104_ce1_oclass;
+extern struct nvkm_oclass gk104_ce2_oclass;
+#endif
diff --git a/drivers/gpu/drm/nouveau/include/nvkm/engine/cipher.h b/drivers/gpu/drm/nouveau/include/nvkm/engine/cipher.h
new file mode 100644 (file)
index 0000000..57c29e9
--- /dev/null
@@ -0,0 +1,5 @@
+#ifndef __NVKM_CIPHER_H__
+#define __NVKM_CIPHER_H__
+#include <core/engine.h>
+extern struct nvkm_oclass g84_cipher_oclass;
+#endif
diff --git a/drivers/gpu/drm/nouveau/include/nvkm/engine/device.h b/drivers/gpu/drm/nouveau/include/nvkm/engine/device.h
new file mode 100644 (file)
index 0000000..5d4805e
--- /dev/null
@@ -0,0 +1,30 @@
+#ifndef __NOUVEAU_SUBDEV_DEVICE_H__
+#define __NOUVEAU_SUBDEV_DEVICE_H__
+
+#include <core/device.h>
+
+struct platform_device;
+
+enum nv_bus_type {
+       NOUVEAU_BUS_PCI,
+       NOUVEAU_BUS_PLATFORM,
+};
+
+#define nouveau_device_create(p,t,n,s,c,d,u)                                   \
+       nouveau_device_create_((void *)(p), (t), (n), (s), (c), (d),           \
+                              sizeof(**u), (void **)u)
+
+int  nouveau_device_create_(void *, enum nv_bus_type type, u64 name,
+                           const char *sname, const char *cfg, const char *dbg,
+                           int, void **);
+
+int nv04_identify(struct nouveau_device *);
+int nv10_identify(struct nouveau_device *);
+int nv20_identify(struct nouveau_device *);
+int nv30_identify(struct nouveau_device *);
+int nv40_identify(struct nouveau_device *);
+int nv50_identify(struct nouveau_device *);
+int nvc0_identify(struct nouveau_device *);
+int nve0_identify(struct nouveau_device *);
+int gm100_identify(struct nouveau_device *);
+#endif
diff --git a/drivers/gpu/drm/nouveau/include/nvkm/engine/disp.h b/drivers/gpu/drm/nouveau/include/nvkm/engine/disp.h
new file mode 100644 (file)
index 0000000..a5e1ed8
--- /dev/null
@@ -0,0 +1,32 @@
+#ifndef __NVKM_DISP_H__
+#define __NVKM_DISP_H__
+#include <core/engine.h>
+#include <core/event.h>
+
+struct nvkm_disp {
+       struct nvkm_engine base;
+
+       struct list_head outp;
+
+       struct nvkm_event hpd;
+       struct nvkm_event vblank;
+};
+
+static inline struct nvkm_disp *
+nvkm_disp(void *obj)
+{
+       return (void *)nvkm_engine(obj, NVDEV_ENGINE_DISP);
+}
+
+extern struct nvkm_oclass *nv04_disp_oclass;
+extern struct nvkm_oclass *nv50_disp_oclass;
+extern struct nvkm_oclass *g84_disp_oclass;
+extern struct nvkm_oclass *gt200_disp_oclass;
+extern struct nvkm_oclass *g94_disp_oclass;
+extern struct nvkm_oclass *gt215_disp_oclass;
+extern struct nvkm_oclass *gf110_disp_oclass;
+extern struct nvkm_oclass *gk104_disp_oclass;
+extern struct nvkm_oclass *gk110_disp_oclass;
+extern struct nvkm_oclass *gm107_disp_oclass;
+extern struct nvkm_oclass *gm204_disp_oclass;
+#endif
diff --git a/drivers/gpu/drm/nouveau/include/nvkm/engine/dmaobj.h b/drivers/gpu/drm/nouveau/include/nvkm/engine/dmaobj.h
new file mode 100644 (file)
index 0000000..c4fce8a
--- /dev/null
@@ -0,0 +1,26 @@
+#ifndef __NVKM_DMAOBJ_H__
+#define __NVKM_DMAOBJ_H__
+#include <core/engine.h>
+struct nvkm_gpuobj;
+
+struct nvkm_dmaobj {
+       struct nvkm_object base;
+       u32 target;
+       u32 access;
+       u64 start;
+       u64 limit;
+};
+
+struct nvkm_dmaeng {
+       struct nvkm_engine base;
+
+       /* creates a "physical" dma object from a struct nvkm_dmaobj */
+       int (*bind)(struct nvkm_dmaobj *dmaobj, struct nvkm_object *parent,
+                   struct nvkm_gpuobj **);
+};
+
+extern struct nvkm_oclass *nv04_dmaeng_oclass;
+extern struct nvkm_oclass *nv50_dmaeng_oclass;
+extern struct nvkm_oclass *gf100_dmaeng_oclass;
+extern struct nvkm_oclass *gf110_dmaeng_oclass;
+#endif
diff --git a/drivers/gpu/drm/nouveau/include/nvkm/engine/falcon.h b/drivers/gpu/drm/nouveau/include/nvkm/engine/falcon.h
new file mode 100644 (file)
index 0000000..bd38cf9
--- /dev/null
@@ -0,0 +1,81 @@
+#ifndef __NVKM_FALCON_H__
+#define __NVKM_FALCON_H__
+#include <core/engctx.h>
+
+struct nvkm_falcon_chan {
+       struct nvkm_engctx base;
+};
+
+#define nvkm_falcon_context_create(p,e,c,g,s,a,f,d)                         \
+       nvkm_engctx_create((p), (e), (c), (g), (s), (a), (f), (d))
+#define nvkm_falcon_context_destroy(d)                                      \
+       nvkm_engctx_destroy(&(d)->base)
+#define nvkm_falcon_context_init(d)                                         \
+       nvkm_engctx_init(&(d)->base)
+#define nvkm_falcon_context_fini(d,s)                                       \
+       nvkm_engctx_fini(&(d)->base, (s))
+
+#define _nvkm_falcon_context_ctor _nvkm_engctx_ctor
+#define _nvkm_falcon_context_dtor _nvkm_engctx_dtor
+#define _nvkm_falcon_context_init _nvkm_engctx_init
+#define _nvkm_falcon_context_fini _nvkm_engctx_fini
+#define _nvkm_falcon_context_rd32 _nvkm_engctx_rd32
+#define _nvkm_falcon_context_wr32 _nvkm_engctx_wr32
+
+struct nvkm_falcon_data {
+       bool external;
+};
+
+#include <core/engine.h>
+
+struct nvkm_falcon {
+       struct nvkm_engine base;
+
+       u32 addr;
+       u8  version;
+       u8  secret;
+
+       struct nvkm_gpuobj *core;
+       bool external;
+
+       struct {
+               u32 limit;
+               u32 *data;
+               u32  size;
+       } code;
+
+       struct {
+               u32 limit;
+               u32 *data;
+               u32  size;
+       } data;
+};
+
+#define nv_falcon(priv) (&(priv)->base)
+
+#define nvkm_falcon_create(p,e,c,b,d,i,f,r)                                 \
+       nvkm_falcon_create_((p), (e), (c), (b), (d), (i), (f),              \
+                              sizeof(**r),(void **)r)
+#define nvkm_falcon_destroy(p)                                              \
+       nvkm_engine_destroy(&(p)->base)
+#define nvkm_falcon_init(p) ({                                              \
+       struct nvkm_falcon *falcon = (p);                                   \
+       _nvkm_falcon_init(nv_object(falcon));                               \
+})
+#define nvkm_falcon_fini(p,s) ({                                            \
+       struct nvkm_falcon *falcon = (p);                                   \
+       _nvkm_falcon_fini(nv_object(falcon), (s));                          \
+})
+
+int nvkm_falcon_create_(struct nvkm_object *, struct nvkm_object *,
+                          struct nvkm_oclass *, u32, bool, const char *,
+                          const char *, int, void **);
+
+void nvkm_falcon_intr(struct nvkm_subdev *subdev);
+
+#define _nvkm_falcon_dtor _nvkm_engine_dtor
+int  _nvkm_falcon_init(struct nvkm_object *);
+int  _nvkm_falcon_fini(struct nvkm_object *, bool);
+u32  _nvkm_falcon_rd32(struct nvkm_object *, u64);
+void _nvkm_falcon_wr32(struct nvkm_object *, u64, u32);
+#endif
diff --git a/drivers/gpu/drm/nouveau/include/nvkm/engine/fifo.h b/drivers/gpu/drm/nouveau/include/nvkm/engine/fifo.h
new file mode 100644 (file)
index 0000000..05321ce
--- /dev/null
@@ -0,0 +1,126 @@
+#ifndef __NVKM_FIFO_H__
+#define __NVKM_FIFO_H__
+#include <core/namedb.h>
+
+struct nvkm_fifo_chan {
+       struct nvkm_namedb namedb;
+       struct nvkm_dmaobj *pushdma;
+       struct nvkm_gpuobj *pushgpu;
+       void __iomem *user;
+       u64 addr;
+       u32 size;
+       u16 chid;
+       atomic_t refcnt; /* NV04_NVSW_SET_REF */
+};
+
+static inline struct nvkm_fifo_chan *
+nvkm_fifo_chan(void *obj)
+{
+       return (void *)nv_namedb(obj);
+}
+
+#define nvkm_fifo_channel_create(p,e,c,b,a,s,n,m,d)                         \
+       nvkm_fifo_channel_create_((p), (e), (c), (b), (a), (s), (n),        \
+                                    (m), sizeof(**d), (void **)d)
+#define nvkm_fifo_channel_init(p)                                           \
+       nvkm_namedb_init(&(p)->namedb)
+#define nvkm_fifo_channel_fini(p,s)                                         \
+       nvkm_namedb_fini(&(p)->namedb, (s))
+
+int  nvkm_fifo_channel_create_(struct nvkm_object *,
+                                 struct nvkm_object *,
+                                 struct nvkm_oclass *,
+                                 int bar, u32 addr, u32 size, u32 push,
+                                 u64 engmask, int len, void **);
+void nvkm_fifo_channel_destroy(struct nvkm_fifo_chan *);
+
+#define _nvkm_fifo_channel_init _nvkm_namedb_init
+#define _nvkm_fifo_channel_fini _nvkm_namedb_fini
+
+void _nvkm_fifo_channel_dtor(struct nvkm_object *);
+int  _nvkm_fifo_channel_map(struct nvkm_object *, u64 *, u32 *);
+u32  _nvkm_fifo_channel_rd32(struct nvkm_object *, u64);
+void _nvkm_fifo_channel_wr32(struct nvkm_object *, u64, u32);
+int  _nvkm_fifo_channel_ntfy(struct nvkm_object *, u32, struct nvkm_event **);
+
+#include <core/gpuobj.h>
+
+struct nvkm_fifo_base {
+       struct nvkm_gpuobj gpuobj;
+};
+
+#define nvkm_fifo_context_create(p,e,c,g,s,a,f,d)                           \
+       nvkm_gpuobj_create((p), (e), (c), 0, (g), (s), (a), (f), (d))
+#define nvkm_fifo_context_destroy(p)                                        \
+       nvkm_gpuobj_destroy(&(p)->gpuobj)
+#define nvkm_fifo_context_init(p)                                           \
+       nvkm_gpuobj_init(&(p)->gpuobj)
+#define nvkm_fifo_context_fini(p,s)                                         \
+       nvkm_gpuobj_fini(&(p)->gpuobj, (s))
+
+#define _nvkm_fifo_context_dtor _nvkm_gpuobj_dtor
+#define _nvkm_fifo_context_init _nvkm_gpuobj_init
+#define _nvkm_fifo_context_fini _nvkm_gpuobj_fini
+#define _nvkm_fifo_context_rd32 _nvkm_gpuobj_rd32
+#define _nvkm_fifo_context_wr32 _nvkm_gpuobj_wr32
+
+#include <core/engine.h>
+#include <core/event.h>
+
+struct nvkm_fifo {
+       struct nvkm_engine base;
+
+       struct nvkm_event cevent; /* channel creation event */
+       struct nvkm_event uevent; /* async user trigger */
+
+       struct nvkm_object **channel;
+       spinlock_t lock;
+       u16 min;
+       u16 max;
+
+       int  (*chid)(struct nvkm_fifo *, struct nvkm_object *);
+       void (*pause)(struct nvkm_fifo *, unsigned long *);
+       void (*start)(struct nvkm_fifo *, unsigned long *);
+};
+
+static inline struct nvkm_fifo *
+nvkm_fifo(void *obj)
+{
+       return (void *)nvkm_engine(obj, NVDEV_ENGINE_FIFO);
+}
+
+#define nvkm_fifo_create(o,e,c,fc,lc,d)                                     \
+       nvkm_fifo_create_((o), (e), (c), (fc), (lc), sizeof(**d), (void **)d)
+#define nvkm_fifo_init(p)                                                   \
+       nvkm_engine_init(&(p)->base)
+#define nvkm_fifo_fini(p,s)                                                 \
+       nvkm_engine_fini(&(p)->base, (s))
+
+int nvkm_fifo_create_(struct nvkm_object *, struct nvkm_object *,
+                        struct nvkm_oclass *, int min, int max,
+                        int size, void **);
+void nvkm_fifo_destroy(struct nvkm_fifo *);
+const char *
+nvkm_client_name_for_fifo_chid(struct nvkm_fifo *fifo, u32 chid);
+
+#define _nvkm_fifo_init _nvkm_engine_init
+#define _nvkm_fifo_fini _nvkm_engine_fini
+
+extern struct nvkm_oclass *nv04_fifo_oclass;
+extern struct nvkm_oclass *nv10_fifo_oclass;
+extern struct nvkm_oclass *nv17_fifo_oclass;
+extern struct nvkm_oclass *nv40_fifo_oclass;
+extern struct nvkm_oclass *nv50_fifo_oclass;
+extern struct nvkm_oclass *g84_fifo_oclass;
+extern struct nvkm_oclass *gf100_fifo_oclass;
+extern struct nvkm_oclass *gk104_fifo_oclass;
+extern struct nvkm_oclass *gk20a_fifo_oclass;
+extern struct nvkm_oclass *gk208_fifo_oclass;
+
+int  nvkm_fifo_uevent_ctor(struct nvkm_object *, void *, u32,
+                          struct nvkm_notify *);
+void nvkm_fifo_uevent(struct nvkm_fifo *);
+
+void nv04_fifo_intr(struct nvkm_subdev *);
+int  nv04_fifo_context_attach(struct nvkm_object *, struct nvkm_object *);
+#endif
diff --git a/drivers/gpu/drm/nouveau/include/nvkm/engine/gr.h b/drivers/gpu/drm/nouveau/include/nvkm/engine/gr.h
new file mode 100644 (file)
index 0000000..93ef1f2
--- /dev/null
@@ -0,0 +1,86 @@
+#ifndef __NVKM_GR_H__
+#define __NVKM_GR_H__
+#include <core/engctx.h>
+
+struct nvkm_gr_chan {
+       struct nvkm_engctx base;
+};
+
+#define nvkm_gr_context_create(p,e,c,g,s,a,f,d)                          \
+       nvkm_engctx_create((p), (e), (c), (g), (s), (a), (f), (d))
+#define nvkm_gr_context_destroy(d)                                       \
+       nvkm_engctx_destroy(&(d)->base)
+#define nvkm_gr_context_init(d)                                          \
+       nvkm_engctx_init(&(d)->base)
+#define nvkm_gr_context_fini(d,s)                                        \
+       nvkm_engctx_fini(&(d)->base, (s))
+
+#define _nvkm_gr_context_dtor _nvkm_engctx_dtor
+#define _nvkm_gr_context_init _nvkm_engctx_init
+#define _nvkm_gr_context_fini _nvkm_engctx_fini
+#define _nvkm_gr_context_rd32 _nvkm_engctx_rd32
+#define _nvkm_gr_context_wr32 _nvkm_engctx_wr32
+
+#include <core/engine.h>
+
+struct nvkm_gr {
+       struct nvkm_engine base;
+
+       /* Returns chipset-specific counts of units packed into an u64.
+        */
+       u64 (*units)(struct nvkm_gr *);
+};
+
+static inline struct nvkm_gr *
+nvkm_gr(void *obj)
+{
+       return (void *)nvkm_engine(obj, NVDEV_ENGINE_GR);
+}
+
+#define nvkm_gr_create(p,e,c,y,d)                                        \
+       nvkm_engine_create((p), (e), (c), (y), "PGR", "graphics", (d))
+#define nvkm_gr_destroy(d)                                               \
+       nvkm_engine_destroy(&(d)->base)
+#define nvkm_gr_init(d)                                                  \
+       nvkm_engine_init(&(d)->base)
+#define nvkm_gr_fini(d,s)                                                \
+       nvkm_engine_fini(&(d)->base, (s))
+
+#define _nvkm_gr_dtor _nvkm_engine_dtor
+#define _nvkm_gr_init _nvkm_engine_init
+#define _nvkm_gr_fini _nvkm_engine_fini
+
+extern struct nvkm_oclass nv04_gr_oclass;
+extern struct nvkm_oclass nv10_gr_oclass;
+extern struct nvkm_oclass nv20_gr_oclass;
+extern struct nvkm_oclass nv25_gr_oclass;
+extern struct nvkm_oclass nv2a_gr_oclass;
+extern struct nvkm_oclass nv30_gr_oclass;
+extern struct nvkm_oclass nv34_gr_oclass;
+extern struct nvkm_oclass nv35_gr_oclass;
+extern struct nvkm_oclass nv40_gr_oclass;
+extern struct nvkm_oclass nv50_gr_oclass;
+extern struct nvkm_oclass *gf100_gr_oclass;
+extern struct nvkm_oclass *gf108_gr_oclass;
+extern struct nvkm_oclass *gf104_gr_oclass;
+extern struct nvkm_oclass *gf110_gr_oclass;
+extern struct nvkm_oclass *gf117_gr_oclass;
+extern struct nvkm_oclass *gf119_gr_oclass;
+extern struct nvkm_oclass *gk104_gr_oclass;
+extern struct nvkm_oclass *gk20a_gr_oclass;
+extern struct nvkm_oclass *gk110_gr_oclass;
+extern struct nvkm_oclass *gk110b_gr_oclass;
+extern struct nvkm_oclass *gk208_gr_oclass;
+extern struct nvkm_oclass *gm107_gr_oclass;
+
+#include <core/enum.h>
+
+extern const struct nvkm_bitfield nv04_gr_nsource[];
+extern struct nvkm_ofuncs nv04_gr_ofuncs;
+bool nv04_gr_idle(void *obj);
+
+extern const struct nvkm_bitfield nv10_gr_intr_name[];
+extern const struct nvkm_bitfield nv10_gr_nstatus[];
+
+extern const struct nvkm_enum nv50_data_error_names[];
+#endif
diff --git a/drivers/gpu/drm/nouveau/include/nvkm/engine/mpeg.h b/drivers/gpu/drm/nouveau/include/nvkm/engine/mpeg.h
new file mode 100644 (file)
index 0000000..4e500b3
--- /dev/null
@@ -0,0 +1,62 @@
+#ifndef __NVKM_MPEG_H__
+#define __NVKM_MPEG_H__
+#include <core/engctx.h>
+
+struct nvkm_mpeg_chan {
+       struct nvkm_engctx base;
+};
+
+#define nvkm_mpeg_context_create(p,e,c,g,s,a,f,d)                           \
+       nvkm_engctx_create((p), (e), (c), (g), (s), (a), (f), (d))
+#define nvkm_mpeg_context_destroy(d)                                        \
+       nvkm_engctx_destroy(&(d)->base)
+#define nvkm_mpeg_context_init(d)                                           \
+       nvkm_engctx_init(&(d)->base)
+#define nvkm_mpeg_context_fini(d,s)                                         \
+       nvkm_engctx_fini(&(d)->base, (s))
+
+#define _nvkm_mpeg_context_dtor _nvkm_engctx_dtor
+#define _nvkm_mpeg_context_init _nvkm_engctx_init
+#define _nvkm_mpeg_context_fini _nvkm_engctx_fini
+#define _nvkm_mpeg_context_rd32 _nvkm_engctx_rd32
+#define _nvkm_mpeg_context_wr32 _nvkm_engctx_wr32
+
+#include <core/engine.h>
+
+struct nvkm_mpeg {
+       struct nvkm_engine base;
+};
+
+#define nvkm_mpeg_create(p,e,c,d)                                           \
+       nvkm_engine_create((p), (e), (c), true, "PMPEG", "mpeg", (d))
+#define nvkm_mpeg_destroy(d)                                                \
+       nvkm_engine_destroy(&(d)->base)
+#define nvkm_mpeg_init(d)                                                   \
+       nvkm_engine_init(&(d)->base)
+#define nvkm_mpeg_fini(d,s)                                                 \
+       nvkm_engine_fini(&(d)->base, (s))
+
+#define _nvkm_mpeg_dtor _nvkm_engine_dtor
+#define _nvkm_mpeg_init _nvkm_engine_init
+#define _nvkm_mpeg_fini _nvkm_engine_fini
+
+extern struct nvkm_oclass nv31_mpeg_oclass;
+extern struct nvkm_oclass nv40_mpeg_oclass;
+extern struct nvkm_oclass nv44_mpeg_oclass;
+extern struct nvkm_oclass nv50_mpeg_oclass;
+extern struct nvkm_oclass g84_mpeg_oclass;
+extern struct nvkm_ofuncs nv31_mpeg_ofuncs;
+extern struct nvkm_oclass nv31_mpeg_cclass;
+extern struct nvkm_oclass nv31_mpeg_sclass[];
+extern struct nvkm_oclass nv40_mpeg_sclass[];
+void nv31_mpeg_intr(struct nvkm_subdev *);
+void nv31_mpeg_tile_prog(struct nvkm_engine *, int);
+int  nv31_mpeg_init(struct nvkm_object *);
+
+extern struct nvkm_ofuncs nv50_mpeg_ofuncs;
+int  nv50_mpeg_context_ctor(struct nvkm_object *, struct nvkm_object *,
+                           struct nvkm_oclass *, void *, u32,
+                           struct nvkm_object **);
+void nv50_mpeg_intr(struct nvkm_subdev *);
+int  nv50_mpeg_init(struct nvkm_object *);
+#endif
diff --git a/drivers/gpu/drm/nouveau/include/nvkm/engine/mspdec.h b/drivers/gpu/drm/nouveau/include/nvkm/engine/mspdec.h
new file mode 100644 (file)
index 0000000..54b7672
--- /dev/null
@@ -0,0 +1,7 @@
+#ifndef __NVKM_MSPDEC_H__
+#define __NVKM_MSPDEC_H__
+#include <core/engine.h>
+extern struct nvkm_oclass g98_mspdec_oclass;
+extern struct nvkm_oclass gf100_mspdec_oclass;
+extern struct nvkm_oclass gk104_mspdec_oclass;
+#endif
diff --git a/drivers/gpu/drm/nouveau/include/nvkm/engine/msppp.h b/drivers/gpu/drm/nouveau/include/nvkm/engine/msppp.h
new file mode 100644 (file)
index 0000000..c6c69d0
--- /dev/null
@@ -0,0 +1,6 @@
+#ifndef __NVKM_MSPPP_H__
+#define __NVKM_MSPPP_H__
+#include <core/engine.h>
+extern struct nvkm_oclass g98_msppp_oclass;
+extern struct nvkm_oclass gf100_msppp_oclass;
+#endif
diff --git a/drivers/gpu/drm/nouveau/include/nvkm/engine/msvld.h b/drivers/gpu/drm/nouveau/include/nvkm/engine/msvld.h
new file mode 100644 (file)
index 0000000..1f193b7
--- /dev/null
@@ -0,0 +1,7 @@
+#ifndef __NVKM_MSVLD_H__
+#define __NVKM_MSVLD_H__
+#include <core/engine.h>
+extern struct nvkm_oclass g98_msvld_oclass;
+extern struct nvkm_oclass gf100_msvld_oclass;
+extern struct nvkm_oclass gk104_msvld_oclass;
+#endif
diff --git a/drivers/gpu/drm/nouveau/include/nvkm/engine/pm.h b/drivers/gpu/drm/nouveau/include/nvkm/engine/pm.h
new file mode 100644 (file)
index 0000000..93181bb
--- /dev/null
@@ -0,0 +1,34 @@
+#ifndef __NVKM_PM_H__
+#define __NVKM_PM_H__
+#include <core/engine.h>
+
+struct nvkm_perfdom;
+struct nvkm_perfctr;
+struct nvkm_pm {
+       struct nvkm_engine base;
+
+       struct nvkm_perfctx *context;
+       void *profile_data;
+
+       struct list_head domains;
+       u32 sequence;
+
+       /*XXX: temp for daemon backend */
+       u32 pwr[8];
+       u32 last;
+};
+
+static inline struct nvkm_pm *
+nvkm_pm(void *obj)
+{
+       return (void *)nvkm_engine(obj, NVDEV_ENGINE_PM);
+}
+
+extern struct nvkm_oclass *nv40_pm_oclass;
+extern struct nvkm_oclass *nv50_pm_oclass;
+extern struct nvkm_oclass *g84_pm_oclass;
+extern struct nvkm_oclass *gt215_pm_oclass;
+extern struct nvkm_oclass gf100_pm_oclass;
+extern struct nvkm_oclass gk104_pm_oclass;
+extern struct nvkm_oclass gk110_pm_oclass;
+#endif
diff --git a/drivers/gpu/drm/nouveau/include/nvkm/engine/sec.h b/drivers/gpu/drm/nouveau/include/nvkm/engine/sec.h
new file mode 100644 (file)
index 0000000..44590a2
--- /dev/null
@@ -0,0 +1,5 @@
+#ifndef __NVKM_SEC_H__
+#define __NVKM_SEC_H__
+#include <core/engine.h>
+extern struct nvkm_oclass g98_sec_oclass;
+#endif
diff --git a/drivers/gpu/drm/nouveau/include/nvkm/engine/sw.h b/drivers/gpu/drm/nouveau/include/nvkm/engine/sw.h
new file mode 100644 (file)
index 0000000..a529013
--- /dev/null
@@ -0,0 +1,50 @@
+#ifndef __NVKM_SW_H__
+#define __NVKM_SW_H__
+#include <core/engctx.h>
+
+struct nvkm_sw_chan {
+       struct nvkm_engctx base;
+
+       int (*flip)(void *);
+       void *flip_data;
+};
+
+#define nvkm_sw_context_create(p,e,c,d)                               \
+       nvkm_engctx_create((p), (e), (c), (p), 0, 0, 0, (d))
+#define nvkm_sw_context_destroy(d)                                    \
+       nvkm_engctx_destroy(&(d)->base)
+#define nvkm_sw_context_init(d)                                       \
+       nvkm_engctx_init(&(d)->base)
+#define nvkm_sw_context_fini(d,s)                                     \
+       nvkm_engctx_fini(&(d)->base, (s))
+
+#define _nvkm_sw_context_dtor _nvkm_engctx_dtor
+#define _nvkm_sw_context_init _nvkm_engctx_init
+#define _nvkm_sw_context_fini _nvkm_engctx_fini
+
+#include <core/engine.h>
+
+struct nvkm_sw {
+       struct nvkm_engine base;
+};
+
+#define nvkm_sw_create(p,e,c,d)                                       \
+       nvkm_engine_create((p), (e), (c), true, "SW", "software", (d))
+#define nvkm_sw_destroy(d)                                            \
+       nvkm_engine_destroy(&(d)->base)
+#define nvkm_sw_init(d)                                               \
+       nvkm_engine_init(&(d)->base)
+#define nvkm_sw_fini(d,s)                                             \
+       nvkm_engine_fini(&(d)->base, (s))
+
+#define _nvkm_sw_dtor _nvkm_engine_dtor
+#define _nvkm_sw_init _nvkm_engine_init
+#define _nvkm_sw_fini _nvkm_engine_fini
+
+extern struct nvkm_oclass *nv04_sw_oclass;
+extern struct nvkm_oclass *nv10_sw_oclass;
+extern struct nvkm_oclass *nv50_sw_oclass;
+extern struct nvkm_oclass *gf100_sw_oclass;
+
+void nv04_sw_intr(struct nvkm_subdev *);
+#endif
diff --git a/drivers/gpu/drm/nouveau/include/nvkm/engine/vp.h b/drivers/gpu/drm/nouveau/include/nvkm/engine/vp.h
new file mode 100644 (file)
index 0000000..7851f18
--- /dev/null
@@ -0,0 +1,5 @@
+#ifndef __NVKM_VP_H__
+#define __NVKM_VP_H__
+#include <core/engine.h>
+extern struct nvkm_oclass g84_vp_oclass;
+#endif
diff --git a/drivers/gpu/drm/nouveau/include/nvkm/engine/xtensa.h b/drivers/gpu/drm/nouveau/include/nvkm/engine/xtensa.h
new file mode 100644 (file)
index 0000000..7a216cc
--- /dev/null
@@ -0,0 +1,35 @@
+#ifndef __NVKM_XTENSA_H__
+#define __NVKM_XTENSA_H__
+#include <core/engine.h>
+struct nvkm_gpuobj;
+
+struct nvkm_xtensa {
+       struct nvkm_engine base;
+
+       u32 addr;
+       struct nvkm_gpuobj *gpu_fw;
+       u32 fifo_val;
+       u32 unkd28;
+};
+
+#define nvkm_xtensa_create(p,e,c,b,d,i,f,r)                            \
+       nvkm_xtensa_create_((p), (e), (c), (b), (d), (i), (f),  \
+                              sizeof(**r),(void **)r)
+
+int _nvkm_xtensa_engctx_ctor(struct nvkm_object *,
+                               struct nvkm_object *,
+                               struct nvkm_oclass *, void *, u32,
+                               struct nvkm_object **);
+
+void _nvkm_xtensa_intr(struct nvkm_subdev *);
+int nvkm_xtensa_create_(struct nvkm_object *,
+                          struct nvkm_object *,
+                          struct nvkm_oclass *, u32, bool,
+                          const char *, const char *,
+                          int, void **);
+#define _nvkm_xtensa_dtor _nvkm_engine_dtor
+int _nvkm_xtensa_init(struct nvkm_object *);
+int _nvkm_xtensa_fini(struct nvkm_object *, bool);
+u32  _nvkm_xtensa_rd32(struct nvkm_object *, u64);
+void _nvkm_xtensa_wr32(struct nvkm_object *, u64, u32);
+#endif
diff --git a/drivers/gpu/drm/nouveau/include/nvkm/subdev/bar.h b/drivers/gpu/drm/nouveau/include/nvkm/subdev/bar.h
new file mode 100644 (file)
index 0000000..c7a007b
--- /dev/null
@@ -0,0 +1,33 @@
+#ifndef __NVKM_BAR_H__
+#define __NVKM_BAR_H__
+#include <core/subdev.h>
+struct nvkm_mem;
+struct nvkm_vma;
+
+struct nvkm_bar {
+       struct nvkm_subdev base;
+
+       int  (*alloc)(struct nvkm_bar *, struct nvkm_object *,
+                     struct nvkm_mem *, struct nvkm_object **);
+
+       int  (*kmap)(struct nvkm_bar *, struct nvkm_mem *, u32 flags,
+                    struct nvkm_vma *);
+       int  (*umap)(struct nvkm_bar *, struct nvkm_mem *, u32 flags,
+                    struct nvkm_vma *);
+       void (*unmap)(struct nvkm_bar *, struct nvkm_vma *);
+       void (*flush)(struct nvkm_bar *);
+
+       /* whether the BAR supports to be ioremapped WC or should be uncached */
+       bool iomap_uncached;
+};
+
+static inline struct nvkm_bar *
+nvkm_bar(void *obj)
+{
+       return (void *)nvkm_subdev(obj, NVDEV_SUBDEV_BAR);
+}
+
+extern struct nvkm_oclass nv50_bar_oclass;
+extern struct nvkm_oclass gf100_bar_oclass;
+extern struct nvkm_oclass gk20a_bar_oclass;
+#endif
diff --git a/drivers/gpu/drm/nouveau/include/nvkm/subdev/bios.h b/drivers/gpu/drm/nouveau/include/nvkm/subdev/bios.h
new file mode 100644 (file)
index 0000000..cef287e
--- /dev/null
@@ -0,0 +1,32 @@
+#ifndef __NVKM_BIOS_H__
+#define __NVKM_BIOS_H__
+#include <core/subdev.h>
+
+struct nvkm_bios {
+       struct nvkm_subdev base;
+       u32 size;
+       u8 *data;
+
+       u32 bmp_offset;
+       u32 bit_offset;
+
+       struct {
+               u8 major;
+               u8 chip;
+               u8 minor;
+               u8 micro;
+               u8 patch;
+       } version;
+};
+
+static inline struct nvkm_bios *
+nvkm_bios(void *obj)
+{
+       return (void *)nvkm_subdev(obj, NVDEV_SUBDEV_VBIOS);
+}
+
+u8  nvbios_checksum(const u8 *data, int size);
+u16 nvbios_findstr(const u8 *data, int size, const char *str, int len);
+
+extern struct nvkm_oclass nvkm_bios_oclass;
+#endif
diff --git a/drivers/gpu/drm/nouveau/include/nvkm/subdev/bios/M0203.h b/drivers/gpu/drm/nouveau/include/nvkm/subdev/bios/M0203.h
new file mode 100644 (file)
index 0000000..cf202c7
--- /dev/null
@@ -0,0 +1,29 @@
+#ifndef __NVBIOS_M0203_H__
+#define __NVBIOS_M0203_H__
+struct nvbios_M0203T {
+#define M0203T_TYPE_RAMCFG 0x00
+       u8  type;
+       u16 pointer;
+};
+
+u32 nvbios_M0203Te(struct nvkm_bios *, u8 *ver, u8 *hdr, u8 *cnt, u8 *len);
+u32 nvbios_M0203Tp(struct nvkm_bios *, u8 *ver, u8 *hdr, u8 *cnt, u8 *len,
+                  struct nvbios_M0203T *);
+
+struct nvbios_M0203E {
+#define M0203E_TYPE_DDR2  0x0
+#define M0203E_TYPE_DDR3  0x1
+#define M0203E_TYPE_GDDR3 0x2
+#define M0203E_TYPE_GDDR5 0x3
+#define M0203E_TYPE_SKIP  0xf
+       u8 type;
+       u8 strap;
+       u8 group;
+};
+
+u32 nvbios_M0203Ee(struct nvkm_bios *, int idx, u8 *ver, u8 *hdr);
+u32 nvbios_M0203Ep(struct nvkm_bios *, int idx, u8 *ver, u8 *hdr,
+                  struct nvbios_M0203E *);
+u32 nvbios_M0203Em(struct nvkm_bios *, u8 ramcfg, u8 *ver, u8 *hdr,
+                  struct nvbios_M0203E *);
+#endif
diff --git a/drivers/gpu/drm/nouveau/include/nvkm/subdev/bios/M0205.h b/drivers/gpu/drm/nouveau/include/nvkm/subdev/bios/M0205.h
new file mode 100644 (file)
index 0000000..d34608f
--- /dev/null
@@ -0,0 +1,29 @@
+#ifndef __NVBIOS_M0205_H__
+#define __NVBIOS_M0205_H__
+struct nvbios_M0205T {
+       u16 freq;
+};
+
+u32 nvbios_M0205Te(struct nvkm_bios *,
+                  u8 *ver, u8 *hdr, u8 *cnt, u8 *len, u8 *snr, u8 *ssz);
+u32 nvbios_M0205Tp(struct nvkm_bios *,
+                  u8 *ver, u8 *hdr, u8 *cnt, u8 *len, u8 *snr, u8 *ssz,
+                  struct nvbios_M0205T *);
+
+struct nvbios_M0205E {
+       u8 type;
+};
+
+u32 nvbios_M0205Ee(struct nvkm_bios *, int idx,
+                  u8 *ver, u8 *hdr, u8 *cnt, u8 *len);
+u32 nvbios_M0205Ep(struct nvkm_bios *, int idx,
+                  u8 *ver, u8 *hdr, u8 *cnt, u8 *len, struct nvbios_M0205E *);
+
+struct nvbios_M0205S {
+       u8 data;
+};
+
+u32 nvbios_M0205Se(struct nvkm_bios *, int ent, int idx, u8 *ver, u8 *hdr);
+u32 nvbios_M0205Sp(struct nvkm_bios *, int ent, int idx, u8 *ver, u8 *hdr,
+                  struct nvbios_M0205S *);
+#endif
diff --git a/drivers/gpu/drm/nouveau/include/nvkm/subdev/bios/M0209.h b/drivers/gpu/drm/nouveau/include/nvkm/subdev/bios/M0209.h
new file mode 100644 (file)
index 0000000..c7ff8d9
--- /dev/null
@@ -0,0 +1,27 @@
+#ifndef __NVBIOS_M0209_H__
+#define __NVBIOS_M0209_H__
+u32 nvbios_M0209Te(struct nvkm_bios *,
+                  u8 *ver, u8 *hdr, u8 *cnt, u8 *len, u8 *snr, u8 *ssz);
+
+struct nvbios_M0209E {
+       u8 v00_40;
+       u8 bits;
+       u8 modulo;
+       u8 v02_40;
+       u8 v02_07;
+       u8 v03;
+};
+
+u32 nvbios_M0209Ee(struct nvkm_bios *, int idx,
+                  u8 *ver, u8 *hdr, u8 *cnt, u8 *len);
+u32 nvbios_M0209Ep(struct nvkm_bios *, int idx,
+                  u8 *ver, u8 *hdr, u8 *cnt, u8 *len, struct nvbios_M0209E *);
+
+struct nvbios_M0209S {
+       u32 data[0x200];
+};
+
+u32 nvbios_M0209Se(struct nvkm_bios *, int ent, int idx, u8 *ver, u8 *hdr);
+u32 nvbios_M0209Sp(struct nvkm_bios *, int ent, int idx, u8 *ver, u8 *hdr,
+                  struct nvbios_M0209S *);
+#endif
diff --git a/drivers/gpu/drm/nouveau/include/nvkm/subdev/bios/P0260.h b/drivers/gpu/drm/nouveau/include/nvkm/subdev/bios/P0260.h
new file mode 100644 (file)
index 0000000..1c1c52e
--- /dev/null
@@ -0,0 +1,21 @@
+#ifndef __NVBIOS_P0260_H__
+#define __NVBIOS_P0260_H__
+u32 nvbios_P0260Te(struct nvkm_bios *,
+                  u8 *ver, u8 *hdr, u8 *cnt, u8 *len, u8 *xnr, u8 *xsz);
+
+struct nvbios_P0260E {
+       u32 data;
+};
+
+u32 nvbios_P0260Ee(struct nvkm_bios *, int idx, u8 *ver, u8 *hdr);
+u32 nvbios_P0260Ep(struct nvkm_bios *, int idx, u8 *ver, u8 *hdr,
+                  struct nvbios_P0260E *);
+
+struct nvbios_P0260X {
+       u32 data;
+};
+
+u32 nvbios_P0260Xe(struct nvkm_bios *, int idx, u8 *ver, u8 *hdr);
+u32 nvbios_P0260Xp(struct nvkm_bios *, int idx, u8 *ver, u8 *hdr,
+                  struct nvbios_P0260X *);
+#endif
diff --git a/drivers/gpu/drm/nouveau/include/nvkm/subdev/bios/bit.h b/drivers/gpu/drm/nouveau/include/nvkm/subdev/bios/bit.h
new file mode 100644 (file)
index 0000000..6711732
--- /dev/null
@@ -0,0 +1,11 @@
+#ifndef __NVBIOS_BIT_H__
+#define __NVBIOS_BIT_H__
+struct bit_entry {
+       u8  id;
+       u8  version;
+       u16 length;
+       u16 offset;
+};
+
+int bit_entry(struct nvkm_bios *, u8 id, struct bit_entry *);
+#endif
diff --git a/drivers/gpu/drm/nouveau/include/nvkm/subdev/bios/bmp.h b/drivers/gpu/drm/nouveau/include/nvkm/subdev/bios/bmp.h
new file mode 100644 (file)
index 0000000..4107aa5
--- /dev/null
@@ -0,0 +1,37 @@
+#ifndef __NVBIOS_BMP_H__
+#define __NVBIOS_BMP_H__
+static inline u16
+bmp_version(struct nvkm_bios *bios)
+{
+       if (bios->bmp_offset) {
+               return nv_ro08(bios, bios->bmp_offset + 5) << 8 |
+                      nv_ro08(bios, bios->bmp_offset + 6);
+       }
+
+       return 0x0000;
+}
+
+static inline u16
+bmp_mem_init_table(struct nvkm_bios *bios)
+{
+       if (bmp_version(bios) >= 0x0300)
+               return nv_ro16(bios, bios->bmp_offset + 24);
+       return 0x0000;
+}
+
+static inline u16
+bmp_sdr_seq_table(struct nvkm_bios *bios)
+{
+       if (bmp_version(bios) >= 0x0300)
+               return nv_ro16(bios, bios->bmp_offset + 26);
+       return 0x0000;
+}
+
+static inline u16
+bmp_ddr_seq_table(struct nvkm_bios *bios)
+{
+       if (bmp_version(bios) >= 0x0300)
+               return nv_ro16(bios, bios->bmp_offset + 28);
+       return 0x0000;
+}
+#endif
diff --git a/drivers/gpu/drm/nouveau/include/nvkm/subdev/bios/boost.h b/drivers/gpu/drm/nouveau/include/nvkm/subdev/bios/boost.h
new file mode 100644 (file)
index 0000000..934b0ae
--- /dev/null
@@ -0,0 +1,27 @@
+#ifndef __NVBIOS_BOOST_H__
+#define __NVBIOS_BOOST_H__
+u16 nvbios_boostTe(struct nvkm_bios *, u8 *, u8 *, u8 *, u8 *, u8 *, u8 *);
+
+struct nvbios_boostE {
+       u8  pstate;
+       u32 min;
+       u32 max;
+};
+
+u16 nvbios_boostEe(struct nvkm_bios *, int idx, u8 *, u8 *, u8 *, u8 *);
+u16 nvbios_boostEp(struct nvkm_bios *, int idx, u8 *, u8 *, u8 *, u8 *,
+                  struct nvbios_boostE *);
+u16 nvbios_boostEm(struct nvkm_bios *, u8, u8 *, u8 *, u8 *, u8 *,
+                  struct nvbios_boostE *);
+
+struct nvbios_boostS {
+       u8  domain;
+       u8  percent;
+       u32 min;
+       u32 max;
+};
+
+u16 nvbios_boostSe(struct nvkm_bios *, int, u16, u8 *, u8 *, u8, u8);
+u16 nvbios_boostSp(struct nvkm_bios *, int, u16, u8 *, u8 *, u8, u8,
+                  struct nvbios_boostS *);
+#endif
diff --git a/drivers/gpu/drm/nouveau/include/nvkm/subdev/bios/conn.h b/drivers/gpu/drm/nouveau/include/nvkm/subdev/bios/conn.h
new file mode 100644 (file)
index 0000000..e8e77ee
--- /dev/null
@@ -0,0 +1,44 @@
+#ifndef __NVBIOS_CONN_H__
+#define __NVBIOS_CONN_H__
+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_DMS59_0 = 0x38,
+       DCB_CONNECTOR_DMS59_1 = 0x39,
+       DCB_CONNECTOR_LVDS = 0x40,
+       DCB_CONNECTOR_LVDS_SPWG = 0x41,
+       DCB_CONNECTOR_DP = 0x46,
+       DCB_CONNECTOR_eDP = 0x47,
+       DCB_CONNECTOR_HDMI_0 = 0x60,
+       DCB_CONNECTOR_HDMI_1 = 0x61,
+       DCB_CONNECTOR_HDMI_C = 0x63,
+       DCB_CONNECTOR_DMS59_DP0 = 0x64,
+       DCB_CONNECTOR_DMS59_DP1 = 0x65,
+       DCB_CONNECTOR_NONE = 0xff
+};
+
+struct nvbios_connT {
+};
+
+u32 nvbios_connTe(struct nvkm_bios *bios, u8 *ver, u8 *hdr, u8 *cnt, u8 *len);
+u32 nvbios_connTp(struct nvkm_bios *bios, u8 *ver, u8 *hdr, u8 *cnt, u8 *len,
+                 struct nvbios_connT *info);
+
+struct nvbios_connE {
+       u8 type;
+       u8 location;
+       u8 hpd;
+       u8 dp;
+       u8 di;
+       u8 sr;
+       u8 lcdid;
+};
+
+u32 nvbios_connEe(struct nvkm_bios *bios, u8 idx, u8 *ver, u8 *hdr);
+u32 nvbios_connEp(struct nvkm_bios *bios, u8 idx, u8 *ver, u8 *hdr,
+                 struct nvbios_connE *info);
+#endif
diff --git a/drivers/gpu/drm/nouveau/include/nvkm/subdev/bios/cstep.h b/drivers/gpu/drm/nouveau/include/nvkm/subdev/bios/cstep.h
new file mode 100644 (file)
index 0000000..2f0e0c8
--- /dev/null
@@ -0,0 +1,26 @@
+#ifndef __NVBIOS_CSTEP_H__
+#define __NVBIOS_CSTEP_H__
+u16 nvbios_cstepTe(struct nvkm_bios *,
+                  u8 *ver, u8 *hdr, u8 *cnt, u8 *len, u8 *xnr, u8 *xsz);
+
+struct nvbios_cstepE {
+       u8  pstate;
+       u8  index;
+};
+
+u16 nvbios_cstepEe(struct nvkm_bios *, int idx, u8 *ver, u8 *hdr);
+u16 nvbios_cstepEp(struct nvkm_bios *, int idx, u8 *ver, u8 *hdr,
+                  struct nvbios_cstepE *);
+u16 nvbios_cstepEm(struct nvkm_bios *, u8 pstate, u8 *ver, u8 *hdr,
+                  struct nvbios_cstepE *);
+
+struct nvbios_cstepX {
+       u32 freq;
+       u8  unkn[2];
+       u8  voltage;
+};
+
+u16 nvbios_cstepXe(struct nvkm_bios *, int idx, u8 *ver, u8 *hdr);
+u16 nvbios_cstepXp(struct nvkm_bios *, int idx, u8 *ver, u8 *hdr,
+                  struct nvbios_cstepX *);
+#endif
diff --git a/drivers/gpu/drm/nouveau/include/nvkm/subdev/bios/dcb.h b/drivers/gpu/drm/nouveau/include/nvkm/subdev/bios/dcb.h
new file mode 100644 (file)
index 0000000..4892a65
--- /dev/null
@@ -0,0 +1,65 @@
+#ifndef __NVBIOS_DCB_H__
+#define __NVBIOS_DCB_H__
+enum dcb_output_type {
+       DCB_OUTPUT_ANALOG       = 0x0,
+       DCB_OUTPUT_TV           = 0x1,
+       DCB_OUTPUT_TMDS         = 0x2,
+       DCB_OUTPUT_LVDS         = 0x3,
+       DCB_OUTPUT_DP           = 0x6,
+       DCB_OUTPUT_EOL          = 0xe,
+       DCB_OUTPUT_UNUSED       = 0xf,
+       DCB_OUTPUT_ANY = -1,
+};
+
+struct dcb_output {
+       int index;      /* may not be raw dcb index if merging has happened */
+       u16 hasht;
+       u16 hashm;
+       enum dcb_output_type type;
+       uint8_t i2c_index;
+       uint8_t heads;
+       uint8_t connector;
+       uint8_t bus;
+       uint8_t location;
+       uint8_t or;
+       uint8_t link;
+       bool duallink_possible;
+       uint8_t extdev;
+       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;
+};
+
+u16 dcb_table(struct nvkm_bios *, u8 *ver, u8 *hdr, u8 *ent, u8 *len);
+u16 dcb_outp(struct nvkm_bios *, u8 idx, u8 *ver, u8 *len);
+u16 dcb_outp_parse(struct nvkm_bios *, u8 idx, u8 *, u8 *,
+                  struct dcb_output *);
+u16 dcb_outp_match(struct nvkm_bios *, u16 type, u16 mask, u8 *, u8 *,
+                  struct dcb_output *);
+int dcb_outp_foreach(struct nvkm_bios *, void *data, int (*exec)
+                    (struct nvkm_bios *, void *, int index, u16 entry));
+#endif
diff --git a/drivers/gpu/drm/nouveau/include/nvkm/subdev/bios/disp.h b/drivers/gpu/drm/nouveau/include/nvkm/subdev/bios/disp.h
new file mode 100644 (file)
index 0000000..db10c11
--- /dev/null
@@ -0,0 +1,39 @@
+#ifndef __NVBIOS_DISP_H__
+#define __NVBIOS_DISP_H__
+u16 nvbios_disp_table(struct nvkm_bios *,
+                     u8 *ver, u8 *hdr, u8 *cnt, u8 *len, u8 *sub);
+
+struct nvbios_disp {
+       u16 data;
+};
+
+u16 nvbios_disp_entry(struct nvkm_bios *, u8 idx, u8 *ver, u8 *hdr, u8 *sub);
+u16 nvbios_disp_parse(struct nvkm_bios *, u8 idx, u8 *ver, u8 *hdr, u8 *sub,
+                     struct nvbios_disp *);
+
+struct nvbios_outp {
+       u16 type;
+       u16 mask;
+       u16 script[3];
+};
+
+u16 nvbios_outp_entry(struct nvkm_bios *, u8 idx,
+                     u8 *ver, u8 *hdr, u8 *cnt, u8 *len);
+u16 nvbios_outp_parse(struct nvkm_bios *, u8 idx,
+                     u8 *ver, u8 *hdr, u8 *cnt, u8 *len, struct nvbios_outp *);
+u16 nvbios_outp_match(struct nvkm_bios *, u16 type, u16 mask,
+                     u8 *ver, u8 *hdr, u8 *cnt, u8 *len, struct nvbios_outp *);
+
+struct nvbios_ocfg {
+       u16 match;
+       u16 clkcmp[2];
+};
+
+u16 nvbios_ocfg_entry(struct nvkm_bios *, u16 outp, u8 idx,
+                     u8 *ver, u8 *hdr, u8 *cnt, u8 *len);
+u16 nvbios_ocfg_parse(struct nvkm_bios *, u16 outp, u8 idx,
+                     u8 *ver, u8 *hdr, u8 *cnt, u8 *len, struct nvbios_ocfg *);
+u16 nvbios_ocfg_match(struct nvkm_bios *, u16 outp, u16 type,
+                     u8 *ver, u8 *hdr, u8 *cnt, u8 *len, struct nvbios_ocfg *);
+u16 nvbios_oclk_match(struct nvkm_bios *, u16 cmp, u32 khz);
+#endif
diff --git a/drivers/gpu/drm/nouveau/include/nvkm/subdev/bios/dp.h b/drivers/gpu/drm/nouveau/include/nvkm/subdev/bios/dp.h
new file mode 100644 (file)
index 0000000..b4d39df
--- /dev/null
@@ -0,0 +1,31 @@
+#ifndef __NVBIOS_DP_H__
+#define __NVBIOS_DP_H__
+struct nvbios_dpout {
+       u16 type;
+       u16 mask;
+       u8  flags;
+       u32 script[5];
+       u32 lnkcmp;
+};
+
+u16 nvbios_dpout_parse(struct nvkm_bios *, u8 idx,
+                      u8 *ver, u8 *hdr, u8 *cnt, u8 *len,
+                      struct nvbios_dpout *);
+u16 nvbios_dpout_match(struct nvkm_bios *, u16 type, u16 mask,
+                      u8 *ver, u8 *hdr, u8 *cnt, u8 *len,
+                      struct nvbios_dpout *);
+
+struct nvbios_dpcfg {
+       u8 pc;
+       u8 dc;
+       u8 pe;
+       u8 tx_pu;
+};
+
+u16
+nvbios_dpcfg_parse(struct nvkm_bios *, u16 outp, u8 idx,
+                  u8 *ver, u8 *hdr, u8 *cnt, u8 *len, struct nvbios_dpcfg *);
+u16
+nvbios_dpcfg_match(struct nvkm_bios *, u16 outp, u8 pc, u8 vs, u8 pe,
+                  u8 *ver, u8 *hdr, u8 *cnt, u8 *len, struct nvbios_dpcfg *);
+#endif
diff --git a/drivers/gpu/drm/nouveau/include/nvkm/subdev/bios/extdev.h b/drivers/gpu/drm/nouveau/include/nvkm/subdev/bios/extdev.h
new file mode 100644 (file)
index 0000000..6d3bedc
--- /dev/null
@@ -0,0 +1,25 @@
+#ifndef __NVBIOS_EXTDEV_H__
+#define __NVBIOS_EXTDEV_H__
+enum nvbios_extdev_type {
+       NVBIOS_EXTDEV_LM89              = 0x02,
+       NVBIOS_EXTDEV_VT1103M           = 0x40,
+       NVBIOS_EXTDEV_PX3540            = 0x41,
+       NVBIOS_EXTDEV_VT1105M           = 0x42, /* or close enough... */
+       NVBIOS_EXTDEV_ADT7473           = 0x70, /* can also be a LM64 */
+       NVBIOS_EXTDEV_HDCP_EEPROM       = 0x90,
+       NVBIOS_EXTDEV_NONE              = 0xff,
+};
+
+struct nvbios_extdev_func {
+       u8 type;
+       u8 addr;
+       u8 bus;
+};
+
+int
+nvbios_extdev_parse(struct nvkm_bios *, int, struct nvbios_extdev_func *);
+
+int
+nvbios_extdev_find(struct nvkm_bios *, enum nvbios_extdev_type,
+                  struct nvbios_extdev_func *);
+#endif
diff --git a/drivers/gpu/drm/nouveau/include/nvkm/subdev/bios/fan.h b/drivers/gpu/drm/nouveau/include/nvkm/subdev/bios/fan.h
new file mode 100644 (file)
index 0000000..693ea7d
--- /dev/null
@@ -0,0 +1,6 @@
+#ifndef __NVBIOS_FAN_H__
+#define __NVBIOS_FAN_H__
+#include <subdev/bios/therm.h>
+
+u16 nvbios_fan_parse(struct nvkm_bios *bios, struct nvbios_therm_fan *fan);
+#endif
diff --git a/drivers/gpu/drm/nouveau/include/nvkm/subdev/bios/gpio.h b/drivers/gpu/drm/nouveau/include/nvkm/subdev/bios/gpio.h
new file mode 100644 (file)
index 0000000..33be260
--- /dev/null
@@ -0,0 +1,46 @@
+#ifndef __NVBIOS_GPIO_H__
+#define __NVBIOS_GPIO_H__
+enum dcb_gpio_func_name {
+       DCB_GPIO_PANEL_POWER = 0x01,
+       DCB_GPIO_TVDAC0 = 0x0c,
+       DCB_GPIO_TVDAC1 = 0x2d,
+       DCB_GPIO_FAN = 0x09,
+       DCB_GPIO_FAN_SENSE = 0x3d,
+       DCB_GPIO_UNUSED = 0xff,
+       DCB_GPIO_VID0 = 0x04,
+       DCB_GPIO_VID1 = 0x05,
+       DCB_GPIO_VID2 = 0x06,
+       DCB_GPIO_VID3 = 0x1a,
+       DCB_GPIO_VID4 = 0x73,
+       DCB_GPIO_VID5 = 0x74,
+       DCB_GPIO_VID6 = 0x75,
+       DCB_GPIO_VID7 = 0x76,
+};
+
+#define DCB_GPIO_LOG_DIR     0x02
+#define DCB_GPIO_LOG_DIR_OUT 0x00
+#define DCB_GPIO_LOG_DIR_IN  0x02
+#define DCB_GPIO_LOG_VAL     0x01
+#define DCB_GPIO_LOG_VAL_LO  0x00
+#define DCB_GPIO_LOG_VAL_HI  0x01
+
+struct dcb_gpio_func {
+       u8 func;
+       u8 line;
+       u8 log[2];
+
+       /* so far, "param" seems to only have an influence on PWM-related
+        * GPIOs such as FAN_CONTROL and PANEL_BACKLIGHT_LEVEL.
+        * if param equals 1, hardware PWM is available
+        * if param equals 0, the host should toggle the GPIO itself
+        */
+       u8 param;
+};
+
+u16 dcb_gpio_table(struct nvkm_bios *, u8 *ver, u8 *hdr, u8 *cnt, u8 *len);
+u16 dcb_gpio_entry(struct nvkm_bios *, int idx, int ent, u8 *ver, u8 *len);
+u16 dcb_gpio_parse(struct nvkm_bios *, int idx, int ent, u8 *ver, u8 *len,
+                  struct dcb_gpio_func *);
+u16 dcb_gpio_match(struct nvkm_bios *, int idx, u8 func, u8 line,
+                  u8 *ver, u8 *len, struct dcb_gpio_func *);
+#endif
diff --git a/drivers/gpu/drm/nouveau/include/nvkm/subdev/bios/i2c.h b/drivers/gpu/drm/nouveau/include/nvkm/subdev/bios/i2c.h
new file mode 100644 (file)
index 0000000..85c529e
--- /dev/null
@@ -0,0 +1,25 @@
+#ifndef __NVBIOS_I2C_H__
+#define __NVBIOS_I2C_H__
+enum dcb_i2c_type {
+       /* matches bios type field prior to ccb 4.1 */
+       DCB_I2C_NV04_BIT = 0x00,
+       DCB_I2C_NV4E_BIT = 0x04,
+       DCB_I2C_NVIO_BIT = 0x05,
+       DCB_I2C_NVIO_AUX = 0x06,
+       /* made up - mostly */
+       DCB_I2C_PMGR     = 0x80,
+       DCB_I2C_UNUSED   = 0xff
+};
+
+struct dcb_i2c_entry {
+       enum dcb_i2c_type type;
+       u8 drive;
+       u8 sense;
+       u8 share;
+       u8 auxch;
+};
+
+u16 dcb_i2c_table(struct nvkm_bios *, u8 *ver, u8 *hdr, u8 *cnt, u8 *len);
+u16 dcb_i2c_entry(struct nvkm_bios *, u8 index, u8 *ver, u8 *len);
+int dcb_i2c_parse(struct nvkm_bios *, u8 index, struct dcb_i2c_entry *);
+#endif
diff --git a/drivers/gpu/drm/nouveau/include/nvkm/subdev/bios/image.h b/drivers/gpu/drm/nouveau/include/nvkm/subdev/bios/image.h
new file mode 100644 (file)
index 0000000..e15d63b
--- /dev/null
@@ -0,0 +1,11 @@
+#ifndef __NVBIOS_IMAGE_H__
+#define __NVBIOS_IMAGE_H__
+struct nvbios_image {
+       u32  base;
+       u32  size;
+       u8   type;
+       bool last;
+};
+
+bool nvbios_image(struct nvkm_bios *, int, struct nvbios_image *);
+#endif
diff --git a/drivers/gpu/drm/nouveau/include/nvkm/subdev/bios/init.h b/drivers/gpu/drm/nouveau/include/nvkm/subdev/bios/init.h
new file mode 100644 (file)
index 0000000..578a667
--- /dev/null
@@ -0,0 +1,20 @@
+#ifndef __NVBIOS_INIT_H__
+#define __NVBIOS_INIT_H__
+struct nvbios_init {
+       struct nvkm_subdev *subdev;
+       struct nvkm_bios *bios;
+       u16 offset;
+       struct dcb_output *outp;
+       int crtc;
+
+       /* internal state used during parsing */
+       u8 execute;
+       u32 nested;
+       u16 repeat;
+       u16 repend;
+       u32 ramcfg;
+};
+
+int nvbios_exec(struct nvbios_init *);
+int nvbios_init(struct nvkm_subdev *, bool execute);
+#endif
diff --git a/drivers/gpu/drm/nouveau/include/nvkm/subdev/bios/mxm.h b/drivers/gpu/drm/nouveau/include/nvkm/subdev/bios/mxm.h
new file mode 100644 (file)
index 0000000..4e31b64
--- /dev/null
@@ -0,0 +1,6 @@
+#ifndef __NVBIOS_MXM_H__
+#define __NVBIOS_MXM_H__
+u16 mxm_table(struct nvkm_bios *, u8 *ver, u8 *hdr);
+u8  mxm_sor_map(struct nvkm_bios *, u8 conn);
+u8  mxm_ddc_map(struct nvkm_bios *, u8 port);
+#endif
diff --git a/drivers/gpu/drm/nouveau/include/nvkm/subdev/bios/npde.h b/drivers/gpu/drm/nouveau/include/nvkm/subdev/bios/npde.h
new file mode 100644 (file)
index 0000000..64a5954
--- /dev/null
@@ -0,0 +1,10 @@
+#ifndef __NVBIOS_NPDE_H__
+#define __NVBIOS_NPDE_H__
+struct nvbios_npdeT {
+       u32 image_size;
+       bool last;
+};
+
+u32 nvbios_npdeTe(struct nvkm_bios *, u32);
+u32 nvbios_npdeTp(struct nvkm_bios *, u32, struct nvbios_npdeT *);
+#endif
diff --git a/drivers/gpu/drm/nouveau/include/nvkm/subdev/bios/pcir.h b/drivers/gpu/drm/nouveau/include/nvkm/subdev/bios/pcir.h
new file mode 100644 (file)
index 0000000..e859315
--- /dev/null
@@ -0,0 +1,16 @@
+#ifndef __NVBIOS_PCIR_H__
+#define __NVBIOS_PCIR_H__
+struct nvbios_pcirT {
+       u16 vendor_id;
+       u16 device_id;
+       u8  class_code[3];
+       u32 image_size;
+       u16 image_rev;
+       u8  image_type;
+       bool last;
+};
+
+u32 nvbios_pcirTe(struct nvkm_bios *, u32, u8 *ver, u16 *hdr);
+u32 nvbios_pcirTp(struct nvkm_bios *, u32, u8 *ver, u16 *hdr,
+                 struct nvbios_pcirT *);
+#endif
diff --git a/drivers/gpu/drm/nouveau/include/nvkm/subdev/bios/perf.h b/drivers/gpu/drm/nouveau/include/nvkm/subdev/bios/perf.h
new file mode 100644 (file)
index 0000000..7cc2bec
--- /dev/null
@@ -0,0 +1,41 @@
+#ifndef __NVBIOS_PERF_H__
+#define __NVBIOS_PERF_H__
+u16 nvbios_perf_table(struct nvkm_bios *, u8 *ver, u8 *hdr,
+                     u8 *cnt, u8 *len, u8 *snr, u8 *ssz);
+
+struct nvbios_perfE {
+       u8  pstate;
+       u8  fanspeed;
+       u8  voltage;
+       u32 core;
+       u32 shader;
+       u32 memory;
+       u32 vdec;
+       u32 disp;
+       u32 script;
+};
+
+u16 nvbios_perf_entry(struct nvkm_bios *, int idx,
+                     u8 *ver, u8 *hdr, u8 *cnt, u8 *len);
+u16 nvbios_perfEp(struct nvkm_bios *, int idx,
+                 u8 *ver, u8 *hdr, u8 *cnt, u8 *len, struct nvbios_perfE *);
+
+struct nvbios_perfS {
+       union {
+               struct {
+                       u32 freq;
+               } v40;
+       };
+};
+
+u32 nvbios_perfSe(struct nvkm_bios *, u32 data, int idx,
+                 u8 *ver, u8 *hdr, u8 cnt, u8 len);
+u32 nvbios_perfSp(struct nvkm_bios *, u32 data, int idx,
+                 u8 *ver, u8 *hdr, u8 cnt, u8 len, struct nvbios_perfS *);
+
+struct nvbios_perf_fan {
+       u32 pwm_divisor;
+};
+
+int nvbios_perf_fan_parse(struct nvkm_bios *, struct nvbios_perf_fan *);
+#endif
diff --git a/drivers/gpu/drm/nouveau/include/nvkm/subdev/bios/pll.h b/drivers/gpu/drm/nouveau/include/nvkm/subdev/bios/pll.h
new file mode 100644 (file)
index 0000000..5a69978
--- /dev/null
@@ -0,0 +1,75 @@
+#ifndef __NVBIOS_PLL_H__
+#define __NVBIOS_PLL_H__
+/*XXX: kill me */
+struct nvkm_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;
+};
+
+/* these match types in pll limits table version 0x40,
+ * nvkm uses them on all chipsets internally where a
+ * specific pll needs to be referenced, but the exact
+ * register isn't known.
+ */
+enum nvbios_pll_type {
+       PLL_CORE   = 0x01,
+       PLL_SHADER = 0x02,
+       PLL_UNK03  = 0x03,
+       PLL_MEMORY = 0x04,
+       PLL_VDEC   = 0x05,
+       PLL_UNK40  = 0x40,
+       PLL_UNK41  = 0x41,
+       PLL_UNK42  = 0x42,
+       PLL_VPLL0  = 0x80,
+       PLL_VPLL1  = 0x81,
+       PLL_VPLL2  = 0x82,
+       PLL_VPLL3  = 0x83,
+       PLL_MAX    = 0xff
+};
+
+struct nvbios_pll {
+       enum nvbios_pll_type type;
+       u32 reg;
+       u32 refclk;
+
+       u8 min_p;
+       u8 max_p;
+       u8 bias_p;
+
+       /*
+        * 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
+        */
+       u8 max_p_usable;
+
+       struct {
+               u32 min_freq;
+               u32 max_freq;
+               u32 min_inputfreq;
+               u32 max_inputfreq;
+               u8  min_m;
+               u8  max_m;
+               u8  min_n;
+               u8  max_n;
+       } vco1, vco2;
+};
+
+int nvbios_pll_parse(struct nvkm_bios *, u32 type, struct nvbios_pll *);
+#endif
diff --git a/drivers/gpu/drm/nouveau/include/nvkm/subdev/bios/pmu.h b/drivers/gpu/drm/nouveau/include/nvkm/subdev/bios/pmu.h
new file mode 100644 (file)
index 0000000..d606875
--- /dev/null
@@ -0,0 +1,35 @@
+#ifndef __NVBIOS_PMU_H__
+#define __NVBIOS_PMU_H__
+struct nvbios_pmuT {
+};
+
+u32 nvbios_pmuTe(struct nvkm_bios *, u8 *ver, u8 *hdr, u8 *cnt, u8 *len);
+u32 nvbios_pmuTp(struct nvkm_bios *, u8 *ver, u8 *hdr, u8 *cnt, u8 *len,
+                struct nvbios_pmuT *);
+
+struct nvbios_pmuE {
+       u8  type;
+       u32 data;
+};
+
+u32 nvbios_pmuEe(struct nvkm_bios *, int idx, u8 *ver, u8 *hdr);
+u32 nvbios_pmuEp(struct nvkm_bios *, int idx, u8 *ver, u8 *hdr,
+                struct nvbios_pmuE *);
+
+struct nvbios_pmuR {
+       u32 boot_addr_pmu;
+       u32 boot_addr;
+       u32 boot_size;
+       u32 code_addr_pmu;
+       u32 code_addr;
+       u32 code_size;
+       u32 init_addr_pmu;
+
+       u32 data_addr_pmu;
+       u32 data_addr;
+       u32 data_size;
+       u32 args_addr_pmu;
+};
+
+bool nvbios_pmuRm(struct nvkm_bios *, u8 type, struct nvbios_pmuR *);
+#endif
diff --git a/drivers/gpu/drm/nouveau/include/nvkm/subdev/bios/ramcfg.h b/drivers/gpu/drm/nouveau/include/nvkm/subdev/bios/ramcfg.h
new file mode 100644 (file)
index 0000000..4204267
--- /dev/null
@@ -0,0 +1,141 @@
+#ifndef __NVBIOS_RAMCFG_H__
+#define __NVBIOS_RAMCFG_H__
+struct nvbios_ramcfg {
+       unsigned rammap_ver;
+       unsigned rammap_hdr;
+       unsigned rammap_min;
+       unsigned rammap_max;
+       union {
+               struct {
+                       unsigned rammap_10_04_02:1;
+                       unsigned rammap_10_04_08:1;
+               };
+               struct {
+                       unsigned rammap_11_08_01:1;
+                       unsigned rammap_11_08_0c:2;
+                       unsigned rammap_11_08_10:1;
+                       unsigned rammap_11_09_01ff:9;
+                       unsigned rammap_11_0a_03fe:9;
+                       unsigned rammap_11_0a_0400:1;
+                       unsigned rammap_11_0a_0800:1;
+                       unsigned rammap_11_0b_01f0:5;
+                       unsigned rammap_11_0b_0200:1;
+                       unsigned rammap_11_0b_0400:1;
+                       unsigned rammap_11_0b_0800:1;
+                       unsigned rammap_11_0d:8;
+                       unsigned rammap_11_0e:8;
+                       unsigned rammap_11_0f:8;
+                       unsigned rammap_11_11_0c:2;
+               };
+       };
+
+       unsigned ramcfg_ver;
+       unsigned ramcfg_hdr;
+       unsigned ramcfg_timing;
+       union {
+               struct {
+                       unsigned ramcfg_10_02_01:1;
+                       unsigned ramcfg_10_02_02:1;
+                       unsigned ramcfg_10_02_04:1;
+                       unsigned ramcfg_10_02_08:1;
+                       unsigned ramcfg_10_02_10:1;
+                       unsigned ramcfg_10_02_20:1;
+                       unsigned ramcfg_10_DLLoff:1;
+                       unsigned ramcfg_10_03_0f:4;
+                       unsigned ramcfg_10_04_01:1;
+                       unsigned ramcfg_10_05:8;
+                       unsigned ramcfg_10_06:8;
+                       unsigned ramcfg_10_07:8;
+                       unsigned ramcfg_10_08:8;
+                       unsigned ramcfg_10_09_0f:4;
+                       unsigned ramcfg_10_09_f0:4;
+               };
+               struct {
+                       unsigned ramcfg_11_01_01:1;
+                       unsigned ramcfg_11_01_02:1;
+                       unsigned ramcfg_11_01_04:1;
+                       unsigned ramcfg_11_01_08:1;
+                       unsigned ramcfg_11_01_10:1;
+                       unsigned ramcfg_11_01_20:1;
+                       unsigned ramcfg_11_01_40:1;
+                       unsigned ramcfg_11_01_80:1;
+                       unsigned ramcfg_11_02_03:2;
+                       unsigned ramcfg_11_02_04:1;
+                       unsigned ramcfg_11_02_08:1;
+                       unsigned ramcfg_11_02_10:1;
+                       unsigned ramcfg_11_02_40:1;
+                       unsigned ramcfg_11_02_80:1;
+                       unsigned ramcfg_11_03_0f:4;
+                       unsigned ramcfg_11_03_30:2;
+                       unsigned ramcfg_11_03_c0:2;
+                       unsigned ramcfg_11_03_f0:4;
+                       unsigned ramcfg_11_04:8;
+                       unsigned ramcfg_11_06:8;
+                       unsigned ramcfg_11_07_02:1;
+                       unsigned ramcfg_11_07_04:1;
+                       unsigned ramcfg_11_07_08:1;
+                       unsigned ramcfg_11_07_10:1;
+                       unsigned ramcfg_11_07_40:1;
+                       unsigned ramcfg_11_07_80:1;
+                       unsigned ramcfg_11_08_01:1;
+                       unsigned ramcfg_11_08_02:1;
+                       unsigned ramcfg_11_08_04:1;
+                       unsigned ramcfg_11_08_08:1;
+                       unsigned ramcfg_11_08_10:1;
+                       unsigned ramcfg_11_08_20:1;
+                       unsigned ramcfg_11_09:8;
+               };
+       };
+
+       unsigned timing_ver;
+       unsigned timing_hdr;
+       unsigned timing[11];
+       union {
+               struct {
+                       unsigned timing_10_WR:8;
+                       unsigned timing_10_WTR:8;
+                       unsigned timing_10_CL:8;
+                       unsigned timing_10_RC:8;
+                       /*empty: 4 */
+                       unsigned timing_10_RFC:8;        /* Byte 5 */
+                       /*empty: 6 */
+                       unsigned timing_10_RAS:8;        /* Byte 7 */
+                       /*empty: 8 */
+                       unsigned timing_10_RP:8;         /* Byte 9 */
+                       unsigned timing_10_RCDRD:8;
+                       unsigned timing_10_RCDWR:8;
+                       unsigned timing_10_RRD:8;
+                       unsigned timing_10_13:8;
+                       unsigned timing_10_ODT:3;
+                       /* empty: 15 */
+                       unsigned timing_10_16:8;
+                       /* empty: 17 */
+                       unsigned timing_10_18:8;
+                       unsigned timing_10_CWL:8;
+                       unsigned timing_10_20:8;
+                       unsigned timing_10_21:8;
+                       /* empty: 22, 23 */
+                       unsigned timing_10_24:8;
+               };
+               struct {
+                       unsigned timing_20_2e_03:2;
+                       unsigned timing_20_2e_30:2;
+                       unsigned timing_20_2e_c0:2;
+                       unsigned timing_20_2f_03:2;
+                       unsigned timing_20_2c_003f:6;
+                       unsigned timing_20_2c_1fc0:7;
+                       unsigned timing_20_30_f8:5;
+                       unsigned timing_20_30_07:3;
+                       unsigned timing_20_31_0007:3;
+                       unsigned timing_20_31_0078:4;
+                       unsigned timing_20_31_0780:4;
+                       unsigned timing_20_31_0800:1;
+                       unsigned timing_20_31_7000:3;
+                       unsigned timing_20_31_8000:1;
+               };
+       };
+};
+
+u8 nvbios_ramcfg_count(struct nvkm_bios *);
+u8 nvbios_ramcfg_index(struct nvkm_subdev *);
+#endif
diff --git a/drivers/gpu/drm/nouveau/include/nvkm/subdev/bios/rammap.h b/drivers/gpu/drm/nouveau/include/nvkm/subdev/bios/rammap.h
new file mode 100644 (file)
index 0000000..609a905
--- /dev/null
@@ -0,0 +1,21 @@
+#ifndef __NVBIOS_RAMMAP_H__
+#define __NVBIOS_RAMMAP_H__
+#include <subdev/bios/ramcfg.h>
+
+u32 nvbios_rammapTe(struct nvkm_bios *, u8 *ver, u8 *hdr,
+                   u8 *cnt, u8 *len, u8 *snr, u8 *ssz);
+
+u32 nvbios_rammapEe(struct nvkm_bios *, int idx,
+                   u8 *ver, u8 *hdr, u8 *cnt, u8 *len);
+u32 nvbios_rammapEp(struct nvkm_bios *, int idx,
+                   u8 *ver, u8 *hdr, u8 *cnt, u8 *len, struct nvbios_ramcfg *);
+u32 nvbios_rammapEm(struct nvkm_bios *, u16 mhz,
+                   u8 *ver, u8 *hdr, u8 *cnt, u8 *len, struct nvbios_ramcfg *);
+
+u32 nvbios_rammapSe(struct nvkm_bios *, u32 data,
+                   u8 ever, u8 ehdr, u8 ecnt, u8 elen, int idx,
+                   u8 *ver, u8 *hdr);
+u32 nvbios_rammapSp(struct nvkm_bios *, u32 data,
+                   u8 ever, u8 ehdr, u8 ecnt, u8 elen, int idx,
+                   u8 *ver, u8 *hdr, struct nvbios_ramcfg *);
+#endif
diff --git a/drivers/gpu/drm/nouveau/include/nvkm/subdev/bios/therm.h b/drivers/gpu/drm/nouveau/include/nvkm/subdev/bios/therm.h
new file mode 100644 (file)
index 0000000..dd3ba96
--- /dev/null
@@ -0,0 +1,72 @@
+#ifndef __NVBIOS_THERM_H__
+#define __NVBIOS_THERM_H__
+struct nvbios_therm_threshold {
+       u8 temp;
+       u8 hysteresis;
+};
+
+struct nvbios_therm_sensor {
+       /* diode */
+       s16 slope_mult;
+       s16 slope_div;
+       s16 offset_num;
+       s16 offset_den;
+       s8 offset_constant;
+
+       /* thresholds */
+       struct nvbios_therm_threshold thrs_fan_boost;
+       struct nvbios_therm_threshold thrs_down_clock;
+       struct nvbios_therm_threshold thrs_critical;
+       struct nvbios_therm_threshold thrs_shutdown;
+};
+
+enum nvbios_therm_fan_type {
+       NVBIOS_THERM_FAN_UNK = 0,
+       NVBIOS_THERM_FAN_TOGGLE = 1,
+       NVBIOS_THERM_FAN_PWM = 2,
+};
+
+/* no vbios have more than 6 */
+#define NVKM_TEMP_FAN_TRIP_MAX 10
+struct nvbios_therm_trip_point {
+       int fan_duty;
+       int temp;
+       int hysteresis;
+};
+
+enum nvbios_therm_fan_mode {
+       NVBIOS_THERM_FAN_TRIP = 0,
+       NVBIOS_THERM_FAN_LINEAR = 1,
+       NVBIOS_THERM_FAN_OTHER = 2,
+};
+
+struct nvbios_therm_fan {
+       enum nvbios_therm_fan_type type;
+
+       u32 pwm_freq;
+
+       u8 min_duty;
+       u8 max_duty;
+
+       u16 bump_period;
+       u16 slow_down_period;
+
+       enum nvbios_therm_fan_mode fan_mode;
+       struct nvbios_therm_trip_point trip[NVKM_TEMP_FAN_TRIP_MAX];
+       u8 nr_fan_trip;
+       u8 linear_min_temp;
+       u8 linear_max_temp;
+};
+
+enum nvbios_therm_domain {
+       NVBIOS_THERM_DOMAIN_CORE,
+       NVBIOS_THERM_DOMAIN_AMBIENT,
+};
+
+int
+nvbios_therm_sensor_parse(struct nvkm_bios *, enum nvbios_therm_domain,
+                         struct nvbios_therm_sensor *);
+
+int
+nvbios_therm_fan_parse(struct nvkm_bios *, struct nvbios_therm_fan *);
+#endif
diff --git a/drivers/gpu/drm/nouveau/include/nvkm/subdev/bios/timing.h b/drivers/gpu/drm/nouveau/include/nvkm/subdev/bios/timing.h
new file mode 100644 (file)
index 0000000..339a826
--- /dev/null
@@ -0,0 +1,11 @@
+#ifndef __NVBIOS_TIMING_H__
+#define __NVBIOS_TIMING_H__
+#include <subdev/bios/ramcfg.h>
+
+u16 nvbios_timingTe(struct nvkm_bios *,
+                   u8 *ver, u8 *hdr, u8 *cnt, u8 *len, u8 *snr, u8 *ssz);
+u16 nvbios_timingEe(struct nvkm_bios *, int idx,
+                   u8 *ver, u8 *hdr, u8 *cnt, u8 *len);
+u16 nvbios_timingEp(struct nvkm_bios *, int idx,
+                   u8 *ver, u8 *hdr, u8 *cnt, u8 *len, struct nvbios_ramcfg *);
+#endif
diff --git a/drivers/gpu/drm/nouveau/include/nvkm/subdev/bios/vmap.h b/drivers/gpu/drm/nouveau/include/nvkm/subdev/bios/vmap.h
new file mode 100644 (file)
index 0000000..6633c6d
--- /dev/null
@@ -0,0 +1,21 @@
+#ifndef __NVBIOS_VMAP_H__
+#define __NVBIOS_VMAP_H__
+struct nvbios_vmap {
+};
+
+u16 nvbios_vmap_table(struct nvkm_bios *, u8 *ver, u8 *hdr, u8 *cnt, u8 *len);
+u16 nvbios_vmap_parse(struct nvkm_bios *, u8 *ver, u8 *hdr, u8 *cnt, u8 *len,
+                     struct nvbios_vmap *);
+
+struct nvbios_vmap_entry {
+       u8  unk0;
+       u8  link;
+       u32 min;
+       u32 max;
+       s32 arg[6];
+};
+
+u16 nvbios_vmap_entry(struct nvkm_bios *, int idx, u8 *ver, u8 *len);
+u16 nvbios_vmap_entry_parse(struct nvkm_bios *, int idx, u8 *ver, u8 *len,
+                           struct nvbios_vmap_entry *);
+#endif
diff --git a/drivers/gpu/drm/nouveau/include/nvkm/subdev/bios/volt.h b/drivers/gpu/drm/nouveau/include/nvkm/subdev/bios/volt.h
new file mode 100644 (file)
index 0000000..eb2de4b
--- /dev/null
@@ -0,0 +1,23 @@
+#ifndef __NVBIOS_VOLT_H__
+#define __NVBIOS_VOLT_H__
+struct nvbios_volt {
+       u8  vidmask;
+       u32 min;
+       u32 max;
+       u32 base;
+       s16 step;
+};
+
+u16 nvbios_volt_table(struct nvkm_bios *, u8 *ver, u8 *hdr, u8 *cnt, u8 *len);
+u16 nvbios_volt_parse(struct nvkm_bios *, u8 *ver, u8 *hdr, u8 *cnt, u8 *len,
+                     struct nvbios_volt *);
+
+struct nvbios_volt_entry {
+       u32 voltage;
+       u8  vid;
+};
+
+u16 nvbios_volt_entry(struct nvkm_bios *, int idx, u8 *ver, u8 *len);
+u16 nvbios_volt_entry_parse(struct nvkm_bios *, int idx, u8 *ver, u8 *len,
+                           struct nvbios_volt_entry *);
+#endif
diff --git a/drivers/gpu/drm/nouveau/include/nvkm/subdev/bios/xpio.h b/drivers/gpu/drm/nouveau/include/nvkm/subdev/bios/xpio.h
new file mode 100644 (file)
index 0000000..0c0fe23
--- /dev/null
@@ -0,0 +1,18 @@
+#ifndef __NVBIOS_XPIO_H__
+#define __NVBIOS_XPIO_H__
+
+#define NVBIOS_XPIO_FLAG_AUX  0x10
+#define NVBIOS_XPIO_FLAG_AUX0 0x00
+#define NVBIOS_XPIO_FLAG_AUX1 0x10
+
+struct nvbios_xpio {
+       u8 type;
+       u8 addr;
+       u8 flags;
+};
+
+u16 dcb_xpio_table(struct nvkm_bios *, u8 idx,
+                  u8 *ver, u8 *hdr, u8 *cnt, u8 *len);
+u16 dcb_xpio_parse(struct nvkm_bios *, u8 idx,
+                  u8 *ver, u8 *hdr, u8 *cnt, u8 *len, struct nvbios_xpio *);
+#endif
diff --git a/drivers/gpu/drm/nouveau/include/nvkm/subdev/bus.h b/drivers/gpu/drm/nouveau/include/nvkm/subdev/bus.h
new file mode 100644 (file)
index 0000000..fba83c0
--- /dev/null
@@ -0,0 +1,50 @@
+#ifndef __NVKM_BUS_H__
+#define __NVKM_BUS_H__
+#include <core/subdev.h>
+
+struct nvkm_bus_intr {
+       u32 stat;
+       u32 unit;
+};
+
+struct nvkm_bus {
+       struct nvkm_subdev base;
+       int (*hwsq_exec)(struct nvkm_bus *, u32 *, u32);
+       u32 hwsq_size;
+};
+
+static inline struct nvkm_bus *
+nvkm_bus(void *obj)
+{
+       return (void *)nvkm_subdev(obj, NVDEV_SUBDEV_BUS);
+}
+
+#define nvkm_bus_create(p, e, o, d)                                         \
+       nvkm_subdev_create_((p), (e), (o), 0, "PBUS", "master",             \
+                              sizeof(**d), (void **)d)
+#define nvkm_bus_destroy(p)                                                 \
+       nvkm_subdev_destroy(&(p)->base)
+#define nvkm_bus_init(p)                                                    \
+       nvkm_subdev_init(&(p)->base)
+#define nvkm_bus_fini(p, s)                                                 \
+       nvkm_subdev_fini(&(p)->base, (s))
+
+#define _nvkm_bus_dtor _nvkm_subdev_dtor
+#define _nvkm_bus_init _nvkm_subdev_init
+#define _nvkm_bus_fini _nvkm_subdev_fini
+
+extern struct nvkm_oclass *nv04_bus_oclass;
+extern struct nvkm_oclass *nv31_bus_oclass;
+extern struct nvkm_oclass *nv50_bus_oclass;
+extern struct nvkm_oclass *g94_bus_oclass;
+extern struct nvkm_oclass *gf100_bus_oclass;
+
+/* interface to sequencer */
+struct nvkm_hwsq;
+int  nvkm_hwsq_init(struct nvkm_bus *, struct nvkm_hwsq **);
+int  nvkm_hwsq_fini(struct nvkm_hwsq **, bool exec);
+void nvkm_hwsq_wr32(struct nvkm_hwsq *, u32 addr, u32 data);
+void nvkm_hwsq_setf(struct nvkm_hwsq *, u8 flag, int data);
+void nvkm_hwsq_wait(struct nvkm_hwsq *, u8 flag, u8 data);
+void nvkm_hwsq_nsec(struct nvkm_hwsq *, u32 nsec);
+#endif
diff --git a/drivers/gpu/drm/nouveau/include/nvkm/subdev/clk.h b/drivers/gpu/drm/nouveau/include/nvkm/subdev/clk.h
new file mode 100644 (file)
index 0000000..f5d3038
--- /dev/null
@@ -0,0 +1,161 @@
+#ifndef __NVKM_CLK_H__
+#define __NVKM_CLK_H__
+#include <core/subdev.h>
+#include <core/notify.h>
+struct nvbios_pll;
+struct nvkm_pll_vals;
+
+enum nv_clk_src {
+       nv_clk_src_crystal,
+       nv_clk_src_href,
+
+       nv_clk_src_hclk,
+       nv_clk_src_hclkm3,
+       nv_clk_src_hclkm3d2,
+       nv_clk_src_hclkm2d3, /* NVAA */
+       nv_clk_src_hclkm4, /* NVAA */
+       nv_clk_src_cclk, /* NVAA */
+
+       nv_clk_src_host,
+
+       nv_clk_src_sppll0,
+       nv_clk_src_sppll1,
+
+       nv_clk_src_mpllsrcref,
+       nv_clk_src_mpllsrc,
+       nv_clk_src_mpll,
+       nv_clk_src_mdiv,
+
+       nv_clk_src_core,
+       nv_clk_src_core_intm,
+       nv_clk_src_shader,
+
+       nv_clk_src_mem,
+
+       nv_clk_src_gpc,
+       nv_clk_src_rop,
+       nv_clk_src_hubk01,
+       nv_clk_src_hubk06,
+       nv_clk_src_hubk07,
+       nv_clk_src_copy,
+       nv_clk_src_daemon,
+       nv_clk_src_disp,
+       nv_clk_src_vdec,
+
+       nv_clk_src_dom6,
+
+       nv_clk_src_max,
+};
+
+struct nvkm_cstate {
+       struct list_head head;
+       u8  voltage;
+       u32 domain[nv_clk_src_max];
+};
+
+struct nvkm_pstate {
+       struct list_head head;
+       struct list_head list; /* c-states */
+       struct nvkm_cstate base;
+       u8 pstate;
+       u8 fanspeed;
+};
+
+struct nvkm_domain {
+       enum nv_clk_src name;
+       u8 bios; /* 0xff for none */
+#define NVKM_CLK_DOM_FLAG_CORE 0x01
+       u8 flags;
+       const char *mname;
+       int mdiv;
+};
+
+struct nvkm_clk {
+       struct nvkm_subdev base;
+
+       struct nvkm_domain *domains;
+       struct nvkm_pstate bstate;
+
+       struct list_head states;
+       int state_nr;
+
+       struct work_struct work;
+       wait_queue_head_t wait;
+       atomic_t waiting;
+
+       struct nvkm_notify pwrsrc_ntfy;
+       int pwrsrc;
+       int pstate; /* current */
+       int ustate_ac; /* user-requested (-1 disabled, -2 perfmon) */
+       int ustate_dc; /* user-requested (-1 disabled, -2 perfmon) */
+       int astate; /* perfmon adjustment (base) */
+       int tstate; /* thermal adjustment (max-) */
+       int dstate; /* display adjustment (min+) */
+
+       bool allow_reclock;
+
+       int  (*read)(struct nvkm_clk *, enum nv_clk_src);
+       int  (*calc)(struct nvkm_clk *, struct nvkm_cstate *);
+       int  (*prog)(struct nvkm_clk *);
+       void (*tidy)(struct nvkm_clk *);
+
+       /*XXX: die, these are here *only* to support the completely
+        *     bat-shit insane what-was-nvkm_hw.c code
+        */
+       int (*pll_calc)(struct nvkm_clk *, struct nvbios_pll *, int clk,
+                       struct nvkm_pll_vals *pv);
+       int (*pll_prog)(struct nvkm_clk *, u32 reg1, struct nvkm_pll_vals *pv);
+};
+
+static inline struct nvkm_clk *
+nvkm_clk(void *obj)
+{
+       return (void *)nvkm_subdev(obj, NVDEV_SUBDEV_CLK);
+}
+
+#define nvkm_clk_create(p,e,o,i,r,s,n,d)                                  \
+       nvkm_clk_create_((p), (e), (o), (i), (r), (s), (n), sizeof(**d),  \
+                             (void **)d)
+#define nvkm_clk_destroy(p) ({                                            \
+       struct nvkm_clk *clk = (p);                                       \
+       _nvkm_clk_dtor(nv_object(clk));                                   \
+})
+#define nvkm_clk_init(p) ({                                               \
+       struct nvkm_clk *clk = (p);                                       \
+       _nvkm_clk_init(nv_object(clk));                                   \
+})
+#define nvkm_clk_fini(p,s) ({                                             \
+       struct nvkm_clk *clk = (p);                                       \
+       _nvkm_clk_fini(nv_object(clk), (s));                              \
+})
+
+int  nvkm_clk_create_(struct nvkm_object *, struct nvkm_object *,
+                          struct nvkm_oclass *,
+                          struct nvkm_domain *, struct nvkm_pstate *,
+                          int, bool, int, void **);
+void _nvkm_clk_dtor(struct nvkm_object *);
+int  _nvkm_clk_init(struct nvkm_object *);
+int  _nvkm_clk_fini(struct nvkm_object *, bool);
+
+extern struct nvkm_oclass nv04_clk_oclass;
+extern struct nvkm_oclass nv40_clk_oclass;
+extern struct nvkm_oclass *nv50_clk_oclass;
+extern struct nvkm_oclass *g84_clk_oclass;
+extern struct nvkm_oclass *mcp77_clk_oclass;
+extern struct nvkm_oclass gt215_clk_oclass;
+extern struct nvkm_oclass gf100_clk_oclass;
+extern struct nvkm_oclass gk104_clk_oclass;
+extern struct nvkm_oclass gk20a_clk_oclass;
+
+int nv04_clk_pll_set(struct nvkm_clk *, u32 type, u32 freq);
+int nv04_clk_pll_calc(struct nvkm_clk *, struct nvbios_pll *, int clk,
+                     struct nvkm_pll_vals *);
+int nv04_clk_pll_prog(struct nvkm_clk *, u32 reg1, struct nvkm_pll_vals *);
+int gt215_clk_pll_calc(struct nvkm_clk *, struct nvbios_pll *,
+                      int clk, struct nvkm_pll_vals *);
+
+int nvkm_clk_ustate(struct nvkm_clk *, int req, int pwr);
+int nvkm_clk_astate(struct nvkm_clk *, int req, int rel, bool wait);
+int nvkm_clk_dstate(struct nvkm_clk *, int req, int rel);
+int nvkm_clk_tstate(struct nvkm_clk *, int req, int rel);
+#endif
diff --git a/drivers/gpu/drm/nouveau/include/nvkm/subdev/devinit.h b/drivers/gpu/drm/nouveau/include/nvkm/subdev/devinit.h
new file mode 100644 (file)
index 0000000..d1bbe0d
--- /dev/null
@@ -0,0 +1,32 @@
+#ifndef __NVKM_DEVINIT_H__
+#define __NVKM_DEVINIT_H__
+#include <core/subdev.h>
+
+struct nvkm_devinit {
+       struct nvkm_subdev base;
+       bool post;
+       void (*meminit)(struct nvkm_devinit *);
+       int  (*pll_set)(struct nvkm_devinit *, u32 type, u32 freq);
+       u32  (*mmio)(struct nvkm_devinit *, u32 addr);
+};
+
+static inline struct nvkm_devinit *
+nvkm_devinit(void *obj)
+{
+       return (void *)nvkm_subdev(obj, NVDEV_SUBDEV_DEVINIT);
+}
+
+extern struct nvkm_oclass *nv04_devinit_oclass;
+extern struct nvkm_oclass *nv05_devinit_oclass;
+extern struct nvkm_oclass *nv10_devinit_oclass;
+extern struct nvkm_oclass *nv1a_devinit_oclass;
+extern struct nvkm_oclass *nv20_devinit_oclass;
+extern struct nvkm_oclass *nv50_devinit_oclass;
+extern struct nvkm_oclass *g84_devinit_oclass;
+extern struct nvkm_oclass *g98_devinit_oclass;
+extern struct nvkm_oclass *gt215_devinit_oclass;
+extern struct nvkm_oclass *mcp89_devinit_oclass;
+extern struct nvkm_oclass *gf100_devinit_oclass;
+extern struct nvkm_oclass *gm107_devinit_oclass;
+extern struct nvkm_oclass *gm204_devinit_oclass;
+#endif
diff --git a/drivers/gpu/drm/nouveau/include/nvkm/subdev/fb.h b/drivers/gpu/drm/nouveau/include/nvkm/subdev/fb.h
new file mode 100644 (file)
index 0000000..16da56c
--- /dev/null
@@ -0,0 +1,154 @@
+#ifndef __NVKM_FB_H__
+#define __NVKM_FB_H__
+#include <core/subdev.h>
+
+#include <subdev/mmu.h>
+
+/* memory type/access flags, do not match hardware values */
+#define NV_MEM_ACCESS_RO  1
+#define NV_MEM_ACCESS_WO  2
+#define NV_MEM_ACCESS_RW (NV_MEM_ACCESS_RO | NV_MEM_ACCESS_WO)
+#define NV_MEM_ACCESS_SYS 4
+#define NV_MEM_ACCESS_VM  8
+#define NV_MEM_ACCESS_NOSNOOP 16
+
+#define NV_MEM_TARGET_VRAM        0
+#define NV_MEM_TARGET_PCI         1
+#define NV_MEM_TARGET_PCI_NOSNOOP 2
+#define NV_MEM_TARGET_VM          3
+#define NV_MEM_TARGET_GART        4
+
+#define NV_MEM_TYPE_VM 0x7f
+#define NV_MEM_COMP_VM 0x03
+
+struct nvkm_mem {
+       struct drm_device *dev;
+
+       struct nvkm_vma bar_vma;
+       struct nvkm_vma vma[2];
+       u8  page_shift;
+
+       struct nvkm_mm_node *tag;
+       struct list_head regions;
+       dma_addr_t *pages;
+       u32 memtype;
+       u64 offset;
+       u64 size;
+       struct sg_table *sg;
+};
+
+struct nvkm_fb_tile {
+       struct nvkm_mm_node *tag;
+       u32 addr;
+       u32 limit;
+       u32 pitch;
+       u32 zcomp;
+};
+
+struct nvkm_fb {
+       struct nvkm_subdev base;
+
+       bool (*memtype_valid)(struct nvkm_fb *, u32 memtype);
+
+       struct nvkm_ram *ram;
+
+       struct nvkm_mm vram;
+       struct nvkm_mm tags;
+
+       struct {
+               struct nvkm_fb_tile region[16];
+               int regions;
+               void (*init)(struct nvkm_fb *, int i, u32 addr, u32 size,
+                            u32 pitch, u32 flags, struct nvkm_fb_tile *);
+               void (*comp)(struct nvkm_fb *, int i, u32 size, u32 flags,
+                            struct nvkm_fb_tile *);
+               void (*fini)(struct nvkm_fb *, int i, struct nvkm_fb_tile *);
+               void (*prog)(struct nvkm_fb *, int i, struct nvkm_fb_tile *);
+       } tile;
+};
+
+static inline struct nvkm_fb *
+nvkm_fb(void *obj)
+{
+       /* fbram uses this before device subdev pointer is valid */
+       if (nv_iclass(obj, NV_SUBDEV_CLASS) &&
+           nv_subidx(obj) == NVDEV_SUBDEV_FB)
+               return obj;
+
+       return (void *)nvkm_subdev(obj, NVDEV_SUBDEV_FB);
+}
+
+extern struct nvkm_oclass *nv04_fb_oclass;
+extern struct nvkm_oclass *nv10_fb_oclass;
+extern struct nvkm_oclass *nv1a_fb_oclass;
+extern struct nvkm_oclass *nv20_fb_oclass;
+extern struct nvkm_oclass *nv25_fb_oclass;
+extern struct nvkm_oclass *nv30_fb_oclass;
+extern struct nvkm_oclass *nv35_fb_oclass;
+extern struct nvkm_oclass *nv36_fb_oclass;
+extern struct nvkm_oclass *nv40_fb_oclass;
+extern struct nvkm_oclass *nv41_fb_oclass;
+extern struct nvkm_oclass *nv44_fb_oclass;
+extern struct nvkm_oclass *nv46_fb_oclass;
+extern struct nvkm_oclass *nv47_fb_oclass;
+extern struct nvkm_oclass *nv49_fb_oclass;
+extern struct nvkm_oclass *nv4e_fb_oclass;
+extern struct nvkm_oclass *nv50_fb_oclass;
+extern struct nvkm_oclass *g84_fb_oclass;
+extern struct nvkm_oclass *gt215_fb_oclass;
+extern struct nvkm_oclass *mcp77_fb_oclass;
+extern struct nvkm_oclass *mcp89_fb_oclass;
+extern struct nvkm_oclass *gf100_fb_oclass;
+extern struct nvkm_oclass *gk104_fb_oclass;
+extern struct nvkm_oclass *gk20a_fb_oclass;
+extern struct nvkm_oclass *gm107_fb_oclass;
+
+#include <subdev/bios.h>
+#include <subdev/bios/ramcfg.h>
+
+struct nvkm_ram_data {
+       struct list_head head;
+       struct nvbios_ramcfg bios;
+       u32 freq;
+};
+
+struct nvkm_ram {
+       struct nvkm_object base;
+       enum {
+               NV_MEM_TYPE_UNKNOWN = 0,
+               NV_MEM_TYPE_STOLEN,
+               NV_MEM_TYPE_SGRAM,
+               NV_MEM_TYPE_SDRAM,
+               NV_MEM_TYPE_DDR1,
+               NV_MEM_TYPE_DDR2,
+               NV_MEM_TYPE_DDR3,
+               NV_MEM_TYPE_GDDR2,
+               NV_MEM_TYPE_GDDR3,
+               NV_MEM_TYPE_GDDR4,
+               NV_MEM_TYPE_GDDR5
+       } type;
+       u64 stolen;
+       u64 size;
+       u32 tags;
+
+       int ranks;
+       int parts;
+       int part_mask;
+
+       int  (*get)(struct nvkm_fb *, u64 size, u32 align, u32 size_nc,
+                   u32 type, struct nvkm_mem **);
+       void (*put)(struct nvkm_fb *, struct nvkm_mem **);
+
+       int  (*calc)(struct nvkm_fb *, u32 freq);
+       int  (*prog)(struct nvkm_fb *);
+       void (*tidy)(struct nvkm_fb *);
+       u32 freq;
+       u32 mr[16];
+       u32 mr1_nuts;
+
+       struct nvkm_ram_data *next;
+       struct nvkm_ram_data former;
+       struct nvkm_ram_data xition;
+       struct nvkm_ram_data target;
+};
+#endif
diff --git a/drivers/gpu/drm/nouveau/include/nvkm/subdev/fuse.h b/drivers/gpu/drm/nouveau/include/nvkm/subdev/fuse.h
new file mode 100644 (file)
index 0000000..a138478
--- /dev/null
@@ -0,0 +1,28 @@
+#ifndef __NVKM_FUSE_H__
+#define __NVKM_FUSE_H__
+#include <core/subdev.h>
+#include <core/device.h>
+
+struct nvkm_fuse {
+       struct nvkm_subdev base;
+};
+
+static inline struct nvkm_fuse *
+nvkm_fuse(void *obj)
+{
+       return (void *)nvkm_subdev(obj, NVDEV_SUBDEV_FUSE);
+}
+
+#define nvkm_fuse_create(p, e, o, d)                                        \
+       nvkm_fuse_create_((p), (e), (o), sizeof(**d), (void **)d)
+
+int  nvkm_fuse_create_(struct nvkm_object *, struct nvkm_object *,
+                         struct nvkm_oclass *, int, void **);
+void _nvkm_fuse_dtor(struct nvkm_object *);
+int  _nvkm_fuse_init(struct nvkm_object *);
+#define _nvkm_fuse_fini _nvkm_subdev_fini
+
+extern struct nvkm_oclass nv50_fuse_oclass;
+extern struct nvkm_oclass gf100_fuse_oclass;
+extern struct nvkm_oclass gm107_fuse_oclass;
+#endif
diff --git a/drivers/gpu/drm/nouveau/include/nvkm/subdev/gpio.h b/drivers/gpu/drm/nouveau/include/nvkm/subdev/gpio.h
new file mode 100644 (file)
index 0000000..ca5099a
--- /dev/null
@@ -0,0 +1,44 @@
+#ifndef __NVKM_GPIO_H__
+#define __NVKM_GPIO_H__
+#include <core/subdev.h>
+#include <core/event.h>
+
+#include <subdev/bios.h>
+#include <subdev/bios/gpio.h>
+
+struct nvkm_gpio_ntfy_req {
+#define NVKM_GPIO_HI                                                       0x01
+#define NVKM_GPIO_LO                                                       0x02
+#define NVKM_GPIO_TOGGLED                                                  0x03
+       u8 mask;
+       u8 line;
+};
+
+struct nvkm_gpio_ntfy_rep {
+       u8 mask;
+};
+
+struct nvkm_gpio {
+       struct nvkm_subdev base;
+
+       struct nvkm_event event;
+
+       void (*reset)(struct nvkm_gpio *, u8 func);
+       int  (*find)(struct nvkm_gpio *, int idx, u8 tag, u8 line,
+                    struct dcb_gpio_func *);
+       int  (*set)(struct nvkm_gpio *, int idx, u8 tag, u8 line, int state);
+       int  (*get)(struct nvkm_gpio *, int idx, u8 tag, u8 line);
+};
+
+static inline struct nvkm_gpio *
+nvkm_gpio(void *obj)
+{
+       return (void *)nvkm_subdev(obj, NVDEV_SUBDEV_GPIO);
+}
+
+extern struct nvkm_oclass *nv10_gpio_oclass;
+extern struct nvkm_oclass *nv50_gpio_oclass;
+extern struct nvkm_oclass *g94_gpio_oclass;
+extern struct nvkm_oclass *gf110_gpio_oclass;
+extern struct nvkm_oclass *gk104_gpio_oclass;
+#endif
diff --git a/drivers/gpu/drm/nouveau/include/nvkm/subdev/i2c.h b/drivers/gpu/drm/nouveau/include/nvkm/subdev/i2c.h
new file mode 100644 (file)
index 0000000..a2e3373
--- /dev/null
@@ -0,0 +1,135 @@
+#ifndef __NVKM_I2C_H__
+#define __NVKM_I2C_H__
+#include <core/subdev.h>
+#include <core/event.h>
+
+#include <subdev/bios.h>
+#include <subdev/bios/i2c.h>
+
+#define NV_I2C_PORT(n)    (0x00 + (n))
+#define NV_I2C_AUX(n)     (0x10 + (n))
+#define NV_I2C_EXT(n)     (0x20 + (n))
+#define NV_I2C_DEFAULT(n) (0x80 + (n))
+
+#define NV_I2C_TYPE_DCBI2C(n) (0x0000 | (n))
+#define NV_I2C_TYPE_EXTDDC(e) (0x0005 | (e) << 8)
+#define NV_I2C_TYPE_EXTAUX(e) (0x0006 | (e) << 8)
+
+struct nvkm_i2c_ntfy_req {
+#define NVKM_I2C_PLUG                                                      0x01
+#define NVKM_I2C_UNPLUG                                                    0x02
+#define NVKM_I2C_IRQ                                                       0x04
+#define NVKM_I2C_DONE                                                      0x08
+#define NVKM_I2C_ANY                                                       0x0f
+       u8 mask;
+       u8 port;
+};
+
+struct nvkm_i2c_ntfy_rep {
+       u8 mask;
+};
+
+struct nvkm_i2c_port {
+       struct nvkm_object base;
+       struct i2c_adapter adapter;
+       struct mutex mutex;
+
+       struct list_head head;
+       u8  index;
+       int aux;
+
+       const struct nvkm_i2c_func *func;
+};
+
+struct nvkm_i2c_func {
+       void (*drive_scl)(struct nvkm_i2c_port *, int);
+       void (*drive_sda)(struct nvkm_i2c_port *, int);
+       int  (*sense_scl)(struct nvkm_i2c_port *);
+       int  (*sense_sda)(struct nvkm_i2c_port *);
+
+       int  (*aux)(struct nvkm_i2c_port *, bool, u8, u32, u8 *, u8);
+       int  (*pattern)(struct nvkm_i2c_port *, int pattern);
+       int  (*lnk_ctl)(struct nvkm_i2c_port *, int nr, int bw, bool enh);
+       int  (*drv_ctl)(struct nvkm_i2c_port *, int lane, int sw, int pe);
+};
+
+struct nvkm_i2c_board_info {
+       struct i2c_board_info dev;
+       u8 udelay; /* set to 0 to use the standard delay */
+};
+
+struct nvkm_i2c {
+       struct nvkm_subdev base;
+       struct nvkm_event event;
+
+       struct nvkm_i2c_port *(*find)(struct nvkm_i2c *, u8 index);
+       struct nvkm_i2c_port *(*find_type)(struct nvkm_i2c *, u16 type);
+       int  (*acquire_pad)(struct nvkm_i2c_port *, unsigned long timeout);
+       void (*release_pad)(struct nvkm_i2c_port *);
+       int  (*acquire)(struct nvkm_i2c_port *, unsigned long timeout);
+       void (*release)(struct nvkm_i2c_port *);
+       int  (*identify)(struct nvkm_i2c *, int index,
+                        const char *what, struct nvkm_i2c_board_info *,
+                        bool (*match)(struct nvkm_i2c_port *,
+                                      struct i2c_board_info *, void *),
+                        void *);
+
+       wait_queue_head_t wait;
+       struct list_head ports;
+};
+
+static inline struct nvkm_i2c *
+nvkm_i2c(void *obj)
+{
+       return (void *)nvkm_subdev(obj, NVDEV_SUBDEV_I2C);
+}
+
+extern struct nvkm_oclass *nv04_i2c_oclass;
+extern struct nvkm_oclass *nv4e_i2c_oclass;
+extern struct nvkm_oclass *nv50_i2c_oclass;
+extern struct nvkm_oclass *g94_i2c_oclass;
+extern struct nvkm_oclass *gf110_i2c_oclass;
+extern struct nvkm_oclass *gf117_i2c_oclass;
+extern struct nvkm_oclass *gk104_i2c_oclass;
+extern struct nvkm_oclass *gm204_i2c_oclass;
+
+static inline int
+nv_rdi2cr(struct nvkm_i2c_port *port, u8 addr, u8 reg)
+{
+       u8 val;
+       struct i2c_msg msgs[] = {
+               { .addr = addr, .flags = 0, .len = 1, .buf = &reg },
+               { .addr = addr, .flags = I2C_M_RD, .len = 1, .buf = &val },
+       };
+
+       int ret = i2c_transfer(&port->adapter, msgs, 2);
+       if (ret != 2)
+               return -EIO;
+
+       return val;
+}
+
+static inline int
+nv_wri2cr(struct nvkm_i2c_port *port, u8 addr, u8 reg, u8 val)
+{
+       u8 buf[2] = { reg, val };
+       struct i2c_msg msgs[] = {
+               { .addr = addr, .flags = 0, .len = 2, .buf = buf },
+       };
+
+       int ret = i2c_transfer(&port->adapter, msgs, 1);
+       if (ret != 1)
+               return -EIO;
+
+       return 0;
+}
+
+static inline bool
+nv_probe_i2c(struct nvkm_i2c_port *port, u8 addr)
+{
+       return nv_rdi2cr(port, addr, 0) >= 0;
+}
+
+int nv_rdaux(struct nvkm_i2c_port *, u32 addr, u8 *data, u8 size);
+int nv_wraux(struct nvkm_i2c_port *, u32 addr, u8 *data, u8 size);
+#endif
diff --git a/drivers/gpu/drm/nouveau/include/nvkm/subdev/ibus.h b/drivers/gpu/drm/nouveau/include/nvkm/subdev/ibus.h
new file mode 100644 (file)
index 0000000..2150d8a
--- /dev/null
@@ -0,0 +1,32 @@
+#ifndef __NVKM_IBUS_H__
+#define __NVKM_IBUS_H__
+#include <core/subdev.h>
+
+struct nvkm_ibus {
+       struct nvkm_subdev base;
+};
+
+static inline struct nvkm_ibus *
+nvkm_ibus(void *obj)
+{
+       return (void *)nvkm_subdev(obj, NVDEV_SUBDEV_IBUS);
+}
+
+#define nvkm_ibus_create(p,e,o,d)                                           \
+       nvkm_subdev_create_((p), (e), (o), 0, "PIBUS", "ibus",              \
+                              sizeof(**d), (void **)d)
+#define nvkm_ibus_destroy(p)                                                \
+       nvkm_subdev_destroy(&(p)->base)
+#define nvkm_ibus_init(p)                                                   \
+       nvkm_subdev_init(&(p)->base)
+#define nvkm_ibus_fini(p,s)                                                 \
+       nvkm_subdev_fini(&(p)->base, (s))
+
+#define _nvkm_ibus_dtor _nvkm_subdev_dtor
+#define _nvkm_ibus_init _nvkm_subdev_init
+#define _nvkm_ibus_fini _nvkm_subdev_fini
+
+extern struct nvkm_oclass gf100_ibus_oclass;
+extern struct nvkm_oclass gk104_ibus_oclass;
+extern struct nvkm_oclass gk20a_ibus_oclass;
+#endif
diff --git a/drivers/gpu/drm/nouveau/include/nvkm/subdev/instmem.h b/drivers/gpu/drm/nouveau/include/nvkm/subdev/instmem.h
new file mode 100644 (file)
index 0000000..d104c1a
--- /dev/null
@@ -0,0 +1,48 @@
+#ifndef __NVKM_INSTMEM_H__
+#define __NVKM_INSTMEM_H__
+#include <core/subdev.h>
+
+struct nvkm_instobj {
+       struct nvkm_object base;
+       struct list_head head;
+       u32 *suspend;
+       u64 addr;
+       u32 size;
+};
+
+static inline struct nvkm_instobj *
+nv_memobj(void *obj)
+{
+#if CONFIG_NOUVEAU_DEBUG >= NV_DBG_PARANOIA
+       if (unlikely(!nv_iclass(obj, NV_MEMOBJ_CLASS)))
+               nv_assert("BAD CAST -> NvMemObj, %08x", nv_hclass(obj));
+#endif
+       return obj;
+}
+
+struct nvkm_instmem {
+       struct nvkm_subdev base;
+       struct list_head list;
+
+       u32 reserved;
+       int (*alloc)(struct nvkm_instmem *, struct nvkm_object *,
+                    u32 size, u32 align, struct nvkm_object **);
+};
+
+static inline struct nvkm_instmem *
+nvkm_instmem(void *obj)
+{
+       /* nv04/nv40 impls need to create objects in their constructor,
+        * which is before the subdev pointer is valid
+        */
+       if (nv_iclass(obj, NV_SUBDEV_CLASS) &&
+           nv_subidx(obj) == NVDEV_SUBDEV_INSTMEM)
+               return obj;
+
+       return (void *)nvkm_subdev(obj, NVDEV_SUBDEV_INSTMEM);
+}
+
+extern struct nvkm_oclass *nv04_instmem_oclass;
+extern struct nvkm_oclass *nv40_instmem_oclass;
+extern struct nvkm_oclass *nv50_instmem_oclass;
+#endif
diff --git a/drivers/gpu/drm/nouveau/include/nvkm/subdev/ltc.h b/drivers/gpu/drm/nouveau/include/nvkm/subdev/ltc.h
new file mode 100644 (file)
index 0000000..cd5d29f
--- /dev/null
@@ -0,0 +1,31 @@
+#ifndef __NVKM_LTC_H__
+#define __NVKM_LTC_H__
+#include <core/subdev.h>
+struct nvkm_mm_node;
+
+#define NVKM_LTC_MAX_ZBC_CNT 16
+
+struct nvkm_ltc {
+       struct nvkm_subdev base;
+
+       int  (*tags_alloc)(struct nvkm_ltc *, u32 count,
+                          struct nvkm_mm_node **);
+       void (*tags_free)(struct nvkm_ltc *, struct nvkm_mm_node **);
+       void (*tags_clear)(struct nvkm_ltc *, u32 first, u32 count);
+
+       int zbc_min;
+       int zbc_max;
+       int (*zbc_color_get)(struct nvkm_ltc *, int index, const u32[4]);
+       int (*zbc_depth_get)(struct nvkm_ltc *, int index, const u32);
+};
+
+static inline struct nvkm_ltc *
+nvkm_ltc(void *obj)
+{
+       return (void *)nvkm_subdev(obj, NVDEV_SUBDEV_LTC);
+}
+
+extern struct nvkm_oclass *gf100_ltc_oclass;
+extern struct nvkm_oclass *gk104_ltc_oclass;
+extern struct nvkm_oclass *gm107_ltc_oclass;
+#endif
diff --git a/drivers/gpu/drm/nouveau/include/nvkm/subdev/mc.h b/drivers/gpu/drm/nouveau/include/nvkm/subdev/mc.h
new file mode 100644 (file)
index 0000000..055bea7
--- /dev/null
@@ -0,0 +1,28 @@
+#ifndef __NVKM_MC_H__
+#define __NVKM_MC_H__
+#include <core/subdev.h>
+
+struct nvkm_mc {
+       struct nvkm_subdev base;
+       bool use_msi;
+       unsigned int irq;
+       void (*unk260)(struct nvkm_mc *, u32);
+};
+
+static inline struct nvkm_mc *
+nvkm_mc(void *obj)
+{
+       return (void *)nvkm_subdev(obj, NVDEV_SUBDEV_MC);
+}
+
+extern struct nvkm_oclass *nv04_mc_oclass;
+extern struct nvkm_oclass *nv40_mc_oclass;
+extern struct nvkm_oclass *nv44_mc_oclass;
+extern struct nvkm_oclass *nv4c_mc_oclass;
+extern struct nvkm_oclass *nv50_mc_oclass;
+extern struct nvkm_oclass *g94_mc_oclass;
+extern struct nvkm_oclass *g98_mc_oclass;
+extern struct nvkm_oclass *gf100_mc_oclass;
+extern struct nvkm_oclass *gf106_mc_oclass;
+extern struct nvkm_oclass *gk20a_mc_oclass;
+#endif
diff --git a/drivers/gpu/drm/nouveau/include/nvkm/subdev/mmu.h b/drivers/gpu/drm/nouveau/include/nvkm/subdev/mmu.h
new file mode 100644 (file)
index 0000000..3a53687
--- /dev/null
@@ -0,0 +1,104 @@
+#ifndef __NVKM_MMU_H__
+#define __NVKM_MMU_H__
+#include <core/subdev.h>
+#include <core/mm.h>
+struct nvkm_device;
+struct nvkm_mem;
+
+struct nvkm_vm_pgt {
+       struct nvkm_gpuobj *obj[2];
+       u32 refcount[2];
+};
+
+struct nvkm_vm_pgd {
+       struct list_head head;
+       struct nvkm_gpuobj *obj;
+};
+
+struct nvkm_vma {
+       struct list_head head;
+       int refcount;
+       struct nvkm_vm *vm;
+       struct nvkm_mm_node *node;
+       u64 offset;
+       u32 access;
+};
+
+struct nvkm_vm {
+       struct nvkm_mmu *mmu;
+       struct nvkm_mm mm;
+       struct kref refcount;
+
+       struct list_head pgd_list;
+       atomic_t engref[NVDEV_SUBDEV_NR];
+
+       struct nvkm_vm_pgt *pgt;
+       u32 fpde;
+       u32 lpde;
+};
+
+struct nvkm_mmu {
+       struct nvkm_subdev base;
+
+       u64 limit;
+       u8  dma_bits;
+       u32 pgt_bits;
+       u8  spg_shift;
+       u8  lpg_shift;
+
+       int  (*create)(struct nvkm_mmu *, u64 offset, u64 length,
+                      u64 mm_offset, struct nvkm_vm **);
+
+       void (*map_pgt)(struct nvkm_gpuobj *pgd, u32 pde,
+                       struct nvkm_gpuobj *pgt[2]);
+       void (*map)(struct nvkm_vma *, struct nvkm_gpuobj *,
+                   struct nvkm_mem *, u32 pte, u32 cnt,
+                   u64 phys, u64 delta);
+       void (*map_sg)(struct nvkm_vma *, struct nvkm_gpuobj *,
+                      struct nvkm_mem *, u32 pte, u32 cnt, dma_addr_t *);
+       void (*unmap)(struct nvkm_gpuobj *pgt, u32 pte, u32 cnt);
+       void (*flush)(struct nvkm_vm *);
+};
+
+static inline struct nvkm_mmu *
+nvkm_mmu(void *obj)
+{
+       return (void *)nvkm_subdev(obj, NVDEV_SUBDEV_MMU);
+}
+
+#define nvkm_mmu_create(p,e,o,i,f,d)                                      \
+       nvkm_subdev_create((p), (e), (o), 0, (i), (f), (d))
+#define nvkm_mmu_destroy(p)                                               \
+       nvkm_subdev_destroy(&(p)->base)
+#define nvkm_mmu_init(p)                                                  \
+       nvkm_subdev_init(&(p)->base)
+#define nvkm_mmu_fini(p,s)                                                \
+       nvkm_subdev_fini(&(p)->base, (s))
+
+#define _nvkm_mmu_dtor _nvkm_subdev_dtor
+#define _nvkm_mmu_init _nvkm_subdev_init
+#define _nvkm_mmu_fini _nvkm_subdev_fini
+
+extern struct nvkm_oclass nv04_mmu_oclass;
+extern struct nvkm_oclass nv41_mmu_oclass;
+extern struct nvkm_oclass nv44_mmu_oclass;
+extern struct nvkm_oclass nv50_mmu_oclass;
+extern struct nvkm_oclass gf100_mmu_oclass;
+
+int  nv04_vm_create(struct nvkm_mmu *, u64, u64, u64,
+                   struct nvkm_vm **);
+void nv04_mmu_dtor(struct nvkm_object *);
+
+int  nvkm_vm_create(struct nvkm_mmu *, u64 offset, u64 length, u64 mm_offset,
+                   u32 block, struct nvkm_vm **);
+int  nvkm_vm_new(struct nvkm_device *, u64 offset, u64 length, u64 mm_offset,
+                struct nvkm_vm **);
+int  nvkm_vm_ref(struct nvkm_vm *, struct nvkm_vm **, struct nvkm_gpuobj *pgd);
+int  nvkm_vm_get(struct nvkm_vm *, u64 size, u32 page_shift, u32 access,
+                struct nvkm_vma *);
+void nvkm_vm_put(struct nvkm_vma *);
+void nvkm_vm_map(struct nvkm_vma *, struct nvkm_mem *);
+void nvkm_vm_map_at(struct nvkm_vma *, u64 offset, struct nvkm_mem *);
+void nvkm_vm_unmap(struct nvkm_vma *);
+void nvkm_vm_unmap_at(struct nvkm_vma *, u64 offset, u64 length);
+#endif
diff --git a/drivers/gpu/drm/nouveau/include/nvkm/subdev/mxm.h b/drivers/gpu/drm/nouveau/include/nvkm/subdev/mxm.h
new file mode 100644 (file)
index 0000000..fba6134
--- /dev/null
@@ -0,0 +1,34 @@
+#ifndef __NVKM_MXM_H__
+#define __NVKM_MXM_H__
+#include <core/subdev.h>
+
+#define MXM_SANITISE_DCB 0x00000001
+
+struct nvkm_mxm {
+       struct nvkm_subdev base;
+       u32 action;
+       u8 *mxms;
+};
+
+static inline struct nvkm_mxm *
+nvkm_mxm(void *obj)
+{
+       return (void *)nvkm_subdev(obj, NVDEV_SUBDEV_MXM);
+}
+
+#define nvkm_mxm_create(p,e,o,d)                                            \
+       nvkm_mxm_create_((p), (e), (o), sizeof(**d), (void **)d)
+#define nvkm_mxm_init(p)                                                    \
+       nvkm_subdev_init(&(p)->base)
+#define nvkm_mxm_fini(p,s)                                                  \
+       nvkm_subdev_fini(&(p)->base, (s))
+int  nvkm_mxm_create_(struct nvkm_object *, struct nvkm_object *,
+                        struct nvkm_oclass *, int, void **);
+void nvkm_mxm_destroy(struct nvkm_mxm *);
+
+#define _nvkm_mxm_dtor _nvkm_subdev_dtor
+#define _nvkm_mxm_init _nvkm_subdev_init
+#define _nvkm_mxm_fini _nvkm_subdev_fini
+
+extern struct nvkm_oclass nv50_mxm_oclass;
+#endif
diff --git a/drivers/gpu/drm/nouveau/include/nvkm/subdev/pmu.h b/drivers/gpu/drm/nouveau/include/nvkm/subdev/pmu.h
new file mode 100644 (file)
index 0000000..7b86acc
--- /dev/null
@@ -0,0 +1,53 @@
+#ifndef __NVKM_PMU_H__
+#define __NVKM_PMU_H__
+#include <core/subdev.h>
+
+struct nvkm_pmu {
+       struct nvkm_subdev base;
+
+       struct {
+               u32 base;
+               u32 size;
+       } send;
+
+       struct {
+               u32 base;
+               u32 size;
+
+               struct work_struct work;
+               wait_queue_head_t wait;
+               u32 process;
+               u32 message;
+               u32 data[2];
+       } recv;
+
+       int  (*message)(struct nvkm_pmu *, u32[2], u32, u32, u32, u32);
+       void (*pgob)(struct nvkm_pmu *, bool);
+};
+
+static inline struct nvkm_pmu *
+nvkm_pmu(void *obj)
+{
+       return (void *)nvkm_subdev(obj, NVDEV_SUBDEV_PMU);
+}
+
+extern struct nvkm_oclass *gt215_pmu_oclass;
+extern struct nvkm_oclass *gf100_pmu_oclass;
+extern struct nvkm_oclass *gf110_pmu_oclass;
+extern struct nvkm_oclass *gk104_pmu_oclass;
+extern struct nvkm_oclass *gk208_pmu_oclass;
+extern struct nvkm_oclass *gk20a_pmu_oclass;
+
+/* interface to MEMX process running on PMU */
+struct nvkm_memx;
+int  nvkm_memx_init(struct nvkm_pmu *, struct nvkm_memx **);
+int  nvkm_memx_fini(struct nvkm_memx **, bool exec);
+void nvkm_memx_wr32(struct nvkm_memx *, u32 addr, u32 data);
+void nvkm_memx_wait(struct nvkm_memx *, u32 addr, u32 mask, u32 data, u32 nsec);
+void nvkm_memx_nsec(struct nvkm_memx *, u32 nsec);
+void nvkm_memx_wait_vblank(struct nvkm_memx *);
+void nvkm_memx_train(struct nvkm_memx *);
+int  nvkm_memx_train_result(struct nvkm_pmu *, u32 *, int);
+void nvkm_memx_block(struct nvkm_memx *);
+void nvkm_memx_unblock(struct nvkm_memx *);
+#endif
diff --git a/drivers/gpu/drm/nouveau/include/nvkm/subdev/therm.h b/drivers/gpu/drm/nouveau/include/nvkm/subdev/therm.h
new file mode 100644 (file)
index 0000000..6662829
--- /dev/null
@@ -0,0 +1,79 @@
+#ifndef __NVKM_THERM_H__
+#define __NVKM_THERM_H__
+#include <core/subdev.h>
+
+enum nvkm_therm_fan_mode {
+       NVKM_THERM_CTRL_NONE = 0,
+       NVKM_THERM_CTRL_MANUAL = 1,
+       NVKM_THERM_CTRL_AUTO = 2,
+};
+
+enum nvkm_therm_attr_type {
+       NVKM_THERM_ATTR_FAN_MIN_DUTY = 0,
+       NVKM_THERM_ATTR_FAN_MAX_DUTY = 1,
+       NVKM_THERM_ATTR_FAN_MODE = 2,
+
+       NVKM_THERM_ATTR_THRS_FAN_BOOST = 10,
+       NVKM_THERM_ATTR_THRS_FAN_BOOST_HYST = 11,
+       NVKM_THERM_ATTR_THRS_DOWN_CLK = 12,
+       NVKM_THERM_ATTR_THRS_DOWN_CLK_HYST = 13,
+       NVKM_THERM_ATTR_THRS_CRITICAL = 14,
+       NVKM_THERM_ATTR_THRS_CRITICAL_HYST = 15,
+       NVKM_THERM_ATTR_THRS_SHUTDOWN = 16,
+       NVKM_THERM_ATTR_THRS_SHUTDOWN_HYST = 17,
+};
+
+struct nvkm_therm {
+       struct nvkm_subdev base;
+
+       int (*pwm_ctrl)(struct nvkm_therm *, int line, bool);
+       int (*pwm_get)(struct nvkm_therm *, int line, u32 *, u32 *);
+       int (*pwm_set)(struct nvkm_therm *, int line, u32, u32);
+       int (*pwm_clock)(struct nvkm_therm *, int line);
+
+       int (*fan_get)(struct nvkm_therm *);
+       int (*fan_set)(struct nvkm_therm *, int);
+       int (*fan_sense)(struct nvkm_therm *);
+
+       int (*temp_get)(struct nvkm_therm *);
+
+       int (*attr_get)(struct nvkm_therm *, enum nvkm_therm_attr_type);
+       int (*attr_set)(struct nvkm_therm *, enum nvkm_therm_attr_type, int);
+};
+
+static inline struct nvkm_therm *
+nvkm_therm(void *obj)
+{
+       return (void *)nvkm_subdev(obj, NVDEV_SUBDEV_THERM);
+}
+
+#define nvkm_therm_create(p,e,o,d)                                          \
+       nvkm_therm_create_((p), (e), (o), sizeof(**d), (void **)d)
+#define nvkm_therm_destroy(p) ({                                            \
+       struct nvkm_therm *therm = (p);                                     \
+        _nvkm_therm_dtor(nv_object(therm));                                 \
+})
+#define nvkm_therm_init(p) ({                                               \
+       struct nvkm_therm *therm = (p);                                     \
+        _nvkm_therm_init(nv_object(therm));                                 \
+})
+#define nvkm_therm_fini(p,s) ({                                             \
+       struct nvkm_therm *therm = (p);                                     \
+        _nvkm_therm_init(nv_object(therm), (s));                            \
+})
+
+int  nvkm_therm_create_(struct nvkm_object *, struct nvkm_object *,
+                          struct nvkm_oclass *, int, void **);
+void _nvkm_therm_dtor(struct nvkm_object *);
+int  _nvkm_therm_init(struct nvkm_object *);
+int  _nvkm_therm_fini(struct nvkm_object *, bool);
+
+int  nvkm_therm_cstate(struct nvkm_therm *, int, int);
+
+extern struct nvkm_oclass nv40_therm_oclass;
+extern struct nvkm_oclass nv50_therm_oclass;
+extern struct nvkm_oclass g84_therm_oclass;
+extern struct nvkm_oclass gt215_therm_oclass;
+extern struct nvkm_oclass gf110_therm_oclass;
+extern struct nvkm_oclass gm107_therm_oclass;
+#endif
diff --git a/drivers/gpu/drm/nouveau/include/nvkm/subdev/timer.h b/drivers/gpu/drm/nouveau/include/nvkm/subdev/timer.h
new file mode 100644 (file)
index 0000000..4ad5508
--- /dev/null
@@ -0,0 +1,61 @@
+#ifndef __NVKM_TIMER_H__
+#define __NVKM_TIMER_H__
+#include <core/subdev.h>
+
+struct nvkm_alarm {
+       struct list_head head;
+       u64 timestamp;
+       void (*func)(struct nvkm_alarm *);
+};
+
+static inline void
+nvkm_alarm_init(struct nvkm_alarm *alarm,
+                  void (*func)(struct nvkm_alarm *))
+{
+       INIT_LIST_HEAD(&alarm->head);
+       alarm->func = func;
+}
+
+bool nvkm_timer_wait_eq(void *, u64 nsec, u32 addr, u32 mask, u32 data);
+bool nvkm_timer_wait_ne(void *, u64 nsec, u32 addr, u32 mask, u32 data);
+bool nvkm_timer_wait_cb(void *, u64 nsec, bool (*func)(void *), void *data);
+void nvkm_timer_alarm(void *, u32 nsec, struct nvkm_alarm *);
+void nvkm_timer_alarm_cancel(void *, struct nvkm_alarm *);
+
+#define NV_WAIT_DEFAULT 2000000000ULL
+#define nv_wait(o,a,m,v)                                                       \
+       nvkm_timer_wait_eq((o), NV_WAIT_DEFAULT, (a), (m), (v))
+#define nv_wait_ne(o,a,m,v)                                                    \
+       nvkm_timer_wait_ne((o), NV_WAIT_DEFAULT, (a), (m), (v))
+#define nv_wait_cb(o,c,d)                                                      \
+       nvkm_timer_wait_cb((o), NV_WAIT_DEFAULT, (c), (d))
+
+struct nvkm_timer {
+       struct nvkm_subdev base;
+       u64  (*read)(struct nvkm_timer *);
+       void (*alarm)(struct nvkm_timer *, u64 time, struct nvkm_alarm *);
+       void (*alarm_cancel)(struct nvkm_timer *, struct nvkm_alarm *);
+};
+
+static inline struct nvkm_timer *
+nvkm_timer(void *obj)
+{
+       return (void *)nvkm_subdev(obj, NVDEV_SUBDEV_TIMER);
+}
+
+#define nvkm_timer_create(p,e,o,d)                                          \
+       nvkm_subdev_create_((p), (e), (o), 0, "PTIMER", "timer",            \
+                              sizeof(**d), (void **)d)
+#define nvkm_timer_destroy(p)                                               \
+       nvkm_subdev_destroy(&(p)->base)
+#define nvkm_timer_init(p)                                                  \
+       nvkm_subdev_init(&(p)->base)
+#define nvkm_timer_fini(p,s)                                                \
+       nvkm_subdev_fini(&(p)->base, (s))
+
+int nvkm_timer_create_(struct nvkm_object *, struct nvkm_engine *,
+                         struct nvkm_oclass *, int size, void **);
+
+extern struct nvkm_oclass nv04_timer_oclass;
+extern struct nvkm_oclass gk20a_timer_oclass;
+#endif
diff --git a/drivers/gpu/drm/nouveau/include/nvkm/subdev/vga.h b/drivers/gpu/drm/nouveau/include/nvkm/subdev/vga.h
new file mode 100644 (file)
index 0000000..fee09ad
--- /dev/null
@@ -0,0 +1,30 @@
+#ifndef __NOUVEAU_VGA_H__
+#define __NOUVEAU_VGA_H__
+
+#include <core/os.h>
+
+/* access to various legacy io ports */
+u8   nv_rdport(void *obj, int head, u16 port);
+void nv_wrport(void *obj, int head, u16 port, u8 value);
+
+/* VGA Sequencer */
+u8   nv_rdvgas(void *obj, int head, u8 index);
+void nv_wrvgas(void *obj, int head, u8 index, u8 value);
+
+/* VGA Graphics */
+u8   nv_rdvgag(void *obj, int head, u8 index);
+void nv_wrvgag(void *obj, int head, u8 index, u8 value);
+
+/* VGA CRTC */
+u8   nv_rdvgac(void *obj, int head, u8 index);
+void nv_wrvgac(void *obj, int head, u8 index, u8 value);
+
+/* VGA indexed port access dispatcher */
+u8   nv_rdvgai(void *obj, int head, u16 port, u8 index);
+void nv_wrvgai(void *obj, int head, u16 port, u8 index, u8 value);
+
+bool nv_lockvgac(void *obj, bool lock);
+u8   nv_rdvgaowner(void *obj);
+void nv_wrvgaowner(void *obj, u8);
+
+#endif
diff --git a/drivers/gpu/drm/nouveau/include/nvkm/subdev/volt.h b/drivers/gpu/drm/nouveau/include/nvkm/subdev/volt.h
new file mode 100644 (file)
index 0000000..e3d7243
--- /dev/null
@@ -0,0 +1,58 @@
+#ifndef __NVKM_VOLT_H__
+#define __NVKM_VOLT_H__
+#include <core/subdev.h>
+
+struct nvkm_voltage {
+       u32 uv;
+       u8  id;
+};
+
+struct nvkm_volt {
+       struct nvkm_subdev base;
+
+       int (*vid_get)(struct nvkm_volt *);
+       int (*get)(struct nvkm_volt *);
+       int (*vid_set)(struct nvkm_volt *, u8 vid);
+       int (*set)(struct nvkm_volt *, u32 uv);
+       int (*set_id)(struct nvkm_volt *, u8 id, int condition);
+
+       u8 vid_mask;
+       u8 vid_nr;
+       struct {
+               u32 uv;
+               u8 vid;
+       } vid[256];
+};
+
+static inline struct nvkm_volt *
+nvkm_volt(void *obj)
+{
+       return (void *)nvkm_subdev(obj, NVDEV_SUBDEV_VOLT);
+}
+
+#define nvkm_volt_create(p, e, o, d)                                        \
+       nvkm_volt_create_((p), (e), (o), sizeof(**d), (void **)d)
+#define nvkm_volt_destroy(p) ({                                             \
+       struct nvkm_volt *v = (p);                                          \
+       _nvkm_volt_dtor(nv_object(v));                                      \
+})
+#define nvkm_volt_init(p) ({                                                \
+       struct nvkm_volt *v = (p);                                          \
+       _nvkm_volt_init(nv_object(v));                                      \
+})
+#define nvkm_volt_fini(p,s)                                                 \
+       nvkm_subdev_fini((p), (s))
+
+int  nvkm_volt_create_(struct nvkm_object *, struct nvkm_object *,
+                         struct nvkm_oclass *, int, void **);
+void _nvkm_volt_dtor(struct nvkm_object *);
+int  _nvkm_volt_init(struct nvkm_object *);
+#define _nvkm_volt_fini _nvkm_subdev_fini
+
+extern struct nvkm_oclass nv40_volt_oclass;
+extern struct nvkm_oclass gk20a_volt_oclass;
+
+int nvkm_voltgpio_init(struct nvkm_volt *);
+int nvkm_voltgpio_get(struct nvkm_volt *);
+int nvkm_voltgpio_set(struct nvkm_volt *, u8);
+#endif
index d39a150000680f0d5c77023670676d322d37bdb3..d8b0891a141c66ce6bdfef1de48d57bc7f9a3e9a 100644 (file)
@@ -100,7 +100,7 @@ static void
 nouveau_abi16_ntfy_fini(struct nouveau_abi16_chan *chan,
                        struct nouveau_abi16_ntfy *ntfy)
 {
-       nouveau_mm_free(&chan->heap, &ntfy->node);
+       nvkm_mm_free(&chan->heap, &ntfy->node);
        list_del(&ntfy->head);
        kfree(ntfy);
 }
@@ -128,7 +128,7 @@ nouveau_abi16_chan_fini(struct nouveau_abi16 *abi16,
        }
 
        if (chan->heap.block_size)
-               nouveau_mm_fini(&chan->heap);
+               nvkm_mm_fini(&chan->heap);
 
        /* destroy channel object, all children will be killed too */
        if (chan->chan) {
@@ -164,8 +164,8 @@ nouveau_abi16_ioctl_getparam(ABI16_IOCTL_ARGS)
        struct nouveau_cli *cli = nouveau_cli(file_priv);
        struct nouveau_drm *drm = nouveau_drm(dev);
        struct nvif_device *device = &drm->device;
-       struct nouveau_timer *ptimer = nvkm_timer(device);
-       struct nouveau_graph *graph = nvkm_gr(device);
+       struct nvkm_timer *ptimer = nvxx_timer(device);
+       struct nvkm_gr *gr = nvxx_gr(device);
        struct drm_nouveau_getparam *getparam = data;
 
        switch (getparam->param) {
@@ -173,19 +173,19 @@ nouveau_abi16_ioctl_getparam(ABI16_IOCTL_ARGS)
                getparam->value = device->info.chipset;
                break;
        case NOUVEAU_GETPARAM_PCI_VENDOR:
-               if (nv_device_is_pci(nvkm_device(device)))
+               if (nv_device_is_pci(nvxx_device(device)))
                        getparam->value = dev->pdev->vendor;
                else
                        getparam->value = 0;
                break;
        case NOUVEAU_GETPARAM_PCI_DEVICE:
-               if (nv_device_is_pci(nvkm_device(device)))
+               if (nv_device_is_pci(nvxx_device(device)))
                        getparam->value = dev->pdev->device;
                else
                        getparam->value = 0;
                break;
        case NOUVEAU_GETPARAM_BUS_TYPE:
-               if (!nv_device_is_pci(nvkm_device(device)))
+               if (!nv_device_is_pci(nvxx_device(device)))
                        getparam->value = 3;
                else
                if (drm_pci_device_is_agp(dev))
@@ -215,7 +215,7 @@ nouveau_abi16_ioctl_getparam(ABI16_IOCTL_ARGS)
                getparam->value = 1;
                break;
        case NOUVEAU_GETPARAM_GRAPH_UNITS:
-               getparam->value = graph->units ? graph->units(graph) : 0;
+               getparam->value = gr->units ? gr->units(gr) : 0;
                break;
        default:
                NV_PRINTK(debug, cli, "unknown parameter %lld\n", getparam->param);
@@ -324,7 +324,7 @@ nouveau_abi16_ioctl_channel_alloc(ABI16_IOCTL_ARGS)
        if (ret)
                goto done;
 
-       ret = nouveau_mm_init(&chan->heap, 0, PAGE_SIZE, 1);
+       ret = nvkm_mm_init(&chan->heap, 0, PAGE_SIZE, 1);
 done:
        if (ret)
                nouveau_abi16_chan_fini(abi16, chan);
@@ -448,8 +448,8 @@ nouveau_abi16_ioctl_notifierobj_alloc(ABI16_IOCTL_ARGS)
        list_add(&ntfy->head, &chan->notifiers);
        ntfy->handle = info->handle;
 
-       ret = nouveau_mm_head(&chan->heap, 0, 1, info->size, info->size, 1,
-                             &ntfy->node);
+       ret = nvkm_mm_head(&chan->heap, 0, 1, info->size, info->size, 1,
+                          &ntfy->node);
        if (ret)
                goto done;
 
@@ -527,7 +527,7 @@ nouveau_abi16_ioctl_gpuobj_free(ABI16_IOCTL_ARGS)
        /* cleanup extra state if this object was a notifier */
        list_for_each_entry(ntfy, &chan->notifiers, head) {
                if (ntfy->handle == fini->handle) {
-                       nouveau_mm_free(&chan->heap, &ntfy->node);
+                       nvkm_mm_free(&chan->heap, &ntfy->node);
                        list_del(&ntfy->head);
                        break;
                }
index 39844e6bfbffd4b33380a0d36cbe16fa8776106f..86eb1caf4957f66da0d1276569168bc10343a60e 100644 (file)
@@ -14,7 +14,7 @@ int nouveau_abi16_ioctl_gpuobj_free(ABI16_IOCTL_ARGS);
 
 struct nouveau_abi16_ntfy {
        struct list_head head;
-       struct nouveau_mm_node *node;
+       struct nvkm_mm_node *node;
        u32 handle;
 };
 
@@ -23,8 +23,8 @@ struct nouveau_abi16_chan {
        struct nouveau_channel *chan;
        struct list_head notifiers;
        struct nouveau_bo *ntfy;
-       struct nouveau_vma ntfy_vma;
-       struct nouveau_mm  heap;
+       struct nvkm_vma ntfy_vma;
+       struct nvkm_mm  heap;
 };
 
 struct nouveau_abi16 {
index 1f6f6ba6847a41e3138ca5a6d31272bc84ae7718..0b59709556047f9cb39245ca0b17661f716f8425 100644 (file)
@@ -45,8 +45,8 @@ get_agp_mode(struct nouveau_drm *drm, const struct drm_agp_info *info)
        while (agpmode == -1 && quirk->hostbridge_vendor) {
                if (info->id_vendor == quirk->hostbridge_vendor &&
                    info->id_device == quirk->hostbridge_device &&
-                   nvkm_device(device)->pdev->vendor == quirk->chip_vendor &&
-                   nvkm_device(device)->pdev->device == quirk->chip_device) {
+                   nvxx_device(device)->pdev->vendor == quirk->chip_vendor &&
+                   nvxx_device(device)->pdev->device == quirk->chip_device) {
                        agpmode = quirk->mode;
                        NV_INFO(drm, "Forcing agp mode to %dX. Use agpmode to override.\n",
                                agpmode);
index 7df6acc8bb3413ad847db56c5b234764dbd7124e..0190b69bbe25fe099a33d515e7b7855b7f98aa03 100644 (file)
@@ -2009,7 +2009,7 @@ uint8_t *nouveau_bios_embedded_edid(struct drm_device *dev)
 static bool NVInitVBIOS(struct drm_device *dev)
 {
        struct nouveau_drm *drm = nouveau_drm(dev);
-       struct nouveau_bios *bios = nvkm_bios(&drm->device);
+       struct nvkm_bios *bios = nvxx_bios(&drm->device);
        struct nvbios *legacy = &drm->vbios;
 
        memset(legacy, 0, sizeof(struct nvbios));
index bba2960d3dfbb5de9b6e69d977f72529624ab65c..77326e344dadaf07720afb30c827d964454e7520 100644 (file)
@@ -48,9 +48,9 @@ nv10_bo_update_tile_region(struct drm_device *dev, struct nouveau_drm_tile *reg,
 {
        struct nouveau_drm *drm = nouveau_drm(dev);
        int i = reg - drm->tile.reg;
-       struct nouveau_fb *pfb = nvkm_fb(&drm->device);
-       struct nouveau_fb_tile *tile = &pfb->tile.region[i];
-       struct nouveau_engine *engine;
+       struct nvkm_fb *pfb = nvxx_fb(&drm->device);
+       struct nvkm_fb_tile *tile = &pfb->tile.region[i];
+       struct nvkm_engine *engine;
 
        nouveau_fence_unref(&reg->fence);
 
@@ -62,9 +62,9 @@ nv10_bo_update_tile_region(struct drm_device *dev, struct nouveau_drm_tile *reg,
 
        pfb->tile.prog(pfb, i, tile);
 
-       if ((engine = nouveau_engine(pfb, NVDEV_ENGINE_GR)))
+       if ((engine = nvkm_engine(pfb, NVDEV_ENGINE_GR)))
                engine->tile_prog(engine, i);
-       if ((engine = nouveau_engine(pfb, NVDEV_ENGINE_MPEG)))
+       if ((engine = nvkm_engine(pfb, NVDEV_ENGINE_MPEG)))
                engine->tile_prog(engine, i);
 }
 
@@ -105,7 +105,7 @@ nv10_bo_set_tiling(struct drm_device *dev, u32 addr,
                   u32 size, u32 pitch, u32 flags)
 {
        struct nouveau_drm *drm = nouveau_drm(dev);
-       struct nouveau_fb *pfb = nvkm_fb(&drm->device);
+       struct nvkm_fb *pfb = nvxx_fb(&drm->device);
        struct nouveau_drm_tile *tile, *found = NULL;
        int i;
 
@@ -193,7 +193,7 @@ nouveau_bo_new(struct drm_device *dev, int size, int align,
        int max_size;
 
        if (drm->client.vm)
-               lpg_shift = drm->client.vm->vmm->lpg_shift;
+               lpg_shift = drm->client.vm->mmu->lpg_shift;
        max_size = INT_MAX & ~((1 << lpg_shift) - 1);
 
        if (size <= 0 || size > max_size) {
@@ -214,13 +214,13 @@ nouveau_bo_new(struct drm_device *dev, int size, int align,
        nvbo->tile_flags = tile_flags;
        nvbo->bo.bdev = &drm->ttm.bdev;
 
-       if (!nv_device_is_cpu_coherent(nvkm_device(&drm->device)))
+       if (!nv_device_is_cpu_coherent(nvxx_device(&drm->device)))
                nvbo->force_coherent = flags & TTM_PL_FLAG_UNCACHED;
 
        nvbo->page_shift = 12;
        if (drm->client.vm) {
                if (!(flags & TTM_PL_FLAG_TT) && size > 256 * 1024)
-                       nvbo->page_shift = drm->client.vm->vmm->lpg_shift;
+                       nvbo->page_shift = drm->client.vm->mmu->lpg_shift;
        }
 
        nouveau_bo_fixup_align(nvbo, flags, &align, &size);
@@ -325,7 +325,7 @@ nouveau_bo_pin(struct nouveau_bo *nvbo, uint32_t memtype, bool contig)
            memtype == TTM_PL_FLAG_VRAM && contig) {
                if (nvbo->tile_flags & NOUVEAU_GEM_TILE_NONCONTIG) {
                        if (bo->mem.mem_type == TTM_PL_VRAM) {
-                               struct nouveau_mem *mem = bo->mem.mm_node;
+                               struct nvkm_mem *mem = bo->mem.mm_node;
                                if (!list_is_singular(&mem->regions))
                                        evict = true;
                        }
@@ -459,7 +459,7 @@ void
 nouveau_bo_sync_for_device(struct nouveau_bo *nvbo)
 {
        struct nouveau_drm *drm = nouveau_bdev(nvbo->bo.bdev);
-       struct nouveau_device *device = nvkm_device(&drm->device);
+       struct nvkm_device *device = nvxx_device(&drm->device);
        struct ttm_dma_tt *ttm_dma = (struct ttm_dma_tt *)nvbo->bo.ttm;
        int i;
 
@@ -479,7 +479,7 @@ void
 nouveau_bo_sync_for_cpu(struct nouveau_bo *nvbo)
 {
        struct nouveau_drm *drm = nouveau_bdev(nvbo->bo.bdev);
-       struct nouveau_device *device = nvkm_device(&drm->device);
+       struct nvkm_device *device = nvxx_device(&drm->device);
        struct ttm_dma_tt *ttm_dma = (struct ttm_dma_tt *)nvbo->bo.ttm;
        int i;
 
@@ -533,20 +533,6 @@ _nouveau_bo_mem_index(struct nouveau_bo *nvbo, unsigned index, void *mem, u8 sz)
 }
 #define nouveau_bo_mem_index(o, i, m) _nouveau_bo_mem_index(o, i, m, sizeof(*m))
 
-u16
-nouveau_bo_rd16(struct nouveau_bo *nvbo, unsigned index)
-{
-       bool is_iomem;
-       u16 *mem = ttm_kmap_obj_virtual(&nvbo->kmap, &is_iomem);
-
-       mem = nouveau_bo_mem_index(nvbo, index, mem);
-
-       if (is_iomem)
-               return ioread16_native((void __force __iomem *)mem);
-       else
-               return *mem;
-}
-
 void
 nouveau_bo_wr16(struct nouveau_bo *nvbo, unsigned index, u16 val)
 {
@@ -634,7 +620,7 @@ nouveau_bo_init_mem_type(struct ttm_bo_device *bdev, uint32_t type,
 
                if (drm->device.info.family >= NV_DEVICE_INFO_V0_TESLA) {
                        /* Some BARs do not support being ioremapped WC */
-                       if (nvkm_bar(&drm->device)->iomap_uncached) {
+                       if (nvxx_bar(&drm->device)->iomap_uncached) {
                                man->available_caching = TTM_PL_FLAG_UNCACHED;
                                man->default_caching = TTM_PL_FLAG_UNCACHED;
                        }
@@ -709,7 +695,7 @@ static int
 nve0_bo_move_copy(struct nouveau_channel *chan, struct ttm_buffer_object *bo,
                  struct ttm_mem_reg *old_mem, struct ttm_mem_reg *new_mem)
 {
-       struct nouveau_mem *node = old_mem->mm_node;
+       struct nvkm_mem *node = old_mem->mm_node;
        int ret = RING_SPACE(chan, 10);
        if (ret == 0) {
                BEGIN_NVC0(chan, NvSubCopy, 0x0400, 8);
@@ -741,7 +727,7 @@ static int
 nvc0_bo_move_copy(struct nouveau_channel *chan, struct ttm_buffer_object *bo,
                  struct ttm_mem_reg *old_mem, struct ttm_mem_reg *new_mem)
 {
-       struct nouveau_mem *node = old_mem->mm_node;
+       struct nvkm_mem *node = old_mem->mm_node;
        u64 src_offset = node->vma[0].offset;
        u64 dst_offset = node->vma[1].offset;
        u32 page_count = new_mem->num_pages;
@@ -779,7 +765,7 @@ static int
 nvc0_bo_move_m2mf(struct nouveau_channel *chan, struct ttm_buffer_object *bo,
                  struct ttm_mem_reg *old_mem, struct ttm_mem_reg *new_mem)
 {
-       struct nouveau_mem *node = old_mem->mm_node;
+       struct nvkm_mem *node = old_mem->mm_node;
        u64 src_offset = node->vma[0].offset;
        u64 dst_offset = node->vma[1].offset;
        u32 page_count = new_mem->num_pages;
@@ -818,7 +804,7 @@ static int
 nva3_bo_move_copy(struct nouveau_channel *chan, struct ttm_buffer_object *bo,
                  struct ttm_mem_reg *old_mem, struct ttm_mem_reg *new_mem)
 {
-       struct nouveau_mem *node = old_mem->mm_node;
+       struct nvkm_mem *node = old_mem->mm_node;
        u64 src_offset = node->vma[0].offset;
        u64 dst_offset = node->vma[1].offset;
        u32 page_count = new_mem->num_pages;
@@ -856,7 +842,7 @@ static int
 nv98_bo_move_exec(struct nouveau_channel *chan, struct ttm_buffer_object *bo,
                  struct ttm_mem_reg *old_mem, struct ttm_mem_reg *new_mem)
 {
-       struct nouveau_mem *node = old_mem->mm_node;
+       struct nvkm_mem *node = old_mem->mm_node;
        int ret = RING_SPACE(chan, 7);
        if (ret == 0) {
                BEGIN_NV04(chan, NvSubCopy, 0x0320, 6);
@@ -874,7 +860,7 @@ static int
 nv84_bo_move_exec(struct nouveau_channel *chan, struct ttm_buffer_object *bo,
                  struct ttm_mem_reg *old_mem, struct ttm_mem_reg *new_mem)
 {
-       struct nouveau_mem *node = old_mem->mm_node;
+       struct nvkm_mem *node = old_mem->mm_node;
        int ret = RING_SPACE(chan, 7);
        if (ret == 0) {
                BEGIN_NV04(chan, NvSubCopy, 0x0304, 6);
@@ -908,12 +894,12 @@ static int
 nv50_bo_move_m2mf(struct nouveau_channel *chan, struct ttm_buffer_object *bo,
                  struct ttm_mem_reg *old_mem, struct ttm_mem_reg *new_mem)
 {
-       struct nouveau_mem *node = old_mem->mm_node;
+       struct nvkm_mem *node = old_mem->mm_node;
        u64 length = (new_mem->num_pages << PAGE_SHIFT);
        u64 src_offset = node->vma[0].offset;
        u64 dst_offset = node->vma[1].offset;
        int src_tiled = !!node->memtype;
-       int dst_tiled = !!((struct nouveau_mem *)new_mem->mm_node)->memtype;
+       int dst_tiled = !!((struct nvkm_mem *)new_mem->mm_node)->memtype;
        int ret;
 
        while (length) {
@@ -1050,25 +1036,25 @@ static int
 nouveau_bo_move_prep(struct nouveau_drm *drm, struct ttm_buffer_object *bo,
                     struct ttm_mem_reg *mem)
 {
-       struct nouveau_mem *old_node = bo->mem.mm_node;
-       struct nouveau_mem *new_node = mem->mm_node;
+       struct nvkm_mem *old_node = bo->mem.mm_node;
+       struct nvkm_mem *new_node = mem->mm_node;
        u64 size = (u64)mem->num_pages << PAGE_SHIFT;
        int ret;
 
-       ret = nouveau_vm_get(drm->client.vm, size, old_node->page_shift,
-                            NV_MEM_ACCESS_RW, &old_node->vma[0]);
+       ret = nvkm_vm_get(drm->client.vm, size, old_node->page_shift,
+                         NV_MEM_ACCESS_RW, &old_node->vma[0]);
        if (ret)
                return ret;
 
-       ret = nouveau_vm_get(drm->client.vm, size, new_node->page_shift,
-                            NV_MEM_ACCESS_RW, &old_node->vma[1]);
+       ret = nvkm_vm_get(drm->client.vm, size, new_node->page_shift,
+                         NV_MEM_ACCESS_RW, &old_node->vma[1]);
        if (ret) {
-               nouveau_vm_put(&old_node->vma[0]);
+               nvkm_vm_put(&old_node->vma[0]);
                return ret;
        }
 
-       nouveau_vm_map(&old_node->vma[0], old_node);
-       nouveau_vm_map(&old_node->vma[1], new_node);
+       nvkm_vm_map(&old_node->vma[0], old_node);
+       nvkm_vm_map(&old_node->vma[1], new_node);
        return 0;
 }
 
@@ -1083,7 +1069,7 @@ nouveau_bo_move_m2mf(struct ttm_buffer_object *bo, int evict, bool intr,
        int ret;
 
        /* create temporary vmas for the transfer and attach them to the
-        * old nouveau_mem node, these will get cleaned up after ttm has
+        * old nvkm_mem node, these will get cleaned up after ttm has
         * destroyed the ttm_mem_reg
         */
        if (drm->device.info.family >= NV_DEVICE_INFO_V0_TESLA) {
@@ -1245,7 +1231,7 @@ static void
 nouveau_bo_move_ntfy(struct ttm_buffer_object *bo, struct ttm_mem_reg *new_mem)
 {
        struct nouveau_bo *nvbo = nouveau_bo(bo);
-       struct nouveau_vma *vma;
+       struct nvkm_vma *vma;
 
        /* ttm can now (stupidly) pass the driver bos it didn't create... */
        if (bo->destroy != nouveau_bo_del_ttm)
@@ -1254,10 +1240,10 @@ nouveau_bo_move_ntfy(struct ttm_buffer_object *bo, struct ttm_mem_reg *new_mem)
        list_for_each_entry(vma, &nvbo->vma_list, head) {
                if (new_mem && new_mem->mem_type != TTM_PL_SYSTEM &&
                              (new_mem->mem_type == TTM_PL_VRAM ||
-                              nvbo->page_shift != vma->vm->vmm->lpg_shift)) {
-                       nouveau_vm_map(vma, new_mem->mm_node);
+                              nvbo->page_shift != vma->vm->mmu->lpg_shift)) {
+                       nvkm_vm_map(vma, new_mem->mm_node);
                } else {
-                       nouveau_vm_unmap(vma);
+                       nvkm_vm_unmap(vma);
                }
        }
 }
@@ -1368,7 +1354,7 @@ nouveau_ttm_io_mem_reserve(struct ttm_bo_device *bdev, struct ttm_mem_reg *mem)
 {
        struct ttm_mem_type_manager *man = &bdev->man[mem->mem_type];
        struct nouveau_drm *drm = nouveau_bdev(bdev);
-       struct nouveau_mem *node = mem->mm_node;
+       struct nvkm_mem *node = mem->mm_node;
        int ret;
 
        mem->bus.addr = NULL;
@@ -1396,10 +1382,10 @@ nouveau_ttm_io_mem_reserve(struct ttm_bo_device *bdev, struct ttm_mem_reg *mem)
                /* fallthrough, tiled memory */
        case TTM_PL_VRAM:
                mem->bus.offset = mem->start << PAGE_SHIFT;
-               mem->bus.base = nv_device_resource_start(nvkm_device(&drm->device), 1);
+               mem->bus.base = nv_device_resource_start(nvxx_device(&drm->device), 1);
                mem->bus.is_iomem = true;
                if (drm->device.info.family >= NV_DEVICE_INFO_V0_TESLA) {
-                       struct nouveau_bar *bar = nvkm_bar(&drm->device);
+                       struct nvkm_bar *bar = nvxx_bar(&drm->device);
 
                        ret = bar->umap(bar, node, NV_MEM_ACCESS_RW,
                                        &node->bar_vma);
@@ -1419,8 +1405,8 @@ static void
 nouveau_ttm_io_mem_free(struct ttm_bo_device *bdev, struct ttm_mem_reg *mem)
 {
        struct nouveau_drm *drm = nouveau_bdev(bdev);
-       struct nouveau_bar *bar = nvkm_bar(&drm->device);
-       struct nouveau_mem *node = mem->mm_node;
+       struct nvkm_bar *bar = nvxx_bar(&drm->device);
+       struct nvkm_mem *node = mem->mm_node;
 
        if (!node->bar_vma.node)
                return;
@@ -1434,7 +1420,7 @@ nouveau_ttm_fault_reserve_notify(struct ttm_buffer_object *bo)
        struct nouveau_drm *drm = nouveau_bdev(bo->bdev);
        struct nouveau_bo *nvbo = nouveau_bo(bo);
        struct nvif_device *device = &drm->device;
-       u32 mappable = nv_device_resource_len(nvkm_device(device), 1) >> PAGE_SHIFT;
+       u32 mappable = nv_device_resource_len(nvxx_device(device), 1) >> PAGE_SHIFT;
        int i, ret;
 
        /* as long as the bo isn't in vram, and isn't tiled, we've got
@@ -1479,7 +1465,7 @@ nouveau_ttm_tt_populate(struct ttm_tt *ttm)
 {
        struct ttm_dma_tt *ttm_dma = (void *)ttm;
        struct nouveau_drm *drm;
-       struct nouveau_device *device;
+       struct nvkm_device *device;
        struct drm_device *dev;
        struct device *pdev;
        unsigned i;
@@ -1498,7 +1484,7 @@ nouveau_ttm_tt_populate(struct ttm_tt *ttm)
        }
 
        drm = nouveau_bdev(ttm->bdev);
-       device = nvkm_device(&drm->device);
+       device = nvxx_device(&drm->device);
        dev = drm->dev;
        pdev = nv_device_base(device);
 
@@ -1553,7 +1539,7 @@ nouveau_ttm_tt_unpopulate(struct ttm_tt *ttm)
 {
        struct ttm_dma_tt *ttm_dma = (void *)ttm;
        struct nouveau_drm *drm;
-       struct nouveau_device *device;
+       struct nvkm_device *device;
        struct drm_device *dev;
        struct device *pdev;
        unsigned i;
@@ -1563,7 +1549,7 @@ nouveau_ttm_tt_unpopulate(struct ttm_tt *ttm)
                return;
 
        drm = nouveau_bdev(ttm->bdev);
-       device = nvkm_device(&drm->device);
+       device = nvxx_device(&drm->device);
        dev = drm->dev;
        pdev = nv_device_base(device);
 
@@ -1627,10 +1613,10 @@ struct ttm_bo_driver nouveau_bo_driver = {
        .io_mem_free = &nouveau_ttm_io_mem_free,
 };
 
-struct nouveau_vma *
-nouveau_bo_vma_find(struct nouveau_bo *nvbo, struct nouveau_vm *vm)
+struct nvkm_vma *
+nouveau_bo_vma_find(struct nouveau_bo *nvbo, struct nvkm_vm *vm)
 {
-       struct nouveau_vma *vma;
+       struct nvkm_vma *vma;
        list_for_each_entry(vma, &nvbo->vma_list, head) {
                if (vma->vm == vm)
                        return vma;
@@ -1640,21 +1626,21 @@ nouveau_bo_vma_find(struct nouveau_bo *nvbo, struct nouveau_vm *vm)
 }
 
 int
-nouveau_bo_vma_add(struct nouveau_bo *nvbo, struct nouveau_vm *vm,
-                  struct nouveau_vma *vma)
+nouveau_bo_vma_add(struct nouveau_bo *nvbo, struct nvkm_vm *vm,
+                  struct nvkm_vma *vma)
 {
        const u32 size = nvbo->bo.mem.num_pages << PAGE_SHIFT;
        int ret;
 
-       ret = nouveau_vm_get(vm, size, nvbo->page_shift,
+       ret = nvkm_vm_get(vm, size, nvbo->page_shift,
                             NV_MEM_ACCESS_RW, vma);
        if (ret)
                return ret;
 
        if ( nvbo->bo.mem.mem_type != TTM_PL_SYSTEM &&
            (nvbo->bo.mem.mem_type == TTM_PL_VRAM ||
-            nvbo->page_shift != vma->vm->vmm->lpg_shift))
-               nouveau_vm_map(vma, nvbo->bo.mem.mm_node);
+            nvbo->page_shift != vma->vm->mmu->lpg_shift))
+               nvkm_vm_map(vma, nvbo->bo.mem.mm_node);
 
        list_add_tail(&vma->head, &nvbo->vma_list);
        vma->refcount = 1;
@@ -1662,12 +1648,12 @@ nouveau_bo_vma_add(struct nouveau_bo *nvbo, struct nouveau_vm *vm,
 }
 
 void
-nouveau_bo_vma_del(struct nouveau_bo *nvbo, struct nouveau_vma *vma)
+nouveau_bo_vma_del(struct nouveau_bo *nvbo, struct nvkm_vma *vma)
 {
        if (vma->node) {
                if (nvbo->bo.mem.mem_type != TTM_PL_SYSTEM)
-                       nouveau_vm_unmap(vma);
-               nouveau_vm_put(vma);
+                       nvkm_vm_unmap(vma);
+               nvkm_vm_put(vma);
                list_del(&vma->head);
        }
 }
index 072222efeeb765467605f844d22e340180cda048..e42360983229960162d057f1e03422616f75a55f 100644 (file)
@@ -5,7 +5,7 @@
 
 struct nouveau_channel;
 struct nouveau_fence;
-struct nouveau_vma;
+struct nvkm_vma;
 
 struct nouveau_bo {
        struct ttm_buffer_object bo;
@@ -78,7 +78,6 @@ int  nouveau_bo_unpin(struct nouveau_bo *);
 int  nouveau_bo_map(struct nouveau_bo *);
 void nouveau_bo_unmap(struct nouveau_bo *);
 void nouveau_bo_placement_set(struct nouveau_bo *, u32 type, u32 busy);
-u16  nouveau_bo_rd16(struct nouveau_bo *, unsigned index);
 void nouveau_bo_wr16(struct nouveau_bo *, unsigned index, u16 val);
 u32  nouveau_bo_rd32(struct nouveau_bo *, unsigned index);
 void nouveau_bo_wr32(struct nouveau_bo *, unsigned index, u32 val);
@@ -88,12 +87,12 @@ int  nouveau_bo_validate(struct nouveau_bo *, bool interruptible,
 void nouveau_bo_sync_for_device(struct nouveau_bo *nvbo);
 void nouveau_bo_sync_for_cpu(struct nouveau_bo *nvbo);
 
-struct nouveau_vma *
-nouveau_bo_vma_find(struct nouveau_bo *, struct nouveau_vm *);
+struct nvkm_vma *
+nouveau_bo_vma_find(struct nouveau_bo *, struct nvkm_vm *);
 
-int  nouveau_bo_vma_add(struct nouveau_bo *, struct nouveau_vm *,
-                       struct nouveau_vma *);
-void nouveau_bo_vma_del(struct nouveau_bo *, struct nouveau_vma *);
+int  nouveau_bo_vma_add(struct nouveau_bo *, struct nvkm_vm *,
+                       struct nvkm_vma *);
+void nouveau_bo_vma_del(struct nouveau_bo *, struct nvkm_vma *);
 
 /* TODO: submit equivalent to TTM generic API upstream? */
 static inline void __iomem *
index aff9099aae6cca23b6e51247ee07068f23b691c1..e581f63cbf25eefabc64c32c6c2f7826d89aede1 100644 (file)
@@ -54,7 +54,7 @@ nouveau_channel_idle(struct nouveau_channel *chan)
 
        if (ret)
                NV_PRINTK(error, cli, "failed to idle channel 0x%08x [%s]\n",
-                         chan->object->handle, nvkm_client(&cli->base)->name);
+                         chan->object->handle, nvxx_client(&cli->base)->name);
        return ret;
 }
 
@@ -88,7 +88,7 @@ nouveau_channel_prep(struct nouveau_drm *drm, struct nvif_device *device,
                     u32 handle, u32 size, struct nouveau_channel **pchan)
 {
        struct nouveau_cli *cli = (void *)nvif_client(&device->base);
-       struct nouveau_vmmgr *vmm = nvkm_vmmgr(device);
+       struct nvkm_mmu *mmu = nvxx_mmu(device);
        struct nv_dma_v0 args = {};
        struct nouveau_channel *chan;
        u32 target;
@@ -136,7 +136,7 @@ nouveau_channel_prep(struct nouveau_drm *drm, struct nvif_device *device,
                args.target = NV_DMA_V0_TARGET_VM;
                args.access = NV_DMA_V0_ACCESS_VM;
                args.start = 0;
-               args.limit = cli->vm->vmm->limit - 1;
+               args.limit = cli->vm->mmu->limit - 1;
        } else
        if (chan->push.buffer->bo.mem.mem_type == TTM_PL_VRAM) {
                if (device->info.family == NV_DEVICE_INFO_V0_TNT) {
@@ -146,7 +146,7 @@ nouveau_channel_prep(struct nouveau_drm *drm, struct nvif_device *device,
                         */
                        args.target = NV_DMA_V0_TARGET_PCI;
                        args.access = NV_DMA_V0_ACCESS_RDWR;
-                       args.start = nv_device_resource_start(nvkm_device(device), 1);
+                       args.start = nv_device_resource_start(nvxx_device(device), 1);
                        args.limit = args.start + device->info.ram_user - 1;
                } else {
                        args.target = NV_DMA_V0_TARGET_VRAM;
@@ -165,7 +165,7 @@ nouveau_channel_prep(struct nouveau_drm *drm, struct nvif_device *device,
                        args.target = NV_DMA_V0_TARGET_VM;
                        args.access = NV_DMA_V0_ACCESS_RDWR;
                        args.start = 0;
-                       args.limit = vmm->limit - 1;
+                       args.limit = mmu->limit - 1;
                }
        }
 
@@ -281,8 +281,8 @@ nouveau_channel_init(struct nouveau_channel *chan, u32 vram, u32 gart)
 {
        struct nvif_device *device = chan->device;
        struct nouveau_cli *cli = (void *)nvif_client(&device->base);
-       struct nouveau_vmmgr *vmm = nvkm_vmmgr(device);
-       struct nouveau_software_chan *swch;
+       struct nvkm_mmu *mmu = nvxx_mmu(device);
+       struct nvkm_sw_chan *swch;
        struct nv_dma_v0 args = {};
        int ret, i;
 
@@ -294,7 +294,7 @@ nouveau_channel_init(struct nouveau_channel *chan, u32 vram, u32 gart)
                        args.target = NV_DMA_V0_TARGET_VM;
                        args.access = NV_DMA_V0_ACCESS_VM;
                        args.start = 0;
-                       args.limit = cli->vm->vmm->limit - 1;
+                       args.limit = cli->vm->mmu->limit - 1;
                } else {
                        args.target = NV_DMA_V0_TARGET_VRAM;
                        args.access = NV_DMA_V0_ACCESS_RDWR;
@@ -312,7 +312,7 @@ nouveau_channel_init(struct nouveau_channel *chan, u32 vram, u32 gart)
                        args.target = NV_DMA_V0_TARGET_VM;
                        args.access = NV_DMA_V0_ACCESS_VM;
                        args.start = 0;
-                       args.limit = cli->vm->vmm->limit - 1;
+                       args.limit = cli->vm->mmu->limit - 1;
                } else
                if (chan->drm->agp.stat == ENABLED) {
                        args.target = NV_DMA_V0_TARGET_AGP;
@@ -324,7 +324,7 @@ nouveau_channel_init(struct nouveau_channel *chan, u32 vram, u32 gart)
                        args.target = NV_DMA_V0_TARGET_VM;
                        args.access = NV_DMA_V0_ACCESS_RDWR;
                        args.start = 0;
-                       args.limit = vmm->limit - 1;
+                       args.limit = mmu->limit - 1;
                }
 
                ret = nvif_object_init(chan->object, NULL, gart,
@@ -372,7 +372,7 @@ nouveau_channel_init(struct nouveau_channel *chan, u32 vram, u32 gart)
                if (ret)
                        return ret;
 
-               swch = (void *)nvkm_object(&chan->nvsw)->parent;
+               swch = (void *)nvxx_object(&chan->nvsw)->parent;
                swch->flip = nouveau_flip_complete;
                swch->flip_data = chan;
 
index 8309c24ee6981f63e3dc5257235ce122e5840de5..8b3640f69e4fc5450411ac1a39bd8b2f9104cb59 100644 (file)
@@ -16,7 +16,7 @@ struct nouveau_channel {
 
        struct {
                struct nouveau_bo *buffer;
-               struct nouveau_vma vma;
+               struct nvkm_vma vma;
                struct nvif_object ctxdma;
        } push;
 
index c8ac9482cf2ed12de114636b004bdd66813bc4ba..db7095ae4ebbdd7266b18c425a3864d2f035b4f6 100644 (file)
@@ -115,7 +115,7 @@ nouveau_connector_ddc_detect(struct drm_connector *connector)
        struct drm_device *dev = connector->dev;
        struct nouveau_connector *nv_connector = nouveau_connector(connector);
        struct nouveau_drm *drm = nouveau_drm(dev);
-       struct nouveau_gpio *gpio = nvkm_gpio(&drm->device);
+       struct nvkm_gpio *gpio = nvxx_gpio(&drm->device);
        struct nouveau_encoder *nv_encoder;
        struct drm_encoder *encoder;
        int i, panel = -ENODEV;
@@ -241,7 +241,7 @@ nouveau_connector_detect(struct drm_connector *connector, bool force)
        struct nouveau_connector *nv_connector = nouveau_connector(connector);
        struct nouveau_encoder *nv_encoder = NULL;
        struct nouveau_encoder *nv_partner;
-       struct nouveau_i2c_port *i2c;
+       struct nvkm_i2c_port *i2c;
        int type;
        int ret;
        enum drm_connector_status conn_status = connector_status_disconnected;
@@ -458,6 +458,28 @@ nouveau_connector_set_property(struct drm_connector *connector,
 
                switch (value) {
                case DRM_MODE_SCALE_NONE:
+                       /* We allow 'None' for EDID modes, even on a fixed
+                        * panel (some exist with support for lower refresh
+                        * rates, which people might want to use for power
+                        * saving purposes).
+                        *
+                        * Non-EDID modes will force the use of GPU scaling
+                        * to the native mode regardless of this setting.
+                        */
+                       switch (nv_connector->type) {
+                       case DCB_CONNECTOR_LVDS:
+                       case DCB_CONNECTOR_LVDS_SPWG:
+                       case DCB_CONNECTOR_eDP:
+                               /* ... except prior to G80, where the code
+                                * doesn't support such things.
+                                */
+                               if (disp->disp.oclass < NV50_DISP)
+                                       return -EINVAL;
+                               break;
+                       default:
+                               break;
+                       }
+                       break;
                case DRM_MODE_SCALE_FULLSCREEN:
                case DRM_MODE_SCALE_CENTER:
                case DRM_MODE_SCALE_ASPECT:
@@ -466,11 +488,6 @@ nouveau_connector_set_property(struct drm_connector *connector,
                        return -EINVAL;
                }
 
-               /* LVDS always needs gpu scaling */
-               if (connector->connector_type == DRM_MODE_CONNECTOR_LVDS &&
-                   value == DRM_MODE_SCALE_NONE)
-                       return -EINVAL;
-
                /* Changing between GPU and panel scaling requires a full
                 * modeset
                 */
@@ -655,15 +672,15 @@ nouveau_connector_scaler_modes_add(struct drm_connector *connector)
 
        while (mode->hdisplay) {
                if (mode->hdisplay <= native->hdisplay &&
-                   mode->vdisplay <= native->vdisplay) {
+                   mode->vdisplay <= native->vdisplay &&
+                   (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++;
                }
@@ -968,7 +985,7 @@ nouveau_connector_aux_xfer(struct drm_dp_aux *aux, struct drm_dp_aux_msg *msg)
        struct nouveau_connector *nv_connector =
                container_of(aux, typeof(*nv_connector), aux);
        struct nouveau_encoder *nv_encoder;
-       struct nouveau_i2c_port *port;
+       struct nvkm_i2c_port *port;
        int ret;
 
        nv_encoder = find_encoder(&nv_connector->base, DCB_OUTPUT_DP);
@@ -979,13 +996,13 @@ nouveau_connector_aux_xfer(struct drm_dp_aux *aux, struct drm_dp_aux_msg *msg)
        if (msg->size == 0)
                return msg->size;
 
-       ret = nouveau_i2c(port)->acquire(port, 0);
+       ret = nvkm_i2c(port)->acquire(port, 0);
        if (ret)
                return ret;
 
        ret = port->func->aux(port, false, msg->request, msg->address,
                              msg->buffer, msg->size);
-       nouveau_i2c(port)->release(port);
+       nvkm_i2c(port)->release(port);
        if (ret >= 0) {
                msg->reply = ret;
                return msg->size;
@@ -1180,36 +1197,61 @@ nouveau_connector_create(struct drm_device *dev, int index)
                                              disp->color_vibrance_property,
                                              150);
 
+       /* default scaling mode */
        switch (nv_connector->type) {
-       case DCB_CONNECTOR_VGA:
-               if (drm->device.info.family >= NV_DEVICE_INFO_V0_TESLA) {
-                       drm_object_attach_property(&connector->base,
-                                       dev->mode_config.scaling_mode_property,
-                                       nv_connector->scaling_mode);
+       case DCB_CONNECTOR_LVDS:
+       case DCB_CONNECTOR_LVDS_SPWG:
+       case DCB_CONNECTOR_eDP:
+               /* see note in nouveau_connector_set_property() */
+               if (disp->disp.oclass < NV50_DISP) {
+                       nv_connector->scaling_mode = DRM_MODE_SCALE_FULLSCREEN;
+                       break;
                }
-               /* fall-through */
+               nv_connector->scaling_mode = DRM_MODE_SCALE_NONE;
+               break;
+       default:
+               nv_connector->scaling_mode = DRM_MODE_SCALE_NONE;
+               break;
+       }
+
+       /* scaling mode property */
+       switch (nv_connector->type) {
        case DCB_CONNECTOR_TV_0:
        case DCB_CONNECTOR_TV_1:
        case DCB_CONNECTOR_TV_3:
-               nv_connector->scaling_mode = DRM_MODE_SCALE_NONE;
                break;
+       case DCB_CONNECTOR_VGA:
+               if (disp->disp.oclass < NV50_DISP)
+                       break; /* can only scale on DFPs */
+               /* fall-through */
        default:
-               nv_connector->scaling_mode = DRM_MODE_SCALE_FULLSCREEN;
+               drm_object_attach_property(&connector->base, dev->mode_config.
+                                          scaling_mode_property,
+                                          nv_connector->scaling_mode);
+               break;
+       }
 
-               drm_object_attach_property(&connector->base,
-                               dev->mode_config.scaling_mode_property,
-                               nv_connector->scaling_mode);
+       /* dithering properties */
+       switch (nv_connector->type) {
+       case DCB_CONNECTOR_TV_0:
+       case DCB_CONNECTOR_TV_1:
+       case DCB_CONNECTOR_TV_3:
+       case DCB_CONNECTOR_VGA:
+               break;
+       default:
                if (disp->dithering_mode) {
-                       nv_connector->dithering_mode = DITHERING_MODE_AUTO;
                        drm_object_attach_property(&connector->base,
-                                               disp->dithering_mode,
-                                               nv_connector->dithering_mode);
+                                                  disp->dithering_mode,
+                                                  nv_connector->
+                                                  dithering_mode);
+                       nv_connector->dithering_mode = DITHERING_MODE_AUTO;
                }
                if (disp->dithering_depth) {
-                       nv_connector->dithering_depth = DITHERING_DEPTH_AUTO;
                        drm_object_attach_property(&connector->base,
-                                               disp->dithering_depth,
-                                               nv_connector->dithering_depth);
+                                                  disp->dithering_depth,
+                                                  nv_connector->
+                                                  dithering_depth);
+                       nv_connector->dithering_depth = DITHERING_DEPTH_AUTO;
                }
                break;
        }
index 629a380c708555b26522987036b458a01fb2983f..7446ee66ea041c2dd9fc3b0444db5309dbcfcdc9 100644 (file)
@@ -33,7 +33,7 @@
 #include <drm/drm_dp_helper.h>
 #include "nouveau_crtc.h"
 
-struct nouveau_i2c_port;
+struct nvkm_i2c_port;
 
 enum nouveau_underscan_type {
        UNDERSCAN_OFF,
@@ -72,6 +72,7 @@ struct nouveau_connector {
        int dithering_mode;
        int dithering_depth;
        int scaling_mode;
+       bool scaling_full;
        enum nouveau_underscan_type underscan;
        u32 underscan_hborder;
        u32 underscan_vborder;
index f8042433752b440d72fd9306009f55e972c68385..860b0e2d4181da85e68abc604a5157d27fceb1b6 100644 (file)
@@ -450,7 +450,7 @@ nouveau_display_create(struct drm_device *dev)
        drm_mode_create_dvi_i_properties(dev);
 
        dev->mode_config.funcs = &nouveau_mode_config_funcs;
-       dev->mode_config.fb_base = nv_device_resource_start(nvkm_device(&drm->device), 1);
+       dev->mode_config.fb_base = nv_device_resource_start(nvxx_device(&drm->device), 1);
 
        dev->mode_config.min_width = 0;
        dev->mode_config.min_height = 0;
@@ -570,7 +570,8 @@ nouveau_display_suspend(struct drm_device *dev, bool runtime)
        list_for_each_entry(crtc, &dev->mode_config.crtc_list, head) {
                struct nouveau_crtc *nv_crtc = nouveau_crtc(crtc);
                if (nv_crtc->cursor.nvbo) {
-                       nouveau_bo_unmap(nv_crtc->cursor.nvbo);
+                       if (nv_crtc->cursor.set_offset)
+                               nouveau_bo_unmap(nv_crtc->cursor.nvbo);
                        nouveau_bo_unpin(nv_crtc->cursor.nvbo);
                }
        }
@@ -604,7 +605,7 @@ nouveau_display_resume(struct drm_device *dev, bool runtime)
                        continue;
 
                ret = nouveau_bo_pin(nv_crtc->cursor.nvbo, TTM_PL_FLAG_VRAM, true);
-               if (!ret)
+               if (!ret && nv_crtc->cursor.set_offset)
                        ret = nouveau_bo_map(nv_crtc->cursor.nvbo);
                if (ret)
                        NV_ERROR(drm, "Could not pin/map cursor.\n");
@@ -637,7 +638,9 @@ nouveau_display_resume(struct drm_device *dev, bool runtime)
 
                if (!nv_crtc->cursor.nvbo)
                        continue;
-               nv_crtc->cursor.set_offset(nv_crtc, nv_crtc->cursor.nvbo->bo.offset);
+
+               if (nv_crtc->cursor.set_offset)
+                       nv_crtc->cursor.set_offset(nv_crtc, nv_crtc->cursor.nvbo->bo.offset);
                nv_crtc->cursor.set_pos(nv_crtc, nv_crtc->cursor_saved_x,
                                                 nv_crtc->cursor_saved_y);
        }
index be3d5947c6be0a6a51fa1730d41501c49fb582c2..a6213e2425c597cca0168e12188476a1e8baad31 100644 (file)
@@ -1,14 +1,14 @@
 #ifndef __NOUVEAU_DISPLAY_H__
 #define __NOUVEAU_DISPLAY_H__
 
-#include <subdev/vm.h>
+#include <subdev/mmu.h>
 
 #include "nouveau_drm.h"
 
 struct nouveau_framebuffer {
        struct drm_framebuffer base;
        struct nouveau_bo *nvbo;
-       struct nouveau_vma vma;
+       struct nvkm_vma vma;
        u32 r_handle;
        u32 r_format;
        u32 r_pitch;
index 8508603cc8c3dfeffd334228d25d435836b9a4c9..6d9245aa81a6aab3497194bd52ef82f761074a40 100644 (file)
@@ -84,7 +84,7 @@ nv50_dma_push(struct nouveau_channel *chan, struct nouveau_bo *bo,
 {
        struct nouveau_cli *cli = (void *)nvif_client(&chan->device->base);
        struct nouveau_bo *pb = chan->push.buffer;
-       struct nouveau_vma *vma;
+       struct nvkm_vma *vma;
        int ip = (chan->dma.ib_put * 2) + chan->dma.ib_base;
        u64 offset;
 
index c5137cccce7dbcac6d05d7b2ebaecb1fd6a3a7c6..c3ef30b3a5ec593bf3b76212772697703b82bf54 100644 (file)
@@ -31,7 +31,7 @@
 #include "nouveau_crtc.h"
 
 static void
-nouveau_dp_probe_oui(struct drm_device *dev, struct nouveau_i2c_port *auxch,
+nouveau_dp_probe_oui(struct drm_device *dev, struct nvkm_i2c_port *auxch,
                     u8 *dpcd)
 {
        struct nouveau_drm *drm = nouveau_drm(dev);
@@ -55,7 +55,7 @@ nouveau_dp_detect(struct nouveau_encoder *nv_encoder)
 {
        struct drm_device *dev = nv_encoder->base.base.dev;
        struct nouveau_drm *drm = nouveau_drm(dev);
-       struct nouveau_i2c_port *auxch;
+       struct nvkm_i2c_port *auxch;
        u8 *dpcd = nv_encoder->dp.dpcd;
        int ret;
 
index 65910e3aed0c86e1240273f274f42ea947373d58..8763deb5188bb75ad041755e75add0b85726e106 100644 (file)
@@ -52,6 +52,7 @@
 #include "nouveau_debugfs.h"
 #include "nouveau_usif.h"
 #include "nouveau_connector.h"
+#include "nouveau_platform.h"
 
 MODULE_PARM_DESC(config, "option string to pass to driver core");
 static char *nouveau_config;
@@ -123,7 +124,7 @@ nouveau_cli_create(u64 name, const char *sname,
 static void
 nouveau_cli_destroy(struct nouveau_cli *cli)
 {
-       nouveau_vm_ref(NULL, &nvkm_client(&cli->base)->vm, NULL);
+       nvkm_vm_ref(NULL, &nvxx_client(&cli->base)->vm, NULL);
        nvif_client_fini(&cli->base);
        usif_client_fini(cli);
 }
@@ -133,7 +134,7 @@ nouveau_accel_fini(struct nouveau_drm *drm)
 {
        nouveau_channel_del(&drm->channel);
        nvif_object_fini(&drm->ntfy);
-       nouveau_gpuobj_ref(NULL, &drm->notify);
+       nvkm_gpuobj_ref(NULL, &drm->notify);
        nvif_object_fini(&drm->nvsw);
        nouveau_channel_del(&drm->cechan);
        nvif_object_fini(&drm->ttm.copy);
@@ -230,7 +231,7 @@ nouveau_accel_init(struct nouveau_drm *drm)
        ret = nvif_object_init(drm->channel->object, NULL, NVDRM_NVSW,
                               nouveau_abi16_swclass(drm), NULL, 0, &drm->nvsw);
        if (ret == 0) {
-               struct nouveau_software_chan *swch;
+               struct nvkm_sw_chan *swch;
                ret = RING_SPACE(drm->channel, 2);
                if (ret == 0) {
                        if (device->info.family < NV_DEVICE_INFO_V0_FERMI) {
@@ -242,7 +243,7 @@ nouveau_accel_init(struct nouveau_drm *drm)
                                OUT_RING  (drm->channel, 0x001f0000);
                        }
                }
-               swch = (void *)nvkm_object(&drm->nvsw)->parent;
+               swch = (void *)nvxx_object(&drm->nvsw)->parent;
                swch->flip = nouveau_flip_complete;
                swch->flip_data = drm->channel;
        }
@@ -254,8 +255,8 @@ nouveau_accel_init(struct nouveau_drm *drm)
        }
 
        if (device->info.family < NV_DEVICE_INFO_V0_FERMI) {
-               ret = nouveau_gpuobj_new(nvkm_object(&drm->device), NULL, 32,
-                                        0, 0, &drm->notify);
+               ret = nvkm_gpuobj_new(nvxx_object(&drm->device), NULL, 32,
+                                     0, 0, &drm->notify);
                if (ret) {
                        NV_ERROR(drm, "failed to allocate notifier, %d\n", ret);
                        nouveau_accel_fini(drm);
@@ -284,7 +285,7 @@ nouveau_accel_init(struct nouveau_drm *drm)
 static int nouveau_drm_probe(struct pci_dev *pdev,
                             const struct pci_device_id *pent)
 {
-       struct nouveau_device *device;
+       struct nvkm_device *device;
        struct apertures_struct *aper;
        bool boot = false;
        int ret;
@@ -317,9 +318,9 @@ static int nouveau_drm_probe(struct pci_dev *pdev,
                remove_conflicting_framebuffers(aper, "nouveaufb", boot);
        kfree(aper);
 
-       ret = nouveau_device_create(pdev, NOUVEAU_BUS_PCI,
-                                   nouveau_pci_name(pdev), pci_name(pdev),
-                                   nouveau_config, nouveau_debug, &device);
+       ret = nvkm_device_create(pdev, NVKM_BUS_PCI,
+                                nouveau_pci_name(pdev), pci_name(pdev),
+                                nouveau_config, nouveau_debug, &device);
        if (ret)
                return ret;
 
@@ -327,7 +328,7 @@ static int nouveau_drm_probe(struct pci_dev *pdev,
 
        ret = drm_get_pci_dev(pdev, pent, &driver_pci);
        if (ret) {
-               nouveau_object_ref(NULL, (struct nouveau_object **)&device);
+               nvkm_object_ref(NULL, (struct nvkm_object **)&device);
                return ret;
        }
 
@@ -378,8 +379,8 @@ nouveau_drm_load(struct drm_device *dev, unsigned long flags)
 
        dev->dev_private = drm;
        drm->dev = dev;
-       nvkm_client(&drm->client.base)->debug =
-               nouveau_dbgopt(nouveau_debug, "DRM");
+       nvxx_client(&drm->client.base)->debug =
+               nvkm_dbgopt(nouveau_debug, "DRM");
 
        INIT_LIST_HEAD(&drm->clients);
        spin_lock_init(&drm->tile.lock);
@@ -434,12 +435,12 @@ nouveau_drm_load(struct drm_device *dev, unsigned long flags)
        nouveau_agp_init(drm);
 
        if (drm->device.info.family >= NV_DEVICE_INFO_V0_TESLA) {
-               ret = nouveau_vm_new(nvkm_device(&drm->device), 0, (1ULL << 40),
-                                    0x1000, &drm->client.vm);
+               ret = nvkm_vm_new(nvxx_device(&drm->device), 0, (1ULL << 40),
+                                 0x1000, &drm->client.vm);
                if (ret)
                        goto fail_device;
 
-               nvkm_client(&drm->client.base)->vm = drm->client.vm;
+               nvxx_client(&drm->client.base)->vm = drm->client.vm;
        }
 
        ret = nouveau_ttm_init(drm);
@@ -522,18 +523,17 @@ void
 nouveau_drm_device_remove(struct drm_device *dev)
 {
        struct nouveau_drm *drm = nouveau_drm(dev);
-       struct nouveau_client *client;
-       struct nouveau_object *device;
+       struct nvkm_client *client;
+       struct nvkm_object *device;
 
        dev->irq_enabled = false;
-       client = nvkm_client(&drm->client.base);
+       client = nvxx_client(&drm->client.base);
        device = client->device;
        drm_put_dev(dev);
 
-       nouveau_object_ref(NULL, &device);
-       nouveau_object_debug();
+       nvkm_object_ref(NULL, &device);
+       nvkm_object_debug();
 }
-EXPORT_SYMBOL(nouveau_drm_device_remove);
 
 static void
 nouveau_drm_remove(struct pci_dev *pdev)
@@ -831,14 +831,14 @@ nouveau_drm_open(struct drm_device *dev, struct drm_file *fpriv)
        cli->base.super = false;
 
        if (drm->device.info.family >= NV_DEVICE_INFO_V0_TESLA) {
-               ret = nouveau_vm_new(nvkm_device(&drm->device), 0, (1ULL << 40),
-                                    0x1000, &cli->vm);
+               ret = nvkm_vm_new(nvxx_device(&drm->device), 0, (1ULL << 40),
+                                 0x1000, &cli->vm);
                if (ret) {
                        nouveau_cli_destroy(cli);
                        goto out_suspend;
                }
 
-               nvkm_client(&cli->base)->vm = cli->vm;
+               nvxx_client(&cli->base)->vm = cli->vm;
        }
 
        fpriv->driver_priv = cli;
@@ -1056,10 +1056,10 @@ nouveau_platform_device_create_(struct platform_device *pdev, int size,
        struct drm_device *drm;
        int err;
 
-       err = nouveau_device_create_(pdev, NOUVEAU_BUS_PLATFORM,
-                                   nouveau_platform_name(pdev),
-                                   dev_name(&pdev->dev), nouveau_config,
-                                   nouveau_debug, size, pobject);
+       err = nvkm_device_create_(pdev, NVKM_BUS_PLATFORM,
+                                 nouveau_platform_name(pdev),
+                                 dev_name(&pdev->dev), nouveau_config,
+                                 nouveau_debug, size, pobject);
        if (err)
                return ERR_PTR(err);
 
@@ -1079,11 +1079,10 @@ nouveau_platform_device_create_(struct platform_device *pdev, int size,
        return drm;
 
 err_free:
-       nouveau_object_ref(NULL, (struct nouveau_object **)pobject);
+       nvkm_object_ref(NULL, (struct nvkm_object **)pobject);
 
        return ERR_PTR(err);
 }
-EXPORT_SYMBOL(nouveau_platform_device_create_);
 
 static int __init
 nouveau_drm_init(void)
@@ -1105,6 +1104,10 @@ nouveau_drm_init(void)
        if (!nouveau_modeset)
                return 0;
 
+#ifdef CONFIG_NOUVEAU_PLATFORM_DRIVER
+       platform_driver_register(&nouveau_platform_driver);
+#endif
+
        nouveau_register_dsm_handler();
        return drm_pci_init(&driver_pci, &nouveau_drm_pci_driver);
 }
@@ -1117,6 +1120,10 @@ nouveau_drm_exit(void)
 
        drm_pci_exit(&driver_pci, &nouveau_drm_pci_driver);
        nouveau_unregister_dsm_handler();
+
+#ifdef CONFIG_NOUVEAU_PLATFORM_DRIVER
+       platform_driver_unregister(&nouveau_platform_driver);
+#endif
 }
 
 module_init(nouveau_drm_init);
index 8ae36f265fb8867b6092a48fcde8b06450148b40..fc68f0973f9e70f3d21fd057740379415e93c7f9 100644 (file)
@@ -80,7 +80,7 @@ enum nouveau_drm_handle {
 
 struct nouveau_cli {
        struct nvif_client base;
-       struct nouveau_vm *vm; /*XXX*/
+       struct nvkm_vm *vm; /*XXX*/
        struct list_head head;
        struct mutex mutex;
        void *abi16;
@@ -142,7 +142,7 @@ struct nouveau_drm {
        /* context for accelerated drm-internal operations */
        struct nouveau_channel *cechan;
        struct nouveau_channel *channel;
-       struct nouveau_gpuobj *notify;
+       struct nvkm_gpuobj *notify;
        struct nouveau_fbdev *fbcon;
        struct nvif_object nvsw;
        struct nvif_object ntfy;
index 5f0e37fc28490901a96f6f6dc1228d02e6bb7b98..c57a37e8e1eb9e213a088bafa0e61f60f8380710 100644 (file)
 
 #define NV_DPMS_CLEARED 0x80
 
-struct nouveau_i2c_port;
+struct nvkm_i2c_port;
 
 struct nouveau_encoder {
        struct drm_encoder_slave base;
 
        struct dcb_output *dcb;
        int or;
-       struct nouveau_i2c_port *i2c;
+       struct nvkm_i2c_port *i2c;
 
        /* different to drm_encoder.crtc, this reflects what's
         * actually programmed on the hw, not the proposed crtc */
index 3ed12a8cfc914520fc097ac98e5e16e63ed0d532..79924e4b1b495577f26822f8f03801b67e4497a6 100644 (file)
@@ -370,6 +370,7 @@ nouveau_fbcon_create(struct drm_fb_helper *helper,
                ret = -ENOMEM;
                goto out_unlock;
        }
+       info->skip_vt_switch = 1;
 
        ret = fb_alloc_cmap(&info->cmap, 256, 0);
        if (ret) {
@@ -487,30 +488,17 @@ static const struct drm_fb_helper_funcs nouveau_fbcon_helper_funcs = {
        .fb_probe = nouveau_fbcon_create,
 };
 
-static void
-nouveau_fbcon_set_suspend_work(struct work_struct *work)
-{
-       struct nouveau_fbdev *fbcon = container_of(work, typeof(*fbcon), work);
-       console_lock();
-       nouveau_fbcon_accel_restore(fbcon->dev);
-       nouveau_fbcon_zfill(fbcon->dev, fbcon);
-       fb_set_suspend(fbcon->helper.fbdev, FBINFO_STATE_RUNNING);
-       console_unlock();
-}
-
 void
 nouveau_fbcon_set_suspend(struct drm_device *dev, int state)
 {
        struct nouveau_drm *drm = nouveau_drm(dev);
        if (drm->fbcon) {
-               if (state == FBINFO_STATE_RUNNING) {
-                       schedule_work(&drm->fbcon->work);
-                       return;
-               }
-               flush_work(&drm->fbcon->work);
                console_lock();
+               if (state == FBINFO_STATE_RUNNING)
+                       nouveau_fbcon_accel_restore(dev);
                fb_set_suspend(drm->fbcon->helper.fbdev, state);
-               nouveau_fbcon_accel_save_disable(dev);
+               if (state != FBINFO_STATE_RUNNING)
+                       nouveau_fbcon_accel_save_disable(dev);
                console_unlock();
        }
 }
@@ -531,7 +519,6 @@ nouveau_fbcon_init(struct drm_device *dev)
        if (!fbcon)
                return -ENOMEM;
 
-       INIT_WORK(&fbcon->work, nouveau_fbcon_set_suspend_work);
        fbcon->dev = dev;
        drm->fbcon = fbcon;
 
@@ -539,12 +526,12 @@ nouveau_fbcon_init(struct drm_device *dev)
 
        ret = drm_fb_helper_init(dev, &fbcon->helper,
                                 dev->mode_config.num_crtc, 4);
-       if (ret) {
-               kfree(fbcon);
-               return ret;
-       }
+       if (ret)
+               goto free;
 
-       drm_fb_helper_single_add_all_connectors(&fbcon->helper);
+       ret = drm_fb_helper_single_add_all_connectors(&fbcon->helper);
+       if (ret)
+               goto fini;
 
        if (drm->device.info.ram_size <= 32 * 1024 * 1024)
                preferred_bpp = 8;
@@ -557,8 +544,17 @@ nouveau_fbcon_init(struct drm_device *dev)
        /* disable all the possible outputs/crtcs before entering KMS mode */
        drm_helper_disable_unused_functions(dev);
 
-       drm_fb_helper_initial_config(&fbcon->helper, preferred_bpp);
+       ret = drm_fb_helper_initial_config(&fbcon->helper, preferred_bpp);
+       if (ret)
+               goto fini;
+
        return 0;
+
+fini:
+       drm_fb_helper_fini(&fbcon->helper);
+free:
+       kfree(fbcon);
+       return ret;
 }
 
 void
index 6208e70e4a1cfdd16a949db884a605466d0ced38..1e2e9e27a03bbdfdbf215d14d22378f9607c4f76 100644 (file)
@@ -36,7 +36,6 @@ struct nouveau_fbdev {
        struct nouveau_framebuffer nouveau_fb;
        struct list_head fbdev_list;
        struct drm_device *dev;
-       struct work_struct work;
        unsigned int saved_flags;
        struct nvif_object surf2d;
        struct nvif_object clip;
index f32a434724e307f5da958de0bdf26bb09d115f4b..c6d56bef5823f7db0ef787d5a0b7e8ae234e1a6c 100644 (file)
@@ -182,7 +182,7 @@ nouveau_fence_context_new(struct nouveau_channel *chan, struct nouveau_fence_cha
        else if (chan == chan->drm->channel)
                strcpy(fctx->name, "generic kernel channel");
        else
-               strcpy(fctx->name, nvkm_client(&cli->base)->name);
+               strcpy(fctx->name, nvxx_client(&cli->base)->name);
 
        kref_init(&fctx->fence_ref);
        if (!priv->uevent)
index 96e461c6f68fac370602777d8e5bd363100fa0a5..d9241d8247fbcb4f1db2f4711633375e8c0164e4 100644 (file)
@@ -89,9 +89,9 @@ int nouveau_flip_complete(void *chan);
 
 struct nv84_fence_chan {
        struct nouveau_fence_chan base;
-       struct nouveau_vma vma;
-       struct nouveau_vma vma_gart;
-       struct nouveau_vma dispc_vma[4];
+       struct nvkm_vma vma;
+       struct nvkm_vma vma_gart;
+       struct nvkm_vma dispc_vma[4];
 };
 
 struct nv84_fence_priv {
index bf0f9e21d714a80248749ed0594699054e1b7fea..7c077fced1d13b84fa9a38e6680ad6174f3d2f08 100644 (file)
@@ -64,7 +64,7 @@ nouveau_gem_object_open(struct drm_gem_object *gem, struct drm_file *file_priv)
        struct nouveau_cli *cli = nouveau_cli(file_priv);
        struct nouveau_bo *nvbo = nouveau_gem_object(gem);
        struct nouveau_drm *drm = nouveau_bdev(nvbo->bo.bdev);
-       struct nouveau_vma *vma;
+       struct nvkm_vma *vma;
        struct device *dev = drm->dev->dev;
        int ret;
 
@@ -105,14 +105,14 @@ out:
 static void
 nouveau_gem_object_delete(void *data)
 {
-       struct nouveau_vma *vma = data;
-       nouveau_vm_unmap(vma);
-       nouveau_vm_put(vma);
+       struct nvkm_vma *vma = data;
+       nvkm_vm_unmap(vma);
+       nvkm_vm_put(vma);
        kfree(vma);
 }
 
 static void
-nouveau_gem_object_unmap(struct nouveau_bo *nvbo, struct nouveau_vma *vma)
+nouveau_gem_object_unmap(struct nouveau_bo *nvbo, struct nvkm_vma *vma)
 {
        const bool mapped = nvbo->bo.mem.mem_type != TTM_PL_SYSTEM;
        struct reservation_object *resv = nvbo->bo.resv;
@@ -135,8 +135,8 @@ nouveau_gem_object_unmap(struct nouveau_bo *nvbo, struct nouveau_vma *vma)
                nouveau_fence_work(fence, nouveau_gem_object_delete, vma);
        } else {
                if (mapped)
-                       nouveau_vm_unmap(vma);
-               nouveau_vm_put(vma);
+                       nvkm_vm_unmap(vma);
+               nvkm_vm_put(vma);
                kfree(vma);
        }
 }
@@ -148,7 +148,7 @@ nouveau_gem_object_close(struct drm_gem_object *gem, struct drm_file *file_priv)
        struct nouveau_bo *nvbo = nouveau_gem_object(gem);
        struct nouveau_drm *drm = nouveau_bdev(nvbo->bo.bdev);
        struct device *dev = drm->dev->dev;
-       struct nouveau_vma *vma;
+       struct nvkm_vma *vma;
        int ret;
 
        if (!cli->vm)
@@ -222,7 +222,7 @@ nouveau_gem_info(struct drm_file *file_priv, struct drm_gem_object *gem,
 {
        struct nouveau_cli *cli = nouveau_cli(file_priv);
        struct nouveau_bo *nvbo = nouveau_gem_object(gem);
-       struct nouveau_vma *vma;
+       struct nvkm_vma *vma;
 
        if (nvbo->bo.mem.mem_type == TTM_PL_TT)
                rep->domain = NOUVEAU_GEM_DOMAIN_GART;
@@ -251,7 +251,7 @@ nouveau_gem_ioctl_new(struct drm_device *dev, void *data,
 {
        struct nouveau_drm *drm = nouveau_drm(dev);
        struct nouveau_cli *cli = nouveau_cli(file_priv);
-       struct nouveau_fb *pfb = nvkm_fb(&drm->device);
+       struct nvkm_fb *pfb = nvxx_fb(&drm->device);
        struct drm_nouveau_gem_new *req = data;
        struct nouveau_bo *nvbo = NULL;
        int ret = 0;
@@ -850,19 +850,6 @@ out_next:
        return nouveau_abi16_put(abi16, ret);
 }
 
-static inline uint32_t
-domain_to_ttm(struct nouveau_bo *nvbo, uint32_t domain)
-{
-       uint32_t flags = 0;
-
-       if (domain & NOUVEAU_GEM_DOMAIN_VRAM)
-               flags |= TTM_PL_FLAG_VRAM;
-       if (domain & NOUVEAU_GEM_DOMAIN_GART)
-               flags |= TTM_PL_FLAG_TT;
-
-       return flags;
-}
-
 int
 nouveau_gem_ioctl_cpu_prep(struct drm_device *dev, void *data,
                           struct drm_file *file_priv)
index afb36d66e78d09133f81ce23a257f713c4f5e5b8..0dbe0060f86e2647fb7af62e19350cce3ee11f77 100644 (file)
@@ -40,7 +40,7 @@ nouveau_hwmon_show_temp(struct device *d, struct device_attribute *a, char *buf)
 {
        struct drm_device *dev = dev_get_drvdata(d);
        struct nouveau_drm *drm = nouveau_drm(dev);
-       struct nouveau_therm *therm = nvkm_therm(&drm->device);
+       struct nvkm_therm *therm = nvxx_therm(&drm->device);
        int temp = therm->temp_get(therm);
 
        if (temp < 0)
@@ -66,10 +66,10 @@ nouveau_hwmon_temp1_auto_point1_temp(struct device *d,
 {
        struct drm_device *dev = dev_get_drvdata(d);
        struct nouveau_drm *drm = nouveau_drm(dev);
-       struct nouveau_therm *therm = nvkm_therm(&drm->device);
+       struct nvkm_therm *therm = nvxx_therm(&drm->device);
 
        return snprintf(buf, PAGE_SIZE, "%d\n",
-             therm->attr_get(therm, NOUVEAU_THERM_ATTR_THRS_FAN_BOOST) * 1000);
+             therm->attr_get(therm, NVKM_THERM_ATTR_THRS_FAN_BOOST) * 1000);
 }
 static ssize_t
 nouveau_hwmon_set_temp1_auto_point1_temp(struct device *d,
@@ -78,13 +78,13 @@ nouveau_hwmon_set_temp1_auto_point1_temp(struct device *d,
 {
        struct drm_device *dev = dev_get_drvdata(d);
        struct nouveau_drm *drm = nouveau_drm(dev);
-       struct nouveau_therm *therm = nvkm_therm(&drm->device);
+       struct nvkm_therm *therm = nvxx_therm(&drm->device);
        long value;
 
        if (kstrtol(buf, 10, &value) == -EINVAL)
                return count;
 
-       therm->attr_set(therm, NOUVEAU_THERM_ATTR_THRS_FAN_BOOST,
+       therm->attr_set(therm, NVKM_THERM_ATTR_THRS_FAN_BOOST,
                        value / 1000);
 
        return count;
@@ -99,10 +99,10 @@ nouveau_hwmon_temp1_auto_point1_temp_hyst(struct device *d,
 {
        struct drm_device *dev = dev_get_drvdata(d);
        struct nouveau_drm *drm = nouveau_drm(dev);
-       struct nouveau_therm *therm = nvkm_therm(&drm->device);
+       struct nvkm_therm *therm = nvxx_therm(&drm->device);
 
        return snprintf(buf, PAGE_SIZE, "%d\n",
-        therm->attr_get(therm, NOUVEAU_THERM_ATTR_THRS_FAN_BOOST_HYST) * 1000);
+        therm->attr_get(therm, NVKM_THERM_ATTR_THRS_FAN_BOOST_HYST) * 1000);
 }
 static ssize_t
 nouveau_hwmon_set_temp1_auto_point1_temp_hyst(struct device *d,
@@ -111,13 +111,13 @@ nouveau_hwmon_set_temp1_auto_point1_temp_hyst(struct device *d,
 {
        struct drm_device *dev = dev_get_drvdata(d);
        struct nouveau_drm *drm = nouveau_drm(dev);
-       struct nouveau_therm *therm = nvkm_therm(&drm->device);
+       struct nvkm_therm *therm = nvxx_therm(&drm->device);
        long value;
 
        if (kstrtol(buf, 10, &value) == -EINVAL)
                return count;
 
-       therm->attr_set(therm, NOUVEAU_THERM_ATTR_THRS_FAN_BOOST_HYST,
+       therm->attr_set(therm, NVKM_THERM_ATTR_THRS_FAN_BOOST_HYST,
                        value / 1000);
 
        return count;
@@ -131,10 +131,10 @@ nouveau_hwmon_max_temp(struct device *d, struct device_attribute *a, char *buf)
 {
        struct drm_device *dev = dev_get_drvdata(d);
        struct nouveau_drm *drm = nouveau_drm(dev);
-       struct nouveau_therm *therm = nvkm_therm(&drm->device);
+       struct nvkm_therm *therm = nvxx_therm(&drm->device);
 
        return snprintf(buf, PAGE_SIZE, "%d\n",
-              therm->attr_get(therm, NOUVEAU_THERM_ATTR_THRS_DOWN_CLK) * 1000);
+              therm->attr_get(therm, NVKM_THERM_ATTR_THRS_DOWN_CLK) * 1000);
 }
 static ssize_t
 nouveau_hwmon_set_max_temp(struct device *d, struct device_attribute *a,
@@ -142,13 +142,13 @@ nouveau_hwmon_set_max_temp(struct device *d, struct device_attribute *a,
 {
        struct drm_device *dev = dev_get_drvdata(d);
        struct nouveau_drm *drm = nouveau_drm(dev);
-       struct nouveau_therm *therm = nvkm_therm(&drm->device);
+       struct nvkm_therm *therm = nvxx_therm(&drm->device);
        long value;
 
        if (kstrtol(buf, 10, &value) == -EINVAL)
                return count;
 
-       therm->attr_set(therm, NOUVEAU_THERM_ATTR_THRS_DOWN_CLK, value / 1000);
+       therm->attr_set(therm, NVKM_THERM_ATTR_THRS_DOWN_CLK, value / 1000);
 
        return count;
 }
@@ -162,10 +162,10 @@ nouveau_hwmon_max_temp_hyst(struct device *d, struct device_attribute *a,
 {
        struct drm_device *dev = dev_get_drvdata(d);
        struct nouveau_drm *drm = nouveau_drm(dev);
-       struct nouveau_therm *therm = nvkm_therm(&drm->device);
+       struct nvkm_therm *therm = nvxx_therm(&drm->device);
 
        return snprintf(buf, PAGE_SIZE, "%d\n",
-         therm->attr_get(therm, NOUVEAU_THERM_ATTR_THRS_DOWN_CLK_HYST) * 1000);
+         therm->attr_get(therm, NVKM_THERM_ATTR_THRS_DOWN_CLK_HYST) * 1000);
 }
 static ssize_t
 nouveau_hwmon_set_max_temp_hyst(struct device *d, struct device_attribute *a,
@@ -173,13 +173,13 @@ nouveau_hwmon_set_max_temp_hyst(struct device *d, struct device_attribute *a,
 {
        struct drm_device *dev = dev_get_drvdata(d);
        struct nouveau_drm *drm = nouveau_drm(dev);
-       struct nouveau_therm *therm = nvkm_therm(&drm->device);
+       struct nvkm_therm *therm = nvxx_therm(&drm->device);
        long value;
 
        if (kstrtol(buf, 10, &value) == -EINVAL)
                return count;
 
-       therm->attr_set(therm, NOUVEAU_THERM_ATTR_THRS_DOWN_CLK_HYST,
+       therm->attr_set(therm, NVKM_THERM_ATTR_THRS_DOWN_CLK_HYST,
                        value / 1000);
 
        return count;
@@ -194,10 +194,10 @@ nouveau_hwmon_critical_temp(struct device *d, struct device_attribute *a,
 {
        struct drm_device *dev = dev_get_drvdata(d);
        struct nouveau_drm *drm = nouveau_drm(dev);
-       struct nouveau_therm *therm = nvkm_therm(&drm->device);
+       struct nvkm_therm *therm = nvxx_therm(&drm->device);
 
        return snprintf(buf, PAGE_SIZE, "%d\n",
-              therm->attr_get(therm, NOUVEAU_THERM_ATTR_THRS_CRITICAL) * 1000);
+              therm->attr_get(therm, NVKM_THERM_ATTR_THRS_CRITICAL) * 1000);
 }
 static ssize_t
 nouveau_hwmon_set_critical_temp(struct device *d, struct device_attribute *a,
@@ -206,13 +206,13 @@ nouveau_hwmon_set_critical_temp(struct device *d, struct device_attribute *a,
 {
        struct drm_device *dev = dev_get_drvdata(d);
        struct nouveau_drm *drm = nouveau_drm(dev);
-       struct nouveau_therm *therm = nvkm_therm(&drm->device);
+       struct nvkm_therm *therm = nvxx_therm(&drm->device);
        long value;
 
        if (kstrtol(buf, 10, &value) == -EINVAL)
                return count;
 
-       therm->attr_set(therm, NOUVEAU_THERM_ATTR_THRS_CRITICAL, value / 1000);
+       therm->attr_set(therm, NVKM_THERM_ATTR_THRS_CRITICAL, value / 1000);
 
        return count;
 }
@@ -227,10 +227,10 @@ nouveau_hwmon_critical_temp_hyst(struct device *d, struct device_attribute *a,
 {
        struct drm_device *dev = dev_get_drvdata(d);
        struct nouveau_drm *drm = nouveau_drm(dev);
-       struct nouveau_therm *therm = nvkm_therm(&drm->device);
+       struct nvkm_therm *therm = nvxx_therm(&drm->device);
 
        return snprintf(buf, PAGE_SIZE, "%d\n",
-         therm->attr_get(therm, NOUVEAU_THERM_ATTR_THRS_CRITICAL_HYST) * 1000);
+         therm->attr_get(therm, NVKM_THERM_ATTR_THRS_CRITICAL_HYST) * 1000);
 }
 static ssize_t
 nouveau_hwmon_set_critical_temp_hyst(struct device *d,
@@ -240,13 +240,13 @@ nouveau_hwmon_set_critical_temp_hyst(struct device *d,
 {
        struct drm_device *dev = dev_get_drvdata(d);
        struct nouveau_drm *drm = nouveau_drm(dev);
-       struct nouveau_therm *therm = nvkm_therm(&drm->device);
+       struct nvkm_therm *therm = nvxx_therm(&drm->device);
        long value;
 
        if (kstrtol(buf, 10, &value) == -EINVAL)
                return count;
 
-       therm->attr_set(therm, NOUVEAU_THERM_ATTR_THRS_CRITICAL_HYST,
+       therm->attr_set(therm, NVKM_THERM_ATTR_THRS_CRITICAL_HYST,
                        value / 1000);
 
        return count;
@@ -260,10 +260,10 @@ nouveau_hwmon_emergency_temp(struct device *d, struct device_attribute *a,
 {
        struct drm_device *dev = dev_get_drvdata(d);
        struct nouveau_drm *drm = nouveau_drm(dev);
-       struct nouveau_therm *therm = nvkm_therm(&drm->device);
+       struct nvkm_therm *therm = nvxx_therm(&drm->device);
 
        return snprintf(buf, PAGE_SIZE, "%d\n",
-              therm->attr_get(therm, NOUVEAU_THERM_ATTR_THRS_SHUTDOWN) * 1000);
+              therm->attr_get(therm, NVKM_THERM_ATTR_THRS_SHUTDOWN) * 1000);
 }
 static ssize_t
 nouveau_hwmon_set_emergency_temp(struct device *d, struct device_attribute *a,
@@ -272,13 +272,13 @@ nouveau_hwmon_set_emergency_temp(struct device *d, struct device_attribute *a,
 {
        struct drm_device *dev = dev_get_drvdata(d);
        struct nouveau_drm *drm = nouveau_drm(dev);
-       struct nouveau_therm *therm = nvkm_therm(&drm->device);
+       struct nvkm_therm *therm = nvxx_therm(&drm->device);
        long value;
 
        if (kstrtol(buf, 10, &value) == -EINVAL)
                return count;
 
-       therm->attr_set(therm, NOUVEAU_THERM_ATTR_THRS_SHUTDOWN, value / 1000);
+       therm->attr_set(therm, NVKM_THERM_ATTR_THRS_SHUTDOWN, value / 1000);
 
        return count;
 }
@@ -293,10 +293,10 @@ nouveau_hwmon_emergency_temp_hyst(struct device *d, struct device_attribute *a,
 {
        struct drm_device *dev = dev_get_drvdata(d);
        struct nouveau_drm *drm = nouveau_drm(dev);
-       struct nouveau_therm *therm = nvkm_therm(&drm->device);
+       struct nvkm_therm *therm = nvxx_therm(&drm->device);
 
        return snprintf(buf, PAGE_SIZE, "%d\n",
-         therm->attr_get(therm, NOUVEAU_THERM_ATTR_THRS_SHUTDOWN_HYST) * 1000);
+         therm->attr_get(therm, NVKM_THERM_ATTR_THRS_SHUTDOWN_HYST) * 1000);
 }
 static ssize_t
 nouveau_hwmon_set_emergency_temp_hyst(struct device *d,
@@ -306,13 +306,13 @@ nouveau_hwmon_set_emergency_temp_hyst(struct device *d,
 {
        struct drm_device *dev = dev_get_drvdata(d);
        struct nouveau_drm *drm = nouveau_drm(dev);
-       struct nouveau_therm *therm = nvkm_therm(&drm->device);
+       struct nvkm_therm *therm = nvxx_therm(&drm->device);
        long value;
 
        if (kstrtol(buf, 10, &value) == -EINVAL)
                return count;
 
-       therm->attr_set(therm, NOUVEAU_THERM_ATTR_THRS_SHUTDOWN_HYST,
+       therm->attr_set(therm, NVKM_THERM_ATTR_THRS_SHUTDOWN_HYST,
                        value / 1000);
 
        return count;
@@ -346,7 +346,7 @@ nouveau_hwmon_show_fan1_input(struct device *d, struct device_attribute *attr,
 {
        struct drm_device *dev = dev_get_drvdata(d);
        struct nouveau_drm *drm = nouveau_drm(dev);
-       struct nouveau_therm *therm = nvkm_therm(&drm->device);
+       struct nvkm_therm *therm = nvxx_therm(&drm->device);
 
        return snprintf(buf, PAGE_SIZE, "%d\n", therm->fan_sense(therm));
 }
@@ -359,10 +359,10 @@ nouveau_hwmon_get_pwm1_enable(struct device *d,
 {
        struct drm_device *dev = dev_get_drvdata(d);
        struct nouveau_drm *drm = nouveau_drm(dev);
-       struct nouveau_therm *therm = nvkm_therm(&drm->device);
+       struct nvkm_therm *therm = nvxx_therm(&drm->device);
        int ret;
 
-       ret = therm->attr_get(therm, NOUVEAU_THERM_ATTR_FAN_MODE);
+       ret = therm->attr_get(therm, NVKM_THERM_ATTR_FAN_MODE);
        if (ret < 0)
                return ret;
 
@@ -375,7 +375,7 @@ nouveau_hwmon_set_pwm1_enable(struct device *d, struct device_attribute *a,
 {
        struct drm_device *dev = dev_get_drvdata(d);
        struct nouveau_drm *drm = nouveau_drm(dev);
-       struct nouveau_therm *therm = nvkm_therm(&drm->device);
+       struct nvkm_therm *therm = nvxx_therm(&drm->device);
        long value;
        int ret;
 
@@ -383,7 +383,7 @@ nouveau_hwmon_set_pwm1_enable(struct device *d, struct device_attribute *a,
        if (ret)
                return ret;
 
-       ret = therm->attr_set(therm, NOUVEAU_THERM_ATTR_FAN_MODE, value);
+       ret = therm->attr_set(therm, NVKM_THERM_ATTR_FAN_MODE, value);
        if (ret)
                return ret;
        else
@@ -398,7 +398,7 @@ nouveau_hwmon_get_pwm1(struct device *d, struct device_attribute *a, char *buf)
 {
        struct drm_device *dev = dev_get_drvdata(d);
        struct nouveau_drm *drm = nouveau_drm(dev);
-       struct nouveau_therm *therm = nvkm_therm(&drm->device);
+       struct nvkm_therm *therm = nvxx_therm(&drm->device);
        int ret;
 
        ret = therm->fan_get(therm);
@@ -414,7 +414,7 @@ nouveau_hwmon_set_pwm1(struct device *d, struct device_attribute *a,
 {
        struct drm_device *dev = dev_get_drvdata(d);
        struct nouveau_drm *drm = nouveau_drm(dev);
-       struct nouveau_therm *therm = nvkm_therm(&drm->device);
+       struct nvkm_therm *therm = nvxx_therm(&drm->device);
        int ret = -ENODEV;
        long value;
 
@@ -438,10 +438,10 @@ nouveau_hwmon_get_pwm1_min(struct device *d,
 {
        struct drm_device *dev = dev_get_drvdata(d);
        struct nouveau_drm *drm = nouveau_drm(dev);
-       struct nouveau_therm *therm = nvkm_therm(&drm->device);
+       struct nvkm_therm *therm = nvxx_therm(&drm->device);
        int ret;
 
-       ret = therm->attr_get(therm, NOUVEAU_THERM_ATTR_FAN_MIN_DUTY);
+       ret = therm->attr_get(therm, NVKM_THERM_ATTR_FAN_MIN_DUTY);
        if (ret < 0)
                return ret;
 
@@ -454,14 +454,14 @@ nouveau_hwmon_set_pwm1_min(struct device *d, struct device_attribute *a,
 {
        struct drm_device *dev = dev_get_drvdata(d);
        struct nouveau_drm *drm = nouveau_drm(dev);
-       struct nouveau_therm *therm = nvkm_therm(&drm->device);
+       struct nvkm_therm *therm = nvxx_therm(&drm->device);
        long value;
        int ret;
 
        if (kstrtol(buf, 10, &value) == -EINVAL)
                return -EINVAL;
 
-       ret = therm->attr_set(therm, NOUVEAU_THERM_ATTR_FAN_MIN_DUTY, value);
+       ret = therm->attr_set(therm, NVKM_THERM_ATTR_FAN_MIN_DUTY, value);
        if (ret < 0)
                return ret;
 
@@ -478,10 +478,10 @@ nouveau_hwmon_get_pwm1_max(struct device *d,
 {
        struct drm_device *dev = dev_get_drvdata(d);
        struct nouveau_drm *drm = nouveau_drm(dev);
-       struct nouveau_therm *therm = nvkm_therm(&drm->device);
+       struct nvkm_therm *therm = nvxx_therm(&drm->device);
        int ret;
 
-       ret = therm->attr_get(therm, NOUVEAU_THERM_ATTR_FAN_MAX_DUTY);
+       ret = therm->attr_get(therm, NVKM_THERM_ATTR_FAN_MAX_DUTY);
        if (ret < 0)
                return ret;
 
@@ -494,14 +494,14 @@ nouveau_hwmon_set_pwm1_max(struct device *d, struct device_attribute *a,
 {
        struct drm_device *dev = dev_get_drvdata(d);
        struct nouveau_drm *drm = nouveau_drm(dev);
-       struct nouveau_therm *therm = nvkm_therm(&drm->device);
+       struct nvkm_therm *therm = nvxx_therm(&drm->device);
        long value;
        int ret;
 
        if (kstrtol(buf, 10, &value) == -EINVAL)
                return -EINVAL;
 
-       ret = therm->attr_set(therm, NOUVEAU_THERM_ATTR_FAN_MAX_DUTY, value);
+       ret = therm->attr_set(therm, NVKM_THERM_ATTR_FAN_MAX_DUTY, value);
        if (ret < 0)
                return ret;
 
@@ -561,7 +561,7 @@ nouveau_hwmon_init(struct drm_device *dev)
 {
 #if defined(CONFIG_HWMON) || (defined(MODULE) && defined(CONFIG_HWMON_MODULE))
        struct nouveau_drm *drm = nouveau_drm(dev);
-       struct nouveau_therm *therm = nvkm_therm(&drm->device);
+       struct nvkm_therm *therm = nvxx_therm(&drm->device);
        struct nouveau_hwmon *hwmon;
        struct device *hwmon_dev;
        int ret = 0;
index 6544b84f03034716e6e465f97366cba1151707ff..ca0ad9d1563df627bd4228212ae294b47f894d74 100644 (file)
@@ -60,22 +60,22 @@ nvkm_client_ioctl(void *priv, bool super, void *data, u32 size, void **hack)
 static int
 nvkm_client_resume(void *priv)
 {
-       return nouveau_client_init(priv);
+       return nvkm_client_init(priv);
 }
 
 static int
 nvkm_client_suspend(void *priv)
 {
-       return nouveau_client_fini(priv, true);
+       return nvkm_client_fini(priv, true);
 }
 
 static void
-nvkm_client_fini(void *priv)
+nvkm_client_driver_fini(void *priv)
 {
-       struct nouveau_object *client = priv;
-       nouveau_client_fini(nv_client(client), false);
+       struct nvkm_object *client = priv;
+       nvkm_client_fini(nv_client(client), false);
        atomic_set(&client->refcount, 1);
-       nouveau_object_ref(NULL, &client);
+       nvkm_object_ref(NULL, &client);
 }
 
 static int
@@ -107,13 +107,13 @@ nvkm_client_ntfy(const void *header, u32 length, const void *data, u32 size)
 }
 
 static int
-nvkm_client_init(const char *name, u64 device, const char *cfg,
-                const char *dbg, void **ppriv)
+nvkm_client_driver_init(const char *name, u64 device, const char *cfg,
+                       const char *dbg, void **ppriv)
 {
-       struct nouveau_client *client;
+       struct nvkm_client *client;
        int ret;
 
-       ret = nouveau_client_create(name, device, cfg, dbg, &client);
+       ret = nvkm_client_create(name, device, cfg, dbg, &client);
        *ppriv = client;
        if (ret)
                return ret;
@@ -125,8 +125,8 @@ nvkm_client_init(const char *name, u64 device, const char *cfg,
 const struct nvif_driver
 nvif_driver_nvkm = {
        .name = "nvkm",
-       .init = nvkm_client_init,
-       .fini = nvkm_client_fini,
+       .init = nvkm_client_driver_init,
+       .fini = nvkm_client_driver_fini,
        .suspend = nvkm_client_suspend,
        .resume = nvkm_client_resume,
        .ioctl = nvkm_client_ioctl,
index b307bbedd4c43548387557ca0cd4a44a5654ae4e..dc5900bf54ff2117667ce0aaea5b3ef3b8516e16 100644 (file)
@@ -152,7 +152,7 @@ static int nouveau_platform_remove(struct platform_device *pdev)
 {
        struct drm_device *drm_dev = platform_get_drvdata(pdev);
        struct nouveau_drm *drm = nouveau_drm(drm_dev);
-       struct nouveau_device *device = nvkm_device(&drm->device);
+       struct nvkm_device *device = nvxx_device(&drm->device);
        struct nouveau_platform_gpu *gpu = nv_device_to_platform(device)->gpu;
 
        nouveau_drm_device_remove(drm_dev);
@@ -177,9 +177,3 @@ struct platform_driver nouveau_platform_driver = {
        .probe = nouveau_platform_probe,
        .remove = nouveau_platform_remove,
 };
-
-module_platform_driver(nouveau_platform_driver);
-
-MODULE_AUTHOR(DRIVER_AUTHOR);
-MODULE_DESCRIPTION(DRIVER_DESC);
-MODULE_LICENSE("GPL and additional rights");
index 58c28b5653d5a8ade0718edd509646888bdf9a6d..268bb72136815a2cc4bb6c9da6bf5b6a4e5d9e7e 100644 (file)
@@ -28,6 +28,7 @@
 struct reset_control;
 struct clk;
 struct regulator;
+struct platform_driver;
 
 struct nouveau_platform_gpu {
        struct reset_control *rst;
@@ -38,7 +39,7 @@ struct nouveau_platform_gpu {
 };
 
 struct nouveau_platform_device {
-       struct nouveau_device device;
+       struct nvkm_device device;
 
        struct nouveau_platform_gpu *gpu;
 
@@ -48,4 +49,6 @@ struct nouveau_platform_device {
 #define nv_device_to_platform(d)                                               \
        container_of(d, struct nouveau_platform_device, device)
 
+extern struct platform_driver nouveau_platform_driver;
+
 #endif
index 43a96b99e18079ba0b808f08c61cb3437e8ebd10..7226f1f609014e9249c2156dbdc523531e21352c 100644 (file)
@@ -72,7 +72,7 @@
 #    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_SW           0
 #        define NV_RAMHT_CONTEXT_ENGINE_GRAPHICS           1
 #    define NV_RAMHT_CONTEXT_INSTANCE_SHIFT                0
 #    define NV40_RAMHT_CONTEXT_CHANNEL_SHIFT               23
index 01707e7deaf5b55f4ff702b54329b7eb7358dd28..8c3053a177d6c4c36a0b5acd405fc72c340eea2c 100644 (file)
@@ -9,8 +9,7 @@ struct nouveau_sgdma_be {
         * nouve_bo.c works properly, otherwise have to move them here
         */
        struct ttm_dma_tt ttm;
-       struct drm_device *dev;
-       struct nouveau_mem *node;
+       struct nvkm_mem *node;
 };
 
 static void
@@ -28,7 +27,7 @@ static int
 nv04_sgdma_bind(struct ttm_tt *ttm, struct ttm_mem_reg *mem)
 {
        struct nouveau_sgdma_be *nvbe = (struct nouveau_sgdma_be *)ttm;
-       struct nouveau_mem *node = mem->mm_node;
+       struct nvkm_mem *node = mem->mm_node;
 
        if (ttm->sg) {
                node->sg    = ttm->sg;
@@ -39,7 +38,7 @@ nv04_sgdma_bind(struct ttm_tt *ttm, struct ttm_mem_reg *mem)
        }
        node->size = (mem->num_pages << PAGE_SHIFT) >> 12;
 
-       nouveau_vm_map(&node->vma[0], node);
+       nvkm_vm_map(&node->vma[0], node);
        nvbe->node = node;
        return 0;
 }
@@ -48,7 +47,7 @@ static int
 nv04_sgdma_unbind(struct ttm_tt *ttm)
 {
        struct nouveau_sgdma_be *nvbe = (struct nouveau_sgdma_be *)ttm;
-       nouveau_vm_unmap(&nvbe->node->vma[0]);
+       nvkm_vm_unmap(&nvbe->node->vma[0]);
        return 0;
 }
 
@@ -62,7 +61,7 @@ static int
 nv50_sgdma_bind(struct ttm_tt *ttm, struct ttm_mem_reg *mem)
 {
        struct nouveau_sgdma_be *nvbe = (struct nouveau_sgdma_be *)ttm;
-       struct nouveau_mem *node = mem->mm_node;
+       struct nvkm_mem *node = mem->mm_node;
 
        /* noop: bound in move_notify() */
        if (ttm->sg) {
@@ -101,13 +100,17 @@ nouveau_sgdma_create_ttm(struct ttm_bo_device *bdev,
        if (!nvbe)
                return NULL;
 
-       nvbe->dev = drm->dev;
        if (drm->device.info.family < NV_DEVICE_INFO_V0_TESLA)
                nvbe->ttm.ttm.func = &nv04_sgdma_backend;
        else
                nvbe->ttm.ttm.func = &nv50_sgdma_backend;
 
        if (ttm_dma_tt_init(&nvbe->ttm, bdev, size, page_flags, dummy_read_page))
+               /*
+                * A failing ttm_dma_tt_init() will call ttm_tt_destroy()
+                * and thus our nouveau_sgdma_destroy() hook, so we don't need
+                * to free nvbe here.
+                */
                return NULL;
        return &nvbe->ttm.ttm;
 }
index 8fbbf3093d8611e9497eaacdad73ec698bf42b10..1ec8f38ae69a030952c88cc685ca7335b5e4275d 100644 (file)
@@ -165,7 +165,7 @@ nouveau_sysfs_fini(struct drm_device *dev)
        struct nvif_device *device = &drm->device;
 
        if (sysfs && sysfs->ctrl.priv) {
-               device_remove_file(nv_device_base(nvkm_device(device)), &dev_attr_pstate);
+               device_remove_file(nv_device_base(nvxx_device(device)), &dev_attr_pstate);
                nvif_object_fini(&sysfs->ctrl);
        }
 
@@ -192,7 +192,7 @@ nouveau_sysfs_init(struct drm_device *dev)
                               NVIF_IOCTL_NEW_V0_CONTROL, NULL, 0,
                              &sysfs->ctrl);
        if (ret == 0)
-               device_create_file(nv_device_base(nvkm_device(device)), &dev_attr_pstate);
+               device_create_file(nv_device_base(nvxx_device(device)), &dev_attr_pstate);
 
        return 0;
 }
index 3d1cfcb96b6bfd9e7dfa50e282d6e3761009f7e1..273e50110ec3c1cd41f846b0ad1813879d159a9b 100644 (file)
@@ -33,7 +33,7 @@ static int
 nouveau_vram_manager_init(struct ttm_mem_type_manager *man, unsigned long psize)
 {
        struct nouveau_drm *drm = nouveau_bdev(man->bdev);
-       struct nouveau_fb *pfb = nvkm_fb(&drm->device);
+       struct nvkm_fb *pfb = nvxx_fb(&drm->device);
        man->priv = pfb;
        return 0;
 }
@@ -46,16 +46,16 @@ nouveau_vram_manager_fini(struct ttm_mem_type_manager *man)
 }
 
 static inline void
-nouveau_mem_node_cleanup(struct nouveau_mem *node)
+nvkm_mem_node_cleanup(struct nvkm_mem *node)
 {
        if (node->vma[0].node) {
-               nouveau_vm_unmap(&node->vma[0]);
-               nouveau_vm_put(&node->vma[0]);
+               nvkm_vm_unmap(&node->vma[0]);
+               nvkm_vm_put(&node->vma[0]);
        }
 
        if (node->vma[1].node) {
-               nouveau_vm_unmap(&node->vma[1]);
-               nouveau_vm_put(&node->vma[1]);
+               nvkm_vm_unmap(&node->vma[1]);
+               nvkm_vm_put(&node->vma[1]);
        }
 }
 
@@ -64,9 +64,9 @@ nouveau_vram_manager_del(struct ttm_mem_type_manager *man,
                         struct ttm_mem_reg *mem)
 {
        struct nouveau_drm *drm = nouveau_bdev(man->bdev);
-       struct nouveau_fb *pfb = nvkm_fb(&drm->device);
-       nouveau_mem_node_cleanup(mem->mm_node);
-       pfb->ram->put(pfb, (struct nouveau_mem **)&mem->mm_node);
+       struct nvkm_fb *pfb = nvxx_fb(&drm->device);
+       nvkm_mem_node_cleanup(mem->mm_node);
+       pfb->ram->put(pfb, (struct nvkm_mem **)&mem->mm_node);
 }
 
 static int
@@ -76,9 +76,9 @@ nouveau_vram_manager_new(struct ttm_mem_type_manager *man,
                         struct ttm_mem_reg *mem)
 {
        struct nouveau_drm *drm = nouveau_bdev(man->bdev);
-       struct nouveau_fb *pfb = nvkm_fb(&drm->device);
+       struct nvkm_fb *pfb = nvxx_fb(&drm->device);
        struct nouveau_bo *nvbo = nouveau_bo(bo);
-       struct nouveau_mem *node;
+       struct nvkm_mem *node;
        u32 size_nc = 0;
        int ret;
 
@@ -103,9 +103,9 @@ nouveau_vram_manager_new(struct ttm_mem_type_manager *man,
 static void
 nouveau_vram_manager_debug(struct ttm_mem_type_manager *man, const char *prefix)
 {
-       struct nouveau_fb *pfb = man->priv;
-       struct nouveau_mm *mm = &pfb->vram;
-       struct nouveau_mm_node *r;
+       struct nvkm_fb *pfb = man->priv;
+       struct nvkm_mm *mm = &pfb->vram;
+       struct nvkm_mm_node *r;
        u32 total = 0, free = 0;
 
        mutex_lock(&nv_subdev(pfb)->mutex);
@@ -150,7 +150,7 @@ static void
 nouveau_gart_manager_del(struct ttm_mem_type_manager *man,
                         struct ttm_mem_reg *mem)
 {
-       nouveau_mem_node_cleanup(mem->mm_node);
+       nvkm_mem_node_cleanup(mem->mm_node);
        kfree(mem->mm_node);
        mem->mm_node = NULL;
 }
@@ -163,7 +163,7 @@ nouveau_gart_manager_new(struct ttm_mem_type_manager *man,
 {
        struct nouveau_drm *drm = nouveau_bdev(bo->bdev);
        struct nouveau_bo *nvbo = nouveau_bo(bo);
-       struct nouveau_mem *node;
+       struct nvkm_mem *node;
 
        node = kzalloc(sizeof(*node), GFP_KERNEL);
        if (!node)
@@ -203,15 +203,15 @@ const struct ttm_mem_type_manager_func nouveau_gart_manager = {
 };
 
 /*XXX*/
-#include <core/subdev/vm/nv04.h>
+#include <subdev/mmu/nv04.h>
 static int
 nv04_gart_manager_init(struct ttm_mem_type_manager *man, unsigned long psize)
 {
        struct nouveau_drm *drm = nouveau_bdev(man->bdev);
-       struct nouveau_vmmgr *vmm = nvkm_vmmgr(&drm->device);
-       struct nv04_vmmgr_priv *priv = (void *)vmm;
-       struct nouveau_vm *vm = NULL;
-       nouveau_vm_ref(priv->vm, &vm, NULL);
+       struct nvkm_mmu *mmu = nvxx_mmu(&drm->device);
+       struct nv04_mmu_priv *priv = (void *)mmu;
+       struct nvkm_vm *vm = NULL;
+       nvkm_vm_ref(priv->vm, &vm, NULL);
        man->priv = vm;
        return 0;
 }
@@ -219,8 +219,8 @@ nv04_gart_manager_init(struct ttm_mem_type_manager *man, unsigned long psize)
 static int
 nv04_gart_manager_fini(struct ttm_mem_type_manager *man)
 {
-       struct nouveau_vm *vm = man->priv;
-       nouveau_vm_ref(NULL, &vm, NULL);
+       struct nvkm_vm *vm = man->priv;
+       nvkm_vm_ref(NULL, &vm, NULL);
        man->priv = NULL;
        return 0;
 }
@@ -228,9 +228,9 @@ nv04_gart_manager_fini(struct ttm_mem_type_manager *man)
 static void
 nv04_gart_manager_del(struct ttm_mem_type_manager *man, struct ttm_mem_reg *mem)
 {
-       struct nouveau_mem *node = mem->mm_node;
+       struct nvkm_mem *node = mem->mm_node;
        if (node->vma[0].node)
-               nouveau_vm_put(&node->vma[0]);
+               nvkm_vm_put(&node->vma[0]);
        kfree(mem->mm_node);
        mem->mm_node = NULL;
 }
@@ -241,7 +241,7 @@ nv04_gart_manager_new(struct ttm_mem_type_manager *man,
                      const struct ttm_place *place,
                      struct ttm_mem_reg *mem)
 {
-       struct nouveau_mem *node;
+       struct nvkm_mem *node;
        int ret;
 
        node = kzalloc(sizeof(*node), GFP_KERNEL);
@@ -250,8 +250,8 @@ nv04_gart_manager_new(struct ttm_mem_type_manager *man,
 
        node->page_shift = 12;
 
-       ret = nouveau_vm_get(man->priv, mem->num_pages << 12, node->page_shift,
-                            NV_MEM_ACCESS_RW, &node->vma[0]);
+       ret = nvkm_vm_get(man->priv, mem->num_pages << 12, node->page_shift,
+                         NV_MEM_ACCESS_RW, &node->vma[0]);
        if (ret) {
                kfree(node);
                return ret;
@@ -354,8 +354,8 @@ nouveau_ttm_init(struct nouveau_drm *drm)
        u32 bits;
        int ret;
 
-       bits = nvkm_vmmgr(&drm->device)->dma_bits;
-       if (nv_device_is_pci(nvkm_device(&drm->device))) {
+       bits = nvxx_mmu(&drm->device)->dma_bits;
+       if (nv_device_is_pci(nvxx_device(&drm->device))) {
                if (drm->agp.stat == ENABLED ||
                     !pci_dma_supported(dev->pdev, DMA_BIT_MASK(bits)))
                        bits = 32;
@@ -396,12 +396,12 @@ nouveau_ttm_init(struct nouveau_drm *drm)
                return ret;
        }
 
-       drm->ttm.mtrr = arch_phys_wc_add(nv_device_resource_start(nvkm_device(&drm->device), 1),
-                                        nv_device_resource_len(nvkm_device(&drm->device), 1));
+       drm->ttm.mtrr = arch_phys_wc_add(nv_device_resource_start(nvxx_device(&drm->device), 1),
+                                        nv_device_resource_len(nvxx_device(&drm->device), 1));
 
        /* GART init */
        if (drm->agp.stat != ENABLED) {
-               drm->gem.gart_available = nvkm_vmmgr(&drm->device)->limit;
+               drm->gem.gart_available = nvxx_mmu(&drm->device)->limit;
        } else {
                drm->gem.gart_available = drm->agp.size;
        }
index f9859deb108a460d34e3740746c691e628cbea4d..c2e05e64cd6f57efedf7154c11b6c5a734725e87 100644 (file)
@@ -57,7 +57,7 @@ nv04_fence_sync(struct nouveau_fence *fence,
 static u32
 nv04_fence_read(struct nouveau_channel *chan)
 {
-       struct nouveau_fifo_chan *fifo = nvkm_fifo_chan(chan);;
+       struct nvkm_fifo_chan *fifo = nvxx_fifo_chan(chan);;
        return atomic_read(&fifo->refcnt);
 }
 
index 490b90866baf4cae9feeb4880d33d03e47528bdc..7da7958556a3abe68f94eac820c62aa8b41a923a 100644 (file)
@@ -125,7 +125,6 @@ nv50_pioc_create(struct nvif_object *disp, const u32 *oclass, u8 head,
 
 struct nv50_curs {
        struct nv50_pioc base;
-       struct nouveau_bo *image;
 };
 
 static int
@@ -201,7 +200,7 @@ nv50_dmac_destroy(struct nv50_dmac *dmac, struct nvif_object *disp)
        nv50_chan_destroy(&dmac->base);
 
        if (dmac->ptr) {
-               struct pci_dev *pdev = nvkm_device(nvif_device(disp))->pdev;
+               struct pci_dev *pdev = nvxx_device(nvif_device(disp))->pdev;
                pci_free_consistent(pdev, PAGE_SIZE, dmac->ptr, dmac->handle);
        }
 }
@@ -218,7 +217,7 @@ nv50_dmac_create(struct nvif_object *disp, const u32 *oclass, u8 head,
 
        mutex_init(&dmac->lock);
 
-       dmac->ptr = pci_alloc_consistent(nvkm_device(device)->pdev,
+       dmac->ptr = pci_alloc_consistent(nvxx_device(device)->pdev,
                                         PAGE_SIZE, &dmac->handle);
        if (!dmac->ptr)
                return -ENOMEM;
@@ -421,9 +420,9 @@ evo_wait(void *evoc, int nr)
                dmac->ptr[put] = 0x20000000;
 
                nvif_wr32(&dmac->base.user, 0x0000, 0x00000000);
-               if (!nvkm_wait(&dmac->base.user, 0x0004, ~0, 0x00000000)) {
+               if (!nvxx_wait(&dmac->base.user, 0x0004, ~0, 0x00000000)) {
                        mutex_unlock(&dmac->lock);
-                       nv_error(nvkm_object(&dmac->base.user), "channel stalled\n");
+                       nv_error(nvxx_object(&dmac->base.user), "channel stalled\n");
                        return NULL;
                }
 
@@ -481,7 +480,7 @@ evo_sync(struct drm_device *dev)
                evo_data(push, 0x00000000);
                evo_data(push, 0x00000000);
                evo_kick(push, mast);
-               if (nv_wait_cb(nvkm_device(device), evo_sync_wait, disp->sync))
+               if (nv_wait_cb(nvxx_device(device), evo_sync_wait, disp->sync))
                        return 0;
        }
 
@@ -536,7 +535,7 @@ nv50_display_flip_stop(struct drm_crtc *crtc)
                evo_kick(push, flip.chan);
        }
 
-       nv_wait_cb(nvkm_device(device), nv50_display_flip_wait, &flip);
+       nv_wait_cb(nvxx_device(device), nv50_display_flip_wait, &flip);
 }
 
 int
@@ -550,6 +549,10 @@ nv50_display_flip_next(struct drm_crtc *crtc, struct drm_framebuffer *fb,
        u32 *push;
        int ret;
 
+       if (crtc->primary->fb->width != fb->width ||
+           crtc->primary->fb->height != fb->height)
+               return -EINVAL;
+
        swap_interval <<= 4;
        if (swap_interval == 0)
                swap_interval |= 0x100;
@@ -729,8 +732,11 @@ nv50_crtc_set_scale(struct nouveau_crtc *nv_crtc, bool update)
         * effectively handles NONE/FULL scaling
         */
        nv_connector = nouveau_crtc_connector_get(nv_crtc);
-       if (nv_connector && nv_connector->native_mode)
+       if (nv_connector && nv_connector->native_mode) {
                mode = nv_connector->scaling_mode;
+               if (nv_connector->scaling_full) /* non-EDID LVDS/eDP mode */
+                       mode = DRM_MODE_SCALE_FULLSCREEN;
+       }
 
        if (mode != DRM_MODE_SCALE_NONE)
                omode = nv_connector->native_mode;
@@ -917,29 +923,29 @@ static void
 nv50_crtc_cursor_show(struct nouveau_crtc *nv_crtc)
 {
        struct nv50_mast *mast = nv50_mast(nv_crtc->base.dev);
-       struct nv50_curs *curs = nv50_curs(&nv_crtc->base);
        u32 *push = evo_wait(mast, 16);
        if (push) {
                if (nv50_vers(mast) < G82_DISP_CORE_CHANNEL_DMA) {
                        evo_mthd(push, 0x0880 + (nv_crtc->index * 0x400), 2);
                        evo_data(push, 0x85000000);
-                       evo_data(push, curs->image->bo.offset >> 8);
+                       evo_data(push, nv_crtc->cursor.nvbo->bo.offset >> 8);
                } else
                if (nv50_vers(mast) < GF110_DISP_CORE_CHANNEL_DMA) {
                        evo_mthd(push, 0x0880 + (nv_crtc->index * 0x400), 2);
                        evo_data(push, 0x85000000);
-                       evo_data(push, curs->image->bo.offset >> 8);
+                       evo_data(push, nv_crtc->cursor.nvbo->bo.offset >> 8);
                        evo_mthd(push, 0x089c + (nv_crtc->index * 0x400), 1);
                        evo_data(push, mast->base.vram.handle);
                } else {
                        evo_mthd(push, 0x0480 + (nv_crtc->index * 0x300), 2);
                        evo_data(push, 0x85000000);
-                       evo_data(push, curs->image->bo.offset >> 8);
+                       evo_data(push, nv_crtc->cursor.nvbo->bo.offset >> 8);
                        evo_mthd(push, 0x048c + (nv_crtc->index * 0x300), 1);
                        evo_data(push, mast->base.vram.handle);
                }
                evo_kick(push, mast);
        }
+       nv_crtc->cursor.visible = true;
 }
 
 static void
@@ -965,15 +971,15 @@ nv50_crtc_cursor_hide(struct nouveau_crtc *nv_crtc)
                }
                evo_kick(push, mast);
        }
+       nv_crtc->cursor.visible = false;
 }
 
 static void
 nv50_crtc_cursor_show_hide(struct nouveau_crtc *nv_crtc, bool show, bool update)
 {
        struct nv50_mast *mast = nv50_mast(nv_crtc->base.dev);
-       struct nv50_curs *curs = nv50_curs(&nv_crtc->base);
 
-       if (show && curs->image)
+       if (show && nv_crtc->cursor.nvbo)
                nv50_crtc_cursor_show(nv_crtc);
        else
                nv50_crtc_cursor_hide(nv_crtc);
@@ -1273,7 +1279,6 @@ nv50_crtc_cursor_set(struct drm_crtc *crtc, struct drm_file *file_priv,
                     uint32_t handle, uint32_t width, uint32_t height)
 {
        struct nouveau_crtc *nv_crtc = nouveau_crtc(crtc);
-       struct nv50_curs *curs = nv50_curs(crtc);
        struct drm_device *dev = crtc->dev;
        struct drm_gem_object *gem = NULL;
        struct nouveau_bo *nvbo = NULL;
@@ -1292,9 +1297,9 @@ nv50_crtc_cursor_set(struct drm_crtc *crtc, struct drm_file *file_priv,
        }
 
        if (ret == 0) {
-               if (curs->image)
-                       nouveau_bo_unpin(curs->image);
-               nouveau_bo_ref(nvbo, &curs->image);
+               if (nv_crtc->cursor.nvbo)
+                       nouveau_bo_unpin(nv_crtc->cursor.nvbo);
+               nouveau_bo_ref(nvbo, &nv_crtc->cursor.nvbo);
        }
        drm_gem_object_unreference_unlocked(gem);
 
@@ -1305,10 +1310,14 @@ nv50_crtc_cursor_set(struct drm_crtc *crtc, struct drm_file *file_priv,
 static int
 nv50_crtc_cursor_move(struct drm_crtc *crtc, int x, int y)
 {
+       struct nouveau_crtc *nv_crtc = nouveau_crtc(crtc);
        struct nv50_curs *curs = nv50_curs(crtc);
        struct nv50_chan *chan = nv50_chan(curs);
        nvif_wr32(&chan->user, 0x0084, (y << 16) | (x & 0xffff));
        nvif_wr32(&chan->user, 0x0080, 0x00000000);
+
+       nv_crtc->cursor_saved_x = x;
+       nv_crtc->cursor_saved_y = y;
        return 0;
 }
 
@@ -1329,6 +1338,14 @@ nv50_crtc_gamma_set(struct drm_crtc *crtc, u16 *r, u16 *g, u16 *b,
        nv50_crtc_lut_load(crtc);
 }
 
+static void
+nv50_crtc_cursor_restore(struct nouveau_crtc *nv_crtc, int x, int y)
+{
+       nv50_crtc_cursor_move(&nv_crtc->base, x, y);
+
+       nv50_crtc_cursor_show_hide(nv_crtc, true, true);
+}
+
 static void
 nv50_crtc_destroy(struct drm_crtc *crtc)
 {
@@ -1354,9 +1371,9 @@ nv50_crtc_destroy(struct drm_crtc *crtc)
        nouveau_bo_ref(NULL, &head->image);
 
        /*XXX: ditto */
-       if (head->curs.image)
-               nouveau_bo_unpin(head->curs.image);
-       nouveau_bo_ref(NULL, &head->curs.image);
+       if (nv_crtc->cursor.nvbo)
+               nouveau_bo_unpin(nv_crtc->cursor.nvbo);
+       nouveau_bo_ref(NULL, &nv_crtc->cursor.nvbo);
 
        nouveau_bo_unmap(nv_crtc->lut.nvbo);
        if (nv_crtc->lut.nvbo)
@@ -1406,6 +1423,7 @@ nv50_crtc_create(struct drm_device *dev, int index)
        head->base.set_color_vibrance = nv50_crtc_set_color_vibrance;
        head->base.color_vibrance = 50;
        head->base.vibrant_hue = 0;
+       head->base.cursor.set_pos = nv50_crtc_cursor_restore;
        for (i = 0; i < 256; i++) {
                head->base.lut.r[i] = i << 8;
                head->base.lut.g[i] = i << 8;
@@ -1433,8 +1451,6 @@ nv50_crtc_create(struct drm_device *dev, int index)
        if (ret)
                goto out;
 
-       nv50_crtc_lut_load(crtc);
-
        /* allocate cursor resources */
        ret = nv50_curs_create(disp->disp, index, &head->curs);
        if (ret)
@@ -1465,6 +1481,41 @@ out:
        return ret;
 }
 
+/******************************************************************************
+ * Encoder helpers
+ *****************************************************************************/
+static bool
+nv50_encoder_mode_fixup(struct drm_encoder *encoder,
+                       const struct drm_display_mode *mode,
+                       struct drm_display_mode *adjusted_mode)
+{
+       struct nouveau_encoder *nv_encoder = nouveau_encoder(encoder);
+       struct nouveau_connector *nv_connector;
+
+       nv_connector = nouveau_encoder_connector_get(nv_encoder);
+       if (nv_connector && nv_connector->native_mode) {
+               nv_connector->scaling_full = false;
+               if (nv_connector->scaling_mode == DRM_MODE_SCALE_NONE) {
+                       switch (nv_connector->type) {
+                       case DCB_CONNECTOR_LVDS:
+                       case DCB_CONNECTOR_LVDS_SPWG:
+                       case DCB_CONNECTOR_eDP:
+                               /* force use of scaler for non-edid modes */
+                               if (adjusted_mode->type & DRM_MODE_TYPE_DRIVER)
+                                       return true;
+                               nv_connector->scaling_full = true;
+                               break;
+                       default:
+                               return true;
+                       }
+               }
+
+               drm_mode_copy(adjusted_mode, nv_connector->native_mode);
+       }
+
+       return true;
+}
+
 /******************************************************************************
  * DAC
  *****************************************************************************/
@@ -1492,26 +1543,6 @@ nv50_dac_dpms(struct drm_encoder *encoder, int mode)
        nvif_mthd(disp->disp, 0, &args, sizeof(args));
 }
 
-static bool
-nv50_dac_mode_fixup(struct drm_encoder *encoder,
-                   const struct drm_display_mode *mode,
-                   struct drm_display_mode *adjusted_mode)
-{
-       struct nouveau_encoder *nv_encoder = nouveau_encoder(encoder);
-       struct nouveau_connector *nv_connector;
-
-       nv_connector = nouveau_encoder_connector_get(nv_encoder);
-       if (nv_connector && nv_connector->native_mode) {
-               if (nv_connector->scaling_mode != DRM_MODE_SCALE_NONE) {
-                       int id = adjusted_mode->base.id;
-                       *adjusted_mode = *nv_connector->native_mode;
-                       adjusted_mode->base.id = id;
-               }
-       }
-
-       return true;
-}
-
 static void
 nv50_dac_commit(struct drm_encoder *encoder)
 {
@@ -1629,7 +1660,7 @@ nv50_dac_destroy(struct drm_encoder *encoder)
 
 static const struct drm_encoder_helper_funcs nv50_dac_hfunc = {
        .dpms = nv50_dac_dpms,
-       .mode_fixup = nv50_dac_mode_fixup,
+       .mode_fixup = nv50_encoder_mode_fixup,
        .prepare = nv50_dac_disconnect,
        .commit = nv50_dac_commit,
        .mode_set = nv50_dac_mode_set,
@@ -1646,7 +1677,7 @@ static int
 nv50_dac_create(struct drm_connector *connector, struct dcb_output *dcbe)
 {
        struct nouveau_drm *drm = nouveau_drm(connector->dev);
-       struct nouveau_i2c *i2c = nvkm_i2c(&drm->device);
+       struct nvkm_i2c *i2c = nvxx_i2c(&drm->device);
        struct nouveau_encoder *nv_encoder;
        struct drm_encoder *encoder;
        int type = DRM_MODE_ENCODER_DAC;
@@ -1834,26 +1865,6 @@ nv50_sor_dpms(struct drm_encoder *encoder, int mode)
        }
 }
 
-static bool
-nv50_sor_mode_fixup(struct drm_encoder *encoder,
-                   const struct drm_display_mode *mode,
-                   struct drm_display_mode *adjusted_mode)
-{
-       struct nouveau_encoder *nv_encoder = nouveau_encoder(encoder);
-       struct nouveau_connector *nv_connector;
-
-       nv_connector = nouveau_encoder_connector_get(nv_encoder);
-       if (nv_connector && nv_connector->native_mode) {
-               if (nv_connector->scaling_mode != DRM_MODE_SCALE_NONE) {
-                       int id = adjusted_mode->base.id;
-                       *adjusted_mode = *nv_connector->native_mode;
-                       adjusted_mode->base.id = id;
-               }
-       }
-
-       return true;
-}
-
 static void
 nv50_sor_ctrl(struct nouveau_encoder *nv_encoder, u32 mask, u32 data)
 {
@@ -2035,7 +2046,7 @@ nv50_sor_destroy(struct drm_encoder *encoder)
 
 static const struct drm_encoder_helper_funcs nv50_sor_hfunc = {
        .dpms = nv50_sor_dpms,
-       .mode_fixup = nv50_sor_mode_fixup,
+       .mode_fixup = nv50_encoder_mode_fixup,
        .prepare = nv50_sor_disconnect,
        .commit = nv50_sor_commit,
        .mode_set = nv50_sor_mode_set,
@@ -2051,7 +2062,7 @@ static int
 nv50_sor_create(struct drm_connector *connector, struct dcb_output *dcbe)
 {
        struct nouveau_drm *drm = nouveau_drm(connector->dev);
-       struct nouveau_i2c *i2c = nvkm_i2c(&drm->device);
+       struct nvkm_i2c *i2c = nvxx_i2c(&drm->device);
        struct nouveau_encoder *nv_encoder;
        struct drm_encoder *encoder;
        int type;
@@ -2112,18 +2123,8 @@ nv50_pior_mode_fixup(struct drm_encoder *encoder,
                     const struct drm_display_mode *mode,
                     struct drm_display_mode *adjusted_mode)
 {
-       struct nouveau_encoder *nv_encoder = nouveau_encoder(encoder);
-       struct nouveau_connector *nv_connector;
-
-       nv_connector = nouveau_encoder_connector_get(nv_encoder);
-       if (nv_connector && nv_connector->native_mode) {
-               if (nv_connector->scaling_mode != DRM_MODE_SCALE_NONE) {
-                       int id = adjusted_mode->base.id;
-                       *adjusted_mode = *nv_connector->native_mode;
-                       adjusted_mode->base.id = id;
-               }
-       }
-
+       if (!nv50_encoder_mode_fixup(encoder, mode, adjusted_mode))
+               return false;
        adjusted_mode->clock *= 2;
        return true;
 }
@@ -2232,8 +2233,8 @@ static int
 nv50_pior_create(struct drm_connector *connector, struct dcb_output *dcbe)
 {
        struct nouveau_drm *drm = nouveau_drm(connector->dev);
-       struct nouveau_i2c *i2c = nvkm_i2c(&drm->device);
-       struct nouveau_i2c_port *ddc = NULL;
+       struct nvkm_i2c *i2c = nvxx_i2c(&drm->device);
+       struct nvkm_i2c_port *ddc = NULL;
        struct nouveau_encoder *nv_encoder;
        struct drm_encoder *encoder;
        int type;
@@ -2427,6 +2428,8 @@ nv50_display_init(struct drm_device *dev)
 
        list_for_each_entry(crtc, &dev->mode_config.crtc_list, head) {
                struct nv50_sync *sync = nv50_sync(crtc);
+
+               nv50_crtc_lut_load(crtc);
                nouveau_bo_wr32(disp->sync, sync->addr / 4, sync->data);
        }
 
index cb5b88938d451c7f8d70be4a2816d11fe3f25d35..bf429cabbaa84cdfb0880702d7c1ee5b49a1c175 100644 (file)
@@ -213,7 +213,7 @@ nv84_fence_destroy(struct nouveau_drm *drm)
 int
 nv84_fence_create(struct nouveau_drm *drm)
 {
-       struct nouveau_fifo *pfifo = nvkm_fifo(&drm->device);
+       struct nvkm_fifo *pfifo = nvxx_fifo(&drm->device);
        struct nv84_fence_priv *priv;
        int ret;
 
diff --git a/drivers/gpu/drm/nouveau/nvif/Kbuild b/drivers/gpu/drm/nouveau/nvif/Kbuild
new file mode 100644 (file)
index 0000000..ff8ed3a
--- /dev/null
@@ -0,0 +1,4 @@
+nvif-y := nvif/object.o
+nvif-y += nvif/client.o
+nvif-y += nvif/device.o
+nvif-y += nvif/notify.o
diff --git a/drivers/gpu/drm/nouveau/nvif/class.h b/drivers/gpu/drm/nouveau/nvif/class.h
deleted file mode 100644 (file)
index 4e308ea..0000000
+++ /dev/null
@@ -1,570 +0,0 @@
-#ifndef __NVIF_CLASS_H__
-#define __NVIF_CLASS_H__
-
-/*******************************************************************************
- * class identifiers
- ******************************************************************************/
-
-/* the below match nvidia-assigned (either in hw, or sw) class numbers */
-#define NV_DEVICE                                                    0x00000080
-
-#define NV_DMA_FROM_MEMORY                                           0x00000002
-#define NV_DMA_TO_MEMORY                                             0x00000003
-#define NV_DMA_IN_MEMORY                                             0x0000003d
-
-#define NV04_DISP                                                    0x00000046
-
-#define NV03_CHANNEL_DMA                                             0x0000006b
-#define NV10_CHANNEL_DMA                                             0x0000006e
-#define NV17_CHANNEL_DMA                                             0x0000176e
-#define NV40_CHANNEL_DMA                                             0x0000406e
-#define NV50_CHANNEL_DMA                                             0x0000506e
-#define G82_CHANNEL_DMA                                              0x0000826e
-
-#define NV50_CHANNEL_GPFIFO                                          0x0000506f
-#define G82_CHANNEL_GPFIFO                                           0x0000826f
-#define FERMI_CHANNEL_GPFIFO                                         0x0000906f
-#define KEPLER_CHANNEL_GPFIFO_A                                      0x0000a06f
-
-#define NV50_DISP                                                    0x00005070
-#define G82_DISP                                                     0x00008270
-#define GT200_DISP                                                   0x00008370
-#define GT214_DISP                                                   0x00008570
-#define GT206_DISP                                                   0x00008870
-#define GF110_DISP                                                   0x00009070
-#define GK104_DISP                                                   0x00009170
-#define GK110_DISP                                                   0x00009270
-#define GM107_DISP                                                   0x00009470
-#define GM204_DISP                                                   0x00009570
-
-#define NV50_DISP_CURSOR                                             0x0000507a
-#define G82_DISP_CURSOR                                              0x0000827a
-#define GT214_DISP_CURSOR                                            0x0000857a
-#define GF110_DISP_CURSOR                                            0x0000907a
-#define GK104_DISP_CURSOR                                            0x0000917a
-
-#define NV50_DISP_OVERLAY                                            0x0000507b
-#define G82_DISP_OVERLAY                                             0x0000827b
-#define GT214_DISP_OVERLAY                                           0x0000857b
-#define GF110_DISP_OVERLAY                                           0x0000907b
-#define GK104_DISP_OVERLAY                                           0x0000917b
-
-#define NV50_DISP_BASE_CHANNEL_DMA                                   0x0000507c
-#define G82_DISP_BASE_CHANNEL_DMA                                    0x0000827c
-#define GT200_DISP_BASE_CHANNEL_DMA                                  0x0000837c
-#define GT214_DISP_BASE_CHANNEL_DMA                                  0x0000857c
-#define GF110_DISP_BASE_CHANNEL_DMA                                  0x0000907c
-#define GK104_DISP_BASE_CHANNEL_DMA                                  0x0000917c
-#define GK110_DISP_BASE_CHANNEL_DMA                                  0x0000927c
-
-#define NV50_DISP_CORE_CHANNEL_DMA                                   0x0000507d
-#define G82_DISP_CORE_CHANNEL_DMA                                    0x0000827d
-#define GT200_DISP_CORE_CHANNEL_DMA                                  0x0000837d
-#define GT214_DISP_CORE_CHANNEL_DMA                                  0x0000857d
-#define GT206_DISP_CORE_CHANNEL_DMA                                  0x0000887d
-#define GF110_DISP_CORE_CHANNEL_DMA                                  0x0000907d
-#define GK104_DISP_CORE_CHANNEL_DMA                                  0x0000917d
-#define GK110_DISP_CORE_CHANNEL_DMA                                  0x0000927d
-#define GM107_DISP_CORE_CHANNEL_DMA                                  0x0000947d
-#define GM204_DISP_CORE_CHANNEL_DMA                                  0x0000957d
-
-#define NV50_DISP_OVERLAY_CHANNEL_DMA                                0x0000507e
-#define G82_DISP_OVERLAY_CHANNEL_DMA                                 0x0000827e
-#define GT200_DISP_OVERLAY_CHANNEL_DMA                               0x0000837e
-#define GT214_DISP_OVERLAY_CHANNEL_DMA                               0x0000857e
-#define GF110_DISP_OVERLAY_CONTROL_DMA                               0x0000907e
-#define GK104_DISP_OVERLAY_CONTROL_DMA                               0x0000917e
-
-#define FERMI_A                                                      0x00009097
-#define FERMI_B                                                      0x00009197
-#define FERMI_C                                                      0x00009297
-
-#define KEPLER_A                                                     0x0000a097
-#define KEPLER_B                                                     0x0000a197
-#define KEPLER_C                                                     0x0000a297
-
-#define MAXWELL_A                                                    0x0000b097
-
-#define FERMI_COMPUTE_A                                              0x000090c0
-#define FERMI_COMPUTE_B                                              0x000091c0
-
-#define KEPLER_COMPUTE_A                                             0x0000a0c0
-#define KEPLER_COMPUTE_B                                             0x0000a1c0
-
-#define MAXWELL_COMPUTE_A                                            0x0000b0c0
-
-
-/*******************************************************************************
- * client
- ******************************************************************************/
-
-#define NV_CLIENT_DEVLIST                                                  0x00
-
-struct nv_client_devlist_v0 {
-       __u8  version;
-       __u8  count;
-       __u8  pad02[6];
-       __u64 device[];
-};
-
-
-/*******************************************************************************
- * device
- ******************************************************************************/
-
-struct nv_device_v0 {
-       __u8  version;
-       __u8  pad01[7];
-       __u64 device;   /* device identifier, ~0 for client default */
-#define NV_DEVICE_V0_DISABLE_IDENTIFY                     0x0000000000000001ULL
-#define NV_DEVICE_V0_DISABLE_MMIO                         0x0000000000000002ULL
-#define NV_DEVICE_V0_DISABLE_VBIOS                        0x0000000000000004ULL
-#define NV_DEVICE_V0_DISABLE_CORE                         0x0000000000000008ULL
-#define NV_DEVICE_V0_DISABLE_DISP                         0x0000000000010000ULL
-#define NV_DEVICE_V0_DISABLE_FIFO                         0x0000000000020000ULL
-#define NV_DEVICE_V0_DISABLE_GRAPH                        0x0000000100000000ULL
-#define NV_DEVICE_V0_DISABLE_MPEG                         0x0000000200000000ULL
-#define NV_DEVICE_V0_DISABLE_ME                           0x0000000400000000ULL
-#define NV_DEVICE_V0_DISABLE_VP                           0x0000000800000000ULL
-#define NV_DEVICE_V0_DISABLE_CRYPT                        0x0000001000000000ULL
-#define NV_DEVICE_V0_DISABLE_BSP                          0x0000002000000000ULL
-#define NV_DEVICE_V0_DISABLE_PPP                          0x0000004000000000ULL
-#define NV_DEVICE_V0_DISABLE_COPY0                        0x0000008000000000ULL
-#define NV_DEVICE_V0_DISABLE_COPY1                        0x0000010000000000ULL
-#define NV_DEVICE_V0_DISABLE_VIC                          0x0000020000000000ULL
-#define NV_DEVICE_V0_DISABLE_VENC                         0x0000040000000000ULL
-#define NV_DEVICE_V0_DISABLE_COPY2                        0x0000080000000000ULL
-       __u64 disable;  /* disable particular subsystems */
-       __u64 debug0;   /* as above, but *internal* ids, and *NOT* ABI */
-};
-
-#define NV_DEVICE_V0_INFO                                                  0x00
-
-struct nv_device_info_v0 {
-       __u8  version;
-#define NV_DEVICE_INFO_V0_IGP                                              0x00
-#define NV_DEVICE_INFO_V0_PCI                                              0x01
-#define NV_DEVICE_INFO_V0_AGP                                              0x02
-#define NV_DEVICE_INFO_V0_PCIE                                             0x03
-#define NV_DEVICE_INFO_V0_SOC                                              0x04
-       __u8  platform;
-       __u16 chipset;  /* from NV_PMC_BOOT_0 */
-       __u8  revision; /* from NV_PMC_BOOT_0 */
-#define NV_DEVICE_INFO_V0_TNT                                              0x01
-#define NV_DEVICE_INFO_V0_CELSIUS                                          0x02
-#define NV_DEVICE_INFO_V0_KELVIN                                           0x03
-#define NV_DEVICE_INFO_V0_RANKINE                                          0x04
-#define NV_DEVICE_INFO_V0_CURIE                                            0x05
-#define NV_DEVICE_INFO_V0_TESLA                                            0x06
-#define NV_DEVICE_INFO_V0_FERMI                                            0x07
-#define NV_DEVICE_INFO_V0_KEPLER                                           0x08
-#define NV_DEVICE_INFO_V0_MAXWELL                                          0x09
-       __u8  family;
-       __u8  pad06[2];
-       __u64 ram_size;
-       __u64 ram_user;
-};
-
-
-/*******************************************************************************
- * context dma
- ******************************************************************************/
-
-struct nv_dma_v0 {
-       __u8  version;
-#define NV_DMA_V0_TARGET_VM                                                0x00
-#define NV_DMA_V0_TARGET_VRAM                                              0x01
-#define NV_DMA_V0_TARGET_PCI                                               0x02
-#define NV_DMA_V0_TARGET_PCI_US                                            0x03
-#define NV_DMA_V0_TARGET_AGP                                               0x04
-       __u8  target;
-#define NV_DMA_V0_ACCESS_VM                                                0x00
-#define NV_DMA_V0_ACCESS_RD                                                0x01
-#define NV_DMA_V0_ACCESS_WR                                                0x02
-#define NV_DMA_V0_ACCESS_RDWR                 (NV_DMA_V0_ACCESS_RD | NV_DMA_V0_ACCESS_WR)
-       __u8  access;
-       __u8  pad03[5];
-       __u64 start;
-       __u64 limit;
-       /* ... chipset-specific class data */
-};
-
-struct nv50_dma_v0 {
-       __u8  version;
-#define NV50_DMA_V0_PRIV_VM                                                0x00
-#define NV50_DMA_V0_PRIV_US                                                0x01
-#define NV50_DMA_V0_PRIV__S                                                0x02
-       __u8  priv;
-#define NV50_DMA_V0_PART_VM                                                0x00
-#define NV50_DMA_V0_PART_256                                               0x01
-#define NV50_DMA_V0_PART_1KB                                               0x02
-       __u8  part;
-#define NV50_DMA_V0_COMP_NONE                                              0x00
-#define NV50_DMA_V0_COMP_1                                                 0x01
-#define NV50_DMA_V0_COMP_2                                                 0x02
-#define NV50_DMA_V0_COMP_VM                                                0x03
-       __u8  comp;
-#define NV50_DMA_V0_KIND_PITCH                                             0x00
-#define NV50_DMA_V0_KIND_VM                                                0x7f
-       __u8  kind;
-       __u8  pad05[3];
-};
-
-struct gf100_dma_v0 {
-       __u8  version;
-#define GF100_DMA_V0_PRIV_VM                                               0x00
-#define GF100_DMA_V0_PRIV_US                                               0x01
-#define GF100_DMA_V0_PRIV__S                                               0x02
-       __u8  priv;
-#define GF100_DMA_V0_KIND_PITCH                                            0x00
-#define GF100_DMA_V0_KIND_VM                                               0xff
-       __u8  kind;
-       __u8  pad03[5];
-};
-
-struct gf110_dma_v0 {
-       __u8  version;
-#define GF110_DMA_V0_PAGE_LP                                               0x00
-#define GF110_DMA_V0_PAGE_SP                                               0x01
-       __u8  page;
-#define GF110_DMA_V0_KIND_PITCH                                            0x00
-#define GF110_DMA_V0_KIND_VM                                               0xff
-       __u8  kind;
-       __u8  pad03[5];
-};
-
-
-/*******************************************************************************
- * perfmon
- ******************************************************************************/
-
-struct nvif_perfctr_v0 {
-       __u8  version;
-       __u8  pad01[1];
-       __u16 logic_op;
-       __u8  pad04[4];
-       char  name[4][64];
-};
-
-#define NVIF_PERFCTR_V0_QUERY                                              0x00
-#define NVIF_PERFCTR_V0_SAMPLE                                             0x01
-#define NVIF_PERFCTR_V0_READ                                               0x02
-
-struct nvif_perfctr_query_v0 {
-       __u8  version;
-       __u8  pad01[3];
-       __u32 iter;
-       char  name[64];
-};
-
-struct nvif_perfctr_sample {
-};
-
-struct nvif_perfctr_read_v0 {
-       __u8  version;
-       __u8  pad01[7];
-       __u32 ctr;
-       __u32 clk;
-};
-
-
-/*******************************************************************************
- * device control
- ******************************************************************************/
-
-#define NVIF_CONTROL_PSTATE_INFO                                           0x00
-#define NVIF_CONTROL_PSTATE_ATTR                                           0x01
-#define NVIF_CONTROL_PSTATE_USER                                           0x02
-
-struct nvif_control_pstate_info_v0 {
-       __u8  version;
-       __u8  count; /* out: number of power states */
-#define NVIF_CONTROL_PSTATE_INFO_V0_USTATE_DISABLE                         (-1)
-#define NVIF_CONTROL_PSTATE_INFO_V0_USTATE_PERFMON                         (-2)
-       __s8  ustate_ac; /* out: target pstate index */
-       __s8  ustate_dc; /* out: target pstate index */
-       __s8  pwrsrc; /* out: current power source */
-#define NVIF_CONTROL_PSTATE_INFO_V0_PSTATE_UNKNOWN                         (-1)
-#define NVIF_CONTROL_PSTATE_INFO_V0_PSTATE_PERFMON                         (-2)
-       __s8  pstate; /* out: current pstate index */
-       __u8  pad06[2];
-};
-
-struct nvif_control_pstate_attr_v0 {
-       __u8  version;
-#define NVIF_CONTROL_PSTATE_ATTR_V0_STATE_CURRENT                          (-1)
-       __s8  state; /*  in: index of pstate to query
-                     * out: pstate identifier
-                     */
-       __u8  index; /*  in: index of attribute to query
-                     * out: index of next attribute, or 0 if no more
-                     */
-       __u8  pad03[5];
-       __u32 min;
-       __u32 max;
-       char  name[32];
-       char  unit[16];
-};
-
-struct nvif_control_pstate_user_v0 {
-       __u8  version;
-#define NVIF_CONTROL_PSTATE_USER_V0_STATE_UNKNOWN                          (-1)
-#define NVIF_CONTROL_PSTATE_USER_V0_STATE_PERFMON                          (-2)
-       __s8  ustate; /*  in: pstate identifier */
-       __s8  pwrsrc; /*  in: target power source */
-       __u8  pad03[5];
-};
-
-
-/*******************************************************************************
- * DMA FIFO channels
- ******************************************************************************/
-
-struct nv03_channel_dma_v0 {
-       __u8  version;
-       __u8  chid;
-       __u8  pad02[2];
-       __u32 pushbuf;
-       __u64 offset;
-};
-
-#define G82_CHANNEL_DMA_V0_NTFY_UEVENT                                     0x00
-
-/*******************************************************************************
- * GPFIFO channels
- ******************************************************************************/
-
-struct nv50_channel_gpfifo_v0 {
-       __u8  version;
-       __u8  chid;
-       __u8  pad01[6];
-       __u32 pushbuf;
-       __u32 ilength;
-       __u64 ioffset;
-};
-
-struct kepler_channel_gpfifo_a_v0 {
-       __u8  version;
-#define KEPLER_CHANNEL_GPFIFO_A_V0_ENGINE_GR                               0x01
-#define KEPLER_CHANNEL_GPFIFO_A_V0_ENGINE_VP                               0x02
-#define KEPLER_CHANNEL_GPFIFO_A_V0_ENGINE_PPP                              0x04
-#define KEPLER_CHANNEL_GPFIFO_A_V0_ENGINE_BSP                              0x08
-#define KEPLER_CHANNEL_GPFIFO_A_V0_ENGINE_CE0                              0x10
-#define KEPLER_CHANNEL_GPFIFO_A_V0_ENGINE_CE1                              0x20
-#define KEPLER_CHANNEL_GPFIFO_A_V0_ENGINE_ENC                              0x40
-       __u8  engine;
-       __u16 chid;
-       __u8  pad04[4];
-       __u32 pushbuf;
-       __u32 ilength;
-       __u64 ioffset;
-};
-
-/*******************************************************************************
- * legacy display
- ******************************************************************************/
-
-#define NV04_DISP_NTFY_VBLANK                                              0x00
-#define NV04_DISP_NTFY_CONN                                                0x01
-
-struct nv04_disp_mthd_v0 {
-       __u8  version;
-#define NV04_DISP_SCANOUTPOS                                               0x00
-       __u8  method;
-       __u8  head;
-       __u8  pad03[5];
-};
-
-struct nv04_disp_scanoutpos_v0 {
-       __u8  version;
-       __u8  pad01[7];
-       __s64 time[2];
-       __u16 vblanks;
-       __u16 vblanke;
-       __u16 vtotal;
-       __u16 vline;
-       __u16 hblanks;
-       __u16 hblanke;
-       __u16 htotal;
-       __u16 hline;
-};
-
-/*******************************************************************************
- * display
- ******************************************************************************/
-
-#define NV50_DISP_MTHD                                                     0x00
-
-struct nv50_disp_mthd_v0 {
-       __u8  version;
-#define NV50_DISP_SCANOUTPOS                                               0x00
-       __u8  method;
-       __u8  head;
-       __u8  pad03[5];
-};
-
-struct nv50_disp_mthd_v1 {
-       __u8  version;
-#define NV50_DISP_MTHD_V1_DAC_PWR                                          0x10
-#define NV50_DISP_MTHD_V1_DAC_LOAD                                         0x11
-#define NV50_DISP_MTHD_V1_SOR_PWR                                          0x20
-#define NV50_DISP_MTHD_V1_SOR_HDA_ELD                                      0x21
-#define NV50_DISP_MTHD_V1_SOR_HDMI_PWR                                     0x22
-#define NV50_DISP_MTHD_V1_SOR_LVDS_SCRIPT                                  0x23
-#define NV50_DISP_MTHD_V1_SOR_DP_PWR                                       0x24
-#define NV50_DISP_MTHD_V1_PIOR_PWR                                         0x30
-       __u8  method;
-       __u16 hasht;
-       __u16 hashm;
-       __u8  pad06[2];
-};
-
-struct nv50_disp_dac_pwr_v0 {
-       __u8  version;
-       __u8  state;
-       __u8  data;
-       __u8  vsync;
-       __u8  hsync;
-       __u8  pad05[3];
-};
-
-struct nv50_disp_dac_load_v0 {
-       __u8  version;
-       __u8  load;
-       __u8  pad02[2];
-       __u32 data;
-};
-
-struct nv50_disp_sor_pwr_v0 {
-       __u8  version;
-       __u8  state;
-       __u8  pad02[6];
-};
-
-struct nv50_disp_sor_hda_eld_v0 {
-       __u8  version;
-       __u8  pad01[7];
-       __u8  data[];
-};
-
-struct nv50_disp_sor_hdmi_pwr_v0 {
-       __u8  version;
-       __u8  state;
-       __u8  max_ac_packet;
-       __u8  rekey;
-       __u8  pad04[4];
-};
-
-struct nv50_disp_sor_lvds_script_v0 {
-       __u8  version;
-       __u8  pad01[1];
-       __u16 script;
-       __u8  pad04[4];
-};
-
-struct nv50_disp_sor_dp_pwr_v0 {
-       __u8  version;
-       __u8  state;
-       __u8  pad02[6];
-};
-
-struct nv50_disp_pior_pwr_v0 {
-       __u8  version;
-       __u8  state;
-       __u8  type;
-       __u8  pad03[5];
-};
-
-/* core */
-struct nv50_disp_core_channel_dma_v0 {
-       __u8  version;
-       __u8  pad01[3];
-       __u32 pushbuf;
-};
-
-#define NV50_DISP_CORE_CHANNEL_DMA_V0_NTFY_UEVENT                          0x00
-
-/* cursor immediate */
-struct nv50_disp_cursor_v0 {
-       __u8  version;
-       __u8  head;
-       __u8  pad02[6];
-};
-
-#define NV50_DISP_CURSOR_V0_NTFY_UEVENT                                    0x00
-
-/* base */
-struct nv50_disp_base_channel_dma_v0 {
-       __u8  version;
-       __u8  pad01[2];
-       __u8  head;
-       __u32 pushbuf;
-};
-
-#define NV50_DISP_BASE_CHANNEL_DMA_V0_NTFY_UEVENT                          0x00
-
-/* overlay */
-struct nv50_disp_overlay_channel_dma_v0 {
-       __u8  version;
-       __u8  pad01[2];
-       __u8  head;
-       __u32 pushbuf;
-};
-
-#define NV50_DISP_OVERLAY_CHANNEL_DMA_V0_NTFY_UEVENT                       0x00
-
-/* overlay immediate */
-struct nv50_disp_overlay_v0 {
-       __u8  version;
-       __u8  head;
-       __u8  pad02[6];
-};
-
-#define NV50_DISP_OVERLAY_V0_NTFY_UEVENT                                   0x00
-
-/*******************************************************************************
- * fermi
- ******************************************************************************/
-
-#define FERMI_A_ZBC_COLOR                                                  0x00
-#define FERMI_A_ZBC_DEPTH                                                  0x01
-
-struct fermi_a_zbc_color_v0 {
-       __u8  version;
-#define FERMI_A_ZBC_COLOR_V0_FMT_ZERO                                      0x01
-#define FERMI_A_ZBC_COLOR_V0_FMT_UNORM_ONE                                 0x02
-#define FERMI_A_ZBC_COLOR_V0_FMT_RF32_GF32_BF32_AF32                       0x04
-#define FERMI_A_ZBC_COLOR_V0_FMT_R16_G16_B16_A16                           0x08
-#define FERMI_A_ZBC_COLOR_V0_FMT_RN16_GN16_BN16_AN16                       0x0c
-#define FERMI_A_ZBC_COLOR_V0_FMT_RS16_GS16_BS16_AS16                       0x10
-#define FERMI_A_ZBC_COLOR_V0_FMT_RU16_GU16_BU16_AU16                       0x14
-#define FERMI_A_ZBC_COLOR_V0_FMT_RF16_GF16_BF16_AF16                       0x16
-#define FERMI_A_ZBC_COLOR_V0_FMT_A8R8G8B8                                  0x18
-#define FERMI_A_ZBC_COLOR_V0_FMT_A8RL8GL8BL8                               0x1c
-#define FERMI_A_ZBC_COLOR_V0_FMT_A2B10G10R10                               0x20
-#define FERMI_A_ZBC_COLOR_V0_FMT_AU2BU10GU10RU10                           0x24
-#define FERMI_A_ZBC_COLOR_V0_FMT_A8B8G8R8                                  0x28
-#define FERMI_A_ZBC_COLOR_V0_FMT_A8BL8GL8RL8                               0x2c
-#define FERMI_A_ZBC_COLOR_V0_FMT_AN8BN8GN8RN8                              0x30
-#define FERMI_A_ZBC_COLOR_V0_FMT_AS8BS8GS8RS8                              0x34
-#define FERMI_A_ZBC_COLOR_V0_FMT_AU8BU8GU8RU8                              0x38
-#define FERMI_A_ZBC_COLOR_V0_FMT_A2R10G10B10                               0x3c
-#define FERMI_A_ZBC_COLOR_V0_FMT_BF10GF11RF11                              0x40
-       __u8  format;
-       __u8  index;
-       __u8  pad03[5];
-       __u32 ds[4];
-       __u32 l2[4];
-};
-
-struct fermi_a_zbc_depth_v0 {
-       __u8  version;
-#define FERMI_A_ZBC_DEPTH_V0_FMT_FP32                                      0x01
-       __u8  format;
-       __u8  index;
-       __u8  pad03[5];
-       __u32 ds;
-       __u32 l2;
-};
-
-#endif
index 3f7ac5bc8e03990426c70a2e3c17622fe9edfb53..80b96844221e1c19ce6247b0f08bf723d4308298 100644 (file)
@@ -22,9 +22,9 @@
  * Authors: Ben Skeggs <bskeggs@redhat.com>
  */
 
-#include "client.h"
-#include "driver.h"
-#include "ioctl.h"
+#include <nvif/client.h>
+#include <nvif/driver.h>
+#include <nvif/ioctl.h>
 
 int
 nvif_client_ioctl(struct nvif_client *client, void *data, u32 size)
diff --git a/drivers/gpu/drm/nouveau/nvif/client.h b/drivers/gpu/drm/nouveau/nvif/client.h
deleted file mode 100644 (file)
index 28352f0..0000000
+++ /dev/null
@@ -1,39 +0,0 @@
-#ifndef __NVIF_CLIENT_H__
-#define __NVIF_CLIENT_H__
-
-#include "object.h"
-
-struct nvif_client {
-       struct nvif_object base;
-       struct nvif_object *object; /*XXX: hack for nvif_object() */
-       const struct nvif_driver *driver;
-       bool super;
-};
-
-static inline struct nvif_client *
-nvif_client(struct nvif_object *object)
-{
-       while (object && object->parent != object)
-               object = object->parent;
-       return (void *)object;
-}
-
-int  nvif_client_init(void (*dtor)(struct nvif_client *), const char *,
-                     const char *, u64, const char *, const char *,
-                     struct nvif_client *);
-void nvif_client_fini(struct nvif_client *);
-int  nvif_client_new(const char *, const char *, u64, const char *,
-                    const char *, struct nvif_client **);
-void nvif_client_ref(struct nvif_client *, struct nvif_client **);
-int  nvif_client_ioctl(struct nvif_client *, void *, u32);
-int  nvif_client_suspend(struct nvif_client *);
-int  nvif_client_resume(struct nvif_client *);
-
-/*XXX*/
-#include <core/client.h>
-#define nvkm_client(a) ({ \
-       struct nvif_client *_client = nvif_client(nvif_object(a)); \
-       nouveau_client(_client->base.priv); \
-})
-
-#endif
index f477579725e3e482634a024d60ebc14736c2041a..6f72244c52cd89294c241d2e8d2ff5aaa764970d 100644 (file)
@@ -22,7 +22,7 @@
  * Authors: Ben Skeggs <bskeggs@redhat.com>
  */
 
-#include "device.h"
+#include <nvif/device.h>
 
 void
 nvif_device_fini(struct nvif_device *device)
diff --git a/drivers/gpu/drm/nouveau/nvif/device.h b/drivers/gpu/drm/nouveau/nvif/device.h
deleted file mode 100644 (file)
index 43180f9..0000000
+++ /dev/null
@@ -1,62 +0,0 @@
-#ifndef __NVIF_DEVICE_H__
-#define __NVIF_DEVICE_H__
-
-#include "object.h"
-#include "class.h"
-
-struct nvif_device {
-       struct nvif_object base;
-       struct nvif_object *object; /*XXX: hack for nvif_object() */
-       struct nv_device_info_v0 info;
-};
-
-static inline struct nvif_device *
-nvif_device(struct nvif_object *object)
-{
-       while (object && object->oclass != 0x0080 /*XXX: NV_DEVICE_CLASS*/ )
-               object = object->parent;
-       return (void *)object;
-}
-
-int  nvif_device_init(struct nvif_object *, void (*dtor)(struct nvif_device *),
-                     u32 handle, u32 oclass, void *, u32,
-                     struct nvif_device *);
-void nvif_device_fini(struct nvif_device *);
-int  nvif_device_new(struct nvif_object *, u32 handle, u32 oclass,
-                    void *, u32, struct nvif_device **);
-void nvif_device_ref(struct nvif_device *, struct nvif_device **);
-
-/*XXX*/
-#include <subdev/bios.h>
-#include <subdev/fb.h>
-#include <subdev/vm.h>
-#include <subdev/bar.h>
-#include <subdev/gpio.h>
-#include <subdev/clock.h>
-#include <subdev/i2c.h>
-#include <subdev/timer.h>
-#include <subdev/therm.h>
-
-#define nvkm_device(a) nv_device(nvkm_object((a)))
-#define nvkm_bios(a) nouveau_bios(nvkm_device(a))
-#define nvkm_fb(a) nouveau_fb(nvkm_device(a))
-#define nvkm_vmmgr(a) nouveau_vmmgr(nvkm_device(a))
-#define nvkm_bar(a) nouveau_bar(nvkm_device(a))
-#define nvkm_gpio(a) nouveau_gpio(nvkm_device(a))
-#define nvkm_clock(a) nouveau_clock(nvkm_device(a))
-#define nvkm_i2c(a) nouveau_i2c(nvkm_device(a))
-#define nvkm_timer(a) nouveau_timer(nvkm_device(a))
-#define nvkm_wait(a,b,c,d) nv_wait(nvkm_timer(a), (b), (c), (d))
-#define nvkm_wait_cb(a,b,c) nv_wait_cb(nvkm_timer(a), (b), (c))
-#define nvkm_therm(a) nouveau_therm(nvkm_device(a))
-
-#include <engine/device.h>
-#include <engine/fifo.h>
-#include <engine/graph.h>
-#include <engine/software.h>
-
-#define nvkm_fifo(a) nouveau_fifo(nvkm_device(a))
-#define nvkm_fifo_chan(a) ((struct nouveau_fifo_chan *)nvkm_object(a))
-#define nvkm_gr(a) ((struct nouveau_graph *)nouveau_engine(nvkm_object(a), NVDEV_ENGINE_GR))
-
-#endif
diff --git a/drivers/gpu/drm/nouveau/nvif/driver.h b/drivers/gpu/drm/nouveau/nvif/driver.h
deleted file mode 100644 (file)
index 8bd39e6..0000000
+++ /dev/null
@@ -1,22 +0,0 @@
-#ifndef __NVIF_DRIVER_H__
-#define __NVIF_DRIVER_H__
-
-struct nvif_driver {
-       const char *name;
-       int (*init)(const char *name, u64 device, const char *cfg,
-                   const char *dbg, void **priv);
-       void (*fini)(void *priv);
-       int (*suspend)(void *priv);
-       int (*resume)(void *priv);
-       int (*ioctl)(void *priv, bool super, void *data, u32 size, void **hack);
-       void __iomem *(*map)(void *priv, u64 handle, u32 size);
-       void (*unmap)(void *priv, void __iomem *ptr, u32 size);
-       bool keep;
-};
-
-extern const struct nvif_driver nvif_driver_nvkm;
-extern const struct nvif_driver nvif_driver_drm;
-extern const struct nvif_driver nvif_driver_lib;
-extern const struct nvif_driver nvif_driver_null;
-
-#endif
diff --git a/drivers/gpu/drm/nouveau/nvif/event.h b/drivers/gpu/drm/nouveau/nvif/event.h
deleted file mode 100644 (file)
index 2176449..0000000
+++ /dev/null
@@ -1,62 +0,0 @@
-#ifndef __NVIF_EVENT_H__
-#define __NVIF_EVENT_H__
-
-struct nvif_notify_req_v0 {
-       __u8  version;
-       __u8  reply;
-       __u8  pad02[5];
-#define NVIF_NOTIFY_V0_ROUTE_NVIF                                          0x00
-       __u8  route;
-       __u64 token;    /* must be unique */
-       __u8  data[];   /* request data (below) */
-};
-
-struct nvif_notify_rep_v0 {
-       __u8  version;
-       __u8  pad01[6];
-       __u8  route;
-       __u64 token;
-       __u8  data[];   /* reply data (below) */
-};
-
-struct nvif_notify_head_req_v0 {
-       /* nvif_notify_req ... */
-       __u8  version;
-       __u8  head;
-       __u8  pad02[6];
-};
-
-struct nvif_notify_head_rep_v0 {
-       /* nvif_notify_rep ... */
-       __u8  version;
-       __u8  pad01[7];
-};
-
-struct nvif_notify_conn_req_v0 {
-       /* nvif_notify_req ... */
-       __u8  version;
-#define NVIF_NOTIFY_CONN_V0_PLUG                                           0x01
-#define NVIF_NOTIFY_CONN_V0_UNPLUG                                         0x02
-#define NVIF_NOTIFY_CONN_V0_IRQ                                            0x04
-#define NVIF_NOTIFY_CONN_V0_ANY                                            0x07
-       __u8  mask;
-       __u8  conn;
-       __u8  pad03[5];
-};
-
-struct nvif_notify_conn_rep_v0 {
-       /* nvif_notify_rep ... */
-       __u8  version;
-       __u8  mask;
-       __u8  pad02[6];
-};
-
-struct nvif_notify_uevent_req {
-       /* nvif_notify_req ... */
-};
-
-struct nvif_notify_uevent_rep {
-       /* nvif_notify_rep ... */
-};
-
-#endif
diff --git a/drivers/gpu/drm/nouveau/nvif/ioctl.h b/drivers/gpu/drm/nouveau/nvif/ioctl.h
deleted file mode 100644 (file)
index 4cd8e32..0000000
+++ /dev/null
@@ -1,128 +0,0 @@
-#ifndef __NVIF_IOCTL_H__
-#define __NVIF_IOCTL_H__
-
-struct nvif_ioctl_v0 {
-       __u8  version;
-#define NVIF_IOCTL_V0_OWNER_NVIF                                           0x00
-#define NVIF_IOCTL_V0_OWNER_ANY                                            0xff
-       __u8  owner;
-#define NVIF_IOCTL_V0_NOP                                                  0x00
-#define NVIF_IOCTL_V0_SCLASS                                               0x01
-#define NVIF_IOCTL_V0_NEW                                                  0x02
-#define NVIF_IOCTL_V0_DEL                                                  0x03
-#define NVIF_IOCTL_V0_MTHD                                                 0x04
-#define NVIF_IOCTL_V0_RD                                                   0x05
-#define NVIF_IOCTL_V0_WR                                                   0x06
-#define NVIF_IOCTL_V0_MAP                                                  0x07
-#define NVIF_IOCTL_V0_UNMAP                                                0x08
-#define NVIF_IOCTL_V0_NTFY_NEW                                             0x09
-#define NVIF_IOCTL_V0_NTFY_DEL                                             0x0a
-#define NVIF_IOCTL_V0_NTFY_GET                                             0x0b
-#define NVIF_IOCTL_V0_NTFY_PUT                                             0x0c
-       __u8  type;
-       __u8  path_nr;
-#define NVIF_IOCTL_V0_ROUTE_NVIF                                           0x00
-#define NVIF_IOCTL_V0_ROUTE_HIDDEN                                         0xff
-       __u8  pad04[3];
-       __u8  route;
-       __u64 token;
-       __u32 path[8];          /* in reverse */
-       __u8  data[];           /* ioctl data (below) */
-};
-
-struct nvif_ioctl_nop {
-};
-
-struct nvif_ioctl_sclass_v0 {
-       /* nvif_ioctl ... */
-       __u8  version;
-       __u8  count;
-       __u8  pad02[6];
-       __u32 oclass[];
-};
-
-struct nvif_ioctl_new_v0 {
-       /* nvif_ioctl ... */
-       __u8  version;
-       __u8  pad01[6];
-       __u8  route;
-       __u64 token;
-       __u32 handle;
-/* these class numbers are made up by us, and not nvidia-assigned */
-#define NVIF_IOCTL_NEW_V0_PERFCTR                                    0x0000ffff
-#define NVIF_IOCTL_NEW_V0_CONTROL                                    0x0000fffe
-       __u32 oclass;
-       __u8  data[];           /* class data (class.h) */
-};
-
-struct nvif_ioctl_del {
-};
-
-struct nvif_ioctl_rd_v0 {
-       /* nvif_ioctl ... */
-       __u8  version;
-       __u8  size;
-       __u8  pad02[2];
-       __u32 data;
-       __u64 addr;
-};
-
-struct nvif_ioctl_wr_v0 {
-       /* nvif_ioctl ... */
-       __u8  version;
-       __u8  size;
-       __u8  pad02[2];
-       __u32 data;
-       __u64 addr;
-};
-
-struct nvif_ioctl_map_v0 {
-       /* nvif_ioctl ... */
-       __u8  version;
-       __u8  pad01[3];
-       __u32 length;
-       __u64 handle;
-};
-
-struct nvif_ioctl_unmap {
-};
-
-struct nvif_ioctl_ntfy_new_v0 {
-       /* nvif_ioctl ... */
-       __u8  version;
-       __u8  event;
-       __u8  index;
-       __u8  pad03[5];
-       __u8  data[];           /* event request data (event.h) */
-};
-
-struct nvif_ioctl_ntfy_del_v0 {
-       /* nvif_ioctl ... */
-       __u8  version;
-       __u8  index;
-       __u8  pad02[6];
-};
-
-struct nvif_ioctl_ntfy_get_v0 {
-       /* nvif_ioctl ... */
-       __u8  version;
-       __u8  index;
-       __u8  pad02[6];
-};
-
-struct nvif_ioctl_ntfy_put_v0 {
-       /* nvif_ioctl ... */
-       __u8  version;
-       __u8  index;
-       __u8  pad02[6];
-};
-
-struct nvif_ioctl_mthd_v0 {
-       /* nvif_ioctl ... */
-       __u8  version;
-       __u8  method;
-       __u8  pad02[6];
-       __u8  data[];           /* method data (class.h) */
-};
-
-#endif
diff --git a/drivers/gpu/drm/nouveau/nvif/list.h b/drivers/gpu/drm/nouveau/nvif/list.h
deleted file mode 100644 (file)
index 8af5d14..0000000
+++ /dev/null
@@ -1,353 +0,0 @@
-/*
- * Copyright © 2010 Intel Corporation
- * Copyright © 2010 Francisco Jerez <currojerez@riseup.net>
- *
- * 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.
- *
- */
-
-/* Modified by Ben Skeggs <bskeggs@redhat.com> to match kernel list APIs */
-
-#ifndef _XORG_LIST_H_
-#define _XORG_LIST_H_
-
-/**
- * @file Classic doubly-link circular list implementation.
- * For real usage examples of the linked list, see the file test/list.c
- *
- * Example:
- * We need to keep a list of struct foo in the parent struct bar, i.e. what
- * we want is something like this.
- *
- *     struct bar {
- *          ...
- *          struct foo *list_of_foos; -----> struct foo {}, struct foo {}, struct foo{}
- *          ...
- *     }
- *
- * We need one list head in bar and a list element in all list_of_foos (both are of
- * data type 'struct list_head').
- *
- *     struct bar {
- *          ...
- *          struct list_head list_of_foos;
- *          ...
- *     }
- *
- *     struct foo {
- *          ...
- *          struct list_head entry;
- *          ...
- *     }
- *
- * Now we initialize the list head:
- *
- *     struct bar bar;
- *     ...
- *     INIT_LIST_HEAD(&bar.list_of_foos);
- *
- * Then we create the first element and add it to this list:
- *
- *     struct foo *foo = malloc(...);
- *     ....
- *     list_add(&foo->entry, &bar.list_of_foos);
- *
- * Repeat the above for each element you want to add to the list. Deleting
- * works with the element itself.
- *      list_del(&foo->entry);
- *      free(foo);
- *
- * Note: calling list_del(&bar.list_of_foos) will set bar.list_of_foos to an empty
- * list again.
- *
- * Looping through the list requires a 'struct foo' as iterator and the
- * name of the field the subnodes use.
- *
- * struct foo *iterator;
- * list_for_each_entry(iterator, &bar.list_of_foos, entry) {
- *      if (iterator->something == ...)
- *             ...
- * }
- *
- * Note: You must not call list_del() on the iterator if you continue the
- * loop. You need to run the safe for-each loop instead:
- *
- * struct foo *iterator, *next;
- * list_for_each_entry_safe(iterator, next, &bar.list_of_foos, entry) {
- *      if (...)
- *              list_del(&iterator->entry);
- * }
- *
- */
-
-/**
- * The linkage struct for list nodes. This struct must be part of your
- * to-be-linked struct. struct list_head is required for both the head of the
- * list and for each list node.
- *
- * Position and name of the struct list_head field is irrelevant.
- * There are no requirements that elements of a list are of the same type.
- * There are no requirements for a list head, any struct list_head can be a list
- * head.
- */
-struct list_head {
-    struct list_head *next, *prev;
-};
-
-/**
- * Initialize the list as an empty list.
- *
- * Example:
- * INIT_LIST_HEAD(&bar->list_of_foos);
- *
- * @param The list to initialized.
- */
-#define LIST_HEAD_INIT(name) { &(name), &(name) }
-
-#define LIST_HEAD(name) \
-       struct list_head name = LIST_HEAD_INIT(name)
-
-static inline void
-INIT_LIST_HEAD(struct list_head *list)
-{
-    list->next = list->prev = list;
-}
-
-static inline void
-__list_add(struct list_head *entry,
-                struct list_head *prev, struct list_head *next)
-{
-    next->prev = entry;
-    entry->next = next;
-    entry->prev = prev;
-    prev->next = entry;
-}
-
-/**
- * Insert a new element after the given list head. The new element does not
- * need to be initialised as empty list.
- * The list changes from:
- *      head → some element → ...
- * to
- *      head → new element → older element → ...
- *
- * Example:
- * struct foo *newfoo = malloc(...);
- * list_add(&newfoo->entry, &bar->list_of_foos);
- *
- * @param entry The new element to prepend to the list.
- * @param head The existing list.
- */
-static inline void
-list_add(struct list_head *entry, struct list_head *head)
-{
-    __list_add(entry, head, head->next);
-}
-
-/**
- * Append a new element to the end of the list given with this list head.
- *
- * The list changes from:
- *      head → some element → ... → lastelement
- * to
- *      head → some element → ... → lastelement → new element
- *
- * Example:
- * struct foo *newfoo = malloc(...);
- * list_add_tail(&newfoo->entry, &bar->list_of_foos);
- *
- * @param entry The new element to prepend to the list.
- * @param head The existing list.
- */
-static inline void
-list_add_tail(struct list_head *entry, struct list_head *head)
-{
-    __list_add(entry, head->prev, head);
-}
-
-static inline void
-__list_del(struct list_head *prev, struct list_head *next)
-{
-    next->prev = prev;
-    prev->next = next;
-}
-
-/**
- * Remove the element from the list it is in. Using this function will reset
- * the pointers to/from this element so it is removed from the list. It does
- * NOT free the element itself or manipulate it otherwise.
- *
- * Using list_del on a pure list head (like in the example at the top of
- * this file) will NOT remove the first element from
- * the list but rather reset the list as empty list.
- *
- * Example:
- * list_del(&foo->entry);
- *
- * @param entry The element to remove.
- */
-static inline void
-list_del(struct list_head *entry)
-{
-    __list_del(entry->prev, entry->next);
-}
-
-static inline void
-list_del_init(struct list_head *entry)
-{
-    __list_del(entry->prev, entry->next);
-    INIT_LIST_HEAD(entry);
-}
-
-static inline void list_move_tail(struct list_head *list,
-                                 struct list_head *head)
-{
-       __list_del(list->prev, list->next);
-       list_add_tail(list, head);
-}
-
-/**
- * Check if the list is empty.
- *
- * Example:
- * list_empty(&bar->list_of_foos);
- *
- * @return True if the list contains one or more elements or False otherwise.
- */
-static inline bool
-list_empty(struct list_head *head)
-{
-    return head->next == head;
-}
-
-/**
- * Returns a pointer to the container of this list element.
- *
- * Example:
- * struct foo* f;
- * f = container_of(&foo->entry, struct foo, entry);
- * assert(f == foo);
- *
- * @param ptr Pointer to the struct list_head.
- * @param type Data type of the list element.
- * @param member Member name of the struct list_head field in the list element.
- * @return A pointer to the data struct containing the list head.
- */
-#ifndef container_of
-#define container_of(ptr, type, member) \
-    (type *)((char *)(ptr) - (char *) &((type *)0)->member)
-#endif
-
-/**
- * Alias of container_of
- */
-#define list_entry(ptr, type, member) \
-    container_of(ptr, type, member)
-
-/**
- * Retrieve the first list entry for the given list pointer.
- *
- * Example:
- * struct foo *first;
- * first = list_first_entry(&bar->list_of_foos, struct foo, list_of_foos);
- *
- * @param ptr The list head
- * @param type Data type of the list element to retrieve
- * @param member Member name of the struct list_head field in the list element.
- * @return A pointer to the first list element.
- */
-#define list_first_entry(ptr, type, member) \
-    list_entry((ptr)->next, type, member)
-
-/**
- * Retrieve the last list entry for the given listpointer.
- *
- * Example:
- * struct foo *first;
- * first = list_last_entry(&bar->list_of_foos, struct foo, list_of_foos);
- *
- * @param ptr The list head
- * @param type Data type of the list element to retrieve
- * @param member Member name of the struct list_head field in the list element.
- * @return A pointer to the last list element.
- */
-#define list_last_entry(ptr, type, member) \
-    list_entry((ptr)->prev, type, member)
-
-#define __container_of(ptr, sample, member)                            \
-    (void *)container_of((ptr), typeof(*(sample)), member)
-
-/**
- * Loop through the list given by head and set pos to struct in the list.
- *
- * Example:
- * struct foo *iterator;
- * list_for_each_entry(iterator, &bar->list_of_foos, entry) {
- *      [modify iterator]
- * }
- *
- * This macro is not safe for node deletion. Use list_for_each_entry_safe
- * instead.
- *
- * @param pos Iterator variable of the type of the list elements.
- * @param head List head
- * @param member Member name of the struct list_head in the list elements.
- *
- */
-#define list_for_each_entry(pos, head, member)                         \
-    for (pos = __container_of((head)->next, pos, member);              \
-        &pos->member != (head);                                        \
-        pos = __container_of(pos->member.next, pos, member))
-
-/**
- * Loop through the list, keeping a backup pointer to the element. This
- * macro allows for the deletion of a list element while looping through the
- * list.
- *
- * See list_for_each_entry for more details.
- */
-#define list_for_each_entry_safe(pos, tmp, head, member)               \
-    for (pos = __container_of((head)->next, pos, member),              \
-        tmp = __container_of(pos->member.next, pos, member);           \
-        &pos->member != (head);                                        \
-        pos = tmp, tmp = __container_of(pos->member.next, tmp, member))
-
-
-#define list_for_each_entry_reverse(pos, head, member)                 \
-       for (pos = __container_of((head)->prev, pos, member);           \
-            &pos->member != (head);                                    \
-            pos = __container_of(pos->member.prev, pos, member))
-
-#define list_for_each_entry_continue(pos, head, member)                        \
-       for (pos = __container_of(pos->member.next, pos, member);       \
-            &pos->member != (head);                                    \
-            pos = __container_of(pos->member.next, pos, member))
-
-#define list_for_each_entry_continue_reverse(pos, head, member)                \
-       for (pos = __container_of(pos->member.prev, pos, member);       \
-            &pos->member != (head);                                    \
-            pos = __container_of(pos->member.prev, pos, member))
-
-#define list_for_each_entry_from(pos, head, member)                    \
-       for (;                                                          \
-            &pos->member != (head);                                    \
-            pos = __container_of(pos->member.next, pos, member))
-
-#endif
index 0898c3155292c54453df568921e546d59bb3db4f..8e34748709a0cfda354d3749f37d01ee609c2457 100644 (file)
@@ -92,7 +92,7 @@ nvif_notify_func(struct nvif_notify *notify, bool keep)
 {
        int ret = notify->func(notify);
        if (ret == NVIF_NOTIFY_KEEP ||
-           !test_and_clear_bit(NVKM_NOTIFY_USER, &notify->flags)) {
+           !test_and_clear_bit(NVIF_NOTIFY_USER, &notify->flags)) {
                if (!keep)
                        atomic_dec(&notify->putcnt);
                else
diff --git a/drivers/gpu/drm/nouveau/nvif/notify.h b/drivers/gpu/drm/nouveau/nvif/notify.h
deleted file mode 100644 (file)
index 9ebfa3b..0000000
+++ /dev/null
@@ -1,39 +0,0 @@
-#ifndef __NVIF_NOTIFY_H__
-#define __NVIF_NOTIFY_H__
-
-struct nvif_notify {
-       struct nvif_object *object;
-       int index;
-
-#define NVIF_NOTIFY_USER 0
-#define NVIF_NOTIFY_WORK 1
-       unsigned long flags;
-       atomic_t putcnt;
-       void (*dtor)(struct nvif_notify *);
-#define NVIF_NOTIFY_DROP 0
-#define NVIF_NOTIFY_KEEP 1
-       int  (*func)(struct nvif_notify *);
-
-       /* this is const for a *very* good reason - the data might be on the
-        * stack from an irq handler.  if you're not nvif/notify.c then you
-        * should probably think twice before casting it away...
-        */
-       const void *data;
-       u32 size;
-       struct work_struct work;
-};
-
-int  nvif_notify_init(struct nvif_object *, void (*dtor)(struct nvif_notify *),
-                     int (*func)(struct nvif_notify *), bool work, u8 type,
-                     void *data, u32 size, u32 reply, struct nvif_notify *);
-int  nvif_notify_fini(struct nvif_notify *);
-int  nvif_notify_get(struct nvif_notify *);
-int  nvif_notify_put(struct nvif_notify *);
-int  nvif_notify(const void *, u32, const void *, u32);
-
-int  nvif_notify_new(struct nvif_object *, int (*func)(struct nvif_notify *),
-                    bool work, u8 type, void *data, u32 size, u32 reply,
-                    struct nvif_notify **);
-void nvif_notify_ref(struct nvif_notify *, struct nvif_notify **);
-
-#endif
index dd85b56f6aa502a9ba65dcb9d9e9b2e61da7f664..3ab4e2f8cc12ef8b6b930304bc2d4c2cf2b801f4 100644 (file)
  * Authors: Ben Skeggs <bskeggs@redhat.com>
  */
 
-#include "object.h"
-#include "client.h"
-#include "driver.h"
-#include "ioctl.h"
+#include <nvif/object.h>
+#include <nvif/client.h>
+#include <nvif/driver.h>
+#include <nvif/ioctl.h>
 
 int
 nvif_object_ioctl(struct nvif_object *object, void *data, u32 size, void **hack)
diff --git a/drivers/gpu/drm/nouveau/nvif/object.h b/drivers/gpu/drm/nouveau/nvif/object.h
deleted file mode 100644 (file)
index fe51917..0000000
+++ /dev/null
@@ -1,75 +0,0 @@
-#ifndef __NVIF_OBJECT_H__
-#define __NVIF_OBJECT_H__
-
-#include <nvif/os.h>
-
-struct nvif_object {
-       struct nvif_object *parent;
-       struct nvif_object *object; /*XXX: hack for nvif_object() */
-       struct kref refcount;
-       u32 handle;
-       u32 oclass;
-       void *data;
-       u32   size;
-       void *priv; /*XXX: hack */
-       void (*dtor)(struct nvif_object *);
-       struct {
-               void __iomem *ptr;
-               u32 size;
-       } map;
-};
-
-int  nvif_object_init(struct nvif_object *, void (*dtor)(struct nvif_object *),
-                     u32 handle, u32 oclass, void *, u32,
-                     struct nvif_object *);
-void nvif_object_fini(struct nvif_object *);
-int  nvif_object_new(struct nvif_object *, u32 handle, u32 oclass,
-                    void *, u32, struct nvif_object **);
-void nvif_object_ref(struct nvif_object *, struct nvif_object **);
-int  nvif_object_ioctl(struct nvif_object *, void *, u32, void **);
-int  nvif_object_sclass(struct nvif_object *, u32 *, int);
-u32  nvif_object_rd(struct nvif_object *, int, u64);
-void nvif_object_wr(struct nvif_object *, int, u64, u32);
-int  nvif_object_mthd(struct nvif_object *, u32, void *, u32);
-int  nvif_object_map(struct nvif_object *);
-void nvif_object_unmap(struct nvif_object *);
-
-#define nvif_object(a) (a)->object
-
-#define ioread8_native ioread8
-#define iowrite8_native iowrite8
-#define nvif_rd(a,b,c) ({                                                      \
-       struct nvif_object *_object = nvif_object(a);                          \
-       u32 _data;                                                             \
-       if (likely(_object->map.ptr))                                          \
-               _data = ioread##b##_native((u8 __iomem *)_object->map.ptr + (c));      \
-       else                                                                   \
-               _data = nvif_object_rd(_object, (b) / 8, (c));                 \
-       _data;                                                                 \
-})
-#define nvif_wr(a,b,c,d) ({                                                    \
-       struct nvif_object *_object = nvif_object(a);                          \
-       if (likely(_object->map.ptr))                                          \
-               iowrite##b##_native((d), (u8 __iomem *)_object->map.ptr + (c));        \
-       else                                                                   \
-               nvif_object_wr(_object, (b) / 8, (c), (d));                    \
-})
-#define nvif_rd08(a,b) ({ u8  _v = nvif_rd((a), 8, (b)); _v; })
-#define nvif_rd16(a,b) ({ u16 _v = nvif_rd((a), 16, (b)); _v; })
-#define nvif_rd32(a,b) ({ u32 _v = nvif_rd((a), 32, (b)); _v; })
-#define nvif_wr08(a,b,c) nvif_wr((a), 8, (b), (u8)(c))
-#define nvif_wr16(a,b,c) nvif_wr((a), 16, (b), (u16)(c))
-#define nvif_wr32(a,b,c) nvif_wr((a), 32, (b), (u32)(c))
-#define nvif_mask(a,b,c,d) ({                                                  \
-       u32 _v = nvif_rd32(nvif_object(a), (b));                               \
-       nvif_wr32(nvif_object(a), (b), (_v & ~(c)) | (d));                     \
-       _v;                                                                    \
-})
-
-#define nvif_mthd(a,b,c,d) nvif_object_mthd(nvif_object(a), (b), (c), (d))
-
-/*XXX*/
-#include <core/object.h>
-#define nvkm_object(a) ((struct nouveau_object *)nvif_object(a)->priv)
-
-#endif
diff --git a/drivers/gpu/drm/nouveau/nvif/os.h b/drivers/gpu/drm/nouveau/nvif/os.h
deleted file mode 120000 (symlink)
index bd744b2..0000000
+++ /dev/null
@@ -1 +0,0 @@
-../core/os.h
\ No newline at end of file
diff --git a/drivers/gpu/drm/nouveau/nvif/unpack.h b/drivers/gpu/drm/nouveau/nvif/unpack.h
deleted file mode 100644 (file)
index 5933188..0000000
+++ /dev/null
@@ -1,24 +0,0 @@
-#ifndef __NVIF_UNPACK_H__
-#define __NVIF_UNPACK_H__
-
-#define nvif_unvers(d) ({                                                      \
-       ret = (size == sizeof(d)) ? 0 : -ENOSYS;                               \
-       (ret == 0);                                                            \
-})
-
-#define nvif_unpack(d,vl,vh,m) ({                                              \
-       if ((vl) == 0 || ret == -ENOSYS) {                                     \
-               int _size = sizeof(d);                                         \
-               if (_size <= size && (d).version >= (vl) &&                    \
-                                    (d).version <= (vh)) {                    \
-                       data = (u8 *)data + _size;                             \
-                       size = size - _size;                                   \
-                       ret = ((m) || !size) ? 0 : -E2BIG;                     \
-               } else {                                                       \
-                       ret = -ENOSYS;                                         \
-               }                                                              \
-       }                                                                      \
-       (ret == 0);                                                            \
-})
-
-#endif
diff --git a/drivers/gpu/drm/nouveau/nvkm/Kbuild b/drivers/gpu/drm/nouveau/nvkm/Kbuild
new file mode 100644 (file)
index 0000000..2832147
--- /dev/null
@@ -0,0 +1,3 @@
+include $(src)/nvkm/core/Kbuild
+include $(src)/nvkm/subdev/Kbuild
+include $(src)/nvkm/engine/Kbuild
diff --git a/drivers/gpu/drm/nouveau/nvkm/core/Kbuild b/drivers/gpu/drm/nouveau/nvkm/core/Kbuild
new file mode 100644 (file)
index 0000000..a2bdb20
--- /dev/null
@@ -0,0 +1,17 @@
+nvkm-y := nvkm/core/client.o
+nvkm-y += nvkm/core/engctx.o
+nvkm-y += nvkm/core/engine.o
+nvkm-y += nvkm/core/enum.o
+nvkm-y += nvkm/core/event.o
+nvkm-y += nvkm/core/gpuobj.o
+nvkm-y += nvkm/core/handle.o
+nvkm-y += nvkm/core/ioctl.o
+nvkm-y += nvkm/core/mm.o
+nvkm-y += nvkm/core/namedb.o
+nvkm-y += nvkm/core/notify.o
+nvkm-y += nvkm/core/object.o
+nvkm-y += nvkm/core/option.o
+nvkm-y += nvkm/core/parent.o
+nvkm-y += nvkm/core/printk.o
+nvkm-y += nvkm/core/ramht.o
+nvkm-y += nvkm/core/subdev.o
diff --git a/drivers/gpu/drm/nouveau/nvkm/core/client.c b/drivers/gpu/drm/nouveau/nvkm/core/client.c
new file mode 100644 (file)
index 0000000..878a82f
--- /dev/null
@@ -0,0 +1,266 @@
+/*
+ * Copyright 2012 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 <core/client.h>
+#include <core/device.h>
+#include <core/handle.h>
+#include <core/notify.h>
+#include <core/option.h>
+
+#include <nvif/class.h>
+#include <nvif/event.h>
+#include <nvif/unpack.h>
+
+struct nvkm_client_notify {
+       struct nvkm_client *client;
+       struct nvkm_notify n;
+       u8 version;
+       u8 size;
+       union {
+               struct nvif_notify_rep_v0 v0;
+       } rep;
+};
+
+static int
+nvkm_client_notify(struct nvkm_notify *n)
+{
+       struct nvkm_client_notify *notify = container_of(n, typeof(*notify), n);
+       struct nvkm_client *client = notify->client;
+       return client->ntfy(&notify->rep, notify->size, n->data, n->size);
+}
+
+int
+nvkm_client_notify_put(struct nvkm_client *client, int index)
+{
+       if (index < ARRAY_SIZE(client->notify)) {
+               if (client->notify[index]) {
+                       nvkm_notify_put(&client->notify[index]->n);
+                       return 0;
+               }
+       }
+       return -ENOENT;
+}
+
+int
+nvkm_client_notify_get(struct nvkm_client *client, int index)
+{
+       if (index < ARRAY_SIZE(client->notify)) {
+               if (client->notify[index]) {
+                       nvkm_notify_get(&client->notify[index]->n);
+                       return 0;
+               }
+       }
+       return -ENOENT;
+}
+
+int
+nvkm_client_notify_del(struct nvkm_client *client, int index)
+{
+       if (index < ARRAY_SIZE(client->notify)) {
+               if (client->notify[index]) {
+                       nvkm_notify_fini(&client->notify[index]->n);
+                       kfree(client->notify[index]);
+                       client->notify[index] = NULL;
+                       return 0;
+               }
+       }
+       return -ENOENT;
+}
+
+int
+nvkm_client_notify_new(struct nvkm_object *object,
+                      struct nvkm_event *event, void *data, u32 size)
+{
+       struct nvkm_client *client = nvkm_client(object);
+       struct nvkm_client_notify *notify;
+       union {
+               struct nvif_notify_req_v0 v0;
+       } *req = data;
+       u8  index, reply;
+       int ret;
+
+       for (index = 0; index < ARRAY_SIZE(client->notify); index++) {
+               if (!client->notify[index])
+                       break;
+       }
+
+       if (index == ARRAY_SIZE(client->notify))
+               return -ENOSPC;
+
+       notify = kzalloc(sizeof(*notify), GFP_KERNEL);
+       if (!notify)
+               return -ENOMEM;
+
+       nv_ioctl(client, "notify new size %d\n", size);
+       if (nvif_unpack(req->v0, 0, 0, true)) {
+               nv_ioctl(client, "notify new vers %d reply %d route %02x "
+                                "token %llx\n", req->v0.version,
+                        req->v0.reply, req->v0.route, req->v0.token);
+               notify->version = req->v0.version;
+               notify->size = sizeof(notify->rep.v0);
+               notify->rep.v0.version = req->v0.version;
+               notify->rep.v0.route = req->v0.route;
+               notify->rep.v0.token = req->v0.token;
+               reply = req->v0.reply;
+       }
+
+       if (ret == 0) {
+               ret = nvkm_notify_init(object, event, nvkm_client_notify,
+                                      false, data, size, reply, &notify->n);
+               if (ret == 0) {
+                       client->notify[index] = notify;
+                       notify->client = client;
+                       return index;
+               }
+       }
+
+       kfree(notify);
+       return ret;
+}
+
+static int
+nvkm_client_mthd_devlist(struct nvkm_object *object, void *data, u32 size)
+{
+       union {
+               struct nv_client_devlist_v0 v0;
+       } *args = data;
+       int ret;
+
+       nv_ioctl(object, "client devlist size %d\n", size);
+       if (nvif_unpack(args->v0, 0, 0, true)) {
+               nv_ioctl(object, "client devlist vers %d count %d\n",
+                        args->v0.version, args->v0.count);
+               if (size == sizeof(args->v0.device[0]) * args->v0.count) {
+                       ret = nvkm_device_list(args->v0.device, args->v0.count);
+                       if (ret >= 0) {
+                               args->v0.count = ret;
+                               ret = 0;
+                       }
+               } else {
+                       ret = -EINVAL;
+               }
+       }
+
+       return ret;
+}
+
+static int
+nvkm_client_mthd(struct nvkm_object *object, u32 mthd, void *data, u32 size)
+{
+       switch (mthd) {
+       case NV_CLIENT_DEVLIST:
+               return nvkm_client_mthd_devlist(object, data, size);
+       default:
+               break;
+       }
+       return -EINVAL;
+}
+
+static void
+nvkm_client_dtor(struct nvkm_object *object)
+{
+       struct nvkm_client *client = (void *)object;
+       int i;
+       for (i = 0; i < ARRAY_SIZE(client->notify); i++)
+               nvkm_client_notify_del(client, i);
+       nvkm_object_ref(NULL, &client->device);
+       nvkm_handle_destroy(client->root);
+       nvkm_namedb_destroy(&client->namedb);
+}
+
+static struct nvkm_oclass
+nvkm_client_oclass = {
+       .ofuncs = &(struct nvkm_ofuncs) {
+               .dtor = nvkm_client_dtor,
+               .mthd = nvkm_client_mthd,
+       },
+};
+
+int
+nvkm_client_create_(const char *name, u64 devname, const char *cfg,
+                   const char *dbg, int length, void **pobject)
+{
+       struct nvkm_object *device;
+       struct nvkm_client *client;
+       int ret;
+
+       device = (void *)nvkm_device_find(devname);
+       if (!device)
+               return -ENODEV;
+
+       ret = nvkm_namedb_create_(NULL, NULL, &nvkm_client_oclass,
+                                 NV_CLIENT_CLASS, NULL,
+                                 (1ULL << NVDEV_ENGINE_DEVICE),
+                                 length, pobject);
+       client = *pobject;
+       if (ret)
+               return ret;
+
+       ret = nvkm_handle_create(nv_object(client), ~0, ~0, nv_object(client),
+                                &client->root);
+       if (ret)
+               return ret;
+
+       /* prevent init/fini being called, os in in charge of this */
+       atomic_set(&nv_object(client)->usecount, 2);
+
+       nvkm_object_ref(device, &client->device);
+       snprintf(client->name, sizeof(client->name), "%s", name);
+       client->debug = nvkm_dbgopt(dbg, "CLIENT");
+       return 0;
+}
+
+int
+nvkm_client_init(struct nvkm_client *client)
+{
+       int ret;
+       nv_debug(client, "init running\n");
+       ret = nvkm_handle_init(client->root);
+       nv_debug(client, "init completed with %d\n", ret);
+       return ret;
+}
+
+int
+nvkm_client_fini(struct nvkm_client *client, bool suspend)
+{
+       const char *name[2] = { "fini", "suspend" };
+       int ret, i;
+       nv_debug(client, "%s running\n", name[suspend]);
+       nv_debug(client, "%s notify\n", name[suspend]);
+       for (i = 0; i < ARRAY_SIZE(client->notify); i++)
+               nvkm_client_notify_put(client, i);
+       nv_debug(client, "%s object\n", name[suspend]);
+       ret = nvkm_handle_fini(client->root, suspend);
+       nv_debug(client, "%s completed with %d\n", name[suspend], ret);
+       return ret;
+}
+
+const char *
+nvkm_client_name(void *obj)
+{
+       const char *client_name = "unknown";
+       struct nvkm_client *client = nvkm_client(obj);
+       if (client)
+               client_name = client->name;
+       return client_name;
+}
diff --git a/drivers/gpu/drm/nouveau/nvkm/core/engctx.c b/drivers/gpu/drm/nouveau/nvkm/core/engctx.c
new file mode 100644 (file)
index 0000000..fb2acbc
--- /dev/null
@@ -0,0 +1,239 @@
+/*
+ * Copyright 2012 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 <core/engctx.h>
+#include <core/engine.h>
+#include <core/client.h>
+
+static inline int
+nvkm_engctx_exists(struct nvkm_object *parent,
+                  struct nvkm_engine *engine, void **pobject)
+{
+       struct nvkm_engctx *engctx;
+       struct nvkm_object *parctx;
+
+       list_for_each_entry(engctx, &engine->contexts, head) {
+               parctx = nv_pclass(nv_object(engctx), NV_PARENT_CLASS);
+               if (parctx == parent) {
+                       atomic_inc(&nv_object(engctx)->refcount);
+                       *pobject = engctx;
+                       return 1;
+               }
+       }
+
+       return 0;
+}
+
+int
+nvkm_engctx_create_(struct nvkm_object *parent, struct nvkm_object *engobj,
+                   struct nvkm_oclass *oclass, struct nvkm_object *pargpu,
+                   u32 size, u32 align, u32 flags, int length, void **pobject)
+{
+       struct nvkm_client *client = nvkm_client(parent);
+       struct nvkm_engine *engine = nv_engine(engobj);
+       struct nvkm_object *engctx;
+       unsigned long save;
+       int ret;
+
+       /* check if this engine already has a context for the parent object,
+        * and reference it instead of creating a new one
+        */
+       spin_lock_irqsave(&engine->lock, save);
+       ret = nvkm_engctx_exists(parent, engine, pobject);
+       spin_unlock_irqrestore(&engine->lock, save);
+       if (ret)
+               return ret;
+
+       /* create the new context, supports creating both raw objects and
+        * objects backed by instance memory
+        */
+       if (size) {
+               ret = nvkm_gpuobj_create_(parent, engobj, oclass,
+                                         NV_ENGCTX_CLASS, pargpu, size,
+                                         align, flags, length, pobject);
+       } else {
+               ret = nvkm_object_create_(parent, engobj, oclass,
+                                         NV_ENGCTX_CLASS, length, pobject);
+       }
+
+       engctx = *pobject;
+       if (ret)
+               return ret;
+
+       /* must take the lock again and re-check a context doesn't already
+        * exist (in case of a race) - the lock had to be dropped before as
+        * it's not possible to allocate the object with it held.
+        */
+       spin_lock_irqsave(&engine->lock, save);
+       ret = nvkm_engctx_exists(parent, engine, pobject);
+       if (ret) {
+               spin_unlock_irqrestore(&engine->lock, save);
+               nvkm_object_ref(NULL, &engctx);
+               return ret;
+       }
+
+       if (client->vm)
+               atomic_inc(&client->vm->engref[nv_engidx(engine)]);
+       list_add(&nv_engctx(engctx)->head, &engine->contexts);
+       nv_engctx(engctx)->addr = ~0ULL;
+       spin_unlock_irqrestore(&engine->lock, save);
+       return 0;
+}
+
+void
+nvkm_engctx_destroy(struct nvkm_engctx *engctx)
+{
+       struct nvkm_engine *engine = engctx->gpuobj.object.engine;
+       struct nvkm_client *client = nvkm_client(engctx);
+       unsigned long save;
+
+       nvkm_gpuobj_unmap(&engctx->vma);
+       spin_lock_irqsave(&engine->lock, save);
+       list_del(&engctx->head);
+       spin_unlock_irqrestore(&engine->lock, save);
+
+       if (client->vm)
+               atomic_dec(&client->vm->engref[nv_engidx(engine)]);
+
+       if (engctx->gpuobj.size)
+               nvkm_gpuobj_destroy(&engctx->gpuobj);
+       else
+               nvkm_object_destroy(&engctx->gpuobj.object);
+}
+
+int
+nvkm_engctx_init(struct nvkm_engctx *engctx)
+{
+       struct nvkm_object *object = nv_object(engctx);
+       struct nvkm_subdev *subdev = nv_subdev(object->engine);
+       struct nvkm_object *parent;
+       struct nvkm_subdev *pardev;
+       int ret;
+
+       ret = nvkm_gpuobj_init(&engctx->gpuobj);
+       if (ret)
+               return ret;
+
+       parent = nv_pclass(object->parent, NV_PARENT_CLASS);
+       pardev = nv_subdev(parent->engine);
+       if (nv_parent(parent)->context_attach) {
+               mutex_lock(&pardev->mutex);
+               ret = nv_parent(parent)->context_attach(parent, object);
+               mutex_unlock(&pardev->mutex);
+       }
+
+       if (ret) {
+               nv_error(parent, "failed to attach %s context, %d\n",
+                        subdev->name, ret);
+               return ret;
+       }
+
+       nv_debug(parent, "attached %s context\n", subdev->name);
+       return 0;
+}
+
+int
+nvkm_engctx_fini(struct nvkm_engctx *engctx, bool suspend)
+{
+       struct nvkm_object *object = nv_object(engctx);
+       struct nvkm_subdev *subdev = nv_subdev(object->engine);
+       struct nvkm_object *parent;
+       struct nvkm_subdev *pardev;
+       int ret = 0;
+
+       parent = nv_pclass(object->parent, NV_PARENT_CLASS);
+       pardev = nv_subdev(parent->engine);
+       if (nv_parent(parent)->context_detach) {
+               mutex_lock(&pardev->mutex);
+               ret = nv_parent(parent)->context_detach(parent, suspend, object);
+               mutex_unlock(&pardev->mutex);
+       }
+
+       if (ret) {
+               nv_error(parent, "failed to detach %s context, %d\n",
+                        subdev->name, ret);
+               return ret;
+       }
+
+       nv_debug(parent, "detached %s context\n", subdev->name);
+       return nvkm_gpuobj_fini(&engctx->gpuobj, suspend);
+}
+
+int
+_nvkm_engctx_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+                 struct nvkm_oclass *oclass, void *data, u32 size,
+                 struct nvkm_object **pobject)
+{
+       struct nvkm_engctx *engctx;
+       int ret;
+
+       ret = nvkm_engctx_create(parent, engine, oclass, NULL, 256, 256,
+                                NVOBJ_FLAG_ZERO_ALLOC, &engctx);
+       *pobject = nv_object(engctx);
+       return ret;
+}
+
+void
+_nvkm_engctx_dtor(struct nvkm_object *object)
+{
+       nvkm_engctx_destroy(nv_engctx(object));
+}
+
+int
+_nvkm_engctx_init(struct nvkm_object *object)
+{
+       return nvkm_engctx_init(nv_engctx(object));
+}
+
+int
+_nvkm_engctx_fini(struct nvkm_object *object, bool suspend)
+{
+       return nvkm_engctx_fini(nv_engctx(object), suspend);
+}
+
+struct nvkm_object *
+nvkm_engctx_get(struct nvkm_engine *engine, u64 addr)
+{
+       struct nvkm_engctx *engctx;
+       unsigned long flags;
+
+       spin_lock_irqsave(&engine->lock, flags);
+       list_for_each_entry(engctx, &engine->contexts, head) {
+               if (engctx->addr == addr) {
+                       engctx->save = flags;
+                       return nv_object(engctx);
+               }
+       }
+       spin_unlock_irqrestore(&engine->lock, flags);
+       return NULL;
+}
+
+void
+nvkm_engctx_put(struct nvkm_object *object)
+{
+       if (object) {
+               struct nvkm_engine *engine = nv_engine(object->engine);
+               struct nvkm_engctx *engctx = nv_engctx(object);
+               spin_unlock_irqrestore(&engine->lock, engctx->save);
+       }
+}
diff --git a/drivers/gpu/drm/nouveau/nvkm/core/engine.c b/drivers/gpu/drm/nouveau/nvkm/core/engine.c
new file mode 100644 (file)
index 0000000..6082017
--- /dev/null
@@ -0,0 +1,75 @@
+/*
+ * Copyright 2012 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 <core/engine.h>
+#include <core/device.h>
+#include <core/option.h>
+
+struct nvkm_engine *
+nvkm_engine(void *obj, int idx)
+{
+       obj = nvkm_subdev(obj, idx);
+       if (obj && nv_iclass(obj, NV_ENGINE_CLASS))
+               return nv_engine(obj);
+       return NULL;
+}
+
+int
+nvkm_engine_create_(struct nvkm_object *parent, struct nvkm_object *engobj,
+                   struct nvkm_oclass *oclass, bool enable,
+                   const char *iname, const char *fname,
+                   int length, void **pobject)
+{
+       struct nvkm_engine *engine;
+       int ret;
+
+       ret = nvkm_subdev_create_(parent, engobj, oclass, NV_ENGINE_CLASS,
+                                 iname, fname, length, pobject);
+       engine = *pobject;
+       if (ret)
+               return ret;
+
+       if (parent) {
+               struct nvkm_device *device = nv_device(parent);
+               int engidx = nv_engidx(engine);
+
+               if (device->disable_mask & (1ULL << engidx)) {
+                       if (!nvkm_boolopt(device->cfgopt, iname, false)) {
+                               nv_debug(engine, "engine disabled by hw/fw\n");
+                               return -ENODEV;
+                       }
+
+                       nv_warn(engine, "ignoring hw/fw engine disable\n");
+               }
+
+               if (!nvkm_boolopt(device->cfgopt, iname, enable)) {
+                       if (!enable)
+                               nv_warn(engine, "disabled, %s=1 to enable\n", iname);
+                       return -ENODEV;
+               }
+       }
+
+       INIT_LIST_HEAD(&engine->contexts);
+       spin_lock_init(&engine->lock);
+       return 0;
+}
diff --git a/drivers/gpu/drm/nouveau/nvkm/core/enum.c b/drivers/gpu/drm/nouveau/nvkm/core/enum.c
new file mode 100644 (file)
index 0000000..4f92bfc
--- /dev/null
@@ -0,0 +1,66 @@
+/*
+ * Copyright (C) 2010 Nouveau Project
+ *
+ * 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 <core/enum.h>
+
+const struct nvkm_enum *
+nvkm_enum_find(const struct nvkm_enum *en, u32 value)
+{
+       while (en->name) {
+               if (en->value == value)
+                       return en;
+               en++;
+       }
+
+       return NULL;
+}
+
+const struct nvkm_enum *
+nvkm_enum_print(const struct nvkm_enum *en, u32 value)
+{
+       en = nvkm_enum_find(en, value);
+       if (en)
+               pr_cont("%s", en->name);
+       else
+               pr_cont("(unknown enum 0x%08x)", value);
+       return en;
+}
+
+void
+nvkm_bitfield_print(const struct nvkm_bitfield *bf, u32 value)
+{
+       while (bf->name) {
+               if (value & bf->mask) {
+                       pr_cont(" %s", bf->name);
+                       value &= ~bf->mask;
+               }
+
+               bf++;
+       }
+
+       if (value)
+               pr_cont(" (unknown bits 0x%08x)", value);
+}
diff --git a/drivers/gpu/drm/nouveau/nvkm/core/event.c b/drivers/gpu/drm/nouveau/nvkm/core/event.c
new file mode 100644 (file)
index 0000000..4e8d3fa
--- /dev/null
@@ -0,0 +1,99 @@
+/*
+ * Copyright 2013-2014 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.
+ */
+#include <core/event.h>
+#include <core/notify.h>
+
+void
+nvkm_event_put(struct nvkm_event *event, u32 types, int index)
+{
+       assert_spin_locked(&event->refs_lock);
+       while (types) {
+               int type = __ffs(types); types &= ~(1 << type);
+               if (--event->refs[index * event->types_nr + type] == 0) {
+                       if (event->func->fini)
+                               event->func->fini(event, 1 << type, index);
+               }
+       }
+}
+
+void
+nvkm_event_get(struct nvkm_event *event, u32 types, int index)
+{
+       assert_spin_locked(&event->refs_lock);
+       while (types) {
+               int type = __ffs(types); types &= ~(1 << type);
+               if (++event->refs[index * event->types_nr + type] == 1) {
+                       if (event->func->init)
+                               event->func->init(event, 1 << type, index);
+               }
+       }
+}
+
+void
+nvkm_event_send(struct nvkm_event *event, u32 types, int index,
+               void *data, u32 size)
+{
+       struct nvkm_notify *notify;
+       unsigned long flags;
+
+       if (!event->refs || WARN_ON(index >= event->index_nr))
+               return;
+
+       spin_lock_irqsave(&event->list_lock, flags);
+       list_for_each_entry(notify, &event->list, head) {
+               if (notify->index == index && (notify->types & types)) {
+                       if (event->func->send) {
+                               event->func->send(data, size, notify);
+                               continue;
+                       }
+                       nvkm_notify_send(notify, data, size);
+               }
+       }
+       spin_unlock_irqrestore(&event->list_lock, flags);
+}
+
+void
+nvkm_event_fini(struct nvkm_event *event)
+{
+       if (event->refs) {
+               kfree(event->refs);
+               event->refs = NULL;
+       }
+}
+
+int
+nvkm_event_init(const struct nvkm_event_func *func, int types_nr, int index_nr,
+               struct nvkm_event *event)
+{
+       event->refs = kzalloc(sizeof(*event->refs) * index_nr * types_nr,
+                             GFP_KERNEL);
+       if (!event->refs)
+               return -ENOMEM;
+
+       event->func = func;
+       event->types_nr = types_nr;
+       event->index_nr = index_nr;
+       spin_lock_init(&event->refs_lock);
+       spin_lock_init(&event->list_lock);
+       INIT_LIST_HEAD(&event->list);
+       return 0;
+}
diff --git a/drivers/gpu/drm/nouveau/nvkm/core/gpuobj.c b/drivers/gpu/drm/nouveau/nvkm/core/gpuobj.c
new file mode 100644 (file)
index 0000000..2eba801
--- /dev/null
@@ -0,0 +1,316 @@
+/*
+ * Copyright 2012 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 <core/gpuobj.h>
+#include <core/engine.h>
+
+#include <subdev/instmem.h>
+#include <subdev/bar.h>
+#include <subdev/mmu.h>
+
+void
+nvkm_gpuobj_destroy(struct nvkm_gpuobj *gpuobj)
+{
+       int i;
+
+       if (gpuobj->flags & NVOBJ_FLAG_ZERO_FREE) {
+               for (i = 0; i < gpuobj->size; i += 4)
+                       nv_wo32(gpuobj, i, 0x00000000);
+       }
+
+       if (gpuobj->node)
+               nvkm_mm_free(&nv_gpuobj(gpuobj->parent)->heap, &gpuobj->node);
+
+       if (gpuobj->heap.block_size)
+               nvkm_mm_fini(&gpuobj->heap);
+
+       nvkm_object_destroy(&gpuobj->object);
+}
+
+int
+nvkm_gpuobj_create_(struct nvkm_object *parent, struct nvkm_object *engine,
+                   struct nvkm_oclass *oclass, u32 pclass,
+                   struct nvkm_object *pargpu, u32 size, u32 align, u32 flags,
+                   int length, void **pobject)
+{
+       struct nvkm_instmem *imem = nvkm_instmem(parent);
+       struct nvkm_bar *bar = nvkm_bar(parent);
+       struct nvkm_gpuobj *gpuobj;
+       struct nvkm_mm *heap = NULL;
+       int ret, i;
+       u64 addr;
+
+       *pobject = NULL;
+
+       if (pargpu) {
+               while ((pargpu = nv_pclass(pargpu, NV_GPUOBJ_CLASS))) {
+                       if (nv_gpuobj(pargpu)->heap.block_size)
+                               break;
+                       pargpu = pargpu->parent;
+               }
+
+               if (unlikely(pargpu == NULL)) {
+                       nv_error(parent, "no gpuobj heap\n");
+                       return -EINVAL;
+               }
+
+               addr =  nv_gpuobj(pargpu)->addr;
+               heap = &nv_gpuobj(pargpu)->heap;
+               atomic_inc(&parent->refcount);
+       } else {
+               ret = imem->alloc(imem, parent, size, align, &parent);
+               pargpu = parent;
+               if (ret)
+                       return ret;
+
+               addr = nv_memobj(pargpu)->addr;
+               size = nv_memobj(pargpu)->size;
+
+               if (bar && bar->alloc) {
+                       struct nvkm_instobj *iobj = (void *)parent;
+                       struct nvkm_mem **mem = (void *)(iobj + 1);
+                       struct nvkm_mem *node = *mem;
+                       if (!bar->alloc(bar, parent, node, &pargpu)) {
+                               nvkm_object_ref(NULL, &parent);
+                               parent = pargpu;
+                       }
+               }
+       }
+
+       ret = nvkm_object_create_(parent, engine, oclass, pclass |
+                                 NV_GPUOBJ_CLASS, length, pobject);
+       nvkm_object_ref(NULL, &parent);
+       gpuobj = *pobject;
+       if (ret)
+               return ret;
+
+       gpuobj->parent = pargpu;
+       gpuobj->flags = flags;
+       gpuobj->addr = addr;
+       gpuobj->size = size;
+
+       if (heap) {
+               ret = nvkm_mm_head(heap, 0, 1, size, size, max(align, (u32)1),
+                                  &gpuobj->node);
+               if (ret)
+                       return ret;
+
+               gpuobj->addr += gpuobj->node->offset;
+       }
+
+       if (gpuobj->flags & NVOBJ_FLAG_HEAP) {
+               ret = nvkm_mm_init(&gpuobj->heap, 0, gpuobj->size, 1);
+               if (ret)
+                       return ret;
+       }
+
+       if (flags & NVOBJ_FLAG_ZERO_ALLOC) {
+               for (i = 0; i < gpuobj->size; i += 4)
+                       nv_wo32(gpuobj, i, 0x00000000);
+       }
+
+       return ret;
+}
+
+struct nvkm_gpuobj_class {
+       struct nvkm_object *pargpu;
+       u64 size;
+       u32 align;
+       u32 flags;
+};
+
+static int
+_nvkm_gpuobj_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+                 struct nvkm_oclass *oclass, void *data, u32 size,
+                 struct nvkm_object **pobject)
+{
+       struct nvkm_gpuobj_class *args = data;
+       struct nvkm_gpuobj *object;
+       int ret;
+
+       ret = nvkm_gpuobj_create(parent, engine, oclass, 0, args->pargpu,
+                                args->size, args->align, args->flags,
+                                &object);
+       *pobject = nv_object(object);
+       if (ret)
+               return ret;
+
+       return 0;
+}
+
+void
+_nvkm_gpuobj_dtor(struct nvkm_object *object)
+{
+       nvkm_gpuobj_destroy(nv_gpuobj(object));
+}
+
+int
+_nvkm_gpuobj_init(struct nvkm_object *object)
+{
+       return nvkm_gpuobj_init(nv_gpuobj(object));
+}
+
+int
+_nvkm_gpuobj_fini(struct nvkm_object *object, bool suspend)
+{
+       return nvkm_gpuobj_fini(nv_gpuobj(object), suspend);
+}
+
+u32
+_nvkm_gpuobj_rd32(struct nvkm_object *object, u64 addr)
+{
+       struct nvkm_gpuobj *gpuobj = nv_gpuobj(object);
+       struct nvkm_ofuncs *pfuncs = nv_ofuncs(gpuobj->parent);
+       if (gpuobj->node)
+               addr += gpuobj->node->offset;
+       return pfuncs->rd32(gpuobj->parent, addr);
+}
+
+void
+_nvkm_gpuobj_wr32(struct nvkm_object *object, u64 addr, u32 data)
+{
+       struct nvkm_gpuobj *gpuobj = nv_gpuobj(object);
+       struct nvkm_ofuncs *pfuncs = nv_ofuncs(gpuobj->parent);
+       if (gpuobj->node)
+               addr += gpuobj->node->offset;
+       pfuncs->wr32(gpuobj->parent, addr, data);
+}
+
+static struct nvkm_oclass
+_nvkm_gpuobj_oclass = {
+       .handle = 0x00000000,
+       .ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = _nvkm_gpuobj_ctor,
+               .dtor = _nvkm_gpuobj_dtor,
+               .init = _nvkm_gpuobj_init,
+               .fini = _nvkm_gpuobj_fini,
+               .rd32 = _nvkm_gpuobj_rd32,
+               .wr32 = _nvkm_gpuobj_wr32,
+       },
+};
+
+int
+nvkm_gpuobj_new(struct nvkm_object *parent, struct nvkm_object *pargpu,
+               u32 size, u32 align, u32 flags,
+               struct nvkm_gpuobj **pgpuobj)
+{
+       struct nvkm_object *engine = parent;
+       struct nvkm_gpuobj_class args = {
+               .pargpu = pargpu,
+               .size = size,
+               .align = align,
+               .flags = flags,
+       };
+
+       if (!nv_iclass(engine, NV_SUBDEV_CLASS))
+               engine = &engine->engine->subdev.object;
+       BUG_ON(engine == NULL);
+
+       return nvkm_object_ctor(parent, engine, &_nvkm_gpuobj_oclass,
+                               &args, sizeof(args),
+                               (struct nvkm_object **)pgpuobj);
+}
+
+int
+nvkm_gpuobj_map(struct nvkm_gpuobj *gpuobj, u32 access, struct nvkm_vma *vma)
+{
+       struct nvkm_bar *bar = nvkm_bar(gpuobj);
+       int ret = -EINVAL;
+
+       if (bar && bar->umap) {
+               struct nvkm_instobj *iobj = (void *)
+                       nv_pclass(nv_object(gpuobj), NV_MEMOBJ_CLASS);
+               struct nvkm_mem **mem = (void *)(iobj + 1);
+               ret = bar->umap(bar, *mem, access, vma);
+       }
+
+       return ret;
+}
+
+int
+nvkm_gpuobj_map_vm(struct nvkm_gpuobj *gpuobj, struct nvkm_vm *vm,
+                  u32 access, struct nvkm_vma *vma)
+{
+       struct nvkm_instobj *iobj = (void *)
+               nv_pclass(nv_object(gpuobj), NV_MEMOBJ_CLASS);
+       struct nvkm_mem **mem = (void *)(iobj + 1);
+       int ret;
+
+       ret = nvkm_vm_get(vm, gpuobj->size, 12, access, vma);
+       if (ret)
+               return ret;
+
+       nvkm_vm_map(vma, *mem);
+       return 0;
+}
+
+void
+nvkm_gpuobj_unmap(struct nvkm_vma *vma)
+{
+       if (vma->node) {
+               nvkm_vm_unmap(vma);
+               nvkm_vm_put(vma);
+       }
+}
+
+/* the below is basically only here to support sharing the paged dma object
+ * for PCI(E)GART on <=nv4x chipsets, and should *not* be expected to work
+ * anywhere else.
+ */
+
+static void
+nvkm_gpudup_dtor(struct nvkm_object *object)
+{
+       struct nvkm_gpuobj *gpuobj = (void *)object;
+       nvkm_object_ref(NULL, &gpuobj->parent);
+       nvkm_object_destroy(&gpuobj->object);
+}
+
+static struct nvkm_oclass
+nvkm_gpudup_oclass = {
+       .handle = NV_GPUOBJ_CLASS,
+       .ofuncs = &(struct nvkm_ofuncs) {
+               .dtor = nvkm_gpudup_dtor,
+               .init = nvkm_object_init,
+               .fini = nvkm_object_fini,
+       },
+};
+
+int
+nvkm_gpuobj_dup(struct nvkm_object *parent, struct nvkm_gpuobj *base,
+               struct nvkm_gpuobj **pgpuobj)
+{
+       struct nvkm_gpuobj *gpuobj;
+       int ret;
+
+       ret = nvkm_object_create(parent, &parent->engine->subdev.object,
+                                &nvkm_gpudup_oclass, 0, &gpuobj);
+       *pgpuobj = gpuobj;
+       if (ret)
+               return ret;
+
+       nvkm_object_ref(nv_object(base), &gpuobj->parent);
+       gpuobj->addr = base->addr;
+       gpuobj->size = base->size;
+       return 0;
+}
diff --git a/drivers/gpu/drm/nouveau/nvkm/core/handle.c b/drivers/gpu/drm/nouveau/nvkm/core/handle.c
new file mode 100644 (file)
index 0000000..dc7ff10
--- /dev/null
@@ -0,0 +1,221 @@
+/*
+ * Copyright 2012 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 <core/handle.h>
+#include <core/client.h>
+
+#define hprintk(h,l,f,a...) do {                                               \
+       struct nvkm_client *c = nvkm_client((h)->object);                      \
+       struct nvkm_handle *p = (h)->parent; u32 n = p ? p->name : ~0;         \
+       nv_printk((c), l, "0x%08x:0x%08x "f, n, (h)->name, ##a);               \
+} while(0)
+
+int
+nvkm_handle_init(struct nvkm_handle *handle)
+{
+       struct nvkm_handle *item;
+       int ret;
+
+       hprintk(handle, TRACE, "init running\n");
+       ret = nvkm_object_inc(handle->object);
+       if (ret)
+               return ret;
+
+       hprintk(handle, TRACE, "init children\n");
+       list_for_each_entry(item, &handle->tree, head) {
+               ret = nvkm_handle_init(item);
+               if (ret)
+                       goto fail;
+       }
+
+       hprintk(handle, TRACE, "init completed\n");
+       return 0;
+fail:
+       hprintk(handle, ERROR, "init failed with %d\n", ret);
+       list_for_each_entry_continue_reverse(item, &handle->tree, head) {
+               nvkm_handle_fini(item, false);
+       }
+
+       nvkm_object_dec(handle->object, false);
+       return ret;
+}
+
+int
+nvkm_handle_fini(struct nvkm_handle *handle, bool suspend)
+{
+       static char *name[2] = { "fini", "suspend" };
+       struct nvkm_handle *item;
+       int ret;
+
+       hprintk(handle, TRACE, "%s children\n", name[suspend]);
+       list_for_each_entry(item, &handle->tree, head) {
+               ret = nvkm_handle_fini(item, suspend);
+               if (ret && suspend)
+                       goto fail;
+       }
+
+       hprintk(handle, TRACE, "%s running\n", name[suspend]);
+       if (handle->object) {
+               ret = nvkm_object_dec(handle->object, suspend);
+               if (ret && suspend)
+                       goto fail;
+       }
+
+       hprintk(handle, TRACE, "%s completed\n", name[suspend]);
+       return 0;
+fail:
+       hprintk(handle, ERROR, "%s failed with %d\n", name[suspend], ret);
+       list_for_each_entry_continue_reverse(item, &handle->tree, head) {
+               int rret = nvkm_handle_init(item);
+               if (rret)
+                       hprintk(handle, FATAL, "failed to restart, %d\n", rret);
+       }
+
+       return ret;
+}
+
+int
+nvkm_handle_create(struct nvkm_object *parent, u32 _parent, u32 _handle,
+                  struct nvkm_object *object, struct nvkm_handle **phandle)
+{
+       struct nvkm_object *namedb;
+       struct nvkm_handle *handle;
+       int ret;
+
+       namedb = parent;
+       while (!nv_iclass(namedb, NV_NAMEDB_CLASS))
+               namedb = namedb->parent;
+
+       handle = kzalloc(sizeof(*handle), GFP_KERNEL);
+       if (!handle)
+               return -ENOMEM;
+
+       INIT_LIST_HEAD(&handle->head);
+       INIT_LIST_HEAD(&handle->tree);
+       handle->name = _handle;
+       handle->priv = ~0;
+
+       ret = nvkm_namedb_insert(nv_namedb(namedb), _handle, object, handle);
+       if (ret) {
+               kfree(handle);
+               return ret;
+       }
+
+       if (nv_parent(parent)->object_attach) {
+               ret = nv_parent(parent)->object_attach(parent, object, _handle);
+               if (ret < 0) {
+                       nvkm_handle_destroy(handle);
+                       return ret;
+               }
+
+               handle->priv = ret;
+       }
+
+       if (object != namedb) {
+               while (!nv_iclass(namedb, NV_CLIENT_CLASS))
+                       namedb = namedb->parent;
+
+               handle->parent = nvkm_namedb_get(nv_namedb(namedb), _parent);
+               if (handle->parent) {
+                       list_add(&handle->head, &handle->parent->tree);
+                       nvkm_namedb_put(handle->parent);
+               }
+       }
+
+       hprintk(handle, TRACE, "created\n");
+       *phandle = handle;
+       return 0;
+}
+
+void
+nvkm_handle_destroy(struct nvkm_handle *handle)
+{
+       struct nvkm_handle *item, *temp;
+
+       hprintk(handle, TRACE, "destroy running\n");
+       list_for_each_entry_safe(item, temp, &handle->tree, head) {
+               nvkm_handle_destroy(item);
+       }
+       list_del(&handle->head);
+
+       if (handle->priv != ~0) {
+               struct nvkm_object *parent = handle->parent->object;
+               nv_parent(parent)->object_detach(parent, handle->priv);
+       }
+
+       hprintk(handle, TRACE, "destroy completed\n");
+       nvkm_namedb_remove(handle);
+       kfree(handle);
+}
+
+struct nvkm_object *
+nvkm_handle_ref(struct nvkm_object *parent, u32 name)
+{
+       struct nvkm_object *object = NULL;
+       struct nvkm_handle *handle;
+
+       while (!nv_iclass(parent, NV_NAMEDB_CLASS))
+               parent = parent->parent;
+
+       handle = nvkm_namedb_get(nv_namedb(parent), name);
+       if (handle) {
+               nvkm_object_ref(handle->object, &object);
+               nvkm_namedb_put(handle);
+       }
+
+       return object;
+}
+
+struct nvkm_handle *
+nvkm_handle_get_class(struct nvkm_object *engctx, u16 oclass)
+{
+       struct nvkm_namedb *namedb;
+       if (engctx && (namedb = (void *)nv_pclass(engctx, NV_NAMEDB_CLASS)))
+               return nvkm_namedb_get_class(namedb, oclass);
+       return NULL;
+}
+
+struct nvkm_handle *
+nvkm_handle_get_vinst(struct nvkm_object *engctx, u64 vinst)
+{
+       struct nvkm_namedb *namedb;
+       if (engctx && (namedb = (void *)nv_pclass(engctx, NV_NAMEDB_CLASS)))
+               return nvkm_namedb_get_vinst(namedb, vinst);
+       return NULL;
+}
+
+struct nvkm_handle *
+nvkm_handle_get_cinst(struct nvkm_object *engctx, u32 cinst)
+{
+       struct nvkm_namedb *namedb;
+       if (engctx && (namedb = (void *)nv_pclass(engctx, NV_NAMEDB_CLASS)))
+               return nvkm_namedb_get_cinst(namedb, cinst);
+       return NULL;
+}
+
+void
+nvkm_handle_put(struct nvkm_handle *handle)
+{
+       if (handle)
+               nvkm_namedb_put(handle);
+}
diff --git a/drivers/gpu/drm/nouveau/nvkm/core/ioctl.c b/drivers/gpu/drm/nouveau/nvkm/core/ioctl.c
new file mode 100644 (file)
index 0000000..4459ff5
--- /dev/null
@@ -0,0 +1,526 @@
+/*
+ * Copyright 2014 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 <bskeggs@redhat.com>
+ */
+#include <core/ioctl.h>
+#include <core/client.h>
+#include <core/engine.h>
+#include <core/handle.h>
+#include <core/namedb.h>
+
+#include <nvif/unpack.h>
+#include <nvif/ioctl.h>
+
+static int
+nvkm_ioctl_nop(struct nvkm_handle *handle, void *data, u32 size)
+{
+       struct nvkm_object *object = handle->object;
+       union {
+               struct nvif_ioctl_nop none;
+       } *args = data;
+       int ret;
+
+       nv_ioctl(object, "nop size %d\n", size);
+       if (nvif_unvers(args->none)) {
+               nv_ioctl(object, "nop\n");
+       }
+
+       return ret;
+}
+
+static int
+nvkm_ioctl_sclass(struct nvkm_handle *handle, void *data, u32 size)
+{
+       struct nvkm_object *object = handle->object;
+       union {
+               struct nvif_ioctl_sclass_v0 v0;
+       } *args = data;
+       int ret;
+
+       if (!nv_iclass(object, NV_PARENT_CLASS)) {
+               nv_debug(object, "cannot have children (sclass)\n");
+               return -ENODEV;
+       }
+
+       nv_ioctl(object, "sclass size %d\n", size);
+       if (nvif_unpack(args->v0, 0, 0, true)) {
+               nv_ioctl(object, "sclass vers %d count %d\n",
+                        args->v0.version, args->v0.count);
+               if (size == args->v0.count * sizeof(args->v0.oclass[0])) {
+                       ret = nvkm_parent_lclass(object, args->v0.oclass,
+                                                        args->v0.count);
+                       if (ret >= 0) {
+                               args->v0.count = ret;
+                               ret = 0;
+                       }
+               } else {
+                       ret = -EINVAL;
+               }
+       }
+
+       return ret;
+}
+
+static int
+nvkm_ioctl_new(struct nvkm_handle *handle, void *data, u32 size)
+{
+       union {
+               struct nvif_ioctl_new_v0 v0;
+       } *args = data;
+       struct nvkm_client *client = nvkm_client(handle->object);
+       struct nvkm_object *engctx = NULL;
+       struct nvkm_object *object = NULL;
+       struct nvkm_parent *parent;
+       struct nvkm_object *engine;
+       struct nvkm_oclass *oclass;
+       u32 _handle, _oclass;
+       int ret;
+
+       nv_ioctl(client, "new size %d\n", size);
+       if (nvif_unpack(args->v0, 0, 0, true)) {
+               _handle = args->v0.handle;
+               _oclass = args->v0.oclass;
+       } else
+               return ret;
+
+       nv_ioctl(client, "new vers %d handle %08x class %08x "
+                        "route %02x token %llx\n",
+                args->v0.version, _handle, _oclass,
+                args->v0.route, args->v0.token);
+
+       if (!nv_iclass(handle->object, NV_PARENT_CLASS)) {
+               nv_debug(handle->object, "cannot have children (ctor)\n");
+               ret = -ENODEV;
+               goto fail_class;
+       }
+
+       parent = nv_parent(handle->object);
+
+       /* check that parent supports the requested subclass */
+       ret = nvkm_parent_sclass(&parent->object, _oclass, &engine, &oclass);
+       if (ret) {
+               nv_debug(parent, "illegal class 0x%04x\n", _oclass);
+               goto fail_class;
+       }
+
+       /* make sure engine init has been completed *before* any objects
+        * it controls are created - the constructors may depend on
+        * state calculated at init (ie. default context construction)
+        */
+       if (engine) {
+               ret = nvkm_object_inc(engine);
+               if (ret)
+                       goto fail_class;
+       }
+
+       /* if engine requires it, create a context object to insert
+        * between the parent and its children (eg. PGRAPH context)
+        */
+       if (engine && nv_engine(engine)->cclass) {
+               ret = nvkm_object_ctor(&parent->object, engine,
+                                      nv_engine(engine)->cclass,
+                                      data, size, &engctx);
+               if (ret)
+                       goto fail_engctx;
+       } else {
+               nvkm_object_ref(&parent->object, &engctx);
+       }
+
+       /* finally, create new object and bind it to its handle */
+       ret = nvkm_object_ctor(engctx, engine, oclass, data, size, &object);
+       client->data = object;
+       if (ret)
+               goto fail_ctor;
+
+       ret = nvkm_object_inc(object);
+       if (ret)
+               goto fail_init;
+
+       ret = nvkm_handle_create(&parent->object, handle->name,
+                                _handle, object, &handle);
+       if (ret)
+               goto fail_handle;
+
+       ret = nvkm_handle_init(handle);
+       handle->route = args->v0.route;
+       handle->token = args->v0.token;
+       if (ret)
+               nvkm_handle_destroy(handle);
+
+fail_handle:
+       nvkm_object_dec(object, false);
+fail_init:
+       nvkm_object_ref(NULL, &object);
+fail_ctor:
+       nvkm_object_ref(NULL, &engctx);
+fail_engctx:
+       if (engine)
+               nvkm_object_dec(engine, false);
+fail_class:
+       return ret;
+}
+
+static int
+nvkm_ioctl_del(struct nvkm_handle *handle, void *data, u32 size)
+{
+       struct nvkm_object *object = handle->object;
+       union {
+               struct nvif_ioctl_del none;
+       } *args = data;
+       int ret;
+
+       nv_ioctl(object, "delete size %d\n", size);
+       if (nvif_unvers(args->none)) {
+               nv_ioctl(object, "delete\n");
+               nvkm_handle_fini(handle, false);
+               nvkm_handle_destroy(handle);
+       }
+
+       return ret;
+}
+
+static int
+nvkm_ioctl_mthd(struct nvkm_handle *handle, void *data, u32 size)
+{
+       struct nvkm_object *object = handle->object;
+       struct nvkm_ofuncs *ofuncs = object->oclass->ofuncs;
+       union {
+               struct nvif_ioctl_mthd_v0 v0;
+       } *args = data;
+       int ret;
+
+       nv_ioctl(object, "mthd size %d\n", size);
+       if (nvif_unpack(args->v0, 0, 0, true)) {
+               nv_ioctl(object, "mthd vers %d mthd %02x\n",
+                        args->v0.version, args->v0.method);
+               if (ret = -ENODEV, ofuncs->mthd)
+                       ret = ofuncs->mthd(object, args->v0.method, data, size);
+       }
+
+       return ret;
+}
+
+
+static int
+nvkm_ioctl_rd(struct nvkm_handle *handle, void *data, u32 size)
+{
+       struct nvkm_object *object = handle->object;
+       struct nvkm_ofuncs *ofuncs = object->oclass->ofuncs;
+       union {
+               struct nvif_ioctl_rd_v0 v0;
+       } *args = data;
+       int ret;
+
+       nv_ioctl(object, "rd size %d\n", size);
+       if (nvif_unpack(args->v0, 0, 0, false)) {
+               nv_ioctl(object, "rd vers %d size %d addr %016llx\n",
+                        args->v0.version, args->v0.size, args->v0.addr);
+               switch (args->v0.size) {
+               case 1:
+                       if (ret = -ENODEV, ofuncs->rd08) {
+                               args->v0.data = nv_ro08(object, args->v0.addr);
+                               ret = 0;
+                       }
+                       break;
+               case 2:
+                       if (ret = -ENODEV, ofuncs->rd16) {
+                               args->v0.data = nv_ro16(object, args->v0.addr);
+                               ret = 0;
+                       }
+                       break;
+               case 4:
+                       if (ret = -ENODEV, ofuncs->rd32) {
+                               args->v0.data = nv_ro32(object, args->v0.addr);
+                               ret = 0;
+                       }
+                       break;
+               default:
+                       ret = -EINVAL;
+                       break;
+               }
+       }
+
+       return ret;
+}
+
+static int
+nvkm_ioctl_wr(struct nvkm_handle *handle, void *data, u32 size)
+{
+       struct nvkm_object *object = handle->object;
+       struct nvkm_ofuncs *ofuncs = object->oclass->ofuncs;
+       union {
+               struct nvif_ioctl_wr_v0 v0;
+       } *args = data;
+       int ret;
+
+       nv_ioctl(object, "wr size %d\n", size);
+       if (nvif_unpack(args->v0, 0, 0, false)) {
+               nv_ioctl(object, "wr vers %d size %d addr %016llx data %08x\n",
+                        args->v0.version, args->v0.size, args->v0.addr,
+                        args->v0.data);
+               switch (args->v0.size) {
+               case 1:
+                       if (ret = -ENODEV, ofuncs->wr08) {
+                               nv_wo08(object, args->v0.addr, args->v0.data);
+                               ret = 0;
+                       }
+                       break;
+               case 2:
+                       if (ret = -ENODEV, ofuncs->wr16) {
+                               nv_wo16(object, args->v0.addr, args->v0.data);
+                               ret = 0;
+                       }
+                       break;
+               case 4:
+                       if (ret = -ENODEV, ofuncs->wr32) {
+                               nv_wo32(object, args->v0.addr, args->v0.data);
+                               ret = 0;
+                       }
+                       break;
+               default:
+                       ret = -EINVAL;
+                       break;
+               }
+       }
+
+       return ret;
+}
+
+static int
+nvkm_ioctl_map(struct nvkm_handle *handle, void *data, u32 size)
+{
+       struct nvkm_object *object = handle->object;
+       struct nvkm_ofuncs *ofuncs = object->oclass->ofuncs;
+       union {
+               struct nvif_ioctl_map_v0 v0;
+       } *args = data;
+       int ret;
+
+       nv_ioctl(object, "map size %d\n", size);
+       if (nvif_unpack(args->v0, 0, 0, false)) {
+               nv_ioctl(object, "map vers %d\n", args->v0.version);
+               if (ret = -ENODEV, ofuncs->map) {
+                       ret = ofuncs->map(object, &args->v0.handle,
+                                                 &args->v0.length);
+               }
+       }
+
+       return ret;
+}
+
+static int
+nvkm_ioctl_unmap(struct nvkm_handle *handle, void *data, u32 size)
+{
+       struct nvkm_object *object = handle->object;
+       union {
+               struct nvif_ioctl_unmap none;
+       } *args = data;
+       int ret;
+
+       nv_ioctl(object, "unmap size %d\n", size);
+       if (nvif_unvers(args->none)) {
+               nv_ioctl(object, "unmap\n");
+       }
+
+       return ret;
+}
+
+static int
+nvkm_ioctl_ntfy_new(struct nvkm_handle *handle, void *data, u32 size)
+{
+       struct nvkm_object *object = handle->object;
+       struct nvkm_ofuncs *ofuncs = object->oclass->ofuncs;
+       union {
+               struct nvif_ioctl_ntfy_new_v0 v0;
+       } *args = data;
+       struct nvkm_event *event;
+       int ret;
+
+       nv_ioctl(object, "ntfy new size %d\n", size);
+       if (nvif_unpack(args->v0, 0, 0, true)) {
+               nv_ioctl(object, "ntfy new vers %d event %02x\n",
+                        args->v0.version, args->v0.event);
+               if (ret = -ENODEV, ofuncs->ntfy)
+                       ret = ofuncs->ntfy(object, args->v0.event, &event);
+               if (ret == 0) {
+                       ret = nvkm_client_notify_new(object, event, data, size);
+                       if (ret >= 0) {
+                               args->v0.index = ret;
+                               ret = 0;
+                       }
+               }
+       }
+
+       return ret;
+}
+
+static int
+nvkm_ioctl_ntfy_del(struct nvkm_handle *handle, void *data, u32 size)
+{
+       struct nvkm_client *client = nvkm_client(handle->object);
+       struct nvkm_object *object = handle->object;
+       union {
+               struct nvif_ioctl_ntfy_del_v0 v0;
+       } *args = data;
+       int ret;
+
+       nv_ioctl(object, "ntfy del size %d\n", size);
+       if (nvif_unpack(args->v0, 0, 0, false)) {
+               nv_ioctl(object, "ntfy del vers %d index %d\n",
+                        args->v0.version, args->v0.index);
+               ret = nvkm_client_notify_del(client, args->v0.index);
+       }
+
+       return ret;
+}
+
+static int
+nvkm_ioctl_ntfy_get(struct nvkm_handle *handle, void *data, u32 size)
+{
+       struct nvkm_client *client = nvkm_client(handle->object);
+       struct nvkm_object *object = handle->object;
+       union {
+               struct nvif_ioctl_ntfy_get_v0 v0;
+       } *args = data;
+       int ret;
+
+       nv_ioctl(object, "ntfy get size %d\n", size);
+       if (nvif_unpack(args->v0, 0, 0, false)) {
+               nv_ioctl(object, "ntfy get vers %d index %d\n",
+                        args->v0.version, args->v0.index);
+               ret = nvkm_client_notify_get(client, args->v0.index);
+       }
+
+       return ret;
+}
+
+static int
+nvkm_ioctl_ntfy_put(struct nvkm_handle *handle, void *data, u32 size)
+{
+       struct nvkm_client *client = nvkm_client(handle->object);
+       struct nvkm_object *object = handle->object;
+       union {
+               struct nvif_ioctl_ntfy_put_v0 v0;
+       } *args = data;
+       int ret;
+
+       nv_ioctl(object, "ntfy put size %d\n", size);
+       if (nvif_unpack(args->v0, 0, 0, false)) {
+               nv_ioctl(object, "ntfy put vers %d index %d\n",
+                        args->v0.version, args->v0.index);
+               ret = nvkm_client_notify_put(client, args->v0.index);
+       }
+
+       return ret;
+}
+
+static struct {
+       int version;
+       int (*func)(struct nvkm_handle *, void *, u32);
+}
+nvkm_ioctl_v0[] = {
+       { 0x00, nvkm_ioctl_nop },
+       { 0x00, nvkm_ioctl_sclass },
+       { 0x00, nvkm_ioctl_new },
+       { 0x00, nvkm_ioctl_del },
+       { 0x00, nvkm_ioctl_mthd },
+       { 0x00, nvkm_ioctl_rd },
+       { 0x00, nvkm_ioctl_wr },
+       { 0x00, nvkm_ioctl_map },
+       { 0x00, nvkm_ioctl_unmap },
+       { 0x00, nvkm_ioctl_ntfy_new },
+       { 0x00, nvkm_ioctl_ntfy_del },
+       { 0x00, nvkm_ioctl_ntfy_get },
+       { 0x00, nvkm_ioctl_ntfy_put },
+};
+
+static int
+nvkm_ioctl_path(struct nvkm_handle *parent, u32 type, u32 nr, u32 *path,
+               void *data, u32 size, u8 owner, u8 *route, u64 *token)
+{
+       struct nvkm_handle *handle = parent;
+       struct nvkm_namedb *namedb;
+       struct nvkm_object *object;
+       int ret;
+
+       while ((object = parent->object), nr--) {
+               nv_ioctl(object, "path 0x%08x\n", path[nr]);
+               if (!nv_iclass(object, NV_PARENT_CLASS)) {
+                       nv_debug(object, "cannot have children (path)\n");
+                       return -EINVAL;
+               }
+
+               if (!(namedb = (void *)nv_pclass(object, NV_NAMEDB_CLASS)) ||
+                   !(handle = nvkm_namedb_get(namedb, path[nr]))) {
+                       nv_debug(object, "handle 0x%08x not found\n", path[nr]);
+                       return -ENOENT;
+               }
+               nvkm_namedb_put(handle);
+               parent = handle;
+       }
+
+       if (owner != NVIF_IOCTL_V0_OWNER_ANY && owner != handle->route) {
+               nv_ioctl(object, "object route != owner\n");
+               return -EACCES;
+       }
+       *route = handle->route;
+       *token = handle->token;
+
+       if (ret = -EINVAL, type < ARRAY_SIZE(nvkm_ioctl_v0)) {
+               if (nvkm_ioctl_v0[type].version == 0)
+                       ret = nvkm_ioctl_v0[type].func(handle, data, size);
+       }
+
+       return ret;
+}
+
+int
+nvkm_ioctl(struct nvkm_client *client, bool supervisor,
+          void *data, u32 size, void **hack)
+{
+       union {
+               struct nvif_ioctl_v0 v0;
+       } *args = data;
+       int ret;
+
+       client->super = supervisor;
+       nv_ioctl(client, "size %d\n", size);
+
+       if (nvif_unpack(args->v0, 0, 0, true)) {
+               nv_ioctl(client, "vers %d type %02x path %d owner %02x\n",
+                        args->v0.version, args->v0.type, args->v0.path_nr,
+                        args->v0.owner);
+               ret = nvkm_ioctl_path(client->root, args->v0.type,
+                                     args->v0.path_nr, args->v0.path,
+                                     data, size, args->v0.owner,
+                                     &args->v0.route, &args->v0.token);
+       }
+
+       nv_ioctl(client, "return %d\n", ret);
+       if (hack) {
+               *hack = client->data;
+               client->data = NULL;
+       }
+
+       client->super = false;
+       return ret;
+}
diff --git a/drivers/gpu/drm/nouveau/nvkm/core/mm.c b/drivers/gpu/drm/nouveau/nvkm/core/mm.c
new file mode 100644 (file)
index 0000000..7f458df
--- /dev/null
@@ -0,0 +1,304 @@
+/*
+ * Copyright 2012 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 <core/mm.h>
+
+#define node(root, dir) ((root)->nl_entry.dir == &mm->nodes) ? NULL :          \
+       list_entry((root)->nl_entry.dir, struct nvkm_mm_node, nl_entry)
+
+static void
+nvkm_mm_dump(struct nvkm_mm *mm, const char *header)
+{
+       struct nvkm_mm_node *node;
+
+       printk(KERN_ERR "nvkm: %s\n", header);
+       printk(KERN_ERR "nvkm: node list:\n");
+       list_for_each_entry(node, &mm->nodes, nl_entry) {
+               printk(KERN_ERR "nvkm: \t%08x %08x %d\n",
+                      node->offset, node->length, node->type);
+       }
+       printk(KERN_ERR "nvkm: free list:\n");
+       list_for_each_entry(node, &mm->free, fl_entry) {
+               printk(KERN_ERR "nvkm: \t%08x %08x %d\n",
+                      node->offset, node->length, node->type);
+       }
+}
+
+void
+nvkm_mm_free(struct nvkm_mm *mm, struct nvkm_mm_node **pthis)
+{
+       struct nvkm_mm_node *this = *pthis;
+
+       if (this) {
+               struct nvkm_mm_node *prev = node(this, prev);
+               struct nvkm_mm_node *next = node(this, next);
+
+               if (prev && prev->type == NVKM_MM_TYPE_NONE) {
+                       prev->length += this->length;
+                       list_del(&this->nl_entry);
+                       kfree(this); this = prev;
+               }
+
+               if (next && next->type == NVKM_MM_TYPE_NONE) {
+                       next->offset  = this->offset;
+                       next->length += this->length;
+                       if (this->type == NVKM_MM_TYPE_NONE)
+                               list_del(&this->fl_entry);
+                       list_del(&this->nl_entry);
+                       kfree(this); this = NULL;
+               }
+
+               if (this && this->type != NVKM_MM_TYPE_NONE) {
+                       list_for_each_entry(prev, &mm->free, fl_entry) {
+                               if (this->offset < prev->offset)
+                                       break;
+                       }
+
+                       list_add_tail(&this->fl_entry, &prev->fl_entry);
+                       this->type = NVKM_MM_TYPE_NONE;
+               }
+       }
+
+       *pthis = NULL;
+}
+
+static struct nvkm_mm_node *
+region_head(struct nvkm_mm *mm, struct nvkm_mm_node *a, u32 size)
+{
+       struct nvkm_mm_node *b;
+
+       if (a->length == size)
+               return a;
+
+       b = kmalloc(sizeof(*b), GFP_KERNEL);
+       if (unlikely(b == NULL))
+               return NULL;
+
+       b->offset = a->offset;
+       b->length = size;
+       b->heap   = a->heap;
+       b->type   = a->type;
+       a->offset += size;
+       a->length -= size;
+       list_add_tail(&b->nl_entry, &a->nl_entry);
+       if (b->type == NVKM_MM_TYPE_NONE)
+               list_add_tail(&b->fl_entry, &a->fl_entry);
+
+       return b;
+}
+
+int
+nvkm_mm_head(struct nvkm_mm *mm, u8 heap, u8 type, u32 size_max, u32 size_min,
+            u32 align, struct nvkm_mm_node **pnode)
+{
+       struct nvkm_mm_node *prev, *this, *next;
+       u32 mask = align - 1;
+       u32 splitoff;
+       u32 s, e;
+
+       BUG_ON(type == NVKM_MM_TYPE_NONE || type == NVKM_MM_TYPE_HOLE);
+
+       list_for_each_entry(this, &mm->free, fl_entry) {
+               if (unlikely(heap != NVKM_MM_HEAP_ANY)) {
+                       if (this->heap != heap)
+                               continue;
+               }
+               e = this->offset + this->length;
+               s = this->offset;
+
+               prev = node(this, prev);
+               if (prev && prev->type != type)
+                       s = roundup(s, mm->block_size);
+
+               next = node(this, next);
+               if (next && next->type != type)
+                       e = rounddown(e, mm->block_size);
+
+               s  = (s + mask) & ~mask;
+               e &= ~mask;
+               if (s > e || e - s < size_min)
+                       continue;
+
+               splitoff = s - this->offset;
+               if (splitoff && !region_head(mm, this, splitoff))
+                       return -ENOMEM;
+
+               this = region_head(mm, this, min(size_max, e - s));
+               if (!this)
+                       return -ENOMEM;
+
+               this->type = type;
+               list_del(&this->fl_entry);
+               *pnode = this;
+               return 0;
+       }
+
+       return -ENOSPC;
+}
+
+static struct nvkm_mm_node *
+region_tail(struct nvkm_mm *mm, struct nvkm_mm_node *a, u32 size)
+{
+       struct nvkm_mm_node *b;
+
+       if (a->length == size)
+               return a;
+
+       b = kmalloc(sizeof(*b), GFP_KERNEL);
+       if (unlikely(b == NULL))
+               return NULL;
+
+       a->length -= size;
+       b->offset  = a->offset + a->length;
+       b->length  = size;
+       b->heap    = a->heap;
+       b->type    = a->type;
+
+       list_add(&b->nl_entry, &a->nl_entry);
+       if (b->type == NVKM_MM_TYPE_NONE)
+               list_add(&b->fl_entry, &a->fl_entry);
+
+       return b;
+}
+
+int
+nvkm_mm_tail(struct nvkm_mm *mm, u8 heap, u8 type, u32 size_max, u32 size_min,
+            u32 align, struct nvkm_mm_node **pnode)
+{
+       struct nvkm_mm_node *prev, *this, *next;
+       u32 mask = align - 1;
+
+       BUG_ON(type == NVKM_MM_TYPE_NONE || type == NVKM_MM_TYPE_HOLE);
+
+       list_for_each_entry_reverse(this, &mm->free, fl_entry) {
+               u32 e = this->offset + this->length;
+               u32 s = this->offset;
+               u32 c = 0, a;
+               if (unlikely(heap != NVKM_MM_HEAP_ANY)) {
+                       if (this->heap != heap)
+                               continue;
+               }
+
+               prev = node(this, prev);
+               if (prev && prev->type != type)
+                       s = roundup(s, mm->block_size);
+
+               next = node(this, next);
+               if (next && next->type != type) {
+                       e = rounddown(e, mm->block_size);
+                       c = next->offset - e;
+               }
+
+               s = (s + mask) & ~mask;
+               a = e - s;
+               if (s > e || a < size_min)
+                       continue;
+
+               a  = min(a, size_max);
+               s  = (e - a) & ~mask;
+               c += (e - s) - a;
+
+               if (c && !region_tail(mm, this, c))
+                       return -ENOMEM;
+
+               this = region_tail(mm, this, a);
+               if (!this)
+                       return -ENOMEM;
+
+               this->type = type;
+               list_del(&this->fl_entry);
+               *pnode = this;
+               return 0;
+       }
+
+       return -ENOSPC;
+}
+
+int
+nvkm_mm_init(struct nvkm_mm *mm, u32 offset, u32 length, u32 block)
+{
+       struct nvkm_mm_node *node, *prev;
+       u32 next;
+
+       if (nvkm_mm_initialised(mm)) {
+               prev = list_last_entry(&mm->nodes, typeof(*node), nl_entry);
+               next = prev->offset + prev->length;
+               if (next != offset) {
+                       BUG_ON(next > offset);
+                       if (!(node = kzalloc(sizeof(*node), GFP_KERNEL)))
+                               return -ENOMEM;
+                       node->type   = NVKM_MM_TYPE_HOLE;
+                       node->offset = next;
+                       node->length = offset - next;
+                       list_add_tail(&node->nl_entry, &mm->nodes);
+               }
+               BUG_ON(block != mm->block_size);
+       } else {
+               INIT_LIST_HEAD(&mm->nodes);
+               INIT_LIST_HEAD(&mm->free);
+               mm->block_size = block;
+               mm->heap_nodes = 0;
+       }
+
+       node = kzalloc(sizeof(*node), GFP_KERNEL);
+       if (!node)
+               return -ENOMEM;
+
+       if (length) {
+               node->offset  = roundup(offset, mm->block_size);
+               node->length  = rounddown(offset + length, mm->block_size);
+               node->length -= node->offset;
+       }
+
+       list_add_tail(&node->nl_entry, &mm->nodes);
+       list_add_tail(&node->fl_entry, &mm->free);
+       node->heap = ++mm->heap_nodes;
+       return 0;
+}
+
+int
+nvkm_mm_fini(struct nvkm_mm *mm)
+{
+       struct nvkm_mm_node *node, *temp;
+       int nodes = 0;
+
+       if (!nvkm_mm_initialised(mm))
+               return 0;
+
+       list_for_each_entry(node, &mm->nodes, nl_entry) {
+               if (node->type != NVKM_MM_TYPE_HOLE) {
+                       if (++nodes > mm->heap_nodes) {
+                               nvkm_mm_dump(mm, "mm not clean!");
+                               return -EBUSY;
+                       }
+               }
+       }
+
+       list_for_each_entry_safe(node, temp, &mm->nodes, nl_entry) {
+               list_del(&node->nl_entry);
+               kfree(node);
+       }
+
+       mm->heap_nodes = 0;
+       return 0;
+}
diff --git a/drivers/gpu/drm/nouveau/nvkm/core/namedb.c b/drivers/gpu/drm/nouveau/nvkm/core/namedb.c
new file mode 100644 (file)
index 0000000..6400767
--- /dev/null
@@ -0,0 +1,199 @@
+/*
+ * Copyright 2012 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 <core/namedb.h>
+#include <core/gpuobj.h>
+#include <core/handle.h>
+
+static struct nvkm_handle *
+nvkm_namedb_lookup(struct nvkm_namedb *namedb, u32 name)
+{
+       struct nvkm_handle *handle;
+
+       list_for_each_entry(handle, &namedb->list, node) {
+               if (handle->name == name)
+                       return handle;
+       }
+
+       return NULL;
+}
+
+static struct nvkm_handle *
+nvkm_namedb_lookup_class(struct nvkm_namedb *namedb, u16 oclass)
+{
+       struct nvkm_handle *handle;
+
+       list_for_each_entry(handle, &namedb->list, node) {
+               if (nv_mclass(handle->object) == oclass)
+                       return handle;
+       }
+
+       return NULL;
+}
+
+static struct nvkm_handle *
+nvkm_namedb_lookup_vinst(struct nvkm_namedb *namedb, u64 vinst)
+{
+       struct nvkm_handle *handle;
+
+       list_for_each_entry(handle, &namedb->list, node) {
+               if (nv_iclass(handle->object, NV_GPUOBJ_CLASS)) {
+                       if (nv_gpuobj(handle->object)->addr == vinst)
+                               return handle;
+               }
+       }
+
+       return NULL;
+}
+
+static struct nvkm_handle *
+nvkm_namedb_lookup_cinst(struct nvkm_namedb *namedb, u32 cinst)
+{
+       struct nvkm_handle *handle;
+
+       list_for_each_entry(handle, &namedb->list, node) {
+               if (nv_iclass(handle->object, NV_GPUOBJ_CLASS)) {
+                       if (nv_gpuobj(handle->object)->node &&
+                           nv_gpuobj(handle->object)->node->offset == cinst)
+                               return handle;
+               }
+       }
+
+       return NULL;
+}
+
+int
+nvkm_namedb_insert(struct nvkm_namedb *namedb, u32 name,
+                  struct nvkm_object *object,
+                  struct nvkm_handle *handle)
+{
+       int ret = -EEXIST;
+       write_lock_irq(&namedb->lock);
+       if (!nvkm_namedb_lookup(namedb, name)) {
+               nvkm_object_ref(object, &handle->object);
+               handle->namedb = namedb;
+               list_add(&handle->node, &namedb->list);
+               ret = 0;
+       }
+       write_unlock_irq(&namedb->lock);
+       return ret;
+}
+
+void
+nvkm_namedb_remove(struct nvkm_handle *handle)
+{
+       struct nvkm_namedb *namedb = handle->namedb;
+       struct nvkm_object *object = handle->object;
+       write_lock_irq(&namedb->lock);
+       list_del(&handle->node);
+       write_unlock_irq(&namedb->lock);
+       nvkm_object_ref(NULL, &object);
+}
+
+struct nvkm_handle *
+nvkm_namedb_get(struct nvkm_namedb *namedb, u32 name)
+{
+       struct nvkm_handle *handle;
+       read_lock(&namedb->lock);
+       handle = nvkm_namedb_lookup(namedb, name);
+       if (handle == NULL)
+               read_unlock(&namedb->lock);
+       return handle;
+}
+
+struct nvkm_handle *
+nvkm_namedb_get_class(struct nvkm_namedb *namedb, u16 oclass)
+{
+       struct nvkm_handle *handle;
+       read_lock(&namedb->lock);
+       handle = nvkm_namedb_lookup_class(namedb, oclass);
+       if (handle == NULL)
+               read_unlock(&namedb->lock);
+       return handle;
+}
+
+struct nvkm_handle *
+nvkm_namedb_get_vinst(struct nvkm_namedb *namedb, u64 vinst)
+{
+       struct nvkm_handle *handle;
+       read_lock(&namedb->lock);
+       handle = nvkm_namedb_lookup_vinst(namedb, vinst);
+       if (handle == NULL)
+               read_unlock(&namedb->lock);
+       return handle;
+}
+
+struct nvkm_handle *
+nvkm_namedb_get_cinst(struct nvkm_namedb *namedb, u32 cinst)
+{
+       struct nvkm_handle *handle;
+       read_lock(&namedb->lock);
+       handle = nvkm_namedb_lookup_cinst(namedb, cinst);
+       if (handle == NULL)
+               read_unlock(&namedb->lock);
+       return handle;
+}
+
+void
+nvkm_namedb_put(struct nvkm_handle *handle)
+{
+       if (handle)
+               read_unlock(&handle->namedb->lock);
+}
+
+int
+nvkm_namedb_create_(struct nvkm_object *parent, struct nvkm_object *engine,
+                   struct nvkm_oclass *oclass, u32 pclass,
+                   struct nvkm_oclass *sclass, u64 engcls,
+                   int length, void **pobject)
+{
+       struct nvkm_namedb *namedb;
+       int ret;
+
+       ret = nvkm_parent_create_(parent, engine, oclass, pclass |
+                                 NV_NAMEDB_CLASS, sclass, engcls,
+                                 length, pobject);
+       namedb = *pobject;
+       if (ret)
+               return ret;
+
+       rwlock_init(&namedb->lock);
+       INIT_LIST_HEAD(&namedb->list);
+       return 0;
+}
+
+int
+_nvkm_namedb_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+                 struct nvkm_oclass *oclass, void *data, u32 size,
+                 struct nvkm_object **pobject)
+{
+       struct nvkm_namedb *object;
+       int ret;
+
+       ret = nvkm_namedb_create(parent, engine, oclass, 0, NULL, 0, &object);
+       *pobject = nv_object(object);
+       if (ret)
+               return ret;
+
+       return 0;
+}
diff --git a/drivers/gpu/drm/nouveau/nvkm/core/notify.c b/drivers/gpu/drm/nouveau/nvkm/core/notify.c
new file mode 100644 (file)
index 0000000..023610d
--- /dev/null
@@ -0,0 +1,163 @@
+/*
+ * Copyright 2014 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 <bskeggs@redhat.com>
+ */
+#include <core/notify.h>
+#include <core/event.h>
+
+static inline void
+nvkm_notify_put_locked(struct nvkm_notify *notify)
+{
+       if (notify->block++ == 0)
+               nvkm_event_put(notify->event, notify->types, notify->index);
+}
+
+void
+nvkm_notify_put(struct nvkm_notify *notify)
+{
+       struct nvkm_event *event = notify->event;
+       unsigned long flags;
+       if (likely(event) &&
+           test_and_clear_bit(NVKM_NOTIFY_USER, &notify->flags)) {
+               spin_lock_irqsave(&event->refs_lock, flags);
+               nvkm_notify_put_locked(notify);
+               spin_unlock_irqrestore(&event->refs_lock, flags);
+               if (test_bit(NVKM_NOTIFY_WORK, &notify->flags))
+                       flush_work(&notify->work);
+       }
+}
+
+static inline void
+nvkm_notify_get_locked(struct nvkm_notify *notify)
+{
+       if (--notify->block == 0)
+               nvkm_event_get(notify->event, notify->types, notify->index);
+}
+
+void
+nvkm_notify_get(struct nvkm_notify *notify)
+{
+       struct nvkm_event *event = notify->event;
+       unsigned long flags;
+       if (likely(event) &&
+           !test_and_set_bit(NVKM_NOTIFY_USER, &notify->flags)) {
+               spin_lock_irqsave(&event->refs_lock, flags);
+               nvkm_notify_get_locked(notify);
+               spin_unlock_irqrestore(&event->refs_lock, flags);
+       }
+}
+
+static inline void
+nvkm_notify_func(struct nvkm_notify *notify)
+{
+       struct nvkm_event *event = notify->event;
+       int ret = notify->func(notify);
+       unsigned long flags;
+       if ((ret == NVKM_NOTIFY_KEEP) ||
+           !test_and_clear_bit(NVKM_NOTIFY_USER, &notify->flags)) {
+               spin_lock_irqsave(&event->refs_lock, flags);
+               nvkm_notify_get_locked(notify);
+               spin_unlock_irqrestore(&event->refs_lock, flags);
+       }
+}
+
+static void
+nvkm_notify_work(struct work_struct *work)
+{
+       struct nvkm_notify *notify = container_of(work, typeof(*notify), work);
+       nvkm_notify_func(notify);
+}
+
+void
+nvkm_notify_send(struct nvkm_notify *notify, void *data, u32 size)
+{
+       struct nvkm_event *event = notify->event;
+       unsigned long flags;
+
+       assert_spin_locked(&event->list_lock);
+       BUG_ON(size != notify->size);
+
+       spin_lock_irqsave(&event->refs_lock, flags);
+       if (notify->block) {
+               spin_unlock_irqrestore(&event->refs_lock, flags);
+               return;
+       }
+       nvkm_notify_put_locked(notify);
+       spin_unlock_irqrestore(&event->refs_lock, flags);
+
+       if (test_bit(NVKM_NOTIFY_WORK, &notify->flags)) {
+               memcpy((void *)notify->data, data, size);
+               schedule_work(&notify->work);
+       } else {
+               notify->data = data;
+               nvkm_notify_func(notify);
+               notify->data = NULL;
+       }
+}
+
+void
+nvkm_notify_fini(struct nvkm_notify *notify)
+{
+       unsigned long flags;
+       if (notify->event) {
+               nvkm_notify_put(notify);
+               spin_lock_irqsave(&notify->event->list_lock, flags);
+               list_del(&notify->head);
+               spin_unlock_irqrestore(&notify->event->list_lock, flags);
+               kfree((void *)notify->data);
+               notify->event = NULL;
+       }
+}
+
+int
+nvkm_notify_init(struct nvkm_object *object, struct nvkm_event *event,
+                int (*func)(struct nvkm_notify *), bool work,
+                void *data, u32 size, u32 reply,
+                struct nvkm_notify *notify)
+{
+       unsigned long flags;
+       int ret = -ENODEV;
+       if ((notify->event = event), event->refs) {
+               ret = event->func->ctor(object, data, size, notify);
+               if (ret == 0 && (ret = -EINVAL, notify->size == reply)) {
+                       notify->flags = 0;
+                       notify->block = 1;
+                       notify->func = func;
+                       notify->data = NULL;
+                       if (ret = 0, work) {
+                               INIT_WORK(&notify->work, nvkm_notify_work);
+                               set_bit(NVKM_NOTIFY_WORK, &notify->flags);
+                               notify->data = kmalloc(reply, GFP_KERNEL);
+                               if (!notify->data)
+                                       ret = -ENOMEM;
+                       }
+               }
+               if (ret == 0) {
+                       spin_lock_irqsave(&event->list_lock, flags);
+                       list_add_tail(&notify->head, &event->list);
+                       spin_unlock_irqrestore(&event->list_lock, flags);
+               }
+       }
+       if (ret)
+               notify->event = NULL;
+       return ret;
+}
diff --git a/drivers/gpu/drm/nouveau/nvkm/core/object.c b/drivers/gpu/drm/nouveau/nvkm/core/object.c
new file mode 100644 (file)
index 0000000..979f362
--- /dev/null
@@ -0,0 +1,330 @@
+/*
+ * Copyright 2012 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 <core/object.h>
+#include <core/engine.h>
+
+#ifdef NVKM_OBJECT_MAGIC
+static struct list_head _objlist = LIST_HEAD_INIT(_objlist);
+static DEFINE_SPINLOCK(_objlist_lock);
+#endif
+
+int
+nvkm_object_create_(struct nvkm_object *parent, struct nvkm_object *engine,
+                   struct nvkm_oclass *oclass, u32 pclass,
+                   int size, void **pobject)
+{
+       struct nvkm_object *object;
+
+       object = *pobject = kzalloc(size, GFP_KERNEL);
+       if (!object)
+               return -ENOMEM;
+
+       nvkm_object_ref(parent, &object->parent);
+       nvkm_object_ref(engine, (struct nvkm_object **)&object->engine);
+       object->oclass = oclass;
+       object->oclass->handle |= pclass;
+       atomic_set(&object->refcount, 1);
+       atomic_set(&object->usecount, 0);
+
+#ifdef NVKM_OBJECT_MAGIC
+       object->_magic = NVKM_OBJECT_MAGIC;
+       spin_lock(&_objlist_lock);
+       list_add(&object->list, &_objlist);
+       spin_unlock(&_objlist_lock);
+#endif
+       return 0;
+}
+
+int
+_nvkm_object_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+                 struct nvkm_oclass *oclass, void *data, u32 size,
+                 struct nvkm_object **pobject)
+{
+       if (size != 0)
+               return -ENOSYS;
+       return nvkm_object_create(parent, engine, oclass, 0, pobject);
+}
+
+void
+nvkm_object_destroy(struct nvkm_object *object)
+{
+#ifdef NVKM_OBJECT_MAGIC
+       spin_lock(&_objlist_lock);
+       list_del(&object->list);
+       spin_unlock(&_objlist_lock);
+#endif
+       nvkm_object_ref(NULL, (struct nvkm_object **)&object->engine);
+       nvkm_object_ref(NULL, &object->parent);
+       kfree(object);
+}
+
+int
+nvkm_object_init(struct nvkm_object *object)
+{
+       return 0;
+}
+
+int
+nvkm_object_fini(struct nvkm_object *object, bool suspend)
+{
+       return 0;
+}
+
+struct nvkm_ofuncs
+nvkm_object_ofuncs = {
+       .ctor = _nvkm_object_ctor,
+       .dtor = nvkm_object_destroy,
+       .init = nvkm_object_init,
+       .fini = nvkm_object_fini,
+};
+
+int
+nvkm_object_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+                struct nvkm_oclass *oclass, void *data, u32 size,
+                struct nvkm_object **pobject)
+{
+       struct nvkm_ofuncs *ofuncs = oclass->ofuncs;
+       struct nvkm_object *object = NULL;
+       int ret;
+
+       ret = ofuncs->ctor(parent, engine, oclass, data, size, &object);
+       *pobject = object;
+       if (ret < 0) {
+               if (ret != -ENODEV) {
+                       nv_error(parent, "failed to create 0x%08x, %d\n",
+                                oclass->handle, ret);
+               }
+
+               if (object) {
+                       ofuncs->dtor(object);
+                       *pobject = NULL;
+               }
+
+               return ret;
+       }
+
+       if (ret == 0) {
+               nv_trace(object, "created\n");
+               atomic_set(&object->refcount, 1);
+       }
+
+       return 0;
+}
+
+static void
+nvkm_object_dtor(struct nvkm_object *object)
+{
+       nv_trace(object, "destroying\n");
+       nv_ofuncs(object)->dtor(object);
+}
+
+void
+nvkm_object_ref(struct nvkm_object *obj, struct nvkm_object **ref)
+{
+       if (obj) {
+               atomic_inc(&obj->refcount);
+               nv_trace(obj, "inc() == %d\n", atomic_read(&obj->refcount));
+       }
+
+       if (*ref) {
+               int dead = atomic_dec_and_test(&(*ref)->refcount);
+               nv_trace(*ref, "dec() == %d\n", atomic_read(&(*ref)->refcount));
+               if (dead)
+                       nvkm_object_dtor(*ref);
+       }
+
+       *ref = obj;
+}
+
+int
+nvkm_object_inc(struct nvkm_object *object)
+{
+       int ref = atomic_add_return(1, &object->usecount);
+       int ret;
+
+       nv_trace(object, "use(+1) == %d\n", atomic_read(&object->usecount));
+       if (ref != 1)
+               return 0;
+
+       nv_trace(object, "initialising...\n");
+       if (object->parent) {
+               ret = nvkm_object_inc(object->parent);
+               if (ret) {
+                       nv_error(object, "parent failed, %d\n", ret);
+                       goto fail_parent;
+               }
+       }
+
+       if (object->engine) {
+               mutex_lock(&nv_subdev(object->engine)->mutex);
+               ret = nvkm_object_inc(&object->engine->subdev.object);
+               mutex_unlock(&nv_subdev(object->engine)->mutex);
+               if (ret) {
+                       nv_error(object, "engine failed, %d\n", ret);
+                       goto fail_engine;
+               }
+       }
+
+       ret = nv_ofuncs(object)->init(object);
+       atomic_set(&object->usecount, 1);
+       if (ret) {
+               nv_error(object, "init failed, %d\n", ret);
+               goto fail_self;
+       }
+
+       nv_trace(object, "initialised\n");
+       return 0;
+
+fail_self:
+       if (object->engine) {
+               mutex_lock(&nv_subdev(object->engine)->mutex);
+               nvkm_object_dec(&object->engine->subdev.object, false);
+               mutex_unlock(&nv_subdev(object->engine)->mutex);
+       }
+fail_engine:
+       if (object->parent)
+                nvkm_object_dec(object->parent, false);
+fail_parent:
+       atomic_dec(&object->usecount);
+       return ret;
+}
+
+static int
+nvkm_object_decf(struct nvkm_object *object)
+{
+       int ret;
+
+       nv_trace(object, "stopping...\n");
+
+       ret = nv_ofuncs(object)->fini(object, false);
+       atomic_set(&object->usecount, 0);
+       if (ret)
+               nv_warn(object, "failed fini, %d\n", ret);
+
+       if (object->engine) {
+               mutex_lock(&nv_subdev(object->engine)->mutex);
+               nvkm_object_dec(&object->engine->subdev.object, false);
+               mutex_unlock(&nv_subdev(object->engine)->mutex);
+       }
+
+       if (object->parent)
+               nvkm_object_dec(object->parent, false);
+
+       nv_trace(object, "stopped\n");
+       return 0;
+}
+
+static int
+nvkm_object_decs(struct nvkm_object *object)
+{
+       int ret, rret;
+
+       nv_trace(object, "suspending...\n");
+
+       ret = nv_ofuncs(object)->fini(object, true);
+       atomic_set(&object->usecount, 0);
+       if (ret) {
+               nv_error(object, "failed suspend, %d\n", ret);
+               return ret;
+       }
+
+       if (object->engine) {
+               mutex_lock(&nv_subdev(object->engine)->mutex);
+               ret = nvkm_object_dec(&object->engine->subdev.object, true);
+               mutex_unlock(&nv_subdev(object->engine)->mutex);
+               if (ret) {
+                       nv_warn(object, "engine failed suspend, %d\n", ret);
+                       goto fail_engine;
+               }
+       }
+
+       if (object->parent) {
+               ret = nvkm_object_dec(object->parent, true);
+               if (ret) {
+                       nv_warn(object, "parent failed suspend, %d\n", ret);
+                       goto fail_parent;
+               }
+       }
+
+       nv_trace(object, "suspended\n");
+       return 0;
+
+fail_parent:
+       if (object->engine) {
+               mutex_lock(&nv_subdev(object->engine)->mutex);
+               rret = nvkm_object_inc(&object->engine->subdev.object);
+               mutex_unlock(&nv_subdev(object->engine)->mutex);
+               if (rret)
+                       nv_fatal(object, "engine failed to reinit, %d\n", rret);
+       }
+
+fail_engine:
+       rret = nv_ofuncs(object)->init(object);
+       if (rret)
+               nv_fatal(object, "failed to reinit, %d\n", rret);
+
+       return ret;
+}
+
+int
+nvkm_object_dec(struct nvkm_object *object, bool suspend)
+{
+       int ref = atomic_add_return(-1, &object->usecount);
+       int ret;
+
+       nv_trace(object, "use(-1) == %d\n", atomic_read(&object->usecount));
+
+       if (ref == 0) {
+               if (suspend)
+                       ret = nvkm_object_decs(object);
+               else
+                       ret = nvkm_object_decf(object);
+
+               if (ret) {
+                       atomic_inc(&object->usecount);
+                       return ret;
+               }
+       }
+
+       return 0;
+}
+
+void
+nvkm_object_debug(void)
+{
+#ifdef NVKM_OBJECT_MAGIC
+       struct nvkm_object *object;
+       if (!list_empty(&_objlist)) {
+               nv_fatal(NULL, "*******************************************\n");
+               nv_fatal(NULL, "* AIIIII! object(s) still exist!!!\n");
+               nv_fatal(NULL, "*******************************************\n");
+               list_for_each_entry(object, &_objlist, list) {
+                       nv_fatal(object, "%p/%p/%d/%d\n",
+                                object->parent, object->engine,
+                                atomic_read(&object->refcount),
+                                atomic_read(&object->usecount));
+               }
+       }
+#endif
+}
diff --git a/drivers/gpu/drm/nouveau/nvkm/core/option.c b/drivers/gpu/drm/nouveau/nvkm/core/option.c
new file mode 100644 (file)
index 0000000..19d153f
--- /dev/null
@@ -0,0 +1,121 @@
+/*
+ * Copyright 2012 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 <core/option.h>
+#include <core/debug.h>
+
+const char *
+nvkm_stropt(const char *optstr, const char *opt, int *arglen)
+{
+       while (optstr && *optstr != '\0') {
+               int len = strcspn(optstr, ",=");
+               switch (optstr[len]) {
+               case '=':
+                       if (!strncasecmpz(optstr, opt, len)) {
+                               optstr += len + 1;
+                               *arglen = strcspn(optstr, ",=");
+                               return *arglen ? optstr : NULL;
+                       }
+                       optstr++;
+                       break;
+               case ',':
+                       optstr++;
+                       break;
+               default:
+                       break;
+               }
+               optstr += len;
+       }
+
+       return NULL;
+}
+
+bool
+nvkm_boolopt(const char *optstr, const char *opt, bool value)
+{
+       int arglen;
+
+       optstr = nvkm_stropt(optstr, opt, &arglen);
+       if (optstr) {
+               if (!strncasecmpz(optstr, "0", arglen) ||
+                   !strncasecmpz(optstr, "no", arglen) ||
+                   !strncasecmpz(optstr, "off", arglen) ||
+                   !strncasecmpz(optstr, "false", arglen))
+                       value = false;
+               else
+               if (!strncasecmpz(optstr, "1", arglen) ||
+                   !strncasecmpz(optstr, "yes", arglen) ||
+                   !strncasecmpz(optstr, "on", arglen) ||
+                   !strncasecmpz(optstr, "true", arglen))
+                       value = true;
+       }
+
+       return value;
+}
+
+int
+nvkm_dbgopt(const char *optstr, const char *sub)
+{
+       int mode = 1, level = CONFIG_NOUVEAU_DEBUG_DEFAULT;
+
+       while (optstr) {
+               int len = strcspn(optstr, ",=");
+               switch (optstr[len]) {
+               case '=':
+                       if (strncasecmpz(optstr, sub, len))
+                               mode = 0;
+                       optstr++;
+                       break;
+               default:
+                       if (mode) {
+                               if (!strncasecmpz(optstr, "fatal", len))
+                                       level = NV_DBG_FATAL;
+                               else if (!strncasecmpz(optstr, "error", len))
+                                       level = NV_DBG_ERROR;
+                               else if (!strncasecmpz(optstr, "warn", len))
+                                       level = NV_DBG_WARN;
+                               else if (!strncasecmpz(optstr, "info", len))
+                                       level = NV_DBG_INFO_NORMAL;
+                               else if (!strncasecmpz(optstr, "debug", len))
+                                       level = NV_DBG_DEBUG;
+                               else if (!strncasecmpz(optstr, "trace", len))
+                                       level = NV_DBG_TRACE;
+                               else if (!strncasecmpz(optstr, "paranoia", len))
+                                       level = NV_DBG_PARANOIA;
+                               else if (!strncasecmpz(optstr, "spam", len))
+                                       level = NV_DBG_SPAM;
+                       }
+
+                       if (optstr[len] != '\0') {
+                               optstr++;
+                               mode = 1;
+                               break;
+                       }
+
+                       return level;
+               }
+               optstr += len;
+       }
+
+       return level;
+}
diff --git a/drivers/gpu/drm/nouveau/nvkm/core/parent.c b/drivers/gpu/drm/nouveau/nvkm/core/parent.c
new file mode 100644 (file)
index 0000000..dd56cd1
--- /dev/null
@@ -0,0 +1,159 @@
+/*
+ * Copyright 2012 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 <core/parent.h>
+#include <core/client.h>
+#include <core/engine.h>
+
+int
+nvkm_parent_sclass(struct nvkm_object *parent, u16 handle,
+                  struct nvkm_object **pengine,
+                  struct nvkm_oclass **poclass)
+{
+       struct nvkm_sclass *sclass;
+       struct nvkm_engine *engine;
+       struct nvkm_oclass *oclass;
+       u64 mask;
+
+       sclass = nv_parent(parent)->sclass;
+       while (sclass) {
+               if ((sclass->oclass->handle & 0xffff) == handle) {
+                       *pengine = &parent->engine->subdev.object;
+                       *poclass = sclass->oclass;
+                       return 0;
+               }
+
+               sclass = sclass->sclass;
+       }
+
+       mask = nv_parent(parent)->engine;
+       while (mask) {
+               int i = __ffs64(mask);
+
+               if (nv_iclass(parent, NV_CLIENT_CLASS))
+                       engine = nv_engine(nv_client(parent)->device);
+               else
+                       engine = nvkm_engine(parent, i);
+
+               if (engine) {
+                       oclass = engine->sclass;
+                       while (oclass->ofuncs) {
+                               if ((oclass->handle & 0xffff) == handle) {
+                                       *pengine = nv_object(engine);
+                                       *poclass = oclass;
+                                       return 0;
+                               }
+                               oclass++;
+                       }
+               }
+
+               mask &= ~(1ULL << i);
+       }
+
+       return -EINVAL;
+}
+
+int
+nvkm_parent_lclass(struct nvkm_object *parent, u32 *lclass, int size)
+{
+       struct nvkm_sclass *sclass;
+       struct nvkm_engine *engine;
+       struct nvkm_oclass *oclass;
+       int nr = -1, i;
+       u64 mask;
+
+       sclass = nv_parent(parent)->sclass;
+       while (sclass) {
+               if (++nr < size)
+                       lclass[nr] = sclass->oclass->handle & 0xffff;
+               sclass = sclass->sclass;
+       }
+
+       mask = nv_parent(parent)->engine;
+       while (i = __ffs64(mask), mask) {
+               engine = nvkm_engine(parent, i);
+               if (engine && (oclass = engine->sclass)) {
+                       while (oclass->ofuncs) {
+                               if (++nr < size)
+                                       lclass[nr] = oclass->handle & 0xffff;
+                               oclass++;
+                       }
+               }
+
+               mask &= ~(1ULL << i);
+       }
+
+       return nr + 1;
+}
+
+int
+nvkm_parent_create_(struct nvkm_object *parent, struct nvkm_object *engine,
+                   struct nvkm_oclass *oclass, u32 pclass,
+                   struct nvkm_oclass *sclass, u64 engcls,
+                   int size, void **pobject)
+{
+       struct nvkm_parent *object;
+       struct nvkm_sclass *nclass;
+       int ret;
+
+       ret = nvkm_object_create_(parent, engine, oclass, pclass |
+                                 NV_PARENT_CLASS, size, pobject);
+       object = *pobject;
+       if (ret)
+               return ret;
+
+       while (sclass && sclass->ofuncs) {
+               nclass = kzalloc(sizeof(*nclass), GFP_KERNEL);
+               if (!nclass)
+                       return -ENOMEM;
+
+               nclass->sclass = object->sclass;
+               object->sclass = nclass;
+               nclass->engine = engine ? nv_engine(engine) : NULL;
+               nclass->oclass = sclass;
+               sclass++;
+       }
+
+       object->engine = engcls;
+       return 0;
+}
+
+void
+nvkm_parent_destroy(struct nvkm_parent *parent)
+{
+       struct nvkm_sclass *sclass;
+
+       while ((sclass = parent->sclass)) {
+               parent->sclass = sclass->sclass;
+               kfree(sclass);
+       }
+
+       nvkm_object_destroy(&parent->object);
+}
+
+
+void
+_nvkm_parent_dtor(struct nvkm_object *object)
+{
+       nvkm_parent_destroy(nv_parent(object));
+}
diff --git a/drivers/gpu/drm/nouveau/nvkm/core/printk.c b/drivers/gpu/drm/nouveau/nvkm/core/printk.c
new file mode 100644 (file)
index 0000000..4a220eb
--- /dev/null
@@ -0,0 +1,103 @@
+/*
+ * Copyright 2012 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 <core/printk.h>
+#include <core/client.h>
+#include <core/device.h>
+
+int nv_info_debug_level = NV_DBG_INFO_NORMAL;
+
+void
+nv_printk_(struct nvkm_object *object, int level, const char *fmt, ...)
+{
+       static const char name[] = { '!', 'E', 'W', ' ', 'D', 'T', 'P', 'S' };
+       const char *pfx;
+       char mfmt[256];
+       va_list args;
+
+       switch (level) {
+       case NV_DBG_FATAL:
+               pfx = KERN_CRIT;
+               break;
+       case NV_DBG_ERROR:
+               pfx = KERN_ERR;
+               break;
+       case NV_DBG_WARN:
+               pfx = KERN_WARNING;
+               break;
+       case NV_DBG_INFO_NORMAL:
+               pfx = KERN_INFO;
+               break;
+       case NV_DBG_DEBUG:
+       case NV_DBG_PARANOIA:
+       case NV_DBG_TRACE:
+       case NV_DBG_SPAM:
+       default:
+               pfx = KERN_DEBUG;
+               break;
+       }
+
+       if (object && !nv_iclass(object, NV_CLIENT_CLASS)) {
+               struct nvkm_object *device;
+               struct nvkm_object *subdev;
+               char obuf[64], *ofmt = "";
+
+               if (object->engine == NULL) {
+                       subdev = object;
+                       while (subdev && !nv_iclass(subdev, NV_SUBDEV_CLASS))
+                               subdev = subdev->parent;
+               } else {
+                       subdev = &object->engine->subdev.object;
+               }
+
+               device = subdev;
+               if (device->parent)
+                       device = device->parent;
+
+               if (object != subdev) {
+                       snprintf(obuf, sizeof(obuf), "[0x%08x]",
+                                nv_hclass(object));
+                       ofmt = obuf;
+               }
+
+               if (level > nv_subdev(subdev)->debug)
+                       return;
+
+               snprintf(mfmt, sizeof(mfmt), "%snouveau %c[%8s][%s]%s %s", pfx,
+                        name[level], nv_subdev(subdev)->name,
+                        nv_device(device)->name, ofmt, fmt);
+       } else
+       if (object && nv_iclass(object, NV_CLIENT_CLASS)) {
+               if (level > nv_client(object)->debug)
+                       return;
+
+               snprintf(mfmt, sizeof(mfmt), "%snouveau %c[%8s] %s", pfx,
+                        name[level], nv_client(object)->name, fmt);
+       } else {
+               snprintf(mfmt, sizeof(mfmt), "%snouveau: %s", pfx, fmt);
+       }
+
+       va_start(args, fmt);
+       vprintk(mfmt, args);
+       va_end(args);
+}
diff --git a/drivers/gpu/drm/nouveau/nvkm/core/ramht.c b/drivers/gpu/drm/nouveau/nvkm/core/ramht.c
new file mode 100644 (file)
index 0000000..ebd4d15
--- /dev/null
@@ -0,0 +1,106 @@
+/*
+ * Copyright 2012 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.
+ */
+#include <core/ramht.h>
+#include <core/engine.h>
+
+#include <subdev/bar.h>
+
+static u32
+nvkm_ramht_hash(struct nvkm_ramht *ramht, int chid, u32 handle)
+{
+       u32 hash = 0;
+
+       while (handle) {
+               hash ^= (handle & ((1 << ramht->bits) - 1));
+               handle >>= ramht->bits;
+       }
+
+       hash ^= chid << (ramht->bits - 4);
+       hash  = hash << 3;
+       return hash;
+}
+
+int
+nvkm_ramht_insert(struct nvkm_ramht *ramht, int chid, u32 handle, u32 context)
+{
+       struct nvkm_bar *bar = nvkm_bar(ramht);
+       u32 co, ho;
+
+       co = ho = nvkm_ramht_hash(ramht, chid, handle);
+       do {
+               if (!nv_ro32(ramht, co + 4)) {
+                       nv_wo32(ramht, co + 0, handle);
+                       nv_wo32(ramht, co + 4, context);
+                       if (bar)
+                               bar->flush(bar);
+                       return co;
+               }
+
+               co += 8;
+               if (co >= nv_gpuobj(ramht)->size)
+                       co = 0;
+       } while (co != ho);
+
+       return -ENOMEM;
+}
+
+void
+nvkm_ramht_remove(struct nvkm_ramht *ramht, int cookie)
+{
+       struct nvkm_bar *bar = nvkm_bar(ramht);
+       nv_wo32(ramht, cookie + 0, 0x00000000);
+       nv_wo32(ramht, cookie + 4, 0x00000000);
+       if (bar)
+               bar->flush(bar);
+}
+
+static struct nvkm_oclass
+nvkm_ramht_oclass = {
+       .handle = 0x0000abcd,
+       .ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = NULL,
+               .dtor = _nvkm_gpuobj_dtor,
+               .init = _nvkm_gpuobj_init,
+               .fini = _nvkm_gpuobj_fini,
+               .rd32 = _nvkm_gpuobj_rd32,
+               .wr32 = _nvkm_gpuobj_wr32,
+       },
+};
+
+int
+nvkm_ramht_new(struct nvkm_object *parent, struct nvkm_object *pargpu,
+              u32 size, u32 align, struct nvkm_ramht **pramht)
+{
+       struct nvkm_ramht *ramht;
+       int ret;
+
+       ret = nvkm_gpuobj_create(parent, parent->engine ?
+                                &parent->engine->subdev.object : parent, /* <nv50 ramht */
+                                &nvkm_ramht_oclass, 0, pargpu, size,
+                                align, NVOBJ_FLAG_ZERO_ALLOC, &ramht);
+       *pramht = ramht;
+       if (ret)
+               return ret;
+
+       ramht->bits = order_base_2(nv_gpuobj(ramht)->size >> 3);
+       return 0;
+}
diff --git a/drivers/gpu/drm/nouveau/nvkm/core/subdev.c b/drivers/gpu/drm/nouveau/nvkm/core/subdev.c
new file mode 100644 (file)
index 0000000..c5fb3a7
--- /dev/null
@@ -0,0 +1,120 @@
+/*
+ * Copyright 2012 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 <core/subdev.h>
+#include <core/device.h>
+#include <core/option.h>
+
+struct nvkm_subdev *
+nvkm_subdev(void *obj, int idx)
+{
+       struct nvkm_object *object = nv_object(obj);
+       while (object && !nv_iclass(object, NV_SUBDEV_CLASS))
+               object = object->parent;
+       if (object == NULL || nv_subidx(nv_subdev(object)) != idx)
+               object = nv_device(obj)->subdev[idx];
+       return object ? nv_subdev(object) : NULL;
+}
+
+void
+nvkm_subdev_reset(struct nvkm_object *subdev)
+{
+       nv_trace(subdev, "resetting...\n");
+       nv_ofuncs(subdev)->fini(subdev, false);
+       nv_debug(subdev, "reset\n");
+}
+
+int
+nvkm_subdev_init(struct nvkm_subdev *subdev)
+{
+       int ret = nvkm_object_init(&subdev->object);
+       if (ret)
+               return ret;
+
+       nvkm_subdev_reset(&subdev->object);
+       return 0;
+}
+
+int
+_nvkm_subdev_init(struct nvkm_object *object)
+{
+       return nvkm_subdev_init(nv_subdev(object));
+}
+
+int
+nvkm_subdev_fini(struct nvkm_subdev *subdev, bool suspend)
+{
+       if (subdev->unit) {
+               nv_mask(subdev, 0x000200, subdev->unit, 0x00000000);
+               nv_mask(subdev, 0x000200, subdev->unit, subdev->unit);
+       }
+
+       return nvkm_object_fini(&subdev->object, suspend);
+}
+
+int
+_nvkm_subdev_fini(struct nvkm_object *object, bool suspend)
+{
+       return nvkm_subdev_fini(nv_subdev(object), suspend);
+}
+
+void
+nvkm_subdev_destroy(struct nvkm_subdev *subdev)
+{
+       int subidx = nv_hclass(subdev) & 0xff;
+       nv_device(subdev)->subdev[subidx] = NULL;
+       nvkm_object_destroy(&subdev->object);
+}
+
+void
+_nvkm_subdev_dtor(struct nvkm_object *object)
+{
+       nvkm_subdev_destroy(nv_subdev(object));
+}
+
+int
+nvkm_subdev_create_(struct nvkm_object *parent, struct nvkm_object *engine,
+                   struct nvkm_oclass *oclass, u32 pclass,
+                   const char *subname, const char *sysname,
+                   int size, void **pobject)
+{
+       struct nvkm_subdev *subdev;
+       int ret;
+
+       ret = nvkm_object_create_(parent, engine, oclass, pclass |
+                                 NV_SUBDEV_CLASS, size, pobject);
+       subdev = *pobject;
+       if (ret)
+               return ret;
+
+       __mutex_init(&subdev->mutex, subname, &oclass->lock_class_key);
+       subdev->name = subname;
+
+       if (parent) {
+               struct nvkm_device *device = nv_device(parent);
+               subdev->debug = nvkm_dbgopt(device->dbgopt, subname);
+               subdev->mmio  = nv_subdev(device)->mmio;
+       }
+
+       return 0;
+}
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/Kbuild b/drivers/gpu/drm/nouveau/nvkm/engine/Kbuild
new file mode 100644 (file)
index 0000000..6bd3d75
--- /dev/null
@@ -0,0 +1,19 @@
+nvkm-y += nvkm/engine/falcon.o
+nvkm-y += nvkm/engine/xtensa.o
+
+include $(src)/nvkm/engine/bsp/Kbuild
+include $(src)/nvkm/engine/ce/Kbuild
+include $(src)/nvkm/engine/cipher/Kbuild
+include $(src)/nvkm/engine/device/Kbuild
+include $(src)/nvkm/engine/disp/Kbuild
+include $(src)/nvkm/engine/dmaobj/Kbuild
+include $(src)/nvkm/engine/fifo/Kbuild
+include $(src)/nvkm/engine/gr/Kbuild
+include $(src)/nvkm/engine/mpeg/Kbuild
+include $(src)/nvkm/engine/mspdec/Kbuild
+include $(src)/nvkm/engine/msppp/Kbuild
+include $(src)/nvkm/engine/msvld/Kbuild
+include $(src)/nvkm/engine/pm/Kbuild
+include $(src)/nvkm/engine/sec/Kbuild
+include $(src)/nvkm/engine/sw/Kbuild
+include $(src)/nvkm/engine/vp/Kbuild
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/bsp/Kbuild b/drivers/gpu/drm/nouveau/nvkm/engine/bsp/Kbuild
new file mode 100644 (file)
index 0000000..5ac9f9e
--- /dev/null
@@ -0,0 +1 @@
+nvkm-y += nvkm/engine/bsp/g84.o
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/bsp/g84.c b/drivers/gpu/drm/nouveau/nvkm/engine/bsp/g84.c
new file mode 100644 (file)
index 0000000..a0b1fd8
--- /dev/null
@@ -0,0 +1,93 @@
+/*
+ * Copyright 2012 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, Ilia Mirkin
+ */
+#include <engine/bsp.h>
+#include <engine/xtensa.h>
+
+#include <core/engctx.h>
+
+/*******************************************************************************
+ * BSP object classes
+ ******************************************************************************/
+
+static struct nvkm_oclass
+g84_bsp_sclass[] = {
+       { 0x74b0, &nvkm_object_ofuncs },
+       {},
+};
+
+/*******************************************************************************
+ * BSP context
+ ******************************************************************************/
+
+static struct nvkm_oclass
+g84_bsp_cclass = {
+       .handle = NV_ENGCTX(BSP, 0x84),
+       .ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = _nvkm_xtensa_engctx_ctor,
+               .dtor = _nvkm_engctx_dtor,
+               .init = _nvkm_engctx_init,
+               .fini = _nvkm_engctx_fini,
+               .rd32 = _nvkm_engctx_rd32,
+               .wr32 = _nvkm_engctx_wr32,
+       },
+};
+
+/*******************************************************************************
+ * BSP engine/subdev functions
+ ******************************************************************************/
+
+static int
+g84_bsp_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+            struct nvkm_oclass *oclass, void *data, u32 size,
+            struct nvkm_object **pobject)
+{
+       struct nvkm_xtensa *priv;
+       int ret;
+
+       ret = nvkm_xtensa_create(parent, engine, oclass, 0x103000, true,
+                                "PBSP", "bsp", &priv);
+       *pobject = nv_object(priv);
+       if (ret)
+               return ret;
+
+       nv_subdev(priv)->unit = 0x04008000;
+       nv_engine(priv)->cclass = &g84_bsp_cclass;
+       nv_engine(priv)->sclass = g84_bsp_sclass;
+       priv->fifo_val = 0x1111;
+       priv->unkd28 = 0x90044;
+       return 0;
+}
+
+struct nvkm_oclass
+g84_bsp_oclass = {
+       .handle = NV_ENGINE(BSP, 0x84),
+       .ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = g84_bsp_ctor,
+               .dtor = _nvkm_xtensa_dtor,
+               .init = _nvkm_xtensa_init,
+               .fini = _nvkm_xtensa_fini,
+               .rd32 = _nvkm_xtensa_rd32,
+               .wr32 = _nvkm_xtensa_wr32,
+       },
+};
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/ce/Kbuild b/drivers/gpu/drm/nouveau/nvkm/engine/ce/Kbuild
new file mode 100644 (file)
index 0000000..8587974
--- /dev/null
@@ -0,0 +1,3 @@
+nvkm-y += nvkm/engine/ce/gt215.o
+nvkm-y += nvkm/engine/ce/gf100.o
+nvkm-y += nvkm/engine/ce/gk104.o
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/ce/fuc/com.fuc b/drivers/gpu/drm/nouveau/nvkm/engine/ce/fuc/com.fuc
new file mode 100644 (file)
index 0000000..a558dfa
--- /dev/null
@@ -0,0 +1,864 @@
+/* fuc microcode for copy engine on gt215- 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
+ */
+
+#ifdef GT215
+.section #gt215_pce_data
+#else
+.section #gf100_pce_data
+#endif
+
+ctx_object:                   .b32 0
+#ifdef GT215
+ctx_dma:
+ctx_dma_query:                .b32 0
+ctx_dma_src:                  .b32 0
+ctx_dma_dst:                  .b32 0
+#endif
+.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 GT215
+// 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
+#endif
+// 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            ~0xffffffff
+.b32 #ctx_dst_address_high           ~0x000000ff
+.b32 #ctx_dst_address_low            ~0xffffffff
+.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 GT215
+.section #gt215_pce_code
+#else
+.section #gf100_pce_code
+#endif
+
+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 GT215
+   // target 7 hardcoded to ctx dma object
+   mov $xdbase $r0
+#else
+   // 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
+#endif
+   // 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 GT215
+      // 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
+#endif
+   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 GT215
+// 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
+#endif
+
+// 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 GT215
+   add b32 $r8 2
+#else
+   add b32 $r8 3
+#endif
+   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/drivers/gpu/drm/nouveau/nvkm/engine/ce/fuc/gf100.fuc3 b/drivers/gpu/drm/nouveau/nvkm/engine/ce/fuc/gf100.fuc3
new file mode 100644 (file)
index 0000000..36f0a99
--- /dev/null
@@ -0,0 +1,2 @@
+#define GF100
+#include "com.fuc"
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/ce/fuc/gf100.fuc3.h b/drivers/gpu/drm/nouveau/nvkm/engine/ce/fuc/gf100.fuc3.h
new file mode 100644 (file)
index 0000000..d9af6e4
--- /dev/null
@@ -0,0 +1,606 @@
+uint32_t gf100_pce_data[] = {
+/* 0x0000: ctx_object */
+       0x00000000,
+/* 0x0004: ctx_query_address_high */
+       0x00000000,
+/* 0x0008: ctx_query_address_low */
+       0x00000000,
+/* 0x000c: ctx_query_counter */
+       0x00000000,
+/* 0x0010: ctx_src_address_high */
+       0x00000000,
+/* 0x0014: ctx_src_address_low */
+       0x00000000,
+/* 0x0018: ctx_src_pitch */
+       0x00000000,
+/* 0x001c: ctx_src_tile_mode */
+       0x00000000,
+/* 0x0020: ctx_src_xsize */
+       0x00000000,
+/* 0x0024: ctx_src_ysize */
+       0x00000000,
+/* 0x0028: ctx_src_zsize */
+       0x00000000,
+/* 0x002c: ctx_src_zoff */
+       0x00000000,
+/* 0x0030: ctx_src_xoff */
+       0x00000000,
+/* 0x0034: ctx_src_yoff */
+       0x00000000,
+/* 0x0038: ctx_src_cpp */
+       0x00000000,
+/* 0x003c: ctx_dst_address_high */
+       0x00000000,
+/* 0x0040: ctx_dst_address_low */
+       0x00000000,
+/* 0x0044: ctx_dst_pitch */
+       0x00000000,
+/* 0x0048: ctx_dst_tile_mode */
+       0x00000000,
+/* 0x004c: ctx_dst_xsize */
+       0x00000000,
+/* 0x0050: ctx_dst_ysize */
+       0x00000000,
+/* 0x0054: ctx_dst_zsize */
+       0x00000000,
+/* 0x0058: ctx_dst_zoff */
+       0x00000000,
+/* 0x005c: ctx_dst_xoff */
+       0x00000000,
+/* 0x0060: ctx_dst_yoff */
+       0x00000000,
+/* 0x0064: ctx_dst_cpp */
+       0x00000000,
+/* 0x0068: ctx_format */
+       0x00000000,
+/* 0x006c: ctx_swz_const0 */
+       0x00000000,
+/* 0x0070: ctx_swz_const1 */
+       0x00000000,
+/* 0x0074: ctx_xcnt */
+       0x00000000,
+/* 0x0078: ctx_ycnt */
+       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,
+/* 0x0100: dispatch_table */
+       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,
+       0x00000000,
+       0x0000003c,
+       0xffffff00,
+       0x00000040,
+       0x00000000,
+       0x00000018,
+       0xfff80000,
+       0x00000044,
+       0xfff80000,
+       0x00000074,
+       0xffff0000,
+       0x00000078,
+       0xffffe000,
+       0x00000068,
+       0xfccc0000,
+       0x0000006c,
+       0x00000000,
+       0x00000070,
+       0x00000000,
+       0x00000004,
+       0xffffff00,
+       0x00000008,
+       0x00000000,
+       0x0000000c,
+       0x00000000,
+       0x00000800,
+};
+
+uint32_t gf100_pce_code[] = {
+/* 0x0000: main */
+       0x04fe04bd,
+       0x3517f000,
+       0xf10010fe,
+       0xf1040017,
+       0xf0fff327,
+       0x12d00023,
+       0x0c25f0c0,
+       0xf40012d0,
+       0x17f11031,
+       0x27f01200,
+       0x0012d003,
+/* 0x002f: spin */
+       0xf40031f4,
+       0x0ef40028,
+/* 0x0035: ih */
+       0x8001cffd,
+       0xf40812c4,
+       0x21f4060b,
+/* 0x0041: ih_no_chsw */
+       0x0412c4ca,
+       0xf5070bf4,
+/* 0x004b: ih_no_cmd */
+       0xc4010221,
+       0x01d00c11,
+/* 0x0053: swctx */
+       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,
+/* 0x00c3: swctx_load */
+       0xfa060ef4,
+/* 0x00c6: swctx_done */
+       0x03f80504,
+/* 0x00ca: chsw */
+       0x27f100f8,
+       0x23cf1400,
+       0x1e3fc800,
+       0xf4170bf4,
+       0x21f40132,
+       0x1e3af053,
+       0xf00023d0,
+       0x24d00147,
+/* 0x00eb: chsw_no_unload */
+       0xcf00f880,
+       0x3dc84023,
+       0x090bf41e,
+       0xf40131f4,
+/* 0x00fa: chsw_finish_load */
+       0x37f05321,
+       0x8023d002,
+/* 0x0102: dispatch */
+       0x37f100f8,
+       0x32cf1900,
+       0x0033cf40,
+       0x07ff24e4,
+       0xf11024b6,
+       0xbd010057,
+/* 0x011b: dispatch_loop */
+       0x5874bd64,
+       0x57580056,
+       0x0450b601,
+       0xf40446b8,
+       0x76bb4d08,
+       0x0447b800,
+       0xbb0f08f4,
+       0x74b60276,
+       0x0057bb03,
+/* 0x013f: dispatch_valid_mthd */
+       0xbbdf0ef4,
+       0x44b60246,
+       0x0045bb03,
+       0xfd014598,
+       0x54b00453,
+       0x201bf400,
+       0x58004558,
+       0x64b00146,
+       0x091bf400,
+       0xf4005380,
+/* 0x0166: dispatch_cmd */
+       0x32f4300e,
+       0xf455f901,
+       0x0ef40c01,
+/* 0x0171: dispatch_invalid_bitfield */
+       0x0225f025,
+/* 0x0174: dispatch_illegal_mthd */
+/* 0x0177: dispatch_error */
+       0xf10125f0,
+       0xd0100047,
+       0x43d00042,
+       0x4027f040,
+/* 0x0187: hostirq_wait */
+       0xcf0002d0,
+       0x24f08002,
+       0x0024b040,
+/* 0x0193: dispatch_done */
+       0xf1f71bf4,
+       0xf01d0027,
+       0x23d00137,
+/* 0x019f: cmd_nop */
+       0xf800f800,
+/* 0x01a1: cmd_pm_trigger */
+       0x0027f100,
+       0xf034bd22,
+       0x23d00233,
+/* 0x01af: cmd_exec_set_format */
+       0xf400f800,
+       0x01b0f030,
+       0x0101b000,
+       0xb00201b0,
+       0x04980301,
+       0x3045c71a,
+       0xc70150b6,
+       0x60b63446,
+       0x3847c701,
+       0xf40170b6,
+       0x84bd0232,
+/* 0x01da: ncomp_loop */
+       0x4ac494bd,
+       0x0445b60f,
+/* 0x01e2: bpc_loop */
+       0xa430b4bd,
+       0x0f18f404,
+       0xbbc0a5ff,
+       0x31f400cb,
+       0x220ef402,
+/* 0x01f4: cmp_c0 */
+       0xf00c1bf4,
+       0xcbbb10c7,
+       0x160ef400,
+/* 0x0200: cmp_c1 */
+       0xf406a430,
+       0xc7f00c18,
+       0x00cbbb14,
+/* 0x020f: cmp_zero */
+       0xf1070ef4,
+/* 0x0213: bpc_next */
+       0x380080c7,
+       0x80b601c8,
+       0x01b0b601,
+       0xf404b5b8,
+       0x90b6c308,
+       0x0497b801,
+       0xfdb208f4,
+       0x06800065,
+       0x1d08980e,
+       0xf40068fd,
+       0x64bd0502,
+/* 0x023c: dst_xcnt */
+       0x800075fd,
+       0x78fd1907,
+       0x1057f100,
+       0x0654b608,
+       0xd00056d0,
+       0x50b74057,
+       0x06980800,
+       0x0162b619,
+       0x980864b6,
+       0x72b60e07,
+       0x0567fd01,
+       0xb70056d0,
+       0xb4010050,
+       0x56d00060,
+       0x0160b400,
+       0xb44056d0,
+       0x56d00260,
+       0x0360b480,
+       0xb7c056d0,
+       0x98040050,
+       0x56d01b06,
+       0x1c069800,
+       0xf44056d0,
+       0x00f81030,
+/* 0x029c: cmd_exec_set_surface_tiled */
+       0xc7075798,
+       0x78c76879,
+       0x0380b664,
+       0xb06077c7,
+       0x1bf40e76,
+       0x0477f009,
+/* 0x02b7: xtile64 */
+       0xf00f0ef4,
+       0x70b6027c,
+       0x0947fd11,
+/* 0x02c3: xtileok */
+       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,
+/* 0x03a8: cmd_exec_set_surface_linear */
+       0xb7026cf0,
+       0xb6020260,
+       0x57980864,
+       0x0067d005,
+       0x040060b7,
+       0xb6045798,
+       0x67d01074,
+       0x0060b700,
+       0x06579804,
+       0xf80067d0,
+/* 0x03d1: cmd_exec_wait */
+       0xf900f900,
+       0x0007f110,
+       0x0604b608,
+/* 0x03dc: loop */
+       0xf00001cf,
+       0x1bf40114,
+       0xfc10fcfa,
+/* 0x03eb: cmd_exec_query */
+       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,
+/* 0x045e: query_counter */
+       0x21f50045,
+       0x47f103d1,
+       0x44b6080c,
+       0x02059806,
+       0xd00045d0,
+       0x57f04040,
+       0x8045d004,
+       0x040040b7,
+       0xb6010598,
+       0x45d01054,
+       0x0040b700,
+       0x0057f105,
+       0x0045d003,
+       0x111057f1,
+       0x131253f1,
+       0x984045d0,
+       0x40b70305,
+       0x45d00500,
+       0x0157f100,
+       0x0153f026,
+       0x080047f1,
+       0xd00644b6,
+       0x00f80045,
+/* 0x04b8: cmd_exec */
+       0x03d121f5,
+       0xf4003fc8,
+       0x21f50e0b,
+       0x47f101af,
+       0x0ef40200,
+/* 0x04cd: cmd_exec_no_format */
+       0x1067f11e,
+       0x0664b608,
+       0x800177f0,
+       0x07800e07,
+       0x1d079819,
+       0xd00067d0,
+       0x44bd4067,
+/* 0x04e8: cmd_exec_init_src_surface */
+       0xbd0232f4,
+       0x043fc854,
+       0xf50a0bf4,
+       0xf403a821,
+/* 0x04fa: src_tiled */
+       0x21f50a0e,
+       0x49f0029c,
+/* 0x0501: cmd_exec_init_dst_surface */
+       0x0231f407,
+       0xc82c57f0,
+       0x0bf4083f,
+       0xa821f50a,
+       0x0a0ef403,
+/* 0x0514: dst_tiled */
+       0x029c21f5,
+/* 0x051b: cmd_exec_kick */
+       0xf10849f0,
+       0xb6080057,
+       0x06980654,
+       0x4056d01e,
+       0xf14167f0,
+       0xfd440063,
+       0x54d00546,
+       0x0c3fc800,
+       0xf5070bf4,
+/* 0x053f: cmd_exec_done */
+       0xf803eb21,
+/* 0x0541: cmd_wrcache_flush */
+       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/drivers/gpu/drm/nouveau/nvkm/engine/ce/fuc/gt215.fuc3 b/drivers/gpu/drm/nouveau/nvkm/engine/ce/fuc/gt215.fuc3
new file mode 100644 (file)
index 0000000..07bda93
--- /dev/null
@@ -0,0 +1,2 @@
+#define GT215
+#include "com.fuc"
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/ce/fuc/gt215.fuc3.h b/drivers/gpu/drm/nouveau/nvkm/engine/ce/fuc/gt215.fuc3.h
new file mode 100644 (file)
index 0000000..f42c0d0
--- /dev/null
@@ -0,0 +1,620 @@
+uint32_t gt215_pce_data[] = {
+/* 0x0000: ctx_object */
+       0x00000000,
+/* 0x0004: ctx_dma */
+/* 0x0004: ctx_dma_query */
+       0x00000000,
+/* 0x0008: ctx_dma_src */
+       0x00000000,
+/* 0x000c: ctx_dma_dst */
+       0x00000000,
+/* 0x0010: ctx_query_address_high */
+       0x00000000,
+/* 0x0014: ctx_query_address_low */
+       0x00000000,
+/* 0x0018: ctx_query_counter */
+       0x00000000,
+/* 0x001c: ctx_src_address_high */
+       0x00000000,
+/* 0x0020: ctx_src_address_low */
+       0x00000000,
+/* 0x0024: ctx_src_pitch */
+       0x00000000,
+/* 0x0028: ctx_src_tile_mode */
+       0x00000000,
+/* 0x002c: ctx_src_xsize */
+       0x00000000,
+/* 0x0030: ctx_src_ysize */
+       0x00000000,
+/* 0x0034: ctx_src_zsize */
+       0x00000000,
+/* 0x0038: ctx_src_zoff */
+       0x00000000,
+/* 0x003c: ctx_src_xoff */
+       0x00000000,
+/* 0x0040: ctx_src_yoff */
+       0x00000000,
+/* 0x0044: ctx_src_cpp */
+       0x00000000,
+/* 0x0048: ctx_dst_address_high */
+       0x00000000,
+/* 0x004c: ctx_dst_address_low */
+       0x00000000,
+/* 0x0050: ctx_dst_pitch */
+       0x00000000,
+/* 0x0054: ctx_dst_tile_mode */
+       0x00000000,
+/* 0x0058: ctx_dst_xsize */
+       0x00000000,
+/* 0x005c: ctx_dst_ysize */
+       0x00000000,
+/* 0x0060: ctx_dst_zsize */
+       0x00000000,
+/* 0x0064: ctx_dst_zoff */
+       0x00000000,
+/* 0x0068: ctx_dst_xoff */
+       0x00000000,
+/* 0x006c: ctx_dst_yoff */
+       0x00000000,
+/* 0x0070: ctx_dst_cpp */
+       0x00000000,
+/* 0x0074: ctx_format */
+       0x00000000,
+/* 0x0078: ctx_swz_const0 */
+       0x00000000,
+/* 0x007c: ctx_swz_const1 */
+       0x00000000,
+/* 0x0080: ctx_xcnt */
+       0x00000000,
+/* 0x0084: ctx_ycnt */
+       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,
+/* 0x0100: dispatch_table */
+       0x00010000,
+       0x00000000,
+       0x00000000,
+       0x00010040,
+       0x00010160,
+       0x00000000,
+       0x00010050,
+       0x00010162,
+       0x00000000,
+       0x00030060,
+/* 0x0128: dispatch_dma */
+       0x00010170,
+       0x00000000,
+       0x00010170,
+       0x00000000,
+       0x00010170,
+       0x00000000,
+       0x00070080,
+       0x00000028,
+       0xfffff000,
+       0x0000002c,
+       0xfff80000,
+       0x00000030,
+       0xffffe000,
+       0x00000034,
+       0xfffff800,
+       0x00000038,
+       0xfffff000,
+       0x0000003c,
+       0xfff80000,
+       0x00000040,
+       0xffffe000,
+       0x00070088,
+       0x00000054,
+       0xfffff000,
+       0x00000058,
+       0xfff80000,
+       0x0000005c,
+       0xffffe000,
+       0x00000060,
+       0xfffff800,
+       0x00000064,
+       0xfffff000,
+       0x00000068,
+       0xfff80000,
+       0x0000006c,
+       0xffffe000,
+       0x000200c0,
+       0x00010492,
+       0x00000000,
+       0x0001051b,
+       0x00000000,
+       0x000e00c3,
+       0x0000001c,
+       0xffffff00,
+       0x00000020,
+       0x00000000,
+       0x00000048,
+       0xffffff00,
+       0x0000004c,
+       0x00000000,
+       0x00000024,
+       0xfff80000,
+       0x00000050,
+       0xfff80000,
+       0x00000080,
+       0xffff0000,
+       0x00000084,
+       0xffffe000,
+       0x00000074,
+       0xfccc0000,
+       0x00000078,
+       0x00000000,
+       0x0000007c,
+       0x00000000,
+       0x00000010,
+       0xffffff00,
+       0x00000014,
+       0x00000000,
+       0x00000018,
+       0x00000000,
+       0x00000800,
+};
+
+uint32_t gt215_pce_code[] = {
+/* 0x0000: main */
+       0x04fe04bd,
+       0x3517f000,
+       0xf10010fe,
+       0xf1040017,
+       0xf0fff327,
+       0x12d00023,
+       0x0c25f0c0,
+       0xf40012d0,
+       0x17f11031,
+       0x27f01200,
+       0x0012d003,
+/* 0x002f: spin */
+       0xf40031f4,
+       0x0ef40028,
+/* 0x0035: ih */
+       0x8001cffd,
+       0xf40812c4,
+       0x21f4060b,
+/* 0x0041: ih_no_chsw */
+       0x0412c472,
+       0xf4060bf4,
+/* 0x004a: ih_no_cmd */
+       0x11c4c321,
+       0x4001d00c,
+/* 0x0052: swctx */
+       0x47f101f8,
+       0x4bfe7700,
+       0x0007fe00,
+       0xf00204b9,
+       0x01f40643,
+       0x0604fa09,
+/* 0x006b: swctx_load */
+       0xfa060ef4,
+/* 0x006e: swctx_done */
+       0x03f80504,
+/* 0x0072: chsw */
+       0x27f100f8,
+       0x23cf1400,
+       0x1e3fc800,
+       0xf4170bf4,
+       0x21f40132,
+       0x1e3af052,
+       0xf00023d0,
+       0x24d00147,
+/* 0x0093: chsw_no_unload */
+       0xcf00f880,
+       0x3dc84023,
+       0x220bf41e,
+       0xf40131f4,
+       0x57f05221,
+       0x0367f004,
+/* 0x00a8: chsw_load_ctx_dma */
+       0xa07856bc,
+       0xb6018068,
+       0x87d00884,
+       0x0162b600,
+/* 0x00bb: chsw_finish_load */
+       0xf0f018f4,
+       0x23d00237,
+/* 0x00c3: dispatch */
+       0xf100f880,
+       0xcf190037,
+       0x33cf4032,
+       0xff24e400,
+       0x1024b607,
+       0x010057f1,
+       0x74bd64bd,
+/* 0x00dc: dispatch_loop */
+       0x58005658,
+       0x50b60157,
+       0x0446b804,
+       0xbb4d08f4,
+       0x47b80076,
+       0x0f08f404,
+       0xb60276bb,
+       0x57bb0374,
+       0xdf0ef400,
+/* 0x0100: dispatch_valid_mthd */
+       0xb60246bb,
+       0x45bb0344,
+       0x01459800,
+       0xb00453fd,
+       0x1bf40054,
+       0x00455820,
+       0xb0014658,
+       0x1bf40064,
+       0x00538009,
+/* 0x0127: dispatch_cmd */
+       0xf4300ef4,
+       0x55f90132,
+       0xf40c01f4,
+/* 0x0132: dispatch_invalid_bitfield */
+       0x25f0250e,
+/* 0x0135: dispatch_illegal_mthd */
+       0x0125f002,
+/* 0x0138: dispatch_error */
+       0x100047f1,
+       0xd00042d0,
+       0x27f04043,
+       0x0002d040,
+/* 0x0148: hostirq_wait */
+       0xf08002cf,
+       0x24b04024,
+       0xf71bf400,
+/* 0x0154: dispatch_done */
+       0x1d0027f1,
+       0xd00137f0,
+       0x00f80023,
+/* 0x0160: cmd_nop */
+/* 0x0162: cmd_pm_trigger */
+       0x27f100f8,
+       0x34bd2200,
+       0xd00233f0,
+       0x00f80023,
+/* 0x0170: cmd_dma */
+       0x012842b7,
+       0xf00145b6,
+       0x43801e39,
+       0x0040b701,
+       0x0644b606,
+       0xf80043d0,
+/* 0x0189: cmd_exec_set_format */
+       0xf030f400,
+       0xb00001b0,
+       0x01b00101,
+       0x0301b002,
+       0xc71d0498,
+       0x50b63045,
+       0x3446c701,
+       0xc70160b6,
+       0x70b63847,
+       0x0232f401,
+       0x94bd84bd,
+/* 0x01b4: ncomp_loop */
+       0xb60f4ac4,
+       0xb4bd0445,
+/* 0x01bc: bpc_loop */
+       0xf404a430,
+       0xa5ff0f18,
+       0x00cbbbc0,
+       0xf40231f4,
+/* 0x01ce: cmp_c0 */
+       0x1bf4220e,
+       0x10c7f00c,
+       0xf400cbbb,
+/* 0x01da: cmp_c1 */
+       0xa430160e,
+       0x0c18f406,
+       0xbb14c7f0,
+       0x0ef400cb,
+/* 0x01e9: cmp_zero */
+       0x80c7f107,
+/* 0x01ed: bpc_next */
+       0x01c83800,
+       0xb60180b6,
+       0xb5b801b0,
+       0xc308f404,
+       0xb80190b6,
+       0x08f40497,
+       0x0065fdb2,
+       0x98110680,
+       0x68fd2008,
+       0x0502f400,
+/* 0x0216: dst_xcnt */
+       0x75fd64bd,
+       0x1c078000,
+       0xf10078fd,
+       0xb6081057,
+       0x56d00654,
+       0x4057d000,
+       0x080050b7,
+       0xb61c0698,
+       0x64b60162,
+       0x11079808,
+       0xfd0172b6,
+       0x56d00567,
+       0x0050b700,
+       0x0060b401,
+       0xb40056d0,
+       0x56d00160,
+       0x0260b440,
+       0xb48056d0,
+       0x56d00360,
+       0x0050b7c0,
+       0x1e069804,
+       0x980056d0,
+       0x56d01f06,
+       0x1030f440,
+/* 0x0276: cmd_exec_set_surface_tiled */
+       0x579800f8,
+       0x6879c70a,
+       0xb66478c7,
+       0x77c70280,
+       0x0e76b060,
+       0xf0091bf4,
+       0x0ef40477,
+/* 0x0291: xtile64 */
+       0x027cf00f,
+       0xfd1170b6,
+       0x77f00947,
+/* 0x029d: xtileok */
+       0x0f5a9806,
+       0xfd115b98,
+       0xb7f000ab,
+       0x04b7bb01,
+       0xff01b2b6,
+       0xa7bbc4ab,
+       0x105d9805,
+       0xbb01e7f0,
+       0xe2b604e8,
+       0xb4deff01,
+       0xb605d8bb,
+       0xef9401e0,
+       0x02ebbb0c,
+       0xf005fefd,
+       0x60b7026c,
+       0x64b60208,
+       0x006fd008,
+       0xbb04b7bb,
+       0x5f9800cb,
+       0x115b980b,
+       0xf000fbfd,
+       0xb7bb01b7,
+       0x01b2b604,
+       0xbb00fbbb,
+       0xf0f905f7,
+       0xf00c5f98,
+       0xb8bb01b7,
+       0x01b2b604,
+       0xbb00fbbb,
+       0xf0f905f8,
+       0xb60078bb,
+       0xb7f00282,
+       0x04b8bb01,
+       0x9804b9bb,
+       0xe7f00e58,
+       0x04e9bb01,
+       0xff01e2b6,
+       0xf7bbf48e,
+       0x00cfbb04,
+       0xbb0079bb,
+       0xf0fc0589,
+       0xd9fd90fc,
+       0x00adbb00,
+       0xfd0089fd,
+       0xa8bb008f,
+       0x04a7bb00,
+       0xbb0192b6,
+       0x69d00497,
+       0x08579880,
+       0xbb075898,
+       0x7abb00ac,
+       0x0081b600,
+       0xfd1084b6,
+       0x62b7058b,
+       0x67d00600,
+       0x0060b700,
+       0x0068d004,
+/* 0x0382: cmd_exec_set_surface_linear */
+       0x6cf000f8,
+       0x0260b702,
+       0x0864b602,
+       0xd0085798,
+       0x60b70067,
+       0x57980400,
+       0x1074b607,
+       0xb70067d0,
+       0x98040060,
+       0x67d00957,
+/* 0x03ab: cmd_exec_wait */
+       0xf900f800,
+       0xf110f900,
+       0xb6080007,
+/* 0x03b6: loop */
+       0x01cf0604,
+       0x0114f000,
+       0xfcfa1bf4,
+       0xf800fc10,
+/* 0x03c5: cmd_exec_query */
+       0x0d34c800,
+       0xf5701bf4,
+       0xf103ab21,
+       0xb6080c47,
+       0x05980644,
+       0x0450b605,
+       0xd00045d0,
+       0x57f04040,
+       0x8045d00c,
+       0x040040b7,
+       0xb6040598,
+       0x45d01054,
+       0x0040b700,
+       0x0057f105,
+       0x0153f00b,
+       0xf10045d0,
+       0xb6404057,
+       0x53f10154,
+       0x45d08080,
+       0x1057f140,
+       0x1253f111,
+       0x8045d013,
+       0x151457f1,
+       0x171653f1,
+       0xf1c045d0,
+       0xf0260157,
+       0x47f10153,
+       0x44b60800,
+       0x0045d006,
+/* 0x0438: query_counter */
+       0x03ab21f5,
+       0x080c47f1,
+       0x980644b6,
+       0x45d00505,
+       0x4040d000,
+       0xd00457f0,
+       0x40b78045,
+       0x05980400,
+       0x1054b604,
+       0xb70045d0,
+       0xf1050040,
+       0xd0030057,
+       0x57f10045,
+       0x53f11110,
+       0x45d01312,
+       0x06059840,
+       0x050040b7,
+       0xf10045d0,
+       0xf0260157,
+       0x47f10153,
+       0x44b60800,
+       0x0045d006,
+/* 0x0492: cmd_exec */
+       0x21f500f8,
+       0x3fc803ab,
+       0x0e0bf400,
+       0x018921f5,
+       0x020047f1,
+/* 0x04a7: cmd_exec_no_format */
+       0xf11e0ef4,
+       0xb6081067,
+       0x77f00664,
+       0x11078001,
+       0x981c0780,
+       0x67d02007,
+       0x4067d000,
+/* 0x04c2: cmd_exec_init_src_surface */
+       0x32f444bd,
+       0xc854bd02,
+       0x0bf4043f,
+       0x8221f50a,
+       0x0a0ef403,
+/* 0x04d4: src_tiled */
+       0x027621f5,
+/* 0x04db: cmd_exec_init_dst_surface */
+       0xf40749f0,
+       0x57f00231,
+       0x083fc82c,
+       0xf50a0bf4,
+       0xf4038221,
+/* 0x04ee: dst_tiled */
+       0x21f50a0e,
+       0x49f00276,
+/* 0x04f5: cmd_exec_kick */
+       0x0057f108,
+       0x0654b608,
+       0xd0210698,
+       0x67f04056,
+       0x0063f141,
+       0x0546fd44,
+       0xc80054d0,
+       0x0bf40c3f,
+       0xc521f507,
+/* 0x0519: cmd_exec_done */
+/* 0x051b: cmd_wrcache_flush */
+       0xf100f803,
+       0xbd220027,
+       0x0133f034,
+       0xf80023d0,
+       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,
+};
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/ce/gf100.c b/drivers/gpu/drm/nouveau/nvkm/engine/ce/gf100.c
new file mode 100644 (file)
index 0000000..2d2e549
--- /dev/null
@@ -0,0 +1,166 @@
+/*
+ * Copyright 2012 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 <engine/ce.h>
+#include <engine/falcon.h>
+#include "fuc/gf100.fuc3.h"
+
+struct gf100_ce_priv {
+       struct nvkm_falcon base;
+};
+
+/*******************************************************************************
+ * Copy object classes
+ ******************************************************************************/
+
+static struct nvkm_oclass
+gf100_ce0_sclass[] = {
+       { 0x90b5, &nvkm_object_ofuncs },
+       {},
+};
+
+static struct nvkm_oclass
+gf100_ce1_sclass[] = {
+       { 0x90b8, &nvkm_object_ofuncs },
+       {},
+};
+
+/*******************************************************************************
+ * PCE context
+ ******************************************************************************/
+
+static struct nvkm_ofuncs
+gf100_ce_context_ofuncs = {
+       .ctor = _nvkm_falcon_context_ctor,
+       .dtor = _nvkm_falcon_context_dtor,
+       .init = _nvkm_falcon_context_init,
+       .fini = _nvkm_falcon_context_fini,
+       .rd32 = _nvkm_falcon_context_rd32,
+       .wr32 = _nvkm_falcon_context_wr32,
+};
+
+static struct nvkm_oclass
+gf100_ce0_cclass = {
+       .handle = NV_ENGCTX(CE0, 0xc0),
+       .ofuncs = &gf100_ce_context_ofuncs,
+};
+
+static struct nvkm_oclass
+gf100_ce1_cclass = {
+       .handle = NV_ENGCTX(CE1, 0xc0),
+       .ofuncs = &gf100_ce_context_ofuncs,
+};
+
+/*******************************************************************************
+ * PCE engine/subdev functions
+ ******************************************************************************/
+
+static int
+gf100_ce_init(struct nvkm_object *object)
+{
+       struct gf100_ce_priv *priv = (void *)object;
+       int ret;
+
+       ret = nvkm_falcon_init(&priv->base);
+       if (ret)
+               return ret;
+
+       nv_wo32(priv, 0x084, nv_engidx(&priv->base.base) - NVDEV_ENGINE_CE0);
+       return 0;
+}
+
+static int
+gf100_ce0_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+              struct nvkm_oclass *oclass, void *data, u32 size,
+              struct nvkm_object **pobject)
+{
+       struct gf100_ce_priv *priv;
+       int ret;
+
+       ret = nvkm_falcon_create(parent, engine, oclass, 0x104000, true,
+                                "PCE0", "ce0", &priv);
+       *pobject = nv_object(priv);
+       if (ret)
+               return ret;
+
+       nv_subdev(priv)->unit = 0x00000040;
+       nv_subdev(priv)->intr = gt215_ce_intr;
+       nv_engine(priv)->cclass = &gf100_ce0_cclass;
+       nv_engine(priv)->sclass = gf100_ce0_sclass;
+       nv_falcon(priv)->code.data = gf100_pce_code;
+       nv_falcon(priv)->code.size = sizeof(gf100_pce_code);
+       nv_falcon(priv)->data.data = gf100_pce_data;
+       nv_falcon(priv)->data.size = sizeof(gf100_pce_data);
+       return 0;
+}
+
+static int
+gf100_ce1_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+              struct nvkm_oclass *oclass, void *data, u32 size,
+              struct nvkm_object **pobject)
+{
+       struct gf100_ce_priv *priv;
+       int ret;
+
+       ret = nvkm_falcon_create(parent, engine, oclass, 0x105000, true,
+                                "PCE1", "ce1", &priv);
+       *pobject = nv_object(priv);
+       if (ret)
+               return ret;
+
+       nv_subdev(priv)->unit = 0x00000080;
+       nv_subdev(priv)->intr = gt215_ce_intr;
+       nv_engine(priv)->cclass = &gf100_ce1_cclass;
+       nv_engine(priv)->sclass = gf100_ce1_sclass;
+       nv_falcon(priv)->code.data = gf100_pce_code;
+       nv_falcon(priv)->code.size = sizeof(gf100_pce_code);
+       nv_falcon(priv)->data.data = gf100_pce_data;
+       nv_falcon(priv)->data.size = sizeof(gf100_pce_data);
+       return 0;
+}
+
+struct nvkm_oclass
+gf100_ce0_oclass = {
+       .handle = NV_ENGINE(CE0, 0xc0),
+       .ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = gf100_ce0_ctor,
+               .dtor = _nvkm_falcon_dtor,
+               .init = gf100_ce_init,
+               .fini = _nvkm_falcon_fini,
+               .rd32 = _nvkm_falcon_rd32,
+               .wr32 = _nvkm_falcon_wr32,
+       },
+};
+
+struct nvkm_oclass
+gf100_ce1_oclass = {
+       .handle = NV_ENGINE(CE1, 0xc0),
+       .ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = gf100_ce1_ctor,
+               .dtor = _nvkm_falcon_dtor,
+               .init = gf100_ce_init,
+               .fini = _nvkm_falcon_fini,
+               .rd32 = _nvkm_falcon_rd32,
+               .wr32 = _nvkm_falcon_wr32,
+       },
+};
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/ce/gk104.c b/drivers/gpu/drm/nouveau/nvkm/engine/ce/gk104.c
new file mode 100644 (file)
index 0000000..a998932
--- /dev/null
@@ -0,0 +1,173 @@
+/*
+ * Copyright 2012 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 <engine/ce.h>
+
+#include <core/engctx.h>
+
+struct gk104_ce_priv {
+       struct nvkm_engine base;
+};
+
+/*******************************************************************************
+ * Copy object classes
+ ******************************************************************************/
+
+static struct nvkm_oclass
+gk104_ce_sclass[] = {
+       { 0xa0b5, &nvkm_object_ofuncs },
+       {},
+};
+
+/*******************************************************************************
+ * PCE context
+ ******************************************************************************/
+
+static struct nvkm_ofuncs
+gk104_ce_context_ofuncs = {
+       .ctor = _nvkm_engctx_ctor,
+       .dtor = _nvkm_engctx_dtor,
+       .init = _nvkm_engctx_init,
+       .fini = _nvkm_engctx_fini,
+       .rd32 = _nvkm_engctx_rd32,
+       .wr32 = _nvkm_engctx_wr32,
+};
+
+static struct nvkm_oclass
+gk104_ce_cclass = {
+       .handle = NV_ENGCTX(CE0, 0xc0),
+       .ofuncs = &gk104_ce_context_ofuncs,
+};
+
+/*******************************************************************************
+ * PCE engine/subdev functions
+ ******************************************************************************/
+
+static void
+gk104_ce_intr(struct nvkm_subdev *subdev)
+{
+       const int ce = nv_subidx(subdev) - NVDEV_ENGINE_CE0;
+       struct gk104_ce_priv *priv = (void *)subdev;
+       u32 stat = nv_rd32(priv, 0x104908 + (ce * 0x1000));
+
+       if (stat) {
+               nv_warn(priv, "unhandled intr 0x%08x\n", stat);
+               nv_wr32(priv, 0x104908 + (ce * 0x1000), stat);
+       }
+}
+
+static int
+gk104_ce0_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+              struct nvkm_oclass *oclass, void *data, u32 size,
+              struct nvkm_object **pobject)
+{
+       struct gk104_ce_priv *priv;
+       int ret;
+
+       ret = nvkm_engine_create(parent, engine, oclass, true,
+                                "PCE0", "ce0", &priv);
+       *pobject = nv_object(priv);
+       if (ret)
+               return ret;
+
+       nv_subdev(priv)->unit = 0x00000040;
+       nv_subdev(priv)->intr = gk104_ce_intr;
+       nv_engine(priv)->cclass = &gk104_ce_cclass;
+       nv_engine(priv)->sclass = gk104_ce_sclass;
+       return 0;
+}
+
+static int
+gk104_ce1_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+              struct nvkm_oclass *oclass, void *data, u32 size,
+              struct nvkm_object **pobject)
+{
+       struct gk104_ce_priv *priv;
+       int ret;
+
+       ret = nvkm_engine_create(parent, engine, oclass, true,
+                                "PCE1", "ce1", &priv);
+       *pobject = nv_object(priv);
+       if (ret)
+               return ret;
+
+       nv_subdev(priv)->unit = 0x00000080;
+       nv_subdev(priv)->intr = gk104_ce_intr;
+       nv_engine(priv)->cclass = &gk104_ce_cclass;
+       nv_engine(priv)->sclass = gk104_ce_sclass;
+       return 0;
+}
+
+static int
+gk104_ce2_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+              struct nvkm_oclass *oclass, void *data, u32 size,
+              struct nvkm_object **pobject)
+{
+       struct gk104_ce_priv *priv;
+       int ret;
+
+       ret = nvkm_engine_create(parent, engine, oclass, true,
+                                "PCE2", "ce2", &priv);
+       *pobject = nv_object(priv);
+       if (ret)
+               return ret;
+
+       nv_subdev(priv)->unit = 0x00200000;
+       nv_subdev(priv)->intr = gk104_ce_intr;
+       nv_engine(priv)->cclass = &gk104_ce_cclass;
+       nv_engine(priv)->sclass = gk104_ce_sclass;
+       return 0;
+}
+
+struct nvkm_oclass
+gk104_ce0_oclass = {
+       .handle = NV_ENGINE(CE0, 0xe0),
+       .ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = gk104_ce0_ctor,
+               .dtor = _nvkm_engine_dtor,
+               .init = _nvkm_engine_init,
+               .fini = _nvkm_engine_fini,
+       },
+};
+
+struct nvkm_oclass
+gk104_ce1_oclass = {
+       .handle = NV_ENGINE(CE1, 0xe0),
+       .ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = gk104_ce1_ctor,
+               .dtor = _nvkm_engine_dtor,
+               .init = _nvkm_engine_init,
+               .fini = _nvkm_engine_fini,
+       },
+};
+
+struct nvkm_oclass
+gk104_ce2_oclass = {
+       .handle = NV_ENGINE(CE2, 0xe0),
+       .ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = gk104_ce2_ctor,
+               .dtor = _nvkm_engine_dtor,
+               .init = _nvkm_engine_init,
+               .fini = _nvkm_engine_fini,
+       },
+};
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/ce/gt215.c b/drivers/gpu/drm/nouveau/nvkm/engine/ce/gt215.c
new file mode 100644 (file)
index 0000000..d8bb429
--- /dev/null
@@ -0,0 +1,152 @@
+/*
+ * Copyright 2012 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 <engine/ce.h>
+#include <engine/falcon.h>
+#include <engine/fifo.h>
+#include "fuc/gt215.fuc3.h"
+
+#include <core/client.h>
+#include <core/device.h>
+#include <core/enum.h>
+
+struct gt215_ce_priv {
+       struct nvkm_falcon base;
+};
+
+/*******************************************************************************
+ * Copy object classes
+ ******************************************************************************/
+
+static struct nvkm_oclass
+gt215_ce_sclass[] = {
+       { 0x85b5, &nvkm_object_ofuncs },
+       {}
+};
+
+/*******************************************************************************
+ * PCE context
+ ******************************************************************************/
+
+static struct nvkm_oclass
+gt215_ce_cclass = {
+       .handle = NV_ENGCTX(CE0, 0xa3),
+       .ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = _nvkm_falcon_context_ctor,
+               .dtor = _nvkm_falcon_context_dtor,
+               .init = _nvkm_falcon_context_init,
+               .fini = _nvkm_falcon_context_fini,
+               .rd32 = _nvkm_falcon_context_rd32,
+               .wr32 = _nvkm_falcon_context_wr32,
+
+       },
+};
+
+/*******************************************************************************
+ * PCE engine/subdev functions
+ ******************************************************************************/
+
+static const struct nvkm_enum
+gt215_ce_isr_error_name[] = {
+       { 0x0001, "ILLEGAL_MTHD" },
+       { 0x0002, "INVALID_ENUM" },
+       { 0x0003, "INVALID_BITFIELD" },
+       {}
+};
+
+void
+gt215_ce_intr(struct nvkm_subdev *subdev)
+{
+       struct nvkm_fifo *pfifo = nvkm_fifo(subdev);
+       struct nvkm_engine *engine = nv_engine(subdev);
+       struct nvkm_falcon *falcon = (void *)subdev;
+       struct nvkm_object *engctx;
+       u32 dispatch = nv_ro32(falcon, 0x01c);
+       u32 stat = nv_ro32(falcon, 0x008) & dispatch & ~(dispatch >> 16);
+       u64 inst = nv_ro32(falcon, 0x050) & 0x3fffffff;
+       u32 ssta = nv_ro32(falcon, 0x040) & 0x0000ffff;
+       u32 addr = nv_ro32(falcon, 0x040) >> 16;
+       u32 mthd = (addr & 0x07ff) << 2;
+       u32 subc = (addr & 0x3800) >> 11;
+       u32 data = nv_ro32(falcon, 0x044);
+       int chid;
+
+       engctx = nvkm_engctx_get(engine, inst);
+       chid   = pfifo->chid(pfifo, engctx);
+
+       if (stat & 0x00000040) {
+               nv_error(falcon, "DISPATCH_ERROR [");
+               nvkm_enum_print(gt215_ce_isr_error_name, ssta);
+               pr_cont("] ch %d [0x%010llx %s] subc %d mthd 0x%04x data 0x%08x\n",
+                      chid, inst << 12, nvkm_client_name(engctx), subc,
+                      mthd, data);
+               nv_wo32(falcon, 0x004, 0x00000040);
+               stat &= ~0x00000040;
+       }
+
+       if (stat) {
+               nv_error(falcon, "unhandled intr 0x%08x\n", stat);
+               nv_wo32(falcon, 0x004, stat);
+       }
+
+       nvkm_engctx_put(engctx);
+}
+
+static int
+gt215_ce_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+             struct nvkm_oclass *oclass, void *data, u32 size,
+             struct nvkm_object **pobject)
+{
+       bool enable = (nv_device(parent)->chipset != 0xaf);
+       struct gt215_ce_priv *priv;
+       int ret;
+
+       ret = nvkm_falcon_create(parent, engine, oclass, 0x104000, enable,
+                                "PCE0", "ce0", &priv);
+       *pobject = nv_object(priv);
+       if (ret)
+               return ret;
+
+       nv_subdev(priv)->unit = 0x00802000;
+       nv_subdev(priv)->intr = gt215_ce_intr;
+       nv_engine(priv)->cclass = &gt215_ce_cclass;
+       nv_engine(priv)->sclass = gt215_ce_sclass;
+       nv_falcon(priv)->code.data = gt215_pce_code;
+       nv_falcon(priv)->code.size = sizeof(gt215_pce_code);
+       nv_falcon(priv)->data.data = gt215_pce_data;
+       nv_falcon(priv)->data.size = sizeof(gt215_pce_data);
+       return 0;
+}
+
+struct nvkm_oclass
+gt215_ce_oclass = {
+       .handle = NV_ENGINE(CE0, 0xa3),
+       .ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = gt215_ce_ctor,
+               .dtor = _nvkm_falcon_dtor,
+               .init = _nvkm_falcon_init,
+               .fini = _nvkm_falcon_fini,
+               .rd32 = _nvkm_falcon_rd32,
+               .wr32 = _nvkm_falcon_wr32,
+       },
+};
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/cipher/Kbuild b/drivers/gpu/drm/nouveau/nvkm/engine/cipher/Kbuild
new file mode 100644 (file)
index 0000000..fa39945
--- /dev/null
@@ -0,0 +1 @@
+nvkm-y += nvkm/engine/cipher/g84.o
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/cipher/g84.c b/drivers/gpu/drm/nouveau/nvkm/engine/cipher/g84.c
new file mode 100644 (file)
index 0000000..13f3042
--- /dev/null
@@ -0,0 +1,184 @@
+/*
+ * Copyright 2012 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 <engine/cipher.h>
+#include <engine/fifo.h>
+
+#include <core/client.h>
+#include <core/engctx.h>
+#include <core/enum.h>
+
+struct g84_cipher_priv {
+       struct nvkm_engine base;
+};
+
+/*******************************************************************************
+ * Crypt object classes
+ ******************************************************************************/
+
+static int
+g84_cipher_object_ctor(struct nvkm_object *parent,
+                      struct nvkm_object *engine,
+                      struct nvkm_oclass *oclass, void *data, u32 size,
+                      struct nvkm_object **pobject)
+{
+       struct nvkm_gpuobj *obj;
+       int ret;
+
+       ret = nvkm_gpuobj_create(parent, engine, oclass, 0, parent,
+                                16, 16, 0, &obj);
+       *pobject = nv_object(obj);
+       if (ret)
+               return ret;
+
+       nv_wo32(obj, 0x00, nv_mclass(obj));
+       nv_wo32(obj, 0x04, 0x00000000);
+       nv_wo32(obj, 0x08, 0x00000000);
+       nv_wo32(obj, 0x0c, 0x00000000);
+       return 0;
+}
+
+static struct nvkm_ofuncs
+g84_cipher_ofuncs = {
+       .ctor = g84_cipher_object_ctor,
+       .dtor = _nvkm_gpuobj_dtor,
+       .init = _nvkm_gpuobj_init,
+       .fini = _nvkm_gpuobj_fini,
+       .rd32 = _nvkm_gpuobj_rd32,
+       .wr32 = _nvkm_gpuobj_wr32,
+};
+
+static struct nvkm_oclass
+g84_cipher_sclass[] = {
+       { 0x74c1, &g84_cipher_ofuncs },
+       {}
+};
+
+/*******************************************************************************
+ * PCIPHER context
+ ******************************************************************************/
+
+static struct nvkm_oclass
+g84_cipher_cclass = {
+       .handle = NV_ENGCTX(CIPHER, 0x84),
+       .ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = _nvkm_engctx_ctor,
+               .dtor = _nvkm_engctx_dtor,
+               .init = _nvkm_engctx_init,
+               .fini = _nvkm_engctx_fini,
+               .rd32 = _nvkm_engctx_rd32,
+               .wr32 = _nvkm_engctx_wr32,
+       },
+};
+
+/*******************************************************************************
+ * PCIPHER engine/subdev functions
+ ******************************************************************************/
+
+static const struct nvkm_bitfield
+g84_cipher_intr_mask[] = {
+       { 0x00000001, "INVALID_STATE" },
+       { 0x00000002, "ILLEGAL_MTHD" },
+       { 0x00000004, "ILLEGAL_CLASS" },
+       { 0x00000080, "QUERY" },
+       { 0x00000100, "FAULT" },
+       {}
+};
+
+static void
+g84_cipher_intr(struct nvkm_subdev *subdev)
+{
+       struct nvkm_fifo *pfifo = nvkm_fifo(subdev);
+       struct nvkm_engine *engine = nv_engine(subdev);
+       struct nvkm_object *engctx;
+       struct g84_cipher_priv *priv = (void *)subdev;
+       u32 stat = nv_rd32(priv, 0x102130);
+       u32 mthd = nv_rd32(priv, 0x102190);
+       u32 data = nv_rd32(priv, 0x102194);
+       u32 inst = nv_rd32(priv, 0x102188) & 0x7fffffff;
+       int chid;
+
+       engctx = nvkm_engctx_get(engine, inst);
+       chid   = pfifo->chid(pfifo, engctx);
+
+       if (stat) {
+               nv_error(priv, "%s", "");
+               nvkm_bitfield_print(g84_cipher_intr_mask, stat);
+               pr_cont(" ch %d [0x%010llx %s] mthd 0x%04x data 0x%08x\n",
+                      chid, (u64)inst << 12, nvkm_client_name(engctx),
+                      mthd, data);
+       }
+
+       nv_wr32(priv, 0x102130, stat);
+       nv_wr32(priv, 0x10200c, 0x10);
+
+       nvkm_engctx_put(engctx);
+}
+
+static int
+g84_cipher_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+               struct nvkm_oclass *oclass, void *data, u32 size,
+               struct nvkm_object **pobject)
+{
+       struct g84_cipher_priv *priv;
+       int ret;
+
+       ret = nvkm_engine_create(parent, engine, oclass, true,
+                                "PCIPHER", "cipher", &priv);
+       *pobject = nv_object(priv);
+       if (ret)
+               return ret;
+
+       nv_subdev(priv)->unit = 0x00004000;
+       nv_subdev(priv)->intr = g84_cipher_intr;
+       nv_engine(priv)->cclass = &g84_cipher_cclass;
+       nv_engine(priv)->sclass = g84_cipher_sclass;
+       return 0;
+}
+
+static int
+g84_cipher_init(struct nvkm_object *object)
+{
+       struct g84_cipher_priv *priv = (void *)object;
+       int ret;
+
+       ret = nvkm_engine_init(&priv->base);
+       if (ret)
+               return ret;
+
+       nv_wr32(priv, 0x102130, 0xffffffff);
+       nv_wr32(priv, 0x102140, 0xffffffbf);
+       nv_wr32(priv, 0x10200c, 0x00000010);
+       return 0;
+}
+
+struct nvkm_oclass
+g84_cipher_oclass = {
+       .handle = NV_ENGINE(CIPHER, 0x84),
+       .ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = g84_cipher_ctor,
+               .dtor = _nvkm_engine_dtor,
+               .init = g84_cipher_init,
+               .fini = _nvkm_engine_fini,
+       },
+};
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/device/Kbuild b/drivers/gpu/drm/nouveau/nvkm/engine/device/Kbuild
new file mode 100644 (file)
index 0000000..de1bf09
--- /dev/null
@@ -0,0 +1,12 @@
+nvkm-y += nvkm/engine/device/acpi.o
+nvkm-y += nvkm/engine/device/base.o
+nvkm-y += nvkm/engine/device/ctrl.o
+nvkm-y += nvkm/engine/device/nv04.o
+nvkm-y += nvkm/engine/device/nv10.o
+nvkm-y += nvkm/engine/device/nv20.o
+nvkm-y += nvkm/engine/device/nv30.o
+nvkm-y += nvkm/engine/device/nv40.o
+nvkm-y += nvkm/engine/device/nv50.o
+nvkm-y += nvkm/engine/device/gf100.o
+nvkm-y += nvkm/engine/device/gk104.o
+nvkm-y += nvkm/engine/device/gm100.o
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/device/acpi.c b/drivers/gpu/drm/nouveau/nvkm/engine/device/acpi.c
new file mode 100644 (file)
index 0000000..f42706e
--- /dev/null
@@ -0,0 +1,60 @@
+/*
+ * Copyright 2014 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 "acpi.h"
+
+#include <core/device.h>
+
+#ifdef CONFIG_ACPI
+static int
+nvkm_acpi_ntfy(struct notifier_block *nb, unsigned long val, void *data)
+{
+       struct nvkm_device *device =
+               container_of(nb, typeof(*device), acpi.nb);
+       struct acpi_bus_event *info = data;
+
+       if (!strcmp(info->device_class, "ac_adapter"))
+               nvkm_event_send(&device->event, 1, 0, NULL, 0);
+
+       return NOTIFY_DONE;
+}
+#endif
+
+int
+nvkm_acpi_fini(struct nvkm_device *device, bool suspend)
+{
+#ifdef CONFIG_ACPI
+       unregister_acpi_notifier(&device->acpi.nb);
+#endif
+       return 0;
+}
+
+int
+nvkm_acpi_init(struct nvkm_device *device)
+{
+#ifdef CONFIG_ACPI
+       device->acpi.nb.notifier_call = nvkm_acpi_ntfy;
+       register_acpi_notifier(&device->acpi.nb);
+#endif
+       return 0;
+}
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/device/acpi.h b/drivers/gpu/drm/nouveau/nvkm/engine/device/acpi.h
new file mode 100644 (file)
index 0000000..82dd359
--- /dev/null
@@ -0,0 +1,8 @@
+#ifndef __NVKM_DEVICE_ACPI_H__
+#define __NVKM_DEVICE_ACPI_H__
+#include <core/os.h>
+struct nvkm_device;
+
+int nvkm_acpi_init(struct nvkm_device *);
+int nvkm_acpi_fini(struct nvkm_device *, bool);
+#endif
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/device/base.c b/drivers/gpu/drm/nouveau/nvkm/engine/device/base.c
new file mode 100644 (file)
index 0000000..29bd539
--- /dev/null
@@ -0,0 +1,730 @@
+/*
+ * Copyright 2012 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 "priv.h"
+#include "acpi.h"
+
+#include <core/client.h>
+#include <core/option.h>
+#include <core/notify.h>
+#include <core/parent.h>
+#include <subdev/bios.h>
+#include <subdev/fb.h>
+#include <subdev/instmem.h>
+
+#include <nvif/class.h>
+#include <nvif/unpack.h>
+
+static DEFINE_MUTEX(nv_devices_mutex);
+static LIST_HEAD(nv_devices);
+
+struct nvkm_device *
+nvkm_device_find(u64 name)
+{
+       struct nvkm_device *device, *match = NULL;
+       mutex_lock(&nv_devices_mutex);
+       list_for_each_entry(device, &nv_devices, head) {
+               if (device->handle == name) {
+                       match = device;
+                       break;
+               }
+       }
+       mutex_unlock(&nv_devices_mutex);
+       return match;
+}
+
+int
+nvkm_device_list(u64 *name, int size)
+{
+       struct nvkm_device *device;
+       int nr = 0;
+       mutex_lock(&nv_devices_mutex);
+       list_for_each_entry(device, &nv_devices, head) {
+               if (nr++ < size)
+                       name[nr - 1] = device->handle;
+       }
+       mutex_unlock(&nv_devices_mutex);
+       return nr;
+}
+
+/******************************************************************************
+ * nvkm_devobj (0x0080): class implementation
+ *****************************************************************************/
+
+struct nvkm_devobj {
+       struct nvkm_parent base;
+       struct nvkm_object *subdev[NVDEV_SUBDEV_NR];
+};
+
+static int
+nvkm_devobj_info(struct nvkm_object *object, void *data, u32 size)
+{
+       struct nvkm_device *device = nv_device(object);
+       struct nvkm_fb *pfb = nvkm_fb(device);
+       struct nvkm_instmem *imem = nvkm_instmem(device);
+       union {
+               struct nv_device_info_v0 v0;
+       } *args = data;
+       int ret;
+
+       nv_ioctl(object, "device info size %d\n", size);
+       if (nvif_unpack(args->v0, 0, 0, false)) {
+               nv_ioctl(object, "device info vers %d\n", args->v0.version);
+       } else
+               return ret;
+
+       switch (device->chipset) {
+       case 0x01a:
+       case 0x01f:
+       case 0x04c:
+       case 0x04e:
+       case 0x063:
+       case 0x067:
+       case 0x068:
+       case 0x0aa:
+       case 0x0ac:
+       case 0x0af:
+               args->v0.platform = NV_DEVICE_INFO_V0_IGP;
+               break;
+       default:
+               if (device->pdev) {
+                       if (pci_find_capability(device->pdev, PCI_CAP_ID_AGP))
+                               args->v0.platform = NV_DEVICE_INFO_V0_AGP;
+                       else
+                       if (pci_is_pcie(device->pdev))
+                               args->v0.platform = NV_DEVICE_INFO_V0_PCIE;
+                       else
+                               args->v0.platform = NV_DEVICE_INFO_V0_PCI;
+               } else {
+                       args->v0.platform = NV_DEVICE_INFO_V0_SOC;
+               }
+               break;
+       }
+
+       switch (device->card_type) {
+       case NV_04: args->v0.family = NV_DEVICE_INFO_V0_TNT; break;
+       case NV_10:
+       case NV_11: args->v0.family = NV_DEVICE_INFO_V0_CELSIUS; break;
+       case NV_20: args->v0.family = NV_DEVICE_INFO_V0_KELVIN; break;
+       case NV_30: args->v0.family = NV_DEVICE_INFO_V0_RANKINE; break;
+       case NV_40: args->v0.family = NV_DEVICE_INFO_V0_CURIE; break;
+       case NV_50: args->v0.family = NV_DEVICE_INFO_V0_TESLA; break;
+       case NV_C0: args->v0.family = NV_DEVICE_INFO_V0_FERMI; break;
+       case NV_E0: args->v0.family = NV_DEVICE_INFO_V0_KEPLER; break;
+       case GM100: args->v0.family = NV_DEVICE_INFO_V0_MAXWELL; break;
+       default:
+               args->v0.family = 0;
+               break;
+       }
+
+       args->v0.chipset  = device->chipset;
+       args->v0.revision = device->chiprev;
+       if (pfb)  args->v0.ram_size = args->v0.ram_user = pfb->ram->size;
+       else      args->v0.ram_size = args->v0.ram_user = 0;
+       if (imem) args->v0.ram_user = args->v0.ram_user - imem->reserved;
+       return 0;
+}
+
+static int
+nvkm_devobj_mthd(struct nvkm_object *object, u32 mthd, void *data, u32 size)
+{
+       switch (mthd) {
+       case NV_DEVICE_V0_INFO:
+               return nvkm_devobj_info(object, data, size);
+       default:
+               break;
+       }
+       return -EINVAL;
+}
+
+static u8
+nvkm_devobj_rd08(struct nvkm_object *object, u64 addr)
+{
+       return nv_rd08(object->engine, addr);
+}
+
+static u16
+nvkm_devobj_rd16(struct nvkm_object *object, u64 addr)
+{
+       return nv_rd16(object->engine, addr);
+}
+
+static u32
+nvkm_devobj_rd32(struct nvkm_object *object, u64 addr)
+{
+       return nv_rd32(object->engine, addr);
+}
+
+static void
+nvkm_devobj_wr08(struct nvkm_object *object, u64 addr, u8 data)
+{
+       nv_wr08(object->engine, addr, data);
+}
+
+static void
+nvkm_devobj_wr16(struct nvkm_object *object, u64 addr, u16 data)
+{
+       nv_wr16(object->engine, addr, data);
+}
+
+static void
+nvkm_devobj_wr32(struct nvkm_object *object, u64 addr, u32 data)
+{
+       nv_wr32(object->engine, addr, data);
+}
+
+static int
+nvkm_devobj_map(struct nvkm_object *object, u64 *addr, u32 *size)
+{
+       struct nvkm_device *device = nv_device(object);
+       *addr = nv_device_resource_start(device, 0);
+       *size = nv_device_resource_len(device, 0);
+       return 0;
+}
+
+static const u64 disable_map[] = {
+       [NVDEV_SUBDEV_VBIOS]    = NV_DEVICE_V0_DISABLE_VBIOS,
+       [NVDEV_SUBDEV_DEVINIT]  = NV_DEVICE_V0_DISABLE_CORE,
+       [NVDEV_SUBDEV_GPIO]     = NV_DEVICE_V0_DISABLE_CORE,
+       [NVDEV_SUBDEV_I2C]      = NV_DEVICE_V0_DISABLE_CORE,
+       [NVDEV_SUBDEV_CLK  ]    = NV_DEVICE_V0_DISABLE_CORE,
+       [NVDEV_SUBDEV_MXM]      = NV_DEVICE_V0_DISABLE_CORE,
+       [NVDEV_SUBDEV_MC]       = NV_DEVICE_V0_DISABLE_CORE,
+       [NVDEV_SUBDEV_BUS]      = NV_DEVICE_V0_DISABLE_CORE,
+       [NVDEV_SUBDEV_TIMER]    = NV_DEVICE_V0_DISABLE_CORE,
+       [NVDEV_SUBDEV_FB]       = NV_DEVICE_V0_DISABLE_CORE,
+       [NVDEV_SUBDEV_LTC]      = NV_DEVICE_V0_DISABLE_CORE,
+       [NVDEV_SUBDEV_IBUS]     = NV_DEVICE_V0_DISABLE_CORE,
+       [NVDEV_SUBDEV_INSTMEM]  = NV_DEVICE_V0_DISABLE_CORE,
+       [NVDEV_SUBDEV_MMU]      = NV_DEVICE_V0_DISABLE_CORE,
+       [NVDEV_SUBDEV_BAR]      = NV_DEVICE_V0_DISABLE_CORE,
+       [NVDEV_SUBDEV_VOLT]     = NV_DEVICE_V0_DISABLE_CORE,
+       [NVDEV_SUBDEV_THERM]    = NV_DEVICE_V0_DISABLE_CORE,
+       [NVDEV_SUBDEV_PMU]      = NV_DEVICE_V0_DISABLE_CORE,
+       [NVDEV_SUBDEV_FUSE]     = NV_DEVICE_V0_DISABLE_CORE,
+       [NVDEV_ENGINE_DMAOBJ]   = NV_DEVICE_V0_DISABLE_CORE,
+       [NVDEV_ENGINE_PM     ]  = NV_DEVICE_V0_DISABLE_CORE,
+       [NVDEV_ENGINE_FIFO]     = NV_DEVICE_V0_DISABLE_FIFO,
+       [NVDEV_ENGINE_SW]       = NV_DEVICE_V0_DISABLE_FIFO,
+       [NVDEV_ENGINE_GR]       = NV_DEVICE_V0_DISABLE_GR,
+       [NVDEV_ENGINE_MPEG]     = NV_DEVICE_V0_DISABLE_MPEG,
+       [NVDEV_ENGINE_ME]       = NV_DEVICE_V0_DISABLE_ME,
+       [NVDEV_ENGINE_VP]       = NV_DEVICE_V0_DISABLE_VP,
+       [NVDEV_ENGINE_CIPHER]   = NV_DEVICE_V0_DISABLE_CIPHER,
+       [NVDEV_ENGINE_BSP]      = NV_DEVICE_V0_DISABLE_BSP,
+       [NVDEV_ENGINE_MSPPP]    = NV_DEVICE_V0_DISABLE_MSPPP,
+       [NVDEV_ENGINE_CE0]      = NV_DEVICE_V0_DISABLE_CE0,
+       [NVDEV_ENGINE_CE1]      = NV_DEVICE_V0_DISABLE_CE1,
+       [NVDEV_ENGINE_CE2]      = NV_DEVICE_V0_DISABLE_CE2,
+       [NVDEV_ENGINE_VIC]      = NV_DEVICE_V0_DISABLE_VIC,
+       [NVDEV_ENGINE_MSENC]    = NV_DEVICE_V0_DISABLE_MSENC,
+       [NVDEV_ENGINE_DISP]     = NV_DEVICE_V0_DISABLE_DISP,
+       [NVDEV_ENGINE_MSVLD]    = NV_DEVICE_V0_DISABLE_MSVLD,
+       [NVDEV_ENGINE_SEC]      = NV_DEVICE_V0_DISABLE_SEC,
+       [NVDEV_SUBDEV_NR]       = 0,
+};
+
+static void
+nvkm_devobj_dtor(struct nvkm_object *object)
+{
+       struct nvkm_devobj *devobj = (void *)object;
+       int i;
+
+       for (i = NVDEV_SUBDEV_NR - 1; i >= 0; i--)
+               nvkm_object_ref(NULL, &devobj->subdev[i]);
+
+       nvkm_parent_destroy(&devobj->base);
+}
+
+static struct nvkm_oclass
+nvkm_devobj_oclass_super = {
+       .handle = NV_DEVICE,
+       .ofuncs = &(struct nvkm_ofuncs) {
+               .dtor = nvkm_devobj_dtor,
+               .init = _nvkm_parent_init,
+               .fini = _nvkm_parent_fini,
+               .mthd = nvkm_devobj_mthd,
+               .map  = nvkm_devobj_map,
+               .rd08 = nvkm_devobj_rd08,
+               .rd16 = nvkm_devobj_rd16,
+               .rd32 = nvkm_devobj_rd32,
+               .wr08 = nvkm_devobj_wr08,
+               .wr16 = nvkm_devobj_wr16,
+               .wr32 = nvkm_devobj_wr32,
+       }
+};
+
+static int
+nvkm_devobj_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+                struct nvkm_oclass *oclass, void *data, u32 size,
+                struct nvkm_object **pobject)
+{
+       union {
+               struct nv_device_v0 v0;
+       } *args = data;
+       struct nvkm_client *client = nv_client(parent);
+       struct nvkm_device *device;
+       struct nvkm_devobj *devobj;
+       u32 boot0, strap;
+       u64 disable, mmio_base, mmio_size;
+       void __iomem *map;
+       int ret, i, c;
+
+       nv_ioctl(parent, "create device size %d\n", size);
+       if (nvif_unpack(args->v0, 0, 0, false)) {
+               nv_ioctl(parent, "create device v%d device %016llx "
+                                "disable %016llx debug0 %016llx\n",
+                        args->v0.version, args->v0.device,
+                        args->v0.disable, args->v0.debug0);
+       } else
+               return ret;
+
+       /* give priviledged clients register access */
+       if (client->super)
+               oclass = &nvkm_devobj_oclass_super;
+
+       /* find the device subdev that matches what the client requested */
+       device = nv_device(client->device);
+       if (args->v0.device != ~0) {
+               device = nvkm_device_find(args->v0.device);
+               if (!device)
+                       return -ENODEV;
+       }
+
+       ret = nvkm_parent_create(parent, nv_object(device), oclass, 0,
+                                nvkm_control_oclass,
+                                (1ULL << NVDEV_ENGINE_DMAOBJ) |
+                                (1ULL << NVDEV_ENGINE_FIFO) |
+                                (1ULL << NVDEV_ENGINE_DISP) |
+                                (1ULL << NVDEV_ENGINE_PM), &devobj);
+       *pobject = nv_object(devobj);
+       if (ret)
+               return ret;
+
+       mmio_base = nv_device_resource_start(device, 0);
+       mmio_size = nv_device_resource_len(device, 0);
+
+       /* translate api disable mask into internal mapping */
+       disable = args->v0.debug0;
+       for (i = 0; i < NVDEV_SUBDEV_NR; i++) {
+               if (args->v0.disable & disable_map[i])
+                       disable |= (1ULL << i);
+       }
+
+       /* identify the chipset, and determine classes of subdev/engines */
+       if (!(args->v0.disable & NV_DEVICE_V0_DISABLE_IDENTIFY) &&
+           !device->card_type) {
+               map = ioremap(mmio_base, 0x102000);
+               if (map == NULL)
+                       return -ENOMEM;
+
+               /* switch mmio to cpu's native endianness */
+#ifndef __BIG_ENDIAN
+               if (ioread32_native(map + 0x000004) != 0x00000000)
+#else
+               if (ioread32_native(map + 0x000004) == 0x00000000)
+#endif
+                       iowrite32_native(0x01000001, map + 0x000004);
+
+               /* read boot0 and strapping information */
+               boot0 = ioread32_native(map + 0x000000);
+               strap = ioread32_native(map + 0x101000);
+               iounmap(map);
+
+               /* determine chipset and derive architecture from it */
+               if ((boot0 & 0x1f000000) > 0) {
+                       device->chipset = (boot0 & 0x1ff00000) >> 20;
+                       device->chiprev = (boot0 & 0x000000ff);
+                       switch (device->chipset & 0x1f0) {
+                       case 0x010: {
+                               if (0x461 & (1 << (device->chipset & 0xf)))
+                                       device->card_type = NV_10;
+                               else
+                                       device->card_type = NV_11;
+                               device->chiprev = 0x00;
+                               break;
+                       }
+                       case 0x020: device->card_type = NV_20; break;
+                       case 0x030: device->card_type = NV_30; break;
+                       case 0x040:
+                       case 0x060: device->card_type = NV_40; break;
+                       case 0x050:
+                       case 0x080:
+                       case 0x090:
+                       case 0x0a0: device->card_type = NV_50; break;
+                       case 0x0c0:
+                       case 0x0d0: device->card_type = NV_C0; break;
+                       case 0x0e0:
+                       case 0x0f0:
+                       case 0x100: device->card_type = NV_E0; break;
+                       case 0x110:
+                       case 0x120: device->card_type = GM100; break;
+                       default:
+                               break;
+                       }
+               } else
+               if ((boot0 & 0xff00fff0) == 0x20004000) {
+                       if (boot0 & 0x00f00000)
+                               device->chipset = 0x05;
+                       else
+                               device->chipset = 0x04;
+                       device->card_type = NV_04;
+               }
+
+               switch (device->card_type) {
+               case NV_04: ret = nv04_identify(device); break;
+               case NV_10:
+               case NV_11: ret = nv10_identify(device); break;
+               case NV_20: ret = nv20_identify(device); break;
+               case NV_30: ret = nv30_identify(device); break;
+               case NV_40: ret = nv40_identify(device); break;
+               case NV_50: ret = nv50_identify(device); break;
+               case NV_C0: ret = gf100_identify(device); break;
+               case NV_E0: ret = gk104_identify(device); break;
+               case GM100: ret = gm100_identify(device); break;
+               default:
+                       ret = -EINVAL;
+                       break;
+               }
+
+               if (ret) {
+                       nv_error(device, "unknown chipset, 0x%08x\n", boot0);
+                       return ret;
+               }
+
+               nv_info(device, "BOOT0  : 0x%08x\n", boot0);
+               nv_info(device, "Chipset: %s (NV%02X)\n",
+                       device->cname, device->chipset);
+               nv_info(device, "Family : NV%02X\n", device->card_type);
+
+               /* determine frequency of timing crystal */
+               if ( device->card_type <= NV_10 || device->chipset < 0x17 ||
+                   (device->chipset >= 0x20 && device->chipset < 0x25))
+                       strap &= 0x00000040;
+               else
+                       strap &= 0x00400040;
+
+               switch (strap) {
+               case 0x00000000: device->crystal = 13500; break;
+               case 0x00000040: device->crystal = 14318; break;
+               case 0x00400000: device->crystal = 27000; break;
+               case 0x00400040: device->crystal = 25000; break;
+               }
+
+               nv_debug(device, "crystal freq: %dKHz\n", device->crystal);
+       } else
+       if ( (args->v0.disable & NV_DEVICE_V0_DISABLE_IDENTIFY)) {
+               device->cname = "NULL";
+               device->oclass[NVDEV_SUBDEV_VBIOS] = &nvkm_bios_oclass;
+       }
+
+       if (!(args->v0.disable & NV_DEVICE_V0_DISABLE_MMIO) &&
+           !nv_subdev(device)->mmio) {
+               nv_subdev(device)->mmio  = ioremap(mmio_base, mmio_size);
+               if (!nv_subdev(device)->mmio) {
+                       nv_error(device, "unable to map device registers\n");
+                       return -ENOMEM;
+               }
+       }
+
+       /* ensure requested subsystems are available for use */
+       for (i = 1, c = 1; i < NVDEV_SUBDEV_NR; i++) {
+               if (!(oclass = device->oclass[i]) || (disable & (1ULL << i)))
+                       continue;
+
+               if (device->subdev[i]) {
+                       nvkm_object_ref(device->subdev[i], &devobj->subdev[i]);
+                       continue;
+               }
+
+               ret = nvkm_object_ctor(nv_object(device), NULL, oclass,
+                                      NULL, i, &devobj->subdev[i]);
+               if (ret == -ENODEV)
+                       continue;
+               if (ret)
+                       return ret;
+
+               device->subdev[i] = devobj->subdev[i];
+
+               /* note: can't init *any* subdevs until devinit has been run
+                * due to not knowing exactly what the vbios init tables will
+                * mess with.  devinit also can't be run until all of its
+                * dependencies have been created.
+                *
+                * this code delays init of any subdev until all of devinit's
+                * dependencies have been created, and then initialises each
+                * subdev in turn as they're created.
+                */
+               while (i >= NVDEV_SUBDEV_DEVINIT_LAST && c <= i) {
+                       struct nvkm_object *subdev = devobj->subdev[c++];
+                       if (subdev && !nv_iclass(subdev, NV_ENGINE_CLASS)) {
+                               ret = nvkm_object_inc(subdev);
+                               if (ret)
+                                       return ret;
+                               atomic_dec(&nv_object(device)->usecount);
+                       } else
+                       if (subdev) {
+                               nvkm_subdev_reset(subdev);
+                       }
+               }
+       }
+
+       return 0;
+}
+
+static struct nvkm_ofuncs
+nvkm_devobj_ofuncs = {
+       .ctor = nvkm_devobj_ctor,
+       .dtor = nvkm_devobj_dtor,
+       .init = _nvkm_parent_init,
+       .fini = _nvkm_parent_fini,
+       .mthd = nvkm_devobj_mthd,
+};
+
+/******************************************************************************
+ * nvkm_device: engine functions
+ *****************************************************************************/
+
+struct nvkm_device *
+nv_device(void *obj)
+{
+       struct nvkm_object *device = nv_object(obj);
+       if (device->engine == NULL) {
+               while (device && device->parent)
+                       device = device->parent;
+       } else {
+               device = &nv_object(obj)->engine->subdev.object;
+               if (device && device->parent)
+                       device = device->parent;
+       }
+#if CONFIG_NOUVEAU_DEBUG >= NV_DBG_PARANOIA
+       if (unlikely(!device))
+               nv_assert("BAD CAST -> NvDevice, 0x%08x\n", nv_hclass(obj));
+#endif
+       return (void *)device;
+}
+
+static struct nvkm_oclass
+nvkm_device_sclass[] = {
+       { 0x0080, &nvkm_devobj_ofuncs },
+       {}
+};
+
+static int
+nvkm_device_event_ctor(struct nvkm_object *object, void *data, u32 size,
+                      struct nvkm_notify *notify)
+{
+       if (!WARN_ON(size != 0)) {
+               notify->size  = 0;
+               notify->types = 1;
+               notify->index = 0;
+               return 0;
+       }
+       return -EINVAL;
+}
+
+static const struct nvkm_event_func
+nvkm_device_event_func = {
+       .ctor = nvkm_device_event_ctor,
+};
+
+static int
+nvkm_device_fini(struct nvkm_object *object, bool suspend)
+{
+       struct nvkm_device *device = (void *)object;
+       struct nvkm_object *subdev;
+       int ret, i;
+
+       for (i = NVDEV_SUBDEV_NR - 1; i >= 0; i--) {
+               if ((subdev = device->subdev[i])) {
+                       if (!nv_iclass(subdev, NV_ENGINE_CLASS)) {
+                               ret = nvkm_object_dec(subdev, suspend);
+                               if (ret && suspend)
+                                       goto fail;
+                       }
+               }
+       }
+
+       ret = nvkm_acpi_fini(device, suspend);
+fail:
+       for (; ret && i < NVDEV_SUBDEV_NR; i++) {
+               if ((subdev = device->subdev[i])) {
+                       if (!nv_iclass(subdev, NV_ENGINE_CLASS)) {
+                               ret = nvkm_object_inc(subdev);
+                               if (ret) {
+                                       /* XXX */
+                               }
+                       }
+               }
+       }
+
+       return ret;
+}
+
+static int
+nvkm_device_init(struct nvkm_object *object)
+{
+       struct nvkm_device *device = (void *)object;
+       struct nvkm_object *subdev;
+       int ret, i = 0;
+
+       ret = nvkm_acpi_init(device);
+       if (ret)
+               goto fail;
+
+       for (i = 0; i < NVDEV_SUBDEV_NR; i++) {
+               if ((subdev = device->subdev[i])) {
+                       if (!nv_iclass(subdev, NV_ENGINE_CLASS)) {
+                               ret = nvkm_object_inc(subdev);
+                               if (ret)
+                                       goto fail;
+                       } else {
+                               nvkm_subdev_reset(subdev);
+                       }
+               }
+       }
+
+       ret = 0;
+fail:
+       for (--i; ret && i >= 0; i--) {
+               if ((subdev = device->subdev[i])) {
+                       if (!nv_iclass(subdev, NV_ENGINE_CLASS))
+                               nvkm_object_dec(subdev, false);
+               }
+       }
+
+       if (ret)
+               nvkm_acpi_fini(device, false);
+       return ret;
+}
+
+static void
+nvkm_device_dtor(struct nvkm_object *object)
+{
+       struct nvkm_device *device = (void *)object;
+
+       nvkm_event_fini(&device->event);
+
+       mutex_lock(&nv_devices_mutex);
+       list_del(&device->head);
+       mutex_unlock(&nv_devices_mutex);
+
+       if (nv_subdev(device)->mmio)
+               iounmap(nv_subdev(device)->mmio);
+
+       nvkm_engine_destroy(&device->engine);
+}
+
+resource_size_t
+nv_device_resource_start(struct nvkm_device *device, unsigned int bar)
+{
+       if (nv_device_is_pci(device)) {
+               return pci_resource_start(device->pdev, bar);
+       } else {
+               struct resource *res;
+               res = platform_get_resource(device->platformdev,
+                                           IORESOURCE_MEM, bar);
+               if (!res)
+                       return 0;
+               return res->start;
+       }
+}
+
+resource_size_t
+nv_device_resource_len(struct nvkm_device *device, unsigned int bar)
+{
+       if (nv_device_is_pci(device)) {
+               return pci_resource_len(device->pdev, bar);
+       } else {
+               struct resource *res;
+               res = platform_get_resource(device->platformdev,
+                                           IORESOURCE_MEM, bar);
+               if (!res)
+                       return 0;
+               return resource_size(res);
+       }
+}
+
+int
+nv_device_get_irq(struct nvkm_device *device, bool stall)
+{
+       if (nv_device_is_pci(device)) {
+               return device->pdev->irq;
+       } else {
+               return platform_get_irq_byname(device->platformdev,
+                                              stall ? "stall" : "nonstall");
+       }
+}
+
+static struct nvkm_oclass
+nvkm_device_oclass = {
+       .handle = NV_ENGINE(DEVICE, 0x00),
+       .ofuncs = &(struct nvkm_ofuncs) {
+               .dtor = nvkm_device_dtor,
+               .init = nvkm_device_init,
+               .fini = nvkm_device_fini,
+       },
+};
+
+int
+nvkm_device_create_(void *dev, enum nv_bus_type type, u64 name,
+                   const char *sname, const char *cfg, const char *dbg,
+                   int length, void **pobject)
+{
+       struct nvkm_device *device;
+       int ret = -EEXIST;
+
+       mutex_lock(&nv_devices_mutex);
+       list_for_each_entry(device, &nv_devices, head) {
+               if (device->handle == name)
+                       goto done;
+       }
+
+       ret = nvkm_engine_create_(NULL, NULL, &nvkm_device_oclass, true,
+                                 "DEVICE", "device", length, pobject);
+       device = *pobject;
+       if (ret)
+               goto done;
+
+       switch (type) {
+       case NVKM_BUS_PCI:
+               device->pdev = dev;
+               break;
+       case NVKM_BUS_PLATFORM:
+               device->platformdev = dev;
+               break;
+       }
+       device->handle = name;
+       device->cfgopt = cfg;
+       device->dbgopt = dbg;
+       device->name = sname;
+
+       nv_subdev(device)->debug = nvkm_dbgopt(device->dbgopt, "DEVICE");
+       nv_engine(device)->sclass = nvkm_device_sclass;
+       list_add(&device->head, &nv_devices);
+
+       ret = nvkm_event_init(&nvkm_device_event_func, 1, 1, &device->event);
+done:
+       mutex_unlock(&nv_devices_mutex);
+       return ret;
+}
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/device/ctrl.c b/drivers/gpu/drm/nouveau/nvkm/engine/device/ctrl.c
new file mode 100644 (file)
index 0000000..0b794b1
--- /dev/null
@@ -0,0 +1,199 @@
+/*
+ * Copyright 2013 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 <bskeggs@redhat.com>
+ */
+#include "priv.h"
+
+#include <core/client.h>
+#include <subdev/clk.h>
+
+#include <nvif/class.h>
+#include <nvif/ioctl.h>
+#include <nvif/unpack.h>
+
+static int
+nvkm_control_mthd_pstate_info(struct nvkm_object *object, void *data, u32 size)
+{
+       union {
+               struct nvif_control_pstate_info_v0 v0;
+       } *args = data;
+       struct nvkm_clk *clk = nvkm_clk(object);
+       int ret;
+
+       nv_ioctl(object, "control pstate info size %d\n", size);
+       if (nvif_unpack(args->v0, 0, 0, false)) {
+               nv_ioctl(object, "control pstate info vers %d\n",
+                        args->v0.version);
+       } else
+               return ret;
+
+       if (clk) {
+               args->v0.count = clk->state_nr;
+               args->v0.ustate_ac = clk->ustate_ac;
+               args->v0.ustate_dc = clk->ustate_dc;
+               args->v0.pwrsrc = clk->pwrsrc;
+               args->v0.pstate = clk->pstate;
+       } else {
+               args->v0.count = 0;
+               args->v0.ustate_ac = NVIF_CONTROL_PSTATE_INFO_V0_USTATE_DISABLE;
+               args->v0.ustate_dc = NVIF_CONTROL_PSTATE_INFO_V0_USTATE_DISABLE;
+               args->v0.pwrsrc = -ENOSYS;
+               args->v0.pstate = NVIF_CONTROL_PSTATE_INFO_V0_PSTATE_UNKNOWN;
+       }
+
+       return 0;
+}
+
+static int
+nvkm_control_mthd_pstate_attr(struct nvkm_object *object, void *data, u32 size)
+{
+       union {
+               struct nvif_control_pstate_attr_v0 v0;
+       } *args = data;
+       struct nvkm_clk *clk = nvkm_clk(object);
+       struct nvkm_domain *domain;
+       struct nvkm_pstate *pstate;
+       struct nvkm_cstate *cstate;
+       int i = 0, j = -1;
+       u32 lo, hi;
+       int ret;
+
+       nv_ioctl(object, "control pstate attr size %d\n", size);
+       if (nvif_unpack(args->v0, 0, 0, false)) {
+               nv_ioctl(object, "control pstate attr vers %d state %d "
+                                "index %d\n",
+                        args->v0.version, args->v0.state, args->v0.index);
+               if (!clk)
+                       return -ENODEV;
+               if (args->v0.state < NVIF_CONTROL_PSTATE_ATTR_V0_STATE_CURRENT)
+                       return -EINVAL;
+               if (args->v0.state >= clk->state_nr)
+                       return -EINVAL;
+       } else
+               return ret;
+       domain = clk->domains;
+
+       while (domain->name != nv_clk_src_max) {
+               if (domain->mname && ++j == args->v0.index)
+                       break;
+               domain++;
+       }
+
+       if (domain->name == nv_clk_src_max)
+               return -EINVAL;
+
+       if (args->v0.state != NVIF_CONTROL_PSTATE_ATTR_V0_STATE_CURRENT) {
+               list_for_each_entry(pstate, &clk->states, head) {
+                       if (i++ == args->v0.state)
+                               break;
+               }
+
+               lo = pstate->base.domain[domain->name];
+               hi = lo;
+               list_for_each_entry(cstate, &pstate->list, head) {
+                       lo = min(lo, cstate->domain[domain->name]);
+                       hi = max(hi, cstate->domain[domain->name]);
+               }
+
+               args->v0.state = pstate->pstate;
+       } else {
+               lo = max(clk->read(clk, domain->name), 0);
+               hi = lo;
+       }
+
+       snprintf(args->v0.name, sizeof(args->v0.name), "%s", domain->mname);
+       snprintf(args->v0.unit, sizeof(args->v0.unit), "MHz");
+       args->v0.min = lo / domain->mdiv;
+       args->v0.max = hi / domain->mdiv;
+
+       args->v0.index = 0;
+       while ((++domain)->name != nv_clk_src_max) {
+               if (domain->mname) {
+                       args->v0.index = ++j;
+                       break;
+               }
+       }
+
+       return 0;
+}
+
+static int
+nvkm_control_mthd_pstate_user(struct nvkm_object *object, void *data, u32 size)
+{
+       union {
+               struct nvif_control_pstate_user_v0 v0;
+       } *args = data;
+       struct nvkm_clk *clk = nvkm_clk(object);
+       int ret;
+
+       nv_ioctl(object, "control pstate user size %d\n", size);
+       if (nvif_unpack(args->v0, 0, 0, false)) {
+               nv_ioctl(object, "control pstate user vers %d ustate %d "
+                                "pwrsrc %d\n", args->v0.version,
+                        args->v0.ustate, args->v0.pwrsrc);
+               if (!clk)
+                       return -ENODEV;
+       } else
+               return ret;
+
+       if (args->v0.pwrsrc >= 0) {
+               ret |= nvkm_clk_ustate(clk, args->v0.ustate, args->v0.pwrsrc);
+       } else {
+               ret |= nvkm_clk_ustate(clk, args->v0.ustate, 0);
+               ret |= nvkm_clk_ustate(clk, args->v0.ustate, 1);
+       }
+
+       return ret;
+}
+
+static int
+nvkm_control_mthd(struct nvkm_object *object, u32 mthd, void *data, u32 size)
+{
+       switch (mthd) {
+       case NVIF_CONTROL_PSTATE_INFO:
+               return nvkm_control_mthd_pstate_info(object, data, size);
+       case NVIF_CONTROL_PSTATE_ATTR:
+               return nvkm_control_mthd_pstate_attr(object, data, size);
+       case NVIF_CONTROL_PSTATE_USER:
+               return nvkm_control_mthd_pstate_user(object, data, size);
+       default:
+               break;
+       }
+       return -EINVAL;
+}
+
+static struct nvkm_ofuncs
+nvkm_control_ofuncs = {
+       .ctor = _nvkm_object_ctor,
+       .dtor = nvkm_object_destroy,
+       .init = nvkm_object_init,
+       .fini = nvkm_object_fini,
+       .mthd = nvkm_control_mthd,
+};
+
+struct nvkm_oclass
+nvkm_control_oclass[] = {
+       { .handle = NVIF_IOCTL_NEW_V0_CONTROL,
+         .ofuncs = &nvkm_control_ofuncs
+       },
+       {}
+};
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/device/gf100.c b/drivers/gpu/drm/nouveau/nvkm/engine/device/gf100.c
new file mode 100644 (file)
index 0000000..82b38d7
--- /dev/null
@@ -0,0 +1,358 @@
+/*
+ * Copyright 2012 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 "priv.h"
+
+#include <subdev/bios.h>
+#include <subdev/bus.h>
+#include <subdev/gpio.h>
+#include <subdev/i2c.h>
+#include <subdev/fuse.h>
+#include <subdev/clk.h>
+#include <subdev/therm.h>
+#include <subdev/mxm.h>
+#include <subdev/devinit.h>
+#include <subdev/mc.h>
+#include <subdev/timer.h>
+#include <subdev/fb.h>
+#include <subdev/ltc.h>
+#include <subdev/ibus.h>
+#include <subdev/instmem.h>
+#include <subdev/mmu.h>
+#include <subdev/bar.h>
+#include <subdev/pmu.h>
+#include <subdev/volt.h>
+
+#include <engine/dmaobj.h>
+#include <engine/fifo.h>
+#include <engine/sw.h>
+#include <engine/gr.h>
+#include <engine/mspdec.h>
+#include <engine/bsp.h>
+#include <engine/msvld.h>
+#include <engine/msppp.h>
+#include <engine/ce.h>
+#include <engine/disp.h>
+#include <engine/pm.h>
+
+int
+gf100_identify(struct nvkm_device *device)
+{
+       switch (device->chipset) {
+       case 0xc0:
+               device->cname = "GF100";
+               device->oclass[NVDEV_SUBDEV_VBIOS  ] = &nvkm_bios_oclass;
+               device->oclass[NVDEV_SUBDEV_GPIO   ] =  g94_gpio_oclass;
+               device->oclass[NVDEV_SUBDEV_I2C    ] =  g94_i2c_oclass;
+               device->oclass[NVDEV_SUBDEV_FUSE   ] = &gf100_fuse_oclass;
+               device->oclass[NVDEV_SUBDEV_CLK    ] = &gf100_clk_oclass;
+               device->oclass[NVDEV_SUBDEV_THERM  ] = &gt215_therm_oclass;
+               device->oclass[NVDEV_SUBDEV_MXM    ] = &nv50_mxm_oclass;
+               device->oclass[NVDEV_SUBDEV_DEVINIT] =  gf100_devinit_oclass;
+               device->oclass[NVDEV_SUBDEV_MC     ] =  gf100_mc_oclass;
+               device->oclass[NVDEV_SUBDEV_BUS    ] =  gf100_bus_oclass;
+               device->oclass[NVDEV_SUBDEV_TIMER  ] = &nv04_timer_oclass;
+               device->oclass[NVDEV_SUBDEV_FB     ] =  gf100_fb_oclass;
+               device->oclass[NVDEV_SUBDEV_LTC    ] =  gf100_ltc_oclass;
+               device->oclass[NVDEV_SUBDEV_IBUS   ] = &gf100_ibus_oclass;
+               device->oclass[NVDEV_SUBDEV_INSTMEM] =  nv50_instmem_oclass;
+               device->oclass[NVDEV_SUBDEV_MMU    ] = &gf100_mmu_oclass;
+               device->oclass[NVDEV_SUBDEV_BAR    ] = &gf100_bar_oclass;
+               device->oclass[NVDEV_SUBDEV_PMU    ] =  gf100_pmu_oclass;
+               device->oclass[NVDEV_SUBDEV_VOLT   ] = &nv40_volt_oclass;
+               device->oclass[NVDEV_ENGINE_DMAOBJ ] =  gf100_dmaeng_oclass;
+               device->oclass[NVDEV_ENGINE_FIFO   ] =  gf100_fifo_oclass;
+               device->oclass[NVDEV_ENGINE_SW     ] =  gf100_sw_oclass;
+               device->oclass[NVDEV_ENGINE_GR     ] =  gf100_gr_oclass;
+               device->oclass[NVDEV_ENGINE_MSPDEC ] = &gf100_mspdec_oclass;
+               device->oclass[NVDEV_ENGINE_MSVLD  ] = &gf100_msvld_oclass;
+               device->oclass[NVDEV_ENGINE_MSPPP  ] = &gf100_msppp_oclass;
+               device->oclass[NVDEV_ENGINE_CE0    ] = &gf100_ce0_oclass;
+               device->oclass[NVDEV_ENGINE_CE1    ] = &gf100_ce1_oclass;
+               device->oclass[NVDEV_ENGINE_DISP   ] =  gt215_disp_oclass;
+               device->oclass[NVDEV_ENGINE_PM     ] = &gf100_pm_oclass;
+               break;
+       case 0xc4:
+               device->cname = "GF104";
+               device->oclass[NVDEV_SUBDEV_VBIOS  ] = &nvkm_bios_oclass;
+               device->oclass[NVDEV_SUBDEV_GPIO   ] =  g94_gpio_oclass;
+               device->oclass[NVDEV_SUBDEV_I2C    ] =  g94_i2c_oclass;
+               device->oclass[NVDEV_SUBDEV_FUSE   ] = &gf100_fuse_oclass;
+               device->oclass[NVDEV_SUBDEV_CLK    ] = &gf100_clk_oclass;
+               device->oclass[NVDEV_SUBDEV_THERM  ] = &gt215_therm_oclass;
+               device->oclass[NVDEV_SUBDEV_MXM    ] = &nv50_mxm_oclass;
+               device->oclass[NVDEV_SUBDEV_DEVINIT] =  gf100_devinit_oclass;
+               device->oclass[NVDEV_SUBDEV_MC     ] =  gf100_mc_oclass;
+               device->oclass[NVDEV_SUBDEV_BUS    ] =  gf100_bus_oclass;
+               device->oclass[NVDEV_SUBDEV_TIMER  ] = &nv04_timer_oclass;
+               device->oclass[NVDEV_SUBDEV_FB     ] =  gf100_fb_oclass;
+               device->oclass[NVDEV_SUBDEV_LTC    ] =  gf100_ltc_oclass;
+               device->oclass[NVDEV_SUBDEV_IBUS   ] = &gf100_ibus_oclass;
+               device->oclass[NVDEV_SUBDEV_INSTMEM] =  nv50_instmem_oclass;
+               device->oclass[NVDEV_SUBDEV_MMU    ] = &gf100_mmu_oclass;
+               device->oclass[NVDEV_SUBDEV_BAR    ] = &gf100_bar_oclass;
+               device->oclass[NVDEV_SUBDEV_PMU    ] =  gf100_pmu_oclass;
+               device->oclass[NVDEV_SUBDEV_VOLT   ] = &nv40_volt_oclass;
+               device->oclass[NVDEV_ENGINE_DMAOBJ ] =  gf100_dmaeng_oclass;
+               device->oclass[NVDEV_ENGINE_FIFO   ] =  gf100_fifo_oclass;
+               device->oclass[NVDEV_ENGINE_SW     ] =  gf100_sw_oclass;
+               device->oclass[NVDEV_ENGINE_GR     ] =  gf104_gr_oclass;
+               device->oclass[NVDEV_ENGINE_MSPDEC ] = &gf100_mspdec_oclass;
+               device->oclass[NVDEV_ENGINE_MSVLD  ] = &gf100_msvld_oclass;
+               device->oclass[NVDEV_ENGINE_MSPPP  ] = &gf100_msppp_oclass;
+               device->oclass[NVDEV_ENGINE_CE0    ] = &gf100_ce0_oclass;
+               device->oclass[NVDEV_ENGINE_CE1    ] = &gf100_ce1_oclass;
+               device->oclass[NVDEV_ENGINE_DISP   ] =  gt215_disp_oclass;
+               device->oclass[NVDEV_ENGINE_PM     ] = &gf100_pm_oclass;
+               break;
+       case 0xc3:
+               device->cname = "GF106";
+               device->oclass[NVDEV_SUBDEV_VBIOS  ] = &nvkm_bios_oclass;
+               device->oclass[NVDEV_SUBDEV_GPIO   ] =  g94_gpio_oclass;
+               device->oclass[NVDEV_SUBDEV_I2C    ] =  g94_i2c_oclass;
+               device->oclass[NVDEV_SUBDEV_FUSE   ] = &gf100_fuse_oclass;
+               device->oclass[NVDEV_SUBDEV_CLK    ] = &gf100_clk_oclass;
+               device->oclass[NVDEV_SUBDEV_THERM  ] = &gt215_therm_oclass;
+               device->oclass[NVDEV_SUBDEV_MXM    ] = &nv50_mxm_oclass;
+               device->oclass[NVDEV_SUBDEV_DEVINIT] =  gf100_devinit_oclass;
+               device->oclass[NVDEV_SUBDEV_MC     ] =  gf106_mc_oclass;
+               device->oclass[NVDEV_SUBDEV_BUS    ] =  gf100_bus_oclass;
+               device->oclass[NVDEV_SUBDEV_TIMER  ] = &nv04_timer_oclass;
+               device->oclass[NVDEV_SUBDEV_FB     ] =  gf100_fb_oclass;
+               device->oclass[NVDEV_SUBDEV_LTC    ] =  gf100_ltc_oclass;
+               device->oclass[NVDEV_SUBDEV_IBUS   ] = &gf100_ibus_oclass;
+               device->oclass[NVDEV_SUBDEV_INSTMEM] =  nv50_instmem_oclass;
+               device->oclass[NVDEV_SUBDEV_MMU    ] = &gf100_mmu_oclass;
+               device->oclass[NVDEV_SUBDEV_BAR    ] = &gf100_bar_oclass;
+               device->oclass[NVDEV_SUBDEV_PMU    ] =  gf100_pmu_oclass;
+               device->oclass[NVDEV_SUBDEV_VOLT   ] = &nv40_volt_oclass;
+               device->oclass[NVDEV_ENGINE_DMAOBJ ] =  gf100_dmaeng_oclass;
+               device->oclass[NVDEV_ENGINE_FIFO   ] =  gf100_fifo_oclass;
+               device->oclass[NVDEV_ENGINE_SW     ] =  gf100_sw_oclass;
+               device->oclass[NVDEV_ENGINE_GR     ] =  gf104_gr_oclass;
+               device->oclass[NVDEV_ENGINE_MSPDEC ] = &gf100_mspdec_oclass;
+               device->oclass[NVDEV_ENGINE_MSVLD  ] = &gf100_msvld_oclass;
+               device->oclass[NVDEV_ENGINE_MSPPP  ] = &gf100_msppp_oclass;
+               device->oclass[NVDEV_ENGINE_CE0    ] = &gf100_ce0_oclass;
+               device->oclass[NVDEV_ENGINE_DISP   ] =  gt215_disp_oclass;
+               device->oclass[NVDEV_ENGINE_PM     ] = &gf100_pm_oclass;
+               break;
+       case 0xce:
+               device->cname = "GF114";
+               device->oclass[NVDEV_SUBDEV_VBIOS  ] = &nvkm_bios_oclass;
+               device->oclass[NVDEV_SUBDEV_GPIO   ] =  g94_gpio_oclass;
+               device->oclass[NVDEV_SUBDEV_I2C    ] =  g94_i2c_oclass;
+               device->oclass[NVDEV_SUBDEV_FUSE   ] = &gf100_fuse_oclass;
+               device->oclass[NVDEV_SUBDEV_CLK    ] = &gf100_clk_oclass;
+               device->oclass[NVDEV_SUBDEV_THERM  ] = &gt215_therm_oclass;
+               device->oclass[NVDEV_SUBDEV_MXM    ] = &nv50_mxm_oclass;
+               device->oclass[NVDEV_SUBDEV_DEVINIT] =  gf100_devinit_oclass;
+               device->oclass[NVDEV_SUBDEV_MC     ] =  gf100_mc_oclass;
+               device->oclass[NVDEV_SUBDEV_BUS    ] =  gf100_bus_oclass;
+               device->oclass[NVDEV_SUBDEV_TIMER  ] = &nv04_timer_oclass;
+               device->oclass[NVDEV_SUBDEV_FB     ] =  gf100_fb_oclass;
+               device->oclass[NVDEV_SUBDEV_LTC    ] =  gf100_ltc_oclass;
+               device->oclass[NVDEV_SUBDEV_IBUS   ] = &gf100_ibus_oclass;
+               device->oclass[NVDEV_SUBDEV_INSTMEM] =  nv50_instmem_oclass;
+               device->oclass[NVDEV_SUBDEV_MMU    ] = &gf100_mmu_oclass;
+               device->oclass[NVDEV_SUBDEV_BAR    ] = &gf100_bar_oclass;
+               device->oclass[NVDEV_SUBDEV_PMU    ] =  gf100_pmu_oclass;
+               device->oclass[NVDEV_SUBDEV_VOLT   ] = &nv40_volt_oclass;
+               device->oclass[NVDEV_ENGINE_DMAOBJ ] =  gf100_dmaeng_oclass;
+               device->oclass[NVDEV_ENGINE_FIFO   ] =  gf100_fifo_oclass;
+               device->oclass[NVDEV_ENGINE_SW     ] =  gf100_sw_oclass;
+               device->oclass[NVDEV_ENGINE_GR     ] =  gf104_gr_oclass;
+               device->oclass[NVDEV_ENGINE_MSPDEC ] = &gf100_mspdec_oclass;
+               device->oclass[NVDEV_ENGINE_MSVLD  ] = &gf100_msvld_oclass;
+               device->oclass[NVDEV_ENGINE_MSPPP  ] = &gf100_msppp_oclass;
+               device->oclass[NVDEV_ENGINE_CE0    ] = &gf100_ce0_oclass;
+               device->oclass[NVDEV_ENGINE_CE1    ] = &gf100_ce1_oclass;
+               device->oclass[NVDEV_ENGINE_DISP   ] =  gt215_disp_oclass;
+               device->oclass[NVDEV_ENGINE_PM     ] = &gf100_pm_oclass;
+               break;
+       case 0xcf:
+               device->cname = "GF116";
+               device->oclass[NVDEV_SUBDEV_VBIOS  ] = &nvkm_bios_oclass;
+               device->oclass[NVDEV_SUBDEV_GPIO   ] =  g94_gpio_oclass;
+               device->oclass[NVDEV_SUBDEV_I2C    ] =  g94_i2c_oclass;
+               device->oclass[NVDEV_SUBDEV_FUSE   ] = &gf100_fuse_oclass;
+               device->oclass[NVDEV_SUBDEV_CLK    ] = &gf100_clk_oclass;
+               device->oclass[NVDEV_SUBDEV_THERM  ] = &gt215_therm_oclass;
+               device->oclass[NVDEV_SUBDEV_MXM    ] = &nv50_mxm_oclass;
+               device->oclass[NVDEV_SUBDEV_DEVINIT] =  gf100_devinit_oclass;
+               device->oclass[NVDEV_SUBDEV_MC     ] =  gf106_mc_oclass;
+               device->oclass[NVDEV_SUBDEV_BUS    ] =  gf100_bus_oclass;
+               device->oclass[NVDEV_SUBDEV_TIMER  ] = &nv04_timer_oclass;
+               device->oclass[NVDEV_SUBDEV_FB     ] =  gf100_fb_oclass;
+               device->oclass[NVDEV_SUBDEV_LTC    ] =  gf100_ltc_oclass;
+               device->oclass[NVDEV_SUBDEV_IBUS   ] = &gf100_ibus_oclass;
+               device->oclass[NVDEV_SUBDEV_INSTMEM] =  nv50_instmem_oclass;
+               device->oclass[NVDEV_SUBDEV_MMU    ] = &gf100_mmu_oclass;
+               device->oclass[NVDEV_SUBDEV_BAR    ] = &gf100_bar_oclass;
+               device->oclass[NVDEV_SUBDEV_PMU    ] =  gf100_pmu_oclass;
+               device->oclass[NVDEV_SUBDEV_VOLT   ] = &nv40_volt_oclass;
+               device->oclass[NVDEV_ENGINE_DMAOBJ ] =  gf100_dmaeng_oclass;
+               device->oclass[NVDEV_ENGINE_FIFO   ] =  gf100_fifo_oclass;
+               device->oclass[NVDEV_ENGINE_SW     ] =  gf100_sw_oclass;
+               device->oclass[NVDEV_ENGINE_GR     ] =  gf104_gr_oclass;
+               device->oclass[NVDEV_ENGINE_MSPDEC ] = &gf100_mspdec_oclass;
+               device->oclass[NVDEV_ENGINE_MSVLD  ] = &gf100_msvld_oclass;
+               device->oclass[NVDEV_ENGINE_MSPPP  ] = &gf100_msppp_oclass;
+               device->oclass[NVDEV_ENGINE_CE0    ] = &gf100_ce0_oclass;
+               device->oclass[NVDEV_ENGINE_DISP   ] =  gt215_disp_oclass;
+               device->oclass[NVDEV_ENGINE_PM     ] = &gf100_pm_oclass;
+               break;
+       case 0xc1:
+               device->cname = "GF108";
+               device->oclass[NVDEV_SUBDEV_VBIOS  ] = &nvkm_bios_oclass;
+               device->oclass[NVDEV_SUBDEV_GPIO   ] =  g94_gpio_oclass;
+               device->oclass[NVDEV_SUBDEV_I2C    ] =  g94_i2c_oclass;
+               device->oclass[NVDEV_SUBDEV_FUSE   ] = &gf100_fuse_oclass;
+               device->oclass[NVDEV_SUBDEV_CLK    ] = &gf100_clk_oclass;
+               device->oclass[NVDEV_SUBDEV_THERM  ] = &gt215_therm_oclass;
+               device->oclass[NVDEV_SUBDEV_MXM    ] = &nv50_mxm_oclass;
+               device->oclass[NVDEV_SUBDEV_DEVINIT] =  gf100_devinit_oclass;
+               device->oclass[NVDEV_SUBDEV_MC     ] =  gf106_mc_oclass;
+               device->oclass[NVDEV_SUBDEV_BUS    ] =  gf100_bus_oclass;
+               device->oclass[NVDEV_SUBDEV_TIMER  ] = &nv04_timer_oclass;
+               device->oclass[NVDEV_SUBDEV_FB     ] =  gf100_fb_oclass;
+               device->oclass[NVDEV_SUBDEV_LTC    ] =  gf100_ltc_oclass;
+               device->oclass[NVDEV_SUBDEV_IBUS   ] = &gf100_ibus_oclass;
+               device->oclass[NVDEV_SUBDEV_INSTMEM] =  nv50_instmem_oclass;
+               device->oclass[NVDEV_SUBDEV_MMU    ] = &gf100_mmu_oclass;
+               device->oclass[NVDEV_SUBDEV_BAR    ] = &gf100_bar_oclass;
+               device->oclass[NVDEV_SUBDEV_PMU    ] =  gf100_pmu_oclass;
+               device->oclass[NVDEV_SUBDEV_VOLT   ] = &nv40_volt_oclass;
+               device->oclass[NVDEV_ENGINE_DMAOBJ ] =  gf100_dmaeng_oclass;
+               device->oclass[NVDEV_ENGINE_FIFO   ] =  gf100_fifo_oclass;
+               device->oclass[NVDEV_ENGINE_SW     ] =  gf100_sw_oclass;
+               device->oclass[NVDEV_ENGINE_GR     ] =  gf108_gr_oclass;
+               device->oclass[NVDEV_ENGINE_MSPDEC ] = &gf100_mspdec_oclass;
+               device->oclass[NVDEV_ENGINE_MSVLD  ] = &gf100_msvld_oclass;
+               device->oclass[NVDEV_ENGINE_MSPPP  ] = &gf100_msppp_oclass;
+               device->oclass[NVDEV_ENGINE_CE0    ] = &gf100_ce0_oclass;
+               device->oclass[NVDEV_ENGINE_DISP   ] =  gt215_disp_oclass;
+               device->oclass[NVDEV_ENGINE_PM     ] = &gf100_pm_oclass;
+               break;
+       case 0xc8:
+               device->cname = "GF110";
+               device->oclass[NVDEV_SUBDEV_VBIOS  ] = &nvkm_bios_oclass;
+               device->oclass[NVDEV_SUBDEV_GPIO   ] =  g94_gpio_oclass;
+               device->oclass[NVDEV_SUBDEV_I2C    ] =  g94_i2c_oclass;
+               device->oclass[NVDEV_SUBDEV_FUSE   ] = &gf100_fuse_oclass;
+               device->oclass[NVDEV_SUBDEV_CLK    ] = &gf100_clk_oclass;
+               device->oclass[NVDEV_SUBDEV_THERM  ] = &gt215_therm_oclass;
+               device->oclass[NVDEV_SUBDEV_MXM    ] = &nv50_mxm_oclass;
+               device->oclass[NVDEV_SUBDEV_DEVINIT] =  gf100_devinit_oclass;
+               device->oclass[NVDEV_SUBDEV_MC     ] =  gf100_mc_oclass;
+               device->oclass[NVDEV_SUBDEV_BUS    ] =  gf100_bus_oclass;
+               device->oclass[NVDEV_SUBDEV_TIMER  ] = &nv04_timer_oclass;
+               device->oclass[NVDEV_SUBDEV_FB     ] =  gf100_fb_oclass;
+               device->oclass[NVDEV_SUBDEV_LTC    ] =  gf100_ltc_oclass;
+               device->oclass[NVDEV_SUBDEV_IBUS   ] = &gf100_ibus_oclass;
+               device->oclass[NVDEV_SUBDEV_INSTMEM] =  nv50_instmem_oclass;
+               device->oclass[NVDEV_SUBDEV_MMU    ] = &gf100_mmu_oclass;
+               device->oclass[NVDEV_SUBDEV_BAR    ] = &gf100_bar_oclass;
+               device->oclass[NVDEV_SUBDEV_PMU    ] =  gf100_pmu_oclass;
+               device->oclass[NVDEV_SUBDEV_VOLT   ] = &nv40_volt_oclass;
+               device->oclass[NVDEV_ENGINE_DMAOBJ ] =  gf100_dmaeng_oclass;
+               device->oclass[NVDEV_ENGINE_FIFO   ] =  gf100_fifo_oclass;
+               device->oclass[NVDEV_ENGINE_SW     ] =  gf100_sw_oclass;
+               device->oclass[NVDEV_ENGINE_GR     ] =  gf110_gr_oclass;
+               device->oclass[NVDEV_ENGINE_MSPDEC ] = &gf100_mspdec_oclass;
+               device->oclass[NVDEV_ENGINE_MSVLD  ] = &gf100_msvld_oclass;
+               device->oclass[NVDEV_ENGINE_MSPPP  ] = &gf100_msppp_oclass;
+               device->oclass[NVDEV_ENGINE_CE0    ] = &gf100_ce0_oclass;
+               device->oclass[NVDEV_ENGINE_CE1    ] = &gf100_ce1_oclass;
+               device->oclass[NVDEV_ENGINE_DISP   ] =  gt215_disp_oclass;
+               device->oclass[NVDEV_ENGINE_PM     ] = &gf100_pm_oclass;
+               break;
+       case 0xd9:
+               device->cname = "GF119";
+               device->oclass[NVDEV_SUBDEV_VBIOS  ] = &nvkm_bios_oclass;
+               device->oclass[NVDEV_SUBDEV_GPIO   ] =  gf110_gpio_oclass;
+               device->oclass[NVDEV_SUBDEV_I2C    ] =  gf110_i2c_oclass;
+               device->oclass[NVDEV_SUBDEV_FUSE   ] = &gf100_fuse_oclass;
+               device->oclass[NVDEV_SUBDEV_CLK    ] = &gf100_clk_oclass;
+               device->oclass[NVDEV_SUBDEV_THERM  ] = &gf110_therm_oclass;
+               device->oclass[NVDEV_SUBDEV_MXM    ] = &nv50_mxm_oclass;
+               device->oclass[NVDEV_SUBDEV_DEVINIT] =  gf100_devinit_oclass;
+               device->oclass[NVDEV_SUBDEV_MC     ] =  gf106_mc_oclass;
+               device->oclass[NVDEV_SUBDEV_BUS    ] =  gf100_bus_oclass;
+               device->oclass[NVDEV_SUBDEV_TIMER  ] = &nv04_timer_oclass;
+               device->oclass[NVDEV_SUBDEV_FB     ] =  gf100_fb_oclass;
+               device->oclass[NVDEV_SUBDEV_LTC    ] =  gf100_ltc_oclass;
+               device->oclass[NVDEV_SUBDEV_IBUS   ] = &gf100_ibus_oclass;
+               device->oclass[NVDEV_SUBDEV_INSTMEM] =  nv50_instmem_oclass;
+               device->oclass[NVDEV_SUBDEV_MMU    ] = &gf100_mmu_oclass;
+               device->oclass[NVDEV_SUBDEV_BAR    ] = &gf100_bar_oclass;
+               device->oclass[NVDEV_SUBDEV_PMU    ] =  gf110_pmu_oclass;
+               device->oclass[NVDEV_SUBDEV_VOLT   ] = &nv40_volt_oclass;
+               device->oclass[NVDEV_ENGINE_DMAOBJ ] =  gf110_dmaeng_oclass;
+               device->oclass[NVDEV_ENGINE_FIFO   ] =  gf100_fifo_oclass;
+               device->oclass[NVDEV_ENGINE_SW     ] =  gf100_sw_oclass;
+               device->oclass[NVDEV_ENGINE_GR     ] =  gf119_gr_oclass;
+               device->oclass[NVDEV_ENGINE_MSPDEC ] = &gf100_mspdec_oclass;
+               device->oclass[NVDEV_ENGINE_MSVLD  ] = &gf100_msvld_oclass;
+               device->oclass[NVDEV_ENGINE_MSPPP  ] = &gf100_msppp_oclass;
+               device->oclass[NVDEV_ENGINE_CE0    ] = &gf100_ce0_oclass;
+               device->oclass[NVDEV_ENGINE_DISP   ] =  gf110_disp_oclass;
+               device->oclass[NVDEV_ENGINE_PM     ] = &gf100_pm_oclass;
+               break;
+       case 0xd7:
+               device->cname = "GF117";
+               device->oclass[NVDEV_SUBDEV_VBIOS  ] = &nvkm_bios_oclass;
+               device->oclass[NVDEV_SUBDEV_GPIO   ] =  gf110_gpio_oclass;
+               device->oclass[NVDEV_SUBDEV_I2C    ] =  gf117_i2c_oclass;
+               device->oclass[NVDEV_SUBDEV_FUSE   ] = &gf100_fuse_oclass;
+               device->oclass[NVDEV_SUBDEV_CLK    ] = &gf100_clk_oclass;
+               device->oclass[NVDEV_SUBDEV_THERM  ] = &gf110_therm_oclass;
+               device->oclass[NVDEV_SUBDEV_MXM    ] = &nv50_mxm_oclass;
+               device->oclass[NVDEV_SUBDEV_DEVINIT] =  gf100_devinit_oclass;
+               device->oclass[NVDEV_SUBDEV_MC     ] =  gf106_mc_oclass;
+               device->oclass[NVDEV_SUBDEV_BUS    ] =  gf100_bus_oclass;
+               device->oclass[NVDEV_SUBDEV_TIMER  ] = &nv04_timer_oclass;
+               device->oclass[NVDEV_SUBDEV_FB     ] =  gf100_fb_oclass;
+               device->oclass[NVDEV_SUBDEV_LTC    ] =  gf100_ltc_oclass;
+               device->oclass[NVDEV_SUBDEV_IBUS   ] = &gf100_ibus_oclass;
+               device->oclass[NVDEV_SUBDEV_INSTMEM] =  nv50_instmem_oclass;
+               device->oclass[NVDEV_SUBDEV_MMU    ] = &gf100_mmu_oclass;
+               device->oclass[NVDEV_SUBDEV_BAR    ] = &gf100_bar_oclass;
+               device->oclass[NVDEV_ENGINE_DMAOBJ ] =  gf110_dmaeng_oclass;
+               device->oclass[NVDEV_ENGINE_FIFO   ] =  gf100_fifo_oclass;
+               device->oclass[NVDEV_ENGINE_SW     ] =  gf100_sw_oclass;
+               device->oclass[NVDEV_ENGINE_GR     ] =  gf117_gr_oclass;
+               device->oclass[NVDEV_ENGINE_MSPDEC ] = &gf100_mspdec_oclass;
+               device->oclass[NVDEV_ENGINE_MSVLD  ] = &gf100_msvld_oclass;
+               device->oclass[NVDEV_ENGINE_MSPPP  ] = &gf100_msppp_oclass;
+               device->oclass[NVDEV_ENGINE_CE0    ] = &gf100_ce0_oclass;
+               device->oclass[NVDEV_ENGINE_DISP   ] =  gf110_disp_oclass;
+               device->oclass[NVDEV_ENGINE_PM     ] = &gf100_pm_oclass;
+               break;
+       default:
+               nv_fatal(device, "unknown Fermi chipset\n");
+               return -EINVAL;
+       }
+
+       return 0;
+}
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/device/gk104.c b/drivers/gpu/drm/nouveau/nvkm/engine/device/gk104.c
new file mode 100644 (file)
index 0000000..bf58934
--- /dev/null
@@ -0,0 +1,326 @@
+/*
+ * Copyright 2012 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 "priv.h"
+
+#include <subdev/bios.h>
+#include <subdev/bus.h>
+#include <subdev/gpio.h>
+#include <subdev/i2c.h>
+#include <subdev/fuse.h>
+#include <subdev/clk.h>
+#include <subdev/therm.h>
+#include <subdev/mxm.h>
+#include <subdev/devinit.h>
+#include <subdev/mc.h>
+#include <subdev/timer.h>
+#include <subdev/fb.h>
+#include <subdev/ltc.h>
+#include <subdev/ibus.h>
+#include <subdev/instmem.h>
+#include <subdev/mmu.h>
+#include <subdev/bar.h>
+#include <subdev/pmu.h>
+#include <subdev/volt.h>
+
+#include <engine/dmaobj.h>
+#include <engine/fifo.h>
+#include <engine/sw.h>
+#include <engine/gr.h>
+#include <engine/disp.h>
+#include <engine/ce.h>
+#include <engine/bsp.h>
+#include <engine/msvld.h>
+#include <engine/mspdec.h>
+#include <engine/msppp.h>
+#include <engine/pm.h>
+
+int
+gk104_identify(struct nvkm_device *device)
+{
+       switch (device->chipset) {
+       case 0xe4:
+               device->cname = "GK104";
+               device->oclass[NVDEV_SUBDEV_VBIOS  ] = &nvkm_bios_oclass;
+               device->oclass[NVDEV_SUBDEV_GPIO   ] =  gk104_gpio_oclass;
+               device->oclass[NVDEV_SUBDEV_I2C    ] =  gk104_i2c_oclass;
+               device->oclass[NVDEV_SUBDEV_FUSE   ] = &gf100_fuse_oclass;
+               device->oclass[NVDEV_SUBDEV_CLK    ] = &gk104_clk_oclass;
+               device->oclass[NVDEV_SUBDEV_THERM  ] = &gf110_therm_oclass;
+               device->oclass[NVDEV_SUBDEV_MXM    ] = &nv50_mxm_oclass;
+               device->oclass[NVDEV_SUBDEV_DEVINIT] =  gf100_devinit_oclass;
+               device->oclass[NVDEV_SUBDEV_MC     ] =  gf106_mc_oclass;
+               device->oclass[NVDEV_SUBDEV_BUS    ] =  gf100_bus_oclass;
+               device->oclass[NVDEV_SUBDEV_TIMER  ] = &nv04_timer_oclass;
+               device->oclass[NVDEV_SUBDEV_FB     ] =  gk104_fb_oclass;
+               device->oclass[NVDEV_SUBDEV_LTC    ] =  gk104_ltc_oclass;
+               device->oclass[NVDEV_SUBDEV_IBUS   ] = &gk104_ibus_oclass;
+               device->oclass[NVDEV_SUBDEV_INSTMEM] =  nv50_instmem_oclass;
+               device->oclass[NVDEV_SUBDEV_MMU    ] = &gf100_mmu_oclass;
+               device->oclass[NVDEV_SUBDEV_BAR    ] = &gf100_bar_oclass;
+               device->oclass[NVDEV_SUBDEV_PMU    ] =  gk104_pmu_oclass;
+               device->oclass[NVDEV_SUBDEV_VOLT   ] = &nv40_volt_oclass;
+               device->oclass[NVDEV_ENGINE_DMAOBJ ] =  gf110_dmaeng_oclass;
+               device->oclass[NVDEV_ENGINE_FIFO   ] =  gk104_fifo_oclass;
+               device->oclass[NVDEV_ENGINE_SW     ] =  gf100_sw_oclass;
+               device->oclass[NVDEV_ENGINE_GR     ] =  gk104_gr_oclass;
+               device->oclass[NVDEV_ENGINE_DISP   ] =  gk104_disp_oclass;
+               device->oclass[NVDEV_ENGINE_CE0    ] = &gk104_ce0_oclass;
+               device->oclass[NVDEV_ENGINE_CE1    ] = &gk104_ce1_oclass;
+               device->oclass[NVDEV_ENGINE_CE2    ] = &gk104_ce2_oclass;
+               device->oclass[NVDEV_ENGINE_MSVLD  ] = &gk104_msvld_oclass;
+               device->oclass[NVDEV_ENGINE_MSPDEC ] = &gk104_mspdec_oclass;
+               device->oclass[NVDEV_ENGINE_MSPPP  ] = &gf100_msppp_oclass;
+               device->oclass[NVDEV_ENGINE_PM     ] = &gk104_pm_oclass;
+               break;
+       case 0xe7:
+               device->cname = "GK107";
+               device->oclass[NVDEV_SUBDEV_VBIOS  ] = &nvkm_bios_oclass;
+               device->oclass[NVDEV_SUBDEV_GPIO   ] =  gk104_gpio_oclass;
+               device->oclass[NVDEV_SUBDEV_I2C    ] =  gk104_i2c_oclass;
+               device->oclass[NVDEV_SUBDEV_FUSE   ] = &gf100_fuse_oclass;
+               device->oclass[NVDEV_SUBDEV_CLK    ] = &gk104_clk_oclass;
+               device->oclass[NVDEV_SUBDEV_THERM  ] = &gf110_therm_oclass;
+               device->oclass[NVDEV_SUBDEV_MXM    ] = &nv50_mxm_oclass;
+               device->oclass[NVDEV_SUBDEV_DEVINIT] =  gf100_devinit_oclass;
+               device->oclass[NVDEV_SUBDEV_MC     ] =  gf106_mc_oclass;
+               device->oclass[NVDEV_SUBDEV_BUS    ] =  gf100_bus_oclass;
+               device->oclass[NVDEV_SUBDEV_TIMER  ] = &nv04_timer_oclass;
+               device->oclass[NVDEV_SUBDEV_FB     ] =  gk104_fb_oclass;
+               device->oclass[NVDEV_SUBDEV_LTC    ] =  gk104_ltc_oclass;
+               device->oclass[NVDEV_SUBDEV_IBUS   ] = &gk104_ibus_oclass;
+               device->oclass[NVDEV_SUBDEV_INSTMEM] =  nv50_instmem_oclass;
+               device->oclass[NVDEV_SUBDEV_MMU    ] = &gf100_mmu_oclass;
+               device->oclass[NVDEV_SUBDEV_BAR    ] = &gf100_bar_oclass;
+               device->oclass[NVDEV_SUBDEV_PMU    ] =  gf110_pmu_oclass;
+               device->oclass[NVDEV_SUBDEV_VOLT   ] = &nv40_volt_oclass;
+               device->oclass[NVDEV_ENGINE_DMAOBJ ] =  gf110_dmaeng_oclass;
+               device->oclass[NVDEV_ENGINE_FIFO   ] =  gk104_fifo_oclass;
+               device->oclass[NVDEV_ENGINE_SW     ] =  gf100_sw_oclass;
+               device->oclass[NVDEV_ENGINE_GR     ] =  gk104_gr_oclass;
+               device->oclass[NVDEV_ENGINE_DISP   ] =  gk104_disp_oclass;
+               device->oclass[NVDEV_ENGINE_CE0    ] = &gk104_ce0_oclass;
+               device->oclass[NVDEV_ENGINE_CE1    ] = &gk104_ce1_oclass;
+               device->oclass[NVDEV_ENGINE_CE2    ] = &gk104_ce2_oclass;
+               device->oclass[NVDEV_ENGINE_MSVLD  ] = &gk104_msvld_oclass;
+               device->oclass[NVDEV_ENGINE_MSPDEC ] = &gk104_mspdec_oclass;
+               device->oclass[NVDEV_ENGINE_MSPPP  ] = &gf100_msppp_oclass;
+               device->oclass[NVDEV_ENGINE_PM     ] = &gk104_pm_oclass;
+               break;
+       case 0xe6:
+               device->cname = "GK106";
+               device->oclass[NVDEV_SUBDEV_VBIOS  ] = &nvkm_bios_oclass;
+               device->oclass[NVDEV_SUBDEV_GPIO   ] =  gk104_gpio_oclass;
+               device->oclass[NVDEV_SUBDEV_I2C    ] =  gk104_i2c_oclass;
+               device->oclass[NVDEV_SUBDEV_FUSE   ] = &gf100_fuse_oclass;
+               device->oclass[NVDEV_SUBDEV_CLK    ] = &gk104_clk_oclass;
+               device->oclass[NVDEV_SUBDEV_THERM  ] = &gf110_therm_oclass;
+               device->oclass[NVDEV_SUBDEV_MXM    ] = &nv50_mxm_oclass;
+               device->oclass[NVDEV_SUBDEV_DEVINIT] =  gf100_devinit_oclass;
+               device->oclass[NVDEV_SUBDEV_MC     ] =  gf106_mc_oclass;
+               device->oclass[NVDEV_SUBDEV_BUS    ] =  gf100_bus_oclass;
+               device->oclass[NVDEV_SUBDEV_TIMER  ] = &nv04_timer_oclass;
+               device->oclass[NVDEV_SUBDEV_FB     ] =  gk104_fb_oclass;
+               device->oclass[NVDEV_SUBDEV_LTC    ] =  gk104_ltc_oclass;
+               device->oclass[NVDEV_SUBDEV_IBUS   ] = &gk104_ibus_oclass;
+               device->oclass[NVDEV_SUBDEV_INSTMEM] =  nv50_instmem_oclass;
+               device->oclass[NVDEV_SUBDEV_MMU    ] = &gf100_mmu_oclass;
+               device->oclass[NVDEV_SUBDEV_BAR    ] = &gf100_bar_oclass;
+               device->oclass[NVDEV_SUBDEV_PMU    ] =  gk104_pmu_oclass;
+               device->oclass[NVDEV_SUBDEV_VOLT   ] = &nv40_volt_oclass;
+               device->oclass[NVDEV_ENGINE_DMAOBJ ] =  gf110_dmaeng_oclass;
+               device->oclass[NVDEV_ENGINE_FIFO   ] =  gk104_fifo_oclass;
+               device->oclass[NVDEV_ENGINE_SW     ] =  gf100_sw_oclass;
+               device->oclass[NVDEV_ENGINE_GR     ] =  gk104_gr_oclass;
+               device->oclass[NVDEV_ENGINE_DISP   ] =  gk104_disp_oclass;
+               device->oclass[NVDEV_ENGINE_CE0    ] = &gk104_ce0_oclass;
+               device->oclass[NVDEV_ENGINE_CE1    ] = &gk104_ce1_oclass;
+               device->oclass[NVDEV_ENGINE_CE2    ] = &gk104_ce2_oclass;
+               device->oclass[NVDEV_ENGINE_MSVLD  ] = &gk104_msvld_oclass;
+               device->oclass[NVDEV_ENGINE_MSPDEC ] = &gk104_mspdec_oclass;
+               device->oclass[NVDEV_ENGINE_MSPPP  ] = &gf100_msppp_oclass;
+               device->oclass[NVDEV_ENGINE_PM     ] = &gk104_pm_oclass;
+               break;
+       case 0xea:
+               device->cname = "GK20A";
+               device->oclass[NVDEV_SUBDEV_CLK    ] = &gk20a_clk_oclass;
+               device->oclass[NVDEV_SUBDEV_MC     ] =  gk20a_mc_oclass;
+               device->oclass[NVDEV_SUBDEV_BUS    ] =  gf100_bus_oclass;
+               device->oclass[NVDEV_SUBDEV_FUSE   ] = &gf100_fuse_oclass;
+               device->oclass[NVDEV_SUBDEV_TIMER  ] = &gk20a_timer_oclass;
+               device->oclass[NVDEV_SUBDEV_FB     ] =  gk20a_fb_oclass;
+               device->oclass[NVDEV_SUBDEV_LTC    ] =  gk104_ltc_oclass;
+               device->oclass[NVDEV_SUBDEV_IBUS   ] = &gk20a_ibus_oclass;
+               device->oclass[NVDEV_SUBDEV_INSTMEM] = nv50_instmem_oclass;
+               device->oclass[NVDEV_SUBDEV_MMU    ] = &gf100_mmu_oclass;
+               device->oclass[NVDEV_SUBDEV_BAR    ] = &gk20a_bar_oclass;
+               device->oclass[NVDEV_ENGINE_DMAOBJ ] =  gf110_dmaeng_oclass;
+               device->oclass[NVDEV_ENGINE_FIFO   ] =  gk20a_fifo_oclass;
+               device->oclass[NVDEV_ENGINE_SW     ] =  gf100_sw_oclass;
+               device->oclass[NVDEV_ENGINE_GR     ] =  gk20a_gr_oclass;
+               device->oclass[NVDEV_ENGINE_CE2    ] = &gk104_ce2_oclass;
+               device->oclass[NVDEV_ENGINE_PM     ] = &gk104_pm_oclass;
+               device->oclass[NVDEV_SUBDEV_VOLT   ] = &gk20a_volt_oclass;
+               device->oclass[NVDEV_SUBDEV_PMU    ] =  gk20a_pmu_oclass;
+               break;
+       case 0xf0:
+               device->cname = "GK110";
+               device->oclass[NVDEV_SUBDEV_VBIOS  ] = &nvkm_bios_oclass;
+               device->oclass[NVDEV_SUBDEV_GPIO   ] =  gk104_gpio_oclass;
+               device->oclass[NVDEV_SUBDEV_I2C    ] =  gk104_i2c_oclass;
+               device->oclass[NVDEV_SUBDEV_FUSE   ] = &gf100_fuse_oclass;
+               device->oclass[NVDEV_SUBDEV_CLK    ] = &gk104_clk_oclass;
+               device->oclass[NVDEV_SUBDEV_THERM  ] = &gf110_therm_oclass;
+               device->oclass[NVDEV_SUBDEV_MXM    ] = &nv50_mxm_oclass;
+               device->oclass[NVDEV_SUBDEV_DEVINIT] =  gf100_devinit_oclass;
+               device->oclass[NVDEV_SUBDEV_MC     ] =  gf106_mc_oclass;
+               device->oclass[NVDEV_SUBDEV_BUS    ] =  gf100_bus_oclass;
+               device->oclass[NVDEV_SUBDEV_TIMER  ] = &nv04_timer_oclass;
+               device->oclass[NVDEV_SUBDEV_FB     ] =  gk104_fb_oclass;
+               device->oclass[NVDEV_SUBDEV_LTC    ] =  gk104_ltc_oclass;
+               device->oclass[NVDEV_SUBDEV_IBUS   ] = &gk104_ibus_oclass;
+               device->oclass[NVDEV_SUBDEV_INSTMEM] =  nv50_instmem_oclass;
+               device->oclass[NVDEV_SUBDEV_MMU    ] = &gf100_mmu_oclass;
+               device->oclass[NVDEV_SUBDEV_BAR    ] = &gf100_bar_oclass;
+               device->oclass[NVDEV_SUBDEV_PMU    ] =  gf110_pmu_oclass;
+               device->oclass[NVDEV_SUBDEV_VOLT   ] = &nv40_volt_oclass;
+               device->oclass[NVDEV_ENGINE_DMAOBJ ] =  gf110_dmaeng_oclass;
+               device->oclass[NVDEV_ENGINE_FIFO   ] =  gk104_fifo_oclass;
+               device->oclass[NVDEV_ENGINE_SW     ] =  gf100_sw_oclass;
+               device->oclass[NVDEV_ENGINE_GR     ] =  gk110_gr_oclass;
+               device->oclass[NVDEV_ENGINE_DISP   ] =  gk110_disp_oclass;
+               device->oclass[NVDEV_ENGINE_CE0    ] = &gk104_ce0_oclass;
+               device->oclass[NVDEV_ENGINE_CE1    ] = &gk104_ce1_oclass;
+               device->oclass[NVDEV_ENGINE_CE2    ] = &gk104_ce2_oclass;
+               device->oclass[NVDEV_ENGINE_MSVLD  ] = &gk104_msvld_oclass;
+               device->oclass[NVDEV_ENGINE_MSPDEC ] = &gk104_mspdec_oclass;
+               device->oclass[NVDEV_ENGINE_MSPPP  ] = &gf100_msppp_oclass;
+               device->oclass[NVDEV_ENGINE_PM     ] = &gk110_pm_oclass;
+               break;
+       case 0xf1:
+               device->cname = "GK110B";
+               device->oclass[NVDEV_SUBDEV_VBIOS  ] = &nvkm_bios_oclass;
+               device->oclass[NVDEV_SUBDEV_GPIO   ] =  gk104_gpio_oclass;
+               device->oclass[NVDEV_SUBDEV_I2C    ] =  gf110_i2c_oclass;
+               device->oclass[NVDEV_SUBDEV_FUSE   ] = &gf100_fuse_oclass;
+               device->oclass[NVDEV_SUBDEV_CLK    ] = &gk104_clk_oclass;
+               device->oclass[NVDEV_SUBDEV_THERM  ] = &gf110_therm_oclass;
+               device->oclass[NVDEV_SUBDEV_MXM    ] = &nv50_mxm_oclass;
+               device->oclass[NVDEV_SUBDEV_DEVINIT] =  gf100_devinit_oclass;
+               device->oclass[NVDEV_SUBDEV_MC     ] =  gf106_mc_oclass;
+               device->oclass[NVDEV_SUBDEV_BUS    ] =  gf100_bus_oclass;
+               device->oclass[NVDEV_SUBDEV_TIMER  ] = &nv04_timer_oclass;
+               device->oclass[NVDEV_SUBDEV_FB     ] =  gk104_fb_oclass;
+               device->oclass[NVDEV_SUBDEV_LTC    ] =  gk104_ltc_oclass;
+               device->oclass[NVDEV_SUBDEV_IBUS   ] = &gk104_ibus_oclass;
+               device->oclass[NVDEV_SUBDEV_INSTMEM] =  nv50_instmem_oclass;
+               device->oclass[NVDEV_SUBDEV_MMU    ] = &gf100_mmu_oclass;
+               device->oclass[NVDEV_SUBDEV_BAR    ] = &gf100_bar_oclass;
+               device->oclass[NVDEV_SUBDEV_PMU    ] =  gf110_pmu_oclass;
+               device->oclass[NVDEV_SUBDEV_VOLT   ] = &nv40_volt_oclass;
+               device->oclass[NVDEV_ENGINE_DMAOBJ ] =  gf110_dmaeng_oclass;
+               device->oclass[NVDEV_ENGINE_FIFO   ] =  gk104_fifo_oclass;
+               device->oclass[NVDEV_ENGINE_SW     ] =  gf100_sw_oclass;
+               device->oclass[NVDEV_ENGINE_GR     ] =  gk110b_gr_oclass;
+               device->oclass[NVDEV_ENGINE_DISP   ] =  gk110_disp_oclass;
+               device->oclass[NVDEV_ENGINE_CE0    ] = &gk104_ce0_oclass;
+               device->oclass[NVDEV_ENGINE_CE1    ] = &gk104_ce1_oclass;
+               device->oclass[NVDEV_ENGINE_CE2    ] = &gk104_ce2_oclass;
+               device->oclass[NVDEV_ENGINE_MSVLD  ] = &gk104_msvld_oclass;
+               device->oclass[NVDEV_ENGINE_MSPDEC ] = &gk104_mspdec_oclass;
+               device->oclass[NVDEV_ENGINE_MSPPP  ] = &gf100_msppp_oclass;
+               device->oclass[NVDEV_ENGINE_PM     ] = &gk110_pm_oclass;
+               break;
+       case 0x106:
+               device->cname = "GK208B";
+               device->oclass[NVDEV_SUBDEV_VBIOS  ] = &nvkm_bios_oclass;
+               device->oclass[NVDEV_SUBDEV_GPIO   ] =  gk104_gpio_oclass;
+               device->oclass[NVDEV_SUBDEV_I2C    ] =  gk104_i2c_oclass;
+               device->oclass[NVDEV_SUBDEV_FUSE   ] = &gf100_fuse_oclass;
+               device->oclass[NVDEV_SUBDEV_CLK    ] = &gk104_clk_oclass;
+               device->oclass[NVDEV_SUBDEV_THERM  ] = &gf110_therm_oclass;
+               device->oclass[NVDEV_SUBDEV_MXM    ] = &nv50_mxm_oclass;
+               device->oclass[NVDEV_SUBDEV_DEVINIT] =  gf100_devinit_oclass;
+               device->oclass[NVDEV_SUBDEV_MC     ] =  gk20a_mc_oclass;
+               device->oclass[NVDEV_SUBDEV_BUS    ] =  gf100_bus_oclass;
+               device->oclass[NVDEV_SUBDEV_TIMER  ] = &nv04_timer_oclass;
+               device->oclass[NVDEV_SUBDEV_FB     ] =  gk104_fb_oclass;
+               device->oclass[NVDEV_SUBDEV_LTC    ] =  gk104_ltc_oclass;
+               device->oclass[NVDEV_SUBDEV_IBUS   ] = &gk104_ibus_oclass;
+               device->oclass[NVDEV_SUBDEV_INSTMEM] =  nv50_instmem_oclass;
+               device->oclass[NVDEV_SUBDEV_MMU    ] = &gf100_mmu_oclass;
+               device->oclass[NVDEV_SUBDEV_BAR    ] = &gf100_bar_oclass;
+               device->oclass[NVDEV_SUBDEV_PMU    ] =  gk208_pmu_oclass;
+               device->oclass[NVDEV_SUBDEV_VOLT   ] = &nv40_volt_oclass;
+               device->oclass[NVDEV_ENGINE_DMAOBJ ] =  gf110_dmaeng_oclass;
+               device->oclass[NVDEV_ENGINE_FIFO   ] =  gk208_fifo_oclass;
+               device->oclass[NVDEV_ENGINE_SW     ] =  gf100_sw_oclass;
+               device->oclass[NVDEV_ENGINE_GR     ] =  gk208_gr_oclass;
+               device->oclass[NVDEV_ENGINE_DISP   ] =  gk110_disp_oclass;
+               device->oclass[NVDEV_ENGINE_CE0    ] = &gk104_ce0_oclass;
+               device->oclass[NVDEV_ENGINE_CE1    ] = &gk104_ce1_oclass;
+               device->oclass[NVDEV_ENGINE_CE2    ] = &gk104_ce2_oclass;
+               device->oclass[NVDEV_ENGINE_MSVLD  ] = &gk104_msvld_oclass;
+               device->oclass[NVDEV_ENGINE_MSPDEC ] = &gk104_mspdec_oclass;
+               device->oclass[NVDEV_ENGINE_MSPPP  ] = &gf100_msppp_oclass;
+               break;
+       case 0x108:
+               device->cname = "GK208";
+               device->oclass[NVDEV_SUBDEV_VBIOS  ] = &nvkm_bios_oclass;
+               device->oclass[NVDEV_SUBDEV_GPIO   ] =  gk104_gpio_oclass;
+               device->oclass[NVDEV_SUBDEV_I2C    ] =  gk104_i2c_oclass;
+               device->oclass[NVDEV_SUBDEV_FUSE   ] = &gf100_fuse_oclass;
+               device->oclass[NVDEV_SUBDEV_CLK    ] = &gk104_clk_oclass;
+               device->oclass[NVDEV_SUBDEV_THERM  ] = &gf110_therm_oclass;
+               device->oclass[NVDEV_SUBDEV_MXM    ] = &nv50_mxm_oclass;
+               device->oclass[NVDEV_SUBDEV_DEVINIT] =  gf100_devinit_oclass;
+               device->oclass[NVDEV_SUBDEV_MC     ] =  gk20a_mc_oclass;
+               device->oclass[NVDEV_SUBDEV_BUS    ] =  gf100_bus_oclass;
+               device->oclass[NVDEV_SUBDEV_TIMER  ] = &nv04_timer_oclass;
+               device->oclass[NVDEV_SUBDEV_FB     ] =  gk104_fb_oclass;
+               device->oclass[NVDEV_SUBDEV_LTC    ] =  gk104_ltc_oclass;
+               device->oclass[NVDEV_SUBDEV_IBUS   ] = &gk104_ibus_oclass;
+               device->oclass[NVDEV_SUBDEV_INSTMEM] =  nv50_instmem_oclass;
+               device->oclass[NVDEV_SUBDEV_MMU    ] = &gf100_mmu_oclass;
+               device->oclass[NVDEV_SUBDEV_BAR    ] = &gf100_bar_oclass;
+               device->oclass[NVDEV_SUBDEV_PMU    ] =  gk208_pmu_oclass;
+               device->oclass[NVDEV_SUBDEV_VOLT   ] = &nv40_volt_oclass;
+               device->oclass[NVDEV_ENGINE_DMAOBJ ] =  gf110_dmaeng_oclass;
+               device->oclass[NVDEV_ENGINE_FIFO   ] =  gk208_fifo_oclass;
+               device->oclass[NVDEV_ENGINE_SW     ] =  gf100_sw_oclass;
+               device->oclass[NVDEV_ENGINE_GR     ] =  gk208_gr_oclass;
+               device->oclass[NVDEV_ENGINE_DISP   ] =  gk110_disp_oclass;
+               device->oclass[NVDEV_ENGINE_CE0    ] = &gk104_ce0_oclass;
+               device->oclass[NVDEV_ENGINE_CE1    ] = &gk104_ce1_oclass;
+               device->oclass[NVDEV_ENGINE_CE2    ] = &gk104_ce2_oclass;
+               device->oclass[NVDEV_ENGINE_MSVLD  ] = &gk104_msvld_oclass;
+               device->oclass[NVDEV_ENGINE_MSPDEC ] = &gk104_mspdec_oclass;
+               device->oclass[NVDEV_ENGINE_MSPPP  ] = &gf100_msppp_oclass;
+               break;
+       default:
+               nv_fatal(device, "unknown Kepler chipset\n");
+               return -EINVAL;
+       }
+
+       return 0;
+}
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/device/gm100.c b/drivers/gpu/drm/nouveau/nvkm/engine/device/gm100.c
new file mode 100644 (file)
index 0000000..539561e
--- /dev/null
@@ -0,0 +1,151 @@
+/*
+ * Copyright 2012 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 "priv.h"
+
+#include <subdev/bios.h>
+#include <subdev/bus.h>
+#include <subdev/gpio.h>
+#include <subdev/i2c.h>
+#include <subdev/fuse.h>
+#include <subdev/clk.h>
+#include <subdev/therm.h>
+#include <subdev/mxm.h>
+#include <subdev/devinit.h>
+#include <subdev/mc.h>
+#include <subdev/timer.h>
+#include <subdev/fb.h>
+#include <subdev/ltc.h>
+#include <subdev/ibus.h>
+#include <subdev/instmem.h>
+#include <subdev/mmu.h>
+#include <subdev/bar.h>
+#include <subdev/pmu.h>
+#include <subdev/volt.h>
+
+#include <engine/dmaobj.h>
+#include <engine/fifo.h>
+#include <engine/sw.h>
+#include <engine/gr.h>
+#include <engine/disp.h>
+#include <engine/ce.h>
+#include <engine/bsp.h>
+#include <engine/msvld.h>
+#include <engine/mspdec.h>
+#include <engine/msppp.h>
+#include <engine/pm.h>
+
+int
+gm100_identify(struct nvkm_device *device)
+{
+       switch (device->chipset) {
+       case 0x117:
+               device->cname = "GM107";
+               device->oclass[NVDEV_SUBDEV_VBIOS  ] = &nvkm_bios_oclass;
+               device->oclass[NVDEV_SUBDEV_GPIO   ] =  gk104_gpio_oclass;
+               device->oclass[NVDEV_SUBDEV_I2C    ] =  gf110_i2c_oclass;
+               device->oclass[NVDEV_SUBDEV_FUSE   ] = &gm107_fuse_oclass;
+               device->oclass[NVDEV_SUBDEV_CLK    ] = &gk104_clk_oclass;
+               device->oclass[NVDEV_SUBDEV_THERM  ] = &gm107_therm_oclass;
+               device->oclass[NVDEV_SUBDEV_MXM    ] = &nv50_mxm_oclass;
+               device->oclass[NVDEV_SUBDEV_DEVINIT] =  gm107_devinit_oclass;
+               device->oclass[NVDEV_SUBDEV_MC     ] =  gk20a_mc_oclass;
+               device->oclass[NVDEV_SUBDEV_BUS    ] =  gf100_bus_oclass;
+               device->oclass[NVDEV_SUBDEV_TIMER  ] = &gk20a_timer_oclass;
+               device->oclass[NVDEV_SUBDEV_FB     ] =  gm107_fb_oclass;
+               device->oclass[NVDEV_SUBDEV_LTC    ] =  gm107_ltc_oclass;
+               device->oclass[NVDEV_SUBDEV_IBUS   ] = &gk104_ibus_oclass;
+               device->oclass[NVDEV_SUBDEV_INSTMEM] =  nv50_instmem_oclass;
+               device->oclass[NVDEV_SUBDEV_MMU    ] = &gf100_mmu_oclass;
+               device->oclass[NVDEV_SUBDEV_BAR    ] = &gf100_bar_oclass;
+               device->oclass[NVDEV_SUBDEV_PMU    ] =  gk208_pmu_oclass;
+
+#if 0
+               device->oclass[NVDEV_SUBDEV_VOLT   ] = &nv40_volt_oclass;
+#endif
+               device->oclass[NVDEV_ENGINE_DMAOBJ ] =  gf110_dmaeng_oclass;
+               device->oclass[NVDEV_ENGINE_FIFO   ] =  gk208_fifo_oclass;
+               device->oclass[NVDEV_ENGINE_SW     ] =  gf100_sw_oclass;
+               device->oclass[NVDEV_ENGINE_GR     ] =  gm107_gr_oclass;
+               device->oclass[NVDEV_ENGINE_DISP   ] =  gm107_disp_oclass;
+               device->oclass[NVDEV_ENGINE_CE0    ] = &gk104_ce0_oclass;
+#if 0
+               device->oclass[NVDEV_ENGINE_CE1    ] = &gk104_ce1_oclass;
+#endif
+               device->oclass[NVDEV_ENGINE_CE2    ] = &gk104_ce2_oclass;
+#if 0
+               device->oclass[NVDEV_ENGINE_MSVLD  ] = &gk104_msvld_oclass;
+               device->oclass[NVDEV_ENGINE_MSPDEC ] = &gk104_mspdec_oclass;
+               device->oclass[NVDEV_ENGINE_MSPPP  ] = &gf100_msppp_oclass;
+#endif
+               break;
+       case 0x124:
+               device->cname = "GM204";
+               device->oclass[NVDEV_SUBDEV_VBIOS  ] = &nvkm_bios_oclass;
+               device->oclass[NVDEV_SUBDEV_GPIO   ] =  gk104_gpio_oclass;
+               device->oclass[NVDEV_SUBDEV_I2C    ] =  gm204_i2c_oclass;
+               device->oclass[NVDEV_SUBDEV_FUSE   ] = &gm107_fuse_oclass;
+#if 0
+               /* looks to be some non-trivial changes */
+               device->oclass[NVDEV_SUBDEV_CLK    ] = &gk104_clk_oclass;
+               /* priv ring says no to 0x10eb14 writes */
+               device->oclass[NVDEV_SUBDEV_THERM  ] = &gm107_therm_oclass;
+#endif
+               device->oclass[NVDEV_SUBDEV_MXM    ] = &nv50_mxm_oclass;
+               device->oclass[NVDEV_SUBDEV_DEVINIT] =  gm204_devinit_oclass;
+               device->oclass[NVDEV_SUBDEV_MC     ] =  gk20a_mc_oclass;
+               device->oclass[NVDEV_SUBDEV_BUS    ] =  gf100_bus_oclass;
+               device->oclass[NVDEV_SUBDEV_TIMER  ] = &gk20a_timer_oclass;
+               device->oclass[NVDEV_SUBDEV_FB     ] =  gm107_fb_oclass;
+               device->oclass[NVDEV_SUBDEV_LTC    ] =  gm107_ltc_oclass;
+               device->oclass[NVDEV_SUBDEV_IBUS   ] = &gk104_ibus_oclass;
+               device->oclass[NVDEV_SUBDEV_INSTMEM] =  nv50_instmem_oclass;
+               device->oclass[NVDEV_SUBDEV_MMU    ] = &gf100_mmu_oclass;
+               device->oclass[NVDEV_SUBDEV_BAR    ] = &gf100_bar_oclass;
+               device->oclass[NVDEV_SUBDEV_PMU    ] =  gk208_pmu_oclass;
+#if 0
+               device->oclass[NVDEV_SUBDEV_VOLT   ] = &nv40_volt_oclass;
+#endif
+               device->oclass[NVDEV_ENGINE_DMAOBJ ] =  gf110_dmaeng_oclass;
+#if 0
+               device->oclass[NVDEV_ENGINE_FIFO   ] =  gk208_fifo_oclass;
+               device->oclass[NVDEV_ENGINE_SW     ] =  gf100_sw_oclass;
+               device->oclass[NVDEV_ENGINE_GR     ] =  gm107_gr_oclass;
+#endif
+               device->oclass[NVDEV_ENGINE_DISP   ] =  gm204_disp_oclass;
+#if 0
+               device->oclass[NVDEV_ENGINE_CE0    ] = &gm204_ce0_oclass;
+               device->oclass[NVDEV_ENGINE_CE1    ] = &gm204_ce1_oclass;
+               device->oclass[NVDEV_ENGINE_CE2    ] = &gm204_ce2_oclass;
+               device->oclass[NVDEV_ENGINE_MSVLD  ] = &gk104_msvld_oclass;
+               device->oclass[NVDEV_ENGINE_MSPDEC ] = &gk104_mspdec_oclass;
+               device->oclass[NVDEV_ENGINE_MSPPP  ] = &gf100_msppp_oclass;
+#endif
+               break;
+       default:
+               nv_fatal(device, "unknown Maxwell chipset\n");
+               return -EINVAL;
+       }
+
+       return 0;
+}
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/device/nv04.c b/drivers/gpu/drm/nouveau/nvkm/engine/device/nv04.c
new file mode 100644 (file)
index 0000000..5a2ae04
--- /dev/null
@@ -0,0 +1,89 @@
+/*
+ * Copyright 2012 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 "priv.h"
+
+#include <subdev/bios.h>
+#include <subdev/bus.h>
+#include <subdev/i2c.h>
+#include <subdev/clk.h>
+#include <subdev/devinit.h>
+#include <subdev/mc.h>
+#include <subdev/timer.h>
+#include <subdev/fb.h>
+#include <subdev/instmem.h>
+#include <subdev/mmu.h>
+
+#include <engine/dmaobj.h>
+#include <engine/fifo.h>
+#include <engine/sw.h>
+#include <engine/gr.h>
+#include <engine/disp.h>
+
+int
+nv04_identify(struct nvkm_device *device)
+{
+       switch (device->chipset) {
+       case 0x04:
+               device->cname = "NV04";
+               device->oclass[NVDEV_SUBDEV_VBIOS  ] = &nvkm_bios_oclass;
+               device->oclass[NVDEV_SUBDEV_I2C    ] =  nv04_i2c_oclass;
+               device->oclass[NVDEV_SUBDEV_CLK    ] = &nv04_clk_oclass;
+               device->oclass[NVDEV_SUBDEV_DEVINIT] =  nv04_devinit_oclass;
+               device->oclass[NVDEV_SUBDEV_MC     ] =  nv04_mc_oclass;
+               device->oclass[NVDEV_SUBDEV_BUS    ] =  nv04_bus_oclass;
+               device->oclass[NVDEV_SUBDEV_TIMER  ] = &nv04_timer_oclass;
+               device->oclass[NVDEV_SUBDEV_FB     ] =  nv04_fb_oclass;
+               device->oclass[NVDEV_SUBDEV_INSTMEM] =  nv04_instmem_oclass;
+               device->oclass[NVDEV_SUBDEV_MMU    ] = &nv04_mmu_oclass;
+               device->oclass[NVDEV_ENGINE_DMAOBJ ] =  nv04_dmaeng_oclass;
+               device->oclass[NVDEV_ENGINE_FIFO   ] =  nv04_fifo_oclass;
+               device->oclass[NVDEV_ENGINE_SW     ] =  nv04_sw_oclass;
+               device->oclass[NVDEV_ENGINE_GR     ] = &nv04_gr_oclass;
+               device->oclass[NVDEV_ENGINE_DISP   ] =  nv04_disp_oclass;
+               break;
+       case 0x05:
+               device->cname = "NV05";
+               device->oclass[NVDEV_SUBDEV_VBIOS  ] = &nvkm_bios_oclass;
+               device->oclass[NVDEV_SUBDEV_I2C    ] =  nv04_i2c_oclass;
+               device->oclass[NVDEV_SUBDEV_CLK    ] = &nv04_clk_oclass;
+               device->oclass[NVDEV_SUBDEV_DEVINIT] =  nv05_devinit_oclass;
+               device->oclass[NVDEV_SUBDEV_MC     ] =  nv04_mc_oclass;
+               device->oclass[NVDEV_SUBDEV_BUS    ] =  nv04_bus_oclass;
+               device->oclass[NVDEV_SUBDEV_TIMER  ] = &nv04_timer_oclass;
+               device->oclass[NVDEV_SUBDEV_FB     ] =  nv04_fb_oclass;
+               device->oclass[NVDEV_SUBDEV_INSTMEM] =  nv04_instmem_oclass;
+               device->oclass[NVDEV_SUBDEV_MMU    ] = &nv04_mmu_oclass;
+               device->oclass[NVDEV_ENGINE_DMAOBJ ] =  nv04_dmaeng_oclass;
+               device->oclass[NVDEV_ENGINE_FIFO   ] =  nv04_fifo_oclass;
+               device->oclass[NVDEV_ENGINE_SW     ] =  nv04_sw_oclass;
+               device->oclass[NVDEV_ENGINE_GR     ] = &nv04_gr_oclass;
+               device->oclass[NVDEV_ENGINE_DISP   ] =  nv04_disp_oclass;
+               break;
+       default:
+               nv_fatal(device, "unknown RIVA chipset\n");
+               return -EINVAL;
+       }
+
+       return 0;
+}
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/device/nv10.c b/drivers/gpu/drm/nouveau/nvkm/engine/device/nv10.c
new file mode 100644 (file)
index 0000000..94a1ca4
--- /dev/null
@@ -0,0 +1,204 @@
+/*
+ * Copyright 2012 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 "priv.h"
+
+#include <subdev/bios.h>
+#include <subdev/bus.h>
+#include <subdev/gpio.h>
+#include <subdev/i2c.h>
+#include <subdev/clk.h>
+#include <subdev/devinit.h>
+#include <subdev/mc.h>
+#include <subdev/timer.h>
+#include <subdev/fb.h>
+#include <subdev/instmem.h>
+#include <subdev/mmu.h>
+
+#include <engine/dmaobj.h>
+#include <engine/fifo.h>
+#include <engine/sw.h>
+#include <engine/gr.h>
+#include <engine/disp.h>
+
+int
+nv10_identify(struct nvkm_device *device)
+{
+       switch (device->chipset) {
+       case 0x10:
+               device->cname = "NV10";
+               device->oclass[NVDEV_SUBDEV_VBIOS  ] = &nvkm_bios_oclass;
+               device->oclass[NVDEV_SUBDEV_GPIO   ] =  nv10_gpio_oclass;
+               device->oclass[NVDEV_SUBDEV_I2C    ] =  nv04_i2c_oclass;
+               device->oclass[NVDEV_SUBDEV_CLK    ] = &nv04_clk_oclass;
+               device->oclass[NVDEV_SUBDEV_DEVINIT] =  nv10_devinit_oclass;
+               device->oclass[NVDEV_SUBDEV_MC     ] =  nv04_mc_oclass;
+               device->oclass[NVDEV_SUBDEV_BUS    ] =  nv04_bus_oclass;
+               device->oclass[NVDEV_SUBDEV_TIMER  ] = &nv04_timer_oclass;
+               device->oclass[NVDEV_SUBDEV_FB     ] =  nv10_fb_oclass;
+               device->oclass[NVDEV_SUBDEV_INSTMEM] =  nv04_instmem_oclass;
+               device->oclass[NVDEV_SUBDEV_MMU    ] = &nv04_mmu_oclass;
+               device->oclass[NVDEV_ENGINE_DMAOBJ ] =  nv04_dmaeng_oclass;
+               device->oclass[NVDEV_ENGINE_GR     ] = &nv10_gr_oclass;
+               device->oclass[NVDEV_ENGINE_DISP   ] =  nv04_disp_oclass;
+               break;
+       case 0x15:
+               device->cname = "NV15";
+               device->oclass[NVDEV_SUBDEV_VBIOS  ] = &nvkm_bios_oclass;
+               device->oclass[NVDEV_SUBDEV_GPIO   ] =  nv10_gpio_oclass;
+               device->oclass[NVDEV_SUBDEV_I2C    ] =  nv04_i2c_oclass;
+               device->oclass[NVDEV_SUBDEV_CLK    ] = &nv04_clk_oclass;
+               device->oclass[NVDEV_SUBDEV_DEVINIT] =  nv10_devinit_oclass;
+               device->oclass[NVDEV_SUBDEV_MC     ] =  nv04_mc_oclass;
+               device->oclass[NVDEV_SUBDEV_BUS    ] =  nv04_bus_oclass;
+               device->oclass[NVDEV_SUBDEV_TIMER  ] = &nv04_timer_oclass;
+               device->oclass[NVDEV_SUBDEV_FB     ] =  nv10_fb_oclass;
+               device->oclass[NVDEV_SUBDEV_INSTMEM] =  nv04_instmem_oclass;
+               device->oclass[NVDEV_SUBDEV_MMU    ] = &nv04_mmu_oclass;
+               device->oclass[NVDEV_ENGINE_DMAOBJ ] =  nv04_dmaeng_oclass;
+               device->oclass[NVDEV_ENGINE_FIFO   ] =  nv10_fifo_oclass;
+               device->oclass[NVDEV_ENGINE_SW     ] =  nv10_sw_oclass;
+               device->oclass[NVDEV_ENGINE_GR     ] = &nv10_gr_oclass;
+               device->oclass[NVDEV_ENGINE_DISP   ] =  nv04_disp_oclass;
+               break;
+       case 0x16:
+               device->cname = "NV16";
+               device->oclass[NVDEV_SUBDEV_VBIOS  ] = &nvkm_bios_oclass;
+               device->oclass[NVDEV_SUBDEV_GPIO   ] =  nv10_gpio_oclass;
+               device->oclass[NVDEV_SUBDEV_I2C    ] =  nv04_i2c_oclass;
+               device->oclass[NVDEV_SUBDEV_CLK    ] = &nv04_clk_oclass;
+               device->oclass[NVDEV_SUBDEV_DEVINIT] =  nv10_devinit_oclass;
+               device->oclass[NVDEV_SUBDEV_MC     ] =  nv04_mc_oclass;
+               device->oclass[NVDEV_SUBDEV_BUS    ] =  nv04_bus_oclass;
+               device->oclass[NVDEV_SUBDEV_TIMER  ] = &nv04_timer_oclass;
+               device->oclass[NVDEV_SUBDEV_FB     ] =  nv10_fb_oclass;
+               device->oclass[NVDEV_SUBDEV_INSTMEM] =  nv04_instmem_oclass;
+               device->oclass[NVDEV_SUBDEV_MMU    ] = &nv04_mmu_oclass;
+               device->oclass[NVDEV_ENGINE_DMAOBJ ] =  nv04_dmaeng_oclass;
+               device->oclass[NVDEV_ENGINE_FIFO   ] =  nv10_fifo_oclass;
+               device->oclass[NVDEV_ENGINE_SW     ] =  nv10_sw_oclass;
+               device->oclass[NVDEV_ENGINE_GR     ] = &nv10_gr_oclass;
+               device->oclass[NVDEV_ENGINE_DISP   ] =  nv04_disp_oclass;
+               break;
+       case 0x1a:
+               device->cname = "nForce";
+               device->oclass[NVDEV_SUBDEV_VBIOS  ] = &nvkm_bios_oclass;
+               device->oclass[NVDEV_SUBDEV_GPIO   ] =  nv10_gpio_oclass;
+               device->oclass[NVDEV_SUBDEV_I2C    ] =  nv04_i2c_oclass;
+               device->oclass[NVDEV_SUBDEV_CLK    ] = &nv04_clk_oclass;
+               device->oclass[NVDEV_SUBDEV_DEVINIT] =  nv1a_devinit_oclass;
+               device->oclass[NVDEV_SUBDEV_MC     ] =  nv04_mc_oclass;
+               device->oclass[NVDEV_SUBDEV_BUS    ] =  nv04_bus_oclass;
+               device->oclass[NVDEV_SUBDEV_TIMER  ] = &nv04_timer_oclass;
+               device->oclass[NVDEV_SUBDEV_FB     ] =  nv1a_fb_oclass;
+               device->oclass[NVDEV_SUBDEV_INSTMEM] =  nv04_instmem_oclass;
+               device->oclass[NVDEV_SUBDEV_MMU    ] = &nv04_mmu_oclass;
+               device->oclass[NVDEV_ENGINE_DMAOBJ ] =  nv04_dmaeng_oclass;
+               device->oclass[NVDEV_ENGINE_FIFO   ] =  nv10_fifo_oclass;
+               device->oclass[NVDEV_ENGINE_SW     ] =  nv10_sw_oclass;
+               device->oclass[NVDEV_ENGINE_GR     ] = &nv10_gr_oclass;
+               device->oclass[NVDEV_ENGINE_DISP   ] =  nv04_disp_oclass;
+               break;
+       case 0x11:
+               device->cname = "NV11";
+               device->oclass[NVDEV_SUBDEV_VBIOS  ] = &nvkm_bios_oclass;
+               device->oclass[NVDEV_SUBDEV_GPIO   ] =  nv10_gpio_oclass;
+               device->oclass[NVDEV_SUBDEV_I2C    ] =  nv04_i2c_oclass;
+               device->oclass[NVDEV_SUBDEV_CLK    ] = &nv04_clk_oclass;
+               device->oclass[NVDEV_SUBDEV_DEVINIT] =  nv10_devinit_oclass;
+               device->oclass[NVDEV_SUBDEV_MC     ] =  nv04_mc_oclass;
+               device->oclass[NVDEV_SUBDEV_BUS    ] =  nv04_bus_oclass;
+               device->oclass[NVDEV_SUBDEV_TIMER  ] = &nv04_timer_oclass;
+               device->oclass[NVDEV_SUBDEV_FB     ] =  nv10_fb_oclass;
+               device->oclass[NVDEV_SUBDEV_INSTMEM] =  nv04_instmem_oclass;
+               device->oclass[NVDEV_SUBDEV_MMU    ] = &nv04_mmu_oclass;
+               device->oclass[NVDEV_ENGINE_DMAOBJ ] =  nv04_dmaeng_oclass;
+               device->oclass[NVDEV_ENGINE_FIFO   ] =  nv10_fifo_oclass;
+               device->oclass[NVDEV_ENGINE_SW     ] =  nv10_sw_oclass;
+               device->oclass[NVDEV_ENGINE_GR     ] = &nv10_gr_oclass;
+               device->oclass[NVDEV_ENGINE_DISP   ] =  nv04_disp_oclass;
+               break;
+       case 0x17:
+               device->cname = "NV17";
+               device->oclass[NVDEV_SUBDEV_VBIOS  ] = &nvkm_bios_oclass;
+               device->oclass[NVDEV_SUBDEV_GPIO   ] =  nv10_gpio_oclass;
+               device->oclass[NVDEV_SUBDEV_I2C    ] =  nv04_i2c_oclass;
+               device->oclass[NVDEV_SUBDEV_CLK    ] = &nv04_clk_oclass;
+               device->oclass[NVDEV_SUBDEV_DEVINIT] =  nv10_devinit_oclass;
+               device->oclass[NVDEV_SUBDEV_MC     ] =  nv04_mc_oclass;
+               device->oclass[NVDEV_SUBDEV_BUS    ] =  nv04_bus_oclass;
+               device->oclass[NVDEV_SUBDEV_TIMER  ] = &nv04_timer_oclass;
+               device->oclass[NVDEV_SUBDEV_FB     ] =  nv10_fb_oclass;
+               device->oclass[NVDEV_SUBDEV_INSTMEM] =  nv04_instmem_oclass;
+               device->oclass[NVDEV_SUBDEV_MMU    ] = &nv04_mmu_oclass;
+               device->oclass[NVDEV_ENGINE_DMAOBJ ] =  nv04_dmaeng_oclass;
+               device->oclass[NVDEV_ENGINE_FIFO   ] =  nv17_fifo_oclass;
+               device->oclass[NVDEV_ENGINE_SW     ] =  nv10_sw_oclass;
+               device->oclass[NVDEV_ENGINE_GR     ] = &nv10_gr_oclass;
+               device->oclass[NVDEV_ENGINE_DISP   ] =  nv04_disp_oclass;
+               break;
+       case 0x1f:
+               device->cname = "nForce2";
+               device->oclass[NVDEV_SUBDEV_VBIOS  ] = &nvkm_bios_oclass;
+               device->oclass[NVDEV_SUBDEV_GPIO   ] =  nv10_gpio_oclass;
+               device->oclass[NVDEV_SUBDEV_I2C    ] =  nv04_i2c_oclass;
+               device->oclass[NVDEV_SUBDEV_CLK    ] = &nv04_clk_oclass;
+               device->oclass[NVDEV_SUBDEV_DEVINIT] =  nv1a_devinit_oclass;
+               device->oclass[NVDEV_SUBDEV_MC     ] =  nv04_mc_oclass;
+               device->oclass[NVDEV_SUBDEV_BUS    ] =  nv04_bus_oclass;
+               device->oclass[NVDEV_SUBDEV_TIMER  ] = &nv04_timer_oclass;
+               device->oclass[NVDEV_SUBDEV_FB     ] =  nv1a_fb_oclass;
+               device->oclass[NVDEV_SUBDEV_INSTMEM] =  nv04_instmem_oclass;
+               device->oclass[NVDEV_SUBDEV_MMU    ] = &nv04_mmu_oclass;
+               device->oclass[NVDEV_ENGINE_DMAOBJ ] =  nv04_dmaeng_oclass;
+               device->oclass[NVDEV_ENGINE_FIFO   ] =  nv17_fifo_oclass;
+               device->oclass[NVDEV_ENGINE_SW     ] =  nv10_sw_oclass;
+               device->oclass[NVDEV_ENGINE_GR     ] = &nv10_gr_oclass;
+               device->oclass[NVDEV_ENGINE_DISP   ] =  nv04_disp_oclass;
+               break;
+       case 0x18:
+               device->cname = "NV18";
+               device->oclass[NVDEV_SUBDEV_VBIOS  ] = &nvkm_bios_oclass;
+               device->oclass[NVDEV_SUBDEV_GPIO   ] =  nv10_gpio_oclass;
+               device->oclass[NVDEV_SUBDEV_I2C    ] =  nv04_i2c_oclass;
+               device->oclass[NVDEV_SUBDEV_CLK    ] = &nv04_clk_oclass;
+               device->oclass[NVDEV_SUBDEV_DEVINIT] =  nv10_devinit_oclass;
+               device->oclass[NVDEV_SUBDEV_MC     ] =  nv04_mc_oclass;
+               device->oclass[NVDEV_SUBDEV_BUS    ] =  nv04_bus_oclass;
+               device->oclass[NVDEV_SUBDEV_TIMER  ] = &nv04_timer_oclass;
+               device->oclass[NVDEV_SUBDEV_FB     ] =  nv10_fb_oclass;
+               device->oclass[NVDEV_SUBDEV_INSTMEM] =  nv04_instmem_oclass;
+               device->oclass[NVDEV_SUBDEV_MMU    ] = &nv04_mmu_oclass;
+               device->oclass[NVDEV_ENGINE_DMAOBJ ] =  nv04_dmaeng_oclass;
+               device->oclass[NVDEV_ENGINE_FIFO   ] =  nv17_fifo_oclass;
+               device->oclass[NVDEV_ENGINE_SW     ] =  nv10_sw_oclass;
+               device->oclass[NVDEV_ENGINE_GR     ] = &nv10_gr_oclass;
+               device->oclass[NVDEV_ENGINE_DISP   ] =  nv04_disp_oclass;
+               break;
+       default:
+               nv_fatal(device, "unknown Celsius chipset\n");
+               return -EINVAL;
+       }
+
+       return 0;
+}
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/device/nv20.c b/drivers/gpu/drm/nouveau/nvkm/engine/device/nv20.c
new file mode 100644 (file)
index 0000000..d5ec893
--- /dev/null
@@ -0,0 +1,131 @@
+/*
+ * Copyright 2012 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 "priv.h"
+
+#include <subdev/bios.h>
+#include <subdev/bus.h>
+#include <subdev/gpio.h>
+#include <subdev/i2c.h>
+#include <subdev/clk.h>
+#include <subdev/therm.h>
+#include <subdev/devinit.h>
+#include <subdev/mc.h>
+#include <subdev/timer.h>
+#include <subdev/fb.h>
+#include <subdev/instmem.h>
+#include <subdev/mmu.h>
+
+#include <engine/dmaobj.h>
+#include <engine/fifo.h>
+#include <engine/sw.h>
+#include <engine/gr.h>
+#include <engine/disp.h>
+
+int
+nv20_identify(struct nvkm_device *device)
+{
+       switch (device->chipset) {
+       case 0x20:
+               device->cname = "NV20";
+               device->oclass[NVDEV_SUBDEV_VBIOS  ] = &nvkm_bios_oclass;
+               device->oclass[NVDEV_SUBDEV_GPIO   ] =  nv10_gpio_oclass;
+               device->oclass[NVDEV_SUBDEV_I2C    ] =  nv04_i2c_oclass;
+               device->oclass[NVDEV_SUBDEV_CLK    ] = &nv04_clk_oclass;
+               device->oclass[NVDEV_SUBDEV_DEVINIT] =  nv20_devinit_oclass;
+               device->oclass[NVDEV_SUBDEV_MC     ] =  nv04_mc_oclass;
+               device->oclass[NVDEV_SUBDEV_BUS    ] =  nv04_bus_oclass;
+               device->oclass[NVDEV_SUBDEV_TIMER  ] = &nv04_timer_oclass;
+               device->oclass[NVDEV_SUBDEV_FB     ] =  nv20_fb_oclass;
+               device->oclass[NVDEV_SUBDEV_INSTMEM] =  nv04_instmem_oclass;
+               device->oclass[NVDEV_SUBDEV_MMU    ] = &nv04_mmu_oclass;
+               device->oclass[NVDEV_ENGINE_DMAOBJ ] =  nv04_dmaeng_oclass;
+               device->oclass[NVDEV_ENGINE_FIFO   ] =  nv17_fifo_oclass;
+               device->oclass[NVDEV_ENGINE_SW     ] =  nv10_sw_oclass;
+               device->oclass[NVDEV_ENGINE_GR     ] = &nv20_gr_oclass;
+               device->oclass[NVDEV_ENGINE_DISP   ] =  nv04_disp_oclass;
+               break;
+       case 0x25:
+               device->cname = "NV25";
+               device->oclass[NVDEV_SUBDEV_VBIOS  ] = &nvkm_bios_oclass;
+               device->oclass[NVDEV_SUBDEV_GPIO   ] =  nv10_gpio_oclass;
+               device->oclass[NVDEV_SUBDEV_I2C    ] =  nv04_i2c_oclass;
+               device->oclass[NVDEV_SUBDEV_CLK    ] = &nv04_clk_oclass;
+               device->oclass[NVDEV_SUBDEV_DEVINIT] =  nv20_devinit_oclass;
+               device->oclass[NVDEV_SUBDEV_MC     ] =  nv04_mc_oclass;
+               device->oclass[NVDEV_SUBDEV_BUS    ] =  nv04_bus_oclass;
+               device->oclass[NVDEV_SUBDEV_TIMER  ] = &nv04_timer_oclass;
+               device->oclass[NVDEV_SUBDEV_FB     ] =  nv25_fb_oclass;
+               device->oclass[NVDEV_SUBDEV_INSTMEM] =  nv04_instmem_oclass;
+               device->oclass[NVDEV_SUBDEV_MMU    ] = &nv04_mmu_oclass;
+               device->oclass[NVDEV_ENGINE_DMAOBJ ] =  nv04_dmaeng_oclass;
+               device->oclass[NVDEV_ENGINE_FIFO   ] =  nv17_fifo_oclass;
+               device->oclass[NVDEV_ENGINE_SW     ] =  nv10_sw_oclass;
+               device->oclass[NVDEV_ENGINE_GR     ] = &nv25_gr_oclass;
+               device->oclass[NVDEV_ENGINE_DISP   ] =  nv04_disp_oclass;
+               break;
+       case 0x28:
+               device->cname = "NV28";
+               device->oclass[NVDEV_SUBDEV_VBIOS  ] = &nvkm_bios_oclass;
+               device->oclass[NVDEV_SUBDEV_GPIO   ] =  nv10_gpio_oclass;
+               device->oclass[NVDEV_SUBDEV_I2C    ] =  nv04_i2c_oclass;
+               device->oclass[NVDEV_SUBDEV_CLK    ] = &nv04_clk_oclass;
+               device->oclass[NVDEV_SUBDEV_DEVINIT] =  nv20_devinit_oclass;
+               device->oclass[NVDEV_SUBDEV_MC     ] =  nv04_mc_oclass;
+               device->oclass[NVDEV_SUBDEV_BUS    ] =  nv04_bus_oclass;
+               device->oclass[NVDEV_SUBDEV_TIMER  ] = &nv04_timer_oclass;
+               device->oclass[NVDEV_SUBDEV_FB     ] =  nv25_fb_oclass;
+               device->oclass[NVDEV_SUBDEV_INSTMEM] =  nv04_instmem_oclass;
+               device->oclass[NVDEV_SUBDEV_MMU    ] = &nv04_mmu_oclass;
+               device->oclass[NVDEV_ENGINE_DMAOBJ ] =  nv04_dmaeng_oclass;
+               device->oclass[NVDEV_ENGINE_FIFO   ] =  nv17_fifo_oclass;
+               device->oclass[NVDEV_ENGINE_SW     ] =  nv10_sw_oclass;
+               device->oclass[NVDEV_ENGINE_GR     ] = &nv25_gr_oclass;
+               device->oclass[NVDEV_ENGINE_DISP   ] =  nv04_disp_oclass;
+               break;
+       case 0x2a:
+               device->cname = "NV2A";
+               device->oclass[NVDEV_SUBDEV_VBIOS  ] = &nvkm_bios_oclass;
+               device->oclass[NVDEV_SUBDEV_GPIO   ] =  nv10_gpio_oclass;
+               device->oclass[NVDEV_SUBDEV_I2C    ] =  nv04_i2c_oclass;
+               device->oclass[NVDEV_SUBDEV_CLK    ] = &nv04_clk_oclass;
+               device->oclass[NVDEV_SUBDEV_DEVINIT] =  nv20_devinit_oclass;
+               device->oclass[NVDEV_SUBDEV_MC     ] =  nv04_mc_oclass;
+               device->oclass[NVDEV_SUBDEV_BUS    ] =  nv04_bus_oclass;
+               device->oclass[NVDEV_SUBDEV_TIMER  ] = &nv04_timer_oclass;
+               device->oclass[NVDEV_SUBDEV_FB     ] =  nv25_fb_oclass;
+               device->oclass[NVDEV_SUBDEV_INSTMEM] =  nv04_instmem_oclass;
+               device->oclass[NVDEV_SUBDEV_MMU    ] = &nv04_mmu_oclass;
+               device->oclass[NVDEV_ENGINE_DMAOBJ ] =  nv04_dmaeng_oclass;
+               device->oclass[NVDEV_ENGINE_FIFO   ] =  nv17_fifo_oclass;
+               device->oclass[NVDEV_ENGINE_SW     ] =  nv10_sw_oclass;
+               device->oclass[NVDEV_ENGINE_GR     ] = &nv2a_gr_oclass;
+               device->oclass[NVDEV_ENGINE_DISP   ] =  nv04_disp_oclass;
+               break;
+       default:
+               nv_fatal(device, "unknown Kelvin chipset\n");
+               return -EINVAL;
+       }
+
+       return 0;
+}
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/device/nv30.c b/drivers/gpu/drm/nouveau/nvkm/engine/device/nv30.c
new file mode 100644 (file)
index 0000000..dda0962
--- /dev/null
@@ -0,0 +1,153 @@
+/*
+ * Copyright 2012 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 "priv.h"
+
+#include <subdev/bios.h>
+#include <subdev/bus.h>
+#include <subdev/gpio.h>
+#include <subdev/i2c.h>
+#include <subdev/clk.h>
+#include <subdev/devinit.h>
+#include <subdev/mc.h>
+#include <subdev/timer.h>
+#include <subdev/fb.h>
+#include <subdev/instmem.h>
+#include <subdev/mmu.h>
+
+#include <engine/dmaobj.h>
+#include <engine/fifo.h>
+#include <engine/sw.h>
+#include <engine/gr.h>
+#include <engine/mpeg.h>
+#include <engine/disp.h>
+
+int
+nv30_identify(struct nvkm_device *device)
+{
+       switch (device->chipset) {
+       case 0x30:
+               device->cname = "NV30";
+               device->oclass[NVDEV_SUBDEV_VBIOS  ] = &nvkm_bios_oclass;
+               device->oclass[NVDEV_SUBDEV_GPIO   ] =  nv10_gpio_oclass;
+               device->oclass[NVDEV_SUBDEV_I2C    ] =  nv04_i2c_oclass;
+               device->oclass[NVDEV_SUBDEV_CLK    ] = &nv04_clk_oclass;
+               device->oclass[NVDEV_SUBDEV_DEVINIT] =  nv20_devinit_oclass;
+               device->oclass[NVDEV_SUBDEV_MC     ] =  nv04_mc_oclass;
+               device->oclass[NVDEV_SUBDEV_BUS    ] =  nv04_bus_oclass;
+               device->oclass[NVDEV_SUBDEV_TIMER  ] = &nv04_timer_oclass;
+               device->oclass[NVDEV_SUBDEV_FB     ] =  nv30_fb_oclass;
+               device->oclass[NVDEV_SUBDEV_INSTMEM] =  nv04_instmem_oclass;
+               device->oclass[NVDEV_SUBDEV_MMU    ] = &nv04_mmu_oclass;
+               device->oclass[NVDEV_ENGINE_DMAOBJ ] =  nv04_dmaeng_oclass;
+               device->oclass[NVDEV_ENGINE_FIFO   ] =  nv17_fifo_oclass;
+               device->oclass[NVDEV_ENGINE_SW     ] =  nv10_sw_oclass;
+               device->oclass[NVDEV_ENGINE_GR     ] = &nv30_gr_oclass;
+               device->oclass[NVDEV_ENGINE_DISP   ] =  nv04_disp_oclass;
+               break;
+       case 0x35:
+               device->cname = "NV35";
+               device->oclass[NVDEV_SUBDEV_VBIOS  ] = &nvkm_bios_oclass;
+               device->oclass[NVDEV_SUBDEV_GPIO   ] =  nv10_gpio_oclass;
+               device->oclass[NVDEV_SUBDEV_I2C    ] =  nv04_i2c_oclass;
+               device->oclass[NVDEV_SUBDEV_CLK    ] = &nv04_clk_oclass;
+               device->oclass[NVDEV_SUBDEV_DEVINIT] =  nv20_devinit_oclass;
+               device->oclass[NVDEV_SUBDEV_MC     ] =  nv04_mc_oclass;
+               device->oclass[NVDEV_SUBDEV_BUS    ] =  nv04_bus_oclass;
+               device->oclass[NVDEV_SUBDEV_TIMER  ] = &nv04_timer_oclass;
+               device->oclass[NVDEV_SUBDEV_FB     ] =  nv35_fb_oclass;
+               device->oclass[NVDEV_SUBDEV_INSTMEM] =  nv04_instmem_oclass;
+               device->oclass[NVDEV_SUBDEV_MMU    ] = &nv04_mmu_oclass;
+               device->oclass[NVDEV_ENGINE_DMAOBJ ] =  nv04_dmaeng_oclass;
+               device->oclass[NVDEV_ENGINE_FIFO   ] =  nv17_fifo_oclass;
+               device->oclass[NVDEV_ENGINE_SW     ] =  nv10_sw_oclass;
+               device->oclass[NVDEV_ENGINE_GR     ] = &nv35_gr_oclass;
+               device->oclass[NVDEV_ENGINE_DISP   ] =  nv04_disp_oclass;
+               break;
+       case 0x31:
+               device->cname = "NV31";
+               device->oclass[NVDEV_SUBDEV_VBIOS  ] = &nvkm_bios_oclass;
+               device->oclass[NVDEV_SUBDEV_GPIO   ] =  nv10_gpio_oclass;
+               device->oclass[NVDEV_SUBDEV_I2C    ] =  nv04_i2c_oclass;
+               device->oclass[NVDEV_SUBDEV_CLK    ] = &nv04_clk_oclass;
+               device->oclass[NVDEV_SUBDEV_DEVINIT] =  nv20_devinit_oclass;
+               device->oclass[NVDEV_SUBDEV_MC     ] =  nv04_mc_oclass;
+               device->oclass[NVDEV_SUBDEV_BUS    ] =  nv31_bus_oclass;
+               device->oclass[NVDEV_SUBDEV_TIMER  ] = &nv04_timer_oclass;
+               device->oclass[NVDEV_SUBDEV_FB     ] =  nv30_fb_oclass;
+               device->oclass[NVDEV_SUBDEV_INSTMEM] =  nv04_instmem_oclass;
+               device->oclass[NVDEV_SUBDEV_MMU    ] = &nv04_mmu_oclass;
+               device->oclass[NVDEV_ENGINE_DMAOBJ ] =  nv04_dmaeng_oclass;
+               device->oclass[NVDEV_ENGINE_FIFO   ] =  nv17_fifo_oclass;
+               device->oclass[NVDEV_ENGINE_SW     ] =  nv10_sw_oclass;
+               device->oclass[NVDEV_ENGINE_GR     ] = &nv30_gr_oclass;
+               device->oclass[NVDEV_ENGINE_MPEG   ] = &nv31_mpeg_oclass;
+               device->oclass[NVDEV_ENGINE_DISP   ] =  nv04_disp_oclass;
+               break;
+       case 0x36:
+               device->cname = "NV36";
+               device->oclass[NVDEV_SUBDEV_VBIOS  ] = &nvkm_bios_oclass;
+               device->oclass[NVDEV_SUBDEV_GPIO   ] =  nv10_gpio_oclass;
+               device->oclass[NVDEV_SUBDEV_I2C    ] =  nv04_i2c_oclass;
+               device->oclass[NVDEV_SUBDEV_CLK    ] = &nv04_clk_oclass;
+               device->oclass[NVDEV_SUBDEV_DEVINIT] =  nv20_devinit_oclass;
+               device->oclass[NVDEV_SUBDEV_MC     ] =  nv04_mc_oclass;
+               device->oclass[NVDEV_SUBDEV_BUS    ] =  nv31_bus_oclass;
+               device->oclass[NVDEV_SUBDEV_TIMER  ] = &nv04_timer_oclass;
+               device->oclass[NVDEV_SUBDEV_FB     ] =  nv36_fb_oclass;
+               device->oclass[NVDEV_SUBDEV_INSTMEM] =  nv04_instmem_oclass;
+               device->oclass[NVDEV_SUBDEV_MMU    ] = &nv04_mmu_oclass;
+               device->oclass[NVDEV_ENGINE_DMAOBJ ] =  nv04_dmaeng_oclass;
+               device->oclass[NVDEV_ENGINE_FIFO   ] =  nv17_fifo_oclass;
+               device->oclass[NVDEV_ENGINE_SW     ] =  nv10_sw_oclass;
+               device->oclass[NVDEV_ENGINE_GR     ] = &nv35_gr_oclass;
+               device->oclass[NVDEV_ENGINE_MPEG   ] = &nv31_mpeg_oclass;
+               device->oclass[NVDEV_ENGINE_DISP   ] =  nv04_disp_oclass;
+               break;
+       case 0x34:
+               device->cname = "NV34";
+               device->oclass[NVDEV_SUBDEV_VBIOS  ] = &nvkm_bios_oclass;
+               device->oclass[NVDEV_SUBDEV_GPIO   ] =  nv10_gpio_oclass;
+               device->oclass[NVDEV_SUBDEV_I2C    ] =  nv04_i2c_oclass;
+               device->oclass[NVDEV_SUBDEV_CLK    ] = &nv04_clk_oclass;
+               device->oclass[NVDEV_SUBDEV_DEVINIT] =  nv10_devinit_oclass;
+               device->oclass[NVDEV_SUBDEV_MC     ] =  nv04_mc_oclass;
+               device->oclass[NVDEV_SUBDEV_BUS    ] =  nv31_bus_oclass;
+               device->oclass[NVDEV_SUBDEV_TIMER  ] = &nv04_timer_oclass;
+               device->oclass[NVDEV_SUBDEV_FB     ] =  nv10_fb_oclass;
+               device->oclass[NVDEV_SUBDEV_INSTMEM] =  nv04_instmem_oclass;
+               device->oclass[NVDEV_SUBDEV_MMU    ] = &nv04_mmu_oclass;
+               device->oclass[NVDEV_ENGINE_DMAOBJ ] =  nv04_dmaeng_oclass;
+               device->oclass[NVDEV_ENGINE_FIFO   ] =  nv17_fifo_oclass;
+               device->oclass[NVDEV_ENGINE_SW     ] =  nv10_sw_oclass;
+               device->oclass[NVDEV_ENGINE_GR     ] = &nv34_gr_oclass;
+               device->oclass[NVDEV_ENGINE_MPEG   ] = &nv31_mpeg_oclass;
+               device->oclass[NVDEV_ENGINE_DISP   ] =  nv04_disp_oclass;
+               break;
+       default:
+               nv_fatal(device, "unknown Rankine chipset\n");
+               return -EINVAL;
+       }
+
+       return 0;
+}
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/device/nv40.c b/drivers/gpu/drm/nouveau/nvkm/engine/device/nv40.c
new file mode 100644 (file)
index 0000000..c630136
--- /dev/null
@@ -0,0 +1,427 @@
+/*
+ * Copyright 2012 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 "priv.h"
+
+#include <subdev/bios.h>
+#include <subdev/bus.h>
+#include <subdev/mmu.h>
+#include <subdev/gpio.h>
+#include <subdev/i2c.h>
+#include <subdev/clk.h>
+#include <subdev/therm.h>
+#include <subdev/devinit.h>
+#include <subdev/mc.h>
+#include <subdev/timer.h>
+#include <subdev/fb.h>
+#include <subdev/instmem.h>
+#include <subdev/mmu.h>
+#include <subdev/volt.h>
+
+#include <engine/dmaobj.h>
+#include <engine/fifo.h>
+#include <engine/sw.h>
+#include <engine/gr.h>
+#include <engine/mpeg.h>
+#include <engine/disp.h>
+#include <engine/pm.h>
+
+int
+nv40_identify(struct nvkm_device *device)
+{
+       switch (device->chipset) {
+       case 0x40:
+               device->cname = "NV40";
+               device->oclass[NVDEV_SUBDEV_VBIOS  ] = &nvkm_bios_oclass;
+               device->oclass[NVDEV_SUBDEV_GPIO   ] =  nv10_gpio_oclass;
+               device->oclass[NVDEV_SUBDEV_I2C    ] =  nv04_i2c_oclass;
+               device->oclass[NVDEV_SUBDEV_CLK    ] = &nv40_clk_oclass;
+               device->oclass[NVDEV_SUBDEV_THERM  ] = &nv40_therm_oclass;
+               device->oclass[NVDEV_SUBDEV_DEVINIT] =  nv1a_devinit_oclass;
+               device->oclass[NVDEV_SUBDEV_MC     ] =  nv40_mc_oclass;
+               device->oclass[NVDEV_SUBDEV_BUS    ] =  nv31_bus_oclass;
+               device->oclass[NVDEV_SUBDEV_TIMER  ] = &nv04_timer_oclass;
+               device->oclass[NVDEV_SUBDEV_FB     ] =  nv40_fb_oclass;
+               device->oclass[NVDEV_SUBDEV_INSTMEM] =  nv40_instmem_oclass;
+               device->oclass[NVDEV_SUBDEV_MMU    ] = &nv04_mmu_oclass;
+               device->oclass[NVDEV_SUBDEV_VOLT   ] = &nv40_volt_oclass;
+               device->oclass[NVDEV_ENGINE_DMAOBJ ] =  nv04_dmaeng_oclass;
+               device->oclass[NVDEV_ENGINE_FIFO   ] =  nv40_fifo_oclass;
+               device->oclass[NVDEV_ENGINE_SW     ] =  nv10_sw_oclass;
+               device->oclass[NVDEV_ENGINE_GR     ] = &nv40_gr_oclass;
+               device->oclass[NVDEV_ENGINE_MPEG   ] = &nv40_mpeg_oclass;
+               device->oclass[NVDEV_ENGINE_DISP   ] =  nv04_disp_oclass;
+               device->oclass[NVDEV_ENGINE_PM     ] =  nv40_pm_oclass;
+               break;
+       case 0x41:
+               device->cname = "NV41";
+               device->oclass[NVDEV_SUBDEV_VBIOS  ] = &nvkm_bios_oclass;
+               device->oclass[NVDEV_SUBDEV_GPIO   ] =  nv10_gpio_oclass;
+               device->oclass[NVDEV_SUBDEV_I2C    ] =  nv04_i2c_oclass;
+               device->oclass[NVDEV_SUBDEV_CLK    ] = &nv40_clk_oclass;
+               device->oclass[NVDEV_SUBDEV_THERM  ] = &nv40_therm_oclass;
+               device->oclass[NVDEV_SUBDEV_DEVINIT] =  nv1a_devinit_oclass;
+               device->oclass[NVDEV_SUBDEV_MC     ] =  nv40_mc_oclass;
+               device->oclass[NVDEV_SUBDEV_BUS    ] =  nv31_bus_oclass;
+               device->oclass[NVDEV_SUBDEV_TIMER  ] = &nv04_timer_oclass;
+               device->oclass[NVDEV_SUBDEV_FB     ] =  nv41_fb_oclass;
+               device->oclass[NVDEV_SUBDEV_INSTMEM] =  nv40_instmem_oclass;
+               device->oclass[NVDEV_SUBDEV_MMU    ] = &nv41_mmu_oclass;
+               device->oclass[NVDEV_SUBDEV_VOLT   ] = &nv40_volt_oclass;
+               device->oclass[NVDEV_ENGINE_DMAOBJ ] =  nv04_dmaeng_oclass;
+               device->oclass[NVDEV_ENGINE_FIFO   ] =  nv40_fifo_oclass;
+               device->oclass[NVDEV_ENGINE_SW     ] =  nv10_sw_oclass;
+               device->oclass[NVDEV_ENGINE_GR     ] = &nv40_gr_oclass;
+               device->oclass[NVDEV_ENGINE_MPEG   ] = &nv40_mpeg_oclass;
+               device->oclass[NVDEV_ENGINE_DISP   ] =  nv04_disp_oclass;
+               device->oclass[NVDEV_ENGINE_PM     ] =  nv40_pm_oclass;
+               break;
+       case 0x42:
+               device->cname = "NV42";
+               device->oclass[NVDEV_SUBDEV_VBIOS  ] = &nvkm_bios_oclass;
+               device->oclass[NVDEV_SUBDEV_GPIO   ] =  nv10_gpio_oclass;
+               device->oclass[NVDEV_SUBDEV_I2C    ] =  nv04_i2c_oclass;
+               device->oclass[NVDEV_SUBDEV_CLK    ] = &nv40_clk_oclass;
+               device->oclass[NVDEV_SUBDEV_THERM  ] = &nv40_therm_oclass;
+               device->oclass[NVDEV_SUBDEV_DEVINIT] =  nv1a_devinit_oclass;
+               device->oclass[NVDEV_SUBDEV_MC     ] =  nv40_mc_oclass;
+               device->oclass[NVDEV_SUBDEV_BUS    ] =  nv31_bus_oclass;
+               device->oclass[NVDEV_SUBDEV_TIMER  ] = &nv04_timer_oclass;
+               device->oclass[NVDEV_SUBDEV_FB     ] =  nv41_fb_oclass;
+               device->oclass[NVDEV_SUBDEV_INSTMEM] =  nv40_instmem_oclass;
+               device->oclass[NVDEV_SUBDEV_MMU    ] = &nv41_mmu_oclass;
+               device->oclass[NVDEV_SUBDEV_VOLT   ] = &nv40_volt_oclass;
+               device->oclass[NVDEV_ENGINE_DMAOBJ ] =  nv04_dmaeng_oclass;
+               device->oclass[NVDEV_ENGINE_FIFO   ] =  nv40_fifo_oclass;
+               device->oclass[NVDEV_ENGINE_SW     ] =  nv10_sw_oclass;
+               device->oclass[NVDEV_ENGINE_GR     ] = &nv40_gr_oclass;
+               device->oclass[NVDEV_ENGINE_MPEG   ] = &nv40_mpeg_oclass;
+               device->oclass[NVDEV_ENGINE_DISP   ] =  nv04_disp_oclass;
+               device->oclass[NVDEV_ENGINE_PM     ] =  nv40_pm_oclass;
+               break;
+       case 0x43:
+               device->cname = "NV43";
+               device->oclass[NVDEV_SUBDEV_VBIOS  ] = &nvkm_bios_oclass;
+               device->oclass[NVDEV_SUBDEV_GPIO   ] =  nv10_gpio_oclass;
+               device->oclass[NVDEV_SUBDEV_I2C    ] =  nv04_i2c_oclass;
+               device->oclass[NVDEV_SUBDEV_CLK    ] = &nv40_clk_oclass;
+               device->oclass[NVDEV_SUBDEV_THERM  ] = &nv40_therm_oclass;
+               device->oclass[NVDEV_SUBDEV_DEVINIT] =  nv1a_devinit_oclass;
+               device->oclass[NVDEV_SUBDEV_MC     ] =  nv40_mc_oclass;
+               device->oclass[NVDEV_SUBDEV_BUS    ] =  nv31_bus_oclass;
+               device->oclass[NVDEV_SUBDEV_TIMER  ] = &nv04_timer_oclass;
+               device->oclass[NVDEV_SUBDEV_FB     ] =  nv41_fb_oclass;
+               device->oclass[NVDEV_SUBDEV_INSTMEM] =  nv40_instmem_oclass;
+               device->oclass[NVDEV_SUBDEV_MMU    ] = &nv41_mmu_oclass;
+               device->oclass[NVDEV_SUBDEV_VOLT   ] = &nv40_volt_oclass;
+               device->oclass[NVDEV_ENGINE_DMAOBJ ] =  nv04_dmaeng_oclass;
+               device->oclass[NVDEV_ENGINE_FIFO   ] =  nv40_fifo_oclass;
+               device->oclass[NVDEV_ENGINE_SW     ] =  nv10_sw_oclass;
+               device->oclass[NVDEV_ENGINE_GR     ] = &nv40_gr_oclass;
+               device->oclass[NVDEV_ENGINE_MPEG   ] = &nv40_mpeg_oclass;
+               device->oclass[NVDEV_ENGINE_DISP   ] =  nv04_disp_oclass;
+               device->oclass[NVDEV_ENGINE_PM     ] =  nv40_pm_oclass;
+               break;
+       case 0x45:
+               device->cname = "NV45";
+               device->oclass[NVDEV_SUBDEV_VBIOS  ] = &nvkm_bios_oclass;
+               device->oclass[NVDEV_SUBDEV_GPIO   ] =  nv10_gpio_oclass;
+               device->oclass[NVDEV_SUBDEV_I2C    ] =  nv04_i2c_oclass;
+               device->oclass[NVDEV_SUBDEV_CLK    ] = &nv40_clk_oclass;
+               device->oclass[NVDEV_SUBDEV_THERM  ] = &nv40_therm_oclass;
+               device->oclass[NVDEV_SUBDEV_DEVINIT] =  nv1a_devinit_oclass;
+               device->oclass[NVDEV_SUBDEV_MC     ] =  nv40_mc_oclass;
+               device->oclass[NVDEV_SUBDEV_BUS    ] =  nv31_bus_oclass;
+               device->oclass[NVDEV_SUBDEV_TIMER  ] = &nv04_timer_oclass;
+               device->oclass[NVDEV_SUBDEV_FB     ] =  nv40_fb_oclass;
+               device->oclass[NVDEV_SUBDEV_INSTMEM] =  nv40_instmem_oclass;
+               device->oclass[NVDEV_SUBDEV_MMU    ] = &nv04_mmu_oclass;
+               device->oclass[NVDEV_SUBDEV_VOLT   ] = &nv40_volt_oclass;
+               device->oclass[NVDEV_ENGINE_DMAOBJ ] =  nv04_dmaeng_oclass;
+               device->oclass[NVDEV_ENGINE_FIFO   ] =  nv40_fifo_oclass;
+               device->oclass[NVDEV_ENGINE_SW     ] =  nv10_sw_oclass;
+               device->oclass[NVDEV_ENGINE_GR     ] = &nv40_gr_oclass;
+               device->oclass[NVDEV_ENGINE_MPEG   ] = &nv44_mpeg_oclass;
+               device->oclass[NVDEV_ENGINE_DISP   ] =  nv04_disp_oclass;
+               device->oclass[NVDEV_ENGINE_PM     ] =  nv40_pm_oclass;
+               break;
+       case 0x47:
+               device->cname = "G70";
+               device->oclass[NVDEV_SUBDEV_VBIOS  ] = &nvkm_bios_oclass;
+               device->oclass[NVDEV_SUBDEV_GPIO   ] =  nv10_gpio_oclass;
+               device->oclass[NVDEV_SUBDEV_I2C    ] =  nv04_i2c_oclass;
+               device->oclass[NVDEV_SUBDEV_CLK    ] = &nv40_clk_oclass;
+               device->oclass[NVDEV_SUBDEV_THERM  ] = &nv40_therm_oclass;
+               device->oclass[NVDEV_SUBDEV_DEVINIT] =  nv1a_devinit_oclass;
+               device->oclass[NVDEV_SUBDEV_MC     ] =  nv40_mc_oclass;
+               device->oclass[NVDEV_SUBDEV_BUS    ] =  nv31_bus_oclass;
+               device->oclass[NVDEV_SUBDEV_TIMER  ] = &nv04_timer_oclass;
+               device->oclass[NVDEV_SUBDEV_FB     ] =  nv47_fb_oclass;
+               device->oclass[NVDEV_SUBDEV_INSTMEM] =  nv40_instmem_oclass;
+               device->oclass[NVDEV_SUBDEV_MMU    ] = &nv41_mmu_oclass;
+               device->oclass[NVDEV_SUBDEV_VOLT   ] = &nv40_volt_oclass;
+               device->oclass[NVDEV_ENGINE_DMAOBJ ] =  nv04_dmaeng_oclass;
+               device->oclass[NVDEV_ENGINE_FIFO   ] =  nv40_fifo_oclass;
+               device->oclass[NVDEV_ENGINE_SW     ] =  nv10_sw_oclass;
+               device->oclass[NVDEV_ENGINE_GR     ] = &nv40_gr_oclass;
+               device->oclass[NVDEV_ENGINE_MPEG   ] = &nv44_mpeg_oclass;
+               device->oclass[NVDEV_ENGINE_DISP   ] =  nv04_disp_oclass;
+               device->oclass[NVDEV_ENGINE_PM     ] =  nv40_pm_oclass;
+               break;
+       case 0x49:
+               device->cname = "G71";
+               device->oclass[NVDEV_SUBDEV_VBIOS  ] = &nvkm_bios_oclass;
+               device->oclass[NVDEV_SUBDEV_GPIO   ] =  nv10_gpio_oclass;
+               device->oclass[NVDEV_SUBDEV_I2C    ] =  nv04_i2c_oclass;
+               device->oclass[NVDEV_SUBDEV_CLK    ] = &nv40_clk_oclass;
+               device->oclass[NVDEV_SUBDEV_THERM  ] = &nv40_therm_oclass;
+               device->oclass[NVDEV_SUBDEV_DEVINIT] =  nv1a_devinit_oclass;
+               device->oclass[NVDEV_SUBDEV_MC     ] =  nv40_mc_oclass;
+               device->oclass[NVDEV_SUBDEV_BUS    ] =  nv31_bus_oclass;
+               device->oclass[NVDEV_SUBDEV_TIMER  ] = &nv04_timer_oclass;
+               device->oclass[NVDEV_SUBDEV_FB     ] =  nv49_fb_oclass;
+               device->oclass[NVDEV_SUBDEV_INSTMEM] =  nv40_instmem_oclass;
+               device->oclass[NVDEV_SUBDEV_MMU    ] = &nv41_mmu_oclass;
+               device->oclass[NVDEV_SUBDEV_VOLT   ] = &nv40_volt_oclass;
+               device->oclass[NVDEV_ENGINE_DMAOBJ ] =  nv04_dmaeng_oclass;
+               device->oclass[NVDEV_ENGINE_FIFO   ] =  nv40_fifo_oclass;
+               device->oclass[NVDEV_ENGINE_SW     ] =  nv10_sw_oclass;
+               device->oclass[NVDEV_ENGINE_GR     ] = &nv40_gr_oclass;
+               device->oclass[NVDEV_ENGINE_MPEG   ] = &nv44_mpeg_oclass;
+               device->oclass[NVDEV_ENGINE_DISP   ] =  nv04_disp_oclass;
+               device->oclass[NVDEV_ENGINE_PM     ] =  nv40_pm_oclass;
+               break;
+       case 0x4b:
+               device->cname = "G73";
+               device->oclass[NVDEV_SUBDEV_VBIOS  ] = &nvkm_bios_oclass;
+               device->oclass[NVDEV_SUBDEV_GPIO   ] =  nv10_gpio_oclass;
+               device->oclass[NVDEV_SUBDEV_I2C    ] =  nv04_i2c_oclass;
+               device->oclass[NVDEV_SUBDEV_CLK    ] = &nv40_clk_oclass;
+               device->oclass[NVDEV_SUBDEV_THERM  ] = &nv40_therm_oclass;
+               device->oclass[NVDEV_SUBDEV_DEVINIT] =  nv1a_devinit_oclass;
+               device->oclass[NVDEV_SUBDEV_MC     ] =  nv40_mc_oclass;
+               device->oclass[NVDEV_SUBDEV_BUS    ] =  nv31_bus_oclass;
+               device->oclass[NVDEV_SUBDEV_TIMER  ] = &nv04_timer_oclass;
+               device->oclass[NVDEV_SUBDEV_FB     ] =  nv49_fb_oclass;
+               device->oclass[NVDEV_SUBDEV_INSTMEM] =  nv40_instmem_oclass;
+               device->oclass[NVDEV_SUBDEV_MMU    ] = &nv41_mmu_oclass;
+               device->oclass[NVDEV_SUBDEV_VOLT   ] = &nv40_volt_oclass;
+               device->oclass[NVDEV_ENGINE_DMAOBJ ] =  nv04_dmaeng_oclass;
+               device->oclass[NVDEV_ENGINE_FIFO   ] =  nv40_fifo_oclass;
+               device->oclass[NVDEV_ENGINE_SW     ] =  nv10_sw_oclass;
+               device->oclass[NVDEV_ENGINE_GR     ] = &nv40_gr_oclass;
+               device->oclass[NVDEV_ENGINE_MPEG   ] = &nv44_mpeg_oclass;
+               device->oclass[NVDEV_ENGINE_DISP   ] =  nv04_disp_oclass;
+               device->oclass[NVDEV_ENGINE_PM     ] =  nv40_pm_oclass;
+               break;
+       case 0x44:
+               device->cname = "NV44";
+               device->oclass[NVDEV_SUBDEV_VBIOS  ] = &nvkm_bios_oclass;
+               device->oclass[NVDEV_SUBDEV_GPIO   ] =  nv10_gpio_oclass;
+               device->oclass[NVDEV_SUBDEV_I2C    ] =  nv04_i2c_oclass;
+               device->oclass[NVDEV_SUBDEV_CLK    ] = &nv40_clk_oclass;
+               device->oclass[NVDEV_SUBDEV_THERM  ] = &nv40_therm_oclass;
+               device->oclass[NVDEV_SUBDEV_DEVINIT] =  nv1a_devinit_oclass;
+               device->oclass[NVDEV_SUBDEV_MC     ] =  nv44_mc_oclass;
+               device->oclass[NVDEV_SUBDEV_BUS    ] =  nv31_bus_oclass;
+               device->oclass[NVDEV_SUBDEV_TIMER  ] = &nv04_timer_oclass;
+               device->oclass[NVDEV_SUBDEV_FB     ] =  nv44_fb_oclass;
+               device->oclass[NVDEV_SUBDEV_INSTMEM] =  nv40_instmem_oclass;
+               device->oclass[NVDEV_SUBDEV_MMU    ] = &nv44_mmu_oclass;
+               device->oclass[NVDEV_SUBDEV_VOLT   ] = &nv40_volt_oclass;
+               device->oclass[NVDEV_ENGINE_DMAOBJ ] =  nv04_dmaeng_oclass;
+               device->oclass[NVDEV_ENGINE_FIFO   ] =  nv40_fifo_oclass;
+               device->oclass[NVDEV_ENGINE_SW     ] =  nv10_sw_oclass;
+               device->oclass[NVDEV_ENGINE_GR     ] = &nv40_gr_oclass;
+               device->oclass[NVDEV_ENGINE_MPEG   ] = &nv44_mpeg_oclass;
+               device->oclass[NVDEV_ENGINE_DISP   ] =  nv04_disp_oclass;
+               device->oclass[NVDEV_ENGINE_PM     ] =  nv40_pm_oclass;
+               break;
+       case 0x46:
+               device->cname = "G72";
+               device->oclass[NVDEV_SUBDEV_VBIOS  ] = &nvkm_bios_oclass;
+               device->oclass[NVDEV_SUBDEV_GPIO   ] =  nv10_gpio_oclass;
+               device->oclass[NVDEV_SUBDEV_I2C    ] =  nv04_i2c_oclass;
+               device->oclass[NVDEV_SUBDEV_CLK    ] = &nv40_clk_oclass;
+               device->oclass[NVDEV_SUBDEV_THERM  ] = &nv40_therm_oclass;
+               device->oclass[NVDEV_SUBDEV_DEVINIT] =  nv1a_devinit_oclass;
+               device->oclass[NVDEV_SUBDEV_MC     ] =  nv44_mc_oclass;
+               device->oclass[NVDEV_SUBDEV_BUS    ] =  nv31_bus_oclass;
+               device->oclass[NVDEV_SUBDEV_TIMER  ] = &nv04_timer_oclass;
+               device->oclass[NVDEV_SUBDEV_FB     ] =  nv46_fb_oclass;
+               device->oclass[NVDEV_SUBDEV_INSTMEM] =  nv40_instmem_oclass;
+               device->oclass[NVDEV_SUBDEV_MMU    ] = &nv44_mmu_oclass;
+               device->oclass[NVDEV_SUBDEV_VOLT   ] = &nv40_volt_oclass;
+               device->oclass[NVDEV_ENGINE_DMAOBJ ] =  nv04_dmaeng_oclass;
+               device->oclass[NVDEV_ENGINE_FIFO   ] =  nv40_fifo_oclass;
+               device->oclass[NVDEV_ENGINE_SW     ] =  nv10_sw_oclass;
+               device->oclass[NVDEV_ENGINE_GR     ] = &nv40_gr_oclass;
+               device->oclass[NVDEV_ENGINE_MPEG   ] = &nv44_mpeg_oclass;
+               device->oclass[NVDEV_ENGINE_DISP   ] =  nv04_disp_oclass;
+               device->oclass[NVDEV_ENGINE_PM     ] =  nv40_pm_oclass;
+               break;
+       case 0x4a:
+               device->cname = "NV44A";
+               device->oclass[NVDEV_SUBDEV_VBIOS  ] = &nvkm_bios_oclass;
+               device->oclass[NVDEV_SUBDEV_GPIO   ] =  nv10_gpio_oclass;
+               device->oclass[NVDEV_SUBDEV_I2C    ] =  nv04_i2c_oclass;
+               device->oclass[NVDEV_SUBDEV_CLK    ] = &nv40_clk_oclass;
+               device->oclass[NVDEV_SUBDEV_THERM  ] = &nv40_therm_oclass;
+               device->oclass[NVDEV_SUBDEV_DEVINIT] =  nv1a_devinit_oclass;
+               device->oclass[NVDEV_SUBDEV_MC     ] =  nv44_mc_oclass;
+               device->oclass[NVDEV_SUBDEV_BUS    ] =  nv31_bus_oclass;
+               device->oclass[NVDEV_SUBDEV_TIMER  ] = &nv04_timer_oclass;
+               device->oclass[NVDEV_SUBDEV_FB     ] =  nv44_fb_oclass;
+               device->oclass[NVDEV_SUBDEV_INSTMEM] =  nv40_instmem_oclass;
+               device->oclass[NVDEV_SUBDEV_MMU    ] = &nv44_mmu_oclass;
+               device->oclass[NVDEV_SUBDEV_VOLT   ] = &nv40_volt_oclass;
+               device->oclass[NVDEV_ENGINE_DMAOBJ ] =  nv04_dmaeng_oclass;
+               device->oclass[NVDEV_ENGINE_FIFO   ] =  nv40_fifo_oclass;
+               device->oclass[NVDEV_ENGINE_SW     ] =  nv10_sw_oclass;
+               device->oclass[NVDEV_ENGINE_GR     ] = &nv40_gr_oclass;
+               device->oclass[NVDEV_ENGINE_MPEG   ] = &nv44_mpeg_oclass;
+               device->oclass[NVDEV_ENGINE_DISP   ] =  nv04_disp_oclass;
+               device->oclass[NVDEV_ENGINE_PM     ] =  nv40_pm_oclass;
+               break;
+       case 0x4c:
+               device->cname = "C61";
+               device->oclass[NVDEV_SUBDEV_VBIOS  ] = &nvkm_bios_oclass;
+               device->oclass[NVDEV_SUBDEV_GPIO   ] =  nv10_gpio_oclass;
+               device->oclass[NVDEV_SUBDEV_I2C    ] =  nv04_i2c_oclass;
+               device->oclass[NVDEV_SUBDEV_CLK    ] = &nv40_clk_oclass;
+               device->oclass[NVDEV_SUBDEV_THERM  ] = &nv40_therm_oclass;
+               device->oclass[NVDEV_SUBDEV_DEVINIT] =  nv1a_devinit_oclass;
+               device->oclass[NVDEV_SUBDEV_MC     ] =  nv4c_mc_oclass;
+               device->oclass[NVDEV_SUBDEV_BUS    ] =  nv31_bus_oclass;
+               device->oclass[NVDEV_SUBDEV_TIMER  ] = &nv04_timer_oclass;
+               device->oclass[NVDEV_SUBDEV_FB     ] =  nv46_fb_oclass;
+               device->oclass[NVDEV_SUBDEV_INSTMEM] =  nv40_instmem_oclass;
+               device->oclass[NVDEV_SUBDEV_MMU    ] = &nv44_mmu_oclass;
+               device->oclass[NVDEV_SUBDEV_VOLT   ] = &nv40_volt_oclass;
+               device->oclass[NVDEV_ENGINE_DMAOBJ ] =  nv04_dmaeng_oclass;
+               device->oclass[NVDEV_ENGINE_FIFO   ] =  nv40_fifo_oclass;
+               device->oclass[NVDEV_ENGINE_SW     ] =  nv10_sw_oclass;
+               device->oclass[NVDEV_ENGINE_GR     ] = &nv40_gr_oclass;
+               device->oclass[NVDEV_ENGINE_MPEG   ] = &nv44_mpeg_oclass;
+               device->oclass[NVDEV_ENGINE_DISP   ] =  nv04_disp_oclass;
+               device->oclass[NVDEV_ENGINE_PM     ] =  nv40_pm_oclass;
+               break;
+       case 0x4e:
+               device->cname = "C51";
+               device->oclass[NVDEV_SUBDEV_VBIOS  ] = &nvkm_bios_oclass;
+               device->oclass[NVDEV_SUBDEV_GPIO   ] =  nv10_gpio_oclass;
+               device->oclass[NVDEV_SUBDEV_I2C    ] =  nv4e_i2c_oclass;
+               device->oclass[NVDEV_SUBDEV_CLK    ] = &nv40_clk_oclass;
+               device->oclass[NVDEV_SUBDEV_THERM  ] = &nv40_therm_oclass;
+               device->oclass[NVDEV_SUBDEV_DEVINIT] =  nv1a_devinit_oclass;
+               device->oclass[NVDEV_SUBDEV_MC     ] =  nv4c_mc_oclass;
+               device->oclass[NVDEV_SUBDEV_BUS    ] =  nv31_bus_oclass;
+               device->oclass[NVDEV_SUBDEV_TIMER  ] = &nv04_timer_oclass;
+               device->oclass[NVDEV_SUBDEV_FB     ] =  nv4e_fb_oclass;
+               device->oclass[NVDEV_SUBDEV_INSTMEM] =  nv40_instmem_oclass;
+               device->oclass[NVDEV_SUBDEV_MMU    ] = &nv44_mmu_oclass;
+               device->oclass[NVDEV_SUBDEV_VOLT   ] = &nv40_volt_oclass;
+               device->oclass[NVDEV_ENGINE_DMAOBJ ] =  nv04_dmaeng_oclass;
+               device->oclass[NVDEV_ENGINE_FIFO   ] =  nv40_fifo_oclass;
+               device->oclass[NVDEV_ENGINE_SW     ] =  nv10_sw_oclass;
+               device->oclass[NVDEV_ENGINE_GR     ] = &nv40_gr_oclass;
+               device->oclass[NVDEV_ENGINE_MPEG   ] = &nv44_mpeg_oclass;
+               device->oclass[NVDEV_ENGINE_DISP   ] =  nv04_disp_oclass;
+               device->oclass[NVDEV_ENGINE_PM     ] =  nv40_pm_oclass;
+               break;
+       case 0x63:
+               device->cname = "C73";
+               device->oclass[NVDEV_SUBDEV_VBIOS  ] = &nvkm_bios_oclass;
+               device->oclass[NVDEV_SUBDEV_GPIO   ] =  nv10_gpio_oclass;
+               device->oclass[NVDEV_SUBDEV_I2C    ] =  nv04_i2c_oclass;
+               device->oclass[NVDEV_SUBDEV_CLK    ] = &nv40_clk_oclass;
+               device->oclass[NVDEV_SUBDEV_THERM  ] = &nv40_therm_oclass;
+               device->oclass[NVDEV_SUBDEV_DEVINIT] =  nv1a_devinit_oclass;
+               device->oclass[NVDEV_SUBDEV_MC     ] =  nv4c_mc_oclass;
+               device->oclass[NVDEV_SUBDEV_BUS    ] =  nv31_bus_oclass;
+               device->oclass[NVDEV_SUBDEV_TIMER  ] = &nv04_timer_oclass;
+               device->oclass[NVDEV_SUBDEV_FB     ] =  nv46_fb_oclass;
+               device->oclass[NVDEV_SUBDEV_INSTMEM] =  nv40_instmem_oclass;
+               device->oclass[NVDEV_SUBDEV_MMU    ] = &nv44_mmu_oclass;
+               device->oclass[NVDEV_SUBDEV_VOLT   ] = &nv40_volt_oclass;
+               device->oclass[NVDEV_ENGINE_DMAOBJ ] =  nv04_dmaeng_oclass;
+               device->oclass[NVDEV_ENGINE_FIFO   ] =  nv40_fifo_oclass;
+               device->oclass[NVDEV_ENGINE_SW     ] =  nv10_sw_oclass;
+               device->oclass[NVDEV_ENGINE_GR     ] = &nv40_gr_oclass;
+               device->oclass[NVDEV_ENGINE_MPEG   ] = &nv44_mpeg_oclass;
+               device->oclass[NVDEV_ENGINE_DISP   ] =  nv04_disp_oclass;
+               device->oclass[NVDEV_ENGINE_PM     ] =  nv40_pm_oclass;
+               break;
+       case 0x67:
+               device->cname = "C67";
+               device->oclass[NVDEV_SUBDEV_VBIOS  ] = &nvkm_bios_oclass;
+               device->oclass[NVDEV_SUBDEV_GPIO   ] =  nv10_gpio_oclass;
+               device->oclass[NVDEV_SUBDEV_I2C    ] =  nv04_i2c_oclass;
+               device->oclass[NVDEV_SUBDEV_CLK    ] = &nv40_clk_oclass;
+               device->oclass[NVDEV_SUBDEV_THERM  ] = &nv40_therm_oclass;
+               device->oclass[NVDEV_SUBDEV_DEVINIT] =  nv1a_devinit_oclass;
+               device->oclass[NVDEV_SUBDEV_MC     ] =  nv4c_mc_oclass;
+               device->oclass[NVDEV_SUBDEV_BUS    ] =  nv31_bus_oclass;
+               device->oclass[NVDEV_SUBDEV_TIMER  ] = &nv04_timer_oclass;
+               device->oclass[NVDEV_SUBDEV_FB     ] =  nv46_fb_oclass;
+               device->oclass[NVDEV_SUBDEV_INSTMEM] =  nv40_instmem_oclass;
+               device->oclass[NVDEV_SUBDEV_MMU    ] = &nv44_mmu_oclass;
+               device->oclass[NVDEV_SUBDEV_VOLT   ] = &nv40_volt_oclass;
+               device->oclass[NVDEV_ENGINE_DMAOBJ ] =  nv04_dmaeng_oclass;
+               device->oclass[NVDEV_ENGINE_FIFO   ] =  nv40_fifo_oclass;
+               device->oclass[NVDEV_ENGINE_SW     ] =  nv10_sw_oclass;
+               device->oclass[NVDEV_ENGINE_GR     ] = &nv40_gr_oclass;
+               device->oclass[NVDEV_ENGINE_MPEG   ] = &nv44_mpeg_oclass;
+               device->oclass[NVDEV_ENGINE_DISP   ] =  nv04_disp_oclass;
+               device->oclass[NVDEV_ENGINE_PM     ] =  nv40_pm_oclass;
+               break;
+       case 0x68:
+               device->cname = "C68";
+               device->oclass[NVDEV_SUBDEV_VBIOS  ] = &nvkm_bios_oclass;
+               device->oclass[NVDEV_SUBDEV_GPIO   ] =  nv10_gpio_oclass;
+               device->oclass[NVDEV_SUBDEV_I2C    ] =  nv04_i2c_oclass;
+               device->oclass[NVDEV_SUBDEV_CLK    ] = &nv40_clk_oclass;
+               device->oclass[NVDEV_SUBDEV_THERM  ] = &nv40_therm_oclass;
+               device->oclass[NVDEV_SUBDEV_DEVINIT] =  nv1a_devinit_oclass;
+               device->oclass[NVDEV_SUBDEV_MC     ] =  nv4c_mc_oclass;
+               device->oclass[NVDEV_SUBDEV_BUS    ] =  nv31_bus_oclass;
+               device->oclass[NVDEV_SUBDEV_TIMER  ] = &nv04_timer_oclass;
+               device->oclass[NVDEV_SUBDEV_FB     ] =  nv46_fb_oclass;
+               device->oclass[NVDEV_SUBDEV_INSTMEM] =  nv40_instmem_oclass;
+               device->oclass[NVDEV_SUBDEV_MMU    ] = &nv44_mmu_oclass;
+               device->oclass[NVDEV_SUBDEV_VOLT   ] = &nv40_volt_oclass;
+               device->oclass[NVDEV_ENGINE_DMAOBJ ] =  nv04_dmaeng_oclass;
+               device->oclass[NVDEV_ENGINE_FIFO   ] =  nv40_fifo_oclass;
+               device->oclass[NVDEV_ENGINE_SW     ] =  nv10_sw_oclass;
+               device->oclass[NVDEV_ENGINE_GR     ] = &nv40_gr_oclass;
+               device->oclass[NVDEV_ENGINE_MPEG   ] = &nv44_mpeg_oclass;
+               device->oclass[NVDEV_ENGINE_DISP   ] =  nv04_disp_oclass;
+               device->oclass[NVDEV_ENGINE_PM     ] =  nv40_pm_oclass;
+               break;
+       default:
+               nv_fatal(device, "unknown Curie chipset\n");
+               return -EINVAL;
+       }
+
+       return 0;
+}
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/device/nv50.c b/drivers/gpu/drm/nouveau/nvkm/engine/device/nv50.c
new file mode 100644 (file)
index 0000000..249b844
--- /dev/null
@@ -0,0 +1,478 @@
+/*
+ * Copyright 2012 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 "priv.h"
+
+#include <subdev/bios.h>
+#include <subdev/bus.h>
+#include <subdev/gpio.h>
+#include <subdev/i2c.h>
+#include <subdev/fuse.h>
+#include <subdev/clk.h>
+#include <subdev/therm.h>
+#include <subdev/mxm.h>
+#include <subdev/devinit.h>
+#include <subdev/mc.h>
+#include <subdev/timer.h>
+#include <subdev/fb.h>
+#include <subdev/instmem.h>
+#include <subdev/mmu.h>
+#include <subdev/bar.h>
+#include <subdev/pmu.h>
+#include <subdev/volt.h>
+
+#include <engine/dmaobj.h>
+#include <engine/fifo.h>
+#include <engine/sw.h>
+#include <engine/gr.h>
+#include <engine/mpeg.h>
+#include <engine/vp.h>
+#include <engine/cipher.h>
+#include <engine/sec.h>
+#include <engine/bsp.h>
+#include <engine/msvld.h>
+#include <engine/mspdec.h>
+#include <engine/msppp.h>
+#include <engine/ce.h>
+#include <engine/disp.h>
+#include <engine/pm.h>
+
+int
+nv50_identify(struct nvkm_device *device)
+{
+       switch (device->chipset) {
+       case 0x50:
+               device->cname = "G80";
+               device->oclass[NVDEV_SUBDEV_VBIOS  ] = &nvkm_bios_oclass;
+               device->oclass[NVDEV_SUBDEV_GPIO   ] =  nv50_gpio_oclass;
+               device->oclass[NVDEV_SUBDEV_I2C    ] =  nv50_i2c_oclass;
+               device->oclass[NVDEV_SUBDEV_FUSE   ] =  &nv50_fuse_oclass;
+               device->oclass[NVDEV_SUBDEV_CLK    ] =  nv50_clk_oclass;
+               device->oclass[NVDEV_SUBDEV_THERM  ] = &nv50_therm_oclass;
+               device->oclass[NVDEV_SUBDEV_MXM    ] = &nv50_mxm_oclass;
+               device->oclass[NVDEV_SUBDEV_DEVINIT] =  nv50_devinit_oclass;
+               device->oclass[NVDEV_SUBDEV_MC     ] =  nv50_mc_oclass;
+               device->oclass[NVDEV_SUBDEV_BUS    ] =  nv50_bus_oclass;
+               device->oclass[NVDEV_SUBDEV_TIMER  ] = &nv04_timer_oclass;
+               device->oclass[NVDEV_SUBDEV_FB     ] =  nv50_fb_oclass;
+               device->oclass[NVDEV_SUBDEV_INSTMEM] =  nv50_instmem_oclass;
+               device->oclass[NVDEV_SUBDEV_MMU    ] = &nv50_mmu_oclass;
+               device->oclass[NVDEV_SUBDEV_BAR    ] = &nv50_bar_oclass;
+               device->oclass[NVDEV_SUBDEV_VOLT   ] = &nv40_volt_oclass;
+               device->oclass[NVDEV_ENGINE_DMAOBJ ] =  nv50_dmaeng_oclass;
+               device->oclass[NVDEV_ENGINE_FIFO   ] =  nv50_fifo_oclass;
+               device->oclass[NVDEV_ENGINE_SW     ] =  nv50_sw_oclass;
+               device->oclass[NVDEV_ENGINE_GR     ] = &nv50_gr_oclass;
+               device->oclass[NVDEV_ENGINE_MPEG   ] = &nv50_mpeg_oclass;
+               device->oclass[NVDEV_ENGINE_DISP   ] =  nv50_disp_oclass;
+               device->oclass[NVDEV_ENGINE_PM     ] =  nv50_pm_oclass;
+               break;
+       case 0x84:
+               device->cname = "G84";
+               device->oclass[NVDEV_SUBDEV_VBIOS  ] = &nvkm_bios_oclass;
+               device->oclass[NVDEV_SUBDEV_GPIO   ] =  nv50_gpio_oclass;
+               device->oclass[NVDEV_SUBDEV_I2C    ] =  nv50_i2c_oclass;
+               device->oclass[NVDEV_SUBDEV_FUSE   ] =  &nv50_fuse_oclass;
+               device->oclass[NVDEV_SUBDEV_CLK    ] =  g84_clk_oclass;
+               device->oclass[NVDEV_SUBDEV_THERM  ] = &g84_therm_oclass;
+               device->oclass[NVDEV_SUBDEV_MXM    ] = &nv50_mxm_oclass;
+               device->oclass[NVDEV_SUBDEV_DEVINIT] =  g84_devinit_oclass;
+               device->oclass[NVDEV_SUBDEV_MC     ] =  nv50_mc_oclass;
+               device->oclass[NVDEV_SUBDEV_BUS    ] =  nv50_bus_oclass;
+               device->oclass[NVDEV_SUBDEV_TIMER  ] = &nv04_timer_oclass;
+               device->oclass[NVDEV_SUBDEV_FB     ] =  g84_fb_oclass;
+               device->oclass[NVDEV_SUBDEV_INSTMEM] =  nv50_instmem_oclass;
+               device->oclass[NVDEV_SUBDEV_MMU    ] = &nv50_mmu_oclass;
+               device->oclass[NVDEV_SUBDEV_BAR    ] = &nv50_bar_oclass;
+               device->oclass[NVDEV_SUBDEV_VOLT   ] = &nv40_volt_oclass;
+               device->oclass[NVDEV_ENGINE_DMAOBJ ] =  nv50_dmaeng_oclass;
+               device->oclass[NVDEV_ENGINE_FIFO   ] =  g84_fifo_oclass;
+               device->oclass[NVDEV_ENGINE_SW     ] =  nv50_sw_oclass;
+               device->oclass[NVDEV_ENGINE_GR     ] = &nv50_gr_oclass;
+               device->oclass[NVDEV_ENGINE_MPEG   ] = &g84_mpeg_oclass;
+               device->oclass[NVDEV_ENGINE_VP     ] = &g84_vp_oclass;
+               device->oclass[NVDEV_ENGINE_CIPHER ] = &g84_cipher_oclass;
+               device->oclass[NVDEV_ENGINE_BSP    ] = &g84_bsp_oclass;
+               device->oclass[NVDEV_ENGINE_DISP   ] =  g84_disp_oclass;
+               device->oclass[NVDEV_ENGINE_PM     ] =  g84_pm_oclass;
+               break;
+       case 0x86:
+               device->cname = "G86";
+               device->oclass[NVDEV_SUBDEV_VBIOS  ] = &nvkm_bios_oclass;
+               device->oclass[NVDEV_SUBDEV_GPIO   ] =  nv50_gpio_oclass;
+               device->oclass[NVDEV_SUBDEV_I2C    ] =  nv50_i2c_oclass;
+               device->oclass[NVDEV_SUBDEV_FUSE   ] =  &nv50_fuse_oclass;
+               device->oclass[NVDEV_SUBDEV_CLK    ] =  g84_clk_oclass;
+               device->oclass[NVDEV_SUBDEV_THERM  ] = &g84_therm_oclass;
+               device->oclass[NVDEV_SUBDEV_MXM    ] = &nv50_mxm_oclass;
+               device->oclass[NVDEV_SUBDEV_DEVINIT] =  g84_devinit_oclass;
+               device->oclass[NVDEV_SUBDEV_MC     ] =  nv50_mc_oclass;
+               device->oclass[NVDEV_SUBDEV_BUS    ] =  nv50_bus_oclass;
+               device->oclass[NVDEV_SUBDEV_TIMER  ] = &nv04_timer_oclass;
+               device->oclass[NVDEV_SUBDEV_FB     ] =  g84_fb_oclass;
+               device->oclass[NVDEV_SUBDEV_INSTMEM] =  nv50_instmem_oclass;
+               device->oclass[NVDEV_SUBDEV_MMU    ] = &nv50_mmu_oclass;
+               device->oclass[NVDEV_SUBDEV_BAR    ] = &nv50_bar_oclass;
+               device->oclass[NVDEV_SUBDEV_VOLT   ] = &nv40_volt_oclass;
+               device->oclass[NVDEV_ENGINE_DMAOBJ ] =  nv50_dmaeng_oclass;
+               device->oclass[NVDEV_ENGINE_FIFO   ] =  g84_fifo_oclass;
+               device->oclass[NVDEV_ENGINE_SW     ] =  nv50_sw_oclass;
+               device->oclass[NVDEV_ENGINE_GR     ] = &nv50_gr_oclass;
+               device->oclass[NVDEV_ENGINE_MPEG   ] = &g84_mpeg_oclass;
+               device->oclass[NVDEV_ENGINE_VP     ] = &g84_vp_oclass;
+               device->oclass[NVDEV_ENGINE_CIPHER ] = &g84_cipher_oclass;
+               device->oclass[NVDEV_ENGINE_BSP    ] = &g84_bsp_oclass;
+               device->oclass[NVDEV_ENGINE_DISP   ] =  g84_disp_oclass;
+               device->oclass[NVDEV_ENGINE_PM     ] =  g84_pm_oclass;
+               break;
+       case 0x92:
+               device->cname = "G92";
+               device->oclass[NVDEV_SUBDEV_VBIOS  ] = &nvkm_bios_oclass;
+               device->oclass[NVDEV_SUBDEV_GPIO   ] =  nv50_gpio_oclass;
+               device->oclass[NVDEV_SUBDEV_I2C    ] =  nv50_i2c_oclass;
+               device->oclass[NVDEV_SUBDEV_FUSE   ] =  &nv50_fuse_oclass;
+               device->oclass[NVDEV_SUBDEV_CLK    ] =  g84_clk_oclass;
+               device->oclass[NVDEV_SUBDEV_THERM  ] = &g84_therm_oclass;
+               device->oclass[NVDEV_SUBDEV_MXM    ] = &nv50_mxm_oclass;
+               device->oclass[NVDEV_SUBDEV_DEVINIT] =  g84_devinit_oclass;
+               device->oclass[NVDEV_SUBDEV_MC     ] =  nv50_mc_oclass;
+               device->oclass[NVDEV_SUBDEV_BUS    ] =  nv50_bus_oclass;
+               device->oclass[NVDEV_SUBDEV_TIMER  ] = &nv04_timer_oclass;
+               device->oclass[NVDEV_SUBDEV_FB     ] =  g84_fb_oclass;
+               device->oclass[NVDEV_SUBDEV_INSTMEM] =  nv50_instmem_oclass;
+               device->oclass[NVDEV_SUBDEV_MMU    ] = &nv50_mmu_oclass;
+               device->oclass[NVDEV_SUBDEV_BAR    ] = &nv50_bar_oclass;
+               device->oclass[NVDEV_SUBDEV_VOLT   ] = &nv40_volt_oclass;
+               device->oclass[NVDEV_ENGINE_DMAOBJ ] =  nv50_dmaeng_oclass;
+               device->oclass[NVDEV_ENGINE_FIFO   ] =  g84_fifo_oclass;
+               device->oclass[NVDEV_ENGINE_SW     ] =  nv50_sw_oclass;
+               device->oclass[NVDEV_ENGINE_GR     ] = &nv50_gr_oclass;
+               device->oclass[NVDEV_ENGINE_MPEG   ] = &g84_mpeg_oclass;
+               device->oclass[NVDEV_ENGINE_VP     ] = &g84_vp_oclass;
+               device->oclass[NVDEV_ENGINE_CIPHER ] = &g84_cipher_oclass;
+               device->oclass[NVDEV_ENGINE_BSP    ] = &g84_bsp_oclass;
+               device->oclass[NVDEV_ENGINE_DISP   ] =  g84_disp_oclass;
+               device->oclass[NVDEV_ENGINE_PM     ] =  g84_pm_oclass;
+               break;
+       case 0x94:
+               device->cname = "G94";
+               device->oclass[NVDEV_SUBDEV_VBIOS  ] = &nvkm_bios_oclass;
+               device->oclass[NVDEV_SUBDEV_GPIO   ] =  g94_gpio_oclass;
+               device->oclass[NVDEV_SUBDEV_I2C    ] =  g94_i2c_oclass;
+               device->oclass[NVDEV_SUBDEV_FUSE   ] =  &nv50_fuse_oclass;
+               device->oclass[NVDEV_SUBDEV_CLK    ] =  g84_clk_oclass;
+               device->oclass[NVDEV_SUBDEV_THERM  ] = &g84_therm_oclass;
+               device->oclass[NVDEV_SUBDEV_MXM    ] = &nv50_mxm_oclass;
+               device->oclass[NVDEV_SUBDEV_DEVINIT] =  g84_devinit_oclass;
+               device->oclass[NVDEV_SUBDEV_MC     ] =  g94_mc_oclass;
+               device->oclass[NVDEV_SUBDEV_BUS    ] =  g94_bus_oclass;
+               device->oclass[NVDEV_SUBDEV_TIMER  ] = &nv04_timer_oclass;
+               device->oclass[NVDEV_SUBDEV_FB     ] =  g84_fb_oclass;
+               device->oclass[NVDEV_SUBDEV_INSTMEM] =  nv50_instmem_oclass;
+               device->oclass[NVDEV_SUBDEV_MMU    ] = &nv50_mmu_oclass;
+               device->oclass[NVDEV_SUBDEV_BAR    ] = &nv50_bar_oclass;
+               device->oclass[NVDEV_SUBDEV_VOLT   ] = &nv40_volt_oclass;
+               device->oclass[NVDEV_ENGINE_DMAOBJ ] =  nv50_dmaeng_oclass;
+               device->oclass[NVDEV_ENGINE_FIFO   ] =  g84_fifo_oclass;
+               device->oclass[NVDEV_ENGINE_SW     ] =  nv50_sw_oclass;
+               device->oclass[NVDEV_ENGINE_GR     ] = &nv50_gr_oclass;
+               device->oclass[NVDEV_ENGINE_MPEG   ] = &g84_mpeg_oclass;
+               device->oclass[NVDEV_ENGINE_VP     ] = &g84_vp_oclass;
+               device->oclass[NVDEV_ENGINE_CIPHER ] = &g84_cipher_oclass;
+               device->oclass[NVDEV_ENGINE_BSP    ] = &g84_bsp_oclass;
+               device->oclass[NVDEV_ENGINE_DISP   ] =  g94_disp_oclass;
+               device->oclass[NVDEV_ENGINE_PM     ] =  g84_pm_oclass;
+               break;
+       case 0x96:
+               device->cname = "G96";
+               device->oclass[NVDEV_SUBDEV_VBIOS  ] = &nvkm_bios_oclass;
+               device->oclass[NVDEV_SUBDEV_GPIO   ] =  g94_gpio_oclass;
+               device->oclass[NVDEV_SUBDEV_I2C    ] =  g94_i2c_oclass;
+               device->oclass[NVDEV_SUBDEV_FUSE   ] =  &nv50_fuse_oclass;
+               device->oclass[NVDEV_SUBDEV_CLK    ] =  g84_clk_oclass;
+               device->oclass[NVDEV_SUBDEV_THERM  ] = &g84_therm_oclass;
+               device->oclass[NVDEV_SUBDEV_MXM    ] = &nv50_mxm_oclass;
+               device->oclass[NVDEV_SUBDEV_DEVINIT] =  g84_devinit_oclass;
+               device->oclass[NVDEV_SUBDEV_MC     ] =  g94_mc_oclass;
+               device->oclass[NVDEV_SUBDEV_BUS    ] =  g94_bus_oclass;
+               device->oclass[NVDEV_SUBDEV_TIMER  ] = &nv04_timer_oclass;
+               device->oclass[NVDEV_SUBDEV_FB     ] =  g84_fb_oclass;
+               device->oclass[NVDEV_SUBDEV_INSTMEM] =  nv50_instmem_oclass;
+               device->oclass[NVDEV_SUBDEV_MMU    ] = &nv50_mmu_oclass;
+               device->oclass[NVDEV_SUBDEV_BAR    ] = &nv50_bar_oclass;
+               device->oclass[NVDEV_SUBDEV_VOLT   ] = &nv40_volt_oclass;
+               device->oclass[NVDEV_ENGINE_DMAOBJ ] =  nv50_dmaeng_oclass;
+               device->oclass[NVDEV_ENGINE_FIFO   ] =  g84_fifo_oclass;
+               device->oclass[NVDEV_ENGINE_SW     ] =  nv50_sw_oclass;
+               device->oclass[NVDEV_ENGINE_GR     ] = &nv50_gr_oclass;
+               device->oclass[NVDEV_ENGINE_MPEG   ] = &g84_mpeg_oclass;
+               device->oclass[NVDEV_ENGINE_VP     ] = &g84_vp_oclass;
+               device->oclass[NVDEV_ENGINE_CIPHER ] = &g84_cipher_oclass;
+               device->oclass[NVDEV_ENGINE_BSP    ] = &g84_bsp_oclass;
+               device->oclass[NVDEV_ENGINE_DISP   ] =  g94_disp_oclass;
+               device->oclass[NVDEV_ENGINE_PM     ] =  g84_pm_oclass;
+               break;
+       case 0x98:
+               device->cname = "G98";
+               device->oclass[NVDEV_SUBDEV_VBIOS  ] = &nvkm_bios_oclass;
+               device->oclass[NVDEV_SUBDEV_GPIO   ] =  g94_gpio_oclass;
+               device->oclass[NVDEV_SUBDEV_I2C    ] =  g94_i2c_oclass;
+               device->oclass[NVDEV_SUBDEV_FUSE   ] =  &nv50_fuse_oclass;
+               device->oclass[NVDEV_SUBDEV_CLK    ] =  g84_clk_oclass;
+               device->oclass[NVDEV_SUBDEV_THERM  ] = &g84_therm_oclass;
+               device->oclass[NVDEV_SUBDEV_MXM    ] = &nv50_mxm_oclass;
+               device->oclass[NVDEV_SUBDEV_DEVINIT] =  g98_devinit_oclass;
+               device->oclass[NVDEV_SUBDEV_MC     ] =  g98_mc_oclass;
+               device->oclass[NVDEV_SUBDEV_BUS    ] =  g94_bus_oclass;
+               device->oclass[NVDEV_SUBDEV_TIMER  ] = &nv04_timer_oclass;
+               device->oclass[NVDEV_SUBDEV_FB     ] =  g84_fb_oclass;
+               device->oclass[NVDEV_SUBDEV_INSTMEM] =  nv50_instmem_oclass;
+               device->oclass[NVDEV_SUBDEV_MMU    ] = &nv50_mmu_oclass;
+               device->oclass[NVDEV_SUBDEV_BAR    ] = &nv50_bar_oclass;
+               device->oclass[NVDEV_SUBDEV_VOLT   ] = &nv40_volt_oclass;
+               device->oclass[NVDEV_ENGINE_DMAOBJ ] =  nv50_dmaeng_oclass;
+               device->oclass[NVDEV_ENGINE_FIFO   ] =  g84_fifo_oclass;
+               device->oclass[NVDEV_ENGINE_SW     ] =  nv50_sw_oclass;
+               device->oclass[NVDEV_ENGINE_GR     ] = &nv50_gr_oclass;
+               device->oclass[NVDEV_ENGINE_MSPDEC ] = &g98_mspdec_oclass;
+               device->oclass[NVDEV_ENGINE_SEC    ] = &g98_sec_oclass;
+               device->oclass[NVDEV_ENGINE_MSVLD  ] = &g98_msvld_oclass;
+               device->oclass[NVDEV_ENGINE_MSPPP  ] = &g98_msppp_oclass;
+               device->oclass[NVDEV_ENGINE_DISP   ] =  g94_disp_oclass;
+               device->oclass[NVDEV_ENGINE_PM     ] =  g84_pm_oclass;
+               break;
+       case 0xa0:
+               device->cname = "G200";
+               device->oclass[NVDEV_SUBDEV_VBIOS  ] = &nvkm_bios_oclass;
+               device->oclass[NVDEV_SUBDEV_GPIO   ] =  g94_gpio_oclass;
+               device->oclass[NVDEV_SUBDEV_I2C    ] =  nv50_i2c_oclass;
+               device->oclass[NVDEV_SUBDEV_FUSE   ] =  &nv50_fuse_oclass;
+               device->oclass[NVDEV_SUBDEV_CLK    ] =  g84_clk_oclass;
+               device->oclass[NVDEV_SUBDEV_THERM  ] = &g84_therm_oclass;
+               device->oclass[NVDEV_SUBDEV_MXM    ] = &nv50_mxm_oclass;
+               device->oclass[NVDEV_SUBDEV_DEVINIT] =  g84_devinit_oclass;
+               device->oclass[NVDEV_SUBDEV_MC     ] =  g98_mc_oclass;
+               device->oclass[NVDEV_SUBDEV_BUS    ] =  g94_bus_oclass;
+               device->oclass[NVDEV_SUBDEV_TIMER  ] = &nv04_timer_oclass;
+               device->oclass[NVDEV_SUBDEV_FB     ] =  g84_fb_oclass;
+               device->oclass[NVDEV_SUBDEV_INSTMEM] =  nv50_instmem_oclass;
+               device->oclass[NVDEV_SUBDEV_MMU    ] = &nv50_mmu_oclass;
+               device->oclass[NVDEV_SUBDEV_BAR    ] = &nv50_bar_oclass;
+               device->oclass[NVDEV_SUBDEV_VOLT   ] = &nv40_volt_oclass;
+               device->oclass[NVDEV_ENGINE_DMAOBJ ] =  nv50_dmaeng_oclass;
+               device->oclass[NVDEV_ENGINE_FIFO   ] =  g84_fifo_oclass;
+               device->oclass[NVDEV_ENGINE_SW     ] =  nv50_sw_oclass;
+               device->oclass[NVDEV_ENGINE_GR     ] = &nv50_gr_oclass;
+               device->oclass[NVDEV_ENGINE_MPEG   ] = &g84_mpeg_oclass;
+               device->oclass[NVDEV_ENGINE_VP     ] = &g84_vp_oclass;
+               device->oclass[NVDEV_ENGINE_CIPHER ] = &g84_cipher_oclass;
+               device->oclass[NVDEV_ENGINE_BSP    ] = &g84_bsp_oclass;
+               device->oclass[NVDEV_ENGINE_DISP   ] =  gt200_disp_oclass;
+               device->oclass[NVDEV_ENGINE_PM     ] =  g84_pm_oclass;
+               break;
+       case 0xaa:
+               device->cname = "MCP77/MCP78";
+               device->oclass[NVDEV_SUBDEV_VBIOS  ] = &nvkm_bios_oclass;
+               device->oclass[NVDEV_SUBDEV_GPIO   ] =  g94_gpio_oclass;
+               device->oclass[NVDEV_SUBDEV_I2C    ] =  g94_i2c_oclass;
+               device->oclass[NVDEV_SUBDEV_FUSE   ] =  &nv50_fuse_oclass;
+               device->oclass[NVDEV_SUBDEV_CLK    ] =  mcp77_clk_oclass;
+               device->oclass[NVDEV_SUBDEV_THERM  ] = &g84_therm_oclass;
+               device->oclass[NVDEV_SUBDEV_MXM    ] = &nv50_mxm_oclass;
+               device->oclass[NVDEV_SUBDEV_DEVINIT] =  g98_devinit_oclass;
+               device->oclass[NVDEV_SUBDEV_MC     ] =  g98_mc_oclass;
+               device->oclass[NVDEV_SUBDEV_BUS    ] =  g94_bus_oclass;
+               device->oclass[NVDEV_SUBDEV_TIMER  ] = &nv04_timer_oclass;
+               device->oclass[NVDEV_SUBDEV_FB     ] =  mcp77_fb_oclass;
+               device->oclass[NVDEV_SUBDEV_INSTMEM] =  nv50_instmem_oclass;
+               device->oclass[NVDEV_SUBDEV_MMU    ] = &nv50_mmu_oclass;
+               device->oclass[NVDEV_SUBDEV_BAR    ] = &nv50_bar_oclass;
+               device->oclass[NVDEV_SUBDEV_VOLT   ] = &nv40_volt_oclass;
+               device->oclass[NVDEV_ENGINE_DMAOBJ ] =  nv50_dmaeng_oclass;
+               device->oclass[NVDEV_ENGINE_FIFO   ] =  g84_fifo_oclass;
+               device->oclass[NVDEV_ENGINE_SW     ] =  nv50_sw_oclass;
+               device->oclass[NVDEV_ENGINE_GR     ] = &nv50_gr_oclass;
+               device->oclass[NVDEV_ENGINE_MSPDEC ] = &g98_mspdec_oclass;
+               device->oclass[NVDEV_ENGINE_SEC    ] = &g98_sec_oclass;
+               device->oclass[NVDEV_ENGINE_MSVLD  ] = &g98_msvld_oclass;
+               device->oclass[NVDEV_ENGINE_MSPPP  ] = &g98_msppp_oclass;
+               device->oclass[NVDEV_ENGINE_DISP   ] =  g94_disp_oclass;
+               device->oclass[NVDEV_ENGINE_PM     ] =  g84_pm_oclass;
+               break;
+       case 0xac:
+               device->cname = "MCP79/MCP7A";
+               device->oclass[NVDEV_SUBDEV_VBIOS  ] = &nvkm_bios_oclass;
+               device->oclass[NVDEV_SUBDEV_GPIO   ] =  g94_gpio_oclass;
+               device->oclass[NVDEV_SUBDEV_I2C    ] =  g94_i2c_oclass;
+               device->oclass[NVDEV_SUBDEV_FUSE   ] =  &nv50_fuse_oclass;
+               device->oclass[NVDEV_SUBDEV_CLK    ] =  mcp77_clk_oclass;
+               device->oclass[NVDEV_SUBDEV_THERM  ] = &g84_therm_oclass;
+               device->oclass[NVDEV_SUBDEV_MXM    ] = &nv50_mxm_oclass;
+               device->oclass[NVDEV_SUBDEV_DEVINIT] =  g98_devinit_oclass;
+               device->oclass[NVDEV_SUBDEV_MC     ] =  g98_mc_oclass;
+               device->oclass[NVDEV_SUBDEV_BUS    ] =  g94_bus_oclass;
+               device->oclass[NVDEV_SUBDEV_TIMER  ] = &nv04_timer_oclass;
+               device->oclass[NVDEV_SUBDEV_FB     ] =  mcp77_fb_oclass;
+               device->oclass[NVDEV_SUBDEV_INSTMEM] =  nv50_instmem_oclass;
+               device->oclass[NVDEV_SUBDEV_MMU    ] = &nv50_mmu_oclass;
+               device->oclass[NVDEV_SUBDEV_BAR    ] = &nv50_bar_oclass;
+               device->oclass[NVDEV_SUBDEV_VOLT   ] = &nv40_volt_oclass;
+               device->oclass[NVDEV_ENGINE_DMAOBJ ] =  nv50_dmaeng_oclass;
+               device->oclass[NVDEV_ENGINE_FIFO   ] =  g84_fifo_oclass;
+               device->oclass[NVDEV_ENGINE_SW     ] =  nv50_sw_oclass;
+               device->oclass[NVDEV_ENGINE_GR     ] = &nv50_gr_oclass;
+               device->oclass[NVDEV_ENGINE_MSPDEC ] = &g98_mspdec_oclass;
+               device->oclass[NVDEV_ENGINE_SEC    ] = &g98_sec_oclass;
+               device->oclass[NVDEV_ENGINE_MSVLD  ] = &g98_msvld_oclass;
+               device->oclass[NVDEV_ENGINE_MSPPP  ] = &g98_msppp_oclass;
+               device->oclass[NVDEV_ENGINE_DISP   ] =  g94_disp_oclass;
+               device->oclass[NVDEV_ENGINE_PM     ] =  g84_pm_oclass;
+               break;
+       case 0xa3:
+               device->cname = "GT215";
+               device->oclass[NVDEV_SUBDEV_VBIOS  ] = &nvkm_bios_oclass;
+               device->oclass[NVDEV_SUBDEV_GPIO   ] =  g94_gpio_oclass;
+               device->oclass[NVDEV_SUBDEV_I2C    ] =  g94_i2c_oclass;
+               device->oclass[NVDEV_SUBDEV_FUSE   ] =  &nv50_fuse_oclass;
+               device->oclass[NVDEV_SUBDEV_CLK    ] = &gt215_clk_oclass;
+               device->oclass[NVDEV_SUBDEV_THERM  ] = &gt215_therm_oclass;
+               device->oclass[NVDEV_SUBDEV_MXM    ] = &nv50_mxm_oclass;
+               device->oclass[NVDEV_SUBDEV_DEVINIT] =  gt215_devinit_oclass;
+               device->oclass[NVDEV_SUBDEV_MC     ] =  g98_mc_oclass;
+               device->oclass[NVDEV_SUBDEV_BUS    ] =  g94_bus_oclass;
+               device->oclass[NVDEV_SUBDEV_TIMER  ] = &nv04_timer_oclass;
+               device->oclass[NVDEV_SUBDEV_FB     ] =  gt215_fb_oclass;
+               device->oclass[NVDEV_SUBDEV_INSTMEM] =  nv50_instmem_oclass;
+               device->oclass[NVDEV_SUBDEV_MMU    ] = &nv50_mmu_oclass;
+               device->oclass[NVDEV_SUBDEV_BAR    ] = &nv50_bar_oclass;
+               device->oclass[NVDEV_SUBDEV_PMU    ] =  gt215_pmu_oclass;
+               device->oclass[NVDEV_SUBDEV_VOLT   ] = &nv40_volt_oclass;
+               device->oclass[NVDEV_ENGINE_DMAOBJ ] =  nv50_dmaeng_oclass;
+               device->oclass[NVDEV_ENGINE_FIFO   ] =  g84_fifo_oclass;
+               device->oclass[NVDEV_ENGINE_SW     ] =  nv50_sw_oclass;
+               device->oclass[NVDEV_ENGINE_GR     ] = &nv50_gr_oclass;
+               device->oclass[NVDEV_ENGINE_MPEG   ] = &g84_mpeg_oclass;
+               device->oclass[NVDEV_ENGINE_MSPDEC ] = &g98_mspdec_oclass;
+               device->oclass[NVDEV_ENGINE_MSVLD  ] = &g98_msvld_oclass;
+               device->oclass[NVDEV_ENGINE_MSPPP  ] = &g98_msppp_oclass;
+               device->oclass[NVDEV_ENGINE_CE0    ] = &gt215_ce_oclass;
+               device->oclass[NVDEV_ENGINE_DISP   ] =  gt215_disp_oclass;
+               device->oclass[NVDEV_ENGINE_PM     ] =  gt215_pm_oclass;
+               break;
+       case 0xa5:
+               device->cname = "GT216";
+               device->oclass[NVDEV_SUBDEV_VBIOS  ] = &nvkm_bios_oclass;
+               device->oclass[NVDEV_SUBDEV_GPIO   ] =  g94_gpio_oclass;
+               device->oclass[NVDEV_SUBDEV_I2C    ] =  g94_i2c_oclass;
+               device->oclass[NVDEV_SUBDEV_FUSE   ] =  &nv50_fuse_oclass;
+               device->oclass[NVDEV_SUBDEV_CLK    ] = &gt215_clk_oclass;
+               device->oclass[NVDEV_SUBDEV_THERM  ] = &gt215_therm_oclass;
+               device->oclass[NVDEV_SUBDEV_MXM    ] = &nv50_mxm_oclass;
+               device->oclass[NVDEV_SUBDEV_DEVINIT] =  gt215_devinit_oclass;
+               device->oclass[NVDEV_SUBDEV_MC     ] =  g98_mc_oclass;
+               device->oclass[NVDEV_SUBDEV_BUS    ] =  g94_bus_oclass;
+               device->oclass[NVDEV_SUBDEV_TIMER  ] = &nv04_timer_oclass;
+               device->oclass[NVDEV_SUBDEV_FB     ] =  gt215_fb_oclass;
+               device->oclass[NVDEV_SUBDEV_INSTMEM] =  nv50_instmem_oclass;
+               device->oclass[NVDEV_SUBDEV_MMU    ] = &nv50_mmu_oclass;
+               device->oclass[NVDEV_SUBDEV_BAR    ] = &nv50_bar_oclass;
+               device->oclass[NVDEV_SUBDEV_PMU    ] =  gt215_pmu_oclass;
+               device->oclass[NVDEV_SUBDEV_VOLT   ] = &nv40_volt_oclass;
+               device->oclass[NVDEV_ENGINE_DMAOBJ ] =  nv50_dmaeng_oclass;
+               device->oclass[NVDEV_ENGINE_FIFO   ] =  g84_fifo_oclass;
+               device->oclass[NVDEV_ENGINE_SW     ] =  nv50_sw_oclass;
+               device->oclass[NVDEV_ENGINE_GR     ] = &nv50_gr_oclass;
+               device->oclass[NVDEV_ENGINE_MSPDEC ] = &g98_mspdec_oclass;
+               device->oclass[NVDEV_ENGINE_MSVLD  ] = &g98_msvld_oclass;
+               device->oclass[NVDEV_ENGINE_MSPPP  ] = &g98_msppp_oclass;
+               device->oclass[NVDEV_ENGINE_CE0    ] = &gt215_ce_oclass;
+               device->oclass[NVDEV_ENGINE_DISP   ] =  gt215_disp_oclass;
+               device->oclass[NVDEV_ENGINE_PM     ] =  gt215_pm_oclass;
+               break;
+       case 0xa8:
+               device->cname = "GT218";
+               device->oclass[NVDEV_SUBDEV_VBIOS  ] = &nvkm_bios_oclass;
+               device->oclass[NVDEV_SUBDEV_GPIO   ] =  g94_gpio_oclass;
+               device->oclass[NVDEV_SUBDEV_I2C    ] =  g94_i2c_oclass;
+               device->oclass[NVDEV_SUBDEV_FUSE   ] =  &nv50_fuse_oclass;
+               device->oclass[NVDEV_SUBDEV_CLK    ] = &gt215_clk_oclass;
+               device->oclass[NVDEV_SUBDEV_THERM  ] = &gt215_therm_oclass;
+               device->oclass[NVDEV_SUBDEV_MXM    ] = &nv50_mxm_oclass;
+               device->oclass[NVDEV_SUBDEV_DEVINIT] =  gt215_devinit_oclass;
+               device->oclass[NVDEV_SUBDEV_MC     ] =  g98_mc_oclass;
+               device->oclass[NVDEV_SUBDEV_BUS    ] =  g94_bus_oclass;
+               device->oclass[NVDEV_SUBDEV_TIMER  ] = &nv04_timer_oclass;
+               device->oclass[NVDEV_SUBDEV_FB     ] =  gt215_fb_oclass;
+               device->oclass[NVDEV_SUBDEV_INSTMEM] =  nv50_instmem_oclass;
+               device->oclass[NVDEV_SUBDEV_MMU    ] = &nv50_mmu_oclass;
+               device->oclass[NVDEV_SUBDEV_BAR    ] = &nv50_bar_oclass;
+               device->oclass[NVDEV_SUBDEV_PMU    ] =  gt215_pmu_oclass;
+               device->oclass[NVDEV_SUBDEV_VOLT   ] = &nv40_volt_oclass;
+               device->oclass[NVDEV_ENGINE_DMAOBJ ] =  nv50_dmaeng_oclass;
+               device->oclass[NVDEV_ENGINE_FIFO   ] =  g84_fifo_oclass;
+               device->oclass[NVDEV_ENGINE_SW     ] =  nv50_sw_oclass;
+               device->oclass[NVDEV_ENGINE_GR     ] = &nv50_gr_oclass;
+               device->oclass[NVDEV_ENGINE_MSPDEC ] = &g98_mspdec_oclass;
+               device->oclass[NVDEV_ENGINE_MSVLD  ] = &g98_msvld_oclass;
+               device->oclass[NVDEV_ENGINE_MSPPP  ] = &g98_msppp_oclass;
+               device->oclass[NVDEV_ENGINE_CE0    ] = &gt215_ce_oclass;
+               device->oclass[NVDEV_ENGINE_DISP   ] =  gt215_disp_oclass;
+               device->oclass[NVDEV_ENGINE_PM     ] =  gt215_pm_oclass;
+               break;
+       case 0xaf:
+               device->cname = "MCP89";
+               device->oclass[NVDEV_SUBDEV_VBIOS  ] = &nvkm_bios_oclass;
+               device->oclass[NVDEV_SUBDEV_GPIO   ] =  g94_gpio_oclass;
+               device->oclass[NVDEV_SUBDEV_I2C    ] =  g94_i2c_oclass;
+               device->oclass[NVDEV_SUBDEV_FUSE   ] =  &nv50_fuse_oclass;
+               device->oclass[NVDEV_SUBDEV_CLK    ] = &gt215_clk_oclass;
+               device->oclass[NVDEV_SUBDEV_THERM  ] = &gt215_therm_oclass;
+               device->oclass[NVDEV_SUBDEV_MXM    ] = &nv50_mxm_oclass;
+               device->oclass[NVDEV_SUBDEV_DEVINIT] =  mcp89_devinit_oclass;
+               device->oclass[NVDEV_SUBDEV_MC     ] =  g98_mc_oclass;
+               device->oclass[NVDEV_SUBDEV_BUS    ] =  g94_bus_oclass;
+               device->oclass[NVDEV_SUBDEV_TIMER  ] = &nv04_timer_oclass;
+               device->oclass[NVDEV_SUBDEV_FB     ] =  mcp89_fb_oclass;
+               device->oclass[NVDEV_SUBDEV_INSTMEM] =  nv50_instmem_oclass;
+               device->oclass[NVDEV_SUBDEV_MMU    ] = &nv50_mmu_oclass;
+               device->oclass[NVDEV_SUBDEV_BAR    ] = &nv50_bar_oclass;
+               device->oclass[NVDEV_SUBDEV_PMU    ] =  gt215_pmu_oclass;
+               device->oclass[NVDEV_SUBDEV_VOLT   ] = &nv40_volt_oclass;
+               device->oclass[NVDEV_ENGINE_DMAOBJ ] =  nv50_dmaeng_oclass;
+               device->oclass[NVDEV_ENGINE_FIFO   ] =  g84_fifo_oclass;
+               device->oclass[NVDEV_ENGINE_SW     ] =  nv50_sw_oclass;
+               device->oclass[NVDEV_ENGINE_GR     ] = &nv50_gr_oclass;
+               device->oclass[NVDEV_ENGINE_MSPDEC ] = &g98_mspdec_oclass;
+               device->oclass[NVDEV_ENGINE_MSVLD  ] = &g98_msvld_oclass;
+               device->oclass[NVDEV_ENGINE_MSPPP  ] = &g98_msppp_oclass;
+               device->oclass[NVDEV_ENGINE_CE0    ] = &gt215_ce_oclass;
+               device->oclass[NVDEV_ENGINE_DISP   ] =  gt215_disp_oclass;
+               device->oclass[NVDEV_ENGINE_PM     ] =  gt215_pm_oclass;
+               break;
+       default:
+               nv_fatal(device, "unknown Tesla chipset\n");
+               return -EINVAL;
+       }
+
+       return 0;
+}
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/device/priv.h b/drivers/gpu/drm/nouveau/nvkm/engine/device/priv.h
new file mode 100644 (file)
index 0000000..8d3590e
--- /dev/null
@@ -0,0 +1,16 @@
+#ifndef __NVKM_DEVICE_PRIV_H__
+#define __NVKM_DEVICE_PRIV_H__
+#include <core/device.h>
+
+extern struct nvkm_oclass nvkm_control_oclass[];
+
+int nv04_identify(struct nvkm_device *);
+int nv10_identify(struct nvkm_device *);
+int nv20_identify(struct nvkm_device *);
+int nv30_identify(struct nvkm_device *);
+int nv40_identify(struct nvkm_device *);
+int nv50_identify(struct nvkm_device *);
+int gf100_identify(struct nvkm_device *);
+int gk104_identify(struct nvkm_device *);
+int gm100_identify(struct nvkm_device *);
+#endif
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/disp/Kbuild b/drivers/gpu/drm/nouveau/nvkm/engine/disp/Kbuild
new file mode 100644 (file)
index 0000000..16a4e2a
--- /dev/null
@@ -0,0 +1,29 @@
+nvkm-y += nvkm/engine/disp/base.o
+nvkm-y += nvkm/engine/disp/conn.o
+nvkm-y += nvkm/engine/disp/outp.o
+nvkm-y += nvkm/engine/disp/outpdp.o
+nvkm-y += nvkm/engine/disp/nv04.o
+nvkm-y += nvkm/engine/disp/nv50.o
+nvkm-y += nvkm/engine/disp/g84.o
+nvkm-y += nvkm/engine/disp/g94.o
+nvkm-y += nvkm/engine/disp/gt200.o
+nvkm-y += nvkm/engine/disp/gt215.o
+nvkm-y += nvkm/engine/disp/gf110.o
+nvkm-y += nvkm/engine/disp/gk104.o
+nvkm-y += nvkm/engine/disp/gk110.o
+nvkm-y += nvkm/engine/disp/gm107.o
+nvkm-y += nvkm/engine/disp/gm204.o
+nvkm-y += nvkm/engine/disp/dacnv50.o
+nvkm-y += nvkm/engine/disp/dport.o
+nvkm-y += nvkm/engine/disp/hdagt215.o
+nvkm-y += nvkm/engine/disp/hdagf110.o
+nvkm-y += nvkm/engine/disp/hdmig84.o
+nvkm-y += nvkm/engine/disp/hdmigt215.o
+nvkm-y += nvkm/engine/disp/hdmigf110.o
+nvkm-y += nvkm/engine/disp/hdmigk104.o
+nvkm-y += nvkm/engine/disp/piornv50.o
+nvkm-y += nvkm/engine/disp/sornv50.o
+nvkm-y += nvkm/engine/disp/sorg94.o
+nvkm-y += nvkm/engine/disp/sorgf110.o
+nvkm-y += nvkm/engine/disp/sorgm204.o
+nvkm-y += nvkm/engine/disp/vga.o
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/disp/base.c b/drivers/gpu/drm/nouveau/nvkm/engine/disp/base.c
new file mode 100644 (file)
index 0000000..23d1b5c
--- /dev/null
@@ -0,0 +1,240 @@
+/*
+ * Copyright 2013 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 "priv.h"
+#include "conn.h"
+#include "outp.h"
+
+#include <core/notify.h>
+#include <subdev/bios.h>
+#include <subdev/bios/dcb.h>
+
+#include <nvif/class.h>
+#include <nvif/event.h>
+#include <nvif/unpack.h>
+
+int
+nvkm_disp_vblank_ctor(struct nvkm_object *object, void *data, u32 size,
+                     struct nvkm_notify *notify)
+{
+       struct nvkm_disp *disp =
+               container_of(notify->event, typeof(*disp), vblank);
+       union {
+               struct nvif_notify_head_req_v0 v0;
+       } *req = data;
+       int ret;
+
+       if (nvif_unpack(req->v0, 0, 0, false)) {
+               notify->size = sizeof(struct nvif_notify_head_rep_v0);
+               if (ret = -ENXIO, req->v0.head <= disp->vblank.index_nr) {
+                       notify->types = 1;
+                       notify->index = req->v0.head;
+                       return 0;
+               }
+       }
+
+       return ret;
+}
+
+void
+nvkm_disp_vblank(struct nvkm_disp *disp, int head)
+{
+       struct nvif_notify_head_rep_v0 rep = {};
+       nvkm_event_send(&disp->vblank, 1, head, &rep, sizeof(rep));
+}
+
+static int
+nvkm_disp_hpd_ctor(struct nvkm_object *object, void *data, u32 size,
+                  struct nvkm_notify *notify)
+{
+       struct nvkm_disp *disp =
+               container_of(notify->event, typeof(*disp), hpd);
+       union {
+               struct nvif_notify_conn_req_v0 v0;
+       } *req = data;
+       struct nvkm_output *outp;
+       int ret;
+
+       if (nvif_unpack(req->v0, 0, 0, false)) {
+               notify->size = sizeof(struct nvif_notify_conn_rep_v0);
+               list_for_each_entry(outp, &disp->outp, head) {
+                       if (ret = -ENXIO, outp->conn->index == req->v0.conn) {
+                               if (ret = -ENODEV, outp->conn->hpd.event) {
+                                       notify->types = req->v0.mask;
+                                       notify->index = req->v0.conn;
+                                       ret = 0;
+                               }
+                               break;
+                       }
+               }
+       }
+
+       return ret;
+}
+
+static const struct nvkm_event_func
+nvkm_disp_hpd_func = {
+       .ctor = nvkm_disp_hpd_ctor
+};
+
+int
+nvkm_disp_ntfy(struct nvkm_object *object, u32 type, struct nvkm_event **event)
+{
+       struct nvkm_disp *disp = (void *)object->engine;
+       switch (type) {
+       case NV04_DISP_NTFY_VBLANK:
+               *event = &disp->vblank;
+               return 0;
+       case NV04_DISP_NTFY_CONN:
+               *event = &disp->hpd;
+               return 0;
+       default:
+               break;
+       }
+       return -EINVAL;
+}
+
+int
+_nvkm_disp_fini(struct nvkm_object *object, bool suspend)
+{
+       struct nvkm_disp *disp = (void *)object;
+       struct nvkm_output *outp;
+       int ret;
+
+       list_for_each_entry(outp, &disp->outp, head) {
+               ret = nv_ofuncs(outp)->fini(nv_object(outp), suspend);
+               if (ret && suspend)
+                       goto fail_outp;
+       }
+
+       return nvkm_engine_fini(&disp->base, suspend);
+
+fail_outp:
+       list_for_each_entry_continue_reverse(outp, &disp->outp, head) {
+               nv_ofuncs(outp)->init(nv_object(outp));
+       }
+
+       return ret;
+}
+
+int
+_nvkm_disp_init(struct nvkm_object *object)
+{
+       struct nvkm_disp *disp = (void *)object;
+       struct nvkm_output *outp;
+       int ret;
+
+       ret = nvkm_engine_init(&disp->base);
+       if (ret)
+               return ret;
+
+       list_for_each_entry(outp, &disp->outp, head) {
+               ret = nv_ofuncs(outp)->init(nv_object(outp));
+               if (ret)
+                       goto fail_outp;
+       }
+
+       return ret;
+
+fail_outp:
+       list_for_each_entry_continue_reverse(outp, &disp->outp, head) {
+               nv_ofuncs(outp)->fini(nv_object(outp), false);
+       }
+
+       return ret;
+}
+
+void
+_nvkm_disp_dtor(struct nvkm_object *object)
+{
+       struct nvkm_disp *disp = (void *)object;
+       struct nvkm_output *outp, *outt;
+
+       nvkm_event_fini(&disp->vblank);
+       nvkm_event_fini(&disp->hpd);
+
+       if (disp->outp.next) {
+               list_for_each_entry_safe(outp, outt, &disp->outp, head) {
+                       nvkm_object_ref(NULL, (struct nvkm_object **)&outp);
+               }
+       }
+
+       nvkm_engine_destroy(&disp->base);
+}
+
+int
+nvkm_disp_create_(struct nvkm_object *parent, struct nvkm_object *engine,
+                 struct nvkm_oclass *oclass, int heads, const char *intname,
+                 const char *extname, int length, void **pobject)
+{
+       struct nvkm_disp_impl *impl = (void *)oclass;
+       struct nvkm_bios *bios = nvkm_bios(parent);
+       struct nvkm_disp *disp;
+       struct nvkm_oclass **sclass;
+       struct nvkm_object *object;
+       struct dcb_output dcbE;
+       u8  hpd = 0, ver, hdr;
+       u32 data;
+       int ret, i;
+
+       ret = nvkm_engine_create_(parent, engine, oclass, true, intname,
+                                 extname, length, pobject);
+       disp = *pobject;
+       if (ret)
+               return ret;
+
+       INIT_LIST_HEAD(&disp->outp);
+
+       /* create output objects for each display path in the vbios */
+       i = -1;
+       while ((data = dcb_outp_parse(bios, ++i, &ver, &hdr, &dcbE))) {
+               if (dcbE.type == DCB_OUTPUT_UNUSED)
+                       continue;
+               if (dcbE.type == DCB_OUTPUT_EOL)
+                       break;
+               data = dcbE.location << 4 | dcbE.type;
+
+               oclass = nvkm_output_oclass;
+               sclass = impl->outp;
+               while (sclass && sclass[0]) {
+                       if (sclass[0]->handle == data) {
+                               oclass = sclass[0];
+                               break;
+                       }
+                       sclass++;
+               }
+
+               nvkm_object_ctor(*pobject, NULL, oclass, &dcbE, i, &object);
+               hpd = max(hpd, (u8)(dcbE.connector + 1));
+       }
+
+       ret = nvkm_event_init(&nvkm_disp_hpd_func, 3, hpd, &disp->hpd);
+       if (ret)
+               return ret;
+
+       ret = nvkm_event_init(impl->vblank, 1, heads, &disp->vblank);
+       if (ret)
+               return ret;
+
+       return 0;
+}
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/disp/conn.c b/drivers/gpu/drm/nouveau/nvkm/engine/disp/conn.c
new file mode 100644 (file)
index 0000000..cf03e02
--- /dev/null
@@ -0,0 +1,174 @@
+/*
+ * Copyright 2014 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 "conn.h"
+#include "outp.h"
+#include "priv.h"
+
+#include <subdev/gpio.h>
+
+#include <nvif/event.h>
+
+static int
+nvkm_connector_hpd(struct nvkm_notify *notify)
+{
+       struct nvkm_connector *conn = container_of(notify, typeof(*conn), hpd);
+       struct nvkm_disp *disp = nvkm_disp(conn);
+       struct nvkm_gpio *gpio = nvkm_gpio(conn);
+       const struct nvkm_gpio_ntfy_rep *line = notify->data;
+       struct nvif_notify_conn_rep_v0 rep;
+       int index = conn->index;
+
+       DBG("HPD: %d\n", line->mask);
+
+       if (!gpio->get(gpio, 0, DCB_GPIO_UNUSED, conn->hpd.index))
+               rep.mask = NVIF_NOTIFY_CONN_V0_UNPLUG;
+       else
+               rep.mask = NVIF_NOTIFY_CONN_V0_PLUG;
+       rep.version = 0;
+
+       nvkm_event_send(&disp->hpd, rep.mask, index, &rep, sizeof(rep));
+       return NVKM_NOTIFY_KEEP;
+}
+
+int
+_nvkm_connector_fini(struct nvkm_object *object, bool suspend)
+{
+       struct nvkm_connector *conn = (void *)object;
+       nvkm_notify_put(&conn->hpd);
+       return nvkm_object_fini(&conn->base, suspend);
+}
+
+int
+_nvkm_connector_init(struct nvkm_object *object)
+{
+       struct nvkm_connector *conn = (void *)object;
+       int ret = nvkm_object_init(&conn->base);
+       if (ret == 0)
+               nvkm_notify_get(&conn->hpd);
+       return ret;
+}
+
+void
+_nvkm_connector_dtor(struct nvkm_object *object)
+{
+       struct nvkm_connector *conn = (void *)object;
+       nvkm_notify_fini(&conn->hpd);
+       nvkm_object_destroy(&conn->base);
+}
+
+int
+nvkm_connector_create_(struct nvkm_object *parent,
+                      struct nvkm_object *engine,
+                      struct nvkm_oclass *oclass,
+                      struct nvbios_connE *info, int index,
+                      int length, void **pobject)
+{
+       static const u8 hpd[] = { 0x07, 0x08, 0x51, 0x52, 0x5e, 0x5f, 0x60 };
+       struct nvkm_disp *disp = nvkm_disp(parent);
+       struct nvkm_gpio *gpio = nvkm_gpio(parent);
+       struct nvkm_connector *conn;
+       struct nvkm_output *outp;
+       struct dcb_gpio_func func;
+       int ret;
+
+       list_for_each_entry(outp, &disp->outp, head) {
+               if (outp->conn && outp->conn->index == index) {
+                       atomic_inc(&nv_object(outp->conn)->refcount);
+                       *pobject = outp->conn;
+                       return 1;
+               }
+       }
+
+       ret = nvkm_object_create_(parent, engine, oclass, 0, length, pobject);
+       conn = *pobject;
+       if (ret)
+               return ret;
+
+       conn->info = *info;
+       conn->index = index;
+
+       DBG("type %02x loc %d hpd %02x dp %x di %x sr %x lcdid %x\n",
+           info->type, info->location, info->hpd, info->dp,
+           info->di, info->sr, info->lcdid);
+
+       if ((info->hpd = ffs(info->hpd))) {
+               if (--info->hpd >= ARRAY_SIZE(hpd)) {
+                       ERR("hpd %02x unknown\n", info->hpd);
+                       return 0;
+               }
+               info->hpd = hpd[info->hpd];
+
+               ret = gpio->find(gpio, 0, info->hpd, DCB_GPIO_UNUSED, &func);
+               if (ret) {
+                       ERR("func %02x lookup failed, %d\n", info->hpd, ret);
+                       return 0;
+               }
+
+               ret = nvkm_notify_init(NULL, &gpio->event, nvkm_connector_hpd,
+                                      true, &(struct nvkm_gpio_ntfy_req) {
+                                       .mask = NVKM_GPIO_TOGGLED,
+                                       .line = func.line,
+                                      },
+                                      sizeof(struct nvkm_gpio_ntfy_req),
+                                      sizeof(struct nvkm_gpio_ntfy_rep),
+                                      &conn->hpd);
+               if (ret) {
+                       ERR("func %02x failed, %d\n", info->hpd, ret);
+               } else {
+                       DBG("func %02x (HPD)\n", info->hpd);
+               }
+       }
+
+       return 0;
+}
+
+int
+_nvkm_connector_ctor(struct nvkm_object *parent,
+                    struct nvkm_object *engine,
+                    struct nvkm_oclass *oclass, void *info, u32 index,
+                    struct nvkm_object **pobject)
+{
+       struct nvkm_connector *conn;
+       int ret;
+
+       ret = nvkm_connector_create(parent, engine, oclass, info, index, &conn);
+       *pobject = nv_object(conn);
+       if (ret)
+               return ret;
+
+       return 0;
+}
+
+struct nvkm_oclass *
+nvkm_connector_oclass = &(struct nvkm_connector_impl) {
+       .base = {
+               .handle = 0,
+               .ofuncs = &(struct nvkm_ofuncs) {
+                       .ctor = _nvkm_connector_ctor,
+                       .dtor = _nvkm_connector_dtor,
+                       .init = _nvkm_connector_init,
+                       .fini = _nvkm_connector_fini,
+               },
+       },
+}.base;
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/disp/conn.h b/drivers/gpu/drm/nouveau/nvkm/engine/disp/conn.h
new file mode 100644 (file)
index 0000000..c87a061
--- /dev/null
@@ -0,0 +1,58 @@
+#ifndef __NVKM_DISP_CONN_H__
+#define __NVKM_DISP_CONN_H__
+#include <core/object.h>
+#include <core/notify.h>
+
+#include <subdev/bios.h>
+#include <subdev/bios/conn.h>
+
+struct nvkm_connector {
+       struct nvkm_object base;
+       struct list_head head;
+
+       struct nvbios_connE info;
+       int index;
+
+       struct nvkm_notify hpd;
+};
+
+#define nvkm_connector_create(p,e,c,b,i,d)                                     \
+       nvkm_connector_create_((p), (e), (c), (b), (i), sizeof(**d), (void **)d)
+#define nvkm_connector_destroy(d) ({                                           \
+       struct nvkm_connector *disp = (d);                                     \
+       _nvkm_connector_dtor(nv_object(disp));                                 \
+})
+#define nvkm_connector_init(d) ({                                              \
+       struct nvkm_connector *disp = (d);                                     \
+       _nvkm_connector_init(nv_object(disp));                                 \
+})
+#define nvkm_connector_fini(d,s) ({                                            \
+       struct nvkm_connector *disp = (d);                                     \
+       _nvkm_connector_fini(nv_object(disp), (s));                            \
+})
+
+int nvkm_connector_create_(struct nvkm_object *, struct nvkm_object *,
+                          struct nvkm_oclass *, struct nvbios_connE *,
+                          int, int, void **);
+
+int  _nvkm_connector_ctor(struct nvkm_object *, struct nvkm_object *,
+                         struct nvkm_oclass *, void *, u32,
+                         struct nvkm_object **);
+void _nvkm_connector_dtor(struct nvkm_object *);
+int  _nvkm_connector_init(struct nvkm_object *);
+int  _nvkm_connector_fini(struct nvkm_object *, bool);
+
+struct nvkm_connector_impl {
+       struct nvkm_oclass base;
+};
+
+#ifndef MSG
+#define MSG(l,f,a...) do {                                                     \
+       struct nvkm_connector *_conn = (void *)conn;                           \
+       nv_##l(_conn, "%02x:%02x%02x: "f, _conn->index,                        \
+              _conn->info.location, _conn->info.type, ##a);                   \
+} while(0)
+#define DBG(f,a...) MSG(debug, f, ##a)
+#define ERR(f,a...) MSG(error, f, ##a)
+#endif
+#endif
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/disp/dacnv50.c b/drivers/gpu/drm/nouveau/nvkm/engine/disp/dacnv50.c
new file mode 100644 (file)
index 0000000..0f7d1ec
--- /dev/null
@@ -0,0 +1,99 @@
+/*
+ * Copyright 2012 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 "nv50.h"
+#include "outp.h"
+
+#include <core/client.h>
+#include <subdev/timer.h>
+
+#include <nvif/class.h>
+#include <nvif/unpack.h>
+
+int
+nv50_dac_power(NV50_DISP_MTHD_V1)
+{
+       const u32 doff = outp->or * 0x800;
+       union {
+               struct nv50_disp_dac_pwr_v0 v0;
+       } *args = data;
+       u32 stat;
+       int ret;
+
+       nv_ioctl(object, "disp dac pwr size %d\n", size);
+       if (nvif_unpack(args->v0, 0, 0, false)) {
+               nv_ioctl(object, "disp dac pwr vers %d state %d data %d "
+                                "vsync %d hsync %d\n",
+                        args->v0.version, args->v0.state, args->v0.data,
+                        args->v0.vsync, args->v0.hsync);
+               stat  = 0x00000040 * !args->v0.state;
+               stat |= 0x00000010 * !args->v0.data;
+               stat |= 0x00000004 * !args->v0.vsync;
+               stat |= 0x00000001 * !args->v0.hsync;
+       } else
+               return ret;
+
+       nv_wait(priv, 0x61a004 + doff, 0x80000000, 0x00000000);
+       nv_mask(priv, 0x61a004 + doff, 0xc000007f, 0x80000000 | stat);
+       nv_wait(priv, 0x61a004 + doff, 0x80000000, 0x00000000);
+       return 0;
+}
+
+int
+nv50_dac_sense(NV50_DISP_MTHD_V1)
+{
+       union {
+               struct nv50_disp_dac_load_v0 v0;
+       } *args = data;
+       const u32 doff = outp->or * 0x800;
+       u32 loadval;
+       int ret;
+
+       nv_ioctl(object, "disp dac load size %d\n", size);
+       if (nvif_unpack(args->v0, 0, 0, false)) {
+               nv_ioctl(object, "disp dac load vers %d data %08x\n",
+                        args->v0.version, args->v0.data);
+               if (args->v0.data & 0xfff00000)
+                       return -EINVAL;
+               loadval = args->v0.data;
+       } else
+               return ret;
+
+       nv_mask(priv, 0x61a004 + doff, 0x807f0000, 0x80150000);
+       nv_wait(priv, 0x61a004 + doff, 0x80000000, 0x00000000);
+
+       nv_wr32(priv, 0x61a00c + doff, 0x00100000 | loadval);
+       mdelay(9);
+       udelay(500);
+       loadval = nv_mask(priv, 0x61a00c + doff, 0xffffffff, 0x00000000);
+
+       nv_mask(priv, 0x61a004 + doff, 0x807f0000, 0x80550000);
+       nv_wait(priv, 0x61a004 + doff, 0x80000000, 0x00000000);
+
+       nv_debug(priv, "DAC%d sense: 0x%08x\n", outp->or, loadval);
+       if (!(loadval & 0x80000000))
+               return -ETIMEDOUT;
+
+       args->v0.load = (loadval & 0x38000000) >> 27;
+       return 0;
+}
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/disp/dport.c b/drivers/gpu/drm/nouveau/nvkm/engine/disp/dport.c
new file mode 100644 (file)
index 0000000..6834766
--- /dev/null
@@ -0,0 +1,398 @@
+/*
+ * Copyright 2013 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 "dport.h"
+#include "outpdp.h"
+#include "nv50.h"
+
+#include <subdev/bios.h>
+#include <subdev/bios/init.h>
+#include <subdev/i2c.h>
+
+#include <nvif/class.h>
+
+/******************************************************************************
+ * link training
+ *****************************************************************************/
+struct dp_state {
+       struct nvkm_output_dp *outp;
+       int link_nr;
+       u32 link_bw;
+       u8  stat[6];
+       u8  conf[4];
+       bool pc2;
+       u8  pc2stat;
+       u8  pc2conf[2];
+};
+
+static int
+dp_set_link_config(struct dp_state *dp)
+{
+       struct nvkm_output_dp_impl *impl = (void *)nv_oclass(dp->outp);
+       struct nvkm_output_dp *outp = dp->outp;
+       struct nvkm_disp *disp = nvkm_disp(outp);
+       struct nvkm_bios *bios = nvkm_bios(disp);
+       struct nvbios_init init = {
+               .subdev = nv_subdev(disp),
+               .bios = bios,
+               .offset = 0x0000,
+               .outp = &outp->base.info,
+               .crtc = -1,
+               .execute = 1,
+       };
+       u32 lnkcmp;
+       u8 sink[2];
+       int ret;
+
+       DBG("%d lanes at %d KB/s\n", dp->link_nr, dp->link_bw);
+
+       /* set desired link configuration on the source */
+       if ((lnkcmp = dp->outp->info.lnkcmp)) {
+               if (outp->version < 0x30) {
+                       while ((dp->link_bw / 10) < nv_ro16(bios, lnkcmp))
+                               lnkcmp += 4;
+                       init.offset = nv_ro16(bios, lnkcmp + 2);
+               } else {
+                       while ((dp->link_bw / 27000) < nv_ro08(bios, lnkcmp))
+                               lnkcmp += 3;
+                       init.offset = nv_ro16(bios, lnkcmp + 1);
+               }
+
+               nvbios_exec(&init);
+       }
+
+       ret = impl->lnk_ctl(outp, dp->link_nr, dp->link_bw / 27000,
+                           outp->dpcd[DPCD_RC02] &
+                                      DPCD_RC02_ENHANCED_FRAME_CAP);
+       if (ret) {
+               if (ret < 0)
+                       ERR("lnk_ctl failed with %d\n", ret);
+               return ret;
+       }
+
+       impl->lnk_pwr(outp, dp->link_nr);
+
+       /* set desired link configuration on the sink */
+       sink[0] = dp->link_bw / 27000;
+       sink[1] = dp->link_nr;
+       if (outp->dpcd[DPCD_RC02] & DPCD_RC02_ENHANCED_FRAME_CAP)
+               sink[1] |= DPCD_LC01_ENHANCED_FRAME_EN;
+
+       return nv_wraux(outp->base.edid, DPCD_LC00_LINK_BW_SET, sink, 2);
+}
+
+static void
+dp_set_training_pattern(struct dp_state *dp, u8 pattern)
+{
+       struct nvkm_output_dp_impl *impl = (void *)nv_oclass(dp->outp);
+       struct nvkm_output_dp *outp = dp->outp;
+       u8 sink_tp;
+
+       DBG("training pattern %d\n", pattern);
+       impl->pattern(outp, pattern);
+
+       nv_rdaux(outp->base.edid, DPCD_LC02, &sink_tp, 1);
+       sink_tp &= ~DPCD_LC02_TRAINING_PATTERN_SET;
+       sink_tp |= pattern;
+       nv_wraux(outp->base.edid, DPCD_LC02, &sink_tp, 1);
+}
+
+static int
+dp_link_train_commit(struct dp_state *dp, bool pc)
+{
+       struct nvkm_output_dp_impl *impl = (void *)nv_oclass(dp->outp);
+       struct nvkm_output_dp *outp = dp->outp;
+       int ret, i;
+
+       for (i = 0; i < dp->link_nr; i++) {
+               u8 lane = (dp->stat[4 + (i >> 1)] >> ((i & 1) * 4)) & 0xf;
+               u8 lpc2 = (dp->pc2stat >> (i * 2)) & 0x3;
+               u8 lpre = (lane & 0x0c) >> 2;
+               u8 lvsw = (lane & 0x03) >> 0;
+               u8 hivs = 3 - lpre;
+               u8 hipe = 3;
+               u8 hipc = 3;
+
+               if (lpc2 >= hipc)
+                       lpc2 = hipc | DPCD_LC0F_LANE0_MAX_POST_CURSOR2_REACHED;
+               if (lpre >= hipe) {
+                       lpre = hipe | DPCD_LC03_MAX_SWING_REACHED; /* yes. */
+                       lvsw = hivs = 3 - (lpre & 3);
+               } else
+               if (lvsw >= hivs) {
+                       lvsw = hivs | DPCD_LC03_MAX_SWING_REACHED;
+               }
+
+               dp->conf[i] = (lpre << 3) | lvsw;
+               dp->pc2conf[i >> 1] |= lpc2 << ((i & 1) * 4);
+
+               DBG("config lane %d %02x %02x\n", i, dp->conf[i], lpc2);
+               impl->drv_ctl(outp, i, lvsw & 3, lpre & 3, lpc2 & 3);
+       }
+
+       ret = nv_wraux(outp->base.edid, DPCD_LC03(0), dp->conf, 4);
+       if (ret)
+               return ret;
+
+       if (pc) {
+               ret = nv_wraux(outp->base.edid, DPCD_LC0F, dp->pc2conf, 2);
+               if (ret)
+                       return ret;
+       }
+
+       return 0;
+}
+
+static int
+dp_link_train_update(struct dp_state *dp, bool pc, u32 delay)
+{
+       struct nvkm_output_dp *outp = dp->outp;
+       int ret;
+
+       if (outp->dpcd[DPCD_RC0E_AUX_RD_INTERVAL])
+               mdelay(outp->dpcd[DPCD_RC0E_AUX_RD_INTERVAL] * 4);
+       else
+               udelay(delay);
+
+       ret = nv_rdaux(outp->base.edid, DPCD_LS02, dp->stat, 6);
+       if (ret)
+               return ret;
+
+       if (pc) {
+               ret = nv_rdaux(outp->base.edid, DPCD_LS0C, &dp->pc2stat, 1);
+               if (ret)
+                       dp->pc2stat = 0x00;
+               DBG("status %6ph pc2 %02x\n", dp->stat, dp->pc2stat);
+       } else {
+               DBG("status %6ph\n", dp->stat);
+       }
+
+       return 0;
+}
+
+static int
+dp_link_train_cr(struct dp_state *dp)
+{
+       bool cr_done = false, abort = false;
+       int voltage = dp->conf[0] & DPCD_LC03_VOLTAGE_SWING_SET;
+       int tries = 0, i;
+
+       dp_set_training_pattern(dp, 1);
+
+       do {
+               if (dp_link_train_commit(dp, false) ||
+                   dp_link_train_update(dp, false, 100))
+                       break;
+
+               cr_done = true;
+               for (i = 0; i < dp->link_nr; i++) {
+                       u8 lane = (dp->stat[i >> 1] >> ((i & 1) * 4)) & 0xf;
+                       if (!(lane & DPCD_LS02_LANE0_CR_DONE)) {
+                               cr_done = false;
+                               if (dp->conf[i] & DPCD_LC03_MAX_SWING_REACHED)
+                                       abort = true;
+                               break;
+                       }
+               }
+
+               if ((dp->conf[0] & DPCD_LC03_VOLTAGE_SWING_SET) != voltage) {
+                       voltage = dp->conf[0] & DPCD_LC03_VOLTAGE_SWING_SET;
+                       tries = 0;
+               }
+       } while (!cr_done && !abort && ++tries < 5);
+
+       return cr_done ? 0 : -1;
+}
+
+static int
+dp_link_train_eq(struct dp_state *dp)
+{
+       struct nvkm_output_dp *outp = dp->outp;
+       bool eq_done = false, cr_done = true;
+       int tries = 0, i;
+
+       if (outp->dpcd[2] & DPCD_RC02_TPS3_SUPPORTED)
+               dp_set_training_pattern(dp, 3);
+       else
+               dp_set_training_pattern(dp, 2);
+
+       do {
+               if ((tries &&
+                   dp_link_train_commit(dp, dp->pc2)) ||
+                   dp_link_train_update(dp, dp->pc2, 400))
+                       break;
+
+               eq_done = !!(dp->stat[2] & DPCD_LS04_INTERLANE_ALIGN_DONE);
+               for (i = 0; i < dp->link_nr && eq_done; i++) {
+                       u8 lane = (dp->stat[i >> 1] >> ((i & 1) * 4)) & 0xf;
+                       if (!(lane & DPCD_LS02_LANE0_CR_DONE))
+                               cr_done = false;
+                       if (!(lane & DPCD_LS02_LANE0_CHANNEL_EQ_DONE) ||
+                           !(lane & DPCD_LS02_LANE0_SYMBOL_LOCKED))
+                               eq_done = false;
+               }
+       } while (!eq_done && cr_done && ++tries <= 5);
+
+       return eq_done ? 0 : -1;
+}
+
+static void
+dp_link_train_init(struct dp_state *dp, bool spread)
+{
+       struct nvkm_output_dp *outp = dp->outp;
+       struct nvkm_disp *disp = nvkm_disp(outp);
+       struct nvkm_bios *bios = nvkm_bios(disp);
+       struct nvbios_init init = {
+               .subdev = nv_subdev(disp),
+               .bios = bios,
+               .outp = &outp->base.info,
+               .crtc = -1,
+               .execute = 1,
+       };
+
+       /* set desired spread */
+       if (spread)
+               init.offset = outp->info.script[2];
+       else
+               init.offset = outp->info.script[3];
+       nvbios_exec(&init);
+
+       /* pre-train script */
+       init.offset = outp->info.script[0];
+       nvbios_exec(&init);
+}
+
+static void
+dp_link_train_fini(struct dp_state *dp)
+{
+       struct nvkm_output_dp *outp = dp->outp;
+       struct nvkm_disp *disp = nvkm_disp(outp);
+       struct nvkm_bios *bios = nvkm_bios(disp);
+       struct nvbios_init init = {
+               .subdev = nv_subdev(disp),
+               .bios = bios,
+               .outp = &outp->base.info,
+               .crtc = -1,
+               .execute = 1,
+       };
+
+       /* post-train script */
+       init.offset = outp->info.script[1],
+       nvbios_exec(&init);
+}
+
+static const struct dp_rates {
+       u32 rate;
+       u8  bw;
+       u8  nr;
+} nvkm_dp_rates[] = {
+       { 2160000, 0x14, 4 },
+       { 1080000, 0x0a, 4 },
+       { 1080000, 0x14, 2 },
+       {  648000, 0x06, 4 },
+       {  540000, 0x0a, 2 },
+       {  540000, 0x14, 1 },
+       {  324000, 0x06, 2 },
+       {  270000, 0x0a, 1 },
+       {  162000, 0x06, 1 },
+       {}
+};
+
+void
+nvkm_dp_train(struct work_struct *w)
+{
+       struct nvkm_output_dp *outp = container_of(w, typeof(*outp), lt.work);
+       struct nv50_disp_priv *priv = (void *)nvkm_disp(outp);
+       const struct dp_rates *cfg = nvkm_dp_rates;
+       struct dp_state _dp = {
+               .outp = outp,
+       }, *dp = &_dp;
+       u32 datarate = 0;
+       int ret;
+
+       if (!outp->base.info.location && priv->sor.magic)
+               priv->sor.magic(&outp->base);
+
+       /* bring capabilities within encoder limits */
+       if (nv_mclass(priv) < GF110_DISP)
+               outp->dpcd[2] &= ~DPCD_RC02_TPS3_SUPPORTED;
+       if ((outp->dpcd[2] & 0x1f) > outp->base.info.dpconf.link_nr) {
+               outp->dpcd[2] &= ~DPCD_RC02_MAX_LANE_COUNT;
+               outp->dpcd[2] |= outp->base.info.dpconf.link_nr;
+       }
+       if (outp->dpcd[1] > outp->base.info.dpconf.link_bw)
+               outp->dpcd[1] = outp->base.info.dpconf.link_bw;
+       dp->pc2 = outp->dpcd[2] & DPCD_RC02_TPS3_SUPPORTED;
+
+       /* restrict link config to the lowest required rate, if requested */
+       if (datarate) {
+               datarate = (datarate / 8) * 10; /* 8B/10B coding overhead */
+               while (cfg[1].rate >= datarate)
+                       cfg++;
+       }
+       cfg--;
+
+       /* disable link interrupt handling during link training */
+       nvkm_notify_put(&outp->irq);
+
+       /* enable down-spreading and execute pre-train script from vbios */
+       dp_link_train_init(dp, outp->dpcd[3] & 0x01);
+
+       while (ret = -EIO, (++cfg)->rate) {
+               /* select next configuration supported by encoder and sink */
+               while (cfg->nr > (outp->dpcd[2] & DPCD_RC02_MAX_LANE_COUNT) ||
+                      cfg->bw > (outp->dpcd[DPCD_RC01_MAX_LINK_RATE]))
+                       cfg++;
+               dp->link_bw = cfg->bw * 27000;
+               dp->link_nr = cfg->nr;
+
+               /* program selected link configuration */
+               ret = dp_set_link_config(dp);
+               if (ret == 0) {
+                       /* attempt to train the link at this configuration */
+                       memset(dp->stat, 0x00, sizeof(dp->stat));
+                       if (!dp_link_train_cr(dp) &&
+                           !dp_link_train_eq(dp))
+                               break;
+               } else
+               if (ret) {
+                       /* dp_set_link_config() handled training, or
+                        * we failed to communicate with the sink.
+                        */
+                       break;
+               }
+       }
+
+       /* finish link training and execute post-train script from vbios */
+       dp_set_training_pattern(dp, 0);
+       if (ret < 0)
+               ERR("link training failed\n");
+
+       dp_link_train_fini(dp);
+
+       /* signal completion and enable link interrupt handling */
+       DBG("training complete\n");
+       atomic_set(&outp->lt.done, 1);
+       wake_up(&outp->lt.wait);
+       nvkm_notify_get(&outp->irq);
+}
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/disp/dport.h b/drivers/gpu/drm/nouveau/nvkm/engine/disp/dport.h
new file mode 100644 (file)
index 0000000..9596290
--- /dev/null
@@ -0,0 +1,75 @@
+#ifndef __NVKM_DISP_DPORT_H__
+#define __NVKM_DISP_DPORT_H__
+#include <core/os.h>
+
+/* DPCD Receiver Capabilities */
+#define DPCD_RC00_DPCD_REV                                              0x00000
+#define DPCD_RC01_MAX_LINK_RATE                                         0x00001
+#define DPCD_RC02                                                       0x00002
+#define DPCD_RC02_ENHANCED_FRAME_CAP                                       0x80
+#define DPCD_RC02_TPS3_SUPPORTED                                           0x40
+#define DPCD_RC02_MAX_LANE_COUNT                                           0x1f
+#define DPCD_RC03                                                       0x00003
+#define DPCD_RC03_MAX_DOWNSPREAD                                           0x01
+#define DPCD_RC0E_AUX_RD_INTERVAL                                       0x0000e
+
+/* DPCD Link Configuration */
+#define DPCD_LC00_LINK_BW_SET                                           0x00100
+#define DPCD_LC01                                                       0x00101
+#define DPCD_LC01_ENHANCED_FRAME_EN                                        0x80
+#define DPCD_LC01_LANE_COUNT_SET                                           0x1f
+#define DPCD_LC02                                                       0x00102
+#define DPCD_LC02_TRAINING_PATTERN_SET                                     0x03
+#define DPCD_LC03(l)                                            ((l) +  0x00103)
+#define DPCD_LC03_MAX_PRE_EMPHASIS_REACHED                                 0x20
+#define DPCD_LC03_PRE_EMPHASIS_SET                                         0x18
+#define DPCD_LC03_MAX_SWING_REACHED                                        0x04
+#define DPCD_LC03_VOLTAGE_SWING_SET                                        0x03
+#define DPCD_LC0F                                                       0x0010f
+#define DPCD_LC0F_LANE1_MAX_POST_CURSOR2_REACHED                           0x40
+#define DPCD_LC0F_LANE1_POST_CURSOR2_SET                                   0x30
+#define DPCD_LC0F_LANE0_MAX_POST_CURSOR2_REACHED                           0x04
+#define DPCD_LC0F_LANE0_POST_CURSOR2_SET                                   0x03
+#define DPCD_LC10                                                       0x00110
+#define DPCD_LC10_LANE3_MAX_POST_CURSOR2_REACHED                           0x40
+#define DPCD_LC10_LANE3_POST_CURSOR2_SET                                   0x30
+#define DPCD_LC10_LANE2_MAX_POST_CURSOR2_REACHED                           0x04
+#define DPCD_LC10_LANE2_POST_CURSOR2_SET                                   0x03
+
+/* DPCD Link/Sink Status */
+#define DPCD_LS02                                                       0x00202
+#define DPCD_LS02_LANE1_SYMBOL_LOCKED                                      0x40
+#define DPCD_LS02_LANE1_CHANNEL_EQ_DONE                                    0x20
+#define DPCD_LS02_LANE1_CR_DONE                                            0x10
+#define DPCD_LS02_LANE0_SYMBOL_LOCKED                                      0x04
+#define DPCD_LS02_LANE0_CHANNEL_EQ_DONE                                    0x02
+#define DPCD_LS02_LANE0_CR_DONE                                            0x01
+#define DPCD_LS03                                                       0x00203
+#define DPCD_LS03_LANE3_SYMBOL_LOCKED                                      0x40
+#define DPCD_LS03_LANE3_CHANNEL_EQ_DONE                                    0x20
+#define DPCD_LS03_LANE3_CR_DONE                                            0x10
+#define DPCD_LS03_LANE2_SYMBOL_LOCKED                                      0x04
+#define DPCD_LS03_LANE2_CHANNEL_EQ_DONE                                    0x02
+#define DPCD_LS03_LANE2_CR_DONE                                            0x01
+#define DPCD_LS04                                                       0x00204
+#define DPCD_LS04_LINK_STATUS_UPDATED                                      0x80
+#define DPCD_LS04_DOWNSTREAM_PORT_STATUS_CHANGED                           0x40
+#define DPCD_LS04_INTERLANE_ALIGN_DONE                                     0x01
+#define DPCD_LS06                                                       0x00206
+#define DPCD_LS06_LANE1_PRE_EMPHASIS                                       0xc0
+#define DPCD_LS06_LANE1_VOLTAGE_SWING                                      0x30
+#define DPCD_LS06_LANE0_PRE_EMPHASIS                                       0x0c
+#define DPCD_LS06_LANE0_VOLTAGE_SWING                                      0x03
+#define DPCD_LS07                                                       0x00207
+#define DPCD_LS07_LANE3_PRE_EMPHASIS                                       0xc0
+#define DPCD_LS07_LANE3_VOLTAGE_SWING                                      0x30
+#define DPCD_LS07_LANE2_PRE_EMPHASIS                                       0x0c
+#define DPCD_LS07_LANE2_VOLTAGE_SWING                                      0x03
+#define DPCD_LS0C                                                       0x0020c
+#define DPCD_LS0C_LANE3_POST_CURSOR2                                       0xc0
+#define DPCD_LS0C_LANE2_POST_CURSOR2                                       0x30
+#define DPCD_LS0C_LANE1_POST_CURSOR2                                       0x0c
+#define DPCD_LS0C_LANE0_POST_CURSOR2                                       0x03
+
+void nvkm_dp_train(struct work_struct *);
+#endif
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/disp/g84.c b/drivers/gpu/drm/nouveau/nvkm/engine/disp/g84.c
new file mode 100644 (file)
index 0000000..a0dcf53
--- /dev/null
@@ -0,0 +1,272 @@
+/*
+ * Copyright 2012 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 "nv50.h"
+
+#include <nvif/class.h>
+
+/*******************************************************************************
+ * EVO master channel object
+ ******************************************************************************/
+
+const struct nv50_disp_mthd_list
+g84_disp_core_mthd_dac = {
+       .mthd = 0x0080,
+       .addr = 0x000008,
+       .data = {
+               { 0x0400, 0x610b58 },
+               { 0x0404, 0x610bdc },
+               { 0x0420, 0x610bc4 },
+               {}
+       }
+};
+
+const struct nv50_disp_mthd_list
+g84_disp_core_mthd_head = {
+       .mthd = 0x0400,
+       .addr = 0x000540,
+       .data = {
+               { 0x0800, 0x610ad8 },
+               { 0x0804, 0x610ad0 },
+               { 0x0808, 0x610a48 },
+               { 0x080c, 0x610a78 },
+               { 0x0810, 0x610ac0 },
+               { 0x0814, 0x610af8 },
+               { 0x0818, 0x610b00 },
+               { 0x081c, 0x610ae8 },
+               { 0x0820, 0x610af0 },
+               { 0x0824, 0x610b08 },
+               { 0x0828, 0x610b10 },
+               { 0x082c, 0x610a68 },
+               { 0x0830, 0x610a60 },
+               { 0x0834, 0x000000 },
+               { 0x0838, 0x610a40 },
+               { 0x0840, 0x610a24 },
+               { 0x0844, 0x610a2c },
+               { 0x0848, 0x610aa8 },
+               { 0x084c, 0x610ab0 },
+               { 0x085c, 0x610c5c },
+               { 0x0860, 0x610a84 },
+               { 0x0864, 0x610a90 },
+               { 0x0868, 0x610b18 },
+               { 0x086c, 0x610b20 },
+               { 0x0870, 0x610ac8 },
+               { 0x0874, 0x610a38 },
+               { 0x0878, 0x610c50 },
+               { 0x0880, 0x610a58 },
+               { 0x0884, 0x610a9c },
+               { 0x089c, 0x610c68 },
+               { 0x08a0, 0x610a70 },
+               { 0x08a4, 0x610a50 },
+               { 0x08a8, 0x610ae0 },
+               { 0x08c0, 0x610b28 },
+               { 0x08c4, 0x610b30 },
+               { 0x08c8, 0x610b40 },
+               { 0x08d4, 0x610b38 },
+               { 0x08d8, 0x610b48 },
+               { 0x08dc, 0x610b50 },
+               { 0x0900, 0x610a18 },
+               { 0x0904, 0x610ab8 },
+               { 0x0910, 0x610c70 },
+               { 0x0914, 0x610c78 },
+               {}
+       }
+};
+
+const struct nv50_disp_mthd_chan
+g84_disp_core_mthd_chan = {
+       .name = "Core",
+       .addr = 0x000000,
+       .data = {
+               { "Global", 1, &nv50_disp_core_mthd_base },
+               {    "DAC", 3, &g84_disp_core_mthd_dac  },
+               {    "SOR", 2, &nv50_disp_core_mthd_sor  },
+               {   "PIOR", 3, &nv50_disp_core_mthd_pior },
+               {   "HEAD", 2, &g84_disp_core_mthd_head },
+               {}
+       }
+};
+
+/*******************************************************************************
+ * EVO sync channel objects
+ ******************************************************************************/
+
+static const struct nv50_disp_mthd_list
+g84_disp_base_mthd_base = {
+       .mthd = 0x0000,
+       .addr = 0x000000,
+       .data = {
+               { 0x0080, 0x000000 },
+               { 0x0084, 0x0008c4 },
+               { 0x0088, 0x0008d0 },
+               { 0x008c, 0x0008dc },
+               { 0x0090, 0x0008e4 },
+               { 0x0094, 0x610884 },
+               { 0x00a0, 0x6108a0 },
+               { 0x00a4, 0x610878 },
+               { 0x00c0, 0x61086c },
+               { 0x00c4, 0x610800 },
+               { 0x00c8, 0x61080c },
+               { 0x00cc, 0x610818 },
+               { 0x00e0, 0x610858 },
+               { 0x00e4, 0x610860 },
+               { 0x00e8, 0x6108ac },
+               { 0x00ec, 0x6108b4 },
+               { 0x00fc, 0x610824 },
+               { 0x0100, 0x610894 },
+               { 0x0104, 0x61082c },
+               { 0x0110, 0x6108bc },
+               { 0x0114, 0x61088c },
+               {}
+       }
+};
+
+const struct nv50_disp_mthd_chan
+g84_disp_base_mthd_chan = {
+       .name = "Base",
+       .addr = 0x000540,
+       .data = {
+               { "Global", 1, &g84_disp_base_mthd_base },
+               {  "Image", 2, &nv50_disp_base_mthd_image },
+               {}
+       }
+};
+
+/*******************************************************************************
+ * EVO overlay channel objects
+ ******************************************************************************/
+
+static const struct nv50_disp_mthd_list
+g84_disp_ovly_mthd_base = {
+       .mthd = 0x0000,
+       .addr = 0x000000,
+       .data = {
+               { 0x0080, 0x000000 },
+               { 0x0084, 0x6109a0 },
+               { 0x0088, 0x6109c0 },
+               { 0x008c, 0x6109c8 },
+               { 0x0090, 0x6109b4 },
+               { 0x0094, 0x610970 },
+               { 0x00a0, 0x610998 },
+               { 0x00a4, 0x610964 },
+               { 0x00c0, 0x610958 },
+               { 0x00e0, 0x6109a8 },
+               { 0x00e4, 0x6109d0 },
+               { 0x00e8, 0x6109d8 },
+               { 0x0100, 0x61094c },
+               { 0x0104, 0x610984 },
+               { 0x0108, 0x61098c },
+               { 0x0800, 0x6109f8 },
+               { 0x0808, 0x610a08 },
+               { 0x080c, 0x610a10 },
+               { 0x0810, 0x610a00 },
+               {}
+       }
+};
+
+const struct nv50_disp_mthd_chan
+g84_disp_ovly_mthd_chan = {
+       .name = "Overlay",
+       .addr = 0x000540,
+       .data = {
+               { "Global", 1, &g84_disp_ovly_mthd_base },
+               {}
+       }
+};
+
+/*******************************************************************************
+ * Base display object
+ ******************************************************************************/
+
+static struct nvkm_oclass
+g84_disp_sclass[] = {
+       { G82_DISP_CORE_CHANNEL_DMA, &nv50_disp_core_ofuncs.base },
+       { G82_DISP_BASE_CHANNEL_DMA, &nv50_disp_base_ofuncs.base },
+       { G82_DISP_OVERLAY_CHANNEL_DMA, &nv50_disp_ovly_ofuncs.base },
+       { G82_DISP_OVERLAY, &nv50_disp_oimm_ofuncs.base },
+       { G82_DISP_CURSOR, &nv50_disp_curs_ofuncs.base },
+       {}
+};
+
+static struct nvkm_oclass
+g84_disp_main_oclass[] = {
+       { G82_DISP, &nv50_disp_main_ofuncs },
+       {}
+};
+
+/*******************************************************************************
+ * Display engine implementation
+ ******************************************************************************/
+
+static int
+g84_disp_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+             struct nvkm_oclass *oclass, void *data, u32 size,
+             struct nvkm_object **pobject)
+{
+       struct nv50_disp_priv *priv;
+       int ret;
+
+       ret = nvkm_disp_create(parent, engine, oclass, 2, "PDISP",
+                              "display", &priv);
+       *pobject = nv_object(priv);
+       if (ret)
+               return ret;
+
+       ret = nvkm_event_init(&nv50_disp_chan_uevent, 1, 9, &priv->uevent);
+       if (ret)
+               return ret;
+
+       nv_engine(priv)->sclass = g84_disp_main_oclass;
+       nv_engine(priv)->cclass = &nv50_disp_cclass;
+       nv_subdev(priv)->intr = nv50_disp_intr;
+       INIT_WORK(&priv->supervisor, nv50_disp_intr_supervisor);
+       priv->sclass = g84_disp_sclass;
+       priv->head.nr = 2;
+       priv->dac.nr = 3;
+       priv->sor.nr = 2;
+       priv->pior.nr = 3;
+       priv->dac.power = nv50_dac_power;
+       priv->dac.sense = nv50_dac_sense;
+       priv->sor.power = nv50_sor_power;
+       priv->sor.hdmi = g84_hdmi_ctrl;
+       priv->pior.power = nv50_pior_power;
+       return 0;
+}
+
+struct nvkm_oclass *
+g84_disp_oclass = &(struct nv50_disp_impl) {
+       .base.base.handle = NV_ENGINE(DISP, 0x82),
+       .base.base.ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = g84_disp_ctor,
+               .dtor = _nvkm_disp_dtor,
+               .init = _nvkm_disp_init,
+               .fini = _nvkm_disp_fini,
+       },
+       .base.vblank = &nv50_disp_vblank_func,
+       .base.outp =  nv50_disp_outp_sclass,
+       .mthd.core = &g84_disp_core_mthd_chan,
+       .mthd.base = &g84_disp_base_mthd_chan,
+       .mthd.ovly = &g84_disp_ovly_mthd_chan,
+       .mthd.prev = 0x000004,
+       .head.scanoutpos = nv50_disp_main_scanoutpos,
+}.base.base;
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/disp/g94.c b/drivers/gpu/drm/nouveau/nvkm/engine/disp/g94.c
new file mode 100644 (file)
index 0000000..1ab0d0a
--- /dev/null
@@ -0,0 +1,139 @@
+/*
+ * Copyright 2012 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 "nv50.h"
+#include "outpdp.h"
+
+#include <nvif/class.h>
+
+/*******************************************************************************
+ * EVO master channel object
+ ******************************************************************************/
+
+const struct nv50_disp_mthd_list
+g94_disp_core_mthd_sor = {
+       .mthd = 0x0040,
+       .addr = 0x000008,
+       .data = {
+               { 0x0600, 0x610794 },
+               {}
+       }
+};
+
+const struct nv50_disp_mthd_chan
+g94_disp_core_mthd_chan = {
+       .name = "Core",
+       .addr = 0x000000,
+       .data = {
+               { "Global", 1, &nv50_disp_core_mthd_base },
+               {    "DAC", 3, &g84_disp_core_mthd_dac  },
+               {    "SOR", 4, &g94_disp_core_mthd_sor  },
+               {   "PIOR", 3, &nv50_disp_core_mthd_pior },
+               {   "HEAD", 2, &g84_disp_core_mthd_head },
+               {}
+       }
+};
+
+/*******************************************************************************
+ * Base display object
+ ******************************************************************************/
+
+static struct nvkm_oclass
+g94_disp_sclass[] = {
+       { GT206_DISP_CORE_CHANNEL_DMA, &nv50_disp_core_ofuncs.base },
+       { GT200_DISP_BASE_CHANNEL_DMA, &nv50_disp_base_ofuncs.base },
+       { GT200_DISP_OVERLAY_CHANNEL_DMA, &nv50_disp_ovly_ofuncs.base },
+       { G82_DISP_OVERLAY, &nv50_disp_oimm_ofuncs.base },
+       { G82_DISP_CURSOR, &nv50_disp_curs_ofuncs.base },
+       {}
+};
+
+static struct nvkm_oclass
+g94_disp_main_oclass[] = {
+       { GT206_DISP, &nv50_disp_main_ofuncs },
+       {}
+};
+
+/*******************************************************************************
+ * Display engine implementation
+ ******************************************************************************/
+
+static int
+g94_disp_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+             struct nvkm_oclass *oclass, void *data, u32 size,
+             struct nvkm_object **pobject)
+{
+       struct nv50_disp_priv *priv;
+       int ret;
+
+       ret = nvkm_disp_create(parent, engine, oclass, 2, "PDISP",
+                              "display", &priv);
+       *pobject = nv_object(priv);
+       if (ret)
+               return ret;
+
+       ret = nvkm_event_init(&nv50_disp_chan_uevent, 1, 9, &priv->uevent);
+       if (ret)
+               return ret;
+
+       nv_engine(priv)->sclass = g94_disp_main_oclass;
+       nv_engine(priv)->cclass = &nv50_disp_cclass;
+       nv_subdev(priv)->intr = nv50_disp_intr;
+       INIT_WORK(&priv->supervisor, nv50_disp_intr_supervisor);
+       priv->sclass = g94_disp_sclass;
+       priv->head.nr = 2;
+       priv->dac.nr = 3;
+       priv->sor.nr = 4;
+       priv->pior.nr = 3;
+       priv->dac.power = nv50_dac_power;
+       priv->dac.sense = nv50_dac_sense;
+       priv->sor.power = nv50_sor_power;
+       priv->sor.hdmi = g84_hdmi_ctrl;
+       priv->pior.power = nv50_pior_power;
+       return 0;
+}
+
+struct nvkm_oclass *
+g94_disp_outp_sclass[] = {
+       &nv50_pior_dp_impl.base.base,
+       &g94_sor_dp_impl.base.base,
+       NULL
+};
+
+struct nvkm_oclass *
+g94_disp_oclass = &(struct nv50_disp_impl) {
+       .base.base.handle = NV_ENGINE(DISP, 0x88),
+       .base.base.ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = g94_disp_ctor,
+               .dtor = _nvkm_disp_dtor,
+               .init = _nvkm_disp_init,
+               .fini = _nvkm_disp_fini,
+       },
+       .base.vblank = &nv50_disp_vblank_func,
+       .base.outp =  g94_disp_outp_sclass,
+       .mthd.core = &g94_disp_core_mthd_chan,
+       .mthd.base = &g84_disp_base_mthd_chan,
+       .mthd.ovly = &g84_disp_ovly_mthd_chan,
+       .mthd.prev = 0x000004,
+       .head.scanoutpos = nv50_disp_main_scanoutpos,
+}.base.base;
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/disp/gf110.c b/drivers/gpu/drm/nouveau/nvkm/engine/disp/gf110.c
new file mode 100644 (file)
index 0000000..0ebf466
--- /dev/null
@@ -0,0 +1,1310 @@
+/*
+ * Copyright 2012 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 "nv50.h"
+#include "outp.h"
+#include "outpdp.h"
+
+#include <core/client.h>
+#include <core/gpuobj.h>
+#include <core/ramht.h>
+#include <subdev/bios.h>
+#include <subdev/bios/dcb.h>
+#include <subdev/bios/disp.h>
+#include <subdev/bios/init.h>
+#include <subdev/bios/pll.h>
+#include <subdev/devinit.h>
+#include <subdev/timer.h>
+
+#include <nvif/class.h>
+#include <nvif/unpack.h>
+
+/*******************************************************************************
+ * EVO channel base class
+ ******************************************************************************/
+
+static void
+gf110_disp_chan_uevent_fini(struct nvkm_event *event, int type, int index)
+{
+       struct nv50_disp_priv *priv = container_of(event, typeof(*priv), uevent);
+       nv_mask(priv, 0x610090, 0x00000001 << index, 0x00000000 << index);
+       nv_wr32(priv, 0x61008c, 0x00000001 << index);
+}
+
+static void
+gf110_disp_chan_uevent_init(struct nvkm_event *event, int types, int index)
+{
+       struct nv50_disp_priv *priv = container_of(event, typeof(*priv), uevent);
+       nv_wr32(priv, 0x61008c, 0x00000001 << index);
+       nv_mask(priv, 0x610090, 0x00000001 << index, 0x00000001 << index);
+}
+
+const struct nvkm_event_func
+gf110_disp_chan_uevent = {
+       .ctor = nv50_disp_chan_uevent_ctor,
+       .init = gf110_disp_chan_uevent_init,
+       .fini = gf110_disp_chan_uevent_fini,
+};
+
+/*******************************************************************************
+ * EVO DMA channel base class
+ ******************************************************************************/
+
+static int
+gf110_disp_dmac_object_attach(struct nvkm_object *parent,
+                             struct nvkm_object *object, u32 name)
+{
+       struct nv50_disp_base *base = (void *)parent->parent;
+       struct nv50_disp_chan *chan = (void *)parent;
+       u32 addr = nv_gpuobj(object)->node->offset;
+       u32 data = (chan->chid << 27) | (addr << 9) | 0x00000001;
+       return nvkm_ramht_insert(base->ramht, chan->chid, name, data);
+}
+
+static void
+gf110_disp_dmac_object_detach(struct nvkm_object *parent, int cookie)
+{
+       struct nv50_disp_base *base = (void *)parent->parent;
+       nvkm_ramht_remove(base->ramht, cookie);
+}
+
+static int
+gf110_disp_dmac_init(struct nvkm_object *object)
+{
+       struct nv50_disp_priv *priv = (void *)object->engine;
+       struct nv50_disp_dmac *dmac = (void *)object;
+       int chid = dmac->base.chid;
+       int ret;
+
+       ret = nv50_disp_chan_init(&dmac->base);
+       if (ret)
+               return ret;
+
+       /* enable error reporting */
+       nv_mask(priv, 0x6100a0, 0x00000001 << chid, 0x00000001 << chid);
+
+       /* initialise channel for dma command submission */
+       nv_wr32(priv, 0x610494 + (chid * 0x0010), dmac->push);
+       nv_wr32(priv, 0x610498 + (chid * 0x0010), 0x00010000);
+       nv_wr32(priv, 0x61049c + (chid * 0x0010), 0x00000001);
+       nv_mask(priv, 0x610490 + (chid * 0x0010), 0x00000010, 0x00000010);
+       nv_wr32(priv, 0x640000 + (chid * 0x1000), 0x00000000);
+       nv_wr32(priv, 0x610490 + (chid * 0x0010), 0x00000013);
+
+       /* wait for it to go inactive */
+       if (!nv_wait(priv, 0x610490 + (chid * 0x10), 0x80000000, 0x00000000)) {
+               nv_error(dmac, "init: 0x%08x\n",
+                        nv_rd32(priv, 0x610490 + (chid * 0x10)));
+               return -EBUSY;
+       }
+
+       return 0;
+}
+
+static int
+gf110_disp_dmac_fini(struct nvkm_object *object, bool suspend)
+{
+       struct nv50_disp_priv *priv = (void *)object->engine;
+       struct nv50_disp_dmac *dmac = (void *)object;
+       int chid = dmac->base.chid;
+
+       /* deactivate channel */
+       nv_mask(priv, 0x610490 + (chid * 0x0010), 0x00001010, 0x00001000);
+       nv_mask(priv, 0x610490 + (chid * 0x0010), 0x00000003, 0x00000000);
+       if (!nv_wait(priv, 0x610490 + (chid * 0x10), 0x001e0000, 0x00000000)) {
+               nv_error(dmac, "fini: 0x%08x\n",
+                        nv_rd32(priv, 0x610490 + (chid * 0x10)));
+               if (suspend)
+                       return -EBUSY;
+       }
+
+       /* disable error reporting and completion notification */
+       nv_mask(priv, 0x610090, 0x00000001 << chid, 0x00000000);
+       nv_mask(priv, 0x6100a0, 0x00000001 << chid, 0x00000000);
+
+       return nv50_disp_chan_fini(&dmac->base, suspend);
+}
+
+/*******************************************************************************
+ * EVO master channel object
+ ******************************************************************************/
+
+const struct nv50_disp_mthd_list
+gf110_disp_core_mthd_base = {
+       .mthd = 0x0000,
+       .addr = 0x000000,
+       .data = {
+               { 0x0080, 0x660080 },
+               { 0x0084, 0x660084 },
+               { 0x0088, 0x660088 },
+               { 0x008c, 0x000000 },
+               {}
+       }
+};
+
+const struct nv50_disp_mthd_list
+gf110_disp_core_mthd_dac = {
+       .mthd = 0x0020,
+       .addr = 0x000020,
+       .data = {
+               { 0x0180, 0x660180 },
+               { 0x0184, 0x660184 },
+               { 0x0188, 0x660188 },
+               { 0x0190, 0x660190 },
+               {}
+       }
+};
+
+const struct nv50_disp_mthd_list
+gf110_disp_core_mthd_sor = {
+       .mthd = 0x0020,
+       .addr = 0x000020,
+       .data = {
+               { 0x0200, 0x660200 },
+               { 0x0204, 0x660204 },
+               { 0x0208, 0x660208 },
+               { 0x0210, 0x660210 },
+               {}
+       }
+};
+
+const struct nv50_disp_mthd_list
+gf110_disp_core_mthd_pior = {
+       .mthd = 0x0020,
+       .addr = 0x000020,
+       .data = {
+               { 0x0300, 0x660300 },
+               { 0x0304, 0x660304 },
+               { 0x0308, 0x660308 },
+               { 0x0310, 0x660310 },
+               {}
+       }
+};
+
+static const struct nv50_disp_mthd_list
+gf110_disp_core_mthd_head = {
+       .mthd = 0x0300,
+       .addr = 0x000300,
+       .data = {
+               { 0x0400, 0x660400 },
+               { 0x0404, 0x660404 },
+               { 0x0408, 0x660408 },
+               { 0x040c, 0x66040c },
+               { 0x0410, 0x660410 },
+               { 0x0414, 0x660414 },
+               { 0x0418, 0x660418 },
+               { 0x041c, 0x66041c },
+               { 0x0420, 0x660420 },
+               { 0x0424, 0x660424 },
+               { 0x0428, 0x660428 },
+               { 0x042c, 0x66042c },
+               { 0x0430, 0x660430 },
+               { 0x0434, 0x660434 },
+               { 0x0438, 0x660438 },
+               { 0x0440, 0x660440 },
+               { 0x0444, 0x660444 },
+               { 0x0448, 0x660448 },
+               { 0x044c, 0x66044c },
+               { 0x0450, 0x660450 },
+               { 0x0454, 0x660454 },
+               { 0x0458, 0x660458 },
+               { 0x045c, 0x66045c },
+               { 0x0460, 0x660460 },
+               { 0x0468, 0x660468 },
+               { 0x046c, 0x66046c },
+               { 0x0470, 0x660470 },
+               { 0x0474, 0x660474 },
+               { 0x0480, 0x660480 },
+               { 0x0484, 0x660484 },
+               { 0x048c, 0x66048c },
+               { 0x0490, 0x660490 },
+               { 0x0494, 0x660494 },
+               { 0x0498, 0x660498 },
+               { 0x04b0, 0x6604b0 },
+               { 0x04b8, 0x6604b8 },
+               { 0x04bc, 0x6604bc },
+               { 0x04c0, 0x6604c0 },
+               { 0x04c4, 0x6604c4 },
+               { 0x04c8, 0x6604c8 },
+               { 0x04d0, 0x6604d0 },
+               { 0x04d4, 0x6604d4 },
+               { 0x04e0, 0x6604e0 },
+               { 0x04e4, 0x6604e4 },
+               { 0x04e8, 0x6604e8 },
+               { 0x04ec, 0x6604ec },
+               { 0x04f0, 0x6604f0 },
+               { 0x04f4, 0x6604f4 },
+               { 0x04f8, 0x6604f8 },
+               { 0x04fc, 0x6604fc },
+               { 0x0500, 0x660500 },
+               { 0x0504, 0x660504 },
+               { 0x0508, 0x660508 },
+               { 0x050c, 0x66050c },
+               { 0x0510, 0x660510 },
+               { 0x0514, 0x660514 },
+               { 0x0518, 0x660518 },
+               { 0x051c, 0x66051c },
+               { 0x052c, 0x66052c },
+               { 0x0530, 0x660530 },
+               { 0x054c, 0x66054c },
+               { 0x0550, 0x660550 },
+               { 0x0554, 0x660554 },
+               { 0x0558, 0x660558 },
+               { 0x055c, 0x66055c },
+               {}
+       }
+};
+
+static const struct nv50_disp_mthd_chan
+gf110_disp_core_mthd_chan = {
+       .name = "Core",
+       .addr = 0x000000,
+       .data = {
+               { "Global", 1, &gf110_disp_core_mthd_base },
+               {    "DAC", 3, &gf110_disp_core_mthd_dac  },
+               {    "SOR", 8, &gf110_disp_core_mthd_sor  },
+               {   "PIOR", 4, &gf110_disp_core_mthd_pior },
+               {   "HEAD", 4, &gf110_disp_core_mthd_head },
+               {}
+       }
+};
+
+static int
+gf110_disp_core_init(struct nvkm_object *object)
+{
+       struct nv50_disp_priv *priv = (void *)object->engine;
+       struct nv50_disp_dmac *mast = (void *)object;
+       int ret;
+
+       ret = nv50_disp_chan_init(&mast->base);
+       if (ret)
+               return ret;
+
+       /* enable error reporting */
+       nv_mask(priv, 0x6100a0, 0x00000001, 0x00000001);
+
+       /* initialise channel for dma command submission */
+       nv_wr32(priv, 0x610494, mast->push);
+       nv_wr32(priv, 0x610498, 0x00010000);
+       nv_wr32(priv, 0x61049c, 0x00000001);
+       nv_mask(priv, 0x610490, 0x00000010, 0x00000010);
+       nv_wr32(priv, 0x640000, 0x00000000);
+       nv_wr32(priv, 0x610490, 0x01000013);
+
+       /* wait for it to go inactive */
+       if (!nv_wait(priv, 0x610490, 0x80000000, 0x00000000)) {
+               nv_error(mast, "init: 0x%08x\n", nv_rd32(priv, 0x610490));
+               return -EBUSY;
+       }
+
+       return 0;
+}
+
+static int
+gf110_disp_core_fini(struct nvkm_object *object, bool suspend)
+{
+       struct nv50_disp_priv *priv = (void *)object->engine;
+       struct nv50_disp_dmac *mast = (void *)object;
+
+       /* deactivate channel */
+       nv_mask(priv, 0x610490, 0x00000010, 0x00000000);
+       nv_mask(priv, 0x610490, 0x00000003, 0x00000000);
+       if (!nv_wait(priv, 0x610490, 0x001e0000, 0x00000000)) {
+               nv_error(mast, "fini: 0x%08x\n", nv_rd32(priv, 0x610490));
+               if (suspend)
+                       return -EBUSY;
+       }
+
+       /* disable error reporting and completion notification */
+       nv_mask(priv, 0x610090, 0x00000001, 0x00000000);
+       nv_mask(priv, 0x6100a0, 0x00000001, 0x00000000);
+
+       return nv50_disp_chan_fini(&mast->base, suspend);
+}
+
+struct nv50_disp_chan_impl
+gf110_disp_core_ofuncs = {
+       .base.ctor = nv50_disp_core_ctor,
+       .base.dtor = nv50_disp_dmac_dtor,
+       .base.init = gf110_disp_core_init,
+       .base.fini = gf110_disp_core_fini,
+       .base.ntfy = nv50_disp_chan_ntfy,
+       .base.map  = nv50_disp_chan_map,
+       .base.rd32 = nv50_disp_chan_rd32,
+       .base.wr32 = nv50_disp_chan_wr32,
+       .chid = 0,
+       .attach = gf110_disp_dmac_object_attach,
+       .detach = gf110_disp_dmac_object_detach,
+};
+
+/*******************************************************************************
+ * EVO sync channel objects
+ ******************************************************************************/
+
+static const struct nv50_disp_mthd_list
+gf110_disp_base_mthd_base = {
+       .mthd = 0x0000,
+       .addr = 0x000000,
+       .data = {
+               { 0x0080, 0x661080 },
+               { 0x0084, 0x661084 },
+               { 0x0088, 0x661088 },
+               { 0x008c, 0x66108c },
+               { 0x0090, 0x661090 },
+               { 0x0094, 0x661094 },
+               { 0x00a0, 0x6610a0 },
+               { 0x00a4, 0x6610a4 },
+               { 0x00c0, 0x6610c0 },
+               { 0x00c4, 0x6610c4 },
+               { 0x00c8, 0x6610c8 },
+               { 0x00cc, 0x6610cc },
+               { 0x00e0, 0x6610e0 },
+               { 0x00e4, 0x6610e4 },
+               { 0x00e8, 0x6610e8 },
+               { 0x00ec, 0x6610ec },
+               { 0x00fc, 0x6610fc },
+               { 0x0100, 0x661100 },
+               { 0x0104, 0x661104 },
+               { 0x0108, 0x661108 },
+               { 0x010c, 0x66110c },
+               { 0x0110, 0x661110 },
+               { 0x0114, 0x661114 },
+               { 0x0118, 0x661118 },
+               { 0x011c, 0x66111c },
+               { 0x0130, 0x661130 },
+               { 0x0134, 0x661134 },
+               { 0x0138, 0x661138 },
+               { 0x013c, 0x66113c },
+               { 0x0140, 0x661140 },
+               { 0x0144, 0x661144 },
+               { 0x0148, 0x661148 },
+               { 0x014c, 0x66114c },
+               { 0x0150, 0x661150 },
+               { 0x0154, 0x661154 },
+               { 0x0158, 0x661158 },
+               { 0x015c, 0x66115c },
+               { 0x0160, 0x661160 },
+               { 0x0164, 0x661164 },
+               { 0x0168, 0x661168 },
+               { 0x016c, 0x66116c },
+               {}
+       }
+};
+
+static const struct nv50_disp_mthd_list
+gf110_disp_base_mthd_image = {
+       .mthd = 0x0400,
+       .addr = 0x000400,
+       .data = {
+               { 0x0400, 0x661400 },
+               { 0x0404, 0x661404 },
+               { 0x0408, 0x661408 },
+               { 0x040c, 0x66140c },
+               { 0x0410, 0x661410 },
+               {}
+       }
+};
+
+const struct nv50_disp_mthd_chan
+gf110_disp_base_mthd_chan = {
+       .name = "Base",
+       .addr = 0x001000,
+       .data = {
+               { "Global", 1, &gf110_disp_base_mthd_base },
+               {  "Image", 2, &gf110_disp_base_mthd_image },
+               {}
+       }
+};
+
+struct nv50_disp_chan_impl
+gf110_disp_base_ofuncs = {
+       .base.ctor = nv50_disp_base_ctor,
+       .base.dtor = nv50_disp_dmac_dtor,
+       .base.init = gf110_disp_dmac_init,
+       .base.fini = gf110_disp_dmac_fini,
+       .base.ntfy = nv50_disp_chan_ntfy,
+       .base.map  = nv50_disp_chan_map,
+       .base.rd32 = nv50_disp_chan_rd32,
+       .base.wr32 = nv50_disp_chan_wr32,
+       .chid = 1,
+       .attach = gf110_disp_dmac_object_attach,
+       .detach = gf110_disp_dmac_object_detach,
+};
+
+/*******************************************************************************
+ * EVO overlay channel objects
+ ******************************************************************************/
+
+static const struct nv50_disp_mthd_list
+gf110_disp_ovly_mthd_base = {
+       .mthd = 0x0000,
+       .data = {
+               { 0x0080, 0x665080 },
+               { 0x0084, 0x665084 },
+               { 0x0088, 0x665088 },
+               { 0x008c, 0x66508c },
+               { 0x0090, 0x665090 },
+               { 0x0094, 0x665094 },
+               { 0x00a0, 0x6650a0 },
+               { 0x00a4, 0x6650a4 },
+               { 0x00b0, 0x6650b0 },
+               { 0x00b4, 0x6650b4 },
+               { 0x00b8, 0x6650b8 },
+               { 0x00c0, 0x6650c0 },
+               { 0x00e0, 0x6650e0 },
+               { 0x00e4, 0x6650e4 },
+               { 0x00e8, 0x6650e8 },
+               { 0x0100, 0x665100 },
+               { 0x0104, 0x665104 },
+               { 0x0108, 0x665108 },
+               { 0x010c, 0x66510c },
+               { 0x0110, 0x665110 },
+               { 0x0118, 0x665118 },
+               { 0x011c, 0x66511c },
+               { 0x0120, 0x665120 },
+               { 0x0124, 0x665124 },
+               { 0x0130, 0x665130 },
+               { 0x0134, 0x665134 },
+               { 0x0138, 0x665138 },
+               { 0x013c, 0x66513c },
+               { 0x0140, 0x665140 },
+               { 0x0144, 0x665144 },
+               { 0x0148, 0x665148 },
+               { 0x014c, 0x66514c },
+               { 0x0150, 0x665150 },
+               { 0x0154, 0x665154 },
+               { 0x0158, 0x665158 },
+               { 0x015c, 0x66515c },
+               { 0x0160, 0x665160 },
+               { 0x0164, 0x665164 },
+               { 0x0168, 0x665168 },
+               { 0x016c, 0x66516c },
+               { 0x0400, 0x665400 },
+               { 0x0408, 0x665408 },
+               { 0x040c, 0x66540c },
+               { 0x0410, 0x665410 },
+               {}
+       }
+};
+
+static const struct nv50_disp_mthd_chan
+gf110_disp_ovly_mthd_chan = {
+       .name = "Overlay",
+       .addr = 0x001000,
+       .data = {
+               { "Global", 1, &gf110_disp_ovly_mthd_base },
+               {}
+       }
+};
+
+struct nv50_disp_chan_impl
+gf110_disp_ovly_ofuncs = {
+       .base.ctor = nv50_disp_ovly_ctor,
+       .base.dtor = nv50_disp_dmac_dtor,
+       .base.init = gf110_disp_dmac_init,
+       .base.fini = gf110_disp_dmac_fini,
+       .base.ntfy = nv50_disp_chan_ntfy,
+       .base.map  = nv50_disp_chan_map,
+       .base.rd32 = nv50_disp_chan_rd32,
+       .base.wr32 = nv50_disp_chan_wr32,
+       .chid = 5,
+       .attach = gf110_disp_dmac_object_attach,
+       .detach = gf110_disp_dmac_object_detach,
+};
+
+/*******************************************************************************
+ * EVO PIO channel base class
+ ******************************************************************************/
+
+static int
+gf110_disp_pioc_init(struct nvkm_object *object)
+{
+       struct nv50_disp_priv *priv = (void *)object->engine;
+       struct nv50_disp_pioc *pioc = (void *)object;
+       int chid = pioc->base.chid;
+       int ret;
+
+       ret = nv50_disp_chan_init(&pioc->base);
+       if (ret)
+               return ret;
+
+       /* enable error reporting */
+       nv_mask(priv, 0x6100a0, 0x00000001 << chid, 0x00000001 << chid);
+
+       /* activate channel */
+       nv_wr32(priv, 0x610490 + (chid * 0x10), 0x00000001);
+       if (!nv_wait(priv, 0x610490 + (chid * 0x10), 0x00030000, 0x00010000)) {
+               nv_error(pioc, "init: 0x%08x\n",
+                        nv_rd32(priv, 0x610490 + (chid * 0x10)));
+               return -EBUSY;
+       }
+
+       return 0;
+}
+
+static int
+gf110_disp_pioc_fini(struct nvkm_object *object, bool suspend)
+{
+       struct nv50_disp_priv *priv = (void *)object->engine;
+       struct nv50_disp_pioc *pioc = (void *)object;
+       int chid = pioc->base.chid;
+
+       nv_mask(priv, 0x610490 + (chid * 0x10), 0x00000001, 0x00000000);
+       if (!nv_wait(priv, 0x610490 + (chid * 0x10), 0x00030000, 0x00000000)) {
+               nv_error(pioc, "timeout: 0x%08x\n",
+                        nv_rd32(priv, 0x610490 + (chid * 0x10)));
+               if (suspend)
+                       return -EBUSY;
+       }
+
+       /* disable error reporting and completion notification */
+       nv_mask(priv, 0x610090, 0x00000001 << chid, 0x00000000);
+       nv_mask(priv, 0x6100a0, 0x00000001 << chid, 0x00000000);
+
+       return nv50_disp_chan_fini(&pioc->base, suspend);
+}
+
+/*******************************************************************************
+ * EVO immediate overlay channel objects
+ ******************************************************************************/
+
+struct nv50_disp_chan_impl
+gf110_disp_oimm_ofuncs = {
+       .base.ctor = nv50_disp_oimm_ctor,
+       .base.dtor = nv50_disp_pioc_dtor,
+       .base.init = gf110_disp_pioc_init,
+       .base.fini = gf110_disp_pioc_fini,
+       .base.ntfy = nv50_disp_chan_ntfy,
+       .base.map  = nv50_disp_chan_map,
+       .base.rd32 = nv50_disp_chan_rd32,
+       .base.wr32 = nv50_disp_chan_wr32,
+       .chid = 9,
+};
+
+/*******************************************************************************
+ * EVO cursor channel objects
+ ******************************************************************************/
+
+struct nv50_disp_chan_impl
+gf110_disp_curs_ofuncs = {
+       .base.ctor = nv50_disp_curs_ctor,
+       .base.dtor = nv50_disp_pioc_dtor,
+       .base.init = gf110_disp_pioc_init,
+       .base.fini = gf110_disp_pioc_fini,
+       .base.ntfy = nv50_disp_chan_ntfy,
+       .base.map  = nv50_disp_chan_map,
+       .base.rd32 = nv50_disp_chan_rd32,
+       .base.wr32 = nv50_disp_chan_wr32,
+       .chid = 13,
+};
+
+/*******************************************************************************
+ * Base display object
+ ******************************************************************************/
+
+int
+gf110_disp_main_scanoutpos(NV50_DISP_MTHD_V0)
+{
+       const u32 total  = nv_rd32(priv, 0x640414 + (head * 0x300));
+       const u32 blanke = nv_rd32(priv, 0x64041c + (head * 0x300));
+       const u32 blanks = nv_rd32(priv, 0x640420 + (head * 0x300));
+       union {
+               struct nv04_disp_scanoutpos_v0 v0;
+       } *args = data;
+       int ret;
+
+       nv_ioctl(object, "disp scanoutpos size %d\n", size);
+       if (nvif_unpack(args->v0, 0, 0, false)) {
+               nv_ioctl(object, "disp scanoutpos vers %d\n", args->v0.version);
+               args->v0.vblanke = (blanke & 0xffff0000) >> 16;
+               args->v0.hblanke = (blanke & 0x0000ffff);
+               args->v0.vblanks = (blanks & 0xffff0000) >> 16;
+               args->v0.hblanks = (blanks & 0x0000ffff);
+               args->v0.vtotal  = ( total & 0xffff0000) >> 16;
+               args->v0.htotal  = ( total & 0x0000ffff);
+               args->v0.time[0] = ktime_to_ns(ktime_get());
+               args->v0.vline = /* vline read locks hline */
+                       nv_rd32(priv, 0x616340 + (head * 0x800)) & 0xffff;
+               args->v0.time[1] = ktime_to_ns(ktime_get());
+               args->v0.hline =
+                       nv_rd32(priv, 0x616344 + (head * 0x800)) & 0xffff;
+       } else
+               return ret;
+
+       return 0;
+}
+
+static int
+gf110_disp_main_init(struct nvkm_object *object)
+{
+       struct nv50_disp_priv *priv = (void *)object->engine;
+       struct nv50_disp_base *base = (void *)object;
+       int ret, i;
+       u32 tmp;
+
+       ret = nvkm_parent_init(&base->base);
+       if (ret)
+               return ret;
+
+       /* The below segments of code copying values from one register to
+        * another appear to inform EVO of the display capabilities or
+        * something similar.
+        */
+
+       /* ... CRTC caps */
+       for (i = 0; i < priv->head.nr; i++) {
+               tmp = nv_rd32(priv, 0x616104 + (i * 0x800));
+               nv_wr32(priv, 0x6101b4 + (i * 0x800), tmp);
+               tmp = nv_rd32(priv, 0x616108 + (i * 0x800));
+               nv_wr32(priv, 0x6101b8 + (i * 0x800), tmp);
+               tmp = nv_rd32(priv, 0x61610c + (i * 0x800));
+               nv_wr32(priv, 0x6101bc + (i * 0x800), tmp);
+       }
+
+       /* ... DAC caps */
+       for (i = 0; i < priv->dac.nr; i++) {
+               tmp = nv_rd32(priv, 0x61a000 + (i * 0x800));
+               nv_wr32(priv, 0x6101c0 + (i * 0x800), tmp);
+       }
+
+       /* ... SOR caps */
+       for (i = 0; i < priv->sor.nr; i++) {
+               tmp = nv_rd32(priv, 0x61c000 + (i * 0x800));
+               nv_wr32(priv, 0x6301c4 + (i * 0x800), tmp);
+       }
+
+       /* steal display away from vbios, or something like that */
+       if (nv_rd32(priv, 0x6100ac) & 0x00000100) {
+               nv_wr32(priv, 0x6100ac, 0x00000100);
+               nv_mask(priv, 0x6194e8, 0x00000001, 0x00000000);
+               if (!nv_wait(priv, 0x6194e8, 0x00000002, 0x00000000)) {
+                       nv_error(priv, "timeout acquiring display\n");
+                       return -EBUSY;
+               }
+       }
+
+       /* point at display engine memory area (hash table, objects) */
+       nv_wr32(priv, 0x610010, (nv_gpuobj(object->parent)->addr >> 8) | 9);
+
+       /* enable supervisor interrupts, disable everything else */
+       nv_wr32(priv, 0x610090, 0x00000000);
+       nv_wr32(priv, 0x6100a0, 0x00000000);
+       nv_wr32(priv, 0x6100b0, 0x00000307);
+
+       /* disable underflow reporting, preventing an intermittent issue
+        * on some gk104 boards where the production vbios left this
+        * setting enabled by default.
+        *
+        * ftp://download.nvidia.com/open-gpu-doc/gk104-disable-underflow-reporting/1/gk104-disable-underflow-reporting.txt
+        */
+       for (i = 0; i < priv->head.nr; i++)
+               nv_mask(priv, 0x616308 + (i * 0x800), 0x00000111, 0x00000010);
+
+       return 0;
+}
+
+static int
+gf110_disp_main_fini(struct nvkm_object *object, bool suspend)
+{
+       struct nv50_disp_priv *priv = (void *)object->engine;
+       struct nv50_disp_base *base = (void *)object;
+
+       /* disable all interrupts */
+       nv_wr32(priv, 0x6100b0, 0x00000000);
+
+       return nvkm_parent_fini(&base->base, suspend);
+}
+
+struct nvkm_ofuncs
+gf110_disp_main_ofuncs = {
+       .ctor = nv50_disp_main_ctor,
+       .dtor = nv50_disp_main_dtor,
+       .init = gf110_disp_main_init,
+       .fini = gf110_disp_main_fini,
+       .mthd = nv50_disp_main_mthd,
+       .ntfy = nvkm_disp_ntfy,
+};
+
+static struct nvkm_oclass
+gf110_disp_main_oclass[] = {
+       { GF110_DISP, &gf110_disp_main_ofuncs },
+       {}
+};
+
+static struct nvkm_oclass
+gf110_disp_sclass[] = {
+       { GF110_DISP_CORE_CHANNEL_DMA, &gf110_disp_core_ofuncs.base },
+       { GF110_DISP_BASE_CHANNEL_DMA, &gf110_disp_base_ofuncs.base },
+       { GF110_DISP_OVERLAY_CONTROL_DMA, &gf110_disp_ovly_ofuncs.base },
+       { GF110_DISP_OVERLAY, &gf110_disp_oimm_ofuncs.base },
+       { GF110_DISP_CURSOR, &gf110_disp_curs_ofuncs.base },
+       {}
+};
+
+/*******************************************************************************
+ * Display engine implementation
+ ******************************************************************************/
+
+static void
+gf110_disp_vblank_init(struct nvkm_event *event, int type, int head)
+{
+       struct nvkm_disp *disp = container_of(event, typeof(*disp), vblank);
+       nv_mask(disp, 0x6100c0 + (head * 0x800), 0x00000001, 0x00000001);
+}
+
+static void
+gf110_disp_vblank_fini(struct nvkm_event *event, int type, int head)
+{
+       struct nvkm_disp *disp = container_of(event, typeof(*disp), vblank);
+       nv_mask(disp, 0x6100c0 + (head * 0x800), 0x00000001, 0x00000000);
+}
+
+const struct nvkm_event_func
+gf110_disp_vblank_func = {
+       .ctor = nvkm_disp_vblank_ctor,
+       .init = gf110_disp_vblank_init,
+       .fini = gf110_disp_vblank_fini,
+};
+
+static struct nvkm_output *
+exec_lookup(struct nv50_disp_priv *priv, int head, int or, u32 ctrl,
+           u32 *data, u8 *ver, u8 *hdr, u8 *cnt, u8 *len,
+           struct nvbios_outp *info)
+{
+       struct nvkm_bios *bios = nvkm_bios(priv);
+       struct nvkm_output *outp;
+       u16 mask, type;
+
+       if (or < 4) {
+               type = DCB_OUTPUT_ANALOG;
+               mask = 0;
+       } else {
+               or -= 4;
+               switch (ctrl & 0x00000f00) {
+               case 0x00000000: type = DCB_OUTPUT_LVDS; mask = 1; break;
+               case 0x00000100: type = DCB_OUTPUT_TMDS; mask = 1; break;
+               case 0x00000200: type = DCB_OUTPUT_TMDS; mask = 2; break;
+               case 0x00000500: type = DCB_OUTPUT_TMDS; mask = 3; break;
+               case 0x00000800: type = DCB_OUTPUT_DP; mask = 1; break;
+               case 0x00000900: type = DCB_OUTPUT_DP; mask = 2; break;
+               default:
+                       nv_error(priv, "unknown SOR mc 0x%08x\n", ctrl);
+                       return 0x0000;
+               }
+       }
+
+       mask  = 0x00c0 & (mask << 6);
+       mask |= 0x0001 << or;
+       mask |= 0x0100 << head;
+
+       list_for_each_entry(outp, &priv->base.outp, head) {
+               if ((outp->info.hasht & 0xff) == type &&
+                   (outp->info.hashm & mask) == mask) {
+                       *data = nvbios_outp_match(bios, outp->info.hasht,
+                                                       outp->info.hashm,
+                                                 ver, hdr, cnt, len, info);
+                       if (!*data)
+                               return NULL;
+                       return outp;
+               }
+       }
+
+       return NULL;
+}
+
+static struct nvkm_output *
+exec_script(struct nv50_disp_priv *priv, int head, int id)
+{
+       struct nvkm_bios *bios = nvkm_bios(priv);
+       struct nvkm_output *outp;
+       struct nvbios_outp info;
+       u8  ver, hdr, cnt, len;
+       u32 data, ctrl = 0;
+       int or;
+
+       for (or = 0; !(ctrl & (1 << head)) && or < 8; or++) {
+               ctrl = nv_rd32(priv, 0x640180 + (or * 0x20));
+               if (ctrl & (1 << head))
+                       break;
+       }
+
+       if (or == 8)
+               return NULL;
+
+       outp = exec_lookup(priv, head, or, ctrl, &data, &ver, &hdr, &cnt, &len, &info);
+       if (outp) {
+               struct nvbios_init init = {
+                       .subdev = nv_subdev(priv),
+                       .bios = bios,
+                       .offset = info.script[id],
+                       .outp = &outp->info,
+                       .crtc = head,
+                       .execute = 1,
+               };
+
+               nvbios_exec(&init);
+       }
+
+       return outp;
+}
+
+static struct nvkm_output *
+exec_clkcmp(struct nv50_disp_priv *priv, int head, int id, u32 pclk, u32 *conf)
+{
+       struct nvkm_bios *bios = nvkm_bios(priv);
+       struct nvkm_output *outp;
+       struct nvbios_outp info1;
+       struct nvbios_ocfg info2;
+       u8  ver, hdr, cnt, len;
+       u32 data, ctrl = 0;
+       int or;
+
+       for (or = 0; !(ctrl & (1 << head)) && or < 8; or++) {
+               ctrl = nv_rd32(priv, 0x660180 + (or * 0x20));
+               if (ctrl & (1 << head))
+                       break;
+       }
+
+       if (or == 8)
+               return NULL;
+
+       outp = exec_lookup(priv, head, or, ctrl, &data, &ver, &hdr, &cnt, &len, &info1);
+       if (!outp)
+               return NULL;
+
+       switch (outp->info.type) {
+       case DCB_OUTPUT_TMDS:
+               *conf = (ctrl & 0x00000f00) >> 8;
+               if (pclk >= 165000)
+                       *conf |= 0x0100;
+               break;
+       case DCB_OUTPUT_LVDS:
+               *conf = priv->sor.lvdsconf;
+               break;
+       case DCB_OUTPUT_DP:
+               *conf = (ctrl & 0x00000f00) >> 8;
+               break;
+       case DCB_OUTPUT_ANALOG:
+       default:
+               *conf = 0x00ff;
+               break;
+       }
+
+       data = nvbios_ocfg_match(bios, data, *conf, &ver, &hdr, &cnt, &len, &info2);
+       if (data && id < 0xff) {
+               data = nvbios_oclk_match(bios, info2.clkcmp[id], pclk);
+               if (data) {
+                       struct nvbios_init init = {
+                               .subdev = nv_subdev(priv),
+                               .bios = bios,
+                               .offset = data,
+                               .outp = &outp->info,
+                               .crtc = head,
+                               .execute = 1,
+                       };
+
+                       nvbios_exec(&init);
+               }
+       }
+
+       return outp;
+}
+
+static void
+gf110_disp_intr_unk1_0(struct nv50_disp_priv *priv, int head)
+{
+       exec_script(priv, head, 1);
+}
+
+static void
+gf110_disp_intr_unk2_0(struct nv50_disp_priv *priv, int head)
+{
+       struct nvkm_output *outp = exec_script(priv, head, 2);
+
+       /* see note in nv50_disp_intr_unk20_0() */
+       if (outp && outp->info.type == DCB_OUTPUT_DP) {
+               struct nvkm_output_dp *outpdp = (void *)outp;
+               struct nvbios_init init = {
+                       .subdev = nv_subdev(priv),
+                       .bios = nvkm_bios(priv),
+                       .outp = &outp->info,
+                       .crtc = head,
+                       .offset = outpdp->info.script[4],
+                       .execute = 1,
+               };
+
+               nvbios_exec(&init);
+               atomic_set(&outpdp->lt.done, 0);
+       }
+}
+
+static void
+gf110_disp_intr_unk2_1(struct nv50_disp_priv *priv, int head)
+{
+       struct nvkm_devinit *devinit = nvkm_devinit(priv);
+       u32 pclk = nv_rd32(priv, 0x660450 + (head * 0x300)) / 1000;
+       if (pclk)
+               devinit->pll_set(devinit, PLL_VPLL0 + head, pclk);
+       nv_wr32(priv, 0x612200 + (head * 0x800), 0x00000000);
+}
+
+static void
+gf110_disp_intr_unk2_2_tu(struct nv50_disp_priv *priv, int head,
+                         struct dcb_output *outp)
+{
+       const int or = ffs(outp->or) - 1;
+       const u32 ctrl = nv_rd32(priv, 0x660200 + (or   * 0x020));
+       const u32 conf = nv_rd32(priv, 0x660404 + (head * 0x300));
+       const s32 vactive = nv_rd32(priv, 0x660414 + (head * 0x300)) & 0xffff;
+       const s32 vblanke = nv_rd32(priv, 0x66041c + (head * 0x300)) & 0xffff;
+       const s32 vblanks = nv_rd32(priv, 0x660420 + (head * 0x300)) & 0xffff;
+       const u32 pclk = nv_rd32(priv, 0x660450 + (head * 0x300)) / 1000;
+       const u32 link = ((ctrl & 0xf00) == 0x800) ? 0 : 1;
+       const u32 hoff = (head * 0x800);
+       const u32 soff = (  or * 0x800);
+       const u32 loff = (link * 0x080) + soff;
+       const u32 symbol = 100000;
+       const u32 TU = 64;
+       u32 dpctrl = nv_rd32(priv, 0x61c10c + loff);
+       u32 clksor = nv_rd32(priv, 0x612300 + soff);
+       u32 datarate, link_nr, link_bw, bits;
+       u64 ratio, value;
+
+       link_nr  = hweight32(dpctrl & 0x000f0000);
+       link_bw  = (clksor & 0x007c0000) >> 18;
+       link_bw *= 27000;
+
+       /* symbols/hblank - algorithm taken from comments in tegra driver */
+       value = vblanke + vactive - vblanks - 7;
+       value = value * link_bw;
+       do_div(value, pclk);
+       value = value - (3 * !!(dpctrl & 0x00004000)) - (12 / link_nr);
+       nv_mask(priv, 0x616620 + hoff, 0x0000ffff, value);
+
+       /* symbols/vblank - algorithm taken from comments in tegra driver */
+       value = vblanks - vblanke - 25;
+       value = value * link_bw;
+       do_div(value, pclk);
+       value = value - ((36 / link_nr) + 3) - 1;
+       nv_mask(priv, 0x616624 + hoff, 0x00ffffff, value);
+
+       /* watermark */
+       if      ((conf & 0x3c0) == 0x180) bits = 30;
+       else if ((conf & 0x3c0) == 0x140) bits = 24;
+       else                              bits = 18;
+       datarate = (pclk * bits) / 8;
+
+       ratio  = datarate;
+       ratio *= symbol;
+       do_div(ratio, link_nr * link_bw);
+
+       value  = (symbol - ratio) * TU;
+       value *= ratio;
+       do_div(value, symbol);
+       do_div(value, symbol);
+
+       value += 5;
+       value |= 0x08000000;
+
+       nv_wr32(priv, 0x616610 + hoff, value);
+}
+
+static void
+gf110_disp_intr_unk2_2(struct nv50_disp_priv *priv, int head)
+{
+       struct nvkm_output *outp;
+       u32 pclk = nv_rd32(priv, 0x660450 + (head * 0x300)) / 1000;
+       u32 conf, addr, data;
+
+       outp = exec_clkcmp(priv, head, 0xff, pclk, &conf);
+       if (!outp)
+               return;
+
+       /* see note in nv50_disp_intr_unk20_2() */
+       if (outp->info.type == DCB_OUTPUT_DP) {
+               u32 sync = nv_rd32(priv, 0x660404 + (head * 0x300));
+               switch ((sync & 0x000003c0) >> 6) {
+               case 6: pclk = pclk * 30; break;
+               case 5: pclk = pclk * 24; break;
+               case 2:
+               default:
+                       pclk = pclk * 18;
+                       break;
+               }
+
+               if (nvkm_output_dp_train(outp, pclk, true))
+                       ERR("link not trained before attach\n");
+       } else {
+               if (priv->sor.magic)
+                       priv->sor.magic(outp);
+       }
+
+       exec_clkcmp(priv, head, 0, pclk, &conf);
+
+       if (outp->info.type == DCB_OUTPUT_ANALOG) {
+               addr = 0x612280 + (ffs(outp->info.or) - 1) * 0x800;
+               data = 0x00000000;
+       } else {
+               addr = 0x612300 + (ffs(outp->info.or) - 1) * 0x800;
+               data = (conf & 0x0100) ? 0x00000101 : 0x00000000;
+               switch (outp->info.type) {
+               case DCB_OUTPUT_TMDS:
+                       nv_mask(priv, addr, 0x007c0000, 0x00280000);
+                       break;
+               case DCB_OUTPUT_DP:
+                       gf110_disp_intr_unk2_2_tu(priv, head, &outp->info);
+                       break;
+               default:
+                       break;
+               }
+       }
+
+       nv_mask(priv, addr, 0x00000707, data);
+}
+
+static void
+gf110_disp_intr_unk4_0(struct nv50_disp_priv *priv, int head)
+{
+       u32 pclk = nv_rd32(priv, 0x660450 + (head * 0x300)) / 1000;
+       u32 conf;
+
+       exec_clkcmp(priv, head, 1, pclk, &conf);
+}
+
+void
+gf110_disp_intr_supervisor(struct work_struct *work)
+{
+       struct nv50_disp_priv *priv =
+               container_of(work, struct nv50_disp_priv, supervisor);
+       struct nv50_disp_impl *impl = (void *)nv_object(priv)->oclass;
+       u32 mask[4];
+       int head;
+
+       nv_debug(priv, "supervisor %d\n", ffs(priv->super));
+       for (head = 0; head < priv->head.nr; head++) {
+               mask[head] = nv_rd32(priv, 0x6101d4 + (head * 0x800));
+               nv_debug(priv, "head %d: 0x%08x\n", head, mask[head]);
+       }
+
+       if (priv->super & 0x00000001) {
+               nv50_disp_mthd_chan(priv, NV_DBG_DEBUG, 0, impl->mthd.core);
+               for (head = 0; head < priv->head.nr; head++) {
+                       if (!(mask[head] & 0x00001000))
+                               continue;
+                       nv_debug(priv, "supervisor 1.0 - head %d\n", head);
+                       gf110_disp_intr_unk1_0(priv, head);
+               }
+       } else
+       if (priv->super & 0x00000002) {
+               for (head = 0; head < priv->head.nr; head++) {
+                       if (!(mask[head] & 0x00001000))
+                               continue;
+                       nv_debug(priv, "supervisor 2.0 - head %d\n", head);
+                       gf110_disp_intr_unk2_0(priv, head);
+               }
+               for (head = 0; head < priv->head.nr; head++) {
+                       if (!(mask[head] & 0x00010000))
+                               continue;
+                       nv_debug(priv, "supervisor 2.1 - head %d\n", head);
+                       gf110_disp_intr_unk2_1(priv, head);
+               }
+               for (head = 0; head < priv->head.nr; head++) {
+                       if (!(mask[head] & 0x00001000))
+                               continue;
+                       nv_debug(priv, "supervisor 2.2 - head %d\n", head);
+                       gf110_disp_intr_unk2_2(priv, head);
+               }
+       } else
+       if (priv->super & 0x00000004) {
+               for (head = 0; head < priv->head.nr; head++) {
+                       if (!(mask[head] & 0x00001000))
+                               continue;
+                       nv_debug(priv, "supervisor 3.0 - head %d\n", head);
+                       gf110_disp_intr_unk4_0(priv, head);
+               }
+       }
+
+       for (head = 0; head < priv->head.nr; head++)
+               nv_wr32(priv, 0x6101d4 + (head * 0x800), 0x00000000);
+       nv_wr32(priv, 0x6101d0, 0x80000000);
+}
+
+static void
+gf110_disp_intr_error(struct nv50_disp_priv *priv, int chid)
+{
+       const struct nv50_disp_impl *impl = (void *)nv_object(priv)->oclass;
+       u32 mthd = nv_rd32(priv, 0x6101f0 + (chid * 12));
+       u32 data = nv_rd32(priv, 0x6101f4 + (chid * 12));
+       u32 unkn = nv_rd32(priv, 0x6101f8 + (chid * 12));
+
+       nv_error(priv, "chid %d mthd 0x%04x data 0x%08x "
+                      "0x%08x 0x%08x\n",
+                chid, (mthd & 0x0000ffc), data, mthd, unkn);
+
+       if (chid == 0) {
+               switch (mthd & 0xffc) {
+               case 0x0080:
+                       nv50_disp_mthd_chan(priv, NV_DBG_ERROR, chid - 0,
+                                           impl->mthd.core);
+                       break;
+               default:
+                       break;
+               }
+       } else
+       if (chid <= 4) {
+               switch (mthd & 0xffc) {
+               case 0x0080:
+                       nv50_disp_mthd_chan(priv, NV_DBG_ERROR, chid - 1,
+                                           impl->mthd.base);
+                       break;
+               default:
+                       break;
+               }
+       } else
+       if (chid <= 8) {
+               switch (mthd & 0xffc) {
+               case 0x0080:
+                       nv50_disp_mthd_chan(priv, NV_DBG_ERROR, chid - 5,
+                                           impl->mthd.ovly);
+                       break;
+               default:
+                       break;
+               }
+       }
+
+       nv_wr32(priv, 0x61009c, (1 << chid));
+       nv_wr32(priv, 0x6101f0 + (chid * 12), 0x90000000);
+}
+
+void
+gf110_disp_intr(struct nvkm_subdev *subdev)
+{
+       struct nv50_disp_priv *priv = (void *)subdev;
+       u32 intr = nv_rd32(priv, 0x610088);
+       int i;
+
+       if (intr & 0x00000001) {
+               u32 stat = nv_rd32(priv, 0x61008c);
+               while (stat) {
+                       int chid = __ffs(stat); stat &= ~(1 << chid);
+                       nv50_disp_chan_uevent_send(priv, chid);
+                       nv_wr32(priv, 0x61008c, 1 << chid);
+               }
+               intr &= ~0x00000001;
+       }
+
+       if (intr & 0x00000002) {
+               u32 stat = nv_rd32(priv, 0x61009c);
+               int chid = ffs(stat) - 1;
+               if (chid >= 0)
+                       gf110_disp_intr_error(priv, chid);
+               intr &= ~0x00000002;
+       }
+
+       if (intr & 0x00100000) {
+               u32 stat = nv_rd32(priv, 0x6100ac);
+               if (stat & 0x00000007) {
+                       priv->super = (stat & 0x00000007);
+                       schedule_work(&priv->supervisor);
+                       nv_wr32(priv, 0x6100ac, priv->super);
+                       stat &= ~0x00000007;
+               }
+
+               if (stat) {
+                       nv_info(priv, "unknown intr24 0x%08x\n", stat);
+                       nv_wr32(priv, 0x6100ac, stat);
+               }
+
+               intr &= ~0x00100000;
+       }
+
+       for (i = 0; i < priv->head.nr; i++) {
+               u32 mask = 0x01000000 << i;
+               if (mask & intr) {
+                       u32 stat = nv_rd32(priv, 0x6100bc + (i * 0x800));
+                       if (stat & 0x00000001)
+                               nvkm_disp_vblank(&priv->base, i);
+                       nv_mask(priv, 0x6100bc + (i * 0x800), 0, 0);
+                       nv_rd32(priv, 0x6100c0 + (i * 0x800));
+               }
+       }
+}
+
+static int
+gf110_disp_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+               struct nvkm_oclass *oclass, void *data, u32 size,
+               struct nvkm_object **pobject)
+{
+       struct nv50_disp_priv *priv;
+       int heads = nv_rd32(parent, 0x022448);
+       int ret;
+
+       ret = nvkm_disp_create(parent, engine, oclass, heads,
+                              "PDISP", "display", &priv);
+       *pobject = nv_object(priv);
+       if (ret)
+               return ret;
+
+       ret = nvkm_event_init(&gf110_disp_chan_uevent, 1, 17, &priv->uevent);
+       if (ret)
+               return ret;
+
+       nv_engine(priv)->sclass = gf110_disp_main_oclass;
+       nv_engine(priv)->cclass = &nv50_disp_cclass;
+       nv_subdev(priv)->intr = gf110_disp_intr;
+       INIT_WORK(&priv->supervisor, gf110_disp_intr_supervisor);
+       priv->sclass = gf110_disp_sclass;
+       priv->head.nr = heads;
+       priv->dac.nr = 3;
+       priv->sor.nr = 4;
+       priv->dac.power = nv50_dac_power;
+       priv->dac.sense = nv50_dac_sense;
+       priv->sor.power = nv50_sor_power;
+       priv->sor.hda_eld = gf110_hda_eld;
+       priv->sor.hdmi = gf110_hdmi_ctrl;
+       return 0;
+}
+
+struct nvkm_oclass *
+gf110_disp_outp_sclass[] = {
+       &gf110_sor_dp_impl.base.base,
+       NULL
+};
+
+struct nvkm_oclass *
+gf110_disp_oclass = &(struct nv50_disp_impl) {
+       .base.base.handle = NV_ENGINE(DISP, 0x90),
+       .base.base.ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = gf110_disp_ctor,
+               .dtor = _nvkm_disp_dtor,
+               .init = _nvkm_disp_init,
+               .fini = _nvkm_disp_fini,
+       },
+       .base.vblank = &gf110_disp_vblank_func,
+       .base.outp =  gf110_disp_outp_sclass,
+       .mthd.core = &gf110_disp_core_mthd_chan,
+       .mthd.base = &gf110_disp_base_mthd_chan,
+       .mthd.ovly = &gf110_disp_ovly_mthd_chan,
+       .mthd.prev = -0x020000,
+       .head.scanoutpos = gf110_disp_main_scanoutpos,
+}.base.base;
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/disp/gk104.c b/drivers/gpu/drm/nouveau/nvkm/engine/disp/gk104.c
new file mode 100644 (file)
index 0000000..6f4019a
--- /dev/null
@@ -0,0 +1,268 @@
+/*
+ * Copyright 2012 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 "nv50.h"
+
+#include <nvif/class.h>
+
+/*******************************************************************************
+ * EVO master channel object
+ ******************************************************************************/
+
+static const struct nv50_disp_mthd_list
+gk104_disp_core_mthd_head = {
+       .mthd = 0x0300,
+       .addr = 0x000300,
+       .data = {
+               { 0x0400, 0x660400 },
+               { 0x0404, 0x660404 },
+               { 0x0408, 0x660408 },
+               { 0x040c, 0x66040c },
+               { 0x0410, 0x660410 },
+               { 0x0414, 0x660414 },
+               { 0x0418, 0x660418 },
+               { 0x041c, 0x66041c },
+               { 0x0420, 0x660420 },
+               { 0x0424, 0x660424 },
+               { 0x0428, 0x660428 },
+               { 0x042c, 0x66042c },
+               { 0x0430, 0x660430 },
+               { 0x0434, 0x660434 },
+               { 0x0438, 0x660438 },
+               { 0x0440, 0x660440 },
+               { 0x0444, 0x660444 },
+               { 0x0448, 0x660448 },
+               { 0x044c, 0x66044c },
+               { 0x0450, 0x660450 },
+               { 0x0454, 0x660454 },
+               { 0x0458, 0x660458 },
+               { 0x045c, 0x66045c },
+               { 0x0460, 0x660460 },
+               { 0x0468, 0x660468 },
+               { 0x046c, 0x66046c },
+               { 0x0470, 0x660470 },
+               { 0x0474, 0x660474 },
+               { 0x047c, 0x66047c },
+               { 0x0480, 0x660480 },
+               { 0x0484, 0x660484 },
+               { 0x0488, 0x660488 },
+               { 0x048c, 0x66048c },
+               { 0x0490, 0x660490 },
+               { 0x0494, 0x660494 },
+               { 0x0498, 0x660498 },
+               { 0x04a0, 0x6604a0 },
+               { 0x04b0, 0x6604b0 },
+               { 0x04b8, 0x6604b8 },
+               { 0x04bc, 0x6604bc },
+               { 0x04c0, 0x6604c0 },
+               { 0x04c4, 0x6604c4 },
+               { 0x04c8, 0x6604c8 },
+               { 0x04d0, 0x6604d0 },
+               { 0x04d4, 0x6604d4 },
+               { 0x04e0, 0x6604e0 },
+               { 0x04e4, 0x6604e4 },
+               { 0x04e8, 0x6604e8 },
+               { 0x04ec, 0x6604ec },
+               { 0x04f0, 0x6604f0 },
+               { 0x04f4, 0x6604f4 },
+               { 0x04f8, 0x6604f8 },
+               { 0x04fc, 0x6604fc },
+               { 0x0500, 0x660500 },
+               { 0x0504, 0x660504 },
+               { 0x0508, 0x660508 },
+               { 0x050c, 0x66050c },
+               { 0x0510, 0x660510 },
+               { 0x0514, 0x660514 },
+               { 0x0518, 0x660518 },
+               { 0x051c, 0x66051c },
+               { 0x0520, 0x660520 },
+               { 0x0524, 0x660524 },
+               { 0x052c, 0x66052c },
+               { 0x0530, 0x660530 },
+               { 0x054c, 0x66054c },
+               { 0x0550, 0x660550 },
+               { 0x0554, 0x660554 },
+               { 0x0558, 0x660558 },
+               { 0x055c, 0x66055c },
+               {}
+       }
+};
+
+const struct nv50_disp_mthd_chan
+gk104_disp_core_mthd_chan = {
+       .name = "Core",
+       .addr = 0x000000,
+       .data = {
+               { "Global", 1, &gf110_disp_core_mthd_base },
+               {    "DAC", 3, &gf110_disp_core_mthd_dac  },
+               {    "SOR", 8, &gf110_disp_core_mthd_sor  },
+               {   "PIOR", 4, &gf110_disp_core_mthd_pior },
+               {   "HEAD", 4, &gk104_disp_core_mthd_head },
+               {}
+       }
+};
+
+/*******************************************************************************
+ * EVO overlay channel objects
+ ******************************************************************************/
+
+static const struct nv50_disp_mthd_list
+gk104_disp_ovly_mthd_base = {
+       .mthd = 0x0000,
+       .data = {
+               { 0x0080, 0x665080 },
+               { 0x0084, 0x665084 },
+               { 0x0088, 0x665088 },
+               { 0x008c, 0x66508c },
+               { 0x0090, 0x665090 },
+               { 0x0094, 0x665094 },
+               { 0x00a0, 0x6650a0 },
+               { 0x00a4, 0x6650a4 },
+               { 0x00b0, 0x6650b0 },
+               { 0x00b4, 0x6650b4 },
+               { 0x00b8, 0x6650b8 },
+               { 0x00c0, 0x6650c0 },
+               { 0x00c4, 0x6650c4 },
+               { 0x00e0, 0x6650e0 },
+               { 0x00e4, 0x6650e4 },
+               { 0x00e8, 0x6650e8 },
+               { 0x0100, 0x665100 },
+               { 0x0104, 0x665104 },
+               { 0x0108, 0x665108 },
+               { 0x010c, 0x66510c },
+               { 0x0110, 0x665110 },
+               { 0x0118, 0x665118 },
+               { 0x011c, 0x66511c },
+               { 0x0120, 0x665120 },
+               { 0x0124, 0x665124 },
+               { 0x0130, 0x665130 },
+               { 0x0134, 0x665134 },
+               { 0x0138, 0x665138 },
+               { 0x013c, 0x66513c },
+               { 0x0140, 0x665140 },
+               { 0x0144, 0x665144 },
+               { 0x0148, 0x665148 },
+               { 0x014c, 0x66514c },
+               { 0x0150, 0x665150 },
+               { 0x0154, 0x665154 },
+               { 0x0158, 0x665158 },
+               { 0x015c, 0x66515c },
+               { 0x0160, 0x665160 },
+               { 0x0164, 0x665164 },
+               { 0x0168, 0x665168 },
+               { 0x016c, 0x66516c },
+               { 0x0400, 0x665400 },
+               { 0x0404, 0x665404 },
+               { 0x0408, 0x665408 },
+               { 0x040c, 0x66540c },
+               { 0x0410, 0x665410 },
+               {}
+       }
+};
+
+const struct nv50_disp_mthd_chan
+gk104_disp_ovly_mthd_chan = {
+       .name = "Overlay",
+       .addr = 0x001000,
+       .data = {
+               { "Global", 1, &gk104_disp_ovly_mthd_base },
+               {}
+       }
+};
+
+/*******************************************************************************
+ * Base display object
+ ******************************************************************************/
+
+static struct nvkm_oclass
+gk104_disp_sclass[] = {
+       { GK104_DISP_CORE_CHANNEL_DMA, &gf110_disp_core_ofuncs.base },
+       { GK104_DISP_BASE_CHANNEL_DMA, &gf110_disp_base_ofuncs.base },
+       { GK104_DISP_OVERLAY_CONTROL_DMA, &gf110_disp_ovly_ofuncs.base },
+       { GK104_DISP_OVERLAY, &gf110_disp_oimm_ofuncs.base },
+       { GK104_DISP_CURSOR, &gf110_disp_curs_ofuncs.base },
+       {}
+};
+
+static struct nvkm_oclass
+gk104_disp_main_oclass[] = {
+       { GK104_DISP, &gf110_disp_main_ofuncs },
+       {}
+};
+
+/*******************************************************************************
+ * Display engine implementation
+ ******************************************************************************/
+
+static int
+gk104_disp_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+               struct nvkm_oclass *oclass, void *data, u32 size,
+               struct nvkm_object **pobject)
+{
+       struct nv50_disp_priv *priv;
+       int heads = nv_rd32(parent, 0x022448);
+       int ret;
+
+       ret = nvkm_disp_create(parent, engine, oclass, heads,
+                              "PDISP", "display", &priv);
+       *pobject = nv_object(priv);
+       if (ret)
+               return ret;
+
+       ret = nvkm_event_init(&gf110_disp_chan_uevent, 1, 17, &priv->uevent);
+       if (ret)
+               return ret;
+
+       nv_engine(priv)->sclass = gk104_disp_main_oclass;
+       nv_engine(priv)->cclass = &nv50_disp_cclass;
+       nv_subdev(priv)->intr = gf110_disp_intr;
+       INIT_WORK(&priv->supervisor, gf110_disp_intr_supervisor);
+       priv->sclass = gk104_disp_sclass;
+       priv->head.nr = heads;
+       priv->dac.nr = 3;
+       priv->sor.nr = 4;
+       priv->dac.power = nv50_dac_power;
+       priv->dac.sense = nv50_dac_sense;
+       priv->sor.power = nv50_sor_power;
+       priv->sor.hda_eld = gf110_hda_eld;
+       priv->sor.hdmi = gk104_hdmi_ctrl;
+       return 0;
+}
+
+struct nvkm_oclass *
+gk104_disp_oclass = &(struct nv50_disp_impl) {
+       .base.base.handle = NV_ENGINE(DISP, 0x91),
+       .base.base.ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = gk104_disp_ctor,
+               .dtor = _nvkm_disp_dtor,
+               .init = _nvkm_disp_init,
+               .fini = _nvkm_disp_fini,
+       },
+       .base.vblank = &gf110_disp_vblank_func,
+       .base.outp =  gf110_disp_outp_sclass,
+       .mthd.core = &gk104_disp_core_mthd_chan,
+       .mthd.base = &gf110_disp_base_mthd_chan,
+       .mthd.ovly = &gk104_disp_ovly_mthd_chan,
+       .mthd.prev = -0x020000,
+       .head.scanoutpos = gf110_disp_main_scanoutpos,
+}.base.base;
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/disp/gk110.c b/drivers/gpu/drm/nouveau/nvkm/engine/disp/gk110.c
new file mode 100644 (file)
index 0000000..daa4b46
--- /dev/null
@@ -0,0 +1,103 @@
+/*
+ * Copyright 2012 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 "nv50.h"
+
+#include <nvif/class.h>
+
+/*******************************************************************************
+ * Base display object
+ ******************************************************************************/
+
+static struct nvkm_oclass
+gk110_disp_sclass[] = {
+       { GK110_DISP_CORE_CHANNEL_DMA, &gf110_disp_core_ofuncs.base },
+       { GK110_DISP_BASE_CHANNEL_DMA, &gf110_disp_base_ofuncs.base },
+       { GK104_DISP_OVERLAY_CONTROL_DMA, &gf110_disp_ovly_ofuncs.base },
+       { GK104_DISP_OVERLAY, &gf110_disp_oimm_ofuncs.base },
+       { GK104_DISP_CURSOR, &gf110_disp_curs_ofuncs.base },
+       {}
+};
+
+static struct nvkm_oclass
+gk110_disp_main_oclass[] = {
+       { GK110_DISP, &gf110_disp_main_ofuncs },
+       {}
+};
+
+/*******************************************************************************
+ * Display engine implementation
+ ******************************************************************************/
+
+static int
+gk110_disp_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+               struct nvkm_oclass *oclass, void *data, u32 size,
+               struct nvkm_object **pobject)
+{
+       struct nv50_disp_priv *priv;
+       int heads = nv_rd32(parent, 0x022448);
+       int ret;
+
+       ret = nvkm_disp_create(parent, engine, oclass, heads,
+                              "PDISP", "display", &priv);
+       *pobject = nv_object(priv);
+       if (ret)
+               return ret;
+
+       ret = nvkm_event_init(&gf110_disp_chan_uevent, 1, 17, &priv->uevent);
+       if (ret)
+               return ret;
+
+       nv_engine(priv)->sclass = gk110_disp_main_oclass;
+       nv_engine(priv)->cclass = &nv50_disp_cclass;
+       nv_subdev(priv)->intr = gf110_disp_intr;
+       INIT_WORK(&priv->supervisor, gf110_disp_intr_supervisor);
+       priv->sclass = gk110_disp_sclass;
+       priv->head.nr = heads;
+       priv->dac.nr = 3;
+       priv->sor.nr = 4;
+       priv->dac.power = nv50_dac_power;
+       priv->dac.sense = nv50_dac_sense;
+       priv->sor.power = nv50_sor_power;
+       priv->sor.hda_eld = gf110_hda_eld;
+       priv->sor.hdmi = gk104_hdmi_ctrl;
+       return 0;
+}
+
+struct nvkm_oclass *
+gk110_disp_oclass = &(struct nv50_disp_impl) {
+       .base.base.handle = NV_ENGINE(DISP, 0x92),
+       .base.base.ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = gk110_disp_ctor,
+               .dtor = _nvkm_disp_dtor,
+               .init = _nvkm_disp_init,
+               .fini = _nvkm_disp_fini,
+       },
+       .base.vblank = &gf110_disp_vblank_func,
+       .base.outp =  gf110_disp_outp_sclass,
+       .mthd.core = &gk104_disp_core_mthd_chan,
+       .mthd.base = &gf110_disp_base_mthd_chan,
+       .mthd.ovly = &gk104_disp_ovly_mthd_chan,
+       .mthd.prev = -0x020000,
+       .head.scanoutpos = gf110_disp_main_scanoutpos,
+}.base.base;
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/disp/gm107.c b/drivers/gpu/drm/nouveau/nvkm/engine/disp/gm107.c
new file mode 100644 (file)
index 0000000..881cc94
--- /dev/null
@@ -0,0 +1,103 @@
+/*
+ * Copyright 2012 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 "nv50.h"
+
+#include <nvif/class.h>
+
+/*******************************************************************************
+ * Base display object
+ ******************************************************************************/
+
+static struct nvkm_oclass
+gm107_disp_sclass[] = {
+       { GM107_DISP_CORE_CHANNEL_DMA, &gf110_disp_core_ofuncs.base },
+       { GK110_DISP_BASE_CHANNEL_DMA, &gf110_disp_base_ofuncs.base },
+       { GK104_DISP_OVERLAY_CONTROL_DMA, &gf110_disp_ovly_ofuncs.base },
+       { GK104_DISP_OVERLAY, &gf110_disp_oimm_ofuncs.base },
+       { GK104_DISP_CURSOR, &gf110_disp_curs_ofuncs.base },
+       {}
+};
+
+static struct nvkm_oclass
+gm107_disp_main_oclass[] = {
+       { GM107_DISP, &gf110_disp_main_ofuncs },
+       {}
+};
+
+/*******************************************************************************
+ * Display engine implementation
+ ******************************************************************************/
+
+static int
+gm107_disp_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+               struct nvkm_oclass *oclass, void *data, u32 size,
+               struct nvkm_object **pobject)
+{
+       struct nv50_disp_priv *priv;
+       int heads = nv_rd32(parent, 0x022448);
+       int ret;
+
+       ret = nvkm_disp_create(parent, engine, oclass, heads,
+                              "PDISP", "display", &priv);
+       *pobject = nv_object(priv);
+       if (ret)
+               return ret;
+
+       ret = nvkm_event_init(&gf110_disp_chan_uevent, 1, 17, &priv->uevent);
+       if (ret)
+               return ret;
+
+       nv_engine(priv)->sclass = gm107_disp_main_oclass;
+       nv_engine(priv)->cclass = &nv50_disp_cclass;
+       nv_subdev(priv)->intr = gf110_disp_intr;
+       INIT_WORK(&priv->supervisor, gf110_disp_intr_supervisor);
+       priv->sclass = gm107_disp_sclass;
+       priv->head.nr = heads;
+       priv->dac.nr = 3;
+       priv->sor.nr = 4;
+       priv->dac.power = nv50_dac_power;
+       priv->dac.sense = nv50_dac_sense;
+       priv->sor.power = nv50_sor_power;
+       priv->sor.hda_eld = gf110_hda_eld;
+       priv->sor.hdmi = gk104_hdmi_ctrl;
+       return 0;
+}
+
+struct nvkm_oclass *
+gm107_disp_oclass = &(struct nv50_disp_impl) {
+       .base.base.handle = NV_ENGINE(DISP, 0x07),
+       .base.base.ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = gm107_disp_ctor,
+               .dtor = _nvkm_disp_dtor,
+               .init = _nvkm_disp_init,
+               .fini = _nvkm_disp_fini,
+       },
+       .base.vblank = &gf110_disp_vblank_func,
+       .base.outp =  gf110_disp_outp_sclass,
+       .mthd.core = &gk104_disp_core_mthd_chan,
+       .mthd.base = &gf110_disp_base_mthd_chan,
+       .mthd.ovly = &gk104_disp_ovly_mthd_chan,
+       .mthd.prev = -0x020000,
+       .head.scanoutpos = gf110_disp_main_scanoutpos,
+}.base.base;
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/disp/gm204.c b/drivers/gpu/drm/nouveau/nvkm/engine/disp/gm204.c
new file mode 100644 (file)
index 0000000..67004f8
--- /dev/null
@@ -0,0 +1,111 @@
+/*
+ * Copyright 2012 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 "nv50.h"
+#include "outpdp.h"
+
+#include <nvif/class.h>
+
+/*******************************************************************************
+ * Base display object
+ ******************************************************************************/
+
+static struct nvkm_oclass
+gm204_disp_sclass[] = {
+       { GM204_DISP_CORE_CHANNEL_DMA, &gf110_disp_core_ofuncs.base },
+       { GK110_DISP_BASE_CHANNEL_DMA, &gf110_disp_base_ofuncs.base },
+       { GK104_DISP_OVERLAY_CONTROL_DMA, &gf110_disp_ovly_ofuncs.base },
+       { GK104_DISP_OVERLAY, &gf110_disp_oimm_ofuncs.base },
+       { GK104_DISP_CURSOR, &gf110_disp_curs_ofuncs.base },
+       {}
+};
+
+static struct nvkm_oclass
+gm204_disp_main_oclass[] = {
+       { GM204_DISP, &gf110_disp_main_ofuncs },
+       {}
+};
+
+/*******************************************************************************
+ * Display engine implementation
+ ******************************************************************************/
+
+static int
+gm204_disp_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+               struct nvkm_oclass *oclass, void *data, u32 size,
+               struct nvkm_object **pobject)
+{
+       struct nv50_disp_priv *priv;
+       int heads = nv_rd32(parent, 0x022448);
+       int ret;
+
+       ret = nvkm_disp_create(parent, engine, oclass, heads,
+                              "PDISP", "display", &priv);
+       *pobject = nv_object(priv);
+       if (ret)
+               return ret;
+
+       ret = nvkm_event_init(&gf110_disp_chan_uevent, 1, 17, &priv->uevent);
+       if (ret)
+               return ret;
+
+       nv_engine(priv)->sclass = gm204_disp_main_oclass;
+       nv_engine(priv)->cclass = &nv50_disp_cclass;
+       nv_subdev(priv)->intr = gf110_disp_intr;
+       INIT_WORK(&priv->supervisor, gf110_disp_intr_supervisor);
+       priv->sclass = gm204_disp_sclass;
+       priv->head.nr = heads;
+       priv->dac.nr = 3;
+       priv->sor.nr = 4;
+       priv->dac.power = nv50_dac_power;
+       priv->dac.sense = nv50_dac_sense;
+       priv->sor.power = nv50_sor_power;
+       priv->sor.hda_eld = gf110_hda_eld;
+       priv->sor.hdmi = gf110_hdmi_ctrl;
+       priv->sor.magic = gm204_sor_magic;
+       return 0;
+}
+
+struct nvkm_oclass *
+gm204_disp_outp_sclass[] = {
+       &gm204_sor_dp_impl.base.base,
+       NULL
+};
+
+struct nvkm_oclass *
+gm204_disp_oclass = &(struct nv50_disp_impl) {
+       .base.base.handle = NV_ENGINE(DISP, 0x07),
+       .base.base.ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = gm204_disp_ctor,
+               .dtor = _nvkm_disp_dtor,
+               .init = _nvkm_disp_init,
+               .fini = _nvkm_disp_fini,
+       },
+       .base.vblank = &gf110_disp_vblank_func,
+       .base.outp =  gm204_disp_outp_sclass,
+       .mthd.core = &gk104_disp_core_mthd_chan,
+       .mthd.base = &gf110_disp_base_mthd_chan,
+       .mthd.ovly = &gk104_disp_ovly_mthd_chan,
+       .mthd.prev = -0x020000,
+       .head.scanoutpos = gf110_disp_main_scanoutpos,
+}.base.base;
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/disp/gt200.c b/drivers/gpu/drm/nouveau/nvkm/engine/disp/gt200.c
new file mode 100644 (file)
index 0000000..a453072
--- /dev/null
@@ -0,0 +1,148 @@
+/*
+ * Copyright 2012 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 "nv50.h"
+
+#include <nvif/class.h>
+
+/*******************************************************************************
+ * EVO overlay channel objects
+ ******************************************************************************/
+
+static const struct nv50_disp_mthd_list
+gt200_disp_ovly_mthd_base = {
+       .mthd = 0x0000,
+       .addr = 0x000000,
+       .data = {
+               { 0x0080, 0x000000 },
+               { 0x0084, 0x6109a0 },
+               { 0x0088, 0x6109c0 },
+               { 0x008c, 0x6109c8 },
+               { 0x0090, 0x6109b4 },
+               { 0x0094, 0x610970 },
+               { 0x00a0, 0x610998 },
+               { 0x00a4, 0x610964 },
+               { 0x00b0, 0x610c98 },
+               { 0x00b4, 0x610ca4 },
+               { 0x00b8, 0x610cac },
+               { 0x00c0, 0x610958 },
+               { 0x00e0, 0x6109a8 },
+               { 0x00e4, 0x6109d0 },
+               { 0x00e8, 0x6109d8 },
+               { 0x0100, 0x61094c },
+               { 0x0104, 0x610984 },
+               { 0x0108, 0x61098c },
+               { 0x0800, 0x6109f8 },
+               { 0x0808, 0x610a08 },
+               { 0x080c, 0x610a10 },
+               { 0x0810, 0x610a00 },
+               {}
+       }
+};
+
+static const struct nv50_disp_mthd_chan
+gt200_disp_ovly_mthd_chan = {
+       .name = "Overlay",
+       .addr = 0x000540,
+       .data = {
+               { "Global", 1, &gt200_disp_ovly_mthd_base },
+               {}
+       }
+};
+
+/*******************************************************************************
+ * Base display object
+ ******************************************************************************/
+
+static struct nvkm_oclass
+gt200_disp_sclass[] = {
+       { GT200_DISP_CORE_CHANNEL_DMA, &nv50_disp_core_ofuncs.base },
+       { GT200_DISP_BASE_CHANNEL_DMA, &nv50_disp_base_ofuncs.base },
+       { GT200_DISP_OVERLAY_CHANNEL_DMA, &nv50_disp_ovly_ofuncs.base },
+       { G82_DISP_OVERLAY, &nv50_disp_oimm_ofuncs.base },
+       { G82_DISP_CURSOR, &nv50_disp_curs_ofuncs.base },
+       {}
+};
+
+static struct nvkm_oclass
+gt200_disp_main_oclass[] = {
+       { GT200_DISP, &nv50_disp_main_ofuncs },
+       {}
+};
+
+/*******************************************************************************
+ * Display engine implementation
+ ******************************************************************************/
+
+static int
+gt200_disp_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+               struct nvkm_oclass *oclass, void *data, u32 size,
+               struct nvkm_object **pobject)
+{
+       struct nv50_disp_priv *priv;
+       int ret;
+
+       ret = nvkm_disp_create(parent, engine, oclass, 2, "PDISP",
+                              "display", &priv);
+       *pobject = nv_object(priv);
+       if (ret)
+               return ret;
+
+       ret = nvkm_event_init(&nv50_disp_chan_uevent, 1, 9, &priv->uevent);
+       if (ret)
+               return ret;
+
+       nv_engine(priv)->sclass = gt200_disp_main_oclass;
+       nv_engine(priv)->cclass = &nv50_disp_cclass;
+       nv_subdev(priv)->intr = nv50_disp_intr;
+       INIT_WORK(&priv->supervisor, nv50_disp_intr_supervisor);
+       priv->sclass = gt200_disp_sclass;
+       priv->head.nr = 2;
+       priv->dac.nr = 3;
+       priv->sor.nr = 2;
+       priv->pior.nr = 3;
+       priv->dac.power = nv50_dac_power;
+       priv->dac.sense = nv50_dac_sense;
+       priv->sor.power = nv50_sor_power;
+       priv->sor.hdmi = g84_hdmi_ctrl;
+       priv->pior.power = nv50_pior_power;
+       return 0;
+}
+
+struct nvkm_oclass *
+gt200_disp_oclass = &(struct nv50_disp_impl) {
+       .base.base.handle = NV_ENGINE(DISP, 0x83),
+       .base.base.ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = gt200_disp_ctor,
+               .dtor = _nvkm_disp_dtor,
+               .init = _nvkm_disp_init,
+               .fini = _nvkm_disp_fini,
+       },
+       .base.vblank = &nv50_disp_vblank_func,
+       .base.outp =  nv50_disp_outp_sclass,
+       .mthd.core = &g84_disp_core_mthd_chan,
+       .mthd.base = &g84_disp_base_mthd_chan,
+       .mthd.ovly = &gt200_disp_ovly_mthd_chan,
+       .mthd.prev = 0x000004,
+       .head.scanoutpos = nv50_disp_main_scanoutpos,
+}.base.base;
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/disp/gt215.c b/drivers/gpu/drm/nouveau/nvkm/engine/disp/gt215.c
new file mode 100644 (file)
index 0000000..55f0d3a
--- /dev/null
@@ -0,0 +1,104 @@
+/*
+ * Copyright 2012 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 "nv50.h"
+
+#include <nvif/class.h>
+
+/*******************************************************************************
+ * Base display object
+ ******************************************************************************/
+
+static struct nvkm_oclass
+gt215_disp_sclass[] = {
+       { GT214_DISP_CORE_CHANNEL_DMA, &nv50_disp_core_ofuncs.base },
+       { GT214_DISP_BASE_CHANNEL_DMA, &nv50_disp_base_ofuncs.base },
+       { GT214_DISP_OVERLAY_CHANNEL_DMA, &nv50_disp_ovly_ofuncs.base },
+       { GT214_DISP_OVERLAY, &nv50_disp_oimm_ofuncs.base },
+       { GT214_DISP_CURSOR, &nv50_disp_curs_ofuncs.base },
+       {}
+};
+
+static struct nvkm_oclass
+gt215_disp_main_oclass[] = {
+       { GT214_DISP, &nv50_disp_main_ofuncs },
+       {}
+};
+
+/*******************************************************************************
+ * Display engine implementation
+ ******************************************************************************/
+
+static int
+gt215_disp_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+               struct nvkm_oclass *oclass, void *data, u32 size,
+               struct nvkm_object **pobject)
+{
+       struct nv50_disp_priv *priv;
+       int ret;
+
+       ret = nvkm_disp_create(parent, engine, oclass, 2, "PDISP",
+                              "display", &priv);
+       *pobject = nv_object(priv);
+       if (ret)
+               return ret;
+
+       ret = nvkm_event_init(&nv50_disp_chan_uevent, 1, 9, &priv->uevent);
+       if (ret)
+               return ret;
+
+       nv_engine(priv)->sclass = gt215_disp_main_oclass;
+       nv_engine(priv)->cclass = &nv50_disp_cclass;
+       nv_subdev(priv)->intr = nv50_disp_intr;
+       INIT_WORK(&priv->supervisor, nv50_disp_intr_supervisor);
+       priv->sclass = gt215_disp_sclass;
+       priv->head.nr = 2;
+       priv->dac.nr = 3;
+       priv->sor.nr = 4;
+       priv->pior.nr = 3;
+       priv->dac.power = nv50_dac_power;
+       priv->dac.sense = nv50_dac_sense;
+       priv->sor.power = nv50_sor_power;
+       priv->sor.hda_eld = gt215_hda_eld;
+       priv->sor.hdmi = gt215_hdmi_ctrl;
+       priv->pior.power = nv50_pior_power;
+       return 0;
+}
+
+struct nvkm_oclass *
+gt215_disp_oclass = &(struct nv50_disp_impl) {
+       .base.base.handle = NV_ENGINE(DISP, 0x85),
+       .base.base.ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = gt215_disp_ctor,
+               .dtor = _nvkm_disp_dtor,
+               .init = _nvkm_disp_init,
+               .fini = _nvkm_disp_fini,
+       },
+       .base.vblank = &nv50_disp_vblank_func,
+       .base.outp =  g94_disp_outp_sclass,
+       .mthd.core = &g94_disp_core_mthd_chan,
+       .mthd.base = &g84_disp_base_mthd_chan,
+       .mthd.ovly = &g84_disp_ovly_mthd_chan,
+       .mthd.prev = 0x000004,
+       .head.scanoutpos = nv50_disp_main_scanoutpos,
+}.base.base;
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/disp/hdagf110.c b/drivers/gpu/drm/nouveau/nvkm/engine/disp/hdagf110.c
new file mode 100644 (file)
index 0000000..b9813d2
--- /dev/null
@@ -0,0 +1,73 @@
+/*
+ * Copyright 2012 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 "nv50.h"
+#include "outp.h"
+
+#include <core/client.h>
+#include <subdev/bios.h>
+#include <subdev/bios/dcb.h>
+#include <subdev/timer.h>
+
+#include <nvif/class.h>
+#include <nvif/unpack.h>
+
+int
+gf110_hda_eld(NV50_DISP_MTHD_V1)
+{
+       union {
+               struct nv50_disp_sor_hda_eld_v0 v0;
+       } *args = data;
+       const u32 soff = outp->or * 0x030;
+       const u32 hoff = head * 0x800;
+       int ret, i;
+
+       nv_ioctl(object, "disp sor hda eld size %d\n", size);
+       if (nvif_unpack(args->v0, 0, 0, true)) {
+               nv_ioctl(object, "disp sor hda eld vers %d\n", args->v0.version);
+               if (size > 0x60)
+                       return -E2BIG;
+       } else
+               return ret;
+
+       if (size && args->v0.data[0]) {
+               if (outp->info.type == DCB_OUTPUT_DP) {
+                       nv_mask(priv, 0x616618 + hoff, 0x8000000c, 0x80000001);
+                       nv_wait(priv, 0x616618 + hoff, 0x80000000, 0x00000000);
+               }
+               nv_mask(priv, 0x616548 + hoff, 0x00000070, 0x00000000);
+               for (i = 0; i < size; i++)
+                       nv_wr32(priv, 0x10ec00 + soff, (i << 8) | args->v0.data[i]);
+               for (; i < 0x60; i++)
+                       nv_wr32(priv, 0x10ec00 + soff, (i << 8));
+               nv_mask(priv, 0x10ec10 + soff, 0x80000003, 0x80000003);
+       } else {
+               if (outp->info.type == DCB_OUTPUT_DP) {
+                       nv_mask(priv, 0x616618 + hoff, 0x80000001, 0x80000000);
+                       nv_wait(priv, 0x616618 + hoff, 0x80000000, 0x00000000);
+               }
+               nv_mask(priv, 0x10ec10 + soff, 0x80000003, 0x80000000 | !!size);
+       }
+
+       return 0;
+}
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/disp/hdagt215.c b/drivers/gpu/drm/nouveau/nvkm/engine/disp/hdagt215.c
new file mode 100644 (file)
index 0000000..891d1e7
--- /dev/null
@@ -0,0 +1,69 @@
+/*
+ * Copyright 2012 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 "nv50.h"
+#include "outp.h"
+
+#include <core/client.h>
+#include <subdev/timer.h>
+
+#include <nvif/class.h>
+#include <nvif/unpack.h>
+
+int
+gt215_hda_eld(NV50_DISP_MTHD_V1)
+{
+       union {
+               struct nv50_disp_sor_hda_eld_v0 v0;
+       } *args = data;
+       const u32 soff = outp->or * 0x800;
+       int ret, i;
+
+       nv_ioctl(object, "disp sor hda eld size %d\n", size);
+       if (nvif_unpack(args->v0, 0, 0, true)) {
+               nv_ioctl(object, "disp sor hda eld vers %d\n", args->v0.version);
+               if (size > 0x60)
+                       return -E2BIG;
+       } else
+               return ret;
+
+       if (size && args->v0.data[0]) {
+               if (outp->info.type == DCB_OUTPUT_DP) {
+                       nv_mask(priv, 0x61c1e0 + soff, 0x8000000d, 0x80000001);
+                       nv_wait(priv, 0x61c1e0 + soff, 0x80000000, 0x00000000);
+               }
+               for (i = 0; i < size; i++)
+                       nv_wr32(priv, 0x61c440 + soff, (i << 8) | args->v0.data[0]);
+               for (; i < 0x60; i++)
+                       nv_wr32(priv, 0x61c440 + soff, (i << 8));
+               nv_mask(priv, 0x61c448 + soff, 0x80000003, 0x80000003);
+       } else {
+               if (outp->info.type == DCB_OUTPUT_DP) {
+                       nv_mask(priv, 0x61c1e0 + soff, 0x80000001, 0x80000000);
+                       nv_wait(priv, 0x61c1e0 + soff, 0x80000000, 0x00000000);
+               }
+               nv_mask(priv, 0x61c448 + soff, 0x80000003, 0x80000000 | !!size);
+       }
+
+       return 0;
+}
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/disp/hdmig84.c b/drivers/gpu/drm/nouveau/nvkm/engine/disp/hdmig84.c
new file mode 100644 (file)
index 0000000..621cb0b
--- /dev/null
@@ -0,0 +1,91 @@
+/*
+ * Copyright 2012 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 "nv50.h"
+
+#include <core/client.h>
+
+#include <nvif/class.h>
+#include <nvif/unpack.h>
+
+int
+g84_hdmi_ctrl(NV50_DISP_MTHD_V1)
+{
+       const u32 hoff = (head * 0x800);
+       union {
+               struct nv50_disp_sor_hdmi_pwr_v0 v0;
+       } *args = data;
+       u32 ctrl;
+       int ret;
+
+       nv_ioctl(object, "disp sor hdmi ctrl size %d\n", size);
+       if (nvif_unpack(args->v0, 0, 0, false)) {
+               nv_ioctl(object, "disp sor hdmi ctrl vers %d state %d "
+                                "max_ac_packet %d rekey %d\n",
+                        args->v0.version, args->v0.state,
+                        args->v0.max_ac_packet, args->v0.rekey);
+               if (args->v0.max_ac_packet > 0x1f || args->v0.rekey > 0x7f)
+                       return -EINVAL;
+               ctrl  = 0x40000000 * !!args->v0.state;
+               ctrl |= args->v0.max_ac_packet << 16;
+               ctrl |= args->v0.rekey;
+               ctrl |= 0x1f000000; /* ??? */
+       } else
+               return ret;
+
+       if (!(ctrl & 0x40000000)) {
+               nv_mask(priv, 0x6165a4 + hoff, 0x40000000, 0x00000000);
+               nv_mask(priv, 0x616520 + hoff, 0x00000001, 0x00000000);
+               nv_mask(priv, 0x616500 + hoff, 0x00000001, 0x00000000);
+               return 0;
+       }
+
+       /* AVI InfoFrame */
+       nv_mask(priv, 0x616520 + hoff, 0x00000001, 0x00000000);
+       nv_wr32(priv, 0x616528 + hoff, 0x000d0282);
+       nv_wr32(priv, 0x61652c + hoff, 0x0000006f);
+       nv_wr32(priv, 0x616530 + hoff, 0x00000000);
+       nv_wr32(priv, 0x616534 + hoff, 0x00000000);
+       nv_wr32(priv, 0x616538 + hoff, 0x00000000);
+       nv_mask(priv, 0x616520 + hoff, 0x00000001, 0x00000001);
+
+       /* Audio InfoFrame */
+       nv_mask(priv, 0x616500 + hoff, 0x00000001, 0x00000000);
+       nv_wr32(priv, 0x616508 + hoff, 0x000a0184);
+       nv_wr32(priv, 0x61650c + hoff, 0x00000071);
+       nv_wr32(priv, 0x616510 + hoff, 0x00000000);
+       nv_mask(priv, 0x616500 + hoff, 0x00000001, 0x00000001);
+
+       nv_mask(priv, 0x6165d0 + hoff, 0x00070001, 0x00010001); /* SPARE, HW_CTS */
+       nv_mask(priv, 0x616568 + hoff, 0x00010101, 0x00000000); /* ACR_CTRL, ?? */
+       nv_mask(priv, 0x616578 + hoff, 0x80000000, 0x80000000); /* ACR_0441_ENABLE */
+
+       /* ??? */
+       nv_mask(priv, 0x61733c, 0x00100000, 0x00100000); /* RESETF */
+       nv_mask(priv, 0x61733c, 0x10000000, 0x10000000); /* LOOKUP_EN */
+       nv_mask(priv, 0x61733c, 0x00100000, 0x00000000); /* !RESETF */
+
+       /* HDMI_CTRL */
+       nv_mask(priv, 0x6165a4 + hoff, 0x5f1f007f, ctrl);
+       return 0;
+}
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/disp/hdmigf110.c b/drivers/gpu/drm/nouveau/nvkm/engine/disp/hdmigf110.c
new file mode 100644 (file)
index 0000000..c284490
--- /dev/null
@@ -0,0 +1,79 @@
+/*
+ * Copyright 2012 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 "nv50.h"
+
+#include <core/client.h>
+
+#include <nvif/class.h>
+#include <nvif/unpack.h>
+
+int
+gf110_hdmi_ctrl(NV50_DISP_MTHD_V1)
+{
+       const u32 hoff = (head * 0x800);
+       union {
+               struct nv50_disp_sor_hdmi_pwr_v0 v0;
+       } *args = data;
+       u32 ctrl;
+       int ret;
+
+       nv_ioctl(object, "disp sor hdmi ctrl size %d\n", size);
+       if (nvif_unpack(args->v0, 0, 0, false)) {
+               nv_ioctl(object, "disp sor hdmi ctrl vers %d state %d "
+                                "max_ac_packet %d rekey %d\n",
+                        args->v0.version, args->v0.state,
+                        args->v0.max_ac_packet, args->v0.rekey);
+               if (args->v0.max_ac_packet > 0x1f || args->v0.rekey > 0x7f)
+                       return -EINVAL;
+               ctrl  = 0x40000000 * !!args->v0.state;
+               ctrl |= args->v0.max_ac_packet << 16;
+               ctrl |= args->v0.rekey;
+       } else
+               return ret;
+
+       if (!(ctrl & 0x40000000)) {
+               nv_mask(priv, 0x616798 + hoff, 0x40000000, 0x00000000);
+               nv_mask(priv, 0x6167a4 + hoff, 0x00000001, 0x00000000);
+               nv_mask(priv, 0x616714 + hoff, 0x00000001, 0x00000000);
+               return 0;
+       }
+
+       /* AVI InfoFrame */
+       nv_mask(priv, 0x616714 + hoff, 0x00000001, 0x00000000);
+       nv_wr32(priv, 0x61671c + hoff, 0x000d0282);
+       nv_wr32(priv, 0x616720 + hoff, 0x0000006f);
+       nv_wr32(priv, 0x616724 + hoff, 0x00000000);
+       nv_wr32(priv, 0x616728 + hoff, 0x00000000);
+       nv_wr32(priv, 0x61672c + hoff, 0x00000000);
+       nv_mask(priv, 0x616714 + hoff, 0x00000001, 0x00000001);
+
+       /* ??? InfoFrame? */
+       nv_mask(priv, 0x6167a4 + hoff, 0x00000001, 0x00000000);
+       nv_wr32(priv, 0x6167ac + hoff, 0x00000010);
+       nv_mask(priv, 0x6167a4 + hoff, 0x00000001, 0x00000001);
+
+       /* HDMI_CTRL */
+       nv_mask(priv, 0x616798 + hoff, 0x401f007f, ctrl);
+       return 0;
+}
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/disp/hdmigk104.c b/drivers/gpu/drm/nouveau/nvkm/engine/disp/hdmigk104.c
new file mode 100644 (file)
index 0000000..ca34ff8
--- /dev/null
@@ -0,0 +1,83 @@
+/*
+ * Copyright 2014 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 "nv50.h"
+
+#include <core/client.h>
+
+#include <nvif/class.h>
+#include <nvif/unpack.h>
+
+int
+gk104_hdmi_ctrl(NV50_DISP_MTHD_V1)
+{
+       const u32 hoff = (head * 0x800);
+       const u32 hdmi = (head * 0x400);
+       union {
+               struct nv50_disp_sor_hdmi_pwr_v0 v0;
+       } *args = data;
+       u32 ctrl;
+       int ret;
+
+       nv_ioctl(object, "disp sor hdmi ctrl size %d\n", size);
+       if (nvif_unpack(args->v0, 0, 0, false)) {
+               nv_ioctl(object, "disp sor hdmi ctrl vers %d state %d "
+                                "max_ac_packet %d rekey %d\n",
+                        args->v0.version, args->v0.state,
+                        args->v0.max_ac_packet, args->v0.rekey);
+               if (args->v0.max_ac_packet > 0x1f || args->v0.rekey > 0x7f)
+                       return -EINVAL;
+               ctrl  = 0x40000000 * !!args->v0.state;
+               ctrl |= args->v0.max_ac_packet << 16;
+               ctrl |= args->v0.rekey;
+       } else
+               return ret;
+
+       if (!(ctrl & 0x40000000)) {
+               nv_mask(priv, 0x616798 + hoff, 0x40000000, 0x00000000);
+               nv_mask(priv, 0x6900c0 + hdmi, 0x00000001, 0x00000000);
+               nv_mask(priv, 0x690000 + hdmi, 0x00000001, 0x00000000);
+               return 0;
+       }
+
+       /* AVI InfoFrame */
+       nv_mask(priv, 0x690000 + hdmi, 0x00000001, 0x00000000);
+       nv_wr32(priv, 0x690008 + hdmi, 0x000d0282);
+       nv_wr32(priv, 0x69000c + hdmi, 0x0000006f);
+       nv_wr32(priv, 0x690010 + hdmi, 0x00000000);
+       nv_wr32(priv, 0x690014 + hdmi, 0x00000000);
+       nv_wr32(priv, 0x690018 + hdmi, 0x00000000);
+       nv_mask(priv, 0x690000 + hdmi, 0x00000001, 0x00000001);
+
+       /* ??? InfoFrame? */
+       nv_mask(priv, 0x6900c0 + hdmi, 0x00000001, 0x00000000);
+       nv_wr32(priv, 0x6900cc + hdmi, 0x00000010);
+       nv_mask(priv, 0x6900c0 + hdmi, 0x00000001, 0x00000001);
+
+       /* ??? */
+       nv_wr32(priv, 0x690080 + hdmi, 0x82000000);
+
+       /* HDMI_CTRL */
+       nv_mask(priv, 0x616798 + hoff, 0x401f007f, ctrl);
+       return 0;
+}
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/disp/hdmigt215.c b/drivers/gpu/drm/nouveau/nvkm/engine/disp/hdmigt215.c
new file mode 100644 (file)
index 0000000..b641c16
--- /dev/null
@@ -0,0 +1,92 @@
+/*
+ * Copyright 2012 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 "nv50.h"
+#include "outp.h"
+
+#include <core/client.h>
+
+#include <nvif/class.h>
+#include <nvif/unpack.h>
+
+int
+gt215_hdmi_ctrl(NV50_DISP_MTHD_V1)
+{
+       const u32 soff = outp->or * 0x800;
+       union {
+               struct nv50_disp_sor_hdmi_pwr_v0 v0;
+       } *args = data;
+       u32 ctrl;
+       int ret;
+
+       nv_ioctl(object, "disp sor hdmi ctrl size %d\n", size);
+       if (nvif_unpack(args->v0, 0, 0, false)) {
+               nv_ioctl(object, "disp sor hdmi ctrl vers %d state %d "
+                                "max_ac_packet %d rekey %d\n",
+                        args->v0.version, args->v0.state,
+                        args->v0.max_ac_packet, args->v0.rekey);
+               if (args->v0.max_ac_packet > 0x1f || args->v0.rekey > 0x7f)
+                       return -EINVAL;
+               ctrl  = 0x40000000 * !!args->v0.state;
+               ctrl |= args->v0.max_ac_packet << 16;
+               ctrl |= args->v0.rekey;
+               ctrl |= 0x1f000000; /* ??? */
+       } else
+               return ret;
+
+       if (!(ctrl & 0x40000000)) {
+               nv_mask(priv, 0x61c5a4 + soff, 0x40000000, 0x00000000);
+               nv_mask(priv, 0x61c520 + soff, 0x00000001, 0x00000000);
+               nv_mask(priv, 0x61c500 + soff, 0x00000001, 0x00000000);
+               return 0;
+       }
+
+       /* AVI InfoFrame */
+       nv_mask(priv, 0x61c520 + soff, 0x00000001, 0x00000000);
+       nv_wr32(priv, 0x61c528 + soff, 0x000d0282);
+       nv_wr32(priv, 0x61c52c + soff, 0x0000006f);
+       nv_wr32(priv, 0x61c530 + soff, 0x00000000);
+       nv_wr32(priv, 0x61c534 + soff, 0x00000000);
+       nv_wr32(priv, 0x61c538 + soff, 0x00000000);
+       nv_mask(priv, 0x61c520 + soff, 0x00000001, 0x00000001);
+
+       /* Audio InfoFrame */
+       nv_mask(priv, 0x61c500 + soff, 0x00000001, 0x00000000);
+       nv_wr32(priv, 0x61c508 + soff, 0x000a0184);
+       nv_wr32(priv, 0x61c50c + soff, 0x00000071);
+       nv_wr32(priv, 0x61c510 + soff, 0x00000000);
+       nv_mask(priv, 0x61c500 + soff, 0x00000001, 0x00000001);
+
+       nv_mask(priv, 0x61c5d0 + soff, 0x00070001, 0x00010001); /* SPARE, HW_CTS */
+       nv_mask(priv, 0x61c568 + soff, 0x00010101, 0x00000000); /* ACR_CTRL, ?? */
+       nv_mask(priv, 0x61c578 + soff, 0x80000000, 0x80000000); /* ACR_0441_ENABLE */
+
+       /* ??? */
+       nv_mask(priv, 0x61733c, 0x00100000, 0x00100000); /* RESETF */
+       nv_mask(priv, 0x61733c, 0x10000000, 0x10000000); /* LOOKUP_EN */
+       nv_mask(priv, 0x61733c, 0x00100000, 0x00000000); /* !RESETF */
+
+       /* HDMI_CTRL */
+       nv_mask(priv, 0x61c5a4 + soff, 0x5f1f007f, ctrl);
+       return 0;
+}
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/disp/nv04.c b/drivers/gpu/drm/nouveau/nvkm/engine/disp/nv04.c
new file mode 100644 (file)
index 0000000..ff09b26
--- /dev/null
@@ -0,0 +1,205 @@
+/*
+ * Copyright 2012 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 "priv.h"
+
+#include <core/client.h>
+#include <core/device.h>
+
+#include <nvif/class.h>
+#include <nvif/unpack.h>
+
+struct nv04_disp_priv {
+       struct nvkm_disp base;
+};
+
+static int
+nv04_disp_scanoutpos(struct nvkm_object *object, struct nv04_disp_priv *priv,
+                    void *data, u32 size, int head)
+{
+       const u32 hoff = head * 0x2000;
+       union {
+               struct nv04_disp_scanoutpos_v0 v0;
+       } *args = data;
+       u32 line;
+       int ret;
+
+       nv_ioctl(object, "disp scanoutpos size %d\n", size);
+       if (nvif_unpack(args->v0, 0, 0, false)) {
+               nv_ioctl(object, "disp scanoutpos vers %d\n", args->v0.version);
+               args->v0.vblanks = nv_rd32(priv, 0x680800 + hoff) & 0xffff;
+               args->v0.vtotal  = nv_rd32(priv, 0x680804 + hoff) & 0xffff;
+               args->v0.vblanke = args->v0.vtotal - 1;
+
+               args->v0.hblanks = nv_rd32(priv, 0x680820 + hoff) & 0xffff;
+               args->v0.htotal  = nv_rd32(priv, 0x680824 + hoff) & 0xffff;
+               args->v0.hblanke = args->v0.htotal - 1;
+
+               /*
+                * If output is vga instead of digital then vtotal/htotal is
+                * invalid so we have to give up and trigger the timestamping
+                * fallback in the drm core.
+                */
+               if (!args->v0.vtotal || !args->v0.htotal)
+                       return -ENOTSUPP;
+
+               args->v0.time[0] = ktime_to_ns(ktime_get());
+               line = nv_rd32(priv, 0x600868 + hoff);
+               args->v0.time[1] = ktime_to_ns(ktime_get());
+               args->v0.hline = (line & 0xffff0000) >> 16;
+               args->v0.vline = (line & 0x0000ffff);
+       } else
+               return ret;
+
+       return 0;
+}
+
+static int
+nv04_disp_mthd(struct nvkm_object *object, u32 mthd, void *data, u32 size)
+{
+       union {
+               struct nv04_disp_mthd_v0 v0;
+       } *args = data;
+       struct nv04_disp_priv *priv = (void *)object->engine;
+       int head, ret;
+
+       nv_ioctl(object, "disp mthd size %d\n", size);
+       if (nvif_unpack(args->v0, 0, 0, true)) {
+               nv_ioctl(object, "disp mthd vers %d mthd %02x head %d\n",
+                        args->v0.version, args->v0.method, args->v0.head);
+               mthd = args->v0.method;
+               head = args->v0.head;
+       } else
+               return ret;
+
+       if (head < 0 || head >= 2)
+               return -ENXIO;
+
+       switch (mthd) {
+       case NV04_DISP_SCANOUTPOS:
+               return nv04_disp_scanoutpos(object, priv, data, size, head);
+       default:
+               break;
+       }
+
+       return -EINVAL;
+}
+
+static struct nvkm_ofuncs
+nv04_disp_ofuncs = {
+       .ctor = _nvkm_object_ctor,
+       .dtor = nvkm_object_destroy,
+       .init = nvkm_object_init,
+       .fini = nvkm_object_fini,
+       .mthd = nv04_disp_mthd,
+       .ntfy = nvkm_disp_ntfy,
+};
+
+static struct nvkm_oclass
+nv04_disp_sclass[] = {
+       { NV04_DISP, &nv04_disp_ofuncs },
+       {},
+};
+
+/*******************************************************************************
+ * Display engine implementation
+ ******************************************************************************/
+
+static void
+nv04_disp_vblank_init(struct nvkm_event *event, int type, int head)
+{
+       struct nvkm_disp *disp = container_of(event, typeof(*disp), vblank);
+       nv_wr32(disp, 0x600140 + (head * 0x2000) , 0x00000001);
+}
+
+static void
+nv04_disp_vblank_fini(struct nvkm_event *event, int type, int head)
+{
+       struct nvkm_disp *disp = container_of(event, typeof(*disp), vblank);
+       nv_wr32(disp, 0x600140 + (head * 0x2000) , 0x00000000);
+}
+
+static const struct nvkm_event_func
+nv04_disp_vblank_func = {
+       .ctor = nvkm_disp_vblank_ctor,
+       .init = nv04_disp_vblank_init,
+       .fini = nv04_disp_vblank_fini,
+};
+
+static void
+nv04_disp_intr(struct nvkm_subdev *subdev)
+{
+       struct nv04_disp_priv *priv = (void *)subdev;
+       u32 crtc0 = nv_rd32(priv, 0x600100);
+       u32 crtc1 = nv_rd32(priv, 0x602100);
+       u32 pvideo;
+
+       if (crtc0 & 0x00000001) {
+               nvkm_disp_vblank(&priv->base, 0);
+               nv_wr32(priv, 0x600100, 0x00000001);
+       }
+
+       if (crtc1 & 0x00000001) {
+               nvkm_disp_vblank(&priv->base, 1);
+               nv_wr32(priv, 0x602100, 0x00000001);
+       }
+
+       if (nv_device(priv)->chipset >= 0x10 &&
+           nv_device(priv)->chipset <= 0x40) {
+               pvideo = nv_rd32(priv, 0x8100);
+               if (pvideo & ~0x11)
+                       nv_info(priv, "PVIDEO intr: %08x\n", pvideo);
+               nv_wr32(priv, 0x8100, pvideo);
+       }
+}
+
+static int
+nv04_disp_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+              struct nvkm_oclass *oclass, void *data, u32 size,
+              struct nvkm_object **pobject)
+{
+       struct nv04_disp_priv *priv;
+       int ret;
+
+       ret = nvkm_disp_create(parent, engine, oclass, 2, "DISPLAY",
+                              "display", &priv);
+       *pobject = nv_object(priv);
+       if (ret)
+               return ret;
+
+       nv_engine(priv)->sclass = nv04_disp_sclass;
+       nv_subdev(priv)->intr = nv04_disp_intr;
+       return 0;
+}
+
+struct nvkm_oclass *
+nv04_disp_oclass = &(struct nvkm_disp_impl) {
+       .base.handle = NV_ENGINE(DISP, 0x04),
+       .base.ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = nv04_disp_ctor,
+               .dtor = _nvkm_disp_dtor,
+               .init = _nvkm_disp_init,
+               .fini = _nvkm_disp_fini,
+       },
+       .vblank = &nv04_disp_vblank_func,
+}.base;
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/disp/nv50.c b/drivers/gpu/drm/nouveau/nvkm/engine/disp/nv50.c
new file mode 100644 (file)
index 0000000..84ade81
--- /dev/null
@@ -0,0 +1,2019 @@
+/*
+ * Copyright 2012 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 "nv50.h"
+#include "outp.h"
+#include "outpdp.h"
+
+#include <core/client.h>
+#include <core/device.h>
+#include <core/engctx.h>
+#include <core/enum.h>
+#include <core/handle.h>
+#include <core/ramht.h>
+#include <engine/dmaobj.h>
+#include <subdev/bios.h>
+#include <subdev/bios/dcb.h>
+#include <subdev/bios/disp.h>
+#include <subdev/bios/init.h>
+#include <subdev/bios/pll.h>
+#include <subdev/devinit.h>
+#include <subdev/fb.h>
+#include <subdev/timer.h>
+
+#include <nvif/class.h>
+#include <nvif/event.h>
+#include <nvif/unpack.h>
+
+/*******************************************************************************
+ * EVO channel base class
+ ******************************************************************************/
+
+static int
+nv50_disp_chan_create_(struct nvkm_object *parent,
+                      struct nvkm_object *engine,
+                      struct nvkm_oclass *oclass, int head,
+                      int length, void **pobject)
+{
+       const struct nv50_disp_chan_impl *impl = (void *)oclass->ofuncs;
+       struct nv50_disp_base *base = (void *)parent;
+       struct nv50_disp_chan *chan;
+       int chid = impl->chid + head;
+       int ret;
+
+       if (base->chan & (1 << chid))
+               return -EBUSY;
+       base->chan |= (1 << chid);
+
+       ret = nvkm_namedb_create_(parent, engine, oclass, 0, NULL,
+                                 (1ULL << NVDEV_ENGINE_DMAOBJ),
+                                 length, pobject);
+       chan = *pobject;
+       if (ret)
+               return ret;
+       chan->chid = chid;
+
+       nv_parent(chan)->object_attach = impl->attach;
+       nv_parent(chan)->object_detach = impl->detach;
+       return 0;
+}
+
+static void
+nv50_disp_chan_destroy(struct nv50_disp_chan *chan)
+{
+       struct nv50_disp_base *base = (void *)nv_object(chan)->parent;
+       base->chan &= ~(1 << chan->chid);
+       nvkm_namedb_destroy(&chan->base);
+}
+
+static void
+nv50_disp_chan_uevent_fini(struct nvkm_event *event, int type, int index)
+{
+       struct nv50_disp_priv *priv = container_of(event, typeof(*priv), uevent);
+       nv_mask(priv, 0x610028, 0x00000001 << index, 0x00000000 << index);
+       nv_wr32(priv, 0x610020, 0x00000001 << index);
+}
+
+static void
+nv50_disp_chan_uevent_init(struct nvkm_event *event, int types, int index)
+{
+       struct nv50_disp_priv *priv = container_of(event, typeof(*priv), uevent);
+       nv_wr32(priv, 0x610020, 0x00000001 << index);
+       nv_mask(priv, 0x610028, 0x00000001 << index, 0x00000001 << index);
+}
+
+void
+nv50_disp_chan_uevent_send(struct nv50_disp_priv *priv, int chid)
+{
+       struct nvif_notify_uevent_rep {
+       } rep;
+
+       nvkm_event_send(&priv->uevent, 1, chid, &rep, sizeof(rep));
+}
+
+int
+nv50_disp_chan_uevent_ctor(struct nvkm_object *object, void *data, u32 size,
+                          struct nvkm_notify *notify)
+{
+       struct nv50_disp_dmac *dmac = (void *)object;
+       union {
+               struct nvif_notify_uevent_req none;
+       } *args = data;
+       int ret;
+
+       if (nvif_unvers(args->none)) {
+               notify->size  = sizeof(struct nvif_notify_uevent_rep);
+               notify->types = 1;
+               notify->index = dmac->base.chid;
+               return 0;
+       }
+
+       return ret;
+}
+
+const struct nvkm_event_func
+nv50_disp_chan_uevent = {
+       .ctor = nv50_disp_chan_uevent_ctor,
+       .init = nv50_disp_chan_uevent_init,
+       .fini = nv50_disp_chan_uevent_fini,
+};
+
+int
+nv50_disp_chan_ntfy(struct nvkm_object *object, u32 type,
+                   struct nvkm_event **pevent)
+{
+       struct nv50_disp_priv *priv = (void *)object->engine;
+       switch (type) {
+       case NV50_DISP_CORE_CHANNEL_DMA_V0_NTFY_UEVENT:
+               *pevent = &priv->uevent;
+               return 0;
+       default:
+               break;
+       }
+       return -EINVAL;
+}
+
+int
+nv50_disp_chan_map(struct nvkm_object *object, u64 *addr, u32 *size)
+{
+       struct nv50_disp_chan *chan = (void *)object;
+       *addr = nv_device_resource_start(nv_device(object), 0) +
+               0x640000 + (chan->chid * 0x1000);
+       *size = 0x001000;
+       return 0;
+}
+
+u32
+nv50_disp_chan_rd32(struct nvkm_object *object, u64 addr)
+{
+       struct nv50_disp_priv *priv = (void *)object->engine;
+       struct nv50_disp_chan *chan = (void *)object;
+       return nv_rd32(priv, 0x640000 + (chan->chid * 0x1000) + addr);
+}
+
+void
+nv50_disp_chan_wr32(struct nvkm_object *object, u64 addr, u32 data)
+{
+       struct nv50_disp_priv *priv = (void *)object->engine;
+       struct nv50_disp_chan *chan = (void *)object;
+       nv_wr32(priv, 0x640000 + (chan->chid * 0x1000) + addr, data);
+}
+
+/*******************************************************************************
+ * EVO DMA channel base class
+ ******************************************************************************/
+
+static int
+nv50_disp_dmac_object_attach(struct nvkm_object *parent,
+                            struct nvkm_object *object, u32 name)
+{
+       struct nv50_disp_base *base = (void *)parent->parent;
+       struct nv50_disp_chan *chan = (void *)parent;
+       u32 addr = nv_gpuobj(object)->node->offset;
+       u32 chid = chan->chid;
+       u32 data = (chid << 28) | (addr << 10) | chid;
+       return nvkm_ramht_insert(base->ramht, chid, name, data);
+}
+
+static void
+nv50_disp_dmac_object_detach(struct nvkm_object *parent, int cookie)
+{
+       struct nv50_disp_base *base = (void *)parent->parent;
+       nvkm_ramht_remove(base->ramht, cookie);
+}
+
+static int
+nv50_disp_dmac_create_(struct nvkm_object *parent,
+                      struct nvkm_object *engine,
+                      struct nvkm_oclass *oclass, u32 pushbuf, int head,
+                      int length, void **pobject)
+{
+       struct nv50_disp_dmac *dmac;
+       int ret;
+
+       ret = nv50_disp_chan_create_(parent, engine, oclass, head,
+                                    length, pobject);
+       dmac = *pobject;
+       if (ret)
+               return ret;
+
+       dmac->pushdma = (void *)nvkm_handle_ref(parent, pushbuf);
+       if (!dmac->pushdma)
+               return -ENOENT;
+
+       switch (nv_mclass(dmac->pushdma)) {
+       case 0x0002:
+       case 0x003d:
+               if (dmac->pushdma->limit - dmac->pushdma->start != 0xfff)
+                       return -EINVAL;
+
+               switch (dmac->pushdma->target) {
+               case NV_MEM_TARGET_VRAM:
+                       dmac->push = 0x00000000 | dmac->pushdma->start >> 8;
+                       break;
+               case NV_MEM_TARGET_PCI_NOSNOOP:
+                       dmac->push = 0x00000003 | dmac->pushdma->start >> 8;
+                       break;
+               default:
+                       return -EINVAL;
+               }
+               break;
+       default:
+               return -EINVAL;
+       }
+
+       return 0;
+}
+
+void
+nv50_disp_dmac_dtor(struct nvkm_object *object)
+{
+       struct nv50_disp_dmac *dmac = (void *)object;
+       nvkm_object_ref(NULL, (struct nvkm_object **)&dmac->pushdma);
+       nv50_disp_chan_destroy(&dmac->base);
+}
+
+static int
+nv50_disp_dmac_init(struct nvkm_object *object)
+{
+       struct nv50_disp_priv *priv = (void *)object->engine;
+       struct nv50_disp_dmac *dmac = (void *)object;
+       int chid = dmac->base.chid;
+       int ret;
+
+       ret = nv50_disp_chan_init(&dmac->base);
+       if (ret)
+               return ret;
+
+       /* enable error reporting */
+       nv_mask(priv, 0x610028, 0x00010000 << chid, 0x00010000 << chid);
+
+       /* initialise channel for dma command submission */
+       nv_wr32(priv, 0x610204 + (chid * 0x0010), dmac->push);
+       nv_wr32(priv, 0x610208 + (chid * 0x0010), 0x00010000);
+       nv_wr32(priv, 0x61020c + (chid * 0x0010), chid);
+       nv_mask(priv, 0x610200 + (chid * 0x0010), 0x00000010, 0x00000010);
+       nv_wr32(priv, 0x640000 + (chid * 0x1000), 0x00000000);
+       nv_wr32(priv, 0x610200 + (chid * 0x0010), 0x00000013);
+
+       /* wait for it to go inactive */
+       if (!nv_wait(priv, 0x610200 + (chid * 0x10), 0x80000000, 0x00000000)) {
+               nv_error(dmac, "init timeout, 0x%08x\n",
+                        nv_rd32(priv, 0x610200 + (chid * 0x10)));
+               return -EBUSY;
+       }
+
+       return 0;
+}
+
+static int
+nv50_disp_dmac_fini(struct nvkm_object *object, bool suspend)
+{
+       struct nv50_disp_priv *priv = (void *)object->engine;
+       struct nv50_disp_dmac *dmac = (void *)object;
+       int chid = dmac->base.chid;
+
+       /* deactivate channel */
+       nv_mask(priv, 0x610200 + (chid * 0x0010), 0x00001010, 0x00001000);
+       nv_mask(priv, 0x610200 + (chid * 0x0010), 0x00000003, 0x00000000);
+       if (!nv_wait(priv, 0x610200 + (chid * 0x10), 0x001e0000, 0x00000000)) {
+               nv_error(dmac, "fini timeout, 0x%08x\n",
+                        nv_rd32(priv, 0x610200 + (chid * 0x10)));
+               if (suspend)
+                       return -EBUSY;
+       }
+
+       /* disable error reporting and completion notifications */
+       nv_mask(priv, 0x610028, 0x00010001 << chid, 0x00000000 << chid);
+
+       return nv50_disp_chan_fini(&dmac->base, suspend);
+}
+
+/*******************************************************************************
+ * EVO master channel object
+ ******************************************************************************/
+
+static void
+nv50_disp_mthd_list(struct nv50_disp_priv *priv, int debug, u32 base, int c,
+                   const struct nv50_disp_mthd_list *list, int inst)
+{
+       struct nvkm_object *disp = nv_object(priv);
+       int i;
+
+       for (i = 0; list->data[i].mthd; i++) {
+               if (list->data[i].addr) {
+                       u32 next = nv_rd32(priv, list->data[i].addr + base + 0);
+                       u32 prev = nv_rd32(priv, list->data[i].addr + base + c);
+                       u32 mthd = list->data[i].mthd + (list->mthd * inst);
+                       const char *name = list->data[i].name;
+                       char mods[16];
+
+                       if (prev != next)
+                               snprintf(mods, sizeof(mods), "-> 0x%08x", next);
+                       else
+                               snprintf(mods, sizeof(mods), "%13c", ' ');
+
+                       nv_printk_(disp, debug, "\t0x%04x: 0x%08x %s%s%s\n",
+                                  mthd, prev, mods, name ? " // " : "",
+                                  name ? name : "");
+               }
+       }
+}
+
+void
+nv50_disp_mthd_chan(struct nv50_disp_priv *priv, int debug, int head,
+                   const struct nv50_disp_mthd_chan *chan)
+{
+       struct nvkm_object *disp = nv_object(priv);
+       const struct nv50_disp_impl *impl = (void *)disp->oclass;
+       const struct nv50_disp_mthd_list *list;
+       int i, j;
+
+       if (debug > nv_subdev(priv)->debug)
+               return;
+
+       for (i = 0; (list = chan->data[i].mthd) != NULL; i++) {
+               u32 base = head * chan->addr;
+               for (j = 0; j < chan->data[i].nr; j++, base += list->addr) {
+                       const char *cname = chan->name;
+                       const char *sname = "";
+                       char cname_[16], sname_[16];
+
+                       if (chan->addr) {
+                               snprintf(cname_, sizeof(cname_), "%s %d",
+                                        chan->name, head);
+                               cname = cname_;
+                       }
+
+                       if (chan->data[i].nr > 1) {
+                               snprintf(sname_, sizeof(sname_), " - %s %d",
+                                        chan->data[i].name, j);
+                               sname = sname_;
+                       }
+
+                       nv_printk_(disp, debug, "%s%s:\n", cname, sname);
+                       nv50_disp_mthd_list(priv, debug, base, impl->mthd.prev,
+                                           list, j);
+               }
+       }
+}
+
+const struct nv50_disp_mthd_list
+nv50_disp_core_mthd_base = {
+       .mthd = 0x0000,
+       .addr = 0x000000,
+       .data = {
+               { 0x0080, 0x000000 },
+               { 0x0084, 0x610bb8 },
+               { 0x0088, 0x610b9c },
+               { 0x008c, 0x000000 },
+               {}
+       }
+};
+
+static const struct nv50_disp_mthd_list
+nv50_disp_core_mthd_dac = {
+       .mthd = 0x0080,
+       .addr = 0x000008,
+       .data = {
+               { 0x0400, 0x610b58 },
+               { 0x0404, 0x610bdc },
+               { 0x0420, 0x610828 },
+               {}
+       }
+};
+
+const struct nv50_disp_mthd_list
+nv50_disp_core_mthd_sor = {
+       .mthd = 0x0040,
+       .addr = 0x000008,
+       .data = {
+               { 0x0600, 0x610b70 },
+               {}
+       }
+};
+
+const struct nv50_disp_mthd_list
+nv50_disp_core_mthd_pior = {
+       .mthd = 0x0040,
+       .addr = 0x000008,
+       .data = {
+               { 0x0700, 0x610b80 },
+               {}
+       }
+};
+
+static const struct nv50_disp_mthd_list
+nv50_disp_core_mthd_head = {
+       .mthd = 0x0400,
+       .addr = 0x000540,
+       .data = {
+               { 0x0800, 0x610ad8 },
+               { 0x0804, 0x610ad0 },
+               { 0x0808, 0x610a48 },
+               { 0x080c, 0x610a78 },
+               { 0x0810, 0x610ac0 },
+               { 0x0814, 0x610af8 },
+               { 0x0818, 0x610b00 },
+               { 0x081c, 0x610ae8 },
+               { 0x0820, 0x610af0 },
+               { 0x0824, 0x610b08 },
+               { 0x0828, 0x610b10 },
+               { 0x082c, 0x610a68 },
+               { 0x0830, 0x610a60 },
+               { 0x0834, 0x000000 },
+               { 0x0838, 0x610a40 },
+               { 0x0840, 0x610a24 },
+               { 0x0844, 0x610a2c },
+               { 0x0848, 0x610aa8 },
+               { 0x084c, 0x610ab0 },
+               { 0x0860, 0x610a84 },
+               { 0x0864, 0x610a90 },
+               { 0x0868, 0x610b18 },
+               { 0x086c, 0x610b20 },
+               { 0x0870, 0x610ac8 },
+               { 0x0874, 0x610a38 },
+               { 0x0880, 0x610a58 },
+               { 0x0884, 0x610a9c },
+               { 0x08a0, 0x610a70 },
+               { 0x08a4, 0x610a50 },
+               { 0x08a8, 0x610ae0 },
+               { 0x08c0, 0x610b28 },
+               { 0x08c4, 0x610b30 },
+               { 0x08c8, 0x610b40 },
+               { 0x08d4, 0x610b38 },
+               { 0x08d8, 0x610b48 },
+               { 0x08dc, 0x610b50 },
+               { 0x0900, 0x610a18 },
+               { 0x0904, 0x610ab8 },
+               {}
+       }
+};
+
+static const struct nv50_disp_mthd_chan
+nv50_disp_core_mthd_chan = {
+       .name = "Core",
+       .addr = 0x000000,
+       .data = {
+               { "Global", 1, &nv50_disp_core_mthd_base },
+               {    "DAC", 3, &nv50_disp_core_mthd_dac  },
+               {    "SOR", 2, &nv50_disp_core_mthd_sor  },
+               {   "PIOR", 3, &nv50_disp_core_mthd_pior },
+               {   "HEAD", 2, &nv50_disp_core_mthd_head },
+               {}
+       }
+};
+
+int
+nv50_disp_core_ctor(struct nvkm_object *parent,
+                   struct nvkm_object *engine,
+                   struct nvkm_oclass *oclass, void *data, u32 size,
+                   struct nvkm_object **pobject)
+{
+       union {
+               struct nv50_disp_core_channel_dma_v0 v0;
+       } *args = data;
+       struct nv50_disp_dmac *mast;
+       int ret;
+
+       nv_ioctl(parent, "create disp core channel dma size %d\n", size);
+       if (nvif_unpack(args->v0, 0, 0, false)) {
+               nv_ioctl(parent, "create disp core channel dma vers %d "
+                                "pushbuf %08x\n",
+                        args->v0.version, args->v0.pushbuf);
+       } else
+               return ret;
+
+       ret = nv50_disp_dmac_create_(parent, engine, oclass, args->v0.pushbuf,
+                                    0, sizeof(*mast), (void **)&mast);
+       *pobject = nv_object(mast);
+       if (ret)
+               return ret;
+
+       return 0;
+}
+
+static int
+nv50_disp_core_init(struct nvkm_object *object)
+{
+       struct nv50_disp_priv *priv = (void *)object->engine;
+       struct nv50_disp_dmac *mast = (void *)object;
+       int ret;
+
+       ret = nv50_disp_chan_init(&mast->base);
+       if (ret)
+               return ret;
+
+       /* enable error reporting */
+       nv_mask(priv, 0x610028, 0x00010000, 0x00010000);
+
+       /* attempt to unstick channel from some unknown state */
+       if ((nv_rd32(priv, 0x610200) & 0x009f0000) == 0x00020000)
+               nv_mask(priv, 0x610200, 0x00800000, 0x00800000);
+       if ((nv_rd32(priv, 0x610200) & 0x003f0000) == 0x00030000)
+               nv_mask(priv, 0x610200, 0x00600000, 0x00600000);
+
+       /* initialise channel for dma command submission */
+       nv_wr32(priv, 0x610204, mast->push);
+       nv_wr32(priv, 0x610208, 0x00010000);
+       nv_wr32(priv, 0x61020c, 0x00000000);
+       nv_mask(priv, 0x610200, 0x00000010, 0x00000010);
+       nv_wr32(priv, 0x640000, 0x00000000);
+       nv_wr32(priv, 0x610200, 0x01000013);
+
+       /* wait for it to go inactive */
+       if (!nv_wait(priv, 0x610200, 0x80000000, 0x00000000)) {
+               nv_error(mast, "init: 0x%08x\n", nv_rd32(priv, 0x610200));
+               return -EBUSY;
+       }
+
+       return 0;
+}
+
+static int
+nv50_disp_core_fini(struct nvkm_object *object, bool suspend)
+{
+       struct nv50_disp_priv *priv = (void *)object->engine;
+       struct nv50_disp_dmac *mast = (void *)object;
+
+       /* deactivate channel */
+       nv_mask(priv, 0x610200, 0x00000010, 0x00000000);
+       nv_mask(priv, 0x610200, 0x00000003, 0x00000000);
+       if (!nv_wait(priv, 0x610200, 0x001e0000, 0x00000000)) {
+               nv_error(mast, "fini: 0x%08x\n", nv_rd32(priv, 0x610200));
+               if (suspend)
+                       return -EBUSY;
+       }
+
+       /* disable error reporting and completion notifications */
+       nv_mask(priv, 0x610028, 0x00010001, 0x00000000);
+
+       return nv50_disp_chan_fini(&mast->base, suspend);
+}
+
+struct nv50_disp_chan_impl
+nv50_disp_core_ofuncs = {
+       .base.ctor = nv50_disp_core_ctor,
+       .base.dtor = nv50_disp_dmac_dtor,
+       .base.init = nv50_disp_core_init,
+       .base.fini = nv50_disp_core_fini,
+       .base.map  = nv50_disp_chan_map,
+       .base.ntfy = nv50_disp_chan_ntfy,
+       .base.rd32 = nv50_disp_chan_rd32,
+       .base.wr32 = nv50_disp_chan_wr32,
+       .chid = 0,
+       .attach = nv50_disp_dmac_object_attach,
+       .detach = nv50_disp_dmac_object_detach,
+};
+
+/*******************************************************************************
+ * EVO sync channel objects
+ ******************************************************************************/
+
+static const struct nv50_disp_mthd_list
+nv50_disp_base_mthd_base = {
+       .mthd = 0x0000,
+       .addr = 0x000000,
+       .data = {
+               { 0x0080, 0x000000 },
+               { 0x0084, 0x0008c4 },
+               { 0x0088, 0x0008d0 },
+               { 0x008c, 0x0008dc },
+               { 0x0090, 0x0008e4 },
+               { 0x0094, 0x610884 },
+               { 0x00a0, 0x6108a0 },
+               { 0x00a4, 0x610878 },
+               { 0x00c0, 0x61086c },
+               { 0x00e0, 0x610858 },
+               { 0x00e4, 0x610860 },
+               { 0x00e8, 0x6108ac },
+               { 0x00ec, 0x6108b4 },
+               { 0x0100, 0x610894 },
+               { 0x0110, 0x6108bc },
+               { 0x0114, 0x61088c },
+               {}
+       }
+};
+
+const struct nv50_disp_mthd_list
+nv50_disp_base_mthd_image = {
+       .mthd = 0x0400,
+       .addr = 0x000000,
+       .data = {
+               { 0x0800, 0x6108f0 },
+               { 0x0804, 0x6108fc },
+               { 0x0808, 0x61090c },
+               { 0x080c, 0x610914 },
+               { 0x0810, 0x610904 },
+               {}
+       }
+};
+
+static const struct nv50_disp_mthd_chan
+nv50_disp_base_mthd_chan = {
+       .name = "Base",
+       .addr = 0x000540,
+       .data = {
+               { "Global", 1, &nv50_disp_base_mthd_base },
+               {  "Image", 2, &nv50_disp_base_mthd_image },
+               {}
+       }
+};
+
+int
+nv50_disp_base_ctor(struct nvkm_object *parent,
+                   struct nvkm_object *engine,
+                   struct nvkm_oclass *oclass, void *data, u32 size,
+                   struct nvkm_object **pobject)
+{
+       union {
+               struct nv50_disp_base_channel_dma_v0 v0;
+       } *args = data;
+       struct nv50_disp_priv *priv = (void *)engine;
+       struct nv50_disp_dmac *dmac;
+       int ret;
+
+       nv_ioctl(parent, "create disp base channel dma size %d\n", size);
+       if (nvif_unpack(args->v0, 0, 0, false)) {
+               nv_ioctl(parent, "create disp base channel dma vers %d "
+                                "pushbuf %08x head %d\n",
+                        args->v0.version, args->v0.pushbuf, args->v0.head);
+               if (args->v0.head > priv->head.nr)
+                       return -EINVAL;
+       } else
+               return ret;
+
+       ret = nv50_disp_dmac_create_(parent, engine, oclass, args->v0.pushbuf,
+                                    args->v0.head, sizeof(*dmac),
+                                    (void **)&dmac);
+       *pobject = nv_object(dmac);
+       if (ret)
+               return ret;
+
+       return 0;
+}
+
+struct nv50_disp_chan_impl
+nv50_disp_base_ofuncs = {
+       .base.ctor = nv50_disp_base_ctor,
+       .base.dtor = nv50_disp_dmac_dtor,
+       .base.init = nv50_disp_dmac_init,
+       .base.fini = nv50_disp_dmac_fini,
+       .base.ntfy = nv50_disp_chan_ntfy,
+       .base.map  = nv50_disp_chan_map,
+       .base.rd32 = nv50_disp_chan_rd32,
+       .base.wr32 = nv50_disp_chan_wr32,
+       .chid = 1,
+       .attach = nv50_disp_dmac_object_attach,
+       .detach = nv50_disp_dmac_object_detach,
+};
+
+/*******************************************************************************
+ * EVO overlay channel objects
+ ******************************************************************************/
+
+const struct nv50_disp_mthd_list
+nv50_disp_ovly_mthd_base = {
+       .mthd = 0x0000,
+       .addr = 0x000000,
+       .data = {
+               { 0x0080, 0x000000 },
+               { 0x0084, 0x0009a0 },
+               { 0x0088, 0x0009c0 },
+               { 0x008c, 0x0009c8 },
+               { 0x0090, 0x6109b4 },
+               { 0x0094, 0x610970 },
+               { 0x00a0, 0x610998 },
+               { 0x00a4, 0x610964 },
+               { 0x00c0, 0x610958 },
+               { 0x00e0, 0x6109a8 },
+               { 0x00e4, 0x6109d0 },
+               { 0x00e8, 0x6109d8 },
+               { 0x0100, 0x61094c },
+               { 0x0104, 0x610984 },
+               { 0x0108, 0x61098c },
+               { 0x0800, 0x6109f8 },
+               { 0x0808, 0x610a08 },
+               { 0x080c, 0x610a10 },
+               { 0x0810, 0x610a00 },
+               {}
+       }
+};
+
+static const struct nv50_disp_mthd_chan
+nv50_disp_ovly_mthd_chan = {
+       .name = "Overlay",
+       .addr = 0x000540,
+       .data = {
+               { "Global", 1, &nv50_disp_ovly_mthd_base },
+               {}
+       }
+};
+
+int
+nv50_disp_ovly_ctor(struct nvkm_object *parent,
+                   struct nvkm_object *engine,
+                   struct nvkm_oclass *oclass, void *data, u32 size,
+                   struct nvkm_object **pobject)
+{
+       union {
+               struct nv50_disp_overlay_channel_dma_v0 v0;
+       } *args = data;
+       struct nv50_disp_priv *priv = (void *)engine;
+       struct nv50_disp_dmac *dmac;
+       int ret;
+
+       nv_ioctl(parent, "create disp overlay channel dma size %d\n", size);
+       if (nvif_unpack(args->v0, 0, 0, false)) {
+               nv_ioctl(parent, "create disp overlay channel dma vers %d "
+                                "pushbuf %08x head %d\n",
+                        args->v0.version, args->v0.pushbuf, args->v0.head);
+               if (args->v0.head > priv->head.nr)
+                       return -EINVAL;
+       } else
+               return ret;
+
+       ret = nv50_disp_dmac_create_(parent, engine, oclass, args->v0.pushbuf,
+                                    args->v0.head, sizeof(*dmac),
+                                    (void **)&dmac);
+       *pobject = nv_object(dmac);
+       if (ret)
+               return ret;
+
+       return 0;
+}
+
+struct nv50_disp_chan_impl
+nv50_disp_ovly_ofuncs = {
+       .base.ctor = nv50_disp_ovly_ctor,
+       .base.dtor = nv50_disp_dmac_dtor,
+       .base.init = nv50_disp_dmac_init,
+       .base.fini = nv50_disp_dmac_fini,
+       .base.ntfy = nv50_disp_chan_ntfy,
+       .base.map  = nv50_disp_chan_map,
+       .base.rd32 = nv50_disp_chan_rd32,
+       .base.wr32 = nv50_disp_chan_wr32,
+       .chid = 3,
+       .attach = nv50_disp_dmac_object_attach,
+       .detach = nv50_disp_dmac_object_detach,
+};
+
+/*******************************************************************************
+ * EVO PIO channel base class
+ ******************************************************************************/
+
+static int
+nv50_disp_pioc_create_(struct nvkm_object *parent,
+                      struct nvkm_object *engine,
+                      struct nvkm_oclass *oclass, int head,
+                      int length, void **pobject)
+{
+       return nv50_disp_chan_create_(parent, engine, oclass, head,
+                                     length, pobject);
+}
+
+void
+nv50_disp_pioc_dtor(struct nvkm_object *object)
+{
+       struct nv50_disp_pioc *pioc = (void *)object;
+       nv50_disp_chan_destroy(&pioc->base);
+}
+
+static int
+nv50_disp_pioc_init(struct nvkm_object *object)
+{
+       struct nv50_disp_priv *priv = (void *)object->engine;
+       struct nv50_disp_pioc *pioc = (void *)object;
+       int chid = pioc->base.chid;
+       int ret;
+
+       ret = nv50_disp_chan_init(&pioc->base);
+       if (ret)
+               return ret;
+
+       nv_wr32(priv, 0x610200 + (chid * 0x10), 0x00002000);
+       if (!nv_wait(priv, 0x610200 + (chid * 0x10), 0x00000000, 0x00000000)) {
+               nv_error(pioc, "timeout0: 0x%08x\n",
+                        nv_rd32(priv, 0x610200 + (chid * 0x10)));
+               return -EBUSY;
+       }
+
+       nv_wr32(priv, 0x610200 + (chid * 0x10), 0x00000001);
+       if (!nv_wait(priv, 0x610200 + (chid * 0x10), 0x00030000, 0x00010000)) {
+               nv_error(pioc, "timeout1: 0x%08x\n",
+                        nv_rd32(priv, 0x610200 + (chid * 0x10)));
+               return -EBUSY;
+       }
+
+       return 0;
+}
+
+static int
+nv50_disp_pioc_fini(struct nvkm_object *object, bool suspend)
+{
+       struct nv50_disp_priv *priv = (void *)object->engine;
+       struct nv50_disp_pioc *pioc = (void *)object;
+       int chid = pioc->base.chid;
+
+       nv_mask(priv, 0x610200 + (chid * 0x10), 0x00000001, 0x00000000);
+       if (!nv_wait(priv, 0x610200 + (chid * 0x10), 0x00030000, 0x00000000)) {
+               nv_error(pioc, "timeout: 0x%08x\n",
+                        nv_rd32(priv, 0x610200 + (chid * 0x10)));
+               if (suspend)
+                       return -EBUSY;
+       }
+
+       return nv50_disp_chan_fini(&pioc->base, suspend);
+}
+
+/*******************************************************************************
+ * EVO immediate overlay channel objects
+ ******************************************************************************/
+
+int
+nv50_disp_oimm_ctor(struct nvkm_object *parent,
+                   struct nvkm_object *engine,
+                   struct nvkm_oclass *oclass, void *data, u32 size,
+                   struct nvkm_object **pobject)
+{
+       union {
+               struct nv50_disp_overlay_v0 v0;
+       } *args = data;
+       struct nv50_disp_priv *priv = (void *)engine;
+       struct nv50_disp_pioc *pioc;
+       int ret;
+
+       nv_ioctl(parent, "create disp overlay size %d\n", size);
+       if (nvif_unpack(args->v0, 0, 0, false)) {
+               nv_ioctl(parent, "create disp overlay vers %d head %d\n",
+                        args->v0.version, args->v0.head);
+               if (args->v0.head > priv->head.nr)
+                       return -EINVAL;
+       } else
+               return ret;
+
+       ret = nv50_disp_pioc_create_(parent, engine, oclass, args->v0.head,
+                                    sizeof(*pioc), (void **)&pioc);
+       *pobject = nv_object(pioc);
+       if (ret)
+               return ret;
+
+       return 0;
+}
+
+struct nv50_disp_chan_impl
+nv50_disp_oimm_ofuncs = {
+       .base.ctor = nv50_disp_oimm_ctor,
+       .base.dtor = nv50_disp_pioc_dtor,
+       .base.init = nv50_disp_pioc_init,
+       .base.fini = nv50_disp_pioc_fini,
+       .base.ntfy = nv50_disp_chan_ntfy,
+       .base.map  = nv50_disp_chan_map,
+       .base.rd32 = nv50_disp_chan_rd32,
+       .base.wr32 = nv50_disp_chan_wr32,
+       .chid = 5,
+};
+
+/*******************************************************************************
+ * EVO cursor channel objects
+ ******************************************************************************/
+
+int
+nv50_disp_curs_ctor(struct nvkm_object *parent,
+                   struct nvkm_object *engine,
+                   struct nvkm_oclass *oclass, void *data, u32 size,
+                   struct nvkm_object **pobject)
+{
+       union {
+               struct nv50_disp_cursor_v0 v0;
+       } *args = data;
+       struct nv50_disp_priv *priv = (void *)engine;
+       struct nv50_disp_pioc *pioc;
+       int ret;
+
+       nv_ioctl(parent, "create disp cursor size %d\n", size);
+       if (nvif_unpack(args->v0, 0, 0, false)) {
+               nv_ioctl(parent, "create disp cursor vers %d head %d\n",
+                        args->v0.version, args->v0.head);
+               if (args->v0.head > priv->head.nr)
+                       return -EINVAL;
+       } else
+               return ret;
+
+       ret = nv50_disp_pioc_create_(parent, engine, oclass, args->v0.head,
+                                    sizeof(*pioc), (void **)&pioc);
+       *pobject = nv_object(pioc);
+       if (ret)
+               return ret;
+
+       return 0;
+}
+
+struct nv50_disp_chan_impl
+nv50_disp_curs_ofuncs = {
+       .base.ctor = nv50_disp_curs_ctor,
+       .base.dtor = nv50_disp_pioc_dtor,
+       .base.init = nv50_disp_pioc_init,
+       .base.fini = nv50_disp_pioc_fini,
+       .base.ntfy = nv50_disp_chan_ntfy,
+       .base.map  = nv50_disp_chan_map,
+       .base.rd32 = nv50_disp_chan_rd32,
+       .base.wr32 = nv50_disp_chan_wr32,
+       .chid = 7,
+};
+
+/*******************************************************************************
+ * Base display object
+ ******************************************************************************/
+
+int
+nv50_disp_main_scanoutpos(NV50_DISP_MTHD_V0)
+{
+       const u32 blanke = nv_rd32(priv, 0x610aec + (head * 0x540));
+       const u32 blanks = nv_rd32(priv, 0x610af4 + (head * 0x540));
+       const u32 total  = nv_rd32(priv, 0x610afc + (head * 0x540));
+       union {
+               struct nv04_disp_scanoutpos_v0 v0;
+       } *args = data;
+       int ret;
+
+       nv_ioctl(object, "disp scanoutpos size %d\n", size);
+       if (nvif_unpack(args->v0, 0, 0, false)) {
+               nv_ioctl(object, "disp scanoutpos vers %d\n", args->v0.version);
+               args->v0.vblanke = (blanke & 0xffff0000) >> 16;
+               args->v0.hblanke = (blanke & 0x0000ffff);
+               args->v0.vblanks = (blanks & 0xffff0000) >> 16;
+               args->v0.hblanks = (blanks & 0x0000ffff);
+               args->v0.vtotal  = ( total & 0xffff0000) >> 16;
+               args->v0.htotal  = ( total & 0x0000ffff);
+               args->v0.time[0] = ktime_to_ns(ktime_get());
+               args->v0.vline = /* vline read locks hline */
+                       nv_rd32(priv, 0x616340 + (head * 0x800)) & 0xffff;
+               args->v0.time[1] = ktime_to_ns(ktime_get());
+               args->v0.hline =
+                       nv_rd32(priv, 0x616344 + (head * 0x800)) & 0xffff;
+       } else
+               return ret;
+
+       return 0;
+}
+
+int
+nv50_disp_main_mthd(struct nvkm_object *object, u32 mthd, void *data, u32 size)
+{
+       const struct nv50_disp_impl *impl = (void *)nv_oclass(object->engine);
+       union {
+               struct nv50_disp_mthd_v0 v0;
+               struct nv50_disp_mthd_v1 v1;
+       } *args = data;
+       struct nv50_disp_priv *priv = (void *)object->engine;
+       struct nvkm_output *outp = NULL;
+       struct nvkm_output *temp;
+       u16 type, mask = 0;
+       int head, ret;
+
+       if (mthd != NV50_DISP_MTHD)
+               return -EINVAL;
+
+       nv_ioctl(object, "disp mthd size %d\n", size);
+       if (nvif_unpack(args->v0, 0, 0, true)) {
+               nv_ioctl(object, "disp mthd vers %d mthd %02x head %d\n",
+                        args->v0.version, args->v0.method, args->v0.head);
+               mthd = args->v0.method;
+               head = args->v0.head;
+       } else
+       if (nvif_unpack(args->v1, 1, 1, true)) {
+               nv_ioctl(object, "disp mthd vers %d mthd %02x "
+                                "type %04x mask %04x\n",
+                        args->v1.version, args->v1.method,
+                        args->v1.hasht, args->v1.hashm);
+               mthd = args->v1.method;
+               type = args->v1.hasht;
+               mask = args->v1.hashm;
+               head = ffs((mask >> 8) & 0x0f) - 1;
+       } else
+               return ret;
+
+       if (head < 0 || head >= priv->head.nr)
+               return -ENXIO;
+
+       if (mask) {
+               list_for_each_entry(temp, &priv->base.outp, head) {
+                       if ((temp->info.hasht         == type) &&
+                           (temp->info.hashm & mask) == mask) {
+                               outp = temp;
+                               break;
+                       }
+               }
+               if (outp == NULL)
+                       return -ENXIO;
+       }
+
+       switch (mthd) {
+       case NV50_DISP_SCANOUTPOS:
+               return impl->head.scanoutpos(object, priv, data, size, head);
+       default:
+               break;
+       }
+
+       switch (mthd * !!outp) {
+       case NV50_DISP_MTHD_V1_DAC_PWR:
+               return priv->dac.power(object, priv, data, size, head, outp);
+       case NV50_DISP_MTHD_V1_DAC_LOAD:
+               return priv->dac.sense(object, priv, data, size, head, outp);
+       case NV50_DISP_MTHD_V1_SOR_PWR:
+               return priv->sor.power(object, priv, data, size, head, outp);
+       case NV50_DISP_MTHD_V1_SOR_HDA_ELD:
+               if (!priv->sor.hda_eld)
+                       return -ENODEV;
+               return priv->sor.hda_eld(object, priv, data, size, head, outp);
+       case NV50_DISP_MTHD_V1_SOR_HDMI_PWR:
+               if (!priv->sor.hdmi)
+                       return -ENODEV;
+               return priv->sor.hdmi(object, priv, data, size, head, outp);
+       case NV50_DISP_MTHD_V1_SOR_LVDS_SCRIPT: {
+               union {
+                       struct nv50_disp_sor_lvds_script_v0 v0;
+               } *args = data;
+               nv_ioctl(object, "disp sor lvds script size %d\n", size);
+               if (nvif_unpack(args->v0, 0, 0, false)) {
+                       nv_ioctl(object, "disp sor lvds script "
+                                        "vers %d name %04x\n",
+                                args->v0.version, args->v0.script);
+                       priv->sor.lvdsconf = args->v0.script;
+                       return 0;
+               } else
+                       return ret;
+       }
+               break;
+       case NV50_DISP_MTHD_V1_SOR_DP_PWR: {
+               struct nvkm_output_dp *outpdp = (void *)outp;
+               union {
+                       struct nv50_disp_sor_dp_pwr_v0 v0;
+               } *args = data;
+               nv_ioctl(object, "disp sor dp pwr size %d\n", size);
+               if (nvif_unpack(args->v0, 0, 0, false)) {
+                       nv_ioctl(object, "disp sor dp pwr vers %d state %d\n",
+                                args->v0.version, args->v0.state);
+                       if (args->v0.state == 0) {
+                               nvkm_notify_put(&outpdp->irq);
+                               ((struct nvkm_output_dp_impl *)nv_oclass(outp))
+                                       ->lnk_pwr(outpdp, 0);
+                               atomic_set(&outpdp->lt.done, 0);
+                               return 0;
+                       } else
+                       if (args->v0.state != 0) {
+                               nvkm_output_dp_train(&outpdp->base, 0, true);
+                               return 0;
+                       }
+               } else
+                       return ret;
+       }
+               break;
+       case NV50_DISP_MTHD_V1_PIOR_PWR:
+               if (!priv->pior.power)
+                       return -ENODEV;
+               return priv->pior.power(object, priv, data, size, head, outp);
+       default:
+               break;
+       }
+
+       return -EINVAL;
+}
+
+int
+nv50_disp_main_ctor(struct nvkm_object *parent,
+                   struct nvkm_object *engine,
+                   struct nvkm_oclass *oclass, void *data, u32 size,
+                   struct nvkm_object **pobject)
+{
+       struct nv50_disp_priv *priv = (void *)engine;
+       struct nv50_disp_base *base;
+       int ret;
+
+       ret = nvkm_parent_create(parent, engine, oclass, 0,
+                                priv->sclass, 0, &base);
+       *pobject = nv_object(base);
+       if (ret)
+               return ret;
+
+       return nvkm_ramht_new(nv_object(base), nv_object(base), 0x1000, 0,
+                             &base->ramht);
+}
+
+void
+nv50_disp_main_dtor(struct nvkm_object *object)
+{
+       struct nv50_disp_base *base = (void *)object;
+       nvkm_ramht_ref(NULL, &base->ramht);
+       nvkm_parent_destroy(&base->base);
+}
+
+static int
+nv50_disp_main_init(struct nvkm_object *object)
+{
+       struct nv50_disp_priv *priv = (void *)object->engine;
+       struct nv50_disp_base *base = (void *)object;
+       int ret, i;
+       u32 tmp;
+
+       ret = nvkm_parent_init(&base->base);
+       if (ret)
+               return ret;
+
+       /* The below segments of code copying values from one register to
+        * another appear to inform EVO of the display capabilities or
+        * something similar.  NFI what the 0x614004 caps are for..
+        */
+       tmp = nv_rd32(priv, 0x614004);
+       nv_wr32(priv, 0x610184, tmp);
+
+       /* ... CRTC caps */
+       for (i = 0; i < priv->head.nr; i++) {
+               tmp = nv_rd32(priv, 0x616100 + (i * 0x800));
+               nv_wr32(priv, 0x610190 + (i * 0x10), tmp);
+               tmp = nv_rd32(priv, 0x616104 + (i * 0x800));
+               nv_wr32(priv, 0x610194 + (i * 0x10), tmp);
+               tmp = nv_rd32(priv, 0x616108 + (i * 0x800));
+               nv_wr32(priv, 0x610198 + (i * 0x10), tmp);
+               tmp = nv_rd32(priv, 0x61610c + (i * 0x800));
+               nv_wr32(priv, 0x61019c + (i * 0x10), tmp);
+       }
+
+       /* ... DAC caps */
+       for (i = 0; i < priv->dac.nr; i++) {
+               tmp = nv_rd32(priv, 0x61a000 + (i * 0x800));
+               nv_wr32(priv, 0x6101d0 + (i * 0x04), tmp);
+       }
+
+       /* ... SOR caps */
+       for (i = 0; i < priv->sor.nr; i++) {
+               tmp = nv_rd32(priv, 0x61c000 + (i * 0x800));
+               nv_wr32(priv, 0x6101e0 + (i * 0x04), tmp);
+       }
+
+       /* ... PIOR caps */
+       for (i = 0; i < priv->pior.nr; i++) {
+               tmp = nv_rd32(priv, 0x61e000 + (i * 0x800));
+               nv_wr32(priv, 0x6101f0 + (i * 0x04), tmp);
+       }
+
+       /* steal display away from vbios, or something like that */
+       if (nv_rd32(priv, 0x610024) & 0x00000100) {
+               nv_wr32(priv, 0x610024, 0x00000100);
+               nv_mask(priv, 0x6194e8, 0x00000001, 0x00000000);
+               if (!nv_wait(priv, 0x6194e8, 0x00000002, 0x00000000)) {
+                       nv_error(priv, "timeout acquiring display\n");
+                       return -EBUSY;
+               }
+       }
+
+       /* point at display engine memory area (hash table, objects) */
+       nv_wr32(priv, 0x610010, (nv_gpuobj(base->ramht)->addr >> 8) | 9);
+
+       /* enable supervisor interrupts, disable everything else */
+       nv_wr32(priv, 0x61002c, 0x00000370);
+       nv_wr32(priv, 0x610028, 0x00000000);
+       return 0;
+}
+
+static int
+nv50_disp_main_fini(struct nvkm_object *object, bool suspend)
+{
+       struct nv50_disp_priv *priv = (void *)object->engine;
+       struct nv50_disp_base *base = (void *)object;
+
+       /* disable all interrupts */
+       nv_wr32(priv, 0x610024, 0x00000000);
+       nv_wr32(priv, 0x610020, 0x00000000);
+
+       return nvkm_parent_fini(&base->base, suspend);
+}
+
+struct nvkm_ofuncs
+nv50_disp_main_ofuncs = {
+       .ctor = nv50_disp_main_ctor,
+       .dtor = nv50_disp_main_dtor,
+       .init = nv50_disp_main_init,
+       .fini = nv50_disp_main_fini,
+       .mthd = nv50_disp_main_mthd,
+       .ntfy = nvkm_disp_ntfy,
+};
+
+static struct nvkm_oclass
+nv50_disp_main_oclass[] = {
+       { NV50_DISP, &nv50_disp_main_ofuncs },
+       {}
+};
+
+static struct nvkm_oclass
+nv50_disp_sclass[] = {
+       { NV50_DISP_CORE_CHANNEL_DMA, &nv50_disp_core_ofuncs.base },
+       { NV50_DISP_BASE_CHANNEL_DMA, &nv50_disp_base_ofuncs.base },
+       { NV50_DISP_OVERLAY_CHANNEL_DMA, &nv50_disp_ovly_ofuncs.base },
+       { NV50_DISP_OVERLAY, &nv50_disp_oimm_ofuncs.base },
+       { NV50_DISP_CURSOR, &nv50_disp_curs_ofuncs.base },
+       {}
+};
+
+/*******************************************************************************
+ * Display context, tracks instmem allocation and prevents more than one
+ * client using the display hardware at any time.
+ ******************************************************************************/
+
+static int
+nv50_disp_data_ctor(struct nvkm_object *parent,
+                   struct nvkm_object *engine,
+                   struct nvkm_oclass *oclass, void *data, u32 size,
+                   struct nvkm_object **pobject)
+{
+       struct nv50_disp_priv *priv = (void *)engine;
+       struct nvkm_engctx *ectx;
+       int ret = -EBUSY;
+
+       /* no context needed for channel objects... */
+       if (nv_mclass(parent) != NV_DEVICE) {
+               atomic_inc(&parent->refcount);
+               *pobject = parent;
+               return 1;
+       }
+
+       /* allocate display hardware to client */
+       mutex_lock(&nv_subdev(priv)->mutex);
+       if (list_empty(&nv_engine(priv)->contexts)) {
+               ret = nvkm_engctx_create(parent, engine, oclass, NULL, 0x10000,
+                                        0x10000, NVOBJ_FLAG_HEAP, &ectx);
+               *pobject = nv_object(ectx);
+       }
+       mutex_unlock(&nv_subdev(priv)->mutex);
+       return ret;
+}
+
+struct nvkm_oclass
+nv50_disp_cclass = {
+       .handle = NV_ENGCTX(DISP, 0x50),
+       .ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = nv50_disp_data_ctor,
+               .dtor = _nvkm_engctx_dtor,
+               .init = _nvkm_engctx_init,
+               .fini = _nvkm_engctx_fini,
+               .rd32 = _nvkm_engctx_rd32,
+               .wr32 = _nvkm_engctx_wr32,
+       },
+};
+
+/*******************************************************************************
+ * Display engine implementation
+ ******************************************************************************/
+
+static void
+nv50_disp_vblank_fini(struct nvkm_event *event, int type, int head)
+{
+       struct nvkm_disp *disp = container_of(event, typeof(*disp), vblank);
+       nv_mask(disp, 0x61002c, (4 << head), 0);
+}
+
+static void
+nv50_disp_vblank_init(struct nvkm_event *event, int type, int head)
+{
+       struct nvkm_disp *disp = container_of(event, typeof(*disp), vblank);
+       nv_mask(disp, 0x61002c, (4 << head), (4 << head));
+}
+
+const struct nvkm_event_func
+nv50_disp_vblank_func = {
+       .ctor = nvkm_disp_vblank_ctor,
+       .init = nv50_disp_vblank_init,
+       .fini = nv50_disp_vblank_fini,
+};
+
+static const struct nvkm_enum
+nv50_disp_intr_error_type[] = {
+       { 3, "ILLEGAL_MTHD" },
+       { 4, "INVALID_VALUE" },
+       { 5, "INVALID_STATE" },
+       { 7, "INVALID_HANDLE" },
+       {}
+};
+
+static const struct nvkm_enum
+nv50_disp_intr_error_code[] = {
+       { 0x00, "" },
+       {}
+};
+
+static void
+nv50_disp_intr_error(struct nv50_disp_priv *priv, int chid)
+{
+       struct nv50_disp_impl *impl = (void *)nv_object(priv)->oclass;
+       u32 data = nv_rd32(priv, 0x610084 + (chid * 0x08));
+       u32 addr = nv_rd32(priv, 0x610080 + (chid * 0x08));
+       u32 code = (addr & 0x00ff0000) >> 16;
+       u32 type = (addr & 0x00007000) >> 12;
+       u32 mthd = (addr & 0x00000ffc);
+       const struct nvkm_enum *ec, *et;
+       char ecunk[6], etunk[6];
+
+       et = nvkm_enum_find(nv50_disp_intr_error_type, type);
+       if (!et)
+               snprintf(etunk, sizeof(etunk), "UNK%02X", type);
+
+       ec = nvkm_enum_find(nv50_disp_intr_error_code, code);
+       if (!ec)
+               snprintf(ecunk, sizeof(ecunk), "UNK%02X", code);
+
+       nv_error(priv, "%s [%s] chid %d mthd 0x%04x data 0x%08x\n",
+                et ? et->name : etunk, ec ? ec->name : ecunk,
+                chid, mthd, data);
+
+       if (chid == 0) {
+               switch (mthd) {
+               case 0x0080:
+                       nv50_disp_mthd_chan(priv, NV_DBG_ERROR, chid - 0,
+                                           impl->mthd.core);
+                       break;
+               default:
+                       break;
+               }
+       } else
+       if (chid <= 2) {
+               switch (mthd) {
+               case 0x0080:
+                       nv50_disp_mthd_chan(priv, NV_DBG_ERROR, chid - 1,
+                                           impl->mthd.base);
+                       break;
+               default:
+                       break;
+               }
+       } else
+       if (chid <= 4) {
+               switch (mthd) {
+               case 0x0080:
+                       nv50_disp_mthd_chan(priv, NV_DBG_ERROR, chid - 3,
+                                           impl->mthd.ovly);
+                       break;
+               default:
+                       break;
+               }
+       }
+
+       nv_wr32(priv, 0x610020, 0x00010000 << chid);
+       nv_wr32(priv, 0x610080 + (chid * 0x08), 0x90000000);
+}
+
+static struct nvkm_output *
+exec_lookup(struct nv50_disp_priv *priv, int head, int or, u32 ctrl,
+           u32 *data, u8 *ver, u8 *hdr, u8 *cnt, u8 *len,
+           struct nvbios_outp *info)
+{
+       struct nvkm_bios *bios = nvkm_bios(priv);
+       struct nvkm_output *outp;
+       u16 mask, type;
+
+       if (or < 4) {
+               type = DCB_OUTPUT_ANALOG;
+               mask = 0;
+       } else
+       if (or < 8) {
+               switch (ctrl & 0x00000f00) {
+               case 0x00000000: type = DCB_OUTPUT_LVDS; mask = 1; break;
+               case 0x00000100: type = DCB_OUTPUT_TMDS; mask = 1; break;
+               case 0x00000200: type = DCB_OUTPUT_TMDS; mask = 2; break;
+               case 0x00000500: type = DCB_OUTPUT_TMDS; mask = 3; break;
+               case 0x00000800: type = DCB_OUTPUT_DP; mask = 1; break;
+               case 0x00000900: type = DCB_OUTPUT_DP; mask = 2; break;
+               default:
+                       nv_error(priv, "unknown SOR mc 0x%08x\n", ctrl);
+                       return NULL;
+               }
+               or  -= 4;
+       } else {
+               or   = or - 8;
+               type = 0x0010;
+               mask = 0;
+               switch (ctrl & 0x00000f00) {
+               case 0x00000000: type |= priv->pior.type[or]; break;
+               default:
+                       nv_error(priv, "unknown PIOR mc 0x%08x\n", ctrl);
+                       return NULL;
+               }
+       }
+
+       mask  = 0x00c0 & (mask << 6);
+       mask |= 0x0001 << or;
+       mask |= 0x0100 << head;
+
+       list_for_each_entry(outp, &priv->base.outp, head) {
+               if ((outp->info.hasht & 0xff) == type &&
+                   (outp->info.hashm & mask) == mask) {
+                       *data = nvbios_outp_match(bios, outp->info.hasht,
+                                                       outp->info.hashm,
+                                                 ver, hdr, cnt, len, info);
+                       if (!*data)
+                               return NULL;
+                       return outp;
+               }
+       }
+
+       return NULL;
+}
+
+static struct nvkm_output *
+exec_script(struct nv50_disp_priv *priv, int head, int id)
+{
+       struct nvkm_bios *bios = nvkm_bios(priv);
+       struct nvkm_output *outp;
+       struct nvbios_outp info;
+       u8  ver, hdr, cnt, len;
+       u32 data, ctrl = 0;
+       u32 reg;
+       int i;
+
+       /* DAC */
+       for (i = 0; !(ctrl & (1 << head)) && i < priv->dac.nr; i++)
+               ctrl = nv_rd32(priv, 0x610b5c + (i * 8));
+
+       /* SOR */
+       if (!(ctrl & (1 << head))) {
+               if (nv_device(priv)->chipset  < 0x90 ||
+                   nv_device(priv)->chipset == 0x92 ||
+                   nv_device(priv)->chipset == 0xa0) {
+                       reg = 0x610b74;
+               } else {
+                       reg = 0x610798;
+               }
+               for (i = 0; !(ctrl & (1 << head)) && i < priv->sor.nr; i++)
+                       ctrl = nv_rd32(priv, reg + (i * 8));
+               i += 4;
+       }
+
+       /* PIOR */
+       if (!(ctrl & (1 << head))) {
+               for (i = 0; !(ctrl & (1 << head)) && i < priv->pior.nr; i++)
+                       ctrl = nv_rd32(priv, 0x610b84 + (i * 8));
+               i += 8;
+       }
+
+       if (!(ctrl & (1 << head)))
+               return NULL;
+       i--;
+
+       outp = exec_lookup(priv, head, i, ctrl, &data, &ver, &hdr, &cnt, &len, &info);
+       if (outp) {
+               struct nvbios_init init = {
+                       .subdev = nv_subdev(priv),
+                       .bios = bios,
+                       .offset = info.script[id],
+                       .outp = &outp->info,
+                       .crtc = head,
+                       .execute = 1,
+               };
+
+               nvbios_exec(&init);
+       }
+
+       return outp;
+}
+
+static struct nvkm_output *
+exec_clkcmp(struct nv50_disp_priv *priv, int head, int id, u32 pclk, u32 *conf)
+{
+       struct nvkm_bios *bios = nvkm_bios(priv);
+       struct nvkm_output *outp;
+       struct nvbios_outp info1;
+       struct nvbios_ocfg info2;
+       u8  ver, hdr, cnt, len;
+       u32 data, ctrl = 0;
+       u32 reg;
+       int i;
+
+       /* DAC */
+       for (i = 0; !(ctrl & (1 << head)) && i < priv->dac.nr; i++)
+               ctrl = nv_rd32(priv, 0x610b58 + (i * 8));
+
+       /* SOR */
+       if (!(ctrl & (1 << head))) {
+               if (nv_device(priv)->chipset  < 0x90 ||
+                   nv_device(priv)->chipset == 0x92 ||
+                   nv_device(priv)->chipset == 0xa0) {
+                       reg = 0x610b70;
+               } else {
+                       reg = 0x610794;
+               }
+               for (i = 0; !(ctrl & (1 << head)) && i < priv->sor.nr; i++)
+                       ctrl = nv_rd32(priv, reg + (i * 8));
+               i += 4;
+       }
+
+       /* PIOR */
+       if (!(ctrl & (1 << head))) {
+               for (i = 0; !(ctrl & (1 << head)) && i < priv->pior.nr; i++)
+                       ctrl = nv_rd32(priv, 0x610b80 + (i * 8));
+               i += 8;
+       }
+
+       if (!(ctrl & (1 << head)))
+               return NULL;
+       i--;
+
+       outp = exec_lookup(priv, head, i, ctrl, &data, &ver, &hdr, &cnt, &len, &info1);
+       if (!outp)
+               return NULL;
+
+       if (outp->info.location == 0) {
+               switch (outp->info.type) {
+               case DCB_OUTPUT_TMDS:
+                       *conf = (ctrl & 0x00000f00) >> 8;
+                       if (pclk >= 165000)
+                               *conf |= 0x0100;
+                       break;
+               case DCB_OUTPUT_LVDS:
+                       *conf = priv->sor.lvdsconf;
+                       break;
+               case DCB_OUTPUT_DP:
+                       *conf = (ctrl & 0x00000f00) >> 8;
+                       break;
+               case DCB_OUTPUT_ANALOG:
+               default:
+                       *conf = 0x00ff;
+                       break;
+               }
+       } else {
+               *conf = (ctrl & 0x00000f00) >> 8;
+               pclk = pclk / 2;
+       }
+
+       data = nvbios_ocfg_match(bios, data, *conf, &ver, &hdr, &cnt, &len, &info2);
+       if (data && id < 0xff) {
+               data = nvbios_oclk_match(bios, info2.clkcmp[id], pclk);
+               if (data) {
+                       struct nvbios_init init = {
+                               .subdev = nv_subdev(priv),
+                               .bios = bios,
+                               .offset = data,
+                               .outp = &outp->info,
+                               .crtc = head,
+                               .execute = 1,
+                       };
+
+                       nvbios_exec(&init);
+               }
+       }
+
+       return outp;
+}
+
+static void
+nv50_disp_intr_unk10_0(struct nv50_disp_priv *priv, int head)
+{
+       exec_script(priv, head, 1);
+}
+
+static void
+nv50_disp_intr_unk20_0(struct nv50_disp_priv *priv, int head)
+{
+       struct nvkm_output *outp = exec_script(priv, head, 2);
+
+       /* the binary driver does this outside of the supervisor handling
+        * (after the third supervisor from a detach).  we (currently?)
+        * allow both detach/attach to happen in the same set of
+        * supervisor interrupts, so it would make sense to execute this
+        * (full power down?) script after all the detach phases of the
+        * supervisor handling.  like with training if needed from the
+        * second supervisor, nvidia doesn't do this, so who knows if it's
+        * entirely safe, but it does appear to work..
+        *
+        * without this script being run, on some configurations i've
+        * seen, switching from DP to TMDS on a DP connector may result
+        * in a blank screen (SOR_PWR off/on can restore it)
+        */
+       if (outp && outp->info.type == DCB_OUTPUT_DP) {
+               struct nvkm_output_dp *outpdp = (void *)outp;
+               struct nvbios_init init = {
+                       .subdev = nv_subdev(priv),
+                       .bios = nvkm_bios(priv),
+                       .outp = &outp->info,
+                       .crtc = head,
+                       .offset = outpdp->info.script[4],
+                       .execute = 1,
+               };
+
+               nvbios_exec(&init);
+               atomic_set(&outpdp->lt.done, 0);
+       }
+}
+
+static void
+nv50_disp_intr_unk20_1(struct nv50_disp_priv *priv, int head)
+{
+       struct nvkm_devinit *devinit = nvkm_devinit(priv);
+       u32 pclk = nv_rd32(priv, 0x610ad0 + (head * 0x540)) & 0x3fffff;
+       if (pclk)
+               devinit->pll_set(devinit, PLL_VPLL0 + head, pclk);
+}
+
+static void
+nv50_disp_intr_unk20_2_dp(struct nv50_disp_priv *priv, int head,
+                         struct dcb_output *outp, u32 pclk)
+{
+       const int link = !(outp->sorconf.link & 1);
+       const int   or = ffs(outp->or) - 1;
+       const u32 soff = (  or * 0x800);
+       const u32 loff = (link * 0x080) + soff;
+       const u32 ctrl = nv_rd32(priv, 0x610794 + (or * 8));
+       const u32 symbol = 100000;
+       const s32 vactive = nv_rd32(priv, 0x610af8 + (head * 0x540)) & 0xffff;
+       const s32 vblanke = nv_rd32(priv, 0x610ae8 + (head * 0x540)) & 0xffff;
+       const s32 vblanks = nv_rd32(priv, 0x610af0 + (head * 0x540)) & 0xffff;
+       u32 dpctrl = nv_rd32(priv, 0x61c10c + loff);
+       u32 clksor = nv_rd32(priv, 0x614300 + soff);
+       int bestTU = 0, bestVTUi = 0, bestVTUf = 0, bestVTUa = 0;
+       int TU, VTUi, VTUf, VTUa;
+       u64 link_data_rate, link_ratio, unk;
+       u32 best_diff = 64 * symbol;
+       u32 link_nr, link_bw, bits;
+       u64 value;
+
+       link_bw = (clksor & 0x000c0000) ? 270000 : 162000;
+       link_nr = hweight32(dpctrl & 0x000f0000);
+
+       /* symbols/hblank - algorithm taken from comments in tegra driver */
+       value = vblanke + vactive - vblanks - 7;
+       value = value * link_bw;
+       do_div(value, pclk);
+       value = value - (3 * !!(dpctrl & 0x00004000)) - (12 / link_nr);
+       nv_mask(priv, 0x61c1e8 + soff, 0x0000ffff, value);
+
+       /* symbols/vblank - algorithm taken from comments in tegra driver */
+       value = vblanks - vblanke - 25;
+       value = value * link_bw;
+       do_div(value, pclk);
+       value = value - ((36 / link_nr) + 3) - 1;
+       nv_mask(priv, 0x61c1ec + soff, 0x00ffffff, value);
+
+       /* watermark / activesym */
+       if      ((ctrl & 0xf0000) == 0x60000) bits = 30;
+       else if ((ctrl & 0xf0000) == 0x50000) bits = 24;
+       else                                  bits = 18;
+
+       link_data_rate = (pclk * bits / 8) / link_nr;
+
+       /* calculate ratio of packed data rate to link symbol rate */
+       link_ratio = link_data_rate * symbol;
+       do_div(link_ratio, link_bw);
+
+       for (TU = 64; TU >= 32; TU--) {
+               /* calculate average number of valid symbols in each TU */
+               u32 tu_valid = link_ratio * TU;
+               u32 calc, diff;
+
+               /* find a hw representation for the fraction.. */
+               VTUi = tu_valid / symbol;
+               calc = VTUi * symbol;
+               diff = tu_valid - calc;
+               if (diff) {
+                       if (diff >= (symbol / 2)) {
+                               VTUf = symbol / (symbol - diff);
+                               if (symbol - (VTUf * diff))
+                                       VTUf++;
+
+                               if (VTUf <= 15) {
+                                       VTUa  = 1;
+                                       calc += symbol - (symbol / VTUf);
+                               } else {
+                                       VTUa  = 0;
+                                       VTUf  = 1;
+                                       calc += symbol;
+                               }
+                       } else {
+                               VTUa  = 0;
+                               VTUf  = min((int)(symbol / diff), 15);
+                               calc += symbol / VTUf;
+                       }
+
+                       diff = calc - tu_valid;
+               } else {
+                       /* no remainder, but the hw doesn't like the fractional
+                        * part to be zero.  decrement the integer part and
+                        * have the fraction add a whole symbol back
+                        */
+                       VTUa = 0;
+                       VTUf = 1;
+                       VTUi--;
+               }
+
+               if (diff < best_diff) {
+                       best_diff = diff;
+                       bestTU = TU;
+                       bestVTUa = VTUa;
+                       bestVTUf = VTUf;
+                       bestVTUi = VTUi;
+                       if (diff == 0)
+                               break;
+               }
+       }
+
+       if (!bestTU) {
+               nv_error(priv, "unable to find suitable dp config\n");
+               return;
+       }
+
+       /* XXX close to vbios numbers, but not right */
+       unk  = (symbol - link_ratio) * bestTU;
+       unk *= link_ratio;
+       do_div(unk, symbol);
+       do_div(unk, symbol);
+       unk += 6;
+
+       nv_mask(priv, 0x61c10c + loff, 0x000001fc, bestTU << 2);
+       nv_mask(priv, 0x61c128 + loff, 0x010f7f3f, bestVTUa << 24 |
+                                                  bestVTUf << 16 |
+                                                  bestVTUi << 8 | unk);
+}
+
+static void
+nv50_disp_intr_unk20_2(struct nv50_disp_priv *priv, int head)
+{
+       struct nvkm_output *outp;
+       u32 pclk = nv_rd32(priv, 0x610ad0 + (head * 0x540)) & 0x3fffff;
+       u32 hval, hreg = 0x614200 + (head * 0x800);
+       u32 oval, oreg;
+       u32 mask, conf;
+
+       outp = exec_clkcmp(priv, head, 0xff, pclk, &conf);
+       if (!outp)
+               return;
+
+       /* we allow both encoder attach and detach operations to occur
+        * within a single supervisor (ie. modeset) sequence.  the
+        * encoder detach scripts quite often switch off power to the
+        * lanes, which requires the link to be re-trained.
+        *
+        * this is not generally an issue as the sink "must" (heh)
+        * signal an irq when it's lost sync so the driver can
+        * re-train.
+        *
+        * however, on some boards, if one does not configure at least
+        * the gpu side of the link *before* attaching, then various
+        * things can go horribly wrong (PDISP disappearing from mmio,
+        * third supervisor never happens, etc).
+        *
+        * the solution is simply to retrain here, if necessary.  last
+        * i checked, the binary driver userspace does not appear to
+        * trigger this situation (it forces an UPDATE between steps).
+        */
+       if (outp->info.type == DCB_OUTPUT_DP) {
+               u32 soff = (ffs(outp->info.or) - 1) * 0x08;
+               u32 ctrl, datarate;
+
+               if (outp->info.location == 0) {
+                       ctrl = nv_rd32(priv, 0x610794 + soff);
+                       soff = 1;
+               } else {
+                       ctrl = nv_rd32(priv, 0x610b80 + soff);
+                       soff = 2;
+               }
+
+               switch ((ctrl & 0x000f0000) >> 16) {
+               case 6: datarate = pclk * 30; break;
+               case 5: datarate = pclk * 24; break;
+               case 2:
+               default:
+                       datarate = pclk * 18;
+                       break;
+               }
+
+               if (nvkm_output_dp_train(outp, datarate / soff, true))
+                       ERR("link not trained before attach\n");
+       }
+
+       exec_clkcmp(priv, head, 0, pclk, &conf);
+
+       if (!outp->info.location && outp->info.type == DCB_OUTPUT_ANALOG) {
+               oreg = 0x614280 + (ffs(outp->info.or) - 1) * 0x800;
+               oval = 0x00000000;
+               hval = 0x00000000;
+               mask = 0xffffffff;
+       } else
+       if (!outp->info.location) {
+               if (outp->info.type == DCB_OUTPUT_DP)
+                       nv50_disp_intr_unk20_2_dp(priv, head, &outp->info, pclk);
+               oreg = 0x614300 + (ffs(outp->info.or) - 1) * 0x800;
+               oval = (conf & 0x0100) ? 0x00000101 : 0x00000000;
+               hval = 0x00000000;
+               mask = 0x00000707;
+       } else {
+               oreg = 0x614380 + (ffs(outp->info.or) - 1) * 0x800;
+               oval = 0x00000001;
+               hval = 0x00000001;
+               mask = 0x00000707;
+       }
+
+       nv_mask(priv, hreg, 0x0000000f, hval);
+       nv_mask(priv, oreg, mask, oval);
+}
+
+/* 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_disp_intr_unk40_0_tmds(struct nv50_disp_priv *priv,
+                           struct dcb_output *outp)
+{
+       struct nvkm_bios *bios = nvkm_bios(priv);
+       const int link = !(outp->sorconf.link & 1);
+       const int   or = ffs(outp->or) - 1;
+       const u32 loff = (or * 0x800) + (link * 0x80);
+       const u16 mask = (outp->sorconf.link << 6) | outp->or;
+       struct dcb_output match;
+       u8  ver, hdr;
+
+       if (dcb_outp_match(bios, DCB_OUTPUT_DP, mask, &ver, &hdr, &match))
+               nv_mask(priv, 0x61c10c + loff, 0x00000001, 0x00000000);
+}
+
+static void
+nv50_disp_intr_unk40_0(struct nv50_disp_priv *priv, int head)
+{
+       struct nvkm_output *outp;
+       u32 pclk = nv_rd32(priv, 0x610ad0 + (head * 0x540)) & 0x3fffff;
+       u32 conf;
+
+       outp = exec_clkcmp(priv, head, 1, pclk, &conf);
+       if (!outp)
+               return;
+
+       if (outp->info.location == 0 && outp->info.type == DCB_OUTPUT_TMDS)
+               nv50_disp_intr_unk40_0_tmds(priv, &outp->info);
+}
+
+void
+nv50_disp_intr_supervisor(struct work_struct *work)
+{
+       struct nv50_disp_priv *priv =
+               container_of(work, struct nv50_disp_priv, supervisor);
+       struct nv50_disp_impl *impl = (void *)nv_object(priv)->oclass;
+       u32 super = nv_rd32(priv, 0x610030);
+       int head;
+
+       nv_debug(priv, "supervisor 0x%08x 0x%08x\n", priv->super, super);
+
+       if (priv->super & 0x00000010) {
+               nv50_disp_mthd_chan(priv, NV_DBG_DEBUG, 0, impl->mthd.core);
+               for (head = 0; head < priv->head.nr; head++) {
+                       if (!(super & (0x00000020 << head)))
+                               continue;
+                       if (!(super & (0x00000080 << head)))
+                               continue;
+                       nv50_disp_intr_unk10_0(priv, head);
+               }
+       } else
+       if (priv->super & 0x00000020) {
+               for (head = 0; head < priv->head.nr; head++) {
+                       if (!(super & (0x00000080 << head)))
+                               continue;
+                       nv50_disp_intr_unk20_0(priv, head);
+               }
+               for (head = 0; head < priv->head.nr; head++) {
+                       if (!(super & (0x00000200 << head)))
+                               continue;
+                       nv50_disp_intr_unk20_1(priv, head);
+               }
+               for (head = 0; head < priv->head.nr; head++) {
+                       if (!(super & (0x00000080 << head)))
+                               continue;
+                       nv50_disp_intr_unk20_2(priv, head);
+               }
+       } else
+       if (priv->super & 0x00000040) {
+               for (head = 0; head < priv->head.nr; head++) {
+                       if (!(super & (0x00000080 << head)))
+                               continue;
+                       nv50_disp_intr_unk40_0(priv, head);
+               }
+       }
+
+       nv_wr32(priv, 0x610030, 0x80000000);
+}
+
+void
+nv50_disp_intr(struct nvkm_subdev *subdev)
+{
+       struct nv50_disp_priv *priv = (void *)subdev;
+       u32 intr0 = nv_rd32(priv, 0x610020);
+       u32 intr1 = nv_rd32(priv, 0x610024);
+
+       while (intr0 & 0x001f0000) {
+               u32 chid = __ffs(intr0 & 0x001f0000) - 16;
+               nv50_disp_intr_error(priv, chid);
+               intr0 &= ~(0x00010000 << chid);
+       }
+
+       while (intr0 & 0x0000001f) {
+               u32 chid = __ffs(intr0 & 0x0000001f);
+               nv50_disp_chan_uevent_send(priv, chid);
+               intr0 &= ~(0x00000001 << chid);
+       }
+
+       if (intr1 & 0x00000004) {
+               nvkm_disp_vblank(&priv->base, 0);
+               nv_wr32(priv, 0x610024, 0x00000004);
+               intr1 &= ~0x00000004;
+       }
+
+       if (intr1 & 0x00000008) {
+               nvkm_disp_vblank(&priv->base, 1);
+               nv_wr32(priv, 0x610024, 0x00000008);
+               intr1 &= ~0x00000008;
+       }
+
+       if (intr1 & 0x00000070) {
+               priv->super = (intr1 & 0x00000070);
+               schedule_work(&priv->supervisor);
+               nv_wr32(priv, 0x610024, priv->super);
+               intr1 &= ~0x00000070;
+       }
+}
+
+static int
+nv50_disp_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+              struct nvkm_oclass *oclass, void *data, u32 size,
+              struct nvkm_object **pobject)
+{
+       struct nv50_disp_priv *priv;
+       int ret;
+
+       ret = nvkm_disp_create(parent, engine, oclass, 2, "PDISP",
+                              "display", &priv);
+       *pobject = nv_object(priv);
+       if (ret)
+               return ret;
+
+       ret = nvkm_event_init(&nv50_disp_chan_uevent, 1, 9, &priv->uevent);
+       if (ret)
+               return ret;
+
+       nv_engine(priv)->sclass = nv50_disp_main_oclass;
+       nv_engine(priv)->cclass = &nv50_disp_cclass;
+       nv_subdev(priv)->intr = nv50_disp_intr;
+       INIT_WORK(&priv->supervisor, nv50_disp_intr_supervisor);
+       priv->sclass = nv50_disp_sclass;
+       priv->head.nr = 2;
+       priv->dac.nr = 3;
+       priv->sor.nr = 2;
+       priv->pior.nr = 3;
+       priv->dac.power = nv50_dac_power;
+       priv->dac.sense = nv50_dac_sense;
+       priv->sor.power = nv50_sor_power;
+       priv->pior.power = nv50_pior_power;
+       return 0;
+}
+
+struct nvkm_oclass *
+nv50_disp_outp_sclass[] = {
+       &nv50_pior_dp_impl.base.base,
+       NULL
+};
+
+struct nvkm_oclass *
+nv50_disp_oclass = &(struct nv50_disp_impl) {
+       .base.base.handle = NV_ENGINE(DISP, 0x50),
+       .base.base.ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = nv50_disp_ctor,
+               .dtor = _nvkm_disp_dtor,
+               .init = _nvkm_disp_init,
+               .fini = _nvkm_disp_fini,
+       },
+       .base.vblank = &nv50_disp_vblank_func,
+       .base.outp =  nv50_disp_outp_sclass,
+       .mthd.core = &nv50_disp_core_mthd_chan,
+       .mthd.base = &nv50_disp_base_mthd_chan,
+       .mthd.ovly = &nv50_disp_ovly_mthd_chan,
+       .mthd.prev = 0x000004,
+       .head.scanoutpos = nv50_disp_main_scanoutpos,
+}.base.base;
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/disp/nv50.h b/drivers/gpu/drm/nouveau/nvkm/engine/disp/nv50.h
new file mode 100644 (file)
index 0000000..b4ed620
--- /dev/null
@@ -0,0 +1,226 @@
+#ifndef __NV50_DISP_H__
+#define __NV50_DISP_H__
+#include "priv.h"
+struct nvkm_output;
+struct nvkm_output_dp;
+
+#define NV50_DISP_MTHD_ struct nvkm_object *object,                            \
+       struct nv50_disp_priv *priv, void *data, u32 size
+#define NV50_DISP_MTHD_V0 NV50_DISP_MTHD_, int head
+#define NV50_DISP_MTHD_V1 NV50_DISP_MTHD_, int head, struct nvkm_output *outp
+
+struct nv50_disp_priv {
+       struct nvkm_disp base;
+       struct nvkm_oclass *sclass;
+
+       struct work_struct supervisor;
+       u32 super;
+
+       struct nvkm_event uevent;
+
+       struct {
+               int nr;
+       } head;
+       struct {
+               int nr;
+               int (*power)(NV50_DISP_MTHD_V1);
+               int (*sense)(NV50_DISP_MTHD_V1);
+       } dac;
+       struct {
+               int nr;
+               int (*power)(NV50_DISP_MTHD_V1);
+               int (*hda_eld)(NV50_DISP_MTHD_V1);
+               int (*hdmi)(NV50_DISP_MTHD_V1);
+               u32 lvdsconf;
+               void (*magic)(struct nvkm_output *);
+       } sor;
+       struct {
+               int nr;
+               int (*power)(NV50_DISP_MTHD_V1);
+               u8 type[3];
+       } pior;
+};
+
+struct nv50_disp_impl {
+       struct nvkm_disp_impl base;
+       struct {
+               const struct nv50_disp_mthd_chan *core;
+               const struct nv50_disp_mthd_chan *base;
+               const struct nv50_disp_mthd_chan *ovly;
+               int prev;
+       } mthd;
+       struct {
+               int (*scanoutpos)(NV50_DISP_MTHD_V0);
+       } head;
+};
+
+int nv50_disp_main_scanoutpos(NV50_DISP_MTHD_V0);
+int nv50_disp_main_mthd(struct nvkm_object *, u32, void *, u32);
+
+int gf110_disp_main_scanoutpos(NV50_DISP_MTHD_V0);
+
+int nv50_dac_power(NV50_DISP_MTHD_V1);
+int nv50_dac_sense(NV50_DISP_MTHD_V1);
+
+int gt215_hda_eld(NV50_DISP_MTHD_V1);
+int gf110_hda_eld(NV50_DISP_MTHD_V1);
+
+int g84_hdmi_ctrl(NV50_DISP_MTHD_V1);
+int gt215_hdmi_ctrl(NV50_DISP_MTHD_V1);
+int gf110_hdmi_ctrl(NV50_DISP_MTHD_V1);
+int gk104_hdmi_ctrl(NV50_DISP_MTHD_V1);
+
+int nv50_sor_power(NV50_DISP_MTHD_V1);
+int nv50_pior_power(NV50_DISP_MTHD_V1);
+
+#include <core/parent.h>
+
+struct nv50_disp_base {
+       struct nvkm_parent base;
+       struct nvkm_ramht *ramht;
+       u32 chan;
+};
+
+struct nv50_disp_chan_impl {
+       struct nvkm_ofuncs base;
+       int chid;
+       int  (*attach)(struct nvkm_object *, struct nvkm_object *, u32);
+       void (*detach)(struct nvkm_object *, int);
+};
+
+#include <core/namedb.h>
+
+struct nv50_disp_chan {
+       struct nvkm_namedb base;
+       int chid;
+};
+
+int  nv50_disp_chan_ntfy(struct nvkm_object *, u32, struct nvkm_event **);
+int  nv50_disp_chan_map(struct nvkm_object *, u64 *, u32 *);
+u32  nv50_disp_chan_rd32(struct nvkm_object *, u64);
+void nv50_disp_chan_wr32(struct nvkm_object *, u64, u32);
+extern const struct nvkm_event_func nv50_disp_chan_uevent;
+int  nv50_disp_chan_uevent_ctor(struct nvkm_object *, void *, u32,
+                               struct nvkm_notify *);
+void nv50_disp_chan_uevent_send(struct nv50_disp_priv *, int);
+
+extern const struct nvkm_event_func gf110_disp_chan_uevent;
+
+#define nv50_disp_chan_init(a)                                                 \
+       nvkm_namedb_init(&(a)->base)
+#define nv50_disp_chan_fini(a,b)                                               \
+       nvkm_namedb_fini(&(a)->base, (b))
+
+struct nv50_disp_dmac {
+       struct nv50_disp_chan base;
+       struct nvkm_dmaobj *pushdma;
+       u32 push;
+};
+
+void nv50_disp_dmac_dtor(struct nvkm_object *);
+
+struct nv50_disp_pioc {
+       struct nv50_disp_chan base;
+};
+
+void nv50_disp_pioc_dtor(struct nvkm_object *);
+
+struct nv50_disp_mthd_list {
+       u32 mthd;
+       u32 addr;
+       struct {
+               u32 mthd;
+               u32 addr;
+               const char *name;
+       } data[];
+};
+
+struct nv50_disp_mthd_chan {
+       const char *name;
+       u32 addr;
+       struct {
+               const char *name;
+               int nr;
+               const struct nv50_disp_mthd_list *mthd;
+       } data[];
+};
+
+extern struct nv50_disp_chan_impl nv50_disp_core_ofuncs;
+int nv50_disp_core_ctor(struct nvkm_object *, struct nvkm_object *,
+                       struct nvkm_oclass *, void *, u32,
+                       struct nvkm_object **);
+extern const struct nv50_disp_mthd_list nv50_disp_core_mthd_base;
+extern const struct nv50_disp_mthd_list nv50_disp_core_mthd_sor;
+extern const struct nv50_disp_mthd_list nv50_disp_core_mthd_pior;
+extern struct nv50_disp_chan_impl nv50_disp_base_ofuncs;
+int nv50_disp_base_ctor(struct nvkm_object *, struct nvkm_object *,
+                       struct nvkm_oclass *, void *, u32,
+                       struct nvkm_object **);
+extern const struct nv50_disp_mthd_list nv50_disp_base_mthd_image;
+extern struct nv50_disp_chan_impl nv50_disp_ovly_ofuncs;
+int nv50_disp_ovly_ctor(struct nvkm_object *, struct nvkm_object *,
+                       struct nvkm_oclass *, void *, u32,
+                       struct nvkm_object **);
+extern const struct nv50_disp_mthd_list nv50_disp_ovly_mthd_base;
+extern struct nv50_disp_chan_impl nv50_disp_oimm_ofuncs;
+int nv50_disp_oimm_ctor(struct nvkm_object *, struct nvkm_object *,
+                       struct nvkm_oclass *, void *, u32,
+                       struct nvkm_object **);
+extern struct nv50_disp_chan_impl nv50_disp_curs_ofuncs;
+int nv50_disp_curs_ctor(struct nvkm_object *, struct nvkm_object *,
+                       struct nvkm_oclass *, void *, u32,
+                       struct nvkm_object **);
+extern struct nvkm_ofuncs nv50_disp_main_ofuncs;
+int  nv50_disp_main_ctor(struct nvkm_object *, struct nvkm_object *,
+                        struct nvkm_oclass *, void *, u32,
+                        struct nvkm_object **);
+void nv50_disp_main_dtor(struct nvkm_object *);
+extern struct nvkm_omthds nv50_disp_main_omthds[];
+extern struct nvkm_oclass nv50_disp_cclass;
+void nv50_disp_mthd_chan(struct nv50_disp_priv *, int debug, int head,
+                        const struct nv50_disp_mthd_chan *);
+void nv50_disp_intr_supervisor(struct work_struct *);
+void nv50_disp_intr(struct nvkm_subdev *);
+extern const struct nvkm_event_func nv50_disp_vblank_func;
+
+extern const struct nv50_disp_mthd_chan g84_disp_core_mthd_chan;
+extern const struct nv50_disp_mthd_list g84_disp_core_mthd_dac;
+extern const struct nv50_disp_mthd_list g84_disp_core_mthd_head;
+extern const struct nv50_disp_mthd_chan g84_disp_base_mthd_chan;
+extern const struct nv50_disp_mthd_chan g84_disp_ovly_mthd_chan;
+
+extern const struct nv50_disp_mthd_chan g94_disp_core_mthd_chan;
+
+extern struct nv50_disp_chan_impl gf110_disp_core_ofuncs;
+extern const struct nv50_disp_mthd_list gf110_disp_core_mthd_base;
+extern const struct nv50_disp_mthd_list gf110_disp_core_mthd_dac;
+extern const struct nv50_disp_mthd_list gf110_disp_core_mthd_sor;
+extern const struct nv50_disp_mthd_list gf110_disp_core_mthd_pior;
+extern struct nv50_disp_chan_impl gf110_disp_base_ofuncs;
+extern struct nv50_disp_chan_impl gf110_disp_ovly_ofuncs;
+extern const struct nv50_disp_mthd_chan gf110_disp_base_mthd_chan;
+extern struct nv50_disp_chan_impl gf110_disp_oimm_ofuncs;
+extern struct nv50_disp_chan_impl gf110_disp_curs_ofuncs;
+extern struct nvkm_ofuncs gf110_disp_main_ofuncs;
+extern struct nvkm_oclass gf110_disp_cclass;
+void gf110_disp_intr_supervisor(struct work_struct *);
+void gf110_disp_intr(struct nvkm_subdev *);
+extern const struct nvkm_event_func gf110_disp_vblank_func;
+
+extern const struct nv50_disp_mthd_chan gk104_disp_core_mthd_chan;
+extern const struct nv50_disp_mthd_chan gk104_disp_ovly_mthd_chan;
+
+extern struct nvkm_output_dp_impl nv50_pior_dp_impl;
+extern struct nvkm_oclass *nv50_disp_outp_sclass[];
+
+extern struct nvkm_output_dp_impl g94_sor_dp_impl;
+int g94_sor_dp_lnk_pwr(struct nvkm_output_dp *, int);
+extern struct nvkm_oclass *g94_disp_outp_sclass[];
+
+extern struct nvkm_output_dp_impl gf110_sor_dp_impl;
+int gf110_sor_dp_lnk_ctl(struct nvkm_output_dp *, int, int, bool);
+extern struct nvkm_oclass *gf110_disp_outp_sclass[];
+
+void gm204_sor_magic(struct nvkm_output *outp);
+extern struct nvkm_output_dp_impl gm204_sor_dp_impl;
+#endif
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/disp/outp.c b/drivers/gpu/drm/nouveau/nvkm/engine/disp/outp.c
new file mode 100644 (file)
index 0000000..9224bcb
--- /dev/null
@@ -0,0 +1,142 @@
+/*
+ * Copyright 2014 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 "outp.h"
+#include "priv.h"
+
+#include <subdev/bios.h>
+#include <subdev/bios/conn.h>
+#include <subdev/bios/dcb.h>
+#include <subdev/i2c.h>
+
+int
+_nvkm_output_fini(struct nvkm_object *object, bool suspend)
+{
+       struct nvkm_output *outp = (void *)object;
+       nv_ofuncs(outp->conn)->fini(nv_object(outp->conn), suspend);
+       return nvkm_object_fini(&outp->base, suspend);
+}
+
+int
+_nvkm_output_init(struct nvkm_object *object)
+{
+       struct nvkm_output *outp = (void *)object;
+       int ret = nvkm_object_init(&outp->base);
+       if (ret == 0)
+               nv_ofuncs(outp->conn)->init(nv_object(outp->conn));
+       return 0;
+}
+
+void
+_nvkm_output_dtor(struct nvkm_object *object)
+{
+       struct nvkm_output *outp = (void *)object;
+       list_del(&outp->head);
+       nvkm_object_ref(NULL, (void *)&outp->conn);
+       nvkm_object_destroy(&outp->base);
+}
+
+int
+nvkm_output_create_(struct nvkm_object *parent,
+                   struct nvkm_object *engine,
+                   struct nvkm_oclass *oclass,
+                   struct dcb_output *dcbE, int index,
+                   int length, void **pobject)
+{
+       struct nvkm_disp *disp = nvkm_disp(parent);
+       struct nvkm_bios *bios = nvkm_bios(parent);
+       struct nvkm_i2c *i2c = nvkm_i2c(parent);
+       struct nvbios_connE connE;
+       struct nvkm_output *outp;
+       u8  ver, hdr;
+       u32 data;
+       int ret;
+
+       ret = nvkm_object_create_(parent, engine, oclass, 0, length, pobject);
+       outp = *pobject;
+       if (ret)
+               return ret;
+
+       outp->info = *dcbE;
+       outp->index = index;
+       outp->or = ffs(outp->info.or) - 1;
+
+       DBG("type %02x loc %d or %d link %d con %x edid %x bus %d head %x\n",
+           dcbE->type, dcbE->location, dcbE->or, dcbE->type >= 2 ?
+           dcbE->sorconf.link : 0, dcbE->connector, dcbE->i2c_index,
+           dcbE->bus, dcbE->heads);
+
+       if (outp->info.type != DCB_OUTPUT_DP)
+               outp->port = i2c->find(i2c, NV_I2C_PORT(outp->info.i2c_index));
+       else
+               outp->port = i2c->find(i2c, NV_I2C_AUX(outp->info.i2c_index));
+       outp->edid = outp->port;
+
+       data = nvbios_connEp(bios, outp->info.connector, &ver, &hdr, &connE);
+       if (!data) {
+               DBG("vbios connector data not found\n");
+               memset(&connE, 0x00, sizeof(connE));
+               connE.type = DCB_CONNECTOR_NONE;
+       }
+
+       ret = nvkm_object_ctor(parent, NULL, nvkm_connector_oclass,
+                              &connE, outp->info.connector,
+                              (struct nvkm_object **)&outp->conn);
+       if (ret < 0) {
+               ERR("error %d creating connector, disabling\n", ret);
+               return ret;
+       }
+
+       list_add_tail(&outp->head, &disp->outp);
+       return 0;
+}
+
+int
+_nvkm_output_ctor(struct nvkm_object *parent,
+                 struct nvkm_object *engine,
+                 struct nvkm_oclass *oclass, void *dcbE, u32 index,
+                 struct nvkm_object **pobject)
+{
+       struct nvkm_output *outp;
+       int ret;
+
+       ret = nvkm_output_create(parent, engine, oclass, dcbE, index, &outp);
+       *pobject = nv_object(outp);
+       if (ret)
+               return ret;
+
+       return 0;
+}
+
+struct nvkm_oclass *
+nvkm_output_oclass = &(struct nvkm_output_impl) {
+       .base = {
+               .handle = 0,
+               .ofuncs = &(struct nvkm_ofuncs) {
+                       .ctor = _nvkm_output_ctor,
+                       .dtor = _nvkm_output_dtor,
+                       .init = _nvkm_output_init,
+                       .fini = _nvkm_output_fini,
+               },
+       },
+}.base;
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/disp/outp.h b/drivers/gpu/drm/nouveau/nvkm/engine/disp/outp.h
new file mode 100644 (file)
index 0000000..d9253d2
--- /dev/null
@@ -0,0 +1,61 @@
+#ifndef __NVKM_DISP_OUTP_H__
+#define __NVKM_DISP_OUTP_H__
+#include <core/object.h>
+
+#include <subdev/bios.h>
+#include <subdev/bios/dcb.h>
+
+struct nvkm_output {
+       struct nvkm_object base;
+       struct list_head head;
+
+       struct dcb_output info;
+       int index;
+       int or;
+
+       struct nvkm_i2c_port *port;
+       struct nvkm_i2c_port *edid;
+
+       struct nvkm_connector *conn;
+};
+
+#define nvkm_output_create(p,e,c,b,i,d)                                        \
+       nvkm_output_create_((p), (e), (c), (b), (i), sizeof(**d), (void **)d)
+#define nvkm_output_destroy(d) ({                                              \
+       struct nvkm_output *_outp = (d);                                       \
+       _nvkm_output_dtor(nv_object(_outp));                                   \
+})
+#define nvkm_output_init(d) ({                                                 \
+       struct nvkm_output *_outp = (d);                                       \
+       _nvkm_output_init(nv_object(_outp));                                   \
+})
+#define nvkm_output_fini(d,s) ({                                               \
+       struct nvkm_output *_outp = (d);                                       \
+       _nvkm_output_fini(nv_object(_outp), (s));                              \
+})
+
+int nvkm_output_create_(struct nvkm_object *, struct nvkm_object *,
+                       struct nvkm_oclass *, struct dcb_output *,
+                       int, int, void **);
+
+int  _nvkm_output_ctor(struct nvkm_object *, struct nvkm_object *,
+                      struct nvkm_oclass *, void *, u32,
+                      struct nvkm_object **);
+void _nvkm_output_dtor(struct nvkm_object *);
+int  _nvkm_output_init(struct nvkm_object *);
+int  _nvkm_output_fini(struct nvkm_object *, bool);
+
+struct nvkm_output_impl {
+       struct nvkm_oclass base;
+};
+
+#ifndef MSG
+#define MSG(l,f,a...) do {                                                     \
+       struct nvkm_output *_outp = (void *)outp;                              \
+       nv_##l(_outp, "%02x:%04x:%04x: "f, _outp->index,                       \
+              _outp->info.hasht, _outp->info.hashm, ##a);                     \
+} while(0)
+#define DBG(f,a...) MSG(debug, f, ##a)
+#define ERR(f,a...) MSG(error, f, ##a)
+#endif
+#endif
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/disp/outpdp.c b/drivers/gpu/drm/nouveau/nvkm/engine/disp/outpdp.c
new file mode 100644 (file)
index 0000000..0bde0fa
--- /dev/null
@@ -0,0 +1,301 @@
+/*
+ * Copyright 2014 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 "outpdp.h"
+#include "conn.h"
+#include "dport.h"
+#include "priv.h"
+
+#include <subdev/i2c.h>
+
+#include <nvif/event.h>
+
+int
+nvkm_output_dp_train(struct nvkm_output *base, u32 datarate, bool wait)
+{
+       struct nvkm_output_dp *outp = (void *)base;
+       bool retrain = true;
+       u8 link[2], stat[3];
+       u32 linkrate;
+       int ret, i;
+
+       /* check that the link is trained at a high enough rate */
+       ret = nv_rdaux(outp->base.edid, DPCD_LC00_LINK_BW_SET, link, 2);
+       if (ret) {
+               DBG("failed to read link config, assuming no sink\n");
+               goto done;
+       }
+
+       linkrate = link[0] * 27000 * (link[1] & DPCD_LC01_LANE_COUNT_SET);
+       linkrate = (linkrate * 8) / 10; /* 8B/10B coding overhead */
+       datarate = (datarate + 9) / 10; /* -> decakilobits */
+       if (linkrate < datarate) {
+               DBG("link not trained at sufficient rate\n");
+               goto done;
+       }
+
+       /* check that link is still trained */
+       ret = nv_rdaux(outp->base.edid, DPCD_LS02, stat, 3);
+       if (ret) {
+               DBG("failed to read link status, assuming no sink\n");
+               goto done;
+       }
+
+       if (stat[2] & DPCD_LS04_INTERLANE_ALIGN_DONE) {
+               for (i = 0; i < (link[1] & DPCD_LC01_LANE_COUNT_SET); i++) {
+                       u8 lane = (stat[i >> 1] >> ((i & 1) * 4)) & 0x0f;
+                       if (!(lane & DPCD_LS02_LANE0_CR_DONE) ||
+                           !(lane & DPCD_LS02_LANE0_CHANNEL_EQ_DONE) ||
+                           !(lane & DPCD_LS02_LANE0_SYMBOL_LOCKED)) {
+                               DBG("lane %d not equalised\n", lane);
+                               goto done;
+                       }
+               }
+               retrain = false;
+       } else {
+               DBG("no inter-lane alignment\n");
+       }
+
+done:
+       if (retrain || !atomic_read(&outp->lt.done)) {
+               /* no sink, but still need to configure source */
+               if (outp->dpcd[DPCD_RC00_DPCD_REV] == 0x00) {
+                       outp->dpcd[DPCD_RC01_MAX_LINK_RATE] =
+                               outp->base.info.dpconf.link_bw;
+                       outp->dpcd[DPCD_RC02] =
+                               outp->base.info.dpconf.link_nr;
+               }
+               atomic_set(&outp->lt.done, 0);
+               schedule_work(&outp->lt.work);
+       } else {
+               nvkm_notify_get(&outp->irq);
+       }
+
+       if (wait) {
+               if (!wait_event_timeout(outp->lt.wait,
+                                       atomic_read(&outp->lt.done),
+                                       msecs_to_jiffies(2000)))
+                       ret = -ETIMEDOUT;
+       }
+
+       return ret;
+}
+
+static void
+nvkm_output_dp_enable(struct nvkm_output_dp *outp, bool present)
+{
+       struct nvkm_i2c_port *port = outp->base.edid;
+       if (present) {
+               if (!outp->present) {
+                       nvkm_i2c(port)->acquire_pad(port, 0);
+                       DBG("aux power -> always\n");
+                       outp->present = true;
+               }
+               nvkm_output_dp_train(&outp->base, 0, true);
+       } else {
+               if (outp->present) {
+                       nvkm_i2c(port)->release_pad(port);
+                       DBG("aux power -> demand\n");
+                       outp->present = false;
+               }
+               atomic_set(&outp->lt.done, 0);
+       }
+}
+
+static void
+nvkm_output_dp_detect(struct nvkm_output_dp *outp)
+{
+       struct nvkm_i2c_port *port = outp->base.edid;
+       int ret = nvkm_i2c(port)->acquire_pad(port, 0);
+       if (ret == 0) {
+               ret = nv_rdaux(outp->base.edid, DPCD_RC00_DPCD_REV,
+                              outp->dpcd, sizeof(outp->dpcd));
+               nvkm_output_dp_enable(outp, ret == 0);
+               nvkm_i2c(port)->release_pad(port);
+       }
+}
+
+static int
+nvkm_output_dp_hpd(struct nvkm_notify *notify)
+{
+       struct nvkm_connector *conn = container_of(notify, typeof(*conn), hpd);
+       struct nvkm_output_dp *outp;
+       struct nvkm_disp *disp = nvkm_disp(conn);
+       const struct nvkm_i2c_ntfy_rep *line = notify->data;
+       struct nvif_notify_conn_rep_v0 rep = {};
+
+       list_for_each_entry(outp, &disp->outp, base.head) {
+               if (outp->base.conn == conn &&
+                   outp->info.type == DCB_OUTPUT_DP) {
+                       DBG("HPD: %d\n", line->mask);
+                       nvkm_output_dp_detect(outp);
+
+                       if (line->mask & NVKM_I2C_UNPLUG)
+                               rep.mask |= NVIF_NOTIFY_CONN_V0_UNPLUG;
+                       if (line->mask & NVKM_I2C_PLUG)
+                               rep.mask |= NVIF_NOTIFY_CONN_V0_PLUG;
+
+                       nvkm_event_send(&disp->hpd, rep.mask, conn->index,
+                                       &rep, sizeof(rep));
+                       return NVKM_NOTIFY_KEEP;
+               }
+       }
+
+       WARN_ON(1);
+       return NVKM_NOTIFY_DROP;
+}
+
+static int
+nvkm_output_dp_irq(struct nvkm_notify *notify)
+{
+       struct nvkm_output_dp *outp = container_of(notify, typeof(*outp), irq);
+       struct nvkm_disp *disp = nvkm_disp(outp);
+       const struct nvkm_i2c_ntfy_rep *line = notify->data;
+       struct nvif_notify_conn_rep_v0 rep = {
+               .mask = NVIF_NOTIFY_CONN_V0_IRQ,
+       };
+       int index = outp->base.info.connector;
+
+       DBG("IRQ: %d\n", line->mask);
+       nvkm_output_dp_train(&outp->base, 0, true);
+
+       nvkm_event_send(&disp->hpd, rep.mask, index, &rep, sizeof(rep));
+       return NVKM_NOTIFY_DROP;
+}
+
+int
+_nvkm_output_dp_fini(struct nvkm_object *object, bool suspend)
+{
+       struct nvkm_output_dp *outp = (void *)object;
+       nvkm_notify_put(&outp->irq);
+       nvkm_output_dp_enable(outp, false);
+       return nvkm_output_fini(&outp->base, suspend);
+}
+
+int
+_nvkm_output_dp_init(struct nvkm_object *object)
+{
+       struct nvkm_output_dp *outp = (void *)object;
+       nvkm_output_dp_detect(outp);
+       return nvkm_output_init(&outp->base);
+}
+
+void
+_nvkm_output_dp_dtor(struct nvkm_object *object)
+{
+       struct nvkm_output_dp *outp = (void *)object;
+       nvkm_notify_fini(&outp->irq);
+       nvkm_output_destroy(&outp->base);
+}
+
+int
+nvkm_output_dp_create_(struct nvkm_object *parent,
+                      struct nvkm_object *engine,
+                      struct nvkm_oclass *oclass,
+                      struct dcb_output *info, int index,
+                      int length, void **pobject)
+{
+       struct nvkm_bios *bios = nvkm_bios(parent);
+       struct nvkm_i2c *i2c = nvkm_i2c(parent);
+       struct nvkm_output_dp *outp;
+       u8  hdr, cnt, len;
+       u32 data;
+       int ret;
+
+       ret = nvkm_output_create_(parent, engine, oclass, info, index,
+                                 length, pobject);
+       outp = *pobject;
+       if (ret)
+               return ret;
+
+       nvkm_notify_fini(&outp->base.conn->hpd);
+
+       /* access to the aux channel is not optional... */
+       if (!outp->base.edid) {
+               ERR("aux channel not found\n");
+               return -ENODEV;
+       }
+
+       /* nor is the bios data for this output... */
+       data = nvbios_dpout_match(bios, outp->base.info.hasht,
+                                 outp->base.info.hashm, &outp->version,
+                                 &hdr, &cnt, &len, &outp->info);
+       if (!data) {
+               ERR("no bios dp data\n");
+               return -ENODEV;
+       }
+
+       DBG("bios dp %02x %02x %02x %02x\n", outp->version, hdr, cnt, len);
+
+       /* link training */
+       INIT_WORK(&outp->lt.work, nvkm_dp_train);
+       init_waitqueue_head(&outp->lt.wait);
+       atomic_set(&outp->lt.done, 0);
+
+       /* link maintenance */
+       ret = nvkm_notify_init(NULL, &i2c->event, nvkm_output_dp_irq, true,
+                              &(struct nvkm_i2c_ntfy_req) {
+                               .mask = NVKM_I2C_IRQ,
+                               .port = outp->base.edid->index,
+                              },
+                              sizeof(struct nvkm_i2c_ntfy_req),
+                              sizeof(struct nvkm_i2c_ntfy_rep),
+                              &outp->irq);
+       if (ret) {
+               ERR("error monitoring aux irq event: %d\n", ret);
+               return ret;
+       }
+
+       /* hotplug detect, replaces gpio-based mechanism with aux events */
+       ret = nvkm_notify_init(NULL, &i2c->event, nvkm_output_dp_hpd, true,
+                              &(struct nvkm_i2c_ntfy_req) {
+                               .mask = NVKM_I2C_PLUG | NVKM_I2C_UNPLUG,
+                               .port = outp->base.edid->index,
+                              },
+                              sizeof(struct nvkm_i2c_ntfy_req),
+                              sizeof(struct nvkm_i2c_ntfy_rep),
+                              &outp->base.conn->hpd);
+       if (ret) {
+               ERR("error monitoring aux hpd events: %d\n", ret);
+               return ret;
+       }
+
+       return 0;
+}
+
+int
+_nvkm_output_dp_ctor(struct nvkm_object *parent,
+                    struct nvkm_object *engine,
+                    struct nvkm_oclass *oclass, void *info, u32 index,
+                    struct nvkm_object **pobject)
+{
+       struct nvkm_output_dp *outp;
+       int ret;
+
+       ret = nvkm_output_dp_create(parent, engine, oclass, info, index, &outp);
+       *pobject = nv_object(outp);
+       if (ret)
+               return ret;
+
+       return 0;
+}
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/disp/outpdp.h b/drivers/gpu/drm/nouveau/nvkm/engine/disp/outpdp.h
new file mode 100644 (file)
index 0000000..70c77ae
--- /dev/null
@@ -0,0 +1,61 @@
+#ifndef __NVKM_DISP_OUTP_DP_H__
+#define __NVKM_DISP_OUTP_DP_H__
+#include "outp.h"
+
+#include <core/notify.h>
+#include <subdev/bios.h>
+#include <subdev/bios/dp.h>
+
+struct nvkm_output_dp {
+       struct nvkm_output base;
+
+       struct nvbios_dpout info;
+       u8 version;
+
+       struct nvkm_notify irq;
+       bool present;
+       u8 dpcd[16];
+
+       struct {
+               struct work_struct work;
+               wait_queue_head_t wait;
+               atomic_t done;
+       } lt;
+};
+
+#define nvkm_output_dp_create(p,e,c,b,i,d)                                     \
+       nvkm_output_dp_create_((p), (e), (c), (b), (i), sizeof(**d), (void **)d)
+#define nvkm_output_dp_destroy(d) ({                                           \
+       struct nvkm_output_dp *_outp = (d);                                    \
+       _nvkm_output_dp_dtor(nv_object(_outp));                                \
+})
+#define nvkm_output_dp_init(d) ({                                              \
+       struct nvkm_output_dp *_outp = (d);                                    \
+       _nvkm_output_dp_init(nv_object(_outp));                                \
+})
+#define nvkm_output_dp_fini(d,s) ({                                            \
+       struct nvkm_output_dp *_outp = (d);                                    \
+       _nvkm_output_dp_fini(nv_object(_outp), (s));                           \
+})
+
+int nvkm_output_dp_create_(struct nvkm_object *, struct nvkm_object *,
+                          struct nvkm_oclass *, struct dcb_output *,
+                          int, int, void **);
+
+int  _nvkm_output_dp_ctor(struct nvkm_object *, struct nvkm_object *,
+                         struct nvkm_oclass *, void *, u32,
+                         struct nvkm_object **);
+void _nvkm_output_dp_dtor(struct nvkm_object *);
+int  _nvkm_output_dp_init(struct nvkm_object *);
+int  _nvkm_output_dp_fini(struct nvkm_object *, bool);
+
+struct nvkm_output_dp_impl {
+       struct nvkm_output_impl base;
+       int (*pattern)(struct nvkm_output_dp *, int);
+       int (*lnk_pwr)(struct nvkm_output_dp *, int nr);
+       int (*lnk_ctl)(struct nvkm_output_dp *, int nr, int bw, bool ef);
+       int (*drv_ctl)(struct nvkm_output_dp *, int ln, int vs, int pe, int pc);
+};
+
+int nvkm_output_dp_train(struct nvkm_output *, u32 rate, bool wait);
+#endif
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/disp/piornv50.c b/drivers/gpu/drm/nouveau/nvkm/engine/disp/piornv50.c
new file mode 100644 (file)
index 0000000..2a1d887
--- /dev/null
@@ -0,0 +1,170 @@
+/*
+ * Copyright 2012 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 "nv50.h"
+#include "outpdp.h"
+
+#include <core/client.h>
+#include <subdev/i2c.h>
+#include <subdev/timer.h>
+
+#include <nvif/class.h>
+#include <nvif/unpack.h>
+
+/******************************************************************************
+ * TMDS
+ *****************************************************************************/
+
+static int
+nv50_pior_tmds_ctor(struct nvkm_object *parent,
+                   struct nvkm_object *engine,
+                   struct nvkm_oclass *oclass, void *info, u32 index,
+                   struct nvkm_object **pobject)
+{
+       struct nvkm_i2c *i2c = nvkm_i2c(parent);
+       struct nvkm_output *outp;
+       int ret;
+
+       ret = nvkm_output_create(parent, engine, oclass, info, index, &outp);
+       *pobject = nv_object(outp);
+       if (ret)
+               return ret;
+
+       outp->edid = i2c->find_type(i2c, NV_I2C_TYPE_EXTDDC(outp->info.extdev));
+       return 0;
+}
+
+struct nvkm_output_impl
+nv50_pior_tmds_impl = {
+       .base.handle = DCB_OUTPUT_TMDS | 0x0100,
+       .base.ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = nv50_pior_tmds_ctor,
+               .dtor = _nvkm_output_dtor,
+               .init = _nvkm_output_init,
+               .fini = _nvkm_output_fini,
+       },
+};
+
+/******************************************************************************
+ * DisplayPort
+ *****************************************************************************/
+
+static int
+nv50_pior_dp_pattern(struct nvkm_output_dp *outp, int pattern)
+{
+       struct nvkm_i2c_port *port = outp->base.edid;
+       if (port && port->func->pattern)
+               return port->func->pattern(port, pattern);
+       return port ? 0 : -ENODEV;
+}
+
+static int
+nv50_pior_dp_lnk_pwr(struct nvkm_output_dp *outp, int nr)
+{
+       return 0;
+}
+
+static int
+nv50_pior_dp_lnk_ctl(struct nvkm_output_dp *outp, int nr, int bw, bool ef)
+{
+       struct nvkm_i2c_port *port = outp->base.edid;
+       if (port && port->func->lnk_ctl)
+               return port->func->lnk_ctl(port, nr, bw, ef);
+       return port ? 0 : -ENODEV;
+}
+
+static int
+nv50_pior_dp_drv_ctl(struct nvkm_output_dp *outp, int ln, int vs, int pe, int pc)
+{
+       struct nvkm_i2c_port *port = outp->base.edid;
+       if (port && port->func->drv_ctl)
+               return port->func->drv_ctl(port, ln, vs, pe);
+       return port ? 0 : -ENODEV;
+}
+
+static int
+nv50_pior_dp_ctor(struct nvkm_object *parent,
+                 struct nvkm_object *engine,
+                 struct nvkm_oclass *oclass, void *info, u32 index,
+                 struct nvkm_object **pobject)
+{
+       struct nvkm_i2c *i2c = nvkm_i2c(parent);
+       struct nvkm_output_dp *outp;
+       int ret;
+
+       ret = nvkm_output_dp_create(parent, engine, oclass, info, index, &outp);
+       *pobject = nv_object(outp);
+       if (ret)
+               return ret;
+
+       outp->base.edid = i2c->find_type(i2c, NV_I2C_TYPE_EXTAUX(
+                                        outp->base.info.extdev));
+       return 0;
+}
+
+struct nvkm_output_dp_impl
+nv50_pior_dp_impl = {
+       .base.base.handle = DCB_OUTPUT_DP | 0x0010,
+       .base.base.ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = nv50_pior_dp_ctor,
+               .dtor = _nvkm_output_dp_dtor,
+               .init = _nvkm_output_dp_init,
+               .fini = _nvkm_output_dp_fini,
+       },
+       .pattern = nv50_pior_dp_pattern,
+       .lnk_pwr = nv50_pior_dp_lnk_pwr,
+       .lnk_ctl = nv50_pior_dp_lnk_ctl,
+       .drv_ctl = nv50_pior_dp_drv_ctl,
+};
+
+/******************************************************************************
+ * General PIOR handling
+ *****************************************************************************/
+
+int
+nv50_pior_power(NV50_DISP_MTHD_V1)
+{
+       const u32 soff = outp->or * 0x800;
+       union {
+               struct nv50_disp_pior_pwr_v0 v0;
+       } *args = data;
+       u32 ctrl, type;
+       int ret;
+
+       nv_ioctl(object, "disp pior pwr size %d\n", size);
+       if (nvif_unpack(args->v0, 0, 0, false)) {
+               nv_ioctl(object, "disp pior pwr vers %d state %d type %x\n",
+                        args->v0.version, args->v0.state, args->v0.type);
+               if (args->v0.type > 0x0f)
+                       return -EINVAL;
+               ctrl = !!args->v0.state;
+               type = args->v0.type;
+       } else
+               return ret;
+
+       nv_wait(priv, 0x61e004 + soff, 0x80000000, 0x00000000);
+       nv_mask(priv, 0x61e004 + soff, 0x80000101, 0x80000000 | ctrl);
+       nv_wait(priv, 0x61e004 + soff, 0x80000000, 0x00000000);
+       priv->pior.type[outp->or] = type;
+       return 0;
+}
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/disp/priv.h b/drivers/gpu/drm/nouveau/nvkm/engine/disp/priv.h
new file mode 100644 (file)
index 0000000..961ce8b
--- /dev/null
@@ -0,0 +1,42 @@
+#ifndef __NVKM_DISP_PRIV_H__
+#define __NVKM_DISP_PRIV_H__
+#include <engine/disp.h>
+
+struct nvkm_disp_impl {
+       struct nvkm_oclass base;
+       struct nvkm_oclass **outp;
+       struct nvkm_oclass **conn;
+       const struct nvkm_event_func *vblank;
+};
+
+#define nvkm_disp_create(p,e,c,h,i,x,d)                                     \
+       nvkm_disp_create_((p), (e), (c), (h), (i), (x),                     \
+                            sizeof(**d), (void **)d)
+#define nvkm_disp_destroy(d) ({                                             \
+       struct nvkm_disp *disp = (d);                                       \
+       _nvkm_disp_dtor(nv_object(disp));                                   \
+})
+#define nvkm_disp_init(d) ({                                                \
+       struct nvkm_disp *disp = (d);                                       \
+       _nvkm_disp_init(nv_object(disp));                                   \
+})
+#define nvkm_disp_fini(d,s) ({                                              \
+       struct nvkm_disp *disp = (d);                                       \
+       _nvkm_disp_fini(nv_object(disp), (s));                              \
+})
+
+int  nvkm_disp_create_(struct nvkm_object *, struct nvkm_object *,
+                         struct nvkm_oclass *, int heads,
+                         const char *, const char *, int, void **);
+void _nvkm_disp_dtor(struct nvkm_object *);
+int  _nvkm_disp_init(struct nvkm_object *);
+int  _nvkm_disp_fini(struct nvkm_object *, bool);
+
+extern struct nvkm_oclass *nvkm_output_oclass;
+extern struct nvkm_oclass *nvkm_connector_oclass;
+
+int  nvkm_disp_vblank_ctor(struct nvkm_object *, void *data, u32 size,
+                          struct nvkm_notify *);
+void nvkm_disp_vblank(struct nvkm_disp *, int head);
+int  nvkm_disp_ntfy(struct nvkm_object *, u32, struct nvkm_event **);
+#endif
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/disp/sorg94.c b/drivers/gpu/drm/nouveau/nvkm/engine/disp/sorg94.c
new file mode 100644 (file)
index 0000000..8918da7
--- /dev/null
@@ -0,0 +1,145 @@
+/*
+ * Copyright 2012 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 "nv50.h"
+#include "outpdp.h"
+
+#include <core/device.h>
+#include <subdev/timer.h>
+
+static inline u32
+g94_sor_soff(struct nvkm_output_dp *outp)
+{
+       return (ffs(outp->base.info.or) - 1) * 0x800;
+}
+
+static inline u32
+g94_sor_loff(struct nvkm_output_dp *outp)
+{
+       return g94_sor_soff(outp) + !(outp->base.info.sorconf.link & 1) * 0x80;
+}
+
+static inline u32
+g94_sor_dp_lane_map(struct nv50_disp_priv *priv, u8 lane)
+{
+       static const u8 mcp89[] = { 24, 16, 8, 0 }; /* thanks, apple.. */
+       static const u8 g94[] = { 16, 8, 0, 24 };
+       if (nv_device(priv)->chipset == 0xaf)
+               return mcp89[lane];
+       return g94[lane];
+}
+
+static int
+g94_sor_dp_pattern(struct nvkm_output_dp *outp, int pattern)
+{
+       struct nv50_disp_priv *priv = (void *)nvkm_disp(outp);
+       const u32 loff = g94_sor_loff(outp);
+       nv_mask(priv, 0x61c10c + loff, 0x0f000000, pattern << 24);
+       return 0;
+}
+
+int
+g94_sor_dp_lnk_pwr(struct nvkm_output_dp *outp, int nr)
+{
+       struct nv50_disp_priv *priv = (void *)nvkm_disp(outp);
+       const u32 soff = g94_sor_soff(outp);
+       const u32 loff = g94_sor_loff(outp);
+       u32 mask = 0, i;
+
+       for (i = 0; i < nr; i++)
+               mask |= 1 << (g94_sor_dp_lane_map(priv, i) >> 3);
+
+       nv_mask(priv, 0x61c130 + loff, 0x0000000f, mask);
+       nv_mask(priv, 0x61c034 + soff, 0x80000000, 0x80000000);
+       nv_wait(priv, 0x61c034 + soff, 0x80000000, 0x00000000);
+       return 0;
+}
+
+static int
+g94_sor_dp_lnk_ctl(struct nvkm_output_dp *outp, int nr, int bw, bool ef)
+{
+       struct nv50_disp_priv *priv = (void *)nvkm_disp(outp);
+       const u32 soff = g94_sor_soff(outp);
+       const u32 loff = g94_sor_loff(outp);
+       u32 dpctrl = 0x00000000;
+       u32 clksor = 0x00000000;
+
+       dpctrl |= ((1 << nr) - 1) << 16;
+       if (ef)
+               dpctrl |= 0x00004000;
+       if (bw > 0x06)
+               clksor |= 0x00040000;
+
+       nv_mask(priv, 0x614300 + soff, 0x000c0000, clksor);
+       nv_mask(priv, 0x61c10c + loff, 0x001f4000, dpctrl);
+       return 0;
+}
+
+static int
+g94_sor_dp_drv_ctl(struct nvkm_output_dp *outp, int ln, int vs, int pe, int pc)
+{
+       struct nv50_disp_priv *priv = (void *)nvkm_disp(outp);
+       struct nvkm_bios *bios = nvkm_bios(priv);
+       const u32 shift = g94_sor_dp_lane_map(priv, ln);
+       const u32 loff = g94_sor_loff(outp);
+       u32 addr, data[3];
+       u8  ver, hdr, cnt, len;
+       struct nvbios_dpout info;
+       struct nvbios_dpcfg ocfg;
+
+       addr = nvbios_dpout_match(bios, outp->base.info.hasht,
+                                       outp->base.info.hashm,
+                                &ver, &hdr, &cnt, &len, &info);
+       if (!addr)
+               return -ENODEV;
+
+       addr = nvbios_dpcfg_match(bios, addr, 0, vs, pe,
+                                &ver, &hdr, &cnt, &len, &ocfg);
+       if (!addr)
+               return -EINVAL;
+
+       data[0] = nv_rd32(priv, 0x61c118 + loff) & ~(0x000000ff << shift);
+       data[1] = nv_rd32(priv, 0x61c120 + loff) & ~(0x000000ff << shift);
+       data[2] = nv_rd32(priv, 0x61c130 + loff);
+       if ((data[2] & 0x0000ff00) < (ocfg.tx_pu << 8) || ln == 0)
+               data[2] = (data[2] & ~0x0000ff00) | (ocfg.tx_pu << 8);
+       nv_wr32(priv, 0x61c118 + loff, data[0] | (ocfg.dc << shift));
+       nv_wr32(priv, 0x61c120 + loff, data[1] | (ocfg.pe << shift));
+       nv_wr32(priv, 0x61c130 + loff, data[2] | (ocfg.tx_pu << 8));
+       return 0;
+}
+
+struct nvkm_output_dp_impl
+g94_sor_dp_impl = {
+       .base.base.handle = DCB_OUTPUT_DP,
+       .base.base.ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = _nvkm_output_dp_ctor,
+               .dtor = _nvkm_output_dp_dtor,
+               .init = _nvkm_output_dp_init,
+               .fini = _nvkm_output_dp_fini,
+       },
+       .pattern = g94_sor_dp_pattern,
+       .lnk_pwr = g94_sor_dp_lnk_pwr,
+       .lnk_ctl = g94_sor_dp_lnk_ctl,
+       .drv_ctl = g94_sor_dp_drv_ctl,
+};
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/disp/sorgf110.c b/drivers/gpu/drm/nouveau/nvkm/engine/disp/sorgf110.c
new file mode 100644 (file)
index 0000000..52fbe48
--- /dev/null
@@ -0,0 +1,124 @@
+/*
+ * Copyright 2012 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 "nv50.h"
+#include "outpdp.h"
+
+static inline u32
+gf110_sor_soff(struct nvkm_output_dp *outp)
+{
+       return (ffs(outp->base.info.or) - 1) * 0x800;
+}
+
+static inline u32
+gf110_sor_loff(struct nvkm_output_dp *outp)
+{
+       return gf110_sor_soff(outp) + !(outp->base.info.sorconf.link & 1) * 0x80;
+}
+
+static inline u32
+gf110_sor_dp_lane_map(struct nv50_disp_priv *priv, u8 lane)
+{
+       static const u8 gf110[] = { 16, 8, 0, 24 };
+       return gf110[lane];
+}
+
+static int
+gf110_sor_dp_pattern(struct nvkm_output_dp *outp, int pattern)
+{
+       struct nv50_disp_priv *priv = (void *)nvkm_disp(outp);
+       const u32 loff = gf110_sor_loff(outp);
+       nv_mask(priv, 0x61c110 + loff, 0x0f0f0f0f, 0x01010101 * pattern);
+       return 0;
+}
+
+int
+gf110_sor_dp_lnk_ctl(struct nvkm_output_dp *outp, int nr, int bw, bool ef)
+{
+       struct nv50_disp_priv *priv = (void *)nvkm_disp(outp);
+       const u32 soff = gf110_sor_soff(outp);
+       const u32 loff = gf110_sor_loff(outp);
+       u32 dpctrl = 0x00000000;
+       u32 clksor = 0x00000000;
+
+       clksor |= bw << 18;
+       dpctrl |= ((1 << nr) - 1) << 16;
+       if (ef)
+               dpctrl |= 0x00004000;
+
+       nv_mask(priv, 0x612300 + soff, 0x007c0000, clksor);
+       nv_mask(priv, 0x61c10c + loff, 0x001f4000, dpctrl);
+       return 0;
+}
+
+static int
+gf110_sor_dp_drv_ctl(struct nvkm_output_dp *outp,
+                    int ln, int vs, int pe, int pc)
+{
+       struct nv50_disp_priv *priv = (void *)nvkm_disp(outp);
+       struct nvkm_bios *bios = nvkm_bios(priv);
+       const u32 shift = gf110_sor_dp_lane_map(priv, ln);
+       const u32 loff = gf110_sor_loff(outp);
+       u32 addr, data[4];
+       u8  ver, hdr, cnt, len;
+       struct nvbios_dpout info;
+       struct nvbios_dpcfg ocfg;
+
+       addr = nvbios_dpout_match(bios, outp->base.info.hasht,
+                                       outp->base.info.hashm,
+                                 &ver, &hdr, &cnt, &len, &info);
+       if (!addr)
+               return -ENODEV;
+
+       addr = nvbios_dpcfg_match(bios, addr, pc, vs, pe,
+                                 &ver, &hdr, &cnt, &len, &ocfg);
+       if (!addr)
+               return -EINVAL;
+
+       data[0] = nv_rd32(priv, 0x61c118 + loff) & ~(0x000000ff << shift);
+       data[1] = nv_rd32(priv, 0x61c120 + loff) & ~(0x000000ff << shift);
+       data[2] = nv_rd32(priv, 0x61c130 + loff);
+       if ((data[2] & 0x0000ff00) < (ocfg.tx_pu << 8) || ln == 0)
+               data[2] = (data[2] & ~0x0000ff00) | (ocfg.tx_pu << 8);
+       nv_wr32(priv, 0x61c118 + loff, data[0] | (ocfg.dc << shift));
+       nv_wr32(priv, 0x61c120 + loff, data[1] | (ocfg.pe << shift));
+       nv_wr32(priv, 0x61c130 + loff, data[2] | (ocfg.tx_pu << 8));
+       data[3] = nv_rd32(priv, 0x61c13c + loff) & ~(0x000000ff << shift);
+       nv_wr32(priv, 0x61c13c + loff, data[3] | (ocfg.pc << shift));
+       return 0;
+}
+
+struct nvkm_output_dp_impl
+gf110_sor_dp_impl = {
+       .base.base.handle = DCB_OUTPUT_DP,
+       .base.base.ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = _nvkm_output_dp_ctor,
+               .dtor = _nvkm_output_dp_dtor,
+               .init = _nvkm_output_dp_init,
+               .fini = _nvkm_output_dp_fini,
+       },
+       .pattern = gf110_sor_dp_pattern,
+       .lnk_pwr = g94_sor_dp_lnk_pwr,
+       .lnk_ctl = gf110_sor_dp_lnk_ctl,
+       .drv_ctl = gf110_sor_dp_drv_ctl,
+};
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/disp/sorgm204.c b/drivers/gpu/drm/nouveau/nvkm/engine/disp/sorgm204.c
new file mode 100644 (file)
index 0000000..1e40dfe
--- /dev/null
@@ -0,0 +1,139 @@
+/*
+ * Copyright 2012 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 "nv50.h"
+#include "outpdp.h"
+
+#include <subdev/timer.h>
+
+static inline u32
+gm204_sor_soff(struct nvkm_output_dp *outp)
+{
+       return (ffs(outp->base.info.or) - 1) * 0x800;
+}
+
+static inline u32
+gm204_sor_loff(struct nvkm_output_dp *outp)
+{
+       return gm204_sor_soff(outp) + !(outp->base.info.sorconf.link & 1) * 0x80;
+}
+
+void
+gm204_sor_magic(struct nvkm_output *outp)
+{
+       struct nv50_disp_priv *priv = (void *)nvkm_disp(outp);
+       const u32 soff = outp->or * 0x100;
+       const u32 data = outp->or + 1;
+       if (outp->info.sorconf.link & 1)
+               nv_mask(priv, 0x612308 + soff, 0x0000001f, 0x00000000 | data);
+       if (outp->info.sorconf.link & 2)
+               nv_mask(priv, 0x612388 + soff, 0x0000001f, 0x00000010 | data);
+}
+
+static inline u32
+gm204_sor_dp_lane_map(struct nv50_disp_priv *priv, u8 lane)
+{
+       return lane * 0x08;
+}
+
+static int
+gm204_sor_dp_pattern(struct nvkm_output_dp *outp, int pattern)
+{
+       struct nv50_disp_priv *priv = (void *)nvkm_disp(outp);
+       const u32 soff = gm204_sor_soff(outp);
+       const u32 data = 0x01010101 * pattern;
+       if (outp->base.info.sorconf.link & 1)
+               nv_mask(priv, 0x61c110 + soff, 0x0f0f0f0f, data);
+       else
+               nv_mask(priv, 0x61c12c + soff, 0x0f0f0f0f, data);
+       return 0;
+}
+
+static int
+gm204_sor_dp_lnk_pwr(struct nvkm_output_dp *outp, int nr)
+{
+       struct nv50_disp_priv *priv = (void *)nvkm_disp(outp);
+       const u32 soff = gm204_sor_soff(outp);
+       const u32 loff = gm204_sor_loff(outp);
+       u32 mask = 0, i;
+
+       for (i = 0; i < nr; i++)
+               mask |= 1 << (gm204_sor_dp_lane_map(priv, i) >> 3);
+
+       nv_mask(priv, 0x61c130 + loff, 0x0000000f, mask);
+       nv_mask(priv, 0x61c034 + soff, 0x80000000, 0x80000000);
+       nv_wait(priv, 0x61c034 + soff, 0x80000000, 0x00000000);
+       return 0;
+}
+
+static int
+gm204_sor_dp_drv_ctl(struct nvkm_output_dp *outp,
+                    int ln, int vs, int pe, int pc)
+{
+       struct nv50_disp_priv *priv = (void *)nvkm_disp(outp);
+       struct nvkm_bios *bios = nvkm_bios(priv);
+       const u32 shift = gm204_sor_dp_lane_map(priv, ln);
+       const u32 loff = gm204_sor_loff(outp);
+       u32 addr, data[4];
+       u8  ver, hdr, cnt, len;
+       struct nvbios_dpout info;
+       struct nvbios_dpcfg ocfg;
+
+       addr = nvbios_dpout_match(bios, outp->base.info.hasht,
+                                       outp->base.info.hashm,
+                                 &ver, &hdr, &cnt, &len, &info);
+       if (!addr)
+               return -ENODEV;
+
+       addr = nvbios_dpcfg_match(bios, addr, pc, vs, pe,
+                                 &ver, &hdr, &cnt, &len, &ocfg);
+       if (!addr)
+               return -EINVAL;
+
+       data[0] = nv_rd32(priv, 0x61c118 + loff) & ~(0x000000ff << shift);
+       data[1] = nv_rd32(priv, 0x61c120 + loff) & ~(0x000000ff << shift);
+       data[2] = nv_rd32(priv, 0x61c130 + loff);
+       if ((data[2] & 0x0000ff00) < (ocfg.tx_pu << 8) || ln == 0)
+               data[2] = (data[2] & ~0x0000ff00) | (ocfg.tx_pu << 8);
+       nv_wr32(priv, 0x61c118 + loff, data[0] | (ocfg.dc << shift));
+       nv_wr32(priv, 0x61c120 + loff, data[1] | (ocfg.pe << shift));
+       nv_wr32(priv, 0x61c130 + loff, data[2] | (ocfg.tx_pu << 8));
+       data[3] = nv_rd32(priv, 0x61c13c + loff) & ~(0x000000ff << shift);
+       nv_wr32(priv, 0x61c13c + loff, data[3] | (ocfg.pc << shift));
+       return 0;
+}
+
+struct nvkm_output_dp_impl
+gm204_sor_dp_impl = {
+       .base.base.handle = DCB_OUTPUT_DP,
+       .base.base.ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = _nvkm_output_dp_ctor,
+               .dtor = _nvkm_output_dp_dtor,
+               .init = _nvkm_output_dp_init,
+               .fini = _nvkm_output_dp_fini,
+       },
+       .pattern = gm204_sor_dp_pattern,
+       .lnk_pwr = gm204_sor_dp_lnk_pwr,
+       .lnk_ctl = gf110_sor_dp_lnk_ctl,
+       .drv_ctl = gm204_sor_dp_drv_ctl,
+};
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/disp/sornv50.c b/drivers/gpu/drm/nouveau/nvkm/engine/disp/sornv50.c
new file mode 100644 (file)
index 0000000..b229a31
--- /dev/null
@@ -0,0 +1,56 @@
+/*
+ * Copyright 2012 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 "nv50.h"
+#include "outp.h"
+
+#include <core/client.h>
+#include <subdev/timer.h>
+
+#include <nvif/class.h>
+#include <nvif/unpack.h>
+
+int
+nv50_sor_power(NV50_DISP_MTHD_V1)
+{
+       union {
+               struct nv50_disp_sor_pwr_v0 v0;
+       } *args = data;
+       const u32 soff = outp->or * 0x800;
+       u32 stat;
+       int ret;
+
+       nv_ioctl(object, "disp sor pwr size %d\n", size);
+       if (nvif_unpack(args->v0, 0, 0, false)) {
+               nv_ioctl(object, "disp sor pwr vers %d state %d\n",
+                        args->v0.version, args->v0.state);
+               stat = !!args->v0.state;
+       } else
+               return ret;
+
+       nv_wait(priv, 0x61c004 + soff, 0x80000000, 0x00000000);
+       nv_mask(priv, 0x61c004 + soff, 0x80000001, 0x80000000 | stat);
+       nv_wait(priv, 0x61c004 + soff, 0x80000000, 0x00000000);
+       nv_wait(priv, 0x61c030 + soff, 0x10000000, 0x00000000);
+       return 0;
+}
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/disp/vga.c b/drivers/gpu/drm/nouveau/nvkm/engine/disp/vga.c
new file mode 100644 (file)
index 0000000..c4622c7
--- /dev/null
@@ -0,0 +1,219 @@
+/*
+ * Copyright 2012 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 <subdev/vga.h>
+
+#include <core/device.h>
+
+u8
+nv_rdport(void *obj, int head, u16 port)
+{
+       struct nvkm_device *device = nv_device(obj);
+
+       if (device->card_type >= NV_50)
+               return nv_rd08(obj, 0x601000 + port);
+
+       if (port == 0x03c0 || port == 0x03c1 || /* AR */
+           port == 0x03c2 || port == 0x03da || /* INP0 */
+           port == 0x03d4 || port == 0x03d5)   /* CR */
+               return nv_rd08(obj, 0x601000 + (head * 0x2000) + port);
+
+       if (port == 0x03c2 || port == 0x03cc || /* MISC */
+           port == 0x03c4 || port == 0x03c5 || /* SR */
+           port == 0x03ce || port == 0x03cf) { /* GR */
+               if (device->card_type < NV_40)
+                       head = 0; /* CR44 selects head */
+               return nv_rd08(obj, 0x0c0000 + (head * 0x2000) + port);
+       }
+
+       nv_error(obj, "unknown vga port 0x%04x\n", port);
+       return 0x00;
+}
+
+void
+nv_wrport(void *obj, int head, u16 port, u8 data)
+{
+       struct nvkm_device *device = nv_device(obj);
+
+       if (device->card_type >= NV_50)
+               nv_wr08(obj, 0x601000 + port, data);
+       else
+       if (port == 0x03c0 || port == 0x03c1 || /* AR */
+           port == 0x03c2 || port == 0x03da || /* INP0 */
+           port == 0x03d4 || port == 0x03d5)   /* CR */
+               nv_wr08(obj, 0x601000 + (head * 0x2000) + port, data);
+       else
+       if (port == 0x03c2 || port == 0x03cc || /* MISC */
+           port == 0x03c4 || port == 0x03c5 || /* SR */
+           port == 0x03ce || port == 0x03cf) { /* GR */
+               if (device->card_type < NV_40)
+                       head = 0; /* CR44 selects head */
+               nv_wr08(obj, 0x0c0000 + (head * 0x2000) + port, data);
+       } else
+               nv_error(obj, "unknown vga port 0x%04x\n", port);
+}
+
+u8
+nv_rdvgas(void *obj, int head, u8 index)
+{
+       nv_wrport(obj, head, 0x03c4, index);
+       return nv_rdport(obj, head, 0x03c5);
+}
+
+void
+nv_wrvgas(void *obj, int head, u8 index, u8 value)
+{
+       nv_wrport(obj, head, 0x03c4, index);
+       nv_wrport(obj, head, 0x03c5, value);
+}
+
+u8
+nv_rdvgag(void *obj, int head, u8 index)
+{
+       nv_wrport(obj, head, 0x03ce, index);
+       return nv_rdport(obj, head, 0x03cf);
+}
+
+void
+nv_wrvgag(void *obj, int head, u8 index, u8 value)
+{
+       nv_wrport(obj, head, 0x03ce, index);
+       nv_wrport(obj, head, 0x03cf, value);
+}
+
+u8
+nv_rdvgac(void *obj, int head, u8 index)
+{
+       nv_wrport(obj, head, 0x03d4, index);
+       return nv_rdport(obj, head, 0x03d5);
+}
+
+void
+nv_wrvgac(void *obj, int head, u8 index, u8 value)
+{
+       nv_wrport(obj, head, 0x03d4, index);
+       nv_wrport(obj, head, 0x03d5, value);
+}
+
+u8
+nv_rdvgai(void *obj, int head, u16 port, u8 index)
+{
+       if (port == 0x03c4) return nv_rdvgas(obj, head, index);
+       if (port == 0x03ce) return nv_rdvgag(obj, head, index);
+       if (port == 0x03d4) return nv_rdvgac(obj, head, index);
+       nv_error(obj, "unknown indexed vga port 0x%04x\n", port);
+       return 0x00;
+}
+
+void
+nv_wrvgai(void *obj, int head, u16 port, u8 index, u8 value)
+{
+       if      (port == 0x03c4) nv_wrvgas(obj, head, index, value);
+       else if (port == 0x03ce) nv_wrvgag(obj, head, index, value);
+       else if (port == 0x03d4) nv_wrvgac(obj, head, index, value);
+       else nv_error(obj, "unknown indexed vga port 0x%04x\n", port);
+}
+
+bool
+nv_lockvgac(void *obj, bool lock)
+{
+       struct nvkm_device *dev = nv_device(obj);
+
+       bool locked = !nv_rdvgac(obj, 0, 0x1f);
+       u8 data = lock ? 0x99 : 0x57;
+       if (dev->card_type < NV_50)
+               nv_wrvgac(obj, 0, 0x1f, data);
+       else
+               nv_wrvgac(obj, 0, 0x3f, data);
+       if (dev->chipset == 0x11) {
+               if (!(nv_rd32(obj, 0x001084) & 0x10000000))
+                       nv_wrvgac(obj, 1, 0x1f, data);
+       }
+       return locked;
+}
+
+/* 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
+ */
+u8
+nv_rdvgaowner(void *obj)
+{
+       if (nv_device(obj)->card_type < NV_50) {
+               if (nv_device(obj)->chipset == 0x11) {
+                       u32 tied = nv_rd32(obj, 0x001084) & 0x10000000;
+                       if (tied == 0) {
+                               u8 slA = nv_rdvgac(obj, 0, 0x28) & 0x80;
+                               u8 tvA = nv_rdvgac(obj, 0, 0x33) & 0x01;
+                               u8 slB = nv_rdvgac(obj, 1, 0x28) & 0x80;
+                               u8 tvB = nv_rdvgac(obj, 1, 0x33) & 0x01;
+                               if (slA && !tvA) return 0x00;
+                               if (slB && !tvB) return 0x03;
+                               if (slA) return 0x00;
+                               if (slB) return 0x03;
+                               return 0x00;
+                       }
+                       return 0x04;
+               }
+
+               return nv_rdvgac(obj, 0, 0x44);
+       }
+
+       nv_error(obj, "rdvgaowner after nv4x\n");
+       return 0x00;
+}
+
+void
+nv_wrvgaowner(void *obj, u8 select)
+{
+       if (nv_device(obj)->card_type < NV_50) {
+               u8 owner = (select == 1) ? 3 : select;
+               if (nv_device(obj)->chipset == 0x11) {
+                       /* workaround hw lockup bug */
+                       nv_rdvgac(obj, 0, 0x1f);
+                       nv_rdvgac(obj, 1, 0x1f);
+               }
+
+               nv_wrvgac(obj, 0, 0x44, owner);
+
+               if (nv_device(obj)->chipset == 0x11) {
+                       nv_wrvgac(obj, 0, 0x2e, owner);
+                       nv_wrvgac(obj, 0, 0x2e, owner);
+               }
+       } else
+               nv_error(obj, "wrvgaowner after nv4x\n");
+}
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/dmaobj/Kbuild b/drivers/gpu/drm/nouveau/nvkm/engine/dmaobj/Kbuild
new file mode 100644 (file)
index 0000000..7529632
--- /dev/null
@@ -0,0 +1,5 @@
+nvkm-y += nvkm/engine/dmaobj/base.o
+nvkm-y += nvkm/engine/dmaobj/nv04.o
+nvkm-y += nvkm/engine/dmaobj/nv50.o
+nvkm-y += nvkm/engine/dmaobj/gf100.o
+nvkm-y += nvkm/engine/dmaobj/gf110.o
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/dmaobj/base.c b/drivers/gpu/drm/nouveau/nvkm/engine/dmaobj/base.c
new file mode 100644 (file)
index 0000000..a2b60d8
--- /dev/null
@@ -0,0 +1,164 @@
+/*
+ * Copyright 2012 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 "priv.h"
+
+#include <core/client.h>
+#include <core/device.h>
+#include <subdev/fb.h>
+#include <subdev/instmem.h>
+
+#include <nvif/class.h>
+#include <nvif/unpack.h>
+
+static int
+nvkm_dmaobj_bind(struct nvkm_dmaobj *dmaobj, struct nvkm_object *parent,
+                struct nvkm_gpuobj **pgpuobj)
+{
+       const struct nvkm_dmaeng_impl *impl = (void *)
+               nv_oclass(nv_object(dmaobj)->engine);
+       int ret = 0;
+
+       if (nv_object(dmaobj) == parent) { /* ctor bind */
+               if (nv_mclass(parent->parent) == NV_DEVICE) {
+                       /* delayed, or no, binding */
+                       return 0;
+               }
+               ret = impl->bind(dmaobj, parent, pgpuobj);
+               if (ret == 0)
+                       nvkm_object_ref(NULL, &parent);
+               return ret;
+       }
+
+       return impl->bind(dmaobj, parent, pgpuobj);
+}
+
+int
+nvkm_dmaobj_create_(struct nvkm_object *parent,
+                   struct nvkm_object *engine,
+                   struct nvkm_oclass *oclass, void **pdata, u32 *psize,
+                   int length, void **pobject)
+{
+       union {
+               struct nv_dma_v0 v0;
+       } *args = *pdata;
+       struct nvkm_instmem *instmem = nvkm_instmem(parent);
+       struct nvkm_client *client = nvkm_client(parent);
+       struct nvkm_device *device = nv_device(parent);
+       struct nvkm_fb *pfb = nvkm_fb(parent);
+       struct nvkm_dmaobj *dmaobj;
+       void *data = *pdata;
+       u32 size = *psize;
+       int ret;
+
+       ret = nvkm_object_create_(parent, engine, oclass, 0, length, pobject);
+       dmaobj = *pobject;
+       if (ret)
+               return ret;
+
+       nv_ioctl(parent, "create dma size %d\n", *psize);
+       if (nvif_unpack(args->v0, 0, 0, true)) {
+               nv_ioctl(parent, "create dma vers %d target %d access %d "
+                                "start %016llx limit %016llx\n",
+                        args->v0.version, args->v0.target, args->v0.access,
+                        args->v0.start, args->v0.limit);
+               dmaobj->target = args->v0.target;
+               dmaobj->access = args->v0.access;
+               dmaobj->start  = args->v0.start;
+               dmaobj->limit  = args->v0.limit;
+       } else
+               return ret;
+
+       *pdata = data;
+       *psize = size;
+
+       if (dmaobj->start > dmaobj->limit)
+               return -EINVAL;
+
+       switch (dmaobj->target) {
+       case NV_DMA_V0_TARGET_VM:
+               dmaobj->target = NV_MEM_TARGET_VM;
+               break;
+       case NV_DMA_V0_TARGET_VRAM:
+               if (!client->super) {
+                       if (dmaobj->limit >= pfb->ram->size - instmem->reserved)
+                               return -EACCES;
+                       if (device->card_type >= NV_50)
+                               return -EACCES;
+               }
+               dmaobj->target = NV_MEM_TARGET_VRAM;
+               break;
+       case NV_DMA_V0_TARGET_PCI:
+               if (!client->super)
+                       return -EACCES;
+               dmaobj->target = NV_MEM_TARGET_PCI;
+               break;
+       case NV_DMA_V0_TARGET_PCI_US:
+       case NV_DMA_V0_TARGET_AGP:
+               if (!client->super)
+                       return -EACCES;
+               dmaobj->target = NV_MEM_TARGET_PCI_NOSNOOP;
+               break;
+       default:
+               return -EINVAL;
+       }
+
+       switch (dmaobj->access) {
+       case NV_DMA_V0_ACCESS_VM:
+               dmaobj->access = NV_MEM_ACCESS_VM;
+               break;
+       case NV_DMA_V0_ACCESS_RD:
+               dmaobj->access = NV_MEM_ACCESS_RO;
+               break;
+       case NV_DMA_V0_ACCESS_WR:
+               dmaobj->access = NV_MEM_ACCESS_WO;
+               break;
+       case NV_DMA_V0_ACCESS_RDWR:
+               dmaobj->access = NV_MEM_ACCESS_RW;
+               break;
+       default:
+               return -EINVAL;
+       }
+
+       return ret;
+}
+
+int
+_nvkm_dmaeng_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+                 struct nvkm_oclass *oclass, void *data, u32 size,
+                 struct nvkm_object **pobject)
+{
+       const struct nvkm_dmaeng_impl *impl = (void *)oclass;
+       struct nvkm_dmaeng *dmaeng;
+       int ret;
+
+       ret = nvkm_engine_create(parent, engine, oclass, true, "DMAOBJ",
+                                "dmaobj", &dmaeng);
+       *pobject = nv_object(dmaeng);
+       if (ret)
+               return ret;
+
+       nv_engine(dmaeng)->sclass = impl->sclass;
+       dmaeng->bind = nvkm_dmaobj_bind;
+       return 0;
+}
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/dmaobj/gf100.c b/drivers/gpu/drm/nouveau/nvkm/engine/dmaobj/gf100.c
new file mode 100644 (file)
index 0000000..f880e51
--- /dev/null
@@ -0,0 +1,176 @@
+/*
+ * Copyright 2012 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 "priv.h"
+
+#include <core/client.h>
+#include <core/gpuobj.h>
+#include <subdev/fb.h>
+
+#include <nvif/class.h>
+#include <nvif/unpack.h>
+
+struct gf100_dmaobj_priv {
+       struct nvkm_dmaobj base;
+       u32 flags0;
+       u32 flags5;
+};
+
+static int
+gf100_dmaobj_bind(struct nvkm_dmaobj *dmaobj, struct nvkm_object *parent,
+                 struct nvkm_gpuobj **pgpuobj)
+{
+       struct gf100_dmaobj_priv *priv = (void *)dmaobj;
+       int ret;
+
+       if (!nv_iclass(parent, NV_ENGCTX_CLASS)) {
+               switch (nv_mclass(parent->parent)) {
+               case GT214_DISP_CORE_CHANNEL_DMA:
+               case GT214_DISP_BASE_CHANNEL_DMA:
+               case GT214_DISP_OVERLAY_CHANNEL_DMA:
+                       break;
+               default:
+                       return -EINVAL;
+               }
+       } else
+               return 0;
+
+       ret = nvkm_gpuobj_new(parent, parent, 24, 32, 0, pgpuobj);
+       if (ret == 0) {
+               nv_wo32(*pgpuobj, 0x00, priv->flags0 | nv_mclass(dmaobj));
+               nv_wo32(*pgpuobj, 0x04, lower_32_bits(priv->base.limit));
+               nv_wo32(*pgpuobj, 0x08, lower_32_bits(priv->base.start));
+               nv_wo32(*pgpuobj, 0x0c, upper_32_bits(priv->base.limit) << 24 |
+                                       upper_32_bits(priv->base.start));
+               nv_wo32(*pgpuobj, 0x10, 0x00000000);
+               nv_wo32(*pgpuobj, 0x14, priv->flags5);
+       }
+
+       return ret;
+}
+
+static int
+gf100_dmaobj_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+                 struct nvkm_oclass *oclass, void *data, u32 size,
+                 struct nvkm_object **pobject)
+{
+       struct nvkm_dmaeng *dmaeng = (void *)engine;
+       union {
+               struct gf100_dma_v0 v0;
+       } *args;
+       struct gf100_dmaobj_priv *priv;
+       u32 kind, user, unkn;
+       int ret;
+
+       ret = nvkm_dmaobj_create(parent, engine, oclass, &data, &size, &priv);
+       *pobject = nv_object(priv);
+       if (ret)
+               return ret;
+       args = data;
+
+       nv_ioctl(parent, "create gf100 dma size %d\n", size);
+       if (nvif_unpack(args->v0, 0, 0, false)) {
+               nv_ioctl(parent, "create gf100 dma vers %d priv %d kind %02x\n",
+                        args->v0.version, args->v0.priv, args->v0.kind);
+               kind = args->v0.kind;
+               user = args->v0.priv;
+               unkn = 0;
+       } else
+       if (size == 0) {
+               if (priv->base.target != NV_MEM_TARGET_VM) {
+                       kind = GF100_DMA_V0_KIND_PITCH;
+                       user = GF100_DMA_V0_PRIV_US;
+                       unkn = 2;
+               } else {
+                       kind = GF100_DMA_V0_KIND_VM;
+                       user = GF100_DMA_V0_PRIV_VM;
+                       unkn = 0;
+               }
+       } else
+               return ret;
+
+       if (user > 2)
+               return -EINVAL;
+       priv->flags0 |= (kind << 22) | (user << 20);
+       priv->flags5 |= (unkn << 16);
+
+       switch (priv->base.target) {
+       case NV_MEM_TARGET_VM:
+               priv->flags0 |= 0x00000000;
+               break;
+       case NV_MEM_TARGET_VRAM:
+               priv->flags0 |= 0x00010000;
+               break;
+       case NV_MEM_TARGET_PCI:
+               priv->flags0 |= 0x00020000;
+               break;
+       case NV_MEM_TARGET_PCI_NOSNOOP:
+               priv->flags0 |= 0x00030000;
+               break;
+       default:
+               return -EINVAL;
+       }
+
+       switch (priv->base.access) {
+       case NV_MEM_ACCESS_VM:
+               break;
+       case NV_MEM_ACCESS_RO:
+               priv->flags0 |= 0x00040000;
+               break;
+       case NV_MEM_ACCESS_WO:
+       case NV_MEM_ACCESS_RW:
+               priv->flags0 |= 0x00080000;
+               break;
+       }
+
+       return dmaeng->bind(&priv->base, nv_object(priv), (void *)pobject);
+}
+
+static struct nvkm_ofuncs
+gf100_dmaobj_ofuncs = {
+       .ctor =  gf100_dmaobj_ctor,
+       .dtor = _nvkm_dmaobj_dtor,
+       .init = _nvkm_dmaobj_init,
+       .fini = _nvkm_dmaobj_fini,
+};
+
+static struct nvkm_oclass
+gf100_dmaeng_sclass[] = {
+       { NV_DMA_FROM_MEMORY, &gf100_dmaobj_ofuncs },
+       { NV_DMA_TO_MEMORY, &gf100_dmaobj_ofuncs },
+       { NV_DMA_IN_MEMORY, &gf100_dmaobj_ofuncs },
+       {}
+};
+
+struct nvkm_oclass *
+gf100_dmaeng_oclass = &(struct nvkm_dmaeng_impl) {
+       .base.handle = NV_ENGINE(DMAOBJ, 0xc0),
+       .base.ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = _nvkm_dmaeng_ctor,
+               .dtor = _nvkm_dmaeng_dtor,
+               .init = _nvkm_dmaeng_init,
+               .fini = _nvkm_dmaeng_fini,
+       },
+       .sclass = gf100_dmaeng_sclass,
+       .bind = gf100_dmaobj_bind,
+}.base;
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/dmaobj/gf110.c b/drivers/gpu/drm/nouveau/nvkm/engine/dmaobj/gf110.c
new file mode 100644 (file)
index 0000000..bf8f0f2
--- /dev/null
@@ -0,0 +1,165 @@
+/*
+ * Copyright 2012 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 "priv.h"
+
+#include <core/client.h>
+#include <core/gpuobj.h>
+#include <subdev/fb.h>
+
+#include <nvif/class.h>
+#include <nvif/unpack.h>
+
+struct gf110_dmaobj_priv {
+       struct nvkm_dmaobj base;
+       u32 flags0;
+};
+
+static int
+gf110_dmaobj_bind(struct nvkm_dmaobj *dmaobj, struct nvkm_object *parent,
+                 struct nvkm_gpuobj **pgpuobj)
+{
+       struct gf110_dmaobj_priv *priv = (void *)dmaobj;
+       int ret;
+
+       if (!nv_iclass(parent, NV_ENGCTX_CLASS)) {
+               switch (nv_mclass(parent->parent)) {
+               case GF110_DISP_CORE_CHANNEL_DMA:
+               case GK104_DISP_CORE_CHANNEL_DMA:
+               case GK110_DISP_CORE_CHANNEL_DMA:
+               case GM107_DISP_CORE_CHANNEL_DMA:
+               case GM204_DISP_CORE_CHANNEL_DMA:
+               case GF110_DISP_BASE_CHANNEL_DMA:
+               case GK104_DISP_BASE_CHANNEL_DMA:
+               case GK110_DISP_BASE_CHANNEL_DMA:
+               case GF110_DISP_OVERLAY_CONTROL_DMA:
+               case GK104_DISP_OVERLAY_CONTROL_DMA:
+                       break;
+               default:
+                       return -EINVAL;
+               }
+       } else
+               return 0;
+
+       ret = nvkm_gpuobj_new(parent, parent, 24, 32, 0, pgpuobj);
+       if (ret == 0) {
+               nv_wo32(*pgpuobj, 0x00, priv->flags0);
+               nv_wo32(*pgpuobj, 0x04, priv->base.start >> 8);
+               nv_wo32(*pgpuobj, 0x08, priv->base.limit >> 8);
+               nv_wo32(*pgpuobj, 0x0c, 0x00000000);
+               nv_wo32(*pgpuobj, 0x10, 0x00000000);
+               nv_wo32(*pgpuobj, 0x14, 0x00000000);
+       }
+
+       return ret;
+}
+
+static int
+gf110_dmaobj_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+                 struct nvkm_oclass *oclass, void *data, u32 size,
+                 struct nvkm_object **pobject)
+{
+       struct nvkm_dmaeng *dmaeng = (void *)engine;
+       union {
+               struct gf110_dma_v0 v0;
+       } *args;
+       struct gf110_dmaobj_priv *priv;
+       u32 kind, page;
+       int ret;
+
+       ret = nvkm_dmaobj_create(parent, engine, oclass, &data, &size, &priv);
+       *pobject = nv_object(priv);
+       if (ret)
+               return ret;
+       args = data;
+
+       nv_ioctl(parent, "create gf110 dma size %d\n", size);
+       if (nvif_unpack(args->v0, 0, 0, false)) {
+               nv_ioctl(parent, "create gf100 dma vers %d page %d kind %02x\n",
+                        args->v0.version, args->v0.page, args->v0.kind);
+               kind = args->v0.kind;
+               page = args->v0.page;
+       } else
+       if (size == 0) {
+               if (priv->base.target != NV_MEM_TARGET_VM) {
+                       kind = GF110_DMA_V0_KIND_PITCH;
+                       page = GF110_DMA_V0_PAGE_SP;
+               } else {
+                       kind = GF110_DMA_V0_KIND_VM;
+                       page = GF110_DMA_V0_PAGE_LP;
+               }
+       } else
+               return ret;
+
+       if (page > 1)
+               return -EINVAL;
+       priv->flags0 = (kind << 20) | (page << 6);
+
+       switch (priv->base.target) {
+       case NV_MEM_TARGET_VRAM:
+               priv->flags0 |= 0x00000009;
+               break;
+       case NV_MEM_TARGET_VM:
+       case NV_MEM_TARGET_PCI:
+       case NV_MEM_TARGET_PCI_NOSNOOP:
+               /* XXX: don't currently know how to construct a real one
+                *      of these.  we only use them to represent pushbufs
+                *      on these chipsets, and the classes that use them
+                *      deal with the target themselves.
+                */
+               break;
+       default:
+               return -EINVAL;
+       }
+
+       return dmaeng->bind(&priv->base, nv_object(priv), (void *)pobject);
+}
+
+static struct nvkm_ofuncs
+gf110_dmaobj_ofuncs = {
+       .ctor =  gf110_dmaobj_ctor,
+       .dtor = _nvkm_dmaobj_dtor,
+       .init = _nvkm_dmaobj_init,
+       .fini = _nvkm_dmaobj_fini,
+};
+
+static struct nvkm_oclass
+gf110_dmaeng_sclass[] = {
+       { NV_DMA_FROM_MEMORY, &gf110_dmaobj_ofuncs },
+       { NV_DMA_TO_MEMORY, &gf110_dmaobj_ofuncs },
+       { NV_DMA_IN_MEMORY, &gf110_dmaobj_ofuncs },
+       {}
+};
+
+struct nvkm_oclass *
+gf110_dmaeng_oclass = &(struct nvkm_dmaeng_impl) {
+       .base.handle = NV_ENGINE(DMAOBJ, 0xd0),
+       .base.ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = _nvkm_dmaeng_ctor,
+               .dtor = _nvkm_dmaeng_dtor,
+               .init = _nvkm_dmaeng_init,
+               .fini = _nvkm_dmaeng_fini,
+       },
+       .sclass = gf110_dmaeng_sclass,
+       .bind = gf110_dmaobj_bind,
+}.base;
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/dmaobj/nv04.c b/drivers/gpu/drm/nouveau/nvkm/engine/dmaobj/nv04.c
new file mode 100644 (file)
index 0000000..b4379c2
--- /dev/null
@@ -0,0 +1,163 @@
+/*
+ * Copyright 2012 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 "priv.h"
+
+#include <core/gpuobj.h>
+#include <subdev/fb.h>
+#include <subdev/mmu/nv04.h>
+
+#include <nvif/class.h>
+
+struct nv04_dmaobj_priv {
+       struct nvkm_dmaobj base;
+       bool clone;
+       u32 flags0;
+       u32 flags2;
+};
+
+static int
+nv04_dmaobj_bind(struct nvkm_dmaobj *dmaobj, struct nvkm_object *parent,
+                struct nvkm_gpuobj **pgpuobj)
+{
+       struct nv04_dmaobj_priv *priv = (void *)dmaobj;
+       struct nvkm_gpuobj *gpuobj;
+       u64 offset = priv->base.start & 0xfffff000;
+       u64 adjust = priv->base.start & 0x00000fff;
+       u32 length = priv->base.limit - priv->base.start;
+       int ret;
+
+       if (!nv_iclass(parent, NV_ENGCTX_CLASS)) {
+               switch (nv_mclass(parent->parent)) {
+               case NV03_CHANNEL_DMA:
+               case NV10_CHANNEL_DMA:
+               case NV17_CHANNEL_DMA:
+               case NV40_CHANNEL_DMA:
+                       break;
+               default:
+                       return -EINVAL;
+               }
+       }
+
+       if (priv->clone) {
+               struct nv04_mmu_priv *mmu = nv04_mmu(dmaobj);
+               struct nvkm_gpuobj *pgt = mmu->vm->pgt[0].obj[0];
+               if (!dmaobj->start)
+                       return nvkm_gpuobj_dup(parent, pgt, pgpuobj);
+               offset  = nv_ro32(pgt, 8 + (offset >> 10));
+               offset &= 0xfffff000;
+       }
+
+       ret = nvkm_gpuobj_new(parent, parent, 16, 16, 0, &gpuobj);
+       *pgpuobj = gpuobj;
+       if (ret == 0) {
+               nv_wo32(*pgpuobj, 0x00, priv->flags0 | (adjust << 20));
+               nv_wo32(*pgpuobj, 0x04, length);
+               nv_wo32(*pgpuobj, 0x08, priv->flags2 | offset);
+               nv_wo32(*pgpuobj, 0x0c, priv->flags2 | offset);
+       }
+
+       return ret;
+}
+
+static int
+nv04_dmaobj_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+                struct nvkm_oclass *oclass, void *data, u32 size,
+                struct nvkm_object **pobject)
+{
+       struct nvkm_dmaeng *dmaeng = (void *)engine;
+       struct nv04_mmu_priv *mmu = nv04_mmu(engine);
+       struct nv04_dmaobj_priv *priv;
+       int ret;
+
+       ret = nvkm_dmaobj_create(parent, engine, oclass, &data, &size, &priv);
+       *pobject = nv_object(priv);
+       if (ret || (ret = -ENOSYS, size))
+               return ret;
+
+       if (priv->base.target == NV_MEM_TARGET_VM) {
+               if (nv_object(mmu)->oclass == &nv04_mmu_oclass)
+                       priv->clone = true;
+               priv->base.target = NV_MEM_TARGET_PCI;
+               priv->base.access = NV_MEM_ACCESS_RW;
+       }
+
+       priv->flags0 = nv_mclass(priv);
+       switch (priv->base.target) {
+       case NV_MEM_TARGET_VRAM:
+               priv->flags0 |= 0x00003000;
+               break;
+       case NV_MEM_TARGET_PCI:
+               priv->flags0 |= 0x00023000;
+               break;
+       case NV_MEM_TARGET_PCI_NOSNOOP:
+               priv->flags0 |= 0x00033000;
+               break;
+       default:
+               return -EINVAL;
+       }
+
+       switch (priv->base.access) {
+       case NV_MEM_ACCESS_RO:
+               priv->flags0 |= 0x00004000;
+               break;
+       case NV_MEM_ACCESS_WO:
+               priv->flags0 |= 0x00008000;
+       case NV_MEM_ACCESS_RW:
+               priv->flags2 |= 0x00000002;
+               break;
+       default:
+               return -EINVAL;
+       }
+
+       return dmaeng->bind(&priv->base, nv_object(priv), (void *)pobject);
+}
+
+static struct nvkm_ofuncs
+nv04_dmaobj_ofuncs = {
+       .ctor =  nv04_dmaobj_ctor,
+       .dtor = _nvkm_dmaobj_dtor,
+       .init = _nvkm_dmaobj_init,
+       .fini = _nvkm_dmaobj_fini,
+};
+
+static struct nvkm_oclass
+nv04_dmaeng_sclass[] = {
+       { NV_DMA_FROM_MEMORY, &nv04_dmaobj_ofuncs },
+       { NV_DMA_TO_MEMORY, &nv04_dmaobj_ofuncs },
+       { NV_DMA_IN_MEMORY, &nv04_dmaobj_ofuncs },
+       {}
+};
+
+struct nvkm_oclass *
+nv04_dmaeng_oclass = &(struct nvkm_dmaeng_impl) {
+       .base.handle = NV_ENGINE(DMAOBJ, 0x04),
+       .base.ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = _nvkm_dmaeng_ctor,
+               .dtor = _nvkm_dmaeng_dtor,
+               .init = _nvkm_dmaeng_init,
+               .fini = _nvkm_dmaeng_fini,
+       },
+       .sclass = nv04_dmaeng_sclass,
+       .bind = nv04_dmaobj_bind,
+}.base;
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/dmaobj/nv50.c b/drivers/gpu/drm/nouveau/nvkm/engine/dmaobj/nv50.c
new file mode 100644 (file)
index 0000000..4d3c828
--- /dev/null
@@ -0,0 +1,195 @@
+/*
+ * Copyright 2012 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 "priv.h"
+
+#include <core/client.h>
+#include <core/gpuobj.h>
+#include <subdev/fb.h>
+
+#include <nvif/class.h>
+#include <nvif/unpack.h>
+
+struct nv50_dmaobj_priv {
+       struct nvkm_dmaobj base;
+       u32 flags0;
+       u32 flags5;
+};
+
+static int
+nv50_dmaobj_bind(struct nvkm_dmaobj *dmaobj, struct nvkm_object *parent,
+                struct nvkm_gpuobj **pgpuobj)
+{
+       struct nv50_dmaobj_priv *priv = (void *)dmaobj;
+       int ret;
+
+       if (!nv_iclass(parent, NV_ENGCTX_CLASS)) {
+               switch (nv_mclass(parent->parent)) {
+               case NV40_CHANNEL_DMA:
+               case NV50_CHANNEL_GPFIFO:
+               case G82_CHANNEL_GPFIFO:
+               case NV50_DISP_CORE_CHANNEL_DMA:
+               case G82_DISP_CORE_CHANNEL_DMA:
+               case GT206_DISP_CORE_CHANNEL_DMA:
+               case GT200_DISP_CORE_CHANNEL_DMA:
+               case GT214_DISP_CORE_CHANNEL_DMA:
+               case NV50_DISP_BASE_CHANNEL_DMA:
+               case G82_DISP_BASE_CHANNEL_DMA:
+               case GT200_DISP_BASE_CHANNEL_DMA:
+               case GT214_DISP_BASE_CHANNEL_DMA:
+               case NV50_DISP_OVERLAY_CHANNEL_DMA:
+               case G82_DISP_OVERLAY_CHANNEL_DMA:
+               case GT200_DISP_OVERLAY_CHANNEL_DMA:
+               case GT214_DISP_OVERLAY_CHANNEL_DMA:
+                       break;
+               default:
+                       return -EINVAL;
+               }
+       }
+
+       ret = nvkm_gpuobj_new(parent, parent, 24, 32, 0, pgpuobj);
+       if (ret == 0) {
+               nv_wo32(*pgpuobj, 0x00, priv->flags0 | nv_mclass(dmaobj));
+               nv_wo32(*pgpuobj, 0x04, lower_32_bits(priv->base.limit));
+               nv_wo32(*pgpuobj, 0x08, lower_32_bits(priv->base.start));
+               nv_wo32(*pgpuobj, 0x0c, upper_32_bits(priv->base.limit) << 24 |
+                                       upper_32_bits(priv->base.start));
+               nv_wo32(*pgpuobj, 0x10, 0x00000000);
+               nv_wo32(*pgpuobj, 0x14, priv->flags5);
+       }
+
+       return ret;
+}
+
+static int
+nv50_dmaobj_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+                struct nvkm_oclass *oclass, void *data, u32 size,
+                struct nvkm_object **pobject)
+{
+       struct nvkm_dmaeng *dmaeng = (void *)engine;
+       union {
+               struct nv50_dma_v0 v0;
+       } *args;
+       struct nv50_dmaobj_priv *priv;
+       u32 user, part, comp, kind;
+       int ret;
+
+       ret = nvkm_dmaobj_create(parent, engine, oclass, &data, &size, &priv);
+       *pobject = nv_object(priv);
+       if (ret)
+               return ret;
+       args = data;
+
+       nv_ioctl(parent, "create nv50 dma size %d\n", size);
+       if (nvif_unpack(args->v0, 0, 0, false)) {
+               nv_ioctl(parent, "create nv50 dma vers %d priv %d part %d "
+                                "comp %d kind %02x\n", args->v0.version,
+                        args->v0.priv, args->v0.part, args->v0.comp,
+                        args->v0.kind);
+               user = args->v0.priv;
+               part = args->v0.part;
+               comp = args->v0.comp;
+               kind = args->v0.kind;
+       } else
+       if (size == 0) {
+               if (priv->base.target != NV_MEM_TARGET_VM) {
+                       user = NV50_DMA_V0_PRIV_US;
+                       part = NV50_DMA_V0_PART_256;
+                       comp = NV50_DMA_V0_COMP_NONE;
+                       kind = NV50_DMA_V0_KIND_PITCH;
+               } else {
+                       user = NV50_DMA_V0_PRIV_VM;
+                       part = NV50_DMA_V0_PART_VM;
+                       comp = NV50_DMA_V0_COMP_VM;
+                       kind = NV50_DMA_V0_KIND_VM;
+               }
+       } else
+               return ret;
+
+       if (user > 2 || part > 2 || comp > 3 || kind > 0x7f)
+               return -EINVAL;
+       priv->flags0 = (comp << 29) | (kind << 22) | (user << 20);
+       priv->flags5 = (part << 16);
+
+       switch (priv->base.target) {
+       case NV_MEM_TARGET_VM:
+               priv->flags0 |= 0x00000000;
+               break;
+       case NV_MEM_TARGET_VRAM:
+               priv->flags0 |= 0x00010000;
+               break;
+       case NV_MEM_TARGET_PCI:
+               priv->flags0 |= 0x00020000;
+               break;
+       case NV_MEM_TARGET_PCI_NOSNOOP:
+               priv->flags0 |= 0x00030000;
+               break;
+       default:
+               return -EINVAL;
+       }
+
+       switch (priv->base.access) {
+       case NV_MEM_ACCESS_VM:
+               break;
+       case NV_MEM_ACCESS_RO:
+               priv->flags0 |= 0x00040000;
+               break;
+       case NV_MEM_ACCESS_WO:
+       case NV_MEM_ACCESS_RW:
+               priv->flags0 |= 0x00080000;
+               break;
+       default:
+               return -EINVAL;
+       }
+
+       return dmaeng->bind(&priv->base, nv_object(priv), (void *)pobject);
+}
+
+static struct nvkm_ofuncs
+nv50_dmaobj_ofuncs = {
+       .ctor =  nv50_dmaobj_ctor,
+       .dtor = _nvkm_dmaobj_dtor,
+       .init = _nvkm_dmaobj_init,
+       .fini = _nvkm_dmaobj_fini,
+};
+
+static struct nvkm_oclass
+nv50_dmaeng_sclass[] = {
+       { NV_DMA_FROM_MEMORY, &nv50_dmaobj_ofuncs },
+       { NV_DMA_TO_MEMORY, &nv50_dmaobj_ofuncs },
+       { NV_DMA_IN_MEMORY, &nv50_dmaobj_ofuncs },
+       {}
+};
+
+struct nvkm_oclass *
+nv50_dmaeng_oclass = &(struct nvkm_dmaeng_impl) {
+       .base.handle = NV_ENGINE(DMAOBJ, 0x50),
+       .base.ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = _nvkm_dmaeng_ctor,
+               .dtor = _nvkm_dmaeng_dtor,
+               .init = _nvkm_dmaeng_init,
+               .fini = _nvkm_dmaeng_fini,
+       },
+       .sclass = nv50_dmaeng_sclass,
+       .bind = nv50_dmaobj_bind,
+}.base;
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/dmaobj/priv.h b/drivers/gpu/drm/nouveau/nvkm/engine/dmaobj/priv.h
new file mode 100644 (file)
index 0000000..44ae8a0
--- /dev/null
@@ -0,0 +1,28 @@
+#ifndef __NVKM_DMAOBJ_PRIV_H__
+#define __NVKM_DMAOBJ_PRIV_H__
+#include <engine/dmaobj.h>
+
+#define nvkm_dmaobj_create(p,e,c,pa,sa,d)                                      \
+       nvkm_dmaobj_create_((p), (e), (c), (pa), (sa), sizeof(**d), (void **)d)
+
+int nvkm_dmaobj_create_(struct nvkm_object *, struct nvkm_object *,
+                       struct nvkm_oclass *, void **, u32 *,
+                       int, void **);
+#define _nvkm_dmaobj_dtor nvkm_object_destroy
+#define _nvkm_dmaobj_init nvkm_object_init
+#define _nvkm_dmaobj_fini nvkm_object_fini
+
+int _nvkm_dmaeng_ctor(struct nvkm_object *, struct nvkm_object *,
+                     struct nvkm_oclass *, void *, u32,
+                     struct nvkm_object **);
+#define _nvkm_dmaeng_dtor _nvkm_engine_dtor
+#define _nvkm_dmaeng_init _nvkm_engine_init
+#define _nvkm_dmaeng_fini _nvkm_engine_fini
+
+struct nvkm_dmaeng_impl {
+       struct nvkm_oclass base;
+       struct nvkm_oclass *sclass;
+       int (*bind)(struct nvkm_dmaobj *, struct nvkm_object *,
+                   struct nvkm_gpuobj **);
+};
+#endif
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/falcon.c b/drivers/gpu/drm/nouveau/nvkm/engine/falcon.c
new file mode 100644 (file)
index 0000000..30958c1
--- /dev/null
@@ -0,0 +1,277 @@
+/*
+ * Copyright 2012 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.
+ */
+#include <engine/falcon.h>
+
+#include <core/device.h>
+#include <subdev/timer.h>
+
+void
+nvkm_falcon_intr(struct nvkm_subdev *subdev)
+{
+       struct nvkm_falcon *falcon = (void *)subdev;
+       u32 dispatch = nv_ro32(falcon, 0x01c);
+       u32 intr = nv_ro32(falcon, 0x008) & dispatch & ~(dispatch >> 16);
+
+       if (intr & 0x00000010) {
+               nv_debug(falcon, "ucode halted\n");
+               nv_wo32(falcon, 0x004, 0x00000010);
+               intr &= ~0x00000010;
+       }
+
+       if (intr)  {
+               nv_error(falcon, "unhandled intr 0x%08x\n", intr);
+               nv_wo32(falcon, 0x004, intr);
+       }
+}
+
+u32
+_nvkm_falcon_rd32(struct nvkm_object *object, u64 addr)
+{
+       struct nvkm_falcon *falcon = (void *)object;
+       return nv_rd32(falcon, falcon->addr + addr);
+}
+
+void
+_nvkm_falcon_wr32(struct nvkm_object *object, u64 addr, u32 data)
+{
+       struct nvkm_falcon *falcon = (void *)object;
+       nv_wr32(falcon, falcon->addr + addr, data);
+}
+
+static void *
+vmemdup(const void *src, size_t len)
+{
+       void *p = vmalloc(len);
+
+       if (p)
+               memcpy(p, src, len);
+       return p;
+}
+
+int
+_nvkm_falcon_init(struct nvkm_object *object)
+{
+       struct nvkm_device *device = nv_device(object);
+       struct nvkm_falcon *falcon = (void *)object;
+       const struct firmware *fw;
+       char name[32] = "internal";
+       int ret, i;
+       u32 caps;
+
+       /* enable engine, and determine its capabilities */
+       ret = nvkm_engine_init(&falcon->base);
+       if (ret)
+               return ret;
+
+       if (device->chipset <  0xa3 ||
+           device->chipset == 0xaa || device->chipset == 0xac) {
+               falcon->version = 0;
+               falcon->secret  = (falcon->addr == 0x087000) ? 1 : 0;
+       } else {
+               caps = nv_ro32(falcon, 0x12c);
+               falcon->version = (caps & 0x0000000f);
+               falcon->secret  = (caps & 0x00000030) >> 4;
+       }
+
+       caps = nv_ro32(falcon, 0x108);
+       falcon->code.limit = (caps & 0x000001ff) << 8;
+       falcon->data.limit = (caps & 0x0003fe00) >> 1;
+
+       nv_debug(falcon, "falcon version: %d\n", falcon->version);
+       nv_debug(falcon, "secret level: %d\n", falcon->secret);
+       nv_debug(falcon, "code limit: %d\n", falcon->code.limit);
+       nv_debug(falcon, "data limit: %d\n", falcon->data.limit);
+
+       /* wait for 'uc halted' to be signalled before continuing */
+       if (falcon->secret && falcon->version < 4) {
+               if (!falcon->version)
+                       nv_wait(falcon, 0x008, 0x00000010, 0x00000010);
+               else
+                       nv_wait(falcon, 0x180, 0x80000000, 0);
+               nv_wo32(falcon, 0x004, 0x00000010);
+       }
+
+       /* disable all interrupts */
+       nv_wo32(falcon, 0x014, 0xffffffff);
+
+       /* no default ucode provided by the engine implementation, try and
+        * locate a "self-bootstrapping" firmware image for the engine
+        */
+       if (!falcon->code.data) {
+               snprintf(name, sizeof(name), "nouveau/nv%02x_fuc%03x",
+                        device->chipset, falcon->addr >> 12);
+
+               ret = request_firmware(&fw, name, nv_device_base(device));
+               if (ret == 0) {
+                       falcon->code.data = vmemdup(fw->data, fw->size);
+                       falcon->code.size = fw->size;
+                       falcon->data.data = NULL;
+                       falcon->data.size = 0;
+                       release_firmware(fw);
+               }
+
+               falcon->external = true;
+       }
+
+       /* next step is to try and load "static code/data segment" firmware
+        * images for the engine
+        */
+       if (!falcon->code.data) {
+               snprintf(name, sizeof(name), "nouveau/nv%02x_fuc%03xd",
+                        device->chipset, falcon->addr >> 12);
+
+               ret = request_firmware(&fw, name, nv_device_base(device));
+               if (ret) {
+                       nv_error(falcon, "unable to load firmware data\n");
+                       return ret;
+               }
+
+               falcon->data.data = vmemdup(fw->data, fw->size);
+               falcon->data.size = fw->size;
+               release_firmware(fw);
+               if (!falcon->data.data)
+                       return -ENOMEM;
+
+               snprintf(name, sizeof(name), "nouveau/nv%02x_fuc%03xc",
+                        device->chipset, falcon->addr >> 12);
+
+               ret = request_firmware(&fw, name, nv_device_base(device));
+               if (ret) {
+                       nv_error(falcon, "unable to load firmware code\n");
+                       return ret;
+               }
+
+               falcon->code.data = vmemdup(fw->data, fw->size);
+               falcon->code.size = fw->size;
+               release_firmware(fw);
+               if (!falcon->code.data)
+                       return -ENOMEM;
+       }
+
+       nv_debug(falcon, "firmware: %s (%s)\n", name, falcon->data.data ?
+                "static code/data segments" : "self-bootstrapping");
+
+       /* ensure any "self-bootstrapping" firmware image is in vram */
+       if (!falcon->data.data && !falcon->core) {
+               ret = nvkm_gpuobj_new(object->parent, NULL, falcon->code.size,
+                                     256, 0, &falcon->core);
+               if (ret) {
+                       nv_error(falcon, "core allocation failed, %d\n", ret);
+                       return ret;
+               }
+
+               for (i = 0; i < falcon->code.size; i += 4)
+                       nv_wo32(falcon->core, i, falcon->code.data[i / 4]);
+       }
+
+       /* upload firmware bootloader (or the full code segments) */
+       if (falcon->core) {
+               if (device->card_type < NV_C0)
+                       nv_wo32(falcon, 0x618, 0x04000000);
+               else
+                       nv_wo32(falcon, 0x618, 0x00000114);
+               nv_wo32(falcon, 0x11c, 0);
+               nv_wo32(falcon, 0x110, falcon->core->addr >> 8);
+               nv_wo32(falcon, 0x114, 0);
+               nv_wo32(falcon, 0x118, 0x00006610);
+       } else {
+               if (falcon->code.size > falcon->code.limit ||
+                   falcon->data.size > falcon->data.limit) {
+                       nv_error(falcon, "ucode exceeds falcon limit(s)\n");
+                       return -EINVAL;
+               }
+
+               if (falcon->version < 3) {
+                       nv_wo32(falcon, 0xff8, 0x00100000);
+                       for (i = 0; i < falcon->code.size / 4; i++)
+                               nv_wo32(falcon, 0xff4, falcon->code.data[i]);
+               } else {
+                       nv_wo32(falcon, 0x180, 0x01000000);
+                       for (i = 0; i < falcon->code.size / 4; i++) {
+                               if ((i & 0x3f) == 0)
+                                       nv_wo32(falcon, 0x188, i >> 6);
+                               nv_wo32(falcon, 0x184, falcon->code.data[i]);
+                       }
+               }
+       }
+
+       /* upload data segment (if necessary), zeroing the remainder */
+       if (falcon->version < 3) {
+               nv_wo32(falcon, 0xff8, 0x00000000);
+               for (i = 0; !falcon->core && i < falcon->data.size / 4; i++)
+                       nv_wo32(falcon, 0xff4, falcon->data.data[i]);
+               for (; i < falcon->data.limit; i += 4)
+                       nv_wo32(falcon, 0xff4, 0x00000000);
+       } else {
+               nv_wo32(falcon, 0x1c0, 0x01000000);
+               for (i = 0; !falcon->core && i < falcon->data.size / 4; i++)
+                       nv_wo32(falcon, 0x1c4, falcon->data.data[i]);
+               for (; i < falcon->data.limit / 4; i++)
+                       nv_wo32(falcon, 0x1c4, 0x00000000);
+       }
+
+       /* start it running */
+       nv_wo32(falcon, 0x10c, 0x00000001); /* BLOCK_ON_FIFO */
+       nv_wo32(falcon, 0x104, 0x00000000); /* ENTRY */
+       nv_wo32(falcon, 0x100, 0x00000002); /* TRIGGER */
+       nv_wo32(falcon, 0x048, 0x00000003); /* FIFO | CHSW */
+       return 0;
+}
+
+int
+_nvkm_falcon_fini(struct nvkm_object *object, bool suspend)
+{
+       struct nvkm_falcon *falcon = (void *)object;
+
+       if (!suspend) {
+               nvkm_gpuobj_ref(NULL, &falcon->core);
+               if (falcon->external) {
+                       vfree(falcon->data.data);
+                       vfree(falcon->code.data);
+                       falcon->code.data = NULL;
+               }
+       }
+
+       nv_mo32(falcon, 0x048, 0x00000003, 0x00000000);
+       nv_wo32(falcon, 0x014, 0xffffffff);
+
+       return nvkm_engine_fini(&falcon->base, suspend);
+}
+
+int
+nvkm_falcon_create_(struct nvkm_object *parent, struct nvkm_object *engine,
+                   struct nvkm_oclass *oclass, u32 addr, bool enable,
+                   const char *iname, const char *fname,
+                   int length, void **pobject)
+{
+       struct nvkm_falcon *falcon;
+       int ret;
+
+       ret = nvkm_engine_create_(parent, engine, oclass, enable, iname,
+                                 fname, length, pobject);
+       falcon = *pobject;
+       if (ret)
+               return ret;
+
+       falcon->addr = addr;
+       return 0;
+}
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/fifo/Kbuild b/drivers/gpu/drm/nouveau/nvkm/engine/fifo/Kbuild
new file mode 100644 (file)
index 0000000..c5a2d87
--- /dev/null
@@ -0,0 +1,11 @@
+nvkm-y += nvkm/engine/fifo/base.o
+nvkm-y += nvkm/engine/fifo/nv04.o
+nvkm-y += nvkm/engine/fifo/nv10.o
+nvkm-y += nvkm/engine/fifo/nv17.o
+nvkm-y += nvkm/engine/fifo/nv40.o
+nvkm-y += nvkm/engine/fifo/nv50.o
+nvkm-y += nvkm/engine/fifo/g84.o
+nvkm-y += nvkm/engine/fifo/gf100.o
+nvkm-y += nvkm/engine/fifo/gk104.o
+nvkm-y += nvkm/engine/fifo/gk20a.o
+nvkm-y += nvkm/engine/fifo/gk208.o
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/fifo/base.c b/drivers/gpu/drm/nouveau/nvkm/engine/fifo/base.c
new file mode 100644 (file)
index 0000000..fa223f8
--- /dev/null
@@ -0,0 +1,282 @@
+/*
+ * Copyright 2012 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 <engine/fifo.h>
+
+#include <core/client.h>
+#include <core/device.h>
+#include <core/handle.h>
+#include <core/notify.h>
+#include <engine/dmaobj.h>
+
+#include <nvif/class.h>
+#include <nvif/event.h>
+#include <nvif/unpack.h>
+
+static int
+nvkm_fifo_event_ctor(struct nvkm_object *object, void *data, u32 size,
+                    struct nvkm_notify *notify)
+{
+       if (size == 0) {
+               notify->size  = 0;
+               notify->types = 1;
+               notify->index = 0;
+               return 0;
+       }
+       return -ENOSYS;
+}
+
+static const struct nvkm_event_func
+nvkm_fifo_event_func = {
+       .ctor = nvkm_fifo_event_ctor,
+};
+
+int
+nvkm_fifo_channel_create_(struct nvkm_object *parent,
+                         struct nvkm_object *engine,
+                         struct nvkm_oclass *oclass,
+                         int bar, u32 addr, u32 size, u32 pushbuf,
+                         u64 engmask, int len, void **ptr)
+{
+       struct nvkm_device *device = nv_device(engine);
+       struct nvkm_fifo *priv = (void *)engine;
+       struct nvkm_fifo_chan *chan;
+       struct nvkm_dmaeng *dmaeng;
+       unsigned long flags;
+       int ret;
+
+       /* create base object class */
+       ret = nvkm_namedb_create_(parent, engine, oclass, 0, NULL,
+                                 engmask, len, ptr);
+       chan = *ptr;
+       if (ret)
+               return ret;
+
+       /* validate dma object representing push buffer */
+       chan->pushdma = (void *)nvkm_handle_ref(parent, pushbuf);
+       if (!chan->pushdma)
+               return -ENOENT;
+
+       dmaeng = (void *)chan->pushdma->base.engine;
+       switch (chan->pushdma->base.oclass->handle) {
+       case NV_DMA_FROM_MEMORY:
+       case NV_DMA_IN_MEMORY:
+               break;
+       default:
+               return -EINVAL;
+       }
+
+       ret = dmaeng->bind(chan->pushdma, parent, &chan->pushgpu);
+       if (ret)
+               return ret;
+
+       /* find a free fifo channel */
+       spin_lock_irqsave(&priv->lock, flags);
+       for (chan->chid = priv->min; chan->chid < priv->max; chan->chid++) {
+               if (!priv->channel[chan->chid]) {
+                       priv->channel[chan->chid] = nv_object(chan);
+                       break;
+               }
+       }
+       spin_unlock_irqrestore(&priv->lock, flags);
+
+       if (chan->chid == priv->max) {
+               nv_error(priv, "no free channels\n");
+               return -ENOSPC;
+       }
+
+       chan->addr = nv_device_resource_start(device, bar) +
+                    addr + size * chan->chid;
+       chan->size = size;
+       nvkm_event_send(&priv->cevent, 1, 0, NULL, 0);
+       return 0;
+}
+
+void
+nvkm_fifo_channel_destroy(struct nvkm_fifo_chan *chan)
+{
+       struct nvkm_fifo *priv = (void *)nv_object(chan)->engine;
+       unsigned long flags;
+
+       if (chan->user)
+               iounmap(chan->user);
+
+       spin_lock_irqsave(&priv->lock, flags);
+       priv->channel[chan->chid] = NULL;
+       spin_unlock_irqrestore(&priv->lock, flags);
+
+       nvkm_gpuobj_ref(NULL, &chan->pushgpu);
+       nvkm_object_ref(NULL, (struct nvkm_object **)&chan->pushdma);
+       nvkm_namedb_destroy(&chan->namedb);
+}
+
+void
+_nvkm_fifo_channel_dtor(struct nvkm_object *object)
+{
+       struct nvkm_fifo_chan *chan = (void *)object;
+       nvkm_fifo_channel_destroy(chan);
+}
+
+int
+_nvkm_fifo_channel_map(struct nvkm_object *object, u64 *addr, u32 *size)
+{
+       struct nvkm_fifo_chan *chan = (void *)object;
+       *addr = chan->addr;
+       *size = chan->size;
+       return 0;
+}
+
+u32
+_nvkm_fifo_channel_rd32(struct nvkm_object *object, u64 addr)
+{
+       struct nvkm_fifo_chan *chan = (void *)object;
+       if (unlikely(!chan->user)) {
+               chan->user = ioremap(chan->addr, chan->size);
+               if (WARN_ON_ONCE(chan->user == NULL))
+                       return 0;
+       }
+       return ioread32_native(chan->user + addr);
+}
+
+void
+_nvkm_fifo_channel_wr32(struct nvkm_object *object, u64 addr, u32 data)
+{
+       struct nvkm_fifo_chan *chan = (void *)object;
+       if (unlikely(!chan->user)) {
+               chan->user = ioremap(chan->addr, chan->size);
+               if (WARN_ON_ONCE(chan->user == NULL))
+                       return;
+       }
+       iowrite32_native(data, chan->user + addr);
+}
+
+int
+nvkm_fifo_uevent_ctor(struct nvkm_object *object, void *data, u32 size,
+                     struct nvkm_notify *notify)
+{
+       union {
+               struct nvif_notify_uevent_req none;
+       } *req = data;
+       int ret;
+
+       if (nvif_unvers(req->none)) {
+               notify->size  = sizeof(struct nvif_notify_uevent_rep);
+               notify->types = 1;
+               notify->index = 0;
+       }
+
+       return ret;
+}
+
+void
+nvkm_fifo_uevent(struct nvkm_fifo *fifo)
+{
+       struct nvif_notify_uevent_rep rep = {
+       };
+       nvkm_event_send(&fifo->uevent, 1, 0, &rep, sizeof(rep));
+}
+
+int
+_nvkm_fifo_channel_ntfy(struct nvkm_object *object, u32 type,
+                       struct nvkm_event **event)
+{
+       struct nvkm_fifo *fifo = (void *)object->engine;
+       switch (type) {
+       case G82_CHANNEL_DMA_V0_NTFY_UEVENT:
+               if (nv_mclass(object) >= G82_CHANNEL_DMA) {
+                       *event = &fifo->uevent;
+                       return 0;
+               }
+               break;
+       default:
+               break;
+       }
+       return -EINVAL;
+}
+
+static int
+nvkm_fifo_chid(struct nvkm_fifo *priv, struct nvkm_object *object)
+{
+       int engidx = nv_hclass(priv) & 0xff;
+
+       while (object && object->parent) {
+               if ( nv_iclass(object->parent, NV_ENGCTX_CLASS) &&
+                   (nv_hclass(object->parent) & 0xff) == engidx)
+                       return nvkm_fifo_chan(object)->chid;
+               object = object->parent;
+       }
+
+       return -1;
+}
+
+const char *
+nvkm_client_name_for_fifo_chid(struct nvkm_fifo *fifo, u32 chid)
+{
+       struct nvkm_fifo_chan *chan = NULL;
+       unsigned long flags;
+
+       spin_lock_irqsave(&fifo->lock, flags);
+       if (chid >= fifo->min && chid <= fifo->max)
+               chan = (void *)fifo->channel[chid];
+       spin_unlock_irqrestore(&fifo->lock, flags);
+
+       return nvkm_client_name(chan);
+}
+
+void
+nvkm_fifo_destroy(struct nvkm_fifo *priv)
+{
+       kfree(priv->channel);
+       nvkm_event_fini(&priv->uevent);
+       nvkm_event_fini(&priv->cevent);
+       nvkm_engine_destroy(&priv->base);
+}
+
+int
+nvkm_fifo_create_(struct nvkm_object *parent, struct nvkm_object *engine,
+                 struct nvkm_oclass *oclass,
+                 int min, int max, int length, void **pobject)
+{
+       struct nvkm_fifo *priv;
+       int ret;
+
+       ret = nvkm_engine_create_(parent, engine, oclass, true, "PFIFO",
+                                 "fifo", length, pobject);
+       priv = *pobject;
+       if (ret)
+               return ret;
+
+       priv->min = min;
+       priv->max = max;
+       priv->channel = kzalloc(sizeof(*priv->channel) * (max + 1), GFP_KERNEL);
+       if (!priv->channel)
+               return -ENOMEM;
+
+       ret = nvkm_event_init(&nvkm_fifo_event_func, 1, 1, &priv->cevent);
+       if (ret)
+               return ret;
+
+       priv->chid = nvkm_fifo_chid;
+       spin_lock_init(&priv->lock);
+       return 0;
+}
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/fifo/g84.c b/drivers/gpu/drm/nouveau/nvkm/engine/fifo/g84.c
new file mode 100644 (file)
index 0000000..a04920b
--- /dev/null
@@ -0,0 +1,487 @@
+/*
+ * Copyright 2012 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 "nv50.h"
+#include "nv04.h"
+
+#include <core/client.h>
+#include <core/engctx.h>
+#include <core/ramht.h>
+#include <subdev/bar.h>
+#include <subdev/mmu.h>
+#include <subdev/timer.h>
+
+#include <nvif/class.h>
+#include <nvif/unpack.h>
+
+/*******************************************************************************
+ * FIFO channel objects
+ ******************************************************************************/
+
+static int
+g84_fifo_context_attach(struct nvkm_object *parent, struct nvkm_object *object)
+{
+       struct nvkm_bar *bar = nvkm_bar(parent);
+       struct nv50_fifo_base *base = (void *)parent->parent;
+       struct nvkm_gpuobj *ectx = (void *)object;
+       u64 limit = ectx->addr + ectx->size - 1;
+       u64 start = ectx->addr;
+       u32 addr;
+
+       switch (nv_engidx(object->engine)) {
+       case NVDEV_ENGINE_SW    : return 0;
+       case NVDEV_ENGINE_GR    : addr = 0x0020; break;
+       case NVDEV_ENGINE_VP    :
+       case NVDEV_ENGINE_MSPDEC: addr = 0x0040; break;
+       case NVDEV_ENGINE_MSPPP :
+       case NVDEV_ENGINE_MPEG  : addr = 0x0060; break;
+       case NVDEV_ENGINE_BSP   :
+       case NVDEV_ENGINE_MSVLD : addr = 0x0080; break;
+       case NVDEV_ENGINE_CIPHER:
+       case NVDEV_ENGINE_SEC   : addr = 0x00a0; break;
+       case NVDEV_ENGINE_CE0   : addr = 0x00c0; break;
+       default:
+               return -EINVAL;
+       }
+
+       nv_engctx(ectx)->addr = nv_gpuobj(base)->addr >> 12;
+       nv_wo32(base->eng, addr + 0x00, 0x00190000);
+       nv_wo32(base->eng, addr + 0x04, lower_32_bits(limit));
+       nv_wo32(base->eng, addr + 0x08, lower_32_bits(start));
+       nv_wo32(base->eng, addr + 0x0c, upper_32_bits(limit) << 24 |
+                                       upper_32_bits(start));
+       nv_wo32(base->eng, addr + 0x10, 0x00000000);
+       nv_wo32(base->eng, addr + 0x14, 0x00000000);
+       bar->flush(bar);
+       return 0;
+}
+
+static int
+g84_fifo_context_detach(struct nvkm_object *parent, bool suspend,
+                       struct nvkm_object *object)
+{
+       struct nvkm_bar *bar = nvkm_bar(parent);
+       struct nv50_fifo_priv *priv = (void *)parent->engine;
+       struct nv50_fifo_base *base = (void *)parent->parent;
+       struct nv50_fifo_chan *chan = (void *)parent;
+       u32 addr, save, engn;
+       bool done;
+
+       switch (nv_engidx(object->engine)) {
+       case NVDEV_ENGINE_SW    : return 0;
+       case NVDEV_ENGINE_GR    : engn = 0; addr = 0x0020; break;
+       case NVDEV_ENGINE_VP    :
+       case NVDEV_ENGINE_MSPDEC: engn = 3; addr = 0x0040; break;
+       case NVDEV_ENGINE_MSPPP :
+       case NVDEV_ENGINE_MPEG  : engn = 1; addr = 0x0060; break;
+       case NVDEV_ENGINE_BSP   :
+       case NVDEV_ENGINE_MSVLD : engn = 5; addr = 0x0080; break;
+       case NVDEV_ENGINE_CIPHER:
+       case NVDEV_ENGINE_SEC   : engn = 4; addr = 0x00a0; break;
+       case NVDEV_ENGINE_CE0   : engn = 2; addr = 0x00c0; break;
+       default:
+               return -EINVAL;
+       }
+
+       save = nv_mask(priv, 0x002520, 0x0000003f, 1 << engn);
+       nv_wr32(priv, 0x0032fc, nv_gpuobj(base)->addr >> 12);
+       done = nv_wait_ne(priv, 0x0032fc, 0xffffffff, 0xffffffff);
+       nv_wr32(priv, 0x002520, save);
+       if (!done) {
+               nv_error(priv, "channel %d [%s] unload timeout\n",
+                        chan->base.chid, nvkm_client_name(chan));
+               if (suspend)
+                       return -EBUSY;
+       }
+
+       nv_wo32(base->eng, addr + 0x00, 0x00000000);
+       nv_wo32(base->eng, addr + 0x04, 0x00000000);
+       nv_wo32(base->eng, addr + 0x08, 0x00000000);
+       nv_wo32(base->eng, addr + 0x0c, 0x00000000);
+       nv_wo32(base->eng, addr + 0x10, 0x00000000);
+       nv_wo32(base->eng, addr + 0x14, 0x00000000);
+       bar->flush(bar);
+       return 0;
+}
+
+static int
+g84_fifo_object_attach(struct nvkm_object *parent,
+                      struct nvkm_object *object, u32 handle)
+{
+       struct nv50_fifo_chan *chan = (void *)parent;
+       u32 context;
+
+       if (nv_iclass(object, NV_GPUOBJ_CLASS))
+               context = nv_gpuobj(object)->node->offset >> 4;
+       else
+               context = 0x00000004; /* just non-zero */
+
+       switch (nv_engidx(object->engine)) {
+       case NVDEV_ENGINE_DMAOBJ:
+       case NVDEV_ENGINE_SW    : context |= 0x00000000; break;
+       case NVDEV_ENGINE_GR    : context |= 0x00100000; break;
+       case NVDEV_ENGINE_MPEG  :
+       case NVDEV_ENGINE_MSPPP : context |= 0x00200000; break;
+       case NVDEV_ENGINE_ME    :
+       case NVDEV_ENGINE_CE0   : context |= 0x00300000; break;
+       case NVDEV_ENGINE_VP    :
+       case NVDEV_ENGINE_MSPDEC: context |= 0x00400000; break;
+       case NVDEV_ENGINE_CIPHER:
+       case NVDEV_ENGINE_SEC   :
+       case NVDEV_ENGINE_VIC   : context |= 0x00500000; break;
+       case NVDEV_ENGINE_BSP   :
+       case NVDEV_ENGINE_MSVLD : context |= 0x00600000; break;
+       default:
+               return -EINVAL;
+       }
+
+       return nvkm_ramht_insert(chan->ramht, 0, handle, context);
+}
+
+static int
+g84_fifo_chan_ctor_dma(struct nvkm_object *parent, struct nvkm_object *engine,
+                      struct nvkm_oclass *oclass, void *data, u32 size,
+                      struct nvkm_object **pobject)
+{
+       union {
+               struct nv03_channel_dma_v0 v0;
+       } *args = data;
+       struct nvkm_bar *bar = nvkm_bar(parent);
+       struct nv50_fifo_base *base = (void *)parent;
+       struct nv50_fifo_chan *chan;
+       int ret;
+
+       nv_ioctl(parent, "create channel dma size %d\n", size);
+       if (nvif_unpack(args->v0, 0, 0, false)) {
+               nv_ioctl(parent, "create channel dma vers %d pushbuf %08x "
+                                "offset %016llx\n", args->v0.version,
+                        args->v0.pushbuf, args->v0.offset);
+       } else
+               return ret;
+
+       ret = nvkm_fifo_channel_create(parent, engine, oclass, 0, 0xc00000,
+                                      0x2000, args->v0.pushbuf,
+                                      (1ULL << NVDEV_ENGINE_DMAOBJ) |
+                                      (1ULL << NVDEV_ENGINE_SW) |
+                                      (1ULL << NVDEV_ENGINE_GR) |
+                                      (1ULL << NVDEV_ENGINE_MPEG) |
+                                      (1ULL << NVDEV_ENGINE_ME) |
+                                      (1ULL << NVDEV_ENGINE_VP) |
+                                      (1ULL << NVDEV_ENGINE_CIPHER) |
+                                      (1ULL << NVDEV_ENGINE_SEC) |
+                                      (1ULL << NVDEV_ENGINE_BSP) |
+                                      (1ULL << NVDEV_ENGINE_MSVLD) |
+                                      (1ULL << NVDEV_ENGINE_MSPDEC) |
+                                      (1ULL << NVDEV_ENGINE_MSPPP) |
+                                      (1ULL << NVDEV_ENGINE_CE0) |
+                                      (1ULL << NVDEV_ENGINE_VIC), &chan);
+       *pobject = nv_object(chan);
+       if (ret)
+               return ret;
+
+       args->v0.chid = chan->base.chid;
+
+       ret = nvkm_ramht_new(nv_object(chan), nv_object(chan), 0x8000, 16,
+                            &chan->ramht);
+       if (ret)
+               return ret;
+
+       nv_parent(chan)->context_attach = g84_fifo_context_attach;
+       nv_parent(chan)->context_detach = g84_fifo_context_detach;
+       nv_parent(chan)->object_attach = g84_fifo_object_attach;
+       nv_parent(chan)->object_detach = nv50_fifo_object_detach;
+
+       nv_wo32(base->ramfc, 0x08, lower_32_bits(args->v0.offset));
+       nv_wo32(base->ramfc, 0x0c, upper_32_bits(args->v0.offset));
+       nv_wo32(base->ramfc, 0x10, lower_32_bits(args->v0.offset));
+       nv_wo32(base->ramfc, 0x14, upper_32_bits(args->v0.offset));
+       nv_wo32(base->ramfc, 0x3c, 0x003f6078);
+       nv_wo32(base->ramfc, 0x44, 0x01003fff);
+       nv_wo32(base->ramfc, 0x48, chan->base.pushgpu->node->offset >> 4);
+       nv_wo32(base->ramfc, 0x4c, 0xffffffff);
+       nv_wo32(base->ramfc, 0x60, 0x7fffffff);
+       nv_wo32(base->ramfc, 0x78, 0x00000000);
+       nv_wo32(base->ramfc, 0x7c, 0x30000001);
+       nv_wo32(base->ramfc, 0x80, ((chan->ramht->bits - 9) << 27) |
+                                  (4 << 24) /* SEARCH_FULL */ |
+                                  (chan->ramht->gpuobj.node->offset >> 4));
+       nv_wo32(base->ramfc, 0x88, base->cache->addr >> 10);
+       nv_wo32(base->ramfc, 0x98, nv_gpuobj(base)->addr >> 12);
+       bar->flush(bar);
+       return 0;
+}
+
+static int
+g84_fifo_chan_ctor_ind(struct nvkm_object *parent, struct nvkm_object *engine,
+                      struct nvkm_oclass *oclass, void *data, u32 size,
+                      struct nvkm_object **pobject)
+{
+       union {
+               struct nv50_channel_gpfifo_v0 v0;
+       } *args = data;
+       struct nvkm_bar *bar = nvkm_bar(parent);
+       struct nv50_fifo_base *base = (void *)parent;
+       struct nv50_fifo_chan *chan;
+       u64 ioffset, ilength;
+       int ret;
+
+       nv_ioctl(parent, "create channel gpfifo size %d\n", size);
+       if (nvif_unpack(args->v0, 0, 0, false)) {
+               nv_ioctl(parent, "create channel gpfifo vers %d pushbuf %08x "
+                                "ioffset %016llx ilength %08x\n",
+                        args->v0.version, args->v0.pushbuf, args->v0.ioffset,
+                        args->v0.ilength);
+       } else
+               return ret;
+
+       ret = nvkm_fifo_channel_create(parent, engine, oclass, 0, 0xc00000,
+                                      0x2000, args->v0.pushbuf,
+                                      (1ULL << NVDEV_ENGINE_DMAOBJ) |
+                                      (1ULL << NVDEV_ENGINE_SW) |
+                                      (1ULL << NVDEV_ENGINE_GR) |
+                                      (1ULL << NVDEV_ENGINE_MPEG) |
+                                      (1ULL << NVDEV_ENGINE_ME) |
+                                      (1ULL << NVDEV_ENGINE_VP) |
+                                      (1ULL << NVDEV_ENGINE_CIPHER) |
+                                      (1ULL << NVDEV_ENGINE_SEC) |
+                                      (1ULL << NVDEV_ENGINE_BSP) |
+                                      (1ULL << NVDEV_ENGINE_MSVLD) |
+                                      (1ULL << NVDEV_ENGINE_MSPDEC) |
+                                      (1ULL << NVDEV_ENGINE_MSPPP) |
+                                      (1ULL << NVDEV_ENGINE_CE0) |
+                                      (1ULL << NVDEV_ENGINE_VIC), &chan);
+       *pobject = nv_object(chan);
+       if (ret)
+               return ret;
+
+       args->v0.chid = chan->base.chid;
+
+       ret = nvkm_ramht_new(nv_object(chan), nv_object(chan), 0x8000, 16,
+                            &chan->ramht);
+       if (ret)
+               return ret;
+
+       nv_parent(chan)->context_attach = g84_fifo_context_attach;
+       nv_parent(chan)->context_detach = g84_fifo_context_detach;
+       nv_parent(chan)->object_attach = g84_fifo_object_attach;
+       nv_parent(chan)->object_detach = nv50_fifo_object_detach;
+
+       ioffset = args->v0.ioffset;
+       ilength = order_base_2(args->v0.ilength / 8);
+
+       nv_wo32(base->ramfc, 0x3c, 0x403f6078);
+       nv_wo32(base->ramfc, 0x44, 0x01003fff);
+       nv_wo32(base->ramfc, 0x48, chan->base.pushgpu->node->offset >> 4);
+       nv_wo32(base->ramfc, 0x50, lower_32_bits(ioffset));
+       nv_wo32(base->ramfc, 0x54, upper_32_bits(ioffset) | (ilength << 16));
+       nv_wo32(base->ramfc, 0x60, 0x7fffffff);
+       nv_wo32(base->ramfc, 0x78, 0x00000000);
+       nv_wo32(base->ramfc, 0x7c, 0x30000001);
+       nv_wo32(base->ramfc, 0x80, ((chan->ramht->bits - 9) << 27) |
+                                  (4 << 24) /* SEARCH_FULL */ |
+                                  (chan->ramht->gpuobj.node->offset >> 4));
+       nv_wo32(base->ramfc, 0x88, base->cache->addr >> 10);
+       nv_wo32(base->ramfc, 0x98, nv_gpuobj(base)->addr >> 12);
+       bar->flush(bar);
+       return 0;
+}
+
+static int
+g84_fifo_chan_init(struct nvkm_object *object)
+{
+       struct nv50_fifo_priv *priv = (void *)object->engine;
+       struct nv50_fifo_base *base = (void *)object->parent;
+       struct nv50_fifo_chan *chan = (void *)object;
+       struct nvkm_gpuobj *ramfc = base->ramfc;
+       u32 chid = chan->base.chid;
+       int ret;
+
+       ret = nvkm_fifo_channel_init(&chan->base);
+       if (ret)
+               return ret;
+
+       nv_wr32(priv, 0x002600 + (chid * 4), 0x80000000 | ramfc->addr >> 8);
+       nv50_fifo_playlist_update(priv);
+       return 0;
+}
+
+static struct nvkm_ofuncs
+g84_fifo_ofuncs_dma = {
+       .ctor = g84_fifo_chan_ctor_dma,
+       .dtor = nv50_fifo_chan_dtor,
+       .init = g84_fifo_chan_init,
+       .fini = nv50_fifo_chan_fini,
+       .map  = _nvkm_fifo_channel_map,
+       .rd32 = _nvkm_fifo_channel_rd32,
+       .wr32 = _nvkm_fifo_channel_wr32,
+       .ntfy = _nvkm_fifo_channel_ntfy
+};
+
+static struct nvkm_ofuncs
+g84_fifo_ofuncs_ind = {
+       .ctor = g84_fifo_chan_ctor_ind,
+       .dtor = nv50_fifo_chan_dtor,
+       .init = g84_fifo_chan_init,
+       .fini = nv50_fifo_chan_fini,
+       .map  = _nvkm_fifo_channel_map,
+       .rd32 = _nvkm_fifo_channel_rd32,
+       .wr32 = _nvkm_fifo_channel_wr32,
+       .ntfy = _nvkm_fifo_channel_ntfy
+};
+
+static struct nvkm_oclass
+g84_fifo_sclass[] = {
+       { G82_CHANNEL_DMA, &g84_fifo_ofuncs_dma },
+       { G82_CHANNEL_GPFIFO, &g84_fifo_ofuncs_ind },
+       {}
+};
+
+/*******************************************************************************
+ * FIFO context - basically just the instmem reserved for the channel
+ ******************************************************************************/
+
+static int
+g84_fifo_context_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+                     struct nvkm_oclass *oclass, void *data, u32 size,
+                     struct nvkm_object **pobject)
+{
+       struct nv50_fifo_base *base;
+       int ret;
+
+       ret = nvkm_fifo_context_create(parent, engine, oclass, NULL, 0x10000,
+                                      0x1000, NVOBJ_FLAG_HEAP, &base);
+       *pobject = nv_object(base);
+       if (ret)
+               return ret;
+
+       ret = nvkm_gpuobj_new(nv_object(base), nv_object(base), 0x0200, 0,
+                             NVOBJ_FLAG_ZERO_ALLOC, &base->eng);
+       if (ret)
+               return ret;
+
+       ret = nvkm_gpuobj_new(nv_object(base), nv_object(base), 0x4000, 0,
+                             0, &base->pgd);
+       if (ret)
+               return ret;
+
+       ret = nvkm_vm_ref(nvkm_client(parent)->vm, &base->vm, base->pgd);
+       if (ret)
+               return ret;
+
+       ret = nvkm_gpuobj_new(nv_object(base), nv_object(base), 0x1000,
+                             0x400, NVOBJ_FLAG_ZERO_ALLOC, &base->cache);
+       if (ret)
+               return ret;
+
+       ret = nvkm_gpuobj_new(nv_object(base), nv_object(base), 0x0100,
+                             0x100, NVOBJ_FLAG_ZERO_ALLOC, &base->ramfc);
+       if (ret)
+               return ret;
+
+       return 0;
+}
+
+static struct nvkm_oclass
+g84_fifo_cclass = {
+       .handle = NV_ENGCTX(FIFO, 0x84),
+       .ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = g84_fifo_context_ctor,
+               .dtor = nv50_fifo_context_dtor,
+               .init = _nvkm_fifo_context_init,
+               .fini = _nvkm_fifo_context_fini,
+               .rd32 = _nvkm_fifo_context_rd32,
+               .wr32 = _nvkm_fifo_context_wr32,
+       },
+};
+
+/*******************************************************************************
+ * PFIFO engine
+ ******************************************************************************/
+
+static void
+g84_fifo_uevent_init(struct nvkm_event *event, int type, int index)
+{
+       struct nvkm_fifo *fifo = container_of(event, typeof(*fifo), uevent);
+       nv_mask(fifo, 0x002140, 0x40000000, 0x40000000);
+}
+
+static void
+g84_fifo_uevent_fini(struct nvkm_event *event, int type, int index)
+{
+       struct nvkm_fifo *fifo = container_of(event, typeof(*fifo), uevent);
+       nv_mask(fifo, 0x002140, 0x40000000, 0x00000000);
+}
+
+static const struct nvkm_event_func
+g84_fifo_uevent_func = {
+       .ctor = nvkm_fifo_uevent_ctor,
+       .init = g84_fifo_uevent_init,
+       .fini = g84_fifo_uevent_fini,
+};
+
+static int
+g84_fifo_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+             struct nvkm_oclass *oclass, void *data, u32 size,
+             struct nvkm_object **pobject)
+{
+       struct nv50_fifo_priv *priv;
+       int ret;
+
+       ret = nvkm_fifo_create(parent, engine, oclass, 1, 127, &priv);
+       *pobject = nv_object(priv);
+       if (ret)
+               return ret;
+
+       ret = nvkm_gpuobj_new(nv_object(priv), NULL, 128 * 4, 0x1000, 0,
+                             &priv->playlist[0]);
+       if (ret)
+               return ret;
+
+       ret = nvkm_gpuobj_new(nv_object(priv), NULL, 128 * 4, 0x1000, 0,
+                             &priv->playlist[1]);
+       if (ret)
+               return ret;
+
+       ret = nvkm_event_init(&g84_fifo_uevent_func, 1, 1, &priv->base.uevent);
+       if (ret)
+               return ret;
+
+       nv_subdev(priv)->unit = 0x00000100;
+       nv_subdev(priv)->intr = nv04_fifo_intr;
+       nv_engine(priv)->cclass = &g84_fifo_cclass;
+       nv_engine(priv)->sclass = g84_fifo_sclass;
+       priv->base.pause = nv04_fifo_pause;
+       priv->base.start = nv04_fifo_start;
+       return 0;
+}
+
+struct nvkm_oclass *
+g84_fifo_oclass = &(struct nvkm_oclass) {
+       .handle = NV_ENGINE(FIFO, 0x84),
+       .ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = g84_fifo_ctor,
+               .dtor = nv50_fifo_dtor,
+               .init = nv50_fifo_init,
+               .fini = _nvkm_fifo_fini,
+       },
+};
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/fifo/gf100.c b/drivers/gpu/drm/nouveau/nvkm/engine/fifo/gf100.c
new file mode 100644 (file)
index 0000000..b745252
--- /dev/null
@@ -0,0 +1,967 @@
+/*
+ * Copyright 2012 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 <engine/fifo.h>
+
+#include <core/client.h>
+#include <core/engctx.h>
+#include <core/enum.h>
+#include <core/handle.h>
+#include <subdev/bar.h>
+#include <subdev/fb.h>
+#include <subdev/mmu.h>
+#include <subdev/timer.h>
+
+#include <nvif/class.h>
+#include <nvif/unpack.h>
+
+struct gf100_fifo_priv {
+       struct nvkm_fifo base;
+
+       struct work_struct fault;
+       u64 mask;
+
+       struct {
+               struct nvkm_gpuobj *mem[2];
+               int active;
+               wait_queue_head_t wait;
+       } runlist;
+
+       struct {
+               struct nvkm_gpuobj *mem;
+               struct nvkm_vma bar;
+       } user;
+       int spoon_nr;
+};
+
+struct gf100_fifo_base {
+       struct nvkm_fifo_base base;
+       struct nvkm_gpuobj *pgd;
+       struct nvkm_vm *vm;
+};
+
+struct gf100_fifo_chan {
+       struct nvkm_fifo_chan base;
+       enum {
+               STOPPED,
+               RUNNING,
+               KILLED
+       } state;
+};
+
+/*******************************************************************************
+ * FIFO channel objects
+ ******************************************************************************/
+
+static void
+gf100_fifo_runlist_update(struct gf100_fifo_priv *priv)
+{
+       struct nvkm_bar *bar = nvkm_bar(priv);
+       struct nvkm_gpuobj *cur;
+       int i, p;
+
+       mutex_lock(&nv_subdev(priv)->mutex);
+       cur = priv->runlist.mem[priv->runlist.active];
+       priv->runlist.active = !priv->runlist.active;
+
+       for (i = 0, p = 0; i < 128; i++) {
+               struct gf100_fifo_chan *chan = (void *)priv->base.channel[i];
+               if (chan && chan->state == RUNNING) {
+                       nv_wo32(cur, p + 0, i);
+                       nv_wo32(cur, p + 4, 0x00000004);
+                       p += 8;
+               }
+       }
+       bar->flush(bar);
+
+       nv_wr32(priv, 0x002270, cur->addr >> 12);
+       nv_wr32(priv, 0x002274, 0x01f00000 | (p >> 3));
+
+       if (wait_event_timeout(priv->runlist.wait,
+                              !(nv_rd32(priv, 0x00227c) & 0x00100000),
+                              msecs_to_jiffies(2000)) == 0)
+               nv_error(priv, "runlist update timeout\n");
+       mutex_unlock(&nv_subdev(priv)->mutex);
+}
+
+static int
+gf100_fifo_context_attach(struct nvkm_object *parent,
+                         struct nvkm_object *object)
+{
+       struct nvkm_bar *bar = nvkm_bar(parent);
+       struct gf100_fifo_base *base = (void *)parent->parent;
+       struct nvkm_engctx *ectx = (void *)object;
+       u32 addr;
+       int ret;
+
+       switch (nv_engidx(object->engine)) {
+       case NVDEV_ENGINE_SW    : return 0;
+       case NVDEV_ENGINE_GR    : addr = 0x0210; break;
+       case NVDEV_ENGINE_CE0   : addr = 0x0230; break;
+       case NVDEV_ENGINE_CE1   : addr = 0x0240; break;
+       case NVDEV_ENGINE_MSVLD : addr = 0x0270; break;
+       case NVDEV_ENGINE_MSPDEC: addr = 0x0250; break;
+       case NVDEV_ENGINE_MSPPP : addr = 0x0260; break;
+       default:
+               return -EINVAL;
+       }
+
+       if (!ectx->vma.node) {
+               ret = nvkm_gpuobj_map_vm(nv_gpuobj(ectx), base->vm,
+                                        NV_MEM_ACCESS_RW, &ectx->vma);
+               if (ret)
+                       return ret;
+
+               nv_engctx(ectx)->addr = nv_gpuobj(base)->addr >> 12;
+       }
+
+       nv_wo32(base, addr + 0x00, lower_32_bits(ectx->vma.offset) | 4);
+       nv_wo32(base, addr + 0x04, upper_32_bits(ectx->vma.offset));
+       bar->flush(bar);
+       return 0;
+}
+
+static int
+gf100_fifo_context_detach(struct nvkm_object *parent, bool suspend,
+                         struct nvkm_object *object)
+{
+       struct nvkm_bar *bar = nvkm_bar(parent);
+       struct gf100_fifo_priv *priv = (void *)parent->engine;
+       struct gf100_fifo_base *base = (void *)parent->parent;
+       struct gf100_fifo_chan *chan = (void *)parent;
+       u32 addr;
+
+       switch (nv_engidx(object->engine)) {
+       case NVDEV_ENGINE_SW    : return 0;
+       case NVDEV_ENGINE_GR    : addr = 0x0210; break;
+       case NVDEV_ENGINE_CE0   : addr = 0x0230; break;
+       case NVDEV_ENGINE_CE1   : addr = 0x0240; break;
+       case NVDEV_ENGINE_MSVLD : addr = 0x0270; break;
+       case NVDEV_ENGINE_MSPDEC: addr = 0x0250; break;
+       case NVDEV_ENGINE_MSPPP : addr = 0x0260; break;
+       default:
+               return -EINVAL;
+       }
+
+       nv_wr32(priv, 0x002634, chan->base.chid);
+       if (!nv_wait(priv, 0x002634, 0xffffffff, chan->base.chid)) {
+               nv_error(priv, "channel %d [%s] kick timeout\n",
+                        chan->base.chid, nvkm_client_name(chan));
+               if (suspend)
+                       return -EBUSY;
+       }
+
+       nv_wo32(base, addr + 0x00, 0x00000000);
+       nv_wo32(base, addr + 0x04, 0x00000000);
+       bar->flush(bar);
+       return 0;
+}
+
+static int
+gf100_fifo_chan_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+                    struct nvkm_oclass *oclass, void *data, u32 size,
+                    struct nvkm_object **pobject)
+{
+       union {
+               struct nv50_channel_gpfifo_v0 v0;
+       } *args = data;
+       struct nvkm_bar *bar = nvkm_bar(parent);
+       struct gf100_fifo_priv *priv = (void *)engine;
+       struct gf100_fifo_base *base = (void *)parent;
+       struct gf100_fifo_chan *chan;
+       u64 usermem, ioffset, ilength;
+       int ret, i;
+
+       nv_ioctl(parent, "create channel gpfifo size %d\n", size);
+       if (nvif_unpack(args->v0, 0, 0, false)) {
+               nv_ioctl(parent, "create channel gpfifo vers %d pushbuf %08x "
+                                "ioffset %016llx ilength %08x\n",
+                        args->v0.version, args->v0.pushbuf, args->v0.ioffset,
+                        args->v0.ilength);
+       } else
+               return ret;
+
+       ret = nvkm_fifo_channel_create(parent, engine, oclass, 1,
+                                      priv->user.bar.offset, 0x1000,
+                                      args->v0.pushbuf,
+                                      (1ULL << NVDEV_ENGINE_SW) |
+                                      (1ULL << NVDEV_ENGINE_GR) |
+                                      (1ULL << NVDEV_ENGINE_CE0) |
+                                      (1ULL << NVDEV_ENGINE_CE1) |
+                                      (1ULL << NVDEV_ENGINE_MSVLD) |
+                                      (1ULL << NVDEV_ENGINE_MSPDEC) |
+                                      (1ULL << NVDEV_ENGINE_MSPPP), &chan);
+       *pobject = nv_object(chan);
+       if (ret)
+               return ret;
+
+       args->v0.chid = chan->base.chid;
+
+       nv_parent(chan)->context_attach = gf100_fifo_context_attach;
+       nv_parent(chan)->context_detach = gf100_fifo_context_detach;
+
+       usermem = chan->base.chid * 0x1000;
+       ioffset = args->v0.ioffset;
+       ilength = order_base_2(args->v0.ilength / 8);
+
+       for (i = 0; i < 0x1000; i += 4)
+               nv_wo32(priv->user.mem, usermem + i, 0x00000000);
+
+       nv_wo32(base, 0x08, lower_32_bits(priv->user.mem->addr + usermem));
+       nv_wo32(base, 0x0c, upper_32_bits(priv->user.mem->addr + usermem));
+       nv_wo32(base, 0x10, 0x0000face);
+       nv_wo32(base, 0x30, 0xfffff902);
+       nv_wo32(base, 0x48, lower_32_bits(ioffset));
+       nv_wo32(base, 0x4c, upper_32_bits(ioffset) | (ilength << 16));
+       nv_wo32(base, 0x54, 0x00000002);
+       nv_wo32(base, 0x84, 0x20400000);
+       nv_wo32(base, 0x94, 0x30000001);
+       nv_wo32(base, 0x9c, 0x00000100);
+       nv_wo32(base, 0xa4, 0x1f1f1f1f);
+       nv_wo32(base, 0xa8, 0x1f1f1f1f);
+       nv_wo32(base, 0xac, 0x0000001f);
+       nv_wo32(base, 0xb8, 0xf8000000);
+       nv_wo32(base, 0xf8, 0x10003080); /* 0x002310 */
+       nv_wo32(base, 0xfc, 0x10000010); /* 0x002350 */
+       bar->flush(bar);
+       return 0;
+}
+
+static int
+gf100_fifo_chan_init(struct nvkm_object *object)
+{
+       struct nvkm_gpuobj *base = nv_gpuobj(object->parent);
+       struct gf100_fifo_priv *priv = (void *)object->engine;
+       struct gf100_fifo_chan *chan = (void *)object;
+       u32 chid = chan->base.chid;
+       int ret;
+
+       ret = nvkm_fifo_channel_init(&chan->base);
+       if (ret)
+               return ret;
+
+       nv_wr32(priv, 0x003000 + (chid * 8), 0xc0000000 | base->addr >> 12);
+
+       if (chan->state == STOPPED && (chan->state = RUNNING) == RUNNING) {
+               nv_wr32(priv, 0x003004 + (chid * 8), 0x001f0001);
+               gf100_fifo_runlist_update(priv);
+       }
+
+       return 0;
+}
+
+static void gf100_fifo_intr_engine(struct gf100_fifo_priv *priv);
+
+static int
+gf100_fifo_chan_fini(struct nvkm_object *object, bool suspend)
+{
+       struct gf100_fifo_priv *priv = (void *)object->engine;
+       struct gf100_fifo_chan *chan = (void *)object;
+       u32 chid = chan->base.chid;
+
+       if (chan->state == RUNNING && (chan->state = STOPPED) == STOPPED) {
+               nv_mask(priv, 0x003004 + (chid * 8), 0x00000001, 0x00000000);
+               gf100_fifo_runlist_update(priv);
+       }
+
+       gf100_fifo_intr_engine(priv);
+
+       nv_wr32(priv, 0x003000 + (chid * 8), 0x00000000);
+       return nvkm_fifo_channel_fini(&chan->base, suspend);
+}
+
+static struct nvkm_ofuncs
+gf100_fifo_ofuncs = {
+       .ctor = gf100_fifo_chan_ctor,
+       .dtor = _nvkm_fifo_channel_dtor,
+       .init = gf100_fifo_chan_init,
+       .fini = gf100_fifo_chan_fini,
+       .map  = _nvkm_fifo_channel_map,
+       .rd32 = _nvkm_fifo_channel_rd32,
+       .wr32 = _nvkm_fifo_channel_wr32,
+       .ntfy = _nvkm_fifo_channel_ntfy
+};
+
+static struct nvkm_oclass
+gf100_fifo_sclass[] = {
+       { FERMI_CHANNEL_GPFIFO, &gf100_fifo_ofuncs },
+       {}
+};
+
+/*******************************************************************************
+ * FIFO context - instmem heap and vm setup
+ ******************************************************************************/
+
+static int
+gf100_fifo_context_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+                       struct nvkm_oclass *oclass, void *data, u32 size,
+                       struct nvkm_object **pobject)
+{
+       struct gf100_fifo_base *base;
+       int ret;
+
+       ret = nvkm_fifo_context_create(parent, engine, oclass, NULL, 0x1000,
+                                      0x1000, NVOBJ_FLAG_ZERO_ALLOC |
+                                      NVOBJ_FLAG_HEAP, &base);
+       *pobject = nv_object(base);
+       if (ret)
+               return ret;
+
+       ret = nvkm_gpuobj_new(nv_object(base), NULL, 0x10000, 0x1000, 0,
+                             &base->pgd);
+       if (ret)
+               return ret;
+
+       nv_wo32(base, 0x0200, lower_32_bits(base->pgd->addr));
+       nv_wo32(base, 0x0204, upper_32_bits(base->pgd->addr));
+       nv_wo32(base, 0x0208, 0xffffffff);
+       nv_wo32(base, 0x020c, 0x000000ff);
+
+       ret = nvkm_vm_ref(nvkm_client(parent)->vm, &base->vm, base->pgd);
+       if (ret)
+               return ret;
+
+       return 0;
+}
+
+static void
+gf100_fifo_context_dtor(struct nvkm_object *object)
+{
+       struct gf100_fifo_base *base = (void *)object;
+       nvkm_vm_ref(NULL, &base->vm, base->pgd);
+       nvkm_gpuobj_ref(NULL, &base->pgd);
+       nvkm_fifo_context_destroy(&base->base);
+}
+
+static struct nvkm_oclass
+gf100_fifo_cclass = {
+       .handle = NV_ENGCTX(FIFO, 0xc0),
+       .ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = gf100_fifo_context_ctor,
+               .dtor = gf100_fifo_context_dtor,
+               .init = _nvkm_fifo_context_init,
+               .fini = _nvkm_fifo_context_fini,
+               .rd32 = _nvkm_fifo_context_rd32,
+               .wr32 = _nvkm_fifo_context_wr32,
+       },
+};
+
+/*******************************************************************************
+ * PFIFO engine
+ ******************************************************************************/
+
+static inline int
+gf100_fifo_engidx(struct gf100_fifo_priv *priv, u32 engn)
+{
+       switch (engn) {
+       case NVDEV_ENGINE_GR    : engn = 0; break;
+       case NVDEV_ENGINE_MSVLD : engn = 1; break;
+       case NVDEV_ENGINE_MSPPP : engn = 2; break;
+       case NVDEV_ENGINE_MSPDEC: engn = 3; break;
+       case NVDEV_ENGINE_CE0   : engn = 4; break;
+       case NVDEV_ENGINE_CE1   : engn = 5; break;
+       default:
+               return -1;
+       }
+
+       return engn;
+}
+
+static inline struct nvkm_engine *
+gf100_fifo_engine(struct gf100_fifo_priv *priv, u32 engn)
+{
+       switch (engn) {
+       case 0: engn = NVDEV_ENGINE_GR; break;
+       case 1: engn = NVDEV_ENGINE_MSVLD; break;
+       case 2: engn = NVDEV_ENGINE_MSPPP; break;
+       case 3: engn = NVDEV_ENGINE_MSPDEC; break;
+       case 4: engn = NVDEV_ENGINE_CE0; break;
+       case 5: engn = NVDEV_ENGINE_CE1; break;
+       default:
+               return NULL;
+       }
+
+       return nvkm_engine(priv, engn);
+}
+
+static void
+gf100_fifo_recover_work(struct work_struct *work)
+{
+       struct gf100_fifo_priv *priv = container_of(work, typeof(*priv), fault);
+       struct nvkm_object *engine;
+       unsigned long flags;
+       u32 engn, engm = 0;
+       u64 mask, todo;
+
+       spin_lock_irqsave(&priv->base.lock, flags);
+       mask = priv->mask;
+       priv->mask = 0ULL;
+       spin_unlock_irqrestore(&priv->base.lock, flags);
+
+       for (todo = mask; engn = __ffs64(todo), todo; todo &= ~(1 << engn))
+               engm |= 1 << gf100_fifo_engidx(priv, engn);
+       nv_mask(priv, 0x002630, engm, engm);
+
+       for (todo = mask; engn = __ffs64(todo), todo; todo &= ~(1 << engn)) {
+               if ((engine = (void *)nvkm_engine(priv, engn))) {
+                       nv_ofuncs(engine)->fini(engine, false);
+                       WARN_ON(nv_ofuncs(engine)->init(engine));
+               }
+       }
+
+       gf100_fifo_runlist_update(priv);
+       nv_wr32(priv, 0x00262c, engm);
+       nv_mask(priv, 0x002630, engm, 0x00000000);
+}
+
+static void
+gf100_fifo_recover(struct gf100_fifo_priv *priv, struct nvkm_engine *engine,
+                  struct gf100_fifo_chan *chan)
+{
+       u32 chid = chan->base.chid;
+       unsigned long flags;
+
+       nv_error(priv, "%s engine fault on channel %d, recovering...\n",
+                      nv_subdev(engine)->name, chid);
+
+       nv_mask(priv, 0x003004 + (chid * 0x08), 0x00000001, 0x00000000);
+       chan->state = KILLED;
+
+       spin_lock_irqsave(&priv->base.lock, flags);
+       priv->mask |= 1ULL << nv_engidx(engine);
+       spin_unlock_irqrestore(&priv->base.lock, flags);
+       schedule_work(&priv->fault);
+}
+
+static int
+gf100_fifo_swmthd(struct gf100_fifo_priv *priv, u32 chid, u32 mthd, u32 data)
+{
+       struct gf100_fifo_chan *chan = NULL;
+       struct nvkm_handle *bind;
+       unsigned long flags;
+       int ret = -EINVAL;
+
+       spin_lock_irqsave(&priv->base.lock, flags);
+       if (likely(chid >= priv->base.min && chid <= priv->base.max))
+               chan = (void *)priv->base.channel[chid];
+       if (unlikely(!chan))
+               goto out;
+
+       bind = nvkm_namedb_get_class(nv_namedb(chan), 0x906e);
+       if (likely(bind)) {
+               if (!mthd || !nv_call(bind->object, mthd, data))
+                       ret = 0;
+               nvkm_namedb_put(bind);
+       }
+
+out:
+       spin_unlock_irqrestore(&priv->base.lock, flags);
+       return ret;
+}
+
+static const struct nvkm_enum
+gf100_fifo_sched_reason[] = {
+       { 0x0a, "CTXSW_TIMEOUT" },
+       {}
+};
+
+static void
+gf100_fifo_intr_sched_ctxsw(struct gf100_fifo_priv *priv)
+{
+       struct nvkm_engine *engine;
+       struct gf100_fifo_chan *chan;
+       u32 engn;
+
+       for (engn = 0; engn < 6; engn++) {
+               u32 stat = nv_rd32(priv, 0x002640 + (engn * 0x04));
+               u32 busy = (stat & 0x80000000);
+               u32 save = (stat & 0x00100000); /* maybe? */
+               u32 unk0 = (stat & 0x00040000);
+               u32 unk1 = (stat & 0x00001000);
+               u32 chid = (stat & 0x0000007f);
+               (void)save;
+
+               if (busy && unk0 && unk1) {
+                       if (!(chan = (void *)priv->base.channel[chid]))
+                               continue;
+                       if (!(engine = gf100_fifo_engine(priv, engn)))
+                               continue;
+                       gf100_fifo_recover(priv, engine, chan);
+               }
+       }
+}
+
+static void
+gf100_fifo_intr_sched(struct gf100_fifo_priv *priv)
+{
+       u32 intr = nv_rd32(priv, 0x00254c);
+       u32 code = intr & 0x000000ff;
+       const struct nvkm_enum *en;
+       char enunk[6] = "";
+
+       en = nvkm_enum_find(gf100_fifo_sched_reason, code);
+       if (!en)
+               snprintf(enunk, sizeof(enunk), "UNK%02x", code);
+
+       nv_error(priv, "SCHED_ERROR [ %s ]\n", en ? en->name : enunk);
+
+       switch (code) {
+       case 0x0a:
+               gf100_fifo_intr_sched_ctxsw(priv);
+               break;
+       default:
+               break;
+       }
+}
+
+static const struct nvkm_enum
+gf100_fifo_fault_engine[] = {
+       { 0x00, "PGRAPH", NULL, NVDEV_ENGINE_GR },
+       { 0x03, "PEEPHOLE", NULL, NVDEV_ENGINE_IFB },
+       { 0x04, "BAR1", NULL, NVDEV_SUBDEV_BAR },
+       { 0x05, "BAR3", NULL, NVDEV_SUBDEV_INSTMEM },
+       { 0x07, "PFIFO", NULL, NVDEV_ENGINE_FIFO },
+       { 0x10, "PMSVLD", NULL, NVDEV_ENGINE_MSVLD },
+       { 0x11, "PMSPPP", NULL, NVDEV_ENGINE_MSPPP },
+       { 0x13, "PCOUNTER" },
+       { 0x14, "PMSPDEC", NULL, NVDEV_ENGINE_MSPDEC },
+       { 0x15, "PCE0", NULL, NVDEV_ENGINE_CE0 },
+       { 0x16, "PCE1", NULL, NVDEV_ENGINE_CE1 },
+       { 0x17, "PDAEMON" },
+       {}
+};
+
+static const struct nvkm_enum
+gf100_fifo_fault_reason[] = {
+       { 0x00, "PT_NOT_PRESENT" },
+       { 0x01, "PT_TOO_SHORT" },
+       { 0x02, "PAGE_NOT_PRESENT" },
+       { 0x03, "VM_LIMIT_EXCEEDED" },
+       { 0x04, "NO_CHANNEL" },
+       { 0x05, "PAGE_SYSTEM_ONLY" },
+       { 0x06, "PAGE_READ_ONLY" },
+       { 0x0a, "COMPRESSED_SYSRAM" },
+       { 0x0c, "INVALID_STORAGE_TYPE" },
+       {}
+};
+
+static const struct nvkm_enum
+gf100_fifo_fault_hubclient[] = {
+       { 0x01, "PCOPY0" },
+       { 0x02, "PCOPY1" },
+       { 0x04, "DISPATCH" },
+       { 0x05, "CTXCTL" },
+       { 0x06, "PFIFO" },
+       { 0x07, "BAR_READ" },
+       { 0x08, "BAR_WRITE" },
+       { 0x0b, "PVP" },
+       { 0x0c, "PMSPPP" },
+       { 0x0d, "PMSVLD" },
+       { 0x11, "PCOUNTER" },
+       { 0x12, "PDAEMON" },
+       { 0x14, "CCACHE" },
+       { 0x15, "CCACHE_POST" },
+       {}
+};
+
+static const struct nvkm_enum
+gf100_fifo_fault_gpcclient[] = {
+       { 0x01, "TEX" },
+       { 0x0c, "ESETUP" },
+       { 0x0e, "CTXCTL" },
+       { 0x0f, "PROP" },
+       {}
+};
+
+static void
+gf100_fifo_intr_fault(struct gf100_fifo_priv *priv, int unit)
+{
+       u32 inst = nv_rd32(priv, 0x002800 + (unit * 0x10));
+       u32 valo = nv_rd32(priv, 0x002804 + (unit * 0x10));
+       u32 vahi = nv_rd32(priv, 0x002808 + (unit * 0x10));
+       u32 stat = nv_rd32(priv, 0x00280c + (unit * 0x10));
+       u32 gpc    = (stat & 0x1f000000) >> 24;
+       u32 client = (stat & 0x00001f00) >> 8;
+       u32 write  = (stat & 0x00000080);
+       u32 hub    = (stat & 0x00000040);
+       u32 reason = (stat & 0x0000000f);
+       struct nvkm_object *engctx = NULL, *object;
+       struct nvkm_engine *engine = NULL;
+       const struct nvkm_enum *er, *eu, *ec;
+       char erunk[6] = "";
+       char euunk[6] = "";
+       char ecunk[6] = "";
+       char gpcid[3] = "";
+
+       er = nvkm_enum_find(gf100_fifo_fault_reason, reason);
+       if (!er)
+               snprintf(erunk, sizeof(erunk), "UNK%02X", reason);
+
+       eu = nvkm_enum_find(gf100_fifo_fault_engine, unit);
+       if (eu) {
+               switch (eu->data2) {
+               case NVDEV_SUBDEV_BAR:
+                       nv_mask(priv, 0x001704, 0x00000000, 0x00000000);
+                       break;
+               case NVDEV_SUBDEV_INSTMEM:
+                       nv_mask(priv, 0x001714, 0x00000000, 0x00000000);
+                       break;
+               case NVDEV_ENGINE_IFB:
+                       nv_mask(priv, 0x001718, 0x00000000, 0x00000000);
+                       break;
+               default:
+                       engine = nvkm_engine(priv, eu->data2);
+                       if (engine)
+                               engctx = nvkm_engctx_get(engine, inst);
+                       break;
+               }
+       } else {
+               snprintf(euunk, sizeof(euunk), "UNK%02x", unit);
+       }
+
+       if (hub) {
+               ec = nvkm_enum_find(gf100_fifo_fault_hubclient, client);
+       } else {
+               ec = nvkm_enum_find(gf100_fifo_fault_gpcclient, client);
+               snprintf(gpcid, sizeof(gpcid), "%d", gpc);
+       }
+
+       if (!ec)
+               snprintf(ecunk, sizeof(ecunk), "UNK%02x", client);
+
+       nv_error(priv, "%s fault at 0x%010llx [%s] from %s/%s%s%s%s on "
+                      "channel 0x%010llx [%s]\n", write ? "write" : "read",
+                (u64)vahi << 32 | valo, er ? er->name : erunk,
+                eu ? eu->name : euunk, hub ? "" : "GPC", gpcid, hub ? "" : "/",
+                ec ? ec->name : ecunk, (u64)inst << 12,
+                nvkm_client_name(engctx));
+
+       object = engctx;
+       while (object) {
+               switch (nv_mclass(object)) {
+               case FERMI_CHANNEL_GPFIFO:
+                       gf100_fifo_recover(priv, engine, (void *)object);
+                       break;
+               }
+               object = object->parent;
+       }
+
+       nvkm_engctx_put(engctx);
+}
+
+static const struct nvkm_bitfield
+gf100_fifo_pbdma_intr[] = {
+/*     { 0x00008000, "" }      seen with null ib push */
+       { 0x00200000, "ILLEGAL_MTHD" },
+       { 0x00800000, "EMPTY_SUBC" },
+       {}
+};
+
+static void
+gf100_fifo_intr_pbdma(struct gf100_fifo_priv *priv, int unit)
+{
+       u32 stat = nv_rd32(priv, 0x040108 + (unit * 0x2000));
+       u32 addr = nv_rd32(priv, 0x0400c0 + (unit * 0x2000));
+       u32 data = nv_rd32(priv, 0x0400c4 + (unit * 0x2000));
+       u32 chid = nv_rd32(priv, 0x040120 + (unit * 0x2000)) & 0x7f;
+       u32 subc = (addr & 0x00070000) >> 16;
+       u32 mthd = (addr & 0x00003ffc);
+       u32 show = stat;
+
+       if (stat & 0x00800000) {
+               if (!gf100_fifo_swmthd(priv, chid, mthd, data))
+                       show &= ~0x00800000;
+       }
+
+       if (show) {
+               nv_error(priv, "PBDMA%d:", unit);
+               nvkm_bitfield_print(gf100_fifo_pbdma_intr, show);
+               pr_cont("\n");
+               nv_error(priv,
+                        "PBDMA%d: ch %d [%s] subc %d mthd 0x%04x data 0x%08x\n",
+                        unit, chid,
+                        nvkm_client_name_for_fifo_chid(&priv->base, chid),
+                        subc, mthd, data);
+       }
+
+       nv_wr32(priv, 0x0400c0 + (unit * 0x2000), 0x80600008);
+       nv_wr32(priv, 0x040108 + (unit * 0x2000), stat);
+}
+
+static void
+gf100_fifo_intr_runlist(struct gf100_fifo_priv *priv)
+{
+       u32 intr = nv_rd32(priv, 0x002a00);
+
+       if (intr & 0x10000000) {
+               wake_up(&priv->runlist.wait);
+               nv_wr32(priv, 0x002a00, 0x10000000);
+               intr &= ~0x10000000;
+       }
+
+       if (intr) {
+               nv_error(priv, "RUNLIST 0x%08x\n", intr);
+               nv_wr32(priv, 0x002a00, intr);
+       }
+}
+
+static void
+gf100_fifo_intr_engine_unit(struct gf100_fifo_priv *priv, int engn)
+{
+       u32 intr = nv_rd32(priv, 0x0025a8 + (engn * 0x04));
+       u32 inte = nv_rd32(priv, 0x002628);
+       u32 unkn;
+
+       nv_wr32(priv, 0x0025a8 + (engn * 0x04), intr);
+
+       for (unkn = 0; unkn < 8; unkn++) {
+               u32 ints = (intr >> (unkn * 0x04)) & inte;
+               if (ints & 0x1) {
+                       nvkm_fifo_uevent(&priv->base);
+                       ints &= ~1;
+               }
+               if (ints) {
+                       nv_error(priv, "ENGINE %d %d %01x", engn, unkn, ints);
+                       nv_mask(priv, 0x002628, ints, 0);
+               }
+       }
+}
+
+static void
+gf100_fifo_intr_engine(struct gf100_fifo_priv *priv)
+{
+       u32 mask = nv_rd32(priv, 0x0025a4);
+       while (mask) {
+               u32 unit = __ffs(mask);
+               gf100_fifo_intr_engine_unit(priv, unit);
+               mask &= ~(1 << unit);
+       }
+}
+
+static void
+gf100_fifo_intr(struct nvkm_subdev *subdev)
+{
+       struct gf100_fifo_priv *priv = (void *)subdev;
+       u32 mask = nv_rd32(priv, 0x002140);
+       u32 stat = nv_rd32(priv, 0x002100) & mask;
+
+       if (stat & 0x00000001) {
+               u32 intr = nv_rd32(priv, 0x00252c);
+               nv_warn(priv, "INTR 0x00000001: 0x%08x\n", intr);
+               nv_wr32(priv, 0x002100, 0x00000001);
+               stat &= ~0x00000001;
+       }
+
+       if (stat & 0x00000100) {
+               gf100_fifo_intr_sched(priv);
+               nv_wr32(priv, 0x002100, 0x00000100);
+               stat &= ~0x00000100;
+       }
+
+       if (stat & 0x00010000) {
+               u32 intr = nv_rd32(priv, 0x00256c);
+               nv_warn(priv, "INTR 0x00010000: 0x%08x\n", intr);
+               nv_wr32(priv, 0x002100, 0x00010000);
+               stat &= ~0x00010000;
+       }
+
+       if (stat & 0x01000000) {
+               u32 intr = nv_rd32(priv, 0x00258c);
+               nv_warn(priv, "INTR 0x01000000: 0x%08x\n", intr);
+               nv_wr32(priv, 0x002100, 0x01000000);
+               stat &= ~0x01000000;
+       }
+
+       if (stat & 0x10000000) {
+               u32 mask = nv_rd32(priv, 0x00259c);
+               while (mask) {
+                       u32 unit = __ffs(mask);
+                       gf100_fifo_intr_fault(priv, unit);
+                       nv_wr32(priv, 0x00259c, (1 << unit));
+                       mask &= ~(1 << unit);
+               }
+               stat &= ~0x10000000;
+       }
+
+       if (stat & 0x20000000) {
+               u32 mask = nv_rd32(priv, 0x0025a0);
+               while (mask) {
+                       u32 unit = __ffs(mask);
+                       gf100_fifo_intr_pbdma(priv, unit);
+                       nv_wr32(priv, 0x0025a0, (1 << unit));
+                       mask &= ~(1 << unit);
+               }
+               stat &= ~0x20000000;
+       }
+
+       if (stat & 0x40000000) {
+               gf100_fifo_intr_runlist(priv);
+               stat &= ~0x40000000;
+       }
+
+       if (stat & 0x80000000) {
+               gf100_fifo_intr_engine(priv);
+               stat &= ~0x80000000;
+       }
+
+       if (stat) {
+               nv_error(priv, "INTR 0x%08x\n", stat);
+               nv_mask(priv, 0x002140, stat, 0x00000000);
+               nv_wr32(priv, 0x002100, stat);
+       }
+}
+
+static void
+gf100_fifo_uevent_init(struct nvkm_event *event, int type, int index)
+{
+       struct nvkm_fifo *fifo = container_of(event, typeof(*fifo), uevent);
+       nv_mask(fifo, 0x002140, 0x80000000, 0x80000000);
+}
+
+static void
+gf100_fifo_uevent_fini(struct nvkm_event *event, int type, int index)
+{
+       struct nvkm_fifo *fifo = container_of(event, typeof(*fifo), uevent);
+       nv_mask(fifo, 0x002140, 0x80000000, 0x00000000);
+}
+
+static const struct nvkm_event_func
+gf100_fifo_uevent_func = {
+       .ctor = nvkm_fifo_uevent_ctor,
+       .init = gf100_fifo_uevent_init,
+       .fini = gf100_fifo_uevent_fini,
+};
+
+static int
+gf100_fifo_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+               struct nvkm_oclass *oclass, void *data, u32 size,
+               struct nvkm_object **pobject)
+{
+       struct gf100_fifo_priv *priv;
+       int ret;
+
+       ret = nvkm_fifo_create(parent, engine, oclass, 0, 127, &priv);
+       *pobject = nv_object(priv);
+       if (ret)
+               return ret;
+
+       INIT_WORK(&priv->fault, gf100_fifo_recover_work);
+
+       ret = nvkm_gpuobj_new(nv_object(priv), NULL, 0x1000, 0x1000, 0,
+                             &priv->runlist.mem[0]);
+       if (ret)
+               return ret;
+
+       ret = nvkm_gpuobj_new(nv_object(priv), NULL, 0x1000, 0x1000, 0,
+                             &priv->runlist.mem[1]);
+       if (ret)
+               return ret;
+
+       init_waitqueue_head(&priv->runlist.wait);
+
+       ret = nvkm_gpuobj_new(nv_object(priv), NULL, 128 * 0x1000, 0x1000, 0,
+                             &priv->user.mem);
+       if (ret)
+               return ret;
+
+       ret = nvkm_gpuobj_map(priv->user.mem, NV_MEM_ACCESS_RW,
+                             &priv->user.bar);
+       if (ret)
+               return ret;
+
+       ret = nvkm_event_init(&gf100_fifo_uevent_func, 1, 1, &priv->base.uevent);
+       if (ret)
+               return ret;
+
+       nv_subdev(priv)->unit = 0x00000100;
+       nv_subdev(priv)->intr = gf100_fifo_intr;
+       nv_engine(priv)->cclass = &gf100_fifo_cclass;
+       nv_engine(priv)->sclass = gf100_fifo_sclass;
+       return 0;
+}
+
+static void
+gf100_fifo_dtor(struct nvkm_object *object)
+{
+       struct gf100_fifo_priv *priv = (void *)object;
+
+       nvkm_gpuobj_unmap(&priv->user.bar);
+       nvkm_gpuobj_ref(NULL, &priv->user.mem);
+       nvkm_gpuobj_ref(NULL, &priv->runlist.mem[0]);
+       nvkm_gpuobj_ref(NULL, &priv->runlist.mem[1]);
+
+       nvkm_fifo_destroy(&priv->base);
+}
+
+static int
+gf100_fifo_init(struct nvkm_object *object)
+{
+       struct gf100_fifo_priv *priv = (void *)object;
+       int ret, i;
+
+       ret = nvkm_fifo_init(&priv->base);
+       if (ret)
+               return ret;
+
+       nv_wr32(priv, 0x000204, 0xffffffff);
+       nv_wr32(priv, 0x002204, 0xffffffff);
+
+       priv->spoon_nr = hweight32(nv_rd32(priv, 0x002204));
+       nv_debug(priv, "%d PBDMA unit(s)\n", priv->spoon_nr);
+
+       /* assign engines to PBDMAs */
+       if (priv->spoon_nr >= 3) {
+               nv_wr32(priv, 0x002208, ~(1 << 0)); /* PGRAPH */
+               nv_wr32(priv, 0x00220c, ~(1 << 1)); /* PVP */
+               nv_wr32(priv, 0x002210, ~(1 << 1)); /* PMSPP */
+               nv_wr32(priv, 0x002214, ~(1 << 1)); /* PMSVLD */
+               nv_wr32(priv, 0x002218, ~(1 << 2)); /* PCE0 */
+               nv_wr32(priv, 0x00221c, ~(1 << 1)); /* PCE1 */
+       }
+
+       /* PBDMA[n] */
+       for (i = 0; i < priv->spoon_nr; i++) {
+               nv_mask(priv, 0x04013c + (i * 0x2000), 0x10000100, 0x00000000);
+               nv_wr32(priv, 0x040108 + (i * 0x2000), 0xffffffff); /* INTR */
+               nv_wr32(priv, 0x04010c + (i * 0x2000), 0xfffffeff); /* INTREN */
+       }
+
+       nv_mask(priv, 0x002200, 0x00000001, 0x00000001);
+       nv_wr32(priv, 0x002254, 0x10000000 | priv->user.bar.offset >> 12);
+
+       nv_wr32(priv, 0x002100, 0xffffffff);
+       nv_wr32(priv, 0x002140, 0x7fffffff);
+       nv_wr32(priv, 0x002628, 0x00000001); /* ENGINE_INTR_EN */
+       return 0;
+}
+
+struct nvkm_oclass *
+gf100_fifo_oclass = &(struct nvkm_oclass) {
+       .handle = NV_ENGINE(FIFO, 0xc0),
+       .ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = gf100_fifo_ctor,
+               .dtor = gf100_fifo_dtor,
+               .init = gf100_fifo_init,
+               .fini = _nvkm_fifo_fini,
+       },
+};
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/fifo/gk104.c b/drivers/gpu/drm/nouveau/nvkm/engine/fifo/gk104.c
new file mode 100644 (file)
index 0000000..9585539
--- /dev/null
@@ -0,0 +1,1138 @@
+/*
+ * Copyright 2012 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 "gk104.h"
+
+#include <core/client.h>
+#include <core/engctx.h>
+#include <core/enum.h>
+#include <core/handle.h>
+#include <subdev/bar.h>
+#include <subdev/fb.h>
+#include <subdev/mmu.h>
+#include <subdev/timer.h>
+
+#include <nvif/class.h>
+#include <nvif/unpack.h>
+
+#define _(a,b) { (a), ((1ULL << (a)) | (b)) }
+static const struct {
+       u64 subdev;
+       u64 mask;
+} fifo_engine[] = {
+       _(NVDEV_ENGINE_GR      , (1ULL << NVDEV_ENGINE_SW) |
+                                (1ULL << NVDEV_ENGINE_CE2)),
+       _(NVDEV_ENGINE_MSPDEC  , 0),
+       _(NVDEV_ENGINE_MSPPP   , 0),
+       _(NVDEV_ENGINE_MSVLD   , 0),
+       _(NVDEV_ENGINE_CE0     , 0),
+       _(NVDEV_ENGINE_CE1     , 0),
+       _(NVDEV_ENGINE_MSENC   , 0),
+};
+#undef _
+#define FIFO_ENGINE_NR ARRAY_SIZE(fifo_engine)
+
+struct gk104_fifo_engn {
+       struct nvkm_gpuobj *runlist[2];
+       int cur_runlist;
+       wait_queue_head_t wait;
+};
+
+struct gk104_fifo_priv {
+       struct nvkm_fifo base;
+
+       struct work_struct fault;
+       u64 mask;
+
+       struct gk104_fifo_engn engine[FIFO_ENGINE_NR];
+       struct {
+               struct nvkm_gpuobj *mem;
+               struct nvkm_vma bar;
+       } user;
+       int spoon_nr;
+};
+
+struct gk104_fifo_base {
+       struct nvkm_fifo_base base;
+       struct nvkm_gpuobj *pgd;
+       struct nvkm_vm *vm;
+};
+
+struct gk104_fifo_chan {
+       struct nvkm_fifo_chan base;
+       u32 engine;
+       enum {
+               STOPPED,
+               RUNNING,
+               KILLED
+       } state;
+};
+
+/*******************************************************************************
+ * FIFO channel objects
+ ******************************************************************************/
+
+static void
+gk104_fifo_runlist_update(struct gk104_fifo_priv *priv, u32 engine)
+{
+       struct nvkm_bar *bar = nvkm_bar(priv);
+       struct gk104_fifo_engn *engn = &priv->engine[engine];
+       struct nvkm_gpuobj *cur;
+       int i, p;
+
+       mutex_lock(&nv_subdev(priv)->mutex);
+       cur = engn->runlist[engn->cur_runlist];
+       engn->cur_runlist = !engn->cur_runlist;
+
+       for (i = 0, p = 0; i < priv->base.max; i++) {
+               struct gk104_fifo_chan *chan = (void *)priv->base.channel[i];
+               if (chan && chan->state == RUNNING && chan->engine == engine) {
+                       nv_wo32(cur, p + 0, i);
+                       nv_wo32(cur, p + 4, 0x00000000);
+                       p += 8;
+               }
+       }
+       bar->flush(bar);
+
+       nv_wr32(priv, 0x002270, cur->addr >> 12);
+       nv_wr32(priv, 0x002274, (engine << 20) | (p >> 3));
+
+       if (wait_event_timeout(engn->wait, !(nv_rd32(priv, 0x002284 +
+                              (engine * 0x08)) & 0x00100000),
+                               msecs_to_jiffies(2000)) == 0)
+               nv_error(priv, "runlist %d update timeout\n", engine);
+       mutex_unlock(&nv_subdev(priv)->mutex);
+}
+
+static int
+gk104_fifo_context_attach(struct nvkm_object *parent,
+                         struct nvkm_object *object)
+{
+       struct nvkm_bar *bar = nvkm_bar(parent);
+       struct gk104_fifo_base *base = (void *)parent->parent;
+       struct nvkm_engctx *ectx = (void *)object;
+       u32 addr;
+       int ret;
+
+       switch (nv_engidx(object->engine)) {
+       case NVDEV_ENGINE_SW   :
+               return 0;
+       case NVDEV_ENGINE_CE0:
+       case NVDEV_ENGINE_CE1:
+       case NVDEV_ENGINE_CE2:
+               nv_engctx(ectx)->addr = nv_gpuobj(base)->addr >> 12;
+               return 0;
+       case NVDEV_ENGINE_GR    : addr = 0x0210; break;
+       case NVDEV_ENGINE_MSVLD : addr = 0x0270; break;
+       case NVDEV_ENGINE_MSPDEC: addr = 0x0250; break;
+       case NVDEV_ENGINE_MSPPP : addr = 0x0260; break;
+       default:
+               return -EINVAL;
+       }
+
+       if (!ectx->vma.node) {
+               ret = nvkm_gpuobj_map_vm(nv_gpuobj(ectx), base->vm,
+                                        NV_MEM_ACCESS_RW, &ectx->vma);
+               if (ret)
+                       return ret;
+
+               nv_engctx(ectx)->addr = nv_gpuobj(base)->addr >> 12;
+       }
+
+       nv_wo32(base, addr + 0x00, lower_32_bits(ectx->vma.offset) | 4);
+       nv_wo32(base, addr + 0x04, upper_32_bits(ectx->vma.offset));
+       bar->flush(bar);
+       return 0;
+}
+
+static int
+gk104_fifo_context_detach(struct nvkm_object *parent, bool suspend,
+                         struct nvkm_object *object)
+{
+       struct nvkm_bar *bar = nvkm_bar(parent);
+       struct gk104_fifo_priv *priv = (void *)parent->engine;
+       struct gk104_fifo_base *base = (void *)parent->parent;
+       struct gk104_fifo_chan *chan = (void *)parent;
+       u32 addr;
+
+       switch (nv_engidx(object->engine)) {
+       case NVDEV_ENGINE_SW    : return 0;
+       case NVDEV_ENGINE_CE0   :
+       case NVDEV_ENGINE_CE1   :
+       case NVDEV_ENGINE_CE2   : addr = 0x0000; break;
+       case NVDEV_ENGINE_GR    : addr = 0x0210; break;
+       case NVDEV_ENGINE_MSVLD : addr = 0x0270; break;
+       case NVDEV_ENGINE_MSPDEC: addr = 0x0250; break;
+       case NVDEV_ENGINE_MSPPP : addr = 0x0260; break;
+       default:
+               return -EINVAL;
+       }
+
+       nv_wr32(priv, 0x002634, chan->base.chid);
+       if (!nv_wait(priv, 0x002634, 0xffffffff, chan->base.chid)) {
+               nv_error(priv, "channel %d [%s] kick timeout\n",
+                        chan->base.chid, nvkm_client_name(chan));
+               if (suspend)
+                       return -EBUSY;
+       }
+
+       if (addr) {
+               nv_wo32(base, addr + 0x00, 0x00000000);
+               nv_wo32(base, addr + 0x04, 0x00000000);
+               bar->flush(bar);
+       }
+
+       return 0;
+}
+
+static int
+gk104_fifo_chan_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+                    struct nvkm_oclass *oclass, void *data, u32 size,
+                    struct nvkm_object **pobject)
+{
+       union {
+               struct kepler_channel_gpfifo_a_v0 v0;
+       } *args = data;
+       struct nvkm_bar *bar = nvkm_bar(parent);
+       struct gk104_fifo_priv *priv = (void *)engine;
+       struct gk104_fifo_base *base = (void *)parent;
+       struct gk104_fifo_chan *chan;
+       u64 usermem, ioffset, ilength;
+       int ret, i;
+
+       nv_ioctl(parent, "create channel gpfifo size %d\n", size);
+       if (nvif_unpack(args->v0, 0, 0, false)) {
+               nv_ioctl(parent, "create channel gpfifo vers %d pushbuf %08x "
+                                "ioffset %016llx ilength %08x engine %08x\n",
+                        args->v0.version, args->v0.pushbuf, args->v0.ioffset,
+                        args->v0.ilength, args->v0.engine);
+       } else
+               return ret;
+
+       for (i = 0; i < FIFO_ENGINE_NR; i++) {
+               if (args->v0.engine & (1 << i)) {
+                       if (nvkm_engine(parent, fifo_engine[i].subdev)) {
+                               args->v0.engine = (1 << i);
+                               break;
+                       }
+               }
+       }
+
+       if (i == FIFO_ENGINE_NR) {
+               nv_error(priv, "unsupported engines 0x%08x\n", args->v0.engine);
+               return -ENODEV;
+       }
+
+       ret = nvkm_fifo_channel_create(parent, engine, oclass, 1,
+                                      priv->user.bar.offset, 0x200,
+                                      args->v0.pushbuf,
+                                      fifo_engine[i].mask, &chan);
+       *pobject = nv_object(chan);
+       if (ret)
+               return ret;
+
+       args->v0.chid = chan->base.chid;
+
+       nv_parent(chan)->context_attach = gk104_fifo_context_attach;
+       nv_parent(chan)->context_detach = gk104_fifo_context_detach;
+       chan->engine = i;
+
+       usermem = chan->base.chid * 0x200;
+       ioffset = args->v0.ioffset;
+       ilength = order_base_2(args->v0.ilength / 8);
+
+       for (i = 0; i < 0x200; i += 4)
+               nv_wo32(priv->user.mem, usermem + i, 0x00000000);
+
+       nv_wo32(base, 0x08, lower_32_bits(priv->user.mem->addr + usermem));
+       nv_wo32(base, 0x0c, upper_32_bits(priv->user.mem->addr + usermem));
+       nv_wo32(base, 0x10, 0x0000face);
+       nv_wo32(base, 0x30, 0xfffff902);
+       nv_wo32(base, 0x48, lower_32_bits(ioffset));
+       nv_wo32(base, 0x4c, upper_32_bits(ioffset) | (ilength << 16));
+       nv_wo32(base, 0x84, 0x20400000);
+       nv_wo32(base, 0x94, 0x30000001);
+       nv_wo32(base, 0x9c, 0x00000100);
+       nv_wo32(base, 0xac, 0x0000001f);
+       nv_wo32(base, 0xe8, chan->base.chid);
+       nv_wo32(base, 0xb8, 0xf8000000);
+       nv_wo32(base, 0xf8, 0x10003080); /* 0x002310 */
+       nv_wo32(base, 0xfc, 0x10000010); /* 0x002350 */
+       bar->flush(bar);
+       return 0;
+}
+
+static int
+gk104_fifo_chan_init(struct nvkm_object *object)
+{
+       struct nvkm_gpuobj *base = nv_gpuobj(object->parent);
+       struct gk104_fifo_priv *priv = (void *)object->engine;
+       struct gk104_fifo_chan *chan = (void *)object;
+       u32 chid = chan->base.chid;
+       int ret;
+
+       ret = nvkm_fifo_channel_init(&chan->base);
+       if (ret)
+               return ret;
+
+       nv_mask(priv, 0x800004 + (chid * 8), 0x000f0000, chan->engine << 16);
+       nv_wr32(priv, 0x800000 + (chid * 8), 0x80000000 | base->addr >> 12);
+
+       if (chan->state == STOPPED && (chan->state = RUNNING) == RUNNING) {
+               nv_mask(priv, 0x800004 + (chid * 8), 0x00000400, 0x00000400);
+               gk104_fifo_runlist_update(priv, chan->engine);
+               nv_mask(priv, 0x800004 + (chid * 8), 0x00000400, 0x00000400);
+       }
+
+       return 0;
+}
+
+static int
+gk104_fifo_chan_fini(struct nvkm_object *object, bool suspend)
+{
+       struct gk104_fifo_priv *priv = (void *)object->engine;
+       struct gk104_fifo_chan *chan = (void *)object;
+       u32 chid = chan->base.chid;
+
+       if (chan->state == RUNNING && (chan->state = STOPPED) == STOPPED) {
+               nv_mask(priv, 0x800004 + (chid * 8), 0x00000800, 0x00000800);
+               gk104_fifo_runlist_update(priv, chan->engine);
+       }
+
+       nv_wr32(priv, 0x800000 + (chid * 8), 0x00000000);
+       return nvkm_fifo_channel_fini(&chan->base, suspend);
+}
+
+static struct nvkm_ofuncs
+gk104_fifo_ofuncs = {
+       .ctor = gk104_fifo_chan_ctor,
+       .dtor = _nvkm_fifo_channel_dtor,
+       .init = gk104_fifo_chan_init,
+       .fini = gk104_fifo_chan_fini,
+       .map  = _nvkm_fifo_channel_map,
+       .rd32 = _nvkm_fifo_channel_rd32,
+       .wr32 = _nvkm_fifo_channel_wr32,
+       .ntfy = _nvkm_fifo_channel_ntfy
+};
+
+static struct nvkm_oclass
+gk104_fifo_sclass[] = {
+       { KEPLER_CHANNEL_GPFIFO_A, &gk104_fifo_ofuncs },
+       {}
+};
+
+/*******************************************************************************
+ * FIFO context - instmem heap and vm setup
+ ******************************************************************************/
+
+static int
+gk104_fifo_context_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+                       struct nvkm_oclass *oclass, void *data, u32 size,
+                       struct nvkm_object **pobject)
+{
+       struct gk104_fifo_base *base;
+       int ret;
+
+       ret = nvkm_fifo_context_create(parent, engine, oclass, NULL, 0x1000,
+                                      0x1000, NVOBJ_FLAG_ZERO_ALLOC, &base);
+       *pobject = nv_object(base);
+       if (ret)
+               return ret;
+
+       ret = nvkm_gpuobj_new(nv_object(base), NULL, 0x10000, 0x1000, 0,
+                             &base->pgd);
+       if (ret)
+               return ret;
+
+       nv_wo32(base, 0x0200, lower_32_bits(base->pgd->addr));
+       nv_wo32(base, 0x0204, upper_32_bits(base->pgd->addr));
+       nv_wo32(base, 0x0208, 0xffffffff);
+       nv_wo32(base, 0x020c, 0x000000ff);
+
+       ret = nvkm_vm_ref(nvkm_client(parent)->vm, &base->vm, base->pgd);
+       if (ret)
+               return ret;
+
+       return 0;
+}
+
+static void
+gk104_fifo_context_dtor(struct nvkm_object *object)
+{
+       struct gk104_fifo_base *base = (void *)object;
+       nvkm_vm_ref(NULL, &base->vm, base->pgd);
+       nvkm_gpuobj_ref(NULL, &base->pgd);
+       nvkm_fifo_context_destroy(&base->base);
+}
+
+static struct nvkm_oclass
+gk104_fifo_cclass = {
+       .handle = NV_ENGCTX(FIFO, 0xe0),
+       .ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = gk104_fifo_context_ctor,
+               .dtor = gk104_fifo_context_dtor,
+               .init = _nvkm_fifo_context_init,
+               .fini = _nvkm_fifo_context_fini,
+               .rd32 = _nvkm_fifo_context_rd32,
+               .wr32 = _nvkm_fifo_context_wr32,
+       },
+};
+
+/*******************************************************************************
+ * PFIFO engine
+ ******************************************************************************/
+
+static inline int
+gk104_fifo_engidx(struct gk104_fifo_priv *priv, u32 engn)
+{
+       switch (engn) {
+       case NVDEV_ENGINE_GR    :
+       case NVDEV_ENGINE_CE2   : engn = 0; break;
+       case NVDEV_ENGINE_MSVLD : engn = 1; break;
+       case NVDEV_ENGINE_MSPPP : engn = 2; break;
+       case NVDEV_ENGINE_MSPDEC: engn = 3; break;
+       case NVDEV_ENGINE_CE0   : engn = 4; break;
+       case NVDEV_ENGINE_CE1   : engn = 5; break;
+       case NVDEV_ENGINE_MSENC : engn = 6; break;
+       default:
+               return -1;
+       }
+
+       return engn;
+}
+
+static inline struct nvkm_engine *
+gk104_fifo_engine(struct gk104_fifo_priv *priv, u32 engn)
+{
+       if (engn >= ARRAY_SIZE(fifo_engine))
+               return NULL;
+       return nvkm_engine(priv, fifo_engine[engn].subdev);
+}
+
+static void
+gk104_fifo_recover_work(struct work_struct *work)
+{
+       struct gk104_fifo_priv *priv = container_of(work, typeof(*priv), fault);
+       struct nvkm_object *engine;
+       unsigned long flags;
+       u32 engn, engm = 0;
+       u64 mask, todo;
+
+       spin_lock_irqsave(&priv->base.lock, flags);
+       mask = priv->mask;
+       priv->mask = 0ULL;
+       spin_unlock_irqrestore(&priv->base.lock, flags);
+
+       for (todo = mask; engn = __ffs64(todo), todo; todo &= ~(1 << engn))
+               engm |= 1 << gk104_fifo_engidx(priv, engn);
+       nv_mask(priv, 0x002630, engm, engm);
+
+       for (todo = mask; engn = __ffs64(todo), todo; todo &= ~(1 << engn)) {
+               if ((engine = (void *)nvkm_engine(priv, engn))) {
+                       nv_ofuncs(engine)->fini(engine, false);
+                       WARN_ON(nv_ofuncs(engine)->init(engine));
+               }
+               gk104_fifo_runlist_update(priv, gk104_fifo_engidx(priv, engn));
+       }
+
+       nv_wr32(priv, 0x00262c, engm);
+       nv_mask(priv, 0x002630, engm, 0x00000000);
+}
+
+static void
+gk104_fifo_recover(struct gk104_fifo_priv *priv, struct nvkm_engine *engine,
+                 struct gk104_fifo_chan *chan)
+{
+       u32 chid = chan->base.chid;
+       unsigned long flags;
+
+       nv_error(priv, "%s engine fault on channel %d, recovering...\n",
+                      nv_subdev(engine)->name, chid);
+
+       nv_mask(priv, 0x800004 + (chid * 0x08), 0x00000800, 0x00000800);
+       chan->state = KILLED;
+
+       spin_lock_irqsave(&priv->base.lock, flags);
+       priv->mask |= 1ULL << nv_engidx(engine);
+       spin_unlock_irqrestore(&priv->base.lock, flags);
+       schedule_work(&priv->fault);
+}
+
+static int
+gk104_fifo_swmthd(struct gk104_fifo_priv *priv, u32 chid, u32 mthd, u32 data)
+{
+       struct gk104_fifo_chan *chan = NULL;
+       struct nvkm_handle *bind;
+       unsigned long flags;
+       int ret = -EINVAL;
+
+       spin_lock_irqsave(&priv->base.lock, flags);
+       if (likely(chid >= priv->base.min && chid <= priv->base.max))
+               chan = (void *)priv->base.channel[chid];
+       if (unlikely(!chan))
+               goto out;
+
+       bind = nvkm_namedb_get_class(nv_namedb(chan), 0x906e);
+       if (likely(bind)) {
+               if (!mthd || !nv_call(bind->object, mthd, data))
+                       ret = 0;
+               nvkm_namedb_put(bind);
+       }
+
+out:
+       spin_unlock_irqrestore(&priv->base.lock, flags);
+       return ret;
+}
+
+static const struct nvkm_enum
+gk104_fifo_bind_reason[] = {
+       { 0x01, "BIND_NOT_UNBOUND" },
+       { 0x02, "SNOOP_WITHOUT_BAR1" },
+       { 0x03, "UNBIND_WHILE_RUNNING" },
+       { 0x05, "INVALID_RUNLIST" },
+       { 0x06, "INVALID_CTX_TGT" },
+       { 0x0b, "UNBIND_WHILE_PARKED" },
+       {}
+};
+
+static void
+gk104_fifo_intr_bind(struct gk104_fifo_priv *priv)
+{
+       u32 intr = nv_rd32(priv, 0x00252c);
+       u32 code = intr & 0x000000ff;
+       const struct nvkm_enum *en;
+       char enunk[6] = "";
+
+       en = nvkm_enum_find(gk104_fifo_bind_reason, code);
+       if (!en)
+               snprintf(enunk, sizeof(enunk), "UNK%02x", code);
+
+       nv_error(priv, "BIND_ERROR [ %s ]\n", en ? en->name : enunk);
+}
+
+static const struct nvkm_enum
+gk104_fifo_sched_reason[] = {
+       { 0x0a, "CTXSW_TIMEOUT" },
+       {}
+};
+
+static void
+gk104_fifo_intr_sched_ctxsw(struct gk104_fifo_priv *priv)
+{
+       struct nvkm_engine *engine;
+       struct gk104_fifo_chan *chan;
+       u32 engn;
+
+       for (engn = 0; engn < ARRAY_SIZE(fifo_engine); engn++) {
+               u32 stat = nv_rd32(priv, 0x002640 + (engn * 0x04));
+               u32 busy = (stat & 0x80000000);
+               u32 next = (stat & 0x07ff0000) >> 16;
+               u32 chsw = (stat & 0x00008000);
+               u32 save = (stat & 0x00004000);
+               u32 load = (stat & 0x00002000);
+               u32 prev = (stat & 0x000007ff);
+               u32 chid = load ? next : prev;
+               (void)save;
+
+               if (busy && chsw) {
+                       if (!(chan = (void *)priv->base.channel[chid]))
+                               continue;
+                       if (!(engine = gk104_fifo_engine(priv, engn)))
+                               continue;
+                       gk104_fifo_recover(priv, engine, chan);
+               }
+       }
+}
+
+static void
+gk104_fifo_intr_sched(struct gk104_fifo_priv *priv)
+{
+       u32 intr = nv_rd32(priv, 0x00254c);
+       u32 code = intr & 0x000000ff;
+       const struct nvkm_enum *en;
+       char enunk[6] = "";
+
+       en = nvkm_enum_find(gk104_fifo_sched_reason, code);
+       if (!en)
+               snprintf(enunk, sizeof(enunk), "UNK%02x", code);
+
+       nv_error(priv, "SCHED_ERROR [ %s ]\n", en ? en->name : enunk);
+
+       switch (code) {
+       case 0x0a:
+               gk104_fifo_intr_sched_ctxsw(priv);
+               break;
+       default:
+               break;
+       }
+}
+
+static void
+gk104_fifo_intr_chsw(struct gk104_fifo_priv *priv)
+{
+       u32 stat = nv_rd32(priv, 0x00256c);
+       nv_error(priv, "CHSW_ERROR 0x%08x\n", stat);
+       nv_wr32(priv, 0x00256c, stat);
+}
+
+static void
+gk104_fifo_intr_dropped_fault(struct gk104_fifo_priv *priv)
+{
+       u32 stat = nv_rd32(priv, 0x00259c);
+       nv_error(priv, "DROPPED_MMU_FAULT 0x%08x\n", stat);
+}
+
+static const struct nvkm_enum
+gk104_fifo_fault_engine[] = {
+       { 0x00, "GR", NULL, NVDEV_ENGINE_GR },
+       { 0x03, "IFB", NULL, NVDEV_ENGINE_IFB },
+       { 0x04, "BAR1", NULL, NVDEV_SUBDEV_BAR },
+       { 0x05, "BAR3", NULL, NVDEV_SUBDEV_INSTMEM },
+       { 0x07, "PBDMA0", NULL, NVDEV_ENGINE_FIFO },
+       { 0x08, "PBDMA1", NULL, NVDEV_ENGINE_FIFO },
+       { 0x09, "PBDMA2", NULL, NVDEV_ENGINE_FIFO },
+       { 0x10, "MSVLD", NULL, NVDEV_ENGINE_MSVLD },
+       { 0x11, "MSPPP", NULL, NVDEV_ENGINE_MSPPP },
+       { 0x13, "PERF" },
+       { 0x14, "MSPDEC", NULL, NVDEV_ENGINE_MSPDEC },
+       { 0x15, "CE0", NULL, NVDEV_ENGINE_CE0 },
+       { 0x16, "CE1", NULL, NVDEV_ENGINE_CE1 },
+       { 0x17, "PMU" },
+       { 0x19, "MSENC", NULL, NVDEV_ENGINE_MSENC },
+       { 0x1b, "CE2", NULL, NVDEV_ENGINE_CE2 },
+       {}
+};
+
+static const struct nvkm_enum
+gk104_fifo_fault_reason[] = {
+       { 0x00, "PDE" },
+       { 0x01, "PDE_SIZE" },
+       { 0x02, "PTE" },
+       { 0x03, "VA_LIMIT_VIOLATION" },
+       { 0x04, "UNBOUND_INST_BLOCK" },
+       { 0x05, "PRIV_VIOLATION" },
+       { 0x06, "RO_VIOLATION" },
+       { 0x07, "WO_VIOLATION" },
+       { 0x08, "PITCH_MASK_VIOLATION" },
+       { 0x09, "WORK_CREATION" },
+       { 0x0a, "UNSUPPORTED_APERTURE" },
+       { 0x0b, "COMPRESSION_FAILURE" },
+       { 0x0c, "UNSUPPORTED_KIND" },
+       { 0x0d, "REGION_VIOLATION" },
+       { 0x0e, "BOTH_PTES_VALID" },
+       { 0x0f, "INFO_TYPE_POISONED" },
+       {}
+};
+
+static const struct nvkm_enum
+gk104_fifo_fault_hubclient[] = {
+       { 0x00, "VIP" },
+       { 0x01, "CE0" },
+       { 0x02, "CE1" },
+       { 0x03, "DNISO" },
+       { 0x04, "FE" },
+       { 0x05, "FECS" },
+       { 0x06, "HOST" },
+       { 0x07, "HOST_CPU" },
+       { 0x08, "HOST_CPU_NB" },
+       { 0x09, "ISO" },
+       { 0x0a, "MMU" },
+       { 0x0b, "MSPDEC" },
+       { 0x0c, "MSPPP" },
+       { 0x0d, "MSVLD" },
+       { 0x0e, "NISO" },
+       { 0x0f, "P2P" },
+       { 0x10, "PD" },
+       { 0x11, "PERF" },
+       { 0x12, "PMU" },
+       { 0x13, "RASTERTWOD" },
+       { 0x14, "SCC" },
+       { 0x15, "SCC_NB" },
+       { 0x16, "SEC" },
+       { 0x17, "SSYNC" },
+       { 0x18, "GR_CE" },
+       { 0x19, "CE2" },
+       { 0x1a, "XV" },
+       { 0x1b, "MMU_NB" },
+       { 0x1c, "MSENC" },
+       { 0x1d, "DFALCON" },
+       { 0x1e, "SKED" },
+       { 0x1f, "AFALCON" },
+       {}
+};
+
+static const struct nvkm_enum
+gk104_fifo_fault_gpcclient[] = {
+       { 0x00, "L1_0" }, { 0x01, "T1_0" }, { 0x02, "PE_0" },
+       { 0x03, "L1_1" }, { 0x04, "T1_1" }, { 0x05, "PE_1" },
+       { 0x06, "L1_2" }, { 0x07, "T1_2" }, { 0x08, "PE_2" },
+       { 0x09, "L1_3" }, { 0x0a, "T1_3" }, { 0x0b, "PE_3" },
+       { 0x0c, "RAST" },
+       { 0x0d, "GCC" },
+       { 0x0e, "GPCCS" },
+       { 0x0f, "PROP_0" },
+       { 0x10, "PROP_1" },
+       { 0x11, "PROP_2" },
+       { 0x12, "PROP_3" },
+       { 0x13, "L1_4" }, { 0x14, "T1_4" }, { 0x15, "PE_4" },
+       { 0x16, "L1_5" }, { 0x17, "T1_5" }, { 0x18, "PE_5" },
+       { 0x19, "L1_6" }, { 0x1a, "T1_6" }, { 0x1b, "PE_6" },
+       { 0x1c, "L1_7" }, { 0x1d, "T1_7" }, { 0x1e, "PE_7" },
+       { 0x1f, "GPM" },
+       { 0x20, "LTP_UTLB_0" },
+       { 0x21, "LTP_UTLB_1" },
+       { 0x22, "LTP_UTLB_2" },
+       { 0x23, "LTP_UTLB_3" },
+       { 0x24, "GPC_RGG_UTLB" },
+       {}
+};
+
+static void
+gk104_fifo_intr_fault(struct gk104_fifo_priv *priv, int unit)
+{
+       u32 inst = nv_rd32(priv, 0x002800 + (unit * 0x10));
+       u32 valo = nv_rd32(priv, 0x002804 + (unit * 0x10));
+       u32 vahi = nv_rd32(priv, 0x002808 + (unit * 0x10));
+       u32 stat = nv_rd32(priv, 0x00280c + (unit * 0x10));
+       u32 gpc    = (stat & 0x1f000000) >> 24;
+       u32 client = (stat & 0x00001f00) >> 8;
+       u32 write  = (stat & 0x00000080);
+       u32 hub    = (stat & 0x00000040);
+       u32 reason = (stat & 0x0000000f);
+       struct nvkm_object *engctx = NULL, *object;
+       struct nvkm_engine *engine = NULL;
+       const struct nvkm_enum *er, *eu, *ec;
+       char erunk[6] = "";
+       char euunk[6] = "";
+       char ecunk[6] = "";
+       char gpcid[3] = "";
+
+       er = nvkm_enum_find(gk104_fifo_fault_reason, reason);
+       if (!er)
+               snprintf(erunk, sizeof(erunk), "UNK%02X", reason);
+
+       eu = nvkm_enum_find(gk104_fifo_fault_engine, unit);
+       if (eu) {
+               switch (eu->data2) {
+               case NVDEV_SUBDEV_BAR:
+                       nv_mask(priv, 0x001704, 0x00000000, 0x00000000);
+                       break;
+               case NVDEV_SUBDEV_INSTMEM:
+                       nv_mask(priv, 0x001714, 0x00000000, 0x00000000);
+                       break;
+               case NVDEV_ENGINE_IFB:
+                       nv_mask(priv, 0x001718, 0x00000000, 0x00000000);
+                       break;
+               default:
+                       engine = nvkm_engine(priv, eu->data2);
+                       if (engine)
+                               engctx = nvkm_engctx_get(engine, inst);
+                       break;
+               }
+       } else {
+               snprintf(euunk, sizeof(euunk), "UNK%02x", unit);
+       }
+
+       if (hub) {
+               ec = nvkm_enum_find(gk104_fifo_fault_hubclient, client);
+       } else {
+               ec = nvkm_enum_find(gk104_fifo_fault_gpcclient, client);
+               snprintf(gpcid, sizeof(gpcid), "%d", gpc);
+       }
+
+       if (!ec)
+               snprintf(ecunk, sizeof(ecunk), "UNK%02x", client);
+
+       nv_error(priv, "%s fault at 0x%010llx [%s] from %s/%s%s%s%s on "
+                      "channel 0x%010llx [%s]\n", write ? "write" : "read",
+                (u64)vahi << 32 | valo, er ? er->name : erunk,
+                eu ? eu->name : euunk, hub ? "" : "GPC", gpcid, hub ? "" : "/",
+                ec ? ec->name : ecunk, (u64)inst << 12,
+                nvkm_client_name(engctx));
+
+       object = engctx;
+       while (object) {
+               switch (nv_mclass(object)) {
+               case KEPLER_CHANNEL_GPFIFO_A:
+                       gk104_fifo_recover(priv, engine, (void *)object);
+                       break;
+               }
+               object = object->parent;
+       }
+
+       nvkm_engctx_put(engctx);
+}
+
+static const struct nvkm_bitfield gk104_fifo_pbdma_intr_0[] = {
+       { 0x00000001, "MEMREQ" },
+       { 0x00000002, "MEMACK_TIMEOUT" },
+       { 0x00000004, "MEMACK_EXTRA" },
+       { 0x00000008, "MEMDAT_TIMEOUT" },
+       { 0x00000010, "MEMDAT_EXTRA" },
+       { 0x00000020, "MEMFLUSH" },
+       { 0x00000040, "MEMOP" },
+       { 0x00000080, "LBCONNECT" },
+       { 0x00000100, "LBREQ" },
+       { 0x00000200, "LBACK_TIMEOUT" },
+       { 0x00000400, "LBACK_EXTRA" },
+       { 0x00000800, "LBDAT_TIMEOUT" },
+       { 0x00001000, "LBDAT_EXTRA" },
+       { 0x00002000, "GPFIFO" },
+       { 0x00004000, "GPPTR" },
+       { 0x00008000, "GPENTRY" },
+       { 0x00010000, "GPCRC" },
+       { 0x00020000, "PBPTR" },
+       { 0x00040000, "PBENTRY" },
+       { 0x00080000, "PBCRC" },
+       { 0x00100000, "XBARCONNECT" },
+       { 0x00200000, "METHOD" },
+       { 0x00400000, "METHODCRC" },
+       { 0x00800000, "DEVICE" },
+       { 0x02000000, "SEMAPHORE" },
+       { 0x04000000, "ACQUIRE" },
+       { 0x08000000, "PRI" },
+       { 0x20000000, "NO_CTXSW_SEG" },
+       { 0x40000000, "PBSEG" },
+       { 0x80000000, "SIGNATURE" },
+       {}
+};
+
+static void
+gk104_fifo_intr_pbdma_0(struct gk104_fifo_priv *priv, int unit)
+{
+       u32 mask = nv_rd32(priv, 0x04010c + (unit * 0x2000));
+       u32 stat = nv_rd32(priv, 0x040108 + (unit * 0x2000)) & mask;
+       u32 addr = nv_rd32(priv, 0x0400c0 + (unit * 0x2000));
+       u32 data = nv_rd32(priv, 0x0400c4 + (unit * 0x2000));
+       u32 chid = nv_rd32(priv, 0x040120 + (unit * 0x2000)) & 0xfff;
+       u32 subc = (addr & 0x00070000) >> 16;
+       u32 mthd = (addr & 0x00003ffc);
+       u32 show = stat;
+
+       if (stat & 0x00800000) {
+               if (!gk104_fifo_swmthd(priv, chid, mthd, data))
+                       show &= ~0x00800000;
+               nv_wr32(priv, 0x0400c0 + (unit * 0x2000), 0x80600008);
+       }
+
+       if (show) {
+               nv_error(priv, "PBDMA%d:", unit);
+               nvkm_bitfield_print(gk104_fifo_pbdma_intr_0, show);
+               pr_cont("\n");
+               nv_error(priv,
+                        "PBDMA%d: ch %d [%s] subc %d mthd 0x%04x data 0x%08x\n",
+                        unit, chid,
+                        nvkm_client_name_for_fifo_chid(&priv->base, chid),
+                        subc, mthd, data);
+       }
+
+       nv_wr32(priv, 0x040108 + (unit * 0x2000), stat);
+}
+
+static const struct nvkm_bitfield gk104_fifo_pbdma_intr_1[] = {
+       { 0x00000001, "HCE_RE_ILLEGAL_OP" },
+       { 0x00000002, "HCE_RE_ALIGNB" },
+       { 0x00000004, "HCE_PRIV" },
+       { 0x00000008, "HCE_ILLEGAL_MTHD" },
+       { 0x00000010, "HCE_ILLEGAL_CLASS" },
+       {}
+};
+
+static void
+gk104_fifo_intr_pbdma_1(struct gk104_fifo_priv *priv, int unit)
+{
+       u32 mask = nv_rd32(priv, 0x04014c + (unit * 0x2000));
+       u32 stat = nv_rd32(priv, 0x040148 + (unit * 0x2000)) & mask;
+       u32 chid = nv_rd32(priv, 0x040120 + (unit * 0x2000)) & 0xfff;
+
+       if (stat) {
+               nv_error(priv, "PBDMA%d:", unit);
+               nvkm_bitfield_print(gk104_fifo_pbdma_intr_1, stat);
+               pr_cont("\n");
+               nv_error(priv, "PBDMA%d: ch %d %08x %08x\n", unit, chid,
+                        nv_rd32(priv, 0x040150 + (unit * 0x2000)),
+                        nv_rd32(priv, 0x040154 + (unit * 0x2000)));
+       }
+
+       nv_wr32(priv, 0x040148 + (unit * 0x2000), stat);
+}
+
+static void
+gk104_fifo_intr_runlist(struct gk104_fifo_priv *priv)
+{
+       u32 mask = nv_rd32(priv, 0x002a00);
+       while (mask) {
+               u32 engn = __ffs(mask);
+               wake_up(&priv->engine[engn].wait);
+               nv_wr32(priv, 0x002a00, 1 << engn);
+               mask &= ~(1 << engn);
+       }
+}
+
+static void
+gk104_fifo_intr_engine(struct gk104_fifo_priv *priv)
+{
+       nvkm_fifo_uevent(&priv->base);
+}
+
+static void
+gk104_fifo_intr(struct nvkm_subdev *subdev)
+{
+       struct gk104_fifo_priv *priv = (void *)subdev;
+       u32 mask = nv_rd32(priv, 0x002140);
+       u32 stat = nv_rd32(priv, 0x002100) & mask;
+
+       if (stat & 0x00000001) {
+               gk104_fifo_intr_bind(priv);
+               nv_wr32(priv, 0x002100, 0x00000001);
+               stat &= ~0x00000001;
+       }
+
+       if (stat & 0x00000010) {
+               nv_error(priv, "PIO_ERROR\n");
+               nv_wr32(priv, 0x002100, 0x00000010);
+               stat &= ~0x00000010;
+       }
+
+       if (stat & 0x00000100) {
+               gk104_fifo_intr_sched(priv);
+               nv_wr32(priv, 0x002100, 0x00000100);
+               stat &= ~0x00000100;
+       }
+
+       if (stat & 0x00010000) {
+               gk104_fifo_intr_chsw(priv);
+               nv_wr32(priv, 0x002100, 0x00010000);
+               stat &= ~0x00010000;
+       }
+
+       if (stat & 0x00800000) {
+               nv_error(priv, "FB_FLUSH_TIMEOUT\n");
+               nv_wr32(priv, 0x002100, 0x00800000);
+               stat &= ~0x00800000;
+       }
+
+       if (stat & 0x01000000) {
+               nv_error(priv, "LB_ERROR\n");
+               nv_wr32(priv, 0x002100, 0x01000000);
+               stat &= ~0x01000000;
+       }
+
+       if (stat & 0x08000000) {
+               gk104_fifo_intr_dropped_fault(priv);
+               nv_wr32(priv, 0x002100, 0x08000000);
+               stat &= ~0x08000000;
+       }
+
+       if (stat & 0x10000000) {
+               u32 mask = nv_rd32(priv, 0x00259c);
+               while (mask) {
+                       u32 unit = __ffs(mask);
+                       gk104_fifo_intr_fault(priv, unit);
+                       nv_wr32(priv, 0x00259c, (1 << unit));
+                       mask &= ~(1 << unit);
+               }
+               stat &= ~0x10000000;
+       }
+
+       if (stat & 0x20000000) {
+               u32 mask = nv_rd32(priv, 0x0025a0);
+               while (mask) {
+                       u32 unit = __ffs(mask);
+                       gk104_fifo_intr_pbdma_0(priv, unit);
+                       gk104_fifo_intr_pbdma_1(priv, unit);
+                       nv_wr32(priv, 0x0025a0, (1 << unit));
+                       mask &= ~(1 << unit);
+               }
+               stat &= ~0x20000000;
+       }
+
+       if (stat & 0x40000000) {
+               gk104_fifo_intr_runlist(priv);
+               stat &= ~0x40000000;
+       }
+
+       if (stat & 0x80000000) {
+               nv_wr32(priv, 0x002100, 0x80000000);
+               gk104_fifo_intr_engine(priv);
+               stat &= ~0x80000000;
+       }
+
+       if (stat) {
+               nv_error(priv, "INTR 0x%08x\n", stat);
+               nv_mask(priv, 0x002140, stat, 0x00000000);
+               nv_wr32(priv, 0x002100, stat);
+       }
+}
+
+static void
+gk104_fifo_uevent_init(struct nvkm_event *event, int type, int index)
+{
+       struct nvkm_fifo *fifo = container_of(event, typeof(*fifo), uevent);
+       nv_mask(fifo, 0x002140, 0x80000000, 0x80000000);
+}
+
+static void
+gk104_fifo_uevent_fini(struct nvkm_event *event, int type, int index)
+{
+       struct nvkm_fifo *fifo = container_of(event, typeof(*fifo), uevent);
+       nv_mask(fifo, 0x002140, 0x80000000, 0x00000000);
+}
+
+static const struct nvkm_event_func
+gk104_fifo_uevent_func = {
+       .ctor = nvkm_fifo_uevent_ctor,
+       .init = gk104_fifo_uevent_init,
+       .fini = gk104_fifo_uevent_fini,
+};
+
+int
+gk104_fifo_fini(struct nvkm_object *object, bool suspend)
+{
+       struct gk104_fifo_priv *priv = (void *)object;
+       int ret;
+
+       ret = nvkm_fifo_fini(&priv->base, suspend);
+       if (ret)
+               return ret;
+
+       /* allow mmu fault interrupts, even when we're not using fifo */
+       nv_mask(priv, 0x002140, 0x10000000, 0x10000000);
+       return 0;
+}
+
+int
+gk104_fifo_init(struct nvkm_object *object)
+{
+       struct gk104_fifo_priv *priv = (void *)object;
+       int ret, i;
+
+       ret = nvkm_fifo_init(&priv->base);
+       if (ret)
+               return ret;
+
+       /* enable all available PBDMA units */
+       nv_wr32(priv, 0x000204, 0xffffffff);
+       priv->spoon_nr = hweight32(nv_rd32(priv, 0x000204));
+       nv_debug(priv, "%d PBDMA unit(s)\n", priv->spoon_nr);
+
+       /* PBDMA[n] */
+       for (i = 0; i < priv->spoon_nr; i++) {
+               nv_mask(priv, 0x04013c + (i * 0x2000), 0x10000100, 0x00000000);
+               nv_wr32(priv, 0x040108 + (i * 0x2000), 0xffffffff); /* INTR */
+               nv_wr32(priv, 0x04010c + (i * 0x2000), 0xfffffeff); /* INTREN */
+       }
+
+       /* PBDMA[n].HCE */
+       for (i = 0; i < priv->spoon_nr; i++) {
+               nv_wr32(priv, 0x040148 + (i * 0x2000), 0xffffffff); /* INTR */
+               nv_wr32(priv, 0x04014c + (i * 0x2000), 0xffffffff); /* INTREN */
+       }
+
+       nv_wr32(priv, 0x002254, 0x10000000 | priv->user.bar.offset >> 12);
+
+       nv_wr32(priv, 0x002100, 0xffffffff);
+       nv_wr32(priv, 0x002140, 0x7fffffff);
+       return 0;
+}
+
+void
+gk104_fifo_dtor(struct nvkm_object *object)
+{
+       struct gk104_fifo_priv *priv = (void *)object;
+       int i;
+
+       nvkm_gpuobj_unmap(&priv->user.bar);
+       nvkm_gpuobj_ref(NULL, &priv->user.mem);
+
+       for (i = 0; i < FIFO_ENGINE_NR; i++) {
+               nvkm_gpuobj_ref(NULL, &priv->engine[i].runlist[1]);
+               nvkm_gpuobj_ref(NULL, &priv->engine[i].runlist[0]);
+       }
+
+       nvkm_fifo_destroy(&priv->base);
+}
+
+int
+gk104_fifo_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+               struct nvkm_oclass *oclass, void *data, u32 size,
+               struct nvkm_object **pobject)
+{
+       struct gk104_fifo_impl *impl = (void *)oclass;
+       struct gk104_fifo_priv *priv;
+       int ret, i;
+
+       ret = nvkm_fifo_create(parent, engine, oclass, 0,
+                              impl->channels - 1, &priv);
+       *pobject = nv_object(priv);
+       if (ret)
+               return ret;
+
+       INIT_WORK(&priv->fault, gk104_fifo_recover_work);
+
+       for (i = 0; i < FIFO_ENGINE_NR; i++) {
+               ret = nvkm_gpuobj_new(nv_object(priv), NULL, 0x8000, 0x1000,
+                                     0, &priv->engine[i].runlist[0]);
+               if (ret)
+                       return ret;
+
+               ret = nvkm_gpuobj_new(nv_object(priv), NULL, 0x8000, 0x1000,
+                                     0, &priv->engine[i].runlist[1]);
+               if (ret)
+                       return ret;
+
+               init_waitqueue_head(&priv->engine[i].wait);
+       }
+
+       ret = nvkm_gpuobj_new(nv_object(priv), NULL, impl->channels * 0x200,
+                             0x1000, NVOBJ_FLAG_ZERO_ALLOC, &priv->user.mem);
+       if (ret)
+               return ret;
+
+       ret = nvkm_gpuobj_map(priv->user.mem, NV_MEM_ACCESS_RW,
+                             &priv->user.bar);
+       if (ret)
+               return ret;
+
+       ret = nvkm_event_init(&gk104_fifo_uevent_func, 1, 1, &priv->base.uevent);
+       if (ret)
+               return ret;
+
+       nv_subdev(priv)->unit = 0x00000100;
+       nv_subdev(priv)->intr = gk104_fifo_intr;
+       nv_engine(priv)->cclass = &gk104_fifo_cclass;
+       nv_engine(priv)->sclass = gk104_fifo_sclass;
+       return 0;
+}
+
+struct nvkm_oclass *
+gk104_fifo_oclass = &(struct gk104_fifo_impl) {
+       .base.handle = NV_ENGINE(FIFO, 0xe0),
+       .base.ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = gk104_fifo_ctor,
+               .dtor = gk104_fifo_dtor,
+               .init = gk104_fifo_init,
+               .fini = gk104_fifo_fini,
+       },
+       .channels = 4096,
+}.base;
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/fifo/gk104.h b/drivers/gpu/drm/nouveau/nvkm/engine/fifo/gk104.h
new file mode 100644 (file)
index 0000000..3046e00
--- /dev/null
@@ -0,0 +1,16 @@
+#ifndef __NVKM_FIFO_NVE0_H__
+#define __NVKM_FIFO_NVE0_H__
+#include <engine/fifo.h>
+
+int  gk104_fifo_ctor(struct nvkm_object *, struct nvkm_object *,
+                   struct nvkm_oclass *, void *, u32,
+                   struct nvkm_object **);
+void gk104_fifo_dtor(struct nvkm_object *);
+int  gk104_fifo_init(struct nvkm_object *);
+int  gk104_fifo_fini(struct nvkm_object *, bool);
+
+struct gk104_fifo_impl {
+       struct nvkm_oclass base;
+       u32 channels;
+};
+#endif
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/fifo/gk208.c b/drivers/gpu/drm/nouveau/nvkm/engine/fifo/gk208.c
new file mode 100644 (file)
index 0000000..9270922
--- /dev/null
@@ -0,0 +1,36 @@
+/*
+ * Copyright 2013 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 "gk104.h"
+
+struct nvkm_oclass *
+gk208_fifo_oclass = &(struct gk104_fifo_impl) {
+       .base.handle = NV_ENGINE(FIFO, 0x08),
+       .base.ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = gk104_fifo_ctor,
+               .dtor = gk104_fifo_dtor,
+               .init = gk104_fifo_init,
+               .fini = _nvkm_fifo_fini,
+       },
+       .channels = 1024,
+}.base;
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/fifo/gk20a.c b/drivers/gpu/drm/nouveau/nvkm/engine/fifo/gk20a.c
new file mode 100644 (file)
index 0000000..b30dc87
--- /dev/null
@@ -0,0 +1,34 @@
+/*
+ * Copyright (c) 2014, NVIDIA CORPORATION. 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 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 "gk104.h"
+
+struct nvkm_oclass *
+gk20a_fifo_oclass = &(struct gk104_fifo_impl) {
+       .base.handle = NV_ENGINE(FIFO, 0xea),
+       .base.ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = gk104_fifo_ctor,
+               .dtor = gk104_fifo_dtor,
+               .init = gk104_fifo_init,
+               .fini = gk104_fifo_fini,
+       },
+       .channels = 128,
+}.base;
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/fifo/nv04.c b/drivers/gpu/drm/nouveau/nvkm/engine/fifo/nv04.c
new file mode 100644 (file)
index 0000000..b038b6e
--- /dev/null
@@ -0,0 +1,650 @@
+/*
+ * Copyright 2012 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 "nv04.h"
+
+#include <core/client.h>
+#include <core/device.h>
+#include <core/engctx.h>
+#include <core/handle.h>
+#include <core/ramht.h>
+#include <subdev/instmem/nv04.h>
+#include <subdev/timer.h>
+
+#include <nvif/class.h>
+#include <nvif/unpack.h>
+
+static struct ramfc_desc
+nv04_ramfc[] = {
+       { 32,  0, 0x00,  0, NV04_PFIFO_CACHE1_DMA_PUT },
+       { 32,  0, 0x04,  0, NV04_PFIFO_CACHE1_DMA_GET },
+       { 16,  0, 0x08,  0, NV04_PFIFO_CACHE1_DMA_INSTANCE },
+       { 16, 16, 0x08,  0, NV04_PFIFO_CACHE1_DMA_DCOUNT },
+       { 32,  0, 0x0c,  0, NV04_PFIFO_CACHE1_DMA_STATE },
+       { 32,  0, 0x10,  0, NV04_PFIFO_CACHE1_DMA_FETCH },
+       { 32,  0, 0x14,  0, NV04_PFIFO_CACHE1_ENGINE },
+       { 32,  0, 0x18,  0, NV04_PFIFO_CACHE1_PULL1 },
+       {}
+};
+
+/*******************************************************************************
+ * FIFO channel objects
+ ******************************************************************************/
+
+int
+nv04_fifo_object_attach(struct nvkm_object *parent,
+                       struct nvkm_object *object, u32 handle)
+{
+       struct nv04_fifo_priv *priv = (void *)parent->engine;
+       struct nv04_fifo_chan *chan = (void *)parent;
+       u32 context, chid = chan->base.chid;
+       int ret;
+
+       if (nv_iclass(object, NV_GPUOBJ_CLASS))
+               context = nv_gpuobj(object)->addr >> 4;
+       else
+               context = 0x00000004; /* just non-zero */
+
+       switch (nv_engidx(object->engine)) {
+       case NVDEV_ENGINE_DMAOBJ:
+       case NVDEV_ENGINE_SW:
+               context |= 0x00000000;
+               break;
+       case NVDEV_ENGINE_GR:
+               context |= 0x00010000;
+               break;
+       case NVDEV_ENGINE_MPEG:
+               context |= 0x00020000;
+               break;
+       default:
+               return -EINVAL;
+       }
+
+       context |= 0x80000000; /* valid */
+       context |= chid << 24;
+
+       mutex_lock(&nv_subdev(priv)->mutex);
+       ret = nvkm_ramht_insert(priv->ramht, chid, handle, context);
+       mutex_unlock(&nv_subdev(priv)->mutex);
+       return ret;
+}
+
+void
+nv04_fifo_object_detach(struct nvkm_object *parent, int cookie)
+{
+       struct nv04_fifo_priv *priv = (void *)parent->engine;
+       mutex_lock(&nv_subdev(priv)->mutex);
+       nvkm_ramht_remove(priv->ramht, cookie);
+       mutex_unlock(&nv_subdev(priv)->mutex);
+}
+
+int
+nv04_fifo_context_attach(struct nvkm_object *parent,
+                        struct nvkm_object *object)
+{
+       nv_engctx(object)->addr = nvkm_fifo_chan(parent)->chid;
+       return 0;
+}
+
+static int
+nv04_fifo_chan_ctor(struct nvkm_object *parent,
+                   struct nvkm_object *engine,
+                   struct nvkm_oclass *oclass, void *data, u32 size,
+                   struct nvkm_object **pobject)
+{
+       union {
+               struct nv03_channel_dma_v0 v0;
+       } *args = data;
+       struct nv04_fifo_priv *priv = (void *)engine;
+       struct nv04_fifo_chan *chan;
+       int ret;
+
+       nv_ioctl(parent, "create channel dma size %d\n", size);
+       if (nvif_unpack(args->v0, 0, 0, false)) {
+               nv_ioctl(parent, "create channel dma vers %d pushbuf %08x "
+                                "offset %016llx\n", args->v0.version,
+                        args->v0.pushbuf, args->v0.offset);
+       } else
+               return ret;
+
+       ret = nvkm_fifo_channel_create(parent, engine, oclass, 0, 0x800000,
+                                      0x10000, args->v0.pushbuf,
+                                      (1ULL << NVDEV_ENGINE_DMAOBJ) |
+                                      (1ULL << NVDEV_ENGINE_SW) |
+                                      (1ULL << NVDEV_ENGINE_GR), &chan);
+       *pobject = nv_object(chan);
+       if (ret)
+               return ret;
+
+       args->v0.chid = chan->base.chid;
+
+       nv_parent(chan)->object_attach = nv04_fifo_object_attach;
+       nv_parent(chan)->object_detach = nv04_fifo_object_detach;
+       nv_parent(chan)->context_attach = nv04_fifo_context_attach;
+       chan->ramfc = chan->base.chid * 32;
+
+       nv_wo32(priv->ramfc, chan->ramfc + 0x00, args->v0.offset);
+       nv_wo32(priv->ramfc, chan->ramfc + 0x04, args->v0.offset);
+       nv_wo32(priv->ramfc, chan->ramfc + 0x08, chan->base.pushgpu->addr >> 4);
+       nv_wo32(priv->ramfc, chan->ramfc + 0x10,
+                            NV_PFIFO_CACHE1_DMA_FETCH_TRIG_128_BYTES |
+                            NV_PFIFO_CACHE1_DMA_FETCH_SIZE_128_BYTES |
+#ifdef __BIG_ENDIAN
+                            NV_PFIFO_CACHE1_BIG_ENDIAN |
+#endif
+                            NV_PFIFO_CACHE1_DMA_FETCH_MAX_REQS_8);
+       return 0;
+}
+
+void
+nv04_fifo_chan_dtor(struct nvkm_object *object)
+{
+       struct nv04_fifo_priv *priv = (void *)object->engine;
+       struct nv04_fifo_chan *chan = (void *)object;
+       struct ramfc_desc *c = priv->ramfc_desc;
+
+       do {
+               nv_wo32(priv->ramfc, chan->ramfc + c->ctxp, 0x00000000);
+       } while ((++c)->bits);
+
+       nvkm_fifo_channel_destroy(&chan->base);
+}
+
+int
+nv04_fifo_chan_init(struct nvkm_object *object)
+{
+       struct nv04_fifo_priv *priv = (void *)object->engine;
+       struct nv04_fifo_chan *chan = (void *)object;
+       u32 mask = 1 << chan->base.chid;
+       unsigned long flags;
+       int ret;
+
+       ret = nvkm_fifo_channel_init(&chan->base);
+       if (ret)
+               return ret;
+
+       spin_lock_irqsave(&priv->base.lock, flags);
+       nv_mask(priv, NV04_PFIFO_MODE, mask, mask);
+       spin_unlock_irqrestore(&priv->base.lock, flags);
+       return 0;
+}
+
+int
+nv04_fifo_chan_fini(struct nvkm_object *object, bool suspend)
+{
+       struct nv04_fifo_priv *priv = (void *)object->engine;
+       struct nv04_fifo_chan *chan = (void *)object;
+       struct nvkm_gpuobj *fctx = priv->ramfc;
+       struct ramfc_desc *c;
+       unsigned long flags;
+       u32 data = chan->ramfc;
+       u32 chid;
+
+       /* prevent fifo context switches */
+       spin_lock_irqsave(&priv->base.lock, flags);
+       nv_wr32(priv, NV03_PFIFO_CACHES, 0);
+
+       /* if this channel is active, replace it with a null context */
+       chid = nv_rd32(priv, NV03_PFIFO_CACHE1_PUSH1) & priv->base.max;
+       if (chid == chan->base.chid) {
+               nv_mask(priv, NV04_PFIFO_CACHE1_DMA_PUSH, 0x00000001, 0);
+               nv_wr32(priv, NV03_PFIFO_CACHE1_PUSH0, 0);
+               nv_mask(priv, NV04_PFIFO_CACHE1_PULL0, 0x00000001, 0);
+
+               c = priv->ramfc_desc;
+               do {
+                       u32 rm = ((1ULL << c->bits) - 1) << c->regs;
+                       u32 cm = ((1ULL << c->bits) - 1) << c->ctxs;
+                       u32 rv = (nv_rd32(priv, c->regp) &  rm) >> c->regs;
+                       u32 cv = (nv_ro32(fctx, c->ctxp + data) & ~cm);
+                       nv_wo32(fctx, c->ctxp + data, cv | (rv << c->ctxs));
+               } while ((++c)->bits);
+
+               c = priv->ramfc_desc;
+               do {
+                       nv_wr32(priv, c->regp, 0x00000000);
+               } while ((++c)->bits);
+
+               nv_wr32(priv, NV03_PFIFO_CACHE1_GET, 0);
+               nv_wr32(priv, NV03_PFIFO_CACHE1_PUT, 0);
+               nv_wr32(priv, NV03_PFIFO_CACHE1_PUSH1, priv->base.max);
+               nv_wr32(priv, NV03_PFIFO_CACHE1_PUSH0, 1);
+               nv_wr32(priv, NV04_PFIFO_CACHE1_PULL0, 1);
+       }
+
+       /* restore normal operation, after disabling dma mode */
+       nv_mask(priv, NV04_PFIFO_MODE, 1 << chan->base.chid, 0);
+       nv_wr32(priv, NV03_PFIFO_CACHES, 1);
+       spin_unlock_irqrestore(&priv->base.lock, flags);
+
+       return nvkm_fifo_channel_fini(&chan->base, suspend);
+}
+
+static struct nvkm_ofuncs
+nv04_fifo_ofuncs = {
+       .ctor = nv04_fifo_chan_ctor,
+       .dtor = nv04_fifo_chan_dtor,
+       .init = nv04_fifo_chan_init,
+       .fini = nv04_fifo_chan_fini,
+       .map  = _nvkm_fifo_channel_map,
+       .rd32 = _nvkm_fifo_channel_rd32,
+       .wr32 = _nvkm_fifo_channel_wr32,
+       .ntfy = _nvkm_fifo_channel_ntfy
+};
+
+static struct nvkm_oclass
+nv04_fifo_sclass[] = {
+       { NV03_CHANNEL_DMA, &nv04_fifo_ofuncs },
+       {}
+};
+
+/*******************************************************************************
+ * FIFO context - basically just the instmem reserved for the channel
+ ******************************************************************************/
+
+int
+nv04_fifo_context_ctor(struct nvkm_object *parent,
+                      struct nvkm_object *engine,
+                      struct nvkm_oclass *oclass, void *data, u32 size,
+                      struct nvkm_object **pobject)
+{
+       struct nv04_fifo_base *base;
+       int ret;
+
+       ret = nvkm_fifo_context_create(parent, engine, oclass, NULL, 0x1000,
+                                      0x1000, NVOBJ_FLAG_HEAP, &base);
+       *pobject = nv_object(base);
+       if (ret)
+               return ret;
+
+       return 0;
+}
+
+static struct nvkm_oclass
+nv04_fifo_cclass = {
+       .handle = NV_ENGCTX(FIFO, 0x04),
+       .ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = nv04_fifo_context_ctor,
+               .dtor = _nvkm_fifo_context_dtor,
+               .init = _nvkm_fifo_context_init,
+               .fini = _nvkm_fifo_context_fini,
+               .rd32 = _nvkm_fifo_context_rd32,
+               .wr32 = _nvkm_fifo_context_wr32,
+       },
+};
+
+/*******************************************************************************
+ * PFIFO engine
+ ******************************************************************************/
+
+void
+nv04_fifo_pause(struct nvkm_fifo *pfifo, unsigned long *pflags)
+__acquires(priv->base.lock)
+{
+       struct nv04_fifo_priv *priv = (void *)pfifo;
+       unsigned long flags;
+
+       spin_lock_irqsave(&priv->base.lock, flags);
+       *pflags = flags;
+
+       nv_wr32(priv, NV03_PFIFO_CACHES, 0x00000000);
+       nv_mask(priv, NV04_PFIFO_CACHE1_PULL0, 0x00000001, 0x00000000);
+
+       /* in some cases the puller may be left in an inconsistent state
+        * if you try to stop it while it's busy translating handles.
+        * sometimes you get a CACHE_ERROR, sometimes it just fails
+        * silently; sending incorrect instance offsets to PGRAPH after
+        * it's started up again.
+        *
+        * to avoid this, we invalidate the most recently calculated
+        * instance.
+        */
+       if (!nv_wait(priv, NV04_PFIFO_CACHE1_PULL0,
+                          NV04_PFIFO_CACHE1_PULL0_HASH_BUSY, 0x00000000))
+               nv_warn(priv, "timeout idling puller\n");
+
+       if (nv_rd32(priv, NV04_PFIFO_CACHE1_PULL0) &
+                         NV04_PFIFO_CACHE1_PULL0_HASH_FAILED)
+               nv_wr32(priv, NV03_PFIFO_INTR_0, NV_PFIFO_INTR_CACHE_ERROR);
+
+       nv_wr32(priv, NV04_PFIFO_CACHE1_HASH, 0x00000000);
+}
+
+void
+nv04_fifo_start(struct nvkm_fifo *pfifo, unsigned long *pflags)
+__releases(priv->base.lock)
+{
+       struct nv04_fifo_priv *priv = (void *)pfifo;
+       unsigned long flags = *pflags;
+
+       nv_mask(priv, NV04_PFIFO_CACHE1_PULL0, 0x00000001, 0x00000001);
+       nv_wr32(priv, NV03_PFIFO_CACHES, 0x00000001);
+
+       spin_unlock_irqrestore(&priv->base.lock, flags);
+}
+
+static const char *
+nv_dma_state_err(u32 state)
+{
+       static const char * const desc[] = {
+               "NONE", "CALL_SUBR_ACTIVE", "INVALID_MTHD", "RET_SUBR_INACTIVE",
+               "INVALID_CMD", "IB_EMPTY"/* NV50+ */, "MEM_FAULT", "UNK"
+       };
+       return desc[(state >> 29) & 0x7];
+}
+
+static bool
+nv04_fifo_swmthd(struct nv04_fifo_priv *priv, u32 chid, u32 addr, u32 data)
+{
+       struct nv04_fifo_chan *chan = NULL;
+       struct nvkm_handle *bind;
+       const int subc = (addr >> 13) & 0x7;
+       const int mthd = addr & 0x1ffc;
+       bool handled = false;
+       unsigned long flags;
+       u32 engine;
+
+       spin_lock_irqsave(&priv->base.lock, flags);
+       if (likely(chid >= priv->base.min && chid <= priv->base.max))
+               chan = (void *)priv->base.channel[chid];
+       if (unlikely(!chan))
+               goto out;
+
+       switch (mthd) {
+       case 0x0000:
+               bind = nvkm_namedb_get(nv_namedb(chan), data);
+               if (unlikely(!bind))
+                       break;
+
+               if (nv_engidx(bind->object->engine) == NVDEV_ENGINE_SW) {
+                       engine = 0x0000000f << (subc * 4);
+                       chan->subc[subc] = data;
+                       handled = true;
+
+                       nv_mask(priv, NV04_PFIFO_CACHE1_ENGINE, engine, 0);
+               }
+
+               nvkm_namedb_put(bind);
+               break;
+       default:
+               engine = nv_rd32(priv, NV04_PFIFO_CACHE1_ENGINE);
+               if (unlikely(((engine >> (subc * 4)) & 0xf) != 0))
+                       break;
+
+               bind = nvkm_namedb_get(nv_namedb(chan), chan->subc[subc]);
+               if (likely(bind)) {
+                       if (!nv_call(bind->object, mthd, data))
+                               handled = true;
+                       nvkm_namedb_put(bind);
+               }
+               break;
+       }
+
+out:
+       spin_unlock_irqrestore(&priv->base.lock, flags);
+       return handled;
+}
+
+static void
+nv04_fifo_cache_error(struct nvkm_device *device,
+                     struct nv04_fifo_priv *priv, u32 chid, u32 get)
+{
+       u32 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 (device->card_type < NV_40) {
+               mthd = nv_rd32(priv, NV04_PFIFO_CACHE1_METHOD(ptr));
+               data = nv_rd32(priv, NV04_PFIFO_CACHE1_DATA(ptr));
+       } else {
+               mthd = nv_rd32(priv, NV40_PFIFO_CACHE1_METHOD(ptr));
+               data = nv_rd32(priv, NV40_PFIFO_CACHE1_DATA(ptr));
+       }
+
+       if (!nv04_fifo_swmthd(priv, chid, mthd, data)) {
+               const char *client_name =
+                       nvkm_client_name_for_fifo_chid(&priv->base, chid);
+               nv_error(priv,
+                        "CACHE_ERROR - ch %d [%s] subc %d mthd 0x%04x data 0x%08x\n",
+                        chid, client_name, (mthd >> 13) & 7, mthd & 0x1ffc,
+                        data);
+       }
+
+       nv_wr32(priv, NV04_PFIFO_CACHE1_DMA_PUSH, 0);
+       nv_wr32(priv, NV03_PFIFO_INTR_0, NV_PFIFO_INTR_CACHE_ERROR);
+
+       nv_wr32(priv, NV03_PFIFO_CACHE1_PUSH0,
+               nv_rd32(priv, NV03_PFIFO_CACHE1_PUSH0) & ~1);
+       nv_wr32(priv, NV03_PFIFO_CACHE1_GET, get + 4);
+       nv_wr32(priv, NV03_PFIFO_CACHE1_PUSH0,
+               nv_rd32(priv, NV03_PFIFO_CACHE1_PUSH0) | 1);
+       nv_wr32(priv, NV04_PFIFO_CACHE1_HASH, 0);
+
+       nv_wr32(priv, NV04_PFIFO_CACHE1_DMA_PUSH,
+               nv_rd32(priv, NV04_PFIFO_CACHE1_DMA_PUSH) | 1);
+       nv_wr32(priv, NV04_PFIFO_CACHE1_PULL0, 1);
+}
+
+static void
+nv04_fifo_dma_pusher(struct nvkm_device *device,
+                    struct nv04_fifo_priv *priv, u32 chid)
+{
+       const char *client_name;
+       u32 dma_get = nv_rd32(priv, 0x003244);
+       u32 dma_put = nv_rd32(priv, 0x003240);
+       u32 push = nv_rd32(priv, 0x003220);
+       u32 state = nv_rd32(priv, 0x003228);
+
+       client_name = nvkm_client_name_for_fifo_chid(&priv->base, chid);
+
+       if (device->card_type == NV_50) {
+               u32 ho_get = nv_rd32(priv, 0x003328);
+               u32 ho_put = nv_rd32(priv, 0x003320);
+               u32 ib_get = nv_rd32(priv, 0x003334);
+               u32 ib_put = nv_rd32(priv, 0x003330);
+
+               nv_error(priv,
+                        "DMA_PUSHER - ch %d [%s] get 0x%02x%08x put 0x%02x%08x ib_get 0x%08x ib_put 0x%08x state 0x%08x (err: %s) push 0x%08x\n",
+                        chid, client_name, ho_get, dma_get, ho_put, dma_put,
+                        ib_get, ib_put, state, nv_dma_state_err(state), push);
+
+               /* METHOD_COUNT, in DMA_STATE on earlier chipsets */
+               nv_wr32(priv, 0x003364, 0x00000000);
+               if (dma_get != dma_put || ho_get != ho_put) {
+                       nv_wr32(priv, 0x003244, dma_put);
+                       nv_wr32(priv, 0x003328, ho_put);
+               } else
+               if (ib_get != ib_put)
+                       nv_wr32(priv, 0x003334, ib_put);
+       } else {
+               nv_error(priv,
+                        "DMA_PUSHER - ch %d [%s] get 0x%08x put 0x%08x state 0x%08x (err: %s) push 0x%08x\n",
+                        chid, client_name, dma_get, dma_put, state,
+                        nv_dma_state_err(state), push);
+
+               if (dma_get != dma_put)
+                       nv_wr32(priv, 0x003244, dma_put);
+       }
+
+       nv_wr32(priv, 0x003228, 0x00000000);
+       nv_wr32(priv, 0x003220, 0x00000001);
+       nv_wr32(priv, 0x002100, NV_PFIFO_INTR_DMA_PUSHER);
+}
+
+void
+nv04_fifo_intr(struct nvkm_subdev *subdev)
+{
+       struct nvkm_device *device = nv_device(subdev);
+       struct nv04_fifo_priv *priv = (void *)subdev;
+       uint32_t status, reassign;
+       int cnt = 0;
+
+       reassign = nv_rd32(priv, NV03_PFIFO_CACHES) & 1;
+       while ((status = nv_rd32(priv, NV03_PFIFO_INTR_0)) && (cnt++ < 100)) {
+               uint32_t chid, get;
+
+               nv_wr32(priv, NV03_PFIFO_CACHES, 0);
+
+               chid = nv_rd32(priv, NV03_PFIFO_CACHE1_PUSH1) & priv->base.max;
+               get  = nv_rd32(priv, NV03_PFIFO_CACHE1_GET);
+
+               if (status & NV_PFIFO_INTR_CACHE_ERROR) {
+                       nv04_fifo_cache_error(device, priv, chid, get);
+                       status &= ~NV_PFIFO_INTR_CACHE_ERROR;
+               }
+
+               if (status & NV_PFIFO_INTR_DMA_PUSHER) {
+                       nv04_fifo_dma_pusher(device, priv, chid);
+                       status &= ~NV_PFIFO_INTR_DMA_PUSHER;
+               }
+
+               if (status & NV_PFIFO_INTR_SEMAPHORE) {
+                       uint32_t sem;
+
+                       status &= ~NV_PFIFO_INTR_SEMAPHORE;
+                       nv_wr32(priv, NV03_PFIFO_INTR_0,
+                               NV_PFIFO_INTR_SEMAPHORE);
+
+                       sem = nv_rd32(priv, NV10_PFIFO_CACHE1_SEMAPHORE);
+                       nv_wr32(priv, NV10_PFIFO_CACHE1_SEMAPHORE, sem | 0x1);
+
+                       nv_wr32(priv, NV03_PFIFO_CACHE1_GET, get + 4);
+                       nv_wr32(priv, NV04_PFIFO_CACHE1_PULL0, 1);
+               }
+
+               if (device->card_type == NV_50) {
+                       if (status & 0x00000010) {
+                               status &= ~0x00000010;
+                               nv_wr32(priv, 0x002100, 0x00000010);
+                       }
+
+                       if (status & 0x40000000) {
+                               nv_wr32(priv, 0x002100, 0x40000000);
+                               nvkm_fifo_uevent(&priv->base);
+                               status &= ~0x40000000;
+                       }
+               }
+
+               if (status) {
+                       nv_warn(priv, "unknown intr 0x%08x, ch %d\n",
+                               status, chid);
+                       nv_wr32(priv, NV03_PFIFO_INTR_0, status);
+                       status = 0;
+               }
+
+               nv_wr32(priv, NV03_PFIFO_CACHES, reassign);
+       }
+
+       if (status) {
+               nv_error(priv, "still angry after %d spins, halt\n", cnt);
+               nv_wr32(priv, 0x002140, 0);
+               nv_wr32(priv, 0x000140, 0);
+       }
+
+       nv_wr32(priv, 0x000100, 0x00000100);
+}
+
+static int
+nv04_fifo_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+              struct nvkm_oclass *oclass, void *data, u32 size,
+              struct nvkm_object **pobject)
+{
+       struct nv04_instmem_priv *imem = nv04_instmem(parent);
+       struct nv04_fifo_priv *priv;
+       int ret;
+
+       ret = nvkm_fifo_create(parent, engine, oclass, 0, 15, &priv);
+       *pobject = nv_object(priv);
+       if (ret)
+               return ret;
+
+       nvkm_ramht_ref(imem->ramht, &priv->ramht);
+       nvkm_gpuobj_ref(imem->ramro, &priv->ramro);
+       nvkm_gpuobj_ref(imem->ramfc, &priv->ramfc);
+
+       nv_subdev(priv)->unit = 0x00000100;
+       nv_subdev(priv)->intr = nv04_fifo_intr;
+       nv_engine(priv)->cclass = &nv04_fifo_cclass;
+       nv_engine(priv)->sclass = nv04_fifo_sclass;
+       priv->base.pause = nv04_fifo_pause;
+       priv->base.start = nv04_fifo_start;
+       priv->ramfc_desc = nv04_ramfc;
+       return 0;
+}
+
+void
+nv04_fifo_dtor(struct nvkm_object *object)
+{
+       struct nv04_fifo_priv *priv = (void *)object;
+       nvkm_gpuobj_ref(NULL, &priv->ramfc);
+       nvkm_gpuobj_ref(NULL, &priv->ramro);
+       nvkm_ramht_ref(NULL, &priv->ramht);
+       nvkm_fifo_destroy(&priv->base);
+}
+
+int
+nv04_fifo_init(struct nvkm_object *object)
+{
+       struct nv04_fifo_priv *priv = (void *)object;
+       int ret;
+
+       ret = nvkm_fifo_init(&priv->base);
+       if (ret)
+               return ret;
+
+       nv_wr32(priv, NV04_PFIFO_DELAY_0, 0x000000ff);
+       nv_wr32(priv, NV04_PFIFO_DMA_TIMESLICE, 0x0101ffff);
+
+       nv_wr32(priv, NV03_PFIFO_RAMHT, (0x03 << 24) /* search 128 */ |
+                                      ((priv->ramht->bits - 9) << 16) |
+                                       (priv->ramht->gpuobj.addr >> 8));
+       nv_wr32(priv, NV03_PFIFO_RAMRO, priv->ramro->addr >> 8);
+       nv_wr32(priv, NV03_PFIFO_RAMFC, priv->ramfc->addr >> 8);
+
+       nv_wr32(priv, NV03_PFIFO_CACHE1_PUSH1, priv->base.max);
+
+       nv_wr32(priv, NV03_PFIFO_INTR_0, 0xffffffff);
+       nv_wr32(priv, NV03_PFIFO_INTR_EN_0, 0xffffffff);
+
+       nv_wr32(priv, NV03_PFIFO_CACHE1_PUSH0, 1);
+       nv_wr32(priv, NV04_PFIFO_CACHE1_PULL0, 1);
+       nv_wr32(priv, NV03_PFIFO_CACHES, 1);
+       return 0;
+}
+
+struct nvkm_oclass *
+nv04_fifo_oclass = &(struct nvkm_oclass) {
+       .handle = NV_ENGINE(FIFO, 0x04),
+       .ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = nv04_fifo_ctor,
+               .dtor = nv04_fifo_dtor,
+               .init = nv04_fifo_init,
+               .fini = _nvkm_fifo_fini,
+       },
+};
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/fifo/nv04.h b/drivers/gpu/drm/nouveau/nvkm/engine/fifo/nv04.h
new file mode 100644 (file)
index 0000000..e0e0c47
--- /dev/null
@@ -0,0 +1,175 @@
+#ifndef __NV04_FIFO_H__
+#define __NV04_FIFO_H__
+#include <engine/fifo.h>
+
+#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))
+
+struct ramfc_desc {
+       unsigned bits:6;
+       unsigned ctxs:5;
+       unsigned ctxp:8;
+       unsigned regs:5;
+       unsigned regp;
+};
+
+struct nv04_fifo_priv {
+       struct nvkm_fifo base;
+       struct ramfc_desc *ramfc_desc;
+       struct nvkm_ramht  *ramht;
+       struct nvkm_gpuobj *ramro;
+       struct nvkm_gpuobj *ramfc;
+};
+
+struct nv04_fifo_base {
+       struct nvkm_fifo_base base;
+};
+
+struct nv04_fifo_chan {
+       struct nvkm_fifo_chan base;
+       u32 subc[8];
+       u32 ramfc;
+};
+
+int  nv04_fifo_object_attach(struct nvkm_object *, struct nvkm_object *, u32);
+void nv04_fifo_object_detach(struct nvkm_object *, int);
+
+void nv04_fifo_chan_dtor(struct nvkm_object *);
+int  nv04_fifo_chan_init(struct nvkm_object *);
+int  nv04_fifo_chan_fini(struct nvkm_object *, bool suspend);
+
+int  nv04_fifo_context_ctor(struct nvkm_object *, struct nvkm_object *,
+                           struct nvkm_oclass *, void *, u32,
+                           struct nvkm_object **);
+
+void nv04_fifo_dtor(struct nvkm_object *);
+int  nv04_fifo_init(struct nvkm_object *);
+void nv04_fifo_pause(struct nvkm_fifo *, unsigned long *);
+void nv04_fifo_start(struct nvkm_fifo *, unsigned long *);
+#endif
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/fifo/nv10.c b/drivers/gpu/drm/nouveau/nvkm/engine/fifo/nv10.c
new file mode 100644 (file)
index 0000000..48ce4af
--- /dev/null
@@ -0,0 +1,178 @@
+/*
+ * Copyright 2012 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 "nv04.h"
+
+#include <core/client.h>
+#include <core/engctx.h>
+#include <core/ramht.h>
+#include <subdev/instmem/nv04.h>
+
+#include <nvif/class.h>
+#include <nvif/unpack.h>
+
+static struct ramfc_desc
+nv10_ramfc[] = {
+       { 32,  0, 0x00,  0, NV04_PFIFO_CACHE1_DMA_PUT },
+       { 32,  0, 0x04,  0, NV04_PFIFO_CACHE1_DMA_GET },
+       { 32,  0, 0x08,  0, NV10_PFIFO_CACHE1_REF_CNT },
+       { 16,  0, 0x0c,  0, NV04_PFIFO_CACHE1_DMA_INSTANCE },
+       { 16, 16, 0x0c,  0, NV04_PFIFO_CACHE1_DMA_DCOUNT },
+       { 32,  0, 0x10,  0, NV04_PFIFO_CACHE1_DMA_STATE },
+       { 32,  0, 0x14,  0, NV04_PFIFO_CACHE1_DMA_FETCH },
+       { 32,  0, 0x18,  0, NV04_PFIFO_CACHE1_ENGINE },
+       { 32,  0, 0x1c,  0, NV04_PFIFO_CACHE1_PULL1 },
+       {}
+};
+
+/*******************************************************************************
+ * FIFO channel objects
+ ******************************************************************************/
+
+static int
+nv10_fifo_chan_ctor(struct nvkm_object *parent,
+                   struct nvkm_object *engine,
+                   struct nvkm_oclass *oclass, void *data, u32 size,
+                   struct nvkm_object **pobject)
+{
+       union {
+               struct nv03_channel_dma_v0 v0;
+       } *args = data;
+       struct nv04_fifo_priv *priv = (void *)engine;
+       struct nv04_fifo_chan *chan;
+       int ret;
+
+       nv_ioctl(parent, "create channel dma size %d\n", size);
+       if (nvif_unpack(args->v0, 0, 0, false)) {
+               nv_ioctl(parent, "create channel dma vers %d pushbuf %08x "
+                                "offset %016llx\n", args->v0.version,
+                        args->v0.pushbuf, args->v0.offset);
+       } else
+               return ret;
+
+       ret = nvkm_fifo_channel_create(parent, engine, oclass, 0, 0x800000,
+                                      0x10000, args->v0.pushbuf,
+                                      (1ULL << NVDEV_ENGINE_DMAOBJ) |
+                                      (1ULL << NVDEV_ENGINE_SW) |
+                                      (1ULL << NVDEV_ENGINE_GR), &chan);
+       *pobject = nv_object(chan);
+       if (ret)
+               return ret;
+
+       args->v0.chid = chan->base.chid;
+
+       nv_parent(chan)->object_attach = nv04_fifo_object_attach;
+       nv_parent(chan)->object_detach = nv04_fifo_object_detach;
+       nv_parent(chan)->context_attach = nv04_fifo_context_attach;
+       chan->ramfc = chan->base.chid * 32;
+
+       nv_wo32(priv->ramfc, chan->ramfc + 0x00, args->v0.offset);
+       nv_wo32(priv->ramfc, chan->ramfc + 0x04, args->v0.offset);
+       nv_wo32(priv->ramfc, chan->ramfc + 0x0c, chan->base.pushgpu->addr >> 4);
+       nv_wo32(priv->ramfc, chan->ramfc + 0x14,
+                            NV_PFIFO_CACHE1_DMA_FETCH_TRIG_128_BYTES |
+                            NV_PFIFO_CACHE1_DMA_FETCH_SIZE_128_BYTES |
+#ifdef __BIG_ENDIAN
+                            NV_PFIFO_CACHE1_BIG_ENDIAN |
+#endif
+                            NV_PFIFO_CACHE1_DMA_FETCH_MAX_REQS_8);
+       return 0;
+}
+
+static struct nvkm_ofuncs
+nv10_fifo_ofuncs = {
+       .ctor = nv10_fifo_chan_ctor,
+       .dtor = nv04_fifo_chan_dtor,
+       .init = nv04_fifo_chan_init,
+       .fini = nv04_fifo_chan_fini,
+       .map  = _nvkm_fifo_channel_map,
+       .rd32 = _nvkm_fifo_channel_rd32,
+       .wr32 = _nvkm_fifo_channel_wr32,
+       .ntfy = _nvkm_fifo_channel_ntfy
+};
+
+static struct nvkm_oclass
+nv10_fifo_sclass[] = {
+       { NV10_CHANNEL_DMA, &nv10_fifo_ofuncs },
+       {}
+};
+
+/*******************************************************************************
+ * FIFO context - basically just the instmem reserved for the channel
+ ******************************************************************************/
+
+static struct nvkm_oclass
+nv10_fifo_cclass = {
+       .handle = NV_ENGCTX(FIFO, 0x10),
+       .ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = nv04_fifo_context_ctor,
+               .dtor = _nvkm_fifo_context_dtor,
+               .init = _nvkm_fifo_context_init,
+               .fini = _nvkm_fifo_context_fini,
+               .rd32 = _nvkm_fifo_context_rd32,
+               .wr32 = _nvkm_fifo_context_wr32,
+       },
+};
+
+/*******************************************************************************
+ * PFIFO engine
+ ******************************************************************************/
+
+static int
+nv10_fifo_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+              struct nvkm_oclass *oclass, void *data, u32 size,
+              struct nvkm_object **pobject)
+{
+       struct nv04_instmem_priv *imem = nv04_instmem(parent);
+       struct nv04_fifo_priv *priv;
+       int ret;
+
+       ret = nvkm_fifo_create(parent, engine, oclass, 0, 31, &priv);
+       *pobject = nv_object(priv);
+       if (ret)
+               return ret;
+
+       nvkm_ramht_ref(imem->ramht, &priv->ramht);
+       nvkm_gpuobj_ref(imem->ramro, &priv->ramro);
+       nvkm_gpuobj_ref(imem->ramfc, &priv->ramfc);
+
+       nv_subdev(priv)->unit = 0x00000100;
+       nv_subdev(priv)->intr = nv04_fifo_intr;
+       nv_engine(priv)->cclass = &nv10_fifo_cclass;
+       nv_engine(priv)->sclass = nv10_fifo_sclass;
+       priv->base.pause = nv04_fifo_pause;
+       priv->base.start = nv04_fifo_start;
+       priv->ramfc_desc = nv10_ramfc;
+       return 0;
+}
+
+struct nvkm_oclass *
+nv10_fifo_oclass = &(struct nvkm_oclass) {
+       .handle = NV_ENGINE(FIFO, 0x10),
+       .ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = nv10_fifo_ctor,
+               .dtor = nv04_fifo_dtor,
+               .init = nv04_fifo_init,
+               .fini = _nvkm_fifo_fini,
+       },
+};
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/fifo/nv17.c b/drivers/gpu/drm/nouveau/nvkm/engine/fifo/nv17.c
new file mode 100644 (file)
index 0000000..4a20a6f
--- /dev/null
@@ -0,0 +1,215 @@
+/*
+ * Copyright 2012 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 "nv04.h"
+
+#include <core/client.h>
+#include <core/engctx.h>
+#include <core/ramht.h>
+#include <subdev/instmem/nv04.h>
+
+#include <nvif/class.h>
+#include <nvif/unpack.h>
+
+static struct ramfc_desc
+nv17_ramfc[] = {
+       { 32,  0, 0x00,  0, NV04_PFIFO_CACHE1_DMA_PUT },
+       { 32,  0, 0x04,  0, NV04_PFIFO_CACHE1_DMA_GET },
+       { 32,  0, 0x08,  0, NV10_PFIFO_CACHE1_REF_CNT },
+       { 16,  0, 0x0c,  0, NV04_PFIFO_CACHE1_DMA_INSTANCE },
+       { 16, 16, 0x0c,  0, NV04_PFIFO_CACHE1_DMA_DCOUNT },
+       { 32,  0, 0x10,  0, NV04_PFIFO_CACHE1_DMA_STATE },
+       { 32,  0, 0x14,  0, NV04_PFIFO_CACHE1_DMA_FETCH },
+       { 32,  0, 0x18,  0, NV04_PFIFO_CACHE1_ENGINE },
+       { 32,  0, 0x1c,  0, NV04_PFIFO_CACHE1_PULL1 },
+       { 32,  0, 0x20,  0, NV10_PFIFO_CACHE1_ACQUIRE_VALUE },
+       { 32,  0, 0x24,  0, NV10_PFIFO_CACHE1_ACQUIRE_TIMESTAMP },
+       { 32,  0, 0x28,  0, NV10_PFIFO_CACHE1_ACQUIRE_TIMEOUT },
+       { 32,  0, 0x2c,  0, NV10_PFIFO_CACHE1_SEMAPHORE },
+       { 32,  0, 0x30,  0, NV10_PFIFO_CACHE1_DMA_SUBROUTINE },
+       {}
+};
+
+/*******************************************************************************
+ * FIFO channel objects
+ ******************************************************************************/
+
+static int
+nv17_fifo_chan_ctor(struct nvkm_object *parent,
+                   struct nvkm_object *engine,
+                   struct nvkm_oclass *oclass, void *data, u32 size,
+                   struct nvkm_object **pobject)
+{
+       union {
+               struct nv03_channel_dma_v0 v0;
+       } *args = data;
+       struct nv04_fifo_priv *priv = (void *)engine;
+       struct nv04_fifo_chan *chan;
+       int ret;
+
+       nv_ioctl(parent, "create channel dma size %d\n", size);
+       if (nvif_unpack(args->v0, 0, 0, false)) {
+               nv_ioctl(parent, "create channel dma vers %d pushbuf %08x "
+                                "offset %016llx\n", args->v0.version,
+                        args->v0.pushbuf, args->v0.offset);
+       } else
+               return ret;
+
+       ret = nvkm_fifo_channel_create(parent, engine, oclass, 0, 0x800000,
+                                      0x10000, args->v0.pushbuf,
+                                      (1ULL << NVDEV_ENGINE_DMAOBJ) |
+                                      (1ULL << NVDEV_ENGINE_SW) |
+                                      (1ULL << NVDEV_ENGINE_GR) |
+                                      (1ULL << NVDEV_ENGINE_MPEG), /* NV31- */
+                                      &chan);
+       *pobject = nv_object(chan);
+       if (ret)
+               return ret;
+
+       args->v0.chid = chan->base.chid;
+
+       nv_parent(chan)->object_attach = nv04_fifo_object_attach;
+       nv_parent(chan)->object_detach = nv04_fifo_object_detach;
+       nv_parent(chan)->context_attach = nv04_fifo_context_attach;
+       chan->ramfc = chan->base.chid * 64;
+
+       nv_wo32(priv->ramfc, chan->ramfc + 0x00, args->v0.offset);
+       nv_wo32(priv->ramfc, chan->ramfc + 0x04, args->v0.offset);
+       nv_wo32(priv->ramfc, chan->ramfc + 0x0c, chan->base.pushgpu->addr >> 4);
+       nv_wo32(priv->ramfc, chan->ramfc + 0x14,
+                            NV_PFIFO_CACHE1_DMA_FETCH_TRIG_128_BYTES |
+                            NV_PFIFO_CACHE1_DMA_FETCH_SIZE_128_BYTES |
+#ifdef __BIG_ENDIAN
+                            NV_PFIFO_CACHE1_BIG_ENDIAN |
+#endif
+                            NV_PFIFO_CACHE1_DMA_FETCH_MAX_REQS_8);
+       return 0;
+}
+
+static struct nvkm_ofuncs
+nv17_fifo_ofuncs = {
+       .ctor = nv17_fifo_chan_ctor,
+       .dtor = nv04_fifo_chan_dtor,
+       .init = nv04_fifo_chan_init,
+       .fini = nv04_fifo_chan_fini,
+       .map  = _nvkm_fifo_channel_map,
+       .rd32 = _nvkm_fifo_channel_rd32,
+       .wr32 = _nvkm_fifo_channel_wr32,
+       .ntfy = _nvkm_fifo_channel_ntfy
+};
+
+static struct nvkm_oclass
+nv17_fifo_sclass[] = {
+       { NV17_CHANNEL_DMA, &nv17_fifo_ofuncs },
+       {}
+};
+
+/*******************************************************************************
+ * FIFO context - basically just the instmem reserved for the channel
+ ******************************************************************************/
+
+static struct nvkm_oclass
+nv17_fifo_cclass = {
+       .handle = NV_ENGCTX(FIFO, 0x17),
+       .ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = nv04_fifo_context_ctor,
+               .dtor = _nvkm_fifo_context_dtor,
+               .init = _nvkm_fifo_context_init,
+               .fini = _nvkm_fifo_context_fini,
+               .rd32 = _nvkm_fifo_context_rd32,
+               .wr32 = _nvkm_fifo_context_wr32,
+       },
+};
+
+/*******************************************************************************
+ * PFIFO engine
+ ******************************************************************************/
+
+static int
+nv17_fifo_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+              struct nvkm_oclass *oclass, void *data, u32 size,
+              struct nvkm_object **pobject)
+{
+       struct nv04_instmem_priv *imem = nv04_instmem(parent);
+       struct nv04_fifo_priv *priv;
+       int ret;
+
+       ret = nvkm_fifo_create(parent, engine, oclass, 0, 31, &priv);
+       *pobject = nv_object(priv);
+       if (ret)
+               return ret;
+
+       nvkm_ramht_ref(imem->ramht, &priv->ramht);
+       nvkm_gpuobj_ref(imem->ramro, &priv->ramro);
+       nvkm_gpuobj_ref(imem->ramfc, &priv->ramfc);
+
+       nv_subdev(priv)->unit = 0x00000100;
+       nv_subdev(priv)->intr = nv04_fifo_intr;
+       nv_engine(priv)->cclass = &nv17_fifo_cclass;
+       nv_engine(priv)->sclass = nv17_fifo_sclass;
+       priv->base.pause = nv04_fifo_pause;
+       priv->base.start = nv04_fifo_start;
+       priv->ramfc_desc = nv17_ramfc;
+       return 0;
+}
+
+static int
+nv17_fifo_init(struct nvkm_object *object)
+{
+       struct nv04_fifo_priv *priv = (void *)object;
+       int ret;
+
+       ret = nvkm_fifo_init(&priv->base);
+       if (ret)
+               return ret;
+
+       nv_wr32(priv, NV04_PFIFO_DELAY_0, 0x000000ff);
+       nv_wr32(priv, NV04_PFIFO_DMA_TIMESLICE, 0x0101ffff);
+
+       nv_wr32(priv, NV03_PFIFO_RAMHT, (0x03 << 24) /* search 128 */ |
+                                      ((priv->ramht->bits - 9) << 16) |
+                                       (priv->ramht->gpuobj.addr >> 8));
+       nv_wr32(priv, NV03_PFIFO_RAMRO, priv->ramro->addr >> 8);
+       nv_wr32(priv, NV03_PFIFO_RAMFC, priv->ramfc->addr >> 8 | 0x00010000);
+
+       nv_wr32(priv, NV03_PFIFO_CACHE1_PUSH1, priv->base.max);
+
+       nv_wr32(priv, NV03_PFIFO_INTR_0, 0xffffffff);
+       nv_wr32(priv, NV03_PFIFO_INTR_EN_0, 0xffffffff);
+
+       nv_wr32(priv, NV03_PFIFO_CACHE1_PUSH0, 1);
+       nv_wr32(priv, NV04_PFIFO_CACHE1_PULL0, 1);
+       nv_wr32(priv, NV03_PFIFO_CACHES, 1);
+       return 0;
+}
+
+struct nvkm_oclass *
+nv17_fifo_oclass = &(struct nvkm_oclass) {
+       .handle = NV_ENGINE(FIFO, 0x17),
+       .ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = nv17_fifo_ctor,
+               .dtor = nv04_fifo_dtor,
+               .init = nv17_fifo_init,
+               .fini = _nvkm_fifo_fini,
+       },
+};
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/fifo/nv40.c b/drivers/gpu/drm/nouveau/nvkm/engine/fifo/nv40.c
new file mode 100644 (file)
index 0000000..5bfc962
--- /dev/null
@@ -0,0 +1,356 @@
+/*
+ * Copyright 2012 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 "nv04.h"
+
+#include <core/client.h>
+#include <core/device.h>
+#include <core/engctx.h>
+#include <core/ramht.h>
+#include <subdev/fb.h>
+#include <subdev/instmem/nv04.h>
+
+#include <nvif/class.h>
+#include <nvif/unpack.h>
+
+static struct ramfc_desc
+nv40_ramfc[] = {
+       { 32,  0, 0x00,  0, NV04_PFIFO_CACHE1_DMA_PUT },
+       { 32,  0, 0x04,  0, NV04_PFIFO_CACHE1_DMA_GET },
+       { 32,  0, 0x08,  0, NV10_PFIFO_CACHE1_REF_CNT },
+       { 32,  0, 0x0c,  0, NV04_PFIFO_CACHE1_DMA_INSTANCE },
+       { 32,  0, 0x10,  0, NV04_PFIFO_CACHE1_DMA_DCOUNT },
+       { 32,  0, 0x14,  0, NV04_PFIFO_CACHE1_DMA_STATE },
+       { 28,  0, 0x18,  0, NV04_PFIFO_CACHE1_DMA_FETCH },
+       {  2, 28, 0x18, 28, 0x002058 },
+       { 32,  0, 0x1c,  0, NV04_PFIFO_CACHE1_ENGINE },
+       { 32,  0, 0x20,  0, NV04_PFIFO_CACHE1_PULL1 },
+       { 32,  0, 0x24,  0, NV10_PFIFO_CACHE1_ACQUIRE_VALUE },
+       { 32,  0, 0x28,  0, NV10_PFIFO_CACHE1_ACQUIRE_TIMESTAMP },
+       { 32,  0, 0x2c,  0, NV10_PFIFO_CACHE1_ACQUIRE_TIMEOUT },
+       { 32,  0, 0x30,  0, NV10_PFIFO_CACHE1_SEMAPHORE },
+       { 32,  0, 0x34,  0, NV10_PFIFO_CACHE1_DMA_SUBROUTINE },
+       { 32,  0, 0x38,  0, NV40_PFIFO_GRCTX_INSTANCE },
+       { 17,  0, 0x3c,  0, NV04_PFIFO_DMA_TIMESLICE },
+       { 32,  0, 0x40,  0, 0x0032e4 },
+       { 32,  0, 0x44,  0, 0x0032e8 },
+       { 32,  0, 0x4c,  0, 0x002088 },
+       { 32,  0, 0x50,  0, 0x003300 },
+       { 32,  0, 0x54,  0, 0x00330c },
+       {}
+};
+
+/*******************************************************************************
+ * FIFO channel objects
+ ******************************************************************************/
+
+static int
+nv40_fifo_object_attach(struct nvkm_object *parent,
+                       struct nvkm_object *object, u32 handle)
+{
+       struct nv04_fifo_priv *priv = (void *)parent->engine;
+       struct nv04_fifo_chan *chan = (void *)parent;
+       u32 context, chid = chan->base.chid;
+       int ret;
+
+       if (nv_iclass(object, NV_GPUOBJ_CLASS))
+               context = nv_gpuobj(object)->addr >> 4;
+       else
+               context = 0x00000004; /* just non-zero */
+
+       switch (nv_engidx(object->engine)) {
+       case NVDEV_ENGINE_DMAOBJ:
+       case NVDEV_ENGINE_SW:
+               context |= 0x00000000;
+               break;
+       case NVDEV_ENGINE_GR:
+               context |= 0x00100000;
+               break;
+       case NVDEV_ENGINE_MPEG:
+               context |= 0x00200000;
+               break;
+       default:
+               return -EINVAL;
+       }
+
+       context |= chid << 23;
+
+       mutex_lock(&nv_subdev(priv)->mutex);
+       ret = nvkm_ramht_insert(priv->ramht, chid, handle, context);
+       mutex_unlock(&nv_subdev(priv)->mutex);
+       return ret;
+}
+
+static int
+nv40_fifo_context_attach(struct nvkm_object *parent, struct nvkm_object *engctx)
+{
+       struct nv04_fifo_priv *priv = (void *)parent->engine;
+       struct nv04_fifo_chan *chan = (void *)parent;
+       unsigned long flags;
+       u32 reg, ctx;
+
+       switch (nv_engidx(engctx->engine)) {
+       case NVDEV_ENGINE_SW:
+               return 0;
+       case NVDEV_ENGINE_GR:
+               reg = 0x32e0;
+               ctx = 0x38;
+               break;
+       case NVDEV_ENGINE_MPEG:
+               reg = 0x330c;
+               ctx = 0x54;
+               break;
+       default:
+               return -EINVAL;
+       }
+
+       spin_lock_irqsave(&priv->base.lock, flags);
+       nv_engctx(engctx)->addr = nv_gpuobj(engctx)->addr >> 4;
+       nv_mask(priv, 0x002500, 0x00000001, 0x00000000);
+
+       if ((nv_rd32(priv, 0x003204) & priv->base.max) == chan->base.chid)
+               nv_wr32(priv, reg, nv_engctx(engctx)->addr);
+       nv_wo32(priv->ramfc, chan->ramfc + ctx, nv_engctx(engctx)->addr);
+
+       nv_mask(priv, 0x002500, 0x00000001, 0x00000001);
+       spin_unlock_irqrestore(&priv->base.lock, flags);
+       return 0;
+}
+
+static int
+nv40_fifo_context_detach(struct nvkm_object *parent, bool suspend,
+                        struct nvkm_object *engctx)
+{
+       struct nv04_fifo_priv *priv = (void *)parent->engine;
+       struct nv04_fifo_chan *chan = (void *)parent;
+       unsigned long flags;
+       u32 reg, ctx;
+
+       switch (nv_engidx(engctx->engine)) {
+       case NVDEV_ENGINE_SW:
+               return 0;
+       case NVDEV_ENGINE_GR:
+               reg = 0x32e0;
+               ctx = 0x38;
+               break;
+       case NVDEV_ENGINE_MPEG:
+               reg = 0x330c;
+               ctx = 0x54;
+               break;
+       default:
+               return -EINVAL;
+       }
+
+       spin_lock_irqsave(&priv->base.lock, flags);
+       nv_mask(priv, 0x002500, 0x00000001, 0x00000000);
+
+       if ((nv_rd32(priv, 0x003204) & priv->base.max) == chan->base.chid)
+               nv_wr32(priv, reg, 0x00000000);
+       nv_wo32(priv->ramfc, chan->ramfc + ctx, 0x00000000);
+
+       nv_mask(priv, 0x002500, 0x00000001, 0x00000001);
+       spin_unlock_irqrestore(&priv->base.lock, flags);
+       return 0;
+}
+
+static int
+nv40_fifo_chan_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+                   struct nvkm_oclass *oclass, void *data, u32 size,
+                   struct nvkm_object **pobject)
+{
+       union {
+               struct nv03_channel_dma_v0 v0;
+       } *args = data;
+       struct nv04_fifo_priv *priv = (void *)engine;
+       struct nv04_fifo_chan *chan;
+       int ret;
+
+       nv_ioctl(parent, "create channel dma size %d\n", size);
+       if (nvif_unpack(args->v0, 0, 0, false)) {
+               nv_ioctl(parent, "create channel dma vers %d pushbuf %08x "
+                                "offset %016llx\n", args->v0.version,
+                        args->v0.pushbuf, args->v0.offset);
+       } else
+               return ret;
+
+       ret = nvkm_fifo_channel_create(parent, engine, oclass, 0, 0xc00000,
+                                      0x1000, args->v0.pushbuf,
+                                      (1ULL << NVDEV_ENGINE_DMAOBJ) |
+                                      (1ULL << NVDEV_ENGINE_SW) |
+                                      (1ULL << NVDEV_ENGINE_GR) |
+                                      (1ULL << NVDEV_ENGINE_MPEG), &chan);
+       *pobject = nv_object(chan);
+       if (ret)
+               return ret;
+
+       args->v0.chid = chan->base.chid;
+
+       nv_parent(chan)->context_attach = nv40_fifo_context_attach;
+       nv_parent(chan)->context_detach = nv40_fifo_context_detach;
+       nv_parent(chan)->object_attach = nv40_fifo_object_attach;
+       nv_parent(chan)->object_detach = nv04_fifo_object_detach;
+       chan->ramfc = chan->base.chid * 128;
+
+       nv_wo32(priv->ramfc, chan->ramfc + 0x00, args->v0.offset);
+       nv_wo32(priv->ramfc, chan->ramfc + 0x04, args->v0.offset);
+       nv_wo32(priv->ramfc, chan->ramfc + 0x0c, chan->base.pushgpu->addr >> 4);
+       nv_wo32(priv->ramfc, chan->ramfc + 0x18, 0x30000000 |
+                            NV_PFIFO_CACHE1_DMA_FETCH_TRIG_128_BYTES |
+                            NV_PFIFO_CACHE1_DMA_FETCH_SIZE_128_BYTES |
+#ifdef __BIG_ENDIAN
+                            NV_PFIFO_CACHE1_BIG_ENDIAN |
+#endif
+                            NV_PFIFO_CACHE1_DMA_FETCH_MAX_REQS_8);
+       nv_wo32(priv->ramfc, chan->ramfc + 0x3c, 0x0001ffff);
+       return 0;
+}
+
+static struct nvkm_ofuncs
+nv40_fifo_ofuncs = {
+       .ctor = nv40_fifo_chan_ctor,
+       .dtor = nv04_fifo_chan_dtor,
+       .init = nv04_fifo_chan_init,
+       .fini = nv04_fifo_chan_fini,
+       .map  = _nvkm_fifo_channel_map,
+       .rd32 = _nvkm_fifo_channel_rd32,
+       .wr32 = _nvkm_fifo_channel_wr32,
+       .ntfy = _nvkm_fifo_channel_ntfy
+};
+
+static struct nvkm_oclass
+nv40_fifo_sclass[] = {
+       { NV40_CHANNEL_DMA, &nv40_fifo_ofuncs },
+       {}
+};
+
+/*******************************************************************************
+ * FIFO context - basically just the instmem reserved for the channel
+ ******************************************************************************/
+
+static struct nvkm_oclass
+nv40_fifo_cclass = {
+       .handle = NV_ENGCTX(FIFO, 0x40),
+       .ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = nv04_fifo_context_ctor,
+               .dtor = _nvkm_fifo_context_dtor,
+               .init = _nvkm_fifo_context_init,
+               .fini = _nvkm_fifo_context_fini,
+               .rd32 = _nvkm_fifo_context_rd32,
+               .wr32 = _nvkm_fifo_context_wr32,
+       },
+};
+
+/*******************************************************************************
+ * PFIFO engine
+ ******************************************************************************/
+
+static int
+nv40_fifo_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+              struct nvkm_oclass *oclass, void *data, u32 size,
+              struct nvkm_object **pobject)
+{
+       struct nv04_instmem_priv *imem = nv04_instmem(parent);
+       struct nv04_fifo_priv *priv;
+       int ret;
+
+       ret = nvkm_fifo_create(parent, engine, oclass, 0, 31, &priv);
+       *pobject = nv_object(priv);
+       if (ret)
+               return ret;
+
+       nvkm_ramht_ref(imem->ramht, &priv->ramht);
+       nvkm_gpuobj_ref(imem->ramro, &priv->ramro);
+       nvkm_gpuobj_ref(imem->ramfc, &priv->ramfc);
+
+       nv_subdev(priv)->unit = 0x00000100;
+       nv_subdev(priv)->intr = nv04_fifo_intr;
+       nv_engine(priv)->cclass = &nv40_fifo_cclass;
+       nv_engine(priv)->sclass = nv40_fifo_sclass;
+       priv->base.pause = nv04_fifo_pause;
+       priv->base.start = nv04_fifo_start;
+       priv->ramfc_desc = nv40_ramfc;
+       return 0;
+}
+
+static int
+nv40_fifo_init(struct nvkm_object *object)
+{
+       struct nv04_fifo_priv *priv = (void *)object;
+       struct nvkm_fb *pfb = nvkm_fb(object);
+       int ret;
+
+       ret = nvkm_fifo_init(&priv->base);
+       if (ret)
+               return ret;
+
+       nv_wr32(priv, 0x002040, 0x000000ff);
+       nv_wr32(priv, 0x002044, 0x2101ffff);
+       nv_wr32(priv, 0x002058, 0x00000001);
+
+       nv_wr32(priv, NV03_PFIFO_RAMHT, (0x03 << 24) /* search 128 */ |
+                                      ((priv->ramht->bits - 9) << 16) |
+                                       (priv->ramht->gpuobj.addr >> 8));
+       nv_wr32(priv, NV03_PFIFO_RAMRO, priv->ramro->addr >> 8);
+
+       switch (nv_device(priv)->chipset) {
+       case 0x47:
+       case 0x49:
+       case 0x4b:
+               nv_wr32(priv, 0x002230, 0x00000001);
+       case 0x40:
+       case 0x41:
+       case 0x42:
+       case 0x43:
+       case 0x45:
+       case 0x48:
+               nv_wr32(priv, 0x002220, 0x00030002);
+               break;
+       default:
+               nv_wr32(priv, 0x002230, 0x00000000);
+               nv_wr32(priv, 0x002220, ((pfb->ram->size - 512 * 1024 +
+                                        priv->ramfc->addr) >> 16) |
+                                       0x00030000);
+               break;
+       }
+
+       nv_wr32(priv, NV03_PFIFO_CACHE1_PUSH1, priv->base.max);
+
+       nv_wr32(priv, NV03_PFIFO_INTR_0, 0xffffffff);
+       nv_wr32(priv, NV03_PFIFO_INTR_EN_0, 0xffffffff);
+
+       nv_wr32(priv, NV03_PFIFO_CACHE1_PUSH0, 1);
+       nv_wr32(priv, NV04_PFIFO_CACHE1_PULL0, 1);
+       nv_wr32(priv, NV03_PFIFO_CACHES, 1);
+       return 0;
+}
+
+struct nvkm_oclass *
+nv40_fifo_oclass = &(struct nvkm_oclass) {
+       .handle = NV_ENGINE(FIFO, 0x40),
+       .ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = nv40_fifo_ctor,
+               .dtor = nv04_fifo_dtor,
+               .init = nv40_fifo_init,
+               .fini = _nvkm_fifo_fini,
+       },
+};
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/fifo/nv50.c b/drivers/gpu/drm/nouveau/nvkm/engine/fifo/nv50.c
new file mode 100644 (file)
index 0000000..f25f0fd
--- /dev/null
@@ -0,0 +1,534 @@
+/*
+ * Copyright 2012 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 "nv50.h"
+#include "nv04.h"
+
+#include <core/client.h>
+#include <core/engctx.h>
+#include <core/ramht.h>
+#include <subdev/bar.h>
+#include <subdev/mmu.h>
+#include <subdev/timer.h>
+
+#include <nvif/class.h>
+#include <nvif/unpack.h>
+
+/*******************************************************************************
+ * FIFO channel objects
+ ******************************************************************************/
+
+static void
+nv50_fifo_playlist_update_locked(struct nv50_fifo_priv *priv)
+{
+       struct nvkm_bar *bar = nvkm_bar(priv);
+       struct nvkm_gpuobj *cur;
+       int i, p;
+
+       cur = priv->playlist[priv->cur_playlist];
+       priv->cur_playlist = !priv->cur_playlist;
+
+       for (i = priv->base.min, p = 0; i < priv->base.max; i++) {
+               if (nv_rd32(priv, 0x002600 + (i * 4)) & 0x80000000)
+                       nv_wo32(cur, p++ * 4, i);
+       }
+
+       bar->flush(bar);
+
+       nv_wr32(priv, 0x0032f4, cur->addr >> 12);
+       nv_wr32(priv, 0x0032ec, p);
+       nv_wr32(priv, 0x002500, 0x00000101);
+}
+
+void
+nv50_fifo_playlist_update(struct nv50_fifo_priv *priv)
+{
+       mutex_lock(&nv_subdev(priv)->mutex);
+       nv50_fifo_playlist_update_locked(priv);
+       mutex_unlock(&nv_subdev(priv)->mutex);
+}
+
+static int
+nv50_fifo_context_attach(struct nvkm_object *parent, struct nvkm_object *object)
+{
+       struct nvkm_bar *bar = nvkm_bar(parent);
+       struct nv50_fifo_base *base = (void *)parent->parent;
+       struct nvkm_gpuobj *ectx = (void *)object;
+       u64 limit = ectx->addr + ectx->size - 1;
+       u64 start = ectx->addr;
+       u32 addr;
+
+       switch (nv_engidx(object->engine)) {
+       case NVDEV_ENGINE_SW   : return 0;
+       case NVDEV_ENGINE_GR   : addr = 0x0000; break;
+       case NVDEV_ENGINE_MPEG : addr = 0x0060; break;
+       default:
+               return -EINVAL;
+       }
+
+       nv_engctx(ectx)->addr = nv_gpuobj(base)->addr >> 12;
+       nv_wo32(base->eng, addr + 0x00, 0x00190000);
+       nv_wo32(base->eng, addr + 0x04, lower_32_bits(limit));
+       nv_wo32(base->eng, addr + 0x08, lower_32_bits(start));
+       nv_wo32(base->eng, addr + 0x0c, upper_32_bits(limit) << 24 |
+                                       upper_32_bits(start));
+       nv_wo32(base->eng, addr + 0x10, 0x00000000);
+       nv_wo32(base->eng, addr + 0x14, 0x00000000);
+       bar->flush(bar);
+       return 0;
+}
+
+static int
+nv50_fifo_context_detach(struct nvkm_object *parent, bool suspend,
+                        struct nvkm_object *object)
+{
+       struct nvkm_bar *bar = nvkm_bar(parent);
+       struct nv50_fifo_priv *priv = (void *)parent->engine;
+       struct nv50_fifo_base *base = (void *)parent->parent;
+       struct nv50_fifo_chan *chan = (void *)parent;
+       u32 addr, me;
+       int ret = 0;
+
+       switch (nv_engidx(object->engine)) {
+       case NVDEV_ENGINE_SW   : return 0;
+       case NVDEV_ENGINE_GR   : addr = 0x0000; break;
+       case NVDEV_ENGINE_MPEG : addr = 0x0060; break;
+       default:
+               return -EINVAL;
+       }
+
+       /* HW bug workaround:
+        *
+        * PFIFO will hang forever if the connected engines don't report
+        * that they've processed the context switch request.
+        *
+        * In order for the kickoff to work, we need to ensure all the
+        * connected engines are in a state where they can answer.
+        *
+        * Newer chipsets don't seem to suffer from this issue, and well,
+        * there's also a "ignore these engines" bitmask reg we can use
+        * if we hit the issue there..
+        */
+       me = nv_mask(priv, 0x00b860, 0x00000001, 0x00000001);
+
+       /* do the kickoff... */
+       nv_wr32(priv, 0x0032fc, nv_gpuobj(base)->addr >> 12);
+       if (!nv_wait_ne(priv, 0x0032fc, 0xffffffff, 0xffffffff)) {
+               nv_error(priv, "channel %d [%s] unload timeout\n",
+                        chan->base.chid, nvkm_client_name(chan));
+               if (suspend)
+                       ret = -EBUSY;
+       }
+       nv_wr32(priv, 0x00b860, me);
+
+       if (ret == 0) {
+               nv_wo32(base->eng, addr + 0x00, 0x00000000);
+               nv_wo32(base->eng, addr + 0x04, 0x00000000);
+               nv_wo32(base->eng, addr + 0x08, 0x00000000);
+               nv_wo32(base->eng, addr + 0x0c, 0x00000000);
+               nv_wo32(base->eng, addr + 0x10, 0x00000000);
+               nv_wo32(base->eng, addr + 0x14, 0x00000000);
+               bar->flush(bar);
+       }
+
+       return ret;
+}
+
+static int
+nv50_fifo_object_attach(struct nvkm_object *parent,
+                       struct nvkm_object *object, u32 handle)
+{
+       struct nv50_fifo_chan *chan = (void *)parent;
+       u32 context;
+
+       if (nv_iclass(object, NV_GPUOBJ_CLASS))
+               context = nv_gpuobj(object)->node->offset >> 4;
+       else
+               context = 0x00000004; /* just non-zero */
+
+       switch (nv_engidx(object->engine)) {
+       case NVDEV_ENGINE_DMAOBJ:
+       case NVDEV_ENGINE_SW    : context |= 0x00000000; break;
+       case NVDEV_ENGINE_GR    : context |= 0x00100000; break;
+       case NVDEV_ENGINE_MPEG  : context |= 0x00200000; break;
+       default:
+               return -EINVAL;
+       }
+
+       return nvkm_ramht_insert(chan->ramht, 0, handle, context);
+}
+
+void
+nv50_fifo_object_detach(struct nvkm_object *parent, int cookie)
+{
+       struct nv50_fifo_chan *chan = (void *)parent;
+       nvkm_ramht_remove(chan->ramht, cookie);
+}
+
+static int
+nv50_fifo_chan_ctor_dma(struct nvkm_object *parent, struct nvkm_object *engine,
+                       struct nvkm_oclass *oclass, void *data, u32 size,
+                       struct nvkm_object **pobject)
+{
+       union {
+               struct nv03_channel_dma_v0 v0;
+       } *args = data;
+       struct nvkm_bar *bar = nvkm_bar(parent);
+       struct nv50_fifo_base *base = (void *)parent;
+       struct nv50_fifo_chan *chan;
+       int ret;
+
+       nv_ioctl(parent, "create channel dma size %d\n", size);
+       if (nvif_unpack(args->v0, 0, 0, false)) {
+               nv_ioctl(parent, "create channel dma vers %d pushbuf %08x "
+                                "offset %016llx\n", args->v0.version,
+                        args->v0.pushbuf, args->v0.offset);
+       } else
+               return ret;
+
+       ret = nvkm_fifo_channel_create(parent, engine, oclass, 0, 0xc00000,
+                                      0x2000, args->v0.pushbuf,
+                                      (1ULL << NVDEV_ENGINE_DMAOBJ) |
+                                      (1ULL << NVDEV_ENGINE_SW) |
+                                      (1ULL << NVDEV_ENGINE_GR) |
+                                      (1ULL << NVDEV_ENGINE_MPEG), &chan);
+       *pobject = nv_object(chan);
+       if (ret)
+               return ret;
+
+       args->v0.chid = chan->base.chid;
+
+       nv_parent(chan)->context_attach = nv50_fifo_context_attach;
+       nv_parent(chan)->context_detach = nv50_fifo_context_detach;
+       nv_parent(chan)->object_attach = nv50_fifo_object_attach;
+       nv_parent(chan)->object_detach = nv50_fifo_object_detach;
+
+       ret = nvkm_ramht_new(nv_object(chan), nv_object(chan), 0x8000, 16,
+                            &chan->ramht);
+       if (ret)
+               return ret;
+
+       nv_wo32(base->ramfc, 0x08, lower_32_bits(args->v0.offset));
+       nv_wo32(base->ramfc, 0x0c, upper_32_bits(args->v0.offset));
+       nv_wo32(base->ramfc, 0x10, lower_32_bits(args->v0.offset));
+       nv_wo32(base->ramfc, 0x14, upper_32_bits(args->v0.offset));
+       nv_wo32(base->ramfc, 0x3c, 0x003f6078);
+       nv_wo32(base->ramfc, 0x44, 0x01003fff);
+       nv_wo32(base->ramfc, 0x48, chan->base.pushgpu->node->offset >> 4);
+       nv_wo32(base->ramfc, 0x4c, 0xffffffff);
+       nv_wo32(base->ramfc, 0x60, 0x7fffffff);
+       nv_wo32(base->ramfc, 0x78, 0x00000000);
+       nv_wo32(base->ramfc, 0x7c, 0x30000001);
+       nv_wo32(base->ramfc, 0x80, ((chan->ramht->bits - 9) << 27) |
+                                  (4 << 24) /* SEARCH_FULL */ |
+                                  (chan->ramht->gpuobj.node->offset >> 4));
+       bar->flush(bar);
+       return 0;
+}
+
+static int
+nv50_fifo_chan_ctor_ind(struct nvkm_object *parent, struct nvkm_object *engine,
+                       struct nvkm_oclass *oclass, void *data, u32 size,
+                       struct nvkm_object **pobject)
+{
+       union {
+               struct nv50_channel_gpfifo_v0 v0;
+       } *args = data;
+       struct nvkm_bar *bar = nvkm_bar(parent);
+       struct nv50_fifo_base *base = (void *)parent;
+       struct nv50_fifo_chan *chan;
+       u64 ioffset, ilength;
+       int ret;
+
+       nv_ioctl(parent, "create channel gpfifo size %d\n", size);
+       if (nvif_unpack(args->v0, 0, 0, false)) {
+               nv_ioctl(parent, "create channel gpfifo vers %d pushbuf %08x "
+                                "ioffset %016llx ilength %08x\n",
+                        args->v0.version, args->v0.pushbuf, args->v0.ioffset,
+                        args->v0.ilength);
+       } else
+               return ret;
+
+       ret = nvkm_fifo_channel_create(parent, engine, oclass, 0, 0xc00000,
+                                      0x2000, args->v0.pushbuf,
+                                      (1ULL << NVDEV_ENGINE_DMAOBJ) |
+                                      (1ULL << NVDEV_ENGINE_SW) |
+                                      (1ULL << NVDEV_ENGINE_GR) |
+                                      (1ULL << NVDEV_ENGINE_MPEG), &chan);
+       *pobject = nv_object(chan);
+       if (ret)
+               return ret;
+
+       args->v0.chid = chan->base.chid;
+
+       nv_parent(chan)->context_attach = nv50_fifo_context_attach;
+       nv_parent(chan)->context_detach = nv50_fifo_context_detach;
+       nv_parent(chan)->object_attach = nv50_fifo_object_attach;
+       nv_parent(chan)->object_detach = nv50_fifo_object_detach;
+
+       ret = nvkm_ramht_new(nv_object(chan), nv_object(chan), 0x8000, 16,
+                            &chan->ramht);
+       if (ret)
+               return ret;
+
+       ioffset = args->v0.ioffset;
+       ilength = order_base_2(args->v0.ilength / 8);
+
+       nv_wo32(base->ramfc, 0x3c, 0x403f6078);
+       nv_wo32(base->ramfc, 0x44, 0x01003fff);
+       nv_wo32(base->ramfc, 0x48, chan->base.pushgpu->node->offset >> 4);
+       nv_wo32(base->ramfc, 0x50, lower_32_bits(ioffset));
+       nv_wo32(base->ramfc, 0x54, upper_32_bits(ioffset) | (ilength << 16));
+       nv_wo32(base->ramfc, 0x60, 0x7fffffff);
+       nv_wo32(base->ramfc, 0x78, 0x00000000);
+       nv_wo32(base->ramfc, 0x7c, 0x30000001);
+       nv_wo32(base->ramfc, 0x80, ((chan->ramht->bits - 9) << 27) |
+                                  (4 << 24) /* SEARCH_FULL */ |
+                                  (chan->ramht->gpuobj.node->offset >> 4));
+       bar->flush(bar);
+       return 0;
+}
+
+void
+nv50_fifo_chan_dtor(struct nvkm_object *object)
+{
+       struct nv50_fifo_chan *chan = (void *)object;
+       nvkm_ramht_ref(NULL, &chan->ramht);
+       nvkm_fifo_channel_destroy(&chan->base);
+}
+
+static int
+nv50_fifo_chan_init(struct nvkm_object *object)
+{
+       struct nv50_fifo_priv *priv = (void *)object->engine;
+       struct nv50_fifo_base *base = (void *)object->parent;
+       struct nv50_fifo_chan *chan = (void *)object;
+       struct nvkm_gpuobj *ramfc = base->ramfc;
+       u32 chid = chan->base.chid;
+       int ret;
+
+       ret = nvkm_fifo_channel_init(&chan->base);
+       if (ret)
+               return ret;
+
+       nv_wr32(priv, 0x002600 + (chid * 4), 0x80000000 | ramfc->addr >> 12);
+       nv50_fifo_playlist_update(priv);
+       return 0;
+}
+
+int
+nv50_fifo_chan_fini(struct nvkm_object *object, bool suspend)
+{
+       struct nv50_fifo_priv *priv = (void *)object->engine;
+       struct nv50_fifo_chan *chan = (void *)object;
+       u32 chid = chan->base.chid;
+
+       /* remove channel from playlist, fifo will unload context */
+       nv_mask(priv, 0x002600 + (chid * 4), 0x80000000, 0x00000000);
+       nv50_fifo_playlist_update(priv);
+       nv_wr32(priv, 0x002600 + (chid * 4), 0x00000000);
+
+       return nvkm_fifo_channel_fini(&chan->base, suspend);
+}
+
+static struct nvkm_ofuncs
+nv50_fifo_ofuncs_dma = {
+       .ctor = nv50_fifo_chan_ctor_dma,
+       .dtor = nv50_fifo_chan_dtor,
+       .init = nv50_fifo_chan_init,
+       .fini = nv50_fifo_chan_fini,
+       .map  = _nvkm_fifo_channel_map,
+       .rd32 = _nvkm_fifo_channel_rd32,
+       .wr32 = _nvkm_fifo_channel_wr32,
+       .ntfy = _nvkm_fifo_channel_ntfy
+};
+
+static struct nvkm_ofuncs
+nv50_fifo_ofuncs_ind = {
+       .ctor = nv50_fifo_chan_ctor_ind,
+       .dtor = nv50_fifo_chan_dtor,
+       .init = nv50_fifo_chan_init,
+       .fini = nv50_fifo_chan_fini,
+       .map  = _nvkm_fifo_channel_map,
+       .rd32 = _nvkm_fifo_channel_rd32,
+       .wr32 = _nvkm_fifo_channel_wr32,
+       .ntfy = _nvkm_fifo_channel_ntfy
+};
+
+static struct nvkm_oclass
+nv50_fifo_sclass[] = {
+       { NV50_CHANNEL_DMA, &nv50_fifo_ofuncs_dma },
+       { NV50_CHANNEL_GPFIFO, &nv50_fifo_ofuncs_ind },
+       {}
+};
+
+/*******************************************************************************
+ * FIFO context - basically just the instmem reserved for the channel
+ ******************************************************************************/
+
+static int
+nv50_fifo_context_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+                      struct nvkm_oclass *oclass, void *data, u32 size,
+                      struct nvkm_object **pobject)
+{
+       struct nv50_fifo_base *base;
+       int ret;
+
+       ret = nvkm_fifo_context_create(parent, engine, oclass, NULL, 0x10000,
+                                      0x1000, NVOBJ_FLAG_HEAP, &base);
+       *pobject = nv_object(base);
+       if (ret)
+               return ret;
+
+       ret = nvkm_gpuobj_new(nv_object(base), nv_object(base), 0x0200,
+                             0x1000, NVOBJ_FLAG_ZERO_ALLOC, &base->ramfc);
+       if (ret)
+               return ret;
+
+       ret = nvkm_gpuobj_new(nv_object(base), nv_object(base), 0x1200, 0,
+                             NVOBJ_FLAG_ZERO_ALLOC, &base->eng);
+       if (ret)
+               return ret;
+
+       ret = nvkm_gpuobj_new(nv_object(base), nv_object(base), 0x4000, 0, 0,
+                             &base->pgd);
+       if (ret)
+               return ret;
+
+       ret = nvkm_vm_ref(nvkm_client(parent)->vm, &base->vm, base->pgd);
+       if (ret)
+               return ret;
+
+       return 0;
+}
+
+void
+nv50_fifo_context_dtor(struct nvkm_object *object)
+{
+       struct nv50_fifo_base *base = (void *)object;
+       nvkm_vm_ref(NULL, &base->vm, base->pgd);
+       nvkm_gpuobj_ref(NULL, &base->pgd);
+       nvkm_gpuobj_ref(NULL, &base->eng);
+       nvkm_gpuobj_ref(NULL, &base->ramfc);
+       nvkm_gpuobj_ref(NULL, &base->cache);
+       nvkm_fifo_context_destroy(&base->base);
+}
+
+static struct nvkm_oclass
+nv50_fifo_cclass = {
+       .handle = NV_ENGCTX(FIFO, 0x50),
+       .ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = nv50_fifo_context_ctor,
+               .dtor = nv50_fifo_context_dtor,
+               .init = _nvkm_fifo_context_init,
+               .fini = _nvkm_fifo_context_fini,
+               .rd32 = _nvkm_fifo_context_rd32,
+               .wr32 = _nvkm_fifo_context_wr32,
+       },
+};
+
+/*******************************************************************************
+ * PFIFO engine
+ ******************************************************************************/
+
+static int
+nv50_fifo_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+              struct nvkm_oclass *oclass, void *data, u32 size,
+              struct nvkm_object **pobject)
+{
+       struct nv50_fifo_priv *priv;
+       int ret;
+
+       ret = nvkm_fifo_create(parent, engine, oclass, 1, 127, &priv);
+       *pobject = nv_object(priv);
+       if (ret)
+               return ret;
+
+       ret = nvkm_gpuobj_new(nv_object(priv), NULL, 128 * 4, 0x1000, 0,
+                             &priv->playlist[0]);
+       if (ret)
+               return ret;
+
+       ret = nvkm_gpuobj_new(nv_object(priv), NULL, 128 * 4, 0x1000, 0,
+                             &priv->playlist[1]);
+       if (ret)
+               return ret;
+
+       nv_subdev(priv)->unit = 0x00000100;
+       nv_subdev(priv)->intr = nv04_fifo_intr;
+       nv_engine(priv)->cclass = &nv50_fifo_cclass;
+       nv_engine(priv)->sclass = nv50_fifo_sclass;
+       priv->base.pause = nv04_fifo_pause;
+       priv->base.start = nv04_fifo_start;
+       return 0;
+}
+
+void
+nv50_fifo_dtor(struct nvkm_object *object)
+{
+       struct nv50_fifo_priv *priv = (void *)object;
+
+       nvkm_gpuobj_ref(NULL, &priv->playlist[1]);
+       nvkm_gpuobj_ref(NULL, &priv->playlist[0]);
+
+       nvkm_fifo_destroy(&priv->base);
+}
+
+int
+nv50_fifo_init(struct nvkm_object *object)
+{
+       struct nv50_fifo_priv *priv = (void *)object;
+       int ret, i;
+
+       ret = nvkm_fifo_init(&priv->base);
+       if (ret)
+               return ret;
+
+       nv_mask(priv, 0x000200, 0x00000100, 0x00000000);
+       nv_mask(priv, 0x000200, 0x00000100, 0x00000100);
+       nv_wr32(priv, 0x00250c, 0x6f3cfc34);
+       nv_wr32(priv, 0x002044, 0x01003fff);
+
+       nv_wr32(priv, 0x002100, 0xffffffff);
+       nv_wr32(priv, 0x002140, 0xbfffffff);
+
+       for (i = 0; i < 128; i++)
+               nv_wr32(priv, 0x002600 + (i * 4), 0x00000000);
+       nv50_fifo_playlist_update_locked(priv);
+
+       nv_wr32(priv, 0x003200, 0x00000001);
+       nv_wr32(priv, 0x003250, 0x00000001);
+       nv_wr32(priv, 0x002500, 0x00000001);
+       return 0;
+}
+
+struct nvkm_oclass *
+nv50_fifo_oclass = &(struct nvkm_oclass) {
+       .handle = NV_ENGINE(FIFO, 0x50),
+       .ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = nv50_fifo_ctor,
+               .dtor = nv50_fifo_dtor,
+               .init = nv50_fifo_init,
+               .fini = _nvkm_fifo_fini,
+       },
+};
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/fifo/nv50.h b/drivers/gpu/drm/nouveau/nvkm/engine/fifo/nv50.h
new file mode 100644 (file)
index 0000000..09ed93c
--- /dev/null
@@ -0,0 +1,36 @@
+#ifndef __NV50_FIFO_H__
+#define __NV50_FIFO_H__
+#include <engine/fifo.h>
+
+struct nv50_fifo_priv {
+       struct nvkm_fifo base;
+       struct nvkm_gpuobj *playlist[2];
+       int cur_playlist;
+};
+
+struct nv50_fifo_base {
+       struct nvkm_fifo_base base;
+       struct nvkm_gpuobj *ramfc;
+       struct nvkm_gpuobj *cache;
+       struct nvkm_gpuobj *eng;
+       struct nvkm_gpuobj *pgd;
+       struct nvkm_vm *vm;
+};
+
+struct nv50_fifo_chan {
+       struct nvkm_fifo_chan base;
+       u32 subc[8];
+       struct nvkm_ramht *ramht;
+};
+
+void nv50_fifo_playlist_update(struct nv50_fifo_priv *);
+
+void nv50_fifo_object_detach(struct nvkm_object *, int);
+void nv50_fifo_chan_dtor(struct nvkm_object *);
+int  nv50_fifo_chan_fini(struct nvkm_object *, bool);
+
+void nv50_fifo_context_dtor(struct nvkm_object *);
+
+void nv50_fifo_dtor(struct nvkm_object *);
+int  nv50_fifo_init(struct nvkm_object *);
+#endif
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/gr/Kbuild b/drivers/gpu/drm/nouveau/nvkm/engine/gr/Kbuild
new file mode 100644 (file)
index 0000000..1771d94
--- /dev/null
@@ -0,0 +1,36 @@
+nvkm-y += nvkm/engine/gr/ctxnv40.o
+nvkm-y += nvkm/engine/gr/ctxnv50.o
+nvkm-y += nvkm/engine/gr/ctxgf100.o
+nvkm-y += nvkm/engine/gr/ctxgf108.o
+nvkm-y += nvkm/engine/gr/ctxgf104.o
+nvkm-y += nvkm/engine/gr/ctxgf110.o
+nvkm-y += nvkm/engine/gr/ctxgf117.o
+nvkm-y += nvkm/engine/gr/ctxgf119.o
+nvkm-y += nvkm/engine/gr/ctxgk104.o
+nvkm-y += nvkm/engine/gr/ctxgk20a.o
+nvkm-y += nvkm/engine/gr/ctxgk110.o
+nvkm-y += nvkm/engine/gr/ctxgk110b.o
+nvkm-y += nvkm/engine/gr/ctxgk208.o
+nvkm-y += nvkm/engine/gr/ctxgm107.o
+nvkm-y += nvkm/engine/gr/nv04.o
+nvkm-y += nvkm/engine/gr/nv10.o
+nvkm-y += nvkm/engine/gr/nv20.o
+nvkm-y += nvkm/engine/gr/nv25.o
+nvkm-y += nvkm/engine/gr/nv2a.o
+nvkm-y += nvkm/engine/gr/nv30.o
+nvkm-y += nvkm/engine/gr/nv34.o
+nvkm-y += nvkm/engine/gr/nv35.o
+nvkm-y += nvkm/engine/gr/nv40.o
+nvkm-y += nvkm/engine/gr/nv50.o
+nvkm-y += nvkm/engine/gr/gf100.o
+nvkm-y += nvkm/engine/gr/gf108.o
+nvkm-y += nvkm/engine/gr/gf104.o
+nvkm-y += nvkm/engine/gr/gf110.o
+nvkm-y += nvkm/engine/gr/gf117.o
+nvkm-y += nvkm/engine/gr/gf119.o
+nvkm-y += nvkm/engine/gr/gk104.o
+nvkm-y += nvkm/engine/gr/gk20a.o
+nvkm-y += nvkm/engine/gr/gk110.o
+nvkm-y += nvkm/engine/gr/gk110b.o
+nvkm-y += nvkm/engine/gr/gk208.o
+nvkm-y += nvkm/engine/gr/gm107.o
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/gr/ctxgf100.c b/drivers/gpu/drm/nouveau/nvkm/engine/gr/ctxgf100.c
new file mode 100644 (file)
index 0000000..2e7ec38
--- /dev/null
@@ -0,0 +1,1390 @@
+/*
+ * 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 "ctxgf100.h"
+
+#include <subdev/bar.h>
+#include <subdev/fb.h>
+#include <subdev/mc.h>
+#include <subdev/timer.h>
+
+/*******************************************************************************
+ * PGRAPH context register lists
+ ******************************************************************************/
+
+static const struct gf100_gr_init
+gf100_grctx_init_icmd_0[] = {
+       { 0x001000,   1, 0x01, 0x00000004 },
+       { 0x0000a9,   1, 0x01, 0x0000ffff },
+       { 0x000038,   1, 0x01, 0x0fac6881 },
+       { 0x00003d,   1, 0x01, 0x00000001 },
+       { 0x0000e8,   8, 0x01, 0x00000400 },
+       { 0x000078,   8, 0x01, 0x00000300 },
+       { 0x000050,   1, 0x01, 0x00000011 },
+       { 0x000058,   8, 0x01, 0x00000008 },
+       { 0x000208,   8, 0x01, 0x00000001 },
+       { 0x000081,   1, 0x01, 0x00000001 },
+       { 0x000085,   1, 0x01, 0x00000004 },
+       { 0x000088,   1, 0x01, 0x00000400 },
+       { 0x000090,   1, 0x01, 0x00000300 },
+       { 0x000098,   1, 0x01, 0x00001001 },
+       { 0x0000e3,   1, 0x01, 0x00000001 },
+       { 0x0000da,   1, 0x01, 0x00000001 },
+       { 0x0000f8,   1, 0x01, 0x00000003 },
+       { 0x0000fa,   1, 0x01, 0x00000001 },
+       { 0x00009f,   4, 0x01, 0x0000ffff },
+       { 0x0000b1,   1, 0x01, 0x00000001 },
+       { 0x0000b2,  40, 0x01, 0x00000000 },
+       { 0x000210,   8, 0x01, 0x00000040 },
+       { 0x000218,   8, 0x01, 0x0000c080 },
+       { 0x0000ad,   1, 0x01, 0x0000013e },
+       { 0x0000e1,   1, 0x01, 0x00000010 },
+       { 0x000290,  16, 0x01, 0x00000000 },
+       { 0x0003b0,  16, 0x01, 0x00000000 },
+       { 0x0002a0,  16, 0x01, 0x00000000 },
+       { 0x000420,  16, 0x01, 0x00000000 },
+       { 0x0002b0,  16, 0x01, 0x00000000 },
+       { 0x000430,  16, 0x01, 0x00000000 },
+       { 0x0002c0,  16, 0x01, 0x00000000 },
+       { 0x0004d0,  16, 0x01, 0x00000000 },
+       { 0x000720,  16, 0x01, 0x00000000 },
+       { 0x0008c0,  16, 0x01, 0x00000000 },
+       { 0x000890,  16, 0x01, 0x00000000 },
+       { 0x0008e0,  16, 0x01, 0x00000000 },
+       { 0x0008a0,  16, 0x01, 0x00000000 },
+       { 0x0008f0,  16, 0x01, 0x00000000 },
+       { 0x00094c,   1, 0x01, 0x000000ff },
+       { 0x00094d,   1, 0x01, 0xffffffff },
+       { 0x00094e,   1, 0x01, 0x00000002 },
+       { 0x0002ec,   1, 0x01, 0x00000001 },
+       { 0x000303,   1, 0x01, 0x00000001 },
+       { 0x0002e6,   1, 0x01, 0x00000001 },
+       { 0x000466,   1, 0x01, 0x00000052 },
+       { 0x000301,   1, 0x01, 0x3f800000 },
+       { 0x000304,   1, 0x01, 0x30201000 },
+       { 0x000305,   1, 0x01, 0x70605040 },
+       { 0x000306,   1, 0x01, 0xb8a89888 },
+       { 0x000307,   1, 0x01, 0xf8e8d8c8 },
+       { 0x00030a,   1, 0x01, 0x00ffff00 },
+       { 0x00030b,   1, 0x01, 0x0000001a },
+       { 0x00030c,   1, 0x01, 0x00000001 },
+       { 0x000318,   1, 0x01, 0x00000001 },
+       { 0x000340,   1, 0x01, 0x00000000 },
+       { 0x000375,   1, 0x01, 0x00000001 },
+       { 0x000351,   1, 0x01, 0x00000100 },
+       { 0x00037d,   1, 0x01, 0x00000006 },
+       { 0x0003a0,   1, 0x01, 0x00000002 },
+       { 0x0003aa,   1, 0x01, 0x00000001 },
+       { 0x0003a9,   1, 0x01, 0x00000001 },
+       { 0x000380,   1, 0x01, 0x00000001 },
+       { 0x000360,   1, 0x01, 0x00000040 },
+       { 0x000366,   2, 0x01, 0x00000000 },
+       { 0x000368,   1, 0x01, 0x00001fff },
+       { 0x000370,   2, 0x01, 0x00000000 },
+       { 0x000372,   1, 0x01, 0x003fffff },
+       { 0x00037a,   1, 0x01, 0x00000012 },
+       { 0x0005e0,   5, 0x01, 0x00000022 },
+       { 0x000619,   1, 0x01, 0x00000003 },
+       { 0x000811,   1, 0x01, 0x00000003 },
+       { 0x000812,   1, 0x01, 0x00000004 },
+       { 0x000813,   1, 0x01, 0x00000006 },
+       { 0x000814,   1, 0x01, 0x00000008 },
+       { 0x000815,   1, 0x01, 0x0000000b },
+       { 0x000800,   6, 0x01, 0x00000001 },
+       { 0x000632,   1, 0x01, 0x00000001 },
+       { 0x000633,   1, 0x01, 0x00000002 },
+       { 0x000634,   1, 0x01, 0x00000003 },
+       { 0x000635,   1, 0x01, 0x00000004 },
+       { 0x000654,   1, 0x01, 0x3f800000 },
+       { 0x000657,   1, 0x01, 0x3f800000 },
+       { 0x000655,   2, 0x01, 0x3f800000 },
+       { 0x0006cd,   1, 0x01, 0x3f800000 },
+       { 0x0007f5,   1, 0x01, 0x3f800000 },
+       { 0x0007dc,   1, 0x01, 0x39291909 },
+       { 0x0007dd,   1, 0x01, 0x79695949 },
+       { 0x0007de,   1, 0x01, 0xb9a99989 },
+       { 0x0007df,   1, 0x01, 0xf9e9d9c9 },
+       { 0x0007e8,   1, 0x01, 0x00003210 },
+       { 0x0007e9,   1, 0x01, 0x00007654 },
+       { 0x0007ea,   1, 0x01, 0x00000098 },
+       { 0x0007ec,   1, 0x01, 0x39291909 },
+       { 0x0007ed,   1, 0x01, 0x79695949 },
+       { 0x0007ee,   1, 0x01, 0xb9a99989 },
+       { 0x0007ef,   1, 0x01, 0xf9e9d9c9 },
+       { 0x0007f0,   1, 0x01, 0x00003210 },
+       { 0x0007f1,   1, 0x01, 0x00007654 },
+       { 0x0007f2,   1, 0x01, 0x00000098 },
+       { 0x0005a5,   1, 0x01, 0x00000001 },
+       { 0x000980, 128, 0x01, 0x00000000 },
+       { 0x000468,   1, 0x01, 0x00000004 },
+       { 0x00046c,   1, 0x01, 0x00000001 },
+       { 0x000470,  96, 0x01, 0x00000000 },
+       { 0x000510,  16, 0x01, 0x3f800000 },
+       { 0x000520,   1, 0x01, 0x000002b6 },
+       { 0x000529,   1, 0x01, 0x00000001 },
+       { 0x000530,  16, 0x01, 0xffff0000 },
+       { 0x000585,   1, 0x01, 0x0000003f },
+       { 0x000576,   1, 0x01, 0x00000003 },
+       { 0x000586,   1, 0x01, 0x00000040 },
+       { 0x000582,   2, 0x01, 0x00000080 },
+       { 0x0005c2,   1, 0x01, 0x00000001 },
+       { 0x000638,   2, 0x01, 0x00000001 },
+       { 0x00063a,   1, 0x01, 0x00000002 },
+       { 0x00063b,   2, 0x01, 0x00000001 },
+       { 0x00063d,   1, 0x01, 0x00000002 },
+       { 0x00063e,   1, 0x01, 0x00000001 },
+       { 0x0008b8,   8, 0x01, 0x00000001 },
+       { 0x000900,   8, 0x01, 0x00000001 },
+       { 0x000908,   8, 0x01, 0x00000002 },
+       { 0x000910,  16, 0x01, 0x00000001 },
+       { 0x000920,   8, 0x01, 0x00000002 },
+       { 0x000928,   8, 0x01, 0x00000001 },
+       { 0x000648,   9, 0x01, 0x00000001 },
+       { 0x000658,   1, 0x01, 0x0000000f },
+       { 0x0007ff,   1, 0x01, 0x0000000a },
+       { 0x00066a,   1, 0x01, 0x40000000 },
+       { 0x00066b,   1, 0x01, 0x10000000 },
+       { 0x00066c,   2, 0x01, 0xffff0000 },
+       { 0x0007af,   2, 0x01, 0x00000008 },
+       { 0x0007f6,   1, 0x01, 0x00000001 },
+       { 0x0006b2,   1, 0x01, 0x00000055 },
+       { 0x0007ad,   1, 0x01, 0x00000003 },
+       { 0x000937,   1, 0x01, 0x00000001 },
+       { 0x000971,   1, 0x01, 0x00000008 },
+       { 0x000972,   1, 0x01, 0x00000040 },
+       { 0x000973,   1, 0x01, 0x0000012c },
+       { 0x00097c,   1, 0x01, 0x00000040 },
+       { 0x000979,   1, 0x01, 0x00000003 },
+       { 0x000975,   1, 0x01, 0x00000020 },
+       { 0x000976,   1, 0x01, 0x00000001 },
+       { 0x000977,   1, 0x01, 0x00000020 },
+       { 0x000978,   1, 0x01, 0x00000001 },
+       { 0x000957,   1, 0x01, 0x00000003 },
+       { 0x00095e,   1, 0x01, 0x20164010 },
+       { 0x00095f,   1, 0x01, 0x00000020 },
+       { 0x000683,   1, 0x01, 0x00000006 },
+       { 0x000685,   1, 0x01, 0x003fffff },
+       { 0x000687,   1, 0x01, 0x00000c48 },
+       { 0x0006a0,   1, 0x01, 0x00000005 },
+       { 0x000840,   1, 0x01, 0x00300008 },
+       { 0x000841,   1, 0x01, 0x04000080 },
+       { 0x000842,   1, 0x01, 0x00300008 },
+       { 0x000843,   1, 0x01, 0x04000080 },
+       { 0x000818,   8, 0x01, 0x00000000 },
+       { 0x000848,  16, 0x01, 0x00000000 },
+       { 0x000738,   1, 0x01, 0x00000000 },
+       { 0x0006aa,   1, 0x01, 0x00000001 },
+       { 0x0006ab,   1, 0x01, 0x00000002 },
+       { 0x0006ac,   1, 0x01, 0x00000080 },
+       { 0x0006ad,   2, 0x01, 0x00000100 },
+       { 0x0006b1,   1, 0x01, 0x00000011 },
+       { 0x0006bb,   1, 0x01, 0x000000cf },
+       { 0x0006ce,   1, 0x01, 0x2a712488 },
+       { 0x000739,   1, 0x01, 0x4085c000 },
+       { 0x00073a,   1, 0x01, 0x00000080 },
+       { 0x000786,   1, 0x01, 0x80000100 },
+       { 0x00073c,   1, 0x01, 0x00010100 },
+       { 0x00073d,   1, 0x01, 0x02800000 },
+       { 0x000787,   1, 0x01, 0x000000cf },
+       { 0x00078c,   1, 0x01, 0x00000008 },
+       { 0x000792,   1, 0x01, 0x00000001 },
+       { 0x000794,   3, 0x01, 0x00000001 },
+       { 0x000797,   1, 0x01, 0x000000cf },
+       { 0x000836,   1, 0x01, 0x00000001 },
+       { 0x00079a,   1, 0x01, 0x00000002 },
+       { 0x000833,   1, 0x01, 0x04444480 },
+       { 0x0007a1,   1, 0x01, 0x00000001 },
+       { 0x0007a3,   3, 0x01, 0x00000001 },
+       { 0x000831,   1, 0x01, 0x00000004 },
+       { 0x00080c,   1, 0x01, 0x00000002 },
+       { 0x00080d,   2, 0x01, 0x00000100 },
+       { 0x00080f,   1, 0x01, 0x00000001 },
+       { 0x000823,   1, 0x01, 0x00000002 },
+       { 0x000824,   2, 0x01, 0x00000100 },
+       { 0x000826,   1, 0x01, 0x00000001 },
+       { 0x00095d,   1, 0x01, 0x00000001 },
+       { 0x00082b,   1, 0x01, 0x00000004 },
+       { 0x000942,   1, 0x01, 0x00010001 },
+       { 0x000943,   1, 0x01, 0x00000001 },
+       { 0x000944,   1, 0x01, 0x00000022 },
+       { 0x0007c5,   1, 0x01, 0x00010001 },
+       { 0x000834,   1, 0x01, 0x00000001 },
+       { 0x0007c7,   1, 0x01, 0x00000001 },
+       { 0x00c1b0,   8, 0x01, 0x0000000f },
+       { 0x00c1b8,   1, 0x01, 0x0fac6881 },
+       { 0x00c1b9,   1, 0x01, 0x00fac688 },
+       { 0x01e100,   1, 0x01, 0x00000001 },
+       { 0x001000,   1, 0x01, 0x00000002 },
+       { 0x0006aa,   1, 0x01, 0x00000001 },
+       { 0x0006ad,   2, 0x01, 0x00000100 },
+       { 0x0006b1,   1, 0x01, 0x00000011 },
+       { 0x00078c,   1, 0x01, 0x00000008 },
+       { 0x000792,   1, 0x01, 0x00000001 },
+       { 0x000794,   3, 0x01, 0x00000001 },
+       { 0x000797,   1, 0x01, 0x000000cf },
+       { 0x00079a,   1, 0x01, 0x00000002 },
+       { 0x000833,   1, 0x01, 0x04444480 },
+       { 0x0007a1,   1, 0x01, 0x00000001 },
+       { 0x0007a3,   3, 0x01, 0x00000001 },
+       { 0x000831,   1, 0x01, 0x00000004 },
+       { 0x01e100,   1, 0x01, 0x00000001 },
+       { 0x001000,   1, 0x01, 0x00000014 },
+       { 0x000351,   1, 0x01, 0x00000100 },
+       { 0x000957,   1, 0x01, 0x00000003 },
+       { 0x00095d,   1, 0x01, 0x00000001 },
+       { 0x00082b,   1, 0x01, 0x00000004 },
+       { 0x000942,   1, 0x01, 0x00010001 },
+       { 0x000943,   1, 0x01, 0x00000001 },
+       { 0x0007c5,   1, 0x01, 0x00010001 },
+       { 0x000834,   1, 0x01, 0x00000001 },
+       { 0x0007c7,   1, 0x01, 0x00000001 },
+       { 0x01e100,   1, 0x01, 0x00000001 },
+       { 0x001000,   1, 0x01, 0x00000001 },
+       { 0x00080c,   1, 0x01, 0x00000002 },
+       { 0x00080d,   2, 0x01, 0x00000100 },
+       { 0x00080f,   1, 0x01, 0x00000001 },
+       { 0x000823,   1, 0x01, 0x00000002 },
+       { 0x000824,   2, 0x01, 0x00000100 },
+       { 0x000826,   1, 0x01, 0x00000001 },
+       { 0x01e100,   1, 0x01, 0x00000001 },
+       {}
+};
+
+const struct gf100_gr_pack
+gf100_grctx_pack_icmd[] = {
+       { gf100_grctx_init_icmd_0 },
+       {}
+};
+
+static const struct gf100_gr_init
+gf100_grctx_init_9097_0[] = {
+       { 0x000800,   8, 0x40, 0x00000000 },
+       { 0x000804,   8, 0x40, 0x00000000 },
+       { 0x000808,   8, 0x40, 0x00000400 },
+       { 0x00080c,   8, 0x40, 0x00000300 },
+       { 0x000810,   1, 0x04, 0x000000cf },
+       { 0x000850,   7, 0x40, 0x00000000 },
+       { 0x000814,   8, 0x40, 0x00000040 },
+       { 0x000818,   8, 0x40, 0x00000001 },
+       { 0x00081c,   8, 0x40, 0x00000000 },
+       { 0x000820,   8, 0x40, 0x00000000 },
+       { 0x002700,   8, 0x20, 0x00000000 },
+       { 0x002704,   8, 0x20, 0x00000000 },
+       { 0x002708,   8, 0x20, 0x00000000 },
+       { 0x00270c,   8, 0x20, 0x00000000 },
+       { 0x002710,   8, 0x20, 0x00014000 },
+       { 0x002714,   8, 0x20, 0x00000040 },
+       { 0x001c00,  16, 0x10, 0x00000000 },
+       { 0x001c04,  16, 0x10, 0x00000000 },
+       { 0x001c08,  16, 0x10, 0x00000000 },
+       { 0x001c0c,  16, 0x10, 0x00000000 },
+       { 0x001d00,  16, 0x10, 0x00000000 },
+       { 0x001d04,  16, 0x10, 0x00000000 },
+       { 0x001d08,  16, 0x10, 0x00000000 },
+       { 0x001d0c,  16, 0x10, 0x00000000 },
+       { 0x001f00,  16, 0x08, 0x00000000 },
+       { 0x001f04,  16, 0x08, 0x00000000 },
+       { 0x001f80,  16, 0x08, 0x00000000 },
+       { 0x001f84,  16, 0x08, 0x00000000 },
+       { 0x002200,   5, 0x10, 0x00000022 },
+       { 0x002000,   1, 0x04, 0x00000000 },
+       { 0x002040,   1, 0x04, 0x00000011 },
+       { 0x002080,   1, 0x04, 0x00000020 },
+       { 0x0020c0,   1, 0x04, 0x00000030 },
+       { 0x002100,   1, 0x04, 0x00000040 },
+       { 0x002140,   1, 0x04, 0x00000051 },
+       { 0x00200c,   6, 0x40, 0x00000001 },
+       { 0x002010,   1, 0x04, 0x00000000 },
+       { 0x002050,   1, 0x04, 0x00000000 },
+       { 0x002090,   1, 0x04, 0x00000001 },
+       { 0x0020d0,   1, 0x04, 0x00000002 },
+       { 0x002110,   1, 0x04, 0x00000003 },
+       { 0x002150,   1, 0x04, 0x00000004 },
+       { 0x000380,   4, 0x20, 0x00000000 },
+       { 0x000384,   4, 0x20, 0x00000000 },
+       { 0x000388,   4, 0x20, 0x00000000 },
+       { 0x00038c,   4, 0x20, 0x00000000 },
+       { 0x000700,   4, 0x10, 0x00000000 },
+       { 0x000704,   4, 0x10, 0x00000000 },
+       { 0x000708,   4, 0x10, 0x00000000 },
+       { 0x002800, 128, 0x04, 0x00000000 },
+       { 0x000a00,  16, 0x20, 0x00000000 },
+       { 0x000a04,  16, 0x20, 0x00000000 },
+       { 0x000a08,  16, 0x20, 0x00000000 },
+       { 0x000a0c,  16, 0x20, 0x00000000 },
+       { 0x000a10,  16, 0x20, 0x00000000 },
+       { 0x000a14,  16, 0x20, 0x00000000 },
+       { 0x000c00,  16, 0x10, 0x00000000 },
+       { 0x000c04,  16, 0x10, 0x00000000 },
+       { 0x000c08,  16, 0x10, 0x00000000 },
+       { 0x000c0c,  16, 0x10, 0x3f800000 },
+       { 0x000d00,   8, 0x08, 0xffff0000 },
+       { 0x000d04,   8, 0x08, 0xffff0000 },
+       { 0x000e00,  16, 0x10, 0x00000000 },
+       { 0x000e04,  16, 0x10, 0xffff0000 },
+       { 0x000e08,  16, 0x10, 0xffff0000 },
+       { 0x000d40,   4, 0x08, 0x00000000 },
+       { 0x000d44,   4, 0x08, 0x00000000 },
+       { 0x001e00,   8, 0x20, 0x00000001 },
+       { 0x001e04,   8, 0x20, 0x00000001 },
+       { 0x001e08,   8, 0x20, 0x00000002 },
+       { 0x001e0c,   8, 0x20, 0x00000001 },
+       { 0x001e10,   8, 0x20, 0x00000001 },
+       { 0x001e14,   8, 0x20, 0x00000002 },
+       { 0x001e18,   8, 0x20, 0x00000001 },
+       { 0x003400, 128, 0x04, 0x00000000 },
+       { 0x00030c,   1, 0x04, 0x00000001 },
+       { 0x001944,   1, 0x04, 0x00000000 },
+       { 0x001514,   1, 0x04, 0x00000000 },
+       { 0x000d68,   1, 0x04, 0x0000ffff },
+       { 0x00121c,   1, 0x04, 0x0fac6881 },
+       { 0x000fac,   1, 0x04, 0x00000001 },
+       { 0x001538,   1, 0x04, 0x00000001 },
+       { 0x000fe0,   2, 0x04, 0x00000000 },
+       { 0x000fe8,   1, 0x04, 0x00000014 },
+       { 0x000fec,   1, 0x04, 0x00000040 },
+       { 0x000ff0,   1, 0x04, 0x00000000 },
+       { 0x00179c,   1, 0x04, 0x00000000 },
+       { 0x001228,   1, 0x04, 0x00000400 },
+       { 0x00122c,   1, 0x04, 0x00000300 },
+       { 0x001230,   1, 0x04, 0x00010001 },
+       { 0x0007f8,   1, 0x04, 0x00000000 },
+       { 0x0015b4,   1, 0x04, 0x00000001 },
+       { 0x0015cc,   1, 0x04, 0x00000000 },
+       { 0x001534,   1, 0x04, 0x00000000 },
+       { 0x000fb0,   1, 0x04, 0x00000000 },
+       { 0x0015d0,   1, 0x04, 0x00000000 },
+       { 0x00153c,   1, 0x04, 0x00000000 },
+       { 0x0016b4,   1, 0x04, 0x00000003 },
+       { 0x000fbc,   4, 0x04, 0x0000ffff },
+       { 0x000df8,   2, 0x04, 0x00000000 },
+       { 0x001948,   1, 0x04, 0x00000000 },
+       { 0x001970,   1, 0x04, 0x00000001 },
+       { 0x00161c,   1, 0x04, 0x000009f0 },
+       { 0x000dcc,   1, 0x04, 0x00000010 },
+       { 0x00163c,   1, 0x04, 0x00000000 },
+       { 0x0015e4,   1, 0x04, 0x00000000 },
+       { 0x001160,  32, 0x04, 0x25e00040 },
+       { 0x001880,  32, 0x04, 0x00000000 },
+       { 0x000f84,   2, 0x04, 0x00000000 },
+       { 0x0017c8,   2, 0x04, 0x00000000 },
+       { 0x0017d0,   1, 0x04, 0x000000ff },
+       { 0x0017d4,   1, 0x04, 0xffffffff },
+       { 0x0017d8,   1, 0x04, 0x00000002 },
+       { 0x0017dc,   1, 0x04, 0x00000000 },
+       { 0x0015f4,   2, 0x04, 0x00000000 },
+       { 0x001434,   2, 0x04, 0x00000000 },
+       { 0x000d74,   1, 0x04, 0x00000000 },
+       { 0x000dec,   1, 0x04, 0x00000001 },
+       { 0x0013a4,   1, 0x04, 0x00000000 },
+       { 0x001318,   1, 0x04, 0x00000001 },
+       { 0x001644,   1, 0x04, 0x00000000 },
+       { 0x000748,   1, 0x04, 0x00000000 },
+       { 0x000de8,   1, 0x04, 0x00000000 },
+       { 0x001648,   1, 0x04, 0x00000000 },
+       { 0x0012a4,   1, 0x04, 0x00000000 },
+       { 0x001120,   4, 0x04, 0x00000000 },
+       { 0x001118,   1, 0x04, 0x00000000 },
+       { 0x00164c,   1, 0x04, 0x00000000 },
+       { 0x001658,   1, 0x04, 0x00000000 },
+       { 0x001910,   1, 0x04, 0x00000290 },
+       { 0x001518,   1, 0x04, 0x00000000 },
+       { 0x00165c,   1, 0x04, 0x00000001 },
+       { 0x001520,   1, 0x04, 0x00000000 },
+       { 0x001604,   1, 0x04, 0x00000000 },
+       { 0x001570,   1, 0x04, 0x00000000 },
+       { 0x0013b0,   2, 0x04, 0x3f800000 },
+       { 0x00020c,   1, 0x04, 0x00000000 },
+       { 0x001670,   1, 0x04, 0x30201000 },
+       { 0x001674,   1, 0x04, 0x70605040 },
+       { 0x001678,   1, 0x04, 0xb8a89888 },
+       { 0x00167c,   1, 0x04, 0xf8e8d8c8 },
+       { 0x00166c,   1, 0x04, 0x00000000 },
+       { 0x001680,   1, 0x04, 0x00ffff00 },
+       { 0x0012d0,   1, 0x04, 0x00000003 },
+       { 0x0012d4,   1, 0x04, 0x00000002 },
+       { 0x001684,   2, 0x04, 0x00000000 },
+       { 0x000dac,   2, 0x04, 0x00001b02 },
+       { 0x000db4,   1, 0x04, 0x00000000 },
+       { 0x00168c,   1, 0x04, 0x00000000 },
+       { 0x0015bc,   1, 0x04, 0x00000000 },
+       { 0x00156c,   1, 0x04, 0x00000000 },
+       { 0x00187c,   1, 0x04, 0x00000000 },
+       { 0x001110,   1, 0x04, 0x00000001 },
+       { 0x000dc0,   3, 0x04, 0x00000000 },
+       { 0x001234,   1, 0x04, 0x00000000 },
+       { 0x001690,   1, 0x04, 0x00000000 },
+       { 0x0012ac,   1, 0x04, 0x00000001 },
+       { 0x0002c4,   1, 0x04, 0x00000000 },
+       { 0x000790,   5, 0x04, 0x00000000 },
+       { 0x00077c,   1, 0x04, 0x00000000 },
+       { 0x001000,   1, 0x04, 0x00000010 },
+       { 0x0010fc,   1, 0x04, 0x00000000 },
+       { 0x001290,   1, 0x04, 0x00000000 },
+       { 0x000218,   1, 0x04, 0x00000010 },
+       { 0x0012d8,   1, 0x04, 0x00000000 },
+       { 0x0012dc,   1, 0x04, 0x00000010 },
+       { 0x000d94,   1, 0x04, 0x00000001 },
+       { 0x00155c,   2, 0x04, 0x00000000 },
+       { 0x001564,   1, 0x04, 0x00001fff },
+       { 0x001574,   2, 0x04, 0x00000000 },
+       { 0x00157c,   1, 0x04, 0x003fffff },
+       { 0x001354,   1, 0x04, 0x00000000 },
+       { 0x001664,   1, 0x04, 0x00000000 },
+       { 0x001610,   1, 0x04, 0x00000012 },
+       { 0x001608,   2, 0x04, 0x00000000 },
+       { 0x00162c,   1, 0x04, 0x00000003 },
+       { 0x000210,   1, 0x04, 0x00000000 },
+       { 0x000320,   1, 0x04, 0x00000000 },
+       { 0x000324,   6, 0x04, 0x3f800000 },
+       { 0x000750,   1, 0x04, 0x00000000 },
+       { 0x000760,   1, 0x04, 0x39291909 },
+       { 0x000764,   1, 0x04, 0x79695949 },
+       { 0x000768,   1, 0x04, 0xb9a99989 },
+       { 0x00076c,   1, 0x04, 0xf9e9d9c9 },
+       { 0x000770,   1, 0x04, 0x30201000 },
+       { 0x000774,   1, 0x04, 0x70605040 },
+       { 0x000778,   1, 0x04, 0x00009080 },
+       { 0x000780,   1, 0x04, 0x39291909 },
+       { 0x000784,   1, 0x04, 0x79695949 },
+       { 0x000788,   1, 0x04, 0xb9a99989 },
+       { 0x00078c,   1, 0x04, 0xf9e9d9c9 },
+       { 0x0007d0,   1, 0x04, 0x30201000 },
+       { 0x0007d4,   1, 0x04, 0x70605040 },
+       { 0x0007d8,   1, 0x04, 0x00009080 },
+       { 0x00037c,   1, 0x04, 0x00000001 },
+       { 0x000740,   2, 0x04, 0x00000000 },
+       { 0x002600,   1, 0x04, 0x00000000 },
+       { 0x001918,   1, 0x04, 0x00000000 },
+       { 0x00191c,   1, 0x04, 0x00000900 },
+       { 0x001920,   1, 0x04, 0x00000405 },
+       { 0x001308,   1, 0x04, 0x00000001 },
+       { 0x001924,   1, 0x04, 0x00000000 },
+       { 0x0013ac,   1, 0x04, 0x00000000 },
+       { 0x00192c,   1, 0x04, 0x00000001 },
+       { 0x00193c,   1, 0x04, 0x00002c1c },
+       { 0x000d7c,   1, 0x04, 0x00000000 },
+       { 0x000f8c,   1, 0x04, 0x00000000 },
+       { 0x0002c0,   1, 0x04, 0x00000001 },
+       { 0x001510,   1, 0x04, 0x00000000 },
+       { 0x001940,   1, 0x04, 0x00000000 },
+       { 0x000ff4,   2, 0x04, 0x00000000 },
+       { 0x00194c,   2, 0x04, 0x00000000 },
+       { 0x001968,   1, 0x04, 0x00000000 },
+       { 0x001590,   1, 0x04, 0x0000003f },
+       { 0x0007e8,   4, 0x04, 0x00000000 },
+       { 0x00196c,   1, 0x04, 0x00000011 },
+       { 0x00197c,   1, 0x04, 0x00000000 },
+       { 0x000fcc,   2, 0x04, 0x00000000 },
+       { 0x0002d8,   1, 0x04, 0x00000040 },
+       { 0x001980,   1, 0x04, 0x00000080 },
+       { 0x001504,   1, 0x04, 0x00000080 },
+       { 0x001984,   1, 0x04, 0x00000000 },
+       { 0x000300,   1, 0x04, 0x00000001 },
+       { 0x0013a8,   1, 0x04, 0x00000000 },
+       { 0x0012ec,   1, 0x04, 0x00000000 },
+       { 0x001310,   1, 0x04, 0x00000000 },
+       { 0x001314,   1, 0x04, 0x00000001 },
+       { 0x001380,   1, 0x04, 0x00000000 },
+       { 0x001384,   4, 0x04, 0x00000001 },
+       { 0x001394,   1, 0x04, 0x00000000 },
+       { 0x00139c,   1, 0x04, 0x00000000 },
+       { 0x001398,   1, 0x04, 0x00000000 },
+       { 0x001594,   1, 0x04, 0x00000000 },
+       { 0x001598,   4, 0x04, 0x00000001 },
+       { 0x000f54,   3, 0x04, 0x00000000 },
+       { 0x0019bc,   1, 0x04, 0x00000000 },
+       { 0x000f9c,   2, 0x04, 0x00000000 },
+       { 0x0012cc,   1, 0x04, 0x00000000 },
+       { 0x0012e8,   1, 0x04, 0x00000000 },
+       { 0x00130c,   1, 0x04, 0x00000001 },
+       { 0x001360,   8, 0x04, 0x00000000 },
+       { 0x00133c,   2, 0x04, 0x00000001 },
+       { 0x001344,   1, 0x04, 0x00000002 },
+       { 0x001348,   2, 0x04, 0x00000001 },
+       { 0x001350,   1, 0x04, 0x00000002 },
+       { 0x001358,   1, 0x04, 0x00000001 },
+       { 0x0012e4,   1, 0x04, 0x00000000 },
+       { 0x00131c,   4, 0x04, 0x00000000 },
+       { 0x0019c0,   1, 0x04, 0x00000000 },
+       { 0x001140,   1, 0x04, 0x00000000 },
+       { 0x0019c4,   1, 0x04, 0x00000000 },
+       { 0x0019c8,   1, 0x04, 0x00001500 },
+       { 0x00135c,   1, 0x04, 0x00000000 },
+       { 0x000f90,   1, 0x04, 0x00000000 },
+       { 0x0019e0,   8, 0x04, 0x00000001 },
+       { 0x0019cc,   1, 0x04, 0x00000001 },
+       { 0x0015b8,   1, 0x04, 0x00000000 },
+       { 0x001a00,   1, 0x04, 0x00001111 },
+       { 0x001a04,   7, 0x04, 0x00000000 },
+       { 0x000d6c,   2, 0x04, 0xffff0000 },
+       { 0x0010f8,   1, 0x04, 0x00001010 },
+       { 0x000d80,   5, 0x04, 0x00000000 },
+       { 0x000da0,   1, 0x04, 0x00000000 },
+       { 0x001508,   1, 0x04, 0x80000000 },
+       { 0x00150c,   1, 0x04, 0x40000000 },
+       { 0x001668,   1, 0x04, 0x00000000 },
+       { 0x000318,   2, 0x04, 0x00000008 },
+       { 0x000d9c,   1, 0x04, 0x00000001 },
+       { 0x0007dc,   1, 0x04, 0x00000000 },
+       { 0x00074c,   1, 0x04, 0x00000055 },
+       { 0x001420,   1, 0x04, 0x00000003 },
+       { 0x0017bc,   2, 0x04, 0x00000000 },
+       { 0x0017c4,   1, 0x04, 0x00000001 },
+       { 0x001008,   1, 0x04, 0x00000008 },
+       { 0x00100c,   1, 0x04, 0x00000040 },
+       { 0x001010,   1, 0x04, 0x0000012c },
+       { 0x000d60,   1, 0x04, 0x00000040 },
+       { 0x00075c,   1, 0x04, 0x00000003 },
+       { 0x001018,   1, 0x04, 0x00000020 },
+       { 0x00101c,   1, 0x04, 0x00000001 },
+       { 0x001020,   1, 0x04, 0x00000020 },
+       { 0x001024,   1, 0x04, 0x00000001 },
+       { 0x001444,   3, 0x04, 0x00000000 },
+       { 0x000360,   1, 0x04, 0x20164010 },
+       { 0x000364,   1, 0x04, 0x00000020 },
+       { 0x000368,   1, 0x04, 0x00000000 },
+       { 0x000de4,   1, 0x04, 0x00000000 },
+       { 0x000204,   1, 0x04, 0x00000006 },
+       { 0x000208,   1, 0x04, 0x00000000 },
+       { 0x0002cc,   1, 0x04, 0x003fffff },
+       { 0x0002d0,   1, 0x04, 0x00000c48 },
+       { 0x001220,   1, 0x04, 0x00000005 },
+       { 0x000fdc,   1, 0x04, 0x00000000 },
+       { 0x000f98,   1, 0x04, 0x00300008 },
+       { 0x001284,   1, 0x04, 0x04000080 },
+       { 0x001450,   1, 0x04, 0x00300008 },
+       { 0x001454,   1, 0x04, 0x04000080 },
+       { 0x000214,   1, 0x04, 0x00000000 },
+       {}
+};
+
+const struct gf100_gr_init
+gf100_grctx_init_902d_0[] = {
+       { 0x000200,   1, 0x04, 0x000000cf },
+       { 0x000204,   1, 0x04, 0x00000001 },
+       { 0x000208,   1, 0x04, 0x00000020 },
+       { 0x00020c,   1, 0x04, 0x00000001 },
+       { 0x000210,   1, 0x04, 0x00000000 },
+       { 0x000214,   1, 0x04, 0x00000080 },
+       { 0x000218,   2, 0x04, 0x00000100 },
+       { 0x000220,   2, 0x04, 0x00000000 },
+       { 0x000230,   1, 0x04, 0x000000cf },
+       { 0x000234,   1, 0x04, 0x00000001 },
+       { 0x000238,   1, 0x04, 0x00000020 },
+       { 0x00023c,   1, 0x04, 0x00000001 },
+       { 0x000244,   1, 0x04, 0x00000080 },
+       { 0x000248,   2, 0x04, 0x00000100 },
+       {}
+};
+
+const struct gf100_gr_init
+gf100_grctx_init_9039_0[] = {
+       { 0x00030c,   3, 0x04, 0x00000000 },
+       { 0x000320,   1, 0x04, 0x00000000 },
+       { 0x000238,   2, 0x04, 0x00000000 },
+       { 0x000318,   2, 0x04, 0x00000000 },
+       {}
+};
+
+const struct gf100_gr_init
+gf100_grctx_init_90c0_0[] = {
+       { 0x00270c,   8, 0x20, 0x00000000 },
+       { 0x00030c,   1, 0x04, 0x00000001 },
+       { 0x001944,   1, 0x04, 0x00000000 },
+       { 0x000758,   1, 0x04, 0x00000100 },
+       { 0x0002c4,   1, 0x04, 0x00000000 },
+       { 0x000790,   5, 0x04, 0x00000000 },
+       { 0x00077c,   1, 0x04, 0x00000000 },
+       { 0x000204,   3, 0x04, 0x00000000 },
+       { 0x000214,   1, 0x04, 0x00000000 },
+       { 0x00024c,   1, 0x04, 0x00000000 },
+       { 0x000d94,   1, 0x04, 0x00000001 },
+       { 0x001608,   2, 0x04, 0x00000000 },
+       { 0x001664,   1, 0x04, 0x00000000 },
+       {}
+};
+
+const struct gf100_gr_pack
+gf100_grctx_pack_mthd[] = {
+       { gf100_grctx_init_9097_0, 0x9097 },
+       { gf100_grctx_init_902d_0, 0x902d },
+       { gf100_grctx_init_9039_0, 0x9039 },
+       { gf100_grctx_init_90c0_0, 0x90c0 },
+       {}
+};
+
+const struct gf100_gr_init
+gf100_grctx_init_main_0[] = {
+       { 0x400204,   2, 0x04, 0x00000000 },
+       {}
+};
+
+const struct gf100_gr_init
+gf100_grctx_init_fe_0[] = {
+       { 0x404004,  11, 0x04, 0x00000000 },
+       { 0x404044,   1, 0x04, 0x00000000 },
+       { 0x404094,  13, 0x04, 0x00000000 },
+       { 0x4040c8,   1, 0x04, 0xf0000087 },
+       { 0x4040d0,   6, 0x04, 0x00000000 },
+       { 0x4040e8,   1, 0x04, 0x00001000 },
+       { 0x4040f8,   1, 0x04, 0x00000000 },
+       { 0x404130,   2, 0x04, 0x00000000 },
+       { 0x404138,   1, 0x04, 0x20000040 },
+       { 0x404150,   1, 0x04, 0x0000002e },
+       { 0x404154,   1, 0x04, 0x00000400 },
+       { 0x404158,   1, 0x04, 0x00000200 },
+       { 0x404164,   1, 0x04, 0x00000055 },
+       { 0x404168,   1, 0x04, 0x00000000 },
+       { 0x404174,   3, 0x04, 0x00000000 },
+       { 0x404200,   8, 0x04, 0x00000000 },
+       {}
+};
+
+const struct gf100_gr_init
+gf100_grctx_init_pri_0[] = {
+       { 0x404404,  14, 0x04, 0x00000000 },
+       { 0x404460,   2, 0x04, 0x00000000 },
+       { 0x404468,   1, 0x04, 0x00ffffff },
+       { 0x40446c,   1, 0x04, 0x00000000 },
+       { 0x404480,   1, 0x04, 0x00000001 },
+       { 0x404498,   1, 0x04, 0x00000001 },
+       {}
+};
+
+const struct gf100_gr_init
+gf100_grctx_init_memfmt_0[] = {
+       { 0x404604,   1, 0x04, 0x00000015 },
+       { 0x404608,   1, 0x04, 0x00000000 },
+       { 0x40460c,   1, 0x04, 0x00002e00 },
+       { 0x404610,   1, 0x04, 0x00000100 },
+       { 0x404618,   8, 0x04, 0x00000000 },
+       { 0x404638,   1, 0x04, 0x00000004 },
+       { 0x40463c,   8, 0x04, 0x00000000 },
+       { 0x40465c,   1, 0x04, 0x007f0100 },
+       { 0x404660,   7, 0x04, 0x00000000 },
+       { 0x40467c,   1, 0x04, 0x00000002 },
+       { 0x404680,   8, 0x04, 0x00000000 },
+       { 0x4046a0,   1, 0x04, 0x007f0080 },
+       { 0x4046a4,  18, 0x04, 0x00000000 },
+       { 0x4046f0,   2, 0x04, 0x00000000 },
+       { 0x404700,  13, 0x04, 0x00000000 },
+       { 0x404734,   1, 0x04, 0x00000100 },
+       { 0x404738,   8, 0x04, 0x00000000 },
+       {}
+};
+
+static const struct gf100_gr_init
+gf100_grctx_init_ds_0[] = {
+       { 0x405800,   1, 0x04, 0x078000bf },
+       { 0x405830,   1, 0x04, 0x02180000 },
+       { 0x405834,   2, 0x04, 0x00000000 },
+       { 0x405854,   1, 0x04, 0x00000000 },
+       { 0x405870,   4, 0x04, 0x00000001 },
+       { 0x405a00,   2, 0x04, 0x00000000 },
+       { 0x405a18,   1, 0x04, 0x00000000 },
+       {}
+};
+
+static const struct gf100_gr_init
+gf100_grctx_init_pd_0[] = {
+       { 0x406020,   1, 0x04, 0x000103c1 },
+       { 0x406028,   4, 0x04, 0x00000001 },
+       { 0x4064a8,   1, 0x04, 0x00000000 },
+       { 0x4064ac,   1, 0x04, 0x00003fff },
+       { 0x4064b4,   2, 0x04, 0x00000000 },
+       {}
+};
+
+const struct gf100_gr_init
+gf100_grctx_init_rstr2d_0[] = {
+       { 0x407804,   1, 0x04, 0x00000023 },
+       { 0x40780c,   1, 0x04, 0x0a418820 },
+       { 0x407810,   1, 0x04, 0x062080e6 },
+       { 0x407814,   1, 0x04, 0x020398a4 },
+       { 0x407818,   1, 0x04, 0x0e629062 },
+       { 0x40781c,   1, 0x04, 0x0a418820 },
+       { 0x407820,   1, 0x04, 0x000000e6 },
+       { 0x4078bc,   1, 0x04, 0x00000103 },
+       {}
+};
+
+const struct gf100_gr_init
+gf100_grctx_init_scc_0[] = {
+       { 0x408000,   2, 0x04, 0x00000000 },
+       { 0x408008,   1, 0x04, 0x00000018 },
+       { 0x40800c,   2, 0x04, 0x00000000 },
+       { 0x408014,   1, 0x04, 0x00000069 },
+       { 0x408018,   1, 0x04, 0xe100e100 },
+       { 0x408064,   1, 0x04, 0x00000000 },
+       {}
+};
+
+static const struct gf100_gr_init
+gf100_grctx_init_be_0[] = {
+       { 0x408800,   1, 0x04, 0x02802a3c },
+       { 0x408804,   1, 0x04, 0x00000040 },
+       { 0x408808,   1, 0x04, 0x0003e00d },
+       { 0x408900,   1, 0x04, 0x3080b801 },
+       { 0x408904,   1, 0x04, 0x02000001 },
+       { 0x408908,   1, 0x04, 0x00c80929 },
+       { 0x408980,   1, 0x04, 0x0000011d },
+       {}
+};
+
+const struct gf100_gr_pack
+gf100_grctx_pack_hub[] = {
+       { gf100_grctx_init_main_0 },
+       { gf100_grctx_init_fe_0 },
+       { gf100_grctx_init_pri_0 },
+       { gf100_grctx_init_memfmt_0 },
+       { gf100_grctx_init_ds_0 },
+       { gf100_grctx_init_pd_0 },
+       { gf100_grctx_init_rstr2d_0 },
+       { gf100_grctx_init_scc_0 },
+       { gf100_grctx_init_be_0 },
+       {}
+};
+
+const struct gf100_gr_init
+gf100_grctx_init_gpc_unk_0[] = {
+       { 0x418380,   1, 0x04, 0x00000016 },
+       {}
+};
+
+const struct gf100_gr_init
+gf100_grctx_init_prop_0[] = {
+       { 0x418400,   1, 0x04, 0x38004e00 },
+       { 0x418404,   1, 0x04, 0x71e0ffff },
+       { 0x418408,   1, 0x04, 0x00000000 },
+       { 0x41840c,   1, 0x04, 0x00001008 },
+       { 0x418410,   1, 0x04, 0x0fff0fff },
+       { 0x418414,   1, 0x04, 0x00200fff },
+       { 0x418450,   6, 0x04, 0x00000000 },
+       { 0x418468,   1, 0x04, 0x00000001 },
+       { 0x41846c,   2, 0x04, 0x00000000 },
+       {}
+};
+
+const struct gf100_gr_init
+gf100_grctx_init_gpc_unk_1[] = {
+       { 0x418600,   1, 0x04, 0x0000001f },
+       { 0x418684,   1, 0x04, 0x0000000f },
+       { 0x418700,   1, 0x04, 0x00000002 },
+       { 0x418704,   1, 0x04, 0x00000080 },
+       { 0x418708,   1, 0x04, 0x00000000 },
+       { 0x41870c,   1, 0x04, 0x07c80000 },
+       { 0x418710,   1, 0x04, 0x00000000 },
+       {}
+};
+
+static const struct gf100_gr_init
+gf100_grctx_init_setup_0[] = {
+       { 0x418800,   1, 0x04, 0x0006860a },
+       { 0x418808,   3, 0x04, 0x00000000 },
+       { 0x418828,   1, 0x04, 0x00008442 },
+       { 0x418830,   1, 0x04, 0x00000001 },
+       { 0x4188d8,   1, 0x04, 0x00000008 },
+       { 0x4188e0,   1, 0x04, 0x01000000 },
+       { 0x4188e8,   5, 0x04, 0x00000000 },
+       { 0x4188fc,   1, 0x04, 0x00100000 },
+       {}
+};
+
+const struct gf100_gr_init
+gf100_grctx_init_zcull_0[] = {
+       { 0x41891c,   1, 0x04, 0x00ff00ff },
+       { 0x418924,   1, 0x04, 0x00000000 },
+       { 0x418928,   1, 0x04, 0x00ffff00 },
+       { 0x41892c,   1, 0x04, 0x0000ff00 },
+       {}
+};
+
+const struct gf100_gr_init
+gf100_grctx_init_crstr_0[] = {
+       { 0x418b00,   1, 0x04, 0x00000000 },
+       { 0x418b08,   1, 0x04, 0x0a418820 },
+       { 0x418b0c,   1, 0x04, 0x062080e6 },
+       { 0x418b10,   1, 0x04, 0x020398a4 },
+       { 0x418b14,   1, 0x04, 0x0e629062 },
+       { 0x418b18,   1, 0x04, 0x0a418820 },
+       { 0x418b1c,   1, 0x04, 0x000000e6 },
+       { 0x418bb8,   1, 0x04, 0x00000103 },
+       {}
+};
+
+const struct gf100_gr_init
+gf100_grctx_init_gpm_0[] = {
+       { 0x418c08,   1, 0x04, 0x00000001 },
+       { 0x418c10,   8, 0x04, 0x00000000 },
+       { 0x418c80,   1, 0x04, 0x20200004 },
+       { 0x418c8c,   1, 0x04, 0x00000001 },
+       {}
+};
+
+const struct gf100_gr_init
+gf100_grctx_init_gcc_0[] = {
+       { 0x419000,   1, 0x04, 0x00000780 },
+       { 0x419004,   2, 0x04, 0x00000000 },
+       { 0x419014,   1, 0x04, 0x00000004 },
+       {}
+};
+
+const struct gf100_gr_pack
+gf100_grctx_pack_gpc[] = {
+       { gf100_grctx_init_gpc_unk_0 },
+       { gf100_grctx_init_prop_0 },
+       { gf100_grctx_init_gpc_unk_1 },
+       { gf100_grctx_init_setup_0 },
+       { gf100_grctx_init_zcull_0 },
+       { gf100_grctx_init_crstr_0 },
+       { gf100_grctx_init_gpm_0 },
+       { gf100_grctx_init_gcc_0 },
+       {}
+};
+
+static const struct gf100_gr_init
+gf100_grctx_init_zcullr_0[] = {
+       { 0x418a00,   3, 0x04, 0x00000000 },
+       { 0x418a0c,   1, 0x04, 0x00010000 },
+       { 0x418a10,   3, 0x04, 0x00000000 },
+       { 0x418a20,   3, 0x04, 0x00000000 },
+       { 0x418a2c,   1, 0x04, 0x00010000 },
+       { 0x418a30,   3, 0x04, 0x00000000 },
+       { 0x418a40,   3, 0x04, 0x00000000 },
+       { 0x418a4c,   1, 0x04, 0x00010000 },
+       { 0x418a50,   3, 0x04, 0x00000000 },
+       { 0x418a60,   3, 0x04, 0x00000000 },
+       { 0x418a6c,   1, 0x04, 0x00010000 },
+       { 0x418a70,   3, 0x04, 0x00000000 },
+       { 0x418a80,   3, 0x04, 0x00000000 },
+       { 0x418a8c,   1, 0x04, 0x00010000 },
+       { 0x418a90,   3, 0x04, 0x00000000 },
+       { 0x418aa0,   3, 0x04, 0x00000000 },
+       { 0x418aac,   1, 0x04, 0x00010000 },
+       { 0x418ab0,   3, 0x04, 0x00000000 },
+       { 0x418ac0,   3, 0x04, 0x00000000 },
+       { 0x418acc,   1, 0x04, 0x00010000 },
+       { 0x418ad0,   3, 0x04, 0x00000000 },
+       { 0x418ae0,   3, 0x04, 0x00000000 },
+       { 0x418aec,   1, 0x04, 0x00010000 },
+       { 0x418af0,   3, 0x04, 0x00000000 },
+       {}
+};
+
+const struct gf100_gr_pack
+gf100_grctx_pack_zcull[] = {
+       { gf100_grctx_init_zcullr_0 },
+       {}
+};
+
+const struct gf100_gr_init
+gf100_grctx_init_pe_0[] = {
+       { 0x419818,   1, 0x04, 0x00000000 },
+       { 0x41983c,   1, 0x04, 0x00038bc7 },
+       { 0x419848,   1, 0x04, 0x00000000 },
+       { 0x419864,   1, 0x04, 0x0000012a },
+       { 0x419888,   1, 0x04, 0x00000000 },
+       {}
+};
+
+static const struct gf100_gr_init
+gf100_grctx_init_tex_0[] = {
+       { 0x419a00,   1, 0x04, 0x000001f0 },
+       { 0x419a04,   1, 0x04, 0x00000001 },
+       { 0x419a08,   1, 0x04, 0x00000023 },
+       { 0x419a0c,   1, 0x04, 0x00020000 },
+       { 0x419a10,   1, 0x04, 0x00000000 },
+       { 0x419a14,   1, 0x04, 0x00000200 },
+       {}
+};
+
+const struct gf100_gr_init
+gf100_grctx_init_wwdx_0[] = {
+       { 0x419b00,   1, 0x04, 0x0a418820 },
+       { 0x419b04,   1, 0x04, 0x062080e6 },
+       { 0x419b08,   1, 0x04, 0x020398a4 },
+       { 0x419b0c,   1, 0x04, 0x0e629062 },
+       { 0x419b10,   1, 0x04, 0x0a418820 },
+       { 0x419b14,   1, 0x04, 0x000000e6 },
+       { 0x419bd0,   1, 0x04, 0x00900103 },
+       { 0x419be0,   1, 0x04, 0x00000001 },
+       { 0x419be4,   1, 0x04, 0x00000000 },
+       {}
+};
+
+const struct gf100_gr_init
+gf100_grctx_init_mpc_0[] = {
+       { 0x419c00,   1, 0x04, 0x00000002 },
+       { 0x419c04,   1, 0x04, 0x00000006 },
+       { 0x419c08,   1, 0x04, 0x00000002 },
+       { 0x419c20,   1, 0x04, 0x00000000 },
+       {}
+};
+
+static const struct gf100_gr_init
+gf100_grctx_init_l1c_0[] = {
+       { 0x419cb0,   1, 0x04, 0x00060048 },
+       { 0x419ce8,   1, 0x04, 0x00000000 },
+       { 0x419cf4,   1, 0x04, 0x00000183 },
+       {}
+};
+
+const struct gf100_gr_init
+gf100_grctx_init_tpccs_0[] = {
+       { 0x419d20,   1, 0x04, 0x02180000 },
+       { 0x419d24,   1, 0x04, 0x00001fff },
+       {}
+};
+
+static const struct gf100_gr_init
+gf100_grctx_init_sm_0[] = {
+       { 0x419e04,   3, 0x04, 0x00000000 },
+       { 0x419e10,   1, 0x04, 0x00000002 },
+       { 0x419e44,   1, 0x04, 0x001beff2 },
+       { 0x419e48,   1, 0x04, 0x00000000 },
+       { 0x419e4c,   1, 0x04, 0x0000000f },
+       { 0x419e50,  17, 0x04, 0x00000000 },
+       { 0x419e98,   1, 0x04, 0x00000000 },
+       { 0x419f50,   2, 0x04, 0x00000000 },
+       {}
+};
+
+const struct gf100_gr_pack
+gf100_grctx_pack_tpc[] = {
+       { gf100_grctx_init_pe_0 },
+       { gf100_grctx_init_tex_0 },
+       { gf100_grctx_init_wwdx_0 },
+       { gf100_grctx_init_mpc_0 },
+       { gf100_grctx_init_l1c_0 },
+       { gf100_grctx_init_tpccs_0 },
+       { gf100_grctx_init_sm_0 },
+       {}
+};
+
+/*******************************************************************************
+ * PGRAPH context implementation
+ ******************************************************************************/
+
+int
+gf100_grctx_mmio_data(struct gf100_grctx *info, u32 size, u32 align, u32 access)
+{
+       if (info->data) {
+               info->buffer[info->buffer_nr] = round_up(info->addr, align);
+               info->addr = info->buffer[info->buffer_nr] + size;
+               info->data->size = size;
+               info->data->align = align;
+               info->data->access = access;
+               info->data++;
+               return info->buffer_nr++;
+       }
+       return -1;
+}
+
+void
+gf100_grctx_mmio_item(struct gf100_grctx *info, u32 addr, u32 data,
+                     int shift, int buffer)
+{
+       if (info->data) {
+               if (shift >= 0) {
+                       info->mmio->addr = addr;
+                       info->mmio->data = data;
+                       info->mmio->shift = shift;
+                       info->mmio->buffer = buffer;
+                       if (buffer >= 0)
+                               data |= info->buffer[buffer] >> shift;
+                       info->mmio++;
+               } else
+                       return;
+       } else {
+               if (buffer >= 0)
+                       return;
+       }
+
+       nv_wr32(info->priv, addr, data);
+}
+
+void
+gf100_grctx_generate_bundle(struct gf100_grctx *info)
+{
+       const struct gf100_grctx_oclass *impl = gf100_grctx_impl(info->priv);
+       const u32 access = NV_MEM_ACCESS_RW | NV_MEM_ACCESS_SYS;
+       const int s = 8;
+       const int b = mmio_vram(info, impl->bundle_size, (1 << s), access);
+       mmio_refn(info, 0x408004, 0x00000000, s, b);
+       mmio_refn(info, 0x408008, 0x80000000 | (impl->bundle_size >> s), 0, b);
+       mmio_refn(info, 0x418808, 0x00000000, s, b);
+       mmio_refn(info, 0x41880c, 0x80000000 | (impl->bundle_size >> s), 0, b);
+}
+
+void
+gf100_grctx_generate_pagepool(struct gf100_grctx *info)
+{
+       const struct gf100_grctx_oclass *impl = gf100_grctx_impl(info->priv);
+       const u32 access = NV_MEM_ACCESS_RW | NV_MEM_ACCESS_SYS;
+       const int s = 8;
+       const int b = mmio_vram(info, impl->pagepool_size, (1 << s), access);
+       mmio_refn(info, 0x40800c, 0x00000000, s, b);
+       mmio_wr32(info, 0x408010, 0x80000000);
+       mmio_refn(info, 0x419004, 0x00000000, s, b);
+       mmio_wr32(info, 0x419008, 0x00000000);
+}
+
+void
+gf100_grctx_generate_attrib(struct gf100_grctx *info)
+{
+       struct gf100_gr_priv *priv = info->priv;
+       const struct gf100_grctx_oclass *impl = gf100_grctx_impl(priv);
+       const u32 attrib = impl->attrib_nr;
+       const u32   size = 0x20 * (impl->attrib_nr_max + impl->alpha_nr_max);
+       const u32 access = NV_MEM_ACCESS_RW;
+       const int s = 12;
+       const int b = mmio_vram(info, size * priv->tpc_total, (1 << s), access);
+       int gpc, tpc;
+       u32 bo = 0;
+
+       mmio_refn(info, 0x418810, 0x80000000, s, b);
+       mmio_refn(info, 0x419848, 0x10000000, s, b);
+       mmio_wr32(info, 0x405830, (attrib << 16));
+
+       for (gpc = 0; gpc < priv->gpc_nr; gpc++) {
+               for (tpc = 0; tpc < priv->tpc_nr[gpc]; tpc++) {
+                       const u32 o = TPC_UNIT(gpc, tpc, 0x0520);
+                       mmio_skip(info, o, (attrib << 16) | ++bo);
+                       mmio_wr32(info, o, (attrib << 16) | --bo);
+                       bo += impl->attrib_nr_max;
+               }
+       }
+}
+
+void
+gf100_grctx_generate_unkn(struct gf100_gr_priv *priv)
+{
+}
+
+void
+gf100_grctx_generate_tpcid(struct gf100_gr_priv *priv)
+{
+       int gpc, tpc, id;
+
+       for (tpc = 0, id = 0; tpc < 4; tpc++) {
+               for (gpc = 0; gpc < priv->gpc_nr; gpc++) {
+                       if (tpc < priv->tpc_nr[gpc]) {
+                               nv_wr32(priv, TPC_UNIT(gpc, tpc, 0x698), id);
+                               nv_wr32(priv, TPC_UNIT(gpc, tpc, 0x4e8), id);
+                               nv_wr32(priv, GPC_UNIT(gpc, 0x0c10 + tpc * 4), id);
+                               nv_wr32(priv, TPC_UNIT(gpc, tpc, 0x088), id);
+                               id++;
+                       }
+
+                       nv_wr32(priv, GPC_UNIT(gpc, 0x0c08), priv->tpc_nr[gpc]);
+                       nv_wr32(priv, GPC_UNIT(gpc, 0x0c8c), priv->tpc_nr[gpc]);
+               }
+       }
+}
+
+void
+gf100_grctx_generate_r406028(struct gf100_gr_priv *priv)
+{
+       u32 tmp[GPC_MAX / 8] = {}, i = 0;
+       for (i = 0; i < priv->gpc_nr; i++)
+               tmp[i / 8] |= priv->tpc_nr[i] << ((i % 8) * 4);
+       for (i = 0; i < 4; i++) {
+               nv_wr32(priv, 0x406028 + (i * 4), tmp[i]);
+               nv_wr32(priv, 0x405870 + (i * 4), tmp[i]);
+       }
+}
+
+void
+gf100_grctx_generate_r4060a8(struct gf100_gr_priv *priv)
+{
+       u8  tpcnr[GPC_MAX], data[TPC_MAX];
+       int gpc, tpc, i;
+
+       memcpy(tpcnr, priv->tpc_nr, sizeof(priv->tpc_nr));
+       memset(data, 0x1f, sizeof(data));
+
+       gpc = -1;
+       for (tpc = 0; tpc < priv->tpc_total; tpc++) {
+               do {
+                       gpc = (gpc + 1) % priv->gpc_nr;
+               } while (!tpcnr[gpc]);
+               tpcnr[gpc]--;
+               data[tpc] = gpc;
+       }
+
+       for (i = 0; i < 4; i++)
+               nv_wr32(priv, 0x4060a8 + (i * 4), ((u32 *)data)[i]);
+}
+
+void
+gf100_grctx_generate_r418bb8(struct gf100_gr_priv *priv)
+{
+       u32 data[6] = {}, data2[2] = {};
+       u8  tpcnr[GPC_MAX];
+       u8  shift, ntpcv;
+       int gpc, tpc, i;
+
+       /* calculate first set of magics */
+       memcpy(tpcnr, priv->tpc_nr, sizeof(priv->tpc_nr));
+
+       gpc = -1;
+       for (tpc = 0; tpc < priv->tpc_total; tpc++) {
+               do {
+                       gpc = (gpc + 1) % priv->gpc_nr;
+               } while (!tpcnr[gpc]);
+               tpcnr[gpc]--;
+
+               data[tpc / 6] |= gpc << ((tpc % 6) * 5);
+       }
+
+       for (; tpc < 32; tpc++)
+               data[tpc / 6] |= 7 << ((tpc % 6) * 5);
+
+       /* and the second... */
+       shift = 0;
+       ntpcv = priv->tpc_total;
+       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(priv, 0x418bb8, (priv->tpc_total << 8) |
+                                priv->magic_not_rop_nr);
+       for (i = 0; i < 6; i++)
+               nv_wr32(priv, 0x418b08 + (i * 4), data[i]);
+
+       /* GPC_BROADCAST.TP_BROADCAST */
+       nv_wr32(priv, 0x419bd0, (priv->tpc_total << 8) |
+                                priv->magic_not_rop_nr | data2[0]);
+       nv_wr32(priv, 0x419be4, data2[1]);
+       for (i = 0; i < 6; i++)
+               nv_wr32(priv, 0x419b00 + (i * 4), data[i]);
+
+       /* UNK78xx */
+       nv_wr32(priv, 0x4078bc, (priv->tpc_total << 8) |
+                                priv->magic_not_rop_nr);
+       for (i = 0; i < 6; i++)
+               nv_wr32(priv, 0x40780c + (i * 4), data[i]);
+}
+
+void
+gf100_grctx_generate_r406800(struct gf100_gr_priv *priv)
+{
+       u64 tpc_mask = 0, tpc_set = 0;
+       u8  tpcnr[GPC_MAX];
+       int gpc, tpc;
+       int i, a, b;
+
+       memcpy(tpcnr, priv->tpc_nr, sizeof(priv->tpc_nr));
+       for (gpc = 0; gpc < priv->gpc_nr; gpc++)
+               tpc_mask |= ((1ULL << priv->tpc_nr[gpc]) - 1) << (gpc * 8);
+
+       for (i = 0, gpc = -1, b = -1; i < 32; i++) {
+               a = (i * (priv->tpc_total - 1)) / 32;
+               if (a != b) {
+                       b = a;
+                       do {
+                               gpc = (gpc + 1) % priv->gpc_nr;
+                       } while (!tpcnr[gpc]);
+                       tpc = priv->tpc_nr[gpc] - tpcnr[gpc]--;
+
+                       tpc_set |= 1ULL << ((gpc * 8) + tpc);
+               }
+
+               nv_wr32(priv, 0x406800 + (i * 0x20), lower_32_bits(tpc_set));
+               nv_wr32(priv, 0x406c00 + (i * 0x20), lower_32_bits(tpc_set ^ tpc_mask));
+               if (priv->gpc_nr > 4) {
+                       nv_wr32(priv, 0x406804 + (i * 0x20), upper_32_bits(tpc_set));
+                       nv_wr32(priv, 0x406c04 + (i * 0x20), upper_32_bits(tpc_set ^ tpc_mask));
+               }
+       }
+}
+
+void
+gf100_grctx_generate_main(struct gf100_gr_priv *priv, struct gf100_grctx *info)
+{
+       struct gf100_grctx_oclass *oclass = (void *)nv_engine(priv)->cclass;
+
+       nvkm_mc(priv)->unk260(nvkm_mc(priv), 0);
+
+       gf100_gr_mmio(priv, oclass->hub);
+       gf100_gr_mmio(priv, oclass->gpc);
+       gf100_gr_mmio(priv, oclass->zcull);
+       gf100_gr_mmio(priv, oclass->tpc);
+       gf100_gr_mmio(priv, oclass->ppc);
+
+       nv_wr32(priv, 0x404154, 0x00000000);
+
+       oclass->bundle(info);
+       oclass->pagepool(info);
+       oclass->attrib(info);
+       oclass->unkn(priv);
+
+       gf100_grctx_generate_tpcid(priv);
+       gf100_grctx_generate_r406028(priv);
+       gf100_grctx_generate_r4060a8(priv);
+       gf100_grctx_generate_r418bb8(priv);
+       gf100_grctx_generate_r406800(priv);
+
+       gf100_gr_icmd(priv, oclass->icmd);
+       nv_wr32(priv, 0x404154, 0x00000400);
+       gf100_gr_mthd(priv, oclass->mthd);
+       nvkm_mc(priv)->unk260(nvkm_mc(priv), 1);
+}
+
+int
+gf100_grctx_generate(struct gf100_gr_priv *priv)
+{
+       struct gf100_grctx_oclass *oclass = (void *)nv_engine(priv)->cclass;
+       struct nvkm_bar *bar = nvkm_bar(priv);
+       struct nvkm_gpuobj *chan;
+       struct gf100_grctx info;
+       int ret, i;
+
+       /* allocate memory to for a "channel", which we'll use to generate
+        * the default context values
+        */
+       ret = nvkm_gpuobj_new(nv_object(priv), NULL, 0x80000 + priv->size,
+                             0x1000, NVOBJ_FLAG_ZERO_ALLOC, &chan);
+       if (ret) {
+               nv_error(priv, "failed to allocate channel memory, %d\n", ret);
+               return ret;
+       }
+
+       /* PGD pointer */
+       nv_wo32(chan, 0x0200, lower_32_bits(chan->addr + 0x1000));
+       nv_wo32(chan, 0x0204, upper_32_bits(chan->addr + 0x1000));
+       nv_wo32(chan, 0x0208, 0xffffffff);
+       nv_wo32(chan, 0x020c, 0x000000ff);
+
+       /* PGT[0] pointer */
+       nv_wo32(chan, 0x1000, 0x00000000);
+       nv_wo32(chan, 0x1004, 0x00000001 | (chan->addr + 0x2000) >> 8);
+
+       /* identity-map the whole "channel" into its own vm */
+       for (i = 0; i < chan->size / 4096; i++) {
+               u64 addr = ((chan->addr + (i * 4096)) >> 8) | 1;
+               nv_wo32(chan, 0x2000 + (i * 8), lower_32_bits(addr));
+               nv_wo32(chan, 0x2004 + (i * 8), upper_32_bits(addr));
+       }
+
+       /* context pointer (virt) */
+       nv_wo32(chan, 0x0210, 0x00080004);
+       nv_wo32(chan, 0x0214, 0x00000000);
+
+       bar->flush(bar);
+
+       nv_wr32(priv, 0x100cb8, (chan->addr + 0x1000) >> 8);
+       nv_wr32(priv, 0x100cbc, 0x80000001);
+       nv_wait(priv, 0x100c80, 0x00008000, 0x00008000);
+
+       /* setup default state for mmio list construction */
+       info.priv = priv;
+       info.data = priv->mmio_data;
+       info.mmio = priv->mmio_list;
+       info.addr = 0x2000 + (i * 8);
+       info.buffer_nr = 0;
+
+       /* make channel current */
+       if (priv->firmware) {
+               nv_wr32(priv, 0x409840, 0x00000030);
+               nv_wr32(priv, 0x409500, 0x80000000 | chan->addr >> 12);
+               nv_wr32(priv, 0x409504, 0x00000003);
+               if (!nv_wait(priv, 0x409800, 0x00000010, 0x00000010))
+                       nv_error(priv, "load_ctx timeout\n");
+
+               nv_wo32(chan, 0x8001c, 1);
+               nv_wo32(chan, 0x80020, 0);
+               nv_wo32(chan, 0x80028, 0);
+               nv_wo32(chan, 0x8002c, 0);
+               bar->flush(bar);
+       } else {
+               nv_wr32(priv, 0x409840, 0x80000000);
+               nv_wr32(priv, 0x409500, 0x80000000 | chan->addr >> 12);
+               nv_wr32(priv, 0x409504, 0x00000001);
+               if (!nv_wait(priv, 0x409800, 0x80000000, 0x80000000))
+                       nv_error(priv, "HUB_SET_CHAN timeout\n");
+       }
+
+       oclass->main(priv, &info);
+
+       /* trigger a context unload by unsetting the "next channel valid" bit
+        * and faking a context switch interrupt
+        */
+       nv_mask(priv, 0x409b04, 0x80000000, 0x00000000);
+       nv_wr32(priv, 0x409000, 0x00000100);
+       if (!nv_wait(priv, 0x409b00, 0x80000000, 0x00000000)) {
+               nv_error(priv, "grctx template channel unload timeout\n");
+               ret = -EBUSY;
+               goto done;
+       }
+
+       priv->data = kmalloc(priv->size, GFP_KERNEL);
+       if (priv->data) {
+               for (i = 0; i < priv->size; i += 4)
+                       priv->data[i / 4] = nv_ro32(chan, 0x80000 + i);
+               ret = 0;
+       } else {
+               ret = -ENOMEM;
+       }
+
+done:
+       nvkm_gpuobj_ref(NULL, &chan);
+       return ret;
+}
+
+struct nvkm_oclass *
+gf100_grctx_oclass = &(struct gf100_grctx_oclass) {
+       .base.handle = NV_ENGCTX(GR, 0xc0),
+       .base.ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = gf100_gr_context_ctor,
+               .dtor = gf100_gr_context_dtor,
+               .init = _nvkm_gr_context_init,
+               .fini = _nvkm_gr_context_fini,
+               .rd32 = _nvkm_gr_context_rd32,
+               .wr32 = _nvkm_gr_context_wr32,
+       },
+       .main  = gf100_grctx_generate_main,
+       .unkn  = gf100_grctx_generate_unkn,
+       .hub   = gf100_grctx_pack_hub,
+       .gpc   = gf100_grctx_pack_gpc,
+       .zcull = gf100_grctx_pack_zcull,
+       .tpc   = gf100_grctx_pack_tpc,
+       .icmd  = gf100_grctx_pack_icmd,
+       .mthd  = gf100_grctx_pack_mthd,
+       .bundle = gf100_grctx_generate_bundle,
+       .bundle_size = 0x1800,
+       .pagepool = gf100_grctx_generate_pagepool,
+       .pagepool_size = 0x8000,
+       .attrib = gf100_grctx_generate_attrib,
+       .attrib_nr_max = 0x324,
+       .attrib_nr = 0x218,
+}.base;
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/gr/ctxgf100.h b/drivers/gpu/drm/nouveau/nvkm/engine/gr/ctxgf100.h
new file mode 100644 (file)
index 0000000..1166b1a
--- /dev/null
@@ -0,0 +1,199 @@
+#ifndef __NVKM_GRCTX_NVC0_H__
+#define __NVKM_GRCTX_NVC0_H__
+#include "gf100.h"
+
+struct gf100_grctx {
+       struct gf100_gr_priv *priv;
+       struct gf100_gr_data *data;
+       struct gf100_gr_mmio *mmio;
+       int buffer_nr;
+       u64 buffer[4];
+       u64 addr;
+};
+
+int  gf100_grctx_mmio_data(struct gf100_grctx *, u32 size, u32 align, u32 access);
+void gf100_grctx_mmio_item(struct gf100_grctx *, u32 addr, u32 data, int s, int);
+
+#define mmio_vram(a,b,c,d) gf100_grctx_mmio_data((a), (b), (c), (d))
+#define mmio_refn(a,b,c,d,e) gf100_grctx_mmio_item((a), (b), (c), (d), (e))
+#define mmio_skip(a,b,c) mmio_refn((a), (b), (c), -1, -1)
+#define mmio_wr32(a,b,c) mmio_refn((a), (b), (c),  0, -1)
+
+struct gf100_grctx_oclass {
+       struct nvkm_oclass base;
+       /* main context generation function */
+       void  (*main)(struct gf100_gr_priv *, struct gf100_grctx *);
+       /* context-specific modify-on-first-load list generation function */
+       void  (*unkn)(struct gf100_gr_priv *);
+       /* mmio context data */
+       const struct gf100_gr_pack *hub;
+       const struct gf100_gr_pack *gpc;
+       const struct gf100_gr_pack *zcull;
+       const struct gf100_gr_pack *tpc;
+       const struct gf100_gr_pack *ppc;
+       /* indirect context data, generated with icmds/mthds */
+       const struct gf100_gr_pack *icmd;
+       const struct gf100_gr_pack *mthd;
+       /* bundle circular buffer */
+       void (*bundle)(struct gf100_grctx *);
+       u32 bundle_size;
+       u32 bundle_min_gpm_fifo_depth;
+       u32 bundle_token_limit;
+       /* pagepool */
+       void (*pagepool)(struct gf100_grctx *);
+       u32 pagepool_size;
+       /* attribute(/alpha) circular buffer */
+       void (*attrib)(struct gf100_grctx *);
+       u32 attrib_nr_max;
+       u32 attrib_nr;
+       u32 alpha_nr_max;
+       u32 alpha_nr;
+};
+
+static inline const struct gf100_grctx_oclass *
+gf100_grctx_impl(struct gf100_gr_priv *priv)
+{
+       return (void *)nv_engine(priv)->cclass;
+}
+
+extern struct nvkm_oclass *gf100_grctx_oclass;
+int  gf100_grctx_generate(struct gf100_gr_priv *);
+void gf100_grctx_generate_main(struct gf100_gr_priv *, struct gf100_grctx *);
+void gf100_grctx_generate_bundle(struct gf100_grctx *);
+void gf100_grctx_generate_pagepool(struct gf100_grctx *);
+void gf100_grctx_generate_attrib(struct gf100_grctx *);
+void gf100_grctx_generate_unkn(struct gf100_gr_priv *);
+void gf100_grctx_generate_tpcid(struct gf100_gr_priv *);
+void gf100_grctx_generate_r406028(struct gf100_gr_priv *);
+void gf100_grctx_generate_r4060a8(struct gf100_gr_priv *);
+void gf100_grctx_generate_r418bb8(struct gf100_gr_priv *);
+void gf100_grctx_generate_r406800(struct gf100_gr_priv *);
+
+extern struct nvkm_oclass *gf108_grctx_oclass;
+void gf108_grctx_generate_attrib(struct gf100_grctx *);
+void gf108_grctx_generate_unkn(struct gf100_gr_priv *);
+
+extern struct nvkm_oclass *gf104_grctx_oclass;
+extern struct nvkm_oclass *gf110_grctx_oclass;
+
+extern struct nvkm_oclass *gf117_grctx_oclass;
+void gf117_grctx_generate_attrib(struct gf100_grctx *);
+
+extern struct nvkm_oclass *gf119_grctx_oclass;
+
+extern struct nvkm_oclass *gk104_grctx_oclass;
+extern struct nvkm_oclass *gk20a_grctx_oclass;
+void gk104_grctx_generate_main(struct gf100_gr_priv *, struct gf100_grctx *);
+void gk104_grctx_generate_bundle(struct gf100_grctx *);
+void gk104_grctx_generate_pagepool(struct gf100_grctx *);
+void gk104_grctx_generate_unkn(struct gf100_gr_priv *);
+void gk104_grctx_generate_r418bb8(struct gf100_gr_priv *);
+
+extern struct nvkm_oclass *gk110_grctx_oclass;
+extern struct nvkm_oclass *gk110b_grctx_oclass;
+extern struct nvkm_oclass *gk208_grctx_oclass;
+extern struct nvkm_oclass *gm107_grctx_oclass;
+
+/* context init value lists */
+
+extern const struct gf100_gr_pack gf100_grctx_pack_icmd[];
+
+extern const struct gf100_gr_pack gf100_grctx_pack_mthd[];
+extern const struct gf100_gr_init gf100_grctx_init_902d_0[];
+extern const struct gf100_gr_init gf100_grctx_init_9039_0[];
+extern const struct gf100_gr_init gf100_grctx_init_90c0_0[];
+
+extern const struct gf100_gr_pack gf100_grctx_pack_hub[];
+extern const struct gf100_gr_init gf100_grctx_init_main_0[];
+extern const struct gf100_gr_init gf100_grctx_init_fe_0[];
+extern const struct gf100_gr_init gf100_grctx_init_pri_0[];
+extern const struct gf100_gr_init gf100_grctx_init_memfmt_0[];
+extern const struct gf100_gr_init gf100_grctx_init_rstr2d_0[];
+extern const struct gf100_gr_init gf100_grctx_init_scc_0[];
+
+extern const struct gf100_gr_pack gf100_grctx_pack_gpc[];
+extern const struct gf100_gr_init gf100_grctx_init_gpc_unk_0[];
+extern const struct gf100_gr_init gf100_grctx_init_prop_0[];
+extern const struct gf100_gr_init gf100_grctx_init_gpc_unk_1[];
+extern const struct gf100_gr_init gf100_grctx_init_zcull_0[];
+extern const struct gf100_gr_init gf100_grctx_init_crstr_0[];
+extern const struct gf100_gr_init gf100_grctx_init_gpm_0[];
+extern const struct gf100_gr_init gf100_grctx_init_gcc_0[];
+
+extern const struct gf100_gr_pack gf100_grctx_pack_zcull[];
+
+extern const struct gf100_gr_pack gf100_grctx_pack_tpc[];
+extern const struct gf100_gr_init gf100_grctx_init_pe_0[];
+extern const struct gf100_gr_init gf100_grctx_init_wwdx_0[];
+extern const struct gf100_gr_init gf100_grctx_init_mpc_0[];
+extern const struct gf100_gr_init gf100_grctx_init_tpccs_0[];
+
+extern const struct gf100_gr_init gf104_grctx_init_tex_0[];
+extern const struct gf100_gr_init gf104_grctx_init_l1c_0[];
+extern const struct gf100_gr_init gf104_grctx_init_sm_0[];
+
+extern const struct gf100_gr_init gf108_grctx_init_9097_0[];
+
+extern const struct gf100_gr_init gf108_grctx_init_gpm_0[];
+
+extern const struct gf100_gr_init gf108_grctx_init_pe_0[];
+extern const struct gf100_gr_init gf108_grctx_init_wwdx_0[];
+extern const struct gf100_gr_init gf108_grctx_init_tpccs_0[];
+
+extern const struct gf100_gr_init gf110_grctx_init_9197_0[];
+extern const struct gf100_gr_init gf110_grctx_init_9297_0[];
+
+extern const struct gf100_gr_pack gf119_grctx_pack_icmd[];
+
+extern const struct gf100_gr_pack gf119_grctx_pack_mthd[];
+
+extern const struct gf100_gr_init gf119_grctx_init_fe_0[];
+extern const struct gf100_gr_init gf119_grctx_init_be_0[];
+
+extern const struct gf100_gr_init gf119_grctx_init_prop_0[];
+extern const struct gf100_gr_init gf119_grctx_init_gpc_unk_1[];
+extern const struct gf100_gr_init gf119_grctx_init_crstr_0[];
+
+extern const struct gf100_gr_init gf119_grctx_init_sm_0[];
+
+extern const struct gf100_gr_init gf117_grctx_init_pe_0[];
+
+extern const struct gf100_gr_init gf117_grctx_init_wwdx_0[];
+
+extern const struct gf100_gr_init gk104_grctx_init_memfmt_0[];
+extern const struct gf100_gr_init gk104_grctx_init_ds_0[];
+extern const struct gf100_gr_init gk104_grctx_init_scc_0[];
+
+extern const struct gf100_gr_init gk104_grctx_init_gpm_0[];
+
+extern const struct gf100_gr_init gk104_grctx_init_pes_0[];
+
+extern const struct gf100_gr_pack gk104_grctx_pack_hub[];
+extern const struct gf100_gr_pack gk104_grctx_pack_gpc[];
+extern const struct gf100_gr_pack gk104_grctx_pack_tpc[];
+extern const struct gf100_gr_pack gk104_grctx_pack_ppc[];
+extern const struct gf100_gr_pack gk104_grctx_pack_icmd[];
+extern const struct gf100_gr_init gk104_grctx_init_a097_0[];
+
+extern const struct gf100_gr_pack gk110_grctx_pack_icmd[];
+
+extern const struct gf100_gr_pack gk110_grctx_pack_mthd[];
+
+extern const struct gf100_gr_pack gk110_grctx_pack_hub[];
+extern const struct gf100_gr_init gk110_grctx_init_pri_0[];
+extern const struct gf100_gr_init gk110_grctx_init_cwd_0[];
+
+extern const struct gf100_gr_pack gk110_grctx_pack_gpc[];
+extern const struct gf100_gr_init gk110_grctx_init_gpc_unk_2[];
+
+extern const struct gf100_gr_init gk110_grctx_init_tex_0[];
+extern const struct gf100_gr_init gk110_grctx_init_mpc_0[];
+extern const struct gf100_gr_init gk110_grctx_init_l1c_0[];
+
+extern const struct gf100_gr_pack gk110_grctx_pack_ppc[];
+
+extern const struct gf100_gr_init gk208_grctx_init_rstr2d_0[];
+
+extern const struct gf100_gr_init gk208_grctx_init_prop_0[];
+extern const struct gf100_gr_init gk208_grctx_init_crstr_0[];
+#endif
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/gr/ctxgf104.c b/drivers/gpu/drm/nouveau/nvkm/engine/gr/ctxgf104.c
new file mode 100644 (file)
index 0000000..c5a8d55
--- /dev/null
@@ -0,0 +1,108 @@
+/*
+ * Copyright 2013 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 <bskeggs@redhat.com>
+ */
+#include "ctxgf100.h"
+
+/*******************************************************************************
+ * PGRAPH context register lists
+ ******************************************************************************/
+
+const struct gf100_gr_init
+gf104_grctx_init_tex_0[] = {
+       { 0x419a00,   1, 0x04, 0x000001f0 },
+       { 0x419a04,   1, 0x04, 0x00000001 },
+       { 0x419a08,   1, 0x04, 0x00000023 },
+       { 0x419a0c,   1, 0x04, 0x00020000 },
+       { 0x419a10,   1, 0x04, 0x00000000 },
+       { 0x419a14,   1, 0x04, 0x00000200 },
+       { 0x419a1c,   1, 0x04, 0x00000000 },
+       { 0x419a20,   1, 0x04, 0x00000800 },
+       { 0x419ac4,   1, 0x04, 0x0007f440 },
+       {}
+};
+
+const struct gf100_gr_init
+gf104_grctx_init_l1c_0[] = {
+       { 0x419cb0,   1, 0x04, 0x00020048 },
+       { 0x419ce8,   1, 0x04, 0x00000000 },
+       { 0x419cf4,   1, 0x04, 0x00000183 },
+       {}
+};
+
+const struct gf100_gr_init
+gf104_grctx_init_sm_0[] = {
+       { 0x419e04,   3, 0x04, 0x00000000 },
+       { 0x419e10,   1, 0x04, 0x00000002 },
+       { 0x419e44,   1, 0x04, 0x001beff2 },
+       { 0x419e48,   1, 0x04, 0x00000000 },
+       { 0x419e4c,   1, 0x04, 0x0000000f },
+       { 0x419e50,  17, 0x04, 0x00000000 },
+       { 0x419e98,   1, 0x04, 0x00000000 },
+       { 0x419ee0,   1, 0x04, 0x00011110 },
+       { 0x419f30,  11, 0x04, 0x00000000 },
+       {}
+};
+
+static const struct gf100_gr_pack
+gf104_grctx_pack_tpc[] = {
+       { gf100_grctx_init_pe_0 },
+       { gf104_grctx_init_tex_0 },
+       { gf100_grctx_init_wwdx_0 },
+       { gf100_grctx_init_mpc_0 },
+       { gf104_grctx_init_l1c_0 },
+       { gf100_grctx_init_tpccs_0 },
+       { gf104_grctx_init_sm_0 },
+       {}
+};
+
+/*******************************************************************************
+ * PGRAPH context implementation
+ ******************************************************************************/
+
+struct nvkm_oclass *
+gf104_grctx_oclass = &(struct gf100_grctx_oclass) {
+       .base.handle = NV_ENGCTX(GR, 0xc3),
+       .base.ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = gf100_gr_context_ctor,
+               .dtor = gf100_gr_context_dtor,
+               .init = _nvkm_gr_context_init,
+               .fini = _nvkm_gr_context_fini,
+               .rd32 = _nvkm_gr_context_rd32,
+               .wr32 = _nvkm_gr_context_wr32,
+       },
+       .main  = gf100_grctx_generate_main,
+       .unkn  = gf100_grctx_generate_unkn,
+       .hub   = gf100_grctx_pack_hub,
+       .gpc   = gf100_grctx_pack_gpc,
+       .zcull = gf100_grctx_pack_zcull,
+       .tpc   = gf104_grctx_pack_tpc,
+       .icmd  = gf100_grctx_pack_icmd,
+       .mthd  = gf100_grctx_pack_mthd,
+       .bundle = gf100_grctx_generate_bundle,
+       .bundle_size = 0x1800,
+       .pagepool = gf100_grctx_generate_pagepool,
+       .pagepool_size = 0x8000,
+       .attrib = gf100_grctx_generate_attrib,
+       .attrib_nr_max = 0x324,
+       .attrib_nr = 0x218,
+}.base;
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/gr/ctxgf108.c b/drivers/gpu/drm/nouveau/nvkm/engine/gr/ctxgf108.c
new file mode 100644 (file)
index 0000000..87c844a
--- /dev/null
@@ -0,0 +1,806 @@
+/*
+ * Copyright 2013 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 <bskeggs@redhat.com>
+ */
+#include "ctxgf100.h"
+
+#include <subdev/fb.h>
+
+/*******************************************************************************
+ * PGRAPH context register lists
+ ******************************************************************************/
+
+static const struct gf100_gr_init
+gf108_grctx_init_icmd_0[] = {
+       { 0x001000,   1, 0x01, 0x00000004 },
+       { 0x0000a9,   1, 0x01, 0x0000ffff },
+       { 0x000038,   1, 0x01, 0x0fac6881 },
+       { 0x00003d,   1, 0x01, 0x00000001 },
+       { 0x0000e8,   8, 0x01, 0x00000400 },
+       { 0x000078,   8, 0x01, 0x00000300 },
+       { 0x000050,   1, 0x01, 0x00000011 },
+       { 0x000058,   8, 0x01, 0x00000008 },
+       { 0x000208,   8, 0x01, 0x00000001 },
+       { 0x000081,   1, 0x01, 0x00000001 },
+       { 0x000085,   1, 0x01, 0x00000004 },
+       { 0x000088,   1, 0x01, 0x00000400 },
+       { 0x000090,   1, 0x01, 0x00000300 },
+       { 0x000098,   1, 0x01, 0x00001001 },
+       { 0x0000e3,   1, 0x01, 0x00000001 },
+       { 0x0000da,   1, 0x01, 0x00000001 },
+       { 0x0000f8,   1, 0x01, 0x00000003 },
+       { 0x0000fa,   1, 0x01, 0x00000001 },
+       { 0x00009f,   4, 0x01, 0x0000ffff },
+       { 0x0000b1,   1, 0x01, 0x00000001 },
+       { 0x0000b2,  40, 0x01, 0x00000000 },
+       { 0x000210,   8, 0x01, 0x00000040 },
+       { 0x000218,   8, 0x01, 0x0000c080 },
+       { 0x0000ad,   1, 0x01, 0x0000013e },
+       { 0x0000e1,   1, 0x01, 0x00000010 },
+       { 0x000290,  16, 0x01, 0x00000000 },
+       { 0x0003b0,  16, 0x01, 0x00000000 },
+       { 0x0002a0,  16, 0x01, 0x00000000 },
+       { 0x000420,  16, 0x01, 0x00000000 },
+       { 0x0002b0,  16, 0x01, 0x00000000 },
+       { 0x000430,  16, 0x01, 0x00000000 },
+       { 0x0002c0,  16, 0x01, 0x00000000 },
+       { 0x0004d0,  16, 0x01, 0x00000000 },
+       { 0x000720,  16, 0x01, 0x00000000 },
+       { 0x0008c0,  16, 0x01, 0x00000000 },
+       { 0x000890,  16, 0x01, 0x00000000 },
+       { 0x0008e0,  16, 0x01, 0x00000000 },
+       { 0x0008a0,  16, 0x01, 0x00000000 },
+       { 0x0008f0,  16, 0x01, 0x00000000 },
+       { 0x00094c,   1, 0x01, 0x000000ff },
+       { 0x00094d,   1, 0x01, 0xffffffff },
+       { 0x00094e,   1, 0x01, 0x00000002 },
+       { 0x0002ec,   1, 0x01, 0x00000001 },
+       { 0x000303,   1, 0x01, 0x00000001 },
+       { 0x0002e6,   1, 0x01, 0x00000001 },
+       { 0x000466,   1, 0x01, 0x00000052 },
+       { 0x000301,   1, 0x01, 0x3f800000 },
+       { 0x000304,   1, 0x01, 0x30201000 },
+       { 0x000305,   1, 0x01, 0x70605040 },
+       { 0x000306,   1, 0x01, 0xb8a89888 },
+       { 0x000307,   1, 0x01, 0xf8e8d8c8 },
+       { 0x00030a,   1, 0x01, 0x00ffff00 },
+       { 0x00030b,   1, 0x01, 0x0000001a },
+       { 0x00030c,   1, 0x01, 0x00000001 },
+       { 0x000318,   1, 0x01, 0x00000001 },
+       { 0x000340,   1, 0x01, 0x00000000 },
+       { 0x000375,   1, 0x01, 0x00000001 },
+       { 0x000351,   1, 0x01, 0x00000100 },
+       { 0x00037d,   1, 0x01, 0x00000006 },
+       { 0x0003a0,   1, 0x01, 0x00000002 },
+       { 0x0003aa,   1, 0x01, 0x00000001 },
+       { 0x0003a9,   1, 0x01, 0x00000001 },
+       { 0x000380,   1, 0x01, 0x00000001 },
+       { 0x000360,   1, 0x01, 0x00000040 },
+       { 0x000366,   2, 0x01, 0x00000000 },
+       { 0x000368,   1, 0x01, 0x00001fff },
+       { 0x000370,   2, 0x01, 0x00000000 },
+       { 0x000372,   1, 0x01, 0x003fffff },
+       { 0x00037a,   1, 0x01, 0x00000012 },
+       { 0x0005e0,   5, 0x01, 0x00000022 },
+       { 0x000619,   1, 0x01, 0x00000003 },
+       { 0x000811,   1, 0x01, 0x00000003 },
+       { 0x000812,   1, 0x01, 0x00000004 },
+       { 0x000813,   1, 0x01, 0x00000006 },
+       { 0x000814,   1, 0x01, 0x00000008 },
+       { 0x000815,   1, 0x01, 0x0000000b },
+       { 0x000800,   6, 0x01, 0x00000001 },
+       { 0x000632,   1, 0x01, 0x00000001 },
+       { 0x000633,   1, 0x01, 0x00000002 },
+       { 0x000634,   1, 0x01, 0x00000003 },
+       { 0x000635,   1, 0x01, 0x00000004 },
+       { 0x000654,   1, 0x01, 0x3f800000 },
+       { 0x000657,   1, 0x01, 0x3f800000 },
+       { 0x000655,   2, 0x01, 0x3f800000 },
+       { 0x0006cd,   1, 0x01, 0x3f800000 },
+       { 0x0007f5,   1, 0x01, 0x3f800000 },
+       { 0x0007dc,   1, 0x01, 0x39291909 },
+       { 0x0007dd,   1, 0x01, 0x79695949 },
+       { 0x0007de,   1, 0x01, 0xb9a99989 },
+       { 0x0007df,   1, 0x01, 0xf9e9d9c9 },
+       { 0x0007e8,   1, 0x01, 0x00003210 },
+       { 0x0007e9,   1, 0x01, 0x00007654 },
+       { 0x0007ea,   1, 0x01, 0x00000098 },
+       { 0x0007ec,   1, 0x01, 0x39291909 },
+       { 0x0007ed,   1, 0x01, 0x79695949 },
+       { 0x0007ee,   1, 0x01, 0xb9a99989 },
+       { 0x0007ef,   1, 0x01, 0xf9e9d9c9 },
+       { 0x0007f0,   1, 0x01, 0x00003210 },
+       { 0x0007f1,   1, 0x01, 0x00007654 },
+       { 0x0007f2,   1, 0x01, 0x00000098 },
+       { 0x0005a5,   1, 0x01, 0x00000001 },
+       { 0x000980, 128, 0x01, 0x00000000 },
+       { 0x000468,   1, 0x01, 0x00000004 },
+       { 0x00046c,   1, 0x01, 0x00000001 },
+       { 0x000470,  96, 0x01, 0x00000000 },
+       { 0x000510,  16, 0x01, 0x3f800000 },
+       { 0x000520,   1, 0x01, 0x000002b6 },
+       { 0x000529,   1, 0x01, 0x00000001 },
+       { 0x000530,  16, 0x01, 0xffff0000 },
+       { 0x000585,   1, 0x01, 0x0000003f },
+       { 0x000576,   1, 0x01, 0x00000003 },
+       { 0x00057b,   1, 0x01, 0x00000059 },
+       { 0x000586,   1, 0x01, 0x00000040 },
+       { 0x000582,   2, 0x01, 0x00000080 },
+       { 0x0005c2,   1, 0x01, 0x00000001 },
+       { 0x000638,   2, 0x01, 0x00000001 },
+       { 0x00063a,   1, 0x01, 0x00000002 },
+       { 0x00063b,   2, 0x01, 0x00000001 },
+       { 0x00063d,   1, 0x01, 0x00000002 },
+       { 0x00063e,   1, 0x01, 0x00000001 },
+       { 0x0008b8,   8, 0x01, 0x00000001 },
+       { 0x000900,   8, 0x01, 0x00000001 },
+       { 0x000908,   8, 0x01, 0x00000002 },
+       { 0x000910,  16, 0x01, 0x00000001 },
+       { 0x000920,   8, 0x01, 0x00000002 },
+       { 0x000928,   8, 0x01, 0x00000001 },
+       { 0x000648,   9, 0x01, 0x00000001 },
+       { 0x000658,   1, 0x01, 0x0000000f },
+       { 0x0007ff,   1, 0x01, 0x0000000a },
+       { 0x00066a,   1, 0x01, 0x40000000 },
+       { 0x00066b,   1, 0x01, 0x10000000 },
+       { 0x00066c,   2, 0x01, 0xffff0000 },
+       { 0x0007af,   2, 0x01, 0x00000008 },
+       { 0x0007f6,   1, 0x01, 0x00000001 },
+       { 0x0006b2,   1, 0x01, 0x00000055 },
+       { 0x0007ad,   1, 0x01, 0x00000003 },
+       { 0x000937,   1, 0x01, 0x00000001 },
+       { 0x000971,   1, 0x01, 0x00000008 },
+       { 0x000972,   1, 0x01, 0x00000040 },
+       { 0x000973,   1, 0x01, 0x0000012c },
+       { 0x00097c,   1, 0x01, 0x00000040 },
+       { 0x000979,   1, 0x01, 0x00000003 },
+       { 0x000975,   1, 0x01, 0x00000020 },
+       { 0x000976,   1, 0x01, 0x00000001 },
+       { 0x000977,   1, 0x01, 0x00000020 },
+       { 0x000978,   1, 0x01, 0x00000001 },
+       { 0x000957,   1, 0x01, 0x00000003 },
+       { 0x00095e,   1, 0x01, 0x20164010 },
+       { 0x00095f,   1, 0x01, 0x00000020 },
+       { 0x000683,   1, 0x01, 0x00000006 },
+       { 0x000685,   1, 0x01, 0x003fffff },
+       { 0x000687,   1, 0x01, 0x00000c48 },
+       { 0x0006a0,   1, 0x01, 0x00000005 },
+       { 0x000840,   1, 0x01, 0x00300008 },
+       { 0x000841,   1, 0x01, 0x04000080 },
+       { 0x000842,   1, 0x01, 0x00300008 },
+       { 0x000843,   1, 0x01, 0x04000080 },
+       { 0x000818,   8, 0x01, 0x00000000 },
+       { 0x000848,  16, 0x01, 0x00000000 },
+       { 0x000738,   1, 0x01, 0x00000000 },
+       { 0x0006aa,   1, 0x01, 0x00000001 },
+       { 0x0006ab,   1, 0x01, 0x00000002 },
+       { 0x0006ac,   1, 0x01, 0x00000080 },
+       { 0x0006ad,   2, 0x01, 0x00000100 },
+       { 0x0006b1,   1, 0x01, 0x00000011 },
+       { 0x0006bb,   1, 0x01, 0x000000cf },
+       { 0x0006ce,   1, 0x01, 0x2a712488 },
+       { 0x000739,   1, 0x01, 0x4085c000 },
+       { 0x00073a,   1, 0x01, 0x00000080 },
+       { 0x000786,   1, 0x01, 0x80000100 },
+       { 0x00073c,   1, 0x01, 0x00010100 },
+       { 0x00073d,   1, 0x01, 0x02800000 },
+       { 0x000787,   1, 0x01, 0x000000cf },
+       { 0x00078c,   1, 0x01, 0x00000008 },
+       { 0x000792,   1, 0x01, 0x00000001 },
+       { 0x000794,   3, 0x01, 0x00000001 },
+       { 0x000797,   1, 0x01, 0x000000cf },
+       { 0x000836,   1, 0x01, 0x00000001 },
+       { 0x00079a,   1, 0x01, 0x00000002 },
+       { 0x000833,   1, 0x01, 0x04444480 },
+       { 0x0007a1,   1, 0x01, 0x00000001 },
+       { 0x0007a3,   3, 0x01, 0x00000001 },
+       { 0x000831,   1, 0x01, 0x00000004 },
+       { 0x00080c,   1, 0x01, 0x00000002 },
+       { 0x00080d,   2, 0x01, 0x00000100 },
+       { 0x00080f,   1, 0x01, 0x00000001 },
+       { 0x000823,   1, 0x01, 0x00000002 },
+       { 0x000824,   2, 0x01, 0x00000100 },
+       { 0x000826,   1, 0x01, 0x00000001 },
+       { 0x00095d,   1, 0x01, 0x00000001 },
+       { 0x00082b,   1, 0x01, 0x00000004 },
+       { 0x000942,   1, 0x01, 0x00010001 },
+       { 0x000943,   1, 0x01, 0x00000001 },
+       { 0x000944,   1, 0x01, 0x00000022 },
+       { 0x0007c5,   1, 0x01, 0x00010001 },
+       { 0x000834,   1, 0x01, 0x00000001 },
+       { 0x0007c7,   1, 0x01, 0x00000001 },
+       { 0x00c1b0,   8, 0x01, 0x0000000f },
+       { 0x00c1b8,   1, 0x01, 0x0fac6881 },
+       { 0x00c1b9,   1, 0x01, 0x00fac688 },
+       { 0x01e100,   1, 0x01, 0x00000001 },
+       { 0x001000,   1, 0x01, 0x00000002 },
+       { 0x0006aa,   1, 0x01, 0x00000001 },
+       { 0x0006ad,   2, 0x01, 0x00000100 },
+       { 0x0006b1,   1, 0x01, 0x00000011 },
+       { 0x00078c,   1, 0x01, 0x00000008 },
+       { 0x000792,   1, 0x01, 0x00000001 },
+       { 0x000794,   3, 0x01, 0x00000001 },
+       { 0x000797,   1, 0x01, 0x000000cf },
+       { 0x00079a,   1, 0x01, 0x00000002 },
+       { 0x000833,   1, 0x01, 0x04444480 },
+       { 0x0007a1,   1, 0x01, 0x00000001 },
+       { 0x0007a3,   3, 0x01, 0x00000001 },
+       { 0x000831,   1, 0x01, 0x00000004 },
+       { 0x01e100,   1, 0x01, 0x00000001 },
+       { 0x001000,   1, 0x01, 0x00000014 },
+       { 0x000351,   1, 0x01, 0x00000100 },
+       { 0x000957,   1, 0x01, 0x00000003 },
+       { 0x00095d,   1, 0x01, 0x00000001 },
+       { 0x00082b,   1, 0x01, 0x00000004 },
+       { 0x000942,   1, 0x01, 0x00010001 },
+       { 0x000943,   1, 0x01, 0x00000001 },
+       { 0x0007c5,   1, 0x01, 0x00010001 },
+       { 0x000834,   1, 0x01, 0x00000001 },
+       { 0x0007c7,   1, 0x01, 0x00000001 },
+       { 0x01e100,   1, 0x01, 0x00000001 },
+       { 0x001000,   1, 0x01, 0x00000001 },
+       { 0x00080c,   1, 0x01, 0x00000002 },
+       { 0x00080d,   2, 0x01, 0x00000100 },
+       { 0x00080f,   1, 0x01, 0x00000001 },
+       { 0x000823,   1, 0x01, 0x00000002 },
+       { 0x000824,   2, 0x01, 0x00000100 },
+       { 0x000826,   1, 0x01, 0x00000001 },
+       { 0x01e100,   1, 0x01, 0x00000001 },
+       {}
+};
+
+static const struct gf100_gr_pack
+gf108_grctx_pack_icmd[] = {
+       { gf108_grctx_init_icmd_0 },
+       {}
+};
+
+const struct gf100_gr_init
+gf108_grctx_init_9097_0[] = {
+       { 0x000800,   8, 0x40, 0x00000000 },
+       { 0x000804,   8, 0x40, 0x00000000 },
+       { 0x000808,   8, 0x40, 0x00000400 },
+       { 0x00080c,   8, 0x40, 0x00000300 },
+       { 0x000810,   1, 0x04, 0x000000cf },
+       { 0x000850,   7, 0x40, 0x00000000 },
+       { 0x000814,   8, 0x40, 0x00000040 },
+       { 0x000818,   8, 0x40, 0x00000001 },
+       { 0x00081c,   8, 0x40, 0x00000000 },
+       { 0x000820,   8, 0x40, 0x00000000 },
+       { 0x002700,   8, 0x20, 0x00000000 },
+       { 0x002704,   8, 0x20, 0x00000000 },
+       { 0x002708,   8, 0x20, 0x00000000 },
+       { 0x00270c,   8, 0x20, 0x00000000 },
+       { 0x002710,   8, 0x20, 0x00014000 },
+       { 0x002714,   8, 0x20, 0x00000040 },
+       { 0x001c00,  16, 0x10, 0x00000000 },
+       { 0x001c04,  16, 0x10, 0x00000000 },
+       { 0x001c08,  16, 0x10, 0x00000000 },
+       { 0x001c0c,  16, 0x10, 0x00000000 },
+       { 0x001d00,  16, 0x10, 0x00000000 },
+       { 0x001d04,  16, 0x10, 0x00000000 },
+       { 0x001d08,  16, 0x10, 0x00000000 },
+       { 0x001d0c,  16, 0x10, 0x00000000 },
+       { 0x001f00,  16, 0x08, 0x00000000 },
+       { 0x001f04,  16, 0x08, 0x00000000 },
+       { 0x001f80,  16, 0x08, 0x00000000 },
+       { 0x001f84,  16, 0x08, 0x00000000 },
+       { 0x002200,   5, 0x10, 0x00000022 },
+       { 0x002000,   1, 0x04, 0x00000000 },
+       { 0x002040,   1, 0x04, 0x00000011 },
+       { 0x002080,   1, 0x04, 0x00000020 },
+       { 0x0020c0,   1, 0x04, 0x00000030 },
+       { 0x002100,   1, 0x04, 0x00000040 },
+       { 0x002140,   1, 0x04, 0x00000051 },
+       { 0x00200c,   6, 0x40, 0x00000001 },
+       { 0x002010,   1, 0x04, 0x00000000 },
+       { 0x002050,   1, 0x04, 0x00000000 },
+       { 0x002090,   1, 0x04, 0x00000001 },
+       { 0x0020d0,   1, 0x04, 0x00000002 },
+       { 0x002110,   1, 0x04, 0x00000003 },
+       { 0x002150,   1, 0x04, 0x00000004 },
+       { 0x000380,   4, 0x20, 0x00000000 },
+       { 0x000384,   4, 0x20, 0x00000000 },
+       { 0x000388,   4, 0x20, 0x00000000 },
+       { 0x00038c,   4, 0x20, 0x00000000 },
+       { 0x000700,   4, 0x10, 0x00000000 },
+       { 0x000704,   4, 0x10, 0x00000000 },
+       { 0x000708,   4, 0x10, 0x00000000 },
+       { 0x002800, 128, 0x04, 0x00000000 },
+       { 0x000a00,  16, 0x20, 0x00000000 },
+       { 0x000a04,  16, 0x20, 0x00000000 },
+       { 0x000a08,  16, 0x20, 0x00000000 },
+       { 0x000a0c,  16, 0x20, 0x00000000 },
+       { 0x000a10,  16, 0x20, 0x00000000 },
+       { 0x000a14,  16, 0x20, 0x00000000 },
+       { 0x000c00,  16, 0x10, 0x00000000 },
+       { 0x000c04,  16, 0x10, 0x00000000 },
+       { 0x000c08,  16, 0x10, 0x00000000 },
+       { 0x000c0c,  16, 0x10, 0x3f800000 },
+       { 0x000d00,   8, 0x08, 0xffff0000 },
+       { 0x000d04,   8, 0x08, 0xffff0000 },
+       { 0x000e00,  16, 0x10, 0x00000000 },
+       { 0x000e04,  16, 0x10, 0xffff0000 },
+       { 0x000e08,  16, 0x10, 0xffff0000 },
+       { 0x000d40,   4, 0x08, 0x00000000 },
+       { 0x000d44,   4, 0x08, 0x00000000 },
+       { 0x001e00,   8, 0x20, 0x00000001 },
+       { 0x001e04,   8, 0x20, 0x00000001 },
+       { 0x001e08,   8, 0x20, 0x00000002 },
+       { 0x001e0c,   8, 0x20, 0x00000001 },
+       { 0x001e10,   8, 0x20, 0x00000001 },
+       { 0x001e14,   8, 0x20, 0x00000002 },
+       { 0x001e18,   8, 0x20, 0x00000001 },
+       { 0x00030c,   1, 0x04, 0x00000001 },
+       { 0x001944,   1, 0x04, 0x00000000 },
+       { 0x001514,   1, 0x04, 0x00000000 },
+       { 0x000d68,   1, 0x04, 0x0000ffff },
+       { 0x00121c,   1, 0x04, 0x0fac6881 },
+       { 0x000fac,   1, 0x04, 0x00000001 },
+       { 0x001538,   1, 0x04, 0x00000001 },
+       { 0x000fe0,   2, 0x04, 0x00000000 },
+       { 0x000fe8,   1, 0x04, 0x00000014 },
+       { 0x000fec,   1, 0x04, 0x00000040 },
+       { 0x000ff0,   1, 0x04, 0x00000000 },
+       { 0x00179c,   1, 0x04, 0x00000000 },
+       { 0x001228,   1, 0x04, 0x00000400 },
+       { 0x00122c,   1, 0x04, 0x00000300 },
+       { 0x001230,   1, 0x04, 0x00010001 },
+       { 0x0007f8,   1, 0x04, 0x00000000 },
+       { 0x0015b4,   1, 0x04, 0x00000001 },
+       { 0x0015cc,   1, 0x04, 0x00000000 },
+       { 0x001534,   1, 0x04, 0x00000000 },
+       { 0x000fb0,   1, 0x04, 0x00000000 },
+       { 0x0015d0,   1, 0x04, 0x00000000 },
+       { 0x00153c,   1, 0x04, 0x00000000 },
+       { 0x0016b4,   1, 0x04, 0x00000003 },
+       { 0x000fbc,   4, 0x04, 0x0000ffff },
+       { 0x000df8,   2, 0x04, 0x00000000 },
+       { 0x001948,   1, 0x04, 0x00000000 },
+       { 0x001970,   1, 0x04, 0x00000001 },
+       { 0x00161c,   1, 0x04, 0x000009f0 },
+       { 0x000dcc,   1, 0x04, 0x00000010 },
+       { 0x00163c,   1, 0x04, 0x00000000 },
+       { 0x0015e4,   1, 0x04, 0x00000000 },
+       { 0x001160,  32, 0x04, 0x25e00040 },
+       { 0x001880,  32, 0x04, 0x00000000 },
+       { 0x000f84,   2, 0x04, 0x00000000 },
+       { 0x0017c8,   2, 0x04, 0x00000000 },
+       { 0x0017d0,   1, 0x04, 0x000000ff },
+       { 0x0017d4,   1, 0x04, 0xffffffff },
+       { 0x0017d8,   1, 0x04, 0x00000002 },
+       { 0x0017dc,   1, 0x04, 0x00000000 },
+       { 0x0015f4,   2, 0x04, 0x00000000 },
+       { 0x001434,   2, 0x04, 0x00000000 },
+       { 0x000d74,   1, 0x04, 0x00000000 },
+       { 0x000dec,   1, 0x04, 0x00000001 },
+       { 0x0013a4,   1, 0x04, 0x00000000 },
+       { 0x001318,   1, 0x04, 0x00000001 },
+       { 0x001644,   1, 0x04, 0x00000000 },
+       { 0x000748,   1, 0x04, 0x00000000 },
+       { 0x000de8,   1, 0x04, 0x00000000 },
+       { 0x001648,   1, 0x04, 0x00000000 },
+       { 0x0012a4,   1, 0x04, 0x00000000 },
+       { 0x001120,   4, 0x04, 0x00000000 },
+       { 0x001118,   1, 0x04, 0x00000000 },
+       { 0x00164c,   1, 0x04, 0x00000000 },
+       { 0x001658,   1, 0x04, 0x00000000 },
+       { 0x001910,   1, 0x04, 0x00000290 },
+       { 0x001518,   1, 0x04, 0x00000000 },
+       { 0x00165c,   1, 0x04, 0x00000001 },
+       { 0x001520,   1, 0x04, 0x00000000 },
+       { 0x001604,   1, 0x04, 0x00000000 },
+       { 0x001570,   1, 0x04, 0x00000000 },
+       { 0x0013b0,   2, 0x04, 0x3f800000 },
+       { 0x00020c,   1, 0x04, 0x00000000 },
+       { 0x001670,   1, 0x04, 0x30201000 },
+       { 0x001674,   1, 0x04, 0x70605040 },
+       { 0x001678,   1, 0x04, 0xb8a89888 },
+       { 0x00167c,   1, 0x04, 0xf8e8d8c8 },
+       { 0x00166c,   1, 0x04, 0x00000000 },
+       { 0x001680,   1, 0x04, 0x00ffff00 },
+       { 0x0012d0,   1, 0x04, 0x00000003 },
+       { 0x0012d4,   1, 0x04, 0x00000002 },
+       { 0x001684,   2, 0x04, 0x00000000 },
+       { 0x000dac,   2, 0x04, 0x00001b02 },
+       { 0x000db4,   1, 0x04, 0x00000000 },
+       { 0x00168c,   1, 0x04, 0x00000000 },
+       { 0x0015bc,   1, 0x04, 0x00000000 },
+       { 0x00156c,   1, 0x04, 0x00000000 },
+       { 0x00187c,   1, 0x04, 0x00000000 },
+       { 0x001110,   1, 0x04, 0x00000001 },
+       { 0x000dc0,   3, 0x04, 0x00000000 },
+       { 0x001234,   1, 0x04, 0x00000000 },
+       { 0x001690,   1, 0x04, 0x00000000 },
+       { 0x0012ac,   1, 0x04, 0x00000001 },
+       { 0x0002c4,   1, 0x04, 0x00000000 },
+       { 0x000790,   5, 0x04, 0x00000000 },
+       { 0x00077c,   1, 0x04, 0x00000000 },
+       { 0x001000,   1, 0x04, 0x00000010 },
+       { 0x0010fc,   1, 0x04, 0x00000000 },
+       { 0x001290,   1, 0x04, 0x00000000 },
+       { 0x000218,   1, 0x04, 0x00000010 },
+       { 0x0012d8,   1, 0x04, 0x00000000 },
+       { 0x0012dc,   1, 0x04, 0x00000010 },
+       { 0x000d94,   1, 0x04, 0x00000001 },
+       { 0x00155c,   2, 0x04, 0x00000000 },
+       { 0x001564,   1, 0x04, 0x00001fff },
+       { 0x001574,   2, 0x04, 0x00000000 },
+       { 0x00157c,   1, 0x04, 0x003fffff },
+       { 0x001354,   1, 0x04, 0x00000000 },
+       { 0x001664,   1, 0x04, 0x00000000 },
+       { 0x001610,   1, 0x04, 0x00000012 },
+       { 0x001608,   2, 0x04, 0x00000000 },
+       { 0x00162c,   1, 0x04, 0x00000003 },
+       { 0x000210,   1, 0x04, 0x00000000 },
+       { 0x000320,   1, 0x04, 0x00000000 },
+       { 0x000324,   6, 0x04, 0x3f800000 },
+       { 0x000750,   1, 0x04, 0x00000000 },
+       { 0x000760,   1, 0x04, 0x39291909 },
+       { 0x000764,   1, 0x04, 0x79695949 },
+       { 0x000768,   1, 0x04, 0xb9a99989 },
+       { 0x00076c,   1, 0x04, 0xf9e9d9c9 },
+       { 0x000770,   1, 0x04, 0x30201000 },
+       { 0x000774,   1, 0x04, 0x70605040 },
+       { 0x000778,   1, 0x04, 0x00009080 },
+       { 0x000780,   1, 0x04, 0x39291909 },
+       { 0x000784,   1, 0x04, 0x79695949 },
+       { 0x000788,   1, 0x04, 0xb9a99989 },
+       { 0x00078c,   1, 0x04, 0xf9e9d9c9 },
+       { 0x0007d0,   1, 0x04, 0x30201000 },
+       { 0x0007d4,   1, 0x04, 0x70605040 },
+       { 0x0007d8,   1, 0x04, 0x00009080 },
+       { 0x00037c,   1, 0x04, 0x00000001 },
+       { 0x000740,   2, 0x04, 0x00000000 },
+       { 0x002600,   1, 0x04, 0x00000000 },
+       { 0x001918,   1, 0x04, 0x00000000 },
+       { 0x00191c,   1, 0x04, 0x00000900 },
+       { 0x001920,   1, 0x04, 0x00000405 },
+       { 0x001308,   1, 0x04, 0x00000001 },
+       { 0x001924,   1, 0x04, 0x00000000 },
+       { 0x0013ac,   1, 0x04, 0x00000000 },
+       { 0x00192c,   1, 0x04, 0x00000001 },
+       { 0x00193c,   1, 0x04, 0x00002c1c },
+       { 0x000d7c,   1, 0x04, 0x00000000 },
+       { 0x000f8c,   1, 0x04, 0x00000000 },
+       { 0x0002c0,   1, 0x04, 0x00000001 },
+       { 0x001510,   1, 0x04, 0x00000000 },
+       { 0x001940,   1, 0x04, 0x00000000 },
+       { 0x000ff4,   2, 0x04, 0x00000000 },
+       { 0x00194c,   2, 0x04, 0x00000000 },
+       { 0x001968,   1, 0x04, 0x00000000 },
+       { 0x001590,   1, 0x04, 0x0000003f },
+       { 0x0007e8,   4, 0x04, 0x00000000 },
+       { 0x00196c,   1, 0x04, 0x00000011 },
+       { 0x00197c,   1, 0x04, 0x00000000 },
+       { 0x000fcc,   2, 0x04, 0x00000000 },
+       { 0x0002d8,   1, 0x04, 0x00000040 },
+       { 0x001980,   1, 0x04, 0x00000080 },
+       { 0x001504,   1, 0x04, 0x00000080 },
+       { 0x001984,   1, 0x04, 0x00000000 },
+       { 0x000300,   1, 0x04, 0x00000001 },
+       { 0x0013a8,   1, 0x04, 0x00000000 },
+       { 0x0012ec,   1, 0x04, 0x00000000 },
+       { 0x001310,   1, 0x04, 0x00000000 },
+       { 0x001314,   1, 0x04, 0x00000001 },
+       { 0x001380,   1, 0x04, 0x00000000 },
+       { 0x001384,   4, 0x04, 0x00000001 },
+       { 0x001394,   1, 0x04, 0x00000000 },
+       { 0x00139c,   1, 0x04, 0x00000000 },
+       { 0x001398,   1, 0x04, 0x00000000 },
+       { 0x001594,   1, 0x04, 0x00000000 },
+       { 0x001598,   4, 0x04, 0x00000001 },
+       { 0x000f54,   3, 0x04, 0x00000000 },
+       { 0x0019bc,   1, 0x04, 0x00000000 },
+       { 0x000f9c,   2, 0x04, 0x00000000 },
+       { 0x0012cc,   1, 0x04, 0x00000000 },
+       { 0x0012e8,   1, 0x04, 0x00000000 },
+       { 0x00130c,   1, 0x04, 0x00000001 },
+       { 0x001360,   8, 0x04, 0x00000000 },
+       { 0x00133c,   2, 0x04, 0x00000001 },
+       { 0x001344,   1, 0x04, 0x00000002 },
+       { 0x001348,   2, 0x04, 0x00000001 },
+       { 0x001350,   1, 0x04, 0x00000002 },
+       { 0x001358,   1, 0x04, 0x00000001 },
+       { 0x0012e4,   1, 0x04, 0x00000000 },
+       { 0x00131c,   4, 0x04, 0x00000000 },
+       { 0x0019c0,   1, 0x04, 0x00000000 },
+       { 0x001140,   1, 0x04, 0x00000000 },
+       { 0x0019c4,   1, 0x04, 0x00000000 },
+       { 0x0019c8,   1, 0x04, 0x00001500 },
+       { 0x00135c,   1, 0x04, 0x00000000 },
+       { 0x000f90,   1, 0x04, 0x00000000 },
+       { 0x0019e0,   8, 0x04, 0x00000001 },
+       { 0x0019cc,   1, 0x04, 0x00000001 },
+       { 0x0015b8,   1, 0x04, 0x00000000 },
+       { 0x001a00,   1, 0x04, 0x00001111 },
+       { 0x001a04,   7, 0x04, 0x00000000 },
+       { 0x000d6c,   2, 0x04, 0xffff0000 },
+       { 0x0010f8,   1, 0x04, 0x00001010 },
+       { 0x000d80,   5, 0x04, 0x00000000 },
+       { 0x000da0,   1, 0x04, 0x00000000 },
+       { 0x001508,   1, 0x04, 0x80000000 },
+       { 0x00150c,   1, 0x04, 0x40000000 },
+       { 0x001668,   1, 0x04, 0x00000000 },
+       { 0x000318,   2, 0x04, 0x00000008 },
+       { 0x000d9c,   1, 0x04, 0x00000001 },
+       { 0x0007dc,   1, 0x04, 0x00000000 },
+       { 0x00074c,   1, 0x04, 0x00000055 },
+       { 0x001420,   1, 0x04, 0x00000003 },
+       { 0x0017bc,   2, 0x04, 0x00000000 },
+       { 0x0017c4,   1, 0x04, 0x00000001 },
+       { 0x001008,   1, 0x04, 0x00000008 },
+       { 0x00100c,   1, 0x04, 0x00000040 },
+       { 0x001010,   1, 0x04, 0x0000012c },
+       { 0x000d60,   1, 0x04, 0x00000040 },
+       { 0x00075c,   1, 0x04, 0x00000003 },
+       { 0x001018,   1, 0x04, 0x00000020 },
+       { 0x00101c,   1, 0x04, 0x00000001 },
+       { 0x001020,   1, 0x04, 0x00000020 },
+       { 0x001024,   1, 0x04, 0x00000001 },
+       { 0x001444,   3, 0x04, 0x00000000 },
+       { 0x000360,   1, 0x04, 0x20164010 },
+       { 0x000364,   1, 0x04, 0x00000020 },
+       { 0x000368,   1, 0x04, 0x00000000 },
+       { 0x000de4,   1, 0x04, 0x00000000 },
+       { 0x000204,   1, 0x04, 0x00000006 },
+       { 0x000208,   1, 0x04, 0x00000000 },
+       { 0x0002cc,   1, 0x04, 0x003fffff },
+       { 0x0002d0,   1, 0x04, 0x00000c48 },
+       { 0x001220,   1, 0x04, 0x00000005 },
+       { 0x000fdc,   1, 0x04, 0x00000000 },
+       { 0x000f98,   1, 0x04, 0x00300008 },
+       { 0x001284,   1, 0x04, 0x04000080 },
+       { 0x001450,   1, 0x04, 0x00300008 },
+       { 0x001454,   1, 0x04, 0x04000080 },
+       { 0x000214,   1, 0x04, 0x00000000 },
+       {}
+};
+
+static const struct gf100_gr_init
+gf108_grctx_init_9197_0[] = {
+       { 0x003400, 128, 0x04, 0x00000000 },
+       { 0x0002e4,   1, 0x04, 0x0000b001 },
+       {}
+};
+
+static const struct gf100_gr_pack
+gf108_grctx_pack_mthd[] = {
+       { gf108_grctx_init_9097_0, 0x9097 },
+       { gf108_grctx_init_9197_0, 0x9197 },
+       { gf100_grctx_init_902d_0, 0x902d },
+       { gf100_grctx_init_9039_0, 0x9039 },
+       { gf100_grctx_init_90c0_0, 0x90c0 },
+       {}
+};
+
+static const struct gf100_gr_init
+gf108_grctx_init_ds_0[] = {
+       { 0x405800,   1, 0x04, 0x0f8000bf },
+       { 0x405830,   1, 0x04, 0x02180218 },
+       { 0x405834,   2, 0x04, 0x00000000 },
+       { 0x405854,   1, 0x04, 0x00000000 },
+       { 0x405870,   4, 0x04, 0x00000001 },
+       { 0x405a00,   2, 0x04, 0x00000000 },
+       { 0x405a18,   1, 0x04, 0x00000000 },
+       {}
+};
+
+static const struct gf100_gr_init
+gf108_grctx_init_pd_0[] = {
+       { 0x406020,   1, 0x04, 0x000103c1 },
+       { 0x406028,   4, 0x04, 0x00000001 },
+       { 0x4064a8,   1, 0x04, 0x00000000 },
+       { 0x4064ac,   1, 0x04, 0x00003fff },
+       { 0x4064b4,   2, 0x04, 0x00000000 },
+       { 0x4064c0,   1, 0x04, 0x80140078 },
+       { 0x4064c4,   1, 0x04, 0x0086ffff },
+       {}
+};
+
+static const struct gf100_gr_init
+gf108_grctx_init_be_0[] = {
+       { 0x408800,   1, 0x04, 0x02802a3c },
+       { 0x408804,   1, 0x04, 0x00000040 },
+       { 0x408808,   1, 0x04, 0x1003e005 },
+       { 0x408900,   1, 0x04, 0x3080b801 },
+       { 0x408904,   1, 0x04, 0x62000001 },
+       { 0x408908,   1, 0x04, 0x00c80929 },
+       { 0x408980,   1, 0x04, 0x0000011d },
+       {}
+};
+
+static const struct gf100_gr_pack
+gf108_grctx_pack_hub[] = {
+       { gf100_grctx_init_main_0 },
+       { gf100_grctx_init_fe_0 },
+       { gf100_grctx_init_pri_0 },
+       { gf100_grctx_init_memfmt_0 },
+       { gf108_grctx_init_ds_0 },
+       { gf108_grctx_init_pd_0 },
+       { gf100_grctx_init_rstr2d_0 },
+       { gf100_grctx_init_scc_0 },
+       { gf108_grctx_init_be_0 },
+       {}
+};
+
+static const struct gf100_gr_init
+gf108_grctx_init_setup_0[] = {
+       { 0x418800,   1, 0x04, 0x0006860a },
+       { 0x418808,   3, 0x04, 0x00000000 },
+       { 0x418828,   1, 0x04, 0x00008442 },
+       { 0x418830,   1, 0x04, 0x10000001 },
+       { 0x4188d8,   1, 0x04, 0x00000008 },
+       { 0x4188e0,   1, 0x04, 0x01000000 },
+       { 0x4188e8,   5, 0x04, 0x00000000 },
+       { 0x4188fc,   1, 0x04, 0x00100018 },
+       {}
+};
+
+const struct gf100_gr_init
+gf108_grctx_init_gpm_0[] = {
+       { 0x418c08,   1, 0x04, 0x00000001 },
+       { 0x418c10,   8, 0x04, 0x00000000 },
+       { 0x418c6c,   1, 0x04, 0x00000001 },
+       { 0x418c80,   1, 0x04, 0x20200004 },
+       { 0x418c8c,   1, 0x04, 0x00000001 },
+       {}
+};
+
+static const struct gf100_gr_pack
+gf108_grctx_pack_gpc[] = {
+       { gf100_grctx_init_gpc_unk_0 },
+       { gf100_grctx_init_prop_0 },
+       { gf100_grctx_init_gpc_unk_1 },
+       { gf108_grctx_init_setup_0 },
+       { gf100_grctx_init_zcull_0 },
+       { gf100_grctx_init_crstr_0 },
+       { gf108_grctx_init_gpm_0 },
+       { gf100_grctx_init_gcc_0 },
+       {}
+};
+
+const struct gf100_gr_init
+gf108_grctx_init_pe_0[] = {
+       { 0x419818,   1, 0x04, 0x00000000 },
+       { 0x41983c,   1, 0x04, 0x00038bc7 },
+       { 0x419848,   1, 0x04, 0x00000000 },
+       { 0x419864,   1, 0x04, 0x00000129 },
+       { 0x419888,   1, 0x04, 0x00000000 },
+       {}
+};
+
+const struct gf100_gr_init
+gf108_grctx_init_wwdx_0[] = {
+       { 0x419b00,   1, 0x04, 0x0a418820 },
+       { 0x419b04,   1, 0x04, 0x062080e6 },
+       { 0x419b08,   1, 0x04, 0x020398a4 },
+       { 0x419b0c,   1, 0x04, 0x0e629062 },
+       { 0x419b10,   1, 0x04, 0x0a418820 },
+       { 0x419b14,   1, 0x04, 0x000000e6 },
+       { 0x419bd0,   1, 0x04, 0x00900103 },
+       { 0x419be0,   1, 0x04, 0x00400001 },
+       { 0x419be4,   1, 0x04, 0x00000000 },
+       {}
+};
+
+const struct gf100_gr_init
+gf108_grctx_init_tpccs_0[] = {
+       { 0x419d20,   1, 0x04, 0x12180000 },
+       { 0x419d24,   1, 0x04, 0x00001fff },
+       { 0x419d44,   1, 0x04, 0x02180218 },
+       {}
+};
+
+static const struct gf100_gr_pack
+gf108_grctx_pack_tpc[] = {
+       { gf108_grctx_init_pe_0 },
+       { gf104_grctx_init_tex_0 },
+       { gf108_grctx_init_wwdx_0 },
+       { gf100_grctx_init_mpc_0 },
+       { gf104_grctx_init_l1c_0 },
+       { gf108_grctx_init_tpccs_0 },
+       { gf104_grctx_init_sm_0 },
+       {}
+};
+
+/*******************************************************************************
+ * PGRAPH context implementation
+ ******************************************************************************/
+
+void
+gf108_grctx_generate_attrib(struct gf100_grctx *info)
+{
+       struct gf100_gr_priv *priv = info->priv;
+       const struct gf100_grctx_oclass *impl = gf100_grctx_impl(priv);
+       const u32  alpha = impl->alpha_nr;
+       const u32   beta = impl->attrib_nr;
+       const u32   size = 0x20 * (impl->attrib_nr_max + impl->alpha_nr_max);
+       const u32 access = NV_MEM_ACCESS_RW;
+       const int s = 12;
+       const int b = mmio_vram(info, size * priv->tpc_total, (1 << s), access);
+       const int timeslice_mode = 1;
+       const int max_batches = 0xffff;
+       u32 bo = 0;
+       u32 ao = bo + impl->attrib_nr_max * priv->tpc_total;
+       int gpc, tpc;
+
+       mmio_refn(info, 0x418810, 0x80000000, s, b);
+       mmio_refn(info, 0x419848, 0x10000000, s, b);
+       mmio_wr32(info, 0x405830, (beta << 16) | alpha);
+       mmio_wr32(info, 0x4064c4, ((alpha / 4) << 16) | max_batches);
+
+       for (gpc = 0; gpc < priv->gpc_nr; gpc++) {
+               for (tpc = 0; tpc < priv->tpc_nr[gpc]; tpc++) {
+                       const u32 a = alpha;
+                       const u32 b =  beta;
+                       const u32 t = timeslice_mode;
+                       const u32 o = TPC_UNIT(gpc, tpc, 0x500);
+                       mmio_skip(info, o + 0x20, (t << 28) | (b << 16) | ++bo);
+                       mmio_wr32(info, o + 0x20, (t << 28) | (b << 16) | --bo);
+                       bo += impl->attrib_nr_max;
+                       mmio_wr32(info, o + 0x44, (a << 16) | ao);
+                       ao += impl->alpha_nr_max;
+               }
+       }
+}
+
+void
+gf108_grctx_generate_unkn(struct gf100_gr_priv *priv)
+{
+       nv_mask(priv, 0x418c6c, 0x00000001, 0x00000001);
+       nv_mask(priv, 0x41980c, 0x00000010, 0x00000010);
+       nv_mask(priv, 0x419814, 0x00000004, 0x00000004);
+       nv_mask(priv, 0x4064c0, 0x80000000, 0x80000000);
+       nv_mask(priv, 0x405800, 0x08000000, 0x08000000);
+       nv_mask(priv, 0x419c00, 0x00000008, 0x00000008);
+}
+
+struct nvkm_oclass *
+gf108_grctx_oclass = &(struct gf100_grctx_oclass) {
+       .base.handle = NV_ENGCTX(GR, 0xc1),
+       .base.ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = gf100_gr_context_ctor,
+               .dtor = gf100_gr_context_dtor,
+               .init = _nvkm_gr_context_init,
+               .fini = _nvkm_gr_context_fini,
+               .rd32 = _nvkm_gr_context_rd32,
+               .wr32 = _nvkm_gr_context_wr32,
+       },
+       .main  = gf100_grctx_generate_main,
+       .unkn  = gf108_grctx_generate_unkn,
+       .hub   = gf108_grctx_pack_hub,
+       .gpc   = gf108_grctx_pack_gpc,
+       .zcull = gf100_grctx_pack_zcull,
+       .tpc   = gf108_grctx_pack_tpc,
+       .icmd  = gf108_grctx_pack_icmd,
+       .mthd  = gf108_grctx_pack_mthd,
+       .bundle = gf100_grctx_generate_bundle,
+       .bundle_size = 0x1800,
+       .pagepool = gf100_grctx_generate_pagepool,
+       .pagepool_size = 0x8000,
+       .attrib = gf108_grctx_generate_attrib,
+       .attrib_nr_max = 0x324,
+       .attrib_nr = 0x218,
+       .alpha_nr_max = 0x324,
+       .alpha_nr = 0x218,
+}.base;
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/gr/ctxgf110.c b/drivers/gpu/drm/nouveau/nvkm/engine/gr/ctxgf110.c
new file mode 100644 (file)
index 0000000..b3acd93
--- /dev/null
@@ -0,0 +1,359 @@
+/*
+ * Copyright 2013 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 <bskeggs@redhat.com>
+ */
+#include "ctxgf100.h"
+
+/*******************************************************************************
+ * PGRAPH context register lists
+ ******************************************************************************/
+
+static const struct gf100_gr_init
+gf110_grctx_init_icmd_0[] = {
+       { 0x001000,   1, 0x01, 0x00000004 },
+       { 0x0000a9,   1, 0x01, 0x0000ffff },
+       { 0x000038,   1, 0x01, 0x0fac6881 },
+       { 0x00003d,   1, 0x01, 0x00000001 },
+       { 0x0000e8,   8, 0x01, 0x00000400 },
+       { 0x000078,   8, 0x01, 0x00000300 },
+       { 0x000050,   1, 0x01, 0x00000011 },
+       { 0x000058,   8, 0x01, 0x00000008 },
+       { 0x000208,   8, 0x01, 0x00000001 },
+       { 0x000081,   1, 0x01, 0x00000001 },
+       { 0x000085,   1, 0x01, 0x00000004 },
+       { 0x000088,   1, 0x01, 0x00000400 },
+       { 0x000090,   1, 0x01, 0x00000300 },
+       { 0x000098,   1, 0x01, 0x00001001 },
+       { 0x0000e3,   1, 0x01, 0x00000001 },
+       { 0x0000da,   1, 0x01, 0x00000001 },
+       { 0x0000f8,   1, 0x01, 0x00000003 },
+       { 0x0000fa,   1, 0x01, 0x00000001 },
+       { 0x00009f,   4, 0x01, 0x0000ffff },
+       { 0x0000b1,   1, 0x01, 0x00000001 },
+       { 0x0000b2,  40, 0x01, 0x00000000 },
+       { 0x000210,   8, 0x01, 0x00000040 },
+       { 0x000218,   8, 0x01, 0x0000c080 },
+       { 0x0000ad,   1, 0x01, 0x0000013e },
+       { 0x0000e1,   1, 0x01, 0x00000010 },
+       { 0x000290,  16, 0x01, 0x00000000 },
+       { 0x0003b0,  16, 0x01, 0x00000000 },
+       { 0x0002a0,  16, 0x01, 0x00000000 },
+       { 0x000420,  16, 0x01, 0x00000000 },
+       { 0x0002b0,  16, 0x01, 0x00000000 },
+       { 0x000430,  16, 0x01, 0x00000000 },
+       { 0x0002c0,  16, 0x01, 0x00000000 },
+       { 0x0004d0,  16, 0x01, 0x00000000 },
+       { 0x000720,  16, 0x01, 0x00000000 },
+       { 0x0008c0,  16, 0x01, 0x00000000 },
+       { 0x000890,  16, 0x01, 0x00000000 },
+       { 0x0008e0,  16, 0x01, 0x00000000 },
+       { 0x0008a0,  16, 0x01, 0x00000000 },
+       { 0x0008f0,  16, 0x01, 0x00000000 },
+       { 0x00094c,   1, 0x01, 0x000000ff },
+       { 0x00094d,   1, 0x01, 0xffffffff },
+       { 0x00094e,   1, 0x01, 0x00000002 },
+       { 0x0002ec,   1, 0x01, 0x00000001 },
+       { 0x000303,   1, 0x01, 0x00000001 },
+       { 0x0002e6,   1, 0x01, 0x00000001 },
+       { 0x000466,   1, 0x01, 0x00000052 },
+       { 0x000301,   1, 0x01, 0x3f800000 },
+       { 0x000304,   1, 0x01, 0x30201000 },
+       { 0x000305,   1, 0x01, 0x70605040 },
+       { 0x000306,   1, 0x01, 0xb8a89888 },
+       { 0x000307,   1, 0x01, 0xf8e8d8c8 },
+       { 0x00030a,   1, 0x01, 0x00ffff00 },
+       { 0x00030b,   1, 0x01, 0x0000001a },
+       { 0x00030c,   1, 0x01, 0x00000001 },
+       { 0x000318,   1, 0x01, 0x00000001 },
+       { 0x000340,   1, 0x01, 0x00000000 },
+       { 0x000375,   1, 0x01, 0x00000001 },
+       { 0x000351,   1, 0x01, 0x00000100 },
+       { 0x00037d,   1, 0x01, 0x00000006 },
+       { 0x0003a0,   1, 0x01, 0x00000002 },
+       { 0x0003aa,   1, 0x01, 0x00000001 },
+       { 0x0003a9,   1, 0x01, 0x00000001 },
+       { 0x000380,   1, 0x01, 0x00000001 },
+       { 0x000360,   1, 0x01, 0x00000040 },
+       { 0x000366,   2, 0x01, 0x00000000 },
+       { 0x000368,   1, 0x01, 0x00001fff },
+       { 0x000370,   2, 0x01, 0x00000000 },
+       { 0x000372,   1, 0x01, 0x003fffff },
+       { 0x00037a,   1, 0x01, 0x00000012 },
+       { 0x0005e0,   5, 0x01, 0x00000022 },
+       { 0x000619,   1, 0x01, 0x00000003 },
+       { 0x000811,   1, 0x01, 0x00000003 },
+       { 0x000812,   1, 0x01, 0x00000004 },
+       { 0x000813,   1, 0x01, 0x00000006 },
+       { 0x000814,   1, 0x01, 0x00000008 },
+       { 0x000815,   1, 0x01, 0x0000000b },
+       { 0x000800,   6, 0x01, 0x00000001 },
+       { 0x000632,   1, 0x01, 0x00000001 },
+       { 0x000633,   1, 0x01, 0x00000002 },
+       { 0x000634,   1, 0x01, 0x00000003 },
+       { 0x000635,   1, 0x01, 0x00000004 },
+       { 0x000654,   1, 0x01, 0x3f800000 },
+       { 0x000657,   1, 0x01, 0x3f800000 },
+       { 0x000655,   2, 0x01, 0x3f800000 },
+       { 0x0006cd,   1, 0x01, 0x3f800000 },
+       { 0x0007f5,   1, 0x01, 0x3f800000 },
+       { 0x0007dc,   1, 0x01, 0x39291909 },
+       { 0x0007dd,   1, 0x01, 0x79695949 },
+       { 0x0007de,   1, 0x01, 0xb9a99989 },
+       { 0x0007df,   1, 0x01, 0xf9e9d9c9 },
+       { 0x0007e8,   1, 0x01, 0x00003210 },
+       { 0x0007e9,   1, 0x01, 0x00007654 },
+       { 0x0007ea,   1, 0x01, 0x00000098 },
+       { 0x0007ec,   1, 0x01, 0x39291909 },
+       { 0x0007ed,   1, 0x01, 0x79695949 },
+       { 0x0007ee,   1, 0x01, 0xb9a99989 },
+       { 0x0007ef,   1, 0x01, 0xf9e9d9c9 },
+       { 0x0007f0,   1, 0x01, 0x00003210 },
+       { 0x0007f1,   1, 0x01, 0x00007654 },
+       { 0x0007f2,   1, 0x01, 0x00000098 },
+       { 0x0005a5,   1, 0x01, 0x00000001 },
+       { 0x000980, 128, 0x01, 0x00000000 },
+       { 0x000468,   1, 0x01, 0x00000004 },
+       { 0x00046c,   1, 0x01, 0x00000001 },
+       { 0x000470,  96, 0x01, 0x00000000 },
+       { 0x000510,  16, 0x01, 0x3f800000 },
+       { 0x000520,   1, 0x01, 0x000002b6 },
+       { 0x000529,   1, 0x01, 0x00000001 },
+       { 0x000530,  16, 0x01, 0xffff0000 },
+       { 0x000585,   1, 0x01, 0x0000003f },
+       { 0x000576,   1, 0x01, 0x00000003 },
+       { 0x00057b,   1, 0x01, 0x00000059 },
+       { 0x000586,   1, 0x01, 0x00000040 },
+       { 0x000582,   2, 0x01, 0x00000080 },
+       { 0x0005c2,   1, 0x01, 0x00000001 },
+       { 0x000638,   2, 0x01, 0x00000001 },
+       { 0x00063a,   1, 0x01, 0x00000002 },
+       { 0x00063b,   2, 0x01, 0x00000001 },
+       { 0x00063d,   1, 0x01, 0x00000002 },
+       { 0x00063e,   1, 0x01, 0x00000001 },
+       { 0x0008b8,   8, 0x01, 0x00000001 },
+       { 0x000900,   8, 0x01, 0x00000001 },
+       { 0x000908,   8, 0x01, 0x00000002 },
+       { 0x000910,  16, 0x01, 0x00000001 },
+       { 0x000920,   8, 0x01, 0x00000002 },
+       { 0x000928,   8, 0x01, 0x00000001 },
+       { 0x000648,   9, 0x01, 0x00000001 },
+       { 0x000658,   1, 0x01, 0x0000000f },
+       { 0x0007ff,   1, 0x01, 0x0000000a },
+       { 0x00066a,   1, 0x01, 0x40000000 },
+       { 0x00066b,   1, 0x01, 0x10000000 },
+       { 0x00066c,   2, 0x01, 0xffff0000 },
+       { 0x0007af,   2, 0x01, 0x00000008 },
+       { 0x0007f6,   1, 0x01, 0x00000001 },
+       { 0x0006b2,   1, 0x01, 0x00000055 },
+       { 0x0007ad,   1, 0x01, 0x00000003 },
+       { 0x000937,   1, 0x01, 0x00000001 },
+       { 0x000971,   1, 0x01, 0x00000008 },
+       { 0x000972,   1, 0x01, 0x00000040 },
+       { 0x000973,   1, 0x01, 0x0000012c },
+       { 0x00097c,   1, 0x01, 0x00000040 },
+       { 0x000979,   1, 0x01, 0x00000003 },
+       { 0x000975,   1, 0x01, 0x00000020 },
+       { 0x000976,   1, 0x01, 0x00000001 },
+       { 0x000977,   1, 0x01, 0x00000020 },
+       { 0x000978,   1, 0x01, 0x00000001 },
+       { 0x000957,   1, 0x01, 0x00000003 },
+       { 0x00095e,   1, 0x01, 0x20164010 },
+       { 0x00095f,   1, 0x01, 0x00000020 },
+       { 0x00097d,   1, 0x01, 0x00000020 },
+       { 0x000683,   1, 0x01, 0x00000006 },
+       { 0x000685,   1, 0x01, 0x003fffff },
+       { 0x000687,   1, 0x01, 0x00000c48 },
+       { 0x0006a0,   1, 0x01, 0x00000005 },
+       { 0x000840,   1, 0x01, 0x00300008 },
+       { 0x000841,   1, 0x01, 0x04000080 },
+       { 0x000842,   1, 0x01, 0x00300008 },
+       { 0x000843,   1, 0x01, 0x04000080 },
+       { 0x000818,   8, 0x01, 0x00000000 },
+       { 0x000848,  16, 0x01, 0x00000000 },
+       { 0x000738,   1, 0x01, 0x00000000 },
+       { 0x0006aa,   1, 0x01, 0x00000001 },
+       { 0x0006ab,   1, 0x01, 0x00000002 },
+       { 0x0006ac,   1, 0x01, 0x00000080 },
+       { 0x0006ad,   2, 0x01, 0x00000100 },
+       { 0x0006b1,   1, 0x01, 0x00000011 },
+       { 0x0006bb,   1, 0x01, 0x000000cf },
+       { 0x0006ce,   1, 0x01, 0x2a712488 },
+       { 0x000739,   1, 0x01, 0x4085c000 },
+       { 0x00073a,   1, 0x01, 0x00000080 },
+       { 0x000786,   1, 0x01, 0x80000100 },
+       { 0x00073c,   1, 0x01, 0x00010100 },
+       { 0x00073d,   1, 0x01, 0x02800000 },
+       { 0x000787,   1, 0x01, 0x000000cf },
+       { 0x00078c,   1, 0x01, 0x00000008 },
+       { 0x000792,   1, 0x01, 0x00000001 },
+       { 0x000794,   3, 0x01, 0x00000001 },
+       { 0x000797,   1, 0x01, 0x000000cf },
+       { 0x000836,   1, 0x01, 0x00000001 },
+       { 0x00079a,   1, 0x01, 0x00000002 },
+       { 0x000833,   1, 0x01, 0x04444480 },
+       { 0x0007a1,   1, 0x01, 0x00000001 },
+       { 0x0007a3,   3, 0x01, 0x00000001 },
+       { 0x000831,   1, 0x01, 0x00000004 },
+       { 0x00080c,   1, 0x01, 0x00000002 },
+       { 0x00080d,   2, 0x01, 0x00000100 },
+       { 0x00080f,   1, 0x01, 0x00000001 },
+       { 0x000823,   1, 0x01, 0x00000002 },
+       { 0x000824,   2, 0x01, 0x00000100 },
+       { 0x000826,   1, 0x01, 0x00000001 },
+       { 0x00095d,   1, 0x01, 0x00000001 },
+       { 0x00082b,   1, 0x01, 0x00000004 },
+       { 0x000942,   1, 0x01, 0x00010001 },
+       { 0x000943,   1, 0x01, 0x00000001 },
+       { 0x000944,   1, 0x01, 0x00000022 },
+       { 0x0007c5,   1, 0x01, 0x00010001 },
+       { 0x000834,   1, 0x01, 0x00000001 },
+       { 0x0007c7,   1, 0x01, 0x00000001 },
+       { 0x00c1b0,   8, 0x01, 0x0000000f },
+       { 0x00c1b8,   1, 0x01, 0x0fac6881 },
+       { 0x00c1b9,   1, 0x01, 0x00fac688 },
+       { 0x01e100,   1, 0x01, 0x00000001 },
+       { 0x001000,   1, 0x01, 0x00000002 },
+       { 0x0006aa,   1, 0x01, 0x00000001 },
+       { 0x0006ad,   2, 0x01, 0x00000100 },
+       { 0x0006b1,   1, 0x01, 0x00000011 },
+       { 0x00078c,   1, 0x01, 0x00000008 },
+       { 0x000792,   1, 0x01, 0x00000001 },
+       { 0x000794,   3, 0x01, 0x00000001 },
+       { 0x000797,   1, 0x01, 0x000000cf },
+       { 0x00079a,   1, 0x01, 0x00000002 },
+       { 0x000833,   1, 0x01, 0x04444480 },
+       { 0x0007a1,   1, 0x01, 0x00000001 },
+       { 0x0007a3,   3, 0x01, 0x00000001 },
+       { 0x000831,   1, 0x01, 0x00000004 },
+       { 0x01e100,   1, 0x01, 0x00000001 },
+       { 0x001000,   1, 0x01, 0x00000014 },
+       { 0x000351,   1, 0x01, 0x00000100 },
+       { 0x000957,   1, 0x01, 0x00000003 },
+       { 0x00095d,   1, 0x01, 0x00000001 },
+       { 0x00082b,   1, 0x01, 0x00000004 },
+       { 0x000942,   1, 0x01, 0x00010001 },
+       { 0x000943,   1, 0x01, 0x00000001 },
+       { 0x0007c5,   1, 0x01, 0x00010001 },
+       { 0x000834,   1, 0x01, 0x00000001 },
+       { 0x0007c7,   1, 0x01, 0x00000001 },
+       { 0x01e100,   1, 0x01, 0x00000001 },
+       { 0x001000,   1, 0x01, 0x00000001 },
+       { 0x00080c,   1, 0x01, 0x00000002 },
+       { 0x00080d,   2, 0x01, 0x00000100 },
+       { 0x00080f,   1, 0x01, 0x00000001 },
+       { 0x000823,   1, 0x01, 0x00000002 },
+       { 0x000824,   2, 0x01, 0x00000100 },
+       { 0x000826,   1, 0x01, 0x00000001 },
+       { 0x01e100,   1, 0x01, 0x00000001 },
+       {}
+};
+
+static const struct gf100_gr_pack
+gf110_grctx_pack_icmd[] = {
+       { gf110_grctx_init_icmd_0 },
+       {}
+};
+
+const struct gf100_gr_init
+gf110_grctx_init_9197_0[] = {
+       { 0x0002e4,   1, 0x04, 0x0000b001 },
+       {}
+};
+
+const struct gf100_gr_init
+gf110_grctx_init_9297_0[] = {
+       { 0x003400, 128, 0x04, 0x00000000 },
+       { 0x00036c,   2, 0x04, 0x00000000 },
+       { 0x0007a4,   2, 0x04, 0x00000000 },
+       { 0x000374,   1, 0x04, 0x00000000 },
+       { 0x000378,   1, 0x04, 0x00000020 },
+       {}
+};
+
+static const struct gf100_gr_pack
+gf110_grctx_pack_mthd[] = {
+       { gf108_grctx_init_9097_0, 0x9097 },
+       { gf110_grctx_init_9197_0, 0x9197 },
+       { gf110_grctx_init_9297_0, 0x9297 },
+       { gf100_grctx_init_902d_0, 0x902d },
+       { gf100_grctx_init_9039_0, 0x9039 },
+       { gf100_grctx_init_90c0_0, 0x90c0 },
+       {}
+};
+
+static const struct gf100_gr_init
+gf110_grctx_init_setup_0[] = {
+       { 0x418800,   1, 0x04, 0x0006860a },
+       { 0x418808,   3, 0x04, 0x00000000 },
+       { 0x418828,   1, 0x04, 0x00008442 },
+       { 0x418830,   1, 0x04, 0x00000001 },
+       { 0x4188d8,   1, 0x04, 0x00000008 },
+       { 0x4188e0,   1, 0x04, 0x01000000 },
+       { 0x4188e8,   5, 0x04, 0x00000000 },
+       { 0x4188fc,   1, 0x04, 0x20100000 },
+       {}
+};
+
+static const struct gf100_gr_pack
+gf110_grctx_pack_gpc[] = {
+       { gf100_grctx_init_gpc_unk_0 },
+       { gf100_grctx_init_prop_0 },
+       { gf100_grctx_init_gpc_unk_1 },
+       { gf110_grctx_init_setup_0 },
+       { gf100_grctx_init_zcull_0 },
+       { gf100_grctx_init_crstr_0 },
+       { gf100_grctx_init_gpm_0 },
+       { gf100_grctx_init_gcc_0 },
+       {}
+};
+
+/*******************************************************************************
+ * PGRAPH context implementation
+ ******************************************************************************/
+
+struct nvkm_oclass *
+gf110_grctx_oclass = &(struct gf100_grctx_oclass) {
+       .base.handle = NV_ENGCTX(GR, 0xc8),
+       .base.ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = gf100_gr_context_ctor,
+               .dtor = gf100_gr_context_dtor,
+               .init = _nvkm_gr_context_init,
+               .fini = _nvkm_gr_context_fini,
+               .rd32 = _nvkm_gr_context_rd32,
+               .wr32 = _nvkm_gr_context_wr32,
+       },
+       .main  = gf100_grctx_generate_main,
+       .unkn  = gf100_grctx_generate_unkn,
+       .hub   = gf100_grctx_pack_hub,
+       .gpc   = gf110_grctx_pack_gpc,
+       .zcull = gf100_grctx_pack_zcull,
+       .tpc   = gf100_grctx_pack_tpc,
+       .icmd  = gf110_grctx_pack_icmd,
+       .mthd  = gf110_grctx_pack_mthd,
+       .bundle = gf100_grctx_generate_bundle,
+       .bundle_size = 0x1800,
+       .pagepool = gf100_grctx_generate_pagepool,
+       .pagepool_size = 0x8000,
+       .attrib = gf100_grctx_generate_attrib,
+       .attrib_nr_max = 0x324,
+       .attrib_nr = 0x218,
+}.base;
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/gr/ctxgf117.c b/drivers/gpu/drm/nouveau/nvkm/engine/gr/ctxgf117.c
new file mode 100644 (file)
index 0000000..9bbe2c9
--- /dev/null
@@ -0,0 +1,284 @@
+/*
+ * Copyright 2013 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 <bskeggs@redhat.com>
+ */
+#include "ctxgf100.h"
+
+#include <subdev/fb.h>
+#include <subdev/mc.h>
+
+/*******************************************************************************
+ * PGRAPH context register lists
+ ******************************************************************************/
+
+static const struct gf100_gr_init
+gf117_grctx_init_ds_0[] = {
+       { 0x405800,   1, 0x04, 0x0f8000bf },
+       { 0x405830,   1, 0x04, 0x02180324 },
+       { 0x405834,   1, 0x04, 0x08000000 },
+       { 0x405838,   1, 0x04, 0x00000000 },
+       { 0x405854,   1, 0x04, 0x00000000 },
+       { 0x405870,   4, 0x04, 0x00000001 },
+       { 0x405a00,   2, 0x04, 0x00000000 },
+       { 0x405a18,   1, 0x04, 0x00000000 },
+       {}
+};
+
+static const struct gf100_gr_init
+gf117_grctx_init_pd_0[] = {
+       { 0x406020,   1, 0x04, 0x000103c1 },
+       { 0x406028,   4, 0x04, 0x00000001 },
+       { 0x4064a8,   1, 0x04, 0x00000000 },
+       { 0x4064ac,   1, 0x04, 0x00003fff },
+       { 0x4064b4,   3, 0x04, 0x00000000 },
+       { 0x4064c0,   1, 0x04, 0x801a0078 },
+       { 0x4064c4,   1, 0x04, 0x00c9ffff },
+       { 0x4064d0,   8, 0x04, 0x00000000 },
+       {}
+};
+
+static const struct gf100_gr_pack
+gf117_grctx_pack_hub[] = {
+       { gf100_grctx_init_main_0 },
+       { gf119_grctx_init_fe_0 },
+       { gf100_grctx_init_pri_0 },
+       { gf100_grctx_init_memfmt_0 },
+       { gf117_grctx_init_ds_0 },
+       { gf117_grctx_init_pd_0 },
+       { gf100_grctx_init_rstr2d_0 },
+       { gf100_grctx_init_scc_0 },
+       { gf119_grctx_init_be_0 },
+       {}
+};
+
+static const struct gf100_gr_init
+gf117_grctx_init_setup_0[] = {
+       { 0x418800,   1, 0x04, 0x7006860a },
+       { 0x418808,   3, 0x04, 0x00000000 },
+       { 0x418828,   1, 0x04, 0x00008442 },
+       { 0x418830,   1, 0x04, 0x10000001 },
+       { 0x4188d8,   1, 0x04, 0x00000008 },
+       { 0x4188e0,   1, 0x04, 0x01000000 },
+       { 0x4188e8,   5, 0x04, 0x00000000 },
+       { 0x4188fc,   1, 0x04, 0x20100018 },
+       {}
+};
+
+static const struct gf100_gr_pack
+gf117_grctx_pack_gpc[] = {
+       { gf100_grctx_init_gpc_unk_0 },
+       { gf119_grctx_init_prop_0 },
+       { gf119_grctx_init_gpc_unk_1 },
+       { gf117_grctx_init_setup_0 },
+       { gf100_grctx_init_zcull_0 },
+       { gf119_grctx_init_crstr_0 },
+       { gf108_grctx_init_gpm_0 },
+       { gf100_grctx_init_gcc_0 },
+       {}
+};
+
+const struct gf100_gr_init
+gf117_grctx_init_pe_0[] = {
+       { 0x419848,   1, 0x04, 0x00000000 },
+       { 0x419864,   1, 0x04, 0x00000129 },
+       { 0x419888,   1, 0x04, 0x00000000 },
+       {}
+};
+
+static const struct gf100_gr_init
+gf117_grctx_init_tex_0[] = {
+       { 0x419a00,   1, 0x04, 0x000001f0 },
+       { 0x419a04,   1, 0x04, 0x00000001 },
+       { 0x419a08,   1, 0x04, 0x00000023 },
+       { 0x419a0c,   1, 0x04, 0x00020000 },
+       { 0x419a10,   1, 0x04, 0x00000000 },
+       { 0x419a14,   1, 0x04, 0x00000200 },
+       { 0x419a1c,   1, 0x04, 0x00008000 },
+       { 0x419a20,   1, 0x04, 0x00000800 },
+       { 0x419ac4,   1, 0x04, 0x0017f440 },
+       {}
+};
+
+static const struct gf100_gr_init
+gf117_grctx_init_mpc_0[] = {
+       { 0x419c00,   1, 0x04, 0x0000000a },
+       { 0x419c04,   1, 0x04, 0x00000006 },
+       { 0x419c08,   1, 0x04, 0x00000002 },
+       { 0x419c20,   1, 0x04, 0x00000000 },
+       { 0x419c24,   1, 0x04, 0x00084210 },
+       { 0x419c28,   1, 0x04, 0x3efbefbe },
+       {}
+};
+
+static const struct gf100_gr_pack
+gf117_grctx_pack_tpc[] = {
+       { gf117_grctx_init_pe_0 },
+       { gf117_grctx_init_tex_0 },
+       { gf117_grctx_init_mpc_0 },
+       { gf104_grctx_init_l1c_0 },
+       { gf119_grctx_init_sm_0 },
+       {}
+};
+
+static const struct gf100_gr_init
+gf117_grctx_init_pes_0[] = {
+       { 0x41be24,   1, 0x04, 0x00000002 },
+       {}
+};
+
+static const struct gf100_gr_init
+gf117_grctx_init_cbm_0[] = {
+       { 0x41bec0,   1, 0x04, 0x12180000 },
+       { 0x41bec4,   1, 0x04, 0x00003fff },
+       { 0x41bee4,   1, 0x04, 0x03240218 },
+       {}
+};
+
+const struct gf100_gr_init
+gf117_grctx_init_wwdx_0[] = {
+       { 0x41bf00,   1, 0x04, 0x0a418820 },
+       { 0x41bf04,   1, 0x04, 0x062080e6 },
+       { 0x41bf08,   1, 0x04, 0x020398a4 },
+       { 0x41bf0c,   1, 0x04, 0x0e629062 },
+       { 0x41bf10,   1, 0x04, 0x0a418820 },
+       { 0x41bf14,   1, 0x04, 0x000000e6 },
+       { 0x41bfd0,   1, 0x04, 0x00900103 },
+       { 0x41bfe0,   1, 0x04, 0x00400001 },
+       { 0x41bfe4,   1, 0x04, 0x00000000 },
+       {}
+};
+
+static const struct gf100_gr_pack
+gf117_grctx_pack_ppc[] = {
+       { gf117_grctx_init_pes_0 },
+       { gf117_grctx_init_cbm_0 },
+       { gf117_grctx_init_wwdx_0 },
+       {}
+};
+
+/*******************************************************************************
+ * PGRAPH context implementation
+ ******************************************************************************/
+
+void
+gf117_grctx_generate_attrib(struct gf100_grctx *info)
+{
+       struct gf100_gr_priv *priv = info->priv;
+       const struct gf100_grctx_oclass *impl = gf100_grctx_impl(priv);
+       const u32  alpha = impl->alpha_nr;
+       const u32   beta = impl->attrib_nr;
+       const u32   size = 0x20 * (impl->attrib_nr_max + impl->alpha_nr_max);
+       const u32 access = NV_MEM_ACCESS_RW;
+       const int s = 12;
+       const int b = mmio_vram(info, size * priv->tpc_total, (1 << s), access);
+       const int timeslice_mode = 1;
+       const int max_batches = 0xffff;
+       u32 bo = 0;
+       u32 ao = bo + impl->attrib_nr_max * priv->tpc_total;
+       int gpc, ppc;
+
+       mmio_refn(info, 0x418810, 0x80000000, s, b);
+       mmio_refn(info, 0x419848, 0x10000000, s, b);
+       mmio_wr32(info, 0x405830, (beta << 16) | alpha);
+       mmio_wr32(info, 0x4064c4, ((alpha / 4) << 16) | max_batches);
+
+       for (gpc = 0; gpc < priv->gpc_nr; gpc++) {
+               for (ppc = 0; ppc < priv->ppc_nr[gpc]; ppc++) {
+                       const u32 a = alpha * priv->ppc_tpc_nr[gpc][ppc];
+                       const u32 b =  beta * priv->ppc_tpc_nr[gpc][ppc];
+                       const u32 t = timeslice_mode;
+                       const u32 o = PPC_UNIT(gpc, ppc, 0);
+                       mmio_skip(info, o + 0xc0, (t << 28) | (b << 16) | ++bo);
+                       mmio_wr32(info, o + 0xc0, (t << 28) | (b << 16) | --bo);
+                       bo += impl->attrib_nr_max * priv->ppc_tpc_nr[gpc][ppc];
+                       mmio_wr32(info, o + 0xe4, (a << 16) | ao);
+                       ao += impl->alpha_nr_max * priv->ppc_tpc_nr[gpc][ppc];
+               }
+       }
+}
+
+void
+gf117_grctx_generate_main(struct gf100_gr_priv *priv, struct gf100_grctx *info)
+{
+       struct gf100_grctx_oclass *oclass = (void *)nv_engine(priv)->cclass;
+       int i;
+
+       nvkm_mc(priv)->unk260(nvkm_mc(priv), 0);
+
+       gf100_gr_mmio(priv, oclass->hub);
+       gf100_gr_mmio(priv, oclass->gpc);
+       gf100_gr_mmio(priv, oclass->zcull);
+       gf100_gr_mmio(priv, oclass->tpc);
+       gf100_gr_mmio(priv, oclass->ppc);
+
+       nv_wr32(priv, 0x404154, 0x00000000);
+
+       oclass->bundle(info);
+       oclass->pagepool(info);
+       oclass->attrib(info);
+       oclass->unkn(priv);
+
+       gf100_grctx_generate_tpcid(priv);
+       gf100_grctx_generate_r406028(priv);
+       gf100_grctx_generate_r4060a8(priv);
+       gk104_grctx_generate_r418bb8(priv);
+       gf100_grctx_generate_r406800(priv);
+
+       for (i = 0; i < 8; i++)
+               nv_wr32(priv, 0x4064d0 + (i * 0x04), 0x00000000);
+
+       gf100_gr_icmd(priv, oclass->icmd);
+       nv_wr32(priv, 0x404154, 0x00000400);
+       gf100_gr_mthd(priv, oclass->mthd);
+       nvkm_mc(priv)->unk260(nvkm_mc(priv), 1);
+}
+
+struct nvkm_oclass *
+gf117_grctx_oclass = &(struct gf100_grctx_oclass) {
+       .base.handle = NV_ENGCTX(GR, 0xd7),
+       .base.ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = gf100_gr_context_ctor,
+               .dtor = gf100_gr_context_dtor,
+               .init = _nvkm_gr_context_init,
+               .fini = _nvkm_gr_context_fini,
+               .rd32 = _nvkm_gr_context_rd32,
+               .wr32 = _nvkm_gr_context_wr32,
+       },
+       .main  = gf117_grctx_generate_main,
+       .unkn  = gk104_grctx_generate_unkn,
+       .hub   = gf117_grctx_pack_hub,
+       .gpc   = gf117_grctx_pack_gpc,
+       .zcull = gf100_grctx_pack_zcull,
+       .tpc   = gf117_grctx_pack_tpc,
+       .ppc   = gf117_grctx_pack_ppc,
+       .icmd  = gf119_grctx_pack_icmd,
+       .mthd  = gf119_grctx_pack_mthd,
+       .bundle = gf100_grctx_generate_bundle,
+       .bundle_size = 0x1800,
+       .pagepool = gf100_grctx_generate_pagepool,
+       .pagepool_size = 0x8000,
+       .attrib = gf117_grctx_generate_attrib,
+       .attrib_nr_max = 0x324,
+       .attrib_nr = 0x218,
+       .alpha_nr_max = 0x7ff,
+       .alpha_nr = 0x324,
+}.base;
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/gr/ctxgf119.c b/drivers/gpu/drm/nouveau/nvkm/engine/gr/ctxgf119.c
new file mode 100644 (file)
index 0000000..8d87614
--- /dev/null
@@ -0,0 +1,529 @@
+/*
+ * Copyright 2013 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 <bskeggs@redhat.com>
+ */
+#include "ctxgf100.h"
+
+/*******************************************************************************
+ * PGRAPH context register lists
+ ******************************************************************************/
+
+static const struct gf100_gr_init
+gf119_grctx_init_icmd_0[] = {
+       { 0x001000,   1, 0x01, 0x00000004 },
+       { 0x0000a9,   1, 0x01, 0x0000ffff },
+       { 0x000038,   1, 0x01, 0x0fac6881 },
+       { 0x00003d,   1, 0x01, 0x00000001 },
+       { 0x0000e8,   8, 0x01, 0x00000400 },
+       { 0x000078,   8, 0x01, 0x00000300 },
+       { 0x000050,   1, 0x01, 0x00000011 },
+       { 0x000058,   8, 0x01, 0x00000008 },
+       { 0x000208,   8, 0x01, 0x00000001 },
+       { 0x000081,   1, 0x01, 0x00000001 },
+       { 0x000085,   1, 0x01, 0x00000004 },
+       { 0x000088,   1, 0x01, 0x00000400 },
+       { 0x000090,   1, 0x01, 0x00000300 },
+       { 0x000098,   1, 0x01, 0x00001001 },
+       { 0x0000e3,   1, 0x01, 0x00000001 },
+       { 0x0000da,   1, 0x01, 0x00000001 },
+       { 0x0000f8,   1, 0x01, 0x00000003 },
+       { 0x0000fa,   1, 0x01, 0x00000001 },
+       { 0x00009f,   4, 0x01, 0x0000ffff },
+       { 0x0000b1,   1, 0x01, 0x00000001 },
+       { 0x0000b2,  40, 0x01, 0x00000000 },
+       { 0x000210,   8, 0x01, 0x00000040 },
+       { 0x000400,  24, 0x01, 0x00000040 },
+       { 0x000218,   8, 0x01, 0x0000c080 },
+       { 0x000440,  24, 0x01, 0x0000c080 },
+       { 0x0000ad,   1, 0x01, 0x0000013e },
+       { 0x0000e1,   1, 0x01, 0x00000010 },
+       { 0x000290,  16, 0x01, 0x00000000 },
+       { 0x0003b0,  16, 0x01, 0x00000000 },
+       { 0x0002a0,  16, 0x01, 0x00000000 },
+       { 0x000420,  16, 0x01, 0x00000000 },
+       { 0x0002b0,  16, 0x01, 0x00000000 },
+       { 0x000430,  16, 0x01, 0x00000000 },
+       { 0x0002c0,  16, 0x01, 0x00000000 },
+       { 0x0004d0,  16, 0x01, 0x00000000 },
+       { 0x000720,  16, 0x01, 0x00000000 },
+       { 0x0008c0,  16, 0x01, 0x00000000 },
+       { 0x000890,  16, 0x01, 0x00000000 },
+       { 0x0008e0,  16, 0x01, 0x00000000 },
+       { 0x0008a0,  16, 0x01, 0x00000000 },
+       { 0x0008f0,  16, 0x01, 0x00000000 },
+       { 0x00094c,   1, 0x01, 0x000000ff },
+       { 0x00094d,   1, 0x01, 0xffffffff },
+       { 0x00094e,   1, 0x01, 0x00000002 },
+       { 0x0002ec,   1, 0x01, 0x00000001 },
+       { 0x000303,   1, 0x01, 0x00000001 },
+       { 0x0002e6,   1, 0x01, 0x00000001 },
+       { 0x000466,   1, 0x01, 0x00000052 },
+       { 0x000301,   1, 0x01, 0x3f800000 },
+       { 0x000304,   1, 0x01, 0x30201000 },
+       { 0x000305,   1, 0x01, 0x70605040 },
+       { 0x000306,   1, 0x01, 0xb8a89888 },
+       { 0x000307,   1, 0x01, 0xf8e8d8c8 },
+       { 0x00030a,   1, 0x01, 0x00ffff00 },
+       { 0x00030b,   1, 0x01, 0x0000001a },
+       { 0x00030c,   1, 0x01, 0x00000001 },
+       { 0x000318,   1, 0x01, 0x00000001 },
+       { 0x000340,   1, 0x01, 0x00000000 },
+       { 0x000375,   1, 0x01, 0x00000001 },
+       { 0x000351,   1, 0x01, 0x00000100 },
+       { 0x00037d,   1, 0x01, 0x00000006 },
+       { 0x0003a0,   1, 0x01, 0x00000002 },
+       { 0x0003aa,   1, 0x01, 0x00000001 },
+       { 0x0003a9,   1, 0x01, 0x00000001 },
+       { 0x000380,   1, 0x01, 0x00000001 },
+       { 0x000360,   1, 0x01, 0x00000040 },
+       { 0x000366,   2, 0x01, 0x00000000 },
+       { 0x000368,   1, 0x01, 0x00001fff },
+       { 0x000370,   2, 0x01, 0x00000000 },
+       { 0x000372,   1, 0x01, 0x003fffff },
+       { 0x00037a,   1, 0x01, 0x00000012 },
+       { 0x0005e0,   5, 0x01, 0x00000022 },
+       { 0x000619,   1, 0x01, 0x00000003 },
+       { 0x000811,   1, 0x01, 0x00000003 },
+       { 0x000812,   1, 0x01, 0x00000004 },
+       { 0x000813,   1, 0x01, 0x00000006 },
+       { 0x000814,   1, 0x01, 0x00000008 },
+       { 0x000815,   1, 0x01, 0x0000000b },
+       { 0x000800,   6, 0x01, 0x00000001 },
+       { 0x000632,   1, 0x01, 0x00000001 },
+       { 0x000633,   1, 0x01, 0x00000002 },
+       { 0x000634,   1, 0x01, 0x00000003 },
+       { 0x000635,   1, 0x01, 0x00000004 },
+       { 0x000654,   1, 0x01, 0x3f800000 },
+       { 0x000657,   1, 0x01, 0x3f800000 },
+       { 0x000655,   2, 0x01, 0x3f800000 },
+       { 0x0006cd,   1, 0x01, 0x3f800000 },
+       { 0x0007f5,   1, 0x01, 0x3f800000 },
+       { 0x0007dc,   1, 0x01, 0x39291909 },
+       { 0x0007dd,   1, 0x01, 0x79695949 },
+       { 0x0007de,   1, 0x01, 0xb9a99989 },
+       { 0x0007df,   1, 0x01, 0xf9e9d9c9 },
+       { 0x0007e8,   1, 0x01, 0x00003210 },
+       { 0x0007e9,   1, 0x01, 0x00007654 },
+       { 0x0007ea,   1, 0x01, 0x00000098 },
+       { 0x0007ec,   1, 0x01, 0x39291909 },
+       { 0x0007ed,   1, 0x01, 0x79695949 },
+       { 0x0007ee,   1, 0x01, 0xb9a99989 },
+       { 0x0007ef,   1, 0x01, 0xf9e9d9c9 },
+       { 0x0007f0,   1, 0x01, 0x00003210 },
+       { 0x0007f1,   1, 0x01, 0x00007654 },
+       { 0x0007f2,   1, 0x01, 0x00000098 },
+       { 0x0005a5,   1, 0x01, 0x00000001 },
+       { 0x000980, 128, 0x01, 0x00000000 },
+       { 0x000468,   1, 0x01, 0x00000004 },
+       { 0x00046c,   1, 0x01, 0x00000001 },
+       { 0x000470,  96, 0x01, 0x00000000 },
+       { 0x000510,  16, 0x01, 0x3f800000 },
+       { 0x000520,   1, 0x01, 0x000002b6 },
+       { 0x000529,   1, 0x01, 0x00000001 },
+       { 0x000530,  16, 0x01, 0xffff0000 },
+       { 0x000585,   1, 0x01, 0x0000003f },
+       { 0x000576,   1, 0x01, 0x00000003 },
+       { 0x00057b,   1, 0x01, 0x00000059 },
+       { 0x000586,   1, 0x01, 0x00000040 },
+       { 0x000582,   2, 0x01, 0x00000080 },
+       { 0x0005c2,   1, 0x01, 0x00000001 },
+       { 0x000638,   2, 0x01, 0x00000001 },
+       { 0x00063a,   1, 0x01, 0x00000002 },
+       { 0x00063b,   2, 0x01, 0x00000001 },
+       { 0x00063d,   1, 0x01, 0x00000002 },
+       { 0x00063e,   1, 0x01, 0x00000001 },
+       { 0x0008b8,   8, 0x01, 0x00000001 },
+       { 0x000900,   8, 0x01, 0x00000001 },
+       { 0x000908,   8, 0x01, 0x00000002 },
+       { 0x000910,  16, 0x01, 0x00000001 },
+       { 0x000920,   8, 0x01, 0x00000002 },
+       { 0x000928,   8, 0x01, 0x00000001 },
+       { 0x000648,   9, 0x01, 0x00000001 },
+       { 0x000658,   1, 0x01, 0x0000000f },
+       { 0x0007ff,   1, 0x01, 0x0000000a },
+       { 0x00066a,   1, 0x01, 0x40000000 },
+       { 0x00066b,   1, 0x01, 0x10000000 },
+       { 0x00066c,   2, 0x01, 0xffff0000 },
+       { 0x0007af,   2, 0x01, 0x00000008 },
+       { 0x0007f6,   1, 0x01, 0x00000001 },
+       { 0x0006b2,   1, 0x01, 0x00000055 },
+       { 0x0007ad,   1, 0x01, 0x00000003 },
+       { 0x000937,   1, 0x01, 0x00000001 },
+       { 0x000971,   1, 0x01, 0x00000008 },
+       { 0x000972,   1, 0x01, 0x00000040 },
+       { 0x000973,   1, 0x01, 0x0000012c },
+       { 0x00097c,   1, 0x01, 0x00000040 },
+       { 0x000979,   1, 0x01, 0x00000003 },
+       { 0x000975,   1, 0x01, 0x00000020 },
+       { 0x000976,   1, 0x01, 0x00000001 },
+       { 0x000977,   1, 0x01, 0x00000020 },
+       { 0x000978,   1, 0x01, 0x00000001 },
+       { 0x000957,   1, 0x01, 0x00000003 },
+       { 0x00095e,   1, 0x01, 0x20164010 },
+       { 0x00095f,   1, 0x01, 0x00000020 },
+       { 0x00097d,   1, 0x01, 0x00000020 },
+       { 0x000683,   1, 0x01, 0x00000006 },
+       { 0x000685,   1, 0x01, 0x003fffff },
+       { 0x000687,   1, 0x01, 0x00000c48 },
+       { 0x0006a0,   1, 0x01, 0x00000005 },
+       { 0x000840,   1, 0x01, 0x00300008 },
+       { 0x000841,   1, 0x01, 0x04000080 },
+       { 0x000842,   1, 0x01, 0x00300008 },
+       { 0x000843,   1, 0x01, 0x04000080 },
+       { 0x000818,   8, 0x01, 0x00000000 },
+       { 0x000848,  16, 0x01, 0x00000000 },
+       { 0x000738,   1, 0x01, 0x00000000 },
+       { 0x0006aa,   1, 0x01, 0x00000001 },
+       { 0x0006ab,   1, 0x01, 0x00000002 },
+       { 0x0006ac,   1, 0x01, 0x00000080 },
+       { 0x0006ad,   2, 0x01, 0x00000100 },
+       { 0x0006b1,   1, 0x01, 0x00000011 },
+       { 0x0006bb,   1, 0x01, 0x000000cf },
+       { 0x0006ce,   1, 0x01, 0x2a712488 },
+       { 0x000739,   1, 0x01, 0x4085c000 },
+       { 0x00073a,   1, 0x01, 0x00000080 },
+       { 0x000786,   1, 0x01, 0x80000100 },
+       { 0x00073c,   1, 0x01, 0x00010100 },
+       { 0x00073d,   1, 0x01, 0x02800000 },
+       { 0x000787,   1, 0x01, 0x000000cf },
+       { 0x00078c,   1, 0x01, 0x00000008 },
+       { 0x000792,   1, 0x01, 0x00000001 },
+       { 0x000794,   3, 0x01, 0x00000001 },
+       { 0x000797,   1, 0x01, 0x000000cf },
+       { 0x000836,   1, 0x01, 0x00000001 },
+       { 0x00079a,   1, 0x01, 0x00000002 },
+       { 0x000833,   1, 0x01, 0x04444480 },
+       { 0x0007a1,   1, 0x01, 0x00000001 },
+       { 0x0007a3,   3, 0x01, 0x00000001 },
+       { 0x000831,   1, 0x01, 0x00000004 },
+       { 0x00080c,   1, 0x01, 0x00000002 },
+       { 0x00080d,   2, 0x01, 0x00000100 },
+       { 0x00080f,   1, 0x01, 0x00000001 },
+       { 0x000823,   1, 0x01, 0x00000002 },
+       { 0x000824,   2, 0x01, 0x00000100 },
+       { 0x000826,   1, 0x01, 0x00000001 },
+       { 0x00095d,   1, 0x01, 0x00000001 },
+       { 0x00082b,   1, 0x01, 0x00000004 },
+       { 0x000942,   1, 0x01, 0x00010001 },
+       { 0x000943,   1, 0x01, 0x00000001 },
+       { 0x000944,   1, 0x01, 0x00000022 },
+       { 0x0007c5,   1, 0x01, 0x00010001 },
+       { 0x000834,   1, 0x01, 0x00000001 },
+       { 0x0007c7,   1, 0x01, 0x00000001 },
+       { 0x00c1b0,   8, 0x01, 0x0000000f },
+       { 0x00c1b8,   1, 0x01, 0x0fac6881 },
+       { 0x00c1b9,   1, 0x01, 0x00fac688 },
+       { 0x01e100,   1, 0x01, 0x00000001 },
+       { 0x001000,   1, 0x01, 0x00000002 },
+       { 0x0006aa,   1, 0x01, 0x00000001 },
+       { 0x0006ad,   2, 0x01, 0x00000100 },
+       { 0x0006b1,   1, 0x01, 0x00000011 },
+       { 0x00078c,   1, 0x01, 0x00000008 },
+       { 0x000792,   1, 0x01, 0x00000001 },
+       { 0x000794,   3, 0x01, 0x00000001 },
+       { 0x000797,   1, 0x01, 0x000000cf },
+       { 0x00079a,   1, 0x01, 0x00000002 },
+       { 0x000833,   1, 0x01, 0x04444480 },
+       { 0x0007a1,   1, 0x01, 0x00000001 },
+       { 0x0007a3,   3, 0x01, 0x00000001 },
+       { 0x000831,   1, 0x01, 0x00000004 },
+       { 0x01e100,   1, 0x01, 0x00000001 },
+       { 0x001000,   1, 0x01, 0x00000014 },
+       { 0x000351,   1, 0x01, 0x00000100 },
+       { 0x000957,   1, 0x01, 0x00000003 },
+       { 0x00095d,   1, 0x01, 0x00000001 },
+       { 0x00082b,   1, 0x01, 0x00000004 },
+       { 0x000942,   1, 0x01, 0x00010001 },
+       { 0x000943,   1, 0x01, 0x00000001 },
+       { 0x0007c5,   1, 0x01, 0x00010001 },
+       { 0x000834,   1, 0x01, 0x00000001 },
+       { 0x0007c7,   1, 0x01, 0x00000001 },
+       { 0x01e100,   1, 0x01, 0x00000001 },
+       { 0x001000,   1, 0x01, 0x00000001 },
+       { 0x00080c,   1, 0x01, 0x00000002 },
+       { 0x00080d,   2, 0x01, 0x00000100 },
+       { 0x00080f,   1, 0x01, 0x00000001 },
+       { 0x000823,   1, 0x01, 0x00000002 },
+       { 0x000824,   2, 0x01, 0x00000100 },
+       { 0x000826,   1, 0x01, 0x00000001 },
+       { 0x01e100,   1, 0x01, 0x00000001 },
+       {}
+};
+
+const struct gf100_gr_pack
+gf119_grctx_pack_icmd[] = {
+       { gf119_grctx_init_icmd_0 },
+       {}
+};
+
+static const struct gf100_gr_init
+gf119_grctx_init_90c0_0[] = {
+       { 0x002700,   8, 0x20, 0x00000000 },
+       { 0x002704,   8, 0x20, 0x00000000 },
+       { 0x002708,   8, 0x20, 0x00000000 },
+       { 0x00270c,   8, 0x20, 0x00000000 },
+       { 0x002710,   8, 0x20, 0x00014000 },
+       { 0x002714,   8, 0x20, 0x00000040 },
+       { 0x00030c,   1, 0x04, 0x00000001 },
+       { 0x001944,   1, 0x04, 0x00000000 },
+       { 0x000758,   1, 0x04, 0x00000100 },
+       { 0x0002c4,   1, 0x04, 0x00000000 },
+       { 0x000790,   5, 0x04, 0x00000000 },
+       { 0x00077c,   1, 0x04, 0x00000000 },
+       { 0x000204,   3, 0x04, 0x00000000 },
+       { 0x000214,   1, 0x04, 0x00000000 },
+       { 0x00024c,   1, 0x04, 0x00000000 },
+       { 0x000d94,   1, 0x04, 0x00000001 },
+       { 0x001608,   2, 0x04, 0x00000000 },
+       { 0x001664,   1, 0x04, 0x00000000 },
+       {}
+};
+
+const struct gf100_gr_pack
+gf119_grctx_pack_mthd[] = {
+       { gf108_grctx_init_9097_0, 0x9097 },
+       { gf110_grctx_init_9197_0, 0x9197 },
+       { gf110_grctx_init_9297_0, 0x9297 },
+       { gf100_grctx_init_902d_0, 0x902d },
+       { gf100_grctx_init_9039_0, 0x9039 },
+       { gf119_grctx_init_90c0_0, 0x90c0 },
+       {}
+};
+
+const struct gf100_gr_init
+gf119_grctx_init_fe_0[] = {
+       { 0x404004,  10, 0x04, 0x00000000 },
+       { 0x404044,   1, 0x04, 0x00000000 },
+       { 0x404094,  13, 0x04, 0x00000000 },
+       { 0x4040c8,   1, 0x04, 0xf0000087 },
+       { 0x4040d0,   6, 0x04, 0x00000000 },
+       { 0x4040e8,   1, 0x04, 0x00001000 },
+       { 0x4040f8,   1, 0x04, 0x00000000 },
+       { 0x404130,   2, 0x04, 0x00000000 },
+       { 0x404138,   1, 0x04, 0x20000040 },
+       { 0x404150,   1, 0x04, 0x0000002e },
+       { 0x404154,   1, 0x04, 0x00000400 },
+       { 0x404158,   1, 0x04, 0x00000200 },
+       { 0x404164,   1, 0x04, 0x00000055 },
+       { 0x404168,   1, 0x04, 0x00000000 },
+       { 0x404178,   2, 0x04, 0x00000000 },
+       { 0x404200,   8, 0x04, 0x00000000 },
+       {}
+};
+
+static const struct gf100_gr_init
+gf119_grctx_init_ds_0[] = {
+       { 0x405800,   1, 0x04, 0x0f8000bf },
+       { 0x405830,   1, 0x04, 0x02180218 },
+       { 0x405834,   1, 0x04, 0x08000000 },
+       { 0x405838,   1, 0x04, 0x00000000 },
+       { 0x405854,   1, 0x04, 0x00000000 },
+       { 0x405870,   4, 0x04, 0x00000001 },
+       { 0x405a00,   2, 0x04, 0x00000000 },
+       { 0x405a18,   1, 0x04, 0x00000000 },
+       {}
+};
+
+static const struct gf100_gr_init
+gf119_grctx_init_pd_0[] = {
+       { 0x406020,   1, 0x04, 0x000103c1 },
+       { 0x406028,   4, 0x04, 0x00000001 },
+       { 0x4064a8,   1, 0x04, 0x00000000 },
+       { 0x4064ac,   1, 0x04, 0x00003fff },
+       { 0x4064b4,   3, 0x04, 0x00000000 },
+       { 0x4064c0,   1, 0x04, 0x80140078 },
+       { 0x4064c4,   1, 0x04, 0x0086ffff },
+       {}
+};
+
+const struct gf100_gr_init
+gf119_grctx_init_be_0[] = {
+       { 0x408800,   1, 0x04, 0x02802a3c },
+       { 0x408804,   1, 0x04, 0x00000040 },
+       { 0x408808,   1, 0x04, 0x1043e005 },
+       { 0x408900,   1, 0x04, 0x3080b801 },
+       { 0x408904,   1, 0x04, 0x62000001 },
+       { 0x408908,   1, 0x04, 0x00c8102f },
+       { 0x408980,   1, 0x04, 0x0000011d },
+       {}
+};
+
+static const struct gf100_gr_pack
+gf119_grctx_pack_hub[] = {
+       { gf100_grctx_init_main_0 },
+       { gf119_grctx_init_fe_0 },
+       { gf100_grctx_init_pri_0 },
+       { gf100_grctx_init_memfmt_0 },
+       { gf119_grctx_init_ds_0 },
+       { gf119_grctx_init_pd_0 },
+       { gf100_grctx_init_rstr2d_0 },
+       { gf100_grctx_init_scc_0 },
+       { gf119_grctx_init_be_0 },
+       {}
+};
+
+const struct gf100_gr_init
+gf119_grctx_init_prop_0[] = {
+       { 0x418400,   1, 0x04, 0x38004e00 },
+       { 0x418404,   1, 0x04, 0x71e0ffff },
+       { 0x41840c,   1, 0x04, 0x00001008 },
+       { 0x418410,   1, 0x04, 0x0fff0fff },
+       { 0x418414,   1, 0x04, 0x02200fff },
+       { 0x418450,   6, 0x04, 0x00000000 },
+       { 0x418468,   1, 0x04, 0x00000001 },
+       { 0x41846c,   2, 0x04, 0x00000000 },
+       {}
+};
+
+const struct gf100_gr_init
+gf119_grctx_init_gpc_unk_1[] = {
+       { 0x418600,   1, 0x04, 0x0000001f },
+       { 0x418684,   1, 0x04, 0x0000000f },
+       { 0x418700,   1, 0x04, 0x00000002 },
+       { 0x418704,   1, 0x04, 0x00000080 },
+       { 0x418708,   3, 0x04, 0x00000000 },
+       {}
+};
+
+static const struct gf100_gr_init
+gf119_grctx_init_setup_0[] = {
+       { 0x418800,   1, 0x04, 0x7006860a },
+       { 0x418808,   3, 0x04, 0x00000000 },
+       { 0x418828,   1, 0x04, 0x00008442 },
+       { 0x418830,   1, 0x04, 0x10000001 },
+       { 0x4188d8,   1, 0x04, 0x00000008 },
+       { 0x4188e0,   1, 0x04, 0x01000000 },
+       { 0x4188e8,   5, 0x04, 0x00000000 },
+       { 0x4188fc,   1, 0x04, 0x20100008 },
+       {}
+};
+
+const struct gf100_gr_init
+gf119_grctx_init_crstr_0[] = {
+       { 0x418b00,   1, 0x04, 0x00000006 },
+       { 0x418b08,   1, 0x04, 0x0a418820 },
+       { 0x418b0c,   1, 0x04, 0x062080e6 },
+       { 0x418b10,   1, 0x04, 0x020398a4 },
+       { 0x418b14,   1, 0x04, 0x0e629062 },
+       { 0x418b18,   1, 0x04, 0x0a418820 },
+       { 0x418b1c,   1, 0x04, 0x000000e6 },
+       { 0x418bb8,   1, 0x04, 0x00000103 },
+       {}
+};
+
+static const struct gf100_gr_pack
+gf119_grctx_pack_gpc[] = {
+       { gf100_grctx_init_gpc_unk_0 },
+       { gf119_grctx_init_prop_0 },
+       { gf119_grctx_init_gpc_unk_1 },
+       { gf119_grctx_init_setup_0 },
+       { gf100_grctx_init_zcull_0 },
+       { gf119_grctx_init_crstr_0 },
+       { gf108_grctx_init_gpm_0 },
+       { gf100_grctx_init_gcc_0 },
+       {}
+};
+
+static const struct gf100_gr_init
+gf119_grctx_init_tex_0[] = {
+       { 0x419a00,   1, 0x04, 0x000001f0 },
+       { 0x419a04,   1, 0x04, 0x00000001 },
+       { 0x419a08,   1, 0x04, 0x00000023 },
+       { 0x419a0c,   1, 0x04, 0x00020000 },
+       { 0x419a10,   1, 0x04, 0x00000000 },
+       { 0x419a14,   1, 0x04, 0x00000200 },
+       { 0x419a1c,   1, 0x04, 0x00000000 },
+       { 0x419a20,   1, 0x04, 0x00000800 },
+       { 0x419ac4,   1, 0x04, 0x0017f440 },
+       {}
+};
+
+static const struct gf100_gr_init
+gf119_grctx_init_mpc_0[] = {
+       { 0x419c00,   1, 0x04, 0x0000000a },
+       { 0x419c04,   1, 0x04, 0x00000006 },
+       { 0x419c08,   1, 0x04, 0x00000002 },
+       { 0x419c20,   1, 0x04, 0x00000000 },
+       { 0x419c24,   1, 0x04, 0x00084210 },
+       { 0x419c28,   1, 0x04, 0x3cf3cf3c },
+       {}
+};
+
+const struct gf100_gr_init
+gf119_grctx_init_sm_0[] = {
+       { 0x419e04,   3, 0x04, 0x00000000 },
+       { 0x419e10,   1, 0x04, 0x00000002 },
+       { 0x419e44,   1, 0x04, 0x001beff2 },
+       { 0x419e48,   1, 0x04, 0x00000000 },
+       { 0x419e4c,   1, 0x04, 0x0000000f },
+       { 0x419e50,  17, 0x04, 0x00000000 },
+       { 0x419e98,   1, 0x04, 0x00000000 },
+       { 0x419ee0,   1, 0x04, 0x00010110 },
+       { 0x419f30,  11, 0x04, 0x00000000 },
+       {}
+};
+
+static const struct gf100_gr_pack
+gf119_grctx_pack_tpc[] = {
+       { gf108_grctx_init_pe_0 },
+       { gf119_grctx_init_tex_0 },
+       { gf108_grctx_init_wwdx_0 },
+       { gf119_grctx_init_mpc_0 },
+       { gf104_grctx_init_l1c_0 },
+       { gf108_grctx_init_tpccs_0 },
+       { gf119_grctx_init_sm_0 },
+       {}
+};
+
+/*******************************************************************************
+ * PGRAPH context implementation
+ ******************************************************************************/
+
+struct nvkm_oclass *
+gf119_grctx_oclass = &(struct gf100_grctx_oclass) {
+       .base.handle = NV_ENGCTX(GR, 0xd9),
+       .base.ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = gf100_gr_context_ctor,
+               .dtor = gf100_gr_context_dtor,
+               .init = _nvkm_gr_context_init,
+               .fini = _nvkm_gr_context_fini,
+               .rd32 = _nvkm_gr_context_rd32,
+               .wr32 = _nvkm_gr_context_wr32,
+       },
+       .main  = gf100_grctx_generate_main,
+       .unkn  = gf108_grctx_generate_unkn,
+       .hub   = gf119_grctx_pack_hub,
+       .gpc   = gf119_grctx_pack_gpc,
+       .zcull = gf100_grctx_pack_zcull,
+       .tpc   = gf119_grctx_pack_tpc,
+       .icmd  = gf119_grctx_pack_icmd,
+       .mthd  = gf119_grctx_pack_mthd,
+       .bundle = gf100_grctx_generate_bundle,
+       .bundle_size = 0x1800,
+       .pagepool = gf100_grctx_generate_pagepool,
+       .pagepool_size = 0x8000,
+       .attrib = gf108_grctx_generate_attrib,
+       .attrib_nr_max = 0x324,
+       .attrib_nr = 0x218,
+       .alpha_nr_max = 0x324,
+       .alpha_nr = 0x218,
+}.base;
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/gr/ctxgk104.c b/drivers/gpu/drm/nouveau/nvkm/engine/gr/ctxgk104.c
new file mode 100644 (file)
index 0000000..b52300d
--- /dev/null
@@ -0,0 +1,1022 @@
+/*
+ * Copyright 2013 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 <bskeggs@redhat.com>
+ */
+#include "ctxgf100.h"
+
+#include <subdev/fb.h>
+#include <subdev/mc.h>
+
+/*******************************************************************************
+ * PGRAPH context register lists
+ ******************************************************************************/
+
+static const struct gf100_gr_init
+gk104_grctx_init_icmd_0[] = {
+       { 0x001000,   1, 0x01, 0x00000004 },
+       { 0x000039,   3, 0x01, 0x00000000 },
+       { 0x0000a9,   1, 0x01, 0x0000ffff },
+       { 0x000038,   1, 0x01, 0x0fac6881 },
+       { 0x00003d,   1, 0x01, 0x00000001 },
+       { 0x0000e8,   8, 0x01, 0x00000400 },
+       { 0x000078,   8, 0x01, 0x00000300 },
+       { 0x000050,   1, 0x01, 0x00000011 },
+       { 0x000058,   8, 0x01, 0x00000008 },
+       { 0x000208,   8, 0x01, 0x00000001 },
+       { 0x000081,   1, 0x01, 0x00000001 },
+       { 0x000085,   1, 0x01, 0x00000004 },
+       { 0x000088,   1, 0x01, 0x00000400 },
+       { 0x000090,   1, 0x01, 0x00000300 },
+       { 0x000098,   1, 0x01, 0x00001001 },
+       { 0x0000e3,   1, 0x01, 0x00000001 },
+       { 0x0000da,   1, 0x01, 0x00000001 },
+       { 0x0000f8,   1, 0x01, 0x00000003 },
+       { 0x0000fa,   1, 0x01, 0x00000001 },
+       { 0x00009f,   4, 0x01, 0x0000ffff },
+       { 0x0000b1,   1, 0x01, 0x00000001 },
+       { 0x0000ad,   1, 0x01, 0x0000013e },
+       { 0x0000e1,   1, 0x01, 0x00000010 },
+       { 0x000290,  16, 0x01, 0x00000000 },
+       { 0x0003b0,  16, 0x01, 0x00000000 },
+       { 0x0002a0,  16, 0x01, 0x00000000 },
+       { 0x000420,  16, 0x01, 0x00000000 },
+       { 0x0002b0,  16, 0x01, 0x00000000 },
+       { 0x000430,  16, 0x01, 0x00000000 },
+       { 0x0002c0,  16, 0x01, 0x00000000 },
+       { 0x0004d0,  16, 0x01, 0x00000000 },
+       { 0x000720,  16, 0x01, 0x00000000 },
+       { 0x0008c0,  16, 0x01, 0x00000000 },
+       { 0x000890,  16, 0x01, 0x00000000 },
+       { 0x0008e0,  16, 0x01, 0x00000000 },
+       { 0x0008a0,  16, 0x01, 0x00000000 },
+       { 0x0008f0,  16, 0x01, 0x00000000 },
+       { 0x00094c,   1, 0x01, 0x000000ff },
+       { 0x00094d,   1, 0x01, 0xffffffff },
+       { 0x00094e,   1, 0x01, 0x00000002 },
+       { 0x0002ec,   1, 0x01, 0x00000001 },
+       { 0x000303,   1, 0x01, 0x00000001 },
+       { 0x0002e6,   1, 0x01, 0x00000001 },
+       { 0x000466,   1, 0x01, 0x00000052 },
+       { 0x000301,   1, 0x01, 0x3f800000 },
+       { 0x000304,   1, 0x01, 0x30201000 },
+       { 0x000305,   1, 0x01, 0x70605040 },
+       { 0x000306,   1, 0x01, 0xb8a89888 },
+       { 0x000307,   1, 0x01, 0xf8e8d8c8 },
+       { 0x00030a,   1, 0x01, 0x00ffff00 },
+       { 0x00030b,   1, 0x01, 0x0000001a },
+       { 0x00030c,   1, 0x01, 0x00000001 },
+       { 0x000318,   1, 0x01, 0x00000001 },
+       { 0x000340,   1, 0x01, 0x00000000 },
+       { 0x000375,   1, 0x01, 0x00000001 },
+       { 0x00037d,   1, 0x01, 0x00000006 },
+       { 0x0003a0,   1, 0x01, 0x00000002 },
+       { 0x0003aa,   1, 0x01, 0x00000001 },
+       { 0x0003a9,   1, 0x01, 0x00000001 },
+       { 0x000380,   1, 0x01, 0x00000001 },
+       { 0x000383,   1, 0x01, 0x00000011 },
+       { 0x000360,   1, 0x01, 0x00000040 },
+       { 0x000366,   2, 0x01, 0x00000000 },
+       { 0x000368,   1, 0x01, 0x00000fff },
+       { 0x000370,   2, 0x01, 0x00000000 },
+       { 0x000372,   1, 0x01, 0x000fffff },
+       { 0x00037a,   1, 0x01, 0x00000012 },
+       { 0x000619,   1, 0x01, 0x00000003 },
+       { 0x000811,   1, 0x01, 0x00000003 },
+       { 0x000812,   1, 0x01, 0x00000004 },
+       { 0x000813,   1, 0x01, 0x00000006 },
+       { 0x000814,   1, 0x01, 0x00000008 },
+       { 0x000815,   1, 0x01, 0x0000000b },
+       { 0x000800,   6, 0x01, 0x00000001 },
+       { 0x000632,   1, 0x01, 0x00000001 },
+       { 0x000633,   1, 0x01, 0x00000002 },
+       { 0x000634,   1, 0x01, 0x00000003 },
+       { 0x000635,   1, 0x01, 0x00000004 },
+       { 0x000654,   1, 0x01, 0x3f800000 },
+       { 0x000657,   1, 0x01, 0x3f800000 },
+       { 0x000655,   2, 0x01, 0x3f800000 },
+       { 0x0006cd,   1, 0x01, 0x3f800000 },
+       { 0x0007f5,   1, 0x01, 0x3f800000 },
+       { 0x0007dc,   1, 0x01, 0x39291909 },
+       { 0x0007dd,   1, 0x01, 0x79695949 },
+       { 0x0007de,   1, 0x01, 0xb9a99989 },
+       { 0x0007df,   1, 0x01, 0xf9e9d9c9 },
+       { 0x0007e8,   1, 0x01, 0x00003210 },
+       { 0x0007e9,   1, 0x01, 0x00007654 },
+       { 0x0007ea,   1, 0x01, 0x00000098 },
+       { 0x0007ec,   1, 0x01, 0x39291909 },
+       { 0x0007ed,   1, 0x01, 0x79695949 },
+       { 0x0007ee,   1, 0x01, 0xb9a99989 },
+       { 0x0007ef,   1, 0x01, 0xf9e9d9c9 },
+       { 0x0007f0,   1, 0x01, 0x00003210 },
+       { 0x0007f1,   1, 0x01, 0x00007654 },
+       { 0x0007f2,   1, 0x01, 0x00000098 },
+       { 0x0005a5,   1, 0x01, 0x00000001 },
+       { 0x000980, 128, 0x01, 0x00000000 },
+       { 0x000468,   1, 0x01, 0x00000004 },
+       { 0x00046c,   1, 0x01, 0x00000001 },
+       { 0x000470,  96, 0x01, 0x00000000 },
+       { 0x000510,  16, 0x01, 0x3f800000 },
+       { 0x000520,   1, 0x01, 0x000002b6 },
+       { 0x000529,   1, 0x01, 0x00000001 },
+       { 0x000530,  16, 0x01, 0xffff0000 },
+       { 0x000585,   1, 0x01, 0x0000003f },
+       { 0x000576,   1, 0x01, 0x00000003 },
+       { 0x00057b,   1, 0x01, 0x00000059 },
+       { 0x000586,   1, 0x01, 0x00000040 },
+       { 0x000582,   2, 0x01, 0x00000080 },
+       { 0x0005c2,   1, 0x01, 0x00000001 },
+       { 0x000638,   2, 0x01, 0x00000001 },
+       { 0x00063a,   1, 0x01, 0x00000002 },
+       { 0x00063b,   2, 0x01, 0x00000001 },
+       { 0x00063d,   1, 0x01, 0x00000002 },
+       { 0x00063e,   1, 0x01, 0x00000001 },
+       { 0x0008b8,   8, 0x01, 0x00000001 },
+       { 0x000900,   8, 0x01, 0x00000001 },
+       { 0x000908,   8, 0x01, 0x00000002 },
+       { 0x000910,  16, 0x01, 0x00000001 },
+       { 0x000920,   8, 0x01, 0x00000002 },
+       { 0x000928,   8, 0x01, 0x00000001 },
+       { 0x000648,   9, 0x01, 0x00000001 },
+       { 0x000658,   1, 0x01, 0x0000000f },
+       { 0x0007ff,   1, 0x01, 0x0000000a },
+       { 0x00066a,   1, 0x01, 0x40000000 },
+       { 0x00066b,   1, 0x01, 0x10000000 },
+       { 0x00066c,   2, 0x01, 0xffff0000 },
+       { 0x0007af,   2, 0x01, 0x00000008 },
+       { 0x0007f6,   1, 0x01, 0x00000001 },
+       { 0x0006b2,   1, 0x01, 0x00000055 },
+       { 0x0007ad,   1, 0x01, 0x00000003 },
+       { 0x000937,   1, 0x01, 0x00000001 },
+       { 0x000971,   1, 0x01, 0x00000008 },
+       { 0x000972,   1, 0x01, 0x00000040 },
+       { 0x000973,   1, 0x01, 0x0000012c },
+       { 0x00097c,   1, 0x01, 0x00000040 },
+       { 0x000979,   1, 0x01, 0x00000003 },
+       { 0x000975,   1, 0x01, 0x00000020 },
+       { 0x000976,   1, 0x01, 0x00000001 },
+       { 0x000977,   1, 0x01, 0x00000020 },
+       { 0x000978,   1, 0x01, 0x00000001 },
+       { 0x000957,   1, 0x01, 0x00000003 },
+       { 0x00095e,   1, 0x01, 0x20164010 },
+       { 0x00095f,   1, 0x01, 0x00000020 },
+       { 0x00097d,   1, 0x01, 0x00000020 },
+       { 0x000683,   1, 0x01, 0x00000006 },
+       { 0x000685,   1, 0x01, 0x003fffff },
+       { 0x000687,   1, 0x01, 0x003fffff },
+       { 0x0006a0,   1, 0x01, 0x00000005 },
+       { 0x000840,   1, 0x01, 0x00400008 },
+       { 0x000841,   1, 0x01, 0x08000080 },
+       { 0x000842,   1, 0x01, 0x00400008 },
+       { 0x000843,   1, 0x01, 0x08000080 },
+       { 0x0006aa,   1, 0x01, 0x00000001 },
+       { 0x0006ab,   1, 0x01, 0x00000002 },
+       { 0x0006ac,   1, 0x01, 0x00000080 },
+       { 0x0006ad,   2, 0x01, 0x00000100 },
+       { 0x0006b1,   1, 0x01, 0x00000011 },
+       { 0x0006bb,   1, 0x01, 0x000000cf },
+       { 0x0006ce,   1, 0x01, 0x2a712488 },
+       { 0x000739,   1, 0x01, 0x4085c000 },
+       { 0x00073a,   1, 0x01, 0x00000080 },
+       { 0x000786,   1, 0x01, 0x80000100 },
+       { 0x00073c,   1, 0x01, 0x00010100 },
+       { 0x00073d,   1, 0x01, 0x02800000 },
+       { 0x000787,   1, 0x01, 0x000000cf },
+       { 0x00078c,   1, 0x01, 0x00000008 },
+       { 0x000792,   1, 0x01, 0x00000001 },
+       { 0x000794,   3, 0x01, 0x00000001 },
+       { 0x000797,   1, 0x01, 0x000000cf },
+       { 0x000836,   1, 0x01, 0x00000001 },
+       { 0x00079a,   1, 0x01, 0x00000002 },
+       { 0x000833,   1, 0x01, 0x04444480 },
+       { 0x0007a1,   1, 0x01, 0x00000001 },
+       { 0x0007a3,   3, 0x01, 0x00000001 },
+       { 0x000831,   1, 0x01, 0x00000004 },
+       { 0x000b07,   1, 0x01, 0x00000002 },
+       { 0x000b08,   2, 0x01, 0x00000100 },
+       { 0x000b0a,   1, 0x01, 0x00000001 },
+       { 0x000a04,   1, 0x01, 0x000000ff },
+       { 0x000a0b,   1, 0x01, 0x00000040 },
+       { 0x00097f,   1, 0x01, 0x00000100 },
+       { 0x000a02,   1, 0x01, 0x00000001 },
+       { 0x000809,   1, 0x01, 0x00000007 },
+       { 0x00c221,   1, 0x01, 0x00000040 },
+       { 0x00c1b0,   8, 0x01, 0x0000000f },
+       { 0x00c1b8,   1, 0x01, 0x0fac6881 },
+       { 0x00c1b9,   1, 0x01, 0x00fac688 },
+       { 0x00c401,   1, 0x01, 0x00000001 },
+       { 0x00c402,   1, 0x01, 0x00010001 },
+       { 0x00c403,   2, 0x01, 0x00000001 },
+       { 0x00c40e,   1, 0x01, 0x00000020 },
+       { 0x00c500,   1, 0x01, 0x00000003 },
+       { 0x01e100,   1, 0x01, 0x00000001 },
+       { 0x001000,   1, 0x01, 0x00000002 },
+       { 0x0006aa,   1, 0x01, 0x00000001 },
+       { 0x0006ad,   2, 0x01, 0x00000100 },
+       { 0x0006b1,   1, 0x01, 0x00000011 },
+       { 0x00078c,   1, 0x01, 0x00000008 },
+       { 0x000792,   1, 0x01, 0x00000001 },
+       { 0x000794,   3, 0x01, 0x00000001 },
+       { 0x000797,   1, 0x01, 0x000000cf },
+       { 0x00079a,   1, 0x01, 0x00000002 },
+       { 0x000833,   1, 0x01, 0x04444480 },
+       { 0x0007a1,   1, 0x01, 0x00000001 },
+       { 0x0007a3,   3, 0x01, 0x00000001 },
+       { 0x000831,   1, 0x01, 0x00000004 },
+       { 0x01e100,   1, 0x01, 0x00000001 },
+       { 0x001000,   1, 0x01, 0x00000008 },
+       { 0x000039,   3, 0x01, 0x00000000 },
+       { 0x000380,   1, 0x01, 0x00000001 },
+       { 0x000366,   2, 0x01, 0x00000000 },
+       { 0x000368,   1, 0x01, 0x00000fff },
+       { 0x000370,   2, 0x01, 0x00000000 },
+       { 0x000372,   1, 0x01, 0x000fffff },
+       { 0x000813,   1, 0x01, 0x00000006 },
+       { 0x000814,   1, 0x01, 0x00000008 },
+       { 0x000957,   1, 0x01, 0x00000003 },
+       { 0x000b07,   1, 0x01, 0x00000002 },
+       { 0x000b08,   2, 0x01, 0x00000100 },
+       { 0x000b0a,   1, 0x01, 0x00000001 },
+       { 0x000a04,   1, 0x01, 0x000000ff },
+       { 0x00097f,   1, 0x01, 0x00000100 },
+       { 0x000a02,   1, 0x01, 0x00000001 },
+       { 0x000809,   1, 0x01, 0x00000007 },
+       { 0x00c221,   1, 0x01, 0x00000040 },
+       { 0x00c401,   1, 0x01, 0x00000001 },
+       { 0x00c402,   1, 0x01, 0x00010001 },
+       { 0x00c403,   2, 0x01, 0x00000001 },
+       { 0x00c40e,   1, 0x01, 0x00000020 },
+       { 0x00c500,   1, 0x01, 0x00000003 },
+       { 0x01e100,   1, 0x01, 0x00000001 },
+       { 0x001000,   1, 0x01, 0x00000001 },
+       { 0x000b07,   1, 0x01, 0x00000002 },
+       { 0x000b08,   2, 0x01, 0x00000100 },
+       { 0x000b0a,   1, 0x01, 0x00000001 },
+       { 0x01e100,   1, 0x01, 0x00000001 },
+       {}
+};
+
+const struct gf100_gr_pack
+gk104_grctx_pack_icmd[] = {
+       { gk104_grctx_init_icmd_0 },
+       {}
+};
+
+const struct gf100_gr_init
+gk104_grctx_init_a097_0[] = {
+       { 0x000800,   8, 0x40, 0x00000000 },
+       { 0x000804,   8, 0x40, 0x00000000 },
+       { 0x000808,   8, 0x40, 0x00000400 },
+       { 0x00080c,   8, 0x40, 0x00000300 },
+       { 0x000810,   1, 0x04, 0x000000cf },
+       { 0x000850,   7, 0x40, 0x00000000 },
+       { 0x000814,   8, 0x40, 0x00000040 },
+       { 0x000818,   8, 0x40, 0x00000001 },
+       { 0x00081c,   8, 0x40, 0x00000000 },
+       { 0x000820,   8, 0x40, 0x00000000 },
+       { 0x001c00,  16, 0x10, 0x00000000 },
+       { 0x001c04,  16, 0x10, 0x00000000 },
+       { 0x001c08,  16, 0x10, 0x00000000 },
+       { 0x001c0c,  16, 0x10, 0x00000000 },
+       { 0x001d00,  16, 0x10, 0x00000000 },
+       { 0x001d04,  16, 0x10, 0x00000000 },
+       { 0x001d08,  16, 0x10, 0x00000000 },
+       { 0x001d0c,  16, 0x10, 0x00000000 },
+       { 0x001f00,  16, 0x08, 0x00000000 },
+       { 0x001f04,  16, 0x08, 0x00000000 },
+       { 0x001f80,  16, 0x08, 0x00000000 },
+       { 0x001f84,  16, 0x08, 0x00000000 },
+       { 0x002000,   1, 0x04, 0x00000000 },
+       { 0x002040,   1, 0x04, 0x00000011 },
+       { 0x002080,   1, 0x04, 0x00000020 },
+       { 0x0020c0,   1, 0x04, 0x00000030 },
+       { 0x002100,   1, 0x04, 0x00000040 },
+       { 0x002140,   1, 0x04, 0x00000051 },
+       { 0x00200c,   6, 0x40, 0x00000001 },
+       { 0x002010,   1, 0x04, 0x00000000 },
+       { 0x002050,   1, 0x04, 0x00000000 },
+       { 0x002090,   1, 0x04, 0x00000001 },
+       { 0x0020d0,   1, 0x04, 0x00000002 },
+       { 0x002110,   1, 0x04, 0x00000003 },
+       { 0x002150,   1, 0x04, 0x00000004 },
+       { 0x000380,   4, 0x20, 0x00000000 },
+       { 0x000384,   4, 0x20, 0x00000000 },
+       { 0x000388,   4, 0x20, 0x00000000 },
+       { 0x00038c,   4, 0x20, 0x00000000 },
+       { 0x000700,   4, 0x10, 0x00000000 },
+       { 0x000704,   4, 0x10, 0x00000000 },
+       { 0x000708,   4, 0x10, 0x00000000 },
+       { 0x002800, 128, 0x04, 0x00000000 },
+       { 0x000a00,  16, 0x20, 0x00000000 },
+       { 0x000a04,  16, 0x20, 0x00000000 },
+       { 0x000a08,  16, 0x20, 0x00000000 },
+       { 0x000a0c,  16, 0x20, 0x00000000 },
+       { 0x000a10,  16, 0x20, 0x00000000 },
+       { 0x000a14,  16, 0x20, 0x00000000 },
+       { 0x000c00,  16, 0x10, 0x00000000 },
+       { 0x000c04,  16, 0x10, 0x00000000 },
+       { 0x000c08,  16, 0x10, 0x00000000 },
+       { 0x000c0c,  16, 0x10, 0x3f800000 },
+       { 0x000d00,   8, 0x08, 0xffff0000 },
+       { 0x000d04,   8, 0x08, 0xffff0000 },
+       { 0x000e00,  16, 0x10, 0x00000000 },
+       { 0x000e04,  16, 0x10, 0xffff0000 },
+       { 0x000e08,  16, 0x10, 0xffff0000 },
+       { 0x000d40,   4, 0x08, 0x00000000 },
+       { 0x000d44,   4, 0x08, 0x00000000 },
+       { 0x001e00,   8, 0x20, 0x00000001 },
+       { 0x001e04,   8, 0x20, 0x00000001 },
+       { 0x001e08,   8, 0x20, 0x00000002 },
+       { 0x001e0c,   8, 0x20, 0x00000001 },
+       { 0x001e10,   8, 0x20, 0x00000001 },
+       { 0x001e14,   8, 0x20, 0x00000002 },
+       { 0x001e18,   8, 0x20, 0x00000001 },
+       { 0x003400, 128, 0x04, 0x00000000 },
+       { 0x00030c,   1, 0x04, 0x00000001 },
+       { 0x001944,   1, 0x04, 0x00000000 },
+       { 0x001514,   1, 0x04, 0x00000000 },
+       { 0x000d68,   1, 0x04, 0x0000ffff },
+       { 0x00121c,   1, 0x04, 0x0fac6881 },
+       { 0x000fac,   1, 0x04, 0x00000001 },
+       { 0x001538,   1, 0x04, 0x00000001 },
+       { 0x000fe0,   2, 0x04, 0x00000000 },
+       { 0x000fe8,   1, 0x04, 0x00000014 },
+       { 0x000fec,   1, 0x04, 0x00000040 },
+       { 0x000ff0,   1, 0x04, 0x00000000 },
+       { 0x00179c,   1, 0x04, 0x00000000 },
+       { 0x001228,   1, 0x04, 0x00000400 },
+       { 0x00122c,   1, 0x04, 0x00000300 },
+       { 0x001230,   1, 0x04, 0x00010001 },
+       { 0x0007f8,   1, 0x04, 0x00000000 },
+       { 0x0015b4,   1, 0x04, 0x00000001 },
+       { 0x0015cc,   1, 0x04, 0x00000000 },
+       { 0x001534,   1, 0x04, 0x00000000 },
+       { 0x000fb0,   1, 0x04, 0x00000000 },
+       { 0x0015d0,   1, 0x04, 0x00000000 },
+       { 0x00153c,   1, 0x04, 0x00000000 },
+       { 0x0016b4,   1, 0x04, 0x00000003 },
+       { 0x000fbc,   4, 0x04, 0x0000ffff },
+       { 0x000df8,   2, 0x04, 0x00000000 },
+       { 0x001948,   1, 0x04, 0x00000000 },
+       { 0x001970,   1, 0x04, 0x00000001 },
+       { 0x00161c,   1, 0x04, 0x000009f0 },
+       { 0x000dcc,   1, 0x04, 0x00000010 },
+       { 0x00163c,   1, 0x04, 0x00000000 },
+       { 0x0015e4,   1, 0x04, 0x00000000 },
+       { 0x001160,  32, 0x04, 0x25e00040 },
+       { 0x001880,  32, 0x04, 0x00000000 },
+       { 0x000f84,   2, 0x04, 0x00000000 },
+       { 0x0017c8,   2, 0x04, 0x00000000 },
+       { 0x0017d0,   1, 0x04, 0x000000ff },
+       { 0x0017d4,   1, 0x04, 0xffffffff },
+       { 0x0017d8,   1, 0x04, 0x00000002 },
+       { 0x0017dc,   1, 0x04, 0x00000000 },
+       { 0x0015f4,   2, 0x04, 0x00000000 },
+       { 0x001434,   2, 0x04, 0x00000000 },
+       { 0x000d74,   1, 0x04, 0x00000000 },
+       { 0x000dec,   1, 0x04, 0x00000001 },
+       { 0x0013a4,   1, 0x04, 0x00000000 },
+       { 0x001318,   1, 0x04, 0x00000001 },
+       { 0x001644,   1, 0x04, 0x00000000 },
+       { 0x000748,   1, 0x04, 0x00000000 },
+       { 0x000de8,   1, 0x04, 0x00000000 },
+       { 0x001648,   1, 0x04, 0x00000000 },
+       { 0x0012a4,   1, 0x04, 0x00000000 },
+       { 0x001120,   4, 0x04, 0x00000000 },
+       { 0x001118,   1, 0x04, 0x00000000 },
+       { 0x00164c,   1, 0x04, 0x00000000 },
+       { 0x001658,   1, 0x04, 0x00000000 },
+       { 0x001910,   1, 0x04, 0x00000290 },
+       { 0x001518,   1, 0x04, 0x00000000 },
+       { 0x00165c,   1, 0x04, 0x00000001 },
+       { 0x001520,   1, 0x04, 0x00000000 },
+       { 0x001604,   1, 0x04, 0x00000000 },
+       { 0x001570,   1, 0x04, 0x00000000 },
+       { 0x0013b0,   2, 0x04, 0x3f800000 },
+       { 0x00020c,   1, 0x04, 0x00000000 },
+       { 0x001670,   1, 0x04, 0x30201000 },
+       { 0x001674,   1, 0x04, 0x70605040 },
+       { 0x001678,   1, 0x04, 0xb8a89888 },
+       { 0x00167c,   1, 0x04, 0xf8e8d8c8 },
+       { 0x00166c,   1, 0x04, 0x00000000 },
+       { 0x001680,   1, 0x04, 0x00ffff00 },
+       { 0x0012d0,   1, 0x04, 0x00000003 },
+       { 0x0012d4,   1, 0x04, 0x00000002 },
+       { 0x001684,   2, 0x04, 0x00000000 },
+       { 0x000dac,   2, 0x04, 0x00001b02 },
+       { 0x000db4,   1, 0x04, 0x00000000 },
+       { 0x00168c,   1, 0x04, 0x00000000 },
+       { 0x0015bc,   1, 0x04, 0x00000000 },
+       { 0x00156c,   1, 0x04, 0x00000000 },
+       { 0x00187c,   1, 0x04, 0x00000000 },
+       { 0x001110,   1, 0x04, 0x00000001 },
+       { 0x000dc0,   3, 0x04, 0x00000000 },
+       { 0x001234,   1, 0x04, 0x00000000 },
+       { 0x001690,   1, 0x04, 0x00000000 },
+       { 0x0012ac,   1, 0x04, 0x00000001 },
+       { 0x000790,   5, 0x04, 0x00000000 },
+       { 0x00077c,   1, 0x04, 0x00000000 },
+       { 0x001000,   1, 0x04, 0x00000010 },
+       { 0x0010fc,   1, 0x04, 0x00000000 },
+       { 0x001290,   1, 0x04, 0x00000000 },
+       { 0x000218,   1, 0x04, 0x00000010 },
+       { 0x0012d8,   1, 0x04, 0x00000000 },
+       { 0x0012dc,   1, 0x04, 0x00000010 },
+       { 0x000d94,   1, 0x04, 0x00000001 },
+       { 0x00155c,   2, 0x04, 0x00000000 },
+       { 0x001564,   1, 0x04, 0x00000fff },
+       { 0x001574,   2, 0x04, 0x00000000 },
+       { 0x00157c,   1, 0x04, 0x000fffff },
+       { 0x001354,   1, 0x04, 0x00000000 },
+       { 0x001610,   1, 0x04, 0x00000012 },
+       { 0x001608,   2, 0x04, 0x00000000 },
+       { 0x00260c,   1, 0x04, 0x00000000 },
+       { 0x0007ac,   1, 0x04, 0x00000000 },
+       { 0x00162c,   1, 0x04, 0x00000003 },
+       { 0x000210,   1, 0x04, 0x00000000 },
+       { 0x000320,   1, 0x04, 0x00000000 },
+       { 0x000324,   6, 0x04, 0x3f800000 },
+       { 0x000750,   1, 0x04, 0x00000000 },
+       { 0x000760,   1, 0x04, 0x39291909 },
+       { 0x000764,   1, 0x04, 0x79695949 },
+       { 0x000768,   1, 0x04, 0xb9a99989 },
+       { 0x00076c,   1, 0x04, 0xf9e9d9c9 },
+       { 0x000770,   1, 0x04, 0x30201000 },
+       { 0x000774,   1, 0x04, 0x70605040 },
+       { 0x000778,   1, 0x04, 0x00009080 },
+       { 0x000780,   1, 0x04, 0x39291909 },
+       { 0x000784,   1, 0x04, 0x79695949 },
+       { 0x000788,   1, 0x04, 0xb9a99989 },
+       { 0x00078c,   1, 0x04, 0xf9e9d9c9 },
+       { 0x0007d0,   1, 0x04, 0x30201000 },
+       { 0x0007d4,   1, 0x04, 0x70605040 },
+       { 0x0007d8,   1, 0x04, 0x00009080 },
+       { 0x00037c,   1, 0x04, 0x00000001 },
+       { 0x000740,   2, 0x04, 0x00000000 },
+       { 0x002600,   1, 0x04, 0x00000000 },
+       { 0x001918,   1, 0x04, 0x00000000 },
+       { 0x00191c,   1, 0x04, 0x00000900 },
+       { 0x001920,   1, 0x04, 0x00000405 },
+       { 0x001308,   1, 0x04, 0x00000001 },
+       { 0x001924,   1, 0x04, 0x00000000 },
+       { 0x0013ac,   1, 0x04, 0x00000000 },
+       { 0x00192c,   1, 0x04, 0x00000001 },
+       { 0x00193c,   1, 0x04, 0x00002c1c },
+       { 0x000d7c,   1, 0x04, 0x00000000 },
+       { 0x000f8c,   1, 0x04, 0x00000000 },
+       { 0x0002c0,   1, 0x04, 0x00000001 },
+       { 0x001510,   1, 0x04, 0x00000000 },
+       { 0x001940,   1, 0x04, 0x00000000 },
+       { 0x000ff4,   2, 0x04, 0x00000000 },
+       { 0x00194c,   2, 0x04, 0x00000000 },
+       { 0x001968,   1, 0x04, 0x00000000 },
+       { 0x001590,   1, 0x04, 0x0000003f },
+       { 0x0007e8,   4, 0x04, 0x00000000 },
+       { 0x00196c,   1, 0x04, 0x00000011 },
+       { 0x0002e4,   1, 0x04, 0x0000b001 },
+       { 0x00036c,   2, 0x04, 0x00000000 },
+       { 0x00197c,   1, 0x04, 0x00000000 },
+       { 0x000fcc,   2, 0x04, 0x00000000 },
+       { 0x0002d8,   1, 0x04, 0x00000040 },
+       { 0x001980,   1, 0x04, 0x00000080 },
+       { 0x001504,   1, 0x04, 0x00000080 },
+       { 0x001984,   1, 0x04, 0x00000000 },
+       { 0x000300,   1, 0x04, 0x00000001 },
+       { 0x0013a8,   1, 0x04, 0x00000000 },
+       { 0x0012ec,   1, 0x04, 0x00000000 },
+       { 0x001310,   1, 0x04, 0x00000000 },
+       { 0x001314,   1, 0x04, 0x00000001 },
+       { 0x001380,   1, 0x04, 0x00000000 },
+       { 0x001384,   4, 0x04, 0x00000001 },
+       { 0x001394,   1, 0x04, 0x00000000 },
+       { 0x00139c,   1, 0x04, 0x00000000 },
+       { 0x001398,   1, 0x04, 0x00000000 },
+       { 0x001594,   1, 0x04, 0x00000000 },
+       { 0x001598,   4, 0x04, 0x00000001 },
+       { 0x000f54,   3, 0x04, 0x00000000 },
+       { 0x0019bc,   1, 0x04, 0x00000000 },
+       { 0x000f9c,   2, 0x04, 0x00000000 },
+       { 0x0012cc,   1, 0x04, 0x00000000 },
+       { 0x0012e8,   1, 0x04, 0x00000000 },
+       { 0x00130c,   1, 0x04, 0x00000001 },
+       { 0x001360,   8, 0x04, 0x00000000 },
+       { 0x00133c,   2, 0x04, 0x00000001 },
+       { 0x001344,   1, 0x04, 0x00000002 },
+       { 0x001348,   2, 0x04, 0x00000001 },
+       { 0x001350,   1, 0x04, 0x00000002 },
+       { 0x001358,   1, 0x04, 0x00000001 },
+       { 0x0012e4,   1, 0x04, 0x00000000 },
+       { 0x00131c,   4, 0x04, 0x00000000 },
+       { 0x0019c0,   1, 0x04, 0x00000000 },
+       { 0x001140,   1, 0x04, 0x00000000 },
+       { 0x0019c4,   1, 0x04, 0x00000000 },
+       { 0x0019c8,   1, 0x04, 0x00001500 },
+       { 0x00135c,   1, 0x04, 0x00000000 },
+       { 0x000f90,   1, 0x04, 0x00000000 },
+       { 0x0019e0,   8, 0x04, 0x00000001 },
+       { 0x0019cc,   1, 0x04, 0x00000001 },
+       { 0x0015b8,   1, 0x04, 0x00000000 },
+       { 0x001a00,   1, 0x04, 0x00001111 },
+       { 0x001a04,   7, 0x04, 0x00000000 },
+       { 0x000d6c,   2, 0x04, 0xffff0000 },
+       { 0x0010f8,   1, 0x04, 0x00001010 },
+       { 0x000d80,   5, 0x04, 0x00000000 },
+       { 0x000da0,   1, 0x04, 0x00000000 },
+       { 0x0007a4,   2, 0x04, 0x00000000 },
+       { 0x001508,   1, 0x04, 0x80000000 },
+       { 0x00150c,   1, 0x04, 0x40000000 },
+       { 0x001668,   1, 0x04, 0x00000000 },
+       { 0x000318,   2, 0x04, 0x00000008 },
+       { 0x000d9c,   1, 0x04, 0x00000001 },
+       { 0x000374,   1, 0x04, 0x00000000 },
+       { 0x000378,   1, 0x04, 0x00000020 },
+       { 0x0007dc,   1, 0x04, 0x00000000 },
+       { 0x00074c,   1, 0x04, 0x00000055 },
+       { 0x001420,   1, 0x04, 0x00000003 },
+       { 0x0017bc,   2, 0x04, 0x00000000 },
+       { 0x0017c4,   1, 0x04, 0x00000001 },
+       { 0x001008,   1, 0x04, 0x00000008 },
+       { 0x00100c,   1, 0x04, 0x00000040 },
+       { 0x001010,   1, 0x04, 0x0000012c },
+       { 0x000d60,   1, 0x04, 0x00000040 },
+       { 0x00075c,   1, 0x04, 0x00000003 },
+       { 0x001018,   1, 0x04, 0x00000020 },
+       { 0x00101c,   1, 0x04, 0x00000001 },
+       { 0x001020,   1, 0x04, 0x00000020 },
+       { 0x001024,   1, 0x04, 0x00000001 },
+       { 0x001444,   3, 0x04, 0x00000000 },
+       { 0x000360,   1, 0x04, 0x20164010 },
+       { 0x000364,   1, 0x04, 0x00000020 },
+       { 0x000368,   1, 0x04, 0x00000000 },
+       { 0x000de4,   1, 0x04, 0x00000000 },
+       { 0x000204,   1, 0x04, 0x00000006 },
+       { 0x000208,   1, 0x04, 0x00000000 },
+       { 0x0002cc,   2, 0x04, 0x003fffff },
+       { 0x001220,   1, 0x04, 0x00000005 },
+       { 0x000fdc,   1, 0x04, 0x00000000 },
+       { 0x000f98,   1, 0x04, 0x00400008 },
+       { 0x001284,   1, 0x04, 0x08000080 },
+       { 0x001450,   1, 0x04, 0x00400008 },
+       { 0x001454,   1, 0x04, 0x08000080 },
+       { 0x000214,   1, 0x04, 0x00000000 },
+       {}
+};
+
+static const struct gf100_gr_pack
+gk104_grctx_pack_mthd[] = {
+       { gk104_grctx_init_a097_0, 0xa097 },
+       { gf100_grctx_init_902d_0, 0x902d },
+       {}
+};
+
+static const struct gf100_gr_init
+gk104_grctx_init_fe_0[] = {
+       { 0x404010,   5, 0x04, 0x00000000 },
+       { 0x404024,   1, 0x04, 0x0000e000 },
+       { 0x404028,   1, 0x04, 0x00000000 },
+       { 0x4040a8,   8, 0x04, 0x00000000 },
+       { 0x4040c8,   1, 0x04, 0xf800008f },
+       { 0x4040d0,   6, 0x04, 0x00000000 },
+       { 0x4040e8,   1, 0x04, 0x00001000 },
+       { 0x4040f8,   1, 0x04, 0x00000000 },
+       { 0x404130,   2, 0x04, 0x00000000 },
+       { 0x404138,   1, 0x04, 0x20000040 },
+       { 0x404150,   1, 0x04, 0x0000002e },
+       { 0x404154,   1, 0x04, 0x00000400 },
+       { 0x404158,   1, 0x04, 0x00000200 },
+       { 0x404164,   1, 0x04, 0x00000055 },
+       { 0x4041a0,   4, 0x04, 0x00000000 },
+       { 0x404200,   4, 0x04, 0x00000000 },
+       {}
+};
+
+const struct gf100_gr_init
+gk104_grctx_init_memfmt_0[] = {
+       { 0x404604,   1, 0x04, 0x00000014 },
+       { 0x404608,   1, 0x04, 0x00000000 },
+       { 0x40460c,   1, 0x04, 0x00003fff },
+       { 0x404610,   1, 0x04, 0x00000100 },
+       { 0x404618,   4, 0x04, 0x00000000 },
+       { 0x40462c,   2, 0x04, 0x00000000 },
+       { 0x404640,   1, 0x04, 0x00000000 },
+       { 0x404654,   1, 0x04, 0x00000000 },
+       { 0x404660,   1, 0x04, 0x00000000 },
+       { 0x404678,   1, 0x04, 0x00000000 },
+       { 0x40467c,   1, 0x04, 0x00000002 },
+       { 0x404680,   8, 0x04, 0x00000000 },
+       { 0x4046a0,   1, 0x04, 0x007f0080 },
+       { 0x4046a4,   8, 0x04, 0x00000000 },
+       { 0x4046c8,   3, 0x04, 0x00000000 },
+       { 0x404700,   3, 0x04, 0x00000000 },
+       { 0x404718,   7, 0x04, 0x00000000 },
+       { 0x404734,   1, 0x04, 0x00000100 },
+       { 0x404738,   2, 0x04, 0x00000000 },
+       { 0x404744,   2, 0x04, 0x00000000 },
+       { 0x404754,   1, 0x04, 0x00000000 },
+       {}
+};
+
+const struct gf100_gr_init
+gk104_grctx_init_ds_0[] = {
+       { 0x405800,   1, 0x04, 0x0f8000bf },
+       { 0x405830,   1, 0x04, 0x02180648 },
+       { 0x405834,   1, 0x04, 0x08000000 },
+       { 0x405838,   1, 0x04, 0x00000000 },
+       { 0x405854,   1, 0x04, 0x00000000 },
+       { 0x405870,   4, 0x04, 0x00000001 },
+       { 0x405a00,   2, 0x04, 0x00000000 },
+       { 0x405a18,   1, 0x04, 0x00000000 },
+       {}
+};
+
+static const struct gf100_gr_init
+gk104_grctx_init_cwd_0[] = {
+       { 0x405b00,   1, 0x04, 0x00000000 },
+       { 0x405b10,   1, 0x04, 0x00001000 },
+       {}
+};
+
+static const struct gf100_gr_init
+gk104_grctx_init_pd_0[] = {
+       { 0x406020,   1, 0x04, 0x004103c1 },
+       { 0x406028,   4, 0x04, 0x00000001 },
+       { 0x4064a8,   1, 0x04, 0x00000000 },
+       { 0x4064ac,   1, 0x04, 0x00003fff },
+       { 0x4064b4,   2, 0x04, 0x00000000 },
+       { 0x4064c0,   1, 0x04, 0x801a00f0 },
+       { 0x4064c4,   1, 0x04, 0x0192ffff },
+       { 0x4064c8,   1, 0x04, 0x01800600 },
+       { 0x4064cc,   9, 0x04, 0x00000000 },
+       { 0x4064fc,   1, 0x04, 0x0000022a },
+       {}
+};
+
+static const struct gf100_gr_init
+gk104_grctx_init_sked_0[] = {
+       { 0x407040,   1, 0x04, 0x00000000 },
+       {}
+};
+
+const struct gf100_gr_init
+gk104_grctx_init_scc_0[] = {
+       { 0x408000,   2, 0x04, 0x00000000 },
+       { 0x408008,   1, 0x04, 0x00000030 },
+       { 0x40800c,   2, 0x04, 0x00000000 },
+       { 0x408014,   1, 0x04, 0x00000069 },
+       { 0x408018,   1, 0x04, 0xe100e100 },
+       { 0x408064,   1, 0x04, 0x00000000 },
+       {}
+};
+
+static const struct gf100_gr_init
+gk104_grctx_init_be_0[] = {
+       { 0x408800,   1, 0x04, 0x02802a3c },
+       { 0x408804,   1, 0x04, 0x00000040 },
+       { 0x408808,   1, 0x04, 0x1043e005 },
+       { 0x408840,   1, 0x04, 0x0000000b },
+       { 0x408900,   1, 0x04, 0x3080b801 },
+       { 0x408904,   1, 0x04, 0x62000001 },
+       { 0x408908,   1, 0x04, 0x00c8102f },
+       { 0x408980,   1, 0x04, 0x0000011d },
+       {}
+};
+
+const struct gf100_gr_pack
+gk104_grctx_pack_hub[] = {
+       { gf100_grctx_init_main_0 },
+       { gk104_grctx_init_fe_0 },
+       { gf100_grctx_init_pri_0 },
+       { gk104_grctx_init_memfmt_0 },
+       { gk104_grctx_init_ds_0 },
+       { gk104_grctx_init_cwd_0 },
+       { gk104_grctx_init_pd_0 },
+       { gk104_grctx_init_sked_0 },
+       { gf100_grctx_init_rstr2d_0 },
+       { gk104_grctx_init_scc_0 },
+       { gk104_grctx_init_be_0 },
+       {}
+};
+
+static const struct gf100_gr_init
+gk104_grctx_init_setup_0[] = {
+       { 0x418800,   1, 0x04, 0x7006860a },
+       { 0x418808,   3, 0x04, 0x00000000 },
+       { 0x418828,   1, 0x04, 0x00000044 },
+       { 0x418830,   1, 0x04, 0x10000001 },
+       { 0x4188d8,   1, 0x04, 0x00000008 },
+       { 0x4188e0,   1, 0x04, 0x01000000 },
+       { 0x4188e8,   5, 0x04, 0x00000000 },
+       { 0x4188fc,   1, 0x04, 0x20100018 },
+       {}
+};
+
+const struct gf100_gr_init
+gk104_grctx_init_gpm_0[] = {
+       { 0x418c08,   1, 0x04, 0x00000001 },
+       { 0x418c10,   8, 0x04, 0x00000000 },
+       { 0x418c40,   1, 0x04, 0xffffffff },
+       { 0x418c6c,   1, 0x04, 0x00000001 },
+       { 0x418c80,   1, 0x04, 0x20200004 },
+       { 0x418c8c,   1, 0x04, 0x00000001 },
+       {}
+};
+
+const struct gf100_gr_pack
+gk104_grctx_pack_gpc[] = {
+       { gf100_grctx_init_gpc_unk_0 },
+       { gf119_grctx_init_prop_0 },
+       { gf119_grctx_init_gpc_unk_1 },
+       { gk104_grctx_init_setup_0 },
+       { gf100_grctx_init_zcull_0 },
+       { gf119_grctx_init_crstr_0 },
+       { gk104_grctx_init_gpm_0 },
+       { gf100_grctx_init_gcc_0 },
+       {}
+};
+
+static const struct gf100_gr_init
+gk104_grctx_init_tex_0[] = {
+       { 0x419a00,   1, 0x04, 0x000000f0 },
+       { 0x419a04,   1, 0x04, 0x00000001 },
+       { 0x419a08,   1, 0x04, 0x00000021 },
+       { 0x419a0c,   1, 0x04, 0x00020000 },
+       { 0x419a10,   1, 0x04, 0x00000000 },
+       { 0x419a14,   1, 0x04, 0x00000200 },
+       { 0x419a1c,   1, 0x04, 0x0000c000 },
+       { 0x419a20,   1, 0x04, 0x00000800 },
+       { 0x419a30,   1, 0x04, 0x00000001 },
+       { 0x419ac4,   1, 0x04, 0x0037f440 },
+       {}
+};
+
+static const struct gf100_gr_init
+gk104_grctx_init_mpc_0[] = {
+       { 0x419c00,   1, 0x04, 0x0000000a },
+       { 0x419c04,   1, 0x04, 0x80000006 },
+       { 0x419c08,   1, 0x04, 0x00000002 },
+       { 0x419c20,   1, 0x04, 0x00000000 },
+       { 0x419c24,   1, 0x04, 0x00084210 },
+       { 0x419c28,   1, 0x04, 0x3efbefbe },
+       {}
+};
+
+static const struct gf100_gr_init
+gk104_grctx_init_l1c_0[] = {
+       { 0x419ce8,   1, 0x04, 0x00000000 },
+       { 0x419cf4,   1, 0x04, 0x00003203 },
+       {}
+};
+
+static const struct gf100_gr_init
+gk104_grctx_init_sm_0[] = {
+       { 0x419e04,   3, 0x04, 0x00000000 },
+       { 0x419e10,   1, 0x04, 0x00000402 },
+       { 0x419e44,   1, 0x04, 0x0013eff2 },
+       { 0x419e48,   1, 0x04, 0x00000000 },
+       { 0x419e4c,   1, 0x04, 0x0000007f },
+       { 0x419e50,  19, 0x04, 0x00000000 },
+       { 0x419eac,   1, 0x04, 0x00001f8f },
+       { 0x419eb0,   1, 0x04, 0x00000d3f },
+       { 0x419ec8,   1, 0x04, 0x0001304f },
+       { 0x419f30,   8, 0x04, 0x00000000 },
+       { 0x419f58,   1, 0x04, 0x00000000 },
+       { 0x419f70,   1, 0x04, 0x00000000 },
+       { 0x419f78,   1, 0x04, 0x0000000b },
+       { 0x419f7c,   1, 0x04, 0x0000027c },
+       {}
+};
+
+const struct gf100_gr_pack
+gk104_grctx_pack_tpc[] = {
+       { gf117_grctx_init_pe_0 },
+       { gk104_grctx_init_tex_0 },
+       { gk104_grctx_init_mpc_0 },
+       { gk104_grctx_init_l1c_0 },
+       { gk104_grctx_init_sm_0 },
+       {}
+};
+
+const struct gf100_gr_init
+gk104_grctx_init_pes_0[] = {
+       { 0x41be24,   1, 0x04, 0x00000006 },
+       {}
+};
+
+static const struct gf100_gr_init
+gk104_grctx_init_cbm_0[] = {
+       { 0x41bec0,   1, 0x04, 0x12180000 },
+       { 0x41bec4,   1, 0x04, 0x00037f7f },
+       { 0x41bee4,   1, 0x04, 0x06480430 },
+       {}
+};
+
+const struct gf100_gr_pack
+gk104_grctx_pack_ppc[] = {
+       { gk104_grctx_init_pes_0 },
+       { gk104_grctx_init_cbm_0 },
+       { gf117_grctx_init_wwdx_0 },
+       {}
+};
+
+/*******************************************************************************
+ * PGRAPH context implementation
+ ******************************************************************************/
+
+void
+gk104_grctx_generate_bundle(struct gf100_grctx *info)
+{
+       const struct gf100_grctx_oclass *impl = gf100_grctx_impl(info->priv);
+       const u32 state_limit = min(impl->bundle_min_gpm_fifo_depth,
+                                   impl->bundle_size / 0x20);
+       const u32 token_limit = impl->bundle_token_limit;
+       const u32 access = NV_MEM_ACCESS_RW | NV_MEM_ACCESS_SYS;
+       const int s = 8;
+       const int b = mmio_vram(info, impl->bundle_size, (1 << s), access);
+       mmio_refn(info, 0x408004, 0x00000000, s, b);
+       mmio_refn(info, 0x408008, 0x80000000 | (impl->bundle_size >> s), 0, b);
+       mmio_refn(info, 0x418808, 0x00000000, s, b);
+       mmio_refn(info, 0x41880c, 0x80000000 | (impl->bundle_size >> s), 0, b);
+       mmio_wr32(info, 0x4064c8, (state_limit << 16) | token_limit);
+}
+
+void
+gk104_grctx_generate_pagepool(struct gf100_grctx *info)
+{
+       const struct gf100_grctx_oclass *impl = gf100_grctx_impl(info->priv);
+       const u32 access = NV_MEM_ACCESS_RW | NV_MEM_ACCESS_SYS;
+       const int s = 8;
+       const int b = mmio_vram(info, impl->pagepool_size, (1 << s), access);
+       mmio_refn(info, 0x40800c, 0x00000000, s, b);
+       mmio_wr32(info, 0x408010, 0x80000000);
+       mmio_refn(info, 0x419004, 0x00000000, s, b);
+       mmio_wr32(info, 0x419008, 0x00000000);
+       mmio_wr32(info, 0x4064cc, 0x80000000);
+}
+
+void
+gk104_grctx_generate_unkn(struct gf100_gr_priv *priv)
+{
+       nv_mask(priv, 0x418c6c, 0x00000001, 0x00000001);
+       nv_mask(priv, 0x41980c, 0x00000010, 0x00000010);
+       nv_mask(priv, 0x41be08, 0x00000004, 0x00000004);
+       nv_mask(priv, 0x4064c0, 0x80000000, 0x80000000);
+       nv_mask(priv, 0x405800, 0x08000000, 0x08000000);
+       nv_mask(priv, 0x419c00, 0x00000008, 0x00000008);
+}
+
+void
+gk104_grctx_generate_r418bb8(struct gf100_gr_priv *priv)
+{
+       u32 data[6] = {}, data2[2] = {};
+       u8  tpcnr[GPC_MAX];
+       u8  shift, ntpcv;
+       int gpc, tpc, i;
+
+       /* calculate first set of magics */
+       memcpy(tpcnr, priv->tpc_nr, sizeof(priv->tpc_nr));
+
+       gpc = -1;
+       for (tpc = 0; tpc < priv->tpc_total; tpc++) {
+               do {
+                       gpc = (gpc + 1) % priv->gpc_nr;
+               } while (!tpcnr[gpc]);
+               tpcnr[gpc]--;
+
+               data[tpc / 6] |= gpc << ((tpc % 6) * 5);
+       }
+
+       for (; tpc < 32; tpc++)
+               data[tpc / 6] |= 7 << ((tpc % 6) * 5);
+
+       /* and the second... */
+       shift = 0;
+       ntpcv = priv->tpc_total;
+       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(priv, 0x418bb8, (priv->tpc_total << 8) |
+                                priv->magic_not_rop_nr);
+       for (i = 0; i < 6; i++)
+               nv_wr32(priv, 0x418b08 + (i * 4), data[i]);
+
+       /* GPC_BROADCAST.TP_BROADCAST */
+       nv_wr32(priv, 0x41bfd0, (priv->tpc_total << 8) |
+                                priv->magic_not_rop_nr | data2[0]);
+       nv_wr32(priv, 0x41bfe4, data2[1]);
+       for (i = 0; i < 6; i++)
+               nv_wr32(priv, 0x41bf00 + (i * 4), data[i]);
+
+       /* UNK78xx */
+       nv_wr32(priv, 0x4078bc, (priv->tpc_total << 8) |
+                                priv->magic_not_rop_nr);
+       for (i = 0; i < 6; i++)
+               nv_wr32(priv, 0x40780c + (i * 4), data[i]);
+}
+
+void
+gk104_grctx_generate_main(struct gf100_gr_priv *priv, struct gf100_grctx *info)
+{
+       struct gf100_grctx_oclass *oclass = (void *)nv_engine(priv)->cclass;
+       int i;
+
+       nvkm_mc(priv)->unk260(nvkm_mc(priv), 0);
+
+       gf100_gr_mmio(priv, oclass->hub);
+       gf100_gr_mmio(priv, oclass->gpc);
+       gf100_gr_mmio(priv, oclass->zcull);
+       gf100_gr_mmio(priv, oclass->tpc);
+       gf100_gr_mmio(priv, oclass->ppc);
+
+       nv_wr32(priv, 0x404154, 0x00000000);
+
+       oclass->bundle(info);
+       oclass->pagepool(info);
+       oclass->attrib(info);
+       oclass->unkn(priv);
+
+       gf100_grctx_generate_tpcid(priv);
+       gf100_grctx_generate_r406028(priv);
+       gk104_grctx_generate_r418bb8(priv);
+       gf100_grctx_generate_r406800(priv);
+
+       for (i = 0; i < 8; i++)
+               nv_wr32(priv, 0x4064d0 + (i * 0x04), 0x00000000);
+
+       nv_wr32(priv, 0x405b00, (priv->tpc_total << 8) | priv->gpc_nr);
+       if (priv->gpc_nr == 1) {
+               nv_mask(priv, 0x408850, 0x0000000f, priv->tpc_nr[0]);
+               nv_mask(priv, 0x408958, 0x0000000f, priv->tpc_nr[0]);
+       } else {
+               nv_mask(priv, 0x408850, 0x0000000f, priv->gpc_nr);
+               nv_mask(priv, 0x408958, 0x0000000f, priv->gpc_nr);
+       }
+       nv_mask(priv, 0x419f78, 0x00000001, 0x00000000);
+
+       gf100_gr_icmd(priv, oclass->icmd);
+       nv_wr32(priv, 0x404154, 0x00000400);
+       gf100_gr_mthd(priv, oclass->mthd);
+       nvkm_mc(priv)->unk260(nvkm_mc(priv), 1);
+
+       nv_mask(priv, 0x418800, 0x00200000, 0x00200000);
+       nv_mask(priv, 0x41be10, 0x00800000, 0x00800000);
+}
+
+struct nvkm_oclass *
+gk104_grctx_oclass = &(struct gf100_grctx_oclass) {
+       .base.handle = NV_ENGCTX(GR, 0xe4),
+       .base.ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = gf100_gr_context_ctor,
+               .dtor = gf100_gr_context_dtor,
+               .init = _nvkm_gr_context_init,
+               .fini = _nvkm_gr_context_fini,
+               .rd32 = _nvkm_gr_context_rd32,
+               .wr32 = _nvkm_gr_context_wr32,
+       },
+       .main  = gk104_grctx_generate_main,
+       .unkn  = gk104_grctx_generate_unkn,
+       .hub   = gk104_grctx_pack_hub,
+       .gpc   = gk104_grctx_pack_gpc,
+       .zcull = gf100_grctx_pack_zcull,
+       .tpc   = gk104_grctx_pack_tpc,
+       .ppc   = gk104_grctx_pack_ppc,
+       .icmd  = gk104_grctx_pack_icmd,
+       .mthd  = gk104_grctx_pack_mthd,
+       .bundle = gk104_grctx_generate_bundle,
+       .bundle_size = 0x3000,
+       .bundle_min_gpm_fifo_depth = 0x180,
+       .bundle_token_limit = 0x600,
+       .pagepool = gk104_grctx_generate_pagepool,
+       .pagepool_size = 0x8000,
+       .attrib = gf117_grctx_generate_attrib,
+       .attrib_nr_max = 0x324,
+       .attrib_nr = 0x218,
+       .alpha_nr_max = 0x7ff,
+       .alpha_nr = 0x648,
+}.base;
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/gr/ctxgk110.c b/drivers/gpu/drm/nouveau/nvkm/engine/gr/ctxgk110.c
new file mode 100644 (file)
index 0000000..b3f58be
--- /dev/null
@@ -0,0 +1,842 @@
+/*
+ * Copyright 2013 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 <bskeggs@redhat.com>
+ */
+#include "ctxgf100.h"
+
+/*******************************************************************************
+ * PGRAPH context register lists
+ ******************************************************************************/
+
+static const struct gf100_gr_init
+gk110_grctx_init_icmd_0[] = {
+       { 0x001000,   1, 0x01, 0x00000004 },
+       { 0x000039,   3, 0x01, 0x00000000 },
+       { 0x0000a9,   1, 0x01, 0x0000ffff },
+       { 0x000038,   1, 0x01, 0x0fac6881 },
+       { 0x00003d,   1, 0x01, 0x00000001 },
+       { 0x0000e8,   8, 0x01, 0x00000400 },
+       { 0x000078,   8, 0x01, 0x00000300 },
+       { 0x000050,   1, 0x01, 0x00000011 },
+       { 0x000058,   8, 0x01, 0x00000008 },
+       { 0x000208,   8, 0x01, 0x00000001 },
+       { 0x000081,   1, 0x01, 0x00000001 },
+       { 0x000085,   1, 0x01, 0x00000004 },
+       { 0x000088,   1, 0x01, 0x00000400 },
+       { 0x000090,   1, 0x01, 0x00000300 },
+       { 0x000098,   1, 0x01, 0x00001001 },
+       { 0x0000e3,   1, 0x01, 0x00000001 },
+       { 0x0000da,   1, 0x01, 0x00000001 },
+       { 0x0000f8,   1, 0x01, 0x00000003 },
+       { 0x0000fa,   1, 0x01, 0x00000001 },
+       { 0x00009f,   4, 0x01, 0x0000ffff },
+       { 0x0000b1,   1, 0x01, 0x00000001 },
+       { 0x0000ad,   1, 0x01, 0x0000013e },
+       { 0x0000e1,   1, 0x01, 0x00000010 },
+       { 0x000290,  16, 0x01, 0x00000000 },
+       { 0x0003b0,  16, 0x01, 0x00000000 },
+       { 0x0002a0,  16, 0x01, 0x00000000 },
+       { 0x000420,  16, 0x01, 0x00000000 },
+       { 0x0002b0,  16, 0x01, 0x00000000 },
+       { 0x000430,  16, 0x01, 0x00000000 },
+       { 0x0002c0,  16, 0x01, 0x00000000 },
+       { 0x0004d0,  16, 0x01, 0x00000000 },
+       { 0x000720,  16, 0x01, 0x00000000 },
+       { 0x0008c0,  16, 0x01, 0x00000000 },
+       { 0x000890,  16, 0x01, 0x00000000 },
+       { 0x0008e0,  16, 0x01, 0x00000000 },
+       { 0x0008a0,  16, 0x01, 0x00000000 },
+       { 0x0008f0,  16, 0x01, 0x00000000 },
+       { 0x00094c,   1, 0x01, 0x000000ff },
+       { 0x00094d,   1, 0x01, 0xffffffff },
+       { 0x00094e,   1, 0x01, 0x00000002 },
+       { 0x0002ec,   1, 0x01, 0x00000001 },
+       { 0x0002f2,   2, 0x01, 0x00000001 },
+       { 0x0002f5,   1, 0x01, 0x00000001 },
+       { 0x0002f7,   1, 0x01, 0x00000001 },
+       { 0x000303,   1, 0x01, 0x00000001 },
+       { 0x0002e6,   1, 0x01, 0x00000001 },
+       { 0x000466,   1, 0x01, 0x00000052 },
+       { 0x000301,   1, 0x01, 0x3f800000 },
+       { 0x000304,   1, 0x01, 0x30201000 },
+       { 0x000305,   1, 0x01, 0x70605040 },
+       { 0x000306,   1, 0x01, 0xb8a89888 },
+       { 0x000307,   1, 0x01, 0xf8e8d8c8 },
+       { 0x00030a,   1, 0x01, 0x00ffff00 },
+       { 0x00030b,   1, 0x01, 0x0000001a },
+       { 0x00030c,   1, 0x01, 0x00000001 },
+       { 0x000318,   1, 0x01, 0x00000001 },
+       { 0x000340,   1, 0x01, 0x00000000 },
+       { 0x000375,   1, 0x01, 0x00000001 },
+       { 0x00037d,   1, 0x01, 0x00000006 },
+       { 0x0003a0,   1, 0x01, 0x00000002 },
+       { 0x0003aa,   1, 0x01, 0x00000001 },
+       { 0x0003a9,   1, 0x01, 0x00000001 },
+       { 0x000380,   1, 0x01, 0x00000001 },
+       { 0x000383,   1, 0x01, 0x00000011 },
+       { 0x000360,   1, 0x01, 0x00000040 },
+       { 0x000366,   2, 0x01, 0x00000000 },
+       { 0x000368,   1, 0x01, 0x00000fff },
+       { 0x000370,   2, 0x01, 0x00000000 },
+       { 0x000372,   1, 0x01, 0x000fffff },
+       { 0x00037a,   1, 0x01, 0x00000012 },
+       { 0x000619,   1, 0x01, 0x00000003 },
+       { 0x000811,   1, 0x01, 0x00000003 },
+       { 0x000812,   1, 0x01, 0x00000004 },
+       { 0x000813,   1, 0x01, 0x00000006 },
+       { 0x000814,   1, 0x01, 0x00000008 },
+       { 0x000815,   1, 0x01, 0x0000000b },
+       { 0x000800,   6, 0x01, 0x00000001 },
+       { 0x000632,   1, 0x01, 0x00000001 },
+       { 0x000633,   1, 0x01, 0x00000002 },
+       { 0x000634,   1, 0x01, 0x00000003 },
+       { 0x000635,   1, 0x01, 0x00000004 },
+       { 0x000654,   1, 0x01, 0x3f800000 },
+       { 0x000657,   1, 0x01, 0x3f800000 },
+       { 0x000655,   2, 0x01, 0x3f800000 },
+       { 0x0006cd,   1, 0x01, 0x3f800000 },
+       { 0x0007f5,   1, 0x01, 0x3f800000 },
+       { 0x0007dc,   1, 0x01, 0x39291909 },
+       { 0x0007dd,   1, 0x01, 0x79695949 },
+       { 0x0007de,   1, 0x01, 0xb9a99989 },
+       { 0x0007df,   1, 0x01, 0xf9e9d9c9 },
+       { 0x0007e8,   1, 0x01, 0x00003210 },
+       { 0x0007e9,   1, 0x01, 0x00007654 },
+       { 0x0007ea,   1, 0x01, 0x00000098 },
+       { 0x0007ec,   1, 0x01, 0x39291909 },
+       { 0x0007ed,   1, 0x01, 0x79695949 },
+       { 0x0007ee,   1, 0x01, 0xb9a99989 },
+       { 0x0007ef,   1, 0x01, 0xf9e9d9c9 },
+       { 0x0007f0,   1, 0x01, 0x00003210 },
+       { 0x0007f1,   1, 0x01, 0x00007654 },
+       { 0x0007f2,   1, 0x01, 0x00000098 },
+       { 0x0005a5,   1, 0x01, 0x00000001 },
+       { 0x000980, 128, 0x01, 0x00000000 },
+       { 0x000468,   1, 0x01, 0x00000004 },
+       { 0x00046c,   1, 0x01, 0x00000001 },
+       { 0x000470,  96, 0x01, 0x00000000 },
+       { 0x000510,  16, 0x01, 0x3f800000 },
+       { 0x000520,   1, 0x01, 0x000002b6 },
+       { 0x000529,   1, 0x01, 0x00000001 },
+       { 0x000530,  16, 0x01, 0xffff0000 },
+       { 0x000585,   1, 0x01, 0x0000003f },
+       { 0x000576,   1, 0x01, 0x00000003 },
+       { 0x00057b,   1, 0x01, 0x00000059 },
+       { 0x000586,   1, 0x01, 0x00000040 },
+       { 0x000582,   2, 0x01, 0x00000080 },
+       { 0x0005c2,   1, 0x01, 0x00000001 },
+       { 0x000638,   2, 0x01, 0x00000001 },
+       { 0x00063a,   1, 0x01, 0x00000002 },
+       { 0x00063b,   2, 0x01, 0x00000001 },
+       { 0x00063d,   1, 0x01, 0x00000002 },
+       { 0x00063e,   1, 0x01, 0x00000001 },
+       { 0x0008b8,   8, 0x01, 0x00000001 },
+       { 0x000900,   8, 0x01, 0x00000001 },
+       { 0x000908,   8, 0x01, 0x00000002 },
+       { 0x000910,  16, 0x01, 0x00000001 },
+       { 0x000920,   8, 0x01, 0x00000002 },
+       { 0x000928,   8, 0x01, 0x00000001 },
+       { 0x000662,   1, 0x01, 0x00000001 },
+       { 0x000648,   9, 0x01, 0x00000001 },
+       { 0x000658,   1, 0x01, 0x0000000f },
+       { 0x0007ff,   1, 0x01, 0x0000000a },
+       { 0x00066a,   1, 0x01, 0x40000000 },
+       { 0x00066b,   1, 0x01, 0x10000000 },
+       { 0x00066c,   2, 0x01, 0xffff0000 },
+       { 0x0007af,   2, 0x01, 0x00000008 },
+       { 0x0007f6,   1, 0x01, 0x00000001 },
+       { 0x00080b,   1, 0x01, 0x00000002 },
+       { 0x0006b2,   1, 0x01, 0x00000055 },
+       { 0x0007ad,   1, 0x01, 0x00000003 },
+       { 0x000937,   1, 0x01, 0x00000001 },
+       { 0x000971,   1, 0x01, 0x00000008 },
+       { 0x000972,   1, 0x01, 0x00000040 },
+       { 0x000973,   1, 0x01, 0x0000012c },
+       { 0x00097c,   1, 0x01, 0x00000040 },
+       { 0x000979,   1, 0x01, 0x00000003 },
+       { 0x000975,   1, 0x01, 0x00000020 },
+       { 0x000976,   1, 0x01, 0x00000001 },
+       { 0x000977,   1, 0x01, 0x00000020 },
+       { 0x000978,   1, 0x01, 0x00000001 },
+       { 0x000957,   1, 0x01, 0x00000003 },
+       { 0x00095e,   1, 0x01, 0x20164010 },
+       { 0x00095f,   1, 0x01, 0x00000020 },
+       { 0x000a0d,   1, 0x01, 0x00000006 },
+       { 0x00097d,   1, 0x01, 0x00000020 },
+       { 0x000683,   1, 0x01, 0x00000006 },
+       { 0x000685,   1, 0x01, 0x003fffff },
+       { 0x000687,   1, 0x01, 0x003fffff },
+       { 0x0006a0,   1, 0x01, 0x00000005 },
+       { 0x000840,   1, 0x01, 0x00400008 },
+       { 0x000841,   1, 0x01, 0x08000080 },
+       { 0x000842,   1, 0x01, 0x00400008 },
+       { 0x000843,   1, 0x01, 0x08000080 },
+       { 0x0006aa,   1, 0x01, 0x00000001 },
+       { 0x0006ab,   1, 0x01, 0x00000002 },
+       { 0x0006ac,   1, 0x01, 0x00000080 },
+       { 0x0006ad,   2, 0x01, 0x00000100 },
+       { 0x0006b1,   1, 0x01, 0x00000011 },
+       { 0x0006bb,   1, 0x01, 0x000000cf },
+       { 0x0006ce,   1, 0x01, 0x2a712488 },
+       { 0x000739,   1, 0x01, 0x4085c000 },
+       { 0x00073a,   1, 0x01, 0x00000080 },
+       { 0x000786,   1, 0x01, 0x80000100 },
+       { 0x00073c,   1, 0x01, 0x00010100 },
+       { 0x00073d,   1, 0x01, 0x02800000 },
+       { 0x000787,   1, 0x01, 0x000000cf },
+       { 0x00078c,   1, 0x01, 0x00000008 },
+       { 0x000792,   1, 0x01, 0x00000001 },
+       { 0x000794,   3, 0x01, 0x00000001 },
+       { 0x000797,   1, 0x01, 0x000000cf },
+       { 0x000836,   1, 0x01, 0x00000001 },
+       { 0x00079a,   1, 0x01, 0x00000002 },
+       { 0x000833,   1, 0x01, 0x04444480 },
+       { 0x0007a1,   1, 0x01, 0x00000001 },
+       { 0x0007a3,   3, 0x01, 0x00000001 },
+       { 0x000831,   1, 0x01, 0x00000004 },
+       { 0x000b07,   1, 0x01, 0x00000002 },
+       { 0x000b08,   2, 0x01, 0x00000100 },
+       { 0x000b0a,   1, 0x01, 0x00000001 },
+       { 0x000a04,   1, 0x01, 0x000000ff },
+       { 0x000a0b,   1, 0x01, 0x00000040 },
+       { 0x00097f,   1, 0x01, 0x00000100 },
+       { 0x000a02,   1, 0x01, 0x00000001 },
+       { 0x000809,   1, 0x01, 0x00000007 },
+       { 0x00c221,   1, 0x01, 0x00000040 },
+       { 0x00c1b0,   8, 0x01, 0x0000000f },
+       { 0x00c1b8,   1, 0x01, 0x0fac6881 },
+       { 0x00c1b9,   1, 0x01, 0x00fac688 },
+       { 0x00c401,   1, 0x01, 0x00000001 },
+       { 0x00c402,   1, 0x01, 0x00010001 },
+       { 0x00c403,   2, 0x01, 0x00000001 },
+       { 0x00c40e,   1, 0x01, 0x00000020 },
+       { 0x00c500,   1, 0x01, 0x00000003 },
+       { 0x01e100,   1, 0x01, 0x00000001 },
+       { 0x001000,   1, 0x01, 0x00000002 },
+       { 0x0006aa,   1, 0x01, 0x00000001 },
+       { 0x0006ad,   2, 0x01, 0x00000100 },
+       { 0x0006b1,   1, 0x01, 0x00000011 },
+       { 0x00078c,   1, 0x01, 0x00000008 },
+       { 0x000792,   1, 0x01, 0x00000001 },
+       { 0x000794,   3, 0x01, 0x00000001 },
+       { 0x000797,   1, 0x01, 0x000000cf },
+       { 0x00079a,   1, 0x01, 0x00000002 },
+       { 0x000833,   1, 0x01, 0x04444480 },
+       { 0x0007a1,   1, 0x01, 0x00000001 },
+       { 0x0007a3,   3, 0x01, 0x00000001 },
+       { 0x000831,   1, 0x01, 0x00000004 },
+       { 0x01e100,   1, 0x01, 0x00000001 },
+       { 0x001000,   1, 0x01, 0x00000008 },
+       { 0x000039,   3, 0x01, 0x00000000 },
+       { 0x000380,   1, 0x01, 0x00000001 },
+       { 0x000366,   2, 0x01, 0x00000000 },
+       { 0x000368,   1, 0x01, 0x00000fff },
+       { 0x000370,   2, 0x01, 0x00000000 },
+       { 0x000372,   1, 0x01, 0x000fffff },
+       { 0x000813,   1, 0x01, 0x00000006 },
+       { 0x000814,   1, 0x01, 0x00000008 },
+       { 0x000957,   1, 0x01, 0x00000003 },
+       { 0x000b07,   1, 0x01, 0x00000002 },
+       { 0x000b08,   2, 0x01, 0x00000100 },
+       { 0x000b0a,   1, 0x01, 0x00000001 },
+       { 0x000a04,   1, 0x01, 0x000000ff },
+       { 0x000a0b,   1, 0x01, 0x00000040 },
+       { 0x00097f,   1, 0x01, 0x00000100 },
+       { 0x000a02,   1, 0x01, 0x00000001 },
+       { 0x000809,   1, 0x01, 0x00000007 },
+       { 0x00c221,   1, 0x01, 0x00000040 },
+       { 0x00c401,   1, 0x01, 0x00000001 },
+       { 0x00c402,   1, 0x01, 0x00010001 },
+       { 0x00c403,   2, 0x01, 0x00000001 },
+       { 0x00c40e,   1, 0x01, 0x00000020 },
+       { 0x00c500,   1, 0x01, 0x00000003 },
+       { 0x01e100,   1, 0x01, 0x00000001 },
+       { 0x001000,   1, 0x01, 0x00000001 },
+       { 0x000b07,   1, 0x01, 0x00000002 },
+       { 0x000b08,   2, 0x01, 0x00000100 },
+       { 0x000b0a,   1, 0x01, 0x00000001 },
+       { 0x01e100,   1, 0x01, 0x00000001 },
+       {}
+};
+
+const struct gf100_gr_pack
+gk110_grctx_pack_icmd[] = {
+       { gk110_grctx_init_icmd_0 },
+       {}
+};
+
+static const struct gf100_gr_init
+gk110_grctx_init_a197_0[] = {
+       { 0x000800,   8, 0x40, 0x00000000 },
+       { 0x000804,   8, 0x40, 0x00000000 },
+       { 0x000808,   8, 0x40, 0x00000400 },
+       { 0x00080c,   8, 0x40, 0x00000300 },
+       { 0x000810,   1, 0x04, 0x000000cf },
+       { 0x000850,   7, 0x40, 0x00000000 },
+       { 0x000814,   8, 0x40, 0x00000040 },
+       { 0x000818,   8, 0x40, 0x00000001 },
+       { 0x00081c,   8, 0x40, 0x00000000 },
+       { 0x000820,   8, 0x40, 0x00000000 },
+       { 0x001c00,  16, 0x10, 0x00000000 },
+       { 0x001c04,  16, 0x10, 0x00000000 },
+       { 0x001c08,  16, 0x10, 0x00000000 },
+       { 0x001c0c,  16, 0x10, 0x00000000 },
+       { 0x001d00,  16, 0x10, 0x00000000 },
+       { 0x001d04,  16, 0x10, 0x00000000 },
+       { 0x001d08,  16, 0x10, 0x00000000 },
+       { 0x001d0c,  16, 0x10, 0x00000000 },
+       { 0x001f00,  16, 0x08, 0x00000000 },
+       { 0x001f04,  16, 0x08, 0x00000000 },
+       { 0x001f80,  16, 0x08, 0x00000000 },
+       { 0x001f84,  16, 0x08, 0x00000000 },
+       { 0x002000,   1, 0x04, 0x00000000 },
+       { 0x002040,   1, 0x04, 0x00000011 },
+       { 0x002080,   1, 0x04, 0x00000020 },
+       { 0x0020c0,   1, 0x04, 0x00000030 },
+       { 0x002100,   1, 0x04, 0x00000040 },
+       { 0x002140,   1, 0x04, 0x00000051 },
+       { 0x00200c,   6, 0x40, 0x00000001 },
+       { 0x002010,   1, 0x04, 0x00000000 },
+       { 0x002050,   1, 0x04, 0x00000000 },
+       { 0x002090,   1, 0x04, 0x00000001 },
+       { 0x0020d0,   1, 0x04, 0x00000002 },
+       { 0x002110,   1, 0x04, 0x00000003 },
+       { 0x002150,   1, 0x04, 0x00000004 },
+       { 0x000380,   4, 0x20, 0x00000000 },
+       { 0x000384,   4, 0x20, 0x00000000 },
+       { 0x000388,   4, 0x20, 0x00000000 },
+       { 0x00038c,   4, 0x20, 0x00000000 },
+       { 0x000700,   4, 0x10, 0x00000000 },
+       { 0x000704,   4, 0x10, 0x00000000 },
+       { 0x000708,   4, 0x10, 0x00000000 },
+       { 0x002800, 128, 0x04, 0x00000000 },
+       { 0x000a00,  16, 0x20, 0x00000000 },
+       { 0x000a04,  16, 0x20, 0x00000000 },
+       { 0x000a08,  16, 0x20, 0x00000000 },
+       { 0x000a0c,  16, 0x20, 0x00000000 },
+       { 0x000a10,  16, 0x20, 0x00000000 },
+       { 0x000a14,  16, 0x20, 0x00000000 },
+       { 0x000c00,  16, 0x10, 0x00000000 },
+       { 0x000c04,  16, 0x10, 0x00000000 },
+       { 0x000c08,  16, 0x10, 0x00000000 },
+       { 0x000c0c,  16, 0x10, 0x3f800000 },
+       { 0x000d00,   8, 0x08, 0xffff0000 },
+       { 0x000d04,   8, 0x08, 0xffff0000 },
+       { 0x000e00,  16, 0x10, 0x00000000 },
+       { 0x000e04,  16, 0x10, 0xffff0000 },
+       { 0x000e08,  16, 0x10, 0xffff0000 },
+       { 0x000d40,   4, 0x08, 0x00000000 },
+       { 0x000d44,   4, 0x08, 0x00000000 },
+       { 0x001e00,   8, 0x20, 0x00000001 },
+       { 0x001e04,   8, 0x20, 0x00000001 },
+       { 0x001e08,   8, 0x20, 0x00000002 },
+       { 0x001e0c,   8, 0x20, 0x00000001 },
+       { 0x001e10,   8, 0x20, 0x00000001 },
+       { 0x001e14,   8, 0x20, 0x00000002 },
+       { 0x001e18,   8, 0x20, 0x00000001 },
+       { 0x003400, 128, 0x04, 0x00000000 },
+       { 0x00030c,   1, 0x04, 0x00000001 },
+       { 0x001944,   1, 0x04, 0x00000000 },
+       { 0x001514,   1, 0x04, 0x00000000 },
+       { 0x000d68,   1, 0x04, 0x0000ffff },
+       { 0x00121c,   1, 0x04, 0x0fac6881 },
+       { 0x000fac,   1, 0x04, 0x00000001 },
+       { 0x001538,   1, 0x04, 0x00000001 },
+       { 0x000fe0,   2, 0x04, 0x00000000 },
+       { 0x000fe8,   1, 0x04, 0x00000014 },
+       { 0x000fec,   1, 0x04, 0x00000040 },
+       { 0x000ff0,   1, 0x04, 0x00000000 },
+       { 0x00179c,   1, 0x04, 0x00000000 },
+       { 0x001228,   1, 0x04, 0x00000400 },
+       { 0x00122c,   1, 0x04, 0x00000300 },
+       { 0x001230,   1, 0x04, 0x00010001 },
+       { 0x0007f8,   1, 0x04, 0x00000000 },
+       { 0x0015b4,   1, 0x04, 0x00000001 },
+       { 0x0015cc,   1, 0x04, 0x00000000 },
+       { 0x001534,   1, 0x04, 0x00000000 },
+       { 0x000fb0,   1, 0x04, 0x00000000 },
+       { 0x0015d0,   1, 0x04, 0x00000000 },
+       { 0x00153c,   1, 0x04, 0x00000000 },
+       { 0x0016b4,   1, 0x04, 0x00000003 },
+       { 0x000fbc,   4, 0x04, 0x0000ffff },
+       { 0x000df8,   2, 0x04, 0x00000000 },
+       { 0x001948,   1, 0x04, 0x00000000 },
+       { 0x001970,   1, 0x04, 0x00000001 },
+       { 0x00161c,   1, 0x04, 0x000009f0 },
+       { 0x000dcc,   1, 0x04, 0x00000010 },
+       { 0x00163c,   1, 0x04, 0x00000000 },
+       { 0x0015e4,   1, 0x04, 0x00000000 },
+       { 0x001160,  32, 0x04, 0x25e00040 },
+       { 0x001880,  32, 0x04, 0x00000000 },
+       { 0x000f84,   2, 0x04, 0x00000000 },
+       { 0x0017c8,   2, 0x04, 0x00000000 },
+       { 0x0017d0,   1, 0x04, 0x000000ff },
+       { 0x0017d4,   1, 0x04, 0xffffffff },
+       { 0x0017d8,   1, 0x04, 0x00000002 },
+       { 0x0017dc,   1, 0x04, 0x00000000 },
+       { 0x0015f4,   2, 0x04, 0x00000000 },
+       { 0x001434,   2, 0x04, 0x00000000 },
+       { 0x000d74,   1, 0x04, 0x00000000 },
+       { 0x000dec,   1, 0x04, 0x00000001 },
+       { 0x0013a4,   1, 0x04, 0x00000000 },
+       { 0x001318,   1, 0x04, 0x00000001 },
+       { 0x001644,   1, 0x04, 0x00000000 },
+       { 0x000748,   1, 0x04, 0x00000000 },
+       { 0x000de8,   1, 0x04, 0x00000000 },
+       { 0x001648,   1, 0x04, 0x00000000 },
+       { 0x0012a4,   1, 0x04, 0x00000000 },
+       { 0x001120,   4, 0x04, 0x00000000 },
+       { 0x001118,   1, 0x04, 0x00000000 },
+       { 0x00164c,   1, 0x04, 0x00000000 },
+       { 0x001658,   1, 0x04, 0x00000000 },
+       { 0x001910,   1, 0x04, 0x00000290 },
+       { 0x001518,   1, 0x04, 0x00000000 },
+       { 0x00165c,   1, 0x04, 0x00000001 },
+       { 0x001520,   1, 0x04, 0x00000000 },
+       { 0x001604,   1, 0x04, 0x00000000 },
+       { 0x001570,   1, 0x04, 0x00000000 },
+       { 0x0013b0,   2, 0x04, 0x3f800000 },
+       { 0x00020c,   1, 0x04, 0x00000000 },
+       { 0x001670,   1, 0x04, 0x30201000 },
+       { 0x001674,   1, 0x04, 0x70605040 },
+       { 0x001678,   1, 0x04, 0xb8a89888 },
+       { 0x00167c,   1, 0x04, 0xf8e8d8c8 },
+       { 0x00166c,   1, 0x04, 0x00000000 },
+       { 0x001680,   1, 0x04, 0x00ffff00 },
+       { 0x0012d0,   1, 0x04, 0x00000003 },
+       { 0x0012d4,   1, 0x04, 0x00000002 },
+       { 0x001684,   2, 0x04, 0x00000000 },
+       { 0x000dac,   2, 0x04, 0x00001b02 },
+       { 0x000db4,   1, 0x04, 0x00000000 },
+       { 0x00168c,   1, 0x04, 0x00000000 },
+       { 0x0015bc,   1, 0x04, 0x00000000 },
+       { 0x00156c,   1, 0x04, 0x00000000 },
+       { 0x00187c,   1, 0x04, 0x00000000 },
+       { 0x001110,   1, 0x04, 0x00000001 },
+       { 0x000dc0,   3, 0x04, 0x00000000 },
+       { 0x001234,   1, 0x04, 0x00000000 },
+       { 0x001690,   1, 0x04, 0x00000000 },
+       { 0x0012ac,   1, 0x04, 0x00000001 },
+       { 0x0002c4,   1, 0x04, 0x00000000 },
+       { 0x000790,   5, 0x04, 0x00000000 },
+       { 0x00077c,   1, 0x04, 0x00000000 },
+       { 0x001000,   1, 0x04, 0x00000010 },
+       { 0x0010fc,   1, 0x04, 0x00000000 },
+       { 0x001290,   1, 0x04, 0x00000000 },
+       { 0x000218,   1, 0x04, 0x00000010 },
+       { 0x0012d8,   1, 0x04, 0x00000000 },
+       { 0x0012dc,   1, 0x04, 0x00000010 },
+       { 0x000d94,   1, 0x04, 0x00000001 },
+       { 0x00155c,   2, 0x04, 0x00000000 },
+       { 0x001564,   1, 0x04, 0x00000fff },
+       { 0x001574,   2, 0x04, 0x00000000 },
+       { 0x00157c,   1, 0x04, 0x000fffff },
+       { 0x001354,   1, 0x04, 0x00000000 },
+       { 0x001610,   1, 0x04, 0x00000012 },
+       { 0x001608,   2, 0x04, 0x00000000 },
+       { 0x00260c,   1, 0x04, 0x00000000 },
+       { 0x0007ac,   1, 0x04, 0x00000000 },
+       { 0x00162c,   1, 0x04, 0x00000003 },
+       { 0x000210,   1, 0x04, 0x00000000 },
+       { 0x000320,   1, 0x04, 0x00000000 },
+       { 0x000324,   6, 0x04, 0x3f800000 },
+       { 0x000750,   1, 0x04, 0x00000000 },
+       { 0x000760,   1, 0x04, 0x39291909 },
+       { 0x000764,   1, 0x04, 0x79695949 },
+       { 0x000768,   1, 0x04, 0xb9a99989 },
+       { 0x00076c,   1, 0x04, 0xf9e9d9c9 },
+       { 0x000770,   1, 0x04, 0x30201000 },
+       { 0x000774,   1, 0x04, 0x70605040 },
+       { 0x000778,   1, 0x04, 0x00009080 },
+       { 0x000780,   1, 0x04, 0x39291909 },
+       { 0x000784,   1, 0x04, 0x79695949 },
+       { 0x000788,   1, 0x04, 0xb9a99989 },
+       { 0x00078c,   1, 0x04, 0xf9e9d9c9 },
+       { 0x0007d0,   1, 0x04, 0x30201000 },
+       { 0x0007d4,   1, 0x04, 0x70605040 },
+       { 0x0007d8,   1, 0x04, 0x00009080 },
+       { 0x00037c,   1, 0x04, 0x00000001 },
+       { 0x000740,   2, 0x04, 0x00000000 },
+       { 0x002600,   1, 0x04, 0x00000000 },
+       { 0x001918,   1, 0x04, 0x00000000 },
+       { 0x00191c,   1, 0x04, 0x00000900 },
+       { 0x001920,   1, 0x04, 0x00000405 },
+       { 0x001308,   1, 0x04, 0x00000001 },
+       { 0x001924,   1, 0x04, 0x00000000 },
+       { 0x0013ac,   1, 0x04, 0x00000000 },
+       { 0x00192c,   1, 0x04, 0x00000001 },
+       { 0x00193c,   1, 0x04, 0x00002c1c },
+       { 0x000d7c,   1, 0x04, 0x00000000 },
+       { 0x000f8c,   1, 0x04, 0x00000000 },
+       { 0x0002c0,   1, 0x04, 0x00000001 },
+       { 0x001510,   1, 0x04, 0x00000000 },
+       { 0x001940,   1, 0x04, 0x00000000 },
+       { 0x000ff4,   2, 0x04, 0x00000000 },
+       { 0x00194c,   2, 0x04, 0x00000000 },
+       { 0x001968,   1, 0x04, 0x00000000 },
+       { 0x001590,   1, 0x04, 0x0000003f },
+       { 0x0007e8,   4, 0x04, 0x00000000 },
+       { 0x00196c,   1, 0x04, 0x00000011 },
+       { 0x0002e4,   1, 0x04, 0x0000b001 },
+       { 0x00036c,   2, 0x04, 0x00000000 },
+       { 0x00197c,   1, 0x04, 0x00000000 },
+       { 0x000fcc,   2, 0x04, 0x00000000 },
+       { 0x0002d8,   1, 0x04, 0x00000040 },
+       { 0x001980,   1, 0x04, 0x00000080 },
+       { 0x001504,   1, 0x04, 0x00000080 },
+       { 0x001984,   1, 0x04, 0x00000000 },
+       { 0x000300,   1, 0x04, 0x00000001 },
+       { 0x0013a8,   1, 0x04, 0x00000000 },
+       { 0x0012ec,   1, 0x04, 0x00000000 },
+       { 0x001310,   1, 0x04, 0x00000000 },
+       { 0x001314,   1, 0x04, 0x00000001 },
+       { 0x001380,   1, 0x04, 0x00000000 },
+       { 0x001384,   4, 0x04, 0x00000001 },
+       { 0x001394,   1, 0x04, 0x00000000 },
+       { 0x00139c,   1, 0x04, 0x00000000 },
+       { 0x001398,   1, 0x04, 0x00000000 },
+       { 0x001594,   1, 0x04, 0x00000000 },
+       { 0x001598,   4, 0x04, 0x00000001 },
+       { 0x000f54,   3, 0x04, 0x00000000 },
+       { 0x0019bc,   1, 0x04, 0x00000000 },
+       { 0x000f9c,   2, 0x04, 0x00000000 },
+       { 0x0012cc,   1, 0x04, 0x00000000 },
+       { 0x0012e8,   1, 0x04, 0x00000000 },
+       { 0x00130c,   1, 0x04, 0x00000001 },
+       { 0x001360,   8, 0x04, 0x00000000 },
+       { 0x00133c,   2, 0x04, 0x00000001 },
+       { 0x001344,   1, 0x04, 0x00000002 },
+       { 0x001348,   2, 0x04, 0x00000001 },
+       { 0x001350,   1, 0x04, 0x00000002 },
+       { 0x001358,   1, 0x04, 0x00000001 },
+       { 0x0012e4,   1, 0x04, 0x00000000 },
+       { 0x00131c,   4, 0x04, 0x00000000 },
+       { 0x0019c0,   1, 0x04, 0x00000000 },
+       { 0x001140,   1, 0x04, 0x00000000 },
+       { 0x0019c4,   1, 0x04, 0x00000000 },
+       { 0x0019c8,   1, 0x04, 0x00001500 },
+       { 0x00135c,   1, 0x04, 0x00000000 },
+       { 0x000f90,   1, 0x04, 0x00000000 },
+       { 0x0019e0,   8, 0x04, 0x00000001 },
+       { 0x0019cc,   1, 0x04, 0x00000001 },
+       { 0x0015b8,   1, 0x04, 0x00000000 },
+       { 0x001a00,   1, 0x04, 0x00001111 },
+       { 0x001a04,   7, 0x04, 0x00000000 },
+       { 0x000d6c,   2, 0x04, 0xffff0000 },
+       { 0x0010f8,   1, 0x04, 0x00001010 },
+       { 0x000d80,   5, 0x04, 0x00000000 },
+       { 0x000da0,   1, 0x04, 0x00000000 },
+       { 0x0007a4,   2, 0x04, 0x00000000 },
+       { 0x001508,   1, 0x04, 0x80000000 },
+       { 0x00150c,   1, 0x04, 0x40000000 },
+       { 0x001668,   1, 0x04, 0x00000000 },
+       { 0x000318,   2, 0x04, 0x00000008 },
+       { 0x000d9c,   1, 0x04, 0x00000001 },
+       { 0x000ddc,   1, 0x04, 0x00000002 },
+       { 0x000374,   1, 0x04, 0x00000000 },
+       { 0x000378,   1, 0x04, 0x00000020 },
+       { 0x0007dc,   1, 0x04, 0x00000000 },
+       { 0x00074c,   1, 0x04, 0x00000055 },
+       { 0x001420,   1, 0x04, 0x00000003 },
+       { 0x0017bc,   2, 0x04, 0x00000000 },
+       { 0x0017c4,   1, 0x04, 0x00000001 },
+       { 0x001008,   1, 0x04, 0x00000008 },
+       { 0x00100c,   1, 0x04, 0x00000040 },
+       { 0x001010,   1, 0x04, 0x0000012c },
+       { 0x000d60,   1, 0x04, 0x00000040 },
+       { 0x00075c,   1, 0x04, 0x00000003 },
+       { 0x001018,   1, 0x04, 0x00000020 },
+       { 0x00101c,   1, 0x04, 0x00000001 },
+       { 0x001020,   1, 0x04, 0x00000020 },
+       { 0x001024,   1, 0x04, 0x00000001 },
+       { 0x001444,   3, 0x04, 0x00000000 },
+       { 0x000360,   1, 0x04, 0x20164010 },
+       { 0x000364,   1, 0x04, 0x00000020 },
+       { 0x000368,   1, 0x04, 0x00000000 },
+       { 0x000de4,   1, 0x04, 0x00000000 },
+       { 0x000204,   1, 0x04, 0x00000006 },
+       { 0x000208,   1, 0x04, 0x00000000 },
+       { 0x0002cc,   2, 0x04, 0x003fffff },
+       { 0x001220,   1, 0x04, 0x00000005 },
+       { 0x000fdc,   1, 0x04, 0x00000000 },
+       { 0x000f98,   1, 0x04, 0x00400008 },
+       { 0x001284,   1, 0x04, 0x08000080 },
+       { 0x001450,   1, 0x04, 0x00400008 },
+       { 0x001454,   1, 0x04, 0x08000080 },
+       { 0x000214,   1, 0x04, 0x00000000 },
+       {}
+};
+
+const struct gf100_gr_pack
+gk110_grctx_pack_mthd[] = {
+       { gk110_grctx_init_a197_0, 0xa197 },
+       { gf100_grctx_init_902d_0, 0x902d },
+       {}
+};
+
+static const struct gf100_gr_init
+gk110_grctx_init_fe_0[] = {
+       { 0x404004,   8, 0x04, 0x00000000 },
+       { 0x404024,   1, 0x04, 0x0000e000 },
+       { 0x404028,   8, 0x04, 0x00000000 },
+       { 0x4040a8,   8, 0x04, 0x00000000 },
+       { 0x4040c8,   1, 0x04, 0xf800008f },
+       { 0x4040d0,   6, 0x04, 0x00000000 },
+       { 0x4040e8,   1, 0x04, 0x00001000 },
+       { 0x4040f8,   1, 0x04, 0x00000000 },
+       { 0x404100,  10, 0x04, 0x00000000 },
+       { 0x404130,   2, 0x04, 0x00000000 },
+       { 0x404138,   1, 0x04, 0x20000040 },
+       { 0x404150,   1, 0x04, 0x0000002e },
+       { 0x404154,   1, 0x04, 0x00000400 },
+       { 0x404158,   1, 0x04, 0x00000200 },
+       { 0x404164,   1, 0x04, 0x00000055 },
+       { 0x40417c,   2, 0x04, 0x00000000 },
+       { 0x4041a0,   4, 0x04, 0x00000000 },
+       { 0x404200,   1, 0x04, 0x0000a197 },
+       { 0x404204,   1, 0x04, 0x0000a1c0 },
+       { 0x404208,   1, 0x04, 0x0000a140 },
+       { 0x40420c,   1, 0x04, 0x0000902d },
+       {}
+};
+
+const struct gf100_gr_init
+gk110_grctx_init_pri_0[] = {
+       { 0x404404,  12, 0x04, 0x00000000 },
+       { 0x404438,   1, 0x04, 0x00000000 },
+       { 0x404460,   2, 0x04, 0x00000000 },
+       { 0x404468,   1, 0x04, 0x00ffffff },
+       { 0x40446c,   1, 0x04, 0x00000000 },
+       { 0x404480,   1, 0x04, 0x00000001 },
+       { 0x404498,   1, 0x04, 0x00000001 },
+       {}
+};
+
+const struct gf100_gr_init
+gk110_grctx_init_cwd_0[] = {
+       { 0x405b00,   1, 0x04, 0x00000000 },
+       { 0x405b10,   1, 0x04, 0x00001000 },
+       { 0x405b20,   1, 0x04, 0x04000000 },
+       {}
+};
+
+static const struct gf100_gr_init
+gk110_grctx_init_pd_0[] = {
+       { 0x406020,   1, 0x04, 0x034103c1 },
+       { 0x406028,   4, 0x04, 0x00000001 },
+       { 0x4064a8,   1, 0x04, 0x00000000 },
+       { 0x4064ac,   1, 0x04, 0x00003fff },
+       { 0x4064b0,   3, 0x04, 0x00000000 },
+       { 0x4064c0,   1, 0x04, 0x802000f0 },
+       { 0x4064c4,   1, 0x04, 0x0192ffff },
+       { 0x4064c8,   1, 0x04, 0x018007c0 },
+       { 0x4064cc,   9, 0x04, 0x00000000 },
+       { 0x4064fc,   1, 0x04, 0x0000022a },
+       {}
+};
+
+static const struct gf100_gr_init
+gk110_grctx_init_be_0[] = {
+       { 0x408800,   1, 0x04, 0x12802a3c },
+       { 0x408804,   1, 0x04, 0x00000040 },
+       { 0x408808,   1, 0x04, 0x1003e005 },
+       { 0x408840,   1, 0x04, 0x0000000b },
+       { 0x408900,   1, 0x04, 0x3080b801 },
+       { 0x408904,   1, 0x04, 0x62000001 },
+       { 0x408908,   1, 0x04, 0x00c8102f },
+       { 0x408980,   1, 0x04, 0x0000011d },
+       {}
+};
+
+const struct gf100_gr_pack
+gk110_grctx_pack_hub[] = {
+       { gf100_grctx_init_main_0 },
+       { gk110_grctx_init_fe_0 },
+       { gk110_grctx_init_pri_0 },
+       { gk104_grctx_init_memfmt_0 },
+       { gk104_grctx_init_ds_0 },
+       { gk110_grctx_init_cwd_0 },
+       { gk110_grctx_init_pd_0 },
+       { gf100_grctx_init_rstr2d_0 },
+       { gk104_grctx_init_scc_0 },
+       { gk110_grctx_init_be_0 },
+       {}
+};
+
+static const struct gf100_gr_init
+gk110_grctx_init_setup_0[] = {
+       { 0x418800,   1, 0x04, 0x7006860a },
+       { 0x418808,   1, 0x04, 0x00000000 },
+       { 0x41880c,   1, 0x04, 0x00000030 },
+       { 0x418810,   1, 0x04, 0x00000000 },
+       { 0x418828,   1, 0x04, 0x00000044 },
+       { 0x418830,   1, 0x04, 0x10000001 },
+       { 0x4188d8,   1, 0x04, 0x00000008 },
+       { 0x4188e0,   1, 0x04, 0x01000000 },
+       { 0x4188e8,   5, 0x04, 0x00000000 },
+       { 0x4188fc,   1, 0x04, 0x20100018 },
+       {}
+};
+
+const struct gf100_gr_init
+gk110_grctx_init_gpc_unk_2[] = {
+       { 0x418d24,   1, 0x04, 0x00000000 },
+       {}
+};
+
+const struct gf100_gr_pack
+gk110_grctx_pack_gpc[] = {
+       { gf100_grctx_init_gpc_unk_0 },
+       { gf119_grctx_init_prop_0 },
+       { gf119_grctx_init_gpc_unk_1 },
+       { gk110_grctx_init_setup_0 },
+       { gf100_grctx_init_zcull_0 },
+       { gf119_grctx_init_crstr_0 },
+       { gk104_grctx_init_gpm_0 },
+       { gk110_grctx_init_gpc_unk_2 },
+       { gf100_grctx_init_gcc_0 },
+       {}
+};
+
+const struct gf100_gr_init
+gk110_grctx_init_tex_0[] = {
+       { 0x419a00,   1, 0x04, 0x000000f0 },
+       { 0x419a04,   1, 0x04, 0x00000001 },
+       { 0x419a08,   1, 0x04, 0x00000021 },
+       { 0x419a0c,   1, 0x04, 0x00020000 },
+       { 0x419a10,   1, 0x04, 0x00000000 },
+       { 0x419a14,   1, 0x04, 0x00000200 },
+       { 0x419a1c,   1, 0x04, 0x0000c000 },
+       { 0x419a20,   1, 0x04, 0x00020800 },
+       { 0x419a30,   1, 0x04, 0x00000001 },
+       { 0x419ac4,   1, 0x04, 0x0037f440 },
+       {}
+};
+
+const struct gf100_gr_init
+gk110_grctx_init_mpc_0[] = {
+       { 0x419c00,   1, 0x04, 0x0000001a },
+       { 0x419c04,   1, 0x04, 0x80000006 },
+       { 0x419c08,   1, 0x04, 0x00000002 },
+       { 0x419c20,   1, 0x04, 0x00000000 },
+       { 0x419c24,   1, 0x04, 0x00084210 },
+       { 0x419c28,   1, 0x04, 0x3efbefbe },
+       {}
+};
+
+const struct gf100_gr_init
+gk110_grctx_init_l1c_0[] = {
+       { 0x419ce8,   1, 0x04, 0x00000000 },
+       { 0x419cf4,   1, 0x04, 0x00000203 },
+       {}
+};
+
+static const struct gf100_gr_init
+gk110_grctx_init_sm_0[] = {
+       { 0x419e04,   1, 0x04, 0x00000000 },
+       { 0x419e08,   1, 0x04, 0x0000001d },
+       { 0x419e0c,   1, 0x04, 0x00000000 },
+       { 0x419e10,   1, 0x04, 0x00001c02 },
+       { 0x419e44,   1, 0x04, 0x0013eff2 },
+       { 0x419e48,   1, 0x04, 0x00000000 },
+       { 0x419e4c,   1, 0x04, 0x0000007f },
+       { 0x419e50,   2, 0x04, 0x00000000 },
+       { 0x419e58,   1, 0x04, 0x00000001 },
+       { 0x419e5c,   3, 0x04, 0x00000000 },
+       { 0x419e68,   1, 0x04, 0x00000002 },
+       { 0x419e6c,  12, 0x04, 0x00000000 },
+       { 0x419eac,   1, 0x04, 0x00001f8f },
+       { 0x419eb0,   1, 0x04, 0x0db00d2f },
+       { 0x419eb8,   1, 0x04, 0x00000000 },
+       { 0x419ec8,   1, 0x04, 0x0001304f },
+       { 0x419f30,   4, 0x04, 0x00000000 },
+       { 0x419f40,   1, 0x04, 0x00000018 },
+       { 0x419f44,   3, 0x04, 0x00000000 },
+       { 0x419f58,   1, 0x04, 0x00000000 },
+       { 0x419f70,   1, 0x04, 0x00007300 },
+       { 0x419f78,   1, 0x04, 0x000000eb },
+       { 0x419f7c,   1, 0x04, 0x00000404 },
+       {}
+};
+
+static const struct gf100_gr_pack
+gk110_grctx_pack_tpc[] = {
+       { gf117_grctx_init_pe_0 },
+       { gk110_grctx_init_tex_0 },
+       { gk110_grctx_init_mpc_0 },
+       { gk110_grctx_init_l1c_0 },
+       { gk110_grctx_init_sm_0 },
+       {}
+};
+
+static const struct gf100_gr_init
+gk110_grctx_init_cbm_0[] = {
+       { 0x41bec0,   1, 0x04, 0x10000000 },
+       { 0x41bec4,   1, 0x04, 0x00037f7f },
+       { 0x41bee4,   1, 0x04, 0x00000000 },
+       {}
+};
+
+const struct gf100_gr_pack
+gk110_grctx_pack_ppc[] = {
+       { gk104_grctx_init_pes_0 },
+       { gk110_grctx_init_cbm_0 },
+       { gf117_grctx_init_wwdx_0 },
+       {}
+};
+
+/*******************************************************************************
+ * PGRAPH context implementation
+ ******************************************************************************/
+
+struct nvkm_oclass *
+gk110_grctx_oclass = &(struct gf100_grctx_oclass) {
+       .base.handle = NV_ENGCTX(GR, 0xf0),
+       .base.ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = gf100_gr_context_ctor,
+               .dtor = gf100_gr_context_dtor,
+               .init = _nvkm_gr_context_init,
+               .fini = _nvkm_gr_context_fini,
+               .rd32 = _nvkm_gr_context_rd32,
+               .wr32 = _nvkm_gr_context_wr32,
+       },
+       .main  = gk104_grctx_generate_main,
+       .unkn  = gk104_grctx_generate_unkn,
+       .hub   = gk110_grctx_pack_hub,
+       .gpc   = gk110_grctx_pack_gpc,
+       .zcull = gf100_grctx_pack_zcull,
+       .tpc   = gk110_grctx_pack_tpc,
+       .ppc   = gk110_grctx_pack_ppc,
+       .icmd  = gk110_grctx_pack_icmd,
+       .mthd  = gk110_grctx_pack_mthd,
+       .bundle = gk104_grctx_generate_bundle,
+       .bundle_size = 0x3000,
+       .bundle_min_gpm_fifo_depth = 0x180,
+       .bundle_token_limit = 0x7c0,
+       .pagepool = gk104_grctx_generate_pagepool,
+       .pagepool_size = 0x8000,
+       .attrib = gf117_grctx_generate_attrib,
+       .attrib_nr_max = 0x324,
+       .attrib_nr = 0x218,
+       .alpha_nr_max = 0x7ff,
+       .alpha_nr = 0x648,
+}.base;
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/gr/ctxgk110b.c b/drivers/gpu/drm/nouveau/nvkm/engine/gr/ctxgk110b.c
new file mode 100644 (file)
index 0000000..b11c267
--- /dev/null
@@ -0,0 +1,103 @@
+/*
+ * Copyright 2013 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 <bskeggs@redhat.com>
+ */
+#include "ctxgf100.h"
+
+/*******************************************************************************
+ * PGRAPH context register lists
+ ******************************************************************************/
+
+static const struct gf100_gr_init
+gk110b_grctx_init_sm_0[] = {
+       { 0x419e04,   1, 0x04, 0x00000000 },
+       { 0x419e08,   1, 0x04, 0x0000001d },
+       { 0x419e0c,   1, 0x04, 0x00000000 },
+       { 0x419e10,   1, 0x04, 0x00001c02 },
+       { 0x419e44,   1, 0x04, 0x0013eff2 },
+       { 0x419e48,   1, 0x04, 0x00000000 },
+       { 0x419e4c,   1, 0x04, 0x0000007f },
+       { 0x419e50,   2, 0x04, 0x00000000 },
+       { 0x419e58,   1, 0x04, 0x00000001 },
+       { 0x419e5c,   3, 0x04, 0x00000000 },
+       { 0x419e68,   1, 0x04, 0x00000002 },
+       { 0x419e6c,  12, 0x04, 0x00000000 },
+       { 0x419eac,   1, 0x04, 0x00001f8f },
+       { 0x419eb0,   1, 0x04, 0x0db00d2f },
+       { 0x419eb8,   1, 0x04, 0x00000000 },
+       { 0x419ec8,   1, 0x04, 0x0001304f },
+       { 0x419f30,   4, 0x04, 0x00000000 },
+       { 0x419f40,   1, 0x04, 0x00000018 },
+       { 0x419f44,   3, 0x04, 0x00000000 },
+       { 0x419f58,   1, 0x04, 0x00000000 },
+       { 0x419f70,   1, 0x04, 0x00006300 },
+       { 0x419f78,   1, 0x04, 0x000000eb },
+       { 0x419f7c,   1, 0x04, 0x00000404 },
+       {}
+};
+
+static const struct gf100_gr_pack
+gk110b_grctx_pack_tpc[] = {
+       { gf117_grctx_init_pe_0 },
+       { gk110_grctx_init_tex_0 },
+       { gk110_grctx_init_mpc_0 },
+       { gk110_grctx_init_l1c_0 },
+       { gk110b_grctx_init_sm_0 },
+       {}
+};
+
+/*******************************************************************************
+ * PGRAPH context implementation
+ ******************************************************************************/
+
+struct nvkm_oclass *
+gk110b_grctx_oclass = &(struct gf100_grctx_oclass) {
+       .base.handle = NV_ENGCTX(GR, 0xf1),
+       .base.ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = gf100_gr_context_ctor,
+               .dtor = gf100_gr_context_dtor,
+               .init = _nvkm_gr_context_init,
+               .fini = _nvkm_gr_context_fini,
+               .rd32 = _nvkm_gr_context_rd32,
+               .wr32 = _nvkm_gr_context_wr32,
+       },
+       .main  = gk104_grctx_generate_main,
+       .unkn  = gk104_grctx_generate_unkn,
+       .hub   = gk110_grctx_pack_hub,
+       .gpc   = gk110_grctx_pack_gpc,
+       .zcull = gf100_grctx_pack_zcull,
+       .tpc   = gk110b_grctx_pack_tpc,
+       .ppc   = gk110_grctx_pack_ppc,
+       .icmd  = gk110_grctx_pack_icmd,
+       .mthd  = gk110_grctx_pack_mthd,
+       .bundle = gk104_grctx_generate_bundle,
+       .bundle_size = 0x3000,
+       .bundle_min_gpm_fifo_depth = 0x180,
+       .bundle_token_limit = 0x600,
+       .pagepool = gk104_grctx_generate_pagepool,
+       .pagepool_size = 0x8000,
+       .attrib = gf117_grctx_generate_attrib,
+       .attrib_nr_max = 0x324,
+       .attrib_nr = 0x218,
+       .alpha_nr_max = 0x7ff,
+       .alpha_nr = 0x648,
+}.base;
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/gr/ctxgk208.c b/drivers/gpu/drm/nouveau/nvkm/engine/gr/ctxgk208.c
new file mode 100644 (file)
index 0000000..6e8ce9f
--- /dev/null
@@ -0,0 +1,564 @@
+/*
+ * Copyright 2013 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 <bskeggs@redhat.com>
+ */
+#include "ctxgf100.h"
+
+/*******************************************************************************
+ * PGRAPH context register lists
+ ******************************************************************************/
+
+static const struct gf100_gr_init
+gk208_grctx_init_icmd_0[] = {
+       { 0x001000,   1, 0x01, 0x00000004 },
+       { 0x000039,   3, 0x01, 0x00000000 },
+       { 0x0000a9,   1, 0x01, 0x0000ffff },
+       { 0x000038,   1, 0x01, 0x0fac6881 },
+       { 0x00003d,   1, 0x01, 0x00000001 },
+       { 0x0000e8,   8, 0x01, 0x00000400 },
+       { 0x000078,   8, 0x01, 0x00000300 },
+       { 0x000050,   1, 0x01, 0x00000011 },
+       { 0x000058,   8, 0x01, 0x00000008 },
+       { 0x000208,   8, 0x01, 0x00000001 },
+       { 0x000081,   1, 0x01, 0x00000001 },
+       { 0x000085,   1, 0x01, 0x00000004 },
+       { 0x000088,   1, 0x01, 0x00000400 },
+       { 0x000090,   1, 0x01, 0x00000300 },
+       { 0x000098,   1, 0x01, 0x00001001 },
+       { 0x0000e3,   1, 0x01, 0x00000001 },
+       { 0x0000da,   1, 0x01, 0x00000001 },
+       { 0x0000f8,   1, 0x01, 0x00000003 },
+       { 0x0000fa,   1, 0x01, 0x00000001 },
+       { 0x00009f,   4, 0x01, 0x0000ffff },
+       { 0x0000b1,   1, 0x01, 0x00000001 },
+       { 0x0000ad,   1, 0x01, 0x0000013e },
+       { 0x0000e1,   1, 0x01, 0x00000010 },
+       { 0x000290,  16, 0x01, 0x00000000 },
+       { 0x0003b0,  16, 0x01, 0x00000000 },
+       { 0x0002a0,  16, 0x01, 0x00000000 },
+       { 0x000420,  16, 0x01, 0x00000000 },
+       { 0x0002b0,  16, 0x01, 0x00000000 },
+       { 0x000430,  16, 0x01, 0x00000000 },
+       { 0x0002c0,  16, 0x01, 0x00000000 },
+       { 0x0004d0,  16, 0x01, 0x00000000 },
+       { 0x000720,  16, 0x01, 0x00000000 },
+       { 0x0008c0,  16, 0x01, 0x00000000 },
+       { 0x000890,  16, 0x01, 0x00000000 },
+       { 0x0008e0,  16, 0x01, 0x00000000 },
+       { 0x0008a0,  16, 0x01, 0x00000000 },
+       { 0x0008f0,  16, 0x01, 0x00000000 },
+       { 0x00094c,   1, 0x01, 0x000000ff },
+       { 0x00094d,   1, 0x01, 0xffffffff },
+       { 0x00094e,   1, 0x01, 0x00000002 },
+       { 0x0002ec,   1, 0x01, 0x00000001 },
+       { 0x0002f2,   2, 0x01, 0x00000001 },
+       { 0x0002f5,   1, 0x01, 0x00000001 },
+       { 0x0002f7,   1, 0x01, 0x00000001 },
+       { 0x000303,   1, 0x01, 0x00000001 },
+       { 0x0002e6,   1, 0x01, 0x00000001 },
+       { 0x000466,   1, 0x01, 0x00000052 },
+       { 0x000301,   1, 0x01, 0x3f800000 },
+       { 0x000304,   1, 0x01, 0x30201000 },
+       { 0x000305,   1, 0x01, 0x70605040 },
+       { 0x000306,   1, 0x01, 0xb8a89888 },
+       { 0x000307,   1, 0x01, 0xf8e8d8c8 },
+       { 0x00030a,   1, 0x01, 0x00ffff00 },
+       { 0x00030b,   1, 0x01, 0x0000001a },
+       { 0x00030c,   1, 0x01, 0x00000001 },
+       { 0x000318,   1, 0x01, 0x00000001 },
+       { 0x000340,   1, 0x01, 0x00000000 },
+       { 0x000375,   1, 0x01, 0x00000001 },
+       { 0x00037d,   1, 0x01, 0x00000006 },
+       { 0x0003a0,   1, 0x01, 0x00000002 },
+       { 0x0003aa,   1, 0x01, 0x00000001 },
+       { 0x0003a9,   1, 0x01, 0x00000001 },
+       { 0x000380,   1, 0x01, 0x00000001 },
+       { 0x000383,   1, 0x01, 0x00000011 },
+       { 0x000360,   1, 0x01, 0x00000040 },
+       { 0x000366,   2, 0x01, 0x00000000 },
+       { 0x000368,   1, 0x01, 0x00000fff },
+       { 0x000370,   2, 0x01, 0x00000000 },
+       { 0x000372,   1, 0x01, 0x000fffff },
+       { 0x00037a,   1, 0x01, 0x00000012 },
+       { 0x000619,   1, 0x01, 0x00000003 },
+       { 0x000811,   1, 0x01, 0x00000003 },
+       { 0x000812,   1, 0x01, 0x00000004 },
+       { 0x000813,   1, 0x01, 0x00000006 },
+       { 0x000814,   1, 0x01, 0x00000008 },
+       { 0x000815,   1, 0x01, 0x0000000b },
+       { 0x000800,   6, 0x01, 0x00000001 },
+       { 0x000632,   1, 0x01, 0x00000001 },
+       { 0x000633,   1, 0x01, 0x00000002 },
+       { 0x000634,   1, 0x01, 0x00000003 },
+       { 0x000635,   1, 0x01, 0x00000004 },
+       { 0x000654,   1, 0x01, 0x3f800000 },
+       { 0x000657,   1, 0x01, 0x3f800000 },
+       { 0x000655,   2, 0x01, 0x3f800000 },
+       { 0x0006cd,   1, 0x01, 0x3f800000 },
+       { 0x0007f5,   1, 0x01, 0x3f800000 },
+       { 0x0007dc,   1, 0x01, 0x39291909 },
+       { 0x0007dd,   1, 0x01, 0x79695949 },
+       { 0x0007de,   1, 0x01, 0xb9a99989 },
+       { 0x0007df,   1, 0x01, 0xf9e9d9c9 },
+       { 0x0007e8,   1, 0x01, 0x00003210 },
+       { 0x0007e9,   1, 0x01, 0x00007654 },
+       { 0x0007ea,   1, 0x01, 0x00000098 },
+       { 0x0007ec,   1, 0x01, 0x39291909 },
+       { 0x0007ed,   1, 0x01, 0x79695949 },
+       { 0x0007ee,   1, 0x01, 0xb9a99989 },
+       { 0x0007ef,   1, 0x01, 0xf9e9d9c9 },
+       { 0x0007f0,   1, 0x01, 0x00003210 },
+       { 0x0007f1,   1, 0x01, 0x00007654 },
+       { 0x0007f2,   1, 0x01, 0x00000098 },
+       { 0x0005a5,   1, 0x01, 0x00000001 },
+       { 0x000980, 128, 0x01, 0x00000000 },
+       { 0x000468,   1, 0x01, 0x00000004 },
+       { 0x00046c,   1, 0x01, 0x00000001 },
+       { 0x000470,  96, 0x01, 0x00000000 },
+       { 0x000510,  16, 0x01, 0x3f800000 },
+       { 0x000520,   1, 0x01, 0x000002b6 },
+       { 0x000529,   1, 0x01, 0x00000001 },
+       { 0x000530,  16, 0x01, 0xffff0000 },
+       { 0x000585,   1, 0x01, 0x0000003f },
+       { 0x000576,   1, 0x01, 0x00000003 },
+       { 0x00057b,   1, 0x01, 0x00000059 },
+       { 0x000586,   1, 0x01, 0x00000040 },
+       { 0x000582,   2, 0x01, 0x00000080 },
+       { 0x0005c2,   1, 0x01, 0x00000001 },
+       { 0x000638,   2, 0x01, 0x00000001 },
+       { 0x00063a,   1, 0x01, 0x00000002 },
+       { 0x00063b,   2, 0x01, 0x00000001 },
+       { 0x00063d,   1, 0x01, 0x00000002 },
+       { 0x00063e,   1, 0x01, 0x00000001 },
+       { 0x0008b8,   8, 0x01, 0x00000001 },
+       { 0x000900,   8, 0x01, 0x00000001 },
+       { 0x000908,   8, 0x01, 0x00000002 },
+       { 0x000910,  16, 0x01, 0x00000001 },
+       { 0x000920,   8, 0x01, 0x00000002 },
+       { 0x000928,   8, 0x01, 0x00000001 },
+       { 0x000662,   1, 0x01, 0x00000001 },
+       { 0x000648,   9, 0x01, 0x00000001 },
+       { 0x000658,   1, 0x01, 0x0000000f },
+       { 0x0007ff,   1, 0x01, 0x0000000a },
+       { 0x00066a,   1, 0x01, 0x40000000 },
+       { 0x00066b,   1, 0x01, 0x10000000 },
+       { 0x00066c,   2, 0x01, 0xffff0000 },
+       { 0x0007af,   2, 0x01, 0x00000008 },
+       { 0x0007f6,   1, 0x01, 0x00000001 },
+       { 0x00080b,   1, 0x01, 0x00000002 },
+       { 0x0006b2,   1, 0x01, 0x00000055 },
+       { 0x0007ad,   1, 0x01, 0x00000003 },
+       { 0x000937,   1, 0x01, 0x00000001 },
+       { 0x000971,   1, 0x01, 0x00000008 },
+       { 0x000972,   1, 0x01, 0x00000040 },
+       { 0x000973,   1, 0x01, 0x0000012c },
+       { 0x00097c,   1, 0x01, 0x00000040 },
+       { 0x000979,   1, 0x01, 0x00000003 },
+       { 0x000975,   1, 0x01, 0x00000020 },
+       { 0x000976,   1, 0x01, 0x00000001 },
+       { 0x000977,   1, 0x01, 0x00000020 },
+       { 0x000978,   1, 0x01, 0x00000001 },
+       { 0x000957,   1, 0x01, 0x00000003 },
+       { 0x00095e,   1, 0x01, 0x20164010 },
+       { 0x00095f,   1, 0x01, 0x00000020 },
+       { 0x000a0d,   1, 0x01, 0x00000006 },
+       { 0x00097d,   1, 0x01, 0x00000020 },
+       { 0x000683,   1, 0x01, 0x00000006 },
+       { 0x000685,   1, 0x01, 0x003fffff },
+       { 0x000687,   1, 0x01, 0x003fffff },
+       { 0x0006a0,   1, 0x01, 0x00000005 },
+       { 0x000840,   1, 0x01, 0x00400008 },
+       { 0x000841,   1, 0x01, 0x08000080 },
+       { 0x000842,   1, 0x01, 0x00400008 },
+       { 0x000843,   1, 0x01, 0x08000080 },
+       { 0x0006aa,   1, 0x01, 0x00000001 },
+       { 0x0006ab,   1, 0x01, 0x00000002 },
+       { 0x0006ac,   1, 0x01, 0x00000080 },
+       { 0x0006ad,   2, 0x01, 0x00000100 },
+       { 0x0006b1,   1, 0x01, 0x00000011 },
+       { 0x0006bb,   1, 0x01, 0x000000cf },
+       { 0x0006ce,   1, 0x01, 0x2a712488 },
+       { 0x000739,   1, 0x01, 0x4085c000 },
+       { 0x00073a,   1, 0x01, 0x00000080 },
+       { 0x000786,   1, 0x01, 0x80000100 },
+       { 0x00073c,   1, 0x01, 0x00010100 },
+       { 0x00073d,   1, 0x01, 0x02800000 },
+       { 0x000787,   1, 0x01, 0x000000cf },
+       { 0x00078c,   1, 0x01, 0x00000008 },
+       { 0x000792,   1, 0x01, 0x00000001 },
+       { 0x000794,   3, 0x01, 0x00000001 },
+       { 0x000797,   1, 0x01, 0x000000cf },
+       { 0x000836,   1, 0x01, 0x00000001 },
+       { 0x00079a,   1, 0x01, 0x00000002 },
+       { 0x000833,   1, 0x01, 0x04444480 },
+       { 0x0007a1,   1, 0x01, 0x00000001 },
+       { 0x0007a3,   3, 0x01, 0x00000001 },
+       { 0x000831,   1, 0x01, 0x00000004 },
+       { 0x000b07,   1, 0x01, 0x00000002 },
+       { 0x000b08,   2, 0x01, 0x00000100 },
+       { 0x000b0a,   1, 0x01, 0x00000001 },
+       { 0x000a04,   1, 0x01, 0x000000ff },
+       { 0x000a0b,   1, 0x01, 0x00000040 },
+       { 0x00097f,   1, 0x01, 0x00000100 },
+       { 0x000a02,   1, 0x01, 0x00000001 },
+       { 0x000809,   1, 0x01, 0x00000007 },
+       { 0x00c221,   1, 0x01, 0x00000040 },
+       { 0x00c1b0,   8, 0x01, 0x0000000f },
+       { 0x00c1b8,   1, 0x01, 0x0fac6881 },
+       { 0x00c1b9,   1, 0x01, 0x00fac688 },
+       { 0x00c401,   1, 0x01, 0x00000001 },
+       { 0x00c402,   1, 0x01, 0x00010001 },
+       { 0x00c403,   2, 0x01, 0x00000001 },
+       { 0x00c40e,   1, 0x01, 0x00000020 },
+       { 0x00c500,   1, 0x01, 0x00000003 },
+       { 0x01e100,   1, 0x01, 0x00000001 },
+       { 0x001000,   1, 0x01, 0x00000002 },
+       { 0x0006aa,   1, 0x01, 0x00000001 },
+       { 0x0006ad,   2, 0x01, 0x00000100 },
+       { 0x0006b1,   1, 0x01, 0x00000011 },
+       { 0x00078c,   1, 0x01, 0x00000008 },
+       { 0x000792,   1, 0x01, 0x00000001 },
+       { 0x000794,   3, 0x01, 0x00000001 },
+       { 0x000797,   1, 0x01, 0x000000cf },
+       { 0x00079a,   1, 0x01, 0x00000002 },
+       { 0x0007a1,   1, 0x01, 0x00000001 },
+       { 0x0007a3,   3, 0x01, 0x00000001 },
+       { 0x000831,   1, 0x01, 0x00000004 },
+       { 0x01e100,   1, 0x01, 0x00000001 },
+       { 0x001000,   1, 0x01, 0x00000008 },
+       { 0x000039,   3, 0x01, 0x00000000 },
+       { 0x000380,   1, 0x01, 0x00000001 },
+       { 0x000366,   2, 0x01, 0x00000000 },
+       { 0x000368,   1, 0x01, 0x00000fff },
+       { 0x000370,   2, 0x01, 0x00000000 },
+       { 0x000372,   1, 0x01, 0x000fffff },
+       { 0x000813,   1, 0x01, 0x00000006 },
+       { 0x000814,   1, 0x01, 0x00000008 },
+       { 0x000957,   1, 0x01, 0x00000003 },
+       { 0x000b07,   1, 0x01, 0x00000002 },
+       { 0x000b08,   2, 0x01, 0x00000100 },
+       { 0x000b0a,   1, 0x01, 0x00000001 },
+       { 0x000a04,   1, 0x01, 0x000000ff },
+       { 0x000a0b,   1, 0x01, 0x00000040 },
+       { 0x00097f,   1, 0x01, 0x00000100 },
+       { 0x000a02,   1, 0x01, 0x00000001 },
+       { 0x000809,   1, 0x01, 0x00000007 },
+       { 0x00c221,   1, 0x01, 0x00000040 },
+       { 0x00c401,   1, 0x01, 0x00000001 },
+       { 0x00c402,   1, 0x01, 0x00010001 },
+       { 0x00c403,   2, 0x01, 0x00000001 },
+       { 0x00c40e,   1, 0x01, 0x00000020 },
+       { 0x00c500,   1, 0x01, 0x00000003 },
+       { 0x01e100,   1, 0x01, 0x00000001 },
+       { 0x001000,   1, 0x01, 0x00000001 },
+       { 0x000b07,   1, 0x01, 0x00000002 },
+       { 0x000b08,   2, 0x01, 0x00000100 },
+       { 0x000b0a,   1, 0x01, 0x00000001 },
+       { 0x01e100,   1, 0x01, 0x00000001 },
+       {}
+};
+
+static const struct gf100_gr_pack
+gk208_grctx_pack_icmd[] = {
+       { gk208_grctx_init_icmd_0 },
+       {}
+};
+
+static const struct gf100_gr_init
+gk208_grctx_init_fe_0[] = {
+       { 0x404004,   8, 0x04, 0x00000000 },
+       { 0x404024,   1, 0x04, 0x0000e000 },
+       { 0x404028,   8, 0x04, 0x00000000 },
+       { 0x4040a8,   8, 0x04, 0x00000000 },
+       { 0x4040c8,   1, 0x04, 0xf800008f },
+       { 0x4040d0,   6, 0x04, 0x00000000 },
+       { 0x4040e8,   1, 0x04, 0x00001000 },
+       { 0x4040f8,   1, 0x04, 0x00000000 },
+       { 0x404100,  10, 0x04, 0x00000000 },
+       { 0x404130,   2, 0x04, 0x00000000 },
+       { 0x404138,   1, 0x04, 0x20000040 },
+       { 0x404150,   1, 0x04, 0x0000002e },
+       { 0x404154,   1, 0x04, 0x00000400 },
+       { 0x404158,   1, 0x04, 0x00000200 },
+       { 0x404164,   1, 0x04, 0x00000055 },
+       { 0x40417c,   2, 0x04, 0x00000000 },
+       { 0x404194,   1, 0x04, 0x01000700 },
+       { 0x4041a0,   4, 0x04, 0x00000000 },
+       { 0x404200,   1, 0x04, 0x0000a197 },
+       { 0x404204,   1, 0x04, 0x0000a1c0 },
+       { 0x404208,   1, 0x04, 0x0000a140 },
+       { 0x40420c,   1, 0x04, 0x0000902d },
+       {}
+};
+
+static const struct gf100_gr_init
+gk208_grctx_init_ds_0[] = {
+       { 0x405800,   1, 0x04, 0x0f8000bf },
+       { 0x405830,   1, 0x04, 0x02180648 },
+       { 0x405834,   1, 0x04, 0x08000000 },
+       { 0x405838,   1, 0x04, 0x00000000 },
+       { 0x405854,   1, 0x04, 0x00000000 },
+       { 0x405870,   4, 0x04, 0x00000001 },
+       { 0x405a00,   2, 0x04, 0x00000000 },
+       { 0x405a18,   1, 0x04, 0x00000000 },
+       { 0x405a1c,   1, 0x04, 0x000000ff },
+       {}
+};
+
+static const struct gf100_gr_init
+gk208_grctx_init_pd_0[] = {
+       { 0x406020,   1, 0x04, 0x034103c1 },
+       { 0x406028,   4, 0x04, 0x00000001 },
+       { 0x4064a8,   1, 0x04, 0x00000000 },
+       { 0x4064ac,   1, 0x04, 0x00003fff },
+       { 0x4064b0,   3, 0x04, 0x00000000 },
+       { 0x4064c0,   1, 0x04, 0x802000f0 },
+       { 0x4064c4,   1, 0x04, 0x0192ffff },
+       { 0x4064c8,   1, 0x04, 0x00c20200 },
+       { 0x4064cc,   9, 0x04, 0x00000000 },
+       { 0x4064fc,   1, 0x04, 0x0000022a },
+       {}
+};
+
+const struct gf100_gr_init
+gk208_grctx_init_rstr2d_0[] = {
+       { 0x407804,   1, 0x04, 0x00000063 },
+       { 0x40780c,   1, 0x04, 0x0a418820 },
+       { 0x407810,   1, 0x04, 0x062080e6 },
+       { 0x407814,   1, 0x04, 0x020398a4 },
+       { 0x407818,   1, 0x04, 0x0e629062 },
+       { 0x40781c,   1, 0x04, 0x0a418820 },
+       { 0x407820,   1, 0x04, 0x000000e6 },
+       { 0x4078bc,   1, 0x04, 0x00000103 },
+       {}
+};
+
+static const struct gf100_gr_init
+gk208_grctx_init_be_0[] = {
+       { 0x408800,   1, 0x04, 0x32802a3c },
+       { 0x408804,   1, 0x04, 0x00000040 },
+       { 0x408808,   1, 0x04, 0x1003e005 },
+       { 0x408840,   1, 0x04, 0x0000000b },
+       { 0x408900,   1, 0x04, 0xb080b801 },
+       { 0x408904,   1, 0x04, 0x62000001 },
+       { 0x408908,   1, 0x04, 0x02c8102f },
+       { 0x408980,   1, 0x04, 0x0000011d },
+       {}
+};
+
+static const struct gf100_gr_pack
+gk208_grctx_pack_hub[] = {
+       { gf100_grctx_init_main_0 },
+       { gk208_grctx_init_fe_0 },
+       { gk110_grctx_init_pri_0 },
+       { gk104_grctx_init_memfmt_0 },
+       { gk208_grctx_init_ds_0 },
+       { gk110_grctx_init_cwd_0 },
+       { gk208_grctx_init_pd_0 },
+       { gk208_grctx_init_rstr2d_0 },
+       { gk104_grctx_init_scc_0 },
+       { gk208_grctx_init_be_0 },
+       {}
+};
+
+const struct gf100_gr_init
+gk208_grctx_init_prop_0[] = {
+       { 0x418400,   1, 0x04, 0x38005e00 },
+       { 0x418404,   1, 0x04, 0x71e0ffff },
+       { 0x41840c,   1, 0x04, 0x00001008 },
+       { 0x418410,   1, 0x04, 0x0fff0fff },
+       { 0x418414,   1, 0x04, 0x02200fff },
+       { 0x418450,   6, 0x04, 0x00000000 },
+       { 0x418468,   1, 0x04, 0x00000001 },
+       { 0x41846c,   2, 0x04, 0x00000000 },
+       {}
+};
+
+static const struct gf100_gr_init
+gk208_grctx_init_gpc_unk_1[] = {
+       { 0x418600,   1, 0x04, 0x0000007f },
+       { 0x418684,   1, 0x04, 0x0000001f },
+       { 0x418700,   1, 0x04, 0x00000002 },
+       { 0x418704,   2, 0x04, 0x00000080 },
+       { 0x41870c,   2, 0x04, 0x00000000 },
+       {}
+};
+
+static const struct gf100_gr_init
+gk208_grctx_init_setup_0[] = {
+       { 0x418800,   1, 0x04, 0x7006863a },
+       { 0x418808,   1, 0x04, 0x00000000 },
+       { 0x41880c,   1, 0x04, 0x00000030 },
+       { 0x418810,   1, 0x04, 0x00000000 },
+       { 0x418828,   1, 0x04, 0x00000044 },
+       { 0x418830,   1, 0x04, 0x10000001 },
+       { 0x4188d8,   1, 0x04, 0x00000008 },
+       { 0x4188e0,   1, 0x04, 0x01000000 },
+       { 0x4188e8,   5, 0x04, 0x00000000 },
+       { 0x4188fc,   1, 0x04, 0x20100058 },
+       {}
+};
+
+const struct gf100_gr_init
+gk208_grctx_init_crstr_0[] = {
+       { 0x418b00,   1, 0x04, 0x0000001e },
+       { 0x418b08,   1, 0x04, 0x0a418820 },
+       { 0x418b0c,   1, 0x04, 0x062080e6 },
+       { 0x418b10,   1, 0x04, 0x020398a4 },
+       { 0x418b14,   1, 0x04, 0x0e629062 },
+       { 0x418b18,   1, 0x04, 0x0a418820 },
+       { 0x418b1c,   1, 0x04, 0x000000e6 },
+       { 0x418bb8,   1, 0x04, 0x00000103 },
+       {}
+};
+
+static const struct gf100_gr_init
+gk208_grctx_init_gpm_0[] = {
+       { 0x418c08,   1, 0x04, 0x00000001 },
+       { 0x418c10,   8, 0x04, 0x00000000 },
+       { 0x418c40,   1, 0x04, 0xffffffff },
+       { 0x418c6c,   1, 0x04, 0x00000001 },
+       { 0x418c80,   1, 0x04, 0x2020000c },
+       { 0x418c8c,   1, 0x04, 0x00000001 },
+       {}
+};
+
+static const struct gf100_gr_pack
+gk208_grctx_pack_gpc[] = {
+       { gf100_grctx_init_gpc_unk_0 },
+       { gk208_grctx_init_prop_0 },
+       { gk208_grctx_init_gpc_unk_1 },
+       { gk208_grctx_init_setup_0 },
+       { gf100_grctx_init_zcull_0 },
+       { gk208_grctx_init_crstr_0 },
+       { gk208_grctx_init_gpm_0 },
+       { gk110_grctx_init_gpc_unk_2 },
+       { gf100_grctx_init_gcc_0 },
+       {}
+};
+
+static const struct gf100_gr_init
+gk208_grctx_init_tex_0[] = {
+       { 0x419a00,   1, 0x04, 0x000100f0 },
+       { 0x419a04,   1, 0x04, 0x00000001 },
+       { 0x419a08,   1, 0x04, 0x00000421 },
+       { 0x419a0c,   1, 0x04, 0x00120000 },
+       { 0x419a10,   1, 0x04, 0x00000000 },
+       { 0x419a14,   1, 0x04, 0x00000200 },
+       { 0x419a1c,   1, 0x04, 0x0000c000 },
+       { 0x419a20,   1, 0x04, 0x00000800 },
+       { 0x419a30,   1, 0x04, 0x00000001 },
+       { 0x419ac4,   1, 0x04, 0x0037f440 },
+       {}
+};
+
+static const struct gf100_gr_init
+gk208_grctx_init_sm_0[] = {
+       { 0x419e04,   1, 0x04, 0x00000000 },
+       { 0x419e08,   1, 0x04, 0x0000001d },
+       { 0x419e0c,   1, 0x04, 0x00000000 },
+       { 0x419e10,   1, 0x04, 0x00001c02 },
+       { 0x419e44,   1, 0x04, 0x0013eff2 },
+       { 0x419e48,   1, 0x04, 0x00000000 },
+       { 0x419e4c,   1, 0x04, 0x0000007f },
+       { 0x419e50,   2, 0x04, 0x00000000 },
+       { 0x419e58,   1, 0x04, 0x00000001 },
+       { 0x419e5c,   3, 0x04, 0x00000000 },
+       { 0x419e68,   1, 0x04, 0x00000002 },
+       { 0x419e6c,  12, 0x04, 0x00000000 },
+       { 0x419eac,   1, 0x04, 0x00001f8f },
+       { 0x419eb0,   1, 0x04, 0x0db00d2f },
+       { 0x419eb8,   1, 0x04, 0x00000000 },
+       { 0x419ec8,   1, 0x04, 0x0001304f },
+       { 0x419f30,   4, 0x04, 0x00000000 },
+       { 0x419f40,   1, 0x04, 0x00000018 },
+       { 0x419f44,   3, 0x04, 0x00000000 },
+       { 0x419f58,   1, 0x04, 0x00000020 },
+       { 0x419f70,   1, 0x04, 0x00000000 },
+       { 0x419f78,   1, 0x04, 0x000001eb },
+       { 0x419f7c,   1, 0x04, 0x00000404 },
+       {}
+};
+
+static const struct gf100_gr_pack
+gk208_grctx_pack_tpc[] = {
+       { gf117_grctx_init_pe_0 },
+       { gk208_grctx_init_tex_0 },
+       { gk110_grctx_init_mpc_0 },
+       { gk110_grctx_init_l1c_0 },
+       { gk208_grctx_init_sm_0 },
+       {}
+};
+
+static const struct gf100_gr_init
+gk208_grctx_init_cbm_0[] = {
+       { 0x41bec0,   1, 0x04, 0x10000000 },
+       { 0x41bec4,   1, 0x04, 0x00037f7f },
+       { 0x41bee4,   1, 0x04, 0x00000000 },
+       { 0x41bef0,   1, 0x04, 0x000003ff },
+       {}
+};
+
+static const struct gf100_gr_pack
+gk208_grctx_pack_ppc[] = {
+       { gk104_grctx_init_pes_0 },
+       { gk208_grctx_init_cbm_0 },
+       { gf117_grctx_init_wwdx_0 },
+       {}
+};
+
+/*******************************************************************************
+ * PGRAPH context implementation
+ ******************************************************************************/
+
+struct nvkm_oclass *
+gk208_grctx_oclass = &(struct gf100_grctx_oclass) {
+       .base.handle = NV_ENGCTX(GR, 0x08),
+       .base.ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = gf100_gr_context_ctor,
+               .dtor = gf100_gr_context_dtor,
+               .init = _nvkm_gr_context_init,
+               .fini = _nvkm_gr_context_fini,
+               .rd32 = _nvkm_gr_context_rd32,
+               .wr32 = _nvkm_gr_context_wr32,
+       },
+       .main  = gk104_grctx_generate_main,
+       .unkn  = gk104_grctx_generate_unkn,
+       .hub   = gk208_grctx_pack_hub,
+       .gpc   = gk208_grctx_pack_gpc,
+       .zcull = gf100_grctx_pack_zcull,
+       .tpc   = gk208_grctx_pack_tpc,
+       .ppc   = gk208_grctx_pack_ppc,
+       .icmd  = gk208_grctx_pack_icmd,
+       .mthd  = gk110_grctx_pack_mthd,
+       .bundle = gk104_grctx_generate_bundle,
+       .bundle_size = 0x3000,
+       .bundle_min_gpm_fifo_depth = 0xc2,
+       .bundle_token_limit = 0x200,
+       .pagepool = gk104_grctx_generate_pagepool,
+       .pagepool_size = 0x8000,
+       .attrib = gf117_grctx_generate_attrib,
+       .attrib_nr_max = 0x324,
+       .attrib_nr = 0x218,
+       .alpha_nr_max = 0x7ff,
+       .alpha_nr = 0x648,
+}.base;
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/gr/ctxgk20a.c b/drivers/gpu/drm/nouveau/nvkm/engine/gr/ctxgk20a.c
new file mode 100644 (file)
index 0000000..2f241f6
--- /dev/null
@@ -0,0 +1,62 @@
+/*
+ * Copyright (c) 2014, NVIDIA CORPORATION. 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 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 "ctxgf100.h"
+
+static const struct gf100_gr_pack
+gk20a_grctx_pack_mthd[] = {
+       { gk104_grctx_init_a097_0, 0xa297 },
+       { gf100_grctx_init_902d_0, 0x902d },
+       {}
+};
+
+struct nvkm_oclass *
+gk20a_grctx_oclass = &(struct gf100_grctx_oclass) {
+       .base.handle = NV_ENGCTX(GR, 0xea),
+       .base.ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = gf100_gr_context_ctor,
+               .dtor = gf100_gr_context_dtor,
+               .init = _nvkm_gr_context_init,
+               .fini = _nvkm_gr_context_fini,
+               .rd32 = _nvkm_gr_context_rd32,
+               .wr32 = _nvkm_gr_context_wr32,
+       },
+       .main  = gk104_grctx_generate_main,
+       .unkn  = gk104_grctx_generate_unkn,
+       .hub   = gk104_grctx_pack_hub,
+       .gpc   = gk104_grctx_pack_gpc,
+       .zcull = gf100_grctx_pack_zcull,
+       .tpc   = gk104_grctx_pack_tpc,
+       .ppc   = gk104_grctx_pack_ppc,
+       .icmd  = gk104_grctx_pack_icmd,
+       .mthd  = gk20a_grctx_pack_mthd,
+       .bundle = gk104_grctx_generate_bundle,
+       .bundle_size = 0x1800,
+       .bundle_min_gpm_fifo_depth = 0x62,
+       .bundle_token_limit = 0x100,
+       .pagepool = gk104_grctx_generate_pagepool,
+       .pagepool_size = 0x8000,
+       .attrib = gf117_grctx_generate_attrib,
+       .attrib_nr_max = 0x240,
+       .attrib_nr = 0x240,
+       .alpha_nr_max = 0x648 + (0x648 / 2),
+       .alpha_nr = 0x648,
+}.base;
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/gr/ctxgm107.c b/drivers/gpu/drm/nouveau/nvkm/engine/gr/ctxgm107.c
new file mode 100644 (file)
index 0000000..956f4dc
--- /dev/null
@@ -0,0 +1,1034 @@
+/*
+ * Copyright 2013 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 <bskeggs@redhat.com>
+ */
+#include "ctxgf100.h"
+
+#include <subdev/fb.h>
+#include <subdev/mc.h>
+
+/*******************************************************************************
+ * PGRAPH context register lists
+ ******************************************************************************/
+
+static const struct gf100_gr_init
+gm107_grctx_init_icmd_0[] = {
+       { 0x001000,   1, 0x01, 0x00000004 },
+       { 0x000039,   3, 0x01, 0x00000000 },
+       { 0x0000a9,   1, 0x01, 0x0000ffff },
+       { 0x000038,   1, 0x01, 0x0fac6881 },
+       { 0x00003d,   1, 0x01, 0x00000001 },
+       { 0x0000e8,   8, 0x01, 0x00000400 },
+       { 0x000078,   8, 0x01, 0x00000300 },
+       { 0x000050,   1, 0x01, 0x00000011 },
+       { 0x000058,   8, 0x01, 0x00000008 },
+       { 0x000208,   8, 0x01, 0x00000001 },
+       { 0x000081,   1, 0x01, 0x00000001 },
+       { 0x000085,   1, 0x01, 0x00000004 },
+       { 0x000088,   1, 0x01, 0x00000400 },
+       { 0x000090,   1, 0x01, 0x00000300 },
+       { 0x000098,   1, 0x01, 0x00001001 },
+       { 0x0000e3,   1, 0x01, 0x00000001 },
+       { 0x0000da,   1, 0x01, 0x00000001 },
+       { 0x0000f8,   1, 0x01, 0x00000003 },
+       { 0x0000fa,   1, 0x01, 0x00000001 },
+       { 0x0000b1,   2, 0x01, 0x00000001 },
+       { 0x00009f,   4, 0x01, 0x0000ffff },
+       { 0x0000a8,   1, 0x01, 0x0000ffff },
+       { 0x0000ad,   1, 0x01, 0x0000013e },
+       { 0x0000e1,   1, 0x01, 0x00000010 },
+       { 0x000290,  16, 0x01, 0x00000000 },
+       { 0x0003b0,  16, 0x01, 0x00000000 },
+       { 0x0002a0,  16, 0x01, 0x00000000 },
+       { 0x000420,  16, 0x01, 0x00000000 },
+       { 0x0002b0,  16, 0x01, 0x00000000 },
+       { 0x000430,  16, 0x01, 0x00000000 },
+       { 0x0002c0,  16, 0x01, 0x00000000 },
+       { 0x0004d0,  16, 0x01, 0x00000000 },
+       { 0x000720,  16, 0x01, 0x00000000 },
+       { 0x0008c0,  16, 0x01, 0x00000000 },
+       { 0x000890,  16, 0x01, 0x00000000 },
+       { 0x0008e0,  16, 0x01, 0x00000000 },
+       { 0x0008a0,  16, 0x01, 0x00000000 },
+       { 0x0008f0,  16, 0x01, 0x00000000 },
+       { 0x00094c,   1, 0x01, 0x000000ff },
+       { 0x00094d,   1, 0x01, 0xffffffff },
+       { 0x00094e,   1, 0x01, 0x00000002 },
+       { 0x0002f2,   2, 0x01, 0x00000001 },
+       { 0x0002f5,   1, 0x01, 0x00000001 },
+       { 0x0002f7,   1, 0x01, 0x00000001 },
+       { 0x000303,   1, 0x01, 0x00000001 },
+       { 0x0002e6,   1, 0x01, 0x00000001 },
+       { 0x000466,   1, 0x01, 0x00000052 },
+       { 0x000301,   1, 0x01, 0x3f800000 },
+       { 0x000304,   1, 0x01, 0x30201000 },
+       { 0x000305,   1, 0x01, 0x70605040 },
+       { 0x000306,   1, 0x01, 0xb8a89888 },
+       { 0x000307,   1, 0x01, 0xf8e8d8c8 },
+       { 0x00030a,   1, 0x01, 0x00ffff00 },
+       { 0x0000de,   1, 0x01, 0x00000001 },
+       { 0x00030b,   1, 0x01, 0x0000001a },
+       { 0x00030c,   1, 0x01, 0x00000001 },
+       { 0x000318,   1, 0x01, 0x00000001 },
+       { 0x000340,   1, 0x01, 0x00000000 },
+       { 0x00037d,   1, 0x01, 0x00000006 },
+       { 0x0003a0,   1, 0x01, 0x00000002 },
+       { 0x0003aa,   1, 0x01, 0x00000001 },
+       { 0x0003a9,   1, 0x01, 0x00000001 },
+       { 0x000380,   1, 0x01, 0x00000001 },
+       { 0x000383,   1, 0x01, 0x00000011 },
+       { 0x000360,   1, 0x01, 0x00000040 },
+       { 0x000366,   2, 0x01, 0x00000000 },
+       { 0x000368,   1, 0x01, 0x00000fff },
+       { 0x000370,   2, 0x01, 0x00000000 },
+       { 0x000372,   1, 0x01, 0x000fffff },
+       { 0x00037a,   1, 0x01, 0x00000012 },
+       { 0x000619,   1, 0x01, 0x00000003 },
+       { 0x000811,   1, 0x01, 0x00000003 },
+       { 0x000812,   1, 0x01, 0x00000004 },
+       { 0x000813,   1, 0x01, 0x00000006 },
+       { 0x000814,   1, 0x01, 0x00000008 },
+       { 0x000815,   1, 0x01, 0x0000000b },
+       { 0x000800,   6, 0x01, 0x00000001 },
+       { 0x000632,   1, 0x01, 0x00000001 },
+       { 0x000633,   1, 0x01, 0x00000002 },
+       { 0x000634,   1, 0x01, 0x00000003 },
+       { 0x000635,   1, 0x01, 0x00000004 },
+       { 0x000654,   1, 0x01, 0x3f800000 },
+       { 0x000657,   1, 0x01, 0x3f800000 },
+       { 0x000655,   2, 0x01, 0x3f800000 },
+       { 0x0006cd,   1, 0x01, 0x3f800000 },
+       { 0x0007f5,   1, 0x01, 0x3f800000 },
+       { 0x0007dc,   1, 0x01, 0x39291909 },
+       { 0x0007dd,   1, 0x01, 0x79695949 },
+       { 0x0007de,   1, 0x01, 0xb9a99989 },
+       { 0x0007df,   1, 0x01, 0xf9e9d9c9 },
+       { 0x0007e8,   1, 0x01, 0x00003210 },
+       { 0x0007e9,   1, 0x01, 0x00007654 },
+       { 0x0007ea,   1, 0x01, 0x00000098 },
+       { 0x0007ec,   1, 0x01, 0x39291909 },
+       { 0x0007ed,   1, 0x01, 0x79695949 },
+       { 0x0007ee,   1, 0x01, 0xb9a99989 },
+       { 0x0007ef,   1, 0x01, 0xf9e9d9c9 },
+       { 0x0007f0,   1, 0x01, 0x00003210 },
+       { 0x0007f1,   1, 0x01, 0x00007654 },
+       { 0x0007f2,   1, 0x01, 0x00000098 },
+       { 0x0005a5,   1, 0x01, 0x00000001 },
+       { 0x0005d0,   1, 0x01, 0x20181008 },
+       { 0x0005d1,   1, 0x01, 0x40383028 },
+       { 0x0005d2,   1, 0x01, 0x60585048 },
+       { 0x0005d3,   1, 0x01, 0x80787068 },
+       { 0x000980, 128, 0x01, 0x00000000 },
+       { 0x000468,   1, 0x01, 0x00000004 },
+       { 0x00046c,   1, 0x01, 0x00000001 },
+       { 0x000470,  96, 0x01, 0x00000000 },
+       { 0x000510,  16, 0x01, 0x3f800000 },
+       { 0x000520,   1, 0x01, 0x000002b6 },
+       { 0x000529,   1, 0x01, 0x00000001 },
+       { 0x000530,  16, 0x01, 0xffff0000 },
+       { 0x000550,  32, 0x01, 0xffff0000 },
+       { 0x000585,   1, 0x01, 0x0000003f },
+       { 0x000576,   1, 0x01, 0x00000003 },
+       { 0x00057b,   1, 0x01, 0x00000059 },
+       { 0x000586,   1, 0x01, 0x00000040 },
+       { 0x000582,   2, 0x01, 0x00000080 },
+       { 0x000595,   1, 0x01, 0x00400040 },
+       { 0x000596,   1, 0x01, 0x00000492 },
+       { 0x000597,   1, 0x01, 0x08080203 },
+       { 0x0005ad,   1, 0x01, 0x00000008 },
+       { 0x000598,   1, 0x01, 0x00020001 },
+       { 0x0005c2,   1, 0x01, 0x00000001 },
+       { 0x000638,   2, 0x01, 0x00000001 },
+       { 0x00063a,   1, 0x01, 0x00000002 },
+       { 0x00063b,   2, 0x01, 0x00000001 },
+       { 0x00063d,   1, 0x01, 0x00000002 },
+       { 0x00063e,   1, 0x01, 0x00000001 },
+       { 0x0008b8,   8, 0x01, 0x00000001 },
+       { 0x000900,   8, 0x01, 0x00000001 },
+       { 0x000908,   8, 0x01, 0x00000002 },
+       { 0x000910,  16, 0x01, 0x00000001 },
+       { 0x000920,   8, 0x01, 0x00000002 },
+       { 0x000928,   8, 0x01, 0x00000001 },
+       { 0x000662,   1, 0x01, 0x00000001 },
+       { 0x000648,   9, 0x01, 0x00000001 },
+       { 0x000658,   1, 0x01, 0x0000000f },
+       { 0x0007ff,   1, 0x01, 0x0000000a },
+       { 0x00066a,   1, 0x01, 0x40000000 },
+       { 0x00066b,   1, 0x01, 0x10000000 },
+       { 0x00066c,   2, 0x01, 0xffff0000 },
+       { 0x0007af,   2, 0x01, 0x00000008 },
+       { 0x0007f6,   1, 0x01, 0x00000001 },
+       { 0x0006b2,   1, 0x01, 0x00000055 },
+       { 0x0007ad,   1, 0x01, 0x00000003 },
+       { 0x000971,   1, 0x01, 0x00000008 },
+       { 0x000972,   1, 0x01, 0x00000040 },
+       { 0x000973,   1, 0x01, 0x0000012c },
+       { 0x00097c,   1, 0x01, 0x00000040 },
+       { 0x000975,   1, 0x01, 0x00000020 },
+       { 0x000976,   1, 0x01, 0x00000001 },
+       { 0x000977,   1, 0x01, 0x00000020 },
+       { 0x000978,   1, 0x01, 0x00000001 },
+       { 0x000957,   1, 0x01, 0x00000003 },
+       { 0x00095e,   1, 0x01, 0x20164010 },
+       { 0x00095f,   1, 0x01, 0x00000020 },
+       { 0x000a0d,   1, 0x01, 0x00000006 },
+       { 0x00097d,   1, 0x01, 0x0000000c },
+       { 0x000683,   1, 0x01, 0x00000006 },
+       { 0x000687,   1, 0x01, 0x003fffff },
+       { 0x0006a0,   1, 0x01, 0x00000005 },
+       { 0x000840,   1, 0x01, 0x00400008 },
+       { 0x000841,   1, 0x01, 0x08000080 },
+       { 0x000842,   1, 0x01, 0x00400008 },
+       { 0x000843,   1, 0x01, 0x08000080 },
+       { 0x000818,   8, 0x01, 0x00000000 },
+       { 0x000848,  16, 0x01, 0x00000000 },
+       { 0x000738,   1, 0x01, 0x00000000 },
+       { 0x0006aa,   1, 0x01, 0x00000001 },
+       { 0x0006ab,   1, 0x01, 0x00000002 },
+       { 0x0006ac,   1, 0x01, 0x00000080 },
+       { 0x0006ad,   2, 0x01, 0x00000100 },
+       { 0x0006b1,   1, 0x01, 0x00000011 },
+       { 0x0006bb,   1, 0x01, 0x000000cf },
+       { 0x0006ce,   1, 0x01, 0x2a712488 },
+       { 0x000739,   1, 0x01, 0x4085c000 },
+       { 0x00073a,   1, 0x01, 0x00000080 },
+       { 0x000786,   1, 0x01, 0x80000100 },
+       { 0x00073c,   1, 0x01, 0x00010100 },
+       { 0x00073d,   1, 0x01, 0x02800000 },
+       { 0x000787,   1, 0x01, 0x000000cf },
+       { 0x00078c,   1, 0x01, 0x00000008 },
+       { 0x000792,   1, 0x01, 0x00000001 },
+       { 0x000794,   3, 0x01, 0x00000001 },
+       { 0x000797,   1, 0x01, 0x000000cf },
+       { 0x000836,   1, 0x01, 0x00000001 },
+       { 0x00079a,   1, 0x01, 0x00000002 },
+       { 0x000833,   1, 0x01, 0x04444480 },
+       { 0x0007a1,   1, 0x01, 0x00000001 },
+       { 0x0007a3,   3, 0x01, 0x00000001 },
+       { 0x000831,   1, 0x01, 0x00000004 },
+       { 0x000b07,   1, 0x01, 0x00000002 },
+       { 0x000b08,   2, 0x01, 0x00000100 },
+       { 0x000b0a,   1, 0x01, 0x00000001 },
+       { 0x000a04,   1, 0x01, 0x000000ff },
+       { 0x000a0b,   1, 0x01, 0x00000040 },
+       { 0x00097f,   1, 0x01, 0x00000100 },
+       { 0x000a02,   1, 0x01, 0x00000001 },
+       { 0x000809,   1, 0x01, 0x00000007 },
+       { 0x00c221,   1, 0x01, 0x00000040 },
+       { 0x00c1b0,   8, 0x01, 0x0000000f },
+       { 0x00c1b8,   1, 0x01, 0x0fac6881 },
+       { 0x00c1b9,   1, 0x01, 0x00fac688 },
+       { 0x00c401,   1, 0x01, 0x00000001 },
+       { 0x00c402,   1, 0x01, 0x00010001 },
+       { 0x00c403,   2, 0x01, 0x00000001 },
+       { 0x00c40e,   1, 0x01, 0x00000020 },
+       { 0x01e100,   1, 0x01, 0x00000001 },
+       { 0x001000,   1, 0x01, 0x00000002 },
+       { 0x0006aa,   1, 0x01, 0x00000001 },
+       { 0x0006ad,   2, 0x01, 0x00000100 },
+       { 0x0006b1,   1, 0x01, 0x00000011 },
+       { 0x00078c,   1, 0x01, 0x00000008 },
+       { 0x000792,   1, 0x01, 0x00000001 },
+       { 0x000794,   3, 0x01, 0x00000001 },
+       { 0x000797,   1, 0x01, 0x000000cf },
+       { 0x00079a,   1, 0x01, 0x00000002 },
+       { 0x0007a1,   1, 0x01, 0x00000001 },
+       { 0x0007a3,   3, 0x01, 0x00000001 },
+       { 0x000831,   1, 0x01, 0x00000004 },
+       { 0x01e100,   1, 0x01, 0x00000001 },
+       { 0x001000,   1, 0x01, 0x00000008 },
+       { 0x000039,   3, 0x01, 0x00000000 },
+       { 0x000380,   1, 0x01, 0x00000001 },
+       { 0x000366,   2, 0x01, 0x00000000 },
+       { 0x000368,   1, 0x01, 0x00000fff },
+       { 0x000370,   2, 0x01, 0x00000000 },
+       { 0x000372,   1, 0x01, 0x000fffff },
+       { 0x000813,   1, 0x01, 0x00000006 },
+       { 0x000814,   1, 0x01, 0x00000008 },
+       { 0x000818,   8, 0x01, 0x00000000 },
+       { 0x000848,  16, 0x01, 0x00000000 },
+       { 0x000738,   1, 0x01, 0x00000000 },
+       { 0x000b07,   1, 0x01, 0x00000002 },
+       { 0x000b08,   2, 0x01, 0x00000100 },
+       { 0x000b0a,   1, 0x01, 0x00000001 },
+       { 0x000a04,   1, 0x01, 0x000000ff },
+       { 0x000a0b,   1, 0x01, 0x00000040 },
+       { 0x00097f,   1, 0x01, 0x00000100 },
+       { 0x000a02,   1, 0x01, 0x00000001 },
+       { 0x000809,   1, 0x01, 0x00000007 },
+       { 0x00c221,   1, 0x01, 0x00000040 },
+       { 0x00c401,   1, 0x01, 0x00000001 },
+       { 0x00c402,   1, 0x01, 0x00010001 },
+       { 0x00c403,   2, 0x01, 0x00000001 },
+       { 0x00c40e,   1, 0x01, 0x00000020 },
+       { 0x01e100,   1, 0x01, 0x00000001 },
+       { 0x001000,   1, 0x01, 0x00000001 },
+       { 0x000b07,   1, 0x01, 0x00000002 },
+       { 0x000b08,   2, 0x01, 0x00000100 },
+       { 0x000b0a,   1, 0x01, 0x00000001 },
+       { 0x01e100,   1, 0x01, 0x00000001 },
+       {}
+};
+
+static const struct gf100_gr_pack
+gm107_grctx_pack_icmd[] = {
+       { gm107_grctx_init_icmd_0 },
+       {}
+};
+
+static const struct gf100_gr_init
+gm107_grctx_init_b097_0[] = {
+       { 0x000800,   8, 0x40, 0x00000000 },
+       { 0x000804,   8, 0x40, 0x00000000 },
+       { 0x000808,   8, 0x40, 0x00000400 },
+       { 0x00080c,   8, 0x40, 0x00000300 },
+       { 0x000810,   1, 0x04, 0x000000cf },
+       { 0x000850,   7, 0x40, 0x00000000 },
+       { 0x000814,   8, 0x40, 0x00000040 },
+       { 0x000818,   8, 0x40, 0x00000001 },
+       { 0x00081c,   8, 0x40, 0x00000000 },
+       { 0x000820,   8, 0x40, 0x00000000 },
+       { 0x001c00,  16, 0x10, 0x00000000 },
+       { 0x001c04,  16, 0x10, 0x00000000 },
+       { 0x001c08,  16, 0x10, 0x00000000 },
+       { 0x001c0c,  16, 0x10, 0x00000000 },
+       { 0x001d00,  16, 0x10, 0x00000000 },
+       { 0x001d04,  16, 0x10, 0x00000000 },
+       { 0x001d08,  16, 0x10, 0x00000000 },
+       { 0x001d0c,  16, 0x10, 0x00000000 },
+       { 0x001f00,  16, 0x08, 0x00000000 },
+       { 0x001f04,  16, 0x08, 0x00000000 },
+       { 0x001f80,  16, 0x08, 0x00000000 },
+       { 0x001f84,  16, 0x08, 0x00000000 },
+       { 0x002000,   1, 0x04, 0x00000000 },
+       { 0x002040,   1, 0x04, 0x00000011 },
+       { 0x002080,   1, 0x04, 0x00000020 },
+       { 0x0020c0,   1, 0x04, 0x00000030 },
+       { 0x002100,   1, 0x04, 0x00000040 },
+       { 0x002140,   1, 0x04, 0x00000051 },
+       { 0x00200c,   6, 0x40, 0x00000001 },
+       { 0x002010,   1, 0x04, 0x00000000 },
+       { 0x002050,   1, 0x04, 0x00000000 },
+       { 0x002090,   1, 0x04, 0x00000001 },
+       { 0x0020d0,   1, 0x04, 0x00000002 },
+       { 0x002110,   1, 0x04, 0x00000003 },
+       { 0x002150,   1, 0x04, 0x00000004 },
+       { 0x000380,   4, 0x20, 0x00000000 },
+       { 0x000384,   4, 0x20, 0x00000000 },
+       { 0x000388,   4, 0x20, 0x00000000 },
+       { 0x00038c,   4, 0x20, 0x00000000 },
+       { 0x000700,   4, 0x10, 0x00000000 },
+       { 0x000704,   4, 0x10, 0x00000000 },
+       { 0x000708,   4, 0x10, 0x00000000 },
+       { 0x002800, 128, 0x04, 0x00000000 },
+       { 0x000a00,  16, 0x20, 0x00000000 },
+       { 0x000a04,  16, 0x20, 0x00000000 },
+       { 0x000a08,  16, 0x20, 0x00000000 },
+       { 0x000a0c,  16, 0x20, 0x00000000 },
+       { 0x000a10,  16, 0x20, 0x00000000 },
+       { 0x000a14,  16, 0x20, 0x00000000 },
+       { 0x000c00,  16, 0x10, 0x00000000 },
+       { 0x000c04,  16, 0x10, 0x00000000 },
+       { 0x000c08,  16, 0x10, 0x00000000 },
+       { 0x000c0c,  16, 0x10, 0x3f800000 },
+       { 0x000d00,   8, 0x08, 0xffff0000 },
+       { 0x000d04,   8, 0x08, 0xffff0000 },
+       { 0x000e00,  16, 0x10, 0x00000000 },
+       { 0x000e04,  16, 0x10, 0xffff0000 },
+       { 0x000e08,  16, 0x10, 0xffff0000 },
+       { 0x000d40,   4, 0x08, 0x00000000 },
+       { 0x000d44,   4, 0x08, 0x00000000 },
+       { 0x001e00,   8, 0x20, 0x00000001 },
+       { 0x001e04,   8, 0x20, 0x00000001 },
+       { 0x001e08,   8, 0x20, 0x00000002 },
+       { 0x001e0c,   8, 0x20, 0x00000001 },
+       { 0x001e10,   8, 0x20, 0x00000001 },
+       { 0x001e14,   8, 0x20, 0x00000002 },
+       { 0x001e18,   8, 0x20, 0x00000001 },
+       { 0x001480,   8, 0x10, 0x00000000 },
+       { 0x001484,   8, 0x10, 0x00000000 },
+       { 0x001488,   8, 0x10, 0x00000000 },
+       { 0x003400, 128, 0x04, 0x00000000 },
+       { 0x00030c,   1, 0x04, 0x00000001 },
+       { 0x001944,   1, 0x04, 0x00000000 },
+       { 0x001514,   1, 0x04, 0x00000000 },
+       { 0x000d68,   1, 0x04, 0x0000ffff },
+       { 0x00121c,   1, 0x04, 0x0fac6881 },
+       { 0x000fac,   1, 0x04, 0x00000001 },
+       { 0x001538,   1, 0x04, 0x00000001 },
+       { 0x000fe0,   2, 0x04, 0x00000000 },
+       { 0x000fe8,   1, 0x04, 0x00000014 },
+       { 0x000fec,   1, 0x04, 0x00000040 },
+       { 0x000ff0,   1, 0x04, 0x00000000 },
+       { 0x00179c,   1, 0x04, 0x00000000 },
+       { 0x001228,   1, 0x04, 0x00000400 },
+       { 0x00122c,   1, 0x04, 0x00000300 },
+       { 0x001230,   1, 0x04, 0x00010001 },
+       { 0x0007f8,   1, 0x04, 0x00000000 },
+       { 0x0015b4,   1, 0x04, 0x00000001 },
+       { 0x0015cc,   1, 0x04, 0x00000000 },
+       { 0x001534,   1, 0x04, 0x00000000 },
+       { 0x000754,   1, 0x04, 0x00000001 },
+       { 0x000fb0,   1, 0x04, 0x00000000 },
+       { 0x0015d0,   1, 0x04, 0x00000000 },
+       { 0x00153c,   1, 0x04, 0x00000000 },
+       { 0x0016b4,   1, 0x04, 0x00000003 },
+       { 0x000fbc,   4, 0x04, 0x0000ffff },
+       { 0x000df8,   2, 0x04, 0x00000000 },
+       { 0x001948,   1, 0x04, 0x00000000 },
+       { 0x001970,   1, 0x04, 0x00000001 },
+       { 0x00161c,   1, 0x04, 0x000009f0 },
+       { 0x000dcc,   1, 0x04, 0x00000010 },
+       { 0x0015e4,   1, 0x04, 0x00000000 },
+       { 0x001160,  32, 0x04, 0x25e00040 },
+       { 0x001880,  32, 0x04, 0x00000000 },
+       { 0x000f84,   2, 0x04, 0x00000000 },
+       { 0x0017c8,   2, 0x04, 0x00000000 },
+       { 0x0017d0,   1, 0x04, 0x000000ff },
+       { 0x0017d4,   1, 0x04, 0xffffffff },
+       { 0x0017d8,   1, 0x04, 0x00000002 },
+       { 0x0017dc,   1, 0x04, 0x00000000 },
+       { 0x0015f4,   2, 0x04, 0x00000000 },
+       { 0x001434,   2, 0x04, 0x00000000 },
+       { 0x000d74,   1, 0x04, 0x00000000 },
+       { 0x0013a4,   1, 0x04, 0x00000000 },
+       { 0x001318,   1, 0x04, 0x00000001 },
+       { 0x001080,   2, 0x04, 0x00000000 },
+       { 0x001088,   2, 0x04, 0x00000001 },
+       { 0x001090,   1, 0x04, 0x00000000 },
+       { 0x001094,   1, 0x04, 0x00000001 },
+       { 0x001098,   1, 0x04, 0x00000000 },
+       { 0x00109c,   1, 0x04, 0x00000001 },
+       { 0x0010a0,   2, 0x04, 0x00000000 },
+       { 0x001644,   1, 0x04, 0x00000000 },
+       { 0x000748,   1, 0x04, 0x00000000 },
+       { 0x000de8,   1, 0x04, 0x00000000 },
+       { 0x001648,   1, 0x04, 0x00000000 },
+       { 0x0012a4,   1, 0x04, 0x00000000 },
+       { 0x001120,   4, 0x04, 0x00000000 },
+       { 0x001118,   1, 0x04, 0x00000000 },
+       { 0x00164c,   1, 0x04, 0x00000000 },
+       { 0x001658,   1, 0x04, 0x00000000 },
+       { 0x001910,   1, 0x04, 0x00000290 },
+       { 0x001518,   1, 0x04, 0x00000000 },
+       { 0x00165c,   1, 0x04, 0x00000001 },
+       { 0x001520,   1, 0x04, 0x00000000 },
+       { 0x001604,   1, 0x04, 0x00000000 },
+       { 0x001570,   1, 0x04, 0x00000000 },
+       { 0x0013b0,   2, 0x04, 0x3f800000 },
+       { 0x00020c,   1, 0x04, 0x00000000 },
+       { 0x001670,   1, 0x04, 0x30201000 },
+       { 0x001674,   1, 0x04, 0x70605040 },
+       { 0x001678,   1, 0x04, 0xb8a89888 },
+       { 0x00167c,   1, 0x04, 0xf8e8d8c8 },
+       { 0x00166c,   1, 0x04, 0x00000000 },
+       { 0x001680,   1, 0x04, 0x00ffff00 },
+       { 0x0012d0,   1, 0x04, 0x00000003 },
+       { 0x0012d4,   1, 0x04, 0x00000002 },
+       { 0x001684,   2, 0x04, 0x00000000 },
+       { 0x000dac,   2, 0x04, 0x00001b02 },
+       { 0x000db4,   1, 0x04, 0x00000000 },
+       { 0x00168c,   1, 0x04, 0x00000000 },
+       { 0x0015bc,   1, 0x04, 0x00000000 },
+       { 0x00156c,   1, 0x04, 0x00000000 },
+       { 0x00187c,   1, 0x04, 0x00000000 },
+       { 0x001110,   1, 0x04, 0x00000001 },
+       { 0x000dc0,   3, 0x04, 0x00000000 },
+       { 0x000f40,   5, 0x04, 0x00000000 },
+       { 0x001234,   1, 0x04, 0x00000000 },
+       { 0x001690,   1, 0x04, 0x00000000 },
+       { 0x000790,   5, 0x04, 0x00000000 },
+       { 0x00077c,   1, 0x04, 0x00000000 },
+       { 0x001000,   1, 0x04, 0x00000010 },
+       { 0x0010fc,   1, 0x04, 0x00000000 },
+       { 0x001290,   1, 0x04, 0x00000000 },
+       { 0x000218,   1, 0x04, 0x00000010 },
+       { 0x0012d8,   1, 0x04, 0x00000000 },
+       { 0x0012dc,   1, 0x04, 0x00000010 },
+       { 0x000d94,   1, 0x04, 0x00000001 },
+       { 0x00155c,   2, 0x04, 0x00000000 },
+       { 0x001564,   1, 0x04, 0x00000fff },
+       { 0x001574,   2, 0x04, 0x00000000 },
+       { 0x00157c,   1, 0x04, 0x000fffff },
+       { 0x001354,   1, 0x04, 0x00000000 },
+       { 0x001610,   1, 0x04, 0x00000012 },
+       { 0x001608,   2, 0x04, 0x00000000 },
+       { 0x00260c,   1, 0x04, 0x00000000 },
+       { 0x0007ac,   1, 0x04, 0x00000000 },
+       { 0x00162c,   1, 0x04, 0x00000003 },
+       { 0x000210,   1, 0x04, 0x00000000 },
+       { 0x000320,   1, 0x04, 0x00000000 },
+       { 0x000324,   6, 0x04, 0x3f800000 },
+       { 0x000750,   1, 0x04, 0x00000000 },
+       { 0x000760,   1, 0x04, 0x39291909 },
+       { 0x000764,   1, 0x04, 0x79695949 },
+       { 0x000768,   1, 0x04, 0xb9a99989 },
+       { 0x00076c,   1, 0x04, 0xf9e9d9c9 },
+       { 0x000770,   1, 0x04, 0x30201000 },
+       { 0x000774,   1, 0x04, 0x70605040 },
+       { 0x000778,   1, 0x04, 0x00009080 },
+       { 0x000780,   1, 0x04, 0x39291909 },
+       { 0x000784,   1, 0x04, 0x79695949 },
+       { 0x000788,   1, 0x04, 0xb9a99989 },
+       { 0x00078c,   1, 0x04, 0xf9e9d9c9 },
+       { 0x0007d0,   1, 0x04, 0x30201000 },
+       { 0x0007d4,   1, 0x04, 0x70605040 },
+       { 0x0007d8,   1, 0x04, 0x00009080 },
+       { 0x00037c,   1, 0x04, 0x00000001 },
+       { 0x000740,   2, 0x04, 0x00000000 },
+       { 0x002600,   1, 0x04, 0x00000000 },
+       { 0x001918,   1, 0x04, 0x00000000 },
+       { 0x00191c,   1, 0x04, 0x00000900 },
+       { 0x001920,   1, 0x04, 0x00000405 },
+       { 0x001308,   1, 0x04, 0x00000001 },
+       { 0x001924,   1, 0x04, 0x00000000 },
+       { 0x0013ac,   1, 0x04, 0x00000000 },
+       { 0x00192c,   1, 0x04, 0x00000001 },
+       { 0x00193c,   1, 0x04, 0x00002c1c },
+       { 0x000d7c,   1, 0x04, 0x00000000 },
+       { 0x000f8c,   1, 0x04, 0x00000000 },
+       { 0x0002c0,   1, 0x04, 0x00000001 },
+       { 0x001510,   1, 0x04, 0x00000000 },
+       { 0x001940,   1, 0x04, 0x00000000 },
+       { 0x000ff4,   2, 0x04, 0x00000000 },
+       { 0x00194c,   2, 0x04, 0x00000000 },
+       { 0x001968,   1, 0x04, 0x00000000 },
+       { 0x001590,   1, 0x04, 0x0000003f },
+       { 0x0007e8,   4, 0x04, 0x00000000 },
+       { 0x00196c,   1, 0x04, 0x00000011 },
+       { 0x0002e4,   1, 0x04, 0x0000b001 },
+       { 0x00036c,   2, 0x04, 0x00000000 },
+       { 0x00197c,   1, 0x04, 0x00000000 },
+       { 0x000fcc,   2, 0x04, 0x00000000 },
+       { 0x0002d8,   1, 0x04, 0x00000040 },
+       { 0x001980,   1, 0x04, 0x00000080 },
+       { 0x001504,   1, 0x04, 0x00000080 },
+       { 0x001984,   1, 0x04, 0x00000000 },
+       { 0x000f60,   1, 0x04, 0x00000000 },
+       { 0x000f64,   1, 0x04, 0x00400040 },
+       { 0x000f68,   1, 0x04, 0x00002212 },
+       { 0x000f6c,   1, 0x04, 0x08080203 },
+       { 0x001108,   1, 0x04, 0x00000008 },
+       { 0x000f70,   1, 0x04, 0x00080001 },
+       { 0x000ffc,   1, 0x04, 0x00000000 },
+       { 0x000300,   1, 0x04, 0x00000001 },
+       { 0x0013a8,   1, 0x04, 0x00000000 },
+       { 0x0012ec,   1, 0x04, 0x00000000 },
+       { 0x001310,   1, 0x04, 0x00000000 },
+       { 0x001314,   1, 0x04, 0x00000001 },
+       { 0x001380,   1, 0x04, 0x00000000 },
+       { 0x001384,   4, 0x04, 0x00000001 },
+       { 0x001394,   1, 0x04, 0x00000000 },
+       { 0x00139c,   1, 0x04, 0x00000000 },
+       { 0x001398,   1, 0x04, 0x00000000 },
+       { 0x001594,   1, 0x04, 0x00000000 },
+       { 0x001598,   4, 0x04, 0x00000001 },
+       { 0x000f54,   3, 0x04, 0x00000000 },
+       { 0x0019bc,   1, 0x04, 0x00000000 },
+       { 0x000f9c,   2, 0x04, 0x00000000 },
+       { 0x0012cc,   1, 0x04, 0x00000000 },
+       { 0x0012e8,   1, 0x04, 0x00000000 },
+       { 0x00130c,   1, 0x04, 0x00000001 },
+       { 0x001360,   8, 0x04, 0x00000000 },
+       { 0x00133c,   2, 0x04, 0x00000001 },
+       { 0x001344,   1, 0x04, 0x00000002 },
+       { 0x001348,   2, 0x04, 0x00000001 },
+       { 0x001350,   1, 0x04, 0x00000002 },
+       { 0x001358,   1, 0x04, 0x00000001 },
+       { 0x0012e4,   1, 0x04, 0x00000000 },
+       { 0x00131c,   4, 0x04, 0x00000000 },
+       { 0x0019c0,   1, 0x04, 0x00000000 },
+       { 0x001140,   1, 0x04, 0x00000000 },
+       { 0x000dd0,   1, 0x04, 0x00000000 },
+       { 0x000dd4,   1, 0x04, 0x00000001 },
+       { 0x0002f4,   1, 0x04, 0x00000000 },
+       { 0x0019c4,   1, 0x04, 0x00000000 },
+       { 0x0019c8,   1, 0x04, 0x00001500 },
+       { 0x00135c,   1, 0x04, 0x00000000 },
+       { 0x000f90,   1, 0x04, 0x00000000 },
+       { 0x0019e0,   8, 0x04, 0x00000001 },
+       { 0x0019cc,   1, 0x04, 0x00000001 },
+       { 0x0015b8,   1, 0x04, 0x00000000 },
+       { 0x001a00,   1, 0x04, 0x00001111 },
+       { 0x001a04,   7, 0x04, 0x00000000 },
+       { 0x000d6c,   2, 0x04, 0xffff0000 },
+       { 0x0010f8,   1, 0x04, 0x00001010 },
+       { 0x000d80,   5, 0x04, 0x00000000 },
+       { 0x000da0,   1, 0x04, 0x00000000 },
+       { 0x0007a4,   2, 0x04, 0x00000000 },
+       { 0x001508,   1, 0x04, 0x80000000 },
+       { 0x00150c,   1, 0x04, 0x40000000 },
+       { 0x001668,   1, 0x04, 0x00000000 },
+       { 0x000318,   2, 0x04, 0x00000008 },
+       { 0x000d9c,   1, 0x04, 0x00000001 },
+       { 0x000f14,   1, 0x04, 0x00000000 },
+       { 0x000374,   1, 0x04, 0x00000000 },
+       { 0x000378,   1, 0x04, 0x0000000c },
+       { 0x0007dc,   1, 0x04, 0x00000000 },
+       { 0x00074c,   1, 0x04, 0x00000055 },
+       { 0x001420,   1, 0x04, 0x00000003 },
+       { 0x001008,   1, 0x04, 0x00000008 },
+       { 0x00100c,   1, 0x04, 0x00000040 },
+       { 0x001010,   1, 0x04, 0x0000012c },
+       { 0x000d60,   1, 0x04, 0x00000040 },
+       { 0x001018,   1, 0x04, 0x00000020 },
+       { 0x00101c,   1, 0x04, 0x00000001 },
+       { 0x001020,   1, 0x04, 0x00000020 },
+       { 0x001024,   1, 0x04, 0x00000001 },
+       { 0x001444,   3, 0x04, 0x00000000 },
+       { 0x000360,   1, 0x04, 0x20164010 },
+       { 0x000364,   1, 0x04, 0x00000020 },
+       { 0x000368,   1, 0x04, 0x00000000 },
+       { 0x000da8,   1, 0x04, 0x00000030 },
+       { 0x000de4,   1, 0x04, 0x00000000 },
+       { 0x000204,   1, 0x04, 0x00000006 },
+       { 0x0002d0,   1, 0x04, 0x003fffff },
+       { 0x001220,   1, 0x04, 0x00000005 },
+       { 0x000fdc,   1, 0x04, 0x00000000 },
+       { 0x000f98,   1, 0x04, 0x00400008 },
+       { 0x001284,   1, 0x04, 0x08000080 },
+       { 0x001450,   1, 0x04, 0x00400008 },
+       { 0x001454,   1, 0x04, 0x08000080 },
+       { 0x000214,   1, 0x04, 0x00000000 },
+       {}
+};
+
+static const struct gf100_gr_pack
+gm107_grctx_pack_mthd[] = {
+       { gm107_grctx_init_b097_0, 0xb097 },
+       { gf100_grctx_init_902d_0, 0x902d },
+       {}
+};
+
+static const struct gf100_gr_init
+gm107_grctx_init_fe_0[] = {
+       { 0x404004,   8, 0x04, 0x00000000 },
+       { 0x404024,   1, 0x04, 0x0000e000 },
+       { 0x404028,   8, 0x04, 0x00000000 },
+       { 0x4040a8,   8, 0x04, 0x00000000 },
+       { 0x4040c8,   1, 0x04, 0xf800008f },
+       { 0x4040d0,   6, 0x04, 0x00000000 },
+       { 0x4040f8,   1, 0x04, 0x00000000 },
+       { 0x404100,  10, 0x04, 0x00000000 },
+       { 0x404130,   2, 0x04, 0x00000000 },
+       { 0x404150,   1, 0x04, 0x0000002e },
+       { 0x404154,   1, 0x04, 0x00000400 },
+       { 0x404158,   1, 0x04, 0x00000200 },
+       { 0x404164,   1, 0x04, 0x00000045 },
+       { 0x40417c,   2, 0x04, 0x00000000 },
+       { 0x404194,   1, 0x04, 0x01000700 },
+       { 0x4041a0,   4, 0x04, 0x00000000 },
+       { 0x404200,   4, 0x04, 0x00000000 },
+       {}
+};
+
+static const struct gf100_gr_init
+gm107_grctx_init_ds_0[] = {
+       { 0x405800,   1, 0x04, 0x0f8001bf },
+       { 0x405830,   1, 0x04, 0x0aa01000 },
+       { 0x405834,   1, 0x04, 0x08000000 },
+       { 0x405838,   1, 0x04, 0x00000000 },
+       { 0x405854,   1, 0x04, 0x00000000 },
+       { 0x405870,   4, 0x04, 0x00000001 },
+       { 0x405a00,   2, 0x04, 0x00000000 },
+       { 0x405a18,   1, 0x04, 0x00000000 },
+       { 0x405a1c,   1, 0x04, 0x000000ff },
+       {}
+};
+
+static const struct gf100_gr_init
+gm107_grctx_init_pd_0[] = {
+       { 0x406020,   1, 0x04, 0x07410001 },
+       { 0x406028,   4, 0x04, 0x00000001 },
+       { 0x4064a8,   1, 0x04, 0x00000000 },
+       { 0x4064ac,   1, 0x04, 0x00003fff },
+       { 0x4064b0,   3, 0x04, 0x00000000 },
+       { 0x4064c0,   1, 0x04, 0x80400280 },
+       { 0x4064c4,   1, 0x04, 0x0400ffff },
+       { 0x4064c8,   1, 0x04, 0x018001ff },
+       { 0x4064cc,   9, 0x04, 0x00000000 },
+       { 0x4064fc,   1, 0x04, 0x0000022a },
+       { 0x406500,   1, 0x04, 0x00000000 },
+       {}
+};
+
+static const struct gf100_gr_init
+gm107_grctx_init_be_0[] = {
+       { 0x408800,   1, 0x04, 0x32802a3c },
+       { 0x408804,   1, 0x04, 0x00000040 },
+       { 0x408808,   1, 0x04, 0x1003e005 },
+       { 0x408840,   1, 0x04, 0x0000000b },
+       { 0x408900,   1, 0x04, 0xb080b801 },
+       { 0x408904,   1, 0x04, 0x63038001 },
+       { 0x408908,   1, 0x04, 0x02c8102f },
+       { 0x408980,   1, 0x04, 0x0000011d },
+       {}
+};
+
+static const struct gf100_gr_pack
+gm107_grctx_pack_hub[] = {
+       { gf100_grctx_init_main_0 },
+       { gm107_grctx_init_fe_0 },
+       { gk110_grctx_init_pri_0 },
+       { gk104_grctx_init_memfmt_0 },
+       { gm107_grctx_init_ds_0 },
+       { gk110_grctx_init_cwd_0 },
+       { gm107_grctx_init_pd_0 },
+       { gk208_grctx_init_rstr2d_0 },
+       { gk104_grctx_init_scc_0 },
+       { gm107_grctx_init_be_0 },
+       {}
+};
+
+static const struct gf100_gr_init
+gm107_grctx_init_gpc_unk_0[] = {
+       { 0x418380,   1, 0x04, 0x00000056 },
+       {}
+};
+
+static const struct gf100_gr_init
+gm107_grctx_init_gpc_unk_1[] = {
+       { 0x418600,   1, 0x04, 0x0000007f },
+       { 0x418684,   1, 0x04, 0x0000001f },
+       { 0x418700,   1, 0x04, 0x00000002 },
+       { 0x418704,   1, 0x04, 0x00000080 },
+       { 0x418708,   1, 0x04, 0x40000000 },
+       { 0x41870c,   2, 0x04, 0x00000000 },
+       {}
+};
+
+static const struct gf100_gr_init
+gm107_grctx_init_setup_0[] = {
+       { 0x418800,   1, 0x04, 0x7006863a },
+       { 0x418810,   1, 0x04, 0x00000000 },
+       { 0x418828,   1, 0x04, 0x00000044 },
+       { 0x418830,   1, 0x04, 0x10000001 },
+       { 0x4188d8,   1, 0x04, 0x00000008 },
+       { 0x4188e0,   1, 0x04, 0x01000000 },
+       { 0x4188e8,   5, 0x04, 0x00000000 },
+       { 0x4188fc,   1, 0x04, 0x20100058 },
+       {}
+};
+
+static const struct gf100_gr_init
+gm107_grctx_init_gpc_unk_2[] = {
+       { 0x418d24,   1, 0x04, 0x00000000 },
+       { 0x418e00,   1, 0x04, 0x90000000 },
+       { 0x418e24,   1, 0x04, 0x00000000 },
+       { 0x418e28,   1, 0x04, 0x00000030 },
+       { 0x418e30,   1, 0x04, 0x00000000 },
+       { 0x418e34,   1, 0x04, 0x00010000 },
+       { 0x418e38,   1, 0x04, 0x00000000 },
+       { 0x418e40,  22, 0x04, 0x00000000 },
+       { 0x418ea0,   2, 0x04, 0x00000000 },
+       {}
+};
+
+static const struct gf100_gr_pack
+gm107_grctx_pack_gpc[] = {
+       { gm107_grctx_init_gpc_unk_0 },
+       { gk208_grctx_init_prop_0 },
+       { gm107_grctx_init_gpc_unk_1 },
+       { gm107_grctx_init_setup_0 },
+       { gf100_grctx_init_zcull_0 },
+       { gk208_grctx_init_crstr_0 },
+       { gk104_grctx_init_gpm_0 },
+       { gm107_grctx_init_gpc_unk_2 },
+       { gf100_grctx_init_gcc_0 },
+       {}
+};
+
+static const struct gf100_gr_init
+gm107_grctx_init_tex_0[] = {
+       { 0x419a00,   1, 0x04, 0x000300f0 },
+       { 0x419a04,   1, 0x04, 0x00000005 },
+       { 0x419a08,   1, 0x04, 0x00000421 },
+       { 0x419a0c,   1, 0x04, 0x00120000 },
+       { 0x419a10,   1, 0x04, 0x00000000 },
+       { 0x419a14,   1, 0x04, 0x00002200 },
+       { 0x419a1c,   1, 0x04, 0x0000c000 },
+       { 0x419a20,   1, 0x04, 0x20008a00 },
+       { 0x419a30,   1, 0x04, 0x00000001 },
+       { 0x419a3c,   1, 0x04, 0x00000002 },
+       { 0x419ac4,   1, 0x04, 0x00000000 },
+       {}
+};
+
+static const struct gf100_gr_init
+gm107_grctx_init_mpc_0[] = {
+       { 0x419c00,   1, 0x04, 0x0000001a },
+       { 0x419c04,   1, 0x04, 0x80000006 },
+       { 0x419c08,   1, 0x04, 0x00000002 },
+       { 0x419c20,   1, 0x04, 0x00000000 },
+       { 0x419c24,   1, 0x04, 0x00084210 },
+       { 0x419c28,   1, 0x04, 0x3efbefbe },
+       { 0x419c2c,   1, 0x04, 0x00000000 },
+       { 0x419c34,   1, 0x04, 0x01ff1ff3 },
+       { 0x419c3c,   1, 0x04, 0x00001919 },
+       {}
+};
+
+static const struct gf100_gr_init
+gm107_grctx_init_l1c_0[] = {
+       { 0x419c84,   1, 0x04, 0x00000020 },
+       {}
+};
+
+static const struct gf100_gr_init
+gm107_grctx_init_sm_0[] = {
+       { 0x419e04,   3, 0x04, 0x00000000 },
+       { 0x419e10,   1, 0x04, 0x00001c02 },
+       { 0x419e44,   1, 0x04, 0x00d3eff2 },
+       { 0x419e48,   1, 0x04, 0x00000000 },
+       { 0x419e4c,   1, 0x04, 0x0000007f },
+       { 0x419e50,   1, 0x04, 0x00000000 },
+       { 0x419e60,   4, 0x04, 0x00000000 },
+       { 0x419e74,  10, 0x04, 0x00000000 },
+       { 0x419eac,   1, 0x04, 0x0001cf8b },
+       { 0x419eb0,   1, 0x04, 0x00030300 },
+       { 0x419eb8,   1, 0x04, 0x00000000 },
+       { 0x419ef0,  24, 0x04, 0x00000000 },
+       { 0x419f68,   2, 0x04, 0x00000000 },
+       { 0x419f70,   1, 0x04, 0x00000020 },
+       { 0x419f78,   1, 0x04, 0x000003eb },
+       { 0x419f7c,   1, 0x04, 0x00000000 },
+       {}
+};
+
+static const struct gf100_gr_pack
+gm107_grctx_pack_tpc[] = {
+       { gf117_grctx_init_pe_0 },
+       { gm107_grctx_init_tex_0 },
+       { gm107_grctx_init_mpc_0 },
+       { gm107_grctx_init_l1c_0 },
+       { gm107_grctx_init_sm_0 },
+       {}
+};
+
+static const struct gf100_gr_init
+gm107_grctx_init_cbm_0[] = {
+       { 0x41bec0,   1, 0x04, 0x00000000 },
+       { 0x41bec4,   1, 0x04, 0x01050000 },
+       { 0x41bee4,   1, 0x04, 0x00000000 },
+       { 0x41bef0,   1, 0x04, 0x000003ff },
+       { 0x41bef4,   2, 0x04, 0x00000000 },
+       {}
+};
+
+static const struct gf100_gr_init
+gm107_grctx_init_wwdx_0[] = {
+       { 0x41bf00,   1, 0x04, 0x0a418820 },
+       { 0x41bf04,   1, 0x04, 0x062080e6 },
+       { 0x41bf08,   1, 0x04, 0x020398a4 },
+       { 0x41bf0c,   1, 0x04, 0x0e629062 },
+       { 0x41bf10,   1, 0x04, 0x0a418820 },
+       { 0x41bf14,   1, 0x04, 0x000000e6 },
+       { 0x41bfd0,   1, 0x04, 0x00900103 },
+       { 0x41bfe0,   1, 0x04, 0x80000000 },
+       { 0x41bfe4,   1, 0x04, 0x00000000 },
+       {}
+};
+
+static const struct gf100_gr_pack
+gm107_grctx_pack_ppc[] = {
+       { gk104_grctx_init_pes_0 },
+       { gm107_grctx_init_cbm_0 },
+       { gm107_grctx_init_wwdx_0 },
+       {}
+};
+
+/*******************************************************************************
+ * PGRAPH context implementation
+ ******************************************************************************/
+
+static void
+gm107_grctx_generate_bundle(struct gf100_grctx *info)
+{
+       const struct gf100_grctx_oclass *impl = gf100_grctx_impl(info->priv);
+       const u32 state_limit = min(impl->bundle_min_gpm_fifo_depth,
+                                   impl->bundle_size / 0x20);
+       const u32 token_limit = impl->bundle_token_limit;
+       const u32 access = NV_MEM_ACCESS_RW | NV_MEM_ACCESS_SYS;
+       const int s = 8;
+       const int b = mmio_vram(info, impl->bundle_size, (1 << s), access);
+       mmio_refn(info, 0x408004, 0x00000000, s, b);
+       mmio_refn(info, 0x408008, 0x80000000 | (impl->bundle_size >> s), 0, b);
+       mmio_refn(info, 0x418e24, 0x00000000, s, b);
+       mmio_refn(info, 0x418e28, 0x80000000 | (impl->bundle_size >> s), 0, b);
+       mmio_wr32(info, 0x4064c8, (state_limit << 16) | token_limit);
+}
+
+static void
+gm107_grctx_generate_pagepool(struct gf100_grctx *info)
+{
+       const struct gf100_grctx_oclass *impl = gf100_grctx_impl(info->priv);
+       const u32 access = NV_MEM_ACCESS_RW | NV_MEM_ACCESS_SYS;
+       const int s = 8;
+       const int b = mmio_vram(info, impl->pagepool_size, (1 << s), access);
+       mmio_refn(info, 0x40800c, 0x00000000, s, b);
+       mmio_wr32(info, 0x408010, 0x80000000);
+       mmio_refn(info, 0x419004, 0x00000000, s, b);
+       mmio_wr32(info, 0x419008, 0x00000000);
+       mmio_wr32(info, 0x4064cc, 0x80000000);
+       mmio_wr32(info, 0x418e30, 0x80000000); /* guess at it being related */
+}
+
+static void
+gm107_grctx_generate_attrib(struct gf100_grctx *info)
+{
+       struct gf100_gr_priv *priv = info->priv;
+       const struct gf100_grctx_oclass *impl = (void *)gf100_grctx_impl(priv);
+       const u32  alpha = impl->alpha_nr;
+       const u32 attrib = impl->attrib_nr;
+       const u32   size = 0x20 * (impl->attrib_nr_max + impl->alpha_nr_max);
+       const u32 access = NV_MEM_ACCESS_RW;
+       const int s = 12;
+       const int b = mmio_vram(info, size * priv->tpc_total, (1 << s), access);
+       const int max_batches = 0xffff;
+       u32 bo = 0;
+       u32 ao = bo + impl->attrib_nr_max * priv->tpc_total;
+       int gpc, ppc, n = 0;
+
+       mmio_refn(info, 0x418810, 0x80000000, s, b);
+       mmio_refn(info, 0x419848, 0x10000000, s, b);
+       mmio_refn(info, 0x419c2c, 0x10000000, s, b);
+       mmio_wr32(info, 0x405830, (attrib << 16) | alpha);
+       mmio_wr32(info, 0x4064c4, ((alpha / 4) << 16) | max_batches);
+
+       for (gpc = 0; gpc < priv->gpc_nr; gpc++) {
+               for (ppc = 0; ppc < priv->ppc_nr[gpc]; ppc++, n++) {
+                       const u32 as =  alpha * priv->ppc_tpc_nr[gpc][ppc];
+                       const u32 bs = attrib * priv->ppc_tpc_nr[gpc][ppc];
+                       const u32 u = 0x418ea0 + (n * 0x04);
+                       const u32 o = PPC_UNIT(gpc, ppc, 0);
+                       mmio_wr32(info, o + 0xc0, bs);
+                       mmio_wr32(info, o + 0xf4, bo);
+                       bo += impl->attrib_nr_max * priv->ppc_tpc_nr[gpc][ppc];
+                       mmio_wr32(info, o + 0xe4, as);
+                       mmio_wr32(info, o + 0xf8, ao);
+                       ao += impl->alpha_nr_max * priv->ppc_tpc_nr[gpc][ppc];
+                       mmio_wr32(info, u, (0x715 /*XXX*/ << 16) | bs);
+               }
+       }
+}
+
+static void
+gm107_grctx_generate_tpcid(struct gf100_gr_priv *priv)
+{
+       int gpc, tpc, id;
+
+       for (tpc = 0, id = 0; tpc < 4; tpc++) {
+               for (gpc = 0; gpc < priv->gpc_nr; gpc++) {
+                       if (tpc < priv->tpc_nr[gpc]) {
+                               nv_wr32(priv, TPC_UNIT(gpc, tpc, 0x698), id);
+                               nv_wr32(priv, GPC_UNIT(gpc, 0x0c10 + tpc * 4), id);
+                               nv_wr32(priv, TPC_UNIT(gpc, tpc, 0x088), id);
+                               id++;
+                       }
+
+                       nv_wr32(priv, GPC_UNIT(gpc, 0x0c08), priv->tpc_nr[gpc]);
+                       nv_wr32(priv, GPC_UNIT(gpc, 0x0c8c), priv->tpc_nr[gpc]);
+               }
+       }
+}
+
+static void
+gm107_grctx_generate_main(struct gf100_gr_priv *priv, struct gf100_grctx *info)
+{
+       struct gf100_grctx_oclass *oclass = (void *)nv_engine(priv)->cclass;
+       int i;
+
+       gf100_gr_mmio(priv, oclass->hub);
+       gf100_gr_mmio(priv, oclass->gpc);
+       gf100_gr_mmio(priv, oclass->zcull);
+       gf100_gr_mmio(priv, oclass->tpc);
+       gf100_gr_mmio(priv, oclass->ppc);
+
+       nv_wr32(priv, 0x404154, 0x00000000);
+
+       oclass->bundle(info);
+       oclass->pagepool(info);
+       oclass->attrib(info);
+       oclass->unkn(priv);
+
+       gm107_grctx_generate_tpcid(priv);
+       gf100_grctx_generate_r406028(priv);
+       gk104_grctx_generate_r418bb8(priv);
+       gf100_grctx_generate_r406800(priv);
+
+       nv_wr32(priv, 0x4064d0, 0x00000001);
+       for (i = 1; i < 8; i++)
+               nv_wr32(priv, 0x4064d0 + (i * 0x04), 0x00000000);
+       nv_wr32(priv, 0x406500, 0x00000001);
+
+       nv_wr32(priv, 0x405b00, (priv->tpc_total << 8) | priv->gpc_nr);
+
+       if (priv->gpc_nr == 1) {
+               nv_mask(priv, 0x408850, 0x0000000f, priv->tpc_nr[0]);
+               nv_mask(priv, 0x408958, 0x0000000f, priv->tpc_nr[0]);
+       } else {
+               nv_mask(priv, 0x408850, 0x0000000f, priv->gpc_nr);
+               nv_mask(priv, 0x408958, 0x0000000f, priv->gpc_nr);
+       }
+
+       gf100_gr_icmd(priv, oclass->icmd);
+       nv_wr32(priv, 0x404154, 0x00000400);
+       gf100_gr_mthd(priv, oclass->mthd);
+
+       nv_mask(priv, 0x419e00, 0x00808080, 0x00808080);
+       nv_mask(priv, 0x419ccc, 0x80000000, 0x80000000);
+       nv_mask(priv, 0x419f80, 0x80000000, 0x80000000);
+       nv_mask(priv, 0x419f88, 0x80000000, 0x80000000);
+}
+
+struct nvkm_oclass *
+gm107_grctx_oclass = &(struct gf100_grctx_oclass) {
+       .base.handle = NV_ENGCTX(GR, 0x08),
+       .base.ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = gf100_gr_context_ctor,
+               .dtor = gf100_gr_context_dtor,
+               .init = _nvkm_gr_context_init,
+               .fini = _nvkm_gr_context_fini,
+               .rd32 = _nvkm_gr_context_rd32,
+               .wr32 = _nvkm_gr_context_wr32,
+       },
+       .main  = gm107_grctx_generate_main,
+       .unkn  = gk104_grctx_generate_unkn,
+       .hub   = gm107_grctx_pack_hub,
+       .gpc   = gm107_grctx_pack_gpc,
+       .zcull = gf100_grctx_pack_zcull,
+       .tpc   = gm107_grctx_pack_tpc,
+       .ppc   = gm107_grctx_pack_ppc,
+       .icmd  = gm107_grctx_pack_icmd,
+       .mthd  = gm107_grctx_pack_mthd,
+       .bundle = gm107_grctx_generate_bundle,
+       .bundle_size = 0x3000,
+       .bundle_min_gpm_fifo_depth = 0x180,
+       .bundle_token_limit = 0x2c0,
+       .pagepool = gm107_grctx_generate_pagepool,
+       .pagepool_size = 0x8000,
+       .attrib = gm107_grctx_generate_attrib,
+       .attrib_nr_max = 0xff0,
+       .attrib_nr = 0xaa0,
+       .alpha_nr_max = 0x1800,
+       .alpha_nr = 0x1000,
+}.base;
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/gr/ctxnv40.c b/drivers/gpu/drm/nouveau/nvkm/engine/gr/ctxnv40.c
new file mode 100644 (file)
index 0000000..dc31462
--- /dev/null
@@ -0,0 +1,694 @@
+/*
+ * 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
+ */
+
+/* NVIDIA context programs handle a number of other conditions which are
+ * not implemented in our versions.  It's not clear why NVIDIA context
+ * programs have this code, nor whether it's strictly necessary for
+ * correct operation.  We'll implement additional handling if/when we
+ * discover it's necessary.
+ *
+ * - On context save, NVIDIA set 0x400314 bit 0 to 1 if the "3D state"
+ *   flag is set, this gets saved into the context.
+ * - On context save, the context program for all cards load nsource
+ *   into a flag register and check for ILLEGAL_MTHD.  If it's set,
+ *   opcode 0x60000d is called before resuming normal operation.
+ * - Some context programs check more conditions than the above.  NV44
+ *   checks: ((nsource & 0x0857) || (0x400718 & 0x0100) || (intr & 0x0001))
+ *   and calls 0x60000d before resuming normal operation.
+ * - At the very beginning of NVIDIA's context programs, flag 9 is checked
+ *   and if true 0x800001 is called with count=0, pos=0, the flag is cleared
+ *   and then the ctxprog is aborted.  It looks like a complicated NOP,
+ *   its purpose is unknown.
+ * - In the section of code that loads the per-vs state, NVIDIA check
+ *   flag 10.  If it's set, they only transfer the small 0x300 byte block
+ *   of state + the state for a single vs as opposed to the state for
+ *   all vs units.  It doesn't seem likely that it'll occur in normal
+ *   operation, especially seeing as it appears NVIDIA may have screwed
+ *   up the ctxprogs for some cards and have an invalid instruction
+ *   rather than a cp_lsr(ctx, dwords_for_1_vs_unit) instruction.
+ * - There's a number of places where context offset 0 (where we place
+ *   the PRAMIN offset of the context) is loaded into either 0x408000,
+ *   0x408004 or 0x408008.  Not sure what's up there either.
+ * - The ctxprogs for some cards save 0x400a00 again during the cleanup
+ *   path for auto-loadctx.
+ */
+
+#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_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_STATUS                ((3 * 32) + 0)
+#define CP_FLAG_STATUS_IDLE           0
+#define CP_FLAG_STATUS_BUSY           1
+#define CP_FLAG_AUTO_SAVE             ((3 * 32) + 4)
+#define CP_FLAG_AUTO_SAVE_NOT_PENDING 0
+#define CP_FLAG_AUTO_SAVE_PENDING     1
+#define CP_FLAG_AUTO_LOAD             ((3 * 32) + 5)
+#define CP_FLAG_AUTO_LOAD_NOT_PENDING 0
+#define CP_FLAG_AUTO_LOAD_PENDING     1
+#define CP_FLAG_UNK54                 ((3 * 32) + 6)
+#define CP_FLAG_UNK54_CLEAR           0
+#define CP_FLAG_UNK54_SET             1
+#define CP_FLAG_ALWAYS                ((3 * 32) + 8)
+#define CP_FLAG_ALWAYS_FALSE          0
+#define CP_FLAG_ALWAYS_TRUE           1
+#define CP_FLAG_UNK57                 ((3 * 32) + 9)
+#define CP_FLAG_UNK57_CLEAR           0
+#define CP_FLAG_UNK57_SET             1
+
+#define CP_CTX                   0x00100000
+#define CP_CTX_COUNT             0x000fc000
+#define CP_CTX_COUNT_SHIFT               14
+#define CP_CTX_REG               0x00003fff
+#define CP_LOAD_SR               0x00200000
+#define CP_LOAD_SR_VALUE         0x000fffff
+#define CP_BRA                   0x00400000
+#define CP_BRA_IP                0x0000ff00
+#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_NEXT_TO_SWAP          0x00600007
+#define CP_NEXT_TO_CURRENT       0x00600009
+#define CP_SET_CONTEXT_POINTER   0x0060000a
+#define CP_END                   0x0060000e
+#define CP_LOAD_MAGIC_UNK01      0x00800001 /* unknown */
+#define CP_LOAD_MAGIC_NV44TCL    0x00800029 /* per-vs state (0x4497) */
+#define CP_LOAD_MAGIC_NV40TCL    0x00800041 /* per-vs state (0x4097) */
+
+#include "ctxnv40.h"
+#include "nv40.h"
+#include <core/device.h>
+
+/* TODO:
+ *  - get vs count from 0x1540
+ */
+
+static int
+nv40_gr_vs_count(struct nvkm_device *device)
+{
+
+       switch (device->chipset) {
+       case 0x47:
+       case 0x49:
+       case 0x4b:
+               return 8;
+       case 0x40:
+               return 6;
+       case 0x41:
+       case 0x42:
+               return 5;
+       case 0x43:
+       case 0x44:
+       case 0x46:
+       case 0x4a:
+               return 3;
+       case 0x4c:
+       case 0x4e:
+       case 0x67:
+       default:
+               return 1;
+       }
+}
+
+
+enum cp_label {
+       cp_check_load = 1,
+       cp_setup_auto_load,
+       cp_setup_load,
+       cp_setup_save,
+       cp_swap_state,
+       cp_swap_state3d_3_is_save,
+       cp_prepare_exit,
+       cp_exit,
+};
+
+static void
+nv40_gr_construct_general(struct nvkm_grctx *ctx)
+{
+       struct nvkm_device *device = ctx->device;
+       int i;
+
+       cp_ctx(ctx, 0x4000a4, 1);
+       gr_def(ctx, 0x4000a4, 0x00000008);
+       cp_ctx(ctx, 0x400144, 58);
+       gr_def(ctx, 0x400144, 0x00000001);
+       cp_ctx(ctx, 0x400314, 1);
+       gr_def(ctx, 0x400314, 0x00000000);
+       cp_ctx(ctx, 0x400400, 10);
+       cp_ctx(ctx, 0x400480, 10);
+       cp_ctx(ctx, 0x400500, 19);
+       gr_def(ctx, 0x400514, 0x00040000);
+       gr_def(ctx, 0x400524, 0x55555555);
+       gr_def(ctx, 0x400528, 0x55555555);
+       gr_def(ctx, 0x40052c, 0x55555555);
+       gr_def(ctx, 0x400530, 0x55555555);
+       cp_ctx(ctx, 0x400560, 6);
+       gr_def(ctx, 0x400568, 0x0000ffff);
+       gr_def(ctx, 0x40056c, 0x0000ffff);
+       cp_ctx(ctx, 0x40057c, 5);
+       cp_ctx(ctx, 0x400710, 3);
+       gr_def(ctx, 0x400710, 0x20010001);
+       gr_def(ctx, 0x400714, 0x0f73ef00);
+       cp_ctx(ctx, 0x400724, 1);
+       gr_def(ctx, 0x400724, 0x02008821);
+       cp_ctx(ctx, 0x400770, 3);
+       if (device->chipset == 0x40) {
+               cp_ctx(ctx, 0x400814, 4);
+               cp_ctx(ctx, 0x400828, 5);
+               cp_ctx(ctx, 0x400840, 5);
+               gr_def(ctx, 0x400850, 0x00000040);
+               cp_ctx(ctx, 0x400858, 4);
+               gr_def(ctx, 0x400858, 0x00000040);
+               gr_def(ctx, 0x40085c, 0x00000040);
+               gr_def(ctx, 0x400864, 0x80000000);
+               cp_ctx(ctx, 0x40086c, 9);
+               gr_def(ctx, 0x40086c, 0x80000000);
+               gr_def(ctx, 0x400870, 0x80000000);
+               gr_def(ctx, 0x400874, 0x80000000);
+               gr_def(ctx, 0x400878, 0x80000000);
+               gr_def(ctx, 0x400888, 0x00000040);
+               gr_def(ctx, 0x40088c, 0x80000000);
+               cp_ctx(ctx, 0x4009c0, 8);
+               gr_def(ctx, 0x4009cc, 0x80000000);
+               gr_def(ctx, 0x4009dc, 0x80000000);
+       } else {
+               cp_ctx(ctx, 0x400840, 20);
+               if (nv44_gr_class(ctx->device)) {
+                       for (i = 0; i < 8; i++)
+                               gr_def(ctx, 0x400860 + (i * 4), 0x00000001);
+               }
+               gr_def(ctx, 0x400880, 0x00000040);
+               gr_def(ctx, 0x400884, 0x00000040);
+               gr_def(ctx, 0x400888, 0x00000040);
+               cp_ctx(ctx, 0x400894, 11);
+               gr_def(ctx, 0x400894, 0x00000040);
+               if (!nv44_gr_class(ctx->device)) {
+                       for (i = 0; i < 8; i++)
+                               gr_def(ctx, 0x4008a0 + (i * 4), 0x80000000);
+               }
+               cp_ctx(ctx, 0x4008e0, 2);
+               cp_ctx(ctx, 0x4008f8, 2);
+               if (device->chipset == 0x4c ||
+                   (device->chipset & 0xf0) == 0x60)
+                       cp_ctx(ctx, 0x4009f8, 1);
+       }
+       cp_ctx(ctx, 0x400a00, 73);
+       gr_def(ctx, 0x400b0c, 0x0b0b0b0c);
+       cp_ctx(ctx, 0x401000, 4);
+       cp_ctx(ctx, 0x405004, 1);
+       switch (device->chipset) {
+       case 0x47:
+       case 0x49:
+       case 0x4b:
+               cp_ctx(ctx, 0x403448, 1);
+               gr_def(ctx, 0x403448, 0x00001010);
+               break;
+       default:
+               cp_ctx(ctx, 0x403440, 1);
+               switch (device->chipset) {
+               case 0x40:
+                       gr_def(ctx, 0x403440, 0x00000010);
+                       break;
+               case 0x44:
+               case 0x46:
+               case 0x4a:
+                       gr_def(ctx, 0x403440, 0x00003010);
+                       break;
+               case 0x41:
+               case 0x42:
+               case 0x43:
+               case 0x4c:
+               case 0x4e:
+               case 0x67:
+               default:
+                       gr_def(ctx, 0x403440, 0x00001010);
+                       break;
+               }
+               break;
+       }
+}
+
+static void
+nv40_gr_construct_state3d(struct nvkm_grctx *ctx)
+{
+       struct nvkm_device *device = ctx->device;
+       int i;
+
+       if (device->chipset == 0x40) {
+               cp_ctx(ctx, 0x401880, 51);
+               gr_def(ctx, 0x401940, 0x00000100);
+       } else
+       if (device->chipset == 0x46 || device->chipset == 0x47 ||
+           device->chipset == 0x49 || device->chipset == 0x4b) {
+               cp_ctx(ctx, 0x401880, 32);
+               for (i = 0; i < 16; i++)
+                       gr_def(ctx, 0x401880 + (i * 4), 0x00000111);
+               if (device->chipset == 0x46)
+                       cp_ctx(ctx, 0x401900, 16);
+               cp_ctx(ctx, 0x401940, 3);
+       }
+       cp_ctx(ctx, 0x40194c, 18);
+       gr_def(ctx, 0x401954, 0x00000111);
+       gr_def(ctx, 0x401958, 0x00080060);
+       gr_def(ctx, 0x401974, 0x00000080);
+       gr_def(ctx, 0x401978, 0xffff0000);
+       gr_def(ctx, 0x40197c, 0x00000001);
+       gr_def(ctx, 0x401990, 0x46400000);
+       if (device->chipset == 0x40) {
+               cp_ctx(ctx, 0x4019a0, 2);
+               cp_ctx(ctx, 0x4019ac, 5);
+       } else {
+               cp_ctx(ctx, 0x4019a0, 1);
+               cp_ctx(ctx, 0x4019b4, 3);
+       }
+       gr_def(ctx, 0x4019bc, 0xffff0000);
+       switch (device->chipset) {
+       case 0x46:
+       case 0x47:
+       case 0x49:
+       case 0x4b:
+               cp_ctx(ctx, 0x4019c0, 18);
+               for (i = 0; i < 16; i++)
+                       gr_def(ctx, 0x4019c0 + (i * 4), 0x88888888);
+               break;
+       }
+       cp_ctx(ctx, 0x401a08, 8);
+       gr_def(ctx, 0x401a10, 0x0fff0000);
+       gr_def(ctx, 0x401a14, 0x0fff0000);
+       gr_def(ctx, 0x401a1c, 0x00011100);
+       cp_ctx(ctx, 0x401a2c, 4);
+       cp_ctx(ctx, 0x401a44, 26);
+       for (i = 0; i < 16; i++)
+               gr_def(ctx, 0x401a44 + (i * 4), 0x07ff0000);
+       gr_def(ctx, 0x401a8c, 0x4b7fffff);
+       if (device->chipset == 0x40) {
+               cp_ctx(ctx, 0x401ab8, 3);
+       } else {
+               cp_ctx(ctx, 0x401ab8, 1);
+               cp_ctx(ctx, 0x401ac0, 1);
+       }
+       cp_ctx(ctx, 0x401ad0, 8);
+       gr_def(ctx, 0x401ad0, 0x30201000);
+       gr_def(ctx, 0x401ad4, 0x70605040);
+       gr_def(ctx, 0x401ad8, 0xb8a89888);
+       gr_def(ctx, 0x401adc, 0xf8e8d8c8);
+       cp_ctx(ctx, 0x401b10, device->chipset == 0x40 ? 2 : 1);
+       gr_def(ctx, 0x401b10, 0x40100000);
+       cp_ctx(ctx, 0x401b18, device->chipset == 0x40 ? 6 : 5);
+       gr_def(ctx, 0x401b28, device->chipset == 0x40 ?
+                             0x00000004 : 0x00000000);
+       cp_ctx(ctx, 0x401b30, 25);
+       gr_def(ctx, 0x401b34, 0x0000ffff);
+       gr_def(ctx, 0x401b68, 0x435185d6);
+       gr_def(ctx, 0x401b6c, 0x2155b699);
+       gr_def(ctx, 0x401b70, 0xfedcba98);
+       gr_def(ctx, 0x401b74, 0x00000098);
+       gr_def(ctx, 0x401b84, 0xffffffff);
+       gr_def(ctx, 0x401b88, 0x00ff7000);
+       gr_def(ctx, 0x401b8c, 0x0000ffff);
+       if (device->chipset != 0x44 && device->chipset != 0x4a &&
+           device->chipset != 0x4e)
+               cp_ctx(ctx, 0x401b94, 1);
+       cp_ctx(ctx, 0x401b98, 8);
+       gr_def(ctx, 0x401b9c, 0x00ff0000);
+       cp_ctx(ctx, 0x401bc0, 9);
+       gr_def(ctx, 0x401be0, 0x00ffff00);
+       cp_ctx(ctx, 0x401c00, 192);
+       for (i = 0; i < 16; i++) { /* fragment texture units */
+               gr_def(ctx, 0x401c40 + (i * 4), 0x00018488);
+               gr_def(ctx, 0x401c80 + (i * 4), 0x00028202);
+               gr_def(ctx, 0x401d00 + (i * 4), 0x0000aae4);
+               gr_def(ctx, 0x401d40 + (i * 4), 0x01012000);
+               gr_def(ctx, 0x401d80 + (i * 4), 0x00080008);
+               gr_def(ctx, 0x401e00 + (i * 4), 0x00100008);
+       }
+       for (i = 0; i < 4; i++) { /* vertex texture units */
+               gr_def(ctx, 0x401e90 + (i * 4), 0x0001bc80);
+               gr_def(ctx, 0x401ea0 + (i * 4), 0x00000202);
+               gr_def(ctx, 0x401ec0 + (i * 4), 0x00000008);
+               gr_def(ctx, 0x401ee0 + (i * 4), 0x00080008);
+       }
+       cp_ctx(ctx, 0x400f5c, 3);
+       gr_def(ctx, 0x400f5c, 0x00000002);
+       cp_ctx(ctx, 0x400f84, 1);
+}
+
+static void
+nv40_gr_construct_state3d_2(struct nvkm_grctx *ctx)
+{
+       struct nvkm_device *device = ctx->device;
+       int i;
+
+       cp_ctx(ctx, 0x402000, 1);
+       cp_ctx(ctx, 0x402404, device->chipset == 0x40 ? 1 : 2);
+       switch (device->chipset) {
+       case 0x40:
+               gr_def(ctx, 0x402404, 0x00000001);
+               break;
+       case 0x4c:
+       case 0x4e:
+       case 0x67:
+               gr_def(ctx, 0x402404, 0x00000020);
+               break;
+       case 0x46:
+       case 0x49:
+       case 0x4b:
+               gr_def(ctx, 0x402404, 0x00000421);
+               break;
+       default:
+               gr_def(ctx, 0x402404, 0x00000021);
+       }
+       if (device->chipset != 0x40)
+               gr_def(ctx, 0x402408, 0x030c30c3);
+       switch (device->chipset) {
+       case 0x44:
+       case 0x46:
+       case 0x4a:
+       case 0x4c:
+       case 0x4e:
+       case 0x67:
+               cp_ctx(ctx, 0x402440, 1);
+               gr_def(ctx, 0x402440, 0x00011001);
+               break;
+       default:
+               break;
+       }
+       cp_ctx(ctx, 0x402480, device->chipset == 0x40 ? 8 : 9);
+       gr_def(ctx, 0x402488, 0x3e020200);
+       gr_def(ctx, 0x40248c, 0x00ffffff);
+       switch (device->chipset) {
+       case 0x40:
+               gr_def(ctx, 0x402490, 0x60103f00);
+               break;
+       case 0x47:
+               gr_def(ctx, 0x402490, 0x40103f00);
+               break;
+       case 0x41:
+       case 0x42:
+       case 0x49:
+       case 0x4b:
+               gr_def(ctx, 0x402490, 0x20103f00);
+               break;
+       default:
+               gr_def(ctx, 0x402490, 0x0c103f00);
+               break;
+       }
+       gr_def(ctx, 0x40249c, device->chipset <= 0x43 ?
+                             0x00020000 : 0x00040000);
+       cp_ctx(ctx, 0x402500, 31);
+       gr_def(ctx, 0x402530, 0x00008100);
+       if (device->chipset == 0x40)
+               cp_ctx(ctx, 0x40257c, 6);
+       cp_ctx(ctx, 0x402594, 16);
+       cp_ctx(ctx, 0x402800, 17);
+       gr_def(ctx, 0x402800, 0x00000001);
+       switch (device->chipset) {
+       case 0x47:
+       case 0x49:
+       case 0x4b:
+               cp_ctx(ctx, 0x402864, 1);
+               gr_def(ctx, 0x402864, 0x00001001);
+               cp_ctx(ctx, 0x402870, 3);
+               gr_def(ctx, 0x402878, 0x00000003);
+               if (device->chipset != 0x47) { /* belong at end!! */
+                       cp_ctx(ctx, 0x402900, 1);
+                       cp_ctx(ctx, 0x402940, 1);
+                       cp_ctx(ctx, 0x402980, 1);
+                       cp_ctx(ctx, 0x4029c0, 1);
+                       cp_ctx(ctx, 0x402a00, 1);
+                       cp_ctx(ctx, 0x402a40, 1);
+                       cp_ctx(ctx, 0x402a80, 1);
+                       cp_ctx(ctx, 0x402ac0, 1);
+               }
+               break;
+       case 0x40:
+               cp_ctx(ctx, 0x402844, 1);
+               gr_def(ctx, 0x402844, 0x00000001);
+               cp_ctx(ctx, 0x402850, 1);
+               break;
+       default:
+               cp_ctx(ctx, 0x402844, 1);
+               gr_def(ctx, 0x402844, 0x00001001);
+               cp_ctx(ctx, 0x402850, 2);
+               gr_def(ctx, 0x402854, 0x00000003);
+               break;
+       }
+
+       cp_ctx(ctx, 0x402c00, 4);
+       gr_def(ctx, 0x402c00, device->chipset == 0x40 ?
+                             0x80800001 : 0x00888001);
+       switch (device->chipset) {
+       case 0x47:
+       case 0x49:
+       case 0x4b:
+               cp_ctx(ctx, 0x402c20, 40);
+               for (i = 0; i < 32; i++)
+                       gr_def(ctx, 0x402c40 + (i * 4), 0xffffffff);
+               cp_ctx(ctx, 0x4030b8, 13);
+               gr_def(ctx, 0x4030dc, 0x00000005);
+               gr_def(ctx, 0x4030e8, 0x0000ffff);
+               break;
+       default:
+               cp_ctx(ctx, 0x402c10, 4);
+               if (device->chipset == 0x40)
+                       cp_ctx(ctx, 0x402c20, 36);
+               else
+               if (device->chipset <= 0x42)
+                       cp_ctx(ctx, 0x402c20, 24);
+               else
+               if (device->chipset <= 0x4a)
+                       cp_ctx(ctx, 0x402c20, 16);
+               else
+                       cp_ctx(ctx, 0x402c20, 8);
+               cp_ctx(ctx, 0x402cb0, device->chipset == 0x40 ? 12 : 13);
+               gr_def(ctx, 0x402cd4, 0x00000005);
+               if (device->chipset != 0x40)
+                       gr_def(ctx, 0x402ce0, 0x0000ffff);
+               break;
+       }
+
+       cp_ctx(ctx, 0x403400, device->chipset == 0x40 ? 4 : 3);
+       cp_ctx(ctx, 0x403410, device->chipset == 0x40 ? 4 : 3);
+       cp_ctx(ctx, 0x403420, nv40_gr_vs_count(ctx->device));
+       for (i = 0; i < nv40_gr_vs_count(ctx->device); i++)
+               gr_def(ctx, 0x403420 + (i * 4), 0x00005555);
+
+       if (device->chipset != 0x40) {
+               cp_ctx(ctx, 0x403600, 1);
+               gr_def(ctx, 0x403600, 0x00000001);
+       }
+       cp_ctx(ctx, 0x403800, 1);
+
+       cp_ctx(ctx, 0x403c18, 1);
+       gr_def(ctx, 0x403c18, 0x00000001);
+       switch (device->chipset) {
+       case 0x46:
+       case 0x47:
+       case 0x49:
+       case 0x4b:
+               cp_ctx(ctx, 0x405018, 1);
+               gr_def(ctx, 0x405018, 0x08e00001);
+               cp_ctx(ctx, 0x405c24, 1);
+               gr_def(ctx, 0x405c24, 0x000e3000);
+               break;
+       }
+       if (device->chipset != 0x4e)
+               cp_ctx(ctx, 0x405800, 11);
+       cp_ctx(ctx, 0x407000, 1);
+}
+
+static void
+nv40_gr_construct_state3d_3(struct nvkm_grctx *ctx)
+{
+       int len = nv44_gr_class(ctx->device) ? 0x0084 : 0x0684;
+
+       cp_out (ctx, 0x300000);
+       cp_lsr (ctx, len - 4);
+       cp_bra (ctx, SWAP_DIRECTION, SAVE, cp_swap_state3d_3_is_save);
+       cp_lsr (ctx, len);
+       cp_name(ctx, cp_swap_state3d_3_is_save);
+       cp_out (ctx, 0x800001);
+
+       ctx->ctxvals_pos += len;
+}
+
+static void
+nv40_gr_construct_shader(struct nvkm_grctx *ctx)
+{
+       struct nvkm_device *device = ctx->device;
+       struct nvkm_gpuobj *obj = ctx->data;
+       int vs, vs_nr, vs_len, vs_nr_b0, vs_nr_b1, b0_offset, b1_offset;
+       int offset, i;
+
+       vs_nr    = nv40_gr_vs_count(ctx->device);
+       vs_nr_b0 = 363;
+       vs_nr_b1 = device->chipset == 0x40 ? 128 : 64;
+       if (device->chipset == 0x40) {
+               b0_offset = 0x2200/4; /* 33a0 */
+               b1_offset = 0x55a0/4; /* 1500 */
+               vs_len = 0x6aa0/4;
+       } else
+       if (device->chipset == 0x41 || device->chipset == 0x42) {
+               b0_offset = 0x2200/4; /* 2200 */
+               b1_offset = 0x4400/4; /* 0b00 */
+               vs_len = 0x4f00/4;
+       } else {
+               b0_offset = 0x1d40/4; /* 2200 */
+               b1_offset = 0x3f40/4; /* 0b00 : 0a40 */
+               vs_len = nv44_gr_class(device) ? 0x4980/4 : 0x4a40/4;
+       }
+
+       cp_lsr(ctx, vs_len * vs_nr + 0x300/4);
+       cp_out(ctx, nv44_gr_class(device) ? 0x800029 : 0x800041);
+
+       offset = ctx->ctxvals_pos;
+       ctx->ctxvals_pos += (0x0300/4 + (vs_nr * vs_len));
+
+       if (ctx->mode != NVKM_GRCTX_VALS)
+               return;
+
+       offset += 0x0280/4;
+       for (i = 0; i < 16; i++, offset += 2)
+               nv_wo32(obj, offset * 4, 0x3f800000);
+
+       for (vs = 0; vs < vs_nr; vs++, offset += vs_len) {
+               for (i = 0; i < vs_nr_b0 * 6; i += 6)
+                       nv_wo32(obj, (offset + b0_offset + i) * 4, 0x00000001);
+               for (i = 0; i < vs_nr_b1 * 4; i += 4)
+                       nv_wo32(obj, (offset + b1_offset + i) * 4, 0x3f800000);
+       }
+}
+
+static void
+nv40_grctx_generate(struct nvkm_grctx *ctx)
+{
+       /* 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_wait(ctx, STATUS, IDLE);
+       cp_out (ctx, CP_NEXT_TO_SWAP);
+       cp_name(ctx, cp_setup_load);
+       cp_wait(ctx, STATUS, IDLE);
+       cp_set (ctx, SWAP_DIRECTION, LOAD);
+       cp_out (ctx, 0x00910880); /* ?? */
+       cp_out (ctx, 0x00901ffe); /* ?? */
+       cp_out (ctx, 0x01940000); /* ?? */
+       cp_lsr (ctx, 0x20);
+       cp_out (ctx, 0x0060000b); /* ?? */
+       cp_wait(ctx, UNK57, CLEAR);
+       cp_out (ctx, 0x0060000c); /* ?? */
+       cp_bra (ctx, ALWAYS, TRUE, cp_swap_state);
+
+       /* setup for context save */
+       cp_name(ctx, cp_setup_save);
+       cp_set (ctx, SWAP_DIRECTION, SAVE);
+
+       /* general PGRAPH state */
+       cp_name(ctx, cp_swap_state);
+       cp_pos (ctx, 0x00020/4);
+       nv40_gr_construct_general(ctx);
+       cp_wait(ctx, STATUS, IDLE);
+
+       /* 3D state, block 1 */
+       cp_bra (ctx, UNK54, CLEAR, cp_prepare_exit);
+       nv40_gr_construct_state3d(ctx);
+       cp_wait(ctx, STATUS, IDLE);
+
+       /* 3D state, block 2 */
+       nv40_gr_construct_state3d_2(ctx);
+
+       /* Some other block of "random" state */
+       nv40_gr_construct_state3d_3(ctx);
+
+       /* Per-vertex shader state */
+       cp_pos (ctx, ctx->ctxvals_pos);
+       nv40_gr_construct_shader(ctx);
+
+       /* pre-exit state updates */
+       cp_name(ctx, cp_prepare_exit);
+       cp_bra (ctx, SWAP_DIRECTION, SAVE, cp_check_load);
+       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);
+}
+
+void
+nv40_grctx_fill(struct nvkm_device *device, struct nvkm_gpuobj *mem)
+{
+       nv40_grctx_generate(&(struct nvkm_grctx) {
+                            .device = device,
+                            .mode = NVKM_GRCTX_VALS,
+                            .data = mem,
+                          });
+}
+
+int
+nv40_grctx_init(struct nvkm_device *device, u32 *size)
+{
+       u32 *ctxprog = kmalloc(256 * 4, GFP_KERNEL), i;
+       struct nvkm_grctx ctx = {
+               .device = device,
+               .mode = NVKM_GRCTX_PROG,
+               .data = ctxprog,
+               .ctxprog_max = 256,
+       };
+
+       if (!ctxprog)
+               return -ENOMEM;
+
+       nv40_grctx_generate(&ctx);
+
+       nv_wr32(device, 0x400324, 0);
+       for (i = 0; i < ctx.ctxprog_len; i++)
+               nv_wr32(device, 0x400328, ctxprog[i]);
+       *size = ctx.ctxvals_pos * 4;
+
+       kfree(ctxprog);
+       return 0;
+}
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/gr/ctxnv40.h b/drivers/gpu/drm/nouveau/nvkm/engine/gr/ctxnv40.h
new file mode 100644 (file)
index 0000000..8a89961
--- /dev/null
@@ -0,0 +1,129 @@
+#ifndef __NVKM_GRCTX_H__
+#define __NVKM_GRCTX_H__
+#include <core/gpuobj.h>
+
+struct nvkm_grctx {
+       struct nvkm_device *device;
+
+       enum {
+               NVKM_GRCTX_PROG,
+               NVKM_GRCTX_VALS
+       } mode;
+       void *data;
+
+       u32 ctxprog_max;
+       u32 ctxprog_len;
+       u32 ctxprog_reg;
+       int ctxprog_label[32];
+       u32 ctxvals_pos;
+       u32 ctxvals_base;
+};
+
+static inline void
+cp_out(struct nvkm_grctx *ctx, u32 inst)
+{
+       u32 *ctxprog = ctx->data;
+
+       if (ctx->mode != NVKM_GRCTX_PROG)
+               return;
+
+       BUG_ON(ctx->ctxprog_len == ctx->ctxprog_max);
+       ctxprog[ctx->ctxprog_len++] = inst;
+}
+
+static inline void
+cp_lsr(struct nvkm_grctx *ctx, u32 val)
+{
+       cp_out(ctx, CP_LOAD_SR | val);
+}
+
+static inline void
+cp_ctx(struct nvkm_grctx *ctx, u32 reg, u32 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 nvkm_grctx *ctx, int name)
+{
+       u32 *ctxprog = ctx->data;
+       int i;
+
+       if (ctx->mode != NVKM_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 nvkm_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)
+#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)
+
+static inline void
+_cp_wait(struct nvkm_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 nvkm_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 nvkm_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 nvkm_grctx *ctx, u32 reg, u32 val)
+{
+       if (ctx->mode != NVKM_GRCTX_VALS)
+               return;
+
+       reg = (reg - 0x00400000) / 4;
+       reg = (reg - ctx->ctxprog_reg) + ctx->ctxvals_base;
+
+       nv_wo32(ctx->data, reg * 4, val);
+}
+#endif
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/gr/ctxnv50.c b/drivers/gpu/drm/nouveau/nvkm/engine/gr/ctxnv50.c
new file mode 100644 (file)
index 0000000..9c9528d
--- /dev/null
@@ -0,0 +1,3345 @@
+/*
+ * 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_XFER_SWITCH           ((0 * 32) + 0xe)
+#define CP_FLAG_XFER_SWITCH_DISABLE   0
+#define CP_FLAG_XFER_SWITCH_ENABLE    1
+#define CP_FLAG_STATE                 ((0 * 32) + 0x1c)
+#define CP_FLAG_STATE_STOPPED         0
+#define CP_FLAG_STATE_RUNNING         1
+#define CP_FLAG_UNK1D                 ((0 * 32) + 0x1d)
+#define CP_FLAG_UNK1D_CLEAR           0
+#define CP_FLAG_UNK1D_SET             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_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 "ctxnv40.h"
+
+#include <core/device.h>
+#include <subdev/fb.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,
+};
+
+static void nv50_gr_construct_mmio(struct nvkm_grctx *ctx);
+static void nv50_gr_construct_xfer1(struct nvkm_grctx *ctx);
+static void nv50_gr_construct_xfer2(struct nvkm_grctx *ctx);
+
+/* Main function: construct the ctxprog skeleton, call the other functions. */
+
+static int
+nv50_grctx_generate(struct nvkm_grctx *ctx)
+{
+       cp_set (ctx, STATE, RUNNING);
+       cp_set (ctx, XFER_SWITCH, ENABLE);
+       /* 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_prepare_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);
+
+       /* setup for context save */
+       cp_name(ctx, cp_setup_save);
+       cp_set (ctx, UNK1D, SET);
+       cp_wait(ctx, STATUS, BUSY);
+       cp_wait(ctx, INTR, PENDING);
+       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_gr_construct_mmio(ctx);
+       nv50_gr_construct_xfer1(ctx);
+       nv50_gr_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_set (ctx, XFER_SWITCH, DISABLE);
+       cp_set (ctx, STATE, STOPPED);
+       cp_out (ctx, CP_END);
+       ctx->ctxvals_pos += 0x400; /* padding... no idea why you need it */
+
+       return 0;
+}
+
+void
+nv50_grctx_fill(struct nvkm_device *device, struct nvkm_gpuobj *mem)
+{
+       nv50_grctx_generate(&(struct nvkm_grctx) {
+                            .device = device,
+                            .mode = NVKM_GRCTX_VALS,
+                            .data = mem,
+                          });
+}
+
+int
+nv50_grctx_init(struct nvkm_device *device, u32 *size)
+{
+       u32 *ctxprog = kmalloc(512 * 4, GFP_KERNEL), i;
+       struct nvkm_grctx ctx = {
+               .device = device,
+               .mode = NVKM_GRCTX_PROG,
+               .data = ctxprog,
+               .ctxprog_max = 512,
+       };
+
+       if (!ctxprog)
+               return -ENOMEM;
+       nv50_grctx_generate(&ctx);
+
+       nv_wr32(device, 0x400324, 0);
+       for (i = 0; i < ctx.ctxprog_len; i++)
+               nv_wr32(device, 0x400328, ctxprog[i]);
+       *size = ctx.ctxvals_pos * 4;
+       kfree(ctxprog);
+       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_gr_construct_mmio_ddata(struct nvkm_grctx *ctx);
+
+static void
+nv50_gr_construct_mmio(struct nvkm_grctx *ctx)
+{
+       struct nvkm_device *device = ctx->device;
+       int i, j;
+       int offset, base;
+       u32 units = nv_rd32 (ctx->device, 0x1540);
+
+       /* 0800: DISPATCH */
+       cp_ctx(ctx, 0x400808, 7);
+       gr_def(ctx, 0x400814, 0x00000030);
+       cp_ctx(ctx, 0x400834, 0x32);
+       if (device->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(device->chipset))
+               gr_def(ctx, 0x400894, 0x00001000);
+       gr_def(ctx, 0x4008e8, 0x00000003);
+       gr_def(ctx, 0x4008ec, 0x00001000);
+       if (device->chipset == 0x50)
+               cp_ctx(ctx, 0x400908, 0xb);
+       else if (device->chipset < 0xa0)
+               cp_ctx(ctx, 0x400908, 0xc);
+       else
+               cp_ctx(ctx, 0x400908, 0xe);
+
+       if (device->chipset >= 0xa0)
+               cp_ctx(ctx, 0x400b00, 0x1);
+       if (IS_NVA3F(device->chipset)) {
+               cp_ctx(ctx, 0x400b10, 0x1);
+               gr_def(ctx, 0x400b10, 0x0001629d);
+               cp_ctx(ctx, 0x400b20, 0x1);
+               gr_def(ctx, 0x400b20, 0x0001629d);
+       }
+
+       nv50_gr_construct_mmio_ddata(ctx);
+
+       /* 0C00: VFETCH */
+       cp_ctx(ctx, 0x400c08, 0x2);
+       gr_def(ctx, 0x400c08, 0x0000fe0c);
+
+       /* 1000 */
+       if (device->chipset < 0xa0) {
+               cp_ctx(ctx, 0x401008, 0x4);
+               gr_def(ctx, 0x401014, 0x00001000);
+       } else if (!IS_NVA3F(device->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 (device->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 (device->chipset == 0x50) {
+               cp_ctx(ctx, 0x40181c, 0xe);
+               gr_def(ctx, 0x401850, 0x00000004);
+       } else if (device->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 (device->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 (device->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 (device->chipset == 0x50)
+               gr_def(ctx, 0x402800, 0x00000006);
+
+       /* 2C00: ZCULL */
+       cp_ctx(ctx, 0x402c08, 0x6);
+       if (device->chipset != 0x50)
+               gr_def(ctx, 0x402c14, 0x01000000);
+       gr_def(ctx, 0x402c18, 0x000000ff);
+       if (device->chipset == 0x50)
+               cp_ctx(ctx, 0x402ca0, 0x1);
+       else
+               cp_ctx(ctx, 0x402ca0, 0x2);
+       if (device->chipset < 0xa0)
+               gr_def(ctx, 0x402ca0, 0x00000400);
+       else if (!IS_NVA3F(device->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 (device->chipset >= 0xa0) {
+               cp_ctx(ctx, 0x403404, 0x1);
+               gr_def(ctx, 0x403404, 0x00000001);
+       }
+
+       /* 5000: CCACHE */
+       cp_ctx(ctx, 0x405000, 0x1);
+       switch (device->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 (device->chipset == 0x50)
+               cp_ctx(ctx, 0x4063e0, 0x1);
+
+       /* 6800: M2MF */
+       if (device->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 (device->chipset == 0x98)
+                       gr_def(ctx, 0x406818, 0x00000f80);
+               else
+                       gr_def(ctx, 0x406818, 0x00001f80);
+               if (IS_NVA3F(device->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 (device->chipset == 0x50)
+                               gr_def(ctx, 0x407000 + (i<<8), 0x1b74f820);
+                       else if (device->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 (device->chipset == 0x50) {
+                               cp_ctx(ctx, 0x407010 + (i<<8), 1);
+                       } else if (device->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 (device->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 (device->chipset != 0xa5)
+                               gr_def(ctx, 0x407080 + (i<<8), 0x027c10fa);
+                       else
+                               gr_def(ctx, 0x407080 + (i<<8), 0x827c10fa);
+                       if (device->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 (device->chipset < 0xa0)
+                               cp_ctx(ctx, 0x407094 + (i<<8), 1);
+                       else if (!IS_NVA3F(device->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 (device->chipset < 0x90)
+               gr_def(ctx, 0x407c00, 0x00010040);
+       else if (device->chipset < 0xa0)
+               gr_def(ctx, 0x407c00, 0x00390040);
+       else
+               gr_def(ctx, 0x407c00, 0x003d0040);
+       gr_def(ctx, 0x407c08, 0x00000022);
+       if (device->chipset >= 0xa0) {
+               cp_ctx(ctx, 0x407c10, 0x3);
+               cp_ctx(ctx, 0x407c20, 0x1);
+               cp_ctx(ctx, 0x407c2c, 0x1);
+       }
+
+       if (device->chipset < 0xa0) {
+               cp_ctx(ctx, 0x407d00, 0x9);
+       } else {
+               cp_ctx(ctx, 0x407d00, 0x15);
+       }
+       if (device->chipset == 0x98)
+               gr_def(ctx, 0x407d08, 0x00380040);
+       else {
+               if (device->chipset < 0x90)
+                       gr_def(ctx, 0x407d08, 0x00010040);
+               else if (device->chipset < 0xa0)
+                       gr_def(ctx, 0x407d08, 0x00390040);
+               else {
+                       if (nvkm_fb(device)->ram->type != NV_MEM_TYPE_GDDR5)
+                               gr_def(ctx, 0x407d08, 0x003d0040);
+                       else
+                               gr_def(ctx, 0x407d08, 0x003c0040);
+               }
+               gr_def(ctx, 0x407d0c, 0x00000022);
+       }
+
+       /* 8000+: per-TP state */
+       for (i = 0; i < 10; i++) {
+               if (units & (1<<i)) {
+                       if (device->chipset < 0xa0)
+                               base = 0x408000 + (i<<12);
+                       else
+                               base = 0x408000 + (i<<11);
+                       if (device->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 < (device->chipset < 0xa0 ? 2 : 4); j++) {
+                               if (!(units & (1 << (j+24)))) continue;
+                               if (device->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 (device->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, 0x018c0000);
+                                       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 (device->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 (device->chipset == 0x50)
+                                       gr_def(ctx, offset + 0x5c, 0x00000080);
+                               else
+                                       gr_def(ctx, offset + 0x5c, 0x08000080);
+                               if (device->chipset >= 0xa0)
+                                       gr_def(ctx, offset + 0x68, 0x0000003e);
+                       }
+
+                       if (device->chipset < 0xa0)
+                               cp_ctx(ctx, base + 0x300, 0x4);
+                       else
+                               cp_ctx(ctx, base + 0x300, 0x5);
+                       if (device->chipset == 0x50)
+                               gr_def(ctx, base + 0x304, 0x00007070);
+                       else if (device->chipset < 0xa0)
+                               gr_def(ctx, base + 0x304, 0x00027070);
+                       else if (!IS_NVA3F(device->chipset))
+                               gr_def(ctx, base + 0x304, 0x01127070);
+                       else
+                               gr_def(ctx, base + 0x304, 0x05127070);
+
+                       if (device->chipset < 0xa0)
+                               cp_ctx(ctx, base + 0x318, 1);
+                       else
+                               cp_ctx(ctx, base + 0x320, 1);
+                       if (device->chipset == 0x50)
+                               gr_def(ctx, base + 0x318, 0x0003ffff);
+                       else if (device->chipset < 0xa0)
+                               gr_def(ctx, base + 0x318, 0x03ffffff);
+                       else
+                               gr_def(ctx, base + 0x320, 0x07ffffff);
+
+                       if (device->chipset < 0xa0)
+                               cp_ctx(ctx, base + 0x324, 5);
+                       else
+                               cp_ctx(ctx, base + 0x328, 4);
+
+                       if (device->chipset < 0xa0) {
+                               cp_ctx(ctx, base + 0x340, 9);
+                               offset = base + 0x340;
+                       } else if (!IS_NVA3F(device->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 (device->chipset == 0x84)
+                               gr_def(ctx, offset + 0x8, 0x05100202);
+                       else
+                               gr_def(ctx, offset + 0x8, 0x05010202);
+                       gr_def(ctx, offset + 0xc, 0x00030201);
+                       if (device->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 (device->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 (device->chipset == 0x50 || IS_NVAAF(device->chipset))
+                               gr_def(ctx, offset + 0xc, 0x00008000);
+                       gr_def(ctx, offset + 0x14, 0x00039e00);
+                       cp_ctx(ctx, offset + 0x1c, 2);
+                       if (device->chipset == 0x50)
+                               gr_def(ctx, offset + 0x1c, 0x00000040);
+                       else
+                               gr_def(ctx, offset + 0x1c, 0x00000100);
+                       gr_def(ctx, offset + 0x20, 0x00003800);
+
+                       if (device->chipset >= 0xa0) {
+                               cp_ctx(ctx, base + 0x54c, 2);
+                               if (!IS_NVA3F(device->chipset))
+                                       gr_def(ctx, base + 0x54c, 0x003fe006);
+                               else
+                                       gr_def(ctx, base + 0x54c, 0x003fe007);
+                               gr_def(ctx, base + 0x550, 0x003fe000);
+                       }
+
+                       if (device->chipset < 0xa0)
+                               offset = base + 0xa00;
+                       else
+                               offset = base + 0x680;
+                       cp_ctx(ctx, offset, 1);
+                       gr_def(ctx, offset, 0x00404040);
+
+                       if (device->chipset < 0xa0)
+                               offset = base + 0xe00;
+                       else
+                               offset = base + 0x700;
+                       cp_ctx(ctx, offset, 2);
+                       if (device->chipset < 0xa0)
+                               gr_def(ctx, offset, 0x0077f005);
+                       else if (device->chipset == 0xa5)
+                               gr_def(ctx, offset, 0x6cf7f007);
+                       else if (device->chipset == 0xa8)
+                               gr_def(ctx, offset, 0x6cfff007);
+                       else if (device->chipset == 0xac)
+                               gr_def(ctx, offset, 0x0cfff007);
+                       else
+                               gr_def(ctx, offset, 0x0cf7f007);
+                       if (device->chipset == 0x50)
+                               gr_def(ctx, offset + 0x4, 0x00007fff);
+                       else if (device->chipset < 0xa0)
+                               gr_def(ctx, offset + 0x4, 0x003f7fff);
+                       else
+                               gr_def(ctx, offset + 0x4, 0x02bf7fff);
+                       cp_ctx(ctx, offset + 0x2c, 1);
+                       if (device->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 (device->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 nvkm_grctx *ctx, int num, u32 val) {
+       int i;
+       if (val && ctx->mode == NVKM_GRCTX_VALS)
+               for (i = 0; i < num; i++)
+                       nv_wo32(ctx->data, 4 * (ctx->ctxvals_pos + i), val);
+       ctx->ctxvals_pos += num;
+}
+
+static void
+nv50_gr_construct_mmio_ddata(struct nvkm_grctx *ctx)
+{
+       struct nvkm_device *device = ctx->device;
+       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 (device->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(device->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 (device->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 (device->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(device->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 (device->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 (device->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 (device->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(device->chipset)) {
+               dd_emit(ctx, 1, 3);     /* 00000003 */
+               dd_emit(ctx, 1, 0);     /* 00000001 UNK1418. Alone. */
+       }
+       if (device->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 (device->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 (device->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 (device->chipset != 0x50)
+               dd_emit(ctx, 8, 0);     /* 00000001 */
+       if (device->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(device->chipset))
+               dd_emit(ctx, 1, 0);     /* 00000001 */
+       dd_emit(ctx, 1, 2);             /* 00000003 POLYGON_MODE_BACK */
+       if (device->chipset >= 0xa0)
+               dd_emit(ctx, 1, 0);     /* 00000003 VTX_ATTR_DEFINE.SIZE - 1 */
+       dd_emit(ctx, 1, 0);             /* 0000ffff CB_ADDR_INDEX */
+       if (device->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 (device->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(device->chipset))
+               dd_emit(ctx, 1, 0x200);
+       dd_emit(ctx, 1, 0);             /* 00000001 */
+       if (device->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(device->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 nvkm_grctx *ctx, int num, u32 val) {
+       int i;
+       if (val && ctx->mode == NVKM_GRCTX_VALS)
+               for (i = 0; i < num; i++)
+                       nv_wo32(ctx->data, 4 * (ctx->ctxvals_pos + (i << 3)), val);
+       ctx->ctxvals_pos += num << 3;
+}
+
+/* Gene declarations... */
+
+static void nv50_gr_construct_gene_dispatch(struct nvkm_grctx *ctx);
+static void nv50_gr_construct_gene_m2mf(struct nvkm_grctx *ctx);
+static void nv50_gr_construct_gene_ccache(struct nvkm_grctx *ctx);
+static void nv50_gr_construct_gene_unk10xx(struct nvkm_grctx *ctx);
+static void nv50_gr_construct_gene_unk14xx(struct nvkm_grctx *ctx);
+static void nv50_gr_construct_gene_zcull(struct nvkm_grctx *ctx);
+static void nv50_gr_construct_gene_clipid(struct nvkm_grctx *ctx);
+static void nv50_gr_construct_gene_unk24xx(struct nvkm_grctx *ctx);
+static void nv50_gr_construct_gene_vfetch(struct nvkm_grctx *ctx);
+static void nv50_gr_construct_gene_eng2d(struct nvkm_grctx *ctx);
+static void nv50_gr_construct_gene_csched(struct nvkm_grctx *ctx);
+static void nv50_gr_construct_gene_unk1cxx(struct nvkm_grctx *ctx);
+static void nv50_gr_construct_gene_strmout(struct nvkm_grctx *ctx);
+static void nv50_gr_construct_gene_unk34xx(struct nvkm_grctx *ctx);
+static void nv50_gr_construct_gene_ropm1(struct nvkm_grctx *ctx);
+static void nv50_gr_construct_gene_ropm2(struct nvkm_grctx *ctx);
+static void nv50_gr_construct_gene_ropc(struct nvkm_grctx *ctx);
+static void nv50_gr_construct_xfer_tp(struct nvkm_grctx *ctx);
+
+static void
+nv50_gr_construct_xfer1(struct nvkm_grctx *ctx)
+{
+       struct nvkm_device *device = ctx->device;
+       int i;
+       int offset;
+       int size = 0;
+       u32 units = nv_rd32 (ctx->device, 0x1540);
+
+       offset = (ctx->ctxvals_pos+0x3f)&~0x3f;
+       ctx->ctxvals_base = offset;
+
+       if (device->chipset < 0xa0) {
+               /* Strand 0 */
+               ctx->ctxvals_pos = offset;
+               nv50_gr_construct_gene_dispatch(ctx);
+               nv50_gr_construct_gene_m2mf(ctx);
+               nv50_gr_construct_gene_unk24xx(ctx);
+               nv50_gr_construct_gene_clipid(ctx);
+               nv50_gr_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_gr_construct_gene_vfetch(ctx);
+               nv50_gr_construct_gene_eng2d(ctx);
+               nv50_gr_construct_gene_csched(ctx);
+               nv50_gr_construct_gene_ropm1(ctx);
+               nv50_gr_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_gr_construct_gene_ccache(ctx);
+               nv50_gr_construct_gene_unk1cxx(ctx);
+               nv50_gr_construct_gene_strmout(ctx);
+               nv50_gr_construct_gene_unk14xx(ctx);
+               nv50_gr_construct_gene_unk10xx(ctx);
+               nv50_gr_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_gr_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_gr_construct_xfer_tp(ctx);
+                       if (units & (1 << (2 * i + 1)))
+                               nv50_gr_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_gr_construct_gene_dispatch(ctx);
+               nv50_gr_construct_gene_m2mf(ctx);
+               nv50_gr_construct_gene_unk34xx(ctx);
+               nv50_gr_construct_gene_csched(ctx);
+               nv50_gr_construct_gene_unk1cxx(ctx);
+               nv50_gr_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_gr_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 (device->chipset == 0xa0)
+                       nv50_gr_construct_gene_unk14xx(ctx);
+               nv50_gr_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_gr_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_gr_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_gr_construct_gene_ropm2(ctx);
+               nv50_gr_construct_gene_ropm1(ctx);
+               /* per-ROP context */
+               for (i = 0; i < 8; i++)
+                       if (units & (1<<(i+16)))
+                               nv50_gr_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_gr_construct_gene_zcull(ctx);
+               nv50_gr_construct_gene_clipid(ctx);
+               nv50_gr_construct_gene_eng2d(ctx);
+               if (units & (1 << 0))
+                       nv50_gr_construct_xfer_tp(ctx);
+               if (units & (1 << 1))
+                       nv50_gr_construct_xfer_tp(ctx);
+               if (units & (1 << 2))
+                       nv50_gr_construct_xfer_tp(ctx);
+               if (units & (1 << 3))
+                       nv50_gr_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 (device->chipset == 0xa0) {
+                       if (units & (1 << 4))
+                               nv50_gr_construct_xfer_tp(ctx);
+                       if (units & (1 << 5))
+                               nv50_gr_construct_xfer_tp(ctx);
+                       if (units & (1 << 6))
+                               nv50_gr_construct_xfer_tp(ctx);
+                       if (units & (1 << 7))
+                               nv50_gr_construct_xfer_tp(ctx);
+                       if (units & (1 << 8))
+                               nv50_gr_construct_xfer_tp(ctx);
+                       if (units & (1 << 9))
+                               nv50_gr_construct_xfer_tp(ctx);
+               } else {
+                       nv50_gr_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_gr_construct_gene_dispatch(struct nvkm_grctx *ctx)
+{
+       /* start of strand 0 */
+       struct nvkm_device *device = ctx->device;
+       /* SEEK */
+       if (device->chipset == 0x50)
+               xf_emit(ctx, 5, 0);
+       else if (!IS_NVA3F(device->chipset))
+               xf_emit(ctx, 6, 0);
+       else
+               xf_emit(ctx, 4, 0);
+       /* SEEK */
+       /* the PGRAPH's internal FIFO */
+       if (device->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(device->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 (device->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 (device->chipset == 0x50)
+               xf_emit(ctx, 0x1c, 0);
+       else if (device->chipset < 0xa0)
+               xf_emit(ctx, 0x1e, 0);
+       else
+               xf_emit(ctx, 0x22, 0);
+       /* SEEK */
+       xf_emit(ctx, 0x15, 0);
+}
+
+static void
+nv50_gr_construct_gene_m2mf(struct nvkm_grctx *ctx)
+{
+       /* Strand 0, right after dispatch */
+       struct nvkm_device *device = ctx->device;
+       int smallm2mf = 0;
+       if (device->chipset < 0x92 || device->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_gr_construct_gene_ccache(struct nvkm_grctx *ctx)
+{
+       struct nvkm_device *device = ctx->device;
+       xf_emit(ctx, 2, 0);             /* RO */
+       xf_emit(ctx, 0x800, 0);         /* ffffffff */
+       switch (device->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_gr_construct_gene_unk10xx(struct nvkm_grctx *ctx)
+{
+       struct nvkm_device *device = ctx->device;
+       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 (device->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 (device->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_gr_construct_gene_unk34xx(struct nvkm_grctx *ctx)
+{
+       struct nvkm_device *device = ctx->device;
+       /* 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 (device->chipset >= 0xa0)
+               xf_emit(ctx, 1, 0x0fac6881);
+       if (IS_NVA3F(device->chipset)) {
+               xf_emit(ctx, 1, 1);
+               xf_emit(ctx, 3, 0);
+       }
+}
+
+static void
+nv50_gr_construct_gene_unk14xx(struct nvkm_grctx *ctx)
+{
+       struct nvkm_device *device = ctx->device;
+       /* middle of area 2 on pre-NVA0, beginning of area 2 on NVA0, area 7 on >NVA0 */
+       if (device->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 (device->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 (device->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 (device->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(device->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 (device->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_gr_construct_gene_zcull(struct nvkm_grctx *ctx)
+{
+       struct nvkm_device *device = ctx->device;
+       /* 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 (device->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 (device->chipset != 0x50)
+               xf_emit(ctx, 1, 0);     /* 0fffffff tesla UNK1104 */
+       xf_emit(ctx, 1, 0);             /* 00000001 tesla UNK151C */
+}
+
+static void
+nv50_gr_construct_gene_clipid(struct nvkm_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_gr_construct_gene_unk24xx(struct nvkm_grctx *ctx)
+{
+       struct nvkm_device *device = ctx->device;
+       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(device->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 (device->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 (device->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 (device->chipset != 0x50)
+               xf_emit(ctx, 1, 0);     /* 000003ff */
+}
+
+static void
+nv50_gr_construct_gene_vfetch(struct nvkm_grctx *ctx)
+{
+       struct nvkm_device *device = ctx->device;
+       int acnt = 0x10, rep, i;
+       /* beginning of strand 1 on pre-NVA0, strand 3 on NVAx */
+       if (IS_NVA3F(device->chipset))
+               acnt = 0x20;
+       /* SEEK */
+       if (device->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(device->chipset))
+               xf_emit(ctx, 0xb, 0);   /* RO */
+       else if (device->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 (device->chipset == 0x50)
+               xf_emit(ctx, 1, 0x3ff); /* 3ff tesla UNK0D68 */
+       else
+               xf_emit(ctx, 1, 0x7ff); /* 7ff tesla UNK0D68 */
+       if (device->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 (device->chipset > 0x50 && device->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(device->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 (device->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(device->chipset)) {
+               xf_emit(ctx, acnt, 0);          /* f */
+               xf_emit(ctx, 3, 0);             /* f/1f */
+       }
+       /* SEEK */
+       if (IS_NVA3F(device->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 (device->chipset < 0xa0) {
+               xf_emit(ctx, 0x41, 0);  /* RO */
+               /* SEEK */
+               xf_emit(ctx, 0x11, 0);  /* RO */
+       } else if (!IS_NVA3F(device->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(device->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 (device->chipset < 0xa0)
+               xf_emit(ctx, 8, 0);     /* RO */
+       else if (IS_NVA3F(device->chipset))
+               xf_emit(ctx, 0xc, 0);   /* RO */
+       else
+               xf_emit(ctx, 7, 0);     /* RO */
+       /* SEEK */
+       xf_emit(ctx, 0xa, 0);           /* RO */
+       if (device->chipset == 0xa0)
+               rep = 0xc;
+       else
+               rep = 4;
+       for (i = 0; i < rep; i++) {
+               /* SEEK */
+               if (IS_NVA3F(device->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(device->chipset))
+               xf_emit(ctx, 7, 0);     /* weird... */
+       else
+               xf_emit(ctx, 5, 0);     /* weird... */
+}
+
+static void
+nv50_gr_construct_gene_eng2d(struct nvkm_grctx *ctx)
+{
+       struct nvkm_device *device = ctx->device;
+       /* 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 (device->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_gr_construct_gene_csched(struct nvkm_grctx *ctx)
+{
+       struct nvkm_device *device = ctx->device;
+       /* 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 (device->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_gr_construct_gene_unk1cxx(struct nvkm_grctx *ctx)
+{
+       struct nvkm_device *device = ctx->device;
+       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(device->chipset))
+               xf_emit(ctx, 1, 3);     /* 00000003 UNK16B4 */
+       else if (device->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 (device->chipset != 0x50) {
+               xf_emit(ctx, 1, 0);     /* 3ff */
+               xf_emit(ctx, 1, 1);     /* 00000001 tesla UNK1110 */
+       }
+       if (IS_NVA3F(device->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 (device->chipset != 0x50)
+               xf_emit(ctx, 1, 3);     /* 00000003 tesla UNK1100 */
+       if (device->chipset < 0xa0)
+               xf_emit(ctx, 0x1c, 0);  /* RO */
+       else if (IS_NVA3F(device->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 (device->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 (device->chipset < 0xa0)
+               xf_emit(ctx, 0x25, 0);
+       else
+               xf_emit(ctx, 0x3b, 0);
+}
+
+static void
+nv50_gr_construct_gene_strmout(struct nvkm_grctx *ctx)
+{
+       struct nvkm_device *device = ctx->device;
+       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 (device->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 (device->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 (device->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_gr_construct_gene_ropm1(struct nvkm_grctx *ctx)
+{
+       struct nvkm_device *device = ctx->device;
+       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(device->chipset))
+               xf_emit(ctx, 1, 0x11);  /* 000000ff tesla UNK1968 */
+       xf_emit(ctx, 1, 0);             /* ffffffff tesla UNK1A3C */
+}
+
+static void
+nv50_gr_construct_gene_ropm2(struct nvkm_grctx *ctx)
+{
+       struct nvkm_device *device = ctx->device;
+       /* 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(device->chipset))
+               xf_emit(ctx, 1, 0x11);  /* 000000ff tesla UNK1968 */
+       xf_emit(ctx, 1, 0);             /* ffffffff tesla UNK1A3C */
+}
+
+static void
+nv50_gr_construct_gene_ropc(struct nvkm_grctx *ctx)
+{
+       struct nvkm_device *device = ctx->device;
+       int magic2;
+       if (device->chipset == 0x50) {
+               magic2 = 0x00003e60;
+       } else if (!IS_NVA3F(device->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(device->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 (device->chipset >= 0xa0 && !IS_NVAAF(device->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 (device->chipset == 0x86 || device->chipset == 0x92 || device->chipset == 0x98 || device->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 (device->chipset != 0xa0) {
+                       if (IS_NVA3F(device->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 (device->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 (device->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(device->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 (device->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 (device->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 (device->chipset >= 0xa0)
+               xf_emit(ctx, 1, 0);     /* 00000001 UNK12E4? NVA3+ only? */
+       if (IS_NVA3F(device->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_gr_construct_xfer_unk84xx(struct nvkm_grctx *ctx)
+{
+       struct nvkm_device *device = ctx->device;
+       int magic3;
+       switch (device->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(device->chipset))
+               xf_emit(ctx, 0x1f, 0);  /* ffffffff */
+       else if (device->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 (device->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 (device->chipset == 0x94 || device->chipset == 0x96)
+               xf_emit(ctx, 0x1020, 0);        /* 4 x (0x400 x 0xffffffff, ff, 0, 0, 0, 4 x ffffffff) */
+       else if (device->chipset < 0xa0)
+               xf_emit(ctx, 0xa20, 0); /* 4 x (0x280 x 0xffffffff, ff, 0, 0, 0, 4 x ffffffff) */
+       else if (!IS_NVA3F(device->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_gr_construct_xfer_tprop(struct nvkm_grctx *ctx)
+{
+       struct nvkm_device *device = ctx->device;
+       int magic1, magic2;
+       if (device->chipset == 0x50) {
+               magic1 = 0x3ff;
+               magic2 = 0x00003e60;
+       } else if (!IS_NVA3F(device->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(device->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(device->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 (device->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(device->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(device->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(device->chipset))
+               xf_emit(ctx, 1, 1);     /* 0000001f tesla UNK169C */
+       if (device->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(device->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(device->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(device->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(device->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 (device->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(device->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 (device->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(device->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(device->chipset)) {
+                       xf_emit(ctx, 1, 0);     /* 00000001 UNK1140 */
+                       xf_emit(ctx, 1, 1);     /* 0000001f tesla UNK169C */
+               }
+       }
+}
+
+static void
+nv50_gr_construct_xfer_tex(struct nvkm_grctx *ctx)
+{
+       struct nvkm_device *device = ctx->device;
+       xf_emit(ctx, 2, 0);             /* 1 LINKED_TSC. yes, 2. */
+       if (device->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 (device->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 (device->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(device->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_gr_construct_xfer_unk8cxx(struct nvkm_grctx *ctx)
+{
+       struct nvkm_device *device = ctx->device;
+       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(device->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_gr_construct_xfer_tp(struct nvkm_grctx *ctx)
+{
+       struct nvkm_device *device = ctx->device;
+       if (device->chipset < 0xa0) {
+               nv50_gr_construct_xfer_unk84xx(ctx);
+               nv50_gr_construct_xfer_tprop(ctx);
+               nv50_gr_construct_xfer_tex(ctx);
+               nv50_gr_construct_xfer_unk8cxx(ctx);
+       } else {
+               nv50_gr_construct_xfer_tex(ctx);
+               nv50_gr_construct_xfer_tprop(ctx);
+               nv50_gr_construct_xfer_unk8cxx(ctx);
+               nv50_gr_construct_xfer_unk84xx(ctx);
+       }
+}
+
+static void
+nv50_gr_construct_xfer_mpc(struct nvkm_grctx *ctx)
+{
+       struct nvkm_device *device = ctx->device;
+       int i, mpcnt = 2;
+       switch (device->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 (device->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 (device->chipset == 0x86 || device->chipset == 0x98 || device->chipset == 0xa8 || IS_NVAAF(device->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 (device->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(device->chipset))
+                       xf_emit(ctx, 0xb, 0);   /* RO */
+               else if (device->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 (device->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(device->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(device->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(device->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 (device->chipset == 0x50)
+               xf_emit(ctx, 0x3a0, 0);
+       else if (device->chipset < 0x94)
+               xf_emit(ctx, 0x3a2, 0);
+       else if (device->chipset == 0x98 || device->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_gr_construct_xfer2(struct nvkm_grctx *ctx)
+{
+       struct nvkm_device *device = ctx->device;
+       int i;
+       u32 offset;
+       u32 units = nv_rd32 (ctx->device, 0x1540);
+       int size = 0;
+
+       offset = (ctx->ctxvals_pos+0x3f)&~0x3f;
+
+       if (device->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_gr_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_gr_construct_xfer_mpc(ctx);
+               if (units & (1 << 1))
+                       nv50_gr_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_gr_construct_xfer_mpc(ctx);
+               if (units & (1 << 3))
+                       nv50_gr_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_gr_construct_xfer_mpc(ctx);
+               if (units & (1 << 5))
+                       nv50_gr_construct_xfer_mpc(ctx);
+               if (units & (1 << 6))
+                       nv50_gr_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_gr_construct_xfer_mpc(ctx);
+               if (units & (1 << 8))
+                       nv50_gr_construct_xfer_mpc(ctx);
+               if (units & (1 << 9))
+                       nv50_gr_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/drivers/gpu/drm/nouveau/nvkm/engine/gr/fuc/com.fuc b/drivers/gpu/drm/nouveau/nvkm/engine/gr/fuc/com.fuc
new file mode 100644 (file)
index 0000000..64208bf
--- /dev/null
@@ -0,0 +1,335 @@
+/* fuc microcode util functions for gf100 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
+ */
+
+#ifdef INCLUDE_CODE
+// 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 b32 $r12 $r14
+       bset $r12 31                    // MMIO_CTRL_PENDING
+       nv_iowr(NV_PGRAPH_FECS_MMIO_CTRL, 0, $r12)
+       nv_rd32_wait:
+               nv_iord($r12, NV_PGRAPH_FECS_MMIO_CTRL, 0)
+               xbit $r12 $r12 31
+               bra ne #nv_rd32_wait
+       mov $r10 6                      // DONE_MMIO_RD
+       call(wait_doneo)
+       nv_iord($r15, NV_PGRAPH_FECS_MMIO_RDVAL, 0)
+       ret
+
+// nv_wr32 - write 32-bit value to nv register
+//
+// In : $r14 register
+//      $r15 value
+//
+nv_wr32:
+       nv_iowr(NV_PGRAPH_FECS_MMIO_WRVAL, 0, $r15)
+       mov b32 $r12 $r14
+       bset $r12 31                    // MMIO_CTRL_PENDING
+       bset $r12 30                    // MMIO_CTRL_WRITE
+       nv_iowr(NV_PGRAPH_FECS_MMIO_CTRL, 0, $r12)
+       nv_wr32_wait:
+               nv_iord($r12, NV_PGRAPH_FECS_MMIO_CTRL, 0)
+               xbit $r12 $r12 31
+               bra ne #nv_wr32_wait
+       ret
+
+// wait_donez - wait on FUC_DONE bit to become clear
+//
+// In : $r10 bit to wait on
+//
+wait_donez:
+       trace_set(T_WAIT);
+       nv_iowr(NV_PGRAPH_FECS_CC_SCRATCH_VAL(6), 0, $r10)
+       wait_donez_ne:
+               nv_iord($r8, NV_PGRAPH_FECS_SIGNAL, 0)
+               xbit $r8 $r8 $r10
+               bra ne #wait_donez_ne
+       trace_clr(T_WAIT)
+       ret
+
+// wait_doneo - wait on FUC_DONE bit to become set
+//
+// In : $r10 bit to wait on
+//
+wait_doneo:
+       trace_set(T_WAIT);
+       nv_iowr(NV_PGRAPH_FECS_CC_SCRATCH_VAL(6), 0, $r10)
+       wait_doneo_e:
+               nv_iord($r8, NV_PGRAPH_FECS_SIGNAL, 0)
+               xbit $r8 $r8 $r10
+               bra e #wait_doneo_e
+       trace_clr(T_WAIT)
+       ret
+
+// 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)
+       clear b32 $r9
+       or $r11 $r11
+       bra e #mmctx_base_disabled
+               nv_iowr(NV_PGRAPH_FECS_MMCTX_BASE, 0, $r11)
+               bset $r9 0                      // BASE_EN
+       mmctx_base_disabled:
+       or $r14 $r14
+       bra e #mmctx_multi_disabled
+               nv_iowr(NV_PGRAPH_FECS_MMCTX_MULTI_STRIDE, 0, $r14)
+               nv_iowr(NV_PGRAPH_FECS_MMCTX_MULTI_MASK, 0, $r15)
+               bset $r9 1                      // MULTI_EN
+       mmctx_multi_disabled:
+
+       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
+       nv_iowr(NV_PGRAPH_FECS_MMCTX_CTRL, 0, $r11)
+
+       // loop over the mmio list, and send requests to the hw
+       mmctx_exec_loop:
+               // wait for space in mmctx queue
+               mmctx_wait_free:
+                       nv_iord($r14, NV_PGRAPH_FECS_MMCTX_CTRL, 0)
+                       and $r14 0x1f
+                       bra e #mmctx_wait_free
+
+               // queue up an entry
+               ld b32 $r14 D[$r12]
+               or $r14 $r9
+               nv_iowr(NV_PGRAPH_FECS_MMCTX_QUEUE, 0, $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:
+                       nv_iord($r11, NV_PGRAPH_FECS_MMCTX_CTRL, 0)
+                       and $r11 0x1f
+                       cmpu b32 $r11 0x10
+                       bra ne #mmctx_fini_wait
+               mov $r10 5                      // 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
+               nv_iowr(NV_PGRAPH_FECS_MMCTX_CTRL, 0, $r11)
+               mmctx_stop_wait:
+                       // wait for STOP_TRIGGER to clear
+                       nv_iord($r11, NV_PGRAPH_FECS_MMCTX_CTRL, 0)
+                       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 $r9 NV_PGRAPH_FECS_STRAND_CMD_ENABLE
+       nv_iowr(NV_PGRAPH_FECS_STRAND_CMD, 0x3f, $r9)
+       call(strand_wait)
+       ret
+
+// unknown - call after issuing strand commands
+//
+strand_post:
+       mov $r9 NV_PGRAPH_FECS_STRAND_CMD_DISABLE
+       nv_iowr(NV_PGRAPH_FECS_STRAND_CMD, 0x3f, $r9)
+       call(strand_wait)
+       ret
+
+// Selects strand set?!
+//
+// In: $r14 id
+//
+strand_set:
+       mov $r12 0xf
+       nv_iowr(NV_PGRAPH_FECS_STRAND_FILTER, 0x3f, $r12)
+       mov $r12 NV_PGRAPH_FECS_STRAND_CMD_DEACTIVATE_FILTER
+       nv_iowr(NV_PGRAPH_FECS_STRAND_CMD, 0x3f, $r12)
+       nv_iowr(NV_PGRAPH_FECS_STRAND_FILTER, 0x3f, $r14)
+       mov $r12 NV_PGRAPH_FECS_STRAND_CMD_ACTIVATE_FILTER
+       nv_iowr(NV_PGRAPH_FECS_STRAND_CMD, 0x3f, $r12)
+       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)
+
+       clear b32 $r12
+       nv_iowr(NV_PGRAPH_FECS_STRAND_SELECT, 0x3f, $r12)
+       mov $r12 NV_PGRAPH_FECS_STRAND_CMD_SEEK
+       nv_iowr(NV_PGRAPH_FECS_STRAND_CMD, 0x3f, $r12)
+       call(strand_wait)
+       sub b32 $r12 $r0 1
+       nv_iowr(NV_PGRAPH_FECS_STRAND_DATA, 0x3f, $r12)
+       mov $r12 NV_PGRAPH_FECS_STRAND_CMD_GET_INFO
+       nv_iowr(NV_PGRAPH_FECS_STRAND_CMD, 0x3f, $r12)
+       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.
+       nv_mkio($r8, NV_PGRAPH_FECS_STRAND_SAVE_SWBASE, 0x00)
+       nv_iord($r9, NV_PGRAPH_FECS_STRANDS_CNT, 0x00)
+       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
+#endif
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/gr/fuc/gpc.fuc b/drivers/gpu/drm/nouveau/nvkm/engine/gr/fuc/gpc.fuc
new file mode 100644 (file)
index 0000000..eaed159
--- /dev/null
@@ -0,0 +1,378 @@
+/* fuc microcode for gf100 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
+ */
+
+/* TODO
+ * - bracket certain functions with scratch writes, useful for debugging
+ * - watchdog timer around ctx operations
+ */
+
+#ifdef INCLUDE_DATA
+gpc_mmio_list_head:    .b32 #mmio_list_base
+gpc_mmio_list_tail:
+tpc_mmio_list_head:    .b32 #mmio_list_base
+tpc_mmio_list_tail:
+unk_mmio_list_head:    .b32 #mmio_list_base
+unk_mmio_list_tail:    .b32 #mmio_list_base
+
+gpc_id:                        .b32 0
+
+tpc_count:             .b32 0
+tpc_mask:              .b32 0
+
+#if NV_PGRAPH_GPCX_UNK__SIZE > 0
+unk_count:             .b32 0
+unk_mask:              .b32 0
+#endif
+
+cmd_queue:             queue_init
+
+mmio_list_base:
+#endif
+
+#ifdef INCLUDE_CODE
+// reports an exception to the host
+//
+// In: $r15 error code (see os.h)
+//
+error:
+       push $r14
+       nv_wr32(NV_PGRAPH_FECS_CC_SCRATCH_VAL(5), $r15)
+       mov $r15 1
+       nv_wr32(NV_PGRAPH_FECS_INTR_UP_SET, $r15)
+       pop $r14
+       ret
+
+// GPC fuc initialisation, executed by triggering ucode start, will
+// fall through to main loop after completion.
+//
+// Input:
+//   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
+
+       // setup stack
+       nv_iord($r1, NV_PGRAPH_GPCX_GPCCS_CAPS, 0)
+       extr $r1 $r1 9:17
+       shl b32 $r1 8
+       mov $sp $r1
+
+       // enable fifo access
+       mov $r2 NV_PGRAPH_GPCX_GPCCS_ACCESS_FIFO
+       nv_iowr(NV_PGRAPH_GPCX_GPCCS_ACCESS, 0, $r2)
+
+       // setup i0 handler, and route all interrupts to it
+       mov $r1 #ih
+       mov $iv0 $r1
+       nv_iowr(NV_PGRAPH_GPCX_GPCCS_INTR_ROUTE, 0, $r0)
+
+       // enable fifo interrupt
+       mov $r2 NV_PGRAPH_GPCX_GPCCS_INTR_EN_SET_FIFO
+       nv_iowr(NV_PGRAPH_GPCX_GPCCS_INTR_EN_SET, 0, $r2)
+
+       // enable interrupts
+       bset $flags ie0
+
+       // figure out which GPC we are, and how many TPCs we have
+       nv_iord($r2, NV_PGRAPH_GPCX_GPCCS_UNITS, 0)
+       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
+       nv_iord($r2, NV_PGRAPH_GPCX_GPCCS_MYINDEX, 0)
+       st b32 D[$r0 + #gpc_id] $r2
+
+#if NV_PGRAPH_GPCX_UNK__SIZE > 0
+       // figure out which, and how many, UNKs are actually present
+       imm32($r14, 0x500c30)
+       clear b32 $r2
+       clear b32 $r3
+       clear b32 $r4
+       init_unk_loop:
+               call(nv_rd32)
+               cmp b32 $r15 0
+               bra z #init_unk_next
+                       mov $r15 1
+                       shl b32 $r15 $r2
+                       or $r4 $r15
+                       add b32 $r3 1
+               init_unk_next:
+               add b32 $r2 1
+               add b32 $r14 4
+               cmp b32 $r2 NV_PGRAPH_GPCX_UNK__SIZE
+               bra ne #init_unk_loop
+       init_unk_done:
+       st b32 D[$r0 + #unk_count] $r3
+       st b32 D[$r0 + #unk_mask] $r4
+#endif
+
+       // initialise context base, and size tracking
+       nv_iord($r2, NV_PGRAPH_GPCX_GPCCS_CC_SCRATCH_VAL(1), 0)
+       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
+       shr b32 $r5 $r2 8
+       nv_iowr(NV_PGRAPH_GPCX_GPCCS_MMCTX_SAVE_SWBASE, 0, $r5)
+       nv_iowr(NV_PGRAPH_GPCX_GPCCS_MMCTX_LOAD_SWBASE, 0, $r5)
+
+       // calculate GPC mmio context size
+       ld b32 $r14 D[$r0 + #gpc_mmio_list_head]
+       ld b32 $r15 D[$r0 + #gpc_mmio_list_tail]
+       call(mmctx_size)
+       add b32 $r2 $r15
+       add b32 $r3 $r15
+
+       // calculate per-TPC mmio context size
+       ld b32 $r14 D[$r0 + #tpc_mmio_list_head]
+       ld b32 $r15 D[$r0 + #tpc_mmio_list_tail]
+       call(mmctx_size)
+       ld b32 $r14 D[$r0 + #tpc_count]
+       mulu $r14 $r15
+       add b32 $r2 $r14
+       add b32 $r3 $r14
+
+#if NV_PGRAPH_GPCX_UNK__SIZE > 0
+       // calculate per-UNK mmio context size
+       ld b32 $r14 D[$r0 + #unk_mmio_list_head]
+       ld b32 $r15 D[$r0 + #unk_mmio_list_tail]
+       call(mmctx_size)
+       ld b32 $r14 D[$r0 + #unk_count]
+       mulu $r14 $r15
+       add b32 $r2 $r14
+       add b32 $r3 $r14
+#endif
+
+       // round up base/size to 256 byte boundary (for strand SWBASE)
+       shr b32 $r3 2
+       nv_iowr(NV_PGRAPH_GPCX_GPCCS_MMCTX_LOAD_COUNT, 0, $r3) // 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
+       nv_iowr(NV_PGRAPH_GPCX_GPCCS_CC_SCRATCH_VAL(1), 0, $r3)
+       clear b32 $r2
+       bset $r2 31
+       nv_iowr(NV_PGRAPH_GPCX_GPCCS_CC_SCRATCH_SET(0), 0, $r2)
+
+// 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
+       clear b32 $r0
+
+       // incoming fifo command?
+       nv_iord($r10, NV_PGRAPH_GPCX_GPCCS_INTR, 0)
+       and $r11 $r10 NV_PGRAPH_GPCX_GPCCS_INTR_FIFO
+       bra e #ih_no_fifo
+               // queue incoming fifo command for later processing
+               mov $r13 #cmd_queue
+               nv_iord($r14, NV_PGRAPH_GPCX_GPCCS_FIFO_CMD, 0)
+               nv_iord($r15, NV_PGRAPH_GPCX_GPCCS_FIFO_DATA, 0)
+               call(queue_put)
+               mov $r14 1
+               nv_iowr(NV_PGRAPH_GPCX_GPCCS_FIFO_ACK, 0, $r14)
+
+       // ack, and wake up main()
+       ih_no_fifo:
+       nv_iowr(NV_PGRAPH_GPCX_GPCCS_INTR_ACK, 0, $r10)
+
+       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
+       nv_wr32(0x409418, $r15) // 0x409418 - HUB_BAR_SET
+       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 $r15 NV_PGRAPH_GPCX_GPCCS_RED_SWITCH_POWER
+       nv_iowr(NV_PGRAPH_GPCX_GPCCS_RED_SWITCH, 0, $r15)
+       mov $r14 8
+       ctx_redswitch_delay:
+               sub b32 $r14 1
+               bra ne #ctx_redswitch_delay
+       or $r15 NV_PGRAPH_GPCX_GPCCS_RED_SWITCH_UNK11
+       or $r15 NV_PGRAPH_GPCX_GPCCS_RED_SWITCH_ENABLE
+       nv_iowr(NV_PGRAPH_GPCX_GPCCS_RED_SWITCH, 0, $r15)
+       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
+       nv_iowr(NV_PGRAPH_GPCX_GPCCS_MEM_BASE, 0, $r15)
+       bra not $p1 #ctx_xfer_not_load
+               call(ctx_redswitch)
+       ctx_xfer_not_load:
+
+       // strands
+       call(strand_pre)
+       clear b32 $r2
+       nv_iowr(NV_PGRAPH_GPCX_GPCCS_STRAND_SELECT, 0x3f, $r2)
+       xbit $r2 $flags $p1     // SAVE/LOAD
+       add b32 $r2 NV_PGRAPH_GPCX_GPCCS_STRAND_CMD_SAVE
+       nv_iowr(NV_PGRAPH_GPCX_GPCCS_STRAND_CMD, 0x3f, $r2)
+
+       // mmio context
+       xbit $r10 $flags $p1    // direction
+       or $r10 2               // first
+       imm32($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
+#if !NV_PGRAPH_GPCX_UNK__SIZE
+       or $r10 4               // last
+#endif
+       imm32($r11, 0x504000)
+       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)
+
+#if NV_PGRAPH_GPCX_UNK__SIZE > 0
+       // per-UNK mmio context
+       xbit $r10 $flags $p1    // direction
+       or $r10 4               // last
+       imm32($r11, 0x503000)
+       ld b32 $r12 D[$r0 + #gpc_id]
+       shl b32 $r12 15
+       add b32 $r11 $r12       // base = NV_PGRAPH_GPCn_UNK0
+       ld b32 $r12 D[$r0 + #unk_mmio_list_head]
+       ld b32 $r13 D[$r0 + #unk_mmio_list_tail]
+       ld b32 $r15 D[$r0 + #unk_mask]
+       mov $r14 0x200          // stride = 0x200
+       call(mmctx_xfer)
+#endif
+
+       // 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:
+               call(strand_post)
+
+       // mark completion in HUB's barrier
+       ctx_xfer_done:
+       call(hub_barrier_done)
+       ret
+#endif
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/gr/fuc/gpcgf100.fuc3 b/drivers/gpu/drm/nouveau/nvkm/engine/gr/fuc/gpcgf100.fuc3
new file mode 100644 (file)
index 0000000..7cf2bf9
--- /dev/null
@@ -0,0 +1,42 @@
+/*
+ * Copyright 2013 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 <bskeggs@redhat.com>
+ */
+
+#define NV_PGRAPH_GPCX_UNK__SIZE                                     0x00000000
+
+#define CHIPSET GF100
+#include "macros.fuc"
+
+.section #gf100_grgpc_data
+#define INCLUDE_DATA
+#include "com.fuc"
+#include "gpc.fuc"
+#undef INCLUDE_DATA
+
+.section #gf100_grgpc_code
+#define INCLUDE_CODE
+bra #init
+#include "com.fuc"
+#include "gpc.fuc"
+.align 256
+#undef INCLUDE_CODE
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/gr/fuc/gpcgf100.fuc3.h b/drivers/gpu/drm/nouveau/nvkm/engine/gr/fuc/gpcgf100.fuc3.h
new file mode 100644 (file)
index 0000000..ea32f56
--- /dev/null
@@ -0,0 +1,530 @@
+uint32_t gf100_grgpc_data[] = {
+/* 0x0000: gpc_mmio_list_head */
+       0x00000064,
+/* 0x0004: gpc_mmio_list_tail */
+/* 0x0004: tpc_mmio_list_head */
+       0x00000064,
+/* 0x0008: tpc_mmio_list_tail */
+/* 0x0008: unk_mmio_list_head */
+       0x00000064,
+/* 0x000c: unk_mmio_list_tail */
+       0x00000064,
+/* 0x0010: gpc_id */
+       0x00000000,
+/* 0x0014: tpc_count */
+       0x00000000,
+/* 0x0018: tpc_mask */
+       0x00000000,
+/* 0x001c: cmd_queue */
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+};
+
+uint32_t gf100_grgpc_code[] = {
+       0x03a10ef5,
+/* 0x0004: queue_put */
+       0x9800d898,
+       0x86f001d9,
+       0x0489b808,
+       0xf00c1bf4,
+       0x21f502f7,
+       0x00f8037e,
+/* 0x001c: queue_put_next */
+       0xb60798c4,
+       0x8dbb0384,
+       0x0880b600,
+       0x80008e80,
+       0x90b6018f,
+       0x0f94f001,
+       0xf801d980,
+/* 0x0039: queue_get */
+       0x0131f400,
+       0x9800d898,
+       0x89b801d9,
+       0x210bf404,
+       0xb60789c4,
+       0x9dbb0394,
+       0x0890b600,
+       0x98009e98,
+       0x80b6019f,
+       0x0f84f001,
+       0xf400d880,
+/* 0x0066: queue_get_done */
+       0x00f80132,
+/* 0x0068: nv_rd32 */
+       0xf002ecb9,
+       0x07f11fc9,
+       0x03f0ca00,
+       0x000cd001,
+/* 0x007a: nv_rd32_wait */
+       0xc7f104bd,
+       0xc3f0ca00,
+       0x00cccf01,
+       0xf41fccc8,
+       0xa7f0f31b,
+       0x1021f506,
+       0x00f7f101,
+       0x01f3f0cb,
+       0xf800ffcf,
+/* 0x009d: nv_wr32 */
+       0x0007f100,
+       0x0103f0cc,
+       0xbd000fd0,
+       0x02ecb904,
+       0xf01fc9f0,
+       0x07f11ec9,
+       0x03f0ca00,
+       0x000cd001,
+/* 0x00be: nv_wr32_wait */
+       0xc7f104bd,
+       0xc3f0ca00,
+       0x00cccf01,
+       0xf41fccc8,
+       0x00f8f31b,
+/* 0x00d0: wait_donez */
+       0x99f094bd,
+       0x0007f100,
+       0x0203f00f,
+       0xbd0009d0,
+       0x0007f104,
+       0x0203f006,
+       0xbd000ad0,
+/* 0x00ed: wait_donez_ne */
+       0x0087f104,
+       0x0183f000,
+       0xff0088cf,
+       0x1bf4888a,
+       0xf094bdf3,
+       0x07f10099,
+       0x03f01700,
+       0x0009d002,
+       0x00f804bd,
+/* 0x0110: wait_doneo */
+       0x99f094bd,
+       0x0007f100,
+       0x0203f00f,
+       0xbd0009d0,
+       0x0007f104,
+       0x0203f006,
+       0xbd000ad0,
+/* 0x012d: wait_doneo_e */
+       0x0087f104,
+       0x0183f000,
+       0xff0088cf,
+       0x0bf4888a,
+       0xf094bdf3,
+       0x07f10099,
+       0x03f01700,
+       0x0009d002,
+       0x00f804bd,
+/* 0x0150: mmctx_size */
+/* 0x0152: nv_mmctx_size_loop */
+       0xe89894bd,
+       0x1a85b600,
+       0xb60180b6,
+       0x98bb0284,
+       0x04e0b600,
+       0xf404efb8,
+       0x9fb9eb1b,
+/* 0x016f: mmctx_xfer */
+       0xbd00f802,
+       0x0199f094,
+       0x0f0007f1,
+       0xd00203f0,
+       0x04bd0009,
+       0xbbfd94bd,
+       0x120bf405,
+       0xc40007f1,
+       0xd00103f0,
+       0x04bd000b,
+/* 0x0197: mmctx_base_disabled */
+       0xfd0099f0,
+       0x0bf405ee,
+       0x0007f11e,
+       0x0103f0c6,
+       0xbd000ed0,
+       0x0007f104,
+       0x0103f0c7,
+       0xbd000fd0,
+       0x0199f004,
+/* 0x01b8: mmctx_multi_disabled */
+       0xb600abc8,
+       0xb9f010b4,
+       0x01aec80c,
+       0xfd11e4b6,
+       0x07f105be,
+       0x03f0c500,
+       0x000bd001,
+/* 0x01d6: mmctx_exec_loop */
+/* 0x01d6: mmctx_wait_free */
+       0xe7f104bd,
+       0xe3f0c500,
+       0x00eecf01,
+       0xf41fe4f0,
+       0xce98f30b,
+       0x05e9fd00,
+       0xc80007f1,
+       0xd00103f0,
+       0x04bd000e,
+       0xb804c0b6,
+       0x1bf404cd,
+       0x02abc8d8,
+/* 0x0207: mmctx_fini_wait */
+       0xf11f1bf4,
+       0xf0c500b7,
+       0xbbcf01b3,
+       0x1fb4f000,
+       0xf410b4b0,
+       0xa7f0f01b,
+       0xd021f405,
+/* 0x0223: mmctx_stop */
+       0xc82b0ef4,
+       0xb4b600ab,
+       0x0cb9f010,
+       0xf112b9f0,
+       0xf0c50007,
+       0x0bd00103,
+/* 0x023b: mmctx_stop_wait */
+       0xf104bd00,
+       0xf0c500b7,
+       0xbbcf01b3,
+       0x12bbc800,
+/* 0x024b: mmctx_done */
+       0xbdf31bf4,
+       0x0199f094,
+       0x170007f1,
+       0xd00203f0,
+       0x04bd0009,
+/* 0x025e: strand_wait */
+       0xa0f900f8,
+       0xf402a7f0,
+       0xa0fcd021,
+/* 0x026a: strand_pre */
+       0x97f000f8,
+       0xfc07f10c,
+       0x0203f04a,
+       0xbd0009d0,
+       0x5e21f504,
+/* 0x027f: strand_post */
+       0xf000f802,
+       0x07f10d97,
+       0x03f04afc,
+       0x0009d002,
+       0x21f504bd,
+       0x00f8025e,
+/* 0x0294: strand_set */
+       0xf10fc7f0,
+       0xf04ffc07,
+       0x0cd00203,
+       0xf004bd00,
+       0x07f10bc7,
+       0x03f04afc,
+       0x000cd002,
+       0x07f104bd,
+       0x03f04ffc,
+       0x000ed002,
+       0xc7f004bd,
+       0xfc07f10a,
+       0x0203f04a,
+       0xbd000cd0,
+       0x5e21f504,
+/* 0x02d3: strand_ctx_init */
+       0xbd00f802,
+       0x0399f094,
+       0x0f0007f1,
+       0xd00203f0,
+       0x04bd0009,
+       0x026a21f5,
+       0xf503e7f0,
+       0xbd029421,
+       0xfc07f1c4,
+       0x0203f047,
+       0xbd000cd0,
+       0x01c7f004,
+       0x4afc07f1,
+       0xd00203f0,
+       0x04bd000c,
+       0x025e21f5,
+       0xf1010c92,
+       0xf046fc07,
+       0x0cd00203,
+       0xf004bd00,
+       0x07f102c7,
+       0x03f04afc,
+       0x000cd002,
+       0x21f504bd,
+       0x21f5025e,
+       0x87f1027f,
+       0x83f04200,
+       0x0097f102,
+       0x0293f020,
+       0x950099cf,
+/* 0x034a: ctx_init_strand_loop */
+       0x8ed008fe,
+       0x408ed000,
+       0xb6808acf,
+       0xa0b606a5,
+       0x00eabb01,
+       0xb60480b6,
+       0x1bf40192,
+       0x08e4b6e8,
+       0xbdf2efbc,
+       0x0399f094,
+       0x170007f1,
+       0xd00203f0,
+       0x04bd0009,
+/* 0x037e: error */
+       0xe0f900f8,
+       0xf102ffb9,
+       0xf09814e7,
+       0x21f440e3,
+       0x01f7f09d,
+       0xf102ffb9,
+       0xf09c1ce7,
+       0x21f440e3,
+       0xf8e0fc9d,
+/* 0x03a1: init */
+       0xf104bd00,
+       0xf0420017,
+       0x11cf0013,
+       0x0911e700,
+       0x0814b601,
+       0xf00014fe,
+       0x07f10227,
+       0x03f01200,
+       0x0002d000,
+       0x17f104bd,
+       0x10fe04e6,
+       0x0007f100,
+       0x0003f007,
+       0xbd0000d0,
+       0x0427f004,
+       0x040007f1,
+       0xd00003f0,
+       0x04bd0002,
+       0xf11031f4,
+       0xf0820027,
+       0x22cf0123,
+       0x0137f000,
+       0xbb1f24f0,
+       0x32b60432,
+       0x05028001,
+       0xf1060380,
+       0xf0860027,
+       0x22cf0123,
+       0x04028000,
+       0x010027f1,
+       0xcf0223f0,
+       0x34bd0022,
+       0xf1082595,
+       0xf0c00007,
+       0x05d00103,
+       0xf104bd00,
+       0xf0c10007,
+       0x05d00103,
+       0x9804bd00,
+       0x0f98000e,
+       0x5021f501,
+       0x002fbb01,
+       0x98003fbb,
+       0x0f98010e,
+       0x5021f502,
+       0x050e9801,
+       0xbb00effd,
+       0x3ebb002e,
+       0x0235b600,
+       0xd30007f1,
+       0xd00103f0,
+       0x04bd0003,
+       0xb60825b6,
+       0x20b60635,
+       0x0130b601,
+       0xb60824b6,
+       0x2fb90834,
+       0xd321f502,
+       0x003fbb02,
+       0x010007f1,
+       0xd00203f0,
+       0x04bd0003,
+       0x29f024bd,
+       0x0007f11f,
+       0x0203f008,
+       0xbd0002d0,
+/* 0x04a9: main */
+       0x0031f404,
+       0xf00028f4,
+       0x21f41cd7,
+       0xf401f439,
+       0xf404e4b0,
+       0x81fe1e18,
+       0x0627f001,
+       0x12fd20bd,
+       0x01e4b604,
+       0xfe051efd,
+       0x21f50018,
+       0x0ef4059e,
+/* 0x04d9: main_not_ctx_xfer */
+       0x10ef94d3,
+       0xf501f5f0,
+       0xf4037e21,
+/* 0x04e6: ih */
+       0x80f9c60e,
+       0xf90188fe,
+       0xf990f980,
+       0xf9b0f9a0,
+       0xf9e0f9d0,
+       0xf104bdf0,
+       0xf00200a7,
+       0xaacf00a3,
+       0x04abc400,
+       0xf02c0bf4,
+       0xe7f11cd7,
+       0xe3f01a00,
+       0x00eecf00,
+       0x1900f7f1,
+       0xcf00f3f0,
+       0x21f400ff,
+       0x01e7f004,
+       0x1d0007f1,
+       0xd00003f0,
+       0x04bd000e,
+/* 0x0534: ih_no_fifo */
+       0x010007f1,
+       0xd00003f0,
+       0x04bd000a,
+       0xe0fcf0fc,
+       0xb0fcd0fc,
+       0x90fca0fc,
+       0x88fe80fc,
+       0xf480fc00,
+       0x01f80032,
+/* 0x0558: hub_barrier_done */
+       0x9801f7f0,
+       0xfebb040e,
+       0x02ffb904,
+       0x9418e7f1,
+       0xf440e3f0,
+       0x00f89d21,
+/* 0x0570: ctx_redswitch */
+       0xf120f7f0,
+       0xf0850007,
+       0x0fd00103,
+       0xf004bd00,
+/* 0x0582: ctx_redswitch_delay */
+       0xe2b608e7,
+       0xfd1bf401,
+       0x0800f5f1,
+       0x0200f5f1,
+       0x850007f1,
+       0xd00103f0,
+       0x04bd000f,
+/* 0x059e: ctx_xfer */
+       0x07f100f8,
+       0x03f08100,
+       0x000fd002,
+       0x11f404bd,
+       0x7021f507,
+/* 0x05b1: ctx_xfer_not_load */
+       0x6a21f505,
+       0xf124bd02,
+       0xf047fc07,
+       0x02d00203,
+       0xf004bd00,
+       0x20b6012c,
+       0xfc07f103,
+       0x0203f04a,
+       0xbd0002d0,
+       0x01acf004,
+       0xf102a5f0,
+       0xf00000b7,
+       0x0c9850b3,
+       0x0fc4b604,
+       0x9800bcbb,
+       0x0d98000c,
+       0x00e7f001,
+       0x016f21f5,
+       0xf001acf0,
+       0xb7f104a5,
+       0xb3f04000,
+       0x040c9850,
+       0xbb0fc4b6,
+       0x0c9800bc,
+       0x020d9801,
+       0xf1060f98,
+       0xf50800e7,
+       0xf5016f21,
+       0xf4025e21,
+       0x12f40601,
+/* 0x0629: ctx_xfer_post */
+       0x7f21f507,
+/* 0x062d: ctx_xfer_done */
+       0x5821f502,
+       0x0000f805,
+       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,
+};
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/gr/fuc/gpcgf117.fuc3 b/drivers/gpu/drm/nouveau/nvkm/engine/gr/fuc/gpcgf117.fuc3
new file mode 100644 (file)
index 0000000..c918f7d
--- /dev/null
@@ -0,0 +1,42 @@
+/*
+ * Copyright 2013 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 <bskeggs@redhat.com>
+ */
+
+#define NV_PGRAPH_GPCX_UNK__SIZE                                     0x00000001
+
+#define CHIPSET GF117
+#include "macros.fuc"
+
+.section #gf117_grgpc_data
+#define INCLUDE_DATA
+#include "com.fuc"
+#include "gpc.fuc"
+#undef INCLUDE_DATA
+
+.section #gf117_grgpc_code
+#define INCLUDE_CODE
+bra #init
+#include "com.fuc"
+#include "gpc.fuc"
+.align 256
+#undef INCLUDE_CODE
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/gr/fuc/gpcgf117.fuc3.h b/drivers/gpu/drm/nouveau/nvkm/engine/gr/fuc/gpcgf117.fuc3.h
new file mode 100644 (file)
index 0000000..9a36d9c
--- /dev/null
@@ -0,0 +1,537 @@
+uint32_t gf117_grgpc_data[] = {
+/* 0x0000: gpc_mmio_list_head */
+       0x0000006c,
+/* 0x0004: gpc_mmio_list_tail */
+/* 0x0004: tpc_mmio_list_head */
+       0x0000006c,
+/* 0x0008: tpc_mmio_list_tail */
+/* 0x0008: unk_mmio_list_head */
+       0x0000006c,
+/* 0x000c: unk_mmio_list_tail */
+       0x0000006c,
+/* 0x0010: gpc_id */
+       0x00000000,
+/* 0x0014: tpc_count */
+       0x00000000,
+/* 0x0018: tpc_mask */
+       0x00000000,
+/* 0x001c: unk_count */
+       0x00000000,
+/* 0x0020: unk_mask */
+       0x00000000,
+/* 0x0024: cmd_queue */
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+};
+
+uint32_t gf117_grgpc_code[] = {
+       0x03a10ef5,
+/* 0x0004: queue_put */
+       0x9800d898,
+       0x86f001d9,
+       0x0489b808,
+       0xf00c1bf4,
+       0x21f502f7,
+       0x00f8037e,
+/* 0x001c: queue_put_next */
+       0xb60798c4,
+       0x8dbb0384,
+       0x0880b600,
+       0x80008e80,
+       0x90b6018f,
+       0x0f94f001,
+       0xf801d980,
+/* 0x0039: queue_get */
+       0x0131f400,
+       0x9800d898,
+       0x89b801d9,
+       0x210bf404,
+       0xb60789c4,
+       0x9dbb0394,
+       0x0890b600,
+       0x98009e98,
+       0x80b6019f,
+       0x0f84f001,
+       0xf400d880,
+/* 0x0066: queue_get_done */
+       0x00f80132,
+/* 0x0068: nv_rd32 */
+       0xf002ecb9,
+       0x07f11fc9,
+       0x03f0ca00,
+       0x000cd001,
+/* 0x007a: nv_rd32_wait */
+       0xc7f104bd,
+       0xc3f0ca00,
+       0x00cccf01,
+       0xf41fccc8,
+       0xa7f0f31b,
+       0x1021f506,
+       0x00f7f101,
+       0x01f3f0cb,
+       0xf800ffcf,
+/* 0x009d: nv_wr32 */
+       0x0007f100,
+       0x0103f0cc,
+       0xbd000fd0,
+       0x02ecb904,
+       0xf01fc9f0,
+       0x07f11ec9,
+       0x03f0ca00,
+       0x000cd001,
+/* 0x00be: nv_wr32_wait */
+       0xc7f104bd,
+       0xc3f0ca00,
+       0x00cccf01,
+       0xf41fccc8,
+       0x00f8f31b,
+/* 0x00d0: wait_donez */
+       0x99f094bd,
+       0x0007f100,
+       0x0203f00f,
+       0xbd0009d0,
+       0x0007f104,
+       0x0203f006,
+       0xbd000ad0,
+/* 0x00ed: wait_donez_ne */
+       0x0087f104,
+       0x0183f000,
+       0xff0088cf,
+       0x1bf4888a,
+       0xf094bdf3,
+       0x07f10099,
+       0x03f01700,
+       0x0009d002,
+       0x00f804bd,
+/* 0x0110: wait_doneo */
+       0x99f094bd,
+       0x0007f100,
+       0x0203f00f,
+       0xbd0009d0,
+       0x0007f104,
+       0x0203f006,
+       0xbd000ad0,
+/* 0x012d: wait_doneo_e */
+       0x0087f104,
+       0x0183f000,
+       0xff0088cf,
+       0x0bf4888a,
+       0xf094bdf3,
+       0x07f10099,
+       0x03f01700,
+       0x0009d002,
+       0x00f804bd,
+/* 0x0150: mmctx_size */
+/* 0x0152: nv_mmctx_size_loop */
+       0xe89894bd,
+       0x1a85b600,
+       0xb60180b6,
+       0x98bb0284,
+       0x04e0b600,
+       0xf404efb8,
+       0x9fb9eb1b,
+/* 0x016f: mmctx_xfer */
+       0xbd00f802,
+       0x0199f094,
+       0x0f0007f1,
+       0xd00203f0,
+       0x04bd0009,
+       0xbbfd94bd,
+       0x120bf405,
+       0xc40007f1,
+       0xd00103f0,
+       0x04bd000b,
+/* 0x0197: mmctx_base_disabled */
+       0xfd0099f0,
+       0x0bf405ee,
+       0x0007f11e,
+       0x0103f0c6,
+       0xbd000ed0,
+       0x0007f104,
+       0x0103f0c7,
+       0xbd000fd0,
+       0x0199f004,
+/* 0x01b8: mmctx_multi_disabled */
+       0xb600abc8,
+       0xb9f010b4,
+       0x01aec80c,
+       0xfd11e4b6,
+       0x07f105be,
+       0x03f0c500,
+       0x000bd001,
+/* 0x01d6: mmctx_exec_loop */
+/* 0x01d6: mmctx_wait_free */
+       0xe7f104bd,
+       0xe3f0c500,
+       0x00eecf01,
+       0xf41fe4f0,
+       0xce98f30b,
+       0x05e9fd00,
+       0xc80007f1,
+       0xd00103f0,
+       0x04bd000e,
+       0xb804c0b6,
+       0x1bf404cd,
+       0x02abc8d8,
+/* 0x0207: mmctx_fini_wait */
+       0xf11f1bf4,
+       0xf0c500b7,
+       0xbbcf01b3,
+       0x1fb4f000,
+       0xf410b4b0,
+       0xa7f0f01b,
+       0xd021f405,
+/* 0x0223: mmctx_stop */
+       0xc82b0ef4,
+       0xb4b600ab,
+       0x0cb9f010,
+       0xf112b9f0,
+       0xf0c50007,
+       0x0bd00103,
+/* 0x023b: mmctx_stop_wait */
+       0xf104bd00,
+       0xf0c500b7,
+       0xbbcf01b3,
+       0x12bbc800,
+/* 0x024b: mmctx_done */
+       0xbdf31bf4,
+       0x0199f094,
+       0x170007f1,
+       0xd00203f0,
+       0x04bd0009,
+/* 0x025e: strand_wait */
+       0xa0f900f8,
+       0xf402a7f0,
+       0xa0fcd021,
+/* 0x026a: strand_pre */
+       0x97f000f8,
+       0xfc07f10c,
+       0x0203f04a,
+       0xbd0009d0,
+       0x5e21f504,
+/* 0x027f: strand_post */
+       0xf000f802,
+       0x07f10d97,
+       0x03f04afc,
+       0x0009d002,
+       0x21f504bd,
+       0x00f8025e,
+/* 0x0294: strand_set */
+       0xf10fc7f0,
+       0xf04ffc07,
+       0x0cd00203,
+       0xf004bd00,
+       0x07f10bc7,
+       0x03f04afc,
+       0x000cd002,
+       0x07f104bd,
+       0x03f04ffc,
+       0x000ed002,
+       0xc7f004bd,
+       0xfc07f10a,
+       0x0203f04a,
+       0xbd000cd0,
+       0x5e21f504,
+/* 0x02d3: strand_ctx_init */
+       0xbd00f802,
+       0x0399f094,
+       0x0f0007f1,
+       0xd00203f0,
+       0x04bd0009,
+       0x026a21f5,
+       0xf503e7f0,
+       0xbd029421,
+       0xfc07f1c4,
+       0x0203f047,
+       0xbd000cd0,
+       0x01c7f004,
+       0x4afc07f1,
+       0xd00203f0,
+       0x04bd000c,
+       0x025e21f5,
+       0xf1010c92,
+       0xf046fc07,
+       0x0cd00203,
+       0xf004bd00,
+       0x07f102c7,
+       0x03f04afc,
+       0x000cd002,
+       0x21f504bd,
+       0x21f5025e,
+       0x87f1027f,
+       0x83f04200,
+       0x0097f102,
+       0x0293f020,
+       0x950099cf,
+/* 0x034a: ctx_init_strand_loop */
+       0x8ed008fe,
+       0x408ed000,
+       0xb6808acf,
+       0xa0b606a5,
+       0x00eabb01,
+       0xb60480b6,
+       0x1bf40192,
+       0x08e4b6e8,
+       0xbdf2efbc,
+       0x0399f094,
+       0x170007f1,
+       0xd00203f0,
+       0x04bd0009,
+/* 0x037e: error */
+       0xe0f900f8,
+       0xf102ffb9,
+       0xf09814e7,
+       0x21f440e3,
+       0x01f7f09d,
+       0xf102ffb9,
+       0xf09c1ce7,
+       0x21f440e3,
+       0xf8e0fc9d,
+/* 0x03a1: init */
+       0xf104bd00,
+       0xf0420017,
+       0x11cf0013,
+       0x0911e700,
+       0x0814b601,
+       0xf00014fe,
+       0x07f10227,
+       0x03f01200,
+       0x0002d000,
+       0x17f104bd,
+       0x10fe0530,
+       0x0007f100,
+       0x0003f007,
+       0xbd0000d0,
+       0x0427f004,
+       0x040007f1,
+       0xd00003f0,
+       0x04bd0002,
+       0xf11031f4,
+       0xf0820027,
+       0x22cf0123,
+       0x0137f000,
+       0xbb1f24f0,
+       0x32b60432,
+       0x05028001,
+       0xf1060380,
+       0xf0860027,
+       0x22cf0123,
+       0x04028000,
+       0x0c30e7f1,
+       0xbd50e3f0,
+       0xbd34bd24,
+/* 0x0421: init_unk_loop */
+       0x6821f444,
+       0xf400f6b0,
+       0xf7f00f0b,
+       0x04f2bb01,
+       0xb6054ffd,
+/* 0x0436: init_unk_next */
+       0x20b60130,
+       0x04e0b601,
+       0xf40126b0,
+/* 0x0442: init_unk_done */
+       0x0380e21b,
+       0x08048007,
+       0x010027f1,
+       0xcf0223f0,
+       0x34bd0022,
+       0xf1082595,
+       0xf0c00007,
+       0x05d00103,
+       0xf104bd00,
+       0xf0c10007,
+       0x05d00103,
+       0x9804bd00,
+       0x0f98000e,
+       0x5021f501,
+       0x002fbb01,
+       0x98003fbb,
+       0x0f98010e,
+       0x5021f502,
+       0x050e9801,
+       0xbb00effd,
+       0x3ebb002e,
+       0x020e9800,
+       0xf5030f98,
+       0x98015021,
+       0xeffd070e,
+       0x002ebb00,
+       0xb6003ebb,
+       0x07f10235,
+       0x03f0d300,
+       0x0003d001,
+       0x25b604bd,
+       0x0635b608,
+       0xb60120b6,
+       0x24b60130,
+       0x0834b608,
+       0xf5022fb9,
+       0xbb02d321,
+       0x07f1003f,
+       0x03f00100,
+       0x0003d002,
+       0x24bd04bd,
+       0xf11f29f0,
+       0xf0080007,
+       0x02d00203,
+/* 0x04f3: main */
+       0xf404bd00,
+       0x28f40031,
+       0x24d7f000,
+       0xf43921f4,
+       0xe4b0f401,
+       0x1e18f404,
+       0xf00181fe,
+       0x20bd0627,
+       0xb60412fd,
+       0x1efd01e4,
+       0x0018fe05,
+       0x05e821f5,
+/* 0x0523: main_not_ctx_xfer */
+       0x94d30ef4,
+       0xf5f010ef,
+       0x7e21f501,
+       0xc60ef403,
+/* 0x0530: ih */
+       0x88fe80f9,
+       0xf980f901,
+       0xf9a0f990,
+       0xf9d0f9b0,
+       0xbdf0f9e0,
+       0x00a7f104,
+       0x00a3f002,
+       0xc400aacf,
+       0x0bf404ab,
+       0x24d7f02c,
+       0x1a00e7f1,
+       0xcf00e3f0,
+       0xf7f100ee,
+       0xf3f01900,
+       0x00ffcf00,
+       0xf00421f4,
+       0x07f101e7,
+       0x03f01d00,
+       0x000ed000,
+/* 0x057e: ih_no_fifo */
+       0x07f104bd,
+       0x03f00100,
+       0x000ad000,
+       0xf0fc04bd,
+       0xd0fce0fc,
+       0xa0fcb0fc,
+       0x80fc90fc,
+       0xfc0088fe,
+       0x0032f480,
+/* 0x05a2: hub_barrier_done */
+       0xf7f001f8,
+       0x040e9801,
+       0xb904febb,
+       0xe7f102ff,
+       0xe3f09418,
+       0x9d21f440,
+/* 0x05ba: ctx_redswitch */
+       0xf7f000f8,
+       0x0007f120,
+       0x0103f085,
+       0xbd000fd0,
+       0x08e7f004,
+/* 0x05cc: ctx_redswitch_delay */
+       0xf401e2b6,
+       0xf5f1fd1b,
+       0xf5f10800,
+       0x07f10200,
+       0x03f08500,
+       0x000fd001,
+       0x00f804bd,
+/* 0x05e8: ctx_xfer */
+       0x810007f1,
+       0xd00203f0,
+       0x04bd000f,
+       0xf50711f4,
+/* 0x05fb: ctx_xfer_not_load */
+       0xf505ba21,
+       0xbd026a21,
+       0xfc07f124,
+       0x0203f047,
+       0xbd0002d0,
+       0x012cf004,
+       0xf10320b6,
+       0xf04afc07,
+       0x02d00203,
+       0xf004bd00,
+       0xa5f001ac,
+       0x00b7f102,
+       0x50b3f000,
+       0xb6040c98,
+       0xbcbb0fc4,
+       0x000c9800,
+       0xf0010d98,
+       0x21f500e7,
+       0xacf0016f,
+       0x00b7f101,
+       0x50b3f040,
+       0xb6040c98,
+       0xbcbb0fc4,
+       0x010c9800,
+       0x98020d98,
+       0xe7f1060f,
+       0x21f50800,
+       0xacf0016f,
+       0x04a5f001,
+       0x3000b7f1,
+       0x9850b3f0,
+       0xc4b6040c,
+       0x00bcbb0f,
+       0x98020c98,
+       0x0f98030d,
+       0x00e7f108,
+       0x6f21f502,
+       0x5e21f501,
+       0x0601f402,
+/* 0x0697: ctx_xfer_post */
+       0xf50712f4,
+/* 0x069b: ctx_xfer_done */
+       0xf5027f21,
+       0xf805a221,
+       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/drivers/gpu/drm/nouveau/nvkm/engine/gr/fuc/gpcgk104.fuc3 b/drivers/gpu/drm/nouveau/nvkm/engine/gr/fuc/gpcgk104.fuc3
new file mode 100644 (file)
index 0000000..b80cdfd
--- /dev/null
@@ -0,0 +1,42 @@
+/*
+ * Copyright 2013 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 <bskeggs@redhat.com>
+ */
+
+#define NV_PGRAPH_GPCX_UNK__SIZE                                     0x00000001
+
+#define CHIPSET GK100
+#include "macros.fuc"
+
+.section #gk104_grgpc_data
+#define INCLUDE_DATA
+#include "com.fuc"
+#include "gpc.fuc"
+#undef INCLUDE_DATA
+
+.section #gk104_grgpc_code
+#define INCLUDE_CODE
+bra #init
+#include "com.fuc"
+#include "gpc.fuc"
+.align 256
+#undef INCLUDE_CODE
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/gr/fuc/gpcgk104.fuc3.h b/drivers/gpu/drm/nouveau/nvkm/engine/gr/fuc/gpcgk104.fuc3.h
new file mode 100644 (file)
index 0000000..49020ff
--- /dev/null
@@ -0,0 +1,537 @@
+uint32_t gk104_grgpc_data[] = {
+/* 0x0000: gpc_mmio_list_head */
+       0x0000006c,
+/* 0x0004: gpc_mmio_list_tail */
+/* 0x0004: tpc_mmio_list_head */
+       0x0000006c,
+/* 0x0008: tpc_mmio_list_tail */
+/* 0x0008: unk_mmio_list_head */
+       0x0000006c,
+/* 0x000c: unk_mmio_list_tail */
+       0x0000006c,
+/* 0x0010: gpc_id */
+       0x00000000,
+/* 0x0014: tpc_count */
+       0x00000000,
+/* 0x0018: tpc_mask */
+       0x00000000,
+/* 0x001c: unk_count */
+       0x00000000,
+/* 0x0020: unk_mask */
+       0x00000000,
+/* 0x0024: cmd_queue */
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+};
+
+uint32_t gk104_grgpc_code[] = {
+       0x03a10ef5,
+/* 0x0004: queue_put */
+       0x9800d898,
+       0x86f001d9,
+       0x0489b808,
+       0xf00c1bf4,
+       0x21f502f7,
+       0x00f8037e,
+/* 0x001c: queue_put_next */
+       0xb60798c4,
+       0x8dbb0384,
+       0x0880b600,
+       0x80008e80,
+       0x90b6018f,
+       0x0f94f001,
+       0xf801d980,
+/* 0x0039: queue_get */
+       0x0131f400,
+       0x9800d898,
+       0x89b801d9,
+       0x210bf404,
+       0xb60789c4,
+       0x9dbb0394,
+       0x0890b600,
+       0x98009e98,
+       0x80b6019f,
+       0x0f84f001,
+       0xf400d880,
+/* 0x0066: queue_get_done */
+       0x00f80132,
+/* 0x0068: nv_rd32 */
+       0xf002ecb9,
+       0x07f11fc9,
+       0x03f0ca00,
+       0x000cd001,
+/* 0x007a: nv_rd32_wait */
+       0xc7f104bd,
+       0xc3f0ca00,
+       0x00cccf01,
+       0xf41fccc8,
+       0xa7f0f31b,
+       0x1021f506,
+       0x00f7f101,
+       0x01f3f0cb,
+       0xf800ffcf,
+/* 0x009d: nv_wr32 */
+       0x0007f100,
+       0x0103f0cc,
+       0xbd000fd0,
+       0x02ecb904,
+       0xf01fc9f0,
+       0x07f11ec9,
+       0x03f0ca00,
+       0x000cd001,
+/* 0x00be: nv_wr32_wait */
+       0xc7f104bd,
+       0xc3f0ca00,
+       0x00cccf01,
+       0xf41fccc8,
+       0x00f8f31b,
+/* 0x00d0: wait_donez */
+       0x99f094bd,
+       0x0007f100,
+       0x0203f00f,
+       0xbd0009d0,
+       0x0007f104,
+       0x0203f006,
+       0xbd000ad0,
+/* 0x00ed: wait_donez_ne */
+       0x0087f104,
+       0x0183f000,
+       0xff0088cf,
+       0x1bf4888a,
+       0xf094bdf3,
+       0x07f10099,
+       0x03f01700,
+       0x0009d002,
+       0x00f804bd,
+/* 0x0110: wait_doneo */
+       0x99f094bd,
+       0x0007f100,
+       0x0203f00f,
+       0xbd0009d0,
+       0x0007f104,
+       0x0203f006,
+       0xbd000ad0,
+/* 0x012d: wait_doneo_e */
+       0x0087f104,
+       0x0183f000,
+       0xff0088cf,
+       0x0bf4888a,
+       0xf094bdf3,
+       0x07f10099,
+       0x03f01700,
+       0x0009d002,
+       0x00f804bd,
+/* 0x0150: mmctx_size */
+/* 0x0152: nv_mmctx_size_loop */
+       0xe89894bd,
+       0x1a85b600,
+       0xb60180b6,
+       0x98bb0284,
+       0x04e0b600,
+       0xf404efb8,
+       0x9fb9eb1b,
+/* 0x016f: mmctx_xfer */
+       0xbd00f802,
+       0x0199f094,
+       0x0f0007f1,
+       0xd00203f0,
+       0x04bd0009,
+       0xbbfd94bd,
+       0x120bf405,
+       0xc40007f1,
+       0xd00103f0,
+       0x04bd000b,
+/* 0x0197: mmctx_base_disabled */
+       0xfd0099f0,
+       0x0bf405ee,
+       0x0007f11e,
+       0x0103f0c6,
+       0xbd000ed0,
+       0x0007f104,
+       0x0103f0c7,
+       0xbd000fd0,
+       0x0199f004,
+/* 0x01b8: mmctx_multi_disabled */
+       0xb600abc8,
+       0xb9f010b4,
+       0x01aec80c,
+       0xfd11e4b6,
+       0x07f105be,
+       0x03f0c500,
+       0x000bd001,
+/* 0x01d6: mmctx_exec_loop */
+/* 0x01d6: mmctx_wait_free */
+       0xe7f104bd,
+       0xe3f0c500,
+       0x00eecf01,
+       0xf41fe4f0,
+       0xce98f30b,
+       0x05e9fd00,
+       0xc80007f1,
+       0xd00103f0,
+       0x04bd000e,
+       0xb804c0b6,
+       0x1bf404cd,
+       0x02abc8d8,
+/* 0x0207: mmctx_fini_wait */
+       0xf11f1bf4,
+       0xf0c500b7,
+       0xbbcf01b3,
+       0x1fb4f000,
+       0xf410b4b0,
+       0xa7f0f01b,
+       0xd021f405,
+/* 0x0223: mmctx_stop */
+       0xc82b0ef4,
+       0xb4b600ab,
+       0x0cb9f010,
+       0xf112b9f0,
+       0xf0c50007,
+       0x0bd00103,
+/* 0x023b: mmctx_stop_wait */
+       0xf104bd00,
+       0xf0c500b7,
+       0xbbcf01b3,
+       0x12bbc800,
+/* 0x024b: mmctx_done */
+       0xbdf31bf4,
+       0x0199f094,
+       0x170007f1,
+       0xd00203f0,
+       0x04bd0009,
+/* 0x025e: strand_wait */
+       0xa0f900f8,
+       0xf402a7f0,
+       0xa0fcd021,
+/* 0x026a: strand_pre */
+       0x97f000f8,
+       0xfc07f10c,
+       0x0203f04a,
+       0xbd0009d0,
+       0x5e21f504,
+/* 0x027f: strand_post */
+       0xf000f802,
+       0x07f10d97,
+       0x03f04afc,
+       0x0009d002,
+       0x21f504bd,
+       0x00f8025e,
+/* 0x0294: strand_set */
+       0xf10fc7f0,
+       0xf04ffc07,
+       0x0cd00203,
+       0xf004bd00,
+       0x07f10bc7,
+       0x03f04afc,
+       0x000cd002,
+       0x07f104bd,
+       0x03f04ffc,
+       0x000ed002,
+       0xc7f004bd,
+       0xfc07f10a,
+       0x0203f04a,
+       0xbd000cd0,
+       0x5e21f504,
+/* 0x02d3: strand_ctx_init */
+       0xbd00f802,
+       0x0399f094,
+       0x0f0007f1,
+       0xd00203f0,
+       0x04bd0009,
+       0x026a21f5,
+       0xf503e7f0,
+       0xbd029421,
+       0xfc07f1c4,
+       0x0203f047,
+       0xbd000cd0,
+       0x01c7f004,
+       0x4afc07f1,
+       0xd00203f0,
+       0x04bd000c,
+       0x025e21f5,
+       0xf1010c92,
+       0xf046fc07,
+       0x0cd00203,
+       0xf004bd00,
+       0x07f102c7,
+       0x03f04afc,
+       0x000cd002,
+       0x21f504bd,
+       0x21f5025e,
+       0x87f1027f,
+       0x83f04200,
+       0x0097f102,
+       0x0293f020,
+       0x950099cf,
+/* 0x034a: ctx_init_strand_loop */
+       0x8ed008fe,
+       0x408ed000,
+       0xb6808acf,
+       0xa0b606a5,
+       0x00eabb01,
+       0xb60480b6,
+       0x1bf40192,
+       0x08e4b6e8,
+       0xbdf2efbc,
+       0x0399f094,
+       0x170007f1,
+       0xd00203f0,
+       0x04bd0009,
+/* 0x037e: error */
+       0xe0f900f8,
+       0xf102ffb9,
+       0xf09814e7,
+       0x21f440e3,
+       0x01f7f09d,
+       0xf102ffb9,
+       0xf09c1ce7,
+       0x21f440e3,
+       0xf8e0fc9d,
+/* 0x03a1: init */
+       0xf104bd00,
+       0xf0420017,
+       0x11cf0013,
+       0x0911e700,
+       0x0814b601,
+       0xf00014fe,
+       0x07f10227,
+       0x03f01200,
+       0x0002d000,
+       0x17f104bd,
+       0x10fe0530,
+       0x0007f100,
+       0x0003f007,
+       0xbd0000d0,
+       0x0427f004,
+       0x040007f1,
+       0xd00003f0,
+       0x04bd0002,
+       0xf11031f4,
+       0xf0820027,
+       0x22cf0123,
+       0x0137f000,
+       0xbb1f24f0,
+       0x32b60432,
+       0x05028001,
+       0xf1060380,
+       0xf0860027,
+       0x22cf0123,
+       0x04028000,
+       0x0c30e7f1,
+       0xbd50e3f0,
+       0xbd34bd24,
+/* 0x0421: init_unk_loop */
+       0x6821f444,
+       0xf400f6b0,
+       0xf7f00f0b,
+       0x04f2bb01,
+       0xb6054ffd,
+/* 0x0436: init_unk_next */
+       0x20b60130,
+       0x04e0b601,
+       0xf40126b0,
+/* 0x0442: init_unk_done */
+       0x0380e21b,
+       0x08048007,
+       0x010027f1,
+       0xcf0223f0,
+       0x34bd0022,
+       0xf1082595,
+       0xf0c00007,
+       0x05d00103,
+       0xf104bd00,
+       0xf0c10007,
+       0x05d00103,
+       0x9804bd00,
+       0x0f98000e,
+       0x5021f501,
+       0x002fbb01,
+       0x98003fbb,
+       0x0f98010e,
+       0x5021f502,
+       0x050e9801,
+       0xbb00effd,
+       0x3ebb002e,
+       0x020e9800,
+       0xf5030f98,
+       0x98015021,
+       0xeffd070e,
+       0x002ebb00,
+       0xb6003ebb,
+       0x07f10235,
+       0x03f0d300,
+       0x0003d001,
+       0x25b604bd,
+       0x0635b608,
+       0xb60120b6,
+       0x24b60130,
+       0x0834b608,
+       0xf5022fb9,
+       0xbb02d321,
+       0x07f1003f,
+       0x03f00100,
+       0x0003d002,
+       0x24bd04bd,
+       0xf11f29f0,
+       0xf0080007,
+       0x02d00203,
+/* 0x04f3: main */
+       0xf404bd00,
+       0x28f40031,
+       0x24d7f000,
+       0xf43921f4,
+       0xe4b0f401,
+       0x1e18f404,
+       0xf00181fe,
+       0x20bd0627,
+       0xb60412fd,
+       0x1efd01e4,
+       0x0018fe05,
+       0x05e821f5,
+/* 0x0523: main_not_ctx_xfer */
+       0x94d30ef4,
+       0xf5f010ef,
+       0x7e21f501,
+       0xc60ef403,
+/* 0x0530: ih */
+       0x88fe80f9,
+       0xf980f901,
+       0xf9a0f990,
+       0xf9d0f9b0,
+       0xbdf0f9e0,
+       0x00a7f104,
+       0x00a3f002,
+       0xc400aacf,
+       0x0bf404ab,
+       0x24d7f02c,
+       0x1a00e7f1,
+       0xcf00e3f0,
+       0xf7f100ee,
+       0xf3f01900,
+       0x00ffcf00,
+       0xf00421f4,
+       0x07f101e7,
+       0x03f01d00,
+       0x000ed000,
+/* 0x057e: ih_no_fifo */
+       0x07f104bd,
+       0x03f00100,
+       0x000ad000,
+       0xf0fc04bd,
+       0xd0fce0fc,
+       0xa0fcb0fc,
+       0x80fc90fc,
+       0xfc0088fe,
+       0x0032f480,
+/* 0x05a2: hub_barrier_done */
+       0xf7f001f8,
+       0x040e9801,
+       0xb904febb,
+       0xe7f102ff,
+       0xe3f09418,
+       0x9d21f440,
+/* 0x05ba: ctx_redswitch */
+       0xf7f000f8,
+       0x0007f120,
+       0x0103f085,
+       0xbd000fd0,
+       0x08e7f004,
+/* 0x05cc: ctx_redswitch_delay */
+       0xf401e2b6,
+       0xf5f1fd1b,
+       0xf5f10800,
+       0x07f10200,
+       0x03f08500,
+       0x000fd001,
+       0x00f804bd,
+/* 0x05e8: ctx_xfer */
+       0x810007f1,
+       0xd00203f0,
+       0x04bd000f,
+       0xf50711f4,
+/* 0x05fb: ctx_xfer_not_load */
+       0xf505ba21,
+       0xbd026a21,
+       0xfc07f124,
+       0x0203f047,
+       0xbd0002d0,
+       0x012cf004,
+       0xf10320b6,
+       0xf04afc07,
+       0x02d00203,
+       0xf004bd00,
+       0xa5f001ac,
+       0x00b7f102,
+       0x50b3f000,
+       0xb6040c98,
+       0xbcbb0fc4,
+       0x000c9800,
+       0xf0010d98,
+       0x21f500e7,
+       0xacf0016f,
+       0x00b7f101,
+       0x50b3f040,
+       0xb6040c98,
+       0xbcbb0fc4,
+       0x010c9800,
+       0x98020d98,
+       0xe7f1060f,
+       0x21f50800,
+       0xacf0016f,
+       0x04a5f001,
+       0x3000b7f1,
+       0x9850b3f0,
+       0xc4b6040c,
+       0x00bcbb0f,
+       0x98020c98,
+       0x0f98030d,
+       0x00e7f108,
+       0x6f21f502,
+       0x5e21f501,
+       0x0601f402,
+/* 0x0697: ctx_xfer_post */
+       0xf50712f4,
+/* 0x069b: ctx_xfer_done */
+       0xf5027f21,
+       0xf805a221,
+       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/drivers/gpu/drm/nouveau/nvkm/engine/gr/fuc/gpcgk110.fuc3 b/drivers/gpu/drm/nouveau/nvkm/engine/gr/fuc/gpcgk110.fuc3
new file mode 100644 (file)
index 0000000..98d85fe
--- /dev/null
@@ -0,0 +1,42 @@
+/*
+ * Copyright 2013 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 <bskeggs@redhat.com>
+ */
+
+#define NV_PGRAPH_GPCX_UNK__SIZE                                     0x00000002
+
+#define CHIPSET GK110
+#include "macros.fuc"
+
+.section #gk110_grgpc_data
+#define INCLUDE_DATA
+#include "com.fuc"
+#include "gpc.fuc"
+#undef INCLUDE_DATA
+
+.section #gk110_grgpc_code
+#define INCLUDE_CODE
+bra #init
+#include "com.fuc"
+#include "gpc.fuc"
+.align 256
+#undef INCLUDE_CODE
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/gr/fuc/gpcgk110.fuc3.h b/drivers/gpu/drm/nouveau/nvkm/engine/gr/fuc/gpcgk110.fuc3.h
new file mode 100644 (file)
index 0000000..c95b07e
--- /dev/null
@@ -0,0 +1,537 @@
+uint32_t gk110_grgpc_data[] = {
+/* 0x0000: gpc_mmio_list_head */
+       0x0000006c,
+/* 0x0004: gpc_mmio_list_tail */
+/* 0x0004: tpc_mmio_list_head */
+       0x0000006c,
+/* 0x0008: tpc_mmio_list_tail */
+/* 0x0008: unk_mmio_list_head */
+       0x0000006c,
+/* 0x000c: unk_mmio_list_tail */
+       0x0000006c,
+/* 0x0010: gpc_id */
+       0x00000000,
+/* 0x0014: tpc_count */
+       0x00000000,
+/* 0x0018: tpc_mask */
+       0x00000000,
+/* 0x001c: unk_count */
+       0x00000000,
+/* 0x0020: unk_mask */
+       0x00000000,
+/* 0x0024: cmd_queue */
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+};
+
+uint32_t gk110_grgpc_code[] = {
+       0x03a10ef5,
+/* 0x0004: queue_put */
+       0x9800d898,
+       0x86f001d9,
+       0x0489b808,
+       0xf00c1bf4,
+       0x21f502f7,
+       0x00f8037e,
+/* 0x001c: queue_put_next */
+       0xb60798c4,
+       0x8dbb0384,
+       0x0880b600,
+       0x80008e80,
+       0x90b6018f,
+       0x0f94f001,
+       0xf801d980,
+/* 0x0039: queue_get */
+       0x0131f400,
+       0x9800d898,
+       0x89b801d9,
+       0x210bf404,
+       0xb60789c4,
+       0x9dbb0394,
+       0x0890b600,
+       0x98009e98,
+       0x80b6019f,
+       0x0f84f001,
+       0xf400d880,
+/* 0x0066: queue_get_done */
+       0x00f80132,
+/* 0x0068: nv_rd32 */
+       0xf002ecb9,
+       0x07f11fc9,
+       0x03f0ca00,
+       0x000cd001,
+/* 0x007a: nv_rd32_wait */
+       0xc7f104bd,
+       0xc3f0ca00,
+       0x00cccf01,
+       0xf41fccc8,
+       0xa7f0f31b,
+       0x1021f506,
+       0x00f7f101,
+       0x01f3f0cb,
+       0xf800ffcf,
+/* 0x009d: nv_wr32 */
+       0x0007f100,
+       0x0103f0cc,
+       0xbd000fd0,
+       0x02ecb904,
+       0xf01fc9f0,
+       0x07f11ec9,
+       0x03f0ca00,
+       0x000cd001,
+/* 0x00be: nv_wr32_wait */
+       0xc7f104bd,
+       0xc3f0ca00,
+       0x00cccf01,
+       0xf41fccc8,
+       0x00f8f31b,
+/* 0x00d0: wait_donez */
+       0x99f094bd,
+       0x0007f100,
+       0x0203f037,
+       0xbd0009d0,
+       0x0007f104,
+       0x0203f006,
+       0xbd000ad0,
+/* 0x00ed: wait_donez_ne */
+       0x0087f104,
+       0x0183f000,
+       0xff0088cf,
+       0x1bf4888a,
+       0xf094bdf3,
+       0x07f10099,
+       0x03f01700,
+       0x0009d002,
+       0x00f804bd,
+/* 0x0110: wait_doneo */
+       0x99f094bd,
+       0x0007f100,
+       0x0203f037,
+       0xbd0009d0,
+       0x0007f104,
+       0x0203f006,
+       0xbd000ad0,
+/* 0x012d: wait_doneo_e */
+       0x0087f104,
+       0x0183f000,
+       0xff0088cf,
+       0x0bf4888a,
+       0xf094bdf3,
+       0x07f10099,
+       0x03f01700,
+       0x0009d002,
+       0x00f804bd,
+/* 0x0150: mmctx_size */
+/* 0x0152: nv_mmctx_size_loop */
+       0xe89894bd,
+       0x1a85b600,
+       0xb60180b6,
+       0x98bb0284,
+       0x04e0b600,
+       0xf404efb8,
+       0x9fb9eb1b,
+/* 0x016f: mmctx_xfer */
+       0xbd00f802,
+       0x0199f094,
+       0x370007f1,
+       0xd00203f0,
+       0x04bd0009,
+       0xbbfd94bd,
+       0x120bf405,
+       0xc40007f1,
+       0xd00103f0,
+       0x04bd000b,
+/* 0x0197: mmctx_base_disabled */
+       0xfd0099f0,
+       0x0bf405ee,
+       0x0007f11e,
+       0x0103f0c6,
+       0xbd000ed0,
+       0x0007f104,
+       0x0103f0c7,
+       0xbd000fd0,
+       0x0199f004,
+/* 0x01b8: mmctx_multi_disabled */
+       0xb600abc8,
+       0xb9f010b4,
+       0x01aec80c,
+       0xfd11e4b6,
+       0x07f105be,
+       0x03f0c500,
+       0x000bd001,
+/* 0x01d6: mmctx_exec_loop */
+/* 0x01d6: mmctx_wait_free */
+       0xe7f104bd,
+       0xe3f0c500,
+       0x00eecf01,
+       0xf41fe4f0,
+       0xce98f30b,
+       0x05e9fd00,
+       0xc80007f1,
+       0xd00103f0,
+       0x04bd000e,
+       0xb804c0b6,
+       0x1bf404cd,
+       0x02abc8d8,
+/* 0x0207: mmctx_fini_wait */
+       0xf11f1bf4,
+       0xf0c500b7,
+       0xbbcf01b3,
+       0x1fb4f000,
+       0xf410b4b0,
+       0xa7f0f01b,
+       0xd021f405,
+/* 0x0223: mmctx_stop */
+       0xc82b0ef4,
+       0xb4b600ab,
+       0x0cb9f010,
+       0xf112b9f0,
+       0xf0c50007,
+       0x0bd00103,
+/* 0x023b: mmctx_stop_wait */
+       0xf104bd00,
+       0xf0c500b7,
+       0xbbcf01b3,
+       0x12bbc800,
+/* 0x024b: mmctx_done */
+       0xbdf31bf4,
+       0x0199f094,
+       0x170007f1,
+       0xd00203f0,
+       0x04bd0009,
+/* 0x025e: strand_wait */
+       0xa0f900f8,
+       0xf402a7f0,
+       0xa0fcd021,
+/* 0x026a: strand_pre */
+       0x97f000f8,
+       0xfc07f10c,
+       0x0203f04a,
+       0xbd0009d0,
+       0x5e21f504,
+/* 0x027f: strand_post */
+       0xf000f802,
+       0x07f10d97,
+       0x03f04afc,
+       0x0009d002,
+       0x21f504bd,
+       0x00f8025e,
+/* 0x0294: strand_set */
+       0xf10fc7f0,
+       0xf04ffc07,
+       0x0cd00203,
+       0xf004bd00,
+       0x07f10bc7,
+       0x03f04afc,
+       0x000cd002,
+       0x07f104bd,
+       0x03f04ffc,
+       0x000ed002,
+       0xc7f004bd,
+       0xfc07f10a,
+       0x0203f04a,
+       0xbd000cd0,
+       0x5e21f504,
+/* 0x02d3: strand_ctx_init */
+       0xbd00f802,
+       0x0399f094,
+       0x370007f1,
+       0xd00203f0,
+       0x04bd0009,
+       0x026a21f5,
+       0xf503e7f0,
+       0xbd029421,
+       0xfc07f1c4,
+       0x0203f047,
+       0xbd000cd0,
+       0x01c7f004,
+       0x4afc07f1,
+       0xd00203f0,
+       0x04bd000c,
+       0x025e21f5,
+       0xf1010c92,
+       0xf046fc07,
+       0x0cd00203,
+       0xf004bd00,
+       0x07f102c7,
+       0x03f04afc,
+       0x000cd002,
+       0x21f504bd,
+       0x21f5025e,
+       0x87f1027f,
+       0x83f04200,
+       0x0097f102,
+       0x0293f020,
+       0x950099cf,
+/* 0x034a: ctx_init_strand_loop */
+       0x8ed008fe,
+       0x408ed000,
+       0xb6808acf,
+       0xa0b606a5,
+       0x00eabb01,
+       0xb60480b6,
+       0x1bf40192,
+       0x08e4b6e8,
+       0xbdf2efbc,
+       0x0399f094,
+       0x170007f1,
+       0xd00203f0,
+       0x04bd0009,
+/* 0x037e: error */
+       0xe0f900f8,
+       0xf102ffb9,
+       0xf09814e7,
+       0x21f440e3,
+       0x01f7f09d,
+       0xf102ffb9,
+       0xf09c1ce7,
+       0x21f440e3,
+       0xf8e0fc9d,
+/* 0x03a1: init */
+       0xf104bd00,
+       0xf0420017,
+       0x11cf0013,
+       0x0911e700,
+       0x0814b601,
+       0xf00014fe,
+       0x07f10227,
+       0x03f01200,
+       0x0002d000,
+       0x17f104bd,
+       0x10fe0530,
+       0x0007f100,
+       0x0003f007,
+       0xbd0000d0,
+       0x0427f004,
+       0x040007f1,
+       0xd00003f0,
+       0x04bd0002,
+       0xf11031f4,
+       0xf0820027,
+       0x22cf0123,
+       0x0137f000,
+       0xbb1f24f0,
+       0x32b60432,
+       0x05028001,
+       0xf1060380,
+       0xf0860027,
+       0x22cf0123,
+       0x04028000,
+       0x0c30e7f1,
+       0xbd50e3f0,
+       0xbd34bd24,
+/* 0x0421: init_unk_loop */
+       0x6821f444,
+       0xf400f6b0,
+       0xf7f00f0b,
+       0x04f2bb01,
+       0xb6054ffd,
+/* 0x0436: init_unk_next */
+       0x20b60130,
+       0x04e0b601,
+       0xf40226b0,
+/* 0x0442: init_unk_done */
+       0x0380e21b,
+       0x08048007,
+       0x010027f1,
+       0xcf0223f0,
+       0x34bd0022,
+       0xf1082595,
+       0xf0c00007,
+       0x05d00103,
+       0xf104bd00,
+       0xf0c10007,
+       0x05d00103,
+       0x9804bd00,
+       0x0f98000e,
+       0x5021f501,
+       0x002fbb01,
+       0x98003fbb,
+       0x0f98010e,
+       0x5021f502,
+       0x050e9801,
+       0xbb00effd,
+       0x3ebb002e,
+       0x020e9800,
+       0xf5030f98,
+       0x98015021,
+       0xeffd070e,
+       0x002ebb00,
+       0xb6003ebb,
+       0x07f10235,
+       0x03f0d300,
+       0x0003d001,
+       0x25b604bd,
+       0x0635b608,
+       0xb60120b6,
+       0x24b60130,
+       0x0834b608,
+       0xf5022fb9,
+       0xbb02d321,
+       0x07f1003f,
+       0x03f00100,
+       0x0003d002,
+       0x24bd04bd,
+       0xf11f29f0,
+       0xf0300007,
+       0x02d00203,
+/* 0x04f3: main */
+       0xf404bd00,
+       0x28f40031,
+       0x24d7f000,
+       0xf43921f4,
+       0xe4b0f401,
+       0x1e18f404,
+       0xf00181fe,
+       0x20bd0627,
+       0xb60412fd,
+       0x1efd01e4,
+       0x0018fe05,
+       0x05e821f5,
+/* 0x0523: main_not_ctx_xfer */
+       0x94d30ef4,
+       0xf5f010ef,
+       0x7e21f501,
+       0xc60ef403,
+/* 0x0530: ih */
+       0x88fe80f9,
+       0xf980f901,
+       0xf9a0f990,
+       0xf9d0f9b0,
+       0xbdf0f9e0,
+       0x00a7f104,
+       0x00a3f002,
+       0xc400aacf,
+       0x0bf404ab,
+       0x24d7f02c,
+       0x1a00e7f1,
+       0xcf00e3f0,
+       0xf7f100ee,
+       0xf3f01900,
+       0x00ffcf00,
+       0xf00421f4,
+       0x07f101e7,
+       0x03f01d00,
+       0x000ed000,
+/* 0x057e: ih_no_fifo */
+       0x07f104bd,
+       0x03f00100,
+       0x000ad000,
+       0xf0fc04bd,
+       0xd0fce0fc,
+       0xa0fcb0fc,
+       0x80fc90fc,
+       0xfc0088fe,
+       0x0032f480,
+/* 0x05a2: hub_barrier_done */
+       0xf7f001f8,
+       0x040e9801,
+       0xb904febb,
+       0xe7f102ff,
+       0xe3f09418,
+       0x9d21f440,
+/* 0x05ba: ctx_redswitch */
+       0xf7f000f8,
+       0x0007f120,
+       0x0103f085,
+       0xbd000fd0,
+       0x08e7f004,
+/* 0x05cc: ctx_redswitch_delay */
+       0xf401e2b6,
+       0xf5f1fd1b,
+       0xf5f10800,
+       0x07f10200,
+       0x03f08500,
+       0x000fd001,
+       0x00f804bd,
+/* 0x05e8: ctx_xfer */
+       0x810007f1,
+       0xd00203f0,
+       0x04bd000f,
+       0xf50711f4,
+/* 0x05fb: ctx_xfer_not_load */
+       0xf505ba21,
+       0xbd026a21,
+       0xfc07f124,
+       0x0203f047,
+       0xbd0002d0,
+       0x012cf004,
+       0xf10320b6,
+       0xf04afc07,
+       0x02d00203,
+       0xf004bd00,
+       0xa5f001ac,
+       0x00b7f102,
+       0x50b3f000,
+       0xb6040c98,
+       0xbcbb0fc4,
+       0x000c9800,
+       0xf0010d98,
+       0x21f500e7,
+       0xacf0016f,
+       0x00b7f101,
+       0x50b3f040,
+       0xb6040c98,
+       0xbcbb0fc4,
+       0x010c9800,
+       0x98020d98,
+       0xe7f1060f,
+       0x21f50800,
+       0xacf0016f,
+       0x04a5f001,
+       0x3000b7f1,
+       0x9850b3f0,
+       0xc4b6040c,
+       0x00bcbb0f,
+       0x98020c98,
+       0x0f98030d,
+       0x00e7f108,
+       0x6f21f502,
+       0x5e21f501,
+       0x0601f402,
+/* 0x0697: ctx_xfer_post */
+       0xf50712f4,
+/* 0x069b: ctx_xfer_done */
+       0xf5027f21,
+       0xf805a221,
+       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/drivers/gpu/drm/nouveau/nvkm/engine/gr/fuc/gpcgk208.fuc5 b/drivers/gpu/drm/nouveau/nvkm/engine/gr/fuc/gpcgk208.fuc5
new file mode 100644 (file)
index 0000000..8f64299
--- /dev/null
@@ -0,0 +1,42 @@
+/*
+ * Copyright 2013 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 <bskeggs@redhat.com>
+ */
+
+#define NV_PGRAPH_GPCX_UNK__SIZE                                     0x00000001
+
+#define CHIPSET GK208
+#include "macros.fuc"
+
+.section #gk208_grgpc_data
+#define INCLUDE_DATA
+#include "com.fuc"
+#include "gpc.fuc"
+#undef INCLUDE_DATA
+
+.section #gk208_grgpc_code
+#define INCLUDE_CODE
+bra #init
+#include "com.fuc"
+#include "gpc.fuc"
+.align 256
+#undef INCLUDE_CODE
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/gr/fuc/gpcgk208.fuc5.h b/drivers/gpu/drm/nouveau/nvkm/engine/gr/fuc/gpcgk208.fuc5.h
new file mode 100644 (file)
index 0000000..7e1c28e
--- /dev/null
@@ -0,0 +1,473 @@
+uint32_t gk208_grgpc_data[] = {
+/* 0x0000: gpc_mmio_list_head */
+       0x0000006c,
+/* 0x0004: gpc_mmio_list_tail */
+/* 0x0004: tpc_mmio_list_head */
+       0x0000006c,
+/* 0x0008: tpc_mmio_list_tail */
+/* 0x0008: unk_mmio_list_head */
+       0x0000006c,
+/* 0x000c: unk_mmio_list_tail */
+       0x0000006c,
+/* 0x0010: gpc_id */
+       0x00000000,
+/* 0x0014: tpc_count */
+       0x00000000,
+/* 0x0018: tpc_mask */
+       0x00000000,
+/* 0x001c: unk_count */
+       0x00000000,
+/* 0x0020: unk_mask */
+       0x00000000,
+/* 0x0024: cmd_queue */
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+};
+
+uint32_t gk208_grgpc_code[] = {
+       0x03140ef5,
+/* 0x0004: queue_put */
+       0x9800d898,
+       0x86f001d9,
+       0xf489a408,
+       0x020f0b1b,
+       0x0002f87e,
+/* 0x001a: queue_put_next */
+       0x98c400f8,
+       0x0384b607,
+       0xb6008dbb,
+       0x8eb50880,
+       0x018fb500,
+       0xf00190b6,
+       0xd9b50f94,
+/* 0x0037: queue_get */
+       0xf400f801,
+       0xd8980131,
+       0x01d99800,
+       0x0bf489a4,
+       0x0789c421,
+       0xbb0394b6,
+       0x90b6009d,
+       0x009e9808,
+       0xb6019f98,
+       0x84f00180,
+       0x00d8b50f,
+/* 0x0063: queue_get_done */
+       0xf80132f4,
+/* 0x0065: nv_rd32 */
+       0xf0ecb200,
+       0x00801fc9,
+       0x0cf601ca,
+/* 0x0073: nv_rd32_wait */
+       0x8c04bd00,
+       0xcf01ca00,
+       0xccc800cc,
+       0xf61bf41f,
+       0xec7e060a,
+       0x008f0000,
+       0xffcf01cb,
+/* 0x008f: nv_wr32 */
+       0x8000f800,
+       0xf601cc00,
+       0x04bd000f,
+       0xc9f0ecb2,
+       0x1ec9f01f,
+       0x01ca0080,
+       0xbd000cf6,
+/* 0x00a9: nv_wr32_wait */
+       0xca008c04,
+       0x00cccf01,
+       0xf41fccc8,
+       0x00f8f61b,
+/* 0x00b8: wait_donez */
+       0x99f094bd,
+       0x37008000,
+       0x0009f602,
+       0x008004bd,
+       0x0af60206,
+/* 0x00cf: wait_donez_ne */
+       0x8804bd00,
+       0xcf010000,
+       0x8aff0088,
+       0xf61bf488,
+       0x99f094bd,
+       0x17008000,
+       0x0009f602,
+       0x00f804bd,
+/* 0x00ec: wait_doneo */
+       0x99f094bd,
+       0x37008000,
+       0x0009f602,
+       0x008004bd,
+       0x0af60206,
+/* 0x0103: wait_doneo_e */
+       0x8804bd00,
+       0xcf010000,
+       0x8aff0088,
+       0xf60bf488,
+       0x99f094bd,
+       0x17008000,
+       0x0009f602,
+       0x00f804bd,
+/* 0x0120: mmctx_size */
+/* 0x0122: nv_mmctx_size_loop */
+       0xe89894bd,
+       0x1a85b600,
+       0xb60180b6,
+       0x98bb0284,
+       0x04e0b600,
+       0x1bf4efa4,
+       0xf89fb2ec,
+/* 0x013d: mmctx_xfer */
+       0xf094bd00,
+       0x00800199,
+       0x09f60237,
+       0xbd04bd00,
+       0x05bbfd94,
+       0x800f0bf4,
+       0xf601c400,
+       0x04bd000b,
+/* 0x015f: mmctx_base_disabled */
+       0xfd0099f0,
+       0x0bf405ee,
+       0xc6008018,
+       0x000ef601,
+       0x008004bd,
+       0x0ff601c7,
+       0xf004bd00,
+/* 0x017a: mmctx_multi_disabled */
+       0xabc80199,
+       0x10b4b600,
+       0xc80cb9f0,
+       0xe4b601ae,
+       0x05befd11,
+       0x01c50080,
+       0xbd000bf6,
+/* 0x0195: mmctx_exec_loop */
+/* 0x0195: mmctx_wait_free */
+       0xc5008e04,
+       0x00eecf01,
+       0xf41fe4f0,
+       0xce98f60b,
+       0x05e9fd00,
+       0x01c80080,
+       0xbd000ef6,
+       0x04c0b604,
+       0x1bf4cda4,
+       0x02abc8df,
+/* 0x01bf: mmctx_fini_wait */
+       0x8b1c1bf4,
+       0xcf01c500,
+       0xb4f000bb,
+       0x10b4b01f,
+       0x0af31bf4,
+       0x00b87e05,
+       0x250ef400,
+/* 0x01d8: mmctx_stop */
+       0xb600abc8,
+       0xb9f010b4,
+       0x12b9f00c,
+       0x01c50080,
+       0xbd000bf6,
+/* 0x01ed: mmctx_stop_wait */
+       0xc5008b04,
+       0x00bbcf01,
+       0xf412bbc8,
+/* 0x01fa: mmctx_done */
+       0x94bdf61b,
+       0x800199f0,
+       0xf6021700,
+       0x04bd0009,
+/* 0x020a: strand_wait */
+       0xa0f900f8,
+       0xb87e020a,
+       0xa0fc0000,
+/* 0x0216: strand_pre */
+       0x0c0900f8,
+       0x024afc80,
+       0xbd0009f6,
+       0x020a7e04,
+/* 0x0227: strand_post */
+       0x0900f800,
+       0x4afc800d,
+       0x0009f602,
+       0x0a7e04bd,
+       0x00f80002,
+/* 0x0238: strand_set */
+       0xfc800f0c,
+       0x0cf6024f,
+       0x0c04bd00,
+       0x4afc800b,
+       0x000cf602,
+       0xfc8004bd,
+       0x0ef6024f,
+       0x0c04bd00,
+       0x4afc800a,
+       0x000cf602,
+       0x0a7e04bd,
+       0x00f80002,
+/* 0x0268: strand_ctx_init */
+       0x99f094bd,
+       0x37008003,
+       0x0009f602,
+       0x167e04bd,
+       0x030e0002,
+       0x0002387e,
+       0xfc80c4bd,
+       0x0cf60247,
+       0x0c04bd00,
+       0x4afc8001,
+       0x000cf602,
+       0x0a7e04bd,
+       0x0c920002,
+       0x46fc8001,
+       0x000cf602,
+       0x020c04bd,
+       0x024afc80,
+       0xbd000cf6,
+       0x020a7e04,
+       0x02277e00,
+       0x42008800,
+       0x20008902,
+       0x0099cf02,
+/* 0x02c7: ctx_init_strand_loop */
+       0xf608fe95,
+       0x8ef6008e,
+       0x808acf40,
+       0xb606a5b6,
+       0xeabb01a0,
+       0x0480b600,
+       0xf40192b6,
+       0xe4b6e81b,
+       0xf2efbc08,
+       0x99f094bd,
+       0x17008003,
+       0x0009f602,
+       0x00f804bd,
+/* 0x02f8: error */
+       0xffb2e0f9,
+       0x4098148e,
+       0x00008f7e,
+       0xffb2010f,
+       0x409c1c8e,
+       0x00008f7e,
+       0x00f8e0fc,
+/* 0x0314: init */
+       0x004104bd,
+       0x0011cf42,
+       0x010911e7,
+       0xfe0814b6,
+       0x02020014,
+       0xf6120040,
+       0x04bd0002,
+       0xfe047241,
+       0x00400010,
+       0x0000f607,
+       0x040204bd,
+       0xf6040040,
+       0x04bd0002,
+       0x821031f4,
+       0xcf018200,
+       0x01030022,
+       0xbb1f24f0,
+       0x32b60432,
+       0x0502b501,
+       0x820603b5,
+       0xcf018600,
+       0x02b50022,
+       0x0c308e04,
+       0xbd24bd50,
+/* 0x0377: init_unk_loop */
+       0x7e44bd34,
+       0xb0000065,
+       0x0bf400f6,
+       0xbb010f0e,
+       0x4ffd04f2,
+       0x0130b605,
+/* 0x038c: init_unk_next */
+       0xb60120b6,
+       0x26b004e0,
+       0xe21bf401,
+/* 0x0398: init_unk_done */
+       0xb50703b5,
+       0x00820804,
+       0x22cf0201,
+       0x9534bd00,
+       0x00800825,
+       0x05f601c0,
+       0x8004bd00,
+       0xf601c100,
+       0x04bd0005,
+       0x98000e98,
+       0x207e010f,
+       0x2fbb0001,
+       0x003fbb00,
+       0x98010e98,
+       0x207e020f,
+       0x0e980001,
+       0x00effd05,
+       0xbb002ebb,
+       0x0e98003e,
+       0x030f9802,
+       0x0001207e,
+       0xfd070e98,
+       0x2ebb00ef,
+       0x003ebb00,
+       0x800235b6,
+       0xf601d300,
+       0x04bd0003,
+       0xb60825b6,
+       0x20b60635,
+       0x0130b601,
+       0xb60824b6,
+       0x2fb20834,
+       0x0002687e,
+       0x80003fbb,
+       0xf6020100,
+       0x04bd0003,
+       0x29f024bd,
+       0x3000801f,
+       0x0002f602,
+/* 0x0436: main */
+       0x31f404bd,
+       0x0028f400,
+       0x377e240d,
+       0x01f40000,
+       0x04e4b0f4,
+       0xfe1d18f4,
+       0x06020181,
+       0x12fd20bd,
+       0x01e4b604,
+       0xfe051efd,
+       0x097e0018,
+       0x0ef40005,
+/* 0x0465: main_not_ctx_xfer */
+       0x10ef94d4,
+       0x7e01f5f0,
+       0xf40002f8,
+/* 0x0472: ih */
+       0x80f9c70e,
+       0xf90188fe,
+       0xf990f980,
+       0xf9b0f9a0,
+       0xf9e0f9d0,
+       0x4a04bdf0,
+       0xaacf0200,
+       0x04abc400,
+       0x0d1f0bf4,
+       0x1a004e24,
+       0x4f00eecf,
+       0xffcf1900,
+       0x00047e00,
+       0x40010e00,
+       0x0ef61d00,
+/* 0x04af: ih_no_fifo */
+       0x4004bd00,
+       0x0af60100,
+       0xfc04bd00,
+       0xfce0fcf0,
+       0xfcb0fcd0,
+       0xfc90fca0,
+       0x0088fe80,
+       0x32f480fc,
+/* 0x04cf: hub_barrier_done */
+       0x0f01f800,
+       0x040e9801,
+       0xb204febb,
+       0x94188eff,
+       0x008f7e40,
+/* 0x04e3: ctx_redswitch */
+       0x0f00f800,
+       0x85008020,
+       0x000ff601,
+       0x080e04bd,
+/* 0x04f0: ctx_redswitch_delay */
+       0xf401e2b6,
+       0xf5f1fd1b,
+       0xf5f10800,
+       0x00800200,
+       0x0ff60185,
+       0xf804bd00,
+/* 0x0509: ctx_xfer */
+       0x81008000,
+       0x000ff602,
+       0x11f404bd,
+       0x04e37e07,
+/* 0x0519: ctx_xfer_not_load */
+       0x02167e00,
+       0x8024bd00,
+       0xf60247fc,
+       0x04bd0002,
+       0xb6012cf0,
+       0xfc800320,
+       0x02f6024a,
+       0xf004bd00,
+       0xa5f001ac,
+       0x00008b02,
+       0x040c9850,
+       0xbb0fc4b6,
+       0x0c9800bc,
+       0x010d9800,
+       0x3d7e000e,
+       0xacf00001,
+       0x40008b01,
+       0x040c9850,
+       0xbb0fc4b6,
+       0x0c9800bc,
+       0x020d9801,
+       0x4e060f98,
+       0x3d7e0800,
+       0xacf00001,
+       0x04a5f001,
+       0x5030008b,
+       0xb6040c98,
+       0xbcbb0fc4,
+       0x020c9800,
+       0x98030d98,
+       0x004e080f,
+       0x013d7e02,
+       0x020a7e00,
+       0x0601f400,
+/* 0x05a3: ctx_xfer_post */
+       0x7e0712f4,
+/* 0x05a7: ctx_xfer_done */
+       0x7e000227,
+       0xf80004cf,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+};
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/gr/fuc/gpcgm107.fuc5 b/drivers/gpu/drm/nouveau/nvkm/engine/gr/fuc/gpcgm107.fuc5
new file mode 100644 (file)
index 0000000..e730603
--- /dev/null
@@ -0,0 +1,42 @@
+/*
+ * Copyright 2013 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 <bskeggs@redhat.com>
+ */
+
+#define NV_PGRAPH_GPCX_UNK__SIZE                                     0x00000002
+
+#define CHIPSET GK208
+#include "macros.fuc"
+
+.section #gm107_grgpc_data
+#define INCLUDE_DATA
+#include "com.fuc"
+#include "gpc.fuc"
+#undef INCLUDE_DATA
+
+.section #gm107_grgpc_code
+#define INCLUDE_CODE
+bra #init
+#include "com.fuc"
+#include "gpc.fuc"
+.align 256
+#undef INCLUDE_CODE
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/gr/fuc/gpcgm107.fuc5.h b/drivers/gpu/drm/nouveau/nvkm/engine/gr/fuc/gpcgm107.fuc5.h
new file mode 100644 (file)
index 0000000..6d53b67
--- /dev/null
@@ -0,0 +1,473 @@
+uint32_t gm107_grgpc_data[] = {
+/* 0x0000: gpc_mmio_list_head */
+       0x0000006c,
+/* 0x0004: gpc_mmio_list_tail */
+/* 0x0004: tpc_mmio_list_head */
+       0x0000006c,
+/* 0x0008: tpc_mmio_list_tail */
+/* 0x0008: unk_mmio_list_head */
+       0x0000006c,
+/* 0x000c: unk_mmio_list_tail */
+       0x0000006c,
+/* 0x0010: gpc_id */
+       0x00000000,
+/* 0x0014: tpc_count */
+       0x00000000,
+/* 0x0018: tpc_mask */
+       0x00000000,
+/* 0x001c: unk_count */
+       0x00000000,
+/* 0x0020: unk_mask */
+       0x00000000,
+/* 0x0024: cmd_queue */
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+};
+
+uint32_t gm107_grgpc_code[] = {
+       0x03140ef5,
+/* 0x0004: queue_put */
+       0x9800d898,
+       0x86f001d9,
+       0xf489a408,
+       0x020f0b1b,
+       0x0002f87e,
+/* 0x001a: queue_put_next */
+       0x98c400f8,
+       0x0384b607,
+       0xb6008dbb,
+       0x8eb50880,
+       0x018fb500,
+       0xf00190b6,
+       0xd9b50f94,
+/* 0x0037: queue_get */
+       0xf400f801,
+       0xd8980131,
+       0x01d99800,
+       0x0bf489a4,
+       0x0789c421,
+       0xbb0394b6,
+       0x90b6009d,
+       0x009e9808,
+       0xb6019f98,
+       0x84f00180,
+       0x00d8b50f,
+/* 0x0063: queue_get_done */
+       0xf80132f4,
+/* 0x0065: nv_rd32 */
+       0xf0ecb200,
+       0x00801fc9,
+       0x0cf601ca,
+/* 0x0073: nv_rd32_wait */
+       0x8c04bd00,
+       0xcf01ca00,
+       0xccc800cc,
+       0xf61bf41f,
+       0xec7e060a,
+       0x008f0000,
+       0xffcf01cb,
+/* 0x008f: nv_wr32 */
+       0x8000f800,
+       0xf601cc00,
+       0x04bd000f,
+       0xc9f0ecb2,
+       0x1ec9f01f,
+       0x01ca0080,
+       0xbd000cf6,
+/* 0x00a9: nv_wr32_wait */
+       0xca008c04,
+       0x00cccf01,
+       0xf41fccc8,
+       0x00f8f61b,
+/* 0x00b8: wait_donez */
+       0x99f094bd,
+       0x37008000,
+       0x0009f602,
+       0x008004bd,
+       0x0af60206,
+/* 0x00cf: wait_donez_ne */
+       0x8804bd00,
+       0xcf010000,
+       0x8aff0088,
+       0xf61bf488,
+       0x99f094bd,
+       0x17008000,
+       0x0009f602,
+       0x00f804bd,
+/* 0x00ec: wait_doneo */
+       0x99f094bd,
+       0x37008000,
+       0x0009f602,
+       0x008004bd,
+       0x0af60206,
+/* 0x0103: wait_doneo_e */
+       0x8804bd00,
+       0xcf010000,
+       0x8aff0088,
+       0xf60bf488,
+       0x99f094bd,
+       0x17008000,
+       0x0009f602,
+       0x00f804bd,
+/* 0x0120: mmctx_size */
+/* 0x0122: nv_mmctx_size_loop */
+       0xe89894bd,
+       0x1a85b600,
+       0xb60180b6,
+       0x98bb0284,
+       0x04e0b600,
+       0x1bf4efa4,
+       0xf89fb2ec,
+/* 0x013d: mmctx_xfer */
+       0xf094bd00,
+       0x00800199,
+       0x09f60237,
+       0xbd04bd00,
+       0x05bbfd94,
+       0x800f0bf4,
+       0xf601c400,
+       0x04bd000b,
+/* 0x015f: mmctx_base_disabled */
+       0xfd0099f0,
+       0x0bf405ee,
+       0xc6008018,
+       0x000ef601,
+       0x008004bd,
+       0x0ff601c7,
+       0xf004bd00,
+/* 0x017a: mmctx_multi_disabled */
+       0xabc80199,
+       0x10b4b600,
+       0xc80cb9f0,
+       0xe4b601ae,
+       0x05befd11,
+       0x01c50080,
+       0xbd000bf6,
+/* 0x0195: mmctx_exec_loop */
+/* 0x0195: mmctx_wait_free */
+       0xc5008e04,
+       0x00eecf01,
+       0xf41fe4f0,
+       0xce98f60b,
+       0x05e9fd00,
+       0x01c80080,
+       0xbd000ef6,
+       0x04c0b604,
+       0x1bf4cda4,
+       0x02abc8df,
+/* 0x01bf: mmctx_fini_wait */
+       0x8b1c1bf4,
+       0xcf01c500,
+       0xb4f000bb,
+       0x10b4b01f,
+       0x0af31bf4,
+       0x00b87e05,
+       0x250ef400,
+/* 0x01d8: mmctx_stop */
+       0xb600abc8,
+       0xb9f010b4,
+       0x12b9f00c,
+       0x01c50080,
+       0xbd000bf6,
+/* 0x01ed: mmctx_stop_wait */
+       0xc5008b04,
+       0x00bbcf01,
+       0xf412bbc8,
+/* 0x01fa: mmctx_done */
+       0x94bdf61b,
+       0x800199f0,
+       0xf6021700,
+       0x04bd0009,
+/* 0x020a: strand_wait */
+       0xa0f900f8,
+       0xb87e020a,
+       0xa0fc0000,
+/* 0x0216: strand_pre */
+       0x0c0900f8,
+       0x024afc80,
+       0xbd0009f6,
+       0x020a7e04,
+/* 0x0227: strand_post */
+       0x0900f800,
+       0x4afc800d,
+       0x0009f602,
+       0x0a7e04bd,
+       0x00f80002,
+/* 0x0238: strand_set */
+       0xfc800f0c,
+       0x0cf6024f,
+       0x0c04bd00,
+       0x4afc800b,
+       0x000cf602,
+       0xfc8004bd,
+       0x0ef6024f,
+       0x0c04bd00,
+       0x4afc800a,
+       0x000cf602,
+       0x0a7e04bd,
+       0x00f80002,
+/* 0x0268: strand_ctx_init */
+       0x99f094bd,
+       0x37008003,
+       0x0009f602,
+       0x167e04bd,
+       0x030e0002,
+       0x0002387e,
+       0xfc80c4bd,
+       0x0cf60247,
+       0x0c04bd00,
+       0x4afc8001,
+       0x000cf602,
+       0x0a7e04bd,
+       0x0c920002,
+       0x46fc8001,
+       0x000cf602,
+       0x020c04bd,
+       0x024afc80,
+       0xbd000cf6,
+       0x020a7e04,
+       0x02277e00,
+       0x42008800,
+       0x20008902,
+       0x0099cf02,
+/* 0x02c7: ctx_init_strand_loop */
+       0xf608fe95,
+       0x8ef6008e,
+       0x808acf40,
+       0xb606a5b6,
+       0xeabb01a0,
+       0x0480b600,
+       0xf40192b6,
+       0xe4b6e81b,
+       0xf2efbc08,
+       0x99f094bd,
+       0x17008003,
+       0x0009f602,
+       0x00f804bd,
+/* 0x02f8: error */
+       0xffb2e0f9,
+       0x4098148e,
+       0x00008f7e,
+       0xffb2010f,
+       0x409c1c8e,
+       0x00008f7e,
+       0x00f8e0fc,
+/* 0x0314: init */
+       0x004104bd,
+       0x0011cf42,
+       0x010911e7,
+       0xfe0814b6,
+       0x02020014,
+       0xf6120040,
+       0x04bd0002,
+       0xfe047241,
+       0x00400010,
+       0x0000f607,
+       0x040204bd,
+       0xf6040040,
+       0x04bd0002,
+       0x821031f4,
+       0xcf018200,
+       0x01030022,
+       0xbb1f24f0,
+       0x32b60432,
+       0x0502b501,
+       0x820603b5,
+       0xcf018600,
+       0x02b50022,
+       0x0c308e04,
+       0xbd24bd50,
+/* 0x0377: init_unk_loop */
+       0x7e44bd34,
+       0xb0000065,
+       0x0bf400f6,
+       0xbb010f0e,
+       0x4ffd04f2,
+       0x0130b605,
+/* 0x038c: init_unk_next */
+       0xb60120b6,
+       0x26b004e0,
+       0xe21bf402,
+/* 0x0398: init_unk_done */
+       0xb50703b5,
+       0x00820804,
+       0x22cf0201,
+       0x9534bd00,
+       0x00800825,
+       0x05f601c0,
+       0x8004bd00,
+       0xf601c100,
+       0x04bd0005,
+       0x98000e98,
+       0x207e010f,
+       0x2fbb0001,
+       0x003fbb00,
+       0x98010e98,
+       0x207e020f,
+       0x0e980001,
+       0x00effd05,
+       0xbb002ebb,
+       0x0e98003e,
+       0x030f9802,
+       0x0001207e,
+       0xfd070e98,
+       0x2ebb00ef,
+       0x003ebb00,
+       0x800235b6,
+       0xf601d300,
+       0x04bd0003,
+       0xb60825b6,
+       0x20b60635,
+       0x0130b601,
+       0xb60824b6,
+       0x2fb20834,
+       0x0002687e,
+       0x80003fbb,
+       0xf6020100,
+       0x04bd0003,
+       0x29f024bd,
+       0x3000801f,
+       0x0002f602,
+/* 0x0436: main */
+       0x31f404bd,
+       0x0028f400,
+       0x377e240d,
+       0x01f40000,
+       0x04e4b0f4,
+       0xfe1d18f4,
+       0x06020181,
+       0x12fd20bd,
+       0x01e4b604,
+       0xfe051efd,
+       0x097e0018,
+       0x0ef40005,
+/* 0x0465: main_not_ctx_xfer */
+       0x10ef94d4,
+       0x7e01f5f0,
+       0xf40002f8,
+/* 0x0472: ih */
+       0x80f9c70e,
+       0xf90188fe,
+       0xf990f980,
+       0xf9b0f9a0,
+       0xf9e0f9d0,
+       0x4a04bdf0,
+       0xaacf0200,
+       0x04abc400,
+       0x0d1f0bf4,
+       0x1a004e24,
+       0x4f00eecf,
+       0xffcf1900,
+       0x00047e00,
+       0x40010e00,
+       0x0ef61d00,
+/* 0x04af: ih_no_fifo */
+       0x4004bd00,
+       0x0af60100,
+       0xfc04bd00,
+       0xfce0fcf0,
+       0xfcb0fcd0,
+       0xfc90fca0,
+       0x0088fe80,
+       0x32f480fc,
+/* 0x04cf: hub_barrier_done */
+       0x0f01f800,
+       0x040e9801,
+       0xb204febb,
+       0x94188eff,
+       0x008f7e40,
+/* 0x04e3: ctx_redswitch */
+       0x0f00f800,
+       0x85008020,
+       0x000ff601,
+       0x080e04bd,
+/* 0x04f0: ctx_redswitch_delay */
+       0xf401e2b6,
+       0xf5f1fd1b,
+       0xf5f10800,
+       0x00800200,
+       0x0ff60185,
+       0xf804bd00,
+/* 0x0509: ctx_xfer */
+       0x81008000,
+       0x000ff602,
+       0x11f404bd,
+       0x04e37e07,
+/* 0x0519: ctx_xfer_not_load */
+       0x02167e00,
+       0x8024bd00,
+       0xf60247fc,
+       0x04bd0002,
+       0xb6012cf0,
+       0xfc800320,
+       0x02f6024a,
+       0xf004bd00,
+       0xa5f001ac,
+       0x00008b02,
+       0x040c9850,
+       0xbb0fc4b6,
+       0x0c9800bc,
+       0x010d9800,
+       0x3d7e000e,
+       0xacf00001,
+       0x40008b01,
+       0x040c9850,
+       0xbb0fc4b6,
+       0x0c9800bc,
+       0x020d9801,
+       0x4e060f98,
+       0x3d7e0800,
+       0xacf00001,
+       0x04a5f001,
+       0x5030008b,
+       0xb6040c98,
+       0xbcbb0fc4,
+       0x020c9800,
+       0x98030d98,
+       0x004e080f,
+       0x013d7e02,
+       0x020a7e00,
+       0x0601f400,
+/* 0x05a3: ctx_xfer_post */
+       0x7e0712f4,
+/* 0x05a7: ctx_xfer_done */
+       0x7e000227,
+       0xf80004cf,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+};
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/gr/fuc/hub.fuc b/drivers/gpu/drm/nouveau/nvkm/engine/gr/fuc/hub.fuc
new file mode 100644 (file)
index 0000000..87f99e3
--- /dev/null
@@ -0,0 +1,696 @@
+/* fuc microcode for gf100 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
+ */
+
+#ifdef INCLUDE_DATA
+hub_mmio_list_head:    .b32 #hub_mmio_list_base
+hub_mmio_list_tail:    .b32 #hub_mmio_list_next
+
+gpc_count:             .b32 0
+rop_count:             .b32 0
+cmd_queue:             queue_init
+
+ctx_current:           .b32 0
+
+.align 256
+chan_data:
+chan_mmio_count:       .b32 0
+chan_mmio_address:     .b32 0
+
+.align 256
+xfer_data:             .skip 256
+
+hub_mmio_list_base:
+.b32 0x0417e91c // 0x17e91c, 2
+hub_mmio_list_next:
+#endif
+
+#ifdef INCLUDE_CODE
+// reports an exception to the host
+//
+// In: $r15 error code (see os.h)
+//
+error:
+       nv_iowr(NV_PGRAPH_FECS_CC_SCRATCH_VAL(5), 0, $r15)
+       mov $r15 1
+       nv_iowr(NV_PGRAPH_FECS_INTR_UP_SET, 0, $r15)
+       ret
+
+// HUB fuc initialisation, executed by triggering ucode start, will
+// fall through to main loop after completion.
+//
+// Output:
+//   CC_SCRATCH[0]:
+//          31:31: set to signal completion
+//   CC_SCRATCH[1]:
+//           31:0: total PGRAPH context size
+//
+init:
+       clear b32 $r0
+       mov $xdbase $r0
+
+       // setup stack
+       nv_iord($r1, NV_PGRAPH_FECS_CAPS, 0)
+       extr $r1 $r1 9:17
+       shl b32 $r1 8
+       mov $sp $r1
+
+       // enable fifo access
+       mov $r2 NV_PGRAPH_FECS_ACCESS_FIFO
+       nv_iowr(NV_PGRAPH_FECS_ACCESS, 0, $r2)
+
+       // setup i0 handler, and route all interrupts to it
+       mov $r1 #ih
+       mov $iv0 $r1
+
+       clear b32 $r2
+       nv_iowr(NV_PGRAPH_FECS_INTR_ROUTE, 0, $r2)
+
+       // route HUB_CHSW_PULSE to fuc interrupt 8
+       mov $r2 0x2003          // { HUB_CHSW_PULSE, ZERO } -> intr 8
+       nv_iowr(NV_PGRAPH_FECS_IROUTE, 0, $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          // { 0x04, ZERO } -> intr 9
+       nv_iowr(NV_PGRAPH_FECS_IROUTE, 1, $r2)
+       mov $r2 0x200b          // { HUB_FIRMWARE_MTHD, ZERO } -> intr 10
+       nv_iowr(NV_PGRAPH_FECS_IROUTE, 2, $r2)
+       mov $r2 0x200c          // { 0x0c, ZERO } -> intr 15
+       nv_iowr(NV_PGRAPH_FECS_IROUTE, 7, $r2)
+
+       // enable all INTR_UP interrupts
+       sub b32 $r3 $r0 1
+       nv_iowr(NV_PGRAPH_FECS_INTR_UP_EN, 0, $r3)
+
+       // enable fifo, ctxsw, 9, fwmthd, 15 interrupts
+       imm32($r2, 0x8704)
+       nv_iowr(NV_PGRAPH_FECS_INTR_EN_SET, 0, $r2)
+
+       // fifo level triggered, rest edge
+       mov $r2 NV_PGRAPH_FECS_INTR_MODE_FIFO_LEVEL
+       nv_iowr(NV_PGRAPH_FECS_INTR_MODE, 0, $r2)
+
+       // enable interrupts
+       bset $flags ie0
+
+       // fetch enabled GPC/ROP counts
+       nv_rd32($r14, 0x409604)
+       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
+       nv_iowr(NV_PGRAPH_FECS_BAR_MASK0, 0, $r1)
+       nv_iowr(NV_PGRAPH_FECS_BAR_MASK1, 0, $r1)
+
+       // context size calculation, reserve first 256 bytes for use by fuc
+       mov $r1 256
+
+       //
+       mov $r15 2
+       call(ctx_4170s)
+       call(ctx_4170w)
+       mov $r15 0x10
+       call(ctx_86c)
+
+       // calculate size of mmio context data
+       ld b32 $r14 D[$r0 + #hub_mmio_list_head]
+       ld b32 $r15 D[$r0 + #hub_mmio_list_tail]
+       call(mmctx_size)
+
+       // set mmctx base addresses now so we don't have to do it later,
+       // they don't (currently) ever change
+       shr b32 $r4 $r1 8
+       nv_iowr(NV_PGRAPH_FECS_MMCTX_SAVE_SWBASE, 0, $r4)
+       nv_iowr(NV_PGRAPH_FECS_MMCTX_LOAD_SWBASE, 0, $r4)
+       add b32 $r3 0x1300
+       add b32 $r1 $r15
+       shr b32 $r15 2
+       nv_iowr(NV_PGRAPH_FECS_MMCTX_LOAD_COUNT, 0, $r15) // wtf??
+
+       // 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]
+       imm32($r4, 0x502000)
+       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 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
+
+       //
+       mov $r15 0
+       call(ctx_86c)
+       mov $r15 0
+       call(ctx_4170s)
+
+       // save context size, and tell host we're ready
+       nv_iowr(NV_PGRAPH_FECS_CC_SCRATCH_VAL(1), 0, $r1)
+       clear b32 $r1
+       bset $r1 31
+       nv_iowr(NV_PGRAPH_FECS_CC_SCRATCH_SET(0), 0, $r1)
+
+// 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)
+               nv_iord($r1, NV_PGRAPH_FECS_CHAN_ADDR, 0)
+               nv_iord($r2, NV_PGRAPH_FECS_CHAN_NEXT, 0)
+
+               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
+                               nv_iowr(NV_PGRAPH_FECS_CHAN_ADDR, 0, $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 $r2 NV_PGRAPH_FECS_CHSW_ACK
+               nv_iowr(NV_PGRAPH_FECS_CHSW, 0, $r2)
+               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:
+       clear b32 $r2
+       bset $r2 31
+       nv_iowr(NV_PGRAPH_FECS_CC_SCRATCH_SET(0), 0, $r2)
+       bra #main
+
+// interrupt handler
+ih:
+       push $r8
+       mov $r8 $flags
+       push $r8
+       push $r9
+       push $r10
+       push $r11
+       push $r13
+       push $r14
+       push $r15
+       clear b32 $r0
+
+       // incoming fifo command?
+       nv_iord($r10, NV_PGRAPH_FECS_INTR, 0)
+       and $r11 $r10 NV_PGRAPH_FECS_INTR_FIFO
+       bra e #ih_no_fifo
+               // queue incoming fifo command for later processing
+               mov $r13 #cmd_queue
+               nv_iord($r14, NV_PGRAPH_FECS_FIFO_CMD, 0)
+               nv_iord($r15, NV_PGRAPH_FECS_FIFO_DATA, 0)
+               call(queue_put)
+               add b32 $r11 0x400
+               mov $r14 1
+               nv_iowr(NV_PGRAPH_FECS_FIFO_ACK, 0, $r14)
+
+       // context switch request?
+       ih_no_fifo:
+       and $r11 $r10 NV_PGRAPH_FECS_INTR_CHSW
+       bra e #ih_no_ctxsw
+               // enqueue a context switch for later processing
+               mov $r13 #cmd_queue
+               mov $r14 0x4001
+               call(queue_put)
+
+       // firmware method?
+       ih_no_ctxsw:
+       and $r11 $r10 NV_PGRAPH_FECS_INTR_FWMTHD
+       bra e #ih_no_fwmthd
+               // none we handle; report to host and ack
+               nv_rd32($r15, NV_PGRAPH_TRAPPED_DATA_LO)
+               nv_iowr(NV_PGRAPH_FECS_CC_SCRATCH_VAL(4), 0, $r15)
+               nv_rd32($r15, NV_PGRAPH_TRAPPED_ADDR)
+               nv_iowr(NV_PGRAPH_FECS_CC_SCRATCH_VAL(3), 0, $r15)
+               extr $r14 $r15 16:18
+               shl b32 $r14 $r14 2
+               imm32($r15, NV_PGRAPH_FE_OBJECT_TABLE(0))
+               add b32 $r14 $r15
+               call(nv_rd32)
+               nv_iowr(NV_PGRAPH_FECS_CC_SCRATCH_VAL(2), 0, $r15)
+               mov $r15 E_BAD_FWMTHD
+               call(error)
+               mov $r11 0x100
+               nv_wr32(0x400144, $r11)
+
+       // anything we didn't handle, bring it to the host's attention
+       ih_no_fwmthd:
+       mov $r11 0x504 // FIFO | CHSW | FWMTHD
+       not b32 $r11
+       and $r11 $r10 $r11
+       bra e #ih_no_other
+               nv_iowr(NV_PGRAPH_FECS_INTR_UP_SET, 0, $r11)
+
+       // ack, and wake up main()
+       ih_no_other:
+       nv_iowr(NV_PGRAPH_FECS_INTR_ACK, 0, $r10)
+
+       pop $r15
+       pop $r14
+       pop $r13
+       pop $r11
+       pop $r10
+       pop $r9
+       pop $r8
+       mov $flags $r8
+       pop $r8
+       bclr $flags $p0
+       iret
+
+#if CHIPSET < GK100
+// Not real sure, but, MEM_CMD 7 will hang forever if this isn't done
+ctx_4160s:
+       mov $r15 1
+       nv_wr32(0x404160, $r15)
+       ctx_4160s_wait:
+               nv_rd32($r15, 0x404160)
+               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:
+       clear b32 $r15
+       nv_wr32(0x404160, $r15)
+       ret
+#endif
+
+// Again, not real sure
+//
+// In: $r15 value to set 0x404170 to
+//
+ctx_4170s:
+       or $r15 0x10
+       nv_wr32(0x404170, $r15)
+       ret
+
+// Waits for a ctx_4170s() call to complete
+//
+ctx_4170w:
+       nv_rd32($r15, 0x404170)
+       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 NV_PGRAPH_FECS_RED_SWITCH_ENABLE_GPC
+       or  $r14 NV_PGRAPH_FECS_RED_SWITCH_POWER_ROP
+       or  $r14 NV_PGRAPH_FECS_RED_SWITCH_POWER_GPC
+       or  $r14 NV_PGRAPH_FECS_RED_SWITCH_POWER_MAIN
+       nv_iowr(NV_PGRAPH_FECS_RED_SWITCH, 0, $r14)
+       mov $r15 8
+       ctx_redswitch_delay:
+               sub b32 $r15 1
+               bra ne #ctx_redswitch_delay
+       or  $r14 NV_PGRAPH_FECS_RED_SWITCH_ENABLE_ROP
+       or  $r14 NV_PGRAPH_FECS_RED_SWITCH_ENABLE_MAIN
+       nv_iowr(NV_PGRAPH_FECS_RED_SWITCH, 0, $r14)
+       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:
+       nv_iowr(NV_PGRAPH_FECS_UNK86C, 0, $r15)
+       nv_wr32(0x408a14, $r15)
+       nv_wr32(NV_PGRAPH_GPCX_GPCCS_UNK86C, $r15)
+       ret
+
+// In: $r15 NV_PGRAPH_FECS_MEM_CMD_*
+ctx_mem:
+       nv_iowr(NV_PGRAPH_FECS_MEM_CMD, 0, $r15)
+       ctx_mem_wait:
+               nv_iord($r15, NV_PGRAPH_FECS_MEM_CMD, 0)
+               or $r15 $r15
+               bra ne #ctx_mem_wait
+       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)
+       clear b32 $r15
+       nv_iowr(0x409a24, 0, $r15)
+       nv_iowr(NV_PGRAPH_FECS_CHAN_NEXT, 0, $r2)
+       nv_iowr(NV_PGRAPH_FECS_MEM_CHAN, 0, $r2)
+       mov $r15 NV_PGRAPH_FECS_MEM_CMD_LOAD_CHAN
+       call(ctx_mem)
+       nv_iowr(NV_PGRAPH_FECS_CHAN_ADDR, 0, $r2)
+
+       // 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)
+       nv_iowr(NV_PGRAPH_FECS_MEM_BASE, 0, $r2)
+       imm32($r2, NV_PGRAPH_FECS_MEM_TARGET_UNK31)
+       or  $r2 NV_PGRAPH_FECS_MEM_TARGET_AS_VRAM
+       nv_iowr(NV_PGRAPH_FECS_MEM_TARGET, 0, $r2)
+       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)
+       nv_iowr(NV_PGRAPH_FECS_MEM_BASE, 0, $r1)
+       mov $r2 NV_PGRAPH_FECS_MEM_TARGET_AS_VM
+       nv_iowr(NV_PGRAPH_FECS_MEM_TARGET, 0, $r2)
+       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:
+#if CHIPSET < GK100
+       call(ctx_4160s)
+#endif
+       call(ctx_load)
+       mov $r10 12                     // DONE_UNK12
+       call(wait_donez)
+       mov $r15 5 // MEM_CMD 5 ???
+       call(ctx_mem)
+#if CHIPSET < GK100
+       call(ctx_4160c)
+#endif
+       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]
+       nv_iowr(NV_PGRAPH_FECS_MEM_BASE, 0, $r3)
+
+       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]
+       nv_iowr(NV_PGRAPH_FECS_MEM_BASE, 0, $r3)
+
+       // 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:
+       // according to mwk, some kind of wait for idle
+       mov $r14 4
+       nv_iowr(0x409c08, 0, $r14)
+       ctx_xfer_idle:
+               nv_iord($r14, 0x409c00, 0)
+               and $r14 0x2000
+               bra ne #ctx_xfer_idle
+
+       bra not $p1 #ctx_xfer_pre
+       bra $p2 #ctx_xfer_pre_load
+       ctx_xfer_pre:
+               mov $r15 0x10
+               call(ctx_86c)
+#if CHIPSET < GK100
+               call(ctx_4160s)
+#endif
+               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]
+
+       clear b32 $r2
+       nv_iowr(NV_PGRAPH_FECS_BAR, 0, $r2)
+
+       nv_wr32(0x41a500, $r1)  // GPC_BCAST_WRCMD_DATA = ctx pointer
+       xbit $r15 $flags $p1
+       xbit $r2 $flags $p2
+       shl b32 $r2 1
+       or $r15 $r2
+       nv_wr32(0x41a504, $r15) // GPC_BCAST_WRCMD_CMD = GPC_XFER(type)
+
+       // strands
+       call(strand_pre)
+       clear b32 $r2
+       nv_iowr(NV_PGRAPH_FECS_STRAND_SELECT, 0x3f, $r2)
+       xbit $r2 $flags $p1     // SAVE/LOAD
+       add b32 $r2 NV_PGRAPH_FECS_STRAND_CMD_SAVE
+       nv_iowr(NV_PGRAPH_FECS_STRAND_CMD, 0x3f, $r2)
+
+       // 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 $r15 5 // MEM_CMD 5 ???
+               call(ctx_mem)
+
+       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:
+#if CHIPSET < GK100
+               call(ctx_4160c)
+#endif
+
+       ctx_xfer_done:
+       ret
+#endif
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/gr/fuc/hubgf100.fuc3 b/drivers/gpu/drm/nouveau/nvkm/engine/gr/fuc/hubgf100.fuc3
new file mode 100644 (file)
index 0000000..2c28e71
--- /dev/null
@@ -0,0 +1,40 @@
+/*
+ * Copyright 2013 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 <bskeggs@redhat.com>
+ */
+
+#define CHIPSET GF100
+#include "macros.fuc"
+
+.section #gf100_grhub_data
+#define INCLUDE_DATA
+#include "com.fuc"
+#include "hub.fuc"
+#undef INCLUDE_DATA
+
+.section #gf100_grhub_code
+#define INCLUDE_CODE
+bra #init
+#include "com.fuc"
+#include "hub.fuc"
+.align 256
+#undef INCLUDE_CODE
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/gr/fuc/hubgf100.fuc3.h b/drivers/gpu/drm/nouveau/nvkm/engine/gr/fuc/hubgf100.fuc3.h
new file mode 100644 (file)
index 0000000..f6acda5
--- /dev/null
@@ -0,0 +1,1047 @@
+uint32_t gf100_grhub_data[] = {
+/* 0x0000: hub_mmio_list_head */
+       0x00000300,
+/* 0x0004: hub_mmio_list_tail */
+       0x00000304,
+/* 0x0008: gpc_count */
+       0x00000000,
+/* 0x000c: rop_count */
+       0x00000000,
+/* 0x0010: cmd_queue */
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+/* 0x0058: ctx_current */
+       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,
+/* 0x0100: chan_data */
+/* 0x0100: chan_mmio_count */
+       0x00000000,
+/* 0x0104: chan_mmio_address */
+       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,
+/* 0x0200: xfer_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,
+/* 0x0300: hub_mmio_list_base */
+       0x0417e91c,
+};
+
+uint32_t gf100_grhub_code[] = {
+       0x039b0ef5,
+/* 0x0004: queue_put */
+       0x9800d898,
+       0x86f001d9,
+       0x0489b808,
+       0xf00c1bf4,
+       0x21f502f7,
+       0x00f8037e,
+/* 0x001c: queue_put_next */
+       0xb60798c4,
+       0x8dbb0384,
+       0x0880b600,
+       0x80008e80,
+       0x90b6018f,
+       0x0f94f001,
+       0xf801d980,
+/* 0x0039: queue_get */
+       0x0131f400,
+       0x9800d898,
+       0x89b801d9,
+       0x210bf404,
+       0xb60789c4,
+       0x9dbb0394,
+       0x0890b600,
+       0x98009e98,
+       0x80b6019f,
+       0x0f84f001,
+       0xf400d880,
+/* 0x0066: queue_get_done */
+       0x00f80132,
+/* 0x0068: nv_rd32 */
+       0xf002ecb9,
+       0x07f11fc9,
+       0x03f0ca00,
+       0x000cd001,
+/* 0x007a: nv_rd32_wait */
+       0xc7f104bd,
+       0xc3f0ca00,
+       0x00cccf01,
+       0xf41fccc8,
+       0xa7f0f31b,
+       0x1021f506,
+       0x00f7f101,
+       0x01f3f0cb,
+       0xf800ffcf,
+/* 0x009d: nv_wr32 */
+       0x0007f100,
+       0x0103f0cc,
+       0xbd000fd0,
+       0x02ecb904,
+       0xf01fc9f0,
+       0x07f11ec9,
+       0x03f0ca00,
+       0x000cd001,
+/* 0x00be: nv_wr32_wait */
+       0xc7f104bd,
+       0xc3f0ca00,
+       0x00cccf01,
+       0xf41fccc8,
+       0x00f8f31b,
+/* 0x00d0: wait_donez */
+       0x99f094bd,
+       0x0007f100,
+       0x0203f00f,
+       0xbd0009d0,
+       0x0007f104,
+       0x0203f006,
+       0xbd000ad0,
+/* 0x00ed: wait_donez_ne */
+       0x0087f104,
+       0x0183f000,
+       0xff0088cf,
+       0x1bf4888a,
+       0xf094bdf3,
+       0x07f10099,
+       0x03f01700,
+       0x0009d002,
+       0x00f804bd,
+/* 0x0110: wait_doneo */
+       0x99f094bd,
+       0x0007f100,
+       0x0203f00f,
+       0xbd0009d0,
+       0x0007f104,
+       0x0203f006,
+       0xbd000ad0,
+/* 0x012d: wait_doneo_e */
+       0x0087f104,
+       0x0183f000,
+       0xff0088cf,
+       0x0bf4888a,
+       0xf094bdf3,
+       0x07f10099,
+       0x03f01700,
+       0x0009d002,
+       0x00f804bd,
+/* 0x0150: mmctx_size */
+/* 0x0152: nv_mmctx_size_loop */
+       0xe89894bd,
+       0x1a85b600,
+       0xb60180b6,
+       0x98bb0284,
+       0x04e0b600,
+       0xf404efb8,
+       0x9fb9eb1b,
+/* 0x016f: mmctx_xfer */
+       0xbd00f802,
+       0x0199f094,
+       0x0f0007f1,
+       0xd00203f0,
+       0x04bd0009,
+       0xbbfd94bd,
+       0x120bf405,
+       0xc40007f1,
+       0xd00103f0,
+       0x04bd000b,
+/* 0x0197: mmctx_base_disabled */
+       0xfd0099f0,
+       0x0bf405ee,
+       0x0007f11e,
+       0x0103f0c6,
+       0xbd000ed0,
+       0x0007f104,
+       0x0103f0c7,
+       0xbd000fd0,
+       0x0199f004,
+/* 0x01b8: mmctx_multi_disabled */
+       0xb600abc8,
+       0xb9f010b4,
+       0x01aec80c,
+       0xfd11e4b6,
+       0x07f105be,
+       0x03f0c500,
+       0x000bd001,
+/* 0x01d6: mmctx_exec_loop */
+/* 0x01d6: mmctx_wait_free */
+       0xe7f104bd,
+       0xe3f0c500,
+       0x00eecf01,
+       0xf41fe4f0,
+       0xce98f30b,
+       0x05e9fd00,
+       0xc80007f1,
+       0xd00103f0,
+       0x04bd000e,
+       0xb804c0b6,
+       0x1bf404cd,
+       0x02abc8d8,
+/* 0x0207: mmctx_fini_wait */
+       0xf11f1bf4,
+       0xf0c500b7,
+       0xbbcf01b3,
+       0x1fb4f000,
+       0xf410b4b0,
+       0xa7f0f01b,
+       0xd021f405,
+/* 0x0223: mmctx_stop */
+       0xc82b0ef4,
+       0xb4b600ab,
+       0x0cb9f010,
+       0xf112b9f0,
+       0xf0c50007,
+       0x0bd00103,
+/* 0x023b: mmctx_stop_wait */
+       0xf104bd00,
+       0xf0c500b7,
+       0xbbcf01b3,
+       0x12bbc800,
+/* 0x024b: mmctx_done */
+       0xbdf31bf4,
+       0x0199f094,
+       0x170007f1,
+       0xd00203f0,
+       0x04bd0009,
+/* 0x025e: strand_wait */
+       0xa0f900f8,
+       0xf402a7f0,
+       0xa0fcd021,
+/* 0x026a: strand_pre */
+       0x97f000f8,
+       0xfc07f10c,
+       0x0203f04a,
+       0xbd0009d0,
+       0x5e21f504,
+/* 0x027f: strand_post */
+       0xf000f802,
+       0x07f10d97,
+       0x03f04afc,
+       0x0009d002,
+       0x21f504bd,
+       0x00f8025e,
+/* 0x0294: strand_set */
+       0xf10fc7f0,
+       0xf04ffc07,
+       0x0cd00203,
+       0xf004bd00,
+       0x07f10bc7,
+       0x03f04afc,
+       0x000cd002,
+       0x07f104bd,
+       0x03f04ffc,
+       0x000ed002,
+       0xc7f004bd,
+       0xfc07f10a,
+       0x0203f04a,
+       0xbd000cd0,
+       0x5e21f504,
+/* 0x02d3: strand_ctx_init */
+       0xbd00f802,
+       0x0399f094,
+       0x0f0007f1,
+       0xd00203f0,
+       0x04bd0009,
+       0x026a21f5,
+       0xf503e7f0,
+       0xbd029421,
+       0xfc07f1c4,
+       0x0203f047,
+       0xbd000cd0,
+       0x01c7f004,
+       0x4afc07f1,
+       0xd00203f0,
+       0x04bd000c,
+       0x025e21f5,
+       0xf1010c92,
+       0xf046fc07,
+       0x0cd00203,
+       0xf004bd00,
+       0x07f102c7,
+       0x03f04afc,
+       0x000cd002,
+       0x21f504bd,
+       0x21f5025e,
+       0x87f1027f,
+       0x83f04200,
+       0x0097f102,
+       0x0293f020,
+       0x950099cf,
+/* 0x034a: ctx_init_strand_loop */
+       0x8ed008fe,
+       0x408ed000,
+       0xb6808acf,
+       0xa0b606a5,
+       0x00eabb01,
+       0xb60480b6,
+       0x1bf40192,
+       0x08e4b6e8,
+       0xbdf2efbc,
+       0x0399f094,
+       0x170007f1,
+       0xd00203f0,
+       0x04bd0009,
+/* 0x037e: error */
+       0x07f100f8,
+       0x03f00500,
+       0x000fd002,
+       0xf7f004bd,
+       0x0007f101,
+       0x0303f007,
+       0xbd000fd0,
+/* 0x039b: init */
+       0xbd00f804,
+       0x0007fe04,
+       0x420017f1,
+       0xcf0013f0,
+       0x11e70011,
+       0x14b60109,
+       0x0014fe08,
+       0xf10227f0,
+       0xf0120007,
+       0x02d00003,
+       0xf104bd00,
+       0xfe06c817,
+       0x24bd0010,
+       0x070007f1,
+       0xd00003f0,
+       0x04bd0002,
+       0x200327f1,
+       0x010007f1,
+       0xd00103f0,
+       0x04bd0002,
+       0x200427f1,
+       0x010407f1,
+       0xd00103f0,
+       0x04bd0002,
+       0x200b27f1,
+       0x010807f1,
+       0xd00103f0,
+       0x04bd0002,
+       0x200c27f1,
+       0x011c07f1,
+       0xd00103f0,
+       0x04bd0002,
+       0xf1010392,
+       0xf0090007,
+       0x03d00303,
+       0xf104bd00,
+       0xf0870427,
+       0x07f10023,
+       0x03f00400,
+       0x0002d000,
+       0x27f004bd,
+       0x0007f104,
+       0x0003f003,
+       0xbd0002d0,
+       0x1031f404,
+       0x9604e7f1,
+       0xf440e3f0,
+       0xfeb96821,
+       0x90f1c702,
+       0xf0030180,
+       0x0f801ff4,
+       0x0117f002,
+       0xb6041fbb,
+       0x07f10112,
+       0x03f00300,
+       0x0001d001,
+       0x07f104bd,
+       0x03f00400,
+       0x0001d001,
+       0x17f104bd,
+       0xf7f00100,
+       0x0d21f502,
+       0x1f21f508,
+       0x10f7f008,
+       0x086c21f5,
+       0x98000e98,
+       0x21f5010f,
+       0x14950150,
+       0x0007f108,
+       0x0103f0c0,
+       0xbd0004d0,
+       0x0007f104,
+       0x0103f0c1,
+       0xbd0004d0,
+       0x0030b704,
+       0x001fbb13,
+       0xf102f5b6,
+       0xf0d30007,
+       0x0fd00103,
+       0xb604bd00,
+       0x10b60815,
+       0x0814b601,
+       0xf5021fb9,
+       0xbb02d321,
+       0x0398001f,
+       0x0047f102,
+       0x5043f020,
+/* 0x04f4: init_gpc */
+       0x08044ea0,
+       0xf4021fb9,
+       0x4ea09d21,
+       0xf4bd010c,
+       0xa09d21f4,
+       0xf401044e,
+       0x4ea09d21,
+       0xf7f00100,
+       0x9d21f402,
+       0x08004ea0,
+/* 0x051c: init_gpc_wait */
+       0xc86821f4,
+       0x0bf41fff,
+       0x044ea0fa,
+       0x6821f408,
+       0xb7001fbb,
+       0xb6800040,
+       0x1bf40132,
+       0x00f7f0be,
+       0x086c21f5,
+       0xf500f7f0,
+       0xf1080d21,
+       0xf0010007,
+       0x01d00203,
+       0xbd04bd00,
+       0x1f19f014,
+       0x080007f1,
+       0xd00203f0,
+       0x04bd0001,
+/* 0x0564: main */
+       0xf40031f4,
+       0xd7f00028,
+       0x3921f410,
+       0xb1f401f4,
+       0xf54001e4,
+       0xbd00e91b,
+       0x0499f094,
+       0x0f0007f1,
+       0xd00203f0,
+       0x04bd0009,
+       0xc00017f1,
+       0xcf0213f0,
+       0x27f10011,
+       0x23f0c100,
+       0x0022cf02,
+       0xf51f13c8,
+       0xc800890b,
+       0x0bf41f23,
+       0xb920f962,
+       0x94bd0212,
+       0xf10799f0,
+       0xf00f0007,
+       0x09d00203,
+       0xf404bd00,
+       0x31f40132,
+       0x4021f502,
+       0xf094bd0a,
+       0x07f10799,
+       0x03f01700,
+       0x0009d002,
+       0x20fc04bd,
+       0x99f094bd,
+       0x0007f106,
+       0x0203f00f,
+       0xbd0009d0,
+       0x0131f404,
+       0x0a4021f5,
+       0x99f094bd,
+       0x0007f106,
+       0x0203f017,
+       0xbd0009d0,
+       0x330ef404,
+/* 0x060c: chsw_prev_no_next */
+       0x12b920f9,
+       0x0132f402,
+       0xf50232f4,
+       0xfc0a4021,
+       0x0007f120,
+       0x0203f0c0,
+       0xbd0002d0,
+       0x130ef404,
+/* 0x062c: chsw_no_prev */
+       0xf41f23c8,
+       0x31f40d0b,
+       0x0232f401,
+       0x0a4021f5,
+/* 0x063c: chsw_done */
+       0xf10127f0,
+       0xf0c30007,
+       0x02d00203,
+       0xbd04bd00,
+       0x0499f094,
+       0x170007f1,
+       0xd00203f0,
+       0x04bd0009,
+       0xff080ef5,
+/* 0x0660: main_not_ctx_switch */
+       0xf401e4b0,
+       0xf2b90d1b,
+       0xd021f502,
+       0x460ef409,
+/* 0x0670: main_not_ctx_chan */
+       0xf402e4b0,
+       0x94bd321b,
+       0xf10799f0,
+       0xf00f0007,
+       0x09d00203,
+       0xf404bd00,
+       0x32f40132,
+       0x4021f502,
+       0xf094bd0a,
+       0x07f10799,
+       0x03f01700,
+       0x0009d002,
+       0x0ef404bd,
+/* 0x06a5: main_not_ctx_save */
+       0x10ef9411,
+       0xf501f5f0,
+       0xf5037e21,
+/* 0x06b3: main_done */
+       0xbdfeb50e,
+       0x1f29f024,
+       0x080007f1,
+       0xd00203f0,
+       0x04bd0002,
+       0xfea00ef5,
+/* 0x06c8: ih */
+       0x88fe80f9,
+       0xf980f901,
+       0xf9a0f990,
+       0xf9d0f9b0,
+       0xbdf0f9e0,
+       0x00a7f104,
+       0x00a3f002,
+       0xc400aacf,
+       0x0bf404ab,
+       0x10d7f030,
+       0x1a00e7f1,
+       0xcf00e3f0,
+       0xf7f100ee,
+       0xf3f01900,
+       0x00ffcf00,
+       0xb70421f4,
+       0xf00400b0,
+       0x07f101e7,
+       0x03f01d00,
+       0x000ed000,
+/* 0x071a: ih_no_fifo */
+       0xabe404bd,
+       0x0bf40100,
+       0x10d7f00d,
+       0x4001e7f1,
+/* 0x072b: ih_no_ctxsw */
+       0xe40421f4,
+       0xf40400ab,
+       0xe7f16c0b,
+       0xe3f00708,
+       0x6821f440,
+       0xf102ffb9,
+       0xf0040007,
+       0x0fd00203,
+       0xf104bd00,
+       0xf00704e7,
+       0x21f440e3,
+       0x02ffb968,
+       0x030007f1,
+       0xd00203f0,
+       0x04bd000f,
+       0x9450fec7,
+       0xf7f102ee,
+       0xf3f00700,
+       0x00efbb40,
+       0xf16821f4,
+       0xf0020007,
+       0x0fd00203,
+       0xf004bd00,
+       0x21f503f7,
+       0xb7f1037e,
+       0xbfb90100,
+       0x44e7f102,
+       0x40e3f001,
+/* 0x079b: ih_no_fwmthd */
+       0xf19d21f4,
+       0xbd0504b7,
+       0xb4abffb0,
+       0xf10f0bf4,
+       0xf0070007,
+       0x0bd00303,
+/* 0x07b3: ih_no_other */
+       0xf104bd00,
+       0xf0010007,
+       0x0ad00003,
+       0xfc04bd00,
+       0xfce0fcf0,
+       0xfcb0fcd0,
+       0xfc90fca0,
+       0x0088fe80,
+       0x32f480fc,
+/* 0x07d7: ctx_4160s */
+       0xf001f800,
+       0xffb901f7,
+       0x60e7f102,
+       0x40e3f041,
+/* 0x07e7: ctx_4160s_wait */
+       0xf19d21f4,
+       0xf04160e7,
+       0x21f440e3,
+       0x02ffb968,
+       0xf404ffc8,
+       0x00f8f00b,
+/* 0x07fc: ctx_4160c */
+       0xffb9f4bd,
+       0x60e7f102,
+       0x40e3f041,
+       0xf89d21f4,
+/* 0x080d: ctx_4170s */
+       0x10f5f000,
+       0xf102ffb9,
+       0xf04170e7,
+       0x21f440e3,
+/* 0x081f: ctx_4170w */
+       0xf100f89d,
+       0xf04170e7,
+       0x21f440e3,
+       0x02ffb968,
+       0xf410f4f0,
+       0x00f8f01b,
+/* 0x0834: ctx_redswitch */
+       0x0200e7f1,
+       0xf040e5f0,
+       0xe5f020e5,
+       0x0007f110,
+       0x0103f085,
+       0xbd000ed0,
+       0x08f7f004,
+/* 0x0850: ctx_redswitch_delay */
+       0xf401f2b6,
+       0xe5f1fd1b,
+       0xe5f10400,
+       0x07f10100,
+       0x03f08500,
+       0x000ed001,
+       0x00f804bd,
+/* 0x086c: ctx_86c */
+       0x1b0007f1,
+       0xd00203f0,
+       0x04bd000f,
+       0xf102ffb9,
+       0xf08a14e7,
+       0x21f440e3,
+       0x02ffb99d,
+       0xa86ce7f1,
+       0xf441e3f0,
+       0x00f89d21,
+/* 0x0894: ctx_mem */
+       0x840007f1,
+       0xd00203f0,
+       0x04bd000f,
+/* 0x08a0: ctx_mem_wait */
+       0x8400f7f1,
+       0xcf02f3f0,
+       0xfffd00ff,
+       0xf31bf405,
+/* 0x08b2: ctx_load */
+       0x94bd00f8,
+       0xf10599f0,
+       0xf00f0007,
+       0x09d00203,
+       0xf004bd00,
+       0x21f40ca7,
+       0xf1f4bdd0,
+       0xf0890007,
+       0x0fd00203,
+       0xf104bd00,
+       0xf0c10007,
+       0x02d00203,
+       0xf104bd00,
+       0xf0830007,
+       0x02d00203,
+       0xf004bd00,
+       0x21f507f7,
+       0x07f10894,
+       0x03f0c000,
+       0x0002d002,
+       0x0bfe04bd,
+       0x1f2af000,
+       0xb60424b6,
+       0x94bd0220,
+       0xf10899f0,
+       0xf00f0007,
+       0x09d00203,
+       0xf104bd00,
+       0xf0810007,
+       0x02d00203,
+       0xf104bd00,
+       0xf1000027,
+       0xf0800023,
+       0x07f10225,
+       0x03f08800,
+       0x0002d002,
+       0x17f004bd,
+       0x0027f110,
+       0x0223f002,
+       0xf80512fa,
+       0xf094bd03,
+       0x07f10899,
+       0x03f01700,
+       0x0009d002,
+       0x019804bd,
+       0x1814b681,
+       0xb6800298,
+       0x12fd0825,
+       0x16018005,
+       0x99f094bd,
+       0x0007f109,
+       0x0203f00f,
+       0xbd0009d0,
+       0x0007f104,
+       0x0203f081,
+       0xbd0001d0,
+       0x0127f004,
+       0x880007f1,
+       0xd00203f0,
+       0x04bd0002,
+       0x010017f1,
+       0xfa0613f0,
+       0x03f80501,
+       0x99f094bd,
+       0x0007f109,
+       0x0203f017,
+       0xbd0009d0,
+       0xf094bd04,
+       0x07f10599,
+       0x03f01700,
+       0x0009d002,
+       0x00f804bd,
+/* 0x09d0: ctx_chan */
+       0x07d721f5,
+       0x08b221f5,
+       0xf40ca7f0,
+       0xf7f0d021,
+       0x9421f505,
+       0xfc21f508,
+/* 0x09eb: ctx_mmio_exec */
+       0x9800f807,
+       0x07f14103,
+       0x03f08100,
+       0x0003d002,
+       0x34bd04bd,
+/* 0x09fc: ctx_mmio_loop */
+       0xf4ff34c4,
+       0x57f10f1b,
+       0x53f00200,
+       0x0535fa06,
+/* 0x0a0e: ctx_mmio_pull */
+       0x4e9803f8,
+       0x814f9880,
+       0xb69d21f4,
+       0x12b60830,
+       0xdf1bf401,
+/* 0x0a20: ctx_mmio_done */
+       0xf1160398,
+       0xf0810007,
+       0x03d00203,
+       0x8004bd00,
+       0x17f14000,
+       0x13f00100,
+       0x0601fa06,
+       0x00f803f8,
+/* 0x0a40: ctx_xfer */
+       0xf104e7f0,
+       0xf0020007,
+       0x0ed00303,
+/* 0x0a4f: ctx_xfer_idle */
+       0xf104bd00,
+       0xf00000e7,
+       0xeecf03e3,
+       0x00e4f100,
+       0xf21bf420,
+       0xf40611f4,
+/* 0x0a66: ctx_xfer_pre */
+       0xf7f01102,
+       0x6c21f510,
+       0xd721f508,
+       0x1c11f407,
+/* 0x0a74: ctx_xfer_pre_load */
+       0xf502f7f0,
+       0xf5080d21,
+       0xf5081f21,
+       0xbd083421,
+       0x0d21f5f4,
+       0xb221f508,
+/* 0x0a8d: ctx_xfer_exec */
+       0x16019808,
+       0x07f124bd,
+       0x03f00500,
+       0x0002d001,
+       0x1fb904bd,
+       0x00e7f102,
+       0x41e3f0a5,
+       0xf09d21f4,
+       0x2cf001fc,
+       0x0124b602,
+       0xb905f2fd,
+       0xe7f102ff,
+       0xe3f0a504,
+       0x9d21f441,
+       0x026a21f5,
+       0x07f124bd,
+       0x03f047fc,
+       0x0002d002,
+       0x2cf004bd,
+       0x0320b601,
+       0x4afc07f1,
+       0xd00203f0,
+       0x04bd0002,
+       0xf001acf0,
+       0xb7f006a5,
+       0x000c9800,
+       0xf0010d98,
+       0x21f500e7,
+       0xa7f0016f,
+       0x1021f508,
+       0x5e21f501,
+       0x1301f402,
+       0xf40ca7f0,
+       0xf7f0d021,
+       0x9421f505,
+       0x3202f408,
+/* 0x0b1c: ctx_xfer_post */
+       0xf502f7f0,
+       0xbd080d21,
+       0x6c21f5f4,
+       0x7f21f508,
+       0x1f21f502,
+       0xf5f4bd08,
+       0xf4080d21,
+       0x01981011,
+       0x0511fd40,
+       0xf5070bf4,
+/* 0x0b47: ctx_xfer_no_post_mmio */
+       0xf509eb21,
+/* 0x0b4b: ctx_xfer_done */
+       0xf807fc21,
+       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,
+};
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/gr/fuc/hubgf117.fuc3 b/drivers/gpu/drm/nouveau/nvkm/engine/gr/fuc/hubgf117.fuc3
new file mode 100644 (file)
index 0000000..581b2d5
--- /dev/null
@@ -0,0 +1,40 @@
+/*
+ * Copyright 2013 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 <bskeggs@redhat.com>
+ */
+
+#define CHIPSET GF117
+#include "macros.fuc"
+
+.section #gf117_grhub_data
+#define INCLUDE_DATA
+#include "com.fuc"
+#include "hub.fuc"
+#undef INCLUDE_DATA
+
+.section #gf117_grhub_code
+#define INCLUDE_CODE
+bra #init
+#include "com.fuc"
+#include "hub.fuc"
+.align 256
+#undef INCLUDE_CODE
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/gr/fuc/hubgf117.fuc3.h b/drivers/gpu/drm/nouveau/nvkm/engine/gr/fuc/hubgf117.fuc3.h
new file mode 100644 (file)
index 0000000..7cb14e5
--- /dev/null
@@ -0,0 +1,1047 @@
+uint32_t gf117_grhub_data[] = {
+/* 0x0000: hub_mmio_list_head */
+       0x00000300,
+/* 0x0004: hub_mmio_list_tail */
+       0x00000304,
+/* 0x0008: gpc_count */
+       0x00000000,
+/* 0x000c: rop_count */
+       0x00000000,
+/* 0x0010: cmd_queue */
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+/* 0x0058: ctx_current */
+       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,
+/* 0x0100: chan_data */
+/* 0x0100: chan_mmio_count */
+       0x00000000,
+/* 0x0104: chan_mmio_address */
+       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,
+/* 0x0200: xfer_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,
+/* 0x0300: hub_mmio_list_base */
+       0x0417e91c,
+};
+
+uint32_t gf117_grhub_code[] = {
+       0x039b0ef5,
+/* 0x0004: queue_put */
+       0x9800d898,
+       0x86f001d9,
+       0x0489b808,
+       0xf00c1bf4,
+       0x21f502f7,
+       0x00f8037e,
+/* 0x001c: queue_put_next */
+       0xb60798c4,
+       0x8dbb0384,
+       0x0880b600,
+       0x80008e80,
+       0x90b6018f,
+       0x0f94f001,
+       0xf801d980,
+/* 0x0039: queue_get */
+       0x0131f400,
+       0x9800d898,
+       0x89b801d9,
+       0x210bf404,
+       0xb60789c4,
+       0x9dbb0394,
+       0x0890b600,
+       0x98009e98,
+       0x80b6019f,
+       0x0f84f001,
+       0xf400d880,
+/* 0x0066: queue_get_done */
+       0x00f80132,
+/* 0x0068: nv_rd32 */
+       0xf002ecb9,
+       0x07f11fc9,
+       0x03f0ca00,
+       0x000cd001,
+/* 0x007a: nv_rd32_wait */
+       0xc7f104bd,
+       0xc3f0ca00,
+       0x00cccf01,
+       0xf41fccc8,
+       0xa7f0f31b,
+       0x1021f506,
+       0x00f7f101,
+       0x01f3f0cb,
+       0xf800ffcf,
+/* 0x009d: nv_wr32 */
+       0x0007f100,
+       0x0103f0cc,
+       0xbd000fd0,
+       0x02ecb904,
+       0xf01fc9f0,
+       0x07f11ec9,
+       0x03f0ca00,
+       0x000cd001,
+/* 0x00be: nv_wr32_wait */
+       0xc7f104bd,
+       0xc3f0ca00,
+       0x00cccf01,
+       0xf41fccc8,
+       0x00f8f31b,
+/* 0x00d0: wait_donez */
+       0x99f094bd,
+       0x0007f100,
+       0x0203f00f,
+       0xbd0009d0,
+       0x0007f104,
+       0x0203f006,
+       0xbd000ad0,
+/* 0x00ed: wait_donez_ne */
+       0x0087f104,
+       0x0183f000,
+       0xff0088cf,
+       0x1bf4888a,
+       0xf094bdf3,
+       0x07f10099,
+       0x03f01700,
+       0x0009d002,
+       0x00f804bd,
+/* 0x0110: wait_doneo */
+       0x99f094bd,
+       0x0007f100,
+       0x0203f00f,
+       0xbd0009d0,
+       0x0007f104,
+       0x0203f006,
+       0xbd000ad0,
+/* 0x012d: wait_doneo_e */
+       0x0087f104,
+       0x0183f000,
+       0xff0088cf,
+       0x0bf4888a,
+       0xf094bdf3,
+       0x07f10099,
+       0x03f01700,
+       0x0009d002,
+       0x00f804bd,
+/* 0x0150: mmctx_size */
+/* 0x0152: nv_mmctx_size_loop */
+       0xe89894bd,
+       0x1a85b600,
+       0xb60180b6,
+       0x98bb0284,
+       0x04e0b600,
+       0xf404efb8,
+       0x9fb9eb1b,
+/* 0x016f: mmctx_xfer */
+       0xbd00f802,
+       0x0199f094,
+       0x0f0007f1,
+       0xd00203f0,
+       0x04bd0009,
+       0xbbfd94bd,
+       0x120bf405,
+       0xc40007f1,
+       0xd00103f0,
+       0x04bd000b,
+/* 0x0197: mmctx_base_disabled */
+       0xfd0099f0,
+       0x0bf405ee,
+       0x0007f11e,
+       0x0103f0c6,
+       0xbd000ed0,
+       0x0007f104,
+       0x0103f0c7,
+       0xbd000fd0,
+       0x0199f004,
+/* 0x01b8: mmctx_multi_disabled */
+       0xb600abc8,
+       0xb9f010b4,
+       0x01aec80c,
+       0xfd11e4b6,
+       0x07f105be,
+       0x03f0c500,
+       0x000bd001,
+/* 0x01d6: mmctx_exec_loop */
+/* 0x01d6: mmctx_wait_free */
+       0xe7f104bd,
+       0xe3f0c500,
+       0x00eecf01,
+       0xf41fe4f0,
+       0xce98f30b,
+       0x05e9fd00,
+       0xc80007f1,
+       0xd00103f0,
+       0x04bd000e,
+       0xb804c0b6,
+       0x1bf404cd,
+       0x02abc8d8,
+/* 0x0207: mmctx_fini_wait */
+       0xf11f1bf4,
+       0xf0c500b7,
+       0xbbcf01b3,
+       0x1fb4f000,
+       0xf410b4b0,
+       0xa7f0f01b,
+       0xd021f405,
+/* 0x0223: mmctx_stop */
+       0xc82b0ef4,
+       0xb4b600ab,
+       0x0cb9f010,
+       0xf112b9f0,
+       0xf0c50007,
+       0x0bd00103,
+/* 0x023b: mmctx_stop_wait */
+       0xf104bd00,
+       0xf0c500b7,
+       0xbbcf01b3,
+       0x12bbc800,
+/* 0x024b: mmctx_done */
+       0xbdf31bf4,
+       0x0199f094,
+       0x170007f1,
+       0xd00203f0,
+       0x04bd0009,
+/* 0x025e: strand_wait */
+       0xa0f900f8,
+       0xf402a7f0,
+       0xa0fcd021,
+/* 0x026a: strand_pre */
+       0x97f000f8,
+       0xfc07f10c,
+       0x0203f04a,
+       0xbd0009d0,
+       0x5e21f504,
+/* 0x027f: strand_post */
+       0xf000f802,
+       0x07f10d97,
+       0x03f04afc,
+       0x0009d002,
+       0x21f504bd,
+       0x00f8025e,
+/* 0x0294: strand_set */
+       0xf10fc7f0,
+       0xf04ffc07,
+       0x0cd00203,
+       0xf004bd00,
+       0x07f10bc7,
+       0x03f04afc,
+       0x000cd002,
+       0x07f104bd,
+       0x03f04ffc,
+       0x000ed002,
+       0xc7f004bd,
+       0xfc07f10a,
+       0x0203f04a,
+       0xbd000cd0,
+       0x5e21f504,
+/* 0x02d3: strand_ctx_init */
+       0xbd00f802,
+       0x0399f094,
+       0x0f0007f1,
+       0xd00203f0,
+       0x04bd0009,
+       0x026a21f5,
+       0xf503e7f0,
+       0xbd029421,
+       0xfc07f1c4,
+       0x0203f047,
+       0xbd000cd0,
+       0x01c7f004,
+       0x4afc07f1,
+       0xd00203f0,
+       0x04bd000c,
+       0x025e21f5,
+       0xf1010c92,
+       0xf046fc07,
+       0x0cd00203,
+       0xf004bd00,
+       0x07f102c7,
+       0x03f04afc,
+       0x000cd002,
+       0x21f504bd,
+       0x21f5025e,
+       0x87f1027f,
+       0x83f04200,
+       0x0097f102,
+       0x0293f020,
+       0x950099cf,
+/* 0x034a: ctx_init_strand_loop */
+       0x8ed008fe,
+       0x408ed000,
+       0xb6808acf,
+       0xa0b606a5,
+       0x00eabb01,
+       0xb60480b6,
+       0x1bf40192,
+       0x08e4b6e8,
+       0xbdf2efbc,
+       0x0399f094,
+       0x170007f1,
+       0xd00203f0,
+       0x04bd0009,
+/* 0x037e: error */
+       0x07f100f8,
+       0x03f00500,
+       0x000fd002,
+       0xf7f004bd,
+       0x0007f101,
+       0x0303f007,
+       0xbd000fd0,
+/* 0x039b: init */
+       0xbd00f804,
+       0x0007fe04,
+       0x420017f1,
+       0xcf0013f0,
+       0x11e70011,
+       0x14b60109,
+       0x0014fe08,
+       0xf10227f0,
+       0xf0120007,
+       0x02d00003,
+       0xf104bd00,
+       0xfe06c817,
+       0x24bd0010,
+       0x070007f1,
+       0xd00003f0,
+       0x04bd0002,
+       0x200327f1,
+       0x010007f1,
+       0xd00103f0,
+       0x04bd0002,
+       0x200427f1,
+       0x010407f1,
+       0xd00103f0,
+       0x04bd0002,
+       0x200b27f1,
+       0x010807f1,
+       0xd00103f0,
+       0x04bd0002,
+       0x200c27f1,
+       0x011c07f1,
+       0xd00103f0,
+       0x04bd0002,
+       0xf1010392,
+       0xf0090007,
+       0x03d00303,
+       0xf104bd00,
+       0xf0870427,
+       0x07f10023,
+       0x03f00400,
+       0x0002d000,
+       0x27f004bd,
+       0x0007f104,
+       0x0003f003,
+       0xbd0002d0,
+       0x1031f404,
+       0x9604e7f1,
+       0xf440e3f0,
+       0xfeb96821,
+       0x90f1c702,
+       0xf0030180,
+       0x0f801ff4,
+       0x0117f002,
+       0xb6041fbb,
+       0x07f10112,
+       0x03f00300,
+       0x0001d001,
+       0x07f104bd,
+       0x03f00400,
+       0x0001d001,
+       0x17f104bd,
+       0xf7f00100,
+       0x0d21f502,
+       0x1f21f508,
+       0x10f7f008,
+       0x086c21f5,
+       0x98000e98,
+       0x21f5010f,
+       0x14950150,
+       0x0007f108,
+       0x0103f0c0,
+       0xbd0004d0,
+       0x0007f104,
+       0x0103f0c1,
+       0xbd0004d0,
+       0x0030b704,
+       0x001fbb13,
+       0xf102f5b6,
+       0xf0d30007,
+       0x0fd00103,
+       0xb604bd00,
+       0x10b60815,
+       0x0814b601,
+       0xf5021fb9,
+       0xbb02d321,
+       0x0398001f,
+       0x0047f102,
+       0x5043f020,
+/* 0x04f4: init_gpc */
+       0x08044ea0,
+       0xf4021fb9,
+       0x4ea09d21,
+       0xf4bd010c,
+       0xa09d21f4,
+       0xf401044e,
+       0x4ea09d21,
+       0xf7f00100,
+       0x9d21f402,
+       0x08004ea0,
+/* 0x051c: init_gpc_wait */
+       0xc86821f4,
+       0x0bf41fff,
+       0x044ea0fa,
+       0x6821f408,
+       0xb7001fbb,
+       0xb6800040,
+       0x1bf40132,
+       0x00f7f0be,
+       0x086c21f5,
+       0xf500f7f0,
+       0xf1080d21,
+       0xf0010007,
+       0x01d00203,
+       0xbd04bd00,
+       0x1f19f014,
+       0x080007f1,
+       0xd00203f0,
+       0x04bd0001,
+/* 0x0564: main */
+       0xf40031f4,
+       0xd7f00028,
+       0x3921f410,
+       0xb1f401f4,
+       0xf54001e4,
+       0xbd00e91b,
+       0x0499f094,
+       0x0f0007f1,
+       0xd00203f0,
+       0x04bd0009,
+       0xc00017f1,
+       0xcf0213f0,
+       0x27f10011,
+       0x23f0c100,
+       0x0022cf02,
+       0xf51f13c8,
+       0xc800890b,
+       0x0bf41f23,
+       0xb920f962,
+       0x94bd0212,
+       0xf10799f0,
+       0xf00f0007,
+       0x09d00203,
+       0xf404bd00,
+       0x31f40132,
+       0x4021f502,
+       0xf094bd0a,
+       0x07f10799,
+       0x03f01700,
+       0x0009d002,
+       0x20fc04bd,
+       0x99f094bd,
+       0x0007f106,
+       0x0203f00f,
+       0xbd0009d0,
+       0x0131f404,
+       0x0a4021f5,
+       0x99f094bd,
+       0x0007f106,
+       0x0203f017,
+       0xbd0009d0,
+       0x330ef404,
+/* 0x060c: chsw_prev_no_next */
+       0x12b920f9,
+       0x0132f402,
+       0xf50232f4,
+       0xfc0a4021,
+       0x0007f120,
+       0x0203f0c0,
+       0xbd0002d0,
+       0x130ef404,
+/* 0x062c: chsw_no_prev */
+       0xf41f23c8,
+       0x31f40d0b,
+       0x0232f401,
+       0x0a4021f5,
+/* 0x063c: chsw_done */
+       0xf10127f0,
+       0xf0c30007,
+       0x02d00203,
+       0xbd04bd00,
+       0x0499f094,
+       0x170007f1,
+       0xd00203f0,
+       0x04bd0009,
+       0xff080ef5,
+/* 0x0660: main_not_ctx_switch */
+       0xf401e4b0,
+       0xf2b90d1b,
+       0xd021f502,
+       0x460ef409,
+/* 0x0670: main_not_ctx_chan */
+       0xf402e4b0,
+       0x94bd321b,
+       0xf10799f0,
+       0xf00f0007,
+       0x09d00203,
+       0xf404bd00,
+       0x32f40132,
+       0x4021f502,
+       0xf094bd0a,
+       0x07f10799,
+       0x03f01700,
+       0x0009d002,
+       0x0ef404bd,
+/* 0x06a5: main_not_ctx_save */
+       0x10ef9411,
+       0xf501f5f0,
+       0xf5037e21,
+/* 0x06b3: main_done */
+       0xbdfeb50e,
+       0x1f29f024,
+       0x080007f1,
+       0xd00203f0,
+       0x04bd0002,
+       0xfea00ef5,
+/* 0x06c8: ih */
+       0x88fe80f9,
+       0xf980f901,
+       0xf9a0f990,
+       0xf9d0f9b0,
+       0xbdf0f9e0,
+       0x00a7f104,
+       0x00a3f002,
+       0xc400aacf,
+       0x0bf404ab,
+       0x10d7f030,
+       0x1a00e7f1,
+       0xcf00e3f0,
+       0xf7f100ee,
+       0xf3f01900,
+       0x00ffcf00,
+       0xb70421f4,
+       0xf00400b0,
+       0x07f101e7,
+       0x03f01d00,
+       0x000ed000,
+/* 0x071a: ih_no_fifo */
+       0xabe404bd,
+       0x0bf40100,
+       0x10d7f00d,
+       0x4001e7f1,
+/* 0x072b: ih_no_ctxsw */
+       0xe40421f4,
+       0xf40400ab,
+       0xe7f16c0b,
+       0xe3f00708,
+       0x6821f440,
+       0xf102ffb9,
+       0xf0040007,
+       0x0fd00203,
+       0xf104bd00,
+       0xf00704e7,
+       0x21f440e3,
+       0x02ffb968,
+       0x030007f1,
+       0xd00203f0,
+       0x04bd000f,
+       0x9450fec7,
+       0xf7f102ee,
+       0xf3f00700,
+       0x00efbb40,
+       0xf16821f4,
+       0xf0020007,
+       0x0fd00203,
+       0xf004bd00,
+       0x21f503f7,
+       0xb7f1037e,
+       0xbfb90100,
+       0x44e7f102,
+       0x40e3f001,
+/* 0x079b: ih_no_fwmthd */
+       0xf19d21f4,
+       0xbd0504b7,
+       0xb4abffb0,
+       0xf10f0bf4,
+       0xf0070007,
+       0x0bd00303,
+/* 0x07b3: ih_no_other */
+       0xf104bd00,
+       0xf0010007,
+       0x0ad00003,
+       0xfc04bd00,
+       0xfce0fcf0,
+       0xfcb0fcd0,
+       0xfc90fca0,
+       0x0088fe80,
+       0x32f480fc,
+/* 0x07d7: ctx_4160s */
+       0xf001f800,
+       0xffb901f7,
+       0x60e7f102,
+       0x40e3f041,
+/* 0x07e7: ctx_4160s_wait */
+       0xf19d21f4,
+       0xf04160e7,
+       0x21f440e3,
+       0x02ffb968,
+       0xf404ffc8,
+       0x00f8f00b,
+/* 0x07fc: ctx_4160c */
+       0xffb9f4bd,
+       0x60e7f102,
+       0x40e3f041,
+       0xf89d21f4,
+/* 0x080d: ctx_4170s */
+       0x10f5f000,
+       0xf102ffb9,
+       0xf04170e7,
+       0x21f440e3,
+/* 0x081f: ctx_4170w */
+       0xf100f89d,
+       0xf04170e7,
+       0x21f440e3,
+       0x02ffb968,
+       0xf410f4f0,
+       0x00f8f01b,
+/* 0x0834: ctx_redswitch */
+       0x0200e7f1,
+       0xf040e5f0,
+       0xe5f020e5,
+       0x0007f110,
+       0x0103f085,
+       0xbd000ed0,
+       0x08f7f004,
+/* 0x0850: ctx_redswitch_delay */
+       0xf401f2b6,
+       0xe5f1fd1b,
+       0xe5f10400,
+       0x07f10100,
+       0x03f08500,
+       0x000ed001,
+       0x00f804bd,
+/* 0x086c: ctx_86c */
+       0x1b0007f1,
+       0xd00203f0,
+       0x04bd000f,
+       0xf102ffb9,
+       0xf08a14e7,
+       0x21f440e3,
+       0x02ffb99d,
+       0xa86ce7f1,
+       0xf441e3f0,
+       0x00f89d21,
+/* 0x0894: ctx_mem */
+       0x840007f1,
+       0xd00203f0,
+       0x04bd000f,
+/* 0x08a0: ctx_mem_wait */
+       0x8400f7f1,
+       0xcf02f3f0,
+       0xfffd00ff,
+       0xf31bf405,
+/* 0x08b2: ctx_load */
+       0x94bd00f8,
+       0xf10599f0,
+       0xf00f0007,
+       0x09d00203,
+       0xf004bd00,
+       0x21f40ca7,
+       0xf1f4bdd0,
+       0xf0890007,
+       0x0fd00203,
+       0xf104bd00,
+       0xf0c10007,
+       0x02d00203,
+       0xf104bd00,
+       0xf0830007,
+       0x02d00203,
+       0xf004bd00,
+       0x21f507f7,
+       0x07f10894,
+       0x03f0c000,
+       0x0002d002,
+       0x0bfe04bd,
+       0x1f2af000,
+       0xb60424b6,
+       0x94bd0220,
+       0xf10899f0,
+       0xf00f0007,
+       0x09d00203,
+       0xf104bd00,
+       0xf0810007,
+       0x02d00203,
+       0xf104bd00,
+       0xf1000027,
+       0xf0800023,
+       0x07f10225,
+       0x03f08800,
+       0x0002d002,
+       0x17f004bd,
+       0x0027f110,
+       0x0223f002,
+       0xf80512fa,
+       0xf094bd03,
+       0x07f10899,
+       0x03f01700,
+       0x0009d002,
+       0x019804bd,
+       0x1814b681,
+       0xb6800298,
+       0x12fd0825,
+       0x16018005,
+       0x99f094bd,
+       0x0007f109,
+       0x0203f00f,
+       0xbd0009d0,
+       0x0007f104,
+       0x0203f081,
+       0xbd0001d0,
+       0x0127f004,
+       0x880007f1,
+       0xd00203f0,
+       0x04bd0002,
+       0x010017f1,
+       0xfa0613f0,
+       0x03f80501,
+       0x99f094bd,
+       0x0007f109,
+       0x0203f017,
+       0xbd0009d0,
+       0xf094bd04,
+       0x07f10599,
+       0x03f01700,
+       0x0009d002,
+       0x00f804bd,
+/* 0x09d0: ctx_chan */
+       0x07d721f5,
+       0x08b221f5,
+       0xf40ca7f0,
+       0xf7f0d021,
+       0x9421f505,
+       0xfc21f508,
+/* 0x09eb: ctx_mmio_exec */
+       0x9800f807,
+       0x07f14103,
+       0x03f08100,
+       0x0003d002,
+       0x34bd04bd,
+/* 0x09fc: ctx_mmio_loop */
+       0xf4ff34c4,
+       0x57f10f1b,
+       0x53f00200,
+       0x0535fa06,
+/* 0x0a0e: ctx_mmio_pull */
+       0x4e9803f8,
+       0x814f9880,
+       0xb69d21f4,
+       0x12b60830,
+       0xdf1bf401,
+/* 0x0a20: ctx_mmio_done */
+       0xf1160398,
+       0xf0810007,
+       0x03d00203,
+       0x8004bd00,
+       0x17f14000,
+       0x13f00100,
+       0x0601fa06,
+       0x00f803f8,
+/* 0x0a40: ctx_xfer */
+       0xf104e7f0,
+       0xf0020007,
+       0x0ed00303,
+/* 0x0a4f: ctx_xfer_idle */
+       0xf104bd00,
+       0xf00000e7,
+       0xeecf03e3,
+       0x00e4f100,
+       0xf21bf420,
+       0xf40611f4,
+/* 0x0a66: ctx_xfer_pre */
+       0xf7f01102,
+       0x6c21f510,
+       0xd721f508,
+       0x1c11f407,
+/* 0x0a74: ctx_xfer_pre_load */
+       0xf502f7f0,
+       0xf5080d21,
+       0xf5081f21,
+       0xbd083421,
+       0x0d21f5f4,
+       0xb221f508,
+/* 0x0a8d: ctx_xfer_exec */
+       0x16019808,
+       0x07f124bd,
+       0x03f00500,
+       0x0002d001,
+       0x1fb904bd,
+       0x00e7f102,
+       0x41e3f0a5,
+       0xf09d21f4,
+       0x2cf001fc,
+       0x0124b602,
+       0xb905f2fd,
+       0xe7f102ff,
+       0xe3f0a504,
+       0x9d21f441,
+       0x026a21f5,
+       0x07f124bd,
+       0x03f047fc,
+       0x0002d002,
+       0x2cf004bd,
+       0x0320b601,
+       0x4afc07f1,
+       0xd00203f0,
+       0x04bd0002,
+       0xf001acf0,
+       0xb7f006a5,
+       0x000c9800,
+       0xf0010d98,
+       0x21f500e7,
+       0xa7f0016f,
+       0x1021f508,
+       0x5e21f501,
+       0x1301f402,
+       0xf40ca7f0,
+       0xf7f0d021,
+       0x9421f505,
+       0x3202f408,
+/* 0x0b1c: ctx_xfer_post */
+       0xf502f7f0,
+       0xbd080d21,
+       0x6c21f5f4,
+       0x7f21f508,
+       0x1f21f502,
+       0xf5f4bd08,
+       0xf4080d21,
+       0x01981011,
+       0x0511fd40,
+       0xf5070bf4,
+/* 0x0b47: ctx_xfer_no_post_mmio */
+       0xf509eb21,
+/* 0x0b4b: ctx_xfer_done */
+       0xf807fc21,
+       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,
+};
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/gr/fuc/hubgk104.fuc3 b/drivers/gpu/drm/nouveau/nvkm/engine/gr/fuc/hubgk104.fuc3
new file mode 100644 (file)
index 0000000..d977d39
--- /dev/null
@@ -0,0 +1,40 @@
+/*
+ * Copyright 2013 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 <bskeggs@redhat.com>
+ */
+
+#define CHIPSET GK100
+#include "macros.fuc"
+
+.section #gk104_grhub_data
+#define INCLUDE_DATA
+#include "com.fuc"
+#include "hub.fuc"
+#undef INCLUDE_DATA
+
+.section #gk104_grhub_code
+#define INCLUDE_CODE
+bra #init
+#include "com.fuc"
+#include "hub.fuc"
+.align 256
+#undef INCLUDE_CODE
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/gr/fuc/hubgk104.fuc3.h b/drivers/gpu/drm/nouveau/nvkm/engine/gr/fuc/hubgk104.fuc3.h
new file mode 100644 (file)
index 0000000..95ac151
--- /dev/null
@@ -0,0 +1,1044 @@
+uint32_t gk104_grhub_data[] = {
+/* 0x0000: hub_mmio_list_head */
+       0x00000300,
+/* 0x0004: hub_mmio_list_tail */
+       0x00000304,
+/* 0x0008: gpc_count */
+       0x00000000,
+/* 0x000c: rop_count */
+       0x00000000,
+/* 0x0010: cmd_queue */
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+/* 0x0058: ctx_current */
+       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,
+/* 0x0100: chan_data */
+/* 0x0100: chan_mmio_count */
+       0x00000000,
+/* 0x0104: chan_mmio_address */
+       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,
+/* 0x0200: xfer_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,
+/* 0x0300: hub_mmio_list_base */
+       0x0417e91c,
+};
+
+uint32_t gk104_grhub_code[] = {
+       0x039b0ef5,
+/* 0x0004: queue_put */
+       0x9800d898,
+       0x86f001d9,
+       0x0489b808,
+       0xf00c1bf4,
+       0x21f502f7,
+       0x00f8037e,
+/* 0x001c: queue_put_next */
+       0xb60798c4,
+       0x8dbb0384,
+       0x0880b600,
+       0x80008e80,
+       0x90b6018f,
+       0x0f94f001,
+       0xf801d980,
+/* 0x0039: queue_get */
+       0x0131f400,
+       0x9800d898,
+       0x89b801d9,
+       0x210bf404,
+       0xb60789c4,
+       0x9dbb0394,
+       0x0890b600,
+       0x98009e98,
+       0x80b6019f,
+       0x0f84f001,
+       0xf400d880,
+/* 0x0066: queue_get_done */
+       0x00f80132,
+/* 0x0068: nv_rd32 */
+       0xf002ecb9,
+       0x07f11fc9,
+       0x03f0ca00,
+       0x000cd001,
+/* 0x007a: nv_rd32_wait */
+       0xc7f104bd,
+       0xc3f0ca00,
+       0x00cccf01,
+       0xf41fccc8,
+       0xa7f0f31b,
+       0x1021f506,
+       0x00f7f101,
+       0x01f3f0cb,
+       0xf800ffcf,
+/* 0x009d: nv_wr32 */
+       0x0007f100,
+       0x0103f0cc,
+       0xbd000fd0,
+       0x02ecb904,
+       0xf01fc9f0,
+       0x07f11ec9,
+       0x03f0ca00,
+       0x000cd001,
+/* 0x00be: nv_wr32_wait */
+       0xc7f104bd,
+       0xc3f0ca00,
+       0x00cccf01,
+       0xf41fccc8,
+       0x00f8f31b,
+/* 0x00d0: wait_donez */
+       0x99f094bd,
+       0x0007f100,
+       0x0203f00f,
+       0xbd0009d0,
+       0x0007f104,
+       0x0203f006,
+       0xbd000ad0,
+/* 0x00ed: wait_donez_ne */
+       0x0087f104,
+       0x0183f000,
+       0xff0088cf,
+       0x1bf4888a,
+       0xf094bdf3,
+       0x07f10099,
+       0x03f01700,
+       0x0009d002,
+       0x00f804bd,
+/* 0x0110: wait_doneo */
+       0x99f094bd,
+       0x0007f100,
+       0x0203f00f,
+       0xbd0009d0,
+       0x0007f104,
+       0x0203f006,
+       0xbd000ad0,
+/* 0x012d: wait_doneo_e */
+       0x0087f104,
+       0x0183f000,
+       0xff0088cf,
+       0x0bf4888a,
+       0xf094bdf3,
+       0x07f10099,
+       0x03f01700,
+       0x0009d002,
+       0x00f804bd,
+/* 0x0150: mmctx_size */
+/* 0x0152: nv_mmctx_size_loop */
+       0xe89894bd,
+       0x1a85b600,
+       0xb60180b6,
+       0x98bb0284,
+       0x04e0b600,
+       0xf404efb8,
+       0x9fb9eb1b,
+/* 0x016f: mmctx_xfer */
+       0xbd00f802,
+       0x0199f094,
+       0x0f0007f1,
+       0xd00203f0,
+       0x04bd0009,
+       0xbbfd94bd,
+       0x120bf405,
+       0xc40007f1,
+       0xd00103f0,
+       0x04bd000b,
+/* 0x0197: mmctx_base_disabled */
+       0xfd0099f0,
+       0x0bf405ee,
+       0x0007f11e,
+       0x0103f0c6,
+       0xbd000ed0,
+       0x0007f104,
+       0x0103f0c7,
+       0xbd000fd0,
+       0x0199f004,
+/* 0x01b8: mmctx_multi_disabled */
+       0xb600abc8,
+       0xb9f010b4,
+       0x01aec80c,
+       0xfd11e4b6,
+       0x07f105be,
+       0x03f0c500,
+       0x000bd001,
+/* 0x01d6: mmctx_exec_loop */
+/* 0x01d6: mmctx_wait_free */
+       0xe7f104bd,
+       0xe3f0c500,
+       0x00eecf01,
+       0xf41fe4f0,
+       0xce98f30b,
+       0x05e9fd00,
+       0xc80007f1,
+       0xd00103f0,
+       0x04bd000e,
+       0xb804c0b6,
+       0x1bf404cd,
+       0x02abc8d8,
+/* 0x0207: mmctx_fini_wait */
+       0xf11f1bf4,
+       0xf0c500b7,
+       0xbbcf01b3,
+       0x1fb4f000,
+       0xf410b4b0,
+       0xa7f0f01b,
+       0xd021f405,
+/* 0x0223: mmctx_stop */
+       0xc82b0ef4,
+       0xb4b600ab,
+       0x0cb9f010,
+       0xf112b9f0,
+       0xf0c50007,
+       0x0bd00103,
+/* 0x023b: mmctx_stop_wait */
+       0xf104bd00,
+       0xf0c500b7,
+       0xbbcf01b3,
+       0x12bbc800,
+/* 0x024b: mmctx_done */
+       0xbdf31bf4,
+       0x0199f094,
+       0x170007f1,
+       0xd00203f0,
+       0x04bd0009,
+/* 0x025e: strand_wait */
+       0xa0f900f8,
+       0xf402a7f0,
+       0xa0fcd021,
+/* 0x026a: strand_pre */
+       0x97f000f8,
+       0xfc07f10c,
+       0x0203f04a,
+       0xbd0009d0,
+       0x5e21f504,
+/* 0x027f: strand_post */
+       0xf000f802,
+       0x07f10d97,
+       0x03f04afc,
+       0x0009d002,
+       0x21f504bd,
+       0x00f8025e,
+/* 0x0294: strand_set */
+       0xf10fc7f0,
+       0xf04ffc07,
+       0x0cd00203,
+       0xf004bd00,
+       0x07f10bc7,
+       0x03f04afc,
+       0x000cd002,
+       0x07f104bd,
+       0x03f04ffc,
+       0x000ed002,
+       0xc7f004bd,
+       0xfc07f10a,
+       0x0203f04a,
+       0xbd000cd0,
+       0x5e21f504,
+/* 0x02d3: strand_ctx_init */
+       0xbd00f802,
+       0x0399f094,
+       0x0f0007f1,
+       0xd00203f0,
+       0x04bd0009,
+       0x026a21f5,
+       0xf503e7f0,
+       0xbd029421,
+       0xfc07f1c4,
+       0x0203f047,
+       0xbd000cd0,
+       0x01c7f004,
+       0x4afc07f1,
+       0xd00203f0,
+       0x04bd000c,
+       0x025e21f5,
+       0xf1010c92,
+       0xf046fc07,
+       0x0cd00203,
+       0xf004bd00,
+       0x07f102c7,
+       0x03f04afc,
+       0x000cd002,
+       0x21f504bd,
+       0x21f5025e,
+       0x87f1027f,
+       0x83f04200,
+       0x0097f102,
+       0x0293f020,
+       0x950099cf,
+/* 0x034a: ctx_init_strand_loop */
+       0x8ed008fe,
+       0x408ed000,
+       0xb6808acf,
+       0xa0b606a5,
+       0x00eabb01,
+       0xb60480b6,
+       0x1bf40192,
+       0x08e4b6e8,
+       0xbdf2efbc,
+       0x0399f094,
+       0x170007f1,
+       0xd00203f0,
+       0x04bd0009,
+/* 0x037e: error */
+       0x07f100f8,
+       0x03f00500,
+       0x000fd002,
+       0xf7f004bd,
+       0x0007f101,
+       0x0303f007,
+       0xbd000fd0,
+/* 0x039b: init */
+       0xbd00f804,
+       0x0007fe04,
+       0x420017f1,
+       0xcf0013f0,
+       0x11e70011,
+       0x14b60109,
+       0x0014fe08,
+       0xf10227f0,
+       0xf0120007,
+       0x02d00003,
+       0xf104bd00,
+       0xfe06c817,
+       0x24bd0010,
+       0x070007f1,
+       0xd00003f0,
+       0x04bd0002,
+       0x200327f1,
+       0x010007f1,
+       0xd00103f0,
+       0x04bd0002,
+       0x200427f1,
+       0x010407f1,
+       0xd00103f0,
+       0x04bd0002,
+       0x200b27f1,
+       0x010807f1,
+       0xd00103f0,
+       0x04bd0002,
+       0x200c27f1,
+       0x011c07f1,
+       0xd00103f0,
+       0x04bd0002,
+       0xf1010392,
+       0xf0090007,
+       0x03d00303,
+       0xf104bd00,
+       0xf0870427,
+       0x07f10023,
+       0x03f00400,
+       0x0002d000,
+       0x27f004bd,
+       0x0007f104,
+       0x0003f003,
+       0xbd0002d0,
+       0x1031f404,
+       0x9604e7f1,
+       0xf440e3f0,
+       0xfeb96821,
+       0x90f1c702,
+       0xf0030180,
+       0x0f801ff4,
+       0x0117f002,
+       0xb6041fbb,
+       0x07f10112,
+       0x03f00300,
+       0x0001d001,
+       0x07f104bd,
+       0x03f00400,
+       0x0001d001,
+       0x17f104bd,
+       0xf7f00100,
+       0xd721f502,
+       0xe921f507,
+       0x10f7f007,
+       0x083621f5,
+       0x98000e98,
+       0x21f5010f,
+       0x14950150,
+       0x0007f108,
+       0x0103f0c0,
+       0xbd0004d0,
+       0x0007f104,
+       0x0103f0c1,
+       0xbd0004d0,
+       0x0030b704,
+       0x001fbb13,
+       0xf102f5b6,
+       0xf0d30007,
+       0x0fd00103,
+       0xb604bd00,
+       0x10b60815,
+       0x0814b601,
+       0xf5021fb9,
+       0xbb02d321,
+       0x0398001f,
+       0x0047f102,
+       0x5043f020,
+/* 0x04f4: init_gpc */
+       0x08044ea0,
+       0xf4021fb9,
+       0x4ea09d21,
+       0xf4bd010c,
+       0xa09d21f4,
+       0xf401044e,
+       0x4ea09d21,
+       0xf7f00100,
+       0x9d21f402,
+       0x08004ea0,
+/* 0x051c: init_gpc_wait */
+       0xc86821f4,
+       0x0bf41fff,
+       0x044ea0fa,
+       0x6821f408,
+       0xb7001fbb,
+       0xb6800040,
+       0x1bf40132,
+       0x00f7f0be,
+       0x083621f5,
+       0xf500f7f0,
+       0xf107d721,
+       0xf0010007,
+       0x01d00203,
+       0xbd04bd00,
+       0x1f19f014,
+       0x080007f1,
+       0xd00203f0,
+       0x04bd0001,
+/* 0x0564: main */
+       0xf40031f4,
+       0xd7f00028,
+       0x3921f410,
+       0xb1f401f4,
+       0xf54001e4,
+       0xbd00e91b,
+       0x0499f094,
+       0x0f0007f1,
+       0xd00203f0,
+       0x04bd0009,
+       0xc00017f1,
+       0xcf0213f0,
+       0x27f10011,
+       0x23f0c100,
+       0x0022cf02,
+       0xf51f13c8,
+       0xc800890b,
+       0x0bf41f23,
+       0xb920f962,
+       0x94bd0212,
+       0xf10799f0,
+       0xf00f0007,
+       0x09d00203,
+       0xf404bd00,
+       0x31f40132,
+       0x0221f502,
+       0xf094bd0a,
+       0x07f10799,
+       0x03f01700,
+       0x0009d002,
+       0x20fc04bd,
+       0x99f094bd,
+       0x0007f106,
+       0x0203f00f,
+       0xbd0009d0,
+       0x0131f404,
+       0x0a0221f5,
+       0x99f094bd,
+       0x0007f106,
+       0x0203f017,
+       0xbd0009d0,
+       0x330ef404,
+/* 0x060c: chsw_prev_no_next */
+       0x12b920f9,
+       0x0132f402,
+       0xf50232f4,
+       0xfc0a0221,
+       0x0007f120,
+       0x0203f0c0,
+       0xbd0002d0,
+       0x130ef404,
+/* 0x062c: chsw_no_prev */
+       0xf41f23c8,
+       0x31f40d0b,
+       0x0232f401,
+       0x0a0221f5,
+/* 0x063c: chsw_done */
+       0xf10127f0,
+       0xf0c30007,
+       0x02d00203,
+       0xbd04bd00,
+       0x0499f094,
+       0x170007f1,
+       0xd00203f0,
+       0x04bd0009,
+       0xff080ef5,
+/* 0x0660: main_not_ctx_switch */
+       0xf401e4b0,
+       0xf2b90d1b,
+       0x9a21f502,
+       0x460ef409,
+/* 0x0670: main_not_ctx_chan */
+       0xf402e4b0,
+       0x94bd321b,
+       0xf10799f0,
+       0xf00f0007,
+       0x09d00203,
+       0xf404bd00,
+       0x32f40132,
+       0x0221f502,
+       0xf094bd0a,
+       0x07f10799,
+       0x03f01700,
+       0x0009d002,
+       0x0ef404bd,
+/* 0x06a5: main_not_ctx_save */
+       0x10ef9411,
+       0xf501f5f0,
+       0xf5037e21,
+/* 0x06b3: main_done */
+       0xbdfeb50e,
+       0x1f29f024,
+       0x080007f1,
+       0xd00203f0,
+       0x04bd0002,
+       0xfea00ef5,
+/* 0x06c8: ih */
+       0x88fe80f9,
+       0xf980f901,
+       0xf9a0f990,
+       0xf9d0f9b0,
+       0xbdf0f9e0,
+       0x00a7f104,
+       0x00a3f002,
+       0xc400aacf,
+       0x0bf404ab,
+       0x10d7f030,
+       0x1a00e7f1,
+       0xcf00e3f0,
+       0xf7f100ee,
+       0xf3f01900,
+       0x00ffcf00,
+       0xb70421f4,
+       0xf00400b0,
+       0x07f101e7,
+       0x03f01d00,
+       0x000ed000,
+/* 0x071a: ih_no_fifo */
+       0xabe404bd,
+       0x0bf40100,
+       0x10d7f00d,
+       0x4001e7f1,
+/* 0x072b: ih_no_ctxsw */
+       0xe40421f4,
+       0xf40400ab,
+       0xe7f16c0b,
+       0xe3f00708,
+       0x6821f440,
+       0xf102ffb9,
+       0xf0040007,
+       0x0fd00203,
+       0xf104bd00,
+       0xf00704e7,
+       0x21f440e3,
+       0x02ffb968,
+       0x030007f1,
+       0xd00203f0,
+       0x04bd000f,
+       0x9450fec7,
+       0xf7f102ee,
+       0xf3f00700,
+       0x00efbb40,
+       0xf16821f4,
+       0xf0020007,
+       0x0fd00203,
+       0xf004bd00,
+       0x21f503f7,
+       0xb7f1037e,
+       0xbfb90100,
+       0x44e7f102,
+       0x40e3f001,
+/* 0x079b: ih_no_fwmthd */
+       0xf19d21f4,
+       0xbd0504b7,
+       0xb4abffb0,
+       0xf10f0bf4,
+       0xf0070007,
+       0x0bd00303,
+/* 0x07b3: ih_no_other */
+       0xf104bd00,
+       0xf0010007,
+       0x0ad00003,
+       0xfc04bd00,
+       0xfce0fcf0,
+       0xfcb0fcd0,
+       0xfc90fca0,
+       0x0088fe80,
+       0x32f480fc,
+/* 0x07d7: ctx_4170s */
+       0xf001f800,
+       0xffb910f5,
+       0x70e7f102,
+       0x40e3f041,
+       0xf89d21f4,
+/* 0x07e9: ctx_4170w */
+       0x70e7f100,
+       0x40e3f041,
+       0xb96821f4,
+       0xf4f002ff,
+       0xf01bf410,
+/* 0x07fe: ctx_redswitch */
+       0xe7f100f8,
+       0xe5f00200,
+       0x20e5f040,
+       0xf110e5f0,
+       0xf0850007,
+       0x0ed00103,
+       0xf004bd00,
+/* 0x081a: ctx_redswitch_delay */
+       0xf2b608f7,
+       0xfd1bf401,
+       0x0400e5f1,
+       0x0100e5f1,
+       0x850007f1,
+       0xd00103f0,
+       0x04bd000e,
+/* 0x0836: ctx_86c */
+       0x07f100f8,
+       0x03f01b00,
+       0x000fd002,
+       0xffb904bd,
+       0x14e7f102,
+       0x40e3f08a,
+       0xb99d21f4,
+       0xe7f102ff,
+       0xe3f0a86c,
+       0x9d21f441,
+/* 0x085e: ctx_mem */
+       0x07f100f8,
+       0x03f08400,
+       0x000fd002,
+/* 0x086a: ctx_mem_wait */
+       0xf7f104bd,
+       0xf3f08400,
+       0x00ffcf02,
+       0xf405fffd,
+       0x00f8f31b,
+/* 0x087c: ctx_load */
+       0x99f094bd,
+       0x0007f105,
+       0x0203f00f,
+       0xbd0009d0,
+       0x0ca7f004,
+       0xbdd021f4,
+       0x0007f1f4,
+       0x0203f089,
+       0xbd000fd0,
+       0x0007f104,
+       0x0203f0c1,
+       0xbd0002d0,
+       0x0007f104,
+       0x0203f083,
+       0xbd0002d0,
+       0x07f7f004,
+       0x085e21f5,
+       0xc00007f1,
+       0xd00203f0,
+       0x04bd0002,
+       0xf0000bfe,
+       0x24b61f2a,
+       0x0220b604,
+       0x99f094bd,
+       0x0007f108,
+       0x0203f00f,
+       0xbd0009d0,
+       0x0007f104,
+       0x0203f081,
+       0xbd0002d0,
+       0x0027f104,
+       0x0023f100,
+       0x0225f080,
+       0x880007f1,
+       0xd00203f0,
+       0x04bd0002,
+       0xf11017f0,
+       0xf0020027,
+       0x12fa0223,
+       0xbd03f805,
+       0x0899f094,
+       0x170007f1,
+       0xd00203f0,
+       0x04bd0009,
+       0xb6810198,
+       0x02981814,
+       0x0825b680,
+       0x800512fd,
+       0x94bd1601,
+       0xf10999f0,
+       0xf00f0007,
+       0x09d00203,
+       0xf104bd00,
+       0xf0810007,
+       0x01d00203,
+       0xf004bd00,
+       0x07f10127,
+       0x03f08800,
+       0x0002d002,
+       0x17f104bd,
+       0x13f00100,
+       0x0501fa06,
+       0x94bd03f8,
+       0xf10999f0,
+       0xf0170007,
+       0x09d00203,
+       0xbd04bd00,
+       0x0599f094,
+       0x170007f1,
+       0xd00203f0,
+       0x04bd0009,
+/* 0x099a: ctx_chan */
+       0x21f500f8,
+       0xa7f0087c,
+       0xd021f40c,
+       0xf505f7f0,
+       0xf8085e21,
+/* 0x09ad: ctx_mmio_exec */
+       0x41039800,
+       0x810007f1,
+       0xd00203f0,
+       0x04bd0003,
+/* 0x09be: ctx_mmio_loop */
+       0x34c434bd,
+       0x0f1bf4ff,
+       0x020057f1,
+       0xfa0653f0,
+       0x03f80535,
+/* 0x09d0: ctx_mmio_pull */
+       0x98804e98,
+       0x21f4814f,
+       0x0830b69d,
+       0xf40112b6,
+/* 0x09e2: ctx_mmio_done */
+       0x0398df1b,
+       0x0007f116,
+       0x0203f081,
+       0xbd0003d0,
+       0x40008004,
+       0x010017f1,
+       0xfa0613f0,
+       0x03f80601,
+/* 0x0a02: ctx_xfer */
+       0xe7f000f8,
+       0x0007f104,
+       0x0303f002,
+       0xbd000ed0,
+/* 0x0a11: ctx_xfer_idle */
+       0x00e7f104,
+       0x03e3f000,
+       0xf100eecf,
+       0xf42000e4,
+       0x11f4f21b,
+       0x0d02f406,
+/* 0x0a28: ctx_xfer_pre */
+       0xf510f7f0,
+       0xf4083621,
+/* 0x0a32: ctx_xfer_pre_load */
+       0xf7f01c11,
+       0xd721f502,
+       0xe921f507,
+       0xfe21f507,
+       0xf5f4bd07,
+       0xf507d721,
+/* 0x0a4b: ctx_xfer_exec */
+       0x98087c21,
+       0x24bd1601,
+       0x050007f1,
+       0xd00103f0,
+       0x04bd0002,
+       0xf1021fb9,
+       0xf0a500e7,
+       0x21f441e3,
+       0x01fcf09d,
+       0xb6022cf0,
+       0xf2fd0124,
+       0x02ffb905,
+       0xa504e7f1,
+       0xf441e3f0,
+       0x21f59d21,
+       0x24bd026a,
+       0x47fc07f1,
+       0xd00203f0,
+       0x04bd0002,
+       0xb6012cf0,
+       0x07f10320,
+       0x03f04afc,
+       0x0002d002,
+       0xacf004bd,
+       0x06a5f001,
+       0x9800b7f0,
+       0x0d98000c,
+       0x00e7f001,
+       0x016f21f5,
+       0xf508a7f0,
+       0xf5011021,
+       0xf4025e21,
+       0xa7f01301,
+       0xd021f40c,
+       0xf505f7f0,
+       0xf4085e21,
+/* 0x0ada: ctx_xfer_post */
+       0xf7f02e02,
+       0xd721f502,
+       0xf5f4bd07,
+       0xf5083621,
+       0xf5027f21,
+       0xbd07e921,
+       0xd721f5f4,
+       0x1011f407,
+       0xfd400198,
+       0x0bf40511,
+       0xad21f507,
+/* 0x0b05: ctx_xfer_no_post_mmio */
+/* 0x0b05: ctx_xfer_done */
+       0x0000f809,
+       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,
+};
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/gr/fuc/hubgk110.fuc3 b/drivers/gpu/drm/nouveau/nvkm/engine/gr/fuc/hubgk110.fuc3
new file mode 100644 (file)
index 0000000..760b463
--- /dev/null
@@ -0,0 +1,40 @@
+/*
+ * Copyright 2013 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 <bskeggs@redhat.com>
+ */
+
+#define CHIPSET GK110
+#include "macros.fuc"
+
+.section #gk110_grhub_data
+#define INCLUDE_DATA
+#include "com.fuc"
+#include "hub.fuc"
+#undef INCLUDE_DATA
+
+.section #gk110_grhub_code
+#define INCLUDE_CODE
+bra #init
+#include "com.fuc"
+#include "hub.fuc"
+.align 256
+#undef INCLUDE_CODE
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/gr/fuc/hubgk110.fuc3.h b/drivers/gpu/drm/nouveau/nvkm/engine/gr/fuc/hubgk110.fuc3.h
new file mode 100644 (file)
index 0000000..8998687
--- /dev/null
@@ -0,0 +1,1044 @@
+uint32_t gk110_grhub_data[] = {
+/* 0x0000: hub_mmio_list_head */
+       0x00000300,
+/* 0x0004: hub_mmio_list_tail */
+       0x00000304,
+/* 0x0008: gpc_count */
+       0x00000000,
+/* 0x000c: rop_count */
+       0x00000000,
+/* 0x0010: cmd_queue */
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+/* 0x0058: ctx_current */
+       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,
+/* 0x0100: chan_data */
+/* 0x0100: chan_mmio_count */
+       0x00000000,
+/* 0x0104: chan_mmio_address */
+       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,
+/* 0x0200: xfer_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,
+/* 0x0300: hub_mmio_list_base */
+       0x0417e91c,
+};
+
+uint32_t gk110_grhub_code[] = {
+       0x039b0ef5,
+/* 0x0004: queue_put */
+       0x9800d898,
+       0x86f001d9,
+       0x0489b808,
+       0xf00c1bf4,
+       0x21f502f7,
+       0x00f8037e,
+/* 0x001c: queue_put_next */
+       0xb60798c4,
+       0x8dbb0384,
+       0x0880b600,
+       0x80008e80,
+       0x90b6018f,
+       0x0f94f001,
+       0xf801d980,
+/* 0x0039: queue_get */
+       0x0131f400,
+       0x9800d898,
+       0x89b801d9,
+       0x210bf404,
+       0xb60789c4,
+       0x9dbb0394,
+       0x0890b600,
+       0x98009e98,
+       0x80b6019f,
+       0x0f84f001,
+       0xf400d880,
+/* 0x0066: queue_get_done */
+       0x00f80132,
+/* 0x0068: nv_rd32 */
+       0xf002ecb9,
+       0x07f11fc9,
+       0x03f0ca00,
+       0x000cd001,
+/* 0x007a: nv_rd32_wait */
+       0xc7f104bd,
+       0xc3f0ca00,
+       0x00cccf01,
+       0xf41fccc8,
+       0xa7f0f31b,
+       0x1021f506,
+       0x00f7f101,
+       0x01f3f0cb,
+       0xf800ffcf,
+/* 0x009d: nv_wr32 */
+       0x0007f100,
+       0x0103f0cc,
+       0xbd000fd0,
+       0x02ecb904,
+       0xf01fc9f0,
+       0x07f11ec9,
+       0x03f0ca00,
+       0x000cd001,
+/* 0x00be: nv_wr32_wait */
+       0xc7f104bd,
+       0xc3f0ca00,
+       0x00cccf01,
+       0xf41fccc8,
+       0x00f8f31b,
+/* 0x00d0: wait_donez */
+       0x99f094bd,
+       0x0007f100,
+       0x0203f037,
+       0xbd0009d0,
+       0x0007f104,
+       0x0203f006,
+       0xbd000ad0,
+/* 0x00ed: wait_donez_ne */
+       0x0087f104,
+       0x0183f000,
+       0xff0088cf,
+       0x1bf4888a,
+       0xf094bdf3,
+       0x07f10099,
+       0x03f01700,
+       0x0009d002,
+       0x00f804bd,
+/* 0x0110: wait_doneo */
+       0x99f094bd,
+       0x0007f100,
+       0x0203f037,
+       0xbd0009d0,
+       0x0007f104,
+       0x0203f006,
+       0xbd000ad0,
+/* 0x012d: wait_doneo_e */
+       0x0087f104,
+       0x0183f000,
+       0xff0088cf,
+       0x0bf4888a,
+       0xf094bdf3,
+       0x07f10099,
+       0x03f01700,
+       0x0009d002,
+       0x00f804bd,
+/* 0x0150: mmctx_size */
+/* 0x0152: nv_mmctx_size_loop */
+       0xe89894bd,
+       0x1a85b600,
+       0xb60180b6,
+       0x98bb0284,
+       0x04e0b600,
+       0xf404efb8,
+       0x9fb9eb1b,
+/* 0x016f: mmctx_xfer */
+       0xbd00f802,
+       0x0199f094,
+       0x370007f1,
+       0xd00203f0,
+       0x04bd0009,
+       0xbbfd94bd,
+       0x120bf405,
+       0xc40007f1,
+       0xd00103f0,
+       0x04bd000b,
+/* 0x0197: mmctx_base_disabled */
+       0xfd0099f0,
+       0x0bf405ee,
+       0x0007f11e,
+       0x0103f0c6,
+       0xbd000ed0,
+       0x0007f104,
+       0x0103f0c7,
+       0xbd000fd0,
+       0x0199f004,
+/* 0x01b8: mmctx_multi_disabled */
+       0xb600abc8,
+       0xb9f010b4,
+       0x01aec80c,
+       0xfd11e4b6,
+       0x07f105be,
+       0x03f0c500,
+       0x000bd001,
+/* 0x01d6: mmctx_exec_loop */
+/* 0x01d6: mmctx_wait_free */
+       0xe7f104bd,
+       0xe3f0c500,
+       0x00eecf01,
+       0xf41fe4f0,
+       0xce98f30b,
+       0x05e9fd00,
+       0xc80007f1,
+       0xd00103f0,
+       0x04bd000e,
+       0xb804c0b6,
+       0x1bf404cd,
+       0x02abc8d8,
+/* 0x0207: mmctx_fini_wait */
+       0xf11f1bf4,
+       0xf0c500b7,
+       0xbbcf01b3,
+       0x1fb4f000,
+       0xf410b4b0,
+       0xa7f0f01b,
+       0xd021f405,
+/* 0x0223: mmctx_stop */
+       0xc82b0ef4,
+       0xb4b600ab,
+       0x0cb9f010,
+       0xf112b9f0,
+       0xf0c50007,
+       0x0bd00103,
+/* 0x023b: mmctx_stop_wait */
+       0xf104bd00,
+       0xf0c500b7,
+       0xbbcf01b3,
+       0x12bbc800,
+/* 0x024b: mmctx_done */
+       0xbdf31bf4,
+       0x0199f094,
+       0x170007f1,
+       0xd00203f0,
+       0x04bd0009,
+/* 0x025e: strand_wait */
+       0xa0f900f8,
+       0xf402a7f0,
+       0xa0fcd021,
+/* 0x026a: strand_pre */
+       0x97f000f8,
+       0xfc07f10c,
+       0x0203f04a,
+       0xbd0009d0,
+       0x5e21f504,
+/* 0x027f: strand_post */
+       0xf000f802,
+       0x07f10d97,
+       0x03f04afc,
+       0x0009d002,
+       0x21f504bd,
+       0x00f8025e,
+/* 0x0294: strand_set */
+       0xf10fc7f0,
+       0xf04ffc07,
+       0x0cd00203,
+       0xf004bd00,
+       0x07f10bc7,
+       0x03f04afc,
+       0x000cd002,
+       0x07f104bd,
+       0x03f04ffc,
+       0x000ed002,
+       0xc7f004bd,
+       0xfc07f10a,
+       0x0203f04a,
+       0xbd000cd0,
+       0x5e21f504,
+/* 0x02d3: strand_ctx_init */
+       0xbd00f802,
+       0x0399f094,
+       0x370007f1,
+       0xd00203f0,
+       0x04bd0009,
+       0x026a21f5,
+       0xf503e7f0,
+       0xbd029421,
+       0xfc07f1c4,
+       0x0203f047,
+       0xbd000cd0,
+       0x01c7f004,
+       0x4afc07f1,
+       0xd00203f0,
+       0x04bd000c,
+       0x025e21f5,
+       0xf1010c92,
+       0xf046fc07,
+       0x0cd00203,
+       0xf004bd00,
+       0x07f102c7,
+       0x03f04afc,
+       0x000cd002,
+       0x21f504bd,
+       0x21f5025e,
+       0x87f1027f,
+       0x83f04200,
+       0x0097f102,
+       0x0293f020,
+       0x950099cf,
+/* 0x034a: ctx_init_strand_loop */
+       0x8ed008fe,
+       0x408ed000,
+       0xb6808acf,
+       0xa0b606a5,
+       0x00eabb01,
+       0xb60480b6,
+       0x1bf40192,
+       0x08e4b6e8,
+       0xbdf2efbc,
+       0x0399f094,
+       0x170007f1,
+       0xd00203f0,
+       0x04bd0009,
+/* 0x037e: error */
+       0x07f100f8,
+       0x03f00500,
+       0x000fd002,
+       0xf7f004bd,
+       0x0007f101,
+       0x0303f007,
+       0xbd000fd0,
+/* 0x039b: init */
+       0xbd00f804,
+       0x0007fe04,
+       0x420017f1,
+       0xcf0013f0,
+       0x11e70011,
+       0x14b60109,
+       0x0014fe08,
+       0xf10227f0,
+       0xf0120007,
+       0x02d00003,
+       0xf104bd00,
+       0xfe06c817,
+       0x24bd0010,
+       0x070007f1,
+       0xd00003f0,
+       0x04bd0002,
+       0x200327f1,
+       0x010007f1,
+       0xd00103f0,
+       0x04bd0002,
+       0x200427f1,
+       0x010407f1,
+       0xd00103f0,
+       0x04bd0002,
+       0x200b27f1,
+       0x010807f1,
+       0xd00103f0,
+       0x04bd0002,
+       0x200c27f1,
+       0x011c07f1,
+       0xd00103f0,
+       0x04bd0002,
+       0xf1010392,
+       0xf0090007,
+       0x03d00303,
+       0xf104bd00,
+       0xf0870427,
+       0x07f10023,
+       0x03f00400,
+       0x0002d000,
+       0x27f004bd,
+       0x0007f104,
+       0x0003f003,
+       0xbd0002d0,
+       0x1031f404,
+       0x9604e7f1,
+       0xf440e3f0,
+       0xfeb96821,
+       0x90f1c702,
+       0xf0030180,
+       0x0f801ff4,
+       0x0117f002,
+       0xb6041fbb,
+       0x07f10112,
+       0x03f00300,
+       0x0001d001,
+       0x07f104bd,
+       0x03f00400,
+       0x0001d001,
+       0x17f104bd,
+       0xf7f00100,
+       0xd721f502,
+       0xe921f507,
+       0x10f7f007,
+       0x083621f5,
+       0x98000e98,
+       0x21f5010f,
+       0x14950150,
+       0x0007f108,
+       0x0103f0c0,
+       0xbd0004d0,
+       0x0007f104,
+       0x0103f0c1,
+       0xbd0004d0,
+       0x0030b704,
+       0x001fbb13,
+       0xf102f5b6,
+       0xf0d30007,
+       0x0fd00103,
+       0xb604bd00,
+       0x10b60815,
+       0x0814b601,
+       0xf5021fb9,
+       0xbb02d321,
+       0x0398001f,
+       0x0047f102,
+       0x5043f020,
+/* 0x04f4: init_gpc */
+       0x08044ea0,
+       0xf4021fb9,
+       0x4ea09d21,
+       0xf4bd010c,
+       0xa09d21f4,
+       0xf401044e,
+       0x4ea09d21,
+       0xf7f00100,
+       0x9d21f402,
+       0x08004ea0,
+/* 0x051c: init_gpc_wait */
+       0xc86821f4,
+       0x0bf41fff,
+       0x044ea0fa,
+       0x6821f408,
+       0xb7001fbb,
+       0xb6800040,
+       0x1bf40132,
+       0x00f7f0be,
+       0x083621f5,
+       0xf500f7f0,
+       0xf107d721,
+       0xf0010007,
+       0x01d00203,
+       0xbd04bd00,
+       0x1f19f014,
+       0x300007f1,
+       0xd00203f0,
+       0x04bd0001,
+/* 0x0564: main */
+       0xf40031f4,
+       0xd7f00028,
+       0x3921f410,
+       0xb1f401f4,
+       0xf54001e4,
+       0xbd00e91b,
+       0x0499f094,
+       0x370007f1,
+       0xd00203f0,
+       0x04bd0009,
+       0xc00017f1,
+       0xcf0213f0,
+       0x27f10011,
+       0x23f0c100,
+       0x0022cf02,
+       0xf51f13c8,
+       0xc800890b,
+       0x0bf41f23,
+       0xb920f962,
+       0x94bd0212,
+       0xf10799f0,
+       0xf0370007,
+       0x09d00203,
+       0xf404bd00,
+       0x31f40132,
+       0x0221f502,
+       0xf094bd0a,
+       0x07f10799,
+       0x03f01700,
+       0x0009d002,
+       0x20fc04bd,
+       0x99f094bd,
+       0x0007f106,
+       0x0203f037,
+       0xbd0009d0,
+       0x0131f404,
+       0x0a0221f5,
+       0x99f094bd,
+       0x0007f106,
+       0x0203f017,
+       0xbd0009d0,
+       0x330ef404,
+/* 0x060c: chsw_prev_no_next */
+       0x12b920f9,
+       0x0132f402,
+       0xf50232f4,
+       0xfc0a0221,
+       0x0007f120,
+       0x0203f0c0,
+       0xbd0002d0,
+       0x130ef404,
+/* 0x062c: chsw_no_prev */
+       0xf41f23c8,
+       0x31f40d0b,
+       0x0232f401,
+       0x0a0221f5,
+/* 0x063c: chsw_done */
+       0xf10127f0,
+       0xf0c30007,
+       0x02d00203,
+       0xbd04bd00,
+       0x0499f094,
+       0x170007f1,
+       0xd00203f0,
+       0x04bd0009,
+       0xff080ef5,
+/* 0x0660: main_not_ctx_switch */
+       0xf401e4b0,
+       0xf2b90d1b,
+       0x9a21f502,
+       0x460ef409,
+/* 0x0670: main_not_ctx_chan */
+       0xf402e4b0,
+       0x94bd321b,
+       0xf10799f0,
+       0xf0370007,
+       0x09d00203,
+       0xf404bd00,
+       0x32f40132,
+       0x0221f502,
+       0xf094bd0a,
+       0x07f10799,
+       0x03f01700,
+       0x0009d002,
+       0x0ef404bd,
+/* 0x06a5: main_not_ctx_save */
+       0x10ef9411,
+       0xf501f5f0,
+       0xf5037e21,
+/* 0x06b3: main_done */
+       0xbdfeb50e,
+       0x1f29f024,
+       0x300007f1,
+       0xd00203f0,
+       0x04bd0002,
+       0xfea00ef5,
+/* 0x06c8: ih */
+       0x88fe80f9,
+       0xf980f901,
+       0xf9a0f990,
+       0xf9d0f9b0,
+       0xbdf0f9e0,
+       0x00a7f104,
+       0x00a3f002,
+       0xc400aacf,
+       0x0bf404ab,
+       0x10d7f030,
+       0x1a00e7f1,
+       0xcf00e3f0,
+       0xf7f100ee,
+       0xf3f01900,
+       0x00ffcf00,
+       0xb70421f4,
+       0xf00400b0,
+       0x07f101e7,
+       0x03f01d00,
+       0x000ed000,
+/* 0x071a: ih_no_fifo */
+       0xabe404bd,
+       0x0bf40100,
+       0x10d7f00d,
+       0x4001e7f1,
+/* 0x072b: ih_no_ctxsw */
+       0xe40421f4,
+       0xf40400ab,
+       0xe7f16c0b,
+       0xe3f00708,
+       0x6821f440,
+       0xf102ffb9,
+       0xf0040007,
+       0x0fd00203,
+       0xf104bd00,
+       0xf00704e7,
+       0x21f440e3,
+       0x02ffb968,
+       0x030007f1,
+       0xd00203f0,
+       0x04bd000f,
+       0x9450fec7,
+       0xf7f102ee,
+       0xf3f00700,
+       0x00efbb40,
+       0xf16821f4,
+       0xf0020007,
+       0x0fd00203,
+       0xf004bd00,
+       0x21f503f7,
+       0xb7f1037e,
+       0xbfb90100,
+       0x44e7f102,
+       0x40e3f001,
+/* 0x079b: ih_no_fwmthd */
+       0xf19d21f4,
+       0xbd0504b7,
+       0xb4abffb0,
+       0xf10f0bf4,
+       0xf0070007,
+       0x0bd00303,
+/* 0x07b3: ih_no_other */
+       0xf104bd00,
+       0xf0010007,
+       0x0ad00003,
+       0xfc04bd00,
+       0xfce0fcf0,
+       0xfcb0fcd0,
+       0xfc90fca0,
+       0x0088fe80,
+       0x32f480fc,
+/* 0x07d7: ctx_4170s */
+       0xf001f800,
+       0xffb910f5,
+       0x70e7f102,
+       0x40e3f041,
+       0xf89d21f4,
+/* 0x07e9: ctx_4170w */
+       0x70e7f100,
+       0x40e3f041,
+       0xb96821f4,
+       0xf4f002ff,
+       0xf01bf410,
+/* 0x07fe: ctx_redswitch */
+       0xe7f100f8,
+       0xe5f00200,
+       0x20e5f040,
+       0xf110e5f0,
+       0xf0850007,
+       0x0ed00103,
+       0xf004bd00,
+/* 0x081a: ctx_redswitch_delay */
+       0xf2b608f7,
+       0xfd1bf401,
+       0x0400e5f1,
+       0x0100e5f1,
+       0x850007f1,
+       0xd00103f0,
+       0x04bd000e,
+/* 0x0836: ctx_86c */
+       0x07f100f8,
+       0x03f02300,
+       0x000fd002,
+       0xffb904bd,
+       0x14e7f102,
+       0x40e3f08a,
+       0xb99d21f4,
+       0xe7f102ff,
+       0xe3f0a88c,
+       0x9d21f441,
+/* 0x085e: ctx_mem */
+       0x07f100f8,
+       0x03f08400,
+       0x000fd002,
+/* 0x086a: ctx_mem_wait */
+       0xf7f104bd,
+       0xf3f08400,
+       0x00ffcf02,
+       0xf405fffd,
+       0x00f8f31b,
+/* 0x087c: ctx_load */
+       0x99f094bd,
+       0x0007f105,
+       0x0203f037,
+       0xbd0009d0,
+       0x0ca7f004,
+       0xbdd021f4,
+       0x0007f1f4,
+       0x0203f089,
+       0xbd000fd0,
+       0x0007f104,
+       0x0203f0c1,
+       0xbd0002d0,
+       0x0007f104,
+       0x0203f083,
+       0xbd0002d0,
+       0x07f7f004,
+       0x085e21f5,
+       0xc00007f1,
+       0xd00203f0,
+       0x04bd0002,
+       0xf0000bfe,
+       0x24b61f2a,
+       0x0220b604,
+       0x99f094bd,
+       0x0007f108,
+       0x0203f037,
+       0xbd0009d0,
+       0x0007f104,
+       0x0203f081,
+       0xbd0002d0,
+       0x0027f104,
+       0x0023f100,
+       0x0225f080,
+       0x880007f1,
+       0xd00203f0,
+       0x04bd0002,
+       0xf11017f0,
+       0xf0020027,
+       0x12fa0223,
+       0xbd03f805,
+       0x0899f094,
+       0x170007f1,
+       0xd00203f0,
+       0x04bd0009,
+       0xb6810198,
+       0x02981814,
+       0x0825b680,
+       0x800512fd,
+       0x94bd1601,
+       0xf10999f0,
+       0xf0370007,
+       0x09d00203,
+       0xf104bd00,
+       0xf0810007,
+       0x01d00203,
+       0xf004bd00,
+       0x07f10127,
+       0x03f08800,
+       0x0002d002,
+       0x17f104bd,
+       0x13f00100,
+       0x0501fa06,
+       0x94bd03f8,
+       0xf10999f0,
+       0xf0170007,
+       0x09d00203,
+       0xbd04bd00,
+       0x0599f094,
+       0x170007f1,
+       0xd00203f0,
+       0x04bd0009,
+/* 0x099a: ctx_chan */
+       0x21f500f8,
+       0xa7f0087c,
+       0xd021f40c,
+       0xf505f7f0,
+       0xf8085e21,
+/* 0x09ad: ctx_mmio_exec */
+       0x41039800,
+       0x810007f1,
+       0xd00203f0,
+       0x04bd0003,
+/* 0x09be: ctx_mmio_loop */
+       0x34c434bd,
+       0x0f1bf4ff,
+       0x020057f1,
+       0xfa0653f0,
+       0x03f80535,
+/* 0x09d0: ctx_mmio_pull */
+       0x98804e98,
+       0x21f4814f,
+       0x0830b69d,
+       0xf40112b6,
+/* 0x09e2: ctx_mmio_done */
+       0x0398df1b,
+       0x0007f116,
+       0x0203f081,
+       0xbd0003d0,
+       0x40008004,
+       0x010017f1,
+       0xfa0613f0,
+       0x03f80601,
+/* 0x0a02: ctx_xfer */
+       0xe7f000f8,
+       0x0007f104,
+       0x0303f002,
+       0xbd000ed0,
+/* 0x0a11: ctx_xfer_idle */
+       0x00e7f104,
+       0x03e3f000,
+       0xf100eecf,
+       0xf42000e4,
+       0x11f4f21b,
+       0x0d02f406,
+/* 0x0a28: ctx_xfer_pre */
+       0xf510f7f0,
+       0xf4083621,
+/* 0x0a32: ctx_xfer_pre_load */
+       0xf7f01c11,
+       0xd721f502,
+       0xe921f507,
+       0xfe21f507,
+       0xf5f4bd07,
+       0xf507d721,
+/* 0x0a4b: ctx_xfer_exec */
+       0x98087c21,
+       0x24bd1601,
+       0x050007f1,
+       0xd00103f0,
+       0x04bd0002,
+       0xf1021fb9,
+       0xf0a500e7,
+       0x21f441e3,
+       0x01fcf09d,
+       0xb6022cf0,
+       0xf2fd0124,
+       0x02ffb905,
+       0xa504e7f1,
+       0xf441e3f0,
+       0x21f59d21,
+       0x24bd026a,
+       0x47fc07f1,
+       0xd00203f0,
+       0x04bd0002,
+       0xb6012cf0,
+       0x07f10320,
+       0x03f04afc,
+       0x0002d002,
+       0xacf004bd,
+       0x06a5f001,
+       0x9800b7f0,
+       0x0d98000c,
+       0x00e7f001,
+       0x016f21f5,
+       0xf508a7f0,
+       0xf5011021,
+       0xf4025e21,
+       0xa7f01301,
+       0xd021f40c,
+       0xf505f7f0,
+       0xf4085e21,
+/* 0x0ada: ctx_xfer_post */
+       0xf7f02e02,
+       0xd721f502,
+       0xf5f4bd07,
+       0xf5083621,
+       0xf5027f21,
+       0xbd07e921,
+       0xd721f5f4,
+       0x1011f407,
+       0xfd400198,
+       0x0bf40511,
+       0xad21f507,
+/* 0x0b05: ctx_xfer_no_post_mmio */
+/* 0x0b05: ctx_xfer_done */
+       0x0000f809,
+       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,
+};
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/gr/fuc/hubgk208.fuc5 b/drivers/gpu/drm/nouveau/nvkm/engine/gr/fuc/hubgk208.fuc5
new file mode 100644 (file)
index 0000000..43243a3
--- /dev/null
@@ -0,0 +1,40 @@
+/*
+ * Copyright 2013 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 <bskeggs@redhat.com>
+ */
+
+#define CHIPSET GK208
+#include "macros.fuc"
+
+.section #gk208_grhub_data
+#define INCLUDE_DATA
+#include "com.fuc"
+#include "hub.fuc"
+#undef INCLUDE_DATA
+
+.section #gk208_grhub_code
+#define INCLUDE_CODE
+bra #init
+#include "com.fuc"
+#include "hub.fuc"
+.align 256
+#undef INCLUDE_CODE
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/gr/fuc/hubgk208.fuc5.h b/drivers/gpu/drm/nouveau/nvkm/engine/gr/fuc/hubgk208.fuc5.h
new file mode 100644 (file)
index 0000000..0e98fa4
--- /dev/null
@@ -0,0 +1,916 @@
+uint32_t gk208_grhub_data[] = {
+/* 0x0000: hub_mmio_list_head */
+       0x00000300,
+/* 0x0004: hub_mmio_list_tail */
+       0x00000304,
+/* 0x0008: gpc_count */
+       0x00000000,
+/* 0x000c: rop_count */
+       0x00000000,
+/* 0x0010: cmd_queue */
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+/* 0x0058: ctx_current */
+       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,
+/* 0x0100: chan_data */
+/* 0x0100: chan_mmio_count */
+       0x00000000,
+/* 0x0104: chan_mmio_address */
+       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,
+/* 0x0200: xfer_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,
+/* 0x0300: hub_mmio_list_base */
+       0x0417e91c,
+};
+
+uint32_t gk208_grhub_code[] = {
+       0x030e0ef5,
+/* 0x0004: queue_put */
+       0x9800d898,
+       0x86f001d9,
+       0xf489a408,
+       0x020f0b1b,
+       0x0002f87e,
+/* 0x001a: queue_put_next */
+       0x98c400f8,
+       0x0384b607,
+       0xb6008dbb,
+       0x8eb50880,
+       0x018fb500,
+       0xf00190b6,
+       0xd9b50f94,
+/* 0x0037: queue_get */
+       0xf400f801,
+       0xd8980131,
+       0x01d99800,
+       0x0bf489a4,
+       0x0789c421,
+       0xbb0394b6,
+       0x90b6009d,
+       0x009e9808,
+       0xb6019f98,
+       0x84f00180,
+       0x00d8b50f,
+/* 0x0063: queue_get_done */
+       0xf80132f4,
+/* 0x0065: nv_rd32 */
+       0xf0ecb200,
+       0x00801fc9,
+       0x0cf601ca,
+/* 0x0073: nv_rd32_wait */
+       0x8c04bd00,
+       0xcf01ca00,
+       0xccc800cc,
+       0xf61bf41f,
+       0xec7e060a,
+       0x008f0000,
+       0xffcf01cb,
+/* 0x008f: nv_wr32 */
+       0x8000f800,
+       0xf601cc00,
+       0x04bd000f,
+       0xc9f0ecb2,
+       0x1ec9f01f,
+       0x01ca0080,
+       0xbd000cf6,
+/* 0x00a9: nv_wr32_wait */
+       0xca008c04,
+       0x00cccf01,
+       0xf41fccc8,
+       0x00f8f61b,
+/* 0x00b8: wait_donez */
+       0x99f094bd,
+       0x37008000,
+       0x0009f602,
+       0x008004bd,
+       0x0af60206,
+/* 0x00cf: wait_donez_ne */
+       0x8804bd00,
+       0xcf010000,
+       0x8aff0088,
+       0xf61bf488,
+       0x99f094bd,
+       0x17008000,
+       0x0009f602,
+       0x00f804bd,
+/* 0x00ec: wait_doneo */
+       0x99f094bd,
+       0x37008000,
+       0x0009f602,
+       0x008004bd,
+       0x0af60206,
+/* 0x0103: wait_doneo_e */
+       0x8804bd00,
+       0xcf010000,
+       0x8aff0088,
+       0xf60bf488,
+       0x99f094bd,
+       0x17008000,
+       0x0009f602,
+       0x00f804bd,
+/* 0x0120: mmctx_size */
+/* 0x0122: nv_mmctx_size_loop */
+       0xe89894bd,
+       0x1a85b600,
+       0xb60180b6,
+       0x98bb0284,
+       0x04e0b600,
+       0x1bf4efa4,
+       0xf89fb2ec,
+/* 0x013d: mmctx_xfer */
+       0xf094bd00,
+       0x00800199,
+       0x09f60237,
+       0xbd04bd00,
+       0x05bbfd94,
+       0x800f0bf4,
+       0xf601c400,
+       0x04bd000b,
+/* 0x015f: mmctx_base_disabled */
+       0xfd0099f0,
+       0x0bf405ee,
+       0xc6008018,
+       0x000ef601,
+       0x008004bd,
+       0x0ff601c7,
+       0xf004bd00,
+/* 0x017a: mmctx_multi_disabled */
+       0xabc80199,
+       0x10b4b600,
+       0xc80cb9f0,
+       0xe4b601ae,
+       0x05befd11,
+       0x01c50080,
+       0xbd000bf6,
+/* 0x0195: mmctx_exec_loop */
+/* 0x0195: mmctx_wait_free */
+       0xc5008e04,
+       0x00eecf01,
+       0xf41fe4f0,
+       0xce98f60b,
+       0x05e9fd00,
+       0x01c80080,
+       0xbd000ef6,
+       0x04c0b604,
+       0x1bf4cda4,
+       0x02abc8df,
+/* 0x01bf: mmctx_fini_wait */
+       0x8b1c1bf4,
+       0xcf01c500,
+       0xb4f000bb,
+       0x10b4b01f,
+       0x0af31bf4,
+       0x00b87e05,
+       0x250ef400,
+/* 0x01d8: mmctx_stop */
+       0xb600abc8,
+       0xb9f010b4,
+       0x12b9f00c,
+       0x01c50080,
+       0xbd000bf6,
+/* 0x01ed: mmctx_stop_wait */
+       0xc5008b04,
+       0x00bbcf01,
+       0xf412bbc8,
+/* 0x01fa: mmctx_done */
+       0x94bdf61b,
+       0x800199f0,
+       0xf6021700,
+       0x04bd0009,
+/* 0x020a: strand_wait */
+       0xa0f900f8,
+       0xb87e020a,
+       0xa0fc0000,
+/* 0x0216: strand_pre */
+       0x0c0900f8,
+       0x024afc80,
+       0xbd0009f6,
+       0x020a7e04,
+/* 0x0227: strand_post */
+       0x0900f800,
+       0x4afc800d,
+       0x0009f602,
+       0x0a7e04bd,
+       0x00f80002,
+/* 0x0238: strand_set */
+       0xfc800f0c,
+       0x0cf6024f,
+       0x0c04bd00,
+       0x4afc800b,
+       0x000cf602,
+       0xfc8004bd,
+       0x0ef6024f,
+       0x0c04bd00,
+       0x4afc800a,
+       0x000cf602,
+       0x0a7e04bd,
+       0x00f80002,
+/* 0x0268: strand_ctx_init */
+       0x99f094bd,
+       0x37008003,
+       0x0009f602,
+       0x167e04bd,
+       0x030e0002,
+       0x0002387e,
+       0xfc80c4bd,
+       0x0cf60247,
+       0x0c04bd00,
+       0x4afc8001,
+       0x000cf602,
+       0x0a7e04bd,
+       0x0c920002,
+       0x46fc8001,
+       0x000cf602,
+       0x020c04bd,
+       0x024afc80,
+       0xbd000cf6,
+       0x020a7e04,
+       0x02277e00,
+       0x42008800,
+       0x20008902,
+       0x0099cf02,
+/* 0x02c7: ctx_init_strand_loop */
+       0xf608fe95,
+       0x8ef6008e,
+       0x808acf40,
+       0xb606a5b6,
+       0xeabb01a0,
+       0x0480b600,
+       0xf40192b6,
+       0xe4b6e81b,
+       0xf2efbc08,
+       0x99f094bd,
+       0x17008003,
+       0x0009f602,
+       0x00f804bd,
+/* 0x02f8: error */
+       0x02050080,
+       0xbd000ff6,
+       0x80010f04,
+       0xf6030700,
+       0x04bd000f,
+/* 0x030e: init */
+       0x04bd00f8,
+       0x410007fe,
+       0x11cf4200,
+       0x0911e700,
+       0x0814b601,
+       0x020014fe,
+       0x12004002,
+       0xbd0002f6,
+       0x05c94104,
+       0xbd0010fe,
+       0x07004024,
+       0xbd0002f6,
+       0x20034204,
+       0x01010080,
+       0xbd0002f6,
+       0x20044204,
+       0x01010480,
+       0xbd0002f6,
+       0x200b4204,
+       0x01010880,
+       0xbd0002f6,
+       0x200c4204,
+       0x01011c80,
+       0xbd0002f6,
+       0x01039204,
+       0x03090080,
+       0xbd0003f6,
+       0x87044204,
+       0xf6040040,
+       0x04bd0002,
+       0x00400402,
+       0x0002f603,
+       0x31f404bd,
+       0x96048e10,
+       0x00657e40,
+       0xc7feb200,
+       0x01b590f1,
+       0x1ff4f003,
+       0x01020fb5,
+       0x041fbb01,
+       0x800112b6,
+       0xf6010300,
+       0x04bd0001,
+       0x01040080,
+       0xbd0001f6,
+       0x01004104,
+       0xa87e020f,
+       0xb77e0006,
+       0x100f0006,
+       0x0006f97e,
+       0x98000e98,
+       0x207e010f,
+       0x14950001,
+       0xc0008008,
+       0x0004f601,
+       0x008004bd,
+       0x04f601c1,
+       0xb704bd00,
+       0xbb130030,
+       0xf5b6001f,
+       0xd3008002,
+       0x000ff601,
+       0x15b604bd,
+       0x0110b608,
+       0xb20814b6,
+       0x02687e1f,
+       0x001fbb00,
+       0x84020398,
+/* 0x041f: init_gpc */
+       0xb8502000,
+       0x0008044e,
+       0x8f7e1fb2,
+       0x4eb80000,
+       0xbd00010c,
+       0x008f7ef4,
+       0x044eb800,
+       0x8f7e0001,
+       0x4eb80000,
+       0x0f000100,
+       0x008f7e02,
+       0x004eb800,
+/* 0x044e: init_gpc_wait */
+       0x657e0008,
+       0xffc80000,
+       0xf90bf41f,
+       0x08044eb8,
+       0x00657e00,
+       0x001fbb00,
+       0x800040b7,
+       0xf40132b6,
+       0x000fb41b,
+       0x0006f97e,
+       0xa87e000f,
+       0x00800006,
+       0x01f60201,
+       0xbd04bd00,
+       0x1f19f014,
+       0x02300080,
+       0xbd0001f6,
+/* 0x0491: main */
+       0x0031f404,
+       0x0d0028f4,
+       0x00377e10,
+       0xf401f400,
+       0x4001e4b1,
+       0x00c71bf5,
+       0x99f094bd,
+       0x37008004,
+       0x0009f602,
+       0x008104bd,
+       0x11cf02c0,
+       0xc1008200,
+       0x0022cf02,
+       0xf41f13c8,
+       0x23c8770b,
+       0x550bf41f,
+       0x12b220f9,
+       0x99f094bd,
+       0x37008007,
+       0x0009f602,
+       0x32f404bd,
+       0x0231f401,
+       0x00087c7e,
+       0x99f094bd,
+       0x17008007,
+       0x0009f602,
+       0x20fc04bd,
+       0x99f094bd,
+       0x37008006,
+       0x0009f602,
+       0x31f404bd,
+       0x087c7e01,
+       0xf094bd00,
+       0x00800699,
+       0x09f60217,
+       0xf404bd00,
+/* 0x0522: chsw_prev_no_next */
+       0x20f92f0e,
+       0x32f412b2,
+       0x0232f401,
+       0x00087c7e,
+       0x008020fc,
+       0x02f602c0,
+       0xf404bd00,
+/* 0x053e: chsw_no_prev */
+       0x23c8130e,
+       0x0d0bf41f,
+       0xf40131f4,
+       0x7c7e0232,
+/* 0x054e: chsw_done */
+       0x01020008,
+       0x02c30080,
+       0xbd0002f6,
+       0xf094bd04,
+       0x00800499,
+       0x09f60217,
+       0xf504bd00,
+/* 0x056b: main_not_ctx_switch */
+       0xb0ff2a0e,
+       0x1bf401e4,
+       0x7ef2b20c,
+       0xf400081c,
+/* 0x057a: main_not_ctx_chan */
+       0xe4b0400e,
+       0x2c1bf402,
+       0x99f094bd,
+       0x37008007,
+       0x0009f602,
+       0x32f404bd,
+       0x0232f401,
+       0x00087c7e,
+       0x99f094bd,
+       0x17008007,
+       0x0009f602,
+       0x0ef404bd,
+/* 0x05a9: main_not_ctx_save */
+       0x10ef9411,
+       0x7e01f5f0,
+       0xf50002f8,
+/* 0x05b7: main_done */
+       0xbdfede0e,
+       0x1f29f024,
+       0x02300080,
+       0xbd0002f6,
+       0xcc0ef504,
+/* 0x05c9: ih */
+       0xfe80f9fe,
+       0x80f90188,
+       0xa0f990f9,
+       0xd0f9b0f9,
+       0xf0f9e0f9,
+       0x004a04bd,
+       0x00aacf02,
+       0xf404abc4,
+       0x100d230b,
+       0xcf1a004e,
+       0x004f00ee,
+       0x00ffcf19,
+       0x0000047e,
+       0x0400b0b7,
+       0x0040010e,
+       0x000ef61d,
+/* 0x060a: ih_no_fifo */
+       0xabe404bd,
+       0x0bf40100,
+       0x4e100d0c,
+       0x047e4001,
+/* 0x061a: ih_no_ctxsw */
+       0xabe40000,
+       0x0bf40400,
+       0x07088e56,
+       0x00657e40,
+       0x80ffb200,
+       0xf6020400,
+       0x04bd000f,
+       0x4007048e,
+       0x0000657e,
+       0x0080ffb2,
+       0x0ff60203,
+       0xc704bd00,
+       0xee9450fe,
+       0x07008f02,
+       0x00efbb40,
+       0x0000657e,
+       0x02020080,
+       0xbd000ff6,
+       0x7e030f04,
+       0x4b0002f8,
+       0xbfb20100,
+       0x4001448e,
+       0x00008f7e,
+/* 0x0674: ih_no_fwmthd */
+       0xbd05044b,
+       0xb4abffb0,
+       0x800c0bf4,
+       0xf6030700,
+       0x04bd000b,
+/* 0x0688: ih_no_other */
+       0xf6010040,
+       0x04bd000a,
+       0xe0fcf0fc,
+       0xb0fcd0fc,
+       0x90fca0fc,
+       0x88fe80fc,
+       0xf480fc00,
+       0x01f80032,
+/* 0x06a8: ctx_4170s */
+       0xb210f5f0,
+       0x41708eff,
+       0x008f7e40,
+/* 0x06b7: ctx_4170w */
+       0x8e00f800,
+       0x7e404170,
+       0xb2000065,
+       0x10f4f0ff,
+       0xf8f31bf4,
+/* 0x06c9: ctx_redswitch */
+       0x02004e00,
+       0xf040e5f0,
+       0xe5f020e5,
+       0x85008010,
+       0x000ef601,
+       0x080f04bd,
+/* 0x06e0: ctx_redswitch_delay */
+       0xf401f2b6,
+       0xe5f1fd1b,
+       0xe5f10400,
+       0x00800100,
+       0x0ef60185,
+       0xf804bd00,
+/* 0x06f9: ctx_86c */
+       0x23008000,
+       0x000ff602,
+       0xffb204bd,
+       0x408a148e,
+       0x00008f7e,
+       0x8c8effb2,
+       0x8f7e41a8,
+       0x00f80000,
+/* 0x0718: ctx_mem */
+       0x02840080,
+       0xbd000ff6,
+/* 0x0721: ctx_mem_wait */
+       0x84008f04,
+       0x00ffcf02,
+       0xf405fffd,
+       0x00f8f61b,
+/* 0x0730: ctx_load */
+       0x99f094bd,
+       0x37008005,
+       0x0009f602,
+       0x0c0a04bd,
+       0x0000b87e,
+       0x0080f4bd,
+       0x0ff60289,
+       0x8004bd00,
+       0xf602c100,
+       0x04bd0002,
+       0x02830080,
+       0xbd0002f6,
+       0x7e070f04,
+       0x80000718,
+       0xf602c000,
+       0x04bd0002,
+       0xf0000bfe,
+       0x24b61f2a,
+       0x0220b604,
+       0x99f094bd,
+       0x37008008,
+       0x0009f602,
+       0x008004bd,
+       0x02f60281,
+       0xd204bd00,
+       0x80000000,
+       0x800225f0,
+       0xf6028800,
+       0x04bd0002,
+       0x00421001,
+       0x0223f002,
+       0xf80512fa,
+       0xf094bd03,
+       0x00800899,
+       0x09f60217,
+       0x9804bd00,
+       0x14b68101,
+       0x80029818,
+       0xfd0825b6,
+       0x01b50512,
+       0xf094bd16,
+       0x00800999,
+       0x09f60237,
+       0x8004bd00,
+       0xf6028100,
+       0x04bd0001,
+       0x00800102,
+       0x02f60288,
+       0x4104bd00,
+       0x13f00100,
+       0x0501fa06,
+       0x94bd03f8,
+       0x800999f0,
+       0xf6021700,
+       0x04bd0009,
+       0x99f094bd,
+       0x17008005,
+       0x0009f602,
+       0x00f804bd,
+/* 0x081c: ctx_chan */
+       0x0007307e,
+       0xb87e0c0a,
+       0x050f0000,
+       0x0007187e,
+/* 0x082e: ctx_mmio_exec */
+       0x039800f8,
+       0x81008041,
+       0x0003f602,
+       0x34bd04bd,
+/* 0x083c: ctx_mmio_loop */
+       0xf4ff34c4,
+       0x00450e1b,
+       0x0653f002,
+       0xf80535fa,
+/* 0x084d: ctx_mmio_pull */
+       0x804e9803,
+       0x7e814f98,
+       0xb600008f,
+       0x12b60830,
+       0xdf1bf401,
+/* 0x0860: ctx_mmio_done */
+       0x80160398,
+       0xf6028100,
+       0x04bd0003,
+       0x414000b5,
+       0x13f00100,
+       0x0601fa06,
+       0x00f803f8,
+/* 0x087c: ctx_xfer */
+       0x0080040e,
+       0x0ef60302,
+/* 0x0887: ctx_xfer_idle */
+       0x8e04bd00,
+       0xcf030000,
+       0xe4f100ee,
+       0x1bf42000,
+       0x0611f4f5,
+/* 0x089b: ctx_xfer_pre */
+       0x0f0c02f4,
+       0x06f97e10,
+       0x1b11f400,
+/* 0x08a4: ctx_xfer_pre_load */
+       0xa87e020f,
+       0xb77e0006,
+       0xc97e0006,
+       0xf4bd0006,
+       0x0006a87e,
+       0x0007307e,
+/* 0x08bc: ctx_xfer_exec */
+       0xbd160198,
+       0x05008024,
+       0x0002f601,
+       0x1fb204bd,
+       0x41a5008e,
+       0x00008f7e,
+       0xf001fcf0,
+       0x24b6022c,
+       0x05f2fd01,
+       0x048effb2,
+       0x8f7e41a5,
+       0x167e0000,
+       0x24bd0002,
+       0x0247fc80,
+       0xbd0002f6,
+       0x012cf004,
+       0x800320b6,
+       0xf6024afc,
+       0x04bd0002,
+       0xf001acf0,
+       0x000b06a5,
+       0x98000c98,
+       0x000e010d,
+       0x00013d7e,
+       0xec7e080a,
+       0x0a7e0000,
+       0x01f40002,
+       0x7e0c0a12,
+       0x0f0000b8,
+       0x07187e05,
+       0x2d02f400,
+/* 0x0938: ctx_xfer_post */
+       0xa87e020f,
+       0xf4bd0006,
+       0x0006f97e,
+       0x0002277e,
+       0x0006b77e,
+       0xa87ef4bd,
+       0x11f40006,
+       0x40019810,
+       0xf40511fd,
+       0x2e7e070b,
+/* 0x0962: ctx_xfer_no_post_mmio */
+/* 0x0962: ctx_xfer_done */
+       0x00f80008,
+       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/drivers/gpu/drm/nouveau/nvkm/engine/gr/fuc/hubgm107.fuc5 b/drivers/gpu/drm/nouveau/nvkm/engine/gr/fuc/hubgm107.fuc5
new file mode 100644 (file)
index 0000000..27591b3
--- /dev/null
@@ -0,0 +1,40 @@
+/*
+ * Copyright 2013 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 <bskeggs@redhat.com>
+ */
+
+#define CHIPSET GK208
+#include "macros.fuc"
+
+.section #gm107_grhub_data
+#define INCLUDE_DATA
+#include "com.fuc"
+#include "hub.fuc"
+#undef INCLUDE_DATA
+
+.section #gm107_grhub_code
+#define INCLUDE_CODE
+bra #init
+#include "com.fuc"
+#include "hub.fuc"
+.align 256
+#undef INCLUDE_CODE
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/gr/fuc/hubgm107.fuc5.h b/drivers/gpu/drm/nouveau/nvkm/engine/gr/fuc/hubgm107.fuc5.h
new file mode 100644 (file)
index 0000000..5f953c5
--- /dev/null
@@ -0,0 +1,916 @@
+uint32_t gm107_grhub_data[] = {
+/* 0x0000: hub_mmio_list_head */
+       0x00000300,
+/* 0x0004: hub_mmio_list_tail */
+       0x00000304,
+/* 0x0008: gpc_count */
+       0x00000000,
+/* 0x000c: rop_count */
+       0x00000000,
+/* 0x0010: cmd_queue */
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+/* 0x0058: ctx_current */
+       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,
+/* 0x0100: chan_data */
+/* 0x0100: chan_mmio_count */
+       0x00000000,
+/* 0x0104: chan_mmio_address */
+       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,
+/* 0x0200: xfer_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,
+/* 0x0300: hub_mmio_list_base */
+       0x0417e91c,
+};
+
+uint32_t gm107_grhub_code[] = {
+       0x030e0ef5,
+/* 0x0004: queue_put */
+       0x9800d898,
+       0x86f001d9,
+       0xf489a408,
+       0x020f0b1b,
+       0x0002f87e,
+/* 0x001a: queue_put_next */
+       0x98c400f8,
+       0x0384b607,
+       0xb6008dbb,
+       0x8eb50880,
+       0x018fb500,
+       0xf00190b6,
+       0xd9b50f94,
+/* 0x0037: queue_get */
+       0xf400f801,
+       0xd8980131,
+       0x01d99800,
+       0x0bf489a4,
+       0x0789c421,
+       0xbb0394b6,
+       0x90b6009d,
+       0x009e9808,
+       0xb6019f98,
+       0x84f00180,
+       0x00d8b50f,
+/* 0x0063: queue_get_done */
+       0xf80132f4,
+/* 0x0065: nv_rd32 */
+       0xf0ecb200,
+       0x00801fc9,
+       0x0cf601ca,
+/* 0x0073: nv_rd32_wait */
+       0x8c04bd00,
+       0xcf01ca00,
+       0xccc800cc,
+       0xf61bf41f,
+       0xec7e060a,
+       0x008f0000,
+       0xffcf01cb,
+/* 0x008f: nv_wr32 */
+       0x8000f800,
+       0xf601cc00,
+       0x04bd000f,
+       0xc9f0ecb2,
+       0x1ec9f01f,
+       0x01ca0080,
+       0xbd000cf6,
+/* 0x00a9: nv_wr32_wait */
+       0xca008c04,
+       0x00cccf01,
+       0xf41fccc8,
+       0x00f8f61b,
+/* 0x00b8: wait_donez */
+       0x99f094bd,
+       0x37008000,
+       0x0009f602,
+       0x008004bd,
+       0x0af60206,
+/* 0x00cf: wait_donez_ne */
+       0x8804bd00,
+       0xcf010000,
+       0x8aff0088,
+       0xf61bf488,
+       0x99f094bd,
+       0x17008000,
+       0x0009f602,
+       0x00f804bd,
+/* 0x00ec: wait_doneo */
+       0x99f094bd,
+       0x37008000,
+       0x0009f602,
+       0x008004bd,
+       0x0af60206,
+/* 0x0103: wait_doneo_e */
+       0x8804bd00,
+       0xcf010000,
+       0x8aff0088,
+       0xf60bf488,
+       0x99f094bd,
+       0x17008000,
+       0x0009f602,
+       0x00f804bd,
+/* 0x0120: mmctx_size */
+/* 0x0122: nv_mmctx_size_loop */
+       0xe89894bd,
+       0x1a85b600,
+       0xb60180b6,
+       0x98bb0284,
+       0x04e0b600,
+       0x1bf4efa4,
+       0xf89fb2ec,
+/* 0x013d: mmctx_xfer */
+       0xf094bd00,
+       0x00800199,
+       0x09f60237,
+       0xbd04bd00,
+       0x05bbfd94,
+       0x800f0bf4,
+       0xf601c400,
+       0x04bd000b,
+/* 0x015f: mmctx_base_disabled */
+       0xfd0099f0,
+       0x0bf405ee,
+       0xc6008018,
+       0x000ef601,
+       0x008004bd,
+       0x0ff601c7,
+       0xf004bd00,
+/* 0x017a: mmctx_multi_disabled */
+       0xabc80199,
+       0x10b4b600,
+       0xc80cb9f0,
+       0xe4b601ae,
+       0x05befd11,
+       0x01c50080,
+       0xbd000bf6,
+/* 0x0195: mmctx_exec_loop */
+/* 0x0195: mmctx_wait_free */
+       0xc5008e04,
+       0x00eecf01,
+       0xf41fe4f0,
+       0xce98f60b,
+       0x05e9fd00,
+       0x01c80080,
+       0xbd000ef6,
+       0x04c0b604,
+       0x1bf4cda4,
+       0x02abc8df,
+/* 0x01bf: mmctx_fini_wait */
+       0x8b1c1bf4,
+       0xcf01c500,
+       0xb4f000bb,
+       0x10b4b01f,
+       0x0af31bf4,
+       0x00b87e05,
+       0x250ef400,
+/* 0x01d8: mmctx_stop */
+       0xb600abc8,
+       0xb9f010b4,
+       0x12b9f00c,
+       0x01c50080,
+       0xbd000bf6,
+/* 0x01ed: mmctx_stop_wait */
+       0xc5008b04,
+       0x00bbcf01,
+       0xf412bbc8,
+/* 0x01fa: mmctx_done */
+       0x94bdf61b,
+       0x800199f0,
+       0xf6021700,
+       0x04bd0009,
+/* 0x020a: strand_wait */
+       0xa0f900f8,
+       0xb87e020a,
+       0xa0fc0000,
+/* 0x0216: strand_pre */
+       0x0c0900f8,
+       0x024afc80,
+       0xbd0009f6,
+       0x020a7e04,
+/* 0x0227: strand_post */
+       0x0900f800,
+       0x4afc800d,
+       0x0009f602,
+       0x0a7e04bd,
+       0x00f80002,
+/* 0x0238: strand_set */
+       0xfc800f0c,
+       0x0cf6024f,
+       0x0c04bd00,
+       0x4afc800b,
+       0x000cf602,
+       0xfc8004bd,
+       0x0ef6024f,
+       0x0c04bd00,
+       0x4afc800a,
+       0x000cf602,
+       0x0a7e04bd,
+       0x00f80002,
+/* 0x0268: strand_ctx_init */
+       0x99f094bd,
+       0x37008003,
+       0x0009f602,
+       0x167e04bd,
+       0x030e0002,
+       0x0002387e,
+       0xfc80c4bd,
+       0x0cf60247,
+       0x0c04bd00,
+       0x4afc8001,
+       0x000cf602,
+       0x0a7e04bd,
+       0x0c920002,
+       0x46fc8001,
+       0x000cf602,
+       0x020c04bd,
+       0x024afc80,
+       0xbd000cf6,
+       0x020a7e04,
+       0x02277e00,
+       0x42008800,
+       0x20008902,
+       0x0099cf02,
+/* 0x02c7: ctx_init_strand_loop */
+       0xf608fe95,
+       0x8ef6008e,
+       0x808acf40,
+       0xb606a5b6,
+       0xeabb01a0,
+       0x0480b600,
+       0xf40192b6,
+       0xe4b6e81b,
+       0xf2efbc08,
+       0x99f094bd,
+       0x17008003,
+       0x0009f602,
+       0x00f804bd,
+/* 0x02f8: error */
+       0x02050080,
+       0xbd000ff6,
+       0x80010f04,
+       0xf6030700,
+       0x04bd000f,
+/* 0x030e: init */
+       0x04bd00f8,
+       0x410007fe,
+       0x11cf4200,
+       0x0911e700,
+       0x0814b601,
+       0x020014fe,
+       0x12004002,
+       0xbd0002f6,
+       0x05c94104,
+       0xbd0010fe,
+       0x07004024,
+       0xbd0002f6,
+       0x20034204,
+       0x01010080,
+       0xbd0002f6,
+       0x20044204,
+       0x01010480,
+       0xbd0002f6,
+       0x200b4204,
+       0x01010880,
+       0xbd0002f6,
+       0x200c4204,
+       0x01011c80,
+       0xbd0002f6,
+       0x01039204,
+       0x03090080,
+       0xbd0003f6,
+       0x87044204,
+       0xf6040040,
+       0x04bd0002,
+       0x00400402,
+       0x0002f603,
+       0x31f404bd,
+       0x96048e10,
+       0x00657e40,
+       0xc7feb200,
+       0x01b590f1,
+       0x1ff4f003,
+       0x01020fb5,
+       0x041fbb01,
+       0x800112b6,
+       0xf6010300,
+       0x04bd0001,
+       0x01040080,
+       0xbd0001f6,
+       0x01004104,
+       0xa87e020f,
+       0xb77e0006,
+       0x100f0006,
+       0x0006f97e,
+       0x98000e98,
+       0x207e010f,
+       0x14950001,
+       0xc0008008,
+       0x0004f601,
+       0x008004bd,
+       0x04f601c1,
+       0xb704bd00,
+       0xbb130030,
+       0xf5b6001f,
+       0xd3008002,
+       0x000ff601,
+       0x15b604bd,
+       0x0110b608,
+       0xb20814b6,
+       0x02687e1f,
+       0x001fbb00,
+       0x84020398,
+/* 0x041f: init_gpc */
+       0xb8502000,
+       0x0008044e,
+       0x8f7e1fb2,
+       0x4eb80000,
+       0xbd00010c,
+       0x008f7ef4,
+       0x044eb800,
+       0x8f7e0001,
+       0x4eb80000,
+       0x0f000100,
+       0x008f7e02,
+       0x004eb800,
+/* 0x044e: init_gpc_wait */
+       0x657e0008,
+       0xffc80000,
+       0xf90bf41f,
+       0x08044eb8,
+       0x00657e00,
+       0x001fbb00,
+       0x800040b7,
+       0xf40132b6,
+       0x000fb41b,
+       0x0006f97e,
+       0xa87e000f,
+       0x00800006,
+       0x01f60201,
+       0xbd04bd00,
+       0x1f19f014,
+       0x02300080,
+       0xbd0001f6,
+/* 0x0491: main */
+       0x0031f404,
+       0x0d0028f4,
+       0x00377e10,
+       0xf401f400,
+       0x4001e4b1,
+       0x00c71bf5,
+       0x99f094bd,
+       0x37008004,
+       0x0009f602,
+       0x008104bd,
+       0x11cf02c0,
+       0xc1008200,
+       0x0022cf02,
+       0xf41f13c8,
+       0x23c8770b,
+       0x550bf41f,
+       0x12b220f9,
+       0x99f094bd,
+       0x37008007,
+       0x0009f602,
+       0x32f404bd,
+       0x0231f401,
+       0x00087c7e,
+       0x99f094bd,
+       0x17008007,
+       0x0009f602,
+       0x20fc04bd,
+       0x99f094bd,
+       0x37008006,
+       0x0009f602,
+       0x31f404bd,
+       0x087c7e01,
+       0xf094bd00,
+       0x00800699,
+       0x09f60217,
+       0xf404bd00,
+/* 0x0522: chsw_prev_no_next */
+       0x20f92f0e,
+       0x32f412b2,
+       0x0232f401,
+       0x00087c7e,
+       0x008020fc,
+       0x02f602c0,
+       0xf404bd00,
+/* 0x053e: chsw_no_prev */
+       0x23c8130e,
+       0x0d0bf41f,
+       0xf40131f4,
+       0x7c7e0232,
+/* 0x054e: chsw_done */
+       0x01020008,
+       0x02c30080,
+       0xbd0002f6,
+       0xf094bd04,
+       0x00800499,
+       0x09f60217,
+       0xf504bd00,
+/* 0x056b: main_not_ctx_switch */
+       0xb0ff2a0e,
+       0x1bf401e4,
+       0x7ef2b20c,
+       0xf400081c,
+/* 0x057a: main_not_ctx_chan */
+       0xe4b0400e,
+       0x2c1bf402,
+       0x99f094bd,
+       0x37008007,
+       0x0009f602,
+       0x32f404bd,
+       0x0232f401,
+       0x00087c7e,
+       0x99f094bd,
+       0x17008007,
+       0x0009f602,
+       0x0ef404bd,
+/* 0x05a9: main_not_ctx_save */
+       0x10ef9411,
+       0x7e01f5f0,
+       0xf50002f8,
+/* 0x05b7: main_done */
+       0xbdfede0e,
+       0x1f29f024,
+       0x02300080,
+       0xbd0002f6,
+       0xcc0ef504,
+/* 0x05c9: ih */
+       0xfe80f9fe,
+       0x80f90188,
+       0xa0f990f9,
+       0xd0f9b0f9,
+       0xf0f9e0f9,
+       0x004a04bd,
+       0x00aacf02,
+       0xf404abc4,
+       0x100d230b,
+       0xcf1a004e,
+       0x004f00ee,
+       0x00ffcf19,
+       0x0000047e,
+       0x0400b0b7,
+       0x0040010e,
+       0x000ef61d,
+/* 0x060a: ih_no_fifo */
+       0xabe404bd,
+       0x0bf40100,
+       0x4e100d0c,
+       0x047e4001,
+/* 0x061a: ih_no_ctxsw */
+       0xabe40000,
+       0x0bf40400,
+       0x07088e56,
+       0x00657e40,
+       0x80ffb200,
+       0xf6020400,
+       0x04bd000f,
+       0x4007048e,
+       0x0000657e,
+       0x0080ffb2,
+       0x0ff60203,
+       0xc704bd00,
+       0xee9450fe,
+       0x07008f02,
+       0x00efbb40,
+       0x0000657e,
+       0x02020080,
+       0xbd000ff6,
+       0x7e030f04,
+       0x4b0002f8,
+       0xbfb20100,
+       0x4001448e,
+       0x00008f7e,
+/* 0x0674: ih_no_fwmthd */
+       0xbd05044b,
+       0xb4abffb0,
+       0x800c0bf4,
+       0xf6030700,
+       0x04bd000b,
+/* 0x0688: ih_no_other */
+       0xf6010040,
+       0x04bd000a,
+       0xe0fcf0fc,
+       0xb0fcd0fc,
+       0x90fca0fc,
+       0x88fe80fc,
+       0xf480fc00,
+       0x01f80032,
+/* 0x06a8: ctx_4170s */
+       0xb210f5f0,
+       0x41708eff,
+       0x008f7e40,
+/* 0x06b7: ctx_4170w */
+       0x8e00f800,
+       0x7e404170,
+       0xb2000065,
+       0x10f4f0ff,
+       0xf8f31bf4,
+/* 0x06c9: ctx_redswitch */
+       0x02004e00,
+       0xf040e5f0,
+       0xe5f020e5,
+       0x85008010,
+       0x000ef601,
+       0x080f04bd,
+/* 0x06e0: ctx_redswitch_delay */
+       0xf401f2b6,
+       0xe5f1fd1b,
+       0xe5f10400,
+       0x00800100,
+       0x0ef60185,
+       0xf804bd00,
+/* 0x06f9: ctx_86c */
+       0x23008000,
+       0x000ff602,
+       0xffb204bd,
+       0x408a148e,
+       0x00008f7e,
+       0x8c8effb2,
+       0x8f7e41a8,
+       0x00f80000,
+/* 0x0718: ctx_mem */
+       0x02840080,
+       0xbd000ff6,
+/* 0x0721: ctx_mem_wait */
+       0x84008f04,
+       0x00ffcf02,
+       0xf405fffd,
+       0x00f8f61b,
+/* 0x0730: ctx_load */
+       0x99f094bd,
+       0x37008005,
+       0x0009f602,
+       0x0c0a04bd,
+       0x0000b87e,
+       0x0080f4bd,
+       0x0ff60289,
+       0x8004bd00,
+       0xf602c100,
+       0x04bd0002,
+       0x02830080,
+       0xbd0002f6,
+       0x7e070f04,
+       0x80000718,
+       0xf602c000,
+       0x04bd0002,
+       0xf0000bfe,
+       0x24b61f2a,
+       0x0220b604,
+       0x99f094bd,
+       0x37008008,
+       0x0009f602,
+       0x008004bd,
+       0x02f60281,
+       0xd204bd00,
+       0x80000000,
+       0x800225f0,
+       0xf6028800,
+       0x04bd0002,
+       0x00421001,
+       0x0223f002,
+       0xf80512fa,
+       0xf094bd03,
+       0x00800899,
+       0x09f60217,
+       0x9804bd00,
+       0x14b68101,
+       0x80029818,
+       0xfd0825b6,
+       0x01b50512,
+       0xf094bd16,
+       0x00800999,
+       0x09f60237,
+       0x8004bd00,
+       0xf6028100,
+       0x04bd0001,
+       0x00800102,
+       0x02f60288,
+       0x4104bd00,
+       0x13f00100,
+       0x0501fa06,
+       0x94bd03f8,
+       0x800999f0,
+       0xf6021700,
+       0x04bd0009,
+       0x99f094bd,
+       0x17008005,
+       0x0009f602,
+       0x00f804bd,
+/* 0x081c: ctx_chan */
+       0x0007307e,
+       0xb87e0c0a,
+       0x050f0000,
+       0x0007187e,
+/* 0x082e: ctx_mmio_exec */
+       0x039800f8,
+       0x81008041,
+       0x0003f602,
+       0x34bd04bd,
+/* 0x083c: ctx_mmio_loop */
+       0xf4ff34c4,
+       0x00450e1b,
+       0x0653f002,
+       0xf80535fa,
+/* 0x084d: ctx_mmio_pull */
+       0x804e9803,
+       0x7e814f98,
+       0xb600008f,
+       0x12b60830,
+       0xdf1bf401,
+/* 0x0860: ctx_mmio_done */
+       0x80160398,
+       0xf6028100,
+       0x04bd0003,
+       0x414000b5,
+       0x13f00100,
+       0x0601fa06,
+       0x00f803f8,
+/* 0x087c: ctx_xfer */
+       0x0080040e,
+       0x0ef60302,
+/* 0x0887: ctx_xfer_idle */
+       0x8e04bd00,
+       0xcf030000,
+       0xe4f100ee,
+       0x1bf42000,
+       0x0611f4f5,
+/* 0x089b: ctx_xfer_pre */
+       0x0f0c02f4,
+       0x06f97e10,
+       0x1b11f400,
+/* 0x08a4: ctx_xfer_pre_load */
+       0xa87e020f,
+       0xb77e0006,
+       0xc97e0006,
+       0xf4bd0006,
+       0x0006a87e,
+       0x0007307e,
+/* 0x08bc: ctx_xfer_exec */
+       0xbd160198,
+       0x05008024,
+       0x0002f601,
+       0x1fb204bd,
+       0x41a5008e,
+       0x00008f7e,
+       0xf001fcf0,
+       0x24b6022c,
+       0x05f2fd01,
+       0x048effb2,
+       0x8f7e41a5,
+       0x167e0000,
+       0x24bd0002,
+       0x0247fc80,
+       0xbd0002f6,
+       0x012cf004,
+       0x800320b6,
+       0xf6024afc,
+       0x04bd0002,
+       0xf001acf0,
+       0x000b06a5,
+       0x98000c98,
+       0x000e010d,
+       0x00013d7e,
+       0xec7e080a,
+       0x0a7e0000,
+       0x01f40002,
+       0x7e0c0a12,
+       0x0f0000b8,
+       0x07187e05,
+       0x2d02f400,
+/* 0x0938: ctx_xfer_post */
+       0xa87e020f,
+       0xf4bd0006,
+       0x0006f97e,
+       0x0002277e,
+       0x0006b77e,
+       0xa87ef4bd,
+       0x11f40006,
+       0x40019810,
+       0xf40511fd,
+       0x2e7e070b,
+/* 0x0962: ctx_xfer_no_post_mmio */
+/* 0x0962: ctx_xfer_done */
+       0x00f80008,
+       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/drivers/gpu/drm/nouveau/nvkm/engine/gr/fuc/macros.fuc b/drivers/gpu/drm/nouveau/nvkm/engine/gr/fuc/macros.fuc
new file mode 100644 (file)
index 0000000..2a0b0f8
--- /dev/null
@@ -0,0 +1,229 @@
+/*
+ * Copyright 2013 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 <bskeggs@redhat.com>
+ */
+
+#include "os.h"
+
+#define GF100 0xc0
+#define GF117 0xd7
+#define GK100 0xe0
+#define GK110 0xf0
+#define GK208 0x108
+
+#define NV_PGRAPH_TRAPPED_ADDR                                         0x400704
+#define NV_PGRAPH_TRAPPED_DATA_LO                                      0x400708
+#define NV_PGRAPH_TRAPPED_DATA_HI                                      0x40070c
+
+#define NV_PGRAPH_FE_OBJECT_TABLE(n)                        ((n) * 4 + 0x400700)
+
+#define NV_PGRAPH_FECS_INTR_ACK                                        0x409004
+#define NV_PGRAPH_FECS_INTR                                            0x409008
+#define NV_PGRAPH_FECS_INTR_FWMTHD                                   0x00000400
+#define NV_PGRAPH_FECS_INTR_CHSW                                     0x00000100
+#define NV_PGRAPH_FECS_INTR_FIFO                                     0x00000004
+#define NV_PGRAPH_FECS_INTR_MODE                                       0x40900c
+#define NV_PGRAPH_FECS_INTR_MODE_FIFO                                0x00000004
+#define NV_PGRAPH_FECS_INTR_MODE_FIFO_LEVEL                          0x00000004
+#define NV_PGRAPH_FECS_INTR_MODE_FIFO_EDGE                           0x00000000
+#define NV_PGRAPH_FECS_INTR_EN_SET                                     0x409010
+#define NV_PGRAPH_FECS_INTR_EN_SET_FIFO                              0x00000004
+#define NV_PGRAPH_FECS_INTR_ROUTE                                      0x40901c
+#define NV_PGRAPH_FECS_ACCESS                                          0x409048
+#define NV_PGRAPH_FECS_ACCESS_FIFO                                   0x00000002
+#define NV_PGRAPH_FECS_FIFO_DATA                                       0x409064
+#define NV_PGRAPH_FECS_FIFO_CMD                                        0x409068
+#define NV_PGRAPH_FECS_FIFO_ACK                                        0x409074
+#define NV_PGRAPH_FECS_CAPS                                            0x409108
+#define NV_PGRAPH_FECS_SIGNAL                                          0x409400
+#define NV_PGRAPH_FECS_IROUTE                                          0x409404
+#define NV_PGRAPH_FECS_BAR_MASK0                                       0x40940c
+#define NV_PGRAPH_FECS_BAR_MASK1                                       0x409410
+#define NV_PGRAPH_FECS_BAR                                             0x409414
+#define NV_PGRAPH_FECS_BAR_SET                                         0x409418
+#define NV_PGRAPH_FECS_RED_SWITCH                                      0x409614
+#define NV_PGRAPH_FECS_RED_SWITCH_ENABLE_ROP                         0x00000400
+#define NV_PGRAPH_FECS_RED_SWITCH_ENABLE_GPC                         0x00000200
+#define NV_PGRAPH_FECS_RED_SWITCH_ENABLE_MAIN                        0x00000100
+#define NV_PGRAPH_FECS_RED_SWITCH_POWER_ROP                          0x00000040
+#define NV_PGRAPH_FECS_RED_SWITCH_POWER_GPC                          0x00000020
+#define NV_PGRAPH_FECS_RED_SWITCH_POWER_MAIN                         0x00000010
+#define NV_PGRAPH_FECS_RED_SWITCH_PAUSE_GPC                          0x00000002
+#define NV_PGRAPH_FECS_RED_SWITCH_PAUSE_MAIN                         0x00000001
+#define NV_PGRAPH_FECS_MMCTX_SAVE_SWBASE                               0x409700
+#define NV_PGRAPH_FECS_MMCTX_LOAD_SWBASE                               0x409704
+#define NV_PGRAPH_FECS_MMCTX_LOAD_COUNT                                0x40974c
+#define NV_PGRAPH_FECS_MMCTX_SAVE_SWBASE                               0x409700
+#define NV_PGRAPH_FECS_MMCTX_LOAD_SWBASE                               0x409704
+#define NV_PGRAPH_FECS_MMCTX_BASE                                      0x409710
+#define NV_PGRAPH_FECS_MMCTX_CTRL                                      0x409714
+#define NV_PGRAPH_FECS_MMCTX_MULTI_STRIDE                              0x409718
+#define NV_PGRAPH_FECS_MMCTX_MULTI_MASK                                0x40971c
+#define NV_PGRAPH_FECS_MMCTX_QUEUE                                     0x409720
+#define NV_PGRAPH_FECS_MMIO_CTRL                                       0x409728
+#define NV_PGRAPH_FECS_MMIO_RDVAL                                      0x40972c
+#define NV_PGRAPH_FECS_MMIO_WRVAL                                      0x409730
+#define NV_PGRAPH_FECS_MMCTX_LOAD_COUNT                                0x40974c
+#if CHIPSET < GK110
+#define NV_PGRAPH_FECS_CC_SCRATCH_VAL(n)                    ((n) * 4 + 0x409800)
+#define NV_PGRAPH_FECS_CC_SCRATCH_SET(n)                    ((n) * 4 + 0x409820)
+#define NV_PGRAPH_FECS_CC_SCRATCH_CLR(n)                    ((n) * 4 + 0x409840)
+#define NV_PGRAPH_FECS_UNK86C                                          0x40986c
+#else
+#define NV_PGRAPH_FECS_CC_SCRATCH_VAL(n)                    ((n) * 4 + 0x409800)
+#define NV_PGRAPH_FECS_CC_SCRATCH_CLR(n)                    ((n) * 4 + 0x409840)
+#define NV_PGRAPH_FECS_UNK86C                                          0x40988c
+#define NV_PGRAPH_FECS_CC_SCRATCH_SET(n)                    ((n) * 4 + 0x4098c0)
+#endif
+#define NV_PGRAPH_FECS_STRANDS_CNT                                     0x409880
+#define NV_PGRAPH_FECS_STRAND_SAVE_SWBASE                              0x409908
+#define NV_PGRAPH_FECS_STRAND_LOAD_SWBASE                              0x40990c
+#define NV_PGRAPH_FECS_STRAND_WORDS                                    0x409910
+#define NV_PGRAPH_FECS_STRAND_DATA                                     0x409918
+#define NV_PGRAPH_FECS_STRAND_SELECT                                   0x40991c
+#define NV_PGRAPH_FECS_STRAND_CMD                                      0x409928
+#define NV_PGRAPH_FECS_STRAND_CMD_SEEK                               0x00000001
+#define NV_PGRAPH_FECS_STRAND_CMD_GET_INFO                           0x00000002
+#define NV_PGRAPH_FECS_STRAND_CMD_SAVE                               0x00000003
+#define NV_PGRAPH_FECS_STRAND_CMD_LOAD                               0x00000004
+#define NV_PGRAPH_FECS_STRAND_CMD_ACTIVATE_FILTER                    0x0000000a
+#define NV_PGRAPH_FECS_STRAND_CMD_DEACTIVATE_FILTER                  0x0000000b
+#define NV_PGRAPH_FECS_STRAND_CMD_ENABLE                             0x0000000c
+#define NV_PGRAPH_FECS_STRAND_CMD_DISABLE                            0x0000000d
+#define NV_PGRAPH_FECS_STRAND_FILTER                                   0x40993c
+#define NV_PGRAPH_FECS_MEM_BASE                                        0x409a04
+#define NV_PGRAPH_FECS_MEM_CHAN                                        0x409a0c
+#define NV_PGRAPH_FECS_MEM_CMD                                         0x409a10
+#define NV_PGRAPH_FECS_MEM_CMD_LOAD_CHAN                             0x00000007
+#define NV_PGRAPH_FECS_MEM_TARGET                                      0x409a20
+#define NV_PGRAPH_FECS_MEM_TARGET_UNK31                              0x80000000
+#define NV_PGRAPH_FECS_MEM_TARGET_AS                                 0x0000001f
+#define NV_PGRAPH_FECS_MEM_TARGET_AS_VM                              0x00000001
+#define NV_PGRAPH_FECS_MEM_TARGET_AS_VRAM                            0x00000002
+#define NV_PGRAPH_FECS_CHAN_ADDR                                       0x409b00
+#define NV_PGRAPH_FECS_CHAN_NEXT                                       0x409b04
+#define NV_PGRAPH_FECS_CHSW                                            0x409b0c
+#define NV_PGRAPH_FECS_CHSW_ACK                                      0x00000001
+#define NV_PGRAPH_FECS_INTR_UP_SET                                     0x409c1c
+#define NV_PGRAPH_FECS_INTR_UP_EN                                      0x409c24
+
+#define NV_PGRAPH_GPCX_GPCCS_INTR_ACK                                  0x41a004
+#define NV_PGRAPH_GPCX_GPCCS_INTR                                      0x41a008
+#define NV_PGRAPH_GPCX_GPCCS_INTR_FIFO                               0x00000004
+#define NV_PGRAPH_GPCX_GPCCS_INTR_EN_SET                               0x41a010
+#define NV_PGRAPH_GPCX_GPCCS_INTR_EN_SET_FIFO                        0x00000004
+#define NV_PGRAPH_GPCX_GPCCS_INTR_ROUTE                                0x41a01c
+#define NV_PGRAPH_GPCX_GPCCS_ACCESS                                    0x41a048
+#define NV_PGRAPH_GPCX_GPCCS_ACCESS_FIFO                             0x00000002
+#define NV_PGRAPH_GPCX_GPCCS_FIFO_DATA                                 0x41a064
+#define NV_PGRAPH_GPCX_GPCCS_FIFO_CMD                                  0x41a068
+#define NV_PGRAPH_GPCX_GPCCS_FIFO_ACK                                  0x41a074
+#define NV_PGRAPH_GPCX_GPCCS_UNITS                                     0x41a608
+#define NV_PGRAPH_GPCX_GPCCS_CAPS                                      0x41a108
+#define NV_PGRAPH_GPCX_GPCCS_RED_SWITCH                                0x41a614
+#define NV_PGRAPH_GPCX_GPCCS_RED_SWITCH_UNK11                        0x00000800
+#define NV_PGRAPH_GPCX_GPCCS_RED_SWITCH_ENABLE                       0x00000200
+#define NV_PGRAPH_GPCX_GPCCS_RED_SWITCH_POWER                        0x00000020
+#define NV_PGRAPH_GPCX_GPCCS_RED_SWITCH_PAUSE                        0x00000002
+#define NV_PGRAPH_GPCX_GPCCS_MYINDEX                                   0x41a618
+#define NV_PGRAPH_GPCX_GPCCS_MMCTX_SAVE_SWBASE                         0x41a700
+#define NV_PGRAPH_GPCX_GPCCS_MMCTX_LOAD_SWBASE                         0x41a704
+#define NV_PGRAPH_GPCX_GPCCS_MMCTX_LOAD_COUNT                          0x41a74c
+#if CHIPSET < GK110
+#define NV_PGRAPH_GPCX_GPCCS_CC_SCRATCH_VAL(n)              ((n) * 4 + 0x41a800)
+#define NV_PGRAPH_GPCX_GPCCS_CC_SCRATCH_SET(n)              ((n) * 4 + 0x41a820)
+#define NV_PGRAPH_GPCX_GPCCS_CC_SCRATCH_CLR(n)              ((n) * 4 + 0x41a840)
+#define NV_PGRAPH_GPCX_GPCCS_UNK86C                                    0x41a86c
+#else
+#define NV_PGRAPH_GPCX_GPCCS_CC_SCRATCH_VAL(n)              ((n) * 4 + 0x41a800)
+#define NV_PGRAPH_GPCX_GPCCS_CC_SCRATCH_CLR(n)              ((n) * 4 + 0x41a840)
+#define NV_PGRAPH_GPCX_GPCCS_UNK86C                                    0x41a88c
+#define NV_PGRAPH_GPCX_GPCCS_CC_SCRATCH_SET(n)              ((n) * 4 + 0x41a8c0)
+#endif
+#define NV_PGRAPH_GPCX_GPCCS_STRAND_SELECT                             0x41a91c
+#define NV_PGRAPH_GPCX_GPCCS_STRAND_CMD                                0x41a928
+#define NV_PGRAPH_GPCX_GPCCS_STRAND_CMD_SAVE                         0x00000003
+#define NV_PGRAPH_GPCX_GPCCS_STRAND_CMD_LOAD                         0x00000004
+#define NV_PGRAPH_GPCX_GPCCS_MEM_BASE                                  0x41aa04
+
+#define mmctx_data(r,c) .b32 (((c - 1) << 26) | r)
+#define queue_init      .skip 72 // (2 * 4) + ((8 * 4) * 2)
+
+#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
+
+#if CHIPSET < GK208
+#define imm32(reg,val) /*
+*/     movw reg  ((val) & 0x0000ffff) /*
+*/     sethi reg ((val) & 0xffff0000)
+#else
+#define imm32(reg,val) /*
+*/     mov reg (val)
+#endif
+
+#define nv_mkio(rv,r,i) /*
+*/     imm32(rv, (((r) & 0xffc) << 6) | ((i) << 2))
+
+#define hash #
+#define fn(a) a
+#if CHIPSET < GK208
+#define call(a) call fn(hash)a
+#else
+#define call(a) lcall fn(hash)a
+#endif
+
+#define nv_iord(rv,r,i) /*
+*/     nv_mkio(rv,r,i) /*
+*/     iord rv I[rv]
+
+#define nv_iowr(r,i,rv) /*
+*/     nv_mkio($r0,r,i) /*
+*/     iowr I[$r0] rv /*
+*/     clear b32 $r0
+
+#define nv_rd32(reg,addr) /*
+*/     imm32($r14, addr) /*
+*/     call(nv_rd32) /*
+*/     mov b32 reg $r15
+
+#define nv_wr32(addr,reg) /*
+*/     mov b32 $r15 reg /*
+*/     imm32($r14, addr) /*
+*/     call(nv_wr32)
+
+#define trace_set(bit) /*
+*/     clear b32 $r9 /*
+*/     bset $r9 bit /*
+*/     nv_iowr(NV_PGRAPH_FECS_CC_SCRATCH_SET(7), 0, $r9)
+
+#define trace_clr(bit) /*
+*/     clear b32 $r9 /*
+*/     bset $r9 bit /*
+*/     nv_iowr(NV_PGRAPH_FECS_CC_SCRATCH_CLR(7), 0, $r9)
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/gr/fuc/os.h b/drivers/gpu/drm/nouveau/nvkm/engine/gr/fuc/os.h
new file mode 100644 (file)
index 0000000..1718ae4
--- /dev/null
@@ -0,0 +1,8 @@
+#ifndef __NVKM_GRAPH_OS_H__
+#define __NVKM_GRAPH_OS_H__
+
+#define E_BAD_COMMAND  0x00000001
+#define E_CMD_OVERFLOW 0x00000002
+#define E_BAD_FWMTHD   0x00000003
+
+#endif
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/gr/gf100.c b/drivers/gpu/drm/nouveau/nvkm/engine/gr/gf100.c
new file mode 100644 (file)
index 0000000..1dd482e
--- /dev/null
@@ -0,0 +1,1678 @@
+/*
+ * Copyright 2012 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 "gf100.h"
+#include "ctxgf100.h"
+#include "fuc/os.h"
+
+#include <core/client.h>
+#include <core/device.h>
+#include <core/handle.h>
+#include <core/option.h>
+#include <engine/fifo.h>
+#include <subdev/fb.h>
+#include <subdev/mc.h>
+#include <subdev/timer.h>
+
+#include <nvif/class.h>
+#include <nvif/unpack.h>
+
+/*******************************************************************************
+ * Zero Bandwidth Clear
+ ******************************************************************************/
+
+static void
+gf100_gr_zbc_clear_color(struct gf100_gr_priv *priv, int zbc)
+{
+       if (priv->zbc_color[zbc].format) {
+               nv_wr32(priv, 0x405804, priv->zbc_color[zbc].ds[0]);
+               nv_wr32(priv, 0x405808, priv->zbc_color[zbc].ds[1]);
+               nv_wr32(priv, 0x40580c, priv->zbc_color[zbc].ds[2]);
+               nv_wr32(priv, 0x405810, priv->zbc_color[zbc].ds[3]);
+       }
+       nv_wr32(priv, 0x405814, priv->zbc_color[zbc].format);
+       nv_wr32(priv, 0x405820, zbc);
+       nv_wr32(priv, 0x405824, 0x00000004); /* TRIGGER | WRITE | COLOR */
+}
+
+static int
+gf100_gr_zbc_color_get(struct gf100_gr_priv *priv, int format,
+                      const u32 ds[4], const u32 l2[4])
+{
+       struct nvkm_ltc *ltc = nvkm_ltc(priv);
+       int zbc = -ENOSPC, i;
+
+       for (i = ltc->zbc_min; i <= ltc->zbc_max; i++) {
+               if (priv->zbc_color[i].format) {
+                       if (priv->zbc_color[i].format != format)
+                               continue;
+                       if (memcmp(priv->zbc_color[i].ds, ds, sizeof(
+                                  priv->zbc_color[i].ds)))
+                               continue;
+                       if (memcmp(priv->zbc_color[i].l2, l2, sizeof(
+                                  priv->zbc_color[i].l2))) {
+                               WARN_ON(1);
+                               return -EINVAL;
+                       }
+                       return i;
+               } else {
+                       zbc = (zbc < 0) ? i : zbc;
+               }
+       }
+
+       if (zbc < 0)
+               return zbc;
+
+       memcpy(priv->zbc_color[zbc].ds, ds, sizeof(priv->zbc_color[zbc].ds));
+       memcpy(priv->zbc_color[zbc].l2, l2, sizeof(priv->zbc_color[zbc].l2));
+       priv->zbc_color[zbc].format = format;
+       ltc->zbc_color_get(ltc, zbc, l2);
+       gf100_gr_zbc_clear_color(priv, zbc);
+       return zbc;
+}
+
+static void
+gf100_gr_zbc_clear_depth(struct gf100_gr_priv *priv, int zbc)
+{
+       if (priv->zbc_depth[zbc].format)
+               nv_wr32(priv, 0x405818, priv->zbc_depth[zbc].ds);
+       nv_wr32(priv, 0x40581c, priv->zbc_depth[zbc].format);
+       nv_wr32(priv, 0x405820, zbc);
+       nv_wr32(priv, 0x405824, 0x00000005); /* TRIGGER | WRITE | DEPTH */
+}
+
+static int
+gf100_gr_zbc_depth_get(struct gf100_gr_priv *priv, int format,
+                      const u32 ds, const u32 l2)
+{
+       struct nvkm_ltc *ltc = nvkm_ltc(priv);
+       int zbc = -ENOSPC, i;
+
+       for (i = ltc->zbc_min; i <= ltc->zbc_max; i++) {
+               if (priv->zbc_depth[i].format) {
+                       if (priv->zbc_depth[i].format != format)
+                               continue;
+                       if (priv->zbc_depth[i].ds != ds)
+                               continue;
+                       if (priv->zbc_depth[i].l2 != l2) {
+                               WARN_ON(1);
+                               return -EINVAL;
+                       }
+                       return i;
+               } else {
+                       zbc = (zbc < 0) ? i : zbc;
+               }
+       }
+
+       if (zbc < 0)
+               return zbc;
+
+       priv->zbc_depth[zbc].format = format;
+       priv->zbc_depth[zbc].ds = ds;
+       priv->zbc_depth[zbc].l2 = l2;
+       ltc->zbc_depth_get(ltc, zbc, l2);
+       gf100_gr_zbc_clear_depth(priv, zbc);
+       return zbc;
+}
+
+/*******************************************************************************
+ * Graphics object classes
+ ******************************************************************************/
+
+static int
+gf100_fermi_mthd_zbc_color(struct nvkm_object *object, void *data, u32 size)
+{
+       struct gf100_gr_priv *priv = (void *)object->engine;
+       union {
+               struct fermi_a_zbc_color_v0 v0;
+       } *args = data;
+       int ret;
+
+       if (nvif_unpack(args->v0, 0, 0, false)) {
+               switch (args->v0.format) {
+               case FERMI_A_ZBC_COLOR_V0_FMT_ZERO:
+               case FERMI_A_ZBC_COLOR_V0_FMT_UNORM_ONE:
+               case FERMI_A_ZBC_COLOR_V0_FMT_RF32_GF32_BF32_AF32:
+               case FERMI_A_ZBC_COLOR_V0_FMT_R16_G16_B16_A16:
+               case FERMI_A_ZBC_COLOR_V0_FMT_RN16_GN16_BN16_AN16:
+               case FERMI_A_ZBC_COLOR_V0_FMT_RS16_GS16_BS16_AS16:
+               case FERMI_A_ZBC_COLOR_V0_FMT_RU16_GU16_BU16_AU16:
+               case FERMI_A_ZBC_COLOR_V0_FMT_RF16_GF16_BF16_AF16:
+               case FERMI_A_ZBC_COLOR_V0_FMT_A8R8G8B8:
+               case FERMI_A_ZBC_COLOR_V0_FMT_A8RL8GL8BL8:
+               case FERMI_A_ZBC_COLOR_V0_FMT_A2B10G10R10:
+               case FERMI_A_ZBC_COLOR_V0_FMT_AU2BU10GU10RU10:
+               case FERMI_A_ZBC_COLOR_V0_FMT_A8B8G8R8:
+               case FERMI_A_ZBC_COLOR_V0_FMT_A8BL8GL8RL8:
+               case FERMI_A_ZBC_COLOR_V0_FMT_AN8BN8GN8RN8:
+               case FERMI_A_ZBC_COLOR_V0_FMT_AS8BS8GS8RS8:
+               case FERMI_A_ZBC_COLOR_V0_FMT_AU8BU8GU8RU8:
+               case FERMI_A_ZBC_COLOR_V0_FMT_A2R10G10B10:
+               case FERMI_A_ZBC_COLOR_V0_FMT_BF10GF11RF11:
+                       ret = gf100_gr_zbc_color_get(priv, args->v0.format,
+                                                          args->v0.ds,
+                                                          args->v0.l2);
+                       if (ret >= 0) {
+                               args->v0.index = ret;
+                               return 0;
+                       }
+                       break;
+               default:
+                       return -EINVAL;
+               }
+       }
+
+       return ret;
+}
+
+static int
+gf100_fermi_mthd_zbc_depth(struct nvkm_object *object, void *data, u32 size)
+{
+       struct gf100_gr_priv *priv = (void *)object->engine;
+       union {
+               struct fermi_a_zbc_depth_v0 v0;
+       } *args = data;
+       int ret;
+
+       if (nvif_unpack(args->v0, 0, 0, false)) {
+               switch (args->v0.format) {
+               case FERMI_A_ZBC_DEPTH_V0_FMT_FP32:
+                       ret = gf100_gr_zbc_depth_get(priv, args->v0.format,
+                                                          args->v0.ds,
+                                                          args->v0.l2);
+                       return (ret >= 0) ? 0 : -ENOSPC;
+               default:
+                       return -EINVAL;
+               }
+       }
+
+       return ret;
+}
+
+static int
+gf100_fermi_mthd(struct nvkm_object *object, u32 mthd, void *data, u32 size)
+{
+       switch (mthd) {
+       case FERMI_A_ZBC_COLOR:
+               return gf100_fermi_mthd_zbc_color(object, data, size);
+       case FERMI_A_ZBC_DEPTH:
+               return gf100_fermi_mthd_zbc_depth(object, data, size);
+       default:
+               break;
+       }
+       return -EINVAL;
+}
+
+struct nvkm_ofuncs
+gf100_fermi_ofuncs = {
+       .ctor = _nvkm_object_ctor,
+       .dtor = nvkm_object_destroy,
+       .init = nvkm_object_init,
+       .fini = nvkm_object_fini,
+       .mthd = gf100_fermi_mthd,
+};
+
+static int
+gf100_gr_set_shader_exceptions(struct nvkm_object *object, u32 mthd,
+                              void *pdata, u32 size)
+{
+       struct gf100_gr_priv *priv = (void *)nv_engine(object);
+       if (size >= sizeof(u32)) {
+               u32 data = *(u32 *)pdata ? 0xffffffff : 0x00000000;
+               nv_wr32(priv, 0x419e44, data);
+               nv_wr32(priv, 0x419e4c, data);
+               return 0;
+       }
+       return -EINVAL;
+}
+
+struct nvkm_omthds
+gf100_gr_9097_omthds[] = {
+       { 0x1528, 0x1528, gf100_gr_set_shader_exceptions },
+       {}
+};
+
+struct nvkm_omthds
+gf100_gr_90c0_omthds[] = {
+       { 0x1528, 0x1528, gf100_gr_set_shader_exceptions },
+       {}
+};
+
+struct nvkm_oclass
+gf100_gr_sclass[] = {
+       { 0x902d, &nvkm_object_ofuncs },
+       { 0x9039, &nvkm_object_ofuncs },
+       { FERMI_A, &gf100_fermi_ofuncs, gf100_gr_9097_omthds },
+       { FERMI_COMPUTE_A, &nvkm_object_ofuncs, gf100_gr_90c0_omthds },
+       {}
+};
+
+/*******************************************************************************
+ * PGRAPH context
+ ******************************************************************************/
+
+int
+gf100_gr_context_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+                     struct nvkm_oclass *oclass, void *args, u32 size,
+                     struct nvkm_object **pobject)
+{
+       struct nvkm_vm *vm = nvkm_client(parent)->vm;
+       struct gf100_gr_priv *priv = (void *)engine;
+       struct gf100_gr_data *data = priv->mmio_data;
+       struct gf100_gr_mmio *mmio = priv->mmio_list;
+       struct gf100_gr_chan *chan;
+       int ret, i;
+
+       /* allocate memory for context, and fill with default values */
+       ret = nvkm_gr_context_create(parent, engine, oclass, NULL,
+                                    priv->size, 0x100,
+                                    NVOBJ_FLAG_ZERO_ALLOC, &chan);
+       *pobject = nv_object(chan);
+       if (ret)
+               return ret;
+
+       /* allocate memory for a "mmio list" buffer that's used by the HUB
+        * fuc to modify some per-context register settings on first load
+        * of the context.
+        */
+       ret = nvkm_gpuobj_new(nv_object(chan), NULL, 0x1000, 0x100, 0,
+                             &chan->mmio);
+       if (ret)
+               return ret;
+
+       ret = nvkm_gpuobj_map_vm(nv_gpuobj(chan->mmio), vm,
+                                NV_MEM_ACCESS_RW | NV_MEM_ACCESS_SYS,
+                                &chan->mmio_vma);
+       if (ret)
+               return ret;
+
+       /* allocate buffers referenced by mmio list */
+       for (i = 0; data->size && i < ARRAY_SIZE(priv->mmio_data); i++) {
+               ret = nvkm_gpuobj_new(nv_object(chan), NULL, data->size,
+                                     data->align, 0, &chan->data[i].mem);
+               if (ret)
+                       return ret;
+
+               ret = nvkm_gpuobj_map_vm(chan->data[i].mem, vm, data->access,
+                                        &chan->data[i].vma);
+               if (ret)
+                       return ret;
+
+               data++;
+       }
+
+       /* finally, fill in the mmio list and point the context at it */
+       for (i = 0; mmio->addr && i < ARRAY_SIZE(priv->mmio_list); i++) {
+               u32 addr = mmio->addr;
+               u32 data = mmio->data;
+
+               if (mmio->buffer >= 0) {
+                       u64 info = chan->data[mmio->buffer].vma.offset;
+                       data |= info >> mmio->shift;
+               }
+
+               nv_wo32(chan->mmio, chan->mmio_nr++ * 4, addr);
+               nv_wo32(chan->mmio, chan->mmio_nr++ * 4, data);
+               mmio++;
+       }
+
+       for (i = 0; i < priv->size; i += 4)
+               nv_wo32(chan, i, priv->data[i / 4]);
+
+       if (!priv->firmware) {
+               nv_wo32(chan, 0x00, chan->mmio_nr / 2);
+               nv_wo32(chan, 0x04, chan->mmio_vma.offset >> 8);
+       } else {
+               nv_wo32(chan, 0xf4, 0);
+               nv_wo32(chan, 0xf8, 0);
+               nv_wo32(chan, 0x10, chan->mmio_nr / 2);
+               nv_wo32(chan, 0x14, lower_32_bits(chan->mmio_vma.offset));
+               nv_wo32(chan, 0x18, upper_32_bits(chan->mmio_vma.offset));
+               nv_wo32(chan, 0x1c, 1);
+               nv_wo32(chan, 0x20, 0);
+               nv_wo32(chan, 0x28, 0);
+               nv_wo32(chan, 0x2c, 0);
+       }
+
+       return 0;
+}
+
+void
+gf100_gr_context_dtor(struct nvkm_object *object)
+{
+       struct gf100_gr_chan *chan = (void *)object;
+       int i;
+
+       for (i = 0; i < ARRAY_SIZE(chan->data); i++) {
+               nvkm_gpuobj_unmap(&chan->data[i].vma);
+               nvkm_gpuobj_ref(NULL, &chan->data[i].mem);
+       }
+
+       nvkm_gpuobj_unmap(&chan->mmio_vma);
+       nvkm_gpuobj_ref(NULL, &chan->mmio);
+
+       nvkm_gr_context_destroy(&chan->base);
+}
+
+/*******************************************************************************
+ * PGRAPH register lists
+ ******************************************************************************/
+
+const struct gf100_gr_init
+gf100_gr_init_main_0[] = {
+       { 0x400080,   1, 0x04, 0x003083c2 },
+       { 0x400088,   1, 0x04, 0x00006fe7 },
+       { 0x40008c,   1, 0x04, 0x00000000 },
+       { 0x400090,   1, 0x04, 0x00000030 },
+       { 0x40013c,   1, 0x04, 0x013901f7 },
+       { 0x400140,   1, 0x04, 0x00000100 },
+       { 0x400144,   1, 0x04, 0x00000000 },
+       { 0x400148,   1, 0x04, 0x00000110 },
+       { 0x400138,   1, 0x04, 0x00000000 },
+       { 0x400130,   2, 0x04, 0x00000000 },
+       { 0x400124,   1, 0x04, 0x00000002 },
+       {}
+};
+
+const struct gf100_gr_init
+gf100_gr_init_fe_0[] = {
+       { 0x40415c,   1, 0x04, 0x00000000 },
+       { 0x404170,   1, 0x04, 0x00000000 },
+       {}
+};
+
+const struct gf100_gr_init
+gf100_gr_init_pri_0[] = {
+       { 0x404488,   2, 0x04, 0x00000000 },
+       {}
+};
+
+const struct gf100_gr_init
+gf100_gr_init_rstr2d_0[] = {
+       { 0x407808,   1, 0x04, 0x00000000 },
+       {}
+};
+
+const struct gf100_gr_init
+gf100_gr_init_pd_0[] = {
+       { 0x406024,   1, 0x04, 0x00000000 },
+       {}
+};
+
+const struct gf100_gr_init
+gf100_gr_init_ds_0[] = {
+       { 0x405844,   1, 0x04, 0x00ffffff },
+       { 0x405850,   1, 0x04, 0x00000000 },
+       { 0x405908,   1, 0x04, 0x00000000 },
+       {}
+};
+
+const struct gf100_gr_init
+gf100_gr_init_scc_0[] = {
+       { 0x40803c,   1, 0x04, 0x00000000 },
+       {}
+};
+
+const struct gf100_gr_init
+gf100_gr_init_prop_0[] = {
+       { 0x4184a0,   1, 0x04, 0x00000000 },
+       {}
+};
+
+const struct gf100_gr_init
+gf100_gr_init_gpc_unk_0[] = {
+       { 0x418604,   1, 0x04, 0x00000000 },
+       { 0x418680,   1, 0x04, 0x00000000 },
+       { 0x418714,   1, 0x04, 0x80000000 },
+       { 0x418384,   1, 0x04, 0x00000000 },
+       {}
+};
+
+const struct gf100_gr_init
+gf100_gr_init_setup_0[] = {
+       { 0x418814,   3, 0x04, 0x00000000 },
+       {}
+};
+
+const struct gf100_gr_init
+gf100_gr_init_crstr_0[] = {
+       { 0x418b04,   1, 0x04, 0x00000000 },
+       {}
+};
+
+const struct gf100_gr_init
+gf100_gr_init_setup_1[] = {
+       { 0x4188c8,   1, 0x04, 0x80000000 },
+       { 0x4188cc,   1, 0x04, 0x00000000 },
+       { 0x4188d0,   1, 0x04, 0x00010000 },
+       { 0x4188d4,   1, 0x04, 0x00000001 },
+       {}
+};
+
+const struct gf100_gr_init
+gf100_gr_init_zcull_0[] = {
+       { 0x418910,   1, 0x04, 0x00010001 },
+       { 0x418914,   1, 0x04, 0x00000301 },
+       { 0x418918,   1, 0x04, 0x00800000 },
+       { 0x418980,   1, 0x04, 0x77777770 },
+       { 0x418984,   3, 0x04, 0x77777777 },
+       {}
+};
+
+const struct gf100_gr_init
+gf100_gr_init_gpm_0[] = {
+       { 0x418c04,   1, 0x04, 0x00000000 },
+       { 0x418c88,   1, 0x04, 0x00000000 },
+       {}
+};
+
+const struct gf100_gr_init
+gf100_gr_init_gpc_unk_1[] = {
+       { 0x418d00,   1, 0x04, 0x00000000 },
+       { 0x418f08,   1, 0x04, 0x00000000 },
+       { 0x418e00,   1, 0x04, 0x00000050 },
+       { 0x418e08,   1, 0x04, 0x00000000 },
+       {}
+};
+
+const struct gf100_gr_init
+gf100_gr_init_gcc_0[] = {
+       { 0x41900c,   1, 0x04, 0x00000000 },
+       { 0x419018,   1, 0x04, 0x00000000 },
+       {}
+};
+
+const struct gf100_gr_init
+gf100_gr_init_tpccs_0[] = {
+       { 0x419d08,   2, 0x04, 0x00000000 },
+       { 0x419d10,   1, 0x04, 0x00000014 },
+       {}
+};
+
+const struct gf100_gr_init
+gf100_gr_init_tex_0[] = {
+       { 0x419ab0,   1, 0x04, 0x00000000 },
+       { 0x419ab8,   1, 0x04, 0x000000e7 },
+       { 0x419abc,   2, 0x04, 0x00000000 },
+       {}
+};
+
+const struct gf100_gr_init
+gf100_gr_init_pe_0[] = {
+       { 0x41980c,   3, 0x04, 0x00000000 },
+       { 0x419844,   1, 0x04, 0x00000000 },
+       { 0x41984c,   1, 0x04, 0x00005bc5 },
+       { 0x419850,   4, 0x04, 0x00000000 },
+       {}
+};
+
+const struct gf100_gr_init
+gf100_gr_init_l1c_0[] = {
+       { 0x419c98,   1, 0x04, 0x00000000 },
+       { 0x419ca8,   1, 0x04, 0x80000000 },
+       { 0x419cb4,   1, 0x04, 0x00000000 },
+       { 0x419cb8,   1, 0x04, 0x00008bf4 },
+       { 0x419cbc,   1, 0x04, 0x28137606 },
+       { 0x419cc0,   2, 0x04, 0x00000000 },
+       {}
+};
+
+const struct gf100_gr_init
+gf100_gr_init_wwdx_0[] = {
+       { 0x419bd4,   1, 0x04, 0x00800000 },
+       { 0x419bdc,   1, 0x04, 0x00000000 },
+       {}
+};
+
+const struct gf100_gr_init
+gf100_gr_init_tpccs_1[] = {
+       { 0x419d2c,   1, 0x04, 0x00000000 },
+       {}
+};
+
+const struct gf100_gr_init
+gf100_gr_init_mpc_0[] = {
+       { 0x419c0c,   1, 0x04, 0x00000000 },
+       {}
+};
+
+static const struct gf100_gr_init
+gf100_gr_init_sm_0[] = {
+       { 0x419e00,   1, 0x04, 0x00000000 },
+       { 0x419ea0,   1, 0x04, 0x00000000 },
+       { 0x419ea4,   1, 0x04, 0x00000100 },
+       { 0x419ea8,   1, 0x04, 0x00001100 },
+       { 0x419eac,   1, 0x04, 0x11100702 },
+       { 0x419eb0,   1, 0x04, 0x00000003 },
+       { 0x419eb4,   4, 0x04, 0x00000000 },
+       { 0x419ec8,   1, 0x04, 0x06060618 },
+       { 0x419ed0,   1, 0x04, 0x0eff0e38 },
+       { 0x419ed4,   1, 0x04, 0x011104f1 },
+       { 0x419edc,   1, 0x04, 0x00000000 },
+       { 0x419f00,   1, 0x04, 0x00000000 },
+       { 0x419f2c,   1, 0x04, 0x00000000 },
+       {}
+};
+
+const struct gf100_gr_init
+gf100_gr_init_be_0[] = {
+       { 0x40880c,   1, 0x04, 0x00000000 },
+       { 0x408910,   9, 0x04, 0x00000000 },
+       { 0x408950,   1, 0x04, 0x00000000 },
+       { 0x408954,   1, 0x04, 0x0000ffff },
+       { 0x408984,   1, 0x04, 0x00000000 },
+       { 0x408988,   1, 0x04, 0x08040201 },
+       { 0x40898c,   1, 0x04, 0x80402010 },
+       {}
+};
+
+const struct gf100_gr_init
+gf100_gr_init_fe_1[] = {
+       { 0x4040f0,   1, 0x04, 0x00000000 },
+       {}
+};
+
+const struct gf100_gr_init
+gf100_gr_init_pe_1[] = {
+       { 0x419880,   1, 0x04, 0x00000002 },
+       {}
+};
+
+static const struct gf100_gr_pack
+gf100_gr_pack_mmio[] = {
+       { gf100_gr_init_main_0 },
+       { gf100_gr_init_fe_0 },
+       { gf100_gr_init_pri_0 },
+       { gf100_gr_init_rstr2d_0 },
+       { gf100_gr_init_pd_0 },
+       { gf100_gr_init_ds_0 },
+       { gf100_gr_init_scc_0 },
+       { gf100_gr_init_prop_0 },
+       { gf100_gr_init_gpc_unk_0 },
+       { gf100_gr_init_setup_0 },
+       { gf100_gr_init_crstr_0 },
+       { gf100_gr_init_setup_1 },
+       { gf100_gr_init_zcull_0 },
+       { gf100_gr_init_gpm_0 },
+       { gf100_gr_init_gpc_unk_1 },
+       { gf100_gr_init_gcc_0 },
+       { gf100_gr_init_tpccs_0 },
+       { gf100_gr_init_tex_0 },
+       { gf100_gr_init_pe_0 },
+       { gf100_gr_init_l1c_0 },
+       { gf100_gr_init_wwdx_0 },
+       { gf100_gr_init_tpccs_1 },
+       { gf100_gr_init_mpc_0 },
+       { gf100_gr_init_sm_0 },
+       { gf100_gr_init_be_0 },
+       { gf100_gr_init_fe_1 },
+       { gf100_gr_init_pe_1 },
+       {}
+};
+
+/*******************************************************************************
+ * PGRAPH engine/subdev functions
+ ******************************************************************************/
+
+void
+gf100_gr_zbc_init(struct gf100_gr_priv *priv)
+{
+       const u32  zero[] = { 0x00000000, 0x00000000, 0x00000000, 0x00000000,
+                             0x00000000, 0x00000000, 0x00000000, 0x00000000 };
+       const u32   one[] = { 0x3f800000, 0x3f800000, 0x3f800000, 0x3f800000,
+                             0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff };
+       const u32 f32_0[] = { 0x00000000, 0x00000000, 0x00000000, 0x00000000,
+                             0x00000000, 0x00000000, 0x00000000, 0x00000000 };
+       const u32 f32_1[] = { 0x3f800000, 0x3f800000, 0x3f800000, 0x3f800000,
+                             0x3f800000, 0x3f800000, 0x3f800000, 0x3f800000 };
+       struct nvkm_ltc *ltc = nvkm_ltc(priv);
+       int index;
+
+       if (!priv->zbc_color[0].format) {
+               gf100_gr_zbc_color_get(priv, 1,  & zero[0],   &zero[4]);
+               gf100_gr_zbc_color_get(priv, 2,  &  one[0],    &one[4]);
+               gf100_gr_zbc_color_get(priv, 4,  &f32_0[0],  &f32_0[4]);
+               gf100_gr_zbc_color_get(priv, 4,  &f32_1[0],  &f32_1[4]);
+               gf100_gr_zbc_depth_get(priv, 1, 0x00000000, 0x00000000);
+               gf100_gr_zbc_depth_get(priv, 1, 0x3f800000, 0x3f800000);
+       }
+
+       for (index = ltc->zbc_min; index <= ltc->zbc_max; index++)
+               gf100_gr_zbc_clear_color(priv, index);
+       for (index = ltc->zbc_min; index <= ltc->zbc_max; index++)
+               gf100_gr_zbc_clear_depth(priv, index);
+}
+
+void
+gf100_gr_mmio(struct gf100_gr_priv *priv, const struct gf100_gr_pack *p)
+{
+       const struct gf100_gr_pack *pack;
+       const struct gf100_gr_init *init;
+
+       pack_for_each_init(init, pack, p) {
+               u32 next = init->addr + init->count * init->pitch;
+               u32 addr = init->addr;
+               while (addr < next) {
+                       nv_wr32(priv, addr, init->data);
+                       addr += init->pitch;
+               }
+       }
+}
+
+void
+gf100_gr_icmd(struct gf100_gr_priv *priv, const struct gf100_gr_pack *p)
+{
+       const struct gf100_gr_pack *pack;
+       const struct gf100_gr_init *init;
+       u32 data = 0;
+
+       nv_wr32(priv, 0x400208, 0x80000000);
+
+       pack_for_each_init(init, pack, p) {
+               u32 next = init->addr + init->count * init->pitch;
+               u32 addr = init->addr;
+
+               if ((pack == p && init == p->init) || data != init->data) {
+                       nv_wr32(priv, 0x400204, init->data);
+                       data = init->data;
+               }
+
+               while (addr < next) {
+                       nv_wr32(priv, 0x400200, addr);
+                       nv_wait(priv, 0x400700, 0x00000002, 0x00000000);
+                       addr += init->pitch;
+               }
+       }
+
+       nv_wr32(priv, 0x400208, 0x00000000);
+}
+
+void
+gf100_gr_mthd(struct gf100_gr_priv *priv, const struct gf100_gr_pack *p)
+{
+       const struct gf100_gr_pack *pack;
+       const struct gf100_gr_init *init;
+       u32 data = 0;
+
+       pack_for_each_init(init, pack, p) {
+               u32 ctrl = 0x80000000 | pack->type;
+               u32 next = init->addr + init->count * init->pitch;
+               u32 addr = init->addr;
+
+               if ((pack == p && init == p->init) || data != init->data) {
+                       nv_wr32(priv, 0x40448c, init->data);
+                       data = init->data;
+               }
+
+               while (addr < next) {
+                       nv_wr32(priv, 0x404488, ctrl | (addr << 14));
+                       addr += init->pitch;
+               }
+       }
+}
+
+u64
+gf100_gr_units(struct nvkm_gr *gr)
+{
+       struct gf100_gr_priv *priv = (void *)gr;
+       u64 cfg;
+
+       cfg  = (u32)priv->gpc_nr;
+       cfg |= (u32)priv->tpc_total << 8;
+       cfg |= (u64)priv->rop_nr << 32;
+
+       return cfg;
+}
+
+static const struct nvkm_enum gk104_sked_error[] = {
+       { 7, "CONSTANT_BUFFER_SIZE" },
+       { 9, "LOCAL_MEMORY_SIZE_POS" },
+       { 10, "LOCAL_MEMORY_SIZE_NEG" },
+       { 11, "WARP_CSTACK_SIZE" },
+       { 12, "TOTAL_TEMP_SIZE" },
+       { 13, "REGISTER_COUNT" },
+       { 18, "TOTAL_THREADS" },
+       { 20, "PROGRAM_OFFSET" },
+       { 21, "SHARED_MEMORY_SIZE" },
+       { 25, "SHARED_CONFIG_TOO_SMALL" },
+       { 26, "TOTAL_REGISTER_COUNT" },
+       {}
+};
+
+static const struct nvkm_enum gf100_gpc_rop_error[] = {
+       { 1, "RT_PITCH_OVERRUN" },
+       { 4, "RT_WIDTH_OVERRUN" },
+       { 5, "RT_HEIGHT_OVERRUN" },
+       { 7, "ZETA_STORAGE_TYPE_MISMATCH" },
+       { 8, "RT_STORAGE_TYPE_MISMATCH" },
+       { 10, "RT_LINEAR_MISMATCH" },
+       {}
+};
+
+static void
+gf100_gr_trap_gpc_rop(struct gf100_gr_priv *priv, int gpc)
+{
+       u32 trap[4];
+       int i;
+
+       trap[0] = nv_rd32(priv, GPC_UNIT(gpc, 0x0420));
+       trap[1] = nv_rd32(priv, GPC_UNIT(gpc, 0x0434));
+       trap[2] = nv_rd32(priv, GPC_UNIT(gpc, 0x0438));
+       trap[3] = nv_rd32(priv, GPC_UNIT(gpc, 0x043c));
+
+       nv_error(priv, "GPC%d/PROP trap:", gpc);
+       for (i = 0; i <= 29; ++i) {
+               if (!(trap[0] & (1 << i)))
+                       continue;
+               pr_cont(" ");
+               nvkm_enum_print(gf100_gpc_rop_error, i);
+       }
+       pr_cont("\n");
+
+       nv_error(priv, "x = %u, y = %u, format = %x, storage type = %x\n",
+                trap[1] & 0xffff, trap[1] >> 16, (trap[2] >> 8) & 0x3f,
+                trap[3] & 0xff);
+       nv_wr32(priv, GPC_UNIT(gpc, 0x0420), 0xc0000000);
+}
+
+static const struct nvkm_enum gf100_mp_warp_error[] = {
+       { 0x00, "NO_ERROR" },
+       { 0x01, "STACK_MISMATCH" },
+       { 0x05, "MISALIGNED_PC" },
+       { 0x08, "MISALIGNED_GPR" },
+       { 0x09, "INVALID_OPCODE" },
+       { 0x0d, "GPR_OUT_OF_BOUNDS" },
+       { 0x0e, "MEM_OUT_OF_BOUNDS" },
+       { 0x0f, "UNALIGNED_MEM_ACCESS" },
+       { 0x11, "INVALID_PARAM" },
+       {}
+};
+
+static const struct nvkm_bitfield gf100_mp_global_error[] = {
+       { 0x00000004, "MULTIPLE_WARP_ERRORS" },
+       { 0x00000008, "OUT_OF_STACK_SPACE" },
+       {}
+};
+
+static void
+gf100_gr_trap_mp(struct gf100_gr_priv *priv, int gpc, int tpc)
+{
+       u32 werr = nv_rd32(priv, TPC_UNIT(gpc, tpc, 0x648));
+       u32 gerr = nv_rd32(priv, TPC_UNIT(gpc, tpc, 0x650));
+
+       nv_error(priv, "GPC%i/TPC%i/MP trap:", gpc, tpc);
+       nvkm_bitfield_print(gf100_mp_global_error, gerr);
+       if (werr) {
+               pr_cont(" ");
+               nvkm_enum_print(gf100_mp_warp_error, werr & 0xffff);
+       }
+       pr_cont("\n");
+
+       nv_wr32(priv, TPC_UNIT(gpc, tpc, 0x648), 0x00000000);
+       nv_wr32(priv, TPC_UNIT(gpc, tpc, 0x650), gerr);
+}
+
+static void
+gf100_gr_trap_tpc(struct gf100_gr_priv *priv, int gpc, int tpc)
+{
+       u32 stat = nv_rd32(priv, TPC_UNIT(gpc, tpc, 0x0508));
+
+       if (stat & 0x00000001) {
+               u32 trap = nv_rd32(priv, TPC_UNIT(gpc, tpc, 0x0224));
+               nv_error(priv, "GPC%d/TPC%d/TEX: 0x%08x\n", gpc, tpc, trap);
+               nv_wr32(priv, TPC_UNIT(gpc, tpc, 0x0224), 0xc0000000);
+               stat &= ~0x00000001;
+       }
+
+       if (stat & 0x00000002) {
+               gf100_gr_trap_mp(priv, gpc, tpc);
+               stat &= ~0x00000002;
+       }
+
+       if (stat & 0x00000004) {
+               u32 trap = nv_rd32(priv, TPC_UNIT(gpc, tpc, 0x0084));
+               nv_error(priv, "GPC%d/TPC%d/POLY: 0x%08x\n", gpc, tpc, trap);
+               nv_wr32(priv, TPC_UNIT(gpc, tpc, 0x0084), 0xc0000000);
+               stat &= ~0x00000004;
+       }
+
+       if (stat & 0x00000008) {
+               u32 trap = nv_rd32(priv, TPC_UNIT(gpc, tpc, 0x048c));
+               nv_error(priv, "GPC%d/TPC%d/L1C: 0x%08x\n", gpc, tpc, trap);
+               nv_wr32(priv, TPC_UNIT(gpc, tpc, 0x048c), 0xc0000000);
+               stat &= ~0x00000008;
+       }
+
+       if (stat) {
+               nv_error(priv, "GPC%d/TPC%d/0x%08x: unknown\n", gpc, tpc, stat);
+       }
+}
+
+static void
+gf100_gr_trap_gpc(struct gf100_gr_priv *priv, int gpc)
+{
+       u32 stat = nv_rd32(priv, GPC_UNIT(gpc, 0x2c90));
+       int tpc;
+
+       if (stat & 0x00000001) {
+               gf100_gr_trap_gpc_rop(priv, gpc);
+               stat &= ~0x00000001;
+       }
+
+       if (stat & 0x00000002) {
+               u32 trap = nv_rd32(priv, GPC_UNIT(gpc, 0x0900));
+               nv_error(priv, "GPC%d/ZCULL: 0x%08x\n", gpc, trap);
+               nv_wr32(priv, GPC_UNIT(gpc, 0x0900), 0xc0000000);
+               stat &= ~0x00000002;
+       }
+
+       if (stat & 0x00000004) {
+               u32 trap = nv_rd32(priv, GPC_UNIT(gpc, 0x1028));
+               nv_error(priv, "GPC%d/CCACHE: 0x%08x\n", gpc, trap);
+               nv_wr32(priv, GPC_UNIT(gpc, 0x1028), 0xc0000000);
+               stat &= ~0x00000004;
+       }
+
+       if (stat & 0x00000008) {
+               u32 trap = nv_rd32(priv, GPC_UNIT(gpc, 0x0824));
+               nv_error(priv, "GPC%d/ESETUP: 0x%08x\n", gpc, trap);
+               nv_wr32(priv, GPC_UNIT(gpc, 0x0824), 0xc0000000);
+               stat &= ~0x00000009;
+       }
+
+       for (tpc = 0; tpc < priv->tpc_nr[gpc]; tpc++) {
+               u32 mask = 0x00010000 << tpc;
+               if (stat & mask) {
+                       gf100_gr_trap_tpc(priv, gpc, tpc);
+                       nv_wr32(priv, GPC_UNIT(gpc, 0x2c90), mask);
+                       stat &= ~mask;
+               }
+       }
+
+       if (stat) {
+               nv_error(priv, "GPC%d/0x%08x: unknown\n", gpc, stat);
+       }
+}
+
+static void
+gf100_gr_trap_intr(struct gf100_gr_priv *priv)
+{
+       u32 trap = nv_rd32(priv, 0x400108);
+       int rop, gpc, i;
+
+       if (trap & 0x00000001) {
+               u32 stat = nv_rd32(priv, 0x404000);
+               nv_error(priv, "DISPATCH 0x%08x\n", stat);
+               nv_wr32(priv, 0x404000, 0xc0000000);
+               nv_wr32(priv, 0x400108, 0x00000001);
+               trap &= ~0x00000001;
+       }
+
+       if (trap & 0x00000002) {
+               u32 stat = nv_rd32(priv, 0x404600);
+               nv_error(priv, "M2MF 0x%08x\n", stat);
+               nv_wr32(priv, 0x404600, 0xc0000000);
+               nv_wr32(priv, 0x400108, 0x00000002);
+               trap &= ~0x00000002;
+       }
+
+       if (trap & 0x00000008) {
+               u32 stat = nv_rd32(priv, 0x408030);
+               nv_error(priv, "CCACHE 0x%08x\n", stat);
+               nv_wr32(priv, 0x408030, 0xc0000000);
+               nv_wr32(priv, 0x400108, 0x00000008);
+               trap &= ~0x00000008;
+       }
+
+       if (trap & 0x00000010) {
+               u32 stat = nv_rd32(priv, 0x405840);
+               nv_error(priv, "SHADER 0x%08x\n", stat);
+               nv_wr32(priv, 0x405840, 0xc0000000);
+               nv_wr32(priv, 0x400108, 0x00000010);
+               trap &= ~0x00000010;
+       }
+
+       if (trap & 0x00000040) {
+               u32 stat = nv_rd32(priv, 0x40601c);
+               nv_error(priv, "UNK6 0x%08x\n", stat);
+               nv_wr32(priv, 0x40601c, 0xc0000000);
+               nv_wr32(priv, 0x400108, 0x00000040);
+               trap &= ~0x00000040;
+       }
+
+       if (trap & 0x00000080) {
+               u32 stat = nv_rd32(priv, 0x404490);
+               nv_error(priv, "MACRO 0x%08x\n", stat);
+               nv_wr32(priv, 0x404490, 0xc0000000);
+               nv_wr32(priv, 0x400108, 0x00000080);
+               trap &= ~0x00000080;
+       }
+
+       if (trap & 0x00000100) {
+               u32 stat = nv_rd32(priv, 0x407020);
+
+               nv_error(priv, "SKED:");
+               for (i = 0; i <= 29; ++i) {
+                       if (!(stat & (1 << i)))
+                               continue;
+                       pr_cont(" ");
+                       nvkm_enum_print(gk104_sked_error, i);
+               }
+               pr_cont("\n");
+
+               if (stat & 0x3fffffff)
+                       nv_wr32(priv, 0x407020, 0x40000000);
+               nv_wr32(priv, 0x400108, 0x00000100);
+               trap &= ~0x00000100;
+       }
+
+       if (trap & 0x01000000) {
+               u32 stat = nv_rd32(priv, 0x400118);
+               for (gpc = 0; stat && gpc < priv->gpc_nr; gpc++) {
+                       u32 mask = 0x00000001 << gpc;
+                       if (stat & mask) {
+                               gf100_gr_trap_gpc(priv, gpc);
+                               nv_wr32(priv, 0x400118, mask);
+                               stat &= ~mask;
+                       }
+               }
+               nv_wr32(priv, 0x400108, 0x01000000);
+               trap &= ~0x01000000;
+       }
+
+       if (trap & 0x02000000) {
+               for (rop = 0; rop < priv->rop_nr; rop++) {
+                       u32 statz = nv_rd32(priv, ROP_UNIT(rop, 0x070));
+                       u32 statc = nv_rd32(priv, ROP_UNIT(rop, 0x144));
+                       nv_error(priv, "ROP%d 0x%08x 0x%08x\n",
+                                rop, statz, statc);
+                       nv_wr32(priv, ROP_UNIT(rop, 0x070), 0xc0000000);
+                       nv_wr32(priv, ROP_UNIT(rop, 0x144), 0xc0000000);
+               }
+               nv_wr32(priv, 0x400108, 0x02000000);
+               trap &= ~0x02000000;
+       }
+
+       if (trap) {
+               nv_error(priv, "TRAP UNHANDLED 0x%08x\n", trap);
+               nv_wr32(priv, 0x400108, trap);
+       }
+}
+
+static void
+gf100_gr_ctxctl_debug_unit(struct gf100_gr_priv *priv, u32 base)
+{
+       nv_error(priv, "%06x - done 0x%08x\n", base,
+                nv_rd32(priv, base + 0x400));
+       nv_error(priv, "%06x - stat 0x%08x 0x%08x 0x%08x 0x%08x\n", base,
+                nv_rd32(priv, base + 0x800), nv_rd32(priv, base + 0x804),
+                nv_rd32(priv, base + 0x808), nv_rd32(priv, base + 0x80c));
+       nv_error(priv, "%06x - stat 0x%08x 0x%08x 0x%08x 0x%08x\n", base,
+                nv_rd32(priv, base + 0x810), nv_rd32(priv, base + 0x814),
+                nv_rd32(priv, base + 0x818), nv_rd32(priv, base + 0x81c));
+}
+
+void
+gf100_gr_ctxctl_debug(struct gf100_gr_priv *priv)
+{
+       u32 gpcnr = nv_rd32(priv, 0x409604) & 0xffff;
+       u32 gpc;
+
+       gf100_gr_ctxctl_debug_unit(priv, 0x409000);
+       for (gpc = 0; gpc < gpcnr; gpc++)
+               gf100_gr_ctxctl_debug_unit(priv, 0x502000 + (gpc * 0x8000));
+}
+
+static void
+gf100_gr_ctxctl_isr(struct gf100_gr_priv *priv)
+{
+       u32 stat = nv_rd32(priv, 0x409c18);
+
+       if (stat & 0x00000001) {
+               u32 code = nv_rd32(priv, 0x409814);
+               if (code == E_BAD_FWMTHD) {
+                       u32 class = nv_rd32(priv, 0x409808);
+                       u32  addr = nv_rd32(priv, 0x40980c);
+                       u32  subc = (addr & 0x00070000) >> 16;
+                       u32  mthd = (addr & 0x00003ffc);
+                       u32  data = nv_rd32(priv, 0x409810);
+
+                       nv_error(priv, "FECS MTHD subc %d class 0x%04x "
+                                      "mthd 0x%04x data 0x%08x\n",
+                                subc, class, mthd, data);
+
+                       nv_wr32(priv, 0x409c20, 0x00000001);
+                       stat &= ~0x00000001;
+               } else {
+                       nv_error(priv, "FECS ucode error %d\n", code);
+               }
+       }
+
+       if (stat & 0x00080000) {
+               nv_error(priv, "FECS watchdog timeout\n");
+               gf100_gr_ctxctl_debug(priv);
+               nv_wr32(priv, 0x409c20, 0x00080000);
+               stat &= ~0x00080000;
+       }
+
+       if (stat) {
+               nv_error(priv, "FECS 0x%08x\n", stat);
+               gf100_gr_ctxctl_debug(priv);
+               nv_wr32(priv, 0x409c20, stat);
+       }
+}
+
+static void
+gf100_gr_intr(struct nvkm_subdev *subdev)
+{
+       struct nvkm_fifo *pfifo = nvkm_fifo(subdev);
+       struct nvkm_engine *engine = nv_engine(subdev);
+       struct nvkm_object *engctx;
+       struct nvkm_handle *handle;
+       struct gf100_gr_priv *priv = (void *)subdev;
+       u64 inst = nv_rd32(priv, 0x409b00) & 0x0fffffff;
+       u32 stat = nv_rd32(priv, 0x400100);
+       u32 addr = nv_rd32(priv, 0x400704);
+       u32 mthd = (addr & 0x00003ffc);
+       u32 subc = (addr & 0x00070000) >> 16;
+       u32 data = nv_rd32(priv, 0x400708);
+       u32 code = nv_rd32(priv, 0x400110);
+       u32 class = nv_rd32(priv, 0x404200 + (subc * 4));
+       int chid;
+
+       engctx = nvkm_engctx_get(engine, inst);
+       chid   = pfifo->chid(pfifo, engctx);
+
+       if (stat & 0x00000010) {
+               handle = nvkm_handle_get_class(engctx, class);
+               if (!handle || nv_call(handle->object, mthd, data)) {
+                       nv_error(priv,
+                                "ILLEGAL_MTHD ch %d [0x%010llx %s] subc %d class 0x%04x mthd 0x%04x data 0x%08x\n",
+                                chid, inst << 12, nvkm_client_name(engctx),
+                                subc, class, mthd, data);
+               }
+               nvkm_handle_put(handle);
+               nv_wr32(priv, 0x400100, 0x00000010);
+               stat &= ~0x00000010;
+       }
+
+       if (stat & 0x00000020) {
+               nv_error(priv,
+                        "ILLEGAL_CLASS ch %d [0x%010llx %s] subc %d class 0x%04x mthd 0x%04x data 0x%08x\n",
+                        chid, inst << 12, nvkm_client_name(engctx), subc,
+                        class, mthd, data);
+               nv_wr32(priv, 0x400100, 0x00000020);
+               stat &= ~0x00000020;
+       }
+
+       if (stat & 0x00100000) {
+               nv_error(priv, "DATA_ERROR [");
+               nvkm_enum_print(nv50_data_error_names, code);
+               pr_cont("] ch %d [0x%010llx %s] subc %d class 0x%04x mthd 0x%04x data 0x%08x\n",
+                       chid, inst << 12, nvkm_client_name(engctx), subc,
+                       class, mthd, data);
+               nv_wr32(priv, 0x400100, 0x00100000);
+               stat &= ~0x00100000;
+       }
+
+       if (stat & 0x00200000) {
+               nv_error(priv, "TRAP ch %d [0x%010llx %s]\n", chid, inst << 12,
+                        nvkm_client_name(engctx));
+               gf100_gr_trap_intr(priv);
+               nv_wr32(priv, 0x400100, 0x00200000);
+               stat &= ~0x00200000;
+       }
+
+       if (stat & 0x00080000) {
+               gf100_gr_ctxctl_isr(priv);
+               nv_wr32(priv, 0x400100, 0x00080000);
+               stat &= ~0x00080000;
+       }
+
+       if (stat) {
+               nv_error(priv, "unknown stat 0x%08x\n", stat);
+               nv_wr32(priv, 0x400100, stat);
+       }
+
+       nv_wr32(priv, 0x400500, 0x00010001);
+       nvkm_engctx_put(engctx);
+}
+
+void
+gf100_gr_init_fw(struct gf100_gr_priv *priv, u32 fuc_base,
+                struct gf100_gr_fuc *code, struct gf100_gr_fuc *data)
+{
+       int i;
+
+       nv_wr32(priv, fuc_base + 0x01c0, 0x01000000);
+       for (i = 0; i < data->size / 4; i++)
+               nv_wr32(priv, fuc_base + 0x01c4, data->data[i]);
+
+       nv_wr32(priv, fuc_base + 0x0180, 0x01000000);
+       for (i = 0; i < code->size / 4; i++) {
+               if ((i & 0x3f) == 0)
+                       nv_wr32(priv, fuc_base + 0x0188, i >> 6);
+               nv_wr32(priv, fuc_base + 0x0184, code->data[i]);
+       }
+
+       /* code must be padded to 0x40 words */
+       for (; i & 0x3f; i++)
+               nv_wr32(priv, fuc_base + 0x0184, 0);
+}
+
+static void
+gf100_gr_init_csdata(struct gf100_gr_priv *priv,
+                    const struct gf100_gr_pack *pack,
+                    u32 falcon, u32 starstar, u32 base)
+{
+       const struct gf100_gr_pack *iter;
+       const struct gf100_gr_init *init;
+       u32 addr = ~0, prev = ~0, xfer = 0;
+       u32 star, temp;
+
+       nv_wr32(priv, falcon + 0x01c0, 0x02000000 + starstar);
+       star = nv_rd32(priv, falcon + 0x01c4);
+       temp = nv_rd32(priv, falcon + 0x01c4);
+       if (temp > star)
+               star = temp;
+       nv_wr32(priv, falcon + 0x01c0, 0x01000000 + star);
+
+       pack_for_each_init(init, iter, pack) {
+               u32 head = init->addr - base;
+               u32 tail = head + init->count * init->pitch;
+               while (head < tail) {
+                       if (head != prev + 4 || xfer >= 32) {
+                               if (xfer) {
+                                       u32 data = ((--xfer << 26) | addr);
+                                       nv_wr32(priv, falcon + 0x01c4, data);
+                                       star += 4;
+                               }
+                               addr = head;
+                               xfer = 0;
+                       }
+                       prev = head;
+                       xfer = xfer + 1;
+                       head = head + init->pitch;
+               }
+       }
+
+       nv_wr32(priv, falcon + 0x01c4, (--xfer << 26) | addr);
+       nv_wr32(priv, falcon + 0x01c0, 0x01000004 + starstar);
+       nv_wr32(priv, falcon + 0x01c4, star + 4);
+}
+
+int
+gf100_gr_init_ctxctl(struct gf100_gr_priv *priv)
+{
+       struct gf100_gr_oclass *oclass = (void *)nv_object(priv)->oclass;
+       struct gf100_grctx_oclass *cclass = (void *)nv_engine(priv)->cclass;
+       int i;
+
+       if (priv->firmware) {
+               /* load fuc microcode */
+               nvkm_mc(priv)->unk260(nvkm_mc(priv), 0);
+               gf100_gr_init_fw(priv, 0x409000, &priv->fuc409c,
+                                                &priv->fuc409d);
+               gf100_gr_init_fw(priv, 0x41a000, &priv->fuc41ac,
+                                                &priv->fuc41ad);
+               nvkm_mc(priv)->unk260(nvkm_mc(priv), 1);
+
+               /* start both of them running */
+               nv_wr32(priv, 0x409840, 0xffffffff);
+               nv_wr32(priv, 0x41a10c, 0x00000000);
+               nv_wr32(priv, 0x40910c, 0x00000000);
+               nv_wr32(priv, 0x41a100, 0x00000002);
+               nv_wr32(priv, 0x409100, 0x00000002);
+               if (!nv_wait(priv, 0x409800, 0x00000001, 0x00000001))
+                       nv_warn(priv, "0x409800 wait failed\n");
+
+               nv_wr32(priv, 0x409840, 0xffffffff);
+               nv_wr32(priv, 0x409500, 0x7fffffff);
+               nv_wr32(priv, 0x409504, 0x00000021);
+
+               nv_wr32(priv, 0x409840, 0xffffffff);
+               nv_wr32(priv, 0x409500, 0x00000000);
+               nv_wr32(priv, 0x409504, 0x00000010);
+               if (!nv_wait_ne(priv, 0x409800, 0xffffffff, 0x00000000)) {
+                       nv_error(priv, "fuc09 req 0x10 timeout\n");
+                       return -EBUSY;
+               }
+               priv->size = nv_rd32(priv, 0x409800);
+
+               nv_wr32(priv, 0x409840, 0xffffffff);
+               nv_wr32(priv, 0x409500, 0x00000000);
+               nv_wr32(priv, 0x409504, 0x00000016);
+               if (!nv_wait_ne(priv, 0x409800, 0xffffffff, 0x00000000)) {
+                       nv_error(priv, "fuc09 req 0x16 timeout\n");
+                       return -EBUSY;
+               }
+
+               nv_wr32(priv, 0x409840, 0xffffffff);
+               nv_wr32(priv, 0x409500, 0x00000000);
+               nv_wr32(priv, 0x409504, 0x00000025);
+               if (!nv_wait_ne(priv, 0x409800, 0xffffffff, 0x00000000)) {
+                       nv_error(priv, "fuc09 req 0x25 timeout\n");
+                       return -EBUSY;
+               }
+
+               if (nv_device(priv)->chipset >= 0xe0) {
+                       nv_wr32(priv, 0x409800, 0x00000000);
+                       nv_wr32(priv, 0x409500, 0x00000001);
+                       nv_wr32(priv, 0x409504, 0x00000030);
+                       if (!nv_wait_ne(priv, 0x409800, 0xffffffff, 0x00000000)) {
+                               nv_error(priv, "fuc09 req 0x30 timeout\n");
+                               return -EBUSY;
+                       }
+
+                       nv_wr32(priv, 0x409810, 0xb00095c8);
+                       nv_wr32(priv, 0x409800, 0x00000000);
+                       nv_wr32(priv, 0x409500, 0x00000001);
+                       nv_wr32(priv, 0x409504, 0x00000031);
+                       if (!nv_wait_ne(priv, 0x409800, 0xffffffff, 0x00000000)) {
+                               nv_error(priv, "fuc09 req 0x31 timeout\n");
+                               return -EBUSY;
+                       }
+
+                       nv_wr32(priv, 0x409810, 0x00080420);
+                       nv_wr32(priv, 0x409800, 0x00000000);
+                       nv_wr32(priv, 0x409500, 0x00000001);
+                       nv_wr32(priv, 0x409504, 0x00000032);
+                       if (!nv_wait_ne(priv, 0x409800, 0xffffffff, 0x00000000)) {
+                               nv_error(priv, "fuc09 req 0x32 timeout\n");
+                               return -EBUSY;
+                       }
+
+                       nv_wr32(priv, 0x409614, 0x00000070);
+                       nv_wr32(priv, 0x409614, 0x00000770);
+                       nv_wr32(priv, 0x40802c, 0x00000001);
+               }
+
+               if (priv->data == NULL) {
+                       int ret = gf100_grctx_generate(priv);
+                       if (ret) {
+                               nv_error(priv, "failed to construct context\n");
+                               return ret;
+                       }
+               }
+
+               return 0;
+       } else
+       if (!oclass->fecs.ucode) {
+               return -ENOSYS;
+       }
+
+       /* load HUB microcode */
+       nvkm_mc(priv)->unk260(nvkm_mc(priv), 0);
+       nv_wr32(priv, 0x4091c0, 0x01000000);
+       for (i = 0; i < oclass->fecs.ucode->data.size / 4; i++)
+               nv_wr32(priv, 0x4091c4, oclass->fecs.ucode->data.data[i]);
+
+       nv_wr32(priv, 0x409180, 0x01000000);
+       for (i = 0; i < oclass->fecs.ucode->code.size / 4; i++) {
+               if ((i & 0x3f) == 0)
+                       nv_wr32(priv, 0x409188, i >> 6);
+               nv_wr32(priv, 0x409184, oclass->fecs.ucode->code.data[i]);
+       }
+
+       /* load GPC microcode */
+       nv_wr32(priv, 0x41a1c0, 0x01000000);
+       for (i = 0; i < oclass->gpccs.ucode->data.size / 4; i++)
+               nv_wr32(priv, 0x41a1c4, oclass->gpccs.ucode->data.data[i]);
+
+       nv_wr32(priv, 0x41a180, 0x01000000);
+       for (i = 0; i < oclass->gpccs.ucode->code.size / 4; i++) {
+               if ((i & 0x3f) == 0)
+                       nv_wr32(priv, 0x41a188, i >> 6);
+               nv_wr32(priv, 0x41a184, oclass->gpccs.ucode->code.data[i]);
+       }
+       nvkm_mc(priv)->unk260(nvkm_mc(priv), 1);
+
+       /* load register lists */
+       gf100_gr_init_csdata(priv, cclass->hub, 0x409000, 0x000, 0x000000);
+       gf100_gr_init_csdata(priv, cclass->gpc, 0x41a000, 0x000, 0x418000);
+       gf100_gr_init_csdata(priv, cclass->tpc, 0x41a000, 0x004, 0x419800);
+       gf100_gr_init_csdata(priv, cclass->ppc, 0x41a000, 0x008, 0x41be00);
+
+       /* start HUB ucode running, it'll init the GPCs */
+       nv_wr32(priv, 0x40910c, 0x00000000);
+       nv_wr32(priv, 0x409100, 0x00000002);
+       if (!nv_wait(priv, 0x409800, 0x80000000, 0x80000000)) {
+               nv_error(priv, "HUB_INIT timed out\n");
+               gf100_gr_ctxctl_debug(priv);
+               return -EBUSY;
+       }
+
+       priv->size = nv_rd32(priv, 0x409804);
+       if (priv->data == NULL) {
+               int ret = gf100_grctx_generate(priv);
+               if (ret) {
+                       nv_error(priv, "failed to construct context\n");
+                       return ret;
+               }
+       }
+
+       return 0;
+}
+
+int
+gf100_gr_init(struct nvkm_object *object)
+{
+       struct gf100_gr_oclass *oclass = (void *)object->oclass;
+       struct gf100_gr_priv *priv = (void *)object;
+       const u32 magicgpc918 = DIV_ROUND_UP(0x00800000, priv->tpc_total);
+       u32 data[TPC_MAX / 8] = {};
+       u8  tpcnr[GPC_MAX];
+       int gpc, tpc, rop;
+       int ret, i;
+
+       ret = nvkm_gr_init(&priv->base);
+       if (ret)
+               return ret;
+
+       nv_wr32(priv, GPC_BCAST(0x0880), 0x00000000);
+       nv_wr32(priv, GPC_BCAST(0x08a4), 0x00000000);
+       nv_wr32(priv, GPC_BCAST(0x0888), 0x00000000);
+       nv_wr32(priv, GPC_BCAST(0x088c), 0x00000000);
+       nv_wr32(priv, GPC_BCAST(0x0890), 0x00000000);
+       nv_wr32(priv, GPC_BCAST(0x0894), 0x00000000);
+       nv_wr32(priv, GPC_BCAST(0x08b4), priv->unk4188b4->addr >> 8);
+       nv_wr32(priv, GPC_BCAST(0x08b8), priv->unk4188b8->addr >> 8);
+
+       gf100_gr_mmio(priv, oclass->mmio);
+
+       memcpy(tpcnr, priv->tpc_nr, sizeof(priv->tpc_nr));
+       for (i = 0, gpc = -1; i < priv->tpc_total; i++) {
+               do {
+                       gpc = (gpc + 1) % priv->gpc_nr;
+               } while (!tpcnr[gpc]);
+               tpc = priv->tpc_nr[gpc] - tpcnr[gpc]--;
+
+               data[i / 8] |= tpc << ((i % 8) * 4);
+       }
+
+       nv_wr32(priv, GPC_BCAST(0x0980), data[0]);
+       nv_wr32(priv, GPC_BCAST(0x0984), data[1]);
+       nv_wr32(priv, GPC_BCAST(0x0988), data[2]);
+       nv_wr32(priv, GPC_BCAST(0x098c), data[3]);
+
+       for (gpc = 0; gpc < priv->gpc_nr; gpc++) {
+               nv_wr32(priv, GPC_UNIT(gpc, 0x0914),
+                       priv->magic_not_rop_nr << 8 | priv->tpc_nr[gpc]);
+               nv_wr32(priv, GPC_UNIT(gpc, 0x0910), 0x00040000 |
+                       priv->tpc_total);
+               nv_wr32(priv, GPC_UNIT(gpc, 0x0918), magicgpc918);
+       }
+
+       if (nv_device(priv)->chipset != 0xd7)
+               nv_wr32(priv, GPC_BCAST(0x1bd4), magicgpc918);
+       else
+               nv_wr32(priv, GPC_BCAST(0x3fd4), magicgpc918);
+
+       nv_wr32(priv, GPC_BCAST(0x08ac), nv_rd32(priv, 0x100800));
+
+       nv_wr32(priv, 0x400500, 0x00010001);
+
+       nv_wr32(priv, 0x400100, 0xffffffff);
+       nv_wr32(priv, 0x40013c, 0xffffffff);
+
+       nv_wr32(priv, 0x409c24, 0x000f0000);
+       nv_wr32(priv, 0x404000, 0xc0000000);
+       nv_wr32(priv, 0x404600, 0xc0000000);
+       nv_wr32(priv, 0x408030, 0xc0000000);
+       nv_wr32(priv, 0x40601c, 0xc0000000);
+       nv_wr32(priv, 0x404490, 0xc0000000);
+       nv_wr32(priv, 0x406018, 0xc0000000);
+       nv_wr32(priv, 0x405840, 0xc0000000);
+       nv_wr32(priv, 0x405844, 0x00ffffff);
+       nv_mask(priv, 0x419cc0, 0x00000008, 0x00000008);
+       nv_mask(priv, 0x419eb4, 0x00001000, 0x00001000);
+
+       for (gpc = 0; gpc < priv->gpc_nr; gpc++) {
+               nv_wr32(priv, GPC_UNIT(gpc, 0x0420), 0xc0000000);
+               nv_wr32(priv, GPC_UNIT(gpc, 0x0900), 0xc0000000);
+               nv_wr32(priv, GPC_UNIT(gpc, 0x1028), 0xc0000000);
+               nv_wr32(priv, GPC_UNIT(gpc, 0x0824), 0xc0000000);
+               for (tpc = 0; tpc < priv->tpc_nr[gpc]; tpc++) {
+                       nv_wr32(priv, TPC_UNIT(gpc, tpc, 0x508), 0xffffffff);
+                       nv_wr32(priv, TPC_UNIT(gpc, tpc, 0x50c), 0xffffffff);
+                       nv_wr32(priv, TPC_UNIT(gpc, tpc, 0x224), 0xc0000000);
+                       nv_wr32(priv, TPC_UNIT(gpc, tpc, 0x48c), 0xc0000000);
+                       nv_wr32(priv, TPC_UNIT(gpc, tpc, 0x084), 0xc0000000);
+                       nv_wr32(priv, TPC_UNIT(gpc, tpc, 0x644), 0x001ffffe);
+                       nv_wr32(priv, TPC_UNIT(gpc, tpc, 0x64c), 0x0000000f);
+               }
+               nv_wr32(priv, GPC_UNIT(gpc, 0x2c90), 0xffffffff);
+               nv_wr32(priv, GPC_UNIT(gpc, 0x2c94), 0xffffffff);
+       }
+
+       for (rop = 0; rop < priv->rop_nr; rop++) {
+               nv_wr32(priv, ROP_UNIT(rop, 0x144), 0xc0000000);
+               nv_wr32(priv, ROP_UNIT(rop, 0x070), 0xc0000000);
+               nv_wr32(priv, ROP_UNIT(rop, 0x204), 0xffffffff);
+               nv_wr32(priv, ROP_UNIT(rop, 0x208), 0xffffffff);
+       }
+
+       nv_wr32(priv, 0x400108, 0xffffffff);
+       nv_wr32(priv, 0x400138, 0xffffffff);
+       nv_wr32(priv, 0x400118, 0xffffffff);
+       nv_wr32(priv, 0x400130, 0xffffffff);
+       nv_wr32(priv, 0x40011c, 0xffffffff);
+       nv_wr32(priv, 0x400134, 0xffffffff);
+
+       nv_wr32(priv, 0x400054, 0x34ce3464);
+
+       gf100_gr_zbc_init(priv);
+
+       return gf100_gr_init_ctxctl(priv);
+}
+
+static void
+gf100_gr_dtor_fw(struct gf100_gr_fuc *fuc)
+{
+       kfree(fuc->data);
+       fuc->data = NULL;
+}
+
+int
+gf100_gr_ctor_fw(struct gf100_gr_priv *priv, const char *fwname,
+                struct gf100_gr_fuc *fuc)
+{
+       struct nvkm_device *device = nv_device(priv);
+       const struct firmware *fw;
+       char f[32];
+       int ret;
+
+       snprintf(f, sizeof(f), "nouveau/nv%02x_%s", device->chipset, fwname);
+       ret = request_firmware(&fw, f, nv_device_base(device));
+       if (ret) {
+               snprintf(f, sizeof(f), "nouveau/%s", fwname);
+               ret = request_firmware(&fw, f, nv_device_base(device));
+               if (ret) {
+                       nv_error(priv, "failed to load %s\n", fwname);
+                       return ret;
+               }
+       }
+
+       fuc->size = fw->size;
+       fuc->data = kmemdup(fw->data, fuc->size, GFP_KERNEL);
+       release_firmware(fw);
+       return (fuc->data != NULL) ? 0 : -ENOMEM;
+}
+
+void
+gf100_gr_dtor(struct nvkm_object *object)
+{
+       struct gf100_gr_priv *priv = (void *)object;
+
+       kfree(priv->data);
+
+       gf100_gr_dtor_fw(&priv->fuc409c);
+       gf100_gr_dtor_fw(&priv->fuc409d);
+       gf100_gr_dtor_fw(&priv->fuc41ac);
+       gf100_gr_dtor_fw(&priv->fuc41ad);
+
+       nvkm_gpuobj_ref(NULL, &priv->unk4188b8);
+       nvkm_gpuobj_ref(NULL, &priv->unk4188b4);
+
+       nvkm_gr_destroy(&priv->base);
+}
+
+int
+gf100_gr_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+             struct nvkm_oclass *bclass, void *data, u32 size,
+             struct nvkm_object **pobject)
+{
+       struct gf100_gr_oclass *oclass = (void *)bclass;
+       struct nvkm_device *device = nv_device(parent);
+       struct gf100_gr_priv *priv;
+       bool use_ext_fw, enable;
+       int ret, i, j;
+
+       use_ext_fw = nvkm_boolopt(device->cfgopt, "NvGrUseFW",
+                                 oclass->fecs.ucode == NULL);
+       enable = use_ext_fw || oclass->fecs.ucode != NULL;
+
+       ret = nvkm_gr_create(parent, engine, bclass, enable, &priv);
+       *pobject = nv_object(priv);
+       if (ret)
+               return ret;
+
+       nv_subdev(priv)->unit = 0x08001000;
+       nv_subdev(priv)->intr = gf100_gr_intr;
+
+       priv->base.units = gf100_gr_units;
+
+       if (use_ext_fw) {
+               nv_info(priv, "using external firmware\n");
+               if (gf100_gr_ctor_fw(priv, "fuc409c", &priv->fuc409c) ||
+                   gf100_gr_ctor_fw(priv, "fuc409d", &priv->fuc409d) ||
+                   gf100_gr_ctor_fw(priv, "fuc41ac", &priv->fuc41ac) ||
+                   gf100_gr_ctor_fw(priv, "fuc41ad", &priv->fuc41ad))
+                       return -ENODEV;
+               priv->firmware = true;
+       }
+
+       ret = nvkm_gpuobj_new(nv_object(priv), NULL, 0x1000, 256, 0,
+                             &priv->unk4188b4);
+       if (ret)
+               return ret;
+
+       ret = nvkm_gpuobj_new(nv_object(priv), NULL, 0x1000, 256, 0,
+                             &priv->unk4188b8);
+       if (ret)
+               return ret;
+
+       for (i = 0; i < 0x1000; i += 4) {
+               nv_wo32(priv->unk4188b4, i, 0x00000010);
+               nv_wo32(priv->unk4188b8, i, 0x00000010);
+       }
+
+       priv->rop_nr = (nv_rd32(priv, 0x409604) & 0x001f0000) >> 16;
+       priv->gpc_nr =  nv_rd32(priv, 0x409604) & 0x0000001f;
+       for (i = 0; i < priv->gpc_nr; i++) {
+               priv->tpc_nr[i]  = nv_rd32(priv, GPC_UNIT(i, 0x2608));
+               priv->tpc_total += priv->tpc_nr[i];
+               priv->ppc_nr[i]  = oclass->ppc_nr;
+               for (j = 0; j < priv->ppc_nr[i]; j++) {
+                       u8 mask = nv_rd32(priv, GPC_UNIT(i, 0x0c30 + (j * 4)));
+                       priv->ppc_tpc_nr[i][j] = hweight8(mask);
+               }
+       }
+
+       /*XXX: these need figuring out... though it might not even matter */
+       switch (nv_device(priv)->chipset) {
+       case 0xc0:
+               if (priv->tpc_total == 11) { /* 465, 3/4/4/0, 4 */
+                       priv->magic_not_rop_nr = 0x07;
+               } else
+               if (priv->tpc_total == 14) { /* 470, 3/3/4/4, 5 */
+                       priv->magic_not_rop_nr = 0x05;
+               } else
+               if (priv->tpc_total == 15) { /* 480, 3/4/4/4, 6 */
+                       priv->magic_not_rop_nr = 0x06;
+               }
+               break;
+       case 0xc3: /* 450, 4/0/0/0, 2 */
+               priv->magic_not_rop_nr = 0x03;
+               break;
+       case 0xc4: /* 460, 3/4/0/0, 4 */
+               priv->magic_not_rop_nr = 0x01;
+               break;
+       case 0xc1: /* 2/0/0/0, 1 */
+               priv->magic_not_rop_nr = 0x01;
+               break;
+       case 0xc8: /* 4/4/3/4, 5 */
+               priv->magic_not_rop_nr = 0x06;
+               break;
+       case 0xce: /* 4/4/0/0, 4 */
+               priv->magic_not_rop_nr = 0x03;
+               break;
+       case 0xcf: /* 4/0/0/0, 3 */
+               priv->magic_not_rop_nr = 0x03;
+               break;
+       case 0xd7:
+       case 0xd9: /* 1/0/0/0, 1 */
+               priv->magic_not_rop_nr = 0x01;
+               break;
+       }
+
+       nv_engine(priv)->cclass = *oclass->cclass;
+       nv_engine(priv)->sclass =  oclass->sclass;
+       return 0;
+}
+
+#include "fuc/hubgf100.fuc3.h"
+
+struct gf100_gr_ucode
+gf100_gr_fecs_ucode = {
+       .code.data = gf100_grhub_code,
+       .code.size = sizeof(gf100_grhub_code),
+       .data.data = gf100_grhub_data,
+       .data.size = sizeof(gf100_grhub_data),
+};
+
+#include "fuc/gpcgf100.fuc3.h"
+
+struct gf100_gr_ucode
+gf100_gr_gpccs_ucode = {
+       .code.data = gf100_grgpc_code,
+       .code.size = sizeof(gf100_grgpc_code),
+       .data.data = gf100_grgpc_data,
+       .data.size = sizeof(gf100_grgpc_data),
+};
+
+struct nvkm_oclass *
+gf100_gr_oclass = &(struct gf100_gr_oclass) {
+       .base.handle = NV_ENGINE(GR, 0xc0),
+       .base.ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = gf100_gr_ctor,
+               .dtor = gf100_gr_dtor,
+               .init = gf100_gr_init,
+               .fini = _nvkm_gr_fini,
+       },
+       .cclass = &gf100_grctx_oclass,
+       .sclass =  gf100_gr_sclass,
+       .mmio = gf100_gr_pack_mmio,
+       .fecs.ucode = &gf100_gr_fecs_ucode,
+       .gpccs.ucode = &gf100_gr_gpccs_ucode,
+}.base;
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/gr/gf100.h b/drivers/gpu/drm/nouveau/nvkm/engine/gr/gf100.h
new file mode 100644 (file)
index 0000000..aeeca1b
--- /dev/null
@@ -0,0 +1,250 @@
+/*
+ * 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 __NVC0_GR_H__
+#define __NVC0_GR_H__
+#include <engine/gr.h>
+
+#include <subdev/ltc.h>
+
+#define GPC_MAX 32
+#define TPC_MAX (GPC_MAX * 8)
+
+#define ROP_BCAST(r)      (0x408800 + (r))
+#define ROP_UNIT(u, r)    (0x410000 + (u) * 0x400 + (r))
+#define GPC_BCAST(r)      (0x418000 + (r))
+#define GPC_UNIT(t, r)    (0x500000 + (t) * 0x8000 + (r))
+#define PPC_UNIT(t, m, r) (0x503000 + (t) * 0x8000 + (m) * 0x200 + (r))
+#define TPC_UNIT(t, m, r) (0x504000 + (t) * 0x8000 + (m) * 0x800 + (r))
+
+struct gf100_gr_data {
+       u32 size;
+       u32 align;
+       u32 access;
+};
+
+struct gf100_gr_mmio {
+       u32 addr;
+       u32 data;
+       u32 shift;
+       int buffer;
+};
+
+struct gf100_gr_fuc {
+       u32 *data;
+       u32  size;
+};
+
+struct gf100_gr_zbc_color {
+       u32 format;
+       u32 ds[4];
+       u32 l2[4];
+};
+
+struct gf100_gr_zbc_depth {
+       u32 format;
+       u32 ds;
+       u32 l2;
+};
+
+struct gf100_gr_priv {
+       struct nvkm_gr base;
+
+       struct gf100_gr_fuc fuc409c;
+       struct gf100_gr_fuc fuc409d;
+       struct gf100_gr_fuc fuc41ac;
+       struct gf100_gr_fuc fuc41ad;
+       bool firmware;
+
+       struct gf100_gr_zbc_color zbc_color[NVKM_LTC_MAX_ZBC_CNT];
+       struct gf100_gr_zbc_depth zbc_depth[NVKM_LTC_MAX_ZBC_CNT];
+
+       u8 rop_nr;
+       u8 gpc_nr;
+       u8 tpc_nr[GPC_MAX];
+       u8 tpc_total;
+       u8 ppc_nr[GPC_MAX];
+       u8 ppc_tpc_nr[GPC_MAX][4];
+
+       struct nvkm_gpuobj *unk4188b4;
+       struct nvkm_gpuobj *unk4188b8;
+
+       struct gf100_gr_data mmio_data[4];
+       struct gf100_gr_mmio mmio_list[4096/8];
+       u32  size;
+       u32 *data;
+
+       u8 magic_not_rop_nr;
+};
+
+struct gf100_gr_chan {
+       struct nvkm_gr_chan base;
+
+       struct nvkm_gpuobj *mmio;
+       struct nvkm_vma mmio_vma;
+       int mmio_nr;
+       struct {
+               struct nvkm_gpuobj *mem;
+               struct nvkm_vma vma;
+       } data[4];
+};
+
+int  gf100_gr_context_ctor(struct nvkm_object *, struct nvkm_object *,
+                            struct nvkm_oclass *, void *, u32,
+                            struct nvkm_object **);
+void gf100_gr_context_dtor(struct nvkm_object *);
+
+void gf100_gr_ctxctl_debug(struct gf100_gr_priv *);
+
+u64  gf100_gr_units(struct nvkm_gr *);
+int  gf100_gr_ctor(struct nvkm_object *, struct nvkm_object *,
+                    struct nvkm_oclass *, void *data, u32 size,
+                    struct nvkm_object **);
+void gf100_gr_dtor(struct nvkm_object *);
+int  gf100_gr_init(struct nvkm_object *);
+void gf100_gr_zbc_init(struct gf100_gr_priv *);
+
+int  gk104_gr_fini(struct nvkm_object *, bool);
+int  gk104_gr_init(struct nvkm_object *);
+
+int  gk110_gr_fini(struct nvkm_object *, bool);
+
+extern struct nvkm_ofuncs gf100_fermi_ofuncs;
+
+extern struct nvkm_oclass gf100_gr_sclass[];
+extern struct nvkm_omthds gf100_gr_9097_omthds[];
+extern struct nvkm_omthds gf100_gr_90c0_omthds[];
+extern struct nvkm_oclass gf110_gr_sclass[];
+extern struct nvkm_oclass gk110_gr_sclass[];
+
+struct gf100_gr_init {
+       u32 addr;
+       u8  count;
+       u8  pitch;
+       u32 data;
+};
+
+struct gf100_gr_pack {
+       const struct gf100_gr_init *init;
+       u32 type;
+};
+
+#define pack_for_each_init(init, pack, head)                                   \
+       for (pack = head; pack && pack->init; pack++)                          \
+                 for (init = pack->init; init && init->count; init++)
+
+struct gf100_gr_ucode {
+       struct gf100_gr_fuc code;
+       struct gf100_gr_fuc data;
+};
+
+extern struct gf100_gr_ucode gf100_gr_fecs_ucode;
+extern struct gf100_gr_ucode gf100_gr_gpccs_ucode;
+
+extern struct gf100_gr_ucode gk110_gr_fecs_ucode;
+extern struct gf100_gr_ucode gk110_gr_gpccs_ucode;
+
+struct gf100_gr_oclass {
+       struct nvkm_oclass base;
+       struct nvkm_oclass **cclass;
+       struct nvkm_oclass *sclass;
+       const struct gf100_gr_pack *mmio;
+       struct {
+               struct gf100_gr_ucode *ucode;
+       } fecs;
+       struct {
+               struct gf100_gr_ucode *ucode;
+       } gpccs;
+       int ppc_nr;
+};
+
+void gf100_gr_mmio(struct gf100_gr_priv *, const struct gf100_gr_pack *);
+void gf100_gr_icmd(struct gf100_gr_priv *, const struct gf100_gr_pack *);
+void gf100_gr_mthd(struct gf100_gr_priv *, const struct gf100_gr_pack *);
+int  gf100_gr_init_ctxctl(struct gf100_gr_priv *);
+
+/* register init value lists */
+
+extern const struct gf100_gr_init gf100_gr_init_main_0[];
+extern const struct gf100_gr_init gf100_gr_init_fe_0[];
+extern const struct gf100_gr_init gf100_gr_init_pri_0[];
+extern const struct gf100_gr_init gf100_gr_init_rstr2d_0[];
+extern const struct gf100_gr_init gf100_gr_init_pd_0[];
+extern const struct gf100_gr_init gf100_gr_init_ds_0[];
+extern const struct gf100_gr_init gf100_gr_init_scc_0[];
+extern const struct gf100_gr_init gf100_gr_init_prop_0[];
+extern const struct gf100_gr_init gf100_gr_init_gpc_unk_0[];
+extern const struct gf100_gr_init gf100_gr_init_setup_0[];
+extern const struct gf100_gr_init gf100_gr_init_crstr_0[];
+extern const struct gf100_gr_init gf100_gr_init_setup_1[];
+extern const struct gf100_gr_init gf100_gr_init_zcull_0[];
+extern const struct gf100_gr_init gf100_gr_init_gpm_0[];
+extern const struct gf100_gr_init gf100_gr_init_gpc_unk_1[];
+extern const struct gf100_gr_init gf100_gr_init_gcc_0[];
+extern const struct gf100_gr_init gf100_gr_init_tpccs_0[];
+extern const struct gf100_gr_init gf100_gr_init_tex_0[];
+extern const struct gf100_gr_init gf100_gr_init_pe_0[];
+extern const struct gf100_gr_init gf100_gr_init_l1c_0[];
+extern const struct gf100_gr_init gf100_gr_init_wwdx_0[];
+extern const struct gf100_gr_init gf100_gr_init_tpccs_1[];
+extern const struct gf100_gr_init gf100_gr_init_mpc_0[];
+extern const struct gf100_gr_init gf100_gr_init_be_0[];
+extern const struct gf100_gr_init gf100_gr_init_fe_1[];
+extern const struct gf100_gr_init gf100_gr_init_pe_1[];
+
+extern const struct gf100_gr_init gf104_gr_init_ds_0[];
+extern const struct gf100_gr_init gf104_gr_init_tex_0[];
+extern const struct gf100_gr_init gf104_gr_init_sm_0[];
+
+extern const struct gf100_gr_init gf108_gr_init_gpc_unk_0[];
+extern const struct gf100_gr_init gf108_gr_init_setup_1[];
+
+extern const struct gf100_gr_init gf119_gr_init_pd_0[];
+extern const struct gf100_gr_init gf119_gr_init_ds_0[];
+extern const struct gf100_gr_init gf119_gr_init_prop_0[];
+extern const struct gf100_gr_init gf119_gr_init_gpm_0[];
+extern const struct gf100_gr_init gf119_gr_init_gpc_unk_1[];
+extern const struct gf100_gr_init gf119_gr_init_tex_0[];
+extern const struct gf100_gr_init gf119_gr_init_sm_0[];
+extern const struct gf100_gr_init gf119_gr_init_fe_1[];
+
+extern const struct gf100_gr_init gf117_gr_init_pes_0[];
+extern const struct gf100_gr_init gf117_gr_init_wwdx_0[];
+extern const struct gf100_gr_init gf117_gr_init_cbm_0[];
+
+extern const struct gf100_gr_init gk104_gr_init_main_0[];
+extern const struct gf100_gr_init gk104_gr_init_tpccs_0[];
+extern const struct gf100_gr_init gk104_gr_init_pe_0[];
+extern const struct gf100_gr_init gk104_gr_init_be_0[];
+extern const struct gf100_gr_pack gk104_gr_pack_mmio[];
+
+extern const struct gf100_gr_init gk110_gr_init_fe_0[];
+extern const struct gf100_gr_init gk110_gr_init_ds_0[];
+extern const struct gf100_gr_init gk110_gr_init_sked_0[];
+extern const struct gf100_gr_init gk110_gr_init_cwd_0[];
+extern const struct gf100_gr_init gk110_gr_init_gpc_unk_1[];
+extern const struct gf100_gr_init gk110_gr_init_tex_0[];
+extern const struct gf100_gr_init gk110_gr_init_sm_0[];
+
+extern const struct gf100_gr_init gk208_gr_init_gpc_unk_0[];
+#endif
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/gr/gf104.c b/drivers/gpu/drm/nouveau/nvkm/engine/gr/gf104.c
new file mode 100644 (file)
index 0000000..20d3b85
--- /dev/null
@@ -0,0 +1,127 @@
+/*
+ * Copyright 2013 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 <bskeggs@redhat.com>
+ */
+#include "gf100.h"
+#include "ctxgf100.h"
+
+/*******************************************************************************
+ * PGRAPH register lists
+ ******************************************************************************/
+
+const struct gf100_gr_init
+gf104_gr_init_ds_0[] = {
+       { 0x405844,   1, 0x04, 0x00ffffff },
+       { 0x405850,   1, 0x04, 0x00000000 },
+       { 0x405900,   1, 0x04, 0x00002834 },
+       { 0x405908,   1, 0x04, 0x00000000 },
+       {}
+};
+
+const struct gf100_gr_init
+gf104_gr_init_tex_0[] = {
+       { 0x419ab0,   1, 0x04, 0x00000000 },
+       { 0x419ac8,   1, 0x04, 0x00000000 },
+       { 0x419ab8,   1, 0x04, 0x000000e7 },
+       { 0x419abc,   2, 0x04, 0x00000000 },
+       {}
+};
+
+static const struct gf100_gr_init
+gf104_gr_init_pe_0[] = {
+       { 0x41980c,   3, 0x04, 0x00000000 },
+       { 0x419844,   1, 0x04, 0x00000000 },
+       { 0x41984c,   1, 0x04, 0x00005bc5 },
+       { 0x419850,   4, 0x04, 0x00000000 },
+       { 0x419880,   1, 0x04, 0x00000002 },
+       {}
+};
+
+const struct gf100_gr_init
+gf104_gr_init_sm_0[] = {
+       { 0x419e00,   1, 0x04, 0x00000000 },
+       { 0x419ea0,   1, 0x04, 0x00000000 },
+       { 0x419ea4,   1, 0x04, 0x00000100 },
+       { 0x419ea8,   1, 0x04, 0x00001100 },
+       { 0x419eac,   1, 0x04, 0x11100702 },
+       { 0x419eb0,   1, 0x04, 0x00000003 },
+       { 0x419eb4,   4, 0x04, 0x00000000 },
+       { 0x419ec8,   1, 0x04, 0x0e063818 },
+       { 0x419ecc,   1, 0x04, 0x0e060e06 },
+       { 0x419ed0,   1, 0x04, 0x00003818 },
+       { 0x419ed4,   1, 0x04, 0x011104f1 },
+       { 0x419edc,   1, 0x04, 0x00000000 },
+       { 0x419f00,   1, 0x04, 0x00000000 },
+       { 0x419f2c,   1, 0x04, 0x00000000 },
+       {}
+};
+
+static const struct gf100_gr_pack
+gf104_gr_pack_mmio[] = {
+       { gf100_gr_init_main_0 },
+       { gf100_gr_init_fe_0 },
+       { gf100_gr_init_pri_0 },
+       { gf100_gr_init_rstr2d_0 },
+       { gf100_gr_init_pd_0 },
+       { gf104_gr_init_ds_0 },
+       { gf100_gr_init_scc_0 },
+       { gf100_gr_init_prop_0 },
+       { gf100_gr_init_gpc_unk_0 },
+       { gf100_gr_init_setup_0 },
+       { gf100_gr_init_crstr_0 },
+       { gf100_gr_init_setup_1 },
+       { gf100_gr_init_zcull_0 },
+       { gf100_gr_init_gpm_0 },
+       { gf100_gr_init_gpc_unk_1 },
+       { gf100_gr_init_gcc_0 },
+       { gf100_gr_init_tpccs_0 },
+       { gf104_gr_init_tex_0 },
+       { gf104_gr_init_pe_0 },
+       { gf100_gr_init_l1c_0 },
+       { gf100_gr_init_wwdx_0 },
+       { gf100_gr_init_tpccs_1 },
+       { gf100_gr_init_mpc_0 },
+       { gf104_gr_init_sm_0 },
+       { gf100_gr_init_be_0 },
+       { gf100_gr_init_fe_1 },
+       {}
+};
+
+/*******************************************************************************
+ * PGRAPH engine/subdev functions
+ ******************************************************************************/
+
+struct nvkm_oclass *
+gf104_gr_oclass = &(struct gf100_gr_oclass) {
+       .base.handle = NV_ENGINE(GR, 0xc3),
+       .base.ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = gf100_gr_ctor,
+               .dtor = gf100_gr_dtor,
+               .init = gf100_gr_init,
+               .fini = _nvkm_gr_fini,
+       },
+       .cclass = &gf104_grctx_oclass,
+       .sclass = gf100_gr_sclass,
+       .mmio = gf104_gr_pack_mmio,
+       .fecs.ucode = &gf100_gr_fecs_ucode,
+       .gpccs.ucode = &gf100_gr_gpccs_ucode,
+}.base;
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/gr/gf108.c b/drivers/gpu/drm/nouveau/nvkm/engine/gr/gf108.c
new file mode 100644 (file)
index 0000000..5362c81
--- /dev/null
@@ -0,0 +1,134 @@
+/*
+ * Copyright 2013 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 <bskeggs@redhat.com>
+ */
+#include "gf100.h"
+#include "ctxgf100.h"
+
+#include <nvif/class.h>
+
+/*******************************************************************************
+ * Graphics object classes
+ ******************************************************************************/
+
+static struct nvkm_oclass
+gf108_gr_sclass[] = {
+       { 0x902d, &nvkm_object_ofuncs },
+       { 0x9039, &nvkm_object_ofuncs },
+       { FERMI_A, &gf100_fermi_ofuncs, gf100_gr_9097_omthds },
+       { FERMI_B, &gf100_fermi_ofuncs, gf100_gr_9097_omthds },
+       { FERMI_COMPUTE_A, &nvkm_object_ofuncs, gf100_gr_90c0_omthds },
+       {}
+};
+
+/*******************************************************************************
+ * PGRAPH register lists
+ ******************************************************************************/
+
+const struct gf100_gr_init
+gf108_gr_init_gpc_unk_0[] = {
+       { 0x418604,   1, 0x04, 0x00000000 },
+       { 0x418680,   1, 0x04, 0x00000000 },
+       { 0x418714,   1, 0x04, 0x00000000 },
+       { 0x418384,   1, 0x04, 0x00000000 },
+       {}
+};
+
+const struct gf100_gr_init
+gf108_gr_init_setup_1[] = {
+       { 0x4188c8,   2, 0x04, 0x00000000 },
+       { 0x4188d0,   1, 0x04, 0x00010000 },
+       { 0x4188d4,   1, 0x04, 0x00000001 },
+       {}
+};
+
+static const struct gf100_gr_init
+gf108_gr_init_gpc_unk_1[] = {
+       { 0x418d00,   1, 0x04, 0x00000000 },
+       { 0x418f08,   1, 0x04, 0x00000000 },
+       { 0x418e00,   1, 0x04, 0x00000003 },
+       { 0x418e08,   1, 0x04, 0x00000000 },
+       {}
+};
+
+static const struct gf100_gr_init
+gf108_gr_init_pe_0[] = {
+       { 0x41980c,   1, 0x04, 0x00000010 },
+       { 0x419810,   1, 0x04, 0x00000000 },
+       { 0x419814,   1, 0x04, 0x00000004 },
+       { 0x419844,   1, 0x04, 0x00000000 },
+       { 0x41984c,   1, 0x04, 0x00005bc5 },
+       { 0x419850,   4, 0x04, 0x00000000 },
+       { 0x419880,   1, 0x04, 0x00000002 },
+       {}
+};
+
+static const struct gf100_gr_pack
+gf108_gr_pack_mmio[] = {
+       { gf100_gr_init_main_0 },
+       { gf100_gr_init_fe_0 },
+       { gf100_gr_init_pri_0 },
+       { gf100_gr_init_rstr2d_0 },
+       { gf100_gr_init_pd_0 },
+       { gf104_gr_init_ds_0 },
+       { gf100_gr_init_scc_0 },
+       { gf100_gr_init_prop_0 },
+       { gf108_gr_init_gpc_unk_0 },
+       { gf100_gr_init_setup_0 },
+       { gf100_gr_init_crstr_0 },
+       { gf108_gr_init_setup_1 },
+       { gf100_gr_init_zcull_0 },
+       { gf100_gr_init_gpm_0 },
+       { gf108_gr_init_gpc_unk_1 },
+       { gf100_gr_init_gcc_0 },
+       { gf100_gr_init_tpccs_0 },
+       { gf104_gr_init_tex_0 },
+       { gf108_gr_init_pe_0 },
+       { gf100_gr_init_l1c_0 },
+       { gf100_gr_init_wwdx_0 },
+       { gf100_gr_init_tpccs_1 },
+       { gf100_gr_init_mpc_0 },
+       { gf104_gr_init_sm_0 },
+       { gf100_gr_init_be_0 },
+       { gf100_gr_init_fe_1 },
+       {}
+};
+
+/*******************************************************************************
+ * PGRAPH engine/subdev functions
+ ******************************************************************************/
+
+struct nvkm_oclass *
+gf108_gr_oclass = &(struct gf100_gr_oclass) {
+       .base.handle = NV_ENGINE(GR, 0xc1),
+       .base.ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = gf100_gr_ctor,
+               .dtor = gf100_gr_dtor,
+               .init = gf100_gr_init,
+               .fini = _nvkm_gr_fini,
+       },
+       .cclass = &gf108_grctx_oclass,
+       .sclass = gf108_gr_sclass,
+       .mmio = gf108_gr_pack_mmio,
+       .fecs.ucode = &gf100_gr_fecs_ucode,
+       .gpccs.ucode = &gf100_gr_gpccs_ucode,
+}.base;
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/gr/gf110.c b/drivers/gpu/drm/nouveau/nvkm/engine/gr/gf110.c
new file mode 100644 (file)
index 0000000..88beb49
--- /dev/null
@@ -0,0 +1,116 @@
+/*
+ * Copyright 2013 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 <bskeggs@redhat.com>
+ */
+#include "gf100.h"
+#include "ctxgf100.h"
+
+#include <nvif/class.h>
+
+/*******************************************************************************
+ * Graphics object classes
+ ******************************************************************************/
+
+struct nvkm_oclass
+gf110_gr_sclass[] = {
+       { 0x902d, &nvkm_object_ofuncs },
+       { 0x9039, &nvkm_object_ofuncs },
+       { FERMI_A, &gf100_fermi_ofuncs, gf100_gr_9097_omthds },
+       { FERMI_B, &gf100_fermi_ofuncs, gf100_gr_9097_omthds },
+       { FERMI_C, &gf100_fermi_ofuncs, gf100_gr_9097_omthds },
+       { FERMI_COMPUTE_A, &nvkm_object_ofuncs, gf100_gr_90c0_omthds },
+       {}
+};
+
+/*******************************************************************************
+ * PGRAPH register lists
+ ******************************************************************************/
+
+static const struct gf100_gr_init
+gf110_gr_init_sm_0[] = {
+       { 0x419e00,   1, 0x04, 0x00000000 },
+       { 0x419ea0,   1, 0x04, 0x00000000 },
+       { 0x419ea4,   1, 0x04, 0x00000100 },
+       { 0x419ea8,   1, 0x04, 0x00001100 },
+       { 0x419eac,   1, 0x04, 0x11100f02 },
+       { 0x419eb0,   1, 0x04, 0x00000003 },
+       { 0x419eb4,   4, 0x04, 0x00000000 },
+       { 0x419ec8,   1, 0x04, 0x06060618 },
+       { 0x419ed0,   1, 0x04, 0x0eff0e38 },
+       { 0x419ed4,   1, 0x04, 0x011104f1 },
+       { 0x419edc,   1, 0x04, 0x00000000 },
+       { 0x419f00,   1, 0x04, 0x00000000 },
+       { 0x419f2c,   1, 0x04, 0x00000000 },
+       {}
+};
+
+static const struct gf100_gr_pack
+gf110_gr_pack_mmio[] = {
+       { gf100_gr_init_main_0 },
+       { gf100_gr_init_fe_0 },
+       { gf100_gr_init_pri_0 },
+       { gf100_gr_init_rstr2d_0 },
+       { gf100_gr_init_pd_0 },
+       { gf100_gr_init_ds_0 },
+       { gf100_gr_init_scc_0 },
+       { gf100_gr_init_prop_0 },
+       { gf100_gr_init_gpc_unk_0 },
+       { gf100_gr_init_setup_0 },
+       { gf100_gr_init_crstr_0 },
+       { gf108_gr_init_setup_1 },
+       { gf100_gr_init_zcull_0 },
+       { gf100_gr_init_gpm_0 },
+       { gf100_gr_init_gpc_unk_1 },
+       { gf100_gr_init_gcc_0 },
+       { gf100_gr_init_tpccs_0 },
+       { gf100_gr_init_tex_0 },
+       { gf100_gr_init_pe_0 },
+       { gf100_gr_init_l1c_0 },
+       { gf100_gr_init_wwdx_0 },
+       { gf100_gr_init_tpccs_1 },
+       { gf100_gr_init_mpc_0 },
+       { gf110_gr_init_sm_0 },
+       { gf100_gr_init_be_0 },
+       { gf100_gr_init_fe_1 },
+       { gf100_gr_init_pe_1 },
+       {}
+};
+
+/*******************************************************************************
+ * PGRAPH engine/subdev functions
+ ******************************************************************************/
+
+struct nvkm_oclass *
+gf110_gr_oclass = &(struct gf100_gr_oclass) {
+       .base.handle = NV_ENGINE(GR, 0xc8),
+       .base.ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = gf100_gr_ctor,
+               .dtor = gf100_gr_dtor,
+               .init = gf100_gr_init,
+               .fini = _nvkm_gr_fini,
+       },
+       .cclass = &gf110_grctx_oclass,
+       .sclass = gf110_gr_sclass,
+       .mmio = gf110_gr_pack_mmio,
+       .fecs.ucode = &gf100_gr_fecs_ucode,
+       .gpccs.ucode = &gf100_gr_gpccs_ucode,
+}.base;
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/gr/gf117.c b/drivers/gpu/drm/nouveau/nvkm/engine/gr/gf117.c
new file mode 100644 (file)
index 0000000..871ac5f
--- /dev/null
@@ -0,0 +1,136 @@
+/*
+ * Copyright 2013 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 <bskeggs@redhat.com>
+ */
+#include "gf100.h"
+#include "ctxgf100.h"
+
+/*******************************************************************************
+ * PGRAPH register lists
+ ******************************************************************************/
+
+static const struct gf100_gr_init
+gf117_gr_init_pe_0[] = {
+       { 0x41980c,   1, 0x04, 0x00000010 },
+       { 0x419844,   1, 0x04, 0x00000000 },
+       { 0x41984c,   1, 0x04, 0x00005bc8 },
+       { 0x419850,   3, 0x04, 0x00000000 },
+       {}
+};
+
+const struct gf100_gr_init
+gf117_gr_init_pes_0[] = {
+       { 0x41be04,   1, 0x04, 0x00000000 },
+       { 0x41be08,   1, 0x04, 0x00000004 },
+       { 0x41be0c,   1, 0x04, 0x00000000 },
+       { 0x41be10,   1, 0x04, 0x003b8bc7 },
+       { 0x41be14,   2, 0x04, 0x00000000 },
+       {}
+};
+
+const struct gf100_gr_init
+gf117_gr_init_wwdx_0[] = {
+       { 0x41bfd4,   1, 0x04, 0x00800000 },
+       { 0x41bfdc,   1, 0x04, 0x00000000 },
+       { 0x41bff8,   2, 0x04, 0x00000000 },
+       {}
+};
+
+const struct gf100_gr_init
+gf117_gr_init_cbm_0[] = {
+       { 0x41becc,   1, 0x04, 0x00000000 },
+       { 0x41bee8,   2, 0x04, 0x00000000 },
+       {}
+};
+
+static const struct gf100_gr_pack
+gf117_gr_pack_mmio[] = {
+       { gf100_gr_init_main_0 },
+       { gf100_gr_init_fe_0 },
+       { gf100_gr_init_pri_0 },
+       { gf100_gr_init_rstr2d_0 },
+       { gf119_gr_init_pd_0 },
+       { gf119_gr_init_ds_0 },
+       { gf100_gr_init_scc_0 },
+       { gf119_gr_init_prop_0 },
+       { gf108_gr_init_gpc_unk_0 },
+       { gf100_gr_init_setup_0 },
+       { gf100_gr_init_crstr_0 },
+       { gf108_gr_init_setup_1 },
+       { gf100_gr_init_zcull_0 },
+       { gf119_gr_init_gpm_0 },
+       { gf119_gr_init_gpc_unk_1 },
+       { gf100_gr_init_gcc_0 },
+       { gf100_gr_init_tpccs_0 },
+       { gf119_gr_init_tex_0 },
+       { gf117_gr_init_pe_0 },
+       { gf100_gr_init_l1c_0 },
+       { gf100_gr_init_mpc_0 },
+       { gf119_gr_init_sm_0 },
+       { gf117_gr_init_pes_0 },
+       { gf117_gr_init_wwdx_0 },
+       { gf117_gr_init_cbm_0 },
+       { gf100_gr_init_be_0 },
+       { gf119_gr_init_fe_1 },
+       {}
+};
+
+/*******************************************************************************
+ * PGRAPH engine/subdev functions
+ ******************************************************************************/
+
+#include "fuc/hubgf117.fuc3.h"
+
+struct gf100_gr_ucode
+gf117_gr_fecs_ucode = {
+       .code.data = gf117_grhub_code,
+       .code.size = sizeof(gf117_grhub_code),
+       .data.data = gf117_grhub_data,
+       .data.size = sizeof(gf117_grhub_data),
+};
+
+#include "fuc/gpcgf117.fuc3.h"
+
+struct gf100_gr_ucode
+gf117_gr_gpccs_ucode = {
+       .code.data = gf117_grgpc_code,
+       .code.size = sizeof(gf117_grgpc_code),
+       .data.data = gf117_grgpc_data,
+       .data.size = sizeof(gf117_grgpc_data),
+};
+
+struct nvkm_oclass *
+gf117_gr_oclass = &(struct gf100_gr_oclass) {
+       .base.handle = NV_ENGINE(GR, 0xd7),
+       .base.ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = gf100_gr_ctor,
+               .dtor = gf100_gr_dtor,
+               .init = gf100_gr_init,
+               .fini = _nvkm_gr_fini,
+       },
+       .cclass = &gf117_grctx_oclass,
+       .sclass = gf110_gr_sclass,
+       .mmio = gf117_gr_pack_mmio,
+       .fecs.ucode = &gf117_gr_fecs_ucode,
+       .gpccs.ucode = &gf117_gr_gpccs_ucode,
+       .ppc_nr = 1,
+}.base;
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/gr/gf119.c b/drivers/gpu/drm/nouveau/nvkm/engine/gr/gf119.c
new file mode 100644 (file)
index 0000000..e6dd651
--- /dev/null
@@ -0,0 +1,190 @@
+/*
+ * Copyright 2013 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 <bskeggs@redhat.com>
+ */
+#include "gf100.h"
+#include "ctxgf100.h"
+
+/*******************************************************************************
+ * PGRAPH register lists
+ ******************************************************************************/
+
+const struct gf100_gr_init
+gf119_gr_init_pd_0[] = {
+       { 0x406024,   1, 0x04, 0x00000000 },
+       { 0x4064f0,   3, 0x04, 0x00000000 },
+       {}
+};
+
+const struct gf100_gr_init
+gf119_gr_init_ds_0[] = {
+       { 0x405844,   1, 0x04, 0x00ffffff },
+       { 0x405850,   1, 0x04, 0x00000000 },
+       { 0x405900,   1, 0x04, 0x00002834 },
+       { 0x405908,   1, 0x04, 0x00000000 },
+       { 0x405928,   2, 0x04, 0x00000000 },
+       {}
+};
+
+const struct gf100_gr_init
+gf119_gr_init_prop_0[] = {
+       { 0x418408,   1, 0x04, 0x00000000 },
+       { 0x4184a0,   3, 0x04, 0x00000000 },
+       {}
+};
+
+const struct gf100_gr_init
+gf119_gr_init_gpm_0[] = {
+       { 0x418c04,   1, 0x04, 0x00000000 },
+       { 0x418c64,   2, 0x04, 0x00000000 },
+       { 0x418c88,   1, 0x04, 0x00000000 },
+       { 0x418cb4,   2, 0x04, 0x00000000 },
+       {}
+};
+
+const struct gf100_gr_init
+gf119_gr_init_gpc_unk_1[] = {
+       { 0x418d00,   1, 0x04, 0x00000000 },
+       { 0x418d28,   2, 0x04, 0x00000000 },
+       { 0x418f00,   1, 0x04, 0x00000000 },
+       { 0x418f08,   1, 0x04, 0x00000000 },
+       { 0x418f20,   2, 0x04, 0x00000000 },
+       { 0x418e00,   1, 0x04, 0x00000003 },
+       { 0x418e08,   1, 0x04, 0x00000000 },
+       { 0x418e1c,   2, 0x04, 0x00000000 },
+       {}
+};
+
+const struct gf100_gr_init
+gf119_gr_init_tex_0[] = {
+       { 0x419ab0,   1, 0x04, 0x00000000 },
+       { 0x419ac8,   1, 0x04, 0x00000000 },
+       { 0x419ab8,   1, 0x04, 0x000000e7 },
+       { 0x419abc,   2, 0x04, 0x00000000 },
+       { 0x419ab4,   1, 0x04, 0x00000000 },
+       {}
+};
+
+static const struct gf100_gr_init
+gf119_gr_init_pe_0[] = {
+       { 0x41980c,   1, 0x04, 0x00000010 },
+       { 0x419810,   1, 0x04, 0x00000000 },
+       { 0x419814,   1, 0x04, 0x00000004 },
+       { 0x419844,   1, 0x04, 0x00000000 },
+       { 0x41984c,   1, 0x04, 0x0000a918 },
+       { 0x419850,   4, 0x04, 0x00000000 },
+       { 0x419880,   1, 0x04, 0x00000002 },
+       {}
+};
+
+static const struct gf100_gr_init
+gf119_gr_init_wwdx_0[] = {
+       { 0x419bd4,   1, 0x04, 0x00800000 },
+       { 0x419bdc,   1, 0x04, 0x00000000 },
+       { 0x419bf8,   2, 0x04, 0x00000000 },
+       {}
+};
+
+static const struct gf100_gr_init
+gf119_gr_init_tpccs_1[] = {
+       { 0x419d2c,   1, 0x04, 0x00000000 },
+       { 0x419d48,   2, 0x04, 0x00000000 },
+       {}
+};
+
+const struct gf100_gr_init
+gf119_gr_init_sm_0[] = {
+       { 0x419e00,   1, 0x04, 0x00000000 },
+       { 0x419ea0,   1, 0x04, 0x00000000 },
+       { 0x419ea4,   1, 0x04, 0x00000100 },
+       { 0x419ea8,   1, 0x04, 0x02001100 },
+       { 0x419eac,   1, 0x04, 0x11100702 },
+       { 0x419eb0,   1, 0x04, 0x00000003 },
+       { 0x419eb4,   4, 0x04, 0x00000000 },
+       { 0x419ec8,   1, 0x04, 0x0e063818 },
+       { 0x419ecc,   1, 0x04, 0x0e060e06 },
+       { 0x419ed0,   1, 0x04, 0x00003818 },
+       { 0x419ed4,   1, 0x04, 0x011104f1 },
+       { 0x419edc,   1, 0x04, 0x00000000 },
+       { 0x419f00,   1, 0x04, 0x00000000 },
+       { 0x419f2c,   1, 0x04, 0x00000000 },
+       {}
+};
+
+const struct gf100_gr_init
+gf119_gr_init_fe_1[] = {
+       { 0x40402c,   1, 0x04, 0x00000000 },
+       { 0x4040f0,   1, 0x04, 0x00000000 },
+       { 0x404174,   1, 0x04, 0x00000000 },
+       {}
+};
+
+static const struct gf100_gr_pack
+gf119_gr_pack_mmio[] = {
+       { gf100_gr_init_main_0 },
+       { gf100_gr_init_fe_0 },
+       { gf100_gr_init_pri_0 },
+       { gf100_gr_init_rstr2d_0 },
+       { gf119_gr_init_pd_0 },
+       { gf119_gr_init_ds_0 },
+       { gf100_gr_init_scc_0 },
+       { gf119_gr_init_prop_0 },
+       { gf108_gr_init_gpc_unk_0 },
+       { gf100_gr_init_setup_0 },
+       { gf100_gr_init_crstr_0 },
+       { gf108_gr_init_setup_1 },
+       { gf100_gr_init_zcull_0 },
+       { gf119_gr_init_gpm_0 },
+       { gf119_gr_init_gpc_unk_1 },
+       { gf100_gr_init_gcc_0 },
+       { gf100_gr_init_tpccs_0 },
+       { gf119_gr_init_tex_0 },
+       { gf119_gr_init_pe_0 },
+       { gf100_gr_init_l1c_0 },
+       { gf119_gr_init_wwdx_0 },
+       { gf119_gr_init_tpccs_1 },
+       { gf100_gr_init_mpc_0 },
+       { gf119_gr_init_sm_0 },
+       { gf100_gr_init_be_0 },
+       { gf119_gr_init_fe_1 },
+       {}
+};
+
+/*******************************************************************************
+ * PGRAPH engine/subdev functions
+ ******************************************************************************/
+
+struct nvkm_oclass *
+gf119_gr_oclass = &(struct gf100_gr_oclass) {
+       .base.handle = NV_ENGINE(GR, 0xd9),
+       .base.ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = gf100_gr_ctor,
+               .dtor = gf100_gr_dtor,
+               .init = gf100_gr_init,
+               .fini = _nvkm_gr_fini,
+       },
+       .cclass = &gf119_grctx_oclass,
+       .sclass = gf110_gr_sclass,
+       .mmio = gf119_gr_pack_mmio,
+       .fecs.ucode = &gf100_gr_fecs_ucode,
+       .gpccs.ucode = &gf100_gr_gpccs_ucode,
+}.base;
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/gr/gk104.c b/drivers/gpu/drm/nouveau/nvkm/engine/gr/gk104.c
new file mode 100644 (file)
index 0000000..489fdd9
--- /dev/null
@@ -0,0 +1,348 @@
+/*
+ * Copyright 2013 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 <bskeggs@redhat.com>
+ */
+#include "gf100.h"
+#include "ctxgf100.h"
+
+#include <subdev/pmu.h>
+
+#include <nvif/class.h>
+
+/*******************************************************************************
+ * Graphics object classes
+ ******************************************************************************/
+
+static struct nvkm_oclass
+gk104_gr_sclass[] = {
+       { 0x902d, &nvkm_object_ofuncs },
+       { 0xa040, &nvkm_object_ofuncs },
+       { KEPLER_A, &gf100_fermi_ofuncs, gf100_gr_9097_omthds },
+       { KEPLER_COMPUTE_A, &nvkm_object_ofuncs, gf100_gr_90c0_omthds },
+       {}
+};
+
+/*******************************************************************************
+ * PGRAPH register lists
+ ******************************************************************************/
+
+const struct gf100_gr_init
+gk104_gr_init_main_0[] = {
+       { 0x400080,   1, 0x04, 0x003083c2 },
+       { 0x400088,   1, 0x04, 0x0001ffe7 },
+       { 0x40008c,   1, 0x04, 0x00000000 },
+       { 0x400090,   1, 0x04, 0x00000030 },
+       { 0x40013c,   1, 0x04, 0x003901f7 },
+       { 0x400140,   1, 0x04, 0x00000100 },
+       { 0x400144,   1, 0x04, 0x00000000 },
+       { 0x400148,   1, 0x04, 0x00000110 },
+       { 0x400138,   1, 0x04, 0x00000000 },
+       { 0x400130,   2, 0x04, 0x00000000 },
+       { 0x400124,   1, 0x04, 0x00000002 },
+       {}
+};
+
+static const struct gf100_gr_init
+gk104_gr_init_ds_0[] = {
+       { 0x405844,   1, 0x04, 0x00ffffff },
+       { 0x405850,   1, 0x04, 0x00000000 },
+       { 0x405900,   1, 0x04, 0x0000ff34 },
+       { 0x405908,   1, 0x04, 0x00000000 },
+       { 0x405928,   2, 0x04, 0x00000000 },
+       {}
+};
+
+static const struct gf100_gr_init
+gk104_gr_init_sked_0[] = {
+       { 0x407010,   1, 0x04, 0x00000000 },
+       {}
+};
+
+static const struct gf100_gr_init
+gk104_gr_init_cwd_0[] = {
+       { 0x405b50,   1, 0x04, 0x00000000 },
+       {}
+};
+
+static const struct gf100_gr_init
+gk104_gr_init_gpc_unk_1[] = {
+       { 0x418d00,   1, 0x04, 0x00000000 },
+       { 0x418d28,   2, 0x04, 0x00000000 },
+       { 0x418f00,   1, 0x04, 0x00000000 },
+       { 0x418f08,   1, 0x04, 0x00000000 },
+       { 0x418f20,   2, 0x04, 0x00000000 },
+       { 0x418e00,   1, 0x04, 0x00000060 },
+       { 0x418e08,   1, 0x04, 0x00000000 },
+       { 0x418e1c,   2, 0x04, 0x00000000 },
+       {}
+};
+
+const struct gf100_gr_init
+gk104_gr_init_tpccs_0[] = {
+       { 0x419d0c,   1, 0x04, 0x00000000 },
+       { 0x419d10,   1, 0x04, 0x00000014 },
+       {}
+};
+
+const struct gf100_gr_init
+gk104_gr_init_pe_0[] = {
+       { 0x41980c,   1, 0x04, 0x00000010 },
+       { 0x419844,   1, 0x04, 0x00000000 },
+       { 0x419850,   1, 0x04, 0x00000004 },
+       { 0x419854,   2, 0x04, 0x00000000 },
+       {}
+};
+
+static const struct gf100_gr_init
+gk104_gr_init_l1c_0[] = {
+       { 0x419c98,   1, 0x04, 0x00000000 },
+       { 0x419ca8,   1, 0x04, 0x00000000 },
+       { 0x419cb0,   1, 0x04, 0x01000000 },
+       { 0x419cb4,   1, 0x04, 0x00000000 },
+       { 0x419cb8,   1, 0x04, 0x00b08bea },
+       { 0x419c84,   1, 0x04, 0x00010384 },
+       { 0x419cbc,   1, 0x04, 0x28137646 },
+       { 0x419cc0,   2, 0x04, 0x00000000 },
+       { 0x419c80,   1, 0x04, 0x00020232 },
+       {}
+};
+
+static const struct gf100_gr_init
+gk104_gr_init_sm_0[] = {
+       { 0x419e00,   1, 0x04, 0x00000000 },
+       { 0x419ea0,   1, 0x04, 0x00000000 },
+       { 0x419ee4,   1, 0x04, 0x00000000 },
+       { 0x419ea4,   1, 0x04, 0x00000100 },
+       { 0x419ea8,   1, 0x04, 0x00000000 },
+       { 0x419eb4,   4, 0x04, 0x00000000 },
+       { 0x419edc,   1, 0x04, 0x00000000 },
+       { 0x419f00,   1, 0x04, 0x00000000 },
+       { 0x419f74,   1, 0x04, 0x00000555 },
+       {}
+};
+
+const struct gf100_gr_init
+gk104_gr_init_be_0[] = {
+       { 0x40880c,   1, 0x04, 0x00000000 },
+       { 0x408850,   1, 0x04, 0x00000004 },
+       { 0x408910,   9, 0x04, 0x00000000 },
+       { 0x408950,   1, 0x04, 0x00000000 },
+       { 0x408954,   1, 0x04, 0x0000ffff },
+       { 0x408958,   1, 0x04, 0x00000034 },
+       { 0x408984,   1, 0x04, 0x00000000 },
+       { 0x408988,   1, 0x04, 0x08040201 },
+       { 0x40898c,   1, 0x04, 0x80402010 },
+       {}
+};
+
+const struct gf100_gr_pack
+gk104_gr_pack_mmio[] = {
+       { gk104_gr_init_main_0 },
+       { gf100_gr_init_fe_0 },
+       { gf100_gr_init_pri_0 },
+       { gf100_gr_init_rstr2d_0 },
+       { gf119_gr_init_pd_0 },
+       { gk104_gr_init_ds_0 },
+       { gf100_gr_init_scc_0 },
+       { gk104_gr_init_sked_0 },
+       { gk104_gr_init_cwd_0 },
+       { gf119_gr_init_prop_0 },
+       { gf108_gr_init_gpc_unk_0 },
+       { gf100_gr_init_setup_0 },
+       { gf100_gr_init_crstr_0 },
+       { gf108_gr_init_setup_1 },
+       { gf100_gr_init_zcull_0 },
+       { gf119_gr_init_gpm_0 },
+       { gk104_gr_init_gpc_unk_1 },
+       { gf100_gr_init_gcc_0 },
+       { gk104_gr_init_tpccs_0 },
+       { gf119_gr_init_tex_0 },
+       { gk104_gr_init_pe_0 },
+       { gk104_gr_init_l1c_0 },
+       { gf100_gr_init_mpc_0 },
+       { gk104_gr_init_sm_0 },
+       { gf117_gr_init_pes_0 },
+       { gf117_gr_init_wwdx_0 },
+       { gf117_gr_init_cbm_0 },
+       { gk104_gr_init_be_0 },
+       { gf100_gr_init_fe_1 },
+       {}
+};
+
+/*******************************************************************************
+ * PGRAPH engine/subdev functions
+ ******************************************************************************/
+
+int
+gk104_gr_init(struct nvkm_object *object)
+{
+       struct gf100_gr_oclass *oclass = (void *)object->oclass;
+       struct gf100_gr_priv *priv = (void *)object;
+       struct nvkm_pmu *pmu = nvkm_pmu(priv);
+       const u32 magicgpc918 = DIV_ROUND_UP(0x00800000, priv->tpc_total);
+       u32 data[TPC_MAX / 8] = {};
+       u8  tpcnr[GPC_MAX];
+       int gpc, tpc, rop;
+       int ret, i;
+
+       if (pmu)
+               pmu->pgob(pmu, false);
+
+       ret = nvkm_gr_init(&priv->base);
+       if (ret)
+               return ret;
+
+       nv_wr32(priv, GPC_BCAST(0x0880), 0x00000000);
+       nv_wr32(priv, GPC_BCAST(0x08a4), 0x00000000);
+       nv_wr32(priv, GPC_BCAST(0x0888), 0x00000000);
+       nv_wr32(priv, GPC_BCAST(0x088c), 0x00000000);
+       nv_wr32(priv, GPC_BCAST(0x0890), 0x00000000);
+       nv_wr32(priv, GPC_BCAST(0x0894), 0x00000000);
+       nv_wr32(priv, GPC_BCAST(0x08b4), priv->unk4188b4->addr >> 8);
+       nv_wr32(priv, GPC_BCAST(0x08b8), priv->unk4188b8->addr >> 8);
+
+       gf100_gr_mmio(priv, oclass->mmio);
+
+       nv_wr32(priv, GPC_UNIT(0, 0x3018), 0x00000001);
+
+       memset(data, 0x00, sizeof(data));
+       memcpy(tpcnr, priv->tpc_nr, sizeof(priv->tpc_nr));
+       for (i = 0, gpc = -1; i < priv->tpc_total; i++) {
+               do {
+                       gpc = (gpc + 1) % priv->gpc_nr;
+               } while (!tpcnr[gpc]);
+               tpc = priv->tpc_nr[gpc] - tpcnr[gpc]--;
+
+               data[i / 8] |= tpc << ((i % 8) * 4);
+       }
+
+       nv_wr32(priv, GPC_BCAST(0x0980), data[0]);
+       nv_wr32(priv, GPC_BCAST(0x0984), data[1]);
+       nv_wr32(priv, GPC_BCAST(0x0988), data[2]);
+       nv_wr32(priv, GPC_BCAST(0x098c), data[3]);
+
+       for (gpc = 0; gpc < priv->gpc_nr; gpc++) {
+               nv_wr32(priv, GPC_UNIT(gpc, 0x0914),
+                       priv->magic_not_rop_nr << 8 | priv->tpc_nr[gpc]);
+               nv_wr32(priv, GPC_UNIT(gpc, 0x0910), 0x00040000 |
+                       priv->tpc_total);
+               nv_wr32(priv, GPC_UNIT(gpc, 0x0918), magicgpc918);
+       }
+
+       nv_wr32(priv, GPC_BCAST(0x3fd4), magicgpc918);
+       nv_wr32(priv, GPC_BCAST(0x08ac), nv_rd32(priv, 0x100800));
+
+       nv_wr32(priv, 0x400500, 0x00010001);
+
+       nv_wr32(priv, 0x400100, 0xffffffff);
+       nv_wr32(priv, 0x40013c, 0xffffffff);
+
+       nv_wr32(priv, 0x409ffc, 0x00000000);
+       nv_wr32(priv, 0x409c14, 0x00003e3e);
+       nv_wr32(priv, 0x409c24, 0x000f0001);
+       nv_wr32(priv, 0x404000, 0xc0000000);
+       nv_wr32(priv, 0x404600, 0xc0000000);
+       nv_wr32(priv, 0x408030, 0xc0000000);
+       nv_wr32(priv, 0x404490, 0xc0000000);
+       nv_wr32(priv, 0x406018, 0xc0000000);
+       nv_wr32(priv, 0x407020, 0x40000000);
+       nv_wr32(priv, 0x405840, 0xc0000000);
+       nv_wr32(priv, 0x405844, 0x00ffffff);
+       nv_mask(priv, 0x419cc0, 0x00000008, 0x00000008);
+       nv_mask(priv, 0x419eb4, 0x00001000, 0x00001000);
+
+       for (gpc = 0; gpc < priv->gpc_nr; gpc++) {
+               nv_wr32(priv, GPC_UNIT(gpc, 0x3038), 0xc0000000);
+               nv_wr32(priv, GPC_UNIT(gpc, 0x0420), 0xc0000000);
+               nv_wr32(priv, GPC_UNIT(gpc, 0x0900), 0xc0000000);
+               nv_wr32(priv, GPC_UNIT(gpc, 0x1028), 0xc0000000);
+               nv_wr32(priv, GPC_UNIT(gpc, 0x0824), 0xc0000000);
+               for (tpc = 0; tpc < priv->tpc_nr[gpc]; tpc++) {
+                       nv_wr32(priv, TPC_UNIT(gpc, tpc, 0x508), 0xffffffff);
+                       nv_wr32(priv, TPC_UNIT(gpc, tpc, 0x50c), 0xffffffff);
+                       nv_wr32(priv, TPC_UNIT(gpc, tpc, 0x224), 0xc0000000);
+                       nv_wr32(priv, TPC_UNIT(gpc, tpc, 0x48c), 0xc0000000);
+                       nv_wr32(priv, TPC_UNIT(gpc, tpc, 0x084), 0xc0000000);
+                       nv_wr32(priv, TPC_UNIT(gpc, tpc, 0x644), 0x001ffffe);
+                       nv_wr32(priv, TPC_UNIT(gpc, tpc, 0x64c), 0x0000000f);
+               }
+               nv_wr32(priv, GPC_UNIT(gpc, 0x2c90), 0xffffffff);
+               nv_wr32(priv, GPC_UNIT(gpc, 0x2c94), 0xffffffff);
+       }
+
+       for (rop = 0; rop < priv->rop_nr; rop++) {
+               nv_wr32(priv, ROP_UNIT(rop, 0x144), 0xc0000000);
+               nv_wr32(priv, ROP_UNIT(rop, 0x070), 0xc0000000);
+               nv_wr32(priv, ROP_UNIT(rop, 0x204), 0xffffffff);
+               nv_wr32(priv, ROP_UNIT(rop, 0x208), 0xffffffff);
+       }
+
+       nv_wr32(priv, 0x400108, 0xffffffff);
+       nv_wr32(priv, 0x400138, 0xffffffff);
+       nv_wr32(priv, 0x400118, 0xffffffff);
+       nv_wr32(priv, 0x400130, 0xffffffff);
+       nv_wr32(priv, 0x40011c, 0xffffffff);
+       nv_wr32(priv, 0x400134, 0xffffffff);
+
+       nv_wr32(priv, 0x400054, 0x34ce3464);
+
+       gf100_gr_zbc_init(priv);
+
+       return gf100_gr_init_ctxctl(priv);
+}
+
+#include "fuc/hubgk104.fuc3.h"
+
+static struct gf100_gr_ucode
+gk104_gr_fecs_ucode = {
+       .code.data = gk104_grhub_code,
+       .code.size = sizeof(gk104_grhub_code),
+       .data.data = gk104_grhub_data,
+       .data.size = sizeof(gk104_grhub_data),
+};
+
+#include "fuc/gpcgk104.fuc3.h"
+
+static struct gf100_gr_ucode
+gk104_gr_gpccs_ucode = {
+       .code.data = gk104_grgpc_code,
+       .code.size = sizeof(gk104_grgpc_code),
+       .data.data = gk104_grgpc_data,
+       .data.size = sizeof(gk104_grgpc_data),
+};
+
+struct nvkm_oclass *
+gk104_gr_oclass = &(struct gf100_gr_oclass) {
+       .base.handle = NV_ENGINE(GR, 0xe4),
+       .base.ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = gf100_gr_ctor,
+               .dtor = gf100_gr_dtor,
+               .init = gk104_gr_init,
+               .fini = _nvkm_gr_fini,
+       },
+       .cclass = &gk104_grctx_oclass,
+       .sclass = gk104_gr_sclass,
+       .mmio = gk104_gr_pack_mmio,
+       .fecs.ucode = &gk104_gr_fecs_ucode,
+       .gpccs.ucode = &gk104_gr_gpccs_ucode,
+       .ppc_nr = 1,
+}.base;
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/gr/gk110.c b/drivers/gpu/drm/nouveau/nvkm/engine/gr/gk110.c
new file mode 100644 (file)
index 0000000..78e03ab
--- /dev/null
@@ -0,0 +1,248 @@
+/*
+ * Copyright 2013 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 <bskeggs@redhat.com>
+ */
+#include "gf100.h"
+#include "ctxgf100.h"
+
+#include <subdev/timer.h>
+
+#include <nvif/class.h>
+
+/*******************************************************************************
+ * Graphics object classes
+ ******************************************************************************/
+
+struct nvkm_oclass
+gk110_gr_sclass[] = {
+       { 0x902d, &nvkm_object_ofuncs },
+       { 0xa140, &nvkm_object_ofuncs },
+       { KEPLER_B, &gf100_fermi_ofuncs, gf100_gr_9097_omthds },
+       { KEPLER_COMPUTE_B, &nvkm_object_ofuncs, gf100_gr_90c0_omthds },
+       {}
+};
+
+/*******************************************************************************
+ * PGRAPH register lists
+ ******************************************************************************/
+
+const struct gf100_gr_init
+gk110_gr_init_fe_0[] = {
+       { 0x40415c,   1, 0x04, 0x00000000 },
+       { 0x404170,   1, 0x04, 0x00000000 },
+       { 0x4041b4,   1, 0x04, 0x00000000 },
+       {}
+};
+
+const struct gf100_gr_init
+gk110_gr_init_ds_0[] = {
+       { 0x405844,   1, 0x04, 0x00ffffff },
+       { 0x405850,   1, 0x04, 0x00000000 },
+       { 0x405900,   1, 0x04, 0x0000ff00 },
+       { 0x405908,   1, 0x04, 0x00000000 },
+       { 0x405928,   2, 0x04, 0x00000000 },
+       {}
+};
+
+const struct gf100_gr_init
+gk110_gr_init_sked_0[] = {
+       { 0x407010,   1, 0x04, 0x00000000 },
+       { 0x407040,   1, 0x04, 0x80440424 },
+       { 0x407048,   1, 0x04, 0x0000000a },
+       {}
+};
+
+const struct gf100_gr_init
+gk110_gr_init_cwd_0[] = {
+       { 0x405b44,   1, 0x04, 0x00000000 },
+       { 0x405b50,   1, 0x04, 0x00000000 },
+       {}
+};
+
+const struct gf100_gr_init
+gk110_gr_init_gpc_unk_1[] = {
+       { 0x418d00,   1, 0x04, 0x00000000 },
+       { 0x418d28,   2, 0x04, 0x00000000 },
+       { 0x418f00,   1, 0x04, 0x00000400 },
+       { 0x418f08,   1, 0x04, 0x00000000 },
+       { 0x418f20,   2, 0x04, 0x00000000 },
+       { 0x418e00,   1, 0x04, 0x00000000 },
+       { 0x418e08,   1, 0x04, 0x00000000 },
+       { 0x418e1c,   2, 0x04, 0x00000000 },
+       {}
+};
+
+const struct gf100_gr_init
+gk110_gr_init_tex_0[] = {
+       { 0x419ab0,   1, 0x04, 0x00000000 },
+       { 0x419ac8,   1, 0x04, 0x00000000 },
+       { 0x419ab8,   1, 0x04, 0x000000e7 },
+       { 0x419aec,   1, 0x04, 0x00000000 },
+       { 0x419abc,   2, 0x04, 0x00000000 },
+       { 0x419ab4,   1, 0x04, 0x00000000 },
+       { 0x419aa8,   2, 0x04, 0x00000000 },
+       {}
+};
+
+static const struct gf100_gr_init
+gk110_gr_init_l1c_0[] = {
+       { 0x419c98,   1, 0x04, 0x00000000 },
+       { 0x419ca8,   1, 0x04, 0x00000000 },
+       { 0x419cb0,   1, 0x04, 0x01000000 },
+       { 0x419cb4,   1, 0x04, 0x00000000 },
+       { 0x419cb8,   1, 0x04, 0x00b08bea },
+       { 0x419c84,   1, 0x04, 0x00010384 },
+       { 0x419cbc,   1, 0x04, 0x281b3646 },
+       { 0x419cc0,   2, 0x04, 0x00000000 },
+       { 0x419c80,   1, 0x04, 0x00020230 },
+       { 0x419ccc,   2, 0x04, 0x00000000 },
+       {}
+};
+
+const struct gf100_gr_init
+gk110_gr_init_sm_0[] = {
+       { 0x419e00,   1, 0x04, 0x00000080 },
+       { 0x419ea0,   1, 0x04, 0x00000000 },
+       { 0x419ee4,   1, 0x04, 0x00000000 },
+       { 0x419ea4,   1, 0x04, 0x00000100 },
+       { 0x419ea8,   1, 0x04, 0x00000000 },
+       { 0x419eb4,   1, 0x04, 0x00000000 },
+       { 0x419ebc,   2, 0x04, 0x00000000 },
+       { 0x419edc,   1, 0x04, 0x00000000 },
+       { 0x419f00,   1, 0x04, 0x00000000 },
+       { 0x419ed0,   1, 0x04, 0x00003234 },
+       { 0x419f74,   1, 0x04, 0x00015555 },
+       { 0x419f80,   4, 0x04, 0x00000000 },
+       {}
+};
+
+static const struct gf100_gr_pack
+gk110_gr_pack_mmio[] = {
+       { gk104_gr_init_main_0 },
+       { gk110_gr_init_fe_0 },
+       { gf100_gr_init_pri_0 },
+       { gf100_gr_init_rstr2d_0 },
+       { gf119_gr_init_pd_0 },
+       { gk110_gr_init_ds_0 },
+       { gf100_gr_init_scc_0 },
+       { gk110_gr_init_sked_0 },
+       { gk110_gr_init_cwd_0 },
+       { gf119_gr_init_prop_0 },
+       { gf108_gr_init_gpc_unk_0 },
+       { gf100_gr_init_setup_0 },
+       { gf100_gr_init_crstr_0 },
+       { gf108_gr_init_setup_1 },
+       { gf100_gr_init_zcull_0 },
+       { gf119_gr_init_gpm_0 },
+       { gk110_gr_init_gpc_unk_1 },
+       { gf100_gr_init_gcc_0 },
+       { gk104_gr_init_tpccs_0 },
+       { gk110_gr_init_tex_0 },
+       { gk104_gr_init_pe_0 },
+       { gk110_gr_init_l1c_0 },
+       { gf100_gr_init_mpc_0 },
+       { gk110_gr_init_sm_0 },
+       { gf117_gr_init_pes_0 },
+       { gf117_gr_init_wwdx_0 },
+       { gf117_gr_init_cbm_0 },
+       { gk104_gr_init_be_0 },
+       { gf100_gr_init_fe_1 },
+       {}
+};
+
+/*******************************************************************************
+ * PGRAPH engine/subdev functions
+ ******************************************************************************/
+
+int
+gk110_gr_fini(struct nvkm_object *object, bool suspend)
+{
+       struct gf100_gr_priv *priv = (void *)object;
+       static const struct {
+               u32 addr;
+               u32 data;
+       } magic[] = {
+               { 0x020520, 0xfffffffc },
+               { 0x020524, 0xfffffffe },
+               { 0x020524, 0xfffffffc },
+               { 0x020524, 0xfffffff8 },
+               { 0x020524, 0xffffffe0 },
+               { 0x020530, 0xfffffffe },
+               { 0x02052c, 0xfffffffa },
+               { 0x02052c, 0xfffffff0 },
+               { 0x02052c, 0xffffffc0 },
+               { 0x02052c, 0xffffff00 },
+               { 0x02052c, 0xfffffc00 },
+               { 0x02052c, 0xfffcfc00 },
+               { 0x02052c, 0xfff0fc00 },
+               { 0x02052c, 0xff80fc00 },
+               { 0x020528, 0xfffffffe },
+               { 0x020528, 0xfffffffc },
+       };
+       int i;
+
+       nv_mask(priv, 0x000200, 0x08001000, 0x00000000);
+       nv_mask(priv, 0x0206b4, 0x00000000, 0x00000000);
+       for (i = 0; i < ARRAY_SIZE(magic); i++) {
+               nv_wr32(priv, magic[i].addr, magic[i].data);
+               nv_wait(priv, magic[i].addr, 0x80000000, 0x00000000);
+       }
+
+       return nvkm_gr_fini(&priv->base, suspend);
+}
+
+#include "fuc/hubgk110.fuc3.h"
+
+struct gf100_gr_ucode
+gk110_gr_fecs_ucode = {
+       .code.data = gk110_grhub_code,
+       .code.size = sizeof(gk110_grhub_code),
+       .data.data = gk110_grhub_data,
+       .data.size = sizeof(gk110_grhub_data),
+};
+
+#include "fuc/gpcgk110.fuc3.h"
+
+struct gf100_gr_ucode
+gk110_gr_gpccs_ucode = {
+       .code.data = gk110_grgpc_code,
+       .code.size = sizeof(gk110_grgpc_code),
+       .data.data = gk110_grgpc_data,
+       .data.size = sizeof(gk110_grgpc_data),
+};
+
+struct nvkm_oclass *
+gk110_gr_oclass = &(struct gf100_gr_oclass) {
+       .base.handle = NV_ENGINE(GR, 0xf0),
+       .base.ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = gf100_gr_ctor,
+               .dtor = gf100_gr_dtor,
+               .init = gk104_gr_init,
+               .fini = gk110_gr_fini,
+       },
+       .cclass = &gk110_grctx_oclass,
+       .sclass =  gk110_gr_sclass,
+       .mmio = gk110_gr_pack_mmio,
+       .fecs.ucode = &gk110_gr_fecs_ucode,
+       .gpccs.ucode = &gk110_gr_gpccs_ucode,
+       .ppc_nr = 2,
+}.base;
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/gr/gk110b.c b/drivers/gpu/drm/nouveau/nvkm/engine/gr/gk110b.c
new file mode 100644 (file)
index 0000000..5292c5a
--- /dev/null
@@ -0,0 +1,116 @@
+/*
+ * Copyright 2013 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 <bskeggs@redhat.com>
+ */
+#include "gf100.h"
+#include "ctxgf100.h"
+
+/*******************************************************************************
+ * PGRAPH register lists
+ ******************************************************************************/
+
+static const struct gf100_gr_init
+gk110b_gr_init_l1c_0[] = {
+       { 0x419c98,   1, 0x04, 0x00000000 },
+       { 0x419ca8,   1, 0x04, 0x00000000 },
+       { 0x419cb0,   1, 0x04, 0x09000000 },
+       { 0x419cb4,   1, 0x04, 0x00000000 },
+       { 0x419cb8,   1, 0x04, 0x00b08bea },
+       { 0x419c84,   1, 0x04, 0x00010384 },
+       { 0x419cbc,   1, 0x04, 0x281b3646 },
+       { 0x419cc0,   2, 0x04, 0x00000000 },
+       { 0x419c80,   1, 0x04, 0x00020230 },
+       { 0x419ccc,   2, 0x04, 0x00000000 },
+       {}
+};
+
+static const struct gf100_gr_init
+gk110b_gr_init_sm_0[] = {
+       { 0x419e00,   1, 0x04, 0x00000080 },
+       { 0x419ea0,   1, 0x04, 0x00000000 },
+       { 0x419ee4,   1, 0x04, 0x00000000 },
+       { 0x419ea4,   1, 0x04, 0x00000100 },
+       { 0x419ea8,   1, 0x04, 0x00000000 },
+       { 0x419eb4,   1, 0x04, 0x00000000 },
+       { 0x419ebc,   2, 0x04, 0x00000000 },
+       { 0x419edc,   1, 0x04, 0x00000000 },
+       { 0x419f00,   1, 0x04, 0x00000000 },
+       { 0x419ed0,   1, 0x04, 0x00002616 },
+       { 0x419f74,   1, 0x04, 0x00015555 },
+       { 0x419f80,   4, 0x04, 0x00000000 },
+       {}
+};
+
+static const struct gf100_gr_pack
+gk110b_gr_pack_mmio[] = {
+       { gk104_gr_init_main_0 },
+       { gk110_gr_init_fe_0 },
+       { gf100_gr_init_pri_0 },
+       { gf100_gr_init_rstr2d_0 },
+       { gf119_gr_init_pd_0 },
+       { gk110_gr_init_ds_0 },
+       { gf100_gr_init_scc_0 },
+       { gk110_gr_init_sked_0 },
+       { gk110_gr_init_cwd_0 },
+       { gf119_gr_init_prop_0 },
+       { gf108_gr_init_gpc_unk_0 },
+       { gf100_gr_init_setup_0 },
+       { gf100_gr_init_crstr_0 },
+       { gf108_gr_init_setup_1 },
+       { gf100_gr_init_zcull_0 },
+       { gf119_gr_init_gpm_0 },
+       { gk110_gr_init_gpc_unk_1 },
+       { gf100_gr_init_gcc_0 },
+       { gk104_gr_init_tpccs_0 },
+       { gk110_gr_init_tex_0 },
+       { gk104_gr_init_pe_0 },
+       { gk110b_gr_init_l1c_0 },
+       { gf100_gr_init_mpc_0 },
+       { gk110b_gr_init_sm_0 },
+       { gf117_gr_init_pes_0 },
+       { gf117_gr_init_wwdx_0 },
+       { gf117_gr_init_cbm_0 },
+       { gk104_gr_init_be_0 },
+       { gf100_gr_init_fe_1 },
+       {}
+};
+
+/*******************************************************************************
+ * PGRAPH engine/subdev functions
+ ******************************************************************************/
+
+struct nvkm_oclass *
+gk110b_gr_oclass = &(struct gf100_gr_oclass) {
+       .base.handle = NV_ENGINE(GR, 0xf1),
+       .base.ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = gf100_gr_ctor,
+               .dtor = gf100_gr_dtor,
+               .init = gk104_gr_init,
+               .fini = gk110_gr_fini,
+       },
+       .cclass = &gk110b_grctx_oclass,
+       .sclass =  gk110_gr_sclass,
+       .mmio = gk110b_gr_pack_mmio,
+       .fecs.ucode = &gk110_gr_fecs_ucode,
+       .gpccs.ucode = &gk110_gr_gpccs_ucode,
+       .ppc_nr = 2,
+}.base;
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/gr/gk208.c b/drivers/gpu/drm/nouveau/nvkm/engine/gr/gk208.c
new file mode 100644 (file)
index 0000000..ae6b853
--- /dev/null
@@ -0,0 +1,227 @@
+/*
+ * Copyright 2013 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 <bskeggs@redhat.com>
+ */
+#include "gf100.h"
+#include "ctxgf100.h"
+
+#include <subdev/timer.h>
+
+#include <nvif/class.h>
+
+/*******************************************************************************
+ * Graphics object classes
+ ******************************************************************************/
+
+static struct nvkm_oclass
+gk208_gr_sclass[] = {
+       { 0x902d, &nvkm_object_ofuncs },
+       { 0xa140, &nvkm_object_ofuncs },
+       { KEPLER_B, &gf100_fermi_ofuncs },
+       { 0xa1c0, &nvkm_object_ofuncs },
+       {}
+};
+
+/*******************************************************************************
+ * PGRAPH register lists
+ ******************************************************************************/
+
+static const struct gf100_gr_init
+gk208_gr_init_main_0[] = {
+       { 0x400080,   1, 0x04, 0x003083c2 },
+       { 0x400088,   1, 0x04, 0x0001bfe7 },
+       { 0x40008c,   1, 0x04, 0x00000000 },
+       { 0x400090,   1, 0x04, 0x00000030 },
+       { 0x40013c,   1, 0x04, 0x003901f7 },
+       { 0x400140,   1, 0x04, 0x00000100 },
+       { 0x400144,   1, 0x04, 0x00000000 },
+       { 0x400148,   1, 0x04, 0x00000110 },
+       { 0x400138,   1, 0x04, 0x00000000 },
+       { 0x400130,   2, 0x04, 0x00000000 },
+       { 0x400124,   1, 0x04, 0x00000002 },
+       {}
+};
+
+static const struct gf100_gr_init
+gk208_gr_init_ds_0[] = {
+       { 0x405844,   1, 0x04, 0x00ffffff },
+       { 0x405850,   1, 0x04, 0x00000000 },
+       { 0x405900,   1, 0x04, 0x00000000 },
+       { 0x405908,   1, 0x04, 0x00000000 },
+       { 0x405928,   2, 0x04, 0x00000000 },
+       {}
+};
+
+const struct gf100_gr_init
+gk208_gr_init_gpc_unk_0[] = {
+       { 0x418604,   1, 0x04, 0x00000000 },
+       { 0x418680,   1, 0x04, 0x00000000 },
+       { 0x418714,   1, 0x04, 0x00000000 },
+       { 0x418384,   2, 0x04, 0x00000000 },
+       {}
+};
+
+static const struct gf100_gr_init
+gk208_gr_init_setup_1[] = {
+       { 0x4188c8,   2, 0x04, 0x00000000 },
+       { 0x4188d0,   1, 0x04, 0x00010000 },
+       { 0x4188d4,   1, 0x04, 0x00000201 },
+       {}
+};
+
+static const struct gf100_gr_init
+gk208_gr_init_tex_0[] = {
+       { 0x419ab0,   1, 0x04, 0x00000000 },
+       { 0x419ac8,   1, 0x04, 0x00000000 },
+       { 0x419ab8,   1, 0x04, 0x000000e7 },
+       { 0x419abc,   2, 0x04, 0x00000000 },
+       { 0x419ab4,   1, 0x04, 0x00000000 },
+       { 0x419aa8,   2, 0x04, 0x00000000 },
+       {}
+};
+
+static const struct gf100_gr_init
+gk208_gr_init_l1c_0[] = {
+       { 0x419c98,   1, 0x04, 0x00000000 },
+       { 0x419ca8,   1, 0x04, 0x00000000 },
+       { 0x419cb0,   1, 0x04, 0x01000000 },
+       { 0x419cb4,   1, 0x04, 0x00000000 },
+       { 0x419cb8,   1, 0x04, 0x00b08bea },
+       { 0x419c84,   1, 0x04, 0x00010384 },
+       { 0x419cbc,   1, 0x04, 0x281b3646 },
+       { 0x419cc0,   2, 0x04, 0x00000000 },
+       { 0x419c80,   1, 0x04, 0x00000230 },
+       { 0x419ccc,   2, 0x04, 0x00000000 },
+       {}
+};
+
+static const struct gf100_gr_pack
+gk208_gr_pack_mmio[] = {
+       { gk208_gr_init_main_0 },
+       { gk110_gr_init_fe_0 },
+       { gf100_gr_init_pri_0 },
+       { gf100_gr_init_rstr2d_0 },
+       { gf119_gr_init_pd_0 },
+       { gk208_gr_init_ds_0 },
+       { gf100_gr_init_scc_0 },
+       { gk110_gr_init_sked_0 },
+       { gk110_gr_init_cwd_0 },
+       { gf119_gr_init_prop_0 },
+       { gk208_gr_init_gpc_unk_0 },
+       { gf100_gr_init_setup_0 },
+       { gf100_gr_init_crstr_0 },
+       { gk208_gr_init_setup_1 },
+       { gf100_gr_init_zcull_0 },
+       { gf119_gr_init_gpm_0 },
+       { gk110_gr_init_gpc_unk_1 },
+       { gf100_gr_init_gcc_0 },
+       { gk104_gr_init_tpccs_0 },
+       { gk208_gr_init_tex_0 },
+       { gk104_gr_init_pe_0 },
+       { gk208_gr_init_l1c_0 },
+       { gf100_gr_init_mpc_0 },
+       { gk110_gr_init_sm_0 },
+       { gf117_gr_init_pes_0 },
+       { gf117_gr_init_wwdx_0 },
+       { gf117_gr_init_cbm_0 },
+       { gk104_gr_init_be_0 },
+       { gf100_gr_init_fe_1 },
+       {}
+};
+
+/*******************************************************************************
+ * PGRAPH engine/subdev functions
+ ******************************************************************************/
+
+static int
+gk208_gr_fini(struct nvkm_object *object, bool suspend)
+{
+       struct gf100_gr_priv *priv = (void *)object;
+       static const struct {
+               u32 addr;
+               u32 data;
+       } magic[] = {
+               { 0x020520, 0xfffffffc },
+               { 0x020524, 0xfffffffe },
+               { 0x020524, 0xfffffffc },
+               { 0x020524, 0xfffffff8 },
+               { 0x020524, 0xffffffe0 },
+               { 0x020530, 0xfffffffe },
+               { 0x02052c, 0xfffffffa },
+               { 0x02052c, 0xfffffff0 },
+               { 0x02052c, 0xffffffc0 },
+               { 0x02052c, 0xffffff00 },
+               { 0x02052c, 0xfffffc00 },
+               { 0x02052c, 0xfffcfc00 },
+               { 0x02052c, 0xfff0fc00 },
+               { 0x02052c, 0xff80fc00 },
+               { 0x020528, 0xfffffffe },
+               { 0x020528, 0xfffffffc },
+       };
+       int i;
+
+       nv_mask(priv, 0x000200, 0x08001000, 0x00000000);
+       nv_mask(priv, 0x0206b4, 0x00000000, 0x00000000);
+       for (i = 0; i < ARRAY_SIZE(magic); i++) {
+               nv_wr32(priv, magic[i].addr, magic[i].data);
+               nv_wait(priv, magic[i].addr, 0x80000000, 0x00000000);
+       }
+
+       return nvkm_gr_fini(&priv->base, suspend);
+}
+
+#include "fuc/hubgk208.fuc5.h"
+
+static struct gf100_gr_ucode
+gk208_gr_fecs_ucode = {
+       .code.data = gk208_grhub_code,
+       .code.size = sizeof(gk208_grhub_code),
+       .data.data = gk208_grhub_data,
+       .data.size = sizeof(gk208_grhub_data),
+};
+
+#include "fuc/gpcgk208.fuc5.h"
+
+static struct gf100_gr_ucode
+gk208_gr_gpccs_ucode = {
+       .code.data = gk208_grgpc_code,
+       .code.size = sizeof(gk208_grgpc_code),
+       .data.data = gk208_grgpc_data,
+       .data.size = sizeof(gk208_grgpc_data),
+};
+
+struct nvkm_oclass *
+gk208_gr_oclass = &(struct gf100_gr_oclass) {
+       .base.handle = NV_ENGINE(GR, 0x08),
+       .base.ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = gf100_gr_ctor,
+               .dtor = gf100_gr_dtor,
+               .init = gk104_gr_init,
+               .fini = gk208_gr_fini,
+       },
+       .cclass = &gk208_grctx_oclass,
+       .sclass =  gk208_gr_sclass,
+       .mmio = gk208_gr_pack_mmio,
+       .fecs.ucode = &gk208_gr_fecs_ucode,
+       .gpccs.ucode = &gk208_gr_gpccs_ucode,
+       .ppc_nr = 1,
+}.base;
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/gr/gk20a.c b/drivers/gpu/drm/nouveau/nvkm/engine/gr/gk20a.c
new file mode 100644 (file)
index 0000000..2137555
--- /dev/null
@@ -0,0 +1,49 @@
+/*
+ * Copyright (c) 2014, NVIDIA CORPORATION. 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 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 "gf100.h"
+#include "ctxgf100.h"
+
+#include <nvif/class.h>
+
+static struct nvkm_oclass
+gk20a_gr_sclass[] = {
+       { 0x902d, &nvkm_object_ofuncs },
+       { 0xa040, &nvkm_object_ofuncs },
+       { KEPLER_C, &gf100_fermi_ofuncs, gf100_gr_9097_omthds },
+       { KEPLER_COMPUTE_A, &nvkm_object_ofuncs, gf100_gr_90c0_omthds },
+       {}
+};
+
+struct nvkm_oclass *
+gk20a_gr_oclass = &(struct gf100_gr_oclass) {
+       .base.handle = NV_ENGINE(GR, 0xea),
+       .base.ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = gf100_gr_ctor,
+               .dtor = gf100_gr_dtor,
+               .init = gk104_gr_init,
+               .fini = _nvkm_gr_fini,
+       },
+       .cclass = &gk20a_grctx_oclass,
+       .sclass = gk20a_gr_sclass,
+       .mmio = gk104_gr_pack_mmio,
+       .ppc_nr = 1,
+}.base;
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/gr/gm107.c b/drivers/gpu/drm/nouveau/nvkm/engine/gr/gm107.c
new file mode 100644 (file)
index 0000000..124492b
--- /dev/null
@@ -0,0 +1,470 @@
+/*
+ * Copyright 2013 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 <bskeggs@redhat.com>
+ */
+#include "gf100.h"
+#include "ctxgf100.h"
+
+#include <subdev/bios.h>
+#include <subdev/bios/P0260.h>
+
+#include <nvif/class.h>
+
+/*******************************************************************************
+ * Graphics object classes
+ ******************************************************************************/
+
+static struct nvkm_oclass
+gm107_gr_sclass[] = {
+       { 0x902d, &nvkm_object_ofuncs },
+       { 0xa140, &nvkm_object_ofuncs },
+       { MAXWELL_A, &gf100_fermi_ofuncs, gf100_gr_9097_omthds },
+       { MAXWELL_COMPUTE_A, &nvkm_object_ofuncs, gf100_gr_90c0_omthds },
+       {}
+};
+
+/*******************************************************************************
+ * PGRAPH register lists
+ ******************************************************************************/
+
+static const struct gf100_gr_init
+gm107_gr_init_main_0[] = {
+       { 0x400080,   1, 0x04, 0x003003c2 },
+       { 0x400088,   1, 0x04, 0x0001bfe7 },
+       { 0x40008c,   1, 0x04, 0x00060000 },
+       { 0x400090,   1, 0x04, 0x00000030 },
+       { 0x40013c,   1, 0x04, 0x003901f3 },
+       { 0x400140,   1, 0x04, 0x00000100 },
+       { 0x400144,   1, 0x04, 0x00000000 },
+       { 0x400148,   1, 0x04, 0x00000110 },
+       { 0x400138,   1, 0x04, 0x00000000 },
+       { 0x400130,   2, 0x04, 0x00000000 },
+       { 0x400124,   1, 0x04, 0x00000002 },
+       {}
+};
+
+static const struct gf100_gr_init
+gm107_gr_init_ds_0[] = {
+       { 0x405844,   1, 0x04, 0x00ffffff },
+       { 0x405850,   1, 0x04, 0x00000000 },
+       { 0x405900,   1, 0x04, 0x00000000 },
+       { 0x405908,   1, 0x04, 0x00000000 },
+       {}
+};
+
+static const struct gf100_gr_init
+gm107_gr_init_scc_0[] = {
+       { 0x40803c,   1, 0x04, 0x00000010 },
+       {}
+};
+
+static const struct gf100_gr_init
+gm107_gr_init_sked_0[] = {
+       { 0x407010,   1, 0x04, 0x00000000 },
+       { 0x407040,   1, 0x04, 0x40440424 },
+       { 0x407048,   1, 0x04, 0x0000000a },
+       {}
+};
+
+static const struct gf100_gr_init
+gm107_gr_init_prop_0[] = {
+       { 0x418408,   1, 0x04, 0x00000000 },
+       { 0x4184a0,   1, 0x04, 0x00000000 },
+       {}
+};
+
+static const struct gf100_gr_init
+gm107_gr_init_setup_1[] = {
+       { 0x4188c8,   2, 0x04, 0x00000000 },
+       { 0x4188d0,   1, 0x04, 0x00010000 },
+       { 0x4188d4,   1, 0x04, 0x00010201 },
+       {}
+};
+
+static const struct gf100_gr_init
+gm107_gr_init_zcull_0[] = {
+       { 0x418910,   1, 0x04, 0x00010001 },
+       { 0x418914,   1, 0x04, 0x00000301 },
+       { 0x418918,   1, 0x04, 0x00800000 },
+       { 0x418930,   2, 0x04, 0x00000000 },
+       { 0x418980,   1, 0x04, 0x77777770 },
+       { 0x418984,   3, 0x04, 0x77777777 },
+       {}
+};
+
+static const struct gf100_gr_init
+gm107_gr_init_gpc_unk_1[] = {
+       { 0x418d00,   1, 0x04, 0x00000000 },
+       { 0x418f00,   1, 0x04, 0x00000400 },
+       { 0x418f08,   1, 0x04, 0x00000000 },
+       { 0x418e08,   1, 0x04, 0x00000000 },
+       {}
+};
+
+static const struct gf100_gr_init
+gm107_gr_init_tpccs_0[] = {
+       { 0x419dc4,   1, 0x04, 0x00000000 },
+       { 0x419dc8,   1, 0x04, 0x00000501 },
+       { 0x419dd0,   1, 0x04, 0x00000000 },
+       { 0x419dd4,   1, 0x04, 0x00000100 },
+       { 0x419dd8,   1, 0x04, 0x00000001 },
+       { 0x419ddc,   1, 0x04, 0x00000002 },
+       { 0x419de0,   1, 0x04, 0x00000001 },
+       { 0x419d0c,   1, 0x04, 0x00000000 },
+       { 0x419d10,   1, 0x04, 0x00000014 },
+       {}
+};
+
+static const struct gf100_gr_init
+gm107_gr_init_tex_0[] = {
+       { 0x419ab0,   1, 0x04, 0x00000000 },
+       { 0x419ab8,   1, 0x04, 0x000000e7 },
+       { 0x419abc,   1, 0x04, 0x00000000 },
+       { 0x419acc,   1, 0x04, 0x000000ff },
+       { 0x419ac0,   1, 0x04, 0x00000000 },
+       { 0x419aa8,   2, 0x04, 0x00000000 },
+       { 0x419ad0,   2, 0x04, 0x00000000 },
+       { 0x419ae0,   2, 0x04, 0x00000000 },
+       { 0x419af0,   4, 0x04, 0x00000000 },
+       {}
+};
+
+static const struct gf100_gr_init
+gm107_gr_init_pe_0[] = {
+       { 0x419900,   1, 0x04, 0x000000ff },
+       { 0x41980c,   1, 0x04, 0x00000010 },
+       { 0x419844,   1, 0x04, 0x00000000 },
+       { 0x419838,   1, 0x04, 0x000000ff },
+       { 0x419850,   1, 0x04, 0x00000004 },
+       { 0x419854,   2, 0x04, 0x00000000 },
+       { 0x419894,   3, 0x04, 0x00100401 },
+       {}
+};
+
+static const struct gf100_gr_init
+gm107_gr_init_l1c_0[] = {
+       { 0x419c98,   1, 0x04, 0x00000000 },
+       { 0x419cc0,   2, 0x04, 0x00000000 },
+       {}
+};
+
+static const struct gf100_gr_init
+gm107_gr_init_sm_0[] = {
+       { 0x419e30,   1, 0x04, 0x000000ff },
+       { 0x419e00,   1, 0x04, 0x00000000 },
+       { 0x419ea0,   1, 0x04, 0x00000000 },
+       { 0x419ee4,   1, 0x04, 0x00000000 },
+       { 0x419ea4,   1, 0x04, 0x00000100 },
+       { 0x419ea8,   1, 0x04, 0x01000000 },
+       { 0x419ee8,   1, 0x04, 0x00000091 },
+       { 0x419eb4,   1, 0x04, 0x00000000 },
+       { 0x419ebc,   2, 0x04, 0x00000000 },
+       { 0x419edc,   1, 0x04, 0x000c1810 },
+       { 0x419ed8,   1, 0x04, 0x00000000 },
+       { 0x419ee0,   1, 0x04, 0x00000000 },
+       { 0x419f74,   1, 0x04, 0x00005155 },
+       { 0x419f80,   4, 0x04, 0x00000000 },
+       {}
+};
+
+static const struct gf100_gr_init
+gm107_gr_init_l1c_1[] = {
+       { 0x419ccc,   2, 0x04, 0x00000000 },
+       { 0x419c80,   1, 0x04, 0x3f006022 },
+       { 0x419c88,   1, 0x04, 0x00000000 },
+       {}
+};
+
+static const struct gf100_gr_init
+gm107_gr_init_pes_0[] = {
+       { 0x41be50,   1, 0x04, 0x000000ff },
+       { 0x41be04,   1, 0x04, 0x00000000 },
+       { 0x41be08,   1, 0x04, 0x00000004 },
+       { 0x41be0c,   1, 0x04, 0x00000008 },
+       { 0x41be10,   1, 0x04, 0x0e3b8bc7 },
+       { 0x41be14,   2, 0x04, 0x00000000 },
+       { 0x41be3c,   5, 0x04, 0x00100401 },
+       {}
+};
+
+static const struct gf100_gr_init
+gm107_gr_init_wwdx_0[] = {
+       { 0x41bfd4,   1, 0x04, 0x00800000 },
+       { 0x41bfdc,   1, 0x04, 0x00000000 },
+       {}
+};
+
+static const struct gf100_gr_init
+gm107_gr_init_cbm_0[] = {
+       { 0x41becc,   1, 0x04, 0x00000000 },
+       {}
+};
+
+static const struct gf100_gr_init
+gm107_gr_init_be_0[] = {
+       { 0x408890,   1, 0x04, 0x000000ff },
+       { 0x40880c,   1, 0x04, 0x00000000 },
+       { 0x408850,   1, 0x04, 0x00000004 },
+       { 0x408878,   1, 0x04, 0x00c81603 },
+       { 0x40887c,   1, 0x04, 0x80543432 },
+       { 0x408880,   1, 0x04, 0x0010581e },
+       { 0x408884,   1, 0x04, 0x00001205 },
+       { 0x408974,   1, 0x04, 0x000000ff },
+       { 0x408910,   9, 0x04, 0x00000000 },
+       { 0x408950,   1, 0x04, 0x00000000 },
+       { 0x408954,   1, 0x04, 0x0000ffff },
+       { 0x408958,   1, 0x04, 0x00000034 },
+       { 0x40895c,   1, 0x04, 0x8531a003 },
+       { 0x408960,   1, 0x04, 0x0561985a },
+       { 0x408964,   1, 0x04, 0x04e15c4f },
+       { 0x408968,   1, 0x04, 0x02808833 },
+       { 0x40896c,   1, 0x04, 0x01f02438 },
+       { 0x408970,   1, 0x04, 0x00012c00 },
+       { 0x408984,   1, 0x04, 0x00000000 },
+       { 0x408988,   1, 0x04, 0x08040201 },
+       { 0x40898c,   1, 0x04, 0x80402010 },
+       {}
+};
+
+static const struct gf100_gr_init
+gm107_gr_init_sm_1[] = {
+       { 0x419e5c,   1, 0x04, 0x00000000 },
+       { 0x419e58,   1, 0x04, 0x00000000 },
+       {}
+};
+
+static const struct gf100_gr_pack
+gm107_gr_pack_mmio[] = {
+       { gm107_gr_init_main_0 },
+       { gk110_gr_init_fe_0 },
+       { gf100_gr_init_pri_0 },
+       { gf100_gr_init_rstr2d_0 },
+       { gf100_gr_init_pd_0 },
+       { gm107_gr_init_ds_0 },
+       { gm107_gr_init_scc_0 },
+       { gm107_gr_init_sked_0 },
+       { gk110_gr_init_cwd_0 },
+       { gm107_gr_init_prop_0 },
+       { gk208_gr_init_gpc_unk_0 },
+       { gf100_gr_init_setup_0 },
+       { gf100_gr_init_crstr_0 },
+       { gm107_gr_init_setup_1 },
+       { gm107_gr_init_zcull_0 },
+       { gf100_gr_init_gpm_0 },
+       { gm107_gr_init_gpc_unk_1 },
+       { gf100_gr_init_gcc_0 },
+       { gm107_gr_init_tpccs_0 },
+       { gm107_gr_init_tex_0 },
+       { gm107_gr_init_pe_0 },
+       { gm107_gr_init_l1c_0 },
+       { gf100_gr_init_mpc_0 },
+       { gm107_gr_init_sm_0 },
+       { gm107_gr_init_l1c_1 },
+       { gm107_gr_init_pes_0 },
+       { gm107_gr_init_wwdx_0 },
+       { gm107_gr_init_cbm_0 },
+       { gm107_gr_init_be_0 },
+       { gm107_gr_init_sm_1 },
+       {}
+};
+
+/*******************************************************************************
+ * PGRAPH engine/subdev functions
+ ******************************************************************************/
+
+static void
+gm107_gr_init_bios(struct gf100_gr_priv *priv)
+{
+       static const struct {
+               u32 ctrl;
+               u32 data;
+       } regs[] = {
+               { 0x419ed8, 0x419ee0 },
+               { 0x419ad0, 0x419ad4 },
+               { 0x419ae0, 0x419ae4 },
+               { 0x419af0, 0x419af4 },
+               { 0x419af8, 0x419afc },
+       };
+       struct nvkm_bios *bios = nvkm_bios(priv);
+       struct nvbios_P0260E infoE;
+       struct nvbios_P0260X infoX;
+       int E = -1, X;
+       u8 ver, hdr;
+
+       while (nvbios_P0260Ep(bios, ++E, &ver, &hdr, &infoE)) {
+               if (X = -1, E < ARRAY_SIZE(regs)) {
+                       nv_wr32(priv, regs[E].ctrl, infoE.data);
+                       while (nvbios_P0260Xp(bios, ++X, &ver, &hdr, &infoX))
+                               nv_wr32(priv, regs[E].data, infoX.data);
+               }
+       }
+}
+
+int
+gm107_gr_init(struct nvkm_object *object)
+{
+       struct gf100_gr_oclass *oclass = (void *)object->oclass;
+       struct gf100_gr_priv *priv = (void *)object;
+       const u32 magicgpc918 = DIV_ROUND_UP(0x00800000, priv->tpc_total);
+       u32 data[TPC_MAX / 8] = {};
+       u8  tpcnr[GPC_MAX];
+       int gpc, tpc, ppc, rop;
+       int ret, i;
+
+       ret = nvkm_gr_init(&priv->base);
+       if (ret)
+               return ret;
+
+       nv_wr32(priv, GPC_BCAST(0x0880), 0x00000000);
+       nv_wr32(priv, GPC_BCAST(0x0890), 0x00000000);
+       nv_wr32(priv, GPC_BCAST(0x0894), 0x00000000);
+       nv_wr32(priv, GPC_BCAST(0x08b4), priv->unk4188b4->addr >> 8);
+       nv_wr32(priv, GPC_BCAST(0x08b8), priv->unk4188b8->addr >> 8);
+
+       gf100_gr_mmio(priv, oclass->mmio);
+
+       gm107_gr_init_bios(priv);
+
+       nv_wr32(priv, GPC_UNIT(0, 0x3018), 0x00000001);
+
+       memset(data, 0x00, sizeof(data));
+       memcpy(tpcnr, priv->tpc_nr, sizeof(priv->tpc_nr));
+       for (i = 0, gpc = -1; i < priv->tpc_total; i++) {
+               do {
+                       gpc = (gpc + 1) % priv->gpc_nr;
+               } while (!tpcnr[gpc]);
+               tpc = priv->tpc_nr[gpc] - tpcnr[gpc]--;
+
+               data[i / 8] |= tpc << ((i % 8) * 4);
+       }
+
+       nv_wr32(priv, GPC_BCAST(0x0980), data[0]);
+       nv_wr32(priv, GPC_BCAST(0x0984), data[1]);
+       nv_wr32(priv, GPC_BCAST(0x0988), data[2]);
+       nv_wr32(priv, GPC_BCAST(0x098c), data[3]);
+
+       for (gpc = 0; gpc < priv->gpc_nr; gpc++) {
+               nv_wr32(priv, GPC_UNIT(gpc, 0x0914),
+                       priv->magic_not_rop_nr << 8 | priv->tpc_nr[gpc]);
+               nv_wr32(priv, GPC_UNIT(gpc, 0x0910), 0x00040000 |
+                       priv->tpc_total);
+               nv_wr32(priv, GPC_UNIT(gpc, 0x0918), magicgpc918);
+       }
+
+       nv_wr32(priv, GPC_BCAST(0x3fd4), magicgpc918);
+       nv_wr32(priv, GPC_BCAST(0x08ac), nv_rd32(priv, 0x100800));
+
+       nv_wr32(priv, 0x400500, 0x00010001);
+
+       nv_wr32(priv, 0x400100, 0xffffffff);
+       nv_wr32(priv, 0x40013c, 0xffffffff);
+       nv_wr32(priv, 0x400124, 0x00000002);
+       nv_wr32(priv, 0x409c24, 0x000e0000);
+
+       nv_wr32(priv, 0x404000, 0xc0000000);
+       nv_wr32(priv, 0x404600, 0xc0000000);
+       nv_wr32(priv, 0x408030, 0xc0000000);
+       nv_wr32(priv, 0x404490, 0xc0000000);
+       nv_wr32(priv, 0x406018, 0xc0000000);
+       nv_wr32(priv, 0x407020, 0x40000000);
+       nv_wr32(priv, 0x405840, 0xc0000000);
+       nv_wr32(priv, 0x405844, 0x00ffffff);
+       nv_mask(priv, 0x419cc0, 0x00000008, 0x00000008);
+
+       for (gpc = 0; gpc < priv->gpc_nr; gpc++) {
+               for (ppc = 0; ppc < 2 /* priv->ppc_nr[gpc] */; ppc++)
+                       nv_wr32(priv, PPC_UNIT(gpc, ppc, 0x038), 0xc0000000);
+               nv_wr32(priv, GPC_UNIT(gpc, 0x0420), 0xc0000000);
+               nv_wr32(priv, GPC_UNIT(gpc, 0x0900), 0xc0000000);
+               nv_wr32(priv, GPC_UNIT(gpc, 0x1028), 0xc0000000);
+               nv_wr32(priv, GPC_UNIT(gpc, 0x0824), 0xc0000000);
+               for (tpc = 0; tpc < priv->tpc_nr[gpc]; tpc++) {
+                       nv_wr32(priv, TPC_UNIT(gpc, tpc, 0x508), 0xffffffff);
+                       nv_wr32(priv, TPC_UNIT(gpc, tpc, 0x50c), 0xffffffff);
+                       nv_wr32(priv, TPC_UNIT(gpc, tpc, 0x224), 0xc0000000);
+                       nv_wr32(priv, TPC_UNIT(gpc, tpc, 0x48c), 0xc0000000);
+                       nv_wr32(priv, TPC_UNIT(gpc, tpc, 0x084), 0xc0000000);
+                       nv_wr32(priv, TPC_UNIT(gpc, tpc, 0x430), 0xc0000000);
+                       nv_wr32(priv, TPC_UNIT(gpc, tpc, 0x644), 0x00dffffe);
+                       nv_wr32(priv, TPC_UNIT(gpc, tpc, 0x64c), 0x00000005);
+               }
+               nv_wr32(priv, GPC_UNIT(gpc, 0x2c90), 0xffffffff);
+               nv_wr32(priv, GPC_UNIT(gpc, 0x2c94), 0xffffffff);
+       }
+
+       for (rop = 0; rop < priv->rop_nr; rop++) {
+               nv_wr32(priv, ROP_UNIT(rop, 0x144), 0x40000000);
+               nv_wr32(priv, ROP_UNIT(rop, 0x070), 0x40000000);
+               nv_wr32(priv, ROP_UNIT(rop, 0x204), 0xffffffff);
+               nv_wr32(priv, ROP_UNIT(rop, 0x208), 0xffffffff);
+       }
+
+       nv_wr32(priv, 0x400108, 0xffffffff);
+       nv_wr32(priv, 0x400138, 0xffffffff);
+       nv_wr32(priv, 0x400118, 0xffffffff);
+       nv_wr32(priv, 0x400130, 0xffffffff);
+       nv_wr32(priv, 0x40011c, 0xffffffff);
+       nv_wr32(priv, 0x400134, 0xffffffff);
+
+       nv_wr32(priv, 0x400054, 0x2c350f63);
+
+       gf100_gr_zbc_init(priv);
+
+       return gf100_gr_init_ctxctl(priv);
+}
+
+#include "fuc/hubgm107.fuc5.h"
+
+static struct gf100_gr_ucode
+gm107_gr_fecs_ucode = {
+       .code.data = gm107_grhub_code,
+       .code.size = sizeof(gm107_grhub_code),
+       .data.data = gm107_grhub_data,
+       .data.size = sizeof(gm107_grhub_data),
+};
+
+#include "fuc/gpcgm107.fuc5.h"
+
+static struct gf100_gr_ucode
+gm107_gr_gpccs_ucode = {
+       .code.data = gm107_grgpc_code,
+       .code.size = sizeof(gm107_grgpc_code),
+       .data.data = gm107_grgpc_data,
+       .data.size = sizeof(gm107_grgpc_data),
+};
+
+struct nvkm_oclass *
+gm107_gr_oclass = &(struct gf100_gr_oclass) {
+       .base.handle = NV_ENGINE(GR, 0x07),
+       .base.ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = gf100_gr_ctor,
+               .dtor = gf100_gr_dtor,
+               .init = gm107_gr_init,
+               .fini = _nvkm_gr_fini,
+       },
+       .cclass = &gm107_grctx_oclass,
+       .sclass =  gm107_gr_sclass,
+       .mmio = gm107_gr_pack_mmio,
+       .fecs.ucode = 0 ? &gm107_gr_fecs_ucode : NULL,
+       .gpccs.ucode = &gm107_gr_gpccs_ucode,
+       .ppc_nr = 2,
+}.base;
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/gr/nv04.c b/drivers/gpu/drm/nouveau/nvkm/engine/gr/nv04.c
new file mode 100644 (file)
index 0000000..2614510
--- /dev/null
@@ -0,0 +1,1382 @@
+/*
+ * Copyright 2007 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
+ * paragr) 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 <engine/gr.h>
+#include "regs.h"
+
+#include <core/client.h>
+#include <core/device.h>
+#include <core/handle.h>
+#include <engine/fifo.h>
+#include <subdev/instmem.h>
+#include <subdev/timer.h>
+
+static u32
+nv04_gr_ctx_regs[] = {
+       0x0040053c,
+       0x00400544,
+       0x00400540,
+       0x00400548,
+       NV04_PGRAPH_CTX_SWITCH1,
+       NV04_PGRAPH_CTX_SWITCH2,
+       NV04_PGRAPH_CTX_SWITCH3,
+       NV04_PGRAPH_CTX_SWITCH4,
+       NV04_PGRAPH_CTX_CACHE1,
+       NV04_PGRAPH_CTX_CACHE2,
+       NV04_PGRAPH_CTX_CACHE3,
+       NV04_PGRAPH_CTX_CACHE4,
+       0x00400184,
+       0x004001a4,
+       0x004001c4,
+       0x004001e4,
+       0x00400188,
+       0x004001a8,
+       0x004001c8,
+       0x004001e8,
+       0x0040018c,
+       0x004001ac,
+       0x004001cc,
+       0x004001ec,
+       0x00400190,
+       0x004001b0,
+       0x004001d0,
+       0x004001f0,
+       0x00400194,
+       0x004001b4,
+       0x004001d4,
+       0x004001f4,
+       0x00400198,
+       0x004001b8,
+       0x004001d8,
+       0x004001f8,
+       0x0040019c,
+       0x004001bc,
+       0x004001dc,
+       0x004001fc,
+       0x00400174,
+       NV04_PGRAPH_DMA_START_0,
+       NV04_PGRAPH_DMA_START_1,
+       NV04_PGRAPH_DMA_LENGTH,
+       NV04_PGRAPH_DMA_MISC,
+       NV04_PGRAPH_DMA_PITCH,
+       NV04_PGRAPH_BOFFSET0,
+       NV04_PGRAPH_BBASE0,
+       NV04_PGRAPH_BLIMIT0,
+       NV04_PGRAPH_BOFFSET1,
+       NV04_PGRAPH_BBASE1,
+       NV04_PGRAPH_BLIMIT1,
+       NV04_PGRAPH_BOFFSET2,
+       NV04_PGRAPH_BBASE2,
+       NV04_PGRAPH_BLIMIT2,
+       NV04_PGRAPH_BOFFSET3,
+       NV04_PGRAPH_BBASE3,
+       NV04_PGRAPH_BLIMIT3,
+       NV04_PGRAPH_BOFFSET4,
+       NV04_PGRAPH_BBASE4,
+       NV04_PGRAPH_BLIMIT4,
+       NV04_PGRAPH_BOFFSET5,
+       NV04_PGRAPH_BBASE5,
+       NV04_PGRAPH_BLIMIT5,
+       NV04_PGRAPH_BPITCH0,
+       NV04_PGRAPH_BPITCH1,
+       NV04_PGRAPH_BPITCH2,
+       NV04_PGRAPH_BPITCH3,
+       NV04_PGRAPH_BPITCH4,
+       NV04_PGRAPH_SURFACE,
+       NV04_PGRAPH_STATE,
+       NV04_PGRAPH_BSWIZZLE2,
+       NV04_PGRAPH_BSWIZZLE5,
+       NV04_PGRAPH_BPIXEL,
+       NV04_PGRAPH_NOTIFY,
+       NV04_PGRAPH_PATT_COLOR0,
+       NV04_PGRAPH_PATT_COLOR1,
+       NV04_PGRAPH_PATT_COLORRAM+0x00,
+       NV04_PGRAPH_PATT_COLORRAM+0x04,
+       NV04_PGRAPH_PATT_COLORRAM+0x08,
+       NV04_PGRAPH_PATT_COLORRAM+0x0c,
+       NV04_PGRAPH_PATT_COLORRAM+0x10,
+       NV04_PGRAPH_PATT_COLORRAM+0x14,
+       NV04_PGRAPH_PATT_COLORRAM+0x18,
+       NV04_PGRAPH_PATT_COLORRAM+0x1c,
+       NV04_PGRAPH_PATT_COLORRAM+0x20,
+       NV04_PGRAPH_PATT_COLORRAM+0x24,
+       NV04_PGRAPH_PATT_COLORRAM+0x28,
+       NV04_PGRAPH_PATT_COLORRAM+0x2c,
+       NV04_PGRAPH_PATT_COLORRAM+0x30,
+       NV04_PGRAPH_PATT_COLORRAM+0x34,
+       NV04_PGRAPH_PATT_COLORRAM+0x38,
+       NV04_PGRAPH_PATT_COLORRAM+0x3c,
+       NV04_PGRAPH_PATT_COLORRAM+0x40,
+       NV04_PGRAPH_PATT_COLORRAM+0x44,
+       NV04_PGRAPH_PATT_COLORRAM+0x48,
+       NV04_PGRAPH_PATT_COLORRAM+0x4c,
+       NV04_PGRAPH_PATT_COLORRAM+0x50,
+       NV04_PGRAPH_PATT_COLORRAM+0x54,
+       NV04_PGRAPH_PATT_COLORRAM+0x58,
+       NV04_PGRAPH_PATT_COLORRAM+0x5c,
+       NV04_PGRAPH_PATT_COLORRAM+0x60,
+       NV04_PGRAPH_PATT_COLORRAM+0x64,
+       NV04_PGRAPH_PATT_COLORRAM+0x68,
+       NV04_PGRAPH_PATT_COLORRAM+0x6c,
+       NV04_PGRAPH_PATT_COLORRAM+0x70,
+       NV04_PGRAPH_PATT_COLORRAM+0x74,
+       NV04_PGRAPH_PATT_COLORRAM+0x78,
+       NV04_PGRAPH_PATT_COLORRAM+0x7c,
+       NV04_PGRAPH_PATT_COLORRAM+0x80,
+       NV04_PGRAPH_PATT_COLORRAM+0x84,
+       NV04_PGRAPH_PATT_COLORRAM+0x88,
+       NV04_PGRAPH_PATT_COLORRAM+0x8c,
+       NV04_PGRAPH_PATT_COLORRAM+0x90,
+       NV04_PGRAPH_PATT_COLORRAM+0x94,
+       NV04_PGRAPH_PATT_COLORRAM+0x98,
+       NV04_PGRAPH_PATT_COLORRAM+0x9c,
+       NV04_PGRAPH_PATT_COLORRAM+0xa0,
+       NV04_PGRAPH_PATT_COLORRAM+0xa4,
+       NV04_PGRAPH_PATT_COLORRAM+0xa8,
+       NV04_PGRAPH_PATT_COLORRAM+0xac,
+       NV04_PGRAPH_PATT_COLORRAM+0xb0,
+       NV04_PGRAPH_PATT_COLORRAM+0xb4,
+       NV04_PGRAPH_PATT_COLORRAM+0xb8,
+       NV04_PGRAPH_PATT_COLORRAM+0xbc,
+       NV04_PGRAPH_PATT_COLORRAM+0xc0,
+       NV04_PGRAPH_PATT_COLORRAM+0xc4,
+       NV04_PGRAPH_PATT_COLORRAM+0xc8,
+       NV04_PGRAPH_PATT_COLORRAM+0xcc,
+       NV04_PGRAPH_PATT_COLORRAM+0xd0,
+       NV04_PGRAPH_PATT_COLORRAM+0xd4,
+       NV04_PGRAPH_PATT_COLORRAM+0xd8,
+       NV04_PGRAPH_PATT_COLORRAM+0xdc,
+       NV04_PGRAPH_PATT_COLORRAM+0xe0,
+       NV04_PGRAPH_PATT_COLORRAM+0xe4,
+       NV04_PGRAPH_PATT_COLORRAM+0xe8,
+       NV04_PGRAPH_PATT_COLORRAM+0xec,
+       NV04_PGRAPH_PATT_COLORRAM+0xf0,
+       NV04_PGRAPH_PATT_COLORRAM+0xf4,
+       NV04_PGRAPH_PATT_COLORRAM+0xf8,
+       NV04_PGRAPH_PATT_COLORRAM+0xfc,
+       NV04_PGRAPH_PATTERN,
+       0x0040080c,
+       NV04_PGRAPH_PATTERN_SHAPE,
+       0x00400600,
+       NV04_PGRAPH_ROP3,
+       NV04_PGRAPH_CHROMA,
+       NV04_PGRAPH_BETA_AND,
+       NV04_PGRAPH_BETA_PREMULT,
+       NV04_PGRAPH_CONTROL0,
+       NV04_PGRAPH_CONTROL1,
+       NV04_PGRAPH_CONTROL2,
+       NV04_PGRAPH_BLEND,
+       NV04_PGRAPH_STORED_FMT,
+       NV04_PGRAPH_SOURCE_COLOR,
+       0x00400560,
+       0x00400568,
+       0x00400564,
+       0x0040056c,
+       0x00400400,
+       0x00400480,
+       0x00400404,
+       0x00400484,
+       0x00400408,
+       0x00400488,
+       0x0040040c,
+       0x0040048c,
+       0x00400410,
+       0x00400490,
+       0x00400414,
+       0x00400494,
+       0x00400418,
+       0x00400498,
+       0x0040041c,
+       0x0040049c,
+       0x00400420,
+       0x004004a0,
+       0x00400424,
+       0x004004a4,
+       0x00400428,
+       0x004004a8,
+       0x0040042c,
+       0x004004ac,
+       0x00400430,
+       0x004004b0,
+       0x00400434,
+       0x004004b4,
+       0x00400438,
+       0x004004b8,
+       0x0040043c,
+       0x004004bc,
+       0x00400440,
+       0x004004c0,
+       0x00400444,
+       0x004004c4,
+       0x00400448,
+       0x004004c8,
+       0x0040044c,
+       0x004004cc,
+       0x00400450,
+       0x004004d0,
+       0x00400454,
+       0x004004d4,
+       0x00400458,
+       0x004004d8,
+       0x0040045c,
+       0x004004dc,
+       0x00400460,
+       0x004004e0,
+       0x00400464,
+       0x004004e4,
+       0x00400468,
+       0x004004e8,
+       0x0040046c,
+       0x004004ec,
+       0x00400470,
+       0x004004f0,
+       0x00400474,
+       0x004004f4,
+       0x00400478,
+       0x004004f8,
+       0x0040047c,
+       0x004004fc,
+       0x00400534,
+       0x00400538,
+       0x00400514,
+       0x00400518,
+       0x0040051c,
+       0x00400520,
+       0x00400524,
+       0x00400528,
+       0x0040052c,
+       0x00400530,
+       0x00400d00,
+       0x00400d40,
+       0x00400d80,
+       0x00400d04,
+       0x00400d44,
+       0x00400d84,
+       0x00400d08,
+       0x00400d48,
+       0x00400d88,
+       0x00400d0c,
+       0x00400d4c,
+       0x00400d8c,
+       0x00400d10,
+       0x00400d50,
+       0x00400d90,
+       0x00400d14,
+       0x00400d54,
+       0x00400d94,
+       0x00400d18,
+       0x00400d58,
+       0x00400d98,
+       0x00400d1c,
+       0x00400d5c,
+       0x00400d9c,
+       0x00400d20,
+       0x00400d60,
+       0x00400da0,
+       0x00400d24,
+       0x00400d64,
+       0x00400da4,
+       0x00400d28,
+       0x00400d68,
+       0x00400da8,
+       0x00400d2c,
+       0x00400d6c,
+       0x00400dac,
+       0x00400d30,
+       0x00400d70,
+       0x00400db0,
+       0x00400d34,
+       0x00400d74,
+       0x00400db4,
+       0x00400d38,
+       0x00400d78,
+       0x00400db8,
+       0x00400d3c,
+       0x00400d7c,
+       0x00400dbc,
+       0x00400590,
+       0x00400594,
+       0x00400598,
+       0x0040059c,
+       0x004005a8,
+       0x004005ac,
+       0x004005b0,
+       0x004005b4,
+       0x004005c0,
+       0x004005c4,
+       0x004005c8,
+       0x004005cc,
+       0x004005d0,
+       0x004005d4,
+       0x004005d8,
+       0x004005dc,
+       0x004005e0,
+       NV04_PGRAPH_PASSTHRU_0,
+       NV04_PGRAPH_PASSTHRU_1,
+       NV04_PGRAPH_PASSTHRU_2,
+       NV04_PGRAPH_DVD_COLORFMT,
+       NV04_PGRAPH_SCALED_FORMAT,
+       NV04_PGRAPH_MISC24_0,
+       NV04_PGRAPH_MISC24_1,
+       NV04_PGRAPH_MISC24_2,
+       0x00400500,
+       0x00400504,
+       NV04_PGRAPH_VALID1,
+       NV04_PGRAPH_VALID2,
+       NV04_PGRAPH_DEBUG_3
+};
+
+struct nv04_gr_priv {
+       struct nvkm_gr base;
+       struct nv04_gr_chan *chan[16];
+       spinlock_t lock;
+};
+
+struct nv04_gr_chan {
+       struct nvkm_object base;
+       int chid;
+       u32 nv04[ARRAY_SIZE(nv04_gr_ctx_regs)];
+};
+
+
+static inline struct nv04_gr_priv *
+nv04_gr_priv(struct nv04_gr_chan *chan)
+{
+       return (void *)nv_object(chan)->engine;
+}
+
+/*******************************************************************************
+ * Graphics object classes
+ ******************************************************************************/
+
+/*
+ * Software methods, why they are needed, and how they all work:
+ *
+ * NV04 and NV05 keep most of the state in PGRAPH context itself, but some
+ * 2d engine settings are kept inside the grobjs themselves. The grobjs are
+ * 3 words long on both. grobj format on NV04 is:
+ *
+ * word 0:
+ *  - bits 0-7: class
+ *  - bit 12: color key active
+ *  - bit 13: clip rect active
+ *  - bit 14: if set, destination surface is swizzled and taken from buffer 5
+ *            [set by NV04_SWIZZLED_SURFACE], otherwise it's linear and taken
+ *            from buffer 0 [set by NV04_CONTEXT_SURFACES_2D or
+ *            NV03_CONTEXT_SURFACE_DST].
+ *  - bits 15-17: 2d operation [aka patch config]
+ *  - bit 24: patch valid [enables rendering using this object]
+ *  - bit 25: surf3d valid [for tex_tri and multitex_tri only]
+ * word 1:
+ *  - bits 0-1: mono format
+ *  - bits 8-13: color format
+ *  - bits 16-31: DMA_NOTIFY instance
+ * word 2:
+ *  - bits 0-15: DMA_A instance
+ *  - bits 16-31: DMA_B instance
+ *
+ * On NV05 it's:
+ *
+ * word 0:
+ *  - bits 0-7: class
+ *  - bit 12: color key active
+ *  - bit 13: clip rect active
+ *  - bit 14: if set, destination surface is swizzled and taken from buffer 5
+ *            [set by NV04_SWIZZLED_SURFACE], otherwise it's linear and taken
+ *            from buffer 0 [set by NV04_CONTEXT_SURFACES_2D or
+ *            NV03_CONTEXT_SURFACE_DST].
+ *  - bits 15-17: 2d operation [aka patch config]
+ *  - bits 20-22: dither mode
+ *  - bit 24: patch valid [enables rendering using this object]
+ *  - bit 25: surface_dst/surface_color/surf2d/surf3d valid
+ *  - bit 26: surface_src/surface_zeta valid
+ *  - bit 27: pattern valid
+ *  - bit 28: rop valid
+ *  - bit 29: beta1 valid
+ *  - bit 30: beta4 valid
+ * word 1:
+ *  - bits 0-1: mono format
+ *  - bits 8-13: color format
+ *  - bits 16-31: DMA_NOTIFY instance
+ * word 2:
+ *  - bits 0-15: DMA_A instance
+ *  - bits 16-31: DMA_B instance
+ *
+ * NV05 will set/unset the relevant valid bits when you poke the relevant
+ * object-binding methods with object of the proper type, or with the NULL
+ * type. It'll only allow rendering using the grobj if all needed objects
+ * are bound. The needed set of objects depends on selected operation: for
+ * example rop object is needed by ROP_AND, but not by SRCCOPY_AND.
+ *
+ * NV04 doesn't have these methods implemented at all, and doesn't have the
+ * relevant bits in grobj. Instead, it'll allow rendering whenever bit 24
+ * is set. So we have to emulate them in software, internally keeping the
+ * same bits as NV05 does. Since grobjs are aligned to 16 bytes on nv04,
+ * but the last word isn't actually used for anything, we abuse it for this
+ * purpose.
+ *
+ * Actually, NV05 can optionally check bit 24 too, but we disable this since
+ * there's no use for it.
+ *
+ * For unknown reasons, NV04 implements surf3d binding in hardware as an
+ * exception. Also for unknown reasons, NV04 doesn't implement the clipping
+ * methods on the surf3d object, so we have to emulate them too.
+ */
+
+static void
+nv04_gr_set_ctx1(struct nvkm_object *object, u32 mask, u32 value)
+{
+       struct nv04_gr_priv *priv = (void *)object->engine;
+       int subc = (nv_rd32(priv, NV04_PGRAPH_TRAPPED_ADDR) >> 13) & 0x7;
+       u32 tmp;
+
+       tmp  = nv_ro32(object, 0x00);
+       tmp &= ~mask;
+       tmp |= value;
+       nv_wo32(object, 0x00, tmp);
+
+       nv_wr32(priv, NV04_PGRAPH_CTX_SWITCH1, tmp);
+       nv_wr32(priv, NV04_PGRAPH_CTX_CACHE1 + (subc<<2), tmp);
+}
+
+static void
+nv04_gr_set_ctx_val(struct nvkm_object *object, u32 mask, u32 value)
+{
+       int class, op, valid = 1;
+       u32 tmp, ctx1;
+
+       ctx1 = nv_ro32(object, 0x00);
+       class = ctx1 & 0xff;
+       op = (ctx1 >> 15) & 7;
+
+       tmp = nv_ro32(object, 0x0c);
+       tmp &= ~mask;
+       tmp |= value;
+       nv_wo32(object, 0x0c, tmp);
+
+       /* check for valid surf2d/surf_dst/surf_color */
+       if (!(tmp & 0x02000000))
+               valid = 0;
+       /* check for valid surf_src/surf_zeta */
+       if ((class == 0x1f || class == 0x48) && !(tmp & 0x04000000))
+               valid = 0;
+
+       switch (op) {
+       /* SRCCOPY_AND, SRCCOPY: no extra objects required */
+       case 0:
+       case 3:
+               break;
+       /* ROP_AND: requires pattern and rop */
+       case 1:
+               if (!(tmp & 0x18000000))
+                       valid = 0;
+               break;
+       /* BLEND_AND: requires beta1 */
+       case 2:
+               if (!(tmp & 0x20000000))
+                       valid = 0;
+               break;
+       /* SRCCOPY_PREMULT, BLEND_PREMULT: beta4 required */
+       case 4:
+       case 5:
+               if (!(tmp & 0x40000000))
+                       valid = 0;
+               break;
+       }
+
+       nv04_gr_set_ctx1(object, 0x01000000, valid << 24);
+}
+
+static int
+nv04_gr_mthd_set_operation(struct nvkm_object *object, u32 mthd,
+                          void *args, u32 size)
+{
+       u32 class = nv_ro32(object, 0) & 0xff;
+       u32 data = *(u32 *)args;
+       if (data > 5)
+               return 1;
+       /* Old versions of the objects only accept first three operations. */
+       if (data > 2 && class < 0x40)
+               return 1;
+       nv04_gr_set_ctx1(object, 0x00038000, data << 15);
+       /* changing operation changes set of objects needed for validation */
+       nv04_gr_set_ctx_val(object, 0, 0);
+       return 0;
+}
+
+static int
+nv04_gr_mthd_surf3d_clip_h(struct nvkm_object *object, u32 mthd,
+                          void *args, u32 size)
+{
+       struct nv04_gr_priv *priv = (void *)object->engine;
+       u32 data = *(u32 *)args;
+       u32 min = data & 0xffff, max;
+       u32 w = data >> 16;
+       if (min & 0x8000)
+               /* too large */
+               return 1;
+       if (w & 0x8000)
+               /* yes, it accepts negative for some reason. */
+               w |= 0xffff0000;
+       max = min + w;
+       max &= 0x3ffff;
+       nv_wr32(priv, 0x40053c, min);
+       nv_wr32(priv, 0x400544, max);
+       return 0;
+}
+
+static int
+nv04_gr_mthd_surf3d_clip_v(struct nvkm_object *object, u32 mthd,
+                          void *args, u32 size)
+{
+       struct nv04_gr_priv *priv = (void *)object->engine;
+       u32 data = *(u32 *)args;
+       u32 min = data & 0xffff, max;
+       u32 w = data >> 16;
+       if (min & 0x8000)
+               /* too large */
+               return 1;
+       if (w & 0x8000)
+               /* yes, it accepts negative for some reason. */
+               w |= 0xffff0000;
+       max = min + w;
+       max &= 0x3ffff;
+       nv_wr32(priv, 0x400540, min);
+       nv_wr32(priv, 0x400548, max);
+       return 0;
+}
+
+static u16
+nv04_gr_mthd_bind_class(struct nvkm_object *object, u32 *args, u32 size)
+{
+       struct nvkm_instmem *imem = nvkm_instmem(object);
+       u32 inst = *(u32 *)args << 4;
+       return nv_ro32(imem, inst);
+}
+
+static int
+nv04_gr_mthd_bind_surf2d(struct nvkm_object *object, u32 mthd,
+                           void *args, u32 size)
+{
+       switch (nv04_gr_mthd_bind_class(object, args, size)) {
+       case 0x30:
+               nv04_gr_set_ctx1(object, 0x00004000, 0);
+               nv04_gr_set_ctx_val(object, 0x02000000, 0);
+               return 0;
+       case 0x42:
+               nv04_gr_set_ctx1(object, 0x00004000, 0);
+               nv04_gr_set_ctx_val(object, 0x02000000, 0x02000000);
+               return 0;
+       }
+       return 1;
+}
+
+static int
+nv04_gr_mthd_bind_surf2d_swzsurf(struct nvkm_object *object, u32 mthd,
+                                void *args, u32 size)
+{
+       switch (nv04_gr_mthd_bind_class(object, args, size)) {
+       case 0x30:
+               nv04_gr_set_ctx1(object, 0x00004000, 0);
+               nv04_gr_set_ctx_val(object, 0x02000000, 0);
+               return 0;
+       case 0x42:
+               nv04_gr_set_ctx1(object, 0x00004000, 0);
+               nv04_gr_set_ctx_val(object, 0x02000000, 0x02000000);
+               return 0;
+       case 0x52:
+               nv04_gr_set_ctx1(object, 0x00004000, 0x00004000);
+               nv04_gr_set_ctx_val(object, 0x02000000, 0x02000000);
+               return 0;
+       }
+       return 1;
+}
+
+static int
+nv01_gr_mthd_bind_patt(struct nvkm_object *object, u32 mthd,
+                      void *args, u32 size)
+{
+       switch (nv04_gr_mthd_bind_class(object, args, size)) {
+       case 0x30:
+               nv04_gr_set_ctx_val(object, 0x08000000, 0);
+               return 0;
+       case 0x18:
+               nv04_gr_set_ctx_val(object, 0x08000000, 0x08000000);
+               return 0;
+       }
+       return 1;
+}
+
+static int
+nv04_gr_mthd_bind_patt(struct nvkm_object *object, u32 mthd,
+                      void *args, u32 size)
+{
+       switch (nv04_gr_mthd_bind_class(object, args, size)) {
+       case 0x30:
+               nv04_gr_set_ctx_val(object, 0x08000000, 0);
+               return 0;
+       case 0x44:
+               nv04_gr_set_ctx_val(object, 0x08000000, 0x08000000);
+               return 0;
+       }
+       return 1;
+}
+
+static int
+nv04_gr_mthd_bind_rop(struct nvkm_object *object, u32 mthd,
+                     void *args, u32 size)
+{
+       switch (nv04_gr_mthd_bind_class(object, args, size)) {
+       case 0x30:
+               nv04_gr_set_ctx_val(object, 0x10000000, 0);
+               return 0;
+       case 0x43:
+               nv04_gr_set_ctx_val(object, 0x10000000, 0x10000000);
+               return 0;
+       }
+       return 1;
+}
+
+static int
+nv04_gr_mthd_bind_beta1(struct nvkm_object *object, u32 mthd,
+                       void *args, u32 size)
+{
+       switch (nv04_gr_mthd_bind_class(object, args, size)) {
+       case 0x30:
+               nv04_gr_set_ctx_val(object, 0x20000000, 0);
+               return 0;
+       case 0x12:
+               nv04_gr_set_ctx_val(object, 0x20000000, 0x20000000);
+               return 0;
+       }
+       return 1;
+}
+
+static int
+nv04_gr_mthd_bind_beta4(struct nvkm_object *object, u32 mthd,
+                       void *args, u32 size)
+{
+       switch (nv04_gr_mthd_bind_class(object, args, size)) {
+       case 0x30:
+               nv04_gr_set_ctx_val(object, 0x40000000, 0);
+               return 0;
+       case 0x72:
+               nv04_gr_set_ctx_val(object, 0x40000000, 0x40000000);
+               return 0;
+       }
+       return 1;
+}
+
+static int
+nv04_gr_mthd_bind_surf_dst(struct nvkm_object *object, u32 mthd,
+                          void *args, u32 size)
+{
+       switch (nv04_gr_mthd_bind_class(object, args, size)) {
+       case 0x30:
+               nv04_gr_set_ctx_val(object, 0x02000000, 0);
+               return 0;
+       case 0x58:
+               nv04_gr_set_ctx_val(object, 0x02000000, 0x02000000);
+               return 0;
+       }
+       return 1;
+}
+
+static int
+nv04_gr_mthd_bind_surf_src(struct nvkm_object *object, u32 mthd,
+                          void *args, u32 size)
+{
+       switch (nv04_gr_mthd_bind_class(object, args, size)) {
+       case 0x30:
+               nv04_gr_set_ctx_val(object, 0x04000000, 0);
+               return 0;
+       case 0x59:
+               nv04_gr_set_ctx_val(object, 0x04000000, 0x04000000);
+               return 0;
+       }
+       return 1;
+}
+
+static int
+nv04_gr_mthd_bind_surf_color(struct nvkm_object *object, u32 mthd,
+                            void *args, u32 size)
+{
+       switch (nv04_gr_mthd_bind_class(object, args, size)) {
+       case 0x30:
+               nv04_gr_set_ctx_val(object, 0x02000000, 0);
+               return 0;
+       case 0x5a:
+               nv04_gr_set_ctx_val(object, 0x02000000, 0x02000000);
+               return 0;
+       }
+       return 1;
+}
+
+static int
+nv04_gr_mthd_bind_surf_zeta(struct nvkm_object *object, u32 mthd,
+                           void *args, u32 size)
+{
+       switch (nv04_gr_mthd_bind_class(object, args, size)) {
+       case 0x30:
+               nv04_gr_set_ctx_val(object, 0x04000000, 0);
+               return 0;
+       case 0x5b:
+               nv04_gr_set_ctx_val(object, 0x04000000, 0x04000000);
+               return 0;
+       }
+       return 1;
+}
+
+static int
+nv01_gr_mthd_bind_clip(struct nvkm_object *object, u32 mthd,
+                      void *args, u32 size)
+{
+       switch (nv04_gr_mthd_bind_class(object, args, size)) {
+       case 0x30:
+               nv04_gr_set_ctx1(object, 0x2000, 0);
+               return 0;
+       case 0x19:
+               nv04_gr_set_ctx1(object, 0x2000, 0x2000);
+               return 0;
+       }
+       return 1;
+}
+
+static int
+nv01_gr_mthd_bind_chroma(struct nvkm_object *object, u32 mthd,
+                        void *args, u32 size)
+{
+       switch (nv04_gr_mthd_bind_class(object, args, size)) {
+       case 0x30:
+               nv04_gr_set_ctx1(object, 0x1000, 0);
+               return 0;
+       /* Yes, for some reason even the old versions of objects
+        * accept 0x57 and not 0x17. Consistency be damned.
+        */
+       case 0x57:
+               nv04_gr_set_ctx1(object, 0x1000, 0x1000);
+               return 0;
+       }
+       return 1;
+}
+
+static struct nvkm_omthds
+nv03_gr_gdi_omthds[] = {
+       { 0x0184, 0x0184, nv01_gr_mthd_bind_patt },
+       { 0x0188, 0x0188, nv04_gr_mthd_bind_rop },
+       { 0x018c, 0x018c, nv04_gr_mthd_bind_beta1 },
+       { 0x0190, 0x0190, nv04_gr_mthd_bind_surf_dst },
+       { 0x02fc, 0x02fc, nv04_gr_mthd_set_operation },
+       {}
+};
+
+static struct nvkm_omthds
+nv04_gr_gdi_omthds[] = {
+       { 0x0188, 0x0188, nv04_gr_mthd_bind_patt },
+       { 0x018c, 0x018c, nv04_gr_mthd_bind_rop },
+       { 0x0190, 0x0190, nv04_gr_mthd_bind_beta1 },
+       { 0x0194, 0x0194, nv04_gr_mthd_bind_beta4 },
+       { 0x0198, 0x0198, nv04_gr_mthd_bind_surf2d },
+       { 0x02fc, 0x02fc, nv04_gr_mthd_set_operation },
+       {}
+};
+
+static struct nvkm_omthds
+nv01_gr_blit_omthds[] = {
+       { 0x0184, 0x0184, nv01_gr_mthd_bind_chroma },
+       { 0x0188, 0x0188, nv01_gr_mthd_bind_clip },
+       { 0x018c, 0x018c, nv01_gr_mthd_bind_patt },
+       { 0x0190, 0x0190, nv04_gr_mthd_bind_rop },
+       { 0x0194, 0x0194, nv04_gr_mthd_bind_beta1 },
+       { 0x0198, 0x0198, nv04_gr_mthd_bind_surf_dst },
+       { 0x019c, 0x019c, nv04_gr_mthd_bind_surf_src },
+       { 0x02fc, 0x02fc, nv04_gr_mthd_set_operation },
+       {}
+};
+
+static struct nvkm_omthds
+nv04_gr_blit_omthds[] = {
+       { 0x0184, 0x0184, nv01_gr_mthd_bind_chroma },
+       { 0x0188, 0x0188, nv01_gr_mthd_bind_clip },
+       { 0x018c, 0x018c, nv04_gr_mthd_bind_patt },
+       { 0x0190, 0x0190, nv04_gr_mthd_bind_rop },
+       { 0x0194, 0x0194, nv04_gr_mthd_bind_beta1 },
+       { 0x0198, 0x0198, nv04_gr_mthd_bind_beta4 },
+       { 0x019c, 0x019c, nv04_gr_mthd_bind_surf2d },
+       { 0x02fc, 0x02fc, nv04_gr_mthd_set_operation },
+       {}
+};
+
+static struct nvkm_omthds
+nv04_gr_iifc_omthds[] = {
+       { 0x0188, 0x0188, nv01_gr_mthd_bind_chroma },
+       { 0x018c, 0x018c, nv01_gr_mthd_bind_clip },
+       { 0x0190, 0x0190, nv04_gr_mthd_bind_patt },
+       { 0x0194, 0x0194, nv04_gr_mthd_bind_rop },
+       { 0x0198, 0x0198, nv04_gr_mthd_bind_beta1 },
+       { 0x019c, 0x019c, nv04_gr_mthd_bind_beta4 },
+       { 0x01a0, 0x01a0, nv04_gr_mthd_bind_surf2d_swzsurf },
+       { 0x03e4, 0x03e4, nv04_gr_mthd_set_operation },
+       {}
+};
+
+static struct nvkm_omthds
+nv01_gr_ifc_omthds[] = {
+       { 0x0184, 0x0184, nv01_gr_mthd_bind_chroma },
+       { 0x0188, 0x0188, nv01_gr_mthd_bind_clip },
+       { 0x018c, 0x018c, nv01_gr_mthd_bind_patt },
+       { 0x0190, 0x0190, nv04_gr_mthd_bind_rop },
+       { 0x0194, 0x0194, nv04_gr_mthd_bind_beta1 },
+       { 0x0198, 0x0198, nv04_gr_mthd_bind_surf_dst },
+       { 0x02fc, 0x02fc, nv04_gr_mthd_set_operation },
+       {}
+};
+
+static struct nvkm_omthds
+nv04_gr_ifc_omthds[] = {
+       { 0x0184, 0x0184, nv01_gr_mthd_bind_chroma },
+       { 0x0188, 0x0188, nv01_gr_mthd_bind_clip },
+       { 0x018c, 0x018c, nv04_gr_mthd_bind_patt },
+       { 0x0190, 0x0190, nv04_gr_mthd_bind_rop },
+       { 0x0194, 0x0194, nv04_gr_mthd_bind_beta1 },
+       { 0x0198, 0x0198, nv04_gr_mthd_bind_beta4 },
+       { 0x019c, 0x019c, nv04_gr_mthd_bind_surf2d },
+       { 0x02fc, 0x02fc, nv04_gr_mthd_set_operation },
+       {}
+};
+
+static struct nvkm_omthds
+nv03_gr_sifc_omthds[] = {
+       { 0x0184, 0x0184, nv01_gr_mthd_bind_chroma },
+       { 0x0188, 0x0188, nv01_gr_mthd_bind_patt },
+       { 0x018c, 0x018c, nv04_gr_mthd_bind_rop },
+       { 0x0190, 0x0190, nv04_gr_mthd_bind_beta1 },
+       { 0x0194, 0x0194, nv04_gr_mthd_bind_surf_dst },
+       { 0x02fc, 0x02fc, nv04_gr_mthd_set_operation },
+       {}
+};
+
+static struct nvkm_omthds
+nv04_gr_sifc_omthds[] = {
+       { 0x0184, 0x0184, nv01_gr_mthd_bind_chroma },
+       { 0x0188, 0x0188, nv04_gr_mthd_bind_patt },
+       { 0x018c, 0x018c, nv04_gr_mthd_bind_rop },
+       { 0x0190, 0x0190, nv04_gr_mthd_bind_beta1 },
+       { 0x0194, 0x0194, nv04_gr_mthd_bind_beta4 },
+       { 0x0198, 0x0198, nv04_gr_mthd_bind_surf2d },
+       { 0x02fc, 0x02fc, nv04_gr_mthd_set_operation },
+       {}
+};
+
+static struct nvkm_omthds
+nv03_gr_sifm_omthds[] = {
+       { 0x0188, 0x0188, nv01_gr_mthd_bind_patt },
+       { 0x018c, 0x018c, nv04_gr_mthd_bind_rop },
+       { 0x0190, 0x0190, nv04_gr_mthd_bind_beta1 },
+       { 0x0194, 0x0194, nv04_gr_mthd_bind_surf_dst },
+       { 0x0304, 0x0304, nv04_gr_mthd_set_operation },
+       {}
+};
+
+static struct nvkm_omthds
+nv04_gr_sifm_omthds[] = {
+       { 0x0188, 0x0188, nv04_gr_mthd_bind_patt },
+       { 0x018c, 0x018c, nv04_gr_mthd_bind_rop },
+       { 0x0190, 0x0190, nv04_gr_mthd_bind_beta1 },
+       { 0x0194, 0x0194, nv04_gr_mthd_bind_beta4 },
+       { 0x0198, 0x0198, nv04_gr_mthd_bind_surf2d },
+       { 0x0304, 0x0304, nv04_gr_mthd_set_operation },
+       {}
+};
+
+static struct nvkm_omthds
+nv04_gr_surf3d_omthds[] = {
+       { 0x02f8, 0x02f8, nv04_gr_mthd_surf3d_clip_h },
+       { 0x02fc, 0x02fc, nv04_gr_mthd_surf3d_clip_v },
+       {}
+};
+
+static struct nvkm_omthds
+nv03_gr_ttri_omthds[] = {
+       { 0x0188, 0x0188, nv01_gr_mthd_bind_clip },
+       { 0x018c, 0x018c, nv04_gr_mthd_bind_surf_color },
+       { 0x0190, 0x0190, nv04_gr_mthd_bind_surf_zeta },
+       {}
+};
+
+static struct nvkm_omthds
+nv01_gr_prim_omthds[] = {
+       { 0x0184, 0x0184, nv01_gr_mthd_bind_clip },
+       { 0x0188, 0x0188, nv01_gr_mthd_bind_patt },
+       { 0x018c, 0x018c, nv04_gr_mthd_bind_rop },
+       { 0x0190, 0x0190, nv04_gr_mthd_bind_beta1 },
+       { 0x0194, 0x0194, nv04_gr_mthd_bind_surf_dst },
+       { 0x02fc, 0x02fc, nv04_gr_mthd_set_operation },
+       {}
+};
+
+static struct nvkm_omthds
+nv04_gr_prim_omthds[] = {
+       { 0x0184, 0x0184, nv01_gr_mthd_bind_clip },
+       { 0x0188, 0x0188, nv04_gr_mthd_bind_patt },
+       { 0x018c, 0x018c, nv04_gr_mthd_bind_rop },
+       { 0x0190, 0x0190, nv04_gr_mthd_bind_beta1 },
+       { 0x0194, 0x0194, nv04_gr_mthd_bind_beta4 },
+       { 0x0198, 0x0198, nv04_gr_mthd_bind_surf2d },
+       { 0x02fc, 0x02fc, nv04_gr_mthd_set_operation },
+       {}
+};
+
+static int
+nv04_gr_object_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+                   struct nvkm_oclass *oclass, void *data, u32 size,
+                   struct nvkm_object **pobject)
+{
+       struct nvkm_gpuobj *obj;
+       int ret;
+
+       ret = nvkm_gpuobj_create(parent, engine, oclass, 0, parent,
+                                16, 16, 0, &obj);
+       *pobject = nv_object(obj);
+       if (ret)
+               return ret;
+
+       nv_wo32(obj, 0x00, nv_mclass(obj));
+#ifdef __BIG_ENDIAN
+       nv_mo32(obj, 0x00, 0x00080000, 0x00080000);
+#endif
+       nv_wo32(obj, 0x04, 0x00000000);
+       nv_wo32(obj, 0x08, 0x00000000);
+       nv_wo32(obj, 0x0c, 0x00000000);
+       return 0;
+}
+
+struct nvkm_ofuncs
+nv04_gr_ofuncs = {
+       .ctor = nv04_gr_object_ctor,
+       .dtor = _nvkm_gpuobj_dtor,
+       .init = _nvkm_gpuobj_init,
+       .fini = _nvkm_gpuobj_fini,
+       .rd32 = _nvkm_gpuobj_rd32,
+       .wr32 = _nvkm_gpuobj_wr32,
+};
+
+static struct nvkm_oclass
+nv04_gr_sclass[] = {
+       { 0x0012, &nv04_gr_ofuncs }, /* beta1 */
+       { 0x0017, &nv04_gr_ofuncs }, /* chroma */
+       { 0x0018, &nv04_gr_ofuncs }, /* pattern (nv01) */
+       { 0x0019, &nv04_gr_ofuncs }, /* clip */
+       { 0x001c, &nv04_gr_ofuncs, nv01_gr_prim_omthds }, /* line */
+       { 0x001d, &nv04_gr_ofuncs, nv01_gr_prim_omthds }, /* tri */
+       { 0x001e, &nv04_gr_ofuncs, nv01_gr_prim_omthds }, /* rect */
+       { 0x001f, &nv04_gr_ofuncs, nv01_gr_blit_omthds },
+       { 0x0021, &nv04_gr_ofuncs, nv01_gr_ifc_omthds },
+       { 0x0030, &nv04_gr_ofuncs }, /* null */
+       { 0x0036, &nv04_gr_ofuncs, nv03_gr_sifc_omthds },
+       { 0x0037, &nv04_gr_ofuncs, nv03_gr_sifm_omthds },
+       { 0x0038, &nv04_gr_ofuncs }, /* dvd subpicture */
+       { 0x0039, &nv04_gr_ofuncs }, /* m2mf */
+       { 0x0042, &nv04_gr_ofuncs }, /* surf2d */
+       { 0x0043, &nv04_gr_ofuncs }, /* rop */
+       { 0x0044, &nv04_gr_ofuncs }, /* pattern */
+       { 0x0048, &nv04_gr_ofuncs, nv03_gr_ttri_omthds },
+       { 0x004a, &nv04_gr_ofuncs, nv04_gr_gdi_omthds },
+       { 0x004b, &nv04_gr_ofuncs, nv03_gr_gdi_omthds },
+       { 0x0052, &nv04_gr_ofuncs }, /* swzsurf */
+       { 0x0053, &nv04_gr_ofuncs, nv04_gr_surf3d_omthds },
+       { 0x0054, &nv04_gr_ofuncs }, /* ttri */
+       { 0x0055, &nv04_gr_ofuncs }, /* mtri */
+       { 0x0057, &nv04_gr_ofuncs }, /* chroma */
+       { 0x0058, &nv04_gr_ofuncs }, /* surf_dst */
+       { 0x0059, &nv04_gr_ofuncs }, /* surf_src */
+       { 0x005a, &nv04_gr_ofuncs }, /* surf_color */
+       { 0x005b, &nv04_gr_ofuncs }, /* surf_zeta */
+       { 0x005c, &nv04_gr_ofuncs, nv04_gr_prim_omthds }, /* line */
+       { 0x005d, &nv04_gr_ofuncs, nv04_gr_prim_omthds }, /* tri */
+       { 0x005e, &nv04_gr_ofuncs, nv04_gr_prim_omthds }, /* rect */
+       { 0x005f, &nv04_gr_ofuncs, nv04_gr_blit_omthds },
+       { 0x0060, &nv04_gr_ofuncs, nv04_gr_iifc_omthds },
+       { 0x0061, &nv04_gr_ofuncs, nv04_gr_ifc_omthds },
+       { 0x0064, &nv04_gr_ofuncs }, /* iifc (nv05) */
+       { 0x0065, &nv04_gr_ofuncs }, /* ifc (nv05) */
+       { 0x0066, &nv04_gr_ofuncs }, /* sifc (nv05) */
+       { 0x0072, &nv04_gr_ofuncs }, /* beta4 */
+       { 0x0076, &nv04_gr_ofuncs, nv04_gr_sifc_omthds },
+       { 0x0077, &nv04_gr_ofuncs, nv04_gr_sifm_omthds },
+       {},
+};
+
+/*******************************************************************************
+ * PGRAPH context
+ ******************************************************************************/
+
+static struct nv04_gr_chan *
+nv04_gr_channel(struct nv04_gr_priv *priv)
+{
+       struct nv04_gr_chan *chan = NULL;
+       if (nv_rd32(priv, NV04_PGRAPH_CTX_CONTROL) & 0x00010000) {
+               int chid = nv_rd32(priv, NV04_PGRAPH_CTX_USER) >> 24;
+               if (chid < ARRAY_SIZE(priv->chan))
+                       chan = priv->chan[chid];
+       }
+       return chan;
+}
+
+static int
+nv04_gr_load_context(struct nv04_gr_chan *chan, int chid)
+{
+       struct nv04_gr_priv *priv = nv04_gr_priv(chan);
+       int i;
+
+       for (i = 0; i < ARRAY_SIZE(nv04_gr_ctx_regs); i++)
+               nv_wr32(priv, nv04_gr_ctx_regs[i], chan->nv04[i]);
+
+       nv_wr32(priv, NV04_PGRAPH_CTX_CONTROL, 0x10010100);
+       nv_mask(priv, NV04_PGRAPH_CTX_USER, 0xff000000, chid << 24);
+       nv_mask(priv, NV04_PGRAPH_FFINTFC_ST2, 0xfff00000, 0x00000000);
+       return 0;
+}
+
+static int
+nv04_gr_unload_context(struct nv04_gr_chan *chan)
+{
+       struct nv04_gr_priv *priv = nv04_gr_priv(chan);
+       int i;
+
+       for (i = 0; i < ARRAY_SIZE(nv04_gr_ctx_regs); i++)
+               chan->nv04[i] = nv_rd32(priv, nv04_gr_ctx_regs[i]);
+
+       nv_wr32(priv, NV04_PGRAPH_CTX_CONTROL, 0x10000000);
+       nv_mask(priv, NV04_PGRAPH_CTX_USER, 0xff000000, 0x0f000000);
+       return 0;
+}
+
+static void
+nv04_gr_context_switch(struct nv04_gr_priv *priv)
+{
+       struct nv04_gr_chan *prev = NULL;
+       struct nv04_gr_chan *next = NULL;
+       unsigned long flags;
+       int chid;
+
+       spin_lock_irqsave(&priv->lock, flags);
+       nv04_gr_idle(priv);
+
+       /* If previous context is valid, we need to save it */
+       prev = nv04_gr_channel(priv);
+       if (prev)
+               nv04_gr_unload_context(prev);
+
+       /* load context for next channel */
+       chid = (nv_rd32(priv, NV04_PGRAPH_TRAPPED_ADDR) >> 24) & 0x0f;
+       next = priv->chan[chid];
+       if (next)
+               nv04_gr_load_context(next, chid);
+
+       spin_unlock_irqrestore(&priv->lock, flags);
+}
+
+static u32 *ctx_reg(struct nv04_gr_chan *chan, u32 reg)
+{
+       int i;
+
+       for (i = 0; i < ARRAY_SIZE(nv04_gr_ctx_regs); i++) {
+               if (nv04_gr_ctx_regs[i] == reg)
+                       return &chan->nv04[i];
+       }
+
+       return NULL;
+}
+
+static int
+nv04_gr_context_ctor(struct nvkm_object *parent,
+                    struct nvkm_object *engine,
+                    struct nvkm_oclass *oclass, void *data, u32 size,
+                    struct nvkm_object **pobject)
+{
+       struct nvkm_fifo_chan *fifo = (void *)parent;
+       struct nv04_gr_priv *priv = (void *)engine;
+       struct nv04_gr_chan *chan;
+       unsigned long flags;
+       int ret;
+
+       ret = nvkm_object_create(parent, engine, oclass, 0, &chan);
+       *pobject = nv_object(chan);
+       if (ret)
+               return ret;
+
+       spin_lock_irqsave(&priv->lock, flags);
+       if (priv->chan[fifo->chid]) {
+               *pobject = nv_object(priv->chan[fifo->chid]);
+               atomic_inc(&(*pobject)->refcount);
+               spin_unlock_irqrestore(&priv->lock, flags);
+               nvkm_object_destroy(&chan->base);
+               return 1;
+       }
+
+       *ctx_reg(chan, NV04_PGRAPH_DEBUG_3) = 0xfad4ff31;
+
+       priv->chan[fifo->chid] = chan;
+       chan->chid = fifo->chid;
+       spin_unlock_irqrestore(&priv->lock, flags);
+       return 0;
+}
+
+static void
+nv04_gr_context_dtor(struct nvkm_object *object)
+{
+       struct nv04_gr_priv *priv = (void *)object->engine;
+       struct nv04_gr_chan *chan = (void *)object;
+       unsigned long flags;
+
+       spin_lock_irqsave(&priv->lock, flags);
+       priv->chan[chan->chid] = NULL;
+       spin_unlock_irqrestore(&priv->lock, flags);
+
+       nvkm_object_destroy(&chan->base);
+}
+
+static int
+nv04_gr_context_fini(struct nvkm_object *object, bool suspend)
+{
+       struct nv04_gr_priv *priv = (void *)object->engine;
+       struct nv04_gr_chan *chan = (void *)object;
+       unsigned long flags;
+
+       spin_lock_irqsave(&priv->lock, flags);
+       nv_mask(priv, NV04_PGRAPH_FIFO, 0x00000001, 0x00000000);
+       if (nv04_gr_channel(priv) == chan)
+               nv04_gr_unload_context(chan);
+       nv_mask(priv, NV04_PGRAPH_FIFO, 0x00000001, 0x00000001);
+       spin_unlock_irqrestore(&priv->lock, flags);
+
+       return nvkm_object_fini(&chan->base, suspend);
+}
+
+static struct nvkm_oclass
+nv04_gr_cclass = {
+       .handle = NV_ENGCTX(GR, 0x04),
+       .ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = nv04_gr_context_ctor,
+               .dtor = nv04_gr_context_dtor,
+               .init = nvkm_object_init,
+               .fini = nv04_gr_context_fini,
+       },
+};
+
+/*******************************************************************************
+ * PGRAPH engine/subdev functions
+ ******************************************************************************/
+
+bool
+nv04_gr_idle(void *obj)
+{
+       struct nvkm_gr *gr = nvkm_gr(obj);
+       u32 mask = 0xffffffff;
+
+       if (nv_device(obj)->card_type == NV_40)
+               mask &= ~NV40_PGRAPH_STATUS_SYNC_STALL;
+
+       if (!nv_wait(gr, NV04_PGRAPH_STATUS, mask, 0)) {
+               nv_error(gr, "idle timed out with status 0x%08x\n",
+                        nv_rd32(gr, NV04_PGRAPH_STATUS));
+               return false;
+       }
+
+       return true;
+}
+
+static const struct nvkm_bitfield
+nv04_gr_intr_name[] = {
+       { NV_PGRAPH_INTR_NOTIFY, "NOTIFY" },
+       {}
+};
+
+static const struct nvkm_bitfield
+nv04_gr_nstatus[] = {
+       { 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" },
+       {}
+};
+
+const struct nvkm_bitfield
+nv04_gr_nsource[] = {
+       { 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
+nv04_gr_intr(struct nvkm_subdev *subdev)
+{
+       struct nv04_gr_priv *priv = (void *)subdev;
+       struct nv04_gr_chan *chan = NULL;
+       struct nvkm_namedb *namedb = NULL;
+       struct nvkm_handle *handle = NULL;
+       u32 stat = nv_rd32(priv, NV03_PGRAPH_INTR);
+       u32 nsource = nv_rd32(priv, NV03_PGRAPH_NSOURCE);
+       u32 nstatus = nv_rd32(priv, NV03_PGRAPH_NSTATUS);
+       u32 addr = nv_rd32(priv, NV04_PGRAPH_TRAPPED_ADDR);
+       u32 chid = (addr & 0x0f000000) >> 24;
+       u32 subc = (addr & 0x0000e000) >> 13;
+       u32 mthd = (addr & 0x00001ffc);
+       u32 data = nv_rd32(priv, NV04_PGRAPH_TRAPPED_DATA);
+       u32 class = nv_rd32(priv, 0x400180 + subc * 4) & 0xff;
+       u32 inst = (nv_rd32(priv, 0x40016c) & 0xffff) << 4;
+       u32 show = stat;
+       unsigned long flags;
+
+       spin_lock_irqsave(&priv->lock, flags);
+       chan = priv->chan[chid];
+       if (chan)
+               namedb = (void *)nv_pclass(nv_object(chan), NV_NAMEDB_CLASS);
+       spin_unlock_irqrestore(&priv->lock, flags);
+
+       if (stat & NV_PGRAPH_INTR_NOTIFY) {
+               if (chan && (nsource & NV03_PGRAPH_NSOURCE_ILLEGAL_MTHD)) {
+                       handle = nvkm_namedb_get_vinst(namedb, inst);
+                       if (handle && !nv_call(handle->object, mthd, data))
+                               show &= ~NV_PGRAPH_INTR_NOTIFY;
+               }
+       }
+
+       if (stat & NV_PGRAPH_INTR_CONTEXT_SWITCH) {
+               nv_wr32(priv, NV03_PGRAPH_INTR, NV_PGRAPH_INTR_CONTEXT_SWITCH);
+               stat &= ~NV_PGRAPH_INTR_CONTEXT_SWITCH;
+               show &= ~NV_PGRAPH_INTR_CONTEXT_SWITCH;
+               nv04_gr_context_switch(priv);
+       }
+
+       nv_wr32(priv, NV03_PGRAPH_INTR, stat);
+       nv_wr32(priv, NV04_PGRAPH_FIFO, 0x00000001);
+
+       if (show) {
+               nv_error(priv, "%s", "");
+               nvkm_bitfield_print(nv04_gr_intr_name, show);
+               pr_cont(" nsource:");
+               nvkm_bitfield_print(nv04_gr_nsource, nsource);
+               pr_cont(" nstatus:");
+               nvkm_bitfield_print(nv04_gr_nstatus, nstatus);
+               pr_cont("\n");
+               nv_error(priv,
+                        "ch %d [%s] subc %d class 0x%04x mthd 0x%04x data 0x%08x\n",
+                        chid, nvkm_client_name(chan), subc, class, mthd,
+                        data);
+       }
+
+       nvkm_namedb_put(handle);
+}
+
+static int
+nv04_gr_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+            struct nvkm_oclass *oclass, void *data, u32 size,
+            struct nvkm_object **pobject)
+{
+       struct nv04_gr_priv *priv;
+       int ret;
+
+       ret = nvkm_gr_create(parent, engine, oclass, true, &priv);
+       *pobject = nv_object(priv);
+       if (ret)
+               return ret;
+
+       nv_subdev(priv)->unit = 0x00001000;
+       nv_subdev(priv)->intr = nv04_gr_intr;
+       nv_engine(priv)->cclass = &nv04_gr_cclass;
+       nv_engine(priv)->sclass = nv04_gr_sclass;
+       spin_lock_init(&priv->lock);
+       return 0;
+}
+
+static int
+nv04_gr_init(struct nvkm_object *object)
+{
+       struct nvkm_engine *engine = nv_engine(object);
+       struct nv04_gr_priv *priv = (void *)engine;
+       int ret;
+
+       ret = nvkm_gr_init(&priv->base);
+       if (ret)
+               return ret;
+
+       /* Enable PGRAPH interrupts */
+       nv_wr32(priv, NV03_PGRAPH_INTR, 0xFFFFFFFF);
+       nv_wr32(priv, NV03_PGRAPH_INTR_EN, 0xFFFFFFFF);
+
+       nv_wr32(priv, NV04_PGRAPH_VALID1, 0);
+       nv_wr32(priv, NV04_PGRAPH_VALID2, 0);
+       /*nv_wr32(priv, NV04_PGRAPH_DEBUG_0, 0x000001FF);
+       nv_wr32(priv, NV04_PGRAPH_DEBUG_0, 0x001FFFFF);*/
+       nv_wr32(priv, NV04_PGRAPH_DEBUG_0, 0x1231c000);
+       /*1231C000 blob, 001 haiku*/
+       /*V_WRITE(NV04_PGRAPH_DEBUG_1, 0xf2d91100);*/
+       nv_wr32(priv, NV04_PGRAPH_DEBUG_1, 0x72111100);
+       /*0x72111100 blob , 01 haiku*/
+       /*nv_wr32(priv, NV04_PGRAPH_DEBUG_2, 0x11d5f870);*/
+       nv_wr32(priv, NV04_PGRAPH_DEBUG_2, 0x11d5f071);
+       /*haiku same*/
+
+       /*nv_wr32(priv, NV04_PGRAPH_DEBUG_3, 0xfad4ff31);*/
+       nv_wr32(priv, NV04_PGRAPH_DEBUG_3, 0xf0d4ff31);
+       /*haiku and blob 10d4*/
+
+       nv_wr32(priv, NV04_PGRAPH_STATE        , 0xFFFFFFFF);
+       nv_wr32(priv, NV04_PGRAPH_CTX_CONTROL  , 0x10000100);
+       nv_mask(priv, NV04_PGRAPH_CTX_USER, 0xff000000, 0x0f000000);
+
+       /* These don't belong here, they're part of a per-channel context */
+       nv_wr32(priv, NV04_PGRAPH_PATTERN_SHAPE, 0x00000000);
+       nv_wr32(priv, NV04_PGRAPH_BETA_AND     , 0xFFFFFFFF);
+       return 0;
+}
+
+struct nvkm_oclass
+nv04_gr_oclass = {
+       .handle = NV_ENGINE(GR, 0x04),
+       .ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = nv04_gr_ctor,
+               .dtor = _nvkm_gr_dtor,
+               .init = nv04_gr_init,
+               .fini = _nvkm_gr_fini,
+       },
+};
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/gr/nv10.c b/drivers/gpu/drm/nouveau/nvkm/engine/gr/nv10.c
new file mode 100644 (file)
index 0000000..389904e
--- /dev/null
@@ -0,0 +1,1315 @@
+/*
+ * Copyright 2007 Matthieu CASTET <castet.matthieu@free.fr>
+ * 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
+ * paragr) 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 <engine/gr.h>
+#include "regs.h"
+
+#include <core/client.h>
+#include <core/device.h>
+#include <core/handle.h>
+#include <engine/fifo.h>
+#include <subdev/fb.h>
+
+struct pipe_state {
+       u32 pipe_0x0000[0x040/4];
+       u32 pipe_0x0040[0x010/4];
+       u32 pipe_0x0200[0x0c0/4];
+       u32 pipe_0x4400[0x080/4];
+       u32 pipe_0x6400[0x3b0/4];
+       u32 pipe_0x6800[0x2f0/4];
+       u32 pipe_0x6c00[0x030/4];
+       u32 pipe_0x7000[0x130/4];
+       u32 pipe_0x7400[0x0c0/4];
+       u32 pipe_0x7800[0x0c0/4];
+};
+
+static int nv10_gr_ctx_regs[] = {
+       NV10_PGRAPH_CTX_SWITCH(0),
+       NV10_PGRAPH_CTX_SWITCH(1),
+       NV10_PGRAPH_CTX_SWITCH(2),
+       NV10_PGRAPH_CTX_SWITCH(3),
+       NV10_PGRAPH_CTX_SWITCH(4),
+       NV10_PGRAPH_CTX_CACHE(0, 0),
+       NV10_PGRAPH_CTX_CACHE(0, 1),
+       NV10_PGRAPH_CTX_CACHE(0, 2),
+       NV10_PGRAPH_CTX_CACHE(0, 3),
+       NV10_PGRAPH_CTX_CACHE(0, 4),
+       NV10_PGRAPH_CTX_CACHE(1, 0),
+       NV10_PGRAPH_CTX_CACHE(1, 1),
+       NV10_PGRAPH_CTX_CACHE(1, 2),
+       NV10_PGRAPH_CTX_CACHE(1, 3),
+       NV10_PGRAPH_CTX_CACHE(1, 4),
+       NV10_PGRAPH_CTX_CACHE(2, 0),
+       NV10_PGRAPH_CTX_CACHE(2, 1),
+       NV10_PGRAPH_CTX_CACHE(2, 2),
+       NV10_PGRAPH_CTX_CACHE(2, 3),
+       NV10_PGRAPH_CTX_CACHE(2, 4),
+       NV10_PGRAPH_CTX_CACHE(3, 0),
+       NV10_PGRAPH_CTX_CACHE(3, 1),
+       NV10_PGRAPH_CTX_CACHE(3, 2),
+       NV10_PGRAPH_CTX_CACHE(3, 3),
+       NV10_PGRAPH_CTX_CACHE(3, 4),
+       NV10_PGRAPH_CTX_CACHE(4, 0),
+       NV10_PGRAPH_CTX_CACHE(4, 1),
+       NV10_PGRAPH_CTX_CACHE(4, 2),
+       NV10_PGRAPH_CTX_CACHE(4, 3),
+       NV10_PGRAPH_CTX_CACHE(4, 4),
+       NV10_PGRAPH_CTX_CACHE(5, 0),
+       NV10_PGRAPH_CTX_CACHE(5, 1),
+       NV10_PGRAPH_CTX_CACHE(5, 2),
+       NV10_PGRAPH_CTX_CACHE(5, 3),
+       NV10_PGRAPH_CTX_CACHE(5, 4),
+       NV10_PGRAPH_CTX_CACHE(6, 0),
+       NV10_PGRAPH_CTX_CACHE(6, 1),
+       NV10_PGRAPH_CTX_CACHE(6, 2),
+       NV10_PGRAPH_CTX_CACHE(6, 3),
+       NV10_PGRAPH_CTX_CACHE(6, 4),
+       NV10_PGRAPH_CTX_CACHE(7, 0),
+       NV10_PGRAPH_CTX_CACHE(7, 1),
+       NV10_PGRAPH_CTX_CACHE(7, 2),
+       NV10_PGRAPH_CTX_CACHE(7, 3),
+       NV10_PGRAPH_CTX_CACHE(7, 4),
+       NV10_PGRAPH_CTX_USER,
+       NV04_PGRAPH_DMA_START_0,
+       NV04_PGRAPH_DMA_START_1,
+       NV04_PGRAPH_DMA_LENGTH,
+       NV04_PGRAPH_DMA_MISC,
+       NV10_PGRAPH_DMA_PITCH,
+       NV04_PGRAPH_BOFFSET0,
+       NV04_PGRAPH_BBASE0,
+       NV04_PGRAPH_BLIMIT0,
+       NV04_PGRAPH_BOFFSET1,
+       NV04_PGRAPH_BBASE1,
+       NV04_PGRAPH_BLIMIT1,
+       NV04_PGRAPH_BOFFSET2,
+       NV04_PGRAPH_BBASE2,
+       NV04_PGRAPH_BLIMIT2,
+       NV04_PGRAPH_BOFFSET3,
+       NV04_PGRAPH_BBASE3,
+       NV04_PGRAPH_BLIMIT3,
+       NV04_PGRAPH_BOFFSET4,
+       NV04_PGRAPH_BBASE4,
+       NV04_PGRAPH_BLIMIT4,
+       NV04_PGRAPH_BOFFSET5,
+       NV04_PGRAPH_BBASE5,
+       NV04_PGRAPH_BLIMIT5,
+       NV04_PGRAPH_BPITCH0,
+       NV04_PGRAPH_BPITCH1,
+       NV04_PGRAPH_BPITCH2,
+       NV04_PGRAPH_BPITCH3,
+       NV04_PGRAPH_BPITCH4,
+       NV10_PGRAPH_SURFACE,
+       NV10_PGRAPH_STATE,
+       NV04_PGRAPH_BSWIZZLE2,
+       NV04_PGRAPH_BSWIZZLE5,
+       NV04_PGRAPH_BPIXEL,
+       NV10_PGRAPH_NOTIFY,
+       NV04_PGRAPH_PATT_COLOR0,
+       NV04_PGRAPH_PATT_COLOR1,
+       NV04_PGRAPH_PATT_COLORRAM, /* 64 values from 0x400900 to 0x4009fc */
+       0x00400904,
+       0x00400908,
+       0x0040090c,
+       0x00400910,
+       0x00400914,
+       0x00400918,
+       0x0040091c,
+       0x00400920,
+       0x00400924,
+       0x00400928,
+       0x0040092c,
+       0x00400930,
+       0x00400934,
+       0x00400938,
+       0x0040093c,
+       0x00400940,
+       0x00400944,
+       0x00400948,
+       0x0040094c,
+       0x00400950,
+       0x00400954,
+       0x00400958,
+       0x0040095c,
+       0x00400960,
+       0x00400964,
+       0x00400968,
+       0x0040096c,
+       0x00400970,
+       0x00400974,
+       0x00400978,
+       0x0040097c,
+       0x00400980,
+       0x00400984,
+       0x00400988,
+       0x0040098c,
+       0x00400990,
+       0x00400994,
+       0x00400998,
+       0x0040099c,
+       0x004009a0,
+       0x004009a4,
+       0x004009a8,
+       0x004009ac,
+       0x004009b0,
+       0x004009b4,
+       0x004009b8,
+       0x004009bc,
+       0x004009c0,
+       0x004009c4,
+       0x004009c8,
+       0x004009cc,
+       0x004009d0,
+       0x004009d4,
+       0x004009d8,
+       0x004009dc,
+       0x004009e0,
+       0x004009e4,
+       0x004009e8,
+       0x004009ec,
+       0x004009f0,
+       0x004009f4,
+       0x004009f8,
+       0x004009fc,
+       NV04_PGRAPH_PATTERN,    /* 2 values from 0x400808 to 0x40080c */
+       0x0040080c,
+       NV04_PGRAPH_PATTERN_SHAPE,
+       NV03_PGRAPH_MONO_COLOR0,
+       NV04_PGRAPH_ROP3,
+       NV04_PGRAPH_CHROMA,
+       NV04_PGRAPH_BETA_AND,
+       NV04_PGRAPH_BETA_PREMULT,
+       0x00400e70,
+       0x00400e74,
+       0x00400e78,
+       0x00400e7c,
+       0x00400e80,
+       0x00400e84,
+       0x00400e88,
+       0x00400e8c,
+       0x00400ea0,
+       0x00400ea4,
+       0x00400ea8,
+       0x00400e90,
+       0x00400e94,
+       0x00400e98,
+       0x00400e9c,
+       NV10_PGRAPH_WINDOWCLIP_HORIZONTAL, /* 8 values from 0x400f00-0x400f1c */
+       NV10_PGRAPH_WINDOWCLIP_VERTICAL,   /* 8 values from 0x400f20-0x400f3c */
+       0x00400f04,
+       0x00400f24,
+       0x00400f08,
+       0x00400f28,
+       0x00400f0c,
+       0x00400f2c,
+       0x00400f10,
+       0x00400f30,
+       0x00400f14,
+       0x00400f34,
+       0x00400f18,
+       0x00400f38,
+       0x00400f1c,
+       0x00400f3c,
+       NV10_PGRAPH_XFMODE0,
+       NV10_PGRAPH_XFMODE1,
+       NV10_PGRAPH_GLOBALSTATE0,
+       NV10_PGRAPH_GLOBALSTATE1,
+       NV04_PGRAPH_STORED_FMT,
+       NV04_PGRAPH_SOURCE_COLOR,
+       NV03_PGRAPH_ABS_X_RAM,  /* 32 values from 0x400400 to 0x40047c */
+       NV03_PGRAPH_ABS_Y_RAM,  /* 32 values from 0x400480 to 0x4004fc */
+       0x00400404,
+       0x00400484,
+       0x00400408,
+       0x00400488,
+       0x0040040c,
+       0x0040048c,
+       0x00400410,
+       0x00400490,
+       0x00400414,
+       0x00400494,
+       0x00400418,
+       0x00400498,
+       0x0040041c,
+       0x0040049c,
+       0x00400420,
+       0x004004a0,
+       0x00400424,
+       0x004004a4,
+       0x00400428,
+       0x004004a8,
+       0x0040042c,
+       0x004004ac,
+       0x00400430,
+       0x004004b0,
+       0x00400434,
+       0x004004b4,
+       0x00400438,
+       0x004004b8,
+       0x0040043c,
+       0x004004bc,
+       0x00400440,
+       0x004004c0,
+       0x00400444,
+       0x004004c4,
+       0x00400448,
+       0x004004c8,
+       0x0040044c,
+       0x004004cc,
+       0x00400450,
+       0x004004d0,
+       0x00400454,
+       0x004004d4,
+       0x00400458,
+       0x004004d8,
+       0x0040045c,
+       0x004004dc,
+       0x00400460,
+       0x004004e0,
+       0x00400464,
+       0x004004e4,
+       0x00400468,
+       0x004004e8,
+       0x0040046c,
+       0x004004ec,
+       0x00400470,
+       0x004004f0,
+       0x00400474,
+       0x004004f4,
+       0x00400478,
+       0x004004f8,
+       0x0040047c,
+       0x004004fc,
+       NV03_PGRAPH_ABS_UCLIP_XMIN,
+       NV03_PGRAPH_ABS_UCLIP_XMAX,
+       NV03_PGRAPH_ABS_UCLIP_YMIN,
+       NV03_PGRAPH_ABS_UCLIP_YMAX,
+       0x00400550,
+       0x00400558,
+       0x00400554,
+       0x0040055c,
+       NV03_PGRAPH_ABS_UCLIPA_XMIN,
+       NV03_PGRAPH_ABS_UCLIPA_XMAX,
+       NV03_PGRAPH_ABS_UCLIPA_YMIN,
+       NV03_PGRAPH_ABS_UCLIPA_YMAX,
+       NV03_PGRAPH_ABS_ICLIP_XMAX,
+       NV03_PGRAPH_ABS_ICLIP_YMAX,
+       NV03_PGRAPH_XY_LOGIC_MISC0,
+       NV03_PGRAPH_XY_LOGIC_MISC1,
+       NV03_PGRAPH_XY_LOGIC_MISC2,
+       NV03_PGRAPH_XY_LOGIC_MISC3,
+       NV03_PGRAPH_CLIPX_0,
+       NV03_PGRAPH_CLIPX_1,
+       NV03_PGRAPH_CLIPY_0,
+       NV03_PGRAPH_CLIPY_1,
+       NV10_PGRAPH_COMBINER0_IN_ALPHA,
+       NV10_PGRAPH_COMBINER1_IN_ALPHA,
+       NV10_PGRAPH_COMBINER0_IN_RGB,
+       NV10_PGRAPH_COMBINER1_IN_RGB,
+       NV10_PGRAPH_COMBINER_COLOR0,
+       NV10_PGRAPH_COMBINER_COLOR1,
+       NV10_PGRAPH_COMBINER0_OUT_ALPHA,
+       NV10_PGRAPH_COMBINER1_OUT_ALPHA,
+       NV10_PGRAPH_COMBINER0_OUT_RGB,
+       NV10_PGRAPH_COMBINER1_OUT_RGB,
+       NV10_PGRAPH_COMBINER_FINAL0,
+       NV10_PGRAPH_COMBINER_FINAL1,
+       0x00400e00,
+       0x00400e04,
+       0x00400e08,
+       0x00400e0c,
+       0x00400e10,
+       0x00400e14,
+       0x00400e18,
+       0x00400e1c,
+       0x00400e20,
+       0x00400e24,
+       0x00400e28,
+       0x00400e2c,
+       0x00400e30,
+       0x00400e34,
+       0x00400e38,
+       0x00400e3c,
+       NV04_PGRAPH_PASSTHRU_0,
+       NV04_PGRAPH_PASSTHRU_1,
+       NV04_PGRAPH_PASSTHRU_2,
+       NV10_PGRAPH_DIMX_TEXTURE,
+       NV10_PGRAPH_WDIMX_TEXTURE,
+       NV10_PGRAPH_DVD_COLORFMT,
+       NV10_PGRAPH_SCALED_FORMAT,
+       NV04_PGRAPH_MISC24_0,
+       NV04_PGRAPH_MISC24_1,
+       NV04_PGRAPH_MISC24_2,
+       NV03_PGRAPH_X_MISC,
+       NV03_PGRAPH_Y_MISC,
+       NV04_PGRAPH_VALID1,
+       NV04_PGRAPH_VALID2,
+};
+
+static int nv17_gr_ctx_regs[] = {
+       NV10_PGRAPH_DEBUG_4,
+       0x004006b0,
+       0x00400eac,
+       0x00400eb0,
+       0x00400eb4,
+       0x00400eb8,
+       0x00400ebc,
+       0x00400ec0,
+       0x00400ec4,
+       0x00400ec8,
+       0x00400ecc,
+       0x00400ed0,
+       0x00400ed4,
+       0x00400ed8,
+       0x00400edc,
+       0x00400ee0,
+       0x00400a00,
+       0x00400a04,
+};
+
+struct nv10_gr_priv {
+       struct nvkm_gr base;
+       struct nv10_gr_chan *chan[32];
+       spinlock_t lock;
+};
+
+struct nv10_gr_chan {
+       struct nvkm_object base;
+       int chid;
+       int nv10[ARRAY_SIZE(nv10_gr_ctx_regs)];
+       int nv17[ARRAY_SIZE(nv17_gr_ctx_regs)];
+       struct pipe_state pipe_state;
+       u32 lma_window[4];
+};
+
+
+static inline struct nv10_gr_priv *
+nv10_gr_priv(struct nv10_gr_chan *chan)
+{
+       return (void *)nv_object(chan)->engine;
+}
+
+/*******************************************************************************
+ * Graphics object classes
+ ******************************************************************************/
+
+#define PIPE_SAVE(priv, state, addr)                                   \
+       do {                                                            \
+               int __i;                                                \
+               nv_wr32(priv, NV10_PGRAPH_PIPE_ADDRESS, addr);          \
+               for (__i = 0; __i < ARRAY_SIZE(state); __i++)           \
+                       state[__i] = nv_rd32(priv, NV10_PGRAPH_PIPE_DATA); \
+       } while (0)
+
+#define PIPE_RESTORE(priv, state, addr)                                        \
+       do {                                                            \
+               int __i;                                                \
+               nv_wr32(priv, NV10_PGRAPH_PIPE_ADDRESS, addr);          \
+               for (__i = 0; __i < ARRAY_SIZE(state); __i++)           \
+                       nv_wr32(priv, NV10_PGRAPH_PIPE_DATA, state[__i]); \
+       } while (0)
+
+static struct nvkm_oclass
+nv10_gr_sclass[] = {
+       { 0x0012, &nv04_gr_ofuncs }, /* beta1 */
+       { 0x0019, &nv04_gr_ofuncs }, /* clip */
+       { 0x0030, &nv04_gr_ofuncs }, /* null */
+       { 0x0039, &nv04_gr_ofuncs }, /* m2mf */
+       { 0x0043, &nv04_gr_ofuncs }, /* rop */
+       { 0x0044, &nv04_gr_ofuncs }, /* pattern */
+       { 0x004a, &nv04_gr_ofuncs }, /* gdi */
+       { 0x0052, &nv04_gr_ofuncs }, /* swzsurf */
+       { 0x005f, &nv04_gr_ofuncs }, /* blit */
+       { 0x0062, &nv04_gr_ofuncs }, /* surf2d */
+       { 0x0072, &nv04_gr_ofuncs }, /* beta4 */
+       { 0x0089, &nv04_gr_ofuncs }, /* sifm */
+       { 0x008a, &nv04_gr_ofuncs }, /* ifc */
+       { 0x009f, &nv04_gr_ofuncs }, /* blit */
+       { 0x0093, &nv04_gr_ofuncs }, /* surf3d */
+       { 0x0094, &nv04_gr_ofuncs }, /* ttri */
+       { 0x0095, &nv04_gr_ofuncs }, /* mtri */
+       { 0x0056, &nv04_gr_ofuncs }, /* celcius */
+       {},
+};
+
+static struct nvkm_oclass
+nv15_gr_sclass[] = {
+       { 0x0012, &nv04_gr_ofuncs }, /* beta1 */
+       { 0x0019, &nv04_gr_ofuncs }, /* clip */
+       { 0x0030, &nv04_gr_ofuncs }, /* null */
+       { 0x0039, &nv04_gr_ofuncs }, /* m2mf */
+       { 0x0043, &nv04_gr_ofuncs }, /* rop */
+       { 0x0044, &nv04_gr_ofuncs }, /* pattern */
+       { 0x004a, &nv04_gr_ofuncs }, /* gdi */
+       { 0x0052, &nv04_gr_ofuncs }, /* swzsurf */
+       { 0x005f, &nv04_gr_ofuncs }, /* blit */
+       { 0x0062, &nv04_gr_ofuncs }, /* surf2d */
+       { 0x0072, &nv04_gr_ofuncs }, /* beta4 */
+       { 0x0089, &nv04_gr_ofuncs }, /* sifm */
+       { 0x008a, &nv04_gr_ofuncs }, /* ifc */
+       { 0x009f, &nv04_gr_ofuncs }, /* blit */
+       { 0x0093, &nv04_gr_ofuncs }, /* surf3d */
+       { 0x0094, &nv04_gr_ofuncs }, /* ttri */
+       { 0x0095, &nv04_gr_ofuncs }, /* mtri */
+       { 0x0096, &nv04_gr_ofuncs }, /* celcius */
+       {},
+};
+
+static int
+nv17_gr_mthd_lma_window(struct nvkm_object *object, u32 mthd,
+                       void *args, u32 size)
+{
+       struct nv10_gr_chan *chan = (void *)object->parent;
+       struct nv10_gr_priv *priv = nv10_gr_priv(chan);
+       struct pipe_state *pipe = &chan->pipe_state;
+       u32 pipe_0x0040[1], pipe_0x64c0[8], pipe_0x6a80[3], pipe_0x6ab0[3];
+       u32 xfmode0, xfmode1;
+       u32 data = *(u32 *)args;
+       int i;
+
+       chan->lma_window[(mthd - 0x1638) / 4] = data;
+
+       if (mthd != 0x1644)
+               return 0;
+
+       nv04_gr_idle(priv);
+
+       PIPE_SAVE(priv, pipe_0x0040, 0x0040);
+       PIPE_SAVE(priv, pipe->pipe_0x0200, 0x0200);
+
+       PIPE_RESTORE(priv, chan->lma_window, 0x6790);
+
+       nv04_gr_idle(priv);
+
+       xfmode0 = nv_rd32(priv, NV10_PGRAPH_XFMODE0);
+       xfmode1 = nv_rd32(priv, NV10_PGRAPH_XFMODE1);
+
+       PIPE_SAVE(priv, pipe->pipe_0x4400, 0x4400);
+       PIPE_SAVE(priv, pipe_0x64c0, 0x64c0);
+       PIPE_SAVE(priv, pipe_0x6ab0, 0x6ab0);
+       PIPE_SAVE(priv, pipe_0x6a80, 0x6a80);
+
+       nv04_gr_idle(priv);
+
+       nv_wr32(priv, NV10_PGRAPH_XFMODE0, 0x10000000);
+       nv_wr32(priv, NV10_PGRAPH_XFMODE1, 0x00000000);
+       nv_wr32(priv, NV10_PGRAPH_PIPE_ADDRESS, 0x000064c0);
+       for (i = 0; i < 4; i++)
+               nv_wr32(priv, NV10_PGRAPH_PIPE_DATA, 0x3f800000);
+       for (i = 0; i < 4; i++)
+               nv_wr32(priv, NV10_PGRAPH_PIPE_DATA, 0x00000000);
+
+       nv_wr32(priv, NV10_PGRAPH_PIPE_ADDRESS, 0x00006ab0);
+       for (i = 0; i < 3; i++)
+               nv_wr32(priv, NV10_PGRAPH_PIPE_DATA, 0x3f800000);
+
+       nv_wr32(priv, NV10_PGRAPH_PIPE_ADDRESS, 0x00006a80);
+       for (i = 0; i < 3; i++)
+               nv_wr32(priv, NV10_PGRAPH_PIPE_DATA, 0x00000000);
+
+       nv_wr32(priv, NV10_PGRAPH_PIPE_ADDRESS, 0x00000040);
+       nv_wr32(priv, NV10_PGRAPH_PIPE_DATA, 0x00000008);
+
+       PIPE_RESTORE(priv, pipe->pipe_0x0200, 0x0200);
+
+       nv04_gr_idle(priv);
+
+       PIPE_RESTORE(priv, pipe_0x0040, 0x0040);
+
+       nv_wr32(priv, NV10_PGRAPH_XFMODE0, xfmode0);
+       nv_wr32(priv, NV10_PGRAPH_XFMODE1, xfmode1);
+
+       PIPE_RESTORE(priv, pipe_0x64c0, 0x64c0);
+       PIPE_RESTORE(priv, pipe_0x6ab0, 0x6ab0);
+       PIPE_RESTORE(priv, pipe_0x6a80, 0x6a80);
+       PIPE_RESTORE(priv, pipe->pipe_0x4400, 0x4400);
+
+       nv_wr32(priv, NV10_PGRAPH_PIPE_ADDRESS, 0x000000c0);
+       nv_wr32(priv, NV10_PGRAPH_PIPE_DATA, 0x00000000);
+
+       nv04_gr_idle(priv);
+
+       return 0;
+}
+
+static int
+nv17_gr_mthd_lma_enable(struct nvkm_object *object, u32 mthd,
+                       void *args, u32 size)
+{
+       struct nv10_gr_chan *chan = (void *)object->parent;
+       struct nv10_gr_priv *priv = nv10_gr_priv(chan);
+
+       nv04_gr_idle(priv);
+
+       nv_mask(priv, NV10_PGRAPH_DEBUG_4, 0x00000100, 0x00000100);
+       nv_mask(priv, 0x4006b0, 0x08000000, 0x08000000);
+       return 0;
+}
+
+static struct nvkm_omthds
+nv17_celcius_omthds[] = {
+       { 0x1638, 0x1638, nv17_gr_mthd_lma_window },
+       { 0x163c, 0x163c, nv17_gr_mthd_lma_window },
+       { 0x1640, 0x1640, nv17_gr_mthd_lma_window },
+       { 0x1644, 0x1644, nv17_gr_mthd_lma_window },
+       { 0x1658, 0x1658, nv17_gr_mthd_lma_enable },
+       {}
+};
+
+static struct nvkm_oclass
+nv17_gr_sclass[] = {
+       { 0x0012, &nv04_gr_ofuncs }, /* beta1 */
+       { 0x0019, &nv04_gr_ofuncs }, /* clip */
+       { 0x0030, &nv04_gr_ofuncs }, /* null */
+       { 0x0039, &nv04_gr_ofuncs }, /* m2mf */
+       { 0x0043, &nv04_gr_ofuncs }, /* rop */
+       { 0x0044, &nv04_gr_ofuncs }, /* pattern */
+       { 0x004a, &nv04_gr_ofuncs }, /* gdi */
+       { 0x0052, &nv04_gr_ofuncs }, /* swzsurf */
+       { 0x005f, &nv04_gr_ofuncs }, /* blit */
+       { 0x0062, &nv04_gr_ofuncs }, /* surf2d */
+       { 0x0072, &nv04_gr_ofuncs }, /* beta4 */
+       { 0x0089, &nv04_gr_ofuncs }, /* sifm */
+       { 0x008a, &nv04_gr_ofuncs }, /* ifc */
+       { 0x009f, &nv04_gr_ofuncs }, /* blit */
+       { 0x0093, &nv04_gr_ofuncs }, /* surf3d */
+       { 0x0094, &nv04_gr_ofuncs }, /* ttri */
+       { 0x0095, &nv04_gr_ofuncs }, /* mtri */
+       { 0x0099, &nv04_gr_ofuncs, nv17_celcius_omthds },
+       {},
+};
+
+/*******************************************************************************
+ * PGRAPH context
+ ******************************************************************************/
+
+static struct nv10_gr_chan *
+nv10_gr_channel(struct nv10_gr_priv *priv)
+{
+       struct nv10_gr_chan *chan = NULL;
+       if (nv_rd32(priv, 0x400144) & 0x00010000) {
+               int chid = nv_rd32(priv, 0x400148) >> 24;
+               if (chid < ARRAY_SIZE(priv->chan))
+                       chan = priv->chan[chid];
+       }
+       return chan;
+}
+
+static void
+nv10_gr_save_pipe(struct nv10_gr_chan *chan)
+{
+       struct nv10_gr_priv *priv = nv10_gr_priv(chan);
+       struct pipe_state *pipe = &chan->pipe_state;
+
+       PIPE_SAVE(priv, pipe->pipe_0x4400, 0x4400);
+       PIPE_SAVE(priv, pipe->pipe_0x0200, 0x0200);
+       PIPE_SAVE(priv, pipe->pipe_0x6400, 0x6400);
+       PIPE_SAVE(priv, pipe->pipe_0x6800, 0x6800);
+       PIPE_SAVE(priv, pipe->pipe_0x6c00, 0x6c00);
+       PIPE_SAVE(priv, pipe->pipe_0x7000, 0x7000);
+       PIPE_SAVE(priv, pipe->pipe_0x7400, 0x7400);
+       PIPE_SAVE(priv, pipe->pipe_0x7800, 0x7800);
+       PIPE_SAVE(priv, pipe->pipe_0x0040, 0x0040);
+       PIPE_SAVE(priv, pipe->pipe_0x0000, 0x0000);
+}
+
+static void
+nv10_gr_load_pipe(struct nv10_gr_chan *chan)
+{
+       struct nv10_gr_priv *priv = nv10_gr_priv(chan);
+       struct pipe_state *pipe = &chan->pipe_state;
+       u32 xfmode0, xfmode1;
+       int i;
+
+       nv04_gr_idle(priv);
+       /* XXX check haiku comments */
+       xfmode0 = nv_rd32(priv, NV10_PGRAPH_XFMODE0);
+       xfmode1 = nv_rd32(priv, NV10_PGRAPH_XFMODE1);
+       nv_wr32(priv, NV10_PGRAPH_XFMODE0, 0x10000000);
+       nv_wr32(priv, NV10_PGRAPH_XFMODE1, 0x00000000);
+       nv_wr32(priv, NV10_PGRAPH_PIPE_ADDRESS, 0x000064c0);
+       for (i = 0; i < 4; i++)
+               nv_wr32(priv, NV10_PGRAPH_PIPE_DATA, 0x3f800000);
+       for (i = 0; i < 4; i++)
+               nv_wr32(priv, NV10_PGRAPH_PIPE_DATA, 0x00000000);
+
+       nv_wr32(priv, NV10_PGRAPH_PIPE_ADDRESS, 0x00006ab0);
+       for (i = 0; i < 3; i++)
+               nv_wr32(priv, NV10_PGRAPH_PIPE_DATA, 0x3f800000);
+
+       nv_wr32(priv, NV10_PGRAPH_PIPE_ADDRESS, 0x00006a80);
+       for (i = 0; i < 3; i++)
+               nv_wr32(priv, NV10_PGRAPH_PIPE_DATA, 0x00000000);
+
+       nv_wr32(priv, NV10_PGRAPH_PIPE_ADDRESS, 0x00000040);
+       nv_wr32(priv, NV10_PGRAPH_PIPE_DATA, 0x00000008);
+
+
+       PIPE_RESTORE(priv, pipe->pipe_0x0200, 0x0200);
+       nv04_gr_idle(priv);
+
+       /* restore XFMODE */
+       nv_wr32(priv, NV10_PGRAPH_XFMODE0, xfmode0);
+       nv_wr32(priv, NV10_PGRAPH_XFMODE1, xfmode1);
+       PIPE_RESTORE(priv, pipe->pipe_0x6400, 0x6400);
+       PIPE_RESTORE(priv, pipe->pipe_0x6800, 0x6800);
+       PIPE_RESTORE(priv, pipe->pipe_0x6c00, 0x6c00);
+       PIPE_RESTORE(priv, pipe->pipe_0x7000, 0x7000);
+       PIPE_RESTORE(priv, pipe->pipe_0x7400, 0x7400);
+       PIPE_RESTORE(priv, pipe->pipe_0x7800, 0x7800);
+       PIPE_RESTORE(priv, pipe->pipe_0x4400, 0x4400);
+       PIPE_RESTORE(priv, pipe->pipe_0x0000, 0x0000);
+       PIPE_RESTORE(priv, pipe->pipe_0x0040, 0x0040);
+       nv04_gr_idle(priv);
+}
+
+static void
+nv10_gr_create_pipe(struct nv10_gr_chan *chan)
+{
+       struct nv10_gr_priv *priv = nv10_gr_priv(chan);
+       struct pipe_state *pipe_state = &chan->pipe_state;
+       u32 *pipe_state_addr;
+       int i;
+#define PIPE_INIT(addr) \
+       do { \
+               pipe_state_addr = pipe_state->pipe_##addr; \
+       } while (0)
+#define PIPE_INIT_END(addr) \
+       do { \
+               u32 *__end_addr = pipe_state->pipe_##addr + \
+                               ARRAY_SIZE(pipe_state->pipe_##addr); \
+               if (pipe_state_addr != __end_addr) \
+                       nv_error(priv, "incomplete pipe init for 0x%x :  %p/%p\n", \
+                               addr, pipe_state_addr, __end_addr); \
+       } while (0)
+#define NV_WRITE_PIPE_INIT(value) *(pipe_state_addr++) = value
+
+       PIPE_INIT(0x0200);
+       for (i = 0; i < 48; i++)
+               NV_WRITE_PIPE_INIT(0x00000000);
+       PIPE_INIT_END(0x0200);
+
+       PIPE_INIT(0x6400);
+       for (i = 0; i < 211; i++)
+               NV_WRITE_PIPE_INIT(0x00000000);
+       NV_WRITE_PIPE_INIT(0x3f800000);
+       NV_WRITE_PIPE_INIT(0x40000000);
+       NV_WRITE_PIPE_INIT(0x40000000);
+       NV_WRITE_PIPE_INIT(0x40000000);
+       NV_WRITE_PIPE_INIT(0x40000000);
+       NV_WRITE_PIPE_INIT(0x00000000);
+       NV_WRITE_PIPE_INIT(0x00000000);
+       NV_WRITE_PIPE_INIT(0x3f800000);
+       NV_WRITE_PIPE_INIT(0x00000000);
+       NV_WRITE_PIPE_INIT(0x3f000000);
+       NV_WRITE_PIPE_INIT(0x3f000000);
+       NV_WRITE_PIPE_INIT(0x00000000);
+       NV_WRITE_PIPE_INIT(0x00000000);
+       NV_WRITE_PIPE_INIT(0x00000000);
+       NV_WRITE_PIPE_INIT(0x00000000);
+       NV_WRITE_PIPE_INIT(0x3f800000);
+       NV_WRITE_PIPE_INIT(0x00000000);
+       NV_WRITE_PIPE_INIT(0x00000000);
+       NV_WRITE_PIPE_INIT(0x00000000);
+       NV_WRITE_PIPE_INIT(0x00000000);
+       NV_WRITE_PIPE_INIT(0x00000000);
+       NV_WRITE_PIPE_INIT(0x3f800000);
+       NV_WRITE_PIPE_INIT(0x3f800000);
+       NV_WRITE_PIPE_INIT(0x3f800000);
+       NV_WRITE_PIPE_INIT(0x3f800000);
+       PIPE_INIT_END(0x6400);
+
+       PIPE_INIT(0x6800);
+       for (i = 0; i < 162; i++)
+               NV_WRITE_PIPE_INIT(0x00000000);
+       NV_WRITE_PIPE_INIT(0x3f800000);
+       for (i = 0; i < 25; i++)
+               NV_WRITE_PIPE_INIT(0x00000000);
+       PIPE_INIT_END(0x6800);
+
+       PIPE_INIT(0x6c00);
+       NV_WRITE_PIPE_INIT(0x00000000);
+       NV_WRITE_PIPE_INIT(0x00000000);
+       NV_WRITE_PIPE_INIT(0x00000000);
+       NV_WRITE_PIPE_INIT(0x00000000);
+       NV_WRITE_PIPE_INIT(0xbf800000);
+       NV_WRITE_PIPE_INIT(0x00000000);
+       NV_WRITE_PIPE_INIT(0x00000000);
+       NV_WRITE_PIPE_INIT(0x00000000);
+       NV_WRITE_PIPE_INIT(0x00000000);
+       NV_WRITE_PIPE_INIT(0x00000000);
+       NV_WRITE_PIPE_INIT(0x00000000);
+       NV_WRITE_PIPE_INIT(0x00000000);
+       PIPE_INIT_END(0x6c00);
+
+       PIPE_INIT(0x7000);
+       NV_WRITE_PIPE_INIT(0x00000000);
+       NV_WRITE_PIPE_INIT(0x00000000);
+       NV_WRITE_PIPE_INIT(0x00000000);
+       NV_WRITE_PIPE_INIT(0x00000000);
+       NV_WRITE_PIPE_INIT(0x00000000);
+       NV_WRITE_PIPE_INIT(0x00000000);
+       NV_WRITE_PIPE_INIT(0x00000000);
+       NV_WRITE_PIPE_INIT(0x00000000);
+       NV_WRITE_PIPE_INIT(0x00000000);
+       NV_WRITE_PIPE_INIT(0x00000000);
+       NV_WRITE_PIPE_INIT(0x00000000);
+       NV_WRITE_PIPE_INIT(0x00000000);
+       NV_WRITE_PIPE_INIT(0x7149f2ca);
+       NV_WRITE_PIPE_INIT(0x00000000);
+       NV_WRITE_PIPE_INIT(0x00000000);
+       NV_WRITE_PIPE_INIT(0x00000000);
+       NV_WRITE_PIPE_INIT(0x7149f2ca);
+       NV_WRITE_PIPE_INIT(0x00000000);
+       NV_WRITE_PIPE_INIT(0x00000000);
+       NV_WRITE_PIPE_INIT(0x00000000);
+       NV_WRITE_PIPE_INIT(0x7149f2ca);
+       NV_WRITE_PIPE_INIT(0x00000000);
+       NV_WRITE_PIPE_INIT(0x00000000);
+       NV_WRITE_PIPE_INIT(0x00000000);
+       NV_WRITE_PIPE_INIT(0x7149f2ca);
+       NV_WRITE_PIPE_INIT(0x00000000);
+       NV_WRITE_PIPE_INIT(0x00000000);
+       NV_WRITE_PIPE_INIT(0x00000000);
+       NV_WRITE_PIPE_INIT(0x7149f2ca);
+       NV_WRITE_PIPE_INIT(0x00000000);
+       NV_WRITE_PIPE_INIT(0x00000000);
+       NV_WRITE_PIPE_INIT(0x00000000);
+       NV_WRITE_PIPE_INIT(0x7149f2ca);
+       NV_WRITE_PIPE_INIT(0x00000000);
+       NV_WRITE_PIPE_INIT(0x00000000);
+       NV_WRITE_PIPE_INIT(0x00000000);
+       NV_WRITE_PIPE_INIT(0x7149f2ca);
+       NV_WRITE_PIPE_INIT(0x00000000);
+       NV_WRITE_PIPE_INIT(0x00000000);
+       NV_WRITE_PIPE_INIT(0x00000000);
+       NV_WRITE_PIPE_INIT(0x7149f2ca);
+       for (i = 0; i < 35; i++)
+               NV_WRITE_PIPE_INIT(0x00000000);
+       PIPE_INIT_END(0x7000);
+
+       PIPE_INIT(0x7400);
+       for (i = 0; i < 48; i++)
+               NV_WRITE_PIPE_INIT(0x00000000);
+       PIPE_INIT_END(0x7400);
+
+       PIPE_INIT(0x7800);
+       for (i = 0; i < 48; i++)
+               NV_WRITE_PIPE_INIT(0x00000000);
+       PIPE_INIT_END(0x7800);
+
+       PIPE_INIT(0x4400);
+       for (i = 0; i < 32; i++)
+               NV_WRITE_PIPE_INIT(0x00000000);
+       PIPE_INIT_END(0x4400);
+
+       PIPE_INIT(0x0000);
+       for (i = 0; i < 16; i++)
+               NV_WRITE_PIPE_INIT(0x00000000);
+       PIPE_INIT_END(0x0000);
+
+       PIPE_INIT(0x0040);
+       for (i = 0; i < 4; i++)
+               NV_WRITE_PIPE_INIT(0x00000000);
+       PIPE_INIT_END(0x0040);
+
+#undef PIPE_INIT
+#undef PIPE_INIT_END
+#undef NV_WRITE_PIPE_INIT
+}
+
+static int
+nv10_gr_ctx_regs_find_offset(struct nv10_gr_priv *priv, int reg)
+{
+       int i;
+       for (i = 0; i < ARRAY_SIZE(nv10_gr_ctx_regs); i++) {
+               if (nv10_gr_ctx_regs[i] == reg)
+                       return i;
+       }
+       nv_error(priv, "unknow offset nv10_ctx_regs %d\n", reg);
+       return -1;
+}
+
+static int
+nv17_gr_ctx_regs_find_offset(struct nv10_gr_priv *priv, int reg)
+{
+       int i;
+       for (i = 0; i < ARRAY_SIZE(nv17_gr_ctx_regs); i++) {
+               if (nv17_gr_ctx_regs[i] == reg)
+                       return i;
+       }
+       nv_error(priv, "unknow offset nv17_ctx_regs %d\n", reg);
+       return -1;
+}
+
+static void
+nv10_gr_load_dma_vtxbuf(struct nv10_gr_chan *chan, int chid, u32 inst)
+{
+       struct nv10_gr_priv *priv = nv10_gr_priv(chan);
+       u32 st2, st2_dl, st2_dh, fifo_ptr, fifo[0x60/4];
+       u32 ctx_user, ctx_switch[5];
+       int i, subchan = -1;
+
+       /* NV10TCL_DMA_VTXBUF (method 0x18c) modifies hidden state
+        * that cannot be restored via MMIO. Do it through the FIFO
+        * instead.
+        */
+
+       /* Look for a celsius object */
+       for (i = 0; i < 8; i++) {
+               int class = nv_rd32(priv, NV10_PGRAPH_CTX_CACHE(i, 0)) & 0xfff;
+
+               if (class == 0x56 || class == 0x96 || class == 0x99) {
+                       subchan = i;
+                       break;
+               }
+       }
+
+       if (subchan < 0 || !inst)
+               return;
+
+       /* Save the current ctx object */
+       ctx_user = nv_rd32(priv, NV10_PGRAPH_CTX_USER);
+       for (i = 0; i < 5; i++)
+               ctx_switch[i] = nv_rd32(priv, NV10_PGRAPH_CTX_SWITCH(i));
+
+       /* Save the FIFO state */
+       st2 = nv_rd32(priv, NV10_PGRAPH_FFINTFC_ST2);
+       st2_dl = nv_rd32(priv, NV10_PGRAPH_FFINTFC_ST2_DL);
+       st2_dh = nv_rd32(priv, NV10_PGRAPH_FFINTFC_ST2_DH);
+       fifo_ptr = nv_rd32(priv, NV10_PGRAPH_FFINTFC_FIFO_PTR);
+
+       for (i = 0; i < ARRAY_SIZE(fifo); i++)
+               fifo[i] = nv_rd32(priv, 0x4007a0 + 4 * i);
+
+       /* Switch to the celsius subchannel */
+       for (i = 0; i < 5; i++)
+               nv_wr32(priv, NV10_PGRAPH_CTX_SWITCH(i),
+                       nv_rd32(priv, NV10_PGRAPH_CTX_CACHE(subchan, i)));
+       nv_mask(priv, NV10_PGRAPH_CTX_USER, 0xe000, subchan << 13);
+
+       /* Inject NV10TCL_DMA_VTXBUF */
+       nv_wr32(priv, NV10_PGRAPH_FFINTFC_FIFO_PTR, 0);
+       nv_wr32(priv, NV10_PGRAPH_FFINTFC_ST2,
+               0x2c000000 | chid << 20 | subchan << 16 | 0x18c);
+       nv_wr32(priv, NV10_PGRAPH_FFINTFC_ST2_DL, inst);
+       nv_mask(priv, NV10_PGRAPH_CTX_CONTROL, 0, 0x10000);
+       nv_mask(priv, NV04_PGRAPH_FIFO, 0x00000001, 0x00000001);
+       nv_mask(priv, NV04_PGRAPH_FIFO, 0x00000001, 0x00000000);
+
+       /* Restore the FIFO state */
+       for (i = 0; i < ARRAY_SIZE(fifo); i++)
+               nv_wr32(priv, 0x4007a0 + 4 * i, fifo[i]);
+
+       nv_wr32(priv, NV10_PGRAPH_FFINTFC_FIFO_PTR, fifo_ptr);
+       nv_wr32(priv, NV10_PGRAPH_FFINTFC_ST2, st2);
+       nv_wr32(priv, NV10_PGRAPH_FFINTFC_ST2_DL, st2_dl);
+       nv_wr32(priv, NV10_PGRAPH_FFINTFC_ST2_DH, st2_dh);
+
+       /* Restore the current ctx object */
+       for (i = 0; i < 5; i++)
+               nv_wr32(priv, NV10_PGRAPH_CTX_SWITCH(i), ctx_switch[i]);
+       nv_wr32(priv, NV10_PGRAPH_CTX_USER, ctx_user);
+}
+
+static int
+nv10_gr_load_context(struct nv10_gr_chan *chan, int chid)
+{
+       struct nv10_gr_priv *priv = nv10_gr_priv(chan);
+       u32 inst;
+       int i;
+
+       for (i = 0; i < ARRAY_SIZE(nv10_gr_ctx_regs); i++)
+               nv_wr32(priv, nv10_gr_ctx_regs[i], chan->nv10[i]);
+
+       if (nv_device(priv)->card_type >= NV_11 &&
+           nv_device(priv)->chipset >= 0x17) {
+               for (i = 0; i < ARRAY_SIZE(nv17_gr_ctx_regs); i++)
+                       nv_wr32(priv, nv17_gr_ctx_regs[i], chan->nv17[i]);
+       }
+
+       nv10_gr_load_pipe(chan);
+
+       inst = nv_rd32(priv, NV10_PGRAPH_GLOBALSTATE1) & 0xffff;
+       nv10_gr_load_dma_vtxbuf(chan, chid, inst);
+
+       nv_wr32(priv, NV10_PGRAPH_CTX_CONTROL, 0x10010100);
+       nv_mask(priv, NV10_PGRAPH_CTX_USER, 0xff000000, chid << 24);
+       nv_mask(priv, NV10_PGRAPH_FFINTFC_ST2, 0x30000000, 0x00000000);
+       return 0;
+}
+
+static int
+nv10_gr_unload_context(struct nv10_gr_chan *chan)
+{
+       struct nv10_gr_priv *priv = nv10_gr_priv(chan);
+       int i;
+
+       for (i = 0; i < ARRAY_SIZE(nv10_gr_ctx_regs); i++)
+               chan->nv10[i] = nv_rd32(priv, nv10_gr_ctx_regs[i]);
+
+       if (nv_device(priv)->card_type >= NV_11 &&
+           nv_device(priv)->chipset >= 0x17) {
+               for (i = 0; i < ARRAY_SIZE(nv17_gr_ctx_regs); i++)
+                       chan->nv17[i] = nv_rd32(priv, nv17_gr_ctx_regs[i]);
+       }
+
+       nv10_gr_save_pipe(chan);
+
+       nv_wr32(priv, NV10_PGRAPH_CTX_CONTROL, 0x10000000);
+       nv_mask(priv, NV10_PGRAPH_CTX_USER, 0xff000000, 0x1f000000);
+       return 0;
+}
+
+static void
+nv10_gr_context_switch(struct nv10_gr_priv *priv)
+{
+       struct nv10_gr_chan *prev = NULL;
+       struct nv10_gr_chan *next = NULL;
+       unsigned long flags;
+       int chid;
+
+       spin_lock_irqsave(&priv->lock, flags);
+       nv04_gr_idle(priv);
+
+       /* If previous context is valid, we need to save it */
+       prev = nv10_gr_channel(priv);
+       if (prev)
+               nv10_gr_unload_context(prev);
+
+       /* load context for next channel */
+       chid = (nv_rd32(priv, NV04_PGRAPH_TRAPPED_ADDR) >> 20) & 0x1f;
+       next = priv->chan[chid];
+       if (next)
+               nv10_gr_load_context(next, chid);
+
+       spin_unlock_irqrestore(&priv->lock, flags);
+}
+
+#define NV_WRITE_CTX(reg, val) do { \
+       int offset = nv10_gr_ctx_regs_find_offset(priv, reg); \
+       if (offset > 0) \
+               chan->nv10[offset] = val; \
+       } while (0)
+
+#define NV17_WRITE_CTX(reg, val) do { \
+       int offset = nv17_gr_ctx_regs_find_offset(priv, reg); \
+       if (offset > 0) \
+               chan->nv17[offset] = val; \
+       } while (0)
+
+static int
+nv10_gr_context_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+                    struct nvkm_oclass *oclass, void *data, u32 size,
+                    struct nvkm_object **pobject)
+{
+       struct nvkm_fifo_chan *fifo = (void *)parent;
+       struct nv10_gr_priv *priv = (void *)engine;
+       struct nv10_gr_chan *chan;
+       unsigned long flags;
+       int ret;
+
+       ret = nvkm_object_create(parent, engine, oclass, 0, &chan);
+       *pobject = nv_object(chan);
+       if (ret)
+               return ret;
+
+       spin_lock_irqsave(&priv->lock, flags);
+       if (priv->chan[fifo->chid]) {
+               *pobject = nv_object(priv->chan[fifo->chid]);
+               atomic_inc(&(*pobject)->refcount);
+               spin_unlock_irqrestore(&priv->lock, flags);
+               nvkm_object_destroy(&chan->base);
+               return 1;
+       }
+
+       NV_WRITE_CTX(0x00400e88, 0x08000000);
+       NV_WRITE_CTX(0x00400e9c, 0x4b7fffff);
+       NV_WRITE_CTX(NV03_PGRAPH_XY_LOGIC_MISC0, 0x0001ffff);
+       NV_WRITE_CTX(0x00400e10, 0x00001000);
+       NV_WRITE_CTX(0x00400e14, 0x00001000);
+       NV_WRITE_CTX(0x00400e30, 0x00080008);
+       NV_WRITE_CTX(0x00400e34, 0x00080008);
+       if (nv_device(priv)->card_type >= NV_11 &&
+           nv_device(priv)->chipset >= 0x17) {
+               /* is it really needed ??? */
+               NV17_WRITE_CTX(NV10_PGRAPH_DEBUG_4,
+                                       nv_rd32(priv, NV10_PGRAPH_DEBUG_4));
+               NV17_WRITE_CTX(0x004006b0, nv_rd32(priv, 0x004006b0));
+               NV17_WRITE_CTX(0x00400eac, 0x0fff0000);
+               NV17_WRITE_CTX(0x00400eb0, 0x0fff0000);
+               NV17_WRITE_CTX(0x00400ec0, 0x00000080);
+               NV17_WRITE_CTX(0x00400ed0, 0x00000080);
+       }
+       NV_WRITE_CTX(NV10_PGRAPH_CTX_USER, chan->chid << 24);
+
+       nv10_gr_create_pipe(chan);
+
+       priv->chan[fifo->chid] = chan;
+       chan->chid = fifo->chid;
+       spin_unlock_irqrestore(&priv->lock, flags);
+       return 0;
+}
+
+static void
+nv10_gr_context_dtor(struct nvkm_object *object)
+{
+       struct nv10_gr_priv *priv = (void *)object->engine;
+       struct nv10_gr_chan *chan = (void *)object;
+       unsigned long flags;
+
+       spin_lock_irqsave(&priv->lock, flags);
+       priv->chan[chan->chid] = NULL;
+       spin_unlock_irqrestore(&priv->lock, flags);
+
+       nvkm_object_destroy(&chan->base);
+}
+
+static int
+nv10_gr_context_fini(struct nvkm_object *object, bool suspend)
+{
+       struct nv10_gr_priv *priv = (void *)object->engine;
+       struct nv10_gr_chan *chan = (void *)object;
+       unsigned long flags;
+
+       spin_lock_irqsave(&priv->lock, flags);
+       nv_mask(priv, NV04_PGRAPH_FIFO, 0x00000001, 0x00000000);
+       if (nv10_gr_channel(priv) == chan)
+               nv10_gr_unload_context(chan);
+       nv_mask(priv, NV04_PGRAPH_FIFO, 0x00000001, 0x00000001);
+       spin_unlock_irqrestore(&priv->lock, flags);
+
+       return nvkm_object_fini(&chan->base, suspend);
+}
+
+static struct nvkm_oclass
+nv10_gr_cclass = {
+       .handle = NV_ENGCTX(GR, 0x10),
+       .ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = nv10_gr_context_ctor,
+               .dtor = nv10_gr_context_dtor,
+               .init = nvkm_object_init,
+               .fini = nv10_gr_context_fini,
+       },
+};
+
+/*******************************************************************************
+ * PGRAPH engine/subdev functions
+ ******************************************************************************/
+
+static void
+nv10_gr_tile_prog(struct nvkm_engine *engine, int i)
+{
+       struct nvkm_fb_tile *tile = &nvkm_fb(engine)->tile.region[i];
+       struct nvkm_fifo *pfifo = nvkm_fifo(engine);
+       struct nv10_gr_priv *priv = (void *)engine;
+       unsigned long flags;
+
+       pfifo->pause(pfifo, &flags);
+       nv04_gr_idle(priv);
+
+       nv_wr32(priv, NV10_PGRAPH_TLIMIT(i), tile->limit);
+       nv_wr32(priv, NV10_PGRAPH_TSIZE(i), tile->pitch);
+       nv_wr32(priv, NV10_PGRAPH_TILE(i), tile->addr);
+
+       pfifo->start(pfifo, &flags);
+}
+
+const struct nvkm_bitfield nv10_gr_intr_name[] = {
+       { NV_PGRAPH_INTR_NOTIFY, "NOTIFY" },
+       { NV_PGRAPH_INTR_ERROR,  "ERROR"  },
+       {}
+};
+
+const struct nvkm_bitfield nv10_gr_nstatus[] = {
+       { 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 void
+nv10_gr_intr(struct nvkm_subdev *subdev)
+{
+       struct nv10_gr_priv *priv = (void *)subdev;
+       struct nv10_gr_chan *chan = NULL;
+       struct nvkm_namedb *namedb = NULL;
+       struct nvkm_handle *handle = NULL;
+       u32 stat = nv_rd32(priv, NV03_PGRAPH_INTR);
+       u32 nsource = nv_rd32(priv, NV03_PGRAPH_NSOURCE);
+       u32 nstatus = nv_rd32(priv, NV03_PGRAPH_NSTATUS);
+       u32 addr = nv_rd32(priv, NV04_PGRAPH_TRAPPED_ADDR);
+       u32 chid = (addr & 0x01f00000) >> 20;
+       u32 subc = (addr & 0x00070000) >> 16;
+       u32 mthd = (addr & 0x00001ffc);
+       u32 data = nv_rd32(priv, NV04_PGRAPH_TRAPPED_DATA);
+       u32 class = nv_rd32(priv, 0x400160 + subc * 4) & 0xfff;
+       u32 show = stat;
+       unsigned long flags;
+
+       spin_lock_irqsave(&priv->lock, flags);
+       chan = priv->chan[chid];
+       if (chan)
+               namedb = (void *)nv_pclass(nv_object(chan), NV_NAMEDB_CLASS);
+       spin_unlock_irqrestore(&priv->lock, flags);
+
+       if (stat & NV_PGRAPH_INTR_ERROR) {
+               if (chan && (nsource & NV03_PGRAPH_NSOURCE_ILLEGAL_MTHD)) {
+                       handle = nvkm_namedb_get_class(namedb, class);
+                       if (handle && !nv_call(handle->object, mthd, data))
+                               show &= ~NV_PGRAPH_INTR_ERROR;
+               }
+       }
+
+       if (stat & NV_PGRAPH_INTR_CONTEXT_SWITCH) {
+               nv_wr32(priv, NV03_PGRAPH_INTR, NV_PGRAPH_INTR_CONTEXT_SWITCH);
+               stat &= ~NV_PGRAPH_INTR_CONTEXT_SWITCH;
+               show &= ~NV_PGRAPH_INTR_CONTEXT_SWITCH;
+               nv10_gr_context_switch(priv);
+       }
+
+       nv_wr32(priv, NV03_PGRAPH_INTR, stat);
+       nv_wr32(priv, NV04_PGRAPH_FIFO, 0x00000001);
+
+       if (show) {
+               nv_error(priv, "%s", "");
+               nvkm_bitfield_print(nv10_gr_intr_name, show);
+               pr_cont(" nsource:");
+               nvkm_bitfield_print(nv04_gr_nsource, nsource);
+               pr_cont(" nstatus:");
+               nvkm_bitfield_print(nv10_gr_nstatus, nstatus);
+               pr_cont("\n");
+               nv_error(priv,
+                        "ch %d [%s] subc %d class 0x%04x mthd 0x%04x data 0x%08x\n",
+                        chid, nvkm_client_name(chan), subc, class, mthd,
+                        data);
+       }
+
+       nvkm_namedb_put(handle);
+}
+
+static int
+nv10_gr_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+            struct nvkm_oclass *oclass, void *data, u32 size,
+            struct nvkm_object **pobject)
+{
+       struct nv10_gr_priv *priv;
+       int ret;
+
+       ret = nvkm_gr_create(parent, engine, oclass, true, &priv);
+       *pobject = nv_object(priv);
+       if (ret)
+               return ret;
+
+       nv_subdev(priv)->unit = 0x00001000;
+       nv_subdev(priv)->intr = nv10_gr_intr;
+       nv_engine(priv)->cclass = &nv10_gr_cclass;
+
+       if (nv_device(priv)->chipset <= 0x10)
+               nv_engine(priv)->sclass = nv10_gr_sclass;
+       else
+       if (nv_device(priv)->chipset <  0x17 ||
+           nv_device(priv)->card_type < NV_11)
+               nv_engine(priv)->sclass = nv15_gr_sclass;
+       else
+               nv_engine(priv)->sclass = nv17_gr_sclass;
+
+       nv_engine(priv)->tile_prog = nv10_gr_tile_prog;
+       spin_lock_init(&priv->lock);
+       return 0;
+}
+
+static void
+nv10_gr_dtor(struct nvkm_object *object)
+{
+       struct nv10_gr_priv *priv = (void *)object;
+       nvkm_gr_destroy(&priv->base);
+}
+
+static int
+nv10_gr_init(struct nvkm_object *object)
+{
+       struct nvkm_engine *engine = nv_engine(object);
+       struct nvkm_fb *pfb = nvkm_fb(object);
+       struct nv10_gr_priv *priv = (void *)engine;
+       int ret, i;
+
+       ret = nvkm_gr_init(&priv->base);
+       if (ret)
+               return ret;
+
+       nv_wr32(priv, NV03_PGRAPH_INTR   , 0xFFFFFFFF);
+       nv_wr32(priv, NV03_PGRAPH_INTR_EN, 0xFFFFFFFF);
+
+       nv_wr32(priv, NV04_PGRAPH_DEBUG_0, 0xFFFFFFFF);
+       nv_wr32(priv, NV04_PGRAPH_DEBUG_0, 0x00000000);
+       nv_wr32(priv, NV04_PGRAPH_DEBUG_1, 0x00118700);
+       /* nv_wr32(priv, NV04_PGRAPH_DEBUG_2, 0x24E00810); */ /* 0x25f92ad9 */
+       nv_wr32(priv, NV04_PGRAPH_DEBUG_2, 0x25f92ad9);
+       nv_wr32(priv, NV04_PGRAPH_DEBUG_3, 0x55DE0830 | (1 << 29) | (1 << 31));
+
+       if (nv_device(priv)->card_type >= NV_11 &&
+           nv_device(priv)->chipset >= 0x17) {
+               nv_wr32(priv, NV10_PGRAPH_DEBUG_4, 0x1f000000);
+               nv_wr32(priv, 0x400a10, 0x03ff3fb6);
+               nv_wr32(priv, 0x400838, 0x002f8684);
+               nv_wr32(priv, 0x40083c, 0x00115f3f);
+               nv_wr32(priv, 0x4006b0, 0x40000020);
+       } else {
+               nv_wr32(priv, NV10_PGRAPH_DEBUG_4, 0x00000000);
+       }
+
+       /* Turn all the tiling regions off. */
+       for (i = 0; i < pfb->tile.regions; i++)
+               engine->tile_prog(engine, i);
+
+       nv_wr32(priv, NV10_PGRAPH_CTX_SWITCH(0), 0x00000000);
+       nv_wr32(priv, NV10_PGRAPH_CTX_SWITCH(1), 0x00000000);
+       nv_wr32(priv, NV10_PGRAPH_CTX_SWITCH(2), 0x00000000);
+       nv_wr32(priv, NV10_PGRAPH_CTX_SWITCH(3), 0x00000000);
+       nv_wr32(priv, NV10_PGRAPH_CTX_SWITCH(4), 0x00000000);
+       nv_wr32(priv, NV10_PGRAPH_STATE, 0xFFFFFFFF);
+
+       nv_mask(priv, NV10_PGRAPH_CTX_USER, 0xff000000, 0x1f000000);
+       nv_wr32(priv, NV10_PGRAPH_CTX_CONTROL, 0x10000100);
+       nv_wr32(priv, NV10_PGRAPH_FFINTFC_ST2, 0x08000000);
+       return 0;
+}
+
+static int
+nv10_gr_fini(struct nvkm_object *object, bool suspend)
+{
+       struct nv10_gr_priv *priv = (void *)object;
+       return nvkm_gr_fini(&priv->base, suspend);
+}
+
+struct nvkm_oclass
+nv10_gr_oclass = {
+       .handle = NV_ENGINE(GR, 0x10),
+       .ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = nv10_gr_ctor,
+               .dtor = nv10_gr_dtor,
+               .init = nv10_gr_init,
+               .fini = nv10_gr_fini,
+       },
+};
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/gr/nv20.c b/drivers/gpu/drm/nouveau/nvkm/engine/gr/nv20.c
new file mode 100644 (file)
index 0000000..1713ffb
--- /dev/null
@@ -0,0 +1,376 @@
+#include "nv20.h"
+#include "regs.h"
+
+#include <core/client.h>
+#include <core/device.h>
+#include <core/handle.h>
+#include <engine/fifo.h>
+#include <subdev/fb.h>
+#include <subdev/timer.h>
+
+/*******************************************************************************
+ * Graphics object classes
+ ******************************************************************************/
+
+static struct nvkm_oclass
+nv20_gr_sclass[] = {
+       { 0x0012, &nv04_gr_ofuncs, NULL }, /* beta1 */
+       { 0x0019, &nv04_gr_ofuncs, NULL }, /* clip */
+       { 0x0030, &nv04_gr_ofuncs, NULL }, /* null */
+       { 0x0039, &nv04_gr_ofuncs, NULL }, /* m2mf */
+       { 0x0043, &nv04_gr_ofuncs, NULL }, /* rop */
+       { 0x0044, &nv04_gr_ofuncs, NULL }, /* patt */
+       { 0x004a, &nv04_gr_ofuncs, NULL }, /* gdi */
+       { 0x0062, &nv04_gr_ofuncs, NULL }, /* surf2d */
+       { 0x0072, &nv04_gr_ofuncs, NULL }, /* beta4 */
+       { 0x0089, &nv04_gr_ofuncs, NULL }, /* sifm */
+       { 0x008a, &nv04_gr_ofuncs, NULL }, /* ifc */
+       { 0x0096, &nv04_gr_ofuncs, NULL }, /* celcius */
+       { 0x0097, &nv04_gr_ofuncs, NULL }, /* kelvin */
+       { 0x009e, &nv04_gr_ofuncs, NULL }, /* swzsurf */
+       { 0x009f, &nv04_gr_ofuncs, NULL }, /* imageblit */
+       {},
+};
+
+/*******************************************************************************
+ * PGRAPH context
+ ******************************************************************************/
+
+static int
+nv20_gr_context_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+                    struct nvkm_oclass *oclass, void *data, u32 size,
+                    struct nvkm_object **pobject)
+{
+       struct nv20_gr_chan *chan;
+       int ret, i;
+
+       ret = nvkm_gr_context_create(parent, engine, oclass, NULL, 0x37f0,
+                                    16, NVOBJ_FLAG_ZERO_ALLOC, &chan);
+       *pobject = nv_object(chan);
+       if (ret)
+               return ret;
+
+       chan->chid = nvkm_fifo_chan(parent)->chid;
+
+       nv_wo32(chan, 0x0000, 0x00000001 | (chan->chid << 24));
+       nv_wo32(chan, 0x033c, 0xffff0000);
+       nv_wo32(chan, 0x03a0, 0x0fff0000);
+       nv_wo32(chan, 0x03a4, 0x0fff0000);
+       nv_wo32(chan, 0x047c, 0x00000101);
+       nv_wo32(chan, 0x0490, 0x00000111);
+       nv_wo32(chan, 0x04a8, 0x44400000);
+       for (i = 0x04d4; i <= 0x04e0; i += 4)
+               nv_wo32(chan, i, 0x00030303);
+       for (i = 0x04f4; i <= 0x0500; i += 4)
+               nv_wo32(chan, i, 0x00080000);
+       for (i = 0x050c; i <= 0x0518; i += 4)
+               nv_wo32(chan, i, 0x01012000);
+       for (i = 0x051c; i <= 0x0528; i += 4)
+               nv_wo32(chan, i, 0x000105b8);
+       for (i = 0x052c; i <= 0x0538; i += 4)
+               nv_wo32(chan, i, 0x00080008);
+       for (i = 0x055c; i <= 0x0598; i += 4)
+               nv_wo32(chan, i, 0x07ff0000);
+       nv_wo32(chan, 0x05a4, 0x4b7fffff);
+       nv_wo32(chan, 0x05fc, 0x00000001);
+       nv_wo32(chan, 0x0604, 0x00004000);
+       nv_wo32(chan, 0x0610, 0x00000001);
+       nv_wo32(chan, 0x0618, 0x00040000);
+       nv_wo32(chan, 0x061c, 0x00010000);
+       for (i = 0x1c1c; i <= 0x248c; i += 16) {
+               nv_wo32(chan, (i + 0), 0x10700ff9);
+               nv_wo32(chan, (i + 4), 0x0436086c);
+               nv_wo32(chan, (i + 8), 0x000c001b);
+       }
+       nv_wo32(chan, 0x281c, 0x3f800000);
+       nv_wo32(chan, 0x2830, 0x3f800000);
+       nv_wo32(chan, 0x285c, 0x40000000);
+       nv_wo32(chan, 0x2860, 0x3f800000);
+       nv_wo32(chan, 0x2864, 0x3f000000);
+       nv_wo32(chan, 0x286c, 0x40000000);
+       nv_wo32(chan, 0x2870, 0x3f800000);
+       nv_wo32(chan, 0x2878, 0xbf800000);
+       nv_wo32(chan, 0x2880, 0xbf800000);
+       nv_wo32(chan, 0x34a4, 0x000fe000);
+       nv_wo32(chan, 0x3530, 0x000003f8);
+       nv_wo32(chan, 0x3540, 0x002fe000);
+       for (i = 0x355c; i <= 0x3578; i += 4)
+               nv_wo32(chan, i, 0x001c527c);
+       return 0;
+}
+
+int
+nv20_gr_context_init(struct nvkm_object *object)
+{
+       struct nv20_gr_priv *priv = (void *)object->engine;
+       struct nv20_gr_chan *chan = (void *)object;
+       int ret;
+
+       ret = nvkm_gr_context_init(&chan->base);
+       if (ret)
+               return ret;
+
+       nv_wo32(priv->ctxtab, chan->chid * 4, nv_gpuobj(chan)->addr >> 4);
+       return 0;
+}
+
+int
+nv20_gr_context_fini(struct nvkm_object *object, bool suspend)
+{
+       struct nv20_gr_priv *priv = (void *)object->engine;
+       struct nv20_gr_chan *chan = (void *)object;
+       int chid = -1;
+
+       nv_mask(priv, 0x400720, 0x00000001, 0x00000000);
+       if (nv_rd32(priv, 0x400144) & 0x00010000)
+               chid = (nv_rd32(priv, 0x400148) & 0x1f000000) >> 24;
+       if (chan->chid == chid) {
+               nv_wr32(priv, 0x400784, nv_gpuobj(chan)->addr >> 4);
+               nv_wr32(priv, 0x400788, 0x00000002);
+               nv_wait(priv, 0x400700, 0xffffffff, 0x00000000);
+               nv_wr32(priv, 0x400144, 0x10000000);
+               nv_mask(priv, 0x400148, 0xff000000, 0x1f000000);
+       }
+       nv_mask(priv, 0x400720, 0x00000001, 0x00000001);
+
+       nv_wo32(priv->ctxtab, chan->chid * 4, 0x00000000);
+       return nvkm_gr_context_fini(&chan->base, suspend);
+}
+
+static struct nvkm_oclass
+nv20_gr_cclass = {
+       .handle = NV_ENGCTX(GR, 0x20),
+       .ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = nv20_gr_context_ctor,
+               .dtor = _nvkm_gr_context_dtor,
+               .init = nv20_gr_context_init,
+               .fini = nv20_gr_context_fini,
+               .rd32 = _nvkm_gr_context_rd32,
+               .wr32 = _nvkm_gr_context_wr32,
+       },
+};
+
+/*******************************************************************************
+ * PGRAPH engine/subdev functions
+ ******************************************************************************/
+
+void
+nv20_gr_tile_prog(struct nvkm_engine *engine, int i)
+{
+       struct nvkm_fb_tile *tile = &nvkm_fb(engine)->tile.region[i];
+       struct nvkm_fifo *pfifo = nvkm_fifo(engine);
+       struct nv20_gr_priv *priv = (void *)engine;
+       unsigned long flags;
+
+       pfifo->pause(pfifo, &flags);
+       nv04_gr_idle(priv);
+
+       nv_wr32(priv, NV20_PGRAPH_TLIMIT(i), tile->limit);
+       nv_wr32(priv, NV20_PGRAPH_TSIZE(i), tile->pitch);
+       nv_wr32(priv, NV20_PGRAPH_TILE(i), tile->addr);
+
+       nv_wr32(priv, NV10_PGRAPH_RDI_INDEX, 0x00EA0030 + 4 * i);
+       nv_wr32(priv, NV10_PGRAPH_RDI_DATA, tile->limit);
+       nv_wr32(priv, NV10_PGRAPH_RDI_INDEX, 0x00EA0050 + 4 * i);
+       nv_wr32(priv, NV10_PGRAPH_RDI_DATA, tile->pitch);
+       nv_wr32(priv, NV10_PGRAPH_RDI_INDEX, 0x00EA0010 + 4 * i);
+       nv_wr32(priv, NV10_PGRAPH_RDI_DATA, tile->addr);
+
+       if (nv_device(engine)->chipset != 0x34) {
+               nv_wr32(priv, NV20_PGRAPH_ZCOMP(i), tile->zcomp);
+               nv_wr32(priv, NV10_PGRAPH_RDI_INDEX, 0x00ea0090 + 4 * i);
+               nv_wr32(priv, NV10_PGRAPH_RDI_DATA, tile->zcomp);
+       }
+
+       pfifo->start(pfifo, &flags);
+}
+
+void
+nv20_gr_intr(struct nvkm_subdev *subdev)
+{
+       struct nvkm_engine *engine = nv_engine(subdev);
+       struct nvkm_object *engctx;
+       struct nvkm_handle *handle;
+       struct nv20_gr_priv *priv = (void *)subdev;
+       u32 stat = nv_rd32(priv, NV03_PGRAPH_INTR);
+       u32 nsource = nv_rd32(priv, NV03_PGRAPH_NSOURCE);
+       u32 nstatus = nv_rd32(priv, NV03_PGRAPH_NSTATUS);
+       u32 addr = nv_rd32(priv, NV04_PGRAPH_TRAPPED_ADDR);
+       u32 chid = (addr & 0x01f00000) >> 20;
+       u32 subc = (addr & 0x00070000) >> 16;
+       u32 mthd = (addr & 0x00001ffc);
+       u32 data = nv_rd32(priv, NV04_PGRAPH_TRAPPED_DATA);
+       u32 class = nv_rd32(priv, 0x400160 + subc * 4) & 0xfff;
+       u32 show = stat;
+
+       engctx = nvkm_engctx_get(engine, chid);
+       if (stat & NV_PGRAPH_INTR_ERROR) {
+               if (nsource & NV03_PGRAPH_NSOURCE_ILLEGAL_MTHD) {
+                       handle = nvkm_handle_get_class(engctx, class);
+                       if (handle && !nv_call(handle->object, mthd, data))
+                               show &= ~NV_PGRAPH_INTR_ERROR;
+                       nvkm_handle_put(handle);
+               }
+       }
+
+       nv_wr32(priv, NV03_PGRAPH_INTR, stat);
+       nv_wr32(priv, NV04_PGRAPH_FIFO, 0x00000001);
+
+       if (show) {
+               nv_error(priv, "%s", "");
+               nvkm_bitfield_print(nv10_gr_intr_name, show);
+               pr_cont(" nsource:");
+               nvkm_bitfield_print(nv04_gr_nsource, nsource);
+               pr_cont(" nstatus:");
+               nvkm_bitfield_print(nv10_gr_nstatus, nstatus);
+               pr_cont("\n");
+               nv_error(priv,
+                        "ch %d [%s] subc %d class 0x%04x mthd 0x%04x data 0x%08x\n",
+                        chid, nvkm_client_name(engctx), subc, class, mthd,
+                        data);
+       }
+
+       nvkm_engctx_put(engctx);
+}
+
+static int
+nv20_gr_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+            struct nvkm_oclass *oclass, void *data, u32 size,
+            struct nvkm_object **pobject)
+{
+       struct nv20_gr_priv *priv;
+       int ret;
+
+       ret = nvkm_gr_create(parent, engine, oclass, true, &priv);
+       *pobject = nv_object(priv);
+       if (ret)
+               return ret;
+
+       ret = nvkm_gpuobj_new(nv_object(priv), NULL, 32 * 4, 16,
+                             NVOBJ_FLAG_ZERO_ALLOC, &priv->ctxtab);
+       if (ret)
+               return ret;
+
+       nv_subdev(priv)->unit = 0x00001000;
+       nv_subdev(priv)->intr = nv20_gr_intr;
+       nv_engine(priv)->cclass = &nv20_gr_cclass;
+       nv_engine(priv)->sclass = nv20_gr_sclass;
+       nv_engine(priv)->tile_prog = nv20_gr_tile_prog;
+       return 0;
+}
+
+void
+nv20_gr_dtor(struct nvkm_object *object)
+{
+       struct nv20_gr_priv *priv = (void *)object;
+       nvkm_gpuobj_ref(NULL, &priv->ctxtab);
+       nvkm_gr_destroy(&priv->base);
+}
+
+int
+nv20_gr_init(struct nvkm_object *object)
+{
+       struct nvkm_engine *engine = nv_engine(object);
+       struct nv20_gr_priv *priv = (void *)engine;
+       struct nvkm_fb *pfb = nvkm_fb(object);
+       u32 tmp, vramsz;
+       int ret, i;
+
+       ret = nvkm_gr_init(&priv->base);
+       if (ret)
+               return ret;
+
+       nv_wr32(priv, NV20_PGRAPH_CHANNEL_CTX_TABLE, priv->ctxtab->addr >> 4);
+
+       if (nv_device(priv)->chipset == 0x20) {
+               nv_wr32(priv, NV10_PGRAPH_RDI_INDEX, 0x003d0000);
+               for (i = 0; i < 15; i++)
+                       nv_wr32(priv, NV10_PGRAPH_RDI_DATA, 0x00000000);
+               nv_wait(priv, 0x400700, 0xffffffff, 0x00000000);
+       } else {
+               nv_wr32(priv, NV10_PGRAPH_RDI_INDEX, 0x02c80000);
+               for (i = 0; i < 32; i++)
+                       nv_wr32(priv, NV10_PGRAPH_RDI_DATA, 0x00000000);
+               nv_wait(priv, 0x400700, 0xffffffff, 0x00000000);
+       }
+
+       nv_wr32(priv, NV03_PGRAPH_INTR   , 0xFFFFFFFF);
+       nv_wr32(priv, NV03_PGRAPH_INTR_EN, 0xFFFFFFFF);
+
+       nv_wr32(priv, NV04_PGRAPH_DEBUG_0, 0xFFFFFFFF);
+       nv_wr32(priv, NV04_PGRAPH_DEBUG_0, 0x00000000);
+       nv_wr32(priv, NV04_PGRAPH_DEBUG_1, 0x00118700);
+       nv_wr32(priv, NV04_PGRAPH_DEBUG_3, 0xF3CE0475); /* 0x4 = auto ctx switch */
+       nv_wr32(priv, NV10_PGRAPH_DEBUG_4, 0x00000000);
+       nv_wr32(priv, 0x40009C           , 0x00000040);
+
+       if (nv_device(priv)->chipset >= 0x25) {
+               nv_wr32(priv, 0x400890, 0x00a8cfff);
+               nv_wr32(priv, 0x400610, 0x304B1FB6);
+               nv_wr32(priv, 0x400B80, 0x1cbd3883);
+               nv_wr32(priv, 0x400B84, 0x44000000);
+               nv_wr32(priv, 0x400098, 0x40000080);
+               nv_wr32(priv, 0x400B88, 0x000000ff);
+
+       } else {
+               nv_wr32(priv, 0x400880, 0x0008c7df);
+               nv_wr32(priv, 0x400094, 0x00000005);
+               nv_wr32(priv, 0x400B80, 0x45eae20e);
+               nv_wr32(priv, 0x400B84, 0x24000000);
+               nv_wr32(priv, 0x400098, 0x00000040);
+               nv_wr32(priv, NV10_PGRAPH_RDI_INDEX, 0x00E00038);
+               nv_wr32(priv, NV10_PGRAPH_RDI_DATA , 0x00000030);
+               nv_wr32(priv, NV10_PGRAPH_RDI_INDEX, 0x00E10038);
+               nv_wr32(priv, NV10_PGRAPH_RDI_DATA , 0x00000030);
+       }
+
+       /* Turn all the tiling regions off. */
+       for (i = 0; i < pfb->tile.regions; i++)
+               engine->tile_prog(engine, i);
+
+       nv_wr32(priv, 0x4009a0, nv_rd32(priv, 0x100324));
+       nv_wr32(priv, NV10_PGRAPH_RDI_INDEX, 0x00EA000C);
+       nv_wr32(priv, NV10_PGRAPH_RDI_DATA, nv_rd32(priv, 0x100324));
+
+       nv_wr32(priv, NV10_PGRAPH_CTX_CONTROL, 0x10000100);
+       nv_wr32(priv, NV10_PGRAPH_STATE      , 0xFFFFFFFF);
+
+       tmp = nv_rd32(priv, NV10_PGRAPH_SURFACE) & 0x0007ff00;
+       nv_wr32(priv, NV10_PGRAPH_SURFACE, tmp);
+       tmp = nv_rd32(priv, NV10_PGRAPH_SURFACE) | 0x00020100;
+       nv_wr32(priv, NV10_PGRAPH_SURFACE, tmp);
+
+       /* begin RAM config */
+       vramsz = nv_device_resource_len(nv_device(priv), 0) - 1;
+       nv_wr32(priv, 0x4009A4, nv_rd32(priv, 0x100200));
+       nv_wr32(priv, 0x4009A8, nv_rd32(priv, 0x100204));
+       nv_wr32(priv, NV10_PGRAPH_RDI_INDEX, 0x00EA0000);
+       nv_wr32(priv, NV10_PGRAPH_RDI_DATA , nv_rd32(priv, 0x100200));
+       nv_wr32(priv, NV10_PGRAPH_RDI_INDEX, 0x00EA0004);
+       nv_wr32(priv, NV10_PGRAPH_RDI_DATA , nv_rd32(priv, 0x100204));
+       nv_wr32(priv, 0x400820, 0);
+       nv_wr32(priv, 0x400824, 0);
+       nv_wr32(priv, 0x400864, vramsz - 1);
+       nv_wr32(priv, 0x400868, vramsz - 1);
+
+       /* interesting.. the below overwrites some of the tile setup above.. */
+       nv_wr32(priv, 0x400B20, 0x00000000);
+       nv_wr32(priv, 0x400B04, 0xFFFFFFFF);
+
+       nv_wr32(priv, NV03_PGRAPH_ABS_UCLIP_XMIN, 0);
+       nv_wr32(priv, NV03_PGRAPH_ABS_UCLIP_YMIN, 0);
+       nv_wr32(priv, NV03_PGRAPH_ABS_UCLIP_XMAX, 0x7fff);
+       nv_wr32(priv, NV03_PGRAPH_ABS_UCLIP_YMAX, 0x7fff);
+       return 0;
+}
+
+struct nvkm_oclass
+nv20_gr_oclass = {
+       .handle = NV_ENGINE(GR, 0x20),
+       .ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = nv20_gr_ctor,
+               .dtor = nv20_gr_dtor,
+               .init = nv20_gr_init,
+               .fini = _nvkm_gr_fini,
+       },
+};
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/gr/nv20.h b/drivers/gpu/drm/nouveau/nvkm/engine/gr/nv20.h
new file mode 100644 (file)
index 0000000..ac4dc04
--- /dev/null
@@ -0,0 +1,26 @@
+#ifndef __NV20_GR_H__
+#define __NV20_GR_H__
+#include <engine/gr.h>
+
+struct nv20_gr_priv {
+       struct nvkm_gr base;
+       struct nvkm_gpuobj *ctxtab;
+};
+
+struct nv20_gr_chan {
+       struct nvkm_gr_chan base;
+       int chid;
+};
+
+extern struct nvkm_oclass nv25_gr_sclass[];
+int  nv20_gr_context_init(struct nvkm_object *);
+int  nv20_gr_context_fini(struct nvkm_object *, bool);
+
+void nv20_gr_tile_prog(struct nvkm_engine *, int);
+void nv20_gr_intr(struct nvkm_subdev *);
+
+void nv20_gr_dtor(struct nvkm_object *);
+int  nv20_gr_init(struct nvkm_object *);
+
+int  nv30_gr_init(struct nvkm_object *);
+#endif
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/gr/nv25.c b/drivers/gpu/drm/nouveau/nvkm/engine/gr/nv25.c
new file mode 100644 (file)
index 0000000..bc36251
--- /dev/null
@@ -0,0 +1,158 @@
+#include "nv20.h"
+#include "regs.h"
+
+#include <engine/fifo.h>
+
+/*******************************************************************************
+ * Graphics object classes
+ ******************************************************************************/
+
+struct nvkm_oclass
+nv25_gr_sclass[] = {
+       { 0x0012, &nv04_gr_ofuncs, NULL }, /* beta1 */
+       { 0x0019, &nv04_gr_ofuncs, NULL }, /* clip */
+       { 0x0030, &nv04_gr_ofuncs, NULL }, /* null */
+       { 0x0039, &nv04_gr_ofuncs, NULL }, /* m2mf */
+       { 0x0043, &nv04_gr_ofuncs, NULL }, /* rop */
+       { 0x0044, &nv04_gr_ofuncs, NULL }, /* patt */
+       { 0x004a, &nv04_gr_ofuncs, NULL }, /* gdi */
+       { 0x0062, &nv04_gr_ofuncs, NULL }, /* surf2d */
+       { 0x0072, &nv04_gr_ofuncs, NULL }, /* beta4 */
+       { 0x0089, &nv04_gr_ofuncs, NULL }, /* sifm */
+       { 0x008a, &nv04_gr_ofuncs, NULL }, /* ifc */
+       { 0x0096, &nv04_gr_ofuncs, NULL }, /* celcius */
+       { 0x009e, &nv04_gr_ofuncs, NULL }, /* swzsurf */
+       { 0x009f, &nv04_gr_ofuncs, NULL }, /* imageblit */
+       { 0x0597, &nv04_gr_ofuncs, NULL }, /* kelvin */
+       {},
+};
+
+/*******************************************************************************
+ * PGRAPH context
+ ******************************************************************************/
+
+static int
+nv25_gr_context_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+                    struct nvkm_oclass *oclass, void *data, u32 size,
+                    struct nvkm_object **pobject)
+{
+       struct nv20_gr_chan *chan;
+       int ret, i;
+
+       ret = nvkm_gr_context_create(parent, engine, oclass, NULL, 0x3724,
+                                    16, NVOBJ_FLAG_ZERO_ALLOC, &chan);
+       *pobject = nv_object(chan);
+       if (ret)
+               return ret;
+
+       chan->chid = nvkm_fifo_chan(parent)->chid;
+
+       nv_wo32(chan, 0x0028, 0x00000001 | (chan->chid << 24));
+       nv_wo32(chan, 0x035c, 0xffff0000);
+       nv_wo32(chan, 0x03c0, 0x0fff0000);
+       nv_wo32(chan, 0x03c4, 0x0fff0000);
+       nv_wo32(chan, 0x049c, 0x00000101);
+       nv_wo32(chan, 0x04b0, 0x00000111);
+       nv_wo32(chan, 0x04c8, 0x00000080);
+       nv_wo32(chan, 0x04cc, 0xffff0000);
+       nv_wo32(chan, 0x04d0, 0x00000001);
+       nv_wo32(chan, 0x04e4, 0x44400000);
+       nv_wo32(chan, 0x04fc, 0x4b800000);
+       for (i = 0x0510; i <= 0x051c; i += 4)
+               nv_wo32(chan, i, 0x00030303);
+       for (i = 0x0530; i <= 0x053c; i += 4)
+               nv_wo32(chan, i, 0x00080000);
+       for (i = 0x0548; i <= 0x0554; i += 4)
+               nv_wo32(chan, i, 0x01012000);
+       for (i = 0x0558; i <= 0x0564; i += 4)
+               nv_wo32(chan, i, 0x000105b8);
+       for (i = 0x0568; i <= 0x0574; i += 4)
+               nv_wo32(chan, i, 0x00080008);
+       for (i = 0x0598; i <= 0x05d4; i += 4)
+               nv_wo32(chan, i, 0x07ff0000);
+       nv_wo32(chan, 0x05e0, 0x4b7fffff);
+       nv_wo32(chan, 0x0620, 0x00000080);
+       nv_wo32(chan, 0x0624, 0x30201000);
+       nv_wo32(chan, 0x0628, 0x70605040);
+       nv_wo32(chan, 0x062c, 0xb0a09080);
+       nv_wo32(chan, 0x0630, 0xf0e0d0c0);
+       nv_wo32(chan, 0x0664, 0x00000001);
+       nv_wo32(chan, 0x066c, 0x00004000);
+       nv_wo32(chan, 0x0678, 0x00000001);
+       nv_wo32(chan, 0x0680, 0x00040000);
+       nv_wo32(chan, 0x0684, 0x00010000);
+       for (i = 0x1b04; i <= 0x2374; i += 16) {
+               nv_wo32(chan, (i + 0), 0x10700ff9);
+               nv_wo32(chan, (i + 4), 0x0436086c);
+               nv_wo32(chan, (i + 8), 0x000c001b);
+       }
+       nv_wo32(chan, 0x2704, 0x3f800000);
+       nv_wo32(chan, 0x2718, 0x3f800000);
+       nv_wo32(chan, 0x2744, 0x40000000);
+       nv_wo32(chan, 0x2748, 0x3f800000);
+       nv_wo32(chan, 0x274c, 0x3f000000);
+       nv_wo32(chan, 0x2754, 0x40000000);
+       nv_wo32(chan, 0x2758, 0x3f800000);
+       nv_wo32(chan, 0x2760, 0xbf800000);
+       nv_wo32(chan, 0x2768, 0xbf800000);
+       nv_wo32(chan, 0x308c, 0x000fe000);
+       nv_wo32(chan, 0x3108, 0x000003f8);
+       nv_wo32(chan, 0x3468, 0x002fe000);
+       for (i = 0x3484; i <= 0x34a0; i += 4)
+               nv_wo32(chan, i, 0x001c527c);
+       return 0;
+}
+
+static struct nvkm_oclass
+nv25_gr_cclass = {
+       .handle = NV_ENGCTX(GR, 0x25),
+       .ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = nv25_gr_context_ctor,
+               .dtor = _nvkm_gr_context_dtor,
+               .init = nv20_gr_context_init,
+               .fini = nv20_gr_context_fini,
+               .rd32 = _nvkm_gr_context_rd32,
+               .wr32 = _nvkm_gr_context_wr32,
+       },
+};
+
+/*******************************************************************************
+ * PGRAPH engine/subdev functions
+ ******************************************************************************/
+
+static int
+nv25_gr_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+            struct nvkm_oclass *oclass, void *data, u32 size,
+            struct nvkm_object **pobject)
+{
+       struct nv20_gr_priv *priv;
+       int ret;
+
+       ret = nvkm_gr_create(parent, engine, oclass, true, &priv);
+       *pobject = nv_object(priv);
+       if (ret)
+               return ret;
+
+       ret = nvkm_gpuobj_new(nv_object(priv), NULL, 32 * 4, 16,
+                             NVOBJ_FLAG_ZERO_ALLOC, &priv->ctxtab);
+       if (ret)
+               return ret;
+
+       nv_subdev(priv)->unit = 0x00001000;
+       nv_subdev(priv)->intr = nv20_gr_intr;
+       nv_engine(priv)->cclass = &nv25_gr_cclass;
+       nv_engine(priv)->sclass = nv25_gr_sclass;
+       nv_engine(priv)->tile_prog = nv20_gr_tile_prog;
+       return 0;
+}
+
+struct nvkm_oclass
+nv25_gr_oclass = {
+       .handle = NV_ENGINE(GR, 0x25),
+       .ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = nv25_gr_ctor,
+               .dtor = nv20_gr_dtor,
+               .init = nv20_gr_init,
+               .fini = _nvkm_gr_fini,
+       },
+};
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/gr/nv2a.c b/drivers/gpu/drm/nouveau/nvkm/engine/gr/nv2a.c
new file mode 100644 (file)
index 0000000..22a5096
--- /dev/null
@@ -0,0 +1,125 @@
+#include "nv20.h"
+#include "regs.h"
+
+#include <engine/fifo.h>
+
+/*******************************************************************************
+ * PGRAPH context
+ ******************************************************************************/
+
+static int
+nv2a_gr_context_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+                    struct nvkm_oclass *oclass, void *data, u32 size,
+                    struct nvkm_object **pobject)
+{
+       struct nv20_gr_chan *chan;
+       int ret, i;
+
+       ret = nvkm_gr_context_create(parent, engine, oclass, NULL, 0x36b0,
+                                    16, NVOBJ_FLAG_ZERO_ALLOC, &chan);
+       *pobject = nv_object(chan);
+       if (ret)
+               return ret;
+
+       chan->chid = nvkm_fifo_chan(parent)->chid;
+
+       nv_wo32(chan, 0x0000, 0x00000001 | (chan->chid << 24));
+       nv_wo32(chan, 0x033c, 0xffff0000);
+       nv_wo32(chan, 0x03a0, 0x0fff0000);
+       nv_wo32(chan, 0x03a4, 0x0fff0000);
+       nv_wo32(chan, 0x047c, 0x00000101);
+       nv_wo32(chan, 0x0490, 0x00000111);
+       nv_wo32(chan, 0x04a8, 0x44400000);
+       for (i = 0x04d4; i <= 0x04e0; i += 4)
+               nv_wo32(chan, i, 0x00030303);
+       for (i = 0x04f4; i <= 0x0500; i += 4)
+               nv_wo32(chan, i, 0x00080000);
+       for (i = 0x050c; i <= 0x0518; i += 4)
+               nv_wo32(chan, i, 0x01012000);
+       for (i = 0x051c; i <= 0x0528; i += 4)
+               nv_wo32(chan, i, 0x000105b8);
+       for (i = 0x052c; i <= 0x0538; i += 4)
+               nv_wo32(chan, i, 0x00080008);
+       for (i = 0x055c; i <= 0x0598; i += 4)
+               nv_wo32(chan, i, 0x07ff0000);
+       nv_wo32(chan, 0x05a4, 0x4b7fffff);
+       nv_wo32(chan, 0x05fc, 0x00000001);
+       nv_wo32(chan, 0x0604, 0x00004000);
+       nv_wo32(chan, 0x0610, 0x00000001);
+       nv_wo32(chan, 0x0618, 0x00040000);
+       nv_wo32(chan, 0x061c, 0x00010000);
+       for (i = 0x1a9c; i <= 0x22fc; i += 16) { /*XXX: check!! */
+               nv_wo32(chan, (i + 0), 0x10700ff9);
+               nv_wo32(chan, (i + 4), 0x0436086c);
+               nv_wo32(chan, (i + 8), 0x000c001b);
+       }
+       nv_wo32(chan, 0x269c, 0x3f800000);
+       nv_wo32(chan, 0x26b0, 0x3f800000);
+       nv_wo32(chan, 0x26dc, 0x40000000);
+       nv_wo32(chan, 0x26e0, 0x3f800000);
+       nv_wo32(chan, 0x26e4, 0x3f000000);
+       nv_wo32(chan, 0x26ec, 0x40000000);
+       nv_wo32(chan, 0x26f0, 0x3f800000);
+       nv_wo32(chan, 0x26f8, 0xbf800000);
+       nv_wo32(chan, 0x2700, 0xbf800000);
+       nv_wo32(chan, 0x3024, 0x000fe000);
+       nv_wo32(chan, 0x30a0, 0x000003f8);
+       nv_wo32(chan, 0x33fc, 0x002fe000);
+       for (i = 0x341c; i <= 0x3438; i += 4)
+               nv_wo32(chan, i, 0x001c527c);
+       return 0;
+}
+
+static struct nvkm_oclass
+nv2a_gr_cclass = {
+       .handle = NV_ENGCTX(GR, 0x2a),
+       .ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = nv2a_gr_context_ctor,
+               .dtor = _nvkm_gr_context_dtor,
+               .init = nv20_gr_context_init,
+               .fini = nv20_gr_context_fini,
+               .rd32 = _nvkm_gr_context_rd32,
+               .wr32 = _nvkm_gr_context_wr32,
+       },
+};
+
+/*******************************************************************************
+ * PGRAPH engine/subdev functions
+ ******************************************************************************/
+
+static int
+nv2a_gr_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+            struct nvkm_oclass *oclass, void *data, u32 size,
+            struct nvkm_object **pobject)
+{
+       struct nv20_gr_priv *priv;
+       int ret;
+
+       ret = nvkm_gr_create(parent, engine, oclass, true, &priv);
+       *pobject = nv_object(priv);
+       if (ret)
+               return ret;
+
+       ret = nvkm_gpuobj_new(nv_object(priv), NULL, 32 * 4, 16,
+                             NVOBJ_FLAG_ZERO_ALLOC, &priv->ctxtab);
+       if (ret)
+               return ret;
+
+       nv_subdev(priv)->unit = 0x00001000;
+       nv_subdev(priv)->intr = nv20_gr_intr;
+       nv_engine(priv)->cclass = &nv2a_gr_cclass;
+       nv_engine(priv)->sclass = nv25_gr_sclass;
+       nv_engine(priv)->tile_prog = nv20_gr_tile_prog;
+       return 0;
+}
+
+struct nvkm_oclass
+nv2a_gr_oclass = {
+       .handle = NV_ENGINE(GR, 0x2a),
+       .ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = nv2a_gr_ctor,
+               .dtor = nv20_gr_dtor,
+               .init = nv20_gr_init,
+               .fini = _nvkm_gr_fini,
+       },
+};
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/gr/nv30.c b/drivers/gpu/drm/nouveau/nvkm/engine/gr/nv30.c
new file mode 100644 (file)
index 0000000..dcc84eb
--- /dev/null
@@ -0,0 +1,231 @@
+#include "nv20.h"
+#include "regs.h"
+
+#include <core/device.h>
+#include <engine/fifo.h>
+#include <subdev/fb.h>
+
+/*******************************************************************************
+ * Graphics object classes
+ ******************************************************************************/
+
+static struct nvkm_oclass
+nv30_gr_sclass[] = {
+       { 0x0012, &nv04_gr_ofuncs, NULL }, /* beta1 */
+       { 0x0019, &nv04_gr_ofuncs, NULL }, /* clip */
+       { 0x0030, &nv04_gr_ofuncs, NULL }, /* null */
+       { 0x0039, &nv04_gr_ofuncs, NULL }, /* m2mf */
+       { 0x0043, &nv04_gr_ofuncs, NULL }, /* rop */
+       { 0x0044, &nv04_gr_ofuncs, NULL }, /* patt */
+       { 0x004a, &nv04_gr_ofuncs, NULL }, /* gdi */
+       { 0x0062, &nv04_gr_ofuncs, NULL }, /* surf2d */
+       { 0x0072, &nv04_gr_ofuncs, NULL }, /* beta4 */
+       { 0x0089, &nv04_gr_ofuncs, NULL }, /* sifm */
+       { 0x008a, &nv04_gr_ofuncs, NULL }, /* ifc */
+       { 0x009f, &nv04_gr_ofuncs, NULL }, /* imageblit */
+       { 0x0362, &nv04_gr_ofuncs, NULL }, /* surf2d (nv30) */
+       { 0x0389, &nv04_gr_ofuncs, NULL }, /* sifm (nv30) */
+       { 0x038a, &nv04_gr_ofuncs, NULL }, /* ifc (nv30) */
+       { 0x039e, &nv04_gr_ofuncs, NULL }, /* swzsurf (nv30) */
+       { 0x0397, &nv04_gr_ofuncs, NULL }, /* rankine */
+       {},
+};
+
+/*******************************************************************************
+ * PGRAPH context
+ ******************************************************************************/
+
+static int
+nv30_gr_context_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+                    struct nvkm_oclass *oclass, void *data, u32 size,
+                    struct nvkm_object **pobject)
+{
+       struct nv20_gr_chan *chan;
+       int ret, i;
+
+       ret = nvkm_gr_context_create(parent, engine, oclass, NULL, 0x5f48,
+                                    16, NVOBJ_FLAG_ZERO_ALLOC, &chan);
+       *pobject = nv_object(chan);
+       if (ret)
+               return ret;
+
+       chan->chid = nvkm_fifo_chan(parent)->chid;
+
+       nv_wo32(chan, 0x0028, 0x00000001 | (chan->chid << 24));
+       nv_wo32(chan, 0x0410, 0x00000101);
+       nv_wo32(chan, 0x0424, 0x00000111);
+       nv_wo32(chan, 0x0428, 0x00000060);
+       nv_wo32(chan, 0x0444, 0x00000080);
+       nv_wo32(chan, 0x0448, 0xffff0000);
+       nv_wo32(chan, 0x044c, 0x00000001);
+       nv_wo32(chan, 0x0460, 0x44400000);
+       nv_wo32(chan, 0x048c, 0xffff0000);
+       for (i = 0x04e0; i < 0x04e8; i += 4)
+               nv_wo32(chan, i, 0x0fff0000);
+       nv_wo32(chan, 0x04ec, 0x00011100);
+       for (i = 0x0508; i < 0x0548; i += 4)
+               nv_wo32(chan, i, 0x07ff0000);
+       nv_wo32(chan, 0x0550, 0x4b7fffff);
+       nv_wo32(chan, 0x058c, 0x00000080);
+       nv_wo32(chan, 0x0590, 0x30201000);
+       nv_wo32(chan, 0x0594, 0x70605040);
+       nv_wo32(chan, 0x0598, 0xb8a89888);
+       nv_wo32(chan, 0x059c, 0xf8e8d8c8);
+       nv_wo32(chan, 0x05b0, 0xb0000000);
+       for (i = 0x0600; i < 0x0640; i += 4)
+               nv_wo32(chan, i, 0x00010588);
+       for (i = 0x0640; i < 0x0680; i += 4)
+               nv_wo32(chan, i, 0x00030303);
+       for (i = 0x06c0; i < 0x0700; i += 4)
+               nv_wo32(chan, i, 0x0008aae4);
+       for (i = 0x0700; i < 0x0740; i += 4)
+               nv_wo32(chan, i, 0x01012000);
+       for (i = 0x0740; i < 0x0780; i += 4)
+               nv_wo32(chan, i, 0x00080008);
+       nv_wo32(chan, 0x085c, 0x00040000);
+       nv_wo32(chan, 0x0860, 0x00010000);
+       for (i = 0x0864; i < 0x0874; i += 4)
+               nv_wo32(chan, i, 0x00040004);
+       for (i = 0x1f18; i <= 0x3088 ; i += 16) {
+               nv_wo32(chan, i + 0, 0x10700ff9);
+               nv_wo32(chan, i + 1, 0x0436086c);
+               nv_wo32(chan, i + 2, 0x000c001b);
+       }
+       for (i = 0x30b8; i < 0x30c8; i += 4)
+               nv_wo32(chan, i, 0x0000ffff);
+       nv_wo32(chan, 0x344c, 0x3f800000);
+       nv_wo32(chan, 0x3808, 0x3f800000);
+       nv_wo32(chan, 0x381c, 0x3f800000);
+       nv_wo32(chan, 0x3848, 0x40000000);
+       nv_wo32(chan, 0x384c, 0x3f800000);
+       nv_wo32(chan, 0x3850, 0x3f000000);
+       nv_wo32(chan, 0x3858, 0x40000000);
+       nv_wo32(chan, 0x385c, 0x3f800000);
+       nv_wo32(chan, 0x3864, 0xbf800000);
+       nv_wo32(chan, 0x386c, 0xbf800000);
+       return 0;
+}
+
+static struct nvkm_oclass
+nv30_gr_cclass = {
+       .handle = NV_ENGCTX(GR, 0x30),
+       .ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = nv30_gr_context_ctor,
+               .dtor = _nvkm_gr_context_dtor,
+               .init = nv20_gr_context_init,
+               .fini = nv20_gr_context_fini,
+               .rd32 = _nvkm_gr_context_rd32,
+               .wr32 = _nvkm_gr_context_wr32,
+       },
+};
+
+/*******************************************************************************
+ * PGRAPH engine/subdev functions
+ ******************************************************************************/
+
+static int
+nv30_gr_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+            struct nvkm_oclass *oclass, void *data, u32 size,
+            struct nvkm_object **pobject)
+{
+       struct nv20_gr_priv *priv;
+       int ret;
+
+       ret = nvkm_gr_create(parent, engine, oclass, true, &priv);
+       *pobject = nv_object(priv);
+       if (ret)
+               return ret;
+
+       ret = nvkm_gpuobj_new(nv_object(priv), NULL, 32 * 4, 16,
+                             NVOBJ_FLAG_ZERO_ALLOC, &priv->ctxtab);
+       if (ret)
+               return ret;
+
+       nv_subdev(priv)->unit = 0x00001000;
+       nv_subdev(priv)->intr = nv20_gr_intr;
+       nv_engine(priv)->cclass = &nv30_gr_cclass;
+       nv_engine(priv)->sclass = nv30_gr_sclass;
+       nv_engine(priv)->tile_prog = nv20_gr_tile_prog;
+       return 0;
+}
+
+int
+nv30_gr_init(struct nvkm_object *object)
+{
+       struct nvkm_engine *engine = nv_engine(object);
+       struct nv20_gr_priv *priv = (void *)engine;
+       struct nvkm_fb *pfb = nvkm_fb(object);
+       int ret, i;
+
+       ret = nvkm_gr_init(&priv->base);
+       if (ret)
+               return ret;
+
+       nv_wr32(priv, NV20_PGRAPH_CHANNEL_CTX_TABLE, priv->ctxtab->addr >> 4);
+
+       nv_wr32(priv, NV03_PGRAPH_INTR   , 0xFFFFFFFF);
+       nv_wr32(priv, NV03_PGRAPH_INTR_EN, 0xFFFFFFFF);
+
+       nv_wr32(priv, NV04_PGRAPH_DEBUG_0, 0xFFFFFFFF);
+       nv_wr32(priv, NV04_PGRAPH_DEBUG_0, 0x00000000);
+       nv_wr32(priv, NV04_PGRAPH_DEBUG_1, 0x401287c0);
+       nv_wr32(priv, 0x400890, 0x01b463ff);
+       nv_wr32(priv, NV04_PGRAPH_DEBUG_3, 0xf2de0475);
+       nv_wr32(priv, NV10_PGRAPH_DEBUG_4, 0x00008000);
+       nv_wr32(priv, NV04_PGRAPH_LIMIT_VIOL_PIX, 0xf04bdff6);
+       nv_wr32(priv, 0x400B80, 0x1003d888);
+       nv_wr32(priv, 0x400B84, 0x0c000000);
+       nv_wr32(priv, 0x400098, 0x00000000);
+       nv_wr32(priv, 0x40009C, 0x0005ad00);
+       nv_wr32(priv, 0x400B88, 0x62ff00ff); /* suspiciously like PGRAPH_DEBUG_2 */
+       nv_wr32(priv, 0x4000a0, 0x00000000);
+       nv_wr32(priv, 0x4000a4, 0x00000008);
+       nv_wr32(priv, 0x4008a8, 0xb784a400);
+       nv_wr32(priv, 0x400ba0, 0x002f8685);
+       nv_wr32(priv, 0x400ba4, 0x00231f3f);
+       nv_wr32(priv, 0x4008a4, 0x40000020);
+
+       if (nv_device(priv)->chipset == 0x34) {
+               nv_wr32(priv, NV10_PGRAPH_RDI_INDEX, 0x00EA0004);
+               nv_wr32(priv, NV10_PGRAPH_RDI_DATA , 0x00200201);
+               nv_wr32(priv, NV10_PGRAPH_RDI_INDEX, 0x00EA0008);
+               nv_wr32(priv, NV10_PGRAPH_RDI_DATA , 0x00000008);
+               nv_wr32(priv, NV10_PGRAPH_RDI_INDEX, 0x00EA0000);
+               nv_wr32(priv, NV10_PGRAPH_RDI_DATA , 0x00000032);
+               nv_wr32(priv, NV10_PGRAPH_RDI_INDEX, 0x00E00004);
+               nv_wr32(priv, NV10_PGRAPH_RDI_DATA , 0x00000002);
+       }
+
+       nv_wr32(priv, 0x4000c0, 0x00000016);
+
+       /* Turn all the tiling regions off. */
+       for (i = 0; i < pfb->tile.regions; i++)
+               engine->tile_prog(engine, i);
+
+       nv_wr32(priv, NV10_PGRAPH_CTX_CONTROL, 0x10000100);
+       nv_wr32(priv, NV10_PGRAPH_STATE      , 0xFFFFFFFF);
+       nv_wr32(priv, 0x0040075c             , 0x00000001);
+
+       /* begin RAM config */
+       /* vramsz = pci_resource_len(priv->dev->pdev, 0) - 1; */
+       nv_wr32(priv, 0x4009A4, nv_rd32(priv, 0x100200));
+       nv_wr32(priv, 0x4009A8, nv_rd32(priv, 0x100204));
+       if (nv_device(priv)->chipset != 0x34) {
+               nv_wr32(priv, 0x400750, 0x00EA0000);
+               nv_wr32(priv, 0x400754, nv_rd32(priv, 0x100200));
+               nv_wr32(priv, 0x400750, 0x00EA0004);
+               nv_wr32(priv, 0x400754, nv_rd32(priv, 0x100204));
+       }
+       return 0;
+}
+
+struct nvkm_oclass
+nv30_gr_oclass = {
+       .handle = NV_ENGINE(GR, 0x30),
+       .ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = nv30_gr_ctor,
+               .dtor = nv20_gr_dtor,
+               .init = nv30_gr_init,
+               .fini = _nvkm_gr_fini,
+       },
+};
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/gr/nv34.c b/drivers/gpu/drm/nouveau/nvkm/engine/gr/nv34.c
new file mode 100644 (file)
index 0000000..985b7f3
--- /dev/null
@@ -0,0 +1,159 @@
+#include "nv20.h"
+#include "regs.h"
+
+#include <engine/fifo.h>
+
+/*******************************************************************************
+ * Graphics object classes
+ ******************************************************************************/
+
+static struct nvkm_oclass
+nv34_gr_sclass[] = {
+       { 0x0012, &nv04_gr_ofuncs, NULL }, /* beta1 */
+       { 0x0019, &nv04_gr_ofuncs, NULL }, /* clip */
+       { 0x0030, &nv04_gr_ofuncs, NULL }, /* null */
+       { 0x0039, &nv04_gr_ofuncs, NULL }, /* m2mf */
+       { 0x0043, &nv04_gr_ofuncs, NULL }, /* rop */
+       { 0x0044, &nv04_gr_ofuncs, NULL }, /* patt */
+       { 0x004a, &nv04_gr_ofuncs, NULL }, /* gdi */
+       { 0x0062, &nv04_gr_ofuncs, NULL }, /* surf2d */
+       { 0x0072, &nv04_gr_ofuncs, NULL }, /* beta4 */
+       { 0x0089, &nv04_gr_ofuncs, NULL }, /* sifm */
+       { 0x008a, &nv04_gr_ofuncs, NULL }, /* ifc */
+       { 0x009f, &nv04_gr_ofuncs, NULL }, /* imageblit */
+       { 0x0362, &nv04_gr_ofuncs, NULL }, /* surf2d (nv30) */
+       { 0x0389, &nv04_gr_ofuncs, NULL }, /* sifm (nv30) */
+       { 0x038a, &nv04_gr_ofuncs, NULL }, /* ifc (nv30) */
+       { 0x039e, &nv04_gr_ofuncs, NULL }, /* swzsurf (nv30) */
+       { 0x0697, &nv04_gr_ofuncs, NULL }, /* rankine */
+       {},
+};
+
+/*******************************************************************************
+ * PGRAPH context
+ ******************************************************************************/
+
+static int
+nv34_gr_context_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+                    struct nvkm_oclass *oclass, void *data, u32 size,
+                    struct nvkm_object **pobject)
+{
+       struct nv20_gr_chan *chan;
+       int ret, i;
+
+       ret = nvkm_gr_context_create(parent, engine, oclass, NULL, 0x46dc,
+                                    16, NVOBJ_FLAG_ZERO_ALLOC, &chan);
+       *pobject = nv_object(chan);
+       if (ret)
+               return ret;
+
+       chan->chid = nvkm_fifo_chan(parent)->chid;
+
+       nv_wo32(chan, 0x0028, 0x00000001 | (chan->chid << 24));
+       nv_wo32(chan, 0x040c, 0x01000101);
+       nv_wo32(chan, 0x0420, 0x00000111);
+       nv_wo32(chan, 0x0424, 0x00000060);
+       nv_wo32(chan, 0x0440, 0x00000080);
+       nv_wo32(chan, 0x0444, 0xffff0000);
+       nv_wo32(chan, 0x0448, 0x00000001);
+       nv_wo32(chan, 0x045c, 0x44400000);
+       nv_wo32(chan, 0x0480, 0xffff0000);
+       for (i = 0x04d4; i < 0x04dc; i += 4)
+               nv_wo32(chan, i, 0x0fff0000);
+       nv_wo32(chan, 0x04e0, 0x00011100);
+       for (i = 0x04fc; i < 0x053c; i += 4)
+               nv_wo32(chan, i, 0x07ff0000);
+       nv_wo32(chan, 0x0544, 0x4b7fffff);
+       nv_wo32(chan, 0x057c, 0x00000080);
+       nv_wo32(chan, 0x0580, 0x30201000);
+       nv_wo32(chan, 0x0584, 0x70605040);
+       nv_wo32(chan, 0x0588, 0xb8a89888);
+       nv_wo32(chan, 0x058c, 0xf8e8d8c8);
+       nv_wo32(chan, 0x05a0, 0xb0000000);
+       for (i = 0x05f0; i < 0x0630; i += 4)
+               nv_wo32(chan, i, 0x00010588);
+       for (i = 0x0630; i < 0x0670; i += 4)
+               nv_wo32(chan, i, 0x00030303);
+       for (i = 0x06b0; i < 0x06f0; i += 4)
+               nv_wo32(chan, i, 0x0008aae4);
+       for (i = 0x06f0; i < 0x0730; i += 4)
+               nv_wo32(chan, i, 0x01012000);
+       for (i = 0x0730; i < 0x0770; i += 4)
+               nv_wo32(chan, i, 0x00080008);
+       nv_wo32(chan, 0x0850, 0x00040000);
+       nv_wo32(chan, 0x0854, 0x00010000);
+       for (i = 0x0858; i < 0x0868; i += 4)
+               nv_wo32(chan, i, 0x00040004);
+       for (i = 0x15ac; i <= 0x271c ; i += 16) {
+               nv_wo32(chan, i + 0, 0x10700ff9);
+               nv_wo32(chan, i + 1, 0x0436086c);
+               nv_wo32(chan, i + 2, 0x000c001b);
+       }
+       for (i = 0x274c; i < 0x275c; i += 4)
+               nv_wo32(chan, i, 0x0000ffff);
+       nv_wo32(chan, 0x2ae0, 0x3f800000);
+       nv_wo32(chan, 0x2e9c, 0x3f800000);
+       nv_wo32(chan, 0x2eb0, 0x3f800000);
+       nv_wo32(chan, 0x2edc, 0x40000000);
+       nv_wo32(chan, 0x2ee0, 0x3f800000);
+       nv_wo32(chan, 0x2ee4, 0x3f000000);
+       nv_wo32(chan, 0x2eec, 0x40000000);
+       nv_wo32(chan, 0x2ef0, 0x3f800000);
+       nv_wo32(chan, 0x2ef8, 0xbf800000);
+       nv_wo32(chan, 0x2f00, 0xbf800000);
+       return 0;
+}
+
+static struct nvkm_oclass
+nv34_gr_cclass = {
+       .handle = NV_ENGCTX(GR, 0x34),
+       .ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = nv34_gr_context_ctor,
+               .dtor = _nvkm_gr_context_dtor,
+               .init = nv20_gr_context_init,
+               .fini = nv20_gr_context_fini,
+               .rd32 = _nvkm_gr_context_rd32,
+               .wr32 = _nvkm_gr_context_wr32,
+       },
+};
+
+/*******************************************************************************
+ * PGRAPH engine/subdev functions
+ ******************************************************************************/
+
+static int
+nv34_gr_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+            struct nvkm_oclass *oclass, void *data, u32 size,
+            struct nvkm_object **pobject)
+{
+       struct nv20_gr_priv *priv;
+       int ret;
+
+       ret = nvkm_gr_create(parent, engine, oclass, true, &priv);
+       *pobject = nv_object(priv);
+       if (ret)
+               return ret;
+
+       ret = nvkm_gpuobj_new(nv_object(priv), NULL, 32 * 4, 16,
+                             NVOBJ_FLAG_ZERO_ALLOC, &priv->ctxtab);
+       if (ret)
+               return ret;
+
+       nv_subdev(priv)->unit = 0x00001000;
+       nv_subdev(priv)->intr = nv20_gr_intr;
+       nv_engine(priv)->cclass = &nv34_gr_cclass;
+       nv_engine(priv)->sclass = nv34_gr_sclass;
+       nv_engine(priv)->tile_prog = nv20_gr_tile_prog;
+       return 0;
+}
+
+struct nvkm_oclass
+nv34_gr_oclass = {
+       .handle = NV_ENGINE(GR, 0x34),
+       .ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = nv34_gr_ctor,
+               .dtor = nv20_gr_dtor,
+               .init = nv30_gr_init,
+               .fini = _nvkm_gr_fini,
+       },
+};
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/gr/nv35.c b/drivers/gpu/drm/nouveau/nvkm/engine/gr/nv35.c
new file mode 100644 (file)
index 0000000..707625f
--- /dev/null
@@ -0,0 +1,159 @@
+#include "nv20.h"
+#include "regs.h"
+
+#include <engine/fifo.h>
+
+/*******************************************************************************
+ * Graphics object classes
+ ******************************************************************************/
+
+static struct nvkm_oclass
+nv35_gr_sclass[] = {
+       { 0x0012, &nv04_gr_ofuncs, NULL }, /* beta1 */
+       { 0x0019, &nv04_gr_ofuncs, NULL }, /* clip */
+       { 0x0030, &nv04_gr_ofuncs, NULL }, /* null */
+       { 0x0039, &nv04_gr_ofuncs, NULL }, /* m2mf */
+       { 0x0043, &nv04_gr_ofuncs, NULL }, /* rop */
+       { 0x0044, &nv04_gr_ofuncs, NULL }, /* patt */
+       { 0x004a, &nv04_gr_ofuncs, NULL }, /* gdi */
+       { 0x0062, &nv04_gr_ofuncs, NULL }, /* surf2d */
+       { 0x0072, &nv04_gr_ofuncs, NULL }, /* beta4 */
+       { 0x0089, &nv04_gr_ofuncs, NULL }, /* sifm */
+       { 0x008a, &nv04_gr_ofuncs, NULL }, /* ifc */
+       { 0x009f, &nv04_gr_ofuncs, NULL }, /* imageblit */
+       { 0x0362, &nv04_gr_ofuncs, NULL }, /* surf2d (nv30) */
+       { 0x0389, &nv04_gr_ofuncs, NULL }, /* sifm (nv30) */
+       { 0x038a, &nv04_gr_ofuncs, NULL }, /* ifc (nv30) */
+       { 0x039e, &nv04_gr_ofuncs, NULL }, /* swzsurf (nv30) */
+       { 0x0497, &nv04_gr_ofuncs, NULL }, /* rankine */
+       {},
+};
+
+/*******************************************************************************
+ * PGRAPH context
+ ******************************************************************************/
+
+static int
+nv35_gr_context_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+                    struct nvkm_oclass *oclass, void *data, u32 size,
+                    struct nvkm_object **pobject)
+{
+       struct nv20_gr_chan *chan;
+       int ret, i;
+
+       ret = nvkm_gr_context_create(parent, engine, oclass, NULL, 0x577c,
+                                    16, NVOBJ_FLAG_ZERO_ALLOC, &chan);
+       *pobject = nv_object(chan);
+       if (ret)
+               return ret;
+
+       chan->chid = nvkm_fifo_chan(parent)->chid;
+
+       nv_wo32(chan, 0x0028, 0x00000001 | (chan->chid << 24));
+       nv_wo32(chan, 0x040c, 0x00000101);
+       nv_wo32(chan, 0x0420, 0x00000111);
+       nv_wo32(chan, 0x0424, 0x00000060);
+       nv_wo32(chan, 0x0440, 0x00000080);
+       nv_wo32(chan, 0x0444, 0xffff0000);
+       nv_wo32(chan, 0x0448, 0x00000001);
+       nv_wo32(chan, 0x045c, 0x44400000);
+       nv_wo32(chan, 0x0488, 0xffff0000);
+       for (i = 0x04dc; i < 0x04e4; i += 4)
+               nv_wo32(chan, i, 0x0fff0000);
+       nv_wo32(chan, 0x04e8, 0x00011100);
+       for (i = 0x0504; i < 0x0544; i += 4)
+               nv_wo32(chan, i, 0x07ff0000);
+       nv_wo32(chan, 0x054c, 0x4b7fffff);
+       nv_wo32(chan, 0x0588, 0x00000080);
+       nv_wo32(chan, 0x058c, 0x30201000);
+       nv_wo32(chan, 0x0590, 0x70605040);
+       nv_wo32(chan, 0x0594, 0xb8a89888);
+       nv_wo32(chan, 0x0598, 0xf8e8d8c8);
+       nv_wo32(chan, 0x05ac, 0xb0000000);
+       for (i = 0x0604; i < 0x0644; i += 4)
+               nv_wo32(chan, i, 0x00010588);
+       for (i = 0x0644; i < 0x0684; i += 4)
+               nv_wo32(chan, i, 0x00030303);
+       for (i = 0x06c4; i < 0x0704; i += 4)
+               nv_wo32(chan, i, 0x0008aae4);
+       for (i = 0x0704; i < 0x0744; i += 4)
+               nv_wo32(chan, i, 0x01012000);
+       for (i = 0x0744; i < 0x0784; i += 4)
+               nv_wo32(chan, i, 0x00080008);
+       nv_wo32(chan, 0x0860, 0x00040000);
+       nv_wo32(chan, 0x0864, 0x00010000);
+       for (i = 0x0868; i < 0x0878; i += 4)
+               nv_wo32(chan, i, 0x00040004);
+       for (i = 0x1f1c; i <= 0x308c ; i += 16) {
+               nv_wo32(chan, i + 0, 0x10700ff9);
+               nv_wo32(chan, i + 4, 0x0436086c);
+               nv_wo32(chan, i + 8, 0x000c001b);
+       }
+       for (i = 0x30bc; i < 0x30cc; i += 4)
+               nv_wo32(chan, i, 0x0000ffff);
+       nv_wo32(chan, 0x3450, 0x3f800000);
+       nv_wo32(chan, 0x380c, 0x3f800000);
+       nv_wo32(chan, 0x3820, 0x3f800000);
+       nv_wo32(chan, 0x384c, 0x40000000);
+       nv_wo32(chan, 0x3850, 0x3f800000);
+       nv_wo32(chan, 0x3854, 0x3f000000);
+       nv_wo32(chan, 0x385c, 0x40000000);
+       nv_wo32(chan, 0x3860, 0x3f800000);
+       nv_wo32(chan, 0x3868, 0xbf800000);
+       nv_wo32(chan, 0x3870, 0xbf800000);
+       return 0;
+}
+
+static struct nvkm_oclass
+nv35_gr_cclass = {
+       .handle = NV_ENGCTX(GR, 0x35),
+       .ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = nv35_gr_context_ctor,
+               .dtor = _nvkm_gr_context_dtor,
+               .init = nv20_gr_context_init,
+               .fini = nv20_gr_context_fini,
+               .rd32 = _nvkm_gr_context_rd32,
+               .wr32 = _nvkm_gr_context_wr32,
+       },
+};
+
+/*******************************************************************************
+ * PGRAPH engine/subdev functions
+ ******************************************************************************/
+
+static int
+nv35_gr_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+            struct nvkm_oclass *oclass, void *data, u32 size,
+            struct nvkm_object **pobject)
+{
+       struct nv20_gr_priv *priv;
+       int ret;
+
+       ret = nvkm_gr_create(parent, engine, oclass, true, &priv);
+       *pobject = nv_object(priv);
+       if (ret)
+               return ret;
+
+       ret = nvkm_gpuobj_new(nv_object(priv), NULL, 32 * 4, 16,
+                             NVOBJ_FLAG_ZERO_ALLOC, &priv->ctxtab);
+       if (ret)
+               return ret;
+
+       nv_subdev(priv)->unit = 0x00001000;
+       nv_subdev(priv)->intr = nv20_gr_intr;
+       nv_engine(priv)->cclass = &nv35_gr_cclass;
+       nv_engine(priv)->sclass = nv35_gr_sclass;
+       nv_engine(priv)->tile_prog = nv20_gr_tile_prog;
+       return 0;
+}
+
+struct nvkm_oclass
+nv35_gr_oclass = {
+       .handle = NV_ENGINE(GR, 0x35),
+       .ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = nv35_gr_ctor,
+               .dtor = nv20_gr_dtor,
+               .init = nv30_gr_init,
+               .fini = _nvkm_gr_fini,
+       },
+};
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/gr/nv40.c b/drivers/gpu/drm/nouveau/nvkm/engine/gr/nv40.c
new file mode 100644 (file)
index 0000000..7e19379
--- /dev/null
@@ -0,0 +1,527 @@
+/*
+ * Copyright 2012 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 "nv40.h"
+#include "regs.h"
+
+#include <core/client.h>
+#include <core/handle.h>
+#include <subdev/fb.h>
+#include <subdev/timer.h>
+#include <engine/fifo.h>
+
+struct nv40_gr_priv {
+       struct nvkm_gr base;
+       u32 size;
+};
+
+struct nv40_gr_chan {
+       struct nvkm_gr_chan base;
+};
+
+static u64
+nv40_gr_units(struct nvkm_gr *gr)
+{
+       struct nv40_gr_priv *priv = (void *)gr;
+
+       return nv_rd32(priv, 0x1540);
+}
+
+/*******************************************************************************
+ * Graphics object classes
+ ******************************************************************************/
+
+static int
+nv40_gr_object_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+                   struct nvkm_oclass *oclass, void *data, u32 size,
+                   struct nvkm_object **pobject)
+{
+       struct nvkm_gpuobj *obj;
+       int ret;
+
+       ret = nvkm_gpuobj_create(parent, engine, oclass, 0, parent,
+                                20, 16, 0, &obj);
+       *pobject = nv_object(obj);
+       if (ret)
+               return ret;
+
+       nv_wo32(obj, 0x00, nv_mclass(obj));
+       nv_wo32(obj, 0x04, 0x00000000);
+       nv_wo32(obj, 0x08, 0x00000000);
+#ifdef __BIG_ENDIAN
+       nv_mo32(obj, 0x08, 0x01000000, 0x01000000);
+#endif
+       nv_wo32(obj, 0x0c, 0x00000000);
+       nv_wo32(obj, 0x10, 0x00000000);
+       return 0;
+}
+
+static struct nvkm_ofuncs
+nv40_gr_ofuncs = {
+       .ctor = nv40_gr_object_ctor,
+       .dtor = _nvkm_gpuobj_dtor,
+       .init = _nvkm_gpuobj_init,
+       .fini = _nvkm_gpuobj_fini,
+       .rd32 = _nvkm_gpuobj_rd32,
+       .wr32 = _nvkm_gpuobj_wr32,
+};
+
+static struct nvkm_oclass
+nv40_gr_sclass[] = {
+       { 0x0012, &nv40_gr_ofuncs, NULL }, /* beta1 */
+       { 0x0019, &nv40_gr_ofuncs, NULL }, /* clip */
+       { 0x0030, &nv40_gr_ofuncs, NULL }, /* null */
+       { 0x0039, &nv40_gr_ofuncs, NULL }, /* m2mf */
+       { 0x0043, &nv40_gr_ofuncs, NULL }, /* rop */
+       { 0x0044, &nv40_gr_ofuncs, NULL }, /* patt */
+       { 0x004a, &nv40_gr_ofuncs, NULL }, /* gdi */
+       { 0x0062, &nv40_gr_ofuncs, NULL }, /* surf2d */
+       { 0x0072, &nv40_gr_ofuncs, NULL }, /* beta4 */
+       { 0x0089, &nv40_gr_ofuncs, NULL }, /* sifm */
+       { 0x008a, &nv40_gr_ofuncs, NULL }, /* ifc */
+       { 0x009f, &nv40_gr_ofuncs, NULL }, /* imageblit */
+       { 0x3062, &nv40_gr_ofuncs, NULL }, /* surf2d (nv40) */
+       { 0x3089, &nv40_gr_ofuncs, NULL }, /* sifm (nv40) */
+       { 0x309e, &nv40_gr_ofuncs, NULL }, /* swzsurf (nv40) */
+       { 0x4097, &nv40_gr_ofuncs, NULL }, /* curie */
+       {},
+};
+
+static struct nvkm_oclass
+nv44_gr_sclass[] = {
+       { 0x0012, &nv40_gr_ofuncs, NULL }, /* beta1 */
+       { 0x0019, &nv40_gr_ofuncs, NULL }, /* clip */
+       { 0x0030, &nv40_gr_ofuncs, NULL }, /* null */
+       { 0x0039, &nv40_gr_ofuncs, NULL }, /* m2mf */
+       { 0x0043, &nv40_gr_ofuncs, NULL }, /* rop */
+       { 0x0044, &nv40_gr_ofuncs, NULL }, /* patt */
+       { 0x004a, &nv40_gr_ofuncs, NULL }, /* gdi */
+       { 0x0062, &nv40_gr_ofuncs, NULL }, /* surf2d */
+       { 0x0072, &nv40_gr_ofuncs, NULL }, /* beta4 */
+       { 0x0089, &nv40_gr_ofuncs, NULL }, /* sifm */
+       { 0x008a, &nv40_gr_ofuncs, NULL }, /* ifc */
+       { 0x009f, &nv40_gr_ofuncs, NULL }, /* imageblit */
+       { 0x3062, &nv40_gr_ofuncs, NULL }, /* surf2d (nv40) */
+       { 0x3089, &nv40_gr_ofuncs, NULL }, /* sifm (nv40) */
+       { 0x309e, &nv40_gr_ofuncs, NULL }, /* swzsurf (nv40) */
+       { 0x4497, &nv40_gr_ofuncs, NULL }, /* curie */
+       {},
+};
+
+/*******************************************************************************
+ * PGRAPH context
+ ******************************************************************************/
+
+static int
+nv40_gr_context_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+                    struct nvkm_oclass *oclass, void *data, u32 size,
+                    struct nvkm_object **pobject)
+{
+       struct nv40_gr_priv *priv = (void *)engine;
+       struct nv40_gr_chan *chan;
+       int ret;
+
+       ret = nvkm_gr_context_create(parent, engine, oclass, NULL, priv->size,
+                                    16, NVOBJ_FLAG_ZERO_ALLOC, &chan);
+       *pobject = nv_object(chan);
+       if (ret)
+               return ret;
+
+       nv40_grctx_fill(nv_device(priv), nv_gpuobj(chan));
+       nv_wo32(chan, 0x00000, nv_gpuobj(chan)->addr >> 4);
+       return 0;
+}
+
+static int
+nv40_gr_context_fini(struct nvkm_object *object, bool suspend)
+{
+       struct nv40_gr_priv *priv = (void *)object->engine;
+       struct nv40_gr_chan *chan = (void *)object;
+       u32 inst = 0x01000000 | nv_gpuobj(chan)->addr >> 4;
+       int ret = 0;
+
+       nv_mask(priv, 0x400720, 0x00000001, 0x00000000);
+
+       if (nv_rd32(priv, 0x40032c) == inst) {
+               if (suspend) {
+                       nv_wr32(priv, 0x400720, 0x00000000);
+                       nv_wr32(priv, 0x400784, inst);
+                       nv_mask(priv, 0x400310, 0x00000020, 0x00000020);
+                       nv_mask(priv, 0x400304, 0x00000001, 0x00000001);
+                       if (!nv_wait(priv, 0x400300, 0x00000001, 0x00000000)) {
+                               u32 insn = nv_rd32(priv, 0x400308);
+                               nv_warn(priv, "ctxprog timeout 0x%08x\n", insn);
+                               ret = -EBUSY;
+                       }
+               }
+
+               nv_mask(priv, 0x40032c, 0x01000000, 0x00000000);
+       }
+
+       if (nv_rd32(priv, 0x400330) == inst)
+               nv_mask(priv, 0x400330, 0x01000000, 0x00000000);
+
+       nv_mask(priv, 0x400720, 0x00000001, 0x00000001);
+       return ret;
+}
+
+static struct nvkm_oclass
+nv40_gr_cclass = {
+       .handle = NV_ENGCTX(GR, 0x40),
+       .ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = nv40_gr_context_ctor,
+               .dtor = _nvkm_gr_context_dtor,
+               .init = _nvkm_gr_context_init,
+               .fini = nv40_gr_context_fini,
+               .rd32 = _nvkm_gr_context_rd32,
+               .wr32 = _nvkm_gr_context_wr32,
+       },
+};
+
+/*******************************************************************************
+ * PGRAPH engine/subdev functions
+ ******************************************************************************/
+
+static void
+nv40_gr_tile_prog(struct nvkm_engine *engine, int i)
+{
+       struct nvkm_fb_tile *tile = &nvkm_fb(engine)->tile.region[i];
+       struct nvkm_fifo *pfifo = nvkm_fifo(engine);
+       struct nv40_gr_priv *priv = (void *)engine;
+       unsigned long flags;
+
+       pfifo->pause(pfifo, &flags);
+       nv04_gr_idle(priv);
+
+       switch (nv_device(priv)->chipset) {
+       case 0x40:
+       case 0x41:
+       case 0x42:
+       case 0x43:
+       case 0x45:
+       case 0x4e:
+               nv_wr32(priv, NV20_PGRAPH_TSIZE(i), tile->pitch);
+               nv_wr32(priv, NV20_PGRAPH_TLIMIT(i), tile->limit);
+               nv_wr32(priv, NV20_PGRAPH_TILE(i), tile->addr);
+               nv_wr32(priv, NV40_PGRAPH_TSIZE1(i), tile->pitch);
+               nv_wr32(priv, NV40_PGRAPH_TLIMIT1(i), tile->limit);
+               nv_wr32(priv, NV40_PGRAPH_TILE1(i), tile->addr);
+               switch (nv_device(priv)->chipset) {
+               case 0x40:
+               case 0x45:
+                       nv_wr32(priv, NV20_PGRAPH_ZCOMP(i), tile->zcomp);
+                       nv_wr32(priv, NV40_PGRAPH_ZCOMP1(i), tile->zcomp);
+                       break;
+               case 0x41:
+               case 0x42:
+               case 0x43:
+                       nv_wr32(priv, NV41_PGRAPH_ZCOMP0(i), tile->zcomp);
+                       nv_wr32(priv, NV41_PGRAPH_ZCOMP1(i), tile->zcomp);
+                       break;
+               default:
+                       break;
+               }
+               break;
+       case 0x44:
+       case 0x4a:
+               nv_wr32(priv, NV20_PGRAPH_TSIZE(i), tile->pitch);
+               nv_wr32(priv, NV20_PGRAPH_TLIMIT(i), tile->limit);
+               nv_wr32(priv, NV20_PGRAPH_TILE(i), tile->addr);
+               break;
+       case 0x46:
+       case 0x4c:
+       case 0x47:
+       case 0x49:
+       case 0x4b:
+       case 0x63:
+       case 0x67:
+       case 0x68:
+               nv_wr32(priv, NV47_PGRAPH_TSIZE(i), tile->pitch);
+               nv_wr32(priv, NV47_PGRAPH_TLIMIT(i), tile->limit);
+               nv_wr32(priv, NV47_PGRAPH_TILE(i), tile->addr);
+               nv_wr32(priv, NV40_PGRAPH_TSIZE1(i), tile->pitch);
+               nv_wr32(priv, NV40_PGRAPH_TLIMIT1(i), tile->limit);
+               nv_wr32(priv, NV40_PGRAPH_TILE1(i), tile->addr);
+               switch (nv_device(priv)->chipset) {
+               case 0x47:
+               case 0x49:
+               case 0x4b:
+                       nv_wr32(priv, NV47_PGRAPH_ZCOMP0(i), tile->zcomp);
+                       nv_wr32(priv, NV47_PGRAPH_ZCOMP1(i), tile->zcomp);
+                       break;
+               default:
+                       break;
+               }
+               break;
+       default:
+               break;
+       }
+
+       pfifo->start(pfifo, &flags);
+}
+
+static void
+nv40_gr_intr(struct nvkm_subdev *subdev)
+{
+       struct nvkm_fifo *pfifo = nvkm_fifo(subdev);
+       struct nvkm_engine *engine = nv_engine(subdev);
+       struct nvkm_object *engctx;
+       struct nvkm_handle *handle = NULL;
+       struct nv40_gr_priv *priv = (void *)subdev;
+       u32 stat = nv_rd32(priv, NV03_PGRAPH_INTR);
+       u32 nsource = nv_rd32(priv, NV03_PGRAPH_NSOURCE);
+       u32 nstatus = nv_rd32(priv, NV03_PGRAPH_NSTATUS);
+       u32 inst = nv_rd32(priv, 0x40032c) & 0x000fffff;
+       u32 addr = nv_rd32(priv, NV04_PGRAPH_TRAPPED_ADDR);
+       u32 subc = (addr & 0x00070000) >> 16;
+       u32 mthd = (addr & 0x00001ffc);
+       u32 data = nv_rd32(priv, NV04_PGRAPH_TRAPPED_DATA);
+       u32 class = nv_rd32(priv, 0x400160 + subc * 4) & 0xffff;
+       u32 show = stat;
+       int chid;
+
+       engctx = nvkm_engctx_get(engine, inst);
+       chid   = pfifo->chid(pfifo, engctx);
+
+       if (stat & NV_PGRAPH_INTR_ERROR) {
+               if (nsource & NV03_PGRAPH_NSOURCE_ILLEGAL_MTHD) {
+                       handle = nvkm_handle_get_class(engctx, class);
+                       if (handle && !nv_call(handle->object, mthd, data))
+                               show &= ~NV_PGRAPH_INTR_ERROR;
+                       nvkm_handle_put(handle);
+               }
+
+               if (nsource & NV03_PGRAPH_NSOURCE_DMA_VTX_PROTECTION) {
+                       nv_mask(priv, 0x402000, 0, 0);
+               }
+       }
+
+       nv_wr32(priv, NV03_PGRAPH_INTR, stat);
+       nv_wr32(priv, NV04_PGRAPH_FIFO, 0x00000001);
+
+       if (show) {
+               nv_error(priv, "%s", "");
+               nvkm_bitfield_print(nv10_gr_intr_name, show);
+               pr_cont(" nsource:");
+               nvkm_bitfield_print(nv04_gr_nsource, nsource);
+               pr_cont(" nstatus:");
+               nvkm_bitfield_print(nv10_gr_nstatus, nstatus);
+               pr_cont("\n");
+               nv_error(priv,
+                        "ch %d [0x%08x %s] subc %d class 0x%04x mthd 0x%04x data 0x%08x\n",
+                        chid, inst << 4, nvkm_client_name(engctx), subc,
+                        class, mthd, data);
+       }
+
+       nvkm_engctx_put(engctx);
+}
+
+static int
+nv40_gr_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+            struct nvkm_oclass *oclass, void *data, u32 size,
+            struct nvkm_object **pobject)
+{
+       struct nv40_gr_priv *priv;
+       int ret;
+
+       ret = nvkm_gr_create(parent, engine, oclass, true, &priv);
+       *pobject = nv_object(priv);
+       if (ret)
+               return ret;
+
+       nv_subdev(priv)->unit = 0x00001000;
+       nv_subdev(priv)->intr = nv40_gr_intr;
+       nv_engine(priv)->cclass = &nv40_gr_cclass;
+       if (nv44_gr_class(priv))
+               nv_engine(priv)->sclass = nv44_gr_sclass;
+       else
+               nv_engine(priv)->sclass = nv40_gr_sclass;
+       nv_engine(priv)->tile_prog = nv40_gr_tile_prog;
+
+       priv->base.units = nv40_gr_units;
+       return 0;
+}
+
+static int
+nv40_gr_init(struct nvkm_object *object)
+{
+       struct nvkm_engine *engine = nv_engine(object);
+       struct nvkm_fb *pfb = nvkm_fb(object);
+       struct nv40_gr_priv *priv = (void *)engine;
+       int ret, i, j;
+       u32 vramsz;
+
+       ret = nvkm_gr_init(&priv->base);
+       if (ret)
+               return ret;
+
+       /* generate and upload context program */
+       ret = nv40_grctx_init(nv_device(priv), &priv->size);
+       if (ret)
+               return ret;
+
+       /* No context present currently */
+       nv_wr32(priv, NV40_PGRAPH_CTXCTL_CUR, 0x00000000);
+
+       nv_wr32(priv, NV03_PGRAPH_INTR   , 0xFFFFFFFF);
+       nv_wr32(priv, NV40_PGRAPH_INTR_EN, 0xFFFFFFFF);
+
+       nv_wr32(priv, NV04_PGRAPH_DEBUG_0, 0xFFFFFFFF);
+       nv_wr32(priv, NV04_PGRAPH_DEBUG_0, 0x00000000);
+       nv_wr32(priv, NV04_PGRAPH_DEBUG_1, 0x401287c0);
+       nv_wr32(priv, NV04_PGRAPH_DEBUG_3, 0xe0de8055);
+       nv_wr32(priv, NV10_PGRAPH_DEBUG_4, 0x00008000);
+       nv_wr32(priv, NV04_PGRAPH_LIMIT_VIOL_PIX, 0x00be3c5f);
+
+       nv_wr32(priv, NV10_PGRAPH_CTX_CONTROL, 0x10010100);
+       nv_wr32(priv, NV10_PGRAPH_STATE      , 0xFFFFFFFF);
+
+       j = nv_rd32(priv, 0x1540) & 0xff;
+       if (j) {
+               for (i = 0; !(j & 1); j >>= 1, i++)
+                       ;
+               nv_wr32(priv, 0x405000, i);
+       }
+
+       if (nv_device(priv)->chipset == 0x40) {
+               nv_wr32(priv, 0x4009b0, 0x83280fff);
+               nv_wr32(priv, 0x4009b4, 0x000000a0);
+       } else {
+               nv_wr32(priv, 0x400820, 0x83280eff);
+               nv_wr32(priv, 0x400824, 0x000000a0);
+       }
+
+       switch (nv_device(priv)->chipset) {
+       case 0x40:
+       case 0x45:
+               nv_wr32(priv, 0x4009b8, 0x0078e366);
+               nv_wr32(priv, 0x4009bc, 0x0000014c);
+               break;
+       case 0x41:
+       case 0x42: /* pciid also 0x00Cx */
+       /* case 0x0120: XXX (pciid) */
+               nv_wr32(priv, 0x400828, 0x007596ff);
+               nv_wr32(priv, 0x40082c, 0x00000108);
+               break;
+       case 0x43:
+               nv_wr32(priv, 0x400828, 0x0072cb77);
+               nv_wr32(priv, 0x40082c, 0x00000108);
+               break;
+       case 0x44:
+       case 0x46: /* G72 */
+       case 0x4a:
+       case 0x4c: /* G7x-based C51 */
+       case 0x4e:
+               nv_wr32(priv, 0x400860, 0);
+               nv_wr32(priv, 0x400864, 0);
+               break;
+       case 0x47: /* G70 */
+       case 0x49: /* G71 */
+       case 0x4b: /* G73 */
+               nv_wr32(priv, 0x400828, 0x07830610);
+               nv_wr32(priv, 0x40082c, 0x0000016A);
+               break;
+       default:
+               break;
+       }
+
+       nv_wr32(priv, 0x400b38, 0x2ffff800);
+       nv_wr32(priv, 0x400b3c, 0x00006000);
+
+       /* Tiling related stuff. */
+       switch (nv_device(priv)->chipset) {
+       case 0x44:
+       case 0x4a:
+               nv_wr32(priv, 0x400bc4, 0x1003d888);
+               nv_wr32(priv, 0x400bbc, 0xb7a7b500);
+               break;
+       case 0x46:
+               nv_wr32(priv, 0x400bc4, 0x0000e024);
+               nv_wr32(priv, 0x400bbc, 0xb7a7b520);
+               break;
+       case 0x4c:
+       case 0x4e:
+       case 0x67:
+               nv_wr32(priv, 0x400bc4, 0x1003d888);
+               nv_wr32(priv, 0x400bbc, 0xb7a7b540);
+               break;
+       default:
+               break;
+       }
+
+       /* Turn all the tiling regions off. */
+       for (i = 0; i < pfb->tile.regions; i++)
+               engine->tile_prog(engine, i);
+
+       /* begin RAM config */
+       vramsz = nv_device_resource_len(nv_device(priv), 0) - 1;
+       switch (nv_device(priv)->chipset) {
+       case 0x40:
+               nv_wr32(priv, 0x4009A4, nv_rd32(priv, 0x100200));
+               nv_wr32(priv, 0x4009A8, nv_rd32(priv, 0x100204));
+               nv_wr32(priv, 0x4069A4, nv_rd32(priv, 0x100200));
+               nv_wr32(priv, 0x4069A8, nv_rd32(priv, 0x100204));
+               nv_wr32(priv, 0x400820, 0);
+               nv_wr32(priv, 0x400824, 0);
+               nv_wr32(priv, 0x400864, vramsz);
+               nv_wr32(priv, 0x400868, vramsz);
+               break;
+       default:
+               switch (nv_device(priv)->chipset) {
+               case 0x41:
+               case 0x42:
+               case 0x43:
+               case 0x45:
+               case 0x4e:
+               case 0x44:
+               case 0x4a:
+                       nv_wr32(priv, 0x4009F0, nv_rd32(priv, 0x100200));
+                       nv_wr32(priv, 0x4009F4, nv_rd32(priv, 0x100204));
+                       break;
+               default:
+                       nv_wr32(priv, 0x400DF0, nv_rd32(priv, 0x100200));
+                       nv_wr32(priv, 0x400DF4, nv_rd32(priv, 0x100204));
+                       break;
+               }
+               nv_wr32(priv, 0x4069F0, nv_rd32(priv, 0x100200));
+               nv_wr32(priv, 0x4069F4, nv_rd32(priv, 0x100204));
+               nv_wr32(priv, 0x400840, 0);
+               nv_wr32(priv, 0x400844, 0);
+               nv_wr32(priv, 0x4008A0, vramsz);
+               nv_wr32(priv, 0x4008A4, vramsz);
+               break;
+       }
+
+       return 0;
+}
+
+struct nvkm_oclass
+nv40_gr_oclass = {
+       .handle = NV_ENGINE(GR, 0x40),
+       .ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = nv40_gr_ctor,
+               .dtor = _nvkm_gr_dtor,
+               .init = nv40_gr_init,
+               .fini = _nvkm_gr_fini,
+       },
+};
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/gr/nv40.h b/drivers/gpu/drm/nouveau/nvkm/engine/gr/nv40.h
new file mode 100644 (file)
index 0000000..d852bd6
--- /dev/null
@@ -0,0 +1,24 @@
+#ifndef __NV40_GR_H__
+#define __NV40_GR_H__
+#include <engine/gr.h>
+
+#include <core/device.h>
+struct nvkm_gpuobj;
+
+/* returns 1 if device is one of the nv4x using the 0x4497 object class,
+ * helpful to determine a number of other hardware features
+ */
+static inline int
+nv44_gr_class(void *priv)
+{
+       struct nvkm_device *device = nv_device(priv);
+
+       if ((device->chipset & 0xf0) == 0x60)
+               return 1;
+
+       return !(0x0baf & (1 << (device->chipset & 0x0f)));
+}
+
+int  nv40_grctx_init(struct nvkm_device *, u32 *size);
+void nv40_grctx_fill(struct nvkm_device *, struct nvkm_gpuobj *);
+#endif
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/gr/nv50.c b/drivers/gpu/drm/nouveau/nvkm/engine/gr/nv50.c
new file mode 100644 (file)
index 0000000..270d7cd
--- /dev/null
@@ -0,0 +1,999 @@
+/*
+ * Copyright 2012 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 "nv50.h"
+
+#include <core/client.h>
+#include <core/device.h>
+#include <core/handle.h>
+#include <engine/fifo.h>
+#include <subdev/timer.h>
+
+struct nv50_gr_priv {
+       struct nvkm_gr base;
+       spinlock_t lock;
+       u32 size;
+};
+
+struct nv50_gr_chan {
+       struct nvkm_gr_chan base;
+};
+
+static u64
+nv50_gr_units(struct nvkm_gr *gr)
+{
+       struct nv50_gr_priv *priv = (void *)gr;
+
+       return nv_rd32(priv, 0x1540);
+}
+
+/*******************************************************************************
+ * Graphics object classes
+ ******************************************************************************/
+
+static int
+nv50_gr_object_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+                   struct nvkm_oclass *oclass, void *data, u32 size,
+                   struct nvkm_object **pobject)
+{
+       struct nvkm_gpuobj *obj;
+       int ret;
+
+       ret = nvkm_gpuobj_create(parent, engine, oclass, 0, parent,
+                                16, 16, 0, &obj);
+       *pobject = nv_object(obj);
+       if (ret)
+               return ret;
+
+       nv_wo32(obj, 0x00, nv_mclass(obj));
+       nv_wo32(obj, 0x04, 0x00000000);
+       nv_wo32(obj, 0x08, 0x00000000);
+       nv_wo32(obj, 0x0c, 0x00000000);
+       return 0;
+}
+
+static struct nvkm_ofuncs
+nv50_gr_ofuncs = {
+       .ctor = nv50_gr_object_ctor,
+       .dtor = _nvkm_gpuobj_dtor,
+       .init = _nvkm_gpuobj_init,
+       .fini = _nvkm_gpuobj_fini,
+       .rd32 = _nvkm_gpuobj_rd32,
+       .wr32 = _nvkm_gpuobj_wr32,
+};
+
+static struct nvkm_oclass
+nv50_gr_sclass[] = {
+       { 0x0030, &nv50_gr_ofuncs },
+       { 0x502d, &nv50_gr_ofuncs },
+       { 0x5039, &nv50_gr_ofuncs },
+       { 0x5097, &nv50_gr_ofuncs },
+       { 0x50c0, &nv50_gr_ofuncs },
+       {}
+};
+
+static struct nvkm_oclass
+g84_gr_sclass[] = {
+       { 0x0030, &nv50_gr_ofuncs },
+       { 0x502d, &nv50_gr_ofuncs },
+       { 0x5039, &nv50_gr_ofuncs },
+       { 0x50c0, &nv50_gr_ofuncs },
+       { 0x8297, &nv50_gr_ofuncs },
+       {}
+};
+
+static struct nvkm_oclass
+gt200_gr_sclass[] = {
+       { 0x0030, &nv50_gr_ofuncs },
+       { 0x502d, &nv50_gr_ofuncs },
+       { 0x5039, &nv50_gr_ofuncs },
+       { 0x50c0, &nv50_gr_ofuncs },
+       { 0x8397, &nv50_gr_ofuncs },
+       {}
+};
+
+static struct nvkm_oclass
+gt215_gr_sclass[] = {
+       { 0x0030, &nv50_gr_ofuncs },
+       { 0x502d, &nv50_gr_ofuncs },
+       { 0x5039, &nv50_gr_ofuncs },
+       { 0x50c0, &nv50_gr_ofuncs },
+       { 0x8597, &nv50_gr_ofuncs },
+       { 0x85c0, &nv50_gr_ofuncs },
+       {}
+};
+
+static struct nvkm_oclass
+mcp89_gr_sclass[] = {
+       { 0x0030, &nv50_gr_ofuncs },
+       { 0x502d, &nv50_gr_ofuncs },
+       { 0x5039, &nv50_gr_ofuncs },
+       { 0x50c0, &nv50_gr_ofuncs },
+       { 0x85c0, &nv50_gr_ofuncs },
+       { 0x8697, &nv50_gr_ofuncs },
+       {}
+};
+
+/*******************************************************************************
+ * PGRAPH context
+ ******************************************************************************/
+
+static int
+nv50_gr_context_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+                    struct nvkm_oclass *oclass, void *data, u32 size,
+                    struct nvkm_object **pobject)
+{
+       struct nv50_gr_priv *priv = (void *)engine;
+       struct nv50_gr_chan *chan;
+       int ret;
+
+       ret = nvkm_gr_context_create(parent, engine, oclass, NULL, priv->size,
+                                    0, NVOBJ_FLAG_ZERO_ALLOC, &chan);
+       *pobject = nv_object(chan);
+       if (ret)
+               return ret;
+
+       nv50_grctx_fill(nv_device(priv), nv_gpuobj(chan));
+       return 0;
+}
+
+static struct nvkm_oclass
+nv50_gr_cclass = {
+       .handle = NV_ENGCTX(GR, 0x50),
+       .ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = nv50_gr_context_ctor,
+               .dtor = _nvkm_gr_context_dtor,
+               .init = _nvkm_gr_context_init,
+               .fini = _nvkm_gr_context_fini,
+               .rd32 = _nvkm_gr_context_rd32,
+               .wr32 = _nvkm_gr_context_wr32,
+       },
+};
+
+/*******************************************************************************
+ * PGRAPH engine/subdev functions
+ ******************************************************************************/
+
+static const struct nvkm_bitfield nv50_pgr_status[] = {
+       { 0x00000001, "BUSY" }, /* set when any bit is set */
+       { 0x00000002, "DISPATCH" },
+       { 0x00000004, "UNK2" },
+       { 0x00000008, "UNK3" },
+       { 0x00000010, "UNK4" },
+       { 0x00000020, "UNK5" },
+       { 0x00000040, "M2MF" },
+       { 0x00000080, "UNK7" },
+       { 0x00000100, "CTXPROG" },
+       { 0x00000200, "VFETCH" },
+       { 0x00000400, "CCACHE_PREGEOM" },
+       { 0x00000800, "STRMOUT_VATTR_POSTGEOM" },
+       { 0x00001000, "VCLIP" },
+       { 0x00002000, "RATTR_APLANE" },
+       { 0x00004000, "TRAST" },
+       { 0x00008000, "CLIPID" },
+       { 0x00010000, "ZCULL" },
+       { 0x00020000, "ENG2D" },
+       { 0x00040000, "RMASK" },
+       { 0x00080000, "TPC_RAST" },
+       { 0x00100000, "TPC_PROP" },
+       { 0x00200000, "TPC_TEX" },
+       { 0x00400000, "TPC_GEOM" },
+       { 0x00800000, "TPC_MP" },
+       { 0x01000000, "ROP" },
+       {}
+};
+
+static const char *const nv50_pgr_vstatus_0[] = {
+       "VFETCH", "CCACHE", "PREGEOM", "POSTGEOM", "VATTR", "STRMOUT", "VCLIP",
+       NULL
+};
+
+static const char *const nv50_pgr_vstatus_1[] = {
+       "TPC_RAST", "TPC_PROP", "TPC_TEX", "TPC_GEOM", "TPC_MP", NULL
+};
+
+static const char *const nv50_pgr_vstatus_2[] = {
+       "RATTR", "APLANE", "TRAST", "CLIPID", "ZCULL", "ENG2D", "RMASK",
+       "ROP", NULL
+};
+
+static void
+nvkm_pgr_vstatus_print(struct nv50_gr_priv *priv, int r,
+                      const char *const units[], u32 status)
+{
+       int i;
+
+       nv_error(priv, "PGRAPH_VSTATUS%d: 0x%08x", r, status);
+
+       for (i = 0; units[i] && status; i++) {
+               if ((status & 7) == 1)
+                       pr_cont(" %s", units[i]);
+               status >>= 3;
+       }
+       if (status)
+               pr_cont(" (invalid: 0x%x)", status);
+       pr_cont("\n");
+}
+
+static int
+g84_gr_tlb_flush(struct nvkm_engine *engine)
+{
+       struct nvkm_timer *ptimer = nvkm_timer(engine);
+       struct nv50_gr_priv *priv = (void *)engine;
+       bool idle, timeout = false;
+       unsigned long flags;
+       u64 start;
+       u32 tmp;
+
+       spin_lock_irqsave(&priv->lock, flags);
+       nv_mask(priv, 0x400500, 0x00000001, 0x00000000);
+
+       start = ptimer->read(ptimer);
+       do {
+               idle = true;
+
+               for (tmp = nv_rd32(priv, 0x400380); tmp && idle; tmp >>= 3) {
+                       if ((tmp & 7) == 1)
+                               idle = false;
+               }
+
+               for (tmp = nv_rd32(priv, 0x400384); tmp && idle; tmp >>= 3) {
+                       if ((tmp & 7) == 1)
+                               idle = false;
+               }
+
+               for (tmp = nv_rd32(priv, 0x400388); tmp && idle; tmp >>= 3) {
+                       if ((tmp & 7) == 1)
+                               idle = false;
+               }
+       } while (!idle &&
+                !(timeout = ptimer->read(ptimer) - start > 2000000000));
+
+       if (timeout) {
+               nv_error(priv, "PGRAPH TLB flush idle timeout fail\n");
+
+               tmp = nv_rd32(priv, 0x400700);
+               nv_error(priv, "PGRAPH_STATUS  : 0x%08x", tmp);
+               nvkm_bitfield_print(nv50_pgr_status, tmp);
+               pr_cont("\n");
+
+               nvkm_pgr_vstatus_print(priv, 0, nv50_pgr_vstatus_0,
+                                      nv_rd32(priv, 0x400380));
+               nvkm_pgr_vstatus_print(priv, 1, nv50_pgr_vstatus_1,
+                                      nv_rd32(priv, 0x400384));
+               nvkm_pgr_vstatus_print(priv, 2, nv50_pgr_vstatus_2,
+                                      nv_rd32(priv, 0x400388));
+       }
+
+
+       nv_wr32(priv, 0x100c80, 0x00000001);
+       if (!nv_wait(priv, 0x100c80, 0x00000001, 0x00000000))
+               nv_error(priv, "vm flush timeout\n");
+       nv_mask(priv, 0x400500, 0x00000001, 0x00000001);
+       spin_unlock_irqrestore(&priv->lock, flags);
+       return timeout ? -EBUSY : 0;
+}
+
+static const struct nvkm_bitfield nv50_mp_exec_errors[] = {
+       { 0x01, "STACK_UNDERFLOW" },
+       { 0x02, "STACK_MISMATCH" },
+       { 0x04, "QUADON_ACTIVE" },
+       { 0x08, "TIMEOUT" },
+       { 0x10, "INVALID_OPCODE" },
+       { 0x20, "PM_OVERFLOW" },
+       { 0x40, "BREAKPOINT" },
+       {}
+};
+
+static const struct nvkm_bitfield nv50_mpc_traps[] = {
+       { 0x0000001, "LOCAL_LIMIT_READ" },
+       { 0x0000010, "LOCAL_LIMIT_WRITE" },
+       { 0x0000040, "STACK_LIMIT" },
+       { 0x0000100, "GLOBAL_LIMIT_READ" },
+       { 0x0001000, "GLOBAL_LIMIT_WRITE" },
+       { 0x0010000, "MP0" },
+       { 0x0020000, "MP1" },
+       { 0x0040000, "GLOBAL_LIMIT_RED" },
+       { 0x0400000, "GLOBAL_LIMIT_ATOM" },
+       { 0x4000000, "MP2" },
+       {}
+};
+
+static const struct nvkm_bitfield nv50_tex_traps[] = {
+       { 0x00000001, "" }, /* any bit set? */
+       { 0x00000002, "FAULT" },
+       { 0x00000004, "STORAGE_TYPE_MISMATCH" },
+       { 0x00000008, "LINEAR_MISMATCH" },
+       { 0x00000020, "WRONG_MEMTYPE" },
+       {}
+};
+
+static const struct nvkm_bitfield nv50_gr_trap_m2mf[] = {
+       { 0x00000001, "NOTIFY" },
+       { 0x00000002, "IN" },
+       { 0x00000004, "OUT" },
+       {}
+};
+
+static const struct nvkm_bitfield nv50_gr_trap_vfetch[] = {
+       { 0x00000001, "FAULT" },
+       {}
+};
+
+static const struct nvkm_bitfield nv50_gr_trap_strmout[] = {
+       { 0x00000001, "FAULT" },
+       {}
+};
+
+static const struct nvkm_bitfield nv50_gr_trap_ccache[] = {
+       { 0x00000001, "FAULT" },
+       {}
+};
+
+/* There must be a *lot* of these. Will take some time to gather them up. */
+const struct nvkm_enum nv50_data_error_names[] = {
+       { 0x00000003, "INVALID_OPERATION", NULL },
+       { 0x00000004, "INVALID_VALUE", NULL },
+       { 0x00000005, "INVALID_ENUM", NULL },
+       { 0x00000008, "INVALID_OBJECT", NULL },
+       { 0x00000009, "READ_ONLY_OBJECT", NULL },
+       { 0x0000000a, "SUPERVISOR_OBJECT", NULL },
+       { 0x0000000b, "INVALID_ADDRESS_ALIGNMENT", NULL },
+       { 0x0000000c, "INVALID_BITFIELD", NULL },
+       { 0x0000000d, "BEGIN_END_ACTIVE", NULL },
+       { 0x0000000e, "SEMANTIC_COLOR_BACK_OVER_LIMIT", NULL },
+       { 0x0000000f, "VIEWPORT_ID_NEEDS_GP", NULL },
+       { 0x00000010, "RT_DOUBLE_BIND", NULL },
+       { 0x00000011, "RT_TYPES_MISMATCH", NULL },
+       { 0x00000012, "RT_LINEAR_WITH_ZETA", NULL },
+       { 0x00000015, "FP_TOO_FEW_REGS", NULL },
+       { 0x00000016, "ZETA_FORMAT_CSAA_MISMATCH", NULL },
+       { 0x00000017, "RT_LINEAR_WITH_MSAA", NULL },
+       { 0x00000018, "FP_INTERPOLANT_START_OVER_LIMIT", NULL },
+       { 0x00000019, "SEMANTIC_LAYER_OVER_LIMIT", NULL },
+       { 0x0000001a, "RT_INVALID_ALIGNMENT", NULL },
+       { 0x0000001b, "SAMPLER_OVER_LIMIT", NULL },
+       { 0x0000001c, "TEXTURE_OVER_LIMIT", NULL },
+       { 0x0000001e, "GP_TOO_MANY_OUTPUTS", NULL },
+       { 0x0000001f, "RT_BPP128_WITH_MS8", NULL },
+       { 0x00000021, "Z_OUT_OF_BOUNDS", NULL },
+       { 0x00000023, "XY_OUT_OF_BOUNDS", NULL },
+       { 0x00000024, "VP_ZERO_INPUTS", NULL },
+       { 0x00000027, "CP_MORE_PARAMS_THAN_SHARED", NULL },
+       { 0x00000028, "CP_NO_REG_SPACE_STRIPED", NULL },
+       { 0x00000029, "CP_NO_REG_SPACE_PACKED", NULL },
+       { 0x0000002a, "CP_NOT_ENOUGH_WARPS", NULL },
+       { 0x0000002b, "CP_BLOCK_SIZE_MISMATCH", NULL },
+       { 0x0000002c, "CP_NOT_ENOUGH_LOCAL_WARPS", NULL },
+       { 0x0000002d, "CP_NOT_ENOUGH_STACK_WARPS", NULL },
+       { 0x0000002e, "CP_NO_BLOCKDIM_LATCH", NULL },
+       { 0x00000031, "ENG2D_FORMAT_MISMATCH", NULL },
+       { 0x0000003f, "PRIMITIVE_ID_NEEDS_GP", NULL },
+       { 0x00000044, "SEMANTIC_VIEWPORT_OVER_LIMIT", NULL },
+       { 0x00000045, "SEMANTIC_COLOR_FRONT_OVER_LIMIT", NULL },
+       { 0x00000046, "LAYER_ID_NEEDS_GP", NULL },
+       { 0x00000047, "SEMANTIC_CLIP_OVER_LIMIT", NULL },
+       { 0x00000048, "SEMANTIC_PTSZ_OVER_LIMIT", NULL },
+       {}
+};
+
+static const struct nvkm_bitfield nv50_gr_intr_name[] = {
+       { 0x00000001, "NOTIFY" },
+       { 0x00000002, "COMPUTE_QUERY" },
+       { 0x00000010, "ILLEGAL_MTHD" },
+       { 0x00000020, "ILLEGAL_CLASS" },
+       { 0x00000040, "DOUBLE_NOTIFY" },
+       { 0x00001000, "CONTEXT_SWITCH" },
+       { 0x00010000, "BUFFER_NOTIFY" },
+       { 0x00100000, "DATA_ERROR" },
+       { 0x00200000, "TRAP" },
+       { 0x01000000, "SINGLE_STEP" },
+       {}
+};
+
+static const struct nvkm_bitfield nv50_gr_trap_prop[] = {
+       { 0x00000004, "SURF_WIDTH_OVERRUN" },
+       { 0x00000008, "SURF_HEIGHT_OVERRUN" },
+       { 0x00000010, "DST2D_FAULT" },
+       { 0x00000020, "ZETA_FAULT" },
+       { 0x00000040, "RT_FAULT" },
+       { 0x00000080, "CUDA_FAULT" },
+       { 0x00000100, "DST2D_STORAGE_TYPE_MISMATCH" },
+       { 0x00000200, "ZETA_STORAGE_TYPE_MISMATCH" },
+       { 0x00000400, "RT_STORAGE_TYPE_MISMATCH" },
+       { 0x00000800, "DST2D_LINEAR_MISMATCH" },
+       { 0x00001000, "RT_LINEAR_MISMATCH" },
+       {}
+};
+
+static void
+nv50_priv_prop_trap(struct nv50_gr_priv *priv,
+                   u32 ustatus_addr, u32 ustatus, u32 tp)
+{
+       u32 e0c = nv_rd32(priv, ustatus_addr + 0x04);
+       u32 e10 = nv_rd32(priv, ustatus_addr + 0x08);
+       u32 e14 = nv_rd32(priv, ustatus_addr + 0x0c);
+       u32 e18 = nv_rd32(priv, ustatus_addr + 0x10);
+       u32 e1c = nv_rd32(priv, ustatus_addr + 0x14);
+       u32 e20 = nv_rd32(priv, ustatus_addr + 0x18);
+       u32 e24 = nv_rd32(priv, ustatus_addr + 0x1c);
+
+       /* CUDA memory: l[], g[] or stack. */
+       if (ustatus & 0x00000080) {
+               if (e18 & 0x80000000) {
+                       /* g[] read fault? */
+                       nv_error(priv, "TRAP_PROP - TP %d - CUDA_FAULT - Global read fault at address %02x%08x\n",
+                                        tp, e14, e10 | ((e18 >> 24) & 0x1f));
+                       e18 &= ~0x1f000000;
+               } else if (e18 & 0xc) {
+                       /* g[] write fault? */
+                       nv_error(priv, "TRAP_PROP - TP %d - CUDA_FAULT - Global write fault at address %02x%08x\n",
+                                tp, e14, e10 | ((e18 >> 7) & 0x1f));
+                       e18 &= ~0x00000f80;
+               } else {
+                       nv_error(priv, "TRAP_PROP - TP %d - Unknown CUDA fault at address %02x%08x\n",
+                                tp, e14, e10);
+               }
+               ustatus &= ~0x00000080;
+       }
+       if (ustatus) {
+               nv_error(priv, "TRAP_PROP - TP %d -", tp);
+               nvkm_bitfield_print(nv50_gr_trap_prop, ustatus);
+               pr_cont(" - Address %02x%08x\n", e14, e10);
+       }
+       nv_error(priv, "TRAP_PROP - TP %d - e0c: %08x, e18: %08x, e1c: %08x, e20: %08x, e24: %08x\n",
+                tp, e0c, e18, e1c, e20, e24);
+}
+
+static void
+nv50_priv_mp_trap(struct nv50_gr_priv *priv, int tpid, int display)
+{
+       u32 units = nv_rd32(priv, 0x1540);
+       u32 addr, mp10, status, pc, oplow, ophigh;
+       int i;
+       int mps = 0;
+       for (i = 0; i < 4; i++) {
+               if (!(units & 1 << (i+24)))
+                       continue;
+               if (nv_device(priv)->chipset < 0xa0)
+                       addr = 0x408200 + (tpid << 12) + (i << 7);
+               else
+                       addr = 0x408100 + (tpid << 11) + (i << 7);
+               mp10 = nv_rd32(priv, addr + 0x10);
+               status = nv_rd32(priv, addr + 0x14);
+               if (!status)
+                       continue;
+               if (display) {
+                       nv_rd32(priv, addr + 0x20);
+                       pc = nv_rd32(priv, addr + 0x24);
+                       oplow = nv_rd32(priv, addr + 0x70);
+                       ophigh = nv_rd32(priv, addr + 0x74);
+                       nv_error(priv, "TRAP_MP_EXEC - "
+                                       "TP %d MP %d:", tpid, i);
+                       nvkm_bitfield_print(nv50_mp_exec_errors, status);
+                       pr_cont(" at %06x warp %d, opcode %08x %08x\n",
+                                       pc&0xffffff, pc >> 24,
+                                       oplow, ophigh);
+               }
+               nv_wr32(priv, addr + 0x10, mp10);
+               nv_wr32(priv, addr + 0x14, 0);
+               mps++;
+       }
+       if (!mps && display)
+               nv_error(priv, "TRAP_MP_EXEC - TP %d: "
+                               "No MPs claiming errors?\n", tpid);
+}
+
+static void
+nv50_priv_tp_trap(struct nv50_gr_priv *priv, int type, u32 ustatus_old,
+                 u32 ustatus_new, int display, const char *name)
+{
+       int tps = 0;
+       u32 units = nv_rd32(priv, 0x1540);
+       int i, r;
+       u32 ustatus_addr, ustatus;
+       for (i = 0; i < 16; i++) {
+               if (!(units & (1 << i)))
+                       continue;
+               if (nv_device(priv)->chipset < 0xa0)
+                       ustatus_addr = ustatus_old + (i << 12);
+               else
+                       ustatus_addr = ustatus_new + (i << 11);
+               ustatus = nv_rd32(priv, ustatus_addr) & 0x7fffffff;
+               if (!ustatus)
+                       continue;
+               tps++;
+               switch (type) {
+               case 6: /* texture error... unknown for now */
+                       if (display) {
+                               nv_error(priv, "magic set %d:\n", i);
+                               for (r = ustatus_addr + 4; r <= ustatus_addr + 0x10; r += 4)
+                                       nv_error(priv, "\t0x%08x: 0x%08x\n", r,
+                                               nv_rd32(priv, r));
+                               if (ustatus) {
+                                       nv_error(priv, "%s - TP%d:", name, i);
+                                       nvkm_bitfield_print(nv50_tex_traps,
+                                                              ustatus);
+                                       pr_cont("\n");
+                                       ustatus = 0;
+                               }
+                       }
+                       break;
+               case 7: /* MP error */
+                       if (ustatus & 0x04030000) {
+                               nv50_priv_mp_trap(priv, i, display);
+                               ustatus &= ~0x04030000;
+                       }
+                       if (ustatus && display) {
+                               nv_error(priv, "%s - TP%d:", name, i);
+                               nvkm_bitfield_print(nv50_mpc_traps, ustatus);
+                               pr_cont("\n");
+                               ustatus = 0;
+                       }
+                       break;
+               case 8: /* PROP error */
+                       if (display)
+                               nv50_priv_prop_trap(
+                                               priv, ustatus_addr, ustatus, i);
+                       ustatus = 0;
+                       break;
+               }
+               if (ustatus) {
+                       if (display)
+                               nv_error(priv, "%s - TP%d: Unhandled ustatus 0x%08x\n", name, i, ustatus);
+               }
+               nv_wr32(priv, ustatus_addr, 0xc0000000);
+       }
+
+       if (!tps && display)
+               nv_warn(priv, "%s - No TPs claiming errors?\n", name);
+}
+
+static int
+nv50_gr_trap_handler(struct nv50_gr_priv *priv, u32 display,
+                    int chid, u64 inst, struct nvkm_object *engctx)
+{
+       u32 status = nv_rd32(priv, 0x400108);
+       u32 ustatus;
+
+       if (!status && display) {
+               nv_error(priv, "TRAP: no units reporting traps?\n");
+               return 1;
+       }
+
+       /* 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(priv, 0x400804) & 0x7fffffff;
+               if (!ustatus && display) {
+                       nv_error(priv, "TRAP_DISPATCH - no ustatus?\n");
+               }
+
+               nv_wr32(priv, 0x400500, 0x00000000);
+
+               /* Known to be triggered by screwed up NOTIFY and COND... */
+               if (ustatus & 0x00000001) {
+                       u32 addr = nv_rd32(priv, 0x400808);
+                       u32 subc = (addr & 0x00070000) >> 16;
+                       u32 mthd = (addr & 0x00001ffc);
+                       u32 datal = nv_rd32(priv, 0x40080c);
+                       u32 datah = nv_rd32(priv, 0x400810);
+                       u32 class = nv_rd32(priv, 0x400814);
+                       u32 r848 = nv_rd32(priv, 0x400848);
+
+                       nv_error(priv, "TRAP DISPATCH_FAULT\n");
+                       if (display && (addr & 0x80000000)) {
+                               nv_error(priv,
+                                        "ch %d [0x%010llx %s] subc %d class 0x%04x mthd 0x%04x data 0x%08x%08x 400808 0x%08x 400848 0x%08x\n",
+                                        chid, inst,
+                                        nvkm_client_name(engctx), subc,
+                                        class, mthd, datah, datal, addr, r848);
+                       } else
+                       if (display) {
+                               nv_error(priv, "no stuck command?\n");
+                       }
+
+                       nv_wr32(priv, 0x400808, 0);
+                       nv_wr32(priv, 0x4008e8, nv_rd32(priv, 0x4008e8) & 3);
+                       nv_wr32(priv, 0x400848, 0);
+                       ustatus &= ~0x00000001;
+               }
+
+               if (ustatus & 0x00000002) {
+                       u32 addr = nv_rd32(priv, 0x40084c);
+                       u32 subc = (addr & 0x00070000) >> 16;
+                       u32 mthd = (addr & 0x00001ffc);
+                       u32 data = nv_rd32(priv, 0x40085c);
+                       u32 class = nv_rd32(priv, 0x400814);
+
+                       nv_error(priv, "TRAP DISPATCH_QUERY\n");
+                       if (display && (addr & 0x80000000)) {
+                               nv_error(priv,
+                                        "ch %d [0x%010llx %s] subc %d class 0x%04x mthd 0x%04x data 0x%08x 40084c 0x%08x\n",
+                                        chid, inst,
+                                        nvkm_client_name(engctx), subc,
+                                        class, mthd, data, addr);
+                       } else
+                       if (display) {
+                               nv_error(priv, "no stuck command?\n");
+                       }
+
+                       nv_wr32(priv, 0x40084c, 0);
+                       ustatus &= ~0x00000002;
+               }
+
+               if (ustatus && display) {
+                       nv_error(priv, "TRAP_DISPATCH (unknown "
+                                     "0x%08x)\n", ustatus);
+               }
+
+               nv_wr32(priv, 0x400804, 0xc0000000);
+               nv_wr32(priv, 0x400108, 0x001);
+               status &= ~0x001;
+               if (!status)
+                       return 0;
+       }
+
+       /* M2MF: Memory to memory copy engine. */
+       if (status & 0x002) {
+               u32 ustatus = nv_rd32(priv, 0x406800) & 0x7fffffff;
+               if (display) {
+                       nv_error(priv, "TRAP_M2MF");
+                       nvkm_bitfield_print(nv50_gr_trap_m2mf, ustatus);
+                       pr_cont("\n");
+                       nv_error(priv, "TRAP_M2MF %08x %08x %08x %08x\n",
+                               nv_rd32(priv, 0x406804), nv_rd32(priv, 0x406808),
+                               nv_rd32(priv, 0x40680c), nv_rd32(priv, 0x406810));
+
+               }
+
+               /* No sane way found yet -- just reset the bugger. */
+               nv_wr32(priv, 0x400040, 2);
+               nv_wr32(priv, 0x400040, 0);
+               nv_wr32(priv, 0x406800, 0xc0000000);
+               nv_wr32(priv, 0x400108, 0x002);
+               status &= ~0x002;
+       }
+
+       /* VFETCH: Fetches data from vertex buffers. */
+       if (status & 0x004) {
+               u32 ustatus = nv_rd32(priv, 0x400c04) & 0x7fffffff;
+               if (display) {
+                       nv_error(priv, "TRAP_VFETCH");
+                       nvkm_bitfield_print(nv50_gr_trap_vfetch, ustatus);
+                       pr_cont("\n");
+                       nv_error(priv, "TRAP_VFETCH %08x %08x %08x %08x\n",
+                               nv_rd32(priv, 0x400c00), nv_rd32(priv, 0x400c08),
+                               nv_rd32(priv, 0x400c0c), nv_rd32(priv, 0x400c10));
+               }
+
+               nv_wr32(priv, 0x400c04, 0xc0000000);
+               nv_wr32(priv, 0x400108, 0x004);
+               status &= ~0x004;
+       }
+
+       /* STRMOUT: DirectX streamout / OpenGL transform feedback. */
+       if (status & 0x008) {
+               ustatus = nv_rd32(priv, 0x401800) & 0x7fffffff;
+               if (display) {
+                       nv_error(priv, "TRAP_STRMOUT");
+                       nvkm_bitfield_print(nv50_gr_trap_strmout, ustatus);
+                       pr_cont("\n");
+                       nv_error(priv, "TRAP_STRMOUT %08x %08x %08x %08x\n",
+                               nv_rd32(priv, 0x401804), nv_rd32(priv, 0x401808),
+                               nv_rd32(priv, 0x40180c), nv_rd32(priv, 0x401810));
+
+               }
+
+               /* No sane way found yet -- just reset the bugger. */
+               nv_wr32(priv, 0x400040, 0x80);
+               nv_wr32(priv, 0x400040, 0);
+               nv_wr32(priv, 0x401800, 0xc0000000);
+               nv_wr32(priv, 0x400108, 0x008);
+               status &= ~0x008;
+       }
+
+       /* CCACHE: Handles code and c[] caches and fills them. */
+       if (status & 0x010) {
+               ustatus = nv_rd32(priv, 0x405018) & 0x7fffffff;
+               if (display) {
+                       nv_error(priv, "TRAP_CCACHE");
+                       nvkm_bitfield_print(nv50_gr_trap_ccache, ustatus);
+                       pr_cont("\n");
+                       nv_error(priv, "TRAP_CCACHE %08x %08x %08x %08x"
+                                    " %08x %08x %08x\n",
+                               nv_rd32(priv, 0x405000), nv_rd32(priv, 0x405004),
+                               nv_rd32(priv, 0x405008), nv_rd32(priv, 0x40500c),
+                               nv_rd32(priv, 0x405010), nv_rd32(priv, 0x405014),
+                               nv_rd32(priv, 0x40501c));
+
+               }
+
+               nv_wr32(priv, 0x405018, 0xc0000000);
+               nv_wr32(priv, 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) {
+               ustatus = nv_rd32(priv, 0x402000) & 0x7fffffff;
+               if (display)
+                       nv_error(priv, "TRAP_UNKC04 0x%08x\n", ustatus);
+               nv_wr32(priv, 0x402000, 0xc0000000);
+               /* no status modifiction on purpose */
+       }
+
+       /* TEXTURE: CUDA texturing units */
+       if (status & 0x040) {
+               nv50_priv_tp_trap(priv, 6, 0x408900, 0x408600, display,
+                                   "TRAP_TEXTURE");
+               nv_wr32(priv, 0x400108, 0x040);
+               status &= ~0x040;
+       }
+
+       /* MP: CUDA execution engines. */
+       if (status & 0x080) {
+               nv50_priv_tp_trap(priv, 7, 0x408314, 0x40831c, display,
+                                   "TRAP_MP");
+               nv_wr32(priv, 0x400108, 0x080);
+               status &= ~0x080;
+       }
+
+       /* PROP:  Handles TP-initiated uncached memory accesses:
+        * l[], g[], stack, 2d surfaces, render targets. */
+       if (status & 0x100) {
+               nv50_priv_tp_trap(priv, 8, 0x408e08, 0x408708, display,
+                                   "TRAP_PROP");
+               nv_wr32(priv, 0x400108, 0x100);
+               status &= ~0x100;
+       }
+
+       if (status) {
+               if (display)
+                       nv_error(priv, "TRAP: unknown 0x%08x\n", status);
+               nv_wr32(priv, 0x400108, status);
+       }
+
+       return 1;
+}
+
+static void
+nv50_gr_intr(struct nvkm_subdev *subdev)
+{
+       struct nvkm_fifo *pfifo = nvkm_fifo(subdev);
+       struct nvkm_engine *engine = nv_engine(subdev);
+       struct nvkm_object *engctx;
+       struct nvkm_handle *handle = NULL;
+       struct nv50_gr_priv *priv = (void *)subdev;
+       u32 stat = nv_rd32(priv, 0x400100);
+       u32 inst = nv_rd32(priv, 0x40032c) & 0x0fffffff;
+       u32 addr = nv_rd32(priv, 0x400704);
+       u32 subc = (addr & 0x00070000) >> 16;
+       u32 mthd = (addr & 0x00001ffc);
+       u32 data = nv_rd32(priv, 0x400708);
+       u32 class = nv_rd32(priv, 0x400814);
+       u32 show = stat, show_bitfield = stat;
+       int chid;
+
+       engctx = nvkm_engctx_get(engine, inst);
+       chid   = pfifo->chid(pfifo, engctx);
+
+       if (stat & 0x00000010) {
+               handle = nvkm_handle_get_class(engctx, class);
+               if (handle && !nv_call(handle->object, mthd, data))
+                       show &= ~0x00000010;
+               nvkm_handle_put(handle);
+       }
+
+       if (show & 0x00100000) {
+               u32 ecode = nv_rd32(priv, 0x400110);
+               nv_error(priv, "DATA_ERROR ");
+               nvkm_enum_print(nv50_data_error_names, ecode);
+               pr_cont("\n");
+               show_bitfield &= ~0x00100000;
+       }
+
+       if (stat & 0x00200000) {
+               if (!nv50_gr_trap_handler(priv, show, chid, (u64)inst << 12,
+                                         engctx))
+                       show &= ~0x00200000;
+               show_bitfield &= ~0x00200000;
+       }
+
+       nv_wr32(priv, 0x400100, stat);
+       nv_wr32(priv, 0x400500, 0x00010001);
+
+       if (show) {
+               show &= show_bitfield;
+               if (show) {
+                       nv_error(priv, "%s", "");
+                       nvkm_bitfield_print(nv50_gr_intr_name, show);
+                       pr_cont("\n");
+               }
+               nv_error(priv,
+                        "ch %d [0x%010llx %s] subc %d class 0x%04x mthd 0x%04x data 0x%08x\n",
+                        chid, (u64)inst << 12, nvkm_client_name(engctx),
+                        subc, class, mthd, data);
+       }
+
+       if (nv_rd32(priv, 0x400824) & (1 << 31))
+               nv_wr32(priv, 0x400824, nv_rd32(priv, 0x400824) & ~(1 << 31));
+
+       nvkm_engctx_put(engctx);
+}
+
+static int
+nv50_gr_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+            struct nvkm_oclass *oclass, void *data, u32 size,
+            struct nvkm_object **pobject)
+{
+       struct nv50_gr_priv *priv;
+       int ret;
+
+       ret = nvkm_gr_create(parent, engine, oclass, true, &priv);
+       *pobject = nv_object(priv);
+       if (ret)
+               return ret;
+
+       nv_subdev(priv)->unit = 0x00201000;
+       nv_subdev(priv)->intr = nv50_gr_intr;
+       nv_engine(priv)->cclass = &nv50_gr_cclass;
+
+       priv->base.units = nv50_gr_units;
+
+       switch (nv_device(priv)->chipset) {
+       case 0x50:
+               nv_engine(priv)->sclass = nv50_gr_sclass;
+               break;
+       case 0x84:
+       case 0x86:
+       case 0x92:
+       case 0x94:
+       case 0x96:
+       case 0x98:
+               nv_engine(priv)->sclass = g84_gr_sclass;
+               break;
+       case 0xa0:
+       case 0xaa:
+       case 0xac:
+               nv_engine(priv)->sclass = gt200_gr_sclass;
+               break;
+       case 0xa3:
+       case 0xa5:
+       case 0xa8:
+               nv_engine(priv)->sclass = gt215_gr_sclass;
+               break;
+       case 0xaf:
+               nv_engine(priv)->sclass = mcp89_gr_sclass;
+               break;
+
+       }
+
+       /* unfortunate hw bug workaround... */
+       if (nv_device(priv)->chipset != 0x50 &&
+           nv_device(priv)->chipset != 0xac)
+               nv_engine(priv)->tlb_flush = g84_gr_tlb_flush;
+
+       spin_lock_init(&priv->lock);
+       return 0;
+}
+
+static int
+nv50_gr_init(struct nvkm_object *object)
+{
+       struct nv50_gr_priv *priv = (void *)object;
+       int ret, units, i;
+
+       ret = nvkm_gr_init(&priv->base);
+       if (ret)
+               return ret;
+
+       /* NV_PGRAPH_DEBUG_3_HW_CTX_SWITCH_ENABLED */
+       nv_wr32(priv, 0x40008c, 0x00000004);
+
+       /* reset/enable traps and interrupts */
+       nv_wr32(priv, 0x400804, 0xc0000000);
+       nv_wr32(priv, 0x406800, 0xc0000000);
+       nv_wr32(priv, 0x400c04, 0xc0000000);
+       nv_wr32(priv, 0x401800, 0xc0000000);
+       nv_wr32(priv, 0x405018, 0xc0000000);
+       nv_wr32(priv, 0x402000, 0xc0000000);
+
+       units = nv_rd32(priv, 0x001540);
+       for (i = 0; i < 16; i++) {
+               if (!(units & (1 << i)))
+                       continue;
+
+               if (nv_device(priv)->chipset < 0xa0) {
+                       nv_wr32(priv, 0x408900 + (i << 12), 0xc0000000);
+                       nv_wr32(priv, 0x408e08 + (i << 12), 0xc0000000);
+                       nv_wr32(priv, 0x408314 + (i << 12), 0xc0000000);
+               } else {
+                       nv_wr32(priv, 0x408600 + (i << 11), 0xc0000000);
+                       nv_wr32(priv, 0x408708 + (i << 11), 0xc0000000);
+                       nv_wr32(priv, 0x40831c + (i << 11), 0xc0000000);
+               }
+       }
+
+       nv_wr32(priv, 0x400108, 0xffffffff);
+       nv_wr32(priv, 0x400138, 0xffffffff);
+       nv_wr32(priv, 0x400100, 0xffffffff);
+       nv_wr32(priv, 0x40013c, 0xffffffff);
+       nv_wr32(priv, 0x400500, 0x00010001);
+
+       /* upload context program, initialise ctxctl defaults */
+       ret = nv50_grctx_init(nv_device(priv), &priv->size);
+       if (ret)
+               return ret;
+
+       nv_wr32(priv, 0x400824, 0x00000000);
+       nv_wr32(priv, 0x400828, 0x00000000);
+       nv_wr32(priv, 0x40082c, 0x00000000);
+       nv_wr32(priv, 0x400830, 0x00000000);
+       nv_wr32(priv, 0x40032c, 0x00000000);
+       nv_wr32(priv, 0x400330, 0x00000000);
+
+       /* some unknown zcull magic */
+       switch (nv_device(priv)->chipset & 0xf0) {
+       case 0x50:
+       case 0x80:
+       case 0x90:
+               nv_wr32(priv, 0x402ca8, 0x00000800);
+               break;
+       case 0xa0:
+       default:
+               if (nv_device(priv)->chipset == 0xa0 ||
+                   nv_device(priv)->chipset == 0xaa ||
+                   nv_device(priv)->chipset == 0xac) {
+                       nv_wr32(priv, 0x402ca8, 0x00000802);
+               } else {
+                       nv_wr32(priv, 0x402cc0, 0x00000000);
+                       nv_wr32(priv, 0x402ca8, 0x00000002);
+               }
+
+               break;
+       }
+
+       /* zero out zcull regions */
+       for (i = 0; i < 8; i++) {
+               nv_wr32(priv, 0x402c20 + (i * 0x10), 0x00000000);
+               nv_wr32(priv, 0x402c24 + (i * 0x10), 0x00000000);
+               nv_wr32(priv, 0x402c28 + (i * 0x10), 0x00000000);
+               nv_wr32(priv, 0x402c2c + (i * 0x10), 0x00000000);
+       }
+       return 0;
+}
+
+struct nvkm_oclass
+nv50_gr_oclass = {
+       .handle = NV_ENGINE(GR, 0x50),
+       .ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = nv50_gr_ctor,
+               .dtor = _nvkm_gr_dtor,
+               .init = nv50_gr_init,
+               .fini = _nvkm_gr_fini,
+       },
+};
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/gr/nv50.h b/drivers/gpu/drm/nouveau/nvkm/engine/gr/nv50.h
new file mode 100644 (file)
index 0000000..bcf786f
--- /dev/null
@@ -0,0 +1,9 @@
+#ifndef __NV50_GR_H__
+#define __NV50_GR_H__
+#include <engine/gr.h>
+struct nvkm_device;
+struct nvkm_gpuobj;
+
+int  nv50_grctx_init(struct nvkm_device *, u32 *size);
+void nv50_grctx_fill(struct nvkm_device *, struct nvkm_gpuobj *);
+#endif
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/gr/regs.h b/drivers/gpu/drm/nouveau/nvkm/engine/gr/regs.h
new file mode 100644 (file)
index 0000000..90a9873
--- /dev/null
@@ -0,0 +1,274 @@
+#ifndef __NVKM_GR_REGS_H__
+#define __NVKM_GR_REGS_H__
+
+#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 NV40_PGRAPH_STATUS_SYNC_STALL                  0x00004000
+#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 NV20_PGRAPH_ZCOMP(i)                               (0x00400980 + 4*(i))
+#define NV41_PGRAPH_ZCOMP0(i)                              (0x004009c0 + 4*(i))
+#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 NV47_PGRAPH_ZCOMP0(i)                              (0x00400e00 + 4*(i))
+#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 NV47_PGRAPH_ZCOMP1(i)                              (0x004068c0 + 4*(i))
+#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))
+#define NV40_PGRAPH_ZCOMP1(i)                              (0x00406980 + 4*(i))
+#define NV41_PGRAPH_ZCOMP1(i)                              (0x004069c0 + 4*(i))
+
+#endif
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/mpeg/Kbuild b/drivers/gpu/drm/nouveau/nvkm/engine/mpeg/Kbuild
new file mode 100644 (file)
index 0000000..61b7b5f
--- /dev/null
@@ -0,0 +1,5 @@
+nvkm-y += nvkm/engine/mpeg/nv31.o
+nvkm-y += nvkm/engine/mpeg/nv40.o
+nvkm-y += nvkm/engine/mpeg/nv44.o
+nvkm-y += nvkm/engine/mpeg/nv50.o
+nvkm-y += nvkm/engine/mpeg/g84.o
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/mpeg/g84.c b/drivers/gpu/drm/nouveau/nvkm/engine/mpeg/g84.c
new file mode 100644 (file)
index 0000000..0df889f
--- /dev/null
@@ -0,0 +1,94 @@
+/*
+ * Copyright 2012 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 <engine/mpeg.h>
+
+struct g84_mpeg_priv {
+       struct nvkm_mpeg base;
+};
+
+struct g84_mpeg_chan {
+       struct nvkm_mpeg_chan base;
+};
+
+/*******************************************************************************
+ * MPEG object classes
+ ******************************************************************************/
+
+static struct nvkm_oclass
+g84_mpeg_sclass[] = {
+       { 0x8274, &nv50_mpeg_ofuncs },
+       {}
+};
+
+/*******************************************************************************
+ * PMPEG context
+ ******************************************************************************/
+
+static struct nvkm_oclass
+g84_mpeg_cclass = {
+       .handle = NV_ENGCTX(MPEG, 0x84),
+       .ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = nv50_mpeg_context_ctor,
+               .dtor = _nvkm_mpeg_context_dtor,
+               .init = _nvkm_mpeg_context_init,
+               .fini = _nvkm_mpeg_context_fini,
+               .rd32 = _nvkm_mpeg_context_rd32,
+               .wr32 = _nvkm_mpeg_context_wr32,
+       },
+};
+
+/*******************************************************************************
+ * PMPEG engine/subdev functions
+ ******************************************************************************/
+
+static int
+g84_mpeg_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+             struct nvkm_oclass *oclass, void *data, u32 size,
+             struct nvkm_object **pobject)
+{
+       struct g84_mpeg_priv *priv;
+       int ret;
+
+       ret = nvkm_mpeg_create(parent, engine, oclass, &priv);
+       *pobject = nv_object(priv);
+       if (ret)
+               return ret;
+
+       nv_subdev(priv)->unit = 0x00000002;
+       nv_subdev(priv)->intr = nv50_mpeg_intr;
+       nv_engine(priv)->cclass = &g84_mpeg_cclass;
+       nv_engine(priv)->sclass = g84_mpeg_sclass;
+       return 0;
+}
+
+struct nvkm_oclass
+g84_mpeg_oclass = {
+       .handle = NV_ENGINE(MPEG, 0x84),
+       .ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = g84_mpeg_ctor,
+               .dtor = _nvkm_mpeg_dtor,
+               .init = nv50_mpeg_init,
+               .fini = _nvkm_mpeg_fini,
+       },
+};
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/mpeg/nv31.c b/drivers/gpu/drm/nouveau/nvkm/engine/mpeg/nv31.c
new file mode 100644 (file)
index 0000000..b5bef07
--- /dev/null
@@ -0,0 +1,304 @@
+/*
+ * Copyright 2012 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 "nv31.h"
+
+#include <core/client.h>
+#include <core/handle.h>
+#include <engine/fifo.h>
+#include <subdev/instmem.h>
+#include <subdev/fb.h>
+#include <subdev/timer.h>
+
+/*******************************************************************************
+ * MPEG object classes
+ ******************************************************************************/
+
+static int
+nv31_mpeg_object_ctor(struct nvkm_object *parent,
+                     struct nvkm_object *engine,
+                     struct nvkm_oclass *oclass, void *data, u32 size,
+                     struct nvkm_object **pobject)
+{
+       struct nvkm_gpuobj *obj;
+       int ret;
+
+       ret = nvkm_gpuobj_create(parent, engine, oclass, 0, parent,
+                                20, 16, 0, &obj);
+       *pobject = nv_object(obj);
+       if (ret)
+               return ret;
+
+       nv_wo32(obj, 0x00, nv_mclass(obj));
+       nv_wo32(obj, 0x04, 0x00000000);
+       nv_wo32(obj, 0x08, 0x00000000);
+       nv_wo32(obj, 0x0c, 0x00000000);
+       return 0;
+}
+
+static int
+nv31_mpeg_mthd_dma(struct nvkm_object *object, u32 mthd, void *arg, u32 len)
+{
+       struct nvkm_instmem *imem = nvkm_instmem(object);
+       struct nv31_mpeg_priv *priv = (void *)object->engine;
+       u32 inst = *(u32 *)arg << 4;
+       u32 dma0 = nv_ro32(imem, inst + 0);
+       u32 dma1 = nv_ro32(imem, inst + 4);
+       u32 dma2 = nv_ro32(imem, inst + 8);
+       u32 base = (dma2 & 0xfffff000) | (dma0 >> 20);
+       u32 size = dma1 + 1;
+
+       /* only allow linear DMA objects */
+       if (!(dma0 & 0x00002000))
+               return -EINVAL;
+
+       if (mthd == 0x0190) {
+               /* DMA_CMD */
+               nv_mask(priv, 0x00b300, 0x00010000, (dma0 & 0x00030000) ? 0x00010000 : 0);
+               nv_wr32(priv, 0x00b334, base);
+               nv_wr32(priv, 0x00b324, size);
+       } else
+       if (mthd == 0x01a0) {
+               /* DMA_DATA */
+               nv_mask(priv, 0x00b300, 0x00020000, (dma0 & 0x00030000) ? 0x00020000 : 0);
+               nv_wr32(priv, 0x00b360, base);
+               nv_wr32(priv, 0x00b364, size);
+       } else {
+               /* DMA_IMAGE, VRAM only */
+               if (dma0 & 0x00030000)
+                       return -EINVAL;
+
+               nv_wr32(priv, 0x00b370, base);
+               nv_wr32(priv, 0x00b374, size);
+       }
+
+       return 0;
+}
+
+struct nvkm_ofuncs
+nv31_mpeg_ofuncs = {
+       .ctor = nv31_mpeg_object_ctor,
+       .dtor = _nvkm_gpuobj_dtor,
+       .init = _nvkm_gpuobj_init,
+       .fini = _nvkm_gpuobj_fini,
+       .rd32 = _nvkm_gpuobj_rd32,
+       .wr32 = _nvkm_gpuobj_wr32,
+};
+
+static struct nvkm_omthds
+nv31_mpeg_omthds[] = {
+       { 0x0190, 0x0190, nv31_mpeg_mthd_dma },
+       { 0x01a0, 0x01a0, nv31_mpeg_mthd_dma },
+       { 0x01b0, 0x01b0, nv31_mpeg_mthd_dma },
+       {}
+};
+
+struct nvkm_oclass
+nv31_mpeg_sclass[] = {
+       { 0x3174, &nv31_mpeg_ofuncs, nv31_mpeg_omthds },
+       {}
+};
+
+/*******************************************************************************
+ * PMPEG context
+ ******************************************************************************/
+
+static int
+nv31_mpeg_context_ctor(struct nvkm_object *parent,
+                      struct nvkm_object *engine,
+                      struct nvkm_oclass *oclass, void *data, u32 size,
+                      struct nvkm_object **pobject)
+{
+       struct nv31_mpeg_priv *priv = (void *)engine;
+       struct nv31_mpeg_chan *chan;
+       unsigned long flags;
+       int ret;
+
+       ret = nvkm_object_create(parent, engine, oclass, 0, &chan);
+       *pobject = nv_object(chan);
+       if (ret)
+               return ret;
+
+       spin_lock_irqsave(&nv_engine(priv)->lock, flags);
+       if (priv->chan) {
+               spin_unlock_irqrestore(&nv_engine(priv)->lock, flags);
+               nvkm_object_destroy(&chan->base);
+               *pobject = NULL;
+               return -EBUSY;
+       }
+       priv->chan = chan;
+       spin_unlock_irqrestore(&nv_engine(priv)->lock, flags);
+       return 0;
+}
+
+static void
+nv31_mpeg_context_dtor(struct nvkm_object *object)
+{
+       struct nv31_mpeg_priv *priv = (void *)object->engine;
+       struct nv31_mpeg_chan *chan = (void *)object;
+       unsigned long flags;
+
+       spin_lock_irqsave(&nv_engine(priv)->lock, flags);
+       priv->chan = NULL;
+       spin_unlock_irqrestore(&nv_engine(priv)->lock, flags);
+       nvkm_object_destroy(&chan->base);
+}
+
+struct nvkm_oclass
+nv31_mpeg_cclass = {
+       .handle = NV_ENGCTX(MPEG, 0x31),
+       .ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = nv31_mpeg_context_ctor,
+               .dtor = nv31_mpeg_context_dtor,
+               .init = nvkm_object_init,
+               .fini = nvkm_object_fini,
+       },
+};
+
+/*******************************************************************************
+ * PMPEG engine/subdev functions
+ ******************************************************************************/
+
+void
+nv31_mpeg_tile_prog(struct nvkm_engine *engine, int i)
+{
+       struct nvkm_fb_tile *tile = &nvkm_fb(engine)->tile.region[i];
+       struct nv31_mpeg_priv *priv = (void *)engine;
+
+       nv_wr32(priv, 0x00b008 + (i * 0x10), tile->pitch);
+       nv_wr32(priv, 0x00b004 + (i * 0x10), tile->limit);
+       nv_wr32(priv, 0x00b000 + (i * 0x10), tile->addr);
+}
+
+void
+nv31_mpeg_intr(struct nvkm_subdev *subdev)
+{
+       struct nv31_mpeg_priv *priv = (void *)subdev;
+       struct nvkm_fifo *pfifo = nvkm_fifo(subdev);
+       struct nvkm_handle *handle;
+       struct nvkm_object *engctx;
+       u32 stat = nv_rd32(priv, 0x00b100);
+       u32 type = nv_rd32(priv, 0x00b230);
+       u32 mthd = nv_rd32(priv, 0x00b234);
+       u32 data = nv_rd32(priv, 0x00b238);
+       u32 show = stat;
+       unsigned long flags;
+
+       spin_lock_irqsave(&nv_engine(priv)->lock, flags);
+       engctx = nv_object(priv->chan);
+
+       if (stat & 0x01000000) {
+               /* happens on initial binding of the object */
+               if (type == 0x00000020 && mthd == 0x0000) {
+                       nv_mask(priv, 0x00b308, 0x00000000, 0x00000000);
+                       show &= ~0x01000000;
+               }
+
+               if (type == 0x00000010 && engctx) {
+                       handle = nvkm_handle_get_class(engctx, 0x3174);
+                       if (handle && !nv_call(handle->object, mthd, data))
+                               show &= ~0x01000000;
+                       nvkm_handle_put(handle);
+               }
+       }
+
+       nv_wr32(priv, 0x00b100, stat);
+       nv_wr32(priv, 0x00b230, 0x00000001);
+
+       if (show) {
+               nv_error(priv, "ch %d [%s] 0x%08x 0x%08x 0x%08x 0x%08x\n",
+                        pfifo->chid(pfifo, engctx),
+                        nvkm_client_name(engctx), stat, type, mthd, data);
+       }
+
+       spin_unlock_irqrestore(&nv_engine(priv)->lock, flags);
+}
+
+static int
+nv31_mpeg_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+              struct nvkm_oclass *oclass, void *data, u32 size,
+              struct nvkm_object **pobject)
+{
+       struct nv31_mpeg_priv *priv;
+       int ret;
+
+       ret = nvkm_mpeg_create(parent, engine, oclass, &priv);
+       *pobject = nv_object(priv);
+       if (ret)
+               return ret;
+
+       nv_subdev(priv)->unit = 0x00000002;
+       nv_subdev(priv)->intr = nv31_mpeg_intr;
+       nv_engine(priv)->cclass = &nv31_mpeg_cclass;
+       nv_engine(priv)->sclass = nv31_mpeg_sclass;
+       nv_engine(priv)->tile_prog = nv31_mpeg_tile_prog;
+       return 0;
+}
+
+int
+nv31_mpeg_init(struct nvkm_object *object)
+{
+       struct nvkm_engine *engine = nv_engine(object);
+       struct nv31_mpeg_priv *priv = (void *)object;
+       struct nvkm_fb *pfb = nvkm_fb(object);
+       int ret, i;
+
+       ret = nvkm_mpeg_init(&priv->base);
+       if (ret)
+               return ret;
+
+       /* VPE init */
+       nv_wr32(priv, 0x00b0e0, 0x00000020); /* nvidia: rd 0x01, wr 0x20 */
+       nv_wr32(priv, 0x00b0e8, 0x00000020); /* nvidia: rd 0x01, wr 0x20 */
+
+       for (i = 0; i < pfb->tile.regions; i++)
+               engine->tile_prog(engine, i);
+
+       /* PMPEG init */
+       nv_wr32(priv, 0x00b32c, 0x00000000);
+       nv_wr32(priv, 0x00b314, 0x00000100);
+       nv_wr32(priv, 0x00b220, 0x00000031);
+       nv_wr32(priv, 0x00b300, 0x02001ec1);
+       nv_mask(priv, 0x00b32c, 0x00000001, 0x00000001);
+
+       nv_wr32(priv, 0x00b100, 0xffffffff);
+       nv_wr32(priv, 0x00b140, 0xffffffff);
+
+       if (!nv_wait(priv, 0x00b200, 0x00000001, 0x00000000)) {
+               nv_error(priv, "timeout 0x%08x\n", nv_rd32(priv, 0x00b200));
+               return -EBUSY;
+       }
+
+       return 0;
+}
+
+struct nvkm_oclass
+nv31_mpeg_oclass = {
+       .handle = NV_ENGINE(MPEG, 0x31),
+       .ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = nv31_mpeg_ctor,
+               .dtor = _nvkm_mpeg_dtor,
+               .init = nv31_mpeg_init,
+               .fini = _nvkm_mpeg_fini,
+       },
+};
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/mpeg/nv31.h b/drivers/gpu/drm/nouveau/nvkm/engine/mpeg/nv31.h
new file mode 100644 (file)
index 0000000..782b796
--- /dev/null
@@ -0,0 +1,13 @@
+#ifndef __NV31_MPEG_H__
+#define __NV31_MPEG_H__
+#include <engine/mpeg.h>
+
+struct nv31_mpeg_chan {
+       struct nvkm_object base;
+};
+
+struct nv31_mpeg_priv {
+       struct nvkm_mpeg base;
+       struct nv31_mpeg_chan *chan;
+};
+#endif
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/mpeg/nv40.c b/drivers/gpu/drm/nouveau/nvkm/engine/mpeg/nv40.c
new file mode 100644 (file)
index 0000000..9508bf9
--- /dev/null
@@ -0,0 +1,134 @@
+/*
+ * Copyright 2012 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 "nv31.h"
+
+#include <subdev/instmem.h>
+
+/*******************************************************************************
+ * MPEG object classes
+ ******************************************************************************/
+
+static int
+nv40_mpeg_mthd_dma(struct nvkm_object *object, u32 mthd, void *arg, u32 len)
+{
+       struct nvkm_instmem *imem = nvkm_instmem(object);
+       struct nv31_mpeg_priv *priv = (void *)object->engine;
+       u32 inst = *(u32 *)arg << 4;
+       u32 dma0 = nv_ro32(imem, inst + 0);
+       u32 dma1 = nv_ro32(imem, inst + 4);
+       u32 dma2 = nv_ro32(imem, inst + 8);
+       u32 base = (dma2 & 0xfffff000) | (dma0 >> 20);
+       u32 size = dma1 + 1;
+
+       /* only allow linear DMA objects */
+       if (!(dma0 & 0x00002000))
+               return -EINVAL;
+
+       if (mthd == 0x0190) {
+               /* DMA_CMD */
+               nv_mask(priv, 0x00b300, 0x00030000, (dma0 & 0x00030000));
+               nv_wr32(priv, 0x00b334, base);
+               nv_wr32(priv, 0x00b324, size);
+       } else
+       if (mthd == 0x01a0) {
+               /* DMA_DATA */
+               nv_mask(priv, 0x00b300, 0x000c0000, (dma0 & 0x00030000) << 2);
+               nv_wr32(priv, 0x00b360, base);
+               nv_wr32(priv, 0x00b364, size);
+       } else {
+               /* DMA_IMAGE, VRAM only */
+               if (dma0 & 0x00030000)
+                       return -EINVAL;
+
+               nv_wr32(priv, 0x00b370, base);
+               nv_wr32(priv, 0x00b374, size);
+       }
+
+       return 0;
+}
+
+static struct nvkm_omthds
+nv40_mpeg_omthds[] = {
+       { 0x0190, 0x0190, nv40_mpeg_mthd_dma },
+       { 0x01a0, 0x01a0, nv40_mpeg_mthd_dma },
+       { 0x01b0, 0x01b0, nv40_mpeg_mthd_dma },
+       {}
+};
+
+struct nvkm_oclass
+nv40_mpeg_sclass[] = {
+       { 0x3174, &nv31_mpeg_ofuncs, nv40_mpeg_omthds },
+       {}
+};
+
+/*******************************************************************************
+ * PMPEG engine/subdev functions
+ ******************************************************************************/
+
+static void
+nv40_mpeg_intr(struct nvkm_subdev *subdev)
+{
+       struct nv31_mpeg_priv *priv = (void *)subdev;
+       u32 stat;
+
+       if ((stat = nv_rd32(priv, 0x00b100)))
+               nv31_mpeg_intr(subdev);
+
+       if ((stat = nv_rd32(priv, 0x00b800))) {
+               nv_error(priv, "PMSRCH 0x%08x\n", stat);
+               nv_wr32(priv, 0x00b800, stat);
+       }
+}
+
+static int
+nv40_mpeg_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+              struct nvkm_oclass *oclass, void *data, u32 size,
+              struct nvkm_object **pobject)
+{
+       struct nv31_mpeg_priv *priv;
+       int ret;
+
+       ret = nvkm_mpeg_create(parent, engine, oclass, &priv);
+       *pobject = nv_object(priv);
+       if (ret)
+               return ret;
+
+       nv_subdev(priv)->unit = 0x00000002;
+       nv_subdev(priv)->intr = nv40_mpeg_intr;
+       nv_engine(priv)->cclass = &nv31_mpeg_cclass;
+       nv_engine(priv)->sclass = nv40_mpeg_sclass;
+       nv_engine(priv)->tile_prog = nv31_mpeg_tile_prog;
+       return 0;
+}
+
+struct nvkm_oclass
+nv40_mpeg_oclass = {
+       .handle = NV_ENGINE(MPEG, 0x40),
+       .ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = nv40_mpeg_ctor,
+               .dtor = _nvkm_mpeg_dtor,
+               .init = nv31_mpeg_init,
+               .fini = _nvkm_mpeg_fini,
+       },
+};
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/mpeg/nv44.c b/drivers/gpu/drm/nouveau/nvkm/engine/mpeg/nv44.c
new file mode 100644 (file)
index 0000000..4720ac8
--- /dev/null
@@ -0,0 +1,185 @@
+/*
+ * Copyright 2012 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 <engine/mpeg.h>
+
+#include <core/client.h>
+#include <core/handle.h>
+#include <engine/fifo.h>
+
+struct nv44_mpeg_priv {
+       struct nvkm_mpeg base;
+};
+
+struct nv44_mpeg_chan {
+       struct nvkm_mpeg_chan base;
+};
+
+/*******************************************************************************
+ * PMPEG context
+ ******************************************************************************/
+
+static int
+nv44_mpeg_context_ctor(struct nvkm_object *parent,
+                      struct nvkm_object *engine,
+                      struct nvkm_oclass *oclass, void *data, u32 size,
+                      struct nvkm_object **pobject)
+{
+       struct nv44_mpeg_chan *chan;
+       int ret;
+
+       ret = nvkm_mpeg_context_create(parent, engine, oclass, NULL, 264 * 4,
+                                      16, NVOBJ_FLAG_ZERO_ALLOC, &chan);
+       *pobject = nv_object(chan);
+       if (ret)
+               return ret;
+
+       nv_wo32(&chan->base.base, 0x78, 0x02001ec1);
+       return 0;
+}
+
+static int
+nv44_mpeg_context_fini(struct nvkm_object *object, bool suspend)
+{
+
+       struct nv44_mpeg_priv *priv = (void *)object->engine;
+       struct nv44_mpeg_chan *chan = (void *)object;
+       u32 inst = 0x80000000 | nv_gpuobj(chan)->addr >> 4;
+
+       nv_mask(priv, 0x00b32c, 0x00000001, 0x00000000);
+       if (nv_rd32(priv, 0x00b318) == inst)
+               nv_mask(priv, 0x00b318, 0x80000000, 0x00000000);
+       nv_mask(priv, 0x00b32c, 0x00000001, 0x00000001);
+       return 0;
+}
+
+static struct nvkm_oclass
+nv44_mpeg_cclass = {
+       .handle = NV_ENGCTX(MPEG, 0x44),
+       .ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = nv44_mpeg_context_ctor,
+               .dtor = _nvkm_mpeg_context_dtor,
+               .init = _nvkm_mpeg_context_init,
+               .fini = nv44_mpeg_context_fini,
+               .rd32 = _nvkm_mpeg_context_rd32,
+               .wr32 = _nvkm_mpeg_context_wr32,
+       },
+};
+
+/*******************************************************************************
+ * PMPEG engine/subdev functions
+ ******************************************************************************/
+
+static void
+nv44_mpeg_intr(struct nvkm_subdev *subdev)
+{
+       struct nvkm_fifo *pfifo = nvkm_fifo(subdev);
+       struct nvkm_engine *engine = nv_engine(subdev);
+       struct nvkm_object *engctx;
+       struct nvkm_handle *handle;
+       struct nv44_mpeg_priv *priv = (void *)subdev;
+       u32 inst = nv_rd32(priv, 0x00b318) & 0x000fffff;
+       u32 stat = nv_rd32(priv, 0x00b100);
+       u32 type = nv_rd32(priv, 0x00b230);
+       u32 mthd = nv_rd32(priv, 0x00b234);
+       u32 data = nv_rd32(priv, 0x00b238);
+       u32 show = stat;
+       int chid;
+
+       engctx = nvkm_engctx_get(engine, inst);
+       chid   = pfifo->chid(pfifo, engctx);
+
+       if (stat & 0x01000000) {
+               /* happens on initial binding of the object */
+               if (type == 0x00000020 && mthd == 0x0000) {
+                       nv_mask(priv, 0x00b308, 0x00000000, 0x00000000);
+                       show &= ~0x01000000;
+               }
+
+               if (type == 0x00000010) {
+                       handle = nvkm_handle_get_class(engctx, 0x3174);
+                       if (handle && !nv_call(handle->object, mthd, data))
+                               show &= ~0x01000000;
+                       nvkm_handle_put(handle);
+               }
+       }
+
+       nv_wr32(priv, 0x00b100, stat);
+       nv_wr32(priv, 0x00b230, 0x00000001);
+
+       if (show) {
+               nv_error(priv,
+                        "ch %d [0x%08x %s] 0x%08x 0x%08x 0x%08x 0x%08x\n",
+                        chid, inst << 4, nvkm_client_name(engctx), stat,
+                        type, mthd, data);
+       }
+
+       nvkm_engctx_put(engctx);
+}
+
+static void
+nv44_mpeg_me_intr(struct nvkm_subdev *subdev)
+{
+       struct nv44_mpeg_priv *priv = (void *)subdev;
+       u32 stat;
+
+       if ((stat = nv_rd32(priv, 0x00b100)))
+               nv44_mpeg_intr(subdev);
+
+       if ((stat = nv_rd32(priv, 0x00b800))) {
+               nv_error(priv, "PMSRCH 0x%08x\n", stat);
+               nv_wr32(priv, 0x00b800, stat);
+       }
+}
+
+static int
+nv44_mpeg_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+              struct nvkm_oclass *oclass, void *data, u32 size,
+              struct nvkm_object **pobject)
+{
+       struct nv44_mpeg_priv *priv;
+       int ret;
+
+       ret = nvkm_mpeg_create(parent, engine, oclass, &priv);
+       *pobject = nv_object(priv);
+       if (ret)
+               return ret;
+
+       nv_subdev(priv)->unit = 0x00000002;
+       nv_subdev(priv)->intr = nv44_mpeg_me_intr;
+       nv_engine(priv)->cclass = &nv44_mpeg_cclass;
+       nv_engine(priv)->sclass = nv40_mpeg_sclass;
+       nv_engine(priv)->tile_prog = nv31_mpeg_tile_prog;
+       return 0;
+}
+
+struct nvkm_oclass
+nv44_mpeg_oclass = {
+       .handle = NV_ENGINE(MPEG, 0x44),
+       .ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = nv44_mpeg_ctor,
+               .dtor = _nvkm_mpeg_dtor,
+               .init = nv31_mpeg_init,
+               .fini = _nvkm_mpeg_fini,
+       },
+};
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/mpeg/nv50.c b/drivers/gpu/drm/nouveau/nvkm/engine/mpeg/nv50.c
new file mode 100644 (file)
index 0000000..b3463f3
--- /dev/null
@@ -0,0 +1,225 @@
+/*
+ * Copyright 2012 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 <engine/mpeg.h>
+
+#include <subdev/bar.h>
+#include <subdev/timer.h>
+
+struct nv50_mpeg_priv {
+       struct nvkm_mpeg base;
+};
+
+struct nv50_mpeg_chan {
+       struct nvkm_mpeg_chan base;
+};
+
+/*******************************************************************************
+ * MPEG object classes
+ ******************************************************************************/
+
+static int
+nv50_mpeg_object_ctor(struct nvkm_object *parent,
+                     struct nvkm_object *engine,
+                     struct nvkm_oclass *oclass, void *data, u32 size,
+                     struct nvkm_object **pobject)
+{
+       struct nvkm_gpuobj *obj;
+       int ret;
+
+       ret = nvkm_gpuobj_create(parent, engine, oclass, 0, parent,
+                                16, 16, 0, &obj);
+       *pobject = nv_object(obj);
+       if (ret)
+               return ret;
+
+       nv_wo32(obj, 0x00, nv_mclass(obj));
+       nv_wo32(obj, 0x04, 0x00000000);
+       nv_wo32(obj, 0x08, 0x00000000);
+       nv_wo32(obj, 0x0c, 0x00000000);
+       return 0;
+}
+
+struct nvkm_ofuncs
+nv50_mpeg_ofuncs = {
+       .ctor = nv50_mpeg_object_ctor,
+       .dtor = _nvkm_gpuobj_dtor,
+       .init = _nvkm_gpuobj_init,
+       .fini = _nvkm_gpuobj_fini,
+       .rd32 = _nvkm_gpuobj_rd32,
+       .wr32 = _nvkm_gpuobj_wr32,
+};
+
+static struct nvkm_oclass
+nv50_mpeg_sclass[] = {
+       { 0x3174, &nv50_mpeg_ofuncs },
+       {}
+};
+
+/*******************************************************************************
+ * PMPEG context
+ ******************************************************************************/
+
+int
+nv50_mpeg_context_ctor(struct nvkm_object *parent,
+                      struct nvkm_object *engine,
+                      struct nvkm_oclass *oclass, void *data, u32 size,
+                      struct nvkm_object **pobject)
+{
+       struct nvkm_bar *bar = nvkm_bar(parent);
+       struct nv50_mpeg_chan *chan;
+       int ret;
+
+       ret = nvkm_mpeg_context_create(parent, engine, oclass, NULL, 128 * 4,
+                                      0, NVOBJ_FLAG_ZERO_ALLOC, &chan);
+       *pobject = nv_object(chan);
+       if (ret)
+               return ret;
+
+       nv_wo32(chan, 0x0070, 0x00801ec1);
+       nv_wo32(chan, 0x007c, 0x0000037c);
+       bar->flush(bar);
+       return 0;
+}
+
+static struct nvkm_oclass
+nv50_mpeg_cclass = {
+       .handle = NV_ENGCTX(MPEG, 0x50),
+       .ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = nv50_mpeg_context_ctor,
+               .dtor = _nvkm_mpeg_context_dtor,
+               .init = _nvkm_mpeg_context_init,
+               .fini = _nvkm_mpeg_context_fini,
+               .rd32 = _nvkm_mpeg_context_rd32,
+               .wr32 = _nvkm_mpeg_context_wr32,
+       },
+};
+
+/*******************************************************************************
+ * PMPEG engine/subdev functions
+ ******************************************************************************/
+
+void
+nv50_mpeg_intr(struct nvkm_subdev *subdev)
+{
+       struct nv50_mpeg_priv *priv = (void *)subdev;
+       u32 stat = nv_rd32(priv, 0x00b100);
+       u32 type = nv_rd32(priv, 0x00b230);
+       u32 mthd = nv_rd32(priv, 0x00b234);
+       u32 data = nv_rd32(priv, 0x00b238);
+       u32 show = stat;
+
+       if (stat & 0x01000000) {
+               /* happens on initial binding of the object */
+               if (type == 0x00000020 && mthd == 0x0000) {
+                       nv_wr32(priv, 0x00b308, 0x00000100);
+                       show &= ~0x01000000;
+               }
+       }
+
+       if (show) {
+               nv_info(priv, "0x%08x 0x%08x 0x%08x 0x%08x\n",
+                       stat, type, mthd, data);
+       }
+
+       nv_wr32(priv, 0x00b100, stat);
+       nv_wr32(priv, 0x00b230, 0x00000001);
+}
+
+static void
+nv50_vpe_intr(struct nvkm_subdev *subdev)
+{
+       struct nv50_mpeg_priv *priv = (void *)subdev;
+
+       if (nv_rd32(priv, 0x00b100))
+               nv50_mpeg_intr(subdev);
+
+       if (nv_rd32(priv, 0x00b800)) {
+               u32 stat = nv_rd32(priv, 0x00b800);
+               nv_info(priv, "PMSRCH: 0x%08x\n", stat);
+               nv_wr32(priv, 0xb800, stat);
+       }
+}
+
+static int
+nv50_mpeg_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+              struct nvkm_oclass *oclass, void *data, u32 size,
+              struct nvkm_object **pobject)
+{
+       struct nv50_mpeg_priv *priv;
+       int ret;
+
+       ret = nvkm_mpeg_create(parent, engine, oclass, &priv);
+       *pobject = nv_object(priv);
+       if (ret)
+               return ret;
+
+       nv_subdev(priv)->unit = 0x00400002;
+       nv_subdev(priv)->intr = nv50_vpe_intr;
+       nv_engine(priv)->cclass = &nv50_mpeg_cclass;
+       nv_engine(priv)->sclass = nv50_mpeg_sclass;
+       return 0;
+}
+
+int
+nv50_mpeg_init(struct nvkm_object *object)
+{
+       struct nv50_mpeg_priv *priv = (void *)object;
+       int ret;
+
+       ret = nvkm_mpeg_init(&priv->base);
+       if (ret)
+               return ret;
+
+       nv_wr32(priv, 0x00b32c, 0x00000000);
+       nv_wr32(priv, 0x00b314, 0x00000100);
+       nv_wr32(priv, 0x00b0e0, 0x0000001a);
+
+       nv_wr32(priv, 0x00b220, 0x00000044);
+       nv_wr32(priv, 0x00b300, 0x00801ec1);
+       nv_wr32(priv, 0x00b390, 0x00000000);
+       nv_wr32(priv, 0x00b394, 0x00000000);
+       nv_wr32(priv, 0x00b398, 0x00000000);
+       nv_mask(priv, 0x00b32c, 0x00000001, 0x00000001);
+
+       nv_wr32(priv, 0x00b100, 0xffffffff);
+       nv_wr32(priv, 0x00b140, 0xffffffff);
+
+       if (!nv_wait(priv, 0x00b200, 0x00000001, 0x00000000)) {
+               nv_error(priv, "timeout 0x%08x\n", nv_rd32(priv, 0x00b200));
+               return -EBUSY;
+       }
+
+       return 0;
+}
+
+struct nvkm_oclass
+nv50_mpeg_oclass = {
+       .handle = NV_ENGINE(MPEG, 0x50),
+       .ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = nv50_mpeg_ctor,
+               .dtor = _nvkm_mpeg_dtor,
+               .init = nv50_mpeg_init,
+               .fini = _nvkm_mpeg_fini,
+       },
+};
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/mspdec/Kbuild b/drivers/gpu/drm/nouveau/nvkm/engine/mspdec/Kbuild
new file mode 100644 (file)
index 0000000..c59c83a
--- /dev/null
@@ -0,0 +1,3 @@
+nvkm-y += nvkm/engine/mspdec/g98.o
+nvkm-y += nvkm/engine/mspdec/gf100.o
+nvkm-y += nvkm/engine/mspdec/gk104.o
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/mspdec/g98.c b/drivers/gpu/drm/nouveau/nvkm/engine/mspdec/g98.c
new file mode 100644 (file)
index 0000000..2174577
--- /dev/null
@@ -0,0 +1,109 @@
+/*
+ * Copyright 2012 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, Maarten Lankhorst, Ilia Mirkin
+ */
+#include <engine/mspdec.h>
+#include <engine/falcon.h>
+
+struct g98_mspdec_priv {
+       struct nvkm_falcon base;
+};
+
+/*******************************************************************************
+ * MSPDEC object classes
+ ******************************************************************************/
+
+static struct nvkm_oclass
+g98_mspdec_sclass[] = {
+       { 0x88b2, &nvkm_object_ofuncs },
+       { 0x85b2, &nvkm_object_ofuncs },
+       {},
+};
+
+/*******************************************************************************
+ * PMSPDEC context
+ ******************************************************************************/
+
+static struct nvkm_oclass
+g98_mspdec_cclass = {
+       .handle = NV_ENGCTX(MSPDEC, 0x98),
+       .ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = _nvkm_falcon_context_ctor,
+               .dtor = _nvkm_falcon_context_dtor,
+               .init = _nvkm_falcon_context_init,
+               .fini = _nvkm_falcon_context_fini,
+               .rd32 = _nvkm_falcon_context_rd32,
+               .wr32 = _nvkm_falcon_context_wr32,
+       },
+};
+
+/*******************************************************************************
+ * PMSPDEC engine/subdev functions
+ ******************************************************************************/
+
+static int
+g98_mspdec_init(struct nvkm_object *object)
+{
+       struct g98_mspdec_priv *priv = (void *)object;
+       int ret;
+
+       ret = nvkm_falcon_init(&priv->base);
+       if (ret)
+               return ret;
+
+       nv_wr32(priv, 0x085010, 0x0000ffd2);
+       nv_wr32(priv, 0x08501c, 0x0000fff2);
+       return 0;
+}
+
+static int
+g98_mspdec_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+               struct nvkm_oclass *oclass, void *data, u32 size,
+               struct nvkm_object **pobject)
+{
+       struct g98_mspdec_priv *priv;
+       int ret;
+
+       ret = nvkm_falcon_create(parent, engine, oclass, 0x085000, true,
+                                "PMSPDEC", "mspdec", &priv);
+       *pobject = nv_object(priv);
+       if (ret)
+               return ret;
+
+       nv_subdev(priv)->unit = 0x01020000;
+       nv_engine(priv)->cclass = &g98_mspdec_cclass;
+       nv_engine(priv)->sclass = g98_mspdec_sclass;
+       return 0;
+}
+
+struct nvkm_oclass
+g98_mspdec_oclass = {
+       .handle = NV_ENGINE(MSPDEC, 0x98),
+       .ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = g98_mspdec_ctor,
+               .dtor = _nvkm_falcon_dtor,
+               .init = g98_mspdec_init,
+               .fini = _nvkm_falcon_fini,
+               .rd32 = _nvkm_falcon_rd32,
+               .wr32 = _nvkm_falcon_wr32,
+       },
+};
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/mspdec/gf100.c b/drivers/gpu/drm/nouveau/nvkm/engine/mspdec/gf100.c
new file mode 100644 (file)
index 0000000..c814a5f
--- /dev/null
@@ -0,0 +1,109 @@
+/*
+ * Copyright 2012 Maarten Lankhorst
+ *
+ * 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: Maarten Lankhorst
+ */
+#include <engine/mspdec.h>
+#include <engine/falcon.h>
+
+struct gf100_mspdec_priv {
+       struct nvkm_falcon base;
+};
+
+/*******************************************************************************
+ * MSPDEC object classes
+ ******************************************************************************/
+
+static struct nvkm_oclass
+gf100_mspdec_sclass[] = {
+       { 0x90b2, &nvkm_object_ofuncs },
+       {},
+};
+
+/*******************************************************************************
+ * PMSPDEC context
+ ******************************************************************************/
+
+static struct nvkm_oclass
+gf100_mspdec_cclass = {
+       .handle = NV_ENGCTX(MSPDEC, 0xc0),
+       .ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = _nvkm_falcon_context_ctor,
+               .dtor = _nvkm_falcon_context_dtor,
+               .init = _nvkm_falcon_context_init,
+               .fini = _nvkm_falcon_context_fini,
+               .rd32 = _nvkm_falcon_context_rd32,
+               .wr32 = _nvkm_falcon_context_wr32,
+       },
+};
+
+/*******************************************************************************
+ * PMSPDEC engine/subdev functions
+ ******************************************************************************/
+
+static int
+gf100_mspdec_init(struct nvkm_object *object)
+{
+       struct gf100_mspdec_priv *priv = (void *)object;
+       int ret;
+
+       ret = nvkm_falcon_init(&priv->base);
+       if (ret)
+               return ret;
+
+       nv_wr32(priv, 0x085010, 0x0000fff2);
+       nv_wr32(priv, 0x08501c, 0x0000fff2);
+       return 0;
+}
+
+static int
+gf100_mspdec_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+                 struct nvkm_oclass *oclass, void *data, u32 size,
+                 struct nvkm_object **pobject)
+{
+       struct gf100_mspdec_priv *priv;
+       int ret;
+
+       ret = nvkm_falcon_create(parent, engine, oclass, 0x085000, true,
+                                "PMSPDEC", "mspdec", &priv);
+       *pobject = nv_object(priv);
+       if (ret)
+               return ret;
+
+       nv_subdev(priv)->unit = 0x00020000;
+       nv_subdev(priv)->intr = nvkm_falcon_intr;
+       nv_engine(priv)->cclass = &gf100_mspdec_cclass;
+       nv_engine(priv)->sclass = gf100_mspdec_sclass;
+       return 0;
+}
+
+struct nvkm_oclass
+gf100_mspdec_oclass = {
+       .handle = NV_ENGINE(MSPDEC, 0xc0),
+       .ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = gf100_mspdec_ctor,
+               .dtor = _nvkm_falcon_dtor,
+               .init = gf100_mspdec_init,
+               .fini = _nvkm_falcon_fini,
+               .rd32 = _nvkm_falcon_rd32,
+               .wr32 = _nvkm_falcon_wr32,
+       },
+};
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/mspdec/gk104.c b/drivers/gpu/drm/nouveau/nvkm/engine/mspdec/gk104.c
new file mode 100644 (file)
index 0000000..9799206
--- /dev/null
@@ -0,0 +1,109 @@
+/*
+ * Copyright 2012 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 <engine/mspdec.h>
+#include <engine/falcon.h>
+
+struct gk104_mspdec_priv {
+       struct nvkm_falcon base;
+};
+
+/*******************************************************************************
+ * MSPDEC object classes
+ ******************************************************************************/
+
+static struct nvkm_oclass
+gk104_mspdec_sclass[] = {
+       { 0x95b2, &nvkm_object_ofuncs },
+       {},
+};
+
+/*******************************************************************************
+ * PMSPDEC context
+ ******************************************************************************/
+
+static struct nvkm_oclass
+gk104_mspdec_cclass = {
+       .handle = NV_ENGCTX(MSPDEC, 0xe0),
+       .ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = _nvkm_falcon_context_ctor,
+               .dtor = _nvkm_falcon_context_dtor,
+               .init = _nvkm_falcon_context_init,
+               .fini = _nvkm_falcon_context_fini,
+               .rd32 = _nvkm_falcon_context_rd32,
+               .wr32 = _nvkm_falcon_context_wr32,
+       },
+};
+
+/*******************************************************************************
+ * PMSPDEC engine/subdev functions
+ ******************************************************************************/
+
+static int
+gk104_mspdec_init(struct nvkm_object *object)
+{
+       struct gk104_mspdec_priv *priv = (void *)object;
+       int ret;
+
+       ret = nvkm_falcon_init(&priv->base);
+       if (ret)
+               return ret;
+
+       nv_wr32(priv, 0x085010, 0x0000fff2);
+       nv_wr32(priv, 0x08501c, 0x0000fff2);
+       return 0;
+}
+
+static int
+gk104_mspdec_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+                 struct nvkm_oclass *oclass, void *data, u32 size,
+                 struct nvkm_object **pobject)
+{
+       struct gk104_mspdec_priv *priv;
+       int ret;
+
+       ret = nvkm_falcon_create(parent, engine, oclass, 0x085000, true,
+                                "PMSPDEC", "mspdec", &priv);
+       *pobject = nv_object(priv);
+       if (ret)
+               return ret;
+
+       nv_subdev(priv)->unit = 0x00020000;
+       nv_subdev(priv)->intr = nvkm_falcon_intr;
+       nv_engine(priv)->cclass = &gk104_mspdec_cclass;
+       nv_engine(priv)->sclass = gk104_mspdec_sclass;
+       return 0;
+}
+
+struct nvkm_oclass
+gk104_mspdec_oclass = {
+       .handle = NV_ENGINE(MSPDEC, 0xe0),
+       .ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = gk104_mspdec_ctor,
+               .dtor = _nvkm_falcon_dtor,
+               .init = gk104_mspdec_init,
+               .fini = _nvkm_falcon_fini,
+               .rd32 = _nvkm_falcon_rd32,
+               .wr32 = _nvkm_falcon_wr32,
+       },
+};
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/msppp/Kbuild b/drivers/gpu/drm/nouveau/nvkm/engine/msppp/Kbuild
new file mode 100644 (file)
index 0000000..4576a9e
--- /dev/null
@@ -0,0 +1,2 @@
+nvkm-y += nvkm/engine/msppp/g98.o
+nvkm-y += nvkm/engine/msppp/gf100.o
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/msppp/g98.c b/drivers/gpu/drm/nouveau/nvkm/engine/msppp/g98.c
new file mode 100644 (file)
index 0000000..7a602a2
--- /dev/null
@@ -0,0 +1,109 @@
+/*
+ * Copyright 2012 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, Maarten Lankhorst, Ilia Mirkin
+ */
+#include <engine/msppp.h>
+#include <engine/falcon.h>
+
+struct g98_msppp_priv {
+       struct nvkm_falcon base;
+};
+
+/*******************************************************************************
+ * MSPPP object classes
+ ******************************************************************************/
+
+static struct nvkm_oclass
+g98_msppp_sclass[] = {
+       { 0x88b3, &nvkm_object_ofuncs },
+       { 0x85b3, &nvkm_object_ofuncs },
+       {},
+};
+
+/*******************************************************************************
+ * PMSPPP context
+ ******************************************************************************/
+
+static struct nvkm_oclass
+g98_msppp_cclass = {
+       .handle = NV_ENGCTX(MSPPP, 0x98),
+       .ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = _nvkm_falcon_context_ctor,
+               .dtor = _nvkm_falcon_context_dtor,
+               .init = _nvkm_falcon_context_init,
+               .fini = _nvkm_falcon_context_fini,
+               .rd32 = _nvkm_falcon_context_rd32,
+               .wr32 = _nvkm_falcon_context_wr32,
+       },
+};
+
+/*******************************************************************************
+ * PMSPPP engine/subdev functions
+ ******************************************************************************/
+
+static int
+g98_msppp_init(struct nvkm_object *object)
+{
+       struct g98_msppp_priv *priv = (void *)object;
+       int ret;
+
+       ret = nvkm_falcon_init(&priv->base);
+       if (ret)
+               return ret;
+
+       nv_wr32(priv, 0x086010, 0x0000ffd2);
+       nv_wr32(priv, 0x08601c, 0x0000fff2);
+       return 0;
+}
+
+static int
+g98_msppp_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+              struct nvkm_oclass *oclass, void *data, u32 size,
+              struct nvkm_object **pobject)
+{
+       struct g98_msppp_priv *priv;
+       int ret;
+
+       ret = nvkm_falcon_create(parent, engine, oclass, 0x086000, true,
+                                "PMSPPP", "msppp", &priv);
+       *pobject = nv_object(priv);
+       if (ret)
+               return ret;
+
+       nv_subdev(priv)->unit = 0x00400002;
+       nv_engine(priv)->cclass = &g98_msppp_cclass;
+       nv_engine(priv)->sclass = g98_msppp_sclass;
+       return 0;
+}
+
+struct nvkm_oclass
+g98_msppp_oclass = {
+       .handle = NV_ENGINE(MSPPP, 0x98),
+       .ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = g98_msppp_ctor,
+               .dtor = _nvkm_falcon_dtor,
+               .init = g98_msppp_init,
+               .fini = _nvkm_falcon_fini,
+               .rd32 = _nvkm_falcon_rd32,
+               .wr32 = _nvkm_falcon_wr32,
+       },
+};
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/msppp/gf100.c b/drivers/gpu/drm/nouveau/nvkm/engine/msppp/gf100.c
new file mode 100644 (file)
index 0000000..6047bae
--- /dev/null
@@ -0,0 +1,109 @@
+/*
+ * Copyright 2012 Maarten Lankhorst
+ *
+ * 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: Maarten Lankhorst
+ */
+#include <engine/msppp.h>
+#include <engine/falcon.h>
+
+struct gf100_msppp_priv {
+       struct nvkm_falcon base;
+};
+
+/*******************************************************************************
+ * MSPPP object classes
+ ******************************************************************************/
+
+static struct nvkm_oclass
+gf100_msppp_sclass[] = {
+       { 0x90b3, &nvkm_object_ofuncs },
+       {},
+};
+
+/*******************************************************************************
+ * PMSPPP context
+ ******************************************************************************/
+
+static struct nvkm_oclass
+gf100_msppp_cclass = {
+       .handle = NV_ENGCTX(MSPPP, 0xc0),
+       .ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = _nvkm_falcon_context_ctor,
+               .dtor = _nvkm_falcon_context_dtor,
+               .init = _nvkm_falcon_context_init,
+               .fini = _nvkm_falcon_context_fini,
+               .rd32 = _nvkm_falcon_context_rd32,
+               .wr32 = _nvkm_falcon_context_wr32,
+       },
+};
+
+/*******************************************************************************
+ * PMSPPP engine/subdev functions
+ ******************************************************************************/
+
+static int
+gf100_msppp_init(struct nvkm_object *object)
+{
+       struct gf100_msppp_priv *priv = (void *)object;
+       int ret;
+
+       ret = nvkm_falcon_init(&priv->base);
+       if (ret)
+               return ret;
+
+       nv_wr32(priv, 0x086010, 0x0000fff2);
+       nv_wr32(priv, 0x08601c, 0x0000fff2);
+       return 0;
+}
+
+static int
+gf100_msppp_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+                struct nvkm_oclass *oclass, void *data, u32 size,
+                struct nvkm_object **pobject)
+{
+       struct gf100_msppp_priv *priv;
+       int ret;
+
+       ret = nvkm_falcon_create(parent, engine, oclass, 0x086000, true,
+                                "PMSPPP", "msppp", &priv);
+       *pobject = nv_object(priv);
+       if (ret)
+               return ret;
+
+       nv_subdev(priv)->unit = 0x00000002;
+       nv_subdev(priv)->intr = nvkm_falcon_intr;
+       nv_engine(priv)->cclass = &gf100_msppp_cclass;
+       nv_engine(priv)->sclass = gf100_msppp_sclass;
+       return 0;
+}
+
+struct nvkm_oclass
+gf100_msppp_oclass = {
+       .handle = NV_ENGINE(MSPPP, 0xc0),
+       .ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = gf100_msppp_ctor,
+               .dtor = _nvkm_falcon_dtor,
+               .init = gf100_msppp_init,
+               .fini = _nvkm_falcon_fini,
+               .rd32 = _nvkm_falcon_rd32,
+               .wr32 = _nvkm_falcon_wr32,
+       },
+};
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/msvld/Kbuild b/drivers/gpu/drm/nouveau/nvkm/engine/msvld/Kbuild
new file mode 100644 (file)
index 0000000..0c98110
--- /dev/null
@@ -0,0 +1,3 @@
+nvkm-y += nvkm/engine/msvld/g98.o
+nvkm-y += nvkm/engine/msvld/gf100.o
+nvkm-y += nvkm/engine/msvld/gk104.o
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/msvld/g98.c b/drivers/gpu/drm/nouveau/nvkm/engine/msvld/g98.c
new file mode 100644 (file)
index 0000000..c8a6b4e
--- /dev/null
@@ -0,0 +1,110 @@
+/*
+ * Copyright 2012 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, Maarten Lankhorst, Ilia Mirkin
+ */
+#include <engine/msvld.h>
+#include <engine/falcon.h>
+
+struct g98_msvld_priv {
+       struct nvkm_falcon base;
+};
+
+/*******************************************************************************
+ * MSVLD object classes
+ ******************************************************************************/
+
+static struct nvkm_oclass
+g98_msvld_sclass[] = {
+       { 0x88b1, &nvkm_object_ofuncs },
+       { 0x85b1, &nvkm_object_ofuncs },
+       { 0x86b1, &nvkm_object_ofuncs },
+       {},
+};
+
+/*******************************************************************************
+ * PMSVLD context
+ ******************************************************************************/
+
+static struct nvkm_oclass
+g98_msvld_cclass = {
+       .handle = NV_ENGCTX(MSVLD, 0x98),
+       .ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = _nvkm_falcon_context_ctor,
+               .dtor = _nvkm_falcon_context_dtor,
+               .init = _nvkm_falcon_context_init,
+               .fini = _nvkm_falcon_context_fini,
+               .rd32 = _nvkm_falcon_context_rd32,
+               .wr32 = _nvkm_falcon_context_wr32,
+       },
+};
+
+/*******************************************************************************
+ * PMSVLD engine/subdev functions
+ ******************************************************************************/
+
+static int
+g98_msvld_init(struct nvkm_object *object)
+{
+       struct g98_msvld_priv *priv = (void *)object;
+       int ret;
+
+       ret = nvkm_falcon_init(&priv->base);
+       if (ret)
+               return ret;
+
+       nv_wr32(priv, 0x084010, 0x0000ffd2);
+       nv_wr32(priv, 0x08401c, 0x0000fff2);
+       return 0;
+}
+
+static int
+g98_msvld_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+              struct nvkm_oclass *oclass, void *data, u32 size,
+              struct nvkm_object **pobject)
+{
+       struct g98_msvld_priv *priv;
+       int ret;
+
+       ret = nvkm_falcon_create(parent, engine, oclass, 0x084000, true,
+                                "PMSVLD", "msvld", &priv);
+       *pobject = nv_object(priv);
+       if (ret)
+               return ret;
+
+       nv_subdev(priv)->unit = 0x04008000;
+       nv_engine(priv)->cclass = &g98_msvld_cclass;
+       nv_engine(priv)->sclass = g98_msvld_sclass;
+       return 0;
+}
+
+struct nvkm_oclass
+g98_msvld_oclass = {
+       .handle = NV_ENGINE(MSVLD, 0x98),
+       .ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = g98_msvld_ctor,
+               .dtor = _nvkm_falcon_dtor,
+               .init = g98_msvld_init,
+               .fini = _nvkm_falcon_fini,
+               .rd32 = _nvkm_falcon_rd32,
+               .wr32 = _nvkm_falcon_wr32,
+       },
+};
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/msvld/gf100.c b/drivers/gpu/drm/nouveau/nvkm/engine/msvld/gf100.c
new file mode 100644 (file)
index 0000000..b8d1e0f
--- /dev/null
@@ -0,0 +1,109 @@
+/*
+ * Copyright 2012 Maarten Lankhorst
+ *
+ * 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: Maarten Lankhorst
+ */
+#include <engine/msvld.h>
+#include <engine/falcon.h>
+
+struct gf100_msvld_priv {
+       struct nvkm_falcon base;
+};
+
+/*******************************************************************************
+ * MSVLD object classes
+ ******************************************************************************/
+
+static struct nvkm_oclass
+gf100_msvld_sclass[] = {
+       { 0x90b1, &nvkm_object_ofuncs },
+       {},
+};
+
+/*******************************************************************************
+ * PMSVLD context
+ ******************************************************************************/
+
+static struct nvkm_oclass
+gf100_msvld_cclass = {
+       .handle = NV_ENGCTX(MSVLD, 0xc0),
+       .ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = _nvkm_falcon_context_ctor,
+               .dtor = _nvkm_falcon_context_dtor,
+               .init = _nvkm_falcon_context_init,
+               .fini = _nvkm_falcon_context_fini,
+               .rd32 = _nvkm_falcon_context_rd32,
+               .wr32 = _nvkm_falcon_context_wr32,
+       },
+};
+
+/*******************************************************************************
+ * PMSVLD engine/subdev functions
+ ******************************************************************************/
+
+static int
+gf100_msvld_init(struct nvkm_object *object)
+{
+       struct gf100_msvld_priv *priv = (void *)object;
+       int ret;
+
+       ret = nvkm_falcon_init(&priv->base);
+       if (ret)
+               return ret;
+
+       nv_wr32(priv, 0x084010, 0x0000fff2);
+       nv_wr32(priv, 0x08401c, 0x0000fff2);
+       return 0;
+}
+
+static int
+gf100_msvld_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+                struct nvkm_oclass *oclass, void *data, u32 size,
+                struct nvkm_object **pobject)
+{
+       struct gf100_msvld_priv *priv;
+       int ret;
+
+       ret = nvkm_falcon_create(parent, engine, oclass, 0x084000, true,
+                                "PMSVLD", "msvld", &priv);
+       *pobject = nv_object(priv);
+       if (ret)
+               return ret;
+
+       nv_subdev(priv)->unit = 0x00008000;
+       nv_subdev(priv)->intr = nvkm_falcon_intr;
+       nv_engine(priv)->cclass = &gf100_msvld_cclass;
+       nv_engine(priv)->sclass = gf100_msvld_sclass;
+       return 0;
+}
+
+struct nvkm_oclass
+gf100_msvld_oclass = {
+       .handle = NV_ENGINE(MSVLD, 0xc0),
+       .ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = gf100_msvld_ctor,
+               .dtor = _nvkm_falcon_dtor,
+               .init = gf100_msvld_init,
+               .fini = _nvkm_falcon_fini,
+               .rd32 = _nvkm_falcon_rd32,
+               .wr32 = _nvkm_falcon_wr32,
+       },
+};
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/msvld/gk104.c b/drivers/gpu/drm/nouveau/nvkm/engine/msvld/gk104.c
new file mode 100644 (file)
index 0000000..a0b0927
--- /dev/null
@@ -0,0 +1,109 @@
+/*
+ * Copyright 2012 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 <engine/msvld.h>
+#include <engine/falcon.h>
+
+struct gk104_msvld_priv {
+       struct nvkm_falcon base;
+};
+
+/*******************************************************************************
+ * MSVLD object classes
+ ******************************************************************************/
+
+static struct nvkm_oclass
+gk104_msvld_sclass[] = {
+       { 0x95b1, &nvkm_object_ofuncs },
+       {},
+};
+
+/*******************************************************************************
+ * PMSVLD context
+ ******************************************************************************/
+
+static struct nvkm_oclass
+gk104_msvld_cclass = {
+       .handle = NV_ENGCTX(MSVLD, 0xe0),
+       .ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = _nvkm_falcon_context_ctor,
+               .dtor = _nvkm_falcon_context_dtor,
+               .init = _nvkm_falcon_context_init,
+               .fini = _nvkm_falcon_context_fini,
+               .rd32 = _nvkm_falcon_context_rd32,
+               .wr32 = _nvkm_falcon_context_wr32,
+       },
+};
+
+/*******************************************************************************
+ * PMSVLD engine/subdev functions
+ ******************************************************************************/
+
+static int
+gk104_msvld_init(struct nvkm_object *object)
+{
+       struct gk104_msvld_priv *priv = (void *)object;
+       int ret;
+
+       ret = nvkm_falcon_init(&priv->base);
+       if (ret)
+               return ret;
+
+       nv_wr32(priv, 0x084010, 0x0000fff2);
+       nv_wr32(priv, 0x08401c, 0x0000fff2);
+       return 0;
+}
+
+static int
+gk104_msvld_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+                struct nvkm_oclass *oclass, void *data, u32 size,
+                struct nvkm_object **pobject)
+{
+       struct gk104_msvld_priv *priv;
+       int ret;
+
+       ret = nvkm_falcon_create(parent, engine, oclass, 0x084000, true,
+                                "PMSVLD", "msvld", &priv);
+       *pobject = nv_object(priv);
+       if (ret)
+               return ret;
+
+       nv_subdev(priv)->unit = 0x00008000;
+       nv_subdev(priv)->intr = nvkm_falcon_intr;
+       nv_engine(priv)->cclass = &gk104_msvld_cclass;
+       nv_engine(priv)->sclass = gk104_msvld_sclass;
+       return 0;
+}
+
+struct nvkm_oclass
+gk104_msvld_oclass = {
+       .handle = NV_ENGINE(MSVLD, 0xe0),
+       .ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = gk104_msvld_ctor,
+               .dtor = _nvkm_falcon_dtor,
+               .init = gk104_msvld_init,
+               .fini = _nvkm_falcon_fini,
+               .rd32 = _nvkm_falcon_rd32,
+               .wr32 = _nvkm_falcon_wr32,
+       },
+};
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/pm/Kbuild b/drivers/gpu/drm/nouveau/nvkm/engine/pm/Kbuild
new file mode 100644 (file)
index 0000000..413b609
--- /dev/null
@@ -0,0 +1,9 @@
+nvkm-y += nvkm/engine/pm/base.o
+nvkm-y += nvkm/engine/pm/daemon.o
+nvkm-y += nvkm/engine/pm/nv40.o
+nvkm-y += nvkm/engine/pm/nv50.o
+nvkm-y += nvkm/engine/pm/g84.o
+nvkm-y += nvkm/engine/pm/gt215.o
+nvkm-y += nvkm/engine/pm/gf100.o
+nvkm-y += nvkm/engine/pm/gk104.o
+nvkm-y += nvkm/engine/pm/gk110.o
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/pm/base.c b/drivers/gpu/drm/nouveau/nvkm/engine/pm/base.c
new file mode 100644 (file)
index 0000000..2006c44
--- /dev/null
@@ -0,0 +1,476 @@
+/*
+ * Copyright 2013 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 "priv.h"
+
+#include <core/client.h>
+#include <core/device.h>
+#include <core/option.h>
+
+#include <nvif/class.h>
+#include <nvif/ioctl.h>
+#include <nvif/unpack.h>
+
+#define QUAD_MASK 0x0f
+#define QUAD_FREE 0x01
+
+static struct nvkm_perfsig *
+nvkm_perfsig_find_(struct nvkm_perfdom *dom, const char *name, u32 size)
+{
+       char path[64];
+       int i;
+
+       if (name[0] != '/') {
+               for (i = 0; i < dom->signal_nr; i++) {
+                       if ( dom->signal[i].name &&
+                           !strncmp(name, dom->signal[i].name, size))
+                               return &dom->signal[i];
+               }
+       } else {
+               for (i = 0; i < dom->signal_nr; i++) {
+                       snprintf(path, sizeof(path), "/%s/%02x", dom->name, i);
+                       if (!strncmp(name, path, size))
+                               return &dom->signal[i];
+               }
+       }
+
+       return NULL;
+}
+
+struct nvkm_perfsig *
+nvkm_perfsig_find(struct nvkm_pm *ppm, const char *name, u32 size,
+                 struct nvkm_perfdom **pdom)
+{
+       struct nvkm_perfdom *dom = *pdom;
+       struct nvkm_perfsig *sig;
+
+       if (dom == NULL) {
+               list_for_each_entry(dom, &ppm->domains, head) {
+                       sig = nvkm_perfsig_find_(dom, name, size);
+                       if (sig) {
+                               *pdom = dom;
+                               return sig;
+                       }
+               }
+
+               return NULL;
+       }
+
+       return nvkm_perfsig_find_(dom, name, size);
+}
+
+struct nvkm_perfctr *
+nvkm_perfsig_wrap(struct nvkm_pm *ppm, const char *name,
+                 struct nvkm_perfdom **pdom)
+{
+       struct nvkm_perfsig *sig;
+       struct nvkm_perfctr *ctr;
+
+       sig = nvkm_perfsig_find(ppm, name, strlen(name), pdom);
+       if (!sig)
+               return NULL;
+
+       ctr = kzalloc(sizeof(*ctr), GFP_KERNEL);
+       if (ctr) {
+               ctr->signal[0] = sig;
+               ctr->logic_op = 0xaaaa;
+       }
+
+       return ctr;
+}
+
+/*******************************************************************************
+ * Perfmon object classes
+ ******************************************************************************/
+static int
+nvkm_perfctr_query(struct nvkm_object *object, void *data, u32 size)
+{
+       union {
+               struct nvif_perfctr_query_v0 v0;
+       } *args = data;
+       struct nvkm_device *device = nv_device(object);
+       struct nvkm_pm *ppm = (void *)object->engine;
+       struct nvkm_perfdom *dom = NULL, *chk;
+       const bool all = nvkm_boolopt(device->cfgopt, "NvPmShowAll", false);
+       const bool raw = nvkm_boolopt(device->cfgopt, "NvPmUnnamed", all);
+       const char *name;
+       int tmp = 0, di, si;
+       int ret;
+
+       nv_ioctl(object, "perfctr query size %d\n", size);
+       if (nvif_unpack(args->v0, 0, 0, false)) {
+               nv_ioctl(object, "perfctr query vers %d iter %08x\n",
+                        args->v0.version, args->v0.iter);
+               di = (args->v0.iter & 0xff000000) >> 24;
+               si = (args->v0.iter & 0x00ffffff) - 1;
+       } else
+               return ret;
+
+       list_for_each_entry(chk, &ppm->domains, head) {
+               if (tmp++ == di) {
+                       dom = chk;
+                       break;
+               }
+       }
+
+       if (dom == NULL || si >= (int)dom->signal_nr)
+               return -EINVAL;
+
+       if (si >= 0) {
+               if (raw || !(name = dom->signal[si].name)) {
+                       snprintf(args->v0.name, sizeof(args->v0.name),
+                                "/%s/%02x", dom->name, si);
+               } else {
+                       strncpy(args->v0.name, name, sizeof(args->v0.name));
+               }
+       }
+
+       do {
+               while (++si < dom->signal_nr) {
+                       if (all || dom->signal[si].name) {
+                               args->v0.iter = (di << 24) | ++si;
+                               return 0;
+                       }
+               }
+               si = -1;
+               di = di + 1;
+               dom = list_entry(dom->head.next, typeof(*dom), head);
+       } while (&dom->head != &ppm->domains);
+
+       args->v0.iter = 0xffffffff;
+       return 0;
+}
+
+static int
+nvkm_perfctr_sample(struct nvkm_object *object, void *data, u32 size)
+{
+       union {
+               struct nvif_perfctr_sample none;
+       } *args = data;
+       struct nvkm_pm *ppm = (void *)object->engine;
+       struct nvkm_perfctr *ctr, *tmp;
+       struct nvkm_perfdom *dom;
+       int ret;
+
+       nv_ioctl(object, "perfctr sample size %d\n", size);
+       if (nvif_unvers(args->none)) {
+               nv_ioctl(object, "perfctr sample\n");
+       } else
+               return ret;
+       ppm->sequence++;
+
+       list_for_each_entry(dom, &ppm->domains, head) {
+               /* sample previous batch of counters */
+               if (dom->quad != QUAD_MASK) {
+                       dom->func->next(ppm, dom);
+                       tmp = NULL;
+                       while (!list_empty(&dom->list)) {
+                               ctr = list_first_entry(&dom->list,
+                                                      typeof(*ctr), head);
+                               if (ctr->slot < 0) break;
+                               if ( tmp && tmp == ctr) break;
+                               if (!tmp) tmp = ctr;
+                               dom->func->read(ppm, dom, ctr);
+                               ctr->slot  = -1;
+                               list_move_tail(&ctr->head, &dom->list);
+                       }
+               }
+
+               dom->quad = QUAD_MASK;
+
+               /* setup next batch of counters for sampling */
+               list_for_each_entry(ctr, &dom->list, head) {
+                       ctr->slot = ffs(dom->quad) - 1;
+                       if (ctr->slot < 0)
+                               break;
+                       dom->quad &= ~(QUAD_FREE << ctr->slot);
+                       dom->func->init(ppm, dom, ctr);
+               }
+
+               if (dom->quad != QUAD_MASK)
+                       dom->func->next(ppm, dom);
+       }
+
+       return 0;
+}
+
+static int
+nvkm_perfctr_read(struct nvkm_object *object, void *data, u32 size)
+{
+       union {
+               struct nvif_perfctr_read_v0 v0;
+       } *args = data;
+       struct nvkm_perfctr *ctr = (void *)object;
+       int ret;
+
+       nv_ioctl(object, "perfctr read size %d\n", size);
+       if (nvif_unpack(args->v0, 0, 0, false)) {
+               nv_ioctl(object, "perfctr read vers %d\n", args->v0.version);
+       } else
+               return ret;
+
+       if (!ctr->clk)
+               return -EAGAIN;
+
+       args->v0.clk = ctr->clk;
+       args->v0.ctr = ctr->ctr;
+       return 0;
+}
+
+static int
+nvkm_perfctr_mthd(struct nvkm_object *object, u32 mthd, void *data, u32 size)
+{
+       switch (mthd) {
+       case NVIF_PERFCTR_V0_QUERY:
+               return nvkm_perfctr_query(object, data, size);
+       case NVIF_PERFCTR_V0_SAMPLE:
+               return nvkm_perfctr_sample(object, data, size);
+       case NVIF_PERFCTR_V0_READ:
+               return nvkm_perfctr_read(object, data, size);
+       default:
+               break;
+       }
+       return -EINVAL;
+}
+
+static void
+nvkm_perfctr_dtor(struct nvkm_object *object)
+{
+       struct nvkm_perfctr *ctr = (void *)object;
+       if (ctr->head.next)
+               list_del(&ctr->head);
+       nvkm_object_destroy(&ctr->base);
+}
+
+static int
+nvkm_perfctr_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+                 struct nvkm_oclass *oclass, void *data, u32 size,
+                 struct nvkm_object **pobject)
+{
+       union {
+               struct nvif_perfctr_v0 v0;
+       } *args = data;
+       struct nvkm_pm *ppm = (void *)engine;
+       struct nvkm_perfdom *dom = NULL;
+       struct nvkm_perfsig *sig[4] = {};
+       struct nvkm_perfctr *ctr;
+       int ret, i;
+
+       nv_ioctl(parent, "create perfctr size %d\n", size);
+       if (nvif_unpack(args->v0, 0, 0, false)) {
+               nv_ioctl(parent, "create perfctr vers %d logic_op %04x\n",
+                        args->v0.version, args->v0.logic_op);
+       } else
+               return ret;
+
+       for (i = 0; i < ARRAY_SIZE(args->v0.name) && args->v0.name[i][0]; i++) {
+               sig[i] = nvkm_perfsig_find(ppm, args->v0.name[i],
+                                          strnlen(args->v0.name[i],
+                                                  sizeof(args->v0.name[i])),
+                                          &dom);
+               if (!sig[i])
+                       return -EINVAL;
+       }
+
+       ret = nvkm_object_create(parent, engine, oclass, 0, &ctr);
+       *pobject = nv_object(ctr);
+       if (ret)
+               return ret;
+
+       ctr->slot = -1;
+       ctr->logic_op = args->v0.logic_op;
+       ctr->signal[0] = sig[0];
+       ctr->signal[1] = sig[1];
+       ctr->signal[2] = sig[2];
+       ctr->signal[3] = sig[3];
+       if (dom)
+               list_add_tail(&ctr->head, &dom->list);
+       return 0;
+}
+
+static struct nvkm_ofuncs
+nvkm_perfctr_ofuncs = {
+       .ctor = nvkm_perfctr_ctor,
+       .dtor = nvkm_perfctr_dtor,
+       .init = nvkm_object_init,
+       .fini = nvkm_object_fini,
+       .mthd = nvkm_perfctr_mthd,
+};
+
+struct nvkm_oclass
+nvkm_pm_sclass[] = {
+       { .handle = NVIF_IOCTL_NEW_V0_PERFCTR,
+         .ofuncs = &nvkm_perfctr_ofuncs,
+       },
+       {},
+};
+
+/*******************************************************************************
+ * PPM context
+ ******************************************************************************/
+static void
+nvkm_perfctx_dtor(struct nvkm_object *object)
+{
+       struct nvkm_pm *ppm = (void *)object->engine;
+       mutex_lock(&nv_subdev(ppm)->mutex);
+       nvkm_engctx_destroy(&ppm->context->base);
+       ppm->context = NULL;
+       mutex_unlock(&nv_subdev(ppm)->mutex);
+}
+
+static int
+nvkm_perfctx_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+                 struct nvkm_oclass *oclass, void *data, u32 size,
+                 struct nvkm_object **pobject)
+{
+       struct nvkm_pm *ppm = (void *)engine;
+       struct nvkm_perfctx *ctx;
+       int ret;
+
+       ret = nvkm_engctx_create(parent, engine, oclass, NULL, 0, 0, 0, &ctx);
+       *pobject = nv_object(ctx);
+       if (ret)
+               return ret;
+
+       mutex_lock(&nv_subdev(ppm)->mutex);
+       if (ppm->context == NULL)
+               ppm->context = ctx;
+       mutex_unlock(&nv_subdev(ppm)->mutex);
+
+       if (ctx != ppm->context)
+               return -EBUSY;
+
+       return 0;
+}
+
+struct nvkm_oclass
+nvkm_pm_cclass = {
+       .handle = NV_ENGCTX(PM, 0x00),
+       .ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = nvkm_perfctx_ctor,
+               .dtor = nvkm_perfctx_dtor,
+               .init = _nvkm_engctx_init,
+               .fini = _nvkm_engctx_fini,
+       },
+};
+
+/*******************************************************************************
+ * PPM engine/subdev functions
+ ******************************************************************************/
+int
+nvkm_perfdom_new(struct nvkm_pm *ppm, const char *name, u32 mask,
+                u32 base, u32 size_unit, u32 size_domain,
+                const struct nvkm_specdom *spec)
+{
+       const struct nvkm_specdom *sdom;
+       const struct nvkm_specsig *ssig;
+       struct nvkm_perfdom *dom;
+       int i;
+
+       for (i = 0; i == 0 || mask; i++) {
+               u32 addr = base + (i * size_unit);
+               if (i && !(mask & (1 << i)))
+                       continue;
+
+               sdom = spec;
+               while (sdom->signal_nr) {
+                       dom = kzalloc(sizeof(*dom) + sdom->signal_nr *
+                                     sizeof(*dom->signal), GFP_KERNEL);
+                       if (!dom)
+                               return -ENOMEM;
+
+                       if (mask) {
+                               snprintf(dom->name, sizeof(dom->name),
+                                        "%s/%02x/%02x", name, i,
+                                        (int)(sdom - spec));
+                       } else {
+                               snprintf(dom->name, sizeof(dom->name),
+                                        "%s/%02x", name, (int)(sdom - spec));
+                       }
+
+                       list_add_tail(&dom->head, &ppm->domains);
+                       INIT_LIST_HEAD(&dom->list);
+                       dom->func = sdom->func;
+                       dom->addr = addr;
+                       dom->quad = QUAD_MASK;
+                       dom->signal_nr = sdom->signal_nr;
+
+                       ssig = (sdom++)->signal;
+                       while (ssig->name) {
+                               dom->signal[ssig->signal].name = ssig->name;
+                               ssig++;
+                       }
+
+                       addr += size_domain;
+               }
+
+               mask &= ~(1 << i);
+       }
+
+       return 0;
+}
+
+int
+_nvkm_pm_fini(struct nvkm_object *object, bool suspend)
+{
+       struct nvkm_pm *ppm = (void *)object;
+       return nvkm_engine_fini(&ppm->base, suspend);
+}
+
+int
+_nvkm_pm_init(struct nvkm_object *object)
+{
+       struct nvkm_pm *ppm = (void *)object;
+       return nvkm_engine_init(&ppm->base);
+}
+
+void
+_nvkm_pm_dtor(struct nvkm_object *object)
+{
+       struct nvkm_pm *ppm = (void *)object;
+       struct nvkm_perfdom *dom, *tmp;
+
+       list_for_each_entry_safe(dom, tmp, &ppm->domains, head) {
+               list_del(&dom->head);
+               kfree(dom);
+       }
+
+       nvkm_engine_destroy(&ppm->base);
+}
+
+int
+nvkm_pm_create_(struct nvkm_object *parent, struct nvkm_object *engine,
+               struct nvkm_oclass *oclass, int length, void **pobject)
+{
+       struct nvkm_pm *ppm;
+       int ret;
+
+       ret = nvkm_engine_create_(parent, engine, oclass, true, "PPM",
+                                 "pm", length, pobject);
+       ppm = *pobject;
+       if (ret)
+               return ret;
+
+       INIT_LIST_HEAD(&ppm->domains);
+       return 0;
+}
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/pm/daemon.c b/drivers/gpu/drm/nouveau/nvkm/engine/pm/daemon.c
new file mode 100644 (file)
index 0000000..a7a5f3a
--- /dev/null
@@ -0,0 +1,108 @@
+/*
+ * Copyright 2013 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 "priv.h"
+
+static void
+pwr_perfctr_init(struct nvkm_pm *ppm, struct nvkm_perfdom *dom,
+                struct nvkm_perfctr *ctr)
+{
+       u32 mask = 0x00000000;
+       u32 ctrl = 0x00000001;
+       int i;
+
+       for (i = 0; i < ARRAY_SIZE(ctr->signal) && ctr->signal[i]; i++)
+               mask |= 1 << (ctr->signal[i] - dom->signal);
+
+       nv_wr32(ppm, 0x10a504 + (ctr->slot * 0x10), mask);
+       nv_wr32(ppm, 0x10a50c + (ctr->slot * 0x10), ctrl);
+       nv_wr32(ppm, 0x10a50c + (ppm->last * 0x10), 0x00000003);
+}
+
+static void
+pwr_perfctr_read(struct nvkm_pm *ppm, struct nvkm_perfdom *dom,
+                struct nvkm_perfctr *ctr)
+{
+       ctr->ctr = ppm->pwr[ctr->slot];
+       ctr->clk = ppm->pwr[ppm->last];
+}
+
+static void
+pwr_perfctr_next(struct nvkm_pm *ppm, struct nvkm_perfdom *dom)
+{
+       int i;
+
+       for (i = 0; i <= ppm->last; i++) {
+               ppm->pwr[i] = nv_rd32(ppm, 0x10a508 + (i * 0x10));
+               nv_wr32(ppm, 0x10a508 + (i * 0x10), 0x80000000);
+       }
+}
+
+static const struct nvkm_funcdom
+pwr_perfctr_func = {
+       .init = pwr_perfctr_init,
+       .read = pwr_perfctr_read,
+       .next = pwr_perfctr_next,
+};
+
+const struct nvkm_specdom
+gt215_pm_pwr[] = {
+       { 0x20, (const struct nvkm_specsig[]) {
+                       { 0x00, "pwr_gr_idle" },
+                       { 0x04, "pwr_bsp_idle" },
+                       { 0x05, "pwr_vp_idle" },
+                       { 0x06, "pwr_ppp_idle" },
+                       { 0x13, "pwr_ce0_idle" },
+                       {}
+               }, &pwr_perfctr_func },
+       {}
+};
+
+const struct nvkm_specdom
+gf100_pm_pwr[] = {
+       { 0x20, (const struct nvkm_specsig[]) {
+                       { 0x00, "pwr_gr_idle" },
+                       { 0x04, "pwr_bsp_idle" },
+                       { 0x05, "pwr_vp_idle" },
+                       { 0x06, "pwr_ppp_idle" },
+                       { 0x13, "pwr_ce0_idle" },
+                       { 0x14, "pwr_ce1_idle" },
+                       {}
+               }, &pwr_perfctr_func },
+       {}
+};
+
+const struct nvkm_specdom
+gk104_pm_pwr[] = {
+       { 0x20, (const struct nvkm_specsig[]) {
+                       { 0x00, "pwr_gr_idle" },
+                       { 0x04, "pwr_bsp_idle" },
+                       { 0x05, "pwr_vp_idle" },
+                       { 0x06, "pwr_ppp_idle" },
+                       { 0x13, "pwr_ce0_idle" },
+                       { 0x14, "pwr_ce1_idle" },
+                       { 0x15, "pwr_ce2_idle" },
+                       {}
+               }, &pwr_perfctr_func },
+       {}
+};
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/pm/g84.c b/drivers/gpu/drm/nouveau/nvkm/engine/pm/g84.c
new file mode 100644 (file)
index 0000000..d54c670
--- /dev/null
@@ -0,0 +1,65 @@
+/*
+ * Copyright 2013 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 "nv40.h"
+
+static const struct nvkm_specdom
+g84_pm[] = {
+       { 0x20, (const struct nvkm_specsig[]) {
+                       {}
+               }, &nv40_perfctr_func },
+       { 0x20, (const struct nvkm_specsig[]) {
+                       {}
+               }, &nv40_perfctr_func },
+       { 0x20, (const struct nvkm_specsig[]) {
+                       {}
+               }, &nv40_perfctr_func },
+       { 0x20, (const struct nvkm_specsig[]) {
+                       {}
+               }, &nv40_perfctr_func },
+       { 0x20, (const struct nvkm_specsig[]) {
+                       {}
+               }, &nv40_perfctr_func },
+       { 0x20, (const struct nvkm_specsig[]) {
+                       {}
+               }, &nv40_perfctr_func },
+       { 0x20, (const struct nvkm_specsig[]) {
+                       {}
+               }, &nv40_perfctr_func },
+       { 0x20, (const struct nvkm_specsig[]) {
+                       {}
+               }, &nv40_perfctr_func },
+       {}
+};
+
+struct nvkm_oclass *
+g84_pm_oclass = &(struct nv40_pm_oclass) {
+       .base.handle = NV_ENGINE(PM, 0x84),
+       .base.ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = nv40_pm_ctor,
+               .dtor = _nvkm_pm_dtor,
+               .init = _nvkm_pm_init,
+               .fini = _nvkm_pm_fini,
+       },
+       .doms = g84_pm,
+}.base;
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/pm/gf100.c b/drivers/gpu/drm/nouveau/nvkm/engine/pm/gf100.c
new file mode 100644 (file)
index 0000000..008fed7
--- /dev/null
@@ -0,0 +1,159 @@
+/*
+ * Copyright 2013 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 "gf100.h"
+
+static const struct nvkm_specdom
+gf100_pm_hub[] = {
+       {}
+};
+
+static const struct nvkm_specdom
+gf100_pm_gpc[] = {
+       {}
+};
+
+static const struct nvkm_specdom
+gf100_pm_part[] = {
+       {}
+};
+
+static void
+gf100_perfctr_init(struct nvkm_pm *ppm, struct nvkm_perfdom *dom,
+                  struct nvkm_perfctr *ctr)
+{
+       struct gf100_pm_priv *priv = (void *)ppm;
+       struct gf100_pm_cntr *cntr = (void *)ctr;
+       u32 log = ctr->logic_op;
+       u32 src = 0x00000000;
+       int i;
+
+       for (i = 0; i < 4 && ctr->signal[i]; i++)
+               src |= (ctr->signal[i] - dom->signal) << (i * 8);
+
+       nv_wr32(priv, dom->addr + 0x09c, 0x00040002);
+       nv_wr32(priv, dom->addr + 0x100, 0x00000000);
+       nv_wr32(priv, dom->addr + 0x040 + (cntr->base.slot * 0x08), src);
+       nv_wr32(priv, dom->addr + 0x044 + (cntr->base.slot * 0x08), log);
+}
+
+static void
+gf100_perfctr_read(struct nvkm_pm *ppm, struct nvkm_perfdom *dom,
+                  struct nvkm_perfctr *ctr)
+{
+       struct gf100_pm_priv *priv = (void *)ppm;
+       struct gf100_pm_cntr *cntr = (void *)ctr;
+
+       switch (cntr->base.slot) {
+       case 0: cntr->base.ctr = nv_rd32(priv, dom->addr + 0x08c); break;
+       case 1: cntr->base.ctr = nv_rd32(priv, dom->addr + 0x088); break;
+       case 2: cntr->base.ctr = nv_rd32(priv, dom->addr + 0x080); break;
+       case 3: cntr->base.ctr = nv_rd32(priv, dom->addr + 0x090); break;
+       }
+       cntr->base.clk = nv_rd32(priv, dom->addr + 0x070);
+}
+
+static void
+gf100_perfctr_next(struct nvkm_pm *ppm, struct nvkm_perfdom *dom)
+{
+       struct gf100_pm_priv *priv = (void *)ppm;
+       nv_wr32(priv, dom->addr + 0x06c, dom->signal_nr - 0x40 + 0x27);
+       nv_wr32(priv, dom->addr + 0x0ec, 0x00000011);
+}
+
+const struct nvkm_funcdom
+gf100_perfctr_func = {
+       .init = gf100_perfctr_init,
+       .read = gf100_perfctr_read,
+       .next = gf100_perfctr_next,
+};
+
+int
+gf100_pm_fini(struct nvkm_object *object, bool suspend)
+{
+       struct gf100_pm_priv *priv = (void *)object;
+       nv_mask(priv, 0x000200, 0x10000000, 0x00000000);
+       nv_mask(priv, 0x000200, 0x10000000, 0x10000000);
+       return nvkm_pm_fini(&priv->base, suspend);
+}
+
+static int
+gf100_pm_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+             struct nvkm_oclass *oclass, void *data, u32 size,
+             struct nvkm_object **pobject)
+{
+       struct gf100_pm_priv *priv;
+       u32 mask;
+       int ret;
+
+       ret = nvkm_pm_create(parent, engine, oclass, &priv);
+       *pobject = nv_object(priv);
+       if (ret)
+               return ret;
+
+       ret = nvkm_perfdom_new(&priv->base, "pwr", 0, 0, 0, 0, gf100_pm_pwr);
+       if (ret)
+               return ret;
+
+       /* HUB */
+       ret = nvkm_perfdom_new(&priv->base, "hub", 0, 0x1b0000, 0, 0x200,
+                              gf100_pm_hub);
+       if (ret)
+               return ret;
+
+       /* GPC */
+       mask  = (1 << nv_rd32(priv, 0x022430)) - 1;
+       mask &= ~nv_rd32(priv, 0x022504);
+       mask &= ~nv_rd32(priv, 0x022584);
+
+       ret = nvkm_perfdom_new(&priv->base, "gpc", mask, 0x180000,
+                              0x1000, 0x200, gf100_pm_gpc);
+       if (ret)
+               return ret;
+
+       /* PART */
+       mask  = (1 << nv_rd32(priv, 0x022438)) - 1;
+       mask &= ~nv_rd32(priv, 0x022548);
+       mask &= ~nv_rd32(priv, 0x0225c8);
+
+       ret = nvkm_perfdom_new(&priv->base, "part", mask, 0x1a0000,
+                              0x1000, 0x200, gf100_pm_part);
+       if (ret)
+               return ret;
+
+       nv_engine(priv)->cclass = &nvkm_pm_cclass;
+       nv_engine(priv)->sclass =  nvkm_pm_sclass;
+       priv->base.last = 7;
+       return 0;
+}
+
+struct nvkm_oclass
+gf100_pm_oclass = {
+       .handle = NV_ENGINE(PM, 0xc0),
+       .ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = gf100_pm_ctor,
+               .dtor = _nvkm_pm_dtor,
+               .init = _nvkm_pm_init,
+               .fini = gf100_pm_fini,
+       },
+};
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/pm/gf100.h b/drivers/gpu/drm/nouveau/nvkm/engine/pm/gf100.h
new file mode 100644 (file)
index 0000000..6a01fc7
--- /dev/null
@@ -0,0 +1,15 @@
+#ifndef __NVKM_PM_NVC0_H__
+#define __NVKM_PM_NVC0_H__
+#include "priv.h"
+
+struct gf100_pm_priv {
+       struct nvkm_pm base;
+};
+
+struct gf100_pm_cntr {
+       struct nvkm_perfctr base;
+};
+
+extern const struct nvkm_funcdom gf100_perfctr_func;
+int gf100_pm_fini(struct nvkm_object *, bool);
+#endif
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/pm/gk104.c b/drivers/gpu/drm/nouveau/nvkm/engine/pm/gk104.c
new file mode 100644 (file)
index 0000000..75b9ff3
--- /dev/null
@@ -0,0 +1,148 @@
+/*
+ * Copyright 2013 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 "gf100.h"
+
+static const struct nvkm_specdom
+gk104_pm_hub[] = {
+       { 0x60, (const struct nvkm_specsig[]) {
+                       { 0x47, "hub00_user_0" },
+                       {}
+               }, &gf100_perfctr_func },
+       { 0x40, (const struct nvkm_specsig[]) {
+                       { 0x27, "hub01_user_0" },
+                       {}
+               }, &gf100_perfctr_func },
+       { 0x60, (const struct nvkm_specsig[]) {
+                       { 0x47, "hub02_user_0" },
+                       {}
+               }, &gf100_perfctr_func },
+       { 0x60, (const struct nvkm_specsig[]) {
+                       { 0x47, "hub03_user_0" },
+                       {}
+               }, &gf100_perfctr_func },
+       { 0x40, (const struct nvkm_specsig[]) {
+                       { 0x03, "host_mmio_rd" },
+                       { 0x27, "hub04_user_0" },
+                       {}
+               }, &gf100_perfctr_func },
+       { 0x60, (const struct nvkm_specsig[]) {
+                       { 0x47, "hub05_user_0" },
+                       {}
+               }, &gf100_perfctr_func },
+       { 0xc0, (const struct nvkm_specsig[]) {
+                       { 0x74, "host_fb_rd3x" },
+                       { 0x75, "host_fb_rd3x_2" },
+                       { 0xa7, "hub06_user_0" },
+                       {}
+               }, &gf100_perfctr_func },
+       { 0x60, (const struct nvkm_specsig[]) {
+                       { 0x47, "hub07_user_0" },
+                       {}
+               }, &gf100_perfctr_func },
+       {}
+};
+
+static const struct nvkm_specdom
+gk104_pm_gpc[] = {
+       { 0xe0, (const struct nvkm_specsig[]) {
+                       { 0xc7, "gpc00_user_0" },
+                       {}
+               }, &gf100_perfctr_func },
+       {}
+};
+
+static const struct nvkm_specdom
+gk104_pm_part[] = {
+       { 0x60, (const struct nvkm_specsig[]) {
+                       { 0x47, "part00_user_0" },
+                       {}
+               }, &gf100_perfctr_func },
+       { 0x60, (const struct nvkm_specsig[]) {
+                       { 0x47, "part01_user_0" },
+                       {}
+               }, &gf100_perfctr_func },
+       {}
+};
+
+static int
+gk104_pm_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+             struct nvkm_oclass *oclass, void *data, u32 size,
+             struct nvkm_object **pobject)
+{
+       struct gf100_pm_priv *priv;
+       u32 mask;
+       int ret;
+
+       ret = nvkm_pm_create(parent, engine, oclass, &priv);
+       *pobject = nv_object(priv);
+       if (ret)
+               return ret;
+
+       /* PDAEMON */
+       ret = nvkm_perfdom_new(&priv->base, "pwr", 0, 0, 0, 0, gk104_pm_pwr);
+       if (ret)
+               return ret;
+
+       /* HUB */
+       ret = nvkm_perfdom_new(&priv->base, "hub", 0, 0x1b0000, 0, 0x200,
+                              gk104_pm_hub);
+       if (ret)
+               return ret;
+
+       /* GPC */
+       mask  = (1 << nv_rd32(priv, 0x022430)) - 1;
+       mask &= ~nv_rd32(priv, 0x022504);
+       mask &= ~nv_rd32(priv, 0x022584);
+
+       ret = nvkm_perfdom_new(&priv->base, "gpc", mask, 0x180000,
+                              0x1000, 0x200, gk104_pm_gpc);
+       if (ret)
+               return ret;
+
+       /* PART */
+       mask  = (1 << nv_rd32(priv, 0x022438)) - 1;
+       mask &= ~nv_rd32(priv, 0x022548);
+       mask &= ~nv_rd32(priv, 0x0225c8);
+
+       ret = nvkm_perfdom_new(&priv->base, "part", mask, 0x1a0000,
+                              0x1000, 0x200, gk104_pm_part);
+       if (ret)
+               return ret;
+
+       nv_engine(priv)->cclass = &nvkm_pm_cclass;
+       nv_engine(priv)->sclass =  nvkm_pm_sclass;
+       priv->base.last = 7;
+       return 0;
+}
+
+struct nvkm_oclass
+gk104_pm_oclass = {
+       .handle = NV_ENGINE(PM, 0xe0),
+       .ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = gk104_pm_ctor,
+               .dtor = _nvkm_pm_dtor,
+               .init = _nvkm_pm_init,
+               .fini = gf100_pm_fini,
+       },
+};
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/pm/gk110.c b/drivers/gpu/drm/nouveau/nvkm/engine/pm/gk110.c
new file mode 100644 (file)
index 0000000..6820176
--- /dev/null
@@ -0,0 +1,57 @@
+/*
+ * Copyright 2013 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 "gf100.h"
+
+static int
+gk110_pm_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+             struct nvkm_oclass *oclass, void *data, u32 size,
+             struct nvkm_object **pobject)
+{
+       struct gf100_pm_priv *priv;
+       int ret;
+
+       ret = nvkm_pm_create(parent, engine, oclass, &priv);
+       *pobject = nv_object(priv);
+       if (ret)
+               return ret;
+
+       ret = nvkm_perfdom_new(&priv->base, "pwr", 0, 0, 0, 0, gk104_pm_pwr);
+       if (ret)
+               return ret;
+
+       nv_engine(priv)->cclass = &nvkm_pm_cclass;
+       nv_engine(priv)->sclass =  nvkm_pm_sclass;
+       return 0;
+}
+
+struct nvkm_oclass
+gk110_pm_oclass = {
+       .handle = NV_ENGINE(PM, 0xf0),
+       .ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = gk110_pm_ctor,
+               .dtor = _nvkm_pm_dtor,
+               .init = _nvkm_pm_init,
+               .fini = gf100_pm_fini,
+       },
+};
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/pm/gt215.c b/drivers/gpu/drm/nouveau/nvkm/engine/pm/gt215.c
new file mode 100644 (file)
index 0000000..d065bfc
--- /dev/null
@@ -0,0 +1,83 @@
+/*
+ * Copyright 2013 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 "nv40.h"
+
+static const struct nvkm_specdom
+gt215_pm[] = {
+       { 0x20, (const struct nvkm_specsig[]) {
+                       {}
+               }, &nv40_perfctr_func },
+       { 0x20, (const struct nvkm_specsig[]) {
+                       {}
+               }, &nv40_perfctr_func },
+       { 0x20, (const struct nvkm_specsig[]) {
+                       {}
+               }, &nv40_perfctr_func },
+       { 0x20, (const struct nvkm_specsig[]) {
+                       {}
+               }, &nv40_perfctr_func },
+       { 0x20, (const struct nvkm_specsig[]) {
+                       {}
+               }, &nv40_perfctr_func },
+       { 0x20, (const struct nvkm_specsig[]) {
+                       {}
+               }, &nv40_perfctr_func },
+       { 0x20, (const struct nvkm_specsig[]) {
+                       {}
+               }, &nv40_perfctr_func },
+       { 0x20, (const struct nvkm_specsig[]) {
+                       {}
+               }, &nv40_perfctr_func },
+       {}
+};
+
+static int
+gt215_pm_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+             struct nvkm_oclass *oclass, void *data, u32 size,
+             struct nvkm_object **object)
+{
+       int ret = nv40_pm_ctor(parent, engine, oclass, data, size, object);
+       if (ret == 0) {
+               struct nv40_pm_priv *priv = (void *)*object;
+               ret = nvkm_perfdom_new(&priv->base, "pwr", 0, 0, 0, 0,
+                                      gt215_pm_pwr);
+               if (ret)
+                       return ret;
+
+               priv->base.last = 3;
+       }
+       return ret;
+}
+
+struct nvkm_oclass *
+gt215_pm_oclass = &(struct nv40_pm_oclass) {
+       .base.handle = NV_ENGINE(PM, 0xa3),
+       .base.ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = gt215_pm_ctor,
+               .dtor = _nvkm_pm_dtor,
+               .init = _nvkm_pm_init,
+               .fini = _nvkm_pm_fini,
+       },
+       .doms = gt215_pm,
+}.base;
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/pm/nv40.c b/drivers/gpu/drm/nouveau/nvkm/engine/pm/nv40.c
new file mode 100644 (file)
index 0000000..ff22f06
--- /dev/null
@@ -0,0 +1,130 @@
+/*
+ * Copyright 2013 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 "nv40.h"
+
+static void
+nv40_perfctr_init(struct nvkm_pm *ppm, struct nvkm_perfdom *dom,
+                 struct nvkm_perfctr *ctr)
+{
+       struct nv40_pm_priv *priv = (void *)ppm;
+       struct nv40_pm_cntr *cntr = (void *)ctr;
+       u32 log = ctr->logic_op;
+       u32 src = 0x00000000;
+       int i;
+
+       for (i = 0; i < 4 && ctr->signal[i]; i++)
+               src |= (ctr->signal[i] - dom->signal) << (i * 8);
+
+       nv_wr32(priv, 0x00a7c0 + dom->addr, 0x00000001);
+       nv_wr32(priv, 0x00a400 + dom->addr + (cntr->base.slot * 0x40), src);
+       nv_wr32(priv, 0x00a420 + dom->addr + (cntr->base.slot * 0x40), log);
+}
+
+static void
+nv40_perfctr_read(struct nvkm_pm *ppm, struct nvkm_perfdom *dom,
+                 struct nvkm_perfctr *ctr)
+{
+       struct nv40_pm_priv *priv = (void *)ppm;
+       struct nv40_pm_cntr *cntr = (void *)ctr;
+
+       switch (cntr->base.slot) {
+       case 0: cntr->base.ctr = nv_rd32(priv, 0x00a700 + dom->addr); break;
+       case 1: cntr->base.ctr = nv_rd32(priv, 0x00a6c0 + dom->addr); break;
+       case 2: cntr->base.ctr = nv_rd32(priv, 0x00a680 + dom->addr); break;
+       case 3: cntr->base.ctr = nv_rd32(priv, 0x00a740 + dom->addr); break;
+       }
+       cntr->base.clk = nv_rd32(priv, 0x00a600 + dom->addr);
+}
+
+static void
+nv40_perfctr_next(struct nvkm_pm *ppm, struct nvkm_perfdom *dom)
+{
+       struct nv40_pm_priv *priv = (void *)ppm;
+       if (priv->sequence != ppm->sequence) {
+               nv_wr32(priv, 0x400084, 0x00000020);
+               priv->sequence = ppm->sequence;
+       }
+}
+
+const struct nvkm_funcdom
+nv40_perfctr_func = {
+       .init = nv40_perfctr_init,
+       .read = nv40_perfctr_read,
+       .next = nv40_perfctr_next,
+};
+
+static const struct nvkm_specdom
+nv40_pm[] = {
+       { 0x20, (const struct nvkm_specsig[]) {
+                       {}
+               }, &nv40_perfctr_func },
+       { 0x20, (const struct nvkm_specsig[]) {
+                       {}
+               }, &nv40_perfctr_func },
+       { 0x20, (const struct nvkm_specsig[]) {
+                       {}
+               }, &nv40_perfctr_func },
+       { 0x20, (const struct nvkm_specsig[]) {
+                       {}
+               }, &nv40_perfctr_func },
+       { 0x20, (const struct nvkm_specsig[]) {
+                       {}
+               }, &nv40_perfctr_func },
+       {}
+};
+
+int
+nv40_pm_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+            struct nvkm_oclass *oclass, void *data, u32 size,
+            struct nvkm_object **pobject)
+{
+       struct nv40_pm_oclass *mclass = (void *)oclass;
+       struct nv40_pm_priv *priv;
+       int ret;
+
+       ret = nvkm_pm_create(parent, engine, oclass, &priv);
+       *pobject = nv_object(priv);
+       if (ret)
+               return ret;
+
+       ret = nvkm_perfdom_new(&priv->base, "pm", 0, 0, 0, 4, mclass->doms);
+       if (ret)
+               return ret;
+
+       nv_engine(priv)->cclass = &nvkm_pm_cclass;
+       nv_engine(priv)->sclass =  nvkm_pm_sclass;
+       return 0;
+}
+
+struct nvkm_oclass *
+nv40_pm_oclass = &(struct nv40_pm_oclass) {
+       .base.handle = NV_ENGINE(PM, 0x40),
+       .base.ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = nv40_pm_ctor,
+               .dtor = _nvkm_pm_dtor,
+               .init = _nvkm_pm_init,
+               .fini = _nvkm_pm_fini,
+       },
+       .doms = nv40_pm,
+}.base;
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/pm/nv40.h b/drivers/gpu/drm/nouveau/nvkm/engine/pm/nv40.h
new file mode 100644 (file)
index 0000000..2338e15
--- /dev/null
@@ -0,0 +1,24 @@
+#ifndef __NVKM_PM_NV40_H__
+#define __NVKM_PM_NV40_H__
+#include "priv.h"
+
+struct nv40_pm_oclass {
+       struct nvkm_oclass base;
+       const struct nvkm_specdom *doms;
+};
+
+struct nv40_pm_priv {
+       struct nvkm_pm base;
+       u32 sequence;
+};
+
+int nv40_pm_ctor(struct nvkm_object *, struct nvkm_object *,
+                     struct nvkm_oclass *, void *data, u32 size,
+                     struct nvkm_object **pobject);
+
+struct nv40_pm_cntr {
+       struct nvkm_perfctr base;
+};
+
+extern const struct nvkm_funcdom nv40_perfctr_func;
+#endif
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/pm/nv50.c b/drivers/gpu/drm/nouveau/nvkm/engine/pm/nv50.c
new file mode 100644 (file)
index 0000000..6af83b5
--- /dev/null
@@ -0,0 +1,57 @@
+/*
+ * Copyright 2013 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 "nv40.h"
+
+static const struct nvkm_specdom
+nv50_pm[] = {
+       { 0x040, (const struct nvkm_specsig[]) {
+                       {}
+               }, &nv40_perfctr_func },
+       { 0x100, (const struct nvkm_specsig[]) {
+                       { 0xc8, "gr_idle" },
+                       {}
+               }, &nv40_perfctr_func },
+       { 0x100, (const struct nvkm_specsig[]) {
+                       {}
+               }, &nv40_perfctr_func },
+       { 0x020, (const struct nvkm_specsig[]) {
+                       {}
+               }, &nv40_perfctr_func },
+       { 0x040, (const struct nvkm_specsig[]) {
+                       {}
+               }, &nv40_perfctr_func },
+       {}
+};
+
+struct nvkm_oclass *
+nv50_pm_oclass = &(struct nv40_pm_oclass) {
+       .base.handle = NV_ENGINE(PM, 0x50),
+       .base.ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = nv40_pm_ctor,
+               .dtor = _nvkm_pm_dtor,
+               .init = _nvkm_pm_init,
+               .fini = _nvkm_pm_fini,
+       },
+       .doms = nv50_pm,
+}.base;
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/pm/priv.h b/drivers/gpu/drm/nouveau/nvkm/engine/pm/priv.h
new file mode 100644 (file)
index 0000000..1e6eff2
--- /dev/null
@@ -0,0 +1,90 @@
+#ifndef __NVKM_PM_PRIV_H__
+#define __NVKM_PM_PRIV_H__
+#include <engine/pm.h>
+
+struct nvkm_perfctr {
+       struct nvkm_object base;
+       struct list_head head;
+       struct nvkm_perfsig *signal[4];
+       int slot;
+       u32 logic_op;
+       u32 clk;
+       u32 ctr;
+};
+
+extern struct nvkm_oclass nvkm_pm_sclass[];
+
+#include <core/engctx.h>
+
+struct nvkm_perfctx {
+       struct nvkm_engctx base;
+};
+
+extern struct nvkm_oclass nvkm_pm_cclass;
+
+struct nvkm_specsig {
+       u8 signal;
+       const char *name;
+};
+
+struct nvkm_perfsig {
+       const char *name;
+};
+
+struct nvkm_perfdom;
+struct nvkm_perfctr *
+nvkm_perfsig_wrap(struct nvkm_pm *, const char *, struct nvkm_perfdom **);
+
+struct nvkm_specdom {
+       u16 signal_nr;
+       const struct nvkm_specsig *signal;
+       const struct nvkm_funcdom *func;
+};
+
+extern const struct nvkm_specdom gt215_pm_pwr[];
+extern const struct nvkm_specdom gf100_pm_pwr[];
+extern const struct nvkm_specdom gk104_pm_pwr[];
+
+struct nvkm_perfdom {
+       struct list_head head;
+       struct list_head list;
+       const struct nvkm_funcdom *func;
+       char name[32];
+       u32 addr;
+       u8  quad;
+       u32 signal_nr;
+       struct nvkm_perfsig signal[];
+};
+
+struct nvkm_funcdom {
+       void (*init)(struct nvkm_pm *, struct nvkm_perfdom *,
+                    struct nvkm_perfctr *);
+       void (*read)(struct nvkm_pm *, struct nvkm_perfdom *,
+                    struct nvkm_perfctr *);
+       void (*next)(struct nvkm_pm *, struct nvkm_perfdom *);
+};
+
+int nvkm_perfdom_new(struct nvkm_pm *, const char *, u32, u32, u32, u32,
+                    const struct nvkm_specdom *);
+
+#define nvkm_pm_create(p,e,o,d)                                        \
+       nvkm_pm_create_((p), (e), (o), sizeof(**d), (void **)d)
+#define nvkm_pm_dtor(p) ({                                             \
+       struct nvkm_pm *c = (p);                                       \
+       _nvkm_pm_dtor(nv_object(c));                                   \
+})
+#define nvkm_pm_init(p) ({                                             \
+       struct nvkm_pm *c = (p);                                       \
+       _nvkm_pm_init(nv_object(c));                                   \
+})
+#define nvkm_pm_fini(p,s) ({                                           \
+       struct nvkm_pm *c = (p);                                       \
+       _nvkm_pm_fini(nv_object(c), (s));                              \
+})
+
+int nvkm_pm_create_(struct nvkm_object *, struct nvkm_object *,
+                           struct nvkm_oclass *, int, void **);
+void _nvkm_pm_dtor(struct nvkm_object *);
+int  _nvkm_pm_init(struct nvkm_object *);
+int  _nvkm_pm_fini(struct nvkm_object *, bool);
+#endif
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/sec/Kbuild b/drivers/gpu/drm/nouveau/nvkm/engine/sec/Kbuild
new file mode 100644 (file)
index 0000000..552d40a
--- /dev/null
@@ -0,0 +1 @@
+nvkm-y += nvkm/engine/sec/g98.o
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/sec/fuc/g98.fuc0s b/drivers/gpu/drm/nouveau/nvkm/engine/sec/fuc/g98.fuc0s
new file mode 100644 (file)
index 0000000..06ee060
--- /dev/null
@@ -0,0 +1,698 @@
+/*
+ *  fuc microcode for g98 psec 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 #g98_psec_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 #sec_cmd_mode + 0x00000 ~0xf
+.b32 #sec_cmd_length + 0x10000 ~0x0ffffff0
+.equ #engine_cmd_max 0xce
+
+.align 4
+sec_dtable:
+.b16 #sec_copy_prep #sec_do_inout
+.b16 #sec_store_prep #sec_do_out
+.b16 #sec_ecb_e_prep #sec_do_inout
+.b16 #sec_ecb_d_prep #sec_do_inout
+.b16 #sec_cbc_e_prep #sec_do_inout
+.b16 #sec_cbc_d_prep #sec_do_inout
+.b16 #sec_pcbc_e_prep #sec_do_inout
+.b16 #sec_pcbc_d_prep #sec_do_inout
+.b16 #sec_cfb_e_prep #sec_do_inout
+.b16 #sec_cfb_d_prep #sec_do_inout
+.b16 #sec_ofb_prep #sec_do_inout
+.b16 #sec_ctr_prep #sec_do_inout
+.b16 #sec_cbc_mac_prep #sec_do_in
+.b16 #sec_cmac_finish_complete_prep #sec_do_in
+.b16 #sec_cmac_finish_partial_prep #sec_do_in
+
+.align 0x100
+
+.section #g98_psec_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)
+                       bset $r3 0x1e
+                       st b32 D[$r5] $r3
+                       add b32 $r4 0x180 - 0x60
+                       shl b32 $r4 8
+                       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
+
+sec_cmd_mode:
+       // if >= 0xf, INVALID_ENUM
+       bset $flags $p1
+       or $r2 2
+       cmpu b32 $r3 0xf
+       bra nc #sec_cmd_mode_return
+
+               bclr $flags $p1
+               st b32 D[$r0 + #ctx_mode] $r3
+
+       sec_cmd_mode_return:
+       ret
+
+sec_cmd_length:
+       // nop if length == 0
+       cmpu b32 $r3 0
+       bra e #sec_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 + #sec_dtable]
+       call $r9
+
+       // do it
+       ld b16 $r9 D[$r8 + #sec_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
+
+
+sec_copy_prep:
+       cs0begin 2
+               cxsin $c0
+               cxsout $c0
+       ret
+
+sec_store_prep:
+       cs0begin 1
+               cxsout $c6
+       ret
+
+sec_ecb_e_prep:
+       cs0begin 3
+               cxsin $c0
+               cenc $c0 $c0
+               cxsout $c0
+       ret
+
+sec_ecb_d_prep:
+       ckexp $c7 $c7
+       cs0begin 3
+               cxsin $c0
+               cdec $c0 $c0
+               cxsout $c0
+       ret
+
+sec_cbc_e_prep:
+       cs0begin 4
+               cxsin $c0
+               cxor $c6 $c0
+               cenc $c6 $c6
+               cxsout $c6
+       ret
+
+sec_cbc_d_prep:
+       ckexp $c7 $c7
+       cs0begin 5
+               cmov $c2 $c6
+               cxsin $c6
+               cdec $c0 $c6
+               cxor $c0 $c2
+               cxsout $c0
+       ret
+
+sec_pcbc_e_prep:
+       cs0begin 5
+               cxsin $c0
+               cxor $c6 $c0
+               cenc $c6 $c6
+               cxsout $c6
+               cxor $c6 $c0
+       ret
+
+sec_pcbc_d_prep:
+       ckexp $c7 $c7
+       cs0begin 5
+               cxsin $c0
+               cdec $c1 $c0
+               cxor $c6 $c1
+               cxsout $c6
+               cxor $c6 $c0
+       ret
+
+sec_cfb_e_prep:
+       cs0begin 4
+               cenc $c6 $c6
+               cxsin $c0
+               cxor $c6 $c0
+               cxsout $c6
+       ret
+
+sec_cfb_d_prep:
+       cs0begin 4
+               cenc $c0 $c6
+               cxsin $c6
+               cxor $c0 $c6
+               cxsout $c0
+       ret
+
+sec_ofb_prep:
+       cs0begin 4
+               cenc $c6 $c6
+               cxsin $c0
+               cxor $c0 $c6
+               cxsout $c0
+       ret
+
+sec_ctr_prep:
+       cs0begin 5
+               cenc $c1 $c6
+               cadd $c6 1
+               cxsin $c0
+               cxor $c0 $c1
+               cxsout $c0
+       ret
+
+sec_cbc_mac_prep:
+       cs0begin 3
+               cxsin $c0
+               cxor $c6 $c0
+               cenc $c6 $c6
+       ret
+
+sec_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
+
+sec_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
+sec_do_in:
+       add b32 $r3 $r5
+       mov $xdbase $r4
+       mov $r9 #swap
+       sethi $r9 0x20000
+       sec_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 #sec_do_in_loop
+       cxset 1
+       xdwait
+       ret
+
+sec_do_out:
+       add b32 $r3 $r7
+       mov $xdbase $r6
+       mov $r9 #swap
+       sethi $r9 0x20000
+       sec_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 #sec_do_out_loop
+       ret
+
+sec_do_inout:
+       add b32 $r3 $r5
+       mov $r9 #swap
+       sethi $r9 0x20000
+       sec_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 #sec_do_inout_loop
+       ret
+
+.align 0x100
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/sec/fuc/g98.fuc0s.h b/drivers/gpu/drm/nouveau/nvkm/engine/sec/fuc/g98.fuc0s.h
new file mode 100644 (file)
index 0000000..5d65c4f
--- /dev/null
@@ -0,0 +1,584 @@
+uint32_t g98_psec_data[] = {
+/* 0x0000: ctx_dma */
+/* 0x0000: ctx_dma_query */
+       0x00000000,
+/* 0x0004: ctx_dma_src */
+       0x00000000,
+/* 0x0008: ctx_dma_dst */
+       0x00000000,
+/* 0x000c: ctx_query_address_high */
+       0x00000000,
+/* 0x0010: ctx_query_address_low */
+       0x00000000,
+/* 0x0014: ctx_query_counter */
+       0x00000000,
+/* 0x0018: ctx_cond_address_high */
+       0x00000000,
+/* 0x001c: ctx_cond_address_low */
+       0x00000000,
+/* 0x0020: ctx_cond_off */
+       0x00000000,
+/* 0x0024: ctx_src_address_high */
+       0x00000000,
+/* 0x0028: ctx_src_address_low */
+       0x00000000,
+/* 0x002c: ctx_dst_address_high */
+       0x00000000,
+/* 0x0030: ctx_dst_address_low */
+       0x00000000,
+/* 0x0034: ctx_mode */
+       0x00000000,
+       0x00000000,
+       0x00000000,
+/* 0x0040: ctx_key */
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+/* 0x0050: ctx_iv */
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+/* 0x0080: swap */
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+/* 0x00a0: common_cmd_dtable */
+       0x0002000c,
+       0xffffff00,
+       0x00020010,
+       0x0000000f,
+       0x00020014,
+       0x00000000,
+       0x00000192,
+       0xfffffffe,
+       0x00020018,
+       0xffffff00,
+       0x0002001c,
+       0x0000000f,
+       0x000001d7,
+       0xfffffff8,
+       0x00000260,
+       0xffffffff,
+/* 0x00e0: engine_cmd_dtable */
+       0x00020040,
+       0x00000000,
+       0x00020044,
+       0x00000000,
+       0x00020048,
+       0x00000000,
+       0x0002004c,
+       0x00000000,
+       0x00020050,
+       0x00000000,
+       0x00020054,
+       0x00000000,
+       0x00020058,
+       0x00000000,
+       0x0002005c,
+       0x00000000,
+       0x00020024,
+       0xffffff00,
+       0x00020028,
+       0x0000000f,
+       0x0002002c,
+       0xffffff00,
+       0x00020030,
+       0x0000000f,
+       0x00000271,
+       0xfffffff0,
+       0x00010285,
+       0xf000000f,
+/* 0x0150: sec_dtable */
+       0x04db0321,
+       0x04b1032f,
+       0x04db0339,
+       0x04db034b,
+       0x04db0361,
+       0x04db0377,
+       0x04db0395,
+       0x04db03af,
+       0x04db03cd,
+       0x04db03e3,
+       0x04db03f9,
+       0x04db040f,
+       0x04830429,
+       0x0483043b,
+       0x0483045d,
+       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,
+};
+
+uint32_t g98_psec_code[] = {
+       0x17f004bd,
+       0x0010fe35,
+       0xf10004fe,
+       0xf0fff017,
+       0x27f10013,
+       0x21d00400,
+       0x0c15f0c0,
+       0xf00021d0,
+       0x27f10317,
+       0x21d01200,
+       0x1031f400,
+/* 0x002f: spin */
+       0xf40031f4,
+       0x0ef40028,
+/* 0x0035: ih */
+       0x8001cffd,
+       0xb00812c4,
+       0x0bf40024,
+       0x0027f167,
+       0x002bfe77,
+       0xf00007fe,
+       0x23f00027,
+       0x0037f105,
+       0x0034cf14,
+       0xb0014594,
+       0x18f40055,
+       0x0602fa17,
+       0x4af003f8,
+       0x0034d01e,
+       0xd00147f0,
+       0x0ef48034,
+/* 0x0075: ctxload */
+       0x4034cf33,
+       0xb0014f94,
+       0x18f400f5,
+       0x0502fa21,
+       0x57f003f8,
+       0x0267f000,
+/* 0x008c: ctxload_dma_loop */
+       0xa07856bc,
+       0xb6018068,
+       0x87d00884,
+       0x0162b600,
+/* 0x009f: dummyload */
+       0xf0f018f4,
+       0x35d00257,
+/* 0x00a5: noctx */
+       0x0412c480,
+       0xf50024b0,
+       0xf100df0b,
+       0xcf190037,
+       0x33cf4032,
+       0xff24e400,
+       0x1024b607,
+       0x07bf45e4,
+       0xf50054b0,
+       0xf100b90b,
+       0xf1fae057,
+       0xb000ce67,
+       0x18f4c044,
+       0xa057f14d,
+       0x8867f1fc,
+       0x8044b000,
+       0xb03f18f4,
+       0x18f46044,
+       0x5044b019,
+       0xf1741bf4,
+       0xbd220027,
+       0x0233f034,
+       0xf50023d0,
+/* 0x0103: dma_cmd */
+       0xb000810e,
+       0x18f46344,
+       0x0245945e,
+       0xfe8050b7,
+       0x801e39f0,
+       0x40b70053,
+       0x44b60120,
+       0x0043d008,
+/* 0x0123: dtable_cmd */
+       0xb8600ef4,
+       0x18f40446,
+       0x0344b63e,
+       0x980045bb,
+       0x53fd0145,
+       0x0054b004,
+       0x58291bf4,
+       0x46580045,
+       0x0264b001,
+       0x98170bf4,
+       0x67fd0807,
+       0x0164b004,
+       0xf9300bf4,
+       0x0f01f455,
+/* 0x015b: cmd_setctx */
+       0x80280ef4,
+       0x0ef40053,
+/* 0x0161: invalid_bitfield */
+       0x0125f022,
+/* 0x0164: dispatch_error */
+/* 0x0164: illegal_mthd */
+       0x100047f1,
+       0xd00042d0,
+       0x47f04043,
+       0x0004d040,
+/* 0x0174: im_loop */
+       0xf08004cf,
+       0x44b04044,
+       0xf71bf400,
+/* 0x0180: cmddone */
+       0x1d0037f1,
+       0xd00147f0,
+/* 0x018a: nocmd */
+       0x11c40034,
+       0x4001d00c,
+/* 0x0192: cmd_query_get */
+       0x38f201f8,
+       0x0325f001,
+       0x0b0047f1,
+/* 0x019c: ptimer_retry */
+       0xcf4046cf,
+       0x47cf0045,
+       0x0467b840,
+       0x98f41bf4,
+       0x04800504,
+       0x21008020,
+       0x80220580,
+       0x0bfe2306,
+       0x03049800,
+       0xfe1844b6,
+       0x04980047,
+       0x8057f104,
+       0x0253f000,
+       0xf80645fa,
+/* 0x01d7: cmd_cond_mode */
+       0xf400f803,
+       0x25f00131,
+       0x0534b002,
+       0xf41218f4,
+       0x34b00132,
+       0x0b18f402,
+       0x800136f0,
+/* 0x01f2: return */
+       0x00f80803,
+/* 0x01f4: cmd_cond_mode_queryful */
+       0x98060498,
+       0x56c40705,
+       0x0855b6ff,
+       0xfd1844b6,
+       0x47fe0545,
+       0x000bfe00,
+       0x008057f1,
+       0xfa0253f0,
+       0x34b00565,
+       0x131bf402,
+       0x049803f8,
+       0x0044b021,
+       0x800b4cf0,
+       0x00f80804,
+/* 0x022c: cmd_cond_mode_double */
+       0xb61060b6,
+       0x65fa1050,
+       0x9803f805,
+       0x06982005,
+       0x0456b824,
+       0x980b4cf0,
+       0x06982105,
+       0x0456b825,
+       0xfd0b5cf0,
+       0x34b00445,
+       0x0b5cf003,
+       0x800645fd,
+       0x00f80804,
+/* 0x0260: cmd_wrcache_flush */
+       0xf10132f4,
+       0xbd220027,
+       0x0133f034,
+       0xf80023d0,
+/* 0x0271: sec_cmd_mode */
+       0x0131f400,
+       0xb00225f0,
+       0x18f40f34,
+       0x0132f409,
+/* 0x0283: sec_cmd_mode_return */
+       0xf80d0380,
+/* 0x0285: sec_cmd_length */
+       0x0034b000,
+       0xf4fb0bf4,
+       0x47f0033c,
+       0x0743f040,
+       0xf00604fa,
+       0x43f05047,
+       0x0604fa06,
+       0x3cf503f8,
+       0x47f1c407,
+       0x4bfe2100,
+       0x09049800,
+       0x950a0598,
+       0x44b60858,
+       0x0548fd18,
+       0x98ff55c4,
+       0x07980b06,
+       0x0878950c,
+       0xfd1864b6,
+       0x77c40568,
+       0x0d0898ff,
+       0x580284b6,
+       0x95f9a889,
+       0xf9a98958,
+       0x013cf495,
+       0x3cf403f8,
+       0xf803f861,
+       0x18489503,
+       0xbb084994,
+       0x81b60095,
+       0x09088000,
+       0x950a0980,
+       0x69941868,
+       0x0097bb08,
+       0x800081b6,
+       0x09800b08,
+       0x023cf40c,
+       0xf05047f0,
+       0x04fa0643,
+       0xf803f805,
+/* 0x0321: sec_copy_prep */
+       0x203cf500,
+       0x003cf594,
+       0x003cf588,
+/* 0x032f: sec_store_prep */
+       0xf500f88c,
+       0xf594103c,
+       0xf88c063c,
+/* 0x0339: sec_ecb_e_prep */
+       0x303cf500,
+       0x003cf594,
+       0x003cf588,
+       0x003cf5d0,
+/* 0x034b: sec_ecb_d_prep */
+       0xf500f88c,
+       0xf5c8773c,
+       0xf594303c,
+       0xf588003c,
+       0xf5d4003c,
+       0xf88c003c,
+/* 0x0361: sec_cbc_e_prep */
+       0x403cf500,
+       0x003cf594,
+       0x063cf588,
+       0x663cf5ac,
+       0x063cf5d0,
+/* 0x0377: sec_cbc_d_prep */
+       0xf500f88c,
+       0xf5c8773c,
+       0xf594503c,
+       0xf584623c,
+       0xf588063c,
+       0xf5d4603c,
+       0xf5ac203c,
+       0xf88c003c,
+/* 0x0395: sec_pcbc_e_prep */
+       0x503cf500,
+       0x003cf594,
+       0x063cf588,
+       0x663cf5ac,
+       0x063cf5d0,
+       0x063cf58c,
+/* 0x03af: sec_pcbc_d_prep */
+       0xf500f8ac,
+       0xf5c8773c,
+       0xf594503c,
+       0xf588003c,
+       0xf5d4013c,
+       0xf5ac163c,
+       0xf58c063c,
+       0xf8ac063c,
+/* 0x03cd: sec_cfb_e_prep */
+       0x403cf500,
+       0x663cf594,
+       0x003cf5d0,
+       0x063cf588,
+       0x063cf5ac,
+/* 0x03e3: sec_cfb_d_prep */
+       0xf500f88c,
+       0xf594403c,
+       0xf5d0603c,
+       0xf588063c,
+       0xf5ac603c,
+       0xf88c003c,
+/* 0x03f9: sec_ofb_prep */
+       0x403cf500,
+       0x663cf594,
+       0x003cf5d0,
+       0x603cf588,
+       0x003cf5ac,
+/* 0x040f: sec_ctr_prep */
+       0xf500f88c,
+       0xf594503c,
+       0xf5d0613c,
+       0xf5b0163c,
+       0xf588003c,
+       0xf5ac103c,
+       0xf88c003c,
+/* 0x0429: sec_cbc_mac_prep */
+       0x303cf500,
+       0x003cf594,
+       0x063cf588,
+       0x663cf5ac,
+/* 0x043b: sec_cmac_finish_complete_prep */
+       0xf500f8d0,
+       0xf594703c,
+       0xf588003c,
+       0xf5ac063c,
+       0xf5ac003c,
+       0xf5d0003c,
+       0xf5bc003c,
+       0xf5ac063c,
+       0xf8d0663c,
+/* 0x045d: sec_cmac_finish_partial_prep */
+       0x803cf500,
+       0x003cf594,
+       0x063cf588,
+       0x003cf5ac,
+       0x003cf5ac,
+       0x003cf5d0,
+       0x003cf5bc,
+       0x063cf5bc,
+       0x663cf5ac,
+/* 0x0483: sec_do_in */
+       0xbb00f8d0,
+       0x47fe0035,
+       0x8097f100,
+       0x0293f000,
+/* 0x0490: sec_do_in_loop */
+       0xf80559fa,
+       0x223cf403,
+       0xf50609fa,
+       0xf898103c,
+       0x1050b603,
+       0xf40453b8,
+       0x3cf4e91b,
+       0xf803f801,
+/* 0x04b1: sec_do_out */
+       0x0037bb00,
+       0xf10067fe,
+       0xf0008097,
+/* 0x04be: sec_do_out_loop */
+       0x3cf50293,
+       0x3cf49810,
+       0x0579fa61,
+       0xf40679fa,
+       0x03f8013c,
+       0xb81070b6,
+       0x1bf40473,
+/* 0x04db: sec_do_inout */
+       0xbb00f8e8,
+       0x97f10035,
+       0x93f00080,
+/* 0x04e5: sec_do_inout_loop */
+       0x0047fe02,
+       0xf80559fa,
+       0x213cf403,
+       0xf50609fa,
+       0xf498103c,
+       0x67fe613c,
+       0x0579fa00,
+       0xf40679fa,
+       0x03f8013c,
+       0xb61050b6,
+       0x53b81070,
+       0xd41bf404,
+       0x000000f8,
+       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,
+};
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/sec/g98.c b/drivers/gpu/drm/nouveau/nvkm/engine/sec/g98.c
new file mode 100644 (file)
index 0000000..9d5c1b8
--- /dev/null
@@ -0,0 +1,149 @@
+/*
+ * Copyright 2012 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 <engine/sec.h>
+#include <engine/falcon.h>
+#include "fuc/g98.fuc0s.h"
+
+#include <core/client.h>
+#include <core/enum.h>
+#include <engine/fifo.h>
+
+struct g98_sec_priv {
+       struct nvkm_falcon base;
+};
+
+/*******************************************************************************
+ * Crypt object classes
+ ******************************************************************************/
+
+static struct nvkm_oclass
+g98_sec_sclass[] = {
+       { 0x88b4, &nvkm_object_ofuncs },
+       {},
+};
+
+/*******************************************************************************
+ * PSEC context
+ ******************************************************************************/
+
+static struct nvkm_oclass
+g98_sec_cclass = {
+       .handle = NV_ENGCTX(SEC, 0x98),
+       .ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = _nvkm_falcon_context_ctor,
+               .dtor = _nvkm_falcon_context_dtor,
+               .init = _nvkm_falcon_context_init,
+               .fini = _nvkm_falcon_context_fini,
+               .rd32 = _nvkm_falcon_context_rd32,
+               .wr32 = _nvkm_falcon_context_wr32,
+       },
+};
+
+/*******************************************************************************
+ * PSEC engine/subdev functions
+ ******************************************************************************/
+
+static const struct nvkm_enum g98_sec_isr_error_name[] = {
+       { 0x0000, "ILLEGAL_MTHD" },
+       { 0x0001, "INVALID_BITFIELD" },
+       { 0x0002, "INVALID_ENUM" },
+       { 0x0003, "QUERY" },
+       {}
+};
+
+static void
+g98_sec_intr(struct nvkm_subdev *subdev)
+{
+       struct nvkm_fifo *pfifo = nvkm_fifo(subdev);
+       struct nvkm_engine *engine = nv_engine(subdev);
+       struct nvkm_object *engctx;
+       struct g98_sec_priv *priv = (void *)subdev;
+       u32 disp = nv_rd32(priv, 0x08701c);
+       u32 stat = nv_rd32(priv, 0x087008) & disp & ~(disp >> 16);
+       u32 inst = nv_rd32(priv, 0x087050) & 0x3fffffff;
+       u32 ssta = nv_rd32(priv, 0x087040) & 0x0000ffff;
+       u32 addr = nv_rd32(priv, 0x087040) >> 16;
+       u32 mthd = (addr & 0x07ff) << 2;
+       u32 subc = (addr & 0x3800) >> 11;
+       u32 data = nv_rd32(priv, 0x087044);
+       int chid;
+
+       engctx = nvkm_engctx_get(engine, inst);
+       chid   = pfifo->chid(pfifo, engctx);
+
+       if (stat & 0x00000040) {
+               nv_error(priv, "DISPATCH_ERROR [");
+               nvkm_enum_print(g98_sec_isr_error_name, ssta);
+               pr_cont("] ch %d [0x%010llx %s] subc %d mthd 0x%04x data 0x%08x\n",
+                      chid, (u64)inst << 12, nvkm_client_name(engctx),
+                      subc, mthd, data);
+               nv_wr32(priv, 0x087004, 0x00000040);
+               stat &= ~0x00000040;
+       }
+
+       if (stat) {
+               nv_error(priv, "unhandled intr 0x%08x\n", stat);
+               nv_wr32(priv, 0x087004, stat);
+       }
+
+       nvkm_engctx_put(engctx);
+}
+
+static int
+g98_sec_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+            struct nvkm_oclass *oclass, void *data, u32 size,
+            struct nvkm_object **pobject)
+{
+       struct g98_sec_priv *priv;
+       int ret;
+
+       ret = nvkm_falcon_create(parent, engine, oclass, 0x087000, true,
+                                "PSEC", "sec", &priv);
+       *pobject = nv_object(priv);
+       if (ret)
+               return ret;
+
+       nv_subdev(priv)->unit = 0x00004000;
+       nv_subdev(priv)->intr = g98_sec_intr;
+       nv_engine(priv)->cclass = &g98_sec_cclass;
+       nv_engine(priv)->sclass = g98_sec_sclass;
+       nv_falcon(priv)->code.data = g98_psec_code;
+       nv_falcon(priv)->code.size = sizeof(g98_psec_code);
+       nv_falcon(priv)->data.data = g98_psec_data;
+       nv_falcon(priv)->data.size = sizeof(g98_psec_data);
+       return 0;
+}
+
+struct nvkm_oclass
+g98_sec_oclass = {
+       .handle = NV_ENGINE(SEC, 0x98),
+       .ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = g98_sec_ctor,
+               .dtor = _nvkm_falcon_dtor,
+               .init = _nvkm_falcon_init,
+               .fini = _nvkm_falcon_fini,
+               .rd32 = _nvkm_falcon_rd32,
+               .wr32 = _nvkm_falcon_wr32,
+       },
+};
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/sw/Kbuild b/drivers/gpu/drm/nouveau/nvkm/engine/sw/Kbuild
new file mode 100644 (file)
index 0000000..bdc3a05
--- /dev/null
@@ -0,0 +1,4 @@
+nvkm-y += nvkm/engine/sw/nv04.o
+nvkm-y += nvkm/engine/sw/nv10.o
+nvkm-y += nvkm/engine/sw/nv50.o
+nvkm-y += nvkm/engine/sw/gf100.o
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/sw/gf100.c b/drivers/gpu/drm/nouveau/nvkm/engine/sw/gf100.c
new file mode 100644 (file)
index 0000000..533d5d8
--- /dev/null
@@ -0,0 +1,141 @@
+/*
+ * Copyright 2012 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 "nv50.h"
+
+#include <subdev/bar.h>
+
+/*******************************************************************************
+ * software object classes
+ ******************************************************************************/
+
+static int
+gf100_sw_mthd_vblsem_offset(struct nvkm_object *object, u32 mthd,
+                           void *args, u32 size)
+{
+       struct nv50_sw_chan *chan = (void *)nv_engctx(object->parent);
+       u64 data = *(u32 *)args;
+       if (mthd == 0x0400) {
+               chan->vblank.offset &= 0x00ffffffffULL;
+               chan->vblank.offset |= data << 32;
+       } else {
+               chan->vblank.offset &= 0xff00000000ULL;
+               chan->vblank.offset |= data;
+       }
+       return 0;
+}
+
+static int
+gf100_sw_mthd_mp_control(struct nvkm_object *object, u32 mthd,
+                        void *args, u32 size)
+{
+       struct nv50_sw_chan *chan = (void *)nv_engctx(object->parent);
+       struct nv50_sw_priv *priv = (void *)nv_object(chan)->engine;
+       u32 data = *(u32 *)args;
+
+       switch (mthd) {
+       case 0x600:
+               nv_wr32(priv, 0x419e00, data); /* MP.PM_UNK000 */
+               break;
+       case 0x644:
+               if (data & ~0x1ffffe)
+                       return -EINVAL;
+               nv_wr32(priv, 0x419e44, data); /* MP.TRAP_WARP_ERROR_EN */
+               break;
+       case 0x6ac:
+               nv_wr32(priv, 0x419eac, data); /* MP.PM_UNK0AC */
+               break;
+       default:
+               return -EINVAL;
+       }
+       return 0;
+}
+
+static struct nvkm_omthds
+gf100_sw_omthds[] = {
+       { 0x0400, 0x0400, gf100_sw_mthd_vblsem_offset },
+       { 0x0404, 0x0404, gf100_sw_mthd_vblsem_offset },
+       { 0x0408, 0x0408, nv50_sw_mthd_vblsem_value },
+       { 0x040c, 0x040c, nv50_sw_mthd_vblsem_release },
+       { 0x0500, 0x0500, nv50_sw_mthd_flip },
+       { 0x0600, 0x0600, gf100_sw_mthd_mp_control },
+       { 0x0644, 0x0644, gf100_sw_mthd_mp_control },
+       { 0x06ac, 0x06ac, gf100_sw_mthd_mp_control },
+       {}
+};
+
+static struct nvkm_oclass
+gf100_sw_sclass[] = {
+       { 0x906e, &nvkm_object_ofuncs, gf100_sw_omthds },
+       {}
+};
+
+/*******************************************************************************
+ * software context
+ ******************************************************************************/
+
+static int
+gf100_sw_vblsem_release(struct nvkm_notify *notify)
+{
+       struct nv50_sw_chan *chan =
+               container_of(notify, typeof(*chan), vblank.notify[notify->index]);
+       struct nv50_sw_priv *priv = (void *)nv_object(chan)->engine;
+       struct nvkm_bar *bar = nvkm_bar(priv);
+
+       nv_wr32(priv, 0x001718, 0x80000000 | chan->vblank.channel);
+       bar->flush(bar);
+       nv_wr32(priv, 0x06000c, upper_32_bits(chan->vblank.offset));
+       nv_wr32(priv, 0x060010, lower_32_bits(chan->vblank.offset));
+       nv_wr32(priv, 0x060014, chan->vblank.value);
+
+       return NVKM_NOTIFY_DROP;
+}
+
+static struct nv50_sw_cclass
+gf100_sw_cclass = {
+       .base.handle = NV_ENGCTX(SW, 0xc0),
+       .base.ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = nv50_sw_context_ctor,
+               .dtor = nv50_sw_context_dtor,
+               .init = _nvkm_sw_context_init,
+               .fini = _nvkm_sw_context_fini,
+       },
+       .vblank = gf100_sw_vblsem_release,
+};
+
+/*******************************************************************************
+ * software engine/subdev functions
+ ******************************************************************************/
+
+struct nvkm_oclass *
+gf100_sw_oclass = &(struct nv50_sw_oclass) {
+       .base.handle = NV_ENGINE(SW, 0xc0),
+       .base.ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = nv50_sw_ctor,
+               .dtor = _nvkm_sw_dtor,
+               .init = _nvkm_sw_init,
+               .fini = _nvkm_sw_fini,
+       },
+       .cclass = &gf100_sw_cclass.base,
+       .sclass =  gf100_sw_sclass,
+}.base;
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/sw/nv04.c b/drivers/gpu/drm/nouveau/nvkm/engine/sw/nv04.c
new file mode 100644 (file)
index 0000000..8970244
--- /dev/null
@@ -0,0 +1,139 @@
+/*
+ * Copyright 2012 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 <engine/sw.h>
+#include <engine/fifo.h>
+
+struct nv04_sw_priv {
+       struct nvkm_sw base;
+};
+
+struct nv04_sw_chan {
+       struct nvkm_sw_chan base;
+};
+
+/*******************************************************************************
+ * software object classes
+ ******************************************************************************/
+
+static int
+nv04_sw_set_ref(struct nvkm_object *object, u32 mthd, void *data, u32 size)
+{
+       struct nvkm_object *channel = (void *)nv_engctx(object->parent);
+       struct nvkm_fifo_chan *fifo = (void *)channel->parent;
+       atomic_set(&fifo->refcnt, *(u32*)data);
+       return 0;
+}
+
+static int
+nv04_sw_flip(struct nvkm_object *object, u32 mthd, void *args, u32 size)
+{
+       struct nv04_sw_chan *chan = (void *)nv_engctx(object->parent);
+       if (chan->base.flip)
+               return chan->base.flip(chan->base.flip_data);
+       return -EINVAL;
+}
+
+static struct nvkm_omthds
+nv04_sw_omthds[] = {
+       { 0x0150, 0x0150, nv04_sw_set_ref },
+       { 0x0500, 0x0500, nv04_sw_flip },
+       {}
+};
+
+static struct nvkm_oclass
+nv04_sw_sclass[] = {
+       { 0x006e, &nvkm_object_ofuncs, nv04_sw_omthds },
+       {}
+};
+
+/*******************************************************************************
+ * software context
+ ******************************************************************************/
+
+static int
+nv04_sw_context_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+                    struct nvkm_oclass *oclass, void *data, u32 size,
+                    struct nvkm_object **pobject)
+{
+       struct nv04_sw_chan *chan;
+       int ret;
+
+       ret = nvkm_sw_context_create(parent, engine, oclass, &chan);
+       *pobject = nv_object(chan);
+       if (ret)
+               return ret;
+
+       return 0;
+}
+
+static struct nvkm_oclass
+nv04_sw_cclass = {
+       .handle = NV_ENGCTX(SW, 0x04),
+       .ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = nv04_sw_context_ctor,
+               .dtor = _nvkm_sw_context_dtor,
+               .init = _nvkm_sw_context_init,
+               .fini = _nvkm_sw_context_fini,
+       },
+};
+
+/*******************************************************************************
+ * software engine/subdev functions
+ ******************************************************************************/
+
+void
+nv04_sw_intr(struct nvkm_subdev *subdev)
+{
+       nv_mask(subdev, 0x000100, 0x80000000, 0x00000000);
+}
+
+static int
+nv04_sw_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+            struct nvkm_oclass *oclass, void *data, u32 size,
+            struct nvkm_object **pobject)
+{
+       struct nv04_sw_priv *priv;
+       int ret;
+
+       ret = nvkm_sw_create(parent, engine, oclass, &priv);
+       *pobject = nv_object(priv);
+       if (ret)
+               return ret;
+
+       nv_engine(priv)->cclass = &nv04_sw_cclass;
+       nv_engine(priv)->sclass = nv04_sw_sclass;
+       nv_subdev(priv)->intr = nv04_sw_intr;
+       return 0;
+}
+
+struct nvkm_oclass *
+nv04_sw_oclass = &(struct nvkm_oclass) {
+       .handle = NV_ENGINE(SW, 0x04),
+       .ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = nv04_sw_ctor,
+               .dtor = _nvkm_sw_dtor,
+               .init = _nvkm_sw_init,
+               .fini = _nvkm_sw_fini,
+       },
+};
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/sw/nv10.c b/drivers/gpu/drm/nouveau/nvkm/engine/sw/nv10.c
new file mode 100644 (file)
index 0000000..c61153a
--- /dev/null
@@ -0,0 +1,122 @@
+/*
+ * Copyright 2012 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 <engine/sw.h>
+
+struct nv10_sw_priv {
+       struct nvkm_sw base;
+};
+
+struct nv10_sw_chan {
+       struct nvkm_sw_chan base;
+};
+
+/*******************************************************************************
+ * software object classes
+ ******************************************************************************/
+
+static int
+nv10_sw_flip(struct nvkm_object *object, u32 mthd, void *args, u32 size)
+{
+       struct nv10_sw_chan *chan = (void *)nv_engctx(object->parent);
+       if (chan->base.flip)
+               return chan->base.flip(chan->base.flip_data);
+       return -EINVAL;
+}
+
+static struct nvkm_omthds
+nv10_sw_omthds[] = {
+       { 0x0500, 0x0500, nv10_sw_flip },
+       {}
+};
+
+static struct nvkm_oclass
+nv10_sw_sclass[] = {
+       { 0x016e, &nvkm_object_ofuncs, nv10_sw_omthds },
+       {}
+};
+
+/*******************************************************************************
+ * software context
+ ******************************************************************************/
+
+static int
+nv10_sw_context_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+                    struct nvkm_oclass *oclass, void *data, u32 size,
+                    struct nvkm_object **pobject)
+{
+       struct nv10_sw_chan *chan;
+       int ret;
+
+       ret = nvkm_sw_context_create(parent, engine, oclass, &chan);
+       *pobject = nv_object(chan);
+       if (ret)
+               return ret;
+
+       return 0;
+}
+
+static struct nvkm_oclass
+nv10_sw_cclass = {
+       .handle = NV_ENGCTX(SW, 0x04),
+       .ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = nv10_sw_context_ctor,
+               .dtor = _nvkm_sw_context_dtor,
+               .init = _nvkm_sw_context_init,
+               .fini = _nvkm_sw_context_fini,
+       },
+};
+
+/*******************************************************************************
+ * software engine/subdev functions
+ ******************************************************************************/
+
+static int
+nv10_sw_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+            struct nvkm_oclass *oclass, void *data, u32 size,
+            struct nvkm_object **pobject)
+{
+       struct nv10_sw_priv *priv;
+       int ret;
+
+       ret = nvkm_sw_create(parent, engine, oclass, &priv);
+       *pobject = nv_object(priv);
+       if (ret)
+               return ret;
+
+       nv_engine(priv)->cclass = &nv10_sw_cclass;
+       nv_engine(priv)->sclass = nv10_sw_sclass;
+       nv_subdev(priv)->intr = nv04_sw_intr;
+       return 0;
+}
+
+struct nvkm_oclass *
+nv10_sw_oclass = &(struct nvkm_oclass) {
+       .handle = NV_ENGINE(SW, 0x10),
+       .ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = nv10_sw_ctor,
+               .dtor = _nvkm_sw_dtor,
+               .init = _nvkm_sw_init,
+               .fini = _nvkm_sw_fini,
+       },
+};
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/sw/nv50.c b/drivers/gpu/drm/nouveau/nvkm/engine/sw/nv50.c
new file mode 100644 (file)
index 0000000..401fcd7
--- /dev/null
@@ -0,0 +1,234 @@
+/*
+ * Copyright 2012 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 "nv50.h"
+
+#include <core/device.h>
+#include <core/handle.h>
+#include <core/namedb.h>
+#include <engine/disp.h>
+#include <subdev/bar.h>
+
+#include <nvif/event.h>
+
+/*******************************************************************************
+ * software object classes
+ ******************************************************************************/
+
+static int
+nv50_sw_mthd_dma_vblsem(struct nvkm_object *object, u32 mthd,
+                       void *args, u32 size)
+{
+       struct nv50_sw_chan *chan = (void *)nv_engctx(object->parent);
+       struct nvkm_fifo_chan *fifo = (void *)nv_object(chan)->parent;
+       struct nvkm_handle *handle;
+       int ret = -EINVAL;
+
+       handle = nvkm_namedb_get(nv_namedb(fifo), *(u32 *)args);
+       if (!handle)
+               return -ENOENT;
+
+       if (nv_iclass(handle->object, NV_GPUOBJ_CLASS)) {
+               struct nvkm_gpuobj *gpuobj = nv_gpuobj(handle->object);
+               chan->vblank.ctxdma = gpuobj->node->offset >> 4;
+               ret = 0;
+       }
+       nvkm_namedb_put(handle);
+       return ret;
+}
+
+static int
+nv50_sw_mthd_vblsem_offset(struct nvkm_object *object, u32 mthd,
+                          void *args, u32 size)
+{
+       struct nv50_sw_chan *chan = (void *)nv_engctx(object->parent);
+       chan->vblank.offset = *(u32 *)args;
+       return 0;
+}
+
+int
+nv50_sw_mthd_vblsem_value(struct nvkm_object *object, u32 mthd,
+                         void *args, u32 size)
+{
+       struct nv50_sw_chan *chan = (void *)nv_engctx(object->parent);
+       chan->vblank.value = *(u32 *)args;
+       return 0;
+}
+
+int
+nv50_sw_mthd_vblsem_release(struct nvkm_object *object, u32 mthd,
+                           void *args, u32 size)
+{
+       struct nv50_sw_chan *chan = (void *)nv_engctx(object->parent);
+       u32 head = *(u32 *)args;
+       if (head >= nvkm_disp(chan)->vblank.index_nr)
+               return -EINVAL;
+
+       nvkm_notify_get(&chan->vblank.notify[head]);
+       return 0;
+}
+
+int
+nv50_sw_mthd_flip(struct nvkm_object *object, u32 mthd, void *args, u32 size)
+{
+       struct nv50_sw_chan *chan = (void *)nv_engctx(object->parent);
+       if (chan->base.flip)
+               return chan->base.flip(chan->base.flip_data);
+       return -EINVAL;
+}
+
+static struct nvkm_omthds
+nv50_sw_omthds[] = {
+       { 0x018c, 0x018c, nv50_sw_mthd_dma_vblsem },
+       { 0x0400, 0x0400, nv50_sw_mthd_vblsem_offset },
+       { 0x0404, 0x0404, nv50_sw_mthd_vblsem_value },
+       { 0x0408, 0x0408, nv50_sw_mthd_vblsem_release },
+       { 0x0500, 0x0500, nv50_sw_mthd_flip },
+       {}
+};
+
+static struct nvkm_oclass
+nv50_sw_sclass[] = {
+       { 0x506e, &nvkm_object_ofuncs, nv50_sw_omthds },
+       {}
+};
+
+/*******************************************************************************
+ * software context
+ ******************************************************************************/
+
+static int
+nv50_sw_vblsem_release(struct nvkm_notify *notify)
+{
+       struct nv50_sw_chan *chan =
+               container_of(notify, typeof(*chan), vblank.notify[notify->index]);
+       struct nv50_sw_priv *priv = (void *)nv_object(chan)->engine;
+       struct nvkm_bar *bar = nvkm_bar(priv);
+
+       nv_wr32(priv, 0x001704, chan->vblank.channel);
+       nv_wr32(priv, 0x001710, 0x80000000 | chan->vblank.ctxdma);
+       bar->flush(bar);
+
+       if (nv_device(priv)->chipset == 0x50) {
+               nv_wr32(priv, 0x001570, chan->vblank.offset);
+               nv_wr32(priv, 0x001574, chan->vblank.value);
+       } else {
+               nv_wr32(priv, 0x060010, chan->vblank.offset);
+               nv_wr32(priv, 0x060014, chan->vblank.value);
+       }
+
+       return NVKM_NOTIFY_DROP;
+}
+
+void
+nv50_sw_context_dtor(struct nvkm_object *object)
+{
+       struct nv50_sw_chan *chan = (void *)object;
+       int i;
+
+       for (i = 0; i < ARRAY_SIZE(chan->vblank.notify); i++)
+               nvkm_notify_fini(&chan->vblank.notify[i]);
+
+       nvkm_sw_context_destroy(&chan->base);
+}
+
+int
+nv50_sw_context_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+                    struct nvkm_oclass *oclass, void *data, u32 size,
+                    struct nvkm_object **pobject)
+{
+       struct nvkm_disp *pdisp = nvkm_disp(parent);
+       struct nv50_sw_cclass *pclass = (void *)oclass;
+       struct nv50_sw_chan *chan;
+       int ret, i;
+
+       ret = nvkm_sw_context_create(parent, engine, oclass, &chan);
+       *pobject = nv_object(chan);
+       if (ret)
+               return ret;
+
+       for (i = 0; pdisp && i < pdisp->vblank.index_nr; i++) {
+               ret = nvkm_notify_init(NULL, &pdisp->vblank, pclass->vblank,
+                                      false,
+                                      &(struct nvif_notify_head_req_v0) {
+                                       .head = i,
+                                      },
+                                      sizeof(struct nvif_notify_head_req_v0),
+                                      sizeof(struct nvif_notify_head_rep_v0),
+                                      &chan->vblank.notify[i]);
+               if (ret)
+                       return ret;
+       }
+
+       chan->vblank.channel = nv_gpuobj(parent->parent)->addr >> 12;
+       return 0;
+}
+
+static struct nv50_sw_cclass
+nv50_sw_cclass = {
+       .base.handle = NV_ENGCTX(SW, 0x50),
+       .base.ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = nv50_sw_context_ctor,
+               .dtor = nv50_sw_context_dtor,
+               .init = _nvkm_sw_context_init,
+               .fini = _nvkm_sw_context_fini,
+       },
+       .vblank = nv50_sw_vblsem_release,
+};
+
+/*******************************************************************************
+ * software engine/subdev functions
+ ******************************************************************************/
+
+int
+nv50_sw_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+            struct nvkm_oclass *oclass, void *data, u32 size,
+            struct nvkm_object **pobject)
+{
+       struct nv50_sw_oclass *pclass = (void *)oclass;
+       struct nv50_sw_priv *priv;
+       int ret;
+
+       ret = nvkm_sw_create(parent, engine, oclass, &priv);
+       *pobject = nv_object(priv);
+       if (ret)
+               return ret;
+
+       nv_engine(priv)->cclass = pclass->cclass;
+       nv_engine(priv)->sclass = pclass->sclass;
+       nv_subdev(priv)->intr = nv04_sw_intr;
+       return 0;
+}
+
+struct nvkm_oclass *
+nv50_sw_oclass = &(struct nv50_sw_oclass) {
+       .base.handle = NV_ENGINE(SW, 0x50),
+       .base.ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = nv50_sw_ctor,
+               .dtor = _nvkm_sw_dtor,
+               .init = _nvkm_sw_init,
+               .fini = _nvkm_sw_fini,
+       },
+       .cclass = &nv50_sw_cclass.base,
+       .sclass =  nv50_sw_sclass,
+}.base;
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/sw/nv50.h b/drivers/gpu/drm/nouveau/nvkm/engine/sw/nv50.h
new file mode 100644 (file)
index 0000000..d8adc11
--- /dev/null
@@ -0,0 +1,45 @@
+#ifndef __NVKM_SW_NV50_H__
+#define __NVKM_SW_NV50_H__
+#include <engine/sw.h>
+#include <core/notify.h>
+
+struct nv50_sw_oclass {
+       struct nvkm_oclass base;
+       struct nvkm_oclass *cclass;
+       struct nvkm_oclass *sclass;
+};
+
+struct nv50_sw_priv {
+       struct nvkm_sw base;
+};
+
+int  nv50_sw_ctor(struct nvkm_object *, struct nvkm_object *,
+                       struct nvkm_oclass *, void *, u32,
+                       struct nvkm_object **);
+
+struct nv50_sw_cclass {
+       struct nvkm_oclass base;
+       int (*vblank)(struct nvkm_notify *);
+};
+
+struct nv50_sw_chan {
+       struct nvkm_sw_chan base;
+       struct {
+               struct nvkm_notify notify[4];
+               u32 channel;
+               u32 ctxdma;
+               u64 offset;
+               u32 value;
+       } vblank;
+};
+
+int  nv50_sw_context_ctor(struct nvkm_object *,
+                               struct nvkm_object *,
+                               struct nvkm_oclass *, void *, u32,
+                               struct nvkm_object **);
+void nv50_sw_context_dtor(struct nvkm_object *);
+
+int nv50_sw_mthd_vblsem_value(struct nvkm_object *, u32, void *, u32);
+int nv50_sw_mthd_vblsem_release(struct nvkm_object *, u32, void *, u32);
+int nv50_sw_mthd_flip(struct nvkm_object *, u32, void *, u32);
+#endif
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/vp/Kbuild b/drivers/gpu/drm/nouveau/nvkm/engine/vp/Kbuild
new file mode 100644 (file)
index 0000000..6b390eb
--- /dev/null
@@ -0,0 +1 @@
+nvkm-y += nvkm/engine/vp/g84.o
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/vp/g84.c b/drivers/gpu/drm/nouveau/nvkm/engine/vp/g84.c
new file mode 100644 (file)
index 0000000..45f4e18
--- /dev/null
@@ -0,0 +1,93 @@
+/*
+ * Copyright 2012 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, Ilia Mirkin
+ */
+#include <engine/vp.h>
+#include <engine/xtensa.h>
+
+#include <core/engctx.h>
+
+/*******************************************************************************
+ * VP object classes
+ ******************************************************************************/
+
+static struct nvkm_oclass
+g84_vp_sclass[] = {
+       { 0x7476, &nvkm_object_ofuncs },
+       {},
+};
+
+/*******************************************************************************
+ * PVP context
+ ******************************************************************************/
+
+static struct nvkm_oclass
+g84_vp_cclass = {
+       .handle = NV_ENGCTX(VP, 0x84),
+       .ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = _nvkm_xtensa_engctx_ctor,
+               .dtor = _nvkm_engctx_dtor,
+               .init = _nvkm_engctx_init,
+               .fini = _nvkm_engctx_fini,
+               .rd32 = _nvkm_engctx_rd32,
+               .wr32 = _nvkm_engctx_wr32,
+       },
+};
+
+/*******************************************************************************
+ * PVP engine/subdev functions
+ ******************************************************************************/
+
+static int
+g84_vp_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+           struct nvkm_oclass *oclass, void *data, u32 size,
+           struct nvkm_object **pobject)
+{
+       struct nvkm_xtensa *priv;
+       int ret;
+
+       ret = nvkm_xtensa_create(parent, engine, oclass, 0xf000, true,
+                                "PVP", "vp", &priv);
+       *pobject = nv_object(priv);
+       if (ret)
+               return ret;
+
+       nv_subdev(priv)->unit = 0x01020000;
+       nv_engine(priv)->cclass = &g84_vp_cclass;
+       nv_engine(priv)->sclass = g84_vp_sclass;
+       priv->fifo_val = 0x111;
+       priv->unkd28 = 0x9c544;
+       return 0;
+}
+
+struct nvkm_oclass
+g84_vp_oclass = {
+       .handle = NV_ENGINE(VP, 0x84),
+       .ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = g84_vp_ctor,
+               .dtor = _nvkm_xtensa_dtor,
+               .init = _nvkm_xtensa_init,
+               .fini = _nvkm_xtensa_fini,
+               .rd32 = _nvkm_xtensa_rd32,
+               .wr32 = _nvkm_xtensa_wr32,
+       },
+};
diff --git a/drivers/gpu/drm/nouveau/nvkm/engine/xtensa.c b/drivers/gpu/drm/nouveau/nvkm/engine/xtensa.c
new file mode 100644 (file)
index 0000000..cea90df
--- /dev/null
@@ -0,0 +1,172 @@
+/*
+ * Copyright 2013 Ilia Mirkin
+ *
+ * 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.
+ */
+#include <engine/xtensa.h>
+#include <core/device.h>
+
+#include <core/engctx.h>
+
+u32
+_nvkm_xtensa_rd32(struct nvkm_object *object, u64 addr)
+{
+       struct nvkm_xtensa *xtensa = (void *)object;
+       return nv_rd32(xtensa, xtensa->addr + addr);
+}
+
+void
+_nvkm_xtensa_wr32(struct nvkm_object *object, u64 addr, u32 data)
+{
+       struct nvkm_xtensa *xtensa = (void *)object;
+       nv_wr32(xtensa, xtensa->addr + addr, data);
+}
+
+int
+_nvkm_xtensa_engctx_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+                        struct nvkm_oclass *oclass, void *data, u32 size,
+                        struct nvkm_object **pobject)
+{
+       struct nvkm_engctx *engctx;
+       int ret;
+
+       ret = nvkm_engctx_create(parent, engine, oclass, NULL, 0x10000, 0x1000,
+                                NVOBJ_FLAG_ZERO_ALLOC, &engctx);
+       *pobject = nv_object(engctx);
+       return ret;
+}
+
+void
+_nvkm_xtensa_intr(struct nvkm_subdev *subdev)
+{
+       struct nvkm_xtensa *xtensa = (void *)subdev;
+       u32 unk104 = nv_ro32(xtensa, 0xd04);
+       u32 intr = nv_ro32(xtensa, 0xc20);
+       u32 chan = nv_ro32(xtensa, 0xc28);
+       u32 unk10c = nv_ro32(xtensa, 0xd0c);
+
+       if (intr & 0x10)
+               nv_warn(xtensa, "Watchdog interrupt, engine hung.\n");
+       nv_wo32(xtensa, 0xc20, intr);
+       intr = nv_ro32(xtensa, 0xc20);
+       if (unk104 == 0x10001 && unk10c == 0x200 && chan && !intr) {
+               nv_debug(xtensa, "Enabling FIFO_CTRL\n");
+               nv_mask(xtensa, xtensa->addr + 0xd94, 0, xtensa->fifo_val);
+       }
+}
+
+int
+nvkm_xtensa_create_(struct nvkm_object *parent, struct nvkm_object *engine,
+                   struct nvkm_oclass *oclass, u32 addr, bool enable,
+                   const char *iname, const char *fname,
+                   int length, void **pobject)
+{
+       struct nvkm_xtensa *xtensa;
+       int ret;
+
+       ret = nvkm_engine_create_(parent, engine, oclass, enable, iname,
+                                 fname, length, pobject);
+       xtensa = *pobject;
+       if (ret)
+               return ret;
+
+       nv_subdev(xtensa)->intr = _nvkm_xtensa_intr;
+       xtensa->addr = addr;
+       return 0;
+}
+
+int
+_nvkm_xtensa_init(struct nvkm_object *object)
+{
+       struct nvkm_device *device = nv_device(object);
+       struct nvkm_xtensa *xtensa = (void *)object;
+       const struct firmware *fw;
+       char name[32];
+       int i, ret;
+       u32 tmp;
+
+       ret = nvkm_engine_init(&xtensa->base);
+       if (ret)
+               return ret;
+
+       if (!xtensa->gpu_fw) {
+               snprintf(name, sizeof(name), "nouveau/nv84_xuc%03x",
+                        xtensa->addr >> 12);
+
+               ret = request_firmware(&fw, name, nv_device_base(device));
+               if (ret) {
+                       nv_warn(xtensa, "unable to load firmware %s\n", name);
+                       return ret;
+               }
+
+               if (fw->size > 0x40000) {
+                       nv_warn(xtensa, "firmware %s too large\n", name);
+                       release_firmware(fw);
+                       return -EINVAL;
+               }
+
+               ret = nvkm_gpuobj_new(object, NULL, 0x40000, 0x1000, 0,
+                                     &xtensa->gpu_fw);
+               if (ret) {
+                       release_firmware(fw);
+                       return ret;
+               }
+
+               nv_debug(xtensa, "Loading firmware to address: 0x%llx\n",
+                        xtensa->gpu_fw->addr);
+
+               for (i = 0; i < fw->size / 4; i++)
+                       nv_wo32(xtensa->gpu_fw, i * 4, *((u32 *)fw->data + i));
+               release_firmware(fw);
+       }
+
+       nv_wo32(xtensa, 0xd10, 0x1fffffff); /* ?? */
+       nv_wo32(xtensa, 0xd08, 0x0fffffff); /* ?? */
+
+       nv_wo32(xtensa, 0xd28, xtensa->unkd28); /* ?? */
+       nv_wo32(xtensa, 0xc20, 0x3f); /* INTR */
+       nv_wo32(xtensa, 0xd84, 0x3f); /* INTR_EN */
+
+       nv_wo32(xtensa, 0xcc0, xtensa->gpu_fw->addr >> 8); /* XT_REGION_BASE */
+       nv_wo32(xtensa, 0xcc4, 0x1c); /* XT_REGION_SETUP */
+       nv_wo32(xtensa, 0xcc8, xtensa->gpu_fw->size >> 8); /* XT_REGION_LIMIT */
+
+       tmp = nv_rd32(xtensa, 0x0);
+       nv_wo32(xtensa, 0xde0, tmp); /* SCRATCH_H2X */
+
+       nv_wo32(xtensa, 0xce8, 0xf); /* XT_REGION_SETUP */
+
+       nv_wo32(xtensa, 0xc20, 0x3f); /* INTR */
+       nv_wo32(xtensa, 0xd84, 0x3f); /* INTR_EN */
+       return 0;
+}
+
+int
+_nvkm_xtensa_fini(struct nvkm_object *object, bool suspend)
+{
+       struct nvkm_xtensa *xtensa = (void *)object;
+
+       nv_wo32(xtensa, 0xd84, 0); /* INTR_EN */
+       nv_wo32(xtensa, 0xd94, 0); /* FIFO_CTRL */
+
+       if (!suspend)
+               nvkm_gpuobj_ref(NULL, &xtensa->gpu_fw);
+
+       return nvkm_engine_fini(&xtensa->base, suspend);
+}
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/Kbuild b/drivers/gpu/drm/nouveau/nvkm/subdev/Kbuild
new file mode 100644 (file)
index 0000000..a1bb3e4
--- /dev/null
@@ -0,0 +1,19 @@
+include $(src)/nvkm/subdev/bar/Kbuild
+include $(src)/nvkm/subdev/bios/Kbuild
+include $(src)/nvkm/subdev/bus/Kbuild
+include $(src)/nvkm/subdev/clk/Kbuild
+include $(src)/nvkm/subdev/devinit/Kbuild
+include $(src)/nvkm/subdev/fb/Kbuild
+include $(src)/nvkm/subdev/fuse/Kbuild
+include $(src)/nvkm/subdev/gpio/Kbuild
+include $(src)/nvkm/subdev/i2c/Kbuild
+include $(src)/nvkm/subdev/ibus/Kbuild
+include $(src)/nvkm/subdev/instmem/Kbuild
+include $(src)/nvkm/subdev/ltc/Kbuild
+include $(src)/nvkm/subdev/mc/Kbuild
+include $(src)/nvkm/subdev/mmu/Kbuild
+include $(src)/nvkm/subdev/mxm/Kbuild
+include $(src)/nvkm/subdev/pmu/Kbuild
+include $(src)/nvkm/subdev/therm/Kbuild
+include $(src)/nvkm/subdev/timer/Kbuild
+include $(src)/nvkm/subdev/volt/Kbuild
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/bar/Kbuild b/drivers/gpu/drm/nouveau/nvkm/subdev/bar/Kbuild
new file mode 100644 (file)
index 0000000..1ab554a
--- /dev/null
@@ -0,0 +1,4 @@
+nvkm-y += nvkm/subdev/bar/base.o
+nvkm-y += nvkm/subdev/bar/nv50.o
+nvkm-y += nvkm/subdev/bar/gf100.o
+nvkm-y += nvkm/subdev/bar/gk20a.o
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/bar/base.c b/drivers/gpu/drm/nouveau/nvkm/subdev/bar/base.c
new file mode 100644 (file)
index 0000000..3502d00
--- /dev/null
@@ -0,0 +1,144 @@
+/*
+ * Copyright 2012 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 "priv.h"
+
+#include <core/device.h>
+#include <subdev/fb.h>
+#include <subdev/mmu.h>
+
+struct nvkm_barobj {
+       struct nvkm_object base;
+       struct nvkm_vma vma;
+       void __iomem *iomem;
+};
+
+static int
+nvkm_barobj_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+                struct nvkm_oclass *oclass, void *data, u32 size,
+                struct nvkm_object **pobject)
+{
+       struct nvkm_device *device = nv_device(parent);
+       struct nvkm_bar *bar = nvkm_bar(device);
+       struct nvkm_mem *mem = data;
+       struct nvkm_barobj *barobj;
+       int ret;
+
+       ret = nvkm_object_create(parent, engine, oclass, 0, &barobj);
+       *pobject = nv_object(barobj);
+       if (ret)
+               return ret;
+
+       ret = bar->kmap(bar, mem, NV_MEM_ACCESS_RW, &barobj->vma);
+       if (ret)
+               return ret;
+
+       barobj->iomem = ioremap(nv_device_resource_start(device, 3) +
+                               (u32)barobj->vma.offset, mem->size << 12);
+       if (!barobj->iomem) {
+               nv_warn(bar, "PRAMIN ioremap failed\n");
+               return -ENOMEM;
+       }
+
+       return 0;
+}
+
+static void
+nvkm_barobj_dtor(struct nvkm_object *object)
+{
+       struct nvkm_bar *bar = nvkm_bar(object);
+       struct nvkm_barobj *barobj = (void *)object;
+       if (barobj->vma.node) {
+               if (barobj->iomem)
+                       iounmap(barobj->iomem);
+               bar->unmap(bar, &barobj->vma);
+       }
+       nvkm_object_destroy(&barobj->base);
+}
+
+static u32
+nvkm_barobj_rd32(struct nvkm_object *object, u64 addr)
+{
+       struct nvkm_barobj *barobj = (void *)object;
+       return ioread32_native(barobj->iomem + addr);
+}
+
+static void
+nvkm_barobj_wr32(struct nvkm_object *object, u64 addr, u32 data)
+{
+       struct nvkm_barobj *barobj = (void *)object;
+       iowrite32_native(data, barobj->iomem + addr);
+}
+
+static struct nvkm_oclass
+nvkm_barobj_oclass = {
+       .ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = nvkm_barobj_ctor,
+               .dtor = nvkm_barobj_dtor,
+               .init = nvkm_object_init,
+               .fini = nvkm_object_fini,
+               .rd32 = nvkm_barobj_rd32,
+               .wr32 = nvkm_barobj_wr32,
+       },
+};
+
+int
+nvkm_bar_alloc(struct nvkm_bar *bar, struct nvkm_object *parent,
+              struct nvkm_mem *mem, struct nvkm_object **pobject)
+{
+       struct nvkm_object *gpuobj;
+       int ret = nvkm_object_ctor(parent, &parent->engine->subdev.object,
+                                  &nvkm_barobj_oclass, mem, 0, &gpuobj);
+       if (ret == 0)
+               *pobject = gpuobj;
+       return ret;
+}
+
+int
+nvkm_bar_create_(struct nvkm_object *parent, struct nvkm_object *engine,
+                struct nvkm_oclass *oclass, int length, void **pobject)
+{
+       struct nvkm_bar *bar;
+       int ret;
+
+       ret = nvkm_subdev_create_(parent, engine, oclass, 0, "BARCTL",
+                                 "bar", length, pobject);
+       bar = *pobject;
+       if (ret)
+               return ret;
+
+       return 0;
+}
+
+void
+nvkm_bar_destroy(struct nvkm_bar *bar)
+{
+       nvkm_subdev_destroy(&bar->base);
+}
+
+void
+_nvkm_bar_dtor(struct nvkm_object *object)
+{
+       struct nvkm_bar *bar = (void *)object;
+       nvkm_bar_destroy(bar);
+}
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/bar/gf100.c b/drivers/gpu/drm/nouveau/nvkm/subdev/bar/gf100.c
new file mode 100644 (file)
index 0000000..12a1aeb
--- /dev/null
@@ -0,0 +1,219 @@
+/*
+ * Copyright 2012 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 "priv.h"
+
+#include <core/device.h>
+#include <core/gpuobj.h>
+#include <subdev/fb.h>
+#include <subdev/mmu.h>
+
+struct gf100_bar_priv_vm {
+       struct nvkm_gpuobj *mem;
+       struct nvkm_gpuobj *pgd;
+       struct nvkm_vm *vm;
+};
+
+struct gf100_bar_priv {
+       struct nvkm_bar base;
+       spinlock_t lock;
+       struct gf100_bar_priv_vm bar[2];
+};
+
+static int
+gf100_bar_kmap(struct nvkm_bar *bar, struct nvkm_mem *mem, u32 flags,
+              struct nvkm_vma *vma)
+{
+       struct gf100_bar_priv *priv = (void *)bar;
+       int ret;
+
+       ret = nvkm_vm_get(priv->bar[0].vm, mem->size << 12, 12, flags, vma);
+       if (ret)
+               return ret;
+
+       nvkm_vm_map(vma, mem);
+       return 0;
+}
+
+static int
+gf100_bar_umap(struct nvkm_bar *bar, struct nvkm_mem *mem, u32 flags,
+              struct nvkm_vma *vma)
+{
+       struct gf100_bar_priv *priv = (void *)bar;
+       int ret;
+
+       ret = nvkm_vm_get(priv->bar[1].vm, mem->size << 12,
+                         mem->page_shift, flags, vma);
+       if (ret)
+               return ret;
+
+       nvkm_vm_map(vma, mem);
+       return 0;
+}
+
+static void
+gf100_bar_unmap(struct nvkm_bar *bar, struct nvkm_vma *vma)
+{
+       nvkm_vm_unmap(vma);
+       nvkm_vm_put(vma);
+}
+
+static int
+gf100_bar_ctor_vm(struct gf100_bar_priv *priv, struct gf100_bar_priv_vm *bar_vm,
+                 int bar_nr)
+{
+       struct nvkm_device *device = nv_device(&priv->base);
+       struct nvkm_vm *vm;
+       resource_size_t bar_len;
+       int ret;
+
+       ret = nvkm_gpuobj_new(nv_object(priv), NULL, 0x1000, 0, 0,
+                             &bar_vm->mem);
+       if (ret)
+               return ret;
+
+       ret = nvkm_gpuobj_new(nv_object(priv), NULL, 0x8000, 0, 0,
+                             &bar_vm->pgd);
+       if (ret)
+               return ret;
+
+       bar_len = nv_device_resource_len(device, bar_nr);
+
+       ret = nvkm_vm_new(device, 0, bar_len, 0, &vm);
+       if (ret)
+               return ret;
+
+       atomic_inc(&vm->engref[NVDEV_SUBDEV_BAR]);
+
+       /*
+        * Bootstrap page table lookup.
+        */
+       if (bar_nr == 3) {
+               ret = nvkm_gpuobj_new(nv_object(priv), NULL,
+                                     (bar_len >> 12) * 8, 0x1000,
+                                     NVOBJ_FLAG_ZERO_ALLOC,
+                                     &vm->pgt[0].obj[0]);
+               vm->pgt[0].refcount[0] = 1;
+               if (ret)
+                       return ret;
+       }
+
+       ret = nvkm_vm_ref(vm, &bar_vm->vm, bar_vm->pgd);
+       nvkm_vm_ref(NULL, &vm, NULL);
+       if (ret)
+               return ret;
+
+       nv_wo32(bar_vm->mem, 0x0200, lower_32_bits(bar_vm->pgd->addr));
+       nv_wo32(bar_vm->mem, 0x0204, upper_32_bits(bar_vm->pgd->addr));
+       nv_wo32(bar_vm->mem, 0x0208, lower_32_bits(bar_len - 1));
+       nv_wo32(bar_vm->mem, 0x020c, upper_32_bits(bar_len - 1));
+       return 0;
+}
+
+int
+gf100_bar_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+              struct nvkm_oclass *oclass, void *data, u32 size,
+              struct nvkm_object **pobject)
+{
+       struct nvkm_device *device = nv_device(parent);
+       struct gf100_bar_priv *priv;
+       bool has_bar3 = nv_device_resource_len(device, 3) != 0;
+       int ret;
+
+       ret = nvkm_bar_create(parent, engine, oclass, &priv);
+       *pobject = nv_object(priv);
+       if (ret)
+               return ret;
+
+       /* BAR3 */
+       if (has_bar3) {
+               ret = gf100_bar_ctor_vm(priv, &priv->bar[0], 3);
+               if (ret)
+                       return ret;
+       }
+
+       /* BAR1 */
+       ret = gf100_bar_ctor_vm(priv, &priv->bar[1], 1);
+       if (ret)
+               return ret;
+
+       if (has_bar3) {
+               priv->base.alloc = nvkm_bar_alloc;
+               priv->base.kmap = gf100_bar_kmap;
+       }
+       priv->base.umap = gf100_bar_umap;
+       priv->base.unmap = gf100_bar_unmap;
+       priv->base.flush = g84_bar_flush;
+       spin_lock_init(&priv->lock);
+       return 0;
+}
+
+void
+gf100_bar_dtor(struct nvkm_object *object)
+{
+       struct gf100_bar_priv *priv = (void *)object;
+
+       nvkm_vm_ref(NULL, &priv->bar[1].vm, priv->bar[1].pgd);
+       nvkm_gpuobj_ref(NULL, &priv->bar[1].pgd);
+       nvkm_gpuobj_ref(NULL, &priv->bar[1].mem);
+
+       if (priv->bar[0].vm) {
+               nvkm_gpuobj_ref(NULL, &priv->bar[0].vm->pgt[0].obj[0]);
+               nvkm_vm_ref(NULL, &priv->bar[0].vm, priv->bar[0].pgd);
+       }
+       nvkm_gpuobj_ref(NULL, &priv->bar[0].pgd);
+       nvkm_gpuobj_ref(NULL, &priv->bar[0].mem);
+
+       nvkm_bar_destroy(&priv->base);
+}
+
+int
+gf100_bar_init(struct nvkm_object *object)
+{
+       struct gf100_bar_priv *priv = (void *)object;
+       int ret;
+
+       ret = nvkm_bar_init(&priv->base);
+       if (ret)
+               return ret;
+
+       nv_mask(priv, 0x000200, 0x00000100, 0x00000000);
+       nv_mask(priv, 0x000200, 0x00000100, 0x00000100);
+
+       nv_wr32(priv, 0x001704, 0x80000000 | priv->bar[1].mem->addr >> 12);
+       if (priv->bar[0].mem)
+               nv_wr32(priv, 0x001714,
+                       0xc0000000 | priv->bar[0].mem->addr >> 12);
+       return 0;
+}
+
+struct nvkm_oclass
+gf100_bar_oclass = {
+       .handle = NV_SUBDEV(BAR, 0xc0),
+       .ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = gf100_bar_ctor,
+               .dtor = gf100_bar_dtor,
+               .init = gf100_bar_init,
+               .fini = _nvkm_bar_fini,
+       },
+};
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/bar/gk20a.c b/drivers/gpu/drm/nouveau/nvkm/subdev/bar/gk20a.c
new file mode 100644 (file)
index 0000000..148f739
--- /dev/null
@@ -0,0 +1,50 @@
+/*
+ * Copyright (c) 2014, NVIDIA CORPORATION. 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 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 "priv.h"
+
+int
+gk20a_bar_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+              struct nvkm_oclass *oclass, void *data, u32 size,
+              struct nvkm_object **pobject)
+{
+       struct nvkm_bar *bar;
+       int ret;
+
+       ret = gf100_bar_ctor(parent, engine, oclass, data, size, pobject);
+       if (ret)
+               return ret;
+
+       bar = (struct nvkm_bar *)*pobject;
+       bar->iomap_uncached = true;
+       return 0;
+}
+
+struct nvkm_oclass
+gk20a_bar_oclass = {
+       .handle = NV_SUBDEV(BAR, 0xea),
+       .ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = gk20a_bar_ctor,
+               .dtor = gf100_bar_dtor,
+               .init = gf100_bar_init,
+               .fini = _nvkm_bar_fini,
+       },
+};
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/bar/nv50.c b/drivers/gpu/drm/nouveau/nvkm/subdev/bar/nv50.c
new file mode 100644 (file)
index 0000000..8548adb
--- /dev/null
@@ -0,0 +1,271 @@
+/*
+ * Copyright 2012 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 "priv.h"
+
+#include <core/device.h>
+#include <core/gpuobj.h>
+#include <subdev/fb.h>
+#include <subdev/mmu.h>
+#include <subdev/timer.h>
+
+struct nv50_bar_priv {
+       struct nvkm_bar base;
+       spinlock_t lock;
+       struct nvkm_gpuobj *mem;
+       struct nvkm_gpuobj *pad;
+       struct nvkm_gpuobj *pgd;
+       struct nvkm_vm *bar1_vm;
+       struct nvkm_gpuobj *bar1;
+       struct nvkm_vm *bar3_vm;
+       struct nvkm_gpuobj *bar3;
+};
+
+static int
+nv50_bar_kmap(struct nvkm_bar *bar, struct nvkm_mem *mem, u32 flags,
+             struct nvkm_vma *vma)
+{
+       struct nv50_bar_priv *priv = (void *)bar;
+       int ret;
+
+       ret = nvkm_vm_get(priv->bar3_vm, mem->size << 12, 12, flags, vma);
+       if (ret)
+               return ret;
+
+       nvkm_vm_map(vma, mem);
+       return 0;
+}
+
+static int
+nv50_bar_umap(struct nvkm_bar *bar, struct nvkm_mem *mem, u32 flags,
+             struct nvkm_vma *vma)
+{
+       struct nv50_bar_priv *priv = (void *)bar;
+       int ret;
+
+       ret = nvkm_vm_get(priv->bar1_vm, mem->size << 12, 12, flags, vma);
+       if (ret)
+               return ret;
+
+       nvkm_vm_map(vma, mem);
+       return 0;
+}
+
+static void
+nv50_bar_unmap(struct nvkm_bar *bar, struct nvkm_vma *vma)
+{
+       nvkm_vm_unmap(vma);
+       nvkm_vm_put(vma);
+}
+
+static void
+nv50_bar_flush(struct nvkm_bar *bar)
+{
+       struct nv50_bar_priv *priv = (void *)bar;
+       unsigned long flags;
+       spin_lock_irqsave(&priv->lock, flags);
+       nv_wr32(priv, 0x00330c, 0x00000001);
+       if (!nv_wait(priv, 0x00330c, 0x00000002, 0x00000000))
+               nv_warn(priv, "flush timeout\n");
+       spin_unlock_irqrestore(&priv->lock, flags);
+}
+
+void
+g84_bar_flush(struct nvkm_bar *bar)
+{
+       struct nv50_bar_priv *priv = (void *)bar;
+       unsigned long flags;
+       spin_lock_irqsave(&priv->lock, flags);
+       nv_wr32(bar, 0x070000, 0x00000001);
+       if (!nv_wait(priv, 0x070000, 0x00000002, 0x00000000))
+               nv_warn(priv, "flush timeout\n");
+       spin_unlock_irqrestore(&priv->lock, flags);
+}
+
+static int
+nv50_bar_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+             struct nvkm_oclass *oclass, void *data, u32 size,
+             struct nvkm_object **pobject)
+{
+       struct nvkm_device *device = nv_device(parent);
+       struct nvkm_object *heap;
+       struct nvkm_vm *vm;
+       struct nv50_bar_priv *priv;
+       u64 start, limit;
+       int ret;
+
+       ret = nvkm_bar_create(parent, engine, oclass, &priv);
+       *pobject = nv_object(priv);
+       if (ret)
+               return ret;
+
+       ret = nvkm_gpuobj_new(nv_object(priv), NULL, 0x20000, 0,
+                             NVOBJ_FLAG_HEAP, &priv->mem);
+       heap = nv_object(priv->mem);
+       if (ret)
+               return ret;
+
+       ret = nvkm_gpuobj_new(nv_object(priv), heap,
+                             (device->chipset == 0x50) ? 0x1400 : 0x0200,
+                             0, 0, &priv->pad);
+       if (ret)
+               return ret;
+
+       ret = nvkm_gpuobj_new(nv_object(priv), heap, 0x4000, 0, 0, &priv->pgd);
+       if (ret)
+               return ret;
+
+       /* BAR3 */
+       start = 0x0100000000ULL;
+       limit = start + nv_device_resource_len(device, 3);
+
+       ret = nvkm_vm_new(device, start, limit, start, &vm);
+       if (ret)
+               return ret;
+
+       atomic_inc(&vm->engref[NVDEV_SUBDEV_BAR]);
+
+       ret = nvkm_gpuobj_new(nv_object(priv), heap,
+                             ((limit-- - start) >> 12) * 8, 0x1000,
+                             NVOBJ_FLAG_ZERO_ALLOC, &vm->pgt[0].obj[0]);
+       vm->pgt[0].refcount[0] = 1;
+       if (ret)
+               return ret;
+
+       ret = nvkm_vm_ref(vm, &priv->bar3_vm, priv->pgd);
+       nvkm_vm_ref(NULL, &vm, NULL);
+       if (ret)
+               return ret;
+
+       ret = nvkm_gpuobj_new(nv_object(priv), heap, 24, 16, 0, &priv->bar3);
+       if (ret)
+               return ret;
+
+       nv_wo32(priv->bar3, 0x00, 0x7fc00000);
+       nv_wo32(priv->bar3, 0x04, lower_32_bits(limit));
+       nv_wo32(priv->bar3, 0x08, lower_32_bits(start));
+       nv_wo32(priv->bar3, 0x0c, upper_32_bits(limit) << 24 |
+                                 upper_32_bits(start));
+       nv_wo32(priv->bar3, 0x10, 0x00000000);
+       nv_wo32(priv->bar3, 0x14, 0x00000000);
+
+       /* BAR1 */
+       start = 0x0000000000ULL;
+       limit = start + nv_device_resource_len(device, 1);
+
+       ret = nvkm_vm_new(device, start, limit--, start, &vm);
+       if (ret)
+               return ret;
+
+       atomic_inc(&vm->engref[NVDEV_SUBDEV_BAR]);
+
+       ret = nvkm_vm_ref(vm, &priv->bar1_vm, priv->pgd);
+       nvkm_vm_ref(NULL, &vm, NULL);
+       if (ret)
+               return ret;
+
+       ret = nvkm_gpuobj_new(nv_object(priv), heap, 24, 16, 0, &priv->bar1);
+       if (ret)
+               return ret;
+
+       nv_wo32(priv->bar1, 0x00, 0x7fc00000);
+       nv_wo32(priv->bar1, 0x04, lower_32_bits(limit));
+       nv_wo32(priv->bar1, 0x08, lower_32_bits(start));
+       nv_wo32(priv->bar1, 0x0c, upper_32_bits(limit) << 24 |
+                                 upper_32_bits(start));
+       nv_wo32(priv->bar1, 0x10, 0x00000000);
+       nv_wo32(priv->bar1, 0x14, 0x00000000);
+
+       priv->base.alloc = nvkm_bar_alloc;
+       priv->base.kmap = nv50_bar_kmap;
+       priv->base.umap = nv50_bar_umap;
+       priv->base.unmap = nv50_bar_unmap;
+       if (device->chipset == 0x50)
+               priv->base.flush = nv50_bar_flush;
+       else
+               priv->base.flush = g84_bar_flush;
+       spin_lock_init(&priv->lock);
+       return 0;
+}
+
+static void
+nv50_bar_dtor(struct nvkm_object *object)
+{
+       struct nv50_bar_priv *priv = (void *)object;
+       nvkm_gpuobj_ref(NULL, &priv->bar1);
+       nvkm_vm_ref(NULL, &priv->bar1_vm, priv->pgd);
+       nvkm_gpuobj_ref(NULL, &priv->bar3);
+       if (priv->bar3_vm) {
+               nvkm_gpuobj_ref(NULL, &priv->bar3_vm->pgt[0].obj[0]);
+               nvkm_vm_ref(NULL, &priv->bar3_vm, priv->pgd);
+       }
+       nvkm_gpuobj_ref(NULL, &priv->pgd);
+       nvkm_gpuobj_ref(NULL, &priv->pad);
+       nvkm_gpuobj_ref(NULL, &priv->mem);
+       nvkm_bar_destroy(&priv->base);
+}
+
+static int
+nv50_bar_init(struct nvkm_object *object)
+{
+       struct nv50_bar_priv *priv = (void *)object;
+       int ret, i;
+
+       ret = nvkm_bar_init(&priv->base);
+       if (ret)
+               return ret;
+
+       nv_mask(priv, 0x000200, 0x00000100, 0x00000000);
+       nv_mask(priv, 0x000200, 0x00000100, 0x00000100);
+       nv_wr32(priv, 0x100c80, 0x00060001);
+       if (!nv_wait(priv, 0x100c80, 0x00000001, 0x00000000)) {
+               nv_error(priv, "vm flush timeout\n");
+               return -EBUSY;
+       }
+
+       nv_wr32(priv, 0x001704, 0x00000000 | priv->mem->addr >> 12);
+       nv_wr32(priv, 0x001704, 0x40000000 | priv->mem->addr >> 12);
+       nv_wr32(priv, 0x001708, 0x80000000 | priv->bar1->node->offset >> 4);
+       nv_wr32(priv, 0x00170c, 0x80000000 | priv->bar3->node->offset >> 4);
+       for (i = 0; i < 8; i++)
+               nv_wr32(priv, 0x001900 + (i * 4), 0x00000000);
+       return 0;
+}
+
+static int
+nv50_bar_fini(struct nvkm_object *object, bool suspend)
+{
+       struct nv50_bar_priv *priv = (void *)object;
+       return nvkm_bar_fini(&priv->base, suspend);
+}
+
+struct nvkm_oclass
+nv50_bar_oclass = {
+       .handle = NV_SUBDEV(BAR, 0x50),
+       .ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = nv50_bar_ctor,
+               .dtor = nv50_bar_dtor,
+               .init = nv50_bar_init,
+               .fini = nv50_bar_fini,
+       },
+};
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/bar/priv.h b/drivers/gpu/drm/nouveau/nvkm/subdev/bar/priv.h
new file mode 100644 (file)
index 0000000..aa85f61
--- /dev/null
@@ -0,0 +1,30 @@
+#ifndef __NVKM_BAR_PRIV_H__
+#define __NVKM_BAR_PRIV_H__
+#include <subdev/bar.h>
+
+#define nvkm_bar_create(p,e,o,d)                                            \
+       nvkm_bar_create_((p), (e), (o), sizeof(**d), (void **)d)
+#define nvkm_bar_init(p)                                                    \
+       nvkm_subdev_init(&(p)->base)
+#define nvkm_bar_fini(p,s)                                                  \
+       nvkm_subdev_fini(&(p)->base, (s))
+
+int nvkm_bar_create_(struct nvkm_object *, struct nvkm_object *,
+                       struct nvkm_oclass *, int, void **);
+void nvkm_bar_destroy(struct nvkm_bar *);
+
+void _nvkm_bar_dtor(struct nvkm_object *);
+#define _nvkm_bar_init _nvkm_subdev_init
+#define _nvkm_bar_fini _nvkm_subdev_fini
+
+int  nvkm_bar_alloc(struct nvkm_bar *, struct nvkm_object *,
+                   struct nvkm_mem *, struct nvkm_object **);
+
+void g84_bar_flush(struct nvkm_bar *);
+
+int gf100_bar_ctor(struct nvkm_object *, struct nvkm_object *,
+                 struct nvkm_oclass *, void *, u32,
+                 struct nvkm_object **);
+void gf100_bar_dtor(struct nvkm_object *);
+int gf100_bar_init(struct nvkm_object *);
+#endif
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/bios/Kbuild b/drivers/gpu/drm/nouveau/nvkm/subdev/bios/Kbuild
new file mode 100644 (file)
index 0000000..64730d5
--- /dev/null
@@ -0,0 +1,37 @@
+nvkm-y += nvkm/subdev/bios/base.o
+nvkm-y += nvkm/subdev/bios/bit.o
+nvkm-y += nvkm/subdev/bios/boost.o
+nvkm-y += nvkm/subdev/bios/conn.o
+nvkm-y += nvkm/subdev/bios/cstep.o
+nvkm-y += nvkm/subdev/bios/dcb.o
+nvkm-y += nvkm/subdev/bios/disp.o
+nvkm-y += nvkm/subdev/bios/dp.o
+nvkm-y += nvkm/subdev/bios/extdev.o
+nvkm-y += nvkm/subdev/bios/fan.o
+nvkm-y += nvkm/subdev/bios/gpio.o
+nvkm-y += nvkm/subdev/bios/i2c.o
+nvkm-y += nvkm/subdev/bios/image.o
+nvkm-y += nvkm/subdev/bios/init.o
+nvkm-y += nvkm/subdev/bios/mxm.o
+nvkm-y += nvkm/subdev/bios/npde.o
+nvkm-y += nvkm/subdev/bios/pcir.o
+nvkm-y += nvkm/subdev/bios/perf.o
+nvkm-y += nvkm/subdev/bios/pll.o
+nvkm-y += nvkm/subdev/bios/pmu.o
+nvkm-y += nvkm/subdev/bios/ramcfg.o
+nvkm-y += nvkm/subdev/bios/rammap.o
+nvkm-y += nvkm/subdev/bios/shadow.o
+nvkm-y += nvkm/subdev/bios/shadowacpi.o
+nvkm-y += nvkm/subdev/bios/shadowof.o
+nvkm-y += nvkm/subdev/bios/shadowpci.o
+nvkm-y += nvkm/subdev/bios/shadowramin.o
+nvkm-y += nvkm/subdev/bios/shadowrom.o
+nvkm-y += nvkm/subdev/bios/timing.o
+nvkm-y += nvkm/subdev/bios/therm.o
+nvkm-y += nvkm/subdev/bios/vmap.o
+nvkm-y += nvkm/subdev/bios/volt.o
+nvkm-y += nvkm/subdev/bios/xpio.o
+nvkm-y += nvkm/subdev/bios/M0203.o
+nvkm-y += nvkm/subdev/bios/M0205.o
+nvkm-y += nvkm/subdev/bios/M0209.o
+nvkm-y += nvkm/subdev/bios/P0260.o
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/bios/M0203.c b/drivers/gpu/drm/nouveau/nvkm/subdev/bios/M0203.c
new file mode 100644 (file)
index 0000000..08eb03f
--- /dev/null
@@ -0,0 +1,128 @@
+/*
+ * Copyright 2014 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 <subdev/bios.h>
+#include <subdev/bios/bit.h>
+#include <subdev/bios/M0203.h>
+
+u32
+nvbios_M0203Te(struct nvkm_bios *bios, u8 *ver, u8 *hdr, u8 *cnt, u8 *len)
+{
+       struct bit_entry bit_M;
+       u32 data = 0x00000000;
+
+       if (!bit_entry(bios, 'M', &bit_M)) {
+               if (bit_M.version == 2 && bit_M.length > 0x04)
+                       data = nv_ro16(bios, bit_M.offset + 0x03);
+               if (data) {
+                       *ver = nv_ro08(bios, data + 0x00);
+                       switch (*ver) {
+                       case 0x10:
+                               *hdr = nv_ro08(bios, data + 0x01);
+                               *len = nv_ro08(bios, data + 0x02);
+                               *cnt = nv_ro08(bios, data + 0x03);
+                               return data;
+                       default:
+                               break;
+                       }
+               }
+       }
+
+       return 0x00000000;
+}
+
+u32
+nvbios_M0203Tp(struct nvkm_bios *bios, u8 *ver, u8 *hdr, u8 *cnt, u8 *len,
+              struct nvbios_M0203T *info)
+{
+       u32 data = nvbios_M0203Te(bios, ver, hdr, cnt, len);
+       memset(info, 0x00, sizeof(*info));
+       switch (!!data * *ver) {
+       case 0x10:
+               info->type    = nv_ro08(bios, data + 0x04);
+               info->pointer = nv_ro16(bios, data + 0x05);
+               break;
+       default:
+               break;
+       }
+       return data;
+}
+
+u32
+nvbios_M0203Ee(struct nvkm_bios *bios, int idx, u8 *ver, u8 *hdr)
+{
+       u8  cnt, len;
+       u32 data = nvbios_M0203Te(bios, ver, hdr, &cnt, &len);
+       if (data && idx < cnt) {
+               data = data + *hdr + idx * len;
+               *hdr = len;
+               return data;
+       }
+       return 0x00000000;
+}
+
+u32
+nvbios_M0203Ep(struct nvkm_bios *bios, int idx, u8 *ver, u8 *hdr,
+              struct nvbios_M0203E *info)
+{
+       u32 data = nvbios_M0203Ee(bios, idx, ver, hdr);
+       memset(info, 0x00, sizeof(*info));
+       switch (!!data * *ver) {
+       case 0x10:
+               info->type  = (nv_ro08(bios, data + 0x00) & 0x0f) >> 0;
+               info->strap = (nv_ro08(bios, data + 0x00) & 0xf0) >> 4;
+               info->group = (nv_ro08(bios, data + 0x01) & 0x0f) >> 0;
+               return data;
+       default:
+               break;
+       }
+       return 0x00000000;
+}
+
+u32
+nvbios_M0203Em(struct nvkm_bios *bios, u8 ramcfg, u8 *ver, u8 *hdr,
+              struct nvbios_M0203E *info)
+{
+       struct nvbios_M0203T M0203T;
+       u8  cnt, len, idx = 0xff;
+       u32 data;
+
+       if (!nvbios_M0203Tp(bios, ver, hdr, &cnt, &len, &M0203T)) {
+               nv_warn(bios, "M0203T not found\n");
+               return 0x00000000;
+       }
+
+       while ((data = nvbios_M0203Ep(bios, ++idx, ver, hdr, info))) {
+               switch (M0203T.type) {
+               case M0203T_TYPE_RAMCFG:
+                       if (info->strap != ramcfg)
+                               continue;
+                       return data;
+               default:
+                       nv_warn(bios, "M0203T type %02x\n", M0203T.type);
+                       return 0x00000000;
+               }
+       }
+
+       return data;
+}
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/bios/M0205.c b/drivers/gpu/drm/nouveau/nvkm/subdev/bios/M0205.c
new file mode 100644 (file)
index 0000000..e1a8ad5
--- /dev/null
@@ -0,0 +1,135 @@
+/*
+ * Copyright 2013 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 <subdev/bios.h>
+#include <subdev/bios/bit.h>
+#include <subdev/bios/M0205.h>
+
+u32
+nvbios_M0205Te(struct nvkm_bios *bios,
+              u8 *ver, u8 *hdr, u8 *cnt, u8 *len, u8 *snr, u8 *ssz)
+{
+       struct bit_entry bit_M;
+       u32 data = 0x00000000;
+
+       if (!bit_entry(bios, 'M', &bit_M)) {
+               if (bit_M.version == 2 && bit_M.length > 0x08)
+                       data = nv_ro32(bios, bit_M.offset + 0x05);
+               if (data) {
+                       *ver = nv_ro08(bios, data + 0x00);
+                       switch (*ver) {
+                       case 0x10:
+                               *hdr = nv_ro08(bios, data + 0x01);
+                               *len = nv_ro08(bios, data + 0x02);
+                               *ssz = nv_ro08(bios, data + 0x03);
+                               *snr = nv_ro08(bios, data + 0x04);
+                               *cnt = nv_ro08(bios, data + 0x05);
+                               return data;
+                       default:
+                               break;
+                       }
+               }
+       }
+
+       return 0x00000000;
+}
+
+u32
+nvbios_M0205Tp(struct nvkm_bios *bios,
+              u8 *ver, u8 *hdr, u8 *cnt, u8 *len, u8 *snr, u8 *ssz,
+              struct nvbios_M0205T *info)
+{
+       u32 data = nvbios_M0205Te(bios, ver, hdr, cnt, len, snr, ssz);
+       memset(info, 0x00, sizeof(*info));
+       switch (!!data * *ver) {
+       case 0x10:
+               info->freq = nv_ro16(bios, data + 0x06);
+               break;
+       default:
+               break;
+       }
+       return data;
+}
+
+u32
+nvbios_M0205Ee(struct nvkm_bios *bios, int idx,
+              u8 *ver, u8 *hdr, u8 *cnt, u8 *len)
+{
+       u8  snr, ssz;
+       u32 data = nvbios_M0205Te(bios, ver, hdr, cnt, len, &snr, &ssz);
+       if (data && idx < *cnt) {
+               data = data + *hdr + idx * (*len + (snr * ssz));
+               *hdr = *len;
+               *cnt = snr;
+               *len = ssz;
+               return data;
+       }
+       return 0x00000000;
+}
+
+u32
+nvbios_M0205Ep(struct nvkm_bios *bios, int idx,
+              u8 *ver, u8 *hdr, u8 *cnt, u8 *len,
+              struct nvbios_M0205E *info)
+{
+       u32 data = nvbios_M0205Ee(bios, idx, ver, hdr, cnt, len);
+       memset(info, 0x00, sizeof(*info));
+       switch (!!data * *ver) {
+       case 0x10:
+               info->type = nv_ro08(bios, data + 0x00) & 0x0f;
+               return data;
+       default:
+               break;
+       }
+       return 0x00000000;
+}
+
+u32
+nvbios_M0205Se(struct nvkm_bios *bios, int ent, int idx, u8 *ver, u8 *hdr)
+{
+
+       u8  cnt, len;
+       u32 data = nvbios_M0205Ee(bios, ent, ver, hdr, &cnt, &len);
+       if (data && idx < cnt) {
+               data = data + *hdr + idx * len;
+               *hdr = len;
+               return data;
+       }
+       return 0x00000000;
+}
+
+u32
+nvbios_M0205Sp(struct nvkm_bios *bios, int ent, int idx, u8 *ver, u8 *hdr,
+              struct nvbios_M0205S *info)
+{
+       u32 data = nvbios_M0205Se(bios, ent, idx, ver, hdr);
+       memset(info, 0x00, sizeof(*info));
+       switch (!!data * *ver) {
+       case 0x10:
+               info->data = nv_ro08(bios, data + 0x00);
+               return data;
+       default:
+               break;
+       }
+       return 0x00000000;
+}
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/bios/M0209.c b/drivers/gpu/drm/nouveau/nvkm/subdev/bios/M0209.c
new file mode 100644 (file)
index 0000000..3026920
--- /dev/null
@@ -0,0 +1,135 @@
+/*
+ * Copyright 2013 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 <subdev/bios.h>
+#include <subdev/bios/bit.h>
+#include <subdev/bios/M0209.h>
+
+u32
+nvbios_M0209Te(struct nvkm_bios *bios,
+              u8 *ver, u8 *hdr, u8 *cnt, u8 *len, u8 *snr, u8 *ssz)
+{
+       struct bit_entry bit_M;
+       u32 data = 0x00000000;
+
+       if (!bit_entry(bios, 'M', &bit_M)) {
+               if (bit_M.version == 2 && bit_M.length > 0x0c)
+                       data = nv_ro32(bios, bit_M.offset + 0x09);
+               if (data) {
+                       *ver = nv_ro08(bios, data + 0x00);
+                       switch (*ver) {
+                       case 0x10:
+                               *hdr = nv_ro08(bios, data + 0x01);
+                               *len = nv_ro08(bios, data + 0x02);
+                               *ssz = nv_ro08(bios, data + 0x03);
+                               *snr = 1;
+                               *cnt = nv_ro08(bios, data + 0x04);
+                               return data;
+                       default:
+                               break;
+                       }
+               }
+       }
+
+       return 0x00000000;
+}
+
+u32
+nvbios_M0209Ee(struct nvkm_bios *bios, int idx,
+              u8 *ver, u8 *hdr, u8 *cnt, u8 *len)
+{
+       u8  snr, ssz;
+       u32 data = nvbios_M0209Te(bios, ver, hdr, cnt, len, &snr, &ssz);
+       if (data && idx < *cnt) {
+               data = data + *hdr + idx * (*len + (snr * ssz));
+               *hdr = *len;
+               *cnt = snr;
+               *len = ssz;
+               return data;
+       }
+       return 0x00000000;
+}
+
+u32
+nvbios_M0209Ep(struct nvkm_bios *bios, int idx,
+              u8 *ver, u8 *hdr, u8 *cnt, u8 *len, struct nvbios_M0209E *info)
+{
+       u32 data = nvbios_M0209Ee(bios, idx, ver, hdr, cnt, len);
+       memset(info, 0x00, sizeof(*info));
+       switch (!!data * *ver) {
+       case 0x10:
+               info->v00_40 = (nv_ro08(bios, data + 0x00) & 0x40) >> 6;
+               info->bits   =  nv_ro08(bios, data + 0x00) & 0x3f;
+               info->modulo =  nv_ro08(bios, data + 0x01);
+               info->v02_40 = (nv_ro08(bios, data + 0x02) & 0x40) >> 6;
+               info->v02_07 =  nv_ro08(bios, data + 0x02) & 0x07;
+               info->v03    =  nv_ro08(bios, data + 0x03);
+               return data;
+       default:
+               break;
+       }
+       return 0x00000000;
+}
+
+u32
+nvbios_M0209Se(struct nvkm_bios *bios, int ent, int idx, u8 *ver, u8 *hdr)
+{
+
+       u8  cnt, len;
+       u32 data = nvbios_M0209Ee(bios, ent, ver, hdr, &cnt, &len);
+       if (data && idx < cnt) {
+               data = data + *hdr + idx * len;
+               *hdr = len;
+               return data;
+       }
+       return 0x00000000;
+}
+
+u32
+nvbios_M0209Sp(struct nvkm_bios *bios, int ent, int idx, u8 *ver, u8 *hdr,
+              struct nvbios_M0209S *info)
+{
+       struct nvbios_M0209E M0209E;
+       u8  cnt, len;
+       u32 data = nvbios_M0209Ep(bios, ent, ver, hdr, &cnt, &len, &M0209E);
+       if (data) {
+               u32 i, data = nvbios_M0209Se(bios, ent, idx, ver, hdr);
+               memset(info, 0x00, sizeof(*info));
+               switch (!!data * *ver) {
+               case 0x10:
+                       for (i = 0; i < ARRAY_SIZE(info->data); i++) {
+                               u32 bits = (i % M0209E.modulo) * M0209E.bits;
+                               u32 mask = (1ULL << M0209E.bits) - 1;
+                               u16  off = bits / 8;
+                               u8   mod = bits % 8;
+                               info->data[i] = nv_ro32(bios, data + off);
+                               info->data[i] = info->data[i] >> mod;
+                               info->data[i] = info->data[i] & mask;
+                       }
+                       return data;
+               default:
+                       break;
+               }
+       }
+       return 0x00000000;
+}
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/bios/P0260.c b/drivers/gpu/drm/nouveau/nvkm/subdev/bios/P0260.c
new file mode 100644 (file)
index 0000000..b72edcf
--- /dev/null
@@ -0,0 +1,107 @@
+/*
+ * Copyright 2013 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 <subdev/bios.h>
+#include <subdev/bios/bit.h>
+#include <subdev/bios/P0260.h>
+
+u32
+nvbios_P0260Te(struct nvkm_bios *bios,
+              u8 *ver, u8 *hdr, u8 *cnt, u8 *len, u8 *xnr, u8 *xsz)
+{
+       struct bit_entry bit_P;
+       u32 data = 0x00000000;
+
+       if (!bit_entry(bios, 'P', &bit_P)) {
+               if (bit_P.version == 2 && bit_P.length > 0x63)
+                       data = nv_ro32(bios, bit_P.offset + 0x60);
+               if (data) {
+                       *ver = nv_ro08(bios, data + 0);
+                       switch (*ver) {
+                       case 0x10:
+                               *hdr = nv_ro08(bios, data + 1);
+                               *cnt = nv_ro08(bios, data + 2);
+                               *len = 4;
+                               *xnr = nv_ro08(bios, data + 3);
+                               *xsz = 4;
+                               return data;
+                       default:
+                               break;
+                       }
+               }
+       }
+
+       return 0x00000000;
+}
+
+u32
+nvbios_P0260Ee(struct nvkm_bios *bios, int idx, u8 *ver, u8 *len)
+{
+       u8  hdr, cnt, xnr, xsz;
+       u32 data = nvbios_P0260Te(bios, ver, &hdr, &cnt, len, &xnr, &xsz);
+       if (data && idx < cnt)
+               return data + hdr + (idx * *len);
+       return 0x00000000;
+}
+
+u32
+nvbios_P0260Ep(struct nvkm_bios *bios, int idx, u8 *ver, u8 *len,
+              struct nvbios_P0260E *info)
+{
+       u32 data = nvbios_P0260Ee(bios, idx, ver, len);
+       memset(info, 0x00, sizeof(*info));
+       switch (!!data * *ver) {
+       case 0x10:
+               info->data = nv_ro32(bios, data);
+               return data;
+       default:
+               break;
+       }
+       return 0x00000000;
+}
+
+u32
+nvbios_P0260Xe(struct nvkm_bios *bios, int idx, u8 *ver, u8 *xsz)
+{
+       u8  hdr, cnt, len, xnr;
+       u32 data = nvbios_P0260Te(bios, ver, &hdr, &cnt, &len, &xnr, xsz);
+       if (data && idx < xnr)
+               return data + hdr + (cnt * len) + (idx * *xsz);
+       return 0x00000000;
+}
+
+u32
+nvbios_P0260Xp(struct nvkm_bios *bios, int idx, u8 *ver, u8 *hdr,
+              struct nvbios_P0260X *info)
+{
+       u32 data = nvbios_P0260Xe(bios, idx, ver, hdr);
+       memset(info, 0x00, sizeof(*info));
+       switch (!!data * *ver) {
+       case 0x10:
+               info->data = nv_ro32(bios, data);
+               return data;
+       default:
+               break;
+       }
+       return 0x00000000;
+}
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/bios/base.c b/drivers/gpu/drm/nouveau/nvkm/subdev/bios/base.c
new file mode 100644 (file)
index 0000000..8db204f
--- /dev/null
@@ -0,0 +1,206 @@
+/*
+ * Copyright 2012 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 "priv.h"
+
+#include <subdev/bios.h>
+#include <subdev/bios/bmp.h>
+#include <subdev/bios/bit.h>
+
+u8
+nvbios_checksum(const u8 *data, int size)
+{
+       u8 sum = 0;
+       while (size--)
+               sum += *data++;
+       return sum;
+}
+
+u16
+nvbios_findstr(const u8 *data, int size, const char *str, int len)
+{
+       int i, j;
+
+       for (i = 0; i <= (size - len); i++) {
+               for (j = 0; j < len; j++)
+                       if ((char)data[i + j] != str[j])
+                               break;
+               if (j == len)
+                       return i;
+       }
+
+       return 0;
+}
+
+int
+nvbios_extend(struct nvkm_bios *bios, u32 length)
+{
+       if (bios->size < length) {
+               u8 *prev = bios->data;
+               if (!(bios->data = kmalloc(length, GFP_KERNEL))) {
+                       bios->data = prev;
+                       return -ENOMEM;
+               }
+               memcpy(bios->data, prev, bios->size);
+               bios->size = length;
+               kfree(prev);
+               return 1;
+       }
+       return 0;
+}
+
+static u8
+nvkm_bios_rd08(struct nvkm_object *object, u64 addr)
+{
+       struct nvkm_bios *bios = (void *)object;
+       return bios->data[addr];
+}
+
+static u16
+nvkm_bios_rd16(struct nvkm_object *object, u64 addr)
+{
+       struct nvkm_bios *bios = (void *)object;
+       return get_unaligned_le16(&bios->data[addr]);
+}
+
+static u32
+nvkm_bios_rd32(struct nvkm_object *object, u64 addr)
+{
+       struct nvkm_bios *bios = (void *)object;
+       return get_unaligned_le32(&bios->data[addr]);
+}
+
+static void
+nvkm_bios_wr08(struct nvkm_object *object, u64 addr, u8 data)
+{
+       struct nvkm_bios *bios = (void *)object;
+       bios->data[addr] = data;
+}
+
+static void
+nvkm_bios_wr16(struct nvkm_object *object, u64 addr, u16 data)
+{
+       struct nvkm_bios *bios = (void *)object;
+       put_unaligned_le16(data, &bios->data[addr]);
+}
+
+static void
+nvkm_bios_wr32(struct nvkm_object *object, u64 addr, u32 data)
+{
+       struct nvkm_bios *bios = (void *)object;
+       put_unaligned_le32(data, &bios->data[addr]);
+}
+
+static int
+nvkm_bios_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+              struct nvkm_oclass *oclass, void *data, u32 size,
+              struct nvkm_object **pobject)
+{
+       struct nvkm_bios *bios;
+       struct bit_entry bit_i;
+       int ret;
+
+       ret = nvkm_subdev_create(parent, engine, oclass, 0,
+                                "VBIOS", "bios", &bios);
+       *pobject = nv_object(bios);
+       if (ret)
+               return ret;
+
+       ret = nvbios_shadow(bios);
+       if (ret)
+               return ret;
+
+       /* detect type of vbios we're dealing with */
+       bios->bmp_offset = nvbios_findstr(bios->data, bios->size,
+                                         "\xff\x7f""NV\0", 5);
+       if (bios->bmp_offset) {
+               nv_info(bios, "BMP version %x.%x\n",
+                       bmp_version(bios) >> 8,
+                       bmp_version(bios) & 0xff);
+       }
+
+       bios->bit_offset = nvbios_findstr(bios->data, bios->size,
+                                         "\xff\xb8""BIT", 5);
+       if (bios->bit_offset)
+               nv_info(bios, "BIT signature found\n");
+
+       /* determine the vbios version number */
+       if (!bit_entry(bios, 'i', &bit_i) && bit_i.length >= 4) {
+               bios->version.major = nv_ro08(bios, bit_i.offset + 3);
+               bios->version.chip  = nv_ro08(bios, bit_i.offset + 2);
+               bios->version.minor = nv_ro08(bios, bit_i.offset + 1);
+               bios->version.micro = nv_ro08(bios, bit_i.offset + 0);
+               bios->version.patch = nv_ro08(bios, bit_i.offset + 4);
+       } else
+       if (bmp_version(bios)) {
+               bios->version.major = nv_ro08(bios, bios->bmp_offset + 13);
+               bios->version.chip  = nv_ro08(bios, bios->bmp_offset + 12);
+               bios->version.minor = nv_ro08(bios, bios->bmp_offset + 11);
+               bios->version.micro = nv_ro08(bios, bios->bmp_offset + 10);
+       }
+
+       nv_info(bios, "version %02x.%02x.%02x.%02x.%02x\n",
+               bios->version.major, bios->version.chip,
+               bios->version.minor, bios->version.micro, bios->version.patch);
+
+       return 0;
+}
+
+static void
+nvkm_bios_dtor(struct nvkm_object *object)
+{
+       struct nvkm_bios *bios = (void *)object;
+       kfree(bios->data);
+       nvkm_subdev_destroy(&bios->base);
+}
+
+static int
+nvkm_bios_init(struct nvkm_object *object)
+{
+       struct nvkm_bios *bios = (void *)object;
+       return nvkm_subdev_init(&bios->base);
+}
+
+static int
+nvkm_bios_fini(struct nvkm_object *object, bool suspend)
+{
+       struct nvkm_bios *bios = (void *)object;
+       return nvkm_subdev_fini(&bios->base, suspend);
+}
+
+struct nvkm_oclass
+nvkm_bios_oclass = {
+       .handle = NV_SUBDEV(VBIOS, 0x00),
+       .ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = nvkm_bios_ctor,
+               .dtor = nvkm_bios_dtor,
+               .init = nvkm_bios_init,
+               .fini = nvkm_bios_fini,
+               .rd08 = nvkm_bios_rd08,
+               .rd16 = nvkm_bios_rd16,
+               .rd32 = nvkm_bios_rd32,
+               .wr08 = nvkm_bios_wr08,
+               .wr16 = nvkm_bios_wr16,
+               .wr32 = nvkm_bios_wr32,
+       },
+};
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/bios/bit.c b/drivers/gpu/drm/nouveau/nvkm/subdev/bios/bit.c
new file mode 100644 (file)
index 0000000..eab5404
--- /dev/null
@@ -0,0 +1,49 @@
+/*
+ * Copyright 2012 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 <subdev/bios.h>
+#include <subdev/bios/bit.h>
+
+int
+bit_entry(struct nvkm_bios *bios, u8 id, struct bit_entry *bit)
+{
+       if (likely(bios->bit_offset)) {
+               u8  entries = nv_ro08(bios, bios->bit_offset + 10);
+               u32 entry   = bios->bit_offset + 12;
+               while (entries--) {
+                       if (nv_ro08(bios, entry + 0) == id) {
+                               bit->id      = nv_ro08(bios, entry + 0);
+                               bit->version = nv_ro08(bios, entry + 1);
+                               bit->length  = nv_ro16(bios, entry + 2);
+                               bit->offset  = nv_ro16(bios, entry + 4);
+                               return 0;
+                       }
+
+                       entry += nv_ro08(bios, bios->bit_offset + 9);
+               }
+
+               return -ENOENT;
+       }
+
+       return -EINVAL;
+}
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/bios/boost.c b/drivers/gpu/drm/nouveau/nvkm/subdev/bios/boost.c
new file mode 100644 (file)
index 0000000..12e9585
--- /dev/null
@@ -0,0 +1,126 @@
+/*
+ * Copyright 2013 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 <subdev/bios.h>
+#include <subdev/bios/bit.h>
+#include <subdev/bios/boost.h>
+
+u16
+nvbios_boostTe(struct nvkm_bios *bios,
+              u8 *ver, u8 *hdr, u8 *cnt, u8 *len, u8 *snr, u8 *ssz)
+{
+       struct bit_entry bit_P;
+       u16 boost = 0x0000;
+
+       if (!bit_entry(bios, 'P', &bit_P)) {
+               if (bit_P.version == 2)
+                       boost = nv_ro16(bios, bit_P.offset + 0x30);
+
+               if (boost) {
+                       *ver = nv_ro08(bios, boost + 0);
+                       switch (*ver) {
+                       case 0x11:
+                               *hdr = nv_ro08(bios, boost + 1);
+                               *cnt = nv_ro08(bios, boost + 5);
+                               *len = nv_ro08(bios, boost + 2);
+                               *snr = nv_ro08(bios, boost + 4);
+                               *ssz = nv_ro08(bios, boost + 3);
+                               return boost;
+                       default:
+                               break;
+                       }
+               }
+       }
+
+       return 0x0000;
+}
+
+u16
+nvbios_boostEe(struct nvkm_bios *bios, int idx,
+              u8 *ver, u8 *hdr, u8 *cnt, u8 *len)
+{
+       u8  snr, ssz;
+       u16 data = nvbios_boostTe(bios, ver, hdr, cnt, len, &snr, &ssz);
+       if (data && idx < *cnt) {
+               data = data + *hdr + (idx * (*len + (snr * ssz)));
+               *hdr = *len;
+               *cnt = snr;
+               *len = ssz;
+               return data;
+       }
+       return 0x0000;
+}
+
+u16
+nvbios_boostEp(struct nvkm_bios *bios, int idx,
+              u8 *ver, u8 *hdr, u8 *cnt, u8 *len, struct nvbios_boostE *info)
+{
+       u16 data = nvbios_boostEe(bios, idx, ver, hdr, cnt, len);
+       memset(info, 0x00, sizeof(*info));
+       if (data) {
+               info->pstate = (nv_ro16(bios, data + 0x00) & 0x01e0) >> 5;
+               info->min    =  nv_ro16(bios, data + 0x02) * 1000;
+               info->max    =  nv_ro16(bios, data + 0x04) * 1000;
+       }
+       return data;
+}
+
+u16
+nvbios_boostEm(struct nvkm_bios *bios, u8 pstate,
+              u8 *ver, u8 *hdr, u8 *cnt, u8 *len, struct nvbios_boostE *info)
+{
+       u32 data, idx = 0;
+       while ((data = nvbios_boostEp(bios, idx++, ver, hdr, cnt, len, info))) {
+               if (info->pstate == pstate)
+                       break;
+       }
+       return data;
+}
+
+u16
+nvbios_boostSe(struct nvkm_bios *bios, int idx,
+              u16 data, u8 *ver, u8 *hdr, u8 cnt, u8 len)
+{
+       if (data && idx < cnt) {
+               data = data + *hdr + (idx * len);
+               *hdr = len;
+               return data;
+       }
+       return 0x0000;
+}
+
+u16
+nvbios_boostSp(struct nvkm_bios *bios, int idx,
+              u16 data, u8 *ver, u8 *hdr, u8 cnt, u8 len,
+              struct nvbios_boostS *info)
+{
+       data = nvbios_boostSe(bios, idx, data, ver, hdr, cnt, len);
+       memset(info, 0x00, sizeof(*info));
+       if (data) {
+               info->domain  = nv_ro08(bios, data + 0x00);
+               info->percent = nv_ro08(bios, data + 0x01);
+               info->min     = nv_ro16(bios, data + 0x02) * 1000;
+               info->max     = nv_ro16(bios, data + 0x04) * 1000;
+       }
+       return data;
+}
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/bios/conn.c b/drivers/gpu/drm/nouveau/nvkm/subdev/bios/conn.c
new file mode 100644 (file)
index 0000000..706a165
--- /dev/null
@@ -0,0 +1,97 @@
+/*
+ * Copyright 2012 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 <subdev/bios.h>
+#include <subdev/bios/dcb.h>
+#include <subdev/bios/conn.h>
+
+u32
+nvbios_connTe(struct nvkm_bios *bios, u8 *ver, u8 *hdr, u8 *cnt, u8 *len)
+{
+       u32 dcb = dcb_table(bios, ver, hdr, cnt, len);
+       if (dcb && *ver >= 0x30 && *hdr >= 0x16) {
+               u32 data = nv_ro16(bios, dcb + 0x14);
+               if (data) {
+                       *ver = nv_ro08(bios, data + 0);
+                       *hdr = nv_ro08(bios, data + 1);
+                       *cnt = nv_ro08(bios, data + 2);
+                       *len = nv_ro08(bios, data + 3);
+                       return data;
+               }
+       }
+       return 0x00000000;
+}
+
+u32
+nvbios_connTp(struct nvkm_bios *bios, u8 *ver, u8 *hdr, u8 *cnt, u8 *len,
+             struct nvbios_connT *info)
+{
+       u32 data = nvbios_connTe(bios, ver, hdr, cnt, len);
+       memset(info, 0x00, sizeof(*info));
+       switch (!!data * *ver) {
+       case 0x30:
+       case 0x40:
+               return data;
+       default:
+               break;
+       }
+       return 0x00000000;
+}
+
+u32
+nvbios_connEe(struct nvkm_bios *bios, u8 idx, u8 *ver, u8 *len)
+{
+       u8  hdr, cnt;
+       u32 data = nvbios_connTe(bios, ver, &hdr, &cnt, len);
+       if (data && idx < cnt)
+               return data + hdr + (idx * *len);
+       return 0x00000000;
+}
+
+u32
+nvbios_connEp(struct nvkm_bios *bios, u8 idx, u8 *ver, u8 *len,
+             struct nvbios_connE *info)
+{
+       u32 data = nvbios_connEe(bios, idx, ver, len);
+       memset(info, 0x00, sizeof(*info));
+       switch (!!data * *ver) {
+       case 0x30:
+       case 0x40:
+               info->type     =  nv_ro08(bios, data + 0x00);
+               info->location =  nv_ro08(bios, data + 0x01) & 0x0f;
+               info->hpd      = (nv_ro08(bios, data + 0x01) & 0x30) >> 4;
+               info->dp       = (nv_ro08(bios, data + 0x01) & 0xc0) >> 6;
+               if (*len < 4)
+                       return data;
+               info->hpd     |= (nv_ro08(bios, data + 0x02) & 0x03) << 2;
+               info->dp      |=  nv_ro08(bios, data + 0x02) & 0x0c;
+               info->di       = (nv_ro08(bios, data + 0x02) & 0xf0) >> 4;
+               info->hpd     |= (nv_ro08(bios, data + 0x03) & 0x07) << 4;
+               info->sr       = (nv_ro08(bios, data + 0x03) & 0x08) >> 3;
+               info->lcdid    = (nv_ro08(bios, data + 0x03) & 0x70) >> 4;
+               return data;
+       default:
+               break;
+       }
+       return 0x00000000;
+}
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/bios/cstep.c b/drivers/gpu/drm/nouveau/nvkm/subdev/bios/cstep.c
new file mode 100644 (file)
index 0000000..16f7ad8
--- /dev/null
@@ -0,0 +1,122 @@
+/*
+ * Copyright 2013 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 <subdev/bios.h>
+#include <subdev/bios/bit.h>
+#include <subdev/bios/cstep.h>
+
+u16
+nvbios_cstepTe(struct nvkm_bios *bios,
+              u8 *ver, u8 *hdr, u8 *cnt, u8 *len, u8 *xnr, u8 *xsz)
+{
+       struct bit_entry bit_P;
+       u16 cstep = 0x0000;
+
+       if (!bit_entry(bios, 'P', &bit_P)) {
+               if (bit_P.version == 2)
+                       cstep = nv_ro16(bios, bit_P.offset + 0x34);
+
+               if (cstep) {
+                       *ver = nv_ro08(bios, cstep + 0);
+                       switch (*ver) {
+                       case 0x10:
+                               *hdr = nv_ro08(bios, cstep + 1);
+                               *cnt = nv_ro08(bios, cstep + 3);
+                               *len = nv_ro08(bios, cstep + 2);
+                               *xnr = nv_ro08(bios, cstep + 5);
+                               *xsz = nv_ro08(bios, cstep + 4);
+                               return cstep;
+                       default:
+                               break;
+                       }
+               }
+       }
+
+       return 0x0000;
+}
+
+u16
+nvbios_cstepEe(struct nvkm_bios *bios, int idx, u8 *ver, u8 *hdr)
+{
+       u8  cnt, len, xnr, xsz;
+       u16 data = nvbios_cstepTe(bios, ver, hdr, &cnt, &len, &xnr, &xsz);
+       if (data && idx < cnt) {
+               data = data + *hdr + (idx * len);
+               *hdr = len;
+               return data;
+       }
+       return 0x0000;
+}
+
+u16
+nvbios_cstepEp(struct nvkm_bios *bios, int idx, u8 *ver, u8 *hdr,
+              struct nvbios_cstepE *info)
+{
+       u16 data = nvbios_cstepEe(bios, idx, ver, hdr);
+       memset(info, 0x00, sizeof(*info));
+       if (data) {
+               info->pstate = (nv_ro16(bios, data + 0x00) & 0x01e0) >> 5;
+               info->index   = nv_ro08(bios, data + 0x03);
+       }
+       return data;
+}
+
+u16
+nvbios_cstepEm(struct nvkm_bios *bios, u8 pstate, u8 *ver, u8 *hdr,
+              struct nvbios_cstepE *info)
+{
+       u32 data, idx = 0;
+       while ((data = nvbios_cstepEp(bios, idx++, ver, hdr, info))) {
+               if (info->pstate == pstate)
+                       break;
+       }
+       return data;
+}
+
+u16
+nvbios_cstepXe(struct nvkm_bios *bios, int idx, u8 *ver, u8 *hdr)
+{
+       u8  cnt, len, xnr, xsz;
+       u16 data = nvbios_cstepTe(bios, ver, hdr, &cnt, &len, &xnr, &xsz);
+       if (data && idx < xnr) {
+               data = data + *hdr + (cnt * len) + (idx * xsz);
+               *hdr = xsz;
+               return data;
+       }
+       return 0x0000;
+}
+
+u16
+nvbios_cstepXp(struct nvkm_bios *bios, int idx, u8 *ver, u8 *hdr,
+              struct nvbios_cstepX *info)
+{
+       u16 data = nvbios_cstepXe(bios, idx, ver, hdr);
+       memset(info, 0x00, sizeof(*info));
+       if (data) {
+               info->freq    = nv_ro16(bios, data + 0x00) * 1000;
+               info->unkn[0] = nv_ro08(bios, data + 0x02);
+               info->unkn[1] = nv_ro08(bios, data + 0x03);
+               info->voltage = nv_ro08(bios, data + 0x04);
+       }
+       return data;
+}
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/bios/dcb.c b/drivers/gpu/drm/nouveau/nvkm/subdev/bios/dcb.c
new file mode 100644 (file)
index 0000000..8d78140
--- /dev/null
@@ -0,0 +1,234 @@
+/*
+ * Copyright 2012 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 <subdev/bios.h>
+#include <subdev/bios/dcb.h>
+
+#include <core/device.h>
+
+u16
+dcb_table(struct nvkm_bios *bios, u8 *ver, u8 *hdr, u8 *cnt, u8 *len)
+{
+       struct nvkm_device *device = nv_device(bios);
+       u16 dcb = 0x0000;
+
+       if (device->card_type > NV_04)
+               dcb = nv_ro16(bios, 0x36);
+       if (!dcb) {
+               nv_warn(bios, "DCB table not found\n");
+               return dcb;
+       }
+
+       *ver = nv_ro08(bios, dcb);
+
+       if (*ver >= 0x42) {
+               nv_warn(bios, "DCB version 0x%02x unknown\n", *ver);
+               return 0x0000;
+       } else
+       if (*ver >= 0x30) {
+               if (nv_ro32(bios, dcb + 6) == 0x4edcbdcb) {
+                       *hdr = nv_ro08(bios, dcb + 1);
+                       *cnt = nv_ro08(bios, dcb + 2);
+                       *len = nv_ro08(bios, dcb + 3);
+                       return dcb;
+               }
+       } else
+       if (*ver >= 0x20) {
+               if (nv_ro32(bios, dcb + 4) == 0x4edcbdcb) {
+                       u16 i2c = nv_ro16(bios, dcb + 2);
+                       *hdr = 8;
+                       *cnt = (i2c - dcb) / 8;
+                       *len = 8;
+                       return dcb;
+               }
+       } else
+       if (*ver >= 0x15) {
+               if (!nv_memcmp(bios, dcb - 7, "DEV_REC", 7)) {
+                       u16 i2c = nv_ro16(bios, dcb + 2);
+                       *hdr = 4;
+                       *cnt = (i2c - dcb) / 10;
+                       *len = 10;
+                       return dcb;
+               }
+       } 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_warn(bios, "DCB contains no useful data\n");
+               return 0x0000;
+       }
+
+       nv_warn(bios, "DCB header validation failed\n");
+       return 0x0000;
+}
+
+u16
+dcb_outp(struct nvkm_bios *bios, u8 idx, u8 *ver, u8 *len)
+{
+       u8  hdr, cnt;
+       u16 dcb = dcb_table(bios, ver, &hdr, &cnt, len);
+       if (dcb && idx < cnt)
+               return dcb + hdr + (idx * *len);
+       return 0x0000;
+}
+
+static inline u16
+dcb_outp_hasht(struct dcb_output *outp)
+{
+       return (outp->extdev << 8) | (outp->location << 4) | outp->type;
+}
+
+static inline u16
+dcb_outp_hashm(struct dcb_output *outp)
+{
+       return (outp->heads << 8) | (outp->link << 6) | outp->or;
+}
+
+u16
+dcb_outp_parse(struct nvkm_bios *bios, u8 idx, u8 *ver, u8 *len,
+              struct dcb_output *outp)
+{
+       u16 dcb = dcb_outp(bios, idx, ver, len);
+       memset(outp, 0x00, sizeof(*outp));
+       if (dcb) {
+               if (*ver >= 0x20) {
+                       u32 conn = nv_ro32(bios, dcb + 0x00);
+                       outp->or        = (conn & 0x0f000000) >> 24;
+                       outp->location  = (conn & 0x00300000) >> 20;
+                       outp->bus       = (conn & 0x000f0000) >> 16;
+                       outp->connector = (conn & 0x0000f000) >> 12;
+                       outp->heads     = (conn & 0x00000f00) >> 8;
+                       outp->i2c_index = (conn & 0x000000f0) >> 4;
+                       outp->type      = (conn & 0x0000000f);
+                       outp->link      = 0;
+               } else {
+                       dcb = 0x0000;
+               }
+
+               if (*ver >= 0x40) {
+                       u32 conf = nv_ro32(bios, dcb + 0x04);
+                       switch (outp->type) {
+                       case DCB_OUTPUT_DP:
+                               switch (conf & 0x00e00000) {
+                               case 0x00000000:
+                                       outp->dpconf.link_bw = 0x06;
+                                       break;
+                               case 0x00200000:
+                                       outp->dpconf.link_bw = 0x0a;
+                                       break;
+                               case 0x00400000:
+                               default:
+                                       outp->dpconf.link_bw = 0x14;
+                                       break;
+                               }
+
+                               outp->dpconf.link_nr = (conf & 0x0f000000) >> 24;
+                               if (*ver < 0x41) {
+                                       switch (outp->dpconf.link_nr) {
+                                       case 0x0f:
+                                               outp->dpconf.link_nr = 4;
+                                               break;
+                                       case 0x03:
+                                               outp->dpconf.link_nr = 2;
+                                               break;
+                                       case 0x01:
+                                       default:
+                                               outp->dpconf.link_nr = 1;
+                                               break;
+                                       }
+                               }
+
+                               /* fall-through... */
+                       case DCB_OUTPUT_TMDS:
+                       case DCB_OUTPUT_LVDS:
+                               outp->link = (conf & 0x00000030) >> 4;
+                               outp->sorconf.link = outp->link; /*XXX*/
+                               outp->extdev = 0x00;
+                               if (outp->location != 0)
+                                       outp->extdev = (conf & 0x0000ff00) >> 8;
+                               break;
+                       default:
+                               break;
+                       }
+               }
+
+               outp->hasht = dcb_outp_hasht(outp);
+               outp->hashm = dcb_outp_hashm(outp);
+       }
+       return dcb;
+}
+
+u16
+dcb_outp_match(struct nvkm_bios *bios, u16 type, u16 mask,
+              u8 *ver, u8 *len, struct dcb_output *outp)
+{
+       u16 dcb, idx = 0;
+       while ((dcb = dcb_outp_parse(bios, idx++, ver, len, outp))) {
+               if ((dcb_outp_hasht(outp) & 0x00ff) == (type & 0x00ff)) {
+                       if ((dcb_outp_hashm(outp) & mask) == mask)
+                               break;
+               }
+       }
+       return dcb;
+}
+
+int
+dcb_outp_foreach(struct nvkm_bios *bios, void *data,
+                int (*exec)(struct nvkm_bios *, void *, int, u16))
+{
+       int ret, idx = -1;
+       u8  ver, len;
+       u16 outp;
+
+       while ((outp = dcb_outp(bios, ++idx, &ver, &len))) {
+               if (nv_ro32(bios, outp) == 0x00000000)
+                       break; /* seen on an NV11 with DCB v1.5 */
+               if (nv_ro32(bios, outp) == 0xffffffff)
+                       break; /* seen on an NV17 with DCB v2.0 */
+
+               if (nv_ro08(bios, outp) == DCB_OUTPUT_UNUSED)
+                       continue;
+               if (nv_ro08(bios, outp) == DCB_OUTPUT_EOL)
+                       break;
+
+               ret = exec(bios, data, idx, outp);
+               if (ret)
+                       return ret;
+       }
+
+       return 0;
+}
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/bios/disp.c b/drivers/gpu/drm/nouveau/nvkm/subdev/bios/disp.c
new file mode 100644 (file)
index 0000000..262c410
--- /dev/null
@@ -0,0 +1,172 @@
+/*
+ * Copyright 2012 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 <subdev/bios.h>
+#include <subdev/bios/bit.h>
+#include <subdev/bios/disp.h>
+
+u16
+nvbios_disp_table(struct nvkm_bios *bios,
+                 u8 *ver, u8 *hdr, u8 *cnt, u8 *len, u8 *sub)
+{
+       struct bit_entry U;
+
+       if (!bit_entry(bios, 'U', &U)) {
+               if (U.version == 1) {
+                       u16 data = nv_ro16(bios, U.offset);
+                       if (data) {
+                               *ver = nv_ro08(bios, data + 0x00);
+                               switch (*ver) {
+                               case 0x20:
+                               case 0x21:
+                               case 0x22:
+                                       *hdr = nv_ro08(bios, data + 0x01);
+                                       *len = nv_ro08(bios, data + 0x02);
+                                       *cnt = nv_ro08(bios, data + 0x03);
+                                       *sub = nv_ro08(bios, data + 0x04);
+                                       return data;
+                               default:
+                                       break;
+                               }
+                       }
+               }
+       }
+
+       return 0x0000;
+}
+
+u16
+nvbios_disp_entry(struct nvkm_bios *bios, u8 idx, u8 *ver, u8 *len, u8 *sub)
+{
+       u8  hdr, cnt;
+       u16 data = nvbios_disp_table(bios, ver, &hdr, &cnt, len, sub);
+       if (data && idx < cnt)
+               return data + hdr + (idx * *len);
+       *ver = 0x00;
+       return 0x0000;
+}
+
+u16
+nvbios_disp_parse(struct nvkm_bios *bios, u8 idx, u8 *ver, u8 *len, u8 *sub,
+                 struct nvbios_disp *info)
+{
+       u16 data = nvbios_disp_entry(bios, idx, ver, len, sub);
+       if (data && *len >= 2) {
+               info->data = nv_ro16(bios, data + 0);
+               return data;
+       }
+       return 0x0000;
+}
+
+u16
+nvbios_outp_entry(struct nvkm_bios *bios, u8 idx,
+                 u8 *ver, u8 *hdr, u8 *cnt, u8 *len)
+{
+       struct nvbios_disp info;
+       u16 data = nvbios_disp_parse(bios, idx, ver, len, hdr, &info);
+       if (data) {
+               *cnt = nv_ro08(bios, info.data + 0x05);
+               *len = 0x06;
+               data = info.data;
+       }
+       return data;
+}
+
+u16
+nvbios_outp_parse(struct nvkm_bios *bios, u8 idx,
+                 u8 *ver, u8 *hdr, u8 *cnt, u8 *len, struct nvbios_outp *info)
+{
+       u16 data = nvbios_outp_entry(bios, idx, ver, hdr, cnt, len);
+       if (data && *hdr >= 0x0a) {
+               info->type      = nv_ro16(bios, data + 0x00);
+               info->mask      = nv_ro32(bios, data + 0x02);
+               if (*ver <= 0x20) /* match any link */
+                       info->mask |= 0x00c0;
+               info->script[0] = nv_ro16(bios, data + 0x06);
+               info->script[1] = nv_ro16(bios, data + 0x08);
+               info->script[2] = 0x0000;
+               if (*hdr >= 0x0c)
+                       info->script[2] = nv_ro16(bios, data + 0x0a);
+               return data;
+       }
+       return 0x0000;
+}
+
+u16
+nvbios_outp_match(struct nvkm_bios *bios, u16 type, u16 mask,
+                 u8 *ver, u8 *hdr, u8 *cnt, u8 *len, struct nvbios_outp *info)
+{
+       u16 data, idx = 0;
+       while ((data = nvbios_outp_parse(bios, idx++, ver, hdr, cnt, len, info)) || *ver) {
+               if (data && info->type == type) {
+                       if ((info->mask & mask) == mask)
+                               break;
+               }
+       }
+       return data;
+}
+
+u16
+nvbios_ocfg_entry(struct nvkm_bios *bios, u16 outp, u8 idx,
+                 u8 *ver, u8 *hdr, u8 *cnt, u8 *len)
+{
+       if (idx < *cnt)
+               return outp + *hdr + (idx * *len);
+       return 0x0000;
+}
+
+u16
+nvbios_ocfg_parse(struct nvkm_bios *bios, u16 outp, u8 idx,
+                 u8 *ver, u8 *hdr, u8 *cnt, u8 *len, struct nvbios_ocfg *info)
+{
+       u16 data = nvbios_ocfg_entry(bios, outp, idx, ver, hdr, cnt, len);
+       if (data) {
+               info->match     = nv_ro16(bios, data + 0x00);
+               info->clkcmp[0] = nv_ro16(bios, data + 0x02);
+               info->clkcmp[1] = nv_ro16(bios, data + 0x04);
+       }
+       return data;
+}
+
+u16
+nvbios_ocfg_match(struct nvkm_bios *bios, u16 outp, u16 type,
+                 u8 *ver, u8 *hdr, u8 *cnt, u8 *len, struct nvbios_ocfg *info)
+{
+       u16 data, idx = 0;
+       while ((data = nvbios_ocfg_parse(bios, outp, idx++, ver, hdr, cnt, len, info))) {
+               if (info->match == type)
+                       break;
+       }
+       return data;
+}
+
+u16
+nvbios_oclk_match(struct nvkm_bios *bios, u16 cmp, u32 khz)
+{
+       while (cmp) {
+               if (khz / 10 >= nv_ro16(bios, cmp + 0x00))
+                       return  nv_ro16(bios, cmp + 0x02);
+               cmp += 0x04;
+       }
+       return 0x0000;
+}
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/bios/dp.c b/drivers/gpu/drm/nouveau/nvkm/subdev/bios/dp.c
new file mode 100644 (file)
index 0000000..95970fa
--- /dev/null
@@ -0,0 +1,215 @@
+/*
+ * Copyright 2012 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 <subdev/bios.h>
+#include <subdev/bios/bit.h>
+#include <subdev/bios/dp.h>
+
+static u16
+nvbios_dp_table(struct nvkm_bios *bios, u8 *ver, u8 *hdr, u8 *cnt, u8 *len)
+{
+       struct bit_entry d;
+
+       if (!bit_entry(bios, 'd', &d)) {
+               if (d.version == 1 && d.length >= 2) {
+                       u16 data = nv_ro16(bios, d.offset);
+                       if (data) {
+                               *ver = nv_ro08(bios, data + 0x00);
+                               switch (*ver) {
+                               case 0x21:
+                               case 0x30:
+                               case 0x40:
+                               case 0x41:
+                                       *hdr = nv_ro08(bios, data + 0x01);
+                                       *len = nv_ro08(bios, data + 0x02);
+                                       *cnt = nv_ro08(bios, data + 0x03);
+                                       return data;
+                               default:
+                                       break;
+                               }
+                       }
+               }
+       }
+
+       return 0x0000;
+}
+
+static u16
+nvbios_dpout_entry(struct nvkm_bios *bios, u8 idx,
+                  u8 *ver, u8 *hdr, u8 *cnt, u8 *len)
+{
+       u16 data = nvbios_dp_table(bios, ver, hdr, cnt, len);
+       if (data && idx < *cnt) {
+               u16 outp = nv_ro16(bios, data + *hdr + idx * *len);
+               switch (*ver * !!outp) {
+               case 0x21:
+               case 0x30:
+                       *hdr = nv_ro08(bios, data + 0x04);
+                       *len = nv_ro08(bios, data + 0x05);
+                       *cnt = nv_ro08(bios, outp + 0x04);
+                       break;
+               case 0x40:
+               case 0x41:
+                       *hdr = nv_ro08(bios, data + 0x04);
+                       *cnt = 0;
+                       *len = 0;
+                       break;
+               default:
+                       break;
+               }
+               return outp;
+       }
+       *ver = 0x00;
+       return 0x0000;
+}
+
+u16
+nvbios_dpout_parse(struct nvkm_bios *bios, u8 idx,
+                  u8 *ver, u8 *hdr, u8 *cnt, u8 *len,
+                  struct nvbios_dpout *info)
+{
+       u16 data = nvbios_dpout_entry(bios, idx, ver, hdr, cnt, len);
+       memset(info, 0x00, sizeof(*info));
+       if (data && *ver) {
+               info->type = nv_ro16(bios, data + 0x00);
+               info->mask = nv_ro16(bios, data + 0x02);
+               switch (*ver) {
+               case 0x21:
+               case 0x30:
+                       info->flags     = nv_ro08(bios, data + 0x05);
+                       info->script[0] = nv_ro16(bios, data + 0x06);
+                       info->script[1] = nv_ro16(bios, data + 0x08);
+                       info->lnkcmp    = nv_ro16(bios, data + 0x0a);
+                       if (*len >= 0x0f) {
+                               info->script[2] = nv_ro16(bios, data + 0x0c);
+                               info->script[3] = nv_ro16(bios, data + 0x0e);
+                       }
+                       if (*len >= 0x11)
+                               info->script[4] = nv_ro16(bios, data + 0x10);
+                       break;
+               case 0x40:
+               case 0x41:
+                       info->flags     = nv_ro08(bios, data + 0x04);
+                       info->script[0] = nv_ro16(bios, data + 0x05);
+                       info->script[1] = nv_ro16(bios, data + 0x07);
+                       info->lnkcmp    = nv_ro16(bios, data + 0x09);
+                       info->script[2] = nv_ro16(bios, data + 0x0b);
+                       info->script[3] = nv_ro16(bios, data + 0x0d);
+                       info->script[4] = nv_ro16(bios, data + 0x0f);
+                       break;
+               default:
+                       data = 0x0000;
+                       break;
+               }
+       }
+       return data;
+}
+
+u16
+nvbios_dpout_match(struct nvkm_bios *bios, u16 type, u16 mask,
+                  u8 *ver, u8 *hdr, u8 *cnt, u8 *len,
+                  struct nvbios_dpout *info)
+{
+       u16 data, idx = 0;
+       while ((data = nvbios_dpout_parse(bios, idx++, ver, hdr, cnt, len, info)) || *ver) {
+               if (data && info->type == type) {
+                       if ((info->mask & mask) == mask)
+                               break;
+               }
+       }
+       return data;
+}
+
+static u16
+nvbios_dpcfg_entry(struct nvkm_bios *bios, u16 outp, u8 idx,
+                  u8 *ver, u8 *hdr, u8 *cnt, u8 *len)
+{
+       if (*ver >= 0x40) {
+               outp = nvbios_dp_table(bios, ver, hdr, cnt, len);
+               *hdr = *hdr + (*len * * cnt);
+               *len = nv_ro08(bios, outp + 0x06);
+               *cnt = nv_ro08(bios, outp + 0x07);
+       }
+
+       if (idx < *cnt)
+               return outp + *hdr + (idx * *len);
+
+       return 0x0000;
+}
+
+u16
+nvbios_dpcfg_parse(struct nvkm_bios *bios, u16 outp, u8 idx,
+                  u8 *ver, u8 *hdr, u8 *cnt, u8 *len,
+                  struct nvbios_dpcfg *info)
+{
+       u16 data = nvbios_dpcfg_entry(bios, outp, idx, ver, hdr, cnt, len);
+       memset(info, 0x00, sizeof(*info));
+       if (data) {
+               switch (*ver) {
+               case 0x21:
+                       info->dc    = nv_ro08(bios, data + 0x02);
+                       info->pe    = nv_ro08(bios, data + 0x03);
+                       info->tx_pu = nv_ro08(bios, data + 0x04);
+                       break;
+               case 0x30:
+               case 0x40:
+               case 0x41:
+                       info->pc    = nv_ro08(bios, data + 0x00);
+                       info->dc    = nv_ro08(bios, data + 0x01);
+                       info->pe    = nv_ro08(bios, data + 0x02);
+                       info->tx_pu = nv_ro08(bios, data + 0x03) & 0x0f;
+                       break;
+               default:
+                       data = 0x0000;
+                       break;
+               }
+       }
+       return data;
+}
+
+u16
+nvbios_dpcfg_match(struct nvkm_bios *bios, u16 outp, u8 pc, u8 vs, u8 pe,
+                  u8 *ver, u8 *hdr, u8 *cnt, u8 *len,
+                  struct nvbios_dpcfg *info)
+{
+       u8 idx = 0xff;
+       u16 data;
+
+       if (*ver >= 0x30) {
+               /*XXX: there's a second set of these on at least 4.1, that
+                *     i've witnessed nvidia using instead of the first
+                *     on gm204.  figure out what/why
+                */
+               const u8 vsoff[] = { 0, 4, 7, 9 };
+               idx = (pc * 10) + vsoff[vs] + pe;
+       } else {
+               while ((data = nvbios_dpcfg_entry(bios, outp, ++idx,
+                                                 ver, hdr, cnt, len))) {
+                       if (nv_ro08(bios, data + 0x00) == vs &&
+                           nv_ro08(bios, data + 0x01) == pe)
+                               break;
+               }
+       }
+
+       return nvbios_dpcfg_parse(bios, outp, idx, ver, hdr, cnt, len, info);
+}
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/bios/extdev.c b/drivers/gpu/drm/nouveau/nvkm/subdev/bios/extdev.c
new file mode 100644 (file)
index 0000000..a8503a1
--- /dev/null
@@ -0,0 +1,97 @@
+/*
+ * Copyright 2012 Nouveau Community
+ *
+ * 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 <subdev/bios.h>
+#include <subdev/bios/dcb.h>
+#include <subdev/bios/extdev.h>
+
+static u16
+extdev_table(struct nvkm_bios *bios, u8 *ver, u8 *hdr, u8 *len, u8 *cnt)
+{
+       u8  dcb_ver, dcb_hdr, dcb_cnt, dcb_len;
+       u16 dcb, extdev = 0;
+
+       dcb = dcb_table(bios, &dcb_ver, &dcb_hdr, &dcb_cnt, &dcb_len);
+       if (!dcb || (dcb_ver != 0x30 && dcb_ver != 0x40))
+               return 0x0000;
+
+       extdev = nv_ro16(bios, dcb + 18);
+       if (!extdev)
+               return 0x0000;
+
+       *ver = nv_ro08(bios, extdev + 0);
+       *hdr = nv_ro08(bios, extdev + 1);
+       *cnt = nv_ro08(bios, extdev + 2);
+       *len = nv_ro08(bios, extdev + 3);
+       return extdev + *hdr;
+}
+
+static u16
+nvbios_extdev_entry(struct nvkm_bios *bios, int idx, u8 *ver, u8 *len)
+{
+       u8 hdr, cnt;
+       u16 extdev = extdev_table(bios, ver, &hdr, len, &cnt);
+       if (extdev && idx < cnt)
+               return extdev + idx * *len;
+       return 0x0000;
+}
+
+static void
+extdev_parse_entry(struct nvkm_bios *bios, u16 offset,
+                  struct nvbios_extdev_func *entry)
+{
+       entry->type = nv_ro08(bios, offset + 0);
+       entry->addr = nv_ro08(bios, offset + 1);
+       entry->bus = (nv_ro08(bios, offset + 2) >> 4) & 1;
+}
+
+int
+nvbios_extdev_parse(struct nvkm_bios *bios, int idx,
+                   struct nvbios_extdev_func *func)
+{
+       u8 ver, len;
+       u16 entry;
+
+       if (!(entry = nvbios_extdev_entry(bios, idx, &ver, &len)))
+               return -EINVAL;
+
+       extdev_parse_entry(bios, entry, func);
+       return 0;
+}
+
+int
+nvbios_extdev_find(struct nvkm_bios *bios, enum nvbios_extdev_type type,
+                  struct nvbios_extdev_func *func)
+{
+       u8 ver, len, i;
+       u16 entry;
+
+       i = 0;
+       while ((entry = nvbios_extdev_entry(bios, i++, &ver, &len))) {
+               extdev_parse_entry(bios, entry, func);
+               if (func->type == type)
+                       return 0;
+       }
+
+       return -EINVAL;
+}
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/bios/fan.c b/drivers/gpu/drm/nouveau/nvkm/subdev/bios/fan.c
new file mode 100644 (file)
index 0000000..8dba70d
--- /dev/null
@@ -0,0 +1,93 @@
+/*
+ * Copyright 2014 Martin Peres
+ *
+ * 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 <subdev/bios.h>
+#include <subdev/bios/bit.h>
+#include <subdev/bios/fan.h>
+
+u16
+nvbios_fan_table(struct nvkm_bios *bios, u8 *ver, u8 *hdr, u8 *cnt, u8 *len)
+{
+       struct bit_entry bit_P;
+       u16 fan = 0x0000;
+
+       if (!bit_entry(bios, 'P', &bit_P)) {
+               if (bit_P.version == 2 && bit_P.length >= 0x5a)
+                       fan = nv_ro16(bios, bit_P.offset + 0x58);
+
+               if (fan) {
+                       *ver = nv_ro08(bios, fan + 0);
+                       switch (*ver) {
+                       case 0x10:
+                               *hdr = nv_ro08(bios, fan + 1);
+                               *len = nv_ro08(bios, fan + 2);
+                               *cnt = nv_ro08(bios, fan + 3);
+                               return fan;
+                       default:
+                               break;
+                       }
+               }
+       }
+
+       return 0x0000;
+}
+
+u16
+nvbios_fan_entry(struct nvkm_bios *bios, int idx, u8 *ver, u8 *hdr,
+                u8 *cnt, u8 *len)
+{
+       u16 data = nvbios_fan_table(bios, ver, hdr, cnt, len);
+       if (data && idx < *cnt)
+               return data + *hdr + (idx * (*len));
+       return 0x0000;
+}
+
+u16
+nvbios_fan_parse(struct nvkm_bios *bios, struct nvbios_therm_fan *fan)
+{
+       u8 ver, hdr, cnt, len;
+
+       u16 data = nvbios_fan_entry(bios, 0, &ver, &hdr, &cnt, &len);
+       if (data) {
+               u8 type = nv_ro08(bios, data + 0x00);
+               switch (type) {
+               case 0:
+                       fan->type = NVBIOS_THERM_FAN_TOGGLE;
+                       break;
+               case 1:
+               case 2:
+                       /* TODO: Understand the difference between the two! */
+                       fan->type = NVBIOS_THERM_FAN_PWM;
+                       break;
+               default:
+                       fan->type = NVBIOS_THERM_FAN_UNK;
+               }
+
+               fan->min_duty = nv_ro08(bios, data + 0x02);
+               fan->max_duty = nv_ro08(bios, data + 0x03);
+
+               fan->pwm_freq = nv_ro32(bios, data + 0x0b) & 0xffffff;
+       }
+
+       return data;
+}
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/bios/gpio.c b/drivers/gpu/drm/nouveau/nvkm/subdev/bios/gpio.c
new file mode 100644 (file)
index 0000000..8ce154d
--- /dev/null
@@ -0,0 +1,150 @@
+/*
+ * Copyright 2012 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 <subdev/bios.h>
+#include <subdev/bios/dcb.h>
+#include <subdev/bios/gpio.h>
+#include <subdev/bios/xpio.h>
+
+u16
+dcb_gpio_table(struct nvkm_bios *bios, u8 *ver, u8 *hdr, u8 *cnt, u8 *len)
+{
+       u16 data = 0x0000;
+       u16 dcb = dcb_table(bios, ver, hdr, cnt, len);
+       if (dcb) {
+               if (*ver >= 0x30 && *hdr >= 0x0c)
+                       data = nv_ro16(bios, dcb + 0x0a);
+               else
+               if (*ver >= 0x22 && nv_ro08(bios, dcb - 1) >= 0x13)
+                       data = nv_ro16(bios, dcb - 0x0f);
+
+               if (data) {
+                       *ver = nv_ro08(bios, data + 0x00);
+                       if (*ver < 0x30) {
+                               *hdr = 3;
+                               *cnt = nv_ro08(bios, data + 0x02);
+                               *len = nv_ro08(bios, data + 0x01);
+                       } else
+                       if (*ver <= 0x41) {
+                               *hdr = nv_ro08(bios, data + 0x01);
+                               *cnt = nv_ro08(bios, data + 0x02);
+                               *len = nv_ro08(bios, data + 0x03);
+                       } else {
+                               data = 0x0000;
+                       }
+               }
+       }
+       return data;
+}
+
+u16
+dcb_gpio_entry(struct nvkm_bios *bios, int idx, int ent, u8 *ver, u8 *len)
+{
+       u8  hdr, cnt, xver; /* use gpio version for xpio entry parsing */
+       u16 gpio;
+
+       if (!idx--)
+               gpio = dcb_gpio_table(bios, ver, &hdr, &cnt, len);
+       else
+               gpio = dcb_xpio_table(bios, idx, &xver, &hdr, &cnt, len);
+
+       if (gpio && ent < cnt)
+               return gpio + hdr + (ent * *len);
+
+       return 0x0000;
+}
+
+u16
+dcb_gpio_parse(struct nvkm_bios *bios, int idx, int ent, u8 *ver, u8 *len,
+              struct dcb_gpio_func *gpio)
+{
+       u16 data = dcb_gpio_entry(bios, idx, ent, ver, len);
+       if (data) {
+               if (*ver < 0x40) {
+                       u16 info = nv_ro16(bios, data);
+                       *gpio = (struct dcb_gpio_func) {
+                               .line = (info & 0x001f) >> 0,
+                               .func = (info & 0x07e0) >> 5,
+                               .log[0] = (info & 0x1800) >> 11,
+                               .log[1] = (info & 0x6000) >> 13,
+                               .param = !!(info & 0x8000),
+                       };
+               } else
+               if (*ver < 0x41) {
+                       u32 info = nv_ro32(bios, data);
+                       *gpio = (struct dcb_gpio_func) {
+                               .line = (info & 0x0000001f) >> 0,
+                               .func = (info & 0x0000ff00) >> 8,
+                               .log[0] = (info & 0x18000000) >> 27,
+                               .log[1] = (info & 0x60000000) >> 29,
+                               .param = !!(info & 0x80000000),
+                       };
+               } else {
+                       u32 info = nv_ro32(bios, data + 0);
+                       u8 info1 = nv_ro32(bios, data + 4);
+                       *gpio = (struct dcb_gpio_func) {
+                               .line = (info & 0x0000003f) >> 0,
+                               .func = (info & 0x0000ff00) >> 8,
+                               .log[0] = (info1 & 0x30) >> 4,
+                               .log[1] = (info1 & 0xc0) >> 6,
+                               .param = !!(info & 0x80000000),
+                       };
+               }
+       }
+
+       return data;
+}
+
+u16
+dcb_gpio_match(struct nvkm_bios *bios, int idx, u8 func, u8 line,
+              u8 *ver, u8 *len, struct dcb_gpio_func *gpio)
+{
+       u8  hdr, cnt, i = 0;
+       u16 data;
+
+       while ((data = dcb_gpio_parse(bios, idx, i++, ver, len, gpio))) {
+               if ((line == 0xff || line == gpio->line) &&
+                   (func == 0xff || func == gpio->func))
+                       return data;
+       }
+
+       /* DCB 2.2, fixed TVDAC GPIO data */
+       if ((data = dcb_table(bios, ver, &hdr, &cnt, len))) {
+               if (*ver >= 0x22 && *ver < 0x30 && func == DCB_GPIO_TVDAC0) {
+                       u8 conf = nv_ro08(bios, data - 5);
+                       u8 addr = nv_ro08(bios, data - 4);
+                       if (conf & 0x01) {
+                               *gpio = (struct dcb_gpio_func) {
+                                       .func = DCB_GPIO_TVDAC0,
+                                       .line = addr >> 4,
+                                       .log[0] = !!(conf & 0x02),
+                                       .log[1] =  !(conf & 0x02),
+                               };
+                               *ver = 0x00;
+                               return data;
+                       }
+               }
+       }
+
+       return 0x0000;
+}
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/bios/i2c.c b/drivers/gpu/drm/nouveau/nvkm/subdev/bios/i2c.c
new file mode 100644 (file)
index 0000000..d1a89b2
--- /dev/null
@@ -0,0 +1,159 @@
+/*
+ * Copyright 2012 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 <subdev/bios.h>
+#include <subdev/bios/dcb.h>
+#include <subdev/bios/i2c.h>
+
+u16
+dcb_i2c_table(struct nvkm_bios *bios, u8 *ver, u8 *hdr, u8 *cnt, u8 *len)
+{
+       u16 i2c = 0x0000;
+       u16 dcb = dcb_table(bios, ver, hdr, cnt, len);
+       if (dcb) {
+               if (*ver >= 0x15)
+                       i2c = nv_ro16(bios, dcb + 2);
+               if (*ver >= 0x30)
+                       i2c = nv_ro16(bios, dcb + 4);
+       }
+
+       if (i2c && *ver >= 0x42) {
+               nv_warn(bios, "ccb %02x not supported\n", *ver);
+               return 0x0000;
+       }
+
+       if (i2c && *ver >= 0x30) {
+               *ver = nv_ro08(bios, i2c + 0);
+               *hdr = nv_ro08(bios, i2c + 1);
+               *cnt = nv_ro08(bios, i2c + 2);
+               *len = nv_ro08(bios, i2c + 3);
+       } else {
+               *ver = *ver; /* use DCB version */
+               *hdr = 0;
+               *cnt = 16;
+               *len = 4;
+       }
+
+       return i2c;
+}
+
+u16
+dcb_i2c_entry(struct nvkm_bios *bios, u8 idx, u8 *ver, u8 *len)
+{
+       u8  hdr, cnt;
+       u16 i2c = dcb_i2c_table(bios, ver, &hdr, &cnt, len);
+       if (i2c && idx < cnt)
+               return i2c + hdr + (idx * *len);
+       return 0x0000;
+}
+
+int
+dcb_i2c_parse(struct nvkm_bios *bios, u8 idx, struct dcb_i2c_entry *info)
+{
+       u8  ver, len;
+       u16 ent = dcb_i2c_entry(bios, idx, &ver, &len);
+       if (ent) {
+               if (ver >= 0x41) {
+                       if (!(nv_ro32(bios, ent) & 0x80000000))
+                               info->type = DCB_I2C_UNUSED;
+                       else
+                               info->type = DCB_I2C_PMGR;
+               } else
+               if (ver >= 0x30) {
+                       info->type = nv_ro08(bios, ent + 0x03);
+               } else {
+                       info->type = nv_ro08(bios, ent + 0x03) & 0x07;
+                       if (info->type == 0x07)
+                               info->type = DCB_I2C_UNUSED;
+               }
+
+               info->drive = DCB_I2C_UNUSED;
+               info->sense = DCB_I2C_UNUSED;
+               info->share = DCB_I2C_UNUSED;
+               info->auxch = DCB_I2C_UNUSED;
+
+               switch (info->type) {
+               case DCB_I2C_NV04_BIT:
+                       info->drive = nv_ro08(bios, ent + 0);
+                       info->sense = nv_ro08(bios, ent + 1);
+                       return 0;
+               case DCB_I2C_NV4E_BIT:
+                       info->drive = nv_ro08(bios, ent + 1);
+                       return 0;
+               case DCB_I2C_NVIO_BIT:
+                       info->drive = nv_ro08(bios, ent + 0) & 0x0f;
+                       if (nv_ro08(bios, ent + 1) & 0x01)
+                               info->share = nv_ro08(bios, ent + 1) >> 1;
+                       return 0;
+               case DCB_I2C_NVIO_AUX:
+                       info->auxch = nv_ro08(bios, ent + 0) & 0x0f;
+                       if (nv_ro08(bios, ent + 1) & 0x01)
+                                       info->share = info->auxch;
+                       return 0;
+               case DCB_I2C_PMGR:
+                       info->drive = (nv_ro16(bios, ent + 0) & 0x01f) >> 0;
+                       if (info->drive == 0x1f)
+                               info->drive = DCB_I2C_UNUSED;
+                       info->auxch = (nv_ro16(bios, ent + 0) & 0x3e0) >> 5;
+                       if (info->auxch == 0x1f)
+                               info->auxch = DCB_I2C_UNUSED;
+                       info->share = info->auxch;
+                       return 0;
+               case DCB_I2C_UNUSED:
+                       return 0;
+               default:
+                       nv_warn(bios, "unknown i2c type %d\n", info->type);
+                       info->type = DCB_I2C_UNUSED;
+                       return 0;
+               }
+       }
+
+       if (bios->bmp_offset && idx < 2) {
+               /* BMP (from v4.0 has i2c info in the structure, it's in a
+                * fixed location on earlier VBIOS
+                */
+               if (nv_ro08(bios, bios->bmp_offset + 5) < 4)
+                       ent = 0x0048;
+               else
+                       ent = 0x0036 + bios->bmp_offset;
+
+               if (idx == 0) {
+                       info->drive = nv_ro08(bios, ent + 4);
+                       if (!info->drive) info->drive = 0x3f;
+                       info->sense = nv_ro08(bios, ent + 5);
+                       if (!info->sense) info->sense = 0x3e;
+               } else
+               if (idx == 1) {
+                       info->drive = nv_ro08(bios, ent + 6);
+                       if (!info->drive) info->drive = 0x37;
+                       info->sense = nv_ro08(bios, ent + 7);
+                       if (!info->sense) info->sense = 0x36;
+               }
+
+               info->type  = DCB_I2C_NV04_BIT;
+               info->share = DCB_I2C_UNUSED;
+               return 0;
+       }
+
+       return -ENOENT;
+}
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/bios/image.c b/drivers/gpu/drm/nouveau/nvkm/subdev/bios/image.c
new file mode 100644 (file)
index 0000000..1815540
--- /dev/null
@@ -0,0 +1,77 @@
+/*
+ * Copyright 2014 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 <bskeggs@redhat.com>
+ */
+#include <subdev/bios.h>
+#include <subdev/bios/image.h>
+#include <subdev/bios/pcir.h>
+#include <subdev/bios/npde.h>
+
+static bool
+nvbios_imagen(struct nvkm_bios *bios, struct nvbios_image *image)
+{
+       struct nvbios_pcirT pcir;
+       struct nvbios_npdeT npde;
+       u8  ver;
+       u16 hdr;
+       u32 data;
+
+       switch ((data = nv_ro16(bios, image->base + 0x00))) {
+       case 0xaa55:
+       case 0xbb77:
+       case 0x4e56: /* NV */
+               break;
+       default:
+               nv_debug(bios, "%08x: ROM signature (%04x) unknown\n",
+                        image->base, data);
+               return false;
+       }
+
+       if (!(data = nvbios_pcirTp(bios, image->base, &ver, &hdr, &pcir)))
+               return false;
+       image->size = pcir.image_size;
+       image->type = pcir.image_type;
+       image->last = pcir.last;
+
+       if (image->type != 0x70) {
+               if (!(data = nvbios_npdeTp(bios, image->base, &npde)))
+                       return true;
+               image->size = npde.image_size;
+               image->last = npde.last;
+       } else {
+               image->last = true;
+       }
+
+       return true;
+}
+
+bool
+nvbios_image(struct nvkm_bios *bios, int idx, struct nvbios_image *image)
+{
+       memset(image, 0x00, sizeof(*image));
+       do {
+               image->base += image->size;
+               if (image->last || !nvbios_imagen(bios, image))
+                       return false;
+       } while(idx--);
+       return true;
+}
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/bios/init.c b/drivers/gpu/drm/nouveau/nvkm/subdev/bios/init.c
new file mode 100644 (file)
index 0000000..f67cdae
--- /dev/null
@@ -0,0 +1,2247 @@
+/*
+ * Copyright 2012 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 <subdev/bios.h>
+#include <subdev/bios/bit.h>
+#include <subdev/bios/bmp.h>
+#include <subdev/bios/conn.h>
+#include <subdev/bios/dcb.h>
+#include <subdev/bios/dp.h>
+#include <subdev/bios/gpio.h>
+#include <subdev/bios/init.h>
+#include <subdev/bios/ramcfg.h>
+
+#include <core/device.h>
+#include <subdev/devinit.h>
+#include <subdev/gpio.h>
+#include <subdev/i2c.h>
+#include <subdev/vga.h>
+
+#define bioslog(lvl, fmt, args...) do {                                        \
+       nv_printk(init->bios, lvl, "0x%04x[%c]: "fmt, init->offset,            \
+                 init_exec(init) ? '0' + (init->nested - 1) : ' ', ##args);   \
+} while(0)
+#define cont(fmt, args...) do {                                                \
+       if (nv_subdev(init->bios)->debug >= NV_DBG_TRACE)                      \
+               printk(fmt, ##args);                                           \
+} while(0)
+#define trace(fmt, args...) bioslog(TRACE, fmt, ##args)
+#define warn(fmt, args...) bioslog(WARN, fmt, ##args)
+#define error(fmt, args...) bioslog(ERROR, fmt, ##args)
+
+/******************************************************************************
+ * init parser control flow helpers
+ *****************************************************************************/
+
+static inline bool
+init_exec(struct nvbios_init *init)
+{
+       return (init->execute == 1) || ((init->execute & 5) == 5);
+}
+
+static inline void
+init_exec_set(struct nvbios_init *init, bool exec)
+{
+       if (exec) init->execute &= 0xfd;
+       else      init->execute |= 0x02;
+}
+
+static inline void
+init_exec_inv(struct nvbios_init *init)
+{
+       init->execute ^= 0x02;
+}
+
+static inline void
+init_exec_force(struct nvbios_init *init, bool exec)
+{
+       if (exec) init->execute |= 0x04;
+       else      init->execute &= 0xfb;
+}
+
+/******************************************************************************
+ * init parser wrappers for normal register/i2c/whatever accessors
+ *****************************************************************************/
+
+static inline int
+init_or(struct nvbios_init *init)
+{
+       if (init_exec(init)) {
+               if (init->outp)
+                       return ffs(init->outp->or) - 1;
+               error("script needs OR!!\n");
+       }
+       return 0;
+}
+
+static inline int
+init_link(struct nvbios_init *init)
+{
+       if (init_exec(init)) {
+               if (init->outp)
+                       return !(init->outp->sorconf.link & 1);
+               error("script needs OR link\n");
+       }
+       return 0;
+}
+
+static inline int
+init_crtc(struct nvbios_init *init)
+{
+       if (init_exec(init)) {
+               if (init->crtc >= 0)
+                       return init->crtc;
+               error("script needs crtc\n");
+       }
+       return 0;
+}
+
+static u8
+init_conn(struct nvbios_init *init)
+{
+       struct nvkm_bios *bios = init->bios;
+       struct nvbios_connE connE;
+       u8  ver, hdr;
+       u32 conn;
+
+       if (init_exec(init)) {
+               if (init->outp) {
+                       conn = init->outp->connector;
+                       conn = nvbios_connEp(bios, conn, &ver, &hdr, &connE);
+                       if (conn)
+                               return connE.type;
+               }
+
+               error("script needs connector type\n");
+       }
+
+       return 0xff;
+}
+
+static inline u32
+init_nvreg(struct nvbios_init *init, u32 reg)
+{
+       struct nvkm_devinit *devinit = nvkm_devinit(init->bios);
+
+       /* C51 (at least) sometimes has the lower bits set which the VBIOS
+        * interprets to mean that access needs to go through certain IO
+        * ports instead.  The NVIDIA binary driver has been seen to access
+        * these through the NV register address, so lets assume we can
+        * do the same
+        */
+       reg &= ~0x00000003;
+
+       /* GF8+ display scripts need register addresses mangled a bit to
+        * select a specific CRTC/OR
+        */
+       if (nv_device(init->bios)->card_type >= NV_50) {
+               if (reg & 0x80000000) {
+                       reg += init_crtc(init) * 0x800;
+                       reg &= ~0x80000000;
+               }
+
+               if (reg & 0x40000000) {
+                       reg += init_or(init) * 0x800;
+                       reg &= ~0x40000000;
+                       if (reg & 0x20000000) {
+                               reg += init_link(init) * 0x80;
+                               reg &= ~0x20000000;
+                       }
+               }
+       }
+
+       if (reg & ~0x00fffffc)
+               warn("unknown bits in register 0x%08x\n", reg);
+
+       if (devinit->mmio)
+               reg = devinit->mmio(devinit, reg);
+       return reg;
+}
+
+static u32
+init_rd32(struct nvbios_init *init, u32 reg)
+{
+       reg = init_nvreg(init, reg);
+       if (reg != ~0 && init_exec(init))
+               return nv_rd32(init->subdev, reg);
+       return 0x00000000;
+}
+
+static void
+init_wr32(struct nvbios_init *init, u32 reg, u32 val)
+{
+       reg = init_nvreg(init, reg);
+       if (reg != ~0 && init_exec(init))
+               nv_wr32(init->subdev, reg, val);
+}
+
+static u32
+init_mask(struct nvbios_init *init, u32 reg, u32 mask, u32 val)
+{
+       reg = init_nvreg(init, reg);
+       if (reg != ~0 && init_exec(init)) {
+               u32 tmp = nv_rd32(init->subdev, reg);
+               nv_wr32(init->subdev, reg, (tmp & ~mask) | val);
+               return tmp;
+       }
+       return 0x00000000;
+}
+
+static u8
+init_rdport(struct nvbios_init *init, u16 port)
+{
+       if (init_exec(init))
+               return nv_rdport(init->subdev, init->crtc, port);
+       return 0x00;
+}
+
+static void
+init_wrport(struct nvbios_init *init, u16 port, u8 value)
+{
+       if (init_exec(init))
+               nv_wrport(init->subdev, init->crtc, port, value);
+}
+
+static u8
+init_rdvgai(struct nvbios_init *init, u16 port, u8 index)
+{
+       struct nvkm_subdev *subdev = init->subdev;
+       if (init_exec(init)) {
+               int head = init->crtc < 0 ? 0 : init->crtc;
+               return nv_rdvgai(subdev, head, port, index);
+       }
+       return 0x00;
+}
+
+static void
+init_wrvgai(struct nvbios_init *init, u16 port, u8 index, u8 value)
+{
+       /* force head 0 for updates to cr44, it only exists on first head */
+       if (nv_device(init->subdev)->card_type < NV_50) {
+               if (port == 0x03d4 && index == 0x44)
+                       init->crtc = 0;
+       }
+
+       if (init_exec(init)) {
+               int head = init->crtc < 0 ? 0 : init->crtc;
+               nv_wrvgai(init->subdev, head, port, index, value);
+       }
+
+       /* select head 1 if cr44 write selected it */
+       if (nv_device(init->subdev)->card_type < NV_50) {
+               if (port == 0x03d4 && index == 0x44 && value == 3)
+                       init->crtc = 1;
+       }
+}
+
+static struct nvkm_i2c_port *
+init_i2c(struct nvbios_init *init, int index)
+{
+       struct nvkm_i2c *i2c = nvkm_i2c(init->bios);
+
+       if (index == 0xff) {
+               index = NV_I2C_DEFAULT(0);
+               if (init->outp && init->outp->i2c_upper_default)
+                       index = NV_I2C_DEFAULT(1);
+       } else
+       if (index < 0) {
+               if (!init->outp) {
+                       if (init_exec(init))
+                               error("script needs output for i2c\n");
+                       return NULL;
+               }
+
+               if (index == -2 && init->outp->location) {
+                       index = NV_I2C_TYPE_EXTAUX(init->outp->extdev);
+                       return i2c->find_type(i2c, index);
+               }
+
+               index = init->outp->i2c_index;
+               if (init->outp->type == DCB_OUTPUT_DP)
+                       index += NV_I2C_AUX(0);
+       }
+
+       return i2c->find(i2c, index);
+}
+
+static int
+init_rdi2cr(struct nvbios_init *init, u8 index, u8 addr, u8 reg)
+{
+       struct nvkm_i2c_port *port = init_i2c(init, index);
+       if (port && init_exec(init))
+               return nv_rdi2cr(port, addr, reg);
+       return -ENODEV;
+}
+
+static int
+init_wri2cr(struct nvbios_init *init, u8 index, u8 addr, u8 reg, u8 val)
+{
+       struct nvkm_i2c_port *port = init_i2c(init, index);
+       if (port && init_exec(init))
+               return nv_wri2cr(port, addr, reg, val);
+       return -ENODEV;
+}
+
+static u8
+init_rdauxr(struct nvbios_init *init, u32 addr)
+{
+       struct nvkm_i2c_port *port = init_i2c(init, -2);
+       u8 data;
+
+       if (port && init_exec(init)) {
+               int ret = nv_rdaux(port, addr, &data, 1);
+               if (ret == 0)
+                       return data;
+               trace("auxch read failed with %d\n", ret);
+       }
+
+       return 0x00;
+}
+
+static int
+init_wrauxr(struct nvbios_init *init, u32 addr, u8 data)
+{
+       struct nvkm_i2c_port *port = init_i2c(init, -2);
+       if (port && init_exec(init)) {
+               int ret = nv_wraux(port, addr, &data, 1);
+               if (ret)
+                       trace("auxch write failed with %d\n", ret);
+               return ret;
+       }
+       return -ENODEV;
+}
+
+static void
+init_prog_pll(struct nvbios_init *init, u32 id, u32 freq)
+{
+       struct nvkm_devinit *devinit = nvkm_devinit(init->bios);
+       if (devinit->pll_set && init_exec(init)) {
+               int ret = devinit->pll_set(devinit, id, freq);
+               if (ret)
+                       warn("failed to prog pll 0x%08x to %dkHz\n", id, freq);
+       }
+}
+
+/******************************************************************************
+ * parsing of bios structures that are required to execute init tables
+ *****************************************************************************/
+
+static u16
+init_table(struct nvkm_bios *bios, u16 *len)
+{
+       struct bit_entry bit_I;
+
+       if (!bit_entry(bios, 'I', &bit_I)) {
+               *len = bit_I.length;
+               return bit_I.offset;
+       }
+
+       if (bmp_version(bios) >= 0x0510) {
+               *len = 14;
+               return bios->bmp_offset + 75;
+       }
+
+       return 0x0000;
+}
+
+static u16
+init_table_(struct nvbios_init *init, u16 offset, const char *name)
+{
+       struct nvkm_bios *bios = init->bios;
+       u16 len, data = init_table(bios, &len);
+       if (data) {
+               if (len >= offset + 2) {
+                       data = nv_ro16(bios, data + offset);
+                       if (data)
+                               return data;
+
+                       warn("%s pointer invalid\n", name);
+                       return 0x0000;
+               }
+
+               warn("init data too short for %s pointer", name);
+               return 0x0000;
+       }
+
+       warn("init data not found\n");
+       return 0x0000;
+}
+
+#define init_script_table(b) init_table_((b), 0x00, "script table")
+#define init_macro_index_table(b) init_table_((b), 0x02, "macro index table")
+#define init_macro_table(b) init_table_((b), 0x04, "macro table")
+#define init_condition_table(b) init_table_((b), 0x06, "condition table")
+#define init_io_condition_table(b) init_table_((b), 0x08, "io condition table")
+#define init_io_flag_condition_table(b) init_table_((b), 0x0a, "io flag conditon table")
+#define init_function_table(b) init_table_((b), 0x0c, "function table")
+#define init_xlat_table(b) init_table_((b), 0x10, "xlat table");
+
+static u16
+init_script(struct nvkm_bios *bios, int index)
+{
+       struct nvbios_init init = { .bios = bios };
+       u16 bmp_ver = bmp_version(bios), data;
+
+       if (bmp_ver && bmp_ver < 0x0510) {
+               if (index > 1 || bmp_ver < 0x0100)
+                       return 0x0000;
+
+               data = bios->bmp_offset + (bmp_ver < 0x0200 ? 14 : 18);
+               return nv_ro16(bios, data + (index * 2));
+       }
+
+       data = init_script_table(&init);
+       if (data)
+               return nv_ro16(bios, data + (index * 2));
+
+       return 0x0000;
+}
+
+static u16
+init_unknown_script(struct nvkm_bios *bios)
+{
+       u16 len, data = init_table(bios, &len);
+       if (data && len >= 16)
+               return nv_ro16(bios, data + 14);
+       return 0x0000;
+}
+
+static u8
+init_ram_restrict_group_count(struct nvbios_init *init)
+{
+       return nvbios_ramcfg_count(init->bios);
+}
+
+static u8
+init_ram_restrict(struct nvbios_init *init)
+{
+       /* This appears to be the behaviour of the VBIOS parser, and *is*
+        * important to cache the NV_PEXTDEV_BOOT0 on later chipsets to
+        * avoid fucking up the memory controller (somehow) by reading it
+        * on every INIT_RAM_RESTRICT_ZM_GROUP opcode.
+        *
+        * Preserving the non-caching behaviour on earlier chipsets just
+        * in case *not* re-reading the strap causes similar breakage.
+        */
+       if (!init->ramcfg || init->bios->version.major < 0x70)
+               init->ramcfg = 0x80000000 | nvbios_ramcfg_index(init->subdev);
+       return (init->ramcfg & 0x7fffffff);
+}
+
+static u8
+init_xlat_(struct nvbios_init *init, u8 index, u8 offset)
+{
+       struct nvkm_bios *bios = init->bios;
+       u16 table = init_xlat_table(init);
+       if (table) {
+               u16 data = nv_ro16(bios, table + (index * 2));
+               if (data)
+                       return nv_ro08(bios, data + offset);
+               warn("xlat table pointer %d invalid\n", index);
+       }
+       return 0x00;
+}
+
+/******************************************************************************
+ * utility functions used by various init opcode handlers
+ *****************************************************************************/
+
+static bool
+init_condition_met(struct nvbios_init *init, u8 cond)
+{
+       struct nvkm_bios *bios = init->bios;
+       u16 table = init_condition_table(init);
+       if (table) {
+               u32 reg = nv_ro32(bios, table + (cond * 12) + 0);
+               u32 msk = nv_ro32(bios, table + (cond * 12) + 4);
+               u32 val = nv_ro32(bios, table + (cond * 12) + 8);
+               trace("\t[0x%02x] (R[0x%06x] & 0x%08x) == 0x%08x\n",
+                     cond, reg, msk, val);
+               return (init_rd32(init, reg) & msk) == val;
+       }
+       return false;
+}
+
+static bool
+init_io_condition_met(struct nvbios_init *init, u8 cond)
+{
+       struct nvkm_bios *bios = init->bios;
+       u16 table = init_io_condition_table(init);
+       if (table) {
+               u16 port = nv_ro16(bios, table + (cond * 5) + 0);
+               u8 index = nv_ro08(bios, table + (cond * 5) + 2);
+               u8  mask = nv_ro08(bios, table + (cond * 5) + 3);
+               u8 value = nv_ro08(bios, table + (cond * 5) + 4);
+               trace("\t[0x%02x] (0x%04x[0x%02x] & 0x%02x) == 0x%02x\n",
+                     cond, port, index, mask, value);
+               return (init_rdvgai(init, port, index) & mask) == value;
+       }
+       return false;
+}
+
+static bool
+init_io_flag_condition_met(struct nvbios_init *init, u8 cond)
+{
+       struct nvkm_bios *bios = init->bios;
+       u16 table = init_io_flag_condition_table(init);
+       if (table) {
+               u16 port = nv_ro16(bios, table + (cond * 9) + 0);
+               u8 index = nv_ro08(bios, table + (cond * 9) + 2);
+               u8  mask = nv_ro08(bios, table + (cond * 9) + 3);
+               u8 shift = nv_ro08(bios, table + (cond * 9) + 4);
+               u16 data = nv_ro16(bios, table + (cond * 9) + 5);
+               u8 dmask = nv_ro08(bios, table + (cond * 9) + 7);
+               u8 value = nv_ro08(bios, table + (cond * 9) + 8);
+               u8 ioval = (init_rdvgai(init, port, index) & mask) >> shift;
+               return (nv_ro08(bios, data + ioval) & dmask) == value;
+       }
+       return false;
+}
+
+static inline u32
+init_shift(u32 data, u8 shift)
+{
+       if (shift < 0x80)
+               return data >> shift;
+       return data << (0x100 - shift);
+}
+
+static u32
+init_tmds_reg(struct nvbios_init *init, u8 tmds)
+{
+       /* 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.
+        */
+       const int pramdac_offset[13] = {
+               0, 0, 0x8, 0, 0x2000, 0, 0, 0, 0x2008, 0, 0, 0, 0x2000 };
+       const u32 pramdac_table[4] = {
+               0x6808b0, 0x6808b8, 0x6828b0, 0x6828b8 };
+
+       if (tmds >= 0x80) {
+               if (init->outp) {
+                       u32 dacoffset = pramdac_offset[init->outp->or];
+                       if (tmds == 0x81)
+                               dacoffset ^= 8;
+                       return 0x6808b0 + dacoffset;
+               }
+
+               if (init_exec(init))
+                       error("tmds opcodes need dcb\n");
+       } else {
+               if (tmds < ARRAY_SIZE(pramdac_table))
+                       return pramdac_table[tmds];
+
+               error("tmds selector 0x%02x unknown\n", tmds);
+       }
+
+       return 0;
+}
+
+/******************************************************************************
+ * init opcode handlers
+ *****************************************************************************/
+
+/**
+ * init_reserved - stub for various unknown/unused single-byte opcodes
+ *
+ */
+static void
+init_reserved(struct nvbios_init *init)
+{
+       u8 opcode = nv_ro08(init->bios, init->offset);
+       u8 length, i;
+
+       switch (opcode) {
+       case 0xaa:
+               length = 4;
+               break;
+       default:
+               length = 1;
+               break;
+       }
+
+       trace("RESERVED 0x%02x\t", opcode);
+       for (i = 1; i < length; i++)
+               cont(" 0x%02x", nv_ro08(init->bios, init->offset + i));
+       cont("\n");
+       init->offset += length;
+}
+
+/**
+ * INIT_DONE - opcode 0x71
+ *
+ */
+static void
+init_done(struct nvbios_init *init)
+{
+       trace("DONE\n");
+       init->offset = 0x0000;
+}
+
+/**
+ * INIT_IO_RESTRICT_PROG - opcode 0x32
+ *
+ */
+static void
+init_io_restrict_prog(struct nvbios_init *init)
+{
+       struct nvkm_bios *bios = init->bios;
+       u16 port = nv_ro16(bios, init->offset + 1);
+       u8 index = nv_ro08(bios, init->offset + 3);
+       u8  mask = nv_ro08(bios, init->offset + 4);
+       u8 shift = nv_ro08(bios, init->offset + 5);
+       u8 count = nv_ro08(bios, init->offset + 6);
+       u32  reg = nv_ro32(bios, init->offset + 7);
+       u8 conf, i;
+
+       trace("IO_RESTRICT_PROG\tR[0x%06x] = "
+             "((0x%04x[0x%02x] & 0x%02x) >> %d) [{\n",
+             reg, port, index, mask, shift);
+       init->offset += 11;
+
+       conf = (init_rdvgai(init, port, index) & mask) >> shift;
+       for (i = 0; i < count; i++) {
+               u32 data = nv_ro32(bios, init->offset);
+
+               if (i == conf) {
+                       trace("\t0x%08x *\n", data);
+                       init_wr32(init, reg, data);
+               } else {
+                       trace("\t0x%08x\n", data);
+               }
+
+               init->offset += 4;
+       }
+       trace("}]\n");
+}
+
+/**
+ * INIT_REPEAT - opcode 0x33
+ *
+ */
+static void
+init_repeat(struct nvbios_init *init)
+{
+       struct nvkm_bios *bios = init->bios;
+       u8 count = nv_ro08(bios, init->offset + 1);
+       u16 repeat = init->repeat;
+
+       trace("REPEAT\t0x%02x\n", count);
+       init->offset += 2;
+
+       init->repeat = init->offset;
+       init->repend = init->offset;
+       while (count--) {
+               init->offset = init->repeat;
+               nvbios_exec(init);
+               if (count)
+                       trace("REPEAT\t0x%02x\n", count);
+       }
+       init->offset = init->repend;
+       init->repeat = repeat;
+}
+
+/**
+ * INIT_IO_RESTRICT_PLL - opcode 0x34
+ *
+ */
+static void
+init_io_restrict_pll(struct nvbios_init *init)
+{
+       struct nvkm_bios *bios = init->bios;
+       u16 port = nv_ro16(bios, init->offset + 1);
+       u8 index = nv_ro08(bios, init->offset + 3);
+       u8  mask = nv_ro08(bios, init->offset + 4);
+       u8 shift = nv_ro08(bios, init->offset + 5);
+       s8  iofc = nv_ro08(bios, init->offset + 6);
+       u8 count = nv_ro08(bios, init->offset + 7);
+       u32  reg = nv_ro32(bios, init->offset + 8);
+       u8 conf, i;
+
+       trace("IO_RESTRICT_PLL\tR[0x%06x] =PLL= "
+             "((0x%04x[0x%02x] & 0x%02x) >> 0x%02x) IOFCOND 0x%02x [{\n",
+             reg, port, index, mask, shift, iofc);
+       init->offset += 12;
+
+       conf = (init_rdvgai(init, port, index) & mask) >> shift;
+       for (i = 0; i < count; i++) {
+               u32 freq = nv_ro16(bios, init->offset) * 10;
+
+               if (i == conf) {
+                       trace("\t%dkHz *\n", freq);
+                       if (iofc > 0 && init_io_flag_condition_met(init, iofc))
+                               freq *= 2;
+                       init_prog_pll(init, reg, freq);
+               } else {
+                       trace("\t%dkHz\n", freq);
+               }
+
+               init->offset += 2;
+       }
+       trace("}]\n");
+}
+
+/**
+ * INIT_END_REPEAT - opcode 0x36
+ *
+ */
+static void
+init_end_repeat(struct nvbios_init *init)
+{
+       trace("END_REPEAT\n");
+       init->offset += 1;
+
+       if (init->repeat) {
+               init->repend = init->offset;
+               init->offset = 0;
+       }
+}
+
+/**
+ * INIT_COPY - opcode 0x37
+ *
+ */
+static void
+init_copy(struct nvbios_init *init)
+{
+       struct nvkm_bios *bios = init->bios;
+       u32  reg = nv_ro32(bios, init->offset + 1);
+       u8 shift = nv_ro08(bios, init->offset + 5);
+       u8 smask = nv_ro08(bios, init->offset + 6);
+       u16 port = nv_ro16(bios, init->offset + 7);
+       u8 index = nv_ro08(bios, init->offset + 9);
+       u8  mask = nv_ro08(bios, init->offset + 10);
+       u8  data;
+
+       trace("COPY\t0x%04x[0x%02x] &= 0x%02x |= "
+             "((R[0x%06x] %s 0x%02x) & 0x%02x)\n",
+             port, index, mask, reg, (shift & 0x80) ? "<<" : ">>",
+             (shift & 0x80) ? (0x100 - shift) : shift, smask);
+       init->offset += 11;
+
+       data  = init_rdvgai(init, port, index) & mask;
+       data |= init_shift(init_rd32(init, reg), shift) & smask;
+       init_wrvgai(init, port, index, data);
+}
+
+/**
+ * INIT_NOT - opcode 0x38
+ *
+ */
+static void
+init_not(struct nvbios_init *init)
+{
+       trace("NOT\n");
+       init->offset += 1;
+       init_exec_inv(init);
+}
+
+/**
+ * INIT_IO_FLAG_CONDITION - opcode 0x39
+ *
+ */
+static void
+init_io_flag_condition(struct nvbios_init *init)
+{
+       struct nvkm_bios *bios = init->bios;
+       u8 cond = nv_ro08(bios, init->offset + 1);
+
+       trace("IO_FLAG_CONDITION\t0x%02x\n", cond);
+       init->offset += 2;
+
+       if (!init_io_flag_condition_met(init, cond))
+               init_exec_set(init, false);
+}
+
+/**
+ * INIT_DP_CONDITION - opcode 0x3a
+ *
+ */
+static void
+init_dp_condition(struct nvbios_init *init)
+{
+       struct nvkm_bios *bios = init->bios;
+       struct nvbios_dpout info;
+       u8  cond = nv_ro08(bios, init->offset + 1);
+       u8  unkn = nv_ro08(bios, init->offset + 2);
+       u8  ver, hdr, cnt, len;
+       u16 data;
+
+       trace("DP_CONDITION\t0x%02x 0x%02x\n", cond, unkn);
+       init->offset += 3;
+
+       switch (cond) {
+       case 0:
+               if (init_conn(init) != DCB_CONNECTOR_eDP)
+                       init_exec_set(init, false);
+               break;
+       case 1:
+       case 2:
+               if ( init->outp &&
+                   (data = nvbios_dpout_match(bios, DCB_OUTPUT_DP,
+                                              (init->outp->or << 0) |
+                                              (init->outp->sorconf.link << 6),
+                                              &ver, &hdr, &cnt, &len, &info)))
+               {
+                       if (!(info.flags & cond))
+                               init_exec_set(init, false);
+                       break;
+               }
+
+               if (init_exec(init))
+                       warn("script needs dp output table data\n");
+               break;
+       case 5:
+               if (!(init_rdauxr(init, 0x0d) & 1))
+                       init_exec_set(init, false);
+               break;
+       default:
+               warn("unknown dp condition 0x%02x\n", cond);
+               break;
+       }
+}
+
+/**
+ * INIT_IO_MASK_OR - opcode 0x3b
+ *
+ */
+static void
+init_io_mask_or(struct nvbios_init *init)
+{
+       struct nvkm_bios *bios = init->bios;
+       u8 index = nv_ro08(bios, init->offset + 1);
+       u8    or = init_or(init);
+       u8  data;
+
+       trace("IO_MASK_OR\t0x03d4[0x%02x] &= ~(1 << 0x%02x)\n", index, or);
+       init->offset += 2;
+
+       data = init_rdvgai(init, 0x03d4, index);
+       init_wrvgai(init, 0x03d4, index, data &= ~(1 << or));
+}
+
+/**
+ * INIT_IO_OR - opcode 0x3c
+ *
+ */
+static void
+init_io_or(struct nvbios_init *init)
+{
+       struct nvkm_bios *bios = init->bios;
+       u8 index = nv_ro08(bios, init->offset + 1);
+       u8    or = init_or(init);
+       u8  data;
+
+       trace("IO_OR\t0x03d4[0x%02x] |= (1 << 0x%02x)\n", index, or);
+       init->offset += 2;
+
+       data = init_rdvgai(init, 0x03d4, index);
+       init_wrvgai(init, 0x03d4, index, data | (1 << or));
+}
+
+/**
+ * INIT_ANDN_REG - opcode 0x47
+ *
+ */
+static void
+init_andn_reg(struct nvbios_init *init)
+{
+       struct nvkm_bios *bios = init->bios;
+       u32  reg = nv_ro32(bios, init->offset + 1);
+       u32 mask = nv_ro32(bios, init->offset + 5);
+
+       trace("ANDN_REG\tR[0x%06x] &= ~0x%08x\n", reg, mask);
+       init->offset += 9;
+
+       init_mask(init, reg, mask, 0);
+}
+
+/**
+ * INIT_OR_REG - opcode 0x48
+ *
+ */
+static void
+init_or_reg(struct nvbios_init *init)
+{
+       struct nvkm_bios *bios = init->bios;
+       u32  reg = nv_ro32(bios, init->offset + 1);
+       u32 mask = nv_ro32(bios, init->offset + 5);
+
+       trace("OR_REG\tR[0x%06x] |= 0x%08x\n", reg, mask);
+       init->offset += 9;
+
+       init_mask(init, reg, 0, mask);
+}
+
+/**
+ * INIT_INDEX_ADDRESS_LATCHED - opcode 0x49
+ *
+ */
+static void
+init_idx_addr_latched(struct nvbios_init *init)
+{
+       struct nvkm_bios *bios = init->bios;
+       u32 creg = nv_ro32(bios, init->offset + 1);
+       u32 dreg = nv_ro32(bios, init->offset + 5);
+       u32 mask = nv_ro32(bios, init->offset + 9);
+       u32 data = nv_ro32(bios, init->offset + 13);
+       u8 count = nv_ro08(bios, init->offset + 17);
+
+       trace("INDEX_ADDRESS_LATCHED\tR[0x%06x] : R[0x%06x]\n", creg, dreg);
+       trace("\tCTRL &= 0x%08x |= 0x%08x\n", mask, data);
+       init->offset += 18;
+
+       while (count--) {
+               u8 iaddr = nv_ro08(bios, init->offset + 0);
+               u8 idata = nv_ro08(bios, init->offset + 1);
+
+               trace("\t[0x%02x] = 0x%02x\n", iaddr, idata);
+               init->offset += 2;
+
+               init_wr32(init, dreg, idata);
+               init_mask(init, creg, ~mask, data | iaddr);
+       }
+}
+
+/**
+ * INIT_IO_RESTRICT_PLL2 - opcode 0x4a
+ *
+ */
+static void
+init_io_restrict_pll2(struct nvbios_init *init)
+{
+       struct nvkm_bios *bios = init->bios;
+       u16 port = nv_ro16(bios, init->offset + 1);
+       u8 index = nv_ro08(bios, init->offset + 3);
+       u8  mask = nv_ro08(bios, init->offset + 4);
+       u8 shift = nv_ro08(bios, init->offset + 5);
+       u8 count = nv_ro08(bios, init->offset + 6);
+       u32  reg = nv_ro32(bios, init->offset + 7);
+       u8  conf, i;
+
+       trace("IO_RESTRICT_PLL2\t"
+             "R[0x%06x] =PLL= ((0x%04x[0x%02x] & 0x%02x) >> 0x%02x) [{\n",
+             reg, port, index, mask, shift);
+       init->offset += 11;
+
+       conf = (init_rdvgai(init, port, index) & mask) >> shift;
+       for (i = 0; i < count; i++) {
+               u32 freq = nv_ro32(bios, init->offset);
+               if (i == conf) {
+                       trace("\t%dkHz *\n", freq);
+                       init_prog_pll(init, reg, freq);
+               } else {
+                       trace("\t%dkHz\n", freq);
+               }
+               init->offset += 4;
+       }
+       trace("}]\n");
+}
+
+/**
+ * INIT_PLL2 - opcode 0x4b
+ *
+ */
+static void
+init_pll2(struct nvbios_init *init)
+{
+       struct nvkm_bios *bios = init->bios;
+       u32  reg = nv_ro32(bios, init->offset + 1);
+       u32 freq = nv_ro32(bios, init->offset + 5);
+
+       trace("PLL2\tR[0x%06x] =PLL= %dkHz\n", reg, freq);
+       init->offset += 9;
+
+       init_prog_pll(init, reg, freq);
+}
+
+/**
+ * INIT_I2C_BYTE - opcode 0x4c
+ *
+ */
+static void
+init_i2c_byte(struct nvbios_init *init)
+{
+       struct nvkm_bios *bios = init->bios;
+       u8 index = nv_ro08(bios, init->offset + 1);
+       u8  addr = nv_ro08(bios, init->offset + 2) >> 1;
+       u8 count = nv_ro08(bios, init->offset + 3);
+
+       trace("I2C_BYTE\tI2C[0x%02x][0x%02x]\n", index, addr);
+       init->offset += 4;
+
+       while (count--) {
+               u8  reg = nv_ro08(bios, init->offset + 0);
+               u8 mask = nv_ro08(bios, init->offset + 1);
+               u8 data = nv_ro08(bios, init->offset + 2);
+               int val;
+
+               trace("\t[0x%02x] &= 0x%02x |= 0x%02x\n", reg, mask, data);
+               init->offset += 3;
+
+               val = init_rdi2cr(init, index, addr, reg);
+               if (val < 0)
+                       continue;
+               init_wri2cr(init, index, addr, reg, (val & mask) | data);
+       }
+}
+
+/**
+ * INIT_ZM_I2C_BYTE - opcode 0x4d
+ *
+ */
+static void
+init_zm_i2c_byte(struct nvbios_init *init)
+{
+       struct nvkm_bios *bios = init->bios;
+       u8 index = nv_ro08(bios, init->offset + 1);
+       u8  addr = nv_ro08(bios, init->offset + 2) >> 1;
+       u8 count = nv_ro08(bios, init->offset + 3);
+
+       trace("ZM_I2C_BYTE\tI2C[0x%02x][0x%02x]\n", index, addr);
+       init->offset += 4;
+
+       while (count--) {
+               u8  reg = nv_ro08(bios, init->offset + 0);
+               u8 data = nv_ro08(bios, init->offset + 1);
+
+               trace("\t[0x%02x] = 0x%02x\n", reg, data);
+               init->offset += 2;
+
+               init_wri2cr(init, index, addr, reg, data);
+       }
+}
+
+/**
+ * INIT_ZM_I2C - opcode 0x4e
+ *
+ */
+static void
+init_zm_i2c(struct nvbios_init *init)
+{
+       struct nvkm_bios *bios = init->bios;
+       u8 index = nv_ro08(bios, init->offset + 1);
+       u8  addr = nv_ro08(bios, init->offset + 2) >> 1;
+       u8 count = nv_ro08(bios, init->offset + 3);
+       u8 data[256], i;
+
+       trace("ZM_I2C\tI2C[0x%02x][0x%02x]\n", index, addr);
+       init->offset += 4;
+
+       for (i = 0; i < count; i++) {
+               data[i] = nv_ro08(bios, init->offset);
+               trace("\t0x%02x\n", data[i]);
+               init->offset++;
+       }
+
+       if (init_exec(init)) {
+               struct nvkm_i2c_port *port = init_i2c(init, index);
+               struct i2c_msg msg = {
+                       .addr = addr, .flags = 0, .len = count, .buf = data,
+               };
+               int ret;
+
+               if (port && (ret = i2c_transfer(&port->adapter, &msg, 1)) != 1)
+                       warn("i2c wr failed, %d\n", ret);
+       }
+}
+
+/**
+ * INIT_TMDS - opcode 0x4f
+ *
+ */
+static void
+init_tmds(struct nvbios_init *init)
+{
+       struct nvkm_bios *bios = init->bios;
+       u8 tmds = nv_ro08(bios, init->offset + 1);
+       u8 addr = nv_ro08(bios, init->offset + 2);
+       u8 mask = nv_ro08(bios, init->offset + 3);
+       u8 data = nv_ro08(bios, init->offset + 4);
+       u32 reg = init_tmds_reg(init, tmds);
+
+       trace("TMDS\tT[0x%02x][0x%02x] &= 0x%02x |= 0x%02x\n",
+             tmds, addr, mask, data);
+       init->offset += 5;
+
+       if (reg == 0)
+               return;
+
+       init_wr32(init, reg + 0, addr | 0x00010000);
+       init_wr32(init, reg + 4, data | (init_rd32(init, reg + 4) & mask));
+       init_wr32(init, reg + 0, addr);
+}
+
+/**
+ * INIT_ZM_TMDS_GROUP - opcode 0x50
+ *
+ */
+static void
+init_zm_tmds_group(struct nvbios_init *init)
+{
+       struct nvkm_bios *bios = init->bios;
+       u8  tmds = nv_ro08(bios, init->offset + 1);
+       u8 count = nv_ro08(bios, init->offset + 2);
+       u32  reg = init_tmds_reg(init, tmds);
+
+       trace("TMDS_ZM_GROUP\tT[0x%02x]\n", tmds);
+       init->offset += 3;
+
+       while (count--) {
+               u8 addr = nv_ro08(bios, init->offset + 0);
+               u8 data = nv_ro08(bios, init->offset + 1);
+
+               trace("\t[0x%02x] = 0x%02x\n", addr, data);
+               init->offset += 2;
+
+               init_wr32(init, reg + 4, data);
+               init_wr32(init, reg + 0, addr);
+       }
+}
+
+/**
+ * INIT_CR_INDEX_ADDRESS_LATCHED - opcode 0x51
+ *
+ */
+static void
+init_cr_idx_adr_latch(struct nvbios_init *init)
+{
+       struct nvkm_bios *bios = init->bios;
+       u8 addr0 = nv_ro08(bios, init->offset + 1);
+       u8 addr1 = nv_ro08(bios, init->offset + 2);
+       u8  base = nv_ro08(bios, init->offset + 3);
+       u8 count = nv_ro08(bios, init->offset + 4);
+       u8 save0;
+
+       trace("CR_INDEX_ADDR C[%02x] C[%02x]\n", addr0, addr1);
+       init->offset += 5;
+
+       save0 = init_rdvgai(init, 0x03d4, addr0);
+       while (count--) {
+               u8 data = nv_ro08(bios, init->offset);
+
+               trace("\t\t[0x%02x] = 0x%02x\n", base, data);
+               init->offset += 1;
+
+               init_wrvgai(init, 0x03d4, addr0, base++);
+               init_wrvgai(init, 0x03d4, addr1, data);
+       }
+       init_wrvgai(init, 0x03d4, addr0, save0);
+}
+
+/**
+ * INIT_CR - opcode 0x52
+ *
+ */
+static void
+init_cr(struct nvbios_init *init)
+{
+       struct nvkm_bios *bios = init->bios;
+       u8 addr = nv_ro08(bios, init->offset + 1);
+       u8 mask = nv_ro08(bios, init->offset + 2);
+       u8 data = nv_ro08(bios, init->offset + 3);
+       u8 val;
+
+       trace("CR\t\tC[0x%02x] &= 0x%02x |= 0x%02x\n", addr, mask, data);
+       init->offset += 4;
+
+       val = init_rdvgai(init, 0x03d4, addr) & mask;
+       init_wrvgai(init, 0x03d4, addr, val | data);
+}
+
+/**
+ * INIT_ZM_CR - opcode 0x53
+ *
+ */
+static void
+init_zm_cr(struct nvbios_init *init)
+{
+       struct nvkm_bios *bios = init->bios;
+       u8 addr = nv_ro08(bios, init->offset + 1);
+       u8 data = nv_ro08(bios, init->offset + 2);
+
+       trace("ZM_CR\tC[0x%02x] = 0x%02x\n", addr,  data);
+       init->offset += 3;
+
+       init_wrvgai(init, 0x03d4, addr, data);
+}
+
+/**
+ * INIT_ZM_CR_GROUP - opcode 0x54
+ *
+ */
+static void
+init_zm_cr_group(struct nvbios_init *init)
+{
+       struct nvkm_bios *bios = init->bios;
+       u8 count = nv_ro08(bios, init->offset + 1);
+
+       trace("ZM_CR_GROUP\n");
+       init->offset += 2;
+
+       while (count--) {
+               u8 addr = nv_ro08(bios, init->offset + 0);
+               u8 data = nv_ro08(bios, init->offset + 1);
+
+               trace("\t\tC[0x%02x] = 0x%02x\n", addr, data);
+               init->offset += 2;
+
+               init_wrvgai(init, 0x03d4, addr, data);
+       }
+}
+
+/**
+ * INIT_CONDITION_TIME - opcode 0x56
+ *
+ */
+static void
+init_condition_time(struct nvbios_init *init)
+{
+       struct nvkm_bios *bios = init->bios;
+       u8  cond = nv_ro08(bios, init->offset + 1);
+       u8 retry = nv_ro08(bios, init->offset + 2);
+       u8  wait = min((u16)retry * 50, 100);
+
+       trace("CONDITION_TIME\t0x%02x 0x%02x\n", cond, retry);
+       init->offset += 3;
+
+       if (!init_exec(init))
+               return;
+
+       while (wait--) {
+               if (init_condition_met(init, cond))
+                       return;
+               mdelay(20);
+       }
+
+       init_exec_set(init, false);
+}
+
+/**
+ * INIT_LTIME - opcode 0x57
+ *
+ */
+static void
+init_ltime(struct nvbios_init *init)
+{
+       struct nvkm_bios *bios = init->bios;
+       u16 msec = nv_ro16(bios, init->offset + 1);
+
+       trace("LTIME\t0x%04x\n", msec);
+       init->offset += 3;
+
+       if (init_exec(init))
+               mdelay(msec);
+}
+
+/**
+ * INIT_ZM_REG_SEQUENCE - opcode 0x58
+ *
+ */
+static void
+init_zm_reg_sequence(struct nvbios_init *init)
+{
+       struct nvkm_bios *bios = init->bios;
+       u32 base = nv_ro32(bios, init->offset + 1);
+       u8 count = nv_ro08(bios, init->offset + 5);
+
+       trace("ZM_REG_SEQUENCE\t0x%02x\n", count);
+       init->offset += 6;
+
+       while (count--) {
+               u32 data = nv_ro32(bios, init->offset);
+
+               trace("\t\tR[0x%06x] = 0x%08x\n", base, data);
+               init->offset += 4;
+
+               init_wr32(init, base, data);
+               base += 4;
+       }
+}
+
+/**
+ * INIT_SUB_DIRECT - opcode 0x5b
+ *
+ */
+static void
+init_sub_direct(struct nvbios_init *init)
+{
+       struct nvkm_bios *bios = init->bios;
+       u16 addr = nv_ro16(bios, init->offset + 1);
+       u16 save;
+
+       trace("SUB_DIRECT\t0x%04x\n", addr);
+
+       if (init_exec(init)) {
+               save = init->offset;
+               init->offset = addr;
+               if (nvbios_exec(init)) {
+                       error("error parsing sub-table\n");
+                       return;
+               }
+               init->offset = save;
+       }
+
+       init->offset += 3;
+}
+
+/**
+ * INIT_JUMP - opcode 0x5c
+ *
+ */
+static void
+init_jump(struct nvbios_init *init)
+{
+       struct nvkm_bios *bios = init->bios;
+       u16 offset = nv_ro16(bios, init->offset + 1);
+
+       trace("JUMP\t0x%04x\n", offset);
+
+       if (init_exec(init))
+               init->offset = offset;
+       else
+               init->offset += 3;
+}
+
+/**
+ * INIT_I2C_IF - opcode 0x5e
+ *
+ */
+static void
+init_i2c_if(struct nvbios_init *init)
+{
+       struct nvkm_bios *bios = init->bios;
+       u8 index = nv_ro08(bios, init->offset + 1);
+       u8  addr = nv_ro08(bios, init->offset + 2);
+       u8   reg = nv_ro08(bios, init->offset + 3);
+       u8  mask = nv_ro08(bios, init->offset + 4);
+       u8  data = nv_ro08(bios, init->offset + 5);
+       u8 value;
+
+       trace("I2C_IF\tI2C[0x%02x][0x%02x][0x%02x] & 0x%02x == 0x%02x\n",
+             index, addr, reg, mask, data);
+       init->offset += 6;
+       init_exec_force(init, true);
+
+       value = init_rdi2cr(init, index, addr, reg);
+       if ((value & mask) != data)
+               init_exec_set(init, false);
+
+       init_exec_force(init, false);
+}
+
+/**
+ * INIT_COPY_NV_REG - opcode 0x5f
+ *
+ */
+static void
+init_copy_nv_reg(struct nvbios_init *init)
+{
+       struct nvkm_bios *bios = init->bios;
+       u32  sreg = nv_ro32(bios, init->offset + 1);
+       u8  shift = nv_ro08(bios, init->offset + 5);
+       u32 smask = nv_ro32(bios, init->offset + 6);
+       u32  sxor = nv_ro32(bios, init->offset + 10);
+       u32  dreg = nv_ro32(bios, init->offset + 14);
+       u32 dmask = nv_ro32(bios, init->offset + 18);
+       u32 data;
+
+       trace("COPY_NV_REG\tR[0x%06x] &= 0x%08x |= "
+             "((R[0x%06x] %s 0x%02x) & 0x%08x ^ 0x%08x)\n",
+             dreg, dmask, sreg, (shift & 0x80) ? "<<" : ">>",
+             (shift & 0x80) ? (0x100 - shift) : shift, smask, sxor);
+       init->offset += 22;
+
+       data = init_shift(init_rd32(init, sreg), shift);
+       init_mask(init, dreg, ~dmask, (data & smask) ^ sxor);
+}
+
+/**
+ * INIT_ZM_INDEX_IO - opcode 0x62
+ *
+ */
+static void
+init_zm_index_io(struct nvbios_init *init)
+{
+       struct nvkm_bios *bios = init->bios;
+       u16 port = nv_ro16(bios, init->offset + 1);
+       u8 index = nv_ro08(bios, init->offset + 3);
+       u8  data = nv_ro08(bios, init->offset + 4);
+
+       trace("ZM_INDEX_IO\tI[0x%04x][0x%02x] = 0x%02x\n", port, index, data);
+       init->offset += 5;
+
+       init_wrvgai(init, port, index, data);
+}
+
+/**
+ * INIT_COMPUTE_MEM - opcode 0x63
+ *
+ */
+static void
+init_compute_mem(struct nvbios_init *init)
+{
+       struct nvkm_devinit *devinit = nvkm_devinit(init->bios);
+
+       trace("COMPUTE_MEM\n");
+       init->offset += 1;
+
+       init_exec_force(init, true);
+       if (init_exec(init) && devinit->meminit)
+               devinit->meminit(devinit);
+       init_exec_force(init, false);
+}
+
+/**
+ * INIT_RESET - opcode 0x65
+ *
+ */
+static void
+init_reset(struct nvbios_init *init)
+{
+       struct nvkm_bios *bios = init->bios;
+       u32   reg = nv_ro32(bios, init->offset + 1);
+       u32 data1 = nv_ro32(bios, init->offset + 5);
+       u32 data2 = nv_ro32(bios, init->offset + 9);
+       u32 savepci19;
+
+       trace("RESET\tR[0x%08x] = 0x%08x, 0x%08x", reg, data1, data2);
+       init->offset += 13;
+       init_exec_force(init, true);
+
+       savepci19 = init_mask(init, 0x00184c, 0x00000f00, 0x00000000);
+       init_wr32(init, reg, data1);
+       udelay(10);
+       init_wr32(init, reg, data2);
+       init_wr32(init, 0x00184c, savepci19);
+       init_mask(init, 0x001850, 0x00000001, 0x00000000);
+
+       init_exec_force(init, false);
+}
+
+/**
+ * INIT_CONFIGURE_MEM - opcode 0x66
+ *
+ */
+static u16
+init_configure_mem_clk(struct nvbios_init *init)
+{
+       u16 mdata = bmp_mem_init_table(init->bios);
+       if (mdata)
+               mdata += (init_rdvgai(init, 0x03d4, 0x3c) >> 4) * 66;
+       return mdata;
+}
+
+static void
+init_configure_mem(struct nvbios_init *init)
+{
+       struct nvkm_bios *bios = init->bios;
+       u16 mdata, sdata;
+       u32 addr, data;
+
+       trace("CONFIGURE_MEM\n");
+       init->offset += 1;
+
+       if (bios->version.major > 2) {
+               init_done(init);
+               return;
+       }
+       init_exec_force(init, true);
+
+       mdata = init_configure_mem_clk(init);
+       sdata = bmp_sdr_seq_table(bios);
+       if (nv_ro08(bios, mdata) & 0x01)
+               sdata = bmp_ddr_seq_table(bios);
+       mdata += 6; /* skip to data */
+
+       data = init_rdvgai(init, 0x03c4, 0x01);
+       init_wrvgai(init, 0x03c4, 0x01, data | 0x20);
+
+       for (; (addr = nv_ro32(bios, sdata)) != 0xffffffff; sdata += 4) {
+               switch (addr) {
+               case 0x10021c: /* CKE_NORMAL */
+               case 0x1002d0: /* CMD_REFRESH */
+               case 0x1002d4: /* CMD_PRECHARGE */
+                       data = 0x00000001;
+                       break;
+               default:
+                       data = nv_ro32(bios, mdata);
+                       mdata += 4;
+                       if (data == 0xffffffff)
+                               continue;
+                       break;
+               }
+
+               init_wr32(init, addr, data);
+       }
+
+       init_exec_force(init, false);
+}
+
+/**
+ * INIT_CONFIGURE_CLK - opcode 0x67
+ *
+ */
+static void
+init_configure_clk(struct nvbios_init *init)
+{
+       struct nvkm_bios *bios = init->bios;
+       u16 mdata, clock;
+
+       trace("CONFIGURE_CLK\n");
+       init->offset += 1;
+
+       if (bios->version.major > 2) {
+               init_done(init);
+               return;
+       }
+       init_exec_force(init, true);
+
+       mdata = init_configure_mem_clk(init);
+
+       /* NVPLL */
+       clock = nv_ro16(bios, mdata + 4) * 10;
+       init_prog_pll(init, 0x680500, clock);
+
+       /* MPLL */
+       clock = nv_ro16(bios, mdata + 2) * 10;
+       if (nv_ro08(bios, mdata) & 0x01)
+               clock *= 2;
+       init_prog_pll(init, 0x680504, clock);
+
+       init_exec_force(init, false);
+}
+
+/**
+ * INIT_CONFIGURE_PREINIT - opcode 0x68
+ *
+ */
+static void
+init_configure_preinit(struct nvbios_init *init)
+{
+       struct nvkm_bios *bios = init->bios;
+       u32 strap;
+
+       trace("CONFIGURE_PREINIT\n");
+       init->offset += 1;
+
+       if (bios->version.major > 2) {
+               init_done(init);
+               return;
+       }
+       init_exec_force(init, true);
+
+       strap = init_rd32(init, 0x101000);
+       strap = ((strap << 2) & 0xf0) | ((strap & 0x40) >> 6);
+       init_wrvgai(init, 0x03d4, 0x3c, strap);
+
+       init_exec_force(init, false);
+}
+
+/**
+ * INIT_IO - opcode 0x69
+ *
+ */
+static void
+init_io(struct nvbios_init *init)
+{
+       struct nvkm_bios *bios = init->bios;
+       u16 port = nv_ro16(bios, init->offset + 1);
+       u8  mask = nv_ro16(bios, init->offset + 3);
+       u8  data = nv_ro16(bios, init->offset + 4);
+       u8 value;
+
+       trace("IO\t\tI[0x%04x] &= 0x%02x |= 0x%02x\n", port, mask, data);
+       init->offset += 5;
+
+       /* ummm.. yes.. should really figure out wtf this is and why it's
+        * needed some day..  it's almost certainly wrong, but, it also
+        * somehow makes things work...
+        */
+       if (nv_device(init->bios)->card_type >= NV_50 &&
+           port == 0x03c3 && data == 0x01) {
+               init_mask(init, 0x614100, 0xf0800000, 0x00800000);
+               init_mask(init, 0x00e18c, 0x00020000, 0x00020000);
+               init_mask(init, 0x614900, 0xf0800000, 0x00800000);
+               init_mask(init, 0x000200, 0x40000000, 0x00000000);
+               mdelay(10);
+               init_mask(init, 0x00e18c, 0x00020000, 0x00000000);
+               init_mask(init, 0x000200, 0x40000000, 0x40000000);
+               init_wr32(init, 0x614100, 0x00800018);
+               init_wr32(init, 0x614900, 0x00800018);
+               mdelay(10);
+               init_wr32(init, 0x614100, 0x10000018);
+               init_wr32(init, 0x614900, 0x10000018);
+       }
+
+       value = init_rdport(init, port) & mask;
+       init_wrport(init, port, data | value);
+}
+
+/**
+ * INIT_SUB - opcode 0x6b
+ *
+ */
+static void
+init_sub(struct nvbios_init *init)
+{
+       struct nvkm_bios *bios = init->bios;
+       u8 index = nv_ro08(bios, init->offset + 1);
+       u16 addr, save;
+
+       trace("SUB\t0x%02x\n", index);
+
+       addr = init_script(bios, index);
+       if (addr && init_exec(init)) {
+               save = init->offset;
+               init->offset = addr;
+               if (nvbios_exec(init)) {
+                       error("error parsing sub-table\n");
+                       return;
+               }
+               init->offset = save;
+       }
+
+       init->offset += 2;
+}
+
+/**
+ * INIT_RAM_CONDITION - opcode 0x6d
+ *
+ */
+static void
+init_ram_condition(struct nvbios_init *init)
+{
+       struct nvkm_bios *bios = init->bios;
+       u8  mask = nv_ro08(bios, init->offset + 1);
+       u8 value = nv_ro08(bios, init->offset + 2);
+
+       trace("RAM_CONDITION\t"
+             "(R[0x100000] & 0x%02x) == 0x%02x\n", mask, value);
+       init->offset += 3;
+
+       if ((init_rd32(init, 0x100000) & mask) != value)
+               init_exec_set(init, false);
+}
+
+/**
+ * INIT_NV_REG - opcode 0x6e
+ *
+ */
+static void
+init_nv_reg(struct nvbios_init *init)
+{
+       struct nvkm_bios *bios = init->bios;
+       u32  reg = nv_ro32(bios, init->offset + 1);
+       u32 mask = nv_ro32(bios, init->offset + 5);
+       u32 data = nv_ro32(bios, init->offset + 9);
+
+       trace("NV_REG\tR[0x%06x] &= 0x%08x |= 0x%08x\n", reg, mask, data);
+       init->offset += 13;
+
+       init_mask(init, reg, ~mask, data);
+}
+
+/**
+ * INIT_MACRO - opcode 0x6f
+ *
+ */
+static void
+init_macro(struct nvbios_init *init)
+{
+       struct nvkm_bios *bios = init->bios;
+       u8  macro = nv_ro08(bios, init->offset + 1);
+       u16 table;
+
+       trace("MACRO\t0x%02x\n", macro);
+
+       table = init_macro_table(init);
+       if (table) {
+               u32 addr = nv_ro32(bios, table + (macro * 8) + 0);
+               u32 data = nv_ro32(bios, table + (macro * 8) + 4);
+               trace("\t\tR[0x%06x] = 0x%08x\n", addr, data);
+               init_wr32(init, addr, data);
+       }
+
+       init->offset += 2;
+}
+
+/**
+ * INIT_RESUME - opcode 0x72
+ *
+ */
+static void
+init_resume(struct nvbios_init *init)
+{
+       trace("RESUME\n");
+       init->offset += 1;
+       init_exec_set(init, true);
+}
+
+/**
+ * INIT_TIME - opcode 0x74
+ *
+ */
+static void
+init_time(struct nvbios_init *init)
+{
+       struct nvkm_bios *bios = init->bios;
+       u16 usec = nv_ro16(bios, init->offset + 1);
+
+       trace("TIME\t0x%04x\n", usec);
+       init->offset += 3;
+
+       if (init_exec(init)) {
+               if (usec < 1000)
+                       udelay(usec);
+               else
+                       mdelay((usec + 900) / 1000);
+       }
+}
+
+/**
+ * INIT_CONDITION - opcode 0x75
+ *
+ */
+static void
+init_condition(struct nvbios_init *init)
+{
+       struct nvkm_bios *bios = init->bios;
+       u8 cond = nv_ro08(bios, init->offset + 1);
+
+       trace("CONDITION\t0x%02x\n", cond);
+       init->offset += 2;
+
+       if (!init_condition_met(init, cond))
+               init_exec_set(init, false);
+}
+
+/**
+ * INIT_IO_CONDITION - opcode 0x76
+ *
+ */
+static void
+init_io_condition(struct nvbios_init *init)
+{
+       struct nvkm_bios *bios = init->bios;
+       u8 cond = nv_ro08(bios, init->offset + 1);
+
+       trace("IO_CONDITION\t0x%02x\n", cond);
+       init->offset += 2;
+
+       if (!init_io_condition_met(init, cond))
+               init_exec_set(init, false);
+}
+
+/**
+ * INIT_INDEX_IO - opcode 0x78
+ *
+ */
+static void
+init_index_io(struct nvbios_init *init)
+{
+       struct nvkm_bios *bios = init->bios;
+       u16 port = nv_ro16(bios, init->offset + 1);
+       u8 index = nv_ro16(bios, init->offset + 3);
+       u8  mask = nv_ro08(bios, init->offset + 4);
+       u8  data = nv_ro08(bios, init->offset + 5);
+       u8 value;
+
+       trace("INDEX_IO\tI[0x%04x][0x%02x] &= 0x%02x |= 0x%02x\n",
+             port, index, mask, data);
+       init->offset += 6;
+
+       value = init_rdvgai(init, port, index) & mask;
+       init_wrvgai(init, port, index, data | value);
+}
+
+/**
+ * INIT_PLL - opcode 0x79
+ *
+ */
+static void
+init_pll(struct nvbios_init *init)
+{
+       struct nvkm_bios *bios = init->bios;
+       u32  reg = nv_ro32(bios, init->offset + 1);
+       u32 freq = nv_ro16(bios, init->offset + 5) * 10;
+
+       trace("PLL\tR[0x%06x] =PLL= %dkHz\n", reg, freq);
+       init->offset += 7;
+
+       init_prog_pll(init, reg, freq);
+}
+
+/**
+ * INIT_ZM_REG - opcode 0x7a
+ *
+ */
+static void
+init_zm_reg(struct nvbios_init *init)
+{
+       struct nvkm_bios *bios = init->bios;
+       u32 addr = nv_ro32(bios, init->offset + 1);
+       u32 data = nv_ro32(bios, init->offset + 5);
+
+       trace("ZM_REG\tR[0x%06x] = 0x%08x\n", addr, data);
+       init->offset += 9;
+
+       if (addr == 0x000200)
+               data |= 0x00000001;
+
+       init_wr32(init, addr, data);
+}
+
+/**
+ * INIT_RAM_RESTRICT_PLL - opcde 0x87
+ *
+ */
+static void
+init_ram_restrict_pll(struct nvbios_init *init)
+{
+       struct nvkm_bios *bios = init->bios;
+       u8  type = nv_ro08(bios, init->offset + 1);
+       u8 count = init_ram_restrict_group_count(init);
+       u8 strap = init_ram_restrict(init);
+       u8 cconf;
+
+       trace("RAM_RESTRICT_PLL\t0x%02x\n", type);
+       init->offset += 2;
+
+       for (cconf = 0; cconf < count; cconf++) {
+               u32 freq = nv_ro32(bios, init->offset);
+
+               if (cconf == strap) {
+                       trace("%dkHz *\n", freq);
+                       init_prog_pll(init, type, freq);
+               } else {
+                       trace("%dkHz\n", freq);
+               }
+
+               init->offset += 4;
+       }
+}
+
+/**
+ * INIT_GPIO - opcode 0x8e
+ *
+ */
+static void
+init_gpio(struct nvbios_init *init)
+{
+       struct nvkm_gpio *gpio = nvkm_gpio(init->bios);
+
+       trace("GPIO\n");
+       init->offset += 1;
+
+       if (init_exec(init) && gpio && gpio->reset)
+               gpio->reset(gpio, DCB_GPIO_UNUSED);
+}
+
+/**
+ * INIT_RAM_RESTRICT_ZM_GROUP - opcode 0x8f
+ *
+ */
+static void
+init_ram_restrict_zm_reg_group(struct nvbios_init *init)
+{
+       struct nvkm_bios *bios = init->bios;
+       u32 addr = nv_ro32(bios, init->offset + 1);
+       u8  incr = nv_ro08(bios, init->offset + 5);
+       u8   num = nv_ro08(bios, init->offset + 6);
+       u8 count = init_ram_restrict_group_count(init);
+       u8 index = init_ram_restrict(init);
+       u8 i, j;
+
+       trace("RAM_RESTRICT_ZM_REG_GROUP\t"
+             "R[0x%08x] 0x%02x 0x%02x\n", addr, incr, num);
+       init->offset += 7;
+
+       for (i = 0; i < num; i++) {
+               trace("\tR[0x%06x] = {\n", addr);
+               for (j = 0; j < count; j++) {
+                       u32 data = nv_ro32(bios, init->offset);
+
+                       if (j == index) {
+                               trace("\t\t0x%08x *\n", data);
+                               init_wr32(init, addr, data);
+                       } else {
+                               trace("\t\t0x%08x\n", data);
+                       }
+
+                       init->offset += 4;
+               }
+               trace("\t}\n");
+               addr += incr;
+       }
+}
+
+/**
+ * INIT_COPY_ZM_REG - opcode 0x90
+ *
+ */
+static void
+init_copy_zm_reg(struct nvbios_init *init)
+{
+       struct nvkm_bios *bios = init->bios;
+       u32 sreg = nv_ro32(bios, init->offset + 1);
+       u32 dreg = nv_ro32(bios, init->offset + 5);
+
+       trace("COPY_ZM_REG\tR[0x%06x] = R[0x%06x]\n", dreg, sreg);
+       init->offset += 9;
+
+       init_wr32(init, dreg, init_rd32(init, sreg));
+}
+
+/**
+ * INIT_ZM_REG_GROUP - opcode 0x91
+ *
+ */
+static void
+init_zm_reg_group(struct nvbios_init *init)
+{
+       struct nvkm_bios *bios = init->bios;
+       u32 addr = nv_ro32(bios, init->offset + 1);
+       u8 count = nv_ro08(bios, init->offset + 5);
+
+       trace("ZM_REG_GROUP\tR[0x%06x] =\n", addr);
+       init->offset += 6;
+
+       while (count--) {
+               u32 data = nv_ro32(bios, init->offset);
+               trace("\t0x%08x\n", data);
+               init_wr32(init, addr, data);
+               init->offset += 4;
+       }
+}
+
+/**
+ * INIT_XLAT - opcode 0x96
+ *
+ */
+static void
+init_xlat(struct nvbios_init *init)
+{
+       struct nvkm_bios *bios = init->bios;
+       u32 saddr = nv_ro32(bios, init->offset + 1);
+       u8 sshift = nv_ro08(bios, init->offset + 5);
+       u8  smask = nv_ro08(bios, init->offset + 6);
+       u8  index = nv_ro08(bios, init->offset + 7);
+       u32 daddr = nv_ro32(bios, init->offset + 8);
+       u32 dmask = nv_ro32(bios, init->offset + 12);
+       u8  shift = nv_ro08(bios, init->offset + 16);
+       u32 data;
+
+       trace("INIT_XLAT\tR[0x%06x] &= 0x%08x |= "
+             "(X%02x((R[0x%06x] %s 0x%02x) & 0x%02x) << 0x%02x)\n",
+             daddr, dmask, index, saddr, (sshift & 0x80) ? "<<" : ">>",
+             (sshift & 0x80) ? (0x100 - sshift) : sshift, smask, shift);
+       init->offset += 17;
+
+       data = init_shift(init_rd32(init, saddr), sshift) & smask;
+       data = init_xlat_(init, index, data) << shift;
+       init_mask(init, daddr, ~dmask, data);
+}
+
+/**
+ * INIT_ZM_MASK_ADD - opcode 0x97
+ *
+ */
+static void
+init_zm_mask_add(struct nvbios_init *init)
+{
+       struct nvkm_bios *bios = init->bios;
+       u32 addr = nv_ro32(bios, init->offset + 1);
+       u32 mask = nv_ro32(bios, init->offset + 5);
+       u32  add = nv_ro32(bios, init->offset + 9);
+       u32 data;
+
+       trace("ZM_MASK_ADD\tR[0x%06x] &= 0x%08x += 0x%08x\n", addr, mask, add);
+       init->offset += 13;
+
+       data =  init_rd32(init, addr);
+       data = (data & mask) | ((data + add) & ~mask);
+       init_wr32(init, addr, data);
+}
+
+/**
+ * INIT_AUXCH - opcode 0x98
+ *
+ */
+static void
+init_auxch(struct nvbios_init *init)
+{
+       struct nvkm_bios *bios = init->bios;
+       u32 addr = nv_ro32(bios, init->offset + 1);
+       u8 count = nv_ro08(bios, init->offset + 5);
+
+       trace("AUXCH\tAUX[0x%08x] 0x%02x\n", addr, count);
+       init->offset += 6;
+
+       while (count--) {
+               u8 mask = nv_ro08(bios, init->offset + 0);
+               u8 data = nv_ro08(bios, init->offset + 1);
+               trace("\tAUX[0x%08x] &= 0x%02x |= 0x%02x\n", addr, mask, data);
+               mask = init_rdauxr(init, addr) & mask;
+               init_wrauxr(init, addr, mask | data);
+               init->offset += 2;
+       }
+}
+
+/**
+ * INIT_AUXCH - opcode 0x99
+ *
+ */
+static void
+init_zm_auxch(struct nvbios_init *init)
+{
+       struct nvkm_bios *bios = init->bios;
+       u32 addr = nv_ro32(bios, init->offset + 1);
+       u8 count = nv_ro08(bios, init->offset + 5);
+
+       trace("ZM_AUXCH\tAUX[0x%08x] 0x%02x\n", addr, count);
+       init->offset += 6;
+
+       while (count--) {
+               u8 data = nv_ro08(bios, init->offset + 0);
+               trace("\tAUX[0x%08x] = 0x%02x\n", addr, data);
+               init_wrauxr(init, addr, data);
+               init->offset += 1;
+       }
+}
+
+/**
+ * INIT_I2C_LONG_IF - opcode 0x9a
+ *
+ */
+static void
+init_i2c_long_if(struct nvbios_init *init)
+{
+       struct nvkm_bios *bios = init->bios;
+       u8 index = nv_ro08(bios, init->offset + 1);
+       u8  addr = nv_ro08(bios, init->offset + 2) >> 1;
+       u8 reglo = nv_ro08(bios, init->offset + 3);
+       u8 reghi = nv_ro08(bios, init->offset + 4);
+       u8  mask = nv_ro08(bios, init->offset + 5);
+       u8  data = nv_ro08(bios, init->offset + 6);
+       struct nvkm_i2c_port *port;
+
+       trace("I2C_LONG_IF\t"
+             "I2C[0x%02x][0x%02x][0x%02x%02x] & 0x%02x == 0x%02x\n",
+             index, addr, reglo, reghi, mask, data);
+       init->offset += 7;
+
+       port = init_i2c(init, index);
+       if (port) {
+               u8 i[2] = { reghi, reglo };
+               u8 o[1] = {};
+               struct i2c_msg msg[] = {
+                       { .addr = addr, .flags = 0, .len = 2, .buf = i },
+                       { .addr = addr, .flags = I2C_M_RD, .len = 1, .buf = o }
+               };
+               int ret;
+
+               ret = i2c_transfer(&port->adapter, msg, 2);
+               if (ret == 2 && ((o[0] & mask) == data))
+                       return;
+       }
+
+       init_exec_set(init, false);
+}
+
+/**
+ * INIT_GPIO_NE - opcode 0xa9
+ *
+ */
+static void
+init_gpio_ne(struct nvbios_init *init)
+{
+       struct nvkm_bios *bios = init->bios;
+       struct nvkm_gpio *gpio = nvkm_gpio(bios);
+       struct dcb_gpio_func func;
+       u8 count = nv_ro08(bios, init->offset + 1);
+       u8 idx = 0, ver, len;
+       u16 data, i;
+
+       trace("GPIO_NE\t");
+       init->offset += 2;
+
+       for (i = init->offset; i < init->offset + count; i++)
+               cont("0x%02x ", nv_ro08(bios, i));
+       cont("\n");
+
+       while ((data = dcb_gpio_parse(bios, 0, idx++, &ver, &len, &func))) {
+               if (func.func != DCB_GPIO_UNUSED) {
+                       for (i = init->offset; i < init->offset + count; i++) {
+                               if (func.func == nv_ro08(bios, i))
+                                       break;
+                       }
+
+                       trace("\tFUNC[0x%02x]", func.func);
+                       if (i == (init->offset + count)) {
+                               cont(" *");
+                               if (init_exec(init) && gpio && gpio->reset)
+                                       gpio->reset(gpio, func.func);
+                       }
+                       cont("\n");
+               }
+       }
+
+       init->offset += count;
+}
+
+static struct nvbios_init_opcode {
+       void (*exec)(struct nvbios_init *);
+} init_opcode[] = {
+       [0x32] = { init_io_restrict_prog },
+       [0x33] = { init_repeat },
+       [0x34] = { init_io_restrict_pll },
+       [0x36] = { init_end_repeat },
+       [0x37] = { init_copy },
+       [0x38] = { init_not },
+       [0x39] = { init_io_flag_condition },
+       [0x3a] = { init_dp_condition },
+       [0x3b] = { init_io_mask_or },
+       [0x3c] = { init_io_or },
+       [0x47] = { init_andn_reg },
+       [0x48] = { init_or_reg },
+       [0x49] = { init_idx_addr_latched },
+       [0x4a] = { init_io_restrict_pll2 },
+       [0x4b] = { init_pll2 },
+       [0x4c] = { init_i2c_byte },
+       [0x4d] = { init_zm_i2c_byte },
+       [0x4e] = { init_zm_i2c },
+       [0x4f] = { init_tmds },
+       [0x50] = { init_zm_tmds_group },
+       [0x51] = { init_cr_idx_adr_latch },
+       [0x52] = { init_cr },
+       [0x53] = { init_zm_cr },
+       [0x54] = { init_zm_cr_group },
+       [0x56] = { init_condition_time },
+       [0x57] = { init_ltime },
+       [0x58] = { init_zm_reg_sequence },
+       [0x5b] = { init_sub_direct },
+       [0x5c] = { init_jump },
+       [0x5e] = { init_i2c_if },
+       [0x5f] = { init_copy_nv_reg },
+       [0x62] = { init_zm_index_io },
+       [0x63] = { init_compute_mem },
+       [0x65] = { init_reset },
+       [0x66] = { init_configure_mem },
+       [0x67] = { init_configure_clk },
+       [0x68] = { init_configure_preinit },
+       [0x69] = { init_io },
+       [0x6b] = { init_sub },
+       [0x6d] = { init_ram_condition },
+       [0x6e] = { init_nv_reg },
+       [0x6f] = { init_macro },
+       [0x71] = { init_done },
+       [0x72] = { init_resume },
+       [0x74] = { init_time },
+       [0x75] = { init_condition },
+       [0x76] = { init_io_condition },
+       [0x78] = { init_index_io },
+       [0x79] = { init_pll },
+       [0x7a] = { init_zm_reg },
+       [0x87] = { init_ram_restrict_pll },
+       [0x8c] = { init_reserved },
+       [0x8d] = { init_reserved },
+       [0x8e] = { init_gpio },
+       [0x8f] = { init_ram_restrict_zm_reg_group },
+       [0x90] = { init_copy_zm_reg },
+       [0x91] = { init_zm_reg_group },
+       [0x92] = { init_reserved },
+       [0x96] = { init_xlat },
+       [0x97] = { init_zm_mask_add },
+       [0x98] = { init_auxch },
+       [0x99] = { init_zm_auxch },
+       [0x9a] = { init_i2c_long_if },
+       [0xa9] = { init_gpio_ne },
+       [0xaa] = { init_reserved },
+};
+
+#define init_opcode_nr (sizeof(init_opcode) / sizeof(init_opcode[0]))
+
+int
+nvbios_exec(struct nvbios_init *init)
+{
+       init->nested++;
+       while (init->offset) {
+               u8 opcode = nv_ro08(init->bios, init->offset);
+               if (opcode >= init_opcode_nr || !init_opcode[opcode].exec) {
+                       error("unknown opcode 0x%02x\n", opcode);
+                       return -EINVAL;
+               }
+
+               init_opcode[opcode].exec(init);
+       }
+       init->nested--;
+       return 0;
+}
+
+int
+nvbios_init(struct nvkm_subdev *subdev, bool execute)
+{
+       struct nvkm_bios *bios = nvkm_bios(subdev);
+       int ret = 0;
+       int i = -1;
+       u16 data;
+
+       if (execute)
+               nv_info(bios, "running init tables\n");
+       while (!ret && (data = (init_script(bios, ++i)))) {
+               struct nvbios_init init = {
+                       .subdev = subdev,
+                       .bios = bios,
+                       .offset = data,
+                       .outp = NULL,
+                       .crtc = -1,
+                       .execute = execute ? 1 : 0,
+               };
+
+               ret = nvbios_exec(&init);
+       }
+
+       /* the vbios parser will run this right after the normal init
+        * tables, whereas the binary driver appears to run it later.
+        */
+       if (!ret && (data = init_unknown_script(bios))) {
+               struct nvbios_init init = {
+                       .subdev = subdev,
+                       .bios = bios,
+                       .offset = data,
+                       .outp = NULL,
+                       .crtc = -1,
+                       .execute = execute ? 1 : 0,
+               };
+
+               ret = nvbios_exec(&init);
+       }
+
+       return ret;
+}
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/bios/mxm.c b/drivers/gpu/drm/nouveau/nvkm/subdev/bios/mxm.c
new file mode 100644 (file)
index 0000000..c4087df
--- /dev/null
@@ -0,0 +1,134 @@
+/*
+ * Copyright 2012 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 <subdev/bios.h>
+#include <subdev/bios/bit.h>
+#include <subdev/bios/mxm.h>
+
+u16
+mxm_table(struct nvkm_bios *bios, u8 *ver, u8 *hdr)
+{
+       struct bit_entry x;
+
+       if (bit_entry(bios, 'x', &x)) {
+               nv_debug(bios, "BIT 'x' table not present\n");
+               return 0x0000;
+       }
+
+       *ver = x.version;
+       *hdr = x.length;
+       if (*ver != 1 || *hdr < 3) {
+               nv_warn(bios, "BIT 'x' table %d/%d unknown\n", *ver, *hdr);
+               return 0x0000;
+       }
+
+       return x.offset;
+}
+
+/* These map MXM v2.x digital connection values to the appropriate SOR/link,
+ * hopefully they're correct for all boards within the same chipset...
+ *
+ * MXM v3.x VBIOS are nicer and provide pointers to these tables.
+ */
+static u8 g84_sor_map[16] = {
+       0x00, 0x12, 0x22, 0x11, 0x32, 0x31, 0x11, 0x31,
+       0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00
+};
+
+static u8 g92_sor_map[16] = {
+       0x00, 0x12, 0x22, 0x11, 0x32, 0x31, 0x11, 0x31,
+       0x11, 0x31, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00
+};
+
+static u8 g94_sor_map[16] = {
+       0x00, 0x14, 0x24, 0x11, 0x34, 0x31, 0x11, 0x31,
+       0x11, 0x31, 0x12, 0x00, 0x00, 0x00, 0x00, 0x00
+};
+
+static u8 g98_sor_map[16] = {
+       0x00, 0x14, 0x12, 0x11, 0x00, 0x31, 0x11, 0x31,
+       0x11, 0x31, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00
+};
+
+u8
+mxm_sor_map(struct nvkm_bios *bios, u8 conn)
+{
+       u8  ver, hdr;
+       u16 mxm = mxm_table(bios, &ver, &hdr);
+       if (mxm && hdr >= 6) {
+               u16 map = nv_ro16(bios, mxm + 4);
+               if (map) {
+                       ver = nv_ro08(bios, map);
+                       if (ver == 0x10) {
+                               if (conn < nv_ro08(bios, map + 3)) {
+                                       map += nv_ro08(bios, map + 1);
+                                       map += conn;
+                                       return nv_ro08(bios, map);
+                               }
+
+                               return 0x00;
+                       }
+
+                       nv_warn(bios, "unknown sor map v%02x\n", ver);
+               }
+       }
+
+       if (bios->version.chip == 0x84 || bios->version.chip == 0x86)
+               return g84_sor_map[conn];
+       if (bios->version.chip == 0x92)
+               return g92_sor_map[conn];
+       if (bios->version.chip == 0x94 || bios->version.chip == 0x96)
+               return g94_sor_map[conn];
+       if (bios->version.chip == 0x98)
+               return g98_sor_map[conn];
+
+       nv_warn(bios, "missing sor map\n");
+       return 0x00;
+}
+
+u8
+mxm_ddc_map(struct nvkm_bios *bios, u8 port)
+{
+       u8  ver, hdr;
+       u16 mxm = mxm_table(bios, &ver, &hdr);
+       if (mxm && hdr >= 8) {
+               u16 map = nv_ro16(bios, mxm + 6);
+               if (map) {
+                       ver = nv_ro08(bios, map);
+                       if (ver == 0x10) {
+                               if (port < nv_ro08(bios, map + 3)) {
+                                       map += nv_ro08(bios, map + 1);
+                                       map += port;
+                                       return nv_ro08(bios, map);
+                               }
+
+                               return 0x00;
+                       }
+
+                       nv_warn(bios, "unknown ddc map v%02x\n", ver);
+               }
+       }
+
+       /* v2.x: directly write port as dcb i2cidx */
+       return (port << 4) | port;
+}
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/bios/npde.c b/drivers/gpu/drm/nouveau/nvkm/subdev/bios/npde.c
new file mode 100644 (file)
index 0000000..fd7dd71
--- /dev/null
@@ -0,0 +1,58 @@
+/*
+ * Copyright 2014 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 <bskeggs@redhat.com>
+ */
+#include <subdev/bios.h>
+#include <subdev/bios/npde.h>
+#include <subdev/bios/pcir.h>
+
+u32
+nvbios_npdeTe(struct nvkm_bios *bios, u32 base)
+{
+       struct nvbios_pcirT pcir;
+       u8  ver; u16 hdr;
+       u32 data = nvbios_pcirTp(bios, base, &ver, &hdr, &pcir);
+       if (data = (data + hdr + 0x0f) & ~0x0f, data) {
+               switch (nv_ro32(bios, data + 0x00)) {
+               case 0x4544504e: /* NPDE */
+                       break;
+               default:
+                       nv_debug(bios, "%08x: NPDE signature (%08x) unknown\n",
+                                data, nv_ro32(bios, data + 0x00));
+                       data = 0;
+                       break;
+               }
+       }
+       return data;
+}
+
+u32
+nvbios_npdeTp(struct nvkm_bios *bios, u32 base, struct nvbios_npdeT *info)
+{
+       u32 data = nvbios_npdeTe(bios, base);
+       memset(info, 0x00, sizeof(*info));
+       if (data) {
+               info->image_size = nv_ro16(bios, data + 0x08) * 512;
+               info->last = nv_ro08(bios, data + 0x0a) & 0x80;
+       }
+       return data;
+}
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/bios/pcir.c b/drivers/gpu/drm/nouveau/nvkm/subdev/bios/pcir.c
new file mode 100644 (file)
index 0000000..df59787
--- /dev/null
@@ -0,0 +1,68 @@
+/*
+ * Copyright 2014 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 <bskeggs@redhat.com>
+ */
+#include <subdev/bios.h>
+#include <subdev/bios/pcir.h>
+
+u32
+nvbios_pcirTe(struct nvkm_bios *bios, u32 base, u8 *ver, u16 *hdr)
+{
+       u32 data = nv_ro16(bios, base + 0x18);
+       if (data) {
+               data += base;
+               switch (nv_ro32(bios, data + 0x00)) {
+               case 0x52494350: /* PCIR */
+               case 0x53494752: /* RGIS */
+               case 0x5344504e: /* NPDS */
+                       *hdr = nv_ro16(bios, data + 0x0a);
+                       *ver = nv_ro08(bios, data + 0x0c);
+                       break;
+               default:
+                       nv_debug(bios, "%08x: PCIR signature (%08x) unknown\n",
+                                data, nv_ro32(bios, data + 0x00));
+                       data = 0;
+                       break;
+               }
+       }
+       return data;
+}
+
+u32
+nvbios_pcirTp(struct nvkm_bios *bios, u32 base, u8 *ver, u16 *hdr,
+             struct nvbios_pcirT *info)
+{
+       u32 data = nvbios_pcirTe(bios, base, ver, hdr);
+       memset(info, 0x00, sizeof(*info));
+       if (data) {
+               info->vendor_id = nv_ro16(bios, data + 0x04);
+               info->device_id = nv_ro16(bios, data + 0x06);
+               info->class_code[0] = nv_ro08(bios, data + 0x0d);
+               info->class_code[1] = nv_ro08(bios, data + 0x0e);
+               info->class_code[2] = nv_ro08(bios, data + 0x0f);
+               info->image_size = nv_ro16(bios, data + 0x10) * 512;
+               info->image_rev = nv_ro16(bios, data + 0x12);
+               info->image_type = nv_ro08(bios, data + 0x14);
+               info->last = nv_ro08(bios, data + 0x15) & 0x80;
+       }
+       return data;
+}
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/bios/perf.c b/drivers/gpu/drm/nouveau/nvkm/subdev/bios/perf.c
new file mode 100644 (file)
index 0000000..382ae9c
--- /dev/null
@@ -0,0 +1,201 @@
+/*
+ * Copyright 2012 Nouveau Community
+ *
+ * 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 <subdev/bios.h>
+#include <subdev/bios/bit.h>
+#include <subdev/bios/perf.h>
+
+#include <core/device.h>
+
+u16
+nvbios_perf_table(struct nvkm_bios *bios, u8 *ver, u8 *hdr,
+                 u8 *cnt, u8 *len, u8 *snr, u8 *ssz)
+{
+       struct bit_entry bit_P;
+       u16 perf = 0x0000;
+
+       if (!bit_entry(bios, 'P', &bit_P)) {
+               if (bit_P.version <= 2) {
+                       perf = nv_ro16(bios, bit_P.offset + 0);
+                       if (perf) {
+                               *ver = nv_ro08(bios, perf + 0);
+                               *hdr = nv_ro08(bios, perf + 1);
+                               if (*ver >= 0x40 && *ver < 0x41) {
+                                       *cnt = nv_ro08(bios, perf + 5);
+                                       *len = nv_ro08(bios, perf + 2);
+                                       *snr = nv_ro08(bios, perf + 4);
+                                       *ssz = nv_ro08(bios, perf + 3);
+                                       return perf;
+                               } else
+                               if (*ver >= 0x20 && *ver < 0x40) {
+                                       *cnt = nv_ro08(bios, perf + 2);
+                                       *len = nv_ro08(bios, perf + 3);
+                                       *snr = nv_ro08(bios, perf + 4);
+                                       *ssz = nv_ro08(bios, perf + 5);
+                                       return perf;
+                               }
+                       }
+               }
+       }
+
+       if (bios->bmp_offset) {
+               if (nv_ro08(bios, bios->bmp_offset + 6) >= 0x25) {
+                       perf = nv_ro16(bios, bios->bmp_offset + 0x94);
+                       if (perf) {
+                               *hdr = nv_ro08(bios, perf + 0);
+                               *ver = nv_ro08(bios, perf + 1);
+                               *cnt = nv_ro08(bios, perf + 2);
+                               *len = nv_ro08(bios, perf + 3);
+                               *snr = 0;
+                               *ssz = 0;
+                               return perf;
+                       }
+               }
+       }
+
+       return 0x0000;
+}
+
+u16
+nvbios_perf_entry(struct nvkm_bios *bios, int idx,
+                 u8 *ver, u8 *hdr, u8 *cnt, u8 *len)
+{
+       u8  snr, ssz;
+       u16 perf = nvbios_perf_table(bios, ver, hdr, cnt, len, &snr, &ssz);
+       if (perf && idx < *cnt) {
+               perf = perf + *hdr + (idx * (*len + (snr * ssz)));
+               *hdr = *len;
+               *cnt = snr;
+               *len = ssz;
+               return perf;
+       }
+       return 0x0000;
+}
+
+u16
+nvbios_perfEp(struct nvkm_bios *bios, int idx,
+             u8 *ver, u8 *hdr, u8 *cnt, u8 *len, struct nvbios_perfE *info)
+{
+       u16 perf = nvbios_perf_entry(bios, idx, ver, hdr, cnt, len);
+       memset(info, 0x00, sizeof(*info));
+       info->pstate = nv_ro08(bios, perf + 0x00);
+       switch (!!perf * *ver) {
+       case 0x12:
+       case 0x13:
+       case 0x14:
+               info->core     = nv_ro32(bios, perf + 0x01) * 10;
+               info->memory   = nv_ro32(bios, perf + 0x05) * 20;
+               info->fanspeed = nv_ro08(bios, perf + 0x37);
+               if (*hdr > 0x38)
+                       info->voltage = nv_ro08(bios, perf + 0x38);
+               break;
+       case 0x21:
+       case 0x23:
+       case 0x24:
+               info->fanspeed = nv_ro08(bios, perf + 0x04);
+               info->voltage  = nv_ro08(bios, perf + 0x05);
+               info->shader   = nv_ro16(bios, perf + 0x06) * 1000;
+               info->core     = info->shader + (signed char)
+                                nv_ro08(bios, perf + 0x08) * 1000;
+               switch (nv_device(bios)->chipset) {
+               case 0x49:
+               case 0x4b:
+                       info->memory = nv_ro16(bios, perf + 0x0b) * 1000;
+                       break;
+               default:
+                       info->memory = nv_ro16(bios, perf + 0x0b) * 2000;
+                       break;
+               }
+               break;
+       case 0x25:
+               info->fanspeed = nv_ro08(bios, perf + 0x04);
+               info->voltage  = nv_ro08(bios, perf + 0x05);
+               info->core     = nv_ro16(bios, perf + 0x06) * 1000;
+               info->shader   = nv_ro16(bios, perf + 0x0a) * 1000;
+               info->memory   = nv_ro16(bios, perf + 0x0c) * 1000;
+               break;
+       case 0x30:
+               info->script   = nv_ro16(bios, perf + 0x02);
+       case 0x35:
+               info->fanspeed = nv_ro08(bios, perf + 0x06);
+               info->voltage  = nv_ro08(bios, perf + 0x07);
+               info->core     = nv_ro16(bios, perf + 0x08) * 1000;
+               info->shader   = nv_ro16(bios, perf + 0x0a) * 1000;
+               info->memory   = nv_ro16(bios, perf + 0x0c) * 1000;
+               info->vdec     = nv_ro16(bios, perf + 0x10) * 1000;
+               info->disp     = nv_ro16(bios, perf + 0x14) * 1000;
+               break;
+       case 0x40:
+               info->voltage  = nv_ro08(bios, perf + 0x02);
+               break;
+       default:
+               return 0x0000;
+       }
+       return perf;
+}
+
+u32
+nvbios_perfSe(struct nvkm_bios *bios, u32 perfE, int idx,
+             u8 *ver, u8 *hdr, u8 cnt, u8 len)
+{
+       u32 data = 0x00000000;
+       if (idx < cnt) {
+               data = perfE + *hdr + (idx * len);
+               *hdr = len;
+       }
+       return data;
+}
+
+u32
+nvbios_perfSp(struct nvkm_bios *bios, u32 perfE, int idx,
+             u8 *ver, u8 *hdr, u8 cnt, u8 len,
+             struct nvbios_perfS *info)
+{
+       u32 data = nvbios_perfSe(bios, perfE, idx, ver, hdr, cnt, len);
+       memset(info, 0x00, sizeof(*info));
+       switch (!!data * *ver) {
+       case 0x40:
+               info->v40.freq = (nv_ro16(bios, data + 0x00) & 0x3fff) * 1000;
+               break;
+       default:
+               break;
+       }
+       return data;
+}
+
+int
+nvbios_perf_fan_parse(struct nvkm_bios *bios,
+                     struct nvbios_perf_fan *fan)
+{
+       u8  ver, hdr, cnt, len, snr, ssz;
+       u16 perf = nvbios_perf_table(bios, &ver, &hdr, &cnt, &len, &snr, &ssz);
+       if (!perf)
+               return -ENODEV;
+
+       if (ver >= 0x20 && ver < 0x40 && hdr > 6)
+               fan->pwm_divisor = nv_ro16(bios, perf + 6);
+       else
+               fan->pwm_divisor = 0;
+
+       return 0;
+}
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/bios/pll.c b/drivers/gpu/drm/nouveau/nvkm/subdev/bios/pll.c
new file mode 100644 (file)
index 0000000..ebd402e
--- /dev/null
@@ -0,0 +1,417 @@
+/*
+ * 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.
+ */
+#include <subdev/bios.h>
+#include <subdev/bios/bit.h>
+#include <subdev/bios/bmp.h>
+#include <subdev/bios/pll.h>
+#include <subdev/vga.h>
+
+#include <core/device.h>
+
+struct pll_mapping {
+       u8  type;
+       u32 reg;
+};
+
+static struct pll_mapping
+nv04_pll_mapping[] = {
+       { PLL_CORE  , 0x680500 },
+       { PLL_MEMORY, 0x680504 },
+       { PLL_VPLL0 , 0x680508 },
+       { PLL_VPLL1 , 0x680520 },
+       {}
+};
+
+static struct pll_mapping
+nv40_pll_mapping[] = {
+       { PLL_CORE  , 0x004000 },
+       { PLL_MEMORY, 0x004020 },
+       { PLL_VPLL0 , 0x680508 },
+       { PLL_VPLL1 , 0x680520 },
+       {}
+};
+
+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
+g84_pll_mapping[] = {
+       { PLL_CORE  , 0x004028 },
+       { PLL_SHADER, 0x004020 },
+       { PLL_MEMORY, 0x004008 },
+       { PLL_VDEC  , 0x004030 },
+       { PLL_UNK41 , 0x00e818 },
+       { PLL_VPLL0 , 0x614100 },
+       { PLL_VPLL1 , 0x614900 },
+       {}
+};
+
+static u16
+pll_limits_table(struct nvkm_bios *bios, u8 *ver, u8 *hdr, u8 *cnt, u8 *len)
+{
+       struct bit_entry bit_C;
+
+       if (!bit_entry(bios, 'C', &bit_C) && bit_C.length >= 10) {
+               u16 data = nv_ro16(bios, bit_C.offset + 8);
+               if (data) {
+                       *ver = nv_ro08(bios, data + 0);
+                       *hdr = nv_ro08(bios, data + 1);
+                       *len = nv_ro08(bios, data + 2);
+                       *cnt = nv_ro08(bios, data + 3);
+                       return data;
+               }
+       }
+
+       if (bmp_version(bios) >= 0x0524) {
+               u16 data = nv_ro16(bios, bios->bmp_offset + 142);
+               if (data) {
+                       *ver = nv_ro08(bios, data + 0);
+                       *hdr = 1;
+                       *cnt = 1;
+                       *len = 0x18;
+                       return data;
+               }
+       }
+
+       *ver = 0x00;
+       return 0x0000;
+}
+
+static struct pll_mapping *
+pll_map(struct nvkm_bios *bios)
+{
+       switch (nv_device(bios)->card_type) {
+       case NV_04:
+       case NV_10:
+       case NV_11:
+       case NV_20:
+       case NV_30:
+               return nv04_pll_mapping;
+               break;
+       case NV_40:
+               return nv40_pll_mapping;
+       case NV_50:
+               if (nv_device(bios)->chipset == 0x50)
+                       return nv50_pll_mapping;
+               else
+               if (nv_device(bios)->chipset <  0xa3 ||
+                   nv_device(bios)->chipset == 0xaa ||
+                   nv_device(bios)->chipset == 0xac)
+                       return g84_pll_mapping;
+       default:
+               return NULL;
+       }
+}
+
+static u16
+pll_map_reg(struct nvkm_bios *bios, u32 reg, u32 *type, u8 *ver, u8 *len)
+{
+       struct pll_mapping *map;
+       u8  hdr, cnt;
+       u16 data;
+
+       data = pll_limits_table(bios, ver, &hdr, &cnt, len);
+       if (data && *ver >= 0x30) {
+               data += hdr;
+               while (cnt--) {
+                       if (nv_ro32(bios, data + 3) == reg) {
+                               *type = nv_ro08(bios, data + 0);
+                               return data;
+                       }
+                       data += *len;
+               }
+               return 0x0000;
+       }
+
+       map = pll_map(bios);
+       while (map->reg) {
+               if (map->reg == reg && *ver >= 0x20) {
+                       u16 addr = (data += hdr);
+                       *type = map->type;
+                       while (cnt--) {
+                               if (nv_ro32(bios, data) == map->reg)
+                                       return data;
+                               data += *len;
+                       }
+                       return addr;
+               } else
+               if (map->reg == reg) {
+                       *type = map->type;
+                       return data + 1;
+               }
+               map++;
+       }
+
+       return 0x0000;
+}
+
+static u16
+pll_map_type(struct nvkm_bios *bios, u8 type, u32 *reg, u8 *ver, u8 *len)
+{
+       struct pll_mapping *map;
+       u8  hdr, cnt;
+       u16 data;
+
+       data = pll_limits_table(bios, ver, &hdr, &cnt, len);
+       if (data && *ver >= 0x30) {
+               data += hdr;
+               while (cnt--) {
+                       if (nv_ro08(bios, data + 0) == type) {
+                               *reg = nv_ro32(bios, data + 3);
+                               return data;
+                       }
+                       data += *len;
+               }
+               return 0x0000;
+       }
+
+       map = pll_map(bios);
+       while (map->reg) {
+               if (map->type == type && *ver >= 0x20) {
+                       u16 addr = (data += hdr);
+                       *reg = map->reg;
+                       while (cnt--) {
+                               if (nv_ro32(bios, data) == map->reg)
+                                       return data;
+                               data += *len;
+                       }
+                       return addr;
+               } else
+               if (map->type == type) {
+                       *reg = map->reg;
+                       return data + 1;
+               }
+               map++;
+       }
+
+       return 0x0000;
+}
+
+int
+nvbios_pll_parse(struct nvkm_bios *bios, u32 type, struct nvbios_pll *info)
+{
+       u8  ver, len;
+       u32 reg = type;
+       u16 data;
+
+       if (type > PLL_MAX) {
+               reg  = type;
+               data = pll_map_reg(bios, reg, &type, &ver, &len);
+       } else {
+               data = pll_map_type(bios, type, &reg, &ver, &len);
+       }
+
+       if (ver && !data)
+               return -ENOENT;
+
+       memset(info, 0, sizeof(*info));
+       info->type = type;
+       info->reg = reg;
+
+       switch (ver) {
+       case 0x00:
+               break;
+       case 0x10:
+       case 0x11:
+               info->vco1.min_freq = nv_ro32(bios, data + 0);
+               info->vco1.max_freq = nv_ro32(bios, data + 4);
+               info->vco2.min_freq = nv_ro32(bios, data + 8);
+               info->vco2.max_freq = nv_ro32(bios, data + 12);
+               info->vco1.min_inputfreq = nv_ro32(bios, data + 16);
+               info->vco2.min_inputfreq = nv_ro32(bios, data + 20);
+               info->vco1.max_inputfreq = INT_MAX;
+               info->vco2.max_inputfreq = INT_MAX;
+
+               info->max_p = 0x7;
+               info->max_p_usable = 0x6;
+
+               /* these values taken from nv30/31/36 */
+               switch (bios->version.chip) {
+               case 0x36:
+                       info->vco1.min_n = 0x5;
+                       break;
+               default:
+                       info->vco1.min_n = 0x1;
+                       break;
+               }
+               info->vco1.max_n = 0xff;
+               info->vco1.min_m = 0x1;
+               info->vco1.max_m = 0xd;
+
+               /*
+                * 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
+                */
+               info->vco2.min_n = 0x4;
+               switch (bios->version.chip) {
+               case 0x30:
+               case 0x35:
+                       info->vco2.max_n = 0x1f;
+                       break;
+               default:
+                       info->vco2.max_n = 0x28;
+                       break;
+               }
+               info->vco2.min_m = 0x1;
+               info->vco2.max_m = 0x4;
+               break;
+       case 0x20:
+       case 0x21:
+               info->vco1.min_freq = nv_ro16(bios, data + 4) * 1000;
+               info->vco1.max_freq = nv_ro16(bios, data + 6) * 1000;
+               info->vco2.min_freq = nv_ro16(bios, data + 8) * 1000;
+               info->vco2.max_freq = nv_ro16(bios, data + 10) * 1000;
+               info->vco1.min_inputfreq = nv_ro16(bios, data + 12) * 1000;
+               info->vco2.min_inputfreq = nv_ro16(bios, data + 14) * 1000;
+               info->vco1.max_inputfreq = nv_ro16(bios, data + 16) * 1000;
+               info->vco2.max_inputfreq = nv_ro16(bios, data + 18) * 1000;
+               info->vco1.min_n = nv_ro08(bios, data + 20);
+               info->vco1.max_n = nv_ro08(bios, data + 21);
+               info->vco1.min_m = nv_ro08(bios, data + 22);
+               info->vco1.max_m = nv_ro08(bios, data + 23);
+               info->vco2.min_n = nv_ro08(bios, data + 24);
+               info->vco2.max_n = nv_ro08(bios, data + 25);
+               info->vco2.min_m = nv_ro08(bios, data + 26);
+               info->vco2.max_m = nv_ro08(bios, data + 27);
+
+               info->max_p = nv_ro08(bios, data + 29);
+               info->max_p_usable = info->max_p;
+               if (bios->version.chip < 0x60)
+                       info->max_p_usable = 0x6;
+               info->bias_p = nv_ro08(bios, data + 30);
+
+               if (len > 0x22)
+                       info->refclk = nv_ro32(bios, data + 31);
+               break;
+       case 0x30:
+               data = nv_ro16(bios, data + 1);
+
+               info->vco1.min_freq = nv_ro16(bios, data + 0) * 1000;
+               info->vco1.max_freq = nv_ro16(bios, data + 2) * 1000;
+               info->vco2.min_freq = nv_ro16(bios, data + 4) * 1000;
+               info->vco2.max_freq = nv_ro16(bios, data + 6) * 1000;
+               info->vco1.min_inputfreq = nv_ro16(bios, data + 8) * 1000;
+               info->vco2.min_inputfreq = nv_ro16(bios, data + 10) * 1000;
+               info->vco1.max_inputfreq = nv_ro16(bios, data + 12) * 1000;
+               info->vco2.max_inputfreq = nv_ro16(bios, data + 14) * 1000;
+               info->vco1.min_n = nv_ro08(bios, data + 16);
+               info->vco1.max_n = nv_ro08(bios, data + 17);
+               info->vco1.min_m = nv_ro08(bios, data + 18);
+               info->vco1.max_m = nv_ro08(bios, data + 19);
+               info->vco2.min_n = nv_ro08(bios, data + 20);
+               info->vco2.max_n = nv_ro08(bios, data + 21);
+               info->vco2.min_m = nv_ro08(bios, data + 22);
+               info->vco2.max_m = nv_ro08(bios, data + 23);
+               info->max_p_usable = info->max_p = nv_ro08(bios, data + 25);
+               info->bias_p = nv_ro08(bios, data + 27);
+               info->refclk = nv_ro32(bios, data + 28);
+               break;
+       case 0x40:
+               info->refclk = nv_ro16(bios, data + 9) * 1000;
+               data = nv_ro16(bios, data + 1);
+
+               info->vco1.min_freq = nv_ro16(bios, data + 0) * 1000;
+               info->vco1.max_freq = nv_ro16(bios, data + 2) * 1000;
+               info->vco1.min_inputfreq = nv_ro16(bios, data + 4) * 1000;
+               info->vco1.max_inputfreq = nv_ro16(bios, data + 6) * 1000;
+               info->vco1.min_m = nv_ro08(bios, data + 8);
+               info->vco1.max_m = nv_ro08(bios, data + 9);
+               info->vco1.min_n = nv_ro08(bios, data + 10);
+               info->vco1.max_n = nv_ro08(bios, data + 11);
+               info->min_p = nv_ro08(bios, data + 12);
+               info->max_p = nv_ro08(bios, data + 13);
+               break;
+       default:
+               nv_error(bios, "unknown pll limits version 0x%02x\n", ver);
+               return -EINVAL;
+       }
+
+       if (!info->refclk) {
+               info->refclk = nv_device(bios)->crystal;
+               if (bios->version.chip == 0x51) {
+                       u32 sel_clk = nv_rd32(bios, 0x680524);
+                       if ((info->reg == 0x680508 && sel_clk & 0x20) ||
+                           (info->reg == 0x680520 && sel_clk & 0x80)) {
+                               if (nv_rdvgac(bios, 0, 0x27) < 0xa3)
+                                       info->refclk = 200000;
+                               else
+                                       info->refclk = 25000;
+                       }
+               }
+       }
+
+       /*
+        * 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 (!info->vco1.max_freq) {
+               info->vco1.max_freq = nv_ro32(bios, bios->bmp_offset + 67);
+               info->vco1.min_freq = nv_ro32(bios, bios->bmp_offset + 71);
+               if (bmp_version(bios) < 0x0506) {
+                       info->vco1.max_freq = 256000;
+                       info->vco1.min_freq = 128000;
+               }
+
+               info->vco1.min_inputfreq = 0;
+               info->vco1.max_inputfreq = INT_MAX;
+               info->vco1.min_n = 0x1;
+               info->vco1.max_n = 0xff;
+               info->vco1.min_m = 0x1;
+
+               if (nv_device(bios)->crystal == 13500) {
+                       /* nv05 does this, nv11 doesn't, nv10 unknown */
+                       if (bios->version.chip < 0x11)
+                               info->vco1.min_m = 0x7;
+                       info->vco1.max_m = 0xd;
+               } else {
+                       if (bios->version.chip < 0x11)
+                               info->vco1.min_m = 0x8;
+                       info->vco1.max_m = 0xe;
+               }
+
+               if (bios->version.chip <  0x17 ||
+                   bios->version.chip == 0x1a ||
+                   bios->version.chip == 0x20)
+                       info->max_p = 4;
+               else
+                       info->max_p = 5;
+               info->max_p_usable = info->max_p;
+       }
+
+       return 0;
+}
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/bios/pmu.c b/drivers/gpu/drm/nouveau/nvkm/subdev/bios/pmu.c
new file mode 100644 (file)
index 0000000..20c5ce0
--- /dev/null
@@ -0,0 +1,134 @@
+/*
+ * Copyright 2014 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 <bskeggs@redhat.com>
+ */
+#include <subdev/bios.h>
+#include <subdev/bios/bit.h>
+#include <subdev/bios/image.h>
+#include <subdev/bios/pmu.h>
+
+static u32
+weirdo_pointer(struct nvkm_bios *bios, u32 data)
+{
+       struct nvbios_image image;
+       int idx = 0;
+       if (nvbios_image(bios, idx++, &image)) {
+               data -= image.size;
+               while (nvbios_image(bios, idx++, &image)) {
+                       if (image.type == 0xe0)
+                               return image.base + data;
+               }
+       }
+       return 0;
+}
+
+u32
+nvbios_pmuTe(struct nvkm_bios *bios, u8 *ver, u8 *hdr, u8 *cnt, u8 *len)
+{
+       struct bit_entry bit_p;
+       u32 data = 0;
+
+       if (!bit_entry(bios, 'p', &bit_p)) {
+               if (bit_p.version == 2 && bit_p.length >= 4)
+                       data = nv_ro32(bios, bit_p.offset + 0x00);
+               if ((data = weirdo_pointer(bios, data))) {
+                       *ver = nv_ro08(bios, data + 0x00); /* maybe? */
+                       *hdr = nv_ro08(bios, data + 0x01);
+                       *len = nv_ro08(bios, data + 0x02);
+                       *cnt = nv_ro08(bios, data + 0x03);
+               }
+       }
+
+       return data;
+}
+
+u32
+nvbios_pmuTp(struct nvkm_bios *bios, u8 *ver, u8 *hdr, u8 *cnt, u8 *len,
+            struct nvbios_pmuT *info)
+{
+       u32 data = nvbios_pmuTe(bios, ver, hdr, cnt, len);
+       memset(info, 0x00, sizeof(*info));
+       switch (!!data * *ver) {
+       default:
+               break;
+       }
+       return data;
+}
+
+u32
+nvbios_pmuEe(struct nvkm_bios *bios, int idx, u8 *ver, u8 *hdr)
+{
+       u8  cnt, len;
+       u32 data = nvbios_pmuTe(bios, ver, hdr, &cnt, &len);
+       if (data && idx < cnt) {
+               data = data + *hdr + (idx * len);
+               *hdr = len;
+               return data;
+       }
+       return 0;
+}
+
+u32
+nvbios_pmuEp(struct nvkm_bios *bios, int idx, u8 *ver, u8 *hdr,
+            struct nvbios_pmuE *info)
+{
+       u32 data = nvbios_pmuEe(bios, idx, ver, hdr);
+       memset(info, 0x00, sizeof(*info));
+       switch (!!data * *ver) {
+       default:
+               info->type = nv_ro08(bios, data + 0x00);
+               info->data = nv_ro32(bios, data + 0x02);
+               break;
+       }
+       return data;
+}
+
+bool
+nvbios_pmuRm(struct nvkm_bios *bios, u8 type, struct nvbios_pmuR *info)
+{
+       struct nvbios_pmuE pmuE;
+       u8  ver, hdr, idx = 0;
+       u32 data;
+       memset(info, 0x00, sizeof(*info));
+       while ((data = nvbios_pmuEp(bios, idx++, &ver, &hdr, &pmuE))) {
+               if ( pmuE.type == type &&
+                   (data = weirdo_pointer(bios, pmuE.data))) {
+                       info->init_addr_pmu = nv_ro32(bios, data + 0x08);
+                       info->args_addr_pmu = nv_ro32(bios, data + 0x0c);
+                       info->boot_addr     = data + 0x30;
+                       info->boot_addr_pmu = nv_ro32(bios, data + 0x10) +
+                                             nv_ro32(bios, data + 0x18);
+                       info->boot_size     = nv_ro32(bios, data + 0x1c) -
+                                             nv_ro32(bios, data + 0x18);
+                       info->code_addr     = info->boot_addr + info->boot_size;
+                       info->code_addr_pmu = info->boot_addr_pmu +
+                                             info->boot_size;
+                       info->code_size     = nv_ro32(bios, data + 0x20);
+                       info->data_addr     = data + 0x30 +
+                                             nv_ro32(bios, data + 0x24);
+                       info->data_addr_pmu = nv_ro32(bios, data + 0x28);
+                       info->data_size     = nv_ro32(bios, data + 0x2c);
+                       return true;
+               }
+       }
+       return false;
+}
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/bios/priv.h b/drivers/gpu/drm/nouveau/nvkm/subdev/bios/priv.h
new file mode 100644 (file)
index 0000000..95e4fa1
--- /dev/null
@@ -0,0 +1,23 @@
+#ifndef __NVKM_BIOS_PRIV_H__
+#define __NVKM_BIOS_PRIV_H__
+#include <subdev/bios.h>
+
+struct nvbios_source {
+       const char *name;
+       void *(*init)(struct nvkm_bios *, const char *);
+       void  (*fini)(void *);
+       u32   (*read)(void *, u32 offset, u32 length, struct nvkm_bios *);
+       bool rw;
+};
+
+int nvbios_extend(struct nvkm_bios *, u32 length);
+int nvbios_shadow(struct nvkm_bios *);
+
+extern const struct nvbios_source nvbios_rom;
+extern const struct nvbios_source nvbios_ramin;
+extern const struct nvbios_source nvbios_acpi_fast;
+extern const struct nvbios_source nvbios_acpi_slow;
+extern const struct nvbios_source nvbios_pcirom;
+extern const struct nvbios_source nvbios_platform;
+extern const struct nvbios_source nvbios_of;
+#endif
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/bios/ramcfg.c b/drivers/gpu/drm/nouveau/nvkm/subdev/bios/ramcfg.c
new file mode 100644 (file)
index 0000000..a17b221
--- /dev/null
@@ -0,0 +1,78 @@
+/*
+ * Copyright 2013 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 <bskeggs@redhat.com>
+ */
+#include <subdev/bios.h>
+#include <subdev/bios/bit.h>
+#include <subdev/bios/ramcfg.h>
+#include <subdev/bios/M0203.h>
+
+static u8
+nvbios_ramcfg_strap(struct nvkm_subdev *subdev)
+{
+       return (nv_rd32(subdev, 0x101000) & 0x0000003c) >> 2;
+}
+
+u8
+nvbios_ramcfg_count(struct nvkm_bios *bios)
+{
+       struct bit_entry bit_M;
+
+       if (!bit_entry(bios, 'M', &bit_M)) {
+               if (bit_M.version == 1 && bit_M.length >= 5)
+                       return nv_ro08(bios, bit_M.offset + 2);
+               if (bit_M.version == 2 && bit_M.length >= 3)
+                       return nv_ro08(bios, bit_M.offset + 0);
+       }
+
+       return 0x00;
+}
+
+u8
+nvbios_ramcfg_index(struct nvkm_subdev *subdev)
+{
+       struct nvkm_bios *bios = nvkm_bios(subdev);
+       u8 strap = nvbios_ramcfg_strap(subdev);
+       u32 xlat = 0x00000000;
+       struct bit_entry bit_M;
+       struct nvbios_M0203E M0203E;
+       u8 ver, hdr;
+
+       if (!bit_entry(bios, 'M', &bit_M)) {
+               if (bit_M.version == 1 && bit_M.length >= 5)
+                       xlat = nv_ro16(bios, bit_M.offset + 3);
+               if (bit_M.version == 2 && bit_M.length >= 3) {
+                       /*XXX: is M ever shorter than this?
+                        *     if not - what is xlat used for now?
+                        *     also - sigh..
+                        */
+                       if (bit_M.length >= 7 &&
+                           nvbios_M0203Em(bios, strap, &ver, &hdr, &M0203E))
+                               return M0203E.group;
+                       xlat = nv_ro16(bios, bit_M.offset + 1);
+               }
+       }
+
+       if (xlat)
+               strap = nv_ro08(bios, xlat + strap);
+       return strap;
+}
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/bios/rammap.c b/drivers/gpu/drm/nouveau/nvkm/subdev/bios/rammap.c
new file mode 100644 (file)
index 0000000..8b17bb4
--- /dev/null
@@ -0,0 +1,211 @@
+/*
+ * Copyright 2013 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 <subdev/bios.h>
+#include <subdev/bios/bit.h>
+#include <subdev/bios/rammap.h>
+
+u32
+nvbios_rammapTe(struct nvkm_bios *bios, u8 *ver, u8 *hdr,
+               u8 *cnt, u8 *len, u8 *snr, u8 *ssz)
+{
+       struct bit_entry bit_P;
+       u16 rammap = 0x0000;
+
+       if (!bit_entry(bios, 'P', &bit_P)) {
+               if (bit_P.version == 2)
+                       rammap = nv_ro16(bios, bit_P.offset + 4);
+
+               if (rammap) {
+                       *ver = nv_ro08(bios, rammap + 0);
+                       switch (*ver) {
+                       case 0x10:
+                       case 0x11:
+                               *hdr = nv_ro08(bios, rammap + 1);
+                               *cnt = nv_ro08(bios, rammap + 5);
+                               *len = nv_ro08(bios, rammap + 2);
+                               *snr = nv_ro08(bios, rammap + 4);
+                               *ssz = nv_ro08(bios, rammap + 3);
+                               return rammap;
+                       default:
+                               break;
+                       }
+               }
+       }
+
+       return 0x0000;
+}
+
+u32
+nvbios_rammapEe(struct nvkm_bios *bios, int idx,
+               u8 *ver, u8 *hdr, u8 *cnt, u8 *len)
+{
+       u8  snr, ssz;
+       u16 rammap = nvbios_rammapTe(bios, ver, hdr, cnt, len, &snr, &ssz);
+       if (rammap && idx < *cnt) {
+               rammap = rammap + *hdr + (idx * (*len + (snr * ssz)));
+               *hdr = *len;
+               *cnt = snr;
+               *len = ssz;
+               return rammap;
+       }
+       return 0x0000;
+}
+
+u32
+nvbios_rammapEp(struct nvkm_bios *bios, int idx,
+               u8 *ver, u8 *hdr, u8 *cnt, u8 *len, struct nvbios_ramcfg *p)
+{
+       u32 data = nvbios_rammapEe(bios, idx, ver, hdr, cnt, len), temp;
+       memset(p, 0x00, sizeof(*p));
+       p->rammap_ver = *ver;
+       p->rammap_hdr = *hdr;
+       switch (!!data * *ver) {
+       case 0x10:
+               p->rammap_min      =  nv_ro16(bios, data + 0x00);
+               p->rammap_max      =  nv_ro16(bios, data + 0x02);
+               p->rammap_10_04_02 = (nv_ro08(bios, data + 0x04) & 0x02) >> 1;
+               p->rammap_10_04_08 = (nv_ro08(bios, data + 0x04) & 0x08) >> 3;
+               break;
+       case 0x11:
+               p->rammap_min      =  nv_ro16(bios, data + 0x00);
+               p->rammap_max      =  nv_ro16(bios, data + 0x02);
+               p->rammap_11_08_01 = (nv_ro08(bios, data + 0x08) & 0x01) >> 0;
+               p->rammap_11_08_0c = (nv_ro08(bios, data + 0x08) & 0x0c) >> 2;
+               p->rammap_11_08_10 = (nv_ro08(bios, data + 0x08) & 0x10) >> 4;
+               temp = nv_ro32(bios, data + 0x09);
+               p->rammap_11_09_01ff = (temp & 0x000001ff) >> 0;
+               p->rammap_11_0a_03fe = (temp & 0x0003fe00) >> 9;
+               p->rammap_11_0a_0400 = (temp & 0x00040000) >> 18;
+               p->rammap_11_0a_0800 = (temp & 0x00080000) >> 19;
+               p->rammap_11_0b_01f0 = (temp & 0x01f00000) >> 20;
+               p->rammap_11_0b_0200 = (temp & 0x02000000) >> 25;
+               p->rammap_11_0b_0400 = (temp & 0x04000000) >> 26;
+               p->rammap_11_0b_0800 = (temp & 0x08000000) >> 27;
+               p->rammap_11_0d    =  nv_ro08(bios, data + 0x0d);
+               p->rammap_11_0e    =  nv_ro08(bios, data + 0x0e);
+               p->rammap_11_0f    =  nv_ro08(bios, data + 0x0f);
+               p->rammap_11_11_0c = (nv_ro08(bios, data + 0x11) & 0x0c) >> 2;
+               break;
+       default:
+               data = 0;
+               break;
+       }
+       return data;
+}
+
+u32
+nvbios_rammapEm(struct nvkm_bios *bios, u16 mhz,
+               u8 *ver, u8 *hdr, u8 *cnt, u8 *len, struct nvbios_ramcfg *info)
+{
+       int idx = 0;
+       u32 data;
+       while ((data = nvbios_rammapEp(bios, idx++, ver, hdr, cnt, len, info))) {
+               if (mhz >= info->rammap_min && mhz <= info->rammap_max)
+                       break;
+       }
+       return data;
+}
+
+u32
+nvbios_rammapSe(struct nvkm_bios *bios, u32 data,
+               u8 ever, u8 ehdr, u8 ecnt, u8 elen, int idx, u8 *ver, u8 *hdr)
+{
+       if (idx < ecnt) {
+               data = data + ehdr + (idx * elen);
+               *ver = ever;
+               *hdr = elen;
+               return data;
+       }
+       return 0;
+}
+
+u32
+nvbios_rammapSp(struct nvkm_bios *bios, u32 data,
+               u8 ever, u8 ehdr, u8 ecnt, u8 elen, int idx,
+               u8 *ver, u8 *hdr, struct nvbios_ramcfg *p)
+{
+       data = nvbios_rammapSe(bios, data, ever, ehdr, ecnt, elen, idx, ver, hdr);
+       p->ramcfg_ver = *ver;
+       p->ramcfg_hdr = *hdr;
+       switch (!!data * *ver) {
+       case 0x10:
+               p->ramcfg_timing   =  nv_ro08(bios, data + 0x01);
+               p->ramcfg_10_02_01 = (nv_ro08(bios, data + 0x02) & 0x01) >> 0;
+               p->ramcfg_10_02_02 = (nv_ro08(bios, data + 0x02) & 0x02) >> 1;
+               p->ramcfg_10_02_04 = (nv_ro08(bios, data + 0x02) & 0x04) >> 2;
+               p->ramcfg_10_02_08 = (nv_ro08(bios, data + 0x02) & 0x08) >> 3;
+               p->ramcfg_10_02_10 = (nv_ro08(bios, data + 0x02) & 0x10) >> 4;
+               p->ramcfg_10_02_20 = (nv_ro08(bios, data + 0x02) & 0x20) >> 5;
+               p->ramcfg_10_DLLoff = (nv_ro08(bios, data + 0x02) & 0x40) >> 6;
+               p->ramcfg_10_03_0f = (nv_ro08(bios, data + 0x03) & 0x0f) >> 0;
+               p->ramcfg_10_04_01 = (nv_ro08(bios, data + 0x04) & 0x01) >> 0;
+               p->ramcfg_10_05    = (nv_ro08(bios, data + 0x05) & 0xff) >> 0;
+               p->ramcfg_10_06    = (nv_ro08(bios, data + 0x06) & 0xff) >> 0;
+               p->ramcfg_10_07    = (nv_ro08(bios, data + 0x07) & 0xff) >> 0;
+               p->ramcfg_10_08    = (nv_ro08(bios, data + 0x08) & 0xff) >> 0;
+               p->ramcfg_10_09_0f = (nv_ro08(bios, data + 0x09) & 0x0f) >> 0;
+               p->ramcfg_10_09_f0 = (nv_ro08(bios, data + 0x09) & 0xf0) >> 4;
+               break;
+       case 0x11:
+               p->ramcfg_timing   =  nv_ro08(bios, data + 0x00);
+               p->ramcfg_11_01_01 = (nv_ro08(bios, data + 0x01) & 0x01) >> 0;
+               p->ramcfg_11_01_02 = (nv_ro08(bios, data + 0x01) & 0x02) >> 1;
+               p->ramcfg_11_01_04 = (nv_ro08(bios, data + 0x01) & 0x04) >> 2;
+               p->ramcfg_11_01_08 = (nv_ro08(bios, data + 0x01) & 0x08) >> 3;
+               p->ramcfg_11_01_10 = (nv_ro08(bios, data + 0x01) & 0x10) >> 4;
+               p->ramcfg_11_01_20 = (nv_ro08(bios, data + 0x01) & 0x20) >> 5;
+               p->ramcfg_11_01_40 = (nv_ro08(bios, data + 0x01) & 0x40) >> 6;
+               p->ramcfg_11_01_80 = (nv_ro08(bios, data + 0x01) & 0x80) >> 7;
+               p->ramcfg_11_02_03 = (nv_ro08(bios, data + 0x02) & 0x03) >> 0;
+               p->ramcfg_11_02_04 = (nv_ro08(bios, data + 0x02) & 0x04) >> 2;
+               p->ramcfg_11_02_08 = (nv_ro08(bios, data + 0x02) & 0x08) >> 3;
+               p->ramcfg_11_02_10 = (nv_ro08(bios, data + 0x02) & 0x10) >> 4;
+               p->ramcfg_11_02_40 = (nv_ro08(bios, data + 0x02) & 0x40) >> 6;
+               p->ramcfg_11_02_80 = (nv_ro08(bios, data + 0x02) & 0x80) >> 7;
+               p->ramcfg_11_03_0f = (nv_ro08(bios, data + 0x03) & 0x0f) >> 0;
+               p->ramcfg_11_03_30 = (nv_ro08(bios, data + 0x03) & 0x30) >> 4;
+               p->ramcfg_11_03_c0 = (nv_ro08(bios, data + 0x03) & 0xc0) >> 6;
+               p->ramcfg_11_03_f0 = (nv_ro08(bios, data + 0x03) & 0xf0) >> 4;
+               p->ramcfg_11_04    = (nv_ro08(bios, data + 0x04) & 0xff) >> 0;
+               p->ramcfg_11_06    = (nv_ro08(bios, data + 0x06) & 0xff) >> 0;
+               p->ramcfg_11_07_02 = (nv_ro08(bios, data + 0x07) & 0x02) >> 1;
+               p->ramcfg_11_07_04 = (nv_ro08(bios, data + 0x07) & 0x04) >> 2;
+               p->ramcfg_11_07_08 = (nv_ro08(bios, data + 0x07) & 0x08) >> 3;
+               p->ramcfg_11_07_10 = (nv_ro08(bios, data + 0x07) & 0x10) >> 4;
+               p->ramcfg_11_07_40 = (nv_ro08(bios, data + 0x07) & 0x40) >> 6;
+               p->ramcfg_11_07_80 = (nv_ro08(bios, data + 0x07) & 0x80) >> 7;
+               p->ramcfg_11_08_01 = (nv_ro08(bios, data + 0x08) & 0x01) >> 0;
+               p->ramcfg_11_08_02 = (nv_ro08(bios, data + 0x08) & 0x02) >> 1;
+               p->ramcfg_11_08_04 = (nv_ro08(bios, data + 0x08) & 0x04) >> 2;
+               p->ramcfg_11_08_08 = (nv_ro08(bios, data + 0x08) & 0x08) >> 3;
+               p->ramcfg_11_08_10 = (nv_ro08(bios, data + 0x08) & 0x10) >> 4;
+               p->ramcfg_11_08_20 = (nv_ro08(bios, data + 0x08) & 0x20) >> 5;
+               p->ramcfg_11_09    = (nv_ro08(bios, data + 0x09) & 0xff) >> 0;
+               break;
+       default:
+               data = 0;
+               break;
+       }
+       return data;
+}
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/bios/shadow.c b/drivers/gpu/drm/nouveau/nvkm/subdev/bios/shadow.c
new file mode 100644 (file)
index 0000000..8c2b7cb
--- /dev/null
@@ -0,0 +1,272 @@
+/*
+ * Copyright 2014 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 <bskeggs@redhat.com>
+ */
+#include "priv.h"
+
+#include <core/device.h>
+#include <core/option.h>
+#include <subdev/bios.h>
+#include <subdev/bios/image.h>
+
+struct shadow {
+       struct nvkm_oclass base;
+       u32 skip;
+       const struct nvbios_source *func;
+       void *data;
+       u32 size;
+       int score;
+};
+
+static bool
+shadow_fetch(struct nvkm_bios *bios, u32 upto)
+{
+       struct shadow *mthd = (void *)nv_object(bios)->oclass;
+       const u32 limit = (upto + 3) & ~3;
+       const u32 start = bios->size;
+       void *data = mthd->data;
+       if (nvbios_extend(bios, limit) > 0) {
+               u32 read = mthd->func->read(data, start, limit - start, bios);
+               bios->size = start + read;
+       }
+       return bios->size >= limit;
+}
+
+static u8
+shadow_rd08(struct nvkm_object *object, u64 addr)
+{
+       struct nvkm_bios *bios = (void *)object;
+       if (shadow_fetch(bios, addr + 1))
+               return bios->data[addr];
+       return 0x00;
+}
+
+static u16
+shadow_rd16(struct nvkm_object *object, u64 addr)
+{
+       struct nvkm_bios *bios = (void *)object;
+       if (shadow_fetch(bios, addr + 2))
+               return get_unaligned_le16(&bios->data[addr]);
+       return 0x0000;
+}
+
+static u32
+shadow_rd32(struct nvkm_object *object, u64 addr)
+{
+       struct nvkm_bios *bios = (void *)object;
+       if (shadow_fetch(bios, addr + 4))
+               return get_unaligned_le32(&bios->data[addr]);
+       return 0x00000000;
+}
+
+static struct nvkm_oclass
+shadow_class = {
+       .handle = NV_SUBDEV(VBIOS, 0x00),
+       .ofuncs = &(struct nvkm_ofuncs) {
+               .rd08 = shadow_rd08,
+               .rd16 = shadow_rd16,
+               .rd32 = shadow_rd32,
+       },
+};
+
+static int
+shadow_image(struct nvkm_bios *bios, int idx, struct shadow *mthd)
+{
+       struct nvbios_image image;
+       int score = 1;
+
+       if (!nvbios_image(bios, idx, &image)) {
+               nv_debug(bios, "image %d invalid\n", idx);
+               return 0;
+       }
+       nv_debug(bios, "%08x: type %02x, %d bytes\n",
+                image.base, image.type, image.size);
+
+       if (!shadow_fetch(bios, image.size)) {
+               nv_debug(bios, "%08x: fetch failed\n", image.base);
+               return 0;
+       }
+
+       switch (image.type) {
+       case 0x00:
+               if (nvbios_checksum(&bios->data[image.base], image.size)) {
+                       nv_debug(bios, "%08x: checksum failed\n", image.base);
+                       if (mthd->func->rw)
+                               score += 1;
+                       score += 1;
+               } else {
+                       score += 3;
+               }
+               break;
+       default:
+               score += 3;
+               break;
+       }
+
+       if (!image.last)
+               score += shadow_image(bios, idx + 1, mthd);
+       return score;
+}
+
+static int
+shadow_score(struct nvkm_bios *bios, struct shadow *mthd)
+{
+       struct nvkm_oclass *oclass = nv_object(bios)->oclass;
+       int score;
+       nv_object(bios)->oclass = &mthd->base;
+       score = shadow_image(bios, 0, mthd);
+       nv_object(bios)->oclass = oclass;
+       return score;
+
+}
+
+static int
+shadow_method(struct nvkm_bios *bios, struct shadow *mthd, const char *name)
+{
+       const struct nvbios_source *func = mthd->func;
+       if (func->name) {
+               nv_debug(bios, "trying %s...\n", name ? name : func->name);
+               if (func->init) {
+                       mthd->data = func->init(bios, name);
+                       if (IS_ERR(mthd->data)) {
+                               mthd->data = NULL;
+                               return 0;
+                       }
+               }
+               mthd->score = shadow_score(bios, mthd);
+               if (func->fini)
+                       func->fini(mthd->data);
+               nv_debug(bios, "scored %d\n", mthd->score);
+               mthd->data = bios->data;
+               mthd->size = bios->size;
+               bios->data  = NULL;
+               bios->size  = 0;
+       }
+       return mthd->score;
+}
+
+static u32
+shadow_fw_read(void *data, u32 offset, u32 length, struct nvkm_bios *bios)
+{
+       const struct firmware *fw = data;
+       if (offset + length <= fw->size) {
+               memcpy(bios->data + offset, fw->data + offset, length);
+               return length;
+       }
+       return 0;
+}
+
+static void *
+shadow_fw_init(struct nvkm_bios *bios, const char *name)
+{
+       struct device *dev = &nv_device(bios)->pdev->dev;
+       const struct firmware *fw;
+       int ret = request_firmware(&fw, name, dev);
+       if (ret)
+               return ERR_PTR(-ENOENT);
+       return (void *)fw;
+}
+
+static const struct nvbios_source
+shadow_fw = {
+       .name = "firmware",
+       .init = shadow_fw_init,
+       .fini = (void(*)(void *))release_firmware,
+       .read = shadow_fw_read,
+       .rw = false,
+};
+
+int
+nvbios_shadow(struct nvkm_bios *bios)
+{
+       struct shadow mthds[] = {
+               { shadow_class, 0, &nvbios_of },
+               { shadow_class, 0, &nvbios_ramin },
+               { shadow_class, 0, &nvbios_rom },
+               { shadow_class, 0, &nvbios_acpi_fast },
+               { shadow_class, 4, &nvbios_acpi_slow },
+               { shadow_class, 1, &nvbios_pcirom },
+               { shadow_class, 1, &nvbios_platform },
+               { shadow_class }
+       }, *mthd = mthds, *best = NULL;
+       const char *optarg;
+       char *source;
+       int optlen;
+
+       /* handle user-specified bios source */
+       optarg = nvkm_stropt(nv_device(bios)->cfgopt, "NvBios", &optlen);
+       source = optarg ? kstrndup(optarg, optlen, GFP_KERNEL) : NULL;
+       if (source) {
+               /* try to match one of the built-in methods */
+               for (mthd = mthds; mthd->func; mthd++) {
+                       if (mthd->func->name &&
+                           !strcasecmp(source, mthd->func->name)) {
+                               best = mthd;
+                               if (shadow_method(bios, mthd, NULL))
+                                       break;
+                       }
+               }
+
+               /* otherwise, attempt to load as firmware */
+               if (!best && (best = mthd)) {
+                       mthd->func = &shadow_fw;
+                       shadow_method(bios, mthd, source);
+                       mthd->func = NULL;
+               }
+
+               if (!best->score) {
+                       nv_error(bios, "%s invalid\n", source);
+                       kfree(source);
+                       source = NULL;
+               }
+       }
+
+       /* scan all potential bios sources, looking for best image */
+       if (!best || !best->score) {
+               for (mthd = mthds, best = mthd; mthd->func; mthd++) {
+                       if (!mthd->skip || best->score < mthd->skip) {
+                               if (shadow_method(bios, mthd, NULL)) {
+                                       if (mthd->score > best->score)
+                                               best = mthd;
+                               }
+                       }
+               }
+       }
+
+       /* cleanup the ones we didn't use */
+       for (mthd = mthds; mthd->func; mthd++) {
+               if (mthd != best)
+                       kfree(mthd->data);
+       }
+
+       if (!best->score) {
+               nv_fatal(bios, "unable to locate usable image\n");
+               return -EINVAL;
+       }
+
+       nv_info(bios, "using image from %s\n", best->func ?
+               best->func->name : source);
+       bios->data = best->data;
+       bios->size = best->size;
+       kfree(source);
+       return 0;
+}
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/bios/shadowacpi.c b/drivers/gpu/drm/nouveau/nvkm/subdev/bios/shadowacpi.c
new file mode 100644 (file)
index 0000000..1fbd93b
--- /dev/null
@@ -0,0 +1,112 @@
+/*
+ * Copyright 2012 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.
+ *
+ */
+#include "priv.h"
+
+#include <core/device.h>
+
+#if defined(CONFIG_ACPI) && defined(CONFIG_X86)
+int nouveau_acpi_get_bios_chunk(uint8_t *bios, int offset, int len);
+bool nouveau_acpi_rom_supported(struct pci_dev *pdev);
+#else
+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;
+}
+#endif
+
+/* This version of the shadow function disobeys the ACPI spec and tries
+ * to fetch in units of more than 4KiB at a time.  This is a LOT faster
+ * on some systems, such as Lenovo W530.
+ */
+static u32
+acpi_read_fast(void *data, u32 offset, u32 length, struct nvkm_bios *bios)
+{
+       u32 limit = (offset + length + 0xfff) & ~0xfff;
+       u32 start = offset & ~0x00000fff;
+       u32 fetch = limit - start;
+
+       if (nvbios_extend(bios, limit) > 0) {
+               int ret = nouveau_acpi_get_bios_chunk(bios->data, start, fetch);
+               if (ret == fetch)
+                       return fetch;
+       }
+
+       return 0;
+}
+
+/* Other systems, such as the one in fdo#55948, will report a success
+ * but only return 4KiB of data.  The common bios fetching logic will
+ * detect an invalid image, and fall back to this version of the read
+ * function.
+ */
+static u32
+acpi_read_slow(void *data, u32 offset, u32 length, struct nvkm_bios *bios)
+{
+       u32 limit = (offset + length + 0xfff) & ~0xfff;
+       u32 start = offset & ~0xfff;
+       u32 fetch = 0;
+
+       if (nvbios_extend(bios, limit) > 0) {
+               while (start + fetch < limit) {
+                       int ret = nouveau_acpi_get_bios_chunk(bios->data,
+                                                             start + fetch,
+                                                             0x1000);
+                       if (ret != 0x1000)
+                               break;
+                       fetch += 0x1000;
+               }
+       }
+
+       return fetch;
+}
+
+static void *
+acpi_init(struct nvkm_bios *bios, const char *name)
+{
+       if (!nouveau_acpi_rom_supported(nv_device(bios)->pdev))
+               return ERR_PTR(-ENODEV);
+       return NULL;
+}
+
+const struct nvbios_source
+nvbios_acpi_fast = {
+       .name = "ACPI",
+       .init = acpi_init,
+       .read = acpi_read_fast,
+       .rw = false,
+};
+
+const struct nvbios_source
+nvbios_acpi_slow = {
+       .name = "ACPI",
+       .init = acpi_init,
+       .read = acpi_read_slow,
+       .rw = false,
+};
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/bios/shadowof.c b/drivers/gpu/drm/nouveau/nvkm/subdev/bios/shadowof.c
new file mode 100644 (file)
index 0000000..4c19a7d
--- /dev/null
@@ -0,0 +1,72 @@
+/*
+ * Copyright 2012 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.
+ *
+ */
+#include "priv.h"
+
+#include <core/device.h>
+
+#if defined(__powerpc__)
+struct priv {
+       const void __iomem *data;
+       int size;
+};
+
+static u32
+of_read(void *data, u32 offset, u32 length, struct nvkm_bios *bios)
+{
+       struct priv *priv = data;
+       if (offset + length <= priv->size) {
+               memcpy_fromio(bios->data + offset, priv->data + offset, length);
+               return length;
+       }
+       return 0;
+}
+
+static void *
+of_init(struct nvkm_bios *bios, const char *name)
+{
+       struct pci_dev *pdev = nv_device(bios)->pdev;
+       struct device_node *dn;
+       struct priv *priv;
+       if (!(dn = pci_device_to_OF_node(pdev)))
+               return ERR_PTR(-ENODEV);
+       if (!(priv = kzalloc(sizeof(*priv), GFP_KERNEL)))
+               return ERR_PTR(-ENOMEM);
+       if ((priv->data = of_get_property(dn, "NVDA,BMP", &priv->size)))
+               return priv;
+       kfree(priv);
+       return ERR_PTR(-EINVAL);
+}
+
+const struct nvbios_source
+nvbios_of = {
+       .name = "OpenFirmware",
+       .init = of_init,
+       .fini = (void(*)(void *))kfree,
+       .read = of_read,
+       .rw = false,
+};
+#else
+const struct nvbios_source
+nvbios_of = {
+};
+#endif
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/bios/shadowpci.c b/drivers/gpu/drm/nouveau/nvkm/subdev/bios/shadowpci.c
new file mode 100644 (file)
index 0000000..1b04548
--- /dev/null
@@ -0,0 +1,109 @@
+/*
+ * Copyright 2012 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.
+ *
+ */
+#include "priv.h"
+
+#include <core/device.h>
+
+struct priv {
+       struct pci_dev *pdev;
+       void __iomem *rom;
+       size_t size;
+};
+
+static u32
+pcirom_read(void *data, u32 offset, u32 length, struct nvkm_bios *bios)
+{
+       struct priv *priv = data;
+       if (offset + length <= priv->size) {
+               memcpy_fromio(bios->data + offset, priv->rom + offset, length);
+               return length;
+       }
+       return 0;
+}
+
+static void
+pcirom_fini(void *data)
+{
+       struct priv *priv = data;
+       pci_unmap_rom(priv->pdev, priv->rom);
+       pci_disable_rom(priv->pdev);
+       kfree(priv);
+}
+
+static void *
+pcirom_init(struct nvkm_bios *bios, const char *name)
+{
+       struct pci_dev *pdev = nv_device(bios)->pdev;
+       struct priv *priv = NULL;
+       int ret;
+
+       if (!(ret = pci_enable_rom(pdev))) {
+               if (ret = -ENOMEM,
+                   (priv = kmalloc(sizeof(*priv), GFP_KERNEL))) {
+                       if (ret = -EFAULT,
+                           (priv->rom = pci_map_rom(pdev, &priv->size))) {
+                               priv->pdev = pdev;
+                               return priv;
+                       }
+                       kfree(priv);
+               }
+               pci_disable_rom(pdev);
+       }
+
+       return ERR_PTR(ret);
+}
+
+const struct nvbios_source
+nvbios_pcirom = {
+       .name = "PCIROM",
+       .init = pcirom_init,
+       .fini = pcirom_fini,
+       .read = pcirom_read,
+       .rw = true,
+};
+
+static void *
+platform_init(struct nvkm_bios *bios, const char *name)
+{
+       struct pci_dev *pdev = nv_device(bios)->pdev;
+       struct priv *priv;
+       int ret = -ENOMEM;
+
+       if ((priv = kmalloc(sizeof(*priv), GFP_KERNEL))) {
+               if (ret = -ENODEV,
+                   (priv->rom = pci_platform_rom(pdev, &priv->size)))
+                       return priv;
+               kfree(priv);
+       }
+
+       return ERR_PTR(ret);
+}
+
+const struct nvbios_source
+nvbios_platform = {
+       .name = "PLATFORM",
+       .init = platform_init,
+       .fini = (void(*)(void *))kfree,
+       .read = pcirom_read,
+       .rw = true,
+};
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/bios/shadowramin.c b/drivers/gpu/drm/nouveau/nvkm/subdev/bios/shadowramin.c
new file mode 100644 (file)
index 0000000..abe8ae4
--- /dev/null
@@ -0,0 +1,115 @@
+/*
+ * Copyright 2012 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.
+ *
+ */
+#include "priv.h"
+
+#include <core/device.h>
+
+struct priv {
+       struct nvkm_bios *bios;
+       u32 bar0;
+};
+
+static u32
+pramin_read(void *data, u32 offset, u32 length, struct nvkm_bios *bios)
+{
+       u32 i;
+       if (offset + length <= 0x00100000) {
+               for (i = offset; i < offset + length; i += 4)
+                       *(u32 *)&bios->data[i] = nv_rd32(bios, 0x700000 + i);
+               return length;
+       }
+       return 0;
+}
+
+static void
+pramin_fini(void *data)
+{
+       struct priv *priv = data;
+       if (priv) {
+               nv_wr32(priv->bios, 0x001700, priv->bar0);
+               kfree(priv);
+       }
+}
+
+static void *
+pramin_init(struct nvkm_bios *bios, const char *name)
+{
+       struct priv *priv = NULL;
+       u64 addr = 0;
+
+       /* PRAMIN always potentially available prior to nv50 */
+       if (nv_device(bios)->card_type < NV_50)
+               return NULL;
+
+       /* we can't get the bios image pointer without PDISP */
+       if (nv_device(bios)->card_type >= GM100)
+               addr = nv_rd32(bios, 0x021c04);
+       else
+       if (nv_device(bios)->card_type >= NV_C0)
+               addr = nv_rd32(bios, 0x022500);
+       if (addr & 0x00000001) {
+               nv_debug(bios, "... display disabled\n");
+               return ERR_PTR(-ENODEV);
+       }
+
+       /* check that the window is enabled and in vram, particularly
+        * important as we don't want to be touching vram on an
+        * uninitialised board
+        */
+       addr = nv_rd32(bios, 0x619f04);
+       if (!(addr & 0x00000008)) {
+               nv_debug(bios, "... not enabled\n");
+               return ERR_PTR(-ENODEV);
+       }
+       if ( (addr & 0x00000003) != 1) {
+               nv_debug(bios, "... not in vram\n");
+               return ERR_PTR(-ENODEV);
+       }
+
+       /* some alternate method inherited from xf86-video-nv... */
+       addr = (addr & 0xffffff00) << 8;
+       if (!addr) {
+               addr  = (u64)nv_rd32(bios, 0x001700) << 16;
+               addr += 0xf0000;
+       }
+
+       /* modify bar0 PRAMIN window to cover the bios image */
+       if (!(priv = kmalloc(sizeof(*priv), GFP_KERNEL))) {
+               nv_error(bios, "... out of memory\n");
+               return ERR_PTR(-ENOMEM);
+       }
+
+       priv->bios = bios;
+       priv->bar0 = nv_rd32(bios, 0x001700);
+       nv_wr32(bios, 0x001700, addr >> 16);
+       return priv;
+}
+
+const struct nvbios_source
+nvbios_ramin = {
+       .name = "PRAMIN",
+       .init = pramin_init,
+       .fini = pramin_fini,
+       .read = pramin_read,
+       .rw = true,
+};
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/bios/shadowrom.c b/drivers/gpu/drm/nouveau/nvkm/subdev/bios/shadowrom.c
new file mode 100644 (file)
index 0000000..6ec3b23
--- /dev/null
@@ -0,0 +1,70 @@
+/*
+ * Copyright 2012 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.
+ *
+ */
+#include "priv.h"
+
+#include <core/device.h>
+
+static u32
+prom_read(void *data, u32 offset, u32 length, struct nvkm_bios *bios)
+{
+       u32 i;
+       if (offset + length <= 0x00100000) {
+               for (i = offset; i < offset + length; i += 4)
+                       *(u32 *)&bios->data[i] = nv_rd32(bios, 0x300000 + i);
+               return length;
+       }
+       return 0;
+}
+
+static void
+prom_fini(void *data)
+{
+       struct nvkm_bios *bios = data;
+       if (nv_device(bios)->card_type < NV_50)
+               nv_mask(bios, 0x001850, 0x00000001, 0x00000001);
+       else
+               nv_mask(bios, 0x088050, 0x00000001, 0x00000001);
+}
+
+static void *
+prom_init(struct nvkm_bios *bios, const char *name)
+{
+       if (nv_device(bios)->card_type < NV_50) {
+               if (nv_device(bios)->card_type == NV_40 &&
+                   nv_device(bios)->chipset >= 0x4c)
+                       return ERR_PTR(-ENODEV);
+               nv_mask(bios, 0x001850, 0x00000001, 0x00000000);
+       } else {
+               nv_mask(bios, 0x088050, 0x00000001, 0x00000000);
+       }
+       return bios;
+}
+
+const struct nvbios_source
+nvbios_rom = {
+       .name = "PROM",
+       .init = prom_init,
+       .fini = prom_fini,
+       .read = prom_read,
+       .rw = false,
+};
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/bios/therm.c b/drivers/gpu/drm/nouveau/nvkm/subdev/bios/therm.c
new file mode 100644 (file)
index 0000000..249ff6d
--- /dev/null
@@ -0,0 +1,214 @@
+/*
+ * Copyright 2012 Nouveau Community
+ *
+ * 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 <subdev/bios.h>
+#include <subdev/bios/bit.h>
+#include <subdev/bios/therm.h>
+
+#include <core/device.h>
+
+static u16
+therm_table(struct nvkm_bios *bios, u8 *ver, u8 *hdr, u8 *len, u8 *cnt)
+{
+       struct bit_entry bit_P;
+       u16 therm = 0;
+
+       if (!bit_entry(bios, 'P', &bit_P)) {
+               if (bit_P.version == 1)
+                       therm = nv_ro16(bios, bit_P.offset + 12);
+               else if (bit_P.version == 2)
+                       therm = nv_ro16(bios, bit_P.offset + 16);
+               else
+                       nv_error(bios,
+                               "unknown offset for thermal in BIT P %d\n",
+                               bit_P.version);
+       }
+
+       /* exit now if we haven't found the thermal table */
+       if (!therm)
+               return 0x0000;
+
+       *ver = nv_ro08(bios, therm + 0);
+       *hdr = nv_ro08(bios, therm + 1);
+       *len = nv_ro08(bios, therm + 2);
+       *cnt = nv_ro08(bios, therm + 3);
+       return therm + nv_ro08(bios, therm + 1);
+}
+
+static u16
+nvbios_therm_entry(struct nvkm_bios *bios, int idx, u8 *ver, u8 *len)
+{
+       u8 hdr, cnt;
+       u16 therm = therm_table(bios, ver, &hdr, len, &cnt);
+       if (therm && idx < cnt)
+               return therm + idx * *len;
+       return 0x0000;
+}
+
+int
+nvbios_therm_sensor_parse(struct nvkm_bios *bios,
+                         enum nvbios_therm_domain domain,
+                         struct nvbios_therm_sensor *sensor)
+{
+       s8 thrs_section, sensor_section, offset;
+       u8 ver, len, i;
+       u16 entry;
+
+       /* we only support the core domain for now */
+       if (domain != NVBIOS_THERM_DOMAIN_CORE)
+               return -EINVAL;
+
+       /* Read the entries from the table */
+       thrs_section = 0;
+       sensor_section = -1;
+       i = 0;
+       while ((entry = nvbios_therm_entry(bios, i++, &ver, &len))) {
+               s16 value = nv_ro16(bios, entry + 1);
+
+               switch (nv_ro08(bios, entry + 0)) {
+               case 0x0:
+                       thrs_section = value;
+                       if (value > 0)
+                               return 0; /* we do not try to support ambient */
+                       break;
+               case 0x01:
+                       sensor_section++;
+                       if (sensor_section == 0) {
+                               offset = ((s8) nv_ro08(bios, entry + 2)) / 2;
+                               sensor->offset_constant = offset;
+                       }
+                       break;
+
+               case 0x04:
+                       if (thrs_section == 0) {
+                               sensor->thrs_critical.temp = (value & 0xff0) >> 4;
+                               sensor->thrs_critical.hysteresis = value & 0xf;
+                       }
+                       break;
+
+               case 0x07:
+                       if (thrs_section == 0) {
+                               sensor->thrs_down_clock.temp = (value & 0xff0) >> 4;
+                               sensor->thrs_down_clock.hysteresis = value & 0xf;
+                       }
+                       break;
+
+               case 0x08:
+                       if (thrs_section == 0) {
+                               sensor->thrs_fan_boost.temp = (value & 0xff0) >> 4;
+                               sensor->thrs_fan_boost.hysteresis = value & 0xf;
+                       }
+                       break;
+
+               case 0x10:
+                       if (sensor_section == 0)
+                               sensor->offset_num = value;
+                       break;
+
+               case 0x11:
+                       if (sensor_section == 0)
+                               sensor->offset_den = value;
+                       break;
+
+               case 0x12:
+                       if (sensor_section == 0)
+                               sensor->slope_mult = value;
+                       break;
+
+               case 0x13:
+                       if (sensor_section == 0)
+                               sensor->slope_div = value;
+                       break;
+               case 0x32:
+                       if (thrs_section == 0) {
+                               sensor->thrs_shutdown.temp = (value & 0xff0) >> 4;
+                               sensor->thrs_shutdown.hysteresis = value & 0xf;
+                       }
+                       break;
+               }
+       }
+
+       return 0;
+}
+
+int
+nvbios_therm_fan_parse(struct nvkm_bios *bios, struct nvbios_therm_fan *fan)
+{
+       struct nvbios_therm_trip_point *cur_trip = NULL;
+       u8 ver, len, i;
+       u16 entry;
+
+       uint8_t duty_lut[] = { 0, 0, 25, 0, 40, 0, 50, 0,
+                               75, 0, 85, 0, 100, 0, 100, 0 };
+
+       i = 0;
+       fan->nr_fan_trip = 0;
+       fan->fan_mode = NVBIOS_THERM_FAN_OTHER;
+       while ((entry = nvbios_therm_entry(bios, i++, &ver, &len))) {
+               s16 value = nv_ro16(bios, entry + 1);
+
+               switch (nv_ro08(bios, entry + 0)) {
+               case 0x22:
+                       fan->min_duty = value & 0xff;
+                       fan->max_duty = (value & 0xff00) >> 8;
+                       break;
+               case 0x24:
+                       fan->nr_fan_trip++;
+                       if (fan->fan_mode > NVBIOS_THERM_FAN_TRIP)
+                               fan->fan_mode = NVBIOS_THERM_FAN_TRIP;
+                       cur_trip = &fan->trip[fan->nr_fan_trip - 1];
+                       cur_trip->hysteresis = value & 0xf;
+                       cur_trip->temp = (value & 0xff0) >> 4;
+                       cur_trip->fan_duty = duty_lut[(value & 0xf000) >> 12];
+                       break;
+               case 0x25:
+                       cur_trip = &fan->trip[fan->nr_fan_trip - 1];
+                       cur_trip->fan_duty = value;
+                       break;
+               case 0x26:
+                       if (!fan->pwm_freq)
+                               fan->pwm_freq = value;
+                       break;
+               case 0x3b:
+                       fan->bump_period = value;
+                       break;
+               case 0x3c:
+                       fan->slow_down_period = value;
+                       break;
+               case 0x46:
+                       if (fan->fan_mode > NVBIOS_THERM_FAN_LINEAR)
+                               fan->fan_mode = NVBIOS_THERM_FAN_LINEAR;
+                       fan->linear_min_temp = nv_ro08(bios, entry + 1);
+                       fan->linear_max_temp = nv_ro08(bios, entry + 2);
+                       break;
+               }
+       }
+
+       /* starting from fermi, fan management is always linear */
+       if (nv_device(bios)->card_type >= NV_C0 &&
+               fan->fan_mode == NVBIOS_THERM_FAN_OTHER) {
+               fan->fan_mode = NVBIOS_THERM_FAN_LINEAR;
+       }
+
+       return 0;
+}
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/bios/timing.c b/drivers/gpu/drm/nouveau/nvkm/subdev/bios/timing.c
new file mode 100644 (file)
index 0000000..763fd29
--- /dev/null
@@ -0,0 +1,166 @@
+/*
+ * Copyright 2013 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 <subdev/bios.h>
+#include <subdev/bios/bit.h>
+#include <subdev/bios/timing.h>
+
+u16
+nvbios_timingTe(struct nvkm_bios *bios,
+               u8 *ver, u8 *hdr, u8 *cnt, u8 *len, u8 *snr, u8 *ssz)
+{
+       struct bit_entry bit_P;
+       u16 timing = 0x0000;
+
+       if (!bit_entry(bios, 'P', &bit_P)) {
+               if (bit_P.version == 1)
+                       timing = nv_ro16(bios, bit_P.offset + 4);
+               else
+               if (bit_P.version == 2)
+                       timing = nv_ro16(bios, bit_P.offset + 8);
+
+               if (timing) {
+                       *ver = nv_ro08(bios, timing + 0);
+                       switch (*ver) {
+                       case 0x10:
+                               *hdr = nv_ro08(bios, timing + 1);
+                               *cnt = nv_ro08(bios, timing + 2);
+                               *len = nv_ro08(bios, timing + 3);
+                               *snr = 0;
+                               *ssz = 0;
+                               return timing;
+                       case 0x20:
+                               *hdr = nv_ro08(bios, timing + 1);
+                               *cnt = nv_ro08(bios, timing + 5);
+                               *len = nv_ro08(bios, timing + 2);
+                               *snr = nv_ro08(bios, timing + 4);
+                               *ssz = nv_ro08(bios, timing + 3);
+                               return timing;
+                       default:
+                               break;
+                       }
+               }
+       }
+
+       return 0x0000;
+}
+
+u16
+nvbios_timingEe(struct nvkm_bios *bios, int idx,
+               u8 *ver, u8 *hdr, u8 *cnt, u8 *len)
+{
+       u8  snr, ssz;
+       u16 timing = nvbios_timingTe(bios, ver, hdr, cnt, len, &snr, &ssz);
+       if (timing && idx < *cnt) {
+               timing += *hdr + idx * (*len + (snr * ssz));
+               *hdr = *len;
+               *cnt = snr;
+               *len = ssz;
+               return timing;
+       }
+       return 0x0000;
+}
+
+u16
+nvbios_timingEp(struct nvkm_bios *bios, int idx,
+               u8 *ver, u8 *hdr, u8 *cnt, u8 *len, struct nvbios_ramcfg *p)
+{
+       u16 data = nvbios_timingEe(bios, idx, ver, hdr, cnt, len), temp;
+       p->timing_ver = *ver;
+       p->timing_hdr = *hdr;
+       switch (!!data * *ver) {
+       case 0x10:
+               p->timing_10_WR    = nv_ro08(bios, data + 0x00);
+               p->timing_10_WTR   = nv_ro08(bios, data + 0x01);
+               p->timing_10_CL    = nv_ro08(bios, data + 0x02);
+               p->timing_10_RC    = nv_ro08(bios, data + 0x03);
+               p->timing_10_RFC   = nv_ro08(bios, data + 0x05);
+               p->timing_10_RAS   = nv_ro08(bios, data + 0x07);
+               p->timing_10_RP    = nv_ro08(bios, data + 0x09);
+               p->timing_10_RCDRD = nv_ro08(bios, data + 0x0a);
+               p->timing_10_RCDWR = nv_ro08(bios, data + 0x0b);
+               p->timing_10_RRD   = nv_ro08(bios, data + 0x0c);
+               p->timing_10_13    = nv_ro08(bios, data + 0x0d);
+               p->timing_10_ODT   = nv_ro08(bios, data + 0x0e) & 0x07;
+
+               p->timing_10_24  = 0xff;
+               p->timing_10_21  = 0;
+               p->timing_10_20  = 0;
+               p->timing_10_CWL = 0;
+               p->timing_10_18  = 0;
+               p->timing_10_16  = 0;
+
+               switch (min_t(u8, *hdr, 25)) {
+               case 25:
+                       p->timing_10_24  = nv_ro08(bios, data + 0x18);
+               case 24:
+               case 23:
+               case 22:
+                       p->timing_10_21  = nv_ro08(bios, data + 0x15);
+               case 21:
+                       p->timing_10_20  = nv_ro08(bios, data + 0x14);
+               case 20:
+                       p->timing_10_CWL = nv_ro08(bios, data + 0x13);
+               case 19:
+                       p->timing_10_18  = nv_ro08(bios, data + 0x12);
+               case 18:
+               case 17:
+                       p->timing_10_16  = nv_ro08(bios, data + 0x10);
+               }
+
+               break;
+       case 0x20:
+               p->timing[0] = nv_ro32(bios, data + 0x00);
+               p->timing[1] = nv_ro32(bios, data + 0x04);
+               p->timing[2] = nv_ro32(bios, data + 0x08);
+               p->timing[3] = nv_ro32(bios, data + 0x0c);
+               p->timing[4] = nv_ro32(bios, data + 0x10);
+               p->timing[5] = nv_ro32(bios, data + 0x14);
+               p->timing[6] = nv_ro32(bios, data + 0x18);
+               p->timing[7] = nv_ro32(bios, data + 0x1c);
+               p->timing[8] = nv_ro32(bios, data + 0x20);
+               p->timing[9] = nv_ro32(bios, data + 0x24);
+               p->timing[10] = nv_ro32(bios, data + 0x28);
+               p->timing_20_2e_03 = (nv_ro08(bios, data + 0x2e) & 0x03) >> 0;
+               p->timing_20_2e_30 = (nv_ro08(bios, data + 0x2e) & 0x30) >> 4;
+               p->timing_20_2e_c0 = (nv_ro08(bios, data + 0x2e) & 0xc0) >> 6;
+               p->timing_20_2f_03 = (nv_ro08(bios, data + 0x2f) & 0x03) >> 0;
+               temp = nv_ro16(bios, data + 0x2c);
+               p->timing_20_2c_003f = (temp & 0x003f) >> 0;
+               p->timing_20_2c_1fc0 = (temp & 0x1fc0) >> 6;
+               p->timing_20_30_07 = (nv_ro08(bios, data + 0x30) & 0x07) >> 0;
+               p->timing_20_30_f8 = (nv_ro08(bios, data + 0x30) & 0xf8) >> 3;
+               temp = nv_ro16(bios, data + 0x31);
+               p->timing_20_31_0007 = (temp & 0x0007) >> 0;
+               p->timing_20_31_0078 = (temp & 0x0078) >> 3;
+               p->timing_20_31_0780 = (temp & 0x0780) >> 7;
+               p->timing_20_31_0800 = (temp & 0x0800) >> 11;
+               p->timing_20_31_7000 = (temp & 0x7000) >> 12;
+               p->timing_20_31_8000 = (temp & 0x8000) >> 15;
+               break;
+       default:
+               data = 0;
+               break;
+       }
+       return data;
+}
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/bios/vmap.c b/drivers/gpu/drm/nouveau/nvkm/subdev/bios/vmap.c
new file mode 100644 (file)
index 0000000..e95b69f
--- /dev/null
@@ -0,0 +1,111 @@
+/*
+ * Copyright 2012 Nouveau Community
+ *
+ * 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 <subdev/bios.h>
+#include <subdev/bios/bit.h>
+#include <subdev/bios/vmap.h>
+
+u16
+nvbios_vmap_table(struct nvkm_bios *bios, u8 *ver, u8 *hdr, u8 *cnt, u8 *len)
+{
+       struct bit_entry bit_P;
+       u16 vmap = 0x0000;
+
+       if (!bit_entry(bios, 'P', &bit_P)) {
+               if (bit_P.version == 2) {
+                       vmap = nv_ro16(bios, bit_P.offset + 0x20);
+                       if (vmap) {
+                               *ver = nv_ro08(bios, vmap + 0);
+                               switch (*ver) {
+                               case 0x10:
+                               case 0x20:
+                                       *hdr = nv_ro08(bios, vmap + 1);
+                                       *cnt = nv_ro08(bios, vmap + 3);
+                                       *len = nv_ro08(bios, vmap + 2);
+                                       return vmap;
+                               default:
+                                       break;
+                               }
+                       }
+               }
+       }
+
+       return 0x0000;
+}
+
+u16
+nvbios_vmap_parse(struct nvkm_bios *bios, u8 *ver, u8 *hdr, u8 *cnt, u8 *len,
+                 struct nvbios_vmap *info)
+{
+       u16 vmap = nvbios_vmap_table(bios, ver, hdr, cnt, len);
+       memset(info, 0x00, sizeof(*info));
+       switch (!!vmap * *ver) {
+       case 0x10:
+       case 0x20:
+               break;
+       }
+       return vmap;
+}
+
+u16
+nvbios_vmap_entry(struct nvkm_bios *bios, int idx, u8 *ver, u8 *len)
+{
+       u8  hdr, cnt;
+       u16 vmap = nvbios_vmap_table(bios, ver, &hdr, &cnt, len);
+       if (vmap && idx < cnt) {
+               vmap = vmap + hdr + (idx * *len);
+               return vmap;
+       }
+       return 0x0000;
+}
+
+u16
+nvbios_vmap_entry_parse(struct nvkm_bios *bios, int idx, u8 *ver, u8 *len,
+                       struct nvbios_vmap_entry *info)
+{
+       u16 vmap = nvbios_vmap_entry(bios, idx, ver, len);
+       memset(info, 0x00, sizeof(*info));
+       switch (!!vmap * *ver) {
+       case 0x10:
+               info->link   = 0xff;
+               info->min    = nv_ro32(bios, vmap + 0x00);
+               info->max    = nv_ro32(bios, vmap + 0x04);
+               info->arg[0] = nv_ro32(bios, vmap + 0x08);
+               info->arg[1] = nv_ro32(bios, vmap + 0x0c);
+               info->arg[2] = nv_ro32(bios, vmap + 0x10);
+               break;
+       case 0x20:
+               info->unk0   = nv_ro08(bios, vmap + 0x00);
+               info->link   = nv_ro08(bios, vmap + 0x01);
+               info->min    = nv_ro32(bios, vmap + 0x02);
+               info->max    = nv_ro32(bios, vmap + 0x06);
+               info->arg[0] = nv_ro32(bios, vmap + 0x0a);
+               info->arg[1] = nv_ro32(bios, vmap + 0x0e);
+               info->arg[2] = nv_ro32(bios, vmap + 0x12);
+               info->arg[3] = nv_ro32(bios, vmap + 0x16);
+               info->arg[4] = nv_ro32(bios, vmap + 0x1a);
+               info->arg[5] = nv_ro32(bios, vmap + 0x1e);
+               break;
+       }
+       return vmap;
+}
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/bios/volt.c b/drivers/gpu/drm/nouveau/nvkm/subdev/bios/volt.c
new file mode 100644 (file)
index 0000000..8454ab7
--- /dev/null
@@ -0,0 +1,136 @@
+/*
+ * Copyright 2012 Nouveau Community
+ *
+ * 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 <subdev/bios.h>
+#include <subdev/bios/bit.h>
+#include <subdev/bios/volt.h>
+
+u16
+nvbios_volt_table(struct nvkm_bios *bios, u8 *ver, u8 *hdr, u8 *cnt, u8 *len)
+{
+       struct bit_entry bit_P;
+       u16 volt = 0x0000;
+
+       if (!bit_entry(bios, 'P', &bit_P)) {
+               if (bit_P.version == 2)
+                       volt = nv_ro16(bios, bit_P.offset + 0x0c);
+               else
+               if (bit_P.version == 1)
+                       volt = nv_ro16(bios, bit_P.offset + 0x10);
+
+               if (volt) {
+                       *ver = nv_ro08(bios, volt + 0);
+                       switch (*ver) {
+                       case 0x12:
+                               *hdr = 5;
+                               *cnt = nv_ro08(bios, volt + 2);
+                               *len = nv_ro08(bios, volt + 1);
+                               return volt;
+                       case 0x20:
+                               *hdr = nv_ro08(bios, volt + 1);
+                               *cnt = nv_ro08(bios, volt + 2);
+                               *len = nv_ro08(bios, volt + 3);
+                               return volt;
+                       case 0x30:
+                       case 0x40:
+                       case 0x50:
+                               *hdr = nv_ro08(bios, volt + 1);
+                               *cnt = nv_ro08(bios, volt + 3);
+                               *len = nv_ro08(bios, volt + 2);
+                               return volt;
+                       }
+               }
+       }
+
+       return 0x0000;
+}
+
+u16
+nvbios_volt_parse(struct nvkm_bios *bios, u8 *ver, u8 *hdr, u8 *cnt, u8 *len,
+                 struct nvbios_volt *info)
+{
+       u16 volt = nvbios_volt_table(bios, ver, hdr, cnt, len);
+       memset(info, 0x00, sizeof(*info));
+       switch (!!volt * *ver) {
+       case 0x12:
+               info->vidmask = nv_ro08(bios, volt + 0x04);
+               break;
+       case 0x20:
+               info->vidmask = nv_ro08(bios, volt + 0x05);
+               break;
+       case 0x30:
+               info->vidmask = nv_ro08(bios, volt + 0x04);
+               break;
+       case 0x40:
+               info->base    = nv_ro32(bios, volt + 0x04);
+               info->step    = nv_ro16(bios, volt + 0x08);
+               info->vidmask = nv_ro08(bios, volt + 0x0b);
+               /*XXX*/
+               info->min     = 0;
+               info->max     = info->base;
+               break;
+       case 0x50:
+               info->vidmask = nv_ro08(bios, volt + 0x06);
+               info->min     = nv_ro32(bios, volt + 0x0a);
+               info->max     = nv_ro32(bios, volt + 0x0e);
+               info->base    = nv_ro32(bios, volt + 0x12) & 0x00ffffff;
+               info->step    = nv_ro16(bios, volt + 0x16);
+               break;
+       }
+       return volt;
+}
+
+u16
+nvbios_volt_entry(struct nvkm_bios *bios, int idx, u8 *ver, u8 *len)
+{
+       u8  hdr, cnt;
+       u16 volt = nvbios_volt_table(bios, ver, &hdr, &cnt, len);
+       if (volt && idx < cnt) {
+               volt = volt + hdr + (idx * *len);
+               return volt;
+       }
+       return 0x0000;
+}
+
+u16
+nvbios_volt_entry_parse(struct nvkm_bios *bios, int idx, u8 *ver, u8 *len,
+                       struct nvbios_volt_entry *info)
+{
+       u16 volt = nvbios_volt_entry(bios, idx, ver, len);
+       memset(info, 0x00, sizeof(*info));
+       switch (!!volt * *ver) {
+       case 0x12:
+       case 0x20:
+               info->voltage = nv_ro08(bios, volt + 0x00) * 10000;
+               info->vid     = nv_ro08(bios, volt + 0x01);
+               break;
+       case 0x30:
+               info->voltage = nv_ro08(bios, volt + 0x00) * 10000;
+               info->vid     = nv_ro08(bios, volt + 0x01) >> 2;
+               break;
+       case 0x40:
+       case 0x50:
+               break;
+       }
+       return volt;
+}
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/bios/xpio.c b/drivers/gpu/drm/nouveau/nvkm/subdev/bios/xpio.c
new file mode 100644 (file)
index 0000000..63a5e1b
--- /dev/null
@@ -0,0 +1,74 @@
+/*
+ * Copyright 2012 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 <subdev/bios.h>
+#include <subdev/bios/gpio.h>
+#include <subdev/bios/xpio.h>
+
+static u16
+dcb_xpiod_table(struct nvkm_bios *bios, u8 *ver, u8 *hdr, u8 *cnt, u8 *len)
+{
+       u16 data = dcb_gpio_table(bios, ver, hdr, cnt, len);
+       if (data && *ver >= 0x40 && *hdr >= 0x06) {
+               u16 xpio = nv_ro16(bios, data + 0x04);
+               if (xpio) {
+                       *ver = nv_ro08(bios, data + 0x00);
+                       *hdr = nv_ro08(bios, data + 0x01);
+                       *cnt = nv_ro08(bios, data + 0x02);
+                       *len = nv_ro08(bios, data + 0x03);
+                       return xpio;
+               }
+       }
+       return 0x0000;
+}
+
+u16
+dcb_xpio_table(struct nvkm_bios *bios, u8 idx,
+              u8 *ver, u8 *hdr, u8 *cnt, u8 *len)
+{
+       u16 data = dcb_xpiod_table(bios, ver, hdr, cnt, len);
+       if (data && idx < *cnt) {
+               u16 xpio = nv_ro16(bios, data + *hdr + (idx * *len));
+               if (xpio) {
+                       *ver = nv_ro08(bios, data + 0x00);
+                       *hdr = nv_ro08(bios, data + 0x01);
+                       *cnt = nv_ro08(bios, data + 0x02);
+                       *len = nv_ro08(bios, data + 0x03);
+                       return xpio;
+               }
+       }
+       return 0x0000;
+}
+
+u16
+dcb_xpio_parse(struct nvkm_bios *bios, u8 idx,
+              u8 *ver, u8 *hdr, u8 *cnt, u8 *len, struct nvbios_xpio *info)
+{
+       u16 data = dcb_xpio_table(bios, idx, ver, hdr, cnt, len);
+       if (data && *len >= 6) {
+               info->type = nv_ro08(bios, data + 0x04);
+               info->addr = nv_ro08(bios, data + 0x05);
+               info->flags = nv_ro08(bios, data + 0x06);
+       }
+       return 0x0000;
+}
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/bus/Kbuild b/drivers/gpu/drm/nouveau/nvkm/subdev/bus/Kbuild
new file mode 100644 (file)
index 0000000..83d80b1
--- /dev/null
@@ -0,0 +1,6 @@
+nvkm-y += nvkm/subdev/bus/hwsq.o
+nvkm-y += nvkm/subdev/bus/nv04.o
+nvkm-y += nvkm/subdev/bus/nv31.o
+nvkm-y += nvkm/subdev/bus/nv50.o
+nvkm-y += nvkm/subdev/bus/g94.o
+nvkm-y += nvkm/subdev/bus/gf100.o
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/bus/g94.c b/drivers/gpu/drm/nouveau/nvkm/subdev/bus/g94.c
new file mode 100644 (file)
index 0000000..cbe699e
--- /dev/null
@@ -0,0 +1,58 @@
+/*
+ * Copyright 2012 Nouveau Community
+ *
+ * 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 <martin.peres@labri.fr>
+ *          Ben Skeggs
+ */
+#include "nv04.h"
+
+#include <subdev/timer.h>
+
+static int
+g94_bus_hwsq_exec(struct nvkm_bus *pbus, u32 *data, u32 size)
+{
+       struct nv50_bus_priv *priv = (void *)pbus;
+       int i;
+
+       nv_mask(pbus, 0x001098, 0x00000008, 0x00000000);
+       nv_wr32(pbus, 0x001304, 0x00000000);
+       nv_wr32(pbus, 0x001318, 0x00000000);
+       for (i = 0; i < size; i++)
+               nv_wr32(priv, 0x080000 + (i * 4), data[i]);
+       nv_mask(pbus, 0x001098, 0x00000018, 0x00000018);
+       nv_wr32(pbus, 0x00130c, 0x00000001);
+
+       return nv_wait(pbus, 0x001308, 0x00000100, 0x00000000) ? 0 : -ETIMEDOUT;
+}
+
+struct nvkm_oclass *
+g94_bus_oclass = &(struct nv04_bus_impl) {
+       .base.handle = NV_SUBDEV(BUS, 0x94),
+       .base.ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = nv04_bus_ctor,
+               .dtor = _nvkm_bus_dtor,
+               .init = nv50_bus_init,
+               .fini = _nvkm_bus_fini,
+       },
+       .intr = nv50_bus_intr,
+       .hwsq_exec = g94_bus_hwsq_exec,
+       .hwsq_size = 128,
+}.base;
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/bus/gf100.c b/drivers/gpu/drm/nouveau/nvkm/subdev/bus/gf100.c
new file mode 100644 (file)
index 0000000..ebc63ba
--- /dev/null
@@ -0,0 +1,80 @@
+/*
+ * Copyright 2012 Nouveau Community
+ *
+ * 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 <martin.peres@labri.fr>
+ *          Ben Skeggs
+ */
+#include "nv04.h"
+
+static void
+gf100_bus_intr(struct nvkm_subdev *subdev)
+{
+       struct nvkm_bus *pbus = nvkm_bus(subdev);
+       u32 stat = nv_rd32(pbus, 0x001100) & nv_rd32(pbus, 0x001140);
+
+       if (stat & 0x0000000e) {
+               u32 addr = nv_rd32(pbus, 0x009084);
+               u32 data = nv_rd32(pbus, 0x009088);
+
+               nv_error(pbus, "MMIO %s of 0x%08x FAULT at 0x%06x [ %s%s%s]\n",
+                        (addr & 0x00000002) ? "write" : "read", data,
+                        (addr & 0x00fffffc),
+                        (stat & 0x00000002) ? "!ENGINE " : "",
+                        (stat & 0x00000004) ? "IBUS " : "",
+                        (stat & 0x00000008) ? "TIMEOUT " : "");
+
+               nv_wr32(pbus, 0x009084, 0x00000000);
+               nv_wr32(pbus, 0x001100, (stat & 0x0000000e));
+               stat &= ~0x0000000e;
+       }
+
+       if (stat) {
+               nv_error(pbus, "unknown intr 0x%08x\n", stat);
+               nv_mask(pbus, 0x001140, stat, 0x00000000);
+       }
+}
+
+static int
+gf100_bus_init(struct nvkm_object *object)
+{
+       struct nv04_bus_priv *priv = (void *)object;
+       int ret;
+
+       ret = nvkm_bus_init(&priv->base);
+       if (ret)
+               return ret;
+
+       nv_wr32(priv, 0x001100, 0xffffffff);
+       nv_wr32(priv, 0x001140, 0x0000000e);
+       return 0;
+}
+
+struct nvkm_oclass *
+gf100_bus_oclass = &(struct nv04_bus_impl) {
+       .base.handle = NV_SUBDEV(BUS, 0xc0),
+       .base.ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = nv04_bus_ctor,
+               .dtor = _nvkm_bus_dtor,
+               .init = gf100_bus_init,
+               .fini = _nvkm_bus_fini,
+       },
+       .intr = gf100_bus_intr,
+}.base;
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/bus/hwsq.c b/drivers/gpu/drm/nouveau/nvkm/subdev/bus/hwsq.c
new file mode 100644 (file)
index 0000000..b8853bf
--- /dev/null
@@ -0,0 +1,143 @@
+/*
+ * Copyright 2013 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 <bskeggs@redhat.com>
+ */
+#include <subdev/bus.h>
+
+struct nvkm_hwsq {
+       struct nvkm_bus *pbus;
+       u32 addr;
+       u32 data;
+       struct {
+               u8 data[512];
+               u8 size;
+       } c;
+};
+
+static void
+hwsq_cmd(struct nvkm_hwsq *hwsq, int size, u8 data[])
+{
+       memcpy(&hwsq->c.data[hwsq->c.size], data, size * sizeof(data[0]));
+       hwsq->c.size += size;
+}
+
+int
+nvkm_hwsq_init(struct nvkm_bus *pbus, struct nvkm_hwsq **phwsq)
+{
+       struct nvkm_hwsq *hwsq;
+
+       hwsq = *phwsq = kmalloc(sizeof(*hwsq), GFP_KERNEL);
+       if (hwsq) {
+               hwsq->pbus = pbus;
+               hwsq->addr = ~0;
+               hwsq->data = ~0;
+               memset(hwsq->c.data, 0x7f, sizeof(hwsq->c.data));
+               hwsq->c.size = 0;
+       }
+
+       return hwsq ? 0 : -ENOMEM;
+}
+
+int
+nvkm_hwsq_fini(struct nvkm_hwsq **phwsq, bool exec)
+{
+       struct nvkm_hwsq *hwsq = *phwsq;
+       int ret = 0, i;
+       if (hwsq) {
+               struct nvkm_bus *pbus = hwsq->pbus;
+               hwsq->c.size = (hwsq->c.size + 4) / 4;
+               if (hwsq->c.size <= pbus->hwsq_size) {
+                       if (exec)
+                               ret = pbus->hwsq_exec(pbus, (u32 *)hwsq->c.data,
+                                                     hwsq->c.size);
+                       if (ret)
+                               nv_error(pbus, "hwsq exec failed: %d\n", ret);
+               } else {
+                       nv_error(pbus, "hwsq ucode too large\n");
+                       ret = -ENOSPC;
+               }
+
+               for (i = 0; ret && i < hwsq->c.size; i++)
+                       nv_error(pbus, "\t0x%08x\n", ((u32 *)hwsq->c.data)[i]);
+
+               *phwsq = NULL;
+               kfree(hwsq);
+       }
+       return ret;
+}
+
+void
+nvkm_hwsq_wr32(struct nvkm_hwsq *hwsq, u32 addr, u32 data)
+{
+       nv_debug(hwsq->pbus, "R[%06x] = 0x%08x\n", addr, data);
+
+       if (hwsq->data != data) {
+               if ((data & 0xffff0000) != (hwsq->data & 0xffff0000)) {
+                       hwsq_cmd(hwsq, 5, (u8[]){ 0xe2, data, data >> 8,
+                                                 data >> 16, data >> 24 });
+               } else {
+                       hwsq_cmd(hwsq, 3, (u8[]){ 0x42, data, data >> 8 });
+               }
+       }
+
+       if ((addr & 0xffff0000) != (hwsq->addr & 0xffff0000)) {
+               hwsq_cmd(hwsq, 5, (u8[]){ 0xe0, addr, addr >> 8,
+                                         addr >> 16, addr >> 24 });
+       } else {
+               hwsq_cmd(hwsq, 3, (u8[]){ 0x40, addr, addr >> 8 });
+       }
+
+       hwsq->addr = addr;
+       hwsq->data = data;
+}
+
+void
+nvkm_hwsq_setf(struct nvkm_hwsq *hwsq, u8 flag, int data)
+{
+       nv_debug(hwsq->pbus, " FLAG[%02x] = %d\n", flag, data);
+       flag += 0x80;
+       if (data >= 0)
+               flag += 0x20;
+       if (data >= 1)
+               flag += 0x20;
+       hwsq_cmd(hwsq, 1, (u8[]){ flag });
+}
+
+void
+nvkm_hwsq_wait(struct nvkm_hwsq *hwsq, u8 flag, u8 data)
+{
+       nv_debug(hwsq->pbus, " WAIT[%02x] = %d\n", flag, data);
+       hwsq_cmd(hwsq, 3, (u8[]){ 0x5f, flag, data });
+}
+
+void
+nvkm_hwsq_nsec(struct nvkm_hwsq *hwsq, u32 nsec)
+{
+       u8 shift = 0, usec = nsec / 1000;
+       while (usec & ~3) {
+               usec >>= 2;
+               shift++;
+       }
+
+       nv_debug(hwsq->pbus, "    DELAY = %d ns\n", nsec);
+       hwsq_cmd(hwsq, 1, (u8[]){ 0x00 | (shift << 2) | usec });
+}
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/bus/hwsq.h b/drivers/gpu/drm/nouveau/nvkm/subdev/bus/hwsq.h
new file mode 100644 (file)
index 0000000..3394a5e
--- /dev/null
@@ -0,0 +1,111 @@
+#ifndef __NVKM_BUS_HWSQ_H__
+#define __NVKM_BUS_HWSQ_H__
+#include <subdev/bus.h>
+
+struct hwsq {
+       struct nvkm_subdev *subdev;
+       struct nvkm_hwsq *hwsq;
+       int sequence;
+};
+
+struct hwsq_reg {
+       int sequence;
+       bool force;
+       u32 addr[2];
+       u32 data;
+};
+
+static inline struct hwsq_reg
+hwsq_reg2(u32 addr1, u32 addr2)
+{
+       return (struct hwsq_reg) {
+               .sequence = 0,
+               .force = 0,
+               .addr = { addr1, addr2 },
+               .data = 0xdeadbeef,
+       };
+}
+
+static inline struct hwsq_reg
+hwsq_reg(u32 addr)
+{
+       return hwsq_reg2(addr, addr);
+}
+
+static inline int
+hwsq_init(struct hwsq *ram, struct nvkm_subdev *subdev)
+{
+       struct nvkm_bus *pbus = nvkm_bus(subdev);
+       int ret;
+
+       ret = nvkm_hwsq_init(pbus, &ram->hwsq);
+       if (ret)
+               return ret;
+
+       ram->sequence++;
+       ram->subdev = subdev;
+       return 0;
+}
+
+static inline int
+hwsq_exec(struct hwsq *ram, bool exec)
+{
+       int ret = 0;
+       if (ram->subdev) {
+               ret = nvkm_hwsq_fini(&ram->hwsq, exec);
+               ram->subdev = NULL;
+       }
+       return ret;
+}
+
+static inline u32
+hwsq_rd32(struct hwsq *ram, struct hwsq_reg *reg)
+{
+       if (reg->sequence != ram->sequence)
+               reg->data = nv_rd32(ram->subdev, reg->addr[0]);
+       return reg->data;
+}
+
+static inline void
+hwsq_wr32(struct hwsq *ram, struct hwsq_reg *reg, u32 data)
+{
+       reg->sequence = ram->sequence;
+       reg->data = data;
+       if (reg->addr[0] != reg->addr[1])
+               nvkm_hwsq_wr32(ram->hwsq, reg->addr[1], reg->data);
+       nvkm_hwsq_wr32(ram->hwsq, reg->addr[0], reg->data);
+}
+
+static inline void
+hwsq_nuke(struct hwsq *ram, struct hwsq_reg *reg)
+{
+       reg->force = true;
+}
+
+static inline u32
+hwsq_mask(struct hwsq *ram, struct hwsq_reg *reg, u32 mask, u32 data)
+{
+       u32 temp = hwsq_rd32(ram, reg);
+       if (temp != ((temp & ~mask) | data) || reg->force)
+               hwsq_wr32(ram, reg, (temp & ~mask) | data);
+       return temp;
+}
+
+static inline void
+hwsq_setf(struct hwsq *ram, u8 flag, int data)
+{
+       nvkm_hwsq_setf(ram->hwsq, flag, data);
+}
+
+static inline void
+hwsq_wait(struct hwsq *ram, u8 flag, u8 data)
+{
+       nvkm_hwsq_wait(ram->hwsq, flag, data);
+}
+
+static inline void
+hwsq_nsec(struct hwsq *ram, u32 nsec)
+{
+       nvkm_hwsq_nsec(ram->hwsq, nsec);
+}
+#endif
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/bus/nv04.c b/drivers/gpu/drm/nouveau/nvkm/subdev/bus/nv04.c
new file mode 100644 (file)
index 0000000..19c8e50
--- /dev/null
@@ -0,0 +1,94 @@
+/*
+ * Copyright 2012 Nouveau Community
+ *
+ * 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 <martin.peres@labri.fr>
+ *          Ben Skeggs
+ */
+#include "nv04.h"
+
+static void
+nv04_bus_intr(struct nvkm_subdev *subdev)
+{
+       struct nvkm_bus *pbus = nvkm_bus(subdev);
+       u32 stat = nv_rd32(pbus, 0x001100) & nv_rd32(pbus, 0x001140);
+
+       if (stat & 0x00000001) {
+               nv_error(pbus, "BUS ERROR\n");
+               stat &= ~0x00000001;
+               nv_wr32(pbus, 0x001100, 0x00000001);
+       }
+
+       if (stat & 0x00000110) {
+               subdev = nvkm_subdev(subdev, NVDEV_SUBDEV_GPIO);
+               if (subdev && subdev->intr)
+                       subdev->intr(subdev);
+               stat &= ~0x00000110;
+               nv_wr32(pbus, 0x001100, 0x00000110);
+       }
+
+       if (stat) {
+               nv_error(pbus, "unknown intr 0x%08x\n", stat);
+               nv_mask(pbus, 0x001140, stat, 0x00000000);
+       }
+}
+
+static int
+nv04_bus_init(struct nvkm_object *object)
+{
+       struct nv04_bus_priv *priv = (void *)object;
+
+       nv_wr32(priv, 0x001100, 0xffffffff);
+       nv_wr32(priv, 0x001140, 0x00000111);
+
+       return nvkm_bus_init(&priv->base);
+}
+
+int
+nv04_bus_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+             struct nvkm_oclass *oclass, void *data, u32 size,
+             struct nvkm_object **pobject)
+{
+       struct nv04_bus_impl *impl = (void *)oclass;
+       struct nv04_bus_priv *priv;
+       int ret;
+
+       ret = nvkm_bus_create(parent, engine, oclass, &priv);
+       *pobject = nv_object(priv);
+       if (ret)
+               return ret;
+
+       nv_subdev(priv)->intr = impl->intr;
+       priv->base.hwsq_exec = impl->hwsq_exec;
+       priv->base.hwsq_size = impl->hwsq_size;
+       return 0;
+}
+
+struct nvkm_oclass *
+nv04_bus_oclass = &(struct nv04_bus_impl) {
+       .base.handle = NV_SUBDEV(BUS, 0x04),
+       .base.ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = nv04_bus_ctor,
+               .dtor = _nvkm_bus_dtor,
+               .init = nv04_bus_init,
+               .fini = _nvkm_bus_fini,
+       },
+       .intr = nv04_bus_intr,
+}.base;
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/bus/nv04.h b/drivers/gpu/drm/nouveau/nvkm/subdev/bus/nv04.h
new file mode 100644 (file)
index 0000000..3ddc8f9
--- /dev/null
@@ -0,0 +1,21 @@
+#ifndef __NVKM_BUS_NV04_H__
+#define __NVKM_BUS_NV04_H__
+#include <subdev/bus.h>
+
+struct nv04_bus_priv {
+       struct nvkm_bus base;
+};
+
+int  nv04_bus_ctor(struct nvkm_object *, struct nvkm_object *,
+                  struct nvkm_oclass *, void *, u32,
+                  struct nvkm_object **);
+int  nv50_bus_init(struct nvkm_object *);
+void nv50_bus_intr(struct nvkm_subdev *);
+
+struct nv04_bus_impl {
+       struct nvkm_oclass base;
+       void (*intr)(struct nvkm_subdev *);
+       int  (*hwsq_exec)(struct nvkm_bus *, u32 *, u32);
+       u32  hwsq_size;
+};
+#endif
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/bus/nv31.c b/drivers/gpu/drm/nouveau/nvkm/subdev/bus/nv31.c
new file mode 100644 (file)
index 0000000..c5739bc
--- /dev/null
@@ -0,0 +1,91 @@
+/*
+ * Copyright 2012 Nouveau Community
+ *
+ * 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 <martin.peres@labri.fr>
+ *          Ben Skeggs
+ */
+#include "nv04.h"
+
+static void
+nv31_bus_intr(struct nvkm_subdev *subdev)
+{
+       struct nvkm_bus *pbus = nvkm_bus(subdev);
+       u32 stat = nv_rd32(pbus, 0x001100) & nv_rd32(pbus, 0x001140);
+       u32 gpio = nv_rd32(pbus, 0x001104) & nv_rd32(pbus, 0x001144);
+
+       if (gpio) {
+               subdev = nvkm_subdev(pbus, NVDEV_SUBDEV_GPIO);
+               if (subdev && subdev->intr)
+                       subdev->intr(subdev);
+       }
+
+       if (stat & 0x00000008) {  /* NV41- */
+               u32 addr = nv_rd32(pbus, 0x009084);
+               u32 data = nv_rd32(pbus, 0x009088);
+
+               nv_error(pbus, "MMIO %s of 0x%08x FAULT at 0x%06x\n",
+                        (addr & 0x00000002) ? "write" : "read", data,
+                        (addr & 0x00fffffc));
+
+               stat &= ~0x00000008;
+               nv_wr32(pbus, 0x001100, 0x00000008);
+       }
+
+       if (stat & 0x00070000) {
+               subdev = nvkm_subdev(pbus, NVDEV_SUBDEV_THERM);
+               if (subdev && subdev->intr)
+                       subdev->intr(subdev);
+               stat &= ~0x00070000;
+               nv_wr32(pbus, 0x001100, 0x00070000);
+       }
+
+       if (stat) {
+               nv_error(pbus, "unknown intr 0x%08x\n", stat);
+               nv_mask(pbus, 0x001140, stat, 0x00000000);
+       }
+}
+
+static int
+nv31_bus_init(struct nvkm_object *object)
+{
+       struct nv04_bus_priv *priv = (void *)object;
+       int ret;
+
+       ret = nvkm_bus_init(&priv->base);
+       if (ret)
+               return ret;
+
+       nv_wr32(priv, 0x001100, 0xffffffff);
+       nv_wr32(priv, 0x001140, 0x00070008);
+       return 0;
+}
+
+struct nvkm_oclass *
+nv31_bus_oclass = &(struct nv04_bus_impl) {
+       .base.handle = NV_SUBDEV(BUS, 0x31),
+       .base.ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = nv04_bus_ctor,
+               .dtor = _nvkm_bus_dtor,
+               .init = nv31_bus_init,
+               .fini = _nvkm_bus_fini,
+       },
+       .intr = nv31_bus_intr,
+}.base;
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/bus/nv50.c b/drivers/gpu/drm/nouveau/nvkm/subdev/bus/nv50.c
new file mode 100644 (file)
index 0000000..1987863
--- /dev/null
@@ -0,0 +1,104 @@
+/*
+ * Copyright 2012 Nouveau Community
+ *
+ * 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 <martin.peres@labri.fr>
+ *          Ben Skeggs
+ */
+#include "nv04.h"
+
+#include <subdev/timer.h>
+
+static int
+nv50_bus_hwsq_exec(struct nvkm_bus *pbus, u32 *data, u32 size)
+{
+       struct nv50_bus_priv *priv = (void *)pbus;
+       int i;
+
+       nv_mask(pbus, 0x001098, 0x00000008, 0x00000000);
+       nv_wr32(pbus, 0x001304, 0x00000000);
+       for (i = 0; i < size; i++)
+               nv_wr32(priv, 0x001400 + (i * 4), data[i]);
+       nv_mask(pbus, 0x001098, 0x00000018, 0x00000018);
+       nv_wr32(pbus, 0x00130c, 0x00000003);
+
+       return nv_wait(pbus, 0x001308, 0x00000100, 0x00000000) ? 0 : -ETIMEDOUT;
+}
+
+void
+nv50_bus_intr(struct nvkm_subdev *subdev)
+{
+       struct nvkm_bus *pbus = nvkm_bus(subdev);
+       u32 stat = nv_rd32(pbus, 0x001100) & nv_rd32(pbus, 0x001140);
+
+       if (stat & 0x00000008) {
+               u32 addr = nv_rd32(pbus, 0x009084);
+               u32 data = nv_rd32(pbus, 0x009088);
+
+               nv_error(pbus, "MMIO %s of 0x%08x FAULT at 0x%06x\n",
+                        (addr & 0x00000002) ? "write" : "read", data,
+                        (addr & 0x00fffffc));
+
+               stat &= ~0x00000008;
+               nv_wr32(pbus, 0x001100, 0x00000008);
+       }
+
+       if (stat & 0x00010000) {
+               subdev = nvkm_subdev(pbus, NVDEV_SUBDEV_THERM);
+               if (subdev && subdev->intr)
+                       subdev->intr(subdev);
+               stat &= ~0x00010000;
+               nv_wr32(pbus, 0x001100, 0x00010000);
+       }
+
+       if (stat) {
+               nv_error(pbus, "unknown intr 0x%08x\n", stat);
+               nv_mask(pbus, 0x001140, stat, 0);
+       }
+}
+
+int
+nv50_bus_init(struct nvkm_object *object)
+{
+       struct nv04_bus_priv *priv = (void *)object;
+       int ret;
+
+       ret = nvkm_bus_init(&priv->base);
+       if (ret)
+               return ret;
+
+       nv_wr32(priv, 0x001100, 0xffffffff);
+       nv_wr32(priv, 0x001140, 0x00010008);
+       return 0;
+}
+
+struct nvkm_oclass *
+nv50_bus_oclass = &(struct nv04_bus_impl) {
+       .base.handle = NV_SUBDEV(BUS, 0x50),
+       .base.ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = nv04_bus_ctor,
+               .dtor = _nvkm_bus_dtor,
+               .init = nv50_bus_init,
+               .fini = _nvkm_bus_fini,
+       },
+       .intr = nv50_bus_intr,
+       .hwsq_exec = nv50_bus_hwsq_exec,
+       .hwsq_size = 64,
+}.base;
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/clk/Kbuild b/drivers/gpu/drm/nouveau/nvkm/subdev/clk/Kbuild
new file mode 100644 (file)
index 0000000..9c2f688
--- /dev/null
@@ -0,0 +1,12 @@
+nvkm-y += nvkm/subdev/clk/base.o
+nvkm-y += nvkm/subdev/clk/nv04.o
+nvkm-y += nvkm/subdev/clk/nv40.o
+nvkm-y += nvkm/subdev/clk/nv50.o
+nvkm-y += nvkm/subdev/clk/g84.o
+nvkm-y += nvkm/subdev/clk/gt215.o
+nvkm-y += nvkm/subdev/clk/mcp77.o
+nvkm-y += nvkm/subdev/clk/gf100.o
+nvkm-y += nvkm/subdev/clk/gk104.o
+nvkm-y += nvkm/subdev/clk/gk20a.o
+nvkm-y += nvkm/subdev/clk/pllnv04.o
+nvkm-y += nvkm/subdev/clk/pllgt215.o
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/clk/base.c b/drivers/gpu/drm/nouveau/nvkm/subdev/clk/base.c
new file mode 100644 (file)
index 0000000..b24a9cc
--- /dev/null
@@ -0,0 +1,591 @@
+/*
+ * Copyright 2013 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 <subdev/clk.h>
+#include <subdev/bios.h>
+#include <subdev/bios/boost.h>
+#include <subdev/bios/cstep.h>
+#include <subdev/bios/perf.h>
+#include <subdev/fb.h>
+#include <subdev/therm.h>
+#include <subdev/volt.h>
+
+#include <core/device.h>
+#include <core/option.h>
+
+/******************************************************************************
+ * misc
+ *****************************************************************************/
+static u32
+nvkm_clk_adjust(struct nvkm_clk *clk, bool adjust,
+               u8 pstate, u8 domain, u32 input)
+{
+       struct nvkm_bios *bios = nvkm_bios(clk);
+       struct nvbios_boostE boostE;
+       u8  ver, hdr, cnt, len;
+       u16 data;
+
+       data = nvbios_boostEm(bios, pstate, &ver, &hdr, &cnt, &len, &boostE);
+       if (data) {
+               struct nvbios_boostS boostS;
+               u8  idx = 0, sver, shdr;
+               u16 subd;
+
+               input = max(boostE.min, input);
+               input = min(boostE.max, input);
+               do {
+                       sver = ver;
+                       shdr = hdr;
+                       subd = nvbios_boostSp(bios, idx++, data, &sver, &shdr,
+                                             cnt, len, &boostS);
+                       if (subd && boostS.domain == domain) {
+                               if (adjust)
+                                       input = input * boostS.percent / 100;
+                               input = max(boostS.min, input);
+                               input = min(boostS.max, input);
+                               break;
+                       }
+               } while (subd);
+       }
+
+       return input;
+}
+
+/******************************************************************************
+ * C-States
+ *****************************************************************************/
+static int
+nvkm_cstate_prog(struct nvkm_clk *clk, struct nvkm_pstate *pstate, int cstatei)
+{
+       struct nvkm_therm *ptherm = nvkm_therm(clk);
+       struct nvkm_volt *volt = nvkm_volt(clk);
+       struct nvkm_cstate *cstate;
+       int ret;
+
+       if (!list_empty(&pstate->list)) {
+               cstate = list_entry(pstate->list.prev, typeof(*cstate), head);
+       } else {
+               cstate = &pstate->base;
+       }
+
+       if (ptherm) {
+               ret = nvkm_therm_cstate(ptherm, pstate->fanspeed, +1);
+               if (ret && ret != -ENODEV) {
+                       nv_error(clk, "failed to raise fan speed: %d\n", ret);
+                       return ret;
+               }
+       }
+
+       if (volt) {
+               ret = volt->set_id(volt, cstate->voltage, +1);
+               if (ret && ret != -ENODEV) {
+                       nv_error(clk, "failed to raise voltage: %d\n", ret);
+                       return ret;
+               }
+       }
+
+       ret = clk->calc(clk, cstate);
+       if (ret == 0) {
+               ret = clk->prog(clk);
+               clk->tidy(clk);
+       }
+
+       if (volt) {
+               ret = volt->set_id(volt, cstate->voltage, -1);
+               if (ret && ret != -ENODEV)
+                       nv_error(clk, "failed to lower voltage: %d\n", ret);
+       }
+
+       if (ptherm) {
+               ret = nvkm_therm_cstate(ptherm, pstate->fanspeed, -1);
+               if (ret && ret != -ENODEV)
+                       nv_error(clk, "failed to lower fan speed: %d\n", ret);
+       }
+
+       return 0;
+}
+
+static void
+nvkm_cstate_del(struct nvkm_cstate *cstate)
+{
+       list_del(&cstate->head);
+       kfree(cstate);
+}
+
+static int
+nvkm_cstate_new(struct nvkm_clk *clk, int idx, struct nvkm_pstate *pstate)
+{
+       struct nvkm_bios *bios = nvkm_bios(clk);
+       struct nvkm_domain *domain = clk->domains;
+       struct nvkm_cstate *cstate = NULL;
+       struct nvbios_cstepX cstepX;
+       u8  ver, hdr;
+       u16 data;
+
+       data = nvbios_cstepXp(bios, idx, &ver, &hdr, &cstepX);
+       if (!data)
+               return -ENOENT;
+
+       cstate = kzalloc(sizeof(*cstate), GFP_KERNEL);
+       if (!cstate)
+               return -ENOMEM;
+
+       *cstate = pstate->base;
+       cstate->voltage = cstepX.voltage;
+
+       while (domain && domain->name != nv_clk_src_max) {
+               if (domain->flags & NVKM_CLK_DOM_FLAG_CORE) {
+                       u32 freq = nvkm_clk_adjust(clk, true, pstate->pstate,
+                                                  domain->bios, cstepX.freq);
+                       cstate->domain[domain->name] = freq;
+               }
+               domain++;
+       }
+
+       list_add(&cstate->head, &pstate->list);
+       return 0;
+}
+
+/******************************************************************************
+ * P-States
+ *****************************************************************************/
+static int
+nvkm_pstate_prog(struct nvkm_clk *clk, int pstatei)
+{
+       struct nvkm_fb *pfb = nvkm_fb(clk);
+       struct nvkm_pstate *pstate;
+       int ret, idx = 0;
+
+       list_for_each_entry(pstate, &clk->states, head) {
+               if (idx++ == pstatei)
+                       break;
+       }
+
+       nv_debug(clk, "setting performance state %d\n", pstatei);
+       clk->pstate = pstatei;
+
+       if (pfb->ram->calc) {
+               int khz = pstate->base.domain[nv_clk_src_mem];
+               do {
+                       ret = pfb->ram->calc(pfb, khz);
+                       if (ret == 0)
+                               ret = pfb->ram->prog(pfb);
+               } while (ret > 0);
+               pfb->ram->tidy(pfb);
+       }
+
+       return nvkm_cstate_prog(clk, pstate, 0);
+}
+
+static void
+nvkm_pstate_work(struct work_struct *work)
+{
+       struct nvkm_clk *clk = container_of(work, typeof(*clk), work);
+       int pstate;
+
+       if (!atomic_xchg(&clk->waiting, 0))
+               return;
+       clk->pwrsrc = power_supply_is_system_supplied();
+
+       nv_trace(clk, "P %d PWR %d U(AC) %d U(DC) %d A %d T %d D %d\n",
+                clk->pstate, clk->pwrsrc, clk->ustate_ac, clk->ustate_dc,
+                clk->astate, clk->tstate, clk->dstate);
+
+       pstate = clk->pwrsrc ? clk->ustate_ac : clk->ustate_dc;
+       if (clk->state_nr && pstate != -1) {
+               pstate = (pstate < 0) ? clk->astate : pstate;
+               pstate = min(pstate, clk->state_nr - 1 - clk->tstate);
+               pstate = max(pstate, clk->dstate);
+       } else {
+               pstate = clk->pstate = -1;
+       }
+
+       nv_trace(clk, "-> %d\n", pstate);
+       if (pstate != clk->pstate) {
+               int ret = nvkm_pstate_prog(clk, pstate);
+               if (ret) {
+                       nv_error(clk, "error setting pstate %d: %d\n",
+                                pstate, ret);
+               }
+       }
+
+       wake_up_all(&clk->wait);
+       nvkm_notify_get(&clk->pwrsrc_ntfy);
+}
+
+static int
+nvkm_pstate_calc(struct nvkm_clk *clk, bool wait)
+{
+       atomic_set(&clk->waiting, 1);
+       schedule_work(&clk->work);
+       if (wait)
+               wait_event(clk->wait, !atomic_read(&clk->waiting));
+       return 0;
+}
+
+static void
+nvkm_pstate_info(struct nvkm_clk *clk, struct nvkm_pstate *pstate)
+{
+       struct nvkm_domain *clock = clk->domains - 1;
+       struct nvkm_cstate *cstate;
+       char info[3][32] = { "", "", "" };
+       char name[4] = "--";
+       int i = -1;
+
+       if (pstate->pstate != 0xff)
+               snprintf(name, sizeof(name), "%02x", pstate->pstate);
+
+       while ((++clock)->name != nv_clk_src_max) {
+               u32 lo = pstate->base.domain[clock->name];
+               u32 hi = lo;
+               if (hi == 0)
+                       continue;
+
+               nv_debug(clk, "%02x: %10d KHz\n", clock->name, lo);
+               list_for_each_entry(cstate, &pstate->list, head) {
+                       u32 freq = cstate->domain[clock->name];
+                       lo = min(lo, freq);
+                       hi = max(hi, freq);
+                       nv_debug(clk, "%10d KHz\n", freq);
+               }
+
+               if (clock->mname && ++i < ARRAY_SIZE(info)) {
+                       lo /= clock->mdiv;
+                       hi /= clock->mdiv;
+                       if (lo == hi) {
+                               snprintf(info[i], sizeof(info[i]), "%s %d MHz",
+                                        clock->mname, lo);
+                       } else {
+                               snprintf(info[i], sizeof(info[i]),
+                                        "%s %d-%d MHz", clock->mname, lo, hi);
+                       }
+               }
+       }
+
+       nv_info(clk, "%s: %s %s %s\n", name, info[0], info[1], info[2]);
+}
+
+static void
+nvkm_pstate_del(struct nvkm_pstate *pstate)
+{
+       struct nvkm_cstate *cstate, *temp;
+
+       list_for_each_entry_safe(cstate, temp, &pstate->list, head) {
+               nvkm_cstate_del(cstate);
+       }
+
+       list_del(&pstate->head);
+       kfree(pstate);
+}
+
+static int
+nvkm_pstate_new(struct nvkm_clk *clk, int idx)
+{
+       struct nvkm_bios *bios = nvkm_bios(clk);
+       struct nvkm_domain *domain = clk->domains - 1;
+       struct nvkm_pstate *pstate;
+       struct nvkm_cstate *cstate;
+       struct nvbios_cstepE cstepE;
+       struct nvbios_perfE perfE;
+       u8  ver, hdr, cnt, len;
+       u16 data;
+
+       data = nvbios_perfEp(bios, idx, &ver, &hdr, &cnt, &len, &perfE);
+       if (!data)
+               return -EINVAL;
+       if (perfE.pstate == 0xff)
+               return 0;
+
+       pstate = kzalloc(sizeof(*pstate), GFP_KERNEL);
+       cstate = &pstate->base;
+       if (!pstate)
+               return -ENOMEM;
+
+       INIT_LIST_HEAD(&pstate->list);
+
+       pstate->pstate = perfE.pstate;
+       pstate->fanspeed = perfE.fanspeed;
+       cstate->voltage = perfE.voltage;
+       cstate->domain[nv_clk_src_core] = perfE.core;
+       cstate->domain[nv_clk_src_shader] = perfE.shader;
+       cstate->domain[nv_clk_src_mem] = perfE.memory;
+       cstate->domain[nv_clk_src_vdec] = perfE.vdec;
+       cstate->domain[nv_clk_src_dom6] = perfE.disp;
+
+       while (ver >= 0x40 && (++domain)->name != nv_clk_src_max) {
+               struct nvbios_perfS perfS;
+               u8  sver = ver, shdr = hdr;
+               u32 perfSe = nvbios_perfSp(bios, data, domain->bios,
+                                         &sver, &shdr, cnt, len, &perfS);
+               if (perfSe == 0 || sver != 0x40)
+                       continue;
+
+               if (domain->flags & NVKM_CLK_DOM_FLAG_CORE) {
+                       perfS.v40.freq = nvkm_clk_adjust(clk, false,
+                                                        pstate->pstate,
+                                                        domain->bios,
+                                                        perfS.v40.freq);
+               }
+
+               cstate->domain[domain->name] = perfS.v40.freq;
+       }
+
+       data = nvbios_cstepEm(bios, pstate->pstate, &ver, &hdr, &cstepE);
+       if (data) {
+               int idx = cstepE.index;
+               do {
+                       nvkm_cstate_new(clk, idx, pstate);
+               } while(idx--);
+       }
+
+       nvkm_pstate_info(clk, pstate);
+       list_add_tail(&pstate->head, &clk->states);
+       clk->state_nr++;
+       return 0;
+}
+
+/******************************************************************************
+ * Adjustment triggers
+ *****************************************************************************/
+static int
+nvkm_clk_ustate_update(struct nvkm_clk *clk, int req)
+{
+       struct nvkm_pstate *pstate;
+       int i = 0;
+
+       if (!clk->allow_reclock)
+               return -ENOSYS;
+
+       if (req != -1 && req != -2) {
+               list_for_each_entry(pstate, &clk->states, head) {
+                       if (pstate->pstate == req)
+                               break;
+                       i++;
+               }
+
+               if (pstate->pstate != req)
+                       return -EINVAL;
+               req = i;
+       }
+
+       return req + 2;
+}
+
+static int
+nvkm_clk_nstate(struct nvkm_clk *clk, const char *mode, int arglen)
+{
+       int ret = 1;
+
+       if (clk->allow_reclock && !strncasecmpz(mode, "auto", arglen))
+               return -2;
+
+       if (strncasecmpz(mode, "disabled", arglen)) {
+               char save = mode[arglen];
+               long v;
+
+               ((char *)mode)[arglen] = '\0';
+               if (!kstrtol(mode, 0, &v)) {
+                       ret = nvkm_clk_ustate_update(clk, v);
+                       if (ret < 0)
+                               ret = 1;
+               }
+               ((char *)mode)[arglen] = save;
+       }
+
+       return ret - 2;
+}
+
+int
+nvkm_clk_ustate(struct nvkm_clk *clk, int req, int pwr)
+{
+       int ret = nvkm_clk_ustate_update(clk, req);
+       if (ret >= 0) {
+               if (ret -= 2, pwr) clk->ustate_ac = ret;
+               else               clk->ustate_dc = ret;
+               return nvkm_pstate_calc(clk, true);
+       }
+       return ret;
+}
+
+int
+nvkm_clk_astate(struct nvkm_clk *clk, int req, int rel, bool wait)
+{
+       if (!rel) clk->astate  = req;
+       if ( rel) clk->astate += rel;
+       clk->astate = min(clk->astate, clk->state_nr - 1);
+       clk->astate = max(clk->astate, 0);
+       return nvkm_pstate_calc(clk, wait);
+}
+
+int
+nvkm_clk_tstate(struct nvkm_clk *clk, int req, int rel)
+{
+       if (!rel) clk->tstate  = req;
+       if ( rel) clk->tstate += rel;
+       clk->tstate = min(clk->tstate, 0);
+       clk->tstate = max(clk->tstate, -(clk->state_nr - 1));
+       return nvkm_pstate_calc(clk, true);
+}
+
+int
+nvkm_clk_dstate(struct nvkm_clk *clk, int req, int rel)
+{
+       if (!rel) clk->dstate  = req;
+       if ( rel) clk->dstate += rel;
+       clk->dstate = min(clk->dstate, clk->state_nr - 1);
+       clk->dstate = max(clk->dstate, 0);
+       return nvkm_pstate_calc(clk, true);
+}
+
+static int
+nvkm_clk_pwrsrc(struct nvkm_notify *notify)
+{
+       struct nvkm_clk *clk =
+               container_of(notify, typeof(*clk), pwrsrc_ntfy);
+       nvkm_pstate_calc(clk, false);
+       return NVKM_NOTIFY_DROP;
+}
+
+/******************************************************************************
+ * subdev base class implementation
+ *****************************************************************************/
+
+int
+_nvkm_clk_fini(struct nvkm_object *object, bool suspend)
+{
+       struct nvkm_clk *clk = (void *)object;
+       nvkm_notify_put(&clk->pwrsrc_ntfy);
+       return nvkm_subdev_fini(&clk->base, suspend);
+}
+
+int
+_nvkm_clk_init(struct nvkm_object *object)
+{
+       struct nvkm_clk *clk = (void *)object;
+       struct nvkm_domain *clock = clk->domains;
+       int ret;
+
+       ret = nvkm_subdev_init(&clk->base);
+       if (ret)
+               return ret;
+
+       memset(&clk->bstate, 0x00, sizeof(clk->bstate));
+       INIT_LIST_HEAD(&clk->bstate.list);
+       clk->bstate.pstate = 0xff;
+
+       while (clock->name != nv_clk_src_max) {
+               ret = clk->read(clk, clock->name);
+               if (ret < 0) {
+                       nv_error(clk, "%02x freq unknown\n", clock->name);
+                       return ret;
+               }
+               clk->bstate.base.domain[clock->name] = ret;
+               clock++;
+       }
+
+       nvkm_pstate_info(clk, &clk->bstate);
+
+       clk->astate = clk->state_nr - 1;
+       clk->tstate = 0;
+       clk->dstate = 0;
+       clk->pstate = -1;
+       nvkm_pstate_calc(clk, true);
+       return 0;
+}
+
+void
+_nvkm_clk_dtor(struct nvkm_object *object)
+{
+       struct nvkm_clk *clk = (void *)object;
+       struct nvkm_pstate *pstate, *temp;
+
+       nvkm_notify_fini(&clk->pwrsrc_ntfy);
+
+       list_for_each_entry_safe(pstate, temp, &clk->states, head) {
+               nvkm_pstate_del(pstate);
+       }
+
+       nvkm_subdev_destroy(&clk->base);
+}
+
+int
+nvkm_clk_create_(struct nvkm_object *parent, struct nvkm_object *engine,
+                struct nvkm_oclass *oclass, struct nvkm_domain *clocks,
+                struct nvkm_pstate *pstates, int nb_pstates,
+                bool allow_reclock, int length, void **object)
+{
+       struct nvkm_device *device = nv_device(parent);
+       struct nvkm_clk *clk;
+       int ret, idx, arglen;
+       const char *mode;
+
+       ret = nvkm_subdev_create_(parent, engine, oclass, 0, "CLK",
+                                 "clock", length, object);
+       clk = *object;
+       if (ret)
+               return ret;
+
+       INIT_LIST_HEAD(&clk->states);
+       clk->domains = clocks;
+       clk->ustate_ac = -1;
+       clk->ustate_dc = -1;
+
+       INIT_WORK(&clk->work, nvkm_pstate_work);
+       init_waitqueue_head(&clk->wait);
+       atomic_set(&clk->waiting, 0);
+
+       /* If no pstates are provided, try and fetch them from the BIOS */
+       if (!pstates) {
+               idx = 0;
+               do {
+                       ret = nvkm_pstate_new(clk, idx++);
+               } while (ret == 0);
+       } else {
+               for (idx = 0; idx < nb_pstates; idx++)
+                       list_add_tail(&pstates[idx].head, &clk->states);
+               clk->state_nr = nb_pstates;
+       }
+
+       clk->allow_reclock = allow_reclock;
+
+       ret = nvkm_notify_init(NULL, &device->event, nvkm_clk_pwrsrc, true,
+                              NULL, 0, 0, &clk->pwrsrc_ntfy);
+       if (ret)
+               return ret;
+
+       mode = nvkm_stropt(device->cfgopt, "NvClkMode", &arglen);
+       if (mode) {
+               clk->ustate_ac = nvkm_clk_nstate(clk, mode, arglen);
+               clk->ustate_dc = nvkm_clk_nstate(clk, mode, arglen);
+       }
+
+       mode = nvkm_stropt(device->cfgopt, "NvClkModeAC", &arglen);
+       if (mode)
+               clk->ustate_ac = nvkm_clk_nstate(clk, mode, arglen);
+
+       mode = nvkm_stropt(device->cfgopt, "NvClkModeDC", &arglen);
+       if (mode)
+               clk->ustate_dc = nvkm_clk_nstate(clk, mode, arglen);
+
+       return 0;
+}
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/clk/g84.c b/drivers/gpu/drm/nouveau/nvkm/subdev/clk/g84.c
new file mode 100644 (file)
index 0000000..4c90b97
--- /dev/null
@@ -0,0 +1,47 @@
+/*
+ * Copyright 2013 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 <bskeggs@redhat.com>
+ */
+#include "nv50.h"
+
+static struct nvkm_domain
+g84_domains[] = {
+       { nv_clk_src_crystal, 0xff },
+       { nv_clk_src_href   , 0xff },
+       { nv_clk_src_core   , 0xff, 0, "core", 1000 },
+       { nv_clk_src_shader , 0xff, 0, "shader", 1000 },
+       { nv_clk_src_mem    , 0xff, 0, "memory", 1000 },
+       { nv_clk_src_vdec   , 0xff },
+       { nv_clk_src_max }
+};
+
+struct nvkm_oclass *
+g84_clk_oclass = &(struct nv50_clk_oclass) {
+       .base.handle = NV_SUBDEV(CLK, 0x84),
+       .base.ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = nv50_clk_ctor,
+               .dtor = _nvkm_clk_dtor,
+               .init = _nvkm_clk_init,
+               .fini = _nvkm_clk_fini,
+       },
+       .domains = g84_domains,
+}.base;
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/clk/gf100.c b/drivers/gpu/drm/nouveau/nvkm/subdev/clk/gf100.c
new file mode 100644 (file)
index 0000000..3d7330d
--- /dev/null
@@ -0,0 +1,462 @@
+/*
+ * Copyright 2012 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 <subdev/clk.h>
+#include "pll.h"
+
+#include <core/device.h>
+#include <subdev/bios.h>
+#include <subdev/bios/pll.h>
+#include <subdev/timer.h>
+
+struct gf100_clk_info {
+       u32 freq;
+       u32 ssel;
+       u32 mdiv;
+       u32 dsrc;
+       u32 ddiv;
+       u32 coef;
+};
+
+struct gf100_clk_priv {
+       struct nvkm_clk base;
+       struct gf100_clk_info eng[16];
+};
+
+static u32 read_div(struct gf100_clk_priv *, int, u32, u32);
+
+static u32
+read_vco(struct gf100_clk_priv *priv, u32 dsrc)
+{
+       struct nvkm_clk *clk = &priv->base;
+       u32 ssrc = nv_rd32(priv, dsrc);
+       if (!(ssrc & 0x00000100))
+               return clk->read(clk, nv_clk_src_sppll0);
+       return clk->read(clk, nv_clk_src_sppll1);
+}
+
+static u32
+read_pll(struct gf100_clk_priv *priv, u32 pll)
+{
+       struct nvkm_clk *clk = &priv->base;
+       u32 ctrl = nv_rd32(priv, pll + 0x00);
+       u32 coef = nv_rd32(priv, pll + 0x04);
+       u32 P = (coef & 0x003f0000) >> 16;
+       u32 N = (coef & 0x0000ff00) >> 8;
+       u32 M = (coef & 0x000000ff) >> 0;
+       u32 sclk;
+
+       if (!(ctrl & 0x00000001))
+               return 0;
+
+       switch (pll) {
+       case 0x00e800:
+       case 0x00e820:
+               sclk = nv_device(priv)->crystal;
+               P = 1;
+               break;
+       case 0x132000:
+               sclk = clk->read(clk, nv_clk_src_mpllsrc);
+               break;
+       case 0x132020:
+               sclk = clk->read(clk, nv_clk_src_mpllsrcref);
+               break;
+       case 0x137000:
+       case 0x137020:
+       case 0x137040:
+       case 0x1370e0:
+               sclk = read_div(priv, (pll & 0xff) / 0x20, 0x137120, 0x137140);
+               break;
+       default:
+               return 0;
+       }
+
+       return sclk * N / M / P;
+}
+
+static u32
+read_div(struct gf100_clk_priv *priv, int doff, u32 dsrc, u32 dctl)
+{
+       u32 ssrc = nv_rd32(priv, dsrc + (doff * 4));
+       u32 sctl = nv_rd32(priv, dctl + (doff * 4));
+
+       switch (ssrc & 0x00000003) {
+       case 0:
+               if ((ssrc & 0x00030000) != 0x00030000)
+                       return nv_device(priv)->crystal;
+               return 108000;
+       case 2:
+               return 100000;
+       case 3:
+               if (sctl & 0x80000000) {
+                       u32 sclk = read_vco(priv, dsrc + (doff * 4));
+                       u32 sdiv = (sctl & 0x0000003f) + 2;
+                       return (sclk * 2) / sdiv;
+               }
+
+               return read_vco(priv, dsrc + (doff * 4));
+       default:
+               return 0;
+       }
+}
+
+static u32
+read_clk(struct gf100_clk_priv *priv, int clk)
+{
+       u32 sctl = nv_rd32(priv, 0x137250 + (clk * 4));
+       u32 ssel = nv_rd32(priv, 0x137100);
+       u32 sclk, sdiv;
+
+       if (ssel & (1 << clk)) {
+               if (clk < 7)
+                       sclk = read_pll(priv, 0x137000 + (clk * 0x20));
+               else
+                       sclk = read_pll(priv, 0x1370e0);
+               sdiv = ((sctl & 0x00003f00) >> 8) + 2;
+       } else {
+               sclk = read_div(priv, clk, 0x137160, 0x1371d0);
+               sdiv = ((sctl & 0x0000003f) >> 0) + 2;
+       }
+
+       if (sctl & 0x80000000)
+               return (sclk * 2) / sdiv;
+
+       return sclk;
+}
+
+static int
+gf100_clk_read(struct nvkm_clk *clk, enum nv_clk_src src)
+{
+       struct nvkm_device *device = nv_device(clk);
+       struct gf100_clk_priv *priv = (void *)clk;
+
+       switch (src) {
+       case nv_clk_src_crystal:
+               return device->crystal;
+       case nv_clk_src_href:
+               return 100000;
+       case nv_clk_src_sppll0:
+               return read_pll(priv, 0x00e800);
+       case nv_clk_src_sppll1:
+               return read_pll(priv, 0x00e820);
+
+       case nv_clk_src_mpllsrcref:
+               return read_div(priv, 0, 0x137320, 0x137330);
+       case nv_clk_src_mpllsrc:
+               return read_pll(priv, 0x132020);
+       case nv_clk_src_mpll:
+               return read_pll(priv, 0x132000);
+       case nv_clk_src_mdiv:
+               return read_div(priv, 0, 0x137300, 0x137310);
+       case nv_clk_src_mem:
+               if (nv_rd32(priv, 0x1373f0) & 0x00000002)
+                       return clk->read(clk, nv_clk_src_mpll);
+               return clk->read(clk, nv_clk_src_mdiv);
+
+       case nv_clk_src_gpc:
+               return read_clk(priv, 0x00);
+       case nv_clk_src_rop:
+               return read_clk(priv, 0x01);
+       case nv_clk_src_hubk07:
+               return read_clk(priv, 0x02);
+       case nv_clk_src_hubk06:
+               return read_clk(priv, 0x07);
+       case nv_clk_src_hubk01:
+               return read_clk(priv, 0x08);
+       case nv_clk_src_copy:
+               return read_clk(priv, 0x09);
+       case nv_clk_src_daemon:
+               return read_clk(priv, 0x0c);
+       case nv_clk_src_vdec:
+               return read_clk(priv, 0x0e);
+       default:
+               nv_error(clk, "invalid clock source %d\n", src);
+               return -EINVAL;
+       }
+}
+
+static u32
+calc_div(struct gf100_clk_priv *priv, int clk, u32 ref, u32 freq, u32 *ddiv)
+{
+       u32 div = min((ref * 2) / freq, (u32)65);
+       if (div < 2)
+               div = 2;
+
+       *ddiv = div - 2;
+       return (ref * 2) / div;
+}
+
+static u32
+calc_src(struct gf100_clk_priv *priv, int clk, u32 freq, u32 *dsrc, u32 *ddiv)
+{
+       u32 sclk;
+
+       /* use one of the fixed frequencies if possible */
+       *ddiv = 0x00000000;
+       switch (freq) {
+       case  27000:
+       case 108000:
+               *dsrc = 0x00000000;
+               if (freq == 108000)
+                       *dsrc |= 0x00030000;
+               return freq;
+       case 100000:
+               *dsrc = 0x00000002;
+               return freq;
+       default:
+               *dsrc = 0x00000003;
+               break;
+       }
+
+       /* otherwise, calculate the closest divider */
+       sclk = read_vco(priv, 0x137160 + (clk * 4));
+       if (clk < 7)
+               sclk = calc_div(priv, clk, sclk, freq, ddiv);
+       return sclk;
+}
+
+static u32
+calc_pll(struct gf100_clk_priv *priv, int clk, u32 freq, u32 *coef)
+{
+       struct nvkm_bios *bios = nvkm_bios(priv);
+       struct nvbios_pll limits;
+       int N, M, P, ret;
+
+       ret = nvbios_pll_parse(bios, 0x137000 + (clk * 0x20), &limits);
+       if (ret)
+               return 0;
+
+       limits.refclk = read_div(priv, clk, 0x137120, 0x137140);
+       if (!limits.refclk)
+               return 0;
+
+       ret = gt215_pll_calc(nv_subdev(priv), &limits, freq, &N, NULL, &M, &P);
+       if (ret <= 0)
+               return 0;
+
+       *coef = (P << 16) | (N << 8) | M;
+       return ret;
+}
+
+static int
+calc_clk(struct gf100_clk_priv *priv,
+        struct nvkm_cstate *cstate, int clk, int dom)
+{
+       struct gf100_clk_info *info = &priv->eng[clk];
+       u32 freq = cstate->domain[dom];
+       u32 src0, div0, div1D, div1P = 0;
+       u32 clk0, clk1 = 0;
+
+       /* invalid clock domain */
+       if (!freq)
+               return 0;
+
+       /* first possible path, using only dividers */
+       clk0 = calc_src(priv, clk, freq, &src0, &div0);
+       clk0 = calc_div(priv, clk, clk0, freq, &div1D);
+
+       /* see if we can get any closer using PLLs */
+       if (clk0 != freq && (0x00004387 & (1 << clk))) {
+               if (clk <= 7)
+                       clk1 = calc_pll(priv, clk, freq, &info->coef);
+               else
+                       clk1 = cstate->domain[nv_clk_src_hubk06];
+               clk1 = calc_div(priv, clk, clk1, freq, &div1P);
+       }
+
+       /* select the method which gets closest to target freq */
+       if (abs((int)freq - clk0) <= abs((int)freq - clk1)) {
+               info->dsrc = src0;
+               if (div0) {
+                       info->ddiv |= 0x80000000;
+                       info->ddiv |= div0 << 8;
+                       info->ddiv |= div0;
+               }
+               if (div1D) {
+                       info->mdiv |= 0x80000000;
+                       info->mdiv |= div1D;
+               }
+               info->ssel = info->coef = 0;
+               info->freq = clk0;
+       } else {
+               if (div1P) {
+                       info->mdiv |= 0x80000000;
+                       info->mdiv |= div1P << 8;
+               }
+               info->ssel = (1 << clk);
+               info->freq = clk1;
+       }
+
+       return 0;
+}
+
+static int
+gf100_clk_calc(struct nvkm_clk *clk, struct nvkm_cstate *cstate)
+{
+       struct gf100_clk_priv *priv = (void *)clk;
+       int ret;
+
+       if ((ret = calc_clk(priv, cstate, 0x00, nv_clk_src_gpc)) ||
+           (ret = calc_clk(priv, cstate, 0x01, nv_clk_src_rop)) ||
+           (ret = calc_clk(priv, cstate, 0x02, nv_clk_src_hubk07)) ||
+           (ret = calc_clk(priv, cstate, 0x07, nv_clk_src_hubk06)) ||
+           (ret = calc_clk(priv, cstate, 0x08, nv_clk_src_hubk01)) ||
+           (ret = calc_clk(priv, cstate, 0x09, nv_clk_src_copy)) ||
+           (ret = calc_clk(priv, cstate, 0x0c, nv_clk_src_daemon)) ||
+           (ret = calc_clk(priv, cstate, 0x0e, nv_clk_src_vdec)))
+               return ret;
+
+       return 0;
+}
+
+static void
+gf100_clk_prog_0(struct gf100_clk_priv *priv, int clk)
+{
+       struct gf100_clk_info *info = &priv->eng[clk];
+       if (clk < 7 && !info->ssel) {
+               nv_mask(priv, 0x1371d0 + (clk * 0x04), 0x80003f3f, info->ddiv);
+               nv_wr32(priv, 0x137160 + (clk * 0x04), info->dsrc);
+       }
+}
+
+static void
+gf100_clk_prog_1(struct gf100_clk_priv *priv, int clk)
+{
+       nv_mask(priv, 0x137100, (1 << clk), 0x00000000);
+       nv_wait(priv, 0x137100, (1 << clk), 0x00000000);
+}
+
+static void
+gf100_clk_prog_2(struct gf100_clk_priv *priv, int clk)
+{
+       struct gf100_clk_info *info = &priv->eng[clk];
+       const u32 addr = 0x137000 + (clk * 0x20);
+       if (clk <= 7) {
+               nv_mask(priv, addr + 0x00, 0x00000004, 0x00000000);
+               nv_mask(priv, addr + 0x00, 0x00000001, 0x00000000);
+               if (info->coef) {
+                       nv_wr32(priv, addr + 0x04, info->coef);
+                       nv_mask(priv, addr + 0x00, 0x00000001, 0x00000001);
+                       nv_wait(priv, addr + 0x00, 0x00020000, 0x00020000);
+                       nv_mask(priv, addr + 0x00, 0x00020004, 0x00000004);
+               }
+       }
+}
+
+static void
+gf100_clk_prog_3(struct gf100_clk_priv *priv, int clk)
+{
+       struct gf100_clk_info *info = &priv->eng[clk];
+       if (info->ssel) {
+               nv_mask(priv, 0x137100, (1 << clk), info->ssel);
+               nv_wait(priv, 0x137100, (1 << clk), info->ssel);
+       }
+}
+
+static void
+gf100_clk_prog_4(struct gf100_clk_priv *priv, int clk)
+{
+       struct gf100_clk_info *info = &priv->eng[clk];
+       nv_mask(priv, 0x137250 + (clk * 0x04), 0x00003f3f, info->mdiv);
+}
+
+static int
+gf100_clk_prog(struct nvkm_clk *clk)
+{
+       struct gf100_clk_priv *priv = (void *)clk;
+       struct {
+               void (*exec)(struct gf100_clk_priv *, int);
+       } stage[] = {
+               { gf100_clk_prog_0 }, /* div programming */
+               { gf100_clk_prog_1 }, /* select div mode */
+               { gf100_clk_prog_2 }, /* (maybe) program pll */
+               { gf100_clk_prog_3 }, /* (maybe) select pll mode */
+               { gf100_clk_prog_4 }, /* final divider */
+       };
+       int i, j;
+
+       for (i = 0; i < ARRAY_SIZE(stage); i++) {
+               for (j = 0; j < ARRAY_SIZE(priv->eng); j++) {
+                       if (!priv->eng[j].freq)
+                               continue;
+                       stage[i].exec(priv, j);
+               }
+       }
+
+       return 0;
+}
+
+static void
+gf100_clk_tidy(struct nvkm_clk *clk)
+{
+       struct gf100_clk_priv *priv = (void *)clk;
+       memset(priv->eng, 0x00, sizeof(priv->eng));
+}
+
+static struct nvkm_domain
+gf100_domain[] = {
+       { nv_clk_src_crystal, 0xff },
+       { nv_clk_src_href   , 0xff },
+       { nv_clk_src_hubk06 , 0x00 },
+       { nv_clk_src_hubk01 , 0x01 },
+       { nv_clk_src_copy   , 0x02 },
+       { nv_clk_src_gpc    , 0x03, 0, "core", 2000 },
+       { nv_clk_src_rop    , 0x04 },
+       { nv_clk_src_mem    , 0x05, 0, "memory", 1000 },
+       { nv_clk_src_vdec   , 0x06 },
+       { nv_clk_src_daemon , 0x0a },
+       { nv_clk_src_hubk07 , 0x0b },
+       { nv_clk_src_max }
+};
+
+static int
+gf100_clk_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+              struct nvkm_oclass *oclass, void *data, u32 size,
+              struct nvkm_object **pobject)
+{
+       struct gf100_clk_priv *priv;
+       int ret;
+
+       ret = nvkm_clk_create(parent, engine, oclass, gf100_domain,
+                             NULL, 0, false, &priv);
+       *pobject = nv_object(priv);
+       if (ret)
+               return ret;
+
+       priv->base.read = gf100_clk_read;
+       priv->base.calc = gf100_clk_calc;
+       priv->base.prog = gf100_clk_prog;
+       priv->base.tidy = gf100_clk_tidy;
+       return 0;
+}
+
+struct nvkm_oclass
+gf100_clk_oclass = {
+       .handle = NV_SUBDEV(CLK, 0xc0),
+       .ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = gf100_clk_ctor,
+               .dtor = _nvkm_clk_dtor,
+               .init = _nvkm_clk_init,
+               .fini = _nvkm_clk_fini,
+       },
+};
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/clk/gk104.c b/drivers/gpu/drm/nouveau/nvkm/subdev/clk/gk104.c
new file mode 100644 (file)
index 0000000..e9b2310
--- /dev/null
@@ -0,0 +1,500 @@
+/*
+ * Copyright 2013 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 <subdev/clk.h>
+#include "pll.h"
+
+#include <core/device.h>
+#include <subdev/timer.h>
+#include <subdev/bios.h>
+#include <subdev/bios/pll.h>
+
+struct gk104_clk_info {
+       u32 freq;
+       u32 ssel;
+       u32 mdiv;
+       u32 dsrc;
+       u32 ddiv;
+       u32 coef;
+};
+
+struct gk104_clk_priv {
+       struct nvkm_clk base;
+       struct gk104_clk_info eng[16];
+};
+
+static u32 read_div(struct gk104_clk_priv *, int, u32, u32);
+static u32 read_pll(struct gk104_clk_priv *, u32);
+
+static u32
+read_vco(struct gk104_clk_priv *priv, u32 dsrc)
+{
+       u32 ssrc = nv_rd32(priv, dsrc);
+       if (!(ssrc & 0x00000100))
+               return read_pll(priv, 0x00e800);
+       return read_pll(priv, 0x00e820);
+}
+
+static u32
+read_pll(struct gk104_clk_priv *priv, u32 pll)
+{
+       u32 ctrl = nv_rd32(priv, pll + 0x00);
+       u32 coef = nv_rd32(priv, pll + 0x04);
+       u32 P = (coef & 0x003f0000) >> 16;
+       u32 N = (coef & 0x0000ff00) >> 8;
+       u32 M = (coef & 0x000000ff) >> 0;
+       u32 sclk;
+       u16 fN = 0xf000;
+
+       if (!(ctrl & 0x00000001))
+               return 0;
+
+       switch (pll) {
+       case 0x00e800:
+       case 0x00e820:
+               sclk = nv_device(priv)->crystal;
+               P = 1;
+               break;
+       case 0x132000:
+               sclk = read_pll(priv, 0x132020);
+               P = (coef & 0x10000000) ? 2 : 1;
+               break;
+       case 0x132020:
+               sclk = read_div(priv, 0, 0x137320, 0x137330);
+               fN   = nv_rd32(priv, pll + 0x10) >> 16;
+               break;
+       case 0x137000:
+       case 0x137020:
+       case 0x137040:
+       case 0x1370e0:
+               sclk = read_div(priv, (pll & 0xff) / 0x20, 0x137120, 0x137140);
+               break;
+       default:
+               return 0;
+       }
+
+       if (P == 0)
+               P = 1;
+
+       sclk = (sclk * N) + (((u16)(fN + 4096) * sclk) >> 13);
+       return sclk / (M * P);
+}
+
+static u32
+read_div(struct gk104_clk_priv *priv, int doff, u32 dsrc, u32 dctl)
+{
+       u32 ssrc = nv_rd32(priv, dsrc + (doff * 4));
+       u32 sctl = nv_rd32(priv, dctl + (doff * 4));
+
+       switch (ssrc & 0x00000003) {
+       case 0:
+               if ((ssrc & 0x00030000) != 0x00030000)
+                       return nv_device(priv)->crystal;
+               return 108000;
+       case 2:
+               return 100000;
+       case 3:
+               if (sctl & 0x80000000) {
+                       u32 sclk = read_vco(priv, dsrc + (doff * 4));
+                       u32 sdiv = (sctl & 0x0000003f) + 2;
+                       return (sclk * 2) / sdiv;
+               }
+
+               return read_vco(priv, dsrc + (doff * 4));
+       default:
+               return 0;
+       }
+}
+
+static u32
+read_mem(struct gk104_clk_priv *priv)
+{
+       switch (nv_rd32(priv, 0x1373f4) & 0x0000000f) {
+       case 1: return read_pll(priv, 0x132020);
+       case 2: return read_pll(priv, 0x132000);
+       default:
+               return 0;
+       }
+}
+
+static u32
+read_clk(struct gk104_clk_priv *priv, int clk)
+{
+       u32 sctl = nv_rd32(priv, 0x137250 + (clk * 4));
+       u32 sclk, sdiv;
+
+       if (clk < 7) {
+               u32 ssel = nv_rd32(priv, 0x137100);
+               if (ssel & (1 << clk)) {
+                       sclk = read_pll(priv, 0x137000 + (clk * 0x20));
+                       sdiv = 1;
+               } else {
+                       sclk = read_div(priv, clk, 0x137160, 0x1371d0);
+                       sdiv = 0;
+               }
+       } else {
+               u32 ssrc = nv_rd32(priv, 0x137160 + (clk * 0x04));
+               if ((ssrc & 0x00000003) == 0x00000003) {
+                       sclk = read_div(priv, clk, 0x137160, 0x1371d0);
+                       if (ssrc & 0x00000100) {
+                               if (ssrc & 0x40000000)
+                                       sclk = read_pll(priv, 0x1370e0);
+                               sdiv = 1;
+                       } else {
+                               sdiv = 0;
+                       }
+               } else {
+                       sclk = read_div(priv, clk, 0x137160, 0x1371d0);
+                       sdiv = 0;
+               }
+       }
+
+       if (sctl & 0x80000000) {
+               if (sdiv)
+                       sdiv = ((sctl & 0x00003f00) >> 8) + 2;
+               else
+                       sdiv = ((sctl & 0x0000003f) >> 0) + 2;
+               return (sclk * 2) / sdiv;
+       }
+
+       return sclk;
+}
+
+static int
+gk104_clk_read(struct nvkm_clk *clk, enum nv_clk_src src)
+{
+       struct nvkm_device *device = nv_device(clk);
+       struct gk104_clk_priv *priv = (void *)clk;
+
+       switch (src) {
+       case nv_clk_src_crystal:
+               return device->crystal;
+       case nv_clk_src_href:
+               return 100000;
+       case nv_clk_src_mem:
+               return read_mem(priv);
+       case nv_clk_src_gpc:
+               return read_clk(priv, 0x00);
+       case nv_clk_src_rop:
+               return read_clk(priv, 0x01);
+       case nv_clk_src_hubk07:
+               return read_clk(priv, 0x02);
+       case nv_clk_src_hubk06:
+               return read_clk(priv, 0x07);
+       case nv_clk_src_hubk01:
+               return read_clk(priv, 0x08);
+       case nv_clk_src_daemon:
+               return read_clk(priv, 0x0c);
+       case nv_clk_src_vdec:
+               return read_clk(priv, 0x0e);
+       default:
+               nv_error(clk, "invalid clock source %d\n", src);
+               return -EINVAL;
+       }
+}
+
+static u32
+calc_div(struct gk104_clk_priv *priv, int clk, u32 ref, u32 freq, u32 *ddiv)
+{
+       u32 div = min((ref * 2) / freq, (u32)65);
+       if (div < 2)
+               div = 2;
+
+       *ddiv = div - 2;
+       return (ref * 2) / div;
+}
+
+static u32
+calc_src(struct gk104_clk_priv *priv, int clk, u32 freq, u32 *dsrc, u32 *ddiv)
+{
+       u32 sclk;
+
+       /* use one of the fixed frequencies if possible */
+       *ddiv = 0x00000000;
+       switch (freq) {
+       case  27000:
+       case 108000:
+               *dsrc = 0x00000000;
+               if (freq == 108000)
+                       *dsrc |= 0x00030000;
+               return freq;
+       case 100000:
+               *dsrc = 0x00000002;
+               return freq;
+       default:
+               *dsrc = 0x00000003;
+               break;
+       }
+
+       /* otherwise, calculate the closest divider */
+       sclk = read_vco(priv, 0x137160 + (clk * 4));
+       if (clk < 7)
+               sclk = calc_div(priv, clk, sclk, freq, ddiv);
+       return sclk;
+}
+
+static u32
+calc_pll(struct gk104_clk_priv *priv, int clk, u32 freq, u32 *coef)
+{
+       struct nvkm_bios *bios = nvkm_bios(priv);
+       struct nvbios_pll limits;
+       int N, M, P, ret;
+
+       ret = nvbios_pll_parse(bios, 0x137000 + (clk * 0x20), &limits);
+       if (ret)
+               return 0;
+
+       limits.refclk = read_div(priv, clk, 0x137120, 0x137140);
+       if (!limits.refclk)
+               return 0;
+
+       ret = gt215_pll_calc(nv_subdev(priv), &limits, freq, &N, NULL, &M, &P);
+       if (ret <= 0)
+               return 0;
+
+       *coef = (P << 16) | (N << 8) | M;
+       return ret;
+}
+
+static int
+calc_clk(struct gk104_clk_priv *priv,
+        struct nvkm_cstate *cstate, int clk, int dom)
+{
+       struct gk104_clk_info *info = &priv->eng[clk];
+       u32 freq = cstate->domain[dom];
+       u32 src0, div0, div1D, div1P = 0;
+       u32 clk0, clk1 = 0;
+
+       /* invalid clock domain */
+       if (!freq)
+               return 0;
+
+       /* first possible path, using only dividers */
+       clk0 = calc_src(priv, clk, freq, &src0, &div0);
+       clk0 = calc_div(priv, clk, clk0, freq, &div1D);
+
+       /* see if we can get any closer using PLLs */
+       if (clk0 != freq && (0x0000ff87 & (1 << clk))) {
+               if (clk <= 7)
+                       clk1 = calc_pll(priv, clk, freq, &info->coef);
+               else
+                       clk1 = cstate->domain[nv_clk_src_hubk06];
+               clk1 = calc_div(priv, clk, clk1, freq, &div1P);
+       }
+
+       /* select the method which gets closest to target freq */
+       if (abs((int)freq - clk0) <= abs((int)freq - clk1)) {
+               info->dsrc = src0;
+               if (div0) {
+                       info->ddiv |= 0x80000000;
+                       info->ddiv |= div0;
+               }
+               if (div1D) {
+                       info->mdiv |= 0x80000000;
+                       info->mdiv |= div1D;
+               }
+               info->ssel = 0;
+               info->freq = clk0;
+       } else {
+               if (div1P) {
+                       info->mdiv |= 0x80000000;
+                       info->mdiv |= div1P << 8;
+               }
+               info->ssel = (1 << clk);
+               info->dsrc = 0x40000100;
+               info->freq = clk1;
+       }
+
+       return 0;
+}
+
+static int
+gk104_clk_calc(struct nvkm_clk *clk, struct nvkm_cstate *cstate)
+{
+       struct gk104_clk_priv *priv = (void *)clk;
+       int ret;
+
+       if ((ret = calc_clk(priv, cstate, 0x00, nv_clk_src_gpc)) ||
+           (ret = calc_clk(priv, cstate, 0x01, nv_clk_src_rop)) ||
+           (ret = calc_clk(priv, cstate, 0x02, nv_clk_src_hubk07)) ||
+           (ret = calc_clk(priv, cstate, 0x07, nv_clk_src_hubk06)) ||
+           (ret = calc_clk(priv, cstate, 0x08, nv_clk_src_hubk01)) ||
+           (ret = calc_clk(priv, cstate, 0x0c, nv_clk_src_daemon)) ||
+           (ret = calc_clk(priv, cstate, 0x0e, nv_clk_src_vdec)))
+               return ret;
+
+       return 0;
+}
+
+static void
+gk104_clk_prog_0(struct gk104_clk_priv *priv, int clk)
+{
+       struct gk104_clk_info *info = &priv->eng[clk];
+       if (!info->ssel) {
+               nv_mask(priv, 0x1371d0 + (clk * 0x04), 0x8000003f, info->ddiv);
+               nv_wr32(priv, 0x137160 + (clk * 0x04), info->dsrc);
+       }
+}
+
+static void
+gk104_clk_prog_1_0(struct gk104_clk_priv *priv, int clk)
+{
+       nv_mask(priv, 0x137100, (1 << clk), 0x00000000);
+       nv_wait(priv, 0x137100, (1 << clk), 0x00000000);
+}
+
+static void
+gk104_clk_prog_1_1(struct gk104_clk_priv *priv, int clk)
+{
+       nv_mask(priv, 0x137160 + (clk * 0x04), 0x00000100, 0x00000000);
+}
+
+static void
+gk104_clk_prog_2(struct gk104_clk_priv *priv, int clk)
+{
+       struct gk104_clk_info *info = &priv->eng[clk];
+       const u32 addr = 0x137000 + (clk * 0x20);
+       nv_mask(priv, addr + 0x00, 0x00000004, 0x00000000);
+       nv_mask(priv, addr + 0x00, 0x00000001, 0x00000000);
+       if (info->coef) {
+               nv_wr32(priv, addr + 0x04, info->coef);
+               nv_mask(priv, addr + 0x00, 0x00000001, 0x00000001);
+               nv_wait(priv, addr + 0x00, 0x00020000, 0x00020000);
+               nv_mask(priv, addr + 0x00, 0x00020004, 0x00000004);
+       }
+}
+
+static void
+gk104_clk_prog_3(struct gk104_clk_priv *priv, int clk)
+{
+       struct gk104_clk_info *info = &priv->eng[clk];
+       if (info->ssel)
+               nv_mask(priv, 0x137250 + (clk * 0x04), 0x00003f00, info->mdiv);
+       else
+               nv_mask(priv, 0x137250 + (clk * 0x04), 0x0000003f, info->mdiv);
+}
+
+static void
+gk104_clk_prog_4_0(struct gk104_clk_priv *priv, int clk)
+{
+       struct gk104_clk_info *info = &priv->eng[clk];
+       if (info->ssel) {
+               nv_mask(priv, 0x137100, (1 << clk), info->ssel);
+               nv_wait(priv, 0x137100, (1 << clk), info->ssel);
+       }
+}
+
+static void
+gk104_clk_prog_4_1(struct gk104_clk_priv *priv, int clk)
+{
+       struct gk104_clk_info *info = &priv->eng[clk];
+       if (info->ssel) {
+               nv_mask(priv, 0x137160 + (clk * 0x04), 0x40000000, 0x40000000);
+               nv_mask(priv, 0x137160 + (clk * 0x04), 0x00000100, 0x00000100);
+       }
+}
+
+static int
+gk104_clk_prog(struct nvkm_clk *clk)
+{
+       struct gk104_clk_priv *priv = (void *)clk;
+       struct {
+               u32 mask;
+               void (*exec)(struct gk104_clk_priv *, int);
+       } stage[] = {
+               { 0x007f, gk104_clk_prog_0   }, /* div programming */
+               { 0x007f, gk104_clk_prog_1_0 }, /* select div mode */
+               { 0xff80, gk104_clk_prog_1_1 },
+               { 0x00ff, gk104_clk_prog_2   }, /* (maybe) program pll */
+               { 0xff80, gk104_clk_prog_3   }, /* final divider */
+               { 0x007f, gk104_clk_prog_4_0 }, /* (maybe) select pll mode */
+               { 0xff80, gk104_clk_prog_4_1 },
+       };
+       int i, j;
+
+       for (i = 0; i < ARRAY_SIZE(stage); i++) {
+               for (j = 0; j < ARRAY_SIZE(priv->eng); j++) {
+                       if (!(stage[i].mask & (1 << j)))
+                               continue;
+                       if (!priv->eng[j].freq)
+                               continue;
+                       stage[i].exec(priv, j);
+               }
+       }
+
+       return 0;
+}
+
+static void
+gk104_clk_tidy(struct nvkm_clk *clk)
+{
+       struct gk104_clk_priv *priv = (void *)clk;
+       memset(priv->eng, 0x00, sizeof(priv->eng));
+}
+
+static struct nvkm_domain
+gk104_domain[] = {
+       { nv_clk_src_crystal, 0xff },
+       { nv_clk_src_href   , 0xff },
+       { nv_clk_src_gpc    , 0x00, NVKM_CLK_DOM_FLAG_CORE, "core", 2000 },
+       { nv_clk_src_hubk07 , 0x01, NVKM_CLK_DOM_FLAG_CORE },
+       { nv_clk_src_rop    , 0x02, NVKM_CLK_DOM_FLAG_CORE },
+       { nv_clk_src_mem    , 0x03, 0, "memory", 500 },
+       { nv_clk_src_hubk06 , 0x04, NVKM_CLK_DOM_FLAG_CORE },
+       { nv_clk_src_hubk01 , 0x05 },
+       { nv_clk_src_vdec   , 0x06 },
+       { nv_clk_src_daemon , 0x07 },
+       { nv_clk_src_max }
+};
+
+static int
+gk104_clk_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+              struct nvkm_oclass *oclass, void *data, u32 size,
+              struct nvkm_object **pobject)
+{
+       struct gk104_clk_priv *priv;
+       int ret;
+
+       ret = nvkm_clk_create(parent, engine, oclass, gk104_domain,
+                             NULL, 0, true, &priv);
+       *pobject = nv_object(priv);
+       if (ret)
+               return ret;
+
+       priv->base.read = gk104_clk_read;
+       priv->base.calc = gk104_clk_calc;
+       priv->base.prog = gk104_clk_prog;
+       priv->base.tidy = gk104_clk_tidy;
+       return 0;
+}
+
+struct nvkm_oclass
+gk104_clk_oclass = {
+       .handle = NV_SUBDEV(CLK, 0xe0),
+       .ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = gk104_clk_ctor,
+               .dtor = _nvkm_clk_dtor,
+               .init = _nvkm_clk_init,
+               .fini = _nvkm_clk_fini,
+       },
+};
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/clk/gk20a.c b/drivers/gpu/drm/nouveau/nvkm/subdev/clk/gk20a.c
new file mode 100644 (file)
index 0000000..65c5327
--- /dev/null
@@ -0,0 +1,680 @@
+/*
+ * Copyright (c) 2014, NVIDIA CORPORATION. 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 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.
+ *
+ * Shamelessly ripped off from ChromeOS's gk20a/clk_pllg.c
+ *
+ */
+#include <subdev/clk.h>
+#include <subdev/timer.h>
+
+#include <core/device.h>
+
+#ifdef __KERNEL__
+#include <nouveau_platform.h>
+#endif
+
+#define MHZ (1000 * 1000)
+
+#define MASK(w)        ((1 << w) - 1)
+
+#define SYS_GPCPLL_CFG_BASE                    0x00137000
+#define GPC_BCASE_GPCPLL_CFG_BASE              0x00132800
+
+#define GPCPLL_CFG             (SYS_GPCPLL_CFG_BASE + 0)
+#define GPCPLL_CFG_ENABLE      BIT(0)
+#define GPCPLL_CFG_IDDQ                BIT(1)
+#define GPCPLL_CFG_LOCK_DET_OFF        BIT(4)
+#define GPCPLL_CFG_LOCK                BIT(17)
+
+#define GPCPLL_COEFF           (SYS_GPCPLL_CFG_BASE + 4)
+#define GPCPLL_COEFF_M_SHIFT   0
+#define GPCPLL_COEFF_M_WIDTH   8
+#define GPCPLL_COEFF_N_SHIFT   8
+#define GPCPLL_COEFF_N_WIDTH   8
+#define GPCPLL_COEFF_P_SHIFT   16
+#define GPCPLL_COEFF_P_WIDTH   6
+
+#define GPCPLL_CFG2                    (SYS_GPCPLL_CFG_BASE + 0xc)
+#define GPCPLL_CFG2_SETUP2_SHIFT       16
+#define GPCPLL_CFG2_PLL_STEPA_SHIFT    24
+
+#define GPCPLL_CFG3                    (SYS_GPCPLL_CFG_BASE + 0x18)
+#define GPCPLL_CFG3_PLL_STEPB_SHIFT    16
+
+#define GPCPLL_NDIV_SLOWDOWN                   (SYS_GPCPLL_CFG_BASE + 0x1c)
+#define GPCPLL_NDIV_SLOWDOWN_NDIV_LO_SHIFT     0
+#define GPCPLL_NDIV_SLOWDOWN_NDIV_MID_SHIFT    8
+#define GPCPLL_NDIV_SLOWDOWN_STEP_SIZE_LO2MID_SHIFT    16
+#define GPCPLL_NDIV_SLOWDOWN_SLOWDOWN_USING_PLL_SHIFT  22
+#define GPCPLL_NDIV_SLOWDOWN_EN_DYNRAMP_SHIFT  31
+
+#define SEL_VCO                                (SYS_GPCPLL_CFG_BASE + 0x100)
+#define SEL_VCO_GPC2CLK_OUT_SHIFT      0
+
+#define GPC2CLK_OUT                    (SYS_GPCPLL_CFG_BASE + 0x250)
+#define GPC2CLK_OUT_SDIV14_INDIV4_WIDTH        1
+#define GPC2CLK_OUT_SDIV14_INDIV4_SHIFT        31
+#define GPC2CLK_OUT_SDIV14_INDIV4_MODE 1
+#define GPC2CLK_OUT_VCODIV_WIDTH       6
+#define GPC2CLK_OUT_VCODIV_SHIFT       8
+#define GPC2CLK_OUT_VCODIV1            0
+#define GPC2CLK_OUT_VCODIV_MASK                (MASK(GPC2CLK_OUT_VCODIV_WIDTH) << \
+                                       GPC2CLK_OUT_VCODIV_SHIFT)
+#define        GPC2CLK_OUT_BYPDIV_WIDTH        6
+#define GPC2CLK_OUT_BYPDIV_SHIFT       0
+#define GPC2CLK_OUT_BYPDIV31           0x3c
+#define GPC2CLK_OUT_INIT_MASK  ((MASK(GPC2CLK_OUT_SDIV14_INDIV4_WIDTH) << \
+               GPC2CLK_OUT_SDIV14_INDIV4_SHIFT)\
+               | (MASK(GPC2CLK_OUT_VCODIV_WIDTH) << GPC2CLK_OUT_VCODIV_SHIFT)\
+               | (MASK(GPC2CLK_OUT_BYPDIV_WIDTH) << GPC2CLK_OUT_BYPDIV_SHIFT))
+#define GPC2CLK_OUT_INIT_VAL   ((GPC2CLK_OUT_SDIV14_INDIV4_MODE << \
+               GPC2CLK_OUT_SDIV14_INDIV4_SHIFT) \
+               | (GPC2CLK_OUT_VCODIV1 << GPC2CLK_OUT_VCODIV_SHIFT) \
+               | (GPC2CLK_OUT_BYPDIV31 << GPC2CLK_OUT_BYPDIV_SHIFT))
+
+#define GPC_BCAST_NDIV_SLOWDOWN_DEBUG  (GPC_BCASE_GPCPLL_CFG_BASE + 0xa0)
+#define GPC_BCAST_NDIV_SLOWDOWN_DEBUG_PLL_DYNRAMP_DONE_SYNCED_SHIFT    24
+#define GPC_BCAST_NDIV_SLOWDOWN_DEBUG_PLL_DYNRAMP_DONE_SYNCED_MASK \
+           (0x1 << GPC_BCAST_NDIV_SLOWDOWN_DEBUG_PLL_DYNRAMP_DONE_SYNCED_SHIFT)
+
+static const u8 pl_to_div[] = {
+/* PL:   0, 1, 2, 3, 4, 5, 6,  7,  8,  9, 10, 11, 12, 13, 14 */
+/* p: */ 1, 2, 3, 4, 5, 6, 8, 10, 12, 16, 12, 16, 20, 24, 32,
+};
+
+/* All frequencies in Mhz */
+struct gk20a_clk_pllg_params {
+       u32 min_vco, max_vco;
+       u32 min_u, max_u;
+       u32 min_m, max_m;
+       u32 min_n, max_n;
+       u32 min_pl, max_pl;
+};
+
+static const struct gk20a_clk_pllg_params gk20a_pllg_params = {
+       .min_vco = 1000, .max_vco = 2064,
+       .min_u = 12, .max_u = 38,
+       .min_m = 1, .max_m = 255,
+       .min_n = 8, .max_n = 255,
+       .min_pl = 1, .max_pl = 32,
+};
+
+struct gk20a_clk_priv {
+       struct nvkm_clk base;
+       const struct gk20a_clk_pllg_params *params;
+       u32 m, n, pl;
+       u32 parent_rate;
+};
+#define to_gk20a_clk(base) container_of(base, struct gk20a_clk_priv, base)
+
+static void
+gk20a_pllg_read_mnp(struct gk20a_clk_priv *priv)
+{
+       u32 val;
+
+       val = nv_rd32(priv, GPCPLL_COEFF);
+       priv->m = (val >> GPCPLL_COEFF_M_SHIFT) & MASK(GPCPLL_COEFF_M_WIDTH);
+       priv->n = (val >> GPCPLL_COEFF_N_SHIFT) & MASK(GPCPLL_COEFF_N_WIDTH);
+       priv->pl = (val >> GPCPLL_COEFF_P_SHIFT) & MASK(GPCPLL_COEFF_P_WIDTH);
+}
+
+static u32
+gk20a_pllg_calc_rate(struct gk20a_clk_priv *priv)
+{
+       u32 rate;
+       u32 divider;
+
+       rate = priv->parent_rate * priv->n;
+       divider = priv->m * pl_to_div[priv->pl];
+       do_div(rate, divider);
+
+       return rate / 2;
+}
+
+static int
+gk20a_pllg_calc_mnp(struct gk20a_clk_priv *priv, unsigned long rate)
+{
+       u32 target_clk_f, ref_clk_f, target_freq;
+       u32 min_vco_f, max_vco_f;
+       u32 low_pl, high_pl, best_pl;
+       u32 target_vco_f, vco_f;
+       u32 best_m, best_n;
+       u32 u_f;
+       u32 m, n, n2;
+       u32 delta, lwv, best_delta = ~0;
+       u32 pl;
+
+       target_clk_f = rate * 2 / MHZ;
+       ref_clk_f = priv->parent_rate / MHZ;
+
+       max_vco_f = priv->params->max_vco;
+       min_vco_f = priv->params->min_vco;
+       best_m = priv->params->max_m;
+       best_n = priv->params->min_n;
+       best_pl = priv->params->min_pl;
+
+       target_vco_f = target_clk_f + target_clk_f / 50;
+       if (max_vco_f < target_vco_f)
+               max_vco_f = target_vco_f;
+
+       /* min_pl <= high_pl <= max_pl */
+       high_pl = (max_vco_f + target_vco_f - 1) / target_vco_f;
+       high_pl = min(high_pl, priv->params->max_pl);
+       high_pl = max(high_pl, priv->params->min_pl);
+
+       /* min_pl <= low_pl <= max_pl */
+       low_pl = min_vco_f / target_vco_f;
+       low_pl = min(low_pl, priv->params->max_pl);
+       low_pl = max(low_pl, priv->params->min_pl);
+
+       /* Find Indices of high_pl and low_pl */
+       for (pl = 0; pl < ARRAY_SIZE(pl_to_div) - 1; pl++) {
+               if (pl_to_div[pl] >= low_pl) {
+                       low_pl = pl;
+                       break;
+               }
+       }
+       for (pl = 0; pl < ARRAY_SIZE(pl_to_div) - 1; pl++) {
+               if (pl_to_div[pl] >= high_pl) {
+                       high_pl = pl;
+                       break;
+               }
+       }
+
+       nv_debug(priv, "low_PL %d(div%d), high_PL %d(div%d)", low_pl,
+                pl_to_div[low_pl], high_pl, pl_to_div[high_pl]);
+
+       /* Select lowest possible VCO */
+       for (pl = low_pl; pl <= high_pl; pl++) {
+               target_vco_f = target_clk_f * pl_to_div[pl];
+               for (m = priv->params->min_m; m <= priv->params->max_m; m++) {
+                       u_f = ref_clk_f / m;
+
+                       if (u_f < priv->params->min_u)
+                               break;
+                       if (u_f > priv->params->max_u)
+                               continue;
+
+                       n = (target_vco_f * m) / ref_clk_f;
+                       n2 = ((target_vco_f * m) + (ref_clk_f - 1)) / ref_clk_f;
+
+                       if (n > priv->params->max_n)
+                               break;
+
+                       for (; n <= n2; n++) {
+                               if (n < priv->params->min_n)
+                                       continue;
+                               if (n > priv->params->max_n)
+                                       break;
+
+                               vco_f = ref_clk_f * n / m;
+
+                               if (vco_f >= min_vco_f && vco_f <= max_vco_f) {
+                                       lwv = (vco_f + (pl_to_div[pl] / 2))
+                                               / pl_to_div[pl];
+                                       delta = abs(lwv - target_clk_f);
+
+                                       if (delta < best_delta) {
+                                               best_delta = delta;
+                                               best_m = m;
+                                               best_n = n;
+                                               best_pl = pl;
+
+                                               if (best_delta == 0)
+                                                       goto found_match;
+                                       }
+                               }
+                       }
+               }
+       }
+
+found_match:
+       WARN_ON(best_delta == ~0);
+
+       if (best_delta != 0)
+               nv_debug(priv, "no best match for target @ %dMHz on gpc_pll",
+                        target_clk_f);
+
+       priv->m = best_m;
+       priv->n = best_n;
+       priv->pl = best_pl;
+
+       target_freq = gk20a_pllg_calc_rate(priv) / MHZ;
+
+       nv_debug(priv, "actual target freq %d MHz, M %d, N %d, PL %d(div%d)\n",
+                target_freq, priv->m, priv->n, priv->pl, pl_to_div[priv->pl]);
+       return 0;
+}
+
+static int
+gk20a_pllg_slide(struct gk20a_clk_priv *priv, u32 n)
+{
+       u32 val;
+       int ramp_timeout;
+
+       /* get old coefficients */
+       val = nv_rd32(priv, GPCPLL_COEFF);
+       /* do nothing if NDIV is the same */
+       if (n == ((val >> GPCPLL_COEFF_N_SHIFT) & MASK(GPCPLL_COEFF_N_WIDTH)))
+               return 0;
+
+       /* setup */
+       nv_mask(priv, GPCPLL_CFG2, 0xff << GPCPLL_CFG2_PLL_STEPA_SHIFT,
+               0x2b << GPCPLL_CFG2_PLL_STEPA_SHIFT);
+       nv_mask(priv, GPCPLL_CFG3, 0xff << GPCPLL_CFG3_PLL_STEPB_SHIFT,
+               0xb << GPCPLL_CFG3_PLL_STEPB_SHIFT);
+
+       /* pll slowdown mode */
+       nv_mask(priv, GPCPLL_NDIV_SLOWDOWN,
+               BIT(GPCPLL_NDIV_SLOWDOWN_SLOWDOWN_USING_PLL_SHIFT),
+               BIT(GPCPLL_NDIV_SLOWDOWN_SLOWDOWN_USING_PLL_SHIFT));
+
+       /* new ndiv ready for ramp */
+       val = nv_rd32(priv, GPCPLL_COEFF);
+       val &= ~(MASK(GPCPLL_COEFF_N_WIDTH) << GPCPLL_COEFF_N_SHIFT);
+       val |= (n & MASK(GPCPLL_COEFF_N_WIDTH)) << GPCPLL_COEFF_N_SHIFT;
+       udelay(1);
+       nv_wr32(priv, GPCPLL_COEFF, val);
+
+       /* dynamic ramp to new ndiv */
+       val = nv_rd32(priv, GPCPLL_NDIV_SLOWDOWN);
+       val |= 0x1 << GPCPLL_NDIV_SLOWDOWN_EN_DYNRAMP_SHIFT;
+       udelay(1);
+       nv_wr32(priv, GPCPLL_NDIV_SLOWDOWN, val);
+
+       for (ramp_timeout = 500; ramp_timeout > 0; ramp_timeout--) {
+               udelay(1);
+               val = nv_rd32(priv, GPC_BCAST_NDIV_SLOWDOWN_DEBUG);
+               if (val & GPC_BCAST_NDIV_SLOWDOWN_DEBUG_PLL_DYNRAMP_DONE_SYNCED_MASK)
+                       break;
+       }
+
+       /* exit slowdown mode */
+       nv_mask(priv, GPCPLL_NDIV_SLOWDOWN,
+               BIT(GPCPLL_NDIV_SLOWDOWN_SLOWDOWN_USING_PLL_SHIFT) |
+               BIT(GPCPLL_NDIV_SLOWDOWN_EN_DYNRAMP_SHIFT), 0);
+       nv_rd32(priv, GPCPLL_NDIV_SLOWDOWN);
+
+       if (ramp_timeout <= 0) {
+               nv_error(priv, "gpcpll dynamic ramp timeout\n");
+               return -ETIMEDOUT;
+       }
+
+       return 0;
+}
+
+static void
+_gk20a_pllg_enable(struct gk20a_clk_priv *priv)
+{
+       nv_mask(priv, GPCPLL_CFG, GPCPLL_CFG_ENABLE, GPCPLL_CFG_ENABLE);
+       nv_rd32(priv, GPCPLL_CFG);
+}
+
+static void
+_gk20a_pllg_disable(struct gk20a_clk_priv *priv)
+{
+       nv_mask(priv, GPCPLL_CFG, GPCPLL_CFG_ENABLE, 0);
+       nv_rd32(priv, GPCPLL_CFG);
+}
+
+static int
+_gk20a_pllg_program_mnp(struct gk20a_clk_priv *priv, bool allow_slide)
+{
+       u32 val, cfg;
+       u32 m_old, pl_old, n_lo;
+
+       /* get old coefficients */
+       val = nv_rd32(priv, GPCPLL_COEFF);
+       m_old = (val >> GPCPLL_COEFF_M_SHIFT) & MASK(GPCPLL_COEFF_M_WIDTH);
+       pl_old = (val >> GPCPLL_COEFF_P_SHIFT) & MASK(GPCPLL_COEFF_P_WIDTH);
+
+       /* do NDIV slide if there is no change in M and PL */
+       cfg = nv_rd32(priv, GPCPLL_CFG);
+       if (allow_slide && priv->m == m_old && priv->pl == pl_old &&
+           (cfg & GPCPLL_CFG_ENABLE)) {
+               return gk20a_pllg_slide(priv, priv->n);
+       }
+
+       /* slide down to NDIV_LO */
+       n_lo = DIV_ROUND_UP(m_old * priv->params->min_vco,
+                           priv->parent_rate / MHZ);
+       if (allow_slide && (cfg & GPCPLL_CFG_ENABLE)) {
+               int ret = gk20a_pllg_slide(priv, n_lo);
+
+               if (ret)
+                       return ret;
+       }
+
+       /* split FO-to-bypass jump in halfs by setting out divider 1:2 */
+       nv_mask(priv, GPC2CLK_OUT, GPC2CLK_OUT_VCODIV_MASK,
+               0x2 << GPC2CLK_OUT_VCODIV_SHIFT);
+
+       /* put PLL in bypass before programming it */
+       val = nv_rd32(priv, SEL_VCO);
+       val &= ~(BIT(SEL_VCO_GPC2CLK_OUT_SHIFT));
+       udelay(2);
+       nv_wr32(priv, SEL_VCO, val);
+
+       /* get out from IDDQ */
+       val = nv_rd32(priv, GPCPLL_CFG);
+       if (val & GPCPLL_CFG_IDDQ) {
+               val &= ~GPCPLL_CFG_IDDQ;
+               nv_wr32(priv, GPCPLL_CFG, val);
+               nv_rd32(priv, GPCPLL_CFG);
+               udelay(2);
+       }
+
+       _gk20a_pllg_disable(priv);
+
+       nv_debug(priv, "%s: m=%d n=%d pl=%d\n", __func__, priv->m, priv->n,
+                priv->pl);
+
+       n_lo = DIV_ROUND_UP(priv->m * priv->params->min_vco,
+                           priv->parent_rate / MHZ);
+       val = priv->m << GPCPLL_COEFF_M_SHIFT;
+       val |= (allow_slide ? n_lo : priv->n) << GPCPLL_COEFF_N_SHIFT;
+       val |= priv->pl << GPCPLL_COEFF_P_SHIFT;
+       nv_wr32(priv, GPCPLL_COEFF, val);
+
+       _gk20a_pllg_enable(priv);
+
+       val = nv_rd32(priv, GPCPLL_CFG);
+       if (val & GPCPLL_CFG_LOCK_DET_OFF) {
+               val &= ~GPCPLL_CFG_LOCK_DET_OFF;
+               nv_wr32(priv, GPCPLL_CFG, val);
+       }
+
+       if (!nvkm_timer_wait_eq(priv, 300000, GPCPLL_CFG, GPCPLL_CFG_LOCK,
+                               GPCPLL_CFG_LOCK)) {
+               nv_error(priv, "%s: timeout waiting for pllg lock\n", __func__);
+               return -ETIMEDOUT;
+       }
+
+       /* switch to VCO mode */
+       nv_mask(priv, SEL_VCO, 0, BIT(SEL_VCO_GPC2CLK_OUT_SHIFT));
+
+       /* restore out divider 1:1 */
+       val = nv_rd32(priv, GPC2CLK_OUT);
+       val &= ~GPC2CLK_OUT_VCODIV_MASK;
+       udelay(2);
+       nv_wr32(priv, GPC2CLK_OUT, val);
+
+       /* slide up to new NDIV */
+       return allow_slide ? gk20a_pllg_slide(priv, priv->n) : 0;
+}
+
+static int
+gk20a_pllg_program_mnp(struct gk20a_clk_priv *priv)
+{
+       int err;
+
+       err = _gk20a_pllg_program_mnp(priv, true);
+       if (err)
+               err = _gk20a_pllg_program_mnp(priv, false);
+
+       return err;
+}
+
+static void
+gk20a_pllg_disable(struct gk20a_clk_priv *priv)
+{
+       u32 val;
+
+       /* slide to VCO min */
+       val = nv_rd32(priv, GPCPLL_CFG);
+       if (val & GPCPLL_CFG_ENABLE) {
+               u32 coeff, m, n_lo;
+
+               coeff = nv_rd32(priv, GPCPLL_COEFF);
+               m = (coeff >> GPCPLL_COEFF_M_SHIFT) & MASK(GPCPLL_COEFF_M_WIDTH);
+               n_lo = DIV_ROUND_UP(m * priv->params->min_vco,
+                                   priv->parent_rate / MHZ);
+               gk20a_pllg_slide(priv, n_lo);
+       }
+
+       /* put PLL in bypass before disabling it */
+       nv_mask(priv, SEL_VCO, BIT(SEL_VCO_GPC2CLK_OUT_SHIFT), 0);
+
+       _gk20a_pllg_disable(priv);
+}
+
+#define GK20A_CLK_GPC_MDIV 1000
+
+static struct nvkm_domain
+gk20a_domains[] = {
+       { nv_clk_src_crystal, 0xff },
+       { nv_clk_src_gpc, 0xff, 0, "core", GK20A_CLK_GPC_MDIV },
+       { nv_clk_src_max }
+};
+
+static struct nvkm_pstate
+gk20a_pstates[] = {
+       {
+               .base = {
+                       .domain[nv_clk_src_gpc] = 72000,
+                       .voltage = 0,
+               },
+       },
+       {
+               .base = {
+                       .domain[nv_clk_src_gpc] = 108000,
+                       .voltage = 1,
+               },
+       },
+       {
+               .base = {
+                       .domain[nv_clk_src_gpc] = 180000,
+                       .voltage = 2,
+               },
+       },
+       {
+               .base = {
+                       .domain[nv_clk_src_gpc] = 252000,
+                       .voltage = 3,
+               },
+       },
+       {
+               .base = {
+                       .domain[nv_clk_src_gpc] = 324000,
+                       .voltage = 4,
+               },
+       },
+       {
+               .base = {
+                       .domain[nv_clk_src_gpc] = 396000,
+                       .voltage = 5,
+               },
+       },
+       {
+               .base = {
+                       .domain[nv_clk_src_gpc] = 468000,
+                       .voltage = 6,
+               },
+       },
+       {
+               .base = {
+                       .domain[nv_clk_src_gpc] = 540000,
+                       .voltage = 7,
+               },
+       },
+       {
+               .base = {
+                       .domain[nv_clk_src_gpc] = 612000,
+                       .voltage = 8,
+               },
+       },
+       {
+               .base = {
+                       .domain[nv_clk_src_gpc] = 648000,
+                       .voltage = 9,
+               },
+       },
+       {
+               .base = {
+                       .domain[nv_clk_src_gpc] = 684000,
+                       .voltage = 10,
+               },
+       },
+       {
+               .base = {
+                       .domain[nv_clk_src_gpc] = 708000,
+                       .voltage = 11,
+               },
+       },
+       {
+               .base = {
+                       .domain[nv_clk_src_gpc] = 756000,
+                       .voltage = 12,
+               },
+       },
+       {
+               .base = {
+                       .domain[nv_clk_src_gpc] = 804000,
+                       .voltage = 13,
+               },
+       },
+       {
+               .base = {
+                       .domain[nv_clk_src_gpc] = 852000,
+                       .voltage = 14,
+               },
+       },
+};
+
+static int
+gk20a_clk_read(struct nvkm_clk *clk, enum nv_clk_src src)
+{
+       struct gk20a_clk_priv *priv = (void *)clk;
+
+       switch (src) {
+       case nv_clk_src_crystal:
+               return nv_device(clk)->crystal;
+       case nv_clk_src_gpc:
+               gk20a_pllg_read_mnp(priv);
+               return gk20a_pllg_calc_rate(priv) / GK20A_CLK_GPC_MDIV;
+       default:
+               nv_error(clk, "invalid clock source %d\n", src);
+               return -EINVAL;
+       }
+}
+
+static int
+gk20a_clk_calc(struct nvkm_clk *clk, struct nvkm_cstate *cstate)
+{
+       struct gk20a_clk_priv *priv = (void *)clk;
+
+       return gk20a_pllg_calc_mnp(priv, cstate->domain[nv_clk_src_gpc] *
+                                        GK20A_CLK_GPC_MDIV);
+}
+
+static int
+gk20a_clk_prog(struct nvkm_clk *clk)
+{
+       struct gk20a_clk_priv *priv = (void *)clk;
+
+       return gk20a_pllg_program_mnp(priv);
+}
+
+static void
+gk20a_clk_tidy(struct nvkm_clk *clk)
+{
+}
+
+static int
+gk20a_clk_fini(struct nvkm_object *object, bool suspend)
+{
+       struct gk20a_clk_priv *priv = (void *)object;
+       int ret;
+
+       ret = nvkm_clk_fini(&priv->base, false);
+
+       gk20a_pllg_disable(priv);
+
+       return ret;
+}
+
+static int
+gk20a_clk_init(struct nvkm_object *object)
+{
+       struct gk20a_clk_priv *priv = (void *)object;
+       int ret;
+
+       nv_mask(priv, GPC2CLK_OUT, GPC2CLK_OUT_INIT_MASK, GPC2CLK_OUT_INIT_VAL);
+
+       ret = nvkm_clk_init(&priv->base);
+       if (ret)
+               return ret;
+
+       ret = gk20a_clk_prog(&priv->base);
+       if (ret) {
+               nv_error(priv, "cannot initialize clock\n");
+               return ret;
+       }
+
+       return 0;
+}
+
+static int
+gk20a_clk_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+              struct nvkm_oclass *oclass, void *data, u32 size,
+              struct nvkm_object **pobject)
+{
+       struct gk20a_clk_priv *priv;
+       struct nouveau_platform_device *plat;
+       int ret;
+       int i;
+
+       /* Finish initializing the pstates */
+       for (i = 0; i < ARRAY_SIZE(gk20a_pstates); i++) {
+               INIT_LIST_HEAD(&gk20a_pstates[i].list);
+               gk20a_pstates[i].pstate = i + 1;
+       }
+
+       ret = nvkm_clk_create(parent, engine, oclass, gk20a_domains,
+                             gk20a_pstates, ARRAY_SIZE(gk20a_pstates),
+                             true, &priv);
+       *pobject = nv_object(priv);
+       if (ret)
+               return ret;
+
+       priv->params = &gk20a_pllg_params;
+
+       plat = nv_device_to_platform(nv_device(parent));
+       priv->parent_rate = clk_get_rate(plat->gpu->clk);
+       nv_info(priv, "parent clock rate: %d Mhz\n", priv->parent_rate / MHZ);
+
+       priv->base.read = gk20a_clk_read;
+       priv->base.calc = gk20a_clk_calc;
+       priv->base.prog = gk20a_clk_prog;
+       priv->base.tidy = gk20a_clk_tidy;
+       return 0;
+}
+
+struct nvkm_oclass
+gk20a_clk_oclass = {
+       .handle = NV_SUBDEV(CLK, 0xea),
+       .ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = gk20a_clk_ctor,
+               .dtor = _nvkm_subdev_dtor,
+               .init = gk20a_clk_init,
+               .fini = gk20a_clk_fini,
+       },
+};
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/clk/gt215.c b/drivers/gpu/drm/nouveau/nvkm/subdev/clk/gt215.c
new file mode 100644 (file)
index 0000000..822d32a
--- /dev/null
@@ -0,0 +1,533 @@
+/*
+ * Copyright 2012 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
+ *          Roy Spliet
+ */
+#include "gt215.h"
+#include "pll.h"
+
+#include <core/device.h>
+#include <engine/fifo.h>
+#include <subdev/bios.h>
+#include <subdev/bios/pll.h>
+#include <subdev/timer.h>
+
+struct gt215_clk_priv {
+       struct nvkm_clk base;
+       struct gt215_clk_info eng[nv_clk_src_max];
+};
+
+static u32 read_clk(struct gt215_clk_priv *, int, bool);
+static u32 read_pll(struct gt215_clk_priv *, int, u32);
+
+static u32
+read_vco(struct gt215_clk_priv *priv, int clk)
+{
+       u32 sctl = nv_rd32(priv, 0x4120 + (clk * 4));
+
+       switch (sctl & 0x00000030) {
+       case 0x00000000:
+               return nv_device(priv)->crystal;
+       case 0x00000020:
+               return read_pll(priv, 0x41, 0x00e820);
+       case 0x00000030:
+               return read_pll(priv, 0x42, 0x00e8a0);
+       default:
+               return 0;
+       }
+}
+
+static u32
+read_clk(struct gt215_clk_priv *priv, int clk, bool ignore_en)
+{
+       u32 sctl, sdiv, sclk;
+
+       /* refclk for the 0xe8xx plls is a fixed frequency */
+       if (clk >= 0x40) {
+               if (nv_device(priv)->chipset == 0xaf) {
+                       /* no joke.. seriously.. sigh.. */
+                       return nv_rd32(priv, 0x00471c) * 1000;
+               }
+
+               return nv_device(priv)->crystal;
+       }
+
+       sctl = nv_rd32(priv, 0x4120 + (clk * 4));
+       if (!ignore_en && !(sctl & 0x00000100))
+               return 0;
+
+       /* out_alt */
+       if (sctl & 0x00000400)
+               return 108000;
+
+       /* vco_out */
+       switch (sctl & 0x00003000) {
+       case 0x00000000:
+               if (!(sctl & 0x00000200))
+                       return nv_device(priv)->crystal;
+               return 0;
+       case 0x00002000:
+               if (sctl & 0x00000040)
+                       return 108000;
+               return 100000;
+       case 0x00003000:
+               /* vco_enable */
+               if (!(sctl & 0x00000001))
+                       return 0;
+
+               sclk = read_vco(priv, clk);
+               sdiv = ((sctl & 0x003f0000) >> 16) + 2;
+               return (sclk * 2) / sdiv;
+       default:
+               return 0;
+       }
+}
+
+static u32
+read_pll(struct gt215_clk_priv *priv, int clk, u32 pll)
+{
+       u32 ctrl = nv_rd32(priv, pll + 0);
+       u32 sclk = 0, P = 1, N = 1, M = 1;
+
+       if (!(ctrl & 0x00000008)) {
+               if (ctrl & 0x00000001) {
+                       u32 coef = nv_rd32(priv, pll + 4);
+                       M = (coef & 0x000000ff) >> 0;
+                       N = (coef & 0x0000ff00) >> 8;
+                       P = (coef & 0x003f0000) >> 16;
+
+                       /* no post-divider on these..
+                        * XXX: it looks more like two post-"dividers" that
+                        * cross each other out in the default RPLL config */
+                       if ((pll & 0x00ff00) == 0x00e800)
+                               P = 1;
+
+                       sclk = read_clk(priv, 0x00 + clk, false);
+               }
+       } else {
+               sclk = read_clk(priv, 0x10 + clk, false);
+       }
+
+       if (M * P)
+               return sclk * N / (M * P);
+
+       return 0;
+}
+
+static int
+gt215_clk_read(struct nvkm_clk *clk, enum nv_clk_src src)
+{
+       struct gt215_clk_priv *priv = (void *)clk;
+       u32 hsrc;
+
+       switch (src) {
+       case nv_clk_src_crystal:
+               return nv_device(priv)->crystal;
+       case nv_clk_src_core:
+       case nv_clk_src_core_intm:
+               return read_pll(priv, 0x00, 0x4200);
+       case nv_clk_src_shader:
+               return read_pll(priv, 0x01, 0x4220);
+       case nv_clk_src_mem:
+               return read_pll(priv, 0x02, 0x4000);
+       case nv_clk_src_disp:
+               return read_clk(priv, 0x20, false);
+       case nv_clk_src_vdec:
+               return read_clk(priv, 0x21, false);
+       case nv_clk_src_daemon:
+               return read_clk(priv, 0x25, false);
+       case nv_clk_src_host:
+               hsrc = (nv_rd32(priv, 0xc040) & 0x30000000) >> 28;
+               switch (hsrc) {
+               case 0:
+                       return read_clk(priv, 0x1d, false);
+               case 2:
+               case 3:
+                       return 277000;
+               default:
+                       nv_error(clk, "unknown HOST clock source %d\n", hsrc);
+                       return -EINVAL;
+               }
+       default:
+               nv_error(clk, "invalid clock source %d\n", src);
+               return -EINVAL;
+       }
+
+       return 0;
+}
+
+int
+gt215_clk_info(struct nvkm_clk *clock, int clk, u32 khz,
+              struct gt215_clk_info *info)
+{
+       struct gt215_clk_priv *priv = (void *)clock;
+       u32 oclk, sclk, sdiv, diff;
+
+       info->clk = 0;
+
+       switch (khz) {
+       case 27000:
+               info->clk = 0x00000100;
+               return khz;
+       case 100000:
+               info->clk = 0x00002100;
+               return khz;
+       case 108000:
+               info->clk = 0x00002140;
+               return khz;
+       default:
+               sclk = read_vco(priv, clk);
+               sdiv = min((sclk * 2) / khz, (u32)65);
+               oclk = (sclk * 2) / sdiv;
+               diff = ((khz + 3000) - oclk);
+
+               /* When imprecise, play it safe and aim for a clock lower than
+                * desired rather than higher */
+               if (diff < 0) {
+                       sdiv++;
+                       oclk = (sclk * 2) / sdiv;
+               }
+
+               /* divider can go as low as 2, limited here because NVIDIA
+                * and the VBIOS on my NVA8 seem to prefer using the PLL
+                * for 810MHz - is there a good reason?
+                * XXX: PLLs with refclk 810MHz?  */
+               if (sdiv > 4) {
+                       info->clk = (((sdiv - 2) << 16) | 0x00003100);
+                       return oclk;
+               }
+
+               break;
+       }
+
+       return -ERANGE;
+}
+
+int
+gt215_pll_info(struct nvkm_clk *clock, int clk, u32 pll, u32 khz,
+              struct gt215_clk_info *info)
+{
+       struct nvkm_bios *bios = nvkm_bios(clock);
+       struct gt215_clk_priv *priv = (void *)clock;
+       struct nvbios_pll limits;
+       int P, N, M, diff;
+       int ret;
+
+       info->pll = 0;
+
+       /* If we can get a within [-2, 3) MHz of a divider, we'll disable the
+        * PLL and use the divider instead. */
+       ret = gt215_clk_info(clock, clk, khz, info);
+       diff = khz - ret;
+       if (!pll || (diff >= -2000 && diff < 3000)) {
+               goto out;
+       }
+
+       /* Try with PLL */
+       ret = nvbios_pll_parse(bios, pll, &limits);
+       if (ret)
+               return ret;
+
+       ret = gt215_clk_info(clock, clk - 0x10, limits.refclk, info);
+       if (ret != limits.refclk)
+               return -EINVAL;
+
+       ret = gt215_pll_calc(nv_subdev(priv), &limits, khz, &N, NULL, &M, &P);
+       if (ret >= 0) {
+               info->pll = (P << 16) | (N << 8) | M;
+       }
+
+out:
+       info->fb_delay = max(((khz + 7566) / 15133), (u32) 18);
+       return ret ? ret : -ERANGE;
+}
+
+static int
+calc_clk(struct gt215_clk_priv *priv, struct nvkm_cstate *cstate,
+        int clk, u32 pll, int idx)
+{
+       int ret = gt215_pll_info(&priv->base, clk, pll, cstate->domain[idx],
+                                &priv->eng[idx]);
+       if (ret >= 0)
+               return 0;
+       return ret;
+}
+
+static int
+calc_host(struct gt215_clk_priv *priv, struct nvkm_cstate *cstate)
+{
+       int ret = 0;
+       u32 kHz = cstate->domain[nv_clk_src_host];
+       struct gt215_clk_info *info = &priv->eng[nv_clk_src_host];
+
+       if (kHz == 277000) {
+               info->clk = 0;
+               info->host_out = NVA3_HOST_277;
+               return 0;
+       }
+
+       info->host_out = NVA3_HOST_CLK;
+
+       ret = gt215_clk_info(&priv->base, 0x1d, kHz, info);
+       if (ret >= 0)
+               return 0;
+
+       return ret;
+}
+
+int
+gt215_clk_pre(struct nvkm_clk *clk, unsigned long *flags)
+{
+       struct nvkm_fifo *pfifo = nvkm_fifo(clk);
+
+       /* halt and idle execution engines */
+       nv_mask(clk, 0x020060, 0x00070000, 0x00000000);
+       nv_mask(clk, 0x002504, 0x00000001, 0x00000001);
+       /* Wait until the interrupt handler is finished */
+       if (!nv_wait(clk, 0x000100, 0xffffffff, 0x00000000))
+               return -EBUSY;
+
+       if (pfifo)
+               pfifo->pause(pfifo, flags);
+
+       if (!nv_wait(clk, 0x002504, 0x00000010, 0x00000010))
+               return -EIO;
+       if (!nv_wait(clk, 0x00251c, 0x0000003f, 0x0000003f))
+               return -EIO;
+
+       return 0;
+}
+
+void
+gt215_clk_post(struct nvkm_clk *clk, unsigned long *flags)
+{
+       struct nvkm_fifo *pfifo = nvkm_fifo(clk);
+
+       if (pfifo && flags)
+               pfifo->start(pfifo, flags);
+
+       nv_mask(clk, 0x002504, 0x00000001, 0x00000000);
+       nv_mask(clk, 0x020060, 0x00070000, 0x00040000);
+}
+
+static void
+disable_clk_src(struct gt215_clk_priv *priv, u32 src)
+{
+       nv_mask(priv, src, 0x00000100, 0x00000000);
+       nv_mask(priv, src, 0x00000001, 0x00000000);
+}
+
+static void
+prog_pll(struct gt215_clk_priv *priv, int clk, u32 pll, int idx)
+{
+       struct gt215_clk_info *info = &priv->eng[idx];
+       const u32 src0 = 0x004120 + (clk * 4);
+       const u32 src1 = 0x004160 + (clk * 4);
+       const u32 ctrl = pll + 0;
+       const u32 coef = pll + 4;
+       u32 bypass;
+
+       if (info->pll) {
+               /* Always start from a non-PLL clock */
+               bypass = nv_rd32(priv, ctrl)  & 0x00000008;
+               if (!bypass) {
+                       nv_mask(priv, src1, 0x00000101, 0x00000101);
+                       nv_mask(priv, ctrl, 0x00000008, 0x00000008);
+                       udelay(20);
+               }
+
+               nv_mask(priv, src0, 0x003f3141, 0x00000101 | info->clk);
+               nv_wr32(priv, coef, info->pll);
+               nv_mask(priv, ctrl, 0x00000015, 0x00000015);
+               nv_mask(priv, ctrl, 0x00000010, 0x00000000);
+               if (!nv_wait(priv, ctrl, 0x00020000, 0x00020000)) {
+                       nv_mask(priv, ctrl, 0x00000010, 0x00000010);
+                       nv_mask(priv, src0, 0x00000101, 0x00000000);
+                       return;
+               }
+               nv_mask(priv, ctrl, 0x00000010, 0x00000010);
+               nv_mask(priv, ctrl, 0x00000008, 0x00000000);
+               disable_clk_src(priv, src1);
+       } else {
+               nv_mask(priv, src1, 0x003f3141, 0x00000101 | info->clk);
+               nv_mask(priv, ctrl, 0x00000018, 0x00000018);
+               udelay(20);
+               nv_mask(priv, ctrl, 0x00000001, 0x00000000);
+               disable_clk_src(priv, src0);
+       }
+}
+
+static void
+prog_clk(struct gt215_clk_priv *priv, int clk, int idx)
+{
+       struct gt215_clk_info *info = &priv->eng[idx];
+       nv_mask(priv, 0x004120 + (clk * 4), 0x003f3141, 0x00000101 | info->clk);
+}
+
+static void
+prog_host(struct gt215_clk_priv *priv)
+{
+       struct gt215_clk_info *info = &priv->eng[nv_clk_src_host];
+       u32 hsrc = (nv_rd32(priv, 0xc040));
+
+       switch (info->host_out) {
+       case NVA3_HOST_277:
+               if ((hsrc & 0x30000000) == 0) {
+                       nv_wr32(priv, 0xc040, hsrc | 0x20000000);
+                       disable_clk_src(priv, 0x4194);
+               }
+               break;
+       case NVA3_HOST_CLK:
+               prog_clk(priv, 0x1d, nv_clk_src_host);
+               if ((hsrc & 0x30000000) >= 0x20000000) {
+                       nv_wr32(priv, 0xc040, hsrc & ~0x30000000);
+               }
+               break;
+       default:
+               break;
+       }
+
+       /* This seems to be a clock gating factor on idle, always set to 64 */
+       nv_wr32(priv, 0xc044, 0x3e);
+}
+
+static void
+prog_core(struct gt215_clk_priv *priv, int idx)
+{
+       struct gt215_clk_info *info = &priv->eng[idx];
+       u32 fb_delay = nv_rd32(priv, 0x10002c);
+
+       if (fb_delay < info->fb_delay)
+               nv_wr32(priv, 0x10002c, info->fb_delay);
+
+       prog_pll(priv, 0x00, 0x004200, idx);
+
+       if (fb_delay > info->fb_delay)
+               nv_wr32(priv, 0x10002c, info->fb_delay);
+}
+
+static int
+gt215_clk_calc(struct nvkm_clk *clk, struct nvkm_cstate *cstate)
+{
+       struct gt215_clk_priv *priv = (void *)clk;
+       struct gt215_clk_info *core = &priv->eng[nv_clk_src_core];
+       int ret;
+
+       if ((ret = calc_clk(priv, cstate, 0x10, 0x4200, nv_clk_src_core)) ||
+           (ret = calc_clk(priv, cstate, 0x11, 0x4220, nv_clk_src_shader)) ||
+           (ret = calc_clk(priv, cstate, 0x20, 0x0000, nv_clk_src_disp)) ||
+           (ret = calc_clk(priv, cstate, 0x21, 0x0000, nv_clk_src_vdec)) ||
+           (ret = calc_host(priv, cstate)))
+               return ret;
+
+       /* XXX: Should be reading the highest bit in the VBIOS clock to decide
+        * whether to use a PLL or not... but using a PLL defeats the purpose */
+       if (core->pll) {
+               ret = gt215_clk_info(clk, 0x10,
+                                    cstate->domain[nv_clk_src_core_intm],
+                                    &priv->eng[nv_clk_src_core_intm]);
+               if (ret < 0)
+                       return ret;
+       }
+
+       return 0;
+}
+
+static int
+gt215_clk_prog(struct nvkm_clk *clk)
+{
+       struct gt215_clk_priv *priv = (void *)clk;
+       struct gt215_clk_info *core = &priv->eng[nv_clk_src_core];
+       int ret = 0;
+       unsigned long flags;
+       unsigned long *f = &flags;
+
+       ret = gt215_clk_pre(clk, f);
+       if (ret)
+               goto out;
+
+       if (core->pll)
+               prog_core(priv, nv_clk_src_core_intm);
+
+       prog_core(priv,  nv_clk_src_core);
+       prog_pll(priv, 0x01, 0x004220, nv_clk_src_shader);
+       prog_clk(priv, 0x20, nv_clk_src_disp);
+       prog_clk(priv, 0x21, nv_clk_src_vdec);
+       prog_host(priv);
+
+out:
+       if (ret == -EBUSY)
+               f = NULL;
+
+       gt215_clk_post(clk, f);
+       return ret;
+}
+
+static void
+gt215_clk_tidy(struct nvkm_clk *clk)
+{
+}
+
+static struct nvkm_domain
+gt215_domain[] = {
+       { nv_clk_src_crystal  , 0xff },
+       { nv_clk_src_core     , 0x00, 0, "core", 1000 },
+       { nv_clk_src_shader   , 0x01, 0, "shader", 1000 },
+       { nv_clk_src_mem      , 0x02, 0, "memory", 1000 },
+       { nv_clk_src_vdec     , 0x03 },
+       { nv_clk_src_disp     , 0x04 },
+       { nv_clk_src_host     , 0x05 },
+       { nv_clk_src_core_intm, 0x06 },
+       { nv_clk_src_max }
+};
+
+static int
+gt215_clk_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+              struct nvkm_oclass *oclass, void *data, u32 size,
+              struct nvkm_object **pobject)
+{
+       struct gt215_clk_priv *priv;
+       int ret;
+
+       ret = nvkm_clk_create(parent, engine, oclass, gt215_domain,
+                             NULL, 0, true, &priv);
+       *pobject = nv_object(priv);
+       if (ret)
+               return ret;
+
+       priv->base.read = gt215_clk_read;
+       priv->base.calc = gt215_clk_calc;
+       priv->base.prog = gt215_clk_prog;
+       priv->base.tidy = gt215_clk_tidy;
+       return 0;
+}
+
+struct nvkm_oclass
+gt215_clk_oclass = {
+       .handle = NV_SUBDEV(CLK, 0xa3),
+       .ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = gt215_clk_ctor,
+               .dtor = _nvkm_clk_dtor,
+               .init = _nvkm_clk_init,
+               .fini = _nvkm_clk_fini,
+       },
+};
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/clk/gt215.h b/drivers/gpu/drm/nouveau/nvkm/subdev/clk/gt215.h
new file mode 100644 (file)
index 0000000..b447d9c
--- /dev/null
@@ -0,0 +1,18 @@
+#ifndef __NVKM_CLK_NVA3_H__
+#define __NVKM_CLK_NVA3_H__
+#include <subdev/clk.h>
+
+struct gt215_clk_info {
+       u32 clk;
+       u32 pll;
+       enum {
+               NVA3_HOST_277,
+               NVA3_HOST_CLK,
+       } host_out;
+       u32 fb_delay;
+};
+
+int  gt215_pll_info(struct nvkm_clk *, int, u32, u32, struct gt215_clk_info *);
+int  gt215_clk_pre(struct nvkm_clk *clk, unsigned long *flags);
+void gt215_clk_post(struct nvkm_clk *clk, unsigned long *flags);
+#endif
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/clk/mcp77.c b/drivers/gpu/drm/nouveau/nvkm/subdev/clk/mcp77.c
new file mode 100644 (file)
index 0000000..c54417b
--- /dev/null
@@ -0,0 +1,429 @@
+/*
+ * Copyright 2012 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 "gt215.h"
+#include "pll.h"
+
+#include <core/device.h>
+#include <subdev/bios.h>
+#include <subdev/bios/pll.h>
+#include <subdev/timer.h>
+
+struct mcp77_clk_priv {
+       struct nvkm_clk base;
+       enum nv_clk_src csrc, ssrc, vsrc;
+       u32 cctrl, sctrl;
+       u32 ccoef, scoef;
+       u32 cpost, spost;
+       u32 vdiv;
+};
+
+static u32
+read_div(struct nvkm_clk *clk)
+{
+       return nv_rd32(clk, 0x004600);
+}
+
+static u32
+read_pll(struct nvkm_clk *clk, u32 base)
+{
+       u32 ctrl = nv_rd32(clk, base + 0);
+       u32 coef = nv_rd32(clk, base + 4);
+       u32 ref = clk->read(clk, nv_clk_src_href);
+       u32 post_div = 0;
+       u32 clock = 0;
+       int N1, M1;
+
+       switch (base){
+       case 0x4020:
+               post_div = 1 << ((nv_rd32(clk, 0x4070) & 0x000f0000) >> 16);
+               break;
+       case 0x4028:
+               post_div = (nv_rd32(clk, 0x4040) & 0x000f0000) >> 16;
+               break;
+       default:
+               break;
+       }
+
+       N1 = (coef & 0x0000ff00) >> 8;
+       M1 = (coef & 0x000000ff);
+       if ((ctrl & 0x80000000) && M1) {
+               clock = ref * N1 / M1;
+               clock = clock / post_div;
+       }
+
+       return clock;
+}
+
+static int
+mcp77_clk_read(struct nvkm_clk *clk, enum nv_clk_src src)
+{
+       struct mcp77_clk_priv *priv = (void *)clk;
+       u32 mast = nv_rd32(clk, 0x00c054);
+       u32 P = 0;
+
+       switch (src) {
+       case nv_clk_src_crystal:
+               return nv_device(priv)->crystal;
+       case nv_clk_src_href:
+               return 100000; /* PCIE reference clock */
+       case nv_clk_src_hclkm4:
+               return clk->read(clk, nv_clk_src_href) * 4;
+       case nv_clk_src_hclkm2d3:
+               return clk->read(clk, nv_clk_src_href) * 2 / 3;
+       case nv_clk_src_host:
+               switch (mast & 0x000c0000) {
+               case 0x00000000: return clk->read(clk, nv_clk_src_hclkm2d3);
+               case 0x00040000: break;
+               case 0x00080000: return clk->read(clk, nv_clk_src_hclkm4);
+               case 0x000c0000: return clk->read(clk, nv_clk_src_cclk);
+               }
+               break;
+       case nv_clk_src_core:
+               P = (nv_rd32(clk, 0x004028) & 0x00070000) >> 16;
+
+               switch (mast & 0x00000003) {
+               case 0x00000000: return clk->read(clk, nv_clk_src_crystal) >> P;
+               case 0x00000001: return 0;
+               case 0x00000002: return clk->read(clk, nv_clk_src_hclkm4) >> P;
+               case 0x00000003: return read_pll(clk, 0x004028) >> P;
+               }
+               break;
+       case nv_clk_src_cclk:
+               if ((mast & 0x03000000) != 0x03000000)
+                       return clk->read(clk, nv_clk_src_core);
+
+               if ((mast & 0x00000200) == 0x00000000)
+                       return clk->read(clk, nv_clk_src_core);
+
+               switch (mast & 0x00000c00) {
+               case 0x00000000: return clk->read(clk, nv_clk_src_href);
+               case 0x00000400: return clk->read(clk, nv_clk_src_hclkm4);
+               case 0x00000800: return clk->read(clk, nv_clk_src_hclkm2d3);
+               default: return 0;
+               }
+       case nv_clk_src_shader:
+               P = (nv_rd32(clk, 0x004020) & 0x00070000) >> 16;
+               switch (mast & 0x00000030) {
+               case 0x00000000:
+                       if (mast & 0x00000040)
+                               return clk->read(clk, nv_clk_src_href) >> P;
+                       return clk->read(clk, nv_clk_src_crystal) >> P;
+               case 0x00000010: break;
+               case 0x00000020: return read_pll(clk, 0x004028) >> P;
+               case 0x00000030: return read_pll(clk, 0x004020) >> P;
+               }
+               break;
+       case nv_clk_src_mem:
+               return 0;
+               break;
+       case nv_clk_src_vdec:
+               P = (read_div(clk) & 0x00000700) >> 8;
+
+               switch (mast & 0x00400000) {
+               case 0x00400000:
+                       return clk->read(clk, nv_clk_src_core) >> P;
+                       break;
+               default:
+                       return 500000 >> P;
+                       break;
+               }
+               break;
+       default:
+               break;
+       }
+
+       nv_debug(priv, "unknown clock source %d 0x%08x\n", src, mast);
+       return 0;
+}
+
+static u32
+calc_pll(struct mcp77_clk_priv *priv, u32 reg,
+        u32 clock, int *N, int *M, int *P)
+{
+       struct nvkm_bios *bios = nvkm_bios(priv);
+       struct nvbios_pll pll;
+       struct nvkm_clk *clk = &priv->base;
+       int ret;
+
+       ret = nvbios_pll_parse(bios, reg, &pll);
+       if (ret)
+               return 0;
+
+       pll.vco2.max_freq = 0;
+       pll.refclk = clk->read(clk, nv_clk_src_href);
+       if (!pll.refclk)
+               return 0;
+
+       return nv04_pll_calc(nv_subdev(priv), &pll, clock, N, M, NULL, NULL, P);
+}
+
+static inline u32
+calc_P(u32 src, u32 target, int *div)
+{
+       u32 clk0 = src, clk1 = src;
+       for (*div = 0; *div <= 7; (*div)++) {
+               if (clk0 <= target) {
+                       clk1 = clk0 << (*div ? 1 : 0);
+                       break;
+               }
+               clk0 >>= 1;
+       }
+
+       if (target - clk0 <= clk1 - target)
+               return clk0;
+       (*div)--;
+       return clk1;
+}
+
+static int
+mcp77_clk_calc(struct nvkm_clk *clk, struct nvkm_cstate *cstate)
+{
+       struct mcp77_clk_priv *priv = (void *)clk;
+       const int shader = cstate->domain[nv_clk_src_shader];
+       const int core = cstate->domain[nv_clk_src_core];
+       const int vdec = cstate->domain[nv_clk_src_vdec];
+       u32 out = 0, clock = 0;
+       int N, M, P1, P2 = 0;
+       int divs = 0;
+
+       /* cclk: find suitable source, disable PLL if we can */
+       if (core < clk->read(clk, nv_clk_src_hclkm4))
+               out = calc_P(clk->read(clk, nv_clk_src_hclkm4), core, &divs);
+
+       /* Calculate clock * 2, so shader clock can use it too */
+       clock = calc_pll(priv, 0x4028, (core << 1), &N, &M, &P1);
+
+       if (abs(core - out) <= abs(core - (clock >> 1))) {
+               priv->csrc = nv_clk_src_hclkm4;
+               priv->cctrl = divs << 16;
+       } else {
+               /* NVCTRL is actually used _after_ NVPOST, and after what we
+                * call NVPLL. To make matters worse, NVPOST is an integer
+                * divider instead of a right-shift number. */
+               if(P1 > 2) {
+                       P2 = P1 - 2;
+                       P1 = 2;
+               }
+
+               priv->csrc = nv_clk_src_core;
+               priv->ccoef = (N << 8) | M;
+
+               priv->cctrl = (P2 + 1) << 16;
+               priv->cpost = (1 << P1) << 16;
+       }
+
+       /* sclk: nvpll + divisor, href or spll */
+       out = 0;
+       if (shader == clk->read(clk, nv_clk_src_href)) {
+               priv->ssrc = nv_clk_src_href;
+       } else {
+               clock = calc_pll(priv, 0x4020, shader, &N, &M, &P1);
+               if (priv->csrc == nv_clk_src_core)
+                       out = calc_P((core << 1), shader, &divs);
+
+               if (abs(shader - out) <=
+                   abs(shader - clock) &&
+                  (divs + P2) <= 7) {
+                       priv->ssrc = nv_clk_src_core;
+                       priv->sctrl = (divs + P2) << 16;
+               } else {
+                       priv->ssrc = nv_clk_src_shader;
+                       priv->scoef = (N << 8) | M;
+                       priv->sctrl = P1 << 16;
+               }
+       }
+
+       /* vclk */
+       out = calc_P(core, vdec, &divs);
+       clock = calc_P(500000, vdec, &P1);
+       if(abs(vdec - out) <= abs(vdec - clock)) {
+               priv->vsrc = nv_clk_src_cclk;
+               priv->vdiv = divs << 16;
+       } else {
+               priv->vsrc = nv_clk_src_vdec;
+               priv->vdiv = P1 << 16;
+       }
+
+       /* Print strategy! */
+       nv_debug(priv, "nvpll: %08x %08x %08x\n",
+                       priv->ccoef, priv->cpost, priv->cctrl);
+       nv_debug(priv, " spll: %08x %08x %08x\n",
+                       priv->scoef, priv->spost, priv->sctrl);
+       nv_debug(priv, " vdiv: %08x\n", priv->vdiv);
+       if (priv->csrc == nv_clk_src_hclkm4)
+               nv_debug(priv, "core: hrefm4\n");
+       else
+               nv_debug(priv, "core: nvpll\n");
+
+       if (priv->ssrc == nv_clk_src_hclkm4)
+               nv_debug(priv, "shader: hrefm4\n");
+       else if (priv->ssrc == nv_clk_src_core)
+               nv_debug(priv, "shader: nvpll\n");
+       else
+               nv_debug(priv, "shader: spll\n");
+
+       if (priv->vsrc == nv_clk_src_hclkm4)
+               nv_debug(priv, "vdec: 500MHz\n");
+       else
+               nv_debug(priv, "vdec: core\n");
+
+       return 0;
+}
+
+static int
+mcp77_clk_prog(struct nvkm_clk *clk)
+{
+       struct mcp77_clk_priv *priv = (void *)clk;
+       u32 pllmask = 0, mast;
+       unsigned long flags;
+       unsigned long *f = &flags;
+       int ret = 0;
+
+       ret = gt215_clk_pre(clk, f);
+       if (ret)
+               goto out;
+
+       /* First switch to safe clocks: href */
+       mast = nv_mask(clk, 0xc054, 0x03400e70, 0x03400640);
+       mast &= ~0x00400e73;
+       mast |= 0x03000000;
+
+       switch (priv->csrc) {
+       case nv_clk_src_hclkm4:
+               nv_mask(clk, 0x4028, 0x00070000, priv->cctrl);
+               mast |= 0x00000002;
+               break;
+       case nv_clk_src_core:
+               nv_wr32(clk, 0x402c, priv->ccoef);
+               nv_wr32(clk, 0x4028, 0x80000000 | priv->cctrl);
+               nv_wr32(clk, 0x4040, priv->cpost);
+               pllmask |= (0x3 << 8);
+               mast |= 0x00000003;
+               break;
+       default:
+               nv_warn(priv,"Reclocking failed: unknown core clock\n");
+               goto resume;
+       }
+
+       switch (priv->ssrc) {
+       case nv_clk_src_href:
+               nv_mask(clk, 0x4020, 0x00070000, 0x00000000);
+               /* mast |= 0x00000000; */
+               break;
+       case nv_clk_src_core:
+               nv_mask(clk, 0x4020, 0x00070000, priv->sctrl);
+               mast |= 0x00000020;
+               break;
+       case nv_clk_src_shader:
+               nv_wr32(clk, 0x4024, priv->scoef);
+               nv_wr32(clk, 0x4020, 0x80000000 | priv->sctrl);
+               nv_wr32(clk, 0x4070, priv->spost);
+               pllmask |= (0x3 << 12);
+               mast |= 0x00000030;
+               break;
+       default:
+               nv_warn(priv,"Reclocking failed: unknown sclk clock\n");
+               goto resume;
+       }
+
+       if (!nv_wait(clk, 0x004080, pllmask, pllmask)) {
+               nv_warn(priv,"Reclocking failed: unstable PLLs\n");
+               goto resume;
+       }
+
+       switch (priv->vsrc) {
+       case nv_clk_src_cclk:
+               mast |= 0x00400000;
+       default:
+               nv_wr32(clk, 0x4600, priv->vdiv);
+       }
+
+       nv_wr32(clk, 0xc054, mast);
+
+resume:
+       /* Disable some PLLs and dividers when unused */
+       if (priv->csrc != nv_clk_src_core) {
+               nv_wr32(clk, 0x4040, 0x00000000);
+               nv_mask(clk, 0x4028, 0x80000000, 0x00000000);
+       }
+
+       if (priv->ssrc != nv_clk_src_shader) {
+               nv_wr32(clk, 0x4070, 0x00000000);
+               nv_mask(clk, 0x4020, 0x80000000, 0x00000000);
+       }
+
+out:
+       if (ret == -EBUSY)
+               f = NULL;
+
+       gt215_clk_post(clk, f);
+       return ret;
+}
+
+static void
+mcp77_clk_tidy(struct nvkm_clk *clk)
+{
+}
+
+static struct nvkm_domain
+mcp77_domains[] = {
+       { nv_clk_src_crystal, 0xff },
+       { nv_clk_src_href   , 0xff },
+       { nv_clk_src_core   , 0xff, 0, "core", 1000 },
+       { nv_clk_src_shader , 0xff, 0, "shader", 1000 },
+       { nv_clk_src_vdec   , 0xff, 0, "vdec", 1000 },
+       { nv_clk_src_max }
+};
+
+static int
+mcp77_clk_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+              struct nvkm_oclass *oclass, void *data, u32 size,
+              struct nvkm_object **pobject)
+{
+       struct mcp77_clk_priv *priv;
+       int ret;
+
+       ret = nvkm_clk_create(parent, engine, oclass, mcp77_domains,
+                             NULL, 0, true, &priv);
+       *pobject = nv_object(priv);
+       if (ret)
+               return ret;
+
+       priv->base.read = mcp77_clk_read;
+       priv->base.calc = mcp77_clk_calc;
+       priv->base.prog = mcp77_clk_prog;
+       priv->base.tidy = mcp77_clk_tidy;
+       return 0;
+}
+
+struct nvkm_oclass *
+mcp77_clk_oclass = &(struct nvkm_oclass) {
+       .handle = NV_SUBDEV(CLK, 0xaa),
+       .ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = mcp77_clk_ctor,
+               .dtor = _nvkm_clk_dtor,
+               .init = _nvkm_clk_init,
+               .fini = _nvkm_clk_fini,
+       },
+};
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/clk/nv04.c b/drivers/gpu/drm/nouveau/nvkm/subdev/clk/nv04.c
new file mode 100644 (file)
index 0000000..63dbbb5
--- /dev/null
@@ -0,0 +1,103 @@
+/*
+ * Copyright 2012 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 <subdev/clk.h>
+#include "pll.h"
+
+#include <subdev/bios.h>
+#include <subdev/bios/pll.h>
+#include <subdev/devinit/nv04.h>
+
+struct nv04_clk_priv {
+       struct nvkm_clk base;
+};
+
+int
+nv04_clk_pll_calc(struct nvkm_clk *clock, struct nvbios_pll *info,
+                 int clk, struct nvkm_pll_vals *pv)
+{
+       int N1, M1, N2, M2, P;
+       int ret = nv04_pll_calc(nv_subdev(clock), info, clk, &N1, &M1, &N2, &M2, &P);
+       if (ret) {
+               pv->refclk = info->refclk;
+               pv->N1 = N1;
+               pv->M1 = M1;
+               pv->N2 = N2;
+               pv->M2 = M2;
+               pv->log2P = P;
+       }
+       return ret;
+}
+
+int
+nv04_clk_pll_prog(struct nvkm_clk *clk, u32 reg1, struct nvkm_pll_vals *pv)
+{
+       struct nvkm_devinit *devinit = nvkm_devinit(clk);
+       int cv = nvkm_bios(clk)->version.chip;
+
+       if (cv == 0x30 || cv == 0x31 || cv == 0x35 || cv == 0x36 ||
+           cv >= 0x40) {
+               if (reg1 > 0x405c)
+                       setPLL_double_highregs(devinit, reg1, pv);
+               else
+                       setPLL_double_lowregs(devinit, reg1, pv);
+       } else
+               setPLL_single(devinit, reg1, pv);
+
+       return 0;
+}
+
+static struct nvkm_domain
+nv04_domain[] = {
+       { nv_clk_src_max }
+};
+
+static int
+nv04_clk_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+             struct nvkm_oclass *oclass, void *data, u32 size,
+             struct nvkm_object **pobject)
+{
+       struct nv04_clk_priv *priv;
+       int ret;
+
+       ret = nvkm_clk_create(parent, engine, oclass, nv04_domain,
+                             NULL, 0, false, &priv);
+       *pobject = nv_object(priv);
+       if (ret)
+               return ret;
+
+       priv->base.pll_calc = nv04_clk_pll_calc;
+       priv->base.pll_prog = nv04_clk_pll_prog;
+       return 0;
+}
+
+struct nvkm_oclass
+nv04_clk_oclass = {
+       .handle = NV_SUBDEV(CLK, 0x04),
+       .ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = nv04_clk_ctor,
+               .dtor = _nvkm_clk_dtor,
+               .init = _nvkm_clk_init,
+               .fini = _nvkm_clk_fini,
+       },
+};
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/clk/nv40.c b/drivers/gpu/drm/nouveau/nvkm/subdev/clk/nv40.c
new file mode 100644 (file)
index 0000000..ed83813
--- /dev/null
@@ -0,0 +1,241 @@
+/*
+ * Copyright 2012 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 <subdev/clk.h>
+#include "pll.h"
+
+#include <core/device.h>
+#include <subdev/bios.h>
+#include <subdev/bios/pll.h>
+
+struct nv40_clk_priv {
+       struct nvkm_clk base;
+       u32 ctrl;
+       u32 npll_ctrl;
+       u32 npll_coef;
+       u32 spll;
+};
+
+static struct nvkm_domain
+nv40_domain[] = {
+       { nv_clk_src_crystal, 0xff },
+       { nv_clk_src_href   , 0xff },
+       { nv_clk_src_core   , 0xff, 0, "core", 1000 },
+       { nv_clk_src_shader , 0xff, 0, "shader", 1000 },
+       { nv_clk_src_mem    , 0xff, 0, "memory", 1000 },
+       { nv_clk_src_max }
+};
+
+static u32
+read_pll_1(struct nv40_clk_priv *priv, u32 reg)
+{
+       u32 ctrl = nv_rd32(priv, reg + 0x00);
+       int P = (ctrl & 0x00070000) >> 16;
+       int N = (ctrl & 0x0000ff00) >> 8;
+       int M = (ctrl & 0x000000ff) >> 0;
+       u32 ref = 27000, clk = 0;
+
+       if (ctrl & 0x80000000)
+               clk = ref * N / M;
+
+       return clk >> P;
+}
+
+static u32
+read_pll_2(struct nv40_clk_priv *priv, u32 reg)
+{
+       u32 ctrl = nv_rd32(priv, reg + 0x00);
+       u32 coef = nv_rd32(priv, reg + 0x04);
+       int N2 = (coef & 0xff000000) >> 24;
+       int M2 = (coef & 0x00ff0000) >> 16;
+       int N1 = (coef & 0x0000ff00) >> 8;
+       int M1 = (coef & 0x000000ff) >> 0;
+       int P = (ctrl & 0x00070000) >> 16;
+       u32 ref = 27000, clk = 0;
+
+       if ((ctrl & 0x80000000) && M1) {
+               clk = ref * N1 / M1;
+               if ((ctrl & 0x40000100) == 0x40000000) {
+                       if (M2)
+                               clk = clk * N2 / M2;
+                       else
+                               clk = 0;
+               }
+       }
+
+       return clk >> P;
+}
+
+static u32
+read_clk(struct nv40_clk_priv *priv, u32 src)
+{
+       switch (src) {
+       case 3:
+               return read_pll_2(priv, 0x004000);
+       case 2:
+               return read_pll_1(priv, 0x004008);
+       default:
+               break;
+       }
+
+       return 0;
+}
+
+static int
+nv40_clk_read(struct nvkm_clk *clk, enum nv_clk_src src)
+{
+       struct nv40_clk_priv *priv = (void *)clk;
+       u32 mast = nv_rd32(priv, 0x00c040);
+
+       switch (src) {
+       case nv_clk_src_crystal:
+               return nv_device(priv)->crystal;
+       case nv_clk_src_href:
+               return 100000; /*XXX: PCIE/AGP differ*/
+       case nv_clk_src_core:
+               return read_clk(priv, (mast & 0x00000003) >> 0);
+       case nv_clk_src_shader:
+               return read_clk(priv, (mast & 0x00000030) >> 4);
+       case nv_clk_src_mem:
+               return read_pll_2(priv, 0x4020);
+       default:
+               break;
+       }
+
+       nv_debug(priv, "unknown clock source %d 0x%08x\n", src, mast);
+       return -EINVAL;
+}
+
+static int
+nv40_clk_calc_pll(struct nv40_clk_priv *priv, u32 reg, u32 clk,
+                 int *N1, int *M1, int *N2, int *M2, int *log2P)
+{
+       struct nvkm_bios *bios = nvkm_bios(priv);
+       struct nvbios_pll pll;
+       int ret;
+
+       ret = nvbios_pll_parse(bios, reg, &pll);
+       if (ret)
+               return ret;
+
+       if (clk < pll.vco1.max_freq)
+               pll.vco2.max_freq = 0;
+
+       ret = nv04_pll_calc(nv_subdev(priv), &pll, clk, N1, M1, N2, M2, log2P);
+       if (ret == 0)
+               return -ERANGE;
+
+       return ret;
+}
+
+static int
+nv40_clk_calc(struct nvkm_clk *clk, struct nvkm_cstate *cstate)
+{
+       struct nv40_clk_priv *priv = (void *)clk;
+       int gclk = cstate->domain[nv_clk_src_core];
+       int sclk = cstate->domain[nv_clk_src_shader];
+       int N1, M1, N2, M2, log2P;
+       int ret;
+
+       /* core/geometric clock */
+       ret = nv40_clk_calc_pll(priv, 0x004000, gclk,
+                               &N1, &M1, &N2, &M2, &log2P);
+       if (ret < 0)
+               return ret;
+
+       if (N2 == M2) {
+               priv->npll_ctrl = 0x80000100 | (log2P << 16);
+               priv->npll_coef = (N1 << 8) | M1;
+       } else {
+               priv->npll_ctrl = 0xc0000000 | (log2P << 16);
+               priv->npll_coef = (N2 << 24) | (M2 << 16) | (N1 << 8) | M1;
+       }
+
+       /* use the second pll for shader/rop clock, if it differs from core */
+       if (sclk && sclk != gclk) {
+               ret = nv40_clk_calc_pll(priv, 0x004008, sclk,
+                                       &N1, &M1, NULL, NULL, &log2P);
+               if (ret < 0)
+                       return ret;
+
+               priv->spll = 0xc0000000 | (log2P << 16) | (N1 << 8) | M1;
+               priv->ctrl = 0x00000223;
+       } else {
+               priv->spll = 0x00000000;
+               priv->ctrl = 0x00000333;
+       }
+
+       return 0;
+}
+
+static int
+nv40_clk_prog(struct nvkm_clk *clk)
+{
+       struct nv40_clk_priv *priv = (void *)clk;
+       nv_mask(priv, 0x00c040, 0x00000333, 0x00000000);
+       nv_wr32(priv, 0x004004, priv->npll_coef);
+       nv_mask(priv, 0x004000, 0xc0070100, priv->npll_ctrl);
+       nv_mask(priv, 0x004008, 0xc007ffff, priv->spll);
+       mdelay(5);
+       nv_mask(priv, 0x00c040, 0x00000333, priv->ctrl);
+       return 0;
+}
+
+static void
+nv40_clk_tidy(struct nvkm_clk *clk)
+{
+}
+
+static int
+nv40_clk_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+             struct nvkm_oclass *oclass, void *data, u32 size,
+             struct nvkm_object **pobject)
+{
+       struct nv40_clk_priv *priv;
+       int ret;
+
+       ret = nvkm_clk_create(parent, engine, oclass, nv40_domain,
+                             NULL, 0, true, &priv);
+       *pobject = nv_object(priv);
+       if (ret)
+               return ret;
+
+       priv->base.pll_calc = nv04_clk_pll_calc;
+       priv->base.pll_prog = nv04_clk_pll_prog;
+       priv->base.read = nv40_clk_read;
+       priv->base.calc = nv40_clk_calc;
+       priv->base.prog = nv40_clk_prog;
+       priv->base.tidy = nv40_clk_tidy;
+       return 0;
+}
+
+struct nvkm_oclass
+nv40_clk_oclass = {
+       .handle = NV_SUBDEV(CLK, 0x40),
+       .ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = nv40_clk_ctor,
+               .dtor = _nvkm_clk_dtor,
+               .init = _nvkm_clk_init,
+               .fini = _nvkm_clk_fini,
+       },
+};
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/clk/nv50.c b/drivers/gpu/drm/nouveau/nvkm/subdev/clk/nv50.c
new file mode 100644 (file)
index 0000000..9b4ffd6
--- /dev/null
@@ -0,0 +1,561 @@
+/*
+ * Copyright 2012 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 "nv50.h"
+#include "pll.h"
+#include "seq.h"
+
+#include <core/device.h>
+#include <subdev/bios.h>
+#include <subdev/bios/pll.h>
+
+static u32
+read_div(struct nv50_clk_priv *priv)
+{
+       switch (nv_device(priv)->chipset) {
+       case 0x50: /* it exists, but only has bit 31, not the dividers.. */
+       case 0x84:
+       case 0x86:
+       case 0x98:
+       case 0xa0:
+               return nv_rd32(priv, 0x004700);
+       case 0x92:
+       case 0x94:
+       case 0x96:
+               return nv_rd32(priv, 0x004800);
+       default:
+               return 0x00000000;
+       }
+}
+
+static u32
+read_pll_src(struct nv50_clk_priv *priv, u32 base)
+{
+       struct nvkm_clk *clk = &priv->base;
+       u32 coef, ref = clk->read(clk, nv_clk_src_crystal);
+       u32 rsel = nv_rd32(priv, 0x00e18c);
+       int P, N, M, id;
+
+       switch (nv_device(priv)->chipset) {
+       case 0x50:
+       case 0xa0:
+               switch (base) {
+               case 0x4020:
+               case 0x4028: id = !!(rsel & 0x00000004); break;
+               case 0x4008: id = !!(rsel & 0x00000008); break;
+               case 0x4030: id = 0; break;
+               default:
+                       nv_error(priv, "ref: bad pll 0x%06x\n", base);
+                       return 0;
+               }
+
+               coef = nv_rd32(priv, 0x00e81c + (id * 0x0c));
+               ref *=  (coef & 0x01000000) ? 2 : 4;
+               P    =  (coef & 0x00070000) >> 16;
+               N    = ((coef & 0x0000ff00) >> 8) + 1;
+               M    = ((coef & 0x000000ff) >> 0) + 1;
+               break;
+       case 0x84:
+       case 0x86:
+       case 0x92:
+               coef = nv_rd32(priv, 0x00e81c);
+               P    = (coef & 0x00070000) >> 16;
+               N    = (coef & 0x0000ff00) >> 8;
+               M    = (coef & 0x000000ff) >> 0;
+               break;
+       case 0x94:
+       case 0x96:
+       case 0x98:
+               rsel = nv_rd32(priv, 0x00c050);
+               switch (base) {
+               case 0x4020: rsel = (rsel & 0x00000003) >> 0; break;
+               case 0x4008: rsel = (rsel & 0x0000000c) >> 2; break;
+               case 0x4028: rsel = (rsel & 0x00001800) >> 11; break;
+               case 0x4030: rsel = 3; break;
+               default:
+                       nv_error(priv, "ref: bad pll 0x%06x\n", base);
+                       return 0;
+               }
+
+               switch (rsel) {
+               case 0: id = 1; break;
+               case 1: return clk->read(clk, nv_clk_src_crystal);
+               case 2: return clk->read(clk, nv_clk_src_href);
+               case 3: id = 0; break;
+               }
+
+               coef =  nv_rd32(priv, 0x00e81c + (id * 0x28));
+               P    = (nv_rd32(priv, 0x00e824 + (id * 0x28)) >> 16) & 7;
+               P   += (coef & 0x00070000) >> 16;
+               N    = (coef & 0x0000ff00) >> 8;
+               M    = (coef & 0x000000ff) >> 0;
+               break;
+       default:
+               BUG_ON(1);
+       }
+
+       if (M)
+               return (ref * N / M) >> P;
+
+       return 0;
+}
+
+static u32
+read_pll_ref(struct nv50_clk_priv *priv, u32 base)
+{
+       struct nvkm_clk *clk = &priv->base;
+       u32 src, mast = nv_rd32(priv, 0x00c040);
+
+       switch (base) {
+       case 0x004028:
+               src = !!(mast & 0x00200000);
+               break;
+       case 0x004020:
+               src = !!(mast & 0x00400000);
+               break;
+       case 0x004008:
+               src = !!(mast & 0x00010000);
+               break;
+       case 0x004030:
+               src = !!(mast & 0x02000000);
+               break;
+       case 0x00e810:
+               return clk->read(clk, nv_clk_src_crystal);
+       default:
+               nv_error(priv, "bad pll 0x%06x\n", base);
+               return 0;
+       }
+
+       if (src)
+               return clk->read(clk, nv_clk_src_href);
+
+       return read_pll_src(priv, base);
+}
+
+static u32
+read_pll(struct nv50_clk_priv *priv, u32 base)
+{
+       struct nvkm_clk *clk = &priv->base;
+       u32 mast = nv_rd32(priv, 0x00c040);
+       u32 ctrl = nv_rd32(priv, base + 0);
+       u32 coef = nv_rd32(priv, base + 4);
+       u32 ref = read_pll_ref(priv, base);
+       u32 freq = 0;
+       int N1, N2, M1, M2;
+
+       if (base == 0x004028 && (mast & 0x00100000)) {
+               /* wtf, appears to only disable post-divider on gt200 */
+               if (nv_device(priv)->chipset != 0xa0)
+                       return clk->read(clk, nv_clk_src_dom6);
+       }
+
+       N2 = (coef & 0xff000000) >> 24;
+       M2 = (coef & 0x00ff0000) >> 16;
+       N1 = (coef & 0x0000ff00) >> 8;
+       M1 = (coef & 0x000000ff);
+       if ((ctrl & 0x80000000) && M1) {
+               freq = ref * N1 / M1;
+               if ((ctrl & 0x40000100) == 0x40000000) {
+                       if (M2)
+                               freq = freq * N2 / M2;
+                       else
+                               freq = 0;
+               }
+       }
+
+       return freq;
+}
+
+static int
+nv50_clk_read(struct nvkm_clk *clk, enum nv_clk_src src)
+{
+       struct nv50_clk_priv *priv = (void *)clk;
+       u32 mast = nv_rd32(priv, 0x00c040);
+       u32 P = 0;
+
+       switch (src) {
+       case nv_clk_src_crystal:
+               return nv_device(priv)->crystal;
+       case nv_clk_src_href:
+               return 100000; /* PCIE reference clock */
+       case nv_clk_src_hclk:
+               return div_u64((u64)clk->read(clk, nv_clk_src_href) * 27778, 10000);
+       case nv_clk_src_hclkm3:
+               return clk->read(clk, nv_clk_src_hclk) * 3;
+       case nv_clk_src_hclkm3d2:
+               return clk->read(clk, nv_clk_src_hclk) * 3 / 2;
+       case nv_clk_src_host:
+               switch (mast & 0x30000000) {
+               case 0x00000000: return clk->read(clk, nv_clk_src_href);
+               case 0x10000000: break;
+               case 0x20000000: /* !0x50 */
+               case 0x30000000: return clk->read(clk, nv_clk_src_hclk);
+               }
+               break;
+       case nv_clk_src_core:
+               if (!(mast & 0x00100000))
+                       P = (nv_rd32(priv, 0x004028) & 0x00070000) >> 16;
+               switch (mast & 0x00000003) {
+               case 0x00000000: return clk->read(clk, nv_clk_src_crystal) >> P;
+               case 0x00000001: return clk->read(clk, nv_clk_src_dom6);
+               case 0x00000002: return read_pll(priv, 0x004020) >> P;
+               case 0x00000003: return read_pll(priv, 0x004028) >> P;
+               }
+               break;
+       case nv_clk_src_shader:
+               P = (nv_rd32(priv, 0x004020) & 0x00070000) >> 16;
+               switch (mast & 0x00000030) {
+               case 0x00000000:
+                       if (mast & 0x00000080)
+                               return clk->read(clk, nv_clk_src_host) >> P;
+                       return clk->read(clk, nv_clk_src_crystal) >> P;
+               case 0x00000010: break;
+               case 0x00000020: return read_pll(priv, 0x004028) >> P;
+               case 0x00000030: return read_pll(priv, 0x004020) >> P;
+               }
+               break;
+       case nv_clk_src_mem:
+               P = (nv_rd32(priv, 0x004008) & 0x00070000) >> 16;
+               if (nv_rd32(priv, 0x004008) & 0x00000200) {
+                       switch (mast & 0x0000c000) {
+                       case 0x00000000:
+                               return clk->read(clk, nv_clk_src_crystal) >> P;
+                       case 0x00008000:
+                       case 0x0000c000:
+                               return clk->read(clk, nv_clk_src_href) >> P;
+                       }
+               } else {
+                       return read_pll(priv, 0x004008) >> P;
+               }
+               break;
+       case nv_clk_src_vdec:
+               P = (read_div(priv) & 0x00000700) >> 8;
+               switch (nv_device(priv)->chipset) {
+               case 0x84:
+               case 0x86:
+               case 0x92:
+               case 0x94:
+               case 0x96:
+               case 0xa0:
+                       switch (mast & 0x00000c00) {
+                       case 0x00000000:
+                               if (nv_device(priv)->chipset == 0xa0) /* wtf?? */
+                                       return clk->read(clk, nv_clk_src_core) >> P;
+                               return clk->read(clk, nv_clk_src_crystal) >> P;
+                       case 0x00000400:
+                               return 0;
+                       case 0x00000800:
+                               if (mast & 0x01000000)
+                                       return read_pll(priv, 0x004028) >> P;
+                               return read_pll(priv, 0x004030) >> P;
+                       case 0x00000c00:
+                               return clk->read(clk, nv_clk_src_core) >> P;
+                       }
+                       break;
+               case 0x98:
+                       switch (mast & 0x00000c00) {
+                       case 0x00000000:
+                               return clk->read(clk, nv_clk_src_core) >> P;
+                       case 0x00000400:
+                               return 0;
+                       case 0x00000800:
+                               return clk->read(clk, nv_clk_src_hclkm3d2) >> P;
+                       case 0x00000c00:
+                               return clk->read(clk, nv_clk_src_mem) >> P;
+                       }
+                       break;
+               }
+               break;
+       case nv_clk_src_dom6:
+               switch (nv_device(priv)->chipset) {
+               case 0x50:
+               case 0xa0:
+                       return read_pll(priv, 0x00e810) >> 2;
+               case 0x84:
+               case 0x86:
+               case 0x92:
+               case 0x94:
+               case 0x96:
+               case 0x98:
+                       P = (read_div(priv) & 0x00000007) >> 0;
+                       switch (mast & 0x0c000000) {
+                       case 0x00000000: return clk->read(clk, nv_clk_src_href);
+                       case 0x04000000: break;
+                       case 0x08000000: return clk->read(clk, nv_clk_src_hclk);
+                       case 0x0c000000:
+                               return clk->read(clk, nv_clk_src_hclkm3) >> P;
+                       }
+                       break;
+               default:
+                       break;
+               }
+       default:
+               break;
+       }
+
+       nv_debug(priv, "unknown clock source %d 0x%08x\n", src, mast);
+       return -EINVAL;
+}
+
+static u32
+calc_pll(struct nv50_clk_priv *priv, u32 reg, u32 clk, int *N, int *M, int *P)
+{
+       struct nvkm_bios *bios = nvkm_bios(priv);
+       struct nvbios_pll pll;
+       int ret;
+
+       ret = nvbios_pll_parse(bios, reg, &pll);
+       if (ret)
+               return 0;
+
+       pll.vco2.max_freq = 0;
+       pll.refclk = read_pll_ref(priv, reg);
+       if (!pll.refclk)
+               return 0;
+
+       return nv04_pll_calc(nv_subdev(priv), &pll, clk, N, M, NULL, NULL, P);
+}
+
+static inline u32
+calc_div(u32 src, u32 target, int *div)
+{
+       u32 clk0 = src, clk1 = src;
+       for (*div = 0; *div <= 7; (*div)++) {
+               if (clk0 <= target) {
+                       clk1 = clk0 << (*div ? 1 : 0);
+                       break;
+               }
+               clk0 >>= 1;
+       }
+
+       if (target - clk0 <= clk1 - target)
+               return clk0;
+       (*div)--;
+       return clk1;
+}
+
+static inline u32
+clk_same(u32 a, u32 b)
+{
+       return ((a / 1000) == (b / 1000));
+}
+
+static int
+nv50_clk_calc(struct nvkm_clk *clk, struct nvkm_cstate *cstate)
+{
+       struct nv50_clk_priv *priv = (void *)clk;
+       struct nv50_clk_hwsq *hwsq = &priv->hwsq;
+       const int shader = cstate->domain[nv_clk_src_shader];
+       const int core = cstate->domain[nv_clk_src_core];
+       const int vdec = cstate->domain[nv_clk_src_vdec];
+       const int dom6 = cstate->domain[nv_clk_src_dom6];
+       u32 mastm = 0, mastv = 0;
+       u32 divsm = 0, divsv = 0;
+       int N, M, P1, P2;
+       int freq, out;
+
+       /* prepare a hwsq script from which we'll perform the reclock */
+       out = clk_init(hwsq, nv_subdev(clk));
+       if (out)
+               return out;
+
+       clk_wr32(hwsq, fifo, 0x00000001); /* block fifo */
+       clk_nsec(hwsq, 8000);
+       clk_setf(hwsq, 0x10, 0x00); /* disable fb */
+       clk_wait(hwsq, 0x00, 0x01); /* wait for fb disabled */
+
+       /* vdec: avoid modifying xpll until we know exactly how the other
+        * clock domains work, i suspect at least some of them can also be
+        * tied to xpll...
+        */
+       if (vdec) {
+               /* see how close we can get using nvclk as a source */
+               freq = calc_div(core, vdec, &P1);
+
+               /* see how close we can get using xpll/hclk as a source */
+               if (nv_device(priv)->chipset != 0x98)
+                       out = read_pll(priv, 0x004030);
+               else
+                       out = clk->read(clk, nv_clk_src_hclkm3d2);
+               out = calc_div(out, vdec, &P2);
+
+               /* select whichever gets us closest */
+               if (abs(vdec - freq) <= abs(vdec - out)) {
+                       if (nv_device(priv)->chipset != 0x98)
+                               mastv |= 0x00000c00;
+                       divsv |= P1 << 8;
+               } else {
+                       mastv |= 0x00000800;
+                       divsv |= P2 << 8;
+               }
+
+               mastm |= 0x00000c00;
+               divsm |= 0x00000700;
+       }
+
+       /* dom6: nfi what this is, but we're limited to various combinations
+        * of the host clock frequency
+        */
+       if (dom6) {
+               if (clk_same(dom6, clk->read(clk, nv_clk_src_href))) {
+                       mastv |= 0x00000000;
+               } else
+               if (clk_same(dom6, clk->read(clk, nv_clk_src_hclk))) {
+                       mastv |= 0x08000000;
+               } else {
+                       freq = clk->read(clk, nv_clk_src_hclk) * 3;
+                       freq = calc_div(freq, dom6, &P1);
+
+                       mastv |= 0x0c000000;
+                       divsv |= P1;
+               }
+
+               mastm |= 0x0c000000;
+               divsm |= 0x00000007;
+       }
+
+       /* vdec/dom6: switch to "safe" clocks temporarily, update dividers
+        * and then switch to target clocks
+        */
+       clk_mask(hwsq, mast, mastm, 0x00000000);
+       clk_mask(hwsq, divs, divsm, divsv);
+       clk_mask(hwsq, mast, mastm, mastv);
+
+       /* core/shader: disconnect nvclk/sclk from their PLLs (nvclk to dom6,
+        * sclk to hclk) before reprogramming
+        */
+       if (nv_device(priv)->chipset < 0x92)
+               clk_mask(hwsq, mast, 0x001000b0, 0x00100080);
+       else
+               clk_mask(hwsq, mast, 0x000000b3, 0x00000081);
+
+       /* core: for the moment at least, always use nvpll */
+       freq = calc_pll(priv, 0x4028, core, &N, &M, &P1);
+       if (freq == 0)
+               return -ERANGE;
+
+       clk_mask(hwsq, nvpll[0], 0xc03f0100,
+                                0x80000000 | (P1 << 19) | (P1 << 16));
+       clk_mask(hwsq, nvpll[1], 0x0000ffff, (N << 8) | M);
+
+       /* shader: tie to nvclk if possible, otherwise use spll.  have to be
+        * very careful that the shader clock is at least twice the core, or
+        * some chipsets will be very unhappy.  i expect most or all of these
+        * cases will be handled by tying to nvclk, but it's possible there's
+        * corners
+        */
+       if (P1-- && shader == (core << 1)) {
+               clk_mask(hwsq, spll[0], 0xc03f0100, (P1 << 19) | (P1 << 16));
+               clk_mask(hwsq, mast, 0x00100033, 0x00000023);
+       } else {
+               freq = calc_pll(priv, 0x4020, shader, &N, &M, &P1);
+               if (freq == 0)
+                       return -ERANGE;
+
+               clk_mask(hwsq, spll[0], 0xc03f0100,
+                                       0x80000000 | (P1 << 19) | (P1 << 16));
+               clk_mask(hwsq, spll[1], 0x0000ffff, (N << 8) | M);
+               clk_mask(hwsq, mast, 0x00100033, 0x00000033);
+       }
+
+       /* restore normal operation */
+       clk_setf(hwsq, 0x10, 0x01); /* enable fb */
+       clk_wait(hwsq, 0x00, 0x00); /* wait for fb enabled */
+       clk_wr32(hwsq, fifo, 0x00000000); /* un-block fifo */
+       return 0;
+}
+
+static int
+nv50_clk_prog(struct nvkm_clk *clk)
+{
+       struct nv50_clk_priv *priv = (void *)clk;
+       return clk_exec(&priv->hwsq, true);
+}
+
+static void
+nv50_clk_tidy(struct nvkm_clk *clk)
+{
+       struct nv50_clk_priv *priv = (void *)clk;
+       clk_exec(&priv->hwsq, false);
+}
+
+int
+nv50_clk_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+             struct nvkm_oclass *oclass, void *data, u32 size,
+             struct nvkm_object **pobject)
+{
+       struct nv50_clk_oclass *pclass = (void *)oclass;
+       struct nv50_clk_priv *priv;
+       int ret;
+
+       ret = nvkm_clk_create(parent, engine, oclass, pclass->domains,
+                             NULL, 0, false, &priv);
+       *pobject = nv_object(priv);
+       if (ret)
+               return ret;
+
+       priv->hwsq.r_fifo = hwsq_reg(0x002504);
+       priv->hwsq.r_spll[0] = hwsq_reg(0x004020);
+       priv->hwsq.r_spll[1] = hwsq_reg(0x004024);
+       priv->hwsq.r_nvpll[0] = hwsq_reg(0x004028);
+       priv->hwsq.r_nvpll[1] = hwsq_reg(0x00402c);
+       switch (nv_device(priv)->chipset) {
+       case 0x92:
+       case 0x94:
+       case 0x96:
+               priv->hwsq.r_divs = hwsq_reg(0x004800);
+               break;
+       default:
+               priv->hwsq.r_divs = hwsq_reg(0x004700);
+               break;
+       }
+       priv->hwsq.r_mast = hwsq_reg(0x00c040);
+
+       priv->base.read = nv50_clk_read;
+       priv->base.calc = nv50_clk_calc;
+       priv->base.prog = nv50_clk_prog;
+       priv->base.tidy = nv50_clk_tidy;
+       return 0;
+}
+
+static struct nvkm_domain
+nv50_domains[] = {
+       { nv_clk_src_crystal, 0xff },
+       { nv_clk_src_href   , 0xff },
+       { nv_clk_src_core   , 0xff, 0, "core", 1000 },
+       { nv_clk_src_shader , 0xff, 0, "shader", 1000 },
+       { nv_clk_src_mem    , 0xff, 0, "memory", 1000 },
+       { nv_clk_src_max }
+};
+
+struct nvkm_oclass *
+nv50_clk_oclass = &(struct nv50_clk_oclass) {
+       .base.handle = NV_SUBDEV(CLK, 0x50),
+       .base.ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = nv50_clk_ctor,
+               .dtor = _nvkm_clk_dtor,
+               .init = _nvkm_clk_init,
+               .fini = _nvkm_clk_fini,
+       },
+       .domains = nv50_domains,
+}.base;
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/clk/nv50.h b/drivers/gpu/drm/nouveau/nvkm/subdev/clk/nv50.h
new file mode 100644 (file)
index 0000000..0ead76a
--- /dev/null
@@ -0,0 +1,28 @@
+#ifndef __NVKM_CLK_NV50_H__
+#define __NVKM_CLK_NV50_H__
+#include <subdev/bus/hwsq.h>
+#include <subdev/clk.h>
+
+struct nv50_clk_hwsq {
+       struct hwsq base;
+       struct hwsq_reg r_fifo;
+       struct hwsq_reg r_spll[2];
+       struct hwsq_reg r_nvpll[2];
+       struct hwsq_reg r_divs;
+       struct hwsq_reg r_mast;
+};
+
+struct nv50_clk_priv {
+       struct nvkm_clk base;
+       struct nv50_clk_hwsq hwsq;
+};
+
+int  nv50_clk_ctor(struct nvkm_object *, struct nvkm_object *,
+                    struct nvkm_oclass *, void *, u32,
+                    struct nvkm_object **);
+
+struct nv50_clk_oclass {
+       struct nvkm_oclass base;
+       struct nvkm_domain *domains;
+};
+#endif
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/clk/pll.h b/drivers/gpu/drm/nouveau/nvkm/subdev/clk/pll.h
new file mode 100644 (file)
index 0000000..44020a3
--- /dev/null
@@ -0,0 +1,11 @@
+#ifndef __NVKM_PLL_H__
+#define __NVKM_PLL_H__
+#include <core/os.h>
+struct nvkm_subdev;
+struct nvbios_pll;
+
+int nv04_pll_calc(struct nvkm_subdev *, struct nvbios_pll *, u32 freq,
+                 int *N1, int *M1, int *N2, int *M2, int *P);
+int gt215_pll_calc(struct nvkm_subdev *, struct nvbios_pll *, u32 freq,
+                 int *N, int *fN, int *M, int *P);
+#endif
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/clk/pllgt215.c b/drivers/gpu/drm/nouveau/nvkm/subdev/clk/pllgt215.c
new file mode 100644 (file)
index 0000000..783a3e7
--- /dev/null
@@ -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 "pll.h"
+
+#include <subdev/bios.h>
+#include <subdev/bios/pll.h>
+
+int
+gt215_pll_calc(struct nvkm_subdev *subdev, struct nvbios_pll *info,
+              u32 freq, int *pN, int *pfN, int *pM, int *P)
+{
+       u32 best_err = ~0, err;
+       int M, lM, hM, N, fN;
+
+       *P = info->vco1.max_freq / freq;
+       if (*P > info->max_p)
+               *P = info->max_p;
+       if (*P < info->min_p)
+               *P = info->min_p;
+
+       lM = (info->refclk + info->vco1.max_inputfreq) / info->vco1.max_inputfreq;
+       lM = max(lM, (int)info->vco1.min_m);
+       hM = (info->refclk + info->vco1.min_inputfreq) / info->vco1.min_inputfreq;
+       hM = min(hM, (int)info->vco1.max_m);
+       lM = min(lM, hM);
+
+       for (M = lM; M <= hM; M++) {
+               u32 tmp = freq * *P * M;
+               N  = tmp / info->refclk;
+               fN = tmp % info->refclk;
+
+               if (!pfN) {
+                       if (fN >= info->refclk / 2)
+                               N++;
+               } else {
+                       if (fN <  info->refclk / 2)
+                               N--;
+                       fN = tmp - (N * info->refclk);
+               }
+
+               if (N < info->vco1.min_n)
+                       continue;
+               if (N > info->vco1.max_n)
+                       break;
+
+               err = abs(freq - (info->refclk * N / M / *P));
+               if (err < best_err) {
+                       best_err = err;
+                       *pN = N;
+                       *pM = M;
+               }
+
+               if (pfN) {
+                       *pfN = ((fN << 13) + info->refclk / 2) / info->refclk;
+                       *pfN = (*pfN - 4096) & 0xffff;
+                       return freq;
+               }
+       }
+
+       if (unlikely(best_err == ~0)) {
+               nv_error(subdev, "unable to find matching pll values\n");
+               return -EINVAL;
+       }
+
+       return info->refclk * *pN / *pM / *P;
+}
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/clk/pllnv04.c b/drivers/gpu/drm/nouveau/nvkm/subdev/clk/pllnv04.c
new file mode 100644 (file)
index 0000000..f229289
--- /dev/null
@@ -0,0 +1,245 @@
+/*
+ * 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 "pll.h"
+
+#include <subdev/bios.h>
+#include <subdev/bios/pll.h>
+
+static int
+getMNP_single(struct nvkm_subdev *subdev, struct nvbios_pll *info, int clk,
+             int *pN, int *pM, int *pP)
+{
+       /* 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 nvkm_bios *bios = nvkm_bios(subdev);
+       int minvco = info->vco1.min_freq, maxvco = info->vco1.max_freq;
+       int minM = info->vco1.min_m, maxM = info->vco1.max_m;
+       int minN = info->vco1.min_n, maxN = info->vco1.max_n;
+       int minU = info->vco1.min_inputfreq;
+       int maxU = info->vco1.max_inputfreq;
+       int minP = info->min_p;
+       int maxP = info->max_p_usable;
+       int crystal = info->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 (bios->version.major < 0x60) {
+               int cv = bios->version.chip;
+               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 = 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 = 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;
+                               *pN = N;
+                               *pM = M;
+                               *pP = thisP;
+                               if (delta == 0) /* except this one */
+                                       return bestclk;
+                       }
+               }
+       }
+
+       return bestclk;
+}
+
+static int
+getMNP_double(struct nvkm_subdev *subdev, struct nvbios_pll *info, int clk,
+             int *pN1, int *pM1, int *pN2, int *pM2, int *pP)
+{
+       /* 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
+        */
+       int chip_version = nvkm_bios(subdev)->version.chip;
+       int minvco1 = info->vco1.min_freq, maxvco1 = info->vco1.max_freq;
+       int minvco2 = info->vco2.min_freq, maxvco2 = info->vco2.max_freq;
+       int minU1 = info->vco1.min_inputfreq, minU2 = info->vco2.min_inputfreq;
+       int maxU1 = info->vco1.max_inputfreq, maxU2 = info->vco2.max_inputfreq;
+       int minM1 = info->vco1.min_m, maxM1 = info->vco1.max_m;
+       int minN1 = info->vco1.min_n, maxN1 = info->vco1.max_n;
+       int minM2 = info->vco2.min_m, maxM2 = info->vco2.max_m;
+       int minN2 = info->vco2.min_n, maxN2 = info->vco2.max_n;
+       int maxlog2P = info->max_p_usable;
+       int crystal = info->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;
+                                       *pN1 = N1;
+                                       *pM1 = M1;
+                                       *pN2 = N2;
+                                       *pM2 = M2;
+                                       *pP = log2P;
+                                       if (delta == 0) /* except this one */
+                                               return bestclk;
+                               }
+                       }
+               }
+       }
+
+       return bestclk;
+}
+
+int
+nv04_pll_calc(struct nvkm_subdev *subdev, struct nvbios_pll *info, u32 freq,
+             int *N1, int *M1, int *N2, int *M2, int *P)
+{
+       int ret;
+
+       if (!info->vco2.max_freq || !N2) {
+               ret = getMNP_single(subdev, info, freq, N1, M1, P);
+               if (N2) {
+                       *N2 = 1;
+                       *M2 = 1;
+               }
+       } else {
+               ret = getMNP_double(subdev, info, freq, N1, M1, N2, M2, P);
+       }
+
+       if (!ret)
+               nv_error(subdev, "unable to compute acceptable pll values\n");
+       return ret;
+}
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/clk/seq.h b/drivers/gpu/drm/nouveau/nvkm/subdev/clk/seq.h
new file mode 100644 (file)
index 0000000..d717e8b
--- /dev/null
@@ -0,0 +1,14 @@
+#ifndef __NVKM_CLK_SEQ_H__
+#define __NVKM_CLK_SEQ_H__
+#include <subdev/bus/hwsq.h>
+
+#define clk_init(s,p)       hwsq_init(&(s)->base, (p))
+#define clk_exec(s,e)       hwsq_exec(&(s)->base, (e))
+#define clk_have(s,r)       ((s)->r_##r.addr != 0x000000)
+#define clk_rd32(s,r)       hwsq_rd32(&(s)->base, &(s)->r_##r)
+#define clk_wr32(s,r,d)     hwsq_wr32(&(s)->base, &(s)->r_##r, (d))
+#define clk_mask(s,r,m,d)   hwsq_mask(&(s)->base, &(s)->r_##r, (m), (d))
+#define clk_setf(s,f,d)     hwsq_setf(&(s)->base, (f), (d))
+#define clk_wait(s,f,d)     hwsq_wait(&(s)->base, (f), (d))
+#define clk_nsec(s,n)       hwsq_nsec(&(s)->base, (n))
+#endif
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/devinit/Kbuild b/drivers/gpu/drm/nouveau/nvkm/subdev/devinit/Kbuild
new file mode 100644 (file)
index 0000000..793e73d
--- /dev/null
@@ -0,0 +1,14 @@
+nvkm-y += nvkm/subdev/devinit/base.o
+nvkm-y += nvkm/subdev/devinit/nv04.o
+nvkm-y += nvkm/subdev/devinit/nv05.o
+nvkm-y += nvkm/subdev/devinit/nv10.o
+nvkm-y += nvkm/subdev/devinit/nv1a.o
+nvkm-y += nvkm/subdev/devinit/nv20.o
+nvkm-y += nvkm/subdev/devinit/nv50.o
+nvkm-y += nvkm/subdev/devinit/g84.o
+nvkm-y += nvkm/subdev/devinit/g98.o
+nvkm-y += nvkm/subdev/devinit/gt215.o
+nvkm-y += nvkm/subdev/devinit/mcp89.o
+nvkm-y += nvkm/subdev/devinit/gf100.o
+nvkm-y += nvkm/subdev/devinit/gm107.o
+nvkm-y += nvkm/subdev/devinit/gm204.o
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/devinit/base.c b/drivers/gpu/drm/nouveau/nvkm/subdev/devinit/base.c
new file mode 100644 (file)
index 0000000..b0d7c5f
--- /dev/null
@@ -0,0 +1,96 @@
+/*
+ * Copyright 2012 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 "priv.h"
+
+#include <core/device.h>
+#include <core/option.h>
+#include <subdev/vga.h>
+
+int
+_nvkm_devinit_fini(struct nvkm_object *object, bool suspend)
+{
+       struct nvkm_devinit *devinit = (void *)object;
+
+       /* force full reinit on resume */
+       if (suspend)
+               devinit->post = true;
+
+       /* unlock the extended vga crtc regs */
+       nv_lockvgac(devinit, false);
+
+       return nvkm_subdev_fini(&devinit->base, suspend);
+}
+
+int
+_nvkm_devinit_init(struct nvkm_object *object)
+{
+       struct nvkm_devinit_impl *impl = (void *)object->oclass;
+       struct nvkm_devinit *devinit = (void *)object;
+       int ret;
+
+       ret = nvkm_subdev_init(&devinit->base);
+       if (ret)
+               return ret;
+
+       ret = impl->post(&devinit->base, devinit->post);
+       if (ret)
+               return ret;
+
+       if (impl->disable)
+               nv_device(devinit)->disable_mask |= impl->disable(devinit);
+       return 0;
+}
+
+void
+_nvkm_devinit_dtor(struct nvkm_object *object)
+{
+       struct nvkm_devinit *devinit = (void *)object;
+
+       /* lock crtc regs */
+       nv_lockvgac(devinit, true);
+
+       nvkm_subdev_destroy(&devinit->base);
+}
+
+int
+nvkm_devinit_create_(struct nvkm_object *parent, struct nvkm_object *engine,
+                    struct nvkm_oclass *oclass, int size, void **pobject)
+{
+       struct nvkm_devinit_impl *impl = (void *)oclass;
+       struct nvkm_device *device = nv_device(parent);
+       struct nvkm_devinit *devinit;
+       int ret;
+
+       ret = nvkm_subdev_create_(parent, engine, oclass, 0, "DEVINIT",
+                                 "init", size, pobject);
+       devinit = *pobject;
+       if (ret)
+               return ret;
+
+       devinit->post = nvkm_boolopt(device->cfgopt, "NvForcePost", false);
+       devinit->meminit = impl->meminit;
+       devinit->pll_set = impl->pll_set;
+       devinit->mmio    = impl->mmio;
+       return 0;
+}
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/devinit/fbmem.h b/drivers/gpu/drm/nouveau/nvkm/subdev/devinit/fbmem.h
new file mode 100644 (file)
index 0000000..36684c3
--- /dev/null
@@ -0,0 +1,84 @@
+/*
+ * 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.
+ *
+ */
+#include <core/device.h>
+#include <subdev/fb/regsnv04.h>
+
+#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_SCRAMBLE(i)                         (0x00100400 + 4 * (i))
+
+#define NV10_PFB_REFCTRL                                       0x00100210
+#      define NV10_PFB_REFCTRL_VALID_1                         (1 << 31)
+
+static inline struct io_mapping *
+fbmem_init(struct nvkm_device *dev)
+{
+       return io_mapping_create_wc(nv_device_resource_start(dev, 1),
+                                   nv_device_resource_len(dev, 1));
+}
+
+static inline void
+fbmem_fini(struct io_mapping *fb)
+{
+       io_mapping_free(fb);
+}
+
+static inline u32
+fbmem_peek(struct io_mapping *fb, u32 off)
+{
+       u8 __iomem *p = io_mapping_map_atomic_wc(fb, off & PAGE_MASK);
+       u32 val = ioread32(p + (off & ~PAGE_MASK));
+       io_mapping_unmap_atomic(p);
+       return val;
+}
+
+static inline void
+fbmem_poke(struct io_mapping *fb, u32 off, u32 val)
+{
+       u8 __iomem *p = io_mapping_map_atomic_wc(fb, off & PAGE_MASK);
+       iowrite32(val, p + (off & ~PAGE_MASK));
+       wmb();
+       io_mapping_unmap_atomic(p);
+}
+
+static inline bool
+fbmem_readback(struct io_mapping *fb, u32 off, u32 val)
+{
+       fbmem_poke(fb, off, val);
+       return val == fbmem_peek(fb, off);
+}
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/devinit/g84.c b/drivers/gpu/drm/nouveau/nvkm/subdev/devinit/g84.c
new file mode 100644 (file)
index 0000000..ca776ce
--- /dev/null
@@ -0,0 +1,66 @@
+/*
+ * Copyright 2013 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 "nv50.h"
+
+#include <subdev/bios.h>
+#include <subdev/bios/init.h>
+
+static u64
+g84_devinit_disable(struct nvkm_devinit *devinit)
+{
+       struct nv50_devinit_priv *priv = (void *)devinit;
+       u32 r001540 = nv_rd32(priv, 0x001540);
+       u32 r00154c = nv_rd32(priv, 0x00154c);
+       u64 disable = 0ULL;
+
+       if (!(r001540 & 0x40000000)) {
+               disable |= (1ULL << NVDEV_ENGINE_MPEG);
+               disable |= (1ULL << NVDEV_ENGINE_VP);
+               disable |= (1ULL << NVDEV_ENGINE_BSP);
+               disable |= (1ULL << NVDEV_ENGINE_CIPHER);
+       }
+
+       if (!(r00154c & 0x00000004))
+               disable |= (1ULL << NVDEV_ENGINE_DISP);
+       if (!(r00154c & 0x00000020))
+               disable |= (1ULL << NVDEV_ENGINE_BSP);
+       if (!(r00154c & 0x00000040))
+               disable |= (1ULL << NVDEV_ENGINE_CIPHER);
+
+       return disable;
+}
+
+struct nvkm_oclass *
+g84_devinit_oclass = &(struct nvkm_devinit_impl) {
+       .base.handle = NV_SUBDEV(DEVINIT, 0x84),
+       .base.ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = nv50_devinit_ctor,
+               .dtor = _nvkm_devinit_dtor,
+               .init = nv50_devinit_init,
+               .fini = _nvkm_devinit_fini,
+       },
+       .pll_set = nv50_devinit_pll_set,
+       .disable = g84_devinit_disable,
+       .post = nvbios_init,
+}.base;
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/devinit/g98.c b/drivers/gpu/drm/nouveau/nvkm/subdev/devinit/g98.c
new file mode 100644 (file)
index 0000000..d29bace
--- /dev/null
@@ -0,0 +1,65 @@
+/*
+ * Copyright 2013 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 "nv50.h"
+
+#include <subdev/bios.h>
+#include <subdev/bios/init.h>
+
+static u64
+g98_devinit_disable(struct nvkm_devinit *devinit)
+{
+       struct nv50_devinit_priv *priv = (void *)devinit;
+       u32 r001540 = nv_rd32(priv, 0x001540);
+       u32 r00154c = nv_rd32(priv, 0x00154c);
+       u64 disable = 0ULL;
+
+       if (!(r001540 & 0x40000000)) {
+               disable |= (1ULL << NVDEV_ENGINE_MSPDEC);
+               disable |= (1ULL << NVDEV_ENGINE_MSVLD);
+               disable |= (1ULL << NVDEV_ENGINE_MSPPP);
+       }
+
+       if (!(r00154c & 0x00000004))
+               disable |= (1ULL << NVDEV_ENGINE_DISP);
+       if (!(r00154c & 0x00000020))
+               disable |= (1ULL << NVDEV_ENGINE_MSVLD);
+       if (!(r00154c & 0x00000040))
+               disable |= (1ULL << NVDEV_ENGINE_SEC);
+
+       return disable;
+}
+
+struct nvkm_oclass *
+g98_devinit_oclass = &(struct nvkm_devinit_impl) {
+       .base.handle = NV_SUBDEV(DEVINIT, 0x98),
+       .base.ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = nv50_devinit_ctor,
+               .dtor = _nvkm_devinit_dtor,
+               .init = nv50_devinit_init,
+               .fini = _nvkm_devinit_fini,
+       },
+       .pll_set = nv50_devinit_pll_set,
+       .disable = g98_devinit_disable,
+       .post = nvbios_init,
+}.base;
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/devinit/gf100.c b/drivers/gpu/drm/nouveau/nvkm/subdev/devinit/gf100.c
new file mode 100644 (file)
index 0000000..e8778c6
--- /dev/null
@@ -0,0 +1,124 @@
+/*
+ * Copyright 2013 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 "nv50.h"
+
+#include <subdev/bios.h>
+#include <subdev/bios/init.h>
+#include <subdev/bios/pll.h>
+#include <subdev/clk/pll.h>
+
+int
+gf100_devinit_pll_set(struct nvkm_devinit *devinit, u32 type, u32 freq)
+{
+       struct nv50_devinit_priv *priv = (void *)devinit;
+       struct nvkm_bios *bios = nvkm_bios(priv);
+       struct nvbios_pll info;
+       int N, fN, M, P;
+       int ret;
+
+       ret = nvbios_pll_parse(bios, type, &info);
+       if (ret)
+               return ret;
+
+       ret = gt215_pll_calc(nv_subdev(devinit), &info, freq, &N, &fN, &M, &P);
+       if (ret < 0)
+               return ret;
+
+       switch (info.type) {
+       case PLL_VPLL0:
+       case PLL_VPLL1:
+       case PLL_VPLL2:
+       case PLL_VPLL3:
+               nv_mask(priv, info.reg + 0x0c, 0x00000000, 0x00000100);
+               nv_wr32(priv, info.reg + 0x04, (P << 16) | (N << 8) | M);
+               nv_wr32(priv, info.reg + 0x10, fN << 16);
+               break;
+       default:
+               nv_warn(priv, "0x%08x/%dKhz unimplemented\n", type, freq);
+               ret = -EINVAL;
+               break;
+       }
+
+       return ret;
+}
+
+static u64
+gf100_devinit_disable(struct nvkm_devinit *devinit)
+{
+       struct nv50_devinit_priv *priv = (void *)devinit;
+       u32 r022500 = nv_rd32(priv, 0x022500);
+       u64 disable = 0ULL;
+
+       if (r022500 & 0x00000001)
+               disable |= (1ULL << NVDEV_ENGINE_DISP);
+
+       if (r022500 & 0x00000002) {
+               disable |= (1ULL << NVDEV_ENGINE_MSPDEC);
+               disable |= (1ULL << NVDEV_ENGINE_MSPPP);
+       }
+
+       if (r022500 & 0x00000004)
+               disable |= (1ULL << NVDEV_ENGINE_MSVLD);
+       if (r022500 & 0x00000008)
+               disable |= (1ULL << NVDEV_ENGINE_MSENC);
+       if (r022500 & 0x00000100)
+               disable |= (1ULL << NVDEV_ENGINE_CE0);
+       if (r022500 & 0x00000200)
+               disable |= (1ULL << NVDEV_ENGINE_CE1);
+
+       return disable;
+}
+
+static int
+gf100_devinit_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+                  struct nvkm_oclass *oclass, void *data, u32 size,
+                  struct nvkm_object **pobject)
+{
+       struct nv50_devinit_priv *priv;
+       int ret;
+
+       ret = nvkm_devinit_create(parent, engine, oclass, &priv);
+       *pobject = nv_object(priv);
+       if (ret)
+               return ret;
+
+       if (nv_rd32(priv, 0x022500) & 0x00000001)
+               priv->base.post = true;
+
+       return 0;
+}
+
+struct nvkm_oclass *
+gf100_devinit_oclass = &(struct nvkm_devinit_impl) {
+       .base.handle = NV_SUBDEV(DEVINIT, 0xc0),
+       .base.ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = gf100_devinit_ctor,
+               .dtor = _nvkm_devinit_dtor,
+               .init = nv50_devinit_init,
+               .fini = _nvkm_devinit_fini,
+       },
+       .pll_set = gf100_devinit_pll_set,
+       .disable = gf100_devinit_disable,
+       .post = nvbios_init,
+}.base;
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/devinit/gm107.c b/drivers/gpu/drm/nouveau/nvkm/subdev/devinit/gm107.c
new file mode 100644 (file)
index 0000000..b345a53
--- /dev/null
@@ -0,0 +1,59 @@
+/*
+ * Copyright 2013 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 "nv50.h"
+
+#include <subdev/bios.h>
+#include <subdev/bios/init.h>
+
+u64
+gm107_devinit_disable(struct nvkm_devinit *devinit)
+{
+       struct nv50_devinit_priv *priv = (void *)devinit;
+       u32 r021c00 = nv_rd32(priv, 0x021c00);
+       u32 r021c04 = nv_rd32(priv, 0x021c04);
+       u64 disable = 0ULL;
+
+       if (r021c00 & 0x00000001)
+               disable |= (1ULL << NVDEV_ENGINE_CE0);
+       if (r021c00 & 0x00000004)
+               disable |= (1ULL << NVDEV_ENGINE_CE2);
+       if (r021c04 & 0x00000001)
+               disable |= (1ULL << NVDEV_ENGINE_DISP);
+
+       return disable;
+}
+
+struct nvkm_oclass *
+gm107_devinit_oclass = &(struct nvkm_devinit_impl) {
+       .base.handle = NV_SUBDEV(DEVINIT, 0x07),
+       .base.ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = nv50_devinit_ctor,
+               .dtor = _nvkm_devinit_dtor,
+               .init = nv50_devinit_init,
+               .fini = _nvkm_devinit_fini,
+       },
+       .pll_set = gf100_devinit_pll_set,
+       .disable = gm107_devinit_disable,
+       .post = nvbios_init,
+}.base;
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/devinit/gm204.c b/drivers/gpu/drm/nouveau/nvkm/subdev/devinit/gm204.c
new file mode 100644 (file)
index 0000000..535172c
--- /dev/null
@@ -0,0 +1,172 @@
+/*
+ * Copyright 2013 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 "nv50.h"
+
+#include <subdev/bios.h>
+#include <subdev/bios/bit.h>
+#include <subdev/bios/pmu.h>
+
+static void
+pmu_code(struct nv50_devinit_priv *priv, u32 pmu, u32 img, u32 len, bool sec)
+{
+       struct nvkm_bios *bios = nvkm_bios(priv);
+       int i;
+
+       nv_wr32(priv, 0x10a180, 0x01000000 | (sec ? 0x10000000 : 0) | pmu);
+       for (i = 0; i < len; i += 4) {
+               if ((i & 0xff) == 0)
+                       nv_wr32(priv, 0x10a188, (pmu + i) >> 8);
+               nv_wr32(priv, 0x10a184, nv_ro32(bios, img + i));
+       }
+
+       while (i & 0xff) {
+               nv_wr32(priv, 0x10a184, 0x00000000);
+               i += 4;
+       }
+}
+
+static void
+pmu_data(struct nv50_devinit_priv *priv, u32 pmu, u32 img, u32 len)
+{
+       struct nvkm_bios *bios = nvkm_bios(priv);
+       int i;
+
+       nv_wr32(priv, 0x10a1c0, 0x01000000 | pmu);
+       for (i = 0; i < len; i += 4)
+               nv_wr32(priv, 0x10a1c4, nv_ro32(bios, img + i));
+}
+
+static u32
+pmu_args(struct nv50_devinit_priv *priv, u32 argp, u32 argi)
+{
+       nv_wr32(priv, 0x10a1c0, argp);
+       nv_wr32(priv, 0x10a1c0, nv_rd32(priv, 0x10a1c4) + argi);
+       return nv_rd32(priv, 0x10a1c4);
+}
+
+static void
+pmu_exec(struct nv50_devinit_priv *priv, u32 init_addr)
+{
+       nv_wr32(priv, 0x10a104, init_addr);
+       nv_wr32(priv, 0x10a10c, 0x00000000);
+       nv_wr32(priv, 0x10a100, 0x00000002);
+}
+
+static int
+pmu_load(struct nv50_devinit_priv *priv, u8 type, bool post,
+        u32 *init_addr_pmu, u32 *args_addr_pmu)
+{
+       struct nvkm_bios *bios = nvkm_bios(priv);
+       struct nvbios_pmuR pmu;
+
+       if (!nvbios_pmuRm(bios, type, &pmu)) {
+               nv_error(priv, "VBIOS PMU fuc %02x not found\n", type);
+               return -EINVAL;
+       }
+
+       if (!post)
+               return 0;
+
+       pmu_code(priv, pmu.boot_addr_pmu, pmu.boot_addr, pmu.boot_size, false);
+       pmu_code(priv, pmu.code_addr_pmu, pmu.code_addr, pmu.code_size, true);
+       pmu_data(priv, pmu.data_addr_pmu, pmu.data_addr, pmu.data_size);
+
+       if (init_addr_pmu) {
+               *init_addr_pmu = pmu.init_addr_pmu;
+               *args_addr_pmu = pmu.args_addr_pmu;
+               return 0;
+       }
+
+       return pmu_exec(priv, pmu.init_addr_pmu), 0;
+}
+
+static int
+gm204_devinit_post(struct nvkm_subdev *subdev, bool post)
+{
+       struct nv50_devinit_priv *priv = (void *)nvkm_devinit(subdev);
+       struct nvkm_bios *bios = nvkm_bios(priv);
+       struct bit_entry bit_I;
+       u32 init, args;
+       int ret;
+
+       if (bit_entry(bios, 'I', &bit_I) || bit_I.version != 1 ||
+                                           bit_I.length < 0x1c) {
+               nv_error(priv, "VBIOS PMU init data not found\n");
+               return -EINVAL;
+       }
+
+       /* reset PMU and load init table parser ucode */
+       if (post) {
+               nv_mask(priv, 0x000200, 0x00002000, 0x00000000);
+               nv_mask(priv, 0x000200, 0x00002000, 0x00002000);
+               nv_rd32(priv, 0x000200);
+               while (nv_rd32(priv, 0x10a10c) & 0x00000006) {
+               }
+       }
+
+       ret = pmu_load(priv, 0x04, post, &init, &args);
+       if (ret)
+               return ret;
+
+       /* upload first chunk of init data */
+       if (post) {
+               u32 pmu = pmu_args(priv, args + 0x08, 0x08);
+               u32 img = nv_ro16(bios, bit_I.offset + 0x14);
+               u32 len = nv_ro16(bios, bit_I.offset + 0x16);
+               pmu_data(priv, pmu, img, len);
+       }
+
+       /* upload second chunk of init data */
+       if (post) {
+               u32 pmu = pmu_args(priv, args + 0x08, 0x10);
+               u32 img = nv_ro16(bios, bit_I.offset + 0x18);
+               u32 len = nv_ro16(bios, bit_I.offset + 0x1a);
+               pmu_data(priv, pmu, img, len);
+       }
+
+       /* execute init tables */
+       if (post) {
+               nv_wr32(priv, 0x10a040, 0x00005000);
+               pmu_exec(priv, init);
+               while (!(nv_rd32(priv, 0x10a040) & 0x00002000)) {
+               }
+       }
+
+       /* load and execute some other ucode image (bios therm?) */
+       return pmu_load(priv, 0x01, post, NULL, NULL);
+}
+
+struct nvkm_oclass *
+gm204_devinit_oclass = &(struct nvkm_devinit_impl) {
+       .base.handle = NV_SUBDEV(DEVINIT, 0x07),
+       .base.ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = nv50_devinit_ctor,
+               .dtor = _nvkm_devinit_dtor,
+               .init = nv50_devinit_init,
+               .fini = _nvkm_devinit_fini,
+       },
+       .pll_set = gf100_devinit_pll_set,
+       .disable = gm107_devinit_disable,
+       .post = gm204_devinit_post,
+}.base;
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/devinit/gt215.c b/drivers/gpu/drm/nouveau/nvkm/subdev/devinit/gt215.c
new file mode 100644 (file)
index 0000000..6a3e8d4
--- /dev/null
@@ -0,0 +1,150 @@
+/*
+ * Copyright 2013 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 "nv50.h"
+
+#include <subdev/bios.h>
+#include <subdev/bios/init.h>
+#include <subdev/bios/pll.h>
+#include <subdev/clk/pll.h>
+
+int
+gt215_devinit_pll_set(struct nvkm_devinit *devinit, u32 type, u32 freq)
+{
+       struct nv50_devinit_priv *priv = (void *)devinit;
+       struct nvkm_bios *bios = nvkm_bios(priv);
+       struct nvbios_pll info;
+       int N, fN, M, P;
+       int ret;
+
+       ret = nvbios_pll_parse(bios, type, &info);
+       if (ret)
+               return ret;
+
+       ret = gt215_pll_calc(nv_subdev(devinit), &info, freq, &N, &fN, &M, &P);
+       if (ret < 0)
+               return ret;
+
+       switch (info.type) {
+       case PLL_VPLL0:
+       case PLL_VPLL1:
+               nv_wr32(priv, info.reg + 0, 0x50000610);
+               nv_mask(priv, info.reg + 4, 0x003fffff,
+                                           (P << 16) | (M << 8) | N);
+               nv_wr32(priv, info.reg + 8, fN);
+               break;
+       default:
+               nv_warn(priv, "0x%08x/%dKhz unimplemented\n", type, freq);
+               ret = -EINVAL;
+               break;
+       }
+
+       return ret;
+}
+
+static u64
+gt215_devinit_disable(struct nvkm_devinit *devinit)
+{
+       struct nv50_devinit_priv *priv = (void *)devinit;
+       u32 r001540 = nv_rd32(priv, 0x001540);
+       u32 r00154c = nv_rd32(priv, 0x00154c);
+       u64 disable = 0ULL;
+
+       if (!(r001540 & 0x40000000)) {
+               disable |= (1ULL << NVDEV_ENGINE_MSPDEC);
+               disable |= (1ULL << NVDEV_ENGINE_MSPPP);
+       }
+
+       if (!(r00154c & 0x00000004))
+               disable |= (1ULL << NVDEV_ENGINE_DISP);
+       if (!(r00154c & 0x00000020))
+               disable |= (1ULL << NVDEV_ENGINE_MSVLD);
+       if (!(r00154c & 0x00000200))
+               disable |= (1ULL << NVDEV_ENGINE_CE0);
+
+       return disable;
+}
+
+static u32
+gt215_devinit_mmio_part[] = {
+       0x100720, 0x1008bc, 4,
+       0x100a20, 0x100adc, 4,
+       0x100d80, 0x100ddc, 4,
+       0x110000, 0x110f9c, 4,
+       0x111000, 0x11103c, 8,
+       0x111080, 0x1110fc, 4,
+       0x111120, 0x1111fc, 4,
+       0x111300, 0x1114bc, 4,
+       0,
+};
+
+static u32
+gt215_devinit_mmio(struct nvkm_devinit *devinit, u32 addr)
+{
+       struct nv50_devinit_priv *priv = (void *)devinit;
+       u32 *mmio = gt215_devinit_mmio_part;
+
+       /* the init tables on some boards have INIT_RAM_RESTRICT_ZM_REG_GROUP
+        * instructions which touch registers that may not even exist on
+        * some configurations (Quadro 400), which causes the register
+        * interface to screw up for some amount of time after attempting to
+        * write to one of these, and results in all sorts of things going
+        * horribly wrong.
+        *
+        * the binary driver avoids touching these registers at all, however,
+        * the video bios doesn't care and does what the scripts say.  it's
+        * presumed that the io-port access to priv registers isn't effected
+        * by the screw-up bug mentioned above.
+        *
+        * really, a new opcode should've been invented to handle these
+        * requirements, but whatever, it's too late for that now.
+        */
+       while (mmio[0]) {
+               if (addr >= mmio[0] && addr <= mmio[1]) {
+                       u32 part = (addr / mmio[2]) & 7;
+                       if (!priv->r001540)
+                               priv->r001540 = nv_rd32(priv, 0x001540);
+                       if (part >= hweight8((priv->r001540 >> 16) & 0xff))
+                               return ~0;
+                       return addr;
+               }
+               mmio += 3;
+       }
+
+       return addr;
+}
+
+struct nvkm_oclass *
+gt215_devinit_oclass = &(struct nvkm_devinit_impl) {
+       .base.handle = NV_SUBDEV(DEVINIT, 0xa3),
+       .base.ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = nv50_devinit_ctor,
+               .dtor = _nvkm_devinit_dtor,
+               .init = nv50_devinit_init,
+               .fini = _nvkm_devinit_fini,
+       },
+       .pll_set = gt215_devinit_pll_set,
+       .disable = gt215_devinit_disable,
+       .mmio    = gt215_devinit_mmio,
+       .post = nvbios_init,
+}.base;
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/devinit/mcp89.c b/drivers/gpu/drm/nouveau/nvkm/subdev/devinit/mcp89.c
new file mode 100644 (file)
index 0000000..55cf48b
--- /dev/null
@@ -0,0 +1,66 @@
+/*
+ * Copyright 2013 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 "nv50.h"
+
+#include <subdev/bios.h>
+#include <subdev/bios/init.h>
+
+static u64
+mcp89_devinit_disable(struct nvkm_devinit *devinit)
+{
+       struct nv50_devinit_priv *priv = (void *)devinit;
+       u32 r001540 = nv_rd32(priv, 0x001540);
+       u32 r00154c = nv_rd32(priv, 0x00154c);
+       u64 disable = 0;
+
+       if (!(r001540 & 0x40000000)) {
+               disable |= (1ULL << NVDEV_ENGINE_MSPDEC);
+               disable |= (1ULL << NVDEV_ENGINE_MSPPP);
+       }
+
+       if (!(r00154c & 0x00000004))
+               disable |= (1ULL << NVDEV_ENGINE_DISP);
+       if (!(r00154c & 0x00000020))
+               disable |= (1ULL << NVDEV_ENGINE_MSVLD);
+       if (!(r00154c & 0x00000040))
+               disable |= (1ULL << NVDEV_ENGINE_VIC);
+       if (!(r00154c & 0x00000200))
+               disable |= (1ULL << NVDEV_ENGINE_CE0);
+
+       return disable;
+}
+
+struct nvkm_oclass *
+mcp89_devinit_oclass = &(struct nvkm_devinit_impl) {
+       .base.handle = NV_SUBDEV(DEVINIT, 0xaf),
+       .base.ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = nv50_devinit_ctor,
+               .dtor = _nvkm_devinit_dtor,
+               .init = nv50_devinit_init,
+               .fini = _nvkm_devinit_fini,
+       },
+       .pll_set = gt215_devinit_pll_set,
+       .disable = mcp89_devinit_disable,
+       .post = nvbios_init,
+}.base;
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/devinit/nv04.c b/drivers/gpu/drm/nouveau/nvkm/subdev/devinit/nv04.c
new file mode 100644 (file)
index 0000000..03a0da8
--- /dev/null
@@ -0,0 +1,470 @@
+/*
+ * 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.
+ *
+ */
+#include "nv04.h"
+#include "fbmem.h"
+
+#include <subdev/bios.h>
+#include <subdev/bios/init.h>
+#include <subdev/bios/pll.h>
+#include <subdev/clk/pll.h>
+#include <subdev/vga.h>
+
+static void
+nv04_devinit_meminit(struct nvkm_devinit *devinit)
+{
+       struct nv04_devinit_priv *priv = (void *)devinit;
+       u32 patt = 0xdeadbeef;
+       struct io_mapping *fb;
+       int i;
+
+       /* Map the framebuffer aperture */
+       fb = fbmem_init(nv_device(priv));
+       if (!fb) {
+               nv_error(priv, "failed to map fb\n");
+               return;
+       }
+
+       /* Sequencer and refresh off */
+       nv_wrvgas(priv, 0, 1, nv_rdvgas(priv, 0, 1) | 0x20);
+       nv_mask(priv, NV04_PFB_DEBUG_0, 0, NV04_PFB_DEBUG_0_REFRESH_OFF);
+
+       nv_mask(priv, 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++)
+               fbmem_poke(fb, 4 * i, patt);
+
+       fbmem_poke(fb, 0x400000, patt + 1);
+
+       if (fbmem_peek(fb, 0) == patt + 1) {
+               nv_mask(priv, NV04_PFB_BOOT_0,
+                             NV04_PFB_BOOT_0_RAM_TYPE,
+                             NV04_PFB_BOOT_0_RAM_TYPE_SDRAM_16MBIT);
+               nv_mask(priv, NV04_PFB_DEBUG_0,
+                             NV04_PFB_DEBUG_0_REFRESH_OFF, 0);
+
+               for (i = 0; i < 4; i++)
+                       fbmem_poke(fb, 4 * i, patt);
+
+               if ((fbmem_peek(fb, 0xc) & 0xffff) != (patt & 0xffff))
+                       nv_mask(priv, 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 ((fbmem_peek(fb, 0xc) & 0xffff0000) != (patt & 0xffff0000)) {
+               nv_mask(priv, 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 (fbmem_peek(fb, 0) != patt) {
+               if (fbmem_readback(fb, 0x800000, patt))
+                       nv_mask(priv, NV04_PFB_BOOT_0,
+                                     NV04_PFB_BOOT_0_RAM_AMOUNT,
+                                     NV04_PFB_BOOT_0_RAM_AMOUNT_8MB);
+               else
+                       nv_mask(priv, NV04_PFB_BOOT_0,
+                                     NV04_PFB_BOOT_0_RAM_AMOUNT,
+                                     NV04_PFB_BOOT_0_RAM_AMOUNT_4MB);
+
+               nv_mask(priv, NV04_PFB_BOOT_0, NV04_PFB_BOOT_0_RAM_TYPE,
+                             NV04_PFB_BOOT_0_RAM_TYPE_SGRAM_8MBIT);
+       } else
+       if (!fbmem_readback(fb, 0x800000, patt)) {
+               nv_mask(priv, NV04_PFB_BOOT_0, NV04_PFB_BOOT_0_RAM_AMOUNT,
+                             NV04_PFB_BOOT_0_RAM_AMOUNT_8MB);
+
+       }
+
+       /* Refresh on, sequencer on */
+       nv_mask(priv, NV04_PFB_DEBUG_0, NV04_PFB_DEBUG_0_REFRESH_OFF, 0);
+       nv_wrvgas(priv, 0, 1, nv_rdvgas(priv, 0, 1) & ~0x20);
+       fbmem_fini(fb);
+}
+
+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 0x680520:
+               shift += 4;
+       case 0x680508:
+               shift += 4;
+       case 0x680504:
+               shift += 4;
+       case 0x680500:
+               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;
+}
+
+void
+setPLL_single(struct nvkm_devinit *devinit, u32 reg,
+             struct nvkm_pll_vals *pv)
+{
+       int chip_version = nvkm_bios(devinit)->version.chip;
+       uint32_t oldpll = nv_rd32(devinit, 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 = nv_rd32(devinit, 0x001584);
+               nv_wr32(devinit, 0x001584,
+                       (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 */
+               nv_wr32(devinit, reg, pv->log2P << 16 | (oldpll & 0xffff));
+       else
+               /* downclock -- write new NM first */
+               nv_wr32(devinit, reg, (oldpll & 0xffff0000) | pv->NM1);
+
+       if ((chip_version < 0x17 || chip_version == 0x1a) &&
+           chip_version != 0x11)
+               /* wait a bit on older chips */
+               msleep(64);
+       nv_rd32(devinit, reg);
+
+       /* then write the other half as well */
+       nv_wr32(devinit, reg, pll);
+
+       if (shift_powerctrl_1 >= 0)
+               nv_wr32(devinit, 0x001584, saved_powerctrl_1);
+}
+
+static uint32_t
+new_ramdac580(uint32_t reg1, bool ss, uint32_t ramdac580)
+{
+       bool head_a = (reg1 == 0x680508);
+
+       if (ss) /* single stage pll mode */
+               ramdac580 |= head_a ? 0x00000100 : 0x10000000;
+       else
+               ramdac580 &= head_a ? 0xfffffeff : 0xefffffff;
+
+       return ramdac580;
+}
+
+void
+setPLL_double_highregs(struct nvkm_devinit *devinit, u32 reg1,
+                      struct nvkm_pll_vals *pv)
+{
+       int chip_version = nvkm_bios(devinit)->version.chip;
+       bool nv3035 = chip_version == 0x30 || chip_version == 0x35;
+       uint32_t reg2 = reg1 + ((reg1 == 0x680520) ? 0x5c : 0x70);
+       uint32_t oldpll1 = nv_rd32(devinit, reg1);
+       uint32_t oldpll2 = !nv3035 ? nv_rd32(devinit, 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 >= 0x680508) { /* !nv40 */
+               oldramdac580 = nv_rd32(devinit, 0x680580);
+               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 = nv_rd32(devinit, 0x001584);
+               nv_wr32(devinit, 0x001584,
+                       (saved_powerctrl_1 & ~(0xf << shift_powerctrl_1)) |
+                       1 << shift_powerctrl_1);
+       }
+
+       if (chip_version >= 0x40) {
+               int shift_c040 = 14;
+
+               switch (reg1) {
+               case 0x680504:
+                       shift_c040 += 2;
+               case 0x680500:
+                       shift_c040 += 2;
+               case 0x680520:
+                       shift_c040 += 2;
+               case 0x680508:
+                       shift_c040 += 2;
+               }
+
+               savedc040 = nv_rd32(devinit, 0xc040);
+               if (shift_c040 != 14)
+                       nv_wr32(devinit, 0xc040, savedc040 & ~(3 << shift_c040));
+       }
+
+       if (oldramdac580 != ramdac580)
+               nv_wr32(devinit, 0x680580, ramdac580);
+
+       if (!nv3035)
+               nv_wr32(devinit, reg2, pll2);
+       nv_wr32(devinit, reg1, pll1);
+
+       if (shift_powerctrl_1 >= 0)
+               nv_wr32(devinit, 0x001584, saved_powerctrl_1);
+       if (chip_version >= 0x40)
+               nv_wr32(devinit, 0xc040, savedc040);
+}
+
+void
+setPLL_double_lowregs(struct nvkm_devinit *devinit, u32 NMNMreg,
+                     struct nvkm_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 = nv_rd32(devinit, 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 (nv_rd32(devinit, NMNMreg) == NMNM && (oldPval & 0xc0070000) == Pval)
+               return;
+
+       if (Preg == 0x4000)
+               maskc040 = ~0x333;
+       if (Preg == 0x4058)
+               maskc040 = ~(0xc << 24);
+
+       if (mpll) {
+               struct nvbios_pll info;
+               uint8_t Pval2;
+
+               if (nvbios_pll_parse(nvkm_bios(devinit), Preg, &info))
+                       return;
+
+               Pval2 = pv->log2P + info.bias_p;
+               if (Pval2 > info.max_p)
+                       Pval2 = info.max_p;
+               Pval |= 1 << 28 | Pval2 << 20;
+
+               saved4600 = nv_rd32(devinit, 0x4600);
+               nv_wr32(devinit, 0x4600, saved4600 | 8 << 28);
+       }
+       if (single_stage)
+               Pval |= mpll ? 1 << 12 : 1 << 8;
+
+       nv_wr32(devinit, Preg, oldPval | 1 << 28);
+       nv_wr32(devinit, Preg, Pval & ~(4 << 28));
+       if (mpll) {
+               Pval |= 8 << 20;
+               nv_wr32(devinit, 0x4020, Pval & ~(0xc << 28));
+               nv_wr32(devinit, 0x4038, Pval & ~(0xc << 28));
+       }
+
+       savedc040 = nv_rd32(devinit, 0xc040);
+       nv_wr32(devinit, 0xc040, savedc040 & maskc040);
+
+       nv_wr32(devinit, NMNMreg, NMNM);
+       if (NMNMreg == 0x4024)
+               nv_wr32(devinit, 0x403c, NMNM);
+
+       nv_wr32(devinit, Preg, Pval);
+       if (mpll) {
+               Pval &= ~(8 << 20);
+               nv_wr32(devinit, 0x4020, Pval);
+               nv_wr32(devinit, 0x4038, Pval);
+               nv_wr32(devinit, 0x4600, saved4600);
+       }
+
+       nv_wr32(devinit, 0xc040, savedc040);
+
+       if (mpll) {
+               nv_wr32(devinit, 0x4020, Pval & ~(1 << 28));
+               nv_wr32(devinit, 0x4038, Pval & ~(1 << 28));
+       }
+}
+
+int
+nv04_devinit_pll_set(struct nvkm_devinit *devinit, u32 type, u32 freq)
+{
+       struct nvkm_bios *bios = nvkm_bios(devinit);
+       struct nvkm_pll_vals pv;
+       struct nvbios_pll info;
+       int cv = bios->version.chip;
+       int N1, M1, N2, M2, P;
+       int ret;
+
+       ret = nvbios_pll_parse(bios, type > 0x405c ? type : type - 4, &info);
+       if (ret)
+               return ret;
+
+       ret = nv04_pll_calc(nv_subdev(devinit), &info, freq,
+                           &N1, &M1, &N2, &M2, &P);
+       if (!ret)
+               return -EINVAL;
+
+       pv.refclk = info.refclk;
+       pv.N1 = N1;
+       pv.M1 = M1;
+       pv.N2 = N2;
+       pv.M2 = M2;
+       pv.log2P = P;
+
+       if (cv == 0x30 || cv == 0x31 || cv == 0x35 || cv == 0x36 ||
+           cv >= 0x40) {
+               if (type > 0x405c)
+                       setPLL_double_highregs(devinit, type, &pv);
+               else
+                       setPLL_double_lowregs(devinit, type, &pv);
+       } else
+               setPLL_single(devinit, type, &pv);
+
+       return 0;
+}
+
+int
+nv04_devinit_fini(struct nvkm_object *object, bool suspend)
+{
+       struct nv04_devinit_priv *priv = (void *)object;
+       int ret;
+
+       /* make i2c busses accessible */
+       nv_mask(priv, 0x000200, 0x00000001, 0x00000001);
+
+       ret = nvkm_devinit_fini(&priv->base, suspend);
+       if (ret)
+               return ret;
+
+       /* unslave crtcs */
+       if (priv->owner < 0)
+               priv->owner = nv_rdvgaowner(priv);
+       nv_wrvgaowner(priv, 0);
+       return 0;
+}
+
+int
+nv04_devinit_init(struct nvkm_object *object)
+{
+       struct nv04_devinit_priv *priv = (void *)object;
+
+       if (!priv->base.post) {
+               u32 htotal = nv_rdvgac(priv, 0, 0x06);
+               htotal |= (nv_rdvgac(priv, 0, 0x07) & 0x01) << 8;
+               htotal |= (nv_rdvgac(priv, 0, 0x07) & 0x20) << 4;
+               htotal |= (nv_rdvgac(priv, 0, 0x25) & 0x01) << 10;
+               htotal |= (nv_rdvgac(priv, 0, 0x41) & 0x01) << 11;
+               if (!htotal) {
+                       nv_info(priv, "adaptor not initialised\n");
+                       priv->base.post = true;
+               }
+       }
+
+       return nvkm_devinit_init(&priv->base);
+}
+
+void
+nv04_devinit_dtor(struct nvkm_object *object)
+{
+       struct nv04_devinit_priv *priv = (void *)object;
+
+       /* restore vga owner saved at first init */
+       nv_wrvgaowner(priv, priv->owner);
+
+       nvkm_devinit_destroy(&priv->base);
+}
+
+int
+nv04_devinit_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+                 struct nvkm_oclass *oclass, void *data, u32 size,
+                 struct nvkm_object **pobject)
+{
+       struct nv04_devinit_priv *priv;
+       int ret;
+
+       ret = nvkm_devinit_create(parent, engine, oclass, &priv);
+       *pobject = nv_object(priv);
+       if (ret)
+               return ret;
+
+       priv->owner = -1;
+       return 0;
+}
+
+struct nvkm_oclass *
+nv04_devinit_oclass = &(struct nvkm_devinit_impl) {
+       .base.handle = NV_SUBDEV(DEVINIT, 0x04),
+       .base.ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = nv04_devinit_ctor,
+               .dtor = nv04_devinit_dtor,
+               .init = nv04_devinit_init,
+               .fini = nv04_devinit_fini,
+       },
+       .meminit = nv04_devinit_meminit,
+       .pll_set = nv04_devinit_pll_set,
+       .post = nvbios_init,
+}.base;
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/devinit/nv04.h b/drivers/gpu/drm/nouveau/nvkm/subdev/devinit/nv04.h
new file mode 100644 (file)
index 0000000..14a51a9
--- /dev/null
@@ -0,0 +1,22 @@
+#ifndef __NVKM_DEVINIT_NV04_H__
+#define __NVKM_DEVINIT_NV04_H__
+#include "priv.h"
+struct nvkm_pll_vals;
+
+struct nv04_devinit_priv {
+       struct nvkm_devinit base;
+       u8 owner;
+};
+
+int  nv04_devinit_ctor(struct nvkm_object *, struct nvkm_object *,
+                      struct nvkm_oclass *, void *, u32,
+                      struct nvkm_object **);
+void nv04_devinit_dtor(struct nvkm_object *);
+int  nv04_devinit_init(struct nvkm_object *);
+int  nv04_devinit_fini(struct nvkm_object *, bool);
+int  nv04_devinit_pll_set(struct nvkm_devinit *, u32, u32);
+
+void setPLL_single(struct nvkm_devinit *, u32, struct nvkm_pll_vals *);
+void setPLL_double_highregs(struct nvkm_devinit *, u32, struct nvkm_pll_vals *);
+void setPLL_double_lowregs(struct nvkm_devinit *, u32, struct nvkm_pll_vals *);
+#endif
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/devinit/nv05.c b/drivers/gpu/drm/nouveau/nvkm/subdev/devinit/nv05.c
new file mode 100644 (file)
index 0000000..def8649
--- /dev/null
@@ -0,0 +1,140 @@
+/*
+ * 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.
+ *
+ */
+#include "nv04.h"
+#include "fbmem.h"
+
+#include <subdev/bios.h>
+#include <subdev/bios/bmp.h>
+#include <subdev/bios/init.h>
+#include <subdev/vga.h>
+
+static void
+nv05_devinit_meminit(struct nvkm_devinit *devinit)
+{
+       static const u8 default_config_tab[][2] = {
+               { 0x24, 0x00 },
+               { 0x28, 0x00 },
+               { 0x24, 0x01 },
+               { 0x1f, 0x00 },
+               { 0x0f, 0x00 },
+               { 0x17, 0x00 },
+               { 0x06, 0x00 },
+               { 0x00, 0x00 }
+       };
+       struct nv04_devinit_priv *priv = (void *)devinit;
+       struct nvkm_bios *bios = nvkm_bios(priv);
+       struct io_mapping *fb;
+       u32 patt = 0xdeadbeef;
+       u16 data;
+       u8 strap, ramcfg[2];
+       int i, v;
+
+       /* Map the framebuffer aperture */
+       fb = fbmem_init(nv_device(priv));
+       if (!fb) {
+               nv_error(priv, "failed to map fb\n");
+               return;
+       }
+
+       strap = (nv_rd32(priv, 0x101000) & 0x0000003c) >> 2;
+       if ((data = bmp_mem_init_table(bios))) {
+               ramcfg[0] = nv_ro08(bios, data + 2 * strap + 0);
+               ramcfg[1] = nv_ro08(bios, data + 2 * strap + 1);
+       } else {
+               ramcfg[0] = default_config_tab[strap][0];
+               ramcfg[1] = default_config_tab[strap][1];
+       }
+
+       /* Sequencer off */
+       nv_wrvgas(priv, 0, 1, nv_rdvgas(priv, 0, 1) | 0x20);
+
+       if (nv_rd32(priv, NV04_PFB_BOOT_0) & NV04_PFB_BOOT_0_UMA_ENABLE)
+               goto out;
+
+       nv_mask(priv, NV04_PFB_DEBUG_0, NV04_PFB_DEBUG_0_REFRESH_OFF, 0);
+
+       /* If present load the hardcoded scrambling table */
+       if (data) {
+               for (i = 0, data += 0x10; i < 8; i++, data += 4) {
+                       u32 scramble = nv_ro32(bios, data);
+                       nv_wr32(priv, NV04_PFB_SCRAMBLE(i), scramble);
+               }
+       }
+
+       /* Set memory type/width/length defaults depending on the straps */
+       nv_mask(priv, NV04_PFB_BOOT_0, 0x3f, ramcfg[0]);
+
+       if (ramcfg[1] & 0x80)
+               nv_mask(priv, NV04_PFB_CFG0, 0, NV04_PFB_CFG0_SCRAMBLE);
+
+       nv_mask(priv, NV04_PFB_CFG1, 0x700001, (ramcfg[1] & 1) << 20);
+       nv_mask(priv, NV04_PFB_CFG1, 0, 1);
+
+       /* Probe memory bus width */
+       for (i = 0; i < 4; i++)
+               fbmem_poke(fb, 4 * i, patt);
+
+       if (fbmem_peek(fb, 0xc) != patt)
+               nv_mask(priv, NV04_PFB_BOOT_0,
+                         NV04_PFB_BOOT_0_RAM_WIDTH_128, 0);
+
+       /* Probe memory length */
+       v = nv_rd32(priv, NV04_PFB_BOOT_0) & NV04_PFB_BOOT_0_RAM_AMOUNT;
+
+       if (v == NV04_PFB_BOOT_0_RAM_AMOUNT_32MB &&
+           (!fbmem_readback(fb, 0x1000000, ++patt) ||
+            !fbmem_readback(fb, 0, ++patt)))
+               nv_mask(priv, 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 &&
+           !fbmem_readback(fb, 0x800000, ++patt))
+               nv_mask(priv, NV04_PFB_BOOT_0, NV04_PFB_BOOT_0_RAM_AMOUNT,
+                         NV04_PFB_BOOT_0_RAM_AMOUNT_8MB);
+
+       if (!fbmem_readback(fb, 0x400000, ++patt))
+               nv_mask(priv, NV04_PFB_BOOT_0, NV04_PFB_BOOT_0_RAM_AMOUNT,
+                         NV04_PFB_BOOT_0_RAM_AMOUNT_4MB);
+
+out:
+       /* Sequencer on */
+       nv_wrvgas(priv, 0, 1, nv_rdvgas(priv, 0, 1) & ~0x20);
+       fbmem_fini(fb);
+}
+
+struct nvkm_oclass *
+nv05_devinit_oclass = &(struct nvkm_devinit_impl) {
+       .base.handle = NV_SUBDEV(DEVINIT, 0x05),
+       .base.ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = nv04_devinit_ctor,
+               .dtor = nv04_devinit_dtor,
+               .init = nv04_devinit_init,
+               .fini = nv04_devinit_fini,
+       },
+       .meminit = nv05_devinit_meminit,
+       .pll_set = nv04_devinit_pll_set,
+       .post = nvbios_init,
+}.base;
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/devinit/nv10.c b/drivers/gpu/drm/nouveau/nvkm/subdev/devinit/nv10.c
new file mode 100644 (file)
index 0000000..7aabc1b
--- /dev/null
@@ -0,0 +1,111 @@
+/*
+ * 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.
+ *
+ */
+#include "nv04.h"
+#include "fbmem.h"
+
+#include <subdev/bios.h>
+#include <subdev/bios/init.h>
+
+static void
+nv10_devinit_meminit(struct nvkm_devinit *devinit)
+{
+       struct nv04_devinit_priv *priv = (void *)devinit;
+       static const int mem_width[] = { 0x10, 0x00, 0x20 };
+       int mem_width_count;
+       uint32_t patt = 0xdeadbeef;
+       struct io_mapping *fb;
+       int i, j, k;
+
+       if (nv_device(priv)->card_type >= NV_11 &&
+           nv_device(priv)->chipset >= 0x17)
+               mem_width_count = 3;
+       else
+               mem_width_count = 2;
+
+       /* Map the framebuffer aperture */
+       fb = fbmem_init(nv_device(priv));
+       if (!fb) {
+               nv_error(priv, "failed to map fb\n");
+               return;
+       }
+
+       nv_wr32(priv, NV10_PFB_REFCTRL, NV10_PFB_REFCTRL_VALID_1);
+
+       /* Probe memory bus width */
+       for (i = 0; i < mem_width_count; i++) {
+               nv_mask(priv, NV04_PFB_CFG0, 0x30, mem_width[i]);
+
+               for (j = 0; j < 4; j++) {
+                       for (k = 0; k < 4; k++)
+                               fbmem_poke(fb, 0x1c, 0);
+
+                       fbmem_poke(fb, 0x1c, patt);
+                       fbmem_poke(fb, 0x3c, 0);
+
+                       if (fbmem_peek(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 = nv_rd32(priv, 0x10020c) - 0x100000;
+
+               fbmem_poke(fb, off, patt);
+               fbmem_poke(fb, 0, 0);
+
+               fbmem_peek(fb, 0);
+               fbmem_peek(fb, 0);
+               fbmem_peek(fb, 0);
+               fbmem_peek(fb, 0);
+
+               if (fbmem_peek(fb, off) == patt)
+                       goto amount_found;
+       }
+
+       /* IC missing - disable the upper half memory space. */
+       nv_mask(priv, NV04_PFB_CFG0, 0x1000, 0);
+
+amount_found:
+       fbmem_fini(fb);
+}
+
+struct nvkm_oclass *
+nv10_devinit_oclass = &(struct nvkm_devinit_impl) {
+       .base.handle = NV_SUBDEV(DEVINIT, 0x10),
+       .base.ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = nv04_devinit_ctor,
+               .dtor = nv04_devinit_dtor,
+               .init = nv04_devinit_init,
+               .fini = nv04_devinit_fini,
+       },
+       .meminit = nv10_devinit_meminit,
+       .pll_set = nv04_devinit_pll_set,
+       .post = nvbios_init,
+}.base;
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/devinit/nv1a.c b/drivers/gpu/drm/nouveau/nvkm/subdev/devinit/nv1a.c
new file mode 100644 (file)
index 0000000..9f36fff
--- /dev/null
@@ -0,0 +1,40 @@
+/*
+ * Copyright 2012 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 "nv04.h"
+
+#include <subdev/bios.h>
+#include <subdev/bios/init.h>
+
+struct nvkm_oclass *
+nv1a_devinit_oclass = &(struct nvkm_devinit_impl) {
+       .base.handle = NV_SUBDEV(DEVINIT, 0x1a),
+       .base.ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = nv04_devinit_ctor,
+               .dtor = nv04_devinit_dtor,
+               .init = nv04_devinit_init,
+               .fini = nv04_devinit_fini,
+       },
+       .pll_set = nv04_devinit_pll_set,
+       .post = nvbios_init,
+}.base;
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/devinit/nv20.c b/drivers/gpu/drm/nouveau/nvkm/subdev/devinit/nv20.c
new file mode 100644 (file)
index 0000000..02fcfd9
--- /dev/null
@@ -0,0 +1,77 @@
+/*
+ * 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.
+ *
+ */
+#include "nv04.h"
+#include "fbmem.h"
+
+#include <subdev/bios.h>
+#include <subdev/bios/init.h>
+
+static void
+nv20_devinit_meminit(struct nvkm_devinit *devinit)
+{
+       struct nv04_devinit_priv *priv = (void *)devinit;
+       struct nvkm_device *device = nv_device(priv);
+       uint32_t mask = (device->chipset >= 0x25 ? 0x300 : 0x900);
+       uint32_t amount, off;
+       struct io_mapping *fb;
+
+       /* Map the framebuffer aperture */
+       fb = fbmem_init(nv_device(priv));
+       if (!fb) {
+               nv_error(priv, "failed to map fb\n");
+               return;
+       }
+
+       nv_wr32(priv, NV10_PFB_REFCTRL, NV10_PFB_REFCTRL_VALID_1);
+
+       /* Allow full addressing */
+       nv_mask(priv, NV04_PFB_CFG0, 0, mask);
+
+       amount = nv_rd32(priv, 0x10020c);
+       for (off = amount; off > 0x2000000; off -= 0x2000000)
+               fbmem_poke(fb, off - 4, off);
+
+       amount = nv_rd32(priv, 0x10020c);
+       if (amount != fbmem_peek(fb, amount - 4))
+               /* IC missing - disable the upper half memory space. */
+               nv_mask(priv, NV04_PFB_CFG0, mask, 0);
+
+       fbmem_fini(fb);
+}
+
+struct nvkm_oclass *
+nv20_devinit_oclass = &(struct nvkm_devinit_impl) {
+       .base.handle = NV_SUBDEV(DEVINIT, 0x20),
+       .base.ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = nv04_devinit_ctor,
+               .dtor = nv04_devinit_dtor,
+               .init = nv04_devinit_init,
+               .fini = nv04_devinit_fini,
+       },
+       .meminit = nv20_devinit_meminit,
+       .pll_set = nv04_devinit_pll_set,
+       .post = nvbios_init,
+}.base;
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/devinit/nv50.c b/drivers/gpu/drm/nouveau/nvkm/subdev/devinit/nv50.c
new file mode 100644 (file)
index 0000000..26b7cb1
--- /dev/null
@@ -0,0 +1,174 @@
+/*
+ * Copyright 2013 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 "nv50.h"
+
+#include <subdev/bios.h>
+#include <subdev/bios/dcb.h>
+#include <subdev/bios/disp.h>
+#include <subdev/bios/init.h>
+#include <subdev/bios/pll.h>
+#include <subdev/clk/pll.h>
+#include <subdev/ibus.h>
+#include <subdev/vga.h>
+
+int
+nv50_devinit_pll_set(struct nvkm_devinit *devinit, u32 type, u32 freq)
+{
+       struct nv50_devinit_priv *priv = (void *)devinit;
+       struct nvkm_bios *bios = nvkm_bios(priv);
+       struct nvbios_pll info;
+       int N1, M1, N2, M2, P;
+       int ret;
+
+       ret = nvbios_pll_parse(bios, type, &info);
+       if (ret) {
+               nv_error(devinit, "failed to retrieve pll data, %d\n", ret);
+               return ret;
+       }
+
+       ret = nv04_pll_calc(nv_subdev(devinit), &info, freq, &N1, &M1, &N2, &M2, &P);
+       if (!ret) {
+               nv_error(devinit, "failed pll calculation\n");
+               return ret;
+       }
+
+       switch (info.type) {
+       case PLL_VPLL0:
+       case PLL_VPLL1:
+               nv_wr32(priv, info.reg + 0, 0x10000611);
+               nv_mask(priv, info.reg + 4, 0x00ff00ff, (M1 << 16) | N1);
+               nv_mask(priv, info.reg + 8, 0x7fff00ff, (P  << 28) |
+                                                       (M2 << 16) | N2);
+               break;
+       case PLL_MEMORY:
+               nv_mask(priv, info.reg + 0, 0x01ff0000, (P << 22) |
+                                                       (info.bias_p << 19) |
+                                                       (P << 16));
+               nv_wr32(priv, info.reg + 4, (N1 << 8) | M1);
+               break;
+       default:
+               nv_mask(priv, info.reg + 0, 0x00070000, (P << 16));
+               nv_wr32(priv, info.reg + 4, (N1 << 8) | M1);
+               break;
+       }
+
+       return 0;
+}
+
+static u64
+nv50_devinit_disable(struct nvkm_devinit *devinit)
+{
+       struct nv50_devinit_priv *priv = (void *)devinit;
+       u32 r001540 = nv_rd32(priv, 0x001540);
+       u64 disable = 0ULL;
+
+       if (!(r001540 & 0x40000000))
+               disable |= (1ULL << NVDEV_ENGINE_MPEG);
+
+       return disable;
+}
+
+int
+nv50_devinit_init(struct nvkm_object *object)
+{
+       struct nvkm_bios *bios = nvkm_bios(object);
+       struct nvkm_ibus *ibus = nvkm_ibus(object);
+       struct nv50_devinit_priv *priv = (void *)object;
+       struct nvbios_outp info;
+       struct dcb_output outp;
+       u8  ver = 0xff, hdr, cnt, len;
+       int ret, i = 0;
+
+       if (!priv->base.post) {
+               if (!nv_rdvgac(priv, 0, 0x00) &&
+                   !nv_rdvgac(priv, 0, 0x1a)) {
+                       nv_info(priv, "adaptor not initialised\n");
+                       priv->base.post = true;
+               }
+       }
+
+       /* some boards appear to require certain priv register timeouts
+        * to be bumped before runing devinit scripts.  not a clue why
+        * the vbios engineers didn't make the scripts just work...
+        */
+       if (priv->base.post && ibus)
+               nv_ofuncs(ibus)->init(nv_object(ibus));
+
+       ret = nvkm_devinit_init(&priv->base);
+       if (ret)
+               return ret;
+
+       /* if we ran the init tables, we have to execute the first script
+        * pointer of each dcb entry's display encoder table in order
+        * to properly initialise each encoder.
+        */
+       while (priv->base.post && dcb_outp_parse(bios, i, &ver, &hdr, &outp)) {
+               if (nvbios_outp_match(bios, outp.hasht, outp.hashm,
+                                     &ver, &hdr, &cnt, &len, &info)) {
+                       struct nvbios_init init = {
+                               .subdev = nv_subdev(priv),
+                               .bios = bios,
+                               .offset = info.script[0],
+                               .outp = &outp,
+                               .crtc = -1,
+                               .execute = 1,
+                       };
+
+                       nvbios_exec(&init);
+               }
+               i++;
+       }
+
+       return 0;
+}
+
+int
+nv50_devinit_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+                 struct nvkm_oclass *oclass, void *data, u32 size,
+                 struct nvkm_object **pobject)
+{
+       struct nv50_devinit_priv *priv;
+       int ret;
+
+       ret = nvkm_devinit_create(parent, engine, oclass, &priv);
+       *pobject = nv_object(priv);
+       if (ret)
+               return ret;
+
+       return 0;
+}
+
+struct nvkm_oclass *
+nv50_devinit_oclass = &(struct nvkm_devinit_impl) {
+       .base.handle = NV_SUBDEV(DEVINIT, 0x50),
+       .base.ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = nv50_devinit_ctor,
+               .dtor = _nvkm_devinit_dtor,
+               .init = nv50_devinit_init,
+               .fini = _nvkm_devinit_fini,
+       },
+       .pll_set = nv50_devinit_pll_set,
+       .disable = nv50_devinit_disable,
+       .post = nvbios_init,
+}.base;
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/devinit/nv50.h b/drivers/gpu/drm/nouveau/nvkm/subdev/devinit/nv50.h
new file mode 100644 (file)
index 0000000..b882b65
--- /dev/null
@@ -0,0 +1,21 @@
+#ifndef __NVKM_DEVINIT_NV50_H__
+#define __NVKM_DEVINIT_NV50_H__
+#include "priv.h"
+
+struct nv50_devinit_priv {
+       struct nvkm_devinit base;
+       u32 r001540;
+};
+
+int  nv50_devinit_ctor(struct nvkm_object *, struct nvkm_object *,
+                      struct nvkm_oclass *, void *, u32,
+                      struct nvkm_object **);
+int  nv50_devinit_init(struct nvkm_object *);
+int  nv50_devinit_pll_set(struct nvkm_devinit *, u32, u32);
+
+int  gt215_devinit_pll_set(struct nvkm_devinit *, u32, u32);
+
+int  gf100_devinit_pll_set(struct nvkm_devinit *, u32, u32);
+
+u64  gm107_devinit_disable(struct nvkm_devinit *);
+#endif
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/devinit/priv.h b/drivers/gpu/drm/nouveau/nvkm/subdev/devinit/priv.h
new file mode 100644 (file)
index 0000000..bb51a95
--- /dev/null
@@ -0,0 +1,34 @@
+#ifndef __NVKM_DEVINIT_PRIV_H__
+#define __NVKM_DEVINIT_PRIV_H__
+#include <subdev/devinit.h>
+
+struct nvkm_devinit_impl {
+       struct nvkm_oclass base;
+       void (*meminit)(struct nvkm_devinit *);
+       int  (*pll_set)(struct nvkm_devinit *, u32 type, u32 freq);
+       u64  (*disable)(struct nvkm_devinit *);
+       u32  (*mmio)(struct nvkm_devinit *, u32);
+       int  (*post)(struct nvkm_subdev *, bool);
+};
+
+#define nvkm_devinit_create(p,e,o,d)                                        \
+       nvkm_devinit_create_((p), (e), (o), sizeof(**d), (void **)d)
+#define nvkm_devinit_destroy(p) ({                                          \
+       struct nvkm_devinit *d = (p);                                       \
+       _nvkm_devinit_dtor(nv_object(d));                                   \
+})
+#define nvkm_devinit_init(p) ({                                             \
+       struct nvkm_devinit *d = (p);                                       \
+       _nvkm_devinit_init(nv_object(d));                                   \
+})
+#define nvkm_devinit_fini(p,s) ({                                           \
+       struct nvkm_devinit *d = (p);                                       \
+       _nvkm_devinit_fini(nv_object(d), (s));                              \
+})
+
+int nvkm_devinit_create_(struct nvkm_object *, struct nvkm_object *,
+                           struct nvkm_oclass *, int, void **);
+void _nvkm_devinit_dtor(struct nvkm_object *);
+int _nvkm_devinit_init(struct nvkm_object *);
+int _nvkm_devinit_fini(struct nvkm_object *, bool suspend);
+#endif
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/fb/Kbuild b/drivers/gpu/drm/nouveau/nvkm/subdev/fb/Kbuild
new file mode 100644 (file)
index 0000000..904d601
--- /dev/null
@@ -0,0 +1,45 @@
+nvkm-y += nvkm/subdev/fb/base.o
+nvkm-y += nvkm/subdev/fb/nv04.o
+nvkm-y += nvkm/subdev/fb/nv10.o
+nvkm-y += nvkm/subdev/fb/nv1a.o
+nvkm-y += nvkm/subdev/fb/nv20.o
+nvkm-y += nvkm/subdev/fb/nv25.o
+nvkm-y += nvkm/subdev/fb/nv30.o
+nvkm-y += nvkm/subdev/fb/nv35.o
+nvkm-y += nvkm/subdev/fb/nv36.o
+nvkm-y += nvkm/subdev/fb/nv40.o
+nvkm-y += nvkm/subdev/fb/nv41.o
+nvkm-y += nvkm/subdev/fb/nv44.o
+nvkm-y += nvkm/subdev/fb/nv46.o
+nvkm-y += nvkm/subdev/fb/nv47.o
+nvkm-y += nvkm/subdev/fb/nv49.o
+nvkm-y += nvkm/subdev/fb/nv4e.o
+nvkm-y += nvkm/subdev/fb/nv50.o
+nvkm-y += nvkm/subdev/fb/g84.o
+nvkm-y += nvkm/subdev/fb/gt215.o
+nvkm-y += nvkm/subdev/fb/mcp77.o
+nvkm-y += nvkm/subdev/fb/mcp89.o
+nvkm-y += nvkm/subdev/fb/gf100.o
+nvkm-y += nvkm/subdev/fb/gk104.o
+nvkm-y += nvkm/subdev/fb/gk20a.o
+nvkm-y += nvkm/subdev/fb/gm107.o
+nvkm-y += nvkm/subdev/fb/ramnv04.o
+nvkm-y += nvkm/subdev/fb/ramnv10.o
+nvkm-y += nvkm/subdev/fb/ramnv1a.o
+nvkm-y += nvkm/subdev/fb/ramnv20.o
+nvkm-y += nvkm/subdev/fb/ramnv40.o
+nvkm-y += nvkm/subdev/fb/ramnv41.o
+nvkm-y += nvkm/subdev/fb/ramnv44.o
+nvkm-y += nvkm/subdev/fb/ramnv49.o
+nvkm-y += nvkm/subdev/fb/ramnv4e.o
+nvkm-y += nvkm/subdev/fb/ramnv50.o
+nvkm-y += nvkm/subdev/fb/ramgt215.o
+nvkm-y += nvkm/subdev/fb/rammcp77.o
+nvkm-y += nvkm/subdev/fb/ramgf100.o
+nvkm-y += nvkm/subdev/fb/ramgk104.o
+nvkm-y += nvkm/subdev/fb/ramgk20a.o
+nvkm-y += nvkm/subdev/fb/ramgm107.o
+nvkm-y += nvkm/subdev/fb/sddr2.o
+nvkm-y += nvkm/subdev/fb/sddr3.o
+nvkm-y += nvkm/subdev/fb/gddr3.o
+nvkm-y += nvkm/subdev/fb/gddr5.o
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/fb/base.c b/drivers/gpu/drm/nouveau/nvkm/subdev/fb/base.c
new file mode 100644 (file)
index 0000000..16589fa
--- /dev/null
@@ -0,0 +1,155 @@
+/*
+ * Copyright 2012 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 "priv.h"
+
+#include <subdev/bios.h>
+#include <subdev/bios/M0203.h>
+
+int
+nvkm_fb_bios_memtype(struct nvkm_bios *bios)
+{
+       const u8 ramcfg = (nv_rd32(bios, 0x101000) & 0x0000003c) >> 2;
+       struct nvbios_M0203E M0203E;
+       u8 ver, hdr;
+
+       if (nvbios_M0203Em(bios, ramcfg, &ver, &hdr, &M0203E)) {
+               switch (M0203E.type) {
+               case M0203E_TYPE_DDR2 : return NV_MEM_TYPE_DDR2;
+               case M0203E_TYPE_DDR3 : return NV_MEM_TYPE_DDR3;
+               case M0203E_TYPE_GDDR3: return NV_MEM_TYPE_GDDR3;
+               case M0203E_TYPE_GDDR5: return NV_MEM_TYPE_GDDR5;
+               default:
+                       nv_warn(bios, "M0203E type %02x\n", M0203E.type);
+                       return NV_MEM_TYPE_UNKNOWN;
+               }
+       }
+
+       nv_warn(bios, "M0203E not matched!\n");
+       return NV_MEM_TYPE_UNKNOWN;
+}
+
+int
+_nvkm_fb_fini(struct nvkm_object *object, bool suspend)
+{
+       struct nvkm_fb *pfb = (void *)object;
+       int ret;
+
+       ret = nv_ofuncs(pfb->ram)->fini(nv_object(pfb->ram), suspend);
+       if (ret && suspend)
+               return ret;
+
+       return nvkm_subdev_fini(&pfb->base, suspend);
+}
+
+int
+_nvkm_fb_init(struct nvkm_object *object)
+{
+       struct nvkm_fb *pfb = (void *)object;
+       int ret, i;
+
+       ret = nvkm_subdev_init(&pfb->base);
+       if (ret)
+               return ret;
+
+       ret = nv_ofuncs(pfb->ram)->init(nv_object(pfb->ram));
+       if (ret)
+               return ret;
+
+       for (i = 0; i < pfb->tile.regions; i++)
+               pfb->tile.prog(pfb, i, &pfb->tile.region[i]);
+
+       return 0;
+}
+
+void
+_nvkm_fb_dtor(struct nvkm_object *object)
+{
+       struct nvkm_fb *pfb = (void *)object;
+       int i;
+
+       for (i = 0; i < pfb->tile.regions; i++)
+               pfb->tile.fini(pfb, i, &pfb->tile.region[i]);
+       nvkm_mm_fini(&pfb->tags);
+       nvkm_mm_fini(&pfb->vram);
+
+       nvkm_object_ref(NULL, (struct nvkm_object **)&pfb->ram);
+       nvkm_subdev_destroy(&pfb->base);
+}
+
+int
+nvkm_fb_create_(struct nvkm_object *parent, struct nvkm_object *engine,
+               struct nvkm_oclass *oclass, int length, void **pobject)
+{
+       struct nvkm_fb_impl *impl = (void *)oclass;
+       static const char *name[] = {
+               [NV_MEM_TYPE_UNKNOWN] = "unknown",
+               [NV_MEM_TYPE_STOLEN ] = "stolen system memory",
+               [NV_MEM_TYPE_SGRAM  ] = "SGRAM",
+               [NV_MEM_TYPE_SDRAM  ] = "SDRAM",
+               [NV_MEM_TYPE_DDR1   ] = "DDR1",
+               [NV_MEM_TYPE_DDR2   ] = "DDR2",
+               [NV_MEM_TYPE_DDR3   ] = "DDR3",
+               [NV_MEM_TYPE_GDDR2  ] = "GDDR2",
+               [NV_MEM_TYPE_GDDR3  ] = "GDDR3",
+               [NV_MEM_TYPE_GDDR4  ] = "GDDR4",
+               [NV_MEM_TYPE_GDDR5  ] = "GDDR5",
+       };
+       struct nvkm_object *ram;
+       struct nvkm_fb *pfb;
+       int ret;
+
+       ret = nvkm_subdev_create_(parent, engine, oclass, 0, "PFB", "fb",
+                                 length, pobject);
+       pfb = *pobject;
+       if (ret)
+               return ret;
+
+       pfb->memtype_valid = impl->memtype;
+
+       ret = nvkm_object_ctor(nv_object(pfb), NULL, impl->ram, NULL, 0, &ram);
+       if (ret) {
+               nv_fatal(pfb, "error detecting memory configuration!!\n");
+               return ret;
+       }
+
+       pfb->ram = (void *)ram;
+
+       if (!nvkm_mm_initialised(&pfb->vram)) {
+               ret = nvkm_mm_init(&pfb->vram, 0, pfb->ram->size >> 12, 1);
+               if (ret)
+                       return ret;
+       }
+
+       if (!nvkm_mm_initialised(&pfb->tags)) {
+               ret = nvkm_mm_init(&pfb->tags, 0, pfb->ram->tags ?
+                                  ++pfb->ram->tags : 0, 1);
+               if (ret)
+                       return ret;
+       }
+
+       nv_info(pfb, "RAM type: %s\n", name[pfb->ram->type]);
+       nv_info(pfb, "RAM size: %d MiB\n", (int)(pfb->ram->size >> 20));
+       nv_info(pfb, "   ZCOMP: %d tags\n", pfb->ram->tags);
+       return 0;
+}
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/fb/g84.c b/drivers/gpu/drm/nouveau/nvkm/subdev/fb/g84.c
new file mode 100644 (file)
index 0000000..6c968d1
--- /dev/null
@@ -0,0 +1,38 @@
+/*
+ * Copyright 2012 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 "nv50.h"
+
+struct nvkm_oclass *
+g84_fb_oclass = &(struct nv50_fb_impl) {
+       .base.base.handle = NV_SUBDEV(FB, 0x84),
+       .base.base.ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = nv50_fb_ctor,
+               .dtor = nv50_fb_dtor,
+               .init = nv50_fb_init,
+               .fini = _nvkm_fb_fini,
+       },
+       .base.memtype = nv50_fb_memtype_valid,
+       .base.ram = &nv50_ram_oclass,
+       .trap = 0x001d07ff,
+}.base.base;
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/fb/gddr3.c b/drivers/gpu/drm/nouveau/nvkm/subdev/fb/gddr3.c
new file mode 100644 (file)
index 0000000..15b462a
--- /dev/null
@@ -0,0 +1,115 @@
+/*
+ * Copyright 2013 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 <bskeggs@redhat.com>
+ *         Roy Spliet <rspliet@eclipso.eu>
+ */
+#include "priv.h"
+
+struct ramxlat {
+       int id;
+       u8 enc;
+};
+
+static inline int
+ramxlat(const struct ramxlat *xlat, int id)
+{
+       while (xlat->id >= 0) {
+               if (xlat->id == id)
+                       return xlat->enc;
+               xlat++;
+       }
+       return -EINVAL;
+}
+
+static const struct ramxlat
+ramgddr3_cl_lo[] = {
+       { 7, 7 }, { 8, 0 }, { 9, 1 }, { 10, 2 }, { 11, 3 },
+       /* the below are mentioned in some, but not all, gddr3 docs */
+       { 12, 4 }, { 13, 5 }, { 14, 6 },
+       /* XXX: Per Samsung docs, are these used? They overlap with Qimonda */
+       /* { 4, 4 }, { 5, 5 }, { 6, 6 }, { 12, 8 }, { 13, 9 }, { 14, 10 },
+        * { 15, 11 }, */
+       { -1 }
+};
+
+static const struct ramxlat
+ramgddr3_cl_hi[] = {
+       { 10, 2 }, { 11, 3 }, { 12, 4 }, { 13, 5 }, { 14, 6 }, { 15, 7 },
+       { 16, 0 }, { 17, 1 },
+       { -1 }
+};
+
+static const struct ramxlat
+ramgddr3_wr_lo[] = {
+       { 5, 2 }, { 7, 4 }, { 8, 5 }, { 9, 6 }, { 10, 7 },
+       { 11, 0 },
+       /* the below are mentioned in some, but not all, gddr3 docs */
+       { 4, 1 }, { 6, 3 }, { 12, 1 }, { 13 , 2 },
+       { -1 }
+};
+
+int
+nvkm_gddr3_calc(struct nvkm_ram *ram)
+{
+       int CL, WR, CWL, DLL = 0, ODT = 0, hi;
+
+       switch (ram->next->bios.timing_ver) {
+       case 0x10:
+               CWL = ram->next->bios.timing_10_CWL;
+               CL  = ram->next->bios.timing_10_CL;
+               WR  = ram->next->bios.timing_10_WR;
+               DLL = !ram->next->bios.ramcfg_10_DLLoff;
+               ODT = ram->next->bios.timing_10_ODT;
+               break;
+       case 0x20:
+               CWL = (ram->next->bios.timing[1] & 0x00000f80) >> 7;
+               CL  = (ram->next->bios.timing[1] & 0x0000001f) >> 0;
+               WR  = (ram->next->bios.timing[2] & 0x007f0000) >> 16;
+               /* XXX: Get these values from the VBIOS instead */
+               DLL = !(ram->mr[1] & 0x1);
+               ODT =  (ram->mr[1] & 0x004) >> 2 |
+                      (ram->mr[1] & 0x040) >> 5 |
+                      (ram->mr[1] & 0x200) >> 7;
+               break;
+       default:
+               return -ENOSYS;
+       }
+
+       hi = ram->mr[2] & 0x1;
+       CL  = ramxlat(hi ? ramgddr3_cl_hi : ramgddr3_cl_lo, CL);
+       WR  = ramxlat(ramgddr3_wr_lo, WR);
+       if (CL < 0 || CWL < 1 || CWL > 7 || WR < 0)
+               return -EINVAL;
+
+       ram->mr[0] &= ~0xf74;
+       ram->mr[0] |= (CWL & 0x07) << 9;
+       ram->mr[0] |= (CL & 0x07) << 4;
+       ram->mr[0] |= (CL & 0x08) >> 1;
+
+       ram->mr[1] &= ~0x3fc;
+       ram->mr[1] |= (ODT & 0x03) << 2;
+       ram->mr[1] |= (ODT & 0x03) << 8;
+       ram->mr[1] |= (WR  & 0x03) << 4;
+       ram->mr[1] |= (WR  & 0x04) << 5;
+       ram->mr[1] |= !DLL << 6;
+       return 0;
+}
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/fb/gddr5.c b/drivers/gpu/drm/nouveau/nvkm/subdev/fb/gddr5.c
new file mode 100644 (file)
index 0000000..f6f9eee
--- /dev/null
@@ -0,0 +1,120 @@
+/*
+ * Copyright 2013 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 <bskeggs@redhat.com>
+ */
+#include "priv.h"
+
+/* binary driver only executes this path if the condition (a) is true
+ * for any configuration (combination of rammap+ramcfg+timing) that
+ * can be reached on a given card.  for now, we will execute the branch
+ * unconditionally in the hope that a "false everywhere" in the bios
+ * tables doesn't actually mean "don't touch this".
+ */
+#define NOTE00(a) 1
+
+int
+nvkm_gddr5_calc(struct nvkm_ram *ram, bool nuts)
+{
+       int pd, lf, xd, vh, vr, vo, l3;
+       int WL, CL, WR, at[2], dt, ds;
+       int rq = ram->freq < 1000000; /* XXX */
+
+       switch (ram->next->bios.ramcfg_ver) {
+       case 0x11:
+               pd =  ram->next->bios.ramcfg_11_01_80;
+               lf =  ram->next->bios.ramcfg_11_01_40;
+               xd = !ram->next->bios.ramcfg_11_01_20;
+               vh =  ram->next->bios.ramcfg_11_02_10;
+               vr =  ram->next->bios.ramcfg_11_02_04;
+               vo =  ram->next->bios.ramcfg_11_06;
+               l3 = !ram->next->bios.ramcfg_11_07_02;
+               break;
+       default:
+               return -ENOSYS;
+       }
+
+       switch (ram->next->bios.timing_ver) {
+       case 0x20:
+               WL = (ram->next->bios.timing[1] & 0x00000f80) >> 7;
+               CL = (ram->next->bios.timing[1] & 0x0000001f);
+               WR = (ram->next->bios.timing[2] & 0x007f0000) >> 16;
+               at[0] = ram->next->bios.timing_20_2e_c0;
+               at[1] = ram->next->bios.timing_20_2e_30;
+               dt =  ram->next->bios.timing_20_2e_03;
+               ds =  ram->next->bios.timing_20_2f_03;
+               break;
+       default:
+               return -ENOSYS;
+       }
+
+       if (WL < 1 || WL > 7 || CL < 5 || CL > 36 || WR < 4 || WR > 35)
+               return -EINVAL;
+       CL -= 5;
+       WR -= 4;
+
+       ram->mr[0] &= ~0xf7f;
+       ram->mr[0] |= (WR & 0x0f) << 8;
+       ram->mr[0] |= (CL & 0x0f) << 3;
+       ram->mr[0] |= (WL & 0x07) << 0;
+
+       ram->mr[1] &= ~0x0bf;
+       ram->mr[1] |= (xd & 0x01) << 7;
+       ram->mr[1] |= (at[0] & 0x03) << 4;
+       ram->mr[1] |= (dt & 0x03) << 2;
+       ram->mr[1] |= (ds & 0x03) << 0;
+
+       /* this seems wrong, alternate field used for the broadcast
+        * on nuts vs non-nuts configs..  meh, it matches for now.
+        */
+       ram->mr1_nuts = ram->mr[1];
+       if (nuts) {
+               ram->mr[1] &= ~0x030;
+               ram->mr[1] |= (at[1] & 0x03) << 4;
+       }
+
+       ram->mr[3] &= ~0x020;
+       ram->mr[3] |= (rq & 0x01) << 5;
+
+       ram->mr[5] &= ~0x004;
+       ram->mr[5] |= (l3 << 2);
+
+       if (!vo)
+               vo = (ram->mr[6] & 0xff0) >> 4;
+       if (ram->mr[6] & 0x001)
+               pd = 1; /* binary driver does this.. bug? */
+       ram->mr[6] &= ~0xff1;
+       ram->mr[6] |= (vo & 0xff) << 4;
+       ram->mr[6] |= (pd & 0x01) << 0;
+
+       if (NOTE00(vr)) {
+               ram->mr[7] &= ~0x300;
+               ram->mr[7] |= (vr & 0x03) << 8;
+       }
+       ram->mr[7] &= ~0x088;
+       ram->mr[7] |= (vh & 0x01) << 7;
+       ram->mr[7] |= (lf & 0x01) << 3;
+
+       ram->mr[8] &= ~0x003;
+       ram->mr[8] |= (WR & 0x10) >> 3;
+       ram->mr[8] |= (CL & 0x10) >> 4;
+       return 0;
+}
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/fb/gf100.c b/drivers/gpu/drm/nouveau/nvkm/subdev/fb/gf100.c
new file mode 100644 (file)
index 0000000..d51aa02
--- /dev/null
@@ -0,0 +1,122 @@
+/*
+ * Copyright 2012 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 "gf100.h"
+
+#include <core/device.h>
+
+extern const u8 gf100_pte_storage_type_map[256];
+
+bool
+gf100_fb_memtype_valid(struct nvkm_fb *pfb, u32 tile_flags)
+{
+       u8 memtype = (tile_flags & 0x0000ff00) >> 8;
+       return likely((gf100_pte_storage_type_map[memtype] != 0xff));
+}
+
+static void
+gf100_fb_intr(struct nvkm_subdev *subdev)
+{
+       struct gf100_fb_priv *priv = (void *)subdev;
+       u32 intr = nv_rd32(priv, 0x000100);
+       if (intr & 0x08000000) {
+               nv_debug(priv, "PFFB intr\n");
+               intr &= ~0x08000000;
+       }
+       if (intr & 0x00002000) {
+               nv_debug(priv, "PBFB intr\n");
+               intr &= ~0x00002000;
+       }
+}
+
+int
+gf100_fb_init(struct nvkm_object *object)
+{
+       struct gf100_fb_priv *priv = (void *)object;
+       int ret;
+
+       ret = nvkm_fb_init(&priv->base);
+       if (ret)
+               return ret;
+
+       if (priv->r100c10_page)
+               nv_wr32(priv, 0x100c10, priv->r100c10 >> 8);
+
+       nv_mask(priv, 0x100c80, 0x00000001, 0x00000000); /* 128KiB lpg */
+       return 0;
+}
+
+void
+gf100_fb_dtor(struct nvkm_object *object)
+{
+       struct nvkm_device *device = nv_device(object);
+       struct gf100_fb_priv *priv = (void *)object;
+
+       if (priv->r100c10_page) {
+               dma_unmap_page(nv_device_base(device), priv->r100c10, PAGE_SIZE,
+                              DMA_BIDIRECTIONAL);
+               __free_page(priv->r100c10_page);
+       }
+
+       nvkm_fb_destroy(&priv->base);
+}
+
+int
+gf100_fb_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+             struct nvkm_oclass *oclass, void *data, u32 size,
+             struct nvkm_object **pobject)
+{
+       struct nvkm_device *device = nv_device(parent);
+       struct gf100_fb_priv *priv;
+       int ret;
+
+       ret = nvkm_fb_create(parent, engine, oclass, &priv);
+       *pobject = nv_object(priv);
+       if (ret)
+               return ret;
+
+       priv->r100c10_page = alloc_page(GFP_KERNEL | __GFP_ZERO);
+       if (priv->r100c10_page) {
+               priv->r100c10 = dma_map_page(nv_device_base(device),
+                                            priv->r100c10_page, 0, PAGE_SIZE,
+                                            DMA_BIDIRECTIONAL);
+               if (dma_mapping_error(nv_device_base(device), priv->r100c10))
+                       return -EFAULT;
+       }
+
+       nv_subdev(priv)->intr = gf100_fb_intr;
+       return 0;
+}
+
+struct nvkm_oclass *
+gf100_fb_oclass = &(struct nvkm_fb_impl) {
+       .base.handle = NV_SUBDEV(FB, 0xc0),
+       .base.ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = gf100_fb_ctor,
+               .dtor = gf100_fb_dtor,
+               .init = gf100_fb_init,
+               .fini = _nvkm_fb_fini,
+       },
+       .memtype = gf100_fb_memtype_valid,
+       .ram = &gf100_ram_oclass,
+}.base;
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/fb/gf100.h b/drivers/gpu/drm/nouveau/nvkm/subdev/fb/gf100.h
new file mode 100644 (file)
index 0000000..0af4da2
--- /dev/null
@@ -0,0 +1,28 @@
+#ifndef __NVKM_RAM_NVC0_H__
+#define __NVKM_RAM_NVC0_H__
+#include "priv.h"
+#include "nv50.h"
+
+struct gf100_fb_priv {
+       struct nvkm_fb base;
+       struct page *r100c10_page;
+       dma_addr_t r100c10;
+};
+
+int  gf100_fb_ctor(struct nvkm_object *, struct nvkm_object *,
+                 struct nvkm_oclass *, void *, u32,
+                 struct nvkm_object **);
+void gf100_fb_dtor(struct nvkm_object *);
+int  gf100_fb_init(struct nvkm_object *);
+bool gf100_fb_memtype_valid(struct nvkm_fb *, u32);
+
+#define gf100_ram_create(p,e,o,m,d)                                             \
+       gf100_ram_create_((p), (e), (o), (m), sizeof(**d), (void **)d)
+int  gf100_ram_create_(struct nvkm_object *, struct nvkm_object *,
+                     struct nvkm_oclass *, u32, int, void **);
+int  gf100_ram_get(struct nvkm_fb *, u64, u32, u32, u32,
+                 struct nvkm_mem **);
+void gf100_ram_put(struct nvkm_fb *, struct nvkm_mem **);
+
+int  gk104_ram_init(struct nvkm_object*);
+#endif
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/fb/gk104.c b/drivers/gpu/drm/nouveau/nvkm/subdev/fb/gk104.c
new file mode 100644 (file)
index 0000000..1c08317
--- /dev/null
@@ -0,0 +1,37 @@
+/*
+ * Copyright 2012 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 "gf100.h"
+
+struct nvkm_oclass *
+gk104_fb_oclass = &(struct nvkm_fb_impl) {
+       .base.handle = NV_SUBDEV(FB, 0xe0),
+       .base.ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = gf100_fb_ctor,
+               .dtor = gf100_fb_dtor,
+               .init = gf100_fb_init,
+               .fini = _nvkm_fb_fini,
+       },
+       .memtype = gf100_fb_memtype_valid,
+       .ram = &gk104_ram_oclass,
+}.base;
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/fb/gk20a.c b/drivers/gpu/drm/nouveau/nvkm/subdev/fb/gk20a.c
new file mode 100644 (file)
index 0000000..6762847
--- /dev/null
@@ -0,0 +1,69 @@
+/*
+ * Copyright (c) 2014, NVIDIA CORPORATION. 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 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 "gf100.h"
+
+struct gk20a_fb_priv {
+       struct nvkm_fb base;
+};
+
+static int
+gk20a_fb_init(struct nvkm_object *object)
+{
+       struct gk20a_fb_priv *priv = (void *)object;
+       int ret;
+
+       ret = nvkm_fb_init(&priv->base);
+       if (ret)
+               return ret;
+
+       nv_mask(priv, 0x100c80, 0x00000001, 0x00000000); /* 128KiB lpg */
+       return 0;
+}
+
+static int
+gk20a_fb_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+             struct nvkm_oclass *oclass, void *data, u32 size,
+             struct nvkm_object **pobject)
+{
+       struct gk20a_fb_priv *priv;
+       int ret;
+
+       ret = nvkm_fb_create(parent, engine, oclass, &priv);
+       *pobject = nv_object(priv);
+       if (ret)
+               return ret;
+
+       return 0;
+}
+
+struct nvkm_oclass *
+gk20a_fb_oclass = &(struct nvkm_fb_impl) {
+       .base.handle = NV_SUBDEV(FB, 0xea),
+       .base.ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = gk20a_fb_ctor,
+               .dtor = _nvkm_fb_dtor,
+               .init = gk20a_fb_init,
+               .fini = _nvkm_fb_fini,
+       },
+       .memtype = gf100_fb_memtype_valid,
+       .ram = &gk20a_ram_oclass,
+}.base;
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/fb/gm107.c b/drivers/gpu/drm/nouveau/nvkm/subdev/fb/gm107.c
new file mode 100644 (file)
index 0000000..843f935
--- /dev/null
@@ -0,0 +1,37 @@
+/*
+ * Copyright 2012 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 "gf100.h"
+
+struct nvkm_oclass *
+gm107_fb_oclass = &(struct nvkm_fb_impl) {
+       .base.handle = NV_SUBDEV(FB, 0x07),
+       .base.ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = gf100_fb_ctor,
+               .dtor = gf100_fb_dtor,
+               .init = gf100_fb_init,
+               .fini = _nvkm_fb_fini,
+       },
+       .memtype = gf100_fb_memtype_valid,
+       .ram = &gm107_ram_oclass,
+}.base;
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/fb/gt215.c b/drivers/gpu/drm/nouveau/nvkm/subdev/fb/gt215.c
new file mode 100644 (file)
index 0000000..dd9b8a0
--- /dev/null
@@ -0,0 +1,38 @@
+/*
+ * Copyright 2012 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 "nv50.h"
+
+struct nvkm_oclass *
+gt215_fb_oclass = &(struct nv50_fb_impl) {
+       .base.base.handle = NV_SUBDEV(FB, 0xa3),
+       .base.base.ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = nv50_fb_ctor,
+               .dtor = nv50_fb_dtor,
+               .init = nv50_fb_init,
+               .fini = _nvkm_fb_fini,
+       },
+       .base.memtype = nv50_fb_memtype_valid,
+       .base.ram = &gt215_ram_oclass,
+       .trap = 0x000d0fff,
+}.base.base;
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/fb/mcp77.c b/drivers/gpu/drm/nouveau/nvkm/subdev/fb/mcp77.c
new file mode 100644 (file)
index 0000000..7be4a47
--- /dev/null
@@ -0,0 +1,38 @@
+/*
+ * Copyright 2012 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 "nv50.h"
+
+struct nvkm_oclass *
+mcp77_fb_oclass = &(struct nv50_fb_impl) {
+       .base.base.handle = NV_SUBDEV(FB, 0xaa),
+       .base.base.ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = nv50_fb_ctor,
+               .dtor = nv50_fb_dtor,
+               .init = nv50_fb_init,
+               .fini = _nvkm_fb_fini,
+       },
+       .base.memtype = nv50_fb_memtype_valid,
+       .base.ram = &mcp77_ram_oclass,
+       .trap = 0x001d07ff,
+}.base.base;
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/fb/mcp89.c b/drivers/gpu/drm/nouveau/nvkm/subdev/fb/mcp89.c
new file mode 100644 (file)
index 0000000..2d00656
--- /dev/null
@@ -0,0 +1,38 @@
+/*
+ * Copyright 2012 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 "nv50.h"
+
+struct nvkm_oclass *
+mcp89_fb_oclass = &(struct nv50_fb_impl) {
+       .base.base.handle = NV_SUBDEV(FB, 0xaf),
+       .base.base.ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = nv50_fb_ctor,
+               .dtor = nv50_fb_dtor,
+               .init = nv50_fb_init,
+               .fini = _nvkm_fb_fini,
+       },
+       .base.memtype = nv50_fb_memtype_valid,
+       .base.ram = &mcp77_ram_oclass,
+       .trap = 0x089d1fff,
+}.base.base;
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/fb/nv04.c b/drivers/gpu/drm/nouveau/nvkm/subdev/fb/nv04.c
new file mode 100644 (file)
index 0000000..c063dec
--- /dev/null
@@ -0,0 +1,87 @@
+/*
+ * Copyright 2012 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 "nv04.h"
+#include "regsnv04.h"
+
+bool
+nv04_fb_memtype_valid(struct nvkm_fb *pfb, u32 tile_flags)
+{
+       if (!(tile_flags & 0xff00))
+               return true;
+
+       return false;
+}
+
+static int
+nv04_fb_init(struct nvkm_object *object)
+{
+       struct nv04_fb_priv *priv = (void *)object;
+       int ret;
+
+       ret = nvkm_fb_init(&priv->base);
+       if (ret)
+               return ret;
+
+       /* This is what the DDX did for NV_ARCH_04, but a mmio-trace shows
+        * nvidia reading PFB_CFG_0, then writing back its original value.
+        * (which was 0x701114 in this case)
+        */
+       nv_wr32(priv, NV04_PFB_CFG0, 0x1114);
+       return 0;
+}
+
+int
+nv04_fb_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+            struct nvkm_oclass *oclass, void *data, u32 size,
+            struct nvkm_object **pobject)
+{
+       struct nv04_fb_impl *impl = (void *)oclass;
+       struct nv04_fb_priv *priv;
+       int ret;
+
+       ret = nvkm_fb_create(parent, engine, oclass, &priv);
+       *pobject = nv_object(priv);
+       if (ret)
+               return ret;
+
+       priv->base.tile.regions = impl->tile.regions;
+       priv->base.tile.init = impl->tile.init;
+       priv->base.tile.comp = impl->tile.comp;
+       priv->base.tile.fini = impl->tile.fini;
+       priv->base.tile.prog = impl->tile.prog;
+       return 0;
+}
+
+struct nvkm_oclass *
+nv04_fb_oclass = &(struct nv04_fb_impl) {
+       .base.base.handle = NV_SUBDEV(FB, 0x04),
+       .base.base.ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = nv04_fb_ctor,
+               .dtor = _nvkm_fb_dtor,
+               .init = nv04_fb_init,
+               .fini = _nvkm_fb_fini,
+       },
+       .base.memtype = nv04_fb_memtype_valid,
+       .base.ram = &nv04_ram_oclass,
+}.base.base;
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/fb/nv04.h b/drivers/gpu/drm/nouveau/nvkm/subdev/fb/nv04.h
new file mode 100644 (file)
index 0000000..caa0d03
--- /dev/null
@@ -0,0 +1,53 @@
+#ifndef __NVKM_FB_NV04_H__
+#define __NVKM_FB_NV04_H__
+#include "priv.h"
+
+struct nv04_fb_priv {
+       struct nvkm_fb base;
+};
+
+int  nv04_fb_ctor(struct nvkm_object *, struct nvkm_object *,
+                 struct nvkm_oclass *, void *, u32,
+                 struct nvkm_object **);
+
+struct nv04_fb_impl {
+       struct nvkm_fb_impl base;
+       struct {
+               int regions;
+               void (*init)(struct nvkm_fb *, int i, u32 addr, u32 size,
+                            u32 pitch, u32 flags, struct nvkm_fb_tile *);
+               void (*comp)(struct nvkm_fb *, int i, u32 size, u32 flags,
+                            struct nvkm_fb_tile *);
+               void (*fini)(struct nvkm_fb *, int i,
+                            struct nvkm_fb_tile *);
+               void (*prog)(struct nvkm_fb *, int i,
+                            struct nvkm_fb_tile *);
+       } tile;
+};
+
+void nv10_fb_tile_init(struct nvkm_fb *, int i, u32 addr, u32 size,
+                      u32 pitch, u32 flags, struct nvkm_fb_tile *);
+void nv10_fb_tile_fini(struct nvkm_fb *, int i, struct nvkm_fb_tile *);
+void nv10_fb_tile_prog(struct nvkm_fb *, int, struct nvkm_fb_tile *);
+
+void nv20_fb_tile_init(struct nvkm_fb *, int i, u32 addr, u32 size,
+                      u32 pitch, u32 flags, struct nvkm_fb_tile *);
+void nv20_fb_tile_fini(struct nvkm_fb *, int i, struct nvkm_fb_tile *);
+void nv20_fb_tile_prog(struct nvkm_fb *, int, struct nvkm_fb_tile *);
+
+int  nv30_fb_init(struct nvkm_object *);
+void nv30_fb_tile_init(struct nvkm_fb *, int i, u32 addr, u32 size,
+                      u32 pitch, u32 flags, struct nvkm_fb_tile *);
+
+void nv40_fb_tile_comp(struct nvkm_fb *, int i, u32 size, u32 flags,
+                      struct nvkm_fb_tile *);
+
+int  nv41_fb_init(struct nvkm_object *);
+void nv41_fb_tile_prog(struct nvkm_fb *, int, struct nvkm_fb_tile *);
+
+int  nv44_fb_init(struct nvkm_object *);
+void nv44_fb_tile_prog(struct nvkm_fb *, int, struct nvkm_fb_tile *);
+
+void nv46_fb_tile_init(struct nvkm_fb *, int i, u32 addr, u32 size,
+                      u32 pitch, u32 flags, struct nvkm_fb_tile *);
+#endif
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/fb/nv10.c b/drivers/gpu/drm/nouveau/nvkm/subdev/fb/nv10.c
new file mode 100644 (file)
index 0000000..f3530e4
--- /dev/null
@@ -0,0 +1,70 @@
+/*
+ * 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.
+ *
+ */
+#include "nv04.h"
+
+void
+nv10_fb_tile_init(struct nvkm_fb *pfb, int i, u32 addr, u32 size, u32 pitch,
+                 u32 flags, struct nvkm_fb_tile *tile)
+{
+       tile->addr  = 0x80000000 | addr;
+       tile->limit = max(1u, addr + size) - 1;
+       tile->pitch = pitch;
+}
+
+void
+nv10_fb_tile_fini(struct nvkm_fb *pfb, int i, struct nvkm_fb_tile *tile)
+{
+       tile->addr  = 0;
+       tile->limit = 0;
+       tile->pitch = 0;
+       tile->zcomp = 0;
+}
+
+void
+nv10_fb_tile_prog(struct nvkm_fb *pfb, int i, struct nvkm_fb_tile *tile)
+{
+       nv_wr32(pfb, 0x100244 + (i * 0x10), tile->limit);
+       nv_wr32(pfb, 0x100248 + (i * 0x10), tile->pitch);
+       nv_wr32(pfb, 0x100240 + (i * 0x10), tile->addr);
+       nv_rd32(pfb, 0x100240 + (i * 0x10));
+}
+
+struct nvkm_oclass *
+nv10_fb_oclass = &(struct nv04_fb_impl) {
+       .base.base.handle = NV_SUBDEV(FB, 0x10),
+       .base.base.ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = nv04_fb_ctor,
+               .dtor = _nvkm_fb_dtor,
+               .init = _nvkm_fb_init,
+               .fini = _nvkm_fb_fini,
+       },
+       .base.memtype = nv04_fb_memtype_valid,
+       .base.ram = &nv10_ram_oclass,
+       .tile.regions = 8,
+       .tile.init = nv10_fb_tile_init,
+       .tile.fini = nv10_fb_tile_fini,
+       .tile.prog = nv10_fb_tile_prog,
+}.base.base;
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/fb/nv1a.c b/drivers/gpu/drm/nouveau/nvkm/subdev/fb/nv1a.c
new file mode 100644 (file)
index 0000000..83bcb73
--- /dev/null
@@ -0,0 +1,43 @@
+/*
+ * 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.
+ *
+ */
+#include "nv04.h"
+
+struct nvkm_oclass *
+nv1a_fb_oclass = &(struct nv04_fb_impl) {
+       .base.base.handle = NV_SUBDEV(FB, 0x1a),
+       .base.base.ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = nv04_fb_ctor,
+               .dtor = _nvkm_fb_dtor,
+               .init = _nvkm_fb_init,
+               .fini = _nvkm_fb_fini,
+       },
+       .base.memtype = nv04_fb_memtype_valid,
+       .base.ram = &nv1a_ram_oclass,
+       .tile.regions = 8,
+       .tile.init = nv10_fb_tile_init,
+       .tile.fini = nv10_fb_tile_fini,
+       .tile.prog = nv10_fb_tile_prog,
+}.base.base;
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/fb/nv20.c b/drivers/gpu/drm/nouveau/nvkm/subdev/fb/nv20.c
new file mode 100644 (file)
index 0000000..e37084b
--- /dev/null
@@ -0,0 +1,94 @@
+/*
+ * 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.
+ *
+ */
+#include "nv04.h"
+
+void
+nv20_fb_tile_init(struct nvkm_fb *pfb, int i, u32 addr, u32 size, u32 pitch,
+                 u32 flags, struct nvkm_fb_tile *tile)
+{
+       tile->addr  = 0x00000001 | addr;
+       tile->limit = max(1u, addr + size) - 1;
+       tile->pitch = pitch;
+       if (flags & 4) {
+               pfb->tile.comp(pfb, i, size, flags, tile);
+               tile->addr |= 2;
+       }
+}
+
+static void
+nv20_fb_tile_comp(struct nvkm_fb *pfb, int i, u32 size, u32 flags,
+                 struct nvkm_fb_tile *tile)
+{
+       u32 tiles = DIV_ROUND_UP(size, 0x40);
+       u32 tags  = round_up(tiles / pfb->ram->parts, 0x40);
+       if (!nvkm_mm_head(&pfb->tags, 0, 1, tags, tags, 1, &tile->tag)) {
+               if (!(flags & 2)) tile->zcomp = 0x00000000; /* Z16 */
+               else              tile->zcomp = 0x04000000; /* Z24S8 */
+               tile->zcomp |= tile->tag->offset;
+               tile->zcomp |= 0x80000000; /* enable */
+#ifdef __BIG_ENDIAN
+               tile->zcomp |= 0x08000000;
+#endif
+       }
+}
+
+void
+nv20_fb_tile_fini(struct nvkm_fb *pfb, int i, struct nvkm_fb_tile *tile)
+{
+       tile->addr  = 0;
+       tile->limit = 0;
+       tile->pitch = 0;
+       tile->zcomp = 0;
+       nvkm_mm_free(&pfb->tags, &tile->tag);
+}
+
+void
+nv20_fb_tile_prog(struct nvkm_fb *pfb, int i, struct nvkm_fb_tile *tile)
+{
+       nv_wr32(pfb, 0x100244 + (i * 0x10), tile->limit);
+       nv_wr32(pfb, 0x100248 + (i * 0x10), tile->pitch);
+       nv_wr32(pfb, 0x100240 + (i * 0x10), tile->addr);
+       nv_rd32(pfb, 0x100240 + (i * 0x10));
+       nv_wr32(pfb, 0x100300 + (i * 0x04), tile->zcomp);
+}
+
+struct nvkm_oclass *
+nv20_fb_oclass = &(struct nv04_fb_impl) {
+       .base.base.handle = NV_SUBDEV(FB, 0x20),
+       .base.base.ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = nv04_fb_ctor,
+               .dtor = _nvkm_fb_dtor,
+               .init = _nvkm_fb_init,
+               .fini = _nvkm_fb_fini,
+       },
+       .base.memtype = nv04_fb_memtype_valid,
+       .base.ram = &nv20_ram_oclass,
+       .tile.regions = 8,
+       .tile.init = nv20_fb_tile_init,
+       .tile.comp = nv20_fb_tile_comp,
+       .tile.fini = nv20_fb_tile_fini,
+       .tile.prog = nv20_fb_tile_prog,
+}.base.base;
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/fb/nv25.c b/drivers/gpu/drm/nouveau/nvkm/subdev/fb/nv25.c
new file mode 100644 (file)
index 0000000..bc9f54f
--- /dev/null
@@ -0,0 +1,60 @@
+/*
+ * 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.
+ *
+ */
+#include "nv04.h"
+
+static void
+nv25_fb_tile_comp(struct nvkm_fb *pfb, int i, u32 size, u32 flags,
+                 struct nvkm_fb_tile *tile)
+{
+       u32 tiles = DIV_ROUND_UP(size, 0x40);
+       u32 tags  = round_up(tiles / pfb->ram->parts, 0x40);
+       if (!nvkm_mm_head(&pfb->tags, 0, 1, tags, tags, 1, &tile->tag)) {
+               if (!(flags & 2)) tile->zcomp = 0x00100000; /* Z16 */
+               else              tile->zcomp = 0x00200000; /* Z24S8 */
+               tile->zcomp |= tile->tag->offset;
+#ifdef __BIG_ENDIAN
+               tile->zcomp |= 0x01000000;
+#endif
+       }
+}
+
+struct nvkm_oclass *
+nv25_fb_oclass = &(struct nv04_fb_impl) {
+       .base.base.handle = NV_SUBDEV(FB, 0x25),
+       .base.base.ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = nv04_fb_ctor,
+               .dtor = _nvkm_fb_dtor,
+               .init = _nvkm_fb_init,
+               .fini = _nvkm_fb_fini,
+       },
+       .base.memtype = nv04_fb_memtype_valid,
+       .base.ram = &nv20_ram_oclass,
+       .tile.regions = 8,
+       .tile.init = nv20_fb_tile_init,
+       .tile.comp = nv25_fb_tile_comp,
+       .tile.fini = nv20_fb_tile_fini,
+       .tile.prog = nv20_fb_tile_prog,
+}.base.base;
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/fb/nv30.c b/drivers/gpu/drm/nouveau/nvkm/subdev/fb/nv30.c
new file mode 100644 (file)
index 0000000..09ebb94
--- /dev/null
@@ -0,0 +1,140 @@
+/*
+ * 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.
+ *
+ */
+#include "nv04.h"
+
+#include <core/device.h>
+
+void
+nv30_fb_tile_init(struct nvkm_fb *pfb, int i, u32 addr, u32 size, u32 pitch,
+                 u32 flags, struct nvkm_fb_tile *tile)
+{
+       /* for performance, select alternate bank offset for zeta */
+       if (!(flags & 4)) {
+               tile->addr = (0 << 4);
+       } else {
+               if (pfb->tile.comp) /* z compression */
+                       pfb->tile.comp(pfb, i, size, flags, tile);
+               tile->addr = (1 << 4);
+       }
+
+       tile->addr |= 0x00000001; /* enable */
+       tile->addr |= addr;
+       tile->limit = max(1u, addr + size) - 1;
+       tile->pitch = pitch;
+}
+
+static void
+nv30_fb_tile_comp(struct nvkm_fb *pfb, int i, u32 size, u32 flags,
+                 struct nvkm_fb_tile *tile)
+{
+       u32 tiles = DIV_ROUND_UP(size, 0x40);
+       u32 tags  = round_up(tiles / pfb->ram->parts, 0x40);
+       if (!nvkm_mm_head(&pfb->tags, 0, 1, tags, tags, 1, &tile->tag)) {
+               if (flags & 2) tile->zcomp |= 0x01000000; /* Z16 */
+               else           tile->zcomp |= 0x02000000; /* Z24S8 */
+               tile->zcomp |= ((tile->tag->offset           ) >> 6);
+               tile->zcomp |= ((tile->tag->offset + tags - 1) >> 6) << 12;
+#ifdef __BIG_ENDIAN
+               tile->zcomp |= 0x10000000;
+#endif
+       }
+}
+
+static int
+calc_bias(struct nv04_fb_priv *priv, int k, int i, int j)
+{
+       struct nvkm_device *device = nv_device(priv);
+       int b = (device->chipset > 0x30 ?
+                nv_rd32(priv, 0x122c + 0x10 * k + 0x4 * j) >> (4 * (i ^ 1)) :
+                0) & 0xf;
+
+       return 2 * (b & 0x8 ? b - 0x10 : b);
+}
+
+static int
+calc_ref(struct nv04_fb_priv *priv, int l, int k, int i)
+{
+       int j, x = 0;
+
+       for (j = 0; j < 4; j++) {
+               int m = (l >> (8 * i) & 0xff) + calc_bias(priv, k, i, j);
+
+               x |= (0x80 | clamp(m, 0, 0x1f)) << (8 * j);
+       }
+
+       return x;
+}
+
+int
+nv30_fb_init(struct nvkm_object *object)
+{
+       struct nvkm_device *device = nv_device(object);
+       struct nv04_fb_priv *priv = (void *)object;
+       int ret, i, j;
+
+       ret = nvkm_fb_init(&priv->base);
+       if (ret)
+               return ret;
+
+       /* Init the memory timing regs at 0x10037c/0x1003ac */
+       if (device->chipset == 0x30 ||
+           device->chipset == 0x31 ||
+           device->chipset == 0x35) {
+               /* Related to ROP count */
+               int n = (device->chipset == 0x31 ? 2 : 4);
+               int l = nv_rd32(priv, 0x1003d0);
+
+               for (i = 0; i < n; i++) {
+                       for (j = 0; j < 3; j++)
+                               nv_wr32(priv, 0x10037c + 0xc * i + 0x4 * j,
+                                       calc_ref(priv, l, 0, j));
+
+                       for (j = 0; j < 2; j++)
+                               nv_wr32(priv, 0x1003ac + 0x8 * i + 0x4 * j,
+                                       calc_ref(priv, l, 1, j));
+               }
+       }
+
+       return 0;
+}
+
+struct nvkm_oclass *
+nv30_fb_oclass = &(struct nv04_fb_impl) {
+       .base.base.handle = NV_SUBDEV(FB, 0x30),
+       .base.base.ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = nv04_fb_ctor,
+               .dtor = _nvkm_fb_dtor,
+               .init = nv30_fb_init,
+               .fini = _nvkm_fb_fini,
+       },
+       .base.memtype = nv04_fb_memtype_valid,
+       .base.ram = &nv20_ram_oclass,
+       .tile.regions = 8,
+       .tile.init = nv30_fb_tile_init,
+       .tile.comp = nv30_fb_tile_comp,
+       .tile.fini = nv20_fb_tile_fini,
+       .tile.prog = nv20_fb_tile_prog,
+}.base.base;
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/fb/nv35.c b/drivers/gpu/drm/nouveau/nvkm/subdev/fb/nv35.c
new file mode 100644 (file)
index 0000000..c01dc18
--- /dev/null
@@ -0,0 +1,61 @@
+/*
+ * 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.
+ *
+ */
+#include "nv04.h"
+
+static void
+nv35_fb_tile_comp(struct nvkm_fb *pfb, int i, u32 size, u32 flags,
+                 struct nvkm_fb_tile *tile)
+{
+       u32 tiles = DIV_ROUND_UP(size, 0x40);
+       u32 tags  = round_up(tiles / pfb->ram->parts, 0x40);
+       if (!nvkm_mm_head(&pfb->tags, 0, 1, tags, tags, 1, &tile->tag)) {
+               if (flags & 2) tile->zcomp |= 0x04000000; /* Z16 */
+               else           tile->zcomp |= 0x08000000; /* Z24S8 */
+               tile->zcomp |= ((tile->tag->offset           ) >> 6);
+               tile->zcomp |= ((tile->tag->offset + tags - 1) >> 6) << 13;
+#ifdef __BIG_ENDIAN
+               tile->zcomp |= 0x40000000;
+#endif
+       }
+}
+
+struct nvkm_oclass *
+nv35_fb_oclass = &(struct nv04_fb_impl) {
+       .base.base.handle = NV_SUBDEV(FB, 0x35),
+       .base.base.ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = nv04_fb_ctor,
+               .dtor = _nvkm_fb_dtor,
+               .init = nv30_fb_init,
+               .fini = _nvkm_fb_fini,
+       },
+       .base.memtype = nv04_fb_memtype_valid,
+       .base.ram = &nv20_ram_oclass,
+       .tile.regions = 8,
+       .tile.init = nv30_fb_tile_init,
+       .tile.comp = nv35_fb_tile_comp,
+       .tile.fini = nv20_fb_tile_fini,
+       .tile.prog = nv20_fb_tile_prog,
+}.base.base;
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/fb/nv36.c b/drivers/gpu/drm/nouveau/nvkm/subdev/fb/nv36.c
new file mode 100644 (file)
index 0000000..cad75a1
--- /dev/null
@@ -0,0 +1,61 @@
+/*
+ * 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.
+ *
+ */
+#include "nv04.h"
+
+static void
+nv36_fb_tile_comp(struct nvkm_fb *pfb, int i, u32 size, u32 flags,
+                 struct nvkm_fb_tile *tile)
+{
+       u32 tiles = DIV_ROUND_UP(size, 0x40);
+       u32 tags  = round_up(tiles / pfb->ram->parts, 0x40);
+       if (!nvkm_mm_head(&pfb->tags, 0, 1, tags, tags, 1, &tile->tag)) {
+               if (flags & 2) tile->zcomp |= 0x10000000; /* Z16 */
+               else           tile->zcomp |= 0x20000000; /* Z24S8 */
+               tile->zcomp |= ((tile->tag->offset           ) >> 6);
+               tile->zcomp |= ((tile->tag->offset + tags - 1) >> 6) << 14;
+#ifdef __BIG_ENDIAN
+               tile->zcomp |= 0x80000000;
+#endif
+       }
+}
+
+struct nvkm_oclass *
+nv36_fb_oclass = &(struct nv04_fb_impl) {
+       .base.base.handle = NV_SUBDEV(FB, 0x36),
+       .base.base.ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = nv04_fb_ctor,
+               .dtor = _nvkm_fb_dtor,
+               .init = nv30_fb_init,
+               .fini = _nvkm_fb_fini,
+       },
+       .base.memtype = nv04_fb_memtype_valid,
+       .base.ram = &nv20_ram_oclass,
+       .tile.regions = 8,
+       .tile.init = nv30_fb_tile_init,
+       .tile.comp = nv36_fb_tile_comp,
+       .tile.fini = nv20_fb_tile_fini,
+       .tile.prog = nv20_fb_tile_prog,
+}.base.base;
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/fb/nv40.c b/drivers/gpu/drm/nouveau/nvkm/subdev/fb/nv40.c
new file mode 100644 (file)
index 0000000..dbe5c19
--- /dev/null
@@ -0,0 +1,75 @@
+/*
+ * 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.
+ *
+ */
+#include "nv04.h"
+
+void
+nv40_fb_tile_comp(struct nvkm_fb *pfb, int i, u32 size, u32 flags,
+                 struct nvkm_fb_tile *tile)
+{
+       u32 tiles = DIV_ROUND_UP(size, 0x80);
+       u32 tags  = round_up(tiles / pfb->ram->parts, 0x100);
+       if ( (flags & 2) &&
+           !nvkm_mm_head(&pfb->tags, 0, 1, tags, tags, 1, &tile->tag)) {
+               tile->zcomp  = 0x28000000; /* Z24S8_SPLIT_GRAD */
+               tile->zcomp |= ((tile->tag->offset           ) >> 8);
+               tile->zcomp |= ((tile->tag->offset + tags - 1) >> 8) << 13;
+#ifdef __BIG_ENDIAN
+               tile->zcomp |= 0x40000000;
+#endif
+       }
+}
+
+static int
+nv40_fb_init(struct nvkm_object *object)
+{
+       struct nv04_fb_priv *priv = (void *)object;
+       int ret;
+
+       ret = nvkm_fb_init(&priv->base);
+       if (ret)
+               return ret;
+
+       nv_mask(priv, 0x10033c, 0x00008000, 0x00000000);
+       return 0;
+}
+
+struct nvkm_oclass *
+nv40_fb_oclass = &(struct nv04_fb_impl) {
+       .base.base.handle = NV_SUBDEV(FB, 0x40),
+       .base.base.ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = nv04_fb_ctor,
+               .dtor = _nvkm_fb_dtor,
+               .init = nv40_fb_init,
+               .fini = _nvkm_fb_fini,
+       },
+       .base.memtype = nv04_fb_memtype_valid,
+       .base.ram = &nv40_ram_oclass,
+       .tile.regions = 8,
+       .tile.init = nv30_fb_tile_init,
+       .tile.comp = nv40_fb_tile_comp,
+       .tile.fini = nv20_fb_tile_fini,
+       .tile.prog = nv20_fb_tile_prog,
+}.base.base;
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/fb/nv40.h b/drivers/gpu/drm/nouveau/nvkm/subdev/fb/nv40.h
new file mode 100644 (file)
index 0000000..6021826
--- /dev/null
@@ -0,0 +1,14 @@
+#ifndef __NVKM_FB_NV40_H__
+#define __NVKM_FB_NV40_H__
+#include "priv.h"
+
+struct nv40_ram {
+       struct nvkm_ram base;
+       u32 ctrl;
+       u32 coef;
+};
+
+int  nv40_ram_calc(struct nvkm_fb *, u32);
+int  nv40_ram_prog(struct nvkm_fb *);
+void nv40_ram_tidy(struct nvkm_fb *);
+#endif
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/fb/nv41.c b/drivers/gpu/drm/nouveau/nvkm/subdev/fb/nv41.c
new file mode 100644 (file)
index 0000000..d9e1a40
--- /dev/null
@@ -0,0 +1,68 @@
+/*
+ * 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.
+ *
+ */
+#include "nv04.h"
+
+void
+nv41_fb_tile_prog(struct nvkm_fb *pfb, int i, struct nvkm_fb_tile *tile)
+{
+       nv_wr32(pfb, 0x100604 + (i * 0x10), tile->limit);
+       nv_wr32(pfb, 0x100608 + (i * 0x10), tile->pitch);
+       nv_wr32(pfb, 0x100600 + (i * 0x10), tile->addr);
+       nv_rd32(pfb, 0x100600 + (i * 0x10));
+       nv_wr32(pfb, 0x100700 + (i * 0x04), tile->zcomp);
+}
+
+int
+nv41_fb_init(struct nvkm_object *object)
+{
+       struct nv04_fb_priv *priv = (void *)object;
+       int ret;
+
+       ret = nvkm_fb_init(&priv->base);
+       if (ret)
+               return ret;
+
+       nv_wr32(priv, 0x100800, 0x00000001);
+       return 0;
+}
+
+struct nvkm_oclass *
+nv41_fb_oclass = &(struct nv04_fb_impl) {
+       .base.base.handle = NV_SUBDEV(FB, 0x41),
+       .base.base.ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = nv04_fb_ctor,
+               .dtor = _nvkm_fb_dtor,
+               .init = nv41_fb_init,
+               .fini = _nvkm_fb_fini,
+       },
+       .base.memtype = nv04_fb_memtype_valid,
+       .base.ram = &nv41_ram_oclass,
+       .tile.regions = 12,
+       .tile.init = nv30_fb_tile_init,
+       .tile.comp = nv40_fb_tile_comp,
+       .tile.fini = nv20_fb_tile_fini,
+       .tile.prog = nv41_fb_tile_prog,
+}.base.base;
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/fb/nv44.c b/drivers/gpu/drm/nouveau/nvkm/subdev/fb/nv44.c
new file mode 100644 (file)
index 0000000..20b97c8
--- /dev/null
@@ -0,0 +1,77 @@
+/*
+ * 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.
+ *
+ */
+#include "nv04.h"
+
+static void
+nv44_fb_tile_init(struct nvkm_fb *pfb, int i, u32 addr, u32 size, u32 pitch,
+                 u32 flags, struct nvkm_fb_tile *tile)
+{
+       tile->addr  = 0x00000001; /* mode = vram */
+       tile->addr |= addr;
+       tile->limit = max(1u, addr + size) - 1;
+       tile->pitch = pitch;
+}
+
+void
+nv44_fb_tile_prog(struct nvkm_fb *pfb, int i, struct nvkm_fb_tile *tile)
+{
+       nv_wr32(pfb, 0x100604 + (i * 0x10), tile->limit);
+       nv_wr32(pfb, 0x100608 + (i * 0x10), tile->pitch);
+       nv_wr32(pfb, 0x100600 + (i * 0x10), tile->addr);
+       nv_rd32(pfb, 0x100600 + (i * 0x10));
+}
+
+int
+nv44_fb_init(struct nvkm_object *object)
+{
+       struct nv04_fb_priv *priv = (void *)object;
+       int ret;
+
+       ret = nvkm_fb_init(&priv->base);
+       if (ret)
+               return ret;
+
+       nv_wr32(priv, 0x100850, 0x80000000);
+       nv_wr32(priv, 0x100800, 0x00000001);
+       return 0;
+}
+
+struct nvkm_oclass *
+nv44_fb_oclass = &(struct nv04_fb_impl) {
+       .base.base.handle = NV_SUBDEV(FB, 0x44),
+       .base.base.ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = nv04_fb_ctor,
+               .dtor = _nvkm_fb_dtor,
+               .init = nv44_fb_init,
+               .fini = _nvkm_fb_fini,
+       },
+       .base.memtype = nv04_fb_memtype_valid,
+       .base.ram = &nv44_ram_oclass,
+       .tile.regions = 12,
+       .tile.init = nv44_fb_tile_init,
+       .tile.fini = nv20_fb_tile_fini,
+       .tile.prog = nv44_fb_tile_prog,
+}.base.base;
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/fb/nv46.c b/drivers/gpu/drm/nouveau/nvkm/subdev/fb/nv46.c
new file mode 100644 (file)
index 0000000..5bfac38
--- /dev/null
@@ -0,0 +1,57 @@
+/*
+ * 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.
+ *
+ */
+#include "nv04.h"
+
+void
+nv46_fb_tile_init(struct nvkm_fb *pfb, int i, u32 addr, u32 size, u32 pitch,
+                 u32 flags, struct nvkm_fb_tile *tile)
+{
+       /* for performance, select alternate bank offset for zeta */
+       if (!(flags & 4)) tile->addr = (0 << 3);
+       else              tile->addr = (1 << 3);
+
+       tile->addr |= 0x00000001; /* mode = vram */
+       tile->addr |= addr;
+       tile->limit = max(1u, addr + size) - 1;
+       tile->pitch = pitch;
+}
+
+struct nvkm_oclass *
+nv46_fb_oclass = &(struct nv04_fb_impl) {
+       .base.base.handle = NV_SUBDEV(FB, 0x46),
+       .base.base.ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = nv04_fb_ctor,
+               .dtor = _nvkm_fb_dtor,
+               .init = nv44_fb_init,
+               .fini = _nvkm_fb_fini,
+       },
+       .base.memtype = nv04_fb_memtype_valid,
+       .base.ram = &nv44_ram_oclass,
+       .tile.regions = 15,
+       .tile.init = nv46_fb_tile_init,
+       .tile.fini = nv20_fb_tile_fini,
+       .tile.prog = nv44_fb_tile_prog,
+}.base.base;
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/fb/nv47.c b/drivers/gpu/drm/nouveau/nvkm/subdev/fb/nv47.c
new file mode 100644 (file)
index 0000000..d3b3988
--- /dev/null
@@ -0,0 +1,44 @@
+/*
+ * 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.
+ *
+ */
+#include "nv04.h"
+
+struct nvkm_oclass *
+nv47_fb_oclass = &(struct nv04_fb_impl) {
+       .base.base.handle = NV_SUBDEV(FB, 0x47),
+       .base.base.ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = nv04_fb_ctor,
+               .dtor = _nvkm_fb_dtor,
+               .init = nv41_fb_init,
+               .fini = _nvkm_fb_fini,
+       },
+       .base.memtype = nv04_fb_memtype_valid,
+       .base.ram = &nv41_ram_oclass,
+       .tile.regions = 15,
+       .tile.init = nv30_fb_tile_init,
+       .tile.comp = nv40_fb_tile_comp,
+       .tile.fini = nv20_fb_tile_fini,
+       .tile.prog = nv41_fb_tile_prog,
+}.base.base;
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/fb/nv49.c b/drivers/gpu/drm/nouveau/nvkm/subdev/fb/nv49.c
new file mode 100644 (file)
index 0000000..236e36c
--- /dev/null
@@ -0,0 +1,44 @@
+/*
+ * 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.
+ *
+ */
+#include "nv04.h"
+
+struct nvkm_oclass *
+nv49_fb_oclass = &(struct nv04_fb_impl) {
+       .base.base.handle = NV_SUBDEV(FB, 0x49),
+       .base.base.ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = nv04_fb_ctor,
+               .dtor = _nvkm_fb_dtor,
+               .init = nv41_fb_init,
+               .fini = _nvkm_fb_fini,
+       },
+       .base.memtype = nv04_fb_memtype_valid,
+       .base.ram = &nv49_ram_oclass,
+       .tile.regions = 15,
+       .tile.init = nv30_fb_tile_init,
+       .tile.comp = nv40_fb_tile_comp,
+       .tile.fini = nv20_fb_tile_fini,
+       .tile.prog = nv41_fb_tile_prog,
+}.base.base;
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/fb/nv4e.c b/drivers/gpu/drm/nouveau/nvkm/subdev/fb/nv4e.c
new file mode 100644 (file)
index 0000000..1352b6a
--- /dev/null
@@ -0,0 +1,43 @@
+/*
+ * 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.
+ *
+ */
+#include "nv04.h"
+
+struct nvkm_oclass *
+nv4e_fb_oclass = &(struct nv04_fb_impl) {
+       .base.base.handle = NV_SUBDEV(FB, 0x4e),
+       .base.base.ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = nv04_fb_ctor,
+               .dtor = _nvkm_fb_dtor,
+               .init = nv44_fb_init,
+               .fini = _nvkm_fb_fini,
+       },
+       .base.memtype = nv04_fb_memtype_valid,
+       .base.ram = &nv4e_ram_oclass,
+       .tile.regions = 12,
+       .tile.init = nv46_fb_tile_init,
+       .tile.fini = nv20_fb_tile_fini,
+       .tile.prog = nv44_fb_tile_prog,
+}.base.base;
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/fb/nv50.c b/drivers/gpu/drm/nouveau/nvkm/subdev/fb/nv50.c
new file mode 100644 (file)
index 0000000..0480ce5
--- /dev/null
@@ -0,0 +1,320 @@
+/*
+ * Copyright 2012 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 "nv50.h"
+
+#include <core/client.h>
+#include <core/device.h>
+#include <core/engctx.h>
+#include <core/enum.h>
+
+int
+nv50_fb_memtype[0x80] = {
+       1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
+       1, 1, 1, 1, 0, 0, 0, 0, 2, 2, 2, 2, 0, 0, 0, 0,
+       1, 1, 1, 1, 1, 1, 1, 0, 2, 2, 2, 2, 2, 2, 2, 0,
+       0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
+       1, 1, 1, 1, 1, 1, 1, 2, 2, 2, 2, 2, 2, 2, 0, 0,
+       0, 0, 0, 0, 1, 1, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0,
+       1, 1, 1, 1, 1, 1, 1, 0, 1, 1, 1, 1, 2, 2, 2, 2,
+       1, 0, 2, 0, 1, 0, 2, 0, 1, 1, 2, 2, 1, 1, 0, 0
+};
+
+bool
+nv50_fb_memtype_valid(struct nvkm_fb *pfb, u32 memtype)
+{
+       return nv50_fb_memtype[(memtype & 0xff00) >> 8] != 0;
+}
+
+static const struct nvkm_enum vm_dispatch_subclients[] = {
+       { 0x00000000, "GRCTX", NULL },
+       { 0x00000001, "NOTIFY", NULL },
+       { 0x00000002, "QUERY", NULL },
+       { 0x00000003, "COND", NULL },
+       { 0x00000004, "M2M_IN", NULL },
+       { 0x00000005, "M2M_OUT", NULL },
+       { 0x00000006, "M2M_NOTIFY", NULL },
+       {}
+};
+
+static const struct nvkm_enum vm_ccache_subclients[] = {
+       { 0x00000000, "CB", NULL },
+       { 0x00000001, "TIC", NULL },
+       { 0x00000002, "TSC", NULL },
+       {}
+};
+
+static const struct nvkm_enum vm_prop_subclients[] = {
+       { 0x00000000, "RT0", NULL },
+       { 0x00000001, "RT1", NULL },
+       { 0x00000002, "RT2", NULL },
+       { 0x00000003, "RT3", NULL },
+       { 0x00000004, "RT4", NULL },
+       { 0x00000005, "RT5", NULL },
+       { 0x00000006, "RT6", NULL },
+       { 0x00000007, "RT7", NULL },
+       { 0x00000008, "ZETA", NULL },
+       { 0x00000009, "LOCAL", NULL },
+       { 0x0000000a, "GLOBAL", NULL },
+       { 0x0000000b, "STACK", NULL },
+       { 0x0000000c, "DST2D", NULL },
+       {}
+};
+
+static const struct nvkm_enum vm_pfifo_subclients[] = {
+       { 0x00000000, "PUSHBUF", NULL },
+       { 0x00000001, "SEMAPHORE", NULL },
+       {}
+};
+
+static const struct nvkm_enum vm_bar_subclients[] = {
+       { 0x00000000, "FB", NULL },
+       { 0x00000001, "IN", NULL },
+       {}
+};
+
+static const struct nvkm_enum vm_client[] = {
+       { 0x00000000, "STRMOUT", NULL },
+       { 0x00000003, "DISPATCH", vm_dispatch_subclients },
+       { 0x00000004, "PFIFO_WRITE", NULL },
+       { 0x00000005, "CCACHE", vm_ccache_subclients },
+       { 0x00000006, "PMSPPP", NULL },
+       { 0x00000007, "CLIPID", NULL },
+       { 0x00000008, "PFIFO_READ", NULL },
+       { 0x00000009, "VFETCH", NULL },
+       { 0x0000000a, "TEXTURE", NULL },
+       { 0x0000000b, "PROP", vm_prop_subclients },
+       { 0x0000000c, "PVP", NULL },
+       { 0x0000000d, "PBSP", NULL },
+       { 0x0000000e, "PCRYPT", NULL },
+       { 0x0000000f, "PCOUNTER", NULL },
+       { 0x00000011, "PDAEMON", NULL },
+       {}
+};
+
+static const struct nvkm_enum vm_engine[] = {
+       { 0x00000000, "PGRAPH", NULL, NVDEV_ENGINE_GR },
+       { 0x00000001, "PVP", NULL, NVDEV_ENGINE_VP },
+       { 0x00000004, "PEEPHOLE", NULL },
+       { 0x00000005, "PFIFO", vm_pfifo_subclients, NVDEV_ENGINE_FIFO },
+       { 0x00000006, "BAR", vm_bar_subclients },
+       { 0x00000008, "PMSPPP", NULL, NVDEV_ENGINE_MSPPP },
+       { 0x00000008, "PMPEG", NULL, NVDEV_ENGINE_MPEG },
+       { 0x00000009, "PBSP", NULL, NVDEV_ENGINE_BSP },
+       { 0x0000000a, "PCRYPT", NULL, NVDEV_ENGINE_CIPHER },
+       { 0x0000000b, "PCOUNTER", NULL },
+       { 0x0000000c, "SEMAPHORE_BG", NULL },
+       { 0x0000000d, "PCE0", NULL, NVDEV_ENGINE_CE0 },
+       { 0x0000000e, "PDAEMON", NULL },
+       {}
+};
+
+static const struct nvkm_enum vm_fault[] = {
+       { 0x00000000, "PT_NOT_PRESENT", NULL },
+       { 0x00000001, "PT_TOO_SHORT", NULL },
+       { 0x00000002, "PAGE_NOT_PRESENT", NULL },
+       { 0x00000003, "PAGE_SYSTEM_ONLY", NULL },
+       { 0x00000004, "PAGE_READ_ONLY", NULL },
+       { 0x00000006, "NULL_DMAOBJ", NULL },
+       { 0x00000007, "WRONG_MEMTYPE", NULL },
+       { 0x0000000b, "VRAM_LIMIT", NULL },
+       { 0x0000000f, "DMAOBJ_LIMIT", NULL },
+       {}
+};
+
+static void
+nv50_fb_intr(struct nvkm_subdev *subdev)
+{
+       struct nvkm_device *device = nv_device(subdev);
+       struct nvkm_engine *engine;
+       struct nv50_fb_priv *priv = (void *)subdev;
+       const struct nvkm_enum *en, *cl;
+       struct nvkm_object *engctx = NULL;
+       u32 trap[6], idx, chan;
+       u8 st0, st1, st2, st3;
+       int i;
+
+       idx = nv_rd32(priv, 0x100c90);
+       if (!(idx & 0x80000000))
+               return;
+       idx &= 0x00ffffff;
+
+       for (i = 0; i < 6; i++) {
+               nv_wr32(priv, 0x100c90, idx | i << 24);
+               trap[i] = nv_rd32(priv, 0x100c94);
+       }
+       nv_wr32(priv, 0x100c90, idx | 0x80000000);
+
+       /* decode status bits into something more useful */
+       if (device->chipset  < 0xa3 ||
+           device->chipset == 0xaa || device->chipset == 0xac) {
+               st0 = (trap[0] & 0x0000000f) >> 0;
+               st1 = (trap[0] & 0x000000f0) >> 4;
+               st2 = (trap[0] & 0x00000f00) >> 8;
+               st3 = (trap[0] & 0x0000f000) >> 12;
+       } else {
+               st0 = (trap[0] & 0x000000ff) >> 0;
+               st1 = (trap[0] & 0x0000ff00) >> 8;
+               st2 = (trap[0] & 0x00ff0000) >> 16;
+               st3 = (trap[0] & 0xff000000) >> 24;
+       }
+       chan = (trap[2] << 16) | trap[1];
+
+       en = nvkm_enum_find(vm_engine, st0);
+
+       if (en && en->data2) {
+               const struct nvkm_enum *orig_en = en;
+               while (en->name && en->value == st0 && en->data2) {
+                       engine = nvkm_engine(subdev, en->data2);
+                       /*XXX: clean this up */
+                       if (!engine && en->data2 == NVDEV_ENGINE_BSP)
+                               engine = nvkm_engine(subdev, NVDEV_ENGINE_MSVLD);
+                       if (!engine && en->data2 == NVDEV_ENGINE_CIPHER)
+                               engine = nvkm_engine(subdev, NVDEV_ENGINE_SEC);
+                       if (!engine && en->data2 == NVDEV_ENGINE_VP)
+                               engine = nvkm_engine(subdev, NVDEV_ENGINE_MSPDEC);
+                       if (engine) {
+                               engctx = nvkm_engctx_get(engine, chan);
+                               if (engctx)
+                                       break;
+                       }
+                       en++;
+               }
+               if (!engctx)
+                       en = orig_en;
+       }
+
+       nv_error(priv, "trapped %s at 0x%02x%04x%04x on channel 0x%08x [%s] ",
+                (trap[5] & 0x00000100) ? "read" : "write",
+                trap[5] & 0xff, trap[4] & 0xffff, trap[3] & 0xffff, chan,
+                nvkm_client_name(engctx));
+
+       nvkm_engctx_put(engctx);
+
+       if (en)
+               pr_cont("%s/", en->name);
+       else
+               pr_cont("%02x/", st0);
+
+       cl = nvkm_enum_find(vm_client, st2);
+       if (cl)
+               pr_cont("%s/", cl->name);
+       else
+               pr_cont("%02x/", st2);
+
+       if      (cl && cl->data) cl = nvkm_enum_find(cl->data, st3);
+       else if (en && en->data) cl = nvkm_enum_find(en->data, st3);
+       else                     cl = NULL;
+       if (cl)
+               pr_cont("%s", cl->name);
+       else
+               pr_cont("%02x", st3);
+
+       pr_cont(" reason: ");
+       en = nvkm_enum_find(vm_fault, st1);
+       if (en)
+               pr_cont("%s\n", en->name);
+       else
+               pr_cont("0x%08x\n", st1);
+}
+
+int
+nv50_fb_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+            struct nvkm_oclass *oclass, void *data, u32 size,
+            struct nvkm_object **pobject)
+{
+       struct nvkm_device *device = nv_device(parent);
+       struct nv50_fb_priv *priv;
+       int ret;
+
+       ret = nvkm_fb_create(parent, engine, oclass, &priv);
+       *pobject = nv_object(priv);
+       if (ret)
+               return ret;
+
+       priv->r100c08_page = alloc_page(GFP_KERNEL | __GFP_ZERO);
+       if (priv->r100c08_page) {
+               priv->r100c08 = dma_map_page(nv_device_base(device),
+                                            priv->r100c08_page, 0, PAGE_SIZE,
+                                            DMA_BIDIRECTIONAL);
+               if (dma_mapping_error(nv_device_base(device), priv->r100c08))
+                       return -EFAULT;
+       } else {
+               nv_warn(priv, "failed 0x100c08 page alloc\n");
+       }
+
+       nv_subdev(priv)->intr = nv50_fb_intr;
+       return 0;
+}
+
+void
+nv50_fb_dtor(struct nvkm_object *object)
+{
+       struct nvkm_device *device = nv_device(object);
+       struct nv50_fb_priv *priv = (void *)object;
+
+       if (priv->r100c08_page) {
+               dma_unmap_page(nv_device_base(device), priv->r100c08, PAGE_SIZE,
+                              DMA_BIDIRECTIONAL);
+               __free_page(priv->r100c08_page);
+       }
+
+       nvkm_fb_destroy(&priv->base);
+}
+
+int
+nv50_fb_init(struct nvkm_object *object)
+{
+       struct nv50_fb_impl *impl = (void *)object->oclass;
+       struct nv50_fb_priv *priv = (void *)object;
+       int ret;
+
+       ret = nvkm_fb_init(&priv->base);
+       if (ret)
+               return ret;
+
+       /* Not a clue what this is exactly.  Without pointing it at a
+        * scratch page, VRAM->GART blits with M2MF (as in DDX DFS)
+        * cause IOMMU "read from address 0" errors (rh#561267)
+        */
+       nv_wr32(priv, 0x100c08, priv->r100c08 >> 8);
+
+       /* This is needed to get meaningful information from 100c90
+        * on traps. No idea what these values mean exactly. */
+       nv_wr32(priv, 0x100c90, impl->trap);
+       return 0;
+}
+
+struct nvkm_oclass *
+nv50_fb_oclass = &(struct nv50_fb_impl) {
+       .base.base.handle = NV_SUBDEV(FB, 0x50),
+       .base.base.ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = nv50_fb_ctor,
+               .dtor = nv50_fb_dtor,
+               .init = nv50_fb_init,
+               .fini = _nvkm_fb_fini,
+       },
+       .base.memtype = nv50_fb_memtype_valid,
+       .base.ram = &nv50_ram_oclass,
+       .trap = 0x000707ff,
+}.base.base;
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/fb/nv50.h b/drivers/gpu/drm/nouveau/nvkm/subdev/fb/nv50.h
new file mode 100644 (file)
index 0000000..f3cde3f
--- /dev/null
@@ -0,0 +1,31 @@
+#ifndef __NVKM_FB_NV50_H__
+#define __NVKM_FB_NV50_H__
+#include "priv.h"
+
+struct nv50_fb_priv {
+       struct nvkm_fb base;
+       struct page *r100c08_page;
+       dma_addr_t r100c08;
+};
+
+int  nv50_fb_ctor(struct nvkm_object *, struct nvkm_object *,
+                 struct nvkm_oclass *, void *, u32,
+                 struct nvkm_object **);
+void nv50_fb_dtor(struct nvkm_object *);
+int  nv50_fb_init(struct nvkm_object *);
+
+struct nv50_fb_impl {
+       struct nvkm_fb_impl base;
+       u32 trap;
+};
+
+#define nv50_ram_create(p,e,o,d)                                               \
+       nv50_ram_create_((p), (e), (o), sizeof(**d), (void **)d)
+int  nv50_ram_create_(struct nvkm_object *, struct nvkm_object *,
+                     struct nvkm_oclass *, int, void **);
+int  nv50_ram_get(struct nvkm_fb *, u64 size, u32 align, u32 ncmin,
+                 u32 memtype, struct nvkm_mem **);
+void nv50_ram_put(struct nvkm_fb *, struct nvkm_mem **);
+void __nv50_ram_put(struct nvkm_fb *, struct nvkm_mem *);
+extern int nv50_fb_memtype[0x80];
+#endif
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/fb/priv.h b/drivers/gpu/drm/nouveau/nvkm/subdev/fb/priv.h
new file mode 100644 (file)
index 0000000..d82da02
--- /dev/null
@@ -0,0 +1,74 @@
+#ifndef __NVKM_FB_PRIV_H__
+#define __NVKM_FB_PRIV_H__
+#include <subdev/fb.h>
+struct nvkm_bios;
+
+#define nvkm_ram_create(p,e,o,d)                                            \
+       nvkm_object_create_((p), (e), (o), 0, sizeof(**d), (void **)d)
+#define nvkm_ram_destroy(p)                                                 \
+       nvkm_object_destroy(&(p)->base)
+#define nvkm_ram_init(p)                                                    \
+       nvkm_object_init(&(p)->base)
+#define nvkm_ram_fini(p,s)                                                  \
+       nvkm_object_fini(&(p)->base, (s))
+
+#define nvkm_ram_create_(p,e,o,s,d)                                         \
+       nvkm_object_create_((p), (e), (o), 0, (s), (void **)d)
+#define _nvkm_ram_dtor nvkm_object_destroy
+#define _nvkm_ram_init nvkm_object_init
+#define _nvkm_ram_fini nvkm_object_fini
+
+extern struct nvkm_oclass nv04_ram_oclass;
+extern struct nvkm_oclass nv10_ram_oclass;
+extern struct nvkm_oclass nv1a_ram_oclass;
+extern struct nvkm_oclass nv20_ram_oclass;
+extern struct nvkm_oclass nv40_ram_oclass;
+extern struct nvkm_oclass nv41_ram_oclass;
+extern struct nvkm_oclass nv44_ram_oclass;
+extern struct nvkm_oclass nv49_ram_oclass;
+extern struct nvkm_oclass nv4e_ram_oclass;
+extern struct nvkm_oclass nv50_ram_oclass;
+extern struct nvkm_oclass gt215_ram_oclass;
+extern struct nvkm_oclass mcp77_ram_oclass;
+extern struct nvkm_oclass gf100_ram_oclass;
+extern struct nvkm_oclass gk104_ram_oclass;
+extern struct nvkm_oclass gk20a_ram_oclass;
+extern struct nvkm_oclass gm107_ram_oclass;
+
+int nvkm_sddr2_calc(struct nvkm_ram *ram);
+int nvkm_sddr3_calc(struct nvkm_ram *ram);
+int nvkm_gddr3_calc(struct nvkm_ram *ram);
+int nvkm_gddr5_calc(struct nvkm_ram *ram, bool nuts);
+
+#define nvkm_fb_create(p,e,c,d)                                             \
+       nvkm_fb_create_((p), (e), (c), sizeof(**d), (void **)d)
+#define nvkm_fb_destroy(p) ({                                               \
+       struct nvkm_fb *pfb = (p);                                          \
+       _nvkm_fb_dtor(nv_object(pfb));                                      \
+})
+#define nvkm_fb_init(p) ({                                                  \
+       struct nvkm_fb *pfb = (p);                                          \
+       _nvkm_fb_init(nv_object(pfb));                                      \
+})
+#define nvkm_fb_fini(p,s) ({                                                \
+       struct nvkm_fb *pfb = (p);                                          \
+       _nvkm_fb_fini(nv_object(pfb), (s));                                 \
+})
+
+int nvkm_fb_create_(struct nvkm_object *, struct nvkm_object *,
+                      struct nvkm_oclass *, int, void **);
+void _nvkm_fb_dtor(struct nvkm_object *);
+int  _nvkm_fb_init(struct nvkm_object *);
+int  _nvkm_fb_fini(struct nvkm_object *, bool);
+
+struct nvkm_fb_impl {
+       struct nvkm_oclass base;
+       struct nvkm_oclass *ram;
+       bool (*memtype)(struct nvkm_fb *, u32);
+};
+
+bool nv04_fb_memtype_valid(struct nvkm_fb *, u32 memtype);
+bool nv50_fb_memtype_valid(struct nvkm_fb *, u32 memtype);
+
+int  nvkm_fb_bios_memtype(struct nvkm_bios *);
+#endif
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/fb/ramfuc.h b/drivers/gpu/drm/nouveau/nvkm/subdev/fb/ramfuc.h
new file mode 100644 (file)
index 0000000..f343682
--- /dev/null
@@ -0,0 +1,180 @@
+#ifndef __NVKM_FBRAM_FUC_H__
+#define __NVKM_FBRAM_FUC_H__
+#include <subdev/pmu.h>
+
+struct ramfuc {
+       struct nvkm_memx *memx;
+       struct nvkm_fb *pfb;
+       int sequence;
+};
+
+struct ramfuc_reg {
+       int sequence;
+       bool force;
+       u32 addr;
+       u32 stride; /* in bytes */
+       u32 mask;
+       u32 data;
+};
+
+static inline struct ramfuc_reg
+ramfuc_stride(u32 addr, u32 stride, u32 mask)
+{
+       return (struct ramfuc_reg) {
+               .sequence = 0,
+               .addr = addr,
+               .stride = stride,
+               .mask = mask,
+               .data = 0xdeadbeef,
+       };
+}
+
+static inline struct ramfuc_reg
+ramfuc_reg2(u32 addr1, u32 addr2)
+{
+       return (struct ramfuc_reg) {
+               .sequence = 0,
+               .addr = addr1,
+               .stride = addr2 - addr1,
+               .mask = 0x3,
+               .data = 0xdeadbeef,
+       };
+}
+
+static noinline struct ramfuc_reg
+ramfuc_reg(u32 addr)
+{
+       return (struct ramfuc_reg) {
+               .sequence = 0,
+               .addr = addr,
+               .stride = 0,
+               .mask = 0x1,
+               .data = 0xdeadbeef,
+       };
+}
+
+static inline int
+ramfuc_init(struct ramfuc *ram, struct nvkm_fb *pfb)
+{
+       struct nvkm_pmu *pmu = nvkm_pmu(pfb);
+       int ret;
+
+       ret = nvkm_memx_init(pmu, &ram->memx);
+       if (ret)
+               return ret;
+
+       ram->sequence++;
+       ram->pfb = pfb;
+       return 0;
+}
+
+static inline int
+ramfuc_exec(struct ramfuc *ram, bool exec)
+{
+       int ret = 0;
+       if (ram->pfb) {
+               ret = nvkm_memx_fini(&ram->memx, exec);
+               ram->pfb = NULL;
+       }
+       return ret;
+}
+
+static inline u32
+ramfuc_rd32(struct ramfuc *ram, struct ramfuc_reg *reg)
+{
+       if (reg->sequence != ram->sequence)
+               reg->data = nv_rd32(ram->pfb, reg->addr);
+       return reg->data;
+}
+
+static inline void
+ramfuc_wr32(struct ramfuc *ram, struct ramfuc_reg *reg, u32 data)
+{
+       unsigned int mask, off = 0;
+
+       reg->sequence = ram->sequence;
+       reg->data = data;
+
+       for (mask = reg->mask; mask > 0; mask = (mask & ~1) >> 1) {
+               if (mask & 1)
+                       nvkm_memx_wr32(ram->memx, reg->addr+off, reg->data);
+               off += reg->stride;
+       }
+}
+
+static inline void
+ramfuc_nuke(struct ramfuc *ram, struct ramfuc_reg *reg)
+{
+       reg->force = true;
+}
+
+static inline u32
+ramfuc_mask(struct ramfuc *ram, struct ramfuc_reg *reg, u32 mask, u32 data)
+{
+       u32 temp = ramfuc_rd32(ram, reg);
+       if (temp != ((temp & ~mask) | data) || reg->force) {
+               ramfuc_wr32(ram, reg, (temp & ~mask) | data);
+               reg->force = false;
+       }
+       return temp;
+}
+
+static inline void
+ramfuc_wait(struct ramfuc *ram, u32 addr, u32 mask, u32 data, u32 nsec)
+{
+       nvkm_memx_wait(ram->memx, addr, mask, data, nsec);
+}
+
+static inline void
+ramfuc_nsec(struct ramfuc *ram, u32 nsec)
+{
+       nvkm_memx_nsec(ram->memx, nsec);
+}
+
+static inline void
+ramfuc_wait_vblank(struct ramfuc *ram)
+{
+       nvkm_memx_wait_vblank(ram->memx);
+}
+
+static inline void
+ramfuc_train(struct ramfuc *ram)
+{
+       nvkm_memx_train(ram->memx);
+}
+
+static inline int
+ramfuc_train_result(struct nvkm_fb *pfb, u32 *result, u32 rsize)
+{
+       struct nvkm_pmu *pmu = nvkm_pmu(pfb);
+
+       return nvkm_memx_train_result(pmu, result, rsize);
+}
+
+static inline void
+ramfuc_block(struct ramfuc *ram)
+{
+       nvkm_memx_block(ram->memx);
+}
+
+static inline void
+ramfuc_unblock(struct ramfuc *ram)
+{
+       nvkm_memx_unblock(ram->memx);
+}
+
+#define ram_init(s,p)        ramfuc_init(&(s)->base, (p))
+#define ram_exec(s,e)        ramfuc_exec(&(s)->base, (e))
+#define ram_have(s,r)        ((s)->r_##r.addr != 0x000000)
+#define ram_rd32(s,r)        ramfuc_rd32(&(s)->base, &(s)->r_##r)
+#define ram_wr32(s,r,d)      ramfuc_wr32(&(s)->base, &(s)->r_##r, (d))
+#define ram_nuke(s,r)        ramfuc_nuke(&(s)->base, &(s)->r_##r)
+#define ram_mask(s,r,m,d)    ramfuc_mask(&(s)->base, &(s)->r_##r, (m), (d))
+#define ram_wait(s,r,m,d,n)  ramfuc_wait(&(s)->base, (r), (m), (d), (n))
+#define ram_nsec(s,n)        ramfuc_nsec(&(s)->base, (n))
+#define ram_wait_vblank(s)   ramfuc_wait_vblank(&(s)->base)
+#define ram_train(s)         ramfuc_train(&(s)->base)
+#define ram_train_result(s,r,l) ramfuc_train_result((s), (r), (l))
+#define ram_block(s)         ramfuc_block(&(s)->base)
+#define ram_unblock(s)       ramfuc_unblock(&(s)->base)
+#endif
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/fb/ramgf100.c b/drivers/gpu/drm/nouveau/nvkm/subdev/fb/ramgf100.c
new file mode 100644 (file)
index 0000000..de9f395
--- /dev/null
@@ -0,0 +1,731 @@
+/*
+ * Copyright 2013 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 "gf100.h"
+#include "ramfuc.h"
+
+#include <core/device.h>
+#include <core/option.h>
+#include <subdev/bios.h>
+#include <subdev/bios/pll.h>
+#include <subdev/bios/rammap.h>
+#include <subdev/bios/timing.h>
+#include <subdev/clk.h>
+#include <subdev/clk/pll.h>
+#include <subdev/ltc.h>
+
+struct gf100_ramfuc {
+       struct ramfuc base;
+
+       struct ramfuc_reg r_0x10fe20;
+       struct ramfuc_reg r_0x10fe24;
+       struct ramfuc_reg r_0x137320;
+       struct ramfuc_reg r_0x137330;
+
+       struct ramfuc_reg r_0x132000;
+       struct ramfuc_reg r_0x132004;
+       struct ramfuc_reg r_0x132100;
+
+       struct ramfuc_reg r_0x137390;
+
+       struct ramfuc_reg r_0x10f290;
+       struct ramfuc_reg r_0x10f294;
+       struct ramfuc_reg r_0x10f298;
+       struct ramfuc_reg r_0x10f29c;
+       struct ramfuc_reg r_0x10f2a0;
+
+       struct ramfuc_reg r_0x10f300;
+       struct ramfuc_reg r_0x10f338;
+       struct ramfuc_reg r_0x10f340;
+       struct ramfuc_reg r_0x10f344;
+       struct ramfuc_reg r_0x10f348;
+
+       struct ramfuc_reg r_0x10f910;
+       struct ramfuc_reg r_0x10f914;
+
+       struct ramfuc_reg r_0x100b0c;
+       struct ramfuc_reg r_0x10f050;
+       struct ramfuc_reg r_0x10f090;
+       struct ramfuc_reg r_0x10f200;
+       struct ramfuc_reg r_0x10f210;
+       struct ramfuc_reg r_0x10f310;
+       struct ramfuc_reg r_0x10f314;
+       struct ramfuc_reg r_0x10f610;
+       struct ramfuc_reg r_0x10f614;
+       struct ramfuc_reg r_0x10f800;
+       struct ramfuc_reg r_0x10f808;
+       struct ramfuc_reg r_0x10f824;
+       struct ramfuc_reg r_0x10f830;
+       struct ramfuc_reg r_0x10f988;
+       struct ramfuc_reg r_0x10f98c;
+       struct ramfuc_reg r_0x10f990;
+       struct ramfuc_reg r_0x10f998;
+       struct ramfuc_reg r_0x10f9b0;
+       struct ramfuc_reg r_0x10f9b4;
+       struct ramfuc_reg r_0x10fb04;
+       struct ramfuc_reg r_0x10fb08;
+       struct ramfuc_reg r_0x137300;
+       struct ramfuc_reg r_0x137310;
+       struct ramfuc_reg r_0x137360;
+       struct ramfuc_reg r_0x1373ec;
+       struct ramfuc_reg r_0x1373f0;
+       struct ramfuc_reg r_0x1373f8;
+
+       struct ramfuc_reg r_0x61c140;
+       struct ramfuc_reg r_0x611200;
+
+       struct ramfuc_reg r_0x13d8f4;
+};
+
+struct gf100_ram {
+       struct nvkm_ram base;
+       struct gf100_ramfuc fuc;
+       struct nvbios_pll refpll;
+       struct nvbios_pll mempll;
+};
+
+static void
+gf100_ram_train(struct gf100_ramfuc *fuc, u32 magic)
+{
+       struct gf100_ram *ram = container_of(fuc, typeof(*ram), fuc);
+       struct nvkm_fb *pfb = nvkm_fb(ram);
+       u32 part = nv_rd32(pfb, 0x022438), i;
+       u32 mask = nv_rd32(pfb, 0x022554);
+       u32 addr = 0x110974;
+
+       ram_wr32(fuc, 0x10f910, magic);
+       ram_wr32(fuc, 0x10f914, magic);
+
+       for (i = 0; (magic & 0x80000000) && i < part; addr += 0x1000, i++) {
+               if (mask & (1 << i))
+                       continue;
+               ram_wait(fuc, addr, 0x0000000f, 0x00000000, 500000);
+       }
+}
+
+static int
+gf100_ram_calc(struct nvkm_fb *pfb, u32 freq)
+{
+       struct nvkm_clk *clk = nvkm_clk(pfb);
+       struct nvkm_bios *bios = nvkm_bios(pfb);
+       struct gf100_ram *ram = (void *)pfb->ram;
+       struct gf100_ramfuc *fuc = &ram->fuc;
+       struct nvbios_ramcfg cfg;
+       u8  ver, cnt, len, strap;
+       struct {
+               u32 data;
+               u8  size;
+       } rammap, ramcfg, timing;
+       int ref, div, out;
+       int from, mode;
+       int N1, M1, P;
+       int ret;
+
+       /* lookup memory config data relevant to the target frequency */
+       rammap.data = nvbios_rammapEm(bios, freq / 1000, &ver, &rammap.size,
+                                     &cnt, &ramcfg.size, &cfg);
+       if (!rammap.data || ver != 0x10 || rammap.size < 0x0e) {
+               nv_error(pfb, "invalid/missing rammap entry\n");
+               return -EINVAL;
+       }
+
+       /* locate specific data set for the attached memory */
+       strap = nvbios_ramcfg_index(nv_subdev(pfb));
+       if (strap >= cnt) {
+               nv_error(pfb, "invalid ramcfg strap\n");
+               return -EINVAL;
+       }
+
+       ramcfg.data = rammap.data + rammap.size + (strap * ramcfg.size);
+       if (!ramcfg.data || ver != 0x10 || ramcfg.size < 0x0e) {
+               nv_error(pfb, "invalid/missing ramcfg entry\n");
+               return -EINVAL;
+       }
+
+       /* lookup memory timings, if bios says they're present */
+       strap = nv_ro08(bios, ramcfg.data + 0x01);
+       if (strap != 0xff) {
+               timing.data = nvbios_timingEe(bios, strap, &ver, &timing.size,
+                                             &cnt, &len);
+               if (!timing.data || ver != 0x10 || timing.size < 0x19) {
+                       nv_error(pfb, "invalid/missing timing entry\n");
+                       return -EINVAL;
+               }
+       } else {
+               timing.data = 0;
+       }
+
+       ret = ram_init(fuc, pfb);
+       if (ret)
+               return ret;
+
+       /* determine current mclk configuration */
+       from = !!(ram_rd32(fuc, 0x1373f0) & 0x00000002); /*XXX: ok? */
+
+       /* determine target mclk configuration */
+       if (!(ram_rd32(fuc, 0x137300) & 0x00000100))
+               ref = clk->read(clk, nv_clk_src_sppll0);
+       else
+               ref = clk->read(clk, nv_clk_src_sppll1);
+       div = max(min((ref * 2) / freq, (u32)65), (u32)2) - 2;
+       out = (ref * 2) / (div + 2);
+       mode = freq != out;
+
+       ram_mask(fuc, 0x137360, 0x00000002, 0x00000000);
+
+       if ((ram_rd32(fuc, 0x132000) & 0x00000002) || 0 /*XXX*/) {
+               ram_nuke(fuc, 0x132000);
+               ram_mask(fuc, 0x132000, 0x00000002, 0x00000002);
+               ram_mask(fuc, 0x132000, 0x00000002, 0x00000000);
+       }
+
+       if (mode == 1) {
+               ram_nuke(fuc, 0x10fe20);
+               ram_mask(fuc, 0x10fe20, 0x00000002, 0x00000002);
+               ram_mask(fuc, 0x10fe20, 0x00000002, 0x00000000);
+       }
+
+// 0x00020034 // 0x0000000a
+       ram_wr32(fuc, 0x132100, 0x00000001);
+
+       if (mode == 1 && from == 0) {
+               /* calculate refpll */
+               ret = gt215_pll_calc(nv_subdev(pfb), &ram->refpll,
+                                    ram->mempll.refclk, &N1, NULL, &M1, &P);
+               if (ret <= 0) {
+                       nv_error(pfb, "unable to calc refpll\n");
+                       return ret ? ret : -ERANGE;
+               }
+
+               ram_wr32(fuc, 0x10fe20, 0x20010000);
+               ram_wr32(fuc, 0x137320, 0x00000003);
+               ram_wr32(fuc, 0x137330, 0x81200006);
+               ram_wr32(fuc, 0x10fe24, (P << 16) | (N1 << 8) | M1);
+               ram_wr32(fuc, 0x10fe20, 0x20010001);
+               ram_wait(fuc, 0x137390, 0x00020000, 0x00020000, 64000);
+
+               /* calculate mempll */
+               ret = gt215_pll_calc(nv_subdev(pfb), &ram->mempll, freq,
+                                    &N1, NULL, &M1, &P);
+               if (ret <= 0) {
+                       nv_error(pfb, "unable to calc refpll\n");
+                       return ret ? ret : -ERANGE;
+               }
+
+               ram_wr32(fuc, 0x10fe20, 0x20010005);
+               ram_wr32(fuc, 0x132004, (P << 16) | (N1 << 8) | M1);
+               ram_wr32(fuc, 0x132000, 0x18010101);
+               ram_wait(fuc, 0x137390, 0x00000002, 0x00000002, 64000);
+       } else
+       if (mode == 0) {
+               ram_wr32(fuc, 0x137300, 0x00000003);
+       }
+
+       if (from == 0) {
+               ram_nuke(fuc, 0x10fb04);
+               ram_mask(fuc, 0x10fb04, 0x0000ffff, 0x00000000);
+               ram_nuke(fuc, 0x10fb08);
+               ram_mask(fuc, 0x10fb08, 0x0000ffff, 0x00000000);
+               ram_wr32(fuc, 0x10f988, 0x2004ff00);
+               ram_wr32(fuc, 0x10f98c, 0x003fc040);
+               ram_wr32(fuc, 0x10f990, 0x20012001);
+               ram_wr32(fuc, 0x10f998, 0x00011a00);
+               ram_wr32(fuc, 0x13d8f4, 0x00000000);
+       } else {
+               ram_wr32(fuc, 0x10f988, 0x20010000);
+               ram_wr32(fuc, 0x10f98c, 0x00000000);
+               ram_wr32(fuc, 0x10f990, 0x20012001);
+               ram_wr32(fuc, 0x10f998, 0x00010a00);
+       }
+
+       if (from == 0) {
+// 0x00020039 // 0x000000ba
+       }
+
+// 0x0002003a // 0x00000002
+       ram_wr32(fuc, 0x100b0c, 0x00080012);
+// 0x00030014 // 0x00000000 // 0x02b5f070
+// 0x00030014 // 0x00010000 // 0x02b5f070
+       ram_wr32(fuc, 0x611200, 0x00003300);
+// 0x00020034 // 0x0000000a
+// 0x00030020 // 0x00000001 // 0x00000000
+
+       ram_mask(fuc, 0x10f200, 0x00000800, 0x00000000);
+       ram_wr32(fuc, 0x10f210, 0x00000000);
+       ram_nsec(fuc, 1000);
+       if (mode == 0)
+               gf100_ram_train(fuc, 0x000c1001);
+       ram_wr32(fuc, 0x10f310, 0x00000001);
+       ram_nsec(fuc, 1000);
+       ram_wr32(fuc, 0x10f090, 0x00000061);
+       ram_wr32(fuc, 0x10f090, 0xc000007f);
+       ram_nsec(fuc, 1000);
+
+       if (from == 0) {
+               ram_wr32(fuc, 0x10f824, 0x00007fd4);
+       } else {
+               ram_wr32(fuc, 0x1373ec, 0x00020404);
+       }
+
+       if (mode == 0) {
+               ram_mask(fuc, 0x10f808, 0x00080000, 0x00000000);
+               ram_mask(fuc, 0x10f200, 0x00008000, 0x00008000);
+               ram_wr32(fuc, 0x10f830, 0x41500010);
+               ram_mask(fuc, 0x10f830, 0x01000000, 0x00000000);
+               ram_mask(fuc, 0x132100, 0x00000100, 0x00000100);
+               ram_wr32(fuc, 0x10f050, 0xff000090);
+               ram_wr32(fuc, 0x1373ec, 0x00020f0f);
+               ram_wr32(fuc, 0x1373f0, 0x00000003);
+               ram_wr32(fuc, 0x137310, 0x81201616);
+               ram_wr32(fuc, 0x132100, 0x00000001);
+// 0x00020039 // 0x000000ba
+               ram_wr32(fuc, 0x10f830, 0x00300017);
+               ram_wr32(fuc, 0x1373f0, 0x00000001);
+               ram_wr32(fuc, 0x10f824, 0x00007e77);
+               ram_wr32(fuc, 0x132000, 0x18030001);
+               ram_wr32(fuc, 0x10f090, 0x4000007e);
+               ram_nsec(fuc, 2000);
+               ram_wr32(fuc, 0x10f314, 0x00000001);
+               ram_wr32(fuc, 0x10f210, 0x80000000);
+               ram_wr32(fuc, 0x10f338, 0x00300220);
+               ram_wr32(fuc, 0x10f300, 0x0000011d);
+               ram_nsec(fuc, 1000);
+               ram_wr32(fuc, 0x10f290, 0x02060505);
+               ram_wr32(fuc, 0x10f294, 0x34208288);
+               ram_wr32(fuc, 0x10f298, 0x44050411);
+               ram_wr32(fuc, 0x10f29c, 0x0000114c);
+               ram_wr32(fuc, 0x10f2a0, 0x42e10069);
+               ram_wr32(fuc, 0x10f614, 0x40044f77);
+               ram_wr32(fuc, 0x10f610, 0x40044f77);
+               ram_wr32(fuc, 0x10f344, 0x00600009);
+               ram_nsec(fuc, 1000);
+               ram_wr32(fuc, 0x10f348, 0x00700008);
+               ram_wr32(fuc, 0x61c140, 0x19240000);
+               ram_wr32(fuc, 0x10f830, 0x00300017);
+               gf100_ram_train(fuc, 0x80021001);
+               gf100_ram_train(fuc, 0x80081001);
+               ram_wr32(fuc, 0x10f340, 0x00500004);
+               ram_nsec(fuc, 1000);
+               ram_wr32(fuc, 0x10f830, 0x01300017);
+               ram_wr32(fuc, 0x10f830, 0x00300017);
+// 0x00030020 // 0x00000000 // 0x00000000
+// 0x00020034 // 0x0000000b
+               ram_wr32(fuc, 0x100b0c, 0x00080028);
+               ram_wr32(fuc, 0x611200, 0x00003330);
+       } else {
+               ram_wr32(fuc, 0x10f800, 0x00001800);
+               ram_wr32(fuc, 0x13d8f4, 0x00000000);
+               ram_wr32(fuc, 0x1373ec, 0x00020404);
+               ram_wr32(fuc, 0x1373f0, 0x00000003);
+               ram_wr32(fuc, 0x10f830, 0x40700010);
+               ram_wr32(fuc, 0x10f830, 0x40500010);
+               ram_wr32(fuc, 0x13d8f4, 0x00000000);
+               ram_wr32(fuc, 0x1373f8, 0x00000000);
+               ram_wr32(fuc, 0x132100, 0x00000101);
+               ram_wr32(fuc, 0x137310, 0x89201616);
+               ram_wr32(fuc, 0x10f050, 0xff000090);
+               ram_wr32(fuc, 0x1373ec, 0x00030404);
+               ram_wr32(fuc, 0x1373f0, 0x00000002);
+       // 0x00020039 // 0x00000011
+               ram_wr32(fuc, 0x132100, 0x00000001);
+               ram_wr32(fuc, 0x1373f8, 0x00002000);
+               ram_nsec(fuc, 2000);
+               ram_wr32(fuc, 0x10f808, 0x7aaa0050);
+               ram_wr32(fuc, 0x10f830, 0x00500010);
+               ram_wr32(fuc, 0x10f200, 0x00ce1000);
+               ram_wr32(fuc, 0x10f090, 0x4000007e);
+               ram_nsec(fuc, 2000);
+               ram_wr32(fuc, 0x10f314, 0x00000001);
+               ram_wr32(fuc, 0x10f210, 0x80000000);
+               ram_wr32(fuc, 0x10f338, 0x00300200);
+               ram_wr32(fuc, 0x10f300, 0x0000084d);
+               ram_nsec(fuc, 1000);
+               ram_wr32(fuc, 0x10f290, 0x0b343825);
+               ram_wr32(fuc, 0x10f294, 0x3483028e);
+               ram_wr32(fuc, 0x10f298, 0x440c0600);
+               ram_wr32(fuc, 0x10f29c, 0x0000214c);
+               ram_wr32(fuc, 0x10f2a0, 0x42e20069);
+               ram_wr32(fuc, 0x10f200, 0x00ce0000);
+               ram_wr32(fuc, 0x10f614, 0x60044e77);
+               ram_wr32(fuc, 0x10f610, 0x60044e77);
+               ram_wr32(fuc, 0x10f340, 0x00500000);
+               ram_nsec(fuc, 1000);
+               ram_wr32(fuc, 0x10f344, 0x00600228);
+               ram_nsec(fuc, 1000);
+               ram_wr32(fuc, 0x10f348, 0x00700000);
+               ram_wr32(fuc, 0x13d8f4, 0x00000000);
+               ram_wr32(fuc, 0x61c140, 0x09a40000);
+
+               gf100_ram_train(fuc, 0x800e1008);
+
+               ram_nsec(fuc, 1000);
+               ram_wr32(fuc, 0x10f800, 0x00001804);
+       // 0x00030020 // 0x00000000 // 0x00000000
+       // 0x00020034 // 0x0000000b
+               ram_wr32(fuc, 0x13d8f4, 0x00000000);
+               ram_wr32(fuc, 0x100b0c, 0x00080028);
+               ram_wr32(fuc, 0x611200, 0x00003330);
+               ram_nsec(fuc, 100000);
+               ram_wr32(fuc, 0x10f9b0, 0x05313f41);
+               ram_wr32(fuc, 0x10f9b4, 0x00002f50);
+
+               gf100_ram_train(fuc, 0x010c1001);
+       }
+
+       ram_mask(fuc, 0x10f200, 0x00000800, 0x00000800);
+// 0x00020016 // 0x00000000
+
+       if (mode == 0)
+               ram_mask(fuc, 0x132000, 0x00000001, 0x00000000);
+
+       return 0;
+}
+
+static int
+gf100_ram_prog(struct nvkm_fb *pfb)
+{
+       struct nvkm_device *device = nv_device(pfb);
+       struct gf100_ram *ram = (void *)pfb->ram;
+       struct gf100_ramfuc *fuc = &ram->fuc;
+       ram_exec(fuc, nvkm_boolopt(device->cfgopt, "NvMemExec", true));
+       return 0;
+}
+
+static void
+gf100_ram_tidy(struct nvkm_fb *pfb)
+{
+       struct gf100_ram *ram = (void *)pfb->ram;
+       struct gf100_ramfuc *fuc = &ram->fuc;
+       ram_exec(fuc, false);
+}
+
+extern const u8 gf100_pte_storage_type_map[256];
+
+void
+gf100_ram_put(struct nvkm_fb *pfb, struct nvkm_mem **pmem)
+{
+       struct nvkm_ltc *ltc = nvkm_ltc(pfb);
+       struct nvkm_mem *mem = *pmem;
+
+       *pmem = NULL;
+       if (unlikely(mem == NULL))
+               return;
+
+       mutex_lock(&pfb->base.mutex);
+       if (mem->tag)
+               ltc->tags_free(ltc, &mem->tag);
+       __nv50_ram_put(pfb, mem);
+       mutex_unlock(&pfb->base.mutex);
+
+       kfree(mem);
+}
+
+int
+gf100_ram_get(struct nvkm_fb *pfb, u64 size, u32 align, u32 ncmin,
+             u32 memtype, struct nvkm_mem **pmem)
+{
+       struct nvkm_mm *mm = &pfb->vram;
+       struct nvkm_mm_node *r;
+       struct nvkm_mem *mem;
+       int type = (memtype & 0x0ff);
+       int back = (memtype & 0x800);
+       const bool comp = gf100_pte_storage_type_map[type] != type;
+       int ret;
+
+       size  >>= 12;
+       align >>= 12;
+       ncmin >>= 12;
+       if (!ncmin)
+               ncmin = size;
+
+       mem = kzalloc(sizeof(*mem), GFP_KERNEL);
+       if (!mem)
+               return -ENOMEM;
+
+       INIT_LIST_HEAD(&mem->regions);
+       mem->size = size;
+
+       mutex_lock(&pfb->base.mutex);
+       if (comp) {
+               struct nvkm_ltc *ltc = nvkm_ltc(pfb);
+
+               /* compression only works with lpages */
+               if (align == (1 << (17 - 12))) {
+                       int n = size >> 5;
+                       ltc->tags_alloc(ltc, n, &mem->tag);
+               }
+
+               if (unlikely(!mem->tag))
+                       type = gf100_pte_storage_type_map[type];
+       }
+       mem->memtype = type;
+
+       do {
+               if (back)
+                       ret = nvkm_mm_tail(mm, 0, 1, size, ncmin, align, &r);
+               else
+                       ret = nvkm_mm_head(mm, 0, 1, size, ncmin, align, &r);
+               if (ret) {
+                       mutex_unlock(&pfb->base.mutex);
+                       pfb->ram->put(pfb, &mem);
+                       return ret;
+               }
+
+               list_add_tail(&r->rl_entry, &mem->regions);
+               size -= r->length;
+       } while (size);
+       mutex_unlock(&pfb->base.mutex);
+
+       r = list_first_entry(&mem->regions, struct nvkm_mm_node, rl_entry);
+       mem->offset = (u64)r->offset << 12;
+       *pmem = mem;
+       return 0;
+}
+
+int
+gf100_ram_create_(struct nvkm_object *parent, struct nvkm_object *engine,
+                 struct nvkm_oclass *oclass, u32 maskaddr, int size,
+                 void **pobject)
+{
+       struct nvkm_fb *pfb = nvkm_fb(parent);
+       struct nvkm_bios *bios = nvkm_bios(pfb);
+       struct nvkm_ram *ram;
+       const u32 rsvd_head = ( 256 * 1024) >> 12; /* vga memory */
+       const u32 rsvd_tail = (1024 * 1024) >> 12; /* vbios etc */
+       u32 parts = nv_rd32(pfb, 0x022438);
+       u32 pmask = nv_rd32(pfb, maskaddr);
+       u32 bsize = nv_rd32(pfb, 0x10f20c);
+       u32 offset, length;
+       bool uniform = true;
+       int ret, part;
+
+       ret = nvkm_ram_create_(parent, engine, oclass, size, pobject);
+       ram = *pobject;
+       if (ret)
+               return ret;
+
+       nv_debug(pfb, "0x100800: 0x%08x\n", nv_rd32(pfb, 0x100800));
+       nv_debug(pfb, "parts 0x%08x mask 0x%08x\n", parts, pmask);
+
+       ram->type = nvkm_fb_bios_memtype(bios);
+       ram->ranks = (nv_rd32(pfb, 0x10f200) & 0x00000004) ? 2 : 1;
+
+       /* read amount of vram attached to each memory controller */
+       for (part = 0; part < parts; part++) {
+               if (!(pmask & (1 << part))) {
+                       u32 psize = nv_rd32(pfb, 0x11020c + (part * 0x1000));
+                       if (psize != bsize) {
+                               if (psize < bsize)
+                                       bsize = psize;
+                               uniform = false;
+                       }
+
+                       nv_debug(pfb, "%d: mem_amount 0x%08x\n", part, psize);
+                       ram->size += (u64)psize << 20;
+               }
+       }
+
+       /* if all controllers have the same amount attached, there's no holes */
+       if (uniform) {
+               offset = rsvd_head;
+               length = (ram->size >> 12) - rsvd_head - rsvd_tail;
+               ret = nvkm_mm_init(&pfb->vram, offset, length, 1);
+       } else {
+               /* otherwise, address lowest common amount from 0GiB */
+               ret = nvkm_mm_init(&pfb->vram, rsvd_head,
+                                  (bsize << 8) * parts - rsvd_head, 1);
+               if (ret)
+                       return ret;
+
+               /* and the rest starting from (8GiB + common_size) */
+               offset = (0x0200000000ULL >> 12) + (bsize << 8);
+               length = (ram->size >> 12) - ((bsize * parts) << 8) - rsvd_tail;
+
+               ret = nvkm_mm_init(&pfb->vram, offset, length, 1);
+               if (ret)
+                       nvkm_mm_fini(&pfb->vram);
+       }
+
+       if (ret)
+               return ret;
+
+       ram->get = gf100_ram_get;
+       ram->put = gf100_ram_put;
+       return 0;
+}
+
+static int
+gf100_ram_init(struct nvkm_object *object)
+{
+       struct nvkm_fb *pfb = (void *)object->parent;
+       struct gf100_ram *ram = (void *)object;
+       int ret, i;
+
+       ret = nvkm_ram_init(&ram->base);
+       if (ret)
+               return ret;
+
+       /* prepare for ddr link training, and load training patterns */
+       switch (ram->base.type) {
+       case NV_MEM_TYPE_GDDR5: {
+               static const u8  train0[] = {
+                       0x00, 0xff, 0x55, 0xaa, 0x33, 0xcc,
+                       0x00, 0xff, 0xff, 0x00, 0xff, 0x00,
+               };
+               static const u32 train1[] = {
+                       0x00000000, 0xffffffff,
+                       0x55555555, 0xaaaaaaaa,
+                       0x33333333, 0xcccccccc,
+                       0xf0f0f0f0, 0x0f0f0f0f,
+                       0x00ff00ff, 0xff00ff00,
+                       0x0000ffff, 0xffff0000,
+               };
+
+               for (i = 0; i < 0x30; i++) {
+                       nv_wr32(pfb, 0x10f968, 0x00000000 | (i << 8));
+                       nv_wr32(pfb, 0x10f96c, 0x00000000 | (i << 8));
+                       nv_wr32(pfb, 0x10f920, 0x00000100 | train0[i % 12]);
+                       nv_wr32(pfb, 0x10f924, 0x00000100 | train0[i % 12]);
+                       nv_wr32(pfb, 0x10f918,              train1[i % 12]);
+                       nv_wr32(pfb, 0x10f91c,              train1[i % 12]);
+                       nv_wr32(pfb, 0x10f920, 0x00000000 | train0[i % 12]);
+                       nv_wr32(pfb, 0x10f924, 0x00000000 | train0[i % 12]);
+                       nv_wr32(pfb, 0x10f918,              train1[i % 12]);
+                       nv_wr32(pfb, 0x10f91c,              train1[i % 12]);
+               }
+       }       break;
+       default:
+               break;
+       }
+
+       return 0;
+}
+
+static int
+gf100_ram_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+              struct nvkm_oclass *oclass, void *data, u32 size,
+              struct nvkm_object **pobject)
+{
+       struct nvkm_bios *bios = nvkm_bios(parent);
+       struct gf100_ram *ram;
+       int ret;
+
+       ret = gf100_ram_create(parent, engine, oclass, 0x022554, &ram);
+       *pobject = nv_object(ram);
+       if (ret)
+               return ret;
+
+       ret = nvbios_pll_parse(bios, 0x0c, &ram->refpll);
+       if (ret) {
+               nv_error(ram, "mclk refpll data not found\n");
+               return ret;
+       }
+
+       ret = nvbios_pll_parse(bios, 0x04, &ram->mempll);
+       if (ret) {
+               nv_error(ram, "mclk pll data not found\n");
+               return ret;
+       }
+
+       switch (ram->base.type) {
+       case NV_MEM_TYPE_GDDR5:
+               ram->base.calc = gf100_ram_calc;
+               ram->base.prog = gf100_ram_prog;
+               ram->base.tidy = gf100_ram_tidy;
+               break;
+       default:
+               nv_warn(ram, "reclocking of this ram type unsupported\n");
+               return 0;
+       }
+
+       ram->fuc.r_0x10fe20 = ramfuc_reg(0x10fe20);
+       ram->fuc.r_0x10fe24 = ramfuc_reg(0x10fe24);
+       ram->fuc.r_0x137320 = ramfuc_reg(0x137320);
+       ram->fuc.r_0x137330 = ramfuc_reg(0x137330);
+
+       ram->fuc.r_0x132000 = ramfuc_reg(0x132000);
+       ram->fuc.r_0x132004 = ramfuc_reg(0x132004);
+       ram->fuc.r_0x132100 = ramfuc_reg(0x132100);
+
+       ram->fuc.r_0x137390 = ramfuc_reg(0x137390);
+
+       ram->fuc.r_0x10f290 = ramfuc_reg(0x10f290);
+       ram->fuc.r_0x10f294 = ramfuc_reg(0x10f294);
+       ram->fuc.r_0x10f298 = ramfuc_reg(0x10f298);
+       ram->fuc.r_0x10f29c = ramfuc_reg(0x10f29c);
+       ram->fuc.r_0x10f2a0 = ramfuc_reg(0x10f2a0);
+
+       ram->fuc.r_0x10f300 = ramfuc_reg(0x10f300);
+       ram->fuc.r_0x10f338 = ramfuc_reg(0x10f338);
+       ram->fuc.r_0x10f340 = ramfuc_reg(0x10f340);
+       ram->fuc.r_0x10f344 = ramfuc_reg(0x10f344);
+       ram->fuc.r_0x10f348 = ramfuc_reg(0x10f348);
+
+       ram->fuc.r_0x10f910 = ramfuc_reg(0x10f910);
+       ram->fuc.r_0x10f914 = ramfuc_reg(0x10f914);
+
+       ram->fuc.r_0x100b0c = ramfuc_reg(0x100b0c);
+       ram->fuc.r_0x10f050 = ramfuc_reg(0x10f050);
+       ram->fuc.r_0x10f090 = ramfuc_reg(0x10f090);
+       ram->fuc.r_0x10f200 = ramfuc_reg(0x10f200);
+       ram->fuc.r_0x10f210 = ramfuc_reg(0x10f210);
+       ram->fuc.r_0x10f310 = ramfuc_reg(0x10f310);
+       ram->fuc.r_0x10f314 = ramfuc_reg(0x10f314);
+       ram->fuc.r_0x10f610 = ramfuc_reg(0x10f610);
+       ram->fuc.r_0x10f614 = ramfuc_reg(0x10f614);
+       ram->fuc.r_0x10f800 = ramfuc_reg(0x10f800);
+       ram->fuc.r_0x10f808 = ramfuc_reg(0x10f808);
+       ram->fuc.r_0x10f824 = ramfuc_reg(0x10f824);
+       ram->fuc.r_0x10f830 = ramfuc_reg(0x10f830);
+       ram->fuc.r_0x10f988 = ramfuc_reg(0x10f988);
+       ram->fuc.r_0x10f98c = ramfuc_reg(0x10f98c);
+       ram->fuc.r_0x10f990 = ramfuc_reg(0x10f990);
+       ram->fuc.r_0x10f998 = ramfuc_reg(0x10f998);
+       ram->fuc.r_0x10f9b0 = ramfuc_reg(0x10f9b0);
+       ram->fuc.r_0x10f9b4 = ramfuc_reg(0x10f9b4);
+       ram->fuc.r_0x10fb04 = ramfuc_reg(0x10fb04);
+       ram->fuc.r_0x10fb08 = ramfuc_reg(0x10fb08);
+       ram->fuc.r_0x137310 = ramfuc_reg(0x137300);
+       ram->fuc.r_0x137310 = ramfuc_reg(0x137310);
+       ram->fuc.r_0x137360 = ramfuc_reg(0x137360);
+       ram->fuc.r_0x1373ec = ramfuc_reg(0x1373ec);
+       ram->fuc.r_0x1373f0 = ramfuc_reg(0x1373f0);
+       ram->fuc.r_0x1373f8 = ramfuc_reg(0x1373f8);
+
+       ram->fuc.r_0x61c140 = ramfuc_reg(0x61c140);
+       ram->fuc.r_0x611200 = ramfuc_reg(0x611200);
+
+       ram->fuc.r_0x13d8f4 = ramfuc_reg(0x13d8f4);
+       return 0;
+}
+
+struct nvkm_oclass
+gf100_ram_oclass = {
+       .handle = 0,
+       .ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = gf100_ram_ctor,
+               .dtor = _nvkm_ram_dtor,
+               .init = gf100_ram_init,
+               .fini = _nvkm_ram_fini,
+       }
+};
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/fb/ramgk104.c b/drivers/gpu/drm/nouveau/nvkm/subdev/fb/ramgk104.c
new file mode 100644 (file)
index 0000000..1ef15c3
--- /dev/null
@@ -0,0 +1,1639 @@
+/*
+ * Copyright 2013 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 "ramfuc.h"
+#include "gf100.h"
+
+#include <core/device.h>
+#include <core/option.h>
+#include <subdev/bios.h>
+#include <subdev/bios/init.h>
+#include <subdev/bios/M0205.h>
+#include <subdev/bios/M0209.h>
+#include <subdev/bios/pll.h>
+#include <subdev/bios/rammap.h>
+#include <subdev/bios/timing.h>
+#include <subdev/clk.h>
+#include <subdev/clk/pll.h>
+#include <subdev/gpio.h>
+
+struct gk104_ramfuc {
+       struct ramfuc base;
+
+       struct nvbios_pll refpll;
+       struct nvbios_pll mempll;
+
+       struct ramfuc_reg r_gpioMV;
+       u32 r_funcMV[2];
+       struct ramfuc_reg r_gpio2E;
+       u32 r_func2E[2];
+       struct ramfuc_reg r_gpiotrig;
+
+       struct ramfuc_reg r_0x132020;
+       struct ramfuc_reg r_0x132028;
+       struct ramfuc_reg r_0x132024;
+       struct ramfuc_reg r_0x132030;
+       struct ramfuc_reg r_0x132034;
+       struct ramfuc_reg r_0x132000;
+       struct ramfuc_reg r_0x132004;
+       struct ramfuc_reg r_0x132040;
+
+       struct ramfuc_reg r_0x10f248;
+       struct ramfuc_reg r_0x10f290;
+       struct ramfuc_reg r_0x10f294;
+       struct ramfuc_reg r_0x10f298;
+       struct ramfuc_reg r_0x10f29c;
+       struct ramfuc_reg r_0x10f2a0;
+       struct ramfuc_reg r_0x10f2a4;
+       struct ramfuc_reg r_0x10f2a8;
+       struct ramfuc_reg r_0x10f2ac;
+       struct ramfuc_reg r_0x10f2cc;
+       struct ramfuc_reg r_0x10f2e8;
+       struct ramfuc_reg r_0x10f250;
+       struct ramfuc_reg r_0x10f24c;
+       struct ramfuc_reg r_0x10fec4;
+       struct ramfuc_reg r_0x10fec8;
+       struct ramfuc_reg r_0x10f604;
+       struct ramfuc_reg r_0x10f614;
+       struct ramfuc_reg r_0x10f610;
+       struct ramfuc_reg r_0x100770;
+       struct ramfuc_reg r_0x100778;
+       struct ramfuc_reg r_0x10f224;
+
+       struct ramfuc_reg r_0x10f870;
+       struct ramfuc_reg r_0x10f698;
+       struct ramfuc_reg r_0x10f694;
+       struct ramfuc_reg r_0x10f6b8;
+       struct ramfuc_reg r_0x10f808;
+       struct ramfuc_reg r_0x10f670;
+       struct ramfuc_reg r_0x10f60c;
+       struct ramfuc_reg r_0x10f830;
+       struct ramfuc_reg r_0x1373ec;
+       struct ramfuc_reg r_0x10f800;
+       struct ramfuc_reg r_0x10f82c;
+
+       struct ramfuc_reg r_0x10f978;
+       struct ramfuc_reg r_0x10f910;
+       struct ramfuc_reg r_0x10f914;
+
+       struct ramfuc_reg r_mr[16]; /* MR0 - MR8, MR15 */
+
+       struct ramfuc_reg r_0x62c000;
+
+       struct ramfuc_reg r_0x10f200;
+
+       struct ramfuc_reg r_0x10f210;
+       struct ramfuc_reg r_0x10f310;
+       struct ramfuc_reg r_0x10f314;
+       struct ramfuc_reg r_0x10f318;
+       struct ramfuc_reg r_0x10f090;
+       struct ramfuc_reg r_0x10f69c;
+       struct ramfuc_reg r_0x10f824;
+       struct ramfuc_reg r_0x1373f0;
+       struct ramfuc_reg r_0x1373f4;
+       struct ramfuc_reg r_0x137320;
+       struct ramfuc_reg r_0x10f65c;
+       struct ramfuc_reg r_0x10f6bc;
+       struct ramfuc_reg r_0x100710;
+       struct ramfuc_reg r_0x100750;
+};
+
+struct gk104_ram {
+       struct nvkm_ram base;
+       struct gk104_ramfuc fuc;
+
+       struct list_head cfg;
+       u32 parts;
+       u32 pmask;
+       u32 pnuts;
+
+       struct nvbios_ramcfg diff;
+       int from;
+       int mode;
+       int N1, fN1, M1, P1;
+       int N2, M2, P2;
+};
+
+/*******************************************************************************
+ * GDDR5
+ ******************************************************************************/
+static void
+gk104_ram_train(struct gk104_ramfuc *fuc, u32 mask, u32 data)
+{
+       struct gk104_ram *ram = container_of(fuc, typeof(*ram), fuc);
+       u32 addr = 0x110974, i;
+
+       ram_mask(fuc, 0x10f910, mask, data);
+       ram_mask(fuc, 0x10f914, mask, data);
+
+       for (i = 0; (data & 0x80000000) && i < ram->parts; addr += 0x1000, i++) {
+               if (ram->pmask & (1 << i))
+                       continue;
+               ram_wait(fuc, addr, 0x0000000f, 0x00000000, 500000);
+       }
+}
+
+static void
+r1373f4_init(struct gk104_ramfuc *fuc)
+{
+       struct gk104_ram *ram = container_of(fuc, typeof(*ram), fuc);
+       const u32 mcoef = ((--ram->P2 << 28) | (ram->N2 << 8) | ram->M2);
+       const u32 rcoef = ((  ram->P1 << 16) | (ram->N1 << 8) | ram->M1);
+       const u32 runk0 = ram->fN1 << 16;
+       const u32 runk1 = ram->fN1;
+
+       if (ram->from == 2) {
+               ram_mask(fuc, 0x1373f4, 0x00000000, 0x00001100);
+               ram_mask(fuc, 0x1373f4, 0x00000000, 0x00000010);
+       } else {
+               ram_mask(fuc, 0x1373f4, 0x00000000, 0x00010010);
+       }
+
+       ram_mask(fuc, 0x1373f4, 0x00000003, 0x00000000);
+       ram_mask(fuc, 0x1373f4, 0x00000010, 0x00000000);
+
+       /* (re)program refpll, if required */
+       if ((ram_rd32(fuc, 0x132024) & 0xffffffff) != rcoef ||
+           (ram_rd32(fuc, 0x132034) & 0x0000ffff) != runk1) {
+               ram_mask(fuc, 0x132000, 0x00000001, 0x00000000);
+               ram_mask(fuc, 0x132020, 0x00000001, 0x00000000);
+               ram_wr32(fuc, 0x137320, 0x00000000);
+               ram_mask(fuc, 0x132030, 0xffff0000, runk0);
+               ram_mask(fuc, 0x132034, 0x0000ffff, runk1);
+               ram_wr32(fuc, 0x132024, rcoef);
+               ram_mask(fuc, 0x132028, 0x00080000, 0x00080000);
+               ram_mask(fuc, 0x132020, 0x00000001, 0x00000001);
+               ram_wait(fuc, 0x137390, 0x00020000, 0x00020000, 64000);
+               ram_mask(fuc, 0x132028, 0x00080000, 0x00000000);
+       }
+
+       /* (re)program mempll, if required */
+       if (ram->mode == 2) {
+               ram_mask(fuc, 0x1373f4, 0x00010000, 0x00000000);
+               ram_mask(fuc, 0x132000, 0x80000000, 0x80000000);
+               ram_mask(fuc, 0x132000, 0x00000001, 0x00000000);
+               ram_mask(fuc, 0x132004, 0x103fffff, mcoef);
+               ram_mask(fuc, 0x132000, 0x00000001, 0x00000001);
+               ram_wait(fuc, 0x137390, 0x00000002, 0x00000002, 64000);
+               ram_mask(fuc, 0x1373f4, 0x00000000, 0x00001100);
+       } else {
+               ram_mask(fuc, 0x1373f4, 0x00000000, 0x00010100);
+       }
+
+       ram_mask(fuc, 0x1373f4, 0x00000000, 0x00000010);
+}
+
+static void
+r1373f4_fini(struct gk104_ramfuc *fuc)
+{
+       struct gk104_ram *ram = container_of(fuc, typeof(*ram), fuc);
+       struct nvkm_ram_data *next = ram->base.next;
+       u8 v0 = next->bios.ramcfg_11_03_c0;
+       u8 v1 = next->bios.ramcfg_11_03_30;
+       u32 tmp;
+
+       tmp = ram_rd32(fuc, 0x1373ec) & ~0x00030000;
+       ram_wr32(fuc, 0x1373ec, tmp | (v1 << 16));
+       ram_mask(fuc, 0x1373f0, (~ram->mode & 3), 0x00000000);
+       if (ram->mode == 2) {
+               ram_mask(fuc, 0x1373f4, 0x00000003, 0x000000002);
+               ram_mask(fuc, 0x1373f4, 0x00001100, 0x000000000);
+       } else {
+               ram_mask(fuc, 0x1373f4, 0x00000003, 0x000000001);
+               ram_mask(fuc, 0x1373f4, 0x00010000, 0x000000000);
+       }
+       ram_mask(fuc, 0x10f800, 0x00000030, (v0 ^ v1) << 4);
+}
+
+static void
+gk104_ram_nuts(struct gk104_ram *ram, struct ramfuc_reg *reg,
+              u32 _mask, u32 _data, u32 _copy)
+{
+       struct gk104_fb_priv *priv = (void *)nvkm_fb(ram);
+       struct ramfuc *fuc = &ram->fuc.base;
+       u32 addr = 0x110000 + (reg->addr & 0xfff);
+       u32 mask = _mask | _copy;
+       u32 data = (_data & _mask) | (reg->data & _copy);
+       u32 i;
+
+       for (i = 0; i < 16; i++, addr += 0x1000) {
+               if (ram->pnuts & (1 << i)) {
+                       u32 prev = nv_rd32(priv, addr);
+                       u32 next = (prev & ~mask) | data;
+                       nvkm_memx_wr32(fuc->memx, addr, next);
+               }
+       }
+}
+#define ram_nuts(s,r,m,d,c)                                                    \
+       gk104_ram_nuts((s), &(s)->fuc.r_##r, (m), (d), (c))
+
+static int
+gk104_ram_calc_gddr5(struct nvkm_fb *pfb, u32 freq)
+{
+       struct gk104_ram *ram = (void *)pfb->ram;
+       struct gk104_ramfuc *fuc = &ram->fuc;
+       struct nvkm_ram_data *next = ram->base.next;
+       int vc = !next->bios.ramcfg_11_02_08;
+       int mv = !next->bios.ramcfg_11_02_04;
+       u32 mask, data;
+
+       ram_mask(fuc, 0x10f808, 0x40000000, 0x40000000);
+       ram_block(fuc);
+       ram_wr32(fuc, 0x62c000, 0x0f0f0000);
+
+       /* MR1: turn termination on early, for some reason.. */
+       if ((ram->base.mr[1] & 0x03c) != 0x030) {
+               ram_mask(fuc, mr[1], 0x03c, ram->base.mr[1] & 0x03c);
+               ram_nuts(ram, mr[1], 0x03c, ram->base.mr1_nuts & 0x03c, 0x000);
+       }
+
+       if (vc == 1 && ram_have(fuc, gpio2E)) {
+               u32 temp  = ram_mask(fuc, gpio2E, 0x3000, fuc->r_func2E[1]);
+               if (temp != ram_rd32(fuc, gpio2E)) {
+                       ram_wr32(fuc, gpiotrig, 1);
+                       ram_nsec(fuc, 20000);
+               }
+       }
+
+       ram_mask(fuc, 0x10f200, 0x00000800, 0x00000000);
+
+       gk104_ram_train(fuc, 0x01020000, 0x000c0000);
+
+       ram_wr32(fuc, 0x10f210, 0x00000000); /* REFRESH_AUTO = 0 */
+       ram_nsec(fuc, 1000);
+       ram_wr32(fuc, 0x10f310, 0x00000001); /* REFRESH */
+       ram_nsec(fuc, 1000);
+
+       ram_mask(fuc, 0x10f200, 0x80000000, 0x80000000);
+       ram_wr32(fuc, 0x10f314, 0x00000001); /* PRECHARGE */
+       ram_mask(fuc, 0x10f200, 0x80000000, 0x00000000);
+       ram_wr32(fuc, 0x10f090, 0x00000061);
+       ram_wr32(fuc, 0x10f090, 0xc000007f);
+       ram_nsec(fuc, 1000);
+
+       ram_wr32(fuc, 0x10f698, 0x00000000);
+       ram_wr32(fuc, 0x10f69c, 0x00000000);
+
+       /*XXX: there does appear to be some kind of condition here, simply
+        *     modifying these bits in the vbios from the default pl0
+        *     entries shows no change.  however, the data does appear to
+        *     be correct and may be required for the transition back
+        */
+       mask = 0x800f07e0;
+       data = 0x00030000;
+       if (ram_rd32(fuc, 0x10f978) & 0x00800000)
+               data |= 0x00040000;
+
+       if (1) {
+               data |= 0x800807e0;
+               switch (next->bios.ramcfg_11_03_c0) {
+               case 3: data &= ~0x00000040; break;
+               case 2: data &= ~0x00000100; break;
+               case 1: data &= ~0x80000000; break;
+               case 0: data &= ~0x00000400; break;
+               }
+
+               switch (next->bios.ramcfg_11_03_30) {
+               case 3: data &= ~0x00000020; break;
+               case 2: data &= ~0x00000080; break;
+               case 1: data &= ~0x00080000; break;
+               case 0: data &= ~0x00000200; break;
+               }
+       }
+
+       if (next->bios.ramcfg_11_02_80)
+               mask |= 0x03000000;
+       if (next->bios.ramcfg_11_02_40)
+               mask |= 0x00002000;
+       if (next->bios.ramcfg_11_07_10)
+               mask |= 0x00004000;
+       if (next->bios.ramcfg_11_07_08)
+               mask |= 0x00000003;
+       else {
+               mask |= 0x34000000;
+               if (ram_rd32(fuc, 0x10f978) & 0x00800000)
+                       mask |= 0x40000000;
+       }
+       ram_mask(fuc, 0x10f824, mask, data);
+
+       ram_mask(fuc, 0x132040, 0x00010000, 0x00000000);
+
+       if (ram->from == 2 && ram->mode != 2) {
+               ram_mask(fuc, 0x10f808, 0x00080000, 0x00000000);
+               ram_mask(fuc, 0x10f200, 0x18008000, 0x00008000);
+               ram_mask(fuc, 0x10f800, 0x00000000, 0x00000004);
+               ram_mask(fuc, 0x10f830, 0x00008000, 0x01040010);
+               ram_mask(fuc, 0x10f830, 0x01000000, 0x00000000);
+               r1373f4_init(fuc);
+               ram_mask(fuc, 0x1373f0, 0x00000002, 0x00000001);
+               r1373f4_fini(fuc);
+               ram_mask(fuc, 0x10f830, 0x00c00000, 0x00240001);
+       } else
+       if (ram->from != 2 && ram->mode != 2) {
+               r1373f4_init(fuc);
+               r1373f4_fini(fuc);
+       }
+
+       if (ram_have(fuc, gpioMV)) {
+               u32 temp  = ram_mask(fuc, gpioMV, 0x3000, fuc->r_funcMV[mv]);
+               if (temp != ram_rd32(fuc, gpioMV)) {
+                       ram_wr32(fuc, gpiotrig, 1);
+                       ram_nsec(fuc, 64000);
+               }
+       }
+
+       if (next->bios.ramcfg_11_02_40 ||
+           next->bios.ramcfg_11_07_10) {
+               ram_mask(fuc, 0x132040, 0x00010000, 0x00010000);
+               ram_nsec(fuc, 20000);
+       }
+
+       if (ram->from != 2 && ram->mode == 2) {
+               if (0 /*XXX: Titan */)
+                       ram_mask(fuc, 0x10f200, 0x18000000, 0x18000000);
+               ram_mask(fuc, 0x10f800, 0x00000004, 0x00000000);
+               ram_mask(fuc, 0x1373f0, 0x00000000, 0x00000002);
+               ram_mask(fuc, 0x10f830, 0x00800001, 0x00408010);
+               r1373f4_init(fuc);
+               r1373f4_fini(fuc);
+               ram_mask(fuc, 0x10f808, 0x00000000, 0x00080000);
+               ram_mask(fuc, 0x10f200, 0x00808000, 0x00800000);
+       } else
+       if (ram->from == 2 && ram->mode == 2) {
+               ram_mask(fuc, 0x10f800, 0x00000004, 0x00000000);
+               r1373f4_init(fuc);
+               r1373f4_fini(fuc);
+       }
+
+       if (ram->mode != 2) /*XXX*/ {
+               if (next->bios.ramcfg_11_07_40)
+                       ram_mask(fuc, 0x10f670, 0x80000000, 0x80000000);
+       }
+
+       ram_wr32(fuc, 0x10f65c, 0x00000011 * next->bios.rammap_11_11_0c);
+       ram_wr32(fuc, 0x10f6b8, 0x01010101 * next->bios.ramcfg_11_09);
+       ram_wr32(fuc, 0x10f6bc, 0x01010101 * next->bios.ramcfg_11_09);
+
+       if (!next->bios.ramcfg_11_07_08 && !next->bios.ramcfg_11_07_04) {
+               ram_wr32(fuc, 0x10f698, 0x01010101 * next->bios.ramcfg_11_04);
+               ram_wr32(fuc, 0x10f69c, 0x01010101 * next->bios.ramcfg_11_04);
+       } else
+       if (!next->bios.ramcfg_11_07_08) {
+               ram_wr32(fuc, 0x10f698, 0x00000000);
+               ram_wr32(fuc, 0x10f69c, 0x00000000);
+       }
+
+       if (ram->mode != 2) {
+               u32 data = 0x01000100 * next->bios.ramcfg_11_04;
+               ram_nuke(fuc, 0x10f694);
+               ram_mask(fuc, 0x10f694, 0xff00ff00, data);
+       }
+
+       if (ram->mode == 2 && next->bios.ramcfg_11_08_10)
+               data = 0x00000080;
+       else
+               data = 0x00000000;
+       ram_mask(fuc, 0x10f60c, 0x00000080, data);
+
+       mask = 0x00070000;
+       data = 0x00000000;
+       if (!next->bios.ramcfg_11_02_80)
+               data |= 0x03000000;
+       if (!next->bios.ramcfg_11_02_40)
+               data |= 0x00002000;
+       if (!next->bios.ramcfg_11_07_10)
+               data |= 0x00004000;
+       if (!next->bios.ramcfg_11_07_08)
+               data |= 0x00000003;
+       else
+               data |= 0x74000000;
+       ram_mask(fuc, 0x10f824, mask, data);
+
+       if (next->bios.ramcfg_11_01_08)
+               data = 0x00000000;
+       else
+               data = 0x00001000;
+       ram_mask(fuc, 0x10f200, 0x00001000, data);
+
+       if (ram_rd32(fuc, 0x10f670) & 0x80000000) {
+               ram_nsec(fuc, 10000);
+               ram_mask(fuc, 0x10f670, 0x80000000, 0x00000000);
+       }
+
+       if (next->bios.ramcfg_11_08_01)
+               data = 0x00100000;
+       else
+               data = 0x00000000;
+       ram_mask(fuc, 0x10f82c, 0x00100000, data);
+
+       data = 0x00000000;
+       if (next->bios.ramcfg_11_08_08)
+               data |= 0x00002000;
+       if (next->bios.ramcfg_11_08_04)
+               data |= 0x00001000;
+       if (next->bios.ramcfg_11_08_02)
+               data |= 0x00004000;
+       ram_mask(fuc, 0x10f830, 0x00007000, data);
+
+       /* PFB timing */
+       ram_mask(fuc, 0x10f248, 0xffffffff, next->bios.timing[10]);
+       ram_mask(fuc, 0x10f290, 0xffffffff, next->bios.timing[0]);
+       ram_mask(fuc, 0x10f294, 0xffffffff, next->bios.timing[1]);
+       ram_mask(fuc, 0x10f298, 0xffffffff, next->bios.timing[2]);
+       ram_mask(fuc, 0x10f29c, 0xffffffff, next->bios.timing[3]);
+       ram_mask(fuc, 0x10f2a0, 0xffffffff, next->bios.timing[4]);
+       ram_mask(fuc, 0x10f2a4, 0xffffffff, next->bios.timing[5]);
+       ram_mask(fuc, 0x10f2a8, 0xffffffff, next->bios.timing[6]);
+       ram_mask(fuc, 0x10f2ac, 0xffffffff, next->bios.timing[7]);
+       ram_mask(fuc, 0x10f2cc, 0xffffffff, next->bios.timing[8]);
+       ram_mask(fuc, 0x10f2e8, 0xffffffff, next->bios.timing[9]);
+
+       data = mask = 0x00000000;
+       if (ram->diff.ramcfg_11_08_20) {
+               if (next->bios.ramcfg_11_08_20)
+                       data |= 0x01000000;
+               mask |= 0x01000000;
+       }
+       ram_mask(fuc, 0x10f200, mask, data);
+
+       data = mask = 0x00000000;
+       if (ram->diff.ramcfg_11_02_03) {
+               data |= next->bios.ramcfg_11_02_03 << 8;
+               mask |= 0x00000300;
+       }
+       if (ram->diff.ramcfg_11_01_10) {
+               if (next->bios.ramcfg_11_01_10)
+                       data |= 0x70000000;
+               mask |= 0x70000000;
+       }
+       ram_mask(fuc, 0x10f604, mask, data);
+
+       data = mask = 0x00000000;
+       if (ram->diff.timing_20_30_07) {
+               data |= next->bios.timing_20_30_07 << 28;
+               mask |= 0x70000000;
+       }
+       if (ram->diff.ramcfg_11_01_01) {
+               if (next->bios.ramcfg_11_01_01)
+                       data |= 0x00000100;
+               mask |= 0x00000100;
+       }
+       ram_mask(fuc, 0x10f614, mask, data);
+
+       data = mask = 0x00000000;
+       if (ram->diff.timing_20_30_07) {
+               data |= next->bios.timing_20_30_07 << 28;
+               mask |= 0x70000000;
+       }
+       if (ram->diff.ramcfg_11_01_02) {
+               if (next->bios.ramcfg_11_01_02)
+                       data |= 0x00000100;
+               mask |= 0x00000100;
+       }
+       ram_mask(fuc, 0x10f610, mask, data);
+
+       mask = 0x33f00000;
+       data = 0x00000000;
+       if (!next->bios.ramcfg_11_01_04)
+               data |= 0x20200000;
+       if (!next->bios.ramcfg_11_07_80)
+               data |= 0x12800000;
+       /*XXX: see note above about there probably being some condition
+        *     for the 10f824 stuff that uses ramcfg 3...
+        */
+       if (next->bios.ramcfg_11_03_f0) {
+               if (next->bios.rammap_11_08_0c) {
+                       if (!next->bios.ramcfg_11_07_80)
+                               mask |= 0x00000020;
+                       else
+                               data |= 0x00000020;
+                       mask |= 0x00000004;
+               }
+       } else {
+               mask |= 0x40000020;
+               data |= 0x00000004;
+       }
+
+       ram_mask(fuc, 0x10f808, mask, data);
+
+       ram_wr32(fuc, 0x10f870, 0x11111111 * next->bios.ramcfg_11_03_0f);
+
+       data = mask = 0x00000000;
+       if (ram->diff.ramcfg_11_02_03) {
+               data |= next->bios.ramcfg_11_02_03;
+               mask |= 0x00000003;
+       }
+       if (ram->diff.ramcfg_11_01_10) {
+               if (next->bios.ramcfg_11_01_10)
+                       data |= 0x00000004;
+               mask |= 0x00000004;
+       }
+
+       if ((ram_mask(fuc, 0x100770, mask, data) & mask & 4) != (data & 4)) {
+               ram_mask(fuc, 0x100750, 0x00000008, 0x00000008);
+               ram_wr32(fuc, 0x100710, 0x00000000);
+               ram_wait(fuc, 0x100710, 0x80000000, 0x80000000, 200000);
+       }
+
+       data = next->bios.timing_20_30_07 << 8;
+       if (next->bios.ramcfg_11_01_01)
+               data |= 0x80000000;
+       ram_mask(fuc, 0x100778, 0x00000700, data);
+
+       ram_mask(fuc, 0x10f250, 0x000003f0, next->bios.timing_20_2c_003f << 4);
+       data = (next->bios.timing[10] & 0x7f000000) >> 24;
+       if (data < next->bios.timing_20_2c_1fc0)
+               data = next->bios.timing_20_2c_1fc0;
+       ram_mask(fuc, 0x10f24c, 0x7f000000, data << 24);
+       ram_mask(fuc, 0x10f224, 0x001f0000, next->bios.timing_20_30_f8 << 16);
+
+       ram_mask(fuc, 0x10fec4, 0x041e0f07, next->bios.timing_20_31_0800 << 26 |
+                                           next->bios.timing_20_31_0780 << 17 |
+                                           next->bios.timing_20_31_0078 << 8 |
+                                           next->bios.timing_20_31_0007);
+       ram_mask(fuc, 0x10fec8, 0x00000027, next->bios.timing_20_31_8000 << 5 |
+                                           next->bios.timing_20_31_7000);
+
+       ram_wr32(fuc, 0x10f090, 0x4000007e);
+       ram_nsec(fuc, 2000);
+       ram_wr32(fuc, 0x10f314, 0x00000001); /* PRECHARGE */
+       ram_wr32(fuc, 0x10f310, 0x00000001); /* REFRESH */
+       ram_wr32(fuc, 0x10f210, 0x80000000); /* REFRESH_AUTO = 1 */
+
+       if (next->bios.ramcfg_11_08_10 && (ram->mode == 2) /*XXX*/) {
+               u32 temp = ram_mask(fuc, 0x10f294, 0xff000000, 0x24000000);
+               gk104_ram_train(fuc, 0xbc0e0000, 0xa4010000); /*XXX*/
+               ram_nsec(fuc, 1000);
+               ram_wr32(fuc, 0x10f294, temp);
+       }
+
+       ram_mask(fuc, mr[3], 0xfff, ram->base.mr[3]);
+       ram_wr32(fuc, mr[0], ram->base.mr[0]);
+       ram_mask(fuc, mr[8], 0xfff, ram->base.mr[8]);
+       ram_nsec(fuc, 1000);
+       ram_mask(fuc, mr[1], 0xfff, ram->base.mr[1]);
+       ram_mask(fuc, mr[5], 0xfff, ram->base.mr[5] & ~0x004); /* LP3 later */
+       ram_mask(fuc, mr[6], 0xfff, ram->base.mr[6]);
+       ram_mask(fuc, mr[7], 0xfff, ram->base.mr[7]);
+
+       if (vc == 0 && ram_have(fuc, gpio2E)) {
+               u32 temp  = ram_mask(fuc, gpio2E, 0x3000, fuc->r_func2E[0]);
+               if (temp != ram_rd32(fuc, gpio2E)) {
+                       ram_wr32(fuc, gpiotrig, 1);
+                       ram_nsec(fuc, 20000);
+               }
+       }
+
+       ram_mask(fuc, 0x10f200, 0x80000000, 0x80000000);
+       ram_wr32(fuc, 0x10f318, 0x00000001); /* NOP? */
+       ram_mask(fuc, 0x10f200, 0x80000000, 0x00000000);
+       ram_nsec(fuc, 1000);
+       ram_nuts(ram, 0x10f200, 0x18808800, 0x00000000, 0x18808800);
+
+       data  = ram_rd32(fuc, 0x10f978);
+       data &= ~0x00046144;
+       data |=  0x0000000b;
+       if (!next->bios.ramcfg_11_07_08) {
+               if (!next->bios.ramcfg_11_07_04)
+                       data |= 0x0000200c;
+               else
+                       data |= 0x00000000;
+       } else {
+               data |= 0x00040044;
+       }
+       ram_wr32(fuc, 0x10f978, data);
+
+       if (ram->mode == 1) {
+               data = ram_rd32(fuc, 0x10f830) | 0x00000001;
+               ram_wr32(fuc, 0x10f830, data);
+       }
+
+       if (!next->bios.ramcfg_11_07_08) {
+               data = 0x88020000;
+               if ( next->bios.ramcfg_11_07_04)
+                       data |= 0x10000000;
+               if (!next->bios.rammap_11_08_10)
+                       data |= 0x00080000;
+       } else {
+               data = 0xa40e0000;
+       }
+       gk104_ram_train(fuc, 0xbc0f0000, data);
+       if (1) /* XXX: not always? */
+               ram_nsec(fuc, 1000);
+
+       if (ram->mode == 2) { /*XXX*/
+               ram_mask(fuc, 0x10f800, 0x00000004, 0x00000004);
+       }
+
+       /* LP3 */
+       if (ram_mask(fuc, mr[5], 0x004, ram->base.mr[5]) != ram->base.mr[5])
+               ram_nsec(fuc, 1000);
+
+       if (ram->mode != 2) {
+               ram_mask(fuc, 0x10f830, 0x01000000, 0x01000000);
+               ram_mask(fuc, 0x10f830, 0x01000000, 0x00000000);
+       }
+
+       if (next->bios.ramcfg_11_07_02)
+               gk104_ram_train(fuc, 0x80020000, 0x01000000);
+
+       ram_unblock(fuc);
+       ram_wr32(fuc, 0x62c000, 0x0f0f0f00);
+
+       if (next->bios.rammap_11_08_01)
+               data = 0x00000800;
+       else
+               data = 0x00000000;
+       ram_mask(fuc, 0x10f200, 0x00000800, data);
+       ram_nuts(ram, 0x10f200, 0x18808800, data, 0x18808800);
+       return 0;
+}
+
+/*******************************************************************************
+ * DDR3
+ ******************************************************************************/
+
+static int
+gk104_ram_calc_sddr3(struct nvkm_fb *pfb, u32 freq)
+{
+       struct gk104_ram *ram = (void *)pfb->ram;
+       struct gk104_ramfuc *fuc = &ram->fuc;
+       const u32 rcoef = ((  ram->P1 << 16) | (ram->N1 << 8) | ram->M1);
+       const u32 runk0 = ram->fN1 << 16;
+       const u32 runk1 = ram->fN1;
+       struct nvkm_ram_data *next = ram->base.next;
+       int vc = !next->bios.ramcfg_11_02_08;
+       int mv = !next->bios.ramcfg_11_02_04;
+       u32 mask, data;
+
+       ram_mask(fuc, 0x10f808, 0x40000000, 0x40000000);
+       ram_block(fuc);
+       ram_wr32(fuc, 0x62c000, 0x0f0f0000);
+
+       if (vc == 1 && ram_have(fuc, gpio2E)) {
+               u32 temp  = ram_mask(fuc, gpio2E, 0x3000, fuc->r_func2E[1]);
+               if (temp != ram_rd32(fuc, gpio2E)) {
+                       ram_wr32(fuc, gpiotrig, 1);
+                       ram_nsec(fuc, 20000);
+               }
+       }
+
+       ram_mask(fuc, 0x10f200, 0x00000800, 0x00000000);
+       if (next->bios.ramcfg_11_03_f0)
+               ram_mask(fuc, 0x10f808, 0x04000000, 0x04000000);
+
+       ram_wr32(fuc, 0x10f314, 0x00000001); /* PRECHARGE */
+       ram_wr32(fuc, 0x10f210, 0x00000000); /* REFRESH_AUTO = 0 */
+       ram_wr32(fuc, 0x10f310, 0x00000001); /* REFRESH */
+       ram_mask(fuc, 0x10f200, 0x80000000, 0x80000000);
+       ram_wr32(fuc, 0x10f310, 0x00000001); /* REFRESH */
+       ram_mask(fuc, 0x10f200, 0x80000000, 0x00000000);
+       ram_nsec(fuc, 1000);
+
+       ram_wr32(fuc, 0x10f090, 0x00000060);
+       ram_wr32(fuc, 0x10f090, 0xc000007e);
+
+       /*XXX: there does appear to be some kind of condition here, simply
+        *     modifying these bits in the vbios from the default pl0
+        *     entries shows no change.  however, the data does appear to
+        *     be correct and may be required for the transition back
+        */
+       mask = 0x00010000;
+       data = 0x00010000;
+
+       if (1) {
+               mask |= 0x800807e0;
+               data |= 0x800807e0;
+               switch (next->bios.ramcfg_11_03_c0) {
+               case 3: data &= ~0x00000040; break;
+               case 2: data &= ~0x00000100; break;
+               case 1: data &= ~0x80000000; break;
+               case 0: data &= ~0x00000400; break;
+               }
+
+               switch (next->bios.ramcfg_11_03_30) {
+               case 3: data &= ~0x00000020; break;
+               case 2: data &= ~0x00000080; break;
+               case 1: data &= ~0x00080000; break;
+               case 0: data &= ~0x00000200; break;
+               }
+       }
+
+       if (next->bios.ramcfg_11_02_80)
+               mask |= 0x03000000;
+       if (next->bios.ramcfg_11_02_40)
+               mask |= 0x00002000;
+       if (next->bios.ramcfg_11_07_10)
+               mask |= 0x00004000;
+       if (next->bios.ramcfg_11_07_08)
+               mask |= 0x00000003;
+       else
+               mask |= 0x14000000;
+       ram_mask(fuc, 0x10f824, mask, data);
+
+       ram_mask(fuc, 0x132040, 0x00010000, 0x00000000);
+
+       ram_mask(fuc, 0x1373f4, 0x00000000, 0x00010010);
+       data  = ram_rd32(fuc, 0x1373ec) & ~0x00030000;
+       data |= next->bios.ramcfg_11_03_30 << 16;
+       ram_wr32(fuc, 0x1373ec, data);
+       ram_mask(fuc, 0x1373f4, 0x00000003, 0x00000000);
+       ram_mask(fuc, 0x1373f4, 0x00000010, 0x00000000);
+
+       /* (re)program refpll, if required */
+       if ((ram_rd32(fuc, 0x132024) & 0xffffffff) != rcoef ||
+           (ram_rd32(fuc, 0x132034) & 0x0000ffff) != runk1) {
+               ram_mask(fuc, 0x132000, 0x00000001, 0x00000000);
+               ram_mask(fuc, 0x132020, 0x00000001, 0x00000000);
+               ram_wr32(fuc, 0x137320, 0x00000000);
+               ram_mask(fuc, 0x132030, 0xffff0000, runk0);
+               ram_mask(fuc, 0x132034, 0x0000ffff, runk1);
+               ram_wr32(fuc, 0x132024, rcoef);
+               ram_mask(fuc, 0x132028, 0x00080000, 0x00080000);
+               ram_mask(fuc, 0x132020, 0x00000001, 0x00000001);
+               ram_wait(fuc, 0x137390, 0x00020000, 0x00020000, 64000);
+               ram_mask(fuc, 0x132028, 0x00080000, 0x00000000);
+       }
+
+       ram_mask(fuc, 0x1373f4, 0x00000010, 0x00000010);
+       ram_mask(fuc, 0x1373f4, 0x00000003, 0x00000001);
+       ram_mask(fuc, 0x1373f4, 0x00010000, 0x00000000);
+
+       if (ram_have(fuc, gpioMV)) {
+               u32 temp  = ram_mask(fuc, gpioMV, 0x3000, fuc->r_funcMV[mv]);
+               if (temp != ram_rd32(fuc, gpioMV)) {
+                       ram_wr32(fuc, gpiotrig, 1);
+                       ram_nsec(fuc, 64000);
+               }
+       }
+
+       if (next->bios.ramcfg_11_02_40 ||
+           next->bios.ramcfg_11_07_10) {
+               ram_mask(fuc, 0x132040, 0x00010000, 0x00010000);
+               ram_nsec(fuc, 20000);
+       }
+
+       if (ram->mode != 2) /*XXX*/ {
+               if (next->bios.ramcfg_11_07_40)
+                       ram_mask(fuc, 0x10f670, 0x80000000, 0x80000000);
+       }
+
+       ram_wr32(fuc, 0x10f65c, 0x00000011 * next->bios.rammap_11_11_0c);
+       ram_wr32(fuc, 0x10f6b8, 0x01010101 * next->bios.ramcfg_11_09);
+       ram_wr32(fuc, 0x10f6bc, 0x01010101 * next->bios.ramcfg_11_09);
+
+       mask = 0x00010000;
+       data = 0x00000000;
+       if (!next->bios.ramcfg_11_02_80)
+               data |= 0x03000000;
+       if (!next->bios.ramcfg_11_02_40)
+               data |= 0x00002000;
+       if (!next->bios.ramcfg_11_07_10)
+               data |= 0x00004000;
+       if (!next->bios.ramcfg_11_07_08)
+               data |= 0x00000003;
+       else
+               data |= 0x14000000;
+       ram_mask(fuc, 0x10f824, mask, data);
+       ram_nsec(fuc, 1000);
+
+       if (next->bios.ramcfg_11_08_01)
+               data = 0x00100000;
+       else
+               data = 0x00000000;
+       ram_mask(fuc, 0x10f82c, 0x00100000, data);
+
+       /* PFB timing */
+       ram_mask(fuc, 0x10f248, 0xffffffff, next->bios.timing[10]);
+       ram_mask(fuc, 0x10f290, 0xffffffff, next->bios.timing[0]);
+       ram_mask(fuc, 0x10f294, 0xffffffff, next->bios.timing[1]);
+       ram_mask(fuc, 0x10f298, 0xffffffff, next->bios.timing[2]);
+       ram_mask(fuc, 0x10f29c, 0xffffffff, next->bios.timing[3]);
+       ram_mask(fuc, 0x10f2a0, 0xffffffff, next->bios.timing[4]);
+       ram_mask(fuc, 0x10f2a4, 0xffffffff, next->bios.timing[5]);
+       ram_mask(fuc, 0x10f2a8, 0xffffffff, next->bios.timing[6]);
+       ram_mask(fuc, 0x10f2ac, 0xffffffff, next->bios.timing[7]);
+       ram_mask(fuc, 0x10f2cc, 0xffffffff, next->bios.timing[8]);
+       ram_mask(fuc, 0x10f2e8, 0xffffffff, next->bios.timing[9]);
+
+       mask = 0x33f00000;
+       data = 0x00000000;
+       if (!next->bios.ramcfg_11_01_04)
+               data |= 0x20200000;
+       if (!next->bios.ramcfg_11_07_80)
+               data |= 0x12800000;
+       /*XXX: see note above about there probably being some condition
+        *     for the 10f824 stuff that uses ramcfg 3...
+        */
+       if (next->bios.ramcfg_11_03_f0) {
+               if (next->bios.rammap_11_08_0c) {
+                       if (!next->bios.ramcfg_11_07_80)
+                               mask |= 0x00000020;
+                       else
+                               data |= 0x00000020;
+                       mask |= 0x08000004;
+               }
+               data |= 0x04000000;
+       } else {
+               mask |= 0x44000020;
+               data |= 0x08000004;
+       }
+
+       ram_mask(fuc, 0x10f808, mask, data);
+
+       ram_wr32(fuc, 0x10f870, 0x11111111 * next->bios.ramcfg_11_03_0f);
+
+       ram_mask(fuc, 0x10f250, 0x000003f0, next->bios.timing_20_2c_003f << 4);
+
+       data = (next->bios.timing[10] & 0x7f000000) >> 24;
+       if (data < next->bios.timing_20_2c_1fc0)
+               data = next->bios.timing_20_2c_1fc0;
+       ram_mask(fuc, 0x10f24c, 0x7f000000, data << 24);
+
+       ram_mask(fuc, 0x10f224, 0x001f0000, next->bios.timing_20_30_f8 << 16);
+
+       ram_wr32(fuc, 0x10f090, 0x4000007f);
+       ram_nsec(fuc, 1000);
+
+       ram_wr32(fuc, 0x10f314, 0x00000001); /* PRECHARGE */
+       ram_wr32(fuc, 0x10f310, 0x00000001); /* REFRESH */
+       ram_wr32(fuc, 0x10f210, 0x80000000); /* REFRESH_AUTO = 1 */
+       ram_nsec(fuc, 1000);
+
+       ram_nuke(fuc, mr[0]);
+       ram_mask(fuc, mr[0], 0x100, 0x100);
+       ram_mask(fuc, mr[0], 0x100, 0x000);
+
+       ram_mask(fuc, mr[2], 0xfff, ram->base.mr[2]);
+       ram_wr32(fuc, mr[0], ram->base.mr[0]);
+       ram_nsec(fuc, 1000);
+
+       ram_nuke(fuc, mr[0]);
+       ram_mask(fuc, mr[0], 0x100, 0x100);
+       ram_mask(fuc, mr[0], 0x100, 0x000);
+
+       if (vc == 0 && ram_have(fuc, gpio2E)) {
+               u32 temp  = ram_mask(fuc, gpio2E, 0x3000, fuc->r_func2E[0]);
+               if (temp != ram_rd32(fuc, gpio2E)) {
+                       ram_wr32(fuc, gpiotrig, 1);
+                       ram_nsec(fuc, 20000);
+               }
+       }
+
+       if (ram->mode != 2) {
+               ram_mask(fuc, 0x10f830, 0x01000000, 0x01000000);
+               ram_mask(fuc, 0x10f830, 0x01000000, 0x00000000);
+       }
+
+       ram_mask(fuc, 0x10f200, 0x80000000, 0x80000000);
+       ram_wr32(fuc, 0x10f318, 0x00000001); /* NOP? */
+       ram_mask(fuc, 0x10f200, 0x80000000, 0x00000000);
+       ram_nsec(fuc, 1000);
+
+       ram_unblock(fuc);
+       ram_wr32(fuc, 0x62c000, 0x0f0f0f00);
+
+       if (next->bios.rammap_11_08_01)
+               data = 0x00000800;
+       else
+               data = 0x00000000;
+       ram_mask(fuc, 0x10f200, 0x00000800, data);
+       return 0;
+}
+
+/*******************************************************************************
+ * main hooks
+ ******************************************************************************/
+
+static int
+gk104_ram_calc_data(struct nvkm_fb *pfb, u32 khz, struct nvkm_ram_data *data)
+{
+       struct gk104_ram *ram = (void *)pfb->ram;
+       struct nvkm_ram_data *cfg;
+       u32 mhz = khz / 1000;
+
+       list_for_each_entry(cfg, &ram->cfg, head) {
+               if (mhz >= cfg->bios.rammap_min &&
+                   mhz <= cfg->bios.rammap_max) {
+                       *data = *cfg;
+                       data->freq = khz;
+                       return 0;
+               }
+       }
+
+       nv_error(ram, "ramcfg data for %dMHz not found\n", mhz);
+       return -EINVAL;
+}
+
+static int
+gk104_ram_calc_xits(struct nvkm_fb *pfb, struct nvkm_ram_data *next)
+{
+       struct gk104_ram *ram = (void *)pfb->ram;
+       struct gk104_ramfuc *fuc = &ram->fuc;
+       int refclk, i;
+       int ret;
+
+       ret = ram_init(fuc, pfb);
+       if (ret)
+               return ret;
+
+       ram->mode = (next->freq > fuc->refpll.vco1.max_freq) ? 2 : 1;
+       ram->from = ram_rd32(fuc, 0x1373f4) & 0x0000000f;
+
+       /* XXX: this is *not* what nvidia do.  on fermi nvidia generally
+        * select, based on some unknown condition, one of the two possible
+        * reference frequencies listed in the vbios table for mempll and
+        * program refpll to that frequency.
+        *
+        * so far, i've seen very weird values being chosen by nvidia on
+        * kepler boards, no idea how/why they're chosen.
+        */
+       refclk = next->freq;
+       if (ram->mode == 2)
+               refclk = fuc->mempll.refclk;
+
+       /* calculate refpll coefficients */
+       ret = gt215_pll_calc(nv_subdev(pfb), &fuc->refpll, refclk, &ram->N1,
+                            &ram->fN1, &ram->M1, &ram->P1);
+       fuc->mempll.refclk = ret;
+       if (ret <= 0) {
+               nv_error(pfb, "unable to calc refpll\n");
+               return -EINVAL;
+       }
+
+       /* calculate mempll coefficients, if we're using it */
+       if (ram->mode == 2) {
+               /* post-divider doesn't work... the reg takes the values but
+                * appears to completely ignore it.  there *is* a bit at
+                * bit 28 that appears to divide the clock by 2 if set.
+                */
+               fuc->mempll.min_p = 1;
+               fuc->mempll.max_p = 2;
+
+               ret = gt215_pll_calc(nv_subdev(pfb), &fuc->mempll, next->freq,
+                                    &ram->N2, NULL, &ram->M2, &ram->P2);
+               if (ret <= 0) {
+                       nv_error(pfb, "unable to calc mempll\n");
+                       return -EINVAL;
+               }
+       }
+
+       for (i = 0; i < ARRAY_SIZE(fuc->r_mr); i++) {
+               if (ram_have(fuc, mr[i]))
+                       ram->base.mr[i] = ram_rd32(fuc, mr[i]);
+       }
+       ram->base.freq = next->freq;
+
+       switch (ram->base.type) {
+       case NV_MEM_TYPE_DDR3:
+               ret = nvkm_sddr3_calc(&ram->base);
+               if (ret == 0)
+                       ret = gk104_ram_calc_sddr3(pfb, next->freq);
+               break;
+       case NV_MEM_TYPE_GDDR5:
+               ret = nvkm_gddr5_calc(&ram->base, ram->pnuts != 0);
+               if (ret == 0)
+                       ret = gk104_ram_calc_gddr5(pfb, next->freq);
+               break;
+       default:
+               ret = -ENOSYS;
+               break;
+       }
+
+       return ret;
+}
+
+static int
+gk104_ram_calc(struct nvkm_fb *pfb, u32 freq)
+{
+       struct nvkm_clk *clk = nvkm_clk(pfb);
+       struct gk104_ram *ram = (void *)pfb->ram;
+       struct nvkm_ram_data *xits = &ram->base.xition;
+       struct nvkm_ram_data *copy;
+       int ret;
+
+       if (ram->base.next == NULL) {
+               ret = gk104_ram_calc_data(pfb, clk->read(clk, nv_clk_src_mem),
+                                         &ram->base.former);
+               if (ret)
+                       return ret;
+
+               ret = gk104_ram_calc_data(pfb, freq, &ram->base.target);
+               if (ret)
+                       return ret;
+
+               if (ram->base.target.freq < ram->base.former.freq) {
+                       *xits = ram->base.target;
+                       copy = &ram->base.former;
+               } else {
+                       *xits = ram->base.former;
+                       copy = &ram->base.target;
+               }
+
+               xits->bios.ramcfg_11_02_04 = copy->bios.ramcfg_11_02_04;
+               xits->bios.ramcfg_11_02_03 = copy->bios.ramcfg_11_02_03;
+               xits->bios.timing_20_30_07 = copy->bios.timing_20_30_07;
+
+               ram->base.next = &ram->base.target;
+               if (memcmp(xits, &ram->base.former, sizeof(xits->bios)))
+                       ram->base.next = &ram->base.xition;
+       } else {
+               BUG_ON(ram->base.next != &ram->base.xition);
+               ram->base.next = &ram->base.target;
+       }
+
+       return gk104_ram_calc_xits(pfb, ram->base.next);
+}
+
+static void
+gk104_ram_prog_0(struct nvkm_fb *pfb, u32 freq)
+{
+       struct gk104_ram *ram = (void *)pfb->ram;
+       struct nvkm_ram_data *cfg;
+       u32 mhz = freq / 1000;
+       u32 mask, data;
+
+       list_for_each_entry(cfg, &ram->cfg, head) {
+               if (mhz >= cfg->bios.rammap_min &&
+                   mhz <= cfg->bios.rammap_max)
+                       break;
+       }
+
+       if (&cfg->head == &ram->cfg)
+               return;
+
+       if (mask = 0, data = 0, ram->diff.rammap_11_0a_03fe) {
+               data |= cfg->bios.rammap_11_0a_03fe << 12;
+               mask |= 0x001ff000;
+       }
+       if (ram->diff.rammap_11_09_01ff) {
+               data |= cfg->bios.rammap_11_09_01ff;
+               mask |= 0x000001ff;
+       }
+       nv_mask(pfb, 0x10f468, mask, data);
+
+       if (mask = 0, data = 0, ram->diff.rammap_11_0a_0400) {
+               data |= cfg->bios.rammap_11_0a_0400;
+               mask |= 0x00000001;
+       }
+       nv_mask(pfb, 0x10f420, mask, data);
+
+       if (mask = 0, data = 0, ram->diff.rammap_11_0a_0800) {
+               data |= cfg->bios.rammap_11_0a_0800;
+               mask |= 0x00000001;
+       }
+       nv_mask(pfb, 0x10f430, mask, data);
+
+       if (mask = 0, data = 0, ram->diff.rammap_11_0b_01f0) {
+               data |= cfg->bios.rammap_11_0b_01f0;
+               mask |= 0x0000001f;
+       }
+       nv_mask(pfb, 0x10f400, mask, data);
+
+       if (mask = 0, data = 0, ram->diff.rammap_11_0b_0200) {
+               data |= cfg->bios.rammap_11_0b_0200 << 9;
+               mask |= 0x00000200;
+       }
+       nv_mask(pfb, 0x10f410, mask, data);
+
+       if (mask = 0, data = 0, ram->diff.rammap_11_0d) {
+               data |= cfg->bios.rammap_11_0d << 16;
+               mask |= 0x00ff0000;
+       }
+       if (ram->diff.rammap_11_0f) {
+               data |= cfg->bios.rammap_11_0f << 8;
+               mask |= 0x0000ff00;
+       }
+       nv_mask(pfb, 0x10f440, mask, data);
+
+       if (mask = 0, data = 0, ram->diff.rammap_11_0e) {
+               data |= cfg->bios.rammap_11_0e << 8;
+               mask |= 0x0000ff00;
+       }
+       if (ram->diff.rammap_11_0b_0800) {
+               data |= cfg->bios.rammap_11_0b_0800 << 7;
+               mask |= 0x00000080;
+       }
+       if (ram->diff.rammap_11_0b_0400) {
+               data |= cfg->bios.rammap_11_0b_0400 << 5;
+               mask |= 0x00000020;
+       }
+       nv_mask(pfb, 0x10f444, mask, data);
+}
+
+static int
+gk104_ram_prog(struct nvkm_fb *pfb)
+{
+       struct nvkm_device *device = nv_device(pfb);
+       struct gk104_ram *ram = (void *)pfb->ram;
+       struct gk104_ramfuc *fuc = &ram->fuc;
+       struct nvkm_ram_data *next = ram->base.next;
+
+       if (!nvkm_boolopt(device->cfgopt, "NvMemExec", true)) {
+               ram_exec(fuc, false);
+               return (ram->base.next == &ram->base.xition);
+       }
+
+       gk104_ram_prog_0(pfb, 1000);
+       ram_exec(fuc, true);
+       gk104_ram_prog_0(pfb, next->freq);
+
+       return (ram->base.next == &ram->base.xition);
+}
+
+static void
+gk104_ram_tidy(struct nvkm_fb *pfb)
+{
+       struct gk104_ram *ram = (void *)pfb->ram;
+       struct gk104_ramfuc *fuc = &ram->fuc;
+       ram->base.next = NULL;
+       ram_exec(fuc, false);
+}
+
+struct gk104_ram_train {
+       u16 mask;
+       struct nvbios_M0209S remap;
+       struct nvbios_M0209S type00;
+       struct nvbios_M0209S type01;
+       struct nvbios_M0209S type04;
+       struct nvbios_M0209S type06;
+       struct nvbios_M0209S type07;
+       struct nvbios_M0209S type08;
+       struct nvbios_M0209S type09;
+};
+
+static int
+gk104_ram_train_type(struct nvkm_fb *pfb, int i, u8 ramcfg,
+                    struct gk104_ram_train *train)
+{
+       struct nvkm_bios *bios = nvkm_bios(pfb);
+       struct nvbios_M0205E M0205E;
+       struct nvbios_M0205S M0205S;
+       struct nvbios_M0209E M0209E;
+       struct nvbios_M0209S *remap = &train->remap;
+       struct nvbios_M0209S *value;
+       u8  ver, hdr, cnt, len;
+       u32 data;
+
+       /* determine type of data for this index */
+       if (!(data = nvbios_M0205Ep(bios, i, &ver, &hdr, &cnt, &len, &M0205E)))
+               return -ENOENT;
+
+       switch (M0205E.type) {
+       case 0x00: value = &train->type00; break;
+       case 0x01: value = &train->type01; break;
+       case 0x04: value = &train->type04; break;
+       case 0x06: value = &train->type06; break;
+       case 0x07: value = &train->type07; break;
+       case 0x08: value = &train->type08; break;
+       case 0x09: value = &train->type09; break;
+       default:
+               return 0;
+       }
+
+       /* training data index determined by ramcfg strap */
+       if (!(data = nvbios_M0205Sp(bios, i, ramcfg, &ver, &hdr, &M0205S)))
+               return -EINVAL;
+       i = M0205S.data;
+
+       /* training data format information */
+       if (!(data = nvbios_M0209Ep(bios, i, &ver, &hdr, &cnt, &len, &M0209E)))
+               return -EINVAL;
+
+       /* ... and the raw data */
+       if (!(data = nvbios_M0209Sp(bios, i, 0, &ver, &hdr, value)))
+               return -EINVAL;
+
+       if (M0209E.v02_07 == 2) {
+               /* of course! why wouldn't we have a pointer to another entry
+                * in the same table, and use the first one as an array of
+                * remap indices...
+                */
+               if (!(data = nvbios_M0209Sp(bios, M0209E.v03, 0, &ver, &hdr,
+                                           remap)))
+                       return -EINVAL;
+
+               for (i = 0; i < ARRAY_SIZE(value->data); i++)
+                       value->data[i] = remap->data[value->data[i]];
+       } else
+       if (M0209E.v02_07 != 1)
+               return -EINVAL;
+
+       train->mask |= 1 << M0205E.type;
+       return 0;
+}
+
+static int
+gk104_ram_train_init_0(struct nvkm_fb *pfb, struct gk104_ram_train *train)
+{
+       int i, j;
+
+       if ((train->mask & 0x03d3) != 0x03d3) {
+               nv_warn(pfb, "missing link training data\n");
+               return -EINVAL;
+       }
+
+       for (i = 0; i < 0x30; i++) {
+               for (j = 0; j < 8; j += 4) {
+                       nv_wr32(pfb, 0x10f968 + j, 0x00000000 | (i << 8));
+                       nv_wr32(pfb, 0x10f920 + j, 0x00000000 |
+                                                  train->type08.data[i] << 4 |
+                                                  train->type06.data[i]);
+                       nv_wr32(pfb, 0x10f918 + j, train->type00.data[i]);
+                       nv_wr32(pfb, 0x10f920 + j, 0x00000100 |
+                                                  train->type09.data[i] << 4 |
+                                                  train->type07.data[i]);
+                       nv_wr32(pfb, 0x10f918 + j, train->type01.data[i]);
+               }
+       }
+
+       for (j = 0; j < 8; j += 4) {
+               for (i = 0; i < 0x100; i++) {
+                       nv_wr32(pfb, 0x10f968 + j, i);
+                       nv_wr32(pfb, 0x10f900 + j, train->type04.data[i]);
+               }
+       }
+
+       return 0;
+}
+
+static int
+gk104_ram_train_init(struct nvkm_fb *pfb)
+{
+       u8 ramcfg = nvbios_ramcfg_index(nv_subdev(pfb));
+       struct gk104_ram_train *train;
+       int ret = -ENOMEM, i;
+
+       if ((train = kzalloc(sizeof(*train), GFP_KERNEL))) {
+               for (i = 0; i < 0x100; i++) {
+                       ret = gk104_ram_train_type(pfb, i, ramcfg, train);
+                       if (ret && ret != -ENOENT)
+                               break;
+               }
+       }
+
+       switch (pfb->ram->type) {
+       case NV_MEM_TYPE_GDDR5:
+               ret = gk104_ram_train_init_0(pfb, train);
+               break;
+       default:
+               ret = 0;
+               break;
+       }
+
+       kfree(train);
+       return ret;
+}
+
+int
+gk104_ram_init(struct nvkm_object *object)
+{
+       struct nvkm_fb *pfb = (void *)object->parent;
+       struct gk104_ram *ram   = (void *)object;
+       struct nvkm_bios *bios = nvkm_bios(pfb);
+       u8  ver, hdr, cnt, len, snr, ssz;
+       u32 data, save;
+       int ret, i;
+
+       ret = nvkm_ram_init(&ram->base);
+       if (ret)
+               return ret;
+
+       /* run a bunch of tables from rammap table.  there's actually
+        * individual pointers for each rammap entry too, but, nvidia
+        * seem to just run the last two entries' scripts early on in
+        * their init, and never again.. we'll just run 'em all once
+        * for now.
+        *
+        * i strongly suspect that each script is for a separate mode
+        * (likely selected by 0x10f65c's lower bits?), and the
+        * binary driver skips the one that's already been setup by
+        * the init tables.
+        */
+       data = nvbios_rammapTe(bios, &ver, &hdr, &cnt, &len, &snr, &ssz);
+       if (!data || hdr < 0x15)
+               return -EINVAL;
+
+       cnt  = nv_ro08(bios, data + 0x14); /* guess at count */
+       data = nv_ro32(bios, data + 0x10); /* guess u32... */
+       save = nv_rd32(pfb, 0x10f65c) & 0x000000f0;
+       for (i = 0; i < cnt; i++, data += 4) {
+               if (i != save >> 4) {
+                       nv_mask(pfb, 0x10f65c, 0x000000f0, i << 4);
+                       nvbios_exec(&(struct nvbios_init) {
+                                       .subdev = nv_subdev(pfb),
+                                       .bios = bios,
+                                       .offset = nv_ro32(bios, data),
+                                       .execute = 1,
+                                   });
+               }
+       }
+       nv_mask(pfb, 0x10f65c, 0x000000f0, save);
+       nv_mask(pfb, 0x10f584, 0x11000000, 0x00000000);
+       nv_wr32(pfb, 0x10ecc0, 0xffffffff);
+       nv_mask(pfb, 0x10f160, 0x00000010, 0x00000010);
+
+       return gk104_ram_train_init(pfb);
+}
+
+static int
+gk104_ram_ctor_data(struct gk104_ram *ram, u8 ramcfg, int i)
+{
+       struct nvkm_fb *pfb = (void *)nv_object(ram)->parent;
+       struct nvkm_bios *bios = nvkm_bios(pfb);
+       struct nvkm_ram_data *cfg;
+       struct nvbios_ramcfg *d = &ram->diff;
+       struct nvbios_ramcfg *p, *n;
+       u8  ver, hdr, cnt, len;
+       u32 data;
+       int ret;
+
+       if (!(cfg = kmalloc(sizeof(*cfg), GFP_KERNEL)))
+               return -ENOMEM;
+       p = &list_last_entry(&ram->cfg, typeof(*cfg), head)->bios;
+       n = &cfg->bios;
+
+       /* memory config data for a range of target frequencies */
+       data = nvbios_rammapEp(bios, i, &ver, &hdr, &cnt, &len, &cfg->bios);
+       if (ret = -ENOENT, !data)
+               goto done;
+       if (ret = -ENOSYS, ver != 0x11 || hdr < 0x12)
+               goto done;
+
+       /* ... and a portion specific to the attached memory */
+       data = nvbios_rammapSp(bios, data, ver, hdr, cnt, len, ramcfg,
+                              &ver, &hdr, &cfg->bios);
+       if (ret = -EINVAL, !data)
+               goto done;
+       if (ret = -ENOSYS, ver != 0x11 || hdr < 0x0a)
+               goto done;
+
+       /* lookup memory timings, if bios says they're present */
+       if (cfg->bios.ramcfg_timing != 0xff) {
+               data = nvbios_timingEp(bios, cfg->bios.ramcfg_timing,
+                                      &ver, &hdr, &cnt, &len,
+                                      &cfg->bios);
+               if (ret = -EINVAL, !data)
+                       goto done;
+               if (ret = -ENOSYS, ver != 0x20 || hdr < 0x33)
+                       goto done;
+       }
+
+       list_add_tail(&cfg->head, &ram->cfg);
+       if (ret = 0, i == 0)
+               goto done;
+
+       d->rammap_11_0a_03fe |= p->rammap_11_0a_03fe != n->rammap_11_0a_03fe;
+       d->rammap_11_09_01ff |= p->rammap_11_09_01ff != n->rammap_11_09_01ff;
+       d->rammap_11_0a_0400 |= p->rammap_11_0a_0400 != n->rammap_11_0a_0400;
+       d->rammap_11_0a_0800 |= p->rammap_11_0a_0800 != n->rammap_11_0a_0800;
+       d->rammap_11_0b_01f0 |= p->rammap_11_0b_01f0 != n->rammap_11_0b_01f0;
+       d->rammap_11_0b_0200 |= p->rammap_11_0b_0200 != n->rammap_11_0b_0200;
+       d->rammap_11_0d |= p->rammap_11_0d != n->rammap_11_0d;
+       d->rammap_11_0f |= p->rammap_11_0f != n->rammap_11_0f;
+       d->rammap_11_0e |= p->rammap_11_0e != n->rammap_11_0e;
+       d->rammap_11_0b_0800 |= p->rammap_11_0b_0800 != n->rammap_11_0b_0800;
+       d->rammap_11_0b_0400 |= p->rammap_11_0b_0400 != n->rammap_11_0b_0400;
+       d->ramcfg_11_01_01 |= p->ramcfg_11_01_01 != n->ramcfg_11_01_01;
+       d->ramcfg_11_01_02 |= p->ramcfg_11_01_02 != n->ramcfg_11_01_02;
+       d->ramcfg_11_01_10 |= p->ramcfg_11_01_10 != n->ramcfg_11_01_10;
+       d->ramcfg_11_02_03 |= p->ramcfg_11_02_03 != n->ramcfg_11_02_03;
+       d->ramcfg_11_08_20 |= p->ramcfg_11_08_20 != n->ramcfg_11_08_20;
+       d->timing_20_30_07 |= p->timing_20_30_07 != n->timing_20_30_07;
+done:
+       if (ret)
+               kfree(cfg);
+       return ret;
+}
+
+static void
+gk104_ram_dtor(struct nvkm_object *object)
+{
+       struct gk104_ram *ram = (void *)object;
+       struct nvkm_ram_data *cfg, *tmp;
+
+       list_for_each_entry_safe(cfg, tmp, &ram->cfg, head) {
+               kfree(cfg);
+       }
+
+       nvkm_ram_destroy(&ram->base);
+}
+
+static int
+gk104_ram_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+              struct nvkm_oclass *oclass, void *data, u32 size,
+              struct nvkm_object **pobject)
+{
+       struct nvkm_fb *pfb = nvkm_fb(parent);
+       struct nvkm_bios *bios = nvkm_bios(pfb);
+       struct nvkm_gpio *gpio = nvkm_gpio(pfb);
+       struct dcb_gpio_func func;
+       struct gk104_ram *ram;
+       int ret, i;
+       u8  ramcfg = nvbios_ramcfg_index(nv_subdev(pfb));
+       u32 tmp;
+
+       ret = gf100_ram_create(parent, engine, oclass, 0x022554, &ram);
+       *pobject = nv_object(ram);
+       if (ret)
+               return ret;
+
+       INIT_LIST_HEAD(&ram->cfg);
+
+       switch (ram->base.type) {
+       case NV_MEM_TYPE_DDR3:
+       case NV_MEM_TYPE_GDDR5:
+               ram->base.calc = gk104_ram_calc;
+               ram->base.prog = gk104_ram_prog;
+               ram->base.tidy = gk104_ram_tidy;
+               break;
+       default:
+               nv_warn(pfb, "reclocking of this RAM type is unsupported\n");
+               break;
+       }
+
+       /* calculate a mask of differently configured memory partitions,
+        * because, of course reclocking wasn't complicated enough
+        * already without having to treat some of them differently to
+        * the others....
+        */
+       ram->parts = nv_rd32(pfb, 0x022438);
+       ram->pmask = nv_rd32(pfb, 0x022554);
+       ram->pnuts = 0;
+       for (i = 0, tmp = 0; i < ram->parts; i++) {
+               if (!(ram->pmask & (1 << i))) {
+                       u32 cfg1 = nv_rd32(pfb, 0x110204 + (i * 0x1000));
+                       if (tmp && tmp != cfg1) {
+                               ram->pnuts |= (1 << i);
+                               continue;
+                       }
+                       tmp = cfg1;
+               }
+       }
+
+       /* parse bios data for all rammap table entries up-front, and
+        * build information on whether certain fields differ between
+        * any of the entries.
+        *
+        * the binary driver appears to completely ignore some fields
+        * when all entries contain the same value.  at first, it was
+        * hoped that these were mere optimisations and the bios init
+        * tables had configured as per the values here, but there is
+        * evidence now to suggest that this isn't the case and we do
+        * need to treat this condition as a "don't touch" indicator.
+        */
+       for (i = 0; !ret; i++) {
+               ret = gk104_ram_ctor_data(ram, ramcfg, i);
+               if (ret && ret != -ENOENT) {
+                       nv_error(pfb, "failed to parse ramcfg data\n");
+                       return ret;
+               }
+       }
+
+       /* parse bios data for both pll's */
+       ret = nvbios_pll_parse(bios, 0x0c, &ram->fuc.refpll);
+       if (ret) {
+               nv_error(pfb, "mclk refpll data not found\n");
+               return ret;
+       }
+
+       ret = nvbios_pll_parse(bios, 0x04, &ram->fuc.mempll);
+       if (ret) {
+               nv_error(pfb, "mclk pll data not found\n");
+               return ret;
+       }
+
+       /* lookup memory voltage gpios */
+       ret = gpio->find(gpio, 0, 0x18, DCB_GPIO_UNUSED, &func);
+       if (ret == 0) {
+               ram->fuc.r_gpioMV = ramfuc_reg(0x00d610 + (func.line * 0x04));
+               ram->fuc.r_funcMV[0] = (func.log[0] ^ 2) << 12;
+               ram->fuc.r_funcMV[1] = (func.log[1] ^ 2) << 12;
+       }
+
+       ret = gpio->find(gpio, 0, 0x2e, DCB_GPIO_UNUSED, &func);
+       if (ret == 0) {
+               ram->fuc.r_gpio2E = ramfuc_reg(0x00d610 + (func.line * 0x04));
+               ram->fuc.r_func2E[0] = (func.log[0] ^ 2) << 12;
+               ram->fuc.r_func2E[1] = (func.log[1] ^ 2) << 12;
+       }
+
+       ram->fuc.r_gpiotrig = ramfuc_reg(0x00d604);
+
+       ram->fuc.r_0x132020 = ramfuc_reg(0x132020);
+       ram->fuc.r_0x132028 = ramfuc_reg(0x132028);
+       ram->fuc.r_0x132024 = ramfuc_reg(0x132024);
+       ram->fuc.r_0x132030 = ramfuc_reg(0x132030);
+       ram->fuc.r_0x132034 = ramfuc_reg(0x132034);
+       ram->fuc.r_0x132000 = ramfuc_reg(0x132000);
+       ram->fuc.r_0x132004 = ramfuc_reg(0x132004);
+       ram->fuc.r_0x132040 = ramfuc_reg(0x132040);
+
+       ram->fuc.r_0x10f248 = ramfuc_reg(0x10f248);
+       ram->fuc.r_0x10f290 = ramfuc_reg(0x10f290);
+       ram->fuc.r_0x10f294 = ramfuc_reg(0x10f294);
+       ram->fuc.r_0x10f298 = ramfuc_reg(0x10f298);
+       ram->fuc.r_0x10f29c = ramfuc_reg(0x10f29c);
+       ram->fuc.r_0x10f2a0 = ramfuc_reg(0x10f2a0);
+       ram->fuc.r_0x10f2a4 = ramfuc_reg(0x10f2a4);
+       ram->fuc.r_0x10f2a8 = ramfuc_reg(0x10f2a8);
+       ram->fuc.r_0x10f2ac = ramfuc_reg(0x10f2ac);
+       ram->fuc.r_0x10f2cc = ramfuc_reg(0x10f2cc);
+       ram->fuc.r_0x10f2e8 = ramfuc_reg(0x10f2e8);
+       ram->fuc.r_0x10f250 = ramfuc_reg(0x10f250);
+       ram->fuc.r_0x10f24c = ramfuc_reg(0x10f24c);
+       ram->fuc.r_0x10fec4 = ramfuc_reg(0x10fec4);
+       ram->fuc.r_0x10fec8 = ramfuc_reg(0x10fec8);
+       ram->fuc.r_0x10f604 = ramfuc_reg(0x10f604);
+       ram->fuc.r_0x10f614 = ramfuc_reg(0x10f614);
+       ram->fuc.r_0x10f610 = ramfuc_reg(0x10f610);
+       ram->fuc.r_0x100770 = ramfuc_reg(0x100770);
+       ram->fuc.r_0x100778 = ramfuc_reg(0x100778);
+       ram->fuc.r_0x10f224 = ramfuc_reg(0x10f224);
+
+       ram->fuc.r_0x10f870 = ramfuc_reg(0x10f870);
+       ram->fuc.r_0x10f698 = ramfuc_reg(0x10f698);
+       ram->fuc.r_0x10f694 = ramfuc_reg(0x10f694);
+       ram->fuc.r_0x10f6b8 = ramfuc_reg(0x10f6b8);
+       ram->fuc.r_0x10f808 = ramfuc_reg(0x10f808);
+       ram->fuc.r_0x10f670 = ramfuc_reg(0x10f670);
+       ram->fuc.r_0x10f60c = ramfuc_reg(0x10f60c);
+       ram->fuc.r_0x10f830 = ramfuc_reg(0x10f830);
+       ram->fuc.r_0x1373ec = ramfuc_reg(0x1373ec);
+       ram->fuc.r_0x10f800 = ramfuc_reg(0x10f800);
+       ram->fuc.r_0x10f82c = ramfuc_reg(0x10f82c);
+
+       ram->fuc.r_0x10f978 = ramfuc_reg(0x10f978);
+       ram->fuc.r_0x10f910 = ramfuc_reg(0x10f910);
+       ram->fuc.r_0x10f914 = ramfuc_reg(0x10f914);
+
+       switch (ram->base.type) {
+       case NV_MEM_TYPE_GDDR5:
+               ram->fuc.r_mr[0] = ramfuc_reg(0x10f300);
+               ram->fuc.r_mr[1] = ramfuc_reg(0x10f330);
+               ram->fuc.r_mr[2] = ramfuc_reg(0x10f334);
+               ram->fuc.r_mr[3] = ramfuc_reg(0x10f338);
+               ram->fuc.r_mr[4] = ramfuc_reg(0x10f33c);
+               ram->fuc.r_mr[5] = ramfuc_reg(0x10f340);
+               ram->fuc.r_mr[6] = ramfuc_reg(0x10f344);
+               ram->fuc.r_mr[7] = ramfuc_reg(0x10f348);
+               ram->fuc.r_mr[8] = ramfuc_reg(0x10f354);
+               ram->fuc.r_mr[15] = ramfuc_reg(0x10f34c);
+               break;
+       case NV_MEM_TYPE_DDR3:
+               ram->fuc.r_mr[0] = ramfuc_reg(0x10f300);
+               ram->fuc.r_mr[2] = ramfuc_reg(0x10f320);
+               break;
+       default:
+               break;
+       }
+
+       ram->fuc.r_0x62c000 = ramfuc_reg(0x62c000);
+       ram->fuc.r_0x10f200 = ramfuc_reg(0x10f200);
+       ram->fuc.r_0x10f210 = ramfuc_reg(0x10f210);
+       ram->fuc.r_0x10f310 = ramfuc_reg(0x10f310);
+       ram->fuc.r_0x10f314 = ramfuc_reg(0x10f314);
+       ram->fuc.r_0x10f318 = ramfuc_reg(0x10f318);
+       ram->fuc.r_0x10f090 = ramfuc_reg(0x10f090);
+       ram->fuc.r_0x10f69c = ramfuc_reg(0x10f69c);
+       ram->fuc.r_0x10f824 = ramfuc_reg(0x10f824);
+       ram->fuc.r_0x1373f0 = ramfuc_reg(0x1373f0);
+       ram->fuc.r_0x1373f4 = ramfuc_reg(0x1373f4);
+       ram->fuc.r_0x137320 = ramfuc_reg(0x137320);
+       ram->fuc.r_0x10f65c = ramfuc_reg(0x10f65c);
+       ram->fuc.r_0x10f6bc = ramfuc_reg(0x10f6bc);
+       ram->fuc.r_0x100710 = ramfuc_reg(0x100710);
+       ram->fuc.r_0x100750 = ramfuc_reg(0x100750);
+       return 0;
+}
+
+struct nvkm_oclass
+gk104_ram_oclass = {
+       .handle = 0,
+       .ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = gk104_ram_ctor,
+               .dtor = gk104_ram_dtor,
+               .init = gk104_ram_init,
+               .fini = _nvkm_ram_fini,
+       }
+};
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/fb/ramgk20a.c b/drivers/gpu/drm/nouveau/nvkm/subdev/fb/ramgk20a.c
new file mode 100644 (file)
index 0000000..5f30db1
--- /dev/null
@@ -0,0 +1,149 @@
+/*
+ * Copyright (c) 2014, NVIDIA CORPORATION. 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 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 "priv.h"
+
+#include <core/device.h>
+
+struct gk20a_mem {
+       struct nvkm_mem base;
+       void *cpuaddr;
+       dma_addr_t handle;
+};
+#define to_gk20a_mem(m) container_of(m, struct gk20a_mem, base)
+
+static void
+gk20a_ram_put(struct nvkm_fb *pfb, struct nvkm_mem **pmem)
+{
+       struct device *dev = nv_device_base(nv_device(pfb));
+       struct gk20a_mem *mem = to_gk20a_mem(*pmem);
+
+       *pmem = NULL;
+       if (unlikely(mem == NULL))
+               return;
+
+       if (likely(mem->cpuaddr))
+               dma_free_coherent(dev, mem->base.size << PAGE_SHIFT,
+                                 mem->cpuaddr, mem->handle);
+
+       kfree(mem->base.pages);
+       kfree(mem);
+}
+
+static int
+gk20a_ram_get(struct nvkm_fb *pfb, u64 size, u32 align, u32 ncmin,
+            u32 memtype, struct nvkm_mem **pmem)
+{
+       struct device *dev = nv_device_base(nv_device(pfb));
+       struct gk20a_mem *mem;
+       u32 type = memtype & 0xff;
+       u32 npages, order;
+       int i;
+
+       nv_debug(pfb, "%s: size: %llx align: %x, ncmin: %x\n", __func__, size,
+                align, ncmin);
+
+       npages = size >> PAGE_SHIFT;
+       if (npages == 0)
+               npages = 1;
+
+       if (align == 0)
+               align = PAGE_SIZE;
+       align >>= PAGE_SHIFT;
+
+       /* round alignment to the next power of 2, if needed */
+       order = fls(align);
+       if ((align & (align - 1)) == 0)
+               order--;
+       align = BIT(order);
+
+       /* ensure returned address is correctly aligned */
+       npages = max(align, npages);
+
+       mem = kzalloc(sizeof(*mem), GFP_KERNEL);
+       if (!mem)
+               return -ENOMEM;
+
+       mem->base.size = npages;
+       mem->base.memtype = type;
+
+       mem->base.pages = kzalloc(sizeof(dma_addr_t) * npages, GFP_KERNEL);
+       if (!mem->base.pages) {
+               kfree(mem);
+               return -ENOMEM;
+       }
+
+       *pmem = &mem->base;
+
+       mem->cpuaddr = dma_alloc_coherent(dev, npages << PAGE_SHIFT,
+                                         &mem->handle, GFP_KERNEL);
+       if (!mem->cpuaddr) {
+               nv_error(pfb, "%s: cannot allocate memory!\n", __func__);
+               gk20a_ram_put(pfb, pmem);
+               return -ENOMEM;
+       }
+
+       align <<= PAGE_SHIFT;
+
+       /* alignment check */
+       if (unlikely(mem->handle & (align - 1)))
+               nv_warn(pfb, "memory not aligned as requested: %pad (0x%x)\n",
+                       &mem->handle, align);
+
+       nv_debug(pfb, "alloc size: 0x%x, align: 0x%x, paddr: %pad, vaddr: %p\n",
+                npages << PAGE_SHIFT, align, &mem->handle, mem->cpuaddr);
+
+       for (i = 0; i < npages; i++)
+               mem->base.pages[i] = mem->handle + (PAGE_SIZE * i);
+
+       mem->base.offset = (u64)mem->base.pages[0];
+       return 0;
+}
+
+static int
+gk20a_ram_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+              struct nvkm_oclass *oclass, void *data, u32 datasize,
+              struct nvkm_object **pobject)
+{
+       struct nvkm_ram *ram;
+       int ret;
+
+       ret = nvkm_ram_create(parent, engine, oclass, &ram);
+       *pobject = nv_object(ram);
+       if (ret)
+               return ret;
+       ram->type = NV_MEM_TYPE_STOLEN;
+       ram->size = get_num_physpages() << PAGE_SHIFT;
+
+       ram->get = gk20a_ram_get;
+       ram->put = gk20a_ram_put;
+       return 0;
+}
+
+struct nvkm_oclass
+gk20a_ram_oclass = {
+       .ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = gk20a_ram_ctor,
+               .dtor = _nvkm_ram_dtor,
+               .init = _nvkm_ram_init,
+               .fini = _nvkm_ram_fini,
+       },
+};
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/fb/ramgm107.c b/drivers/gpu/drm/nouveau/nvkm/subdev/fb/ramgm107.c
new file mode 100644 (file)
index 0000000..a298b39
--- /dev/null
@@ -0,0 +1,55 @@
+/*
+ * Copyright 2013 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 "gf100.h"
+
+struct gm107_ram {
+       struct nvkm_ram base;
+};
+
+static int
+gm107_ram_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+              struct nvkm_oclass *oclass, void *data, u32 size,
+              struct nvkm_object **pobject)
+{
+       struct gm107_ram *ram;
+       int ret;
+
+       ret = gf100_ram_create(parent, engine, oclass, 0x021c14, &ram);
+       *pobject = nv_object(ram);
+       if (ret)
+               return ret;
+
+       return 0;
+}
+
+struct nvkm_oclass
+gm107_ram_oclass = {
+       .handle = 0,
+       .ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = gm107_ram_ctor,
+               .dtor = _nvkm_ram_dtor,
+               .init = gk104_ram_init,
+               .fini = _nvkm_ram_fini,
+       }
+};
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/fb/ramgt215.c b/drivers/gpu/drm/nouveau/nvkm/subdev/fb/ramgt215.c
new file mode 100644 (file)
index 0000000..2417640
--- /dev/null
@@ -0,0 +1,1012 @@
+/*
+ * Copyright 2013 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
+ *         Roy Spliet <rspliet@eclipso.eu>
+ */
+
+#include "ramfuc.h"
+#include "nv50.h"
+
+#include <core/device.h>
+#include <core/option.h>
+#include <subdev/bios.h>
+#include <subdev/bios/M0205.h>
+#include <subdev/bios/rammap.h>
+#include <subdev/bios/timing.h>
+#include <subdev/clk/gt215.h>
+#include <subdev/gpio.h>
+
+/* XXX: Remove when memx gains GPIO support */
+extern int nv50_gpio_location(int line, u32 *reg, u32 *shift);
+
+struct gt215_ramfuc {
+       struct ramfuc base;
+       struct ramfuc_reg r_0x001610;
+       struct ramfuc_reg r_0x001700;
+       struct ramfuc_reg r_0x002504;
+       struct ramfuc_reg r_0x004000;
+       struct ramfuc_reg r_0x004004;
+       struct ramfuc_reg r_0x004018;
+       struct ramfuc_reg r_0x004128;
+       struct ramfuc_reg r_0x004168;
+       struct ramfuc_reg r_0x100080;
+       struct ramfuc_reg r_0x100200;
+       struct ramfuc_reg r_0x100210;
+       struct ramfuc_reg r_0x100220[9];
+       struct ramfuc_reg r_0x100264;
+       struct ramfuc_reg r_0x1002d0;
+       struct ramfuc_reg r_0x1002d4;
+       struct ramfuc_reg r_0x1002dc;
+       struct ramfuc_reg r_0x10053c;
+       struct ramfuc_reg r_0x1005a0;
+       struct ramfuc_reg r_0x1005a4;
+       struct ramfuc_reg r_0x100700;
+       struct ramfuc_reg r_0x100714;
+       struct ramfuc_reg r_0x100718;
+       struct ramfuc_reg r_0x10071c;
+       struct ramfuc_reg r_0x100720;
+       struct ramfuc_reg r_0x100760;
+       struct ramfuc_reg r_0x1007a0;
+       struct ramfuc_reg r_0x1007e0;
+       struct ramfuc_reg r_0x100da0;
+       struct ramfuc_reg r_0x10f804;
+       struct ramfuc_reg r_0x1110e0;
+       struct ramfuc_reg r_0x111100;
+       struct ramfuc_reg r_0x111104;
+       struct ramfuc_reg r_0x1111e0;
+       struct ramfuc_reg r_0x111400;
+       struct ramfuc_reg r_0x611200;
+       struct ramfuc_reg r_mr[4];
+       struct ramfuc_reg r_gpioFBVREF;
+};
+
+struct gt215_ltrain {
+       enum {
+               NVA3_TRAIN_UNKNOWN,
+               NVA3_TRAIN_UNSUPPORTED,
+               NVA3_TRAIN_ONCE,
+               NVA3_TRAIN_EXEC,
+               NVA3_TRAIN_DONE
+       } state;
+       u32 r_100720;
+       u32 r_1111e0;
+       u32 r_111400;
+       struct nvkm_mem *mem;
+};
+
+struct gt215_ram {
+       struct nvkm_ram base;
+       struct gt215_ramfuc fuc;
+       struct gt215_ltrain ltrain;
+};
+
+void
+gt215_link_train_calc(u32 *vals, struct gt215_ltrain *train)
+{
+       int i, lo, hi;
+       u8 median[8], bins[4] = {0, 0, 0, 0}, bin = 0, qty = 0;
+
+       for (i = 0; i < 8; i++) {
+               for (lo = 0; lo < 0x40; lo++) {
+                       if (!(vals[lo] & 0x80000000))
+                               continue;
+                       if (vals[lo] & (0x101 << i))
+                               break;
+               }
+
+               if (lo == 0x40)
+                       return;
+
+               for (hi = lo + 1; hi < 0x40; hi++) {
+                       if (!(vals[lo] & 0x80000000))
+                               continue;
+                       if (!(vals[hi] & (0x101 << i))) {
+                               hi--;
+                               break;
+                       }
+               }
+
+               median[i] = ((hi - lo) >> 1) + lo;
+               bins[(median[i] & 0xf0) >> 4]++;
+               median[i] += 0x30;
+       }
+
+       /* Find the best value for 0x1111e0 */
+       for (i = 0; i < 4; i++) {
+               if (bins[i] > qty) {
+                       bin = i + 3;
+                       qty = bins[i];
+               }
+       }
+
+       train->r_100720 = 0;
+       for (i = 0; i < 8; i++) {
+               median[i] = max(median[i], (u8) (bin << 4));
+               median[i] = min(median[i], (u8) ((bin << 4) | 0xf));
+
+               train->r_100720 |= ((median[i] & 0x0f) << (i << 2));
+       }
+
+       train->r_1111e0 = 0x02000000 | (bin * 0x101);
+       train->r_111400 = 0x0;
+}
+
+/*
+ * Link training for (at least) DDR3
+ */
+int
+gt215_link_train(struct nvkm_fb *pfb)
+{
+       struct nvkm_bios *bios = nvkm_bios(pfb);
+       struct gt215_ram *ram = (void *)pfb->ram;
+       struct nvkm_clk *clk = nvkm_clk(pfb);
+       struct gt215_ltrain *train = &ram->ltrain;
+       struct nvkm_device *device = nv_device(pfb);
+       struct gt215_ramfuc *fuc = &ram->fuc;
+       u32 *result, r1700;
+       int ret, i;
+       struct nvbios_M0205T M0205T = { 0 };
+       u8 ver, hdr, cnt, len, snr, ssz;
+       unsigned int clk_current;
+       unsigned long flags;
+       unsigned long *f = &flags;
+
+       if (nvkm_boolopt(device->cfgopt, "NvMemExec", true) != true)
+               return -ENOSYS;
+
+       /* XXX: Multiple partitions? */
+       result = kmalloc(64 * sizeof(u32), GFP_KERNEL);
+       if (!result)
+               return -ENOMEM;
+
+       train->state = NVA3_TRAIN_EXEC;
+
+       /* Clock speeds for training and back */
+       nvbios_M0205Tp(bios, &ver, &hdr, &cnt, &len, &snr, &ssz, &M0205T);
+       if (M0205T.freq == 0)
+               return -ENOENT;
+
+       clk_current = clk->read(clk, nv_clk_src_mem);
+
+       ret = gt215_clk_pre(clk, f);
+       if (ret)
+               goto out;
+
+       /* First: clock up/down */
+       ret = ram->base.calc(pfb, (u32) M0205T.freq * 1000);
+       if (ret)
+               goto out;
+
+       /* Do this *after* calc, eliminates write in script */
+       nv_wr32(pfb, 0x111400, 0x00000000);
+       /* XXX: Magic writes that improve train reliability? */
+       nv_mask(pfb, 0x100674, 0x0000ffff, 0x00000000);
+       nv_mask(pfb, 0x1005e4, 0x0000ffff, 0x00000000);
+       nv_mask(pfb, 0x100b0c, 0x000000ff, 0x00000000);
+       nv_wr32(pfb, 0x100c04, 0x00000400);
+
+       /* Now the training script */
+       r1700 = ram_rd32(fuc, 0x001700);
+
+       ram_mask(fuc, 0x100200, 0x00000800, 0x00000000);
+       ram_wr32(fuc, 0x611200, 0x3300);
+       ram_wait_vblank(fuc);
+       ram_wait(fuc, 0x611200, 0x00000003, 0x00000000, 500000);
+       ram_mask(fuc, 0x001610, 0x00000083, 0x00000003);
+       ram_mask(fuc, 0x100080, 0x00000020, 0x00000000);
+       ram_mask(fuc, 0x10f804, 0x80000000, 0x00000000);
+       ram_wr32(fuc, 0x001700, 0x00000000);
+
+       ram_train(fuc);
+
+       /* Reset */
+       ram_mask(fuc, 0x10f804, 0x80000000, 0x80000000);
+       ram_wr32(fuc, 0x10053c, 0x0);
+       ram_wr32(fuc, 0x100720, train->r_100720);
+       ram_wr32(fuc, 0x1111e0, train->r_1111e0);
+       ram_wr32(fuc, 0x111400, train->r_111400);
+       ram_nuke(fuc, 0x100080);
+       ram_mask(fuc, 0x100080, 0x00000020, 0x00000020);
+       ram_nsec(fuc, 1000);
+
+       ram_wr32(fuc, 0x001700, r1700);
+       ram_mask(fuc, 0x001610, 0x00000083, 0x00000080);
+       ram_wr32(fuc, 0x611200, 0x3330);
+       ram_mask(fuc, 0x100200, 0x00000800, 0x00000800);
+
+       ram_exec(fuc, true);
+
+       ram->base.calc(pfb, clk_current);
+       ram_exec(fuc, true);
+
+       /* Post-processing, avoids flicker */
+       nv_mask(pfb, 0x616308, 0x10, 0x10);
+       nv_mask(pfb, 0x616b08, 0x10, 0x10);
+
+       gt215_clk_post(clk, f);
+
+       ram_train_result(pfb, result, 64);
+       for (i = 0; i < 64; i++)
+               nv_debug(pfb, "Train: %08x", result[i]);
+       gt215_link_train_calc(result, train);
+
+       nv_debug(pfb, "Train: %08x %08x %08x", train->r_100720,
+                       train->r_1111e0, train->r_111400);
+
+       kfree(result);
+
+       train->state = NVA3_TRAIN_DONE;
+
+       return ret;
+
+out:
+       if(ret == -EBUSY)
+               f = NULL;
+
+       train->state = NVA3_TRAIN_UNSUPPORTED;
+
+       gt215_clk_post(clk, f);
+       return ret;
+}
+
+int
+gt215_link_train_init(struct nvkm_fb *pfb)
+{
+       static const u32 pattern[16] = {
+               0xaaaaaaaa, 0xcccccccc, 0xdddddddd, 0xeeeeeeee,
+               0x00000000, 0x11111111, 0x44444444, 0xdddddddd,
+               0x33333333, 0x55555555, 0x77777777, 0x66666666,
+               0x99999999, 0x88888888, 0xeeeeeeee, 0xbbbbbbbb,
+       };
+       struct nvkm_bios *bios = nvkm_bios(pfb);
+       struct gt215_ram *ram = (void *)pfb->ram;
+       struct gt215_ltrain *train = &ram->ltrain;
+       struct nvkm_mem *mem;
+       struct nvbios_M0205E M0205E;
+       u8 ver, hdr, cnt, len;
+       u32 r001700;
+       int ret, i = 0;
+
+       train->state = NVA3_TRAIN_UNSUPPORTED;
+
+       /* We support type "5"
+        * XXX: training pattern table appears to be unused for this routine */
+       if (!nvbios_M0205Ep(bios, i, &ver, &hdr, &cnt, &len, &M0205E))
+               return -ENOENT;
+
+       if (M0205E.type != 5)
+               return 0;
+
+       train->state = NVA3_TRAIN_ONCE;
+
+       ret = pfb->ram->get(pfb, 0x8000, 0x10000, 0, 0x800, &ram->ltrain.mem);
+       if (ret)
+               return ret;
+
+       mem = ram->ltrain.mem;
+
+       nv_wr32(pfb, 0x100538, 0x10000000 | (mem->offset >> 16));
+       nv_wr32(pfb, 0x1005a8, 0x0000ffff);
+       nv_mask(pfb, 0x10f800, 0x00000001, 0x00000001);
+
+       for (i = 0; i < 0x30; i++) {
+               nv_wr32(pfb, 0x10f8c0, (i << 8) | i);
+               nv_wr32(pfb, 0x10f900, pattern[i % 16]);
+       }
+
+       for (i = 0; i < 0x30; i++) {
+               nv_wr32(pfb, 0x10f8e0, (i << 8) | i);
+               nv_wr32(pfb, 0x10f920, pattern[i % 16]);
+       }
+
+       /* And upload the pattern */
+       r001700 = nv_rd32(pfb, 0x1700);
+       nv_wr32(pfb, 0x1700, mem->offset >> 16);
+       for (i = 0; i < 16; i++)
+               nv_wr32(pfb, 0x700000 + (i << 2), pattern[i]);
+       for (i = 0; i < 16; i++)
+               nv_wr32(pfb, 0x700100 + (i << 2), pattern[i]);
+       nv_wr32(pfb, 0x1700, r001700);
+
+       train->r_100720 = nv_rd32(pfb, 0x100720);
+       train->r_1111e0 = nv_rd32(pfb, 0x1111e0);
+       train->r_111400 = nv_rd32(pfb, 0x111400);
+       return 0;
+}
+
+void
+gt215_link_train_fini(struct nvkm_fb *pfb)
+{
+       struct gt215_ram *ram = (void *)pfb->ram;
+
+       if (ram->ltrain.mem)
+               pfb->ram->put(pfb, &ram->ltrain.mem);
+}
+
+/*
+ * RAM reclocking
+ */
+#define T(t) cfg->timing_10_##t
+static int
+gt215_ram_timing_calc(struct nvkm_fb *pfb, u32 *timing)
+{
+       struct gt215_ram *ram = (void *)pfb->ram;
+       struct nvbios_ramcfg *cfg = &ram->base.target.bios;
+       int tUNK_base, tUNK_40_0, prevCL;
+       u32 cur2, cur3, cur7, cur8;
+
+       cur2 = nv_rd32(pfb, 0x100228);
+       cur3 = nv_rd32(pfb, 0x10022c);
+       cur7 = nv_rd32(pfb, 0x10023c);
+       cur8 = nv_rd32(pfb, 0x100240);
+
+
+       switch ((!T(CWL)) * ram->base.type) {
+       case NV_MEM_TYPE_DDR2:
+               T(CWL) = T(CL) - 1;
+               break;
+       case NV_MEM_TYPE_GDDR3:
+               T(CWL) = ((cur2 & 0xff000000) >> 24) + 1;
+               break;
+       }
+
+       prevCL = (cur3 & 0x000000ff) + 1;
+       tUNK_base = ((cur7 & 0x00ff0000) >> 16) - prevCL;
+
+       timing[0] = (T(RP) << 24 | T(RAS) << 16 | T(RFC) << 8 | T(RC));
+       timing[1] = (T(WR) + 1 + T(CWL)) << 24 |
+                   max_t(u8,T(18), 1) << 16 |
+                   (T(WTR) + 1 + T(CWL)) << 8 |
+                   (5 + T(CL) - T(CWL));
+       timing[2] = (T(CWL) - 1) << 24 |
+                   (T(RRD) << 16) |
+                   (T(RCDWR) << 8) |
+                   T(RCDRD);
+       timing[3] = (cur3 & 0x00ff0000) |
+                   (0x30 + T(CL)) << 24 |
+                   (0xb + T(CL)) << 8 |
+                   (T(CL) - 1);
+       timing[4] = T(20) << 24 |
+                   T(21) << 16 |
+                   T(13) << 8 |
+                   T(13);
+       timing[5] = T(RFC) << 24 |
+                   max_t(u8,T(RCDRD), T(RCDWR)) << 16 |
+                   max_t(u8, (T(CWL) + 6), (T(CL) + 2)) << 8 |
+                   T(RP);
+       timing[6] = (0x5a + T(CL)) << 16 |
+                   max_t(u8, 1, (6 - T(CL) + T(CWL))) << 8 |
+                   (0x50 + T(CL) - T(CWL));
+       timing[7] = (cur7 & 0xff000000) |
+                   ((tUNK_base + T(CL)) << 16) |
+                   0x202;
+       timing[8] = cur8 & 0xffffff00;
+
+       switch (ram->base.type) {
+       case NV_MEM_TYPE_DDR2:
+       case NV_MEM_TYPE_GDDR3:
+               tUNK_40_0 = prevCL - (cur8 & 0xff);
+               if (tUNK_40_0 > 0)
+                       timing[8] |= T(CL);
+               break;
+       default:
+               break;
+       }
+
+       nv_debug(pfb, "Entry: 220: %08x %08x %08x %08x\n",
+                       timing[0], timing[1], timing[2], timing[3]);
+       nv_debug(pfb, "  230: %08x %08x %08x %08x\n",
+                       timing[4], timing[5], timing[6], timing[7]);
+       nv_debug(pfb, "  240: %08x\n", timing[8]);
+       return 0;
+}
+#undef T
+
+static void
+nvkm_sddr2_dll_reset(struct gt215_ramfuc *fuc)
+{
+       ram_mask(fuc, mr[0], 0x100, 0x100);
+       ram_nsec(fuc, 1000);
+       ram_mask(fuc, mr[0], 0x100, 0x000);
+       ram_nsec(fuc, 1000);
+}
+
+static void
+nvkm_sddr3_dll_disable(struct gt215_ramfuc *fuc, u32 *mr)
+{
+       u32 mr1_old = ram_rd32(fuc, mr[1]);
+
+       if (!(mr1_old & 0x1)) {
+               ram_wr32(fuc, 0x1002d4, 0x00000001);
+               ram_wr32(fuc, mr[1], mr[1]);
+               ram_nsec(fuc, 1000);
+       }
+}
+
+static void
+nvkm_gddr3_dll_disable(struct gt215_ramfuc *fuc, u32 *mr)
+{
+       u32 mr1_old = ram_rd32(fuc, mr[1]);
+
+       if (!(mr1_old & 0x40)) {
+               ram_wr32(fuc, mr[1], mr[1]);
+               ram_nsec(fuc, 1000);
+       }
+}
+
+static void
+gt215_ram_lock_pll(struct gt215_ramfuc *fuc, struct gt215_clk_info *mclk)
+{
+       ram_wr32(fuc, 0x004004, mclk->pll);
+       ram_mask(fuc, 0x004000, 0x00000001, 0x00000001);
+       ram_mask(fuc, 0x004000, 0x00000010, 0x00000000);
+       ram_wait(fuc, 0x004000, 0x00020000, 0x00020000, 64000);
+       ram_mask(fuc, 0x004000, 0x00000010, 0x00000010);
+}
+
+static void
+gt215_ram_fbvref(struct gt215_ramfuc *fuc, u32 val)
+{
+       struct nvkm_gpio *gpio = nvkm_gpio(fuc->base.pfb);
+       struct dcb_gpio_func func;
+       u32 reg, sh, gpio_val;
+       int ret;
+
+       if (gpio->get(gpio, 0, 0x2e, DCB_GPIO_UNUSED) != val) {
+               ret = gpio->find(gpio, 0, 0x2e, DCB_GPIO_UNUSED, &func);
+               if (ret)
+                       return;
+
+               nv50_gpio_location(func.line, &reg, &sh);
+               gpio_val = ram_rd32(fuc, gpioFBVREF);
+               if (gpio_val & (8 << sh))
+                       val = !val;
+
+               ram_mask(fuc, gpioFBVREF, (0x3 << sh), ((val | 0x2) << sh));
+               ram_nsec(fuc, 20000);
+       }
+}
+
+static int
+gt215_ram_calc(struct nvkm_fb *pfb, u32 freq)
+{
+       struct nvkm_bios *bios = nvkm_bios(pfb);
+       struct gt215_ram *ram = (void *)pfb->ram;
+       struct gt215_ramfuc *fuc = &ram->fuc;
+       struct gt215_ltrain *train = &ram->ltrain;
+       struct gt215_clk_info mclk;
+       struct nvkm_ram_data *next;
+       u8  ver, hdr, cnt, len, strap;
+       u32 data;
+       u32 r004018, r100760, r100da0, r111100, ctrl;
+       u32 unk714, unk718, unk71c;
+       int ret, i;
+       u32 timing[9];
+       bool pll2pll;
+
+       next = &ram->base.target;
+       next->freq = freq;
+       ram->base.next = next;
+
+       if (ram->ltrain.state == NVA3_TRAIN_ONCE)
+               gt215_link_train(pfb);
+
+       /* lookup memory config data relevant to the target frequency */
+       i = 0;
+       data = nvbios_rammapEm(bios, freq / 1000, &ver, &hdr, &cnt, &len,
+                              &next->bios);
+       if (!data || ver != 0x10 || hdr < 0x05) {
+               nv_error(pfb, "invalid/missing rammap entry\n");
+               return -EINVAL;
+       }
+
+       /* locate specific data set for the attached memory */
+       strap = nvbios_ramcfg_index(nv_subdev(pfb));
+       if (strap >= cnt) {
+               nv_error(pfb, "invalid ramcfg strap\n");
+               return -EINVAL;
+       }
+
+       data = nvbios_rammapSp(bios, data, ver, hdr, cnt, len, strap,
+                              &ver, &hdr, &next->bios);
+       if (!data || ver != 0x10 || hdr < 0x09) {
+               nv_error(pfb, "invalid/missing ramcfg entry\n");
+               return -EINVAL;
+       }
+
+       /* lookup memory timings, if bios says they're present */
+       if (next->bios.ramcfg_timing != 0xff) {
+               data = nvbios_timingEp(bios, next->bios.ramcfg_timing,
+                                      &ver, &hdr, &cnt, &len,
+                                      &next->bios);
+               if (!data || ver != 0x10 || hdr < 0x17) {
+                       nv_error(pfb, "invalid/missing timing entry\n");
+                       return -EINVAL;
+               }
+       }
+
+       ret = gt215_pll_info(nvkm_clk(pfb), 0x12, 0x4000, freq, &mclk);
+       if (ret < 0) {
+               nv_error(pfb, "failed mclk calculation\n");
+               return ret;
+       }
+
+       gt215_ram_timing_calc(pfb, timing);
+
+       ret = ram_init(fuc, pfb);
+       if (ret)
+               return ret;
+
+       /* Determine ram-specific MR values */
+       ram->base.mr[0] = ram_rd32(fuc, mr[0]);
+       ram->base.mr[1] = ram_rd32(fuc, mr[1]);
+       ram->base.mr[2] = ram_rd32(fuc, mr[2]);
+
+       switch (ram->base.type) {
+       case NV_MEM_TYPE_DDR2:
+               ret = nvkm_sddr2_calc(&ram->base);
+               break;
+       case NV_MEM_TYPE_DDR3:
+               ret = nvkm_sddr3_calc(&ram->base);
+               break;
+       case NV_MEM_TYPE_GDDR3:
+               ret = nvkm_gddr3_calc(&ram->base);
+               break;
+       default:
+               ret = -ENOSYS;
+               break;
+       }
+
+       if (ret)
+               return ret;
+
+       /* XXX: where the fuck does 750MHz come from? */
+       if (freq <= 750000) {
+               r004018 = 0x10000000;
+               r100760 = 0x22222222;
+               r100da0 = 0x00000010;
+       } else {
+               r004018 = 0x00000000;
+               r100760 = 0x00000000;
+               r100da0 = 0x00000000;
+       }
+
+       if (!next->bios.ramcfg_10_DLLoff)
+               r004018 |= 0x00004000;
+
+       /* pll2pll requires to switch to a safe clock first */
+       ctrl = ram_rd32(fuc, 0x004000);
+       pll2pll = (!(ctrl & 0x00000008)) && mclk.pll;
+
+       /* Pre, NVIDIA does this outside the script */
+       if (next->bios.ramcfg_10_02_10) {
+               ram_mask(fuc, 0x111104, 0x00000600, 0x00000000);
+       } else {
+               ram_mask(fuc, 0x111100, 0x40000000, 0x40000000);
+               ram_mask(fuc, 0x111104, 0x00000180, 0x00000000);
+       }
+       /* Always disable this bit during reclock */
+       ram_mask(fuc, 0x100200, 0x00000800, 0x00000000);
+
+       /* If switching from non-pll to pll, lock before disabling FB */
+       if (mclk.pll && !pll2pll) {
+               ram_mask(fuc, 0x004128, 0x003f3141, mclk.clk | 0x00000101);
+               gt215_ram_lock_pll(fuc, &mclk);
+       }
+
+       /* Start with disabling some CRTCs and PFIFO? */
+       ram_wait_vblank(fuc);
+       ram_wr32(fuc, 0x611200, 0x3300);
+       ram_mask(fuc, 0x002504, 0x1, 0x1);
+       ram_nsec(fuc, 10000);
+       ram_wait(fuc, 0x002504, 0x10, 0x10, 20000); /* XXX: or longer? */
+       ram_block(fuc);
+       ram_nsec(fuc, 2000);
+
+       if (!next->bios.ramcfg_10_02_10) {
+               if (ram->base.type == NV_MEM_TYPE_GDDR3)
+                       ram_mask(fuc, 0x111100, 0x04020000, 0x00020000);
+               else
+                       ram_mask(fuc, 0x111100, 0x04020000, 0x04020000);
+       }
+
+       /* If we're disabling the DLL, do it now */
+       switch (next->bios.ramcfg_10_DLLoff * ram->base.type) {
+       case NV_MEM_TYPE_DDR3:
+               nvkm_sddr3_dll_disable(fuc, ram->base.mr);
+               break;
+       case NV_MEM_TYPE_GDDR3:
+               nvkm_gddr3_dll_disable(fuc, ram->base.mr);
+               break;
+       }
+
+       if (fuc->r_gpioFBVREF.addr && next->bios.timing_10_ODT)
+               gt215_ram_fbvref(fuc, 0);
+
+       /* Brace RAM for impact */
+       ram_wr32(fuc, 0x1002d4, 0x00000001);
+       ram_wr32(fuc, 0x1002d0, 0x00000001);
+       ram_wr32(fuc, 0x1002d0, 0x00000001);
+       ram_wr32(fuc, 0x100210, 0x00000000);
+       ram_wr32(fuc, 0x1002dc, 0x00000001);
+       ram_nsec(fuc, 2000);
+
+       if (nv_device(pfb)->chipset == 0xa3 && freq <= 500000)
+               ram_mask(fuc, 0x100700, 0x00000006, 0x00000006);
+
+       /* Fiddle with clocks */
+       /* There's 4 scenario's
+        * pll->pll: first switch to a 324MHz clock, set up new PLL, switch
+        * clk->pll: Set up new PLL, switch
+        * pll->clk: Set up clock, switch
+        * clk->clk: Overwrite ctrl and other bits, switch */
+
+       /* Switch to regular clock - 324MHz */
+       if (pll2pll) {
+               ram_mask(fuc, 0x004000, 0x00000004, 0x00000004);
+               ram_mask(fuc, 0x004168, 0x003f3141, 0x00083101);
+               ram_mask(fuc, 0x004000, 0x00000008, 0x00000008);
+               ram_mask(fuc, 0x1110e0, 0x00088000, 0x00088000);
+               ram_wr32(fuc, 0x004018, 0x00001000);
+               gt215_ram_lock_pll(fuc, &mclk);
+       }
+
+       if (mclk.pll) {
+               ram_mask(fuc, 0x004000, 0x00000105, 0x00000105);
+               ram_wr32(fuc, 0x004018, 0x00001000 | r004018);
+               ram_wr32(fuc, 0x100da0, r100da0);
+       } else {
+               ram_mask(fuc, 0x004168, 0x003f3141, mclk.clk | 0x00000101);
+               ram_mask(fuc, 0x004000, 0x00000108, 0x00000008);
+               ram_mask(fuc, 0x1110e0, 0x00088000, 0x00088000);
+               ram_wr32(fuc, 0x004018, 0x00009000 | r004018);
+               ram_wr32(fuc, 0x100da0, r100da0);
+       }
+       ram_nsec(fuc, 20000);
+
+       if (next->bios.rammap_10_04_08) {
+               ram_wr32(fuc, 0x1005a0, next->bios.ramcfg_10_06 << 16 |
+                                       next->bios.ramcfg_10_05 << 8 |
+                                       next->bios.ramcfg_10_05);
+               ram_wr32(fuc, 0x1005a4, next->bios.ramcfg_10_08 << 8 |
+                                       next->bios.ramcfg_10_07);
+               ram_wr32(fuc, 0x10f804, next->bios.ramcfg_10_09_f0 << 20 |
+                                       next->bios.ramcfg_10_03_0f << 16 |
+                                       next->bios.ramcfg_10_09_0f |
+                                       0x80000000);
+               ram_mask(fuc, 0x10053c, 0x00001000, 0x00000000);
+       } else {
+               if (train->state == NVA3_TRAIN_DONE) {
+                       ram_wr32(fuc, 0x100080, 0x1020);
+                       ram_mask(fuc, 0x111400, 0xffffffff, train->r_111400);
+                       ram_mask(fuc, 0x1111e0, 0xffffffff, train->r_1111e0);
+                       ram_mask(fuc, 0x100720, 0xffffffff, train->r_100720);
+               }
+               ram_mask(fuc, 0x10053c, 0x00001000, 0x00001000);
+               ram_mask(fuc, 0x10f804, 0x80000000, 0x00000000);
+               ram_mask(fuc, 0x100760, 0x22222222, r100760);
+               ram_mask(fuc, 0x1007a0, 0x22222222, r100760);
+               ram_mask(fuc, 0x1007e0, 0x22222222, r100760);
+       }
+
+       if (nv_device(pfb)->chipset == 0xa3 && freq > 500000) {
+               ram_mask(fuc, 0x100700, 0x00000006, 0x00000000);
+       }
+
+       /* Final switch */
+       if (mclk.pll) {
+               ram_mask(fuc, 0x1110e0, 0x00088000, 0x00011000);
+               ram_mask(fuc, 0x004000, 0x00000008, 0x00000000);
+       }
+
+       ram_wr32(fuc, 0x1002dc, 0x00000000);
+       ram_wr32(fuc, 0x1002d4, 0x00000001);
+       ram_wr32(fuc, 0x100210, 0x80000000);
+       ram_nsec(fuc, 2000);
+
+       /* Set RAM MR parameters and timings */
+       for (i = 2; i >= 0; i--) {
+               if (ram_rd32(fuc, mr[i]) != ram->base.mr[i]) {
+                       ram_wr32(fuc, mr[i], ram->base.mr[i]);
+                       ram_nsec(fuc, 1000);
+               }
+       }
+
+       ram_wr32(fuc, 0x100220[3], timing[3]);
+       ram_wr32(fuc, 0x100220[1], timing[1]);
+       ram_wr32(fuc, 0x100220[6], timing[6]);
+       ram_wr32(fuc, 0x100220[7], timing[7]);
+       ram_wr32(fuc, 0x100220[2], timing[2]);
+       ram_wr32(fuc, 0x100220[4], timing[4]);
+       ram_wr32(fuc, 0x100220[5], timing[5]);
+       ram_wr32(fuc, 0x100220[0], timing[0]);
+       ram_wr32(fuc, 0x100220[8], timing[8]);
+
+       /* Misc */
+       ram_mask(fuc, 0x100200, 0x00001000, !next->bios.ramcfg_10_02_08 << 12);
+
+       /* XXX: A lot of "chipset"/"ram type" specific stuff...? */
+       unk714  = ram_rd32(fuc, 0x100714) & ~0xf0000130;
+       unk718  = ram_rd32(fuc, 0x100718) & ~0x00000100;
+       unk71c  = ram_rd32(fuc, 0x10071c) & ~0x00000100;
+       r111100 = ram_rd32(fuc, 0x111100) & ~0x3a800000;
+
+       if (next->bios.ramcfg_10_02_04) {
+               switch (ram->base.type) {
+               case NV_MEM_TYPE_DDR3:
+                       if (nv_device(pfb)->chipset != 0xa8)
+                               r111100 |= 0x00000004;
+                       /* no break */
+               case NV_MEM_TYPE_DDR2:
+                       r111100 |= 0x08000000;
+                       break;
+               default:
+                       break;
+               }
+       } else {
+               switch (ram->base.type) {
+               case NV_MEM_TYPE_DDR2:
+                       r111100 |= 0x1a800000;
+                       unk714  |= 0x00000010;
+                       break;
+               case NV_MEM_TYPE_DDR3:
+                       if (nv_device(pfb)->chipset == 0xa8) {
+                               r111100 |=  0x08000000;
+                       } else {
+                               r111100 &= ~0x00000004;
+                               r111100 |=  0x12800000;
+                       }
+                       unk714  |= 0x00000010;
+                       break;
+               case NV_MEM_TYPE_GDDR3:
+                       r111100 |= 0x30000000;
+                       unk714  |= 0x00000020;
+                       break;
+               default:
+                       break;
+               }
+       }
+
+       unk714 |= (next->bios.ramcfg_10_04_01) << 8;
+
+       if (next->bios.ramcfg_10_02_20)
+               unk714 |= 0xf0000000;
+       if (next->bios.ramcfg_10_02_02)
+               unk718 |= 0x00000100;
+       if (next->bios.ramcfg_10_02_01)
+               unk71c |= 0x00000100;
+       if (next->bios.timing_10_24 != 0xff) {
+               unk718 &= ~0xf0000000;
+               unk718 |= next->bios.timing_10_24 << 28;
+       }
+       if (next->bios.ramcfg_10_02_10)
+               r111100 &= ~0x04020000;
+
+       ram_mask(fuc, 0x100714, 0xffffffff, unk714);
+       ram_mask(fuc, 0x10071c, 0xffffffff, unk71c);
+       ram_mask(fuc, 0x100718, 0xffffffff, unk718);
+       ram_mask(fuc, 0x111100, 0xffffffff, r111100);
+
+       if (fuc->r_gpioFBVREF.addr && !next->bios.timing_10_ODT)
+               gt215_ram_fbvref(fuc, 1);
+
+       /* Reset DLL */
+       if (!next->bios.ramcfg_10_DLLoff)
+               nvkm_sddr2_dll_reset(fuc);
+
+       if (ram->base.type == NV_MEM_TYPE_GDDR3) {
+               ram_nsec(fuc, 31000);
+       } else {
+               ram_nsec(fuc, 14000);
+       }
+
+       if (ram->base.type == NV_MEM_TYPE_DDR3) {
+               ram_wr32(fuc, 0x100264, 0x1);
+               ram_nsec(fuc, 2000);
+       }
+
+       ram_nuke(fuc, 0x100700);
+       ram_mask(fuc, 0x100700, 0x01000000, 0x01000000);
+       ram_mask(fuc, 0x100700, 0x01000000, 0x00000000);
+
+       /* Re-enable FB */
+       ram_unblock(fuc);
+       ram_wr32(fuc, 0x611200, 0x3330);
+
+       /* Post fiddlings */
+       if (next->bios.rammap_10_04_02)
+               ram_mask(fuc, 0x100200, 0x00000800, 0x00000800);
+       if (next->bios.ramcfg_10_02_10) {
+               ram_mask(fuc, 0x111104, 0x00000180, 0x00000180);
+               ram_mask(fuc, 0x111100, 0x40000000, 0x00000000);
+       } else {
+               ram_mask(fuc, 0x111104, 0x00000600, 0x00000600);
+       }
+
+       if (mclk.pll) {
+               ram_mask(fuc, 0x004168, 0x00000001, 0x00000000);
+               ram_mask(fuc, 0x004168, 0x00000100, 0x00000000);
+       } else {
+               ram_mask(fuc, 0x004000, 0x00000001, 0x00000000);
+               ram_mask(fuc, 0x004128, 0x00000001, 0x00000000);
+               ram_mask(fuc, 0x004128, 0x00000100, 0x00000000);
+       }
+
+       return 0;
+}
+
+static int
+gt215_ram_prog(struct nvkm_fb *pfb)
+{
+       struct nvkm_device *device = nv_device(pfb);
+       struct gt215_ram *ram = (void *)pfb->ram;
+       struct gt215_ramfuc *fuc = &ram->fuc;
+       bool exec = nvkm_boolopt(device->cfgopt, "NvMemExec", true);
+
+       if (exec) {
+               nv_mask(pfb, 0x001534, 0x2, 0x2);
+
+               ram_exec(fuc, true);
+
+               /* Post-processing, avoids flicker */
+               nv_mask(pfb, 0x002504, 0x1, 0x0);
+               nv_mask(pfb, 0x001534, 0x2, 0x0);
+
+               nv_mask(pfb, 0x616308, 0x10, 0x10);
+               nv_mask(pfb, 0x616b08, 0x10, 0x10);
+       } else {
+               ram_exec(fuc, false);
+       }
+       return 0;
+}
+
+static void
+gt215_ram_tidy(struct nvkm_fb *pfb)
+{
+       struct gt215_ram *ram = (void *)pfb->ram;
+       struct gt215_ramfuc *fuc = &ram->fuc;
+       ram_exec(fuc, false);
+}
+
+static int
+gt215_ram_init(struct nvkm_object *object)
+{
+       struct nvkm_fb *pfb = (void *)object->parent;
+       struct gt215_ram   *ram = (void *)object;
+       int ret;
+
+       ret = nvkm_ram_init(&ram->base);
+       if (ret)
+               return ret;
+
+       gt215_link_train_init(pfb);
+       return 0;
+}
+
+static int
+gt215_ram_fini(struct nvkm_object *object, bool suspend)
+{
+       struct nvkm_fb *pfb = (void *)object->parent;
+
+       if (!suspend)
+               gt215_link_train_fini(pfb);
+
+       return 0;
+}
+
+static int
+gt215_ram_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+              struct nvkm_oclass *oclass, void *data, u32 datasize,
+              struct nvkm_object **pobject)
+{
+       struct nvkm_fb *pfb = nvkm_fb(parent);
+       struct nvkm_gpio *gpio = nvkm_gpio(pfb);
+       struct dcb_gpio_func func;
+       struct gt215_ram *ram;
+       int ret, i;
+       u32 reg, shift;
+
+       ret = nv50_ram_create(parent, engine, oclass, &ram);
+       *pobject = nv_object(ram);
+       if (ret)
+               return ret;
+
+       switch (ram->base.type) {
+       case NV_MEM_TYPE_DDR2:
+       case NV_MEM_TYPE_DDR3:
+       case NV_MEM_TYPE_GDDR3:
+               ram->base.calc = gt215_ram_calc;
+               ram->base.prog = gt215_ram_prog;
+               ram->base.tidy = gt215_ram_tidy;
+               break;
+       default:
+               nv_warn(ram, "reclocking of this ram type unsupported\n");
+               return 0;
+       }
+
+       ram->fuc.r_0x001610 = ramfuc_reg(0x001610);
+       ram->fuc.r_0x001700 = ramfuc_reg(0x001700);
+       ram->fuc.r_0x002504 = ramfuc_reg(0x002504);
+       ram->fuc.r_0x004000 = ramfuc_reg(0x004000);
+       ram->fuc.r_0x004004 = ramfuc_reg(0x004004);
+       ram->fuc.r_0x004018 = ramfuc_reg(0x004018);
+       ram->fuc.r_0x004128 = ramfuc_reg(0x004128);
+       ram->fuc.r_0x004168 = ramfuc_reg(0x004168);
+       ram->fuc.r_0x100080 = ramfuc_reg(0x100080);
+       ram->fuc.r_0x100200 = ramfuc_reg(0x100200);
+       ram->fuc.r_0x100210 = ramfuc_reg(0x100210);
+       for (i = 0; i < 9; i++)
+               ram->fuc.r_0x100220[i] = ramfuc_reg(0x100220 + (i * 4));
+       ram->fuc.r_0x100264 = ramfuc_reg(0x100264);
+       ram->fuc.r_0x1002d0 = ramfuc_reg(0x1002d0);
+       ram->fuc.r_0x1002d4 = ramfuc_reg(0x1002d4);
+       ram->fuc.r_0x1002dc = ramfuc_reg(0x1002dc);
+       ram->fuc.r_0x10053c = ramfuc_reg(0x10053c);
+       ram->fuc.r_0x1005a0 = ramfuc_reg(0x1005a0);
+       ram->fuc.r_0x1005a4 = ramfuc_reg(0x1005a4);
+       ram->fuc.r_0x100700 = ramfuc_reg(0x100700);
+       ram->fuc.r_0x100714 = ramfuc_reg(0x100714);
+       ram->fuc.r_0x100718 = ramfuc_reg(0x100718);
+       ram->fuc.r_0x10071c = ramfuc_reg(0x10071c);
+       ram->fuc.r_0x100720 = ramfuc_reg(0x100720);
+       ram->fuc.r_0x100760 = ramfuc_stride(0x100760, 4, ram->base.part_mask);
+       ram->fuc.r_0x1007a0 = ramfuc_stride(0x1007a0, 4, ram->base.part_mask);
+       ram->fuc.r_0x1007e0 = ramfuc_stride(0x1007e0, 4, ram->base.part_mask);
+       ram->fuc.r_0x100da0 = ramfuc_stride(0x100da0, 4, ram->base.part_mask);
+       ram->fuc.r_0x10f804 = ramfuc_reg(0x10f804);
+       ram->fuc.r_0x1110e0 = ramfuc_stride(0x1110e0, 4, ram->base.part_mask);
+       ram->fuc.r_0x111100 = ramfuc_reg(0x111100);
+       ram->fuc.r_0x111104 = ramfuc_reg(0x111104);
+       ram->fuc.r_0x1111e0 = ramfuc_reg(0x1111e0);
+       ram->fuc.r_0x111400 = ramfuc_reg(0x111400);
+       ram->fuc.r_0x611200 = ramfuc_reg(0x611200);
+
+       if (ram->base.ranks > 1) {
+               ram->fuc.r_mr[0] = ramfuc_reg2(0x1002c0, 0x1002c8);
+               ram->fuc.r_mr[1] = ramfuc_reg2(0x1002c4, 0x1002cc);
+               ram->fuc.r_mr[2] = ramfuc_reg2(0x1002e0, 0x1002e8);
+               ram->fuc.r_mr[3] = ramfuc_reg2(0x1002e4, 0x1002ec);
+       } else {
+               ram->fuc.r_mr[0] = ramfuc_reg(0x1002c0);
+               ram->fuc.r_mr[1] = ramfuc_reg(0x1002c4);
+               ram->fuc.r_mr[2] = ramfuc_reg(0x1002e0);
+               ram->fuc.r_mr[3] = ramfuc_reg(0x1002e4);
+       }
+
+       ret = gpio->find(gpio, 0, 0x2e, DCB_GPIO_UNUSED, &func);
+       if (ret == 0) {
+               nv50_gpio_location(func.line, &reg, &shift);
+               ram->fuc.r_gpioFBVREF = ramfuc_reg(reg);
+       }
+
+       return 0;
+}
+
+struct nvkm_oclass
+gt215_ram_oclass = {
+       .ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = gt215_ram_ctor,
+               .dtor = _nvkm_ram_dtor,
+               .init = gt215_ram_init,
+               .fini = gt215_ram_fini,
+       },
+};
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/fb/rammcp77.c b/drivers/gpu/drm/nouveau/nvkm/subdev/fb/rammcp77.c
new file mode 100644 (file)
index 0000000..abc18e8
--- /dev/null
@@ -0,0 +1,101 @@
+/*
+ * Copyright 2013 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 "nv50.h"
+
+struct mcp77_ram_priv {
+       struct nvkm_ram base;
+       u64 poller_base;
+};
+
+static int
+mcp77_ram_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+              struct nvkm_oclass *oclass, void *data, u32 datasize,
+              struct nvkm_object **pobject)
+{
+       u32 rsvd_head = ( 256 * 1024); /* vga memory */
+       u32 rsvd_tail = (1024 * 1024); /* vbios etc */
+       struct nvkm_fb *pfb = nvkm_fb(parent);
+       struct mcp77_ram_priv *priv;
+       int ret;
+
+       ret = nvkm_ram_create(parent, engine, oclass, &priv);
+       *pobject = nv_object(priv);
+       if (ret)
+               return ret;
+
+       priv->base.type   = NV_MEM_TYPE_STOLEN;
+       priv->base.stolen = (u64)nv_rd32(pfb, 0x100e10) << 12;
+       priv->base.size   = (u64)nv_rd32(pfb, 0x100e14) << 12;
+
+       rsvd_tail += 0x1000;
+       priv->poller_base = priv->base.size - rsvd_tail;
+
+       ret = nvkm_mm_init(&pfb->vram, rsvd_head >> 12,
+                          (priv->base.size  - (rsvd_head + rsvd_tail)) >> 12,
+                          1);
+       if (ret)
+               return ret;
+
+       priv->base.get = nv50_ram_get;
+       priv->base.put = nv50_ram_put;
+       return 0;
+}
+
+static int
+mcp77_ram_init(struct nvkm_object *object)
+{
+       struct nvkm_fb *pfb = nvkm_fb(object);
+       struct mcp77_ram_priv *priv = (void *)object;
+       int ret;
+       u64 dniso, hostnb, flush;
+
+       ret = nvkm_ram_init(&priv->base);
+       if (ret)
+               return ret;
+
+       dniso  = ((priv->base.size - (priv->poller_base + 0x00)) >> 5) - 1;
+       hostnb = ((priv->base.size - (priv->poller_base + 0x20)) >> 5) - 1;
+       flush  = ((priv->base.size - (priv->poller_base + 0x40)) >> 5) - 1;
+
+       /* Enable NISO poller for various clients and set their associated
+        * read address, only for MCP77/78 and MCP79/7A. (fd#25701)
+        */
+       nv_wr32(pfb, 0x100c18, dniso);
+       nv_mask(pfb, 0x100c14, 0x00000000, 0x00000001);
+       nv_wr32(pfb, 0x100c1c, hostnb);
+       nv_mask(pfb, 0x100c14, 0x00000000, 0x00000002);
+       nv_wr32(pfb, 0x100c24, flush);
+       nv_mask(pfb, 0x100c14, 0x00000000, 0x00010000);
+       return 0;
+}
+
+struct nvkm_oclass
+mcp77_ram_oclass = {
+       .ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = mcp77_ram_ctor,
+               .dtor = _nvkm_ram_dtor,
+               .init = mcp77_ram_init,
+               .fini = _nvkm_ram_fini,
+       },
+};
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/fb/ramnv04.c b/drivers/gpu/drm/nouveau/nvkm/subdev/fb/ramnv04.c
new file mode 100644 (file)
index 0000000..855de16
--- /dev/null
@@ -0,0 +1,79 @@
+/*
+ * Copyright 2013 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 "priv.h"
+#include "regsnv04.h"
+
+static int
+nv04_ram_create(struct nvkm_object *parent, struct nvkm_object *engine,
+               struct nvkm_oclass *oclass, void *data, u32 size,
+               struct nvkm_object **pobject)
+{
+       struct nvkm_fb *pfb = nvkm_fb(parent);
+       struct nvkm_ram *ram;
+       u32 boot0 = nv_rd32(pfb, NV04_PFB_BOOT_0);
+       int ret;
+
+       ret = nvkm_ram_create(parent, engine, oclass, &ram);
+       *pobject = nv_object(ram);
+       if (ret)
+               return ret;
+
+       if (boot0 & 0x00000100) {
+               ram->size  = ((boot0 >> 12) & 0xf) * 2 + 2;
+               ram->size *= 1024 * 1024;
+       } else {
+               switch (boot0 & NV04_PFB_BOOT_0_RAM_AMOUNT) {
+               case NV04_PFB_BOOT_0_RAM_AMOUNT_32MB:
+                       ram->size = 32 * 1024 * 1024;
+                       break;
+               case NV04_PFB_BOOT_0_RAM_AMOUNT_16MB:
+                       ram->size = 16 * 1024 * 1024;
+                       break;
+               case NV04_PFB_BOOT_0_RAM_AMOUNT_8MB:
+                       ram->size = 8 * 1024 * 1024;
+                       break;
+               case NV04_PFB_BOOT_0_RAM_AMOUNT_4MB:
+                       ram->size = 4 * 1024 * 1024;
+                       break;
+               }
+       }
+
+       if ((boot0 & 0x00000038) <= 0x10)
+               ram->type = NV_MEM_TYPE_SGRAM;
+       else
+               ram->type = NV_MEM_TYPE_SDRAM;
+
+       return 0;
+}
+
+struct nvkm_oclass
+nv04_ram_oclass = {
+       .handle = 0,
+       .ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = nv04_ram_create,
+               .dtor = _nvkm_ram_dtor,
+               .init = _nvkm_ram_init,
+               .fini = _nvkm_ram_fini,
+       }
+};
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/fb/ramnv10.c b/drivers/gpu/drm/nouveau/nvkm/subdev/fb/ramnv10.c
new file mode 100644 (file)
index 0000000..3b8a1ed
--- /dev/null
@@ -0,0 +1,59 @@
+/*
+ * Copyright 2013 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 "priv.h"
+
+static int
+nv10_ram_create(struct nvkm_object *parent, struct nvkm_object *engine,
+               struct nvkm_oclass *oclass, void *data, u32 size,
+               struct nvkm_object **pobject)
+{
+       struct nvkm_fb *pfb = nvkm_fb(parent);
+       struct nvkm_ram *ram;
+       u32 cfg0 = nv_rd32(pfb, 0x100200);
+       int ret;
+
+       ret = nvkm_ram_create(parent, engine, oclass, &ram);
+       *pobject = nv_object(ram);
+       if (ret)
+               return ret;
+
+       if (cfg0 & 0x00000001)
+               ram->type = NV_MEM_TYPE_DDR1;
+       else
+               ram->type = NV_MEM_TYPE_SDRAM;
+
+       ram->size = nv_rd32(pfb, 0x10020c) & 0xff000000;
+       return 0;
+}
+
+struct nvkm_oclass
+nv10_ram_oclass = {
+       .handle = 0,
+       .ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = nv10_ram_create,
+               .dtor = _nvkm_ram_dtor,
+               .init = _nvkm_ram_init,
+               .fini = _nvkm_ram_fini,
+       }
+};
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/fb/ramnv1a.c b/drivers/gpu/drm/nouveau/nvkm/subdev/fb/ramnv1a.c
new file mode 100644 (file)
index 0000000..fbae05d
--- /dev/null
@@ -0,0 +1,72 @@
+/*
+ * Copyright 2013 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 "priv.h"
+
+#include <core/device.h>
+
+static int
+nv1a_ram_create(struct nvkm_object *parent, struct nvkm_object *engine,
+               struct nvkm_oclass *oclass, void *data, u32 size,
+               struct nvkm_object **pobject)
+{
+       struct nvkm_fb *pfb = nvkm_fb(parent);
+       struct nvkm_ram *ram;
+       struct pci_dev *bridge;
+       u32 mem, mib;
+       int ret;
+
+       bridge = pci_get_bus_and_slot(0, PCI_DEVFN(0, 1));
+       if (!bridge) {
+               nv_fatal(pfb, "no bridge device\n");
+               return -ENODEV;
+       }
+
+       ret = nvkm_ram_create(parent, engine, oclass, &ram);
+       *pobject = nv_object(ram);
+       if (ret)
+               return ret;
+
+       if (nv_device(pfb)->chipset == 0x1a) {
+               pci_read_config_dword(bridge, 0x7c, &mem);
+               mib = ((mem >> 6) & 31) + 1;
+       } else {
+               pci_read_config_dword(bridge, 0x84, &mem);
+               mib = ((mem >> 4) & 127) + 1;
+       }
+
+       ram->type = NV_MEM_TYPE_STOLEN;
+       ram->size = mib * 1024 * 1024;
+       return 0;
+}
+
+struct nvkm_oclass
+nv1a_ram_oclass = {
+       .handle = 0,
+       .ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = nv1a_ram_create,
+               .dtor = _nvkm_ram_dtor,
+               .init = _nvkm_ram_init,
+               .fini = _nvkm_ram_fini,
+       }
+};
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/fb/ramnv20.c b/drivers/gpu/drm/nouveau/nvkm/subdev/fb/ramnv20.c
new file mode 100644 (file)
index 0000000..d9e7187
--- /dev/null
@@ -0,0 +1,62 @@
+/*
+ * Copyright 2013 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 "priv.h"
+
+static int
+nv20_ram_create(struct nvkm_object *parent, struct nvkm_object *engine,
+               struct nvkm_oclass *oclass, void *data, u32 size,
+               struct nvkm_object **pobject)
+{
+       struct nvkm_fb *pfb = nvkm_fb(parent);
+       struct nvkm_ram *ram;
+       u32 pbus1218 = nv_rd32(pfb, 0x001218);
+       int ret;
+
+       ret = nvkm_ram_create(parent, engine, oclass, &ram);
+       *pobject = nv_object(ram);
+       if (ret)
+               return ret;
+
+       switch (pbus1218 & 0x00000300) {
+       case 0x00000000: ram->type = NV_MEM_TYPE_SDRAM; break;
+       case 0x00000100: ram->type = NV_MEM_TYPE_DDR1; break;
+       case 0x00000200: ram->type = NV_MEM_TYPE_GDDR3; break;
+       case 0x00000300: ram->type = NV_MEM_TYPE_GDDR2; break;
+       }
+       ram->size  = (nv_rd32(pfb, 0x10020c) & 0xff000000);
+       ram->parts = (nv_rd32(pfb, 0x100200) & 0x00000003) + 1;
+       ram->tags  = nv_rd32(pfb, 0x100320);
+       return 0;
+}
+
+struct nvkm_oclass
+nv20_ram_oclass = {
+       .handle = 0,
+       .ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = nv20_ram_create,
+               .dtor = _nvkm_ram_dtor,
+               .init = _nvkm_ram_init,
+               .fini = _nvkm_ram_fini,
+       }
+};
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/fb/ramnv40.c b/drivers/gpu/drm/nouveau/nvkm/subdev/fb/ramnv40.c
new file mode 100644 (file)
index 0000000..3d31fa4
--- /dev/null
@@ -0,0 +1,212 @@
+/*
+ * Copyright 2013 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 "nv40.h"
+
+#include <core/device.h>
+#include <subdev/bios.h>
+#include <subdev/bios/bit.h>
+#include <subdev/bios/init.h>
+#include <subdev/bios/pll.h>
+#include <subdev/clk/pll.h>
+#include <subdev/timer.h>
+
+int
+nv40_ram_calc(struct nvkm_fb *pfb, u32 freq)
+{
+       struct nvkm_bios *bios = nvkm_bios(pfb);
+       struct nv40_ram *ram = (void *)pfb->ram;
+       struct nvbios_pll pll;
+       int N1, M1, N2, M2;
+       int log2P, ret;
+
+       ret = nvbios_pll_parse(bios, 0x04, &pll);
+       if (ret) {
+               nv_error(pfb, "mclk pll data not found\n");
+               return ret;
+       }
+
+       ret = nv04_pll_calc(nv_subdev(pfb), &pll, freq,
+                           &N1, &M1, &N2, &M2, &log2P);
+       if (ret < 0)
+               return ret;
+
+       ram->ctrl  = 0x80000000 | (log2P << 16);
+       ram->ctrl |= min(pll.bias_p + log2P, (int)pll.max_p) << 20;
+       if (N2 == M2) {
+               ram->ctrl |= 0x00000100;
+               ram->coef  = (N1 << 8) | M1;
+       } else {
+               ram->ctrl |= 0x40000000;
+               ram->coef  = (N2 << 24) | (M2 << 16) | (N1 << 8) | M1;
+       }
+
+       return 0;
+}
+
+int
+nv40_ram_prog(struct nvkm_fb *pfb)
+{
+       struct nvkm_bios *bios = nvkm_bios(pfb);
+       struct nv40_ram *ram = (void *)pfb->ram;
+       struct bit_entry M;
+       u32 crtc_mask = 0;
+       u8  sr1[2];
+       int i;
+
+       /* determine which CRTCs are active, fetch VGA_SR1 for each */
+       for (i = 0; i < 2; i++) {
+               u32 vbl = nv_rd32(pfb, 0x600808 + (i * 0x2000));
+               u32 cnt = 0;
+               do {
+                       if (vbl != nv_rd32(pfb, 0x600808 + (i * 0x2000))) {
+                               nv_wr08(pfb, 0x0c03c4 + (i * 0x2000), 0x01);
+                               sr1[i] = nv_rd08(pfb, 0x0c03c5 + (i * 0x2000));
+                               if (!(sr1[i] & 0x20))
+                                       crtc_mask |= (1 << i);
+                               break;
+                       }
+                       udelay(1);
+               } while (cnt++ < 32);
+       }
+
+       /* wait for vblank start on active crtcs, disable memory access */
+       for (i = 0; i < 2; i++) {
+               if (!(crtc_mask & (1 << i)))
+                       continue;
+               nv_wait(pfb, 0x600808 + (i * 0x2000), 0x00010000, 0x00000000);
+               nv_wait(pfb, 0x600808 + (i * 0x2000), 0x00010000, 0x00010000);
+               nv_wr08(pfb, 0x0c03c4 + (i * 0x2000), 0x01);
+               nv_wr08(pfb, 0x0c03c5 + (i * 0x2000), sr1[i] | 0x20);
+       }
+
+       /* prepare ram for reclocking */
+       nv_wr32(pfb, 0x1002d4, 0x00000001); /* precharge */
+       nv_wr32(pfb, 0x1002d0, 0x00000001); /* refresh */
+       nv_wr32(pfb, 0x1002d0, 0x00000001); /* refresh */
+       nv_mask(pfb, 0x100210, 0x80000000, 0x00000000); /* no auto refresh */
+       nv_wr32(pfb, 0x1002dc, 0x00000001); /* enable self-refresh */
+
+       /* change the PLL of each memory partition */
+       nv_mask(pfb, 0x00c040, 0x0000c000, 0x00000000);
+       switch (nv_device(pfb)->chipset) {
+       case 0x40:
+       case 0x45:
+       case 0x41:
+       case 0x42:
+       case 0x47:
+               nv_mask(pfb, 0x004044, 0xc0771100, ram->ctrl);
+               nv_mask(pfb, 0x00402c, 0xc0771100, ram->ctrl);
+               nv_wr32(pfb, 0x004048, ram->coef);
+               nv_wr32(pfb, 0x004030, ram->coef);
+       case 0x43:
+       case 0x49:
+       case 0x4b:
+               nv_mask(pfb, 0x004038, 0xc0771100, ram->ctrl);
+               nv_wr32(pfb, 0x00403c, ram->coef);
+       default:
+               nv_mask(pfb, 0x004020, 0xc0771100, ram->ctrl);
+               nv_wr32(pfb, 0x004024, ram->coef);
+               break;
+       }
+       udelay(100);
+       nv_mask(pfb, 0x00c040, 0x0000c000, 0x0000c000);
+
+       /* re-enable normal operation of memory controller */
+       nv_wr32(pfb, 0x1002dc, 0x00000000);
+       nv_mask(pfb, 0x100210, 0x80000000, 0x80000000);
+       udelay(100);
+
+       /* execute memory reset script from vbios */
+       if (!bit_entry(bios, 'M', &M)) {
+               struct nvbios_init init = {
+                       .subdev = nv_subdev(pfb),
+                       .bios = bios,
+                       .offset = nv_ro16(bios, M.offset + 0x00),
+                       .execute = 1,
+               };
+
+               nvbios_exec(&init);
+       }
+
+       /* make sure we're in vblank (hopefully the same one as before), and
+        * then re-enable crtc memory access
+        */
+       for (i = 0; i < 2; i++) {
+               if (!(crtc_mask & (1 << i)))
+                       continue;
+               nv_wait(pfb, 0x600808 + (i * 0x2000), 0x00010000, 0x00010000);
+               nv_wr08(pfb, 0x0c03c4 + (i * 0x2000), 0x01);
+               nv_wr08(pfb, 0x0c03c5 + (i * 0x2000), sr1[i]);
+       }
+
+       return 0;
+}
+
+void
+nv40_ram_tidy(struct nvkm_fb *pfb)
+{
+}
+
+static int
+nv40_ram_create(struct nvkm_object *parent, struct nvkm_object *engine,
+               struct nvkm_oclass *oclass, void *data, u32 size,
+               struct nvkm_object **pobject)
+{
+       struct nvkm_fb *pfb = nvkm_fb(parent);
+       struct nv40_ram *ram;
+       u32 pbus1218 = nv_rd32(pfb, 0x001218);
+       int ret;
+
+       ret = nvkm_ram_create(parent, engine, oclass, &ram);
+       *pobject = nv_object(ram);
+       if (ret)
+               return ret;
+
+       switch (pbus1218 & 0x00000300) {
+       case 0x00000000: ram->base.type = NV_MEM_TYPE_SDRAM; break;
+       case 0x00000100: ram->base.type = NV_MEM_TYPE_DDR1; break;
+       case 0x00000200: ram->base.type = NV_MEM_TYPE_GDDR3; break;
+       case 0x00000300: ram->base.type = NV_MEM_TYPE_DDR2; break;
+       }
+
+       ram->base.size  =  nv_rd32(pfb, 0x10020c) & 0xff000000;
+       ram->base.parts = (nv_rd32(pfb, 0x100200) & 0x00000003) + 1;
+       ram->base.tags  =  nv_rd32(pfb, 0x100320);
+       ram->base.calc = nv40_ram_calc;
+       ram->base.prog = nv40_ram_prog;
+       ram->base.tidy = nv40_ram_tidy;
+       return 0;
+}
+
+
+struct nvkm_oclass
+nv40_ram_oclass = {
+       .handle = 0,
+       .ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = nv40_ram_create,
+               .dtor = _nvkm_ram_dtor,
+               .init = _nvkm_ram_init,
+               .fini = _nvkm_ram_fini,
+       }
+};
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/fb/ramnv41.c b/drivers/gpu/drm/nouveau/nvkm/subdev/fb/ramnv41.c
new file mode 100644 (file)
index 0000000..33c612b
--- /dev/null
@@ -0,0 +1,66 @@
+/*
+ * Copyright 2013 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 "nv40.h"
+
+static int
+nv41_ram_create(struct nvkm_object *parent, struct nvkm_object *engine,
+               struct nvkm_oclass *oclass, void *data, u32 size,
+               struct nvkm_object **pobject)
+{
+       struct nvkm_fb *pfb = nvkm_fb(parent);
+       struct nv40_ram *ram;
+       u32 pfb474 = nv_rd32(pfb, 0x100474);
+       int ret;
+
+       ret = nvkm_ram_create(parent, engine, oclass, &ram);
+       *pobject = nv_object(ram);
+       if (ret)
+               return ret;
+
+       if (pfb474 & 0x00000004)
+               ram->base.type = NV_MEM_TYPE_GDDR3;
+       if (pfb474 & 0x00000002)
+               ram->base.type = NV_MEM_TYPE_DDR2;
+       if (pfb474 & 0x00000001)
+               ram->base.type = NV_MEM_TYPE_DDR1;
+
+       ram->base.size  =  nv_rd32(pfb, 0x10020c) & 0xff000000;
+       ram->base.parts = (nv_rd32(pfb, 0x100200) & 0x00000003) + 1;
+       ram->base.tags  =  nv_rd32(pfb, 0x100320);
+       ram->base.calc = nv40_ram_calc;
+       ram->base.prog = nv40_ram_prog;
+       ram->base.tidy = nv40_ram_tidy;
+       return 0;
+}
+
+struct nvkm_oclass
+nv41_ram_oclass = {
+       .handle = 0,
+       .ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = nv41_ram_create,
+               .dtor = _nvkm_ram_dtor,
+               .init = _nvkm_ram_init,
+               .fini = _nvkm_ram_fini,
+       }
+};
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/fb/ramnv44.c b/drivers/gpu/drm/nouveau/nvkm/subdev/fb/ramnv44.c
new file mode 100644 (file)
index 0000000..f575a72
--- /dev/null
@@ -0,0 +1,64 @@
+/*
+ * Copyright 2013 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 "nv40.h"
+
+static int
+nv44_ram_create(struct nvkm_object *parent, struct nvkm_object *engine,
+               struct nvkm_oclass *oclass, void *data, u32 size,
+               struct nvkm_object **pobject)
+{
+       struct nvkm_fb *pfb = nvkm_fb(parent);
+       struct nv40_ram *ram;
+       u32 pfb474 = nv_rd32(pfb, 0x100474);
+       int ret;
+
+       ret = nvkm_ram_create(parent, engine, oclass, &ram);
+       *pobject = nv_object(ram);
+       if (ret)
+               return ret;
+
+       if (pfb474 & 0x00000004)
+               ram->base.type = NV_MEM_TYPE_GDDR3;
+       if (pfb474 & 0x00000002)
+               ram->base.type = NV_MEM_TYPE_DDR2;
+       if (pfb474 & 0x00000001)
+               ram->base.type = NV_MEM_TYPE_DDR1;
+
+       ram->base.size = nv_rd32(pfb, 0x10020c) & 0xff000000;
+       ram->base.calc = nv40_ram_calc;
+       ram->base.prog = nv40_ram_prog;
+       ram->base.tidy = nv40_ram_tidy;
+       return 0;
+}
+
+struct nvkm_oclass
+nv44_ram_oclass = {
+       .handle = 0,
+       .ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = nv44_ram_create,
+               .dtor = _nvkm_ram_dtor,
+               .init = _nvkm_ram_init,
+               .fini = _nvkm_ram_fini,
+       }
+};
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/fb/ramnv49.c b/drivers/gpu/drm/nouveau/nvkm/subdev/fb/ramnv49.c
new file mode 100644 (file)
index 0000000..51b44cd
--- /dev/null
@@ -0,0 +1,66 @@
+/*
+ * Copyright 2013 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 "nv40.h"
+
+static int
+nv49_ram_create(struct nvkm_object *parent, struct nvkm_object *engine,
+               struct nvkm_oclass *oclass, void *data, u32 size,
+               struct nvkm_object **pobject)
+{
+       struct nvkm_fb *pfb = nvkm_fb(parent);
+       struct nv40_ram *ram;
+       u32 pfb914 = nv_rd32(pfb, 0x100914);
+       int ret;
+
+       ret = nvkm_ram_create(parent, engine, oclass, &ram);
+       *pobject = nv_object(ram);
+       if (ret)
+               return ret;
+
+       switch (pfb914 & 0x00000003) {
+       case 0x00000000: ram->base.type = NV_MEM_TYPE_DDR1; break;
+       case 0x00000001: ram->base.type = NV_MEM_TYPE_DDR2; break;
+       case 0x00000002: ram->base.type = NV_MEM_TYPE_GDDR3; break;
+       case 0x00000003: break;
+       }
+
+       ram->base.size  =  nv_rd32(pfb, 0x10020c) & 0xff000000;
+       ram->base.parts = (nv_rd32(pfb, 0x100200) & 0x00000003) + 1;
+       ram->base.tags  =  nv_rd32(pfb, 0x100320);
+       ram->base.calc = nv40_ram_calc;
+       ram->base.prog = nv40_ram_prog;
+       ram->base.tidy = nv40_ram_tidy;
+       return 0;
+}
+
+struct nvkm_oclass
+nv49_ram_oclass = {
+       .handle = 0,
+       .ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = nv49_ram_create,
+               .dtor = _nvkm_ram_dtor,
+               .init = _nvkm_ram_init,
+               .fini = _nvkm_ram_fini,
+       }
+};
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/fb/ramnv4e.c b/drivers/gpu/drm/nouveau/nvkm/subdev/fb/ramnv4e.c
new file mode 100644 (file)
index 0000000..f3ed1c6
--- /dev/null
@@ -0,0 +1,54 @@
+/*
+ * Copyright 2013 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 "priv.h"
+
+static int
+nv4e_ram_create(struct nvkm_object *parent, struct nvkm_object *engine,
+               struct nvkm_oclass *oclass, void *data, u32 size,
+               struct nvkm_object **pobject)
+{
+       struct nvkm_fb *pfb = nvkm_fb(parent);
+       struct nvkm_ram *ram;
+       int ret;
+
+       ret = nvkm_ram_create(parent, engine, oclass, &ram);
+       *pobject = nv_object(ram);
+       if (ret)
+               return ret;
+
+       ram->size = nv_rd32(pfb, 0x10020c) & 0xff000000;
+       ram->type = NV_MEM_TYPE_STOLEN;
+       return 0;
+}
+
+struct nvkm_oclass
+nv4e_ram_oclass = {
+       .handle = 0,
+       .ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = nv4e_ram_create,
+               .dtor = _nvkm_ram_dtor,
+               .init = _nvkm_ram_init,
+               .fini = _nvkm_ram_fini,
+       }
+};
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/fb/ramnv50.c b/drivers/gpu/drm/nouveau/nvkm/subdev/fb/ramnv50.c
new file mode 100644 (file)
index 0000000..d2c81dd
--- /dev/null
@@ -0,0 +1,465 @@
+/*
+ * Copyright 2013 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 "nv50.h"
+#include "ramseq.h"
+
+#include <core/device.h>
+#include <core/option.h>
+#include <subdev/bios.h>
+#include <subdev/bios/perf.h>
+#include <subdev/bios/pll.h>
+#include <subdev/bios/timing.h>
+#include <subdev/clk/pll.h>
+
+struct nv50_ramseq {
+       struct hwsq base;
+       struct hwsq_reg r_0x002504;
+       struct hwsq_reg r_0x004008;
+       struct hwsq_reg r_0x00400c;
+       struct hwsq_reg r_0x00c040;
+       struct hwsq_reg r_0x100210;
+       struct hwsq_reg r_0x1002d0;
+       struct hwsq_reg r_0x1002d4;
+       struct hwsq_reg r_0x1002dc;
+       struct hwsq_reg r_0x100da0[8];
+       struct hwsq_reg r_0x100e20;
+       struct hwsq_reg r_0x100e24;
+       struct hwsq_reg r_0x611200;
+       struct hwsq_reg r_timing[9];
+       struct hwsq_reg r_mr[4];
+};
+
+struct nv50_ram {
+       struct nvkm_ram base;
+       struct nv50_ramseq hwsq;
+};
+
+#define QFX5800NVA0 1
+
+static int
+nv50_ram_calc(struct nvkm_fb *pfb, u32 freq)
+{
+       struct nvkm_bios *bios = nvkm_bios(pfb);
+       struct nv50_ram *ram = (void *)pfb->ram;
+       struct nv50_ramseq *hwsq = &ram->hwsq;
+       struct nvbios_perfE perfE;
+       struct nvbios_pll mpll;
+       struct {
+               u32 data;
+               u8  size;
+       } ramcfg, timing;
+       u8  ver, hdr, cnt, len, strap;
+       int N1, M1, N2, M2, P;
+       int ret, i;
+
+       /* lookup closest matching performance table entry for frequency */
+       i = 0;
+       do {
+               ramcfg.data = nvbios_perfEp(bios, i++, &ver, &hdr, &cnt,
+                                           &ramcfg.size, &perfE);
+               if (!ramcfg.data || (ver < 0x25 || ver >= 0x40) ||
+                   (ramcfg.size < 2)) {
+                       nv_error(pfb, "invalid/missing perftab entry\n");
+                       return -EINVAL;
+               }
+       } while (perfE.memory < freq);
+
+       /* locate specific data set for the attached memory */
+       strap = nvbios_ramcfg_index(nv_subdev(pfb));
+       if (strap >= cnt) {
+               nv_error(pfb, "invalid ramcfg strap\n");
+               return -EINVAL;
+       }
+
+       ramcfg.data += hdr + (strap * ramcfg.size);
+
+       /* lookup memory timings, if bios says they're present */
+       strap = nv_ro08(bios, ramcfg.data + 0x01);
+       if (strap != 0xff) {
+               timing.data = nvbios_timingEe(bios, strap, &ver, &hdr,
+                                             &cnt, &len);
+               if (!timing.data || ver != 0x10 || hdr < 0x12) {
+                       nv_error(pfb, "invalid/missing timing entry "
+                                "%02x %04x %02x %02x\n",
+                                strap, timing.data, ver, hdr);
+                       return -EINVAL;
+               }
+       } else {
+               timing.data = 0;
+       }
+
+       ret = ram_init(hwsq, nv_subdev(pfb));
+       if (ret)
+               return ret;
+
+       ram_wait(hwsq, 0x01, 0x00); /* wait for !vblank */
+       ram_wait(hwsq, 0x01, 0x01); /* wait for vblank */
+       ram_wr32(hwsq, 0x611200, 0x00003300);
+       ram_wr32(hwsq, 0x002504, 0x00000001); /* block fifo */
+       ram_nsec(hwsq, 8000);
+       ram_setf(hwsq, 0x10, 0x00); /* disable fb */
+       ram_wait(hwsq, 0x00, 0x01); /* wait for fb disabled */
+
+       ram_wr32(hwsq, 0x1002d4, 0x00000001); /* precharge */
+       ram_wr32(hwsq, 0x1002d0, 0x00000001); /* refresh */
+       ram_wr32(hwsq, 0x1002d0, 0x00000001); /* refresh */
+       ram_wr32(hwsq, 0x100210, 0x00000000); /* disable auto-refresh */
+       ram_wr32(hwsq, 0x1002dc, 0x00000001); /* enable self-refresh */
+
+       ret = nvbios_pll_parse(bios, 0x004008, &mpll);
+       mpll.vco2.max_freq = 0;
+       if (ret == 0) {
+               ret = nv04_pll_calc(nv_subdev(pfb), &mpll, freq,
+                                   &N1, &M1, &N2, &M2, &P);
+               if (ret == 0)
+                       ret = -EINVAL;
+       }
+
+       if (ret < 0)
+               return ret;
+
+       ram_mask(hwsq, 0x00c040, 0xc000c000, 0x0000c000);
+       ram_mask(hwsq, 0x004008, 0x00000200, 0x00000200);
+       ram_mask(hwsq, 0x00400c, 0x0000ffff, (N1 << 8) | M1);
+       ram_mask(hwsq, 0x004008, 0x81ff0000, 0x80000000 | (mpll.bias_p << 19) |
+                                            (P << 22) | (P << 16));
+#if QFX5800NVA0
+       for (i = 0; i < 8; i++)
+               ram_mask(hwsq, 0x100da0[i], 0x00000000, 0x00000000); /*XXX*/
+#endif
+       ram_nsec(hwsq, 96000); /*XXX*/
+       ram_mask(hwsq, 0x004008, 0x00002200, 0x00002000);
+
+       ram_wr32(hwsq, 0x1002dc, 0x00000000); /* disable self-refresh */
+       ram_wr32(hwsq, 0x100210, 0x80000000); /* enable auto-refresh */
+
+       ram_nsec(hwsq, 12000);
+
+       switch (ram->base.type) {
+       case NV_MEM_TYPE_DDR2:
+               ram_nuke(hwsq, mr[0]); /* force update */
+               ram_mask(hwsq, mr[0], 0x000, 0x000);
+               break;
+       case NV_MEM_TYPE_GDDR3:
+               ram_mask(hwsq, mr[2], 0x000, 0x000);
+               ram_nuke(hwsq, mr[0]); /* force update */
+               ram_mask(hwsq, mr[0], 0x000, 0x000);
+               break;
+       default:
+               break;
+       }
+
+       ram_mask(hwsq, timing[3], 0x00000000, 0x00000000); /*XXX*/
+       ram_mask(hwsq, timing[1], 0x00000000, 0x00000000); /*XXX*/
+       ram_mask(hwsq, timing[6], 0x00000000, 0x00000000); /*XXX*/
+       ram_mask(hwsq, timing[7], 0x00000000, 0x00000000); /*XXX*/
+       ram_mask(hwsq, timing[8], 0x00000000, 0x00000000); /*XXX*/
+       ram_mask(hwsq, timing[0], 0x00000000, 0x00000000); /*XXX*/
+       ram_mask(hwsq, timing[2], 0x00000000, 0x00000000); /*XXX*/
+       ram_mask(hwsq, timing[4], 0x00000000, 0x00000000); /*XXX*/
+       ram_mask(hwsq, timing[5], 0x00000000, 0x00000000); /*XXX*/
+
+       ram_mask(hwsq, timing[0], 0x00000000, 0x00000000); /*XXX*/
+
+#if QFX5800NVA0
+       ram_nuke(hwsq, 0x100e24);
+       ram_mask(hwsq, 0x100e24, 0x00000000, 0x00000000);
+       ram_nuke(hwsq, 0x100e20);
+       ram_mask(hwsq, 0x100e20, 0x00000000, 0x00000000);
+#endif
+
+       ram_mask(hwsq, mr[0], 0x100, 0x100);
+       ram_mask(hwsq, mr[0], 0x100, 0x000);
+
+       ram_setf(hwsq, 0x10, 0x01); /* enable fb */
+       ram_wait(hwsq, 0x00, 0x00); /* wait for fb enabled */
+       ram_wr32(hwsq, 0x611200, 0x00003330);
+       ram_wr32(hwsq, 0x002504, 0x00000000); /* un-block fifo */
+       return 0;
+}
+
+static int
+nv50_ram_prog(struct nvkm_fb *pfb)
+{
+       struct nvkm_device *device = nv_device(pfb);
+       struct nv50_ram *ram = (void *)pfb->ram;
+       struct nv50_ramseq *hwsq = &ram->hwsq;
+
+       ram_exec(hwsq, nvkm_boolopt(device->cfgopt, "NvMemExec", true));
+       return 0;
+}
+
+static void
+nv50_ram_tidy(struct nvkm_fb *pfb)
+{
+       struct nv50_ram *ram = (void *)pfb->ram;
+       struct nv50_ramseq *hwsq = &ram->hwsq;
+       ram_exec(hwsq, false);
+}
+
+void
+__nv50_ram_put(struct nvkm_fb *pfb, struct nvkm_mem *mem)
+{
+       struct nvkm_mm_node *this;
+
+       while (!list_empty(&mem->regions)) {
+               this = list_first_entry(&mem->regions, typeof(*this), rl_entry);
+
+               list_del(&this->rl_entry);
+               nvkm_mm_free(&pfb->vram, &this);
+       }
+
+       nvkm_mm_free(&pfb->tags, &mem->tag);
+}
+
+void
+nv50_ram_put(struct nvkm_fb *pfb, struct nvkm_mem **pmem)
+{
+       struct nvkm_mem *mem = *pmem;
+
+       *pmem = NULL;
+       if (unlikely(mem == NULL))
+               return;
+
+       mutex_lock(&pfb->base.mutex);
+       __nv50_ram_put(pfb, mem);
+       mutex_unlock(&pfb->base.mutex);
+
+       kfree(mem);
+}
+
+int
+nv50_ram_get(struct nvkm_fb *pfb, u64 size, u32 align, u32 ncmin,
+            u32 memtype, struct nvkm_mem **pmem)
+{
+       struct nvkm_mm *heap = &pfb->vram;
+       struct nvkm_mm *tags = &pfb->tags;
+       struct nvkm_mm_node *r;
+       struct nvkm_mem *mem;
+       int comp = (memtype & 0x300) >> 8;
+       int type = (memtype & 0x07f);
+       int back = (memtype & 0x800);
+       int min, max, ret;
+
+       max = (size >> 12);
+       min = ncmin ? (ncmin >> 12) : max;
+       align >>= 12;
+
+       mem = kzalloc(sizeof(*mem), GFP_KERNEL);
+       if (!mem)
+               return -ENOMEM;
+
+       mutex_lock(&pfb->base.mutex);
+       if (comp) {
+               if (align == 16) {
+                       int n = (max >> 4) * comp;
+
+                       ret = nvkm_mm_head(tags, 0, 1, n, n, 1, &mem->tag);
+                       if (ret)
+                               mem->tag = NULL;
+               }
+
+               if (unlikely(!mem->tag))
+                       comp = 0;
+       }
+
+       INIT_LIST_HEAD(&mem->regions);
+       mem->memtype = (comp << 7) | type;
+       mem->size = max;
+
+       type = nv50_fb_memtype[type];
+       do {
+               if (back)
+                       ret = nvkm_mm_tail(heap, 0, type, max, min, align, &r);
+               else
+                       ret = nvkm_mm_head(heap, 0, type, max, min, align, &r);
+               if (ret) {
+                       mutex_unlock(&pfb->base.mutex);
+                       pfb->ram->put(pfb, &mem);
+                       return ret;
+               }
+
+               list_add_tail(&r->rl_entry, &mem->regions);
+               max -= r->length;
+       } while (max);
+       mutex_unlock(&pfb->base.mutex);
+
+       r = list_first_entry(&mem->regions, struct nvkm_mm_node, rl_entry);
+       mem->offset = (u64)r->offset << 12;
+       *pmem = mem;
+       return 0;
+}
+
+static u32
+nv50_fb_vram_rblock(struct nvkm_fb *pfb, struct nvkm_ram *ram)
+{
+       int colbits, rowbitsa, rowbitsb, banks;
+       u64 rowsize, predicted;
+       u32 r0, r4, rt, rblock_size;
+
+       r0 = nv_rd32(pfb, 0x100200);
+       r4 = nv_rd32(pfb, 0x100204);
+       rt = nv_rd32(pfb, 0x100250);
+       nv_debug(pfb, "memcfg 0x%08x 0x%08x 0x%08x 0x%08x\n",
+                r0, r4, rt, nv_rd32(pfb, 0x001540));
+
+       colbits  =  (r4 & 0x0000f000) >> 12;
+       rowbitsa = ((r4 & 0x000f0000) >> 16) + 8;
+       rowbitsb = ((r4 & 0x00f00000) >> 20) + 8;
+       banks    = 1 << (((r4 & 0x03000000) >> 24) + 2);
+
+       rowsize = ram->parts * banks * (1 << colbits) * 8;
+       predicted = rowsize << rowbitsa;
+       if (r0 & 0x00000004)
+               predicted += rowsize << rowbitsb;
+
+       if (predicted != ram->size) {
+               nv_warn(pfb, "memory controller reports %d MiB VRAM\n",
+                       (u32)(ram->size >> 20));
+       }
+
+       rblock_size = rowsize;
+       if (rt & 1)
+               rblock_size *= 3;
+
+       nv_debug(pfb, "rblock %d bytes\n", rblock_size);
+       return rblock_size;
+}
+
+int
+nv50_ram_create_(struct nvkm_object *parent, struct nvkm_object *engine,
+                struct nvkm_oclass *oclass, int length, void **pobject)
+{
+       const u32 rsvd_head = ( 256 * 1024) >> 12; /* vga memory */
+       const u32 rsvd_tail = (1024 * 1024) >> 12; /* vbios etc */
+       struct nvkm_bios *bios = nvkm_bios(parent);
+       struct nvkm_fb *pfb = nvkm_fb(parent);
+       struct nvkm_ram *ram;
+       int ret;
+
+       ret = nvkm_ram_create_(parent, engine, oclass, length, pobject);
+       ram = *pobject;
+       if (ret)
+               return ret;
+
+       ram->size = nv_rd32(pfb, 0x10020c);
+       ram->size = (ram->size & 0xffffff00) | ((ram->size & 0x000000ff) << 32);
+
+       ram->part_mask = (nv_rd32(pfb, 0x001540) & 0x00ff0000) >> 16;
+       ram->parts = hweight8(ram->part_mask);
+
+       switch (nv_rd32(pfb, 0x100714) & 0x00000007) {
+       case 0: ram->type = NV_MEM_TYPE_DDR1; break;
+       case 1:
+               if (nvkm_fb_bios_memtype(bios) == NV_MEM_TYPE_DDR3)
+                       ram->type = NV_MEM_TYPE_DDR3;
+               else
+                       ram->type = NV_MEM_TYPE_DDR2;
+               break;
+       case 2: ram->type = NV_MEM_TYPE_GDDR3; break;
+       case 3: ram->type = NV_MEM_TYPE_GDDR4; break;
+       case 4: ram->type = NV_MEM_TYPE_GDDR5; break;
+       default:
+               break;
+       }
+
+       ret = nvkm_mm_init(&pfb->vram, rsvd_head, (ram->size >> 12) -
+                          (rsvd_head + rsvd_tail),
+                          nv50_fb_vram_rblock(pfb, ram) >> 12);
+       if (ret)
+               return ret;
+
+       ram->ranks = (nv_rd32(pfb, 0x100200) & 0x4) ? 2 : 1;
+       ram->tags  =  nv_rd32(pfb, 0x100320);
+       ram->get = nv50_ram_get;
+       ram->put = nv50_ram_put;
+       return 0;
+}
+
+static int
+nv50_ram_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+             struct nvkm_oclass *oclass, void *data, u32 datasize,
+             struct nvkm_object **pobject)
+{
+       struct nv50_ram *ram;
+       int ret, i;
+
+       ret = nv50_ram_create(parent, engine, oclass, &ram);
+       *pobject = nv_object(ram);
+       if (ret)
+               return ret;
+
+       switch (ram->base.type) {
+       case NV_MEM_TYPE_DDR2:
+       case NV_MEM_TYPE_GDDR3:
+               ram->base.calc = nv50_ram_calc;
+               ram->base.prog = nv50_ram_prog;
+               ram->base.tidy = nv50_ram_tidy;
+               break;
+       default:
+               nv_warn(ram, "reclocking of this ram type unsupported\n");
+               return 0;
+       }
+
+       ram->hwsq.r_0x002504 = hwsq_reg(0x002504);
+       ram->hwsq.r_0x00c040 = hwsq_reg(0x00c040);
+       ram->hwsq.r_0x004008 = hwsq_reg(0x004008);
+       ram->hwsq.r_0x00400c = hwsq_reg(0x00400c);
+       ram->hwsq.r_0x100210 = hwsq_reg(0x100210);
+       ram->hwsq.r_0x1002d0 = hwsq_reg(0x1002d0);
+       ram->hwsq.r_0x1002d4 = hwsq_reg(0x1002d4);
+       ram->hwsq.r_0x1002dc = hwsq_reg(0x1002dc);
+       for (i = 0; i < 8; i++)
+               ram->hwsq.r_0x100da0[i] = hwsq_reg(0x100da0 + (i * 0x04));
+       ram->hwsq.r_0x100e20 = hwsq_reg(0x100e20);
+       ram->hwsq.r_0x100e24 = hwsq_reg(0x100e24);
+       ram->hwsq.r_0x611200 = hwsq_reg(0x611200);
+
+       for (i = 0; i < 9; i++)
+               ram->hwsq.r_timing[i] = hwsq_reg(0x100220 + (i * 0x04));
+
+       if (ram->base.ranks > 1) {
+               ram->hwsq.r_mr[0] = hwsq_reg2(0x1002c0, 0x1002c8);
+               ram->hwsq.r_mr[1] = hwsq_reg2(0x1002c4, 0x1002cc);
+               ram->hwsq.r_mr[2] = hwsq_reg2(0x1002e0, 0x1002e8);
+               ram->hwsq.r_mr[3] = hwsq_reg2(0x1002e4, 0x1002ec);
+       } else {
+               ram->hwsq.r_mr[0] = hwsq_reg(0x1002c0);
+               ram->hwsq.r_mr[1] = hwsq_reg(0x1002c4);
+               ram->hwsq.r_mr[2] = hwsq_reg(0x1002e0);
+               ram->hwsq.r_mr[3] = hwsq_reg(0x1002e4);
+       }
+
+       return 0;
+}
+
+struct nvkm_oclass
+nv50_ram_oclass = {
+       .ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = nv50_ram_ctor,
+               .dtor = _nvkm_ram_dtor,
+               .init = _nvkm_ram_init,
+               .fini = _nvkm_ram_fini,
+       }
+};
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/fb/ramseq.h b/drivers/gpu/drm/nouveau/nvkm/subdev/fb/ramseq.h
new file mode 100644 (file)
index 0000000..0f1f97c
--- /dev/null
@@ -0,0 +1,15 @@
+#ifndef __NVKM_FBRAM_SEQ_H__
+#define __NVKM_FBRAM_SEQ_H__
+#include <subdev/bus/hwsq.h>
+
+#define ram_init(s,p)       hwsq_init(&(s)->base, (p))
+#define ram_exec(s,e)       hwsq_exec(&(s)->base, (e))
+#define ram_have(s,r)       ((s)->r_##r.addr != 0x000000)
+#define ram_rd32(s,r)       hwsq_rd32(&(s)->base, &(s)->r_##r)
+#define ram_wr32(s,r,d)     hwsq_wr32(&(s)->base, &(s)->r_##r, (d))
+#define ram_nuke(s,r)       hwsq_nuke(&(s)->base, &(s)->r_##r)
+#define ram_mask(s,r,m,d)   hwsq_mask(&(s)->base, &(s)->r_##r, (m), (d))
+#define ram_setf(s,f,d)     hwsq_setf(&(s)->base, (f), (d))
+#define ram_wait(s,f,d)     hwsq_wait(&(s)->base, (f), (d))
+#define ram_nsec(s,n)       hwsq_nsec(&(s)->base, (n))
+#endif
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/fb/regsnv04.h b/drivers/gpu/drm/nouveau/nvkm/subdev/fb/regsnv04.h
new file mode 100644 (file)
index 0000000..1f865f6
--- /dev/null
@@ -0,0 +1,22 @@
+#ifndef __NVKM_FB_REGS_04_H__
+#define __NVKM_FB_REGS_04_H__
+
+#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_CFG0                                          0x00100200
+
+#endif
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/fb/sddr2.c b/drivers/gpu/drm/nouveau/nvkm/subdev/fb/sddr2.c
new file mode 100644 (file)
index 0000000..afab42d
--- /dev/null
@@ -0,0 +1,93 @@
+/*
+ * Copyright 2014 Roy Spliet
+ *
+ * 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: Roy Spliet <rspliet@eclipso.eu>
+ *          Ben Skeggs
+ */
+#include "priv.h"
+
+struct ramxlat {
+       int id;
+       u8 enc;
+};
+
+static inline int
+ramxlat(const struct ramxlat *xlat, int id)
+{
+       while (xlat->id >= 0) {
+               if (xlat->id == id)
+                       return xlat->enc;
+               xlat++;
+       }
+       return -EINVAL;
+}
+
+static const struct ramxlat
+ramddr2_cl[] = {
+       { 2, 2 }, { 3, 3 }, { 4, 4 }, { 5, 5 }, { 6, 6 },
+       /* The following are available in some, but not all DDR2 docs */
+       { 7, 7 },
+       { -1 }
+};
+
+static const struct ramxlat
+ramddr2_wr[] = {
+       { 2, 1 }, { 3, 2 }, { 4, 3 }, { 5, 4 }, { 6, 5 },
+       /* The following are available in some, but not all DDR2 docs */
+       { 7, 6 },
+       { -1 }
+};
+
+int
+nvkm_sddr2_calc(struct nvkm_ram *ram)
+{
+       int CL, WR, DLL = 0, ODT = 0;
+
+       switch (ram->next->bios.timing_ver) {
+       case 0x10:
+               CL  = ram->next->bios.timing_10_CL;
+               WR  = ram->next->bios.timing_10_WR;
+               DLL = !ram->next->bios.ramcfg_10_DLLoff;
+               ODT = ram->next->bios.timing_10_ODT & 3;
+               break;
+       case 0x20:
+               CL  = (ram->next->bios.timing[1] & 0x0000001f);
+               WR  = (ram->next->bios.timing[2] & 0x007f0000) >> 16;
+               break;
+       default:
+               return -ENOSYS;
+       }
+
+       CL  = ramxlat(ramddr2_cl, CL);
+       WR  = ramxlat(ramddr2_wr, WR);
+       if (CL < 0 || WR < 0)
+               return -EINVAL;
+
+       ram->mr[0] &= ~0xf70;
+       ram->mr[0] |= (WR & 0x07) << 9;
+       ram->mr[0] |= (CL & 0x07) << 4;
+
+       ram->mr[1] &= ~0x045;
+       ram->mr[1] |= (ODT & 0x1) << 2;
+       ram->mr[1] |= (ODT & 0x2) << 5;
+       ram->mr[1] |= !DLL;
+       return 0;
+}
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/fb/sddr3.c b/drivers/gpu/drm/nouveau/nvkm/subdev/fb/sddr3.c
new file mode 100644 (file)
index 0000000..1084435
--- /dev/null
@@ -0,0 +1,119 @@
+/*
+ * Copyright 2013 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 <bskeggs@redhat.com>
+ *         Roy Spliet <rspliet@eclipso.eu>
+ */
+#include "priv.h"
+
+struct ramxlat {
+       int id;
+       u8 enc;
+};
+
+static inline int
+ramxlat(const struct ramxlat *xlat, int id)
+{
+       while (xlat->id >= 0) {
+               if (xlat->id == id)
+                       return xlat->enc;
+               xlat++;
+       }
+       return -EINVAL;
+}
+
+static const struct ramxlat
+ramddr3_cl[] = {
+       { 5, 2 }, { 6, 4 }, { 7, 6 }, { 8, 8 }, { 9, 10 }, { 10, 12 },
+       { 11, 14 },
+       /* the below are mentioned in some, but not all, ddr3 docs */
+       { 12, 1 }, { 13, 3 }, { 14, 5 },
+       { -1 }
+};
+
+static const struct ramxlat
+ramddr3_wr[] = {
+       { 5, 1 }, { 6, 2 }, { 7, 3 }, { 8, 4 }, { 10, 5 }, { 12, 6 },
+       /* the below are mentioned in some, but not all, ddr3 docs */
+       { 14, 7 }, { 16, 0 },
+       { -1 }
+};
+
+static const struct ramxlat
+ramddr3_cwl[] = {
+       { 5, 0 }, { 6, 1 }, { 7, 2 }, { 8, 3 },
+       /* the below are mentioned in some, but not all, ddr3 docs */
+       { 9, 4 },
+       { -1 }
+};
+
+int
+nvkm_sddr3_calc(struct nvkm_ram *ram)
+{
+       int CWL, CL, WR, DLL = 0, ODT = 0;
+
+       switch (ram->next->bios.timing_ver) {
+       case 0x10:
+               if (ram->next->bios.timing_hdr < 0x17) {
+                       /* XXX: NV50: Get CWL from the timing register */
+                       return -ENOSYS;
+               }
+               CWL = ram->next->bios.timing_10_CWL;
+               CL  = ram->next->bios.timing_10_CL;
+               WR  = ram->next->bios.timing_10_WR;
+               DLL = !ram->next->bios.ramcfg_10_DLLoff;
+               ODT = ram->next->bios.timing_10_ODT;
+               break;
+       case 0x20:
+               CWL = (ram->next->bios.timing[1] & 0x00000f80) >> 7;
+               CL  = (ram->next->bios.timing[1] & 0x0000001f) >> 0;
+               WR  = (ram->next->bios.timing[2] & 0x007f0000) >> 16;
+               /* XXX: Get these values from the VBIOS instead */
+               DLL = !(ram->mr[1] & 0x1);
+               ODT =   (ram->mr[1] & 0x004) >> 2 |
+                       (ram->mr[1] & 0x040) >> 5 |
+                       (ram->mr[1] & 0x200) >> 7;
+               break;
+       default:
+               return -ENOSYS;
+       }
+
+       CWL = ramxlat(ramddr3_cwl, CWL);
+       CL  = ramxlat(ramddr3_cl, CL);
+       WR  = ramxlat(ramddr3_wr, WR);
+       if (CL < 0 || CWL < 0 || WR < 0)
+               return -EINVAL;
+
+       ram->mr[0] &= ~0xf74;
+       ram->mr[0] |= (WR & 0x07) << 9;
+       ram->mr[0] |= (CL & 0x0e) << 3;
+       ram->mr[0] |= (CL & 0x01) << 2;
+
+       ram->mr[1] &= ~0x245;
+       ram->mr[1] |= (ODT & 0x1) << 2;
+       ram->mr[1] |= (ODT & 0x2) << 5;
+       ram->mr[1] |= (ODT & 0x4) << 7;
+       ram->mr[1] |= !DLL;
+
+       ram->mr[2] &= ~0x038;
+       ram->mr[2] |= (CWL & 0x07) << 3;
+       return 0;
+}
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/fuse/Kbuild b/drivers/gpu/drm/nouveau/nvkm/subdev/fuse/Kbuild
new file mode 100644 (file)
index 0000000..f3d4e6e
--- /dev/null
@@ -0,0 +1,4 @@
+nvkm-y += nvkm/subdev/fuse/base.o
+nvkm-y += nvkm/subdev/fuse/nv50.o
+nvkm-y += nvkm/subdev/fuse/gf100.o
+nvkm-y += nvkm/subdev/fuse/gm107.o
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/fuse/base.c b/drivers/gpu/drm/nouveau/nvkm/subdev/fuse/base.c
new file mode 100644 (file)
index 0000000..b7b7193
--- /dev/null
@@ -0,0 +1,51 @@
+/*
+ * Copyright 2014 Martin Peres
+ *
+ * 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 <subdev/fuse.h>
+
+int
+_nvkm_fuse_init(struct nvkm_object *object)
+{
+       struct nvkm_fuse *fuse = (void *)object;
+       return nvkm_subdev_init(&fuse->base);
+}
+
+void
+_nvkm_fuse_dtor(struct nvkm_object *object)
+{
+       struct nvkm_fuse *fuse = (void *)object;
+       nvkm_subdev_destroy(&fuse->base);
+}
+
+int
+nvkm_fuse_create_(struct nvkm_object *parent, struct nvkm_object *engine,
+                 struct nvkm_oclass *oclass, int length, void **pobject)
+{
+       struct nvkm_fuse *fuse;
+       int ret;
+
+       ret = nvkm_subdev_create_(parent, engine, oclass, 0, "FUSE",
+                                 "fuse", length, pobject);
+       fuse = *pobject;
+       return ret;
+}
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/fuse/gf100.c b/drivers/gpu/drm/nouveau/nvkm/subdev/fuse/gf100.c
new file mode 100644 (file)
index 0000000..393ef3a
--- /dev/null
@@ -0,0 +1,78 @@
+/*
+ * Copyright 2014 Martin Peres
+ *
+ * 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 "priv.h"
+
+struct gf100_fuse_priv {
+       struct nvkm_fuse base;
+
+       spinlock_t fuse_enable_lock;
+};
+
+static u32
+gf100_fuse_rd32(struct nvkm_object *object, u64 addr)
+{
+       struct gf100_fuse_priv *priv = (void *)object;
+       unsigned long flags;
+       u32 fuse_enable, unk, val;
+
+       /* racy if another part of nvkm start writing to these regs */
+       spin_lock_irqsave(&priv->fuse_enable_lock, flags);
+       fuse_enable = nv_mask(priv, 0x22400, 0x800, 0x800);
+       unk = nv_mask(priv, 0x21000, 0x1, 0x1);
+       val = nv_rd32(priv, 0x21100 + addr);
+       nv_wr32(priv, 0x21000, unk);
+       nv_wr32(priv, 0x22400, fuse_enable);
+       spin_unlock_irqrestore(&priv->fuse_enable_lock, flags);
+       return val;
+}
+
+
+static int
+gf100_fuse_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+               struct nvkm_oclass *oclass, void *data, u32 size,
+               struct nvkm_object **pobject)
+{
+       struct gf100_fuse_priv *priv;
+       int ret;
+
+       ret = nvkm_fuse_create(parent, engine, oclass, &priv);
+       *pobject = nv_object(priv);
+       if (ret)
+               return ret;
+
+       spin_lock_init(&priv->fuse_enable_lock);
+       return 0;
+}
+
+struct nvkm_oclass
+gf100_fuse_oclass = {
+       .handle = NV_SUBDEV(FUSE, 0xC0),
+       .ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = gf100_fuse_ctor,
+               .dtor = _nvkm_fuse_dtor,
+               .init = _nvkm_fuse_init,
+               .fini = _nvkm_fuse_fini,
+               .rd32 = gf100_fuse_rd32,
+       },
+};
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/fuse/gm107.c b/drivers/gpu/drm/nouveau/nvkm/subdev/fuse/gm107.c
new file mode 100644 (file)
index 0000000..ba19158
--- /dev/null
@@ -0,0 +1,64 @@
+/*
+ * Copyright 2014 Martin Peres
+ *
+ * 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 "priv.h"
+
+struct gm107_fuse_priv {
+       struct nvkm_fuse base;
+};
+
+static u32
+gm107_fuse_rd32(struct nvkm_object *object, u64 addr)
+{
+       struct gf100_fuse_priv *priv = (void *)object;
+       return nv_rd32(priv, 0x21100 + addr);
+}
+
+
+static int
+gm107_fuse_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+               struct nvkm_oclass *oclass, void *data, u32 size,
+               struct nvkm_object **pobject)
+{
+       struct gm107_fuse_priv *priv;
+       int ret;
+
+       ret = nvkm_fuse_create(parent, engine, oclass, &priv);
+       *pobject = nv_object(priv);
+       if (ret)
+               return ret;
+
+       return 0;
+}
+
+struct nvkm_oclass
+gm107_fuse_oclass = {
+       .handle = NV_SUBDEV(FUSE, 0x117),
+       .ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = gm107_fuse_ctor,
+               .dtor = _nvkm_fuse_dtor,
+               .init = _nvkm_fuse_init,
+               .fini = _nvkm_fuse_fini,
+               .rd32 = gm107_fuse_rd32,
+       },
+};
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/fuse/nv50.c b/drivers/gpu/drm/nouveau/nvkm/subdev/fuse/nv50.c
new file mode 100644 (file)
index 0000000..0d2afc4
--- /dev/null
@@ -0,0 +1,76 @@
+/*
+ * Copyright 2014 Martin Peres
+ *
+ * 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 "priv.h"
+
+struct nv50_fuse_priv {
+       struct nvkm_fuse base;
+
+       spinlock_t fuse_enable_lock;
+};
+
+static u32
+nv50_fuse_rd32(struct nvkm_object *object, u64 addr)
+{
+       struct nv50_fuse_priv *priv = (void *)object;
+       unsigned long flags;
+       u32 fuse_enable, val;
+
+       /* racy if another part of nvkm start writing to this reg */
+       spin_lock_irqsave(&priv->fuse_enable_lock, flags);
+       fuse_enable = nv_mask(priv, 0x1084, 0x800, 0x800);
+       val = nv_rd32(priv, 0x21000 + addr);
+       nv_wr32(priv, 0x1084, fuse_enable);
+       spin_unlock_irqrestore(&priv->fuse_enable_lock, flags);
+       return val;
+}
+
+
+static int
+nv50_fuse_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+              struct nvkm_oclass *oclass, void *data, u32 size,
+              struct nvkm_object **pobject)
+{
+       struct nv50_fuse_priv *priv;
+       int ret;
+
+       ret = nvkm_fuse_create(parent, engine, oclass, &priv);
+       *pobject = nv_object(priv);
+       if (ret)
+               return ret;
+
+       spin_lock_init(&priv->fuse_enable_lock);
+       return 0;
+}
+
+struct nvkm_oclass
+nv50_fuse_oclass = {
+       .handle = NV_SUBDEV(FUSE, 0x50),
+       .ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = nv50_fuse_ctor,
+               .dtor = _nvkm_fuse_dtor,
+               .init = _nvkm_fuse_init,
+               .fini = _nvkm_fuse_fini,
+               .rd32 = nv50_fuse_rd32,
+       },
+};
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/fuse/priv.h b/drivers/gpu/drm/nouveau/nvkm/subdev/fuse/priv.h
new file mode 100644 (file)
index 0000000..7e050f7
--- /dev/null
@@ -0,0 +1,7 @@
+#ifndef __NVKM_FUSE_PRIV_H__
+#define __NVKM_FUSE_PRIV_H__
+#include <subdev/fuse.h>
+
+int _nvkm_fuse_init(struct nvkm_object *object);
+void _nvkm_fuse_dtor(struct nvkm_object *object);
+#endif
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/gpio/Kbuild b/drivers/gpu/drm/nouveau/nvkm/subdev/gpio/Kbuild
new file mode 100644 (file)
index 0000000..ea42a9e
--- /dev/null
@@ -0,0 +1,6 @@
+nvkm-y += nvkm/subdev/gpio/base.o
+nvkm-y += nvkm/subdev/gpio/nv10.o
+nvkm-y += nvkm/subdev/gpio/nv50.o
+nvkm-y += nvkm/subdev/gpio/g94.o
+nvkm-y += nvkm/subdev/gpio/gf110.o
+nvkm-y += nvkm/subdev/gpio/gk104.o
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/gpio/base.c b/drivers/gpu/drm/nouveau/nvkm/subdev/gpio/base.c
new file mode 100644 (file)
index 0000000..dea5816
--- /dev/null
@@ -0,0 +1,251 @@
+/*
+ * 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 "priv.h"
+
+#include <core/device.h>
+#include <core/notify.h>
+
+static int
+nvkm_gpio_drive(struct nvkm_gpio *gpio, int idx, int line, int dir, int out)
+{
+       const struct nvkm_gpio_impl *impl = (void *)nv_object(gpio)->oclass;
+       return impl->drive ? impl->drive(gpio, line, dir, out) : -ENODEV;
+}
+
+static int
+nvkm_gpio_sense(struct nvkm_gpio *gpio, int idx, int line)
+{
+       const struct nvkm_gpio_impl *impl = (void *)nv_object(gpio)->oclass;
+       return impl->sense ? impl->sense(gpio, line) : -ENODEV;
+}
+
+static int
+nvkm_gpio_find(struct nvkm_gpio *gpio, int idx, u8 tag, u8 line,
+              struct dcb_gpio_func *func)
+{
+       struct nvkm_bios *bios = nvkm_bios(gpio);
+       u8  ver, len;
+       u16 data;
+
+       if (line == 0xff && tag == 0xff)
+               return -EINVAL;
+
+       data = dcb_gpio_match(bios, idx, tag, line, &ver, &len, func);
+       if (data)
+               return 0;
+
+       /* Apple iMac G4 NV18 */
+       if (nv_device_match(nv_object(gpio), 0x0189, 0x10de, 0x0010)) {
+               if (tag == DCB_GPIO_TVDAC0) {
+                       *func = (struct dcb_gpio_func) {
+                               .func = DCB_GPIO_TVDAC0,
+                               .line = 4,
+                               .log[0] = 0,
+                               .log[1] = 1,
+                       };
+                       return 0;
+               }
+       }
+
+       return -ENOENT;
+}
+
+static int
+nvkm_gpio_set(struct nvkm_gpio *gpio, int idx, u8 tag, u8 line, int state)
+{
+       struct dcb_gpio_func func;
+       int ret;
+
+       ret = nvkm_gpio_find(gpio, idx, tag, line, &func);
+       if (ret == 0) {
+               int dir = !!(func.log[state] & 0x02);
+               int out = !!(func.log[state] & 0x01);
+               ret = nvkm_gpio_drive(gpio, idx, func.line, dir, out);
+       }
+
+       return ret;
+}
+
+static int
+nvkm_gpio_get(struct nvkm_gpio *gpio, int idx, u8 tag, u8 line)
+{
+       struct dcb_gpio_func func;
+       int ret;
+
+       ret = nvkm_gpio_find(gpio, idx, tag, line, &func);
+       if (ret == 0) {
+               ret = nvkm_gpio_sense(gpio, idx, func.line);
+               if (ret >= 0)
+                       ret = (ret == (func.log[1] & 1));
+       }
+
+       return ret;
+}
+
+static void
+nvkm_gpio_intr_fini(struct nvkm_event *event, int type, int index)
+{
+       struct nvkm_gpio *gpio = container_of(event, typeof(*gpio), event);
+       const struct nvkm_gpio_impl *impl = (void *)nv_object(gpio)->oclass;
+       impl->intr_mask(gpio, type, 1 << index, 0);
+}
+
+static void
+nvkm_gpio_intr_init(struct nvkm_event *event, int type, int index)
+{
+       struct nvkm_gpio *gpio = container_of(event, typeof(*gpio), event);
+       const struct nvkm_gpio_impl *impl = (void *)nv_object(gpio)->oclass;
+       impl->intr_mask(gpio, type, 1 << index, 1 << index);
+}
+
+static int
+nvkm_gpio_intr_ctor(struct nvkm_object *object, void *data, u32 size,
+                   struct nvkm_notify *notify)
+{
+       struct nvkm_gpio_ntfy_req *req = data;
+       if (!WARN_ON(size != sizeof(*req))) {
+               notify->size  = sizeof(struct nvkm_gpio_ntfy_rep);
+               notify->types = req->mask;
+               notify->index = req->line;
+               return 0;
+       }
+       return -EINVAL;
+}
+
+static void
+nvkm_gpio_intr(struct nvkm_subdev *subdev)
+{
+       struct nvkm_gpio *gpio = nvkm_gpio(subdev);
+       const struct nvkm_gpio_impl *impl = (void *)nv_object(gpio)->oclass;
+       u32 hi, lo, i;
+
+       impl->intr_stat(gpio, &hi, &lo);
+
+       for (i = 0; (hi | lo) && i < impl->lines; i++) {
+               struct nvkm_gpio_ntfy_rep rep = {
+                       .mask = (NVKM_GPIO_HI * !!(hi & (1 << i))) |
+                               (NVKM_GPIO_LO * !!(lo & (1 << i))),
+               };
+               nvkm_event_send(&gpio->event, rep.mask, i, &rep, sizeof(rep));
+       }
+}
+
+static const struct nvkm_event_func
+nvkm_gpio_intr_func = {
+       .ctor = nvkm_gpio_intr_ctor,
+       .init = nvkm_gpio_intr_init,
+       .fini = nvkm_gpio_intr_fini,
+};
+
+int
+_nvkm_gpio_fini(struct nvkm_object *object, bool suspend)
+{
+       const struct nvkm_gpio_impl *impl = (void *)object->oclass;
+       struct nvkm_gpio *gpio = nvkm_gpio(object);
+       u32 mask = (1 << impl->lines) - 1;
+
+       impl->intr_mask(gpio, NVKM_GPIO_TOGGLED, mask, 0);
+       impl->intr_stat(gpio, &mask, &mask);
+
+       return nvkm_subdev_fini(&gpio->base, suspend);
+}
+
+static struct dmi_system_id gpio_reset_ids[] = {
+       {
+               .ident = "Apple Macbook 10,1",
+               .matches = {
+                       DMI_MATCH(DMI_SYS_VENDOR, "Apple Inc."),
+                       DMI_MATCH(DMI_PRODUCT_NAME, "MacBookPro10,1"),
+               }
+       },
+       { }
+};
+
+int
+_nvkm_gpio_init(struct nvkm_object *object)
+{
+       struct nvkm_gpio *gpio = nvkm_gpio(object);
+       int ret;
+
+       ret = nvkm_subdev_init(&gpio->base);
+       if (ret)
+               return ret;
+
+       if (gpio->reset && dmi_check_system(gpio_reset_ids))
+               gpio->reset(gpio, DCB_GPIO_UNUSED);
+
+       return ret;
+}
+
+void
+_nvkm_gpio_dtor(struct nvkm_object *object)
+{
+       struct nvkm_gpio *gpio = (void *)object;
+       nvkm_event_fini(&gpio->event);
+       nvkm_subdev_destroy(&gpio->base);
+}
+
+int
+nvkm_gpio_create_(struct nvkm_object *parent, struct nvkm_object *engine,
+                 struct nvkm_oclass *oclass, int length, void **pobject)
+{
+       const struct nvkm_gpio_impl *impl = (void *)oclass;
+       struct nvkm_gpio *gpio;
+       int ret;
+
+       ret = nvkm_subdev_create_(parent, engine, oclass, 0, "GPIO",
+                                 "gpio", length, pobject);
+       gpio = *pobject;
+       if (ret)
+               return ret;
+
+       gpio->find = nvkm_gpio_find;
+       gpio->set  = nvkm_gpio_set;
+       gpio->get  = nvkm_gpio_get;
+       gpio->reset = impl->reset;
+
+       ret = nvkm_event_init(&nvkm_gpio_intr_func, 2, impl->lines,
+                             &gpio->event);
+       if (ret)
+               return ret;
+
+       nv_subdev(gpio)->intr = nvkm_gpio_intr;
+       return 0;
+}
+
+int
+_nvkm_gpio_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+               struct nvkm_oclass *oclass, void *data, u32 size,
+               struct nvkm_object **pobject)
+{
+       struct nvkm_gpio *gpio;
+       int ret;
+
+       ret = nvkm_gpio_create(parent, engine, oclass, &gpio);
+       *pobject = nv_object(gpio);
+       if (ret)
+               return ret;
+
+       return 0;
+}
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/gpio/g94.c b/drivers/gpu/drm/nouveau/nvkm/subdev/gpio/g94.c
new file mode 100644 (file)
index 0000000..12b3e01
--- /dev/null
@@ -0,0 +1,73 @@
+/*
+ * Copyright 2012 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 "priv.h"
+
+void
+g94_gpio_intr_stat(struct nvkm_gpio *gpio, u32 *hi, u32 *lo)
+{
+       u32 intr0 = nv_rd32(gpio, 0x00e054);
+       u32 intr1 = nv_rd32(gpio, 0x00e074);
+       u32 stat0 = nv_rd32(gpio, 0x00e050) & intr0;
+       u32 stat1 = nv_rd32(gpio, 0x00e070) & intr1;
+       *lo = (stat1 & 0xffff0000) | (stat0 >> 16);
+       *hi = (stat1 << 16) | (stat0 & 0x0000ffff);
+       nv_wr32(gpio, 0x00e054, intr0);
+       nv_wr32(gpio, 0x00e074, intr1);
+}
+
+void
+g94_gpio_intr_mask(struct nvkm_gpio *gpio, u32 type, u32 mask, u32 data)
+{
+       u32 inte0 = nv_rd32(gpio, 0x00e050);
+       u32 inte1 = nv_rd32(gpio, 0x00e070);
+       if (type & NVKM_GPIO_LO)
+               inte0 = (inte0 & ~(mask << 16)) | (data << 16);
+       if (type & NVKM_GPIO_HI)
+               inte0 = (inte0 & ~(mask & 0xffff)) | (data & 0xffff);
+       mask >>= 16;
+       data >>= 16;
+       if (type & NVKM_GPIO_LO)
+               inte1 = (inte1 & ~(mask << 16)) | (data << 16);
+       if (type & NVKM_GPIO_HI)
+               inte1 = (inte1 & ~mask) | data;
+       nv_wr32(gpio, 0x00e050, inte0);
+       nv_wr32(gpio, 0x00e070, inte1);
+}
+
+struct nvkm_oclass *
+g94_gpio_oclass = &(struct nvkm_gpio_impl) {
+       .base.handle = NV_SUBDEV(GPIO, 0x94),
+       .base.ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = _nvkm_gpio_ctor,
+               .dtor = _nvkm_gpio_dtor,
+               .init = _nvkm_gpio_init,
+               .fini = _nvkm_gpio_fini,
+       },
+       .lines = 32,
+       .intr_stat = g94_gpio_intr_stat,
+       .intr_mask = g94_gpio_intr_mask,
+       .drive = nv50_gpio_drive,
+       .sense = nv50_gpio_sense,
+       .reset = nv50_gpio_reset,
+}.base;
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/gpio/gf110.c b/drivers/gpu/drm/nouveau/nvkm/subdev/gpio/gf110.c
new file mode 100644 (file)
index 0000000..2c3bb25
--- /dev/null
@@ -0,0 +1,84 @@
+/*
+ * Copyright 2012 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 "priv.h"
+
+void
+gf110_gpio_reset(struct nvkm_gpio *gpio, u8 match)
+{
+       struct nvkm_bios *bios = nvkm_bios(gpio);
+       u8 ver, len;
+       u16 entry;
+       int ent = -1;
+
+       while ((entry = dcb_gpio_entry(bios, 0, ++ent, &ver, &len))) {
+               u32 data = nv_ro32(bios, entry);
+               u8  line =   (data & 0x0000003f);
+               u8  defs = !!(data & 0x00000080);
+               u8  func =   (data & 0x0000ff00) >> 8;
+               u8  unk0 =   (data & 0x00ff0000) >> 16;
+               u8  unk1 =   (data & 0x1f000000) >> 24;
+
+               if ( func  == DCB_GPIO_UNUSED ||
+                   (match != DCB_GPIO_UNUSED && match != func))
+                       continue;
+
+               gpio->set(gpio, 0, func, line, defs);
+
+               nv_mask(gpio, 0x00d610 + (line * 4), 0xff, unk0);
+               if (unk1--)
+                       nv_mask(gpio, 0x00d740 + (unk1 * 4), 0xff, line);
+       }
+}
+
+int
+gf110_gpio_drive(struct nvkm_gpio *gpio, int line, int dir, int out)
+{
+       u32 data = ((dir ^ 1) << 13) | (out << 12);
+       nv_mask(gpio, 0x00d610 + (line * 4), 0x00003000, data);
+       nv_mask(gpio, 0x00d604, 0x00000001, 0x00000001); /* update? */
+       return 0;
+}
+
+int
+gf110_gpio_sense(struct nvkm_gpio *gpio, int line)
+{
+       return !!(nv_rd32(gpio, 0x00d610 + (line * 4)) & 0x00004000);
+}
+
+struct nvkm_oclass *
+gf110_gpio_oclass = &(struct nvkm_gpio_impl) {
+       .base.handle = NV_SUBDEV(GPIO, 0xd0),
+       .base.ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = _nvkm_gpio_ctor,
+               .dtor = _nvkm_gpio_dtor,
+               .init = _nvkm_gpio_init,
+               .fini = _nvkm_gpio_fini,
+       },
+       .lines = 32,
+       .intr_stat = g94_gpio_intr_stat,
+       .intr_mask = g94_gpio_intr_mask,
+       .drive = gf110_gpio_drive,
+       .sense = gf110_gpio_sense,
+       .reset = gf110_gpio_reset,
+}.base;
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/gpio/gk104.c b/drivers/gpu/drm/nouveau/nvkm/subdev/gpio/gk104.c
new file mode 100644 (file)
index 0000000..42fd2fa
--- /dev/null
@@ -0,0 +1,73 @@
+/*
+ * Copyright 2012 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 "priv.h"
+
+static void
+gk104_gpio_intr_stat(struct nvkm_gpio *gpio, u32 *hi, u32 *lo)
+{
+       u32 intr0 = nv_rd32(gpio, 0x00dc00);
+       u32 intr1 = nv_rd32(gpio, 0x00dc80);
+       u32 stat0 = nv_rd32(gpio, 0x00dc08) & intr0;
+       u32 stat1 = nv_rd32(gpio, 0x00dc88) & intr1;
+       *lo = (stat1 & 0xffff0000) | (stat0 >> 16);
+       *hi = (stat1 << 16) | (stat0 & 0x0000ffff);
+       nv_wr32(gpio, 0x00dc00, intr0);
+       nv_wr32(gpio, 0x00dc80, intr1);
+}
+
+void
+gk104_gpio_intr_mask(struct nvkm_gpio *gpio, u32 type, u32 mask, u32 data)
+{
+       u32 inte0 = nv_rd32(gpio, 0x00dc08);
+       u32 inte1 = nv_rd32(gpio, 0x00dc88);
+       if (type & NVKM_GPIO_LO)
+               inte0 = (inte0 & ~(mask << 16)) | (data << 16);
+       if (type & NVKM_GPIO_HI)
+               inte0 = (inte0 & ~(mask & 0xffff)) | (data & 0xffff);
+       mask >>= 16;
+       data >>= 16;
+       if (type & NVKM_GPIO_LO)
+               inte1 = (inte1 & ~(mask << 16)) | (data << 16);
+       if (type & NVKM_GPIO_HI)
+               inte1 = (inte1 & ~mask) | data;
+       nv_wr32(gpio, 0x00dc08, inte0);
+       nv_wr32(gpio, 0x00dc88, inte1);
+}
+
+struct nvkm_oclass *
+gk104_gpio_oclass = &(struct nvkm_gpio_impl) {
+       .base.handle = NV_SUBDEV(GPIO, 0xe0),
+       .base.ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = _nvkm_gpio_ctor,
+               .dtor = _nvkm_gpio_dtor,
+               .init = _nvkm_gpio_init,
+               .fini = _nvkm_gpio_fini,
+       },
+       .lines = 32,
+       .intr_stat = gk104_gpio_intr_stat,
+       .intr_mask = gk104_gpio_intr_mask,
+       .drive = gf110_gpio_drive,
+       .sense = gf110_gpio_sense,
+       .reset = gf110_gpio_reset,
+}.base;
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/gpio/nv10.c b/drivers/gpu/drm/nouveau/nvkm/subdev/gpio/nv10.c
new file mode 100644 (file)
index 0000000..2b29515
--- /dev/null
@@ -0,0 +1,115 @@
+/*
+ * 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 "priv.h"
+
+static int
+nv10_gpio_sense(struct nvkm_gpio *gpio, int line)
+{
+       if (line < 2) {
+               line = line * 16;
+               line = nv_rd32(gpio, 0x600818) >> line;
+               return !!(line & 0x0100);
+       } else
+       if (line < 10) {
+               line = (line - 2) * 4;
+               line = nv_rd32(gpio, 0x60081c) >> line;
+               return !!(line & 0x04);
+       } else
+       if (line < 14) {
+               line = (line - 10) * 4;
+               line = nv_rd32(gpio, 0x600850) >> line;
+               return !!(line & 0x04);
+       }
+
+       return -EINVAL;
+}
+
+static int
+nv10_gpio_drive(struct nvkm_gpio *gpio, int line, int dir, int out)
+{
+       u32 reg, mask, data;
+
+       if (line < 2) {
+               line = line * 16;
+               reg  = 0x600818;
+               mask = 0x00000011;
+               data = (dir << 4) | out;
+       } else
+       if (line < 10) {
+               line = (line - 2) * 4;
+               reg  = 0x60081c;
+               mask = 0x00000003;
+               data = (dir << 1) | out;
+       } else
+       if (line < 14) {
+               line = (line - 10) * 4;
+               reg  = 0x600850;
+               mask = 0x00000003;
+               data = (dir << 1) | out;
+       } else {
+               return -EINVAL;
+       }
+
+       nv_mask(gpio, reg, mask << line, data << line);
+       return 0;
+}
+
+static void
+nv10_gpio_intr_stat(struct nvkm_gpio *gpio, u32 *hi, u32 *lo)
+{
+       u32 intr = nv_rd32(gpio, 0x001104);
+       u32 stat = nv_rd32(gpio, 0x001144) & intr;
+       *lo = (stat & 0xffff0000) >> 16;
+       *hi = (stat & 0x0000ffff);
+       nv_wr32(gpio, 0x001104, intr);
+}
+
+static void
+nv10_gpio_intr_mask(struct nvkm_gpio *gpio, u32 type, u32 mask, u32 data)
+{
+       u32 inte = nv_rd32(gpio, 0x001144);
+       if (type & NVKM_GPIO_LO)
+               inte = (inte & ~(mask << 16)) | (data << 16);
+       if (type & NVKM_GPIO_HI)
+               inte = (inte & ~mask) | data;
+       nv_wr32(gpio, 0x001144, inte);
+}
+
+struct nvkm_oclass *
+nv10_gpio_oclass = &(struct nvkm_gpio_impl) {
+       .base.handle = NV_SUBDEV(GPIO, 0x10),
+       .base.ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = _nvkm_gpio_ctor,
+               .dtor = _nvkm_gpio_dtor,
+               .init = _nvkm_gpio_init,
+               .fini = _nvkm_gpio_fini,
+       },
+       .lines = 16,
+       .intr_stat = nv10_gpio_intr_stat,
+       .intr_mask = nv10_gpio_intr_mask,
+       .drive = nv10_gpio_drive,
+       .sense = nv10_gpio_sense,
+}.base;
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/gpio/nv50.c b/drivers/gpu/drm/nouveau/nvkm/subdev/gpio/nv50.c
new file mode 100644 (file)
index 0000000..6a03103
--- /dev/null
@@ -0,0 +1,128 @@
+/*
+ * Copyright 2012 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 "priv.h"
+
+void
+nv50_gpio_reset(struct nvkm_gpio *gpio, u8 match)
+{
+       struct nvkm_bios *bios = nvkm_bios(gpio);
+       u8 ver, len;
+       u16 entry;
+       int ent = -1;
+
+       while ((entry = dcb_gpio_entry(bios, 0, ++ent, &ver, &len))) {
+               static const u32 regs[] = { 0xe100, 0xe28c };
+               u32 data = nv_ro32(bios, entry);
+               u8  line =   (data & 0x0000001f);
+               u8  func =   (data & 0x0000ff00) >> 8;
+               u8  defs = !!(data & 0x01000000);
+               u8  unk0 = !!(data & 0x02000000);
+               u8  unk1 = !!(data & 0x04000000);
+               u32 val = (unk1 << 16) | unk0;
+               u32 reg = regs[line >> 4];
+               u32 lsh = line & 0x0f;
+
+               if ( func  == DCB_GPIO_UNUSED ||
+                   (match != DCB_GPIO_UNUSED && match != func))
+                       continue;
+
+               gpio->set(gpio, 0, func, line, defs);
+
+               nv_mask(gpio, reg, 0x00010001 << lsh, val << lsh);
+       }
+}
+
+int
+nv50_gpio_location(int line, u32 *reg, u32 *shift)
+{
+       const u32 nv50_gpio_reg[4] = { 0xe104, 0xe108, 0xe280, 0xe284 };
+
+       if (line >= 32)
+               return -EINVAL;
+
+       *reg = nv50_gpio_reg[line >> 3];
+       *shift = (line & 7) << 2;
+       return 0;
+}
+
+int
+nv50_gpio_drive(struct nvkm_gpio *gpio, int line, int dir, int out)
+{
+       u32 reg, shift;
+
+       if (nv50_gpio_location(line, &reg, &shift))
+               return -EINVAL;
+
+       nv_mask(gpio, reg, 3 << shift, (((dir ^ 1) << 1) | out) << shift);
+       return 0;
+}
+
+int
+nv50_gpio_sense(struct nvkm_gpio *gpio, int line)
+{
+       u32 reg, shift;
+
+       if (nv50_gpio_location(line, &reg, &shift))
+               return -EINVAL;
+
+       return !!(nv_rd32(gpio, reg) & (4 << shift));
+}
+
+static void
+nv50_gpio_intr_stat(struct nvkm_gpio *gpio, u32 *hi, u32 *lo)
+{
+       u32 intr = nv_rd32(gpio, 0x00e054);
+       u32 stat = nv_rd32(gpio, 0x00e050) & intr;
+       *lo = (stat & 0xffff0000) >> 16;
+       *hi = (stat & 0x0000ffff);
+       nv_wr32(gpio, 0x00e054, intr);
+}
+
+static void
+nv50_gpio_intr_mask(struct nvkm_gpio *gpio, u32 type, u32 mask, u32 data)
+{
+       u32 inte = nv_rd32(gpio, 0x00e050);
+       if (type & NVKM_GPIO_LO)
+               inte = (inte & ~(mask << 16)) | (data << 16);
+       if (type & NVKM_GPIO_HI)
+               inte = (inte & ~mask) | data;
+       nv_wr32(gpio, 0x00e050, inte);
+}
+
+struct nvkm_oclass *
+nv50_gpio_oclass = &(struct nvkm_gpio_impl) {
+       .base.handle = NV_SUBDEV(GPIO, 0x50),
+       .base.ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = _nvkm_gpio_ctor,
+               .dtor = _nvkm_gpio_dtor,
+               .init = _nvkm_gpio_init,
+               .fini = _nvkm_gpio_fini,
+       },
+       .lines = 16,
+       .intr_stat = nv50_gpio_intr_stat,
+       .intr_mask = nv50_gpio_intr_mask,
+       .drive = nv50_gpio_drive,
+       .sense = nv50_gpio_sense,
+       .reset = nv50_gpio_reset,
+}.base;
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/gpio/priv.h b/drivers/gpu/drm/nouveau/nvkm/subdev/gpio/priv.h
new file mode 100644 (file)
index 0000000..382f8d4
--- /dev/null
@@ -0,0 +1,64 @@
+#ifndef __NVKM_GPIO_PRIV_H__
+#define __NVKM_GPIO_PRIV_H__
+#include <subdev/gpio.h>
+
+#define nvkm_gpio_create(p,e,o,d)                                           \
+       nvkm_gpio_create_((p), (e), (o), sizeof(**d), (void **)d)
+#define nvkm_gpio_destroy(p) ({                                             \
+       struct nvkm_gpio *gpio = (p);                                       \
+       _nvkm_gpio_dtor(nv_object(gpio));                                   \
+})
+#define nvkm_gpio_init(p) ({                                                \
+       struct nvkm_gpio *gpio = (p);                                       \
+       _nvkm_gpio_init(nv_object(gpio));                                   \
+})
+#define nvkm_gpio_fini(p,s) ({                                              \
+       struct nvkm_gpio *gpio = (p);                                       \
+       _nvkm_gpio_fini(nv_object(gpio), (s));                              \
+})
+
+int  nvkm_gpio_create_(struct nvkm_object *, struct nvkm_object *,
+                         struct nvkm_oclass *, int, void **);
+int  _nvkm_gpio_ctor(struct nvkm_object *, struct nvkm_object *,
+                       struct nvkm_oclass *, void *, u32,
+                       struct nvkm_object **);
+void _nvkm_gpio_dtor(struct nvkm_object *);
+int  _nvkm_gpio_init(struct nvkm_object *);
+int  _nvkm_gpio_fini(struct nvkm_object *, bool);
+
+struct nvkm_gpio_impl {
+       struct nvkm_oclass base;
+       int lines;
+
+       /* read and ack pending interrupts, returning only data
+        * for lines that have not been masked off, while still
+        * performing the ack for anything that was pending.
+        */
+       void (*intr_stat)(struct nvkm_gpio *, u32 *, u32 *);
+
+       /* mask on/off interrupts for hi/lo transitions on a
+        * given set of gpio lines
+        */
+       void (*intr_mask)(struct nvkm_gpio *, u32, u32, u32);
+
+       /* configure gpio direction and output value */
+       int  (*drive)(struct nvkm_gpio *, int line, int dir, int out);
+
+       /* sense current state of given gpio line */
+       int  (*sense)(struct nvkm_gpio *, int line);
+
+       /*XXX*/
+       void (*reset)(struct nvkm_gpio *, u8);
+};
+
+void nv50_gpio_reset(struct nvkm_gpio *, u8);
+int  nv50_gpio_drive(struct nvkm_gpio *, int, int, int);
+int  nv50_gpio_sense(struct nvkm_gpio *, int);
+
+void g94_gpio_intr_stat(struct nvkm_gpio *, u32 *, u32 *);
+void g94_gpio_intr_mask(struct nvkm_gpio *, u32, u32, u32);
+
+void gf110_gpio_reset(struct nvkm_gpio *, u8);
+int  gf110_gpio_drive(struct nvkm_gpio *, int, int, int);
+int  gf110_gpio_sense(struct nvkm_gpio *, int);
+#endif
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/i2c/Kbuild b/drivers/gpu/drm/nouveau/nvkm/subdev/i2c/Kbuild
new file mode 100644 (file)
index 0000000..d683074
--- /dev/null
@@ -0,0 +1,16 @@
+nvkm-y += nvkm/subdev/i2c/base.o
+nvkm-y += nvkm/subdev/i2c/anx9805.o
+nvkm-y += nvkm/subdev/i2c/aux.o
+nvkm-y += nvkm/subdev/i2c/bit.o
+nvkm-y += nvkm/subdev/i2c/pad.o
+nvkm-y += nvkm/subdev/i2c/padnv04.o
+nvkm-y += nvkm/subdev/i2c/padg94.o
+nvkm-y += nvkm/subdev/i2c/padgm204.o
+nvkm-y += nvkm/subdev/i2c/nv04.o
+nvkm-y += nvkm/subdev/i2c/nv4e.o
+nvkm-y += nvkm/subdev/i2c/nv50.o
+nvkm-y += nvkm/subdev/i2c/g94.o
+nvkm-y += nvkm/subdev/i2c/gf110.o
+nvkm-y += nvkm/subdev/i2c/gf117.o
+nvkm-y += nvkm/subdev/i2c/gk104.o
+nvkm-y += nvkm/subdev/i2c/gm204.o
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/i2c/anx9805.c b/drivers/gpu/drm/nouveau/nvkm/subdev/i2c/anx9805.c
new file mode 100644 (file)
index 0000000..d17dd1c
--- /dev/null
@@ -0,0 +1,292 @@
+/*
+ * Copyright 2013 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 <bskeggs@redhat.com>
+ */
+#include "port.h"
+
+struct anx9805_i2c_port {
+       struct nvkm_i2c_port base;
+       u32 addr;
+       u32 ctrl;
+};
+
+static int
+anx9805_train(struct nvkm_i2c_port *port, int link_nr, int link_bw, bool enh)
+{
+       struct anx9805_i2c_port *chan = (void *)port;
+       struct nvkm_i2c_port *mast = (void *)nv_object(chan)->parent;
+       u8 tmp, i;
+
+       DBG("ANX9805 train %d 0x%02x %d\n", link_nr, link_bw, enh);
+
+       nv_wri2cr(mast, chan->addr, 0xa0, link_bw);
+       nv_wri2cr(mast, chan->addr, 0xa1, link_nr | (enh ? 0x80 : 0x00));
+       nv_wri2cr(mast, chan->addr, 0xa2, 0x01);
+       nv_wri2cr(mast, chan->addr, 0xa8, 0x01);
+
+       i = 0;
+       while ((tmp = nv_rdi2cr(mast, chan->addr, 0xa8)) & 0x01) {
+               mdelay(5);
+               if (i++ == 100) {
+                       nv_error(port, "link training timed out\n");
+                       return -ETIMEDOUT;
+               }
+       }
+
+       if (tmp & 0x70) {
+               nv_error(port, "link training failed: 0x%02x\n", tmp);
+               return -EIO;
+       }
+
+       return 1;
+}
+
+static int
+anx9805_aux(struct nvkm_i2c_port *port, bool retry,
+           u8 type, u32 addr, u8 *data, u8 size)
+{
+       struct anx9805_i2c_port *chan = (void *)port;
+       struct nvkm_i2c_port *mast = (void *)nv_object(chan)->parent;
+       int i, ret = -ETIMEDOUT;
+       u8 buf[16] = {};
+       u8 tmp;
+
+       DBG("%02x %05x %d\n", type, addr, size);
+
+       tmp = nv_rdi2cr(mast, chan->ctrl, 0x07) & ~0x04;
+       nv_wri2cr(mast, chan->ctrl, 0x07, tmp | 0x04);
+       nv_wri2cr(mast, chan->ctrl, 0x07, tmp);
+       nv_wri2cr(mast, chan->ctrl, 0xf7, 0x01);
+
+       nv_wri2cr(mast, chan->addr, 0xe4, 0x80);
+       if (!(type & 1)) {
+               memcpy(buf, data, size);
+               DBG("%16ph", buf);
+               for (i = 0; i < size; i++)
+                       nv_wri2cr(mast, chan->addr, 0xf0 + i, buf[i]);
+       }
+       nv_wri2cr(mast, chan->addr, 0xe5, ((size - 1) << 4) | type);
+       nv_wri2cr(mast, chan->addr, 0xe6, (addr & 0x000ff) >>  0);
+       nv_wri2cr(mast, chan->addr, 0xe7, (addr & 0x0ff00) >>  8);
+       nv_wri2cr(mast, chan->addr, 0xe8, (addr & 0xf0000) >> 16);
+       nv_wri2cr(mast, chan->addr, 0xe9, 0x01);
+
+       i = 0;
+       while ((tmp = nv_rdi2cr(mast, chan->addr, 0xe9)) & 0x01) {
+               mdelay(5);
+               if (i++ == 32)
+                       goto done;
+       }
+
+       if ((tmp = nv_rdi2cr(mast, chan->ctrl, 0xf7)) & 0x01) {
+               ret = -EIO;
+               goto done;
+       }
+
+       if (type & 1) {
+               for (i = 0; i < size; i++)
+                       buf[i] = nv_rdi2cr(mast, chan->addr, 0xf0 + i);
+               DBG("%16ph", buf);
+               memcpy(data, buf, size);
+       }
+
+       ret = 0;
+done:
+       nv_wri2cr(mast, chan->ctrl, 0xf7, 0x01);
+       return ret;
+}
+
+static const struct nvkm_i2c_func
+anx9805_aux_func = {
+       .aux = anx9805_aux,
+       .lnk_ctl = anx9805_train,
+};
+
+static int
+anx9805_aux_chan_ctor(struct nvkm_object *parent,
+                     struct nvkm_object *engine,
+                     struct nvkm_oclass *oclass, void *data, u32 index,
+                     struct nvkm_object **pobject)
+{
+       struct nvkm_i2c_port *mast = (void *)parent;
+       struct anx9805_i2c_port *chan;
+       int ret;
+
+       ret = nvkm_i2c_port_create(parent, engine, oclass, index,
+                                  &nvkm_i2c_aux_algo, &anx9805_aux_func,
+                                  &chan);
+       *pobject = nv_object(chan);
+       if (ret)
+               return ret;
+
+       switch ((oclass->handle & 0xff00) >> 8) {
+       case 0x0d:
+               chan->addr = 0x38;
+               chan->ctrl = 0x39;
+               break;
+       case 0x0e:
+               chan->addr = 0x3c;
+               chan->ctrl = 0x3b;
+               break;
+       default:
+               BUG_ON(1);
+       }
+
+       if (mast->adapter.algo == &i2c_bit_algo) {
+               struct i2c_algo_bit_data *algo = mast->adapter.algo_data;
+               algo->udelay = max(algo->udelay, 40);
+       }
+
+       return 0;
+}
+
+static struct nvkm_ofuncs
+anx9805_aux_ofuncs = {
+       .ctor =  anx9805_aux_chan_ctor,
+       .dtor = _nvkm_i2c_port_dtor,
+       .init = _nvkm_i2c_port_init,
+       .fini = _nvkm_i2c_port_fini,
+};
+
+static int
+anx9805_xfer(struct i2c_adapter *adap, struct i2c_msg *msgs, int num)
+{
+       struct anx9805_i2c_port *port = adap->algo_data;
+       struct nvkm_i2c_port *mast = (void *)nv_object(port)->parent;
+       struct i2c_msg *msg = msgs;
+       int ret = -ETIMEDOUT;
+       int i, j, cnt = num;
+       u8 seg = 0x00, off = 0x00, tmp;
+
+       tmp = nv_rdi2cr(mast, port->ctrl, 0x07) & ~0x10;
+       nv_wri2cr(mast, port->ctrl, 0x07, tmp | 0x10);
+       nv_wri2cr(mast, port->ctrl, 0x07, tmp);
+       nv_wri2cr(mast, port->addr, 0x43, 0x05);
+       mdelay(5);
+
+       while (cnt--) {
+               if ( (msg->flags & I2C_M_RD) && msg->addr == 0x50) {
+                       nv_wri2cr(mast, port->addr, 0x40, msg->addr << 1);
+                       nv_wri2cr(mast, port->addr, 0x41, seg);
+                       nv_wri2cr(mast, port->addr, 0x42, off);
+                       nv_wri2cr(mast, port->addr, 0x44, msg->len);
+                       nv_wri2cr(mast, port->addr, 0x45, 0x00);
+                       nv_wri2cr(mast, port->addr, 0x43, 0x01);
+                       for (i = 0; i < msg->len; i++) {
+                               j = 0;
+                               while (nv_rdi2cr(mast, port->addr, 0x46) & 0x10) {
+                                       mdelay(5);
+                                       if (j++ == 32)
+                                               goto done;
+                               }
+                               msg->buf[i] = nv_rdi2cr(mast, port->addr, 0x47);
+                       }
+               } else
+               if (!(msg->flags & I2C_M_RD)) {
+                       if (msg->addr == 0x50 && msg->len == 0x01) {
+                               off = msg->buf[0];
+                       } else
+                       if (msg->addr == 0x30 && msg->len == 0x01) {
+                               seg = msg->buf[0];
+                       } else
+                               goto done;
+               } else {
+                       goto done;
+               }
+               msg++;
+       }
+
+       ret = num;
+done:
+       nv_wri2cr(mast, port->addr, 0x43, 0x00);
+       return ret;
+}
+
+static u32
+anx9805_func(struct i2c_adapter *adap)
+{
+       return I2C_FUNC_I2C | I2C_FUNC_SMBUS_EMUL;
+}
+
+static const struct i2c_algorithm
+anx9805_i2c_algo = {
+       .master_xfer = anx9805_xfer,
+       .functionality = anx9805_func
+};
+
+static const struct nvkm_i2c_func
+anx9805_i2c_func = {
+};
+
+static int
+anx9805_ddc_port_ctor(struct nvkm_object *parent,
+                     struct nvkm_object *engine,
+                     struct nvkm_oclass *oclass, void *data, u32 index,
+                     struct nvkm_object **pobject)
+{
+       struct nvkm_i2c_port *mast = (void *)parent;
+       struct anx9805_i2c_port *port;
+       int ret;
+
+       ret = nvkm_i2c_port_create(parent, engine, oclass, index,
+                                  &anx9805_i2c_algo, &anx9805_i2c_func, &port);
+       *pobject = nv_object(port);
+       if (ret)
+               return ret;
+
+       switch ((oclass->handle & 0xff00) >> 8) {
+       case 0x0d:
+               port->addr = 0x3d;
+               port->ctrl = 0x39;
+               break;
+       case 0x0e:
+               port->addr = 0x3f;
+               port->ctrl = 0x3b;
+               break;
+       default:
+               BUG_ON(1);
+       }
+
+       if (mast->adapter.algo == &i2c_bit_algo) {
+               struct i2c_algo_bit_data *algo = mast->adapter.algo_data;
+               algo->udelay = max(algo->udelay, 40);
+       }
+
+       return 0;
+}
+
+static struct nvkm_ofuncs
+anx9805_ddc_ofuncs = {
+       .ctor =  anx9805_ddc_port_ctor,
+       .dtor = _nvkm_i2c_port_dtor,
+       .init = _nvkm_i2c_port_init,
+       .fini = _nvkm_i2c_port_fini,
+};
+
+struct nvkm_oclass
+nvkm_anx9805_sclass[] = {
+       { .handle = NV_I2C_TYPE_EXTDDC(0x0d), .ofuncs = &anx9805_ddc_ofuncs },
+       { .handle = NV_I2C_TYPE_EXTAUX(0x0d), .ofuncs = &anx9805_aux_ofuncs },
+       { .handle = NV_I2C_TYPE_EXTDDC(0x0e), .ofuncs = &anx9805_ddc_ofuncs },
+       { .handle = NV_I2C_TYPE_EXTAUX(0x0e), .ofuncs = &anx9805_aux_ofuncs },
+       {}
+};
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/i2c/aux.c b/drivers/gpu/drm/nouveau/nvkm/subdev/i2c/aux.c
new file mode 100644 (file)
index 0000000..1c18860
--- /dev/null
@@ -0,0 +1,113 @@
+/*
+ * 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 "priv.h"
+
+int
+nv_rdaux(struct nvkm_i2c_port *port, u32 addr, u8 *data, u8 size)
+{
+       struct nvkm_i2c *i2c = nvkm_i2c(port);
+       if (port->func->aux) {
+               int ret = i2c->acquire(port, 0);
+               if (ret == 0) {
+                       ret = port->func->aux(port, true, 9, addr, data, size);
+                       i2c->release(port);
+               }
+               return ret;
+       }
+       return -ENODEV;
+}
+
+int
+nv_wraux(struct nvkm_i2c_port *port, u32 addr, u8 *data, u8 size)
+{
+       struct nvkm_i2c *i2c = nvkm_i2c(port);
+       if (port->func->aux) {
+               int ret = i2c->acquire(port, 0);
+               if (ret == 0) {
+                       ret = port->func->aux(port, true, 8, addr, data, size);
+                       i2c->release(port);
+               }
+               return ret;
+       }
+       return -ENODEV;
+}
+
+static int
+aux_xfer(struct i2c_adapter *adap, struct i2c_msg *msgs, int num)
+{
+       struct nvkm_i2c_port *port = adap->algo_data;
+       struct nvkm_i2c *i2c = nvkm_i2c(port);
+       struct i2c_msg *msg = msgs;
+       int ret, mcnt = num;
+
+       if (!port->func->aux)
+               return -ENODEV;
+
+       ret = i2c->acquire(port, 0);
+       if (ret)
+               return ret;
+
+       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 = 1;
+                       else
+                               cmd = 0;
+
+                       if (mcnt || remaining > 16)
+                               cmd |= 4; /* MOT */
+
+                       ret = port->func->aux(port, true, cmd, msg->addr, ptr, cnt);
+                       if (ret < 0) {
+                               i2c->release(port);
+                               return ret;
+                       }
+
+                       ptr += cnt;
+                       remaining -= cnt;
+               }
+
+               msg++;
+       }
+
+       i2c->release(port);
+       return num;
+}
+
+static u32
+aux_func(struct i2c_adapter *adap)
+{
+       return I2C_FUNC_I2C | I2C_FUNC_SMBUS_EMUL;
+}
+
+const struct i2c_algorithm nvkm_i2c_aux_algo = {
+       .master_xfer = aux_xfer,
+       .functionality = aux_func
+};
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/i2c/base.c b/drivers/gpu/drm/nouveau/nvkm/subdev/i2c/base.c
new file mode 100644 (file)
index 0000000..9200f12
--- /dev/null
@@ -0,0 +1,622 @@
+/*
+ * Copyright 2013 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 "priv.h"
+#include "pad.h"
+
+#include <core/device.h>
+#include <core/notify.h>
+#include <core/option.h>
+#include <subdev/bios.h>
+#include <subdev/bios/dcb.h>
+
+/******************************************************************************
+ * interface to linux i2c bit-banging algorithm
+ *****************************************************************************/
+
+#ifdef CONFIG_NOUVEAU_I2C_INTERNAL_DEFAULT
+#define CSTMSEL true
+#else
+#define CSTMSEL false
+#endif
+
+static int
+nvkm_i2c_pre_xfer(struct i2c_adapter *adap)
+{
+       struct i2c_algo_bit_data *bit = adap->algo_data;
+       struct nvkm_i2c_port *port = bit->data;
+       return nvkm_i2c(port)->acquire(port, bit->timeout);
+}
+
+static void
+nvkm_i2c_post_xfer(struct i2c_adapter *adap)
+{
+       struct i2c_algo_bit_data *bit = adap->algo_data;
+       struct nvkm_i2c_port *port = bit->data;
+       return nvkm_i2c(port)->release(port);
+}
+
+static void
+nvkm_i2c_setscl(void *data, int state)
+{
+       struct nvkm_i2c_port *port = data;
+       port->func->drive_scl(port, state);
+}
+
+static void
+nvkm_i2c_setsda(void *data, int state)
+{
+       struct nvkm_i2c_port *port = data;
+       port->func->drive_sda(port, state);
+}
+
+static int
+nvkm_i2c_getscl(void *data)
+{
+       struct nvkm_i2c_port *port = data;
+       return port->func->sense_scl(port);
+}
+
+static int
+nvkm_i2c_getsda(void *data)
+{
+       struct nvkm_i2c_port *port = data;
+       return port->func->sense_sda(port);
+}
+
+/******************************************************************************
+ * base i2c "port" class implementation
+ *****************************************************************************/
+
+int
+_nvkm_i2c_port_fini(struct nvkm_object *object, bool suspend)
+{
+       struct nvkm_i2c_port *port = (void *)object;
+       struct nvkm_i2c_pad *pad = nvkm_i2c_pad(port);
+       nv_ofuncs(pad)->fini(nv_object(pad), suspend);
+       return nvkm_object_fini(&port->base, suspend);
+}
+
+void
+_nvkm_i2c_port_dtor(struct nvkm_object *object)
+{
+       struct nvkm_i2c_port *port = (void *)object;
+       i2c_del_adapter(&port->adapter);
+       nvkm_object_destroy(&port->base);
+}
+
+int
+nvkm_i2c_port_create_(struct nvkm_object *parent, struct nvkm_object *engine,
+                     struct nvkm_oclass *oclass, u8 index,
+                     const struct i2c_algorithm *algo,
+                     const struct nvkm_i2c_func *func,
+                     int size, void **pobject)
+{
+       struct nvkm_device *device = nv_device(parent);
+       struct nvkm_i2c *i2c = nvkm_i2c(parent);
+       struct nvkm_i2c_port *port;
+       int ret;
+
+       ret = nvkm_object_create_(parent, engine, oclass, 0, size, pobject);
+       port = *pobject;
+       if (ret)
+               return ret;
+
+       snprintf(port->adapter.name, sizeof(port->adapter.name),
+                "nvkm-%s-%d", device->name, index);
+       port->adapter.owner = THIS_MODULE;
+       port->adapter.dev.parent = nv_device_base(device);
+       port->index = index;
+       port->aux = -1;
+       port->func = func;
+       mutex_init(&port->mutex);
+
+       if ( algo == &nvkm_i2c_bit_algo &&
+           !nvkm_boolopt(device->cfgopt, "NvI2C", CSTMSEL)) {
+               struct i2c_algo_bit_data *bit;
+
+               bit = kzalloc(sizeof(*bit), GFP_KERNEL);
+               if (!bit)
+                       return -ENOMEM;
+
+               bit->udelay = 10;
+               bit->timeout = usecs_to_jiffies(2200);
+               bit->data = port;
+               bit->pre_xfer = nvkm_i2c_pre_xfer;
+               bit->post_xfer = nvkm_i2c_post_xfer;
+               bit->setsda = nvkm_i2c_setsda;
+               bit->setscl = nvkm_i2c_setscl;
+               bit->getsda = nvkm_i2c_getsda;
+               bit->getscl = nvkm_i2c_getscl;
+
+               port->adapter.algo_data = bit;
+               ret = i2c_bit_add_bus(&port->adapter);
+       } else {
+               port->adapter.algo_data = port;
+               port->adapter.algo = algo;
+               ret = i2c_add_adapter(&port->adapter);
+       }
+
+       if (ret == 0)
+               list_add_tail(&port->head, &i2c->ports);
+       return ret;
+}
+
+/******************************************************************************
+ * base i2c subdev class implementation
+ *****************************************************************************/
+
+static struct nvkm_i2c_port *
+nvkm_i2c_find(struct nvkm_i2c *i2c, u8 index)
+{
+       struct nvkm_bios *bios = nvkm_bios(i2c);
+       struct nvkm_i2c_port *port;
+
+       if (index == NV_I2C_DEFAULT(0) ||
+           index == NV_I2C_DEFAULT(1)) {
+               u8  ver, hdr, cnt, len;
+               u16 i2c = dcb_i2c_table(bios, &ver, &hdr, &cnt, &len);
+               if (i2c && ver >= 0x30) {
+                       u8 auxidx = nv_ro08(bios, i2c + 4);
+                       if (index == NV_I2C_DEFAULT(0))
+                               index = (auxidx & 0x0f) >> 0;
+                       else
+                               index = (auxidx & 0xf0) >> 4;
+               } else {
+                       index = 2;
+               }
+       }
+
+       list_for_each_entry(port, &i2c->ports, head) {
+               if (port->index == index)
+                       return port;
+       }
+
+       return NULL;
+}
+
+static struct nvkm_i2c_port *
+nvkm_i2c_find_type(struct nvkm_i2c *i2c, u16 type)
+{
+       struct nvkm_i2c_port *port;
+
+       list_for_each_entry(port, &i2c->ports, head) {
+               if (nv_hclass(port) == type)
+                       return port;
+       }
+
+       return NULL;
+}
+
+static void
+nvkm_i2c_release_pad(struct nvkm_i2c_port *port)
+{
+       struct nvkm_i2c_pad *pad = nvkm_i2c_pad(port);
+       struct nvkm_i2c *i2c = nvkm_i2c(port);
+
+       if (atomic_dec_and_test(&nv_object(pad)->usecount)) {
+               nv_ofuncs(pad)->fini(nv_object(pad), false);
+               wake_up_all(&i2c->wait);
+       }
+}
+
+static int
+nvkm_i2c_try_acquire_pad(struct nvkm_i2c_port *port)
+{
+       struct nvkm_i2c_pad *pad = nvkm_i2c_pad(port);
+
+       if (atomic_add_return(1, &nv_object(pad)->usecount) != 1) {
+               struct nvkm_object *owner = (void *)pad->port;
+               do {
+                       if (owner == (void *)port)
+                               return 0;
+                       owner = owner->parent;
+               } while(owner);
+               nvkm_i2c_release_pad(port);
+               return -EBUSY;
+       }
+
+       pad->next = port;
+       nv_ofuncs(pad)->init(nv_object(pad));
+       return 0;
+}
+
+static int
+nvkm_i2c_acquire_pad(struct nvkm_i2c_port *port, unsigned long timeout)
+{
+       struct nvkm_i2c *i2c = nvkm_i2c(port);
+
+       if (timeout) {
+               if (wait_event_timeout(i2c->wait,
+                                      nvkm_i2c_try_acquire_pad(port) == 0,
+                                      timeout) == 0)
+                       return -EBUSY;
+       } else {
+               wait_event(i2c->wait, nvkm_i2c_try_acquire_pad(port) == 0);
+       }
+
+       return 0;
+}
+
+static void
+nvkm_i2c_release(struct nvkm_i2c_port *port)
+__releases(pad->mutex)
+{
+       nvkm_i2c(port)->release_pad(port);
+       mutex_unlock(&port->mutex);
+}
+
+static int
+nvkm_i2c_acquire(struct nvkm_i2c_port *port, unsigned long timeout)
+__acquires(pad->mutex)
+{
+       int ret;
+       mutex_lock(&port->mutex);
+       if ((ret = nvkm_i2c(port)->acquire_pad(port, timeout)))
+               mutex_unlock(&port->mutex);
+       return ret;
+}
+
+static int
+nvkm_i2c_identify(struct nvkm_i2c *i2c, int index, const char *what,
+                 struct nvkm_i2c_board_info *info,
+                 bool (*match)(struct nvkm_i2c_port *,
+                               struct i2c_board_info *, void *), void *data)
+{
+       struct nvkm_i2c_port *port = nvkm_i2c_find(i2c, index);
+       int i;
+
+       if (!port) {
+               nv_debug(i2c, "no bus when probing %s on %d\n", what, index);
+               return -ENODEV;
+       }
+
+       nv_debug(i2c, "probing %ss on bus: %d\n", what, port->index);
+       for (i = 0; info[i].dev.addr; i++) {
+               u8 orig_udelay = 0;
+
+               if ((port->adapter.algo == &i2c_bit_algo) &&
+                   (info[i].udelay != 0)) {
+                       struct i2c_algo_bit_data *algo = port->adapter.algo_data;
+                       nv_debug(i2c, "using custom udelay %d instead of %d\n",
+                                info[i].udelay, algo->udelay);
+                       orig_udelay = algo->udelay;
+                       algo->udelay = info[i].udelay;
+               }
+
+               if (nv_probe_i2c(port, info[i].dev.addr) &&
+                   (!match || match(port, &info[i].dev, data))) {
+                       nv_info(i2c, "detected %s: %s\n", what,
+                               info[i].dev.type);
+                       return i;
+               }
+
+               if (orig_udelay) {
+                       struct i2c_algo_bit_data *algo = port->adapter.algo_data;
+                       algo->udelay = orig_udelay;
+               }
+       }
+
+       nv_debug(i2c, "no devices found.\n");
+       return -ENODEV;
+}
+
+static void
+nvkm_i2c_intr_fini(struct nvkm_event *event, int type, int index)
+{
+       struct nvkm_i2c *i2c = container_of(event, typeof(*i2c), event);
+       struct nvkm_i2c_port *port = i2c->find(i2c, index);
+       const struct nvkm_i2c_impl *impl = (void *)nv_object(i2c)->oclass;
+       if (port && port->aux >= 0)
+               impl->aux_mask(i2c, type, 1 << port->aux, 0);
+}
+
+static void
+nvkm_i2c_intr_init(struct nvkm_event *event, int type, int index)
+{
+       struct nvkm_i2c *i2c = container_of(event, typeof(*i2c), event);
+       struct nvkm_i2c_port *port = i2c->find(i2c, index);
+       const struct nvkm_i2c_impl *impl = (void *)nv_object(i2c)->oclass;
+       if (port && port->aux >= 0)
+               impl->aux_mask(i2c, type, 1 << port->aux, 1 << port->aux);
+}
+
+static int
+nvkm_i2c_intr_ctor(struct nvkm_object *object, void *data, u32 size,
+                     struct nvkm_notify *notify)
+{
+       struct nvkm_i2c_ntfy_req *req = data;
+       if (!WARN_ON(size != sizeof(*req))) {
+               notify->size  = sizeof(struct nvkm_i2c_ntfy_rep);
+               notify->types = req->mask;
+               notify->index = req->port;
+               return 0;
+       }
+       return -EINVAL;
+}
+
+static void
+nvkm_i2c_intr(struct nvkm_subdev *subdev)
+{
+       struct nvkm_i2c_impl *impl = (void *)nv_oclass(subdev);
+       struct nvkm_i2c *i2c = nvkm_i2c(subdev);
+       struct nvkm_i2c_port *port;
+       u32 hi, lo, rq, tx, e;
+
+       if (impl->aux_stat) {
+               impl->aux_stat(i2c, &hi, &lo, &rq, &tx);
+               if (hi || lo || rq || tx) {
+                       list_for_each_entry(port, &i2c->ports, head) {
+                               if (e = 0, port->aux < 0)
+                                       continue;
+
+                               if (hi & (1 << port->aux)) e |= NVKM_I2C_PLUG;
+                               if (lo & (1 << port->aux)) e |= NVKM_I2C_UNPLUG;
+                               if (rq & (1 << port->aux)) e |= NVKM_I2C_IRQ;
+                               if (tx & (1 << port->aux)) e |= NVKM_I2C_DONE;
+                               if (e) {
+                                       struct nvkm_i2c_ntfy_rep rep = {
+                                               .mask = e,
+                                       };
+                                       nvkm_event_send(&i2c->event, rep.mask,
+                                                       port->index, &rep,
+                                                       sizeof(rep));
+                               }
+                       }
+               }
+       }
+}
+
+static const struct nvkm_event_func
+nvkm_i2c_intr_func = {
+       .ctor = nvkm_i2c_intr_ctor,
+       .init = nvkm_i2c_intr_init,
+       .fini = nvkm_i2c_intr_fini,
+};
+
+int
+_nvkm_i2c_fini(struct nvkm_object *object, bool suspend)
+{
+       struct nvkm_i2c_impl *impl = (void *)nv_oclass(object);
+       struct nvkm_i2c *i2c = (void *)object;
+       struct nvkm_i2c_port *port;
+       u32 mask;
+       int ret;
+
+       list_for_each_entry(port, &i2c->ports, head) {
+               ret = nv_ofuncs(port)->fini(nv_object(port), suspend);
+               if (ret && suspend)
+                       goto fail;
+       }
+
+       if ((mask = (1 << impl->aux) - 1), impl->aux_stat) {
+               impl->aux_mask(i2c, NVKM_I2C_ANY, mask, 0);
+               impl->aux_stat(i2c, &mask, &mask, &mask, &mask);
+       }
+
+       return nvkm_subdev_fini(&i2c->base, suspend);
+fail:
+       list_for_each_entry_continue_reverse(port, &i2c->ports, head) {
+               nv_ofuncs(port)->init(nv_object(port));
+       }
+
+       return ret;
+}
+
+int
+_nvkm_i2c_init(struct nvkm_object *object)
+{
+       struct nvkm_i2c *i2c = (void *)object;
+       struct nvkm_i2c_port *port;
+       int ret;
+
+       ret = nvkm_subdev_init(&i2c->base);
+       if (ret == 0) {
+               list_for_each_entry(port, &i2c->ports, head) {
+                       ret = nv_ofuncs(port)->init(nv_object(port));
+                       if (ret)
+                               goto fail;
+               }
+       }
+
+       return ret;
+fail:
+       list_for_each_entry_continue_reverse(port, &i2c->ports, head) {
+               nv_ofuncs(port)->fini(nv_object(port), false);
+       }
+
+       return ret;
+}
+
+void
+_nvkm_i2c_dtor(struct nvkm_object *object)
+{
+       struct nvkm_i2c *i2c = (void *)object;
+       struct nvkm_i2c_port *port, *temp;
+
+       nvkm_event_fini(&i2c->event);
+
+       list_for_each_entry_safe(port, temp, &i2c->ports, head) {
+               nvkm_object_ref(NULL, (struct nvkm_object **)&port);
+       }
+
+       nvkm_subdev_destroy(&i2c->base);
+}
+
+static struct nvkm_oclass *
+nvkm_i2c_extdev_sclass[] = {
+       nvkm_anx9805_sclass,
+};
+
+static void
+nvkm_i2c_create_port(struct nvkm_i2c *i2c, int index, u8 type,
+                    struct dcb_i2c_entry *info)
+{
+       const struct nvkm_i2c_impl *impl = (void *)nv_oclass(i2c);
+       struct nvkm_oclass *oclass;
+       struct nvkm_object *parent;
+       struct nvkm_object *object;
+       int ret, pad;
+
+       if (info->share != DCB_I2C_UNUSED) {
+               pad    = info->share;
+               oclass = impl->pad_s;
+       } else {
+               if (type != DCB_I2C_NVIO_AUX)
+                       pad = 0x100 + info->drive;
+               else
+                       pad = 0x100 + info->auxch;
+               oclass = impl->pad_x;
+       }
+
+       ret = nvkm_object_ctor(nv_object(i2c), NULL, oclass,
+                              NULL, pad, &parent);
+       if (ret < 0)
+               return;
+
+       oclass = impl->sclass;
+       do {
+               ret = -EINVAL;
+               if (oclass->handle == type) {
+                       ret = nvkm_object_ctor(parent, NULL, oclass,
+                                              info, index, &object);
+               }
+       } while (ret && (++oclass)->handle);
+
+       nvkm_object_ref(NULL, &parent);
+}
+
+int
+nvkm_i2c_create_(struct nvkm_object *parent, struct nvkm_object *engine,
+                struct nvkm_oclass *oclass, int length, void **pobject)
+{
+       struct nvkm_bios *bios = nvkm_bios(parent);
+       struct nvkm_i2c *i2c;
+       struct nvkm_object *object;
+       struct dcb_i2c_entry info;
+       int ret, i, j, index = -1;
+       struct dcb_output outp;
+       u8  ver, hdr;
+       u32 data;
+
+       ret = nvkm_subdev_create(parent, engine, oclass, 0, "I2C", "i2c", &i2c);
+       *pobject = nv_object(i2c);
+       if (ret)
+               return ret;
+
+       nv_subdev(i2c)->intr = nvkm_i2c_intr;
+       i2c->find = nvkm_i2c_find;
+       i2c->find_type = nvkm_i2c_find_type;
+       i2c->acquire_pad = nvkm_i2c_acquire_pad;
+       i2c->release_pad = nvkm_i2c_release_pad;
+       i2c->acquire = nvkm_i2c_acquire;
+       i2c->release = nvkm_i2c_release;
+       i2c->identify = nvkm_i2c_identify;
+       init_waitqueue_head(&i2c->wait);
+       INIT_LIST_HEAD(&i2c->ports);
+
+       while (!dcb_i2c_parse(bios, ++index, &info)) {
+               switch (info.type) {
+               case DCB_I2C_NV04_BIT:
+               case DCB_I2C_NV4E_BIT:
+               case DCB_I2C_NVIO_BIT:
+                       nvkm_i2c_create_port(i2c, NV_I2C_PORT(index),
+                                            info.type, &info);
+                       break;
+               case DCB_I2C_NVIO_AUX:
+                       nvkm_i2c_create_port(i2c, NV_I2C_AUX(index),
+                                            info.type, &info);
+                       break;
+               case DCB_I2C_PMGR:
+                       if (info.drive != DCB_I2C_UNUSED) {
+                               nvkm_i2c_create_port(i2c, NV_I2C_PORT(index),
+                                                    DCB_I2C_NVIO_BIT, &info);
+                       }
+                       if (info.auxch != DCB_I2C_UNUSED) {
+                               nvkm_i2c_create_port(i2c, NV_I2C_AUX(index),
+                                                    DCB_I2C_NVIO_AUX, &info);
+                       }
+                       break;
+               case DCB_I2C_UNUSED:
+               default:
+                       continue;
+               }
+       }
+
+       /* in addition to the busses specified in the i2c table, there
+        * may be ddc/aux channels hiding behind external tmds/dp/etc
+        * transmitters.
+        */
+       index = NV_I2C_EXT(0);
+       i = -1;
+       while ((data = dcb_outp_parse(bios, ++i, &ver, &hdr, &outp))) {
+               if (!outp.location || !outp.extdev)
+                       continue;
+
+               switch (outp.type) {
+               case DCB_OUTPUT_TMDS:
+                       info.type = NV_I2C_TYPE_EXTDDC(outp.extdev);
+                       break;
+               case DCB_OUTPUT_DP:
+                       info.type = NV_I2C_TYPE_EXTAUX(outp.extdev);
+                       break;
+               default:
+                       continue;
+               }
+
+               ret = -ENODEV;
+               j = -1;
+               while (ret && ++j < ARRAY_SIZE(nvkm_i2c_extdev_sclass)) {
+                       parent = nv_object(i2c->find(i2c, outp.i2c_index));
+                       oclass = nvkm_i2c_extdev_sclass[j];
+                       do {
+                               if (oclass->handle != info.type)
+                                       continue;
+                               ret = nvkm_object_ctor(parent, NULL, oclass,
+                                                      NULL, index++, &object);
+                       } while (ret && (++oclass)->handle);
+               }
+       }
+
+       ret = nvkm_event_init(&nvkm_i2c_intr_func, 4, index, &i2c->event);
+       if (ret)
+               return ret;
+
+       return 0;
+}
+
+int
+_nvkm_i2c_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+              struct nvkm_oclass *oclass, void *data, u32 size,
+              struct nvkm_object **pobject)
+{
+       struct nvkm_i2c *i2c;
+       int ret;
+
+       ret = nvkm_i2c_create(parent, engine, oclass, &i2c);
+       *pobject = nv_object(i2c);
+       if (ret)
+               return ret;
+
+       return 0;
+}
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/i2c/bit.c b/drivers/gpu/drm/nouveau/nvkm/subdev/i2c/bit.c
new file mode 100644 (file)
index 0000000..861a453
--- /dev/null
@@ -0,0 +1,233 @@
+/*
+ * Copyright 2012 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 "priv.h"
+
+#ifdef CONFIG_NOUVEAU_I2C_INTERNAL
+#define T_TIMEOUT  2200000
+#define T_RISEFALL 1000
+#define T_HOLD     5000
+
+static inline void
+i2c_drive_scl(struct nvkm_i2c_port *port, int state)
+{
+       port->func->drive_scl(port, state);
+}
+
+static inline void
+i2c_drive_sda(struct nvkm_i2c_port *port, int state)
+{
+       port->func->drive_sda(port, state);
+}
+
+static inline int
+i2c_sense_scl(struct nvkm_i2c_port *port)
+{
+       return port->func->sense_scl(port);
+}
+
+static inline int
+i2c_sense_sda(struct nvkm_i2c_port *port)
+{
+       return port->func->sense_sda(port);
+}
+
+static void
+i2c_delay(struct nvkm_i2c_port *port, u32 nsec)
+{
+       udelay((nsec + 500) / 1000);
+}
+
+static bool
+i2c_raise_scl(struct nvkm_i2c_port *port)
+{
+       u32 timeout = T_TIMEOUT / T_RISEFALL;
+
+       i2c_drive_scl(port, 1);
+       do {
+               i2c_delay(port, T_RISEFALL);
+       } while (!i2c_sense_scl(port) && --timeout);
+
+       return timeout != 0;
+}
+
+static int
+i2c_start(struct nvkm_i2c_port *port)
+{
+       int ret = 0;
+
+       if (!i2c_sense_scl(port) ||
+           !i2c_sense_sda(port)) {
+               i2c_drive_scl(port, 0);
+               i2c_drive_sda(port, 1);
+               if (!i2c_raise_scl(port))
+                       ret = -EBUSY;
+       }
+
+       i2c_drive_sda(port, 0);
+       i2c_delay(port, T_HOLD);
+       i2c_drive_scl(port, 0);
+       i2c_delay(port, T_HOLD);
+       return ret;
+}
+
+static void
+i2c_stop(struct nvkm_i2c_port *port)
+{
+       i2c_drive_scl(port, 0);
+       i2c_drive_sda(port, 0);
+       i2c_delay(port, T_RISEFALL);
+
+       i2c_drive_scl(port, 1);
+       i2c_delay(port, T_HOLD);
+       i2c_drive_sda(port, 1);
+       i2c_delay(port, T_HOLD);
+}
+
+static int
+i2c_bitw(struct nvkm_i2c_port *port, int sda)
+{
+       i2c_drive_sda(port, sda);
+       i2c_delay(port, T_RISEFALL);
+
+       if (!i2c_raise_scl(port))
+               return -ETIMEDOUT;
+       i2c_delay(port, T_HOLD);
+
+       i2c_drive_scl(port, 0);
+       i2c_delay(port, T_HOLD);
+       return 0;
+}
+
+static int
+i2c_bitr(struct nvkm_i2c_port *port)
+{
+       int sda;
+
+       i2c_drive_sda(port, 1);
+       i2c_delay(port, T_RISEFALL);
+
+       if (!i2c_raise_scl(port))
+               return -ETIMEDOUT;
+       i2c_delay(port, T_HOLD);
+
+       sda = i2c_sense_sda(port);
+
+       i2c_drive_scl(port, 0);
+       i2c_delay(port, T_HOLD);
+       return sda;
+}
+
+static int
+i2c_get_byte(struct nvkm_i2c_port *port, u8 *byte, bool last)
+{
+       int i, bit;
+
+       *byte = 0;
+       for (i = 7; i >= 0; i--) {
+               bit = i2c_bitr(port);
+               if (bit < 0)
+                       return bit;
+               *byte |= bit << i;
+       }
+
+       return i2c_bitw(port, last ? 1 : 0);
+}
+
+static int
+i2c_put_byte(struct nvkm_i2c_port *port, u8 byte)
+{
+       int i, ret;
+       for (i = 7; i >= 0; i--) {
+               ret = i2c_bitw(port, !!(byte & (1 << i)));
+               if (ret < 0)
+                       return ret;
+       }
+
+       ret = i2c_bitr(port);
+       if (ret == 1) /* nack */
+               ret = -EIO;
+       return ret;
+}
+
+static int
+i2c_addr(struct nvkm_i2c_port *port, struct i2c_msg *msg)
+{
+       u32 addr = msg->addr << 1;
+       if (msg->flags & I2C_M_RD)
+               addr |= 1;
+       return i2c_put_byte(port, addr);
+}
+
+static int
+i2c_bit_xfer(struct i2c_adapter *adap, struct i2c_msg *msgs, int num)
+{
+       struct nvkm_i2c_port *port = adap->algo_data;
+       struct i2c_msg *msg = msgs;
+       int ret = 0, mcnt = num;
+
+       ret = nvkm_i2c(port)->acquire(port, nsecs_to_jiffies(T_TIMEOUT));
+       if (ret)
+               return ret;
+
+       while (!ret && mcnt--) {
+               u8 remaining = msg->len;
+               u8 *ptr = msg->buf;
+
+               ret = i2c_start(port);
+               if (ret == 0)
+                       ret = i2c_addr(port, msg);
+
+               if (msg->flags & I2C_M_RD) {
+                       while (!ret && remaining--)
+                               ret = i2c_get_byte(port, ptr++, !remaining);
+               } else {
+                       while (!ret && remaining--)
+                               ret = i2c_put_byte(port, *ptr++);
+               }
+
+               msg++;
+       }
+
+       i2c_stop(port);
+       nvkm_i2c(port)->release(port);
+       return (ret < 0) ? ret : num;
+}
+#else
+static int
+i2c_bit_xfer(struct i2c_adapter *adap, struct i2c_msg *msgs, int num)
+{
+       return -ENODEV;
+}
+#endif
+
+static u32
+i2c_bit_func(struct i2c_adapter *adap)
+{
+       return I2C_FUNC_I2C | I2C_FUNC_SMBUS_EMUL;
+}
+
+const struct i2c_algorithm nvkm_i2c_bit_algo = {
+       .master_xfer = i2c_bit_xfer,
+       .functionality = i2c_bit_func
+};
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/i2c/g94.c b/drivers/gpu/drm/nouveau/nvkm/subdev/i2c/g94.c
new file mode 100644 (file)
index 0000000..2a2dd47
--- /dev/null
@@ -0,0 +1,279 @@
+/*
+ * Copyright 2012 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 "nv50.h"
+
+void
+g94_aux_stat(struct nvkm_i2c *i2c, u32 *hi, u32 *lo, u32 *rq, u32 *tx)
+{
+       u32 intr = nv_rd32(i2c, 0x00e06c);
+       u32 stat = nv_rd32(i2c, 0x00e068) & intr, i;
+       for (i = 0, *hi = *lo = *rq = *tx = 0; i < 8; i++) {
+               if ((stat & (1 << (i * 4)))) *hi |= 1 << i;
+               if ((stat & (2 << (i * 4)))) *lo |= 1 << i;
+               if ((stat & (4 << (i * 4)))) *rq |= 1 << i;
+               if ((stat & (8 << (i * 4)))) *tx |= 1 << i;
+       }
+       nv_wr32(i2c, 0x00e06c, intr);
+}
+
+void
+g94_aux_mask(struct nvkm_i2c *i2c, u32 type, u32 mask, u32 data)
+{
+       u32 temp = nv_rd32(i2c, 0x00e068), i;
+       for (i = 0; i < 8; i++) {
+               if (mask & (1 << i)) {
+                       if (!(data & (1 << i))) {
+                               temp &= ~(type << (i * 4));
+                               continue;
+                       }
+                       temp |= type << (i * 4);
+               }
+       }
+       nv_wr32(i2c, 0x00e068, temp);
+}
+
+#define AUX_DBG(fmt, args...) nv_debug(aux, "AUXCH(%d): " fmt, ch, ##args)
+#define AUX_ERR(fmt, args...) nv_error(aux, "AUXCH(%d): " fmt, ch, ##args)
+
+static void
+auxch_fini(struct nvkm_i2c *aux, int ch)
+{
+       nv_mask(aux, 0x00e4e4 + (ch * 0x50), 0x00310000, 0x00000000);
+}
+
+static int
+auxch_init(struct nvkm_i2c *aux, int ch)
+{
+       const u32 unksel = 1; /* nfi which to use, or if it matters.. */
+       const u32 ureq = unksel ? 0x00100000 : 0x00200000;
+       const u32 urep = unksel ? 0x01000000 : 0x02000000;
+       u32 ctrl, timeout;
+
+       /* wait up to 1ms for any previous transaction to be done... */
+       timeout = 1000;
+       do {
+               ctrl = nv_rd32(aux, 0x00e4e4 + (ch * 0x50));
+               udelay(1);
+               if (!timeout--) {
+                       AUX_ERR("begin idle timeout 0x%08x\n", ctrl);
+                       return -EBUSY;
+               }
+       } while (ctrl & 0x03010000);
+
+       /* set some magic, and wait up to 1ms for it to appear */
+       nv_mask(aux, 0x00e4e4 + (ch * 0x50), 0x00300000, ureq);
+       timeout = 1000;
+       do {
+               ctrl = nv_rd32(aux, 0x00e4e4 + (ch * 0x50));
+               udelay(1);
+               if (!timeout--) {
+                       AUX_ERR("magic wait 0x%08x\n", ctrl);
+                       auxch_fini(aux, ch);
+                       return -EBUSY;
+               }
+       } while ((ctrl & 0x03000000) != urep);
+
+       return 0;
+}
+
+int
+g94_aux(struct nvkm_i2c_port *base, bool retry,
+        u8 type, u32 addr, u8 *data, u8 size)
+{
+       struct nvkm_i2c *aux = nvkm_i2c(base);
+       struct nv50_i2c_port *port = (void *)base;
+       u32 ctrl, stat, timeout, retries;
+       u32 xbuf[4] = {};
+       int ch = port->addr;
+       int ret, i;
+
+       AUX_DBG("%d: 0x%08x %d\n", type, addr, size);
+
+       ret = auxch_init(aux, ch);
+       if (ret)
+               goto out;
+
+       stat = nv_rd32(aux, 0x00e4e8 + (ch * 0x50));
+       if (!(stat & 0x10000000)) {
+               AUX_DBG("sink not detected\n");
+               ret = -ENXIO;
+               goto out;
+       }
+
+       if (!(type & 1)) {
+               memcpy(xbuf, data, size);
+               for (i = 0; i < 16; i += 4) {
+                       AUX_DBG("wr 0x%08x\n", xbuf[i / 4]);
+                       nv_wr32(aux, 0x00e4c0 + (ch * 0x50) + i, xbuf[i / 4]);
+               }
+       }
+
+       ctrl  = nv_rd32(aux, 0x00e4e4 + (ch * 0x50));
+       ctrl &= ~0x0001f0ff;
+       ctrl |= type << 12;
+       ctrl |= size - 1;
+       nv_wr32(aux, 0x00e4e0 + (ch * 0x50), addr);
+
+       /* (maybe) retry transaction a number of times on failure... */
+       for (retries = 0; !ret && retries < 32; retries++) {
+               /* reset, and delay a while if this is a retry */
+               nv_wr32(aux, 0x00e4e4 + (ch * 0x50), 0x80000000 | ctrl);
+               nv_wr32(aux, 0x00e4e4 + (ch * 0x50), 0x00000000 | ctrl);
+               if (retries)
+                       udelay(400);
+
+               /* transaction request, wait up to 1ms for it to complete */
+               nv_wr32(aux, 0x00e4e4 + (ch * 0x50), 0x00010000 | ctrl);
+
+               timeout = 1000;
+               do {
+                       ctrl = nv_rd32(aux, 0x00e4e4 + (ch * 0x50));
+                       udelay(1);
+                       if (!timeout--) {
+                               AUX_ERR("tx req timeout 0x%08x\n", ctrl);
+                               ret = -EIO;
+                               goto out;
+                       }
+               } while (ctrl & 0x00010000);
+               ret = 1;
+
+               /* read status, and check if transaction completed ok */
+               stat = nv_mask(aux, 0x00e4e8 + (ch * 0x50), 0, 0);
+               if ((stat & 0x000f0000) == 0x00080000 ||
+                   (stat & 0x000f0000) == 0x00020000)
+                       ret = retry ? 0 : 1;
+               if ((stat & 0x00000100))
+                       ret = -ETIMEDOUT;
+               if ((stat & 0x00000e00))
+                       ret = -EIO;
+
+               AUX_DBG("%02d 0x%08x 0x%08x\n", retries, ctrl, stat);
+       }
+
+       if (type & 1) {
+               for (i = 0; i < 16; i += 4) {
+                       xbuf[i / 4] = nv_rd32(aux, 0x00e4d0 + (ch * 0x50) + i);
+                       AUX_DBG("rd 0x%08x\n", xbuf[i / 4]);
+               }
+               memcpy(data, xbuf, size);
+       }
+
+out:
+       auxch_fini(aux, ch);
+       return ret < 0 ? ret : (stat & 0x000f0000) >> 16;
+}
+
+static const struct nvkm_i2c_func
+g94_i2c_func = {
+       .drive_scl = nv50_i2c_drive_scl,
+       .drive_sda = nv50_i2c_drive_sda,
+       .sense_scl = nv50_i2c_sense_scl,
+       .sense_sda = nv50_i2c_sense_sda,
+};
+
+static int
+g94_i2c_port_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+                 struct nvkm_oclass *oclass, void *data, u32 index,
+                 struct nvkm_object **pobject)
+{
+       struct dcb_i2c_entry *info = data;
+       struct nv50_i2c_port *port;
+       int ret;
+
+       ret = nvkm_i2c_port_create(parent, engine, oclass, index,
+                                  &nvkm_i2c_bit_algo, &g94_i2c_func, &port);
+       *pobject = nv_object(port);
+       if (ret)
+               return ret;
+
+       if (info->drive >= nv50_i2c_addr_nr)
+               return -EINVAL;
+
+       port->state = 7;
+       port->addr = nv50_i2c_addr[info->drive];
+       return 0;
+}
+
+static const struct nvkm_i2c_func
+g94_aux_func = {
+       .aux       = g94_aux,
+};
+
+int
+g94_aux_port_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+                 struct nvkm_oclass *oclass, void *data, u32 index,
+                 struct nvkm_object **pobject)
+{
+       struct dcb_i2c_entry *info = data;
+       struct nv50_i2c_port *port;
+       int ret;
+
+       ret = nvkm_i2c_port_create(parent, engine, oclass, index,
+                                  &nvkm_i2c_aux_algo, &g94_aux_func, &port);
+       *pobject = nv_object(port);
+       if (ret)
+               return ret;
+
+       port->base.aux = info->auxch;
+       port->addr = info->auxch;
+       return 0;
+}
+
+static struct nvkm_oclass
+g94_i2c_sclass[] = {
+       { .handle = NV_I2C_TYPE_DCBI2C(DCB_I2C_NVIO_BIT),
+         .ofuncs = &(struct nvkm_ofuncs) {
+                 .ctor = g94_i2c_port_ctor,
+                 .dtor = _nvkm_i2c_port_dtor,
+                 .init = nv50_i2c_port_init,
+                 .fini = _nvkm_i2c_port_fini,
+         },
+       },
+       { .handle = NV_I2C_TYPE_DCBI2C(DCB_I2C_NVIO_AUX),
+         .ofuncs = &(struct nvkm_ofuncs) {
+                 .ctor = g94_aux_port_ctor,
+                 .dtor = _nvkm_i2c_port_dtor,
+                 .init = _nvkm_i2c_port_init,
+                 .fini = _nvkm_i2c_port_fini,
+         },
+       },
+       {}
+};
+
+struct nvkm_oclass *
+g94_i2c_oclass = &(struct nvkm_i2c_impl) {
+       .base.handle = NV_SUBDEV(I2C, 0x94),
+       .base.ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = _nvkm_i2c_ctor,
+               .dtor = _nvkm_i2c_dtor,
+               .init = _nvkm_i2c_init,
+               .fini = _nvkm_i2c_fini,
+       },
+       .sclass = g94_i2c_sclass,
+       .pad_x = &nv04_i2c_pad_oclass,
+       .pad_s = &g94_i2c_pad_oclass,
+       .aux = 4,
+       .aux_stat = g94_aux_stat,
+       .aux_mask = g94_aux_mask,
+}.base;
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/i2c/gf110.c b/drivers/gpu/drm/nouveau/nvkm/subdev/i2c/gf110.c
new file mode 100644 (file)
index 0000000..4d4ac66
--- /dev/null
@@ -0,0 +1,106 @@
+/*
+ * Copyright 2012 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 "nv50.h"
+
+static int
+gf110_i2c_sense_scl(struct nvkm_i2c_port *base)
+{
+       struct nv50_i2c_priv *priv = (void *)nvkm_i2c(base);
+       struct nv50_i2c_port *port = (void *)base;
+       return !!(nv_rd32(priv, port->addr) & 0x00000010);
+}
+
+static int
+gf110_i2c_sense_sda(struct nvkm_i2c_port *base)
+{
+       struct nv50_i2c_priv *priv = (void *)nvkm_i2c(base);
+       struct nv50_i2c_port *port = (void *)base;
+       return !!(nv_rd32(priv, port->addr) & 0x00000020);
+}
+
+static const struct nvkm_i2c_func
+gf110_i2c_func = {
+       .drive_scl = nv50_i2c_drive_scl,
+       .drive_sda = nv50_i2c_drive_sda,
+       .sense_scl = gf110_i2c_sense_scl,
+       .sense_sda = gf110_i2c_sense_sda,
+};
+
+int
+gf110_i2c_port_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+                   struct nvkm_oclass *oclass, void *data, u32 index,
+                   struct nvkm_object **pobject)
+{
+       struct dcb_i2c_entry *info = data;
+       struct nv50_i2c_port *port;
+       int ret;
+
+       ret = nvkm_i2c_port_create(parent, engine, oclass, index,
+                                  &nvkm_i2c_bit_algo, &gf110_i2c_func, &port);
+       *pobject = nv_object(port);
+       if (ret)
+               return ret;
+
+       port->state = 0x00000007;
+       port->addr = 0x00d014 + (info->drive * 0x20);
+       return 0;
+}
+
+struct nvkm_oclass
+gf110_i2c_sclass[] = {
+       { .handle = NV_I2C_TYPE_DCBI2C(DCB_I2C_NVIO_BIT),
+         .ofuncs = &(struct nvkm_ofuncs) {
+                 .ctor = gf110_i2c_port_ctor,
+                 .dtor = _nvkm_i2c_port_dtor,
+                 .init = nv50_i2c_port_init,
+                 .fini = _nvkm_i2c_port_fini,
+         },
+       },
+       { .handle = NV_I2C_TYPE_DCBI2C(DCB_I2C_NVIO_AUX),
+         .ofuncs = &(struct nvkm_ofuncs) {
+                 .ctor = g94_aux_port_ctor,
+                 .dtor = _nvkm_i2c_port_dtor,
+                 .init = _nvkm_i2c_port_init,
+                 .fini = _nvkm_i2c_port_fini,
+         },
+       },
+       {}
+};
+
+struct nvkm_oclass *
+gf110_i2c_oclass = &(struct nvkm_i2c_impl) {
+       .base.handle = NV_SUBDEV(I2C, 0xd0),
+       .base.ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = _nvkm_i2c_ctor,
+               .dtor = _nvkm_i2c_dtor,
+               .init = _nvkm_i2c_init,
+               .fini = _nvkm_i2c_fini,
+       },
+       .sclass = gf110_i2c_sclass,
+       .pad_x = &nv04_i2c_pad_oclass,
+       .pad_s = &g94_i2c_pad_oclass,
+       .aux = 4,
+       .aux_stat = g94_aux_stat,
+       .aux_mask = g94_aux_mask,
+}.base;
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/i2c/gf117.c b/drivers/gpu/drm/nouveau/nvkm/subdev/i2c/gf117.c
new file mode 100644 (file)
index 0000000..e290b40
--- /dev/null
@@ -0,0 +1,38 @@
+/*
+ * Copyright 2012 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 "nv50.h"
+
+struct nvkm_oclass *
+gf117_i2c_oclass = &(struct nvkm_i2c_impl) {
+       .base.handle = NV_SUBDEV(I2C, 0xd7),
+       .base.ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = _nvkm_i2c_ctor,
+               .dtor = _nvkm_i2c_dtor,
+               .init = _nvkm_i2c_init,
+               .fini = _nvkm_i2c_fini,
+       },
+       .sclass = gf110_i2c_sclass,
+       .pad_x = &nv04_i2c_pad_oclass,
+       .pad_s = &nv04_i2c_pad_oclass,
+}.base;
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/i2c/gk104.c b/drivers/gpu/drm/nouveau/nvkm/subdev/i2c/gk104.c
new file mode 100644 (file)
index 0000000..1a46490
--- /dev/null
@@ -0,0 +1,71 @@
+/*
+ * Copyright 2012 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 "nv50.h"
+
+void
+gk104_aux_stat(struct nvkm_i2c *i2c, u32 *hi, u32 *lo, u32 *rq, u32 *tx)
+{
+       u32 intr = nv_rd32(i2c, 0x00dc60);
+       u32 stat = nv_rd32(i2c, 0x00dc68) & intr, i;
+       for (i = 0, *hi = *lo = *rq = *tx = 0; i < 8; i++) {
+               if ((stat & (1 << (i * 4)))) *hi |= 1 << i;
+               if ((stat & (2 << (i * 4)))) *lo |= 1 << i;
+               if ((stat & (4 << (i * 4)))) *rq |= 1 << i;
+               if ((stat & (8 << (i * 4)))) *tx |= 1 << i;
+       }
+       nv_wr32(i2c, 0x00dc60, intr);
+}
+
+void
+gk104_aux_mask(struct nvkm_i2c *i2c, u32 type, u32 mask, u32 data)
+{
+       u32 temp = nv_rd32(i2c, 0x00dc68), i;
+       for (i = 0; i < 8; i++) {
+               if (mask & (1 << i)) {
+                       if (!(data & (1 << i))) {
+                               temp &= ~(type << (i * 4));
+                               continue;
+                       }
+                       temp |= type << (i * 4);
+               }
+       }
+       nv_wr32(i2c, 0x00dc68, temp);
+}
+
+struct nvkm_oclass *
+gk104_i2c_oclass = &(struct nvkm_i2c_impl) {
+       .base.handle = NV_SUBDEV(I2C, 0xe0),
+       .base.ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = _nvkm_i2c_ctor,
+               .dtor = _nvkm_i2c_dtor,
+               .init = _nvkm_i2c_init,
+               .fini = _nvkm_i2c_fini,
+       },
+       .sclass = gf110_i2c_sclass,
+       .pad_x = &nv04_i2c_pad_oclass,
+       .pad_s = &g94_i2c_pad_oclass,
+       .aux = 4,
+       .aux_stat = gk104_aux_stat,
+       .aux_mask = gk104_aux_mask,
+}.base;
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/i2c/gm204.c b/drivers/gpu/drm/nouveau/nvkm/subdev/i2c/gm204.c
new file mode 100644 (file)
index 0000000..ab64237
--- /dev/null
@@ -0,0 +1,219 @@
+/*
+ * Copyright 2012 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 "nv50.h"
+
+#define AUX_DBG(fmt, args...) nv_debug(aux, "AUXCH(%d): " fmt, ch, ##args)
+#define AUX_ERR(fmt, args...) nv_error(aux, "AUXCH(%d): " fmt, ch, ##args)
+
+static void
+auxch_fini(struct nvkm_i2c *aux, int ch)
+{
+       nv_mask(aux, 0x00d954 + (ch * 0x50), 0x00310000, 0x00000000);
+}
+
+static int
+auxch_init(struct nvkm_i2c *aux, int ch)
+{
+       const u32 unksel = 1; /* nfi which to use, or if it matters.. */
+       const u32 ureq = unksel ? 0x00100000 : 0x00200000;
+       const u32 urep = unksel ? 0x01000000 : 0x02000000;
+       u32 ctrl, timeout;
+
+       /* wait up to 1ms for any previous transaction to be done... */
+       timeout = 1000;
+       do {
+               ctrl = nv_rd32(aux, 0x00d954 + (ch * 0x50));
+               udelay(1);
+               if (!timeout--) {
+                       AUX_ERR("begin idle timeout 0x%08x\n", ctrl);
+                       return -EBUSY;
+               }
+       } while (ctrl & 0x03010000);
+
+       /* set some magic, and wait up to 1ms for it to appear */
+       nv_mask(aux, 0x00d954 + (ch * 0x50), 0x00300000, ureq);
+       timeout = 1000;
+       do {
+               ctrl = nv_rd32(aux, 0x00d954 + (ch * 0x50));
+               udelay(1);
+               if (!timeout--) {
+                       AUX_ERR("magic wait 0x%08x\n", ctrl);
+                       auxch_fini(aux, ch);
+                       return -EBUSY;
+               }
+       } while ((ctrl & 0x03000000) != urep);
+
+       return 0;
+}
+
+int
+gm204_aux(struct nvkm_i2c_port *base, bool retry,
+        u8 type, u32 addr, u8 *data, u8 size)
+{
+       struct nvkm_i2c *aux = nvkm_i2c(base);
+       struct nv50_i2c_port *port = (void *)base;
+       u32 ctrl, stat, timeout, retries;
+       u32 xbuf[4] = {};
+       int ch = port->addr;
+       int ret, i;
+
+       AUX_DBG("%d: 0x%08x %d\n", type, addr, size);
+
+       ret = auxch_init(aux, ch);
+       if (ret)
+               goto out;
+
+       stat = nv_rd32(aux, 0x00d958 + (ch * 0x50));
+       if (!(stat & 0x10000000)) {
+               AUX_DBG("sink not detected\n");
+               ret = -ENXIO;
+               goto out;
+       }
+
+       if (!(type & 1)) {
+               memcpy(xbuf, data, size);
+               for (i = 0; i < 16; i += 4) {
+                       AUX_DBG("wr 0x%08x\n", xbuf[i / 4]);
+                       nv_wr32(aux, 0x00d930 + (ch * 0x50) + i, xbuf[i / 4]);
+               }
+       }
+
+       ctrl  = nv_rd32(aux, 0x00d954 + (ch * 0x50));
+       ctrl &= ~0x0001f0ff;
+       ctrl |= type << 12;
+       ctrl |= size - 1;
+       nv_wr32(aux, 0x00d950 + (ch * 0x50), addr);
+
+       /* (maybe) retry transaction a number of times on failure... */
+       for (retries = 0; !ret && retries < 32; retries++) {
+               /* reset, and delay a while if this is a retry */
+               nv_wr32(aux, 0x00d954 + (ch * 0x50), 0x80000000 | ctrl);
+               nv_wr32(aux, 0x00d954 + (ch * 0x50), 0x00000000 | ctrl);
+               if (retries)
+                       udelay(400);
+
+               /* transaction request, wait up to 1ms for it to complete */
+               nv_wr32(aux, 0x00d954 + (ch * 0x50), 0x00010000 | ctrl);
+
+               timeout = 1000;
+               do {
+                       ctrl = nv_rd32(aux, 0x00d954 + (ch * 0x50));
+                       udelay(1);
+                       if (!timeout--) {
+                               AUX_ERR("tx req timeout 0x%08x\n", ctrl);
+                               ret = -EIO;
+                               goto out;
+                       }
+               } while (ctrl & 0x00010000);
+               ret = 1;
+
+               /* read status, and check if transaction completed ok */
+               stat = nv_mask(aux, 0x00d958 + (ch * 0x50), 0, 0);
+               if ((stat & 0x000f0000) == 0x00080000 ||
+                   (stat & 0x000f0000) == 0x00020000)
+                       ret = retry ? 0 : 1;
+               if ((stat & 0x00000100))
+                       ret = -ETIMEDOUT;
+               if ((stat & 0x00000e00))
+                       ret = -EIO;
+
+               AUX_DBG("%02d 0x%08x 0x%08x\n", retries, ctrl, stat);
+       }
+
+       if (type & 1) {
+               for (i = 0; i < 16; i += 4) {
+                       xbuf[i / 4] = nv_rd32(aux, 0x00d940 + (ch * 0x50) + i);
+                       AUX_DBG("rd 0x%08x\n", xbuf[i / 4]);
+               }
+               memcpy(data, xbuf, size);
+       }
+
+out:
+       auxch_fini(aux, ch);
+       return ret < 0 ? ret : (stat & 0x000f0000) >> 16;
+}
+
+static const struct nvkm_i2c_func
+gm204_aux_func = {
+       .aux       = gm204_aux,
+};
+
+int
+gm204_aux_port_ctor(struct nvkm_object *parent,
+                   struct nvkm_object *engine,
+                   struct nvkm_oclass *oclass, void *data, u32 index,
+                   struct nvkm_object **pobject)
+{
+       struct dcb_i2c_entry *info = data;
+       struct nv50_i2c_port *port;
+       int ret;
+
+       ret = nvkm_i2c_port_create(parent, engine, oclass, index,
+                                  &nvkm_i2c_aux_algo, &gm204_aux_func, &port);
+       *pobject = nv_object(port);
+       if (ret)
+               return ret;
+
+       port->base.aux = info->auxch;
+       port->addr = info->auxch;
+       return 0;
+}
+
+struct nvkm_oclass
+gm204_i2c_sclass[] = {
+       { .handle = NV_I2C_TYPE_DCBI2C(DCB_I2C_NVIO_BIT),
+         .ofuncs = &(struct nvkm_ofuncs) {
+                 .ctor = gf110_i2c_port_ctor,
+                 .dtor = _nvkm_i2c_port_dtor,
+                 .init = nv50_i2c_port_init,
+                 .fini = _nvkm_i2c_port_fini,
+         },
+       },
+       { .handle = NV_I2C_TYPE_DCBI2C(DCB_I2C_NVIO_AUX),
+         .ofuncs = &(struct nvkm_ofuncs) {
+                 .ctor = gm204_aux_port_ctor,
+                 .dtor = _nvkm_i2c_port_dtor,
+                 .init = _nvkm_i2c_port_init,
+                 .fini = _nvkm_i2c_port_fini,
+         },
+       },
+       {}
+};
+
+struct nvkm_oclass *
+gm204_i2c_oclass = &(struct nvkm_i2c_impl) {
+       .base.handle = NV_SUBDEV(I2C, 0x24),
+       .base.ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = _nvkm_i2c_ctor,
+               .dtor = _nvkm_i2c_dtor,
+               .init = _nvkm_i2c_init,
+               .fini = _nvkm_i2c_fini,
+       },
+       .sclass = gm204_i2c_sclass,
+       .pad_x = &nv04_i2c_pad_oclass,
+       .pad_s = &gm204_i2c_pad_oclass,
+       .aux = 8,
+       .aux_stat = gk104_aux_stat,
+       .aux_mask = gk104_aux_mask,
+}.base;
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/i2c/nv04.c b/drivers/gpu/drm/nouveau/nvkm/subdev/i2c/nv04.c
new file mode 100644 (file)
index 0000000..4cdf1c4
--- /dev/null
@@ -0,0 +1,128 @@
+/*
+ * Copyright 2012 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 "priv.h"
+
+#include <subdev/vga.h>
+
+struct nv04_i2c_priv {
+       struct nvkm_i2c base;
+};
+
+struct nv04_i2c_port {
+       struct nvkm_i2c_port base;
+       u8 drive;
+       u8 sense;
+};
+
+static void
+nv04_i2c_drive_scl(struct nvkm_i2c_port *base, int state)
+{
+       struct nv04_i2c_priv *priv = (void *)nvkm_i2c(base);
+       struct nv04_i2c_port *port = (void *)base;
+       u8 val = nv_rdvgac(priv, 0, port->drive);
+       if (state) val |= 0x20;
+       else       val &= 0xdf;
+       nv_wrvgac(priv, 0, port->drive, val | 0x01);
+}
+
+static void
+nv04_i2c_drive_sda(struct nvkm_i2c_port *base, int state)
+{
+       struct nv04_i2c_priv *priv = (void *)nvkm_i2c(base);
+       struct nv04_i2c_port *port = (void *)base;
+       u8 val = nv_rdvgac(priv, 0, port->drive);
+       if (state) val |= 0x10;
+       else       val &= 0xef;
+       nv_wrvgac(priv, 0, port->drive, val | 0x01);
+}
+
+static int
+nv04_i2c_sense_scl(struct nvkm_i2c_port *base)
+{
+       struct nv04_i2c_priv *priv = (void *)nvkm_i2c(base);
+       struct nv04_i2c_port *port = (void *)base;
+       return !!(nv_rdvgac(priv, 0, port->sense) & 0x04);
+}
+
+static int
+nv04_i2c_sense_sda(struct nvkm_i2c_port *base)
+{
+       struct nv04_i2c_priv *priv = (void *)nvkm_i2c(base);
+       struct nv04_i2c_port *port = (void *)base;
+       return !!(nv_rdvgac(priv, 0, port->sense) & 0x08);
+}
+
+static const struct nvkm_i2c_func
+nv04_i2c_func = {
+       .drive_scl = nv04_i2c_drive_scl,
+       .drive_sda = nv04_i2c_drive_sda,
+       .sense_scl = nv04_i2c_sense_scl,
+       .sense_sda = nv04_i2c_sense_sda,
+};
+
+static int
+nv04_i2c_port_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+                  struct nvkm_oclass *oclass, void *data, u32 index,
+                  struct nvkm_object **pobject)
+{
+       struct dcb_i2c_entry *info = data;
+       struct nv04_i2c_port *port;
+       int ret;
+
+       ret = nvkm_i2c_port_create(parent, engine, oclass, index,
+                                  &nvkm_i2c_bit_algo, &nv04_i2c_func, &port);
+       *pobject = nv_object(port);
+       if (ret)
+               return ret;
+
+       port->drive = info->drive;
+       port->sense = info->sense;
+       return 0;
+}
+
+static struct nvkm_oclass
+nv04_i2c_sclass[] = {
+       { .handle = NV_I2C_TYPE_DCBI2C(DCB_I2C_NV04_BIT),
+         .ofuncs = &(struct nvkm_ofuncs) {
+                 .ctor = nv04_i2c_port_ctor,
+                 .dtor = _nvkm_i2c_port_dtor,
+                 .init = _nvkm_i2c_port_init,
+                 .fini = _nvkm_i2c_port_fini,
+         },
+       },
+       {}
+};
+
+struct nvkm_oclass *
+nv04_i2c_oclass = &(struct nvkm_i2c_impl) {
+       .base.handle = NV_SUBDEV(I2C, 0x04),
+       .base.ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = _nvkm_i2c_ctor,
+               .dtor = _nvkm_i2c_dtor,
+               .init = _nvkm_i2c_init,
+               .fini = _nvkm_i2c_fini,
+       },
+       .sclass = nv04_i2c_sclass,
+       .pad_x = &nv04_i2c_pad_oclass,
+}.base;
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/i2c/nv4e.c b/drivers/gpu/drm/nouveau/nvkm/subdev/i2c/nv4e.c
new file mode 100644 (file)
index 0000000..046fe5e
--- /dev/null
@@ -0,0 +1,120 @@
+/*
+ * Copyright 2012 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 "priv.h"
+
+#include <subdev/vga.h>
+
+struct nv4e_i2c_priv {
+       struct nvkm_i2c base;
+};
+
+struct nv4e_i2c_port {
+       struct nvkm_i2c_port base;
+       u32 addr;
+};
+
+static void
+nv4e_i2c_drive_scl(struct nvkm_i2c_port *base, int state)
+{
+       struct nv4e_i2c_priv *priv = (void *)nvkm_i2c(base);
+       struct nv4e_i2c_port *port = (void *)base;
+       nv_mask(priv, port->addr, 0x2f, state ? 0x21 : 0x01);
+}
+
+static void
+nv4e_i2c_drive_sda(struct nvkm_i2c_port *base, int state)
+{
+       struct nv4e_i2c_priv *priv = (void *)nvkm_i2c(base);
+       struct nv4e_i2c_port *port = (void *)base;
+       nv_mask(priv, port->addr, 0x1f, state ? 0x11 : 0x01);
+}
+
+static int
+nv4e_i2c_sense_scl(struct nvkm_i2c_port *base)
+{
+       struct nv4e_i2c_priv *priv = (void *)nvkm_i2c(base);
+       struct nv4e_i2c_port *port = (void *)base;
+       return !!(nv_rd32(priv, port->addr) & 0x00040000);
+}
+
+static int
+nv4e_i2c_sense_sda(struct nvkm_i2c_port *base)
+{
+       struct nv4e_i2c_priv *priv = (void *)nvkm_i2c(base);
+       struct nv4e_i2c_port *port = (void *)base;
+       return !!(nv_rd32(priv, port->addr) & 0x00080000);
+}
+
+static const struct nvkm_i2c_func
+nv4e_i2c_func = {
+       .drive_scl = nv4e_i2c_drive_scl,
+       .drive_sda = nv4e_i2c_drive_sda,
+       .sense_scl = nv4e_i2c_sense_scl,
+       .sense_sda = nv4e_i2c_sense_sda,
+};
+
+static int
+nv4e_i2c_port_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+                  struct nvkm_oclass *oclass, void *data, u32 index,
+                  struct nvkm_object **pobject)
+{
+       struct dcb_i2c_entry *info = data;
+       struct nv4e_i2c_port *port;
+       int ret;
+
+       ret = nvkm_i2c_port_create(parent, engine, oclass, index,
+                                  &nvkm_i2c_bit_algo, &nv4e_i2c_func, &port);
+       *pobject = nv_object(port);
+       if (ret)
+               return ret;
+
+       port->addr = 0x600800 + info->drive;
+       return 0;
+}
+
+static struct nvkm_oclass
+nv4e_i2c_sclass[] = {
+       { .handle = NV_I2C_TYPE_DCBI2C(DCB_I2C_NV4E_BIT),
+         .ofuncs = &(struct nvkm_ofuncs) {
+                 .ctor = nv4e_i2c_port_ctor,
+                 .dtor = _nvkm_i2c_port_dtor,
+                 .init = _nvkm_i2c_port_init,
+                 .fini = _nvkm_i2c_port_fini,
+         },
+       },
+       {}
+};
+
+struct nvkm_oclass *
+nv4e_i2c_oclass = &(struct nvkm_i2c_impl) {
+       .base.handle = NV_SUBDEV(I2C, 0x4e),
+       .base.ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = _nvkm_i2c_ctor,
+               .dtor = _nvkm_i2c_dtor,
+               .init = _nvkm_i2c_init,
+               .fini = _nvkm_i2c_fini,
+       },
+       .sclass = nv4e_i2c_sclass,
+       .pad_x = &nv04_i2c_pad_oclass,
+}.base;
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/i2c/nv50.c b/drivers/gpu/drm/nouveau/nvkm/subdev/i2c/nv50.c
new file mode 100644 (file)
index 0000000..fba5b26
--- /dev/null
@@ -0,0 +1,133 @@
+/*
+ * Copyright 2012 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 "nv50.h"
+
+void
+nv50_i2c_drive_scl(struct nvkm_i2c_port *base, int state)
+{
+       struct nv50_i2c_priv *priv = (void *)nvkm_i2c(base);
+       struct nv50_i2c_port *port = (void *)base;
+       if (state) port->state |= 0x01;
+       else       port->state &= 0xfe;
+       nv_wr32(priv, port->addr, port->state);
+}
+
+void
+nv50_i2c_drive_sda(struct nvkm_i2c_port *base, int state)
+{
+       struct nv50_i2c_priv *priv = (void *)nvkm_i2c(base);
+       struct nv50_i2c_port *port = (void *)base;
+       if (state) port->state |= 0x02;
+       else       port->state &= 0xfd;
+       nv_wr32(priv, port->addr, port->state);
+}
+
+int
+nv50_i2c_sense_scl(struct nvkm_i2c_port *base)
+{
+       struct nv50_i2c_priv *priv = (void *)nvkm_i2c(base);
+       struct nv50_i2c_port *port = (void *)base;
+       return !!(nv_rd32(priv, port->addr) & 0x00000001);
+}
+
+int
+nv50_i2c_sense_sda(struct nvkm_i2c_port *base)
+{
+       struct nv50_i2c_priv *priv = (void *)nvkm_i2c(base);
+       struct nv50_i2c_port *port = (void *)base;
+       return !!(nv_rd32(priv, port->addr) & 0x00000002);
+}
+
+static const struct nvkm_i2c_func
+nv50_i2c_func = {
+       .drive_scl = nv50_i2c_drive_scl,
+       .drive_sda = nv50_i2c_drive_sda,
+       .sense_scl = nv50_i2c_sense_scl,
+       .sense_sda = nv50_i2c_sense_sda,
+};
+
+const u32 nv50_i2c_addr[] = {
+       0x00e138, 0x00e150, 0x00e168, 0x00e180,
+       0x00e254, 0x00e274, 0x00e764, 0x00e780,
+       0x00e79c, 0x00e7b8
+};
+const int nv50_i2c_addr_nr = ARRAY_SIZE(nv50_i2c_addr);
+
+static int
+nv50_i2c_port_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+                  struct nvkm_oclass *oclass, void *data, u32 index,
+                  struct nvkm_object **pobject)
+{
+       struct dcb_i2c_entry *info = data;
+       struct nv50_i2c_port *port;
+       int ret;
+
+       ret = nvkm_i2c_port_create(parent, engine, oclass, index,
+                                  &nvkm_i2c_bit_algo, &nv50_i2c_func, &port);
+       *pobject = nv_object(port);
+       if (ret)
+               return ret;
+
+       if (info->drive >= nv50_i2c_addr_nr)
+               return -EINVAL;
+
+       port->state = 0x00000007;
+       port->addr = nv50_i2c_addr[info->drive];
+       return 0;
+}
+
+int
+nv50_i2c_port_init(struct nvkm_object *object)
+{
+       struct nv50_i2c_priv *priv = (void *)nvkm_i2c(object);
+       struct nv50_i2c_port *port = (void *)object;
+       nv_wr32(priv, port->addr, port->state);
+       return nvkm_i2c_port_init(&port->base);
+}
+
+static struct nvkm_oclass
+nv50_i2c_sclass[] = {
+       { .handle = NV_I2C_TYPE_DCBI2C(DCB_I2C_NVIO_BIT),
+         .ofuncs = &(struct nvkm_ofuncs) {
+                 .ctor = nv50_i2c_port_ctor,
+                 .dtor = _nvkm_i2c_port_dtor,
+                 .init = nv50_i2c_port_init,
+                 .fini = _nvkm_i2c_port_fini,
+         },
+       },
+       {}
+};
+
+struct nvkm_oclass *
+nv50_i2c_oclass = &(struct nvkm_i2c_impl) {
+       .base.handle = NV_SUBDEV(I2C, 0x50),
+       .base.ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = _nvkm_i2c_ctor,
+               .dtor = _nvkm_i2c_dtor,
+               .init = _nvkm_i2c_init,
+               .fini = _nvkm_i2c_fini,
+       },
+       .sclass = nv50_i2c_sclass,
+       .pad_x = &nv04_i2c_pad_oclass,
+}.base;
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/i2c/nv50.h b/drivers/gpu/drm/nouveau/nvkm/subdev/i2c/nv50.h
new file mode 100644 (file)
index 0000000..b3139e7
--- /dev/null
@@ -0,0 +1,32 @@
+#ifndef __NV50_I2C_H__
+#define __NV50_I2C_H__
+#include "priv.h"
+
+struct nv50_i2c_priv {
+       struct nvkm_i2c base;
+};
+
+struct nv50_i2c_port {
+       struct nvkm_i2c_port base;
+       u32 addr;
+       u32 state;
+};
+
+extern const u32 nv50_i2c_addr[];
+extern const int nv50_i2c_addr_nr;
+int  nv50_i2c_port_init(struct nvkm_object *);
+int  nv50_i2c_sense_scl(struct nvkm_i2c_port *);
+int  nv50_i2c_sense_sda(struct nvkm_i2c_port *);
+void nv50_i2c_drive_scl(struct nvkm_i2c_port *, int state);
+void nv50_i2c_drive_sda(struct nvkm_i2c_port *, int state);
+
+int  g94_aux_port_ctor(struct nvkm_object *, struct nvkm_object *,
+                       struct nvkm_oclass *, void *, u32,
+                       struct nvkm_object **);
+void g94_i2c_acquire(struct nvkm_i2c_port *);
+void g94_i2c_release(struct nvkm_i2c_port *);
+
+int  gf110_i2c_port_ctor(struct nvkm_object *, struct nvkm_object *,
+                       struct nvkm_oclass *, void *, u32,
+                       struct nvkm_object **);
+#endif
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/i2c/pad.c b/drivers/gpu/drm/nouveau/nvkm/subdev/i2c/pad.c
new file mode 100644 (file)
index 0000000..a242eeb
--- /dev/null
@@ -0,0 +1,83 @@
+/*
+ * Copyright 2014 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 "pad.h"
+
+int
+_nvkm_i2c_pad_fini(struct nvkm_object *object, bool suspend)
+{
+       struct nvkm_i2c_pad *pad = (void *)object;
+       DBG("-> NULL\n");
+       pad->port = NULL;
+       return nvkm_object_fini(&pad->base, suspend);
+}
+
+int
+_nvkm_i2c_pad_init(struct nvkm_object *object)
+{
+       struct nvkm_i2c_pad *pad = (void *)object;
+       DBG("-> PORT:%02x\n", pad->next->index);
+       pad->port = pad->next;
+       return nvkm_object_init(&pad->base);
+}
+
+int
+nvkm_i2c_pad_create_(struct nvkm_object *parent,
+                    struct nvkm_object *engine,
+                    struct nvkm_oclass *oclass, int index,
+                    int size, void **pobject)
+{
+       struct nvkm_i2c *i2c = nvkm_i2c(parent);
+       struct nvkm_i2c_port *port;
+       struct nvkm_i2c_pad *pad;
+       int ret;
+
+       list_for_each_entry(port, &i2c->ports, head) {
+               pad = nvkm_i2c_pad(port);
+               if (pad->index == index) {
+                       atomic_inc(&nv_object(pad)->refcount);
+                       *pobject = pad;
+                       return 1;
+               }
+       }
+
+       ret = nvkm_object_create_(parent, engine, oclass, 0, size, pobject);
+       pad = *pobject;
+       if (ret)
+               return ret;
+
+       pad->index = index;
+       return 0;
+}
+
+int
+_nvkm_i2c_pad_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+                  struct nvkm_oclass *oclass, void *data, u32 index,
+                  struct nvkm_object **pobject)
+{
+       struct nvkm_i2c_pad *pad;
+       int ret;
+       ret = nvkm_i2c_pad_create(parent, engine, oclass, index, &pad);
+       *pobject = nv_object(pad);
+       return ret;
+}
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/i2c/pad.h b/drivers/gpu/drm/nouveau/nvkm/subdev/i2c/pad.h
new file mode 100644 (file)
index 0000000..f3422cc
--- /dev/null
@@ -0,0 +1,56 @@
+#ifndef __NVKM_I2C_PAD_H__
+#define __NVKM_I2C_PAD_H__
+#include "priv.h"
+
+struct nvkm_i2c_pad {
+       struct nvkm_object base;
+       int index;
+       struct nvkm_i2c_port *port;
+       struct nvkm_i2c_port *next;
+};
+
+static inline struct nvkm_i2c_pad *
+nvkm_i2c_pad(struct nvkm_i2c_port *port)
+{
+       struct nvkm_object *pad = nv_object(port);
+       while (!nv_iclass(pad->parent, NV_SUBDEV_CLASS))
+               pad = pad->parent;
+       return (void *)pad;
+}
+
+#define nvkm_i2c_pad_create(p,e,o,i,d)                                         \
+       nvkm_i2c_pad_create_((p), (e), (o), (i), sizeof(**d), (void **)d)
+#define nvkm_i2c_pad_destroy(p) ({                                             \
+       struct nvkm_i2c_pad *_p = (p);                                         \
+       _nvkm_i2c_pad_dtor(nv_object(_p));                                     \
+})
+#define nvkm_i2c_pad_init(p) ({                                                \
+       struct nvkm_i2c_pad *_p = (p);                                         \
+       _nvkm_i2c_pad_init(nv_object(_p));                                     \
+})
+#define nvkm_i2c_pad_fini(p,s) ({                                              \
+       struct nvkm_i2c_pad *_p = (p);                                         \
+       _nvkm_i2c_pad_fini(nv_object(_p), (s));                                \
+})
+
+int nvkm_i2c_pad_create_(struct nvkm_object *, struct nvkm_object *,
+                        struct nvkm_oclass *, int index, int, void **);
+
+int _nvkm_i2c_pad_ctor(struct nvkm_object *, struct nvkm_object *,
+                      struct nvkm_oclass *, void *, u32,
+                      struct nvkm_object **);
+#define _nvkm_i2c_pad_dtor nvkm_object_destroy
+int _nvkm_i2c_pad_init(struct nvkm_object *);
+int _nvkm_i2c_pad_fini(struct nvkm_object *, bool);
+
+#ifndef MSG
+#define MSG(l,f,a...) do {                                                     \
+       struct nvkm_i2c_pad *_pad = (void *)pad;                               \
+       nv_##l(_pad, "PAD:%c:%02x: "f,                                         \
+              _pad->index >= 0x100 ? 'X' : 'S',                               \
+              _pad->index >= 0x100 ? _pad->index - 0x100 : _pad->index, ##a); \
+} while(0)
+#define DBG(f,a...) MSG(debug, f, ##a)
+#define ERR(f,a...) MSG(error, f, ##a)
+#endif
+#endif
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/i2c/padg94.c b/drivers/gpu/drm/nouveau/nvkm/subdev/i2c/padg94.c
new file mode 100644 (file)
index 0000000..e9832f7
--- /dev/null
@@ -0,0 +1,85 @@
+/*
+ * Copyright 2014 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 "pad.h"
+
+struct g94_i2c_pad {
+       struct nvkm_i2c_pad base;
+       int addr;
+};
+
+static int
+g94_i2c_pad_fini(struct nvkm_object *object, bool suspend)
+{
+       struct nvkm_i2c *i2c = (void *)nvkm_i2c(object);
+       struct g94_i2c_pad *pad = (void *)object;
+       nv_mask(i2c, 0x00e50c + pad->addr, 0x00000001, 0x00000001);
+       return nvkm_i2c_pad_fini(&pad->base, suspend);
+}
+
+static int
+g94_i2c_pad_init(struct nvkm_object *object)
+{
+       struct nvkm_i2c *i2c = (void *)nvkm_i2c(object);
+       struct g94_i2c_pad *pad = (void *)object;
+
+       switch (nv_oclass(pad->base.next)->handle) {
+       case NV_I2C_TYPE_DCBI2C(DCB_I2C_NVIO_AUX):
+               nv_mask(i2c, 0x00e500 + pad->addr, 0x0000c003, 0x00000002);
+               break;
+       case NV_I2C_TYPE_DCBI2C(DCB_I2C_NVIO_BIT):
+       default:
+               nv_mask(i2c, 0x00e500 + pad->addr, 0x0000c003, 0x0000c001);
+               break;
+       }
+
+       nv_mask(i2c, 0x00e50c + pad->addr, 0x00000001, 0x00000000);
+       return nvkm_i2c_pad_init(&pad->base);
+}
+
+static int
+g94_i2c_pad_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+                struct nvkm_oclass *oclass, void *data, u32 index,
+                struct nvkm_object **pobject)
+{
+       struct g94_i2c_pad *pad;
+       int ret;
+
+       ret = nvkm_i2c_pad_create(parent, engine, oclass, index, &pad);
+       *pobject = nv_object(pad);
+       if (ret)
+               return ret;
+
+       pad->addr = index * 0x50;;
+       return 0;
+}
+
+struct nvkm_oclass
+g94_i2c_pad_oclass = {
+       .ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = g94_i2c_pad_ctor,
+               .dtor = _nvkm_i2c_pad_dtor,
+               .init = g94_i2c_pad_init,
+               .fini = g94_i2c_pad_fini,
+       },
+};
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/i2c/padgm204.c b/drivers/gpu/drm/nouveau/nvkm/subdev/i2c/padgm204.c
new file mode 100644 (file)
index 0000000..be59040
--- /dev/null
@@ -0,0 +1,85 @@
+/*
+ * Copyright 2014 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 "pad.h"
+
+struct gm204_i2c_pad {
+       struct nvkm_i2c_pad base;
+       int addr;
+};
+
+static int
+gm204_i2c_pad_fini(struct nvkm_object *object, bool suspend)
+{
+       struct nvkm_i2c *i2c = (void *)nvkm_i2c(object);
+       struct gm204_i2c_pad *pad = (void *)object;
+       nv_mask(i2c, 0x00d97c + pad->addr, 0x00000001, 0x00000001);
+       return nvkm_i2c_pad_fini(&pad->base, suspend);
+}
+
+static int
+gm204_i2c_pad_init(struct nvkm_object *object)
+{
+       struct nvkm_i2c *i2c = (void *)nvkm_i2c(object);
+       struct gm204_i2c_pad *pad = (void *)object;
+
+       switch (nv_oclass(pad->base.next)->handle) {
+       case NV_I2C_TYPE_DCBI2C(DCB_I2C_NVIO_AUX):
+               nv_mask(i2c, 0x00d970 + pad->addr, 0x0000c003, 0x00000002);
+               break;
+       case NV_I2C_TYPE_DCBI2C(DCB_I2C_NVIO_BIT):
+       default:
+               nv_mask(i2c, 0x00d970 + pad->addr, 0x0000c003, 0x0000c001);
+               break;
+       }
+
+       nv_mask(i2c, 0x00d97c + pad->addr, 0x00000001, 0x00000000);
+       return nvkm_i2c_pad_init(&pad->base);
+}
+
+static int
+gm204_i2c_pad_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+                  struct nvkm_oclass *oclass, void *data, u32 index,
+                  struct nvkm_object **pobject)
+{
+       struct gm204_i2c_pad *pad;
+       int ret;
+
+       ret = nvkm_i2c_pad_create(parent, engine, oclass, index, &pad);
+       *pobject = nv_object(pad);
+       if (ret)
+               return ret;
+
+       pad->addr = index * 0x50;;
+       return 0;
+}
+
+struct nvkm_oclass
+gm204_i2c_pad_oclass = {
+       .ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = gm204_i2c_pad_ctor,
+               .dtor = _nvkm_i2c_pad_dtor,
+               .init = gm204_i2c_pad_init,
+               .fini = gm204_i2c_pad_fini,
+       },
+};
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/i2c/padnv04.c b/drivers/gpu/drm/nouveau/nvkm/subdev/i2c/padnv04.c
new file mode 100644 (file)
index 0000000..22c7daa
--- /dev/null
@@ -0,0 +1,34 @@
+/*
+ * Copyright 2014 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 "pad.h"
+
+struct nvkm_oclass
+nv04_i2c_pad_oclass = {
+       .ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = _nvkm_i2c_pad_ctor,
+               .dtor = _nvkm_i2c_pad_dtor,
+               .init = _nvkm_i2c_pad_init,
+               .fini = _nvkm_i2c_pad_fini,
+       },
+};
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/i2c/port.h b/drivers/gpu/drm/nouveau/nvkm/subdev/i2c/port.h
new file mode 100644 (file)
index 0000000..586f53d
--- /dev/null
@@ -0,0 +1,13 @@
+#ifndef __NVKM_I2C_PORT_H__
+#define __NVKM_I2C_PORT_H__
+#include "priv.h"
+
+#ifndef MSG
+#define MSG(l,f,a...) do {                                                     \
+       struct nvkm_i2c_port *_port = (void *)port;                         \
+       nv_##l(_port, "PORT:%02x: "f, _port->index, ##a);                      \
+} while(0)
+#define DBG(f,a...) MSG(debug, f, ##a)
+#define ERR(f,a...) MSG(error, f, ##a)
+#endif
+#endif
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/i2c/priv.h b/drivers/gpu/drm/nouveau/nvkm/subdev/i2c/priv.h
new file mode 100644 (file)
index 0000000..6586e15
--- /dev/null
@@ -0,0 +1,87 @@
+#ifndef __NVKM_I2C_PRIV_H__
+#define __NVKM_I2C_PRIV_H__
+#include <subdev/i2c.h>
+
+extern struct nvkm_oclass nv04_i2c_pad_oclass;
+extern struct nvkm_oclass g94_i2c_pad_oclass;
+extern struct nvkm_oclass gm204_i2c_pad_oclass;
+
+#define nvkm_i2c_port_create(p,e,o,i,a,f,d)                                 \
+       nvkm_i2c_port_create_((p), (e), (o), (i), (a), (f),                 \
+                                sizeof(**d), (void **)d)
+#define nvkm_i2c_port_destroy(p) ({                                         \
+       struct nvkm_i2c_port *port = (p);                                   \
+       _nvkm_i2c_port_dtor(nv_object(i2c));                                \
+})
+#define nvkm_i2c_port_init(p)                                               \
+       nvkm_object_init(&(p)->base)
+#define nvkm_i2c_port_fini(p,s)                                             \
+       nvkm_object_fini(&(p)->base, (s))
+
+int nvkm_i2c_port_create_(struct nvkm_object *, struct nvkm_object *,
+                            struct nvkm_oclass *, u8,
+                            const struct i2c_algorithm *,
+                            const struct nvkm_i2c_func *,
+                            int, void **);
+void _nvkm_i2c_port_dtor(struct nvkm_object *);
+#define _nvkm_i2c_port_init nvkm_object_init
+int  _nvkm_i2c_port_fini(struct nvkm_object *, bool);
+
+#define nvkm_i2c_create(p,e,o,d)                                            \
+       nvkm_i2c_create_((p), (e), (o), sizeof(**d), (void **)d)
+#define nvkm_i2c_destroy(p) ({                                              \
+       struct nvkm_i2c *i2c = (p);                                         \
+       _nvkm_i2c_dtor(nv_object(i2c));                                     \
+})
+#define nvkm_i2c_init(p) ({                                                 \
+       struct nvkm_i2c *i2c = (p);                                         \
+       _nvkm_i2c_init(nv_object(i2c));                                     \
+})
+#define nvkm_i2c_fini(p,s) ({                                               \
+       struct nvkm_i2c *i2c = (p);                                         \
+       _nvkm_i2c_fini(nv_object(i2c), (s));                                \
+})
+
+int nvkm_i2c_create_(struct nvkm_object *, struct nvkm_object *,
+                       struct nvkm_oclass *, int, void **);
+int  _nvkm_i2c_ctor(struct nvkm_object *, struct nvkm_object *,
+                      struct nvkm_oclass *, void *, u32,
+                      struct nvkm_object **);
+void _nvkm_i2c_dtor(struct nvkm_object *);
+int  _nvkm_i2c_init(struct nvkm_object *);
+int  _nvkm_i2c_fini(struct nvkm_object *, bool);
+
+extern struct nvkm_oclass nvkm_anx9805_sclass[];
+extern struct nvkm_oclass gf110_i2c_sclass[];
+
+extern const struct i2c_algorithm nvkm_i2c_bit_algo;
+extern const struct i2c_algorithm nvkm_i2c_aux_algo;
+
+struct nvkm_i2c_impl {
+       struct nvkm_oclass base;
+
+       /* supported i2c port classes */
+       struct nvkm_oclass *sclass;
+       struct nvkm_oclass *pad_x;
+       struct nvkm_oclass *pad_s;
+
+       /* number of native dp aux channels present */
+       int aux;
+
+       /* read and ack pending interrupts, returning only data
+        * for ports that have not been masked off, while still
+        * performing the ack for anything that was pending.
+        */
+       void (*aux_stat)(struct nvkm_i2c *, u32 *, u32 *, u32 *, u32 *);
+
+       /* mask on/off interrupt types for a given set of auxch
+        */
+       void (*aux_mask)(struct nvkm_i2c *, u32, u32, u32);
+};
+
+void g94_aux_stat(struct nvkm_i2c *, u32 *, u32 *, u32 *, u32 *);
+void g94_aux_mask(struct nvkm_i2c *, u32, u32, u32);
+
+void gk104_aux_stat(struct nvkm_i2c *, u32 *, u32 *, u32 *, u32 *);
+void gk104_aux_mask(struct nvkm_i2c *, u32, u32, u32);
+#endif
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/ibus/Kbuild b/drivers/gpu/drm/nouveau/nvkm/subdev/ibus/Kbuild
new file mode 100644 (file)
index 0000000..a0b12d2
--- /dev/null
@@ -0,0 +1,3 @@
+nvkm-y += nvkm/subdev/ibus/gf100.o
+nvkm-y += nvkm/subdev/ibus/gk104.o
+nvkm-y += nvkm/subdev/ibus/gk20a.o
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/ibus/gf100.c b/drivers/gpu/drm/nouveau/nvkm/subdev/ibus/gf100.c
new file mode 100644 (file)
index 0000000..8e578f8
--- /dev/null
@@ -0,0 +1,122 @@
+/*
+ * Copyright 2012 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 <subdev/ibus.h>
+
+struct gf100_ibus_priv {
+       struct nvkm_ibus base;
+};
+
+static void
+gf100_ibus_intr_hub(struct gf100_ibus_priv *priv, int i)
+{
+       u32 addr = nv_rd32(priv, 0x122120 + (i * 0x0400));
+       u32 data = nv_rd32(priv, 0x122124 + (i * 0x0400));
+       u32 stat = nv_rd32(priv, 0x122128 + (i * 0x0400));
+       nv_error(priv, "HUB%d: 0x%06x 0x%08x (0x%08x)\n", i, addr, data, stat);
+       nv_mask(priv, 0x122128 + (i * 0x0400), 0x00000200, 0x00000000);
+}
+
+static void
+gf100_ibus_intr_rop(struct gf100_ibus_priv *priv, int i)
+{
+       u32 addr = nv_rd32(priv, 0x124120 + (i * 0x0400));
+       u32 data = nv_rd32(priv, 0x124124 + (i * 0x0400));
+       u32 stat = nv_rd32(priv, 0x124128 + (i * 0x0400));
+       nv_error(priv, "ROP%d: 0x%06x 0x%08x (0x%08x)\n", i, addr, data, stat);
+       nv_mask(priv, 0x124128 + (i * 0x0400), 0x00000200, 0x00000000);
+}
+
+static void
+gf100_ibus_intr_gpc(struct gf100_ibus_priv *priv, int i)
+{
+       u32 addr = nv_rd32(priv, 0x128120 + (i * 0x0400));
+       u32 data = nv_rd32(priv, 0x128124 + (i * 0x0400));
+       u32 stat = nv_rd32(priv, 0x128128 + (i * 0x0400));
+       nv_error(priv, "GPC%d: 0x%06x 0x%08x (0x%08x)\n", i, addr, data, stat);
+       nv_mask(priv, 0x128128 + (i * 0x0400), 0x00000200, 0x00000000);
+}
+
+static void
+gf100_ibus_intr(struct nvkm_subdev *subdev)
+{
+       struct gf100_ibus_priv *priv = (void *)subdev;
+       u32 intr0 = nv_rd32(priv, 0x121c58);
+       u32 intr1 = nv_rd32(priv, 0x121c5c);
+       u32 hubnr = nv_rd32(priv, 0x121c70);
+       u32 ropnr = nv_rd32(priv, 0x121c74);
+       u32 gpcnr = nv_rd32(priv, 0x121c78);
+       u32 i;
+
+       for (i = 0; (intr0 & 0x0000ff00) && i < hubnr; i++) {
+               u32 stat = 0x00000100 << i;
+               if (intr0 & stat) {
+                       gf100_ibus_intr_hub(priv, i);
+                       intr0 &= ~stat;
+               }
+       }
+
+       for (i = 0; (intr0 & 0xffff0000) && i < ropnr; i++) {
+               u32 stat = 0x00010000 << i;
+               if (intr0 & stat) {
+                       gf100_ibus_intr_rop(priv, i);
+                       intr0 &= ~stat;
+               }
+       }
+
+       for (i = 0; intr1 && i < gpcnr; i++) {
+               u32 stat = 0x00000001 << i;
+               if (intr1 & stat) {
+                       gf100_ibus_intr_gpc(priv, i);
+                       intr1 &= ~stat;
+               }
+       }
+}
+
+static int
+gf100_ibus_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+               struct nvkm_oclass *oclass, void *data, u32 size,
+               struct nvkm_object **pobject)
+{
+       struct gf100_ibus_priv *priv;
+       int ret;
+
+       ret = nvkm_ibus_create(parent, engine, oclass, &priv);
+       *pobject = nv_object(priv);
+       if (ret)
+               return ret;
+
+       nv_subdev(priv)->intr = gf100_ibus_intr;
+       return 0;
+}
+
+struct nvkm_oclass
+gf100_ibus_oclass = {
+       .handle = NV_SUBDEV(IBUS, 0xc0),
+       .ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = gf100_ibus_ctor,
+               .dtor = _nvkm_ibus_dtor,
+               .init = _nvkm_ibus_init,
+               .fini = _nvkm_ibus_fini,
+       },
+};
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/ibus/gk104.c b/drivers/gpu/drm/nouveau/nvkm/subdev/ibus/gk104.c
new file mode 100644 (file)
index 0000000..7b6e9a6
--- /dev/null
@@ -0,0 +1,139 @@
+/*
+ * Copyright 2012 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 <subdev/ibus.h>
+
+struct gk104_ibus_priv {
+       struct nvkm_ibus base;
+};
+
+static void
+gk104_ibus_intr_hub(struct gk104_ibus_priv *priv, int i)
+{
+       u32 addr = nv_rd32(priv, 0x122120 + (i * 0x0800));
+       u32 data = nv_rd32(priv, 0x122124 + (i * 0x0800));
+       u32 stat = nv_rd32(priv, 0x122128 + (i * 0x0800));
+       nv_error(priv, "HUB%d: 0x%06x 0x%08x (0x%08x)\n", i, addr, data, stat);
+       nv_mask(priv, 0x122128 + (i * 0x0800), 0x00000200, 0x00000000);
+}
+
+static void
+gk104_ibus_intr_rop(struct gk104_ibus_priv *priv, int i)
+{
+       u32 addr = nv_rd32(priv, 0x124120 + (i * 0x0800));
+       u32 data = nv_rd32(priv, 0x124124 + (i * 0x0800));
+       u32 stat = nv_rd32(priv, 0x124128 + (i * 0x0800));
+       nv_error(priv, "ROP%d: 0x%06x 0x%08x (0x%08x)\n", i, addr, data, stat);
+       nv_mask(priv, 0x124128 + (i * 0x0800), 0x00000200, 0x00000000);
+}
+
+static void
+gk104_ibus_intr_gpc(struct gk104_ibus_priv *priv, int i)
+{
+       u32 addr = nv_rd32(priv, 0x128120 + (i * 0x0800));
+       u32 data = nv_rd32(priv, 0x128124 + (i * 0x0800));
+       u32 stat = nv_rd32(priv, 0x128128 + (i * 0x0800));
+       nv_error(priv, "GPC%d: 0x%06x 0x%08x (0x%08x)\n", i, addr, data, stat);
+       nv_mask(priv, 0x128128 + (i * 0x0800), 0x00000200, 0x00000000);
+}
+
+static void
+gk104_ibus_intr(struct nvkm_subdev *subdev)
+{
+       struct gk104_ibus_priv *priv = (void *)subdev;
+       u32 intr0 = nv_rd32(priv, 0x120058);
+       u32 intr1 = nv_rd32(priv, 0x12005c);
+       u32 hubnr = nv_rd32(priv, 0x120070);
+       u32 ropnr = nv_rd32(priv, 0x120074);
+       u32 gpcnr = nv_rd32(priv, 0x120078);
+       u32 i;
+
+       for (i = 0; (intr0 & 0x0000ff00) && i < hubnr; i++) {
+               u32 stat = 0x00000100 << i;
+               if (intr0 & stat) {
+                       gk104_ibus_intr_hub(priv, i);
+                       intr0 &= ~stat;
+               }
+       }
+
+       for (i = 0; (intr0 & 0xffff0000) && i < ropnr; i++) {
+               u32 stat = 0x00010000 << i;
+               if (intr0 & stat) {
+                       gk104_ibus_intr_rop(priv, i);
+                       intr0 &= ~stat;
+               }
+       }
+
+       for (i = 0; intr1 && i < gpcnr; i++) {
+               u32 stat = 0x00000001 << i;
+               if (intr1 & stat) {
+                       gk104_ibus_intr_gpc(priv, i);
+                       intr1 &= ~stat;
+               }
+       }
+}
+
+static int
+gk104_ibus_init(struct nvkm_object *object)
+{
+       struct gk104_ibus_priv *priv = (void *)object;
+       int ret = nvkm_ibus_init(&priv->base);
+       if (ret == 0) {
+               nv_mask(priv, 0x122318, 0x0003ffff, 0x00001000);
+               nv_mask(priv, 0x12231c, 0x0003ffff, 0x00000200);
+               nv_mask(priv, 0x122310, 0x0003ffff, 0x00000800);
+               nv_mask(priv, 0x122348, 0x0003ffff, 0x00000100);
+               nv_mask(priv, 0x1223b0, 0x0003ffff, 0x00000fff);
+               nv_mask(priv, 0x122348, 0x0003ffff, 0x00000200);
+               nv_mask(priv, 0x122358, 0x0003ffff, 0x00002880);
+       }
+       return ret;
+}
+
+static int
+gk104_ibus_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+               struct nvkm_oclass *oclass, void *data, u32 size,
+               struct nvkm_object **pobject)
+{
+       struct gk104_ibus_priv *priv;
+       int ret;
+
+       ret = nvkm_ibus_create(parent, engine, oclass, &priv);
+       *pobject = nv_object(priv);
+       if (ret)
+               return ret;
+
+       nv_subdev(priv)->intr = gk104_ibus_intr;
+       return 0;
+}
+
+struct nvkm_oclass
+gk104_ibus_oclass = {
+       .handle = NV_SUBDEV(IBUS, 0xe0),
+       .ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = gk104_ibus_ctor,
+               .dtor = _nvkm_ibus_dtor,
+               .init = gk104_ibus_init,
+               .fini = _nvkm_ibus_fini,
+       },
+};
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/ibus/gk20a.c b/drivers/gpu/drm/nouveau/nvkm/subdev/ibus/gk20a.c
new file mode 100644 (file)
index 0000000..c0fdb89
--- /dev/null
@@ -0,0 +1,102 @@
+/*
+ * Copyright (c) 2014, NVIDIA CORPORATION. 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 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 <subdev/ibus.h>
+#include <subdev/timer.h>
+
+struct gk20a_ibus_priv {
+       struct nvkm_ibus base;
+};
+
+static void
+gk20a_ibus_init_priv_ring(struct gk20a_ibus_priv *priv)
+{
+       nv_mask(priv, 0x137250, 0x3f, 0);
+
+       nv_mask(priv, 0x000200, 0x20, 0);
+       usleep_range(20, 30);
+       nv_mask(priv, 0x000200, 0x20, 0x20);
+
+       nv_wr32(priv, 0x12004c, 0x4);
+       nv_wr32(priv, 0x122204, 0x2);
+       nv_rd32(priv, 0x122204);
+}
+
+static void
+gk20a_ibus_intr(struct nvkm_subdev *subdev)
+{
+       struct gk20a_ibus_priv *priv = (void *)subdev;
+       u32 status0 = nv_rd32(priv, 0x120058);
+
+       if (status0 & 0x7) {
+               nv_debug(priv, "resetting priv ring\n");
+               gk20a_ibus_init_priv_ring(priv);
+       }
+
+       /* Acknowledge interrupt */
+       nv_mask(priv, 0x12004c, 0x2, 0x2);
+
+       if (!nv_wait(subdev, 0x12004c, 0x3f, 0x00))
+               nv_warn(priv, "timeout waiting for ringmaster ack\n");
+}
+
+static int
+gk20a_ibus_init(struct nvkm_object *object)
+{
+       struct gk20a_ibus_priv *priv = (void *)object;
+       int ret;
+
+       ret = _nvkm_ibus_init(object);
+       if (ret)
+               return ret;
+
+       gk20a_ibus_init_priv_ring(priv);
+
+       return 0;
+}
+
+static int
+gk20a_ibus_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+               struct nvkm_oclass *oclass, void *data, u32 size,
+               struct nvkm_object **pobject)
+{
+       struct gk20a_ibus_priv *priv;
+       int ret;
+
+       ret = nvkm_ibus_create(parent, engine, oclass, &priv);
+       *pobject = nv_object(priv);
+       if (ret)
+               return ret;
+
+       nv_subdev(priv)->intr = gk20a_ibus_intr;
+       return 0;
+}
+
+struct nvkm_oclass
+gk20a_ibus_oclass = {
+       .handle = NV_SUBDEV(IBUS, 0xea),
+       .ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = gk20a_ibus_ctor,
+               .dtor = _nvkm_ibus_dtor,
+               .init = gk20a_ibus_init,
+               .fini = _nvkm_ibus_fini,
+       },
+};
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/instmem/Kbuild b/drivers/gpu/drm/nouveau/nvkm/subdev/instmem/Kbuild
new file mode 100644 (file)
index 0000000..e6f35ab
--- /dev/null
@@ -0,0 +1,4 @@
+nvkm-y += nvkm/subdev/instmem/base.o
+nvkm-y += nvkm/subdev/instmem/nv04.o
+nvkm-y += nvkm/subdev/instmem/nv40.o
+nvkm-y += nvkm/subdev/instmem/nv50.o
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/instmem/base.c b/drivers/gpu/drm/nouveau/nvkm/subdev/instmem/base.c
new file mode 100644 (file)
index 0000000..d16358c
--- /dev/null
@@ -0,0 +1,146 @@
+/*
+ * Copyright 2012 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 "priv.h"
+
+#include <core/engine.h>
+
+/******************************************************************************
+ * instmem object base implementation
+ *****************************************************************************/
+
+void
+_nvkm_instobj_dtor(struct nvkm_object *object)
+{
+       struct nvkm_instmem *imem = nvkm_instmem(object);
+       struct nvkm_instobj *iobj = (void *)object;
+
+       mutex_lock(&nv_subdev(imem)->mutex);
+       list_del(&iobj->head);
+       mutex_unlock(&nv_subdev(imem)->mutex);
+
+       return nvkm_object_destroy(&iobj->base);
+}
+
+int
+nvkm_instobj_create_(struct nvkm_object *parent, struct nvkm_object *engine,
+                    struct nvkm_oclass *oclass, int length, void **pobject)
+{
+       struct nvkm_instmem *imem = nvkm_instmem(parent);
+       struct nvkm_instobj *iobj;
+       int ret;
+
+       ret = nvkm_object_create_(parent, engine, oclass, NV_MEMOBJ_CLASS,
+                                 length, pobject);
+       iobj = *pobject;
+       if (ret)
+               return ret;
+
+       mutex_lock(&imem->base.mutex);
+       list_add(&iobj->head, &imem->list);
+       mutex_unlock(&imem->base.mutex);
+       return 0;
+}
+
+/******************************************************************************
+ * instmem subdev base implementation
+ *****************************************************************************/
+
+static int
+nvkm_instmem_alloc(struct nvkm_instmem *imem, struct nvkm_object *parent,
+                  u32 size, u32 align, struct nvkm_object **pobject)
+{
+       struct nvkm_instmem_impl *impl = (void *)imem->base.object.oclass;
+       struct nvkm_instobj_args args = { .size = size, .align = align };
+       return nvkm_object_ctor(parent, &parent->engine->subdev.object,
+                               impl->instobj, &args, sizeof(args), pobject);
+}
+
+int
+_nvkm_instmem_fini(struct nvkm_object *object, bool suspend)
+{
+       struct nvkm_instmem *imem = (void *)object;
+       struct nvkm_instobj *iobj;
+       int i, ret = 0;
+
+       if (suspend) {
+               mutex_lock(&imem->base.mutex);
+               list_for_each_entry(iobj, &imem->list, head) {
+                       iobj->suspend = vmalloc(iobj->size);
+                       if (!iobj->suspend) {
+                               ret = -ENOMEM;
+                               break;
+                       }
+
+                       for (i = 0; i < iobj->size; i += 4)
+                               iobj->suspend[i / 4] = nv_ro32(iobj, i);
+               }
+               mutex_unlock(&imem->base.mutex);
+               if (ret)
+                       return ret;
+       }
+
+       return nvkm_subdev_fini(&imem->base, suspend);
+}
+
+int
+_nvkm_instmem_init(struct nvkm_object *object)
+{
+       struct nvkm_instmem *imem = (void *)object;
+       struct nvkm_instobj *iobj;
+       int ret, i;
+
+       ret = nvkm_subdev_init(&imem->base);
+       if (ret)
+               return ret;
+
+       mutex_lock(&imem->base.mutex);
+       list_for_each_entry(iobj, &imem->list, head) {
+               if (iobj->suspend) {
+                       for (i = 0; i < iobj->size; i += 4)
+                               nv_wo32(iobj, i, iobj->suspend[i / 4]);
+                       vfree(iobj->suspend);
+                       iobj->suspend = NULL;
+               }
+       }
+       mutex_unlock(&imem->base.mutex);
+       return 0;
+}
+
+int
+nvkm_instmem_create_(struct nvkm_object *parent, struct nvkm_object *engine,
+                    struct nvkm_oclass *oclass, int length, void **pobject)
+{
+       struct nvkm_instmem *imem;
+       int ret;
+
+       ret = nvkm_subdev_create_(parent, engine, oclass, 0, "INSTMEM",
+                                 "instmem", length, pobject);
+       imem = *pobject;
+       if (ret)
+               return ret;
+
+       INIT_LIST_HEAD(&imem->list);
+       imem->alloc = nvkm_instmem_alloc;
+       return 0;
+}
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/instmem/nv04.c b/drivers/gpu/drm/nouveau/nvkm/subdev/instmem/nv04.c
new file mode 100644 (file)
index 0000000..80614f1
--- /dev/null
@@ -0,0 +1,185 @@
+/*
+ * Copyright 2012 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 "nv04.h"
+
+#include <core/ramht.h>
+
+/******************************************************************************
+ * instmem object implementation
+ *****************************************************************************/
+
+static u32
+nv04_instobj_rd32(struct nvkm_object *object, u64 addr)
+{
+       struct nv04_instmem_priv *priv = (void *)nvkm_instmem(object);
+       struct nv04_instobj_priv *node = (void *)object;
+       return nv_ro32(priv, node->mem->offset + addr);
+}
+
+static void
+nv04_instobj_wr32(struct nvkm_object *object, u64 addr, u32 data)
+{
+       struct nv04_instmem_priv *priv = (void *)nvkm_instmem(object);
+       struct nv04_instobj_priv *node = (void *)object;
+       nv_wo32(priv, node->mem->offset + addr, data);
+}
+
+static void
+nv04_instobj_dtor(struct nvkm_object *object)
+{
+       struct nv04_instmem_priv *priv = (void *)nvkm_instmem(object);
+       struct nv04_instobj_priv *node = (void *)object;
+       nvkm_mm_free(&priv->heap, &node->mem);
+       nvkm_instobj_destroy(&node->base);
+}
+
+static int
+nv04_instobj_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+                 struct nvkm_oclass *oclass, void *data, u32 size,
+                 struct nvkm_object **pobject)
+{
+       struct nv04_instmem_priv *priv = (void *)nvkm_instmem(parent);
+       struct nv04_instobj_priv *node;
+       struct nvkm_instobj_args *args = data;
+       int ret;
+
+       if (!args->align)
+               args->align = 1;
+
+       ret = nvkm_instobj_create(parent, engine, oclass, &node);
+       *pobject = nv_object(node);
+       if (ret)
+               return ret;
+
+       ret = nvkm_mm_head(&priv->heap, 0, 1, args->size, args->size,
+                          args->align, &node->mem);
+       if (ret)
+               return ret;
+
+       node->base.addr = node->mem->offset;
+       node->base.size = node->mem->length;
+       return 0;
+}
+
+struct nvkm_instobj_impl
+nv04_instobj_oclass = {
+       .base.ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = nv04_instobj_ctor,
+               .dtor = nv04_instobj_dtor,
+               .init = _nvkm_instobj_init,
+               .fini = _nvkm_instobj_fini,
+               .rd32 = nv04_instobj_rd32,
+               .wr32 = nv04_instobj_wr32,
+       },
+};
+
+/******************************************************************************
+ * instmem subdev implementation
+ *****************************************************************************/
+
+static u32
+nv04_instmem_rd32(struct nvkm_object *object, u64 addr)
+{
+       return nv_rd32(object, 0x700000 + addr);
+}
+
+static void
+nv04_instmem_wr32(struct nvkm_object *object, u64 addr, u32 data)
+{
+       return nv_wr32(object, 0x700000 + addr, data);
+}
+
+void
+nv04_instmem_dtor(struct nvkm_object *object)
+{
+       struct nv04_instmem_priv *priv = (void *)object;
+       nvkm_gpuobj_ref(NULL, &priv->ramfc);
+       nvkm_gpuobj_ref(NULL, &priv->ramro);
+       nvkm_ramht_ref(NULL, &priv->ramht);
+       nvkm_gpuobj_ref(NULL, &priv->vbios);
+       nvkm_mm_fini(&priv->heap);
+       if (priv->iomem)
+               iounmap(priv->iomem);
+       nvkm_instmem_destroy(&priv->base);
+}
+
+static int
+nv04_instmem_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+                 struct nvkm_oclass *oclass, void *data, u32 size,
+                 struct nvkm_object **pobject)
+{
+       struct nv04_instmem_priv *priv;
+       int ret;
+
+       ret = nvkm_instmem_create(parent, engine, oclass, &priv);
+       *pobject = nv_object(priv);
+       if (ret)
+               return ret;
+
+       /* PRAMIN aperture maps over the end of VRAM, reserve it */
+       priv->base.reserved = 512 * 1024;
+
+       ret = nvkm_mm_init(&priv->heap, 0, priv->base.reserved, 1);
+       if (ret)
+               return ret;
+
+       /* 0x00000-0x10000: reserve for probable vbios image */
+       ret = nvkm_gpuobj_new(nv_object(priv), NULL, 0x10000, 0, 0,
+                             &priv->vbios);
+       if (ret)
+               return ret;
+
+       /* 0x10000-0x18000: reserve for RAMHT */
+       ret = nvkm_ramht_new(nv_object(priv), NULL, 0x08000, 0, &priv->ramht);
+       if (ret)
+               return ret;
+
+       /* 0x18000-0x18800: reserve for RAMFC (enough for 32 nv30 channels) */
+       ret = nvkm_gpuobj_new(nv_object(priv), NULL, 0x00800, 0,
+                             NVOBJ_FLAG_ZERO_ALLOC, &priv->ramfc);
+       if (ret)
+               return ret;
+
+       /* 0x18800-0x18a00: reserve for RAMRO */
+       ret = nvkm_gpuobj_new(nv_object(priv), NULL, 0x00200, 0, 0,
+                             &priv->ramro);
+       if (ret)
+               return ret;
+
+       return 0;
+}
+
+struct nvkm_oclass *
+nv04_instmem_oclass = &(struct nvkm_instmem_impl) {
+       .base.handle = NV_SUBDEV(INSTMEM, 0x04),
+       .base.ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = nv04_instmem_ctor,
+               .dtor = nv04_instmem_dtor,
+               .init = _nvkm_instmem_init,
+               .fini = _nvkm_instmem_fini,
+               .rd32 = nv04_instmem_rd32,
+               .wr32 = nv04_instmem_wr32,
+       },
+       .instobj = &nv04_instobj_oclass.base,
+}.base;
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/instmem/nv04.h b/drivers/gpu/drm/nouveau/nvkm/subdev/instmem/nv04.h
new file mode 100644 (file)
index 0000000..42b6c92
--- /dev/null
@@ -0,0 +1,36 @@
+#ifndef __NV04_INSTMEM_H__
+#define __NV04_INSTMEM_H__
+#include "priv.h"
+
+#include <core/mm.h>
+
+extern struct nvkm_instobj_impl nv04_instobj_oclass;
+
+struct nv04_instmem_priv {
+       struct nvkm_instmem base;
+
+       void __iomem *iomem;
+       struct nvkm_mm heap;
+
+       struct nvkm_gpuobj *vbios;
+       struct nvkm_ramht  *ramht;
+       struct nvkm_gpuobj *ramro;
+       struct nvkm_gpuobj *ramfc;
+};
+
+static inline struct nv04_instmem_priv *
+nv04_instmem(void *obj)
+{
+       return (void *)nvkm_instmem(obj);
+}
+
+struct nv04_instobj_priv {
+       struct nvkm_instobj base;
+       struct nvkm_mm_node *mem;
+};
+
+void nv04_instmem_dtor(struct nvkm_object *);
+
+int nv04_instmem_alloc(struct nvkm_instmem *, struct nvkm_object *,
+                      u32 size, u32 align, struct nvkm_object **pobject);
+#endif
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/instmem/nv40.c b/drivers/gpu/drm/nouveau/nvkm/subdev/instmem/nv40.c
new file mode 100644 (file)
index 0000000..b42b858
--- /dev/null
@@ -0,0 +1,136 @@
+/*
+ * Copyright 2012 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 "nv04.h"
+
+#include <core/ramht.h>
+#include <engine/gr/nv40.h>
+
+/******************************************************************************
+ * instmem subdev implementation
+ *****************************************************************************/
+
+static u32
+nv40_instmem_rd32(struct nvkm_object *object, u64 addr)
+{
+       struct nv04_instmem_priv *priv = (void *)object;
+       return ioread32_native(priv->iomem + addr);
+}
+
+static void
+nv40_instmem_wr32(struct nvkm_object *object, u64 addr, u32 data)
+{
+       struct nv04_instmem_priv *priv = (void *)object;
+       iowrite32_native(data, priv->iomem + addr);
+}
+
+static int
+nv40_instmem_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+                 struct nvkm_oclass *oclass, void *data, u32 size,
+                 struct nvkm_object **pobject)
+{
+       struct nvkm_device *device = nv_device(parent);
+       struct nv04_instmem_priv *priv;
+       int ret, bar, vs;
+
+       ret = nvkm_instmem_create(parent, engine, oclass, &priv);
+       *pobject = nv_object(priv);
+       if (ret)
+               return ret;
+
+       /* map bar */
+       if (nv_device_resource_len(device, 2))
+               bar = 2;
+       else
+               bar = 3;
+
+       priv->iomem = ioremap(nv_device_resource_start(device, bar),
+                             nv_device_resource_len(device, bar));
+       if (!priv->iomem) {
+               nv_error(priv, "unable to map PRAMIN BAR\n");
+               return -EFAULT;
+       }
+
+       /* PRAMIN aperture maps over the end of vram, reserve enough space
+        * to fit graphics contexts for every channel, the magics come
+        * from engine/gr/nv40.c
+        */
+       vs = hweight8((nv_rd32(priv, 0x001540) & 0x0000ff00) >> 8);
+       if      (device->chipset == 0x40) priv->base.reserved = 0x6aa0 * vs;
+       else if (device->chipset  < 0x43) priv->base.reserved = 0x4f00 * vs;
+       else if (nv44_gr_class(priv))  priv->base.reserved = 0x4980 * vs;
+       else                              priv->base.reserved = 0x4a40 * vs;
+       priv->base.reserved += 16 * 1024;
+       priv->base.reserved *= 32;              /* per-channel */
+       priv->base.reserved += 512 * 1024;      /* pci(e)gart table */
+       priv->base.reserved += 512 * 1024;      /* object storage */
+
+       priv->base.reserved = round_up(priv->base.reserved, 4096);
+
+       ret = nvkm_mm_init(&priv->heap, 0, priv->base.reserved, 1);
+       if (ret)
+               return ret;
+
+       /* 0x00000-0x10000: reserve for probable vbios image */
+       ret = nvkm_gpuobj_new(nv_object(priv), NULL, 0x10000, 0, 0,
+                             &priv->vbios);
+       if (ret)
+               return ret;
+
+       /* 0x10000-0x18000: reserve for RAMHT */
+       ret = nvkm_ramht_new(nv_object(priv), NULL, 0x08000, 0, &priv->ramht);
+       if (ret)
+               return ret;
+
+       /* 0x18000-0x18200: reserve for RAMRO
+        * 0x18200-0x20000: padding
+        */
+       ret = nvkm_gpuobj_new(nv_object(priv), NULL, 0x08000, 0, 0,
+                             &priv->ramro);
+       if (ret)
+               return ret;
+
+       /* 0x20000-0x21000: reserve for RAMFC
+        * 0x21000-0x40000: padding and some unknown crap
+        */
+       ret = nvkm_gpuobj_new(nv_object(priv), NULL, 0x20000, 0,
+                             NVOBJ_FLAG_ZERO_ALLOC, &priv->ramfc);
+       if (ret)
+               return ret;
+
+       return 0;
+}
+
+struct nvkm_oclass *
+nv40_instmem_oclass = &(struct nvkm_instmem_impl) {
+       .base.handle = NV_SUBDEV(INSTMEM, 0x40),
+       .base.ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = nv40_instmem_ctor,
+               .dtor = nv04_instmem_dtor,
+               .init = _nvkm_instmem_init,
+               .fini = _nvkm_instmem_fini,
+               .rd32 = nv40_instmem_rd32,
+               .wr32 = nv40_instmem_wr32,
+       },
+       .instobj = &nv04_instobj_oclass.base,
+}.base;
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/instmem/nv50.c b/drivers/gpu/drm/nouveau/nvkm/subdev/instmem/nv50.c
new file mode 100644 (file)
index 0000000..8404143
--- /dev/null
@@ -0,0 +1,169 @@
+/*
+ * Copyright 2012 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 "priv.h"
+
+#include <subdev/fb.h>
+
+struct nv50_instmem_priv {
+       struct nvkm_instmem base;
+       spinlock_t lock;
+       u64 addr;
+};
+
+struct nv50_instobj_priv {
+       struct nvkm_instobj base;
+       struct nvkm_mem *mem;
+};
+
+/******************************************************************************
+ * instmem object implementation
+ *****************************************************************************/
+
+static u32
+nv50_instobj_rd32(struct nvkm_object *object, u64 offset)
+{
+       struct nv50_instmem_priv *priv = (void *)nvkm_instmem(object);
+       struct nv50_instobj_priv *node = (void *)object;
+       unsigned long flags;
+       u64 base = (node->mem->offset + offset) & 0xffffff00000ULL;
+       u64 addr = (node->mem->offset + offset) & 0x000000fffffULL;
+       u32 data;
+
+       spin_lock_irqsave(&priv->lock, flags);
+       if (unlikely(priv->addr != base)) {
+               nv_wr32(priv, 0x001700, base >> 16);
+               priv->addr = base;
+       }
+       data = nv_rd32(priv, 0x700000 + addr);
+       spin_unlock_irqrestore(&priv->lock, flags);
+       return data;
+}
+
+static void
+nv50_instobj_wr32(struct nvkm_object *object, u64 offset, u32 data)
+{
+       struct nv50_instmem_priv *priv = (void *)nvkm_instmem(object);
+       struct nv50_instobj_priv *node = (void *)object;
+       unsigned long flags;
+       u64 base = (node->mem->offset + offset) & 0xffffff00000ULL;
+       u64 addr = (node->mem->offset + offset) & 0x000000fffffULL;
+
+       spin_lock_irqsave(&priv->lock, flags);
+       if (unlikely(priv->addr != base)) {
+               nv_wr32(priv, 0x001700, base >> 16);
+               priv->addr = base;
+       }
+       nv_wr32(priv, 0x700000 + addr, data);
+       spin_unlock_irqrestore(&priv->lock, flags);
+}
+
+static void
+nv50_instobj_dtor(struct nvkm_object *object)
+{
+       struct nv50_instobj_priv *node = (void *)object;
+       struct nvkm_fb *pfb = nvkm_fb(object);
+       pfb->ram->put(pfb, &node->mem);
+       nvkm_instobj_destroy(&node->base);
+}
+
+static int
+nv50_instobj_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+                 struct nvkm_oclass *oclass, void *data, u32 size,
+                 struct nvkm_object **pobject)
+{
+       struct nvkm_fb *pfb = nvkm_fb(parent);
+       struct nvkm_instobj_args *args = data;
+       struct nv50_instobj_priv *node;
+       int ret;
+
+       args->size  = max((args->size  + 4095) & ~4095, (u32)4096);
+       args->align = max((args->align + 4095) & ~4095, (u32)4096);
+
+       ret = nvkm_instobj_create(parent, engine, oclass, &node);
+       *pobject = nv_object(node);
+       if (ret)
+               return ret;
+
+       ret = pfb->ram->get(pfb, args->size, args->align, 0, 0x800, &node->mem);
+       if (ret)
+               return ret;
+
+       node->base.addr = node->mem->offset;
+       node->base.size = node->mem->size << 12;
+       node->mem->page_shift = 12;
+       return 0;
+}
+
+static struct nvkm_instobj_impl
+nv50_instobj_oclass = {
+       .base.ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = nv50_instobj_ctor,
+               .dtor = nv50_instobj_dtor,
+               .init = _nvkm_instobj_init,
+               .fini = _nvkm_instobj_fini,
+               .rd32 = nv50_instobj_rd32,
+               .wr32 = nv50_instobj_wr32,
+       },
+};
+
+/******************************************************************************
+ * instmem subdev implementation
+ *****************************************************************************/
+
+static int
+nv50_instmem_fini(struct nvkm_object *object, bool suspend)
+{
+       struct nv50_instmem_priv *priv = (void *)object;
+       priv->addr = ~0ULL;
+       return nvkm_instmem_fini(&priv->base, suspend);
+}
+
+static int
+nv50_instmem_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+                 struct nvkm_oclass *oclass, void *data, u32 size,
+                 struct nvkm_object **pobject)
+{
+       struct nv50_instmem_priv *priv;
+       int ret;
+
+       ret = nvkm_instmem_create(parent, engine, oclass, &priv);
+       *pobject = nv_object(priv);
+       if (ret)
+               return ret;
+
+       spin_lock_init(&priv->lock);
+       return 0;
+}
+
+struct nvkm_oclass *
+nv50_instmem_oclass = &(struct nvkm_instmem_impl) {
+       .base.handle = NV_SUBDEV(INSTMEM, 0x50),
+       .base.ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = nv50_instmem_ctor,
+               .dtor = _nvkm_instmem_dtor,
+               .init = _nvkm_instmem_init,
+               .fini = nv50_instmem_fini,
+       },
+       .instobj = &nv50_instobj_oclass.base,
+}.base;
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/instmem/priv.h b/drivers/gpu/drm/nouveau/nvkm/subdev/instmem/priv.h
new file mode 100644 (file)
index 0000000..b10e292
--- /dev/null
@@ -0,0 +1,54 @@
+#ifndef __NVKM_INSTMEM_PRIV_H__
+#define __NVKM_INSTMEM_PRIV_H__
+#include <subdev/instmem.h>
+
+struct nvkm_instobj_impl {
+       struct nvkm_oclass base;
+};
+
+struct nvkm_instobj_args {
+       u32 size;
+       u32 align;
+};
+
+#define nvkm_instobj_create(p,e,o,d)                                        \
+       nvkm_instobj_create_((p), (e), (o), sizeof(**d), (void **)d)
+#define nvkm_instobj_destroy(p) ({                                          \
+       struct nvkm_instobj *iobj = (p);                                    \
+       _nvkm_instobj_dtor(nv_object(iobj));                                \
+})
+#define nvkm_instobj_init(p)                                                \
+       nvkm_object_init(&(p)->base)
+#define nvkm_instobj_fini(p,s)                                              \
+       nvkm_object_fini(&(p)->base, (s))
+
+int  nvkm_instobj_create_(struct nvkm_object *, struct nvkm_object *,
+                            struct nvkm_oclass *, int, void **);
+void _nvkm_instobj_dtor(struct nvkm_object *);
+#define _nvkm_instobj_init nvkm_object_init
+#define _nvkm_instobj_fini nvkm_object_fini
+
+struct nvkm_instmem_impl {
+       struct nvkm_oclass base;
+       struct nvkm_oclass *instobj;
+};
+
+#define nvkm_instmem_create(p,e,o,d)                                        \
+       nvkm_instmem_create_((p), (e), (o), sizeof(**d), (void **)d)
+#define nvkm_instmem_destroy(p)                                             \
+       nvkm_subdev_destroy(&(p)->base)
+#define nvkm_instmem_init(p) ({                                             \
+       struct nvkm_instmem *imem = (p);                                    \
+       _nvkm_instmem_init(nv_object(imem));                                \
+})
+#define nvkm_instmem_fini(p,s) ({                                           \
+       struct nvkm_instmem *imem = (p);                                    \
+       _nvkm_instmem_fini(nv_object(imem), (s));                           \
+})
+
+int nvkm_instmem_create_(struct nvkm_object *, struct nvkm_object *,
+                           struct nvkm_oclass *, int, void **);
+#define _nvkm_instmem_dtor _nvkm_subdev_dtor
+int _nvkm_instmem_init(struct nvkm_object *);
+int _nvkm_instmem_fini(struct nvkm_object *, bool);
+#endif
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/ltc/Kbuild b/drivers/gpu/drm/nouveau/nvkm/subdev/ltc/Kbuild
new file mode 100644 (file)
index 0000000..e5df3d8
--- /dev/null
@@ -0,0 +1,4 @@
+nvkm-y += nvkm/subdev/ltc/base.o
+nvkm-y += nvkm/subdev/ltc/gf100.o
+nvkm-y += nvkm/subdev/ltc/gk104.o
+nvkm-y += nvkm/subdev/ltc/gm107.o
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/ltc/base.c b/drivers/gpu/drm/nouveau/nvkm/subdev/ltc/base.c
new file mode 100644 (file)
index 0000000..2fb87fb
--- /dev/null
@@ -0,0 +1,124 @@
+/*
+ * Copyright 2014 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 <bskeggs@redhat.com>
+ */
+#include "priv.h"
+
+static int
+nvkm_ltc_tags_alloc(struct nvkm_ltc *ltc, u32 n, struct nvkm_mm_node **pnode)
+{
+       struct nvkm_ltc_priv *priv = (void *)ltc;
+       int ret;
+
+       ret = nvkm_mm_head(&priv->tags, 0, 1, n, n, 1, pnode);
+       if (ret)
+               *pnode = NULL;
+
+       return ret;
+}
+
+static void
+nvkm_ltc_tags_free(struct nvkm_ltc *ltc, struct nvkm_mm_node **pnode)
+{
+       struct nvkm_ltc_priv *priv = (void *)ltc;
+       nvkm_mm_free(&priv->tags, pnode);
+}
+
+static void
+nvkm_ltc_tags_clear(struct nvkm_ltc *ltc, u32 first, u32 count)
+{
+       const struct nvkm_ltc_impl *impl = (void *)nv_oclass(ltc);
+       struct nvkm_ltc_priv *priv = (void *)ltc;
+       const u32 limit = first + count - 1;
+
+       BUG_ON((first > limit) || (limit >= priv->num_tags));
+
+       impl->cbc_clear(priv, first, limit);
+       impl->cbc_wait(priv);
+}
+
+static int
+nvkm_ltc_zbc_color_get(struct nvkm_ltc *ltc, int index, const u32 color[4])
+{
+       const struct nvkm_ltc_impl *impl = (void *)nv_oclass(ltc);
+       struct nvkm_ltc_priv *priv = (void *)ltc;
+       memcpy(priv->zbc_color[index], color, sizeof(priv->zbc_color[index]));
+       impl->zbc_clear_color(priv, index, color);
+       return index;
+}
+
+static int
+nvkm_ltc_zbc_depth_get(struct nvkm_ltc *ltc, int index, const u32 depth)
+{
+       const struct nvkm_ltc_impl *impl = (void *)nv_oclass(ltc);
+       struct nvkm_ltc_priv *priv = (void *)ltc;
+       priv->zbc_depth[index] = depth;
+       impl->zbc_clear_depth(priv, index, depth);
+       return index;
+}
+
+int
+_nvkm_ltc_init(struct nvkm_object *object)
+{
+       const struct nvkm_ltc_impl *impl = (void *)nv_oclass(object);
+       struct nvkm_ltc_priv *priv = (void *)object;
+       int ret, i;
+
+       ret = nvkm_subdev_init(&priv->base.base);
+       if (ret)
+               return ret;
+
+       for (i = priv->base.zbc_min; i <= priv->base.zbc_max; i++) {
+               impl->zbc_clear_color(priv, i, priv->zbc_color[i]);
+               impl->zbc_clear_depth(priv, i, priv->zbc_depth[i]);
+       }
+
+       return 0;
+}
+
+int
+nvkm_ltc_create_(struct nvkm_object *parent, struct nvkm_object *engine,
+                struct nvkm_oclass *oclass, int length, void **pobject)
+{
+       const struct nvkm_ltc_impl *impl = (void *)oclass;
+       struct nvkm_ltc_priv *priv;
+       int ret;
+
+       ret = nvkm_subdev_create_(parent, engine, oclass, 0, "PLTCG",
+                                 "l2c", length, pobject);
+       priv = *pobject;
+       if (ret)
+               return ret;
+
+       memset(priv->zbc_color, 0x00, sizeof(priv->zbc_color));
+       memset(priv->zbc_depth, 0x00, sizeof(priv->zbc_depth));
+
+       priv->base.base.intr = impl->intr;
+       priv->base.tags_alloc = nvkm_ltc_tags_alloc;
+       priv->base.tags_free = nvkm_ltc_tags_free;
+       priv->base.tags_clear = nvkm_ltc_tags_clear;
+       priv->base.zbc_min = 1; /* reserve 0 for disabled */
+       priv->base.zbc_max = min(impl->zbc, NVKM_LTC_MAX_ZBC_CNT) - 1;
+       priv->base.zbc_color_get = nvkm_ltc_zbc_color_get;
+       priv->base.zbc_depth_get = nvkm_ltc_zbc_depth_get;
+       return 0;
+}
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/ltc/gf100.c b/drivers/gpu/drm/nouveau/nvkm/subdev/ltc/gf100.c
new file mode 100644 (file)
index 0000000..8e7cc62
--- /dev/null
@@ -0,0 +1,236 @@
+/*
+ * Copyright 2012 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 "priv.h"
+
+#include <core/enum.h>
+#include <subdev/fb.h>
+#include <subdev/timer.h>
+
+void
+gf100_ltc_cbc_clear(struct nvkm_ltc_priv *priv, u32 start, u32 limit)
+{
+       nv_wr32(priv, 0x17e8cc, start);
+       nv_wr32(priv, 0x17e8d0, limit);
+       nv_wr32(priv, 0x17e8c8, 0x00000004);
+}
+
+void
+gf100_ltc_cbc_wait(struct nvkm_ltc_priv *priv)
+{
+       int c, s;
+       for (c = 0; c < priv->ltc_nr; c++) {
+               for (s = 0; s < priv->lts_nr; s++)
+                       nv_wait(priv, 0x1410c8 + c * 0x2000 + s * 0x400, ~0, 0);
+       }
+}
+
+void
+gf100_ltc_zbc_clear_color(struct nvkm_ltc_priv *priv, int i, const u32 color[4])
+{
+       nv_mask(priv, 0x17ea44, 0x0000000f, i);
+       nv_wr32(priv, 0x17ea48, color[0]);
+       nv_wr32(priv, 0x17ea4c, color[1]);
+       nv_wr32(priv, 0x17ea50, color[2]);
+       nv_wr32(priv, 0x17ea54, color[3]);
+}
+
+void
+gf100_ltc_zbc_clear_depth(struct nvkm_ltc_priv *priv, int i, const u32 depth)
+{
+       nv_mask(priv, 0x17ea44, 0x0000000f, i);
+       nv_wr32(priv, 0x17ea58, depth);
+}
+
+static const struct nvkm_bitfield
+gf100_ltc_lts_intr_name[] = {
+       { 0x00000001, "IDLE_ERROR_IQ" },
+       { 0x00000002, "IDLE_ERROR_CBC" },
+       { 0x00000004, "IDLE_ERROR_TSTG" },
+       { 0x00000008, "IDLE_ERROR_DSTG" },
+       { 0x00000010, "EVICTED_CB" },
+       { 0x00000020, "ILLEGAL_COMPSTAT" },
+       { 0x00000040, "BLOCKLINEAR_CB" },
+       { 0x00000100, "ECC_SEC_ERROR" },
+       { 0x00000200, "ECC_DED_ERROR" },
+       { 0x00000400, "DEBUG" },
+       { 0x00000800, "ATOMIC_TO_Z" },
+       { 0x00001000, "ILLEGAL_ATOMIC" },
+       { 0x00002000, "BLKACTIVITY_ERR" },
+       {}
+};
+
+static void
+gf100_ltc_lts_intr(struct nvkm_ltc_priv *priv, int ltc, int lts)
+{
+       u32 base = 0x141000 + (ltc * 0x2000) + (lts * 0x400);
+       u32 intr = nv_rd32(priv, base + 0x020);
+       u32 stat = intr & 0x0000ffff;
+
+       if (stat) {
+               nv_info(priv, "LTC%d_LTS%d:", ltc, lts);
+               nvkm_bitfield_print(gf100_ltc_lts_intr_name, stat);
+               pr_cont("\n");
+       }
+
+       nv_wr32(priv, base + 0x020, intr);
+}
+
+void
+gf100_ltc_intr(struct nvkm_subdev *subdev)
+{
+       struct nvkm_ltc_priv *priv = (void *)subdev;
+       u32 mask;
+
+       mask = nv_rd32(priv, 0x00017c);
+       while (mask) {
+               u32 lts, ltc = __ffs(mask);
+               for (lts = 0; lts < priv->lts_nr; lts++)
+                       gf100_ltc_lts_intr(priv, ltc, lts);
+               mask &= ~(1 << ltc);
+       }
+}
+
+static int
+gf100_ltc_init(struct nvkm_object *object)
+{
+       struct nvkm_ltc_priv *priv = (void *)object;
+       u32 lpg128 = !(nv_rd32(priv, 0x100c80) & 0x00000001);
+       int ret;
+
+       ret = nvkm_ltc_init(priv);
+       if (ret)
+               return ret;
+
+       nv_mask(priv, 0x17e820, 0x00100000, 0x00000000); /* INTR_EN &= ~0x10 */
+       nv_wr32(priv, 0x17e8d8, priv->ltc_nr);
+       nv_wr32(priv, 0x17e8d4, priv->tag_base);
+       nv_mask(priv, 0x17e8c0, 0x00000002, lpg128 ? 0x00000002 : 0x00000000);
+       return 0;
+}
+
+void
+gf100_ltc_dtor(struct nvkm_object *object)
+{
+       struct nvkm_fb *pfb = nvkm_fb(object);
+       struct nvkm_ltc_priv *priv = (void *)object;
+
+       nvkm_mm_fini(&priv->tags);
+       nvkm_mm_free(&pfb->vram, &priv->tag_ram);
+
+       nvkm_ltc_destroy(priv);
+}
+
+/* TODO: Figure out tag memory details and drop the over-cautious allocation.
+ */
+int
+gf100_ltc_init_tag_ram(struct nvkm_fb *pfb, struct nvkm_ltc_priv *priv)
+{
+       u32 tag_size, tag_margin, tag_align;
+       int ret;
+
+       /* tags for 1/4 of VRAM should be enough (8192/4 per GiB of VRAM) */
+       priv->num_tags = (pfb->ram->size >> 17) / 4;
+       if (priv->num_tags > (1 << 17))
+               priv->num_tags = 1 << 17; /* we have 17 bits in PTE */
+       priv->num_tags = (priv->num_tags + 63) & ~63; /* round up to 64 */
+
+       tag_align = priv->ltc_nr * 0x800;
+       tag_margin = (tag_align < 0x6000) ? 0x6000 : tag_align;
+
+       /* 4 part 4 sub: 0x2000 bytes for 56 tags */
+       /* 3 part 4 sub: 0x6000 bytes for 168 tags */
+       /*
+        * About 147 bytes per tag. Let's be safe and allocate x2, which makes
+        * 0x4980 bytes for 64 tags, and round up to 0x6000 bytes for 64 tags.
+        *
+        * For 4 GiB of memory we'll have 8192 tags which makes 3 MiB, < 0.1 %.
+        */
+       tag_size  = (priv->num_tags / 64) * 0x6000 + tag_margin;
+       tag_size += tag_align;
+       tag_size  = (tag_size + 0xfff) >> 12; /* round up */
+
+       ret = nvkm_mm_tail(&pfb->vram, 1, 1, tag_size, tag_size, 1,
+                          &priv->tag_ram);
+       if (ret) {
+               priv->num_tags = 0;
+       } else {
+               u64 tag_base = ((u64)priv->tag_ram->offset << 12) + tag_margin;
+
+               tag_base += tag_align - 1;
+               ret = do_div(tag_base, tag_align);
+
+               priv->tag_base = tag_base;
+       }
+
+       ret = nvkm_mm_init(&priv->tags, 0, priv->num_tags, 1);
+       return ret;
+}
+
+int
+gf100_ltc_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+              struct nvkm_oclass *oclass, void *data, u32 size,
+              struct nvkm_object **pobject)
+{
+       struct nvkm_fb *pfb = nvkm_fb(parent);
+       struct nvkm_ltc_priv *priv;
+       u32 parts, mask;
+       int ret, i;
+
+       ret = nvkm_ltc_create(parent, engine, oclass, &priv);
+       *pobject = nv_object(priv);
+       if (ret)
+               return ret;
+
+       parts = nv_rd32(priv, 0x022438);
+       mask = nv_rd32(priv, 0x022554);
+       for (i = 0; i < parts; i++) {
+               if (!(mask & (1 << i)))
+                       priv->ltc_nr++;
+       }
+       priv->lts_nr = nv_rd32(priv, 0x17e8dc) >> 28;
+
+       ret = gf100_ltc_init_tag_ram(pfb, priv);
+       if (ret)
+               return ret;
+
+       nv_subdev(priv)->intr = gf100_ltc_intr;
+       return 0;
+}
+
+struct nvkm_oclass *
+gf100_ltc_oclass = &(struct nvkm_ltc_impl) {
+       .base.handle = NV_SUBDEV(LTC, 0xc0),
+       .base.ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = gf100_ltc_ctor,
+               .dtor = gf100_ltc_dtor,
+               .init = gf100_ltc_init,
+               .fini = _nvkm_ltc_fini,
+       },
+       .intr = gf100_ltc_intr,
+       .cbc_clear = gf100_ltc_cbc_clear,
+       .cbc_wait = gf100_ltc_cbc_wait,
+       .zbc = 16,
+       .zbc_clear_color = gf100_ltc_zbc_clear_color,
+       .zbc_clear_depth = gf100_ltc_zbc_clear_depth,
+}.base;
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/ltc/gk104.c b/drivers/gpu/drm/nouveau/nvkm/subdev/ltc/gk104.c
new file mode 100644 (file)
index 0000000..d53959b
--- /dev/null
@@ -0,0 +1,59 @@
+/*
+ * Copyright 2012 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 "priv.h"
+
+static int
+gk104_ltc_init(struct nvkm_object *object)
+{
+       struct nvkm_ltc_priv *priv = (void *)object;
+       u32 lpg128 = !(nv_rd32(priv, 0x100c80) & 0x00000001);
+       int ret;
+
+       ret = nvkm_ltc_init(priv);
+       if (ret)
+               return ret;
+
+       nv_wr32(priv, 0x17e8d8, priv->ltc_nr);
+       nv_wr32(priv, 0x17e000, priv->ltc_nr);
+       nv_wr32(priv, 0x17e8d4, priv->tag_base);
+       nv_mask(priv, 0x17e8c0, 0x00000002, lpg128 ? 0x00000002 : 0x00000000);
+       return 0;
+}
+
+struct nvkm_oclass *
+gk104_ltc_oclass = &(struct nvkm_ltc_impl) {
+       .base.handle = NV_SUBDEV(LTC, 0xe4),
+       .base.ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = gf100_ltc_ctor,
+               .dtor = gf100_ltc_dtor,
+               .init = gk104_ltc_init,
+               .fini = _nvkm_ltc_fini,
+       },
+       .intr = gf100_ltc_intr,
+       .cbc_clear = gf100_ltc_cbc_clear,
+       .cbc_wait = gf100_ltc_cbc_wait,
+       .zbc = 16,
+       .zbc_clear_color = gf100_ltc_zbc_clear_color,
+       .zbc_clear_depth = gf100_ltc_zbc_clear_depth,
+}.base;
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/ltc/gm107.c b/drivers/gpu/drm/nouveau/nvkm/subdev/ltc/gm107.c
new file mode 100644 (file)
index 0000000..6b3f6f4
--- /dev/null
@@ -0,0 +1,153 @@
+/*
+ * Copyright 2014 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 "priv.h"
+
+#include <subdev/fb.h>
+#include <subdev/timer.h>
+
+static void
+gm107_ltc_cbc_clear(struct nvkm_ltc_priv *priv, u32 start, u32 limit)
+{
+       nv_wr32(priv, 0x17e270, start);
+       nv_wr32(priv, 0x17e274, limit);
+       nv_wr32(priv, 0x17e26c, 0x00000004);
+}
+
+static void
+gm107_ltc_cbc_wait(struct nvkm_ltc_priv *priv)
+{
+       int c, s;
+       for (c = 0; c < priv->ltc_nr; c++) {
+               for (s = 0; s < priv->lts_nr; s++)
+                       nv_wait(priv, 0x14046c + c * 0x2000 + s * 0x200, ~0, 0);
+       }
+}
+
+static void
+gm107_ltc_zbc_clear_color(struct nvkm_ltc_priv *priv, int i, const u32 color[4])
+{
+       nv_mask(priv, 0x17e338, 0x0000000f, i);
+       nv_wr32(priv, 0x17e33c, color[0]);
+       nv_wr32(priv, 0x17e340, color[1]);
+       nv_wr32(priv, 0x17e344, color[2]);
+       nv_wr32(priv, 0x17e348, color[3]);
+}
+
+static void
+gm107_ltc_zbc_clear_depth(struct nvkm_ltc_priv *priv, int i, const u32 depth)
+{
+       nv_mask(priv, 0x17e338, 0x0000000f, i);
+       nv_wr32(priv, 0x17e34c, depth);
+}
+
+static void
+gm107_ltc_lts_isr(struct nvkm_ltc_priv *priv, int ltc, int lts)
+{
+       u32 base = 0x140000 + (ltc * 0x2000) + (lts * 0x400);
+       u32 stat = nv_rd32(priv, base + 0x00c);
+
+       if (stat) {
+               nv_info(priv, "LTC%d_LTS%d: 0x%08x\n", ltc, lts, stat);
+               nv_wr32(priv, base + 0x00c, stat);
+       }
+}
+
+static void
+gm107_ltc_intr(struct nvkm_subdev *subdev)
+{
+       struct nvkm_ltc_priv *priv = (void *)subdev;
+       u32 mask;
+
+       mask = nv_rd32(priv, 0x00017c);
+       while (mask) {
+               u32 lts, ltc = __ffs(mask);
+               for (lts = 0; lts < priv->lts_nr; lts++)
+                       gm107_ltc_lts_isr(priv, ltc, lts);
+               mask &= ~(1 << ltc);
+       }
+}
+
+static int
+gm107_ltc_init(struct nvkm_object *object)
+{
+       struct nvkm_ltc_priv *priv = (void *)object;
+       u32 lpg128 = !(nv_rd32(priv, 0x100c80) & 0x00000001);
+       int ret;
+
+       ret = nvkm_ltc_init(priv);
+       if (ret)
+               return ret;
+
+       nv_wr32(priv, 0x17e27c, priv->ltc_nr);
+       nv_wr32(priv, 0x17e278, priv->tag_base);
+       nv_mask(priv, 0x17e264, 0x00000002, lpg128 ? 0x00000002 : 0x00000000);
+       return 0;
+}
+
+static int
+gm107_ltc_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+              struct nvkm_oclass *oclass, void *data, u32 size,
+              struct nvkm_object **pobject)
+{
+       struct nvkm_fb *pfb = nvkm_fb(parent);
+       struct nvkm_ltc_priv *priv;
+       u32 parts, mask;
+       int ret, i;
+
+       ret = nvkm_ltc_create(parent, engine, oclass, &priv);
+       *pobject = nv_object(priv);
+       if (ret)
+               return ret;
+
+       parts = nv_rd32(priv, 0x022438);
+       mask = nv_rd32(priv, 0x021c14);
+       for (i = 0; i < parts; i++) {
+               if (!(mask & (1 << i)))
+                       priv->ltc_nr++;
+       }
+       priv->lts_nr = nv_rd32(priv, 0x17e280) >> 28;
+
+       ret = gf100_ltc_init_tag_ram(pfb, priv);
+       if (ret)
+               return ret;
+
+       return 0;
+}
+
+struct nvkm_oclass *
+gm107_ltc_oclass = &(struct nvkm_ltc_impl) {
+       .base.handle = NV_SUBDEV(LTC, 0xff),
+       .base.ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = gm107_ltc_ctor,
+               .dtor = gf100_ltc_dtor,
+               .init = gm107_ltc_init,
+               .fini = _nvkm_ltc_fini,
+       },
+       .intr = gm107_ltc_intr,
+       .cbc_clear = gm107_ltc_cbc_clear,
+       .cbc_wait = gm107_ltc_cbc_wait,
+       .zbc = 16,
+       .zbc_clear_color = gm107_ltc_zbc_clear_color,
+       .zbc_clear_depth = gm107_ltc_zbc_clear_depth,
+}.base;
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/ltc/priv.h b/drivers/gpu/drm/nouveau/nvkm/subdev/ltc/priv.h
new file mode 100644 (file)
index 0000000..09537d7
--- /dev/null
@@ -0,0 +1,69 @@
+#ifndef __NVKM_LTC_PRIV_H__
+#define __NVKM_LTC_PRIV_H__
+#include <subdev/ltc.h>
+
+#include <core/mm.h>
+struct nvkm_fb;
+
+struct nvkm_ltc_priv {
+       struct nvkm_ltc base;
+       u32 ltc_nr;
+       u32 lts_nr;
+
+       u32 num_tags;
+       u32 tag_base;
+       struct nvkm_mm tags;
+       struct nvkm_mm_node *tag_ram;
+
+       u32 zbc_color[NVKM_LTC_MAX_ZBC_CNT][4];
+       u32 zbc_depth[NVKM_LTC_MAX_ZBC_CNT];
+};
+
+#define nvkm_ltc_create(p,e,o,d)                                               \
+       nvkm_ltc_create_((p), (e), (o), sizeof(**d), (void **)d)
+#define nvkm_ltc_destroy(p) ({                                                 \
+       struct nvkm_ltc_priv *_priv = (p);                                     \
+       _nvkm_ltc_dtor(nv_object(_priv));                                      \
+})
+#define nvkm_ltc_init(p) ({                                                    \
+       struct nvkm_ltc_priv *_priv = (p);                                     \
+       _nvkm_ltc_init(nv_object(_priv));                                      \
+})
+#define nvkm_ltc_fini(p,s) ({                                                  \
+       struct nvkm_ltc_priv *_priv = (p);                                     \
+       _nvkm_ltc_fini(nv_object(_priv), (s));                                 \
+})
+
+int  nvkm_ltc_create_(struct nvkm_object *, struct nvkm_object *,
+                     struct nvkm_oclass *, int, void **);
+
+#define _nvkm_ltc_dtor _nvkm_subdev_dtor
+int _nvkm_ltc_init(struct nvkm_object *);
+#define _nvkm_ltc_fini _nvkm_subdev_fini
+
+int  gf100_ltc_ctor(struct nvkm_object *, struct nvkm_object *,
+                   struct nvkm_oclass *, void *, u32,
+                   struct nvkm_object **);
+void gf100_ltc_dtor(struct nvkm_object *);
+int  gf100_ltc_init_tag_ram(struct nvkm_fb *, struct nvkm_ltc_priv *);
+int  gf100_ltc_tags_alloc(struct nvkm_ltc *, u32, struct nvkm_mm_node **);
+void gf100_ltc_tags_free(struct nvkm_ltc *, struct nvkm_mm_node **);
+
+struct nvkm_ltc_impl {
+       struct nvkm_oclass base;
+       void (*intr)(struct nvkm_subdev *);
+
+       void (*cbc_clear)(struct nvkm_ltc_priv *, u32 start, u32 limit);
+       void (*cbc_wait)(struct nvkm_ltc_priv *);
+
+       int zbc;
+       void (*zbc_clear_color)(struct nvkm_ltc_priv *, int, const u32[4]);
+       void (*zbc_clear_depth)(struct nvkm_ltc_priv *, int, const u32);
+};
+
+void gf100_ltc_intr(struct nvkm_subdev *);
+void gf100_ltc_cbc_clear(struct nvkm_ltc_priv *, u32, u32);
+void gf100_ltc_cbc_wait(struct nvkm_ltc_priv *);
+void gf100_ltc_zbc_clear_color(struct nvkm_ltc_priv *, int, const u32[4]);
+void gf100_ltc_zbc_clear_depth(struct nvkm_ltc_priv *, int, const u32);
+#endif
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/mc/Kbuild b/drivers/gpu/drm/nouveau/nvkm/subdev/mc/Kbuild
new file mode 100644 (file)
index 0000000..721643f
--- /dev/null
@@ -0,0 +1,11 @@
+nvkm-y += nvkm/subdev/mc/base.o
+nvkm-y += nvkm/subdev/mc/nv04.o
+nvkm-y += nvkm/subdev/mc/nv40.o
+nvkm-y += nvkm/subdev/mc/nv44.o
+nvkm-y += nvkm/subdev/mc/nv4c.o
+nvkm-y += nvkm/subdev/mc/nv50.o
+nvkm-y += nvkm/subdev/mc/g94.o
+nvkm-y += nvkm/subdev/mc/g98.o
+nvkm-y += nvkm/subdev/mc/gf100.o
+nvkm-y += nvkm/subdev/mc/gf106.o
+nvkm-y += nvkm/subdev/mc/gk20a.o
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/mc/base.c b/drivers/gpu/drm/nouveau/nvkm/subdev/mc/base.c
new file mode 100644 (file)
index 0000000..5b051a2
--- /dev/null
@@ -0,0 +1,169 @@
+/*
+ * Copyright 2012 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 "priv.h"
+
+#include <core/device.h>
+#include <core/option.h>
+
+static inline void
+nvkm_mc_unk260(struct nvkm_mc *pmc, u32 data)
+{
+       const struct nvkm_mc_oclass *impl = (void *)nv_oclass(pmc);
+       if (impl->unk260)
+               impl->unk260(pmc, data);
+}
+
+static inline u32
+nvkm_mc_intr_mask(struct nvkm_mc *pmc)
+{
+       u32 intr = nv_rd32(pmc, 0x000100);
+       if (intr == 0xffffffff) /* likely fallen off the bus */
+               intr = 0x00000000;
+       return intr;
+}
+
+static irqreturn_t
+nvkm_mc_intr(int irq, void *arg)
+{
+       struct nvkm_mc *pmc = arg;
+       const struct nvkm_mc_oclass *oclass = (void *)nv_object(pmc)->oclass;
+       const struct nvkm_mc_intr *map = oclass->intr;
+       struct nvkm_subdev *unit;
+       u32 intr;
+
+       nv_wr32(pmc, 0x000140, 0x00000000);
+       nv_rd32(pmc, 0x000140);
+       intr = nvkm_mc_intr_mask(pmc);
+       if (pmc->use_msi)
+               oclass->msi_rearm(pmc);
+
+       if (intr) {
+               u32 stat = intr = nvkm_mc_intr_mask(pmc);
+               while (map->stat) {
+                       if (intr & map->stat) {
+                               unit = nvkm_subdev(pmc, map->unit);
+                               if (unit && unit->intr)
+                                       unit->intr(unit);
+                               stat &= ~map->stat;
+                       }
+                       map++;
+               }
+
+               if (stat)
+                       nv_error(pmc, "unknown intr 0x%08x\n", stat);
+       }
+
+       nv_wr32(pmc, 0x000140, 0x00000001);
+       return intr ? IRQ_HANDLED : IRQ_NONE;
+}
+
+int
+_nvkm_mc_fini(struct nvkm_object *object, bool suspend)
+{
+       struct nvkm_mc *pmc = (void *)object;
+       nv_wr32(pmc, 0x000140, 0x00000000);
+       return nvkm_subdev_fini(&pmc->base, suspend);
+}
+
+int
+_nvkm_mc_init(struct nvkm_object *object)
+{
+       struct nvkm_mc *pmc = (void *)object;
+       int ret = nvkm_subdev_init(&pmc->base);
+       if (ret)
+               return ret;
+       nv_wr32(pmc, 0x000140, 0x00000001);
+       return 0;
+}
+
+void
+_nvkm_mc_dtor(struct nvkm_object *object)
+{
+       struct nvkm_device *device = nv_device(object);
+       struct nvkm_mc *pmc = (void *)object;
+       free_irq(pmc->irq, pmc);
+       if (pmc->use_msi)
+               pci_disable_msi(device->pdev);
+       nvkm_subdev_destroy(&pmc->base);
+}
+
+int
+nvkm_mc_create_(struct nvkm_object *parent, struct nvkm_object *engine,
+               struct nvkm_oclass *bclass, int length, void **pobject)
+{
+       const struct nvkm_mc_oclass *oclass = (void *)bclass;
+       struct nvkm_device *device = nv_device(parent);
+       struct nvkm_mc *pmc;
+       int ret;
+
+       ret = nvkm_subdev_create_(parent, engine, bclass, 0, "PMC",
+                                 "master", length, pobject);
+       pmc = *pobject;
+       if (ret)
+               return ret;
+
+       pmc->unk260 = nvkm_mc_unk260;
+
+       if (nv_device_is_pci(device)) {
+               switch (device->pdev->device & 0x0ff0) {
+               case 0x00f0:
+               case 0x02e0:
+                       /* BR02? NFI how these would be handled yet exactly */
+                       break;
+               default:
+                       switch (device->chipset) {
+                       case 0xaa:
+                               /* reported broken, nv also disable it */
+                               break;
+                       default:
+                               pmc->use_msi = true;
+                               break;
+                       }
+               }
+
+               pmc->use_msi = nvkm_boolopt(device->cfgopt, "NvMSI",
+                                           pmc->use_msi);
+
+               if (pmc->use_msi && oclass->msi_rearm) {
+                       pmc->use_msi = pci_enable_msi(device->pdev) == 0;
+                       if (pmc->use_msi) {
+                               nv_info(pmc, "MSI interrupts enabled\n");
+                               oclass->msi_rearm(pmc);
+                       }
+               } else {
+                       pmc->use_msi = false;
+               }
+       }
+
+       ret = nv_device_get_irq(device, true);
+       if (ret < 0)
+               return ret;
+       pmc->irq = ret;
+
+       ret = request_irq(pmc->irq, nvkm_mc_intr, IRQF_SHARED, "nvkm", pmc);
+       if (ret < 0)
+               return ret;
+
+       return 0;
+}
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/mc/g94.c b/drivers/gpu/drm/nouveau/nvkm/subdev/mc/g94.c
new file mode 100644 (file)
index 0000000..f042e7d
--- /dev/null
@@ -0,0 +1,37 @@
+/*
+ * Copyright 2012 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 "nv04.h"
+
+struct nvkm_oclass *
+g94_mc_oclass = &(struct nvkm_mc_oclass) {
+       .base.handle = NV_SUBDEV(MC, 0x94),
+       .base.ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = nv04_mc_ctor,
+               .dtor = _nvkm_mc_dtor,
+               .init = nv50_mc_init,
+               .fini = _nvkm_mc_fini,
+       },
+       .intr = nv50_mc_intr,
+       .msi_rearm = nv40_mc_msi_rearm,
+}.base;
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/mc/g98.c b/drivers/gpu/drm/nouveau/nvkm/subdev/mc/g98.c
new file mode 100644 (file)
index 0000000..8ab7f12
--- /dev/null
@@ -0,0 +1,58 @@
+/*
+ * Copyright 2012 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 "nv04.h"
+
+static const struct nvkm_mc_intr
+g98_mc_intr[] = {
+       { 0x04000000, NVDEV_ENGINE_DISP },  /* DISP first, so pageflip timestamps work */
+       { 0x00000001, NVDEV_ENGINE_MSPPP },
+       { 0x00000100, NVDEV_ENGINE_FIFO },
+       { 0x00001000, NVDEV_ENGINE_GR },
+       { 0x00004000, NVDEV_ENGINE_SEC },       /* NV84:NVA3 */
+       { 0x00008000, NVDEV_ENGINE_MSVLD },
+       { 0x00020000, NVDEV_ENGINE_MSPDEC },
+       { 0x00040000, NVDEV_SUBDEV_PMU },       /* NVA3:NVC0 */
+       { 0x00080000, NVDEV_SUBDEV_THERM },     /* NVA3:NVC0 */
+       { 0x00100000, NVDEV_SUBDEV_TIMER },
+       { 0x00200000, NVDEV_SUBDEV_GPIO },      /* PMGR->GPIO */
+       { 0x00200000, NVDEV_SUBDEV_I2C },       /* PMGR->I2C/AUX */
+       { 0x00400000, NVDEV_ENGINE_CE0 },       /* NVA3-     */
+       { 0x10000000, NVDEV_SUBDEV_BUS },
+       { 0x80000000, NVDEV_ENGINE_SW },
+       { 0x0042d101, NVDEV_SUBDEV_FB },
+       {},
+};
+
+struct nvkm_oclass *
+g98_mc_oclass = &(struct nvkm_mc_oclass) {
+       .base.handle = NV_SUBDEV(MC, 0x98),
+       .base.ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = nv04_mc_ctor,
+               .dtor = _nvkm_mc_dtor,
+               .init = nv50_mc_init,
+               .fini = _nvkm_mc_fini,
+       },
+       .intr = g98_mc_intr,
+       .msi_rearm = nv40_mc_msi_rearm,
+}.base;
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/mc/gf100.c b/drivers/gpu/drm/nouveau/nvkm/subdev/mc/gf100.c
new file mode 100644 (file)
index 0000000..2425984
--- /dev/null
@@ -0,0 +1,76 @@
+/*
+ * Copyright 2012 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 "nv04.h"
+
+const struct nvkm_mc_intr
+gf100_mc_intr[] = {
+       { 0x04000000, NVDEV_ENGINE_DISP },  /* DISP first, so pageflip timestamps work. */
+       { 0x00000001, NVDEV_ENGINE_MSPPP },
+       { 0x00000020, NVDEV_ENGINE_CE0 },
+       { 0x00000040, NVDEV_ENGINE_CE1 },
+       { 0x00000080, NVDEV_ENGINE_CE2 },
+       { 0x00000100, NVDEV_ENGINE_FIFO },
+       { 0x00001000, NVDEV_ENGINE_GR },
+       { 0x00002000, NVDEV_SUBDEV_FB },
+       { 0x00008000, NVDEV_ENGINE_MSVLD },
+       { 0x00040000, NVDEV_SUBDEV_THERM },
+       { 0x00020000, NVDEV_ENGINE_MSPDEC },
+       { 0x00100000, NVDEV_SUBDEV_TIMER },
+       { 0x00200000, NVDEV_SUBDEV_GPIO },      /* PMGR->GPIO */
+       { 0x00200000, NVDEV_SUBDEV_I2C },       /* PMGR->I2C/AUX */
+       { 0x01000000, NVDEV_SUBDEV_PMU },
+       { 0x02000000, NVDEV_SUBDEV_LTC },
+       { 0x08000000, NVDEV_SUBDEV_FB },
+       { 0x10000000, NVDEV_SUBDEV_BUS },
+       { 0x40000000, NVDEV_SUBDEV_IBUS },
+       { 0x80000000, NVDEV_ENGINE_SW },
+       {},
+};
+
+static void
+gf100_mc_msi_rearm(struct nvkm_mc *pmc)
+{
+       struct nv04_mc_priv *priv = (void *)pmc;
+       nv_wr32(priv, 0x088704, 0x00000000);
+}
+
+void
+gf100_mc_unk260(struct nvkm_mc *pmc, u32 data)
+{
+       nv_wr32(pmc, 0x000260, data);
+}
+
+struct nvkm_oclass *
+gf100_mc_oclass = &(struct nvkm_mc_oclass) {
+       .base.handle = NV_SUBDEV(MC, 0xc0),
+       .base.ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = nv04_mc_ctor,
+               .dtor = _nvkm_mc_dtor,
+               .init = nv50_mc_init,
+               .fini = _nvkm_mc_fini,
+       },
+       .intr = gf100_mc_intr,
+       .msi_rearm = gf100_mc_msi_rearm,
+       .unk260 = gf100_mc_unk260,
+}.base;
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/mc/gf106.c b/drivers/gpu/drm/nouveau/nvkm/subdev/mc/gf106.c
new file mode 100644 (file)
index 0000000..8d2a8f4
--- /dev/null
@@ -0,0 +1,38 @@
+/*
+ * Copyright 2012 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 "nv04.h"
+
+struct nvkm_oclass *
+gf106_mc_oclass = &(struct nvkm_mc_oclass) {
+       .base.handle = NV_SUBDEV(MC, 0xc3),
+       .base.ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = nv04_mc_ctor,
+               .dtor = _nvkm_mc_dtor,
+               .init = nv50_mc_init,
+               .fini = _nvkm_mc_fini,
+       },
+       .intr = gf100_mc_intr,
+       .msi_rearm = nv40_mc_msi_rearm,
+       .unk260 = gf100_mc_unk260,
+}.base;
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/mc/gk20a.c b/drivers/gpu/drm/nouveau/nvkm/subdev/mc/gk20a.c
new file mode 100644 (file)
index 0000000..43b2774
--- /dev/null
@@ -0,0 +1,37 @@
+/*
+ * Copyright 2012 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 "nv04.h"
+
+struct nvkm_oclass *
+gk20a_mc_oclass = &(struct nvkm_mc_oclass) {
+       .base.handle = NV_SUBDEV(MC, 0xea),
+       .base.ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = nv04_mc_ctor,
+               .dtor = _nvkm_mc_dtor,
+               .init = nv50_mc_init,
+               .fini = _nvkm_mc_fini,
+       },
+       .intr = gf100_mc_intr,
+       .msi_rearm = nv40_mc_msi_rearm,
+}.base;
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/mc/nv04.c b/drivers/gpu/drm/nouveau/nvkm/subdev/mc/nv04.c
new file mode 100644 (file)
index 0000000..3271382
--- /dev/null
@@ -0,0 +1,78 @@
+/*
+ * Copyright 2012 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 "nv04.h"
+
+const struct nvkm_mc_intr
+nv04_mc_intr[] = {
+       { 0x00000001, NVDEV_ENGINE_MPEG },      /* NV17- MPEG/ME */
+       { 0x00000100, NVDEV_ENGINE_FIFO },
+       { 0x00001000, NVDEV_ENGINE_GR },
+       { 0x00010000, NVDEV_ENGINE_DISP },
+       { 0x00020000, NVDEV_ENGINE_VP },        /* NV40- */
+       { 0x00100000, NVDEV_SUBDEV_TIMER },
+       { 0x01000000, NVDEV_ENGINE_DISP },      /* NV04- PCRTC0 */
+       { 0x02000000, NVDEV_ENGINE_DISP },      /* NV11- PCRTC1 */
+       { 0x10000000, NVDEV_SUBDEV_BUS },
+       { 0x80000000, NVDEV_ENGINE_SW },
+       {}
+};
+
+int
+nv04_mc_init(struct nvkm_object *object)
+{
+       struct nv04_mc_priv *priv = (void *)object;
+
+       nv_wr32(priv, 0x000200, 0xffffffff); /* everything enabled */
+       nv_wr32(priv, 0x001850, 0x00000001); /* disable rom access */
+
+       return nvkm_mc_init(&priv->base);
+}
+
+int
+nv04_mc_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+            struct nvkm_oclass *oclass, void *data, u32 size,
+            struct nvkm_object **pobject)
+{
+       struct nv04_mc_priv *priv;
+       int ret;
+
+       ret = nvkm_mc_create(parent, engine, oclass, &priv);
+       *pobject = nv_object(priv);
+       if (ret)
+               return ret;
+
+       return 0;
+}
+
+struct nvkm_oclass *
+nv04_mc_oclass = &(struct nvkm_mc_oclass) {
+       .base.handle = NV_SUBDEV(MC, 0x04),
+       .base.ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = nv04_mc_ctor,
+               .dtor = _nvkm_mc_dtor,
+               .init = nv04_mc_init,
+               .fini = _nvkm_mc_fini,
+       },
+       .intr = nv04_mc_intr,
+}.base;
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/mc/nv04.h b/drivers/gpu/drm/nouveau/nvkm/subdev/mc/nv04.h
new file mode 100644 (file)
index 0000000..411de3d
--- /dev/null
@@ -0,0 +1,20 @@
+#ifndef __NVKM_MC_NV04_H__
+#define __NVKM_MC_NV04_H__
+#include "priv.h"
+
+struct nv04_mc_priv {
+       struct nvkm_mc base;
+};
+
+int  nv04_mc_ctor(struct nvkm_object *, struct nvkm_object *,
+                 struct nvkm_oclass *, void *, u32,
+                 struct nvkm_object **);
+
+extern const struct nvkm_mc_intr nv04_mc_intr[];
+int  nv04_mc_init(struct nvkm_object *);
+void nv40_mc_msi_rearm(struct nvkm_mc *);
+int  nv44_mc_init(struct nvkm_object *object);
+int  nv50_mc_init(struct nvkm_object *);
+extern const struct nvkm_mc_intr nv50_mc_intr[];
+extern const struct nvkm_mc_intr gf100_mc_intr[];
+#endif
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/mc/nv40.c b/drivers/gpu/drm/nouveau/nvkm/subdev/mc/nv40.c
new file mode 100644 (file)
index 0000000..b761305
--- /dev/null
@@ -0,0 +1,44 @@
+/*
+ * Copyright 2012 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 "nv04.h"
+
+void
+nv40_mc_msi_rearm(struct nvkm_mc *pmc)
+{
+       struct nv04_mc_priv *priv = (void *)pmc;
+       nv_wr08(priv, 0x088068, 0xff);
+}
+
+struct nvkm_oclass *
+nv40_mc_oclass = &(struct nvkm_mc_oclass) {
+       .base.handle = NV_SUBDEV(MC, 0x40),
+       .base.ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = nv04_mc_ctor,
+               .dtor = _nvkm_mc_dtor,
+               .init = nv04_mc_init,
+               .fini = _nvkm_mc_fini,
+       },
+       .intr = nv04_mc_intr,
+       .msi_rearm = nv40_mc_msi_rearm,
+}.base;
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/mc/nv44.c b/drivers/gpu/drm/nouveau/nvkm/subdev/mc/nv44.c
new file mode 100644 (file)
index 0000000..2c7f7c7
--- /dev/null
@@ -0,0 +1,53 @@
+/*
+ * Copyright 2012 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 "nv04.h"
+
+int
+nv44_mc_init(struct nvkm_object *object)
+{
+       struct nv04_mc_priv *priv = (void *)object;
+       u32 tmp = nv_rd32(priv, 0x10020c);
+
+       nv_wr32(priv, 0x000200, 0xffffffff); /* everything enabled */
+
+       nv_wr32(priv, 0x001700, tmp);
+       nv_wr32(priv, 0x001704, 0);
+       nv_wr32(priv, 0x001708, 0);
+       nv_wr32(priv, 0x00170c, tmp);
+
+       return nvkm_mc_init(&priv->base);
+}
+
+struct nvkm_oclass *
+nv44_mc_oclass = &(struct nvkm_mc_oclass) {
+       .base.handle = NV_SUBDEV(MC, 0x44),
+       .base.ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = nv04_mc_ctor,
+               .dtor = _nvkm_mc_dtor,
+               .init = nv44_mc_init,
+               .fini = _nvkm_mc_fini,
+       },
+       .intr = nv04_mc_intr,
+       .msi_rearm = nv40_mc_msi_rearm,
+}.base;
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/mc/nv4c.c b/drivers/gpu/drm/nouveau/nvkm/subdev/mc/nv4c.c
new file mode 100644 (file)
index 0000000..c0aac7e
--- /dev/null
@@ -0,0 +1,36 @@
+/*
+ * Copyright 2014 Ilia Mirkin
+ *
+ * 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: Ilia Mirkin
+ */
+#include "nv04.h"
+
+struct nvkm_oclass *
+nv4c_mc_oclass = &(struct nvkm_mc_oclass) {
+       .base.handle = NV_SUBDEV(MC, 0x4c),
+       .base.ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = nv04_mc_ctor,
+               .dtor = _nvkm_mc_dtor,
+               .init = nv44_mc_init,
+               .fini = _nvkm_mc_fini,
+       },
+       .intr = nv04_mc_intr,
+}.base;
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/mc/nv50.c b/drivers/gpu/drm/nouveau/nvkm/subdev/mc/nv50.c
new file mode 100644 (file)
index 0000000..40e3019
--- /dev/null
@@ -0,0 +1,72 @@
+/*
+ * Copyright 2012 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 "nv04.h"
+
+#include <core/device.h>
+
+const struct nvkm_mc_intr
+nv50_mc_intr[] = {
+       { 0x04000000, NVDEV_ENGINE_DISP },  /* DISP before FIFO, so pageflip-timestamping works! */
+       { 0x00000001, NVDEV_ENGINE_MPEG },
+       { 0x00000100, NVDEV_ENGINE_FIFO },
+       { 0x00001000, NVDEV_ENGINE_GR },
+       { 0x00004000, NVDEV_ENGINE_CIPHER },    /* NV84- */
+       { 0x00008000, NVDEV_ENGINE_BSP },       /* NV84- */
+       { 0x00020000, NVDEV_ENGINE_VP },        /* NV84- */
+       { 0x00100000, NVDEV_SUBDEV_TIMER },
+       { 0x00200000, NVDEV_SUBDEV_GPIO },      /* PMGR->GPIO */
+       { 0x00200000, NVDEV_SUBDEV_I2C },       /* PMGR->I2C/AUX */
+       { 0x10000000, NVDEV_SUBDEV_BUS },
+       { 0x80000000, NVDEV_ENGINE_SW },
+       { 0x0002d101, NVDEV_SUBDEV_FB },
+       {},
+};
+
+static void
+nv50_mc_msi_rearm(struct nvkm_mc *pmc)
+{
+       struct nvkm_device *device = nv_device(pmc);
+       pci_write_config_byte(device->pdev, 0x68, 0xff);
+}
+
+int
+nv50_mc_init(struct nvkm_object *object)
+{
+       struct nv04_mc_priv *priv = (void *)object;
+       nv_wr32(priv, 0x000200, 0xffffffff); /* everything on */
+       return nvkm_mc_init(&priv->base);
+}
+
+struct nvkm_oclass *
+nv50_mc_oclass = &(struct nvkm_mc_oclass) {
+       .base.handle = NV_SUBDEV(MC, 0x50),
+       .base.ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = nv04_mc_ctor,
+               .dtor = _nvkm_mc_dtor,
+               .init = nv50_mc_init,
+               .fini = _nvkm_mc_fini,
+       },
+       .intr = nv50_mc_intr,
+       .msi_rearm = nv50_mc_msi_rearm,
+}.base;
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/mc/priv.h b/drivers/gpu/drm/nouveau/nvkm/subdev/mc/priv.h
new file mode 100644 (file)
index 0000000..d2cad07
--- /dev/null
@@ -0,0 +1,36 @@
+#ifndef __NVKM_MC_PRIV_H__
+#define __NVKM_MC_PRIV_H__
+#include <subdev/mc.h>
+
+#define nvkm_mc_create(p,e,o,d)                                             \
+       nvkm_mc_create_((p), (e), (o), sizeof(**d), (void **)d)
+#define nvkm_mc_destroy(p) ({                                               \
+       struct nvkm_mc *pmc = (p); _nvkm_mc_dtor(nv_object(pmc));        \
+})
+#define nvkm_mc_init(p) ({                                                  \
+       struct nvkm_mc *pmc = (p); _nvkm_mc_init(nv_object(pmc));        \
+})
+#define nvkm_mc_fini(p,s) ({                                                \
+       struct nvkm_mc *pmc = (p); _nvkm_mc_fini(nv_object(pmc), (s));   \
+})
+
+int  nvkm_mc_create_(struct nvkm_object *, struct nvkm_object *,
+                       struct nvkm_oclass *, int, void **);
+void _nvkm_mc_dtor(struct nvkm_object *);
+int  _nvkm_mc_init(struct nvkm_object *);
+int  _nvkm_mc_fini(struct nvkm_object *, bool);
+
+struct nvkm_mc_intr {
+       u32 stat;
+       u32 unit;
+};
+
+struct nvkm_mc_oclass {
+       struct nvkm_oclass base;
+       const struct nvkm_mc_intr *intr;
+       void (*msi_rearm)(struct nvkm_mc *);
+       void (*unk260)(struct nvkm_mc *, u32);
+};
+
+void gf100_mc_unk260(struct nvkm_mc *, u32);
+#endif
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/mmu/Kbuild b/drivers/gpu/drm/nouveau/nvkm/subdev/mmu/Kbuild
new file mode 100644 (file)
index 0000000..012c9db
--- /dev/null
@@ -0,0 +1,6 @@
+nvkm-y += nvkm/subdev/mmu/base.o
+nvkm-y += nvkm/subdev/mmu/nv04.o
+nvkm-y += nvkm/subdev/mmu/nv41.o
+nvkm-y += nvkm/subdev/mmu/nv44.o
+nvkm-y += nvkm/subdev/mmu/nv50.o
+nvkm-y += nvkm/subdev/mmu/gf100.o
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/mmu/base.c b/drivers/gpu/drm/nouveau/nvkm/subdev/mmu/base.c
new file mode 100644 (file)
index 0000000..277b6ec
--- /dev/null
@@ -0,0 +1,480 @@
+/*
+ * 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 <subdev/mmu.h>
+#include <subdev/fb.h>
+
+#include <core/gpuobj.h>
+
+void
+nvkm_vm_map_at(struct nvkm_vma *vma, u64 delta, struct nvkm_mem *node)
+{
+       struct nvkm_vm *vm = vma->vm;
+       struct nvkm_mmu *mmu = vm->mmu;
+       struct nvkm_mm_node *r;
+       int big = vma->node->type != mmu->spg_shift;
+       u32 offset = vma->node->offset + (delta >> 12);
+       u32 bits = vma->node->type - 12;
+       u32 pde  = (offset >> mmu->pgt_bits) - vm->fpde;
+       u32 pte  = (offset & ((1 << mmu->pgt_bits) - 1)) >> bits;
+       u32 max  = 1 << (mmu->pgt_bits - bits);
+       u32 end, len;
+
+       delta = 0;
+       list_for_each_entry(r, &node->regions, rl_entry) {
+               u64 phys = (u64)r->offset << 12;
+               u32 num  = r->length >> bits;
+
+               while (num) {
+                       struct nvkm_gpuobj *pgt = vm->pgt[pde].obj[big];
+
+                       end = (pte + num);
+                       if (unlikely(end >= max))
+                               end = max;
+                       len = end - pte;
+
+                       mmu->map(vma, pgt, node, pte, len, phys, delta);
+
+                       num -= len;
+                       pte += len;
+                       if (unlikely(end >= max)) {
+                               phys += len << (bits + 12);
+                               pde++;
+                               pte = 0;
+                       }
+
+                       delta += (u64)len << vma->node->type;
+               }
+       }
+
+       mmu->flush(vm);
+}
+
+static void
+nvkm_vm_map_sg_table(struct nvkm_vma *vma, u64 delta, u64 length,
+                    struct nvkm_mem *mem)
+{
+       struct nvkm_vm *vm = vma->vm;
+       struct nvkm_mmu *mmu = vm->mmu;
+       int big = vma->node->type != mmu->spg_shift;
+       u32 offset = vma->node->offset + (delta >> 12);
+       u32 bits = vma->node->type - 12;
+       u32 num  = length >> vma->node->type;
+       u32 pde  = (offset >> mmu->pgt_bits) - vm->fpde;
+       u32 pte  = (offset & ((1 << mmu->pgt_bits) - 1)) >> bits;
+       u32 max  = 1 << (mmu->pgt_bits - bits);
+       unsigned m, sglen;
+       u32 end, len;
+       int i;
+       struct scatterlist *sg;
+
+       for_each_sg(mem->sg->sgl, sg, mem->sg->nents, i) {
+               struct nvkm_gpuobj *pgt = vm->pgt[pde].obj[big];
+               sglen = sg_dma_len(sg) >> PAGE_SHIFT;
+
+               end = pte + sglen;
+               if (unlikely(end >= max))
+                       end = max;
+               len = end - pte;
+
+               for (m = 0; m < len; m++) {
+                       dma_addr_t addr = sg_dma_address(sg) + (m << PAGE_SHIFT);
+
+                       mmu->map_sg(vma, pgt, mem, pte, 1, &addr);
+                       num--;
+                       pte++;
+
+                       if (num == 0)
+                               goto finish;
+               }
+               if (unlikely(end >= max)) {
+                       pde++;
+                       pte = 0;
+               }
+               if (m < sglen) {
+                       for (; m < sglen; m++) {
+                               dma_addr_t addr = sg_dma_address(sg) + (m << PAGE_SHIFT);
+
+                               mmu->map_sg(vma, pgt, mem, pte, 1, &addr);
+                               num--;
+                               pte++;
+                               if (num == 0)
+                                       goto finish;
+                       }
+               }
+
+       }
+finish:
+       mmu->flush(vm);
+}
+
+static void
+nvkm_vm_map_sg(struct nvkm_vma *vma, u64 delta, u64 length,
+              struct nvkm_mem *mem)
+{
+       struct nvkm_vm *vm = vma->vm;
+       struct nvkm_mmu *mmu = vm->mmu;
+       dma_addr_t *list = mem->pages;
+       int big = vma->node->type != mmu->spg_shift;
+       u32 offset = vma->node->offset + (delta >> 12);
+       u32 bits = vma->node->type - 12;
+       u32 num  = length >> vma->node->type;
+       u32 pde  = (offset >> mmu->pgt_bits) - vm->fpde;
+       u32 pte  = (offset & ((1 << mmu->pgt_bits) - 1)) >> bits;
+       u32 max  = 1 << (mmu->pgt_bits - bits);
+       u32 end, len;
+
+       while (num) {
+               struct nvkm_gpuobj *pgt = vm->pgt[pde].obj[big];
+
+               end = (pte + num);
+               if (unlikely(end >= max))
+                       end = max;
+               len = end - pte;
+
+               mmu->map_sg(vma, pgt, mem, pte, len, list);
+
+               num  -= len;
+               pte  += len;
+               list += len;
+               if (unlikely(end >= max)) {
+                       pde++;
+                       pte = 0;
+               }
+       }
+
+       mmu->flush(vm);
+}
+
+void
+nvkm_vm_map(struct nvkm_vma *vma, struct nvkm_mem *node)
+{
+       if (node->sg)
+               nvkm_vm_map_sg_table(vma, 0, node->size << 12, node);
+       else
+       if (node->pages)
+               nvkm_vm_map_sg(vma, 0, node->size << 12, node);
+       else
+               nvkm_vm_map_at(vma, 0, node);
+}
+
+void
+nvkm_vm_unmap_at(struct nvkm_vma *vma, u64 delta, u64 length)
+{
+       struct nvkm_vm *vm = vma->vm;
+       struct nvkm_mmu *mmu = vm->mmu;
+       int big = vma->node->type != mmu->spg_shift;
+       u32 offset = vma->node->offset + (delta >> 12);
+       u32 bits = vma->node->type - 12;
+       u32 num  = length >> vma->node->type;
+       u32 pde  = (offset >> mmu->pgt_bits) - vm->fpde;
+       u32 pte  = (offset & ((1 << mmu->pgt_bits) - 1)) >> bits;
+       u32 max  = 1 << (mmu->pgt_bits - bits);
+       u32 end, len;
+
+       while (num) {
+               struct nvkm_gpuobj *pgt = vm->pgt[pde].obj[big];
+
+               end = (pte + num);
+               if (unlikely(end >= max))
+                       end = max;
+               len = end - pte;
+
+               mmu->unmap(pgt, pte, len);
+
+               num -= len;
+               pte += len;
+               if (unlikely(end >= max)) {
+                       pde++;
+                       pte = 0;
+               }
+       }
+
+       mmu->flush(vm);
+}
+
+void
+nvkm_vm_unmap(struct nvkm_vma *vma)
+{
+       nvkm_vm_unmap_at(vma, 0, (u64)vma->node->length << 12);
+}
+
+static void
+nvkm_vm_unmap_pgt(struct nvkm_vm *vm, int big, u32 fpde, u32 lpde)
+{
+       struct nvkm_mmu *mmu = vm->mmu;
+       struct nvkm_vm_pgd *vpgd;
+       struct nvkm_vm_pgt *vpgt;
+       struct nvkm_gpuobj *pgt;
+       u32 pde;
+
+       for (pde = fpde; pde <= lpde; pde++) {
+               vpgt = &vm->pgt[pde - vm->fpde];
+               if (--vpgt->refcount[big])
+                       continue;
+
+               pgt = vpgt->obj[big];
+               vpgt->obj[big] = NULL;
+
+               list_for_each_entry(vpgd, &vm->pgd_list, head) {
+                       mmu->map_pgt(vpgd->obj, pde, vpgt->obj);
+               }
+
+               mutex_unlock(&nv_subdev(mmu)->mutex);
+               nvkm_gpuobj_ref(NULL, &pgt);
+               mutex_lock(&nv_subdev(mmu)->mutex);
+       }
+}
+
+static int
+nvkm_vm_map_pgt(struct nvkm_vm *vm, u32 pde, u32 type)
+{
+       struct nvkm_mmu *mmu = vm->mmu;
+       struct nvkm_vm_pgt *vpgt = &vm->pgt[pde - vm->fpde];
+       struct nvkm_vm_pgd *vpgd;
+       struct nvkm_gpuobj *pgt;
+       int big = (type != mmu->spg_shift);
+       u32 pgt_size;
+       int ret;
+
+       pgt_size  = (1 << (mmu->pgt_bits + 12)) >> type;
+       pgt_size *= 8;
+
+       mutex_unlock(&nv_subdev(mmu)->mutex);
+       ret = nvkm_gpuobj_new(nv_object(vm->mmu), NULL, pgt_size, 0x1000,
+                             NVOBJ_FLAG_ZERO_ALLOC, &pgt);
+       mutex_lock(&nv_subdev(mmu)->mutex);
+       if (unlikely(ret))
+               return ret;
+
+       /* someone beat us to filling the PDE while we didn't have the lock */
+       if (unlikely(vpgt->refcount[big]++)) {
+               mutex_unlock(&nv_subdev(mmu)->mutex);
+               nvkm_gpuobj_ref(NULL, &pgt);
+               mutex_lock(&nv_subdev(mmu)->mutex);
+               return 0;
+       }
+
+       vpgt->obj[big] = pgt;
+       list_for_each_entry(vpgd, &vm->pgd_list, head) {
+               mmu->map_pgt(vpgd->obj, pde, vpgt->obj);
+       }
+
+       return 0;
+}
+
+int
+nvkm_vm_get(struct nvkm_vm *vm, u64 size, u32 page_shift, u32 access,
+           struct nvkm_vma *vma)
+{
+       struct nvkm_mmu *mmu = vm->mmu;
+       u32 align = (1 << page_shift) >> 12;
+       u32 msize = size >> 12;
+       u32 fpde, lpde, pde;
+       int ret;
+
+       mutex_lock(&nv_subdev(mmu)->mutex);
+       ret = nvkm_mm_head(&vm->mm, 0, page_shift, msize, msize, align,
+                          &vma->node);
+       if (unlikely(ret != 0)) {
+               mutex_unlock(&nv_subdev(mmu)->mutex);
+               return ret;
+       }
+
+       fpde = (vma->node->offset >> mmu->pgt_bits);
+       lpde = (vma->node->offset + vma->node->length - 1) >> mmu->pgt_bits;
+
+       for (pde = fpde; pde <= lpde; pde++) {
+               struct nvkm_vm_pgt *vpgt = &vm->pgt[pde - vm->fpde];
+               int big = (vma->node->type != mmu->spg_shift);
+
+               if (likely(vpgt->refcount[big])) {
+                       vpgt->refcount[big]++;
+                       continue;
+               }
+
+               ret = nvkm_vm_map_pgt(vm, pde, vma->node->type);
+               if (ret) {
+                       if (pde != fpde)
+                               nvkm_vm_unmap_pgt(vm, big, fpde, pde - 1);
+                       nvkm_mm_free(&vm->mm, &vma->node);
+                       mutex_unlock(&nv_subdev(mmu)->mutex);
+                       return ret;
+               }
+       }
+       mutex_unlock(&nv_subdev(mmu)->mutex);
+
+       vma->vm = NULL;
+       nvkm_vm_ref(vm, &vma->vm, NULL);
+       vma->offset = (u64)vma->node->offset << 12;
+       vma->access = access;
+       return 0;
+}
+
+void
+nvkm_vm_put(struct nvkm_vma *vma)
+{
+       struct nvkm_vm *vm = vma->vm;
+       struct nvkm_mmu *mmu = vm->mmu;
+       u32 fpde, lpde;
+
+       if (unlikely(vma->node == NULL))
+               return;
+       fpde = (vma->node->offset >> mmu->pgt_bits);
+       lpde = (vma->node->offset + vma->node->length - 1) >> mmu->pgt_bits;
+
+       mutex_lock(&nv_subdev(mmu)->mutex);
+       nvkm_vm_unmap_pgt(vm, vma->node->type != mmu->spg_shift, fpde, lpde);
+       nvkm_mm_free(&vm->mm, &vma->node);
+       mutex_unlock(&nv_subdev(mmu)->mutex);
+
+       nvkm_vm_ref(NULL, &vma->vm, NULL);
+}
+
+int
+nvkm_vm_create(struct nvkm_mmu *mmu, u64 offset, u64 length, u64 mm_offset,
+              u32 block, struct nvkm_vm **pvm)
+{
+       struct nvkm_vm *vm;
+       u64 mm_length = (offset + length) - mm_offset;
+       int ret;
+
+       vm = kzalloc(sizeof(*vm), GFP_KERNEL);
+       if (!vm)
+               return -ENOMEM;
+
+       INIT_LIST_HEAD(&vm->pgd_list);
+       vm->mmu = mmu;
+       kref_init(&vm->refcount);
+       vm->fpde = offset >> (mmu->pgt_bits + 12);
+       vm->lpde = (offset + length - 1) >> (mmu->pgt_bits + 12);
+
+       vm->pgt  = vzalloc((vm->lpde - vm->fpde + 1) * sizeof(*vm->pgt));
+       if (!vm->pgt) {
+               kfree(vm);
+               return -ENOMEM;
+       }
+
+       ret = nvkm_mm_init(&vm->mm, mm_offset >> 12, mm_length >> 12,
+                          block >> 12);
+       if (ret) {
+               vfree(vm->pgt);
+               kfree(vm);
+               return ret;
+       }
+
+       *pvm = vm;
+
+       return 0;
+}
+
+int
+nvkm_vm_new(struct nvkm_device *device, u64 offset, u64 length, u64 mm_offset,
+           struct nvkm_vm **pvm)
+{
+       struct nvkm_mmu *mmu = nvkm_mmu(device);
+       return mmu->create(mmu, offset, length, mm_offset, pvm);
+}
+
+static int
+nvkm_vm_link(struct nvkm_vm *vm, struct nvkm_gpuobj *pgd)
+{
+       struct nvkm_mmu *mmu = vm->mmu;
+       struct nvkm_vm_pgd *vpgd;
+       int i;
+
+       if (!pgd)
+               return 0;
+
+       vpgd = kzalloc(sizeof(*vpgd), GFP_KERNEL);
+       if (!vpgd)
+               return -ENOMEM;
+
+       nvkm_gpuobj_ref(pgd, &vpgd->obj);
+
+       mutex_lock(&nv_subdev(mmu)->mutex);
+       for (i = vm->fpde; i <= vm->lpde; i++)
+               mmu->map_pgt(pgd, i, vm->pgt[i - vm->fpde].obj);
+       list_add(&vpgd->head, &vm->pgd_list);
+       mutex_unlock(&nv_subdev(mmu)->mutex);
+       return 0;
+}
+
+static void
+nvkm_vm_unlink(struct nvkm_vm *vm, struct nvkm_gpuobj *mpgd)
+{
+       struct nvkm_mmu *mmu = vm->mmu;
+       struct nvkm_vm_pgd *vpgd, *tmp;
+       struct nvkm_gpuobj *pgd = NULL;
+
+       if (!mpgd)
+               return;
+
+       mutex_lock(&nv_subdev(mmu)->mutex);
+       list_for_each_entry_safe(vpgd, tmp, &vm->pgd_list, head) {
+               if (vpgd->obj == mpgd) {
+                       pgd = vpgd->obj;
+                       list_del(&vpgd->head);
+                       kfree(vpgd);
+                       break;
+               }
+       }
+       mutex_unlock(&nv_subdev(mmu)->mutex);
+
+       nvkm_gpuobj_ref(NULL, &pgd);
+}
+
+static void
+nvkm_vm_del(struct kref *kref)
+{
+       struct nvkm_vm *vm = container_of(kref, typeof(*vm), refcount);
+       struct nvkm_vm_pgd *vpgd, *tmp;
+
+       list_for_each_entry_safe(vpgd, tmp, &vm->pgd_list, head) {
+               nvkm_vm_unlink(vm, vpgd->obj);
+       }
+
+       nvkm_mm_fini(&vm->mm);
+       vfree(vm->pgt);
+       kfree(vm);
+}
+
+int
+nvkm_vm_ref(struct nvkm_vm *ref, struct nvkm_vm **ptr, struct nvkm_gpuobj *pgd)
+{
+       if (ref) {
+               int ret = nvkm_vm_link(ref, pgd);
+               if (ret)
+                       return ret;
+
+               kref_get(&ref->refcount);
+       }
+
+       if (*ptr) {
+               nvkm_vm_unlink(*ptr, pgd);
+               kref_put(&(*ptr)->refcount, nvkm_vm_del);
+       }
+
+       *ptr = ref;
+       return 0;
+}
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/mmu/gf100.c b/drivers/gpu/drm/nouveau/nvkm/subdev/mmu/gf100.c
new file mode 100644 (file)
index 0000000..294cda3
--- /dev/null
@@ -0,0 +1,237 @@
+/*
+ * 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 <subdev/mmu.h>
+#include <subdev/bar.h>
+#include <subdev/fb.h>
+#include <subdev/ltc.h>
+#include <subdev/timer.h>
+
+#include <core/gpuobj.h>
+
+struct gf100_mmu_priv {
+       struct nvkm_mmu base;
+};
+
+
+/* Map from compressed to corresponding uncompressed storage type.
+ * The value 0xff represents an invalid storage type.
+ */
+const u8 gf100_pte_storage_type_map[256] =
+{
+       0x00, 0x01, 0x01, 0x01, 0x01, 0x01, 0xff, 0x01, /* 0x00 */
+       0x01, 0x01, 0x01, 0xff, 0xff, 0xff, 0xff, 0xff,
+       0xff, 0x11, 0xff, 0xff, 0xff, 0xff, 0xff, 0x11, /* 0x10 */
+       0x11, 0x11, 0x11, 0xff, 0xff, 0xff, 0xff, 0xff,
+       0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0x26, 0x27, /* 0x20 */
+       0x28, 0x29, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
+       0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, /* 0x30 */
+       0xff, 0xff, 0x26, 0x27, 0x28, 0x29, 0x26, 0x27,
+       0x28, 0x29, 0xff, 0xff, 0xff, 0xff, 0x46, 0xff, /* 0x40 */
+       0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
+       0xff, 0x46, 0x46, 0x46, 0x46, 0xff, 0xff, 0xff, /* 0x50 */
+       0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
+       0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, /* 0x60 */
+       0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
+       0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, /* 0x70 */
+       0xff, 0xff, 0xff, 0x7b, 0xff, 0xff, 0xff, 0xff,
+       0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0x7b, 0x7b, /* 0x80 */
+       0x7b, 0x7b, 0xff, 0x8b, 0x8c, 0x8d, 0x8e, 0xff,
+       0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, /* 0x90 */
+       0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
+       0xff, 0xff, 0xff, 0x8b, 0x8c, 0x8d, 0x8e, 0xa7, /* 0xa0 */
+       0xa8, 0xa9, 0xaa, 0xff, 0xff, 0xff, 0xff, 0xff,
+       0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, /* 0xb0 */
+       0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xa7,
+       0xa8, 0xa9, 0xaa, 0xc3, 0xff, 0xff, 0xff, 0xff, /* 0xc0 */
+       0xff, 0xff, 0xff, 0xff, 0xfe, 0xfe, 0xc3, 0xc3,
+       0xc3, 0xc3, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, /* 0xd0 */
+       0xfe, 0xff, 0xff, 0xfe, 0xff, 0xfe, 0xff, 0xfe,
+       0xfe, 0xff, 0xfe, 0xfe, 0xfe, 0xfe, 0xfe, 0xff, /* 0xe0 */
+       0xff, 0xfe, 0xff, 0xfe, 0xff, 0xfe, 0xfe, 0xff,
+       0xfe, 0xfe, 0xfe, 0xfe, 0xfe, 0xfe, 0xfe, 0xfe, /* 0xf0 */
+       0xfe, 0xfe, 0xfe, 0xfe, 0xff, 0xfd, 0xfe, 0xff
+};
+
+
+static void
+gf100_vm_map_pgt(struct nvkm_gpuobj *pgd, u32 index, struct nvkm_gpuobj *pgt[2])
+{
+       u32 pde[2] = { 0, 0 };
+
+       if (pgt[0])
+               pde[1] = 0x00000001 | (pgt[0]->addr >> 8);
+       if (pgt[1])
+               pde[0] = 0x00000001 | (pgt[1]->addr >> 8);
+
+       nv_wo32(pgd, (index * 8) + 0, pde[0]);
+       nv_wo32(pgd, (index * 8) + 4, pde[1]);
+}
+
+static inline u64
+gf100_vm_addr(struct nvkm_vma *vma, u64 phys, u32 memtype, u32 target)
+{
+       phys >>= 8;
+
+       phys |= 0x00000001; /* present */
+       if (vma->access & NV_MEM_ACCESS_SYS)
+               phys |= 0x00000002;
+
+       phys |= ((u64)target  << 32);
+       phys |= ((u64)memtype << 36);
+       return phys;
+}
+
+static void
+gf100_vm_map(struct nvkm_vma *vma, struct nvkm_gpuobj *pgt,
+            struct nvkm_mem *mem, u32 pte, u32 cnt, u64 phys, u64 delta)
+{
+       u64 next = 1 << (vma->node->type - 8);
+
+       phys  = gf100_vm_addr(vma, phys, mem->memtype, 0);
+       pte <<= 3;
+
+       if (mem->tag) {
+               struct nvkm_ltc *ltc = nvkm_ltc(vma->vm->mmu);
+               u32 tag = mem->tag->offset + (delta >> 17);
+               phys |= (u64)tag << (32 + 12);
+               next |= (u64)1   << (32 + 12);
+               ltc->tags_clear(ltc, tag, cnt);
+       }
+
+       while (cnt--) {
+               nv_wo32(pgt, pte + 0, lower_32_bits(phys));
+               nv_wo32(pgt, pte + 4, upper_32_bits(phys));
+               phys += next;
+               pte  += 8;
+       }
+}
+
+static void
+gf100_vm_map_sg(struct nvkm_vma *vma, struct nvkm_gpuobj *pgt,
+               struct nvkm_mem *mem, u32 pte, u32 cnt, dma_addr_t *list)
+{
+       u32 target = (vma->access & NV_MEM_ACCESS_NOSNOOP) ? 7 : 5;
+       /* compressed storage types are invalid for system memory */
+       u32 memtype = gf100_pte_storage_type_map[mem->memtype & 0xff];
+
+       pte <<= 3;
+       while (cnt--) {
+               u64 phys = gf100_vm_addr(vma, *list++, memtype, target);
+               nv_wo32(pgt, pte + 0, lower_32_bits(phys));
+               nv_wo32(pgt, pte + 4, upper_32_bits(phys));
+               pte += 8;
+       }
+}
+
+static void
+gf100_vm_unmap(struct nvkm_gpuobj *pgt, u32 pte, u32 cnt)
+{
+       pte <<= 3;
+       while (cnt--) {
+               nv_wo32(pgt, pte + 0, 0x00000000);
+               nv_wo32(pgt, pte + 4, 0x00000000);
+               pte += 8;
+       }
+}
+
+static void
+gf100_vm_flush(struct nvkm_vm *vm)
+{
+       struct gf100_mmu_priv *priv = (void *)vm->mmu;
+       struct nvkm_bar *bar = nvkm_bar(priv);
+       struct nvkm_vm_pgd *vpgd;
+       u32 type;
+
+       bar->flush(bar);
+
+       type = 0x00000001; /* PAGE_ALL */
+       if (atomic_read(&vm->engref[NVDEV_SUBDEV_BAR]))
+               type |= 0x00000004; /* HUB_ONLY */
+
+       mutex_lock(&nv_subdev(priv)->mutex);
+       list_for_each_entry(vpgd, &vm->pgd_list, head) {
+               /* looks like maybe a "free flush slots" counter, the
+                * faster you write to 0x100cbc to more it decreases
+                */
+               if (!nv_wait_ne(priv, 0x100c80, 0x00ff0000, 0x00000000)) {
+                       nv_error(priv, "vm timeout 0: 0x%08x %d\n",
+                                nv_rd32(priv, 0x100c80), type);
+               }
+
+               nv_wr32(priv, 0x100cb8, vpgd->obj->addr >> 8);
+               nv_wr32(priv, 0x100cbc, 0x80000000 | type);
+
+               /* wait for flush to be queued? */
+               if (!nv_wait(priv, 0x100c80, 0x00008000, 0x00008000)) {
+                       nv_error(priv, "vm timeout 1: 0x%08x %d\n",
+                                nv_rd32(priv, 0x100c80), type);
+               }
+       }
+       mutex_unlock(&nv_subdev(priv)->mutex);
+}
+
+static int
+gf100_vm_create(struct nvkm_mmu *mmu, u64 offset, u64 length, u64 mm_offset,
+               struct nvkm_vm **pvm)
+{
+       return nvkm_vm_create(mmu, offset, length, mm_offset, 4096, pvm);
+}
+
+static int
+gf100_mmu_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+              struct nvkm_oclass *oclass, void *data, u32 size,
+              struct nvkm_object **pobject)
+{
+       struct gf100_mmu_priv *priv;
+       int ret;
+
+       ret = nvkm_mmu_create(parent, engine, oclass, "VM", "vm", &priv);
+       *pobject = nv_object(priv);
+       if (ret)
+               return ret;
+
+       priv->base.limit = 1ULL << 40;
+       priv->base.dma_bits = 40;
+       priv->base.pgt_bits  = 27 - 12;
+       priv->base.spg_shift = 12;
+       priv->base.lpg_shift = 17;
+       priv->base.create = gf100_vm_create;
+       priv->base.map_pgt = gf100_vm_map_pgt;
+       priv->base.map = gf100_vm_map;
+       priv->base.map_sg = gf100_vm_map_sg;
+       priv->base.unmap = gf100_vm_unmap;
+       priv->base.flush = gf100_vm_flush;
+       return 0;
+}
+
+struct nvkm_oclass
+gf100_mmu_oclass = {
+       .handle = NV_SUBDEV(MMU, 0xc0),
+       .ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = gf100_mmu_ctor,
+               .dtor = _nvkm_mmu_dtor,
+               .init = _nvkm_mmu_init,
+               .fini = _nvkm_mmu_fini,
+       },
+};
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/mmu/nv04.c b/drivers/gpu/drm/nouveau/nvkm/subdev/mmu/nv04.c
new file mode 100644 (file)
index 0000000..fe93ea2
--- /dev/null
@@ -0,0 +1,151 @@
+/*
+ * Copyright 2012 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 "nv04.h"
+
+#include <core/device.h>
+#include <core/gpuobj.h>
+
+#define NV04_PDMA_SIZE (128 * 1024 * 1024)
+#define NV04_PDMA_PAGE (  4 * 1024)
+
+/*******************************************************************************
+ * VM map/unmap callbacks
+ ******************************************************************************/
+
+static void
+nv04_vm_map_sg(struct nvkm_vma *vma, struct nvkm_gpuobj *pgt,
+              struct nvkm_mem *mem, u32 pte, u32 cnt, dma_addr_t *list)
+{
+       pte = 0x00008 + (pte * 4);
+       while (cnt) {
+               u32 page = PAGE_SIZE / NV04_PDMA_PAGE;
+               u32 phys = (u32)*list++;
+               while (cnt && page--) {
+                       nv_wo32(pgt, pte, phys | 3);
+                       phys += NV04_PDMA_PAGE;
+                       pte += 4;
+                       cnt -= 1;
+               }
+       }
+}
+
+static void
+nv04_vm_unmap(struct nvkm_gpuobj *pgt, u32 pte, u32 cnt)
+{
+       pte = 0x00008 + (pte * 4);
+       while (cnt--) {
+               nv_wo32(pgt, pte, 0x00000000);
+               pte += 4;
+       }
+}
+
+static void
+nv04_vm_flush(struct nvkm_vm *vm)
+{
+}
+
+/*******************************************************************************
+ * VM object
+ ******************************************************************************/
+
+int
+nv04_vm_create(struct nvkm_mmu *mmu, u64 offset, u64 length, u64 mmstart,
+              struct nvkm_vm **pvm)
+{
+       return -EINVAL;
+}
+
+/*******************************************************************************
+ * MMU subdev
+ ******************************************************************************/
+
+static int
+nv04_mmu_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+             struct nvkm_oclass *oclass, void *data, u32 size,
+             struct nvkm_object **pobject)
+{
+       struct nv04_mmu_priv *priv;
+       struct nvkm_gpuobj *dma;
+       int ret;
+
+       ret = nvkm_mmu_create(parent, engine, oclass, "PCIGART",
+                             "pcigart", &priv);
+       *pobject = nv_object(priv);
+       if (ret)
+               return ret;
+
+       priv->base.create = nv04_vm_create;
+       priv->base.limit = NV04_PDMA_SIZE;
+       priv->base.dma_bits = 32;
+       priv->base.pgt_bits = 32 - 12;
+       priv->base.spg_shift = 12;
+       priv->base.lpg_shift = 12;
+       priv->base.map_sg = nv04_vm_map_sg;
+       priv->base.unmap = nv04_vm_unmap;
+       priv->base.flush = nv04_vm_flush;
+
+       ret = nvkm_vm_create(&priv->base, 0, NV04_PDMA_SIZE, 0, 4096,
+                            &priv->vm);
+       if (ret)
+               return ret;
+
+       ret = nvkm_gpuobj_new(nv_object(priv), NULL,
+                             (NV04_PDMA_SIZE / NV04_PDMA_PAGE) * 4 + 8,
+                             16, NVOBJ_FLAG_ZERO_ALLOC,
+                             &priv->vm->pgt[0].obj[0]);
+       dma = priv->vm->pgt[0].obj[0];
+       priv->vm->pgt[0].refcount[0] = 1;
+       if (ret)
+               return ret;
+
+       nv_wo32(dma, 0x00000, 0x0002103d); /* PCI, RW, PT, !LN */
+       nv_wo32(dma, 0x00004, NV04_PDMA_SIZE - 1);
+       return 0;
+}
+
+void
+nv04_mmu_dtor(struct nvkm_object *object)
+{
+       struct nv04_mmu_priv *priv = (void *)object;
+       if (priv->vm) {
+               nvkm_gpuobj_ref(NULL, &priv->vm->pgt[0].obj[0]);
+               nvkm_vm_ref(NULL, &priv->vm, NULL);
+       }
+       if (priv->nullp) {
+               pci_free_consistent(nv_device(priv)->pdev, 16 * 1024,
+                                   priv->nullp, priv->null);
+       }
+       nvkm_mmu_destroy(&priv->base);
+}
+
+struct nvkm_oclass
+nv04_mmu_oclass = {
+       .handle = NV_SUBDEV(MMU, 0x04),
+       .ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = nv04_mmu_ctor,
+               .dtor = nv04_mmu_dtor,
+               .init = _nvkm_mmu_init,
+               .fini = _nvkm_mmu_fini,
+       },
+};
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/mmu/nv04.h b/drivers/gpu/drm/nouveau/nvkm/subdev/mmu/nv04.h
new file mode 100644 (file)
index 0000000..7bf6f4b
--- /dev/null
@@ -0,0 +1,19 @@
+#ifndef __NV04_MMU_PRIV__
+#define __NV04_MMU_PRIV__
+
+#include <subdev/mmu.h>
+
+struct nv04_mmu_priv {
+       struct nvkm_mmu base;
+       struct nvkm_vm *vm;
+       dma_addr_t null;
+       void *nullp;
+};
+
+static inline struct nv04_mmu_priv *
+nv04_mmu(void *obj)
+{
+       return (void *)nvkm_mmu(obj);
+}
+
+#endif
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/mmu/nv41.c b/drivers/gpu/drm/nouveau/nvkm/subdev/mmu/nv41.c
new file mode 100644 (file)
index 0000000..61ee3ab
--- /dev/null
@@ -0,0 +1,157 @@
+/*
+ * Copyright 2012 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 "nv04.h"
+
+#include <core/device.h>
+#include <core/gpuobj.h>
+#include <core/option.h>
+#include <subdev/timer.h>
+
+#define NV41_GART_SIZE (512 * 1024 * 1024)
+#define NV41_GART_PAGE (  4 * 1024)
+
+/*******************************************************************************
+ * VM map/unmap callbacks
+ ******************************************************************************/
+
+static void
+nv41_vm_map_sg(struct nvkm_vma *vma, struct nvkm_gpuobj *pgt,
+              struct nvkm_mem *mem, u32 pte, u32 cnt, dma_addr_t *list)
+{
+       pte = pte * 4;
+       while (cnt) {
+               u32 page = PAGE_SIZE / NV41_GART_PAGE;
+               u64 phys = (u64)*list++;
+               while (cnt && page--) {
+                       nv_wo32(pgt, pte, (phys >> 7) | 1);
+                       phys += NV41_GART_PAGE;
+                       pte += 4;
+                       cnt -= 1;
+               }
+       }
+}
+
+static void
+nv41_vm_unmap(struct nvkm_gpuobj *pgt, u32 pte, u32 cnt)
+{
+       pte = pte * 4;
+       while (cnt--) {
+               nv_wo32(pgt, pte, 0x00000000);
+               pte += 4;
+       }
+}
+
+static void
+nv41_vm_flush(struct nvkm_vm *vm)
+{
+       struct nv04_mmu_priv *priv = (void *)vm->mmu;
+
+       mutex_lock(&nv_subdev(priv)->mutex);
+       nv_wr32(priv, 0x100810, 0x00000022);
+       if (!nv_wait(priv, 0x100810, 0x00000020, 0x00000020)) {
+               nv_warn(priv, "flush timeout, 0x%08x\n",
+                       nv_rd32(priv, 0x100810));
+       }
+       nv_wr32(priv, 0x100810, 0x00000000);
+       mutex_unlock(&nv_subdev(priv)->mutex);
+}
+
+/*******************************************************************************
+ * MMU subdev
+ ******************************************************************************/
+
+static int
+nv41_mmu_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+             struct nvkm_oclass *oclass, void *data, u32 size,
+             struct nvkm_object **pobject)
+{
+       struct nvkm_device *device = nv_device(parent);
+       struct nv04_mmu_priv *priv;
+       int ret;
+
+       if (pci_find_capability(device->pdev, PCI_CAP_ID_AGP) ||
+           !nvkm_boolopt(device->cfgopt, "NvPCIE", true)) {
+               return nvkm_object_ctor(parent, engine, &nv04_mmu_oclass,
+                                       data, size, pobject);
+       }
+
+       ret = nvkm_mmu_create(parent, engine, oclass, "PCIEGART",
+                             "pciegart", &priv);
+       *pobject = nv_object(priv);
+       if (ret)
+               return ret;
+
+       priv->base.create = nv04_vm_create;
+       priv->base.limit = NV41_GART_SIZE;
+       priv->base.dma_bits = 39;
+       priv->base.pgt_bits = 32 - 12;
+       priv->base.spg_shift = 12;
+       priv->base.lpg_shift = 12;
+       priv->base.map_sg = nv41_vm_map_sg;
+       priv->base.unmap = nv41_vm_unmap;
+       priv->base.flush = nv41_vm_flush;
+
+       ret = nvkm_vm_create(&priv->base, 0, NV41_GART_SIZE, 0, 4096,
+                            &priv->vm);
+       if (ret)
+               return ret;
+
+       ret = nvkm_gpuobj_new(nv_object(priv), NULL,
+                             (NV41_GART_SIZE / NV41_GART_PAGE) * 4, 16,
+                             NVOBJ_FLAG_ZERO_ALLOC,
+                             &priv->vm->pgt[0].obj[0]);
+       priv->vm->pgt[0].refcount[0] = 1;
+       if (ret)
+               return ret;
+
+       return 0;
+}
+
+static int
+nv41_mmu_init(struct nvkm_object *object)
+{
+       struct nv04_mmu_priv *priv = (void *)object;
+       struct nvkm_gpuobj *dma = priv->vm->pgt[0].obj[0];
+       int ret;
+
+       ret = nvkm_mmu_init(&priv->base);
+       if (ret)
+               return ret;
+
+       nv_wr32(priv, 0x100800, dma->addr | 0x00000002);
+       nv_mask(priv, 0x10008c, 0x00000100, 0x00000100);
+       nv_wr32(priv, 0x100820, 0x00000000);
+       return 0;
+}
+
+struct nvkm_oclass
+nv41_mmu_oclass = {
+       .handle = NV_SUBDEV(MMU, 0x41),
+       .ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = nv41_mmu_ctor,
+               .dtor = nv04_mmu_dtor,
+               .init = nv41_mmu_init,
+               .fini = _nvkm_mmu_fini,
+       },
+};
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/mmu/nv44.c b/drivers/gpu/drm/nouveau/nvkm/subdev/mmu/nv44.c
new file mode 100644 (file)
index 0000000..b90ded1
--- /dev/null
@@ -0,0 +1,247 @@
+/*
+ * Copyright 2012 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 "nv04.h"
+
+#include <core/device.h>
+#include <core/gpuobj.h>
+#include <core/option.h>
+#include <subdev/timer.h>
+
+#define NV44_GART_SIZE (512 * 1024 * 1024)
+#define NV44_GART_PAGE (  4 * 1024)
+
+/*******************************************************************************
+ * VM map/unmap callbacks
+ ******************************************************************************/
+
+static void
+nv44_vm_fill(struct nvkm_gpuobj *pgt, dma_addr_t null,
+            dma_addr_t *list, u32 pte, u32 cnt)
+{
+       u32 base = (pte << 2) & ~0x0000000f;
+       u32 tmp[4];
+
+       tmp[0] = nv_ro32(pgt, base + 0x0);
+       tmp[1] = nv_ro32(pgt, base + 0x4);
+       tmp[2] = nv_ro32(pgt, base + 0x8);
+       tmp[3] = nv_ro32(pgt, base + 0xc);
+
+       while (cnt--) {
+               u32 addr = list ? (*list++ >> 12) : (null >> 12);
+               switch (pte++ & 0x3) {
+               case 0:
+                       tmp[0] &= ~0x07ffffff;
+                       tmp[0] |= addr;
+                       break;
+               case 1:
+                       tmp[0] &= ~0xf8000000;
+                       tmp[0] |= addr << 27;
+                       tmp[1] &= ~0x003fffff;
+                       tmp[1] |= addr >> 5;
+                       break;
+               case 2:
+                       tmp[1] &= ~0xffc00000;
+                       tmp[1] |= addr << 22;
+                       tmp[2] &= ~0x0001ffff;
+                       tmp[2] |= addr >> 10;
+                       break;
+               case 3:
+                       tmp[2] &= ~0xfffe0000;
+                       tmp[2] |= addr << 17;
+                       tmp[3] &= ~0x00000fff;
+                       tmp[3] |= addr >> 15;
+                       break;
+               }
+       }
+
+       nv_wo32(pgt, base + 0x0, tmp[0]);
+       nv_wo32(pgt, base + 0x4, tmp[1]);
+       nv_wo32(pgt, base + 0x8, tmp[2]);
+       nv_wo32(pgt, base + 0xc, tmp[3] | 0x40000000);
+}
+
+static void
+nv44_vm_map_sg(struct nvkm_vma *vma, struct nvkm_gpuobj *pgt,
+              struct nvkm_mem *mem, u32 pte, u32 cnt, dma_addr_t *list)
+{
+       struct nv04_mmu_priv *priv = (void *)vma->vm->mmu;
+       u32 tmp[4];
+       int i;
+
+       if (pte & 3) {
+               u32  max = 4 - (pte & 3);
+               u32 part = (cnt > max) ? max : cnt;
+               nv44_vm_fill(pgt, priv->null, list, pte, part);
+               pte  += part;
+               list += part;
+               cnt  -= part;
+       }
+
+       while (cnt >= 4) {
+               for (i = 0; i < 4; i++)
+                       tmp[i] = *list++ >> 12;
+               nv_wo32(pgt, pte++ * 4, tmp[0] >>  0 | tmp[1] << 27);
+               nv_wo32(pgt, pte++ * 4, tmp[1] >>  5 | tmp[2] << 22);
+               nv_wo32(pgt, pte++ * 4, tmp[2] >> 10 | tmp[3] << 17);
+               nv_wo32(pgt, pte++ * 4, tmp[3] >> 15 | 0x40000000);
+               cnt -= 4;
+       }
+
+       if (cnt)
+               nv44_vm_fill(pgt, priv->null, list, pte, cnt);
+}
+
+static void
+nv44_vm_unmap(struct nvkm_gpuobj *pgt, u32 pte, u32 cnt)
+{
+       struct nv04_mmu_priv *priv = (void *)nvkm_mmu(pgt);
+
+       if (pte & 3) {
+               u32  max = 4 - (pte & 3);
+               u32 part = (cnt > max) ? max : cnt;
+               nv44_vm_fill(pgt, priv->null, NULL, pte, part);
+               pte  += part;
+               cnt  -= part;
+       }
+
+       while (cnt >= 4) {
+               nv_wo32(pgt, pte++ * 4, 0x00000000);
+               nv_wo32(pgt, pte++ * 4, 0x00000000);
+               nv_wo32(pgt, pte++ * 4, 0x00000000);
+               nv_wo32(pgt, pte++ * 4, 0x00000000);
+               cnt -= 4;
+       }
+
+       if (cnt)
+               nv44_vm_fill(pgt, priv->null, NULL, pte, cnt);
+}
+
+static void
+nv44_vm_flush(struct nvkm_vm *vm)
+{
+       struct nv04_mmu_priv *priv = (void *)vm->mmu;
+       nv_wr32(priv, 0x100814, priv->base.limit - NV44_GART_PAGE);
+       nv_wr32(priv, 0x100808, 0x00000020);
+       if (!nv_wait(priv, 0x100808, 0x00000001, 0x00000001))
+               nv_error(priv, "timeout: 0x%08x\n", nv_rd32(priv, 0x100808));
+       nv_wr32(priv, 0x100808, 0x00000000);
+}
+
+/*******************************************************************************
+ * MMU subdev
+ ******************************************************************************/
+
+static int
+nv44_mmu_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+             struct nvkm_oclass *oclass, void *data, u32 size,
+             struct nvkm_object **pobject)
+{
+       struct nvkm_device *device = nv_device(parent);
+       struct nv04_mmu_priv *priv;
+       int ret;
+
+       if (pci_find_capability(device->pdev, PCI_CAP_ID_AGP) ||
+           !nvkm_boolopt(device->cfgopt, "NvPCIE", true)) {
+               return nvkm_object_ctor(parent, engine, &nv04_mmu_oclass,
+                                       data, size, pobject);
+       }
+
+       ret = nvkm_mmu_create(parent, engine, oclass, "PCIEGART",
+                             "pciegart", &priv);
+       *pobject = nv_object(priv);
+       if (ret)
+               return ret;
+
+       priv->base.create = nv04_vm_create;
+       priv->base.limit = NV44_GART_SIZE;
+       priv->base.dma_bits = 39;
+       priv->base.pgt_bits = 32 - 12;
+       priv->base.spg_shift = 12;
+       priv->base.lpg_shift = 12;
+       priv->base.map_sg = nv44_vm_map_sg;
+       priv->base.unmap = nv44_vm_unmap;
+       priv->base.flush = nv44_vm_flush;
+
+       priv->nullp = pci_alloc_consistent(device->pdev, 16 * 1024, &priv->null);
+       if (!priv->nullp) {
+               nv_error(priv, "unable to allocate dummy pages\n");
+               return -ENOMEM;
+       }
+
+       ret = nvkm_vm_create(&priv->base, 0, NV44_GART_SIZE, 0, 4096,
+                            &priv->vm);
+       if (ret)
+               return ret;
+
+       ret = nvkm_gpuobj_new(nv_object(priv), NULL,
+                             (NV44_GART_SIZE / NV44_GART_PAGE) * 4,
+                             512 * 1024, NVOBJ_FLAG_ZERO_ALLOC,
+                             &priv->vm->pgt[0].obj[0]);
+       priv->vm->pgt[0].refcount[0] = 1;
+       if (ret)
+               return ret;
+
+       return 0;
+}
+
+static int
+nv44_mmu_init(struct nvkm_object *object)
+{
+       struct nv04_mmu_priv *priv = (void *)object;
+       struct nvkm_gpuobj *gart = priv->vm->pgt[0].obj[0];
+       u32 addr;
+       int ret;
+
+       ret = nvkm_mmu_init(&priv->base);
+       if (ret)
+               return ret;
+
+       /* calculate vram address of this PRAMIN block, object must be
+        * allocated on 512KiB alignment, and not exceed a total size
+        * of 512KiB for this to work correctly
+        */
+       addr  = nv_rd32(priv, 0x10020c);
+       addr -= ((gart->addr >> 19) + 1) << 19;
+
+       nv_wr32(priv, 0x100850, 0x80000000);
+       nv_wr32(priv, 0x100818, priv->null);
+       nv_wr32(priv, 0x100804, NV44_GART_SIZE);
+       nv_wr32(priv, 0x100850, 0x00008000);
+       nv_mask(priv, 0x10008c, 0x00000200, 0x00000200);
+       nv_wr32(priv, 0x100820, 0x00000000);
+       nv_wr32(priv, 0x10082c, 0x00000001);
+       nv_wr32(priv, 0x100800, addr | 0x00000010);
+       return 0;
+}
+
+struct nvkm_oclass
+nv44_mmu_oclass = {
+       .handle = NV_SUBDEV(MMU, 0x44),
+       .ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = nv44_mmu_ctor,
+               .dtor = nv04_mmu_dtor,
+               .init = nv44_mmu_init,
+               .fini = _nvkm_mmu_fini,
+       },
+};
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/mmu/nv50.c b/drivers/gpu/drm/nouveau/nvkm/subdev/mmu/nv50.c
new file mode 100644 (file)
index 0000000..b83550f
--- /dev/null
@@ -0,0 +1,241 @@
+/*
+ * 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 <subdev/mmu.h>
+#include <subdev/bar.h>
+#include <subdev/fb.h>
+#include <subdev/timer.h>
+
+#include <core/engine.h>
+#include <core/gpuobj.h>
+
+struct nv50_mmu_priv {
+       struct nvkm_mmu base;
+};
+
+static void
+nv50_vm_map_pgt(struct nvkm_gpuobj *pgd, u32 pde, struct nvkm_gpuobj *pgt[2])
+{
+       u64 phys = 0xdeadcafe00000000ULL;
+       u32 coverage = 0;
+
+       if (pgt[0]) {
+               phys = 0x00000003 | pgt[0]->addr; /* present, 4KiB pages */
+               coverage = (pgt[0]->size >> 3) << 12;
+       } else
+       if (pgt[1]) {
+               phys = 0x00000001 | pgt[1]->addr; /* present */
+               coverage = (pgt[1]->size >> 3) << 16;
+       }
+
+       if (phys & 1) {
+               if (coverage <= 32 * 1024 * 1024)
+                       phys |= 0x60;
+               else if (coverage <= 64 * 1024 * 1024)
+                       phys |= 0x40;
+               else if (coverage <= 128 * 1024 * 1024)
+                       phys |= 0x20;
+       }
+
+       nv_wo32(pgd, (pde * 8) + 0, lower_32_bits(phys));
+       nv_wo32(pgd, (pde * 8) + 4, upper_32_bits(phys));
+}
+
+static inline u64
+vm_addr(struct nvkm_vma *vma, u64 phys, u32 memtype, u32 target)
+{
+       phys |= 1; /* present */
+       phys |= (u64)memtype << 40;
+       phys |= target << 4;
+       if (vma->access & NV_MEM_ACCESS_SYS)
+               phys |= (1 << 6);
+       if (!(vma->access & NV_MEM_ACCESS_WO))
+               phys |= (1 << 3);
+       return phys;
+}
+
+static void
+nv50_vm_map(struct nvkm_vma *vma, struct nvkm_gpuobj *pgt,
+           struct nvkm_mem *mem, u32 pte, u32 cnt, u64 phys, u64 delta)
+{
+       u32 comp = (mem->memtype & 0x180) >> 7;
+       u32 block, target;
+       int i;
+
+       /* IGPs don't have real VRAM, re-target to stolen system memory */
+       target = 0;
+       if (nvkm_fb(vma->vm->mmu)->ram->stolen) {
+               phys += nvkm_fb(vma->vm->mmu)->ram->stolen;
+               target = 3;
+       }
+
+       phys  = vm_addr(vma, phys, mem->memtype, target);
+       pte <<= 3;
+       cnt <<= 3;
+
+       while (cnt) {
+               u32 offset_h = upper_32_bits(phys);
+               u32 offset_l = lower_32_bits(phys);
+
+               for (i = 7; i >= 0; i--) {
+                       block = 1 << (i + 3);
+                       if (cnt >= block && !(pte & (block - 1)))
+                               break;
+               }
+               offset_l |= (i << 7);
+
+               phys += block << (vma->node->type - 3);
+               cnt  -= block;
+               if (comp) {
+                       u32 tag = mem->tag->offset + ((delta >> 16) * comp);
+                       offset_h |= (tag << 17);
+                       delta    += block << (vma->node->type - 3);
+               }
+
+               while (block) {
+                       nv_wo32(pgt, pte + 0, offset_l);
+                       nv_wo32(pgt, pte + 4, offset_h);
+                       pte += 8;
+                       block -= 8;
+               }
+       }
+}
+
+static void
+nv50_vm_map_sg(struct nvkm_vma *vma, struct nvkm_gpuobj *pgt,
+              struct nvkm_mem *mem, u32 pte, u32 cnt, dma_addr_t *list)
+{
+       u32 target = (vma->access & NV_MEM_ACCESS_NOSNOOP) ? 3 : 2;
+       pte <<= 3;
+       while (cnt--) {
+               u64 phys = vm_addr(vma, (u64)*list++, mem->memtype, target);
+               nv_wo32(pgt, pte + 0, lower_32_bits(phys));
+               nv_wo32(pgt, pte + 4, upper_32_bits(phys));
+               pte += 8;
+       }
+}
+
+static void
+nv50_vm_unmap(struct nvkm_gpuobj *pgt, u32 pte, u32 cnt)
+{
+       pte <<= 3;
+       while (cnt--) {
+               nv_wo32(pgt, pte + 0, 0x00000000);
+               nv_wo32(pgt, pte + 4, 0x00000000);
+               pte += 8;
+       }
+}
+
+static void
+nv50_vm_flush(struct nvkm_vm *vm)
+{
+       struct nv50_mmu_priv *priv = (void *)vm->mmu;
+       struct nvkm_bar *bar = nvkm_bar(priv);
+       struct nvkm_engine *engine;
+       int i, vme;
+
+       bar->flush(bar);
+
+       mutex_lock(&nv_subdev(priv)->mutex);
+       for (i = 0; i < NVDEV_SUBDEV_NR; i++) {
+               if (!atomic_read(&vm->engref[i]))
+                       continue;
+
+               /* unfortunate hw bug workaround... */
+               engine = nvkm_engine(priv, i);
+               if (engine && engine->tlb_flush) {
+                       engine->tlb_flush(engine);
+                       continue;
+               }
+
+               switch (i) {
+               case NVDEV_ENGINE_GR    : vme = 0x00; break;
+               case NVDEV_ENGINE_VP    :
+               case NVDEV_ENGINE_MSPDEC: vme = 0x01; break;
+               case NVDEV_SUBDEV_BAR   : vme = 0x06; break;
+               case NVDEV_ENGINE_MSPPP :
+               case NVDEV_ENGINE_MPEG  : vme = 0x08; break;
+               case NVDEV_ENGINE_BSP   :
+               case NVDEV_ENGINE_MSVLD : vme = 0x09; break;
+               case NVDEV_ENGINE_CIPHER:
+               case NVDEV_ENGINE_SEC   : vme = 0x0a; break;
+               case NVDEV_ENGINE_CE0   : vme = 0x0d; break;
+               default:
+                       continue;
+               }
+
+               nv_wr32(priv, 0x100c80, (vme << 16) | 1);
+               if (!nv_wait(priv, 0x100c80, 0x00000001, 0x00000000))
+                       nv_error(priv, "vm flush timeout: engine %d\n", vme);
+       }
+       mutex_unlock(&nv_subdev(priv)->mutex);
+}
+
+static int
+nv50_vm_create(struct nvkm_mmu *mmu, u64 offset, u64 length,
+              u64 mm_offset, struct nvkm_vm **pvm)
+{
+       u32 block = (1 << (mmu->pgt_bits + 12));
+       if (block > length)
+               block = length;
+
+       return nvkm_vm_create(mmu, offset, length, mm_offset, block, pvm);
+}
+
+static int
+nv50_mmu_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+             struct nvkm_oclass *oclass, void *data, u32 size,
+             struct nvkm_object **pobject)
+{
+       struct nv50_mmu_priv *priv;
+       int ret;
+
+       ret = nvkm_mmu_create(parent, engine, oclass, "VM", "vm", &priv);
+       *pobject = nv_object(priv);
+       if (ret)
+               return ret;
+
+       priv->base.limit = 1ULL << 40;
+       priv->base.dma_bits = 40;
+       priv->base.pgt_bits  = 29 - 12;
+       priv->base.spg_shift = 12;
+       priv->base.lpg_shift = 16;
+       priv->base.create = nv50_vm_create;
+       priv->base.map_pgt = nv50_vm_map_pgt;
+       priv->base.map = nv50_vm_map;
+       priv->base.map_sg = nv50_vm_map_sg;
+       priv->base.unmap = nv50_vm_unmap;
+       priv->base.flush = nv50_vm_flush;
+       return 0;
+}
+
+struct nvkm_oclass
+nv50_mmu_oclass = {
+       .handle = NV_SUBDEV(MMU, 0x50),
+       .ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = nv50_mmu_ctor,
+               .dtor = _nvkm_mmu_dtor,
+               .init = _nvkm_mmu_init,
+               .fini = _nvkm_mmu_fini,
+       },
+};
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/mxm/Kbuild b/drivers/gpu/drm/nouveau/nvkm/subdev/mxm/Kbuild
new file mode 100644 (file)
index 0000000..1a479e0
--- /dev/null
@@ -0,0 +1,3 @@
+nvkm-y += nvkm/subdev/mxm/base.o
+nvkm-y += nvkm/subdev/mxm/mxms.o
+nvkm-y += nvkm/subdev/mxm/nv50.o
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/mxm/base.c b/drivers/gpu/drm/nouveau/nvkm/subdev/mxm/base.c
new file mode 100644 (file)
index 0000000..0ca9dca
--- /dev/null
@@ -0,0 +1,271 @@
+/*
+ * 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 "mxms.h"
+
+#include <core/device.h>
+#include <core/option.h>
+#include <subdev/bios.h>
+#include <subdev/bios/mxm.h>
+#include <subdev/i2c.h>
+
+static bool
+mxm_shadow_rom_fetch(struct nvkm_i2c_port *i2c, u8 addr,
+                    u8 offset, u8 size, u8 *data)
+{
+       struct i2c_msg msgs[] = {
+               { .addr = addr, .flags = 0, .len = 1, .buf = &offset },
+               { .addr = addr, .flags = I2C_M_RD, .len = size, .buf = data, },
+       };
+
+       return i2c_transfer(&i2c->adapter, msgs, 2) == 2;
+}
+
+static bool
+mxm_shadow_rom(struct nvkm_mxm *mxm, u8 version)
+{
+       struct nvkm_bios *bios = nvkm_bios(mxm);
+       struct nvkm_i2c *i2c = nvkm_i2c(mxm);
+       struct nvkm_i2c_port *port = NULL;
+       u8 i2cidx, mxms[6], addr, size;
+
+       i2cidx = mxm_ddc_map(bios, 1 /* LVDS_DDC */) & 0x0f;
+       if (i2cidx < 0x0f)
+               port = i2c->find(i2c, i2cidx);
+       if (!port)
+               return false;
+
+       addr = 0x54;
+       if (!mxm_shadow_rom_fetch(port, addr, 0, 6, mxms)) {
+               addr = 0x56;
+               if (!mxm_shadow_rom_fetch(port, addr, 0, 6, mxms))
+                       return false;
+       }
+
+       mxm->mxms = mxms;
+       size = mxms_headerlen(mxm) + mxms_structlen(mxm);
+       mxm->mxms = kmalloc(size, GFP_KERNEL);
+
+       if (mxm->mxms &&
+           mxm_shadow_rom_fetch(port, addr, 0, size, mxm->mxms))
+               return true;
+
+       kfree(mxm->mxms);
+       mxm->mxms = NULL;
+       return false;
+}
+
+#if defined(CONFIG_ACPI)
+static bool
+mxm_shadow_dsm(struct nvkm_mxm *mxm, u8 version)
+{
+       struct nvkm_device *device = nv_device(mxm);
+       static char muid[] = {
+               0x00, 0xA4, 0x04, 0x40, 0x7D, 0x91, 0xF2, 0x4C,
+               0xB8, 0x9C, 0x79, 0xB6, 0x2F, 0xD5, 0x56, 0x65
+       };
+       u32 mxms_args[] = { 0x00000000 };
+       union acpi_object argv4 = {
+               .buffer.type = ACPI_TYPE_BUFFER,
+               .buffer.length = sizeof(mxms_args),
+               .buffer.pointer = (char *)mxms_args,
+       };
+       union acpi_object *obj;
+       acpi_handle handle;
+       int rev;
+
+       handle = ACPI_HANDLE(nv_device_base(device));
+       if (!handle)
+               return false;
+
+       /*
+        * spec says this can be zero to mean "highest revision", but
+        * of course there's at least one bios out there which fails
+        * unless you pass in exactly the version it supports..
+        */
+       rev = (version & 0xf0) << 4 | (version & 0x0f);
+       obj = acpi_evaluate_dsm(handle, muid, rev, 0x00000010, &argv4);
+       if (!obj) {
+               nv_debug(mxm, "DSM MXMS failed\n");
+               return false;
+       }
+
+       if (obj->type == ACPI_TYPE_BUFFER) {
+               mxm->mxms = kmemdup(obj->buffer.pointer,
+                                        obj->buffer.length, GFP_KERNEL);
+       } else if (obj->type == ACPI_TYPE_INTEGER) {
+               nv_debug(mxm, "DSM MXMS returned 0x%llx\n", obj->integer.value);
+       }
+
+       ACPI_FREE(obj);
+       return mxm->mxms != NULL;
+}
+#endif
+
+#if defined(CONFIG_ACPI_WMI) || defined(CONFIG_ACPI_WMI_MODULE)
+
+#define WMI_WMMX_GUID "F6CB5C3C-9CAE-4EBD-B577-931EA32A2CC0"
+
+static u8
+wmi_wmmx_mxmi(struct nvkm_mxm *mxm, u8 version)
+{
+       u32 mxmi_args[] = { 0x494D584D /* MXMI */, version, 0 };
+       struct acpi_buffer args = { sizeof(mxmi_args), mxmi_args };
+       struct acpi_buffer retn = { ACPI_ALLOCATE_BUFFER, NULL };
+       union acpi_object *obj;
+       acpi_status status;
+
+       status = wmi_evaluate_method(WMI_WMMX_GUID, 0, 0, &args, &retn);
+       if (ACPI_FAILURE(status)) {
+               nv_debug(mxm, "WMMX MXMI returned %d\n", status);
+               return 0x00;
+       }
+
+       obj = retn.pointer;
+       if (obj->type == ACPI_TYPE_INTEGER) {
+               version = obj->integer.value;
+               nv_debug(mxm, "WMMX MXMI version %d.%d\n",
+                            (version >> 4), version & 0x0f);
+       } else {
+               version = 0;
+               nv_debug(mxm, "WMMX MXMI returned non-integer\n");
+       }
+
+       kfree(obj);
+       return version;
+}
+
+static bool
+mxm_shadow_wmi(struct nvkm_mxm *mxm, u8 version)
+{
+       u32 mxms_args[] = { 0x534D584D /* MXMS */, version, 0 };
+       struct acpi_buffer args = { sizeof(mxms_args), mxms_args };
+       struct acpi_buffer retn = { ACPI_ALLOCATE_BUFFER, NULL };
+       union acpi_object *obj;
+       acpi_status status;
+
+       if (!wmi_has_guid(WMI_WMMX_GUID)) {
+               nv_debug(mxm, "WMMX GUID not found\n");
+               return false;
+       }
+
+       mxms_args[1] = wmi_wmmx_mxmi(mxm, 0x00);
+       if (!mxms_args[1])
+               mxms_args[1] = wmi_wmmx_mxmi(mxm, version);
+       if (!mxms_args[1])
+               return false;
+
+       status = wmi_evaluate_method(WMI_WMMX_GUID, 0, 0, &args, &retn);
+       if (ACPI_FAILURE(status)) {
+               nv_debug(mxm, "WMMX MXMS returned %d\n", status);
+               return false;
+       }
+
+       obj = retn.pointer;
+       if (obj->type == ACPI_TYPE_BUFFER) {
+               mxm->mxms = kmemdup(obj->buffer.pointer,
+                                   obj->buffer.length, GFP_KERNEL);
+       }
+
+       kfree(obj);
+       return mxm->mxms != NULL;
+}
+#endif
+
+static struct mxm_shadow_h {
+       const char *name;
+       bool (*exec)(struct nvkm_mxm *, u8 version);
+} _mxm_shadow[] = {
+       { "ROM", mxm_shadow_rom },
+#if defined(CONFIG_ACPI)
+       { "DSM", mxm_shadow_dsm },
+#endif
+#if defined(CONFIG_ACPI_WMI) || defined(CONFIG_ACPI_WMI_MODULE)
+       { "WMI", mxm_shadow_wmi },
+#endif
+       {}
+};
+
+static int
+mxm_shadow(struct nvkm_mxm *mxm, u8 version)
+{
+       struct mxm_shadow_h *shadow = _mxm_shadow;
+       do {
+               nv_debug(mxm, "checking %s\n", shadow->name);
+               if (shadow->exec(mxm, version)) {
+                       if (mxms_valid(mxm))
+                               return 0;
+                       kfree(mxm->mxms);
+                       mxm->mxms = NULL;
+               }
+       } while ((++shadow)->name);
+       return -ENOENT;
+}
+
+int
+nvkm_mxm_create_(struct nvkm_object *parent, struct nvkm_object *engine,
+                struct nvkm_oclass *oclass, int length, void **pobject)
+{
+       struct nvkm_device *device = nv_device(parent);
+       struct nvkm_bios *bios = nvkm_bios(device);
+       struct nvkm_mxm *mxm;
+       u8  ver, len;
+       u16 data;
+       int ret;
+
+       ret = nvkm_subdev_create_(parent, engine, oclass, 0, "MXM", "mxm",
+                                 length, pobject);
+       mxm = *pobject;
+       if (ret)
+               return ret;
+
+       data = mxm_table(bios, &ver, &len);
+       if (!data || !(ver = nv_ro08(bios, data))) {
+               nv_debug(mxm, "no VBIOS data, nothing to do\n");
+               return 0;
+       }
+
+       nv_info(mxm, "BIOS version %d.%d\n", ver >> 4, ver & 0x0f);
+
+       if (mxm_shadow(mxm, ver)) {
+               nv_info(mxm, "failed to locate valid SIS\n");
+#if 0
+               /* we should, perhaps, fall back to some kind of limited
+                * mode here if the x86 vbios hasn't already done the
+                * work for us (so we prevent loading with completely
+                * whacked vbios tables).
+                */
+               return -EINVAL;
+#else
+               return 0;
+#endif
+       }
+
+       nv_info(mxm, "MXMS Version %d.%d\n",
+               mxms_version(mxm) >> 8, mxms_version(mxm) & 0xff);
+       mxms_foreach(mxm, 0, NULL, NULL);
+
+       if (nvkm_boolopt(device->cfgopt, "NvMXMDCB", true))
+               mxm->action |= MXM_SANITISE_DCB;
+       return 0;
+}
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/mxm/mxms.c b/drivers/gpu/drm/nouveau/nvkm/subdev/mxm/mxms.c
new file mode 100644 (file)
index 0000000..a9b1d63
--- /dev/null
@@ -0,0 +1,191 @@
+/*
+ * Copyright 2012 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 "mxms.h"
+
+#define ROM16(x) le16_to_cpu(*(u16 *)&(x))
+#define ROM32(x) le32_to_cpu(*(u32 *)&(x))
+
+static u8 *
+mxms_data(struct nvkm_mxm *mxm)
+{
+       return mxm->mxms;
+
+}
+
+u16
+mxms_version(struct nvkm_mxm *mxm)
+{
+       u8 *mxms = mxms_data(mxm);
+       u16 version = (mxms[4] << 8) | mxms[5];
+       switch (version ) {
+       case 0x0200:
+       case 0x0201:
+       case 0x0300:
+               return version;
+       default:
+               break;
+       }
+
+       nv_debug(mxm, "unknown version %d.%d\n", mxms[4], mxms[5]);
+       return 0x0000;
+}
+
+u16
+mxms_headerlen(struct nvkm_mxm *mxm)
+{
+       return 8;
+}
+
+u16
+mxms_structlen(struct nvkm_mxm *mxm)
+{
+       return *(u16 *)&mxms_data(mxm)[6];
+}
+
+bool
+mxms_checksum(struct nvkm_mxm *mxm)
+{
+       u16 size = mxms_headerlen(mxm) + mxms_structlen(mxm);
+       u8 *mxms = mxms_data(mxm), sum = 0;
+       while (size--)
+               sum += *mxms++;
+       if (sum) {
+               nv_debug(mxm, "checksum invalid\n");
+               return false;
+       }
+       return true;
+}
+
+bool
+mxms_valid(struct nvkm_mxm *mxm)
+{
+       u8 *mxms = mxms_data(mxm);
+       if (*(u32 *)mxms != 0x5f4d584d) {
+               nv_debug(mxm, "signature invalid\n");
+               return false;
+       }
+
+       if (!mxms_version(mxm) || !mxms_checksum(mxm))
+               return false;
+
+       return true;
+}
+
+bool
+mxms_foreach(struct nvkm_mxm *mxm, u8 types,
+            bool (*exec)(struct nvkm_mxm *, u8 *, void *), void *info)
+{
+       u8 *mxms = mxms_data(mxm);
+       u8 *desc = mxms + mxms_headerlen(mxm);
+       u8 *fini = desc + mxms_structlen(mxm) - 1;
+       while (desc < fini) {
+               u8 type = desc[0] & 0x0f;
+               u8 headerlen = 0;
+               u8 recordlen = 0;
+               u8 entries = 0;
+
+               switch (type) {
+               case 0: /* Output Device Structure */
+                       if (mxms_version(mxm) >= 0x0300)
+                               headerlen = 8;
+                       else
+                               headerlen = 6;
+                       break;
+               case 1: /* System Cooling Capability Structure */
+               case 2: /* Thermal Structure */
+               case 3: /* Input Power Structure */
+                       headerlen = 4;
+                       break;
+               case 4: /* GPIO Device Structure */
+                       headerlen = 4;
+                       recordlen = 2;
+                       entries   = (ROM32(desc[0]) & 0x01f00000) >> 20;
+                       break;
+               case 5: /* Vendor Specific Structure */
+                       headerlen = 8;
+                       break;
+               case 6: /* Backlight Control Structure */
+                       if (mxms_version(mxm) >= 0x0300) {
+                               headerlen = 4;
+                               recordlen = 8;
+                               entries   = (desc[1] & 0xf0) >> 4;
+                       } else {
+                               headerlen = 8;
+                       }
+                       break;
+               case 7: /* Fan Control Structure */
+                       headerlen = 8;
+                       recordlen = 4;
+                       entries   = desc[1] & 0x07;
+                       break;
+               default:
+                       nv_debug(mxm, "unknown descriptor type %d\n", type);
+                       return false;
+               }
+
+               if (nv_subdev(mxm)->debug >= NV_DBG_DEBUG && (exec == NULL)) {
+                       static const char * mxms_desc_name[] = {
+                               "ODS", "SCCS", "TS", "IPS",
+                               "GSD", "VSS", "BCS", "FCS",
+                       };
+                       u8 *dump = desc;
+                       int i, j;
+
+                       nv_debug(mxm, "%4s: ", mxms_desc_name[type]);
+                       for (j = headerlen - 1; j >= 0; j--)
+                               pr_cont("%02x", dump[j]);
+                       pr_cont("\n");
+                       dump += headerlen;
+
+                       for (i = 0; i < entries; i++, dump += recordlen) {
+                               nv_debug(mxm, "      ");
+                               for (j = recordlen - 1; j >= 0; j--)
+                                       pr_cont("%02x", dump[j]);
+                               pr_cont("\n");
+                       }
+               }
+
+               if (types & (1 << type)) {
+                       if (!exec(mxm, desc, info))
+                               return false;
+               }
+
+               desc += headerlen + (entries * recordlen);
+       }
+
+       return true;
+}
+
+void
+mxms_output_device(struct nvkm_mxm *mxm, u8 *pdata, struct mxms_odev *desc)
+{
+       u64 data = ROM32(pdata[0]);
+       if (mxms_version(mxm) >= 0x0300)
+               data |= (u64)ROM16(pdata[4]) << 32;
+
+       desc->outp_type = (data & 0x00000000000000f0ULL) >> 4;
+       desc->ddc_port  = (data & 0x0000000000000f00ULL) >> 8;
+       desc->conn_type = (data & 0x000000000001f000ULL) >> 12;
+       desc->dig_conn  = (data & 0x0000000000780000ULL) >> 19;
+}
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/mxm/mxms.h b/drivers/gpu/drm/nouveau/nvkm/subdev/mxm/mxms.h
new file mode 100644 (file)
index 0000000..4ef8040
--- /dev/null
@@ -0,0 +1,22 @@
+#ifndef __NVMXM_MXMS_H__
+#define __NVMXM_MXMS_H__
+#include <subdev/mxm.h>
+
+struct mxms_odev {
+       u8 outp_type;
+       u8 conn_type;
+       u8 ddc_port;
+       u8 dig_conn;
+};
+
+void mxms_output_device(struct nvkm_mxm *, u8 *, struct mxms_odev *);
+
+u16  mxms_version(struct nvkm_mxm *);
+u16  mxms_headerlen(struct nvkm_mxm *);
+u16  mxms_structlen(struct nvkm_mxm *);
+bool mxms_checksum(struct nvkm_mxm *);
+bool mxms_valid(struct nvkm_mxm *);
+
+bool mxms_foreach(struct nvkm_mxm *, u8,
+                 bool (*)(struct nvkm_mxm *, u8 *, void *), void *);
+#endif
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/mxm/nv50.c b/drivers/gpu/drm/nouveau/nvkm/subdev/mxm/nv50.c
new file mode 100644 (file)
index 0000000..42cac13
--- /dev/null
@@ -0,0 +1,231 @@
+/*
+ * 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 "mxms.h"
+
+#include <subdev/bios.h>
+#include <subdev/bios/conn.h>
+#include <subdev/bios/dcb.h>
+#include <subdev/bios/mxm.h>
+
+struct nv50_mxm_priv {
+       struct nvkm_mxm base;
+};
+
+struct context {
+       u32 *outp;
+       struct mxms_odev desc;
+};
+
+static bool
+mxm_match_tmds_partner(struct nvkm_mxm *mxm, u8 *data, void *info)
+{
+       struct context *ctx = info;
+       struct mxms_odev desc;
+
+       mxms_output_device(mxm, data, &desc);
+       if (desc.outp_type == 2 &&
+           desc.dig_conn == ctx->desc.dig_conn)
+               return false;
+       return true;
+}
+
+static bool
+mxm_match_dcb(struct nvkm_mxm *mxm, u8 *data, void *info)
+{
+       struct nvkm_bios *bios = nvkm_bios(mxm);
+       struct context *ctx = info;
+       u64 desc = *(u64 *)data;
+
+       mxms_output_device(mxm, data, &ctx->desc);
+
+       /* match dcb encoder type to mxm-ods device type */
+       if ((ctx->outp[0] & 0x0000000f) != ctx->desc.outp_type)
+               return true;
+
+       /* digital output, have some extra stuff to match here, there's a
+        * table in the vbios that provides a mapping from the mxm digital
+        * connection enum values to SOR/link
+        */
+       if ((desc & 0x00000000000000f0) >= 0x20) {
+               /* check against sor index */
+               u8 link = mxm_sor_map(bios, ctx->desc.dig_conn);
+               if ((ctx->outp[0] & 0x0f000000) != (link & 0x0f) << 24)
+                       return true;
+
+               /* check dcb entry has a compatible link field */
+               link = (link & 0x30) >> 4;
+               if ((link & ((ctx->outp[1] & 0x00000030) >> 4)) != link)
+                       return true;
+       }
+
+       /* mark this descriptor accounted for by setting invalid device type,
+        * except of course some manufactures don't follow specs properly and
+        * we need to avoid killing off the TMDS function on DP connectors
+        * if MXM-SIS is missing an entry for it.
+        */
+       data[0] &= ~0xf0;
+       if (ctx->desc.outp_type == 6 && ctx->desc.conn_type == 6 &&
+           mxms_foreach(mxm, 0x01, mxm_match_tmds_partner, ctx)) {
+               data[0] |= 0x20; /* modify descriptor to match TMDS now */
+       } else {
+               data[0] |= 0xf0;
+       }
+
+       return false;
+}
+
+static int
+mxm_dcb_sanitise_entry(struct nvkm_bios *bios, void *data, int idx, u16 pdcb)
+{
+       struct nvkm_mxm *mxm = data;
+       struct context ctx = { .outp = (u32 *)(bios->data + pdcb) };
+       u8 type, i2cidx, link, ver, len;
+       u8 *conn;
+
+       /* look for an output device structure that matches this dcb entry.
+        * if one isn't found, disable it.
+        */
+       if (mxms_foreach(mxm, 0x01, mxm_match_dcb, &ctx)) {
+               nv_debug(mxm, "disable %d: 0x%08x 0x%08x\n",
+                       idx, ctx.outp[0], ctx.outp[1]);
+               ctx.outp[0] |= 0x0000000f;
+               return 0;
+       }
+
+       /* modify the output's ddc/aux port, there's a pointer to a table
+        * with the mapping from mxm ddc/aux port to dcb i2c_index in the
+        * vbios mxm table
+        */
+       i2cidx = mxm_ddc_map(bios, ctx.desc.ddc_port);
+       if ((ctx.outp[0] & 0x0000000f) != DCB_OUTPUT_DP)
+               i2cidx = (i2cidx & 0x0f) << 4;
+       else
+               i2cidx = (i2cidx & 0xf0);
+
+       if (i2cidx != 0xf0) {
+               ctx.outp[0] &= ~0x000000f0;
+               ctx.outp[0] |= i2cidx;
+       }
+
+       /* override dcb sorconf.link, based on what mxm data says */
+       switch (ctx.desc.outp_type) {
+       case 0x00: /* Analog CRT */
+       case 0x01: /* Analog TV/HDTV */
+               break;
+       default:
+               link = mxm_sor_map(bios, ctx.desc.dig_conn) & 0x30;
+               ctx.outp[1] &= ~0x00000030;
+               ctx.outp[1] |= link;
+               break;
+       }
+
+       /* we may need to fixup various other vbios tables based on what
+        * the descriptor says the connector type should be.
+        *
+        * in a lot of cases, the vbios tables will claim DVI-I is possible,
+        * and the mxm data says the connector is really HDMI.  another
+        * common example is DP->eDP.
+        */
+       conn  = bios->data;
+       conn += nvbios_connEe(bios, (ctx.outp[0] & 0x0000f000) >> 12, &ver, &len);
+       type  = conn[0];
+       switch (ctx.desc.conn_type) {
+       case 0x01: /* LVDS */
+               ctx.outp[1] |= 0x00000004; /* use_power_scripts */
+               /* XXX: modify default link width in LVDS table */
+               break;
+       case 0x02: /* HDMI */
+               type = DCB_CONNECTOR_HDMI_1;
+               break;
+       case 0x03: /* DVI-D */
+               type = DCB_CONNECTOR_DVI_D;
+               break;
+       case 0x0e: /* eDP, falls through to DPint */
+               ctx.outp[1] |= 0x00010000;
+       case 0x07: /* DP internal, wtf is this?? HP8670w */
+               ctx.outp[1] |= 0x00000004; /* use_power_scripts? */
+               type = DCB_CONNECTOR_eDP;
+               break;
+       default:
+               break;
+       }
+
+       if (mxms_version(mxm) >= 0x0300)
+               conn[0] = type;
+
+       return 0;
+}
+
+static bool
+mxm_show_unmatched(struct nvkm_mxm *mxm, u8 *data, void *info)
+{
+       u64 desc = *(u64 *)data;
+       if ((desc & 0xf0) != 0xf0)
+       nv_info(mxm, "unmatched output device 0x%016llx\n", desc);
+       return true;
+}
+
+static void
+mxm_dcb_sanitise(struct nvkm_mxm *mxm)
+{
+       struct nvkm_bios *bios = nvkm_bios(mxm);
+       u8  ver, hdr, cnt, len;
+       u16 dcb = dcb_table(bios, &ver, &hdr, &cnt, &len);
+       if (dcb == 0x0000 || ver != 0x40) {
+               nv_debug(mxm, "unsupported DCB version\n");
+               return;
+       }
+
+       dcb_outp_foreach(bios, mxm, mxm_dcb_sanitise_entry);
+       mxms_foreach(mxm, 0x01, mxm_show_unmatched, NULL);
+}
+
+static int
+nv50_mxm_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+             struct nvkm_oclass *oclass, void *data, u32 size,
+             struct nvkm_object **pobject)
+{
+       struct nv50_mxm_priv *priv;
+       int ret;
+
+       ret = nvkm_mxm_create(parent, engine, oclass, &priv);
+       *pobject = nv_object(priv);
+       if (ret)
+               return ret;
+
+       if (priv->base.action & MXM_SANITISE_DCB)
+               mxm_dcb_sanitise(&priv->base);
+       return 0;
+}
+
+struct nvkm_oclass
+nv50_mxm_oclass = {
+       .handle = NV_SUBDEV(MXM, 0x50),
+       .ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = nv50_mxm_ctor,
+               .dtor = _nvkm_mxm_dtor,
+               .init = _nvkm_mxm_init,
+               .fini = _nvkm_mxm_fini,
+       },
+};
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/pmu/Kbuild b/drivers/gpu/drm/nouveau/nvkm/subdev/pmu/Kbuild
new file mode 100644 (file)
index 0000000..9a150d5
--- /dev/null
@@ -0,0 +1,8 @@
+nvkm-y += nvkm/subdev/pmu/base.o
+nvkm-y += nvkm/subdev/pmu/memx.o
+nvkm-y += nvkm/subdev/pmu/gt215.o
+nvkm-y += nvkm/subdev/pmu/gf100.o
+nvkm-y += nvkm/subdev/pmu/gf110.o
+nvkm-y += nvkm/subdev/pmu/gk104.o
+nvkm-y += nvkm/subdev/pmu/gk208.o
+nvkm-y += nvkm/subdev/pmu/gk20a.o
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/pmu/base.c b/drivers/gpu/drm/nouveau/nvkm/subdev/pmu/base.c
new file mode 100644 (file)
index 0000000..054b2d2
--- /dev/null
@@ -0,0 +1,268 @@
+/*
+ * Copyright 2013 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 "priv.h"
+
+#include <subdev/timer.h>
+
+void
+nvkm_pmu_pgob(struct nvkm_pmu *pmu, bool enable)
+{
+       const struct nvkm_pmu_impl *impl = (void *)nv_oclass(pmu);
+       if (impl->pgob)
+               impl->pgob(pmu, enable);
+}
+
+static int
+nvkm_pmu_send(struct nvkm_pmu *pmu, u32 reply[2],
+             u32 process, u32 message, u32 data0, u32 data1)
+{
+       struct nvkm_subdev *subdev = nv_subdev(pmu);
+       u32 addr;
+
+       /* wait for a free slot in the fifo */
+       addr  = nv_rd32(pmu, 0x10a4a0);
+       if (!nv_wait_ne(pmu, 0x10a4b0, 0xffffffff, addr ^ 8))
+               return -EBUSY;
+
+       /* we currently only support a single process at a time waiting
+        * on a synchronous reply, take the PMU mutex and tell the
+        * receive handler what we're waiting for
+        */
+       if (reply) {
+               mutex_lock(&subdev->mutex);
+               pmu->recv.message = message;
+               pmu->recv.process = process;
+       }
+
+       /* acquire data segment access */
+       do {
+               nv_wr32(pmu, 0x10a580, 0x00000001);
+       } while (nv_rd32(pmu, 0x10a580) != 0x00000001);
+
+       /* write the packet */
+       nv_wr32(pmu, 0x10a1c0, 0x01000000 | (((addr & 0x07) << 4) +
+                               pmu->send.base));
+       nv_wr32(pmu, 0x10a1c4, process);
+       nv_wr32(pmu, 0x10a1c4, message);
+       nv_wr32(pmu, 0x10a1c4, data0);
+       nv_wr32(pmu, 0x10a1c4, data1);
+       nv_wr32(pmu, 0x10a4a0, (addr + 1) & 0x0f);
+
+       /* release data segment access */
+       nv_wr32(pmu, 0x10a580, 0x00000000);
+
+       /* wait for reply, if requested */
+       if (reply) {
+               wait_event(pmu->recv.wait, (pmu->recv.process == 0));
+               reply[0] = pmu->recv.data[0];
+               reply[1] = pmu->recv.data[1];
+               mutex_unlock(&subdev->mutex);
+       }
+
+       return 0;
+}
+
+static void
+nvkm_pmu_recv(struct work_struct *work)
+{
+       struct nvkm_pmu *pmu = container_of(work, struct nvkm_pmu, recv.work);
+       u32 process, message, data0, data1;
+
+       /* nothing to do if GET == PUT */
+       u32 addr =  nv_rd32(pmu, 0x10a4cc);
+       if (addr == nv_rd32(pmu, 0x10a4c8))
+               return;
+
+       /* acquire data segment access */
+       do {
+               nv_wr32(pmu, 0x10a580, 0x00000002);
+       } while (nv_rd32(pmu, 0x10a580) != 0x00000002);
+
+       /* read the packet */
+       nv_wr32(pmu, 0x10a1c0, 0x02000000 | (((addr & 0x07) << 4) +
+                               pmu->recv.base));
+       process = nv_rd32(pmu, 0x10a1c4);
+       message = nv_rd32(pmu, 0x10a1c4);
+       data0   = nv_rd32(pmu, 0x10a1c4);
+       data1   = nv_rd32(pmu, 0x10a1c4);
+       nv_wr32(pmu, 0x10a4cc, (addr + 1) & 0x0f);
+
+       /* release data segment access */
+       nv_wr32(pmu, 0x10a580, 0x00000000);
+
+       /* wake process if it's waiting on a synchronous reply */
+       if (pmu->recv.process) {
+               if (process == pmu->recv.process &&
+                   message == pmu->recv.message) {
+                       pmu->recv.data[0] = data0;
+                       pmu->recv.data[1] = data1;
+                       pmu->recv.process = 0;
+                       wake_up(&pmu->recv.wait);
+                       return;
+               }
+       }
+
+       /* right now there's no other expected responses from the engine,
+        * so assume that any unexpected message is an error.
+        */
+       nv_warn(pmu, "%c%c%c%c 0x%08x 0x%08x 0x%08x 0x%08x\n",
+               (char)((process & 0x000000ff) >>  0),
+               (char)((process & 0x0000ff00) >>  8),
+               (char)((process & 0x00ff0000) >> 16),
+               (char)((process & 0xff000000) >> 24),
+               process, message, data0, data1);
+}
+
+static void
+nvkm_pmu_intr(struct nvkm_subdev *subdev)
+{
+       struct nvkm_pmu *pmu = (void *)subdev;
+       u32 disp = nv_rd32(pmu, 0x10a01c);
+       u32 intr = nv_rd32(pmu, 0x10a008) & disp & ~(disp >> 16);
+
+       if (intr & 0x00000020) {
+               u32 stat = nv_rd32(pmu, 0x10a16c);
+               if (stat & 0x80000000) {
+                       nv_error(pmu, "UAS fault at 0x%06x addr 0x%08x\n",
+                                stat & 0x00ffffff, nv_rd32(pmu, 0x10a168));
+                       nv_wr32(pmu, 0x10a16c, 0x00000000);
+                       intr &= ~0x00000020;
+               }
+       }
+
+       if (intr & 0x00000040) {
+               schedule_work(&pmu->recv.work);
+               nv_wr32(pmu, 0x10a004, 0x00000040);
+               intr &= ~0x00000040;
+       }
+
+       if (intr & 0x00000080) {
+               nv_info(pmu, "wr32 0x%06x 0x%08x\n", nv_rd32(pmu, 0x10a7a0),
+                                                    nv_rd32(pmu, 0x10a7a4));
+               nv_wr32(pmu, 0x10a004, 0x00000080);
+               intr &= ~0x00000080;
+       }
+
+       if (intr) {
+               nv_error(pmu, "intr 0x%08x\n", intr);
+               nv_wr32(pmu, 0x10a004, intr);
+       }
+}
+
+int
+_nvkm_pmu_fini(struct nvkm_object *object, bool suspend)
+{
+       struct nvkm_pmu *pmu = (void *)object;
+
+       nv_wr32(pmu, 0x10a014, 0x00000060);
+       flush_work(&pmu->recv.work);
+
+       return nvkm_subdev_fini(&pmu->base, suspend);
+}
+
+int
+_nvkm_pmu_init(struct nvkm_object *object)
+{
+       const struct nvkm_pmu_impl *impl = (void *)object->oclass;
+       struct nvkm_pmu *pmu = (void *)object;
+       int ret, i;
+
+       ret = nvkm_subdev_init(&pmu->base);
+       if (ret)
+               return ret;
+
+       nv_subdev(pmu)->intr = nvkm_pmu_intr;
+       pmu->message = nvkm_pmu_send;
+       pmu->pgob = nvkm_pmu_pgob;
+
+       /* prevent previous ucode from running, wait for idle, reset */
+       nv_wr32(pmu, 0x10a014, 0x0000ffff); /* INTR_EN_CLR = ALL */
+       nv_wait(pmu, 0x10a04c, 0xffffffff, 0x00000000);
+       nv_mask(pmu, 0x000200, 0x00002000, 0x00000000);
+       nv_mask(pmu, 0x000200, 0x00002000, 0x00002000);
+       nv_rd32(pmu, 0x000200);
+       nv_wait(pmu, 0x10a10c, 0x00000006, 0x00000000);
+
+       /* upload data segment */
+       nv_wr32(pmu, 0x10a1c0, 0x01000000);
+       for (i = 0; i < impl->data.size / 4; i++)
+               nv_wr32(pmu, 0x10a1c4, impl->data.data[i]);
+
+       /* upload code segment */
+       nv_wr32(pmu, 0x10a180, 0x01000000);
+       for (i = 0; i < impl->code.size / 4; i++) {
+               if ((i & 0x3f) == 0)
+                       nv_wr32(pmu, 0x10a188, i >> 6);
+               nv_wr32(pmu, 0x10a184, impl->code.data[i]);
+       }
+
+       /* start it running */
+       nv_wr32(pmu, 0x10a10c, 0x00000000);
+       nv_wr32(pmu, 0x10a104, 0x00000000);
+       nv_wr32(pmu, 0x10a100, 0x00000002);
+
+       /* wait for valid host->pmu ring configuration */
+       if (!nv_wait_ne(pmu, 0x10a4d0, 0xffffffff, 0x00000000))
+               return -EBUSY;
+       pmu->send.base = nv_rd32(pmu, 0x10a4d0) & 0x0000ffff;
+       pmu->send.size = nv_rd32(pmu, 0x10a4d0) >> 16;
+
+       /* wait for valid pmu->host ring configuration */
+       if (!nv_wait_ne(pmu, 0x10a4dc, 0xffffffff, 0x00000000))
+               return -EBUSY;
+       pmu->recv.base = nv_rd32(pmu, 0x10a4dc) & 0x0000ffff;
+       pmu->recv.size = nv_rd32(pmu, 0x10a4dc) >> 16;
+
+       nv_wr32(pmu, 0x10a010, 0x000000e0);
+       return 0;
+}
+
+int
+nvkm_pmu_create_(struct nvkm_object *parent, struct nvkm_object *engine,
+                struct nvkm_oclass *oclass, int length, void **pobject)
+{
+       struct nvkm_pmu *pmu;
+       int ret;
+
+       ret = nvkm_subdev_create_(parent, engine, oclass, 0, "PMU",
+                                 "pmu", length, pobject);
+       pmu = *pobject;
+       if (ret)
+               return ret;
+
+       INIT_WORK(&pmu->recv.work, nvkm_pmu_recv);
+       init_waitqueue_head(&pmu->recv.wait);
+       return 0;
+}
+
+int
+_nvkm_pmu_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+              struct nvkm_oclass *oclass, void *data, u32 size,
+              struct nvkm_object **pobject)
+{
+       struct nvkm_pmu *pmu;
+       int ret = nvkm_pmu_create(parent, engine, oclass, &pmu);
+       *pobject = nv_object(pmu);
+       return ret;
+}
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/pmu/fuc/arith.fuc b/drivers/gpu/drm/nouveau/nvkm/subdev/pmu/fuc/arith.fuc
new file mode 100644 (file)
index 0000000..214a6d9
--- /dev/null
@@ -0,0 +1,94 @@
+/*
+ * Copyright 2014 Martin Peres <martin.peres@free.fr>
+ *
+ * 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 folloing 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
+ */
+
+/******************************************************************************
+ * arith data segment
+ *****************************************************************************/
+#ifdef INCLUDE_PROC
+#endif
+
+#ifdef INCLUDE_DATA
+#endif
+
+/******************************************************************************
+ * arith code segment
+ *****************************************************************************/
+#ifdef INCLUDE_CODE
+
+// does a 32x32 -> 64 multiplication
+//
+// A * B = A_lo * B_lo
+//        + ( A_hi * B_lo ) << 16
+//        + ( A_lo * B_hi ) << 16
+//        + ( A_hi * B_hi ) << 32
+//
+// $r15 - current
+// $r14 - A
+// $r13 - B
+// $r12 - mul_lo (return)
+// $r11 - mul_hi (return)
+// $r0  - zero
+mulu32_32_64:
+       push $r1 // A_hi
+       push $r2 // B_hi
+       push $r3 // tmp0
+       push $r4 // tmp1
+
+       shr b32 $r1 $r14 16
+       shr b32 $r2 $r13 16
+
+       clear b32 $r12
+       clear b32 $r11
+
+       // A_lo * B_lo
+       mulu $r12 $r14 $r13
+
+       // ( A_hi * B_lo ) << 16
+       mulu $r3 $r1 $r13 // tmp0 = A_hi * B_lo
+       mov b32 $r4 $r3
+       and $r3 0xffff // tmp0 = tmp0_lo
+       shl b32 $r3 16
+       shr b32 $r4 16 // tmp1 = tmp0_hi
+       add b32 $r12 $r3
+       adc b32 $r11 $r4
+
+       // ( A_lo * B_hi ) << 16
+       mulu $r3 $r14 $r2 // tmp0 = A_lo * B_hi
+       mov b32 $r4 $r3
+       and $r3 0xffff // tmp0 = tmp0_lo
+       shl b32 $r3 16
+       shr b32 $r4 16 // tmp1 = tmp0_hi
+       add b32 $r12 $r3
+       adc b32 $r11 $r4
+
+       // ( A_hi * B_hi ) << 32
+       mulu $r3 $r1 $r2 // tmp0 = A_hi * B_hi
+       add b32 $r11 $r3
+
+       pop $r4
+       pop $r3
+       pop $r2
+       pop $r1
+       ret
+#endif
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/pmu/fuc/gf100.fuc3 b/drivers/gpu/drm/nouveau/nvkm/subdev/pmu/fuc/gf100.fuc3
new file mode 100644 (file)
index 0000000..37e8407
--- /dev/null
@@ -0,0 +1,70 @@
+/*
+ * Copyright 2013 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 NVKM_PPWR_CHIPSET GF100
+#define HW_TICKS_PER_US 203 // should be 202.5
+
+//#define NVKM_FALCON_PC24
+//#define NVKM_FALCON_UNSHIFTED_IO
+//#define NVKM_FALCON_MMIO_UAS
+//#define NVKM_FALCON_MMIO_TRAP
+
+#include "macros.fuc"
+
+.section #gf100_pmu_data
+#define INCLUDE_PROC
+#include "kernel.fuc"
+#include "arith.fuc"
+#include "host.fuc"
+#include "memx.fuc"
+#include "perf.fuc"
+#include "i2c_.fuc"
+#include "test.fuc"
+#include "idle.fuc"
+#undef INCLUDE_PROC
+
+#define INCLUDE_DATA
+#include "kernel.fuc"
+#include "arith.fuc"
+#include "host.fuc"
+#include "memx.fuc"
+#include "perf.fuc"
+#include "i2c_.fuc"
+#include "test.fuc"
+#include "idle.fuc"
+#undef INCLUDE_DATA
+.align 256
+
+.section #gf100_pmu_code
+#define INCLUDE_CODE
+#include "kernel.fuc"
+#include "arith.fuc"
+#include "host.fuc"
+#include "memx.fuc"
+#include "perf.fuc"
+#include "i2c_.fuc"
+#include "test.fuc"
+#include "idle.fuc"
+#undef INCLUDE_CODE
+.align 256
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/pmu/fuc/gf100.fuc3.h b/drivers/gpu/drm/nouveau/nvkm/subdev/pmu/fuc/gf100.fuc3.h
new file mode 100644 (file)
index 0000000..302557c
--- /dev/null
@@ -0,0 +1,1865 @@
+uint32_t gf100_pmu_data[] = {
+/* 0x0000: proc_kern */
+       0x52544e49,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+/* 0x0058: proc_list_head */
+       0x54534f48,
+       0x00000512,
+       0x000004af,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x584d454d,
+       0x0000075e,
+       0x00000750,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x46524550,
+       0x00000762,
+       0x00000760,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x5f433249,
+       0x00000b92,
+       0x00000a35,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x54534554,
+       0x00000bbb,
+       0x00000b94,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x454c4449,
+       0x00000bc7,
+       0x00000bc5,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+/* 0x0268: proc_list_tail */
+/* 0x0268: time_prev */
+       0x00000000,
+/* 0x026c: time_next */
+       0x00000000,
+/* 0x0270: fifo_queue */
+       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,
+/* 0x02f0: rfifo_queue */
+       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,
+/* 0x0370: memx_func_head */
+       0x00000001,
+       0x00000000,
+       0x00000551,
+/* 0x037c: memx_func_next */
+       0x00000002,
+       0x00000000,
+       0x000005db,
+       0x00000003,
+       0x00000002,
+       0x000006a5,
+       0x00040004,
+       0x00000000,
+       0x000006c1,
+       0x00010005,
+       0x00000000,
+       0x000006de,
+       0x00010006,
+       0x00000000,
+       0x00000663,
+       0x00000007,
+       0x00000000,
+       0x000006e9,
+/* 0x03c4: memx_func_tail */
+/* 0x03c4: memx_ts_start */
+       0x00000000,
+/* 0x03c8: memx_ts_end */
+       0x00000000,
+/* 0x03cc: memx_data_head */
+       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,
+       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,
+       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,
+       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,
+       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,
+       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,
+       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,
+       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,
+/* 0x0bcc: memx_data_tail */
+/* 0x0bcc: memx_train_head */
+       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,
+/* 0x0ccc: memx_train_tail */
+/* 0x0ccc: i2c_scl_map */
+       0x00001000,
+       0x00004000,
+       0x00010000,
+       0x00000100,
+       0x00040000,
+       0x00100000,
+       0x00400000,
+       0x01000000,
+       0x04000000,
+       0x10000000,
+/* 0x0cf4: i2c_sda_map */
+       0x00002000,
+       0x00008000,
+       0x00020000,
+       0x00000200,
+       0x00080000,
+       0x00200000,
+       0x00800000,
+       0x02000000,
+       0x08000000,
+       0x20000000,
+/* 0x0d1c: i2c_ctrl */
+       0x0000e138,
+       0x0000e150,
+       0x0000e168,
+       0x0000e180,
+       0x0000e254,
+       0x0000e274,
+       0x0000e764,
+       0x0000e780,
+       0x0000e79c,
+       0x0000e7b8,
+       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,
+};
+
+uint32_t gf100_pmu_code[] = {
+       0x039e0ef5,
+/* 0x0004: rd32 */
+       0x07a007f1,
+       0xd00604b6,
+       0x04bd000e,
+       0xf001d7f0,
+       0x07f101d3,
+       0x04b607ac,
+       0x000dd006,
+/* 0x0022: rd32_wait */
+       0xd7f104bd,
+       0xd4b607ac,
+       0x00ddcf06,
+       0x7000d4f1,
+       0xf1f21bf4,
+       0xb607a4d7,
+       0xddcf06d4,
+/* 0x003f: wr32 */
+       0xf100f800,
+       0xb607a007,
+       0x0ed00604,
+       0xf104bd00,
+       0xb607a407,
+       0x0dd00604,
+       0xf004bd00,
+       0xd5f002d7,
+       0x01d3f0f0,
+       0x07ac07f1,
+       0xd00604b6,
+       0x04bd000d,
+/* 0x006c: wr32_wait */
+       0x07acd7f1,
+       0xcf06d4b6,
+       0xd4f100dd,
+       0x1bf47000,
+/* 0x007f: nsec */
+       0xf900f8f2,
+       0xf080f990,
+       0x84b62c87,
+       0x0088cf06,
+/* 0x008c: nsec_loop */
+       0xb62c97f0,
+       0x99cf0694,
+       0x0298bb00,
+       0xf4069eb8,
+       0x80fcf11e,
+       0x00f890fc,
+/* 0x00a4: wait */
+       0x80f990f9,
+       0xb62c87f0,
+       0x88cf0684,
+/* 0x00b1: wait_loop */
+       0x02eeb900,
+       0xb90421f4,
+       0xadfd02da,
+       0x06acb804,
+       0xf0150bf4,
+       0x94b62c97,
+       0x0099cf06,
+       0xb80298bb,
+       0x1ef4069b,
+/* 0x00d5: wait_done */
+       0xfc80fcdf,
+/* 0x00db: intr_watchdog */
+       0x9800f890,
+       0x96b003e9,
+       0x2a0bf400,
+       0xbb9a0a98,
+       0x1cf4029a,
+       0x01d7f00f,
+       0x02dd21f5,
+       0x0ef494bd,
+/* 0x00f9: intr_watchdog_next_time */
+       0x9b0a9815,
+       0xf400a6b0,
+       0x9ab8090b,
+       0x061cf406,
+/* 0x0108: intr_watchdog_next_time_set */
+/* 0x010b: intr_watchdog_next_proc */
+       0x809b0980,
+       0xe0b603e9,
+       0x68e6b158,
+       0xc61bf402,
+/* 0x011a: intr */
+       0x00f900f8,
+       0x80f904bd,
+       0xa0f990f9,
+       0xc0f9b0f9,
+       0xe0f9d0f9,
+       0xf7f0f0f9,
+       0x0188fe00,
+       0x87f180f9,
+       0x84b605d0,
+       0x0088cf06,
+       0xf10180b6,
+       0xb605d007,
+       0x08d00604,
+       0xf004bd00,
+       0x84b60887,
+       0x0088cf06,
+       0xf40289c4,
+       0x0080230b,
+       0x58e7f09b,
+       0x98db21f4,
+       0x96b09b09,
+       0x110bf400,
+       0xb63407f0,
+       0x09d00604,
+       0x8004bd00,
+/* 0x017e: intr_skip_watchdog */
+       0x89e49a09,
+       0x0bf40800,
+       0x8897f148,
+       0x0694b606,
+       0xc40099cf,
+       0x0bf4029a,
+       0xc0c7f12c,
+       0x06c4b604,
+       0xf900cccf,
+       0x48e7f1c0,
+       0x53e3f14f,
+       0x00d7f054,
+       0x034221f5,
+       0x07f1c0fc,
+       0x04b604c0,
+       0x000cd006,
+/* 0x01be: intr_subintr_skip_fifo */
+       0x07f104bd,
+       0x04b60688,
+       0x0009d006,
+/* 0x01ca: intr_skip_subintr */
+       0x89c404bd,
+       0x070bf420,
+       0xffbfa4f1,
+/* 0x01d4: intr_skip_pause */
+       0xf44089c4,
+       0xa4f1070b,
+/* 0x01de: intr_skip_user0 */
+       0x07f0ffbf,
+       0x0604b604,
+       0xbd0008d0,
+       0xfe80fc04,
+       0xf0fc0088,
+       0xd0fce0fc,
+       0xb0fcc0fc,
+       0x90fca0fc,
+       0x00fc80fc,
+       0xf80032f4,
+/* 0x0205: ticks_from_ns */
+       0xf9c0f901,
+       0xcbd7f1b0,
+       0x00d3f000,
+       0x041321f5,
+       0x03e8ccec,
+       0xf400b4b0,
+       0xeeec120b,
+       0xd7f103e8,
+       0xd3f000cb,
+       0x1321f500,
+/* 0x022d: ticks_from_ns_quit */
+       0x02ceb904,
+       0xc0fcb0fc,
+/* 0x0236: ticks_from_us */
+       0xc0f900f8,
+       0xd7f1b0f9,
+       0xd3f000cb,
+       0x1321f500,
+       0x02ceb904,
+       0xf400b4b0,
+       0xe4bd050b,
+/* 0x0250: ticks_from_us_quit */
+       0xc0fcb0fc,
+/* 0x0256: ticks_to_us */
+       0xd7f100f8,
+       0xd3f000cb,
+       0xecedff00,
+/* 0x0262: timer */
+       0x90f900f8,
+       0x32f480f9,
+       0x03f89810,
+       0xf40086b0,
+       0x84bd651c,
+       0xb63807f0,
+       0x08d00604,
+       0xf004bd00,
+       0x84b63487,
+       0x0088cf06,
+       0xbb9a0998,
+       0xe9bb0298,
+       0x03fe8000,
+       0xb60887f0,
+       0x88cf0684,
+       0x0284f000,
+       0xf0261bf4,
+       0x84b63487,
+       0x0088cf06,
+       0xf406e0b8,
+       0xe8b8090b,
+       0x111cf406,
+/* 0x02b8: timer_reset */
+       0xb63407f0,
+       0x0ed00604,
+       0x8004bd00,
+/* 0x02c6: timer_enable */
+       0x87f09a0e,
+       0x3807f001,
+       0xd00604b6,
+       0x04bd0008,
+/* 0x02d4: timer_done */
+       0xfc1031f4,
+       0xf890fc80,
+/* 0x02dd: send_proc */
+       0xf980f900,
+       0x05e89890,
+       0xf004e998,
+       0x89b80486,
+       0x2a0bf406,
+       0x940398c4,
+       0x80b60488,
+       0x008ebb18,
+       0x8000fa98,
+       0x8d80008a,
+       0x028c8001,
+       0xb6038b80,
+       0x94f00190,
+       0x04e98007,
+/* 0x0317: send_done */
+       0xfc0231f4,
+       0xf880fc90,
+/* 0x031d: find */
+       0xf080f900,
+       0x31f45887,
+/* 0x0325: find_loop */
+       0x008a9801,
+       0xf406aeb8,
+       0x80b6100b,
+       0x6886b158,
+       0xf01bf402,
+/* 0x033b: find_done */
+       0xb90132f4,
+       0x80fc028e,
+/* 0x0342: send */
+       0x21f500f8,
+       0x01f4031d,
+/* 0x034b: recv */
+       0xf900f897,
+       0x9880f990,
+       0xe99805e8,
+       0x0132f404,
+       0xf40689b8,
+       0x89c43d0b,
+       0x0180b603,
+       0x800784f0,
+       0xea9805e8,
+       0xfef0f902,
+       0xf0f9018f,
+       0x9402efb9,
+       0xe9bb0499,
+       0x18e0b600,
+       0x9803eb98,
+       0xed9802ec,
+       0x00ee9801,
+       0xf0fca5f9,
+       0xf400f8fe,
+       0xf0fc0131,
+/* 0x0398: recv_done */
+       0x90fc80fc,
+/* 0x039e: init */
+       0x17f100f8,
+       0x14b60108,
+       0x0011cf06,
+       0x010911e7,
+       0xfe0814b6,
+       0x17f10014,
+       0x13f000e0,
+       0x1c07f000,
+       0xd00604b6,
+       0x04bd0001,
+       0xf0ff17f0,
+       0x04b61407,
+       0x0001d006,
+       0x17f004bd,
+       0x0015f102,
+       0x1007f008,
+       0xd00604b6,
+       0x04bd0001,
+       0x011a17f1,
+       0xfe0013f0,
+       0x31f40010,
+       0x0117f010,
+       0xb63807f0,
+       0x01d00604,
+       0xf004bd00,
+/* 0x0402: init_proc */
+       0xf19858f7,
+       0x0016b001,
+       0xf9fa0bf4,
+       0x58f0b615,
+/* 0x0413: mulu32_32_64 */
+       0xf9f20ef4,
+       0xf920f910,
+       0x9540f930,
+       0xd29510e1,
+       0xbdc4bd10,
+       0xc0edffb4,
+       0xb9301dff,
+       0x34f10234,
+       0x34b6ffff,
+       0x1045b610,
+       0xbb00c3bb,
+       0xe2ff01b4,
+       0x0234b930,
+       0xffff34f1,
+       0xb61034b6,
+       0xc3bb1045,
+       0x01b4bb00,
+       0xbb3012ff,
+       0x40fc00b3,
+       0x20fc30fc,
+       0x00f810fc,
+/* 0x0464: host_send */
+       0x04b017f1,
+       0xcf0614b6,
+       0x27f10011,
+       0x24b604a0,
+       0x0022cf06,
+       0xf40612b8,
+       0x1ec4320b,
+       0x04ee9407,
+       0x0270e0b7,
+       0x9803eb98,
+       0xed9802ec,
+       0x00ee9801,
+       0x034221f5,
+       0xc40110b6,
+       0x07f10f1e,
+       0x04b604b0,
+       0x000ed006,
+       0x0ef404bd,
+/* 0x04ad: host_send_done */
+/* 0x04af: host_recv */
+       0xf100f8ba,
+       0xf14e4917,
+       0xb8525413,
+       0x0bf406e1,
+/* 0x04bd: host_recv_wait */
+       0xcc17f1aa,
+       0x0614b604,
+       0xf10011cf,
+       0xb604c827,
+       0x22cf0624,
+       0x0816f000,
+       0xf40612b8,
+       0x23c4e60b,
+       0x0434b607,
+       0x02f030b7,
+       0x80033b80,
+       0x3d80023c,
+       0x003e8001,
+       0xf00120b6,
+       0x07f10f24,
+       0x04b604c8,
+       0x0002d006,
+       0x27f004bd,
+       0x0007f040,
+       0xd00604b6,
+       0x04bd0002,
+/* 0x0512: host_init */
+       0x17f100f8,
+       0x14b60080,
+       0x7015f110,
+       0xd007f102,
+       0x0604b604,
+       0xbd0001d0,
+       0x8017f104,
+       0x1014b600,
+       0x02f015f1,
+       0x04dc07f1,
+       0xd00604b6,
+       0x04bd0001,
+       0xf10117f0,
+       0xb604c407,
+       0x01d00604,
+       0xf804bd00,
+/* 0x0551: memx_func_enter */
+       0x2067f100,
+       0x5d77f116,
+       0xff73f1f5,
+       0x026eb9ff,
+       0xb90421f4,
+       0x87fd02d8,
+       0xf960f904,
+       0xfcd0fc80,
+       0x3f21f4e0,
+       0xfffe77f1,
+       0xffff73f1,
+       0xf4026eb9,
+       0xd8b90421,
+       0x0487fd02,
+       0x80f960f9,
+       0xe0fcd0fc,
+       0xf13f21f4,
+       0xb926f067,
+       0x21f4026e,
+       0x02d8b904,
+       0xf90487fd,
+       0xfc80f960,
+       0xf4e0fcd0,
+       0x67f03f21,
+       0xe007f104,
+       0x0604b607,
+       0xbd0006d0,
+/* 0x05bd: memx_func_enter_wait */
+       0xc067f104,
+       0x0664b607,
+       0xf00066cf,
+       0x0bf40464,
+       0x2c67f0f3,
+       0xcf0664b6,
+       0x06800066,
+/* 0x05db: memx_func_leave */
+       0xf000f8f1,
+       0x64b62c67,
+       0x0066cf06,
+       0xf0f20680,
+       0x07f10467,
+       0x04b607e4,
+       0x0006d006,
+/* 0x05f6: memx_func_leave_wait */
+       0x67f104bd,
+       0x64b607c0,
+       0x0066cf06,
+       0xf40464f0,
+       0x67f1f31b,
+       0x77f126f0,
+       0x73f00001,
+       0x026eb900,
+       0xb90421f4,
+       0x87fd02d8,
+       0xf960f905,
+       0xfcd0fc80,
+       0x3f21f4e0,
+       0x162067f1,
+       0xf4026eb9,
+       0xd8b90421,
+       0x0587fd02,
+       0x80f960f9,
+       0xe0fcd0fc,
+       0xf13f21f4,
+       0xf00aa277,
+       0x6eb90073,
+       0x0421f402,
+       0xfd02d8b9,
+       0x60f90587,
+       0xd0fc80f9,
+       0x21f4e0fc,
+/* 0x0663: memx_func_wait_vblank */
+       0x9800f83f,
+       0x66b00016,
+       0x130bf400,
+       0xf40166b0,
+       0x0ef4060b,
+/* 0x0675: memx_func_wait_vblank_head1 */
+       0x2077f12e,
+       0x070ef400,
+/* 0x067c: memx_func_wait_vblank_head0 */
+       0x000877f1,
+/* 0x0680: memx_func_wait_vblank_0 */
+       0x07c467f1,
+       0xcf0664b6,
+       0x67fd0066,
+       0xf31bf404,
+/* 0x0690: memx_func_wait_vblank_1 */
+       0x07c467f1,
+       0xcf0664b6,
+       0x67fd0066,
+       0xf30bf404,
+/* 0x06a0: memx_func_wait_vblank_fini */
+       0xf80410b6,
+/* 0x06a5: memx_func_wr32 */
+       0x00169800,
+       0xb6011598,
+       0x60f90810,
+       0xd0fc50f9,
+       0x21f4e0fc,
+       0x0242b63f,
+       0xf8e91bf4,
+/* 0x06c1: memx_func_wait */
+       0x2c87f000,
+       0xcf0684b6,
+       0x1e980088,
+       0x011d9800,
+       0x98021c98,
+       0x10b6031b,
+       0xa421f410,
+/* 0x06de: memx_func_delay */
+       0x1e9800f8,
+       0x0410b600,
+       0xf87f21f4,
+/* 0x06e9: memx_func_train */
+/* 0x06eb: memx_exec */
+       0xf900f800,
+       0xb9d0f9e0,
+       0xb2b902c1,
+/* 0x06f5: memx_exec_next */
+       0x00139802,
+       0xe70410b6,
+       0xe701f034,
+       0xb601e033,
+       0x30f00132,
+       0xde35980c,
+       0x12b855f9,
+       0xe41ef406,
+       0x98f10b98,
+       0xcbbbf20c,
+       0xc4b7f102,
+       0x06b4b607,
+       0xfc00bbcf,
+       0xf5e0fcd0,
+       0xf8034221,
+/* 0x0731: memx_info */
+       0x01c67000,
+/* 0x0737: memx_info_data */
+       0xf10e0bf4,
+       0xf103ccc7,
+       0xf40800b7,
+/* 0x0742: memx_info_train */
+       0xc7f10b0e,
+       0xb7f10bcc,
+/* 0x074a: memx_info_send */
+       0x21f50100,
+       0x00f80342,
+/* 0x0750: memx_recv */
+       0xf401d6b0,
+       0xd6b0980b,
+       0xd80bf400,
+/* 0x075e: memx_init */
+       0x00f800f8,
+/* 0x0760: perf_recv */
+/* 0x0762: perf_init */
+       0x00f800f8,
+/* 0x0764: i2c_drive_scl */
+       0xf40036b0,
+       0x07f1110b,
+       0x04b607e0,
+       0x0001d006,
+       0x00f804bd,
+/* 0x0778: i2c_drive_scl_lo */
+       0x07e407f1,
+       0xd00604b6,
+       0x04bd0001,
+/* 0x0786: i2c_drive_sda */
+       0x36b000f8,
+       0x110bf400,
+       0x07e007f1,
+       0xd00604b6,
+       0x04bd0002,
+/* 0x079a: i2c_drive_sda_lo */
+       0x07f100f8,
+       0x04b607e4,
+       0x0002d006,
+       0x00f804bd,
+/* 0x07a8: i2c_sense_scl */
+       0xf10132f4,
+       0xb607c437,
+       0x33cf0634,
+       0x0431fd00,
+       0xf4060bf4,
+/* 0x07be: i2c_sense_scl_done */
+       0x00f80131,
+/* 0x07c0: i2c_sense_sda */
+       0xf10132f4,
+       0xb607c437,
+       0x33cf0634,
+       0x0432fd00,
+       0xf4060bf4,
+/* 0x07d6: i2c_sense_sda_done */
+       0x00f80131,
+/* 0x07d8: i2c_raise_scl */
+       0x47f140f9,
+       0x37f00898,
+       0x6421f501,
+/* 0x07e5: i2c_raise_scl_wait */
+       0xe8e7f107,
+       0x7f21f403,
+       0x07a821f5,
+       0xb60901f4,
+       0x1bf40142,
+/* 0x07f9: i2c_raise_scl_done */
+       0xf840fcef,
+/* 0x07fd: i2c_start */
+       0xa821f500,
+       0x0d11f407,
+       0x07c021f5,
+       0xf40611f4,
+/* 0x080e: i2c_start_rep */
+       0x37f0300e,
+       0x6421f500,
+       0x0137f007,
+       0x078621f5,
+       0xb60076bb,
+       0x50f90465,
+       0xbb046594,
+       0x50bd0256,
+       0xfc0475fd,
+       0xd821f550,
+       0x0464b607,
+/* 0x083b: i2c_start_send */
+       0xf01f11f4,
+       0x21f50037,
+       0xe7f10786,
+       0x21f41388,
+       0x0037f07f,
+       0x076421f5,
+       0x1388e7f1,
+/* 0x0857: i2c_start_out */
+       0xf87f21f4,
+/* 0x0859: i2c_stop */
+       0x0037f000,
+       0x076421f5,
+       0xf50037f0,
+       0xf1078621,
+       0xf403e8e7,
+       0x37f07f21,
+       0x6421f501,
+       0x88e7f107,
+       0x7f21f413,
+       0xf50137f0,
+       0xf1078621,
+       0xf41388e7,
+       0x00f87f21,
+/* 0x088c: i2c_bitw */
+       0x078621f5,
+       0x03e8e7f1,
+       0xbb7f21f4,
+       0x65b60076,
+       0x9450f904,
+       0x56bb0465,
+       0xfd50bd02,
+       0x50fc0475,
+       0x07d821f5,
+       0xf40464b6,
+       0xe7f11811,
+       0x21f41388,
+       0x0037f07f,
+       0x076421f5,
+       0x1388e7f1,
+/* 0x08cb: i2c_bitw_out */
+       0xf87f21f4,
+/* 0x08cd: i2c_bitr */
+       0x0137f000,
+       0x078621f5,
+       0x03e8e7f1,
+       0xbb7f21f4,
+       0x65b60076,
+       0x9450f904,
+       0x56bb0465,
+       0xfd50bd02,
+       0x50fc0475,
+       0x07d821f5,
+       0xf40464b6,
+       0x21f51b11,
+       0x37f007c0,
+       0x6421f500,
+       0x88e7f107,
+       0x7f21f413,
+       0xf4013cf0,
+/* 0x0912: i2c_bitr_done */
+       0x00f80131,
+/* 0x0914: i2c_get_byte */
+       0xf00057f0,
+/* 0x091a: i2c_get_byte_next */
+       0x54b60847,
+       0x0076bb01,
+       0xf90465b6,
+       0x04659450,
+       0xbd0256bb,
+       0x0475fd50,
+       0x21f550fc,
+       0x64b608cd,
+       0x2b11f404,
+       0xb60553fd,
+       0x1bf40142,
+       0x0137f0d8,
+       0xb60076bb,
+       0x50f90465,
+       0xbb046594,
+       0x50bd0256,
+       0xfc0475fd,
+       0x8c21f550,
+       0x0464b608,
+/* 0x0964: i2c_get_byte_done */
+/* 0x0966: i2c_put_byte */
+       0x47f000f8,
+/* 0x0969: i2c_put_byte_next */
+       0x0142b608,
+       0xbb3854ff,
+       0x65b60076,
+       0x9450f904,
+       0x56bb0465,
+       0xfd50bd02,
+       0x50fc0475,
+       0x088c21f5,
+       0xf40464b6,
+       0x46b03411,
+       0xd81bf400,
+       0xb60076bb,
+       0x50f90465,
+       0xbb046594,
+       0x50bd0256,
+       0xfc0475fd,
+       0xcd21f550,
+       0x0464b608,
+       0xbb0f11f4,
+       0x36b00076,
+       0x061bf401,
+/* 0x09bf: i2c_put_byte_done */
+       0xf80132f4,
+/* 0x09c1: i2c_addr */
+       0x0076bb00,
+       0xf90465b6,
+       0x04659450,
+       0xbd0256bb,
+       0x0475fd50,
+       0x21f550fc,
+       0x64b607fd,
+       0x2911f404,
+       0x012ec3e7,
+       0xfd0134b6,
+       0x76bb0553,
+       0x0465b600,
+       0x659450f9,
+       0x0256bb04,
+       0x75fd50bd,
+       0xf550fc04,
+       0xb6096621,
+/* 0x0a06: i2c_addr_done */
+       0x00f80464,
+/* 0x0a08: i2c_acquire_addr */
+       0xb6f8cec7,
+       0xe0b702e4,
+       0xee980d1c,
+/* 0x0a17: i2c_acquire */
+       0xf500f800,
+       0xf40a0821,
+       0xd9f00421,
+       0x3f21f403,
+/* 0x0a26: i2c_release */
+       0x21f500f8,
+       0x21f40a08,
+       0x03daf004,
+       0xf83f21f4,
+/* 0x0a35: i2c_recv */
+       0x0132f400,
+       0xb6f8c1c7,
+       0x16b00214,
+       0x3a1ff528,
+       0xf413a001,
+       0x0032980c,
+       0x0ccc13a0,
+       0xf4003198,
+       0xd0f90231,
+       0xd0f9e0f9,
+       0x000067f1,
+       0x100063f1,
+       0xbb016792,
+       0x65b60076,
+       0x9450f904,
+       0x56bb0465,
+       0xfd50bd02,
+       0x50fc0475,
+       0x0a1721f5,
+       0xfc0464b6,
+       0x00d6b0d0,
+       0x00b31bf5,
+       0xbb0057f0,
+       0x65b60076,
+       0x9450f904,
+       0x56bb0465,
+       0xfd50bd02,
+       0x50fc0475,
+       0x09c121f5,
+       0xf50464b6,
+       0xc700d011,
+       0x76bbe0c5,
+       0x0465b600,
+       0x659450f9,
+       0x0256bb04,
+       0x75fd50bd,
+       0xf550fc04,
+       0xb6096621,
+       0x11f50464,
+       0x57f000ad,
+       0x0076bb01,
+       0xf90465b6,
+       0x04659450,
+       0xbd0256bb,
+       0x0475fd50,
+       0x21f550fc,
+       0x64b609c1,
+       0x8a11f504,
+       0x0076bb00,
+       0xf90465b6,
+       0x04659450,
+       0xbd0256bb,
+       0x0475fd50,
+       0x21f550fc,
+       0x64b60914,
+       0x6a11f404,
+       0xbbe05bcb,
+       0x65b60076,
+       0x9450f904,
+       0x56bb0465,
+       0xfd50bd02,
+       0x50fc0475,
+       0x085921f5,
+       0xb90464b6,
+       0x74bd025b,
+/* 0x0b3b: i2c_recv_not_rd08 */
+       0xb0430ef4,
+       0x1bf401d6,
+       0x0057f03d,
+       0x09c121f5,
+       0xc73311f4,
+       0x21f5e0c5,
+       0x11f40966,
+       0x0057f029,
+       0x09c121f5,
+       0xc71f11f4,
+       0x21f5e0b5,
+       0x11f40966,
+       0x5921f515,
+       0xc774bd08,
+       0x1bf408c5,
+       0x0232f409,
+/* 0x0b7b: i2c_recv_not_wr08 */
+/* 0x0b7b: i2c_recv_done */
+       0xc7030ef4,
+       0x21f5f8ce,
+       0xe0fc0a26,
+       0x12f4d0fc,
+       0x027cb90a,
+       0x034221f5,
+/* 0x0b90: i2c_recv_exit */
+/* 0x0b92: i2c_init */
+       0x00f800f8,
+/* 0x0b94: test_recv */
+       0x05d817f1,
+       0xcf0614b6,
+       0x10b60011,
+       0xd807f101,
+       0x0604b605,
+       0xbd0001d0,
+       0x00e7f104,
+       0x4fe3f1d9,
+       0x6221f513,
+/* 0x0bbb: test_init */
+       0xf100f802,
+       0xf50800e7,
+       0xf8026221,
+/* 0x0bc5: idle_recv */
+/* 0x0bc7: idle */
+       0xf400f800,
+       0x17f10031,
+       0x14b605d4,
+       0x0011cf06,
+       0xf10110b6,
+       0xb605d407,
+       0x01d00604,
+/* 0x0be3: idle_loop */
+       0xf004bd00,
+       0x32f45817,
+/* 0x0be9: idle_proc */
+/* 0x0be9: idle_proc_exec */
+       0xb910f902,
+       0x21f5021e,
+       0x10fc034b,
+       0xf40911f4,
+       0x0ef40231,
+/* 0x0bfd: idle_proc_next */
+       0x5810b6ef,
+       0xf4061fb8,
+       0x02f4e61b,
+       0x0028f4dd,
+       0x00bb0ef4,
+       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,
+};
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/pmu/fuc/gf110.fuc4 b/drivers/gpu/drm/nouveau/nvkm/subdev/pmu/fuc/gf110.fuc4
new file mode 100644 (file)
index 0000000..ae9c3f1
--- /dev/null
@@ -0,0 +1,70 @@
+/*
+ * Copyright 2013 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 NVKM_PPWR_CHIPSET GF119
+#define HW_TICKS_PER_US 324
+
+//#define NVKM_FALCON_PC24
+#define NVKM_FALCON_UNSHIFTED_IO
+//#define NVKM_FALCON_MMIO_UAS
+//#define NVKM_FALCON_MMIO_TRAP
+
+#include "macros.fuc"
+
+.section #gf110_pmu_data
+#define INCLUDE_PROC
+#include "kernel.fuc"
+#include "arith.fuc"
+#include "host.fuc"
+#include "memx.fuc"
+#include "perf.fuc"
+#include "i2c_.fuc"
+#include "test.fuc"
+#include "idle.fuc"
+#undef INCLUDE_PROC
+
+#define INCLUDE_DATA
+#include "kernel.fuc"
+#include "arith.fuc"
+#include "host.fuc"
+#include "memx.fuc"
+#include "perf.fuc"
+#include "i2c_.fuc"
+#include "test.fuc"
+#include "idle.fuc"
+#undef INCLUDE_DATA
+.align 256
+
+.section #gf110_pmu_code
+#define INCLUDE_CODE
+#include "kernel.fuc"
+#include "arith.fuc"
+#include "host.fuc"
+#include "memx.fuc"
+#include "perf.fuc"
+#include "i2c_.fuc"
+#include "test.fuc"
+#include "idle.fuc"
+#undef INCLUDE_CODE
+.align 256
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/pmu/fuc/gf110.fuc4.h b/drivers/gpu/drm/nouveau/nvkm/subdev/pmu/fuc/gf110.fuc4.h
new file mode 100644 (file)
index 0000000..a0c499e
--- /dev/null
@@ -0,0 +1,1795 @@
+uint32_t gf110_pmu_data[] = {
+/* 0x0000: proc_kern */
+       0x52544e49,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+/* 0x0058: proc_list_head */
+       0x54534f48,
+       0x0000049d,
+       0x00000446,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x584d454d,
+       0x0000068b,
+       0x0000067d,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x46524550,
+       0x0000068f,
+       0x0000068d,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x5f433249,
+       0x00000aaa,
+       0x0000094d,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x54534554,
+       0x00000acd,
+       0x00000aac,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x454c4449,
+       0x00000ad9,
+       0x00000ad7,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+/* 0x0268: proc_list_tail */
+/* 0x0268: time_prev */
+       0x00000000,
+/* 0x026c: time_next */
+       0x00000000,
+/* 0x0270: fifo_queue */
+       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,
+/* 0x02f0: rfifo_queue */
+       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,
+/* 0x0370: memx_func_head */
+       0x00000001,
+       0x00000000,
+       0x000004d3,
+/* 0x037c: memx_func_next */
+       0x00000002,
+       0x00000000,
+       0x00000554,
+       0x00000003,
+       0x00000002,
+       0x000005d8,
+       0x00040004,
+       0x00000000,
+       0x000005f4,
+       0x00010005,
+       0x00000000,
+       0x0000060e,
+       0x00010006,
+       0x00000000,
+       0x000005d3,
+       0x00000007,
+       0x00000000,
+       0x00000619,
+/* 0x03c4: memx_func_tail */
+/* 0x03c4: memx_ts_start */
+       0x00000000,
+/* 0x03c8: memx_ts_end */
+       0x00000000,
+/* 0x03cc: memx_data_head */
+       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,
+       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,
+       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,
+       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,
+       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,
+       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,
+       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,
+       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,
+/* 0x0bcc: memx_data_tail */
+/* 0x0bcc: memx_train_head */
+       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,
+/* 0x0ccc: memx_train_tail */
+/* 0x0ccc: i2c_scl_map */
+       0x00000400,
+       0x00000800,
+       0x00001000,
+       0x00002000,
+       0x00004000,
+       0x00008000,
+       0x00010000,
+       0x00020000,
+       0x00040000,
+       0x00080000,
+/* 0x0cf4: i2c_sda_map */
+       0x00100000,
+       0x00200000,
+       0x00400000,
+       0x00800000,
+       0x01000000,
+       0x02000000,
+       0x04000000,
+       0x08000000,
+       0x10000000,
+       0x20000000,
+       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,
+};
+
+uint32_t gf110_pmu_code[] = {
+       0x034d0ef5,
+/* 0x0004: rd32 */
+       0x07a007f1,
+       0xbd000ed0,
+       0x01d7f004,
+       0xf101d3f0,
+       0xd007ac07,
+       0x04bd000d,
+/* 0x001c: rd32_wait */
+       0x07acd7f1,
+       0xf100ddcf,
+       0xf47000d4,
+       0xd7f1f51b,
+       0xddcf07a4,
+/* 0x0033: wr32 */
+       0xf100f800,
+       0xd007a007,
+       0x04bd000e,
+       0x07a407f1,
+       0xbd000dd0,
+       0x02d7f004,
+       0xf0f0d5f0,
+       0x07f101d3,
+       0x0dd007ac,
+/* 0x0057: wr32_wait */
+       0xf104bd00,
+       0xcf07acd7,
+       0xd4f100dd,
+       0x1bf47000,
+/* 0x0067: nsec */
+       0xf900f8f5,
+       0xf080f990,
+       0x88cf2c87,
+/* 0x0071: nsec_loop */
+       0x2c97f000,
+       0xbb0099cf,
+       0x9eb80298,
+       0xf41ef406,
+       0x90fc80fc,
+/* 0x0086: wait */
+       0x90f900f8,
+       0x87f080f9,
+       0x0088cf2c,
+/* 0x0090: wait_loop */
+       0xf402eeb9,
+       0xdab90421,
+       0x04adfd02,
+       0xf406acb8,
+       0x97f0120b,
+       0x0099cf2c,
+       0xb80298bb,
+       0x1ef4069b,
+/* 0x00b1: wait_done */
+       0xfc80fce2,
+/* 0x00b7: intr_watchdog */
+       0x9800f890,
+       0x96b003e9,
+       0x2a0bf400,
+       0xbb9a0a98,
+       0x1cf4029a,
+       0x01d7f00f,
+       0x028c21f5,
+       0x0ef494bd,
+/* 0x00d5: intr_watchdog_next_time */
+       0x9b0a9815,
+       0xf400a6b0,
+       0x9ab8090b,
+       0x061cf406,
+/* 0x00e4: intr_watchdog_next_time_set */
+/* 0x00e7: intr_watchdog_next_proc */
+       0x809b0980,
+       0xe0b603e9,
+       0x68e6b158,
+       0xc61bf402,
+/* 0x00f6: intr */
+       0x00f900f8,
+       0x80f904bd,
+       0xa0f990f9,
+       0xc0f9b0f9,
+       0xe0f9d0f9,
+       0xf7f0f0f9,
+       0x0188fe00,
+       0x87f180f9,
+       0x88cf05d0,
+       0x0180b600,
+       0x05d007f1,
+       0xbd0008d0,
+       0x0887f004,
+       0xc40088cf,
+       0x0bf40289,
+       0x9b008020,
+       0xf458e7f0,
+       0x0998b721,
+       0x0096b09b,
+       0xf00e0bf4,
+       0x09d03407,
+       0x8004bd00,
+/* 0x014e: intr_skip_watchdog */
+       0x89e49a09,
+       0x0bf40800,
+       0x8897f13c,
+       0x0099cf06,
+       0xf4029ac4,
+       0xc7f1260b,
+       0xcccf04c0,
+       0xf1c0f900,
+       0xf14f48e7,
+       0xf05453e3,
+       0x21f500d7,
+       0xc0fc02f1,
+       0x04c007f1,
+       0xbd000cd0,
+/* 0x0185: intr_subintr_skip_fifo */
+       0x8807f104,
+       0x0009d006,
+/* 0x018e: intr_skip_subintr */
+       0x89c404bd,
+       0x070bf420,
+       0xffbfa4f1,
+/* 0x0198: intr_skip_pause */
+       0xf44089c4,
+       0xa4f1070b,
+/* 0x01a2: intr_skip_user0 */
+       0x07f0ffbf,
+       0x0008d004,
+       0x80fc04bd,
+       0xfc0088fe,
+       0xfce0fcf0,
+       0xfcc0fcd0,
+       0xfca0fcb0,
+       0xfc80fc90,
+       0x0032f400,
+/* 0x01c6: ticks_from_ns */
+       0xc0f901f8,
+       0xd7f1b0f9,
+       0xd3f00144,
+       0xb321f500,
+       0xe8ccec03,
+       0x00b4b003,
+       0xec120bf4,
+       0xf103e8ee,
+       0xf00144d7,
+       0x21f500d3,
+/* 0x01ee: ticks_from_ns_quit */
+       0xceb903b3,
+       0xfcb0fc02,
+/* 0x01f7: ticks_from_us */
+       0xf900f8c0,
+       0xf1b0f9c0,
+       0xf00144d7,
+       0x21f500d3,
+       0xceb903b3,
+       0x00b4b002,
+       0xbd050bf4,
+/* 0x0211: ticks_from_us_quit */
+       0xfcb0fce4,
+/* 0x0217: ticks_to_us */
+       0xf100f8c0,
+       0xf00144d7,
+       0xedff00d3,
+/* 0x0223: timer */
+       0xf900f8ec,
+       0xf480f990,
+       0xf8981032,
+       0x0086b003,
+       0xbd531cf4,
+       0x3807f084,
+       0xbd0008d0,
+       0x3487f004,
+       0x980088cf,
+       0x98bb9a09,
+       0x00e9bb02,
+       0xf003fe80,
+       0x88cf0887,
+       0x0284f000,
+       0xf0201bf4,
+       0x88cf3487,
+       0x06e0b800,
+       0xb8090bf4,
+       0x1cf406e8,
+/* 0x026d: timer_reset */
+       0x3407f00e,
+       0xbd000ed0,
+       0x9a0e8004,
+/* 0x0278: timer_enable */
+       0xf00187f0,
+       0x08d03807,
+/* 0x0283: timer_done */
+       0xf404bd00,
+       0x80fc1031,
+       0x00f890fc,
+/* 0x028c: send_proc */
+       0x90f980f9,
+       0x9805e898,
+       0x86f004e9,
+       0x0689b804,
+       0xc42a0bf4,
+       0x88940398,
+       0x1880b604,
+       0x98008ebb,
+       0x8a8000fa,
+       0x018d8000,
+       0x80028c80,
+       0x90b6038b,
+       0x0794f001,
+       0xf404e980,
+/* 0x02c6: send_done */
+       0x90fc0231,
+       0x00f880fc,
+/* 0x02cc: find */
+       0x87f080f9,
+       0x0131f458,
+/* 0x02d4: find_loop */
+       0xb8008a98,
+       0x0bf406ae,
+       0x5880b610,
+       0x026886b1,
+       0xf4f01bf4,
+/* 0x02ea: find_done */
+       0x8eb90132,
+       0xf880fc02,
+/* 0x02f1: send */
+       0xcc21f500,
+       0x9701f402,
+/* 0x02fa: recv */
+       0x90f900f8,
+       0xe89880f9,
+       0x04e99805,
+       0xb80132f4,
+       0x0bf40689,
+       0x0389c43d,
+       0xf00180b6,
+       0xe8800784,
+       0x02ea9805,
+       0x8ffef0f9,
+       0xb9f0f901,
+       0x999402ef,
+       0x00e9bb04,
+       0x9818e0b6,
+       0xec9803eb,
+       0x01ed9802,
+       0xf900ee98,
+       0xfef0fca5,
+       0x31f400f8,
+/* 0x0347: recv_done */
+       0xfcf0fc01,
+       0xf890fc80,
+/* 0x034d: init */
+       0x0817f100,
+       0x0011cf01,
+       0x010911e7,
+       0xfe0814b6,
+       0x17f10014,
+       0x13f000e0,
+       0x1c07f000,
+       0xbd0001d0,
+       0xff17f004,
+       0xd01407f0,
+       0x04bd0001,
+       0xf10217f0,
+       0xf0080015,
+       0x01d01007,
+       0xf104bd00,
+       0xf000f617,
+       0x10fe0013,
+       0x1031f400,
+       0xf00117f0,
+       0x01d03807,
+       0xf004bd00,
+/* 0x03a2: init_proc */
+       0xf19858f7,
+       0x0016b001,
+       0xf9fa0bf4,
+       0x58f0b615,
+/* 0x03b3: mulu32_32_64 */
+       0xf9f20ef4,
+       0xf920f910,
+       0x9540f930,
+       0xd29510e1,
+       0xbdc4bd10,
+       0xc0edffb4,
+       0xb9301dff,
+       0x34f10234,
+       0x34b6ffff,
+       0x1045b610,
+       0xbb00c3bb,
+       0xe2ff01b4,
+       0x0234b930,
+       0xffff34f1,
+       0xb61034b6,
+       0xc3bb1045,
+       0x01b4bb00,
+       0xbb3012ff,
+       0x40fc00b3,
+       0x20fc30fc,
+       0x00f810fc,
+/* 0x0404: host_send */
+       0x04b017f1,
+       0xf10011cf,
+       0xcf04a027,
+       0x12b80022,
+       0x2f0bf406,
+       0x94071ec4,
+       0xe0b704ee,
+       0xeb980270,
+       0x02ec9803,
+       0x9801ed98,
+       0x21f500ee,
+       0x10b602f1,
+       0x0f1ec401,
+       0x04b007f1,
+       0xbd000ed0,
+       0xc30ef404,
+/* 0x0444: host_send_done */
+/* 0x0446: host_recv */
+       0x17f100f8,
+       0x13f14e49,
+       0xe1b85254,
+       0xb30bf406,
+/* 0x0454: host_recv_wait */
+       0x04cc17f1,
+       0xf10011cf,
+       0xcf04c827,
+       0x16f00022,
+       0x0612b808,
+       0xc4ec0bf4,
+       0x34b60723,
+       0xf030b704,
+       0x033b8002,
+       0x80023c80,
+       0x3e80013d,
+       0x0120b600,
+       0xf10f24f0,
+       0xd004c807,
+       0x04bd0002,
+       0xf04027f0,
+       0x02d00007,
+       0xf804bd00,
+/* 0x049d: host_init */
+       0x8017f100,
+       0x1014b600,
+       0x027015f1,
+       0x04d007f1,
+       0xbd0001d0,
+       0x8017f104,
+       0x1014b600,
+       0x02f015f1,
+       0x04dc07f1,
+       0xbd0001d0,
+       0x0117f004,
+       0x04c407f1,
+       0xbd0001d0,
+/* 0x04d3: memx_func_enter */
+       0xf100f804,
+       0xf1162067,
+       0xf1f55d77,
+       0xb9ffff73,
+       0x21f4026e,
+       0x02d8b904,
+       0xf90487fd,
+       0xfc80f960,
+       0xf4e0fcd0,
+       0x77f13321,
+       0x73f1fffe,
+       0x6eb9ffff,
+       0x0421f402,
+       0xfd02d8b9,
+       0x60f90487,
+       0xd0fc80f9,
+       0x21f4e0fc,
+       0xf067f133,
+       0x026eb926,
+       0xb90421f4,
+       0x87fd02d8,
+       0xf960f904,
+       0xfcd0fc80,
+       0x3321f4e0,
+       0xf10467f0,
+       0xd007e007,
+       0x04bd0006,
+/* 0x053c: memx_func_enter_wait */
+       0x07c067f1,
+       0xf00066cf,
+       0x0bf40464,
+       0x2c67f0f6,
+       0x800066cf,
+       0x00f8f106,
+/* 0x0554: memx_func_leave */
+       0xcf2c67f0,
+       0x06800066,
+       0x0467f0f2,
+       0x07e407f1,
+       0xbd0006d0,
+/* 0x0569: memx_func_leave_wait */
+       0xc067f104,
+       0x0066cf07,
+       0xf40464f0,
+       0x67f1f61b,
+       0x77f126f0,
+       0x73f00001,
+       0x026eb900,
+       0xb90421f4,
+       0x87fd02d8,
+       0xf960f905,
+       0xfcd0fc80,
+       0x3321f4e0,
+       0x162067f1,
+       0xf4026eb9,
+       0xd8b90421,
+       0x0587fd02,
+       0x80f960f9,
+       0xe0fcd0fc,
+       0xf13321f4,
+       0xf00aa277,
+       0x6eb90073,
+       0x0421f402,
+       0xfd02d8b9,
+       0x60f90587,
+       0xd0fc80f9,
+       0x21f4e0fc,
+/* 0x05d3: memx_func_wait_vblank */
+       0xb600f833,
+       0x00f80410,
+/* 0x05d8: memx_func_wr32 */
+       0x98001698,
+       0x10b60115,
+       0xf960f908,
+       0xfcd0fc50,
+       0x3321f4e0,
+       0xf40242b6,
+       0x00f8e91b,
+/* 0x05f4: memx_func_wait */
+       0xcf2c87f0,
+       0x1e980088,
+       0x011d9800,
+       0x98021c98,
+       0x10b6031b,
+       0x8621f410,
+/* 0x060e: memx_func_delay */
+       0x1e9800f8,
+       0x0410b600,
+       0xf86721f4,
+/* 0x0619: memx_func_train */
+/* 0x061b: memx_exec */
+       0xf900f800,
+       0xb9d0f9e0,
+       0xb2b902c1,
+/* 0x0625: memx_exec_next */
+       0x00139802,
+       0xe70410b6,
+       0xe701f034,
+       0xb601e033,
+       0x30f00132,
+       0xde35980c,
+       0x12b855f9,
+       0xe41ef406,
+       0x98f10b98,
+       0xcbbbf20c,
+       0xc4b7f102,
+       0x00bbcf07,
+       0xe0fcd0fc,
+       0x02f121f5,
+/* 0x065e: memx_info */
+       0xc67000f8,
+       0x0e0bf401,
+/* 0x0664: memx_info_data */
+       0x03ccc7f1,
+       0x0800b7f1,
+/* 0x066f: memx_info_train */
+       0xf10b0ef4,
+       0xf10bccc7,
+/* 0x0677: memx_info_send */
+       0xf50100b7,
+       0xf802f121,
+/* 0x067d: memx_recv */
+       0x01d6b000,
+       0xb09b0bf4,
+       0x0bf400d6,
+/* 0x068b: memx_init */
+       0xf800f8d8,
+/* 0x068d: perf_recv */
+/* 0x068f: perf_init */
+       0xf800f800,
+/* 0x0691: i2c_drive_scl */
+       0x0036b000,
+       0xf10e0bf4,
+       0xd007e007,
+       0x04bd0001,
+/* 0x06a2: i2c_drive_scl_lo */
+       0x07f100f8,
+       0x01d007e4,
+       0xf804bd00,
+/* 0x06ad: i2c_drive_sda */
+       0x0036b000,
+       0xf10e0bf4,
+       0xd007e007,
+       0x04bd0002,
+/* 0x06be: i2c_drive_sda_lo */
+       0x07f100f8,
+       0x02d007e4,
+       0xf804bd00,
+/* 0x06c9: i2c_sense_scl */
+       0x0132f400,
+       0x07c437f1,
+       0xfd0033cf,
+       0x0bf40431,
+       0x0131f406,
+/* 0x06dc: i2c_sense_scl_done */
+/* 0x06de: i2c_sense_sda */
+       0x32f400f8,
+       0xc437f101,
+       0x0033cf07,
+       0xf40432fd,
+       0x31f4060b,
+/* 0x06f1: i2c_sense_sda_done */
+/* 0x06f3: i2c_raise_scl */
+       0xf900f801,
+       0x9847f140,
+       0x0137f008,
+       0x069121f5,
+/* 0x0700: i2c_raise_scl_wait */
+       0x03e8e7f1,
+       0xf56721f4,
+       0xf406c921,
+       0x42b60901,
+       0xef1bf401,
+/* 0x0714: i2c_raise_scl_done */
+       0x00f840fc,
+/* 0x0718: i2c_start */
+       0x06c921f5,
+       0xf50d11f4,
+       0xf406de21,
+       0x0ef40611,
+/* 0x0729: i2c_start_rep */
+       0x0037f030,
+       0x069121f5,
+       0xf50137f0,
+       0xbb06ad21,
+       0x65b60076,
+       0x9450f904,
+       0x56bb0465,
+       0xfd50bd02,
+       0x50fc0475,
+       0x06f321f5,
+       0xf40464b6,
+/* 0x0756: i2c_start_send */
+       0x37f01f11,
+       0xad21f500,
+       0x88e7f106,
+       0x6721f413,
+       0xf50037f0,
+       0xf1069121,
+       0xf41388e7,
+/* 0x0772: i2c_start_out */
+       0x00f86721,
+/* 0x0774: i2c_stop */
+       0xf50037f0,
+       0xf0069121,
+       0x21f50037,
+       0xe7f106ad,
+       0x21f403e8,
+       0x0137f067,
+       0x069121f5,
+       0x1388e7f1,
+       0xf06721f4,
+       0x21f50137,
+       0xe7f106ad,
+       0x21f41388,
+/* 0x07a7: i2c_bitw */
+       0xf500f867,
+       0xf106ad21,
+       0xf403e8e7,
+       0x76bb6721,
+       0x0465b600,
+       0x659450f9,
+       0x0256bb04,
+       0x75fd50bd,
+       0xf550fc04,
+       0xb606f321,
+       0x11f40464,
+       0x88e7f118,
+       0x6721f413,
+       0xf50037f0,
+       0xf1069121,
+       0xf41388e7,
+/* 0x07e6: i2c_bitw_out */
+       0x00f86721,
+/* 0x07e8: i2c_bitr */
+       0xf50137f0,
+       0xf106ad21,
+       0xf403e8e7,
+       0x76bb6721,
+       0x0465b600,
+       0x659450f9,
+       0x0256bb04,
+       0x75fd50bd,
+       0xf550fc04,
+       0xb606f321,
+       0x11f40464,
+       0xde21f51b,
+       0x0037f006,
+       0x069121f5,
+       0x1388e7f1,
+       0xf06721f4,
+       0x31f4013c,
+/* 0x082d: i2c_bitr_done */
+/* 0x082f: i2c_get_byte */
+       0xf000f801,
+       0x47f00057,
+/* 0x0835: i2c_get_byte_next */
+       0x0154b608,
+       0xb60076bb,
+       0x50f90465,
+       0xbb046594,
+       0x50bd0256,
+       0xfc0475fd,
+       0xe821f550,
+       0x0464b607,
+       0xfd2b11f4,
+       0x42b60553,
+       0xd81bf401,
+       0xbb0137f0,
+       0x65b60076,
+       0x9450f904,
+       0x56bb0465,
+       0xfd50bd02,
+       0x50fc0475,
+       0x07a721f5,
+/* 0x087f: i2c_get_byte_done */
+       0xf80464b6,
+/* 0x0881: i2c_put_byte */
+       0x0847f000,
+/* 0x0884: i2c_put_byte_next */
+       0xff0142b6,
+       0x76bb3854,
+       0x0465b600,
+       0x659450f9,
+       0x0256bb04,
+       0x75fd50bd,
+       0xf550fc04,
+       0xb607a721,
+       0x11f40464,
+       0x0046b034,
+       0xbbd81bf4,
+       0x65b60076,
+       0x9450f904,
+       0x56bb0465,
+       0xfd50bd02,
+       0x50fc0475,
+       0x07e821f5,
+       0xf40464b6,
+       0x76bb0f11,
+       0x0136b000,
+       0xf4061bf4,
+/* 0x08da: i2c_put_byte_done */
+       0x00f80132,
+/* 0x08dc: i2c_addr */
+       0xb60076bb,
+       0x50f90465,
+       0xbb046594,
+       0x50bd0256,
+       0xfc0475fd,
+       0x1821f550,
+       0x0464b607,
+       0xe72911f4,
+       0xb6012ec3,
+       0x53fd0134,
+       0x0076bb05,
+       0xf90465b6,
+       0x04659450,
+       0xbd0256bb,
+       0x0475fd50,
+       0x21f550fc,
+       0x64b60881,
+/* 0x0921: i2c_addr_done */
+/* 0x0923: i2c_acquire_addr */
+       0xc700f804,
+       0xe4b6f8ce,
+       0x14e0b705,
+/* 0x092f: i2c_acquire */
+       0xf500f8d0,
+       0xf4092321,
+       0xd9f00421,
+       0x3321f403,
+/* 0x093e: i2c_release */
+       0x21f500f8,
+       0x21f40923,
+       0x03daf004,
+       0xf83321f4,
+/* 0x094d: i2c_recv */
+       0x0132f400,
+       0xb6f8c1c7,
+       0x16b00214,
+       0x3a1ff528,
+       0xf413a001,
+       0x0032980c,
+       0x0ccc13a0,
+       0xf4003198,
+       0xd0f90231,
+       0xd0f9e0f9,
+       0x000067f1,
+       0x100063f1,
+       0xbb016792,
+       0x65b60076,
+       0x9450f904,
+       0x56bb0465,
+       0xfd50bd02,
+       0x50fc0475,
+       0x092f21f5,
+       0xfc0464b6,
+       0x00d6b0d0,
+       0x00b31bf5,
+       0xbb0057f0,
+       0x65b60076,
+       0x9450f904,
+       0x56bb0465,
+       0xfd50bd02,
+       0x50fc0475,
+       0x08dc21f5,
+       0xf50464b6,
+       0xc700d011,
+       0x76bbe0c5,
+       0x0465b600,
+       0x659450f9,
+       0x0256bb04,
+       0x75fd50bd,
+       0xf550fc04,
+       0xb6088121,
+       0x11f50464,
+       0x57f000ad,
+       0x0076bb01,
+       0xf90465b6,
+       0x04659450,
+       0xbd0256bb,
+       0x0475fd50,
+       0x21f550fc,
+       0x64b608dc,
+       0x8a11f504,
+       0x0076bb00,
+       0xf90465b6,
+       0x04659450,
+       0xbd0256bb,
+       0x0475fd50,
+       0x21f550fc,
+       0x64b6082f,
+       0x6a11f404,
+       0xbbe05bcb,
+       0x65b60076,
+       0x9450f904,
+       0x56bb0465,
+       0xfd50bd02,
+       0x50fc0475,
+       0x077421f5,
+       0xb90464b6,
+       0x74bd025b,
+/* 0x0a53: i2c_recv_not_rd08 */
+       0xb0430ef4,
+       0x1bf401d6,
+       0x0057f03d,
+       0x08dc21f5,
+       0xc73311f4,
+       0x21f5e0c5,
+       0x11f40881,
+       0x0057f029,
+       0x08dc21f5,
+       0xc71f11f4,
+       0x21f5e0b5,
+       0x11f40881,
+       0x7421f515,
+       0xc774bd07,
+       0x1bf408c5,
+       0x0232f409,
+/* 0x0a93: i2c_recv_not_wr08 */
+/* 0x0a93: i2c_recv_done */
+       0xc7030ef4,
+       0x21f5f8ce,
+       0xe0fc093e,
+       0x12f4d0fc,
+       0x027cb90a,
+       0x02f121f5,
+/* 0x0aa8: i2c_recv_exit */
+/* 0x0aaa: i2c_init */
+       0x00f800f8,
+/* 0x0aac: test_recv */
+       0x05d817f1,
+       0xb60011cf,
+       0x07f10110,
+       0x01d005d8,
+       0xf104bd00,
+       0xf1d900e7,
+       0xf5134fe3,
+       0xf8022321,
+/* 0x0acd: test_init */
+       0x00e7f100,
+       0x2321f508,
+/* 0x0ad7: idle_recv */
+       0xf800f802,
+/* 0x0ad9: idle */
+       0x0031f400,
+       0x05d417f1,
+       0xb60011cf,
+       0x07f10110,
+       0x01d005d4,
+/* 0x0aef: idle_loop */
+       0xf004bd00,
+       0x32f45817,
+/* 0x0af5: idle_proc */
+/* 0x0af5: idle_proc_exec */
+       0xb910f902,
+       0x21f5021e,
+       0x10fc02fa,
+       0xf40911f4,
+       0x0ef40231,
+/* 0x0b09: idle_proc_next */
+       0x5810b6ef,
+       0xf4061fb8,
+       0x02f4e61b,
+       0x0028f4dd,
+       0x00c10ef4,
+       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,
+};
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/pmu/fuc/gk208.fuc5 b/drivers/gpu/drm/nouveau/nvkm/subdev/pmu/fuc/gk208.fuc5
new file mode 100644 (file)
index 0000000..093dc81
--- /dev/null
@@ -0,0 +1,70 @@
+/*
+ * Copyright 2013 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 NVKM_PPWR_CHIPSET GK208
+#define HW_TICKS_PER_US 324
+
+#define NVKM_FALCON_PC24
+#define NVKM_FALCON_UNSHIFTED_IO
+//#define NVKM_FALCON_MMIO_UAS
+//#define NVKM_FALCON_MMIO_TRAP
+
+#include "macros.fuc"
+
+.section #gk208_pmu_data
+#define INCLUDE_PROC
+#include "kernel.fuc"
+#include "arith.fuc"
+#include "host.fuc"
+#include "memx.fuc"
+#include "perf.fuc"
+#include "i2c_.fuc"
+#include "test.fuc"
+#include "idle.fuc"
+#undef INCLUDE_PROC
+
+#define INCLUDE_DATA
+#include "kernel.fuc"
+#include "arith.fuc"
+#include "host.fuc"
+#include "memx.fuc"
+#include "perf.fuc"
+#include "i2c_.fuc"
+#include "test.fuc"
+#include "idle.fuc"
+#undef INCLUDE_DATA
+.align 256
+
+.section #gk208_pmu_code
+#define INCLUDE_CODE
+#include "kernel.fuc"
+#include "arith.fuc"
+#include "host.fuc"
+#include "memx.fuc"
+#include "perf.fuc"
+#include "i2c_.fuc"
+#include "test.fuc"
+#include "idle.fuc"
+#undef INCLUDE_CODE
+.align 256
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/pmu/fuc/gk208.fuc5.h b/drivers/gpu/drm/nouveau/nvkm/subdev/pmu/fuc/gk208.fuc5.h
new file mode 100644 (file)
index 0000000..fe4f63d
--- /dev/null
@@ -0,0 +1,1731 @@
+uint32_t gk208_pmu_data[] = {
+/* 0x0000: proc_kern */
+       0x52544e49,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+/* 0x0058: proc_list_head */
+       0x54534f48,
+       0x00000453,
+       0x00000404,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x584d454d,
+       0x0000062d,
+       0x0000061f,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x46524550,
+       0x00000631,
+       0x0000062f,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x5f433249,
+       0x00000a35,
+       0x000008dc,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x54534554,
+       0x00000a56,
+       0x00000a37,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x454c4449,
+       0x00000a61,
+       0x00000a5f,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+/* 0x0268: proc_list_tail */
+/* 0x0268: time_prev */
+       0x00000000,
+/* 0x026c: time_next */
+       0x00000000,
+/* 0x0270: fifo_queue */
+       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,
+/* 0x02f0: rfifo_queue */
+       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,
+/* 0x0370: memx_func_head */
+       0x00000001,
+       0x00000000,
+       0x00000483,
+/* 0x037c: memx_func_next */
+       0x00000002,
+       0x00000000,
+       0x00000500,
+       0x00000003,
+       0x00000002,
+       0x00000580,
+       0x00040004,
+       0x00000000,
+       0x0000059d,
+       0x00010005,
+       0x00000000,
+       0x000005b7,
+       0x00010006,
+       0x00000000,
+       0x0000057b,
+       0x00000007,
+       0x00000000,
+       0x000005c3,
+/* 0x03c4: memx_func_tail */
+/* 0x03c4: memx_ts_start */
+       0x00000000,
+/* 0x03c8: memx_ts_end */
+       0x00000000,
+/* 0x03cc: memx_data_head */
+       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,
+       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,
+       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,
+       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,
+       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,
+       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,
+       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,
+       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,
+/* 0x0bcc: memx_data_tail */
+/* 0x0bcc: memx_train_head */
+       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,
+/* 0x0ccc: memx_train_tail */
+/* 0x0ccc: i2c_scl_map */
+       0x00000400,
+       0x00000800,
+       0x00001000,
+       0x00002000,
+       0x00004000,
+       0x00008000,
+       0x00010000,
+       0x00020000,
+       0x00040000,
+       0x00080000,
+/* 0x0cf4: i2c_sda_map */
+       0x00100000,
+       0x00200000,
+       0x00400000,
+       0x00800000,
+       0x01000000,
+       0x02000000,
+       0x04000000,
+       0x08000000,
+       0x10000000,
+       0x20000000,
+       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,
+};
+
+uint32_t gk208_pmu_code[] = {
+       0x031c0ef5,
+/* 0x0004: rd32 */
+       0xf607a040,
+       0x04bd000e,
+       0xd3f0010d,
+       0x07ac4001,
+       0xbd000df6,
+/* 0x0019: rd32_wait */
+       0x07ac4d04,
+       0xf100ddcf,
+       0xf47000d4,
+       0xa44df61b,
+       0x00ddcf07,
+/* 0x002e: wr32 */
+       0xa04000f8,
+       0x000ef607,
+       0xa44004bd,
+       0x000df607,
+       0x020d04bd,
+       0xf0f0d5f0,
+       0xac4001d3,
+       0x000df607,
+/* 0x004e: wr32_wait */
+       0xac4d04bd,
+       0x00ddcf07,
+       0x7000d4f1,
+       0xf8f61bf4,
+/* 0x005d: nsec */
+       0xf990f900,
+       0xcf2c0880,
+/* 0x0066: nsec_loop */
+       0x2c090088,
+       0xbb0099cf,
+       0x9ea60298,
+       0xfcf61ef4,
+       0xf890fc80,
+/* 0x0079: wait */
+       0xf990f900,
+       0xcf2c0880,
+/* 0x0082: wait_loop */
+       0xeeb20088,
+       0x0000047e,
+       0xadfddab2,
+       0xf4aca604,
+       0x2c09100b,
+       0xbb0099cf,
+       0x9ba60298,
+/* 0x009f: wait_done */
+       0xfce61ef4,
+       0xf890fc80,
+/* 0x00a5: intr_watchdog */
+       0x03e99800,
+       0xf40096b0,
+       0x0a98280b,
+       0x029abb9a,
+       0x0d0e1cf4,
+       0x02617e01,
+       0xf494bd00,
+/* 0x00c2: intr_watchdog_next_time */
+       0x0a98140e,
+       0x00a6b09b,
+       0xa6080bf4,
+       0x061cf49a,
+/* 0x00d0: intr_watchdog_next_time_set */
+/* 0x00d3: intr_watchdog_next_proc */
+       0xb59b09b5,
+       0xe0b603e9,
+       0x68e6b158,
+       0xc81bf402,
+/* 0x00e2: intr */
+       0x00f900f8,
+       0x80f904bd,
+       0xa0f990f9,
+       0xc0f9b0f9,
+       0xe0f9d0f9,
+       0x000ff0f9,
+       0xf90188fe,
+       0x04504880,
+       0xb60088cf,
+       0x50400180,
+       0x0008f604,
+       0x080804bd,
+       0xc40088cf,
+       0x0bf40289,
+       0x9b00b51f,
+       0xa57e580e,
+       0x09980000,
+       0x0096b09b,
+       0x000d0bf4,
+       0x0009f634,
+       0x09b504bd,
+/* 0x0135: intr_skip_watchdog */
+       0x0089e49a,
+       0x360bf408,
+       0xcf068849,
+       0x9ac40099,
+       0x220bf402,
+       0xcf04c04c,
+       0xc0f900cc,
+       0xf14f484e,
+       0x0d5453e3,
+       0x02c27e00,
+       0x40c0fc00,
+       0x0cf604c0,
+/* 0x0167: intr_subintr_skip_fifo */
+       0x4004bd00,
+       0x09f60688,
+/* 0x016f: intr_skip_subintr */
+       0xc404bd00,
+       0x0bf42089,
+       0xbfa4f107,
+/* 0x0179: intr_skip_pause */
+       0x4089c4ff,
+       0xf1070bf4,
+/* 0x0183: intr_skip_user0 */
+       0x00ffbfa4,
+       0x0008f604,
+       0x80fc04bd,
+       0xfc0088fe,
+       0xfce0fcf0,
+       0xfcc0fcd0,
+       0xfca0fcb0,
+       0xfc80fc90,
+       0x0032f400,
+/* 0x01a6: ticks_from_ns */
+       0xc0f901f8,
+       0xd7f1b0f9,
+       0xd3f00144,
+       0x7721f500,
+       0xe8ccec03,
+       0x00b4b003,
+       0xec120bf4,
+       0xf103e8ee,
+       0xf00144d7,
+       0x21f500d3,
+/* 0x01ce: ticks_from_ns_quit */
+       0xceb20377,
+       0xc0fcb0fc,
+/* 0x01d6: ticks_from_us */
+       0xc0f900f8,
+       0xd7f1b0f9,
+       0xd3f00144,
+       0x7721f500,
+       0xb0ceb203,
+       0x0bf400b4,
+/* 0x01ef: ticks_from_us_quit */
+       0xfce4bd05,
+       0xf8c0fcb0,
+/* 0x01f5: ticks_to_us */
+       0x44d7f100,
+       0x00d3f001,
+       0xf8ecedff,
+/* 0x0201: timer */
+       0xf990f900,
+       0x1032f480,
+       0xb003f898,
+       0x1cf40086,
+       0x0084bd4a,
+       0x0008f638,
+       0x340804bd,
+       0x980088cf,
+       0x98bb9a09,
+       0x00e9bb02,
+       0x0803feb5,
+       0x0088cf08,
+       0xf40284f0,
+       0x34081c1b,
+       0xa60088cf,
+       0x080bf4e0,
+       0x1cf4e8a6,
+/* 0x0245: timer_reset */
+       0xf634000d,
+       0x04bd000e,
+/* 0x024f: timer_enable */
+       0x089a0eb5,
+       0xf6380001,
+       0x04bd0008,
+/* 0x0258: timer_done */
+       0xfc1031f4,
+       0xf890fc80,
+/* 0x0261: send_proc */
+       0xf980f900,
+       0x05e89890,
+       0xf004e998,
+       0x89a60486,
+       0xc42a0bf4,
+       0x88940398,
+       0x1880b604,
+       0x98008ebb,
+       0x8ab500fa,
+       0x018db500,
+       0xb5028cb5,
+       0x90b6038b,
+       0x0794f001,
+       0xf404e9b5,
+/* 0x029a: send_done */
+       0x90fc0231,
+       0x00f880fc,
+/* 0x02a0: find */
+       0x580880f9,
+/* 0x02a7: find_loop */
+       0x980131f4,
+       0xaea6008a,
+       0xb6100bf4,
+       0x86b15880,
+       0x1bf40268,
+       0x0132f4f1,
+/* 0x02bc: find_done */
+       0x80fc8eb2,
+/* 0x02c2: send */
+       0xa07e00f8,
+       0x01f40002,
+/* 0x02cb: recv */
+       0xf900f89b,
+       0x9880f990,
+       0xe99805e8,
+       0x0132f404,
+       0x0bf489a6,
+       0x0389c43c,
+       0xf00180b6,
+       0xe8b50784,
+       0x02ea9805,
+       0x8ffef0f9,
+       0xb2f0f901,
+       0x049994ef,
+       0xb600e9bb,
+       0xeb9818e0,
+       0x02ec9803,
+       0x9801ed98,
+       0xa5f900ee,
+       0xf8fef0fc,
+       0x0131f400,
+/* 0x0316: recv_done */
+       0x80fcf0fc,
+       0x00f890fc,
+/* 0x031c: init */
+       0xcf010841,
+       0x11e70011,
+       0x14b60109,
+       0x0014fe08,
+       0xf000e041,
+       0x1c000013,
+       0xbd0001f6,
+       0x00ff0104,
+       0x0001f614,
+       0x020104bd,
+       0x080015f1,
+       0x01f61000,
+       0x4104bd00,
+       0x13f000e2,
+       0x0010fe00,
+       0x011031f4,
+       0xf6380001,
+       0x04bd0001,
+/* 0x0366: init_proc */
+       0xf198580f,
+       0x0016b001,
+       0xf9fa0bf4,
+       0x58f0b615,
+/* 0x0377: mulu32_32_64 */
+       0xf9f20ef4,
+       0xf920f910,
+       0x9540f930,
+       0xd29510e1,
+       0xbdc4bd10,
+       0xc0edffb4,
+       0xb2301dff,
+       0xff34f134,
+       0x1034b6ff,
+       0xbb1045b6,
+       0xb4bb00c3,
+       0x30e2ff01,
+       0x34f134b2,
+       0x34b6ffff,
+       0x1045b610,
+       0xbb00c3bb,
+       0x12ff01b4,
+       0x00b3bb30,
+       0x30fc40fc,
+       0x10fc20fc,
+/* 0x03c6: host_send */
+       0xb04100f8,
+       0x0011cf04,
+       0xcf04a042,
+       0x12a60022,
+       0xc42e0bf4,
+       0xee94071e,
+       0x70e0b704,
+       0x03eb9802,
+       0x9802ec98,
+       0xee9801ed,
+       0x02c27e00,
+       0x0110b600,
+       0x400f1ec4,
+       0x0ef604b0,
+       0xf404bd00,
+/* 0x0402: host_send_done */
+       0x00f8c70e,
+/* 0x0404: host_recv */
+       0xf14e4941,
+       0xa6525413,
+       0xb90bf4e1,
+/* 0x0410: host_recv_wait */
+       0xcf04cc41,
+       0xc8420011,
+       0x0022cf04,
+       0xa60816f0,
+       0xef0bf412,
+       0xb60723c4,
+       0x30b70434,
+       0x3bb502f0,
+       0x023cb503,
+       0xb5013db5,
+       0x20b6003e,
+       0x0f24f001,
+       0xf604c840,
+       0x04bd0002,
+       0x00004002,
+       0xbd0002f6,
+/* 0x0453: host_init */
+       0x4100f804,
+       0x14b60080,
+       0x7015f110,
+       0x04d04002,
+       0xbd0001f6,
+       0x00804104,
+       0xf11014b6,
+       0x4002f015,
+       0x01f604dc,
+       0x0104bd00,
+       0x04c44001,
+       0xbd0001f6,
+/* 0x0483: memx_func_enter */
+       0xf100f804,
+       0xf1162067,
+       0xf1f55d77,
+       0xb2ffff73,
+       0x00047e6e,
+       0xfdd8b200,
+       0x60f90487,
+       0xd0fc80f9,
+       0x2e7ee0fc,
+       0x77f10000,
+       0x73f1fffe,
+       0x6eb2ffff,
+       0x0000047e,
+       0x87fdd8b2,
+       0xf960f904,
+       0xfcd0fc80,
+       0x002e7ee0,
+       0xf067f100,
+       0x7e6eb226,
+       0xb2000004,
+       0x0487fdd8,
+       0x80f960f9,
+       0xe0fcd0fc,
+       0x00002e7e,
+       0xe0400406,
+       0x0006f607,
+/* 0x04ea: memx_func_enter_wait */
+       0xc04604bd,
+       0x0066cf07,
+       0xf40464f0,
+       0x2c06f70b,
+       0xb50066cf,
+       0x00f8f106,
+/* 0x0500: memx_func_leave */
+       0x66cf2c06,
+       0xf206b500,
+       0xe4400406,
+       0x0006f607,
+/* 0x0512: memx_func_leave_wait */
+       0xc04604bd,
+       0x0066cf07,
+       0xf40464f0,
+       0x67f1f71b,
+       0x77f126f0,
+       0x73f00001,
+       0x7e6eb200,
+       0xb2000004,
+       0x0587fdd8,
+       0x80f960f9,
+       0xe0fcd0fc,
+       0x00002e7e,
+       0x162067f1,
+       0x047e6eb2,
+       0xd8b20000,
+       0xf90587fd,
+       0xfc80f960,
+       0x7ee0fcd0,
+       0xf100002e,
+       0xf00aa277,
+       0x6eb20073,
+       0x0000047e,
+       0x87fdd8b2,
+       0xf960f905,
+       0xfcd0fc80,
+       0x002e7ee0,
+/* 0x057b: memx_func_wait_vblank */
+       0xb600f800,
+       0x00f80410,
+/* 0x0580: memx_func_wr32 */
+       0x98001698,
+       0x10b60115,
+       0xf960f908,
+       0xfcd0fc50,
+       0x002e7ee0,
+       0x0242b600,
+       0xf8e81bf4,
+/* 0x059d: memx_func_wait */
+       0xcf2c0800,
+       0x1e980088,
+       0x011d9800,
+       0x98021c98,
+       0x10b6031b,
+       0x00797e10,
+/* 0x05b7: memx_func_delay */
+       0x9800f800,
+       0x10b6001e,
+       0x005d7e04,
+/* 0x05c3: memx_func_train */
+       0xf800f800,
+/* 0x05c5: memx_exec */
+       0xf9e0f900,
+       0xb2c1b2d0,
+/* 0x05cd: memx_exec_next */
+       0x001398b2,
+       0xe70410b6,
+       0xe701f034,
+       0xb601e033,
+       0x30f00132,
+       0xde35980c,
+       0x12a655f9,
+       0x98e51ef4,
+       0x0c98f10b,
+       0x02cbbbf2,
+       0xcf07c44b,
+       0xd0fc00bb,
+       0xc27ee0fc,
+       0x00f80002,
+/* 0x0604: memx_info */
+       0xf401c670,
+/* 0x060a: memx_info_data */
+       0xcc4c0c0b,
+       0x08004b03,
+/* 0x0613: memx_info_train */
+       0x4c090ef4,
+       0x004b0bcc,
+/* 0x0619: memx_info_send */
+       0x02c27e01,
+/* 0x061f: memx_recv */
+       0xb000f800,
+       0x0bf401d6,
+       0x00d6b0a3,
+       0xf8dc0bf4,
+/* 0x062d: memx_init */
+/* 0x062f: perf_recv */
+       0xf800f800,
+/* 0x0631: perf_init */
+/* 0x0633: i2c_drive_scl */
+       0xb000f800,
+       0x0bf40036,
+       0x07e0400d,
+       0xbd0001f6,
+/* 0x0643: i2c_drive_scl_lo */
+       0x4000f804,
+       0x01f607e4,
+       0xf804bd00,
+/* 0x064d: i2c_drive_sda */
+       0x0036b000,
+       0x400d0bf4,
+       0x02f607e0,
+       0xf804bd00,
+/* 0x065d: i2c_drive_sda_lo */
+       0x07e44000,
+       0xbd0002f6,
+/* 0x0667: i2c_sense_scl */
+       0xf400f804,
+       0xc4430132,
+       0x0033cf07,
+       0xf40431fd,
+       0x31f4060b,
+/* 0x0679: i2c_sense_scl_done */
+/* 0x067b: i2c_sense_sda */
+       0xf400f801,
+       0xc4430132,
+       0x0033cf07,
+       0xf40432fd,
+       0x31f4060b,
+/* 0x068d: i2c_sense_sda_done */
+/* 0x068f: i2c_raise_scl */
+       0xf900f801,
+       0x08984440,
+       0x337e0103,
+/* 0x069a: i2c_raise_scl_wait */
+       0xe84e0006,
+       0x005d7e03,
+       0x06677e00,
+       0x0901f400,
+       0xf40142b6,
+/* 0x06ae: i2c_raise_scl_done */
+       0x40fcef1b,
+/* 0x06b2: i2c_start */
+       0x677e00f8,
+       0x11f40006,
+       0x067b7e0d,
+       0x0611f400,
+/* 0x06c3: i2c_start_rep */
+       0x032e0ef4,
+       0x06337e00,
+       0x7e010300,
+       0xbb00064d,
+       0x65b60076,
+       0x9450f904,
+       0x56bb0465,
+       0xfd50bd02,
+       0x50fc0475,
+       0x00068f7e,
+       0xf40464b6,
+/* 0x06ee: i2c_start_send */
+       0x00031d11,
+       0x00064d7e,
+       0x7e13884e,
+       0x0300005d,
+       0x06337e00,
+       0x13884e00,
+       0x00005d7e,
+/* 0x0708: i2c_start_out */
+/* 0x070a: i2c_stop */
+       0x000300f8,
+       0x0006337e,
+       0x4d7e0003,
+       0xe84e0006,
+       0x005d7e03,
+       0x7e010300,
+       0x4e000633,
+       0x5d7e1388,
+       0x01030000,
+       0x00064d7e,
+       0x7e13884e,
+       0xf800005d,
+/* 0x0739: i2c_bitw */
+       0x064d7e00,
+       0x03e84e00,
+       0x00005d7e,
+       0xb60076bb,
+       0x50f90465,
+       0xbb046594,
+       0x50bd0256,
+       0xfc0475fd,
+       0x068f7e50,
+       0x0464b600,
+       0x4e1711f4,
+       0x5d7e1388,
+       0x00030000,
+       0x0006337e,
+       0x7e13884e,
+/* 0x0777: i2c_bitw_out */
+       0xf800005d,
+/* 0x0779: i2c_bitr */
+       0x7e010300,
+       0x4e00064d,
+       0x5d7e03e8,
+       0x76bb0000,
+       0x0465b600,
+       0x659450f9,
+       0x0256bb04,
+       0x75fd50bd,
+       0x7e50fc04,
+       0xb600068f,
+       0x11f40464,
+       0x067b7e1a,
+       0x7e000300,
+       0x4e000633,
+       0x5d7e1388,
+       0x3cf00000,
+       0x0131f401,
+/* 0x07bc: i2c_bitr_done */
+/* 0x07be: i2c_get_byte */
+       0x000500f8,
+/* 0x07c2: i2c_get_byte_next */
+       0x54b60804,
+       0x0076bb01,
+       0xf90465b6,
+       0x04659450,
+       0xbd0256bb,
+       0x0475fd50,
+       0x797e50fc,
+       0x64b60007,
+       0x2a11f404,
+       0xb60553fd,
+       0x1bf40142,
+       0xbb0103d8,
+       0x65b60076,
+       0x9450f904,
+       0x56bb0465,
+       0xfd50bd02,
+       0x50fc0475,
+       0x0007397e,
+/* 0x080b: i2c_get_byte_done */
+       0xf80464b6,
+/* 0x080d: i2c_put_byte */
+/* 0x080f: i2c_put_byte_next */
+       0xb6080400,
+       0x54ff0142,
+       0x0076bb38,
+       0xf90465b6,
+       0x04659450,
+       0xbd0256bb,
+       0x0475fd50,
+       0x397e50fc,
+       0x64b60007,
+       0x3411f404,
+       0xf40046b0,
+       0x76bbd81b,
+       0x0465b600,
+       0x659450f9,
+       0x0256bb04,
+       0x75fd50bd,
+       0x7e50fc04,
+       0xb6000779,
+       0x11f40464,
+       0x0076bb0f,
+       0xf40136b0,
+       0x32f4061b,
+/* 0x0865: i2c_put_byte_done */
+/* 0x0867: i2c_addr */
+       0xbb00f801,
+       0x65b60076,
+       0x9450f904,
+       0x56bb0465,
+       0xfd50bd02,
+       0x50fc0475,
+       0x0006b27e,
+       0xf40464b6,
+       0xc3e72911,
+       0x34b6012e,
+       0x0553fd01,
+       0xb60076bb,
+       0x50f90465,
+       0xbb046594,
+       0x50bd0256,
+       0xfc0475fd,
+       0x080d7e50,
+       0x0464b600,
+/* 0x08ac: i2c_addr_done */
+/* 0x08ae: i2c_acquire_addr */
+       0xcec700f8,
+       0x05e4b6f8,
+       0xd014e0b7,
+/* 0x08ba: i2c_acquire */
+       0xae7e00f8,
+       0x047e0008,
+       0xd9f00000,
+       0x002e7e03,
+/* 0x08cb: i2c_release */
+       0x7e00f800,
+       0x7e0008ae,
+       0xf0000004,
+       0x2e7e03da,
+       0x00f80000,
+/* 0x08dc: i2c_recv */
+       0xc70132f4,
+       0x14b6f8c1,
+       0x2816b002,
+       0x01371ff5,
+       0x0cf413b8,
+       0x00329800,
+       0x0ccc13b8,
+       0x00319800,
+       0xf90231f4,
+       0xf9e0f9d0,
+       0x0067f1d0,
+       0x0063f100,
+       0x01679210,
+       0xb60076bb,
+       0x50f90465,
+       0xbb046594,
+       0x50bd0256,
+       0xfc0475fd,
+       0x08ba7e50,
+       0x0464b600,
+       0xd6b0d0fc,
+       0xb01bf500,
+       0xbb000500,
+       0x65b60076,
+       0x9450f904,
+       0x56bb0465,
+       0xfd50bd02,
+       0x50fc0475,
+       0x0008677e,
+       0xf50464b6,
+       0xc700cc11,
+       0x76bbe0c5,
+       0x0465b600,
+       0x659450f9,
+       0x0256bb04,
+       0x75fd50bd,
+       0x7e50fc04,
+       0xb600080d,
+       0x11f50464,
+       0x010500a9,
+       0xb60076bb,
+       0x50f90465,
+       0xbb046594,
+       0x50bd0256,
+       0xfc0475fd,
+       0x08677e50,
+       0x0464b600,
+       0x008711f5,
+       0xb60076bb,
+       0x50f90465,
+       0xbb046594,
+       0x50bd0256,
+       0xfc0475fd,
+       0x07be7e50,
+       0x0464b600,
+       0xcb6711f4,
+       0x76bbe05b,
+       0x0465b600,
+       0x659450f9,
+       0x0256bb04,
+       0x75fd50bd,
+       0x7e50fc04,
+       0xb600070a,
+       0x5bb20464,
+       0x0ef474bd,
+/* 0x09e1: i2c_recv_not_rd08 */
+       0x01d6b041,
+       0x053b1bf4,
+       0x08677e00,
+       0x3211f400,
+       0x7ee0c5c7,
+       0xf400080d,
+       0x00052811,
+       0x0008677e,
+       0xc71f11f4,
+       0x0d7ee0b5,
+       0x11f40008,
+       0x070a7e15,
+       0xc774bd00,
+       0x1bf408c5,
+       0x0232f409,
+/* 0x0a1f: i2c_recv_not_wr08 */
+/* 0x0a1f: i2c_recv_done */
+       0xc7030ef4,
+       0xcb7ef8ce,
+       0xe0fc0008,
+       0x12f4d0fc,
+       0x7e7cb209,
+/* 0x0a33: i2c_recv_exit */
+       0xf80002c2,
+/* 0x0a35: i2c_init */
+/* 0x0a37: test_recv */
+       0x4100f800,
+       0x11cf0458,
+       0x0110b600,
+       0xf6045840,
+       0x04bd0001,
+       0xd900e7f1,
+       0x134fe3f1,
+       0x0002017e,
+/* 0x0a56: test_init */
+       0x004e00f8,
+       0x02017e08,
+/* 0x0a5f: idle_recv */
+       0xf800f800,
+/* 0x0a61: idle */
+       0x0031f400,
+       0xcf045441,
+       0x10b60011,
+       0x04544001,
+       0xbd0001f6,
+/* 0x0a75: idle_loop */
+       0xf4580104,
+/* 0x0a7a: idle_proc */
+/* 0x0a7a: idle_proc_exec */
+       0x10f90232,
+       0xcb7e1eb2,
+       0x10fc0002,
+       0xf40911f4,
+       0x0ef40231,
+/* 0x0a8d: idle_proc_next */
+       0x5810b6f0,
+       0x1bf41fa6,
+       0xe002f4e8,
+       0xf40028f4,
+       0x0000c60e,
+       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/drivers/gpu/drm/nouveau/nvkm/subdev/pmu/fuc/gt215.fuc3 b/drivers/gpu/drm/nouveau/nvkm/subdev/pmu/fuc/gt215.fuc3
new file mode 100644 (file)
index 0000000..393049f
--- /dev/null
@@ -0,0 +1,70 @@
+/*
+ * Copyright 2013 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 NVKM_PPWR_CHIPSET GT215
+#define HW_TICKS_PER_US 203 // should be 202.5
+
+//#define NVKM_FALCON_PC24
+//#define NVKM_FALCON_UNSHIFTED_IO
+//#define NVKM_FALCON_MMIO_UAS
+//#define NVKM_FALCON_MMIO_TRAP
+
+#include "macros.fuc"
+
+.section #gt215_pmu_data
+#define INCLUDE_PROC
+#include "kernel.fuc"
+#include "arith.fuc"
+#include "host.fuc"
+#include "memx.fuc"
+#include "perf.fuc"
+#include "i2c_.fuc"
+#include "test.fuc"
+#include "idle.fuc"
+#undef INCLUDE_PROC
+
+#define INCLUDE_DATA
+#include "kernel.fuc"
+#include "arith.fuc"
+#include "host.fuc"
+#include "memx.fuc"
+#include "perf.fuc"
+#include "i2c_.fuc"
+#include "test.fuc"
+#include "idle.fuc"
+#undef INCLUDE_DATA
+.align 256
+
+.section #gt215_pmu_code
+#define INCLUDE_CODE
+#include "kernel.fuc"
+#include "arith.fuc"
+#include "host.fuc"
+#include "memx.fuc"
+#include "perf.fuc"
+#include "i2c_.fuc"
+#include "test.fuc"
+#include "idle.fuc"
+#undef INCLUDE_CODE
+.align 256
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/pmu/fuc/gt215.fuc3.h b/drivers/gpu/drm/nouveau/nvkm/subdev/pmu/fuc/gt215.fuc3.h
new file mode 100644 (file)
index 0000000..2686f8f
--- /dev/null
@@ -0,0 +1,1868 @@
+uint32_t gt215_pmu_data[] = {
+/* 0x0000: proc_kern */
+       0x52544e49,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+/* 0x0058: proc_list_head */
+       0x54534f48,
+       0x00000512,
+       0x000004af,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x584d454d,
+       0x00000842,
+       0x00000834,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x46524550,
+       0x00000846,
+       0x00000844,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x5f433249,
+       0x00000c76,
+       0x00000b19,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x54534554,
+       0x00000c9f,
+       0x00000c78,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x454c4449,
+       0x00000cab,
+       0x00000ca9,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+/* 0x0268: proc_list_tail */
+/* 0x0268: time_prev */
+       0x00000000,
+/* 0x026c: time_next */
+       0x00000000,
+/* 0x0270: fifo_queue */
+       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,
+/* 0x02f0: rfifo_queue */
+       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,
+/* 0x0370: memx_func_head */
+       0x00000001,
+       0x00000000,
+       0x00000551,
+/* 0x037c: memx_func_next */
+       0x00000002,
+       0x00000000,
+       0x000005a8,
+       0x00000003,
+       0x00000002,
+       0x0000063a,
+       0x00040004,
+       0x00000000,
+       0x00000656,
+       0x00010005,
+       0x00000000,
+       0x00000673,
+       0x00010006,
+       0x00000000,
+       0x000005f8,
+       0x00000007,
+       0x00000000,
+       0x0000067e,
+/* 0x03c4: memx_func_tail */
+/* 0x03c4: memx_ts_start */
+       0x00000000,
+/* 0x03c8: memx_ts_end */
+       0x00000000,
+/* 0x03cc: memx_data_head */
+       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,
+       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,
+       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,
+       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,
+       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,
+       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,
+       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,
+       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,
+/* 0x0bcc: memx_data_tail */
+/* 0x0bcc: memx_train_head */
+       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,
+/* 0x0ccc: memx_train_tail */
+/* 0x0ccc: i2c_scl_map */
+       0x00001000,
+       0x00004000,
+       0x00010000,
+       0x00000100,
+       0x00040000,
+       0x00100000,
+       0x00400000,
+       0x01000000,
+       0x04000000,
+       0x10000000,
+/* 0x0cf4: i2c_sda_map */
+       0x00002000,
+       0x00008000,
+       0x00020000,
+       0x00000200,
+       0x00080000,
+       0x00200000,
+       0x00800000,
+       0x02000000,
+       0x08000000,
+       0x20000000,
+/* 0x0d1c: i2c_ctrl */
+       0x0000e138,
+       0x0000e150,
+       0x0000e168,
+       0x0000e180,
+       0x0000e254,
+       0x0000e274,
+       0x0000e764,
+       0x0000e780,
+       0x0000e79c,
+       0x0000e7b8,
+       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,
+};
+
+uint32_t gt215_pmu_code[] = {
+       0x039e0ef5,
+/* 0x0004: rd32 */
+       0x07a007f1,
+       0xd00604b6,
+       0x04bd000e,
+       0xf001d7f0,
+       0x07f101d3,
+       0x04b607ac,
+       0x000dd006,
+/* 0x0022: rd32_wait */
+       0xd7f104bd,
+       0xd4b607ac,
+       0x00ddcf06,
+       0x7000d4f1,
+       0xf1f21bf4,
+       0xb607a4d7,
+       0xddcf06d4,
+/* 0x003f: wr32 */
+       0xf100f800,
+       0xb607a007,
+       0x0ed00604,
+       0xf104bd00,
+       0xb607a407,
+       0x0dd00604,
+       0xf004bd00,
+       0xd5f002d7,
+       0x01d3f0f0,
+       0x07ac07f1,
+       0xd00604b6,
+       0x04bd000d,
+/* 0x006c: wr32_wait */
+       0x07acd7f1,
+       0xcf06d4b6,
+       0xd4f100dd,
+       0x1bf47000,
+/* 0x007f: nsec */
+       0xf900f8f2,
+       0xf080f990,
+       0x84b62c87,
+       0x0088cf06,
+/* 0x008c: nsec_loop */
+       0xb62c97f0,
+       0x99cf0694,
+       0x0298bb00,
+       0xf4069eb8,
+       0x80fcf11e,
+       0x00f890fc,
+/* 0x00a4: wait */
+       0x80f990f9,
+       0xb62c87f0,
+       0x88cf0684,
+/* 0x00b1: wait_loop */
+       0x02eeb900,
+       0xb90421f4,
+       0xadfd02da,
+       0x06acb804,
+       0xf0150bf4,
+       0x94b62c97,
+       0x0099cf06,
+       0xb80298bb,
+       0x1ef4069b,
+/* 0x00d5: wait_done */
+       0xfc80fcdf,
+/* 0x00db: intr_watchdog */
+       0x9800f890,
+       0x96b003e9,
+       0x2a0bf400,
+       0xbb9a0a98,
+       0x1cf4029a,
+       0x01d7f00f,
+       0x02dd21f5,
+       0x0ef494bd,
+/* 0x00f9: intr_watchdog_next_time */
+       0x9b0a9815,
+       0xf400a6b0,
+       0x9ab8090b,
+       0x061cf406,
+/* 0x0108: intr_watchdog_next_time_set */
+/* 0x010b: intr_watchdog_next_proc */
+       0x809b0980,
+       0xe0b603e9,
+       0x68e6b158,
+       0xc61bf402,
+/* 0x011a: intr */
+       0x00f900f8,
+       0x80f904bd,
+       0xa0f990f9,
+       0xc0f9b0f9,
+       0xe0f9d0f9,
+       0xf7f0f0f9,
+       0x0188fe00,
+       0x87f180f9,
+       0x84b605d0,
+       0x0088cf06,
+       0xf10180b6,
+       0xb605d007,
+       0x08d00604,
+       0xf004bd00,
+       0x84b60887,
+       0x0088cf06,
+       0xf40289c4,
+       0x0080230b,
+       0x58e7f09b,
+       0x98db21f4,
+       0x96b09b09,
+       0x110bf400,
+       0xb63407f0,
+       0x09d00604,
+       0x8004bd00,
+/* 0x017e: intr_skip_watchdog */
+       0x89e49a09,
+       0x0bf40800,
+       0x8897f148,
+       0x0694b606,
+       0xc40099cf,
+       0x0bf4029a,
+       0xc0c7f12c,
+       0x06c4b604,
+       0xf900cccf,
+       0x48e7f1c0,
+       0x53e3f14f,
+       0x00d7f054,
+       0x034221f5,
+       0x07f1c0fc,
+       0x04b604c0,
+       0x000cd006,
+/* 0x01be: intr_subintr_skip_fifo */
+       0x07f104bd,
+       0x04b60688,
+       0x0009d006,
+/* 0x01ca: intr_skip_subintr */
+       0x89c404bd,
+       0x070bf420,
+       0xffbfa4f1,
+/* 0x01d4: intr_skip_pause */
+       0xf44089c4,
+       0xa4f1070b,
+/* 0x01de: intr_skip_user0 */
+       0x07f0ffbf,
+       0x0604b604,
+       0xbd0008d0,
+       0xfe80fc04,
+       0xf0fc0088,
+       0xd0fce0fc,
+       0xb0fcc0fc,
+       0x90fca0fc,
+       0x00fc80fc,
+       0xf80032f4,
+/* 0x0205: ticks_from_ns */
+       0xf9c0f901,
+       0xcbd7f1b0,
+       0x00d3f000,
+       0x041321f5,
+       0x03e8ccec,
+       0xf400b4b0,
+       0xeeec120b,
+       0xd7f103e8,
+       0xd3f000cb,
+       0x1321f500,
+/* 0x022d: ticks_from_ns_quit */
+       0x02ceb904,
+       0xc0fcb0fc,
+/* 0x0236: ticks_from_us */
+       0xc0f900f8,
+       0xd7f1b0f9,
+       0xd3f000cb,
+       0x1321f500,
+       0x02ceb904,
+       0xf400b4b0,
+       0xe4bd050b,
+/* 0x0250: ticks_from_us_quit */
+       0xc0fcb0fc,
+/* 0x0256: ticks_to_us */
+       0xd7f100f8,
+       0xd3f000cb,
+       0xecedff00,
+/* 0x0262: timer */
+       0x90f900f8,
+       0x32f480f9,
+       0x03f89810,
+       0xf40086b0,
+       0x84bd651c,
+       0xb63807f0,
+       0x08d00604,
+       0xf004bd00,
+       0x84b63487,
+       0x0088cf06,
+       0xbb9a0998,
+       0xe9bb0298,
+       0x03fe8000,
+       0xb60887f0,
+       0x88cf0684,
+       0x0284f000,
+       0xf0261bf4,
+       0x84b63487,
+       0x0088cf06,
+       0xf406e0b8,
+       0xe8b8090b,
+       0x111cf406,
+/* 0x02b8: timer_reset */
+       0xb63407f0,
+       0x0ed00604,
+       0x8004bd00,
+/* 0x02c6: timer_enable */
+       0x87f09a0e,
+       0x3807f001,
+       0xd00604b6,
+       0x04bd0008,
+/* 0x02d4: timer_done */
+       0xfc1031f4,
+       0xf890fc80,
+/* 0x02dd: send_proc */
+       0xf980f900,
+       0x05e89890,
+       0xf004e998,
+       0x89b80486,
+       0x2a0bf406,
+       0x940398c4,
+       0x80b60488,
+       0x008ebb18,
+       0x8000fa98,
+       0x8d80008a,
+       0x028c8001,
+       0xb6038b80,
+       0x94f00190,
+       0x04e98007,
+/* 0x0317: send_done */
+       0xfc0231f4,
+       0xf880fc90,
+/* 0x031d: find */
+       0xf080f900,
+       0x31f45887,
+/* 0x0325: find_loop */
+       0x008a9801,
+       0xf406aeb8,
+       0x80b6100b,
+       0x6886b158,
+       0xf01bf402,
+/* 0x033b: find_done */
+       0xb90132f4,
+       0x80fc028e,
+/* 0x0342: send */
+       0x21f500f8,
+       0x01f4031d,
+/* 0x034b: recv */
+       0xf900f897,
+       0x9880f990,
+       0xe99805e8,
+       0x0132f404,
+       0xf40689b8,
+       0x89c43d0b,
+       0x0180b603,
+       0x800784f0,
+       0xea9805e8,
+       0xfef0f902,
+       0xf0f9018f,
+       0x9402efb9,
+       0xe9bb0499,
+       0x18e0b600,
+       0x9803eb98,
+       0xed9802ec,
+       0x00ee9801,
+       0xf0fca5f9,
+       0xf400f8fe,
+       0xf0fc0131,
+/* 0x0398: recv_done */
+       0x90fc80fc,
+/* 0x039e: init */
+       0x17f100f8,
+       0x14b60108,
+       0x0011cf06,
+       0x010911e7,
+       0xfe0814b6,
+       0x17f10014,
+       0x13f000e0,
+       0x1c07f000,
+       0xd00604b6,
+       0x04bd0001,
+       0xf0ff17f0,
+       0x04b61407,
+       0x0001d006,
+       0x17f004bd,
+       0x0015f102,
+       0x1007f008,
+       0xd00604b6,
+       0x04bd0001,
+       0x011a17f1,
+       0xfe0013f0,
+       0x31f40010,
+       0x0117f010,
+       0xb63807f0,
+       0x01d00604,
+       0xf004bd00,
+/* 0x0402: init_proc */
+       0xf19858f7,
+       0x0016b001,
+       0xf9fa0bf4,
+       0x58f0b615,
+/* 0x0413: mulu32_32_64 */
+       0xf9f20ef4,
+       0xf920f910,
+       0x9540f930,
+       0xd29510e1,
+       0xbdc4bd10,
+       0xc0edffb4,
+       0xb9301dff,
+       0x34f10234,
+       0x34b6ffff,
+       0x1045b610,
+       0xbb00c3bb,
+       0xe2ff01b4,
+       0x0234b930,
+       0xffff34f1,
+       0xb61034b6,
+       0xc3bb1045,
+       0x01b4bb00,
+       0xbb3012ff,
+       0x40fc00b3,
+       0x20fc30fc,
+       0x00f810fc,
+/* 0x0464: host_send */
+       0x04b017f1,
+       0xcf0614b6,
+       0x27f10011,
+       0x24b604a0,
+       0x0022cf06,
+       0xf40612b8,
+       0x1ec4320b,
+       0x04ee9407,
+       0x0270e0b7,
+       0x9803eb98,
+       0xed9802ec,
+       0x00ee9801,
+       0x034221f5,
+       0xc40110b6,
+       0x07f10f1e,
+       0x04b604b0,
+       0x000ed006,
+       0x0ef404bd,
+/* 0x04ad: host_send_done */
+/* 0x04af: host_recv */
+       0xf100f8ba,
+       0xf14e4917,
+       0xb8525413,
+       0x0bf406e1,
+/* 0x04bd: host_recv_wait */
+       0xcc17f1aa,
+       0x0614b604,
+       0xf10011cf,
+       0xb604c827,
+       0x22cf0624,
+       0x0816f000,
+       0xf40612b8,
+       0x23c4e60b,
+       0x0434b607,
+       0x02f030b7,
+       0x80033b80,
+       0x3d80023c,
+       0x003e8001,
+       0xf00120b6,
+       0x07f10f24,
+       0x04b604c8,
+       0x0002d006,
+       0x27f004bd,
+       0x0007f040,
+       0xd00604b6,
+       0x04bd0002,
+/* 0x0512: host_init */
+       0x17f100f8,
+       0x14b60080,
+       0x7015f110,
+       0xd007f102,
+       0x0604b604,
+       0xbd0001d0,
+       0x8017f104,
+       0x1014b600,
+       0x02f015f1,
+       0x04dc07f1,
+       0xd00604b6,
+       0x04bd0001,
+       0xf10117f0,
+       0xb604c407,
+       0x01d00604,
+       0xf804bd00,
+/* 0x0551: memx_func_enter */
+       0x1087f100,
+       0x028eb916,
+       0xb90421f4,
+       0x67f102d7,
+       0x63f1fffc,
+       0x76fdffff,
+       0x0267f104,
+       0x0576fd00,
+       0x70f980f9,
+       0xe0fcd0fc,
+       0xf03f21f4,
+       0x07f10467,
+       0x04b607e0,
+       0x0006d006,
+/* 0x058a: memx_func_enter_wait */
+       0x67f104bd,
+       0x64b607c0,
+       0x0066cf06,
+       0xf40464f0,
+       0x67f0f30b,
+       0x0664b62c,
+       0x800066cf,
+       0x00f8f106,
+/* 0x05a8: memx_func_leave */
+       0xb62c67f0,
+       0x66cf0664,
+       0xf2068000,
+       0xf10467f0,
+       0xb607e407,
+       0x06d00604,
+/* 0x05c3: memx_func_leave_wait */
+       0xf104bd00,
+       0xb607c067,
+       0x66cf0664,
+       0x0464f000,
+       0xf1f31bf4,
+       0xb9161087,
+       0x21f4028e,
+       0x02d7b904,
+       0xffcc67f1,
+       0xffff63f1,
+       0xf90476fd,
+       0xfc70f980,
+       0xf4e0fcd0,
+       0x00f83f21,
+/* 0x05f8: memx_func_wait_vblank */
+       0xb0001698,
+       0x0bf40066,
+       0x0166b013,
+       0xf4060bf4,
+/* 0x060a: memx_func_wait_vblank_head1 */
+       0x77f12e0e,
+       0x0ef40020,
+/* 0x0611: memx_func_wait_vblank_head0 */
+       0x0877f107,
+/* 0x0615: memx_func_wait_vblank_0 */
+       0xc467f100,
+       0x0664b607,
+       0xfd0066cf,
+       0x1bf40467,
+/* 0x0625: memx_func_wait_vblank_1 */
+       0xc467f1f3,
+       0x0664b607,
+       0xfd0066cf,
+       0x0bf40467,
+/* 0x0635: memx_func_wait_vblank_fini */
+       0x0410b6f3,
+/* 0x063a: memx_func_wr32 */
+       0x169800f8,
+       0x01159800,
+       0xf90810b6,
+       0xfc50f960,
+       0xf4e0fcd0,
+       0x42b63f21,
+       0xe91bf402,
+/* 0x0656: memx_func_wait */
+       0x87f000f8,
+       0x0684b62c,
+       0x980088cf,
+       0x1d98001e,
+       0x021c9801,
+       0xb6031b98,
+       0x21f41010,
+/* 0x0673: memx_func_delay */
+       0x9800f8a4,
+       0x10b6001e,
+       0x7f21f404,
+/* 0x067e: memx_func_train */
+       0x57f100f8,
+       0x77f10003,
+       0x97f10000,
+       0x93f00000,
+       0x029eb970,
+       0xb90421f4,
+       0xe7f102d8,
+       0x21f42710,
+/* 0x069d: memx_func_train_loop_outer */
+       0x0158e07f,
+       0x0083f101,
+       0xe097f102,
+       0x1193f011,
+       0x80f990f9,
+       0xe0fcd0fc,
+       0xf93f21f4,
+       0x0067f150,
+/* 0x06bd: memx_func_train_loop_inner */
+       0x1187f100,
+       0x9068ff11,
+       0xfd109894,
+       0x97f10589,
+       0x93f00720,
+       0xf990f910,
+       0xfcd0fc80,
+       0x3f21f4e0,
+       0x008097f1,
+       0xb91093f0,
+       0x21f4029e,
+       0x02d8b904,
+       0xf92088c5,
+       0xfc80f990,
+       0xf4e0fcd0,
+       0x97f13f21,
+       0x93f0053c,
+       0x0287f110,
+       0x0083f130,
+       0xf990f980,
+       0xfcd0fc80,
+       0x3f21f4e0,
+       0x0560e7f1,
+       0xf110e3f0,
+       0xf10000d7,
+       0x908000d3,
+       0xb7f100dc,
+       0xb3f08480,
+       0xa421f41e,
+       0x000057f1,
+       0xffff97f1,
+       0x830093f1,
+/* 0x073c: memx_func_train_loop_4x */
+       0x0080a7f1,
+       0xb910a3f0,
+       0x21f402ae,
+       0x02d8b904,
+       0xffdfb7f1,
+       0xffffb3f1,
+       0xf9048bfd,
+       0xfc80f9a0,
+       0xf4e0fcd0,
+       0xa7f13f21,
+       0xa3f0053c,
+       0x0287f110,
+       0x0083f130,
+       0xf9a0f980,
+       0xfcd0fc80,
+       0x3f21f4e0,
+       0x0560e7f1,
+       0xf110e3f0,
+       0xf10000d7,
+       0xb98000d3,
+       0xb7f102dc,
+       0xb3f02710,
+       0xa421f400,
+       0xf402eeb9,
+       0xddb90421,
+       0x949dff02,
+       0x700150b6,
+       0x1ef40456,
+       0xcc7aa092,
+       0x00a9800b,
+       0xb60160b6,
+       0x66700470,
+       0x001ef510,
+       0xb650fcff,
+       0x56700150,
+       0xd41ef507,
+/* 0x07cf: memx_exec */
+       0xf900f8fe,
+       0xb9d0f9e0,
+       0xb2b902c1,
+/* 0x07d9: memx_exec_next */
+       0x00139802,
+       0xe70410b6,
+       0xe701f034,
+       0xb601e033,
+       0x30f00132,
+       0xde35980c,
+       0x12b855f9,
+       0xe41ef406,
+       0x98f10b98,
+       0xcbbbf20c,
+       0xc4b7f102,
+       0x06b4b607,
+       0xfc00bbcf,
+       0xf5e0fcd0,
+       0xf8034221,
+/* 0x0815: memx_info */
+       0x01c67000,
+/* 0x081b: memx_info_data */
+       0xf10e0bf4,
+       0xf103ccc7,
+       0xf40800b7,
+/* 0x0826: memx_info_train */
+       0xc7f10b0e,
+       0xb7f10bcc,
+/* 0x082e: memx_info_send */
+       0x21f50100,
+       0x00f80342,
+/* 0x0834: memx_recv */
+       0xf401d6b0,
+       0xd6b0980b,
+       0xd80bf400,
+/* 0x0842: memx_init */
+       0x00f800f8,
+/* 0x0844: perf_recv */
+/* 0x0846: perf_init */
+       0x00f800f8,
+/* 0x0848: i2c_drive_scl */
+       0xf40036b0,
+       0x07f1110b,
+       0x04b607e0,
+       0x0001d006,
+       0x00f804bd,
+/* 0x085c: i2c_drive_scl_lo */
+       0x07e407f1,
+       0xd00604b6,
+       0x04bd0001,
+/* 0x086a: i2c_drive_sda */
+       0x36b000f8,
+       0x110bf400,
+       0x07e007f1,
+       0xd00604b6,
+       0x04bd0002,
+/* 0x087e: i2c_drive_sda_lo */
+       0x07f100f8,
+       0x04b607e4,
+       0x0002d006,
+       0x00f804bd,
+/* 0x088c: i2c_sense_scl */
+       0xf10132f4,
+       0xb607c437,
+       0x33cf0634,
+       0x0431fd00,
+       0xf4060bf4,
+/* 0x08a2: i2c_sense_scl_done */
+       0x00f80131,
+/* 0x08a4: i2c_sense_sda */
+       0xf10132f4,
+       0xb607c437,
+       0x33cf0634,
+       0x0432fd00,
+       0xf4060bf4,
+/* 0x08ba: i2c_sense_sda_done */
+       0x00f80131,
+/* 0x08bc: i2c_raise_scl */
+       0x47f140f9,
+       0x37f00898,
+       0x4821f501,
+/* 0x08c9: i2c_raise_scl_wait */
+       0xe8e7f108,
+       0x7f21f403,
+       0x088c21f5,
+       0xb60901f4,
+       0x1bf40142,
+/* 0x08dd: i2c_raise_scl_done */
+       0xf840fcef,
+/* 0x08e1: i2c_start */
+       0x8c21f500,
+       0x0d11f408,
+       0x08a421f5,
+       0xf40611f4,
+/* 0x08f2: i2c_start_rep */
+       0x37f0300e,
+       0x4821f500,
+       0x0137f008,
+       0x086a21f5,
+       0xb60076bb,
+       0x50f90465,
+       0xbb046594,
+       0x50bd0256,
+       0xfc0475fd,
+       0xbc21f550,
+       0x0464b608,
+/* 0x091f: i2c_start_send */
+       0xf01f11f4,
+       0x21f50037,
+       0xe7f1086a,
+       0x21f41388,
+       0x0037f07f,
+       0x084821f5,
+       0x1388e7f1,
+/* 0x093b: i2c_start_out */
+       0xf87f21f4,
+/* 0x093d: i2c_stop */
+       0x0037f000,
+       0x084821f5,
+       0xf50037f0,
+       0xf1086a21,
+       0xf403e8e7,
+       0x37f07f21,
+       0x4821f501,
+       0x88e7f108,
+       0x7f21f413,
+       0xf50137f0,
+       0xf1086a21,
+       0xf41388e7,
+       0x00f87f21,
+/* 0x0970: i2c_bitw */
+       0x086a21f5,
+       0x03e8e7f1,
+       0xbb7f21f4,
+       0x65b60076,
+       0x9450f904,
+       0x56bb0465,
+       0xfd50bd02,
+       0x50fc0475,
+       0x08bc21f5,
+       0xf40464b6,
+       0xe7f11811,
+       0x21f41388,
+       0x0037f07f,
+       0x084821f5,
+       0x1388e7f1,
+/* 0x09af: i2c_bitw_out */
+       0xf87f21f4,
+/* 0x09b1: i2c_bitr */
+       0x0137f000,
+       0x086a21f5,
+       0x03e8e7f1,
+       0xbb7f21f4,
+       0x65b60076,
+       0x9450f904,
+       0x56bb0465,
+       0xfd50bd02,
+       0x50fc0475,
+       0x08bc21f5,
+       0xf40464b6,
+       0x21f51b11,
+       0x37f008a4,
+       0x4821f500,
+       0x88e7f108,
+       0x7f21f413,
+       0xf4013cf0,
+/* 0x09f6: i2c_bitr_done */
+       0x00f80131,
+/* 0x09f8: i2c_get_byte */
+       0xf00057f0,
+/* 0x09fe: i2c_get_byte_next */
+       0x54b60847,
+       0x0076bb01,
+       0xf90465b6,
+       0x04659450,
+       0xbd0256bb,
+       0x0475fd50,
+       0x21f550fc,
+       0x64b609b1,
+       0x2b11f404,
+       0xb60553fd,
+       0x1bf40142,
+       0x0137f0d8,
+       0xb60076bb,
+       0x50f90465,
+       0xbb046594,
+       0x50bd0256,
+       0xfc0475fd,
+       0x7021f550,
+       0x0464b609,
+/* 0x0a48: i2c_get_byte_done */
+/* 0x0a4a: i2c_put_byte */
+       0x47f000f8,
+/* 0x0a4d: i2c_put_byte_next */
+       0x0142b608,
+       0xbb3854ff,
+       0x65b60076,
+       0x9450f904,
+       0x56bb0465,
+       0xfd50bd02,
+       0x50fc0475,
+       0x097021f5,
+       0xf40464b6,
+       0x46b03411,
+       0xd81bf400,
+       0xb60076bb,
+       0x50f90465,
+       0xbb046594,
+       0x50bd0256,
+       0xfc0475fd,
+       0xb121f550,
+       0x0464b609,
+       0xbb0f11f4,
+       0x36b00076,
+       0x061bf401,
+/* 0x0aa3: i2c_put_byte_done */
+       0xf80132f4,
+/* 0x0aa5: i2c_addr */
+       0x0076bb00,
+       0xf90465b6,
+       0x04659450,
+       0xbd0256bb,
+       0x0475fd50,
+       0x21f550fc,
+       0x64b608e1,
+       0x2911f404,
+       0x012ec3e7,
+       0xfd0134b6,
+       0x76bb0553,
+       0x0465b600,
+       0x659450f9,
+       0x0256bb04,
+       0x75fd50bd,
+       0xf550fc04,
+       0xb60a4a21,
+/* 0x0aea: i2c_addr_done */
+       0x00f80464,
+/* 0x0aec: i2c_acquire_addr */
+       0xb6f8cec7,
+       0xe0b702e4,
+       0xee980d1c,
+/* 0x0afb: i2c_acquire */
+       0xf500f800,
+       0xf40aec21,
+       0xd9f00421,
+       0x3f21f403,
+/* 0x0b0a: i2c_release */
+       0x21f500f8,
+       0x21f40aec,
+       0x03daf004,
+       0xf83f21f4,
+/* 0x0b19: i2c_recv */
+       0x0132f400,
+       0xb6f8c1c7,
+       0x16b00214,
+       0x3a1ff528,
+       0xf413a001,
+       0x0032980c,
+       0x0ccc13a0,
+       0xf4003198,
+       0xd0f90231,
+       0xd0f9e0f9,
+       0x000067f1,
+       0x100063f1,
+       0xbb016792,
+       0x65b60076,
+       0x9450f904,
+       0x56bb0465,
+       0xfd50bd02,
+       0x50fc0475,
+       0x0afb21f5,
+       0xfc0464b6,
+       0x00d6b0d0,
+       0x00b31bf5,
+       0xbb0057f0,
+       0x65b60076,
+       0x9450f904,
+       0x56bb0465,
+       0xfd50bd02,
+       0x50fc0475,
+       0x0aa521f5,
+       0xf50464b6,
+       0xc700d011,
+       0x76bbe0c5,
+       0x0465b600,
+       0x659450f9,
+       0x0256bb04,
+       0x75fd50bd,
+       0xf550fc04,
+       0xb60a4a21,
+       0x11f50464,
+       0x57f000ad,
+       0x0076bb01,
+       0xf90465b6,
+       0x04659450,
+       0xbd0256bb,
+       0x0475fd50,
+       0x21f550fc,
+       0x64b60aa5,
+       0x8a11f504,
+       0x0076bb00,
+       0xf90465b6,
+       0x04659450,
+       0xbd0256bb,
+       0x0475fd50,
+       0x21f550fc,
+       0x64b609f8,
+       0x6a11f404,
+       0xbbe05bcb,
+       0x65b60076,
+       0x9450f904,
+       0x56bb0465,
+       0xfd50bd02,
+       0x50fc0475,
+       0x093d21f5,
+       0xb90464b6,
+       0x74bd025b,
+/* 0x0c1f: i2c_recv_not_rd08 */
+       0xb0430ef4,
+       0x1bf401d6,
+       0x0057f03d,
+       0x0aa521f5,
+       0xc73311f4,
+       0x21f5e0c5,
+       0x11f40a4a,
+       0x0057f029,
+       0x0aa521f5,
+       0xc71f11f4,
+       0x21f5e0b5,
+       0x11f40a4a,
+       0x3d21f515,
+       0xc774bd09,
+       0x1bf408c5,
+       0x0232f409,
+/* 0x0c5f: i2c_recv_not_wr08 */
+/* 0x0c5f: i2c_recv_done */
+       0xc7030ef4,
+       0x21f5f8ce,
+       0xe0fc0b0a,
+       0x12f4d0fc,
+       0x027cb90a,
+       0x034221f5,
+/* 0x0c74: i2c_recv_exit */
+/* 0x0c76: i2c_init */
+       0x00f800f8,
+/* 0x0c78: test_recv */
+       0x05d817f1,
+       0xcf0614b6,
+       0x10b60011,
+       0xd807f101,
+       0x0604b605,
+       0xbd0001d0,
+       0x00e7f104,
+       0x4fe3f1d9,
+       0x6221f513,
+/* 0x0c9f: test_init */
+       0xf100f802,
+       0xf50800e7,
+       0xf8026221,
+/* 0x0ca9: idle_recv */
+/* 0x0cab: idle */
+       0xf400f800,
+       0x17f10031,
+       0x14b605d4,
+       0x0011cf06,
+       0xf10110b6,
+       0xb605d407,
+       0x01d00604,
+/* 0x0cc7: idle_loop */
+       0xf004bd00,
+       0x32f45817,
+/* 0x0ccd: idle_proc */
+/* 0x0ccd: idle_proc_exec */
+       0xb910f902,
+       0x21f5021e,
+       0x10fc034b,
+       0xf40911f4,
+       0x0ef40231,
+/* 0x0ce1: idle_proc_next */
+       0x5810b6ef,
+       0xf4061fb8,
+       0x02f4e61b,
+       0x0028f4dd,
+       0x00bb0ef4,
+       0x00000000,
+       0x00000000,
+       0x00000000,
+};
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/pmu/fuc/host.fuc b/drivers/gpu/drm/nouveau/nvkm/subdev/pmu/fuc/host.fuc
new file mode 100644 (file)
index 0000000..c2bb616
--- /dev/null
@@ -0,0 +1,151 @@
+/*
+ * Copyright 2013 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
+ */
+
+#ifdef INCLUDE_PROC
+process(PROC_HOST, #host_init, #host_recv)
+#endif
+
+/******************************************************************************
+ * HOST data segment
+ *****************************************************************************/
+#ifdef INCLUDE_DATA
+// HOST (R)FIFO packet format
+.equ #fifo_process 0x00
+.equ #fifo_message 0x04
+.equ #fifo_data0   0x08
+.equ #fifo_data1   0x0c
+
+// HOST HOST->PWR queue description
+.equ #fifo_qlen 4 // log2(size of queue entry in bytes)
+.equ #fifo_qnum 3 // log2(max number of entries in queue)
+.equ #fifo_qmaskb (1 << #fifo_qnum) // max number of entries in queue
+.equ #fifo_qmaskp (#fifo_qmaskb - 1)
+.equ #fifo_qmaskf ((#fifo_qmaskb << 1) - 1)
+.equ #fifo_qsize  (1 << (#fifo_qlen + #fifo_qnum))
+fifo_queue: .skip 128 // #fifo_qsize
+
+// HOST PWR->HOST queue description
+.equ #rfifo_qlen 4 // log2(size of queue entry in bytes)
+.equ #rfifo_qnum 3 // log2(max number of entries in queue)
+.equ #rfifo_qmaskb (1 << #rfifo_qnum) // max number of entries in queue
+.equ #rfifo_qmaskp (#rfifo_qmaskb - 1)
+.equ #rfifo_qmaskf ((#rfifo_qmaskb << 1) - 1)
+.equ #rfifo_qsize  (1 << (#rfifo_qlen + #rfifo_qnum))
+rfifo_queue: .skip 128 // #rfifo_qsize
+#endif
+
+/******************************************************************************
+ * HOST code segment
+ *****************************************************************************/
+#ifdef INCLUDE_CODE
+// HOST->PWR comms - dequeue message(s) for process(es) from FIFO
+//
+// $r15 - current (host)
+// $r0  - zero
+host_send:
+       nv_iord($r1, NV_PPWR_FIFO_GET(0))
+       nv_iord($r2, NV_PPWR_FIFO_PUT(0))
+       cmp b32 $r1 $r2
+       bra e #host_send_done
+               // calculate address of message
+               and $r14 $r1 #fifo_qmaskp
+               shl b32 $r14 $r14 #fifo_qlen
+               add b32 $r14 #fifo_queue
+
+               // read message data, and pass to appropriate process
+               ld b32 $r11 D[$r14 + #fifo_data1]
+               ld b32 $r12 D[$r14 + #fifo_data0]
+               ld b32 $r13 D[$r14 + #fifo_message]
+               ld b32 $r14 D[$r14 + #fifo_process]
+               call(send)
+
+               // increment GET
+               add b32 $r1 0x1
+               and $r14 $r1 #fifo_qmaskf
+               nv_iowr(NV_PPWR_FIFO_GET(0), $r14)
+               bra #host_send
+       host_send_done:
+       ret
+
+// PWR->HOST comms - enqueue message for HOST to RFIFO
+//
+// $r15 - current (host)
+// $r14 - process
+// $r13 - message
+// $r12 - message data 0
+// $r11 - message data 1
+// $r0  - zero
+host_recv:
+       // message from intr handler == HOST->PWR comms pending
+       mov $r1 (PROC_KERN & 0x0000ffff)
+       sethi $r1 (PROC_KERN & 0xffff0000)
+       cmp b32 $r14 $r1
+       bra e #host_send
+
+       // wait for space in RFIFO
+       host_recv_wait:
+       nv_iord($r1, NV_PPWR_RFIFO_GET)
+       nv_iord($r2, NV_PPWR_RFIFO_PUT)
+       xor $r1 #rfifo_qmaskb
+       cmp b32 $r1 $r2
+       bra e #host_recv_wait
+
+       and $r3 $r2 #rfifo_qmaskp
+       shl b32 $r3 #rfifo_qlen
+       add b32 $r3 #rfifo_queue
+
+       // enqueue message
+       st b32 D[$r3 + #fifo_data1] $r11
+       st b32 D[$r3 + #fifo_data0] $r12
+       st b32 D[$r3 + #fifo_message] $r13
+       st b32 D[$r3 + #fifo_process] $r14
+
+       add b32 $r2 0x1
+       and $r2 #rfifo_qmaskf
+       nv_iowr(NV_PPWR_RFIFO_PUT, $r2)
+
+       // notify host of pending message
+       mov $r2 NV_PPWR_INTR_TRIGGER_USER0
+       nv_iowr(NV_PPWR_INTR_TRIGGER, $r2)
+       ret
+
+// $r15 - current (host)
+// $r0  - zero
+host_init:
+       // store each fifo's base/size in H2D/D2H scratch regs
+       mov $r1 #fifo_qsize
+       shl b32 $r1 16
+       or $r1 #fifo_queue
+       nv_iowr(NV_PPWR_H2D, $r1);
+
+       mov $r1 #rfifo_qsize
+       shl b32 $r1 16
+       or $r1 #rfifo_queue
+       nv_iowr(NV_PPWR_D2H, $r1);
+
+       // enable fifo subintr for first fifo
+       mov $r1 1
+       nv_iowr(NV_PPWR_FIFO_INTR_EN, $r1)
+       ret
+#endif
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/pmu/fuc/i2c_.fuc b/drivers/gpu/drm/nouveau/nvkm/subdev/pmu/fuc/i2c_.fuc
new file mode 100644 (file)
index 0000000..757dda7
--- /dev/null
@@ -0,0 +1,393 @@
+/*
+ * Copyright 2013 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 T_TIMEOUT  2200000
+#define T_RISEFALL 1000
+#define T_HOLD     5000
+
+#ifdef INCLUDE_PROC
+process(PROC_I2C_, #i2c_init, #i2c_recv)
+#endif
+
+/******************************************************************************
+ * I2C_ data segment
+ *****************************************************************************/
+#ifdef INCLUDE_DATA
+i2c_scl_map:
+.b32 NV_PPWR_OUTPUT_I2C_0_SCL
+.b32 NV_PPWR_OUTPUT_I2C_1_SCL
+.b32 NV_PPWR_OUTPUT_I2C_2_SCL
+.b32 NV_PPWR_OUTPUT_I2C_3_SCL
+.b32 NV_PPWR_OUTPUT_I2C_4_SCL
+.b32 NV_PPWR_OUTPUT_I2C_5_SCL
+.b32 NV_PPWR_OUTPUT_I2C_6_SCL
+.b32 NV_PPWR_OUTPUT_I2C_7_SCL
+.b32 NV_PPWR_OUTPUT_I2C_8_SCL
+.b32 NV_PPWR_OUTPUT_I2C_9_SCL
+i2c_sda_map:
+.b32 NV_PPWR_OUTPUT_I2C_0_SDA
+.b32 NV_PPWR_OUTPUT_I2C_1_SDA
+.b32 NV_PPWR_OUTPUT_I2C_2_SDA
+.b32 NV_PPWR_OUTPUT_I2C_3_SDA
+.b32 NV_PPWR_OUTPUT_I2C_4_SDA
+.b32 NV_PPWR_OUTPUT_I2C_5_SDA
+.b32 NV_PPWR_OUTPUT_I2C_6_SDA
+.b32 NV_PPWR_OUTPUT_I2C_7_SDA
+.b32 NV_PPWR_OUTPUT_I2C_8_SDA
+.b32 NV_PPWR_OUTPUT_I2C_9_SDA
+#if NVKM_PPWR_CHIPSET < GF119
+i2c_ctrl:
+.b32 0x00e138
+.b32 0x00e150
+.b32 0x00e168
+.b32 0x00e180
+.b32 0x00e254
+.b32 0x00e274
+.b32 0x00e764
+.b32 0x00e780
+.b32 0x00e79c
+.b32 0x00e7b8
+#endif
+#endif
+
+/******************************************************************************
+ * I2C_ code segment
+ *****************************************************************************/
+#ifdef INCLUDE_CODE
+
+// $r3  - value
+// $r2  - sda line
+// $r1  - scl line
+// $r0  - zero
+i2c_drive_scl:
+       cmp b32 $r3 0
+       bra e #i2c_drive_scl_lo
+       nv_iowr(NV_PPWR_OUTPUT_SET, $r1)
+       ret
+       i2c_drive_scl_lo:
+       nv_iowr(NV_PPWR_OUTPUT_CLR, $r1)
+       ret
+
+i2c_drive_sda:
+       cmp b32 $r3 0
+       bra e #i2c_drive_sda_lo
+       nv_iowr(NV_PPWR_OUTPUT_SET, $r2)
+       ret
+       i2c_drive_sda_lo:
+       nv_iowr(NV_PPWR_OUTPUT_CLR, $r2)
+       ret
+
+i2c_sense_scl:
+       bclr $flags $p1
+       nv_iord($r3, NV_PPWR_INPUT)
+       and $r3 $r1
+       bra z #i2c_sense_scl_done
+               bset $flags $p1
+       i2c_sense_scl_done:
+       ret
+
+i2c_sense_sda:
+       bclr $flags $p1
+       nv_iord($r3, NV_PPWR_INPUT)
+       and $r3 $r2
+       bra z #i2c_sense_sda_done
+               bset $flags $p1
+       i2c_sense_sda_done:
+       ret
+
+#define i2c_drive_scl(v) /*
+*/     mov $r3 (v) /*
+*/     call(i2c_drive_scl)
+#define i2c_drive_sda(v) /*
+*/     mov $r3 (v) /*
+*/     call(i2c_drive_sda)
+#define i2c_sense_scl() /*
+*/     call(i2c_sense_scl)
+#define i2c_sense_sda() /*
+*/     call(i2c_sense_sda)
+#define i2c_delay(v) /*
+*/     mov $r14 (v) /*
+*/     call(nsec)
+
+#define i2c_trace_init() /*
+*/     imm32($r6, 0x10000000) /*
+*/     sub b32 $r7 $r6 1 /*
+*/
+#define i2c_trace_down() /*
+*/     shr b32 $r6 4 /*
+*/     push $r5 /*
+*/     shl b32 $r5 $r6 4 /*
+*/     sub b32 $r5 $r6 /*
+*/     not b32 $r5 /*
+*/     and $r7 $r5 /*
+*/     pop $r5 /*
+*/
+#define i2c_trace_exit() /*
+*/     shl b32 $r6 4 /*
+*/
+#define i2c_trace_next() /*
+*/     add b32 $r7 $r6 /*
+*/
+#define i2c_trace_call(func) /*
+*/     i2c_trace_next() /*
+*/     i2c_trace_down() /*
+*/     call(func) /*
+*/     i2c_trace_exit() /*
+*/
+
+i2c_raise_scl:
+       push $r4
+       mov $r4 (T_TIMEOUT / T_RISEFALL)
+       i2c_drive_scl(1)
+       i2c_raise_scl_wait:
+               i2c_delay(T_RISEFALL)
+               i2c_sense_scl()
+               bra $p1 #i2c_raise_scl_done
+               sub b32 $r4 1
+               bra nz #i2c_raise_scl_wait
+       i2c_raise_scl_done:
+       pop $r4
+       ret
+
+i2c_start:
+       i2c_sense_scl()
+       bra not $p1 #i2c_start_rep
+       i2c_sense_sda()
+       bra not $p1 #i2c_start_rep
+       bra #i2c_start_send
+       i2c_start_rep:
+               i2c_drive_scl(0)
+               i2c_drive_sda(1)
+               i2c_trace_call(i2c_raise_scl)
+               bra not $p1 #i2c_start_out
+       i2c_start_send:
+       i2c_drive_sda(0)
+       i2c_delay(T_HOLD)
+       i2c_drive_scl(0)
+       i2c_delay(T_HOLD)
+       i2c_start_out:
+       ret
+
+i2c_stop:
+       i2c_drive_scl(0)
+       i2c_drive_sda(0)
+       i2c_delay(T_RISEFALL)
+       i2c_drive_scl(1)
+       i2c_delay(T_HOLD)
+       i2c_drive_sda(1)
+       i2c_delay(T_HOLD)
+       ret
+
+// $r3  - value
+// $r2  - sda line
+// $r1  - scl line
+// $r0  - zero
+i2c_bitw:
+       call(i2c_drive_sda)
+       i2c_delay(T_RISEFALL)
+       i2c_trace_call(i2c_raise_scl)
+       bra not $p1 #i2c_bitw_out
+       i2c_delay(T_HOLD)
+       i2c_drive_scl(0)
+       i2c_delay(T_HOLD)
+       i2c_bitw_out:
+       ret
+
+// $r3  - value (out)
+// $r2  - sda line
+// $r1  - scl line
+// $r0  - zero
+i2c_bitr:
+       i2c_drive_sda(1)
+       i2c_delay(T_RISEFALL)
+       i2c_trace_call(i2c_raise_scl)
+       bra not $p1 #i2c_bitr_done
+       i2c_sense_sda()
+       i2c_drive_scl(0)
+       i2c_delay(T_HOLD)
+       xbit $r3 $flags $p1
+       bset $flags $p1
+       i2c_bitr_done:
+       ret
+
+i2c_get_byte:
+       mov $r5 0
+       mov $r4 8
+       i2c_get_byte_next:
+               shl b32 $r5 1
+               i2c_trace_call(i2c_bitr)
+               bra not $p1 #i2c_get_byte_done
+               or $r5 $r3
+               sub b32 $r4 1
+               bra nz #i2c_get_byte_next
+       mov $r3 1
+       i2c_trace_call(i2c_bitw)
+       i2c_get_byte_done:
+       ret
+
+i2c_put_byte:
+       mov $r4 8
+       i2c_put_byte_next:
+               sub b32 $r4 1
+               xbit $r3 $r5 $r4
+               i2c_trace_call(i2c_bitw)
+               bra not $p1 #i2c_put_byte_done
+               cmp b32 $r4 0
+               bra ne #i2c_put_byte_next
+       i2c_trace_call(i2c_bitr)
+       bra not $p1 #i2c_put_byte_done
+       i2c_trace_next()
+       cmp b32 $r3 1
+       bra ne #i2c_put_byte_done
+       bclr $flags $p1 // nack
+       i2c_put_byte_done:
+       ret
+
+i2c_addr:
+       i2c_trace_call(i2c_start)
+       bra not $p1 #i2c_addr_done
+       extr $r3 $r12 I2C__MSG_DATA0_ADDR
+       shl b32 $r3 1
+       or $r5 $r3
+       i2c_trace_call(i2c_put_byte)
+       i2c_addr_done:
+       ret
+
+i2c_acquire_addr:
+       extr $r14 $r12 I2C__MSG_DATA0_PORT
+#if NVKM_PPWR_CHIPSET < GF119
+       shl b32 $r14 2
+       add b32 $r14 #i2c_ctrl
+       ld b32 $r14 D[$r14]
+#else
+       shl b32 $r14 5
+       add b32 $r14 0x00d014
+#endif
+       ret
+
+i2c_acquire:
+       call(i2c_acquire_addr)
+       call(rd32)
+       bset $r13 3
+       call(wr32)
+       ret
+
+i2c_release:
+       call(i2c_acquire_addr)
+       call(rd32)
+       bclr $r13 3
+       call(wr32)
+       ret
+
+// description
+//
+// $r15 - current (i2c)
+// $r14 - sender process name
+// $r13 - message
+// $r12 - data0
+// $r11 - data1
+// $r0  - zero
+i2c_recv:
+       bclr $flags $p1
+       extr $r1 $r12 I2C__MSG_DATA0_PORT
+       shl b32 $r1 2
+       cmp b32 $r1 (#i2c_sda_map - #i2c_scl_map)
+       bra ge #i2c_recv_done
+       add b32 $r3 $r1 #i2c_sda_map
+       ld b32 $r2 D[$r3]
+       add b32 $r3 $r1 #i2c_scl_map
+       ld b32 $r1 D[$r3]
+
+       bset $flags $p2
+       push $r13
+       push $r14
+
+       push $r13
+       i2c_trace_init()
+       i2c_trace_call(i2c_acquire)
+       pop $r13
+
+       cmp b32 $r13 I2C__MSG_RD08
+       bra ne #i2c_recv_not_rd08
+               mov $r5 0
+               i2c_trace_call(i2c_addr)
+               bra not $p1 #i2c_recv_done
+               extr $r5 $r12 I2C__MSG_DATA0_RD08_REG
+               i2c_trace_call(i2c_put_byte)
+               bra not $p1 #i2c_recv_done
+               mov $r5 1
+               i2c_trace_call(i2c_addr)
+               bra not $p1 #i2c_recv_done
+               i2c_trace_call(i2c_get_byte)
+               bra not $p1 #i2c_recv_done
+               ins $r11 $r5 I2C__MSG_DATA1_RD08_VAL
+               i2c_trace_call(i2c_stop)
+               mov b32 $r11 $r5
+               clear b32 $r7
+               bra #i2c_recv_done
+
+       i2c_recv_not_rd08:
+       cmp b32 $r13 I2C__MSG_WR08
+       bra ne #i2c_recv_not_wr08
+               mov $r5 0
+               call(i2c_addr)
+               bra not $p1 #i2c_recv_done
+               extr $r5 $r12 I2C__MSG_DATA0_WR08_REG
+               call(i2c_put_byte)
+               bra not $p1 #i2c_recv_done
+               mov $r5 0
+               call(i2c_addr)
+               bra not $p1 #i2c_recv_done
+               extr $r5 $r11 I2C__MSG_DATA1_WR08_VAL
+               call(i2c_put_byte)
+               bra not $p1 #i2c_recv_done
+               call(i2c_stop)
+               clear b32 $r7
+               extr $r5 $r12 I2C__MSG_DATA0_WR08_SYNC
+               bra nz #i2c_recv_done
+               bclr $flags $p2
+               bra #i2c_recv_done
+
+       i2c_recv_not_wr08:
+
+       i2c_recv_done:
+       extr $r14 $r12 I2C__MSG_DATA0_PORT
+       call(i2c_release)
+
+       pop $r14
+       pop $r13
+       bra not $p2 #i2c_recv_exit
+       mov b32 $r12 $r7
+       call(send)
+
+       i2c_recv_exit:
+       ret
+
+// description
+//
+// $r15 - current (i2c)
+// $r0  - zero
+i2c_init:
+       ret
+#endif
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/pmu/fuc/idle.fuc b/drivers/gpu/drm/nouveau/nvkm/subdev/pmu/fuc/idle.fuc
new file mode 100644 (file)
index 0000000..98f1c37
--- /dev/null
@@ -0,0 +1,84 @@
+/*
+ * Copyright 2013 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
+ */
+
+#ifdef INCLUDE_PROC
+process(PROC_IDLE, #idle, #idle_recv)
+#endif
+
+/******************************************************************************
+ * IDLE data segment
+ *****************************************************************************/
+#ifdef INCLUDE_DATA
+#endif
+
+/******************************************************************************
+ * IDLE code segment
+ *****************************************************************************/
+#ifdef INCLUDE_CODE
+// description
+//
+// $r15 - current (idle)
+// $r14 - message
+// $r0  - zero
+idle_recv:
+       ret
+
+// description
+//
+// $r15 - current (idle)
+// $r0  - zero
+idle:
+       // set our "no interrupt has occurred during our execution" flag
+       bset $flags $p0
+
+       // count IDLE invocations for debugging purposes
+       nv_iord($r1, NV_PPWR_DSCRATCH(1))
+       add b32 $r1 1
+       nv_iowr(NV_PPWR_DSCRATCH(1), $r1)
+
+       // keep looping while there's pending messages for any process
+       idle_loop:
+       mov $r1 #proc_list_head
+       bclr $flags $p2
+       idle_proc:
+               // process the process' messages until there's none left
+               idle_proc_exec:
+                       push $r1
+                       mov b32 $r14 $r1
+                       call(recv)
+                       pop $r1
+                       bra not $p1 #idle_proc_next
+                       bset $flags $p2
+                       bra #idle_proc_exec
+               // next process!
+               idle_proc_next:
+               add b32 $r1 #proc_size
+               cmp b32 $r1 $r15
+               bra ne #idle_proc
+       bra $p2 #idle_loop
+
+       // sleep if no interrupts have occurred
+       sleep $p0
+       bra #idle
+#endif
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/pmu/fuc/kernel.fuc b/drivers/gpu/drm/nouveau/nvkm/subdev/pmu/fuc/kernel.fuc
new file mode 100644 (file)
index 0000000..5cf5be6
--- /dev/null
@@ -0,0 +1,556 @@
+/*
+ * Copyright 2013 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
+ */
+
+/******************************************************************************
+ * kernel data segment
+ *****************************************************************************/
+#ifdef INCLUDE_PROC
+proc_kern:
+process(PROC_KERN, 0, 0)
+proc_list_head:
+#endif
+
+#ifdef INCLUDE_DATA
+proc_list_tail:
+time_prev: .b32 0
+time_next: .b32 0
+#endif
+
+/******************************************************************************
+ * kernel code segment
+ *****************************************************************************/
+#ifdef INCLUDE_CODE
+       bra #init
+
+// read nv register
+//
+// $r15 - current
+// $r14 - addr
+// $r13 - data (return)
+// $r0  - zero
+rd32:
+       nv_iowr(NV_PPWR_MMIO_ADDR, $r14)
+       mov $r13 NV_PPWR_MMIO_CTRL_OP_RD
+       sethi $r13 NV_PPWR_MMIO_CTRL_TRIGGER
+       nv_iowr(NV_PPWR_MMIO_CTRL, $r13)
+       rd32_wait:
+               nv_iord($r13, NV_PPWR_MMIO_CTRL)
+               and $r13 NV_PPWR_MMIO_CTRL_STATUS
+               bra nz #rd32_wait
+       nv_iord($r13, NV_PPWR_MMIO_DATA)
+       ret
+
+// write nv register
+//
+// $r15 - current
+// $r14 - addr
+// $r13 - data
+// $r0  - zero
+wr32:
+       nv_iowr(NV_PPWR_MMIO_ADDR, $r14)
+       nv_iowr(NV_PPWR_MMIO_DATA, $r13)
+       mov $r13 NV_PPWR_MMIO_CTRL_OP_WR
+       or $r13 NV_PPWR_MMIO_CTRL_MASK_B32_0
+       sethi $r13 NV_PPWR_MMIO_CTRL_TRIGGER
+
+#ifdef NVKM_FALCON_MMIO_TRAP
+       push $r13
+       mov $r13 NV_PPWR_INTR_TRIGGER_USER1
+       nv_iowr(NV_PPWR_INTR_TRIGGER, $r13)
+       wr32_host:
+               nv_iord($r13, NV_PPWR_INTR)
+               and $r13 NV_PPWR_INTR_USER1
+               bra nz #wr32_host
+       pop $r13
+#endif
+
+       nv_iowr(NV_PPWR_MMIO_CTRL, $r13)
+       wr32_wait:
+               nv_iord($r13, NV_PPWR_MMIO_CTRL)
+               and $r13 NV_PPWR_MMIO_CTRL_STATUS
+               bra nz #wr32_wait
+       ret
+
+// busy-wait for a period of time
+//
+// $r15 - current
+// $r14 - ns
+// $r0  - zero
+nsec:
+       push $r9
+       push $r8
+       nv_iord($r8, NV_PPWR_TIMER_LOW)
+       nsec_loop:
+               nv_iord($r9, NV_PPWR_TIMER_LOW)
+               sub b32 $r9 $r8
+               cmp b32 $r9 $r14
+               bra l #nsec_loop
+       pop $r8
+       pop $r9
+       ret
+
+// busy-wait for a period of time
+//
+// $r15 - current
+// $r14 - addr
+// $r13 - mask
+// $r12 - data
+// $r11 - timeout (ns)
+// $r0  - zero
+wait:
+       push $r9
+       push $r8
+       nv_iord($r8, NV_PPWR_TIMER_LOW)
+       wait_loop:
+               nv_rd32($r10, $r14)
+               and $r10 $r13
+               cmp b32 $r10 $r12
+               bra e #wait_done
+               nv_iord($r9, NV_PPWR_TIMER_LOW)
+               sub b32 $r9 $r8
+               cmp b32 $r9 $r11
+               bra l #wait_loop
+       wait_done:
+       pop $r8
+       pop $r9
+       ret
+
+// $r15 - current (kern)
+// $r14 - process
+// $r8  - NV_PPWR_INTR
+intr_watchdog:
+       // read process' timer status, skip if not enabled
+       ld b32 $r9 D[$r14 + #proc_time]
+       cmp b32 $r9 0
+       bra z #intr_watchdog_next_proc
+
+       // subtract last timer's value from process' timer,
+       // if it's <= 0 then the timer has expired
+       ld b32 $r10 D[$r0 + #time_prev]
+       sub b32 $r9 $r10
+       bra g #intr_watchdog_next_time
+               mov $r13 KMSG_ALARM
+               call(send_proc)
+               clear b32 $r9
+               bra #intr_watchdog_next_proc
+
+       // otherwise, update the next timer's value if this
+       // process' timer is the soonest
+       intr_watchdog_next_time:
+               // ... or if there's no next timer yet
+               ld b32 $r10 D[$r0 + #time_next]
+               cmp b32 $r10 0
+               bra z #intr_watchdog_next_time_set
+
+               cmp b32 $r9 $r10
+               bra g #intr_watchdog_next_proc
+               intr_watchdog_next_time_set:
+               st b32 D[$r0 + #time_next] $r9
+
+       // update process' timer status, and advance
+       intr_watchdog_next_proc:
+       st b32 D[$r14 + #proc_time] $r9
+       add b32 $r14 #proc_size
+       cmp b32 $r14 #proc_list_tail
+       bra ne #intr_watchdog
+       ret
+
+intr:
+       push $r0
+       clear b32 $r0
+       push $r8
+       push $r9
+       push $r10
+       push $r11
+       push $r12
+       push $r13
+       push $r14
+       push $r15
+       mov $r15 #proc_kern
+       mov $r8 $flags
+       push $r8
+
+       nv_iord($r8, NV_PPWR_DSCRATCH(0))
+       add b32 $r8 1
+       nv_iowr(NV_PPWR_DSCRATCH(0), $r8)
+
+       nv_iord($r8, NV_PPWR_INTR)
+       and $r9 $r8 NV_PPWR_INTR_WATCHDOG
+       bra z #intr_skip_watchdog
+               st b32 D[$r0 + #time_next] $r0
+               mov $r14 #proc_list_head
+               call(intr_watchdog)
+               ld b32 $r9 D[$r0 + #time_next]
+               cmp b32 $r9 0
+               bra z #intr_skip_watchdog
+                       nv_iowr(NV_PPWR_WATCHDOG_TIME, $r9)
+                       st b32 D[$r0 + #time_prev] $r9
+
+       intr_skip_watchdog:
+       and $r9 $r8 NV_PPWR_INTR_SUBINTR
+       bra z #intr_skip_subintr
+               nv_iord($r9, NV_PPWR_SUBINTR)
+               and $r10 $r9 NV_PPWR_SUBINTR_FIFO
+               bra z #intr_subintr_skip_fifo
+                       nv_iord($r12, NV_PPWR_FIFO_INTR)
+                       push $r12
+                       mov $r14 (PROC_HOST & 0x0000ffff)
+                       sethi $r14 (PROC_HOST & 0xffff0000)
+                       mov $r13 KMSG_FIFO
+                       call(send)
+                       pop $r12
+                       nv_iowr(NV_PPWR_FIFO_INTR, $r12)
+               intr_subintr_skip_fifo:
+               nv_iowr(NV_PPWR_SUBINTR, $r9)
+
+       intr_skip_subintr:
+       and $r9 $r8 NV_PPWR_INTR_PAUSE
+       bra z #intr_skip_pause
+               and $r10 0xffbf
+
+       intr_skip_pause:
+       and $r9 $r8 NV_PPWR_INTR_USER0
+       bra z #intr_skip_user0
+               and $r10 0xffbf
+
+       intr_skip_user0:
+       nv_iowr(NV_PPWR_INTR_ACK, $r8)
+       pop $r8
+       mov $flags $r8
+       pop $r15
+       pop $r14
+       pop $r13
+       pop $r12
+       pop $r11
+       pop $r10
+       pop $r9
+       pop $r8
+       pop $r0
+       bclr $flags $p0
+       iret
+
+// calculate the number of ticks in the specified nanoseconds delay
+//
+// $r15 - current
+// $r14 - ns
+// $r14 - ticks (return)
+// $r0  - zero
+ticks_from_ns:
+       push $r12
+       push $r11
+
+       /* try not losing precision (multiply then divide) */
+       imm32($r13, HW_TICKS_PER_US)
+       call #mulu32_32_64
+
+       /* use an immeditate, it's ok because HW_TICKS_PER_US < 16 bits */
+       div $r12 $r12 1000
+
+       /* check if there wasn't any overflow */
+       cmpu b32 $r11 0
+       bra e #ticks_from_ns_quit
+
+       /* let's divide then multiply, too bad for the precision! */
+       div $r14 $r14 1000
+       imm32($r13, HW_TICKS_PER_US)
+       call #mulu32_32_64
+
+       /* this cannot overflow as long as HW_TICKS_PER_US < 1000 */
+
+ticks_from_ns_quit:
+       mov b32 $r14 $r12
+       pop $r11
+       pop $r12
+       ret
+
+// calculate the number of ticks in the specified microsecond delay
+//
+// $r15 - current
+// $r14 - us
+// $r14 - ticks (return)
+// $r0  - zero
+ticks_from_us:
+       push $r12
+       push $r11
+
+       /* simply multiply $us by HW_TICKS_PER_US */
+       imm32($r13, HW_TICKS_PER_US)
+       call #mulu32_32_64
+       mov b32 $r14 $r12
+
+       /* check if there wasn't any overflow */
+       cmpu b32 $r11 0
+       bra e #ticks_from_us_quit
+
+       /* Overflow! */
+       clear b32 $r14
+
+ticks_from_us_quit:
+       pop $r11
+       pop $r12
+       ret
+
+// calculate the number of ticks in the specified microsecond delay
+//
+// $r15 - current
+// $r14 - ticks
+// $r14 - us (return)
+// $r0  - zero
+ticks_to_us:
+       /* simply divide $ticks by HW_TICKS_PER_US */
+       imm32($r13, HW_TICKS_PER_US)
+       div $r14 $r14 $r13
+
+       ret
+
+// request the current process be sent a message after a timeout expires
+//
+// $r15 - current
+// $r14 - ticks (make sure it is < 2^31 to avoid any possible overflow)
+// $r0  - zero
+timer:
+       push $r9
+       push $r8
+
+       // interrupts off to prevent racing with timer isr
+       bclr $flags ie0
+
+       // if current process already has a timer set, bail
+       ld b32 $r8 D[$r15 + #proc_time]
+       cmp b32 $r8 0
+       bra g #timer_done
+
+       // halt watchdog timer temporarily
+       clear b32 $r8
+       nv_iowr(NV_PPWR_WATCHDOG_ENABLE, $r8)
+
+       // find out how much time elapsed since the last update
+       // of the watchdog and add this time to the wanted ticks
+       nv_iord($r8, NV_PPWR_WATCHDOG_TIME)
+       ld b32 $r9 D[$r0 + #time_prev]
+       sub b32 $r9 $r8
+       add b32 $r14 $r9
+       st b32 D[$r15 + #proc_time] $r14
+
+       // check for a pending interrupt.  if there's one already
+       // pending, we can just bail since the timer isr will
+       // queue the next soonest right after it's done
+       nv_iord($r8, NV_PPWR_INTR)
+       and $r8 NV_PPWR_INTR_WATCHDOG
+       bra nz #timer_enable
+
+       // update the watchdog if this timer should expire first,
+       // or if there's no timeout already set
+       nv_iord($r8, NV_PPWR_WATCHDOG_TIME)
+       cmp b32 $r14 $r0
+       bra e #timer_reset
+       cmp b32 $r14 $r8
+       bra g #timer_enable
+               timer_reset:
+               nv_iowr(NV_PPWR_WATCHDOG_TIME, $r14)
+               st b32 D[$r0 + #time_prev] $r14
+
+       // re-enable the watchdog timer
+       timer_enable:
+       mov $r8 1
+       nv_iowr(NV_PPWR_WATCHDOG_ENABLE, $r8)
+
+       // interrupts back on
+       timer_done:
+       bset $flags ie0
+
+       pop $r8
+       pop $r9
+       ret
+
+// send message to another process
+//
+// $r15 - current
+// $r14 - process
+// $r13 - message
+// $r12 - message data 0
+// $r11 - message data 1
+// $r0  - zero
+send_proc:
+       push $r8
+       push $r9
+       // check for space in queue
+       ld b32 $r8 D[$r14 + #proc_qget]
+       ld b32 $r9 D[$r14 + #proc_qput]
+       xor $r8 #proc_qmaskb
+       cmp b32 $r8 $r9
+       bra e #send_done
+
+       // enqueue message
+       and $r8 $r9 #proc_qmaskp
+       shl b32 $r8 $r8 #proc_qlen
+       add b32 $r8 #proc_queue
+       add b32 $r8 $r14
+
+       ld b32 $r10 D[$r15 + #proc_id]
+       st b32 D[$r8 + #msg_process] $r10
+       st b32 D[$r8 + #msg_message] $r13
+       st b32 D[$r8 + #msg_data0] $r12
+       st b32 D[$r8 + #msg_data1] $r11
+
+       // increment PUT
+       add b32 $r9 1
+       and $r9 #proc_qmaskf
+       st b32 D[$r14 + #proc_qput] $r9
+       bset $flags $p2
+       send_done:
+       pop $r9
+       pop $r8
+       ret
+
+// lookup process structure by its name
+//
+// $r15 - current
+// $r14 - process name
+// $r0  - zero
+//
+// $r14 - process
+// $p1  - success
+find:
+       push $r8
+       mov $r8 #proc_list_head
+       bset $flags $p1
+       find_loop:
+               ld b32 $r10 D[$r8 + #proc_id]
+               cmp b32 $r10 $r14
+               bra e #find_done
+               add b32 $r8 #proc_size
+               cmp b32 $r8 #proc_list_tail
+               bra ne #find_loop
+               bclr $flags $p1
+       find_done:
+       mov b32 $r14 $r8
+       pop $r8
+       ret
+
+// send message to another process
+//
+// $r15 - current
+// $r14 - process id
+// $r13 - message
+// $r12 - message data 0
+// $r11 - message data 1
+// $r0  - zero
+send:
+       call(find)
+       bra $p1 #send_proc
+       ret
+
+// process single message for a given process
+//
+// $r15 - current
+// $r14 - process
+// $r0  - zero
+recv:
+       push $r9
+       push $r8
+
+       ld b32 $r8 D[$r14 + #proc_qget]
+       ld b32 $r9 D[$r14 + #proc_qput]
+       bclr $flags $p1
+       cmp b32 $r8 $r9
+       bra e #recv_done
+               // dequeue message
+               and $r9 $r8 #proc_qmaskp
+               add b32 $r8 1
+               and $r8 #proc_qmaskf
+               st b32 D[$r14 + #proc_qget] $r8
+               ld b32 $r10 D[$r14 + #proc_recv]
+
+               push $r15
+               mov $r15 $flags
+               push $r15
+               mov b32 $r15 $r14
+
+               shl b32 $r9 $r9 #proc_qlen
+               add b32 $r14 $r9
+               add b32 $r14 #proc_queue
+               ld b32 $r11 D[$r14 + #msg_data1]
+               ld b32 $r12 D[$r14 + #msg_data0]
+               ld b32 $r13 D[$r14 + #msg_message]
+               ld b32 $r14 D[$r14 + #msg_process]
+
+               // process it
+               call $r10
+               pop $r15
+               mov $flags $r15
+               bset $flags $p1
+               pop $r15
+       recv_done:
+       pop $r8
+       pop $r9
+       ret
+
+init:
+       // setup stack
+       nv_iord($r1, NV_PPWR_CAPS)
+       extr $r1 $r1 9:17
+       shl b32 $r1 8
+       mov $sp $r1
+
+#ifdef NVKM_FALCON_MMIO_UAS
+       // somehow allows the magic "access mmio via D[]" stuff that's
+       // used by the nv_rd32/nv_wr32 macros to work
+       mov $r1 0x0010
+       sethi $r1 NV_PPWR_UAS_CONFIG_ENABLE
+       nv_iowrs(NV_PPWR_UAS_CONFIG, $r1)
+#endif
+
+       // route all interrupts except user0/1 and pause to fuc
+       mov $r1 0x00e0
+       sethi $r1 0x00000000
+       nv_iowr(NV_PPWR_INTR_ROUTE, $r1)
+
+       // enable watchdog and subintr intrs
+       mov $r1 NV_PPWR_INTR_EN_CLR_MASK
+       nv_iowr(NV_PPWR_INTR_EN_CLR, $r1)
+       mov $r1 NV_PPWR_INTR_EN_SET_WATCHDOG
+       or $r1 NV_PPWR_INTR_EN_SET_SUBINTR
+       nv_iowr(NV_PPWR_INTR_EN_SET, $r1)
+
+       // enable interrupts globally
+       mov $r1 #intr
+       sethi $r1 0x00000000
+       mov $iv0 $r1
+       bset $flags ie0
+
+       // enable watchdog timer
+       mov $r1 1
+       nv_iowr(NV_PPWR_WATCHDOG_ENABLE, $r1)
+
+       // bootstrap processes, idle process will be last, and not return
+       mov $r15 #proc_list_head
+       init_proc:
+               ld b32 $r1 D[$r15 + #proc_init]
+               cmp b32 $r1 0
+               bra z #init_proc
+               call $r1
+               add b32 $r15 #proc_size
+               bra #init_proc
+#endif
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/pmu/fuc/macros.fuc b/drivers/gpu/drm/nouveau/nvkm/subdev/pmu/fuc/macros.fuc
new file mode 100644 (file)
index 0000000..96fc984
--- /dev/null
@@ -0,0 +1,272 @@
+/*
+ * Copyright 2013 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 GT215 0xa3
+#define GF100 0xc0
+#define GF119 0xd9
+#define GK208 0x108
+
+#include "os.h"
+
+// IO addresses
+#define NV_PPWR_INTR_TRIGGER                                             0x0000
+#define NV_PPWR_INTR_TRIGGER_USER1                                   0x00000080
+#define NV_PPWR_INTR_TRIGGER_USER0                                   0x00000040
+#define NV_PPWR_INTR_ACK                                                 0x0004
+#define NV_PPWR_INTR_ACK_SUBINTR                                     0x00000800
+#define NV_PPWR_INTR_ACK_WATCHDOG                                    0x00000002
+#define NV_PPWR_INTR                                                     0x0008
+#define NV_PPWR_INTR_SUBINTR                                         0x00000800
+#define NV_PPWR_INTR_USER1                                           0x00000080
+#define NV_PPWR_INTR_USER0                                           0x00000040
+#define NV_PPWR_INTR_PAUSE                                           0x00000020
+#define NV_PPWR_INTR_WATCHDOG                                        0x00000002
+#define NV_PPWR_INTR_EN_SET                                              0x0010
+#define NV_PPWR_INTR_EN_SET_SUBINTR                                  0x00000800
+#define NV_PPWR_INTR_EN_SET_WATCHDOG                                 0x00000002
+#define NV_PPWR_INTR_EN_CLR                                              0x0014
+#define NV_PPWR_INTR_EN_CLR_MASK                    /* fuck i hate envyas */ -1
+#define NV_PPWR_INTR_ROUTE                                               0x001c
+#define NV_PPWR_TIMER_LOW                                                0x002c
+#define NV_PPWR_WATCHDOG_TIME                                            0x0034
+#define NV_PPWR_WATCHDOG_ENABLE                                          0x0038
+#define NV_PPWR_CAPS                                                     0x0108
+#define NV_PPWR_UAS_CONFIG                                               0x0164
+#define NV_PPWR_UAS_CONFIG_ENABLE                                    0x00010000
+#if NVKM_PPWR_CHIPSET >= GK208
+#define NV_PPWR_DSCRATCH(i)                                   (4 * (i) + 0x0450)
+#endif
+#define NV_PPWR_FIFO_PUT(i)                                   (4 * (i) + 0x04a0)
+#define NV_PPWR_FIFO_GET(i)                                   (4 * (i) + 0x04b0)
+#define NV_PPWR_FIFO_INTR                                                0x04c0
+#define NV_PPWR_FIFO_INTR_EN                                             0x04c4
+#define NV_PPWR_RFIFO_PUT                                                0x04c8
+#define NV_PPWR_RFIFO_GET                                                0x04cc
+#define NV_PPWR_H2D                                                      0x04d0
+#define NV_PPWR_D2H                                                      0x04dc
+#if NVKM_PPWR_CHIPSET < GK208
+#define NV_PPWR_DSCRATCH(i)                                   (4 * (i) + 0x05d0)
+#endif
+#define NV_PPWR_SUBINTR                                                  0x0688
+#define NV_PPWR_SUBINTR_FIFO                                         0x00000002
+#define NV_PPWR_MMIO_ADDR                                                0x07a0
+#define NV_PPWR_MMIO_DATA                                                0x07a4
+#define NV_PPWR_MMIO_CTRL                                                0x07ac
+#define NV_PPWR_MMIO_CTRL_TRIGGER                                    0x00010000
+#define NV_PPWR_MMIO_CTRL_STATUS                                     0x00007000
+#define NV_PPWR_MMIO_CTRL_STATUS_IDLE                                0x00000000
+#define NV_PPWR_MMIO_CTRL_MASK                                       0x000000f0
+#define NV_PPWR_MMIO_CTRL_MASK_B32_0                                 0x000000f0
+#define NV_PPWR_MMIO_CTRL_OP                                         0x00000003
+#define NV_PPWR_MMIO_CTRL_OP_RD                                      0x00000001
+#define NV_PPWR_MMIO_CTRL_OP_WR                                      0x00000002
+#define NV_PPWR_OUTPUT                                                   0x07c0
+#define NV_PPWR_OUTPUT_FB_PAUSE                                      0x00000004
+#if NVKM_PPWR_CHIPSET < GF119
+#define NV_PPWR_OUTPUT_I2C_3_SCL                                     0x00000100
+#define NV_PPWR_OUTPUT_I2C_3_SDA                                     0x00000200
+#define NV_PPWR_OUTPUT_I2C_0_SCL                                     0x00001000
+#define NV_PPWR_OUTPUT_I2C_0_SDA                                     0x00002000
+#define NV_PPWR_OUTPUT_I2C_1_SCL                                     0x00004000
+#define NV_PPWR_OUTPUT_I2C_1_SDA                                     0x00008000
+#define NV_PPWR_OUTPUT_I2C_2_SCL                                     0x00010000
+#define NV_PPWR_OUTPUT_I2C_2_SDA                                     0x00020000
+#define NV_PPWR_OUTPUT_I2C_4_SCL                                     0x00040000
+#define NV_PPWR_OUTPUT_I2C_4_SDA                                     0x00080000
+#define NV_PPWR_OUTPUT_I2C_5_SCL                                     0x00100000
+#define NV_PPWR_OUTPUT_I2C_5_SDA                                     0x00200000
+#define NV_PPWR_OUTPUT_I2C_6_SCL                                     0x00400000
+#define NV_PPWR_OUTPUT_I2C_6_SDA                                     0x00800000
+#define NV_PPWR_OUTPUT_I2C_7_SCL                                     0x01000000
+#define NV_PPWR_OUTPUT_I2C_7_SDA                                     0x02000000
+#define NV_PPWR_OUTPUT_I2C_8_SCL                                     0x04000000
+#define NV_PPWR_OUTPUT_I2C_8_SDA                                     0x08000000
+#define NV_PPWR_OUTPUT_I2C_9_SCL                                     0x10000000
+#define NV_PPWR_OUTPUT_I2C_9_SDA                                     0x20000000
+#else
+#define NV_PPWR_OUTPUT_I2C_0_SCL                                     0x00000400
+#define NV_PPWR_OUTPUT_I2C_1_SCL                                     0x00000800
+#define NV_PPWR_OUTPUT_I2C_2_SCL                                     0x00001000
+#define NV_PPWR_OUTPUT_I2C_3_SCL                                     0x00002000
+#define NV_PPWR_OUTPUT_I2C_4_SCL                                     0x00004000
+#define NV_PPWR_OUTPUT_I2C_5_SCL                                     0x00008000
+#define NV_PPWR_OUTPUT_I2C_6_SCL                                     0x00010000
+#define NV_PPWR_OUTPUT_I2C_7_SCL                                     0x00020000
+#define NV_PPWR_OUTPUT_I2C_8_SCL                                     0x00040000
+#define NV_PPWR_OUTPUT_I2C_9_SCL                                     0x00080000
+#define NV_PPWR_OUTPUT_I2C_0_SDA                                     0x00100000
+#define NV_PPWR_OUTPUT_I2C_1_SDA                                     0x00200000
+#define NV_PPWR_OUTPUT_I2C_2_SDA                                     0x00400000
+#define NV_PPWR_OUTPUT_I2C_3_SDA                                     0x00800000
+#define NV_PPWR_OUTPUT_I2C_4_SDA                                     0x01000000
+#define NV_PPWR_OUTPUT_I2C_5_SDA                                     0x02000000
+#define NV_PPWR_OUTPUT_I2C_6_SDA                                     0x04000000
+#define NV_PPWR_OUTPUT_I2C_7_SDA                                     0x08000000
+#define NV_PPWR_OUTPUT_I2C_8_SDA                                     0x10000000
+#define NV_PPWR_OUTPUT_I2C_9_SDA                                     0x20000000
+#endif
+#define NV_PPWR_INPUT                                                    0x07c4
+#define NV_PPWR_OUTPUT_SET                                               0x07e0
+#define NV_PPWR_OUTPUT_SET_FB_PAUSE                                  0x00000004
+#define NV_PPWR_OUTPUT_CLR                                               0x07e4
+#define NV_PPWR_OUTPUT_CLR_FB_PAUSE                                  0x00000004
+
+// Inter-process message format
+.equ #msg_process 0x00 /* send() target, recv() sender */
+.equ #msg_message 0x04
+.equ #msg_data0   0x08
+.equ #msg_data1   0x0c
+
+// Kernel message IDs
+#define KMSG_FIFO  0x00000000
+#define KMSG_ALARM 0x00000001
+
+// Process message queue description
+.equ #proc_qlen 4 // log2(size of queue entry in bytes)
+.equ #proc_qnum 2 // log2(max number of entries in queue)
+.equ #proc_qmaskb (1 << #proc_qnum) // max number of entries in queue
+.equ #proc_qmaskp (#proc_qmaskb - 1)
+.equ #proc_qmaskf ((#proc_qmaskb << 1) - 1)
+.equ #proc_qsize  (1 << (#proc_qlen + #proc_qnum))
+
+// Process table entry
+.equ #proc_id    0x00
+.equ #proc_init  0x04
+.equ #proc_recv  0x08
+.equ #proc_time  0x0c
+.equ #proc_qput  0x10
+.equ #proc_qget  0x14
+.equ #proc_queue 0x18
+.equ #proc_size (0x18 + #proc_qsize)
+
+#define process(id,init,recv) /*
+*/     .b32 id /*
+*/     .b32 init /*
+*/     .b32 recv /*
+*/     .b32 0 /*
+*/     .b32 0 /*
+*/     .b32 0 /*
+*/     .skip 64
+
+#if NV_PPWR_CHIPSET < GK208
+#define imm32(reg,val) /*
+*/     movw reg  ((val) & 0x0000ffff) /*
+*/     sethi reg ((val) & 0xffff0000)
+#else
+#define imm32(reg,val) /*
+*/     mov reg (val)
+#endif
+
+#ifndef NVKM_FALCON_UNSHIFTED_IO
+#define nv_iord(reg,ior) /*
+*/     mov reg ior /*
+*/     shl b32 reg 6 /*
+*/     iord reg I[reg + 0x000]
+#else
+#define nv_iord(reg,ior) /*
+*/     mov reg ior /*
+*/     iord reg I[reg + 0x000]
+#endif
+
+#ifndef NVKM_FALCON_UNSHIFTED_IO
+#define nv_iowr(ior,reg) /*
+*/     mov $r0 ior /*
+*/     shl b32 $r0 6 /*
+*/     iowr I[$r0 + 0x000] reg /*
+*/     clear b32 $r0
+#else
+#define nv_iowr(ior,reg) /*
+*/     mov $r0 ior /*
+*/     iowr I[$r0 + 0x000] reg /*
+*/     clear b32 $r0
+#endif
+
+#ifndef NVKM_FALCON_UNSHIFTED_IO
+#define nv_iowrs(ior,reg) /*
+*/     mov $r0 ior /*
+*/     shl b32 $r0 6 /*
+*/     iowrs I[$r0 + 0x000] reg /*
+*/     clear b32 $r0
+#else
+#define nv_iowrs(ior,reg) /*
+*/     mov $r0 ior /*
+*/     iowrs I[$r0 + 0x000] reg /*
+*/     clear b32 $r0
+#endif
+
+#define hash #
+#define fn(a) a
+#ifndef NVKM_FALCON_PC24
+#define call(a) call fn(hash)a
+#else
+#define call(a) lcall fn(hash)a
+#endif
+
+#ifndef NVKM_FALCON_MMIO_UAS
+#define nv_rd32(reg,addr) /*
+*/     mov b32 $r14 addr /*
+*/     call(rd32) /*
+*/     mov b32 reg $r13
+#else
+#define nv_rd32(reg,addr) /*
+*/     sethi $r0 0x14000000 /*
+*/     or $r0 addr /*
+*/     ld b32 reg D[$r0] /*
+*/     clear b32 $r0
+#endif
+
+#if !defined(NVKM_FALCON_MMIO_UAS) || defined(NVKM_FALCON_MMIO_TRAP)
+#define nv_wr32(addr,reg) /*
+*/     push addr /*
+*/     push reg /*
+*/     pop $r13 /*
+*/     pop $r14 /*
+*/     call(wr32)
+#else
+#define nv_wr32(addr,reg) /*
+*/     sethi $r0 0x14000000 /*
+*/     or $r0 addr /*
+*/     st b32 D[$r0] reg /*
+*/     clear b32 $r0
+#endif
+
+#define st(size, addr, reg) /*
+*/     movw $r0 addr /*
+*/     st size D[$r0] reg /*
+*/     clear b32 $r0
+
+#define ld(size, reg, addr) /*
+*/     movw $r0 addr /*
+*/     ld size reg D[$r0] /*
+*/     clear b32 $r0
+
+// does a 64+64 -> 64 unsigned addition (C = A + B)
+#define addu64(reg_a_c_hi, reg_a_c_lo, b_hi, b_lo) /*
+*/    add b32 reg_a_c_lo b_lo /*
+*/    adc b32 reg_a_c_hi b_hi
+
+// does a 64+64 -> 64 substraction (C = A - B)
+#define subu64(reg_a_c_hi, reg_a_c_lo, b_hi, b_lo) /*
+*/    sub b32 reg_a_c_lo b_lo /*
+*/    sbb b32 reg_a_c_hi b_hi
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/pmu/fuc/memx.fuc b/drivers/gpu/drm/nouveau/nvkm/subdev/pmu/fuc/memx.fuc
new file mode 100644 (file)
index 0000000..ec03f9a
--- /dev/null
@@ -0,0 +1,447 @@
+/*
+ * Copyright 2013 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
+ */
+
+#ifdef INCLUDE_PROC
+process(PROC_MEMX, #memx_init, #memx_recv)
+#endif
+
+/******************************************************************************
+ * MEMX data segment
+ *****************************************************************************/
+#ifdef INCLUDE_DATA
+.equ #memx_opcode 0
+.equ #memx_header 2
+.equ #memx_length 4
+.equ #memx_func   8
+
+#define handler(cmd,hdr,len,func) /*
+*/     .b16 MEMX_##cmd /*
+*/     .b16 hdr /*
+*/     .b16 len /*
+*/      .b16 0 /*
+*/     .b32 func
+
+memx_func_head:
+handler(ENTER , 0x0000, 0x0000, #memx_func_enter)
+memx_func_next:
+handler(LEAVE , 0x0000, 0x0000, #memx_func_leave)
+handler(WR32  , 0x0000, 0x0002, #memx_func_wr32)
+handler(WAIT  , 0x0004, 0x0000, #memx_func_wait)
+handler(DELAY , 0x0001, 0x0000, #memx_func_delay)
+handler(VBLANK, 0x0001, 0x0000, #memx_func_wait_vblank)
+handler(TRAIN , 0x0000, 0x0000, #memx_func_train)
+memx_func_tail:
+
+.equ #memx_func_size #memx_func_next - #memx_func_head
+.equ #memx_func_num (#memx_func_tail - #memx_func_head) / #memx_func_size
+
+memx_ts_start:
+.b32 0
+memx_ts_end:
+.b32 0
+
+memx_data_head:
+.skip 0x0800
+memx_data_tail:
+
+memx_train_head:
+.skip 0x0100
+memx_train_tail:
+#endif
+
+/******************************************************************************
+ * MEMX code segment
+ *****************************************************************************/
+#ifdef INCLUDE_CODE
+// description
+//
+// $r15 - current (memx)
+// $r4  - packet length
+// $r3  - opcode desciption
+// $r0  - zero
+memx_func_enter:
+#if NVKM_PPWR_CHIPSET == GT215
+       movw $r8 0x1610
+       nv_rd32($r7, $r8)
+       imm32($r6, 0xfffffffc)
+       and $r7 $r6
+       movw $r6 0x2
+       or $r7 $r6
+       nv_wr32($r8, $r7)
+#else
+       movw $r6 0x001620
+       imm32($r7, ~0x00000aa2);
+       nv_rd32($r8, $r6)
+       and $r8 $r7
+       nv_wr32($r6, $r8)
+
+       imm32($r7, ~0x00000001)
+       nv_rd32($r8, $r6)
+       and $r8 $r7
+       nv_wr32($r6, $r8)
+
+       movw $r6 0x0026f0
+       nv_rd32($r8, $r6)
+       and $r8 $r7
+       nv_wr32($r6, $r8)
+#endif
+
+       mov $r6 NV_PPWR_OUTPUT_SET_FB_PAUSE
+       nv_iowr(NV_PPWR_OUTPUT_SET, $r6)
+       memx_func_enter_wait:
+               nv_iord($r6, NV_PPWR_OUTPUT)
+               and $r6 NV_PPWR_OUTPUT_FB_PAUSE
+               bra z #memx_func_enter_wait
+
+       nv_iord($r6, NV_PPWR_TIMER_LOW)
+       st b32 D[$r0 + #memx_ts_start] $r6
+       ret
+
+// description
+//
+// $r15 - current (memx)
+// $r4  - packet length
+// $r3  - opcode desciption
+// $r0  - zero
+memx_func_leave:
+       nv_iord($r6, NV_PPWR_TIMER_LOW)
+       st b32 D[$r0 + #memx_ts_end] $r6
+
+       mov $r6 NV_PPWR_OUTPUT_CLR_FB_PAUSE
+       nv_iowr(NV_PPWR_OUTPUT_CLR, $r6)
+       memx_func_leave_wait:
+               nv_iord($r6, NV_PPWR_OUTPUT)
+               and $r6 NV_PPWR_OUTPUT_FB_PAUSE
+               bra nz #memx_func_leave_wait
+
+#if NVKM_PPWR_CHIPSET == GT215
+       movw $r8 0x1610
+       nv_rd32($r7, $r8)
+       imm32($r6, 0xffffffcc)
+       and $r7 $r6
+       nv_wr32($r8, $r7)
+#else
+       movw $r6 0x0026f0
+       imm32($r7, 0x00000001)
+       nv_rd32($r8, $r6)
+       or $r8 $r7
+       nv_wr32($r6, $r8)
+
+       movw $r6 0x001620
+       nv_rd32($r8, $r6)
+       or $r8 $r7
+       nv_wr32($r6, $r8)
+
+       imm32($r7, 0x00000aa2);
+       nv_rd32($r8, $r6)
+       or $r8 $r7
+       nv_wr32($r6, $r8)
+#endif
+       ret
+
+#if NVKM_PPWR_CHIPSET < GF119
+// description
+//
+// $r15 - current (memx)
+// $r4  - packet length
+//     +00: head to wait for vblank on
+// $r3  - opcode desciption
+// $r0  - zero
+memx_func_wait_vblank:
+       ld b32 $r6 D[$r1 + 0x00]
+       cmp b32 $r6 0x0
+       bra z #memx_func_wait_vblank_head0
+       cmp b32 $r6 0x1
+       bra z #memx_func_wait_vblank_head1
+       bra #memx_func_wait_vblank_fini
+
+       memx_func_wait_vblank_head1:
+       movw $r7 0x20
+       bra #memx_func_wait_vblank_0
+
+       memx_func_wait_vblank_head0:
+       movw $r7 0x8
+
+       memx_func_wait_vblank_0:
+               nv_iord($r6, NV_PPWR_INPUT)
+               and $r6 $r7
+               bra nz #memx_func_wait_vblank_0
+
+       memx_func_wait_vblank_1:
+               nv_iord($r6, NV_PPWR_INPUT)
+               and $r6 $r7
+               bra z #memx_func_wait_vblank_1
+
+       memx_func_wait_vblank_fini:
+       add b32 $r1 0x4
+       ret
+
+#else
+
+// XXX: currently no-op
+//
+// $r15 - current (memx)
+// $r4  - packet length
+//     +00: head to wait for vblank on
+// $r3  - opcode desciption
+// $r0  - zero
+memx_func_wait_vblank:
+       add b32 $r1 0x4
+       ret
+
+#endif
+
+// description
+//
+// $r15 - current (memx)
+// $r4  - packet length
+//     +00*n: addr
+//     +04*n: data
+// $r3  - opcode desciption
+// $r0  - zero
+memx_func_wr32:
+       ld b32 $r6 D[$r1 + 0x00]
+       ld b32 $r5 D[$r1 + 0x04]
+       add b32 $r1 0x08
+       nv_wr32($r6, $r5)
+       sub b32 $r4 0x02
+       bra nz #memx_func_wr32
+       ret
+
+// description
+//
+// $r15 - current (memx)
+// $r4  - packet length
+//     +00: addr
+//     +04: mask
+//     +08: data
+//     +0c: timeout (ns)
+// $r3  - opcode desciption
+// $r0  - zero
+memx_func_wait:
+       nv_iord($r8, NV_PPWR_TIMER_LOW)
+       ld b32 $r14 D[$r1 + 0x00]
+       ld b32 $r13 D[$r1 + 0x04]
+       ld b32 $r12 D[$r1 + 0x08]
+       ld b32 $r11 D[$r1 + 0x0c]
+       add b32 $r1 0x10
+       call(wait)
+       ret
+
+// description
+//
+// $r15 - current (memx)
+// $r4  - packet length
+//     +00: time (ns)
+// $r3  - opcode desciption
+// $r0  - zero
+memx_func_delay:
+       ld b32 $r14 D[$r1 + 0x00]
+       add b32 $r1 0x04
+       call(nsec)
+       ret
+
+// description
+//
+// $r15 - current (memx)
+// $r4  - packet length
+// $r3  - opcode desciption
+// $r0  - zero
+memx_func_train:
+#if NVKM_PPWR_CHIPSET == GT215
+// $r5 - outer loop counter
+// $r6 - inner loop counter
+// $r7 - entry counter (#memx_train_head + $r7)
+       movw $r5 0x3
+       movw $r7 0x0
+
+// Read random memory to wake up... things
+       imm32($r9, 0x700000)
+       nv_rd32($r8,$r9)
+       movw $r14 0x2710
+       call(nsec)
+
+       memx_func_train_loop_outer:
+               mulu $r8 $r5 0x101
+               sethi $r8 0x02000000
+               imm32($r9, 0x1111e0)
+               nv_wr32($r9, $r8)
+               push $r5
+
+               movw $r6 0x0
+               memx_func_train_loop_inner:
+                       movw $r8 0x1111
+                       mulu $r9 $r6 $r8
+                       shl b32 $r8 $r9 0x10
+                       or $r8 $r9
+                       imm32($r9, 0x100720)
+                       nv_wr32($r9, $r8)
+
+                       imm32($r9, 0x100080)
+                       nv_rd32($r8, $r9)
+                       or $r8 $r8 0x20
+                       nv_wr32($r9, $r8)
+
+                       imm32($r9, 0x10053c)
+                       imm32($r8, 0x80003002)
+                       nv_wr32($r9, $r8)
+
+                       imm32($r14, 0x100560)
+                       imm32($r13, 0x80000000)
+                       add b32 $r12 $r13 0
+                       imm32($r11, 0x001e8480)
+                       call(wait)
+
+                       // $r5 - inner inner loop counter
+                       // $r9 - result
+                       movw $r5 0
+                       imm32($r9, 0x8300ffff)
+                       memx_func_train_loop_4x:
+                               imm32($r10, 0x100080)
+                               nv_rd32($r8, $r10)
+                               imm32($r11, 0xffffffdf)
+                               and $r8 $r11
+                               nv_wr32($r10, $r8)
+
+                               imm32($r10, 0x10053c)
+                               imm32($r8, 0x80003002)
+                               nv_wr32($r10, $r8)
+
+                               imm32($r14, 0x100560)
+                               imm32($r13, 0x80000000)
+                               mov b32 $r12 $r13
+                               imm32($r11, 0x00002710)
+                               call(wait)
+
+                               nv_rd32($r13, $r14)
+                               and $r9 $r9 $r13
+
+                               add b32 $r5 1
+                               cmp b16 $r5 0x4
+                               bra l #memx_func_train_loop_4x
+
+                       add b32 $r10 $r7 #memx_train_head
+                       st b32 D[$r10 + 0] $r9
+                       add b32 $r6 1
+                       add b32 $r7 4
+
+                       cmp b16 $r6 0x10
+                       bra l #memx_func_train_loop_inner
+
+               pop $r5
+               add b32 $r5 1
+               cmp b16 $r5 7
+               bra l #memx_func_train_loop_outer
+
+#endif
+       ret
+
+// description
+//
+// $r15 - current (memx)
+// $r14 - sender process name
+// $r13 - message (exec)
+// $r12 - head of script
+// $r11 - tail of script
+// $r0  - zero
+memx_exec:
+       push $r14
+       push $r13
+       mov b32 $r1 $r12
+       mov b32 $r2 $r11
+
+       memx_exec_next:
+               // fetch the packet header
+               ld b32 $r3 D[$r1]
+               add b32 $r1 4
+               extr $r4 $r3 16:31
+               extr $r3 $r3 0:15
+
+               // execute the opcode handler
+               sub b32 $r3 1
+               mulu $r3 #memx_func_size
+               ld b32 $r5 D[$r3 + #memx_func_head + #memx_func]
+               call $r5
+
+               // keep going, if we haven't reached the end
+               cmp b32 $r1 $r2
+               bra l #memx_exec_next
+
+       // send completion reply
+       ld b32 $r11 D[$r0 + #memx_ts_start]
+       ld b32 $r12 D[$r0 + #memx_ts_end]
+       sub b32 $r12 $r11
+       nv_iord($r11, NV_PPWR_INPUT)
+       pop $r13
+       pop $r14
+       call(send)
+       ret
+
+// description
+//
+// $r15 - current (memx)
+// $r14 - sender process name
+// $r13 - message
+// $r12 - data0
+// $r11 - data1
+// $r0  - zero
+memx_info:
+       cmp b16 $r12 0x1
+       bra e #memx_info_train
+
+       memx_info_data:
+       mov $r12 #memx_data_head
+       mov $r11 #memx_data_tail - #memx_data_head
+       bra #memx_info_send
+
+       memx_info_train:
+       mov $r12 #memx_train_head
+       mov $r11 #memx_train_tail - #memx_train_head
+
+       memx_info_send:
+       call(send)
+       ret
+
+// description
+//
+// $r15 - current (memx)
+// $r14 - sender process name
+// $r13 - message
+// $r12 - data0
+// $r11 - data1
+// $r0  - zero
+memx_recv:
+       cmp b32 $r13 MEMX_MSG_EXEC
+       bra e #memx_exec
+       cmp b32 $r13 MEMX_MSG_INFO
+       bra e #memx_info
+       ret
+
+// description
+//
+// $r15 - current (memx)
+// $r0  - zero
+memx_init:
+       ret
+#endif
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/pmu/fuc/os.h b/drivers/gpu/drm/nouveau/nvkm/subdev/pmu/fuc/os.h
new file mode 100644 (file)
index 0000000..c8b06cb
--- /dev/null
@@ -0,0 +1,52 @@
+#ifndef __NVKM_PWR_OS_H__
+#define __NVKM_PWR_OS_H__
+
+/* Process names */
+#define PROC_KERN 0x52544e49
+#define PROC_IDLE 0x454c4449
+#define PROC_HOST 0x54534f48
+#define PROC_MEMX 0x584d454d
+#define PROC_PERF 0x46524550
+#define PROC_I2C_ 0x5f433249
+#define PROC_TEST 0x54534554
+
+/* KERN: message identifiers */
+#define KMSG_FIFO   0x00000000
+#define KMSG_ALARM  0x00000001
+
+/* MEMX: message identifiers */
+#define MEMX_MSG_INFO 0
+#define MEMX_MSG_EXEC 1
+
+/* MEMX: info types */
+#define MEMX_INFO_DATA  0
+#define MEMX_INFO_TRAIN 1
+
+/* MEMX: script opcode definitions */
+#define MEMX_ENTER  1
+#define MEMX_LEAVE  2
+#define MEMX_WR32   3
+#define MEMX_WAIT   4
+#define MEMX_DELAY  5
+#define MEMX_VBLANK 6
+#define MEMX_TRAIN  7
+
+/* I2C_: message identifiers */
+#define I2C__MSG_RD08 0
+#define I2C__MSG_WR08 1
+
+#define I2C__MSG_DATA0_PORT 24:31
+#define I2C__MSG_DATA0_ADDR 14:23
+
+#define I2C__MSG_DATA0_RD08_PORT I2C__MSG_DATA0_PORT
+#define I2C__MSG_DATA0_RD08_ADDR I2C__MSG_DATA0_ADDR
+#define I2C__MSG_DATA0_RD08_REG 0:7
+#define I2C__MSG_DATA1_RD08_VAL 0:7
+
+#define I2C__MSG_DATA0_WR08_PORT I2C__MSG_DATA0_PORT
+#define I2C__MSG_DATA0_WR08_ADDR I2C__MSG_DATA0_ADDR
+#define I2C__MSG_DATA0_WR08_SYNC 8:8
+#define I2C__MSG_DATA0_WR08_REG 0:7
+#define I2C__MSG_DATA1_WR08_VAL 0:7
+
+#endif
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/pmu/fuc/perf.fuc b/drivers/gpu/drm/nouveau/nvkm/subdev/pmu/fuc/perf.fuc
new file mode 100644 (file)
index 0000000..38eadf7
--- /dev/null
@@ -0,0 +1,57 @@
+/*
+ * Copyright 2013 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
+ */
+
+#ifdef INCLUDE_PROC
+process(PROC_PERF, #perf_init, #perf_recv)
+#endif
+
+/******************************************************************************
+ * PERF data segment
+ *****************************************************************************/
+#ifdef INCLUDE_DATA
+#endif
+
+/******************************************************************************
+ * PERF code segment
+ *****************************************************************************/
+#ifdef INCLUDE_CODE
+
+// description
+//
+// $r15 - current (perf)
+// $r14 - sender process name
+// $r13 - message
+// $r12 - data0
+// $r11 - data1
+// $r0  - zero
+perf_recv:
+       ret
+
+// description
+//
+// $r15 - current (perf)
+// $r0  - zero
+perf_init:
+       ret
+#endif
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/pmu/fuc/test.fuc b/drivers/gpu/drm/nouveau/nvkm/subdev/pmu/fuc/test.fuc
new file mode 100644 (file)
index 0000000..0c3a71b
--- /dev/null
@@ -0,0 +1,64 @@
+/*
+ * Copyright 2013 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
+ */
+
+#ifdef INCLUDE_PROC
+process(PROC_TEST, #test_init, #test_recv)
+#endif
+
+/******************************************************************************
+ * TEST data segment
+ *****************************************************************************/
+#ifdef INCLUDE_DATA
+#endif
+
+/******************************************************************************
+ * TEST code segment
+ *****************************************************************************/
+#ifdef INCLUDE_CODE
+// description
+//
+// $r15 - current (test)
+// $r14 - sender process name
+// $r13 - message
+// $r12 - data0
+// $r11 - data1
+// $r0  - zero
+test_recv:
+       nv_iord($r1, NV_PPWR_DSCRATCH(2))
+       add b32 $r1 1
+       nv_iowr(NV_PPWR_DSCRATCH(2), $r1)
+       mov $r14 -0x2700 /* 0xd900, envyas grrr! */
+       sethi $r14 0x134f0000
+       call(timer)
+       ret
+
+// description
+//
+// $r15 - current (test)
+// $r0  - zero
+test_init:
+       mov $r14 0x800
+       call(timer)
+       ret
+#endif
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/pmu/gf100.c b/drivers/gpu/drm/nouveau/nvkm/subdev/pmu/gf100.c
new file mode 100644 (file)
index 0000000..78a4ea0
--- /dev/null
@@ -0,0 +1,40 @@
+/*
+ * Copyright 2013 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 "priv.h"
+#include "fuc/gf100.fuc3.h"
+
+struct nvkm_oclass *
+gf100_pmu_oclass = &(struct nvkm_pmu_impl) {
+       .base.handle = NV_SUBDEV(PMU, 0xc0),
+       .base.ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = _nvkm_pmu_ctor,
+               .dtor = _nvkm_pmu_dtor,
+               .init = _nvkm_pmu_init,
+               .fini = _nvkm_pmu_fini,
+       },
+       .code.data = gf100_pmu_code,
+       .code.size = sizeof(gf100_pmu_code),
+       .data.data = gf100_pmu_data,
+       .data.size = sizeof(gf100_pmu_data),
+}.base;
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/pmu/gf110.c b/drivers/gpu/drm/nouveau/nvkm/subdev/pmu/gf110.c
new file mode 100644 (file)
index 0000000..6b3a238
--- /dev/null
@@ -0,0 +1,40 @@
+/*
+ * Copyright 2013 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 "priv.h"
+#include "fuc/gf110.fuc4.h"
+
+struct nvkm_oclass *
+gf110_pmu_oclass = &(struct nvkm_pmu_impl) {
+       .base.handle = NV_SUBDEV(PMU, 0xd0),
+       .base.ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = _nvkm_pmu_ctor,
+               .dtor = _nvkm_pmu_dtor,
+               .init = _nvkm_pmu_init,
+               .fini = _nvkm_pmu_fini,
+       },
+       .code.data = gf110_pmu_code,
+       .code.size = sizeof(gf110_pmu_code),
+       .data.data = gf110_pmu_data,
+       .data.size = sizeof(gf110_pmu_data),
+}.base;
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/pmu/gk104.c b/drivers/gpu/drm/nouveau/nvkm/subdev/pmu/gk104.c
new file mode 100644 (file)
index 0000000..28fdb8e
--- /dev/null
@@ -0,0 +1,67 @@
+/*
+ * Copyright 2013 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 gf110_pmu_code gk104_pmu_code
+#define gf110_pmu_data gk104_pmu_data
+#include "priv.h"
+#include "fuc/gf110.fuc4.h"
+
+static void
+gk104_pmu_pgob(struct nvkm_pmu *pmu, bool enable)
+{
+       nv_mask(pmu, 0x000200, 0x00001000, 0x00000000);
+       nv_rd32(pmu, 0x000200);
+       nv_mask(pmu, 0x000200, 0x08000000, 0x08000000);
+       msleep(50);
+
+       nv_mask(pmu, 0x10a78c, 0x00000002, 0x00000002);
+       nv_mask(pmu, 0x10a78c, 0x00000001, 0x00000001);
+       nv_mask(pmu, 0x10a78c, 0x00000001, 0x00000000);
+
+       nv_mask(pmu, 0x020004, 0xc0000000, enable ? 0xc0000000 : 0x40000000);
+       msleep(50);
+
+       nv_mask(pmu, 0x10a78c, 0x00000002, 0x00000000);
+       nv_mask(pmu, 0x10a78c, 0x00000001, 0x00000001);
+       nv_mask(pmu, 0x10a78c, 0x00000001, 0x00000000);
+
+       nv_mask(pmu, 0x000200, 0x08000000, 0x00000000);
+       nv_mask(pmu, 0x000200, 0x00001000, 0x00001000);
+       nv_rd32(pmu, 0x000200);
+}
+
+struct nvkm_oclass *
+gk104_pmu_oclass = &(struct nvkm_pmu_impl) {
+       .base.handle = NV_SUBDEV(PMU, 0xe4),
+       .base.ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = _nvkm_pmu_ctor,
+               .dtor = _nvkm_pmu_dtor,
+               .init = _nvkm_pmu_init,
+               .fini = _nvkm_pmu_fini,
+       },
+       .code.data = gk104_pmu_code,
+       .code.size = sizeof(gk104_pmu_code),
+       .data.data = gk104_pmu_data,
+       .data.size = sizeof(gk104_pmu_data),
+       .pgob = gk104_pmu_pgob,
+}.base;
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/pmu/gk208.c b/drivers/gpu/drm/nouveau/nvkm/subdev/pmu/gk208.c
new file mode 100644 (file)
index 0000000..6f9c09a
--- /dev/null
@@ -0,0 +1,40 @@
+/*
+ * Copyright 2013 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 "priv.h"
+#include "fuc/gk208.fuc5.h"
+
+struct nvkm_oclass *
+gk208_pmu_oclass = &(struct nvkm_pmu_impl) {
+       .base.handle = NV_SUBDEV(PMU, 0x00),
+       .base.ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = _nvkm_pmu_ctor,
+               .dtor = _nvkm_pmu_dtor,
+               .init = _nvkm_pmu_init,
+               .fini = _nvkm_pmu_fini,
+       },
+       .code.data = gk208_pmu_code,
+       .code.size = sizeof(gk208_pmu_code),
+       .data.data = gk208_pmu_data,
+       .data.size = sizeof(gk208_pmu_data),
+}.base;
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/pmu/gk20a.c b/drivers/gpu/drm/nouveau/nvkm/subdev/pmu/gk20a.c
new file mode 100644 (file)
index 0000000..a49934b
--- /dev/null
@@ -0,0 +1,229 @@
+/*
+ * Copyright (c) 2014, NVIDIA CORPORATION. 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 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 "priv.h"
+
+#include <subdev/clk.h>
+#include <subdev/timer.h>
+#include <subdev/volt.h>
+
+#define BUSY_SLOT      0
+#define CLK_SLOT       7
+
+struct gk20a_pmu_dvfs_data {
+       int p_load_target;
+       int p_load_max;
+       int p_smooth;
+       unsigned int avg_load;
+};
+
+struct gk20a_pmu_priv {
+       struct nvkm_pmu base;
+       struct nvkm_alarm alarm;
+       struct gk20a_pmu_dvfs_data *data;
+};
+
+struct gk20a_pmu_dvfs_dev_status {
+       unsigned long total;
+       unsigned long busy;
+       int cur_state;
+};
+
+static int
+gk20a_pmu_dvfs_target(struct gk20a_pmu_priv *priv, int *state)
+{
+       struct nvkm_clk *clk = nvkm_clk(priv);
+
+       return nvkm_clk_astate(clk, *state, 0, false);
+}
+
+static int
+gk20a_pmu_dvfs_get_cur_state(struct gk20a_pmu_priv *priv, int *state)
+{
+       struct nvkm_clk *clk = nvkm_clk(priv);
+
+       *state = clk->pstate;
+       return 0;
+}
+
+static int
+gk20a_pmu_dvfs_get_target_state(struct gk20a_pmu_priv *priv,
+                               int *state, int load)
+{
+       struct gk20a_pmu_dvfs_data *data = priv->data;
+       struct nvkm_clk *clk = nvkm_clk(priv);
+       int cur_level, level;
+
+       /* For GK20A, the performance level is directly mapped to pstate */
+       level = cur_level = clk->pstate;
+
+       if (load > data->p_load_max) {
+               level = min(clk->state_nr - 1, level + (clk->state_nr / 3));
+       } else {
+               level += ((load - data->p_load_target) * 10 /
+                               data->p_load_target) / 2;
+               level = max(0, level);
+               level = min(clk->state_nr - 1, level);
+       }
+
+       nv_trace(priv, "cur level = %d, new level = %d\n", cur_level, level);
+
+       *state = level;
+
+       if (level == cur_level)
+               return 0;
+       else
+               return 1;
+}
+
+static int
+gk20a_pmu_dvfs_get_dev_status(struct gk20a_pmu_priv *priv,
+                             struct gk20a_pmu_dvfs_dev_status *status)
+{
+       status->busy = nv_rd32(priv, 0x10a508 + (BUSY_SLOT * 0x10));
+       status->total= nv_rd32(priv, 0x10a508 + (CLK_SLOT * 0x10));
+       return 0;
+}
+
+static void
+gk20a_pmu_dvfs_reset_dev_status(struct gk20a_pmu_priv *priv)
+{
+       nv_wr32(priv, 0x10a508 + (BUSY_SLOT * 0x10), 0x80000000);
+       nv_wr32(priv, 0x10a508 + (CLK_SLOT * 0x10), 0x80000000);
+}
+
+static void
+gk20a_pmu_dvfs_work(struct nvkm_alarm *alarm)
+{
+       struct gk20a_pmu_priv *priv =
+               container_of(alarm, struct gk20a_pmu_priv, alarm);
+       struct gk20a_pmu_dvfs_data *data = priv->data;
+       struct gk20a_pmu_dvfs_dev_status status;
+       struct nvkm_clk *clk = nvkm_clk(priv);
+       struct nvkm_volt *volt = nvkm_volt(priv);
+       u32 utilization = 0;
+       int state, ret;
+
+       /*
+        * The PMU is initialized before CLK and VOLT, so we have to make sure the
+        * CLK and VOLT are ready here.
+        */
+       if (!clk || !volt)
+               goto resched;
+
+       ret = gk20a_pmu_dvfs_get_dev_status(priv, &status);
+       if (ret) {
+               nv_warn(priv, "failed to get device status\n");
+               goto resched;
+       }
+
+       if (status.total)
+               utilization = div_u64((u64)status.busy * 100, status.total);
+
+       data->avg_load = (data->p_smooth * data->avg_load) + utilization;
+       data->avg_load /= data->p_smooth + 1;
+       nv_trace(priv, "utilization = %d %%, avg_load = %d %%\n",
+                       utilization, data->avg_load);
+
+       ret = gk20a_pmu_dvfs_get_cur_state(priv, &state);
+       if (ret) {
+               nv_warn(priv, "failed to get current state\n");
+               goto resched;
+       }
+
+       if (gk20a_pmu_dvfs_get_target_state(priv, &state, data->avg_load)) {
+               nv_trace(priv, "set new state to %d\n", state);
+               gk20a_pmu_dvfs_target(priv, &state);
+       }
+
+resched:
+       gk20a_pmu_dvfs_reset_dev_status(priv);
+       nvkm_timer_alarm(priv, 100000000, alarm);
+}
+
+int
+gk20a_pmu_fini(struct nvkm_object *object, bool suspend)
+{
+       struct nvkm_pmu *pmu = (void *)object;
+       struct gk20a_pmu_priv *priv = (void *)pmu;
+
+       nvkm_timer_alarm_cancel(priv, &priv->alarm);
+
+       return nvkm_subdev_fini(&pmu->base, suspend);
+}
+
+int
+gk20a_pmu_init(struct nvkm_object *object)
+{
+       struct nvkm_pmu *pmu = (void *)object;
+       struct gk20a_pmu_priv *priv = (void *)pmu;
+       int ret;
+
+       ret = nvkm_subdev_init(&pmu->base);
+       if (ret)
+               return ret;
+
+       pmu->pgob = nvkm_pmu_pgob;
+
+       /* init pwr perf counter */
+       nv_wr32(pmu, 0x10a504 + (BUSY_SLOT * 0x10), 0x00200001);
+       nv_wr32(pmu, 0x10a50c + (BUSY_SLOT * 0x10), 0x00000002);
+       nv_wr32(pmu, 0x10a50c + (CLK_SLOT * 0x10), 0x00000003);
+
+       nvkm_timer_alarm(pmu, 2000000000, &priv->alarm);
+       return ret;
+}
+
+struct gk20a_pmu_dvfs_data gk20a_dvfs_data= {
+       .p_load_target = 70,
+       .p_load_max = 90,
+       .p_smooth = 1,
+};
+
+static int
+gk20a_pmu_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+              struct nvkm_oclass *oclass, void *data, u32 size,
+              struct nvkm_object **pobject)
+{
+       struct gk20a_pmu_priv *priv;
+       int ret;
+
+       ret = nvkm_pmu_create(parent, engine, oclass, &priv);
+       *pobject = nv_object(priv);
+       if (ret)
+               return ret;
+
+       priv->data = &gk20a_dvfs_data;
+
+       nvkm_alarm_init(&priv->alarm, gk20a_pmu_dvfs_work);
+       return 0;
+}
+
+struct nvkm_oclass *
+gk20a_pmu_oclass = &(struct nvkm_pmu_impl) {
+       .base.handle = NV_SUBDEV(PMU, 0xea),
+       .base.ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = gk20a_pmu_ctor,
+               .dtor = _nvkm_pmu_dtor,
+               .init = gk20a_pmu_init,
+               .fini = gk20a_pmu_fini,
+       },
+}.base;
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/pmu/gt215.c b/drivers/gpu/drm/nouveau/nvkm/subdev/pmu/gt215.c
new file mode 100644 (file)
index 0000000..30aaeb2
--- /dev/null
@@ -0,0 +1,49 @@
+/*
+ * Copyright 2013 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 "priv.h"
+#include "fuc/gt215.fuc3.h"
+
+static int
+gt215_pmu_init(struct nvkm_object *object)
+{
+       struct nvkm_pmu *pmu = (void *)object;
+       nv_mask(pmu, 0x022210, 0x00000001, 0x00000000);
+       nv_mask(pmu, 0x022210, 0x00000001, 0x00000001);
+       return nvkm_pmu_init(pmu);
+}
+
+struct nvkm_oclass *
+gt215_pmu_oclass = &(struct nvkm_pmu_impl) {
+       .base.handle = NV_SUBDEV(PMU, 0xa3),
+       .base.ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = _nvkm_pmu_ctor,
+               .dtor = _nvkm_pmu_dtor,
+               .init = gt215_pmu_init,
+               .fini = _nvkm_pmu_fini,
+       },
+       .code.data = gt215_pmu_code,
+       .code.size = sizeof(gt215_pmu_code),
+       .data.data = gt215_pmu_data,
+       .data.size = sizeof(gt215_pmu_data),
+}.base;
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/pmu/memx.c b/drivers/gpu/drm/nouveau/nvkm/subdev/pmu/memx.c
new file mode 100644 (file)
index 0000000..b75c5b8
--- /dev/null
@@ -0,0 +1,200 @@
+#ifndef __NVKM_PMU_MEMX_H__
+#define __NVKM_PMU_MEMX_H__
+#include "priv.h"
+
+#include <core/device.h>
+
+struct nvkm_memx {
+       struct nvkm_pmu *pmu;
+       u32 base;
+       u32 size;
+       struct {
+               u32 mthd;
+               u32 size;
+               u32 data[64];
+       } c;
+};
+
+static void
+memx_out(struct nvkm_memx *memx)
+{
+       struct nvkm_pmu *pmu = memx->pmu;
+       int i;
+
+       if (memx->c.mthd) {
+               nv_wr32(pmu, 0x10a1c4, (memx->c.size << 16) | memx->c.mthd);
+               for (i = 0; i < memx->c.size; i++)
+                       nv_wr32(pmu, 0x10a1c4, memx->c.data[i]);
+               memx->c.mthd = 0;
+               memx->c.size = 0;
+       }
+}
+
+static void
+memx_cmd(struct nvkm_memx *memx, u32 mthd, u32 size, u32 data[])
+{
+       if ((memx->c.size + size >= ARRAY_SIZE(memx->c.data)) ||
+           (memx->c.mthd && memx->c.mthd != mthd))
+               memx_out(memx);
+       memcpy(&memx->c.data[memx->c.size], data, size * sizeof(data[0]));
+       memx->c.size += size;
+       memx->c.mthd  = mthd;
+}
+
+int
+nvkm_memx_init(struct nvkm_pmu *pmu, struct nvkm_memx **pmemx)
+{
+       struct nvkm_memx *memx;
+       u32 reply[2];
+       int ret;
+
+       ret = pmu->message(pmu, reply, PROC_MEMX, MEMX_MSG_INFO,
+                          MEMX_INFO_DATA, 0);
+       if (ret)
+               return ret;
+
+       memx = *pmemx = kzalloc(sizeof(*memx), GFP_KERNEL);
+       if (!memx)
+               return -ENOMEM;
+       memx->pmu = pmu;
+       memx->base = reply[0];
+       memx->size = reply[1];
+
+       /* acquire data segment access */
+       do {
+               nv_wr32(pmu, 0x10a580, 0x00000003);
+       } while (nv_rd32(pmu, 0x10a580) != 0x00000003);
+       nv_wr32(pmu, 0x10a1c0, 0x01000000 | memx->base);
+       return 0;
+}
+
+int
+nvkm_memx_fini(struct nvkm_memx **pmemx, bool exec)
+{
+       struct nvkm_memx *memx = *pmemx;
+       struct nvkm_pmu *pmu = memx->pmu;
+       u32 finish, reply[2];
+
+       /* flush the cache... */
+       memx_out(memx);
+
+       /* release data segment access */
+       finish = nv_rd32(pmu, 0x10a1c0) & 0x00ffffff;
+       nv_wr32(pmu, 0x10a580, 0x00000000);
+
+       /* call MEMX process to execute the script, and wait for reply */
+       if (exec) {
+               pmu->message(pmu, reply, PROC_MEMX, MEMX_MSG_EXEC,
+                            memx->base, finish);
+       }
+
+       nv_debug(memx->pmu, "Exec took %uns, PMU_IN %08x\n",
+                reply[0], reply[1]);
+       kfree(memx);
+       return 0;
+}
+
+void
+nvkm_memx_wr32(struct nvkm_memx *memx, u32 addr, u32 data)
+{
+       nv_debug(memx->pmu, "R[%06x] = 0x%08x\n", addr, data);
+       memx_cmd(memx, MEMX_WR32, 2, (u32[]){ addr, data });
+}
+
+void
+nvkm_memx_wait(struct nvkm_memx *memx,
+                 u32 addr, u32 mask, u32 data, u32 nsec)
+{
+       nv_debug(memx->pmu, "R[%06x] & 0x%08x == 0x%08x, %d us\n",
+                               addr, mask, data, nsec);
+       memx_cmd(memx, MEMX_WAIT, 4, (u32[]){ addr, mask, data, nsec });
+       memx_out(memx); /* fuc can't handle multiple */
+}
+
+void
+nvkm_memx_nsec(struct nvkm_memx *memx, u32 nsec)
+{
+       nv_debug(memx->pmu, "    DELAY = %d ns\n", nsec);
+       memx_cmd(memx, MEMX_DELAY, 1, (u32[]){ nsec });
+       memx_out(memx); /* fuc can't handle multiple */
+}
+
+void
+nvkm_memx_wait_vblank(struct nvkm_memx *memx)
+{
+       struct nvkm_pmu *pmu = memx->pmu;
+       u32 heads, x, y, px = 0;
+       int i, head_sync;
+
+       if (nv_device(pmu)->chipset < 0xd0) {
+               heads = nv_rd32(pmu, 0x610050);
+               for (i = 0; i < 2; i++) {
+                       /* Heuristic: sync to head with biggest resolution */
+                       if (heads & (2 << (i << 3))) {
+                               x = nv_rd32(pmu, 0x610b40 + (0x540 * i));
+                               y = (x & 0xffff0000) >> 16;
+                               x &= 0x0000ffff;
+                               if ((x * y) > px) {
+                                       px = (x * y);
+                                       head_sync = i;
+                               }
+                       }
+               }
+       }
+
+       if (px == 0) {
+               nv_debug(memx->pmu, "WAIT VBLANK !NO ACTIVE HEAD\n");
+               return;
+       }
+
+       nv_debug(memx->pmu, "WAIT VBLANK HEAD%d\n", head_sync);
+       memx_cmd(memx, MEMX_VBLANK, 1, (u32[]){ head_sync });
+       memx_out(memx); /* fuc can't handle multiple */
+}
+
+void
+nvkm_memx_train(struct nvkm_memx *memx)
+{
+       nv_debug(memx->pmu, "   MEM TRAIN\n");
+       memx_cmd(memx, MEMX_TRAIN, 0, NULL);
+}
+
+int
+nvkm_memx_train_result(struct nvkm_pmu *pmu, u32 *res, int rsize)
+{
+       u32 reply[2], base, size, i;
+       int ret;
+
+       ret = pmu->message(pmu, reply, PROC_MEMX, MEMX_MSG_INFO,
+                          MEMX_INFO_TRAIN, 0);
+       if (ret)
+               return ret;
+
+       base = reply[0];
+       size = reply[1] >> 2;
+       if (size > rsize)
+               return -ENOMEM;
+
+       /* read the packet */
+       nv_wr32(pmu, 0x10a1c0, 0x02000000 | base);
+
+       for (i = 0; i < size; i++)
+               res[i] = nv_rd32(pmu, 0x10a1c4);
+
+       return 0;
+}
+
+void
+nvkm_memx_block(struct nvkm_memx *memx)
+{
+       nv_debug(memx->pmu, "   HOST BLOCKED\n");
+       memx_cmd(memx, MEMX_ENTER, 0, NULL);
+}
+
+void
+nvkm_memx_unblock(struct nvkm_memx *memx)
+{
+       nv_debug(memx->pmu, "   HOST UNBLOCKED\n");
+       memx_cmd(memx, MEMX_LEAVE, 0, NULL);
+}
+#endif
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/pmu/priv.h b/drivers/gpu/drm/nouveau/nvkm/subdev/pmu/priv.h
new file mode 100644 (file)
index 0000000..9984105
--- /dev/null
@@ -0,0 +1,43 @@
+#ifndef __NVKM_PMU_PRIV_H__
+#define __NVKM_PMU_PRIV_H__
+#include <subdev/pmu.h>
+#include <subdev/pmu/fuc/os.h>
+
+#define nvkm_pmu_create(p, e, o, d)                                         \
+       nvkm_pmu_create_((p), (e), (o), sizeof(**d), (void **)d)
+#define nvkm_pmu_destroy(p)                                                 \
+       nvkm_subdev_destroy(&(p)->base)
+#define nvkm_pmu_init(p) ({                                                 \
+       struct nvkm_pmu *_pmu = (p);                                       \
+       _nvkm_pmu_init(nv_object(_pmu));                                   \
+})
+#define nvkm_pmu_fini(p,s) ({                                               \
+       struct nvkm_pmu *_pmu = (p);                                       \
+       _nvkm_pmu_fini(nv_object(_pmu), (s));                              \
+})
+
+int nvkm_pmu_create_(struct nvkm_object *, struct nvkm_object *,
+                       struct nvkm_oclass *, int, void **);
+
+int _nvkm_pmu_ctor(struct nvkm_object *, struct nvkm_object *,
+                     struct nvkm_oclass *, void *, u32,
+                     struct nvkm_object **);
+#define _nvkm_pmu_dtor _nvkm_subdev_dtor
+int _nvkm_pmu_init(struct nvkm_object *);
+int _nvkm_pmu_fini(struct nvkm_object *, bool);
+void nvkm_pmu_pgob(struct nvkm_pmu *pmu, bool enable);
+
+struct nvkm_pmu_impl {
+       struct nvkm_oclass base;
+       struct {
+               u32 *data;
+               u32  size;
+       } code;
+       struct {
+               u32 *data;
+               u32  size;
+       } data;
+
+       void (*pgob)(struct nvkm_pmu *, bool);
+};
+#endif
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/therm/Kbuild b/drivers/gpu/drm/nouveau/nvkm/subdev/therm/Kbuild
new file mode 100644 (file)
index 0000000..5837cf1
--- /dev/null
@@ -0,0 +1,13 @@
+nvkm-y += nvkm/subdev/therm/base.o
+nvkm-y += nvkm/subdev/therm/fan.o
+nvkm-y += nvkm/subdev/therm/fannil.o
+nvkm-y += nvkm/subdev/therm/fanpwm.o
+nvkm-y += nvkm/subdev/therm/fantog.o
+nvkm-y += nvkm/subdev/therm/ic.o
+nvkm-y += nvkm/subdev/therm/temp.o
+nvkm-y += nvkm/subdev/therm/nv40.o
+nvkm-y += nvkm/subdev/therm/nv50.o
+nvkm-y += nvkm/subdev/therm/g84.o
+nvkm-y += nvkm/subdev/therm/gt215.o
+nvkm-y += nvkm/subdev/therm/gf110.o
+nvkm-y += nvkm/subdev/therm/gm107.o
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/therm/base.c b/drivers/gpu/drm/nouveau/nvkm/subdev/therm/base.c
new file mode 100644 (file)
index 0000000..ec327cb
--- /dev/null
@@ -0,0 +1,367 @@
+/*
+ * Copyright 2012 The Nouveau community
+ *
+ * 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 "priv.h"
+
+#include <core/device.h>
+
+static int
+nvkm_therm_update_trip(struct nvkm_therm *therm)
+{
+       struct nvkm_therm_priv *priv = (void *)therm;
+       struct nvbios_therm_trip_point *trip = priv->fan->bios.trip,
+                                      *cur_trip = NULL,
+                                      *last_trip = priv->last_trip;
+       u8  temp = therm->temp_get(therm);
+       u16 duty, i;
+
+       /* look for the trip point corresponding to the current temperature */
+       cur_trip = NULL;
+       for (i = 0; i < priv->fan->bios.nr_fan_trip; i++) {
+               if (temp >= trip[i].temp)
+                       cur_trip = &trip[i];
+       }
+
+       /* account for the hysteresis cycle */
+       if (last_trip && temp <= (last_trip->temp) &&
+           temp > (last_trip->temp - last_trip->hysteresis))
+               cur_trip = last_trip;
+
+       if (cur_trip) {
+               duty = cur_trip->fan_duty;
+               priv->last_trip = cur_trip;
+       } else {
+               duty = 0;
+               priv->last_trip = NULL;
+       }
+
+       return duty;
+}
+
+static int
+nvkm_therm_update_linear(struct nvkm_therm *therm)
+{
+       struct nvkm_therm_priv *priv = (void *)therm;
+       u8  linear_min_temp = priv->fan->bios.linear_min_temp;
+       u8  linear_max_temp = priv->fan->bios.linear_max_temp;
+       u8  temp = therm->temp_get(therm);
+       u16 duty;
+
+       /* handle the non-linear part first */
+       if (temp < linear_min_temp)
+               return priv->fan->bios.min_duty;
+       else if (temp > linear_max_temp)
+               return priv->fan->bios.max_duty;
+
+       /* we are in the linear zone */
+       duty  = (temp - linear_min_temp);
+       duty *= (priv->fan->bios.max_duty - priv->fan->bios.min_duty);
+       duty /= (linear_max_temp - linear_min_temp);
+       duty += priv->fan->bios.min_duty;
+       return duty;
+}
+
+static void
+nvkm_therm_update(struct nvkm_therm *therm, int mode)
+{
+       struct nvkm_timer *ptimer = nvkm_timer(therm);
+       struct nvkm_therm_priv *priv = (void *)therm;
+       unsigned long flags;
+       bool immd = true;
+       bool poll = true;
+       int duty = -1;
+
+       spin_lock_irqsave(&priv->lock, flags);
+       if (mode < 0)
+               mode = priv->mode;
+       priv->mode = mode;
+
+       switch (mode) {
+       case NVKM_THERM_CTRL_MANUAL:
+               ptimer->alarm_cancel(ptimer, &priv->alarm);
+               duty = nvkm_therm_fan_get(therm);
+               if (duty < 0)
+                       duty = 100;
+               poll = false;
+               break;
+       case NVKM_THERM_CTRL_AUTO:
+               switch(priv->fan->bios.fan_mode) {
+               case NVBIOS_THERM_FAN_TRIP:
+                       duty = nvkm_therm_update_trip(therm);
+                       break;
+               case NVBIOS_THERM_FAN_LINEAR:
+                       duty = nvkm_therm_update_linear(therm);
+                       break;
+               case NVBIOS_THERM_FAN_OTHER:
+                       if (priv->cstate)
+                               duty = priv->cstate;
+                       poll = false;
+                       break;
+               }
+               immd = false;
+               break;
+       case NVKM_THERM_CTRL_NONE:
+       default:
+               ptimer->alarm_cancel(ptimer, &priv->alarm);
+               poll = false;
+       }
+
+       if (list_empty(&priv->alarm.head) && poll)
+               ptimer->alarm(ptimer, 1000000000ULL, &priv->alarm);
+       spin_unlock_irqrestore(&priv->lock, flags);
+
+       if (duty >= 0) {
+               nv_debug(therm, "FAN target request: %d%%\n", duty);
+               nvkm_therm_fan_set(therm, immd, duty);
+       }
+}
+
+int
+nvkm_therm_cstate(struct nvkm_therm *ptherm, int fan, int dir)
+{
+       struct nvkm_therm_priv *priv = (void *)ptherm;
+       if (!dir || (dir < 0 && fan < priv->cstate) ||
+                   (dir > 0 && fan > priv->cstate)) {
+               nv_debug(ptherm, "default fan speed -> %d%%\n", fan);
+               priv->cstate = fan;
+               nvkm_therm_update(ptherm, -1);
+       }
+       return 0;
+}
+
+static void
+nvkm_therm_alarm(struct nvkm_alarm *alarm)
+{
+       struct nvkm_therm_priv *priv =
+              container_of(alarm, struct nvkm_therm_priv, alarm);
+       nvkm_therm_update(&priv->base, -1);
+}
+
+int
+nvkm_therm_fan_mode(struct nvkm_therm *therm, int mode)
+{
+       struct nvkm_therm_priv *priv = (void *)therm;
+       struct nvkm_device *device = nv_device(therm);
+       static const char *name[] = {
+               "disabled",
+               "manual",
+               "automatic"
+       };
+
+       /* The default PPWR ucode on fermi interferes with fan management */
+       if ((mode >= ARRAY_SIZE(name)) ||
+           (mode != NVKM_THERM_CTRL_NONE && device->card_type >= NV_C0 &&
+            !nvkm_subdev(device, NVDEV_SUBDEV_PMU)))
+               return -EINVAL;
+
+       /* do not allow automatic fan management if the thermal sensor is
+        * not available */
+       if (mode == NVKM_THERM_CTRL_AUTO && therm->temp_get(therm) < 0)
+               return -EINVAL;
+
+       if (priv->mode == mode)
+               return 0;
+
+       nv_info(therm, "fan management: %s\n", name[mode]);
+       nvkm_therm_update(therm, mode);
+       return 0;
+}
+
+int
+nvkm_therm_attr_get(struct nvkm_therm *therm,
+                      enum nvkm_therm_attr_type type)
+{
+       struct nvkm_therm_priv *priv = (void *)therm;
+
+       switch (type) {
+       case NVKM_THERM_ATTR_FAN_MIN_DUTY:
+               return priv->fan->bios.min_duty;
+       case NVKM_THERM_ATTR_FAN_MAX_DUTY:
+               return priv->fan->bios.max_duty;
+       case NVKM_THERM_ATTR_FAN_MODE:
+               return priv->mode;
+       case NVKM_THERM_ATTR_THRS_FAN_BOOST:
+               return priv->bios_sensor.thrs_fan_boost.temp;
+       case NVKM_THERM_ATTR_THRS_FAN_BOOST_HYST:
+               return priv->bios_sensor.thrs_fan_boost.hysteresis;
+       case NVKM_THERM_ATTR_THRS_DOWN_CLK:
+               return priv->bios_sensor.thrs_down_clock.temp;
+       case NVKM_THERM_ATTR_THRS_DOWN_CLK_HYST:
+               return priv->bios_sensor.thrs_down_clock.hysteresis;
+       case NVKM_THERM_ATTR_THRS_CRITICAL:
+               return priv->bios_sensor.thrs_critical.temp;
+       case NVKM_THERM_ATTR_THRS_CRITICAL_HYST:
+               return priv->bios_sensor.thrs_critical.hysteresis;
+       case NVKM_THERM_ATTR_THRS_SHUTDOWN:
+               return priv->bios_sensor.thrs_shutdown.temp;
+       case NVKM_THERM_ATTR_THRS_SHUTDOWN_HYST:
+               return priv->bios_sensor.thrs_shutdown.hysteresis;
+       }
+
+       return -EINVAL;
+}
+
+int
+nvkm_therm_attr_set(struct nvkm_therm *therm,
+                   enum nvkm_therm_attr_type type, int value)
+{
+       struct nvkm_therm_priv *priv = (void *)therm;
+
+       switch (type) {
+       case NVKM_THERM_ATTR_FAN_MIN_DUTY:
+               if (value < 0)
+                       value = 0;
+               if (value > priv->fan->bios.max_duty)
+                       value = priv->fan->bios.max_duty;
+               priv->fan->bios.min_duty = value;
+               return 0;
+       case NVKM_THERM_ATTR_FAN_MAX_DUTY:
+               if (value < 0)
+                       value = 0;
+               if (value < priv->fan->bios.min_duty)
+                       value = priv->fan->bios.min_duty;
+               priv->fan->bios.max_duty = value;
+               return 0;
+       case NVKM_THERM_ATTR_FAN_MODE:
+               return nvkm_therm_fan_mode(therm, value);
+       case NVKM_THERM_ATTR_THRS_FAN_BOOST:
+               priv->bios_sensor.thrs_fan_boost.temp = value;
+               priv->sensor.program_alarms(therm);
+               return 0;
+       case NVKM_THERM_ATTR_THRS_FAN_BOOST_HYST:
+               priv->bios_sensor.thrs_fan_boost.hysteresis = value;
+               priv->sensor.program_alarms(therm);
+               return 0;
+       case NVKM_THERM_ATTR_THRS_DOWN_CLK:
+               priv->bios_sensor.thrs_down_clock.temp = value;
+               priv->sensor.program_alarms(therm);
+               return 0;
+       case NVKM_THERM_ATTR_THRS_DOWN_CLK_HYST:
+               priv->bios_sensor.thrs_down_clock.hysteresis = value;
+               priv->sensor.program_alarms(therm);
+               return 0;
+       case NVKM_THERM_ATTR_THRS_CRITICAL:
+               priv->bios_sensor.thrs_critical.temp = value;
+               priv->sensor.program_alarms(therm);
+               return 0;
+       case NVKM_THERM_ATTR_THRS_CRITICAL_HYST:
+               priv->bios_sensor.thrs_critical.hysteresis = value;
+               priv->sensor.program_alarms(therm);
+               return 0;
+       case NVKM_THERM_ATTR_THRS_SHUTDOWN:
+               priv->bios_sensor.thrs_shutdown.temp = value;
+               priv->sensor.program_alarms(therm);
+               return 0;
+       case NVKM_THERM_ATTR_THRS_SHUTDOWN_HYST:
+               priv->bios_sensor.thrs_shutdown.hysteresis = value;
+               priv->sensor.program_alarms(therm);
+               return 0;
+       }
+
+       return -EINVAL;
+}
+
+int
+_nvkm_therm_init(struct nvkm_object *object)
+{
+       struct nvkm_therm *therm = (void *)object;
+       struct nvkm_therm_priv *priv = (void *)therm;
+       int ret;
+
+       ret = nvkm_subdev_init(&therm->base);
+       if (ret)
+               return ret;
+
+       if (priv->suspend >= 0) {
+               /* restore the pwm value only when on manual or auto mode */
+               if (priv->suspend > 0)
+                       nvkm_therm_fan_set(therm, true, priv->fan->percent);
+
+               nvkm_therm_fan_mode(therm, priv->suspend);
+       }
+       nvkm_therm_sensor_init(therm);
+       nvkm_therm_fan_init(therm);
+       return 0;
+}
+
+int
+_nvkm_therm_fini(struct nvkm_object *object, bool suspend)
+{
+       struct nvkm_therm *therm = (void *)object;
+       struct nvkm_therm_priv *priv = (void *)therm;
+
+       nvkm_therm_fan_fini(therm, suspend);
+       nvkm_therm_sensor_fini(therm, suspend);
+       if (suspend) {
+               priv->suspend = priv->mode;
+               priv->mode = NVKM_THERM_CTRL_NONE;
+       }
+
+       return nvkm_subdev_fini(&therm->base, suspend);
+}
+
+int
+nvkm_therm_create_(struct nvkm_object *parent, struct nvkm_object *engine,
+                  struct nvkm_oclass *oclass, int length, void **pobject)
+{
+       struct nvkm_therm_priv *priv;
+       int ret;
+
+       ret = nvkm_subdev_create_(parent, engine, oclass, 0, "PTHERM",
+                                 "therm", length, pobject);
+       priv = *pobject;
+       if (ret)
+               return ret;
+
+       nvkm_alarm_init(&priv->alarm, nvkm_therm_alarm);
+       spin_lock_init(&priv->lock);
+       spin_lock_init(&priv->sensor.alarm_program_lock);
+
+       priv->base.fan_get = nvkm_therm_fan_user_get;
+       priv->base.fan_set = nvkm_therm_fan_user_set;
+       priv->base.fan_sense = nvkm_therm_fan_sense;
+       priv->base.attr_get = nvkm_therm_attr_get;
+       priv->base.attr_set = nvkm_therm_attr_set;
+       priv->mode = priv->suspend = -1; /* undefined */
+       return 0;
+}
+
+int
+nvkm_therm_preinit(struct nvkm_therm *therm)
+{
+       nvkm_therm_sensor_ctor(therm);
+       nvkm_therm_ic_ctor(therm);
+       nvkm_therm_fan_ctor(therm);
+
+       nvkm_therm_fan_mode(therm, NVKM_THERM_CTRL_AUTO);
+       nvkm_therm_sensor_preinit(therm);
+       return 0;
+}
+
+void
+_nvkm_therm_dtor(struct nvkm_object *object)
+{
+       struct nvkm_therm_priv *priv = (void *)object;
+       kfree(priv->fan);
+       nvkm_subdev_destroy(&priv->base.base);
+}
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/therm/fan.c b/drivers/gpu/drm/nouveau/nvkm/subdev/therm/fan.c
new file mode 100644 (file)
index 0000000..434fa74
--- /dev/null
@@ -0,0 +1,282 @@
+/*
+ * Copyright 2012 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
+ *         Martin Peres
+ */
+#include "priv.h"
+
+#include <subdev/bios/fan.h>
+#include <subdev/gpio.h>
+#include <subdev/timer.h>
+
+static int
+nvkm_fan_update(struct nvkm_fan *fan, bool immediate, int target)
+{
+       struct nvkm_therm *therm = fan->parent;
+       struct nvkm_therm_priv *priv = (void *)therm;
+       struct nvkm_timer *ptimer = nvkm_timer(priv);
+       unsigned long flags;
+       int ret = 0;
+       int duty;
+
+       /* update target fan speed, restricting to allowed range */
+       spin_lock_irqsave(&fan->lock, flags);
+       if (target < 0)
+               target = fan->percent;
+       target = max_t(u8, target, fan->bios.min_duty);
+       target = min_t(u8, target, fan->bios.max_duty);
+       if (fan->percent != target) {
+               nv_debug(therm, "FAN target: %d\n", target);
+               fan->percent = target;
+       }
+
+       /* check that we're not already at the target duty cycle */
+       duty = fan->get(therm);
+       if (duty == target) {
+               spin_unlock_irqrestore(&fan->lock, flags);
+               return 0;
+       }
+
+       /* smooth out the fanspeed increase/decrease */
+       if (!immediate && duty >= 0) {
+               /* the constant "3" is a rough approximation taken from
+                * nvidia's behaviour.
+                * it is meant to bump the fan speed more incrementally
+                */
+               if (duty < target)
+                       duty = min(duty + 3, target);
+               else if (duty > target)
+                       duty = max(duty - 3, target);
+       } else {
+               duty = target;
+       }
+
+       nv_debug(therm, "FAN update: %d\n", duty);
+       ret = fan->set(therm, duty);
+       if (ret) {
+               spin_unlock_irqrestore(&fan->lock, flags);
+               return ret;
+       }
+
+       /* fan speed updated, drop the fan lock before grabbing the
+        * alarm-scheduling lock and risking a deadlock
+        */
+       spin_unlock_irqrestore(&fan->lock, flags);
+
+       /* schedule next fan update, if not at target speed already */
+       if (list_empty(&fan->alarm.head) && target != duty) {
+               u16 bump_period = fan->bios.bump_period;
+               u16 slow_down_period = fan->bios.slow_down_period;
+               u64 delay;
+
+               if (duty > target)
+                       delay = slow_down_period;
+               else if (duty == target)
+                       delay = min(bump_period, slow_down_period) ;
+               else
+                       delay = bump_period;
+
+               ptimer->alarm(ptimer, delay * 1000 * 1000, &fan->alarm);
+       }
+
+       return ret;
+}
+
+static void
+nvkm_fan_alarm(struct nvkm_alarm *alarm)
+{
+       struct nvkm_fan *fan = container_of(alarm, struct nvkm_fan, alarm);
+       nvkm_fan_update(fan, false, -1);
+}
+
+int
+nvkm_therm_fan_get(struct nvkm_therm *therm)
+{
+       struct nvkm_therm_priv *priv = (void *)therm;
+       return priv->fan->get(therm);
+}
+
+int
+nvkm_therm_fan_set(struct nvkm_therm *therm, bool immediate, int percent)
+{
+       struct nvkm_therm_priv *priv = (void *)therm;
+       return nvkm_fan_update(priv->fan, immediate, percent);
+}
+
+int
+nvkm_therm_fan_sense(struct nvkm_therm *therm)
+{
+       struct nvkm_therm_priv *priv = (void *)therm;
+       struct nvkm_timer *ptimer = nvkm_timer(therm);
+       struct nvkm_gpio *gpio = nvkm_gpio(therm);
+       u32 cycles, cur, prev;
+       u64 start, end, tach;
+
+       if (priv->fan->tach.func == DCB_GPIO_UNUSED)
+               return -ENODEV;
+
+       /* Time a complete rotation and extrapolate to RPM:
+        * When the fan spins, it changes the value of GPIO FAN_SENSE.
+        * We get 4 changes (0 -> 1 -> 0 -> 1) per complete rotation.
+        */
+       start = ptimer->read(ptimer);
+       prev = gpio->get(gpio, 0, priv->fan->tach.func, priv->fan->tach.line);
+       cycles = 0;
+       do {
+               usleep_range(500, 1000); /* supports 0 < rpm < 7500 */
+
+               cur = gpio->get(gpio, 0, priv->fan->tach.func, priv->fan->tach.line);
+               if (prev != cur) {
+                       if (!start)
+                               start = ptimer->read(ptimer);
+                       cycles++;
+                       prev = cur;
+               }
+       } while (cycles < 5 && ptimer->read(ptimer) - start < 250000000);
+       end = ptimer->read(ptimer);
+
+       if (cycles == 5) {
+               tach = (u64)60000000000ULL;
+               do_div(tach, (end - start));
+               return tach;
+       } else
+               return 0;
+}
+
+int
+nvkm_therm_fan_user_get(struct nvkm_therm *therm)
+{
+       return nvkm_therm_fan_get(therm);
+}
+
+int
+nvkm_therm_fan_user_set(struct nvkm_therm *therm, int percent)
+{
+       struct nvkm_therm_priv *priv = (void *)therm;
+
+       if (priv->mode != NVKM_THERM_CTRL_MANUAL)
+               return -EINVAL;
+
+       return nvkm_therm_fan_set(therm, true, percent);
+}
+
+static void
+nvkm_therm_fan_set_defaults(struct nvkm_therm *therm)
+{
+       struct nvkm_therm_priv *priv = (void *)therm;
+
+       priv->fan->bios.pwm_freq = 0;
+       priv->fan->bios.min_duty = 0;
+       priv->fan->bios.max_duty = 100;
+       priv->fan->bios.bump_period = 500;
+       priv->fan->bios.slow_down_period = 2000;
+       priv->fan->bios.linear_min_temp = 40;
+       priv->fan->bios.linear_max_temp = 85;
+}
+
+static void
+nvkm_therm_fan_safety_checks(struct nvkm_therm *therm)
+{
+       struct nvkm_therm_priv *priv = (void *)therm;
+
+       if (priv->fan->bios.min_duty > 100)
+               priv->fan->bios.min_duty = 100;
+       if (priv->fan->bios.max_duty > 100)
+               priv->fan->bios.max_duty = 100;
+
+       if (priv->fan->bios.min_duty > priv->fan->bios.max_duty)
+               priv->fan->bios.min_duty = priv->fan->bios.max_duty;
+}
+
+int
+nvkm_therm_fan_init(struct nvkm_therm *therm)
+{
+       return 0;
+}
+
+int
+nvkm_therm_fan_fini(struct nvkm_therm *therm, bool suspend)
+{
+       struct nvkm_therm_priv *priv = (void *)therm;
+       struct nvkm_timer *ptimer = nvkm_timer(therm);
+
+       if (suspend)
+               ptimer->alarm_cancel(ptimer, &priv->fan->alarm);
+       return 0;
+}
+
+int
+nvkm_therm_fan_ctor(struct nvkm_therm *therm)
+{
+       struct nvkm_therm_priv *priv = (void *)therm;
+       struct nvkm_gpio *gpio = nvkm_gpio(therm);
+       struct nvkm_bios *bios = nvkm_bios(therm);
+       struct dcb_gpio_func func;
+       int ret;
+
+       /* attempt to locate a drivable fan, and determine control method */
+       ret = gpio->find(gpio, 0, DCB_GPIO_FAN, 0xff, &func);
+       if (ret == 0) {
+               /* FIXME: is this really the place to perform such checks ? */
+               if (func.line != 16 && func.log[0] & DCB_GPIO_LOG_DIR_IN) {
+                       nv_debug(therm, "GPIO_FAN is in input mode\n");
+                       ret = -EINVAL;
+               } else {
+                       ret = nvkm_fanpwm_create(therm, &func);
+                       if (ret != 0)
+                               ret = nvkm_fantog_create(therm, &func);
+               }
+       }
+
+       /* no controllable fan found, create a dummy fan module */
+       if (ret != 0) {
+               ret = nvkm_fannil_create(therm);
+               if (ret)
+                       return ret;
+       }
+
+       nv_info(therm, "FAN control: %s\n", priv->fan->type);
+
+       /* read the current speed, it is useful when resuming */
+       priv->fan->percent = nvkm_therm_fan_get(therm);
+
+       /* attempt to detect a tachometer connection */
+       ret = gpio->find(gpio, 0, DCB_GPIO_FAN_SENSE, 0xff, &priv->fan->tach);
+       if (ret)
+               priv->fan->tach.func = DCB_GPIO_UNUSED;
+
+       /* initialise fan bump/slow update handling */
+       priv->fan->parent = therm;
+       nvkm_alarm_init(&priv->fan->alarm, nvkm_fan_alarm);
+       spin_lock_init(&priv->fan->lock);
+
+       /* other random init... */
+       nvkm_therm_fan_set_defaults(therm);
+       nvbios_perf_fan_parse(bios, &priv->fan->perf);
+       if (!nvbios_fan_parse(bios, &priv->fan->bios)) {
+               nv_debug(therm, "parsing the fan table failed\n");
+               if (nvbios_therm_fan_parse(bios, &priv->fan->bios))
+                       nv_error(therm, "parsing both fan tables failed\n");
+       }
+       nvkm_therm_fan_safety_checks(therm);
+       return 0;
+}
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/therm/fannil.c b/drivers/gpu/drm/nouveau/nvkm/subdev/therm/fannil.c
new file mode 100644 (file)
index 0000000..534e597
--- /dev/null
@@ -0,0 +1,53 @@
+/*
+ * Copyright 2012 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 "priv.h"
+
+static int
+nvkm_fannil_get(struct nvkm_therm *therm)
+{
+       return -ENODEV;
+}
+
+static int
+nvkm_fannil_set(struct nvkm_therm *therm, int percent)
+{
+       return -ENODEV;
+}
+
+int
+nvkm_fannil_create(struct nvkm_therm *therm)
+{
+       struct nvkm_therm_priv *tpriv = (void *)therm;
+       struct nvkm_fan *priv;
+
+       priv = kzalloc(sizeof(*priv), GFP_KERNEL);
+       tpriv->fan = priv;
+       if (!priv)
+               return -ENOMEM;
+
+       priv->type = "none / external";
+       priv->get = nvkm_fannil_get;
+       priv->set = nvkm_fannil_set;
+       return 0;
+}
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/therm/fanpwm.c b/drivers/gpu/drm/nouveau/nvkm/subdev/therm/fanpwm.c
new file mode 100644 (file)
index 0000000..bde5cea
--- /dev/null
@@ -0,0 +1,113 @@
+/*
+ * Copyright 2012 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
+ *         Martin Peres
+ */
+#include "priv.h"
+
+#include <core/device.h>
+#include <core/option.h>
+#include <subdev/bios.h>
+#include <subdev/bios/fan.h>
+#include <subdev/gpio.h>
+
+struct nvkm_fanpwm_priv {
+       struct nvkm_fan base;
+       struct dcb_gpio_func func;
+};
+
+static int
+nvkm_fanpwm_get(struct nvkm_therm *therm)
+{
+       struct nvkm_therm_priv *tpriv = (void *)therm;
+       struct nvkm_fanpwm_priv *priv = (void *)tpriv->fan;
+       struct nvkm_gpio *gpio = nvkm_gpio(therm);
+       int card_type = nv_device(therm)->card_type;
+       u32 divs, duty;
+       int ret;
+
+       ret = therm->pwm_get(therm, priv->func.line, &divs, &duty);
+       if (ret == 0 && divs) {
+               divs = max(divs, duty);
+               if (card_type <= NV_40 || (priv->func.log[0] & 1))
+                       duty = divs - duty;
+               return (duty * 100) / divs;
+       }
+
+       return gpio->get(gpio, 0, priv->func.func, priv->func.line) * 100;
+}
+
+static int
+nvkm_fanpwm_set(struct nvkm_therm *therm, int percent)
+{
+       struct nvkm_therm_priv *tpriv = (void *)therm;
+       struct nvkm_fanpwm_priv *priv = (void *)tpriv->fan;
+       int card_type = nv_device(therm)->card_type;
+       u32 divs, duty;
+       int ret;
+
+       divs = priv->base.perf.pwm_divisor;
+       if (priv->base.bios.pwm_freq) {
+               divs = 1;
+               if (therm->pwm_clock)
+                       divs = therm->pwm_clock(therm, priv->func.line);
+               divs /= priv->base.bios.pwm_freq;
+       }
+
+       duty = ((divs * percent) + 99) / 100;
+       if (card_type <= NV_40 || (priv->func.log[0] & 1))
+               duty = divs - duty;
+
+       ret = therm->pwm_set(therm, priv->func.line, divs, duty);
+       if (ret == 0)
+               ret = therm->pwm_ctrl(therm, priv->func.line, true);
+       return ret;
+}
+
+int
+nvkm_fanpwm_create(struct nvkm_therm *therm, struct dcb_gpio_func *func)
+{
+       struct nvkm_device *device = nv_device(therm);
+       struct nvkm_therm_priv *tpriv = (void *)therm;
+       struct nvkm_bios *bios = nvkm_bios(therm);
+       struct nvkm_fanpwm_priv *priv;
+       struct nvbios_therm_fan fan;
+       u32 divs, duty;
+
+       nvbios_fan_parse(bios, &fan);
+
+       if (!nvkm_boolopt(device->cfgopt, "NvFanPWM", func->param) ||
+           !therm->pwm_ctrl || fan.type == NVBIOS_THERM_FAN_TOGGLE ||
+            therm->pwm_get(therm, func->line, &divs, &duty) == -ENODEV)
+               return -ENODEV;
+
+       priv = kzalloc(sizeof(*priv), GFP_KERNEL);
+       tpriv->fan = &priv->base;
+       if (!priv)
+               return -ENOMEM;
+
+       priv->base.type = "PWM";
+       priv->base.get = nvkm_fanpwm_get;
+       priv->base.set = nvkm_fanpwm_set;
+       priv->func = *func;
+       return 0;
+}
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/therm/fantog.c b/drivers/gpu/drm/nouveau/nvkm/subdev/therm/fantog.c
new file mode 100644 (file)
index 0000000..4ce041e
--- /dev/null
@@ -0,0 +1,118 @@
+/*
+ * Copyright 2012 The Nouveau community
+ *
+ * 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 "priv.h"
+
+#include <subdev/gpio.h>
+#include <subdev/timer.h>
+
+struct nvkm_fantog_priv {
+       struct nvkm_fan base;
+       struct nvkm_alarm alarm;
+       spinlock_t lock;
+       u32 period_us;
+       u32 percent;
+       struct dcb_gpio_func func;
+};
+
+static void
+nvkm_fantog_update(struct nvkm_fantog_priv *priv, int percent)
+{
+       struct nvkm_therm_priv *tpriv = (void *)priv->base.parent;
+       struct nvkm_timer *ptimer = nvkm_timer(tpriv);
+       struct nvkm_gpio *gpio = nvkm_gpio(tpriv);
+       unsigned long flags;
+       int duty;
+
+       spin_lock_irqsave(&priv->lock, flags);
+       if (percent < 0)
+               percent = priv->percent;
+       priv->percent = percent;
+
+       duty = !gpio->get(gpio, 0, DCB_GPIO_FAN, 0xff);
+       gpio->set(gpio, 0, DCB_GPIO_FAN, 0xff, duty);
+
+       if (list_empty(&priv->alarm.head) && percent != (duty * 100)) {
+               u64 next_change = (percent * priv->period_us) / 100;
+               if (!duty)
+                       next_change = priv->period_us - next_change;
+               ptimer->alarm(ptimer, next_change * 1000, &priv->alarm);
+       }
+       spin_unlock_irqrestore(&priv->lock, flags);
+}
+
+static void
+nvkm_fantog_alarm(struct nvkm_alarm *alarm)
+{
+       struct nvkm_fantog_priv *priv =
+              container_of(alarm, struct nvkm_fantog_priv, alarm);
+       nvkm_fantog_update(priv, -1);
+}
+
+static int
+nvkm_fantog_get(struct nvkm_therm *therm)
+{
+       struct nvkm_therm_priv *tpriv = (void *)therm;
+       struct nvkm_fantog_priv *priv = (void *)tpriv->fan;
+       return priv->percent;
+}
+
+static int
+nvkm_fantog_set(struct nvkm_therm *therm, int percent)
+{
+       struct nvkm_therm_priv *tpriv = (void *)therm;
+       struct nvkm_fantog_priv *priv = (void *)tpriv->fan;
+       if (therm->pwm_ctrl)
+               therm->pwm_ctrl(therm, priv->func.line, false);
+       nvkm_fantog_update(priv, percent);
+       return 0;
+}
+
+int
+nvkm_fantog_create(struct nvkm_therm *therm, struct dcb_gpio_func *func)
+{
+       struct nvkm_therm_priv *tpriv = (void *)therm;
+       struct nvkm_fantog_priv *priv;
+       int ret;
+
+       if (therm->pwm_ctrl) {
+               ret = therm->pwm_ctrl(therm, func->line, false);
+               if (ret)
+                       return ret;
+       }
+
+       priv = kzalloc(sizeof(*priv), GFP_KERNEL);
+       tpriv->fan = &priv->base;
+       if (!priv)
+               return -ENOMEM;
+
+       priv->base.type = "toggle";
+       priv->base.get = nvkm_fantog_get;
+       priv->base.set = nvkm_fantog_set;
+       nvkm_alarm_init(&priv->alarm, nvkm_fantog_alarm);
+       priv->period_us = 100000; /* 10Hz */
+       priv->percent = 100;
+       priv->func = *func;
+       spin_lock_init(&priv->lock);
+       return 0;
+}
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/therm/g84.c b/drivers/gpu/drm/nouveau/nvkm/subdev/therm/g84.c
new file mode 100644 (file)
index 0000000..85b5d0c
--- /dev/null
@@ -0,0 +1,266 @@
+/*
+ * Copyright 2012 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
+ *         Martin Peres
+ */
+#include "priv.h"
+
+#include <subdev/fuse.h>
+
+struct g84_therm_priv {
+       struct nvkm_therm_priv base;
+};
+
+int
+g84_temp_get(struct nvkm_therm *therm)
+{
+       struct nvkm_fuse *fuse = nvkm_fuse(therm);
+
+       if (nv_ro32(fuse, 0x1a8) == 1)
+               return nv_rd32(therm, 0x20400);
+       else
+               return -ENODEV;
+}
+
+void
+g84_sensor_setup(struct nvkm_therm *therm)
+{
+       struct nvkm_fuse *fuse = nvkm_fuse(therm);
+
+       /* enable temperature reading for cards with insane defaults */
+       if (nv_ro32(fuse, 0x1a8) == 1) {
+               nv_mask(therm, 0x20008, 0x80008000, 0x80000000);
+               nv_mask(therm, 0x2000c, 0x80000003, 0x00000000);
+               mdelay(20); /* wait for the temperature to stabilize */
+       }
+}
+
+static void
+g84_therm_program_alarms(struct nvkm_therm *therm)
+{
+       struct nvkm_therm_priv *priv = (void *)therm;
+       struct nvbios_therm_sensor *sensor = &priv->bios_sensor;
+       unsigned long flags;
+
+       spin_lock_irqsave(&priv->sensor.alarm_program_lock, flags);
+
+       /* enable RISING and FALLING IRQs for shutdown, THRS 0, 1, 2 and 4 */
+       nv_wr32(therm, 0x20000, 0x000003ff);
+
+       /* shutdown: The computer should be shutdown when reached */
+       nv_wr32(therm, 0x20484, sensor->thrs_shutdown.hysteresis);
+       nv_wr32(therm, 0x20480, sensor->thrs_shutdown.temp);
+
+       /* THRS_1 : fan boost*/
+       nv_wr32(therm, 0x204c4, sensor->thrs_fan_boost.temp);
+
+       /* THRS_2 : critical */
+       nv_wr32(therm, 0x204c0, sensor->thrs_critical.temp);
+
+       /* THRS_4 : down clock */
+       nv_wr32(therm, 0x20414, sensor->thrs_down_clock.temp);
+       spin_unlock_irqrestore(&priv->sensor.alarm_program_lock, flags);
+
+       nv_debug(therm,
+                "Programmed thresholds [ %d(%d), %d(%d), %d(%d), %d(%d) ]\n",
+                sensor->thrs_fan_boost.temp, sensor->thrs_fan_boost.hysteresis,
+                sensor->thrs_down_clock.temp,
+                sensor->thrs_down_clock.hysteresis,
+                sensor->thrs_critical.temp, sensor->thrs_critical.hysteresis,
+                sensor->thrs_shutdown.temp, sensor->thrs_shutdown.hysteresis);
+
+}
+
+/* must be called with alarm_program_lock taken ! */
+static void
+g84_therm_threshold_hyst_emulation(struct nvkm_therm *therm,
+                                  uint32_t thrs_reg, u8 status_bit,
+                                  const struct nvbios_therm_threshold *thrs,
+                                  enum nvkm_therm_thrs thrs_name)
+{
+       enum nvkm_therm_thrs_direction direction;
+       enum nvkm_therm_thrs_state prev_state, new_state;
+       int temp, cur;
+
+       prev_state = nvkm_therm_sensor_get_threshold_state(therm, thrs_name);
+       temp = nv_rd32(therm, thrs_reg);
+
+       /* program the next threshold */
+       if (temp == thrs->temp) {
+               nv_wr32(therm, thrs_reg, thrs->temp - thrs->hysteresis);
+               new_state = NVKM_THERM_THRS_HIGHER;
+       } else {
+               nv_wr32(therm, thrs_reg, thrs->temp);
+               new_state = NVKM_THERM_THRS_LOWER;
+       }
+
+       /* fix the state (in case someone reprogrammed the alarms) */
+       cur = therm->temp_get(therm);
+       if (new_state == NVKM_THERM_THRS_LOWER && cur > thrs->temp)
+               new_state = NVKM_THERM_THRS_HIGHER;
+       else if (new_state == NVKM_THERM_THRS_HIGHER &&
+               cur < thrs->temp - thrs->hysteresis)
+               new_state = NVKM_THERM_THRS_LOWER;
+       nvkm_therm_sensor_set_threshold_state(therm, thrs_name, new_state);
+
+       /* find the direction */
+       if (prev_state < new_state)
+               direction = NVKM_THERM_THRS_RISING;
+       else if (prev_state > new_state)
+               direction = NVKM_THERM_THRS_FALLING;
+       else
+               return;
+
+       /* advertise a change in direction */
+       nvkm_therm_sensor_event(therm, thrs_name, direction);
+}
+
+static void
+g84_therm_intr(struct nvkm_subdev *subdev)
+{
+       struct nvkm_therm *therm = nvkm_therm(subdev);
+       struct nvkm_therm_priv *priv = (void *)therm;
+       struct nvbios_therm_sensor *sensor = &priv->bios_sensor;
+       unsigned long flags;
+       uint32_t intr;
+
+       spin_lock_irqsave(&priv->sensor.alarm_program_lock, flags);
+
+       intr = nv_rd32(therm, 0x20100) & 0x3ff;
+
+       /* THRS_4: downclock */
+       if (intr & 0x002) {
+               g84_therm_threshold_hyst_emulation(therm, 0x20414, 24,
+                                                  &sensor->thrs_down_clock,
+                                                  NVKM_THERM_THRS_DOWNCLOCK);
+               intr &= ~0x002;
+       }
+
+       /* shutdown */
+       if (intr & 0x004) {
+               g84_therm_threshold_hyst_emulation(therm, 0x20480, 20,
+                                                  &sensor->thrs_shutdown,
+                                                  NVKM_THERM_THRS_SHUTDOWN);
+               intr &= ~0x004;
+       }
+
+       /* THRS_1 : fan boost */
+       if (intr & 0x008) {
+               g84_therm_threshold_hyst_emulation(therm, 0x204c4, 21,
+                                                  &sensor->thrs_fan_boost,
+                                                  NVKM_THERM_THRS_FANBOOST);
+               intr &= ~0x008;
+       }
+
+       /* THRS_2 : critical */
+       if (intr & 0x010) {
+               g84_therm_threshold_hyst_emulation(therm, 0x204c0, 22,
+                                                  &sensor->thrs_critical,
+                                                  NVKM_THERM_THRS_CRITICAL);
+               intr &= ~0x010;
+       }
+
+       if (intr)
+               nv_error(therm, "unhandled intr 0x%08x\n", intr);
+
+       /* ACK everything */
+       nv_wr32(therm, 0x20100, 0xffffffff);
+       nv_wr32(therm, 0x1100, 0x10000); /* PBUS */
+
+       spin_unlock_irqrestore(&priv->sensor.alarm_program_lock, flags);
+}
+
+static int
+g84_therm_init(struct nvkm_object *object)
+{
+       struct g84_therm_priv *priv = (void *)object;
+       int ret;
+
+       ret = nvkm_therm_init(&priv->base.base);
+       if (ret)
+               return ret;
+
+       g84_sensor_setup(&priv->base.base);
+       return 0;
+}
+
+static int
+g84_therm_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+              struct nvkm_oclass *oclass, void *data, u32 size,
+              struct nvkm_object **pobject)
+{
+       struct g84_therm_priv *priv;
+       int ret;
+
+       ret = nvkm_therm_create(parent, engine, oclass, &priv);
+       *pobject = nv_object(priv);
+       if (ret)
+               return ret;
+
+       priv->base.base.pwm_ctrl = nv50_fan_pwm_ctrl;
+       priv->base.base.pwm_get = nv50_fan_pwm_get;
+       priv->base.base.pwm_set = nv50_fan_pwm_set;
+       priv->base.base.pwm_clock = nv50_fan_pwm_clock;
+       priv->base.base.temp_get = g84_temp_get;
+       priv->base.sensor.program_alarms = g84_therm_program_alarms;
+       nv_subdev(priv)->intr = g84_therm_intr;
+
+       /* init the thresholds */
+       nvkm_therm_sensor_set_threshold_state(&priv->base.base,
+                                             NVKM_THERM_THRS_SHUTDOWN,
+                                             NVKM_THERM_THRS_LOWER);
+       nvkm_therm_sensor_set_threshold_state(&priv->base.base,
+                                             NVKM_THERM_THRS_FANBOOST,
+                                             NVKM_THERM_THRS_LOWER);
+       nvkm_therm_sensor_set_threshold_state(&priv->base.base,
+                                             NVKM_THERM_THRS_CRITICAL,
+                                             NVKM_THERM_THRS_LOWER);
+       nvkm_therm_sensor_set_threshold_state(&priv->base.base,
+                                             NVKM_THERM_THRS_DOWNCLOCK,
+                                             NVKM_THERM_THRS_LOWER);
+
+       return nvkm_therm_preinit(&priv->base.base);
+}
+
+int
+g84_therm_fini(struct nvkm_object *object, bool suspend)
+{
+       /* Disable PTherm IRQs */
+       nv_wr32(object, 0x20000, 0x00000000);
+
+       /* ACK all PTherm IRQs */
+       nv_wr32(object, 0x20100, 0xffffffff);
+       nv_wr32(object, 0x1100, 0x10000); /* PBUS */
+
+       return _nvkm_therm_fini(object, suspend);
+}
+
+struct nvkm_oclass
+g84_therm_oclass = {
+       .handle = NV_SUBDEV(THERM, 0x84),
+       .ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = g84_therm_ctor,
+               .dtor = _nvkm_therm_dtor,
+               .init = g84_therm_init,
+               .fini = g84_therm_fini,
+       },
+};
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/therm/gf110.c b/drivers/gpu/drm/nouveau/nvkm/subdev/therm/gf110.c
new file mode 100644 (file)
index 0000000..46b7e65
--- /dev/null
@@ -0,0 +1,174 @@
+/*
+ * Copyright 2012 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 "priv.h"
+
+#include <core/device.h>
+
+struct gf110_therm_priv {
+       struct nvkm_therm_priv base;
+};
+
+static int
+pwm_info(struct nvkm_therm *therm, int line)
+{
+       u32 gpio = nv_rd32(therm, 0x00d610 + (line * 0x04));
+
+       switch (gpio & 0x000000c0) {
+       case 0x00000000: /* normal mode, possibly pwm forced off by us */
+       case 0x00000040: /* nvio special */
+               switch (gpio & 0x0000001f) {
+               case 0x00: return 2;
+               case 0x19: return 1;
+               case 0x1c: return 0;
+               case 0x1e: return 2;
+               default:
+                       break;
+               }
+       default:
+               break;
+       }
+
+       nv_error(therm, "GPIO %d unknown PWM: 0x%08x\n", line, gpio);
+       return -ENODEV;
+}
+
+static int
+gf110_fan_pwm_ctrl(struct nvkm_therm *therm, int line, bool enable)
+{
+       u32 data = enable ? 0x00000040 : 0x00000000;
+       int indx = pwm_info(therm, line);
+       if (indx < 0)
+               return indx;
+       else if (indx < 2)
+               nv_mask(therm, 0x00d610 + (line * 0x04), 0x000000c0, data);
+       /* nothing to do for indx == 2, it seems hardwired to PTHERM */
+       return 0;
+}
+
+static int
+gf110_fan_pwm_get(struct nvkm_therm *therm, int line, u32 *divs, u32 *duty)
+{
+       int indx = pwm_info(therm, line);
+       if (indx < 0)
+               return indx;
+       else if (indx < 2) {
+               if (nv_rd32(therm, 0x00d610 + (line * 0x04)) & 0x00000040) {
+                       *divs = nv_rd32(therm, 0x00e114 + (indx * 8));
+                       *duty = nv_rd32(therm, 0x00e118 + (indx * 8));
+                       return 0;
+               }
+       } else if (indx == 2) {
+               *divs = nv_rd32(therm, 0x0200d8) & 0x1fff;
+               *duty = nv_rd32(therm, 0x0200dc) & 0x1fff;
+               return 0;
+       }
+
+       return -EINVAL;
+}
+
+static int
+gf110_fan_pwm_set(struct nvkm_therm *therm, int line, u32 divs, u32 duty)
+{
+       int indx = pwm_info(therm, line);
+       if (indx < 0)
+               return indx;
+       else if (indx < 2) {
+               nv_wr32(therm, 0x00e114 + (indx * 8), divs);
+               nv_wr32(therm, 0x00e118 + (indx * 8), duty | 0x80000000);
+       } else if (indx == 2) {
+               nv_mask(therm, 0x0200d8, 0x1fff, divs); /* keep the high bits */
+               nv_wr32(therm, 0x0200dc, duty | 0x40000000);
+       }
+       return 0;
+}
+
+static int
+gf110_fan_pwm_clock(struct nvkm_therm *therm, int line)
+{
+       int indx = pwm_info(therm, line);
+       if (indx < 0)
+               return 0;
+       else if (indx < 2)
+               return (nv_device(therm)->crystal * 1000) / 20;
+       else
+               return nv_device(therm)->crystal * 1000 / 10;
+}
+
+int
+gf110_therm_init(struct nvkm_object *object)
+{
+       struct gf110_therm_priv *priv = (void *)object;
+       int ret;
+
+       ret = nvkm_therm_init(&priv->base.base);
+       if (ret)
+               return ret;
+
+       /* enable fan tach, count revolutions per-second */
+       nv_mask(priv, 0x00e720, 0x00000003, 0x00000002);
+       if (priv->base.fan->tach.func != DCB_GPIO_UNUSED) {
+               nv_mask(priv, 0x00d79c, 0x000000ff, priv->base.fan->tach.line);
+               nv_wr32(priv, 0x00e724, nv_device(priv)->crystal * 1000);
+               nv_mask(priv, 0x00e720, 0x00000001, 0x00000001);
+       }
+       nv_mask(priv, 0x00e720, 0x00000002, 0x00000000);
+
+       return 0;
+}
+
+static int
+gf110_therm_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+                struct nvkm_oclass *oclass, void *data, u32 size,
+                struct nvkm_object **pobject)
+{
+       struct gf110_therm_priv *priv;
+       int ret;
+
+       ret = nvkm_therm_create(parent, engine, oclass, &priv);
+       *pobject = nv_object(priv);
+       if (ret)
+               return ret;
+
+       g84_sensor_setup(&priv->base.base);
+
+       priv->base.base.pwm_ctrl = gf110_fan_pwm_ctrl;
+       priv->base.base.pwm_get = gf110_fan_pwm_get;
+       priv->base.base.pwm_set = gf110_fan_pwm_set;
+       priv->base.base.pwm_clock = gf110_fan_pwm_clock;
+       priv->base.base.temp_get = g84_temp_get;
+       priv->base.base.fan_sense = gt215_therm_fan_sense;
+       priv->base.sensor.program_alarms = nvkm_therm_program_alarms_polling;
+       return nvkm_therm_preinit(&priv->base.base);
+}
+
+struct nvkm_oclass
+gf110_therm_oclass = {
+       .handle = NV_SUBDEV(THERM, 0xd0),
+       .ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = gf110_therm_ctor,
+               .dtor = _nvkm_therm_dtor,
+               .init = gf110_therm_init,
+               .fini = g84_therm_fini,
+       },
+};
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/therm/gm107.c b/drivers/gpu/drm/nouveau/nvkm/subdev/therm/gm107.c
new file mode 100644 (file)
index 0000000..2fd110f
--- /dev/null
@@ -0,0 +1,93 @@
+/*
+ * Copyright 2014 Martin Peres
+ *
+ * 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 "priv.h"
+
+#include <core/device.h>
+
+struct gm107_therm_priv {
+       struct nvkm_therm_priv base;
+};
+
+static int
+gm107_fan_pwm_ctrl(struct nvkm_therm *therm, int line, bool enable)
+{
+       /* nothing to do, it seems hardwired */
+       return 0;
+}
+
+static int
+gm107_fan_pwm_get(struct nvkm_therm *therm, int line, u32 *divs, u32 *duty)
+{
+       *divs = nv_rd32(therm, 0x10eb20) & 0x1fff;
+       *duty = nv_rd32(therm, 0x10eb24) & 0x1fff;
+       return 0;
+}
+
+static int
+gm107_fan_pwm_set(struct nvkm_therm *therm, int line, u32 divs, u32 duty)
+{
+       nv_mask(therm, 0x10eb10, 0x1fff, divs); /* keep the high bits */
+       nv_wr32(therm, 0x10eb14, duty | 0x80000000);
+       return 0;
+}
+
+static int
+gm107_fan_pwm_clock(struct nvkm_therm *therm, int line)
+{
+       return nv_device(therm)->crystal * 1000;
+}
+
+static int
+gm107_therm_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+                struct nvkm_oclass *oclass, void *data, u32 size,
+                struct nvkm_object **pobject)
+{
+       struct gm107_therm_priv *priv;
+       int ret;
+
+       ret = nvkm_therm_create(parent, engine, oclass, &priv);
+       *pobject = nv_object(priv);
+       if (ret)
+               return ret;
+
+       priv->base.base.pwm_ctrl = gm107_fan_pwm_ctrl;
+       priv->base.base.pwm_get = gm107_fan_pwm_get;
+       priv->base.base.pwm_set = gm107_fan_pwm_set;
+       priv->base.base.pwm_clock = gm107_fan_pwm_clock;
+       priv->base.base.temp_get = g84_temp_get;
+       priv->base.base.fan_sense = gt215_therm_fan_sense;
+       priv->base.sensor.program_alarms = nvkm_therm_program_alarms_polling;
+       return nvkm_therm_preinit(&priv->base.base);
+}
+
+struct nvkm_oclass
+gm107_therm_oclass = {
+       .handle = NV_SUBDEV(THERM, 0x117),
+       .ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = gm107_therm_ctor,
+               .dtor = _nvkm_therm_dtor,
+               .init = gf110_therm_init,
+               .fini = g84_therm_fini,
+       },
+};
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/therm/gt215.c b/drivers/gpu/drm/nouveau/nvkm/subdev/therm/gt215.c
new file mode 100644 (file)
index 0000000..e99be20
--- /dev/null
@@ -0,0 +1,100 @@
+/*
+ * Copyright 2012 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 "priv.h"
+
+#include <core/device.h>
+#include <subdev/gpio.h>
+
+struct gt215_therm_priv {
+       struct nvkm_therm_priv base;
+};
+
+int
+gt215_therm_fan_sense(struct nvkm_therm *therm)
+{
+       u32 tach = nv_rd32(therm, 0x00e728) & 0x0000ffff;
+       u32 ctrl = nv_rd32(therm, 0x00e720);
+       if (ctrl & 0x00000001)
+               return tach * 60 / 2;
+       return -ENODEV;
+}
+
+static int
+gt215_therm_init(struct nvkm_object *object)
+{
+       struct gt215_therm_priv *priv = (void *)object;
+       struct dcb_gpio_func *tach = &priv->base.fan->tach;
+       int ret;
+
+       ret = nvkm_therm_init(&priv->base.base);
+       if (ret)
+               return ret;
+
+       g84_sensor_setup(&priv->base.base);
+
+       /* enable fan tach, count revolutions per-second */
+       nv_mask(priv, 0x00e720, 0x00000003, 0x00000002);
+       if (tach->func != DCB_GPIO_UNUSED) {
+               nv_wr32(priv, 0x00e724, nv_device(priv)->crystal * 1000);
+               nv_mask(priv, 0x00e720, 0x001f0000, tach->line << 16);
+               nv_mask(priv, 0x00e720, 0x00000001, 0x00000001);
+       }
+       nv_mask(priv, 0x00e720, 0x00000002, 0x00000000);
+
+       return 0;
+}
+
+static int
+gt215_therm_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+                struct nvkm_oclass *oclass, void *data, u32 size,
+                struct nvkm_object **pobject)
+{
+       struct gt215_therm_priv *priv;
+       int ret;
+
+       ret = nvkm_therm_create(parent, engine, oclass, &priv);
+       *pobject = nv_object(priv);
+       if (ret)
+               return ret;
+
+       priv->base.base.pwm_ctrl = nv50_fan_pwm_ctrl;
+       priv->base.base.pwm_get = nv50_fan_pwm_get;
+       priv->base.base.pwm_set = nv50_fan_pwm_set;
+       priv->base.base.pwm_clock = nv50_fan_pwm_clock;
+       priv->base.base.temp_get = g84_temp_get;
+       priv->base.base.fan_sense = gt215_therm_fan_sense;
+       priv->base.sensor.program_alarms = nvkm_therm_program_alarms_polling;
+       return nvkm_therm_preinit(&priv->base.base);
+}
+
+struct nvkm_oclass
+gt215_therm_oclass = {
+       .handle = NV_SUBDEV(THERM, 0xa3),
+       .ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = gt215_therm_ctor,
+               .dtor = _nvkm_therm_dtor,
+               .init = gt215_therm_init,
+               .fini = g84_therm_fini,
+       },
+};
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/therm/ic.c b/drivers/gpu/drm/nouveau/nvkm/subdev/therm/ic.c
new file mode 100644 (file)
index 0000000..09fc460
--- /dev/null
@@ -0,0 +1,119 @@
+/*
+ * Copyright 2012 Nouveau community
+ *
+ * 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 "priv.h"
+
+#include <subdev/bios/extdev.h>
+#include <subdev/i2c.h>
+
+static bool
+probe_monitoring_device(struct nvkm_i2c_port *i2c,
+                       struct i2c_board_info *info, void *data)
+{
+       struct nvkm_therm_priv *priv = data;
+       struct nvbios_therm_sensor *sensor = &priv->bios_sensor;
+       struct i2c_client *client;
+
+       request_module("%s%s", I2C_MODULE_PREFIX, info->type);
+
+       client = i2c_new_device(&i2c->adapter, info);
+       if (!client)
+               return false;
+
+       if (!client->dev.driver ||
+           to_i2c_driver(client->dev.driver)->detect(client, info)) {
+               i2c_unregister_device(client);
+               return false;
+       }
+
+       nv_info(priv,
+               "Found an %s at address 0x%x (controlled by lm_sensors, "
+               "temp offset %+i C)\n",
+               info->type, info->addr, sensor->offset_constant);
+       priv->ic = client;
+       return true;
+}
+
+static struct nvkm_i2c_board_info
+nv_board_infos[] = {
+       { { I2C_BOARD_INFO("w83l785ts", 0x2d) }, 0 },
+       { { I2C_BOARD_INFO("w83781d", 0x2d) }, 0  },
+       { { I2C_BOARD_INFO("adt7473", 0x2e) }, 40  },
+       { { I2C_BOARD_INFO("adt7473", 0x2d) }, 40  },
+       { { I2C_BOARD_INFO("adt7473", 0x2c) }, 40  },
+       { { I2C_BOARD_INFO("f75375", 0x2e) }, 0  },
+       { { I2C_BOARD_INFO("lm99", 0x4c) }, 0  },
+       { { I2C_BOARD_INFO("lm90", 0x4c) }, 0  },
+       { { I2C_BOARD_INFO("lm90", 0x4d) }, 0  },
+       { { I2C_BOARD_INFO("adm1021", 0x18) }, 0  },
+       { { I2C_BOARD_INFO("adm1021", 0x19) }, 0  },
+       { { I2C_BOARD_INFO("adm1021", 0x1a) }, 0  },
+       { { I2C_BOARD_INFO("adm1021", 0x29) }, 0  },
+       { { I2C_BOARD_INFO("adm1021", 0x2a) }, 0  },
+       { { I2C_BOARD_INFO("adm1021", 0x2b) }, 0  },
+       { { I2C_BOARD_INFO("adm1021", 0x4c) }, 0  },
+       { { I2C_BOARD_INFO("adm1021", 0x4d) }, 0  },
+       { { I2C_BOARD_INFO("adm1021", 0x4e) }, 0  },
+       { { I2C_BOARD_INFO("lm63", 0x18) }, 0  },
+       { { I2C_BOARD_INFO("lm63", 0x4e) }, 0  },
+       { }
+};
+
+void
+nvkm_therm_ic_ctor(struct nvkm_therm *therm)
+{
+       struct nvkm_therm_priv *priv = (void *)therm;
+       struct nvkm_bios *bios = nvkm_bios(therm);
+       struct nvkm_i2c *i2c = nvkm_i2c(therm);
+       struct nvbios_extdev_func extdev_entry;
+
+       if (!nvbios_extdev_find(bios, NVBIOS_EXTDEV_LM89, &extdev_entry)) {
+               struct nvkm_i2c_board_info board[] = {
+                 { { I2C_BOARD_INFO("lm90", extdev_entry.addr >> 1) }, 0},
+                 { }
+               };
+
+               i2c->identify(i2c, NV_I2C_DEFAULT(0), "monitoring device",
+                             board, probe_monitoring_device, therm);
+               if (priv->ic)
+                       return;
+       }
+
+       if (!nvbios_extdev_find(bios, NVBIOS_EXTDEV_ADT7473, &extdev_entry)) {
+               struct nvkm_i2c_board_info board[] = {
+                 { { I2C_BOARD_INFO("adt7473", extdev_entry.addr >> 1) }, 20 },
+                 { }
+               };
+
+               i2c->identify(i2c, NV_I2C_DEFAULT(0), "monitoring device",
+                             board, probe_monitoring_device, therm);
+               if (priv->ic)
+                       return;
+       }
+
+       /* The vbios doesn't provide the address of an exisiting monitoring
+          device. Let's try our static list.
+        */
+       i2c->identify(i2c, NV_I2C_DEFAULT(0), "monitoring device",
+                     nv_board_infos, probe_monitoring_device, therm);
+}
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/therm/nv40.c b/drivers/gpu/drm/nouveau/nvkm/subdev/therm/nv40.c
new file mode 100644 (file)
index 0000000..8496fff
--- /dev/null
@@ -0,0 +1,225 @@
+/*
+ * Copyright 2012 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
+ *         Martin Peres
+ */
+#include "priv.h"
+
+#include <core/device.h>
+
+struct nv40_therm_priv {
+       struct nvkm_therm_priv base;
+};
+
+enum nv40_sensor_style { INVALID_STYLE = -1, OLD_STYLE = 0, NEW_STYLE = 1 };
+
+static enum nv40_sensor_style
+nv40_sensor_style(struct nvkm_therm *therm)
+{
+       struct nvkm_device *device = nv_device(therm);
+
+       switch (device->chipset) {
+       case 0x43:
+       case 0x44:
+       case 0x4a:
+       case 0x47:
+               return OLD_STYLE;
+
+       case 0x46:
+       case 0x49:
+       case 0x4b:
+       case 0x4e:
+       case 0x4c:
+       case 0x67:
+       case 0x68:
+       case 0x63:
+               return NEW_STYLE;
+       default:
+               return INVALID_STYLE;
+       }
+}
+
+static int
+nv40_sensor_setup(struct nvkm_therm *therm)
+{
+       enum nv40_sensor_style style = nv40_sensor_style(therm);
+
+       /* enable ADC readout and disable the ALARM threshold */
+       if (style == NEW_STYLE) {
+               nv_mask(therm, 0x15b8, 0x80000000, 0);
+               nv_wr32(therm, 0x15b0, 0x80003fff);
+               mdelay(20); /* wait for the temperature to stabilize */
+               return nv_rd32(therm, 0x15b4) & 0x3fff;
+       } else if (style == OLD_STYLE) {
+               nv_wr32(therm, 0x15b0, 0xff);
+               mdelay(20); /* wait for the temperature to stabilize */
+               return nv_rd32(therm, 0x15b4) & 0xff;
+       } else
+               return -ENODEV;
+}
+
+static int
+nv40_temp_get(struct nvkm_therm *therm)
+{
+       struct nvkm_therm_priv *priv = (void *)therm;
+       struct nvbios_therm_sensor *sensor = &priv->bios_sensor;
+       enum nv40_sensor_style style = nv40_sensor_style(therm);
+       int core_temp;
+
+       if (style == NEW_STYLE) {
+               nv_wr32(therm, 0x15b0, 0x80003fff);
+               core_temp = nv_rd32(therm, 0x15b4) & 0x3fff;
+       } else if (style == OLD_STYLE) {
+               nv_wr32(therm, 0x15b0, 0xff);
+               core_temp = nv_rd32(therm, 0x15b4) & 0xff;
+       } else
+               return -ENODEV;
+
+       /* if the slope or the offset is unset, do no use the sensor */
+       if (!sensor->slope_div || !sensor->slope_mult ||
+           !sensor->offset_num || !sensor->offset_den)
+           return -ENODEV;
+
+       core_temp = core_temp * sensor->slope_mult / sensor->slope_div;
+       core_temp = core_temp + sensor->offset_num / sensor->offset_den;
+       core_temp = core_temp + sensor->offset_constant - 8;
+
+       /* reserve negative temperatures for errors */
+       if (core_temp < 0)
+               core_temp = 0;
+
+       return core_temp;
+}
+
+static int
+nv40_fan_pwm_ctrl(struct nvkm_therm *therm, int line, bool enable)
+{
+       u32 mask = enable ? 0x80000000 : 0x0000000;
+       if      (line == 2) nv_mask(therm, 0x0010f0, 0x80000000, mask);
+       else if (line == 9) nv_mask(therm, 0x0015f4, 0x80000000, mask);
+       else {
+               nv_error(therm, "unknown pwm ctrl for gpio %d\n", line);
+               return -ENODEV;
+       }
+       return 0;
+}
+
+static int
+nv40_fan_pwm_get(struct nvkm_therm *therm, int line, u32 *divs, u32 *duty)
+{
+       if (line == 2) {
+               u32 reg = nv_rd32(therm, 0x0010f0);
+               if (reg & 0x80000000) {
+                       *duty = (reg & 0x7fff0000) >> 16;
+                       *divs = (reg & 0x00007fff);
+                       return 0;
+               }
+       } else
+       if (line == 9) {
+               u32 reg = nv_rd32(therm, 0x0015f4);
+               if (reg & 0x80000000) {
+                       *divs = nv_rd32(therm, 0x0015f8);
+                       *duty = (reg & 0x7fffffff);
+                       return 0;
+               }
+       } else {
+               nv_error(therm, "unknown pwm ctrl for gpio %d\n", line);
+               return -ENODEV;
+       }
+
+       return -EINVAL;
+}
+
+static int
+nv40_fan_pwm_set(struct nvkm_therm *therm, int line, u32 divs, u32 duty)
+{
+       if (line == 2) {
+               nv_mask(therm, 0x0010f0, 0x7fff7fff, (duty << 16) | divs);
+       } else
+       if (line == 9) {
+               nv_wr32(therm, 0x0015f8, divs);
+               nv_mask(therm, 0x0015f4, 0x7fffffff, duty);
+       } else {
+               nv_error(therm, "unknown pwm ctrl for gpio %d\n", line);
+               return -ENODEV;
+       }
+
+       return 0;
+}
+
+void
+nv40_therm_intr(struct nvkm_subdev *subdev)
+{
+       struct nvkm_therm *therm = nvkm_therm(subdev);
+       uint32_t stat = nv_rd32(therm, 0x1100);
+
+       /* traitement */
+
+       /* ack all IRQs */
+       nv_wr32(therm, 0x1100, 0x70000);
+
+       nv_error(therm, "THERM received an IRQ: stat = %x\n", stat);
+}
+
+static int
+nv40_therm_ctor(struct nvkm_object *parent,
+               struct nvkm_object *engine,
+               struct nvkm_oclass *oclass, void *data, u32 size,
+               struct nvkm_object **pobject)
+{
+       struct nv40_therm_priv *priv;
+       int ret;
+
+       ret = nvkm_therm_create(parent, engine, oclass, &priv);
+       *pobject = nv_object(priv);
+       if (ret)
+               return ret;
+
+       priv->base.base.pwm_ctrl = nv40_fan_pwm_ctrl;
+       priv->base.base.pwm_get = nv40_fan_pwm_get;
+       priv->base.base.pwm_set = nv40_fan_pwm_set;
+       priv->base.base.temp_get = nv40_temp_get;
+       priv->base.sensor.program_alarms = nvkm_therm_program_alarms_polling;
+       nv_subdev(priv)->intr = nv40_therm_intr;
+       return nvkm_therm_preinit(&priv->base.base);
+}
+
+static int
+nv40_therm_init(struct nvkm_object *object)
+{
+       struct nvkm_therm *therm = (void *)object;
+
+       nv40_sensor_setup(therm);
+
+       return _nvkm_therm_init(object);
+}
+
+struct nvkm_oclass
+nv40_therm_oclass = {
+       .handle = NV_SUBDEV(THERM, 0x40),
+       .ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = nv40_therm_ctor,
+               .dtor = _nvkm_therm_dtor,
+               .init = nv40_therm_init,
+               .fini = _nvkm_therm_fini,
+       },
+};
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/therm/nv50.c b/drivers/gpu/drm/nouveau/nvkm/subdev/therm/nv50.c
new file mode 100644 (file)
index 0000000..1ef59e8
--- /dev/null
@@ -0,0 +1,198 @@
+/*
+ * Copyright 2012 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
+ *         Martin Peres
+ */
+#include "priv.h"
+
+#include <core/device.h>
+
+struct nv50_therm_priv {
+       struct nvkm_therm_priv base;
+};
+
+static int
+pwm_info(struct nvkm_therm *therm, int *line, int *ctrl, int *indx)
+{
+       if (*line == 0x04) {
+               *ctrl = 0x00e100;
+               *line = 4;
+               *indx = 0;
+       } else
+       if (*line == 0x09) {
+               *ctrl = 0x00e100;
+               *line = 9;
+               *indx = 1;
+       } else
+       if (*line == 0x10) {
+               *ctrl = 0x00e28c;
+               *line = 0;
+               *indx = 0;
+       } else {
+               nv_error(therm, "unknown pwm ctrl for gpio %d\n", *line);
+               return -ENODEV;
+       }
+
+       return 0;
+}
+
+int
+nv50_fan_pwm_ctrl(struct nvkm_therm *therm, int line, bool enable)
+{
+       u32 data = enable ? 0x00000001 : 0x00000000;
+       int ctrl, id, ret = pwm_info(therm, &line, &ctrl, &id);
+       if (ret == 0)
+               nv_mask(therm, ctrl, 0x00010001 << line, data << line);
+       return ret;
+}
+
+int
+nv50_fan_pwm_get(struct nvkm_therm *therm, int line, u32 *divs, u32 *duty)
+{
+       int ctrl, id, ret = pwm_info(therm, &line, &ctrl, &id);
+       if (ret)
+               return ret;
+
+       if (nv_rd32(therm, ctrl) & (1 << line)) {
+               *divs = nv_rd32(therm, 0x00e114 + (id * 8));
+               *duty = nv_rd32(therm, 0x00e118 + (id * 8));
+               return 0;
+       }
+
+       return -EINVAL;
+}
+
+int
+nv50_fan_pwm_set(struct nvkm_therm *therm, int line, u32 divs, u32 duty)
+{
+       int ctrl, id, ret = pwm_info(therm, &line, &ctrl, &id);
+       if (ret)
+               return ret;
+
+       nv_wr32(therm, 0x00e114 + (id * 8), divs);
+       nv_wr32(therm, 0x00e118 + (id * 8), duty | 0x80000000);
+       return 0;
+}
+
+int
+nv50_fan_pwm_clock(struct nvkm_therm *therm, int line)
+{
+       int chipset = nv_device(therm)->chipset;
+       int crystal = nv_device(therm)->crystal;
+       int pwm_clock;
+
+       /* determine the PWM source clock */
+       if (chipset > 0x50 && chipset < 0x94) {
+               u8 pwm_div = nv_rd32(therm, 0x410c);
+               if (nv_rd32(therm, 0xc040) & 0x800000) {
+                       /* Use the HOST clock (100 MHz)
+                       * Where does this constant(2.4) comes from? */
+                       pwm_clock = (100000000 >> pwm_div) * 10 / 24;
+               } else {
+                       /* Where does this constant(20) comes from? */
+                       pwm_clock = (crystal * 1000) >> pwm_div;
+                       pwm_clock /= 20;
+               }
+       } else {
+               pwm_clock = (crystal * 1000) / 20;
+       }
+
+       return pwm_clock;
+}
+
+static void
+nv50_sensor_setup(struct nvkm_therm *therm)
+{
+       nv_mask(therm, 0x20010, 0x40000000, 0x0);
+       mdelay(20); /* wait for the temperature to stabilize */
+}
+
+static int
+nv50_temp_get(struct nvkm_therm *therm)
+{
+       struct nvkm_therm_priv *priv = (void *)therm;
+       struct nvbios_therm_sensor *sensor = &priv->bios_sensor;
+       int core_temp;
+
+       core_temp = nv_rd32(therm, 0x20014) & 0x3fff;
+
+       /* if the slope or the offset is unset, do no use the sensor */
+       if (!sensor->slope_div || !sensor->slope_mult ||
+           !sensor->offset_num || !sensor->offset_den)
+           return -ENODEV;
+
+       core_temp = core_temp * sensor->slope_mult / sensor->slope_div;
+       core_temp = core_temp + sensor->offset_num / sensor->offset_den;
+       core_temp = core_temp + sensor->offset_constant - 8;
+
+       /* reserve negative temperatures for errors */
+       if (core_temp < 0)
+               core_temp = 0;
+
+       return core_temp;
+}
+
+static int
+nv50_therm_ctor(struct nvkm_object *parent,
+               struct nvkm_object *engine,
+               struct nvkm_oclass *oclass, void *data, u32 size,
+               struct nvkm_object **pobject)
+{
+       struct nv50_therm_priv *priv;
+       int ret;
+
+       ret = nvkm_therm_create(parent, engine, oclass, &priv);
+       *pobject = nv_object(priv);
+       if (ret)
+               return ret;
+
+       priv->base.base.pwm_ctrl = nv50_fan_pwm_ctrl;
+       priv->base.base.pwm_get = nv50_fan_pwm_get;
+       priv->base.base.pwm_set = nv50_fan_pwm_set;
+       priv->base.base.pwm_clock = nv50_fan_pwm_clock;
+       priv->base.base.temp_get = nv50_temp_get;
+       priv->base.sensor.program_alarms = nvkm_therm_program_alarms_polling;
+       nv_subdev(priv)->intr = nv40_therm_intr;
+
+       return nvkm_therm_preinit(&priv->base.base);
+}
+
+static int
+nv50_therm_init(struct nvkm_object *object)
+{
+       struct nvkm_therm *therm = (void *)object;
+
+       nv50_sensor_setup(therm);
+
+       return _nvkm_therm_init(object);
+}
+
+struct nvkm_oclass
+nv50_therm_oclass = {
+       .handle = NV_SUBDEV(THERM, 0x50),
+       .ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = nv50_therm_ctor,
+               .dtor = _nvkm_therm_dtor,
+               .init = nv50_therm_init,
+               .fini = _nvkm_therm_fini,
+       },
+};
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/therm/priv.h b/drivers/gpu/drm/nouveau/nvkm/subdev/therm/priv.h
new file mode 100644 (file)
index 0000000..916a149
--- /dev/null
@@ -0,0 +1,153 @@
+#ifndef __NVTHERM_PRIV_H__
+#define __NVTHERM_PRIV_H__
+/*
+ * Copyright 2012 The Nouveau community
+ *
+ * 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 <subdev/therm.h>
+#include <subdev/bios.h>
+#include <subdev/bios/extdev.h>
+#include <subdev/bios/gpio.h>
+#include <subdev/bios/perf.h>
+#include <subdev/bios/therm.h>
+#include <subdev/timer.h>
+
+struct nvkm_fan {
+       struct nvkm_therm *parent;
+       const char *type;
+
+       struct nvbios_therm_fan bios;
+       struct nvbios_perf_fan perf;
+
+       struct nvkm_alarm alarm;
+       spinlock_t lock;
+       int percent;
+
+       int (*get)(struct nvkm_therm *);
+       int (*set)(struct nvkm_therm *, int percent);
+
+       struct dcb_gpio_func tach;
+};
+
+enum nvkm_therm_thrs_direction {
+       NVKM_THERM_THRS_FALLING = 0,
+       NVKM_THERM_THRS_RISING = 1
+};
+
+enum nvkm_therm_thrs_state {
+       NVKM_THERM_THRS_LOWER = 0,
+       NVKM_THERM_THRS_HIGHER = 1
+};
+
+enum nvkm_therm_thrs {
+       NVKM_THERM_THRS_FANBOOST = 0,
+       NVKM_THERM_THRS_DOWNCLOCK = 1,
+       NVKM_THERM_THRS_CRITICAL = 2,
+       NVKM_THERM_THRS_SHUTDOWN = 3,
+       NVKM_THERM_THRS_NR
+};
+
+struct nvkm_therm_priv {
+       struct nvkm_therm base;
+
+       /* automatic thermal management */
+       struct nvkm_alarm alarm;
+       spinlock_t lock;
+       struct nvbios_therm_trip_point *last_trip;
+       int mode;
+       int cstate;
+       int suspend;
+
+       /* bios */
+       struct nvbios_therm_sensor bios_sensor;
+
+       /* fan priv */
+       struct nvkm_fan *fan;
+
+       /* alarms priv */
+       struct {
+               spinlock_t alarm_program_lock;
+               struct nvkm_alarm therm_poll_alarm;
+               enum nvkm_therm_thrs_state alarm_state[NVKM_THERM_THRS_NR];
+               void (*program_alarms)(struct nvkm_therm *);
+       } sensor;
+
+       /* what should be done if the card overheats */
+       struct {
+               void (*downclock)(struct nvkm_therm *, bool active);
+               void (*pause)(struct nvkm_therm *, bool active);
+       } emergency;
+
+       /* ic */
+       struct i2c_client *ic;
+};
+
+int nvkm_therm_fan_mode(struct nvkm_therm *, int mode);
+int nvkm_therm_attr_get(struct nvkm_therm *, enum nvkm_therm_attr_type);
+int nvkm_therm_attr_set(struct nvkm_therm *, enum nvkm_therm_attr_type, int);
+
+void nvkm_therm_ic_ctor(struct nvkm_therm *);
+
+int nvkm_therm_sensor_ctor(struct nvkm_therm *);
+
+int nvkm_therm_fan_ctor(struct nvkm_therm *);
+int nvkm_therm_fan_init(struct nvkm_therm *);
+int nvkm_therm_fan_fini(struct nvkm_therm *, bool suspend);
+int nvkm_therm_fan_get(struct nvkm_therm *);
+int nvkm_therm_fan_set(struct nvkm_therm *, bool now, int percent);
+int nvkm_therm_fan_user_get(struct nvkm_therm *);
+int nvkm_therm_fan_user_set(struct nvkm_therm *, int percent);
+
+int nvkm_therm_fan_sense(struct nvkm_therm *);
+
+int nvkm_therm_preinit(struct nvkm_therm *);
+
+int  nvkm_therm_sensor_init(struct nvkm_therm *);
+int  nvkm_therm_sensor_fini(struct nvkm_therm *, bool suspend);
+void nvkm_therm_sensor_preinit(struct nvkm_therm *);
+void nvkm_therm_sensor_set_threshold_state(struct nvkm_therm *,
+                                          enum nvkm_therm_thrs,
+                                          enum nvkm_therm_thrs_state);
+enum nvkm_therm_thrs_state
+nvkm_therm_sensor_get_threshold_state(struct nvkm_therm *,
+                                     enum nvkm_therm_thrs);
+void nvkm_therm_sensor_event(struct nvkm_therm *, enum nvkm_therm_thrs,
+                            enum nvkm_therm_thrs_direction);
+void nvkm_therm_program_alarms_polling(struct nvkm_therm *);
+
+void nv40_therm_intr(struct nvkm_subdev *);
+int  nv50_fan_pwm_ctrl(struct nvkm_therm *, int, bool);
+int  nv50_fan_pwm_get(struct nvkm_therm *, int, u32 *, u32 *);
+int  nv50_fan_pwm_set(struct nvkm_therm *, int, u32, u32);
+int  nv50_fan_pwm_clock(struct nvkm_therm *, int);
+int  g84_temp_get(struct nvkm_therm *);
+void g84_sensor_setup(struct nvkm_therm *);
+int  g84_therm_fini(struct nvkm_object *, bool suspend);
+
+int gt215_therm_fan_sense(struct nvkm_therm *);
+
+int gf110_therm_init(struct nvkm_object *);
+
+int nvkm_fanpwm_create(struct nvkm_therm *, struct dcb_gpio_func *);
+int nvkm_fantog_create(struct nvkm_therm *, struct dcb_gpio_func *);
+int nvkm_fannil_create(struct nvkm_therm *);
+#endif
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/therm/temp.c b/drivers/gpu/drm/nouveau/nvkm/subdev/therm/temp.c
new file mode 100644 (file)
index 0000000..aa13744
--- /dev/null
@@ -0,0 +1,259 @@
+/*
+ * Copyright 2012 The Nouveau community
+ *
+ * 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 "priv.h"
+
+static void
+nvkm_therm_temp_set_defaults(struct nvkm_therm *therm)
+{
+       struct nvkm_therm_priv *priv = (void *)therm;
+
+       priv->bios_sensor.offset_constant = 0;
+
+       priv->bios_sensor.thrs_fan_boost.temp = 90;
+       priv->bios_sensor.thrs_fan_boost.hysteresis = 3;
+
+       priv->bios_sensor.thrs_down_clock.temp = 95;
+       priv->bios_sensor.thrs_down_clock.hysteresis = 3;
+
+       priv->bios_sensor.thrs_critical.temp = 105;
+       priv->bios_sensor.thrs_critical.hysteresis = 5;
+
+       priv->bios_sensor.thrs_shutdown.temp = 135;
+       priv->bios_sensor.thrs_shutdown.hysteresis = 5; /*not that it matters */
+}
+
+
+static void
+nvkm_therm_temp_safety_checks(struct nvkm_therm *therm)
+{
+       struct nvkm_therm_priv *priv = (void *)therm;
+       struct nvbios_therm_sensor *s = &priv->bios_sensor;
+
+       /* enforce a minimum hysteresis on thresholds */
+       s->thrs_fan_boost.hysteresis = max_t(u8, s->thrs_fan_boost.hysteresis, 2);
+       s->thrs_down_clock.hysteresis = max_t(u8, s->thrs_down_clock.hysteresis, 2);
+       s->thrs_critical.hysteresis = max_t(u8, s->thrs_critical.hysteresis, 2);
+       s->thrs_shutdown.hysteresis = max_t(u8, s->thrs_shutdown.hysteresis, 2);
+}
+
+/* must be called with alarm_program_lock taken ! */
+void
+nvkm_therm_sensor_set_threshold_state(struct nvkm_therm *therm,
+                                     enum nvkm_therm_thrs thrs,
+                                     enum nvkm_therm_thrs_state st)
+{
+       struct nvkm_therm_priv *priv = (void *)therm;
+       priv->sensor.alarm_state[thrs] = st;
+}
+
+/* must be called with alarm_program_lock taken ! */
+enum nvkm_therm_thrs_state
+nvkm_therm_sensor_get_threshold_state(struct nvkm_therm *therm,
+                                     enum nvkm_therm_thrs thrs)
+{
+       struct nvkm_therm_priv *priv = (void *)therm;
+       return priv->sensor.alarm_state[thrs];
+}
+
+static void
+nv_poweroff_work(struct work_struct *work)
+{
+       orderly_poweroff(true);
+       kfree(work);
+}
+
+void
+nvkm_therm_sensor_event(struct nvkm_therm *therm, enum nvkm_therm_thrs thrs,
+                       enum nvkm_therm_thrs_direction dir)
+{
+       struct nvkm_therm_priv *priv = (void *)therm;
+       bool active;
+       const char *thresolds[] = {
+               "fanboost", "downclock", "critical", "shutdown"
+       };
+       int temperature = therm->temp_get(therm);
+
+       if (thrs < 0 || thrs > 3)
+               return;
+
+       if (dir == NVKM_THERM_THRS_FALLING)
+               nv_info(therm, "temperature (%i C) went below the '%s' threshold\n",
+                       temperature, thresolds[thrs]);
+       else
+               nv_info(therm, "temperature (%i C) hit the '%s' threshold\n",
+                       temperature, thresolds[thrs]);
+
+       active = (dir == NVKM_THERM_THRS_RISING);
+       switch (thrs) {
+       case NVKM_THERM_THRS_FANBOOST:
+               if (active) {
+                       nvkm_therm_fan_set(therm, true, 100);
+                       nvkm_therm_fan_mode(therm, NVKM_THERM_CTRL_AUTO);
+               }
+               break;
+       case NVKM_THERM_THRS_DOWNCLOCK:
+               if (priv->emergency.downclock)
+                       priv->emergency.downclock(therm, active);
+               break;
+       case NVKM_THERM_THRS_CRITICAL:
+               if (priv->emergency.pause)
+                       priv->emergency.pause(therm, active);
+               break;
+       case NVKM_THERM_THRS_SHUTDOWN:
+               if (active) {
+                       struct work_struct *work;
+
+                       work = kmalloc(sizeof(*work), GFP_ATOMIC);
+                       if (work) {
+                               INIT_WORK(work, nv_poweroff_work);
+                               schedule_work(work);
+                       }
+               }
+               break;
+       case NVKM_THERM_THRS_NR:
+               break;
+       }
+
+}
+
+/* must be called with alarm_program_lock taken ! */
+static void
+nvkm_therm_threshold_hyst_polling(struct nvkm_therm *therm,
+                                 const struct nvbios_therm_threshold *thrs,
+                                 enum nvkm_therm_thrs thrs_name)
+{
+       enum nvkm_therm_thrs_direction direction;
+       enum nvkm_therm_thrs_state prev_state, new_state;
+       int temp = therm->temp_get(therm);
+
+       prev_state = nvkm_therm_sensor_get_threshold_state(therm, thrs_name);
+
+       if (temp >= thrs->temp && prev_state == NVKM_THERM_THRS_LOWER) {
+               direction = NVKM_THERM_THRS_RISING;
+               new_state = NVKM_THERM_THRS_HIGHER;
+       } else if (temp <= thrs->temp - thrs->hysteresis &&
+                       prev_state == NVKM_THERM_THRS_HIGHER) {
+               direction = NVKM_THERM_THRS_FALLING;
+               new_state = NVKM_THERM_THRS_LOWER;
+       } else
+               return; /* nothing to do */
+
+       nvkm_therm_sensor_set_threshold_state(therm, thrs_name, new_state);
+       nvkm_therm_sensor_event(therm, thrs_name, direction);
+}
+
+static void
+alarm_timer_callback(struct nvkm_alarm *alarm)
+{
+       struct nvkm_therm_priv *priv =
+       container_of(alarm, struct nvkm_therm_priv, sensor.therm_poll_alarm);
+       struct nvbios_therm_sensor *sensor = &priv->bios_sensor;
+       struct nvkm_timer *ptimer = nvkm_timer(priv);
+       struct nvkm_therm *therm = &priv->base;
+       unsigned long flags;
+
+       spin_lock_irqsave(&priv->sensor.alarm_program_lock, flags);
+
+       nvkm_therm_threshold_hyst_polling(therm, &sensor->thrs_fan_boost,
+                                         NVKM_THERM_THRS_FANBOOST);
+
+       nvkm_therm_threshold_hyst_polling(therm, &sensor->thrs_down_clock,
+                                         NVKM_THERM_THRS_DOWNCLOCK);
+
+       nvkm_therm_threshold_hyst_polling(therm, &sensor->thrs_critical,
+                                         NVKM_THERM_THRS_CRITICAL);
+
+       nvkm_therm_threshold_hyst_polling(therm, &sensor->thrs_shutdown,
+                                         NVKM_THERM_THRS_SHUTDOWN);
+
+       spin_unlock_irqrestore(&priv->sensor.alarm_program_lock, flags);
+
+       /* schedule the next poll in one second */
+       if (therm->temp_get(therm) >= 0 && list_empty(&alarm->head))
+               ptimer->alarm(ptimer, 1000000000ULL, alarm);
+}
+
+void
+nvkm_therm_program_alarms_polling(struct nvkm_therm *therm)
+{
+       struct nvkm_therm_priv *priv = (void *)therm;
+       struct nvbios_therm_sensor *sensor = &priv->bios_sensor;
+
+       nv_debug(therm,
+                "programmed thresholds [ %d(%d), %d(%d), %d(%d), %d(%d) ]\n",
+                sensor->thrs_fan_boost.temp, sensor->thrs_fan_boost.hysteresis,
+                sensor->thrs_down_clock.temp,
+                sensor->thrs_down_clock.hysteresis,
+                sensor->thrs_critical.temp, sensor->thrs_critical.hysteresis,
+                sensor->thrs_shutdown.temp, sensor->thrs_shutdown.hysteresis);
+
+       alarm_timer_callback(&priv->sensor.therm_poll_alarm);
+}
+
+int
+nvkm_therm_sensor_init(struct nvkm_therm *therm)
+{
+       struct nvkm_therm_priv *priv = (void *)therm;
+       priv->sensor.program_alarms(therm);
+       return 0;
+}
+
+int
+nvkm_therm_sensor_fini(struct nvkm_therm *therm, bool suspend)
+{
+       struct nvkm_therm_priv *priv = (void *)therm;
+       struct nvkm_timer *ptimer = nvkm_timer(therm);
+
+       if (suspend)
+               ptimer->alarm_cancel(ptimer, &priv->sensor.therm_poll_alarm);
+       return 0;
+}
+
+void
+nvkm_therm_sensor_preinit(struct nvkm_therm *therm)
+{
+       const char *sensor_avail = "yes";
+
+       if (therm->temp_get(therm) < 0)
+               sensor_avail = "no";
+
+       nv_info(therm, "internal sensor: %s\n", sensor_avail);
+}
+
+int
+nvkm_therm_sensor_ctor(struct nvkm_therm *therm)
+{
+       struct nvkm_therm_priv *priv = (void *)therm;
+       struct nvkm_bios *bios = nvkm_bios(therm);
+
+       nvkm_alarm_init(&priv->sensor.therm_poll_alarm, alarm_timer_callback);
+
+       nvkm_therm_temp_set_defaults(therm);
+       if (nvbios_therm_sensor_parse(bios, NVBIOS_THERM_DOMAIN_CORE,
+                                     &priv->bios_sensor))
+               nv_error(therm, "nvbios_therm_sensor_parse failed\n");
+       nvkm_therm_temp_safety_checks(therm);
+
+       return 0;
+}
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/timer/Kbuild b/drivers/gpu/drm/nouveau/nvkm/subdev/timer/Kbuild
new file mode 100644 (file)
index 0000000..d1d38b4
--- /dev/null
@@ -0,0 +1,3 @@
+nvkm-y += nvkm/subdev/timer/base.o
+nvkm-y += nvkm/subdev/timer/nv04.o
+nvkm-y += nvkm/subdev/timer/gk20a.o
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/timer/base.c b/drivers/gpu/drm/nouveau/nvkm/subdev/timer/base.c
new file mode 100644 (file)
index 0000000..d894061
--- /dev/null
@@ -0,0 +1,93 @@
+/*
+ * Copyright 2012 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 <subdev/timer.h>
+
+bool
+nvkm_timer_wait_eq(void *obj, u64 nsec, u32 addr, u32 mask, u32 data)
+{
+       struct nvkm_timer *ptimer = nvkm_timer(obj);
+       u64 time0;
+
+       time0 = ptimer->read(ptimer);
+       do {
+               if (nv_iclass(obj, NV_SUBDEV_CLASS)) {
+                       if ((nv_rd32(obj, addr) & mask) == data)
+                               return true;
+               } else {
+                       if ((nv_ro32(obj, addr) & mask) == data)
+                               return true;
+               }
+       } while (ptimer->read(ptimer) - time0 < nsec);
+
+       return false;
+}
+
+bool
+nvkm_timer_wait_ne(void *obj, u64 nsec, u32 addr, u32 mask, u32 data)
+{
+       struct nvkm_timer *ptimer = nvkm_timer(obj);
+       u64 time0;
+
+       time0 = ptimer->read(ptimer);
+       do {
+               if (nv_iclass(obj, NV_SUBDEV_CLASS)) {
+                       if ((nv_rd32(obj, addr) & mask) != data)
+                               return true;
+               } else {
+                       if ((nv_ro32(obj, addr) & mask) != data)
+                               return true;
+               }
+       } while (ptimer->read(ptimer) - time0 < nsec);
+
+       return false;
+}
+
+bool
+nvkm_timer_wait_cb(void *obj, u64 nsec, bool (*func)(void *), void *data)
+{
+       struct nvkm_timer *ptimer = nvkm_timer(obj);
+       u64 time0;
+
+       time0 = ptimer->read(ptimer);
+       do {
+               if (func(data) == true)
+                       return true;
+       } while (ptimer->read(ptimer) - time0 < nsec);
+
+       return false;
+}
+
+void
+nvkm_timer_alarm(void *obj, u32 nsec, struct nvkm_alarm *alarm)
+{
+       struct nvkm_timer *ptimer = nvkm_timer(obj);
+       ptimer->alarm(ptimer, nsec, alarm);
+}
+
+void
+nvkm_timer_alarm_cancel(void *obj, struct nvkm_alarm *alarm)
+{
+       struct nvkm_timer *ptimer = nvkm_timer(obj);
+       ptimer->alarm_cancel(ptimer, alarm);
+}
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/timer/gk20a.c b/drivers/gpu/drm/nouveau/nvkm/subdev/timer/gk20a.c
new file mode 100644 (file)
index 0000000..80e3806
--- /dev/null
@@ -0,0 +1,56 @@
+/*
+ * Copyright 2012 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 "nv04.h"
+
+static int
+gk20a_timer_init(struct nvkm_object *object)
+{
+       struct nv04_timer_priv *priv = (void *)object;
+       u32 hi = upper_32_bits(priv->suspend_time);
+       u32 lo = lower_32_bits(priv->suspend_time);
+       int ret;
+
+       ret = nvkm_timer_init(&priv->base);
+       if (ret)
+               return ret;
+
+       nv_debug(priv, "time low        : 0x%08x\n", lo);
+       nv_debug(priv, "time high       : 0x%08x\n", hi);
+
+       /* restore the time before suspend */
+       nv_wr32(priv, NV04_PTIMER_TIME_1, hi);
+       nv_wr32(priv, NV04_PTIMER_TIME_0, lo);
+       return 0;
+}
+
+struct nvkm_oclass
+gk20a_timer_oclass = {
+       .handle = NV_SUBDEV(TIMER, 0xff),
+       .ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = nv04_timer_ctor,
+               .dtor = nv04_timer_dtor,
+               .init = gk20a_timer_init,
+               .fini = nv04_timer_fini,
+       }
+};
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/timer/nv04.c b/drivers/gpu/drm/nouveau/nvkm/subdev/timer/nv04.c
new file mode 100644 (file)
index 0000000..6b7facb
--- /dev/null
@@ -0,0 +1,262 @@
+/*
+ * Copyright 2012 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 "nv04.h"
+
+#include <core/device.h>
+
+static u64
+nv04_timer_read(struct nvkm_timer *ptimer)
+{
+       struct nv04_timer_priv *priv = (void *)ptimer;
+       u32 hi, lo;
+
+       do {
+               hi = nv_rd32(priv, NV04_PTIMER_TIME_1);
+               lo = nv_rd32(priv, NV04_PTIMER_TIME_0);
+       } while (hi != nv_rd32(priv, NV04_PTIMER_TIME_1));
+
+       return ((u64)hi << 32 | lo);
+}
+
+static void
+nv04_timer_alarm_trigger(struct nvkm_timer *ptimer)
+{
+       struct nv04_timer_priv *priv = (void *)ptimer;
+       struct nvkm_alarm *alarm, *atemp;
+       unsigned long flags;
+       LIST_HEAD(exec);
+
+       /* move any due alarms off the pending list */
+       spin_lock_irqsave(&priv->lock, flags);
+       list_for_each_entry_safe(alarm, atemp, &priv->alarms, head) {
+               if (alarm->timestamp <= ptimer->read(ptimer))
+                       list_move_tail(&alarm->head, &exec);
+       }
+
+       /* reschedule interrupt for next alarm time */
+       if (!list_empty(&priv->alarms)) {
+               alarm = list_first_entry(&priv->alarms, typeof(*alarm), head);
+               nv_wr32(priv, NV04_PTIMER_ALARM_0, alarm->timestamp);
+               nv_wr32(priv, NV04_PTIMER_INTR_EN_0, 0x00000001);
+       } else {
+               nv_wr32(priv, NV04_PTIMER_INTR_EN_0, 0x00000000);
+       }
+       spin_unlock_irqrestore(&priv->lock, flags);
+
+       /* execute any pending alarm handlers */
+       list_for_each_entry_safe(alarm, atemp, &exec, head) {
+               list_del_init(&alarm->head);
+               alarm->func(alarm);
+       }
+}
+
+static void
+nv04_timer_alarm(struct nvkm_timer *ptimer, u64 time, struct nvkm_alarm *alarm)
+{
+       struct nv04_timer_priv *priv = (void *)ptimer;
+       struct nvkm_alarm *list;
+       unsigned long flags;
+
+       alarm->timestamp = ptimer->read(ptimer) + time;
+
+       /* append new alarm to list, in soonest-alarm-first order */
+       spin_lock_irqsave(&priv->lock, flags);
+       if (!time) {
+               if (!list_empty(&alarm->head))
+                       list_del(&alarm->head);
+       } else {
+               list_for_each_entry(list, &priv->alarms, head) {
+                       if (list->timestamp > alarm->timestamp)
+                               break;
+               }
+               list_add_tail(&alarm->head, &list->head);
+       }
+       spin_unlock_irqrestore(&priv->lock, flags);
+
+       /* process pending alarms */
+       nv04_timer_alarm_trigger(ptimer);
+}
+
+static void
+nv04_timer_alarm_cancel(struct nvkm_timer *ptimer, struct nvkm_alarm *alarm)
+{
+       struct nv04_timer_priv *priv = (void *)ptimer;
+       unsigned long flags;
+       spin_lock_irqsave(&priv->lock, flags);
+       list_del_init(&alarm->head);
+       spin_unlock_irqrestore(&priv->lock, flags);
+}
+
+static void
+nv04_timer_intr(struct nvkm_subdev *subdev)
+{
+       struct nv04_timer_priv *priv = (void *)subdev;
+       u32 stat = nv_rd32(priv, NV04_PTIMER_INTR_0);
+
+       if (stat & 0x00000001) {
+               nv04_timer_alarm_trigger(&priv->base);
+               nv_wr32(priv, NV04_PTIMER_INTR_0, 0x00000001);
+               stat &= ~0x00000001;
+       }
+
+       if (stat) {
+               nv_error(priv, "unknown stat 0x%08x\n", stat);
+               nv_wr32(priv, NV04_PTIMER_INTR_0, stat);
+       }
+}
+
+int
+nv04_timer_fini(struct nvkm_object *object, bool suspend)
+{
+       struct nv04_timer_priv *priv = (void *)object;
+       if (suspend)
+               priv->suspend_time = nv04_timer_read(&priv->base);
+       nv_wr32(priv, NV04_PTIMER_INTR_EN_0, 0x00000000);
+       return nvkm_timer_fini(&priv->base, suspend);
+}
+
+static int
+nv04_timer_init(struct nvkm_object *object)
+{
+       struct nvkm_device *device = nv_device(object);
+       struct nv04_timer_priv *priv = (void *)object;
+       u32 m = 1, f, n, d, lo, hi;
+       int ret;
+
+       ret = nvkm_timer_init(&priv->base);
+       if (ret)
+               return ret;
+
+       /* aim for 31.25MHz, which gives us nanosecond timestamps */
+       d = 1000000 / 32;
+
+       /* determine base clock for timer source */
+#if 0 /*XXX*/
+       if (device->chipset < 0x40) {
+               n = nvkm_hw_get_clock(device, PLL_CORE);
+       } else
+#endif
+       if (device->chipset <= 0x40) {
+               /*XXX: figure this out */
+               f = -1;
+               n = 0;
+       } else {
+               f = device->crystal;
+               n = f;
+               while (n < (d * 2)) {
+                       n += (n / m);
+                       m++;
+               }
+
+               nv_wr32(priv, 0x009220, m - 1);
+       }
+
+       if (!n) {
+               nv_warn(priv, "unknown input clock freq\n");
+               if (!nv_rd32(priv, NV04_PTIMER_NUMERATOR) ||
+                   !nv_rd32(priv, NV04_PTIMER_DENOMINATOR)) {
+                       nv_wr32(priv, NV04_PTIMER_NUMERATOR, 1);
+                       nv_wr32(priv, NV04_PTIMER_DENOMINATOR, 1);
+               }
+               return 0;
+       }
+
+       /* reduce ratio to acceptable values */
+       while (((n % 5) == 0) && ((d % 5) == 0)) {
+               n /= 5;
+               d /= 5;
+       }
+
+       while (((n % 2) == 0) && ((d % 2) == 0)) {
+               n /= 2;
+               d /= 2;
+       }
+
+       while (n > 0xffff || d > 0xffff) {
+               n >>= 1;
+               d >>= 1;
+       }
+
+       /* restore the time before suspend */
+       lo = priv->suspend_time;
+       hi = (priv->suspend_time >> 32);
+
+       nv_debug(priv, "input frequency : %dHz\n", f);
+       nv_debug(priv, "input multiplier: %d\n", m);
+       nv_debug(priv, "numerator       : 0x%08x\n", n);
+       nv_debug(priv, "denominator     : 0x%08x\n", d);
+       nv_debug(priv, "timer frequency : %dHz\n", (f * m) * d / n);
+       nv_debug(priv, "time low        : 0x%08x\n", lo);
+       nv_debug(priv, "time high       : 0x%08x\n", hi);
+
+       nv_wr32(priv, NV04_PTIMER_NUMERATOR, n);
+       nv_wr32(priv, NV04_PTIMER_DENOMINATOR, d);
+       nv_wr32(priv, NV04_PTIMER_INTR_0, 0xffffffff);
+       nv_wr32(priv, NV04_PTIMER_INTR_EN_0, 0x00000000);
+       nv_wr32(priv, NV04_PTIMER_TIME_1, hi);
+       nv_wr32(priv, NV04_PTIMER_TIME_0, lo);
+       return 0;
+}
+
+void
+nv04_timer_dtor(struct nvkm_object *object)
+{
+       struct nv04_timer_priv *priv = (void *)object;
+       return nvkm_timer_destroy(&priv->base);
+}
+
+int
+nv04_timer_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+               struct nvkm_oclass *oclass, void *data, u32 size,
+               struct nvkm_object **pobject)
+{
+       struct nv04_timer_priv *priv;
+       int ret;
+
+       ret = nvkm_timer_create(parent, engine, oclass, &priv);
+       *pobject = nv_object(priv);
+       if (ret)
+               return ret;
+
+       priv->base.base.intr = nv04_timer_intr;
+       priv->base.read = nv04_timer_read;
+       priv->base.alarm = nv04_timer_alarm;
+       priv->base.alarm_cancel = nv04_timer_alarm_cancel;
+       priv->suspend_time = 0;
+
+       INIT_LIST_HEAD(&priv->alarms);
+       spin_lock_init(&priv->lock);
+       return 0;
+}
+
+struct nvkm_oclass
+nv04_timer_oclass = {
+       .handle = NV_SUBDEV(TIMER, 0x04),
+       .ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = nv04_timer_ctor,
+               .dtor = nv04_timer_dtor,
+               .init = nv04_timer_init,
+               .fini = nv04_timer_fini,
+       }
+};
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/timer/nv04.h b/drivers/gpu/drm/nouveau/nvkm/subdev/timer/nv04.h
new file mode 100644 (file)
index 0000000..89996a9
--- /dev/null
@@ -0,0 +1,25 @@
+#ifndef __NVKM_TIMER_NV04_H__
+#define __NVKM_TIMER_NV04_H__
+#include "priv.h"
+
+#define NV04_PTIMER_INTR_0      0x009100
+#define NV04_PTIMER_INTR_EN_0   0x009140
+#define NV04_PTIMER_NUMERATOR   0x009200
+#define NV04_PTIMER_DENOMINATOR 0x009210
+#define NV04_PTIMER_TIME_0      0x009400
+#define NV04_PTIMER_TIME_1      0x009410
+#define NV04_PTIMER_ALARM_0     0x009420
+
+struct nv04_timer_priv {
+       struct nvkm_timer base;
+       struct list_head alarms;
+       spinlock_t lock;
+       u64 suspend_time;
+};
+
+int  nv04_timer_ctor(struct nvkm_object *, struct nvkm_object *,
+                    struct nvkm_oclass *, void *, u32,
+                    struct nvkm_object **);
+void nv04_timer_dtor(struct nvkm_object *);
+int  nv04_timer_fini(struct nvkm_object *, bool);
+#endif
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/timer/priv.h b/drivers/gpu/drm/nouveau/nvkm/subdev/timer/priv.h
new file mode 100644 (file)
index 0000000..08e29a3
--- /dev/null
@@ -0,0 +1,4 @@
+#ifndef __NVKM_TIMER_PRIV_H__
+#define __NVKM_TIMER_PRIV_H__
+#include <subdev/timer.h>
+#endif
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/volt/Kbuild b/drivers/gpu/drm/nouveau/nvkm/subdev/volt/Kbuild
new file mode 100644 (file)
index 0000000..6b46ff4
--- /dev/null
@@ -0,0 +1,4 @@
+nvkm-y += nvkm/subdev/volt/base.o
+nvkm-y += nvkm/subdev/volt/gpio.o
+nvkm-y += nvkm/subdev/volt/nv40.o
+nvkm-y += nvkm/subdev/volt/gk20a.o
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/volt/base.c b/drivers/gpu/drm/nouveau/nvkm/subdev/volt/base.c
new file mode 100644 (file)
index 0000000..39f1580
--- /dev/null
@@ -0,0 +1,204 @@
+/*
+ * Copyright 2013 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 <subdev/volt.h>
+#include <subdev/bios.h>
+#include <subdev/bios/vmap.h>
+#include <subdev/bios/volt.h>
+
+static int
+nvkm_volt_get(struct nvkm_volt *volt)
+{
+       if (volt->vid_get) {
+               int ret = volt->vid_get(volt), i;
+               if (ret >= 0) {
+                       for (i = 0; i < volt->vid_nr; i++) {
+                               if (volt->vid[i].vid == ret)
+                                       return volt->vid[i].uv;
+                       }
+                       ret = -EINVAL;
+               }
+               return ret;
+       }
+       return -ENODEV;
+}
+
+static int
+nvkm_volt_set(struct nvkm_volt *volt, u32 uv)
+{
+       if (volt->vid_set) {
+               int i, ret = -EINVAL;
+               for (i = 0; i < volt->vid_nr; i++) {
+                       if (volt->vid[i].uv == uv) {
+                               ret = volt->vid_set(volt, volt->vid[i].vid);
+                               nv_debug(volt, "set %duv: %d\n", uv, ret);
+                               break;
+                       }
+               }
+               return ret;
+       }
+       return -ENODEV;
+}
+
+static int
+nvkm_volt_map(struct nvkm_volt *volt, u8 id)
+{
+       struct nvkm_bios *bios = nvkm_bios(volt);
+       struct nvbios_vmap_entry info;
+       u8  ver, len;
+       u16 vmap;
+
+       vmap = nvbios_vmap_entry_parse(bios, id, &ver, &len, &info);
+       if (vmap) {
+               if (info.link != 0xff) {
+                       int ret = nvkm_volt_map(volt, info.link);
+                       if (ret < 0)
+                               return ret;
+                       info.min += ret;
+               }
+               return info.min;
+       }
+
+       return id ? id * 10000 : -ENODEV;
+}
+
+static int
+nvkm_volt_set_id(struct nvkm_volt *volt, u8 id, int condition)
+{
+       int ret = nvkm_volt_map(volt, id);
+       if (ret >= 0) {
+               int prev = nvkm_volt_get(volt);
+               if (!condition || prev < 0 ||
+                   (condition < 0 && ret < prev) ||
+                   (condition > 0 && ret > prev)) {
+                       ret = nvkm_volt_set(volt, ret);
+               } else {
+                       ret = 0;
+               }
+       }
+       return ret;
+}
+
+static void
+nvkm_volt_parse_bios(struct nvkm_bios *bios, struct nvkm_volt *volt)
+{
+       struct nvbios_volt_entry ivid;
+       struct nvbios_volt info;
+       u8  ver, hdr, cnt, len;
+       u16 data;
+       int i;
+
+       data = nvbios_volt_parse(bios, &ver, &hdr, &cnt, &len, &info);
+       if (data && info.vidmask && info.base && info.step) {
+               for (i = 0; i < info.vidmask + 1; i++) {
+                       if (info.base >= info.min &&
+                               info.base <= info.max) {
+                               volt->vid[volt->vid_nr].uv = info.base;
+                               volt->vid[volt->vid_nr].vid = i;
+                               volt->vid_nr++;
+                       }
+                       info.base += info.step;
+               }
+               volt->vid_mask = info.vidmask;
+       } else if (data && info.vidmask) {
+               for (i = 0; i < cnt; i++) {
+                       data = nvbios_volt_entry_parse(bios, i, &ver, &hdr,
+                                                      &ivid);
+                       if (data) {
+                               volt->vid[volt->vid_nr].uv = ivid.voltage;
+                               volt->vid[volt->vid_nr].vid = ivid.vid;
+                               volt->vid_nr++;
+                       }
+               }
+               volt->vid_mask = info.vidmask;
+       }
+}
+
+int
+_nvkm_volt_init(struct nvkm_object *object)
+{
+       struct nvkm_volt *volt = (void *)object;
+       int ret;
+
+       ret = nvkm_subdev_init(&volt->base);
+       if (ret)
+               return ret;
+
+       ret = volt->get(volt);
+       if (ret < 0) {
+               if (ret != -ENODEV)
+                       nv_debug(volt, "current voltage unknown\n");
+               return 0;
+       }
+
+       nv_info(volt, "GPU voltage: %duv\n", ret);
+       return 0;
+}
+
+void
+_nvkm_volt_dtor(struct nvkm_object *object)
+{
+       struct nvkm_volt *volt = (void *)object;
+       nvkm_subdev_destroy(&volt->base);
+}
+
+int
+nvkm_volt_create_(struct nvkm_object *parent, struct nvkm_object *engine,
+                 struct nvkm_oclass *oclass, int length, void **pobject)
+{
+       struct nvkm_bios *bios = nvkm_bios(parent);
+       struct nvkm_volt *volt;
+       int ret, i;
+
+       ret = nvkm_subdev_create_(parent, engine, oclass, 0, "VOLT",
+                                 "voltage", length, pobject);
+       volt = *pobject;
+       if (ret)
+               return ret;
+
+       volt->get = nvkm_volt_get;
+       volt->set = nvkm_volt_set;
+       volt->set_id = nvkm_volt_set_id;
+
+       /* Assuming the non-bios device should build the voltage table later */
+       if (bios)
+               nvkm_volt_parse_bios(bios, volt);
+
+       if (volt->vid_nr) {
+               for (i = 0; i < volt->vid_nr; i++) {
+                       nv_debug(volt, "VID %02x: %duv\n",
+                                volt->vid[i].vid, volt->vid[i].uv);
+               }
+
+               /*XXX: this is an assumption.. there probably exists boards
+                * out there with i2c-connected voltage controllers too..
+                */
+               ret = nvkm_voltgpio_init(volt);
+               if (ret == 0) {
+                       volt->vid_get = nvkm_voltgpio_get;
+                       volt->vid_set = nvkm_voltgpio_set;
+               }
+       }
+
+       return ret;
+}
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/volt/gk20a.c b/drivers/gpu/drm/nouveau/nvkm/subdev/volt/gk20a.c
new file mode 100644 (file)
index 0000000..871fd51
--- /dev/null
@@ -0,0 +1,197 @@
+/*
+ * Copyright (c) 2014, NVIDIA CORPORATION. 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 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 <subdev/volt.h>
+#ifdef __KERNEL__
+#include <nouveau_platform.h>
+#endif
+
+struct cvb_coef {
+       int c0;
+       int c1;
+       int c2;
+       int c3;
+       int c4;
+       int c5;
+};
+
+struct gk20a_volt_priv {
+       struct nvkm_volt base;
+       struct regulator *vdd;
+};
+
+const struct cvb_coef gk20a_cvb_coef[] = {
+       /* MHz,        c0,     c1,   c2,    c3,     c4,   c5 */
+       /*  72 */ { 1209886, -36468,  515,   417, -13123,  203},
+       /* 108 */ { 1130804, -27659,  296,   298, -10834,  221},
+       /* 180 */ { 1162871, -27110,  247,   238, -10681,  268},
+       /* 252 */ { 1220458, -28654,  247,   179, -10376,  298},
+       /* 324 */ { 1280953, -30204,  247,   119,  -9766,  304},
+       /* 396 */ { 1344547, -31777,  247,   119,  -8545,  292},
+       /* 468 */ { 1420168, -34227,  269,    60,  -7172,  256},
+       /* 540 */ { 1490757, -35955,  274,    60,  -5188,  197},
+       /* 612 */ { 1599112, -42583,  398,     0,  -1831,  119},
+       /* 648 */ { 1366986, -16459, -274,     0,  -3204,   72},
+       /* 684 */ { 1391884, -17078, -274,   -60,  -1526,   30},
+       /* 708 */ { 1415522, -17497, -274,   -60,   -458,    0},
+       /* 756 */ { 1464061, -18331, -274,  -119,   1831,  -72},
+       /* 804 */ { 1524225, -20064, -254,  -119,   4272, -155},
+       /* 852 */ { 1608418, -21643, -269,     0,    763,  -48},
+};
+
+/**
+ * cvb_mv = ((c2 * speedo / s_scale + c1) * speedo / s_scale + c0)
+ */
+static inline int
+gk20a_volt_get_cvb_voltage(int speedo, int s_scale, const struct cvb_coef *coef)
+{
+       int mv;
+
+       mv = DIV_ROUND_CLOSEST(coef->c2 * speedo, s_scale);
+       mv = DIV_ROUND_CLOSEST((mv + coef->c1) * speedo, s_scale) + coef->c0;
+       return mv;
+}
+
+/**
+ * cvb_t_mv =
+ * ((c2 * speedo / s_scale + c1) * speedo / s_scale + c0) +
+ * ((c3 * speedo / s_scale + c4 + c5 * T / t_scale) * T / t_scale)
+ */
+static inline int
+gk20a_volt_get_cvb_t_voltage(int speedo, int temp, int s_scale, int t_scale,
+                            const struct cvb_coef *coef)
+{
+       int cvb_mv, mv;
+
+       cvb_mv = gk20a_volt_get_cvb_voltage(speedo, s_scale, coef);
+
+       mv = DIV_ROUND_CLOSEST(coef->c3 * speedo, s_scale) + coef->c4 +
+               DIV_ROUND_CLOSEST(coef->c5 * temp, t_scale);
+       mv = DIV_ROUND_CLOSEST(mv * temp, t_scale) + cvb_mv;
+       return mv;
+}
+
+static int
+gk20a_volt_calc_voltage(const struct cvb_coef *coef, int speedo)
+{
+       int mv;
+
+       mv = gk20a_volt_get_cvb_t_voltage(speedo, -10, 100, 10, coef);
+       mv = DIV_ROUND_UP(mv, 1000);
+
+       return mv * 1000;
+}
+
+static int
+gk20a_volt_vid_get(struct nvkm_volt *volt)
+{
+       struct gk20a_volt_priv *priv = (void *)volt;
+       int i, uv;
+
+       uv = regulator_get_voltage(priv->vdd);
+
+       for (i = 0; i < volt->vid_nr; i++)
+               if (volt->vid[i].uv >= uv)
+                       return i;
+
+       return -EINVAL;
+}
+
+static int
+gk20a_volt_vid_set(struct nvkm_volt *volt, u8 vid)
+{
+       struct gk20a_volt_priv *priv = (void *)volt;
+
+       nv_debug(volt, "set voltage as %duv\n", volt->vid[vid].uv);
+       return regulator_set_voltage(priv->vdd, volt->vid[vid].uv, 1200000);
+}
+
+static int
+gk20a_volt_set_id(struct nvkm_volt *volt, u8 id, int condition)
+{
+       struct gk20a_volt_priv *priv = (void *)volt;
+       int prev_uv = regulator_get_voltage(priv->vdd);
+       int target_uv = volt->vid[id].uv;
+       int ret;
+
+       nv_debug(volt, "prev=%d, target=%d, condition=%d\n",
+                       prev_uv, target_uv, condition);
+       if (!condition ||
+               (condition < 0 && target_uv < prev_uv) ||
+               (condition > 0 && target_uv > prev_uv)) {
+               ret = gk20a_volt_vid_set(volt, volt->vid[id].vid);
+       } else {
+               ret = 0;
+       }
+
+       return ret;
+}
+
+static int
+gk20a_volt_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+               struct nvkm_oclass *oclass, void *data, u32 size,
+               struct nvkm_object **pobject)
+{
+       struct gk20a_volt_priv *priv;
+       struct nvkm_volt *volt;
+       struct nouveau_platform_device *plat;
+       int i, ret, uv;
+
+       ret = nvkm_volt_create(parent, engine, oclass, &priv);
+       *pobject = nv_object(priv);
+       if (ret)
+               return ret;
+
+       volt = &priv->base;
+
+       plat = nv_device_to_platform(nv_device(parent));
+
+       uv = regulator_get_voltage(plat->gpu->vdd);
+       nv_info(priv, "The default voltage is %duV\n", uv);
+
+       priv->vdd = plat->gpu->vdd;
+       priv->base.vid_get = gk20a_volt_vid_get;
+       priv->base.vid_set = gk20a_volt_vid_set;
+       priv->base.set_id = gk20a_volt_set_id;
+
+       volt->vid_nr = ARRAY_SIZE(gk20a_cvb_coef);
+       nv_debug(priv, "%s - vid_nr = %d\n", __func__, volt->vid_nr);
+       for (i = 0; i < volt->vid_nr; i++) {
+               volt->vid[i].vid = i;
+               volt->vid[i].uv = gk20a_volt_calc_voltage(&gk20a_cvb_coef[i],
+                                       plat->gpu_speedo);
+               nv_debug(priv, "%2d: vid=%d, uv=%d\n", i, volt->vid[i].vid,
+                                       volt->vid[i].uv);
+       }
+
+       return 0;
+}
+
+struct nvkm_oclass
+gk20a_volt_oclass = {
+       .handle = NV_SUBDEV(VOLT, 0xea),
+       .ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = gk20a_volt_ctor,
+               .dtor = _nvkm_volt_dtor,
+               .init = _nvkm_volt_init,
+               .fini = _nvkm_volt_fini,
+       },
+};
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/volt/gpio.c b/drivers/gpu/drm/nouveau/nvkm/subdev/volt/gpio.c
new file mode 100644 (file)
index 0000000..b778deb
--- /dev/null
@@ -0,0 +1,96 @@
+/*
+ * Copyright 2013 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 <subdev/volt.h>
+#include <subdev/bios.h>
+#include <subdev/bios/gpio.h>
+#include <subdev/gpio.h>
+
+static const u8 tags[] = {
+       DCB_GPIO_VID0, DCB_GPIO_VID1, DCB_GPIO_VID2, DCB_GPIO_VID3,
+       DCB_GPIO_VID4, DCB_GPIO_VID5, DCB_GPIO_VID6, DCB_GPIO_VID7,
+};
+
+int
+nvkm_voltgpio_get(struct nvkm_volt *volt)
+{
+       struct nvkm_gpio *gpio = nvkm_gpio(volt);
+       u8 vid = 0;
+       int i;
+
+       for (i = 0; i < ARRAY_SIZE(tags); i++) {
+               if (volt->vid_mask & (1 << i)) {
+                       int ret = gpio->get(gpio, 0, tags[i], 0xff);
+                       if (ret < 0)
+                               return ret;
+                       vid |= ret << i;
+               }
+       }
+
+       return vid;
+}
+
+int
+nvkm_voltgpio_set(struct nvkm_volt *volt, u8 vid)
+{
+       struct nvkm_gpio *gpio = nvkm_gpio(volt);
+       int i;
+
+       for (i = 0; i < ARRAY_SIZE(tags); i++, vid >>= 1) {
+               if (volt->vid_mask & (1 << i)) {
+                       int ret = gpio->set(gpio, 0, tags[i], 0xff, vid & 1);
+                       if (ret < 0)
+                               return ret;
+               }
+       }
+
+       return 0;
+}
+
+int
+nvkm_voltgpio_init(struct nvkm_volt *volt)
+{
+       struct nvkm_gpio *gpio = nvkm_gpio(volt);
+       struct dcb_gpio_func func;
+       int i;
+
+       /* check we have gpio function info for each vid bit.  on some
+        * boards (ie. nvs295) the vid mask has more bits than there
+        * are valid gpio functions... from traces, nvidia appear to
+        * just touch the existing ones, so let's mask off the invalid
+        * bits and continue with life
+        */
+       for (i = 0; i < ARRAY_SIZE(tags); i++) {
+               if (volt->vid_mask & (1 << i)) {
+                       int ret = gpio->find(gpio, 0, tags[i], 0xff, &func);
+                       if (ret) {
+                               if (ret != -ENOENT)
+                                       return ret;
+                               nv_debug(volt, "VID bit %d has no GPIO\n", i);
+                               volt->vid_mask &= ~(1 << i);
+                       }
+               }
+       }
+
+       return 0;
+}
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/volt/nv40.c b/drivers/gpu/drm/nouveau/nvkm/subdev/volt/nv40.c
new file mode 100644 (file)
index 0000000..0ac5a3f
--- /dev/null
@@ -0,0 +1,55 @@
+/*
+ * Copyright 2013 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 <subdev/volt.h>
+
+struct nv40_volt_priv {
+       struct nvkm_volt base;
+};
+
+static int
+nv40_volt_ctor(struct nvkm_object *parent, struct nvkm_object *engine,
+              struct nvkm_oclass *oclass, void *data, u32 size,
+              struct nvkm_object **pobject)
+{
+       struct nv40_volt_priv *priv;
+       int ret;
+
+       ret = nvkm_volt_create(parent, engine, oclass, &priv);
+       *pobject = nv_object(priv);
+       if (ret)
+               return ret;
+
+       return 0;
+}
+
+struct nvkm_oclass
+nv40_volt_oclass = {
+       .handle = NV_SUBDEV(VOLT, 0x40),
+       .ofuncs = &(struct nvkm_ofuncs) {
+               .ctor = nv40_volt_ctor,
+               .dtor = _nvkm_volt_dtor,
+               .init = _nvkm_volt_init,
+               .fini = _nvkm_volt_fini,
+       },
+};
index 8436c6857cda76f2311af5d612f50315a58438ce..d292d24b3a6e673977b9c5f5ebc353bc6c5c18b7 100644 (file)
@@ -334,17 +334,23 @@ struct drm_fb_helper *omap_fbdev_init(struct drm_device *dev)
                goto fail;
        }
 
-       drm_fb_helper_single_add_all_connectors(helper);
+       ret = drm_fb_helper_single_add_all_connectors(helper);
+       if (ret)
+               goto fini;
 
        /* disable all the possible outputs/crtcs before entering KMS mode */
        drm_helper_disable_unused_functions(dev);
 
-       drm_fb_helper_initial_config(helper, 32);
+       ret = drm_fb_helper_initial_config(helper, 32);
+       if (ret)
+               goto fini;
 
        priv->fbdev = helper;
 
        return helper;
 
+fini:
+       drm_fb_helper_fini(helper);
 fail:
        kfree(fbdev);
        return NULL;
index e95385bf835634e163cced6947920c688f7cc9a7..6049d245c20edde75ac65f85d465adf7c0aa720f 100644 (file)
@@ -61,6 +61,8 @@ struct panel_desc {
                unsigned int disable;
                unsigned int unprepare;
        } delay;
+
+       u32 bus_format;
 };
 
 struct panel_simple {
@@ -111,6 +113,9 @@ static int panel_simple_get_fixed_modes(struct panel_simple *panel)
        connector->display_info.bpc = panel->desc->bpc;
        connector->display_info.width_mm = panel->desc->size.width;
        connector->display_info.height_mm = panel->desc->size.height;
+       if (panel->desc->bus_format)
+               drm_display_info_set_bus_formats(&connector->display_info,
+                                                &panel->desc->bus_format, 1);
 
        return num;
 }
@@ -558,6 +563,7 @@ static const struct panel_desc foxlink_fl500wvr00_a0t = {
                .width = 108,
                .height = 65,
        },
+       .bus_format = MEDIA_BUS_FMT_RGB888_1X24,
 };
 
 static const struct drm_display_mode hannstar_hsd070pww1_mode = {
index 3d7c1d00a424cfbdbdf53881421f2f4e193f247e..f778c0e8ae3cabc4738165998e37e6b49d0df7b6 100644 (file)
@@ -686,14 +686,24 @@ int qxl_fbdev_init(struct qxl_device *qdev)
        ret = drm_fb_helper_init(qdev->ddev, &qfbdev->helper,
                                 qxl_num_crtc /* num_crtc - QXL supports just 1 */,
                                 QXLFB_CONN_LIMIT);
-       if (ret) {
-               kfree(qfbdev);
-               return ret;
-       }
+       if (ret)
+               goto free;
+
+       ret = drm_fb_helper_single_add_all_connectors(&qfbdev->helper);
+       if (ret)
+               goto fini;
+
+       ret = drm_fb_helper_initial_config(&qfbdev->helper, bpp_sel);
+       if (ret)
+               goto fini;
 
-       drm_fb_helper_single_add_all_connectors(&qfbdev->helper);
-       drm_fb_helper_initial_config(&qfbdev->helper, bpp_sel);
        return 0;
+
+fini:
+       drm_fb_helper_fini(&qfbdev->helper);
+free:
+       kfree(qfbdev);
+       return ret;
 }
 
 void qxl_fbdev_fini(struct qxl_device *qdev)
index 12bc21219a0ea13f305133139ba9a4afe9dcf618..c58cfd3c3917845c137651c03b8ed41da672b11d 100644 (file)
@@ -2,7 +2,7 @@
 # Makefile for the drm device driver.  This driver provides support for the
 # Direct Rendering Infrastructure (DRI) in XFree86 4.1.0 and higher.
 
-ccflags-y := -Iinclude/drm
+ccflags-y := -Iinclude/drm -Idrivers/gpu/drm/amd/include
 
 hostprogs-y := mkregtable
 clean-files := rn50_reg_safe.h r100_reg_safe.h r200_reg_safe.h rv515_reg_safe.h r300_reg_safe.h r420_reg_safe.h rs600_reg_safe.h r600_reg_safe.h evergreen_reg_safe.h cayman_reg_safe.h
index 6dcde3798b45a026f0be30f8e7bffb8b254ace81..ed336fbfab7c50f6f7ddea35115e6ac224157faf 100644 (file)
@@ -5707,6 +5707,28 @@ void cik_pcie_gart_tlb_flush(struct radeon_device *rdev)
        WREG32(VM_INVALIDATE_REQUEST, 0x1);
 }
 
+static void cik_pcie_init_compute_vmid(struct radeon_device *rdev)
+{
+       int i;
+       uint32_t sh_mem_bases, sh_mem_config;
+
+       sh_mem_bases = 0x6000 | 0x6000 << 16;
+       sh_mem_config = ALIGNMENT_MODE(SH_MEM_ALIGNMENT_MODE_UNALIGNED);
+       sh_mem_config |= DEFAULT_MTYPE(MTYPE_NONCACHED);
+
+       mutex_lock(&rdev->srbm_mutex);
+       for (i = 8; i < 16; i++) {
+               cik_srbm_select(rdev, 0, 0, 0, i);
+               /* CP and shaders */
+               WREG32(SH_MEM_CONFIG, sh_mem_config);
+               WREG32(SH_MEM_APE1_BASE, 1);
+               WREG32(SH_MEM_APE1_LIMIT, 0);
+               WREG32(SH_MEM_BASES, sh_mem_bases);
+       }
+       cik_srbm_select(rdev, 0, 0, 0, 0);
+       mutex_unlock(&rdev->srbm_mutex);
+}
+
 /**
  * cik_pcie_gart_enable - gart enable
  *
@@ -5820,6 +5842,8 @@ static int cik_pcie_gart_enable(struct radeon_device *rdev)
        cik_srbm_select(rdev, 0, 0, 0, 0);
        mutex_unlock(&rdev->srbm_mutex);
 
+       cik_pcie_init_compute_vmid(rdev);
+
        cik_pcie_gart_tlb_flush(rdev);
        DRM_INFO("PCIE GART of %uM enabled (table at 0x%016llX).\n",
                 (unsigned)(rdev->mc.gtt_size >> 20),
@@ -6033,6 +6057,17 @@ void cik_vm_flush(struct radeon_device *rdev, struct radeon_ring *ring,
        radeon_ring_write(ring, 0);
        radeon_ring_write(ring, 1 << vm_id);
 
+       /* wait for the invalidate to complete */
+       radeon_ring_write(ring, PACKET3(PACKET3_WAIT_REG_MEM, 5));
+       radeon_ring_write(ring, (WAIT_REG_MEM_OPERATION(0) | /* wait */
+                                WAIT_REG_MEM_FUNCTION(0) |  /* always */
+                                WAIT_REG_MEM_ENGINE(0))); /* me */
+       radeon_ring_write(ring, VM_INVALIDATE_REQUEST >> 2);
+       radeon_ring_write(ring, 0);
+       radeon_ring_write(ring, 0); /* ref */
+       radeon_ring_write(ring, 0); /* mask */
+       radeon_ring_write(ring, 0x20); /* poll interval */
+
        /* compute doesn't have PFP */
        if (usepfp) {
                /* sync PFP to ME, otherwise we might get invalid PFP reads */
index 79c45e8a536b03405d061dec6e41eb0f3eea6ca7..f667347d8157ce81374ca7b91ec20b72be675028 100644 (file)
 
 #define CIK_LB_DESKTOP_HEIGHT                     0x6b0c
 
+#define KFD_CIK_SDMA_QUEUE_OFFSET              0x200
+
 #define CP_HQD_IQ_RPTR                                 0xC970u
 #define AQL_ENABLE                                     (1U << 0)
-
-#define IDLE                                   (1 << 2)
-
-struct cik_mqd {
-       uint32_t header;
-       uint32_t compute_dispatch_initiator;
-       uint32_t compute_dim_x;
-       uint32_t compute_dim_y;
-       uint32_t compute_dim_z;
-       uint32_t compute_start_x;
-       uint32_t compute_start_y;
-       uint32_t compute_start_z;
-       uint32_t compute_num_thread_x;
-       uint32_t compute_num_thread_y;
-       uint32_t compute_num_thread_z;
-       uint32_t compute_pipelinestat_enable;
-       uint32_t compute_perfcount_enable;
-       uint32_t compute_pgm_lo;
-       uint32_t compute_pgm_hi;
-       uint32_t compute_tba_lo;
-       uint32_t compute_tba_hi;
-       uint32_t compute_tma_lo;
-       uint32_t compute_tma_hi;
-       uint32_t compute_pgm_rsrc1;
-       uint32_t compute_pgm_rsrc2;
-       uint32_t compute_vmid;
-       uint32_t compute_resource_limits;
-       uint32_t compute_static_thread_mgmt_se0;
-       uint32_t compute_static_thread_mgmt_se1;
-       uint32_t compute_tmpring_size;
-       uint32_t compute_static_thread_mgmt_se2;
-       uint32_t compute_static_thread_mgmt_se3;
-       uint32_t compute_restart_x;
-       uint32_t compute_restart_y;
-       uint32_t compute_restart_z;
-       uint32_t compute_thread_trace_enable;
-       uint32_t compute_misc_reserved;
-       uint32_t compute_user_data_0;
-       uint32_t compute_user_data_1;
-       uint32_t compute_user_data_2;
-       uint32_t compute_user_data_3;
-       uint32_t compute_user_data_4;
-       uint32_t compute_user_data_5;
-       uint32_t compute_user_data_6;
-       uint32_t compute_user_data_7;
-       uint32_t compute_user_data_8;
-       uint32_t compute_user_data_9;
-       uint32_t compute_user_data_10;
-       uint32_t compute_user_data_11;
-       uint32_t compute_user_data_12;
-       uint32_t compute_user_data_13;
-       uint32_t compute_user_data_14;
-       uint32_t compute_user_data_15;
-       uint32_t cp_compute_csinvoc_count_lo;
-       uint32_t cp_compute_csinvoc_count_hi;
-       uint32_t cp_mqd_base_addr_lo;
-       uint32_t cp_mqd_base_addr_hi;
-       uint32_t cp_hqd_active;
-       uint32_t cp_hqd_vmid;
-       uint32_t cp_hqd_persistent_state;
-       uint32_t cp_hqd_pipe_priority;
-       uint32_t cp_hqd_queue_priority;
-       uint32_t cp_hqd_quantum;
-       uint32_t cp_hqd_pq_base_lo;
-       uint32_t cp_hqd_pq_base_hi;
-       uint32_t cp_hqd_pq_rptr;
-       uint32_t cp_hqd_pq_rptr_report_addr_lo;
-       uint32_t cp_hqd_pq_rptr_report_addr_hi;
-       uint32_t cp_hqd_pq_wptr_poll_addr_lo;
-       uint32_t cp_hqd_pq_wptr_poll_addr_hi;
-       uint32_t cp_hqd_pq_doorbell_control;
-       uint32_t cp_hqd_pq_wptr;
-       uint32_t cp_hqd_pq_control;
-       uint32_t cp_hqd_ib_base_addr_lo;
-       uint32_t cp_hqd_ib_base_addr_hi;
-       uint32_t cp_hqd_ib_rptr;
-       uint32_t cp_hqd_ib_control;
-       uint32_t cp_hqd_iq_timer;
-       uint32_t cp_hqd_iq_rptr;
-       uint32_t cp_hqd_dequeue_request;
-       uint32_t cp_hqd_dma_offload;
-       uint32_t cp_hqd_sema_cmd;
-       uint32_t cp_hqd_msg_type;
-       uint32_t cp_hqd_atomic0_preop_lo;
-       uint32_t cp_hqd_atomic0_preop_hi;
-       uint32_t cp_hqd_atomic1_preop_lo;
-       uint32_t cp_hqd_atomic1_preop_hi;
-       uint32_t cp_hqd_hq_status0;
-       uint32_t cp_hqd_hq_control0;
-       uint32_t cp_mqd_control;
-       uint32_t cp_mqd_query_time_lo;
-       uint32_t cp_mqd_query_time_hi;
-       uint32_t cp_mqd_connect_start_time_lo;
-       uint32_t cp_mqd_connect_start_time_hi;
-       uint32_t cp_mqd_connect_end_time_lo;
-       uint32_t cp_mqd_connect_end_time_hi;
-       uint32_t cp_mqd_connect_end_wf_count;
-       uint32_t cp_mqd_connect_end_pq_rptr;
-       uint32_t cp_mqd_connect_end_pq_wptr;
-       uint32_t cp_mqd_connect_end_ib_rptr;
-       uint32_t reserved_96;
-       uint32_t reserved_97;
-       uint32_t reserved_98;
-       uint32_t reserved_99;
-       uint32_t iqtimer_pkt_header;
-       uint32_t iqtimer_pkt_dw0;
-       uint32_t iqtimer_pkt_dw1;
-       uint32_t iqtimer_pkt_dw2;
-       uint32_t iqtimer_pkt_dw3;
-       uint32_t iqtimer_pkt_dw4;
-       uint32_t iqtimer_pkt_dw5;
-       uint32_t iqtimer_pkt_dw6;
-       uint32_t reserved_108;
-       uint32_t reserved_109;
-       uint32_t reserved_110;
-       uint32_t reserved_111;
-       uint32_t queue_doorbell_id0;
-       uint32_t queue_doorbell_id1;
-       uint32_t queue_doorbell_id2;
-       uint32_t queue_doorbell_id3;
-       uint32_t queue_doorbell_id4;
-       uint32_t queue_doorbell_id5;
-       uint32_t queue_doorbell_id6;
-       uint32_t queue_doorbell_id7;
-       uint32_t queue_doorbell_id8;
-       uint32_t queue_doorbell_id9;
-       uint32_t queue_doorbell_id10;
-       uint32_t queue_doorbell_id11;
-       uint32_t queue_doorbell_id12;
-       uint32_t queue_doorbell_id13;
-       uint32_t queue_doorbell_id14;
-       uint32_t queue_doorbell_id15;
-};
+#define SDMA0_RLC0_RB_CNTL                             0xD400u
+#define        SDMA_RB_VMID(x)                                 (x << 24)
+#define        SDMA0_RLC0_RB_BASE                              0xD404u
+#define        SDMA0_RLC0_RB_BASE_HI                           0xD408u
+#define        SDMA0_RLC0_RB_RPTR                              0xD40Cu
+#define        SDMA0_RLC0_RB_WPTR                              0xD410u
+#define        SDMA0_RLC0_RB_WPTR_POLL_CNTL                    0xD414u
+#define        SDMA0_RLC0_RB_WPTR_POLL_ADDR_HI                 0xD418u
+#define        SDMA0_RLC0_RB_WPTR_POLL_ADDR_LO                 0xD41Cu
+#define        SDMA0_RLC0_RB_RPTR_ADDR_HI                      0xD420u
+#define        SDMA0_RLC0_RB_RPTR_ADDR_LO                      0xD424u
+#define        SDMA0_RLC0_IB_CNTL                              0xD428u
+#define        SDMA0_RLC0_IB_RPTR                              0xD42Cu
+#define        SDMA0_RLC0_IB_OFFSET                            0xD430u
+#define        SDMA0_RLC0_IB_BASE_LO                           0xD434u
+#define        SDMA0_RLC0_IB_BASE_HI                           0xD438u
+#define        SDMA0_RLC0_IB_SIZE                              0xD43Cu
+#define        SDMA0_RLC0_SKIP_CNTL                            0xD440u
+#define        SDMA0_RLC0_CONTEXT_STATUS                       0xD444u
+#define        SDMA_RLC_IDLE                                   (1 << 2)
+#define        SDMA0_RLC0_DOORBELL                             0xD448u
+#define        SDMA_OFFSET(x)                                  (x << 0)
+#define        SDMA_DB_ENABLE                                  (1 << 28)
+#define        SDMA0_RLC0_VIRTUAL_ADDR                         0xD49Cu
+#define        SDMA_ATC                                        (1 << 0)
+#define        SDMA_VA_PTR32                                   (1 << 4)
+#define        SDMA_VA_SHARED_BASE(x)                          (x << 8)
+#define        SDMA0_RLC0_APE1_CNTL                            0xD4A0u
+#define        SDMA0_RLC0_DOORBELL_LOG                         0xD4A4u
+#define        SDMA0_RLC0_WATERMARK                            0xD4A8u
+#define        SDMA0_CNTL                                      0xD010
+#define        SDMA1_CNTL                                      0xD810
 
 #endif
index dde5c7e29eb200b6dc78f1fad46197e43e0013ed..479519c24a1f678fe7eaf5e0224763defddcdec8 100644 (file)
@@ -282,6 +282,33 @@ static void cik_sdma_rlc_stop(struct radeon_device *rdev)
        /* XXX todo */
 }
 
+/**
+ * cik_sdma_ctx_switch_enable - enable/disable sdma engine preemption
+ *
+ * @rdev: radeon_device pointer
+ * @enable: enable/disable preemption.
+ *
+ * Halt or unhalt the async dma engines (CIK).
+ */
+void cik_sdma_ctx_switch_enable(struct radeon_device *rdev, bool enable)
+{
+       uint32_t reg_offset, value;
+       int i;
+
+       for (i = 0; i < 2; i++) {
+               if (i == 0)
+                       reg_offset = SDMA0_REGISTER_OFFSET;
+               else
+                       reg_offset = SDMA1_REGISTER_OFFSET;
+               value = RREG32(SDMA0_CNTL + reg_offset);
+               if (enable)
+                       value |= AUTO_CTXSW_ENABLE;
+               else
+                       value &= ~AUTO_CTXSW_ENABLE;
+               WREG32(SDMA0_CNTL + reg_offset, value);
+       }
+}
+
 /**
  * cik_sdma_enable - stop the async dma engines
  *
@@ -312,6 +339,8 @@ void cik_sdma_enable(struct radeon_device *rdev, bool enable)
                        me_cntl |= SDMA_HALT;
                WREG32(SDMA0_ME_CNTL + reg_offset, me_cntl);
        }
+
+       cik_sdma_ctx_switch_enable(rdev, enable);
 }
 
 /**
@@ -903,6 +932,9 @@ void cik_sdma_vm_pad_ib(struct radeon_ib *ib)
 void cik_dma_vm_flush(struct radeon_device *rdev, struct radeon_ring *ring,
                      unsigned vm_id, uint64_t pd_addr)
 {
+       u32 extra_bits = (SDMA_POLL_REG_MEM_EXTRA_OP(0) |
+                         SDMA_POLL_REG_MEM_EXTRA_FUNC(0)); /* always */
+
        radeon_ring_write(ring, SDMA_PACKET(SDMA_OPCODE_SRBM_WRITE, 0, 0xf000));
        if (vm_id < 8) {
                radeon_ring_write(ring, (VM_CONTEXT0_PAGE_TABLE_BASE_ADDR + (vm_id << 2)) >> 2);
@@ -943,5 +975,12 @@ void cik_dma_vm_flush(struct radeon_device *rdev, struct radeon_ring *ring,
        radeon_ring_write(ring, SDMA_PACKET(SDMA_OPCODE_SRBM_WRITE, 0, 0xf000));
        radeon_ring_write(ring, VM_INVALIDATE_REQUEST >> 2);
        radeon_ring_write(ring, 1 << vm_id);
+
+       radeon_ring_write(ring, SDMA_PACKET(SDMA_OPCODE_POLL_REG_MEM, 0, extra_bits));
+       radeon_ring_write(ring, VM_INVALIDATE_REQUEST >> 2);
+       radeon_ring_write(ring, 0);
+       radeon_ring_write(ring, 0); /* reference */
+       radeon_ring_write(ring, 0); /* mask */
+       radeon_ring_write(ring, (0xfff << 16) | 10); /* retry count, poll interval */
 }
 
index 360de9f1f4914079d3de3ad0022a50862b934395..aea48c89b24170e692bc91bf2b4c927ef9d08784 100644 (file)
@@ -2516,6 +2516,16 @@ void cayman_vm_flush(struct radeon_device *rdev, struct radeon_ring *ring,
        radeon_ring_write(ring, PACKET0(VM_INVALIDATE_REQUEST, 0));
        radeon_ring_write(ring, 1 << vm_id);
 
+       /* wait for the invalidate to complete */
+       radeon_ring_write(ring, PACKET3(PACKET3_WAIT_REG_MEM, 5));
+       radeon_ring_write(ring, (WAIT_REG_MEM_FUNCTION(0) |  /* always */
+                                WAIT_REG_MEM_ENGINE(0))); /* me */
+       radeon_ring_write(ring, VM_INVALIDATE_REQUEST >> 2);
+       radeon_ring_write(ring, 0);
+       radeon_ring_write(ring, 0); /* ref */
+       radeon_ring_write(ring, 0); /* mask */
+       radeon_ring_write(ring, 0x20); /* poll interval */
+
        /* sync PFP to ME, otherwise we might get invalid PFP reads */
        radeon_ring_write(ring, PACKET3(PACKET3_PFP_SYNC_ME, 0));
        radeon_ring_write(ring, 0x0);
index 50f88611ff60c832dc59e767543f91f8baf859eb..4be2bb7cbef3058b49864fd7a6505e97e1017d6d 100644 (file)
@@ -463,5 +463,11 @@ void cayman_dma_vm_flush(struct radeon_device *rdev, struct radeon_ring *ring,
        radeon_ring_write(ring, DMA_PACKET(DMA_PACKET_SRBM_WRITE, 0, 0, 0));
        radeon_ring_write(ring, (0xf << 16) | (VM_INVALIDATE_REQUEST >> 2));
        radeon_ring_write(ring, 1 << vm_id);
+
+       /* wait for invalidate to complete */
+       radeon_ring_write(ring, DMA_SRBM_READ_PACKET);
+       radeon_ring_write(ring, (0xff << 20) | (VM_INVALIDATE_REQUEST >> 2));
+       radeon_ring_write(ring, 0); /* mask */
+       radeon_ring_write(ring, 0); /* value */
 }
 
index 2e12e4d69253fde453c3fb648566c0224bfe06bc..ad7125486894d18ae90b0bc507d248d92baaf3e6 100644 (file)
 #define        PACKET3_MEM_SEMAPHORE                           0x39
 #define        PACKET3_MPEG_INDEX                              0x3A
 #define        PACKET3_WAIT_REG_MEM                            0x3C
+#define                WAIT_REG_MEM_FUNCTION(x)                ((x) << 0)
+                /* 0 - always
+                * 1 - <
+                * 2 - <=
+                * 3 - ==
+                * 4 - !=
+                * 5 - >=
+                * 6 - >
+                */
+#define                WAIT_REG_MEM_MEM_SPACE(x)               ((x) << 4)
+                /* 0 - reg
+                * 1 - mem
+                */
+#define                WAIT_REG_MEM_ENGINE(x)                  ((x) << 8)
+                /* 0 - me
+                * 1 - pfp
+                */
 #define        PACKET3_MEM_WRITE                               0x3D
 #define        PACKET3_PFP_SYNC_ME                             0x42
 #define        PACKET3_SURFACE_SYNC                            0x43
                                         (1 << 21) |                    \
                                         (((n) & 0xFFFFF) << 0))
 
+#define DMA_SRBM_POLL_PACKET           ((9 << 28) |                    \
+                                        (1 << 27) |                    \
+                                        (1 << 26))
+
+#define DMA_SRBM_READ_PACKET           ((9 << 28) |                    \
+                                        (1 << 27))
+
 /* async DMA Packet types */
 #define        DMA_PACKET_WRITE                                  0x2
 #define        DMA_PACKET_COPY                                   0x3
index 850de57069bec0effcadd4a55c6b1abead242314..121aff6a3b4108f1fb9eeb9790873dba8323ff09 100644 (file)
@@ -333,6 +333,20 @@ static struct radeon_asic_ring r300_gfx_ring = {
        .set_wptr = &r100_gfx_set_wptr,
 };
 
+static struct radeon_asic_ring rv515_gfx_ring = {
+       .ib_execute = &r100_ring_ib_execute,
+       .emit_fence = &r300_fence_ring_emit,
+       .emit_semaphore = &r100_semaphore_ring_emit,
+       .cs_parse = &r300_cs_parse,
+       .ring_start = &rv515_ring_start,
+       .ring_test = &r100_ring_test,
+       .ib_test = &r100_ib_test,
+       .is_lockup = &r100_gpu_is_lockup,
+       .get_rptr = &r100_gfx_get_rptr,
+       .get_wptr = &r100_gfx_get_wptr,
+       .set_wptr = &r100_gfx_set_wptr,
+};
+
 static struct radeon_asic r300_asic = {
        .init = &r300_init,
        .fini = &r300_fini,
@@ -748,7 +762,7 @@ static struct radeon_asic rv515_asic = {
                .set_page = &rv370_pcie_gart_set_page,
        },
        .ring = {
-               [RADEON_RING_TYPE_GFX_INDEX] = &r300_gfx_ring
+               [RADEON_RING_TYPE_GFX_INDEX] = &rv515_gfx_ring
        },
        .irq = {
                .set = &rs600_irq_set,
@@ -814,7 +828,7 @@ static struct radeon_asic r520_asic = {
                .set_page = &rv370_pcie_gart_set_page,
        },
        .ring = {
-               [RADEON_RING_TYPE_GFX_INDEX] = &r300_gfx_ring
+               [RADEON_RING_TYPE_GFX_INDEX] = &rv515_gfx_ring
        },
        .irq = {
                .set = &rs600_irq_set,
index 29b9220ec3998daee56bac0969de169268964c13..3000bc4c136b912c2576ca82ebc00e35678451bd 100644 (file)
@@ -390,18 +390,27 @@ int radeon_fbdev_init(struct radeon_device *rdev)
        ret = drm_fb_helper_init(rdev->ddev, &rfbdev->helper,
                                 rdev->num_crtc,
                                 RADEONFB_CONN_LIMIT);
-       if (ret) {
-               kfree(rfbdev);
-               return ret;
-       }
+       if (ret)
+               goto free;
 
-       drm_fb_helper_single_add_all_connectors(&rfbdev->helper);
+       ret = drm_fb_helper_single_add_all_connectors(&rfbdev->helper);
+       if (ret)
+               goto fini;
 
        /* disable all the possible outputs/crtcs before entering KMS mode */
        drm_helper_disable_unused_functions(rdev->ddev);
 
-       drm_fb_helper_initial_config(&rfbdev->helper, bpp_sel);
+       ret = drm_fb_helper_initial_config(&rfbdev->helper, bpp_sel);
+       if (ret)
+               goto fini;
+
        return 0;
+
+fini:
+       drm_fb_helper_fini(&rfbdev->helper);
+free:
+       kfree(rfbdev);
+       return ret;
 }
 
 void radeon_fbdev_fini(struct radeon_device *rdev)
index a46f73737994aba3f603aea4dde15ff916a91109..d0b4f7d1140d6a391a9f32c7ec466f099b99b5fe 100644 (file)
@@ -576,7 +576,7 @@ error_unreserve:
 error_free:
        drm_free_large(vm_bos);
 
-       if (r)
+       if (r && r != -ERESTARTSYS)
                DRM_ERROR("Couldn't update BO_VA (%d)\n", r);
 }
 
index 8bf87f1203ccaddd85a215dc0c5e19fb48305dbf..7b274205eeaf05d0e2001848a4449091d0962db2 100644 (file)
 #include "radeon_kfd.h"
 #include "radeon_ucode.h"
 #include <linux/firmware.h>
+#include "cik_structs.h"
 
 #define CIK_PIPE_PER_MEC       (4)
 
 struct kgd_mem {
-       struct radeon_sa_bo *sa_bo;
+       struct radeon_bo *bo;
        uint64_t gpu_addr;
-       void *ptr;
+       void *cpu_ptr;
 };
 
-static int init_sa_manager(struct kgd_dev *kgd, unsigned int size);
-static void fini_sa_manager(struct kgd_dev *kgd);
 
-static int allocate_mem(struct kgd_dev *kgd, size_t size, size_t alignment,
-               enum kgd_memory_pool pool, struct kgd_mem **mem);
+static int alloc_gtt_mem(struct kgd_dev *kgd, size_t size,
+                       void **mem_obj, uint64_t *gpu_addr,
+                       void **cpu_ptr);
 
-static void free_mem(struct kgd_dev *kgd, struct kgd_mem *mem);
+static void free_gtt_mem(struct kgd_dev *kgd, void *mem_obj);
 
 static uint64_t get_vmem_size(struct kgd_dev *kgd);
 static uint64_t get_gpu_clock_counter(struct kgd_dev *kgd);
@@ -64,36 +64,37 @@ static void kgd_program_sh_mem_settings(struct kgd_dev *kgd, uint32_t vmid,
 static int kgd_set_pasid_vmid_mapping(struct kgd_dev *kgd, unsigned int pasid,
                                        unsigned int vmid);
 
-static int kgd_init_memory(struct kgd_dev *kgd);
-
 static int kgd_init_pipeline(struct kgd_dev *kgd, uint32_t pipe_id,
                                uint32_t hpd_size, uint64_t hpd_gpu_addr);
 
 static int kgd_hqd_load(struct kgd_dev *kgd, void *mqd, uint32_t pipe_id,
                        uint32_t queue_id, uint32_t __user *wptr);
-
+static int kgd_hqd_sdma_load(struct kgd_dev *kgd, void *mqd);
 static bool kgd_hqd_is_occupied(struct kgd_dev *kgd, uint64_t queue_address,
                                uint32_t pipe_id, uint32_t queue_id);
 
 static int kgd_hqd_destroy(struct kgd_dev *kgd, uint32_t reset_type,
                                unsigned int timeout, uint32_t pipe_id,
                                uint32_t queue_id);
+static bool kgd_hqd_sdma_is_occupied(struct kgd_dev *kgd, void *mqd);
+static int kgd_hqd_sdma_destroy(struct kgd_dev *kgd, void *mqd,
+                               unsigned int timeout);
 
 static const struct kfd2kgd_calls kfd2kgd = {
-       .init_sa_manager = init_sa_manager,
-       .fini_sa_manager = fini_sa_manager,
-       .allocate_mem = allocate_mem,
-       .free_mem = free_mem,
+       .init_gtt_mem_allocation = alloc_gtt_mem,
+       .free_gtt_mem = free_gtt_mem,
        .get_vmem_size = get_vmem_size,
        .get_gpu_clock_counter = get_gpu_clock_counter,
        .get_max_engine_clock_in_mhz = get_max_engine_clock_in_mhz,
        .program_sh_mem_settings = kgd_program_sh_mem_settings,
        .set_pasid_vmid_mapping = kgd_set_pasid_vmid_mapping,
-       .init_memory = kgd_init_memory,
        .init_pipeline = kgd_init_pipeline,
        .hqd_load = kgd_hqd_load,
+       .hqd_sdma_load = kgd_hqd_sdma_load,
        .hqd_is_occupied = kgd_hqd_is_occupied,
+       .hqd_sdma_is_occupied = kgd_hqd_sdma_is_occupied,
        .hqd_destroy = kgd_hqd_destroy,
+       .hqd_sdma_destroy = kgd_hqd_sdma_destroy,
        .get_fw_version = get_fw_version
 };
 
@@ -194,87 +195,78 @@ int radeon_kfd_resume(struct radeon_device *rdev)
        return r;
 }
 
-static u32 pool_to_domain(enum kgd_memory_pool p)
-{
-       switch (p) {
-       case KGD_POOL_FRAMEBUFFER: return RADEON_GEM_DOMAIN_VRAM;
-       default: return RADEON_GEM_DOMAIN_GTT;
-       }
-}
-
-static int init_sa_manager(struct kgd_dev *kgd, unsigned int size)
+static int alloc_gtt_mem(struct kgd_dev *kgd, size_t size,
+                       void **mem_obj, uint64_t *gpu_addr,
+                       void **cpu_ptr)
 {
        struct radeon_device *rdev = (struct radeon_device *)kgd;
+       struct kgd_mem **mem = (struct kgd_mem **) mem_obj;
        int r;
 
        BUG_ON(kgd == NULL);
+       BUG_ON(gpu_addr == NULL);
+       BUG_ON(cpu_ptr == NULL);
 
-       r = radeon_sa_bo_manager_init(rdev, &rdev->kfd_bo,
-                                     size,
-                                     RADEON_GPU_PAGE_SIZE,
-                                     RADEON_GEM_DOMAIN_GTT,
-                                     RADEON_GEM_GTT_WC);
+       *mem = kmalloc(sizeof(struct kgd_mem), GFP_KERNEL);
+       if ((*mem) == NULL)
+               return -ENOMEM;
 
-       if (r)
+       r = radeon_bo_create(rdev, size, PAGE_SIZE, true, RADEON_GEM_DOMAIN_GTT,
+                               RADEON_GEM_GTT_WC, NULL, NULL, &(*mem)->bo);
+       if (r) {
+               dev_err(rdev->dev,
+                       "failed to allocate BO for amdkfd (%d)\n", r);
                return r;
+       }
 
-       r = radeon_sa_bo_manager_start(rdev, &rdev->kfd_bo);
-       if (r)
-               radeon_sa_bo_manager_fini(rdev, &rdev->kfd_bo);
-
-       return r;
-}
-
-static void fini_sa_manager(struct kgd_dev *kgd)
-{
-       struct radeon_device *rdev = (struct radeon_device *)kgd;
-
-       BUG_ON(kgd == NULL);
-
-       radeon_sa_bo_manager_suspend(rdev, &rdev->kfd_bo);
-       radeon_sa_bo_manager_fini(rdev, &rdev->kfd_bo);
-}
-
-static int allocate_mem(struct kgd_dev *kgd, size_t size, size_t alignment,
-               enum kgd_memory_pool pool, struct kgd_mem **mem)
-{
-       struct radeon_device *rdev = (struct radeon_device *)kgd;
-       u32 domain;
-       int r;
-
-       BUG_ON(kgd == NULL);
-
-       domain = pool_to_domain(pool);
-       if (domain != RADEON_GEM_DOMAIN_GTT) {
-               dev_err(rdev->dev,
-                       "Only allowed to allocate gart memory for kfd\n");
-               return -EINVAL;
+       /* map the buffer */
+       r = radeon_bo_reserve((*mem)->bo, true);
+       if (r) {
+               dev_err(rdev->dev, "(%d) failed to reserve bo for amdkfd\n", r);
+               goto allocate_mem_reserve_bo_failed;
        }
 
-       *mem = kmalloc(sizeof(struct kgd_mem), GFP_KERNEL);
-       if ((*mem) == NULL)
-               return -ENOMEM;
+       r = radeon_bo_pin((*mem)->bo, RADEON_GEM_DOMAIN_GTT,
+                               &(*mem)->gpu_addr);
+       if (r) {
+               dev_err(rdev->dev, "(%d) failed to pin bo for amdkfd\n", r);
+               goto allocate_mem_pin_bo_failed;
+       }
+       *gpu_addr = (*mem)->gpu_addr;
 
-       r = radeon_sa_bo_new(rdev, &rdev->kfd_bo, &(*mem)->sa_bo, size,
-                               alignment);
+       r = radeon_bo_kmap((*mem)->bo, &(*mem)->cpu_ptr);
        if (r) {
-               dev_err(rdev->dev, "failed to get memory for kfd (%d)\n", r);
-               return r;
+               dev_err(rdev->dev,
+                       "(%d) failed to map bo to kernel for amdkfd\n", r);
+               goto allocate_mem_kmap_bo_failed;
        }
+       *cpu_ptr = (*mem)->cpu_ptr;
 
-       (*mem)->ptr = radeon_sa_bo_cpu_addr((*mem)->sa_bo);
-       (*mem)->gpu_addr = radeon_sa_bo_gpu_addr((*mem)->sa_bo);
+       radeon_bo_unreserve((*mem)->bo);
 
        return 0;
+
+allocate_mem_kmap_bo_failed:
+       radeon_bo_unpin((*mem)->bo);
+allocate_mem_pin_bo_failed:
+       radeon_bo_unreserve((*mem)->bo);
+allocate_mem_reserve_bo_failed:
+       radeon_bo_unref(&(*mem)->bo);
+
+       return r;
 }
 
-static void free_mem(struct kgd_dev *kgd, struct kgd_mem *mem)
+static void free_gtt_mem(struct kgd_dev *kgd, void *mem_obj)
 {
-       struct radeon_device *rdev = (struct radeon_device *)kgd;
+       struct kgd_mem *mem = (struct kgd_mem *) mem_obj;
 
-       BUG_ON(kgd == NULL);
+       BUG_ON(mem == NULL);
 
-       radeon_sa_bo_free(rdev, &mem->sa_bo, NULL);
+       radeon_bo_reserve(mem->bo, true);
+       radeon_bo_kunmap(mem->bo);
+       radeon_bo_unpin(mem->bo);
+       radeon_bo_unreserve(mem->bo);
+       radeon_bo_unref(&(mem->bo));
        kfree(mem);
 }
 
@@ -397,42 +389,6 @@ static int kgd_set_pasid_vmid_mapping(struct kgd_dev *kgd, unsigned int pasid,
        return 0;
 }
 
-static int kgd_init_memory(struct kgd_dev *kgd)
-{
-       /*
-        * Configure apertures:
-        * LDS:         0x60000000'00000000 - 0x60000001'00000000 (4GB)
-        * Scratch:     0x60000001'00000000 - 0x60000002'00000000 (4GB)
-        * GPUVM:       0x60010000'00000000 - 0x60020000'00000000 (1TB)
-        */
-       int i;
-       uint32_t sh_mem_bases = PRIVATE_BASE(0x6000) | SHARED_BASE(0x6000);
-
-       for (i = 8; i < 16; i++) {
-               uint32_t sh_mem_config;
-
-               lock_srbm(kgd, 0, 0, 0, i);
-
-               sh_mem_config = ALIGNMENT_MODE(SH_MEM_ALIGNMENT_MODE_UNALIGNED);
-               sh_mem_config |= DEFAULT_MTYPE(MTYPE_NONCACHED);
-
-               write_register(kgd, SH_MEM_CONFIG, sh_mem_config);
-
-               write_register(kgd, SH_MEM_BASES, sh_mem_bases);
-
-               /* Scratch aperture is not supported for now. */
-               write_register(kgd, SH_STATIC_MEM_CONFIG, 0);
-
-               /* APE1 disabled for now. */
-               write_register(kgd, SH_MEM_APE1_BASE, 1);
-               write_register(kgd, SH_MEM_APE1_LIMIT, 0);
-
-               unlock_srbm(kgd);
-       }
-
-       return 0;
-}
-
 static int kgd_init_pipeline(struct kgd_dev *kgd, uint32_t pipe_id,
                                uint32_t hpd_size, uint64_t hpd_gpu_addr)
 {
@@ -451,11 +407,28 @@ static int kgd_init_pipeline(struct kgd_dev *kgd, uint32_t pipe_id,
        return 0;
 }
 
+static inline uint32_t get_sdma_base_addr(struct cik_sdma_rlc_registers *m)
+{
+       uint32_t retval;
+
+       retval = m->sdma_engine_id * SDMA1_REGISTER_OFFSET +
+                       m->sdma_queue_id * KFD_CIK_SDMA_QUEUE_OFFSET;
+
+       pr_debug("kfd: sdma base address: 0x%x\n", retval);
+
+       return retval;
+}
+
 static inline struct cik_mqd *get_mqd(void *mqd)
 {
        return (struct cik_mqd *)mqd;
 }
 
+static inline struct cik_sdma_rlc_registers *get_sdma_mqd(void *mqd)
+{
+       return (struct cik_sdma_rlc_registers *)mqd;
+}
+
 static int kgd_hqd_load(struct kgd_dev *kgd, void *mqd, uint32_t pipe_id,
                        uint32_t queue_id, uint32_t __user *wptr)
 {
@@ -533,6 +506,45 @@ static int kgd_hqd_load(struct kgd_dev *kgd, void *mqd, uint32_t pipe_id,
        return 0;
 }
 
+static int kgd_hqd_sdma_load(struct kgd_dev *kgd, void *mqd)
+{
+       struct cik_sdma_rlc_registers *m;
+       uint32_t sdma_base_addr;
+
+       m = get_sdma_mqd(mqd);
+       sdma_base_addr = get_sdma_base_addr(m);
+
+       write_register(kgd,
+                       sdma_base_addr + SDMA0_RLC0_VIRTUAL_ADDR,
+                       m->sdma_rlc_virtual_addr);
+
+       write_register(kgd,
+                       sdma_base_addr + SDMA0_RLC0_RB_BASE,
+                       m->sdma_rlc_rb_base);
+
+       write_register(kgd,
+                       sdma_base_addr + SDMA0_RLC0_RB_BASE_HI,
+                       m->sdma_rlc_rb_base_hi);
+
+       write_register(kgd,
+                       sdma_base_addr + SDMA0_RLC0_RB_RPTR_ADDR_LO,
+                       m->sdma_rlc_rb_rptr_addr_lo);
+
+       write_register(kgd,
+                       sdma_base_addr + SDMA0_RLC0_RB_RPTR_ADDR_HI,
+                       m->sdma_rlc_rb_rptr_addr_hi);
+
+       write_register(kgd,
+                       sdma_base_addr + SDMA0_RLC0_DOORBELL,
+                       m->sdma_rlc_doorbell);
+
+       write_register(kgd,
+                       sdma_base_addr + SDMA0_RLC0_RB_CNTL,
+                       m->sdma_rlc_rb_cntl);
+
+       return 0;
+}
+
 static bool kgd_hqd_is_occupied(struct kgd_dev *kgd, uint64_t queue_address,
                                uint32_t pipe_id, uint32_t queue_id)
 {
@@ -554,6 +566,24 @@ static bool kgd_hqd_is_occupied(struct kgd_dev *kgd, uint64_t queue_address,
        return retval;
 }
 
+static bool kgd_hqd_sdma_is_occupied(struct kgd_dev *kgd, void *mqd)
+{
+       struct cik_sdma_rlc_registers *m;
+       uint32_t sdma_base_addr;
+       uint32_t sdma_rlc_rb_cntl;
+
+       m = get_sdma_mqd(mqd);
+       sdma_base_addr = get_sdma_base_addr(m);
+
+       sdma_rlc_rb_cntl = read_register(kgd,
+                                       sdma_base_addr + SDMA0_RLC0_RB_CNTL);
+
+       if (sdma_rlc_rb_cntl & SDMA_RB_ENABLE)
+               return true;
+
+       return false;
+}
+
 static int kgd_hqd_destroy(struct kgd_dev *kgd, uint32_t reset_type,
                                unsigned int timeout, uint32_t pipe_id,
                                uint32_t queue_id)
@@ -583,6 +613,39 @@ static int kgd_hqd_destroy(struct kgd_dev *kgd, uint32_t reset_type,
        return 0;
 }
 
+static int kgd_hqd_sdma_destroy(struct kgd_dev *kgd, void *mqd,
+                               unsigned int timeout)
+{
+       struct cik_sdma_rlc_registers *m;
+       uint32_t sdma_base_addr;
+       uint32_t temp;
+
+       m = get_sdma_mqd(mqd);
+       sdma_base_addr = get_sdma_base_addr(m);
+
+       temp = read_register(kgd, sdma_base_addr + SDMA0_RLC0_RB_CNTL);
+       temp = temp & ~SDMA_RB_ENABLE;
+       write_register(kgd, sdma_base_addr + SDMA0_RLC0_RB_CNTL, temp);
+
+       while (true) {
+               temp = read_register(kgd, sdma_base_addr +
+                                               SDMA0_RLC0_CONTEXT_STATUS);
+               if (temp & SDMA_RLC_IDLE)
+                       break;
+               if (timeout == 0)
+                       return -ETIME;
+               msleep(20);
+               timeout -= 20;
+       }
+
+       write_register(kgd, sdma_base_addr + SDMA0_RLC0_DOORBELL, 0);
+       write_register(kgd, sdma_base_addr + SDMA0_RLC0_RB_RPTR, 0);
+       write_register(kgd, sdma_base_addr + SDMA0_RLC0_RB_WPTR, 0);
+       write_register(kgd, sdma_base_addr + SDMA0_RLC0_RB_BASE, 0);
+
+       return 0;
+}
+
 static uint16_t get_fw_version(struct kgd_dev *kgd, enum kgd_engine_type type)
 {
        struct radeon_device *rdev = (struct radeon_device *) kgd;
index f90e161ca507c5d8b4e839abad43f0333994e093..1103f9082f6b069aa1c4501347ef3066fc1a619a 100644 (file)
@@ -29,7 +29,7 @@
 #define RADEON_KFD_H_INCLUDED
 
 #include <linux/types.h>
-#include "../amd/include/kgd_kfd_interface.h"
+#include "kgd_kfd_interface.h"
 
 struct radeon_device;
 
index 32522cc940a127c4b413c9928121c2b9258457fd..f7da8fe96a66b51e40aedb6ee0255770821cb989 100644 (file)
@@ -1287,8 +1287,39 @@ dpm_failed:
        return ret;
 }
 
+struct radeon_dpm_quirk {
+       u32 chip_vendor;
+       u32 chip_device;
+       u32 subsys_vendor;
+       u32 subsys_device;
+};
+
+/* cards with dpm stability problems */
+static struct radeon_dpm_quirk radeon_dpm_quirk_list[] = {
+       /* TURKS - https://bugs.launchpad.net/ubuntu/+source/linux/+bug/1386534 */
+       { PCI_VENDOR_ID_ATI, 0x6759, 0x1682, 0x3195 },
+       /* TURKS - https://bugzilla.kernel.org/show_bug.cgi?id=83731 */
+       { PCI_VENDOR_ID_ATI, 0x6840, 0x1179, 0xfb81 },
+       { 0, 0, 0, 0 },
+};
+
 int radeon_pm_init(struct radeon_device *rdev)
 {
+       struct radeon_dpm_quirk *p = radeon_dpm_quirk_list;
+       bool disable_dpm = false;
+
+       /* Apply dpm quirks */
+       while (p && p->chip_device != 0) {
+               if (rdev->pdev->vendor == p->chip_vendor &&
+                   rdev->pdev->device == p->chip_device &&
+                   rdev->pdev->subsystem_vendor == p->subsys_vendor &&
+                   rdev->pdev->subsystem_device == p->subsys_device) {
+                       disable_dpm = true;
+                       break;
+               }
+               ++p;
+       }
+
        /* enable dpm on rv6xx+ */
        switch (rdev->family) {
        case CHIP_RV610:
@@ -1344,6 +1375,8 @@ int radeon_pm_init(struct radeon_device *rdev)
                         (!(rdev->flags & RADEON_IS_IGP)) &&
                         (!rdev->smc_fw))
                        rdev->pm.pm_method = PM_METHOD_PROFILE;
+               else if (disable_dpm && (radeon_dpm == -1))
+                       rdev->pm.pm_method = PM_METHOD_PROFILE;
                else if (radeon_dpm == 0)
                        rdev->pm.pm_method = PM_METHOD_PROFILE;
                else
index 60df444bd0756fbe42b5a5dab1072f47c5c73a3a..5d89b874a1a25851aa331af54f3ae6a0fd7c39cc 100644 (file)
@@ -5057,6 +5057,16 @@ void si_vm_flush(struct radeon_device *rdev, struct radeon_ring *ring,
        radeon_ring_write(ring, 0);
        radeon_ring_write(ring, 1 << vm_id);
 
+       /* wait for the invalidate to complete */
+       radeon_ring_write(ring, PACKET3(PACKET3_WAIT_REG_MEM, 5));
+       radeon_ring_write(ring, (WAIT_REG_MEM_FUNCTION(0) |  /* always */
+                                WAIT_REG_MEM_ENGINE(0))); /* me */
+       radeon_ring_write(ring, VM_INVALIDATE_REQUEST >> 2);
+       radeon_ring_write(ring, 0);
+       radeon_ring_write(ring, 0); /* ref */
+       radeon_ring_write(ring, 0); /* mask */
+       radeon_ring_write(ring, 0x20); /* poll interval */
+
        /* sync PFP to ME, otherwise we might get invalid PFP reads */
        radeon_ring_write(ring, PACKET3(PACKET3_PFP_SYNC_ME, 0));
        radeon_ring_write(ring, 0x0);
index f5cc777e1c5f142ff00b383e3863b70b47a96b3e..aa7b872b2c438d28101f081c920715b651917f1d 100644 (file)
@@ -206,6 +206,14 @@ void si_dma_vm_flush(struct radeon_device *rdev, struct radeon_ring *ring,
        radeon_ring_write(ring, DMA_PACKET(DMA_PACKET_SRBM_WRITE, 0, 0, 0, 0));
        radeon_ring_write(ring, (0xf << 16) | (VM_INVALIDATE_REQUEST >> 2));
        radeon_ring_write(ring, 1 << vm_id);
+
+       /* wait for invalidate to complete */
+       radeon_ring_write(ring, DMA_PACKET(DMA_PACKET_POLL_REG_MEM, 0, 0, 0, 0));
+       radeon_ring_write(ring, VM_INVALIDATE_REQUEST);
+       radeon_ring_write(ring, 0xff << 16); /* retry */
+       radeon_ring_write(ring, 1 << vm_id); /* mask */
+       radeon_ring_write(ring, 0); /* value */
+       radeon_ring_write(ring, (0 << 28) | 0x20); /* func(always) | poll interval */
 }
 
 /**
index 32e354b8b0aba6b96cfc8e94b1519b7fca4f47fb..eff8a6444956310a591afdf3d980f2f3288cf386 100644 (file)
@@ -2908,6 +2908,22 @@ static int si_init_smc_spll_table(struct radeon_device *rdev)
        return ret;
 }
 
+struct si_dpm_quirk {
+       u32 chip_vendor;
+       u32 chip_device;
+       u32 subsys_vendor;
+       u32 subsys_device;
+       u32 max_sclk;
+       u32 max_mclk;
+};
+
+/* cards with dpm stability problems */
+static struct si_dpm_quirk si_dpm_quirk_list[] = {
+       /* PITCAIRN - https://bugs.freedesktop.org/show_bug.cgi?id=76490 */
+       { PCI_VENDOR_ID_ATI, 0x6810, 0x1462, 0x3036, 0, 120000 },
+       { 0, 0, 0, 0 },
+};
+
 static void si_apply_state_adjust_rules(struct radeon_device *rdev,
                                        struct radeon_ps *rps)
 {
@@ -2918,7 +2934,22 @@ static void si_apply_state_adjust_rules(struct radeon_device *rdev,
        u32 mclk, sclk;
        u16 vddc, vddci;
        u32 max_sclk_vddc, max_mclk_vddci, max_mclk_vddc;
+       u32 max_sclk = 0, max_mclk = 0;
        int i;
+       struct si_dpm_quirk *p = si_dpm_quirk_list;
+
+       /* Apply dpm quirks */
+       while (p && p->chip_device != 0) {
+               if (rdev->pdev->vendor == p->chip_vendor &&
+                   rdev->pdev->device == p->chip_device &&
+                   rdev->pdev->subsystem_vendor == p->subsys_vendor &&
+                   rdev->pdev->subsystem_device == p->subsys_device) {
+                       max_sclk = p->max_sclk;
+                       max_mclk = p->max_mclk;
+                       break;
+               }
+               ++p;
+       }
 
        if ((rdev->pm.dpm.new_active_crtc_count > 1) ||
            ni_dpm_vblank_too_short(rdev))
@@ -2972,6 +3003,14 @@ static void si_apply_state_adjust_rules(struct radeon_device *rdev,
                        if (ps->performance_levels[i].mclk > max_mclk_vddc)
                                ps->performance_levels[i].mclk = max_mclk_vddc;
                }
+               if (max_mclk) {
+                       if (ps->performance_levels[i].mclk > max_mclk)
+                               ps->performance_levels[i].mclk = max_mclk;
+               }
+               if (max_sclk) {
+                       if (ps->performance_levels[i].sclk > max_sclk)
+                               ps->performance_levels[i].sclk = max_sclk;
+               }
        }
 
        /* XXX validate the min clocks required for display */
index 4069be89e5852852ff4e884630571908dda6e387..84999242c74746317dfeed4954fee7baec4019e7 100644 (file)
 #define        PACKET3_MPEG_INDEX                              0x3A
 #define        PACKET3_COPY_DW                                 0x3B
 #define        PACKET3_WAIT_REG_MEM                            0x3C
+#define                WAIT_REG_MEM_FUNCTION(x)                ((x) << 0)
+                /* 0 - always
+                * 1 - <
+                * 2 - <=
+                * 3 - ==
+                * 4 - !=
+                * 5 - >=
+                * 6 - >
+                */
+#define                WAIT_REG_MEM_MEM_SPACE(x)               ((x) << 4)
+                /* 0 - reg
+                * 1 - mem
+                */
+#define                WAIT_REG_MEM_ENGINE(x)                  ((x) << 8)
+                /* 0 - me
+                * 1 - pfp
+                */
 #define        PACKET3_MEM_WRITE                               0x3D
 #define        PACKET3_COPY_DATA                               0x40
 #define        PACKET3_CP_DMA                                  0x41
 #define        DMA_PACKET_TRAP                                   0x7
 #define        DMA_PACKET_SRBM_WRITE                             0x9
 #define        DMA_PACKET_CONSTANT_FILL                          0xd
+#define        DMA_PACKET_POLL_REG_MEM                           0xe
 #define        DMA_PACKET_NOP                                    0xf
 
 #define VCE_STATUS                                     0x20004
index 23cc910951f430a279b6b01ae88e5f03d7de3e74..25c7a998fc2cf075fe1ecb6c8fe603f439abab7f 100644 (file)
@@ -74,39 +74,77 @@ static int rcar_du_crtc_get(struct rcar_du_crtc *rcrtc)
        if (ret < 0)
                return ret;
 
+       ret = clk_prepare_enable(rcrtc->extclock);
+       if (ret < 0)
+               goto error_clock;
+
        ret = rcar_du_group_get(rcrtc->group);
        if (ret < 0)
-               clk_disable_unprepare(rcrtc->clock);
+               goto error_group;
+
+       return 0;
 
+error_group:
+       clk_disable_unprepare(rcrtc->extclock);
+error_clock:
+       clk_disable_unprepare(rcrtc->clock);
        return ret;
 }
 
 static void rcar_du_crtc_put(struct rcar_du_crtc *rcrtc)
 {
        rcar_du_group_put(rcrtc->group);
+
+       clk_disable_unprepare(rcrtc->extclock);
        clk_disable_unprepare(rcrtc->clock);
 }
 
 static void rcar_du_crtc_set_display_timing(struct rcar_du_crtc *rcrtc)
 {
        const struct drm_display_mode *mode = &rcrtc->crtc.mode;
+       unsigned long mode_clock = mode->clock * 1000;
        unsigned long clk;
        u32 value;
+       u32 escr;
        u32 div;
 
-       /* Dot clock */
+       /* Compute the clock divisor and select the internal or external dot
+        * clock based on the requested frequency.
+        */
        clk = clk_get_rate(rcrtc->clock);
-       div = DIV_ROUND_CLOSEST(clk, mode->clock * 1000);
+       div = DIV_ROUND_CLOSEST(clk, mode_clock);
        div = clamp(div, 1U, 64U) - 1;
+       escr = div | ESCR_DCLKSEL_CLKS;
+
+       if (rcrtc->extclock) {
+               unsigned long extclk;
+               unsigned long extrate;
+               unsigned long rate;
+               u32 extdiv;
+
+               extclk = clk_get_rate(rcrtc->extclock);
+               extdiv = DIV_ROUND_CLOSEST(extclk, mode_clock);
+               extdiv = clamp(extdiv, 1U, 64U) - 1;
+
+               rate = clk / (div + 1);
+               extrate = extclk / (extdiv + 1);
+
+               if (abs((long)extrate - (long)mode_clock) <
+                   abs((long)rate - (long)mode_clock)) {
+                       dev_dbg(rcrtc->group->dev->dev,
+                               "crtc%u: using external clock\n", rcrtc->index);
+                       escr = extdiv | ESCR_DCLKSEL_DCLKIN;
+               }
+       }
 
        rcar_du_group_write(rcrtc->group, rcrtc->index % 2 ? ESCR2 : ESCR,
-                           ESCR_DCLKSEL_CLKS | div);
+                           escr);
        rcar_du_group_write(rcrtc->group, rcrtc->index % 2 ? OTAR2 : OTAR, 0);
 
        /* Signal polarities */
        value = ((mode->flags & DRM_MODE_FLAG_PVSYNC) ? 0 : DSMR_VSL)
              | ((mode->flags & DRM_MODE_FLAG_PHSYNC) ? 0 : DSMR_HSL)
-             | DSMR_DIPM_DE;
+             | DSMR_DIPM_DE | DSMR_CSPM;
        rcar_du_crtc_write(rcrtc, DSMR, value);
 
        /* Display timings */
@@ -117,12 +155,15 @@ static void rcar_du_crtc_set_display_timing(struct rcar_du_crtc *rcrtc)
                                        mode->hsync_start - 1);
        rcar_du_crtc_write(rcrtc, HCR,  mode->htotal - 1);
 
-       rcar_du_crtc_write(rcrtc, VDSR, mode->vtotal - mode->vsync_end - 2);
-       rcar_du_crtc_write(rcrtc, VDER, mode->vtotal - mode->vsync_end +
-                                       mode->vdisplay - 2);
-       rcar_du_crtc_write(rcrtc, VSPR, mode->vtotal - mode->vsync_end +
-                                       mode->vsync_start - 1);
-       rcar_du_crtc_write(rcrtc, VCR,  mode->vtotal - 1);
+       rcar_du_crtc_write(rcrtc, VDSR, mode->crtc_vtotal -
+                                       mode->crtc_vsync_end - 2);
+       rcar_du_crtc_write(rcrtc, VDER, mode->crtc_vtotal -
+                                       mode->crtc_vsync_end +
+                                       mode->crtc_vdisplay - 2);
+       rcar_du_crtc_write(rcrtc, VSPR, mode->crtc_vtotal -
+                                       mode->crtc_vsync_end +
+                                       mode->crtc_vsync_start - 1);
+       rcar_du_crtc_write(rcrtc, VCR,  mode->crtc_vtotal - 1);
 
        rcar_du_crtc_write(rcrtc, DESR,  mode->htotal - mode->hsync_start);
        rcar_du_crtc_write(rcrtc, DEWR,  mode->hdisplay);
@@ -139,9 +180,10 @@ void rcar_du_crtc_route_output(struct drm_crtc *crtc,
         */
        rcrtc->outputs |= BIT(output);
 
-       /* Store RGB routing to DPAD0 for R8A7790. */
-       if (rcar_du_has(rcdu, RCAR_DU_FEATURE_DEFR8) &&
-           output == RCAR_DU_OUTPUT_DPAD0)
+       /* Store RGB routing to DPAD0, the hardware will be configured when
+        * starting the CRTC.
+        */
+       if (output == RCAR_DU_OUTPUT_DPAD0)
                rcdu->dpad0_source = rcrtc->index;
 }
 
@@ -217,6 +259,7 @@ void rcar_du_crtc_update_planes(struct drm_crtc *crtc)
 static void rcar_du_crtc_start(struct rcar_du_crtc *rcrtc)
 {
        struct drm_crtc *crtc = &rcrtc->crtc;
+       bool interlaced;
        unsigned int i;
 
        if (rcrtc->started)
@@ -252,7 +295,10 @@ static void rcar_du_crtc_start(struct rcar_du_crtc *rcrtc)
         * sync mode (with the HSYNC and VSYNC signals configured as outputs and
         * actively driven).
         */
-       rcar_du_crtc_clr_set(rcrtc, DSYSR, DSYSR_TVM_MASK, DSYSR_TVM_MASTER);
+       interlaced = rcrtc->crtc.mode.flags & DRM_MODE_FLAG_INTERLACE;
+       rcar_du_crtc_clr_set(rcrtc, DSYSR, DSYSR_TVM_MASK | DSYSR_SCM_MASK,
+                            (interlaced ? DSYSR_SCM_INT_VIDEO : 0) |
+                            DSYSR_TVM_MASTER);
 
        rcar_du_group_start_stop(rcrtc->group, true);
 
@@ -308,6 +354,9 @@ static void rcar_du_crtc_dpms(struct drm_crtc *crtc, int mode)
 {
        struct rcar_du_crtc *rcrtc = to_rcar_crtc(crtc);
 
+       if (mode != DRM_MODE_DPMS_ON)
+               mode = DRM_MODE_DPMS_OFF;
+
        if (rcrtc->dpms == mode)
                return;
 
@@ -486,7 +535,7 @@ static irqreturn_t rcar_du_crtc_irq(int irq, void *arg)
        status = rcar_du_crtc_read(rcrtc, DSSR);
        rcar_du_crtc_write(rcrtc, DSRCR, status & DSRCR_MASK);
 
-       if (status & DSSR_VBK) {
+       if (status & DSSR_FRM) {
                drm_handle_vblank(rcrtc->crtc.dev, rcrtc->index);
                rcar_du_crtc_finish_page_flip(rcrtc);
                ret = IRQ_HANDLED;
@@ -542,12 +591,13 @@ int rcar_du_crtc_create(struct rcar_du_group *rgrp, unsigned int index)
        struct rcar_du_crtc *rcrtc = &rcdu->crtcs[index];
        struct drm_crtc *crtc = &rcrtc->crtc;
        unsigned int irqflags;
-       char clk_name[5];
+       struct clk *clk;
+       char clk_name[9];
        char *name;
        int irq;
        int ret;
 
-       /* Get the CRTC clock. */
+       /* Get the CRTC clock and the optional external clock. */
        if (rcar_du_has(rcdu, RCAR_DU_FEATURE_CRTC_IRQ_CLOCK)) {
                sprintf(clk_name, "du.%u", index);
                name = clk_name;
@@ -561,6 +611,15 @@ int rcar_du_crtc_create(struct rcar_du_group *rgrp, unsigned int index)
                return PTR_ERR(rcrtc->clock);
        }
 
+       sprintf(clk_name, "dclkin.%u", index);
+       clk = devm_clk_get(rcdu->dev, clk_name);
+       if (!IS_ERR(clk)) {
+               rcrtc->extclock = clk;
+       } else if (PTR_ERR(rcrtc->clock) == -EPROBE_DEFER) {
+               dev_info(rcdu->dev, "can't get external clock %u\n", index);
+               return -EPROBE_DEFER;
+       }
+
        rcrtc->group = rgrp;
        rcrtc->mmio_offset = mmio_offsets[index];
        rcrtc->index = index;
index 984e6083699fe380a1d6b1e9d9c4c249ee6d4167..d2f89f7d2e5e3e6c6001c63a49ff032ece9aeded 100644 (file)
@@ -26,6 +26,7 @@ struct rcar_du_crtc {
        struct drm_crtc crtc;
 
        struct clk *clock;
+       struct clk *extclock;
        unsigned int mmio_offset;
        unsigned int index;
        bool started;
index 7bfa09cf18d59a3d7a526b77cf897d168b384326..e0d74f821416cdf31ed7e738b8726395276891b6 100644 (file)
@@ -56,7 +56,8 @@ static const struct rcar_du_device_info rcar_du_r8a7779_info = {
 };
 
 static const struct rcar_du_device_info rcar_du_r8a7790_info = {
-       .features = RCAR_DU_FEATURE_CRTC_IRQ_CLOCK | RCAR_DU_FEATURE_DEFR8,
+       .features = RCAR_DU_FEATURE_CRTC_IRQ_CLOCK
+                 | RCAR_DU_FEATURE_EXT_CTRL_REGS,
        .quirks = RCAR_DU_QUIRK_ALIGN_128B | RCAR_DU_QUIRK_LVDS_LANES,
        .num_crtcs = 3,
        .routes = {
@@ -83,7 +84,8 @@ static const struct rcar_du_device_info rcar_du_r8a7790_info = {
 };
 
 static const struct rcar_du_device_info rcar_du_r8a7791_info = {
-       .features = RCAR_DU_FEATURE_CRTC_IRQ_CLOCK | RCAR_DU_FEATURE_DEFR8,
+       .features = RCAR_DU_FEATURE_CRTC_IRQ_CLOCK
+                 | RCAR_DU_FEATURE_EXT_CTRL_REGS,
        .num_crtcs = 2,
        .routes = {
                /* R8A7791 has one RGB output, one LVDS output and one
index 0a724669f02d461351617c5044b4e7e89f7262da..c5b9ea6a7eaab38d370014b643298064ba9a32ab 100644 (file)
@@ -27,7 +27,7 @@ struct rcar_du_device;
 struct rcar_du_lvdsenc;
 
 #define RCAR_DU_FEATURE_CRTC_IRQ_CLOCK (1 << 0)        /* Per-CRTC IRQ and clock */
-#define RCAR_DU_FEATURE_DEFR8          (1 << 1)        /* Has DEFR8 register */
+#define RCAR_DU_FEATURE_EXT_CTRL_REGS  (1 << 1)        /* Has extended control registers */
 
 #define RCAR_DU_QUIRK_ALIGN_128B       (1 << 0)        /* Align pitches to 128 bytes */
 #define RCAR_DU_QUIRK_LVDS_LANES       (1 << 1)        /* LVDS lanes 1 and 3 inverted */
index 34a122a3966419e406cb958ce8a6b194f9fdae1f..279167f783f67857ee3b37cd491419626933399d 100644 (file)
@@ -46,6 +46,9 @@ static void rcar_du_encoder_dpms(struct drm_encoder *encoder, int mode)
 {
        struct rcar_du_encoder *renc = to_rcar_encoder(encoder);
 
+       if (mode != DRM_MODE_DPMS_ON)
+               mode = DRM_MODE_DPMS_OFF;
+
        if (renc->lvds)
                rcar_du_lvdsenc_dpms(renc->lvds, encoder->crtc, mode);
 }
@@ -190,35 +193,42 @@ int rcar_du_encoder_init(struct rcar_du_device *rcdu,
        }
 
        if (type == RCAR_DU_ENCODER_HDMI) {
-               if (renc->lvds) {
-                       dev_err(rcdu->dev,
-                               "Chaining LVDS and HDMI encoders not supported\n");
-                       return -EINVAL;
-               }
-
                ret = rcar_du_hdmienc_init(rcdu, renc, enc_node);
                if (ret < 0)
-                       return ret;
+                       goto done;
        } else {
                ret = drm_encoder_init(rcdu->ddev, encoder, &encoder_funcs,
                                       encoder_type);
                if (ret < 0)
-                       return ret;
+                       goto done;
 
                drm_encoder_helper_add(encoder, &encoder_helper_funcs);
        }
 
        switch (encoder_type) {
        case DRM_MODE_ENCODER_LVDS:
-               return rcar_du_lvds_connector_init(rcdu, renc, con_node);
+               ret = rcar_du_lvds_connector_init(rcdu, renc, con_node);
+               break;
 
        case DRM_MODE_ENCODER_DAC:
-               return rcar_du_vga_connector_init(rcdu, renc);
+               ret = rcar_du_vga_connector_init(rcdu, renc);
+               break;
 
        case DRM_MODE_ENCODER_TMDS:
-               return rcar_du_hdmi_connector_init(rcdu, renc);
+               ret = rcar_du_hdmi_connector_init(rcdu, renc);
+               break;
 
        default:
-               return -EINVAL;
+               ret = -EINVAL;
+               break;
        }
+
+done:
+       if (ret < 0) {
+               if (encoder->name)
+                       encoder->funcs->destroy(encoder);
+               devm_kfree(rcdu->dev, renc);
+       }
+
+       return ret;
 }
index 4e7614b145db550d1364723e76dd27ffd36b404f..1bdc0ee0c2483c936b8fffd31948c42fe74e8455 100644 (file)
@@ -48,9 +48,6 @@ static void rcar_du_group_setup_defr8(struct rcar_du_group *rgrp)
 {
        u32 defr8 = DEFR8_CODE | DEFR8_DEFE8;
 
-       if (!rcar_du_has(rgrp->dev, RCAR_DU_FEATURE_DEFR8))
-               return;
-
        /* The DEFR8 register for the first group also controls RGB output
         * routing to DPAD0
         */
@@ -69,7 +66,20 @@ static void rcar_du_group_setup(struct rcar_du_group *rgrp)
        rcar_du_group_write(rgrp, DEFR4, DEFR4_CODE);
        rcar_du_group_write(rgrp, DEFR5, DEFR5_CODE | DEFR5_DEFE5);
 
-       rcar_du_group_setup_defr8(rgrp);
+       if (rcar_du_has(rgrp->dev, RCAR_DU_FEATURE_EXT_CTRL_REGS)) {
+               rcar_du_group_setup_defr8(rgrp);
+
+               /* Configure input dot clock routing. We currently hardcode the
+                * configuration to routing DOTCLKINn to DUn.
+                */
+               rcar_du_group_write(rgrp, DIDSR, DIDSR_CODE |
+                                   DIDSR_LCDS_DCLKIN(2) |
+                                   DIDSR_LCDS_DCLKIN(1) |
+                                   DIDSR_LCDS_DCLKIN(0) |
+                                   DIDSR_PDCS_CLK(2, 0) |
+                                   DIDSR_PDCS_CLK(1, 0) |
+                                   DIDSR_PDCS_CLK(0, 0));
+       }
 
        /* Use DS1PR and DS2PR to configure planes priorities and connects the
         * superposition 0 to DU0 pins. DU1 pins will be configured dynamically.
@@ -149,6 +159,9 @@ static int rcar_du_set_dpad0_routing(struct rcar_du_device *rcdu)
 {
        int ret;
 
+       if (!rcar_du_has(rcdu, RCAR_DU_FEATURE_EXT_CTRL_REGS))
+               return 0;
+
        /* RGB output routing to DPAD0 is configured in the DEFR8 register of
         * the first group. As this function can be called with the DU0 and DU1
         * CRTCs disabled, we need to enable the first group clock before
index 4d7d4dd46d2603c6cc3d4f06958edac30d34a2a4..ca94b029ac80ca664c0a53631328eaf90e971754 100644 (file)
@@ -95,6 +95,8 @@ int rcar_du_hdmi_connector_init(struct rcar_du_device *rcdu,
        connector = &rcon->connector;
        connector->display_info.width_mm = 0;
        connector->display_info.height_mm = 0;
+       connector->interlace_allowed = true;
+       connector->polled = DRM_CONNECTOR_POLL_HPD;
 
        ret = drm_connector_init(rcdu->ddev, connector, &connector_funcs,
                                 DRM_MODE_CONNECTOR_HDMIA);
index 359bc999a9c8444ff41d43ee2c8af3cc36308509..221f0a17fd6a62bbde33950e8529ce371aff9323 100644 (file)
@@ -21,6 +21,7 @@
 #include "rcar_du_drv.h"
 #include "rcar_du_encoder.h"
 #include "rcar_du_hdmienc.h"
+#include "rcar_du_lvdsenc.h"
 
 struct rcar_du_hdmienc {
        struct rcar_du_encoder *renc;
@@ -36,12 +37,21 @@ static void rcar_du_hdmienc_dpms(struct drm_encoder *encoder, int mode)
        struct rcar_du_hdmienc *hdmienc = to_rcar_hdmienc(encoder);
        struct drm_encoder_slave_funcs *sfuncs = to_slave_funcs(encoder);
 
+       if (mode != DRM_MODE_DPMS_ON)
+               mode = DRM_MODE_DPMS_OFF;
+
        if (hdmienc->dpms == mode)
                return;
 
+       if (mode == DRM_MODE_DPMS_ON && hdmienc->renc->lvds)
+               rcar_du_lvdsenc_dpms(hdmienc->renc->lvds, encoder->crtc, mode);
+
        if (sfuncs->dpms)
                sfuncs->dpms(encoder, mode);
 
+       if (mode != DRM_MODE_DPMS_ON && hdmienc->renc->lvds)
+               rcar_du_lvdsenc_dpms(hdmienc->renc->lvds, encoder->crtc, mode);
+
        hdmienc->dpms = mode;
 }
 
@@ -49,8 +59,16 @@ static bool rcar_du_hdmienc_mode_fixup(struct drm_encoder *encoder,
                                       const struct drm_display_mode *mode,
                                       struct drm_display_mode *adjusted_mode)
 {
+       struct rcar_du_hdmienc *hdmienc = to_rcar_hdmienc(encoder);
        struct drm_encoder_slave_funcs *sfuncs = to_slave_funcs(encoder);
 
+       /* The internal LVDS encoder has a clock frequency operating range of
+        * 30MHz to 150MHz. Clamp the clock accordingly.
+        */
+       if (hdmienc->renc->lvds)
+               adjusted_mode->clock = clamp(adjusted_mode->clock,
+                                            30000, 150000);
+
        if (sfuncs->mode_fixup == NULL)
                return true;
 
index 0c5ee616b5a3aabd12234ee7f208dc277a99d73f..cc9136e8ee9cd2f73c65850215fad60a584358ee 100644 (file)
@@ -346,8 +346,14 @@ static int rcar_du_encoders_init(struct rcar_du_device *rcdu)
                /* Process the output pipeline. */
                ret = rcar_du_encoders_init_one(rcdu, output, &ep);
                if (ret < 0) {
-                       of_node_put(ep_node);
-                       return ret;
+                       if (ret == -EPROBE_DEFER) {
+                               of_node_put(ep_node);
+                               return ret;
+                       }
+
+                       dev_info(rcdu->dev,
+                                "encoder initialization failed, skipping\n");
+                       continue;
                }
 
                num_encoders += ret;
@@ -413,6 +419,11 @@ int rcar_du_modeset_init(struct rcar_du_device *rcdu)
        if (ret < 0)
                return ret;
 
+       if (ret == 0) {
+               dev_err(rcdu->dev, "error: no encoder could be initialized\n");
+               return -EINVAL;
+       }
+
        num_encoders = ret;
 
        /* Set the possible CRTCs and possible clones. There's always at least
index 72a7cb47bd9f8a2e18d846185e9b7a0ee77dcefb..50f2f2b20d39fce3d8465611196a6ee6f36e803d 100644 (file)
@@ -104,14 +104,22 @@ void rcar_du_plane_update_base(struct rcar_du_plane *plane)
 {
        struct rcar_du_group *rgrp = plane->group;
        unsigned int index = plane->hwindex;
+       bool interlaced;
        u32 mwr;
 
-       /* Memory pitch (expressed in pixels) */
+       interlaced = plane->crtc->mode.flags & DRM_MODE_FLAG_INTERLACE;
+
+       /* Memory pitch (expressed in pixels). Must be doubled for interlaced
+        * operation with 32bpp formats.
+        */
        if (plane->format->planes == 2)
                mwr = plane->pitch;
        else
                mwr = plane->pitch * 8 / plane->format->bpp;
 
+       if (interlaced && plane->format->bpp == 32)
+               mwr *= 2;
+
        rcar_du_plane_write(rgrp, index, PnMWR, mwr);
 
        /* The Y position is expressed in raster line units and must be doubled
@@ -119,17 +127,23 @@ void rcar_du_plane_update_base(struct rcar_du_plane *plane)
         * doubling the Y position is found in the R8A7779 datasheet, but the
         * rule seems to apply there as well.
         *
+        * Despite not being documented, doubling seem not to be needed when
+        * operating in interlaced mode.
+        *
         * Similarly, for the second plane, NV12 and NV21 formats seem to
-        * require a halved Y position value.
+        * require a halved Y position value, in both progressive and interlaced
+        * modes.
         */
        rcar_du_plane_write(rgrp, index, PnSPXR, plane->src_x);
        rcar_du_plane_write(rgrp, index, PnSPYR, plane->src_y *
-                           (plane->format->bpp == 32 ? 2 : 1));
+                           (!interlaced && plane->format->bpp == 32 ? 2 : 1));
        rcar_du_plane_write(rgrp, index, PnDSA0R, plane->dma[0]);
 
        if (plane->format->planes == 2) {
                index = (index + 1) % 8;
 
+               rcar_du_plane_write(rgrp, index, PnMWR, plane->pitch);
+
                rcar_du_plane_write(rgrp, index, PnSPXR, plane->src_x);
                rcar_du_plane_write(rgrp, index, PnSPYR, plane->src_y *
                                    (plane->format->bpp == 16 ? 2 : 1) / 2);
index 73f7347f740bd1f94707990a8d9115fcf57fc518..70fcbc471ebdc81e45542ca9262376e6caf3ba5b 100644 (file)
@@ -34,6 +34,7 @@
 #define DSYSR_SCM_INT_NONE     (0 << 4)
 #define DSYSR_SCM_INT_SYNC     (2 << 4)
 #define DSYSR_SCM_INT_VIDEO    (3 << 4)
+#define DSYSR_SCM_MASK         (3 << 4)
 
 #define DSMR                   0x00004
 #define DSMR_VSPM              (1 << 28)
 #define DIDSR_LCDS_LVDS0(n)    (2 << (8 + (n) * 2))
 #define DIDSR_LCDS_LVDS1(n)    (3 << (8 + (n) * 2))
 #define DIDSR_LCDS_MASK(n)     (3 << (8 + (n) * 2))
-#define DIDSR_PCDS_CLK(n, clk) (clk << ((n) * 2))
-#define DIDSR_PCDS_MASK(n)     (3 << ((n) * 2))
+#define DIDSR_PDCS_CLK(n, clk) (clk << ((n) * 2))
+#define DIDSR_PDCS_MASK(n)     (3 << ((n) * 2))
 
 /* -----------------------------------------------------------------------------
  * Display Timing Generation Registers
index 752747a5e920e847ac689aa78555da1c12716b9e..9d4879921cc7a92e574ba15f47c95370e9a469b9 100644 (file)
@@ -64,6 +64,7 @@ int rcar_du_vga_connector_init(struct rcar_du_device *rcdu,
        connector = &rcon->connector;
        connector->display_info.width_mm = 0;
        connector->display_info.height_mm = 0;
+       connector->interlace_allowed = true;
 
        ret = drm_connector_init(rcdu->ddev, connector, &connector_funcs,
                                 DRM_MODE_CONNECTOR_VGA);
index ca9f085efa922982bf0f90b70010988576524583..cb21e382124444372a806b0fc44e00061ae66079 100644 (file)
@@ -7,7 +7,6 @@ config DRM_ROCKCHIP
        select FB_CFB_FILLRECT
        select FB_CFB_COPYAREA
        select FB_CFB_IMAGEBLIT
-       select VT_HW_CONSOLE_BINDING if FRAMEBUFFER_CONSOLE
        select VIDEOMODE_HELPERS
        help
          Choose this option if you have a Rockchip soc chipset.
@@ -15,3 +14,13 @@ config DRM_ROCKCHIP
          management to userspace. This driver does not provide
          2D or 3D acceleration; acceleration is performed by other
          IP found on the SoC.
+
+config ROCKCHIP_DW_HDMI
+        tristate "Rockchip specific extensions for Synopsys DW HDMI"
+        depends on DRM_ROCKCHIP
+        select DRM_DW_HDMI
+        help
+         This selects support for Rockchip SoC specific extensions
+         for the Synopsys DesignWare HDMI driver. If you want to
+         enable HDMI on RK3288 based SoC, you should selet this
+         option.
index 2cb0672f57edafd15ce7c972daafb3d3bc97c319..f3d8a19c641ffd4a6925a1f86b485ff4055d865a 100644 (file)
@@ -5,4 +5,6 @@
 rockchipdrm-y := rockchip_drm_drv.o rockchip_drm_fb.o rockchip_drm_fbdev.o \
                rockchip_drm_gem.o
 
+obj-$(CONFIG_ROCKCHIP_DW_HDMI) += dw_hdmi-rockchip.o
+
 obj-$(CONFIG_DRM_ROCKCHIP) += rockchipdrm.o rockchip_drm_vop.o
diff --git a/drivers/gpu/drm/rockchip/dw_hdmi-rockchip.c b/drivers/gpu/drm/rockchip/dw_hdmi-rockchip.c
new file mode 100644 (file)
index 0000000..d236faa
--- /dev/null
@@ -0,0 +1,341 @@
+/*
+ * Copyright (c) 2014, Fuzhou Rockchip Electronics Co., Ltd
+ *
+ * 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.
+ */
+
+#include <linux/module.h>
+#include <linux/platform_device.h>
+#include <linux/mfd/syscon.h>
+#include <linux/regmap.h>
+#include <drm/drm_of.h>
+#include <drm/drmP.h>
+#include <drm/drm_crtc_helper.h>
+#include <drm/drm_edid.h>
+#include <drm/drm_encoder_slave.h>
+#include <drm/bridge/dw_hdmi.h>
+
+#include "rockchip_drm_drv.h"
+#include "rockchip_drm_vop.h"
+
+#define GRF_SOC_CON6                    0x025c
+#define HDMI_SEL_VOP_LIT                (1 << 4)
+
+struct rockchip_hdmi {
+       struct device *dev;
+       struct regmap *regmap;
+       struct drm_encoder encoder;
+};
+
+#define to_rockchip_hdmi(x)    container_of(x, struct rockchip_hdmi, x)
+
+static const struct dw_hdmi_mpll_config rockchip_mpll_cfg[] = {
+       {
+               27000000, {
+                       { 0x00b3, 0x0000},
+                       { 0x2153, 0x0000},
+                       { 0x40f3, 0x0000}
+               },
+       }, {
+               36000000, {
+                       { 0x00b3, 0x0000},
+                       { 0x2153, 0x0000},
+                       { 0x40f3, 0x0000}
+               },
+       }, {
+               40000000, {
+                       { 0x00b3, 0x0000},
+                       { 0x2153, 0x0000},
+                       { 0x40f3, 0x0000}
+               },
+       }, {
+               54000000, {
+                       { 0x0072, 0x0001},
+                       { 0x2142, 0x0001},
+                       { 0x40a2, 0x0001},
+               },
+       }, {
+               65000000, {
+                       { 0x0072, 0x0001},
+                       { 0x2142, 0x0001},
+                       { 0x40a2, 0x0001},
+               },
+       }, {
+               66000000, {
+                       { 0x013e, 0x0003},
+                       { 0x217e, 0x0002},
+                       { 0x4061, 0x0002}
+               },
+       }, {
+               74250000, {
+                       { 0x0072, 0x0001},
+                       { 0x2145, 0x0002},
+                       { 0x4061, 0x0002}
+               },
+       }, {
+               83500000, {
+                       { 0x0072, 0x0001},
+               },
+       }, {
+               108000000, {
+                       { 0x0051, 0x0002},
+                       { 0x2145, 0x0002},
+                       { 0x4061, 0x0002}
+               },
+       }, {
+               106500000, {
+                       { 0x0051, 0x0002},
+                       { 0x2145, 0x0002},
+                       { 0x4061, 0x0002}
+               },
+       }, {
+               146250000, {
+                       { 0x0051, 0x0002},
+                       { 0x2145, 0x0002},
+                       { 0x4061, 0x0002}
+               },
+       }, {
+               148500000, {
+                       { 0x0051, 0x0003},
+                       { 0x214c, 0x0003},
+                       { 0x4064, 0x0003}
+               },
+       }, {
+               ~0UL, {
+                       { 0x00a0, 0x000a },
+                       { 0x2001, 0x000f },
+                       { 0x4002, 0x000f },
+               },
+       }
+};
+
+static const struct dw_hdmi_curr_ctrl rockchip_cur_ctr[] = {
+       /*      pixelclk    bpp8    bpp10   bpp12 */
+       {
+               40000000,  { 0x0018, 0x0018, 0x0018 },
+       }, {
+               65000000,  { 0x0028, 0x0028, 0x0028 },
+       }, {
+               66000000,  { 0x0038, 0x0038, 0x0038 },
+       }, {
+               74250000,  { 0x0028, 0x0038, 0x0038 },
+       }, {
+               83500000,  { 0x0028, 0x0038, 0x0038 },
+       }, {
+               146250000, { 0x0038, 0x0038, 0x0038 },
+       }, {
+               148500000, { 0x0000, 0x0038, 0x0038 },
+       }, {
+               ~0UL,      { 0x0000, 0x0000, 0x0000},
+       }
+};
+
+static const struct dw_hdmi_sym_term rockchip_sym_term[] = {
+       /*pixelclk   symbol   term*/
+       { 74250000,  0x8009, 0x0004 },
+       { 148500000, 0x8029, 0x0004 },
+       { 297000000, 0x8039, 0x0005 },
+       { ~0UL,      0x0000, 0x0000 }
+};
+
+static int rockchip_hdmi_parse_dt(struct rockchip_hdmi *hdmi)
+{
+       struct device_node *np = hdmi->dev->of_node;
+
+       hdmi->regmap = syscon_regmap_lookup_by_phandle(np, "rockchip,grf");
+       if (IS_ERR(hdmi->regmap)) {
+               dev_err(hdmi->dev, "Unable to get rockchip,grf\n");
+               return PTR_ERR(hdmi->regmap);
+       }
+
+       return 0;
+}
+
+static enum drm_mode_status
+dw_hdmi_rockchip_mode_valid(struct drm_connector *connector,
+                           struct drm_display_mode *mode)
+{
+       const struct dw_hdmi_mpll_config *mpll_cfg = rockchip_mpll_cfg;
+       int pclk = mode->clock * 1000;
+       bool valid = false;
+       int i;
+
+       for (i = 0; mpll_cfg[i].mpixelclock != (~0UL); i++) {
+               if (pclk == mpll_cfg[i].mpixelclock) {
+                       valid = true;
+                       break;
+               }
+       }
+
+       return (valid) ? MODE_OK : MODE_BAD;
+}
+
+static struct drm_encoder_funcs dw_hdmi_rockchip_encoder_funcs = {
+       .destroy = drm_encoder_cleanup,
+};
+
+static void dw_hdmi_rockchip_encoder_disable(struct drm_encoder *encoder)
+{
+}
+
+static bool
+dw_hdmi_rockchip_encoder_mode_fixup(struct drm_encoder *encoder,
+                                   const struct drm_display_mode *mode,
+                                   struct drm_display_mode *adj_mode)
+{
+       return true;
+}
+
+static void dw_hdmi_rockchip_encoder_mode_set(struct drm_encoder *encoder,
+                                             struct drm_display_mode *mode,
+                                             struct drm_display_mode *adj_mode)
+{
+}
+
+static void dw_hdmi_rockchip_encoder_commit(struct drm_encoder *encoder)
+{
+       struct rockchip_hdmi *hdmi = to_rockchip_hdmi(encoder);
+       u32 val;
+       int mux;
+
+       mux = rockchip_drm_encoder_get_mux_id(hdmi->dev->of_node, encoder);
+       if (mux)
+               val = HDMI_SEL_VOP_LIT | (HDMI_SEL_VOP_LIT << 16);
+       else
+               val = HDMI_SEL_VOP_LIT << 16;
+
+       regmap_write(hdmi->regmap, GRF_SOC_CON6, val);
+       dev_dbg(hdmi->dev, "vop %s output to hdmi\n",
+               (mux) ? "LIT" : "BIG");
+}
+
+static void dw_hdmi_rockchip_encoder_prepare(struct drm_encoder *encoder)
+{
+       rockchip_drm_crtc_mode_config(encoder->crtc, DRM_MODE_CONNECTOR_HDMIA,
+                                     ROCKCHIP_OUT_MODE_AAAA);
+}
+
+static struct drm_encoder_helper_funcs dw_hdmi_rockchip_encoder_helper_funcs = {
+       .mode_fixup = dw_hdmi_rockchip_encoder_mode_fixup,
+       .mode_set   = dw_hdmi_rockchip_encoder_mode_set,
+       .prepare    = dw_hdmi_rockchip_encoder_prepare,
+       .commit     = dw_hdmi_rockchip_encoder_commit,
+       .disable    = dw_hdmi_rockchip_encoder_disable,
+};
+
+static const struct dw_hdmi_plat_data rockchip_hdmi_drv_data = {
+       .mode_valid = dw_hdmi_rockchip_mode_valid,
+       .mpll_cfg   = rockchip_mpll_cfg,
+       .cur_ctr    = rockchip_cur_ctr,
+       .sym_term   = rockchip_sym_term,
+       .dev_type   = RK3288_HDMI,
+};
+
+static const struct of_device_id dw_hdmi_rockchip_dt_ids[] = {
+       { .compatible = "rockchip,rk3288-dw-hdmi",
+         .data = &rockchip_hdmi_drv_data
+       },
+       {},
+};
+MODULE_DEVICE_TABLE(of, dw_hdmi_rockchip_dt_ids);
+
+static int dw_hdmi_rockchip_bind(struct device *dev, struct device *master,
+                                void *data)
+{
+       struct platform_device *pdev = to_platform_device(dev);
+       const struct dw_hdmi_plat_data *plat_data;
+       const struct of_device_id *match;
+       struct drm_device *drm = data;
+       struct drm_encoder *encoder;
+       struct rockchip_hdmi *hdmi;
+       struct resource *iores;
+       int irq;
+       int ret;
+
+       if (!pdev->dev.of_node)
+               return -ENODEV;
+
+       hdmi = devm_kzalloc(&pdev->dev, sizeof(*hdmi), GFP_KERNEL);
+       if (!hdmi)
+               return -ENOMEM;
+
+       match = of_match_node(dw_hdmi_rockchip_dt_ids, pdev->dev.of_node);
+       plat_data = match->data;
+       hdmi->dev = &pdev->dev;
+       encoder = &hdmi->encoder;
+
+       irq = platform_get_irq(pdev, 0);
+       if (irq < 0)
+               return irq;
+
+       iores = platform_get_resource(pdev, IORESOURCE_MEM, 0);
+       if (!iores)
+               return -ENXIO;
+
+       platform_set_drvdata(pdev, hdmi);
+
+       encoder->possible_crtcs = drm_of_find_possible_crtcs(drm, dev->of_node);
+       /*
+        * If we failed to find the CRTC(s) which this encoder is
+        * supposed to be connected to, it's because the CRTC has
+        * not been registered yet.  Defer probing, and hope that
+        * the required CRTC is added later.
+        */
+       if (encoder->possible_crtcs == 0)
+               return -EPROBE_DEFER;
+
+       ret = rockchip_hdmi_parse_dt(hdmi);
+       if (ret) {
+               dev_err(hdmi->dev, "Unable to parse OF data\n");
+               return ret;
+       }
+
+       drm_encoder_helper_add(encoder, &dw_hdmi_rockchip_encoder_helper_funcs);
+       drm_encoder_init(drm, encoder, &dw_hdmi_rockchip_encoder_funcs,
+                        DRM_MODE_ENCODER_TMDS);
+
+       return dw_hdmi_bind(dev, master, data, encoder, iores, irq, plat_data);
+}
+
+static void dw_hdmi_rockchip_unbind(struct device *dev, struct device *master,
+                                   void *data)
+{
+       return dw_hdmi_unbind(dev, master, data);
+}
+
+static const struct component_ops dw_hdmi_rockchip_ops = {
+       .bind   = dw_hdmi_rockchip_bind,
+       .unbind = dw_hdmi_rockchip_unbind,
+};
+
+static int dw_hdmi_rockchip_probe(struct platform_device *pdev)
+{
+       return component_add(&pdev->dev, &dw_hdmi_rockchip_ops);
+}
+
+static int dw_hdmi_rockchip_remove(struct platform_device *pdev)
+{
+       component_del(&pdev->dev, &dw_hdmi_rockchip_ops);
+
+       return 0;
+}
+
+static struct platform_driver dw_hdmi_rockchip_pltfm_driver = {
+       .probe  = dw_hdmi_rockchip_probe,
+       .remove = dw_hdmi_rockchip_remove,
+       .driver = {
+               .name = "dwhdmi-rockchip",
+               .of_match_table = dw_hdmi_rockchip_dt_ids,
+       },
+};
+
+module_platform_driver(dw_hdmi_rockchip_pltfm_driver);
+
+MODULE_AUTHOR("Andy Yan <andy.yan@rock-chips.com>");
+MODULE_AUTHOR("Yakir Yang <ykk@rock-chips.com>");
+MODULE_DESCRIPTION("Rockchip Specific DW-HDMI Driver Extension");
+MODULE_LICENSE("GPL");
+MODULE_ALIAS("platform:dwhdmi-rockchip");
index a798c7c71f9166f19d93df76f77dd15f08fb4f40..21a481b224ebab6ef896bbbf5e2a9036c5cfb0ed 100644 (file)
@@ -390,6 +390,7 @@ int rockchip_drm_encoder_get_mux_id(struct device_node *node,
 
        return -EINVAL;
 }
+EXPORT_SYMBOL_GPL(rockchip_drm_encoder_get_mux_id);
 
 static int compare_of(struct device *dev, void *data)
 {
index e7ca25b3fb38616dd307b6c441d29c6c8c3ccd2e..9a5c571b95fceb97dae7bfadf1b9782ede0f686e 100644 (file)
@@ -735,6 +735,7 @@ int rockchip_drm_crtc_mode_config(struct drm_crtc *crtc,
 
        return 0;
 }
+EXPORT_SYMBOL_GPL(rockchip_drm_crtc_mode_config);
 
 static int vop_crtc_enable_vblank(struct drm_crtc *crtc)
 {
index 6ba9d27c1b90b81060754ee9893b539851044118..f0f1e4ee2d922060d579e40ed2f664576f94a1d5 100644 (file)
@@ -12,6 +12,9 @@ stihdmi-y := sti_hdmi.o \
        sti_hdmi_tx3g0c55phy.o \
        sti_hdmi_tx3g4c28phy.o \
 
+stidvo-y := sti_dvo.o \
+       sti_awg_utils.o
+
 obj-$(CONFIG_DRM_STI) = \
        sti_vtg.o \
        sti_vtac.o \
@@ -20,4 +23,5 @@ obj-$(CONFIG_DRM_STI) = \
        sti_tvout.o \
        sticompositor.o \
        sti_hqvdp.o \
+       stidvo.o \
        sti_drm_drv.o
diff --git a/drivers/gpu/drm/sti/sti_awg_utils.c b/drivers/gpu/drm/sti/sti_awg_utils.c
new file mode 100644 (file)
index 0000000..9fde3ee
--- /dev/null
@@ -0,0 +1,184 @@
+/*
+ * Copyright (C) STMicroelectronics SA 2014
+ * Author: Vincent Abriou <vincent.abriou@st.com> for STMicroelectronics.
+ * License terms:  GNU General Public License (GPL), version 2
+ */
+
+#include "sti_awg_utils.h"
+
+#define AWG_OPCODE_OFFSET 10
+
+enum opcode {
+       SET,
+       RPTSET,
+       RPLSET,
+       SKIP,
+       STOP,
+       REPEAT,
+       REPLAY,
+       JUMP,
+       HOLD,
+};
+
+static int awg_generate_instr(enum opcode opcode,
+                             long int arg,
+                             long int mux_sel,
+                             long int data_en,
+                             struct awg_code_generation_params *fwparams)
+{
+       u32 instruction = 0;
+       u32 mux = (mux_sel << 8) & 0x1ff;
+       u32 data_enable = (data_en << 9) & 0x2ff;
+       long int arg_tmp = arg;
+
+       /* skip, repeat and replay arg should not exceed 1023.
+        * If user wants to exceed this value, the instruction should be
+        * duplicate and arg should be adjust for each duplicated instruction.
+        */
+
+       while (arg_tmp > 0) {
+               arg = arg_tmp;
+               if (fwparams->instruction_offset >= AWG_MAX_INST) {
+                       DRM_ERROR("too many number of instructions\n");
+                       return -EINVAL;
+               }
+
+               switch (opcode) {
+               case SKIP:
+                       /* leave 'arg' + 1 pixel elapsing without changing
+                        * output bus */
+                       arg--; /* pixel adjustment */
+                       arg_tmp--;
+
+                       if (arg < 0) {
+                               /* SKIP instruction not needed */
+                               return 0;
+                       }
+
+                       if (arg == 0) {
+                               /* SKIP 0 not permitted but we want to skip 1
+                                * pixel. So we transform SKIP into SET
+                                * instruction */
+                               opcode = SET;
+                               arg = (arg << 24) >> 24;
+                               arg &= (0x0ff);
+                               break;
+                       }
+
+                       mux = 0;
+                       data_enable = 0;
+                       arg = (arg << 22) >> 22;
+                       arg &= (0x3ff);
+                       break;
+               case REPEAT:
+               case REPLAY:
+                       if (arg == 0) {
+                               /* REPEAT or REPLAY instruction not needed */
+                               return 0;
+                       }
+
+                       mux = 0;
+                       data_enable = 0;
+                       arg = (arg << 22) >> 22;
+                       arg &= (0x3ff);
+                       break;
+               case JUMP:
+                       mux = 0;
+                       data_enable = 0;
+                       arg |= 0x40; /* for jump instruction 7th bit is 1 */
+                       arg = (arg << 22) >> 22;
+                       arg &= 0x3ff;
+                       break;
+               case STOP:
+                       arg = 0;
+                       break;
+               case SET:
+               case RPTSET:
+               case RPLSET:
+               case HOLD:
+                       arg = (arg << 24) >> 24;
+                       arg &= (0x0ff);
+                       break;
+               default:
+                       DRM_ERROR("instruction %d does not exist\n", opcode);
+                       return -EINVAL;
+               }
+
+               arg_tmp = arg_tmp - arg;
+
+               arg = ((arg + mux) + data_enable);
+
+               instruction = ((opcode) << AWG_OPCODE_OFFSET) | arg;
+               fwparams->ram_code[fwparams->instruction_offset] =
+                       instruction & (0x3fff);
+               fwparams->instruction_offset++;
+       }
+       return 0;
+}
+
+int sti_awg_generate_code_data_enable_mode(
+               struct awg_code_generation_params *fwparams,
+               struct awg_timing *timing)
+{
+       long int val;
+       long int data_en;
+       int ret = 0;
+
+       if (timing->trailing_lines > 0) {
+               /* skip trailing lines */
+               val = timing->blanking_level;
+               data_en = 0;
+               ret |= awg_generate_instr(RPLSET, val, 0, data_en, fwparams);
+
+               val = timing->trailing_lines - 1;
+               data_en = 0;
+               ret |= awg_generate_instr(REPLAY, val, 0, data_en, fwparams);
+       }
+
+       if (timing->trailing_pixels > 0) {
+               /* skip trailing pixel */
+               val = timing->blanking_level;
+               data_en = 0;
+               ret |= awg_generate_instr(RPLSET, val, 0, data_en, fwparams);
+
+               val = timing->trailing_pixels - 1;
+               data_en = 0;
+               ret |= awg_generate_instr(SKIP, val, 0, data_en, fwparams);
+       }
+
+       /* set DE signal high */
+       val = timing->blanking_level;
+       data_en = 1;
+       ret |= awg_generate_instr((timing->trailing_pixels > 0) ? SET : RPLSET,
+                       val, 0, data_en, fwparams);
+
+       if (timing->blanking_pixels > 0) {
+               /* skip the number of active pixel */
+               val = timing->active_pixels - 1;
+               data_en = 1;
+               ret |= awg_generate_instr(SKIP, val, 0, data_en, fwparams);
+
+               /* set DE signal low */
+               val = timing->blanking_level;
+               data_en = 0;
+               ret |= awg_generate_instr(SET, val, 0, data_en, fwparams);
+       }
+
+       /* replay the sequence as many active lines defined */
+       val = timing->active_lines - 1;
+       data_en = 0;
+       ret |= awg_generate_instr(REPLAY, val, 0, data_en, fwparams);
+
+       if (timing->blanking_lines > 0) {
+               /* skip blanking lines */
+               val = timing->blanking_level;
+               data_en = 0;
+               ret |= awg_generate_instr(RPLSET, val, 0, data_en, fwparams);
+
+               val = timing->blanking_lines - 1;
+               data_en = 0;
+               ret |= awg_generate_instr(REPLAY, val, 0, data_en, fwparams);
+       }
+
+       return ret;
+}
diff --git a/drivers/gpu/drm/sti/sti_awg_utils.h b/drivers/gpu/drm/sti/sti_awg_utils.h
new file mode 100644 (file)
index 0000000..45d599b
--- /dev/null
@@ -0,0 +1,34 @@
+/*
+ * Copyright (C) STMicroelectronics SA 2014
+ * Author: Vincent Abriou <vincent.abriou@st.com> for STMicroelectronics.
+ * License terms:  GNU General Public License (GPL), version 2
+ */
+
+#ifndef _STI_AWG_UTILS_H_
+#define _STI_AWG_UTILS_H_
+
+#include <drm/drmP.h>
+
+#define AWG_MAX_INST 64
+
+struct awg_code_generation_params {
+       u32 *ram_code;
+       u8 instruction_offset;
+};
+
+struct awg_timing {
+       u32 total_lines;
+       u32 active_lines;
+       u32 blanking_lines;
+       u32 trailing_lines;
+       u32 total_pixels;
+       u32 active_pixels;
+       u32 blanking_pixels;
+       u32 trailing_pixels;
+       u32 blanking_level;
+};
+
+int sti_awg_generate_code_data_enable_mode(
+               struct awg_code_generation_params *fw_gen_params,
+               struct awg_timing *timing);
+#endif
index 4c651c200f205693f9e166963803992008255ea5..e6f6ef7c4866ad94eb7bd503eabc9aee7e2b8181 100644 (file)
@@ -190,11 +190,6 @@ out:
        return ret;
 }
 
-static void sti_drm_crtc_load_lut(struct drm_crtc *crtc)
-{
-       /* do nothing */
-}
-
 static void sti_drm_crtc_disable(struct drm_crtc *crtc)
 {
        struct sti_mixer *mixer = to_sti_mixer(crtc);
@@ -249,7 +244,6 @@ static struct drm_crtc_helper_funcs sti_crtc_helper_funcs = {
        .mode_fixup = sti_drm_crtc_mode_fixup,
        .mode_set = sti_drm_crtc_mode_set,
        .mode_set_base = sti_drm_crtc_mode_set_base,
-       .load_lut = sti_drm_crtc_load_lut,
        .disable = sti_drm_crtc_disable,
 };
 
diff --git a/drivers/gpu/drm/sti/sti_dvo.c b/drivers/gpu/drm/sti/sti_dvo.c
new file mode 100644 (file)
index 0000000..651afad
--- /dev/null
@@ -0,0 +1,551 @@
+/*
+ * Copyright (C) STMicroelectronics SA 2014
+ * Author: Vincent Abriou <vincent.abriou@st.com> for STMicroelectronics.
+ * License terms:  GNU General Public License (GPL), version 2
+ */
+
+#include <linux/clk.h>
+#include <linux/component.h>
+#include <linux/module.h>
+#include <linux/of_gpio.h>
+#include <linux/platform_device.h>
+
+#include <drm/drmP.h>
+#include <drm/drm_crtc_helper.h>
+#include <drm/drm_panel.h>
+
+#include "sti_awg_utils.h"
+#include "sti_mixer.h"
+
+/* DVO registers */
+#define DVO_AWG_DIGSYNC_CTRL      0x0000
+#define DVO_DOF_CFG               0x0004
+#define DVO_LUT_PROG_LOW          0x0008
+#define DVO_LUT_PROG_MID          0x000C
+#define DVO_LUT_PROG_HIGH         0x0010
+#define DVO_DIGSYNC_INSTR_I       0x0100
+
+#define DVO_AWG_CTRL_EN           BIT(0)
+#define DVO_AWG_FRAME_BASED_SYNC  BIT(2)
+
+#define DVO_DOF_EN_LOWBYTE        BIT(0)
+#define DVO_DOF_EN_MIDBYTE        BIT(1)
+#define DVO_DOF_EN_HIGHBYTE       BIT(2)
+#define DVO_DOF_EN                BIT(6)
+#define DVO_DOF_MOD_COUNT_SHIFT   8
+
+#define DVO_LUT_ZERO              0
+#define DVO_LUT_Y_G               1
+#define DVO_LUT_Y_G_DEL           2
+#define DVO_LUT_CB_B              3
+#define DVO_LUT_CB_B_DEL          4
+#define DVO_LUT_CR_R              5
+#define DVO_LUT_CR_R_DEL          6
+#define DVO_LUT_HOLD              7
+
+struct dvo_config {
+       u32 flags;
+       u32 lowbyte;
+       u32 midbyte;
+       u32 highbyte;
+       int (*awg_fwgen_fct)(
+                       struct awg_code_generation_params *fw_gen_params,
+                       struct awg_timing *timing);
+};
+
+static struct dvo_config rgb_24bit_de_cfg = {
+       .flags         = (0L << DVO_DOF_MOD_COUNT_SHIFT),
+       .lowbyte       = DVO_LUT_CR_R,
+       .midbyte       = DVO_LUT_Y_G,
+       .highbyte      = DVO_LUT_CB_B,
+       .awg_fwgen_fct = sti_awg_generate_code_data_enable_mode,
+};
+
+/**
+ * STI digital video output structure
+ *
+ * @dev: driver device
+ * @drm_dev: pointer to drm device
+ * @mode: current display mode selected
+ * @regs: dvo registers
+ * @clk_pix: pixel clock for dvo
+ * @clk: clock for dvo
+ * @clk_main_parent: dvo parent clock if main path used
+ * @clk_aux_parent: dvo parent clock if aux path used
+ * @panel_node: panel node reference from device tree
+ * @panel: reference to the panel connected to the dvo
+ * @enabled: true if dvo is enabled else false
+ * @encoder: drm_encoder it is bound
+ */
+struct sti_dvo {
+       struct device dev;
+       struct drm_device *drm_dev;
+       struct drm_display_mode mode;
+       void __iomem *regs;
+       struct clk *clk_pix;
+       struct clk *clk;
+       struct clk *clk_main_parent;
+       struct clk *clk_aux_parent;
+       struct device_node *panel_node;
+       struct drm_panel *panel;
+       struct dvo_config *config;
+       bool enabled;
+       struct drm_encoder *encoder;
+};
+
+struct sti_dvo_connector {
+       struct drm_connector drm_connector;
+       struct drm_encoder *encoder;
+       struct sti_dvo *dvo;
+};
+
+#define to_sti_dvo_connector(x) \
+       container_of(x, struct sti_dvo_connector, drm_connector)
+
+#define BLANKING_LEVEL 16
+int dvo_awg_generate_code(struct sti_dvo *dvo, u8 *ram_size, u32 *ram_code)
+{
+       struct drm_display_mode *mode = &dvo->mode;
+       struct dvo_config *config = dvo->config;
+       struct awg_code_generation_params fw_gen_params;
+       struct awg_timing timing;
+
+       fw_gen_params.ram_code = ram_code;
+       fw_gen_params.instruction_offset = 0;
+
+       timing.total_lines = mode->vtotal;
+       timing.active_lines = mode->vdisplay;
+       timing.blanking_lines = mode->vsync_start - mode->vdisplay;
+       timing.trailing_lines = mode->vtotal - mode->vsync_start;
+       timing.total_pixels = mode->htotal;
+       timing.active_pixels = mode->hdisplay;
+       timing.blanking_pixels = mode->hsync_start - mode->hdisplay;
+       timing.trailing_pixels = mode->htotal - mode->hsync_start;
+       timing.blanking_level = BLANKING_LEVEL;
+
+       if (config->awg_fwgen_fct(&fw_gen_params, &timing)) {
+               DRM_ERROR("AWG firmware not properly generated\n");
+               return -EINVAL;
+       }
+
+       *ram_size = fw_gen_params.instruction_offset;
+
+       return 0;
+}
+
+/* Configure AWG, writing instructions
+ *
+ * @dvo: pointer to DVO structure
+ * @awg_ram_code: pointer to AWG instructions table
+ * @nb: nb of AWG instructions
+ */
+static void dvo_awg_configure(struct sti_dvo *dvo, u32 *awg_ram_code, int nb)
+{
+       int i;
+
+       DRM_DEBUG_DRIVER("\n");
+
+       for (i = 0; i < nb; i++)
+               writel(awg_ram_code[i],
+                      dvo->regs + DVO_DIGSYNC_INSTR_I + i * 4);
+       for (i = nb; i < AWG_MAX_INST; i++)
+               writel(0, dvo->regs + DVO_DIGSYNC_INSTR_I + i * 4);
+
+       writel(DVO_AWG_CTRL_EN, dvo->regs + DVO_AWG_DIGSYNC_CTRL);
+}
+
+static void sti_dvo_disable(struct drm_bridge *bridge)
+{
+       struct sti_dvo *dvo = bridge->driver_private;
+
+       if (!dvo->enabled)
+               return;
+
+       DRM_DEBUG_DRIVER("\n");
+
+       if (dvo->config->awg_fwgen_fct)
+               writel(0x00000000, dvo->regs + DVO_AWG_DIGSYNC_CTRL);
+
+       writel(0x00000000, dvo->regs + DVO_DOF_CFG);
+
+       if (dvo->panel)
+               dvo->panel->funcs->disable(dvo->panel);
+
+       /* Disable/unprepare dvo clock */
+       clk_disable_unprepare(dvo->clk_pix);
+       clk_disable_unprepare(dvo->clk);
+
+       dvo->enabled = false;
+}
+
+static void sti_dvo_pre_enable(struct drm_bridge *bridge)
+{
+       struct sti_dvo *dvo = bridge->driver_private;
+       struct dvo_config *config = dvo->config;
+       u32 val;
+
+       DRM_DEBUG_DRIVER("\n");
+
+       if (dvo->enabled)
+               return;
+
+       /* Make sure DVO is disabled */
+       writel(0x00000000, dvo->regs + DVO_DOF_CFG);
+       writel(0x00000000, dvo->regs + DVO_AWG_DIGSYNC_CTRL);
+
+       if (config->awg_fwgen_fct) {
+               u8 nb_instr;
+               u32 awg_ram_code[AWG_MAX_INST];
+               /* Configure AWG */
+               if (!dvo_awg_generate_code(dvo, &nb_instr, awg_ram_code))
+                       dvo_awg_configure(dvo, awg_ram_code, nb_instr);
+               else
+                       return;
+       }
+
+       /* Prepare/enable clocks */
+       if (clk_prepare_enable(dvo->clk_pix))
+               DRM_ERROR("Failed to prepare/enable dvo_pix clk\n");
+       if (clk_prepare_enable(dvo->clk))
+               DRM_ERROR("Failed to prepare/enable dvo clk\n");
+
+       if (dvo->panel)
+               dvo->panel->funcs->enable(dvo->panel);
+
+       /* Set LUT */
+       writel(config->lowbyte,  dvo->regs + DVO_LUT_PROG_LOW);
+       writel(config->midbyte,  dvo->regs + DVO_LUT_PROG_MID);
+       writel(config->highbyte, dvo->regs + DVO_LUT_PROG_HIGH);
+
+       /* Digital output formatter config */
+       val = (config->flags | DVO_DOF_EN);
+       writel(val, dvo->regs + DVO_DOF_CFG);
+
+       dvo->enabled = true;
+}
+
+static void sti_dvo_set_mode(struct drm_bridge *bridge,
+                            struct drm_display_mode *mode,
+                            struct drm_display_mode *adjusted_mode)
+{
+       struct sti_dvo *dvo = bridge->driver_private;
+       struct sti_mixer *mixer = to_sti_mixer(dvo->encoder->crtc);
+       int rate = mode->clock * 1000;
+       struct clk *clkp;
+       int ret;
+
+       DRM_DEBUG_DRIVER("\n");
+
+       memcpy(&dvo->mode, mode, sizeof(struct drm_display_mode));
+
+       /* According to the path used (main or aux), the dvo clocks should
+        * have a different parent clock. */
+       if (mixer->id == STI_MIXER_MAIN)
+               clkp = dvo->clk_main_parent;
+       else
+               clkp = dvo->clk_aux_parent;
+
+       if (clkp) {
+               clk_set_parent(dvo->clk_pix, clkp);
+               clk_set_parent(dvo->clk, clkp);
+       }
+
+       /* DVO clocks = compositor clock */
+       ret = clk_set_rate(dvo->clk_pix, rate);
+       if (ret < 0) {
+               DRM_ERROR("Cannot set rate (%dHz) for dvo_pix clk\n", rate);
+               return;
+       }
+
+       ret = clk_set_rate(dvo->clk, rate);
+       if (ret < 0) {
+               DRM_ERROR("Cannot set rate (%dHz) for dvo clk\n", rate);
+               return;
+       }
+
+       /* For now, we only support 24bit data enable (DE) synchro format */
+       dvo->config = &rgb_24bit_de_cfg;
+}
+
+static void sti_dvo_bridge_nope(struct drm_bridge *bridge)
+{
+       /* do nothing */
+}
+
+static void sti_dvo_brigde_destroy(struct drm_bridge *bridge)
+{
+       drm_bridge_cleanup(bridge);
+       kfree(bridge);
+}
+
+static const struct drm_bridge_funcs sti_dvo_bridge_funcs = {
+       .pre_enable = sti_dvo_pre_enable,
+       .enable = sti_dvo_bridge_nope,
+       .disable = sti_dvo_disable,
+       .post_disable = sti_dvo_bridge_nope,
+       .mode_set = sti_dvo_set_mode,
+       .destroy = sti_dvo_brigde_destroy,
+};
+
+static int sti_dvo_connector_get_modes(struct drm_connector *connector)
+{
+       struct sti_dvo_connector *dvo_connector
+               = to_sti_dvo_connector(connector);
+       struct sti_dvo *dvo = dvo_connector->dvo;
+
+       if (dvo->panel)
+               return dvo->panel->funcs->get_modes(dvo->panel);
+
+       return 0;
+}
+
+#define CLK_TOLERANCE_HZ 50
+
+static int sti_dvo_connector_mode_valid(struct drm_connector *connector,
+                                       struct drm_display_mode *mode)
+{
+       int target = mode->clock * 1000;
+       int target_min = target - CLK_TOLERANCE_HZ;
+       int target_max = target + CLK_TOLERANCE_HZ;
+       int result;
+       struct sti_dvo_connector *dvo_connector
+               = to_sti_dvo_connector(connector);
+       struct sti_dvo *dvo = dvo_connector->dvo;
+
+       result = clk_round_rate(dvo->clk_pix, target);
+
+       DRM_DEBUG_DRIVER("target rate = %d => available rate = %d\n",
+                        target, result);
+
+       if ((result < target_min) || (result > target_max)) {
+               DRM_DEBUG_DRIVER("dvo pixclk=%d not supported\n", target);
+               return MODE_BAD;
+       }
+
+       return MODE_OK;
+}
+
+struct drm_encoder *sti_dvo_best_encoder(struct drm_connector *connector)
+{
+       struct sti_dvo_connector *dvo_connector
+               = to_sti_dvo_connector(connector);
+
+       /* Best encoder is the one associated during connector creation */
+       return dvo_connector->encoder;
+}
+
+static struct drm_connector_helper_funcs sti_dvo_connector_helper_funcs = {
+       .get_modes = sti_dvo_connector_get_modes,
+       .mode_valid = sti_dvo_connector_mode_valid,
+       .best_encoder = sti_dvo_best_encoder,
+};
+
+static enum drm_connector_status
+sti_dvo_connector_detect(struct drm_connector *connector, bool force)
+{
+       struct sti_dvo_connector *dvo_connector
+               = to_sti_dvo_connector(connector);
+       struct sti_dvo *dvo = dvo_connector->dvo;
+
+       DRM_DEBUG_DRIVER("\n");
+
+       if (!dvo->panel)
+               dvo->panel = of_drm_find_panel(dvo->panel_node);
+
+       if (dvo->panel)
+               if (!drm_panel_attach(dvo->panel, connector))
+                       return connector_status_connected;
+
+       return connector_status_disconnected;
+}
+
+static void sti_dvo_connector_destroy(struct drm_connector *connector)
+{
+       struct sti_dvo_connector *dvo_connector
+               = to_sti_dvo_connector(connector);
+
+       drm_connector_unregister(connector);
+       drm_connector_cleanup(connector);
+       kfree(dvo_connector);
+}
+
+static struct drm_connector_funcs sti_dvo_connector_funcs = {
+       .dpms = drm_helper_connector_dpms,
+       .fill_modes = drm_helper_probe_single_connector_modes,
+       .detect = sti_dvo_connector_detect,
+       .destroy = sti_dvo_connector_destroy,
+};
+
+static struct drm_encoder *sti_dvo_find_encoder(struct drm_device *dev)
+{
+       struct drm_encoder *encoder;
+
+       list_for_each_entry(encoder, &dev->mode_config.encoder_list, head) {
+               if (encoder->encoder_type == DRM_MODE_ENCODER_LVDS)
+                       return encoder;
+       }
+
+       return NULL;
+}
+
+static int sti_dvo_bind(struct device *dev, struct device *master, void *data)
+{
+       struct sti_dvo *dvo = dev_get_drvdata(dev);
+       struct drm_device *drm_dev = data;
+       struct drm_encoder *encoder;
+       struct sti_dvo_connector *connector;
+       struct drm_connector *drm_connector;
+       struct drm_bridge *bridge;
+       int err;
+
+       /* Set the drm device handle */
+       dvo->drm_dev = drm_dev;
+
+       encoder = sti_dvo_find_encoder(drm_dev);
+       if (!encoder)
+               return -ENOMEM;
+
+       connector = devm_kzalloc(dev, sizeof(*connector), GFP_KERNEL);
+       if (!connector)
+               return -ENOMEM;
+
+       connector->dvo = dvo;
+
+       bridge = devm_kzalloc(dev, sizeof(*bridge), GFP_KERNEL);
+       if (!bridge)
+               return -ENOMEM;
+
+       bridge->driver_private = dvo;
+       drm_bridge_init(drm_dev, bridge, &sti_dvo_bridge_funcs);
+
+       encoder->bridge = bridge;
+       connector->encoder = encoder;
+       dvo->encoder = encoder;
+
+       drm_connector = (struct drm_connector *)connector;
+
+       drm_connector->polled = DRM_CONNECTOR_POLL_HPD;
+
+       drm_connector_init(drm_dev, drm_connector,
+                          &sti_dvo_connector_funcs, DRM_MODE_CONNECTOR_LVDS);
+       drm_connector_helper_add(drm_connector,
+                                &sti_dvo_connector_helper_funcs);
+
+       err = drm_connector_register(drm_connector);
+       if (err)
+               goto err_connector;
+
+       err = drm_mode_connector_attach_encoder(drm_connector, encoder);
+       if (err) {
+               DRM_ERROR("Failed to attach a connector to a encoder\n");
+               goto err_sysfs;
+       }
+
+       return 0;
+
+err_sysfs:
+       drm_connector_unregister(drm_connector);
+err_connector:
+       drm_bridge_cleanup(bridge);
+       drm_connector_cleanup(drm_connector);
+       return -EINVAL;
+}
+
+static void sti_dvo_unbind(struct device *dev,
+                          struct device *master, void *data)
+{
+       /* do nothing */
+}
+
+static const struct component_ops sti_dvo_ops = {
+       .bind = sti_dvo_bind,
+       .unbind = sti_dvo_unbind,
+};
+
+static int sti_dvo_probe(struct platform_device *pdev)
+{
+       struct device *dev = &pdev->dev;
+       struct sti_dvo *dvo;
+       struct resource *res;
+       struct device_node *np = dev->of_node;
+
+       DRM_INFO("%s\n", __func__);
+
+       dvo = devm_kzalloc(dev, sizeof(*dvo), GFP_KERNEL);
+       if (!dvo) {
+               DRM_ERROR("Failed to allocate memory for DVO\n");
+               return -ENOMEM;
+       }
+
+       dvo->dev = pdev->dev;
+
+       res = platform_get_resource_byname(pdev, IORESOURCE_MEM, "dvo-reg");
+       if (!res) {
+               DRM_ERROR("Invalid dvo resource\n");
+               return -ENOMEM;
+       }
+       dvo->regs = devm_ioremap_nocache(dev, res->start,
+                       resource_size(res));
+       if (IS_ERR(dvo->regs))
+               return PTR_ERR(dvo->regs);
+
+       dvo->clk_pix = devm_clk_get(dev, "dvo_pix");
+       if (IS_ERR(dvo->clk_pix)) {
+               DRM_ERROR("Cannot get dvo_pix clock\n");
+               return PTR_ERR(dvo->clk_pix);
+       }
+
+       dvo->clk = devm_clk_get(dev, "dvo");
+       if (IS_ERR(dvo->clk)) {
+               DRM_ERROR("Cannot get dvo clock\n");
+               return PTR_ERR(dvo->clk);
+       }
+
+       dvo->clk_main_parent = devm_clk_get(dev, "main_parent");
+       if (IS_ERR(dvo->clk_main_parent)) {
+               DRM_DEBUG_DRIVER("Cannot get main_parent clock\n");
+               dvo->clk_main_parent = NULL;
+       }
+
+       dvo->clk_aux_parent = devm_clk_get(dev, "aux_parent");
+       if (IS_ERR(dvo->clk_aux_parent)) {
+               DRM_DEBUG_DRIVER("Cannot get aux_parent clock\n");
+               dvo->clk_aux_parent = NULL;
+       }
+
+       dvo->panel_node = of_parse_phandle(np, "sti,panel", 0);
+       if (!dvo->panel_node)
+               DRM_ERROR("No panel associated to the dvo output\n");
+
+       platform_set_drvdata(pdev, dvo);
+
+       return component_add(&pdev->dev, &sti_dvo_ops);
+}
+
+static int sti_dvo_remove(struct platform_device *pdev)
+{
+       component_del(&pdev->dev, &sti_dvo_ops);
+       return 0;
+}
+
+static struct of_device_id dvo_of_match[] = {
+       { .compatible = "st,stih407-dvo", },
+       { /* end node */ }
+};
+MODULE_DEVICE_TABLE(of, dvo_of_match);
+
+struct platform_driver sti_dvo_driver = {
+       .driver = {
+               .name = "sti-dvo",
+               .owner = THIS_MODULE,
+               .of_match_table = dvo_of_match,
+       },
+       .probe = sti_dvo_probe,
+       .remove = sti_dvo_remove,
+};
+
+module_platform_driver(sti_dvo_driver);
+
+MODULE_AUTHOR("Benjamin Gaignard <benjamin.gaignard@st.com>");
+MODULE_DESCRIPTION("STMicroelectronics SoC DRM driver");
+MODULE_LICENSE("GPL");
index cb924aa2b321b3e0b499876770b86f76eb78a751..5cc53116508ebac4ecd469b76785a4b1bd033374 100644 (file)
@@ -48,6 +48,9 @@
 #define TVO_HDMI_CLIP_VALUE_R_CR         0x514
 #define TVO_HDMI_SYNC_SEL                0x518
 #define TVO_HDMI_DFV_OBS                 0x540
+#define TVO_VIP_DVO                      0x600
+#define TVO_DVO_SYNC_SEL                 0x618
+#define TVO_DVO_CONFIG                   0x620
 
 #define TVO_IN_FMT_SIGNED                BIT(0)
 #define TVO_SYNC_EXT                     BIT(4)
 
 #define TVO_SYNC_HD_DCS_SHIFT            8
 
+#define TVO_SYNC_DVO_PAD_HSYNC_SHIFT     8
+#define TVO_SYNC_DVO_PAD_VSYNC_SHIFT     16
+
 #define ENCODER_CRTC_MASK                (BIT(0) | BIT(1))
 
 /* enum listing the supported output data format */
@@ -113,6 +119,7 @@ struct sti_tvout {
        struct reset_control *reset;
        struct drm_encoder *hdmi;
        struct drm_encoder *hda;
+       struct drm_encoder *dvo;
 };
 
 struct sti_tvout_encoder {
@@ -261,6 +268,66 @@ static void tvout_vip_set_in_vid_fmt(struct sti_tvout *tvout,
        tvout_write(tvout, val, reg);
 }
 
+/**
+ * Start VIP block for DVO output
+ *
+ * @tvout: pointer on tvout structure
+ * @main_path: true if main path has to be used in the vip configuration
+ *       else aux path is used.
+ */
+static void tvout_dvo_start(struct sti_tvout *tvout, bool main_path)
+{
+       struct device_node *node = tvout->dev->of_node;
+       bool sel_input_logic_inverted = false;
+       u32 tvo_in_vid_format;
+       int val;
+
+       dev_dbg(tvout->dev, "%s\n", __func__);
+
+       if (main_path) {
+               DRM_DEBUG_DRIVER("main vip for DVO\n");
+               /* Select the input sync for dvo = VTG set 4 */
+               val  = TVO_SYNC_MAIN_VTG_SET_4 << TVO_SYNC_DVO_PAD_VSYNC_SHIFT;
+               val |= TVO_SYNC_MAIN_VTG_SET_4 << TVO_SYNC_DVO_PAD_HSYNC_SHIFT;
+               val |= TVO_SYNC_MAIN_VTG_SET_4;
+               tvout_write(tvout, val, TVO_DVO_SYNC_SEL);
+               tvo_in_vid_format = TVO_MAIN_IN_VID_FORMAT;
+       } else {
+               DRM_DEBUG_DRIVER("aux vip for DVO\n");
+               /* Select the input sync for dvo = VTG set 4 */
+               val  = TVO_SYNC_AUX_VTG_SET_4 << TVO_SYNC_DVO_PAD_VSYNC_SHIFT;
+               val |= TVO_SYNC_AUX_VTG_SET_4 << TVO_SYNC_DVO_PAD_HSYNC_SHIFT;
+               val |= TVO_SYNC_AUX_VTG_SET_4;
+               tvout_write(tvout, val, TVO_DVO_SYNC_SEL);
+               tvo_in_vid_format = TVO_AUX_IN_VID_FORMAT;
+       }
+
+       /* Set color channel order */
+       tvout_vip_set_color_order(tvout, TVO_VIP_DVO,
+                                 TVO_VIP_REORDER_CR_R_SEL,
+                                 TVO_VIP_REORDER_Y_G_SEL,
+                                 TVO_VIP_REORDER_CB_B_SEL);
+
+       /* Set clipping mode (Limited range RGB/Y) */
+       tvout_vip_set_clip_mode(tvout, TVO_VIP_DVO,
+                               TVO_VIP_CLIP_LIMITED_RANGE_RGB_Y);
+
+       /* Set round mode (rounded to 8-bit per component) */
+       tvout_vip_set_rnd(tvout, TVO_VIP_DVO, TVO_VIP_RND_8BIT_ROUNDED);
+
+       if (of_device_is_compatible(node, "st,stih407-tvout")) {
+               /* Set input video format */
+               tvout_vip_set_in_vid_fmt(tvout, tvo_in_vid_format,
+                                        TVO_IN_FMT_SIGNED);
+               sel_input_logic_inverted = true;
+       }
+
+       /* Input selection */
+       tvout_vip_set_sel_input(tvout, TVO_VIP_DVO, main_path,
+                               sel_input_logic_inverted,
+                               STI_TVOUT_VIDEO_OUT_RGB);
+}
+
 /**
  * Start VIP block for HDMI output
  *
@@ -402,6 +469,56 @@ static const struct drm_encoder_funcs sti_tvout_encoder_funcs = {
        .destroy = sti_tvout_encoder_destroy,
 };
 
+static void sti_dvo_encoder_commit(struct drm_encoder *encoder)
+{
+       struct sti_tvout *tvout = to_sti_tvout(encoder);
+
+       tvout_dvo_start(tvout, sti_drm_crtc_is_main(encoder->crtc));
+}
+
+static void sti_dvo_encoder_disable(struct drm_encoder *encoder)
+{
+       struct sti_tvout *tvout = to_sti_tvout(encoder);
+
+       /* Reset VIP register */
+       tvout_write(tvout, 0x0, TVO_VIP_DVO);
+}
+
+static const struct drm_encoder_helper_funcs sti_dvo_encoder_helper_funcs = {
+       .dpms = sti_tvout_encoder_dpms,
+       .mode_fixup = sti_tvout_encoder_mode_fixup,
+       .mode_set = sti_tvout_encoder_mode_set,
+       .prepare = sti_tvout_encoder_prepare,
+       .commit = sti_dvo_encoder_commit,
+       .disable = sti_dvo_encoder_disable,
+};
+
+static struct drm_encoder *
+sti_tvout_create_dvo_encoder(struct drm_device *dev,
+                            struct sti_tvout *tvout)
+{
+       struct sti_tvout_encoder *encoder;
+       struct drm_encoder *drm_encoder;
+
+       encoder = devm_kzalloc(tvout->dev, sizeof(*encoder), GFP_KERNEL);
+       if (!encoder)
+               return NULL;
+
+       encoder->tvout = tvout;
+
+       drm_encoder = (struct drm_encoder *)encoder;
+
+       drm_encoder->possible_crtcs = ENCODER_CRTC_MASK;
+       drm_encoder->possible_clones = 1 << 0;
+
+       drm_encoder_init(dev, drm_encoder,
+                        &sti_tvout_encoder_funcs, DRM_MODE_ENCODER_LVDS);
+
+       drm_encoder_helper_add(drm_encoder, &sti_dvo_encoder_helper_funcs);
+
+       return drm_encoder;
+}
+
 static void sti_hda_encoder_commit(struct drm_encoder *encoder)
 {
        struct sti_tvout *tvout = to_sti_tvout(encoder);
@@ -508,6 +625,7 @@ static void sti_tvout_create_encoders(struct drm_device *dev,
 {
        tvout->hdmi = sti_tvout_create_hdmi_encoder(dev, tvout);
        tvout->hda = sti_tvout_create_hda_encoder(dev, tvout);
+       tvout->dvo = sti_tvout_create_dvo_encoder(dev, tvout);
 }
 
 static void sti_tvout_destroy_encoders(struct sti_tvout *tvout)
index 978993fa3a360ef426b6dc48a3c287c3eda0cf48..ae26cc054fffcb225fc658bdae490a38d00a8f92 100644 (file)
@@ -1119,10 +1119,6 @@ static void tegra_crtc_commit(struct drm_crtc *crtc)
        tegra_dc_commit(dc);
 }
 
-static void tegra_crtc_load_lut(struct drm_crtc *crtc)
-{
-}
-
 static const struct drm_crtc_helper_funcs tegra_crtc_helper_funcs = {
        .disable = tegra_crtc_disable,
        .mode_fixup = tegra_crtc_mode_fixup,
@@ -1130,7 +1126,6 @@ static const struct drm_crtc_helper_funcs tegra_crtc_helper_funcs = {
        .mode_set_base = tegra_crtc_mode_set_base,
        .prepare = tegra_crtc_prepare,
        .commit = tegra_crtc_commit,
-       .load_lut = tegra_crtc_load_lut,
 };
 
 static irqreturn_t tegra_dc_irq(int irq, void *data)
index 8cbcb4589bd34db8fd35e8186eed1700dd9ba8cb..5fc16cecd3ba595584f01f5f9a7e0b729f125341 100644 (file)
@@ -589,19 +589,27 @@ int udl_fbdev_init(struct drm_device *dev)
 
        ret = drm_fb_helper_init(dev, &ufbdev->helper,
                                 1, 1);
-       if (ret) {
-               kfree(ufbdev);
-               return ret;
-
-       }
+       if (ret)
+               goto free;
 
-       drm_fb_helper_single_add_all_connectors(&ufbdev->helper);
+       ret = drm_fb_helper_single_add_all_connectors(&ufbdev->helper);
+       if (ret)
+               goto fini;
 
        /* disable all the possible outputs/crtcs before entering KMS mode */
        drm_helper_disable_unused_functions(dev);
 
-       drm_fb_helper_initial_config(&ufbdev->helper, bpp_sel);
+       ret = drm_fb_helper_initial_config(&ufbdev->helper, bpp_sel);
+       if (ret)
+               goto fini;
+
        return 0;
+
+fini:
+       drm_fb_helper_fini(&ufbdev->helper);
+free:
+       kfree(ufbdev);
+       return ret;
 }
 
 void udl_fbdev_cleanup(struct drm_device *dev)
index 2326c752d89b2086cb51234ef9b55ccda6bec87b..323203d0503aab371b1dd75e2baceae2b1958014 100644 (file)
@@ -114,6 +114,7 @@ struct ipu_dc_priv {
        struct completion       comp;
        int                     dc_irq;
        int                     dp_irq;
+       int                     use_count;
 };
 
 static void dc_link_event(struct ipu_dc *dc, int event, int addr, int priority)
@@ -232,7 +233,16 @@ EXPORT_SYMBOL_GPL(ipu_dc_init_sync);
 
 void ipu_dc_enable(struct ipu_soc *ipu)
 {
-       ipu_module_enable(ipu, IPU_CONF_DC_EN);
+       struct ipu_dc_priv *priv = ipu->dc_priv;
+
+       mutex_lock(&priv->mutex);
+
+       if (!priv->use_count)
+               ipu_module_enable(priv->ipu, IPU_CONF_DC_EN);
+
+       priv->use_count++;
+
+       mutex_unlock(&priv->mutex);
 }
 EXPORT_SYMBOL_GPL(ipu_dc_enable);
 
@@ -294,7 +304,18 @@ EXPORT_SYMBOL_GPL(ipu_dc_disable_channel);
 
 void ipu_dc_disable(struct ipu_soc *ipu)
 {
-       ipu_module_disable(ipu, IPU_CONF_DC_EN);
+       struct ipu_dc_priv *priv = ipu->dc_priv;
+
+       mutex_lock(&priv->mutex);
+
+       priv->use_count--;
+       if (!priv->use_count)
+               ipu_module_disable(priv->ipu, IPU_CONF_DC_EN);
+
+       if (priv->use_count < 0)
+               priv->use_count = 0;
+
+       mutex_unlock(&priv->mutex);
 }
 EXPORT_SYMBOL_GPL(ipu_dc_disable);
 
index c490ba4384fc5c0b2f65621d2079a384eb4eba1f..b61d6be97602222d3ae51b39d939d00cf8f5731b 100644 (file)
@@ -207,10 +207,10 @@ static void ipu_di_sync_config(struct ipu_di *di, struct di_sync_config *config,
 static void ipu_di_sync_config_interlaced(struct ipu_di *di,
                struct ipu_di_signal_cfg *sig)
 {
-       u32 h_total = sig->width + sig->h_sync_width +
-               sig->h_start_width + sig->h_end_width;
-       u32 v_total = sig->height + sig->v_sync_width +
-               sig->v_start_width + sig->v_end_width;
+       u32 h_total = sig->mode.hactive + sig->mode.hsync_len +
+               sig->mode.hback_porch + sig->mode.hfront_porch;
+       u32 v_total = sig->mode.vactive + sig->mode.vsync_len +
+               sig->mode.vback_porch + sig->mode.vfront_porch;
        u32 reg;
        struct di_sync_config cfg[] = {
                {
@@ -229,13 +229,13 @@ static void ipu_di_sync_config_interlaced(struct ipu_di *di,
                }, {
                        .run_count = v_total / 2 - 1,
                        .run_src = DI_SYNC_HSYNC,
-                       .offset_count = sig->v_start_width,
+                       .offset_count = sig->mode.vback_porch,
                        .offset_src = DI_SYNC_HSYNC,
                        .repeat_count = 2,
                        .cnt_clr_src = DI_SYNC_VSYNC,
                }, {
                        .run_src = DI_SYNC_HSYNC,
-                       .repeat_count = sig->height / 2,
+                       .repeat_count = sig->mode.vactive / 2,
                        .cnt_clr_src = 4,
                }, {
                        .run_count = v_total - 1,
@@ -249,9 +249,9 @@ static void ipu_di_sync_config_interlaced(struct ipu_di *di,
                        .cnt_clr_src = DI_SYNC_VSYNC,
                }, {
                        .run_src = DI_SYNC_CLK,
-                       .offset_count = sig->h_start_width,
+                       .offset_count = sig->mode.hback_porch,
                        .offset_src = DI_SYNC_CLK,
-                       .repeat_count = sig->width,
+                       .repeat_count = sig->mode.hactive,
                        .cnt_clr_src = 5,
                }, {
                        .run_count = v_total - 1,
@@ -277,10 +277,10 @@ static void ipu_di_sync_config_interlaced(struct ipu_di *di,
 static void ipu_di_sync_config_noninterlaced(struct ipu_di *di,
                struct ipu_di_signal_cfg *sig, int div)
 {
-       u32 h_total = sig->width + sig->h_sync_width + sig->h_start_width +
-               sig->h_end_width;
-       u32 v_total = sig->height + sig->v_sync_width + sig->v_start_width +
-               sig->v_end_width;
+       u32 h_total = sig->mode.hactive + sig->mode.hsync_len +
+               sig->mode.hback_porch + sig->mode.hfront_porch;
+       u32 v_total = sig->mode.vactive + sig->mode.vsync_len +
+               sig->mode.vback_porch + sig->mode.vfront_porch;
        struct di_sync_config cfg[] = {
                {
                        /* 1: INT_HSYNC */
@@ -294,27 +294,29 @@ static void ipu_di_sync_config_noninterlaced(struct ipu_di *di,
                        .offset_src = DI_SYNC_CLK,
                        .cnt_polarity_gen_en = 1,
                        .cnt_polarity_trigger_src = DI_SYNC_CLK,
-                       .cnt_down = sig->h_sync_width * 2,
+                       .cnt_down = sig->mode.hsync_len * 2,
                } , {
                        /* PIN3: VSYNC */
                        .run_count = v_total - 1,
                        .run_src = DI_SYNC_INT_HSYNC,
                        .cnt_polarity_gen_en = 1,
                        .cnt_polarity_trigger_src = DI_SYNC_INT_HSYNC,
-                       .cnt_down = sig->v_sync_width * 2,
+                       .cnt_down = sig->mode.vsync_len * 2,
                } , {
                        /* 4: Line Active */
                        .run_src = DI_SYNC_HSYNC,
-                       .offset_count = sig->v_sync_width + sig->v_start_width,
+                       .offset_count = sig->mode.vsync_len +
+                                       sig->mode.vback_porch,
                        .offset_src = DI_SYNC_HSYNC,
-                       .repeat_count = sig->height,
+                       .repeat_count = sig->mode.vactive,
                        .cnt_clr_src = DI_SYNC_VSYNC,
                } , {
                        /* 5: Pixel Active, referenced by DC */
                        .run_src = DI_SYNC_CLK,
-                       .offset_count = sig->h_sync_width + sig->h_start_width,
+                       .offset_count = sig->mode.hsync_len +
+                                       sig->mode.hback_porch,
                        .offset_src = DI_SYNC_CLK,
-                       .repeat_count = sig->width,
+                       .repeat_count = sig->mode.hactive,
                        .cnt_clr_src = 5, /* Line Active */
                } , {
                        /* unused */
@@ -339,9 +341,10 @@ static void ipu_di_sync_config_noninterlaced(struct ipu_di *di,
                } , {
                        /* 3: Line Active */
                        .run_src = DI_SYNC_INT_HSYNC,
-                       .offset_count = sig->v_sync_width + sig->v_start_width,
+                       .offset_count = sig->mode.vsync_len +
+                                       sig->mode.vback_porch,
                        .offset_src = DI_SYNC_INT_HSYNC,
-                       .repeat_count = sig->height,
+                       .repeat_count = sig->mode.vactive,
                        .cnt_clr_src = 3 /* VSYNC */,
                } , {
                        /* PIN4: HSYNC for VGA via TVEv2 on TQ MBa53 */
@@ -351,13 +354,14 @@ static void ipu_di_sync_config_noninterlaced(struct ipu_di *di,
                        .offset_src = DI_SYNC_CLK,
                        .cnt_polarity_gen_en = 1,
                        .cnt_polarity_trigger_src = DI_SYNC_CLK,
-                       .cnt_down = sig->h_sync_width * 2,
+                       .cnt_down = sig->mode.hsync_len * 2,
                } , {
                        /* 5: Pixel Active signal to DC */
                        .run_src = DI_SYNC_CLK,
-                       .offset_count = sig->h_sync_width + sig->h_start_width,
+                       .offset_count = sig->mode.hsync_len +
+                                       sig->mode.hback_porch,
                        .offset_src = DI_SYNC_CLK,
-                       .repeat_count = sig->width,
+                       .repeat_count = sig->mode.hactive,
                        .cnt_clr_src = 4, /* Line Active */
                } , {
                        /* PIN6: VSYNC for VGA via TVEv2 on TQ MBa53 */
@@ -367,7 +371,7 @@ static void ipu_di_sync_config_noninterlaced(struct ipu_di *di,
                        .offset_src = DI_SYNC_INT_HSYNC,
                        .cnt_polarity_gen_en = 1,
                        .cnt_polarity_trigger_src = DI_SYNC_INT_HSYNC,
-                       .cnt_down = sig->v_sync_width * 2,
+                       .cnt_down = sig->mode.vsync_len * 2,
                } , {
                        /* PIN4: HSYNC for VGA via TVEv2 on i.MX53-QSB */
                        .run_count = h_total - 1,
@@ -376,7 +380,7 @@ static void ipu_di_sync_config_noninterlaced(struct ipu_di *di,
                        .offset_src = DI_SYNC_CLK,
                        .cnt_polarity_gen_en = 1,
                        .cnt_polarity_trigger_src = DI_SYNC_CLK,
-                       .cnt_down = sig->h_sync_width * 2,
+                       .cnt_down = sig->mode.hsync_len * 2,
                } , {
                        /* PIN6: VSYNC for VGA via TVEv2 on i.MX53-QSB */
                        .run_count = v_total - 1,
@@ -385,7 +389,7 @@ static void ipu_di_sync_config_noninterlaced(struct ipu_di *di,
                        .offset_src = DI_SYNC_INT_HSYNC,
                        .cnt_polarity_gen_en = 1,
                        .cnt_polarity_trigger_src = DI_SYNC_INT_HSYNC,
-                       .cnt_down = sig->v_sync_width * 2,
+                       .cnt_down = sig->mode.vsync_len * 2,
                } , {
                        /* unused */
                },
@@ -433,10 +437,10 @@ static void ipu_di_config_clock(struct ipu_di *di,
                        unsigned long in_rate;
                        unsigned div;
 
-                       clk_set_rate(clk, sig->pixelclock);
+                       clk_set_rate(clk, sig->mode.pixelclock);
 
                        in_rate = clk_get_rate(clk);
-                       div = (in_rate + sig->pixelclock / 2) / sig->pixelclock;
+                       div = DIV_ROUND_CLOSEST(in_rate, sig->mode.pixelclock);
                        if (div == 0)
                                div = 1;
 
@@ -454,10 +458,10 @@ static void ipu_di_config_clock(struct ipu_di *di,
                unsigned div, error;
 
                clkrate = clk_get_rate(di->clk_ipu);
-               div = (clkrate + sig->pixelclock / 2) / sig->pixelclock;
+               div = DIV_ROUND_CLOSEST(clkrate, sig->mode.pixelclock);
                rate = clkrate / div;
 
-               error = rate / (sig->pixelclock / 1000);
+               error = rate / (sig->mode.pixelclock / 1000);
 
                dev_dbg(di->ipu->dev, "  IPU clock can give %lu with divider %u, error %d.%u%%\n",
                        rate, div, (signed)(error - 1000) / 10, error % 10);
@@ -473,10 +477,10 @@ static void ipu_di_config_clock(struct ipu_di *di,
 
                        clk = di->clk_di;
 
-                       clk_set_rate(clk, sig->pixelclock);
+                       clk_set_rate(clk, sig->mode.pixelclock);
 
                        in_rate = clk_get_rate(clk);
-                       div = (in_rate + sig->pixelclock / 2) / sig->pixelclock;
+                       div = DIV_ROUND_CLOSEST(in_rate, sig->mode.pixelclock);
                        if (div == 0)
                                div = 1;
 
@@ -504,35 +508,58 @@ static void ipu_di_config_clock(struct ipu_di *di,
        ipu_di_write(di, val, DI_GENERAL);
 
        dev_dbg(di->ipu->dev, "Want %luHz IPU %luHz DI %luHz using %s, %luHz\n",
-               sig->pixelclock,
+               sig->mode.pixelclock,
                clk_get_rate(di->clk_ipu),
                clk_get_rate(di->clk_di),
                clk == di->clk_di ? "DI" : "IPU",
                clk_get_rate(di->clk_di_pixel) / (clkgen0 >> 4));
 }
 
+/*
+ * This function is called to adjust a video mode to IPU restrictions.
+ * It is meant to be called from drm crtc mode_fixup() methods.
+ */
+int ipu_di_adjust_videomode(struct ipu_di *di, struct videomode *mode)
+{
+       u32 diff;
+
+       if (mode->vfront_porch >= 2)
+               return 0;
+
+       diff = 2 - mode->vfront_porch;
+
+       if (mode->vback_porch >= diff) {
+               mode->vfront_porch = 2;
+               mode->vback_porch -= diff;
+       } else if (mode->vsync_len > diff) {
+               mode->vfront_porch = 2;
+               mode->vsync_len = mode->vsync_len - diff;
+       } else {
+               dev_warn(di->ipu->dev, "failed to adjust videomode\n");
+               return -EINVAL;
+       }
+
+       dev_warn(di->ipu->dev, "videomode adapted for IPU restrictions\n");
+       return 0;
+}
+EXPORT_SYMBOL_GPL(ipu_di_adjust_videomode);
+
 int ipu_di_init_sync_panel(struct ipu_di *di, struct ipu_di_signal_cfg *sig)
 {
        u32 reg;
        u32 di_gen, vsync_cnt;
        u32 div;
-       u32 h_total, v_total;
 
        dev_dbg(di->ipu->dev, "disp %d: panel size = %d x %d\n",
-               di->id, sig->width, sig->height);
+               di->id, sig->mode.hactive, sig->mode.vactive);
 
-       if ((sig->v_sync_width == 0) || (sig->h_sync_width == 0))
+       if ((sig->mode.vsync_len == 0) || (sig->mode.hsync_len == 0))
                return -EINVAL;
 
-       h_total = sig->width + sig->h_sync_width + sig->h_start_width +
-               sig->h_end_width;
-       v_total = sig->height + sig->v_sync_width + sig->v_start_width +
-               sig->v_end_width;
-
        dev_dbg(di->ipu->dev, "Clocks: IPU %luHz DI %luHz Needed %luHz\n",
                clk_get_rate(di->clk_ipu),
                clk_get_rate(di->clk_di),
-               sig->pixelclock);
+               sig->mode.pixelclock);
 
        mutex_lock(&di_mutex);
 
@@ -551,7 +578,7 @@ int ipu_di_init_sync_panel(struct ipu_di *di, struct ipu_di_signal_cfg *sig)
        di_gen = ipu_di_read(di, DI_GENERAL) & DI_GEN_DI_CLK_EXT;
        di_gen |= DI_GEN_DI_VSYNC_EXT;
 
-       if (sig->interlaced) {
+       if (sig->mode.flags & DISPLAY_FLAGS_INTERLACED) {
                ipu_di_sync_config_interlaced(di, sig);
 
                /* set y_sel = 1 */
@@ -561,9 +588,9 @@ int ipu_di_init_sync_panel(struct ipu_di *di, struct ipu_di_signal_cfg *sig)
 
                vsync_cnt = 7;
 
-               if (sig->Hsync_pol)
+               if (sig->mode.flags & DISPLAY_FLAGS_HSYNC_HIGH)
                        di_gen |= DI_GEN_POLARITY_3;
-               if (sig->Vsync_pol)
+               if (sig->mode.flags & DISPLAY_FLAGS_VSYNC_HIGH)
                        di_gen |= DI_GEN_POLARITY_2;
        } else {
                ipu_di_sync_config_noninterlaced(di, sig, div);
@@ -577,7 +604,7 @@ int ipu_di_init_sync_panel(struct ipu_di *di, struct ipu_di_signal_cfg *sig)
                        if (!(sig->hsync_pin == 2 && sig->vsync_pin == 3))
                                vsync_cnt = 6;
 
-               if (sig->Hsync_pol) {
+               if (sig->mode.flags & DISPLAY_FLAGS_HSYNC_HIGH) {
                        if (sig->hsync_pin == 2)
                                di_gen |= DI_GEN_POLARITY_2;
                        else if (sig->hsync_pin == 4)
@@ -585,7 +612,7 @@ int ipu_di_init_sync_panel(struct ipu_di *di, struct ipu_di_signal_cfg *sig)
                        else if (sig->hsync_pin == 7)
                                di_gen |= DI_GEN_POLARITY_7;
                }
-               if (sig->Vsync_pol) {
+               if (sig->mode.flags & DISPLAY_FLAGS_VSYNC_HIGH) {
                        if (sig->vsync_pin == 3)
                                di_gen |= DI_GEN_POLARITY_3;
                        else if (sig->vsync_pin == 6)
index e37412da15f5c8ea300c7a096368d564a0acfba0..b99de00e57b86ce8164eb0b3ad02a8de11b8597e 100644 (file)
@@ -143,9 +143,15 @@ static int ad799x_write_config(struct ad799x_state *st, u16 val)
        case ad7998:
                return i2c_smbus_write_word_swapped(st->client, AD7998_CONF_REG,
                        val);
-       default:
+       case ad7992:
+       case ad7993:
+       case ad7994:
                return i2c_smbus_write_byte_data(st->client, AD7998_CONF_REG,
                        val);
+       default:
+               /* Will be written when doing a conversion */
+               st->config = val;
+               return 0;
        }
 }
 
@@ -155,8 +161,13 @@ static int ad799x_read_config(struct ad799x_state *st)
        case ad7997:
        case ad7998:
                return i2c_smbus_read_word_swapped(st->client, AD7998_CONF_REG);
-       default:
+       case ad7992:
+       case ad7993:
+       case ad7994:
                return i2c_smbus_read_byte_data(st->client, AD7998_CONF_REG);
+       default:
+               /* No readback support */
+               return st->config;
        }
 }
 
index 866fe904cba29e9f9f06d26fb0da16a9ce62b4d4..90c8cb727cc700b63f25c451c5eb4758bb3e400b 100644 (file)
@@ -449,6 +449,9 @@ static int iio_channel_read(struct iio_channel *chan, int *val, int *val2,
        if (val2 == NULL)
                val2 = &unused;
 
+       if(!iio_channel_has_info(chan->channel, info))
+               return -EINVAL;
+
        if (chan->indio_dev->info->read_raw_multi) {
                ret = chan->indio_dev->info->read_raw_multi(chan->indio_dev,
                                        chan->channel, INDIO_MAX_RAW_ELEMENTS,
index 57ecc5b204f3f6fdb01f1c2bebcdb6c752ad2ece..9117b7a2d5f8beeddebb367e421bbf7a8ca81807 100644 (file)
@@ -1114,7 +1114,8 @@ static int mlx4_ib_tunnel_steer_add(struct ib_qp *qp, struct ib_flow_attr *flow_
        struct mlx4_dev *dev = to_mdev(qp->device)->dev;
        int err = 0;
 
-       if (dev->caps.tunnel_offload_mode != MLX4_TUNNEL_OFFLOAD_MODE_VXLAN)
+       if (dev->caps.tunnel_offload_mode != MLX4_TUNNEL_OFFLOAD_MODE_VXLAN ||
+           dev->caps.dmfs_high_steer_mode == MLX4_STEERING_DMFS_A0_STATIC)
                return 0; /* do nothing */
 
        ib_flow = flow_attr + 1;
index f2b97802640755aacfcde04005b125717cb63818..77ecf6d322370ea8566ade345da953b13cc6362d 100644 (file)
@@ -1520,6 +1520,8 @@ static int elantech_set_properties(struct elantech_data *etd)
                case 7:
                case 8:
                case 9:
+               case 10:
+               case 13:
                        etd->hw_version = 4;
                        break;
                default:
index c66d1b53843e326a246aadd9050cd089c69e112a..764857b4e2682fa5d3ecc74f77d4f41a92eb34bb 100644 (file)
@@ -414,6 +414,13 @@ static const struct dmi_system_id __initconst i8042_dmi_nomux_table[] = {
                        DMI_MATCH(DMI_PRODUCT_NAME, "Aspire 5710"),
                },
        },
+       {
+               /* Acer Aspire 7738 */
+               .matches = {
+                       DMI_MATCH(DMI_SYS_VENDOR, "Acer"),
+                       DMI_MATCH(DMI_PRODUCT_NAME, "Aspire 7738"),
+               },
+       },
        {
                /* Gericom Bellagio */
                .matches = {
@@ -745,6 +752,35 @@ static const struct dmi_system_id __initconst i8042_dmi_dritek_table[] = {
        { }
 };
 
+/*
+ * Some laptops need keyboard reset before probing for the trackpad to get
+ * it detected, initialised & finally work.
+ */
+static const struct dmi_system_id __initconst i8042_dmi_kbdreset_table[] = {
+       {
+               /* Gigabyte P35 v2 - Elantech touchpad */
+               .matches = {
+                       DMI_MATCH(DMI_SYS_VENDOR, "GIGABYTE"),
+                       DMI_MATCH(DMI_PRODUCT_NAME, "P35V2"),
+               },
+       },
+               {
+               /* Aorus branded Gigabyte X3 Plus - Elantech touchpad */
+               .matches = {
+                       DMI_MATCH(DMI_SYS_VENDOR, "GIGABYTE"),
+                       DMI_MATCH(DMI_PRODUCT_NAME, "X3"),
+               },
+       },
+       {
+               /* Gigabyte P34 - Elantech touchpad */
+               .matches = {
+                       DMI_MATCH(DMI_SYS_VENDOR, "GIGABYTE"),
+                       DMI_MATCH(DMI_PRODUCT_NAME, "P34"),
+               },
+       },
+       { }
+};
+
 #endif /* CONFIG_X86 */
 
 #ifdef CONFIG_PNP
@@ -1040,6 +1076,9 @@ static int __init i8042_platform_init(void)
        if (dmi_check_system(i8042_dmi_dritek_table))
                i8042_dritek = true;
 
+       if (dmi_check_system(i8042_dmi_kbdreset_table))
+               i8042_kbdreset = true;
+
        /*
         * A20 was already enabled during early kernel init. But some buggy
         * BIOSes (in MSI Laptops) require A20 to be enabled using 8042 to
index 924e4bf357fb2607bb14fdf32173cc049830c3ab..986a71c614b0461bce7825ba34fc78aefcd4a7e4 100644 (file)
@@ -67,6 +67,10 @@ static bool i8042_notimeout;
 module_param_named(notimeout, i8042_notimeout, bool, 0);
 MODULE_PARM_DESC(notimeout, "Ignore timeouts signalled by i8042");
 
+static bool i8042_kbdreset;
+module_param_named(kbdreset, i8042_kbdreset, bool, 0);
+MODULE_PARM_DESC(kbdreset, "Reset device connected to KBD port");
+
 #ifdef CONFIG_X86
 static bool i8042_dritek;
 module_param_named(dritek, i8042_dritek, bool, 0);
@@ -789,6 +793,16 @@ static int __init i8042_check_aux(void)
        if (i8042_toggle_aux(true))
                return -1;
 
+/*
+ * Reset keyboard (needed on some laptops to successfully detect
+ * touchpad, e.g., some Gigabyte laptop models with Elantech
+ * touchpads).
+ */
+       if (i8042_kbdreset) {
+               pr_warn("Attempting to reset device connected to KBD port\n");
+               i8042_kbd_write(NULL, (unsigned char) 0xff);
+       }
+
 /*
  * Test AUX IRQ delivery to make sure BIOS did not grab the IRQ and
  * used it for a PCI card or somethig else.
index a82e542ffc21dd4dccf9d1b810ab9373984c1d0d..0b380603a578543bcd275d248ade94f3f07b24a8 100644 (file)
@@ -4880,7 +4880,7 @@ static void sig_ind(PLCI *plci)
        byte SS_Ind[] = "\x05\x02\x00\x02\x00\x00"; /* Hold_Ind struct*/
        byte CF_Ind[] = "\x09\x02\x00\x06\x00\x00\x00\x00\x00\x00";
        byte Interr_Err_Ind[] = "\x0a\x02\x00\x07\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00";
-       byte CONF_Ind[] = "\x09\x16\x00\x06\x00\x00\0x00\0x00\0x00\0x00";
+       byte CONF_Ind[] = "\x09\x16\x00\x06\x00\x00\x00\x00\x00\x00";
        byte force_mt_info = false;
        byte dir;
        dword d;
index 26515c27ea8cca18a2e5f5ac24f82a6158194182..25e419752a7b7c5719baa69bd114d57720a62f92 100644 (file)
@@ -330,18 +330,18 @@ create_netxbig_led(struct platform_device *pdev,
        led_dat->sata = 0;
        led_dat->cdev.brightness = LED_OFF;
        led_dat->cdev.flags |= LED_CORE_SUSPENDRESUME;
-       /*
-        * If available, expose the SATA activity blink capability through
-        * a "sata" sysfs attribute.
-        */
-       if (led_dat->mode_val[NETXBIG_LED_SATA] != NETXBIG_LED_INVALID_MODE)
-               led_dat->cdev.groups = netxbig_led_groups;
        led_dat->mode_addr = template->mode_addr;
        led_dat->mode_val = template->mode_val;
        led_dat->bright_addr = template->bright_addr;
        led_dat->bright_max = (1 << pdata->gpio_ext->num_data) - 1;
        led_dat->timer = pdata->timer;
        led_dat->num_timer = pdata->num_timer;
+       /*
+        * If available, expose the SATA activity blink capability through
+        * a "sata" sysfs attribute.
+        */
+       if (led_dat->mode_val[NETXBIG_LED_SATA] != NETXBIG_LED_INVALID_MODE)
+               led_dat->cdev.groups = netxbig_led_groups;
 
        return led_classdev_register(&pdev->dev, &led_dat->cdev);
 }
index f956ef26c0ce2ddc1f81014b8ab5e0b658eb9977..fb7493dcfb79f409a8f483480f1c8d50bdba2278 100644 (file)
@@ -7,6 +7,7 @@
 #define PCI_DEVICE_ID_MEN_CHAMELEON    0x4d45
 #define CHAMELEON_FILENAME_LEN         12
 #define CHAMELEONV2_MAGIC              0xabce
+#define CHAM_HEADER_SIZE               0x200
 
 enum chameleon_descriptor_type {
        CHAMELEON_DTYPE_GENERAL = 0x0,
index b5918196564376b028e825ccc75131ae74b1cdd0..5e1bd5db02c8ee7f21e0de9b778d2d1bb17a2d6c 100644 (file)
@@ -17,6 +17,7 @@
 
 struct priv {
        struct mcb_bus *bus;
+       phys_addr_t mapbase;
        void __iomem *base;
 };
 
@@ -31,8 +32,8 @@ static int mcb_pci_get_irq(struct mcb_device *mdev)
 
 static int mcb_pci_probe(struct pci_dev *pdev, const struct pci_device_id *id)
 {
+       struct resource *res;
        struct priv *priv;
-       phys_addr_t mapbase;
        int ret;
        int num_cells;
        unsigned long flags;
@@ -47,19 +48,21 @@ static int mcb_pci_probe(struct pci_dev *pdev, const struct pci_device_id *id)
                return -ENODEV;
        }
 
-       mapbase = pci_resource_start(pdev, 0);
-       if (!mapbase) {
+       priv->mapbase = pci_resource_start(pdev, 0);
+       if (!priv->mapbase) {
                dev_err(&pdev->dev, "No PCI resource\n");
                goto err_start;
        }
 
-       ret = pci_request_region(pdev, 0, KBUILD_MODNAME);
-       if (ret) {
-               dev_err(&pdev->dev, "Failed to request PCI BARs\n");
+       res = request_mem_region(priv->mapbase, CHAM_HEADER_SIZE,
+                                KBUILD_MODNAME);
+       if (IS_ERR(res)) {
+               dev_err(&pdev->dev, "Failed to request PCI memory\n");
+               ret = PTR_ERR(res);
                goto err_start;
        }
 
-       priv->base = pci_iomap(pdev, 0, 0);
+       priv->base = ioremap(priv->mapbase, CHAM_HEADER_SIZE);
        if (!priv->base) {
                dev_err(&pdev->dev, "Cannot ioremap\n");
                ret = -ENOMEM;
@@ -84,7 +87,7 @@ static int mcb_pci_probe(struct pci_dev *pdev, const struct pci_device_id *id)
 
        priv->bus->get_irq = mcb_pci_get_irq;
 
-       ret = chameleon_parse_cells(priv->bus, mapbase, priv->base);
+       ret = chameleon_parse_cells(priv->bus, priv->mapbase, priv->base);
        if (ret < 0)
                goto err_drvdata;
        num_cells = ret;
@@ -93,8 +96,10 @@ static int mcb_pci_probe(struct pci_dev *pdev, const struct pci_device_id *id)
 
        mcb_bus_add_devices(priv->bus);
 
+       return 0;
+
 err_drvdata:
-       pci_iounmap(pdev, priv->base);
+       iounmap(priv->base);
 err_ioremap:
        pci_release_region(pdev, 0);
 err_start:
@@ -107,6 +112,10 @@ static void mcb_pci_remove(struct pci_dev *pdev)
        struct priv *priv = pci_get_drvdata(pdev);
 
        mcb_release_bus(priv->bus);
+
+       iounmap(priv->base);
+       release_region(priv->mapbase, CHAM_HEADER_SIZE);
+       pci_disable_device(pdev);
 }
 
 static const struct pci_device_id mcb_pci_tbl[] = {
index 52a0c2f6264ff041f43a2fbcb2e187ada48e6d4b..ae498b53ee4042ef3e39e6f77a7272cffe4abe74 100644 (file)
@@ -554,7 +554,8 @@ int da9052_device_init(struct da9052 *da9052, u8 chip_id)
                return ret;
        }
 
-       ret = mfd_add_devices(da9052->dev, -1, da9052_subdev_info,
+       ret = mfd_add_devices(da9052->dev, PLATFORM_DEVID_AUTO,
+                             da9052_subdev_info,
                              ARRAY_SIZE(da9052_subdev_info), NULL, 0, NULL);
        if (ret) {
                dev_err(da9052->dev, "mfd_add_devices failed: %d\n", ret);
index dbdd0faeb6ce500678d9dc4f014504560693bded..210d1f85679e50dca4cbb034d4bd4ce91c1bb23f 100644 (file)
@@ -681,21 +681,9 @@ static void rtsx_usb_disconnect(struct usb_interface *intf)
 #ifdef CONFIG_PM
 static int rtsx_usb_suspend(struct usb_interface *intf, pm_message_t message)
 {
-       struct rtsx_ucr *ucr =
-               (struct rtsx_ucr *)usb_get_intfdata(intf);
-
        dev_dbg(&intf->dev, "%s called with pm message 0x%04x\n",
                        __func__, message.event);
 
-       /*
-        * Call to make sure LED is off during suspend to save more power.
-        * It is NOT a permanent state and could be turned on anytime later.
-        * Thus no need to call turn_on when resunming.
-        */
-       mutex_lock(&ucr->dev_mutex);
-       rtsx_usb_turn_off_led(ucr);
-       mutex_unlock(&ucr->dev_mutex);
-
        return 0;
 }
 
index 0d256cb002eb00480113435390fc19d5d92cb6cf..d6b764349f9d309956b36fd270ae1b6940e8167c 100644 (file)
@@ -125,10 +125,21 @@ int tps65218_clear_bits(struct tps65218 *tps, unsigned int reg,
 }
 EXPORT_SYMBOL_GPL(tps65218_clear_bits);
 
+static const struct regmap_range tps65218_yes_ranges[] = {
+       regmap_reg_range(TPS65218_REG_INT1, TPS65218_REG_INT2),
+       regmap_reg_range(TPS65218_REG_STATUS, TPS65218_REG_STATUS),
+};
+
+static const struct regmap_access_table tps65218_volatile_table = {
+       .yes_ranges = tps65218_yes_ranges,
+       .n_yes_ranges = ARRAY_SIZE(tps65218_yes_ranges),
+};
+
 static struct regmap_config tps65218_regmap_config = {
        .reg_bits = 8,
        .val_bits = 8,
        .cache_type = REGCACHE_RBTREE,
+       .volatile_table = &tps65218_volatile_table,
 };
 
 static const struct regmap_irq tps65218_irqs[] = {
@@ -193,6 +204,7 @@ static struct regmap_irq_chip tps65218_irq_chip = {
 
        .num_regs = 2,
        .mask_base = TPS65218_REG_INT_MASK1,
+       .status_base = TPS65218_REG_INT1,
 };
 
 static const struct of_device_id of_tps65218_match_table[] = {
index 51fd6b524371ecd9ae762716e4cf33692c36ce45..d1b55fe62817dcd0261ab926a704a37f590ca67c 100644 (file)
@@ -100,6 +100,46 @@ int cxl_context_init(struct cxl_context *ctx, struct cxl_afu *afu, bool master,
        return 0;
 }
 
+static int cxl_mmap_fault(struct vm_area_struct *vma, struct vm_fault *vmf)
+{
+       struct cxl_context *ctx = vma->vm_file->private_data;
+       unsigned long address = (unsigned long)vmf->virtual_address;
+       u64 area, offset;
+
+       offset = vmf->pgoff << PAGE_SHIFT;
+
+       pr_devel("%s: pe: %i address: 0x%lx offset: 0x%llx\n",
+                       __func__, ctx->pe, address, offset);
+
+       if (ctx->afu->current_mode == CXL_MODE_DEDICATED) {
+               area = ctx->afu->psn_phys;
+               if (offset > ctx->afu->adapter->ps_size)
+                       return VM_FAULT_SIGBUS;
+       } else {
+               area = ctx->psn_phys;
+               if (offset > ctx->psn_size)
+                       return VM_FAULT_SIGBUS;
+       }
+
+       mutex_lock(&ctx->status_mutex);
+
+       if (ctx->status != STARTED) {
+               mutex_unlock(&ctx->status_mutex);
+               pr_devel("%s: Context not started, failing problem state access\n", __func__);
+               return VM_FAULT_SIGBUS;
+       }
+
+       vm_insert_pfn(vma, address, (area + offset) >> PAGE_SHIFT);
+
+       mutex_unlock(&ctx->status_mutex);
+
+       return VM_FAULT_NOPAGE;
+}
+
+static const struct vm_operations_struct cxl_mmap_vmops = {
+       .fault = cxl_mmap_fault,
+};
+
 /*
  * Map a per-context mmio space into the given vma.
  */
@@ -108,26 +148,25 @@ int cxl_context_iomap(struct cxl_context *ctx, struct vm_area_struct *vma)
        u64 len = vma->vm_end - vma->vm_start;
        len = min(len, ctx->psn_size);
 
-       if (ctx->afu->current_mode == CXL_MODE_DEDICATED) {
-               vma->vm_page_prot = pgprot_noncached(vma->vm_page_prot);
-               return vm_iomap_memory(vma, ctx->afu->psn_phys, ctx->afu->adapter->ps_size);
-       }
+       if (ctx->afu->current_mode != CXL_MODE_DEDICATED) {
+               /* make sure there is a valid per process space for this AFU */
+               if ((ctx->master && !ctx->afu->psa) || (!ctx->afu->pp_psa)) {
+                       pr_devel("AFU doesn't support mmio space\n");
+                       return -EINVAL;
+               }
 
-       /* make sure there is a valid per process space for this AFU */
-       if ((ctx->master && !ctx->afu->psa) || (!ctx->afu->pp_psa)) {
-               pr_devel("AFU doesn't support mmio space\n");
-               return -EINVAL;
+               /* Can't mmap until the AFU is enabled */
+               if (!ctx->afu->enabled)
+                       return -EBUSY;
        }
 
-       /* Can't mmap until the AFU is enabled */
-       if (!ctx->afu->enabled)
-               return -EBUSY;
-
        pr_devel("%s: mmio physical: %llx pe: %i master:%i\n", __func__,
                 ctx->psn_phys, ctx->pe , ctx->master);
 
+       vma->vm_flags |= VM_IO | VM_PFNMAP;
        vma->vm_page_prot = pgprot_noncached(vma->vm_page_prot);
-       return vm_iomap_memory(vma, ctx->psn_phys, len);
+       vma->vm_ops = &cxl_mmap_vmops;
+       return 0;
 }
 
 /*
@@ -150,12 +189,6 @@ static void __detach_context(struct cxl_context *ctx)
        afu_release_irqs(ctx);
        flush_work(&ctx->fault_work); /* Only needed for dedicated process */
        wake_up_all(&ctx->wq);
-
-       /* Release Problem State Area mapping */
-       mutex_lock(&ctx->mapping_lock);
-       if (ctx->mapping)
-               unmap_mapping_range(ctx->mapping, 0, 0, 1);
-       mutex_unlock(&ctx->mapping_lock);
 }
 
 /*
@@ -184,6 +217,17 @@ void cxl_context_detach_all(struct cxl_afu *afu)
                 * created and torn down after the IDR removed
                 */
                __detach_context(ctx);
+
+               /*
+                * We are force detaching - remove any active PSA mappings so
+                * userspace cannot interfere with the card if it comes back.
+                * Easiest way to exercise this is to unbind and rebind the
+                * driver via sysfs while it is in use.
+                */
+               mutex_lock(&ctx->mapping_lock);
+               if (ctx->mapping)
+                       unmap_mapping_range(ctx->mapping, 0, 0, 1);
+               mutex_unlock(&ctx->mapping_lock);
        }
        mutex_unlock(&afu->contexts_lock);
 }
index e9f2f10dbb3734f3de4df60cdaed583415cfd831..b15d8113877c9f6ed5c45c58fb012fa6f50276aa 100644 (file)
@@ -140,18 +140,20 @@ static long afu_ioctl_start_work(struct cxl_context *ctx,
 
        pr_devel("%s: pe: %i\n", __func__, ctx->pe);
 
-       mutex_lock(&ctx->status_mutex);
-       if (ctx->status != OPENED) {
-               rc = -EIO;
-               goto out;
-       }
-
+       /* Do this outside the status_mutex to avoid a circular dependency with
+        * the locking in cxl_mmap_fault() */
        if (copy_from_user(&work, uwork,
                           sizeof(struct cxl_ioctl_start_work))) {
                rc = -EFAULT;
                goto out;
        }
 
+       mutex_lock(&ctx->status_mutex);
+       if (ctx->status != OPENED) {
+               rc = -EIO;
+               goto out;
+       }
+
        /*
         * if any of the reserved fields are set or any of the unused
         * flags are set it's invalid
index ff2755062b4420cf3239a80e0f767d6dc333b6a6..06ff0a2ec96071c5b2d1c2c5dffdff7a5c03d938 100644 (file)
@@ -234,6 +234,18 @@ static int mei_me_hw_reset(struct mei_device *dev, bool intr_enable)
        struct mei_me_hw *hw = to_me_hw(dev);
        u32 hcsr = mei_hcsr_read(hw);
 
+       /* H_RST may be found lit before reset is started,
+        * for example if preceding reset flow hasn't completed.
+        * In that case asserting H_RST will be ignored, therefore
+        * we need to clean H_RST bit to start a successful reset sequence.
+        */
+       if ((hcsr & H_RST) == H_RST) {
+               dev_warn(dev->dev, "H_RST is set = 0x%08X", hcsr);
+               hcsr &= ~H_RST;
+               mei_me_reg_write(hw, H_CSR, hcsr);
+               hcsr = mei_hcsr_read(hw);
+       }
+
        hcsr |= H_RST | H_IG | H_IS;
 
        if (intr_enable)
index e3e56d35f0eeee634a0930acce0500bb33cb3258..970314e0aac8f1f05e5b9ff199e28723b9d85a19 100644 (file)
@@ -247,6 +247,7 @@ static const struct sdhci_acpi_uid_slot sdhci_acpi_uids[] = {
        { "INT33BB"  , "3" , &sdhci_acpi_slot_int_sd },
        { "INT33C6"  , NULL, &sdhci_acpi_slot_int_sdio },
        { "INT3436"  , NULL, &sdhci_acpi_slot_int_sdio },
+       { "INT344D"  , NULL, &sdhci_acpi_slot_int_sdio },
        { "PNP0D40"  },
        { },
 };
@@ -257,6 +258,7 @@ static const struct acpi_device_id sdhci_acpi_ids[] = {
        { "INT33BB"  },
        { "INT33C6"  },
        { "INT3436"  },
+       { "INT344D"  },
        { "PNP0D40"  },
        { },
 };
index 03427755b9029b297393d1d43851b4f678f2bbae..4f38554ce6797e0a461a3ddaf76261264229f107 100644 (file)
@@ -993,6 +993,31 @@ static const struct pci_device_id pci_ids[] = {
                .subdevice      = PCI_ANY_ID,
                .driver_data    = (kernel_ulong_t)&sdhci_intel_mrfl_mmc,
        },
+
+       {
+               .vendor         = PCI_VENDOR_ID_INTEL,
+               .device         = PCI_DEVICE_ID_INTEL_SPT_EMMC,
+               .subvendor      = PCI_ANY_ID,
+               .subdevice      = PCI_ANY_ID,
+               .driver_data    = (kernel_ulong_t)&sdhci_intel_byt_emmc,
+       },
+
+       {
+               .vendor         = PCI_VENDOR_ID_INTEL,
+               .device         = PCI_DEVICE_ID_INTEL_SPT_SDIO,
+               .subvendor      = PCI_ANY_ID,
+               .subdevice      = PCI_ANY_ID,
+               .driver_data    = (kernel_ulong_t)&sdhci_intel_byt_sdio,
+       },
+
+       {
+               .vendor         = PCI_VENDOR_ID_INTEL,
+               .device         = PCI_DEVICE_ID_INTEL_SPT_SD,
+               .subvendor      = PCI_ANY_ID,
+               .subdevice      = PCI_ANY_ID,
+               .driver_data    = (kernel_ulong_t)&sdhci_intel_byt_sd,
+       },
+
        {
                .vendor         = PCI_VENDOR_ID_O2,
                .device         = PCI_DEVICE_ID_O2_8120,
index d57c3d169914e94e716b64b90e8b8da2b86afa87..1ec684d06d54733b35b2427d4007bfd5cfd3d52b 100644 (file)
@@ -21,6 +21,9 @@
 #define PCI_DEVICE_ID_INTEL_CLV_EMMC0  0x08e5
 #define PCI_DEVICE_ID_INTEL_CLV_EMMC1  0x08e6
 #define PCI_DEVICE_ID_INTEL_QRK_SD     0x08A7
+#define PCI_DEVICE_ID_INTEL_SPT_EMMC   0x9d2b
+#define PCI_DEVICE_ID_INTEL_SPT_SDIO   0x9d2c
+#define PCI_DEVICE_ID_INTEL_SPT_SD     0x9d2d
 
 /*
  * PCI registers
index 45238871192da1d6553268d82659dce3cc600d68..ca3424e7ef717c59a82da1e13a8ca3cf939da7f2 100644 (file)
@@ -300,13 +300,6 @@ static int sdhci_pxav3_probe(struct platform_device *pdev)
        if (IS_ERR(host))
                return PTR_ERR(host);
 
-       if (of_device_is_compatible(np, "marvell,armada-380-sdhci")) {
-               ret = mv_conf_mbus_windows(pdev, mv_mbus_dram_info());
-               if (ret < 0)
-                       goto err_mbus_win;
-       }
-
-
        pltfm_host = sdhci_priv(host);
        pltfm_host->priv = pxa;
 
@@ -325,6 +318,12 @@ static int sdhci_pxav3_probe(struct platform_device *pdev)
        if (!IS_ERR(pxa->clk_core))
                clk_prepare_enable(pxa->clk_core);
 
+       if (of_device_is_compatible(np, "marvell,armada-380-sdhci")) {
+               ret = mv_conf_mbus_windows(pdev, mv_mbus_dram_info());
+               if (ret < 0)
+                       goto err_mbus_win;
+       }
+
        /* enable 1/8V DDR capable */
        host->mmc->caps |= MMC_CAP_1_8V_DDR;
 
@@ -396,11 +395,11 @@ err_add_host:
        pm_runtime_disable(&pdev->dev);
 err_of_parse:
 err_cd_req:
+err_mbus_win:
        clk_disable_unprepare(pxa->clk_io);
        if (!IS_ERR(pxa->clk_core))
                clk_disable_unprepare(pxa->clk_core);
 err_clk_get:
-err_mbus_win:
        sdhci_pltfm_free(pdev);
        return ret;
 }
index cbb245b5853873cbddc2f1a0967c8bcc989ea4e1..f1a488ee432f891971f79707d78ca91a631b6c51 100644 (file)
@@ -259,8 +259,6 @@ static void sdhci_reinit(struct sdhci_host *host)
 
                del_timer_sync(&host->tuning_timer);
                host->flags &= ~SDHCI_NEEDS_RETUNING;
-               host->mmc->max_blk_count =
-                       (host->quirks & SDHCI_QUIRK_NO_MULTIBLOCK) ? 1 : 65535;
        }
        sdhci_enable_card_detection(host);
 }
@@ -1273,6 +1271,12 @@ static void sdhci_set_power(struct sdhci_host *host, unsigned char mode,
                spin_unlock_irq(&host->lock);
                mmc_regulator_set_ocr(mmc, mmc->supply.vmmc, vdd);
                spin_lock_irq(&host->lock);
+
+               if (mode != MMC_POWER_OFF)
+                       sdhci_writeb(host, SDHCI_POWER_ON, SDHCI_POWER_CONTROL);
+               else
+                       sdhci_writeb(host, 0, SDHCI_POWER_CONTROL);
+
                return;
        }
 
@@ -1353,6 +1357,8 @@ static void sdhci_request(struct mmc_host *mmc, struct mmc_request *mrq)
 
        sdhci_runtime_pm_get(host);
 
+       present = mmc_gpio_get_cd(host->mmc);
+
        spin_lock_irqsave(&host->lock, flags);
 
        WARN_ON(host->mrq != NULL);
@@ -1381,7 +1387,6 @@ static void sdhci_request(struct mmc_host *mmc, struct mmc_request *mrq)
         *     zero: cd-gpio is used, and card is removed
         *     one: cd-gpio is used, and card is present
         */
-       present = mmc_gpio_get_cd(host->mmc);
        if (present < 0) {
                /* If polling, assume that the card is always present. */
                if (host->quirks & SDHCI_QUIRK_BROKEN_CARD_DETECTION)
@@ -1880,6 +1885,18 @@ static int sdhci_card_busy(struct mmc_host *mmc)
        return !(present_state & SDHCI_DATA_LVL_MASK);
 }
 
+static int sdhci_prepare_hs400_tuning(struct mmc_host *mmc, struct mmc_ios *ios)
+{
+       struct sdhci_host *host = mmc_priv(mmc);
+       unsigned long flags;
+
+       spin_lock_irqsave(&host->lock, flags);
+       host->flags |= SDHCI_HS400_TUNING;
+       spin_unlock_irqrestore(&host->lock, flags);
+
+       return 0;
+}
+
 static int sdhci_execute_tuning(struct mmc_host *mmc, u32 opcode)
 {
        struct sdhci_host *host = mmc_priv(mmc);
@@ -1887,10 +1904,18 @@ static int sdhci_execute_tuning(struct mmc_host *mmc, u32 opcode)
        int tuning_loop_counter = MAX_TUNING_LOOP;
        int err = 0;
        unsigned long flags;
+       unsigned int tuning_count = 0;
+       bool hs400_tuning;
 
        sdhci_runtime_pm_get(host);
        spin_lock_irqsave(&host->lock, flags);
 
+       hs400_tuning = host->flags & SDHCI_HS400_TUNING;
+       host->flags &= ~SDHCI_HS400_TUNING;
+
+       if (host->tuning_mode == SDHCI_TUNING_MODE_1)
+               tuning_count = host->tuning_count;
+
        /*
         * The Host Controller needs tuning only in case of SDR104 mode
         * and for SDR50 mode when Use Tuning for SDR50 is set in the
@@ -1899,8 +1924,20 @@ static int sdhci_execute_tuning(struct mmc_host *mmc, u32 opcode)
         * tuning function has to be executed.
         */
        switch (host->timing) {
+       /* HS400 tuning is done in HS200 mode */
        case MMC_TIMING_MMC_HS400:
+               err = -EINVAL;
+               goto out_unlock;
+
        case MMC_TIMING_MMC_HS200:
+               /*
+                * Periodic re-tuning for HS400 is not expected to be needed, so
+                * disable it here.
+                */
+               if (hs400_tuning)
+                       tuning_count = 0;
+               break;
+
        case MMC_TIMING_UHS_SDR104:
                break;
 
@@ -1911,9 +1948,7 @@ static int sdhci_execute_tuning(struct mmc_host *mmc, u32 opcode)
                /* FALLTHROUGH */
 
        default:
-               spin_unlock_irqrestore(&host->lock, flags);
-               sdhci_runtime_pm_put(host);
-               return 0;
+               goto out_unlock;
        }
 
        if (host->ops->platform_execute_tuning) {
@@ -2037,24 +2072,11 @@ static int sdhci_execute_tuning(struct mmc_host *mmc, u32 opcode)
        }
 
 out:
-       /*
-        * If this is the very first time we are here, we start the retuning
-        * timer. Since only during the first time, SDHCI_NEEDS_RETUNING
-        * flag won't be set, we check this condition before actually starting
-        * the timer.
-        */
-       if (!(host->flags & SDHCI_NEEDS_RETUNING) && host->tuning_count &&
-           (host->tuning_mode == SDHCI_TUNING_MODE_1)) {
+       host->flags &= ~SDHCI_NEEDS_RETUNING;
+
+       if (tuning_count) {
                host->flags |= SDHCI_USING_RETUNING_TIMER;
-               mod_timer(&host->tuning_timer, jiffies +
-                       host->tuning_count * HZ);
-               /* Tuning mode 1 limits the maximum data length to 4MB */
-               mmc->max_blk_count = (4 * 1024 * 1024) / mmc->max_blk_size;
-       } else if (host->flags & SDHCI_USING_RETUNING_TIMER) {
-               host->flags &= ~SDHCI_NEEDS_RETUNING;
-               /* Reload the new initial value for timer */
-               mod_timer(&host->tuning_timer, jiffies +
-                         host->tuning_count * HZ);
+               mod_timer(&host->tuning_timer, jiffies + tuning_count * HZ);
        }
 
        /*
@@ -2070,6 +2092,7 @@ out:
 
        sdhci_writel(host, host->ier, SDHCI_INT_ENABLE);
        sdhci_writel(host, host->ier, SDHCI_SIGNAL_ENABLE);
+out_unlock:
        spin_unlock_irqrestore(&host->lock, flags);
        sdhci_runtime_pm_put(host);
 
@@ -2110,15 +2133,18 @@ static void sdhci_card_event(struct mmc_host *mmc)
 {
        struct sdhci_host *host = mmc_priv(mmc);
        unsigned long flags;
+       int present;
 
        /* First check if client has provided their own card event */
        if (host->ops->card_event)
                host->ops->card_event(host);
 
+       present = sdhci_do_get_cd(host);
+
        spin_lock_irqsave(&host->lock, flags);
 
        /* Check host->mrq first in case we are runtime suspended */
-       if (host->mrq && !sdhci_do_get_cd(host)) {
+       if (host->mrq && !present) {
                pr_err("%s: Card removed during transfer!\n",
                        mmc_hostname(host->mmc));
                pr_err("%s: Resetting controller.\n",
@@ -2142,6 +2168,7 @@ static const struct mmc_host_ops sdhci_ops = {
        .hw_reset       = sdhci_hw_reset,
        .enable_sdio_irq = sdhci_enable_sdio_irq,
        .start_signal_voltage_switch    = sdhci_start_signal_voltage_switch,
+       .prepare_hs400_tuning           = sdhci_prepare_hs400_tuning,
        .execute_tuning                 = sdhci_execute_tuning,
        .card_event                     = sdhci_card_event,
        .card_busy      = sdhci_card_busy,
@@ -3260,8 +3287,9 @@ int sdhci_add_host(struct sdhci_host *host)
                mmc->max_segs = SDHCI_MAX_SEGS;
 
        /*
-        * Maximum number of sectors in one transfer. Limited by DMA boundary
-        * size (512KiB).
+        * Maximum number of sectors in one transfer. Limited by SDMA boundary
+        * size (512KiB). Note some tuning modes impose a 4MiB limit, but this
+        * is less anyway.
         */
        mmc->max_req_size = 524288;
 
index f363972cd77d9a5a44267811a5db48c8d40ed397..e36d10520e248cd2b4d67bee15b1876cccf994d3 100644 (file)
@@ -103,27 +103,34 @@ static void c_can_hw_raminit_syscon(const struct c_can_priv *priv, bool enable)
        mask = 1 << raminit->bits.start | 1 << raminit->bits.done;
        regmap_read(raminit->syscon, raminit->reg, &ctrl);
 
-       /* We clear the done and start bit first. The start bit is
+       /* We clear the start bit first. The start bit is
         * looking at the 0 -> transition, but is not self clearing;
-        * And we clear the init done bit as well.
         * NOTE: DONE must be written with 1 to clear it.
+        * We can't clear the DONE bit here using regmap_update_bits()
+        * as it will bypass the write if initial condition is START:0 DONE:1
+        * e.g. on DRA7 which needs START pulse.
         */
-       ctrl &= ~(1 << raminit->bits.start);
-       ctrl |= 1 << raminit->bits.done;
-       regmap_write(raminit->syscon, raminit->reg, ctrl);
+       ctrl &= ~mask;  /* START = 0, DONE = 0 */
+       regmap_update_bits(raminit->syscon, raminit->reg, mask, ctrl);
 
-       ctrl &= ~(1 << raminit->bits.done);
-       c_can_hw_raminit_wait_syscon(priv, mask, ctrl);
+       /* check if START bit is 0. Ignore DONE bit for now
+        * as it can be either 0 or 1.
+        */
+       c_can_hw_raminit_wait_syscon(priv, 1 << raminit->bits.start, ctrl);
 
        if (enable) {
-               /* Set start bit and wait for the done bit. */
+               /* Clear DONE bit & set START bit. */
                ctrl |= 1 << raminit->bits.start;
-               regmap_write(raminit->syscon, raminit->reg, ctrl);
-
+               /* DONE must be written with 1 to clear it */
+               ctrl |= 1 << raminit->bits.done;
+               regmap_update_bits(raminit->syscon, raminit->reg, mask, ctrl);
+               /* prevent further clearing of DONE bit */
+               ctrl &= ~(1 << raminit->bits.done);
                /* clear START bit if start pulse is needed */
                if (raminit->needs_pulse) {
                        ctrl &= ~(1 << raminit->bits.start);
-                       regmap_write(raminit->syscon, raminit->reg, ctrl);
+                       regmap_update_bits(raminit->syscon, raminit->reg,
+                                          mask, ctrl);
                }
 
                ctrl |= 1 << raminit->bits.done;
index 3ec8f6f25e5f979e16838930295fe4cd66b2841c..847c1f813261d92a9188983141a79e2fddfcb3e7 100644 (file)
@@ -807,10 +807,14 @@ static int can_changelink(struct net_device *dev,
                if (dev->flags & IFF_UP)
                        return -EBUSY;
                cm = nla_data(data[IFLA_CAN_CTRLMODE]);
-               if (cm->flags & ~priv->ctrlmode_supported)
+
+               /* check whether changed bits are allowed to be modified */
+               if (cm->mask & ~priv->ctrlmode_supported)
                        return -EOPNOTSUPP;
+
+               /* clear bits to be modified and copy the flag values */
                priv->ctrlmode &= ~cm->mask;
-               priv->ctrlmode |= cm->flags;
+               priv->ctrlmode |= (cm->flags & cm->mask);
 
                /* CAN_CTRLMODE_FD can only be set when driver supports FD */
                if (priv->ctrlmode & CAN_CTRLMODE_FD)
index d7bc462aafdc27a26774aa6cb6cadb0e0d8547a3..244529881be9d919850df2c522ffb95e616c1e6d 100644 (file)
@@ -955,6 +955,11 @@ static struct net_device *alloc_m_can_dev(void)
        priv->can.data_bittiming_const = &m_can_data_bittiming_const;
        priv->can.do_set_mode = m_can_set_mode;
        priv->can.do_get_berr_counter = m_can_get_berr_counter;
+
+       /* CAN_CTRLMODE_FD_NON_ISO is fixed with M_CAN IP v3.0.1 */
+       priv->can.ctrlmode = CAN_CTRLMODE_FD_NON_ISO;
+
+       /* CAN_CTRLMODE_FD_NON_ISO can not be changed with M_CAN IP v3.0.1 */
        priv->can.ctrlmode_supported = CAN_CTRLMODE_LOOPBACK |
                                        CAN_CTRLMODE_LISTENONLY |
                                        CAN_CTRLMODE_BERR_REPORTING |
index 541fb7a05625aaf889089704ec155956629e77c8..c32cd61073bcc71048899f0ccb04cbcef2fe293c 100644 (file)
@@ -520,10 +520,10 @@ static void kvaser_usb_tx_acknowledge(const struct kvaser_usb *dev,
                skb = alloc_can_err_skb(priv->netdev, &cf);
                if (skb) {
                        cf->can_id |= CAN_ERR_RESTARTED;
-                       netif_rx(skb);
 
                        stats->rx_packets++;
                        stats->rx_bytes += cf->can_dlc;
+                       netif_rx(skb);
                } else {
                        netdev_err(priv->netdev,
                                   "No memory left for err_skb\n");
@@ -770,10 +770,9 @@ static void kvaser_usb_rx_error(const struct kvaser_usb *dev,
 
        priv->can.state = new_state;
 
-       netif_rx(skb);
-
        stats->rx_packets++;
        stats->rx_bytes += cf->can_dlc;
+       netif_rx(skb);
 }
 
 static void kvaser_usb_rx_can_err(const struct kvaser_usb_net_priv *priv,
@@ -805,10 +804,9 @@ static void kvaser_usb_rx_can_err(const struct kvaser_usb_net_priv *priv,
                stats->rx_over_errors++;
                stats->rx_errors++;
 
-               netif_rx(skb);
-
                stats->rx_packets++;
                stats->rx_bytes += cf->can_dlc;
+               netif_rx(skb);
        }
 }
 
@@ -887,10 +885,9 @@ static void kvaser_usb_rx_can_msg(const struct kvaser_usb *dev,
                               cf->can_dlc);
        }
 
-       netif_rx(skb);
-
        stats->rx_packets++;
        stats->rx_bytes += cf->can_dlc;
+       netif_rx(skb);
 }
 
 static void kvaser_usb_start_chip_reply(const struct kvaser_usb *dev,
@@ -1246,6 +1243,9 @@ static int kvaser_usb_close(struct net_device *netdev)
        if (err)
                netdev_warn(netdev, "Cannot stop device, error %d\n", err);
 
+       /* reset tx contexts */
+       kvaser_usb_unlink_tx_urbs(priv);
+
        priv->can.state = CAN_STATE_STOPPED;
        close_candev(priv->netdev);
 
@@ -1294,12 +1294,14 @@ static netdev_tx_t kvaser_usb_start_xmit(struct sk_buff *skb,
        if (!urb) {
                netdev_err(netdev, "No memory left for URBs\n");
                stats->tx_dropped++;
-               goto nourbmem;
+               dev_kfree_skb(skb);
+               return NETDEV_TX_OK;
        }
 
        buf = kmalloc(sizeof(struct kvaser_msg), GFP_ATOMIC);
        if (!buf) {
                stats->tx_dropped++;
+               dev_kfree_skb(skb);
                goto nobufmem;
        }
 
@@ -1334,6 +1336,7 @@ static netdev_tx_t kvaser_usb_start_xmit(struct sk_buff *skb,
                }
        }
 
+       /* This should never happen; it implies a flow control bug */
        if (!context) {
                netdev_warn(netdev, "cannot find free context\n");
                ret =  NETDEV_TX_BUSY;
@@ -1364,9 +1367,6 @@ static netdev_tx_t kvaser_usb_start_xmit(struct sk_buff *skb,
        if (unlikely(err)) {
                can_free_echo_skb(netdev, context->echo_index);
 
-               skb = NULL; /* set to NULL to avoid double free in
-                            * dev_kfree_skb(skb) */
-
                atomic_dec(&priv->active_tx_urbs);
                usb_unanchor_urb(urb);
 
@@ -1388,8 +1388,6 @@ releasebuf:
        kfree(buf);
 nobufmem:
        usb_free_urb(urb);
-nourbmem:
-       dev_kfree_skb(skb);
        return ret;
 }
 
@@ -1502,6 +1500,10 @@ static int kvaser_usb_init_one(struct usb_interface *intf,
        struct kvaser_usb_net_priv *priv;
        int i, err;
 
+       err = kvaser_usb_send_simple_msg(dev, CMD_RESET_CHIP, channel);
+       if (err)
+               return err;
+
        netdev = alloc_candev(sizeof(*priv), MAX_TX_URBS);
        if (!netdev) {
                dev_err(&intf->dev, "Cannot alloc candev\n");
@@ -1606,9 +1608,6 @@ static int kvaser_usb_probe(struct usb_interface *intf,
 
        usb_set_intfdata(intf, dev);
 
-       for (i = 0; i < MAX_NET_DEVICES; i++)
-               kvaser_usb_send_simple_msg(dev, CMD_RESET_CHIP, i);
-
        err = kvaser_usb_get_software_info(dev);
        if (err) {
                dev_err(&intf->dev,
index e398eda0729832671561490c6d18fce9db485f5e..c8af3ce3ea38d16d4c470ec5773b2d4f088b0f15 100644 (file)
@@ -184,15 +184,16 @@ static void alx_schedule_reset(struct alx_priv *alx)
        schedule_work(&alx->reset_wk);
 }
 
-static bool alx_clean_rx_irq(struct alx_priv *alx, int budget)
+static int alx_clean_rx_irq(struct alx_priv *alx, int budget)
 {
        struct alx_rx_queue *rxq = &alx->rxq;
        struct alx_rrd *rrd;
        struct alx_buffer *rxb;
        struct sk_buff *skb;
        u16 length, rfd_cleaned = 0;
+       int work = 0;
 
-       while (budget > 0) {
+       while (work < budget) {
                rrd = &rxq->rrd[rxq->rrd_read_idx];
                if (!(rrd->word3 & cpu_to_le32(1 << RRD_UPDATED_SHIFT)))
                        break;
@@ -203,7 +204,7 @@ static bool alx_clean_rx_irq(struct alx_priv *alx, int budget)
                    ALX_GET_FIELD(le32_to_cpu(rrd->word0),
                                  RRD_NOR) != 1) {
                        alx_schedule_reset(alx);
-                       return 0;
+                       return work;
                }
 
                rxb = &rxq->bufs[rxq->read_idx];
@@ -243,7 +244,7 @@ static bool alx_clean_rx_irq(struct alx_priv *alx, int budget)
                }
 
                napi_gro_receive(&alx->napi, skb);
-               budget--;
+               work++;
 
 next_pkt:
                if (++rxq->read_idx == alx->rx_ringsz)
@@ -258,21 +259,22 @@ next_pkt:
        if (rfd_cleaned)
                alx_refill_rx_ring(alx, GFP_ATOMIC);
 
-       return budget > 0;
+       return work;
 }
 
 static int alx_poll(struct napi_struct *napi, int budget)
 {
        struct alx_priv *alx = container_of(napi, struct alx_priv, napi);
        struct alx_hw *hw = &alx->hw;
-       bool complete = true;
        unsigned long flags;
+       bool tx_complete;
+       int work;
 
-       complete = alx_clean_tx_irq(alx) &&
-                  alx_clean_rx_irq(alx, budget);
+       tx_complete = alx_clean_tx_irq(alx);
+       work = alx_clean_rx_irq(alx, budget);
 
-       if (!complete)
-               return 1;
+       if (!tx_complete || work == budget)
+               return budget;
 
        napi_complete(&alx->napi);
 
@@ -284,7 +286,7 @@ static int alx_poll(struct napi_struct *napi, int budget)
 
        alx_post_write(hw);
 
-       return 0;
+       return work;
 }
 
 static irqreturn_t alx_intr_handle(struct alx_priv *alx, u32 intr)
index 05c6af6c418fa45690d085885b0cca330b58c210..3007d95fbb9f69c460a83d57bc66c7488421a627 100644 (file)
@@ -1167,10 +1167,10 @@ static int bgmac_poll(struct napi_struct *napi, int weight)
                bgmac->int_status = 0;
        }
 
-       if (handled < weight)
+       if (handled < weight) {
                napi_complete(napi);
-
-       bgmac_chip_intrs_on(bgmac);
+               bgmac_chip_intrs_on(bgmac);
+       }
 
        return handled;
 }
@@ -1515,6 +1515,8 @@ static int bgmac_probe(struct bcma_device *core)
        if (core->bus->sprom.boardflags_lo & BGMAC_BFL_ENETADM)
                bgmac_warn(bgmac, "Support for ADMtek ethernet switch not implemented\n");
 
+       netif_napi_add(net_dev, &bgmac->napi, bgmac_poll, BGMAC_WEIGHT);
+
        err = bgmac_mii_register(bgmac);
        if (err) {
                bgmac_err(bgmac, "Cannot register MDIO\n");
@@ -1529,8 +1531,6 @@ static int bgmac_probe(struct bcma_device *core)
 
        netif_carrier_off(net_dev);
 
-       netif_napi_add(net_dev, &bgmac->napi, bgmac_poll, BGMAC_WEIGHT);
-
        return 0;
 
 err_mii_unregister:
@@ -1549,9 +1549,9 @@ static void bgmac_remove(struct bcma_device *core)
 {
        struct bgmac *bgmac = bcma_get_drvdata(core);
 
-       netif_napi_del(&bgmac->napi);
        unregister_netdev(bgmac->net_dev);
        bgmac_mii_unregister(bgmac);
+       netif_napi_del(&bgmac->napi);
        bgmac_dma_free(bgmac);
        bcma_set_drvdata(core, NULL);
        free_netdev(bgmac->net_dev);
index 553dcd8a9df29f64108285c1f520635e287f7ca8..96bf01ba32dda179b15d2c36d6168581ee43c250 100644 (file)
@@ -7413,6 +7413,8 @@ static inline void tg3_netif_start(struct tg3 *tp)
 }
 
 static void tg3_irq_quiesce(struct tg3 *tp)
+       __releases(tp->lock)
+       __acquires(tp->lock)
 {
        int i;
 
@@ -7421,8 +7423,12 @@ static void tg3_irq_quiesce(struct tg3 *tp)
        tp->irq_sync = 1;
        smp_mb();
 
+       spin_unlock_bh(&tp->lock);
+
        for (i = 0; i < tp->irq_cnt; i++)
                synchronize_irq(tp->napi[i].irq_vec);
+
+       spin_lock_bh(&tp->lock);
 }
 
 /* Fully shutdown all tg3 driver activity elsewhere in the system.
@@ -9018,6 +9024,8 @@ static void tg3_restore_clk(struct tg3 *tp)
 
 /* tp->lock is held. */
 static int tg3_chip_reset(struct tg3 *tp)
+       __releases(tp->lock)
+       __acquires(tp->lock)
 {
        u32 val;
        void (*write_op)(struct tg3 *, u32, u32);
@@ -9073,9 +9081,13 @@ static int tg3_chip_reset(struct tg3 *tp)
        }
        smp_mb();
 
+       tg3_full_unlock(tp);
+
        for (i = 0; i < tp->irq_cnt; i++)
                synchronize_irq(tp->napi[i].irq_vec);
 
+       tg3_full_lock(tp, 0);
+
        if (tg3_asic_rev(tp) == ASIC_REV_57780) {
                val = tr32(TG3_PCIE_LNKCTL) & ~TG3_PCIE_LNKCTL_L1_PLL_PD_EN;
                tw32(TG3_PCIE_LNKCTL, val | TG3_PCIE_LNKCTL_L1_PLL_PD_DIS);
@@ -10903,11 +10915,13 @@ static void tg3_timer(unsigned long __opaque)
 {
        struct tg3 *tp = (struct tg3 *) __opaque;
 
-       if (tp->irq_sync || tg3_flag(tp, RESET_TASK_PENDING))
-               goto restart_timer;
-
        spin_lock(&tp->lock);
 
+       if (tp->irq_sync || tg3_flag(tp, RESET_TASK_PENDING)) {
+               spin_unlock(&tp->lock);
+               goto restart_timer;
+       }
+
        if (tg3_asic_rev(tp) == ASIC_REV_5717 ||
            tg3_flag(tp, 57765_CLASS))
                tg3_chk_missed_msi(tp);
@@ -11101,11 +11115,13 @@ static void tg3_reset_task(struct work_struct *work)
        struct tg3 *tp = container_of(work, struct tg3, reset_task);
        int err;
 
+       rtnl_lock();
        tg3_full_lock(tp, 0);
 
        if (!netif_running(tp->dev)) {
                tg3_flag_clear(tp, RESET_TASK_PENDING);
                tg3_full_unlock(tp);
+               rtnl_unlock();
                return;
        }
 
@@ -11138,6 +11154,7 @@ out:
                tg3_phy_start(tp);
 
        tg3_flag_clear(tp, RESET_TASK_PENDING);
+       rtnl_unlock();
 }
 
 static int tg3_request_irq(struct tg3 *tp, int irq_num)
index 55eb7f2af2b41ccf031f5018c12137daf752dc6c..7ef55f5fa664480ce052720bc55bd5ffb9ca8b57 100644 (file)
@@ -340,7 +340,7 @@ static int __init at91ether_probe(struct platform_device *pdev)
                res = PTR_ERR(lp->pclk);
                goto err_free_dev;
        }
-       clk_enable(lp->pclk);
+       clk_prepare_enable(lp->pclk);
 
        lp->hclk = ERR_PTR(-ENOENT);
        lp->tx_clk = ERR_PTR(-ENOENT);
@@ -406,7 +406,7 @@ static int __init at91ether_probe(struct platform_device *pdev)
 err_out_unregister_netdev:
        unregister_netdev(dev);
 err_disable_clock:
-       clk_disable(lp->pclk);
+       clk_disable_unprepare(lp->pclk);
 err_free_dev:
        free_netdev(dev);
        return res;
@@ -424,7 +424,7 @@ static int at91ether_remove(struct platform_device *pdev)
        kfree(lp->mii_bus->irq);
        mdiobus_free(lp->mii_bus);
        unregister_netdev(dev);
-       clk_disable(lp->pclk);
+       clk_disable_unprepare(lp->pclk);
        free_netdev(dev);
 
        return 0;
@@ -440,7 +440,7 @@ static int at91ether_suspend(struct platform_device *pdev, pm_message_t mesg)
                netif_stop_queue(net_dev);
                netif_device_detach(net_dev);
 
-               clk_disable(lp->pclk);
+               clk_disable_unprepare(lp->pclk);
        }
        return 0;
 }
@@ -451,7 +451,7 @@ static int at91ether_resume(struct platform_device *pdev)
        struct macb *lp = netdev_priv(net_dev);
 
        if (netif_running(net_dev)) {
-               clk_enable(lp->pclk);
+               clk_prepare_enable(lp->pclk);
 
                netif_device_attach(net_dev);
                netif_start_queue(net_dev);
index 2215d432a05958ddb25e6b0d1a4bee27562f748a..a936ee8958c704fa90321a1934b2c7dacbf046a6 100644 (file)
@@ -2430,7 +2430,7 @@ static void cfg_queues(struct adapter *adapter)
         */
        n10g = 0;
        for_each_port(adapter, pidx)
-               n10g += is_10g_port(&adap2pinfo(adapter, pidx)->link_cfg);
+               n10g += is_x_10g_port(&adap2pinfo(adapter, pidx)->link_cfg);
 
        /*
         * We default to 1 queue per non-10G port and up to # of cores queues
index 21dc9a20308c58dabef4b77b1fad338547e20df3..60426cf890a774dd07ec939a622f88991c1044f6 100644 (file)
@@ -323,6 +323,8 @@ int t4vf_port_init(struct adapter *adapter, int pidx)
                return v;
 
        v = be32_to_cpu(port_rpl.u.info.lstatus_to_modtype);
+       pi->mdio_addr = (v & FW_PORT_CMD_MDIOCAP_F) ?
+                       FW_PORT_CMD_MDIOADDR_G(v) : -1;
        pi->port_type = FW_PORT_CMD_PTYPE_G(v);
        pi->mod_type = FW_PORT_MOD_TYPE_NA;
 
index a379c3e4b57f73ef3fd133bd4bb5114e29f10cb4..13d00a38a5bd60ed1e7af054f3a22b617e64317d 100644 (file)
@@ -398,13 +398,8 @@ static int dnet_poll(struct napi_struct *napi, int budget)
                 * break out of while loop if there are no more
                 * packets waiting
                 */
-               if (!(dnet_readl(bp, RX_FIFO_WCNT) >> 16)) {
-                       napi_complete(napi);
-                       int_enable = dnet_readl(bp, INTR_ENB);
-                       int_enable |= DNET_INTR_SRC_RX_CMDFIFOAF;
-                       dnet_writel(bp, int_enable, INTR_ENB);
-                       return 0;
-               }
+               if (!(dnet_readl(bp, RX_FIFO_WCNT) >> 16))
+                       break;
 
                cmd_word = dnet_readl(bp, RX_LEN_FIFO);
                pkt_len = cmd_word & 0xFFFF;
@@ -433,20 +428,17 @@ static int dnet_poll(struct napi_struct *napi, int budget)
                               "size %u.\n", dev->name, pkt_len);
        }
 
-       budget -= npackets;
-
        if (npackets < budget) {
                /* We processed all packets available.  Tell NAPI it can
-                * stop polling then re-enable rx interrupts */
+                * stop polling then re-enable rx interrupts.
+                */
                napi_complete(napi);
                int_enable = dnet_readl(bp, INTR_ENB);
                int_enable |= DNET_INTR_SRC_RX_CMDFIFOAF;
                dnet_writel(bp, int_enable, INTR_ENB);
-               return 0;
        }
 
-       /* There are still packets waiting */
-       return 1;
+       return npackets;
 }
 
 static irqreturn_t dnet_interrupt(int irq, void *dev_id)
index 41a0a5498da74c7b9b1129b68c9173c1b15470a4..d48806b5cd8889457f28062336d7c4bf308af6a1 100644 (file)
@@ -4383,8 +4383,9 @@ static int be_ndo_bridge_getlink(struct sk_buff *skb, u32 pid, u32 seq,
  * distinguish various types of transports (VxLAN, GRE, NVGRE ..). So, offload
  * is expected to work across all types of IP tunnels once exported. Skyhawk
  * supports offloads for either VxLAN or NVGRE, exclusively. So we export VxLAN
- * offloads in hw_enc_features only when a VxLAN port is added. Note this only
- * ensures that other tunnels work fine while VxLAN offloads are not enabled.
+ * offloads in hw_enc_features only when a VxLAN port is added. If other (non
+ * VxLAN) tunnels are configured while VxLAN offloads are enabled, offloads for
+ * those other tunnels are unexported on the fly through ndo_features_check().
  *
  * Skyhawk supports VxLAN offloads only for one UDP dport. So, if the stack
  * adds more than one port, disable offloads and don't re-enable them again
@@ -4463,7 +4464,41 @@ static netdev_features_t be_features_check(struct sk_buff *skb,
                                           struct net_device *dev,
                                           netdev_features_t features)
 {
-       return vxlan_features_check(skb, features);
+       struct be_adapter *adapter = netdev_priv(dev);
+       u8 l4_hdr = 0;
+
+       /* The code below restricts offload features for some tunneled packets.
+        * Offload features for normal (non tunnel) packets are unchanged.
+        */
+       if (!skb->encapsulation ||
+           !(adapter->flags & BE_FLAGS_VXLAN_OFFLOADS))
+               return features;
+
+       /* It's an encapsulated packet and VxLAN offloads are enabled. We
+        * should disable tunnel offload features if it's not a VxLAN packet,
+        * as tunnel offloads have been enabled only for VxLAN. This is done to
+        * allow other tunneled traffic like GRE work fine while VxLAN
+        * offloads are configured in Skyhawk-R.
+        */
+       switch (vlan_get_protocol(skb)) {
+       case htons(ETH_P_IP):
+               l4_hdr = ip_hdr(skb)->protocol;
+               break;
+       case htons(ETH_P_IPV6):
+               l4_hdr = ipv6_hdr(skb)->nexthdr;
+               break;
+       default:
+               return features;
+       }
+
+       if (l4_hdr != IPPROTO_UDP ||
+           skb->inner_protocol_type != ENCAP_TYPE_ETHER ||
+           skb->inner_protocol != htons(ETH_P_TEB) ||
+           skb_inner_mac_header(skb) - skb_transport_header(skb) !=
+           sizeof(struct udphdr) + sizeof(struct vxlanhdr))
+               return features & ~(NETIF_F_ALL_CSUM | NETIF_F_GSO_MASK);
+
+       return features;
 }
 #endif
 
index 469691ad4a1ee25dda5ff9dbec0ef8735ae0f6bf..40132929daf7ac7713f2cd0f1f469656616fadfc 100644 (file)
@@ -424,6 +424,8 @@ struct bufdesc_ex {
  * (40ns * 6).
  */
 #define FEC_QUIRK_BUG_CAPTURE          (1 << 10)
+/* Controller has only one MDIO bus */
+#define FEC_QUIRK_SINGLE_MDIO          (1 << 11)
 
 struct fec_enet_priv_tx_q {
        int index;
index 5ebdf8dc8a31300f526fd98912080dc4850937f2..bba87775419dc9c0d5adadcdda8c1e634dc8e04d 100644 (file)
@@ -91,7 +91,8 @@ static struct platform_device_id fec_devtype[] = {
                .driver_data = 0,
        }, {
                .name = "imx28-fec",
-               .driver_data = FEC_QUIRK_ENET_MAC | FEC_QUIRK_SWAP_FRAME,
+               .driver_data = FEC_QUIRK_ENET_MAC | FEC_QUIRK_SWAP_FRAME |
+                               FEC_QUIRK_SINGLE_MDIO,
        }, {
                .name = "imx6q-fec",
                .driver_data = FEC_QUIRK_ENET_MAC | FEC_QUIRK_HAS_GBIT |
@@ -1937,7 +1938,7 @@ static int fec_enet_mii_init(struct platform_device *pdev)
        int err = -ENXIO, i;
 
        /*
-        * The dual fec interfaces are not equivalent with enet-mac.
+        * The i.MX28 dual fec interfaces are not equal.
         * Here are the differences:
         *
         *  - fec0 supports MII & RMII modes while fec1 only supports RMII
@@ -1952,7 +1953,7 @@ static int fec_enet_mii_init(struct platform_device *pdev)
         * mdio interface in board design, and need to be configured by
         * fec0 mii_bus.
         */
-       if ((fep->quirks & FEC_QUIRK_ENET_MAC) && fep->dev_id > 0) {
+       if ((fep->quirks & FEC_QUIRK_SINGLE_MDIO) && fep->dev_id > 0) {
                /* fec1 uses fec0 mii_bus */
                if (mii_cnt && fec0_mii_bus) {
                        fep->mii_bus = fec0_mii_bus;
@@ -2015,7 +2016,7 @@ static int fec_enet_mii_init(struct platform_device *pdev)
        mii_cnt++;
 
        /* save fec0 mii_bus */
-       if (fep->quirks & FEC_QUIRK_ENET_MAC)
+       if (fep->quirks & FEC_QUIRK_SINGLE_MDIO)
                fec0_mii_bus = fep->mii_bus;
 
        return 0;
@@ -3129,6 +3130,7 @@ fec_probe(struct platform_device *pdev)
                pdev->id_entry = of_id->data;
        fep->quirks = pdev->id_entry->driver_data;
 
+       fep->netdev = ndev;
        fep->num_rx_queues = num_rx_qs;
        fep->num_tx_queues = num_tx_qs;
 
index 5b8300a32bf5f5eb1df93d7262b22a00b7d77a9f..4d61ef50b465b73bd4bd87256a2ad47d83d4d666 100644 (file)
@@ -281,6 +281,17 @@ config I40E_DCB
 
          If unsure, say N.
 
+config I40E_FCOE
+       bool "Fibre Channel over Ethernet (FCoE)"
+       default n
+       depends on I40E && DCB && FCOE
+       ---help---
+         Say Y here if you want to use Fibre Channel over Ethernet (FCoE)
+         in the driver. This will create new netdev for exclusive FCoE
+         use with XL710 FCoE offloads enabled.
+
+         If unsure, say N.
+
 config I40EVF
        tristate "Intel(R) XL710 X710 Virtual Function Ethernet support"
        depends on PCI_MSI
index 4b94ddb29c248ed2571c4d90eb37d8c8ecbec935..c405819991214e21a25b5a670d0097482fd643ab 100644 (file)
@@ -44,4 +44,4 @@ i40e-objs := i40e_main.o \
        i40e_virtchnl_pf.o
 
 i40e-$(CONFIG_I40E_DCB) += i40e_dcb.o i40e_dcb_nl.o
-i40e-$(CONFIG_FCOE:m=y) += i40e_fcoe.o
+i40e-$(CONFIG_I40E_FCOE) += i40e_fcoe.o
index 045b5c4b98b38ba74ef68104828351f2a8fdc67c..ad802dd0f67a3d4fdcb6810ebdc8d66b67706d66 100644 (file)
@@ -78,7 +78,7 @@ do {                                                            \
 } while (0)
 
 typedef enum i40e_status_code i40e_status;
-#if defined(CONFIG_FCOE) || defined(CONFIG_FCOE_MODULE)
+#ifdef CONFIG_I40E_FCOE
 #define I40E_FCOE
-#endif /* CONFIG_FCOE or CONFIG_FCOE_MODULE */
+#endif
 #endif /* _I40E_OSDEP_H_ */
index 04b441460bbda6e36cb64731d24247a1b954e506..cecb340898fe2a881aac449c7377110ccc56793b 100644 (file)
@@ -658,6 +658,8 @@ static inline u32 i40e_get_head(struct i40e_ring *tx_ring)
        return le32_to_cpu(*(volatile __le32 *)head);
 }
 
+#define WB_STRIDE 0x3
+
 /**
  * i40e_clean_tx_irq - Reclaim resources after transmit completes
  * @tx_ring:  tx ring to clean
@@ -759,6 +761,18 @@ static bool i40e_clean_tx_irq(struct i40e_ring *tx_ring, int budget)
        tx_ring->q_vector->tx.total_bytes += total_bytes;
        tx_ring->q_vector->tx.total_packets += total_packets;
 
+       /* check to see if there are any non-cache aligned descriptors
+        * waiting to be written back, and kick the hardware to force
+        * them to be written back in case of napi polling
+        */
+       if (budget &&
+           !((i & WB_STRIDE) == WB_STRIDE) &&
+           !test_bit(__I40E_DOWN, &tx_ring->vsi->state) &&
+           (I40E_DESC_UNUSED(tx_ring) != tx_ring->count))
+               tx_ring->arm_wb = true;
+       else
+               tx_ring->arm_wb = false;
+
        if (check_for_tx_hang(tx_ring) && i40e_check_tx_hang(tx_ring)) {
                /* schedule immediate reset if we believe we hung */
                dev_info(tx_ring->dev, "Detected Tx Unit Hang\n"
@@ -777,13 +791,16 @@ static bool i40e_clean_tx_irq(struct i40e_ring *tx_ring, int budget)
                netif_stop_subqueue(tx_ring->netdev, tx_ring->queue_index);
 
                dev_info(tx_ring->dev,
-                        "tx hang detected on queue %d, resetting adapter\n",
+                        "tx hang detected on queue %d, reset requested\n",
                         tx_ring->queue_index);
 
-               tx_ring->netdev->netdev_ops->ndo_tx_timeout(tx_ring->netdev);
+               /* do not fire the reset immediately, wait for the stack to
+                * decide we are truly stuck, also prevents every queue from
+                * simultaneously requesting a reset
+                */
 
-               /* the adapter is about to reset, no point in enabling stuff */
-               return true;
+               /* the adapter is about to reset, no point in enabling polling */
+               budget = 1;
        }
 
        netdev_tx_completed_queue(netdev_get_tx_queue(tx_ring->netdev,
@@ -806,7 +823,25 @@ static bool i40e_clean_tx_irq(struct i40e_ring *tx_ring, int budget)
                }
        }
 
-       return budget > 0;
+       return !!budget;
+}
+
+/**
+ * i40e_force_wb - Arm hardware to do a wb on noncache aligned descriptors
+ * @vsi: the VSI we care about
+ * @q_vector: the vector  on which to force writeback
+ *
+ **/
+static void i40e_force_wb(struct i40e_vsi *vsi, struct i40e_q_vector *q_vector)
+{
+       u32 val = I40E_PFINT_DYN_CTLN_INTENA_MASK |
+                 I40E_PFINT_DYN_CTLN_SWINT_TRIG_MASK |
+                 I40E_PFINT_DYN_CTLN_SW_ITR_INDX_ENA_MASK
+                 /* allow 00 to be written to the index */;
+
+       wr32(&vsi->back->hw,
+            I40E_PFINT_DYN_CTLN(q_vector->v_idx + vsi->base_vector - 1),
+            val);
 }
 
 /**
@@ -1290,9 +1325,7 @@ static inline void i40e_rx_checksum(struct i40e_vsi *vsi,
         * so the total length of IPv4 header is IHL*4 bytes
         * The UDP_0 bit *may* bet set if the *inner* header is UDP
         */
-       if (ipv4_tunnel &&
-           (decoded.inner_prot != I40E_RX_PTYPE_INNER_PROT_UDP) &&
-           !(rx_status & (1 << I40E_RX_DESC_STATUS_UDP_0_SHIFT))) {
+       if (ipv4_tunnel) {
                skb->transport_header = skb->mac_header +
                                        sizeof(struct ethhdr) +
                                        (ip_hdr(skb)->ihl * 4);
@@ -1302,15 +1335,19 @@ static inline void i40e_rx_checksum(struct i40e_vsi *vsi,
                                          skb->protocol == htons(ETH_P_8021AD))
                                          ? VLAN_HLEN : 0;
 
-               rx_udp_csum = udp_csum(skb);
-               iph = ip_hdr(skb);
-               csum = csum_tcpudp_magic(
-                               iph->saddr, iph->daddr,
-                               (skb->len - skb_transport_offset(skb)),
-                               IPPROTO_UDP, rx_udp_csum);
+               if ((ip_hdr(skb)->protocol == IPPROTO_UDP) &&
+                   (udp_hdr(skb)->check != 0)) {
+                       rx_udp_csum = udp_csum(skb);
+                       iph = ip_hdr(skb);
+                       csum = csum_tcpudp_magic(
+                                       iph->saddr, iph->daddr,
+                                       (skb->len - skb_transport_offset(skb)),
+                                       IPPROTO_UDP, rx_udp_csum);
 
-               if (udp_hdr(skb)->check != csum)
-                       goto checksum_fail;
+                       if (udp_hdr(skb)->check != csum)
+                               goto checksum_fail;
+
+               } /* else its GRE and so no outer UDP header */
        }
 
        skb->ip_summed = CHECKSUM_UNNECESSARY;
@@ -1581,6 +1618,7 @@ int i40e_napi_poll(struct napi_struct *napi, int budget)
        struct i40e_vsi *vsi = q_vector->vsi;
        struct i40e_ring *ring;
        bool clean_complete = true;
+       bool arm_wb = false;
        int budget_per_ring;
 
        if (test_bit(__I40E_DOWN, &vsi->state)) {
@@ -1591,8 +1629,10 @@ int i40e_napi_poll(struct napi_struct *napi, int budget)
        /* Since the actual Tx work is minimal, we can give the Tx a larger
         * budget and be more aggressive about cleaning up the Tx descriptors.
         */
-       i40e_for_each_ring(ring, q_vector->tx)
+       i40e_for_each_ring(ring, q_vector->tx) {
                clean_complete &= i40e_clean_tx_irq(ring, vsi->work_limit);
+               arm_wb |= ring->arm_wb;
+       }
 
        /* We attempt to distribute budget to each Rx queue fairly, but don't
         * allow the budget to go below 1 because that would exit polling early.
@@ -1603,8 +1643,11 @@ int i40e_napi_poll(struct napi_struct *napi, int budget)
                clean_complete &= i40e_clean_rx_irq(ring, budget_per_ring);
 
        /* If work not completed, return budget and polling will return */
-       if (!clean_complete)
+       if (!clean_complete) {
+               if (arm_wb)
+                       i40e_force_wb(vsi, q_vector);
                return budget;
+       }
 
        /* Work is done so exit the polling mode and re-enable the interrupt */
        napi_complete(napi);
@@ -1840,17 +1883,16 @@ static int i40e_tso(struct i40e_ring *tx_ring, struct sk_buff *skb,
        if (err < 0)
                return err;
 
-       if (protocol == htons(ETH_P_IP)) {
-               iph = skb->encapsulation ? inner_ip_hdr(skb) : ip_hdr(skb);
+       iph = skb->encapsulation ? inner_ip_hdr(skb) : ip_hdr(skb);
+       ipv6h = skb->encapsulation ? inner_ipv6_hdr(skb) : ipv6_hdr(skb);
+
+       if (iph->version == 4) {
                tcph = skb->encapsulation ? inner_tcp_hdr(skb) : tcp_hdr(skb);
                iph->tot_len = 0;
                iph->check = 0;
                tcph->check = ~csum_tcpudp_magic(iph->saddr, iph->daddr,
                                                 0, IPPROTO_TCP, 0);
-       } else if (skb_is_gso_v6(skb)) {
-
-               ipv6h = skb->encapsulation ? inner_ipv6_hdr(skb)
-                                          : ipv6_hdr(skb);
+       } else if (ipv6h->version == 6) {
                tcph = skb->encapsulation ? inner_tcp_hdr(skb) : tcp_hdr(skb);
                ipv6h->payload_len = 0;
                tcph->check = ~csum_ipv6_magic(&ipv6h->saddr, &ipv6h->daddr,
@@ -1946,13 +1988,9 @@ static void i40e_tx_enable_csum(struct sk_buff *skb, u32 tx_flags,
                                         I40E_TX_CTX_EXT_IP_IPV4_NO_CSUM;
                        }
                } else if (tx_flags & I40E_TX_FLAGS_IPV6) {
-                       if (tx_flags & I40E_TX_FLAGS_TSO) {
-                               *cd_tunneling |= I40E_TX_CTX_EXT_IP_IPV6;
+                       *cd_tunneling |= I40E_TX_CTX_EXT_IP_IPV6;
+                       if (tx_flags & I40E_TX_FLAGS_TSO)
                                ip_hdr(skb)->check = 0;
-                       } else {
-                               *cd_tunneling |=
-                                        I40E_TX_CTX_EXT_IP_IPV4_NO_CSUM;
-                       }
                }
 
                /* Now set the ctx descriptor fields */
@@ -1962,7 +2000,10 @@ static void i40e_tx_enable_csum(struct sk_buff *skb, u32 tx_flags,
                                   ((skb_inner_network_offset(skb) -
                                        skb_transport_offset(skb)) >> 1) <<
                                   I40E_TXD_CTX_QW0_NATLEN_SHIFT;
-
+               if (this_ip_hdr->version == 6) {
+                       tx_flags &= ~I40E_TX_FLAGS_IPV4;
+                       tx_flags |= I40E_TX_FLAGS_IPV6;
+               }
        } else {
                network_hdr_len = skb_network_header_len(skb);
                this_ip_hdr = ip_hdr(skb);
@@ -2198,7 +2239,6 @@ static void i40e_tx_map(struct i40e_ring *tx_ring, struct sk_buff *skb,
        /* Place RS bit on last descriptor of any packet that spans across the
         * 4th descriptor (WB_STRIDE aka 0x3) in a 64B cacheline.
         */
-#define WB_STRIDE 0x3
        if (((i & WB_STRIDE) != WB_STRIDE) &&
            (first <= &tx_ring->tx_bi[i]) &&
            (first >= &tx_ring->tx_bi[i & ~WB_STRIDE])) {
index e60d3accb2e2ec3f2992b056da718d633b978157..18b00231d2f117d714e7e1399aecba0061ead41a 100644 (file)
@@ -241,6 +241,7 @@ struct i40e_ring {
        unsigned long last_rx_timestamp;
 
        bool ring_active;               /* is ring online or not */
+       bool arm_wb;            /* do something to arm write back */
 
        /* stats structs */
        struct i40e_queue_stats stats;
index d0d6dc1b8e46e8173cbd61f5c2e84d4292301bc4..ac6a8f1eea6ca2dbaa94cce76cde89b85eda32c5 100644 (file)
@@ -475,7 +475,8 @@ static int mlx4_en_tunnel_steer_add(struct mlx4_en_priv *priv, unsigned char *ad
 {
        int err;
 
-       if (priv->mdev->dev->caps.tunnel_offload_mode != MLX4_TUNNEL_OFFLOAD_MODE_VXLAN)
+       if (priv->mdev->dev->caps.tunnel_offload_mode != MLX4_TUNNEL_OFFLOAD_MODE_VXLAN ||
+           priv->mdev->dev->caps.dmfs_high_steer_mode == MLX4_STEERING_DMFS_A0_STATIC)
                return 0; /* do nothing */
 
        err = mlx4_tunnel_steer_add(priv->mdev->dev, addr, priv->port, qpn,
index 03e9eb0dc761e00a6488583881deb91dfd610464..6e08352ec994df3d403b8a46699cb224aa9b6702 100644 (file)
@@ -1744,8 +1744,7 @@ static void choose_tunnel_offload_mode(struct mlx4_dev *dev,
                                       struct mlx4_dev_cap *dev_cap)
 {
        if (dev->caps.steering_mode == MLX4_STEERING_MODE_DEVICE_MANAGED &&
-           dev_cap->flags2 & MLX4_DEV_CAP_FLAG2_VXLAN_OFFLOADS &&
-           dev->caps.dmfs_high_steer_mode != MLX4_STEERING_DMFS_A0_STATIC)
+           dev_cap->flags2 & MLX4_DEV_CAP_FLAG2_VXLAN_OFFLOADS)
                dev->caps.tunnel_offload_mode = MLX4_TUNNEL_OFFLOAD_MODE_VXLAN;
        else
                dev->caps.tunnel_offload_mode = MLX4_TUNNEL_OFFLOAD_MODE_NONE;
index f5e4b820128ba8966e8a7d4ecdc9713e7982aa61..db0c7a9aee601d1241b0dcfcc267efa2469a4f0b 100644 (file)
@@ -6987,7 +6987,9 @@ static int s2io_add_isr(struct s2io_nic *sp)
                        if (sp->s2io_entries[i].in_use == MSIX_FLG) {
                                if (sp->s2io_entries[i].type ==
                                    MSIX_RING_TYPE) {
-                                       sprintf(sp->desc[i], "%s:MSI-X-%d-RX",
+                                       snprintf(sp->desc[i],
+                                               sizeof(sp->desc[i]),
+                                               "%s:MSI-X-%d-RX",
                                                dev->name, i);
                                        err = request_irq(sp->entries[i].vector,
                                                          s2io_msix_ring_handle,
@@ -6996,7 +6998,9 @@ static int s2io_add_isr(struct s2io_nic *sp)
                                                          sp->s2io_entries[i].arg);
                                } else if (sp->s2io_entries[i].type ==
                                           MSIX_ALARM_TYPE) {
-                                       sprintf(sp->desc[i], "%s:MSI-X-%d-TX",
+                                       snprintf(sp->desc[i],
+                                               sizeof(sp->desc[i]),
+                                               "%s:MSI-X-%d-TX",
                                                dev->name, i);
                                        err = request_irq(sp->entries[i].vector,
                                                          s2io_msix_fifo_handle,
@@ -8154,7 +8158,8 @@ s2io_init_nic(struct pci_dev *pdev, const struct pci_device_id *pre)
                          "%s: UDP Fragmentation Offload(UFO) enabled\n",
                          dev->name);
        /* Initialize device name */
-       sprintf(sp->name, "%s Neterion %s", dev->name, sp->product_name);
+       snprintf(sp->name, sizeof(sp->name), "%s Neterion %s", dev->name,
+                sp->product_name);
 
        if (vlan_tag_strip)
                sp->vlan_strip_flag = 1;
index c29ba80ae02bfde60f41f4118c02bab642303b89..6576243222af74f593419e6e338cdd9387b949af 100644 (file)
@@ -473,6 +473,7 @@ static struct sh_eth_cpu_data r8a777x_data = {
        .eesr_err_check = EESR_TWB | EESR_TABT | EESR_RABT | EESR_RFE |
                          EESR_RDE | EESR_RFRMER | EESR_TFE | EESR_TDE |
                          EESR_ECI,
+       .fdr_value      = 0x00000f0f,
 
        .apr            = 1,
        .mpr            = 1,
@@ -495,6 +496,9 @@ static struct sh_eth_cpu_data r8a779x_data = {
        .eesr_err_check = EESR_TWB | EESR_TABT | EESR_RABT | EESR_RFE |
                          EESR_RDE | EESR_RFRMER | EESR_TFE | EESR_TDE |
                          EESR_ECI,
+       .fdr_value      = 0x00000f0f,
+
+       .trscer_err_mask = DESC_I_RINT8,
 
        .apr            = 1,
        .mpr            = 1,
@@ -856,6 +860,9 @@ static void sh_eth_set_default_cpu_data(struct sh_eth_cpu_data *cd)
 
        if (!cd->eesr_err_check)
                cd->eesr_err_check = DEFAULT_EESR_ERR_CHECK;
+
+       if (!cd->trscer_err_mask)
+               cd->trscer_err_mask = DEFAULT_TRSCER_ERR_MASK;
 }
 
 static int sh_eth_check_reset(struct net_device *ndev)
@@ -1294,7 +1301,7 @@ static int sh_eth_dev_init(struct net_device *ndev, bool start)
        /* Frame recv control (enable multiple-packets per rx irq) */
        sh_eth_write(ndev, RMCR_RNC, RMCR);
 
-       sh_eth_write(ndev, DESC_I_RINT8 | DESC_I_RINT5 | DESC_I_TINT2, TRSCER);
+       sh_eth_write(ndev, mdp->cd->trscer_err_mask, TRSCER);
 
        if (mdp->cd->bculr)
                sh_eth_write(ndev, 0x800, BCULR);       /* Burst sycle set */
@@ -1820,6 +1827,9 @@ static int sh_eth_get_settings(struct net_device *ndev,
        unsigned long flags;
        int ret;
 
+       if (!mdp->phydev)
+               return -ENODEV;
+
        spin_lock_irqsave(&mdp->lock, flags);
        ret = phy_ethtool_gset(mdp->phydev, ecmd);
        spin_unlock_irqrestore(&mdp->lock, flags);
@@ -1834,6 +1844,9 @@ static int sh_eth_set_settings(struct net_device *ndev,
        unsigned long flags;
        int ret;
 
+       if (!mdp->phydev)
+               return -ENODEV;
+
        spin_lock_irqsave(&mdp->lock, flags);
 
        /* disable tx and rx */
@@ -1868,6 +1881,9 @@ static int sh_eth_nway_reset(struct net_device *ndev)
        unsigned long flags;
        int ret;
 
+       if (!mdp->phydev)
+               return -ENODEV;
+
        spin_lock_irqsave(&mdp->lock, flags);
        ret = phy_start_aneg(mdp->phydev);
        spin_unlock_irqrestore(&mdp->lock, flags);
@@ -2177,6 +2193,7 @@ static int sh_eth_close(struct net_device *ndev)
        if (mdp->phydev) {
                phy_stop(mdp->phydev);
                phy_disconnect(mdp->phydev);
+               mdp->phydev = NULL;
        }
 
        free_irq(ndev->irq, ndev);
@@ -2410,7 +2427,7 @@ static int sh_eth_tsu_purge_all(struct net_device *ndev)
        struct sh_eth_private *mdp = netdev_priv(ndev);
        int i, ret;
 
-       if (unlikely(!mdp->cd->tsu))
+       if (!mdp->cd->tsu)
                return 0;
 
        for (i = 0; i < SH_ETH_TSU_CAM_ENTRIES; i++) {
@@ -2433,7 +2450,7 @@ static void sh_eth_tsu_purge_mcast(struct net_device *ndev)
        void *reg_offset = sh_eth_tsu_get_offset(mdp, TSU_ADRH0);
        int i;
 
-       if (unlikely(!mdp->cd->tsu))
+       if (!mdp->cd->tsu)
                return;
 
        for (i = 0; i < SH_ETH_TSU_CAM_ENTRIES; i++, reg_offset += 8) {
@@ -2443,8 +2460,8 @@ static void sh_eth_tsu_purge_mcast(struct net_device *ndev)
        }
 }
 
-/* Multicast reception directions set */
-static void sh_eth_set_multicast_list(struct net_device *ndev)
+/* Update promiscuous flag and multicast filter */
+static void sh_eth_set_rx_mode(struct net_device *ndev)
 {
        struct sh_eth_private *mdp = netdev_priv(ndev);
        u32 ecmr_bits;
@@ -2455,7 +2472,9 @@ static void sh_eth_set_multicast_list(struct net_device *ndev)
        /* Initial condition is MCT = 1, PRM = 0.
         * Depending on ndev->flags, set PRM or clear MCT
         */
-       ecmr_bits = (sh_eth_read(ndev, ECMR) & ~ECMR_PRM) | ECMR_MCT;
+       ecmr_bits = sh_eth_read(ndev, ECMR) & ~ECMR_PRM;
+       if (mdp->cd->tsu)
+               ecmr_bits |= ECMR_MCT;
 
        if (!(ndev->flags & IFF_MULTICAST)) {
                sh_eth_tsu_purge_mcast(ndev);
@@ -2484,9 +2503,6 @@ static void sh_eth_set_multicast_list(struct net_device *ndev)
                                }
                        }
                }
-       } else {
-               /* Normal, unicast/broadcast-only mode. */
-               ecmr_bits = (ecmr_bits & ~ECMR_PRM) | ECMR_MCT;
        }
 
        /* update the ethernet mode */
@@ -2694,6 +2710,7 @@ static const struct net_device_ops sh_eth_netdev_ops = {
        .ndo_stop               = sh_eth_close,
        .ndo_start_xmit         = sh_eth_start_xmit,
        .ndo_get_stats          = sh_eth_get_stats,
+       .ndo_set_rx_mode        = sh_eth_set_rx_mode,
        .ndo_tx_timeout         = sh_eth_tx_timeout,
        .ndo_do_ioctl           = sh_eth_do_ioctl,
        .ndo_validate_addr      = eth_validate_addr,
@@ -2706,7 +2723,7 @@ static const struct net_device_ops sh_eth_netdev_ops_tsu = {
        .ndo_stop               = sh_eth_close,
        .ndo_start_xmit         = sh_eth_start_xmit,
        .ndo_get_stats          = sh_eth_get_stats,
-       .ndo_set_rx_mode        = sh_eth_set_multicast_list,
+       .ndo_set_rx_mode        = sh_eth_set_rx_mode,
        .ndo_vlan_rx_add_vid    = sh_eth_vlan_rx_add_vid,
        .ndo_vlan_rx_kill_vid   = sh_eth_vlan_rx_kill_vid,
        .ndo_tx_timeout         = sh_eth_tx_timeout,
index 22301bf9c21daeb925d75aa7ce5c7a588d977e11..71f5de1171bd93d004beacf880c387a4168eaada 100644 (file)
@@ -369,6 +369,8 @@ enum DESC_I_BIT {
        DESC_I_RINT1 = 0x0001,
 };
 
+#define DEFAULT_TRSCER_ERR_MASK (DESC_I_RINT8 | DESC_I_RINT5 | DESC_I_TINT2)
+
 /* RPADIR */
 enum RPADIR_BIT {
        RPADIR_PADS1 = 0x20000, RPADIR_PADS0 = 0x10000,
@@ -470,6 +472,9 @@ struct sh_eth_cpu_data {
        unsigned long tx_check;
        unsigned long eesr_err_check;
 
+       /* Error mask */
+       unsigned long trscer_err_mask;
+
        /* hardware features */
        unsigned long irq_flags; /* IRQ configuration flags */
        unsigned no_psr:1;      /* EtherC DO NOT have PSR */
index 698494481d18072ca00ddecb825ea92bd4e86c56..b1a271853d8556a08592e2a89e8b5a5f7cb8ba67 100644 (file)
@@ -474,13 +474,19 @@ static int init_rx_ring(struct net_device *dev, u8 queue_no,
        /* allocate memory for RX skbuff array */
        rx_ring->rx_skbuff_dma = kmalloc_array(rx_rsize,
                                               sizeof(dma_addr_t), GFP_KERNEL);
-       if (rx_ring->rx_skbuff_dma == NULL)
-               goto dmamem_err;
+       if (!rx_ring->rx_skbuff_dma) {
+               dma_free_coherent(priv->device,
+                                 rx_rsize * sizeof(struct sxgbe_rx_norm_desc),
+                                 rx_ring->dma_rx, rx_ring->dma_rx_phy);
+               goto error;
+       }
 
        rx_ring->rx_skbuff = kmalloc_array(rx_rsize,
                                           sizeof(struct sk_buff *), GFP_KERNEL);
-       if (rx_ring->rx_skbuff == NULL)
-               goto rxbuff_err;
+       if (!rx_ring->rx_skbuff) {
+               kfree(rx_ring->rx_skbuff_dma);
+               goto error;
+       }
 
        /* initialise the buffers */
        for (desc_index = 0; desc_index < rx_rsize; desc_index++) {
@@ -502,13 +508,6 @@ static int init_rx_ring(struct net_device *dev, u8 queue_no,
 err_init_rx_buffers:
        while (--desc_index >= 0)
                free_rx_ring(priv->device, rx_ring, desc_index);
-       kfree(rx_ring->rx_skbuff);
-rxbuff_err:
-       kfree(rx_ring->rx_skbuff_dma);
-dmamem_err:
-       dma_free_coherent(priv->device,
-                         rx_rsize * sizeof(struct sxgbe_rx_norm_desc),
-                         rx_ring->dma_rx, rx_ring->dma_rx_phy);
 error:
        return -ENOMEM;
 }
index 866560ea9e180d115513eead6d5b2a3bc1754f7b..b02eed12bfc5743117285216db1b4fe6ba19536e 100644 (file)
@@ -108,10 +108,6 @@ static int sxgbe_platform_probe(struct platform_device *pdev)
                }
        }
 
-       /* Get MAC address if available (DT) */
-       if (mac)
-               ether_addr_copy(priv->dev->dev_addr, mac);
-
        priv = sxgbe_drv_probe(&(pdev->dev), plat_dat, addr);
        if (!priv) {
                pr_err("%s: main driver probe failed\n", __func__);
@@ -125,6 +121,10 @@ static int sxgbe_platform_probe(struct platform_device *pdev)
                goto err_drv_remove;
        }
 
+       /* Get MAC address if available (DT) */
+       if (mac)
+               ether_addr_copy(priv->dev->dev_addr, mac);
+
        /* Get the TX/RX IRQ numbers */
        for (i = 0, chan = 1; i < SXGBE_TX_QUEUES; i++) {
                priv->txq[i]->irq_no = irq_of_parse_and_map(node, chan++);
index e61ee8351272bceda3c98a8fb21fcb216c6f56bb..e068d48b0f21f713e3537fdf293741c2c7526baa 100644 (file)
@@ -610,7 +610,7 @@ static void cpsw_set_promiscious(struct net_device *ndev, bool enable)
 
                        /* Clear all mcast from ALE */
                        cpsw_ale_flush_multicast(ale, ALE_ALL_PORTS <<
-                                                priv->host_port);
+                                                priv->host_port, -1);
 
                        /* Flood All Unicast Packets to Host port */
                        cpsw_ale_control_set(ale, 0, ALE_P0_UNI_FLOOD, 1);
@@ -634,6 +634,12 @@ static void cpsw_set_promiscious(struct net_device *ndev, bool enable)
 static void cpsw_ndo_set_rx_mode(struct net_device *ndev)
 {
        struct cpsw_priv *priv = netdev_priv(ndev);
+       int vid;
+
+       if (priv->data.dual_emac)
+               vid = priv->slaves[priv->emac_port].port_vlan;
+       else
+               vid = priv->data.default_vlan;
 
        if (ndev->flags & IFF_PROMISC) {
                /* Enable promiscuous mode */
@@ -649,7 +655,8 @@ static void cpsw_ndo_set_rx_mode(struct net_device *ndev)
        cpsw_ale_set_allmulti(priv->ale, priv->ndev->flags & IFF_ALLMULTI);
 
        /* Clear all mcast from ALE */
-       cpsw_ale_flush_multicast(priv->ale, ALE_ALL_PORTS << priv->host_port);
+       cpsw_ale_flush_multicast(priv->ale, ALE_ALL_PORTS << priv->host_port,
+                                vid);
 
        if (!netdev_mc_empty(ndev)) {
                struct netdev_hw_addr *ha;
@@ -1627,16 +1634,24 @@ static inline int cpsw_add_vlan_ale_entry(struct cpsw_priv *priv,
                                unsigned short vid)
 {
        int ret;
-       int unreg_mcast_mask;
+       int unreg_mcast_mask = 0;
+       u32 port_mask;
 
-       if (priv->ndev->flags & IFF_ALLMULTI)
-               unreg_mcast_mask = ALE_ALL_PORTS;
-       else
-               unreg_mcast_mask = ALE_PORT_1 | ALE_PORT_2;
+       if (priv->data.dual_emac) {
+               port_mask = (1 << (priv->emac_port + 1)) | ALE_PORT_HOST;
+
+               if (priv->ndev->flags & IFF_ALLMULTI)
+                       unreg_mcast_mask = port_mask;
+       } else {
+               port_mask = ALE_ALL_PORTS;
+
+               if (priv->ndev->flags & IFF_ALLMULTI)
+                       unreg_mcast_mask = ALE_ALL_PORTS;
+               else
+                       unreg_mcast_mask = ALE_PORT_1 | ALE_PORT_2;
+       }
 
-       ret = cpsw_ale_add_vlan(priv->ale, vid,
-                               ALE_ALL_PORTS << priv->host_port,
-                               0, ALE_ALL_PORTS << priv->host_port,
+       ret = cpsw_ale_add_vlan(priv->ale, vid, port_mask, 0, port_mask,
                                unreg_mcast_mask << priv->host_port);
        if (ret != 0)
                return ret;
@@ -1647,8 +1662,7 @@ static inline int cpsw_add_vlan_ale_entry(struct cpsw_priv *priv,
                goto clean_vid;
 
        ret = cpsw_ale_add_mcast(priv->ale, priv->ndev->broadcast,
-                                ALE_ALL_PORTS << priv->host_port,
-                                ALE_VLAN, vid, 0);
+                                port_mask, ALE_VLAN, vid, 0);
        if (ret != 0)
                goto clean_vlan_ucast;
        return 0;
index 097ebe7077ac0c8de51e3eb7e8da5809f5e6bcea..5246b3a18ff86e8494d30db90c6154ba9f7ed25f 100644 (file)
@@ -234,7 +234,7 @@ static void cpsw_ale_flush_mcast(struct cpsw_ale *ale, u32 *ale_entry,
                cpsw_ale_set_entry_type(ale_entry, ALE_TYPE_FREE);
 }
 
-int cpsw_ale_flush_multicast(struct cpsw_ale *ale, int port_mask)
+int cpsw_ale_flush_multicast(struct cpsw_ale *ale, int port_mask, int vid)
 {
        u32 ale_entry[ALE_ENTRY_WORDS];
        int ret, idx;
@@ -245,6 +245,14 @@ int cpsw_ale_flush_multicast(struct cpsw_ale *ale, int port_mask)
                if (ret != ALE_TYPE_ADDR && ret != ALE_TYPE_VLAN_ADDR)
                        continue;
 
+               /* if vid passed is -1 then remove all multicast entry from
+                * the table irrespective of vlan id, if a valid vlan id is
+                * passed then remove only multicast added to that vlan id.
+                * if vlan id doesn't match then move on to next entry.
+                */
+               if (vid != -1 && cpsw_ale_get_vlan_id(ale_entry) != vid)
+                       continue;
+
                if (cpsw_ale_get_mcast(ale_entry)) {
                        u8 addr[6];
 
index c0d4127aa549285c7e50e47214c1579e17478210..af1e7ecd87c6fbd24b80954c7977e96aa3676a0c 100644 (file)
@@ -92,7 +92,7 @@ void cpsw_ale_stop(struct cpsw_ale *ale);
 
 int cpsw_ale_set_ageout(struct cpsw_ale *ale, int ageout);
 int cpsw_ale_flush(struct cpsw_ale *ale, int port_mask);
-int cpsw_ale_flush_multicast(struct cpsw_ale *ale, int port_mask);
+int cpsw_ale_flush_multicast(struct cpsw_ale *ale, int port_mask, int vid);
 int cpsw_ale_add_ucast(struct cpsw_ale *ale, u8 *addr, int port,
                       int flags, u16 vid);
 int cpsw_ale_del_ucast(struct cpsw_ale *ale, u8 *addr, int port,
index ea712512c7d1f5e155129bf073cac1d7381d38bb..5fae4354722c040308190d4ca9c3664cfbdd7113 100644 (file)
@@ -62,6 +62,7 @@
 #include <linux/of.h>
 #include <linux/of_address.h>
 #include <linux/of_device.h>
+#include <linux/of_mdio.h>
 #include <linux/of_irq.h>
 #include <linux/of_net.h>
 
@@ -343,9 +344,7 @@ struct emac_priv {
        u32 multicast_hash_cnt[EMAC_NUM_MULTICAST_BITS];
        u32 rx_addr_type;
        const char *phy_id;
-#ifdef CONFIG_OF
        struct device_node *phy_node;
-#endif
        struct phy_device *phydev;
        spinlock_t lock;
        /*platform specific members*/
@@ -922,6 +921,16 @@ static void emac_int_disable(struct emac_priv *priv)
                if (priv->int_disable)
                        priv->int_disable();
 
+               /* NOTE: Rx Threshold and Misc interrupts are not enabled */
+
+               /* ack rxen only then a new pulse will be generated */
+               emac_write(EMAC_DM646X_MACEOIVECTOR,
+                       EMAC_DM646X_MAC_EOI_C0_RXEN);
+
+               /* ack txen- only then a new pulse will be generated */
+               emac_write(EMAC_DM646X_MACEOIVECTOR,
+                       EMAC_DM646X_MAC_EOI_C0_TXEN);
+
                local_irq_restore(flags);
 
        } else {
@@ -951,15 +960,6 @@ static void emac_int_enable(struct emac_priv *priv)
                 * register */
 
                /* NOTE: Rx Threshold and Misc interrupts are not enabled */
-
-               /* ack rxen only then a new pulse will be generated */
-               emac_write(EMAC_DM646X_MACEOIVECTOR,
-                       EMAC_DM646X_MAC_EOI_C0_RXEN);
-
-               /* ack txen- only then a new pulse will be generated */
-               emac_write(EMAC_DM646X_MACEOIVECTOR,
-                       EMAC_DM646X_MAC_EOI_C0_TXEN);
-
        } else {
                /* Set DM644x control registers for interrupt control */
                emac_ctrl_write(EMAC_CTRL_EWCTL, 0x1);
@@ -1537,7 +1537,13 @@ static int emac_dev_open(struct net_device *ndev)
        int i = 0;
        struct emac_priv *priv = netdev_priv(ndev);
 
-       pm_runtime_get(&priv->pdev->dev);
+       ret = pm_runtime_get_sync(&priv->pdev->dev);
+       if (ret < 0) {
+               pm_runtime_put_noidle(&priv->pdev->dev);
+               dev_err(&priv->pdev->dev, "%s: failed to get_sync(%d)\n",
+                       __func__, ret);
+               return ret;
+       }
 
        netif_carrier_off(ndev);
        for (cnt = 0; cnt < ETH_ALEN; cnt++)
@@ -1596,8 +1602,20 @@ static int emac_dev_open(struct net_device *ndev)
        cpdma_ctlr_start(priv->dma);
 
        priv->phydev = NULL;
+
+       if (priv->phy_node) {
+               priv->phydev = of_phy_connect(ndev, priv->phy_node,
+                                             &emac_adjust_link, 0, 0);
+               if (!priv->phydev) {
+                       dev_err(emac_dev, "could not connect to phy %s\n",
+                               priv->phy_node->full_name);
+                       ret = -ENODEV;
+                       goto err;
+               }
+       }
+
        /* use the first phy on the bus if pdata did not give us a phy id */
-       if (!priv->phy_id) {
+       if (!priv->phydev && !priv->phy_id) {
                struct device *phy;
 
                phy = bus_find_device(&mdio_bus_type, NULL, NULL,
@@ -1606,7 +1624,7 @@ static int emac_dev_open(struct net_device *ndev)
                        priv->phy_id = dev_name(phy);
        }
 
-       if (priv->phy_id && *priv->phy_id) {
+       if (!priv->phydev && priv->phy_id && *priv->phy_id) {
                priv->phydev = phy_connect(ndev, priv->phy_id,
                                           &emac_adjust_link,
                                           PHY_INTERFACE_MODE_MII);
@@ -1627,7 +1645,9 @@ static int emac_dev_open(struct net_device *ndev)
                        "(mii_bus:phy_addr=%s, id=%x)\n",
                        priv->phydev->drv->name, dev_name(&priv->phydev->dev),
                        priv->phydev->phy_id);
-       } else {
+       }
+
+       if (!priv->phydev) {
                /* No PHY , fix the link, speed and duplex settings */
                dev_notice(emac_dev, "no phy, defaulting to 100/full\n");
                priv->link = 1;
@@ -1724,6 +1744,15 @@ static struct net_device_stats *emac_dev_getnetstats(struct net_device *ndev)
        struct emac_priv *priv = netdev_priv(ndev);
        u32 mac_control;
        u32 stats_clear_mask;
+       int err;
+
+       err = pm_runtime_get_sync(&priv->pdev->dev);
+       if (err < 0) {
+               pm_runtime_put_noidle(&priv->pdev->dev);
+               dev_err(&priv->pdev->dev, "%s: failed to get_sync(%d)\n",
+                       __func__, err);
+               return &ndev->stats;
+       }
 
        /* update emac hardware stats and reset the registers*/
 
@@ -1766,6 +1795,8 @@ static struct net_device_stats *emac_dev_getnetstats(struct net_device *ndev)
        ndev->stats.tx_fifo_errors += emac_read(EMAC_TXUNDERRUN);
        emac_write(EMAC_TXUNDERRUN, stats_clear_mask);
 
+       pm_runtime_put(&priv->pdev->dev);
+
        return &ndev->stats;
 }
 
@@ -1859,7 +1890,7 @@ davinci_emac_of_get_pdata(struct platform_device *pdev, struct emac_priv *priv)
 static int davinci_emac_probe(struct platform_device *pdev)
 {
        int rc = 0;
-       struct resource *res;
+       struct resource *res, *res_ctrl;
        struct net_device *ndev;
        struct emac_priv *priv;
        unsigned long hw_ram_addr;
@@ -1876,6 +1907,7 @@ static int davinci_emac_probe(struct platform_device *pdev)
                return -EBUSY;
        }
        emac_bus_frequency = clk_get_rate(emac_clk);
+       devm_clk_put(&pdev->dev, emac_clk);
 
        /* TODO: Probe PHY here if possible */
 
@@ -1917,11 +1949,20 @@ static int davinci_emac_probe(struct platform_device *pdev)
                rc = PTR_ERR(priv->remap_addr);
                goto no_pdata;
        }
+
+       res_ctrl = platform_get_resource(pdev, IORESOURCE_MEM, 1);
+       if (res_ctrl) {
+               priv->ctrl_base =
+                       devm_ioremap_resource(&pdev->dev, res_ctrl);
+               if (IS_ERR(priv->ctrl_base))
+                       goto no_pdata;
+       } else {
+               priv->ctrl_base = priv->remap_addr + pdata->ctrl_mod_reg_offset;
+       }
+
        priv->emac_base = priv->remap_addr + pdata->ctrl_reg_offset;
        ndev->base_addr = (unsigned long)priv->remap_addr;
 
-       priv->ctrl_base = priv->remap_addr + pdata->ctrl_mod_reg_offset;
-
        hw_ram_addr = pdata->hw_ram_addr;
        if (!hw_ram_addr)
                hw_ram_addr = (u32 __force)res->start + pdata->ctrl_ram_offset;
@@ -1980,12 +2021,22 @@ static int davinci_emac_probe(struct platform_device *pdev)
        ndev->ethtool_ops = &ethtool_ops;
        netif_napi_add(ndev, &priv->napi, emac_poll, EMAC_POLL_WEIGHT);
 
+       pm_runtime_enable(&pdev->dev);
+       rc = pm_runtime_get_sync(&pdev->dev);
+       if (rc < 0) {
+               pm_runtime_put_noidle(&pdev->dev);
+               dev_err(&pdev->dev, "%s: failed to get_sync(%d)\n",
+                       __func__, rc);
+               goto no_cpdma_chan;
+       }
+
        /* register the network device */
        SET_NETDEV_DEV(ndev, &pdev->dev);
        rc = register_netdev(ndev);
        if (rc) {
                dev_err(&pdev->dev, "error in register_netdev\n");
                rc = -ENODEV;
+               pm_runtime_put(&pdev->dev);
                goto no_cpdma_chan;
        }
 
@@ -1995,9 +2046,7 @@ static int davinci_emac_probe(struct platform_device *pdev)
                           "(regs: %p, irq: %d)\n",
                           (void *)priv->emac_base_phys, ndev->irq);
        }
-
-       pm_runtime_enable(&pdev->dev);
-       pm_runtime_resume(&pdev->dev);
+       pm_runtime_put(&pdev->dev);
 
        return 0;
 
@@ -2071,9 +2120,14 @@ static const struct emac_platform_data am3517_emac_data = {
        .hw_ram_addr            = 0x01e20000,
 };
 
+static const struct emac_platform_data dm816_emac_data = {
+       .version                = EMAC_VERSION_2,
+};
+
 static const struct of_device_id davinci_emac_of_match[] = {
        {.compatible = "ti,davinci-dm6467-emac", },
        {.compatible = "ti,am3517-emac", .data = &am3517_emac_data, },
+       {.compatible = "ti,dm816-emac", .data = &dm816_emac_data, },
        {},
 };
 MODULE_DEVICE_TABLE(of, davinci_emac_of_match);
index 93e224217e24b36b089102be11ada5921f62d83b..f7ff493f1e73dfa129dbb10ed68c6436c52a4b1b 100644 (file)
@@ -629,6 +629,7 @@ static int team_change_mode(struct team *team, const char *kind)
 static void team_notify_peers_work(struct work_struct *work)
 {
        struct team *team;
+       int val;
 
        team = container_of(work, struct team, notify_peers.dw.work);
 
@@ -636,9 +637,14 @@ static void team_notify_peers_work(struct work_struct *work)
                schedule_delayed_work(&team->notify_peers.dw, 0);
                return;
        }
+       val = atomic_dec_if_positive(&team->notify_peers.count_pending);
+       if (val < 0) {
+               rtnl_unlock();
+               return;
+       }
        call_netdevice_notifiers(NETDEV_NOTIFY_PEERS, team->dev);
        rtnl_unlock();
-       if (!atomic_dec_and_test(&team->notify_peers.count_pending))
+       if (val)
                schedule_delayed_work(&team->notify_peers.dw,
                                      msecs_to_jiffies(team->notify_peers.interval));
 }
@@ -669,6 +675,7 @@ static void team_notify_peers_fini(struct team *team)
 static void team_mcast_rejoin_work(struct work_struct *work)
 {
        struct team *team;
+       int val;
 
        team = container_of(work, struct team, mcast_rejoin.dw.work);
 
@@ -676,9 +683,14 @@ static void team_mcast_rejoin_work(struct work_struct *work)
                schedule_delayed_work(&team->mcast_rejoin.dw, 0);
                return;
        }
+       val = atomic_dec_if_positive(&team->mcast_rejoin.count_pending);
+       if (val < 0) {
+               rtnl_unlock();
+               return;
+       }
        call_netdevice_notifiers(NETDEV_RESEND_IGMP, team->dev);
        rtnl_unlock();
-       if (!atomic_dec_and_test(&team->mcast_rejoin.count_pending))
+       if (val)
                schedule_delayed_work(&team->mcast_rejoin.dw,
                                      msecs_to_jiffies(team->mcast_rejoin.interval));
 }
index dcb6d33141e0640f545555848434d8efd7822878..1e9cdca370144cffb22141e4c03aa3ff800aefdd 100644 (file)
@@ -1276,7 +1276,7 @@ static int usb_start_wait_urb(struct urb *urb, int timeout, int* actual_length)
         awd.done = 0;
 
         urb->context = &awd;
-        status = usb_submit_urb(urb, GFP_NOIO);
+        status = usb_submit_urb(urb, GFP_ATOMIC);
         if (status) {
                 // something went wrong
                 usb_free_urb(urb);
index 57ec23e8ccfa4396610bb7bbfe99ec68145cdc12..bf405f134d3aa69c60006536da0419f4a2b1f06b 100644 (file)
@@ -833,9 +833,6 @@ static void ocp_write_word(struct r8152 *tp, u16 type, u16 index, u32 data)
                index &= ~3;
        }
 
-       generic_ocp_read(tp, index, sizeof(tmp), &tmp, type);
-
-       data |= __le32_to_cpu(tmp) & ~mask;
        tmp = __cpu_to_le32(data);
 
        generic_ocp_write(tp, index, byen, sizeof(tmp), &tmp, type);
@@ -874,9 +871,6 @@ static void ocp_write_byte(struct r8152 *tp, u16 type, u16 index, u32 data)
                index &= ~3;
        }
 
-       generic_ocp_read(tp, index, sizeof(tmp), &tmp, type);
-
-       data |= __le32_to_cpu(tmp) & ~mask;
        tmp = __cpu_to_le32(data);
 
        generic_ocp_write(tp, index, byen, sizeof(tmp), &tmp, type);
@@ -926,12 +920,6 @@ static void sram_write(struct r8152 *tp, u16 addr, u16 data)
        ocp_reg_write(tp, OCP_SRAM_DATA, data);
 }
 
-static u16 sram_read(struct r8152 *tp, u16 addr)
-{
-       ocp_reg_write(tp, OCP_SRAM_ADDR, addr);
-       return ocp_reg_read(tp, OCP_SRAM_DATA);
-}
-
 static int read_mii_word(struct net_device *netdev, int phy_id, int reg)
 {
        struct r8152 *tp = netdev_priv(netdev);
@@ -2518,24 +2506,18 @@ static void r8153_hw_phy_cfg(struct r8152 *tp)
        data = ocp_reg_read(tp, OCP_POWER_CFG);
        data |= EN_10M_PLLOFF;
        ocp_reg_write(tp, OCP_POWER_CFG, data);
-       data = sram_read(tp, SRAM_IMPEDANCE);
-       data &= ~RX_DRIVING_MASK;
-       sram_write(tp, SRAM_IMPEDANCE, data);
+       sram_write(tp, SRAM_IMPEDANCE, 0x0b13);
 
        ocp_data = ocp_read_word(tp, MCU_TYPE_PLA, PLA_PHY_PWR);
        ocp_data |= PFM_PWM_SWITCH;
        ocp_write_word(tp, MCU_TYPE_PLA, PLA_PHY_PWR, ocp_data);
 
-       data = sram_read(tp, SRAM_LPF_CFG);
-       data |= LPF_AUTO_TUNE;
-       sram_write(tp, SRAM_LPF_CFG, data);
+       /* Enable LPF corner auto tune */
+       sram_write(tp, SRAM_LPF_CFG, 0xf70f);
 
-       data = sram_read(tp, SRAM_10M_AMP1);
-       data |= GDAC_IB_UPALL;
-       sram_write(tp, SRAM_10M_AMP1, data);
-       data = sram_read(tp, SRAM_10M_AMP2);
-       data |= AMP_DN;
-       sram_write(tp, SRAM_10M_AMP2, data);
+       /* Adjust 10M Amplitude */
+       sram_write(tp, SRAM_10M_AMP1, 0x00af);
+       sram_write(tp, SRAM_10M_AMP2, 0x0208);
 
        set_bit(PHY_RESET, &tp->flags);
 }
index e5be2d21868fa975619b72fb8217cad0f54cefe6..a5f9198d57473e6ab18966ca58ec88047f4428dc 100644 (file)
@@ -69,8 +69,8 @@
 #include "iwl-agn-hw.h"
 
 /* Highest firmware API version supported */
-#define IWL7260_UCODE_API_MAX  10
-#define IWL3160_UCODE_API_MAX  10
+#define IWL7260_UCODE_API_MAX  12
+#define IWL3160_UCODE_API_MAX  12
 
 /* Oldest version we won't warn about */
 #define IWL7260_UCODE_API_OK   10
 #define IWL7265_MODULE_FIRMWARE(api) IWL7265_FW_PRE __stringify(api) ".ucode"
 
 #define IWL7265D_FW_PRE "iwlwifi-7265D-"
-#define IWL7265D_MODULE_FIRMWARE(api) IWL7265_FW_PRE __stringify(api) ".ucode"
+#define IWL7265D_MODULE_FIRMWARE(api) IWL7265D_FW_PRE __stringify(api) ".ucode"
 
 #define NVM_HW_SECTION_NUM_FAMILY_7000         0
 
index bf0a95cb71535f390dfcfcc5820d39901359d440..3668fc57e7708be5e655353078f0bb44589ad6a1 100644 (file)
@@ -69,7 +69,7 @@
 #include "iwl-agn-hw.h"
 
 /* Highest firmware API version supported */
-#define IWL8000_UCODE_API_MAX  10
+#define IWL8000_UCODE_API_MAX  12
 
 /* Oldest version we won't warn about */
 #define IWL8000_UCODE_API_OK   10
index f2a047f6bb3e519a6ab3ce3032be18aac3aa9aa9..1bbe4fc47b97bcbcd4c828ce094f487c81edd357 100644 (file)
@@ -243,6 +243,9 @@ enum iwl_ucode_tlv_flag {
  * @IWL_UCODE_TLV_API_SF_NO_DUMMY_NOTIF: ucode supports disabling dummy notif.
  * @IWL_UCODE_TLV_API_FRAGMENTED_SCAN: This ucode supports active dwell time
  *     longer than the passive one, which is essential for fragmented scan.
+ * @IWL_UCODE_TLV_API_BASIC_DWELL: use only basic dwell time in scan command,
+ *     regardless of the band or the number of the probes. FW will calculate
+ *     the actual dwell time.
  */
 enum iwl_ucode_tlv_api {
        IWL_UCODE_TLV_API_WOWLAN_CONFIG_TID     = BIT(0),
@@ -253,6 +256,7 @@ enum iwl_ucode_tlv_api {
        IWL_UCODE_TLV_API_LMAC_SCAN             = BIT(6),
        IWL_UCODE_TLV_API_SF_NO_DUMMY_NOTIF     = BIT(7),
        IWL_UCODE_TLV_API_FRAGMENTED_SCAN       = BIT(8),
+       IWL_UCODE_TLV_API_BASIC_DWELL           = BIT(13),
 };
 
 /**
index 1f2acf47bfb2c78ddb1ee623f9254e35fa8eb109..201846de94e7d949819afacd8f5bac3d9379a6ec 100644 (file)
@@ -672,6 +672,7 @@ struct iwl_scan_channel_opt {
  * @IWL_MVM_LMAC_SCAN_FLAG_FRAGMENTED: all passive scans will be fragmented
  * @IWL_MVM_LMAC_SCAN_FLAGS_RRM_ENABLED: insert WFA vendor-specific TPC report
  *     and DS parameter set IEs into probe requests.
+ * @IWL_MVM_LMAC_SCAN_FLAG_MATCH: Send match found notification on matches
  */
 enum iwl_mvm_lmac_scan_flags {
        IWL_MVM_LMAC_SCAN_FLAG_PASS_ALL         = BIT(0),
@@ -681,6 +682,7 @@ enum iwl_mvm_lmac_scan_flags {
        IWL_MVM_LMAC_SCAN_FLAG_MULTIPLE_SSIDS   = BIT(4),
        IWL_MVM_LMAC_SCAN_FLAG_FRAGMENTED       = BIT(5),
        IWL_MVM_LMAC_SCAN_FLAGS_RRM_ENABLED     = BIT(6),
+       IWL_MVM_LMAC_SCAN_FLAG_MATCH            = BIT(9),
 };
 
 enum iwl_scan_priority {
index e5294d01181e404c44d78190df5ae869d8c0cd21..ec9a8e7bae1de2934d9fddcd26e7d4b481cdafb9 100644 (file)
@@ -171,15 +171,21 @@ static void iwl_mvm_scan_fill_ssids(struct iwl_ssid_ie *cmd_ssid,
  * already included in the probe template, so we need to set only
  * req->n_ssids - 1 bits in addition to the first bit.
  */
-static u16 iwl_mvm_get_active_dwell(enum ieee80211_band band, int n_ssids)
+static u16 iwl_mvm_get_active_dwell(struct iwl_mvm *mvm,
+                                   enum ieee80211_band band, int n_ssids)
 {
+       if (mvm->fw->ucode_capa.api[0] & IWL_UCODE_TLV_API_BASIC_DWELL)
+               return 10;
        if (band == IEEE80211_BAND_2GHZ)
                return 20  + 3 * (n_ssids + 1);
        return 10  + 2 * (n_ssids + 1);
 }
 
-static u16 iwl_mvm_get_passive_dwell(enum ieee80211_band band)
+static u16 iwl_mvm_get_passive_dwell(struct iwl_mvm *mvm,
+                                    enum ieee80211_band band)
 {
+       if (mvm->fw->ucode_capa.api[0] & IWL_UCODE_TLV_API_BASIC_DWELL)
+                       return 110;
        return band == IEEE80211_BAND_2GHZ ? 100 + 20 : 100 + 10;
 }
 
@@ -331,7 +337,8 @@ static void iwl_mvm_scan_calc_params(struct iwl_mvm *mvm,
                 */
                if (vif->type == NL80211_IFTYPE_P2P_DEVICE) {
                        u32 passive_dwell =
-                               iwl_mvm_get_passive_dwell(IEEE80211_BAND_2GHZ);
+                               iwl_mvm_get_passive_dwell(mvm,
+                                                         IEEE80211_BAND_2GHZ);
                        params->max_out_time = passive_dwell;
                } else {
                        params->passive_fragmented = true;
@@ -348,8 +355,8 @@ not_bound:
                        params->dwell[band].passive = frag_passive_dwell;
                else
                        params->dwell[band].passive =
-                               iwl_mvm_get_passive_dwell(band);
-               params->dwell[band].active = iwl_mvm_get_active_dwell(band,
+                               iwl_mvm_get_passive_dwell(mvm, band);
+               params->dwell[band].active = iwl_mvm_get_active_dwell(mvm, band,
                                                                      n_ssids);
        }
 }
@@ -1448,6 +1455,8 @@ int iwl_mvm_unified_sched_scan_lmac(struct iwl_mvm *mvm,
 
        if (iwl_mvm_scan_pass_all(mvm, req))
                flags |= IWL_MVM_LMAC_SCAN_FLAG_PASS_ALL;
+       else
+               flags |= IWL_MVM_LMAC_SCAN_FLAG_MATCH;
 
        if (req->n_ssids == 1 && req->ssids[0].ssid_len != 0)
                flags |= IWL_MVM_LMAC_SCAN_FLAG_PRE_CONNECTION;
index 4f15d9decc81bd4fe80bd2ac716667e2c3b97aa1..4333306ccdee75a02952288196897d63a349b6b0 100644 (file)
@@ -108,8 +108,12 @@ void iwl_mvm_set_tx_cmd(struct iwl_mvm *mvm, struct sk_buff *skb,
                        tx_flags &= ~TX_CMD_FLG_SEQ_CTL;
        }
 
-       /* tid_tspec will default to 0 = BE when QOS isn't enabled */
-       ac = tid_to_mac80211_ac[tx_cmd->tid_tspec];
+       /* Default to 0 (BE) when tid_spec is set to IWL_TID_NON_QOS */
+       if (tx_cmd->tid_tspec < IWL_MAX_TID_COUNT)
+               ac = tid_to_mac80211_ac[tx_cmd->tid_tspec];
+       else
+               ac = tid_to_mac80211_ac[0];
+
        tx_flags |= iwl_mvm_bt_coex_tx_prio(mvm, hdr, info, ac) <<
                        TX_CMD_FLG_BT_PRIO_POS;
 
index e56e77ef5d2e3d28d9a30185ef257aa43912ed23..917431e30f747bf9411c8c33b1f013d18b14f29e 100644 (file)
@@ -665,7 +665,7 @@ bool iwl_mvm_rx_diversity_allowed(struct iwl_mvm *mvm)
        if (num_of_ant(mvm->fw->valid_rx_ant) == 1)
                return false;
 
-       if (!mvm->cfg->rx_with_siso_diversity)
+       if (mvm->cfg->rx_with_siso_diversity)
                return false;
 
        ieee80211_iterate_active_interfaces_atomic(
index 2f0c4b1703442b85b3a56bd90c0548995e0bc661..d5aadb00dd9e4a6acf4e29c72dd0d55d59d59203 100644 (file)
@@ -527,8 +527,10 @@ static int iwl_pci_probe(struct pci_dev *pdev, const struct pci_device_id *ent)
        else if (cfg == &iwl7265_n_cfg)
                cfg_7265d = &iwl7265d_n_cfg;
        if (cfg_7265d &&
-           (iwl_trans->hw_rev & CSR_HW_REV_TYPE_MSK) == CSR_HW_REV_TYPE_7265D)
+           (iwl_trans->hw_rev & CSR_HW_REV_TYPE_MSK) == CSR_HW_REV_TYPE_7265D) {
                cfg = cfg_7265d;
+               iwl_trans->cfg = cfg_7265d;
+       }
 #endif
 
        pci_set_drvdata(pdev, iwl_trans);
index 846a2e6e34d855d62726eda65b51ee427bc1a939..c70efb9a6e78ccf22170bb8bbfe0abe89be695ef 100644 (file)
@@ -666,7 +666,8 @@ tx_status_ok:
 }
 
 static int _rtl_pci_init_one_rxdesc(struct ieee80211_hw *hw,
-                                   u8 *entry, int rxring_idx, int desc_idx)
+                                   struct sk_buff *new_skb, u8 *entry,
+                                   int rxring_idx, int desc_idx)
 {
        struct rtl_priv *rtlpriv = rtl_priv(hw);
        struct rtl_pci *rtlpci = rtl_pcidev(rtl_pcipriv(hw));
@@ -674,11 +675,15 @@ static int _rtl_pci_init_one_rxdesc(struct ieee80211_hw *hw,
        u8 tmp_one = 1;
        struct sk_buff *skb;
 
+       if (likely(new_skb)) {
+               skb = new_skb;
+               goto remap;
+       }
        skb = dev_alloc_skb(rtlpci->rxbuffersize);
        if (!skb)
                return 0;
-       rtlpci->rx_ring[rxring_idx].rx_buf[desc_idx] = skb;
 
+remap:
        /* just set skb->cb to mapping addr for pci_unmap_single use */
        *((dma_addr_t *)skb->cb) =
                pci_map_single(rtlpci->pdev, skb_tail_pointer(skb),
@@ -686,6 +691,7 @@ static int _rtl_pci_init_one_rxdesc(struct ieee80211_hw *hw,
        bufferaddress = *((dma_addr_t *)skb->cb);
        if (pci_dma_mapping_error(rtlpci->pdev, bufferaddress))
                return 0;
+       rtlpci->rx_ring[rxring_idx].rx_buf[desc_idx] = skb;
        if (rtlpriv->use_new_trx_flow) {
                rtlpriv->cfg->ops->set_desc(hw, (u8 *)entry, false,
                                            HW_DESC_RX_PREPARE,
@@ -781,6 +787,7 @@ static void _rtl_pci_rx_interrupt(struct ieee80211_hw *hw)
                /*rx pkt */
                struct sk_buff *skb = rtlpci->rx_ring[rxring_idx].rx_buf[
                                      rtlpci->rx_ring[rxring_idx].idx];
+               struct sk_buff *new_skb;
 
                if (rtlpriv->use_new_trx_flow) {
                        rx_remained_cnt =
@@ -807,6 +814,13 @@ static void _rtl_pci_rx_interrupt(struct ieee80211_hw *hw)
                pci_unmap_single(rtlpci->pdev, *((dma_addr_t *)skb->cb),
                                 rtlpci->rxbuffersize, PCI_DMA_FROMDEVICE);
 
+               /* get a new skb - if fail, old one will be reused */
+               new_skb = dev_alloc_skb(rtlpci->rxbuffersize);
+               if (unlikely(!new_skb)) {
+                       pr_err("Allocation of new skb failed in %s\n",
+                              __func__);
+                       goto no_new;
+               }
                if (rtlpriv->use_new_trx_flow) {
                        buffer_desc =
                          &rtlpci->rx_ring[rxring_idx].buffer_desc
@@ -911,14 +925,16 @@ static void _rtl_pci_rx_interrupt(struct ieee80211_hw *hw)
                        schedule_work(&rtlpriv->works.lps_change_work);
                }
 end:
+               skb = new_skb;
+no_new:
                if (rtlpriv->use_new_trx_flow) {
-                       _rtl_pci_init_one_rxdesc(hw, (u8 *)buffer_desc,
+                       _rtl_pci_init_one_rxdesc(hw, skb, (u8 *)buffer_desc,
                                                 rxring_idx,
-                                              rtlpci->rx_ring[rxring_idx].idx);
+                                                rtlpci->rx_ring[rxring_idx].idx);
                } else {
-                       _rtl_pci_init_one_rxdesc(hw, (u8 *)pdesc, rxring_idx,
+                       _rtl_pci_init_one_rxdesc(hw, skb, (u8 *)pdesc,
+                                                rxring_idx,
                                                 rtlpci->rx_ring[rxring_idx].idx);
-
                        if (rtlpci->rx_ring[rxring_idx].idx ==
                            rtlpci->rxringcount - 1)
                                rtlpriv->cfg->ops->set_desc(hw, (u8 *)pdesc,
@@ -1307,7 +1323,7 @@ static int _rtl_pci_init_rx_ring(struct ieee80211_hw *hw, int rxring_idx)
                rtlpci->rx_ring[rxring_idx].idx = 0;
                for (i = 0; i < rtlpci->rxringcount; i++) {
                        entry = &rtlpci->rx_ring[rxring_idx].buffer_desc[i];
-                       if (!_rtl_pci_init_one_rxdesc(hw, (u8 *)entry,
+                       if (!_rtl_pci_init_one_rxdesc(hw, NULL, (u8 *)entry,
                                                      rxring_idx, i))
                                return -ENOMEM;
                }
@@ -1332,7 +1348,7 @@ static int _rtl_pci_init_rx_ring(struct ieee80211_hw *hw, int rxring_idx)
 
                for (i = 0; i < rtlpci->rxringcount; i++) {
                        entry = &rtlpci->rx_ring[rxring_idx].desc[i];
-                       if (!_rtl_pci_init_one_rxdesc(hw, (u8 *)entry,
+                       if (!_rtl_pci_init_one_rxdesc(hw, NULL, (u8 *)entry,
                                                      rxring_idx, i))
                                return -ENOMEM;
                }
index 22bcb4e12e2a1318fc1802fb3c5ff6b2cb4acf92..d8c10764f13061fd355e0e36abff7c83d3a458a5 100644 (file)
@@ -88,10 +88,8 @@ struct netfront_cb {
 #define IRQ_NAME_SIZE (QUEUE_NAME_SIZE + 3)
 
 struct netfront_stats {
-       u64                     rx_packets;
-       u64                     tx_packets;
-       u64                     rx_bytes;
-       u64                     tx_bytes;
+       u64                     packets;
+       u64                     bytes;
        struct u64_stats_sync   syncp;
 };
 
@@ -160,7 +158,8 @@ struct netfront_info {
        struct netfront_queue *queues;
 
        /* Statistics */
-       struct netfront_stats __percpu *stats;
+       struct netfront_stats __percpu *rx_stats;
+       struct netfront_stats __percpu *tx_stats;
 
        atomic_t rx_gso_checksum_fixup;
 };
@@ -565,7 +564,7 @@ static int xennet_start_xmit(struct sk_buff *skb, struct net_device *dev)
 {
        unsigned short id;
        struct netfront_info *np = netdev_priv(dev);
-       struct netfront_stats *stats = this_cpu_ptr(np->stats);
+       struct netfront_stats *tx_stats = this_cpu_ptr(np->tx_stats);
        struct xen_netif_tx_request *tx;
        char *data = skb->data;
        RING_IDX i;
@@ -672,10 +671,10 @@ static int xennet_start_xmit(struct sk_buff *skb, struct net_device *dev)
        if (notify)
                notify_remote_via_irq(queue->tx_irq);
 
-       u64_stats_update_begin(&stats->syncp);
-       stats->tx_bytes += skb->len;
-       stats->tx_packets++;
-       u64_stats_update_end(&stats->syncp);
+       u64_stats_update_begin(&tx_stats->syncp);
+       tx_stats->bytes += skb->len;
+       tx_stats->packets++;
+       u64_stats_update_end(&tx_stats->syncp);
 
        /* Note: It is not safe to access skb after xennet_tx_buf_gc()! */
        xennet_tx_buf_gc(queue);
@@ -931,7 +930,7 @@ static int checksum_setup(struct net_device *dev, struct sk_buff *skb)
 static int handle_incoming_queue(struct netfront_queue *queue,
                                 struct sk_buff_head *rxq)
 {
-       struct netfront_stats *stats = this_cpu_ptr(queue->info->stats);
+       struct netfront_stats *rx_stats = this_cpu_ptr(queue->info->rx_stats);
        int packets_dropped = 0;
        struct sk_buff *skb;
 
@@ -952,10 +951,10 @@ static int handle_incoming_queue(struct netfront_queue *queue,
                        continue;
                }
 
-               u64_stats_update_begin(&stats->syncp);
-               stats->rx_packets++;
-               stats->rx_bytes += skb->len;
-               u64_stats_update_end(&stats->syncp);
+               u64_stats_update_begin(&rx_stats->syncp);
+               rx_stats->packets++;
+               rx_stats->bytes += skb->len;
+               u64_stats_update_end(&rx_stats->syncp);
 
                /* Pass it up. */
                napi_gro_receive(&queue->napi, skb);
@@ -1079,18 +1078,22 @@ static struct rtnl_link_stats64 *xennet_get_stats64(struct net_device *dev,
        int cpu;
 
        for_each_possible_cpu(cpu) {
-               struct netfront_stats *stats = per_cpu_ptr(np->stats, cpu);
+               struct netfront_stats *rx_stats = per_cpu_ptr(np->rx_stats, cpu);
+               struct netfront_stats *tx_stats = per_cpu_ptr(np->tx_stats, cpu);
                u64 rx_packets, rx_bytes, tx_packets, tx_bytes;
                unsigned int start;
 
                do {
-                       start = u64_stats_fetch_begin_irq(&stats->syncp);
+                       start = u64_stats_fetch_begin_irq(&tx_stats->syncp);
+                       tx_packets = tx_stats->packets;
+                       tx_bytes = tx_stats->bytes;
+               } while (u64_stats_fetch_retry_irq(&tx_stats->syncp, start));
 
-                       rx_packets = stats->rx_packets;
-                       tx_packets = stats->tx_packets;
-                       rx_bytes = stats->rx_bytes;
-                       tx_bytes = stats->tx_bytes;
-               } while (u64_stats_fetch_retry_irq(&stats->syncp, start));
+               do {
+                       start = u64_stats_fetch_begin_irq(&rx_stats->syncp);
+                       rx_packets = rx_stats->packets;
+                       rx_bytes = rx_stats->bytes;
+               } while (u64_stats_fetch_retry_irq(&rx_stats->syncp, start));
 
                tot->rx_packets += rx_packets;
                tot->tx_packets += tx_packets;
@@ -1275,6 +1278,15 @@ static const struct net_device_ops xennet_netdev_ops = {
 #endif
 };
 
+static void xennet_free_netdev(struct net_device *netdev)
+{
+       struct netfront_info *np = netdev_priv(netdev);
+
+       free_percpu(np->rx_stats);
+       free_percpu(np->tx_stats);
+       free_netdev(netdev);
+}
+
 static struct net_device *xennet_create_dev(struct xenbus_device *dev)
 {
        int err;
@@ -1295,8 +1307,11 @@ static struct net_device *xennet_create_dev(struct xenbus_device *dev)
        np->queues = NULL;
 
        err = -ENOMEM;
-       np->stats = netdev_alloc_pcpu_stats(struct netfront_stats);
-       if (np->stats == NULL)
+       np->rx_stats = netdev_alloc_pcpu_stats(struct netfront_stats);
+       if (np->rx_stats == NULL)
+               goto exit;
+       np->tx_stats = netdev_alloc_pcpu_stats(struct netfront_stats);
+       if (np->tx_stats == NULL)
                goto exit;
 
        netdev->netdev_ops      = &xennet_netdev_ops;
@@ -1327,7 +1342,7 @@ static struct net_device *xennet_create_dev(struct xenbus_device *dev)
        return netdev;
 
  exit:
-       free_netdev(netdev);
+       xennet_free_netdev(netdev);
        return ERR_PTR(err);
 }
 
@@ -1369,7 +1384,7 @@ static int netfront_probe(struct xenbus_device *dev,
        return 0;
 
  fail:
-       free_netdev(netdev);
+       xennet_free_netdev(netdev);
        dev_set_drvdata(&dev->dev, NULL);
        return err;
 }
@@ -2189,9 +2204,7 @@ static int xennet_remove(struct xenbus_device *dev)
                info->queues = NULL;
        }
 
-       free_percpu(info->stats);
-
-       free_netdev(info->netdev);
+       xennet_free_netdev(info->netdev);
 
        return 0;
 }
index e34da13885e8c422a7fdecc153d6407c0b52999f..27fa62ce613618debb31fadb6bb50a51d9e65893 100644 (file)
@@ -1050,7 +1050,8 @@ static int miphy28lp_init(struct phy *phy)
                ret = miphy28lp_init_usb3(miphy_phy);
                break;
        default:
-               return -EINVAL;
+               ret = -EINVAL;
+               break;
        }
 
        mutex_unlock(&miphy_dev->miphy_mutex);
index c96e8183a8ffe061e017976daa40632ac5a22c56..efe724f97e02fbf9eba84c215628993fa3ea1274 100644 (file)
 /**
  * omap_control_pcie_pcs - set the PCS delay count
  * @dev: the control module device
- * @id: index of the pcie PHY (should be 1 or 2)
  * @delay: 8 bit delay value
  */
-void omap_control_pcie_pcs(struct device *dev, u8 id, u8 delay)
+void omap_control_pcie_pcs(struct device *dev, u8 delay)
 {
        u32 val;
        struct omap_control_phy *control_phy;
@@ -55,8 +54,8 @@ void omap_control_pcie_pcs(struct device *dev, u8 id, u8 delay)
 
        val = readl(control_phy->pcie_pcs);
        val &= ~(OMAP_CTRL_PCIE_PCS_MASK <<
-               (id * OMAP_CTRL_PCIE_PCS_DELAY_COUNT_SHIFT));
-       val |= delay << (id * OMAP_CTRL_PCIE_PCS_DELAY_COUNT_SHIFT);
+               OMAP_CTRL_PCIE_PCS_DELAY_COUNT_SHIFT);
+       val |= (delay << OMAP_CTRL_PCIE_PCS_DELAY_COUNT_SHIFT);
        writel(val, control_phy->pcie_pcs);
 }
 EXPORT_SYMBOL_GPL(omap_control_pcie_pcs);
index fb02a67c91811e5291757c8fbb330439c3d95e89..a2b08f3ccb031cbf3a484cb0afab5665c0fb3ad7 100644 (file)
@@ -244,7 +244,8 @@ static int sun4i_usb_phy_probe(struct platform_device *pdev)
        else
                data->num_phys = 3;
 
-       if (of_device_is_compatible(np, "allwinner,sun4i-a10-usb-phy"))
+       if (of_device_is_compatible(np, "allwinner,sun4i-a10-usb-phy") ||
+           of_device_is_compatible(np, "allwinner,sun6i-a31-usb-phy"))
                data->disc_thresh = 3;
        else
                data->disc_thresh = 2;
index 1387b4d4afe376556661f49938bf71bb85572d94..465de2c800f228d7fa4961083e243349f5fbcd33 100644 (file)
@@ -82,7 +82,6 @@ struct ti_pipe3 {
        struct clk              *refclk;
        struct clk              *div_clk;
        struct pipe3_dpll_map   *dpll_map;
-       u8                      id;
 };
 
 static struct pipe3_dpll_map dpll_map_usb[] = {
@@ -217,8 +216,13 @@ static int ti_pipe3_init(struct phy *x)
        u32 val;
        int ret = 0;
 
+       /*
+        * Set pcie_pcs register to 0x96 for proper functioning of phy
+        * as recommended in AM572x TRM SPRUHZ6, section 18.5.2.2, table
+        * 18-1804.
+        */
        if (of_device_is_compatible(phy->dev->of_node, "ti,phy-pipe3-pcie")) {
-               omap_control_pcie_pcs(phy->control_dev, phy->id, 0xF1);
+               omap_control_pcie_pcs(phy->control_dev, 0x96);
                return 0;
        }
 
@@ -347,8 +351,6 @@ static int ti_pipe3_probe(struct platform_device *pdev)
        }
 
        if (of_device_is_compatible(node, "ti,phy-pipe3-pcie")) {
-               if (of_property_read_u8(node, "id", &phy->id) < 0)
-                       phy->id = 1;
 
                clk = devm_clk_get(phy->dev, "dpll_ref");
                if (IS_ERR(clk)) {
index e4f65510c87e8928666e195b6b76e52cae9252b5..89dca77ca0382e93909188cad63ccd9ef6bff41b 100644 (file)
@@ -1801,14 +1801,15 @@ void pinctrl_unregister(struct pinctrl_dev *pctldev)
        if (pctldev == NULL)
                return;
 
-       mutex_lock(&pinctrldev_list_mutex);
        mutex_lock(&pctldev->mutex);
-
        pinctrl_remove_device_debugfs(pctldev);
+       mutex_unlock(&pctldev->mutex);
 
        if (!IS_ERR(pctldev->p))
                pinctrl_put(pctldev->p);
 
+       mutex_lock(&pinctrldev_list_mutex);
+       mutex_lock(&pctldev->mutex);
        /* TODO: check that no pinmuxes are still active? */
        list_del(&pctldev->node);
        /* Destroy descriptor tree */
index 3c22dbebc80f202087c9940b05e3887a4c002252..43eacc924b7eb96c0cb0b4fd02d2f91f3c9a2fde 100644 (file)
@@ -1398,10 +1398,7 @@ static void rockchip_irq_demux(unsigned int irq, struct irq_desc *desc)
 {
        struct irq_chip *chip = irq_get_chip(irq);
        struct rockchip_pin_bank *bank = irq_get_handler_data(irq);
-       u32 polarity = 0, data = 0;
        u32 pend;
-       bool edge_changed = false;
-       unsigned long flags;
 
        dev_dbg(bank->drvdata->dev, "got irq for bank %s\n", bank->name);
 
@@ -1409,12 +1406,6 @@ static void rockchip_irq_demux(unsigned int irq, struct irq_desc *desc)
 
        pend = readl_relaxed(bank->reg_base + GPIO_INT_STATUS);
 
-       if (bank->toggle_edge_mode) {
-               polarity = readl_relaxed(bank->reg_base +
-                                        GPIO_INT_POLARITY);
-               data = readl_relaxed(bank->reg_base + GPIO_EXT_PORT);
-       }
-
        while (pend) {
                unsigned int virq;
 
@@ -1434,27 +1425,31 @@ static void rockchip_irq_demux(unsigned int irq, struct irq_desc *desc)
                 * needs manual intervention.
                 */
                if (bank->toggle_edge_mode & BIT(irq)) {
-                       if (data & BIT(irq))
-                               polarity &= ~BIT(irq);
-                       else
-                               polarity |= BIT(irq);
+                       u32 data, data_old, polarity;
+                       unsigned long flags;
 
-                       edge_changed = true;
-               }
+                       data = readl_relaxed(bank->reg_base + GPIO_EXT_PORT);
+                       do {
+                               spin_lock_irqsave(&bank->slock, flags);
 
-               generic_handle_irq(virq);
-       }
+                               polarity = readl_relaxed(bank->reg_base +
+                                                        GPIO_INT_POLARITY);
+                               if (data & BIT(irq))
+                                       polarity &= ~BIT(irq);
+                               else
+                                       polarity |= BIT(irq);
+                               writel(polarity,
+                                      bank->reg_base + GPIO_INT_POLARITY);
 
-       if (bank->toggle_edge_mode && edge_changed) {
-               /* Interrupt params should only be set with ints disabled */
-               spin_lock_irqsave(&bank->slock, flags);
+                               spin_unlock_irqrestore(&bank->slock, flags);
 
-               data = readl_relaxed(bank->reg_base + GPIO_INTEN);
-               writel_relaxed(0, bank->reg_base + GPIO_INTEN);
-               writel(polarity, bank->reg_base + GPIO_INT_POLARITY);
-               writel(data, bank->reg_base + GPIO_INTEN);
+                               data_old = data;
+                               data = readl_relaxed(bank->reg_base +
+                                                    GPIO_EXT_PORT);
+                       } while ((data & BIT(irq)) != (data_old & BIT(irq)));
+               }
 
-               spin_unlock_irqrestore(&bank->slock, flags);
+               generic_handle_irq(virq);
        }
 
        chained_irq_exit(chip, desc);
index c5cef59f59654cad158677f8dbc664051a222508..779950c62e53d238e7a4c35d7290ca66475fed86 100644 (file)
@@ -798,10 +798,8 @@ static int pinmux_xway_probe(struct platform_device *pdev)
 
        /* load the gpio chip */
        xway_chip.dev = &pdev->dev;
-       of_gpiochip_add(&xway_chip);
        ret = gpiochip_add(&xway_chip);
        if (ret) {
-               of_gpiochip_remove(&xway_chip);
                dev_err(&pdev->dev, "Failed to register gpio chip\n");
                return ret;
        }
index e730935fa4577deb2582ea493ab60aa2b0f176fe..ed7017df065d3f002bada2659f4be9baccf6c1f2 100644 (file)
@@ -865,10 +865,10 @@ static int msm_ps_hold_restart(struct notifier_block *nb, unsigned long action,
 
 static void msm_pinctrl_setup_pm_reset(struct msm_pinctrl *pctrl)
 {
-       int i = 0;
+       int i;
        const struct msm_function *func = pctrl->soc->functions;
 
-       for (; i <= pctrl->soc->nfunctions; i++)
+       for (i = 0; i < pctrl->soc->nfunctions; i++)
                if (!strcmp(func[i].name, "ps_hold")) {
                        pctrl->restart_nb.notifier_call = msm_ps_hold_restart;
                        pctrl->restart_nb.priority = 128;
index eebc52cb69849ea99f07c9c6694389a92e39afa5..3d95c87160b35003635460d5d67379d3da33d27f 100644 (file)
@@ -102,6 +102,8 @@ static int sunxi_reset_init(struct device_node *np)
                goto err_alloc;
        }
 
+       spin_lock_init(&data->lock);
+
        data->rcdev.owner = THIS_MODULE;
        data->rcdev.nr_resets = size * 32;
        data->rcdev.ops = &sunxi_reset_ops;
@@ -157,6 +159,8 @@ static int sunxi_reset_probe(struct platform_device *pdev)
        if (IS_ERR(data->membase))
                return PTR_ERR(data->membase);
 
+       spin_lock_init(&data->lock);
+
        data->rcdev.owner = THIS_MODULE;
        data->rcdev.nr_resets = resource_size(res) * 32;
        data->rcdev.ops = &sunxi_reset_ops;
index 91e97ec0141892cbf4d1676480d5fda3223b0e6b..4d41bf75c23318577638fa45493aab748e0473a7 100644 (file)
@@ -1163,9 +1163,13 @@ static inline int ap_test_config_card_id(unsigned int id)
  */
 static inline int ap_test_config_domain(unsigned int domain)
 {
-       if (!ap_configuration)
-               return 1;
-       return ap_test_config(ap_configuration->aqm, domain);
+       if (!ap_configuration)    /* QCI not supported */
+               if (domain < 16)
+                       return 1; /* then domains 0...15 are configured */
+               else
+                       return 0;
+       else
+               return ap_test_config(ap_configuration->aqm, domain);
 }
 
 /**
index 9ea95dd3e2604eea2613a5a15d074c2357fac7dd..6d5c0b8cb0bb47a040d7aec986dbcbae68ffa2b5 100644 (file)
@@ -591,7 +591,6 @@ static void scsi_free_sgtable(struct scsi_data_buffer *sdb, bool mq)
 static int scsi_alloc_sgtable(struct scsi_data_buffer *sdb, int nents, bool mq)
 {
        struct scatterlist *first_chunk = NULL;
-       gfp_t gfp_mask = mq ? GFP_NOIO : GFP_ATOMIC;
        int ret;
 
        BUG_ON(!nents);
@@ -606,7 +605,7 @@ static int scsi_alloc_sgtable(struct scsi_data_buffer *sdb, int nents, bool mq)
        }
 
        ret = __sg_alloc_table(&sdb->table, nents, SCSI_MAX_SG_SEGMENTS,
-                              first_chunk, gfp_mask, scsi_sg_alloc);
+                              first_chunk, GFP_ATOMIC, scsi_sg_alloc);
        if (unlikely(ret))
                scsi_free_sgtable(sdb, mq);
        return ret;
index 86c72ba0a0cd5cc019ef068dcec54886f88e7653..f8c5fc371c4cb4ff0b349e9eb2ff871bc60a0574 100644 (file)
@@ -2177,7 +2177,7 @@ bool BBbVT3253Init(struct vnt_private *priv)
                /* Init ANT B select,RX Config CR10 = 0x28->0x2A, 0x2A->0x28(VC1/VC2 define, make the ANT_A, ANT_B inverted) */
                /*bResult &= BBbWriteEmbedded(dwIoBase,0x0a,0x28);*/
                /* Select VC1/VC2, CR215 = 0x02->0x06 */
-               bResult &= BBbWriteEmbedded(dwIoBase, 0xd7, 0x06);
+               bResult &= BBbWriteEmbedded(priv, 0xd7, 0x06);
                /* }} */
 
                for (ii = 0; ii < CB_VT3253B0_AGC; ii++)
index c8f739dd346eea7e4fc3287eb2eb5338955a1e46..70f870541f9268b598d78c8bf04792877b635231 100644 (file)
@@ -182,6 +182,14 @@ bool set_channel(void *pDeviceHandler, unsigned int uConnectionChannel)
        if (pDevice->byCurrentCh == uConnectionChannel)
                return bResult;
 
+       /* Set VGA to max sensitivity */
+       if (pDevice->bUpdateBBVGA &&
+           pDevice->byBBVGACurrent != pDevice->abyBBVGA[0]) {
+               pDevice->byBBVGACurrent = pDevice->abyBBVGA[0];
+
+               BBvSetVGAGainOffset(pDevice, pDevice->byBBVGACurrent);
+       }
+
        /* clear NAV */
        MACvRegBitsOn(pDevice->PortOffset, MAC_REG_MACCR, MACCR_CLRNAV);
 
index 83e4162c0094c4b2bed6853bc8cfb5636011191a..cd1a277d853b5d4cfa6f6e4156761f5d20558e25 100644 (file)
@@ -1232,7 +1232,7 @@ static int vnt_tx_packet(struct vnt_private *priv, struct sk_buff *skb)
 
        head_td = priv->apCurrTD[dma_idx];
 
-       head_td->m_td1TD1.byTCR = (TCR_EDP|TCR_STP);
+       head_td->m_td1TD1.byTCR = 0;
 
        head_td->pTDInfo->skb = skb;
 
@@ -1257,6 +1257,11 @@ static int vnt_tx_packet(struct vnt_private *priv, struct sk_buff *skb)
 
        priv->bPWBitOn = false;
 
+       /* Set TSR1 & ReqCount in TxDescHead */
+       head_td->m_td1TD1.byTCR |= (TCR_STP | TCR_EDP | EDMSDU);
+       head_td->m_td1TD1.wReqCount =
+                       cpu_to_le16((u16)head_td->pTDInfo->dwReqCount);
+
        head_td->pTDInfo->byFlags = TD_FLAGS_NETIF_SKB;
 
        if (dma_idx == TYPE_AC0DMA)
@@ -1500,9 +1505,11 @@ static void vnt_bss_info_changed(struct ieee80211_hw *hw,
                if (conf->enable_beacon) {
                        vnt_beacon_enable(priv, vif, conf);
 
-                       MACvRegBitsOn(priv, MAC_REG_TCR, TCR_AUTOBCNTX);
+                       MACvRegBitsOn(priv->PortOffset, MAC_REG_TCR,
+                                     TCR_AUTOBCNTX);
                } else {
-                       MACvRegBitsOff(priv, MAC_REG_TCR, TCR_AUTOBCNTX);
+                       MACvRegBitsOff(priv->PortOffset, MAC_REG_TCR,
+                                      TCR_AUTOBCNTX);
                }
        }
 
index 61c39dd7ad013c9e40b784c70414fac62bac908b..b5b0155961f22e08959766d01cea8db241893a7e 100644 (file)
@@ -1204,13 +1204,10 @@ s_cbFillTxBufHead(struct vnt_private *pDevice, unsigned char byPktType,
 
        ptdCurr = (PSTxDesc)pHeadTD;
 
-       ptdCurr->pTDInfo->dwReqCount = cbReqCount - uPadding;
+       ptdCurr->pTDInfo->dwReqCount = cbReqCount;
        ptdCurr->pTDInfo->dwHeaderLength = cbHeaderLength;
        ptdCurr->pTDInfo->skb_dma = ptdCurr->pTDInfo->buf_dma;
        ptdCurr->buff_addr = cpu_to_le32(ptdCurr->pTDInfo->skb_dma);
-       /* Set TSR1 & ReqCount in TxDescHead */
-       ptdCurr->m_td1TD1.byTCR |= (TCR_STP | TCR_EDP | EDMSDU);
-       ptdCurr->m_td1TD1.wReqCount = cpu_to_le16((unsigned short)(cbReqCount));
 
        return cbHeaderLength;
 }
index 55f6774f706f729b92fb2045abb7f9a33740c2b4..aebde3289c50de6722062dfdea21fa1c549090cd 100644 (file)
@@ -2027,10 +2027,10 @@ iscsit_process_text_cmd(struct iscsi_conn *conn, struct iscsi_cmd *cmd,
                goto reject;
        }
        if (!strncmp("=All", text_ptr, 4)) {
-               cmd->cmd_flags |= IFC_SENDTARGETS_ALL;
+               cmd->cmd_flags |= ICF_SENDTARGETS_ALL;
        } else if (!strncmp("=iqn.", text_ptr, 5) ||
                   !strncmp("=eui.", text_ptr, 5)) {
-               cmd->cmd_flags |= IFC_SENDTARGETS_SINGLE;
+               cmd->cmd_flags |= ICF_SENDTARGETS_SINGLE;
        } else {
                pr_err("Unable to locate valid SendTargets=%s value\n", text_ptr);
                goto reject;
@@ -3415,10 +3415,10 @@ iscsit_build_sendtargets_response(struct iscsi_cmd *cmd,
                return -ENOMEM;
        }
        /*
-        * Locate pointer to iqn./eui. string for IFC_SENDTARGETS_SINGLE
+        * Locate pointer to iqn./eui. string for ICF_SENDTARGETS_SINGLE
         * explicit case..
         */
-       if (cmd->cmd_flags & IFC_SENDTARGETS_SINGLE) {
+       if (cmd->cmd_flags & ICF_SENDTARGETS_SINGLE) {
                text_ptr = strchr(text_in, '=');
                if (!text_ptr) {
                        pr_err("Unable to locate '=' string in text_in:"
@@ -3434,7 +3434,7 @@ iscsit_build_sendtargets_response(struct iscsi_cmd *cmd,
 
        spin_lock(&tiqn_lock);
        list_for_each_entry(tiqn, &g_tiqn_list, tiqn_list) {
-               if ((cmd->cmd_flags & IFC_SENDTARGETS_SINGLE) &&
+               if ((cmd->cmd_flags & ICF_SENDTARGETS_SINGLE) &&
                     strcmp(tiqn->tiqn, text_ptr)) {
                        continue;
                }
@@ -3512,7 +3512,7 @@ eob:
                if (end_of_buf)
                        break;
 
-               if (cmd->cmd_flags & IFC_SENDTARGETS_SINGLE)
+               if (cmd->cmd_flags & ICF_SENDTARGETS_SINGLE)
                        break;
        }
        spin_unlock(&tiqn_lock);
index 09a522bae222d190ec92e157a42f13d2e361da4a..cbcff38ac9b7d30cf5b21882efeb34bb4fb39641 100644 (file)
@@ -135,8 +135,8 @@ enum cmd_flags_table {
        ICF_CONTIG_MEMORY                       = 0x00000020,
        ICF_ATTACHED_TO_RQUEUE                  = 0x00000040,
        ICF_OOO_CMDSN                           = 0x00000080,
-       IFC_SENDTARGETS_ALL                     = 0x00000100,
-       IFC_SENDTARGETS_SINGLE                  = 0x00000200,
+       ICF_SENDTARGETS_ALL                     = 0x00000100,
+       ICF_SENDTARGETS_SINGLE                  = 0x00000200,
 };
 
 /* struct iscsi_cmd->i_state */
index 7653cfb027a200cbec0dd51c95047708837c7227..58f49ff69b1424bf5feb33ed64eba495d8826851 100644 (file)
@@ -1103,51 +1103,6 @@ int se_dev_set_queue_depth(struct se_device *dev, u32 queue_depth)
 }
 EXPORT_SYMBOL(se_dev_set_queue_depth);
 
-int se_dev_set_fabric_max_sectors(struct se_device *dev, u32 fabric_max_sectors)
-{
-       int block_size = dev->dev_attrib.block_size;
-
-       if (dev->export_count) {
-               pr_err("dev[%p]: Unable to change SE Device"
-                       " fabric_max_sectors while export_count is %d\n",
-                       dev, dev->export_count);
-               return -EINVAL;
-       }
-       if (!fabric_max_sectors) {
-               pr_err("dev[%p]: Illegal ZERO value for"
-                       " fabric_max_sectors\n", dev);
-               return -EINVAL;
-       }
-       if (fabric_max_sectors < DA_STATUS_MAX_SECTORS_MIN) {
-               pr_err("dev[%p]: Passed fabric_max_sectors: %u less than"
-                       " DA_STATUS_MAX_SECTORS_MIN: %u\n", dev, fabric_max_sectors,
-                               DA_STATUS_MAX_SECTORS_MIN);
-               return -EINVAL;
-       }
-       if (fabric_max_sectors > DA_STATUS_MAX_SECTORS_MAX) {
-               pr_err("dev[%p]: Passed fabric_max_sectors: %u"
-                       " greater than DA_STATUS_MAX_SECTORS_MAX:"
-                       " %u\n", dev, fabric_max_sectors,
-                       DA_STATUS_MAX_SECTORS_MAX);
-               return -EINVAL;
-       }
-       /*
-        * Align max_sectors down to PAGE_SIZE to follow transport_allocate_data_tasks()
-        */
-       if (!block_size) {
-               block_size = 512;
-               pr_warn("Defaulting to 512 for zero block_size\n");
-       }
-       fabric_max_sectors = se_dev_align_max_sectors(fabric_max_sectors,
-                                                     block_size);
-
-       dev->dev_attrib.fabric_max_sectors = fabric_max_sectors;
-       pr_debug("dev[%p]: SE Device max_sectors changed to %u\n",
-                       dev, fabric_max_sectors);
-       return 0;
-}
-EXPORT_SYMBOL(se_dev_set_fabric_max_sectors);
-
 int se_dev_set_optimal_sectors(struct se_device *dev, u32 optimal_sectors)
 {
        if (dev->export_count) {
@@ -1156,10 +1111,10 @@ int se_dev_set_optimal_sectors(struct se_device *dev, u32 optimal_sectors)
                        dev, dev->export_count);
                return -EINVAL;
        }
-       if (optimal_sectors > dev->dev_attrib.fabric_max_sectors) {
+       if (optimal_sectors > dev->dev_attrib.hw_max_sectors) {
                pr_err("dev[%p]: Passed optimal_sectors %u cannot be"
-                       " greater than fabric_max_sectors: %u\n", dev,
-                       optimal_sectors, dev->dev_attrib.fabric_max_sectors);
+                       " greater than hw_max_sectors: %u\n", dev,
+                       optimal_sectors, dev->dev_attrib.hw_max_sectors);
                return -EINVAL;
        }
 
@@ -1553,8 +1508,6 @@ struct se_device *target_alloc_device(struct se_hba *hba, const char *name)
        dev->dev_attrib.unmap_granularity_alignment =
                                DA_UNMAP_GRANULARITY_ALIGNMENT_DEFAULT;
        dev->dev_attrib.max_write_same_len = DA_MAX_WRITE_SAME_LEN;
-       dev->dev_attrib.fabric_max_sectors = DA_FABRIC_MAX_SECTORS;
-       dev->dev_attrib.optimal_sectors = DA_FABRIC_MAX_SECTORS;
 
        xcopy_lun = &dev->xcopy_lun;
        xcopy_lun->lun_se_dev = dev;
@@ -1595,6 +1548,7 @@ int target_configure_device(struct se_device *dev)
        dev->dev_attrib.hw_max_sectors =
                se_dev_align_max_sectors(dev->dev_attrib.hw_max_sectors,
                                         dev->dev_attrib.hw_block_size);
+       dev->dev_attrib.optimal_sectors = dev->dev_attrib.hw_max_sectors;
 
        dev->dev_index = scsi_get_new_index(SCSI_DEVICE_INDEX);
        dev->creation_time = get_jiffies_64();
index c2aea099ea4adf7c0ee60ac7949fa02089162932..d836de200a03bcf24be54004df89c7d6d5039030 100644 (file)
@@ -621,7 +621,16 @@ fd_execute_rw(struct se_cmd *cmd, struct scatterlist *sgl, u32 sgl_nents,
        struct fd_prot fd_prot;
        sense_reason_t rc;
        int ret = 0;
-
+       /*
+        * We are currently limited by the number of iovecs (2048) per
+        * single vfs_[writev,readv] call.
+        */
+       if (cmd->data_length > FD_MAX_BYTES) {
+               pr_err("FILEIO: Not able to process I/O of %u bytes due to"
+                      "FD_MAX_BYTES: %u iovec count limitiation\n",
+                       cmd->data_length, FD_MAX_BYTES);
+               return TCM_LOGICAL_UNIT_COMMUNICATION_FAILURE;
+       }
        /*
         * Call vectorized fileio functions to map struct scatterlist
         * physical memory addresses to struct iovec virtual memory.
@@ -959,7 +968,6 @@ static struct configfs_attribute *fileio_backend_dev_attrs[] = {
        &fileio_dev_attrib_hw_block_size.attr,
        &fileio_dev_attrib_block_size.attr,
        &fileio_dev_attrib_hw_max_sectors.attr,
-       &fileio_dev_attrib_fabric_max_sectors.attr,
        &fileio_dev_attrib_optimal_sectors.attr,
        &fileio_dev_attrib_hw_queue_depth.attr,
        &fileio_dev_attrib_queue_depth.attr,
index 3efff94fbd9788838f565218965d180b78a67604..78346b850968ed8da28d88f35cf6a3ac15512a1b 100644 (file)
@@ -124,7 +124,7 @@ static int iblock_configure_device(struct se_device *dev)
        q = bdev_get_queue(bd);
 
        dev->dev_attrib.hw_block_size = bdev_logical_block_size(bd);
-       dev->dev_attrib.hw_max_sectors = UINT_MAX;
+       dev->dev_attrib.hw_max_sectors = queue_max_hw_sectors(q);
        dev->dev_attrib.hw_queue_depth = q->nr_requests;
 
        /*
@@ -883,7 +883,6 @@ static struct configfs_attribute *iblock_backend_dev_attrs[] = {
        &iblock_dev_attrib_hw_block_size.attr,
        &iblock_dev_attrib_block_size.attr,
        &iblock_dev_attrib_hw_max_sectors.attr,
-       &iblock_dev_attrib_fabric_max_sectors.attr,
        &iblock_dev_attrib_optimal_sectors.attr,
        &iblock_dev_attrib_hw_queue_depth.attr,
        &iblock_dev_attrib_queue_depth.attr,
index d56f2aaba9af9a6bb4b89d5c1080d426cba84e63..283cf786ef98be3d0594e847cc9749a072986b80 100644 (file)
@@ -528,6 +528,18 @@ static int core_scsi3_pr_seq_non_holder(
 
                        return 0;
                }
+       } else if (we && registered_nexus) {
+               /*
+                * Reads are allowed for Write Exclusive locks
+                * from all registrants.
+                */
+               if (cmd->data_direction == DMA_FROM_DEVICE) {
+                       pr_debug("Allowing READ CDB: 0x%02x for %s"
+                               " reservation\n", cdb[0],
+                               core_scsi3_pr_dump_type(pr_reg_type));
+
+                       return 0;
+               }
        }
        pr_debug("%s Conflict for %sregistered nexus %s CDB: 0x%2x"
                " for %s reservation\n", transport_dump_cmd_direction(cmd),
index 60ebd170a561943be8bde26cd40112bbd22d1e8e..98e83ac5661bcfe5b3b7b98d6c9fbf21bb27c14e 100644 (file)
@@ -657,7 +657,6 @@ static struct configfs_attribute *rd_mcp_backend_dev_attrs[] = {
        &rd_mcp_dev_attrib_hw_block_size.attr,
        &rd_mcp_dev_attrib_block_size.attr,
        &rd_mcp_dev_attrib_hw_max_sectors.attr,
-       &rd_mcp_dev_attrib_fabric_max_sectors.attr,
        &rd_mcp_dev_attrib_optimal_sectors.attr,
        &rd_mcp_dev_attrib_hw_queue_depth.attr,
        &rd_mcp_dev_attrib_queue_depth.attr,
index 11bea1952435a397172ce69804a1088567bde03f..cd4bed7b27579b14a0f6e517eed23dacb6c1fe02 100644 (file)
@@ -953,21 +953,6 @@ sbc_parse_cdb(struct se_cmd *cmd, struct sbc_ops *ops)
 
        if (cmd->se_cmd_flags & SCF_SCSI_DATA_CDB) {
                unsigned long long end_lba;
-
-               if (sectors > dev->dev_attrib.fabric_max_sectors) {
-                       printk_ratelimited(KERN_ERR "SCSI OP %02xh with too"
-                               " big sectors %u exceeds fabric_max_sectors:"
-                               " %u\n", cdb[0], sectors,
-                               dev->dev_attrib.fabric_max_sectors);
-                       return TCM_INVALID_CDB_FIELD;
-               }
-               if (sectors > dev->dev_attrib.hw_max_sectors) {
-                       printk_ratelimited(KERN_ERR "SCSI OP %02xh with too"
-                               " big sectors %u exceeds backend hw_max_sectors:"
-                               " %u\n", cdb[0], sectors,
-                               dev->dev_attrib.hw_max_sectors);
-                       return TCM_INVALID_CDB_FIELD;
-               }
 check_lba:
                end_lba = dev->transport->get_blocks(dev) + 1;
                if (cmd->t_task_lba + sectors > end_lba) {
index 1307600fe7264cb55234b6b8e88d8cc15878c799..4c71657da56ab3cdc96b5c1f8d784722f10e2c1d 100644 (file)
@@ -505,7 +505,6 @@ static sense_reason_t
 spc_emulate_evpd_b0(struct se_cmd *cmd, unsigned char *buf)
 {
        struct se_device *dev = cmd->se_dev;
-       u32 max_sectors;
        int have_tp = 0;
        int opt, min;
 
@@ -539,9 +538,7 @@ spc_emulate_evpd_b0(struct se_cmd *cmd, unsigned char *buf)
        /*
         * Set MAXIMUM TRANSFER LENGTH
         */
-       max_sectors = min(dev->dev_attrib.fabric_max_sectors,
-                         dev->dev_attrib.hw_max_sectors);
-       put_unaligned_be32(max_sectors, &buf[8]);
+       put_unaligned_be32(dev->dev_attrib.hw_max_sectors, &buf[8]);
 
        /*
         * Set OPTIMAL TRANSFER LENGTH
index 8bfa61c9693dbef6fe6267e16a48c566eae6ac4a..1157b559683b1ff437f9eba74626a90f517d0a1e 100644 (file)
@@ -1118,7 +1118,6 @@ static struct configfs_attribute *tcmu_backend_dev_attrs[] = {
        &tcmu_dev_attrib_hw_block_size.attr,
        &tcmu_dev_attrib_block_size.attr,
        &tcmu_dev_attrib_hw_max_sectors.attr,
-       &tcmu_dev_attrib_fabric_max_sectors.attr,
        &tcmu_dev_attrib_optimal_sectors.attr,
        &tcmu_dev_attrib_hw_queue_depth.attr,
        &tcmu_dev_attrib_queue_depth.attr,
index c1188ac053c9650ce163a3e9e37f34a877959dc2..2ccbc0788353e9488e3f730de80d52ecafaf9082 100644 (file)
@@ -608,6 +608,7 @@ static int imx_thermal_suspend(struct device *dev)
        regmap_write(map, TEMPSENSE0 + REG_CLR, TEMPSENSE0_MEASURE_TEMP);
        regmap_write(map, TEMPSENSE0 + REG_SET, TEMPSENSE0_POWER_DOWN);
        data->mode = THERMAL_DEVICE_DISABLED;
+       clk_disable_unprepare(data->thermal_clk);
 
        return 0;
 }
@@ -617,6 +618,7 @@ static int imx_thermal_resume(struct device *dev)
        struct imx_thermal_data *data = dev_get_drvdata(dev);
        struct regmap *map = data->tempmon;
 
+       clk_prepare_enable(data->thermal_clk);
        /* Enabled thermal sensor after resume */
        regmap_write(map, TEMPSENSE0 + REG_CLR, TEMPSENSE0_POWER_DOWN);
        regmap_write(map, TEMPSENSE0 + REG_SET, TEMPSENSE0_MEASURE_TEMP);
index 231cabc16e160e7318b4339a9d3d5210ff8b2ec3..2c2ec7666eb182c44c24225609ab9ecd723ea04a 100644 (file)
@@ -119,15 +119,11 @@ int acpi_parse_trt(acpi_handle handle, int *trt_count, struct trt **trtp,
                        continue;
 
                result = acpi_bus_get_device(trt->source, &adev);
-               if (!result)
-                       acpi_create_platform_device(adev);
-               else
+               if (result)
                        pr_warn("Failed to get source ACPI device\n");
 
                result = acpi_bus_get_device(trt->target, &adev);
-               if (!result)
-                       acpi_create_platform_device(adev);
-               else
+               if (result)
                        pr_warn("Failed to get target ACPI device\n");
        }
 
@@ -206,16 +202,12 @@ int acpi_parse_art(acpi_handle handle, int *art_count, struct art **artp,
 
                if (art->source) {
                        result = acpi_bus_get_device(art->source, &adev);
-                       if (!result)
-                               acpi_create_platform_device(adev);
-                       else
+                       if (result)
                                pr_warn("Failed to get source ACPI device\n");
                }
                if (art->target) {
                        result = acpi_bus_get_device(art->target, &adev);
-                       if (!result)
-                               acpi_create_platform_device(adev);
-                       else
+                       if (result)
                                pr_warn("Failed to get source ACPI device\n");
                }
        }
index 31bb553aac2633e6ca96ad6c115fe409c610bc35..0fe5dbbea9687053b835ee12eae553930b5ce1f9 100644 (file)
@@ -130,6 +130,8 @@ static int proc_thermal_add(struct device *dev,
        int ret;
 
        adev = ACPI_COMPANION(dev);
+       if (!adev)
+               return -ENODEV;
 
        status = acpi_evaluate_object(adev->handle, "PPCC", NULL, &buf);
        if (ACPI_FAILURE(status))
index e145b66df444e65bb5cc4f9d7e7ed4dce7f76435..d717f3dab6f1410fc955daefb0497c2096298b56 100644 (file)
@@ -149,7 +149,7 @@ EXPORT_SYMBOL_GPL(of_thermal_is_trip_valid);
  *
  * Return: pointer to trip points table, NULL otherwise
  */
-const struct thermal_trip * const
+const struct thermal_trip *
 of_thermal_get_trip_points(struct thermal_zone_device *tz)
 {
        struct __thermal_zone *data = tz->devdata;
index 8803e693fe6868a620b76abda347e0e27645d6d3..2580a4872f90febeb5af00136e16054bb59e4903 100644 (file)
@@ -63,7 +63,7 @@ struct rcar_thermal_priv {
        struct mutex lock;
        struct list_head list;
        int id;
-       int ctemp;
+       u32 ctemp;
 };
 
 #define rcar_thermal_for_each_priv(pos, common)        \
@@ -145,7 +145,7 @@ static int rcar_thermal_update_temp(struct rcar_thermal_priv *priv)
 {
        struct device *dev = rcar_priv_to_dev(priv);
        int i;
-       int ctemp, old, new;
+       u32 ctemp, old, new;
        int ret = -EINVAL;
 
        mutex_lock(&priv->lock);
@@ -372,6 +372,7 @@ static int rcar_thermal_probe(struct platform_device *pdev)
        int i;
        int ret = -ENODEV;
        int idle = IDLE_INTERVAL;
+       u32 enr_bits = 0;
 
        common = devm_kzalloc(dev, sizeof(*common), GFP_KERNEL);
        if (!common)
@@ -390,7 +391,7 @@ static int rcar_thermal_probe(struct platform_device *pdev)
 
                /*
                 * platform has IRQ support.
-                * Then, drier use common register
+                * Then, driver uses common registers
                 */
 
                ret = devm_request_irq(dev, irq->start, rcar_thermal_irq, 0,
@@ -408,9 +409,6 @@ static int rcar_thermal_probe(struct platform_device *pdev)
                if (IS_ERR(common->base))
                        return PTR_ERR(common->base);
 
-               /* enable temperature comparation */
-               rcar_thermal_common_write(common, ENR, 0x00030303);
-
                idle = 0; /* polling delay is not needed */
        }
 
@@ -452,8 +450,15 @@ static int rcar_thermal_probe(struct platform_device *pdev)
                        rcar_thermal_irq_enable(priv);
 
                list_move_tail(&priv->list, &common->head);
+
+               /* update ENR bits */
+               enr_bits |= 3 << (i * 8);
        }
 
+       /* enable temperature comparation */
+       if (irq)
+               rcar_thermal_common_write(common, ENR, enr_bits);
+
        platform_set_drvdata(pdev, common);
 
        dev_info(dev, "%d sensor probed\n", i);
index 9083e75206236c1953e4ad5d7858fbc5f164fad0..0531c752fbbb6680c40e939ad2a14fdc1830f357 100644 (file)
@@ -91,7 +91,7 @@ int of_parse_thermal_zones(void);
 void of_thermal_destroy_zones(void);
 int of_thermal_get_ntrips(struct thermal_zone_device *);
 bool of_thermal_is_trip_valid(struct thermal_zone_device *, int);
-const struct thermal_trip * const
+const struct thermal_trip *
 of_thermal_get_trip_points(struct thermal_zone_device *);
 #else
 static inline int of_parse_thermal_zones(void) { return 0; }
@@ -105,7 +105,7 @@ static inline bool of_thermal_is_trip_valid(struct thermal_zone_device *tz,
 {
        return 0;
 }
-static inline const struct thermal_trip * const
+static inline const struct thermal_trip *
 of_thermal_get_trip_points(struct thermal_zone_device *tz)
 {
        return NULL;
index d2b496750d590c1e06d755b0b563f40c30f8d165..4ddfa60c922205513d16ed74a770eefd111fda83 100644 (file)
@@ -2399,17 +2399,12 @@ static unsigned int n_tty_poll(struct tty_struct *tty, struct file *file,
 
        poll_wait(file, &tty->read_wait, wait);
        poll_wait(file, &tty->write_wait, wait);
-       if (test_bit(TTY_OTHER_CLOSED, &tty->flags))
-               mask |= POLLHUP;
        if (input_available_p(tty, 1))
                mask |= POLLIN | POLLRDNORM;
-       else if (mask & POLLHUP) {
-               tty_flush_to_ldisc(tty);
-               if (input_available_p(tty, 1))
-                       mask |= POLLIN | POLLRDNORM;
-       }
        if (tty->packet && tty->link->ctrl_status)
                mask |= POLLPRI | POLLIN | POLLRDNORM;
+       if (test_bit(TTY_OTHER_CLOSED, &tty->flags))
+               mask |= POLLHUP;
        if (tty_hung_up_p(file))
                mask |= POLLHUP;
        if (!(mask & (POLLHUP | POLLIN | POLLRDNORM))) {
index 31feeb2d0a6688513e1dccf82521f281d9842b03..d1f8dc6aabcbe5bca9b6b6bbfc14e6f3f75e60c5 100644 (file)
@@ -1815,7 +1815,7 @@ pci_wch_ch353_setup(struct serial_private *priv,
 }
 
 static int
-pci_wch_ch382_setup(struct serial_private *priv,
+pci_wch_ch38x_setup(struct serial_private *priv,
                     const struct pciserial_board *board,
                     struct uart_8250_port *port, int idx)
 {
@@ -1880,6 +1880,7 @@ pci_wch_ch382_setup(struct serial_private *priv,
 
 #define PCIE_VENDOR_ID_WCH             0x1c00
 #define PCIE_DEVICE_ID_WCH_CH382_2S1P  0x3250
+#define PCIE_DEVICE_ID_WCH_CH384_4S    0x3470
 
 /* Unknown vendors/cards - this should not be in linux/pci_ids.h */
 #define PCI_SUBDEVICE_ID_UNKNOWN_0x1584        0x1584
@@ -2571,13 +2572,21 @@ static struct pci_serial_quirk pci_serial_quirks[] __refdata = {
                .subdevice      = PCI_ANY_ID,
                .setup          = pci_wch_ch353_setup,
        },
-       /* WCH CH382 2S1P card (16750 clone) */
+       /* WCH CH382 2S1P card (16850 clone) */
        {
                .vendor         = PCIE_VENDOR_ID_WCH,
                .device         = PCIE_DEVICE_ID_WCH_CH382_2S1P,
                .subvendor      = PCI_ANY_ID,
                .subdevice      = PCI_ANY_ID,
-               .setup          = pci_wch_ch382_setup,
+               .setup          = pci_wch_ch38x_setup,
+       },
+       /* WCH CH384 4S card (16850 clone) */
+       {
+               .vendor         = PCIE_VENDOR_ID_WCH,
+               .device         = PCIE_DEVICE_ID_WCH_CH384_4S,
+               .subvendor      = PCI_ANY_ID,
+               .subdevice      = PCI_ANY_ID,
+               .setup          = pci_wch_ch38x_setup,
        },
        /*
         * ASIX devices with FIFO bug
@@ -2876,6 +2885,7 @@ enum pci_board_num_t {
        pbn_fintek_4,
        pbn_fintek_8,
        pbn_fintek_12,
+       pbn_wch384_4,
 };
 
 /*
@@ -3675,6 +3685,14 @@ static struct pciserial_board pci_boards[] = {
                .base_baud      = 115200,
                .first_offset   = 0x40,
        },
+
+       [pbn_wch384_4] = {
+               .flags          = FL_BASE0,
+               .num_ports      = 4,
+               .base_baud      = 115200,
+               .uart_offset    = 8,
+               .first_offset   = 0xC0,
+       },
 };
 
 static const struct pci_device_id blacklist[] = {
@@ -3687,6 +3705,7 @@ static const struct pci_device_id blacklist[] = {
        { PCI_DEVICE(0x4348, 0x7053), }, /* WCH CH353 2S1P */
        { PCI_DEVICE(0x4348, 0x5053), }, /* WCH CH353 1S1P */
        { PCI_DEVICE(0x1c00, 0x3250), }, /* WCH CH382 2S1P */
+       { PCI_DEVICE(0x1c00, 0x3470), }, /* WCH CH384 4S */
 };
 
 /*
@@ -5400,6 +5419,10 @@ static struct pci_device_id serial_pci_tbl[] = {
                PCI_ANY_ID, PCI_ANY_ID,
                0, 0, pbn_b0_bt_2_115200 },
 
+       {       PCIE_VENDOR_ID_WCH, PCIE_DEVICE_ID_WCH_CH384_4S,
+               PCI_ANY_ID, PCI_ANY_ID,
+               0, 0, pbn_wch384_4 },
+
        /*
         * Commtech, Inc. Fastcom adapters
         */
index 19273e31d22426071cc445e0c76655cc6394dbb2..107e807225752623c7f8cae56b17f00d4d003d37 100644 (file)
@@ -1757,32 +1757,43 @@ static struct s3c24xx_serial_drv_data s5pv210_serial_drv_data = {
 #endif
 
 #if defined(CONFIG_ARCH_EXYNOS)
+#define EXYNOS_COMMON_SERIAL_DRV_DATA                          \
+       .info = &(struct s3c24xx_uart_info) {                   \
+               .name           = "Samsung Exynos UART",        \
+               .type           = PORT_S3C6400,                 \
+               .has_divslot    = 1,                            \
+               .rx_fifomask    = S5PV210_UFSTAT_RXMASK,        \
+               .rx_fifoshift   = S5PV210_UFSTAT_RXSHIFT,       \
+               .rx_fifofull    = S5PV210_UFSTAT_RXFULL,        \
+               .tx_fifofull    = S5PV210_UFSTAT_TXFULL,        \
+               .tx_fifomask    = S5PV210_UFSTAT_TXMASK,        \
+               .tx_fifoshift   = S5PV210_UFSTAT_TXSHIFT,       \
+               .def_clk_sel    = S3C2410_UCON_CLKSEL0,         \
+               .num_clks       = 1,                            \
+               .clksel_mask    = 0,                            \
+               .clksel_shift   = 0,                            \
+       },                                                      \
+       .def_cfg = &(struct s3c2410_uartcfg) {                  \
+               .ucon           = S5PV210_UCON_DEFAULT,         \
+               .ufcon          = S5PV210_UFCON_DEFAULT,        \
+               .has_fracval    = 1,                            \
+       }                                                       \
+
 static struct s3c24xx_serial_drv_data exynos4210_serial_drv_data = {
-       .info = &(struct s3c24xx_uart_info) {
-               .name           = "Samsung Exynos4 UART",
-               .type           = PORT_S3C6400,
-               .has_divslot    = 1,
-               .rx_fifomask    = S5PV210_UFSTAT_RXMASK,
-               .rx_fifoshift   = S5PV210_UFSTAT_RXSHIFT,
-               .rx_fifofull    = S5PV210_UFSTAT_RXFULL,
-               .tx_fifofull    = S5PV210_UFSTAT_TXFULL,
-               .tx_fifomask    = S5PV210_UFSTAT_TXMASK,
-               .tx_fifoshift   = S5PV210_UFSTAT_TXSHIFT,
-               .def_clk_sel    = S3C2410_UCON_CLKSEL0,
-               .num_clks       = 1,
-               .clksel_mask    = 0,
-               .clksel_shift   = 0,
-       },
-       .def_cfg = &(struct s3c2410_uartcfg) {
-               .ucon           = S5PV210_UCON_DEFAULT,
-               .ufcon          = S5PV210_UFCON_DEFAULT,
-               .has_fracval    = 1,
-       },
+       EXYNOS_COMMON_SERIAL_DRV_DATA,
        .fifosize = { 256, 64, 16, 16 },
 };
+
+static struct s3c24xx_serial_drv_data exynos5433_serial_drv_data = {
+       EXYNOS_COMMON_SERIAL_DRV_DATA,
+       .fifosize = { 64, 256, 16, 256 },
+};
+
 #define EXYNOS4210_SERIAL_DRV_DATA ((kernel_ulong_t)&exynos4210_serial_drv_data)
+#define EXYNOS5433_SERIAL_DRV_DATA ((kernel_ulong_t)&exynos5433_serial_drv_data)
 #else
 #define EXYNOS4210_SERIAL_DRV_DATA (kernel_ulong_t)NULL
+#define EXYNOS5433_SERIAL_DRV_DATA (kernel_ulong_t)NULL
 #endif
 
 static struct platform_device_id s3c24xx_serial_driver_ids[] = {
@@ -1804,6 +1815,9 @@ static struct platform_device_id s3c24xx_serial_driver_ids[] = {
        }, {
                .name           = "exynos4210-uart",
                .driver_data    = EXYNOS4210_SERIAL_DRV_DATA,
+       }, {
+               .name           = "exynos5433-uart",
+               .driver_data    = EXYNOS5433_SERIAL_DRV_DATA,
        },
        { },
 };
@@ -1823,6 +1837,8 @@ static const struct of_device_id s3c24xx_uart_dt_match[] = {
                .data = (void *)S5PV210_SERIAL_DRV_DATA },
        { .compatible = "samsung,exynos4210-uart",
                .data = (void *)EXYNOS4210_SERIAL_DRV_DATA },
+       { .compatible = "samsung,exynos5433-uart",
+               .data = (void *)EXYNOS5433_SERIAL_DRV_DATA },
        {},
 };
 MODULE_DEVICE_TABLE(of, s3c24xx_uart_dt_match);
index 57ca61b14670f1a540c3f82a24328a390edcfb3c..984605bb5bf1d593087bfffe485323538144b2c5 100644 (file)
@@ -2164,7 +2164,9 @@ uart_report_port(struct uart_driver *drv, struct uart_port *port)
                break;
        }
 
-       dev_info(port->dev, "%s%d at %s (irq = %d, base_baud = %d) is a %s\n",
+       printk(KERN_INFO "%s%s%s%d at %s (irq = %d, base_baud = %d) is a %s\n",
+              port->dev ? dev_name(port->dev) : "",
+              port->dev ? ": " : "",
               drv->dev_name,
               drv->tty_driver->name_base + port->line,
               address, port->irq, port->uartclk / 16, uart_type(port));
index 4f35b43e24759c5ab2ae5bcfd7a0fd49672ed3d8..51f066aa375e64789e03b9a527679e3a0a7e1c8d 100644 (file)
@@ -1464,6 +1464,9 @@ static int tty_reopen(struct tty_struct *tty)
            driver->subtype == PTY_TYPE_MASTER)
                return -EIO;
 
+       if (test_bit(TTY_EXCLUSIVE, &tty->flags) && !capable(CAP_SYS_ADMIN))
+               return -EBUSY;
+
        tty->count++;
 
        WARN_ON(!tty->ldisc);
@@ -2106,10 +2109,6 @@ retry_open:
                retval = -ENODEV;
        filp->f_flags = saved_flags;
 
-       if (!retval && test_bit(TTY_EXCLUSIVE, &tty->flags) &&
-                                               !capable(CAP_SYS_ADMIN))
-               retval = -EBUSY;
-
        if (retval) {
 #ifdef TTY_DEBUG_HANGUP
                printk(KERN_DEBUG "%s: error %d in opening %s...\n", __func__,
index 5b9825a4538a67740a3ccf0d1ceea28d08f5d5c5..a57dc8866fc5ff938641686f7945916074723fe8 100644 (file)
@@ -669,7 +669,6 @@ static int ci_hdrc_probe(struct platform_device *pdev)
        if (!ci)
                return -ENOMEM;
 
-       platform_set_drvdata(pdev, ci);
        ci->dev = dev;
        ci->platdata = dev_get_platdata(dev);
        ci->imx28_write_fix = !!(ci->platdata->flags &
@@ -783,6 +782,7 @@ static int ci_hdrc_probe(struct platform_device *pdev)
                }
        }
 
+       platform_set_drvdata(pdev, ci);
        ret = devm_request_irq(dev, ci->irq, ci_irq, IRQF_SHARED,
                        ci->platdata->name, ci);
        if (ret)
index c1694cff1eafd287c600435a45c861a4406e6514..48731d0bab357a75232fdbd7b4063fe29af3ad4e 100644 (file)
@@ -91,6 +91,7 @@ static int host_start(struct ci_hdrc *ci)
        if (!hcd)
                return -ENOMEM;
 
+       dev_set_drvdata(ci->dev, ci);
        hcd->rsrc_start = ci->hw_bank.phys;
        hcd->rsrc_len = ci->hw_bank.size;
        hcd->regs = ci->hw_bank.abs;
index 200168ec2d7567e63ce9b8a8fa4afb0009b85831..79242008085bbed84a9e7caf142077215d89aab7 100644 (file)
@@ -2567,7 +2567,7 @@ error:
  * s3c_hsotg_ep_disable - disable given endpoint
  * @ep: The endpoint to disable.
  */
-static int s3c_hsotg_ep_disable(struct usb_ep *ep)
+static int s3c_hsotg_ep_disable_force(struct usb_ep *ep, bool force)
 {
        struct s3c_hsotg_ep *hs_ep = our_ep(ep);
        struct dwc2_hsotg *hsotg = hs_ep->parent;
@@ -2588,7 +2588,7 @@ static int s3c_hsotg_ep_disable(struct usb_ep *ep)
 
        spin_lock_irqsave(&hsotg->lock, flags);
        /* terminate all requests with shutdown */
-       kill_all_requests(hsotg, hs_ep, -ESHUTDOWN, false);
+       kill_all_requests(hsotg, hs_ep, -ESHUTDOWN, force);
 
        hsotg->fifo_map &= ~(1<<hs_ep->fifo_index);
        hs_ep->fifo_index = 0;
@@ -2609,6 +2609,10 @@ static int s3c_hsotg_ep_disable(struct usb_ep *ep)
        return 0;
 }
 
+static int s3c_hsotg_ep_disable(struct usb_ep *ep)
+{
+       return s3c_hsotg_ep_disable_force(ep, false);
+}
 /**
  * on_list - check request is on the given endpoint
  * @ep: The endpoint to check.
@@ -2924,7 +2928,7 @@ static int s3c_hsotg_udc_stop(struct usb_gadget *gadget)
 
        /* all endpoints should be shutdown */
        for (ep = 1; ep < hsotg->num_of_eps; ep++)
-               s3c_hsotg_ep_disable(&hsotg->eps[ep].ep);
+               s3c_hsotg_ep_disable_force(&hsotg->eps[ep].ep, true);
 
        spin_lock_irqsave(&hsotg->lock, flags);
 
index 7c4faf738747bdab2bf5a73e39297f8ae437aeb7..b642a2f998f9eaf8079b36e1b22612042e353288 100644 (file)
@@ -33,6 +33,8 @@
 #define PCI_DEVICE_ID_INTEL_BYT                0x0f37
 #define PCI_DEVICE_ID_INTEL_MRFLD      0x119e
 #define PCI_DEVICE_ID_INTEL_BSW                0x22B7
+#define PCI_DEVICE_ID_INTEL_SPTLP      0x9d30
+#define PCI_DEVICE_ID_INTEL_SPTH       0xa130
 
 struct dwc3_pci {
        struct device           *dev;
@@ -219,6 +221,8 @@ static const struct pci_device_id dwc3_pci_id_table[] = {
        { PCI_DEVICE(PCI_VENDOR_ID_INTEL, PCI_DEVICE_ID_INTEL_BSW), },
        { PCI_DEVICE(PCI_VENDOR_ID_INTEL, PCI_DEVICE_ID_INTEL_BYT), },
        { PCI_DEVICE(PCI_VENDOR_ID_INTEL, PCI_DEVICE_ID_INTEL_MRFLD), },
+       { PCI_DEVICE(PCI_VENDOR_ID_INTEL, PCI_DEVICE_ID_INTEL_SPTLP), },
+       { PCI_DEVICE(PCI_VENDOR_ID_INTEL, PCI_DEVICE_ID_INTEL_SPTH), },
        { PCI_DEVICE(PCI_VENDOR_ID_AMD, PCI_DEVICE_ID_AMD_NL_USB), },
        {  }    /* Terminating Entry */
 };
index f03b136ecfce33b3b6936314d1fdebabb4ce936d..8f65ab3a3b928f3872dcc42b1ddfef38d4ba5d26 100644 (file)
@@ -882,8 +882,7 @@ static void dwc3_prepare_trbs(struct dwc3_ep *dep, bool starting)
 
                                if (i == (request->num_mapped_sgs - 1) ||
                                                sg_is_last(s)) {
-                                       if (list_is_last(&req->list,
-                                                       &dep->request_list))
+                                       if (list_empty(&dep->request_list))
                                                last_one = true;
                                        chain = false;
                                }
@@ -901,6 +900,9 @@ static void dwc3_prepare_trbs(struct dwc3_ep *dep, bool starting)
                                if (last_one)
                                        break;
                        }
+
+                       if (last_one)
+                               break;
                } else {
                        dma = req->request.dma;
                        length = req->request.length;
index 6e04e302dc3a85b0dba95cc90c12e97323fa635c..a1bc3e3a0b09f740342e949024db337e030e9ed9 100644 (file)
@@ -399,8 +399,9 @@ static int hidg_setup(struct usb_function *f,
        value   = __le16_to_cpu(ctrl->wValue);
        length  = __le16_to_cpu(ctrl->wLength);
 
-       VDBG(cdev, "hid_setup crtl_request : bRequestType:0x%x bRequest:0x%x "
-               "Value:0x%x\n", ctrl->bRequestType, ctrl->bRequest, value);
+       VDBG(cdev,
+            "%s crtl_request : bRequestType:0x%x bRequest:0x%x Value:0x%x\n",
+            __func__, ctrl->bRequestType, ctrl->bRequest, value);
 
        switch ((ctrl->bRequestType << 8) | ctrl->bRequest) {
        case ((USB_DIR_IN | USB_TYPE_CLASS | USB_RECIP_INTERFACE) << 8
index a90440300735fecaa9502c0234e7abbb81db860b..259b656c0b3ec7bde9e119488f46ded351bb7300 100644 (file)
@@ -520,7 +520,7 @@ static void f_midi_transmit(struct f_midi *midi, struct usb_request *req)
                req = midi_alloc_ep_req(ep, midi->buflen);
 
        if (!req) {
-               ERROR(midi, "gmidi_transmit: alloc_ep_request failed\n");
+               ERROR(midi, "%s: alloc_ep_request failed\n", __func__);
                return;
        }
        req->length = 0;
index f7b20329320583d05c096882d8e04cec7d905097..e9715845f82e1dc825690c05f8cc08c2d8e41df7 100644 (file)
@@ -897,7 +897,6 @@ static void f_audio_free_inst(struct usb_function_instance *f)
        struct f_uac1_opts *opts;
 
        opts = container_of(f, struct f_uac1_opts, func_inst);
-       gaudio_cleanup(opts->card);
        if (opts->fn_play_alloc)
                kfree(opts->fn_play);
        if (opts->fn_cap_alloc)
@@ -935,6 +934,7 @@ static void f_audio_free(struct usb_function *f)
        struct f_audio *audio = func_to_audio(f);
        struct f_uac1_opts *opts;
 
+       gaudio_cleanup(&audio->card);
        opts = container_of(f->fi, struct f_uac1_opts, func_inst);
        kfree(audio);
        mutex_lock(&opts->lock);
index c744e4975d744c4fb710a429ec055616fffd4833..db49ec4c748e9469bd694645c8cfc22df7c829fa 100644 (file)
@@ -441,6 +441,7 @@ ep_write (struct file *fd, const char __user *buf, size_t len, loff_t *ptr)
        kbuf = memdup_user(buf, len);
        if (IS_ERR(kbuf)) {
                value = PTR_ERR(kbuf);
+               kbuf = NULL;
                goto free1;
        }
 
@@ -449,6 +450,7 @@ ep_write (struct file *fd, const char __user *buf, size_t len, loff_t *ptr)
                data->name, len, (int) value);
 free1:
        mutex_unlock(&data->lock);
+       kfree (kbuf);
        return value;
 }
 
index ce882371786b184d7b02f4a451d6c8c1b7a80efa..9f93bed42052cb5c910d5f34218287e58a558c6b 100644 (file)
@@ -716,10 +716,10 @@ static int queue_dma(struct usba_udc *udc, struct usba_ep *ep,
        req->using_dma = 1;
        req->ctrl = USBA_BF(DMA_BUF_LEN, req->req.length)
                        | USBA_DMA_CH_EN | USBA_DMA_END_BUF_IE
-                       | USBA_DMA_END_TR_EN | USBA_DMA_END_TR_IE;
+                       | USBA_DMA_END_BUF_EN;
 
-       if (ep->is_in)
-               req->ctrl |= USBA_DMA_END_BUF_EN;
+       if (!ep->is_in)
+               req->ctrl |= USBA_DMA_END_TR_EN | USBA_DMA_END_TR_IE;
 
        /*
         * Add this request to the queue and submit for DMA if
@@ -828,7 +828,7 @@ static int usba_ep_dequeue(struct usb_ep *_ep, struct usb_request *_req)
 {
        struct usba_ep *ep = to_usba_ep(_ep);
        struct usba_udc *udc = ep->udc;
-       struct usba_request *req = to_usba_req(_req);
+       struct usba_request *req;
        unsigned long flags;
        u32 status;
 
@@ -837,6 +837,16 @@ static int usba_ep_dequeue(struct usb_ep *_ep, struct usb_request *_req)
 
        spin_lock_irqsave(&udc->lock, flags);
 
+       list_for_each_entry(req, &ep->queue, queue) {
+               if (&req->req == _req)
+                       break;
+       }
+
+       if (&req->req != _req) {
+               spin_unlock_irqrestore(&udc->lock, flags);
+               return -EINVAL;
+       }
+
        if (req->using_dma) {
                /*
                 * If this request is currently being transferred,
@@ -1563,7 +1573,6 @@ static void usba_ep_irq(struct usba_udc *udc, struct usba_ep *ep)
        if ((epstatus & epctrl) & USBA_RX_BK_RDY) {
                DBG(DBG_BUS, "%s: RX data ready\n", ep->ep.name);
                receive_data(ep);
-               usba_ep_writel(ep, CLR_STA, USBA_RX_BK_RDY);
        }
 }
 
index ff67ceac77c410a8f6a9ab27fc63f63afd9dc01b..d4fe8d769bd673c384707fae714944885061911d 100644 (file)
@@ -718,10 +718,11 @@ static int ep_queue(struct bdc_ep *ep, struct bdc_req *req)
        struct bdc *bdc;
        int ret = 0;
 
-       bdc = ep->bdc;
        if (!req || !ep || !ep->usb_ep.desc)
                return -EINVAL;
 
+       bdc = ep->bdc;
+
        req->usb_req.actual = 0;
        req->usb_req.status = -EINPROGRESS;
        req->epnum = ep->ep_num;
index e113fd73aeae7148b0cbcd0d424aebb16d84a694..f9a332775c4781e57faf7bd584d5d58cbf5397e3 100644 (file)
@@ -1581,6 +1581,10 @@ iso_stream_schedule (
        else
                next = (now + 2 + 7) & ~0x07;   /* full frame cache */
 
+       /* If needed, initialize last_iso_frame so that this URB will be seen */
+       if (ehci->isoc_count == 0)
+               ehci->last_iso_frame = now >> 3;
+
        /*
         * Use ehci->last_iso_frame as the base.  There can't be any
         * TDs scheduled for earlier than that.
@@ -1600,11 +1604,11 @@ iso_stream_schedule (
         */
        now2 = (now - base) & (mod - 1);
 
-       /* Is the schedule already full? */
+       /* Is the schedule about to wrap around? */
        if (unlikely(!empty && start < period)) {
-               ehci_dbg(ehci, "iso sched full %p (%u-%u < %u mod %u)\n",
+               ehci_dbg(ehci, "request %p would overflow (%u-%u < %u mod %u)\n",
                                urb, stream->next_uframe, base, period, mod);
-               status = -ENOSPC;
+               status = -EFBIG;
                goto fail;
        }
 
@@ -1671,10 +1675,6 @@ iso_stream_schedule (
        urb->start_frame = start & (mod - 1);
        if (!stream->highspeed)
                urb->start_frame >>= 3;
-
-       /* Make sure scan_isoc() sees these */
-       if (ehci->isoc_count == 0)
-               ehci->last_iso_frame = now >> 3;
        return status;
 
  fail:
index 19a9af1b4d749cd577e1215a200679f9a1c8b37d..ff9af29b4e9f6b0ea4bfa1decd8050fcbede061d 100644 (file)
@@ -451,7 +451,7 @@ static int tegra_ehci_probe(struct platform_device *pdev)
 
        u_phy = devm_usb_get_phy_by_phandle(&pdev->dev, "nvidia,phy", 0);
        if (IS_ERR(u_phy)) {
-               err = PTR_ERR(u_phy);
+               err = -EPROBE_DEFER;
                goto cleanup_clk_en;
        }
        hcd->usb_phy = u_phy;
index dd483c13565bb7bbedc561d6e39fccee1477c279..ce636466edb7a390efb346d3b0f511b9d4eb5404 100644 (file)
@@ -567,7 +567,8 @@ static void quirk_usb_handoff_ohci(struct pci_dev *pdev)
 {
        void __iomem *base;
        u32 control;
-       u32 fminterval;
+       u32 fminterval = 0;
+       bool no_fminterval = false;
        int cnt;
 
        if (!mmio_resource_enabled(pdev, 0))
@@ -577,6 +578,13 @@ static void quirk_usb_handoff_ohci(struct pci_dev *pdev)
        if (base == NULL)
                return;
 
+       /*
+        * ULi M5237 OHCI controller locks the whole system when accessing
+        * the OHCI_FMINTERVAL offset.
+        */
+       if (pdev->vendor == PCI_VENDOR_ID_AL && pdev->device == 0x5237)
+               no_fminterval = true;
+
        control = readl(base + OHCI_CONTROL);
 
 /* On PA-RISC, PDC can leave IR set incorrectly; ignore it there. */
@@ -615,7 +623,9 @@ static void quirk_usb_handoff_ohci(struct pci_dev *pdev)
        }
 
        /* software reset of the controller, preserving HcFmInterval */
-       fminterval = readl(base + OHCI_FMINTERVAL);
+       if (!no_fminterval)
+               fminterval = readl(base + OHCI_FMINTERVAL);
+
        writel(OHCI_HCR, base + OHCI_CMDSTATUS);
 
        /* reset requires max 10 us delay */
@@ -624,7 +634,9 @@ static void quirk_usb_handoff_ohci(struct pci_dev *pdev)
                        break;
                udelay(1);
        }
-       writel(fminterval, base + OHCI_FMINTERVAL);
+
+       if (!no_fminterval)
+               writel(fminterval, base + OHCI_FMINTERVAL);
 
        /* Now the controller is safely in SUSPEND and nothing can wake it up */
        iounmap(base);
index 142b601f95636fdff622bca8c4fb1a9aef87093b..7f76c8a12f89db425e19c4f3a2a5200de542dbd7 100644 (file)
@@ -82,6 +82,8 @@ static void xhci_pci_quirks(struct device *dev, struct xhci_hcd *xhci)
                                "must be suspended extra slowly",
                                pdev->revision);
                }
+               if (pdev->device == PCI_DEVICE_ID_FRESCO_LOGIC_PDK)
+                       xhci->quirks |= XHCI_BROKEN_STREAMS;
                /* Fresco Logic confirms: all revisions of this chip do not
                 * support MSI, even though some of them claim to in their PCI
                 * capabilities.
index 01fcbb5eb06e7ec3d03bcd81d90941f889c5654a..c50d8d202618521793b37a8bd57d7b343cd757fd 100644 (file)
@@ -3803,6 +3803,15 @@ static int xhci_setup_device(struct usb_hcd *hcd, struct usb_device *udev,
                return -EINVAL;
        }
 
+       if (setup == SETUP_CONTEXT_ONLY) {
+               slot_ctx = xhci_get_slot_ctx(xhci, virt_dev->out_ctx);
+               if (GET_SLOT_STATE(le32_to_cpu(slot_ctx->dev_state)) ==
+                   SLOT_STATE_DEFAULT) {
+                       xhci_dbg(xhci, "Slot already in default state\n");
+                       return 0;
+               }
+       }
+
        command = xhci_alloc_command(xhci, false, false, GFP_KERNEL);
        if (!command)
                return -ENOMEM;
index 9d68372dd9aaa01d72b3a192959b3bccc2b2de93..b005010240e5b30df0823d220664f5829855ac81 100644 (file)
@@ -72,6 +72,8 @@ config USB_MUSB_DA8XX
 
 config USB_MUSB_TUSB6010
        tristate "TUSB6010"
+       depends on ARCH_OMAP2PLUS || COMPILE_TEST
+       depends on NOP_USB_XCEIV = USB_MUSB_HDRC # both built-in or both modules
 
 config USB_MUSB_OMAP2PLUS
        tristate "OMAP2430 and onwards"
@@ -85,6 +87,7 @@ config USB_MUSB_AM35X
 config USB_MUSB_DSPS
        tristate "TI DSPS platforms"
        select USB_MUSB_AM335X_CHILD
+       depends on ARCH_OMAP2PLUS || COMPILE_TEST
        depends on OF_IRQ
 
 config USB_MUSB_BLACKFIN
@@ -93,6 +96,7 @@ config USB_MUSB_BLACKFIN
 
 config USB_MUSB_UX500
        tristate "Ux500 platforms"
+       depends on ARCH_U8500 || COMPILE_TEST
 
 config USB_MUSB_JZ4740
        tristate "JZ4740"
index a441a2de8619e51d5f639e47332f3ec120d2a4f2..1782501456139aeb8f970fa51311a215a909d555 100644 (file)
@@ -63,7 +63,7 @@ static void bfin_writew(void __iomem *addr, unsigned offset, u16 data)
        bfin_write16(addr + offset, data);
 }
 
-static void binf_writel(void __iomem *addr, unsigned offset, u32 data)
+static void bfin_writel(void __iomem *addr, unsigned offset, u32 data)
 {
        bfin_write16(addr + offset, (u16)data);
 }
index f64fd964dc6d544b0fecee86a1fd9bd85993862a..c39a16ad78329194e78135464283dea4e760a4cc 100644 (file)
@@ -628,9 +628,9 @@ static int cppi41_dma_controller_start(struct cppi41_dma_controller *controller)
                ret = of_property_read_string_index(np, "dma-names", i, &str);
                if (ret)
                        goto err;
-               if (!strncmp(str, "tx", 2))
+               if (strstarts(str, "tx"))
                        is_tx = 1;
-               else if (!strncmp(str, "rx", 2))
+               else if (strstarts(str, "rx"))
                        is_tx = 0;
                else {
                        dev_err(dev, "Wrong dmatype %s\n", str);
index ad3701a9738964d5f7846e76ec69a31660badda1..48131aa8472cfef70b19d6a2a72db0a8d6b2db85 100644 (file)
@@ -59,20 +59,12 @@ static const struct musb_register_map musb_regmap[] = {
        { "RxMaxPp",    MUSB_RXMAXP,    16 },
        { "RxCSR",      MUSB_RXCSR,     16 },
        { "RxCount",    MUSB_RXCOUNT,   16 },
-       { "ConfigData", MUSB_CONFIGDATA,8 },
        { "IntrRxE",    MUSB_INTRRXE,   16 },
        { "IntrTxE",    MUSB_INTRTXE,   16 },
        { "IntrUsbE",   MUSB_INTRUSBE,  8 },
        { "DevCtl",     MUSB_DEVCTL,    8 },
-       { "BabbleCtl",  MUSB_BABBLE_CTL,8 },
-       { "TxFIFOsz",   MUSB_TXFIFOSZ,  8 },
-       { "RxFIFOsz",   MUSB_RXFIFOSZ,  8 },
-       { "TxFIFOadd",  MUSB_TXFIFOADD, 16 },
-       { "RxFIFOadd",  MUSB_RXFIFOADD, 16 },
        { "VControl",   0x68,           32 },
        { "HWVers",     0x69,           16 },
-       { "EPInfo",     MUSB_EPINFO,    8 },
-       { "RAMInfo",    MUSB_RAMINFO,   8 },
        { "LinkInfo",   MUSB_LINKINFO,  8 },
        { "VPLen",      MUSB_VPLEN,     8 },
        { "HS_EOF1",    MUSB_HS_EOF1,   8 },
@@ -103,6 +95,16 @@ static const struct musb_register_map musb_regmap[] = {
        { "DMA_CNTLch7",        0x274,  16 },
        { "DMA_ADDRch7",        0x278,  32 },
        { "DMA_COUNTch7",       0x27C,  32 },
+#ifndef CONFIG_BLACKFIN
+       { "ConfigData", MUSB_CONFIGDATA,8 },
+       { "BabbleCtl",  MUSB_BABBLE_CTL,8 },
+       { "TxFIFOsz",   MUSB_TXFIFOSZ,  8 },
+       { "RxFIFOsz",   MUSB_RXFIFOSZ,  8 },
+       { "TxFIFOadd",  MUSB_TXFIFOADD, 16 },
+       { "RxFIFOadd",  MUSB_RXFIFOADD, 16 },
+       { "EPInfo",     MUSB_EPINFO,    8 },
+       { "RAMInfo",    MUSB_RAMINFO,   8 },
+#endif
        {  }    /* Terminating Entry */
 };
 
@@ -197,30 +199,30 @@ static ssize_t musb_test_mode_write(struct file *file,
        if (copy_from_user(&buf, ubuf, min_t(size_t, sizeof(buf) - 1, count)))
                return -EFAULT;
 
-       if (!strncmp(buf, "force host", 9))
+       if (strstarts(buf, "force host"))
                test = MUSB_TEST_FORCE_HOST;
 
-       if (!strncmp(buf, "fifo access", 11))
+       if (strstarts(buf, "fifo access"))
                test = MUSB_TEST_FIFO_ACCESS;
 
-       if (!strncmp(buf, "force full-speed", 15))
+       if (strstarts(buf, "force full-speed"))
                test = MUSB_TEST_FORCE_FS;
 
-       if (!strncmp(buf, "force high-speed", 15))
+       if (strstarts(buf, "force high-speed"))
                test = MUSB_TEST_FORCE_HS;
 
-       if (!strncmp(buf, "test packet", 10)) {
+       if (strstarts(buf, "test packet")) {
                test = MUSB_TEST_PACKET;
                musb_load_testpacket(musb);
        }
 
-       if (!strncmp(buf, "test K", 6))
+       if (strstarts(buf, "test K"))
                test = MUSB_TEST_K;
 
-       if (!strncmp(buf, "test J", 6))
+       if (strstarts(buf, "test J"))
                test = MUSB_TEST_J;
 
-       if (!strncmp(buf, "test SE0 NAK", 12))
+       if (strstarts(buf, "test SE0 NAK"))
                test = MUSB_TEST_SE0_NAK;
 
        musb_writeb(musb->mregs, MUSB_TESTMODE, test);
index 23d474d3d7f466188bcf4cee8c8f974e4274d22f..883a9adfdfff5f0c1643036e0be7d7d22d1e73a8 100644 (file)
@@ -2663,7 +2663,6 @@ void musb_host_cleanup(struct musb *musb)
        if (musb->port_mode == MUSB_PORT_MODE_GADGET)
                return;
        usb_remove_hcd(musb->hcd);
-       musb->hcd = NULL;
 }
 
 void musb_host_free(struct musb *musb)
index 699e38c73d82c2ae76feddfe07f85a54ca76dd73..697a741a0cb1ed36ff336af31d8c3cd7d2fd32a5 100644 (file)
@@ -338,7 +338,6 @@ static void mv_otg_update_inputs(struct mv_otg *mvotg)
 static void mv_otg_update_state(struct mv_otg *mvotg)
 {
        struct mv_otg_ctrl *otg_ctrl = &mvotg->otg_ctrl;
-       struct usb_phy *phy = &mvotg->phy;
        int old_state = mvotg->phy.otg->state;
 
        switch (old_state) {
@@ -858,10 +857,10 @@ static int mv_otg_suspend(struct platform_device *pdev, pm_message_t state)
 {
        struct mv_otg *mvotg = platform_get_drvdata(pdev);
 
-       if (mvotg->phy.state != OTG_STATE_B_IDLE) {
+       if (mvotg->phy.otg->state != OTG_STATE_B_IDLE) {
                dev_info(&pdev->dev,
                         "OTG state is not B_IDLE, it is %d!\n",
-                        mvotg->phy.state);
+                        mvotg->phy.otg->state);
                return -EAGAIN;
        }
 
index b4066a001ba01573f9546749b7d4978180c48dc5..ccfdfb24b24017e8eda929fb30fb8363311ab7d2 100644 (file)
@@ -34,7 +34,7 @@ static struct usb_phy *__usb_find_phy(struct list_head *list,
                return phy;
        }
 
-       return ERR_PTR(-ENODEV);
+       return ERR_PTR(-EPROBE_DEFER);
 }
 
 static struct usb_phy *__usb_find_phy_dev(struct device *dev,
@@ -59,6 +59,9 @@ static struct usb_phy *__of_usb_find_phy(struct device_node *node)
 {
        struct usb_phy  *phy;
 
+       if (!of_device_is_available(node))
+               return ERR_PTR(-ENODEV);
+
        list_for_each_entry(phy, &phy_list, head) {
                if (node != phy->dev->of_node)
                        continue;
@@ -66,7 +69,7 @@ static struct usb_phy *__of_usb_find_phy(struct device_node *node)
                return phy;
        }
 
-       return ERR_PTR(-ENODEV);
+       return ERR_PTR(-EPROBE_DEFER);
 }
 
 static void devm_usb_phy_release(struct device *dev, void *res)
@@ -190,10 +193,13 @@ struct usb_phy *devm_usb_get_phy_by_phandle(struct device *dev,
        spin_lock_irqsave(&phy_lock, flags);
 
        phy = __of_usb_find_phy(node);
-       if (IS_ERR(phy) || !try_module_get(phy->dev->driver->owner)) {
-               if (!IS_ERR(phy))
-                       phy = ERR_PTR(-EPROBE_DEFER);
+       if (IS_ERR(phy)) {
+               devres_free(ptr);
+               goto err1;
+       }
 
+       if (!try_module_get(phy->dev->driver->owner)) {
+               phy = ERR_PTR(-ENODEV);
                devres_free(ptr);
                goto err1;
        }
index 8d7fc48b1f307efffa1e5ec40a6e3250b852a54c..29fa1c3d0089bee738ed4f54a8b65d4f82dd0c03 100644 (file)
@@ -46,6 +46,8 @@ static struct console usbcons;
  * ------------------------------------------------------------
  */
 
+static const struct tty_operations usb_console_fake_tty_ops = {
+};
 
 /*
  * The parsing of the command line works exactly like the
@@ -137,13 +139,17 @@ static int usb_console_setup(struct console *co, char *options)
                                goto reset_open_count;
                        }
                        kref_init(&tty->kref);
-                       tty_port_tty_set(&port->port, tty);
                        tty->driver = usb_serial_tty_driver;
                        tty->index = co->index;
+                       init_ldsem(&tty->ldisc_sem);
+                       INIT_LIST_HEAD(&tty->tty_files);
+                       kref_get(&tty->driver->kref);
+                       tty->ops = &usb_console_fake_tty_ops;
                        if (tty_init_termios(tty)) {
                                retval = -ENOMEM;
-                               goto free_tty;
+                               goto put_tty;
                        }
+                       tty_port_tty_set(&port->port, tty);
                }
 
                /* only call the device specific open if this
@@ -161,7 +167,7 @@ static int usb_console_setup(struct console *co, char *options)
                        serial->type->set_termios(tty, port, &dummy);
 
                        tty_port_tty_set(&port->port, NULL);
-                       kfree(tty);
+                       tty_kref_put(tty);
                }
                set_bit(ASYNCB_INITIALIZED, &port->port.flags);
        }
@@ -177,8 +183,8 @@ static int usb_console_setup(struct console *co, char *options)
 
  fail:
        tty_port_tty_set(&port->port, NULL);
free_tty:
-       kfree(tty);
put_tty:
+       tty_kref_put(tty);
  reset_open_count:
        port->port.count = 0;
        usb_autopm_put_interface(serial->interface);
index 6c4eb3cf5efd599653641e5d96d20b05610a6ed5..f4c56fc1a9f64dd32fae247c351c1b34e0d6400e 100644 (file)
@@ -120,10 +120,12 @@ static const struct usb_device_id id_table[] = {
        { USB_DEVICE(0x10C4, 0x85F8) }, /* Virtenio Preon32 */
        { USB_DEVICE(0x10C4, 0x8664) }, /* AC-Services CAN-IF */
        { USB_DEVICE(0x10C4, 0x8665) }, /* AC-Services OBD-IF */
-       { USB_DEVICE(0x10C4, 0x8875) }, /* CEL MeshConnect USB Stick */
+       { USB_DEVICE(0x10C4, 0x8856) }, /* CEL EM357 ZigBee USB Stick - LR */
+       { USB_DEVICE(0x10C4, 0x8857) }, /* CEL EM357 ZigBee USB Stick */
        { USB_DEVICE(0x10C4, 0x88A4) }, /* MMB Networks ZigBee USB Device */
        { USB_DEVICE(0x10C4, 0x88A5) }, /* Planet Innovation Ingeni ZigBee USB Device */
        { USB_DEVICE(0x10C4, 0x8946) }, /* Ketra N1 Wireless Interface */
+       { USB_DEVICE(0x10C4, 0x8977) }, /* CEL MeshWorks DevKit Device */
        { USB_DEVICE(0x10C4, 0xEA60) }, /* Silicon Labs factory default */
        { USB_DEVICE(0x10C4, 0xEA61) }, /* Silicon Labs factory default */
        { USB_DEVICE(0x10C4, 0xEA70) }, /* Silicon Labs factory default */
index 1bd192290b08df0fb697fa91f2517b6756680012..ccf1df7c4b80f3f7a596fa3d1d8904eb64a78db6 100644 (file)
@@ -286,7 +286,7 @@ static int usb_serial_generic_submit_read_urb(struct usb_serial_port *port,
 
        res = usb_submit_urb(port->read_urbs[index], mem_flags);
        if (res) {
-               if (res != -EPERM) {
+               if (res != -EPERM && res != -ENODEV) {
                        dev_err(&port->dev,
                                        "%s - usb_submit_urb failed: %d\n",
                                        __func__, res);
@@ -373,7 +373,7 @@ void usb_serial_generic_read_bulk_callback(struct urb *urb)
                                                        __func__, urb->status);
                return;
        default:
-               dev_err(&port->dev, "%s - nonzero urb status: %d\n",
+               dev_dbg(&port->dev, "%s - nonzero urb status: %d\n",
                                                        __func__, urb->status);
                goto resubmit;
        }
index 077c714f1285171ee3b9e4c418e0df42f60cd42c..e07b15ed58148698d939370ac8bf73b20141669a 100644 (file)
@@ -410,6 +410,8 @@ static void usa26_instat_callback(struct urb *urb)
        }
        port = serial->port[msg->port];
        p_priv = usb_get_serial_port_data(port);
+       if (!p_priv)
+               goto resubmit;
 
        /* Update handshaking pin state information */
        old_dcd_state = p_priv->dcd_state;
@@ -420,7 +422,7 @@ static void usa26_instat_callback(struct urb *urb)
 
        if (old_dcd_state != p_priv->dcd_state)
                tty_port_tty_hangup(&port->port, true);
-
+resubmit:
        /* Resubmit urb so we continue receiving */
        err = usb_submit_urb(urb, GFP_ATOMIC);
        if (err != 0)
@@ -527,6 +529,8 @@ static void usa28_instat_callback(struct urb *urb)
        }
        port = serial->port[msg->port];
        p_priv = usb_get_serial_port_data(port);
+       if (!p_priv)
+               goto resubmit;
 
        /* Update handshaking pin state information */
        old_dcd_state = p_priv->dcd_state;
@@ -537,7 +541,7 @@ static void usa28_instat_callback(struct urb *urb)
 
        if (old_dcd_state != p_priv->dcd_state && old_dcd_state)
                tty_port_tty_hangup(&port->port, true);
-
+resubmit:
                /* Resubmit urb so we continue receiving */
        err = usb_submit_urb(urb, GFP_ATOMIC);
        if (err != 0)
@@ -607,6 +611,8 @@ static void usa49_instat_callback(struct urb *urb)
        }
        port = serial->port[msg->portNumber];
        p_priv = usb_get_serial_port_data(port);
+       if (!p_priv)
+               goto resubmit;
 
        /* Update handshaking pin state information */
        old_dcd_state = p_priv->dcd_state;
@@ -617,7 +623,7 @@ static void usa49_instat_callback(struct urb *urb)
 
        if (old_dcd_state != p_priv->dcd_state && old_dcd_state)
                tty_port_tty_hangup(&port->port, true);
-
+resubmit:
        /* Resubmit urb so we continue receiving */
        err = usb_submit_urb(urb, GFP_ATOMIC);
        if (err != 0)
@@ -855,6 +861,8 @@ static void usa90_instat_callback(struct urb *urb)
 
        port = serial->port[0];
        p_priv = usb_get_serial_port_data(port);
+       if (!p_priv)
+               goto resubmit;
 
        /* Update handshaking pin state information */
        old_dcd_state = p_priv->dcd_state;
@@ -865,7 +873,7 @@ static void usa90_instat_callback(struct urb *urb)
 
        if (old_dcd_state != p_priv->dcd_state && old_dcd_state)
                tty_port_tty_hangup(&port->port, true);
-
+resubmit:
        /* Resubmit urb so we continue receiving */
        err = usb_submit_urb(urb, GFP_ATOMIC);
        if (err != 0)
@@ -926,6 +934,8 @@ static void usa67_instat_callback(struct urb *urb)
 
        port = serial->port[msg->port];
        p_priv = usb_get_serial_port_data(port);
+       if (!p_priv)
+               goto resubmit;
 
        /* Update handshaking pin state information */
        old_dcd_state = p_priv->dcd_state;
@@ -934,7 +944,7 @@ static void usa67_instat_callback(struct urb *urb)
 
        if (old_dcd_state != p_priv->dcd_state && old_dcd_state)
                tty_port_tty_hangup(&port->port, true);
-
+resubmit:
        /* Resubmit urb so we continue receiving */
        err = usb_submit_urb(urb, GFP_ATOMIC);
        if (err != 0)
index 7a4c21b4f67613f7bf64839b4cf4faf09804355e..efdcee15b52030e455ce3c6e17d401d4a5e2660d 100644 (file)
@@ -234,6 +234,8 @@ static void option_instat_callback(struct urb *urb);
 
 #define QUALCOMM_VENDOR_ID                     0x05C6
 
+#define SIERRA_VENDOR_ID                       0x1199
+
 #define CMOTECH_VENDOR_ID                      0x16d8
 #define CMOTECH_PRODUCT_6001                   0x6001
 #define CMOTECH_PRODUCT_CMU_300                        0x6002
@@ -512,7 +514,7 @@ enum option_blacklist_reason {
                OPTION_BLACKLIST_RESERVED_IF = 2
 };
 
-#define MAX_BL_NUM  8
+#define MAX_BL_NUM  11
 struct option_blacklist_info {
        /* bitfield of interface numbers for OPTION_BLACKLIST_SENDSETUP */
        const unsigned long sendsetup;
@@ -601,6 +603,11 @@ static const struct option_blacklist_info telit_le920_blacklist = {
        .reserved = BIT(1) | BIT(5),
 };
 
+static const struct option_blacklist_info sierra_mc73xx_blacklist = {
+       .sendsetup = BIT(0) | BIT(2),
+       .reserved = BIT(8) | BIT(10) | BIT(11),
+};
+
 static const struct usb_device_id option_ids[] = {
        { USB_DEVICE(OPTION_VENDOR_ID, OPTION_PRODUCT_COLT) },
        { USB_DEVICE(OPTION_VENDOR_ID, OPTION_PRODUCT_RICOLA) },
@@ -1098,6 +1105,8 @@ static const struct usb_device_id option_ids[] = {
        { USB_DEVICE(QUALCOMM_VENDOR_ID, 0x6613)}, /* Onda H600/ZTE MF330 */
        { USB_DEVICE(QUALCOMM_VENDOR_ID, 0x0023)}, /* ONYX 3G device */
        { USB_DEVICE(QUALCOMM_VENDOR_ID, 0x9000)}, /* SIMCom SIM5218 */
+       { USB_DEVICE_INTERFACE_CLASS(SIERRA_VENDOR_ID, 0x68c0, 0xff),
+         .driver_info = (kernel_ulong_t)&sierra_mc73xx_blacklist }, /* MC73xx */
        { USB_DEVICE(CMOTECH_VENDOR_ID, CMOTECH_PRODUCT_6001) },
        { USB_DEVICE(CMOTECH_VENDOR_ID, CMOTECH_PRODUCT_CMU_300) },
        { USB_DEVICE(CMOTECH_VENDOR_ID, CMOTECH_PRODUCT_6003),
index cb3e14780a7e0c6182e5f9bf3ad505b61fa75684..9c63897b3a564012ea63f99b9e5e73bc48b93d36 100644 (file)
@@ -142,7 +142,6 @@ static const struct usb_device_id id_table[] = {
        {DEVICE_SWI(0x0f3d, 0x68a2)},   /* Sierra Wireless MC7700 */
        {DEVICE_SWI(0x114f, 0x68a2)},   /* Sierra Wireless MC7750 */
        {DEVICE_SWI(0x1199, 0x68a2)},   /* Sierra Wireless MC7710 */
-       {DEVICE_SWI(0x1199, 0x68c0)},   /* Sierra Wireless MC73xx */
        {DEVICE_SWI(0x1199, 0x901c)},   /* Sierra Wireless EM7700 */
        {DEVICE_SWI(0x1199, 0x901f)},   /* Sierra Wireless EM7355 */
        {DEVICE_SWI(0x1199, 0x9040)},   /* Sierra Wireless Modem */
index 8a6f371ed6e77e3ccdc99632c3cd41ebeb155213..9893d696fc973e9e4183b57b56b3ceb22570942f 100644 (file)
@@ -69,16 +69,39 @@ static int uas_use_uas_driver(struct usb_interface *intf,
                return 0;
 
        /*
-        * ASM1051 and older ASM1053 devices have the same usb-id, and UAS is
-        * broken on the ASM1051, use the number of streams to differentiate.
-        * New ASM1053-s also support 32 streams, but have a different prod-id.
+        * ASMedia has a number of usb3 to sata bridge chips, at the time of
+        * this writing the following versions exist:
+        * ASM1051 - no uas support version
+        * ASM1051 - with broken (*) uas support
+        * ASM1053 - with working uas support
+        * ASM1153 - with working uas support
+        *
+        * Devices with these chips re-use a number of device-ids over the
+        * entire line, so the device-id is useless to determine if we're
+        * dealing with an ASM1051 (which we want to avoid).
+        *
+        * The ASM1153 can be identified by config.MaxPower == 0,
+        * where as the ASM105x models have config.MaxPower == 36.
+        *
+        * Differentiating between the ASM1053 and ASM1051 is trickier, when
+        * connected over USB-3 we can look at the number of streams supported,
+        * ASM1051 supports 32 streams, where as early ASM1053 versions support
+        * 16 streams, newer ASM1053-s also support 32 streams, but have a
+        * different prod-id.
+        *
+        * (*) ASM1051 chips do work with UAS with some disks (with the
+        *     US_FL_NO_REPORT_OPCODES quirk), but are broken with other disks
         */
        if (le16_to_cpu(udev->descriptor.idVendor) == 0x174c &&
-                       le16_to_cpu(udev->descriptor.idProduct) == 0x55aa) {
-               if (udev->speed < USB_SPEED_SUPER) {
+                       (le16_to_cpu(udev->descriptor.idProduct) == 0x5106 ||
+                        le16_to_cpu(udev->descriptor.idProduct) == 0x55aa)) {
+               if (udev->actconfig->desc.bMaxPower == 0) {
+                       /* ASM1153, do nothing */
+               } else if (udev->speed < USB_SPEED_SUPER) {
                        /* No streams info, assume ASM1051 */
                        flags |= US_FL_IGNORE_UAS;
                } else if (usb_ss_max_streams(&eps[1]->ss_ep_comp) == 32) {
+                       /* Possibly an ASM1051, disable uas */
                        flags |= US_FL_IGNORE_UAS;
                }
        }
index 18a283d6de1c8bd18663b57bbf7499510c49fa2d..6df4357d9ee358b36d33961507e8677bd346d432 100644 (file)
  * and don't forget to CC: the USB development list <linux-usb@vger.kernel.org>
  */
 
+/*
+ * Apricorn USB3 dongle sometimes returns "USBSUSBSUSBS" in response to SCSI
+ * commands in UAS mode.  Observed with the 1.28 firmware; are there others?
+ */
+UNUSUAL_DEV(0x0984, 0x0301, 0x0128, 0x0128,
+               "Apricorn",
+               "",
+               USB_SC_DEVICE, USB_PR_DEVICE, NULL,
+               US_FL_IGNORE_UAS),
+
 /* https://bugzilla.kernel.org/show_bug.cgi?id=79511 */
 UNUSUAL_DEV(0x0bc2, 0x2312, 0x0000, 0x9999,
                "Seagate",
@@ -68,6 +78,20 @@ UNUSUAL_DEV(0x0bc2, 0xa003, 0x0000, 0x9999,
                USB_SC_DEVICE, USB_PR_DEVICE, NULL,
                US_FL_NO_ATA_1X),
 
+/* Reported-by: Marcin Zajączkowski <mszpak@wp.pl> */
+UNUSUAL_DEV(0x0bc2, 0xa013, 0x0000, 0x9999,
+               "Seagate",
+               "Backup Plus",
+               USB_SC_DEVICE, USB_PR_DEVICE, NULL,
+               US_FL_NO_ATA_1X),
+
+/* Reported-by: Hans de Goede <hdegoede@redhat.com> */
+UNUSUAL_DEV(0x0bc2, 0xa0a4, 0x0000, 0x9999,
+               "Seagate",
+               "Backup Plus Desk",
+               USB_SC_DEVICE, USB_PR_DEVICE, NULL,
+               US_FL_NO_ATA_1X),
+
 /* https://bbs.archlinux.org/viewtopic.php?id=183190 */
 UNUSUAL_DEV(0x0bc2, 0xab20, 0x0000, 0x9999,
                "Seagate",
@@ -82,6 +106,13 @@ UNUSUAL_DEV(0x0bc2, 0xab21, 0x0000, 0x9999,
                USB_SC_DEVICE, USB_PR_DEVICE, NULL,
                US_FL_NO_ATA_1X),
 
+/* Reported-by: G. Richard Bellamy <rbellamy@pteradigm.com> */
+UNUSUAL_DEV(0x0bc2, 0xab2a, 0x0000, 0x9999,
+               "Seagate",
+               "BUP Fast HDD",
+               USB_SC_DEVICE, USB_PR_DEVICE, NULL,
+               US_FL_NO_ATA_1X),
+
 /* Reported-by: Claudio Bizzarri <claudio.bizzarri@gmail.com> */
 UNUSUAL_DEV(0x152d, 0x0567, 0x0000, 0x9999,
                "JMicron",
@@ -89,14 +120,6 @@ UNUSUAL_DEV(0x152d, 0x0567, 0x0000, 0x9999,
                USB_SC_DEVICE, USB_PR_DEVICE, NULL,
                US_FL_NO_REPORT_OPCODES),
 
-/* Most ASM1051 based devices have issues with uas, blacklist them all */
-/* Reported-by: Hans de Goede <hdegoede@redhat.com> */
-UNUSUAL_DEV(0x174c, 0x5106, 0x0000, 0x9999,
-               "ASMedia",
-               "ASM1051",
-               USB_SC_DEVICE, USB_PR_DEVICE, NULL,
-               US_FL_IGNORE_UAS),
-
 /* Reported-by: Hans de Goede <hdegoede@redhat.com> */
 UNUSUAL_DEV(0x2109, 0x0711, 0x0000, 0x9999,
                "VIA",
@@ -104,6 +127,13 @@ UNUSUAL_DEV(0x2109, 0x0711, 0x0000, 0x9999,
                USB_SC_DEVICE, USB_PR_DEVICE, NULL,
                US_FL_NO_ATA_1X),
 
+/* Reported-by: Takeo Nakayama <javhera@gmx.com> */
+UNUSUAL_DEV(0x357d, 0x7788, 0x0000, 0x9999,
+               "JMicron",
+               "JMS566",
+               USB_SC_DEVICE, USB_PR_DEVICE, NULL,
+               US_FL_NO_REPORT_OPCODES),
+
 /* Reported-by: Hans de Goede <hdegoede@redhat.com> */
 UNUSUAL_DEV(0x4971, 0x1012, 0x0000, 0x9999,
                "Hitachi",
index 01c01cb3933fdfc5bce7e9c457d128d2e8f460e4..d695b1673ae532d9ac873bdc5661ccab84995c04 100644 (file)
@@ -911,6 +911,23 @@ vhost_scsi_map_iov_to_prot(struct tcm_vhost_cmd *cmd,
        return 0;
 }
 
+static int vhost_scsi_to_tcm_attr(int attr)
+{
+       switch (attr) {
+       case VIRTIO_SCSI_S_SIMPLE:
+               return TCM_SIMPLE_TAG;
+       case VIRTIO_SCSI_S_ORDERED:
+               return TCM_ORDERED_TAG;
+       case VIRTIO_SCSI_S_HEAD:
+               return TCM_HEAD_TAG;
+       case VIRTIO_SCSI_S_ACA:
+               return TCM_ACA_TAG;
+       default:
+               break;
+       }
+       return TCM_SIMPLE_TAG;
+}
+
 static void tcm_vhost_submission_work(struct work_struct *work)
 {
        struct tcm_vhost_cmd *cmd =
@@ -936,9 +953,10 @@ static void tcm_vhost_submission_work(struct work_struct *work)
        rc = target_submit_cmd_map_sgls(se_cmd, tv_nexus->tvn_se_sess,
                        cmd->tvc_cdb, &cmd->tvc_sense_buf[0],
                        cmd->tvc_lun, cmd->tvc_exp_data_len,
-                       cmd->tvc_task_attr, cmd->tvc_data_direction,
-                       TARGET_SCF_ACK_KREF, sg_ptr, cmd->tvc_sgl_count,
-                       NULL, 0, sg_prot_ptr, cmd->tvc_prot_sgl_count);
+                       vhost_scsi_to_tcm_attr(cmd->tvc_task_attr),
+                       cmd->tvc_data_direction, TARGET_SCF_ACK_KREF,
+                       sg_ptr, cmd->tvc_sgl_count, NULL, 0, sg_prot_ptr,
+                       cmd->tvc_prot_sgl_count);
        if (rc < 0) {
                transport_send_check_condition_and_sense(se_cmd,
                                TCM_LOGICAL_UNIT_COMMUNICATION_FAILURE, 0);
index 1c29bd19e3d5fe9954153a8b821058a1be5ff6d5..0e5fde1d3ffbe5a152035f33063afa98bf84f33e 100644 (file)
@@ -636,7 +636,7 @@ static int broadsheet_spiflash_rewrite_sector(struct broadsheetfb_par *par,
                err = broadsheet_spiflash_read_range(par, start_sector_addr,
                                                data_start_addr, sector_buffer);
                if (err)
-                       return err;
+                       goto out;
        }
 
        /* now we copy our data into the right place in the sector buffer */
@@ -657,7 +657,7 @@ static int broadsheet_spiflash_rewrite_sector(struct broadsheetfb_par *par,
                err = broadsheet_spiflash_read_range(par, tail_start_addr,
                        tail_len, sector_buffer + tail_start_addr);
                if (err)
-                       return err;
+                       goto out;
        }
 
        /* if we got here we have the full sector that we want to rewrite. */
@@ -665,11 +665,13 @@ static int broadsheet_spiflash_rewrite_sector(struct broadsheetfb_par *par,
        /* first erase the sector */
        err = broadsheet_spiflash_erase_sector(par, start_sector_addr);
        if (err)
-               return err;
+               goto out;
 
        /* now write it */
        err = broadsheet_spiflash_write_sector(par, start_sector_addr,
                                        sector_buffer, sector_size);
+out:
+       kfree(sector_buffer);
        return err;
 }
 
index 92cac803dee3c2261655a34a45a6a0c2d170636f..1085c0432158c02038aba6f961ea7e300f7f950b 100644 (file)
@@ -402,7 +402,7 @@ static int __init simplefb_init(void)
        if (ret)
                return ret;
 
-       if (IS_ENABLED(CONFIG_OF) && of_chosen) {
+       if (IS_ENABLED(CONFIG_OF_ADDRESS) && of_chosen) {
                for_each_child_of_node(of_chosen, np) {
                        if (of_device_is_compatible(np, "simple-framebuffer"))
                                of_platform_device_create(np, NULL, NULL);
index ba1107977f2ecafa96cafc04f6498b3fb79a3145..ed19a7d622fa35decaa08b10e83b8bdee8712419 100644 (file)
@@ -131,6 +131,13 @@ static void fuse_req_init_context(struct fuse_req *req)
        req->in.h.pid = current->pid;
 }
 
+void fuse_set_initialized(struct fuse_conn *fc)
+{
+       /* Make sure stores before this are seen on another CPU */
+       smp_wmb();
+       fc->initialized = 1;
+}
+
 static bool fuse_block_alloc(struct fuse_conn *fc, bool for_background)
 {
        return !fc->initialized || (for_background && fc->blocked);
@@ -155,6 +162,8 @@ static struct fuse_req *__fuse_get_req(struct fuse_conn *fc, unsigned npages,
                if (intr)
                        goto out;
        }
+       /* Matches smp_wmb() in fuse_set_initialized() */
+       smp_rmb();
 
        err = -ENOTCONN;
        if (!fc->connected)
@@ -253,6 +262,8 @@ struct fuse_req *fuse_get_req_nofail_nopages(struct fuse_conn *fc,
 
        atomic_inc(&fc->num_waiting);
        wait_event(fc->blocked_waitq, fc->initialized);
+       /* Matches smp_wmb() in fuse_set_initialized() */
+       smp_rmb();
        req = fuse_request_alloc(0);
        if (!req)
                req = get_reserved_req(fc, file);
@@ -511,6 +522,39 @@ void fuse_request_send(struct fuse_conn *fc, struct fuse_req *req)
 }
 EXPORT_SYMBOL_GPL(fuse_request_send);
 
+static void fuse_adjust_compat(struct fuse_conn *fc, struct fuse_args *args)
+{
+       if (fc->minor < 4 && args->in.h.opcode == FUSE_STATFS)
+               args->out.args[0].size = FUSE_COMPAT_STATFS_SIZE;
+
+       if (fc->minor < 9) {
+               switch (args->in.h.opcode) {
+               case FUSE_LOOKUP:
+               case FUSE_CREATE:
+               case FUSE_MKNOD:
+               case FUSE_MKDIR:
+               case FUSE_SYMLINK:
+               case FUSE_LINK:
+                       args->out.args[0].size = FUSE_COMPAT_ENTRY_OUT_SIZE;
+                       break;
+               case FUSE_GETATTR:
+               case FUSE_SETATTR:
+                       args->out.args[0].size = FUSE_COMPAT_ATTR_OUT_SIZE;
+                       break;
+               }
+       }
+       if (fc->minor < 12) {
+               switch (args->in.h.opcode) {
+               case FUSE_CREATE:
+                       args->in.args[0].size = sizeof(struct fuse_open_in);
+                       break;
+               case FUSE_MKNOD:
+                       args->in.args[0].size = FUSE_COMPAT_MKNOD_IN_SIZE;
+                       break;
+               }
+       }
+}
+
 ssize_t fuse_simple_request(struct fuse_conn *fc, struct fuse_args *args)
 {
        struct fuse_req *req;
@@ -520,6 +564,9 @@ ssize_t fuse_simple_request(struct fuse_conn *fc, struct fuse_args *args)
        if (IS_ERR(req))
                return PTR_ERR(req);
 
+       /* Needs to be done after fuse_get_req() so that fc->minor is valid */
+       fuse_adjust_compat(fc, args);
+
        req->in.h.opcode = args->in.h.opcode;
        req->in.h.nodeid = args->in.h.nodeid;
        req->in.numargs = args->in.numargs;
@@ -2127,7 +2174,7 @@ void fuse_abort_conn(struct fuse_conn *fc)
        if (fc->connected) {
                fc->connected = 0;
                fc->blocked = 0;
-               fc->initialized = 1;
+               fuse_set_initialized(fc);
                end_io_requests(fc);
                end_queued_requests(fc);
                end_polls(fc);
@@ -2146,7 +2193,7 @@ int fuse_dev_release(struct inode *inode, struct file *file)
                spin_lock(&fc->lock);
                fc->connected = 0;
                fc->blocked = 0;
-               fc->initialized = 1;
+               fuse_set_initialized(fc);
                end_queued_requests(fc);
                end_polls(fc);
                wake_up_all(&fc->blocked_waitq);
index 252b8a5de8b57f71b841d1fc64c9f48e78b641c2..08e7b1a9d5d0edaca8b94ef386d9200078958df3 100644 (file)
@@ -156,10 +156,7 @@ static void fuse_lookup_init(struct fuse_conn *fc, struct fuse_args *args,
        args->in.args[0].size = name->len + 1;
        args->in.args[0].value = name->name;
        args->out.numargs = 1;
-       if (fc->minor < 9)
-               args->out.args[0].size = FUSE_COMPAT_ENTRY_OUT_SIZE;
-       else
-               args->out.args[0].size = sizeof(struct fuse_entry_out);
+       args->out.args[0].size = sizeof(struct fuse_entry_out);
        args->out.args[0].value = outarg;
 }
 
@@ -422,16 +419,12 @@ static int fuse_create_open(struct inode *dir, struct dentry *entry,
        args.in.h.opcode = FUSE_CREATE;
        args.in.h.nodeid = get_node_id(dir);
        args.in.numargs = 2;
-       args.in.args[0].size = fc->minor < 12 ? sizeof(struct fuse_open_in) :
-                                               sizeof(inarg);
+       args.in.args[0].size = sizeof(inarg);
        args.in.args[0].value = &inarg;
        args.in.args[1].size = entry->d_name.len + 1;
        args.in.args[1].value = entry->d_name.name;
        args.out.numargs = 2;
-       if (fc->minor < 9)
-               args.out.args[0].size = FUSE_COMPAT_ENTRY_OUT_SIZE;
-       else
-               args.out.args[0].size = sizeof(outentry);
+       args.out.args[0].size = sizeof(outentry);
        args.out.args[0].value = &outentry;
        args.out.args[1].size = sizeof(outopen);
        args.out.args[1].value = &outopen;
@@ -539,10 +532,7 @@ static int create_new_entry(struct fuse_conn *fc, struct fuse_args *args,
        memset(&outarg, 0, sizeof(outarg));
        args->in.h.nodeid = get_node_id(dir);
        args->out.numargs = 1;
-       if (fc->minor < 9)
-               args->out.args[0].size = FUSE_COMPAT_ENTRY_OUT_SIZE;
-       else
-               args->out.args[0].size = sizeof(outarg);
+       args->out.args[0].size = sizeof(outarg);
        args->out.args[0].value = &outarg;
        err = fuse_simple_request(fc, args);
        if (err)
@@ -592,8 +582,7 @@ static int fuse_mknod(struct inode *dir, struct dentry *entry, umode_t mode,
        inarg.umask = current_umask();
        args.in.h.opcode = FUSE_MKNOD;
        args.in.numargs = 2;
-       args.in.args[0].size = fc->minor < 12 ? FUSE_COMPAT_MKNOD_IN_SIZE :
-                                               sizeof(inarg);
+       args.in.args[0].size = sizeof(inarg);
        args.in.args[0].value = &inarg;
        args.in.args[1].size = entry->d_name.len + 1;
        args.in.args[1].value = entry->d_name.name;
@@ -899,10 +888,7 @@ static int fuse_do_getattr(struct inode *inode, struct kstat *stat,
        args.in.args[0].size = sizeof(inarg);
        args.in.args[0].value = &inarg;
        args.out.numargs = 1;
-       if (fc->minor < 9)
-               args.out.args[0].size = FUSE_COMPAT_ATTR_OUT_SIZE;
-       else
-               args.out.args[0].size = sizeof(outarg);
+       args.out.args[0].size = sizeof(outarg);
        args.out.args[0].value = &outarg;
        err = fuse_simple_request(fc, &args);
        if (!err) {
@@ -1574,10 +1560,7 @@ static void fuse_setattr_fill(struct fuse_conn *fc, struct fuse_args *args,
        args->in.args[0].size = sizeof(*inarg_p);
        args->in.args[0].value = inarg_p;
        args->out.numargs = 1;
-       if (fc->minor < 9)
-               args->out.args[0].size = FUSE_COMPAT_ATTR_OUT_SIZE;
-       else
-               args->out.args[0].size = sizeof(*outarg_p);
+       args->out.args[0].size = sizeof(*outarg_p);
        args->out.args[0].value = outarg_p;
 }
 
index e0fc6725d1d0d66a4c3c7dce595239631ba353b1..1cdfb07c1376b4f4b5633e86fdbdfc4320953de2 100644 (file)
@@ -906,4 +906,6 @@ int fuse_write_inode(struct inode *inode, struct writeback_control *wbc);
 int fuse_do_setattr(struct inode *inode, struct iattr *attr,
                    struct file *file);
 
+void fuse_set_initialized(struct fuse_conn *fc);
+
 #endif /* _FS_FUSE_I_H */
index 6749109f255da69a5c24825aab1f2a25140fbb47..f38256e4476ed2a9101480342bcd0fd90a99fd38 100644 (file)
@@ -424,8 +424,7 @@ static int fuse_statfs(struct dentry *dentry, struct kstatfs *buf)
        args.in.h.opcode = FUSE_STATFS;
        args.in.h.nodeid = get_node_id(dentry->d_inode);
        args.out.numargs = 1;
-       args.out.args[0].size =
-               fc->minor < 4 ? FUSE_COMPAT_STATFS_SIZE : sizeof(outarg);
+       args.out.args[0].size = sizeof(outarg);
        args.out.args[0].value = &outarg;
        err = fuse_simple_request(fc, &args);
        if (!err)
@@ -898,7 +897,7 @@ static void process_init_reply(struct fuse_conn *fc, struct fuse_req *req)
                fc->max_write = max_t(unsigned, 4096, fc->max_write);
                fc->conn_init = 1;
        }
-       fc->initialized = 1;
+       fuse_set_initialized(fc);
        wake_up_all(&fc->blocked_waitq);
 }
 
index 37989f02a226ac40e104ee02efdad39d805686c5..2d881b381d2b787bbb2ff40b151e7496c0abafae 100644 (file)
@@ -201,10 +201,14 @@ static unsigned int kernfs_name_hash(const char *name, const void *ns)
 static int kernfs_name_compare(unsigned int hash, const char *name,
                               const void *ns, const struct kernfs_node *kn)
 {
-       if (hash != kn->hash)
-               return hash - kn->hash;
-       if (ns != kn->ns)
-               return ns - kn->ns;
+       if (hash < kn->hash)
+               return -1;
+       if (hash > kn->hash)
+               return 1;
+       if (ns < kn->ns)
+               return -1;
+       if (ns > kn->ns)
+               return 1;
        return strcmp(name, kn->name);
 }
 
index e94c887da2d72f7043ed010bfa8675b4ad825bb6..55505cbe11afa165ec90ec934301c15a1b9a4314 100644 (file)
@@ -138,10 +138,6 @@ lockd(void *vrqstp)
 
        dprintk("NFS locking service started (ver " LOCKD_VERSION ").\n");
 
-       if (!nlm_timeout)
-               nlm_timeout = LOCKD_DFLT_TIMEO;
-       nlmsvc_timeout = nlm_timeout * HZ;
-
        /*
         * The main request loop. We don't terminate until the last
         * NFS mount or NFS daemon has gone away.
@@ -350,6 +346,10 @@ static struct svc_serv *lockd_create_svc(void)
                printk(KERN_WARNING
                        "lockd_up: no pid, %d users??\n", nlmsvc_users);
 
+       if (!nlm_timeout)
+               nlm_timeout = LOCKD_DFLT_TIMEO;
+       nlmsvc_timeout = nlm_timeout * HZ;
+
        serv = svc_create(&nlmsvc_program, LOCKD_BUFSIZE, svc_rpcb_cleanup);
        if (!serv) {
                printk(KERN_WARNING "lockd_up: create service failed\n");
index 735b8d3fa78c92bf746aff05475be1fa2a82abd6..59e2f905e4ffea324dbf44faf1b666974adc6c23 100644 (file)
@@ -1702,7 +1702,7 @@ static int generic_delete_lease(struct file *filp)
                        break;
        }
        trace_generic_delete_lease(inode, fl);
-       if (fl)
+       if (fl && IS_LEASE(fl))
                error = fl->fl_lmops->lm_change(before, F_UNLCK, &dispose);
        spin_unlock(&inode->i_lock);
        locks_dispose_list(&dispose);
index 03311259b0c45c88de37122cffc0f28c8f6c7e63..953daa44a28232d6863da375e59d44a0b42f49b6 100644 (file)
@@ -228,6 +228,7 @@ static void nfs4_shutdown_client(struct nfs_client *clp)
        kfree(clp->cl_serverowner);
        kfree(clp->cl_serverscope);
        kfree(clp->cl_implid);
+       kfree(clp->cl_owner_id);
 }
 
 void nfs4_free_client(struct nfs_client *clp)
@@ -452,6 +453,14 @@ static void nfs4_swap_callback_idents(struct nfs_client *keep,
        spin_unlock(&nn->nfs_client_lock);
 }
 
+static bool nfs4_match_client_owner_id(const struct nfs_client *clp1,
+               const struct nfs_client *clp2)
+{
+       if (clp1->cl_owner_id == NULL || clp2->cl_owner_id == NULL)
+               return true;
+       return strcmp(clp1->cl_owner_id, clp2->cl_owner_id) == 0;
+}
+
 /**
  * nfs40_walk_client_list - Find server that recognizes a client ID
  *
@@ -483,9 +492,6 @@ int nfs40_walk_client_list(struct nfs_client *new,
                if (pos->rpc_ops != new->rpc_ops)
                        continue;
 
-               if (pos->cl_proto != new->cl_proto)
-                       continue;
-
                if (pos->cl_minorversion != new->cl_minorversion)
                        continue;
 
@@ -510,6 +516,9 @@ int nfs40_walk_client_list(struct nfs_client *new,
                if (pos->cl_clientid != new->cl_clientid)
                        continue;
 
+               if (!nfs4_match_client_owner_id(pos, new))
+                       continue;
+
                atomic_inc(&pos->cl_count);
                spin_unlock(&nn->nfs_client_lock);
 
@@ -566,20 +575,14 @@ static bool nfs4_match_clientids(struct nfs_client *a, struct nfs_client *b)
 }
 
 /*
- * Returns true if the server owners match
+ * Returns true if the server major ids match
  */
 static bool
-nfs4_match_serverowners(struct nfs_client *a, struct nfs_client *b)
+nfs4_check_clientid_trunking(struct nfs_client *a, struct nfs_client *b)
 {
        struct nfs41_server_owner *o1 = a->cl_serverowner;
        struct nfs41_server_owner *o2 = b->cl_serverowner;
 
-       if (o1->minor_id != o2->minor_id) {
-               dprintk("NFS: --> %s server owner minor IDs do not match\n",
-                       __func__);
-               return false;
-       }
-
        if (o1->major_id_sz != o2->major_id_sz)
                goto out_major_mismatch;
        if (memcmp(o1->major_id, o2->major_id, o1->major_id_sz) != 0)
@@ -621,9 +624,6 @@ int nfs41_walk_client_list(struct nfs_client *new,
                if (pos->rpc_ops != new->rpc_ops)
                        continue;
 
-               if (pos->cl_proto != new->cl_proto)
-                       continue;
-
                if (pos->cl_minorversion != new->cl_minorversion)
                        continue;
 
@@ -654,7 +654,19 @@ int nfs41_walk_client_list(struct nfs_client *new,
                if (!nfs4_match_clientids(pos, new))
                        continue;
 
-               if (!nfs4_match_serverowners(pos, new))
+               /*
+                * Note that session trunking is just a special subcase of
+                * client id trunking. In either case, we want to fall back
+                * to using the existing nfs_client.
+                */
+               if (!nfs4_check_clientid_trunking(pos, new))
+                       continue;
+
+               /* Unlike NFSv4.0, we know that NFSv4.1 always uses the
+                * uniform string, however someone might switch the
+                * uniquifier string on us.
+                */
+               if (!nfs4_match_client_owner_id(pos, new))
                        continue;
 
                atomic_inc(&pos->cl_count);
index e7f8d5ff2581a98269a262998beb43ccaca23e3c..c347705b016104de8b0360f163e87c19d9b4d78c 100644 (file)
@@ -1117,8 +1117,6 @@ static int can_open_delegated(struct nfs_delegation *delegation, fmode_t fmode)
                return 0;
        if ((delegation->type & fmode) != fmode)
                return 0;
-       if (test_bit(NFS_DELEGATION_NEED_RECLAIM, &delegation->flags))
-               return 0;
        if (test_bit(NFS_DELEGATION_RETURNING, &delegation->flags))
                return 0;
        nfs_mark_delegation_referenced(delegation);
@@ -4917,11 +4915,14 @@ static void nfs4_init_boot_verifier(const struct nfs_client *clp,
 }
 
 static unsigned int
-nfs4_init_nonuniform_client_string(const struct nfs_client *clp,
+nfs4_init_nonuniform_client_string(struct nfs_client *clp,
                                   char *buf, size_t len)
 {
        unsigned int result;
 
+       if (clp->cl_owner_id != NULL)
+               return strlcpy(buf, clp->cl_owner_id, len);
+
        rcu_read_lock();
        result = scnprintf(buf, len, "Linux NFSv4.0 %s/%s %s",
                                clp->cl_ipaddr,
@@ -4930,24 +4931,32 @@ nfs4_init_nonuniform_client_string(const struct nfs_client *clp,
                                rpc_peeraddr2str(clp->cl_rpcclient,
                                                        RPC_DISPLAY_PROTO));
        rcu_read_unlock();
+       clp->cl_owner_id = kstrdup(buf, GFP_KERNEL);
        return result;
 }
 
 static unsigned int
-nfs4_init_uniform_client_string(const struct nfs_client *clp,
+nfs4_init_uniform_client_string(struct nfs_client *clp,
                                char *buf, size_t len)
 {
        const char *nodename = clp->cl_rpcclient->cl_nodename;
+       unsigned int result;
+
+       if (clp->cl_owner_id != NULL)
+               return strlcpy(buf, clp->cl_owner_id, len);
 
        if (nfs4_client_id_uniquifier[0] != '\0')
-               return scnprintf(buf, len, "Linux NFSv%u.%u %s/%s",
+               result = scnprintf(buf, len, "Linux NFSv%u.%u %s/%s",
                                clp->rpc_ops->version,
                                clp->cl_minorversion,
                                nfs4_client_id_uniquifier,
                                nodename);
-       return scnprintf(buf, len, "Linux NFSv%u.%u %s",
+       else
+               result = scnprintf(buf, len, "Linux NFSv%u.%u %s",
                                clp->rpc_ops->version, clp->cl_minorversion,
                                nodename);
+       clp->cl_owner_id = kstrdup(buf, GFP_KERNEL);
+       return result;
 }
 
 /*
index 08848050922e613f28a1d8f7e4b3ad4c34b463be..db284bff29dcceb39360d458cec3a194745955f8 100644 (file)
@@ -136,8 +136,12 @@ static inline void __tlb_adjust_range(struct mmu_gather *tlb,
 
 static inline void __tlb_reset_range(struct mmu_gather *tlb)
 {
-       tlb->start = TASK_SIZE;
-       tlb->end = 0;
+       if (tlb->fullmm) {
+               tlb->start = tlb->end = ~0;
+       } else {
+               tlb->start = TASK_SIZE;
+               tlb->end = 0;
+       }
 }
 
 /*
diff --git a/include/drm/bridge/dw_hdmi.h b/include/drm/bridge/dw_hdmi.h
new file mode 100644 (file)
index 0000000..5a4f490
--- /dev/null
@@ -0,0 +1,61 @@
+/*
+ * Copyright (C) 2011 Freescale Semiconductor, Inc.
+ *
+ * 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.
+ */
+
+#ifndef __DW_HDMI__
+#define __DW_HDMI__
+
+#include <drm/drmP.h>
+
+enum {
+       DW_HDMI_RES_8,
+       DW_HDMI_RES_10,
+       DW_HDMI_RES_12,
+       DW_HDMI_RES_MAX,
+};
+
+enum dw_hdmi_devtype {
+       IMX6Q_HDMI,
+       IMX6DL_HDMI,
+       RK3288_HDMI,
+};
+
+struct dw_hdmi_mpll_config {
+       unsigned long mpixelclock;
+       struct {
+               u16 cpce;
+               u16 gmp;
+       } res[DW_HDMI_RES_MAX];
+};
+
+struct dw_hdmi_curr_ctrl {
+       unsigned long mpixelclock;
+       u16 curr[DW_HDMI_RES_MAX];
+};
+
+struct dw_hdmi_sym_term {
+       unsigned long mpixelclock;
+       u16 sym_ctr;    /*clock symbol and transmitter control*/
+       u16 term;       /*transmission termination value*/
+};
+
+struct dw_hdmi_plat_data {
+       enum dw_hdmi_devtype dev_type;
+       const struct dw_hdmi_mpll_config *mpll_cfg;
+       const struct dw_hdmi_curr_ctrl *cur_ctr;
+       const struct dw_hdmi_sym_term *sym_term;
+       enum drm_mode_status (*mode_valid)(struct drm_connector *connector,
+                                          struct drm_display_mode *mode);
+};
+
+void dw_hdmi_unbind(struct device *dev, struct device *master, void *data);
+int dw_hdmi_bind(struct device *dev, struct device *master,
+                void *data, struct drm_encoder *encoder,
+                struct resource *iores, int irq,
+                const struct dw_hdmi_plat_data *plat_data);
+#endif /* __IMX_HDMI_H__ */
index e1b2e8b98af7cde2c7276e915cd90ea4794b317e..e928625a9da0be41b7b03508a19f3df2cfb8acb5 100644 (file)
@@ -143,6 +143,7 @@ void drm_err(const char *format, ...);
 #define DRIVER_MODESET     0x2000
 #define DRIVER_PRIME       0x4000
 #define DRIVER_RENDER      0x8000
+#define DRIVER_ATOMIC      0x10000
 
 /***********************************************************************/
 /** \name Macros to make printk easier */
@@ -283,6 +284,8 @@ struct drm_file {
         * in the plane list
         */
        unsigned universal_planes:1;
+       /* true if client understands atomic properties */
+       unsigned atomic:1;
 
        struct pid *pid;
        kuid_t uid;
@@ -744,8 +747,6 @@ struct drm_device {
 
        /** \name Context support */
        /*@{ */
-       bool irq_enabled;               /**< True if irq handler is enabled */
-       int irq;
 
        __volatile__ long context_flag; /**< Context swapping flag */
        int last_context;               /**< Last current context */
@@ -753,6 +754,8 @@ struct drm_device {
 
        /** \name VBLANK IRQ support */
        /*@{ */
+       bool irq_enabled;
+       int irq;
 
        /*
         * At load time, disabling the vblank interrupt won't be allowed since
@@ -954,6 +957,7 @@ extern void drm_master_put(struct drm_master **master);
 extern void drm_put_dev(struct drm_device *dev);
 extern void drm_unplug_dev(struct drm_device *dev);
 extern unsigned int drm_debug;
+extern bool drm_atomic;
 
                                /* Debugfs support */
 #if defined(CONFIG_DEBUG_FS)
index ad2229574dd9456e9ba28a4c8e16f2492963b3b3..51168a8b723a2d45f4ff658eb27d2b54bd5f1d88 100644 (file)
@@ -38,16 +38,25 @@ void drm_atomic_state_free(struct drm_atomic_state *state);
 struct drm_crtc_state * __must_check
 drm_atomic_get_crtc_state(struct drm_atomic_state *state,
                          struct drm_crtc *crtc);
+int drm_atomic_crtc_set_property(struct drm_crtc *crtc,
+               struct drm_crtc_state *state, struct drm_property *property,
+               uint64_t val);
 struct drm_plane_state * __must_check
 drm_atomic_get_plane_state(struct drm_atomic_state *state,
                           struct drm_plane *plane);
+int drm_atomic_plane_set_property(struct drm_plane *plane,
+               struct drm_plane_state *state, struct drm_property *property,
+               uint64_t val);
 struct drm_connector_state * __must_check
 drm_atomic_get_connector_state(struct drm_atomic_state *state,
                               struct drm_connector *connector);
+int drm_atomic_connector_set_property(struct drm_connector *connector,
+               struct drm_connector_state *state, struct drm_property *property,
+               uint64_t val);
 
 int __must_check
-drm_atomic_set_crtc_for_plane(struct drm_atomic_state *state,
-                             struct drm_plane *plane, struct drm_crtc *crtc);
+drm_atomic_set_crtc_for_plane(struct drm_plane_state *plane_state,
+                             struct drm_crtc *crtc);
 void drm_atomic_set_fb_for_plane(struct drm_plane_state *plane_state,
                                 struct drm_framebuffer *fb);
 int __must_check
index f956b413311e15eed5653b348708468d26197ed9..2095917ff8c77d8ca691f34bb3bbb21c726f0f07 100644 (file)
 
 #include <drm/drm_crtc.h>
 
+int drm_atomic_helper_check_modeset(struct drm_device *dev,
+                               struct drm_atomic_state *state);
+int drm_atomic_helper_check_planes(struct drm_device *dev,
+                              struct drm_atomic_state *state);
 int drm_atomic_helper_check(struct drm_device *dev,
                            struct drm_atomic_state *state);
 int drm_atomic_helper_commit(struct drm_device *dev,
index d21135dc7a2225f80bce84f054a642e73c51737e..ac55ab0dc88b0eaba336072de0059d142f130272 100644 (file)
@@ -31,6 +31,7 @@
 #include <linux/idr.h>
 #include <linux/fb.h>
 #include <linux/hdmi.h>
+#include <linux/media-bus-format.h>
 #include <uapi/drm/drm_mode.h>
 #include <uapi/drm/drm_fourcc.h>
 #include <drm/drm_modeset_lock.h>
@@ -63,8 +64,16 @@ struct drm_mode_object {
 
 #define DRM_OBJECT_MAX_PROPERTY 24
 struct drm_object_properties {
-       int count;
-       uint32_t ids[DRM_OBJECT_MAX_PROPERTY];
+       int count, atomic_count;
+       /* NOTE: if we ever start dynamically destroying properties (ie.
+        * not at drm_mode_config_cleanup() time), then we'd have to do
+        * a better job of detaching property from mode objects to avoid
+        * dangling property pointers:
+        */
+       struct drm_property *properties[DRM_OBJECT_MAX_PROPERTY];
+       /* do not read/write values directly, but use drm_object_property_get_value()
+        * and drm_object_property_set_value():
+        */
        uint64_t values[DRM_OBJECT_MAX_PROPERTY];
 };
 
@@ -131,6 +140,9 @@ struct drm_display_info {
        enum subpixel_order subpixel_order;
        u32 color_formats;
 
+       const u32 *bus_formats;
+       unsigned int num_bus_formats;
+
        /* Mask of supported hdmi deep color modes */
        u8 edid_hdmi_dc_modes;
 
@@ -237,7 +249,9 @@ struct drm_atomic_state;
 
 /**
  * struct drm_crtc_state - mutable CRTC state
+ * @crtc: backpointer to the CRTC
  * @enable: whether the CRTC should be enabled, gates all other state
+ * @active: whether the CRTC is actively displaying (used for DPMS)
  * @mode_changed: for use by helpers and drivers when computing state updates
  * @plane_mask: bitmask of (1 << drm_plane_index(plane)) of attached planes
  * @last_vblank_count: for helpers and drivers to capture the vblank of the
@@ -248,9 +262,18 @@ struct drm_atomic_state;
  * @event: optional pointer to a DRM event to signal upon completion of the
  *     state update
  * @state: backpointer to global drm_atomic_state
+ *
+ * Note that the distinction between @enable and @active is rather subtile:
+ * Flipping @active while @enable is set without changing anything else may
+ * never return in a failure from the ->atomic_check callback. Userspace assumes
+ * that a DPMS On will always succeed. In other words: @enable controls resource
+ * assignment, @active controls the actual hardware state.
  */
 struct drm_crtc_state {
+       struct drm_crtc *crtc;
+
        bool enable;
+       bool active;
 
        /* computed state bits used by helpers and drivers */
        bool planes_changed : 1;
@@ -292,6 +315,9 @@ struct drm_crtc_state {
  * @atomic_duplicate_state: duplicate the atomic state for this CRTC
  * @atomic_destroy_state: destroy an atomic state for this CRTC
  * @atomic_set_property: set a property on an atomic state for this CRTC
+ *    (do not call directly, use drm_atomic_crtc_set_property())
+ * @atomic_get_property: get a property on an atomic state for this CRTC
+ *    (do not call directly, use drm_atomic_crtc_get_property())
  *
  * The drm_crtc_funcs structure is the central CRTC management structure
  * in the DRM.  Each CRTC controls one or more connectors (note that the name
@@ -351,6 +377,10 @@ struct drm_crtc_funcs {
                                   struct drm_crtc_state *state,
                                   struct drm_property *property,
                                   uint64_t val);
+       int (*atomic_get_property)(struct drm_crtc *crtc,
+                                  const struct drm_crtc_state *state,
+                                  struct drm_property *property,
+                                  uint64_t *val);
 };
 
 /**
@@ -449,11 +479,14 @@ struct drm_crtc {
 
 /**
  * struct drm_connector_state - mutable connector state
+ * @connector: backpointer to the connector
  * @crtc: CRTC to connect connector to, NULL if disabled
  * @best_encoder: can be used by helpers and drivers to select the encoder
  * @state: backpointer to global drm_atomic_state
  */
 struct drm_connector_state {
+       struct drm_connector *connector;
+
        struct drm_crtc *crtc;  /* do not write directly, use drm_atomic_set_crtc_for_connector() */
 
        struct drm_encoder *best_encoder;
@@ -463,7 +496,7 @@ struct drm_connector_state {
 
 /**
  * struct drm_connector_funcs - control connectors on a given device
- * @dpms: set power state (see drm_crtc_funcs above)
+ * @dpms: set power state
  * @save: save connector state
  * @restore: restore connector state
  * @reset: reset connector after state has been invalidated (e.g. resume)
@@ -475,6 +508,9 @@ struct drm_connector_state {
  * @atomic_duplicate_state: duplicate the atomic state for this connector
  * @atomic_destroy_state: destroy an atomic state for this connector
  * @atomic_set_property: set a property on an atomic state for this connector
+ *    (do not call directly, use drm_atomic_connector_set_property())
+ * @atomic_get_property: get a property on an atomic state for this connector
+ *    (do not call directly, use drm_atomic_connector_get_property())
  *
  * Each CRTC may have one or more connectors attached to it.  The functions
  * below allow the core DRM code to control connectors, enumerate available modes,
@@ -508,6 +544,10 @@ struct drm_connector_funcs {
                                   struct drm_connector_state *state,
                                   struct drm_property *property,
                                   uint64_t val);
+       int (*atomic_get_property)(struct drm_connector *connector,
+                                  const struct drm_connector_state *state,
+                                  struct drm_property *property,
+                                  uint64_t *val);
 };
 
 /**
@@ -693,6 +733,7 @@ struct drm_connector {
 
 /**
  * struct drm_plane_state - mutable plane state
+ * @plane: backpointer to the plane
  * @crtc: currently bound CRTC, NULL if disabled
  * @fb: currently bound framebuffer
  * @fence: optional fence to wait for before scanning out @fb
@@ -709,6 +750,8 @@ struct drm_connector {
  * @state: backpointer to global drm_atomic_state
  */
 struct drm_plane_state {
+       struct drm_plane *plane;
+
        struct drm_crtc *crtc;   /* do not write directly, use drm_atomic_set_crtc_for_plane() */
        struct drm_framebuffer *fb;  /* do not write directly, use drm_atomic_set_fb_for_plane() */
        struct fence *fence;
@@ -735,6 +778,9 @@ struct drm_plane_state {
  * @atomic_duplicate_state: duplicate the atomic state for this plane
  * @atomic_destroy_state: destroy an atomic state for this plane
  * @atomic_set_property: set a property on an atomic state for this plane
+ *    (do not call directly, use drm_atomic_plane_set_property())
+ * @atomic_get_property: get a property on an atomic state for this plane
+ *    (do not call directly, use drm_atomic_plane_get_property())
  */
 struct drm_plane_funcs {
        int (*update_plane)(struct drm_plane *plane,
@@ -758,6 +804,10 @@ struct drm_plane_funcs {
                                   struct drm_plane_state *state,
                                   struct drm_property *property,
                                   uint64_t val);
+       int (*atomic_get_property)(struct drm_plane *plane,
+                                  const struct drm_plane_state *state,
+                                  struct drm_property *property,
+                                  uint64_t *val);
 };
 
 enum drm_plane_type {
@@ -856,7 +906,7 @@ struct drm_bridge {
 /**
  * struct struct drm_atomic_state - the global state object for atomic updates
  * @dev: parent DRM device
- * @flags: state flags like async update
+ * @allow_modeset: allow full modeset
  * @planes: pointer to array of plane pointers
  * @plane_states: pointer to array of plane states pointers
  * @crtcs: pointer to array of CRTC pointers
@@ -868,7 +918,7 @@ struct drm_bridge {
  */
 struct drm_atomic_state {
        struct drm_device *dev;
-       uint32_t flags;
+       bool allow_modeset : 1;
        struct drm_plane **planes;
        struct drm_plane_state **plane_states;
        struct drm_crtc **crtcs;
@@ -1043,6 +1093,7 @@ struct drm_mode_config {
        /* output poll support */
        bool poll_enabled;
        bool poll_running;
+       bool delayed_event;
        struct delayed_work output_poll_work;
 
        /* pointers to standard properties */
@@ -1053,6 +1104,16 @@ struct drm_mode_config {
        struct drm_property *tile_property;
        struct drm_property *plane_type_property;
        struct drm_property *rotation_property;
+       struct drm_property *prop_src_x;
+       struct drm_property *prop_src_y;
+       struct drm_property *prop_src_w;
+       struct drm_property *prop_src_h;
+       struct drm_property *prop_crtc_x;
+       struct drm_property *prop_crtc_y;
+       struct drm_property *prop_crtc_w;
+       struct drm_property *prop_crtc_h;
+       struct drm_property *prop_fb_id;
+       struct drm_property *prop_crtc_id;
 
        /* DVI-I properties */
        struct drm_property *dvi_i_subconnector_property;
@@ -1226,6 +1287,10 @@ int drm_mode_connector_set_tile_property(struct drm_connector *connector);
 extern int drm_mode_connector_update_edid_property(struct drm_connector *connector,
                                                   const struct edid *edid);
 
+extern int drm_display_info_set_bus_formats(struct drm_display_info *info,
+                                           const u32 *formats,
+                                           unsigned int num_formats);
+
 static inline bool drm_property_type_is(struct drm_property *property,
                uint32_t type)
 {
@@ -1292,6 +1357,10 @@ extern int drm_mode_create_scaling_mode_property(struct drm_device *dev);
 extern int drm_mode_create_aspect_ratio_property(struct drm_device *dev);
 extern int drm_mode_create_dirty_info_property(struct drm_device *dev);
 extern int drm_mode_create_suggested_offset_properties(struct drm_device *dev);
+extern bool drm_property_change_valid_get(struct drm_property *property,
+                                        uint64_t value, struct drm_mode_object **ref);
+extern void drm_property_change_valid_put(struct drm_property *property,
+               struct drm_mode_object *ref);
 
 extern int drm_mode_connector_attach_encoder(struct drm_connector *connector,
                                             struct drm_encoder *encoder);
@@ -1383,6 +1452,8 @@ extern int drm_mode_obj_set_property_ioctl(struct drm_device *dev, void *data,
 extern int drm_mode_plane_set_obj_prop(struct drm_plane *plane,
                                       struct drm_property *property,
                                       uint64_t value);
+extern int drm_mode_atomic_ioctl(struct drm_device *dev,
+                                void *data, struct drm_file *file_priv);
 
 extern void drm_fb_get_bpp_depth(uint32_t format, unsigned int *depth,
                                 int *bpp);
index 7adbb65ea8aeaa92eb750bab5dad3a2c8fef28eb..e76828d81a8bfab4c9c2fe0c3eb9c0323af2957c 100644 (file)
 
 #include <linux/fb.h>
 
+#include <drm/drm_crtc.h>
+
 enum mode_set_atomic {
        LEAVE_ATOMIC_MODE_SET,
        ENTER_ATOMIC_MODE_SET,
 };
 
 /**
- * drm_crtc_helper_funcs - helper operations for CRTCs
- * @mode_fixup: try to fixup proposed mode for this connector
+ * struct drm_crtc_helper_funcs - helper operations for CRTCs
+ * @dpms: set power state
+ * @prepare: prepare the CRTC, called before @mode_set
+ * @commit: commit changes to CRTC, called after @mode_set
+ * @mode_fixup: try to fixup proposed mode for this CRTC
  * @mode_set: set this mode
+ * @mode_set_nofb: set mode only (no scanout buffer attached)
+ * @mode_set_base: update the scanout buffer
+ * @mode_set_base_atomic: non-blocking mode set (used for kgdb support)
+ * @load_lut: load color palette
+ * @disable: disable CRTC when no longer in use
+ * @atomic_check: check for validity of an atomic state
+ * @atomic_begin: begin atomic update
+ * @atomic_flush: flush atomic update
  *
  * The helper operations are called by the mid-layer CRTC helper.
  */
@@ -91,9 +104,17 @@ struct drm_crtc_helper_funcs {
 };
 
 /**
- * drm_encoder_helper_funcs - helper operations for encoders
+ * struct drm_encoder_helper_funcs - helper operations for encoders
+ * @dpms: set power state
+ * @save: save connector state
+ * @restore: restore connector state
  * @mode_fixup: try to fixup proposed mode for this connector
+ * @prepare: part of the disable sequence, called before the CRTC modeset
+ * @commit: called after the CRTC modeset
  * @mode_set: set this mode
+ * @get_crtc: return CRTC that the encoder is currently attached to
+ * @detect: connection status detection
+ * @disable: disable encoder when not in use (overrides DPMS off)
  *
  * The helper operations are called by the mid-layer CRTC helper.
  */
@@ -119,9 +140,10 @@ struct drm_encoder_helper_funcs {
 };
 
 /**
- * drm_connector_helper_funcs - helper operations for connectors
+ * struct drm_connector_helper_funcs - helper operations for connectors
  * @get_modes: get mode list for this connector
- * @mode_valid (optional): is this mode valid on the given connector?
+ * @mode_valid: is this mode valid on the given connector? (optional)
+ * @best_encoder: return the preferred encoder for this connector
  *
  * The helper operations are called by the mid-layer CRTC helper.
  */
index b597068103aa9d8d1bf66841f76858e904f72c34..21b944c456f69dceb9c4762384d04717d82b41ff 100644 (file)
@@ -125,7 +125,7 @@ void drm_fb_helper_fill_fix(struct fb_info *info, uint32_t pitch,
 int drm_fb_helper_setcmap(struct fb_cmap *cmap, struct fb_info *info);
 
 int drm_fb_helper_hotplug_event(struct drm_fb_helper *fb_helper);
-bool drm_fb_helper_initial_config(struct drm_fb_helper *fb_helper, int bpp_sel);
+int drm_fb_helper_initial_config(struct drm_fb_helper *fb_helper, int bpp_sel);
 int drm_fb_helper_single_add_all_connectors(struct drm_fb_helper *fb_helper);
 int drm_fb_helper_debug_enter(struct fb_info *info);
 int drm_fb_helper_debug_leave(struct fb_info *info);
index 8f17811d27f50560214044c0f7356f604f1a91f4..d92f6dd1fb11fdfc5f1f648e21b9a8e9dc6f9322 100644 (file)
@@ -200,6 +200,8 @@ struct drm_display_mode *drm_gtf_mode_complex(struct drm_device *dev,
                                              int GTF_K, int GTF_2J);
 void drm_display_mode_from_videomode(const struct videomode *vm,
                                     struct drm_display_mode *dmode);
+void drm_display_mode_to_videomode(const struct drm_display_mode *dmode,
+                                  struct videomode *vm);
 int of_get_drm_display_mode(struct device_node *np,
                            struct drm_display_mode *dmode,
                            int index);
@@ -220,9 +222,9 @@ bool drm_mode_equal_no_clocks_no_stereo(const struct drm_display_mode *mode1,
                                        const struct drm_display_mode *mode2);
 
 /* for use by the crtc helper probe functions */
-void drm_mode_validate_size(struct drm_device *dev,
-                           struct list_head *mode_list,
-                           int maxX, int maxY);
+enum drm_mode_status drm_mode_validate_basic(const struct drm_display_mode *mode);
+enum drm_mode_status drm_mode_validate_size(const struct drm_display_mode *mode,
+                                           int maxX, int maxY);
 void drm_mode_prune_invalid(struct drm_device *dev,
                            struct list_head *mode_list, bool verbose);
 void drm_mode_sort(struct list_head *mode_list);
index 8aded9ab2e4e89ddb66e5920c0819bade6fb0760..5735e7130d630f94fe62d3e0a7a7078434c8ee12 100644 (file)
@@ -34,7 +34,6 @@ struct blk_mq_hw_ctx {
        unsigned long           flags;          /* BLK_MQ_F_* flags */
 
        struct request_queue    *queue;
-       unsigned int            queue_num;
        struct blk_flush_queue  *fq;
 
        void                    *driver_data;
@@ -54,7 +53,7 @@ struct blk_mq_hw_ctx {
        unsigned long           dispatched[BLK_MQ_MAX_DISPATCH_ORDER];
 
        unsigned int            numa_node;
-       unsigned int            cmd_size;       /* per-request extra data */
+       unsigned int            queue_num;
 
        atomic_t                nr_active;
 
@@ -195,13 +194,16 @@ static inline u16 blk_mq_unique_tag_to_tag(u32 unique_tag)
 struct blk_mq_hw_ctx *blk_mq_map_queue(struct request_queue *, const int ctx_index);
 struct blk_mq_hw_ctx *blk_mq_alloc_single_hw_queue(struct blk_mq_tag_set *, unsigned int, int);
 
+int blk_mq_request_started(struct request *rq);
 void blk_mq_start_request(struct request *rq);
 void blk_mq_end_request(struct request *rq, int error);
 void __blk_mq_end_request(struct request *rq, int error);
 
 void blk_mq_requeue_request(struct request *rq);
 void blk_mq_add_to_requeue_list(struct request *rq, bool at_head);
+void blk_mq_cancel_requeue_work(struct request_queue *q);
 void blk_mq_kick_requeue_list(struct request_queue *q);
+void blk_mq_abort_requeue_list(struct request_queue *q);
 void blk_mq_complete_request(struct request *rq);
 
 void blk_mq_stop_hw_queue(struct blk_mq_hw_ctx *hctx);
@@ -212,6 +214,8 @@ void blk_mq_start_stopped_hw_queues(struct request_queue *q, bool async);
 void blk_mq_delay_queue(struct blk_mq_hw_ctx *hctx, unsigned long msecs);
 void blk_mq_tag_busy_iter(struct blk_mq_hw_ctx *hctx, busy_iter_fn *fn,
                void *priv);
+void blk_mq_unfreeze_queue(struct request_queue *q);
+void blk_mq_freeze_queue_start(struct request_queue *q);
 
 /*
  * Driver command data is immediately after the request. So subtract request
index 445d59231bc4cc242e2aa0e1ca073e3c320af56c..c294e3e25e37a50a953a4a0bb3cb1aa66ba904d9 100644 (file)
@@ -190,6 +190,7 @@ enum rq_flag_bits {
        __REQ_PM,               /* runtime pm request */
        __REQ_HASHED,           /* on IO scheduler merge hash */
        __REQ_MQ_INFLIGHT,      /* track inflight for MQ */
+       __REQ_NO_TIMEOUT,       /* requests may never expire */
        __REQ_NR_BITS,          /* stops here */
 };
 
@@ -243,5 +244,6 @@ enum rq_flag_bits {
 #define REQ_PM                 (1ULL << __REQ_PM)
 #define REQ_HASHED             (1ULL << __REQ_HASHED)
 #define REQ_MQ_INFLIGHT                (1ULL << __REQ_MQ_INFLIGHT)
+#define REQ_NO_TIMEOUT         (1ULL << __REQ_NO_TIMEOUT)
 
 #endif /* __LINUX_BLK_TYPES_H */
index a1c81f80978ee4b38bbbb1cdd781c7afa0362c5e..33063f872ee3cd698a233a0f0defa67aa1b6bd01 100644 (file)
@@ -215,7 +215,7 @@ static __always_inline void __read_once_size(volatile void *p, void *res, int si
        }
 }
 
-static __always_inline void __assign_once_size(volatile void *p, void *res, int size)
+static __always_inline void __write_once_size(volatile void *p, void *res, int size)
 {
        switch (size) {
        case 1: *(volatile __u8 *)p = *(__u8 *)res; break;
@@ -235,15 +235,15 @@ static __always_inline void __assign_once_size(volatile void *p, void *res, int
 /*
  * Prevent the compiler from merging or refetching reads or writes. The
  * compiler is also forbidden from reordering successive instances of
- * READ_ONCE, ASSIGN_ONCE and ACCESS_ONCE (see below), but only when the
+ * READ_ONCE, WRITE_ONCE and ACCESS_ONCE (see below), but only when the
  * compiler is aware of some particular ordering.  One way to make the
  * compiler aware of ordering is to put the two invocations of READ_ONCE,
- * ASSIGN_ONCE or ACCESS_ONCE() in different C statements.
+ * WRITE_ONCE or ACCESS_ONCE() in different C statements.
  *
  * In contrast to ACCESS_ONCE these two macros will also work on aggregate
  * data types like structs or unions. If the size of the accessed data
  * type exceeds the word size of the machine (e.g., 32 bits or 64 bits)
- * READ_ONCE() and ASSIGN_ONCE()  will fall back to memcpy and print a
+ * READ_ONCE() and WRITE_ONCE()  will fall back to memcpy and print a
  * compile-time warning.
  *
  * Their two major use cases are: (1) Mediating communication between
@@ -257,8 +257,8 @@ static __always_inline void __assign_once_size(volatile void *p, void *res, int
 #define READ_ONCE(x) \
        ({ typeof(x) __val; __read_once_size(&x, &__val, sizeof(__val)); __val; })
 
-#define ASSIGN_ONCE(val, x) \
-       ({ typeof(x) __val; __val = val; __assign_once_size(&x, &__val, sizeof(__val)); __val; })
+#define WRITE_ONCE(x, val) \
+       ({ typeof(x) __val; __val = val; __write_once_size(&x, &__val, sizeof(__val)); __val; })
 
 #endif /* __KERNEL__ */
 
index 55b685719d522da32a37ba59013d1f029ff6a37e..09460d6d668208e3e4997b42f6dca05d0ef917a8 100644 (file)
@@ -11,6 +11,10 @@ extern void genl_unlock(void);
 extern int lockdep_genl_is_held(void);
 #endif
 
+/* for synchronisation between af_netlink and genetlink */
+extern atomic_t genl_sk_destructing_cnt;
+extern wait_queue_head_t genl_sk_destructing_waitq;
+
 /**
  * rcu_dereference_genl - rcu_dereference with debug checking
  * @p: The pointer to read, prior to dereferencing
index 2d182413b1db5bbf3b9afa2c15dd674d2b817b4e..91f705de2c0be743dac06dac565817516058fc56 100644 (file)
@@ -231,6 +231,7 @@ enum {
        ATA_FLAG_SW_ACTIVITY    = (1 << 22), /* driver supports sw activity
                                              * led */
        ATA_FLAG_NO_DIPM        = (1 << 23), /* host not happy with DIPM */
+       ATA_FLAG_LOWTAG         = (1 << 24), /* host wants lowest available tag */
 
        /* bits 24:31 of ap->flags are reserved for LLD specific flags */
 
@@ -422,6 +423,7 @@ enum {
        ATA_HORKAGE_NO_NCQ_TRIM = (1 << 19),    /* don't use queued TRIM */
        ATA_HORKAGE_NOLPM       = (1 << 20),    /* don't use LPM */
        ATA_HORKAGE_WD_BROKEN_LPM = (1 << 21),  /* some WDs have broken LPM */
+       ATA_HORKAGE_ZERO_AFTER_TRIM = (1 << 22),/* guarantees zero after trim */
 
         /* DMA mask for user DMA control: User visible values; DO NOT
            renumber */
index 375af80bde7d7c90bb1c09efb3edc297dbe4d864..f767a0de611f8a726df957c6595d84df92d8efb3 100644 (file)
@@ -137,6 +137,7 @@ struct sdhci_host {
 #define SDHCI_SDR104_NEEDS_TUNING (1<<10)      /* SDR104/HS200 needs tuning */
 #define SDHCI_USING_RETUNING_TIMER (1<<11)     /* Host is using a retuning timer for the card */
 #define SDHCI_USE_64_BIT_DMA   (1<<12) /* Use 64-bit DMA */
+#define SDHCI_HS400_TUNING     (1<<13) /* Tuning for HS400 */
 
        unsigned int version;   /* SDHCI spec. version */
 
index 679e6e90aa4c2b1a2e9ea9c3fde52e12ea389b91..52fd8e8694cfade5e844d52a70b191c3183f60a2 100644 (file)
@@ -852,11 +852,11 @@ typedef u16 (*select_queue_fallback_t)(struct net_device *dev,
  *     3. Update dev->stats asynchronously and atomically, and define
  *        neither operation.
  *
- * int (*ndo_vlan_rx_add_vid)(struct net_device *dev, __be16 proto, u16t vid);
+ * int (*ndo_vlan_rx_add_vid)(struct net_device *dev, __be16 proto, u16 vid);
  *     If device support VLAN filtering this function is called when a
  *     VLAN id is registered.
  *
- * int (*ndo_vlan_rx_kill_vid)(struct net_device *dev, unsigned short vid);
+ * int (*ndo_vlan_rx_kill_vid)(struct net_device *dev, __be16 proto, u16 vid);
  *     If device support VLAN filtering this function is called when a
  *     VLAN id is unregistered.
  *
@@ -2085,7 +2085,7 @@ extern rwlock_t                           dev_base_lock;          /* Device list lock */
        list_for_each_entry_continue_rcu(d, &(net)->dev_base_head, dev_list)
 #define for_each_netdev_in_bond_rcu(bond, slave)       \
                for_each_netdev_rcu(&init_net, slave)   \
-                       if (netdev_master_upper_dev_get_rcu(slave) == bond)
+                       if (netdev_master_upper_dev_get_rcu(slave) == (bond))
 #define net_device_entry(lh)   list_entry(lh, struct net_device, dev_list)
 
 static inline struct net_device *next_net_device(struct net_device *dev)
index 1e37fbb78f7afbc57b8ab3c076d66ce7555f3cb0..ddea982355f3be93947dae0b2e30f9e00209920e 100644 (file)
@@ -74,6 +74,9 @@ struct nfs_client {
        /* idmapper */
        struct idmap *          cl_idmap;
 
+       /* Client owner identifier */
+       const char *            cl_owner_id;
+
        /* Our own IP address, as a null-terminated string.
         * This is used to generate the mv0 callback address.
         */
index e9e6cfbfbb589d0393060e2fed0422ec402dd612..eb7d4a135a9ea71364105c0bade762b5f06b67da 100644 (file)
@@ -66,7 +66,7 @@ enum omap_control_usb_mode {
 #define        OMAP_CTRL_PIPE3_PHY_TX_RX_POWEROFF      0x0
 
 #define        OMAP_CTRL_PCIE_PCS_MASK                 0xff
-#define        OMAP_CTRL_PCIE_PCS_DELAY_COUNT_SHIFT    0x8
+#define        OMAP_CTRL_PCIE_PCS_DELAY_COUNT_SHIFT    16
 
 #define OMAP_CTRL_USB2_PHY_PD          BIT(28)
 
@@ -79,7 +79,7 @@ enum omap_control_usb_mode {
 void omap_control_phy_power(struct device *dev, int on);
 void omap_control_usb_set_mode(struct device *dev,
                               enum omap_control_usb_mode mode);
-void omap_control_pcie_pcs(struct device *dev, u8 id, u8 delay);
+void omap_control_pcie_pcs(struct device *dev, u8 delay);
 #else
 
 static inline void omap_control_phy_power(struct device *dev, int on)
@@ -91,7 +91,7 @@ static inline void omap_control_usb_set_mode(struct device *dev,
 {
 }
 
-static inline void omap_control_pcie_pcs(struct device *dev, u8 id, u8 delay)
+static inline void omap_control_pcie_pcs(struct device *dev, u8 delay)
 {
 }
 #endif
index 84125088c309afb988daa4b24368c2d9e0f02588..6c92415311cacb3ee39ff768edc3d2a4461e922f 100644 (file)
@@ -27,13 +27,18 @@ struct genl_info;
  * @maxattr: maximum number of attributes supported
  * @netnsok: set to true if the family can handle network
  *     namespaces and should be presented in all of them
+ * @parallel_ops: operations can be called in parallel and aren't
+ *     synchronized by the core genetlink code
  * @pre_doit: called before an operation's doit callback, it may
  *     do additional, common, filtering and return an error
  * @post_doit: called after an operation's doit callback, it may
  *     undo operations done by pre_doit, for example release locks
  * @mcast_bind: a socket bound to the given multicast group (which
  *     is given as the offset into the groups array)
- * @mcast_unbind: a socket was unbound from the given multicast group
+ * @mcast_unbind: a socket was unbound from the given multicast group.
+ *     Note that unbind() will not be called symmetrically if the
+ *     generic netlink family is removed while there are still open
+ *     sockets.
  * @attrbuf: buffer to store parsed attributes
  * @family_list: family list
  * @mcgrps: multicast groups used by this family (private)
index 430cfaf92285f177d977d11717599bf1ff85b70b..db81c65b8f4857c011a025e5b54026bf7d683f7c 100644 (file)
@@ -135,7 +135,6 @@ int se_dev_set_is_nonrot(struct se_device *, int);
 int    se_dev_set_emulate_rest_reord(struct se_device *dev, int);
 int    se_dev_set_queue_depth(struct se_device *, u32);
 int    se_dev_set_max_sectors(struct se_device *, u32);
-int    se_dev_set_fabric_max_sectors(struct se_device *, u32);
 int    se_dev_set_optimal_sectors(struct se_device *, u32);
 int    se_dev_set_block_size(struct se_device *, u32);
 
index 3247d7530107968aa7c1d1957f96790c226845dd..186f7a92357094fbb4735043b2a2b8c8cd884af8 100644 (file)
@@ -98,8 +98,6 @@ static struct target_backend_dev_attrib_attribute _backend##_dev_attrib_##_name
        TB_DEV_ATTR(_backend, block_size, S_IRUGO | S_IWUSR);           \
        DEF_TB_DEV_ATTRIB_RO(_backend, hw_max_sectors);                 \
        TB_DEV_ATTR_RO(_backend, hw_max_sectors);                       \
-       DEF_TB_DEV_ATTRIB(_backend, fabric_max_sectors);                \
-       TB_DEV_ATTR(_backend, fabric_max_sectors, S_IRUGO | S_IWUSR);   \
        DEF_TB_DEV_ATTRIB(_backend, optimal_sectors);                   \
        TB_DEV_ATTR(_backend, optimal_sectors, S_IRUGO | S_IWUSR);      \
        DEF_TB_DEV_ATTRIB_RO(_backend, hw_queue_depth);                 \
index 397fb635766a96faa94c5b91788ad24fca0d2a34..4a8795a87b9e99f30ee07f43fdce3984ddc658e0 100644 (file)
@@ -77,8 +77,6 @@
 #define DA_UNMAP_GRANULARITY_ALIGNMENT_DEFAULT 0
 /* Default max_write_same_len, disabled by default */
 #define DA_MAX_WRITE_SAME_LEN                  0
-/* Default max transfer length */
-#define DA_FABRIC_MAX_SECTORS                  8192
 /* Use a model alias based on the configfs backend device name */
 #define DA_EMULATE_MODEL_ALIAS                 0
 /* Emulation for Direct Page Out */
@@ -694,7 +692,6 @@ struct se_dev_attrib {
        u32             hw_block_size;
        u32             block_size;
        u32             hw_max_sectors;
-       u32             fabric_max_sectors;
        u32             optimal_sectors;
        u32             hw_queue_depth;
        u32             queue_depth;
index b0b85561364161e7ce5c8196a6a8b03940db4b9d..01b2d6d0e35529d534ca5d6bd8c3efcbcbd2d838 100644 (file)
@@ -654,6 +654,13 @@ struct drm_get_cap {
  */
 #define DRM_CLIENT_CAP_UNIVERSAL_PLANES  2
 
+/**
+ * DRM_CLIENT_CAP_ATOMIC
+ *
+ * If set to 1, the DRM core will expose atomic properties to userspace
+ */
+#define DRM_CLIENT_CAP_ATOMIC  3
+
 /** DRM_IOCTL_SET_CLIENT_CAP ioctl argument type */
 struct drm_set_client_cap {
        __u64 capability;
@@ -777,6 +784,7 @@ struct drm_prime_handle {
 #define DRM_IOCTL_MODE_OBJ_GETPROPERTIES       DRM_IOWR(0xB9, struct drm_mode_obj_get_properties)
 #define DRM_IOCTL_MODE_OBJ_SETPROPERTY DRM_IOWR(0xBA, struct drm_mode_obj_set_property)
 #define DRM_IOCTL_MODE_CURSOR2         DRM_IOWR(0xBB, struct drm_mode_cursor2)
+#define DRM_IOCTL_MODE_ATOMIC          DRM_IOWR(0xBC, struct drm_mode_atomic)
 
 /**
  * Device specific ioctls should only be in their respective headers
index 86574b0005ff0a476fa2299b8ef73de418670024..ca788e01dab20795ea848b0ab9c70ef3d9487743 100644 (file)
@@ -272,6 +272,13 @@ struct drm_mode_get_connector {
 #define DRM_MODE_PROP_OBJECT           DRM_MODE_PROP_TYPE(1)
 #define DRM_MODE_PROP_SIGNED_RANGE     DRM_MODE_PROP_TYPE(2)
 
+/* the PROP_ATOMIC flag is used to hide properties from userspace that
+ * is not aware of atomic properties.  This is mostly to work around
+ * older userspace (DDX drivers) that read/write each prop they find,
+ * witout being aware that this could be triggering a lengthy modeset.
+ */
+#define DRM_MODE_PROP_ATOMIC        0x80000000
+
 struct drm_mode_property_enum {
        __u64 value;
        char name[DRM_PROP_NAME_LEN];
@@ -338,7 +345,7 @@ struct drm_mode_fb_cmd2 {
 
        /*
         * In case of planar formats, this ioctl allows up to 4
-        * buffer objects with offets and pitches per plane.
+        * buffer objects with offsets and pitches per plane.
         * The pitch and offset order is dictated by the fourcc,
         * e.g. NV12 (http://fourcc.org/yuv.php#NV12) is described as:
         *
@@ -346,9 +353,9 @@ struct drm_mode_fb_cmd2 {
         *   followed by an interleaved U/V plane containing
         *   8 bit 2x2 subsampled colour difference samples.
         *
-        * So it would consist of Y as offset[0] and UV as
-        * offeset[1].  Note that offset[0] will generally
-        * be 0.
+        * So it would consist of Y as offsets[0] and UV as
+        * offsets[1].  Note that offsets[0] will generally
+        * be 0 (but this is not required).
         */
        __u32 handles[4];
        __u32 pitches[4]; /* pitch for each plane */
@@ -519,4 +526,27 @@ struct drm_mode_destroy_dumb {
        uint32_t handle;
 };
 
+/* page-flip flags are valid, plus: */
+#define DRM_MODE_ATOMIC_TEST_ONLY 0x0100
+#define DRM_MODE_ATOMIC_NONBLOCK  0x0200
+#define DRM_MODE_ATOMIC_ALLOW_MODESET 0x0400
+
+#define DRM_MODE_ATOMIC_FLAGS (\
+               DRM_MODE_PAGE_FLIP_EVENT |\
+               DRM_MODE_PAGE_FLIP_ASYNC |\
+               DRM_MODE_ATOMIC_TEST_ONLY |\
+               DRM_MODE_ATOMIC_NONBLOCK |\
+               DRM_MODE_ATOMIC_ALLOW_MODESET)
+
+struct drm_mode_atomic {
+       __u32 flags;
+       __u32 count_objs;
+       __u64 objs_ptr;
+       __u64 count_props_ptr;
+       __u64 props_ptr;
+       __u64 prop_values_ptr;
+       __u64 reserved;
+       __u64 user_data;
+};
+
 #endif
index 3e4323a3918d7266efc46edb622636621f042afc..94ffe0c83ce72cf5e396a615fe039bec6fe468d4 100644 (file)
@@ -98,6 +98,7 @@ struct can_ctrlmode {
 #define CAN_CTRLMODE_BERR_REPORTING    0x10    /* Bus-error reporting */
 #define CAN_CTRLMODE_FD                        0x20    /* CAN FD mode */
 #define CAN_CTRLMODE_PRESUME_ACK       0x40    /* Ignore missing CAN ACKs */
+#define CAN_CTRLMODE_FD_NON_ISO                0x80    /* CAN FD in non-ISO mode */
 
 /*
  * CAN device statistics
index 3a6dcaa359b768d09bfc58f71c0f9b23582d9f24..f714e863335204a4c3e29525e41605f3a9e0f0f4 100644 (file)
@@ -174,6 +174,10 @@ enum ovs_packet_attr {
        OVS_PACKET_ATTR_USERDATA,    /* OVS_ACTION_ATTR_USERSPACE arg. */
        OVS_PACKET_ATTR_EGRESS_TUN_KEY,  /* Nested OVS_TUNNEL_KEY_ATTR_*
                                            attributes. */
+       OVS_PACKET_ATTR_UNUSED1,
+       OVS_PACKET_ATTR_UNUSED2,
+       OVS_PACKET_ATTR_PROBE,      /* Packet operation is a feature probe,
+                                      error logging should be suppressed. */
        __OVS_PACKET_ATTR_MAX
 };
 
index baeab83deb6469c5abb22ac61ee07f73b0dfedfe..013c9d8db3720cc1c606323def3e47692702cfa2 100644 (file)
@@ -82,7 +82,7 @@ struct uinput_ff_erase {
  * The complete sysfs path is then /sys/devices/virtual/input/--NAME--
  * Usually, it is in the form "inputN"
  */
-#define UI_GET_SYSNAME(len)    _IOC(_IOC_READ, UINPUT_IOCTL_BASE, 300, len)
+#define UI_GET_SYSNAME(len)    _IOC(_IOC_READ, UINPUT_IOCTL_BASE, 44, len)
 
 /**
  * UI_GET_VERSION - Return version of uinput protocol
@@ -91,7 +91,7 @@ struct uinput_ff_erase {
  * the integer pointed to by the ioctl argument. The protocol version
  * is hard-coded in the kernel and is independent of the uinput device.
  */
-#define UI_GET_VERSION         _IOR(UINPUT_IOCTL_BASE, 301, unsigned int)
+#define UI_GET_VERSION         _IOR(UINPUT_IOCTL_BASE, 45, unsigned int)
 
 /*
  * To write a force-feedback-capable driver, the upload_effect
index c74bf4a0520e5860d4548713794d0985d4eb0150..73390c120cad03ec38030e68a4e5a1801d5fe668 100644 (file)
@@ -17,6 +17,7 @@
 #include <linux/bitmap.h>
 #include <linux/fb.h>
 #include <media/v4l2-mediabus.h>
+#include <video/videomode.h>
 
 struct ipu_soc;
 
@@ -32,28 +33,15 @@ enum ipuv3_type {
  * Bitfield of Display Interface signal polarities.
  */
 struct ipu_di_signal_cfg {
-       unsigned datamask_en:1;
-       unsigned interlaced:1;
-       unsigned odd_field_first:1;
-       unsigned clksel_en:1;
-       unsigned clkidle_en:1;
        unsigned data_pol:1;    /* true = inverted */
        unsigned clk_pol:1;     /* true = rising edge */
        unsigned enable_pol:1;
-       unsigned Hsync_pol:1;   /* true = active high */
-       unsigned Vsync_pol:1;
 
-       u16 width;
-       u16 height;
+       struct videomode mode;
+
        u32 pixel_fmt;
-       u16 h_start_width;
-       u16 h_sync_width;
-       u16 h_end_width;
-       u16 v_start_width;
-       u16 v_sync_width;
-       u16 v_end_width;
        u32 v_to_h_sync;
-       unsigned long pixelclock;
+
 #define IPU_DI_CLKMODE_SYNC    (1 << 0)
 #define IPU_DI_CLKMODE_EXT     (1 << 1)
        unsigned long clkflags;
@@ -236,6 +224,7 @@ void ipu_di_put(struct ipu_di *);
 int ipu_di_disable(struct ipu_di *);
 int ipu_di_enable(struct ipu_di *);
 int ipu_di_get_num(struct ipu_di *);
+int ipu_di_adjust_videomode(struct ipu_di *di, struct videomode *mode);
 int ipu_di_init_sync_panel(struct ipu_di *, struct ipu_di_signal_cfg *sig);
 
 /*
diff --git a/include/xen/interface/nmi.h b/include/xen/interface/nmi.h
new file mode 100644 (file)
index 0000000..b47d9d0
--- /dev/null
@@ -0,0 +1,51 @@
+/******************************************************************************
+ * nmi.h
+ *
+ * NMI callback registration and reason codes.
+ *
+ * Copyright (c) 2005, Keir Fraser <keir@xensource.com>
+ */
+
+#ifndef __XEN_PUBLIC_NMI_H__
+#define __XEN_PUBLIC_NMI_H__
+
+#include <xen/interface/xen.h>
+
+/*
+ * NMI reason codes:
+ * Currently these are x86-specific, stored in arch_shared_info.nmi_reason.
+ */
+ /* I/O-check error reported via ISA port 0x61, bit 6. */
+#define _XEN_NMIREASON_io_error     0
+#define XEN_NMIREASON_io_error      (1UL << _XEN_NMIREASON_io_error)
+ /* PCI SERR reported via ISA port 0x61, bit 7. */
+#define _XEN_NMIREASON_pci_serr     1
+#define XEN_NMIREASON_pci_serr      (1UL << _XEN_NMIREASON_pci_serr)
+ /* Unknown hardware-generated NMI. */
+#define _XEN_NMIREASON_unknown      2
+#define XEN_NMIREASON_unknown       (1UL << _XEN_NMIREASON_unknown)
+
+/*
+ * long nmi_op(unsigned int cmd, void *arg)
+ * NB. All ops return zero on success, else a negative error code.
+ */
+
+/*
+ * Register NMI callback for this (calling) VCPU. Currently this only makes
+ * sense for domain 0, vcpu 0. All other callers will be returned EINVAL.
+ * arg == pointer to xennmi_callback structure.
+ */
+#define XENNMI_register_callback   0
+struct xennmi_callback {
+    unsigned long handler_address;
+    unsigned long pad;
+};
+DEFINE_GUEST_HANDLE_STRUCT(xennmi_callback);
+
+/*
+ * Deregister NMI callback for this (calling) VCPU.
+ * arg == NULL.
+ */
+#define XENNMI_unregister_callback 1
+
+#endif /* __XEN_PUBLIC_NMI_H__ */
index 322ea8e93e4ba36c11c0348a34c12e58c983da03..82cfc285b046d8e320559a48cf08007a19742dc0 100644 (file)
@@ -113,12 +113,12 @@ static int cmp_range(const void *x1, const void *x2)
 {
        const struct range *r1 = x1;
        const struct range *r2 = x2;
-       s64 start1, start2;
 
-       start1 = r1->start;
-       start2 = r2->start;
-
-       return start1 - start2;
+       if (r1->start < r2->start)
+               return -1;
+       if (r1->start > r2->start)
+               return 1;
+       return 0;
 }
 
 int clean_sort_range(struct range *range, int az)
index 929a733d302e0d438d2f15f8dfaf6e2e4c56c0d0..224e768bdc738da7c47aca41fcc6d9ecd4c190b4 100644 (file)
@@ -2497,12 +2497,14 @@ static void ftrace_run_update_code(int command)
 }
 
 static void ftrace_run_modify_code(struct ftrace_ops *ops, int command,
-                                  struct ftrace_hash *old_hash)
+                                  struct ftrace_ops_hash *old_hash)
 {
        ops->flags |= FTRACE_OPS_FL_MODIFYING;
-       ops->old_hash.filter_hash = old_hash;
+       ops->old_hash.filter_hash = old_hash->filter_hash;
+       ops->old_hash.notrace_hash = old_hash->notrace_hash;
        ftrace_run_update_code(command);
        ops->old_hash.filter_hash = NULL;
+       ops->old_hash.notrace_hash = NULL;
        ops->flags &= ~FTRACE_OPS_FL_MODIFYING;
 }
 
@@ -3579,7 +3581,7 @@ static struct ftrace_ops trace_probe_ops __read_mostly =
 
 static int ftrace_probe_registered;
 
-static void __enable_ftrace_function_probe(struct ftrace_hash *old_hash)
+static void __enable_ftrace_function_probe(struct ftrace_ops_hash *old_hash)
 {
        int ret;
        int i;
@@ -3637,6 +3639,7 @@ int
 register_ftrace_function_probe(char *glob, struct ftrace_probe_ops *ops,
                              void *data)
 {
+       struct ftrace_ops_hash old_hash_ops;
        struct ftrace_func_probe *entry;
        struct ftrace_hash **orig_hash = &trace_probe_ops.func_hash->filter_hash;
        struct ftrace_hash *old_hash = *orig_hash;
@@ -3658,6 +3661,10 @@ register_ftrace_function_probe(char *glob, struct ftrace_probe_ops *ops,
 
        mutex_lock(&trace_probe_ops.func_hash->regex_lock);
 
+       old_hash_ops.filter_hash = old_hash;
+       /* Probes only have filters */
+       old_hash_ops.notrace_hash = NULL;
+
        hash = alloc_and_copy_ftrace_hash(FTRACE_HASH_DEFAULT_BITS, old_hash);
        if (!hash) {
                count = -ENOMEM;
@@ -3718,7 +3725,7 @@ register_ftrace_function_probe(char *glob, struct ftrace_probe_ops *ops,
 
        ret = ftrace_hash_move(&trace_probe_ops, 1, orig_hash, hash);
 
-       __enable_ftrace_function_probe(old_hash);
+       __enable_ftrace_function_probe(&old_hash_ops);
 
        if (!ret)
                free_ftrace_hash_rcu(old_hash);
@@ -4006,10 +4013,34 @@ ftrace_match_addr(struct ftrace_hash *hash, unsigned long ip, int remove)
 }
 
 static void ftrace_ops_update_code(struct ftrace_ops *ops,
-                                  struct ftrace_hash *old_hash)
+                                  struct ftrace_ops_hash *old_hash)
 {
-       if (ops->flags & FTRACE_OPS_FL_ENABLED && ftrace_enabled)
+       struct ftrace_ops *op;
+
+       if (!ftrace_enabled)
+               return;
+
+       if (ops->flags & FTRACE_OPS_FL_ENABLED) {
                ftrace_run_modify_code(ops, FTRACE_UPDATE_CALLS, old_hash);
+               return;
+       }
+
+       /*
+        * If this is the shared global_ops filter, then we need to
+        * check if there is another ops that shares it, is enabled.
+        * If so, we still need to run the modify code.
+        */
+       if (ops->func_hash != &global_ops.local_hash)
+               return;
+
+       do_for_each_ftrace_op(op, ftrace_ops_list) {
+               if (op->func_hash == &global_ops.local_hash &&
+                   op->flags & FTRACE_OPS_FL_ENABLED) {
+                       ftrace_run_modify_code(op, FTRACE_UPDATE_CALLS, old_hash);
+                       /* Only need to do this once */
+                       return;
+               }
+       } while_for_each_ftrace_op(op);
 }
 
 static int
@@ -4017,6 +4048,7 @@ ftrace_set_hash(struct ftrace_ops *ops, unsigned char *buf, int len,
                unsigned long ip, int remove, int reset, int enable)
 {
        struct ftrace_hash **orig_hash;
+       struct ftrace_ops_hash old_hash_ops;
        struct ftrace_hash *old_hash;
        struct ftrace_hash *hash;
        int ret;
@@ -4053,9 +4085,11 @@ ftrace_set_hash(struct ftrace_ops *ops, unsigned char *buf, int len,
 
        mutex_lock(&ftrace_lock);
        old_hash = *orig_hash;
+       old_hash_ops.filter_hash = ops->func_hash->filter_hash;
+       old_hash_ops.notrace_hash = ops->func_hash->notrace_hash;
        ret = ftrace_hash_move(ops, enable, orig_hash, hash);
        if (!ret) {
-               ftrace_ops_update_code(ops, old_hash);
+               ftrace_ops_update_code(ops, &old_hash_ops);
                free_ftrace_hash_rcu(old_hash);
        }
        mutex_unlock(&ftrace_lock);
@@ -4267,6 +4301,7 @@ static void __init set_ftrace_early_filters(void)
 int ftrace_regex_release(struct inode *inode, struct file *file)
 {
        struct seq_file *m = (struct seq_file *)file->private_data;
+       struct ftrace_ops_hash old_hash_ops;
        struct ftrace_iterator *iter;
        struct ftrace_hash **orig_hash;
        struct ftrace_hash *old_hash;
@@ -4300,10 +4335,12 @@ int ftrace_regex_release(struct inode *inode, struct file *file)
 
                mutex_lock(&ftrace_lock);
                old_hash = *orig_hash;
+               old_hash_ops.filter_hash = iter->ops->func_hash->filter_hash;
+               old_hash_ops.notrace_hash = iter->ops->func_hash->notrace_hash;
                ret = ftrace_hash_move(iter->ops, filter_hash,
                                       orig_hash, iter->hash);
                if (!ret) {
-                       ftrace_ops_update_code(iter->ops, old_hash);
+                       ftrace_ops_update_code(iter->ops, &old_hash_ops);
                        free_ftrace_hash_rcu(old_hash);
                }
                mutex_unlock(&ftrace_lock);
index 2e767972e99c2e8791236d10afa717b920543b70..4a9079b9f082fd3bb14e3b46522b1540b001fea1 100644 (file)
@@ -6918,7 +6918,6 @@ void __init trace_init(void)
                        tracepoint_printk = 0;
        }
        tracer_alloc_buffers();
-       init_ftrace_syscalls();
        trace_event_init();     
 }
 
index 366a78a3e61e21a94c06aa96f5b5c02a72c41e78..b03a0ea77b993cf9f175ed7b44fc239832de7def 100644 (file)
@@ -2429,12 +2429,39 @@ static __init int event_trace_memsetup(void)
        return 0;
 }
 
+static __init void
+early_enable_events(struct trace_array *tr, bool disable_first)
+{
+       char *buf = bootup_event_buf;
+       char *token;
+       int ret;
+
+       while (true) {
+               token = strsep(&buf, ",");
+
+               if (!token)
+                       break;
+               if (!*token)
+                       continue;
+
+               /* Restarting syscalls requires that we stop them first */
+               if (disable_first)
+                       ftrace_set_clr_event(tr, token, 0);
+
+               ret = ftrace_set_clr_event(tr, token, 1);
+               if (ret)
+                       pr_warn("Failed to enable trace event: %s\n", token);
+
+               /* Put back the comma to allow this to be called again */
+               if (buf)
+                       *(buf - 1) = ',';
+       }
+}
+
 static __init int event_trace_enable(void)
 {
        struct trace_array *tr = top_trace_array();
        struct ftrace_event_call **iter, *call;
-       char *buf = bootup_event_buf;
-       char *token;
        int ret;
 
        if (!tr)
@@ -2456,18 +2483,7 @@ static __init int event_trace_enable(void)
         */
        __trace_early_add_events(tr);
 
-       while (true) {
-               token = strsep(&buf, ",");
-
-               if (!token)
-                       break;
-               if (!*token)
-                       continue;
-
-               ret = ftrace_set_clr_event(tr, token, 1);
-               if (ret)
-                       pr_warn("Failed to enable trace event: %s\n", token);
-       }
+       early_enable_events(tr, false);
 
        trace_printk_start_comm();
 
@@ -2478,6 +2494,31 @@ static __init int event_trace_enable(void)
        return 0;
 }
 
+/*
+ * event_trace_enable() is called from trace_event_init() first to
+ * initialize events and perhaps start any events that are on the
+ * command line. Unfortunately, there are some events that will not
+ * start this early, like the system call tracepoints that need
+ * to set the TIF_SYSCALL_TRACEPOINT flag of pid 1. But event_trace_enable()
+ * is called before pid 1 starts, and this flag is never set, making
+ * the syscall tracepoint never get reached, but the event is enabled
+ * regardless (and not doing anything).
+ */
+static __init int event_trace_enable_again(void)
+{
+       struct trace_array *tr;
+
+       tr = top_trace_array();
+       if (!tr)
+               return -ENODEV;
+
+       early_enable_events(tr, true);
+
+       return 0;
+}
+
+early_initcall(event_trace_enable_again);
+
 static __init int event_trace_init(void)
 {
        struct trace_array *tr;
index 6202b08f1933bd5eaca37f0e09ff5bbdfbb9f606..beeeac9e0e3e6829faa3fe16304cb3e7adbe8850 100644 (file)
@@ -1841,17 +1841,11 @@ static void pool_mayday_timeout(unsigned long __pool)
  * spin_lock_irq(pool->lock) which may be released and regrabbed
  * multiple times.  Does GFP_KERNEL allocations.  Called only from
  * manager.
- *
- * Return:
- * %false if no action was taken and pool->lock stayed locked, %true
- * otherwise.
  */
-static bool maybe_create_worker(struct worker_pool *pool)
+static void maybe_create_worker(struct worker_pool *pool)
 __releases(&pool->lock)
 __acquires(&pool->lock)
 {
-       if (!need_to_create_worker(pool))
-               return false;
 restart:
        spin_unlock_irq(&pool->lock);
 
@@ -1877,7 +1871,6 @@ restart:
         */
        if (need_to_create_worker(pool))
                goto restart;
-       return true;
 }
 
 /**
@@ -1897,16 +1890,14 @@ restart:
  * multiple times.  Does GFP_KERNEL allocations.
  *
  * Return:
- * %false if the pool don't need management and the caller can safely start
- * processing works, %true indicates that the function released pool->lock
- * and reacquired it to perform some management function and that the
- * conditions that the caller verified while holding the lock before
- * calling the function might no longer be true.
+ * %false if the pool doesn't need management and the caller can safely
+ * start processing works, %true if management function was performed and
+ * the conditions that the caller verified before calling the function may
+ * no longer be true.
  */
 static bool manage_workers(struct worker *worker)
 {
        struct worker_pool *pool = worker->pool;
-       bool ret = false;
 
        /*
         * Anyone who successfully grabs manager_arb wins the arbitration
@@ -1919,12 +1910,12 @@ static bool manage_workers(struct worker *worker)
         * actual management, the pool may stall indefinitely.
         */
        if (!mutex_trylock(&pool->manager_arb))
-               return ret;
+               return false;
 
-       ret |= maybe_create_worker(pool);
+       maybe_create_worker(pool);
 
        mutex_unlock(&pool->manager_arb);
-       return ret;
+       return true;
 }
 
 /**
index c6565f00fb38bdc89e0c0ae061786af4bc9c1667..54f3a9b0095600749fda793d7e6067bd2c7f997d 100644 (file)
@@ -235,6 +235,9 @@ void tlb_gather_mmu(struct mmu_gather *tlb, struct mm_struct *mm, unsigned long
 
 static void tlb_flush_mmu_tlbonly(struct mmu_gather *tlb)
 {
+       if (!tlb->end)
+               return;
+
        tlb_flush(tlb);
        mmu_notifier_invalidate_range(tlb->mm, tlb->start, tlb->end);
 #ifdef CONFIG_HAVE_RCU_TABLE_FREE
@@ -247,7 +250,7 @@ static void tlb_flush_mmu_free(struct mmu_gather *tlb)
 {
        struct mmu_gather_batch *batch;
 
-       for (batch = &tlb->local; batch; batch = batch->next) {
+       for (batch = &tlb->local; batch && batch->nr; batch = batch->next) {
                free_pages_and_swap_cache(batch->pages, batch->nr);
                batch->nr = 0;
        }
@@ -256,9 +259,6 @@ static void tlb_flush_mmu_free(struct mmu_gather *tlb)
 
 void tlb_flush_mmu(struct mmu_gather *tlb)
 {
-       if (!tlb->end)
-               return;
-
        tlb_flush_mmu_tlbonly(tlb);
        tlb_flush_mmu_free(tlb);
 }
index 1f1de715197c19ab12f5333e9a518a317754f041..e2aa7be3a847f448a404e0a43f6d1a09f1a0517a 100644 (file)
@@ -154,7 +154,8 @@ int br_handle_frame_finish(struct sk_buff *skb)
        dst = NULL;
 
        if (is_broadcast_ether_addr(dest)) {
-               if (p->flags & BR_PROXYARP &&
+               if (IS_ENABLED(CONFIG_INET) &&
+                   p->flags & BR_PROXYARP &&
                    skb->protocol == htons(ETH_P_ARP))
                        br_do_proxy_arp(skb, br, vid);
 
index 683d493aa1bf2225ac0c029ac403841f7d3c740e..171420e75b03e5b9a020e6d417b72efbed5d5aba 100644 (file)
@@ -7072,10 +7072,20 @@ static int dev_cpu_callback(struct notifier_block *nfb,
                oldsd->output_queue = NULL;
                oldsd->output_queue_tailp = &oldsd->output_queue;
        }
-       /* Append NAPI poll list from offline CPU. */
-       if (!list_empty(&oldsd->poll_list)) {
-               list_splice_init(&oldsd->poll_list, &sd->poll_list);
-               raise_softirq_irqoff(NET_RX_SOFTIRQ);
+       /* Append NAPI poll list from offline CPU, with one exception :
+        * process_backlog() must be called by cpu owning percpu backlog.
+        * We properly handle process_queue & input_pkt_queue later.
+        */
+       while (!list_empty(&oldsd->poll_list)) {
+               struct napi_struct *napi = list_first_entry(&oldsd->poll_list,
+                                                           struct napi_struct,
+                                                           poll_list);
+
+               list_del_init(&napi->poll_list);
+               if (napi->poll == process_backlog)
+                       napi->state = 0;
+               else
+                       ____napi_schedule(sd, napi);
        }
 
        raise_softirq_irqoff(NET_TX_SOFTIRQ);
@@ -7086,7 +7096,7 @@ static int dev_cpu_callback(struct notifier_block *nfb,
                netif_rx_internal(skb);
                input_queue_head_incr(oldsd);
        }
-       while ((skb = __skb_dequeue(&oldsd->input_pkt_queue))) {
+       while ((skb = skb_dequeue(&oldsd->input_pkt_queue))) {
                netif_rx_internal(skb);
                input_queue_head_incr(oldsd);
        }
index 8e38f17288d3c5a475471b0e56e339d9b6d5bf9e..8d614c93f86a233a5cb3864c600d9c68fe5f9ea1 100644 (file)
@@ -2043,6 +2043,12 @@ static int neightbl_set(struct sk_buff *skb, struct nlmsghdr *nlh)
                        case NDTPA_BASE_REACHABLE_TIME:
                                NEIGH_VAR_SET(p, BASE_REACHABLE_TIME,
                                              nla_get_msecs(tbp[i]));
+                               /* update reachable_time as well, otherwise, the change will
+                                * only be effective after the next time neigh_periodic_work
+                                * decides to recompute it (can be multiple minutes)
+                                */
+                               p->reachable_time =
+                                       neigh_rand_reach_time(NEIGH_VAR(p, BASE_REACHABLE_TIME));
                                break;
                        case NDTPA_GC_STALETIME:
                                NEIGH_VAR_SET(p, GC_STALETIME,
@@ -2921,6 +2927,31 @@ static int neigh_proc_dointvec_unres_qlen(struct ctl_table *ctl, int write,
        return ret;
 }
 
+static int neigh_proc_base_reachable_time(struct ctl_table *ctl, int write,
+                                         void __user *buffer,
+                                         size_t *lenp, loff_t *ppos)
+{
+       struct neigh_parms *p = ctl->extra2;
+       int ret;
+
+       if (strcmp(ctl->procname, "base_reachable_time") == 0)
+               ret = neigh_proc_dointvec_jiffies(ctl, write, buffer, lenp, ppos);
+       else if (strcmp(ctl->procname, "base_reachable_time_ms") == 0)
+               ret = neigh_proc_dointvec_ms_jiffies(ctl, write, buffer, lenp, ppos);
+       else
+               ret = -1;
+
+       if (write && ret == 0) {
+               /* update reachable_time as well, otherwise, the change will
+                * only be effective after the next time neigh_periodic_work
+                * decides to recompute it
+                */
+               p->reachable_time =
+                       neigh_rand_reach_time(NEIGH_VAR(p, BASE_REACHABLE_TIME));
+       }
+       return ret;
+}
+
 #define NEIGH_PARMS_DATA_OFFSET(index) \
        (&((struct neigh_parms *) 0)->data[index])
 
@@ -3047,6 +3078,19 @@ int neigh_sysctl_register(struct net_device *dev, struct neigh_parms *p,
                t->neigh_vars[NEIGH_VAR_RETRANS_TIME_MS].proc_handler = handler;
                /* ReachableTime (in milliseconds) */
                t->neigh_vars[NEIGH_VAR_BASE_REACHABLE_TIME_MS].proc_handler = handler;
+       } else {
+               /* Those handlers will update p->reachable_time after
+                * base_reachable_time(_ms) is set to ensure the new timer starts being
+                * applied after the next neighbour update instead of waiting for
+                * neigh_periodic_work to update its value (can be multiple minutes)
+                * So any handler that replaces them should do this as well
+                */
+               /* ReachableTime */
+               t->neigh_vars[NEIGH_VAR_BASE_REACHABLE_TIME].proc_handler =
+                       neigh_proc_base_reachable_time;
+               /* ReachableTime (in milliseconds) */
+               t->neigh_vars[NEIGH_VAR_BASE_REACHABLE_TIME_MS].proc_handler =
+                       neigh_proc_base_reachable_time;
        }
 
        /* Don't export sysctls to unprivileged users */
index 8a89c738b7a3b43407293f521bd6d7e009ee7c80..6b85adb05003cb775b538aacb81a37ec398d8b3c 100644 (file)
@@ -461,17 +461,13 @@ int ip_recv_error(struct sock *sk, struct msghdr *msg, int len, int *addr_len)
 
        memcpy(&errhdr.ee, &serr->ee, sizeof(struct sock_extended_err));
        sin = &errhdr.offender;
-       sin->sin_family = AF_UNSPEC;
+       memset(sin, 0, sizeof(*sin));
 
        if (serr->ee.ee_origin == SO_EE_ORIGIN_ICMP ||
            ipv4_pktinfo_prepare_errqueue(sk, skb, serr->ee.ee_origin)) {
-               struct inet_sock *inet = inet_sk(sk);
-
                sin->sin_family = AF_INET;
                sin->sin_addr.s_addr = ip_hdr(skb)->saddr;
-               sin->sin_port = 0;
-               memset(&sin->sin_zero, 0, sizeof(sin->sin_zero));
-               if (inet->cmsg_flags)
+               if (inet_sk(sk)->cmsg_flags)
                        ip_cmsg_recv(msg, skb);
        }
 
index ff2d23d8c87a16964e29f478640dccd5ca527a02..6ecfce63201a2753d4943813d3eccbb951f34d0b 100644 (file)
@@ -27,10 +27,10 @@ static void nft_redir_ipv4_eval(const struct nft_expr *expr,
 
        memset(&mr, 0, sizeof(mr));
        if (priv->sreg_proto_min) {
-               mr.range[0].min.all = (__force __be16)
-                                       data[priv->sreg_proto_min].data[0];
-               mr.range[0].max.all = (__force __be16)
-                                       data[priv->sreg_proto_max].data[0];
+               mr.range[0].min.all =
+                       *(__be16 *)&data[priv->sreg_proto_min].data[0];
+               mr.range[0].max.all =
+                       *(__be16 *)&data[priv->sreg_proto_max].data[0];
                mr.range[0].flags |= NF_NAT_RANGE_PROTO_SPECIFIED;
        }
 
index 100c589a2a6cf951bdb8a7a2e56b087fb4fe56bf..49f5e73db1224549c7f3fc156209a85ed6ce4056 100644 (file)
@@ -393,11 +393,10 @@ int ipv6_recv_error(struct sock *sk, struct msghdr *msg, int len, int *addr_len)
 
        memcpy(&errhdr.ee, &serr->ee, sizeof(struct sock_extended_err));
        sin = &errhdr.offender;
-       sin->sin6_family = AF_UNSPEC;
+       memset(sin, 0, sizeof(*sin));
+
        if (serr->ee.ee_origin != SO_EE_ORIGIN_LOCAL) {
                sin->sin6_family = AF_INET6;
-               sin->sin6_flowinfo = 0;
-               sin->sin6_port = 0;
                if (np->rxopt.all) {
                        if (serr->ee.ee_origin != SO_EE_ORIGIN_ICMP &&
                            serr->ee.ee_origin != SO_EE_ORIGIN_ICMP6)
@@ -412,12 +411,9 @@ int ipv6_recv_error(struct sock *sk, struct msghdr *msg, int len, int *addr_len)
                                ipv6_iface_scope_id(&sin->sin6_addr,
                                                    IP6CB(skb)->iif);
                } else {
-                       struct inet_sock *inet = inet_sk(sk);
-
                        ipv6_addr_set_v4mapped(ip_hdr(skb)->saddr,
                                               &sin->sin6_addr);
-                       sin->sin6_scope_id = 0;
-                       if (inet->cmsg_flags)
+                       if (inet_sk(sk)->cmsg_flags)
                                ip_cmsg_recv(msg, skb);
                }
        }
index 2433a6bfb191c4259bedfe2d697baa618c818b51..11820b6b36130d4ec83af3f173a1ca70df8cbf93 100644 (file)
@@ -27,10 +27,10 @@ static void nft_redir_ipv6_eval(const struct nft_expr *expr,
 
        memset(&range, 0, sizeof(range));
        if (priv->sreg_proto_min) {
-               range.min_proto.all = (__force __be16)
-                                       data[priv->sreg_proto_min].data[0];
-               range.max_proto.all = (__force __be16)
-                                       data[priv->sreg_proto_max].data[0];
+               range.min_proto.all =
+                       *(__be16 *)&data[priv->sreg_proto_min].data[0];
+               range.max_proto.all =
+                       *(__be16 *)&data[priv->sreg_proto_max].data[0];
                range.flags |= NF_NAT_RANGE_PROTO_SPECIFIED;
        }
 
index c91083156edbe2b631b1fb11e3ead35f1925b8a7..166e33bed222d94eaf5b72de183544bfc7f762de 100644 (file)
@@ -1160,12 +1160,9 @@ static void ip6_rt_update_pmtu(struct dst_entry *dst, struct sock *sk,
                struct net *net = dev_net(dst->dev);
 
                rt6->rt6i_flags |= RTF_MODIFIED;
-               if (mtu < IPV6_MIN_MTU) {
-                       u32 features = dst_metric(dst, RTAX_FEATURES);
+               if (mtu < IPV6_MIN_MTU)
                        mtu = IPV6_MIN_MTU;
-                       features |= RTAX_FEATURE_ALLFRAG;
-                       dst_metric_set(dst, RTAX_FEATURES, features);
-               }
+
                dst_metric_set(dst, RTAX_MTU, mtu);
                rt6_update_expires(rt6, net->ipv6.sysctl.ip6_rt_mtu_expires);
        }
index 2c36c4765f47f28c42d1b2112b59a764ba4ed82f..837a406a9dd67bdf506f98a3ae05be55c06f2211 100644 (file)
@@ -1643,7 +1643,7 @@ __ieee80211_sta_handle_tspec_ac_params(struct ieee80211_sub_if_data *sdata)
 {
        struct ieee80211_local *local = sdata->local;
        struct ieee80211_if_managed *ifmgd = &sdata->u.mgd;
-       bool ret;
+       bool ret = false;
        int ac;
 
        if (local->hw.queues < IEEE80211_NUM_ACS)
index 1d5341f3761dfe1e57cc6505493bf270cca672de..5d3daae98bf0be1bc0fa699ec96208d2fa3da1d4 100644 (file)
@@ -183,6 +183,8 @@ static int ip_vs_ftp_out(struct ip_vs_app *app, struct ip_vs_conn *cp,
        struct nf_conn *ct;
        struct net *net;
 
+       *diff = 0;
+
 #ifdef CONFIG_IP_VS_IPV6
        /* This application helper doesn't work with IPv6 yet,
         * so turn this into a no-op for IPv6 packets
@@ -191,8 +193,6 @@ static int ip_vs_ftp_out(struct ip_vs_app *app, struct ip_vs_conn *cp,
                return 1;
 #endif
 
-       *diff = 0;
-
        /* Only useful for established sessions */
        if (cp->state != IP_VS_TCP_S_ESTABLISHED)
                return 1;
@@ -322,6 +322,9 @@ static int ip_vs_ftp_in(struct ip_vs_app *app, struct ip_vs_conn *cp,
        struct ip_vs_conn *n_cp;
        struct net *net;
 
+       /* no diff required for incoming packets */
+       *diff = 0;
+
 #ifdef CONFIG_IP_VS_IPV6
        /* This application helper doesn't work with IPv6 yet,
         * so turn this into a no-op for IPv6 packets
@@ -330,9 +333,6 @@ static int ip_vs_ftp_in(struct ip_vs_app *app, struct ip_vs_conn *cp,
                return 1;
 #endif
 
-       /* no diff required for incoming packets */
-       *diff = 0;
-
        /* Only useful for established sessions */
        if (cp->state != IP_VS_TCP_S_ESTABLISHED)
                return 1;
index a11674806707e18fb9d86860ad0717dfda0b0da2..46d1b26a468ed0d4cd0c9f30c02398f51c922db0 100644 (file)
@@ -611,16 +611,15 @@ __nf_conntrack_confirm(struct sk_buff *skb)
         */
        NF_CT_ASSERT(!nf_ct_is_confirmed(ct));
        pr_debug("Confirming conntrack %p\n", ct);
-       /* We have to check the DYING flag inside the lock to prevent
-          a race against nf_ct_get_next_corpse() possibly called from
-          user context, else we insert an already 'dead' hash, blocking
-          further use of that particular connection -JM */
+       /* We have to check the DYING flag after unlink to prevent
+        * a race against nf_ct_get_next_corpse() possibly called from
+        * user context, else we insert an already 'dead' hash, blocking
+        * further use of that particular connection -JM.
+        */
+       nf_ct_del_from_dying_or_unconfirmed_list(ct);
 
-       if (unlikely(nf_ct_is_dying(ct))) {
-               nf_conntrack_double_unlock(hash, reply_hash);
-               local_bh_enable();
-               return NF_ACCEPT;
-       }
+       if (unlikely(nf_ct_is_dying(ct)))
+               goto out;
 
        /* See if there's one in the list already, including reverse:
           NAT could have grabbed it without realizing, since we're
@@ -636,8 +635,6 @@ __nf_conntrack_confirm(struct sk_buff *skb)
                    zone == nf_ct_zone(nf_ct_tuplehash_to_ctrack(h)))
                        goto out;
 
-       nf_ct_del_from_dying_or_unconfirmed_list(ct);
-
        /* Timer relative to confirmation time, not original
           setting time, otherwise we'd get timer wrap in
           weird delay cases. */
@@ -673,6 +670,7 @@ __nf_conntrack_confirm(struct sk_buff *skb)
        return NF_ACCEPT;
 
 out:
+       nf_ct_add_to_dying_list(ct);
        nf_conntrack_double_unlock(hash, reply_hash);
        NF_CT_STAT_INC(net, insert_failed);
        local_bh_enable();
index 129a8daa4abf31959801e99c4f2fbfc7f1aab230..3b3ddb4fb9ee122a5b6d3a39450be38a64d6f614 100644 (file)
@@ -713,16 +713,12 @@ static int nft_flush_table(struct nft_ctx *ctx)
        struct nft_chain *chain, *nc;
        struct nft_set *set, *ns;
 
-       list_for_each_entry_safe(chain, nc, &ctx->table->chains, list) {
+       list_for_each_entry(chain, &ctx->table->chains, list) {
                ctx->chain = chain;
 
                err = nft_delrule_by_chain(ctx);
                if (err < 0)
                        goto out;
-
-               err = nft_delchain(ctx);
-               if (err < 0)
-                       goto out;
        }
 
        list_for_each_entry_safe(set, ns, &ctx->table->sets, list) {
@@ -735,6 +731,14 @@ static int nft_flush_table(struct nft_ctx *ctx)
                        goto out;
        }
 
+       list_for_each_entry_safe(chain, nc, &ctx->table->chains, list) {
+               ctx->chain = chain;
+
+               err = nft_delchain(ctx);
+               if (err < 0)
+                       goto out;
+       }
+
        err = nft_deltable(ctx);
 out:
        return err;
index cde4a6702fa3199421d6ced324e2bb74fdaa46ab..c421d94c4652625147ba65aebe4c251561cf37ff 100644 (file)
@@ -321,7 +321,8 @@ replay:
                nlh = nlmsg_hdr(skb);
                err = 0;
 
-               if (nlh->nlmsg_len < NLMSG_HDRLEN) {
+               if (nlmsg_len(nlh) < sizeof(struct nfgenmsg) ||
+                   skb->len < nlh->nlmsg_len) {
                        err = -EINVAL;
                        goto ack;
                }
@@ -469,7 +470,7 @@ static int nfnetlink_bind(struct net *net, int group)
        int type;
 
        if (group <= NFNLGRP_NONE || group > NFNLGRP_MAX)
-               return -EINVAL;
+               return 0;
 
        type = nfnl_group2type[group];
 
index afe2b0b45ec41f82df6f2430958a4392aa5eb608..aff54fb1c8a09fdb99fd4caab0959a80f28ffc37 100644 (file)
@@ -65,10 +65,10 @@ static void nft_nat_eval(const struct nft_expr *expr,
        }
 
        if (priv->sreg_proto_min) {
-               range.min_proto.all = (__force __be16)
-                                       data[priv->sreg_proto_min].data[0];
-               range.max_proto.all = (__force __be16)
-                                       data[priv->sreg_proto_max].data[0];
+               range.min_proto.all =
+                       *(__be16 *)&data[priv->sreg_proto_min].data[0];
+               range.max_proto.all =
+                       *(__be16 *)&data[priv->sreg_proto_max].data[0];
                range.flags |= NF_NAT_RANGE_PROTO_SPECIFIED;
        }
 
index 84ea76ca3f1fc52da96c31d3bf27fda678a1dd19..02fdde28dada498c1715b18ffa166d72ac6807d6 100644 (file)
@@ -61,6 +61,7 @@
 #include <linux/rhashtable.h>
 #include <asm/cacheflush.h>
 #include <linux/hash.h>
+#include <linux/genetlink.h>
 
 #include <net/net_namespace.h>
 #include <net/sock.h>
@@ -1095,6 +1096,8 @@ static void netlink_remove(struct sock *sk)
                __sk_del_bind_node(sk);
                netlink_update_listeners(sk);
        }
+       if (sk->sk_protocol == NETLINK_GENERIC)
+               atomic_inc(&genl_sk_destructing_cnt);
        netlink_table_ungrab();
 }
 
@@ -1211,6 +1214,20 @@ static int netlink_release(struct socket *sock)
         * will be purged.
         */
 
+       /* must not acquire netlink_table_lock in any way again before unbind
+        * and notifying genetlink is done as otherwise it might deadlock
+        */
+       if (nlk->netlink_unbind) {
+               int i;
+
+               for (i = 0; i < nlk->ngroups; i++)
+                       if (test_bit(i, nlk->groups))
+                               nlk->netlink_unbind(sock_net(sk), i + 1);
+       }
+       if (sk->sk_protocol == NETLINK_GENERIC &&
+           atomic_dec_return(&genl_sk_destructing_cnt) == 0)
+               wake_up(&genl_sk_destructing_waitq);
+
        sock->sk = NULL;
        wake_up_interruptible_all(&nlk->wait);
 
@@ -1246,13 +1263,6 @@ static int netlink_release(struct socket *sock)
                netlink_table_ungrab();
        }
 
-       if (nlk->netlink_unbind) {
-               int i;
-
-               for (i = 0; i < nlk->ngroups; i++)
-                       if (test_bit(i, nlk->groups))
-                               nlk->netlink_unbind(sock_net(sk), i + 1);
-       }
        kfree(nlk->groups);
        nlk->groups = NULL;
 
index f123a88496f8f5282287ba5028ae03110d25bb7c..f1c31b39aa3e0f5f8257b0ff72bd8bf909cac481 100644 (file)
@@ -2,6 +2,7 @@
 #define _AF_NETLINK_H
 
 #include <linux/rhashtable.h>
+#include <linux/atomic.h>
 #include <net/sock.h>
 
 #define NLGRPSZ(x)     (ALIGN(x, sizeof(unsigned long) * 8) / 8)
index 2e11061ef885562d2ff2a098448a7d9c8d1b64ee..ee57459fc2586842908751d282384dd1d683ed6f 100644 (file)
@@ -23,6 +23,9 @@
 static DEFINE_MUTEX(genl_mutex); /* serialization of message processing */
 static DECLARE_RWSEM(cb_lock);
 
+atomic_t genl_sk_destructing_cnt = ATOMIC_INIT(0);
+DECLARE_WAIT_QUEUE_HEAD(genl_sk_destructing_waitq);
+
 void genl_lock(void)
 {
        mutex_lock(&genl_mutex);
@@ -435,15 +438,18 @@ int genl_unregister_family(struct genl_family *family)
 
        genl_lock_all();
 
-       genl_unregister_mc_groups(family);
-
        list_for_each_entry(rc, genl_family_chain(family->id), family_list) {
                if (family->id != rc->id || strcmp(rc->name, family->name))
                        continue;
 
+               genl_unregister_mc_groups(family);
+
                list_del(&rc->family_list);
                family->n_ops = 0;
-               genl_unlock_all();
+               up_write(&cb_lock);
+               wait_event(genl_sk_destructing_waitq,
+                          atomic_read(&genl_sk_destructing_cnt) == 0);
+               genl_unlock();
 
                kfree(family->attrbuf);
                genl_ctrl_event(CTRL_CMD_DELFAMILY, family, NULL, 0);
@@ -985,7 +991,7 @@ static struct genl_multicast_group genl_ctrl_groups[] = {
 
 static int genl_bind(struct net *net, int group)
 {
-       int i, err = 0;
+       int i, err = -ENOENT;
 
        down_read(&cb_lock);
        for (i = 0; i < GENL_FAM_TAB_SIZE; i++) {
@@ -1014,7 +1020,6 @@ static int genl_bind(struct net *net, int group)
 static void genl_unbind(struct net *net, int group)
 {
        int i;
-       bool found = false;
 
        down_read(&cb_lock);
        for (i = 0; i < GENL_FAM_TAB_SIZE; i++) {
@@ -1027,14 +1032,11 @@ static void genl_unbind(struct net *net, int group)
 
                                if (f->mcast_unbind)
                                        f->mcast_unbind(net, fam_grp);
-                               found = true;
                                break;
                        }
                }
        }
        up_read(&cb_lock);
-
-       WARN_ON(!found);
 }
 
 static int __net_init genl_pernet_init(struct net *net)
index 4e9a5f035cbcf144998ae7c22c90151429cf7031..b07349e82d788dba64e768cf3ea1da77b08a9652 100644 (file)
@@ -524,7 +524,7 @@ static int ovs_packet_cmd_execute(struct sk_buff *skb, struct genl_info *info)
        struct vport *input_vport;
        int len;
        int err;
-       bool log = !a[OVS_FLOW_ATTR_PROBE];
+       bool log = !a[OVS_PACKET_ATTR_PROBE];
 
        err = -EINVAL;
        if (!a[OVS_PACKET_ATTR_PACKET] || !a[OVS_PACKET_ATTR_KEY] ||
@@ -610,6 +610,7 @@ static const struct nla_policy packet_policy[OVS_PACKET_ATTR_MAX + 1] = {
        [OVS_PACKET_ATTR_PACKET] = { .len = ETH_HLEN },
        [OVS_PACKET_ATTR_KEY] = { .type = NLA_NESTED },
        [OVS_PACKET_ATTR_ACTIONS] = { .type = NLA_NESTED },
+       [OVS_PACKET_ATTR_PROBE] = { .type = NLA_FLAG },
 };
 
 static const struct genl_ops dp_packet_genl_ops[] = {
index 6880f34a529a56510b1145e14d41ed04803dd6a7..9cfe2e1dd8b5099bbac7d824241bd0d06cb01cf7 100644 (file)
@@ -2517,7 +2517,7 @@ static int packet_snd(struct socket *sock, struct msghdr *msg, size_t len)
        err = -EINVAL;
        if (sock->type == SOCK_DGRAM) {
                offset = dev_hard_header(skb, dev, ntohs(proto), addr, NULL, len);
-               if (unlikely(offset) < 0)
+               if (unlikely(offset < 0))
                        goto out_free;
        } else {
                if (ll_header_truncated(dev, len))
index 2625eccb77d5d7738f9e50930ab37a6db6a80760..aafe94bf292e73ecb765a31ae3456c3c11fe932f 100644 (file)
@@ -1603,7 +1603,7 @@ static int sctp_sendmsg(struct kiocb *iocb, struct sock *sk,
        sctp_assoc_t associd = 0;
        sctp_cmsgs_t cmsgs = { NULL };
        sctp_scope_t scope;
-       bool fill_sinfo_ttl = false;
+       bool fill_sinfo_ttl = false, wait_connect = false;
        struct sctp_datamsg *datamsg;
        int msg_flags = msg->msg_flags;
        __u16 sinfo_flags = 0;
@@ -1943,6 +1943,7 @@ static int sctp_sendmsg(struct kiocb *iocb, struct sock *sk,
                if (err < 0)
                        goto out_free;
 
+               wait_connect = true;
                pr_debug("%s: we associated primitively\n", __func__);
        }
 
@@ -1980,6 +1981,11 @@ static int sctp_sendmsg(struct kiocb *iocb, struct sock *sk,
        sctp_datamsg_put(datamsg);
        err = msg_len;
 
+       if (unlikely(wait_connect)) {
+               timeo = sock_sndtimeo(sk, msg_flags & MSG_DONTWAIT);
+               sctp_wait_for_connect(asoc, &timeo);
+       }
+
        /* If we are already past ASSOCIATE, the lower
         * layers are responsible for association cleanup.
         */
index 96ceefeb9daf4eb780cd168b4d008418c0055dd9..a9e174fc0f91fd672eb3779f23fff9ef7decdb74 100644 (file)
@@ -220,10 +220,11 @@ static void bclink_retransmit_pkt(u32 after, u32 to)
        struct sk_buff *skb;
 
        skb_queue_walk(&bcl->outqueue, skb) {
-               if (more(buf_seqno(skb), after))
+               if (more(buf_seqno(skb), after)) {
+                       tipc_link_retransmit(bcl, skb, mod(to - after));
                        break;
+               }
        }
-       tipc_link_retransmit(bcl, skb, mod(to - after));
 }
 
 /**
index 7b8309840d4e1b499cc7efbd73bc07222c0d5def..d39d1cbc86b1663f1902e6662dfe372c50978327 100644 (file)
@@ -1530,45 +1530,40 @@ static void reg_call_notifier(struct wiphy *wiphy,
 
 static bool reg_wdev_chan_valid(struct wiphy *wiphy, struct wireless_dev *wdev)
 {
-       struct ieee80211_channel *ch;
        struct cfg80211_chan_def chandef;
        struct cfg80211_registered_device *rdev = wiphy_to_rdev(wiphy);
-       bool ret = true;
+       enum nl80211_iftype iftype;
 
        wdev_lock(wdev);
+       iftype = wdev->iftype;
 
+       /* make sure the interface is active */
        if (!wdev->netdev || !netif_running(wdev->netdev))
-               goto out;
+               goto wdev_inactive_unlock;
 
-       switch (wdev->iftype) {
+       switch (iftype) {
        case NL80211_IFTYPE_AP:
        case NL80211_IFTYPE_P2P_GO:
                if (!wdev->beacon_interval)
-                       goto out;
-
-               ret = cfg80211_reg_can_beacon(wiphy,
-                                             &wdev->chandef, wdev->iftype);
+                       goto wdev_inactive_unlock;
+               chandef = wdev->chandef;
                break;
        case NL80211_IFTYPE_ADHOC:
                if (!wdev->ssid_len)
-                       goto out;
-
-               ret = cfg80211_reg_can_beacon(wiphy,
-                                             &wdev->chandef, wdev->iftype);
+                       goto wdev_inactive_unlock;
+               chandef = wdev->chandef;
                break;
        case NL80211_IFTYPE_STATION:
        case NL80211_IFTYPE_P2P_CLIENT:
                if (!wdev->current_bss ||
                    !wdev->current_bss->pub.channel)
-                       goto out;
+                       goto wdev_inactive_unlock;
 
-               ch = wdev->current_bss->pub.channel;
-               if (rdev->ops->get_channel &&
-                   !rdev_get_channel(rdev, wdev, &chandef))
-                       ret = cfg80211_chandef_usable(wiphy, &chandef,
-                                                     IEEE80211_CHAN_DISABLED);
-               else
-                       ret = !(ch->flags & IEEE80211_CHAN_DISABLED);
+               if (!rdev->ops->get_channel ||
+                   rdev_get_channel(rdev, wdev, &chandef))
+                       cfg80211_chandef_create(&chandef,
+                                               wdev->current_bss->pub.channel,
+                                               NL80211_CHAN_NO_HT);
                break;
        case NL80211_IFTYPE_MONITOR:
        case NL80211_IFTYPE_AP_VLAN:
@@ -1581,9 +1576,26 @@ static bool reg_wdev_chan_valid(struct wiphy *wiphy, struct wireless_dev *wdev)
                break;
        }
 
-out:
        wdev_unlock(wdev);
-       return ret;
+
+       switch (iftype) {
+       case NL80211_IFTYPE_AP:
+       case NL80211_IFTYPE_P2P_GO:
+       case NL80211_IFTYPE_ADHOC:
+               return cfg80211_reg_can_beacon(wiphy, &chandef, iftype);
+       case NL80211_IFTYPE_STATION:
+       case NL80211_IFTYPE_P2P_CLIENT:
+               return cfg80211_chandef_usable(wiphy, &chandef,
+                                              IEEE80211_CHAN_DISABLED);
+       default:
+               break;
+       }
+
+       return true;
+
+wdev_inactive_unlock:
+       wdev_unlock(wdev);
+       return true;
 }
 
 static void reg_leave_invalid_chans(struct wiphy *wiphy)
index 56ea99a12ab79c82e062b54cfd34d9a39ef6a867..537c38ca2e1c7008b2f0f98d4e172c714162eb79 100755 (executable)
@@ -255,7 +255,6 @@ if ($arch eq "x86_64") {
     # force flags for this arch
     $ld .= " -m shlelf_linux";
     $objcopy .= " -O elf32-sh-linux";
-    $cc .= " -m32";
 
 } elsif ($arch eq "powerpc") {
     $local_regex = "^[0-9a-fA-F]+\\s+t\\s+(\\.?\\S+)";
index 3badc70124ab19d9b2e6115198e88c46718676e9..0d580186ef1ac379bcd2cb699ac2f33baeac9029 100644 (file)
 #define CYCLES_PER_SECOND      8000
 #define TICKS_PER_SECOND       (TICKS_PER_CYCLE * CYCLES_PER_SECOND)
 
-#define TRANSFER_DELAY_TICKS   0x2e00 /* 479.17 µs */
+/*
+ * Nominally 3125 bytes/second, but the MIDI port's clock might be
+ * 1% too slow, and the bus clock 100 ppm too fast.
+ */
+#define MIDI_BYTES_PER_SECOND  3093
+
+/*
+ * Several devices look only at the first eight data blocks.
+ * In any case, this is more than enough for the MIDI data rate.
+ */
+#define MAX_MIDI_RX_BLOCKS     8
+
+#define TRANSFER_DELAY_TICKS   0x2e00 /* 479.17 Âµs */
 
 /* isochronous header parameters */
 #define ISO_DATA_LENGTH_SHIFT  16
@@ -78,8 +90,6 @@ int amdtp_stream_init(struct amdtp_stream *s, struct fw_unit *unit,
        s->callbacked = false;
        s->sync_slave = NULL;
 
-       s->rx_blocks_for_midi = UINT_MAX;
-
        return 0;
 }
 EXPORT_SYMBOL(amdtp_stream_init);
@@ -222,6 +232,14 @@ sfc_found:
        for (i = 0; i < pcm_channels; i++)
                s->pcm_positions[i] = i;
        s->midi_position = s->pcm_channels;
+
+       /*
+        * We do not know the actual MIDI FIFO size of most devices.  Just
+        * assume two bytes, i.e., one byte can be received over the bus while
+        * the previous one is transmitted over MIDI.
+        * (The value here is adjusted for midi_ratelimit_per_packet().)
+        */
+       s->midi_fifo_limit = rate - MIDI_BYTES_PER_SECOND * s->syt_interval + 1;
 }
 EXPORT_SYMBOL(amdtp_stream_set_parameters);
 
@@ -463,6 +481,36 @@ static void amdtp_fill_pcm_silence(struct amdtp_stream *s,
        }
 }
 
+/*
+ * To avoid sending MIDI bytes at too high a rate, assume that the receiving
+ * device has a FIFO, and track how much it is filled.  This values increases
+ * by one whenever we send one byte in a packet, but the FIFO empties at
+ * a constant rate independent of our packet rate.  One packet has syt_interval
+ * samples, so the number of bytes that empty out of the FIFO, per packet(!),
+ * is MIDI_BYTES_PER_SECOND * syt_interval / sample_rate.  To avoid storing
+ * fractional values, the values in midi_fifo_used[] are measured in bytes
+ * multiplied by the sample rate.
+ */
+static bool midi_ratelimit_per_packet(struct amdtp_stream *s, unsigned int port)
+{
+       int used;
+
+       used = s->midi_fifo_used[port];
+       if (used == 0) /* common shortcut */
+               return true;
+
+       used -= MIDI_BYTES_PER_SECOND * s->syt_interval;
+       used = max(used, 0);
+       s->midi_fifo_used[port] = used;
+
+       return used < s->midi_fifo_limit;
+}
+
+static void midi_rate_use_one_byte(struct amdtp_stream *s, unsigned int port)
+{
+       s->midi_fifo_used[port] += amdtp_rate_table[s->sfc];
+}
+
 static void amdtp_fill_midi(struct amdtp_stream *s,
                            __be32 *buffer, unsigned int frames)
 {
@@ -470,16 +518,21 @@ static void amdtp_fill_midi(struct amdtp_stream *s,
        u8 *b;
 
        for (f = 0; f < frames; f++) {
-               buffer[s->midi_position] = 0;
                b = (u8 *)&buffer[s->midi_position];
 
                port = (s->data_block_counter + f) % 8;
-               if ((f >= s->rx_blocks_for_midi) ||
-                   (s->midi[port] == NULL) ||
-                   (snd_rawmidi_transmit(s->midi[port], b + 1, 1) <= 0))
-                       b[0] = 0x80;
-               else
+               if (f < MAX_MIDI_RX_BLOCKS &&
+                   midi_ratelimit_per_packet(s, port) &&
+                   s->midi[port] != NULL &&
+                   snd_rawmidi_transmit(s->midi[port], &b[1], 1) == 1) {
+                       midi_rate_use_one_byte(s, port);
                        b[0] = 0x81;
+               } else {
+                       b[0] = 0x80;
+                       b[1] = 0;
+               }
+               b[2] = 0;
+               b[3] = 0;
 
                buffer += s->data_block_quadlets;
        }
index e6e8926275b0542c9891373e2d3d473cbd682286..8a03a91e728b0f9bc4feb23a4bdd9f22fdf5952d 100644 (file)
@@ -148,13 +148,12 @@ struct amdtp_stream {
        bool double_pcm_frames;
 
        struct snd_rawmidi_substream *midi[AMDTP_MAX_CHANNELS_FOR_MIDI * 8];
+       int midi_fifo_limit;
+       int midi_fifo_used[AMDTP_MAX_CHANNELS_FOR_MIDI * 8];
 
        /* quirk: fixed interval of dbc between previos/current packets. */
        unsigned int tx_dbc_interval;
 
-       /* quirk: the first count of data blocks in an rx packet for MIDI */
-       unsigned int rx_blocks_for_midi;
-
        bool callbacked;
        wait_queue_head_t callback_wait;
        struct amdtp_stream *sync_slave;
index 1aab0a32870c84d20a0c5b87f46d625299b34fd4..0ebcabfdc7ce0162c9a77ed30ca038e6588cae63 100644 (file)
@@ -484,13 +484,6 @@ int snd_bebob_stream_init_duplex(struct snd_bebob *bebob)
                amdtp_stream_destroy(&bebob->rx_stream);
                destroy_both_connections(bebob);
        }
-       /*
-        * The firmware for these devices ignore MIDI messages in more than
-        * first 8 data blocks of an received AMDTP packet.
-        */
-       if (bebob->spec == &maudio_fw410_spec ||
-           bebob->spec == &maudio_special_spec)
-               bebob->rx_stream.rx_blocks_for_midi = 8;
 end:
        return err;
 }
index b985fc5ebdc6b9cc490e41695d76b579a7b3fe3d..4f440e16366780f097d8c03daeb45e01fb5e7eb0 100644 (file)
@@ -179,11 +179,6 @@ int snd_efw_stream_init_duplex(struct snd_efw *efw)
                destroy_stream(efw, &efw->tx_stream);
                goto end;
        }
-       /*
-        * Fireworks ignores MIDI messages in more than first 8 data
-        * blocks of an received AMDTP packet.
-        */
-       efw->rx_stream.rx_blocks_for_midi = 8;
 
        /* set IEC61883 compliant mode (actually not fully compliant...) */
        err = snd_efw_command_set_tx_mode(efw, SND_EFW_TRANSPORT_MODE_IEC61883);
index 41650d5b93b70e5a9a36abbb7ffae4579075d8ab..3e2ef61c627b831bfec65724cc7166db051f5099 100644 (file)
@@ -913,6 +913,7 @@ static void volume_control_quirks(struct usb_mixer_elem_info *cval,
        case USB_ID(0x046d, 0x0807): /* Logitech Webcam C500 */
        case USB_ID(0x046d, 0x0808):
        case USB_ID(0x046d, 0x0809):
+       case USB_ID(0x046d, 0x0819): /* Logitech Webcam C210 */
        case USB_ID(0x046d, 0x081b): /* HD Webcam c310 */
        case USB_ID(0x046d, 0x081d): /* HD Webcam c510 */
        case USB_ID(0x046d, 0x0825): /* HD Webcam c270 */
index 6eedba1f773227d5df93bae06d7f3a0fcc1bd648..653d1bad77de2331ba18771f99a01dddcee0175c 100644 (file)
@@ -22,6 +22,8 @@
 #error only <linux/bitops.h> can be included directly
 #endif
 
+#include <asm-generic/bitops/hweight.h>
+
 #include <asm-generic/bitops/atomic.h>
 
 #endif /* __TOOLS_ASM_GENERIC_BITOPS_H */
diff --git a/tools/include/asm-generic/bitops/arch_hweight.h b/tools/include/asm-generic/bitops/arch_hweight.h
new file mode 100644 (file)
index 0000000..318bb2b
--- /dev/null
@@ -0,0 +1 @@
+#include "../../../../include/asm-generic/bitops/arch_hweight.h"
diff --git a/tools/include/asm-generic/bitops/const_hweight.h b/tools/include/asm-generic/bitops/const_hweight.h
new file mode 100644 (file)
index 0000000..0afd644
--- /dev/null
@@ -0,0 +1 @@
+#include "../../../../include/asm-generic/bitops/const_hweight.h"
diff --git a/tools/include/asm-generic/bitops/hweight.h b/tools/include/asm-generic/bitops/hweight.h
new file mode 100644 (file)
index 0000000..290120c
--- /dev/null
@@ -0,0 +1,7 @@
+#ifndef _TOOLS_LINUX_ASM_GENERIC_BITOPS_HWEIGHT_H_
+#define _TOOLS_LINUX_ASM_GENERIC_BITOPS_HWEIGHT_H_
+
+#include <asm-generic/bitops/arch_hweight.h>
+#include <asm-generic/bitops/const_hweight.h>
+
+#endif /* _TOOLS_LINUX_ASM_GENERIC_BITOPS_HWEIGHT_H_ */
index 26005a15e7e29d34332b88e68a49fe223953913b..5ad9ee1dd7f6aed579a5e631e309438a80bb472f 100644 (file)
@@ -1,9 +1,9 @@
 #ifndef _TOOLS_LINUX_BITOPS_H_
 #define _TOOLS_LINUX_BITOPS_H_
 
+#include <asm/types.h>
 #include <linux/kernel.h>
 #include <linux/compiler.h>
-#include <asm/hweight.h>
 
 #ifndef __WORDSIZE
 #define __WORDSIZE (__SIZEOF_LONG__ * 8)
 #define BITS_TO_U32(nr)                DIV_ROUND_UP(nr, BITS_PER_BYTE * sizeof(u32))
 #define BITS_TO_BYTES(nr)      DIV_ROUND_UP(nr, BITS_PER_BYTE)
 
+extern unsigned int __sw_hweight8(unsigned int w);
+extern unsigned int __sw_hweight16(unsigned int w);
+extern unsigned int __sw_hweight32(unsigned int w);
+extern unsigned long __sw_hweight64(__u64 w);
+
 /*
  * Include this here because some architectures need generic_ffs/fls in
  * scope
index a74fba6d774353d33fac7f04b71abdd241e0218e..86ea2d7b88451c219dacad848e60564fb1a64ecf 100644 (file)
@@ -67,7 +67,7 @@ int debugfs_valid_mountpoint(const char *debugfs)
 
        if (statfs(debugfs, &st_fs) < 0)
                return -ENOENT;
-       else if (st_fs.f_type != (long) DEBUGFS_MAGIC)
+       else if ((long)st_fs.f_type != (long)DEBUGFS_MAGIC)
                return -ENOENT;
 
        return 0;
index 65d9be3f988747ae300db30d3b62cf0e8213dd69..128ef6332a6bd89c0ddbeef283c4dfccbf5f8417 100644 (file)
@@ -79,7 +79,7 @@ static int fs__valid_mount(const char *fs, long magic)
 
        if (statfs(fs, &st_fs) < 0)
                return -ENOENT;
-       else if (st_fs.f_type != magic)
+       else if ((long)st_fs.f_type != magic)
                return -ENOENT;
 
        return 0;
index 83e2887f91a39200612290bd0b2b2fbd824e660a..fbbfdc39271dac69bd96aa932d6e62318dbce143 100644 (file)
@@ -6,12 +6,15 @@ tools/lib/symbol/kallsyms.c
 tools/lib/symbol/kallsyms.h
 tools/lib/util/find_next_bit.c
 tools/include/asm/bug.h
+tools/include/asm-generic/bitops/arch_hweight.h
 tools/include/asm-generic/bitops/atomic.h
+tools/include/asm-generic/bitops/const_hweight.h
 tools/include/asm-generic/bitops/__ffs.h
 tools/include/asm-generic/bitops/__fls.h
 tools/include/asm-generic/bitops/find.h
 tools/include/asm-generic/bitops/fls64.h
 tools/include/asm-generic/bitops/fls.h
+tools/include/asm-generic/bitops/hweight.h
 tools/include/asm-generic/bitops.h
 tools/include/linux/bitops.h
 tools/include/linux/compiler.h
@@ -19,6 +22,8 @@ tools/include/linux/export.h
 tools/include/linux/hash.h
 tools/include/linux/log2.h
 tools/include/linux/types.h
+include/asm-generic/bitops/arch_hweight.h
+include/asm-generic/bitops/const_hweight.h
 include/asm-generic/bitops/fls64.h
 include/asm-generic/bitops/__fls.h
 include/asm-generic/bitops/fls.h
@@ -29,6 +34,7 @@ include/linux/list.h
 include/linux/hash.h
 include/linux/stringify.h
 lib/find_next_bit.c
+lib/hweight.c
 lib/rbtree.c
 include/linux/swab.h
 arch/*/include/asm/unistd*.h
index 67a03a825b3c94bb894f0f557dac3bb520943e65..aa6a50447c32b63fd3f55a5ada5059610d610ec1 100644 (file)
@@ -232,12 +232,15 @@ LIB_H += ../include/linux/hash.h
 LIB_H += ../../include/linux/stringify.h
 LIB_H += util/include/linux/bitmap.h
 LIB_H += ../include/linux/bitops.h
+LIB_H += ../include/asm-generic/bitops/arch_hweight.h
 LIB_H += ../include/asm-generic/bitops/atomic.h
+LIB_H += ../include/asm-generic/bitops/const_hweight.h
 LIB_H += ../include/asm-generic/bitops/find.h
 LIB_H += ../include/asm-generic/bitops/fls64.h
 LIB_H += ../include/asm-generic/bitops/fls.h
 LIB_H += ../include/asm-generic/bitops/__ffs.h
 LIB_H += ../include/asm-generic/bitops/__fls.h
+LIB_H += ../include/asm-generic/bitops/hweight.h
 LIB_H += ../include/asm-generic/bitops.h
 LIB_H += ../include/linux/compiler.h
 LIB_H += ../include/linux/log2.h
@@ -255,7 +258,6 @@ LIB_H += util/include/linux/linkage.h
 LIB_H += util/include/asm/asm-offsets.h
 LIB_H += ../include/asm/bug.h
 LIB_H += util/include/asm/byteorder.h
-LIB_H += util/include/asm/hweight.h
 LIB_H += util/include/asm/swab.h
 LIB_H += util/include/asm/system.h
 LIB_H += util/include/asm/uaccess.h
@@ -462,10 +464,12 @@ BUILTIN_OBJS += $(OUTPUT)builtin-bench.o
 # Benchmark modules
 BUILTIN_OBJS += $(OUTPUT)bench/sched-messaging.o
 BUILTIN_OBJS += $(OUTPUT)bench/sched-pipe.o
-ifeq ($(RAW_ARCH),x86_64)
+ifeq ($(ARCH), x86)
+ifeq ($(IS_64_BIT), 1)
 BUILTIN_OBJS += $(OUTPUT)bench/mem-memcpy-x86-64-asm.o
 BUILTIN_OBJS += $(OUTPUT)bench/mem-memset-x86-64-asm.o
 endif
+endif
 BUILTIN_OBJS += $(OUTPUT)bench/mem-memcpy.o
 BUILTIN_OBJS += $(OUTPUT)bench/futex-hash.o
 BUILTIN_OBJS += $(OUTPUT)bench/futex-wake.o
@@ -743,6 +747,9 @@ $(OUTPUT)util/kallsyms.o: ../lib/symbol/kallsyms.c $(OUTPUT)PERF-CFLAGS
 $(OUTPUT)util/rbtree.o: ../../lib/rbtree.c $(OUTPUT)PERF-CFLAGS
        $(QUIET_CC)$(CC) -o $@ -c $(CFLAGS) -Wno-unused-parameter -DETC_PERFCONFIG='"$(ETC_PERFCONFIG_SQ)"' $<
 
+$(OUTPUT)util/hweight.o: ../../lib/hweight.c $(OUTPUT)PERF-CFLAGS
+       $(QUIET_CC)$(CC) -o $@ -c $(CFLAGS) -Wno-unused-parameter -DETC_PERFCONFIG='"$(ETC_PERFCONFIG_SQ)"' $<
+
 $(OUTPUT)util/find_next_bit.o: ../lib/util/find_next_bit.c $(OUTPUT)PERF-CFLAGS
        $(QUIET_CC)$(CC) -o $@ -c $(CFLAGS) -Wno-unused-parameter -DETC_PERFCONFIG='"$(ETC_PERFCONFIG_SQ)"' $<
 
index 3bb50eac5542fc62c4482c92f4478806e731a9f7..0c370f81e00280c6428ddfe0975584edcb9d02a7 100644 (file)
@@ -103,7 +103,7 @@ static Dwarf_Frame *get_eh_frame(Dwfl_Module *mod, Dwarf_Addr pc)
                return NULL;
        }
 
-       result = dwarf_cfi_addrframe(cfi, pc, &frame);
+       result = dwarf_cfi_addrframe(cfi, pc-bias, &frame);
        if (result) {
                pr_debug("%s(): %s\n", __func__, dwfl_errmsg(-1));
                return NULL;
@@ -128,7 +128,7 @@ static Dwarf_Frame *get_dwarf_frame(Dwfl_Module *mod, Dwarf_Addr pc)
                return NULL;
        }
 
-       result = dwarf_cfi_addrframe(cfi, pc, &frame);
+       result = dwarf_cfi_addrframe(cfi, pc-bias, &frame);
        if (result) {
                pr_debug("%s(): %s\n", __func__, dwfl_errmsg(-1));
                return NULL;
@@ -145,7 +145,7 @@ static Dwarf_Frame *get_dwarf_frame(Dwfl_Module *mod, Dwarf_Addr pc)
  *             yet used)
  *     -1 in case of errors
  */
-static int check_return_addr(struct dso *dso, Dwarf_Addr pc)
+static int check_return_addr(struct dso *dso, u64 map_start, Dwarf_Addr pc)
 {
        int             rc = -1;
        Dwfl            *dwfl;
@@ -155,6 +155,7 @@ static int check_return_addr(struct dso *dso, Dwarf_Addr pc)
        Dwarf_Addr      start = pc;
        Dwarf_Addr      end = pc;
        bool            signalp;
+       const char      *exec_file = dso->long_name;
 
        dwfl = dso->dwfl;
 
@@ -165,8 +166,10 @@ static int check_return_addr(struct dso *dso, Dwarf_Addr pc)
                        return -1;
                }
 
-               if (dwfl_report_offline(dwfl, "", dso->long_name, -1) == NULL) {
-                       pr_debug("dwfl_report_offline() failed %s\n",
+               mod = dwfl_report_elf(dwfl, exec_file, exec_file, -1,
+                                               map_start, false);
+               if (!mod) {
+                       pr_debug("dwfl_report_elf() failed %s\n",
                                                dwarf_errmsg(-1));
                        /*
                         * We normally cache the DWARF debug info and never
@@ -256,10 +259,10 @@ int arch_skip_callchain_idx(struct thread *thread, struct ip_callchain *chain)
                return skip_slot;
        }
 
-       rc = check_return_addr(dso, ip);
+       rc = check_return_addr(dso, al.map->start, ip);
 
-       pr_debug("DSO %s, nr %" PRIx64 ", ip 0x%" PRIx64 "rc %d\n",
-                               dso->long_name, chain->nr, ip, rc);
+       pr_debug("[DSO %s, sym %s, ip 0x%" PRIx64 "] rc %d\n",
+                               dso->long_name, al.sym->name, ip, rc);
 
        if (rc == 0) {
                /*
index 07a8d7646a1549c61699f7311285238ef5ef93cf..005cc283790cfb7cf4db014362cb5d56f2a89ca2 100644 (file)
 #include <stdlib.h>
 #include <signal.h>
 #include <sys/wait.h>
-#include <linux/unistd.h>
 #include <string.h>
 #include <errno.h>
 #include <assert.h>
 #include <sys/time.h>
 #include <sys/types.h>
+#include <sys/syscall.h>
 
 #include <pthread.h>
 
index 961cea183a832fb831fc40ae4d88a96e661c197e..616f0fcb47010abf68ac7e4a9e256fa559af4499 100644 (file)
@@ -66,7 +66,6 @@
 #include <sys/utsname.h>
 #include <sys/mman.h>
 
-#include <linux/unistd.h>
 #include <linux/types.h>
 
 static volatile int done;
index 5d4b039fe1edc6ebf6f6dafec597e125383d0c4f..648e31ff4021c2e11520ab8b00e6f89213d324a9 100644 (file)
@@ -20,7 +20,7 @@ NO_PERF_REGS := 1
 
 # Additional ARCH settings for x86
 ifeq ($(ARCH),x86)
-  ifeq (${IS_X86_64}, 1)
+  ifeq (${IS_64_BIT}, 1)
     CFLAGS += -DHAVE_ARCH_X86_64_SUPPORT
     ARCH_INCLUDE = ../../arch/x86/lib/memcpy_64.S ../../arch/x86/lib/memset_64.S
     LIBUNWIND_LIBS = -lunwind -lunwind-x86_64
index 851cd0172a7694a0e21fd18d07c79031d5f9b253..ff95a68741d1ccdb54e54d929f2292e88963a5d1 100644 (file)
@@ -1,7 +1,7 @@
 
 uname_M := $(shell uname -m 2>/dev/null || echo not)
 
-ARCH ?= $(shell echo $(uname_M) | sed -e s/i.86/i386/ -e s/sun4u/sparc64/ \
+RAW_ARCH := $(shell echo $(uname_M) | sed -e s/i.86/i386/ -e s/sun4u/sparc64/ \
                                   -e s/arm.*/arm/ -e s/sa110/arm/ \
                                   -e s/s390x/s390/ -e s/parisc64/parisc/ \
                                   -e s/ppc.*/powerpc/ -e s/mips.*/mips/ \
@@ -9,23 +9,23 @@ ARCH ?= $(shell echo $(uname_M) | sed -e s/i.86/i386/ -e s/sun4u/sparc64/ \
                                   -e s/tile.*/tile/ )
 
 # Additional ARCH settings for x86
-ifeq ($(ARCH),i386)
-  override ARCH := x86
+ifeq ($(RAW_ARCH),i386)
+  ARCH ?= x86
 endif
 
-ifeq ($(ARCH),x86_64)
-  override ARCH := x86
-  IS_X86_64 := 0
-  ifeq (, $(findstring m32,$(CFLAGS)))
-    IS_X86_64 := $(shell echo __x86_64__ | ${CC} -E -x c - | tail -n 1)
-    RAW_ARCH := x86_64
+ifeq ($(RAW_ARCH),x86_64)
+  ARCH ?= x86
+
+  ifneq (, $(findstring m32,$(CFLAGS)))
+    RAW_ARCH := x86_32
   endif
 endif
 
-ifeq (${IS_X86_64}, 1)
+ARCH ?= $(RAW_ARCH)
+
+LP64 := $(shell echo __LP64__ | ${CC} ${CFLAGS} -E -x c - | tail -n 1)
+ifeq ($(LP64), 1)
   IS_64_BIT := 1
-else ifeq ($(ARCH),x86)
-  IS_64_BIT := 0
 else
-  IS_64_BIT := $(shell echo __LP64__ | ${CC} ${CFLAGS} -E -x c - | tail -n 1)
+  IS_64_BIT := 0
 endif
index a3b13d7dc1d43f3caf301b4d9f941c60d88ed37c..6ef68165c9db628d23bbe85b48945ac2581ec979 100644 (file)
@@ -6,7 +6,6 @@
 #include <sys/syscall.h>
 #include <linux/types.h>
 #include <linux/perf_event.h>
-#include <asm/unistd.h>
 
 #if defined(__i386__)
 #define mb()           asm volatile("lock; addl $0,0(%%esp)" ::: "memory")
index ab28cca2cb97ad436dd7c419ee4ee7fa37ecb0b9..0bf06bec68c7e9786668990ad399b578326726c5 100644 (file)
@@ -11,6 +11,9 @@
 #include "thread.h"
 #include "callchain.h"
 
+/* For bsearch. We try to unwind functions in shared object. */
+#include <stdlib.h>
+
 static int mmap_handler(struct perf_tool *tool __maybe_unused,
                        union perf_event *event,
                        struct perf_sample *sample __maybe_unused,
@@ -28,7 +31,7 @@ static int init_live_machine(struct machine *machine)
                                                  mmap_handler, machine, true);
 }
 
-#define MAX_STACK 6
+#define MAX_STACK 8
 
 static int unwind_entry(struct unwind_entry *entry, void *arg)
 {
@@ -37,6 +40,8 @@ static int unwind_entry(struct unwind_entry *entry, void *arg)
        static const char *funcs[MAX_STACK] = {
                "test__arch_unwind_sample",
                "unwind_thread",
+               "compare",
+               "bsearch",
                "krava_3",
                "krava_2",
                "krava_1",
@@ -88,10 +93,37 @@ static int unwind_thread(struct thread *thread)
        return err;
 }
 
+static int global_unwind_retval = -INT_MAX;
+
+__attribute__ ((noinline))
+static int compare(void *p1, void *p2)
+{
+       /* Any possible value should be 'thread' */
+       struct thread *thread = *(struct thread **)p1;
+
+       if (global_unwind_retval == -INT_MAX)
+               global_unwind_retval = unwind_thread(thread);
+
+       return p1 - p2;
+}
+
 __attribute__ ((noinline))
 static int krava_3(struct thread *thread)
 {
-       return unwind_thread(thread);
+       struct thread *array[2] = {thread, thread};
+       void *fp = &bsearch;
+       /*
+        * make _bsearch a volatile function pointer to
+        * prevent potential optimization, which may expand
+        * bsearch and call compare directly from this function,
+        * instead of libc shared object.
+        */
+       void *(*volatile _bsearch)(void *, void *, size_t,
+                       size_t, int (*)(void *, void *));
+
+       _bsearch = fp;
+       _bsearch(array, &thread, 2, sizeof(struct thread **), compare);
+       return global_unwind_retval;
 }
 
 __attribute__ ((noinline))
index 0784a9420528603efa9450a8c72c78ebf271298a..cadbdc90a5cbf319385cb67aa5a88c06cdf107dc 100644 (file)
@@ -116,11 +116,6 @@ struct annotation {
        struct annotated_source *src;
 };
 
-struct sannotation {
-       struct annotation annotation;
-       struct symbol     symbol;
-};
-
 static inline struct sym_hist *annotation__histogram(struct annotation *notes, int idx)
 {
        return (((void *)&notes->src->histograms) +
@@ -129,8 +124,7 @@ static inline struct sym_hist *annotation__histogram(struct annotation *notes, i
 
 static inline struct annotation *symbol__annotation(struct symbol *sym)
 {
-       struct sannotation *a = container_of(sym, struct sannotation, symbol);
-       return &a->annotation;
+       return (void *)sym - symbol_conf.priv_size;
 }
 
 int addr_map_symbol__inc_samples(struct addr_map_symbol *ams, int evidx);
index 5cf9e1b5989de40cb677b1bd744d684cd3bfc871..d04d770d90f6e29bc17d4d5d1299e76278b5ee1c 100644 (file)
@@ -71,7 +71,9 @@ extern char *perf_path(const char *fmt, ...) __attribute__((format (printf, 1, 2
 extern char *perf_pathdup(const char *fmt, ...)
        __attribute__((format (printf, 1, 2)));
 
+#ifndef __UCLIBC__
 /* Matches the libc/libbsd function attribute so we declare this unconditionally: */
 extern size_t strlcpy(char *dest, const char *src, size_t size);
+#endif
 
 #endif /* __PERF_CACHE_H */
diff --git a/tools/perf/util/hweight.c b/tools/perf/util/hweight.c
deleted file mode 100644 (file)
index 5c1d0d0..0000000
+++ /dev/null
@@ -1,31 +0,0 @@
-#include <linux/bitops.h>
-
-/**
- * hweightN - returns the hamming weight of a N-bit word
- * @x: the word to weigh
- *
- * The Hamming Weight of a number is the total number of bits set in it.
- */
-
-unsigned int hweight32(unsigned int w)
-{
-       unsigned int res = w - ((w >> 1) & 0x55555555);
-       res = (res & 0x33333333) + ((res >> 2) & 0x33333333);
-       res = (res + (res >> 4)) & 0x0F0F0F0F;
-       res = res + (res >> 8);
-       return (res + (res >> 16)) & 0x000000FF;
-}
-
-unsigned long hweight64(__u64 w)
-{
-#if BITS_PER_LONG == 32
-       return hweight32((unsigned int)(w >> 32)) + hweight32((unsigned int)w);
-#elif BITS_PER_LONG == 64
-       __u64 res = w - ((w >> 1) & 0x5555555555555555ul);
-       res = (res & 0x3333333333333333ul) + ((res >> 2) & 0x3333333333333333ul);
-       res = (res + (res >> 4)) & 0x0F0F0F0F0F0F0F0Ful;
-       res = res + (res >> 8);
-       res = res + (res >> 16);
-       return (res + (res >> 32)) & 0x00000000000000FFul;
-#endif
-}
diff --git a/tools/perf/util/include/asm/hweight.h b/tools/perf/util/include/asm/hweight.h
deleted file mode 100644 (file)
index 36cf26d..0000000
+++ /dev/null
@@ -1,8 +0,0 @@
-#ifndef PERF_HWEIGHT_H
-#define PERF_HWEIGHT_H
-
-#include <linux/types.h>
-unsigned int hweight32(unsigned int w);
-unsigned long hweight64(__u64 w);
-
-#endif /* PERF_HWEIGHT_H */
index 94de3e48b4909a03a7e7037f779074e5bf31ff8a..1bca3a9f2b16bc91670f731e05564680d2f12a10 100644 (file)
@@ -389,7 +389,6 @@ static struct thread *__machine__findnew_thread(struct machine *machine,
        if (th != NULL) {
                rb_link_node(&th->rb_node, parent, p);
                rb_insert_color(&th->rb_node, &machine->threads);
-               machine->last_match = th;
 
                /*
                 * We have to initialize map_groups separately
@@ -400,9 +399,12 @@ static struct thread *__machine__findnew_thread(struct machine *machine,
                 * leader and that would screwed the rb tree.
                 */
                if (thread__init_map_groups(th, machine)) {
+                       rb_erase(&th->rb_node, &machine->threads);
                        thread__delete(th);
                        return NULL;
                }
+
+               machine->last_match = th;
        }
 
        return th;
index 7f9b8632e4331bc2216b29dd15374cac69e83d96..94a717bf007de77658032dcb03dcc6db818b451b 100644 (file)
@@ -2052,9 +2052,11 @@ static int write_probe_trace_event(int fd, struct probe_trace_event *tev)
        pr_debug("Writing event: %s\n", buf);
        if (!probe_event_dry_run) {
                ret = write(fd, buf, strlen(buf));
-               if (ret <= 0)
+               if (ret <= 0) {
+                       ret = -errno;
                        pr_warning("Failed to write event: %s\n",
                                   strerror_r(errno, sbuf, sizeof(sbuf)));
+               }
        }
        free(buf);
        return ret;
index 16a475a7d492177623062143434488116cdf2a38..6c6a6953fa93fa5b4fe92229df7613bbe996bec9 100644 (file)
@@ -10,7 +10,7 @@ util/ctype.c
 util/evlist.c
 util/evsel.c
 util/cpumap.c
-util/hweight.c
+../../lib/hweight.c
 util/thread_map.c
 util/util.c
 util/xyarray.c
index 371219a6daf1cd8209687115bca9a67f7ffc3209..6edf535f65c23428b4982fb651ba3df997d55dfb 100644 (file)
@@ -185,6 +185,28 @@ static u64 elf_section_offset(int fd, const char *name)
        return offset;
 }
 
+#ifndef NO_LIBUNWIND_DEBUG_FRAME
+static int elf_is_exec(int fd, const char *name)
+{
+       Elf *elf;
+       GElf_Ehdr ehdr;
+       int retval = 0;
+
+       elf = elf_begin(fd, PERF_ELF_C_READ_MMAP, NULL);
+       if (elf == NULL)
+               return 0;
+       if (gelf_getehdr(elf, &ehdr) == NULL)
+               goto out;
+
+       retval = (ehdr.e_type == ET_EXEC);
+
+out:
+       elf_end(elf);
+       pr_debug("unwind: elf_is_exec(%s): %d\n", name, retval);
+       return retval;
+}
+#endif
+
 struct table_entry {
        u32 start_ip_offset;
        u32 fde_offset;
@@ -322,8 +344,12 @@ find_proc_info(unw_addr_space_t as, unw_word_t ip, unw_proc_info_t *pi,
 #ifndef NO_LIBUNWIND_DEBUG_FRAME
        /* Check the .debug_frame section for unwinding info */
        if (!read_unwind_spec_debug_frame(map->dso, ui->machine, &segbase)) {
+               int fd = dso__data_fd(map->dso, ui->machine);
+               int is_exec = elf_is_exec(fd, map->dso->name);
+               unw_word_t base = is_exec ? 0 : map->start;
+
                memset(&di, 0, sizeof(di));
-               if (dwarf_find_debug_frame(0, &di, ip, 0, map->dso->name,
+               if (dwarf_find_debug_frame(0, &di, ip, base, map->dso->name,
                                           map->start, map->end))
                        return dwarf_search_unwind_table(as, ip, &di, pi,
                                                         need_unwind_info, arg);
index d273624c93a642544f8ba2b31d45cebbc505dc52..e238c9559caf9a7757d2d389e0bda57cd73229a8 100644 (file)
@@ -62,7 +62,7 @@ static int _check_execveat_fail(int fd, const char *path, int flags,
 }
 
 static int check_execveat_invoked_rc(int fd, const char *path, int flags,
-                                    int expected_rc)
+                                    int expected_rc, int expected_rc2)
 {
        int status;
        int rc;
@@ -98,9 +98,10 @@ static int check_execveat_invoked_rc(int fd, const char *path, int flags,
                        child, status);
                return 1;
        }
-       if (WEXITSTATUS(status) != expected_rc) {
-               printf("[FAIL] (child %d exited with %d not %d)\n",
-                       child, WEXITSTATUS(status), expected_rc);
+       if ((WEXITSTATUS(status) != expected_rc) &&
+           (WEXITSTATUS(status) != expected_rc2)) {
+               printf("[FAIL] (child %d exited with %d not %d nor %d)\n",
+                       child, WEXITSTATUS(status), expected_rc, expected_rc2);
                return 1;
        }
        printf("[OK]\n");
@@ -109,7 +110,7 @@ static int check_execveat_invoked_rc(int fd, const char *path, int flags,
 
 static int check_execveat(int fd, const char *path, int flags)
 {
-       return check_execveat_invoked_rc(fd, path, flags, 99);
+       return check_execveat_invoked_rc(fd, path, flags, 99, 99);
 }
 
 static char *concat(const char *left, const char *right)
@@ -192,9 +193,15 @@ static int check_execveat_pathmax(int dot_dfd, const char *src, int is_script)
         * Execute as a long pathname relative to ".".  If this is a script,
         * the interpreter will launch but fail to open the script because its
         * name ("/dev/fd/5/xxx....") is bigger than PATH_MAX.
+        *
+        * The failure code is usually 127 (POSIX: "If a command is not found,
+        * the exit status shall be 127."), but some systems give 126 (POSIX:
+        * "If the command name is found, but it is not an executable utility,
+        * the exit status shall be 126."), so allow either.
         */
        if (is_script)
-               fail += check_execveat_invoked_rc(dot_dfd, longpath, 0, 127);
+               fail += check_execveat_invoked_rc(dot_dfd, longpath, 0,
+                                                 127, 126);
        else
                fail += check_execveat(dot_dfd, longpath, 0);
 
index 94dae65eea4183b43bf3e52bf9bf22dc9c0d4471..8519e9ee97e3d3e4a344e798cabf5b38edfff602 100644 (file)
@@ -536,10 +536,9 @@ int main(int argc, char *argv[])
 {
        struct mq_attr attr;
        char *option, *next_option;
-       int i, cpu;
+       int i, cpu, rc;
        struct sigaction sa;
        poptContext popt_context;
-       char rc;
        void *retval;
 
        main_thread = pthread_self();
index 4c4b1f631ecf61f6e3048d746c23be39ea4f2ef9..077828c889f1377886b98c93349919d55ccb57a2 100644 (file)
@@ -7,7 +7,7 @@ BINARIES += transhuge-stress
 
 all: $(BINARIES)
 %: %.c
-       $(CC) $(CFLAGS) -o $@ $^
+       $(CC) $(CFLAGS) -o $@ $^ -lrt
 
 run_tests: all
        @/bin/sh ./run_vmtests || (echo "vmtests: [FAIL]"; exit 1)