drm/nouveau/devinit: move simple pll setting routines to devinit
authorBen Skeggs <bskeggs@redhat.com>
Tue, 5 Mar 2013 00:53:54 +0000 (10:53 +1000)
committerBen Skeggs <bskeggs@redhat.com>
Mon, 1 Jul 2013 03:43:54 +0000 (13:43 +1000)
These are pretty much useless for reclocking purposes.  Lets make it
clearer what they're for and move them to DEVINIT to signify they're
for the very simple PLL setting requirements of running the init
tables.

Signed-off-by: Ben Skeggs <bskeggs@redhat.com>
24 files changed:
drivers/gpu/drm/nouveau/Makefile
drivers/gpu/drm/nouveau/core/engine/device/nv50.c
drivers/gpu/drm/nouveau/core/engine/device/nvc0.c
drivers/gpu/drm/nouveau/core/engine/device/nve0.c
drivers/gpu/drm/nouveau/core/engine/disp/nv50.c
drivers/gpu/drm/nouveau/core/engine/disp/nvd0.c
drivers/gpu/drm/nouveau/core/include/subdev/clock.h
drivers/gpu/drm/nouveau/core/include/subdev/devinit.h
drivers/gpu/drm/nouveau/core/subdev/bios/init.c
drivers/gpu/drm/nouveau/core/subdev/clock/nv04.c
drivers/gpu/drm/nouveau/core/subdev/clock/nv40.c
drivers/gpu/drm/nouveau/core/subdev/clock/nv50.c
drivers/gpu/drm/nouveau/core/subdev/clock/nva3.c
drivers/gpu/drm/nouveau/core/subdev/clock/nvc0.c
drivers/gpu/drm/nouveau/core/subdev/devinit/base.c
drivers/gpu/drm/nouveau/core/subdev/devinit/nv04.c
drivers/gpu/drm/nouveau/core/subdev/devinit/nv05.c
drivers/gpu/drm/nouveau/core/subdev/devinit/nv10.c
drivers/gpu/drm/nouveau/core/subdev/devinit/nv1a.c
drivers/gpu/drm/nouveau/core/subdev/devinit/nv20.c
drivers/gpu/drm/nouveau/core/subdev/devinit/nv50.c
drivers/gpu/drm/nouveau/core/subdev/devinit/nva3.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/core/subdev/devinit/nvc0.c [new file with mode: 0644]
drivers/gpu/drm/nouveau/core/subdev/devinit/priv.h [new file with mode: 0644]

index 998e8b4444f35e90d7b863dbf5167efb0e0f94f8..f689d31e71fac13b0dd786972ba385765d73de49 100644 (file)
@@ -60,6 +60,8 @@ 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/nva3.o
+nouveau-y += core/subdev/devinit/nvc0.o
 nouveau-y += core/subdev/fb/base.o
 nouveau-y += core/subdev/fb/nv04.o
 nouveau-y += core/subdev/fb/nv10.o
index 5e8c3de75593d04390f4e95964363d86ffb1551d..5c1db3e1f0f29aa0978206898ff42d3f22cad5bb 100644 (file)
@@ -319,7 +319,7 @@ nv50_identify(struct nouveau_device *device)
                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] = &nv50_devinit_oclass;
+               device->oclass[NVDEV_SUBDEV_DEVINIT] = &nva3_devinit_oclass;
                device->oclass[NVDEV_SUBDEV_MC     ] = &nv98_mc_oclass;
                device->oclass[NVDEV_SUBDEV_BUS    ] = &nv50_bus_oclass;
                device->oclass[NVDEV_SUBDEV_TIMER  ] = &nv04_timer_oclass;
@@ -346,7 +346,7 @@ nv50_identify(struct nouveau_device *device)
                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] = &nv50_devinit_oclass;
+               device->oclass[NVDEV_SUBDEV_DEVINIT] = &nva3_devinit_oclass;
                device->oclass[NVDEV_SUBDEV_MC     ] = &nv98_mc_oclass;
                device->oclass[NVDEV_SUBDEV_BUS    ] = &nv50_bus_oclass;
                device->oclass[NVDEV_SUBDEV_TIMER  ] = &nv04_timer_oclass;
@@ -372,7 +372,7 @@ nv50_identify(struct nouveau_device *device)
                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] = &nv50_devinit_oclass;
