Forum: Mikrocontroller und Digitale Elektronik xmega eeprom - kompakter code


von Martin (Gast)


Lesenswert?

Hallo alle miteinander. Ich habe mich bisher kaum mit EEPROMs
beschäftigt und suche eine einfache Variante, wie ich ein paar Variablen
fix und fest abspeichern kann. Das Forum habe ich schon durchforstet,
aber eine kopakte Variante hab ich noch nicht gefunden. Ich Suche nen
Codebeispiel für den Xmega, weil der EEPROM dort in pages organisiert
ist...

kann mir jemand nen Tip geben?

von Warhawk (Gast)


Lesenswert?

Hallo,

hast du dir schonmal die Application-Notes bei Atmel zum XMega 
angeschaut?

Da gibt es gleich einige Beispiele mit. Such einfach mal nach: "AVR1315"
Weiterhin könnten für dich auch die Notes "AVR1008" und "AVR101" 
interessant sein.

von Vlad T. (vlad_tepesch)


Lesenswert?

Martin schrieb im Beitrag #2280251:
> kann mir jemand nen Tip geben?

ja:
Doppelposter mag niemand
https://www.mikrocontroller.net/topic/226649#2280251

von Timmo H. (masterfx)


Lesenswert?

Wenn du mit AVRGCC arbeitest kannst du dich einfach hier nach richten: 
AVR-GCC-Tutorial: EEPROM
Geht geht beim Xmega genauso wie beim Atmega/Tiny

von xmega (Gast)


Lesenswert?

Hallo,

Timmo H. schrieb:
> Geht geht beim Xmega genauso wie beim Atmega/Tiny

EEPROM bleibt EEPROM.. das ist richtig. Aber das EEPROM des XMEGA 
funktioniert etwas anders, es ist pageweise organisiert.

Der alten Atmega-Befehlssatz funktioniert 100-prozentig nicht mehr.

Gruß XMEGA

von Martin (Gast)


Lesenswert?

xmega schrieb:
> EEPROM bleibt EEPROM.. das ist richtig. Aber das EEPROM des XMEGA
> funktioniert etwas anders, es ist pageweise organisiert.

Genau das ist ja mein Problem ;-)

von Timmo H. (masterfx)


Lesenswert?

xmega schrieb:
> Der alten Atmega-Befehlssatz funktioniert 100-prozentig nicht mehr.
>
> Gruß XMEGA

Doch wenn man die lib nutzt schon.
Steht ja auch so im Comment vom eeprom.h:
1
For Xmega the EEPROM start address is 0, like other architectures. The reading functions add the 0x2000 value to use EEPROM mapping into data space.
Darum kümmert sich eben avrgcc.

Man kann natürlich auch direkt durch das mapping darauf zugreifen.

So wirds in der libc gemacht:
1
Register usage of internally-used functions, XMEGA arch:
2
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
3
4
    eeprom_mapen:
5
  Input:
6
      r25,r24  - EEPROM address
7
  Output:
8
      ZH,ZL  - EEPROM address + 0x2000 (to use mapping)
9
  Scratch:
10
      r19
11
12
    eeprom_update_r18:
13
  Input:
14
      r18    - byte to write
15
      r25,r24  - EEPROM address
16
  Output:
17
      r25,r24  - decremented EEPROM address
18
  Scratch:
19
      r31,r30,r19,r18,r0
20
21
    eeprom_update_byte:
22
  Input:
23
      r22    - byte to write
24
      r25,r24  - EEPROM address
25
  Output:
26
      r25,r24  - decremented EEPROM address
27
  Scratch:
28
      r31,r30,r19,r18,r0
29
30
    eeprom_write_r18:
31
  Input:
32
      r18    - byte to write
33
      r25,r24  - EEPROM address
34
  Output:
35
      r25,r24  - incremented EEPROM address
36
  Scratch:
37
      r31,r30,r19,r18
38
39
    eeprom_write_byte:
40
  Input:
41
      r22    - byte to write
42
      r25,r24  - EEPROM address
43
  Output:
44
      r25,r24  - incremented EEPROM address
45
  Scratch:
46
      r31,r30,r19,r18

von Timmo H. (masterfx)


Lesenswert?

Ups, falscher Code, das kam aus der Readme. Also hier aus eewr_byte.S, 
ist also alles drin für den xmega:
1
#include <avr/io.h>
2
3
#if  E2END && __AVR_ARCH__ > 1
4
5
#include <avr/eeprom.h>
6
#include "asmdef.h"
7
#include "eedef.h"
8
9
ENTRY  eeprom_write_byte
10
  mov  r18, r22
