2 * Copyright 2003 NVIDIA, Corporation
3 * Copyright 2006 Dave Airlie
4 * Copyright 2007 Maarten Maathuis
5 * Copyright 2007-2009 Stuart Bennett
7 * Permission is hereby granted, free of charge, to any person obtaining a
8 * copy of this software and associated documentation files (the "Software"),
9 * to deal in the Software without restriction, including without limitation
10 * the rights to use, copy, modify, merge, publish, distribute, sublicense,
11 * and/or sell copies of the Software, and to permit persons to whom the
12 * Software is furnished to do so, subject to the following conditions:
14 * The above copyright notice and this permission notice (including the next
15 * paragraph) shall be included in all copies or substantial portions of the
18 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
19 * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
20 * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
21 * THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
22 * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
23 * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
24 * DEALINGS IN THE SOFTWARE.
28 #include <drm/drm_crtc_helper.h>
30 #include "nouveau_drv.h"
31 #include "nouveau_encoder.h"
32 #include "nouveau_connector.h"
33 #include "nouveau_crtc.h"
37 #include <subdev/bios/gpio.h>
38 #include <subdev/gpio.h>
39 #include <subdev/timer.h>
41 int nv04_dac_output_offset(struct drm_encoder
*encoder
)
43 struct dcb_output
*dcb
= nouveau_encoder(encoder
)->dcb
;
46 if (dcb
->or & (8 | DCB_OUTPUT_C
))
48 if (dcb
->or & (8 | DCB_OUTPUT_B
))
55 * arbitrary limit to number of sense oscillations tolerated in one sample
56 * period (observed to be at least 13 in "nvidia")
58 #define MAX_HBLANK_OSC 20
61 * arbitrary limit to number of conflicting sample pairs to tolerate at a
62 * voltage step (observed to be at least 5 in "nvidia")
64 #define MAX_SAMPLE_PAIRS 10
66 static int sample_load_twice(struct drm_device
*dev
, bool sense
[2])
68 struct nouveau_drm
*drm
= nouveau_drm(dev
);
69 struct nvif_object
*device
= &drm
->client
.device
.object
;
72 for (i
= 0; i
< 2; i
++) {
73 bool sense_a
, sense_b
, sense_b_prime
;
77 * wait for bit 0 clear -- out of hblank -- (say reg value 0x4),
78 * then wait for transition 0x4->0x5->0x4: enter hblank, leave
80 * use a 10ms timeout (guards against crtc being inactive, in
81 * which case blank state would never change)
83 if (nvif_msec(&drm
->client
.device
, 10,
84 if (!(nvif_rd32(device
, NV_PRMCIO_INP0__COLOR
) & 1))
89 if (nvif_msec(&drm
->client
.device
, 10,
90 if ( (nvif_rd32(device
, NV_PRMCIO_INP0__COLOR
) & 1))
95 if (nvif_msec(&drm
->client
.device
, 10,
96 if (!(nvif_rd32(device
, NV_PRMCIO_INP0__COLOR
) & 1))
102 /* when level triggers, sense is _LO_ */
103 sense_a
= nvif_rd08(device
, NV_PRMCIO_INP0
) & 0x10;
105 /* take another reading until it agrees with sense_a... */
108 sense_b
= nvif_rd08(device
, NV_PRMCIO_INP0
) & 0x10;
109 if (sense_a
!= sense_b
) {
111 nvif_rd08(device
, NV_PRMCIO_INP0
) & 0x10;
112 if (sense_b
== sense_b_prime
) {
113 /* ... unless two consecutive subsequent
114 * samples agree; sense_a is replaced */
116 /* force mis-match so we loop */
120 } while ((sense_a
!= sense_b
) && ++j
< MAX_HBLANK_OSC
);
122 if (j
== MAX_HBLANK_OSC
)
123 /* with so much oscillation, default to sense:LO */
132 static enum drm_connector_status
nv04_dac_detect(struct drm_encoder
*encoder
,
133 struct drm_connector
*connector
)
135 struct drm_device
*dev
= encoder
->dev
;
136 struct nvif_object
*device
= &nouveau_drm(dev
)->client
.device
.object
;
137 struct nouveau_drm
*drm
= nouveau_drm(dev
);
138 uint8_t saved_seq1
, saved_pi
, saved_rpc1
, saved_cr_mode
;
139 uint8_t saved_palette0
[3], saved_palette_mask
;
140 uint32_t saved_rtest_ctrl
, saved_rgen_ctrl
;
146 * for this detection to work, there needs to be a mode set up on the
147 * CRTC. this is presumed to be the case
150 if (nv_two_heads(dev
))
151 /* only implemented for head A for now */
154 saved_cr_mode
= NVReadVgaCrtc(dev
, 0, NV_CIO_CR_MODE_INDEX
);
155 NVWriteVgaCrtc(dev
, 0, NV_CIO_CR_MODE_INDEX
, saved_cr_mode
| 0x80);
157 saved_seq1
= NVReadVgaSeq(dev
, 0, NV_VIO_SR_CLOCK_INDEX
);
158 NVWriteVgaSeq(dev
, 0, NV_VIO_SR_CLOCK_INDEX
, saved_seq1
& ~0x20);
160 saved_rtest_ctrl
= NVReadRAMDAC(dev
, 0, NV_PRAMDAC_TEST_CONTROL
);
161 NVWriteRAMDAC(dev
, 0, NV_PRAMDAC_TEST_CONTROL
,
162 saved_rtest_ctrl
& ~NV_PRAMDAC_TEST_CONTROL_PWRDWN_DAC_OFF
);
166 saved_pi
= NVReadVgaCrtc(dev
, 0, NV_CIO_CRE_PIXEL_INDEX
);
167 NVWriteVgaCrtc(dev
, 0, NV_CIO_CRE_PIXEL_INDEX
,
168 saved_pi
& ~(0x80 | MASK(NV_CIO_CRE_PIXEL_FORMAT
)));
169 saved_rpc1
= NVReadVgaCrtc(dev
, 0, NV_CIO_CRE_RPC1_INDEX
);
170 NVWriteVgaCrtc(dev
, 0, NV_CIO_CRE_RPC1_INDEX
, saved_rpc1
& ~0xc0);
172 nvif_wr08(device
, NV_PRMDIO_READ_MODE_ADDRESS
, 0x0);
173 for (i
= 0; i
< 3; i
++)
174 saved_palette0
[i
] = nvif_rd08(device
, NV_PRMDIO_PALETTE_DATA
);
175 saved_palette_mask
= nvif_rd08(device
, NV_PRMDIO_PIXEL_MASK
);
176 nvif_wr08(device
, NV_PRMDIO_PIXEL_MASK
, 0);
178 saved_rgen_ctrl
= NVReadRAMDAC(dev
, 0, NV_PRAMDAC_GENERAL_CONTROL
);
179 NVWriteRAMDAC(dev
, 0, NV_PRAMDAC_GENERAL_CONTROL
,
180 (saved_rgen_ctrl
& ~(NV_PRAMDAC_GENERAL_CONTROL_BPC_8BITS
|
181 NV_PRAMDAC_GENERAL_CONTROL_TERMINATION_75OHM
)) |
182 NV_PRAMDAC_GENERAL_CONTROL_PIXMIX_ON
);
184 blue
= 8; /* start of test range */
189 nvif_wr08(device
, NV_PRMDIO_WRITE_MODE_ADDRESS
, 0);
190 nvif_wr08(device
, NV_PRMDIO_PALETTE_DATA
, 0);
191 nvif_wr08(device
, NV_PRMDIO_PALETTE_DATA
, 0);
192 /* testing blue won't find monochrome monitors. I don't care */
193 nvif_wr08(device
, NV_PRMDIO_PALETTE_DATA
, blue
);
196 /* take sample pairs until both samples in the pair agree */
198 if (sample_load_twice(dev
, sense_pair
))
200 } while ((sense_pair
[0] != sense_pair
[1]) &&
201 ++i
< MAX_SAMPLE_PAIRS
);
203 if (i
== MAX_SAMPLE_PAIRS
)
204 /* too much oscillation defaults to LO */
207 sense
= sense_pair
[0];
210 * if sense goes LO before blue ramps to 0x18, monitor is not connected.
211 * ergo, if blue gets to 0x18, monitor must be connected
213 } while (++blue
< 0x18 && sense
);
216 nvif_wr08(device
, NV_PRMDIO_PIXEL_MASK
, saved_palette_mask
);
217 NVWriteRAMDAC(dev
, 0, NV_PRAMDAC_GENERAL_CONTROL
, saved_rgen_ctrl
);
218 nvif_wr08(device
, NV_PRMDIO_WRITE_MODE_ADDRESS
, 0);
219 for (i
= 0; i
< 3; i
++)
220 nvif_wr08(device
, NV_PRMDIO_PALETTE_DATA
, saved_palette0
[i
]);
221 NVWriteRAMDAC(dev
, 0, NV_PRAMDAC_TEST_CONTROL
, saved_rtest_ctrl
);
222 NVWriteVgaCrtc(dev
, 0, NV_CIO_CRE_PIXEL_INDEX
, saved_pi
);
223 NVWriteVgaCrtc(dev
, 0, NV_CIO_CRE_RPC1_INDEX
, saved_rpc1
);
224 NVWriteVgaSeq(dev
, 0, NV_VIO_SR_CLOCK_INDEX
, saved_seq1
);
225 NVWriteVgaCrtc(dev
, 0, NV_CIO_CR_MODE_INDEX
, saved_cr_mode
);
228 NV_DEBUG(drm
, "Load detected on head A\n");
229 return connector_status_connected
;
232 return connector_status_disconnected
;
235 uint32_t nv17_dac_sample_load(struct drm_encoder
*encoder
)
237 struct drm_device
*dev
= encoder
->dev
;
238 struct nouveau_drm
*drm
= nouveau_drm(dev
);
239 struct nvif_object
*device
= &nouveau_drm(dev
)->client
.device
.object
;
240 struct nvkm_gpio
*gpio
= nvxx_gpio(&drm
->client
.device
);
241 struct dcb_output
*dcb
= nouveau_encoder(encoder
)->dcb
;
242 uint32_t sample
, testval
, regoffset
= nv04_dac_output_offset(encoder
);
243 uint32_t saved_powerctrl_2
= 0, saved_powerctrl_4
= 0, saved_routput
,
244 saved_rtest_ctrl
, saved_gpio0
= 0, saved_gpio1
= 0, temp
, routput
;
247 #define RGB_TEST_DATA(r, g, b) (r << 0 | g << 10 | b << 20)
248 if (dcb
->type
== DCB_OUTPUT_TV
) {
249 testval
= RGB_TEST_DATA(0xa0, 0xa0, 0xa0);
251 if (drm
->vbios
.tvdactestval
)
252 testval
= drm
->vbios
.tvdactestval
;
254 testval
= RGB_TEST_DATA(0x140, 0x140, 0x140); /* 0x94050140 */
256 if (drm
->vbios
.dactestval
)
257 testval
= drm
->vbios
.dactestval
;
260 saved_rtest_ctrl
= NVReadRAMDAC(dev
, 0, NV_PRAMDAC_TEST_CONTROL
+ regoffset
);
261 NVWriteRAMDAC(dev
, 0, NV_PRAMDAC_TEST_CONTROL
+ regoffset
,
262 saved_rtest_ctrl
& ~NV_PRAMDAC_TEST_CONTROL_PWRDWN_DAC_OFF
);
264 saved_powerctrl_2
= nvif_rd32(device
, NV_PBUS_POWERCTRL_2
);
266 nvif_wr32(device
, NV_PBUS_POWERCTRL_2
, saved_powerctrl_2
& 0xd7ffffff);
267 if (regoffset
== 0x68) {
268 saved_powerctrl_4
= nvif_rd32(device
, NV_PBUS_POWERCTRL_4
);
269 nvif_wr32(device
, NV_PBUS_POWERCTRL_4
, saved_powerctrl_4
& 0xffffffcf);
273 saved_gpio1
= nvkm_gpio_get(gpio
, 0, DCB_GPIO_TVDAC1
, 0xff);
274 saved_gpio0
= nvkm_gpio_get(gpio
, 0, DCB_GPIO_TVDAC0
, 0xff);
275 nvkm_gpio_set(gpio
, 0, DCB_GPIO_TVDAC1
, 0xff, dcb
->type
== DCB_OUTPUT_TV
);
276 nvkm_gpio_set(gpio
, 0, DCB_GPIO_TVDAC0
, 0xff, dcb
->type
== DCB_OUTPUT_TV
);
281 saved_routput
= NVReadRAMDAC(dev
, 0, NV_PRAMDAC_DACCLK
+ regoffset
);
282 head
= (saved_routput
& 0x100) >> 8;
284 /* if there's a spare crtc, using it will minimise flicker */
285 if (!(NVReadVgaCrtc(dev
, head
, NV_CIO_CRE_RPC1_INDEX
) & 0xC0))
288 /* nv driver and nv31 use 0xfffffeee, nv34 and 6600 use 0xfffffece */
289 routput
= (saved_routput
& 0xfffffece) | head
<< 8;
291 if (drm
->client
.device
.info
.family
>= NV_DEVICE_INFO_V0_CURIE
) {
292 if (dcb
->type
== DCB_OUTPUT_TV
)
293 routput
|= 0x1a << 16;
295 routput
&= ~(0x1a << 16);
298 NVWriteRAMDAC(dev
, 0, NV_PRAMDAC_DACCLK
+ regoffset
, routput
);
301 temp
= NVReadRAMDAC(dev
, 0, NV_PRAMDAC_DACCLK
+ regoffset
);
302 NVWriteRAMDAC(dev
, 0, NV_PRAMDAC_DACCLK
+ regoffset
, temp
| 1);
304 NVWriteRAMDAC(dev
, head
, NV_PRAMDAC_TESTPOINT_DATA
,
305 NV_PRAMDAC_TESTPOINT_DATA_NOTBLANK
| testval
);
306 temp
= NVReadRAMDAC(dev
, head
, NV_PRAMDAC_TEST_CONTROL
);
307 NVWriteRAMDAC(dev
, head
, NV_PRAMDAC_TEST_CONTROL
,
308 temp
| NV_PRAMDAC_TEST_CONTROL_TP_INS_EN_ASSERTED
);
311 sample
= NVReadRAMDAC(dev
, 0, NV_PRAMDAC_TEST_CONTROL
+ regoffset
);
312 /* do it again just in case it's a residual current */
313 sample
&= NVReadRAMDAC(dev
, 0, NV_PRAMDAC_TEST_CONTROL
+ regoffset
);
315 temp
= NVReadRAMDAC(dev
, head
, NV_PRAMDAC_TEST_CONTROL
);
316 NVWriteRAMDAC(dev
, head
, NV_PRAMDAC_TEST_CONTROL
,
317 temp
& ~NV_PRAMDAC_TEST_CONTROL_TP_INS_EN_ASSERTED
);
318 NVWriteRAMDAC(dev
, head
, NV_PRAMDAC_TESTPOINT_DATA
, 0);
320 /* bios does something more complex for restoring, but I think this is good enough */
321 NVWriteRAMDAC(dev
, 0, NV_PRAMDAC_DACCLK
+ regoffset
, saved_routput
);
322 NVWriteRAMDAC(dev
, 0, NV_PRAMDAC_TEST_CONTROL
+ regoffset
, saved_rtest_ctrl
);
323 if (regoffset
== 0x68)
324 nvif_wr32(device
, NV_PBUS_POWERCTRL_4
, saved_powerctrl_4
);
325 nvif_wr32(device
, NV_PBUS_POWERCTRL_2
, saved_powerctrl_2
);
328 nvkm_gpio_set(gpio
, 0, DCB_GPIO_TVDAC1
, 0xff, saved_gpio1
);
329 nvkm_gpio_set(gpio
, 0, DCB_GPIO_TVDAC0
, 0xff, saved_gpio0
);
335 static enum drm_connector_status
336 nv17_dac_detect(struct drm_encoder
*encoder
, struct drm_connector
*connector
)
338 struct nouveau_drm
*drm
= nouveau_drm(encoder
->dev
);
339 struct dcb_output
*dcb
= nouveau_encoder(encoder
)->dcb
;
341 if (nv04_dac_in_use(encoder
))
342 return connector_status_disconnected
;
344 if (nv17_dac_sample_load(encoder
) &
345 NV_PRAMDAC_TEST_CONTROL_SENSEB_ALLHI
) {
346 NV_DEBUG(drm
, "Load detected on output %c\n",
348 return connector_status_connected
;
350 return connector_status_disconnected
;
354 static bool nv04_dac_mode_fixup(struct drm_encoder
*encoder
,
355 const struct drm_display_mode
*mode
,
356 struct drm_display_mode
*adjusted_mode
)
358 if (nv04_dac_in_use(encoder
))
364 static void nv04_dac_prepare(struct drm_encoder
*encoder
)
366 const struct drm_encoder_helper_funcs
*helper
= encoder
->helper_private
;
367 struct drm_device
*dev
= encoder
->dev
;
368 int head
= nouveau_crtc(encoder
->crtc
)->index
;
370 helper
->dpms(encoder
, DRM_MODE_DPMS_OFF
);
372 nv04_dfp_disable(dev
, head
);
375 static void nv04_dac_mode_set(struct drm_encoder
*encoder
,
376 struct drm_display_mode
*mode
,
377 struct drm_display_mode
*adjusted_mode
)
379 struct drm_device
*dev
= encoder
->dev
;
380 struct nouveau_drm
*drm
= nouveau_drm(dev
);
381 int head
= nouveau_crtc(encoder
->crtc
)->index
;
383 if (nv_gf4_disp_arch(dev
)) {
384 struct drm_encoder
*rebind
;
385 uint32_t dac_offset
= nv04_dac_output_offset(encoder
);
388 /* bit 16-19 are bits that are set on some G70 cards,
389 * but don't seem to have much effect */
390 NVWriteRAMDAC(dev
, 0, NV_PRAMDAC_DACCLK
+ dac_offset
,
391 head
<< 8 | NV_PRAMDAC_DACCLK_SEL_DACCLK
);
392 /* force any other vga encoders to bind to the other crtc */
393 list_for_each_entry(rebind
, &dev
->mode_config
.encoder_list
, head
) {
394 if (rebind
== encoder
395 || nouveau_encoder(rebind
)->dcb
->type
!= DCB_OUTPUT_ANALOG
)
398 dac_offset
= nv04_dac_output_offset(rebind
);
399 otherdac
= NVReadRAMDAC(dev
, 0, NV_PRAMDAC_DACCLK
+ dac_offset
);
400 NVWriteRAMDAC(dev
, 0, NV_PRAMDAC_DACCLK
+ dac_offset
,
401 (otherdac
& ~0x0100) | (head
^ 1) << 8);
405 /* This could use refinement for flatpanels, but it should work this way */
406 if (drm
->client
.device
.info
.chipset
< 0x44)
407 NVWriteRAMDAC(dev
, 0, NV_PRAMDAC_TEST_CONTROL
+ nv04_dac_output_offset(encoder
), 0xf0000000);
409 NVWriteRAMDAC(dev
, 0, NV_PRAMDAC_TEST_CONTROL
+ nv04_dac_output_offset(encoder
), 0x00100000);
412 static void nv04_dac_commit(struct drm_encoder
*encoder
)
414 struct nouveau_encoder
*nv_encoder
= nouveau_encoder(encoder
);
415 struct nouveau_drm
*drm
= nouveau_drm(encoder
->dev
);
416 struct nouveau_crtc
*nv_crtc
= nouveau_crtc(encoder
->crtc
);
417 const struct drm_encoder_helper_funcs
*helper
= encoder
->helper_private
;
419 helper
->dpms(encoder
, DRM_MODE_DPMS_ON
);
421 NV_DEBUG(drm
, "Output %s is running on CRTC %d using output %c\n",
422 nouveau_encoder_connector_get(nv_encoder
)->base
.name
,
423 nv_crtc
->index
, '@' + ffs(nv_encoder
->dcb
->or));
426 void nv04_dac_update_dacclk(struct drm_encoder
*encoder
, bool enable
)
428 struct drm_device
*dev
= encoder
->dev
;
429 struct dcb_output
*dcb
= nouveau_encoder(encoder
)->dcb
;
431 if (nv_gf4_disp_arch(dev
)) {
432 uint32_t *dac_users
= &nv04_display(dev
)->dac_users
[ffs(dcb
->or) - 1];
433 int dacclk_off
= NV_PRAMDAC_DACCLK
+ nv04_dac_output_offset(encoder
);
434 uint32_t dacclk
= NVReadRAMDAC(dev
, 0, dacclk_off
);
437 *dac_users
|= 1 << dcb
->index
;
438 NVWriteRAMDAC(dev
, 0, dacclk_off
, dacclk
| NV_PRAMDAC_DACCLK_SEL_DACCLK
);
441 *dac_users
&= ~(1 << dcb
->index
);
443 NVWriteRAMDAC(dev
, 0, dacclk_off
,
444 dacclk
& ~NV_PRAMDAC_DACCLK_SEL_DACCLK
);
449 /* Check if the DAC corresponding to 'encoder' is being used by
451 bool nv04_dac_in_use(struct drm_encoder
*encoder
)
453 struct drm_device
*dev
= encoder
->dev
;
454 struct dcb_output
*dcb
= nouveau_encoder(encoder
)->dcb
;
456 return nv_gf4_disp_arch(encoder
->dev
) &&
457 (nv04_display(dev
)->dac_users
[ffs(dcb
->or) - 1] & ~(1 << dcb
->index
));
460 static void nv04_dac_dpms(struct drm_encoder
*encoder
, int mode
)
462 struct nouveau_encoder
*nv_encoder
= nouveau_encoder(encoder
);
463 struct nouveau_drm
*drm
= nouveau_drm(encoder
->dev
);
465 if (nv_encoder
->last_dpms
== mode
)
467 nv_encoder
->last_dpms
= mode
;
469 NV_DEBUG(drm
, "Setting dpms mode %d on vga encoder (output %d)\n",
470 mode
, nv_encoder
->dcb
->index
);
472 nv04_dac_update_dacclk(encoder
, mode
== DRM_MODE_DPMS_ON
);
475 static void nv04_dac_save(struct drm_encoder
*encoder
)
477 struct nouveau_encoder
*nv_encoder
= nouveau_encoder(encoder
);
478 struct drm_device
*dev
= encoder
->dev
;
480 if (nv_gf4_disp_arch(dev
))
481 nv_encoder
->restore
.output
= NVReadRAMDAC(dev
, 0, NV_PRAMDAC_DACCLK
+
482 nv04_dac_output_offset(encoder
));
485 static void nv04_dac_restore(struct drm_encoder
*encoder
)
487 struct nouveau_encoder
*nv_encoder
= nouveau_encoder(encoder
);
488 struct drm_device
*dev
= encoder
->dev
;
490 if (nv_gf4_disp_arch(dev
))
491 NVWriteRAMDAC(dev
, 0, NV_PRAMDAC_DACCLK
+ nv04_dac_output_offset(encoder
),
492 nv_encoder
->restore
.output
);
494 nv_encoder
->last_dpms
= NV_DPMS_CLEARED
;
497 static void nv04_dac_destroy(struct drm_encoder
*encoder
)
499 struct nouveau_encoder
*nv_encoder
= nouveau_encoder(encoder
);
501 drm_encoder_cleanup(encoder
);
505 static const struct drm_encoder_helper_funcs nv04_dac_helper_funcs
= {
506 .dpms
= nv04_dac_dpms
,
507 .mode_fixup
= nv04_dac_mode_fixup
,
508 .prepare
= nv04_dac_prepare
,
509 .commit
= nv04_dac_commit
,
510 .mode_set
= nv04_dac_mode_set
,
511 .detect
= nv04_dac_detect
514 static const struct drm_encoder_helper_funcs nv17_dac_helper_funcs
= {
515 .dpms
= nv04_dac_dpms
,
516 .mode_fixup
= nv04_dac_mode_fixup
,
517 .prepare
= nv04_dac_prepare
,
518 .commit
= nv04_dac_commit
,
519 .mode_set
= nv04_dac_mode_set
,
520 .detect
= nv17_dac_detect
523 static const struct drm_encoder_funcs nv04_dac_funcs
= {
524 .destroy
= nv04_dac_destroy
,
528 nv04_dac_create(struct drm_connector
*connector
, struct dcb_output
*entry
)
530 const struct drm_encoder_helper_funcs
*helper
;
531 struct nouveau_encoder
*nv_encoder
= NULL
;
532 struct drm_device
*dev
= connector
->dev
;
533 struct drm_encoder
*encoder
;
535 nv_encoder
= kzalloc(sizeof(*nv_encoder
), GFP_KERNEL
);
539 encoder
= to_drm_encoder(nv_encoder
);
541 nv_encoder
->dcb
= entry
;
542 nv_encoder
->or = ffs(entry
->or) - 1;
544 nv_encoder
->enc_save
= nv04_dac_save
;
545 nv_encoder
->enc_restore
= nv04_dac_restore
;
547 if (nv_gf4_disp_arch(dev
))
548 helper
= &nv17_dac_helper_funcs
;
550 helper
= &nv04_dac_helper_funcs
;
552 drm_encoder_init(dev
, encoder
, &nv04_dac_funcs
, DRM_MODE_ENCODER_DAC
,
554 drm_encoder_helper_add(encoder
, helper
);
556 encoder
->possible_crtcs
= entry
->heads
;
557 encoder
->possible_clones
= 0;
559 drm_connector_attach_encoder(connector
, encoder
);