+               device->oclass[NVDEV_SUBDEV_DEVINIT] = &nva3_devinit_oclass;
                device->oclass[NVDEV_SUBDEV_MC     ] = &nv98_mc_oclass;
                device->oclass[NVDEV_SUBDEV_BUS    ] = &nv50_bus_oclass;
                device->oclass[NVDEV_SUBDEV_TIMER  ] = &nv04_timer_oclass;
@@ -398,7 +398,7 @@ nv50_identify(struct nouveau_device *device)
                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] = &nv50_devinit_oclass;
+               device->oclass[NVDEV_SUBDEV_DEVINIT] = &nva3_devinit_oclass;
                device->oclass[NVDEV_SUBDEV_MC     ] = &nv98_mc_oclass;
                device->oclass[NVDEV_SUBDEV_BUS    ] = &nv50_bus_oclass;
                device->oclass[NVDEV_SUBDEV_TIMER  ] = &nv04_timer_oclass;
index a36e64e98ef372a91566da1d6fb0fff6ebef400f..1df3578a531507f79000d34501f58ab256b756ee 100644 (file)
@@ -62,7 +62,7 @@ nvc0_identify(struct nouveau_device *device)
                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] = &nv50_devinit_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;
@@ -91,7 +91,7 @@ nvc0_identify(struct nouveau_device *device)
                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] = &nv50_devinit_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;
@@ -120,7 +120,7 @@ nvc0_identify(struct nouveau_device *device)
                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] = &nv50_devinit_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;
@@ -148,7 +148,7 @@ nvc0_identify(struct nouveau_device *device)
                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] = &nv50_devinit_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;
@@ -177,7 +177,7 @@ nvc0_identify(struct nouveau_device *device)
                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] = &nv50_devinit_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;
@@ -206,7 +206,7 @@ nvc0_identify(struct nouveau_device *device)
                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] = &nv50_devinit_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;
@@ -234,7 +234,7 @@ nvc0_identify(struct nouveau_device *device)
                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] = &nv50_devinit_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;
@@ -263,7 +263,7 @@ nvc0_identify(struct nouveau_device *device)
                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] = &nv50_devinit_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;
index 8a84d528057d45314b8867f5ac820088621386e6..4e6ef62e88c88be57734ba66b915f90eecf64eb0 100644 (file)
@@ -62,7 +62,7 @@ nve0_identify(struct nouveau_device *device)
                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] = &nv50_devinit_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;
@@ -92,7 +92,7 @@ nve0_identify(struct nouveau_device *device)
                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] = &nv50_devinit_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;
@@ -122,7 +122,7 @@ nve0_identify(struct nouveau_device *device)
                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] = &nv50_devinit_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;
@@ -152,7 +152,7 @@ nve0_identify(struct nouveau_device *device)
                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] = &nv50_devinit_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;
index 6a38402fa56c95cd01a98ba89d01e71dccf92fb3..8b42f45c2b1d5accb03f992371fab5c65af785fe 100644 (file)
@@ -34,9 +34,9 @@
 #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 <subdev/clock.h>
 
 #include "nv50.h"
 
@@ -987,10 +987,10 @@ nv50_disp_intr_unk20_0(struct nv50_disp_priv *priv, int head)
 static void
 nv50_disp_intr_unk20_1(struct nv50_disp_priv *priv, int head)
 {
-       struct nouveau_clock *clk = nouveau_clock(priv);
+       struct nouveau_devinit *devinit = nouveau_devinit(priv);
        u32 pclk = nv_rd32(priv, 0x610ad0 + (head * 0x540)) & 0x3fffff;
        if (pclk)
-               clk->pll_set(clk, PLL_VPLL0 + head, pclk);
+               devinit->pll_set(devinit, PLL_VPLL0 + head, pclk);
 }
 
 static void
index 019eacd8a68fad2d7d36f4eb80584a25b3badbdf..3ed10b00e81cbaba22fa79bb44cf7096b65eeeeb 100644 (file)
 
 #include <engine/disp.h>
 
-#include <subdev/timer.h>
-#include <subdev/fb.h>
-#include <subdev/clock.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"
 
@@ -738,10 +737,10 @@ nvd0_disp_intr_unk2_0(struct nv50_disp_priv *priv, int head)
 static void
 nvd0_disp_intr_unk2_1(struct nv50_disp_priv *priv, int head)
 {
-       struct nouveau_clock *clk = nouveau_clock(priv);
+       struct nouveau_devinit *devinit = nouveau_devinit(priv);
        u32 pclk = nv_rd32(priv, 0x660450 + (head * 0x300)) / 1000;
        if (pclk)
-               clk->pll_set(clk, PLL_VPLL0 + head, pclk);
+               devinit->pll_set(devinit, PLL_VPLL0 + head, pclk);
        nv_wr32(priv, 0x612200 + (head * 0x800), 0x00000000);
 }
 
