aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorKarol Herbst <nouveau@karolherbst.de>2016-01-05 15:44:18 -0500
committerBen Skeggs <bskeggs@redhat.com>2016-01-10 20:30:20 -0500
commit5cca4bdc0d0518b31c7bf8f5e8a895af01c4c90a (patch)
treebecad663c7629018b82125fd9cec2a0127afcc34
parentbcc19d9bf5cd8d49428c487adced1aa101271b18 (diff)
drm/nouveau/pci: implement pcie speed change for tesla
v5: don't set fermi or kepler func pointers v6: fix alignment
-rw-r--r--drivers/gpu/drm/nouveau/nvkm/subdev/pci/g84.c92
-rw-r--r--drivers/gpu/drm/nouveau/nvkm/subdev/pci/g94.c18
-rw-r--r--drivers/gpu/drm/nouveau/nvkm/subdev/pci/priv.h10
3 files changed, 120 insertions, 0 deletions
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/pci/g84.c b/drivers/gpu/drm/nouveau/nvkm/subdev/pci/g84.c
index 3faa6bfb895b..62438d892f42 100644
--- a/drivers/gpu/drm/nouveau/nvkm/subdev/pci/g84.c
+++ b/drivers/gpu/drm/nouveau/nvkm/subdev/pci/g84.c
@@ -25,6 +25,80 @@
25 25
26#include <core/pci.h> 26#include <core/pci.h>
27 27
28static int
29g84_pcie_version_supported(struct nvkm_pci *pci)
30{
31 /* g84 and g86 report wrong information about what they support */
32 return 1;
33}
34
35int
36g84_pcie_version(struct nvkm_pci *pci)
37{
38 struct nvkm_device *device = pci->subdev.device;
39 return (nvkm_rd32(device, 0x00154c) & 0x1) + 1;
40}
41
42void
43g84_pcie_set_version(struct nvkm_pci *pci, u8 ver)
44{
45 struct nvkm_device *device = pci->subdev.device;
46 nvkm_mask(device, 0x00154c, 0x1, (ver >= 2 ? 0x1 : 0x0));
47}
48
49static void
50g84_pcie_set_cap_speed(struct nvkm_pci *pci, bool full_speed)
51{
52 struct nvkm_device *device = pci->subdev.device;
53 nvkm_mask(device, 0x00154c, 0x80, full_speed ? 0x80 : 0x0);
54}
55
56enum nvkm_pcie_speed
57g84_pcie_cur_speed(struct nvkm_pci *pci)
58{
59 u32 reg_v = nvkm_pci_rd32(pci, 0x88) & 0x30000;
60 switch (reg_v) {
61 case 0x30000:
62 return NVKM_PCIE_SPEED_8_0;
63 case 0x20000:
64 return NVKM_PCIE_SPEED_5_0;
65 case 0x10000:
66 default:
67 return NVKM_PCIE_SPEED_2_5;
68 }
69}
70
71enum nvkm_pcie_speed
72g84_pcie_max_speed(struct nvkm_pci *pci)
73{
74 u32 reg_v = nvkm_pci_rd32(pci, 0x460) & 0x3300;
75 if (reg_v == 0x2200)
76 return NVKM_PCIE_SPEED_5_0;
77 return NVKM_PCIE_SPEED_2_5;
78}
79
80void
81g84_pcie_set_link_speed(struct nvkm_pci *pci, enum nvkm_pcie_speed speed)
82{
83 u32 mask_value;
84
85 if (speed == NVKM_PCIE_SPEED_5_0)
86 mask_value = 0x20;
87 else
88 mask_value = 0x10;
89
90 nvkm_pci_mask(pci, 0x460, 0x30, mask_value);
91 nvkm_pci_mask(pci, 0x460, 0x1, 0x1);
92}
93
94int
95g84_pcie_set_link(struct nvkm_pci *pci, enum nvkm_pcie_speed speed, u8 width)
96{
97 g84_pcie_set_cap_speed(pci, speed == NVKM_PCIE_SPEED_5_0);
98 g84_pcie_set_link_speed(pci, speed);
99 return 0;
100}
101
28void 102void
29g84_pci_init(struct nvkm_pci *pci) 103g84_pci_init(struct nvkm_pci *pci)
30{ 104{
@@ -48,6 +122,14 @@ g84_pci_init(struct nvkm_pci *pci)
48 nvkm_pci_mask(pci, 0x041c, 0x00000060, 0x00000000); 122 nvkm_pci_mask(pci, 0x041c, 0x00000060, 0x00000000);
49} 123}
50 124
125int
126g84_pcie_init(struct nvkm_pci *pci)
127{
128 bool full_speed = g84_pcie_cur_speed(pci) == NVKM_PCIE_SPEED_5_0;
129 g84_pcie_set_cap_speed(pci, full_speed);
130 return 0;
131}
132
51static const struct nvkm_pci_func 133static const struct nvkm_pci_func
52g84_pci_func = { 134g84_pci_func = {
53 .init = g84_pci_init, 135 .init = g84_pci_init,
@@ -55,6 +137,16 @@ g84_pci_func = {
55 .wr08 = nv40_pci_wr08, 137 .wr08 = nv40_pci_wr08,
56 .wr32 = nv40_pci_wr32, 138 .wr32 = nv40_pci_wr32,
57 .msi_rearm = nv46_pci_msi_rearm, 139 .msi_rearm = nv46_pci_msi_rearm,
140
141 .pcie.init = g84_pcie_init,
142 .pcie.set_link = g84_pcie_set_link,
143
144 .pcie.max_speed = g84_pcie_max_speed,
145 .pcie.cur_speed = g84_pcie_cur_speed,
146
147 .pcie.set_version = g84_pcie_set_version,
148 .pcie.version = g84_pcie_version,
149 .pcie.version_supported = g84_pcie_version_supported,
58}; 150};
59 151
60int 152int
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/pci/g94.c b/drivers/gpu/drm/nouveau/nvkm/subdev/pci/g94.c
index cd311ee311cc..43444123bc04 100644
--- a/drivers/gpu/drm/nouveau/nvkm/subdev/pci/g94.c
+++ b/drivers/gpu/drm/nouveau/nvkm/subdev/pci/g94.c
@@ -23,6 +23,14 @@
23 */ 23 */
24#include "priv.h" 24#include "priv.h"
25 25
26int
27g94_pcie_version_supported(struct nvkm_pci *pci)
28{
29 if ((nvkm_pci_rd32(pci, 0x460) & 0x200) == 0x200)
30 return 2;
31 return 1;
32}
33
26static const struct nvkm_pci_func 34static const struct nvkm_pci_func
27g94_pci_func = { 35g94_pci_func = {
28 .init = g84_pci_init, 36 .init = g84_pci_init,
@@ -30,6 +38,16 @@ g94_pci_func = {
30 .wr08 = nv40_pci_wr08, 38 .wr08 = nv40_pci_wr08,
31 .wr32 = nv40_pci_wr32, 39 .wr32 = nv40_pci_wr32,
32 .msi_rearm = nv40_pci_msi_rearm, 40 .msi_rearm = nv40_pci_msi_rearm,
41
42 .pcie.init = g84_pcie_init,
43 .pcie.set_link = g84_pcie_set_link,
44
45 .pcie.max_speed = g84_pcie_max_speed,
46 .pcie.cur_speed = g84_pcie_cur_speed,
47
48 .pcie.set_version = g84_pcie_set_version,
49 .pcie.version = g84_pcie_version,
50 .pcie.version_supported = g94_pcie_version_supported,
33}; 51};
34 52
35int 53int
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/pci/priv.h b/drivers/gpu/drm/nouveau/nvkm/subdev/pci/priv.h
index 79eb9795dda1..8c389a61d5a1 100644
--- a/drivers/gpu/drm/nouveau/nvkm/subdev/pci/priv.h
+++ b/drivers/gpu/drm/nouveau/nvkm/subdev/pci/priv.h
@@ -36,6 +36,16 @@ void nv46_pci_msi_rearm(struct nvkm_pci *);
36void g84_pci_init(struct nvkm_pci *pci); 36void g84_pci_init(struct nvkm_pci *pci);
37 37
38/* pcie functions */ 38/* pcie functions */
39void g84_pcie_set_version(struct nvkm_pci *, u8);
40int g84_pcie_version(struct nvkm_pci *);
41void g84_pcie_set_link_speed(struct nvkm_pci *, enum nvkm_pcie_speed);
42enum nvkm_pcie_speed g84_pcie_cur_speed(struct nvkm_pci *);
43enum nvkm_pcie_speed g84_pcie_max_speed(struct nvkm_pci *);
44int g84_pcie_init(struct nvkm_pci *);
45int g84_pcie_set_link(struct nvkm_pci *, enum nvkm_pcie_speed, u8);
46
47int g94_pcie_version_supported(struct nvkm_pci *);
48
39int nvkm_pcie_oneinit(struct nvkm_pci *); 49int nvkm_pcie_oneinit(struct nvkm_pci *);
40int nvkm_pcie_init(struct nvkm_pci *); 50int nvkm_pcie_init(struct nvkm_pci *);
41#endif 51#endif