123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249 |
- #include "ddk750_reg.h"
- #include "ddk750_help.h"
- #include "ddk750_display.h"
- #include "ddk750_power.h"
- #include "ddk750_dvi.h"
- #define primaryWaitVerticalSync(delay) waitNextVerticalSync(0, delay)
- static void setDisplayControl(int ctrl, int disp_state)
- {
- /* state != 0 means turn on both timing & plane en_bit */
- unsigned long ulDisplayCtrlReg, ulReservedBits;
- int cnt;
- cnt = 0;
- /* Set the primary display control */
- if (!ctrl) {
- ulDisplayCtrlReg = PEEK32(PANEL_DISPLAY_CTRL);
- /* Turn on/off the Panel display control */
- if (disp_state) {
- /* Timing should be enabled first before enabling the plane
- * because changing at the same time does not guarantee that
- * the plane will also enabled or disabled.
- */
- ulDisplayCtrlReg = FIELD_SET(ulDisplayCtrlReg,
- PANEL_DISPLAY_CTRL, TIMING, ENABLE);
- POKE32(PANEL_DISPLAY_CTRL, ulDisplayCtrlReg);
- ulDisplayCtrlReg = FIELD_SET(ulDisplayCtrlReg,
- PANEL_DISPLAY_CTRL, PLANE, ENABLE);
- /* Added some masks to mask out the reserved bits.
- * Sometimes, the reserved bits are set/reset randomly when
- * writing to the PRIMARY_DISPLAY_CTRL, therefore, the register
- * reserved bits are needed to be masked out.
- */
- ulReservedBits = FIELD_SET(0, PANEL_DISPLAY_CTRL, RESERVED_1_MASK, ENABLE) |
- FIELD_SET(0, PANEL_DISPLAY_CTRL, RESERVED_2_MASK, ENABLE) |
- FIELD_SET(0, PANEL_DISPLAY_CTRL, RESERVED_3_MASK, ENABLE);
- /* Somehow the register value on the plane is not set
- * until a few delay. Need to write
- * and read it a couple times
- */
- do {
- cnt++;
- POKE32(PANEL_DISPLAY_CTRL, ulDisplayCtrlReg);
- } while ((PEEK32(PANEL_DISPLAY_CTRL) & ~ulReservedBits) !=
- (ulDisplayCtrlReg & ~ulReservedBits));
- printk("Set Panel Plane enbit:after tried %d times\n", cnt);
- } else {
- /* When turning off, there is no rule on the programming
- * sequence since whenever the clock is off, then it does not
- * matter whether the plane is enabled or disabled.
- * Note: Modifying the plane bit will take effect on the
- * next vertical sync. Need to find out if it is necessary to
- * wait for 1 vsync before modifying the timing enable bit.
- * */
- ulDisplayCtrlReg = FIELD_SET(ulDisplayCtrlReg,
- PANEL_DISPLAY_CTRL, PLANE, DISABLE);
- POKE32(PANEL_DISPLAY_CTRL, ulDisplayCtrlReg);
- ulDisplayCtrlReg = FIELD_SET(ulDisplayCtrlReg,
- PANEL_DISPLAY_CTRL, TIMING, DISABLE);
- POKE32(PANEL_DISPLAY_CTRL, ulDisplayCtrlReg);
- }
- } else {
- /* Set the secondary display control */
- ulDisplayCtrlReg = PEEK32(CRT_DISPLAY_CTRL);
- if (disp_state) {
- /* Timing should be enabled first before enabling the plane because changing at the
- same time does not guarantee that the plane will also enabled or disabled.
- */
- ulDisplayCtrlReg = FIELD_SET(ulDisplayCtrlReg,
- CRT_DISPLAY_CTRL, TIMING, ENABLE);
- POKE32(CRT_DISPLAY_CTRL, ulDisplayCtrlReg);
- ulDisplayCtrlReg = FIELD_SET(ulDisplayCtrlReg,
- CRT_DISPLAY_CTRL, PLANE, ENABLE);
- /* Added some masks to mask out the reserved bits.
- * Sometimes, the reserved bits are set/reset randomly when
- * writing to the PRIMARY_DISPLAY_CTRL, therefore, the register
- * reserved bits are needed to be masked out.
- */
- ulReservedBits = FIELD_SET(0, CRT_DISPLAY_CTRL, RESERVED_1_MASK, ENABLE) |
- FIELD_SET(0, CRT_DISPLAY_CTRL, RESERVED_2_MASK, ENABLE) |
- FIELD_SET(0, CRT_DISPLAY_CTRL, RESERVED_3_MASK, ENABLE) |
- FIELD_SET(0, CRT_DISPLAY_CTRL, RESERVED_4_MASK, ENABLE);
- do {
- cnt++;
- POKE32(CRT_DISPLAY_CTRL, ulDisplayCtrlReg);
- } while ((PEEK32(CRT_DISPLAY_CTRL) & ~ulReservedBits) !=
- (ulDisplayCtrlReg & ~ulReservedBits));
- printk("Set Crt Plane enbit:after tried %d times\n", cnt);
- } else {
- /* When turning off, there is no rule on the programming
- * sequence since whenever the clock is off, then it does not
- * matter whether the plane is enabled or disabled.
- * Note: Modifying the plane bit will take effect on the next
- * vertical sync. Need to find out if it is necessary to
- * wait for 1 vsync before modifying the timing enable bit.
- */
- ulDisplayCtrlReg = FIELD_SET(ulDisplayCtrlReg,
- CRT_DISPLAY_CTRL, PLANE, DISABLE);
- POKE32(CRT_DISPLAY_CTRL, ulDisplayCtrlReg);
- ulDisplayCtrlReg = FIELD_SET(ulDisplayCtrlReg,
- CRT_DISPLAY_CTRL, TIMING, DISABLE);
- POKE32(CRT_DISPLAY_CTRL, ulDisplayCtrlReg);
- }
- }
- }
- static void waitNextVerticalSync(int ctrl, int delay)
- {
- unsigned int status;
- if (!ctrl) {
- /* primary controller */
- /* Do not wait when the Primary PLL is off or display control is already off.
- This will prevent the software to wait forever. */
- if ((FIELD_GET(PEEK32(PANEL_PLL_CTRL), PANEL_PLL_CTRL, POWER) ==
- PANEL_PLL_CTRL_POWER_OFF) ||
- (FIELD_GET(PEEK32(PANEL_DISPLAY_CTRL), PANEL_DISPLAY_CTRL, TIMING) ==
- PANEL_DISPLAY_CTRL_TIMING_DISABLE)) {
- return;
- }
- while (delay-- > 0) {
- /* Wait for end of vsync. */
- do {
- status = FIELD_GET(PEEK32(SYSTEM_CTRL),
- SYSTEM_CTRL,
- PANEL_VSYNC);
- } while (status == SYSTEM_CTRL_PANEL_VSYNC_ACTIVE);
- /* Wait for start of vsync. */
- do {
- status = FIELD_GET(PEEK32(SYSTEM_CTRL),
- SYSTEM_CTRL,
- PANEL_VSYNC);
- } while (status == SYSTEM_CTRL_PANEL_VSYNC_INACTIVE);
- }
- } else {
- /* Do not wait when the Primary PLL is off or display control is already off.
- This will prevent the software to wait forever. */
- if ((FIELD_GET(PEEK32(CRT_PLL_CTRL), CRT_PLL_CTRL, POWER) ==
- CRT_PLL_CTRL_POWER_OFF) ||
- (FIELD_GET(PEEK32(CRT_DISPLAY_CTRL), CRT_DISPLAY_CTRL, TIMING) ==
- CRT_DISPLAY_CTRL_TIMING_DISABLE)) {
- return;
- }
- while (delay-- > 0) {
- /* Wait for end of vsync. */
- do {
- status = FIELD_GET(PEEK32(SYSTEM_CTRL),
- SYSTEM_CTRL,
- CRT_VSYNC);
- } while (status == SYSTEM_CTRL_CRT_VSYNC_ACTIVE);
- /* Wait for start of vsync. */
- do {
- status = FIELD_GET(PEEK32(SYSTEM_CTRL),
- SYSTEM_CTRL,
- CRT_VSYNC);
- } while (status == SYSTEM_CTRL_CRT_VSYNC_INACTIVE);
- }
- }
- }
- static void swPanelPowerSequence(int disp, int delay)
- {
- unsigned int reg;
- /* disp should be 1 to open sequence */
- reg = PEEK32(PANEL_DISPLAY_CTRL);
- reg = FIELD_VALUE(reg, PANEL_DISPLAY_CTRL, FPEN, disp);
- POKE32(PANEL_DISPLAY_CTRL, reg);
- primaryWaitVerticalSync(delay);
- reg = PEEK32(PANEL_DISPLAY_CTRL);
- reg = FIELD_VALUE(reg, PANEL_DISPLAY_CTRL, DATA, disp);
- POKE32(PANEL_DISPLAY_CTRL, reg);
- primaryWaitVerticalSync(delay);
- reg = PEEK32(PANEL_DISPLAY_CTRL);
- reg = FIELD_VALUE(reg, PANEL_DISPLAY_CTRL, VBIASEN, disp);
- POKE32(PANEL_DISPLAY_CTRL, reg);
- primaryWaitVerticalSync(delay);
- reg = PEEK32(PANEL_DISPLAY_CTRL);
- reg = FIELD_VALUE(reg, PANEL_DISPLAY_CTRL, FPEN, disp);
- POKE32(PANEL_DISPLAY_CTRL, reg);
- primaryWaitVerticalSync(delay);
- }
- void ddk750_setLogicalDispOut(disp_output_t output)
- {
- unsigned int reg;
- if (output & PNL_2_USAGE) {
- /* set panel path controller select */
- reg = PEEK32(PANEL_DISPLAY_CTRL);
- reg = FIELD_VALUE(reg, PANEL_DISPLAY_CTRL, SELECT, (output & PNL_2_MASK)>>PNL_2_OFFSET);
- POKE32(PANEL_DISPLAY_CTRL, reg);
- }
- if (output & CRT_2_USAGE) {
- /* set crt path controller select */
- reg = PEEK32(CRT_DISPLAY_CTRL);
- reg = FIELD_VALUE(reg, CRT_DISPLAY_CTRL, SELECT, (output & CRT_2_MASK)>>CRT_2_OFFSET);
- /*se blank off */
- reg = FIELD_SET(reg, CRT_DISPLAY_CTRL, BLANK, OFF);
- POKE32(CRT_DISPLAY_CTRL, reg);
- }
- if (output & PRI_TP_USAGE) {
- /* set primary timing and plane en_bit */
- setDisplayControl(0, (output & PRI_TP_MASK) >> PRI_TP_OFFSET);
- }
- if (output & SEC_TP_USAGE) {
- /* set secondary timing and plane en_bit*/
- setDisplayControl(1, (output & SEC_TP_MASK) >> SEC_TP_OFFSET);
- }
- if (output & PNL_SEQ_USAGE) {
- /* set panel sequence */
- swPanelPowerSequence((output & PNL_SEQ_MASK) >> PNL_SEQ_OFFSET, 4);
- }
- if (output & DAC_USAGE)
- setDAC((output & DAC_MASK) >> DAC_OFFSET);
- if (output & DPMS_USAGE)
- ddk750_setDPMS((output & DPMS_MASK) >> DPMS_OFFSET);
- }
|