Macademia'nın robotik ve mühendislik programı · ücretsiz seviye tespiti ve kişisel öğrenme yolu

1. ünite / 11 · yaklaşık 3 saat

Cortex-M mimarisi ve bellek haritası

ARM çekirdeği, STM32 aileleri, Harvard veri yolları ve her şeyin bir adres olduğu 4 GB'lık harita.

Bu ünitenin sonunda

  • Cortex-M0+, M3, M4 ve M7 çekirdeklerini ve STM32 ailelerini (C0, F1, F4, G4, H7) ayırt etmek
  • Flash, SRAM, çevre birimi ve sistem bölgelerini adres haritasında bulmak
  • Bir çevre birimi yazmacının adresini taban + ofsetten hesaplamak
  • Açılışta vektör tablosunun ve Reset_Handler'ın rolünü açıklamak

Ders notları

ARM, işlemci çekirdeğini tasarlar ve lisanslar; ST gibi üreticiler bu çekirdeğin çevresine bellek ve çevre birimleri koyup STM32 gibi mikrodenetleyiciler üretir. Cortex-M ailesi gömülü sistemler içindir: M0+ küçük ve az güç çeker, M4 kayan nokta birimi (FPU) ve DSP komutları ekler, M7 daha hızlı ve önbelleklidir.

Her şey bir adres

Cortex-M 32 bitlik bir adres alanı görür (4 GB). Haritanın düzeni sabittir: 0x0800_0000'da Flash, 0x2000_0000'da SRAM, 0x4000_0000'dan itibaren çevre birimleri, 0xE000_0000'da çekirdeğin kendi birimleri (NVIC, SysTick). Bir LED'i yakmak, aslında belirli bir adrese bir sayı yazmaktır: STM32F4'te GPIOA tabanı 0x4002_0000, ODR yazmacının ofseti 0x14, yani adres 0x4002_0014.

adres = taban + ofset  →  GPIOA→ODR = 0x4002_0000 + 0x14

Açılış

Elektrik gelince çekirdek Flash'ın ilk iki kelimesini okur: yığının tepe adresi ve Reset_Handler adresi. Reset_Handler, ilk değerli değişkenleri (.data) Flash'tan RAM'e kopyalar, sıfır değerlileri (.bss) temizler ve main()'i çağırır. İşletim sistemi yoktur; main hiç dönmemelidir.

Bu derste STM32F4 (Nucleo-F401RE ya da F411 "Black Pill") temel alınır. Adresler ailelere göre değişir ama düşünce aynıdır: başvuru kılavuzu (Reference Manual) her yazmacın adresini ve bitlerini verir.

Simülasyon

Cortex-M bellek haritası gezgini

4 GB'lık adres alanında bir adres yaz ya da bir birime tıkla: hangi bölgede olduğunu, hangi çevre birimine ve yazmaç ofsetine düştüğünü gör. Adresler STM32F4 başvuru kılavuzundaki düzendedir.

Code / Flash0x0000_0000SRAM0x2000_0000Peripheral0x4000_0000External RAM0x6000_0000External device0xA000_0000Private Peripheral Bus0xE000_0000FLASH0x0800_0000SRAM0x2000_0000TIM20x4000_0000USART20x4000_4400I2C10x4000_5400TIM10x4001_0000USART10x4001_1000ADC10x4001_2000SPI10x4001_3000EXTI0x4001_3C00GPIOA0x4002_0000GPIOB0x4002_0400GPIOC0x4002_0800RCC0x4002_3800DMA20x4002_6400SYSTICK0xE000_E010NVIC_ISER0xE000_E100SCB0xE000_ED00
0x4002_0014 · Peripheral Çevre birimleri: APB1 (0x4000_0000), APB2 (0x4001_0000), AHB1 (0x4002_0000; GPIO, RCC, DMA). GPIOA + 0x14 = GPIOA->ODR

Sol: bölgeler (ölçeksiz değil, 4 GB doğrusal). Sağ: bilinen birimlere tıkla.

