FILLING atmega8515 SRAM

Go To Last Post
29 posts / 0 new
Author
Message
#1
  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

I AM TRYING TO FILL the FIRST 10 BYTES OF RAM location with some default value(0xaa). But while debugging , in the memory view it is loading like AA 00 AA 00 AA 00..

#include

int main()
{
volatile unsigned int *address = (volatile unsigned int*)(0x0060);
unsigned int count = 0;
while(count<=10)
{
*(volatile unsigned int*)(address) = 0xaa;
address++;
count++;

}
}
It is supposed to be AA AA AA AA ..
I use stk500. Any help to understand why?

Is there any other way to use section directives?

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

int is 16 bit not 8 bit

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

thanks. I want to fill all my sram locations with aa.
The sram address is 16 bit.How to do that?

sparrow2 wrote:
int is 16 bit not 8 bit

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

make address a char pointer ! (do some C study)

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

I'd have used memset() for this. It's a std. C library function, google for it or RTM for compiler.

1) Studio 4.18 build 716 (SP3)
2) WinAvr 20100110
3) PN, all on Doze XP... For Now
A) Avr Dragon ver. 1
B) Avr MKII ISP, 2009 model
C) MKII JTAGICE ver. 1

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

could you please post me some example or link?

indianajones11 wrote:
I'd have used memset() for this. It's a std. C library function, google for it or RTM for compiler.

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

Google is your friend.

If you quote any passage that you find that you do not understand, we can help.

David.

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

sparrow2 wrote:
make address a char pointer ! (do some C study)

Here is my implementation for filling the sram from(0x0060 to 0x025f)

int main()
{
	 volatile unsigned char *address = (volatile unsigned char*)0x0060;
volatile unsigned short count = 0;	

	while (count < 512)
	{

		(*(volatile unsigned char*)address)  = 0xa;
		count++;
		address++;
		

	}
	
}

How to do we make sure it is exiting properly?
I tried to use memory view , but i see some values in the bottom of the sram .
Last 6 bytes looks like.
0c 0a 02 5f 00 2b
Is this correct? Any pointers to confirm that ther is no stack overflow?
  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

Before you get to main your program run some code (normaly called cstartup) where the basic things like stack setup, clear memory etc. get done. If you want some special RAM pattern you should make the changes to that file.

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

In your OP you want to fill 1st 10 places and in last code you fill entire ram with the pattern. What do you want to do ? Why are you worrying about those 6 bytes ? I thought you were setting up to monitor the stack, but then... :?:

You need a while(1); at the end of the code and why you're asking about overflow, NOTHING happens after you fill ram. These are all things you really should know. Slow down and STUDY a good ( embedded ) C book.

1) Studio 4.18 build 716 (SP3)
2) WinAvr 20100110
3) PN, all on Doze XP... For Now
A) Avr Dragon ver. 1
B) Avr MKII ISP, 2009 model
C) MKII JTAGICE ver. 1

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

I want to fill the entire RAM with 0xa. First I tried to fill the 10 bytes. Then I filled the entire ram. Next I am going to implement some code, to monitor the stack. This is what I am trying to do.

I worry about those 6 bytes, because When I am filling up my entire RAM WITH 0xa, how those 6 bytes are different.

indianajones11 wrote:
In your OP you want to fill 1st 10 places and in last code you fill entire ram with the pattern. What do you want to do ? Why are you worrying about those 6 bytes ? I thought you were setting up to monitor the stack, but then... :?:

You need a while(1); at the end of the code and why you're asking about overflow, NOTHING happens after you fill ram. These are all things you really should know. Slow down and STUDY a good ( embedded ) C book.

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

dolphin@gmx.com wrote:
I worry about those 6 bytes, because When I am filling up my entire RAM WITH 0xa, how those 6 bytes are different.
Maybe because the local variables in your main() function are allocated on the stack...?

And with that in mind, maybe you realize it's not such a good idea to corrupt the entire stack contents in your main() function? As already mentioned, you should do that in your C startup code.

/Jakob Selbing

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

