Jump to content
43oh

Another MSP430 Binary Clock


Recommended Posts

I saw this project hit Hackaday http://hackaday.com/2011/10/13/build-a-binary-wall-clock-for-just-a-few-bucks/ a few weeks ago and was inspired to make my own with a Launchpad. So, last night I got out the leds, resistors and a launchpad and made it happen. I'm only using one button to increment minutes and just setting the time via the debugger for now.

 

I know others on here have made a binary clock (@sugaraddict), but I did this one with nothing but the LP, resistors and LEDs using all I/O of a G2553 and no shift registers.

 

[attachment=0]binary_rtc.png[/attachment]

 

/****************************************************************/
/* Greg Whitmore						*/
/* greg@gwdeveloper.net						*/
/* www.gwdeveloper.net						*/
/****************************************************************/
/* released under the "Use at your own risk" license		*/
/* use it how you want, where you want and have fun		*/
/* debugging the code.						*/
/* MSP430G2553 Real Time Binary Clock				*/
/****************************************************************/

#include 

int sec, min, hour;
int minOnesPlace, minTensPlace, hourOnesPlace, hourTensPlace;

void BCS_init(void);
void WDT_init(void);
void GPIO_init(void);
void TA0_init(void);

void main(void)
{
BCS_init();
WDT_init();
GPIO_init();
TA0_init();

   __enable_interrupt();           // Set global interrupt enable

   // set initial time
   sec = 0;
   min = 30;
   hour = 4;

while (1)
{
	LPM3;						// enter lowest power module with ACLK active

	if (sec > 59)				// check seconds; increase minutes if needed
	{
		sec = 0;
		min++;
	}
	if (min > 59)			// check minutes; increase hours if needed
	{
		min = 0;
		hour++;
	}
	if (hour == 24)		// check 24 hour clock; rollover if needed
	{
		hour = 0;
	}

	// split minutes and hours to ones and tens place values
	minOnesPlace = min % 10;
		switch(minOnesPlace)
		{
			case 0: P1OUT &= ~(BIT4 + BIT5 + BIT6+ BIT7); break;
			case 1: P1OUT |= BIT4; 
					P1OUT &= ~(BIT5 + BIT6 + BIT7); break;
			case 2: P1OUT |= BIT5;
					P1OUT &= ~(BIT4 + BIT6 + BIT7); break;
			case 3: P1OUT |= (BIT4 + BIT5);
					P1OUT &= ~(BIT6 + BIT7); break;
			case 4: P1OUT |= BIT6;
					P1OUT &= ~(BIT4 + BIT5 + BIT7); break;
			case 5: P1OUT |= (BIT4 + BIT6);
					P1OUT &= ~(BIT5 + BIT7); break;
			case 6: P1OUT |= (BIT5 + BIT6);
					P1OUT &= ~(BIT4 + BIT7); break;
			case 7: P1OUT |= (BIT4 + BIT5 + BIT6);
					P1OUT &= ~(BIT7); break;
			case 8: P1OUT |= BIT7;
					P1OUT &= ~(BIT4 + BIT5 + BIT6); break;
			case 9: P1OUT |= (BIT4 + BIT7);
					P1OUT &= ~(BIT5 + BIT6); break;
			default: break;
		}		
	minTensPlace = (min / 10) % 10;
		switch(minTensPlace)
		{
			case 0: P1OUT &= ~(BIT0 + BIT1 + BIT2); break;
			case 1: P1OUT |= BIT2;
					P1OUT &= ~(BIT0 + BIT1); break;
			case 2: P1OUT |= BIT1;
					P1OUT &= ~(BIT0 + BIT2); break;
			case 3: P1OUT |= (BIT2 + BIT1);
					P1OUT &= ~(BIT0); break;
			case 4: P1OUT |= BIT0;
					P1OUT &= ~(BIT2 + BIT1); break;
			case 5: P1OUT |= (BIT2 + BIT0);
					P1OUT &= ~(BIT1); break;
			default: break;
		}	
	hourOnesPlace = hour % 10;
		switch(hourOnesPlace)
		{
			case 0: P2OUT &= ~(BIT2 + BIT3 + BIT4 + BIT5); break;
			case 1: P2OUT |= BIT2;
					P2OUT &= ~(BIT3 + BIT4 + BIT5); break;
			case 2: P2OUT |= BIT3;
					P2OUT &= ~(BIT2 + BIT4 + BIT5); break;
			case 3: P2OUT |= (BIT2 + BIT3);
					P2OUT &= ~(BIT4 + BIT5); break;
			case 4: P2OUT |= BIT4;
					P2OUT &= ~(BIT2 + BIT3 + BIT5); break;
			case 5: P2OUT |= (BIT2 + BIT4);
					P2OUT &= ~(BIT3 + BIT5); break;
			case 6: P2OUT |= (BIT3 + BIT4);
					P2OUT &= ~(BIT2 + BIT5); break;
			case 7: P2OUT |= (BIT2 + BIT3 + BIT4);
					P2OUT &= ~(BIT5); break;
			case 8: P2OUT |= BIT5;
					P2OUT &= ~(BIT2 + BIT3 + BIT4); break;
			case 9: P2OUT |= (BIT2 + BIT5);
					P2OUT &= ~(BIT3 + BIT4); break;
			default: break;
		}
	hourTensPlace = (hour / 10) % 10;
		switch(hourTensPlace)
		{
			case 0: P2OUT |= (BIT0 + BIT1); break;
			case 1: P2OUT |= BIT1;
					P2OUT &= ~(BIT0); break;
			case 2: P2OUT |= BIT0;
					P2OUT &= ~(BIT1); break;
			default: break;
		}
}
}

