Shop OBEX P1 Docs P2 Docs Learn Events
ADC object works in one section of program, but not another section of same program??? — Parallax Forums

ADC object works in one section of program, but not another section of same program???

The following code displays a value of q = 357, verifying my ADC is working.
OBJ    
       fMath          : "Float32"
       PST              : "Parallax Serial Terminal"           'used for comments to debug   
       LcdSerial     : "FullDuplexSerialPlus"
       MCP3202    :  "MCP3202"
PUB Main   | localindex
      pst.Start(115_200)                                     'Start Parallax Serial Terminal
      fMath.start                                                 'Start Floating point Math
      InitDisplay                                                 'Zero out display                        
      MCP3202.start(dataio, clk, cs, %0011)
      waitcnt(80000 + cnt)
 ================================================      
      q  := MCP3202.in(0)
           PST.Str(String(pst#NL," q = "))  
           PST.dec(q)   
 ================================================    
repeat localIndex from 0 to 2                     'Initialize encoder status

        oldState[localIndex] := ina[pinA[localindex]..pinB[localIndex]]
        oldencstat := INA[18..23]



Yet when I use the same command in another method of the same program
PUB CalcSWR  | a,b,c,d,e,f,g,h,j,k,m,x,z,pwrmw,top,bot,ADCfwdin,ADCrefin
  
  PST.Str(String(pst#NL)) 
  PST.Str(String(pst#NL," CalcSWR "))
 
 'Tstart
           r := 0
          r2 := 0 
        
       repeat times                                     'sample forward and reflected voltages times      
==========================================================
           q  := MCP3202.in(0)
           PST.Str(String(pst#NL," q = "))  
           PST.dec(q) 
===========================================================               
               if q < floor                             'check to see if you still have signal, if not,
                 nstep := 0
                 return                                 'break sampling


I receive q = 0. I am at a total loss why MCP.in works one place in my program, but doesn't elsewhere. Can someone provide some clues where to look for the problem.
«1

Comments

  • well you have q not declared as a local, so it might be global and something else is clobbering it?

    Mike
  • Mike, I have declared q both local and global with same results. It appears that MCP3202 is not actually firing to take a reading. I think q is correct at 0. I don't understand why the call MCP3202.in(0) works in one method, but not another in the same program.

    Jim
  • JonnyMacJonnyMac Posts: 9,102
    edited 2020-03-05 03:07
    Is your new section in a different cog? If that's the case, and the MCP3202 code is not running a cog, there could be a problem with IO configuration. .
  • I agree, Do you the pins wired correctly for CS, Clk, Mosi, Miso etc.
  • Duane DegnDuane Degn Posts: 10,588
    edited 2020-03-05 04:09
    JonnyMac wrote: »
    Is your new section in a different cog? If that's the case, and the MCP3202 code is not running a cog, there could be a problem with IO configuration. .

    I second Jon's question.

    My guess is the MCP3202 object is controlling the I/O pins with Spin.

    You want to make sure the same cog which initializes the object is the cog to call the object.

    Edit: If you attach an archive of your code, we could examine it to see if the cog issue is the problem.

  • The same cog which initialized the object is calling the object. I have attached the complete program, which with your guidance Duane now works flawlessly. I cleaned up the structure and it ran as expected, but my ADC was a little slow with collecting and calculating between each encoder click. So I have moved to faster one, and plugged it into the working program. I stuck a statement to read the ADC right at start up in Main, and it reads a value at this point in execution, but when I use it again in PUB Calcswr, nothing.
  • There's a caveat in the datasheet that reads "* After completing the data transfer, if further clocks are applied with CS low, the A/D Converter will output zeros indefinitely." Is your MCP3202.in method pulling your CS line high after the first data read?
  • Duane DegnDuane Degn Posts: 10,588
    edited 2020-03-05 10:08
    An archive of your program will include all the objects in a zip file. To archive a program, first compile the program (press F9). The select File\Archive "AutoTuner II R9"\Project...

    Here's a screen grab of what to select after you've compiled the program.

    Archive.PNG

    You can attach the zip file in a similar way you attached the Spin file. This will let us see the complete program and run with our own hardware if desired.
    556 x 447 - 20K
  • CJMJ wrote: »
    There's a caveat in the datasheet that reads "* After completing the data transfer, if further clocks are applied with CS low, the A/D Converter will output zeros indefinitely." Is your MCP3202.in method pulling your CS line high after the first data read?

    My program does nothing to pull CS line high. But the attached demo does nothing to pull CS high, and it works. I can load this file into same setup on Prop, and it works. Unfortunately I know nothing about PASM, and MCP3202 is written with PASM, so I can't tell you if it is pulling CS high, but I assume so since the attached program works
  • Duane Degn wrote: »
    An archive of your program will include all the objects in a zip file. To archive a program, first compile the program (press F9). The select File\Archive "AutoTuner II R9"\Project...

    Here's a screen grab of what to select after you've compiled the program.

    Archive.PNG

    You can attach the zip file in a similar way you attached the Spin file. This will let us see the complete program and run with our own hardware if desired.

    Sorry Duane. Here is archive of program.
  • jcfjr wrote: »
    CJMJ wrote: »
    There's a caveat in the datasheet that reads "* After completing the data transfer, if further clocks are applied with CS low, the A/D Converter will output zeros indefinitely." Is your MCP3202.in method pulling your CS line high after the first data read?

    My program does nothing to pull CS line high. But the attached demo does nothing to pull CS high, and it works. I can load this file into same setup on Prop, and it works. Unfortunately I know nothing about PASM, and MCP3202 is written with PASM, so I can't tell you if it is pulling CS high, but I assume so since the attached program works

    I did take look at the PASM, and comments in program appear to handle this.
  • Duane DegnDuane Degn Posts: 10,588
    edited 2020-03-05 17:51
    It looks like the MCP 3202 being controlled from PASM so it should be safe to use from multiple cogs. It also looks like you're always calling the ADC object from the same cog as you initialized it so that wouldn't be a problem even if the I/O pins were controlled from Spin.

    What do you get from your initial ADC reading?

    I'd suggest adding a test loop just to make sure the ADC is behaving as expected.
    
          repeat
           
            zz  := MCP3202.in(0)
            PST.Str(String(pst#NL," zz = "))  
            PST.dec(zz)
            waitcnt(clkfreq / 2 + cnt)
    

    Use some code like the code above to make sure output from the ADC is what you expect. When you use a loop like this does the output behave as expected?
  • Initial ADC reading is reading 357, which is noise without a signal. This works as expected.

    Inserted your code, and yes, it repeatedly showed a value.

    Looping doesn't seem to be a problem, see my comment with code to CJMJ above. I can load this program into my setup, and it works all day in a loop.
  • What type of input are you monitoring with the MCP3202? I recall having trouble with a MCP3208 chip when I was attempting to monitor a line with too low of impedance.
    Here's a link to discussion of the issue. There's a lot of good advice in the replies.
  • I am monitoring output from the AD8307, a DC output, which is monitoring a RF frequency of about 3Mhz-30Mhz. I can run the demo program I sent previously , without any problems monitoring the output. I just can't understand why the call works in the beginning of my program, but not later. I am pretty sure it is something in the software.
  • I had trouble reading the output of a 10KΩ pot with the MCP3208. The output resistance of the AD8307 is even higher at 12.5KΩ. I think you're having the same problem discussed in the thread I linked in my last reply.
    You might need a voltage following buffer of some sort.
  • I read your thread on your issues with the 3208, but I don't think I have the same issue. I can hook up my MCP3202 to the AD8307, load up my demo program(attached), and it works great reading the voltages with the MCP3202.in command. I load up my main program AutotunerIIR9, use the same commands, and I get 0. So I stick the MCP3202.in command in at the begining of the program, and it reads a voltage, but when I try to read the same voltage through my Calcswr routine later in the program, it reads 0. So the hardware is working I believe., the MCP3203.in command is not working in my Calcswr method.
  • msrobotsmsrobots Posts: 3,709
    edited 2020-03-06 04:35
    @jcfjr,

    I scanned thru your file and found quite creative indention.

    Unlike C in spin the horizontal position is very important for the compiler.

    So my guess is that your formatting of the source does things you do not intend!

    First put a empty line above any PRI/PUB/VAR stuff like that.

    Next REALLY be careful to put statements into EXACTLY the same column it belongs following its previous one in the same indention.

    Else you shoot yourself in the foot.

    Enjoy!

    Mike

  • msrobots wrote: »
    Next REALLY be careful to put statements into EXACTLY the same column it belongs following its previous one in the same indention.

    I second Mike's advice.
    jcfjr wrote: »
    . . . I can hook up my MCP3202 to the AD8307, load up my demo program(attached), and it works great reading the voltages with the MCP3202.in command.

    That sounds very frustrating.

    One possible troubleshooting technique is to make the smallest program possible which recreates the problem.

    I'll try to take a look at your code some more when I have time.
  • rosco_pcrosco_pc Posts: 464
    edited 2020-03-06 18:35
    Try adding this line back into the repeat loop:
      waitcnt(4000000 + cnt)
    

    I think you're reading the ADC too fast
  • rosco_pc wrote: »
    Try adding this line back into the repeat loop:
      waitcnt(4000000 + cnt)
    

    I think you're reading the ADC too fast

    I added your pause, and it had no effect. I can read this chip this fast in a little demo program I worked up attached.
  • RaymanRayman Posts: 14,640
    Figure it out yet?
    If not...

    In Process() it looks like Tune is being used without being initialized. Is that right?
    Might want to set it to 1 first or just call Calcswr() directly in your main() routine.

    I'm also wondering if you're running out of cogs, I can't tell for sure...
  • jcfjrjcfjr Posts: 74
    edited 2020-03-06 21:19

    One possible troubleshooting technique is to make the smallest program possible which recreates the problem.



    I have tried most of today trying to "break" the small demo file MCP3202demojcfbreak.spin . I have set it up similiar to the structure of my already broken AutotunerIIR9.spin, but cannot break it. Can see results that show 3202 working as expected in attached document. It works as one would expect.

    I have also diagnosed the actions in my none working AutotunerIIR9, and attached both of these files. In AutotunerIIR9, the MCP3202 reads correctly after start up, reads correctly in the first method call, but reads 0 after that. I have found that if you don't start the MCP3202, you will get a 0 reading. I am wondering if the cog for the 3202 is some how getting clobbered between the first two calls and the rest. Is there a way to query how many cogs are running?
  • RaymanRayman Posts: 14,640
    edited 2020-03-06 23:14
    If you have a free pin, you could put an LED on it and toggle it inside the driver's assembly main loop...

    Actually, I guess you could just put an LED on the chip-select pin to try to see if it's toggling.
    Maybe you'd need an oscilloscope or multimeter to say for sure, if the loop is very fast...
  • RaymanRayman Posts: 14,640
    Actually, I just noticed this in the assembly driver:
                            wrlong  counter,t1              'channels done, update counter
                            add     counter,#1
    

    It looks like the variable "count" is incremented in every assembly loop.

    I think I'd add this to the driver Spin:
    PUB GetCount
    
      return count
    

    It should be changing very often if the driver is running....
  • jcfjrjcfjr Posts: 74
    edited 2020-03-07 17:39
    I put the chip on my scope and monitored the data line. When the MCP3202 is running, there is a constant stream of data, when I don't start the 3202 driver, the scope is flat. So I am assuming that this is a good measure that the 3202 driver is still running. I monitored my AutotunerIIR9 program, and the driver never quit running, so I am assuming that the cog was not clobbered, and I have another problem.



  • Have you monitored the analog input to the 3202?
    Can you capture the data pins and the input at the same time and compare the data with what you're seeing.

    Another alternative is to switch 3202 drivers. There's a bunch of different versions. Some which run entirely in Spin. I know JonnyMac has written a couple different versions himself. If you have trouble finding these, I'm sure I have copies on my hard drive.
  • I will try to set this up, but I just see pulses, no idea what the data is, or how to compare. It reads the right values at the start of the program, it stays running, it is just not functioning in my CalcSWR method when called. I have looked for alternative drivers, but have not seen any on OBEX. This driver seems to work fine, it works with my demo program that has a similar structure , and I like the PASM for speed. If you have some alternative drivers, I can try them, I certainly have had no luck getting this driver to work in my program, even though it works great in my demo program.
  • RaymanRayman Posts: 14,640
    edited 2020-03-07 18:21
    I think I see the problem...

    You have this in hover:
            Dira := Fpin
    

    This is forcing your I/O pin for the 3202 low and giving you zero readings...
  • Duane Degn wrote: »
    Have you monitored the analog input to the 3202?
    Can you capture the data pins and the input at the same time and compare the data with what you're seeing.

    Another alternative is to switch 3202 drivers. There's a bunch of different versions. Some which run entirely in Spin. I know JonnyMac has written a couple different versions himself. If you have trouble finding these, I'm sure I have copies on my hard drive.

    The analog input always has noise on the line that the 3202 correctly measures the first time after 3202 is called. So it should at least measure this value which is around 317.
Sign In or Register to comment.