Kendin dene

Bellek haritasında 0x4002_0014, 0x2000_0400 ve 0xE000_E100 adreslerini yaz: her biri hangi bölge ve birim? GPIOB'nin IDR yazmacının adresini hesapla ve doğrula. Sonra RCC'ye tıkla ve AHB1ENR'nin (ofset 0x30) adresini not et: GPIO saatini açmak için bu adrese yazacağız.

Kod

Açılış: vektör tablosu ve Reset_Handler (sadeleştirilmiş)
#include <stdint.h>
extern uint32_t _estack, _sidata, _sdata, _edata, _sbss, _ebss;   /* bağlayıcı betiğinden */
int main(void);
void Reset_Handler(void);
void Default_Handler(void) { while (1) {} }
void SysTick_Handler(void) __attribute__((weak, alias("Default_Handler")));

/* Flash'ın başı (0x0800_0000): ilk kelime yığın tepesi, ikincisi reset adresi */
__attribute__((section(".isr_vector")))
const void *vectors[] = { &_estack, Reset_Handler, 0, 0, /* ... */ };

void Reset_Handler(void) {
  uint32_t *src = &_sidata, *dst = &_sdata;
  while (dst < &_edata) *dst++ = *src++;          /* .data: ilk değerleri Flash'tan RAM'e kopyala */
  for (dst = &_sbss; dst < &_ebss; ) *dst++ = 0;   /* .bss: sıfırla */
  main();
  while (1) {}
}

Sık yapılan hatalar

  • Adresleri farklı aileler arasında aynı sanmak: STM32F1'de GPIO tabanı ve yazmaç düzeni farklıdır; her zaman kendi kartının başvuru kılavuzuna bak.
  • Veri sayfası ile başvuru kılavuzunu karıştırmak: veri sayfası pin ve elektrik değerlerini, başvuru kılavuzu yazmaçları anlatır.
  • main()'den dönmek: dönülecek bir işletim sistemi yoktur; sonsuz döngü şarttır.
  • Yığın boyutunu hesaba katmamak: yığın taşınca .bss değişkenlerinin üzerine yazar ve hata tuhaf yerlerde görünür.

Yazılım mühendisliği bağlantısı

Gömülü yazılımda belgelere izlenebilirlik önemlidir: her yazmaç erişiminin yanına başvuru kılavuzunun bölüm numarasını yaz.

  • Sihirli sayılar yerine CMSIS başlıklarındaki adlar (GPIOA->ODR, RCC_AHB1ENR_GPIOAEN) kullan.
  • Kartı ve aileyi değiştirmeyi kolaylaştırmak için donanıma özgü kodu ayrı dosyada (bsp/) topla.

Kendini sına

  1. STM32F4'te Flash hangi adresten başlar?

  2. GPIOA tabanı 0x4002_0000, ODR ofseti 0x14. ODR adresi?

  3. Reset_Handler main()'den önce ne yapar?

  4. Kayan nokta birimi (FPU) hangi çekirdekte vardır?

Gerçek parçalar (Hyvex, 3B modelli)

ESOF 323, 2. hafta

Esc
  • PanelAna sayfaSayfa
  • ModüllerTüm modüllerSayfa
  • ParçalarParça ansiklopedisiSayfa
  • Mühendislik yoluBüyükler için robotik: 128 parça, 7 seviyeSayfa
  • Robotik dersi (ESOF 323)Üniversite robotik dersi, 14 haftaSayfa
  • Drone dersiBüyükler için: parça, simülasyon, yazılım; 10 üniteSayfa
  • Blok atölyesiSerbest blok programlamaAraç
  • Devre laboratuvarıSanal Arduino ve devreAraç
  • Robot arenasıSanal robot sürüşüAraç
  • OyunlarBloklarla 8 öğretici oyunAraç
  • Mikro Kart atölyesiSanal LED kartı bloklarla programlaAraç
  • Robot atölyesiMikro Kart'ı robota tak, bloklarla görev yapAraç