2 Attachment(s)
MCP3301 A/D converter SPI reading
Hi there,
I'm trying to read a 13 bits MCP3301 A/D converter who's output value should go from 0 to 8191.
Unfortunately, even if I can read something, it looks to be only the "upper half" of the expected full value.
Attachment 9580
Could I have a hardware (wiring) issue or is there something in my code that would be wrong?
Code:
' ====== DESCRIPTION ===============================================================================
' MCP3301: SPI 13Bits ADC
' ====== FUSES =====================================================================================
' PIC 16F690 Fuses - Internal oscillator (activate OSCCON register)
'@ __config _FCMEN_OFF &_IESO_OFF &_CPD_OFF &_WDT_OFF &_INTRC_OSC_NOCLKOUT &_BOR_OFF &_CP_OFF &_PWRTE_OFF &_MCLRE_OFF
#CONFIG
__config _FCMEN_OFF &_IESO_OFF &_CPD_OFF &_WDT_OFF &_INTRC_OSC_NOCLKOUT &_BOR_OFF &_CP_OFF &_PWRTE_OFF &_MCLRE_OFF
#ENDCONFIG
@ ERRORLEVEL -306
@ ERRORLEVEL -202
' ====== REGISTERS =================================================================================
' 76543210
OPTION_REG = %10000000 'PORT A&B Pull-Ups disabled (see WPUA & WPUB)
OSCCON = %01100000 'Internal RC set to 4MHZ
ANSEL = %00010100 'Select analog inputs Channels 0 to 7 (AN2 + AN4 selected)
ANSELH = %00000000 'Select analog inputs Channels 8 to 11
ADCON0 = %10000000 'A/D Module (Bit5:2 select channels 0:11)
ADCON1 = %00000000 'A/D control register
CM1CON0 = %00000000 'Comparator1 Module is OFF
CM2CON0 = %00000000 'Comparator2 Module is OFF
INTCON = %00000000 'INTerrupts CONtrol (TMR0 OFF)
TRISA = %00000100 'Set Input/Output (0 to 5)
PORTA = %00000000 'Ports High/Low (0 to 5)
TRISB = %00000000 'Set Input/Output (4 to 7)
PORTB = %00000000 'Ports High/Low (4 to 7)
TRISC = %00000001 'Set Input/Output (0 to 7)
PORTC = %00000000 'Ports High/Low (0 to 7)
' ====== DEFINES ===================================================================================
DEFINE OSC 4
DEFINE NO_CLRWDT 1 'Don't waste cycles clearing WDT
DEFINE HSER_CLOERR 1 'Automatic clear overrun error
DEFINE SHIFT_PAUSEUS 100
' ====== VARIABLES =================================================================================
SD var PORTB.4 'SPI Data pin
CS var PORTB.5 'SPI Chip Select
SCK var PORTB.6 'SPI Clock pin
Serial_Out VAR PORTB.7
Mode Var WORD
MCP3301 Var WORD
' ====== INITIALIZE VARIABLES ======================================================================
CS = 1
Mode = 84 'serial com
MCP3301 = 0
' ====== PROGRAM ===================================================================================
MAIN:
CS = 0 'initiate 3301 comm
SHIFTIN SD,SCK,1,[MCP3301\13] 'shift 13 bits of data in, lowest bit first
CS = 1 'stop 3301 comm
Serout2 Serial_Out,Mode,["MCP3301: ", BIN13 MCP3301," - ", DEC4 MCP3301,13,10]
PAUSE 1000
GOTO MAIN
END
Re: MCP3301 A/D converter SPI reading
according to the data sheet the data read is 12 data bits + sign bit
1 Attachment(s)
MCP3301 A/D converter SPI reading
Really?
Attachment 9582
I don't get it :frown:
2 Attachment(s)
Re: MCP3301 A/D converter SPI reading
i'm looking at the data sheet you posted, that's what i see
Attachment 9583
Attachment 9584
Re: MCP3301 A/D converter SPI reading
Keep reading. It's a 13-bit differential converter.
From the datasheet section 5.1:
Quote:
and the device uses the collected charge to produce a serial 13-bit binary two’s complement output code.
So that's 12 bits of data + sign. See Section 6.1.
Re: MCP3301 A/D converter SPI reading
Okay then, didn't see that one 😵
So I'll get a 12 bits "value" and the last bit will indicate either "+" or "-", right?
Re: MCP3301 A/D converter SPI reading
Quote:
the last bit will indicate either "+" or "-", right?
if by last bit you mean the msb then yes
not forgetting its a 13-bit binary two’s complement number
MCP3301 A/D converter SPI reading
Quote:
not forgetting its a 13-bit binary two’s complement number
...and that means what exactly please? :confused:
Re: MCP3301 A/D converter SPI reading
Your ADC is differential one. So, that means it can convert positive and also negative (in relation to the two inputs + and -) voltages.
If the + input is more positive than the - input of the converter then the output will be a plain 12 bit binary number.
But if the - input is more positive than the + input, then as you can understand the result of the ADC should be negative. This is shown in binary with the most significant bit (MSB) of the value being 1. That is the sign bit.
But the rest of the 12 bits follow a specific rule then. All bits are reversed and also -1.
For example, 1 1111 1111 1111 means negative number and this number is the reverse of 1111 1111 1111 plus one, or just 1. So in total -1.
Or, 1 0000 1111 0000 is also negative and the value is -3856
Hope this clear a bit of the mud!
Ioannis
More here https://www.cs.cornell.edu/~tomf/not.../twoscomp.html
1 Attachment(s)
MCP3301 A/D converter SPI reading
Thanks Ioannis and sorry for the late reply,
So, if I would connect GND to the "-" input and measure i.e. a + signal from 0 to 5 Volts, I should have as 12 bits result, right?
Quote:
Or, 1 0000 1111 0000 is also negative and the value is -3856
This is confusing to me. I get the positive and negative thing but I can't figure out how you come to this 3856 number?
Attachment 9594
1 Attachment(s)
Re: MCP3301 A/D converter SPI reading
to expand a 13 bit negative two's complement number to a 16 bit number bits 13,14 an 15 need to be set accordingly
in general the "sign bit" needs to be extended to the new width
so 1 0000 1111 0000 becomes 1111 0000 1111 0000 qed -3856
Attachment 9595
Re: MCP3301 A/D converter SPI reading
Yes, Richard is correct. I forgot to mention you have to adjust the value to the byte, word or whatever width you have.
So the sign is the left most bit but the rest should also be 1. Remember we reverse the bits to get the absolute value disregarding the left most, sign bit.
Seems confusing at first, but has its logic.
Ioannis
MCP3301 A/D converter SPI reading
Got it now!
Thanks a lot :wink:
Re: MCP3301 A/D converter SPI reading
Quote:
Remember we reverse the bits to get the absolute value disregarding the left most, sign bit
To convert a 2's compliment negative value to a positive number, invert all the bits (NOT) and add 1.
For example 2's compliment -1 = FFFF
invert = 0000, add 1 = 0001
Re: MCP3301 A/D converter SPI reading
I was reffering to the left most bits but yes. Absolutely correct, to convert a positive to negative after reversing all bits you add one.
Ioannis