/**********
 This program coordinates SH-1 EVB activities for the direct digital
 amplifier, also known as the class-D amplifier.

 cd1.c                       Andrew Huang            San Diego, CA
***********/
/* Last modified by bunnie@burrow.mit.edu Sun Aug 11 19:03:55 1996 */

#include "iosh7030.h"
#include "montraps.h"

#define IS   ==
#define AINT !=
#define AND  &&
#define OR   ||

#define HACKING 1
#define FUN     1

/* initial GRA3 and GRB3 values */
#define TOP  (unsigned int) 0x0FF
#define BOT  (unsigned int) 0x007F

#define LRCK_MASK 0x02

/* globals */

typedef void (*Function) ();

CMONtrap (a1,a2,a3)
{
  asm ("trapa #33");               /* args are passed implicitly */
}

/* function attribute declaration */
void exit() __attribute__ ((noreturn)); 

void exit()
{
  CMONtrap (CMON_EXIT, 0);         /* trap exit to monitor, rnt status = 0 */
}

void loop()
{ /* loop */
  /* locals */
  unsigned short Adata;
  unsigned short Bdata;
  int lrck_state;

  /* body */
  /* bit 0 is output */
  /* BCLK is bit 1, mask 0x02 */
  /* SIN is bit 2, mask 0x04 */
  /* LRCK is bit 3, mask 0x08 */

  lrck_state = 0;
  while( HACKING IS FUN ) {
    Adata = PADR;               /* get new PADR value */
    if( (PADR & LRCK_MASK) ) {  /* if LRCK is 1 */
      if( lrck_state IS 0 ) {   /* if this is a rising edge */
        lrck_state = 1;         /* update state */

        Bdata = PADR;           /* get the data */
        Bdata >>= 8;            /* shift it down so we can use it */
        Bdata &= 0xFF;          /* mask only lower 8 bits */
      if( Bdata < 0x80 ) {      /* do 2's complement bipolor to unipolar */
        Bdata += 0x80;        /* conversion */
      } /* if */
      else {
        Bdata -= 0x80;
      } /* else */
      Bdata &= 0xFF;          /* mask it again just for safety */

      ITU_BRB3 = (unsigned int) Bdata;  /* load the data in */

      } /* if */   /* else lrck_state is 0...don't do anything now! */
    } /* if */
    else {
      lrck_state = 0;   /* else LRCK must be 0, don't do anything */
    } /* else */
  } /* while 1 */

} /* loop */


void main()
{ /* main */
  /* locals */
  int i;
  unsigned char cycle;

  /* body */
  PFC_PBIOR &= ~0x0004;  /* setup PB to do TIOCA3 PWM output */
  PFC_PBIOR |= 0x04;
  PFC_PBCR2 &= 0x0000;
  PFC_PBCR2 |= 0x0020;
  

  CMONtrap(CMON_PUTSTR, CMON_PORTB, "\nSetting up CD interface...\n");
  PFC_PAIOR &= 0x0000;  /* clear paior */
  PFC_PAIOR |= 0x0001;  /* pwm output */

  PFC_PACR2 &= 0xFF03;  /* PA1, PA2, PA3 I/O pins */
  PFC_PACR1 &= 0x0000;  /* PA8-15 are inputs */

  CMONtrap(CMON_PUTSTR, CMON_PORTB, "\nSetting up PWM...\n");
  /* we will use channel 3 in PWM mode--it supports buffering */
  
  /* step 1: select counter clock */
  /* step 2: select counter clear source */
  /* bit pattern is 0bX0100000 */
  /* sets up clear by GRA, count rising and falling edges, internal clock, 
     no subdiv */

  ITU_TCR3 |= 0x20;

  /* step 3: set GRA */
  ITU_GRA3 = TOP;
  ITU_BRA3 = TOP;
  
  /* step 4: set GRB */
  ITU_GRB3 = BOT;
  ITU_BRB3 = BOT;

  /* step 5: select PWM mode */
  ITU_TMDR = 0x08;        /* bit one selects channel 3 PWM mode */
  
  /* select buffer mode */
  ITU_TFCR &= 0xCF;
  ITU_TFCR |= 0x02;       /* GRB3 BRB3 in buffer mode */

  /* step 6: start counting */
  ITU_TSTR |= 0x08;       /* bit one starts channel 3 counting */

  /* that should do it! */

  cycle = ITU_TSR3;       /* make sure its a-workin' */
  if( cycle & 0x01 )
    ITU_TSR3 &= 0xFE;     /* clear bit 0 */

  cycle = ITU_TSR3;
  if( cycle & 0x01 )
    CMONtrap(CMON_PUTSTR, CMON_PORTB, "\nProblems setting 
ITU_TSR3...\n");

  CMONtrap(CMON_PUTSTR, CMON_PORTB, "\nPWM has been set...\n");

  loop();   /* loop never returns */

  exit();

} /* main */

int __main() {  }         /* now required by compiler; see release notes */



