adding blinker03 example uses the ARM freerunning timer

This commit is contained in:
David Welch
2012-05-26 16:28:23 -04:00
parent 250a069163
commit b0b864e352
5 changed files with 147 additions and 0 deletions

30
blinker03/Makefile Normal file
View File

@@ -0,0 +1,30 @@
ARMGNU ?= arm-none-eabi
COPS = -Wall -O2 -nostdlib -nostartfiles -ffreestanding
all : kernel.img
clean :
rm -f *.o
rm -f *.bin
rm -f *.elf
rm -f *.list
rm -f *.img
novectors.o : novectors.s
$(ARMGNU)-as novectors.s -o novectors.o
blinker03.o : blinker03.c
$(ARMGNU)-gcc $(COPS) -c blinker03.c -o blinker03.o
kernel.img : memmap novectors.o blinker03.o
$(ARMGNU)-ld novectors.o blinker03.o -T memmap -o blinker03.elf
$(ARMGNU)-objdump -D blinker03.elf > blinker03.list
$(ARMGNU)-objcopy blinker03.elf -O binary kernel.img

12
blinker03/README Normal file
View File

@@ -0,0 +1,12 @@
See the top level README for information on where to find the
schematic and programmers reference manual for the ARM processor
on the raspberry pi.
This example uses the free running ARM timer, not the 64 bit system
one as in blinker02 but the so called ARM timer.
The system clock appears to come up at 250MHz as documented. Divide that
by 250 to get 1Mhz on this free running ARM timer. Then count to four
million ticks between led state changes and the led will change state
every four seconds.

70
blinker03/blinker03.c Normal file
View File

@@ -0,0 +1,70 @@
//-------------------------------------------------------------------------
//-------------------------------------------------------------------------
extern void PUT32 ( unsigned int, unsigned int );
extern unsigned int GET32 ( unsigned int );
extern void dummy ( unsigned int );
#define ARM_TIMER_LOD 0x2000B400
#define ARM_TIMER_VAL 0x2000B404
#define ARM_TIMER_CTL 0x2000B408
#define ARM_TIMER_DIV 0x2000B41C
#define ARM_TIMER_CNT 0x2000B420
#define SYSTIMERCLO 0x20003004
#define GPFSEL1 0x20200004
#define GPSET0 0x2020001C
#define GPCLR0 0x20200028
//From experiments and from the manual the freerunning ARM timer is
//not affected by the timer enable bit. Not affected by the 0x41C
//prescaler. Not affected by bits 3:2 of the control register.
//And is affected by bits 23:16 of the control register.
//It still appears as if the system timer is 250Mhz as mentioned somewhere
//in the manual (starts up at 250MHz).
//If we divide 250MHz/250 we can make the free running clock 1mhz
//wait for 4 million ticks and the led will change state every 4 seconds
//Note the free running timer is an up counting timer, the other arm
//timer is a down counter.
#define TIMEOUT 4000000
//-------------------------------------------------------------------------
int notmain ( void )
{
unsigned int ra;
unsigned int rb;
ra=GET32(GPFSEL1);
ra&=~(7<<18);
ra|=1<<18;
PUT32(GPFSEL1,ra);
PUT32(ARM_TIMER_CTL,0x00F90000);
PUT32(ARM_TIMER_CTL,0x00F90200);
rb=GET32(ARM_TIMER_CNT);
while(1)
{
PUT32(GPSET0,1<<16);
while(1)
{
ra=GET32(ARM_TIMER_CNT);
if((ra-rb)>=TIMEOUT) break;
}
rb+=TIMEOUT;
PUT32(GPCLR0,1<<16);
while(1)
{
ra=GET32(ARM_TIMER_CNT);
if((ra-rb)>=TIMEOUT) break;
}
rb+=TIMEOUT;
}
return(0);
}
//-------------------------------------------------------------------------
//-------------------------------------------------------------------------

12
blinker03/memmap Normal file
View File

@@ -0,0 +1,12 @@
MEMORY
{
ram : ORIGIN = 0x00000000, LENGTH = 0x1000
}
SECTIONS
{
.text : { *(.text*) } > ram
.bss : { *(.bss*) } > ram
}

23
blinker03/novectors.s Normal file
View File

@@ -0,0 +1,23 @@
.globl _start
_start:
b reset
reset:
mov sp,#0x1000
bl notmain
hang: b hang
.globl PUT32
PUT32:
str r1,[r0]
bx lr
.globl GET32
GET32:
ldr r0,[r0]
bx lr
.globl dummy
dummy:
bx lr