1/************************************************************************** 2 3Copyright 1998-1999 Precision Insight, Inc., Cedar Park, Texas. 4All Rights Reserved. 5 6Permission is hereby granted, free of charge, to any person obtaining a 7copy of this software and associated documentation files (the 8"Software"), to deal in the Software without restriction, including 9without limitation the rights to use, copy, modify, merge, publish, 10distribute, sub license, and/or sell copies of the Software, and to 11permit persons to whom the Software is furnished to do so, subject to 12the following conditions: 13 14The above copyright notice and this permission notice (including the 15next paragraph) shall be included in all copies or substantial portions 16of the Software. 17 18THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS 19OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF 20MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NON-INFRINGEMENT. 21IN NO EVENT SHALL PRECISION INSIGHT AND/OR ITS SUPPLIERS BE LIABLE FOR 22ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, 23TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE 24SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. 25 26**************************************************************************/ 27 28/* 29 * Authors: 30 * Keith Whitwell <keith@tungstengraphics.com> 31 */ 32 33#ifdef HAVE_CONFIG_H 34#include "config.h" 35#endif 36 37#include "xorg-server.h" 38#include "xf86.h" 39#include "i810.h" 40 41struct wm_info { 42 double freq; 43 unsigned int wm; 44}; 45 46static struct wm_info i810_wm_8_100[] = { 47 {0, 0x22003000}, 48 {25.2, 0x22003000}, 49 {28.0, 0x22003000}, 50 {31.5, 0x22003000}, 51 {36.0, 0x22007000}, 52 {40.0, 0x22007000}, 53 {45.0, 0x22007000}, 54 {49.5, 0x22008000}, 55 {50.0, 0x22008000}, 56 {56.3, 0x22008000}, 57 {65.0, 0x22008000}, 58 {75.0, 0x22008000}, 59 {78.8, 0x22008000}, 60 {80.0, 0x22008000}, 61 {94.0, 0x22008000}, 62 {96.0, 0x22107000}, 63 {99.0, 0x22107000}, 64 {108.0, 0x22107000}, 65 {121.0, 0x22107000}, 66 {128.9, 0x22107000}, 67 {132.0, 0x22109000}, 68 {135.0, 0x22109000}, 69 {157.5, 0x2210b000}, 70 {162.0, 0x2210b000}, 71 {175.5, 0x2210b000}, 72 {189.0, 0x2220e000}, 73 {202.5, 0x2220e000} 74}; 75 76static struct wm_info i810_wm_16_100[] = { 77 {0, 0x22004000}, 78 {25.2, 0x22006000}, 79 {28.0, 0x22006000}, 80 {31.5, 0x22007000}, 81 {36.0, 0x22007000}, 82 {40.0, 0x22007000}, 83 {45.0, 0x22007000}, 84 {49.5, 0x22009000}, 85 {50.0, 0x22009000}, 86 {56.3, 0x22108000}, 87 {65.0, 0x2210e000}, 88 {75.0, 0x2210e000}, 89 {78.8, 0x2210e000}, 90 {80.0, 0x22210000}, 91 {94.5, 0x22210000}, 92 {96.0, 0x22210000}, 93 {99.0, 0x22210000}, 94 {108.0, 0x22210000}, 95 {121.0, 0x22210000}, 96 {128.9, 0x22210000}, 97 {132.0, 0x22314000}, 98 {135.0, 0x22314000}, 99 {157.5, 0x22415000}, 100 {162.0, 0x22416000}, 101 {175.5, 0x22416000}, 102 {189.0, 0x22416000}, 103 {195.0, 0x22416000}, 104 {202.5, 0x22416000} 105}; 106 107static struct wm_info i810_wm_24_100[] = { 108 {0, 0x22006000}, 109 {25.2, 0x22009000}, 110 {28.0, 0x22009000}, 111 {31.5, 0x2200a000}, 112 {36.0, 0x2210c000}, 113 {40.0, 0x2210c000}, 114 {45.0, 0x2210c000}, 115 {49.5, 0x22111000}, 116 {50.0, 0x22111000}, 117 {56.3, 0x22111000}, 118 {65.0, 0x22214000}, 119 {75.0, 0x22214000}, 120 {78.8, 0x22215000}, 121 {80.0, 0x22216000}, 122 {94.5, 0x22218000}, 123 {96.0, 0x22418000}, 124 {99.0, 0x22418000}, 125 {108.0, 0x22418000}, 126 {121.0, 0x22418000}, 127 {128.9, 0x22419000}, 128 {132.0, 0x22519000}, 129 {135.0, 0x4441d000}, 130 {157.5, 0x44419000}, 131 {162.0, 0x44419000}, 132 {175.5, 0x44419000}, 133 {189.0, 0x44419000}, 134 {195.0, 0x44419000}, 135 {202.5, 0x44419000} 136}; 137 138#if 0 139/* not used */ 140static struct wm_info i810_wm_32_100[] = { 141 {0, 0x2210b000}, 142 {60, 0x22415000}, /* 0x314000 works too */ 143 {80, 0x22419000} /* 0x518000 works too */ 144}; 145#endif 146 147static struct wm_info i810_wm_8_133[] = { 148 {0, 0x22003000}, 149 {25.2, 0x22003000}, 150 {28.0, 0x22003000}, 151 {31.5, 0x22003000}, 152 {36.0, 0x22007000}, 153 {40.0, 0x22007000}, 154 {45.0, 0x22007000}, 155 {49.5, 0x22008000}, 156 {50.0, 0x22008000}, 157 {56.3, 0x22008000}, 158 {65.0, 0x22008000}, 159 {75.0, 0x22008000}, 160 {78.8, 0x22008000}, 161 {80.0, 0x22008000}, 162 {94.0, 0x22008000}, 163 {96.0, 0x22107000}, 164 {99.0, 0x22107000}, 165 {108.0, 0x22107000}, 166 {121.0, 0x22107000}, 167 {128.9, 0x22107000}, 168 {132.0, 0x22109000}, 169 {135.0, 0x22109000}, 170 {157.5, 0x2210b000}, 171 {162.0, 0x2210b000}, 172 {175.5, 0x2210b000}, 173 {189.0, 0x2220e000}, 174 {202.5, 0x2220e000} 175}; 176 177static struct wm_info i810_wm_16_133[] = { 178 {0, 0x22004000}, 179 {25.2, 0x22006000}, 180 {28.0, 0x22006000}, 181 {31.5, 0x22007000}, 182 {36.0, 0x22007000}, 183 {40.0, 0x22007000}, 184 {45.0, 0x22007000}, 185 {49.5, 0x22009000}, 186 {50.0, 0x22009000}, 187 {56.3, 0x22108000}, 188 {65.0, 0x2210e000}, 189 {75.0, 0x2210e000}, 190 {78.8, 0x2210e000}, 191 {80.0, 0x22210000}, 192 {94.5, 0x22210000}, 193 {96.0, 0x22210000}, 194 {99.0, 0x22210000}, 195 {108.0, 0x22210000}, 196 {121.0, 0x22210000}, 197 {128.9, 0x22210000}, 198 {132.0, 0x22314000}, 199 {135.0, 0x22314000}, 200 {157.5, 0x22415000}, 201 {162.0, 0x22416000}, 202 {175.5, 0x22416000}, 203 {189.0, 0x22416000}, 204 {195.0, 0x22416000}, 205 {202.5, 0x22416000} 206}; 207 208static struct wm_info i810_wm_24_133[] = { 209 {0, 0x22006000}, 210 {25.2, 0x22009000}, 211 {28.0, 0x22009000}, 212 {31.5, 0x2200a000}, 213 {36.0, 0x2210c000}, 214 {40.0, 0x2210c000}, 215 {45.0, 0x2210c000}, 216 {49.5, 0x22111000}, 217 {50.0, 0x22111000}, 218 {56.3, 0x22111000}, 219 {65.0, 0x22214000}, 220 {75.0, 0x22214000}, 221 {78.8, 0x22215000}, 222 {80.0, 0x22216000}, 223 {94.5, 0x22218000}, 224 {96.0, 0x22418000}, 225 {99.0, 0x22418000}, 226 {108.0, 0x22418000}, 227 {121.0, 0x22418000}, 228 {128.9, 0x22419000}, 229 {132.0, 0x22519000}, 230 {135.0, 0x4441d000}, 231 {157.5, 0x44419000}, 232 {162.0, 0x44419000}, 233 {175.5, 0x44419000}, 234 {189.0, 0x44419000}, 235 {195.0, 0x44419000}, 236 {202.5, 0x44419000} 237}; 238 239#define Elements(x) (sizeof(x)/sizeof(*x)) 240 241/* 242 * I810CalcFIFO -- 243 * 244 * Calculate burst length and FIFO watermark. 245 */ 246 247unsigned int 248I810CalcWatermark(ScrnInfoPtr pScrn, double freq, Bool dcache) 249{ 250 I810Ptr pI810 = I810PTR(pScrn); 251 struct wm_info *tab; 252 int nr; 253 int i; 254 255 if (pI810->LmFreqSel == 100) { 256 switch (pScrn->bitsPerPixel) { 257 case 8: 258 tab = i810_wm_8_100; 259 nr = Elements(i810_wm_8_100); 260 break; 261 case 16: 262 tab = i810_wm_16_100; 263 nr = Elements(i810_wm_16_100); 264 break; 265 case 24: 266 tab = i810_wm_24_100; 267 nr = Elements(i810_wm_24_100); 268 break; 269 default: 270 return 0; 271 } 272 } else { 273 switch (pScrn->bitsPerPixel) { 274 case 8: 275 tab = i810_wm_8_133; 276 nr = Elements(i810_wm_8_133); 277 break; 278 case 16: 279 tab = i810_wm_16_133; 280 nr = Elements(i810_wm_16_133); 281 break; 282 case 24: 283 tab = i810_wm_24_133; 284 nr = Elements(i810_wm_24_133); 285 break; 286 default: 287 return 0; 288 } 289 } 290 291 for (i = 0; i < nr && tab[i].freq < freq; i++) ; 292 293 if (i == nr) 294 i--; 295 296 xf86DrvMsgVerb(pScrn->scrnIndex, X_INFO, 3, 297 "chose watermark 0x%x: (tab.freq %.1f)\n", 298 tab[i].wm, tab[i].freq); 299 300 /* None of these values (sourced from intel) have watermarks for 301 * the dcache memory. Fake it for now by using the same watermark 302 * for both... 303 * 304 * Update: this is probably because dcache isn't real useful as 305 * framebuffer memory, so intel's drivers don't need watermarks 306 * for that memory because they never use it to feed the ramdacs. 307 * We do use it in the fallback mode, so keep the watermarks for 308 * now. 309 */ 310 if (dcache) 311 return (tab[i].wm & ~0xffffff) | ((tab[i].wm >> 12) & 0xfff); 312 else 313 return tab[i].wm; 314} 315