xref: /haiku/src/add-ons/accelerants/ati/rage128_dpms.cpp (revision 4c9da6dc09e79654948b64ba600c4d4b1b12109e)
180829ec8SRene Gollent /*
280829ec8SRene Gollent 	Haiku ATI video driver adapted from the X.org ATI driver.
380829ec8SRene Gollent 
480829ec8SRene Gollent 	Copyright 1999, 2000 ATI Technologies Inc., Markham, Ontario,
580829ec8SRene Gollent 						 Precision Insight, Inc., Cedar Park, Texas, and
680829ec8SRene Gollent 						 VA Linux Systems Inc., Fremont, California.
780829ec8SRene Gollent 
880829ec8SRene Gollent 	Copyright 2009 Haiku, Inc.  All rights reserved.
980829ec8SRene Gollent 	Distributed under the terms of the MIT license.
1080829ec8SRene Gollent 
1180829ec8SRene Gollent 	Authors:
1280829ec8SRene Gollent 	Gerald Zajac 2009
1380829ec8SRene Gollent */
1480829ec8SRene Gollent 
1580829ec8SRene Gollent 
1680829ec8SRene Gollent #include "accelerant.h"
1780829ec8SRene Gollent #include "rage128.h"
1880829ec8SRene Gollent 
1980829ec8SRene Gollent 
2080829ec8SRene Gollent 
2180829ec8SRene Gollent uint32
Rage128_DPMSCapabilities(void)2280829ec8SRene Gollent Rage128_DPMSCapabilities(void)
2380829ec8SRene Gollent {
2480829ec8SRene Gollent 	// Return DPMS modes supported by this device.
2580829ec8SRene Gollent 
2680829ec8SRene Gollent 	return B_DPMS_ON | B_DPMS_STAND_BY | B_DPMS_SUSPEND | B_DPMS_OFF;
2780829ec8SRene Gollent }
2880829ec8SRene Gollent 
2980829ec8SRene Gollent 
3080829ec8SRene Gollent uint32
Rage128_GetDPMSMode(void)3180829ec8SRene Gollent Rage128_GetDPMSMode(void)
3280829ec8SRene Gollent {
3380829ec8SRene Gollent 	// Return the current DPMS mode.
3480829ec8SRene Gollent 
3580829ec8SRene Gollent 	uint32 tmp = INREG(R128_CRTC_EXT_CNTL);
3680829ec8SRene Gollent 	uint32 mode;
3780829ec8SRene Gollent 
3880829ec8SRene Gollent 	if( (tmp & R128_CRTC_DISPLAY_DIS) == 0 )
3980829ec8SRene Gollent 		mode = B_DPMS_ON;
4080829ec8SRene Gollent 	else if( (tmp & R128_CRTC_VSYNC_DIS) == 0 )
4180829ec8SRene Gollent 		mode = B_DPMS_STAND_BY;
4280829ec8SRene Gollent 	else if( (tmp & R128_CRTC_HSYNC_DIS) == 0 )
4380829ec8SRene Gollent 		mode = B_DPMS_SUSPEND;
4480829ec8SRene Gollent 	else
4580829ec8SRene Gollent 		mode = B_DPMS_OFF;
4680829ec8SRene Gollent 
4780829ec8SRene Gollent 	TRACE("Rage128_DPMSMode() mode: %d\n", mode);
4880829ec8SRene Gollent 	return mode;
4980829ec8SRene Gollent }
5080829ec8SRene Gollent 
5180829ec8SRene Gollent 
5280829ec8SRene Gollent status_t
Rage128_SetDPMSMode(uint32 dpmsMode)5380829ec8SRene Gollent Rage128_SetDPMSMode(uint32 dpmsMode)
5480829ec8SRene Gollent {
5580829ec8SRene Gollent 	// Set the display into one of the Display Power Management modes,
5680829ec8SRene Gollent 	// and return B_OK if successful, else return B_ERROR.
5780829ec8SRene Gollent 
5880829ec8SRene Gollent 	SharedInfo& si = *gInfo.sharedInfo;
5980829ec8SRene Gollent 
6080829ec8SRene Gollent 	TRACE("Rage128_SetDPMSMode() mode: %d, display type: %d\n", dpmsMode, si.displayType);
6180829ec8SRene Gollent 
6280829ec8SRene Gollent 	int mask = (R128_CRTC_DISPLAY_DIS
6380829ec8SRene Gollent 				| R128_CRTC_HSYNC_DIS
6480829ec8SRene Gollent 				| R128_CRTC_VSYNC_DIS);
6580829ec8SRene Gollent 
6680829ec8SRene Gollent 	switch (dpmsMode) {
6780829ec8SRene Gollent 		case B_DPMS_ON:
6880829ec8SRene Gollent 			// Screen: On; HSync: On, VSync: On.
6980829ec8SRene Gollent 			OUTREGM(R128_CRTC_EXT_CNTL, 0, mask);
7080829ec8SRene Gollent 			break;
7180829ec8SRene Gollent 
7280829ec8SRene Gollent 		case B_DPMS_STAND_BY:
7380829ec8SRene Gollent 			// Screen: Off; HSync: Off, VSync: On.
7480829ec8SRene Gollent 			OUTREGM(R128_CRTC_EXT_CNTL,
75*4c9da6dcSStephan Aßmus 				R128_CRTC_DISPLAY_DIS | R128_CRTC_HSYNC_DIS, mask);
7680829ec8SRene Gollent 			break;
7780829ec8SRene Gollent 
7880829ec8SRene Gollent 		case B_DPMS_SUSPEND:
7980829ec8SRene Gollent 			// Screen: Off; HSync: On, VSync: Off.
8080829ec8SRene Gollent 			OUTREGM(R128_CRTC_EXT_CNTL,
81*4c9da6dcSStephan Aßmus 				R128_CRTC_DISPLAY_DIS | R128_CRTC_VSYNC_DIS, mask);
8280829ec8SRene Gollent 			break;
8380829ec8SRene Gollent 
8480829ec8SRene Gollent 		case B_DPMS_OFF:
8580829ec8SRene Gollent 			// Screen: Off; HSync: Off, VSync: Off.
8680829ec8SRene Gollent 			OUTREGM(R128_CRTC_EXT_CNTL, mask, mask);
8780829ec8SRene Gollent 			break;
8880829ec8SRene Gollent 
8980829ec8SRene Gollent 		default:
9080829ec8SRene Gollent 			TRACE("Invalid DPMS mode %d\n", dpmsMode);
9180829ec8SRene Gollent 			return B_ERROR;
9280829ec8SRene Gollent 	}
9380829ec8SRene Gollent 
9480829ec8SRene Gollent 	if (si.displayType == MT_LAPTOP) {
9580829ec8SRene Gollent 		uint32 genCtrl;
9680829ec8SRene Gollent 
9780829ec8SRene Gollent 		switch (dpmsMode) {
9880829ec8SRene Gollent 			case B_DPMS_ON:
9980829ec8SRene Gollent 				genCtrl = INREG(R128_LVDS_GEN_CNTL);
10080829ec8SRene Gollent 				genCtrl |= R128_LVDS_ON | R128_LVDS_EN | R128_LVDS_BLON | R128_LVDS_DIGON;
10180829ec8SRene Gollent 				genCtrl &= ~R128_LVDS_DISPLAY_DIS;
10280829ec8SRene Gollent 				OUTREG(R128_LVDS_GEN_CNTL, genCtrl);
10380829ec8SRene Gollent 				break;
10480829ec8SRene Gollent 
10580829ec8SRene Gollent 			case B_DPMS_STAND_BY:
10680829ec8SRene Gollent 			case B_DPMS_SUSPEND:
10780829ec8SRene Gollent 			case B_DPMS_OFF:
10880829ec8SRene Gollent 				genCtrl = INREG(R128_LVDS_GEN_CNTL);
10980829ec8SRene Gollent 				genCtrl |= R128_LVDS_DISPLAY_DIS;
11080829ec8SRene Gollent 				OUTREG(R128_LVDS_GEN_CNTL, genCtrl);
11180829ec8SRene Gollent 				snooze(10);
11280829ec8SRene Gollent 				genCtrl &= ~(R128_LVDS_ON | R128_LVDS_EN | R128_LVDS_BLON | R128_LVDS_DIGON);
11380829ec8SRene Gollent 				OUTREG(R128_LVDS_GEN_CNTL, genCtrl);
11480829ec8SRene Gollent 				break;
11580829ec8SRene Gollent 
11680829ec8SRene Gollent 			default:
11780829ec8SRene Gollent 				TRACE("Invalid DPMS mode %d\n", dpmsMode);
11880829ec8SRene Gollent 				return B_ERROR;
11980829ec8SRene Gollent 		}
12080829ec8SRene Gollent 	}
12180829ec8SRene Gollent 
12280829ec8SRene Gollent 	if (gInfo.sharedInfo->displayType == MT_DVI) {
12380829ec8SRene Gollent 		switch (dpmsMode) {
12480829ec8SRene Gollent 			case B_DPMS_ON:
12580829ec8SRene Gollent 				OUTREG(R128_FP_GEN_CNTL, INREG(R128_FP_GEN_CNTL)
12680829ec8SRene Gollent 					| (R128_FP_FPON | R128_FP_TDMS_EN));
12780829ec8SRene Gollent 				break;
12880829ec8SRene Gollent 
12980829ec8SRene Gollent 			case B_DPMS_STAND_BY:
13080829ec8SRene Gollent 			case B_DPMS_SUSPEND:
13180829ec8SRene Gollent 			case B_DPMS_OFF:
13280829ec8SRene Gollent 				OUTREG(R128_FP_GEN_CNTL, INREG(R128_FP_GEN_CNTL)
13380829ec8SRene Gollent 					& ~(R128_FP_FPON | R128_FP_TDMS_EN));
13480829ec8SRene Gollent 				break;
13580829ec8SRene Gollent 
13680829ec8SRene Gollent 			default:
13780829ec8SRene Gollent 				TRACE("Invalid DPMS mode %d\n", dpmsMode);
13880829ec8SRene Gollent 				return B_ERROR;
13980829ec8SRene Gollent 		}
14080829ec8SRene Gollent 	}
14180829ec8SRene Gollent 
14280829ec8SRene Gollent 	return B_OK;
14380829ec8SRene Gollent }
14480829ec8SRene Gollent 
145