// © RiceMotion ( Robert Carl Rice ) 2012-2016 - All rights reserved


// This software makes use of tools and libraries obtained from open source projects or released for

// use by relevant hardware manufactures. However, this software is NOT a part of any open source project.

// It is released only on a "need to know" basis for beta testers of the "RiceCNC Interpolation Engine".

// Recipents of this source code must respect the confidential nature of this software and prevent any

// distribution that could result in counterfeit copies of the "RiceCNC Interpolation Engine".


// © RiceMotion ( Robert Carl Rice ) 2012-2016 - All rights reserved

#include <AnalogPin.h>

#include <Timers.h>

#include <ADC.h>

#include <Spindle.h>

#include <MainCommands.h>


// derived classes


#include "inc/hw_adc.h"

#include "driverlib/adc.h"

#include <inc/hw_gpio.h>


//#define DebugDelete 1


AnalogPin::AnalogPin (

     char*          data,

     String*          msgPtr )


     :     GpioPin(

          data,

          msgPtr ) {


     nextAnalogPin          = NULL;

     aid                         = NULL;

     reportedAnalogValue     = 0;

     softwareOvesampling     = activeMode - '0';

     enabled                    = true;


     if ( valid() ) {

          fmtPin( msgPtr );


          for (     int index = 0;

                    index < AnalogTableLength;

                    index++ ) {


               AnalogChannelPins* tableAid = &AnalogChannel[ index ];

               if (     tableAid->port     == portC

                    &&     tableAid->pin     == pin ) {

                    

                    aid          = tableAid;

                    break; }; };


          if ( aid ) { // Analog

               ROM_SysCtlPeripheralEnable( SYSCTL_PERIPH_ADC0 );

               ROM_SysCtlPeripheralEnable( SYSCTL_PERIPH_ADC1 );


               ROM_GPIOPinTypeADC( gpioBase, mask );

               ADC::addAnalogPin( this );


               *msgPtr

                    += " ok"; }


          else

               *msgPtr

                    += " invalid"; }; };



AnalogPin::~AnalogPin() {


#ifdef DebugDelete

     Serial.println( " delete AnalogPin" );

#endif


     if ( aid ) // Analog

          ADC::removeAnalogPin( this ); };


void

     AnalogPin::fmtPin( String* msgPtr ) {


     char data[30];

     snprintf( data, 30,

          " P%c%d sw over-sample %d",

          portC,

          pin,

          1 << softwareOvesampling );


     *msgPtr += String( data ); };


void

     AnalogPin::reportAnalog( String* msgPtr ) {


     if ( aid ) {

          uint32_t currentValue = analogValue();

          if ( currentValue != reportedAnalogValue ) {

               reportedAnalogValue = currentValue;


               char data[8];

               snprintf( data, 8,

                    " %c%d %d",

                    portC,

                    pin,

                    analogValue() );

               *msgPtr  += String( data ); }; }; };


void

     AnalogPin::averageSample(     uint32_t sample ) {


     if ( enabled ) {

          analogAverage     -= analogAverage >> softwareOvesampling;

          analogAverage     += sample << 10; }; }; // sample is 12 bits


uint32_t

     AnalogPin::analogValue() {


     return

          analogAverage >> softwareOvesampling + 10; };