11
12
ENTRY  eeprom_write_r18
13
14
#if  __AVR_XMEGA__  /* --------------------------------------------  */
15
16
# ifndef CCP_IOREG_gc
17
#  define CCP_IOREG_gc  0xD8  /* IO Register Protection  */
18
# endif
19
# ifndef NVM_CMD_READ_EEPROM_gc
20
#  define NVM_CMD_READ_EEPROM_gc    0x06
21
# endif
22
# ifndef NVM_CMD_LOAD_EEPROM_BUFFER_gc
23
#  define NVM_CMD_LOAD_EEPROM_BUFFER_gc    0x33
24
# endif
25
# ifndef NVM_CMD_ERASE_WRITE_EEPROM_PAGE_gc
26
#  define NVM_CMD_ERASE_WRITE_EEPROM_PAGE_gc  0x35
27
# endif
28
# ifndef  NVM_CMD_ERASE_EEPROM_BUFFER_gc
29
#  define NVM_CMD_ERASE_EEPROM_BUFFER_gc  0x36
30
# endif
31
32
  ; Prepare base address of NVM.
33
  ldi  ZL, lo8(NVM_BASE)
34
  ldi  ZH, hi8(NVM_BASE)
35
36
  ; Wait until NVM is not busy.
37
1:  ldd  r19, Z + NVM_STATUS - NVM_BASE
38
  sbrc  r19, NVM_NVMBUSY_bp
39
  rjmp  1b
40
41
  ; Disable EEPROM mapping into data space.
42
  ldd  r19, Z + NVM_CTRLB - NVM_BASE
43
  andi  r19, ~NVM_EEMAPEN_bm
44
  std  Z + NVM_CTRLB - NVM_BASE, r19
45
46
  ; Check the clearance of EEPROM page buffer.
47
  ldd  r19, Z + NVM_STATUS - NVM_BASE
48
  sbrs  r19, NVM_EELOAD_bp
49
  rjmp  3f      ; erase is not required
50
51
  ; Note that we have only four clock cycles to write to the CCP
52
  ; protected register NVM_CTRLA, after writing to CCP.  The 'ldi'
53
  ; instruction always takes one clock to execute and 'std' instruction takes
54
  ; two clock cycles.  We fall within the four cycles that the CCP leaves
55
  ; us to write the command execution start bit to the NVM_CTRLA
56
  ; register.  Note that r18 must be preserved until written to NVM_DATA0
57
58
  ; Issue EEPROM Buffer Erase:
59
  ldi  r19, NVM_CMD_ERASE_EEPROM_BUFFER_gc
60
  std  Z + NVM_CMD - NVM_BASE, r19
61
  ldi  r19, CCP_IOREG_gc
62
  out  CCP, r19
63
  ldi  r19, NVM_CMDEX_bm
64
  std  Z + NVM_CTRLA - NVM_BASE, r19
65
66
  ; Wait until NVM is not busy.
67
2:  ldd  r19, Z + NVM_STATUS - NVM_BASE
68
  sbrc  r19, NVM_NVMBUSY_bp
69
  rjmp  2b
70
71
  ; Issue EEPROM Buffer Load command.
72
3:  ldi  r19, NVM_CMD_LOAD_EEPROM_BUFFER_gc
73
  std  Z + NVM_CMD - NVM_BASE, r19
74
  std  Z + NVM_ADDR0 - NVM_BASE, addr_lo
75
  std  Z + NVM_ADDR1 - NVM_BASE, addr_hi
76
  std  Z + NVM_ADDR2 - NVM_BASE, __zero_reg__
77
  std  Z + NVM_DATA0 - NVM_BASE, r18
78
79
  ; Issue EEPROM Erase & Write command.
80
  ldi  r18, NVM_CMD_ERASE_WRITE_EEPROM_PAGE_gc
81
  std  Z + NVM_CMD - NVM_BASE, r18
82
  ldi  r18, CCP_IOREG_gc
83
  ldi  r19, NVM_CMDEX_bm
84
  out  CCP, r18
85
  std  Z + NVM_CTRLA - NVM_BASE, r19
86
87
  ; Increment address.
88
  adiw  addr_lo, 1
89
90
  ret

Bitte melde dich an um einen Beitrag zu schreiben. Anmeldung ist kostenlos und dauert nur eine Minute.
Bestehender Account
Schon ein Account bei Google/GoogleMail? Keine Anmeldung erforderlich!
Mit Google-Account einloggen
Noch kein Account? Hier anmelden.