SAM3X: HardFault bei Wechsel der Taktquelle

OP #4262850
Lesenswert?

Hallo,

ich programmiere an einem Startup-Code für einen Atmel SAM3X8E (das ist 
der auf dem Arduino Due). Ich habe bereits funktionierenden Code in 
Assembler für Keil IAR geschrieben, der folgendes tut:
- Watchdog ausmachen (WDDIS in WDT_MR setzen)
- Vektortabelle umplatzieren (Adresse nach SCB_VTORS schreiben)
- Slow Clock (SCK) auf 32 kHz-Quarz einstellen
  (XTALSEL in SUPC_CR setzen) und Status-Register pollen
- Main Clock (MAINCK) auf externen 12 MHz-Quarz einstellen
  (CKGR_MOR einstellen) und Status-Register pollen
- CPU auf MAINCK umstellen und Status-Register pollen
- "main" anspringen.

Genau das möchte ich jetzt in einer C-Umgebung unter Linux auch tun. 
Allerdings kriege ich beim Versuch, den externen Quarz einzuschalten, 
einen HardFault. Also beim Schreibzugriff auf CKGR_MOR. Inzwischen bin 
ich da ziemlich ratlos.

Ich versuche, den Wert 0x0137FF01 dort reinzuschreiben (Main Oscillator 
Selection = Crystal, Key=0x37, Main Crystal Oscillator Startup Time=255, 
Main Crystal Oscillator Enable), was in der Keil-Umgebung auch 
funktioniert.

Im Datenblatt habe ich nichts gefunden, was auf einen HardFault 
schließen lässt. Die Taktumschaltung soll glitch-free sein.

Nachtrag:
Der HardFault tritt nicht auf, wenn der Code aus dem RAM läuft (siehe 
Thread zum JLink von vorhin). Das verwirrt mich nur noch mehr.

Gruß,
Svenska
#4262875
Lesenswert?

Meine Kristallkugel sagt....
Her mit dem Code!
Ohne Code können wir mehr oder weniger nur wild raten.

Wenn wir deinen Asm und C-Code haben können wir den vergelichen & dir 
besser helfen als wenn wir einfach nur raten.

Aber einen 1. Rateversuch wage ich mal....
Ist der Stack initialisiert?
OP #4262909
Lesenswert?

Hi,

angehängt ist der Startup-Code aus dem Keil-Projekt (startup_sam3x.s), 
sowie mein der Startup-Code in C (start.c), das Exception-Zeug 
(sam3xa.{c,h}) und ein Teil der Registerbeschreibungen (pmc, supc).

Die Linkerscripts sind direkt von Atmel, der Stack ist 8K groß.

Gruß,
Svenska
Angehängte Dateien:
#4262938
Lesenswert?

>/* point vector table to SRAM if run from SRAM */
>  if((uint32_t)vector_table < 0x20000000) {
>    *(uint32_t*)0xE000ED08 = (uint32_t)vector_table;
>  }

Sollte hier nicht >= als vergleich stehen?
Damit wird die Adresse nur dann geschrieben, wenn sie kleiner wie 
0x20000000 ist. D.h. wenn sie unterhalb vom Ram ist.
Ist mir jetzt als erstes aufgefallen.

Antwort schreiben

Bitte melde dich an, um einen Beitrag zu schreiben.

oder

Mit Google-Account einloggen

Die Registrierung ist kostenlos und dauert nur eine Minute.

Jetzt registrieren