// clock init for 32.768kHz operation from XT1
void BCS_init(void)
{
   BCSCTL2 = SELM_0 + DIVM_0 + DIVS_0;		// dco; /1; /1

   if (CALBC1_1MHZ != 0xFF)
   {
       DCOCTL = 0x00;
       BCSCTL1 = CALBC1_1MHZ;      		// calibrated 1MHz
       DCOCTL = CALDCO_1MHZ;
   }

   BCSCTL1 |= XT2OFF + DIVA_0;				// XT2 off; /1

   BCSCTL3 = XT2S_0 + LFXT1S_0 + XCAP_1;	// 32.768kHz crystal; ~6pf load
}

// wdt init as interval timer; used for debouncing S1
void WDT_init(void)
{
   WDTCTL = WDTPW + WDTTMSEL + WDTSSEL + WDTIS1;	// interval timer; aclk

   IFG1 &= ~(WDTIFG);		// clear WDT flags
   IE1 |= WDTIE;			// enable WDT interrupt
}

// gpio init
void GPIO_init(void)
{
// setup push button; edge interrupt; clear port 1 flags
   P1OUT = BIT3;
   P1REN = BIT3;
P1IES = BIT3;
   P1IE = BIT3;
   P1IFG = 0;

   // led outputs
   P1DIR = BIT0 + BIT1 + BIT2 + BIT4 + BIT5 + BIT6 + BIT7;
   P2DIR = BIT0 + BIT1 + BIT2 + BIT3 + BIT4 + BIT5;
   P2OUT = 0;
}

void TA0_init(void)
{
   TA0CCTL0 = CM_0 + CCIS_0 + OUTMOD_5 + CCIE;		// no capture; CCI0A; PWM reset

   TA0CCR0 = 32767;

   TA0CTL = TASSEL_1 + ID_0 + MC_1;				// aclk source; /1; up mode
}

// push button ISR
#pragma vector=PORT1_VECTOR
__interrupt void add_time_isr(void)
{
   P1IFG &= ~BIT3;
   P1IE &= ~BIT3;

   // wdt interval as debouncer
   IFG1 &= ~WDTIFG;
   WDTCTL = (WDTCTL & 7) + WDTCNTCL  + WDTPW + WDTTMSEL;
   IE1 |= WDTIE;

   // increase minute counter
   min++;
}

// timerA isr; interrupt every 1 sec
#pragma vector=TIMER0_A0_VECTOR
__interrupt void ta_1sec_isr(void)
{
sec++;		// increase seconds counter
LPM3_EXIT;
}

// wdt isr clear port 1 interrupt flags
#pragma vector=WDT_VECTOR
__interrupt void wdt_isr(void)
{
   IE1 &= ~WDTIE;

   P1IFG &= ~BIT3;
   P1IE |= BIT3;
}

 

Not sure of the final accuracy as the battery I was using to test it overnight, died.

Link to post
Share on other sites

Join the conversation

You can post now and register later. If you have an account, sign in now to post with your account.

Guest
Reply to this topic...

×   Pasted as rich text.   Paste as plain text instead

  Only 75 emoji are allowed.

×   Your link has been automatically embedded.   Display as a link instead

×   Your previous content has been restored.   Clear editor

×   You cannot paste images directly. Upload or insert images from URL.

×
×
  • Create New...