avr-as string handling: strange stuff with null termination

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

I'm using the AVR-GCC toolchain to compile a bit of hello world code for an LCD screen and ATmega168. I can get everything to work if my message is an odd number of characters, but not if it is an even number. For instance, "Hello World' displays just fine, but 'Hello World!' displays nothing.

I'm using the .asciz directive to create null terminated strings, then testing for the last byte read from program memory to be zero. Is this the wrong way to do it?

Pertinent code below.

Thanks for any help you can give.

#define mp r16
#define payload r17

#...cut a bunch of code here #

	;print message from program memory
	ldi ZH, hi8(greeting)
	ldi ZL, lo8(greeting)
	rcall sendMsg

loop:
	rjmp loop

greeting:
.asciz "Hello World"

sendMsg:
	lpm payload,Z+
	cpi payload,0	; test for null character
	breq done	; issues RET command if end of string is found
	rcall writeChar
	rjmp sendMsg

done:
	ret
	

writeChar:
#...cut a bunch of code here #
  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

The gnu assembler is byte based. You need to insert an alignment after the string so the code after it starts at a word boundary.

Stefan Ernst

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

sternst wrote:
The gnu assembler is byte based. You need to insert an alignment after the string so the code after it starts at a word boundary.

Thanks, that fixes it right up.

For anyone else wondering, here's a reference to that .align directive: http://tigcc.ticalc.org/doc/gnua...

Also, here's what my string section looks like now:

greeting:
.asciz "Hello World!"
.align 1

If I understand this correctly, the constant after the .align command tells the compiler to pad the table 2 raised to the power of 1 (all data must be a multiple of 2 bytes).

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

What you want is maybe something like that:

.section .progmem.data,"a",@progbits
.string "some text"

.text
; some code

.section .progmem.data
.string "more text"

.data
some_data:
   .byte  1

.text
; more code

I.e. use appropriate section (drawer) for each kind of data. Strings are no code co be execited, they should not go into .text.

Using alignment after each string will waste you
(estimated) 1/2 byte per string unnecessarily.

1/2 byte waste per section is enough ;-)

avrfreaks does not support Opera. Profile inactive.