diff options
-rw-r--r-- | drivers/gpu/drm/radeon/radeon_clocks.c | 81 |
1 files changed, 81 insertions, 0 deletions
diff --git a/drivers/gpu/drm/radeon/radeon_clocks.c b/drivers/gpu/drm/radeon/radeon_clocks.c index f64936cc4dd9..14448a740ba6 100644 --- a/drivers/gpu/drm/radeon/radeon_clocks.c +++ b/drivers/gpu/drm/radeon/radeon_clocks.c | |||
@@ -91,6 +91,85 @@ uint32_t radeon_legacy_get_memory_clock(struct radeon_device *rdev) | |||
91 | return mclk; | 91 | return mclk; |
92 | } | 92 | } |
93 | 93 | ||
94 | #ifdef CONFIG_OF | ||
95 | /* | ||
96 | * Read XTAL (ref clock), SCLK and MCLK from Open Firmware device | ||
97 | * tree. Hopefully, ATI OF driver is kind enough to fill these | ||
98 | */ | ||
99 | static bool __devinit radeon_read_clocks_OF(struct drm_device *dev) | ||
100 | { | ||
101 | struct radeon_device *rdev = dev->dev_private; | ||
102 | struct device_node *dp = rdev->pdev->dev.of_node; | ||
103 | const u32 *val; | ||
104 | struct radeon_pll *p1pll = &rdev->clock.p1pll; | ||
105 | struct radeon_pll *p2pll = &rdev->clock.p2pll; | ||
106 | struct radeon_pll *spll = &rdev->clock.spll; | ||
107 | struct radeon_pll *mpll = &rdev->clock.mpll; | ||
108 | |||
109 | if (dp == NULL) | ||
110 | return false; | ||
111 | val = of_get_property(dp, "ATY,RefCLK", NULL); | ||
112 | if (!val || !*val) { | ||
113 | printk(KERN_WARNING "radeonfb: No ATY,RefCLK property !\n"); | ||
114 | return false; | ||
115 | } | ||
116 | p1pll->reference_freq = p2pll->reference_freq = (*val) / 10; | ||
117 | p1pll->reference_div = RREG32_PLL(RADEON_PPLL_REF_DIV) & 0x3ff; | ||
118 | if (p1pll->reference_div < 2) | ||
119 | p1pll->reference_div = 12; | ||
120 | p2pll->reference_div = p1pll->reference_div; | ||
121 | |||
122 | /* These aren't in the device-tree */ | ||
123 | if (rdev->family >= CHIP_R420) { | ||
124 | p1pll->pll_in_min = 100; | ||
125 | p1pll->pll_in_max = 1350; | ||
126 | p1pll->pll_out_min = 20000; | ||
127 | p1pll->pll_out_max = 50000; | ||
128 | p2pll->pll_in_min = 100; | ||
129 | p2pll->pll_in_max = 1350; | ||
130 | p2pll->pll_out_min = 20000; | ||
131 | p2pll->pll_out_max = 50000; | ||
132 | } else { | ||
133 | p1pll->pll_in_min = 40; | ||
134 | p1pll->pll_in_max = 500; | ||
135 | p1pll->pll_out_min = 12500; | ||
136 | p1pll->pll_out_max = 35000; | ||
137 | p2pll->pll_in_min = 40; | ||
138 | p2pll->pll_in_max = 500; | ||
139 | p2pll->pll_out_min = 12500; | ||
140 | p2pll->pll_out_max = 35000; | ||
141 | } | ||
142 | |||
143 | spll->reference_freq = mpll->reference_freq = p1pll->reference_freq; | ||
144 | spll->reference_div = mpll->reference_div = | ||
145 | RREG32_PLL(RADEON_M_SPLL_REF_FB_DIV) & | ||
146 | RADEON_M_SPLL_REF_DIV_MASK; | ||
147 | |||
148 | val = of_get_property(dp, "ATY,SCLK", NULL); | ||
149 | if (val && *val) | ||
150 | rdev->clock.default_sclk = (*val) / 10; | ||
151 | else | ||
152 | rdev->clock.default_sclk = | ||
153 | radeon_legacy_get_engine_clock(rdev); | ||
154 | |||
155 | val = of_get_property(dp, "ATY,MCLK", NULL); | ||
156 | if (val && *val) | ||
157 | rdev->clock.default_mclk = (*val) / 10; | ||
158 | else | ||
159 | rdev->clock.default_mclk = | ||
160 | radeon_legacy_get_memory_clock(rdev); | ||
161 | |||
162 | DRM_INFO("Using device-tree clock info\n"); | ||
163 | |||
164 | return true; | ||
165 | } | ||
166 | #else | ||
167 | static bool __devinit radeon_read_clocks_OF(struct drm_device *dev) | ||
168 | { | ||
169 | return false; | ||
170 | } | ||
171 | #endif /* CONFIG_OF */ | ||
172 | |||
94 | void radeon_get_clock_info(struct drm_device *dev) | 173 | void radeon_get_clock_info(struct drm_device *dev) |
95 | { | 174 | { |
96 | struct radeon_device *rdev = dev->dev_private; | 175 | struct radeon_device *rdev = dev->dev_private; |
@@ -105,6 +184,8 @@ void radeon_get_clock_info(struct drm_device *dev) | |||
105 | ret = radeon_atom_get_clock_info(dev); | 184 | ret = radeon_atom_get_clock_info(dev); |
106 | else | 185 | else |
107 | ret = radeon_combios_get_clock_info(dev); | 186 | ret = radeon_combios_get_clock_info(dev); |
187 | if (!ret) | ||
188 | ret = radeon_read_clocks_OF(dev); | ||
108 | 189 | ||
109 | if (ret) { | 190 | if (ret) { |
110 | if (p1pll->reference_div < 2) { | 191 | if (p1pll->reference_div < 2) { |