EmbDev.net

Forum: ARM programming with GCC/GNU tools LPC2148 ADC Help


von alex (Guest)


Rate this post
useful
not useful
Hi everyone,

I have been working on this for about a week, looking at examples from 
all over the place and pouring through datasheets, but I cannot get this 
to work(or many ARM Features for that matter)

I have worked with AVRs for a while and I love them, but I wanted to 
move up to ARM.  I know a reasonable amount of C, and no assembler.  I 
don't really want to get this example working as much as I want to learn 
what im not doing right.  I really want to learn how to be able to do 
ARM programs on my own and not rely on forums to help me, so any 
tutorials or books would be greatly appreciated.

So, I am trying to get the ADC working so it will print the 10-bit value 
of ADC0.3 over uart0 at 19200 baud.  Here is my code:
1
#include "LPC214x.h"
2
3
#define ADC_CLK    1000000    /* set to 1Mhz */
4
5
#include "serial.h"
6
#include "rprintf.h"
7
#include "target.h"
8
9
void delay_ms(int x);
10
11
int main(void)
12
{
13
  init_serial0(19200);
14
  rprintf_devopen(putc_serial0);
15
  rprintf("Hello!\n\n");
16
17
  PINSEL0 = 0x10000000;
18
19
  AD0CR = (0x01 << 0) |   
20
  (1 << 3) | //Turn analog 3 on
21
  (( Fpclk / ADC_CLK - 1 ) << 8) |
22
  (0 << 16) |     // BURST = 0, no BURST, software controlled
23
  (0 << 17) |      // CLKS = 000, 11 clocks/10 bits 
24
  (0 << 18) |    //^
25
  (0 << 19) |    //^
26
  (1 << 21) |      // PDN = 1, normal operation 
27
  (0 << 22) |      // TEST1:0 = 00 
28
  (0 << 24);      // START = 0 A/D conversion stops
29
30
  while(1) {
31
    AD0CR |= (1 << 24); //Start Conversion
32
    delay_ms(1); //Give it time to convert(I doubt this is necessary?)
33
    rprintf("%luH", ((AD0DR3 >> 6) & 0x000003ff) * 0x40);
34
    AD0CR &= (1 << 24);  //Stop Conversion
35
    delay_ms(50);
36
  }
37
}  
38
39
void delay_ms(int x)
40
//Rough, not meant to be accurate
41
{
42
    int a,b;
43
    for(a=0;a<x;a++){
44
        for(b=0;b<3000;b++);
45
    }
46
}

And when I run the code this is all I get:
1
Hello!
2
ÿ

Any ideas for what I am doing wrong?

Thanks!

von alex (Guest)


Attached files:

Rate this post
useful
not useful
After I posted this I thought I should mention that I am using an 
LPC2148, on the Olimex Header Board.  I am compiling with GCC.

I also just noticed you prefer code attached.  Sorry for the large paste 
above.

von Andreas S. (andreas) (Admin)


Rate this post
useful
not useful
Your delay loop is not going to work if you compile with optimization 
enabled (-Ox), because the compiler will detect an empty loop and remove 
it. Use volatile variables for the counter, then it won't get removed.

If your controller hangs, the reason is usually an exception caused by 
an invalid memory access. Do you have a JTAG debugger? If yes, try to 
find out what the controller is doing after you have received the output 
(it is probably hanging at the abort handler), then rerun and use single 
step to locate the statement that's causing it. If you don't have a 
debugger, you can for example comment out lines until you have found the 
problem.

von mthomas (Guest)


Rate this post
useful
not useful
- Strange output might just be caused by missing functionality in 
rprintf. Since rprintf is not shown it's difficult to analyse. Test with 
a known uint32_t value first, see rprintf source and check for "l", test 
with "L", test with cast to uin32_t. Try to use sprintf from the newlib.
- add volatile to counters definition (a,b) in delay-function.

von Noel Le Moult (Guest)


Rate this post
useful
not useful
You can try to read the Logomatic-v2 code from sparkfun electronic.

It use the LPC2148 ADC, I have tested and it works very well with Uart 
output.

Link to the Logomatic-v2 product info: 
http://www.sparkfun.com/commerce/product_info.php?products_id=8627
There is a link to get the source code (main firmware)

von alex (Guest)


Attached files:

Rate this post
useful
not useful
Thank you everyone!

I do not have an ARM JTAG, dongle, but I do have a USB Xilinx FPGA one, 
would that work?

I played around with it some more, commenting out lines until I got it 
working.  I found that PINSEL0 = 0x10000000; was the problem, and by 
removing it it will now actually print the ADC value.

The problem is, it always prints zero.  I know that the ADC is actually 
reading zero because I did a test with if(adcval == 0), and it always 
returned true.

I did like mthomas suggested as use sprintf from newlib, but 
unfortunately this did not help.  I have attached the code and all other 
files I include(except the standard ones).  Any help is greatly 
appreciated.

Thank you!

von alex (Guest)


Rate this post
useful
not useful
Neal Le Moult:  I looked at the Logomatic Code, but the ADC Part seemed 
really jumbled in with everything else, and what I am really looking for 
is learning how to use the ADC, which is hard when its combined with 
interrupts and timers and the like.

Thanks anyway!

von Noel Le Moult (Guest)


Rate this post
useful
not useful
Here is an application note from Nxp about LPC21xx ADC

http://www.vas.co.kr/nxp/support/technical_notes/tn06004.pdf

Please log in before posting. Registration is free and takes only a minute.
Existing account
Do you have a Google/GoogleMail account? No registration required!
Log in with Google account
No account? Register here.