Thursday, February 26, 2015

Time to checkout the Magic Smoke!

I have finished assembling a solar MPPT controller - here are a couple photos:

I really should not have the camera THAT close.
Those Caps look like towers!
Have also been working to clean up the Arduino IDE and the port of the ATmega64M1 CPU.  I think I have most things fixed and will post corrections as I continue the debugging effort.  A bit on that: the porting is to the IDE version 1.0.5 / 1.0.6.   Arduino just released their 'updated' IDE v 1.6.0, and it will be much better - mostly because it uses an updated version of AVRDUDE and the GCC compiler - providing native support for the ATmegaxxM1 series of CPUs.   However, there has been some large changes in the support files - specifically around the hardware serial port, and it will take me some time to work though that all.  So for now, I am continuing my efforts under the 1.0.x line of the IDE.

Just last night I moved to start some live testing using the Solar Panels on Viking Star.  It is perhaps a good time to do this as the weather has changed, and our overcast winter sky's limit the panels output.  So far results tell me there is still a bit of work to do.  Am not happy with the +12v boost power source, and have worked though a fuse or two already...

But will carry on, and see what all I can get working.

Tuesday, February 24, 2015

More on ATmega32M1 and ATmega64M1 support with Arduino IDE

This morning I have posted up a refreshed set of 'files' to enable the ATmega64M1 uC in the Arduino IDE.  See 'Arduino Libs' resource tab above.  Specifically I have made edits to pins.h, and the wiring.c files scrubbing port names and how they are handled.  I also desk-confirmed the macro's needed to support software serial.  At this time I have touched a good portion of the Arduino IDE stack, and think most is 'ported' in support of the Arduino IDE - the two areas I have not touched, but perhaps will work fine due to how things are written, is the basic PWM and timing functions.

If you have downloaded the porting files before, you should do it again as there has been some significant corrections made in the area of how port names and numbers are defined.

I have also expanded the supported variants to include:  8Mhz, and 16Mhz external crystals, and an 8Mhz internal oscillator variant.  

All these changes are in support of the Arduino IDE version 1.0.x.  Going forward, I am working to bring up the SmartMPPT controller and as I find issues I will continue to update these files.  I also want to make a set of files targeting the new 1.6.x series of Arduino IDE's  as that will simplify things given their usage of more current compilers and ARVDUDE and as a result better native support of the ATmegaxxM1 uC's.  However, there are some major changes which have been done and porting to the new environment will take some time.

Monday, February 9, 2015

Expanding Arduino analogRead() and pinMode() to support the differential inputs on the ATmega32M1 / ATmega64M1

A nice feature of the Atmega32M1 / ATmega64M1 line of uC's is the addition of a differential input amplifier as one of the options for the ADC.  No longer must one take two measurements and subtract them in software, the 'op-amp' can do it for us.  Plus these differential inputs have a selectable gain from 5x to 40x.

On the Solar MPPT controller I use this capability to measure the battery and solar panel currents via a simple low ohm resistor.  Add in a small RC low-pass filter, and that is all that is needed...  (Using the ATmega32M1 uC allowed me to remove several other components typically used in other approaches, current measurement being one of those areas).

There are three differential channels: 0, 1, and 2.  I have extended the Arduino IDE's wiring_analog.c to recognize three new 'virtual ports'**:  AD0, AD1, and AD2.   Reading the value of these differential analog ports one simply uses the oh so familiar analogRead() function, example:

    solarAmpsRaw = analogRead(AD2);       // Read raw value of Solar Amp Shunt.

pinMode() has also been modified to recognize AD0, AD1, and AD2, with a slight change:  the 2nd parameter no longer specifies a 'mode' - as differential reads are always input.  Now the 2nd parameter is used to specific the amplifier gain to be used:  GAIN5, GAIN10, GAIN20, GAIN40

  pinMode(AD2, GAIN40);                 // Enable diff-amp #2, with gain of 40x

** Do take note that when enabling the 'virtual' differential analog inputs, two actual hardware ports are repurposed:

  • AD0 returned results of:  (  D9 - D8)   * gain
  • AD1 returned results of:  (  A3 - A4)   * gain
  • AD2 returned results of:  (D10 - A6)   * gain

Summary of changes:

  1. analogRead() expanded to recognize differential virtual ports AD0, AD1, and AD2
  2. pinMode() expanded to enable AD0, AD1, AD2 and set the gain with: GAIN5, GAIN10, GAIN20 or GAIN40.

An example sketch:

#define SOL_AMPS_CHAN AD2               // ADC channel to read solar amps
                                        //  (Differential channel #2)
#define SOL_AMPS_SCALE (1/(40 * 0.002)) // Channel gain of 40x, 2mOhm shunt

void setup() {
   Serial.begin(9600);                  // open the serial port at 9600 bps:
   pinMode (SOL_AMPS_CHAN, GAIN40);     // Set up the differential channels.

void loop() {
  Serial.print(" Solar Amps are now: ");
  Serial.println(analogRead(SOL_AMPS_CHAN)*(int)(SOL_AMPS_SCALE  * 5/1024));
                                       //read and convert Solar Amps

Saturday, February 7, 2015

Turning the PCB - and Arduino internal ADC accuracy

I have found enough errata to want to do a turn of the PCB.  v0.0.2 was send to OSHPark Thursday, as with a Mouser order.  Should have them in in a couple of week.  I will work on porting Tom Nolan's simple MPPT software (  to the SmartMPPT controller in preparation.  v0.0.2 has several changes, including:
  • Corrected SMT footprints
  • Cost reduced power supply, USB designs.
  • Removal of SERVICE port (functions could be accessed via ICSP port)
  • Improved voltage sampling buffering ckt - removal of offset errors in op-amps
Overall cleanup of board, and improvement in tight Hi/Low FET layout.

One area I struggled with a little was the voltage sensing design - based around using the Arduino's built in A/D.   In short - how much $ vs. desired accuracy?   One might noticed I backed off from the 0.1% resistors in the voltage divider, and now just use 1% devices.  This saved about $1 in BOM cost.  And here was my thinking:   The ATmega32M1 is able to selected one of two sources for its A/D converter reference:  External (Vaa, or +5 in this design), or an internal 2.56 source.   And there is the basic issue.  The internal source is known to be rather stable over time and temperature, but not all that accurate (2.5-5% or so).  Using Vaa tied to +5, even with the filtering, can present a significant error its self (And is dependent on the accuracy fo the +5 supply to boot).

All told, using high precision components in the op-amp ckt seemed kind of like putting silk on a pig's ear.  Additional cost could have been added by adding an external voltage reference (i.e. LM4040) - but I think even then we would not know the BATTERIES voltage, only what we see at the output of the MPPT controller.

So, I have  backed off - and accept a few % error in absolute accuracy for voltage readings, but still look for stability.  As far as the MPPT logic is concerned, it is trying to maximize a value - and it really does not care too much how accurate that value is, just that it is repeatable.

For accurate battery voltage information, to say decide charging states and accommodate voltage drops over the battery cables, will look to the CAN BMS device attached via a simple CAT-5 cable.