Thanks. you are correct. I am working on that.

jaksel wrote:
dolphin@gmx.com wrote:
I worry about those 6 bytes, because When I am filling up my entire RAM WITH 0xa, how those 6 bytes are different.
Maybe because the local variables in your main() function are allocated on the stack...?

And with that in mind, maybe you realize it's not such a good idea to corrupt the entire stack contents in your main() function? As already mentioned, you should do that in your C startup code.

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

I've posted a flood SRAM routine before now that I placed in .init3 (so it's before the data and bss loops in .init4). The compiler will generally put the for() index in a register not on the stack but you obviously MUST check this or force register binding for it.

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

clawson wrote:
I've posted a flood SRAM routine before now that I placed in .init3 (so it's before the data and bss loops in .init4). The compiler will generally put the for() index in a register not on the stack but you obviously MUST check this or force register binding for it.

	.section .init1,"ax",@progbits

	LDI R27, 0X02 ;upper ram address high byte
	ldI R26,0x5f ;upper ram address low byte
	ldi R25,0X00 ;lower  ram address high  byte
	ldi R24,0X60 ;lower ram address low byte
	LDI R16,0xAA ; VALUE TO BE COPIED 

loop:
	st x,r16   ; STORE 0XAA VALUE IN RAM LOCATION 
	sbiw r26,1 ;DECREMENT THE RAM ADDRESS
	cp r26,r24  ;COMPARE THE LOW BYTES OF THE RAM  END AND STARTING  ADRDRESS
	cpc r27,r25 ;COMPARE THE HIGH BYTES OF THE RAM END AND STARTING  ADRDRESS THROUGH THE CARRY 
	brne loop ;	loop continues untill it becomes equal 


This is my assembly routine to fill the ram  with 0xaa before the main starts.
My main() is just empty. I viewed the memory , it seems like my first location is 0xff(0x0060), last 2 locations of 00 35. Why is that?  Any help?
  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

dolphin@gmx.com wrote:
last 2 locations of 00 35. Why is that?

Because there is a call to main(), so that's the return address pushed to stack.

dolphin@gmx.com wrote:
first location is 0xff(0x0060),
Because your loop exits before you write to this address. Use BRSH (BRCC) instead of BRNE.

JW

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

Thanks to you.

wek wrote:
dolphin@gmx.com wrote:
last 2 locations of 00 35. Why is that?

Because there is a call to main(), so that's the return address pushed to stack.

dolphin@gmx.com wrote:
first location is 0xff(0x0060),
Because your loop exits before you write to this address. Use BRSH (BRCC) instead of BRNE.

JW

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

You can shorten it a bit by doing this in your fill loop :

*address++ = 0xaa;
++count;

1) Studio 4.18 build 716 (SP3)
2) WinAvr 20100110
3) PN, all on Doze XP... For Now
A) Avr Dragon ver. 1
B) Avr MKII ISP, 2009 model
C) MKII JTAGICE ver. 1

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

Hello everybody,

I am trying to do the same thing (filling RAM with a pattern 0xAA). In fact, am taking classes and this is a project...I am not asking for the solution so please don't get offended (don't really know whether this is THE solution). I don't know Assembly language & while looking for help I landed here. So my questions are related to this code:

.section .init1,"ax",@progbits 

   LDI R27, 0X02 ;upper ram address high byte 
   ldI R26,0x5f ;upper ram address low byte 
   ldi R25,0X00 ;lower  ram address high  byte 
   ldi R24,0X60 ;lower ram address low byte 
   LDI R16,0xAA ; VALUE TO BE COPIED 

loop: 
   st x,r16   ; STORE 0XAA VALUE IN RAM LOCATION 
   sbiw r26,1 ;DECREMENT THE RAM ADDRESS 
   cp r26,r24  ;COMPARE THE LOW BYTES OF THE RAM  END AND STARTING  ADRDRESS 
   cpc r27,r25 ;COMPARE THE HIGH BYTES OF THE RAM END AND STARTING  ADRDRESS THROUGH THE CARRY 
   brne loop ;   loop continues untill it becomes equal 