index 41b7a6a76f1981ae3427278bacaf8d2c99edbe09..89ee289097a6533a66ea50a85c298d4163378d8c 100644 (file)
@@ -10,8 +10,6 @@ struct nvbios_pll;
 struct nouveau_clock {
        struct nouveau_subdev base;
 
-       int (*pll_set)(struct nouveau_clock *, u32 type, u32 freq);
-
        /*XXX: die, these are here *only* to support the completely
         *     bat-shit insane what-was-nouveau_hw.c code
         */
index 29e4cc1f6cc0dd7f6e2688cdb125fc1f11601558..685c9b12ee4cff48a682f373b7dbd94d5ea0bb24 100644 (file)
@@ -8,6 +8,8 @@ struct nouveau_devinit {
        struct nouveau_subdev base;
        bool post;
        void (*meminit)(struct nouveau_devinit *);
+       int  (*pll_set)(struct nouveau_devinit *, u32 type, u32 freq);
+
 };
 
 static inline struct nouveau_devinit *
@@ -20,11 +22,20 @@ nouveau_devinit(void *obj)
        nouveau_devinit_create_((p), (e), (o), sizeof(**d), (void **)d)
 #define nouveau_devinit_destroy(p)                                             \
        nouveau_subdev_destroy(&(p)->base)
+#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 **);
-int nouveau_devinit_init(struct nouveau_devinit *);
-int nouveau_devinit_fini(struct nouveau_devinit *, bool suspend);
+#define _nouveau_devinit_dtor _nouveau_subdev_dtor
+int _nouveau_devinit_init(struct nouveau_object *);
+int _nouveau_devinit_fini(struct nouveau_object *, bool suspend);
 
 extern struct nouveau_oclass nv04_devinit_oclass;
 extern struct nouveau_oclass nv05_devinit_oclass;
@@ -32,9 +43,7 @@ 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;
-
-void nv04_devinit_dtor(struct nouveau_object *);
-int  nv04_devinit_init(struct nouveau_object *);
-int  nv04_devinit_fini(struct nouveau_object *, bool);
+extern struct nouveau_oclass nva3_devinit_oclass;
+extern struct nouveau_oclass nvc0_devinit_oclass;
 
 #endif
index c434d398d16f0302bec862c95b6421cb8e505652..0687e6481438bb2c6fdec16467dc949574ee3402 100644 (file)
@@ -10,7 +10,6 @@
 #include <subdev/bios/gpio.h>
 #include <subdev/bios/init.h>
 #include <subdev/devinit.h>
-#include <subdev/clock.h>
 #include <subdev/i2c.h>
 #include <subdev/vga.h>
 #include <subdev/gpio.h>
@@ -300,9 +299,9 @@ init_wrauxr(struct nvbios_init *init, u32 addr, u8 data)
 static void
 init_prog_pll(struct nvbios_init *init, u32 id, u32 freq)
 {
-       struct nouveau_clock *clk = nouveau_clock(init->bios);
-       if (clk && clk->pll_set && init_exec(init)) {
-               int ret = clk->pll_set(clk, id, 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);
        }
index 3c2fb68255a8baa35cee7b80d23eeaa0eec400f5..a1427758659532babd63689c03584112e973b4c5 100644 (file)
  * Authors: Ben Skeggs
  */
 
-#include <subdev/clock.h>
 #include <subdev/bios.h>
 #include <subdev/bios/pll.h>
+#include <subdev/clock.h>
+#include <subdev/devinit/priv.h>
 
 #include "pll.h"
 
@@ -32,266 +33,6 @@ struct nv04_clock_priv {
        struct nouveau_clock base;
 };
 
-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;
-}
-
-static void
-setPLL_single(struct nv04_clock_priv *priv, u32 reg,
-             struct nouveau_pll_vals *pv)
-{
-       int chip_version = nouveau_bios(priv)->version.chip;
-       uint32_t oldpll = nv_rd32(priv, 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(priv, 0x001584);
-               nv_wr32(priv, 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(priv, reg, pv->log2P << 16 | (oldpll & 0xffff));
-       else
-               /* downclock -- write new NM first */
-               nv_wr32(priv, reg, (oldpll & 0xffff0000) | pv->NM1);
-
-       if (chip_version < 0x17 && chip_version != 0x11)
-               /* wait a bit on older chips */
-               msleep(64);
-       nv_rd32(priv, reg);
-
-       /* then write the other half as well */
-       nv_wr32(priv, reg, pll);
-
-       if (shift_powerctrl_1 >= 0)
-               nv_wr32(priv, 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;
-}
-
-static void
-setPLL_double_highregs(struct nv04_clock_priv *priv, u32 reg1,
-                      struct nouveau_pll_vals *pv)
-{
-       int chip_version = nouveau_bios(priv)->version.chip;
-       bool nv3035 = chip_version == 0x30 || chip_version == 0x35;
-       uint32_t reg2 = reg1 + ((reg1 == 0x680520) ? 0x5c : 0x70);
-       uint32_t oldpll1 = nv_rd32(priv, reg1);
-       uint32_t oldpll2 = !nv3035 ? nv_rd32(priv, 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(priv, 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(priv, 0x001584);
-               nv_wr32(priv, 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(priv, 0xc040);
-               if (shift_c040 != 14)
-                       nv_wr32(priv, 0xc040, savedc040 & ~(3 << shift_c040));
-       }
-
-       if (oldramdac580 != ramdac580)
-               nv_wr32(priv, 0x680580, ramdac580);
-
-       if (!nv3035)
-               nv_wr32(priv, reg2, pll2);
-       nv_wr32(priv, reg1, pll1);
-
-       if (shift_powerctrl_1 >= 0)
-               nv_wr32(priv, 0x001584, saved_powerctrl_1);
-       if (chip_version >= 0x40)
-               nv_wr32(priv, 0xc040, savedc040);
-}
-
-static void
-setPLL_double_lowregs(struct nv04_clock_priv *priv, 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(priv, 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(priv, 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(priv), 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(priv, 0x4600);
-               nv_wr32(priv, 0x4600, saved4600 | 8 << 28);
-       }
-       if (single_stage)
-               Pval |= mpll ? 1 << 12 : 1 << 8;
-
-       nv_wr32(priv, Preg, oldPval | 1 << 28);
-       nv_wr32(priv, Preg, Pval & ~(4 << 28));
-       if (mpll) {
-               Pval |= 8 << 20;
-               nv_wr32(priv, 0x4020, Pval & ~(0xc << 28));
-               nv_wr32(priv, 0x4038, Pval & ~(0xc << 28));
-       }
-
-       savedc040 = nv_rd32(priv, 0xc040);
-       nv_wr32(priv, 0xc040, savedc040 & maskc040);
-
-       nv_wr32(priv, NMNMreg, NMNM);
-       if (NMNMreg == 0x4024)
-               nv_wr32(priv, 0x403c, NMNM);
-
-       nv_wr32(priv, Preg, Pval);
-       if (mpll) {
-               Pval &= ~(8 << 20);
-               nv_wr32(priv, 0x4020, Pval);
-               nv_wr32(priv, 0x4038, Pval);
-               nv_wr32(priv, 0x4600, saved4600);
-       }
-
-       nv_wr32(priv, 0xc040, savedc040);
-
-       if (mpll) {
-               nv_wr32(priv, 0x4020, Pval & ~(1 << 28));
-               nv_wr32(priv, 0x4038, Pval & ~(1 << 28));
-       }
-}
-
-int
-nv04_clock_pll_set(struct nouveau_clock *clk, u32 type, u32 freq)
-{
-       struct nv04_clock_priv *priv = (void *)clk;
-       struct nouveau_pll_vals pv;
-       struct nvbios_pll info;
-       int ret;
-
-       ret = nvbios_pll_parse(nouveau_bios(priv), type > 0x405c ?
-                              type : type - 4, &info);
-       if (ret)
-               return ret;
-
-       ret = clk->pll_calc(clk, &info, freq, &pv);
-       if (!ret)
-               return ret;
-
-       return clk->pll_prog(clk, type, &pv);
-}
-
 int
 nv04_clock_pll_calc(struct nouveau_clock *clock, struct nvbios_pll *info,
                    int clk, struct nouveau_pll_vals *pv)
@@ -313,17 +54,17 @@ int
 nv04_clock_pll_prog(struct nouveau_clock *clk, u32 reg1,
                    struct nouveau_pll_vals *pv)
 {
-       struct nv04_clock_priv *priv = (void *)clk;
+       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(priv, reg1, pv);
+                       setPLL_double_highregs(devinit, reg1, pv);
                else
-                       setPLL_double_lowregs(priv, reg1, pv);
+                       setPLL_double_lowregs(devinit, reg1, pv);
        } else
-               setPLL_single(priv, reg1, pv);
+               setPLL_single(devinit, reg1, pv);
 
        return 0;
 }
@@ -341,7 +82,6 @@ nv04_clock_ctor(struct nouveau_object *parent, struct nouveau_object *engine,
        if (ret)
                return ret;
 
-       priv->base.pll_set = nv04_clock_pll_set;
        priv->base.pll_calc = nv04_clock_pll_calc;
        priv->base.pll_prog = nv04_clock_pll_prog;
        return 0;
index a4b2b7ebf9af6f48c3b44c50e11a5a07cbd99341..0db5dbfd91b5b0ef6cfb2209432ca92714fa7300 100644 (file)
@@ -41,7 +41,6 @@ nv40_clock_ctor(struct nouveau_object *parent, struct nouveau_object *engine,
        if (ret)
                return ret;
 
-       priv->base.pll_set = nv04_clock_pll_set;
        priv->base.pll_calc = nv04_clock_pll_calc;
        priv->base.pll_prog = nv04_clock_pll_prog;
        return 0;
index 5e9d5e283dc46e8250d0b2f7b5d6cf13beb7bff0..d09d3e78040c13630d3e0e677e05535c3cfd1c25 100644 (file)
@@ -32,50 +32,6 @@ struct nv50_clock_priv {
        struct nouveau_clock base;
 };
 
-static int
-nv50_clock_pll_set(struct nouveau_clock *clk, u32 type, u32 freq)
-{
-       struct nv50_clock_priv *priv = (void *)clk;
-       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(clk, "failed to retrieve pll data, %d\n", ret);
-               return ret;
-       }
-
-       ret = nv04_pll_calc(nv_subdev(clk), &info, freq, &N1, &M1, &N2, &M2, &P);
-       if (!ret) {
-               nv_error(clk, "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 int
 nv50_clock_ctor(struct nouveau_object *parent, struct nouveau_object *engine,
                struct nouveau_oclass *oclass, void *data, u32 size,
@@ -89,7 +45,6 @@ nv50_clock_ctor(struct nouveau_object *parent, struct nouveau_object *engine,
        if (ret)
                return ret;
 
-       priv->base.pll_set = nv50_clock_pll_set;
        priv->base.pll_calc = nv04_clock_pll_calc;
        return 0;
 }
index 2cedfd7020a045f5f29052cba5ec1a9add8d231d..f074cd20bc9c5f5e51c403f51f20b340609d832d 100644 (file)
@@ -32,40 +32,6 @@ struct nva3_clock_priv {
        struct nouveau_clock base;
 };
 
-static int
-nva3_clock_pll_set(struct nouveau_clock *clk, u32 type, u32 freq)
-{
-       struct nva3_clock_priv *priv = (void *)clk;
-       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(clk), &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;
-}
-
 int
 nva3_clock_pll_calc(struct nouveau_clock *clock, struct nvbios_pll *info,
                    int clk, struct nouveau_pll_vals *pv)
@@ -97,7 +63,6 @@ nva3_clock_ctor(struct nouveau_object *parent, struct nouveau_object *engine,
        if (ret)
                return ret;
 
-       priv->base.pll_set = nva3_clock_pll_set;
        priv->base.pll_calc = nva3_clock_pll_calc;
        return 0;
 }
index 495b21f2766208af229e93d93e929bf4b677bcf7..439d81c261309bda696d9e6e51a1e4b122c3b6c6 100644 (file)
@@ -32,41 +32,6 @@ struct nvc0_clock_priv {
        struct nouveau_clock base;
 };
 
-static int
-nvc0_clock_pll_set(struct nouveau_clock *clk, u32 type, u32 freq)
-{
-       struct nvc0_clock_priv *priv = (void *)clk;
-       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(clk), &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 int
 nvc0_clock_ctor(struct nouveau_object *parent, struct nouveau_object *engine,
                struct nouveau_oclass *oclass, void *data, u32 size,
@@ -80,7 +45,6 @@ nvc0_clock_ctor(struct nouveau_object *parent, struct nouveau_object *engine,
        if (ret)
                return ret;
 
-       priv->base.pll_set = nvc0_clock_pll_set;
        priv->base.pll_calc = nva3_clock_pll_calc;
        return 0;
 }
index 5a07a39c1735ce6129404b8bdddd40d5708ffbb2..79c81d3d9bacee32ec45f36dee8b73cee3ac2953 100644 (file)
 #include <subdev/bios/init.h>
 
 int
-nouveau_devinit_init(struct nouveau_devinit *devinit)
+_nouveau_devinit_fini(struct nouveau_object *object, bool suspend)
 {
-       int ret = nouveau_subdev_init(&devinit->base);
-       if (ret)
-               return ret;
+       struct nouveau_devinit *devinit = (void *)object;
 
-       return nvbios_init(&devinit->base, devinit->post);
-}
-
-int
-nouveau_devinit_fini(struct nouveau_devinit *devinit, bool suspend)
-{
        /* force full reinit on resume */
        if (suspend)
                devinit->post = true;
@@ -48,6 +40,17 @@ nouveau_devinit_fini(struct nouveau_devinit *devinit, bool suspend)
        return nouveau_subdev_fini(&devinit->base, suspend);
 }
 
+int
+_nouveau_devinit_init(struct nouveau_object *object)
+{
+       struct nouveau_devinit *devinit = (void *)object;
+       int ret = nouveau_subdev_init(&devinit->base);
+       if (ret)
+               return ret;
+
+       return nvbios_init(&devinit->base, devinit->post);
+}
+
 int
 nouveau_devinit_create_(struct nouveau_object *parent,
                        struct nouveau_object *engine,
index 7a72d9394340ab30e2479786e4298d1b1c2a978d..b22357d9b82185023b9ba93bb70a76ca6f99ae84 100644 (file)
  *
  */
 
-#include <subdev/devinit.h>
 #include <subdev/vga.h>
 
 #include "fbmem.h"
+#include "priv.h"
 
 struct nv04_devinit_priv {
        struct nouveau_devinit base;
@@ -111,33 +111,298 @@ nv04_devinit_meminit(struct nouveau_devinit *devinit)
 }
 
 static int
-nv04_devinit_ctor(struct nouveau_object *parent, struct nouveau_object *engine,
-                 struct nouveau_oclass *oclass, void *data, u32 size,
-                 struct nouveau_object **pobject)
+powerctrl_1_shift(int chip_version, int reg)
 {
-       struct nv04_devinit_priv *priv;
+       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 != 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 = nouveau_devinit_create(parent, engine, oclass, &priv);
-       *pobject = nv_object(priv);
+       ret = nvbios_pll_parse(bios, type > 0x405c ? type : type - 4, &info);
        if (ret)
                return ret;
 
-       priv->base.meminit = nv04_devinit_meminit;
-       priv->owner = -1;
+       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;
 }
 
-void
-nv04_devinit_dtor(struct nouveau_object *object)
+int
+nv04_devinit_fini(struct nouveau_object *object, bool suspend)
 {
        struct nv04_devinit_priv *priv = (void *)object;
 
-       /* restore vga owner saved at first init, and lock crtc regs  */
-       nv_wrvgaowner(priv, priv->owner);
-       nv_lockvgac(priv, true);
+       /* make i2c busses accessible */
+       nv_mask(priv, 0x000200, 0x00000001, 0x00000001);
 
-       nouveau_devinit_destroy(&priv->base);
+       /* unlock extended vga crtc regs, and unslave crtcs */
+       nv_lockvgac(priv, false);
+       if (priv->owner < 0)
+               priv->owner = nv_rdvgaowner(priv);
+       nv_wrvgaowner(priv, 0);
+
+       return nouveau_devinit_fini(&priv->base, suspend);
 }
 
 int
@@ -160,21 +425,35 @@ nv04_devinit_init(struct nouveau_object *object)
        return nouveau_devinit_init(&priv->base);
 }
 
-int
-nv04_devinit_fini(struct nouveau_object *object, bool suspend)
+void
+nv04_devinit_dtor(struct nouveau_object *object)
 {
        struct nv04_devinit_priv *priv = (void *)object;
 
-       /* make i2c busses accessible */
-       nv_mask(priv, 0x000200, 0x00000001, 0x00000001);
+       /* restore vga owner saved at first init, and lock crtc regs  */
+       nv_wrvgaowner(priv, priv->owner);
+       nv_lockvgac(priv, true);
 
-       /* unlock extended vga crtc regs, and unslave crtcs */
-       nv_lockvgac(priv, false);
-       if (priv->owner < 0)
-               priv->owner = nv_rdvgaowner(priv);
-       nv_wrvgaowner(priv, 0);
+       nouveau_devinit_destroy(&priv->base);
+}
 
-       return nouveau_devinit_fini(&priv->base, suspend);
+static 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->base.meminit = nv04_devinit_meminit;
+       priv->base.pll_set = nv04_devinit_pll_set;
+       priv->owner = -1;
+       return 0;
 }
 
 struct nouveau_oclass
index 191447d0d252814424f79c986831e36854040659..b1912a8a8942129b6292323faed5aa11475bfe3e 100644 (file)
  *
  */
 
-#include <subdev/devinit.h>
 #include <subdev/bios.h>
 #include <subdev/bios/bmp.h>
 #include <subdev/vga.h>
 
 #include "fbmem.h"
+#include "priv.h"
 
 struct nv05_devinit_priv {
        struct nouveau_devinit base;
@@ -144,6 +144,7 @@ nv05_devinit_ctor(struct nouveau_object *parent, struct nouveau_object *engine,
                return ret;
 
        priv->base.meminit = nv05_devinit_meminit;
+       priv->base.pll_set = nv04_devinit_pll_set;
        return 0;
 }
 
index eb76ffab6b0cef6960244f646bb979ef57f7d864..463b08fa09688e69da4f5e3ea640412b151c222a 100644 (file)
  *
  */
 
-#include <subdev/devinit.h>
 #include <subdev/vga.h>
 
 #include "fbmem.h"
+#include "priv.h"
 
 struct nv10_devinit_priv {
        struct nouveau_devinit base;
@@ -109,6 +109,7 @@ nv10_devinit_ctor(struct nouveau_object *parent, struct nouveau_object *engine,
                return ret;
 
        priv->base.meminit = nv10_devinit_meminit;
+       priv->base.pll_set = nv04_devinit_pll_set;
        return 0;
 }
 
index 5b2ba630d9134841cd1669e90f20118f62a6f23b..e9743cdabe757df66b92509f295d9c800a6ae919 100644 (file)
@@ -22,8 +22,7 @@
  * Authors: Ben Skeggs
  */
 
-#include <subdev/devinit.h>
-#include <subdev/vga.h>
+#include "priv.h"
 
 struct nv1a_devinit_priv {
        struct nouveau_devinit base;
@@ -43,6 +42,7 @@ nv1a_devinit_ctor(struct nouveau_object *parent, struct nouveau_object *engine,
        if (ret)
                return ret;
 
+       priv->base.pll_set = nv04_devinit_pll_set;
        return 0;
 }
 
index eb32e99005e49a2551fc9e6b9c6ad75e171611a3..6cc6080d3bc01e4e9e461bb5c323f82e48a60908 100644 (file)
@@ -24,9 +24,7 @@
  *
  */
 
-#include <subdev/devinit.h>
-#include <subdev/vga.h>
-
+#include "priv.h"
 #include "fbmem.h"
 
 struct nv20_devinit_priv {
@@ -81,6 +79,7 @@ nv20_devinit_ctor(struct nouveau_object *parent, struct nouveau_object *engine,
                return ret;
 
        priv->base.meminit = nv20_devinit_meminit;
+       priv->base.pll_set = nv04_devinit_pll_set;
        return 0;
 }
 
index 4a85778384172292202cc115f92c9a50132e5c26..6df72247c477b5a7c96214fe28a0d7a40be82696 100644 (file)
@@ -1,5 +1,5 @@
 /*
- * Copyright 2012 Red Hat Inc.
+ * 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"),
 #include <subdev/bios/dcb.h>
 #include <subdev/bios/disp.h>
 #include <subdev/bios/init.h>
-#include <subdev/devinit.h>
 #include <subdev/vga.h>
 
-struct nv50_devinit_priv {
-       struct nouveau_devinit base;
-};
+#include "priv.h"
 
 static int
-nv50_devinit_ctor(struct nouveau_object *parent, struct nouveau_object *engine,
-                 struct nouveau_oclass *oclass, void *data, u32 size,
-                 struct nouveau_object **pobject)
+nv50_devinit_pll_set(struct nouveau_devinit *devinit, u32 type, u32 freq)
 {
-       struct nv50_devinit_priv *priv;
+       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 = nouveau_devinit_create(parent, engine, oclass, &priv);
-       *pobject = nv_object(priv);
-       if (ret)
+       ret = nvbios_pll_parse(bios, type, &info);
+       if (ret) {
+               nv_error(devinit, "failed to retrieve pll data, %d\n", ret);
                return ret;
+       }
 
-       return 0;
-}
+       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;
+       }
 
-static void
-nv50_devinit_dtor(struct nouveau_object *object)
-{
-       struct nv50_devinit_priv *priv = (void *)object;
-       nouveau_devinit_destroy(&priv->base);
+       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 int
+int
 nv50_devinit_init(struct nouveau_object *object)
 {
        struct nouveau_bios *bios = nouveau_bios(object);
@@ -103,10 +121,20 @@ nv50_devinit_init(struct nouveau_object *object)
 }
 
 static int
-nv50_devinit_fini(struct nouveau_object *object, bool suspend)
+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 = (void *)object;
-       return nouveau_devinit_fini(&priv->base, suspend);
+       struct nv50_devinit_priv *priv;
+       int ret;
+
+       ret = nouveau_devinit_create(parent, engine, oclass, &priv);
+       *pobject = nv_object(priv);
+       if (ret)
+               return ret;
+
+       priv->base.pll_set = nv50_devinit_pll_set;
+       return 0;
 }
 
 struct nouveau_oclass
@@ -114,8 +142,8 @@ nv50_devinit_oclass = {
        .handle = NV_SUBDEV(DEVINIT, 0x50),
        .ofuncs = &(struct nouveau_ofuncs) {
                .ctor = nv50_devinit_ctor,
-               .dtor = nv50_devinit_dtor,
+               .dtor = _nouveau_devinit_dtor,
                .init = nv50_devinit_init,
-               .fini = nv50_devinit_fini,
+               .fini = _nouveau_devinit_fini,
        },
 };
diff --git a/drivers/gpu/drm/nouveau/core/subdev/devinit/nva3.c b/drivers/gpu/drm/nouveau/core/subdev/devinit/nva3.c
new file mode 100644 (file)
index 0000000..76a68b2
--- /dev/null
@@ -0,0 +1,87 @@
+/*
+ * 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
+nva3_devinit_pll_set(struct nouveau_devinit *devinit, u32 type, u32 freq)
+{
+       struct nva3_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 int
+nva3_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;
+
+       priv->base.pll_set = nva3_devinit_pll_set;
+       return 0;
+}
+
+struct nouveau_oclass
+nva3_devinit_oclass = {
+       .handle = NV_SUBDEV(DEVINIT, 0xa3),
+       .ofuncs = &(struct nouveau_ofuncs) {
+               .ctor = nva3_devinit_ctor,
+               .dtor = _nouveau_devinit_dtor,
+               .init = nv50_devinit_init,
+               .fini = _nouveau_devinit_fini,
+       },
+};
diff --git a/drivers/gpu/drm/nouveau/core/subdev/devinit/nvc0.c b/drivers/gpu/drm/nouveau/core/subdev/devinit/nvc0.c
new file mode 100644 (file)
index 0000000..dd78efb
--- /dev/null
@@ -0,0 +1,88 @@
+/*
+ * 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
+nvc0_devinit_pll_set(struct nouveau_devinit *devinit, u32 type, u32 freq)
+{
+       struct nvc0_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 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;
+
+       priv->base.pll_set = nvc0_devinit_pll_set;
+       return 0;
+}
+
+struct nouveau_oclass
+nvc0_devinit_oclass = {
+       .handle = NV_SUBDEV(DEVINIT, 0xa3),
+       .ofuncs = &(struct nouveau_ofuncs) {
+               .ctor = nvc0_devinit_ctor,
+               .dtor = _nouveau_devinit_dtor,
+               .init = nv50_devinit_init,
+               .fini = _nouveau_devinit_fini,
+       },
+};
diff --git a/drivers/gpu/drm/nouveau/core/subdev/devinit/priv.h b/drivers/gpu/drm/nouveau/core/subdev/devinit/priv.h
new file mode 100644 (file)
index 0000000..7d622e2
--- /dev/null
@@ -0,0 +1,25 @@
+#ifndef __NVKM_DEVINIT_PRIV_H__
+#define __NVKM_DEVINIT_PRIV_H__
+
+#include <subdev/bios.h>
+#include <subdev/bios/pll.h>
+#include <subdev/clock/pll.h>
+#include <subdev/devinit.h>
+
+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 *);
+
+
+struct nv50_devinit_priv {
+       struct nouveau_devinit base;
+};
+
+int  nv50_devinit_init(struct nouveau_object *);
+
+#endif