ATX Power Supply: Pushbutton Control

Given that the GX270 case has a power pushbutton on the front panel, it seemed only reasonable to let it control the ATX power supply just like it used to. Most of the parts clumped in front of the panel’s ribbon cable handle that logic:

Low Voltage Interface Board - detail
Low Voltage Interface Board – detail

The pushbutton on the far left parallels the front-panel button so I don’t have to reach around the box just to turn it on.

The schematic shows the relevant bits:

LV Power Interface - Power Button
LV Power Interface – Power Button

The ATX +5 V Standby output remains turned on all the time, so I wired that to the power button’s yellow LED, to show that the plug is in the wall.

The pushbutton pulls the ATX Power_On line down, which turns on the supply outputs, which fires up the Arduino, which turns on the transistor, which holds the Power_On line down. D302 isolates the transistor from the button, so the code can sense the button’s on/off state with the power on. D303 isolates the Power_On line from the sense input to prevent the pullup on the Power_On line from back-powering the Arduino through its input protection diodes when the power is off.

The Arduino code starts by arranging the I/O states, turning the transistor on, pulsing the green power LED until until the button releases, then leaving the green LED on:

	pinMode(PIN_PWR_G,OUTPUT);
	digitalWrite(PIN_PWR_G,HIGH);				// visible on front panel

	pinMode(PIN_ENABLE_ATX,OUTPUT);				// hold ATX power supply on
	digitalWrite(PIN_ENABLE_ATX,HIGH);

	pinMode(PIN_ENABLE_AC,OUTPUT);				// turn on AC power
	digitalWrite(PIN_ENABLE_AC,HIGH);

	pinMode(PIN_BUTTON_SENSE,INPUT_PULLUP);		// wait for power button release
	while (LOW == digitalRead(PIN_BUTTON_SENSE)) {
		delay(50);
		TogglePin(PIN_PWR_G);					// show we have control
	}
	digitalWrite(PIN_PWR_G,HIGH);

Every time around the main loop, this chunk of code checks the button input:

	if (LOW == digitalRead(PIN_BUTTON_SENSE)) {
		printf("Shutting down!\r\n");
		digitalWrite(PIN_ENABLE_AC,LOW);
		digitalWrite(PIN_ENABLE_ATX,LOW);
		while(true) {
			delay(20);
			TogglePin(PIN_PWR_G);				// show we have shut down
		}
	}

The never-ending loop blinks the green LED until the power goes down, which happens when the button releases. That terminates the loop with extreme prejudice., which is the difference between embedded programming and high-falutin’ Webbish stuff.

And it Just Worked the first time I fired it up…

One thought on “ATX Power Supply: Pushbutton Control

Comments are closed.