1. I understand that in assembly language we need to write data to registers and then work with those registers. But why these registers only (R27, R26, R24, R25, R16)? When I see the datasheet for Atmega2560, R26-R31 registers are X,Y,Z-register Low/high Byte registers.

2. Why do we need to use X,Y,Z-register Low/high Byte registers and why those values (0X02, 0x5f, 0X00, 0X60) in the above code? Why are we not using other registers like R0, R1...,etc?

3. How this code fills RAM with 0xaa when it's using only 4-5 registers?

Any response, help or criticism are welcome.

Thanks

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

Herte are some cluse:

See the comments to the right of the instructions?

E.g.

   st x, r16

stores the value in register r16 in the RAM cell whose address is in register x. Register x is an alias for the 8-bit register r27:r26. It is effectively a 16 bit register.

And

   sbiw r26,1

subtracts the value 1 from the registers r27:r26 (read it out as "subtract immediate from word", where "word" means a 16-bit value (i.e r27:r26).

In order to interpret the code bove, instruction by instruction, you need to get your hands on a document from Atmel entiteled "AVR Instruction Set Manual" or something very similar. It sould be accessible at Atmels site - go to any 8-bit AVR device page and then select the "Documents" tab and scroll through it to fins the document.

The details on why sometimes you need to use the register name x and sometimes the register names r27, r26 is in that document.

In some sort of pseudocode, this is what happens:

r27:r26 = 0x025f
r25:r24 = 0x0060
r16 = 0xaa
do
   ram[x] = r16
   x = x - 1
while r27:r26 <> r25:r24

As of January 15, 2018, Site fix-up work has begun! Now do your part and report any bugs or deficiencies here

No guarantees, but if we don't report problems they won't get much of  a chance to be fixed! Details/discussions at link given just above.

 

"Some questions have no answers."[C Baird] "There comes a point where the spoon-feeding has to stop and the independent thinking has to start." [C Lawson] "There are always ways to disagree, without being disagreeable."[E Weddington] "Words represent concepts. Use the wrong words, communicate the wrong concept." [J Morin] "Persistence only goes so far if you set yourself up for failure." [Kartman]

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

Stepping through the code in a simulator (such as in AVRStudio) may be very instructive, too; although it may take some effort to set it up.

Johan (or others): is there any truly step-by-step guide for this?

JW

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

Thanks, your reply was very helpful. But I still have some doubts.

1. r26,r27 is X-low/high byte register (so is it true that r24,25 are also low/high byte; r22,r23 - low/high & so on..) [sorry, if it sounds silly but that's what I feel from the code]

2. Couldn't understand the values given to r24...r27. But if I want to fill RAM with 0xAA from 0x21ff-0x200 then is this code correct?

.section .init0,"ax",@progbits 

LDI r27;          CLEAR X HIGH BYTE
LDI r26, 0x21FF;  SET X LOW BYTE TO 0X21FF LOCATION
LDI r25;          CLEAR HIGH BYTE
LDI r24, 0X200;   SET LOW BYTE TO 0X200 LOCATION
LDI r16, 0XAA;    VALUE TO BE STORED

LOOP:
ST X, r16;
SBIW r26,1;    DECREMENT LOCATION BY 1
CP r26,r24;    COMPARE LOW BYTES
CPC r27, r25;  COMPARE HIGH BYTE WITH CARRY
BRNE LOOP;     BRANCH IF r27 & r25 ARE NOT EQUAL

Can I write:

ST X, r16;
SBIW r26,1;    DECREMENT LOCATION BY 1

as

ST X-, r16;

3. r16 register is used to set the value 0xAA (just like we use a variable in C), instead we can use r0, r1..or r15. Am I correct?

Thanks once again

JohanEkdahl wrote:
Herte are some cluse:

Last Edited: Fri. Apr 27, 2012 - 04:28 AM
  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

Quote:

that's what I feel from the code

You can feel all you like. If you want facts then download the AVR Instruction Set document and use it.

As of January 15, 2018, Site fix-up work has begun! Now do your part and report any bugs or deficiencies here

No guarantees, but if we don't report problems they won't get much of  a chance to be fixed! Details/discussions at link given just above.

 

"Some questions have no answers."[C Baird] "There comes a point where the spoon-feeding has to stop and the independent thinking has to start." [C Lawson] "There are always ways to disagree, without being disagreeable."[E Weddington] "Words represent concepts. Use the wrong words, communicate the wrong concept." [J Morin] "Persistence only goes so far if you set yourself up for failure." [Kartman]

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

Hey, it's not like that (you guys are great, you catch every single word :)).I downloaded the manual and read it...but I couldn't find or may be couldn't get it into my head correctly, that's why I said that. The manual is still open, am compiling the code and trying to solve errors & warning..if you don't believe..here are some of them after compiling the exact code written above(by me):

../RamInit.S: Assembler messages:
../RamInit.S:3: Error: `,' required
../RamInit.S:3: Error: garbage at end of line
../RamInit.S:4: Warning: constant out of 8-bit range: 8703
../RamInit.S:5: Error: `,' required
../RamInit.S:5: Error: garbage at end of line
../RamInit.S:6: Warning: constant out of 8-bit range: 512
  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

At least I got rid of the messages with this:

.section .init0,"ax",@progbits 

clr r27;          CLEAR X HIGH BYTE 
LDS r26, 0x21FF;  SET X LOW BYTE TO 0X21FF LOCATION 
clr r25;          CLEAR HIGH BYTE 
LDS r24, 0x200;   SET LOW BYTE TO 0X200 LOCATION 
LDI r16, 0XAA;    VALUE TO BE STORED 
  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

Hello,

I am debugging the program and watching the memory & registers. The program does fill 0xAA but at the wrong places (from 78-60). I don't understand why? The start & end address that I've given is 0x200-0x21FF respectively.

Somebody please point out my mistake...

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0
LDS r26, 0x21FF;  SET X LOW BYTE TO 0X21FF LOCATION 

You CANNOT put a 16 bit value into a 8 bit register, that is loading r26 FROM address 0x21FF

LDS r24, 0x200;   SET LOW BYTE TO 0X200 LOCATION 

same thing here

John Samperi

Ampertronics Pty. Ltd.

https://www.ampertronics.com.au

* Electronic Design * Custom Products * Contract Assembly

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

You can use the code from here:
http://www.rn-wissen.de/index.ph...

#include  // RAMEND

#define MASK 0xaa

// !!! Never call this function, it is part of .init-Code
void __attribute__ ((naked, used, section(".init3"))) init_mem (void);
void init_mem (void)
{
   //  Use inline assembler so it works even with optimization turned off
   __asm volatile (
      "ldi r30, lo8 (__heap_start)"  "\n\t"
      "ldi r31, hi8 (__heap_start)"  "\n\t"
      "ldi r24, %0"                  "\n\t"
      "ldi r25, hi8 (%1)"            "\n"
      "0:"                           "\n\t"
      "st  Z+,  r24"                 "\n\t"
      "cpi r30, lo8 (%1)"            "\n\t"
      "cpc r31, r25"                 "\n\t"
      "brlo 0b"
         :
         : "n" (MASK), "n" (RAMEND+1)
   );
}

If you want a different start, use a different start address. The example above uses __heap_start which starts after static data.

For the start of RAM, you can use __data_start which is defined in the linker script, just like __heap_start.

I'd discourage to write this in C for several obvious reasons like, e.g. not overriding the return address of the worker.

avrfreaks does not support Opera. Profile inactive.

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

js wrote:

LDS r26, 0x21FF;  SET X LOW BYTE TO 0X21FF LOCATION 

You CANNOT put a 16 bit value into a 8 bit register, that is loading r26 FROM address 0x21FF

LDS r24, 0x200;   SET LOW BYTE TO 0X200 LOCATION 

same thing here

Thanks so much, it was very helpful (also understood why the values for R24...R27 were like that). Got the desired output.

Thanks everybody!