STM32F7 Discovery Ekran Hafıza yapısı.

Başlatan Mucit23, 22 Şubat 2016, 14:30:29

Mucit23

Bu kartın hafıza yapısını anlamam lazım. Yardımcı olursanız sevinirim.

https://www.picproje.org/index.php/topic,63205.15.html
Daha önce bu başlıkta sormuştum. F429 için SDRAM olayını anladım. Ama bugün F7 disco da yine sorun yaşayınca bu konunun tam oturmadığını anladım.

İlk Önce anladıklarımı anlatayım.

Kartta 128Mbit Ram var. Bu ram'in başlangıç adresi 0xC0000000 olarak tanımlanmış

Şimdi LCD'nin iki katmandan oluştuğunu biliyorum. Bu katmalar Layer 0 ve Layer 1 olarak geçiyor. Layer 0 BackGround, Layer1 ise ForeGround olarak tanımlı.

LCD_init ayarlarında Layer0 ve Layer1 adresleri aşağıdaki gibi tanımlanmış.
  /* LCD Initialization */
  BSP_LCD_LayerDefaultInit(0, LCD_FB_START_ADDRESS);
  BSP_LCD_LayerDefaultInit(1, LCD_FB_START_ADDRESS+(BSP_LCD_GetXSize()*BSP_LCD_GetYSize()*4));

LCD_FB_START_ADDRESS değeri 0xC0000000 olarak tanımlanmış. Yani SDRAM'in başlangıç adresi. Layer0 buradan başlıyor. Layer1 ise LCD_FB_START_ADDRESS  adresine ofset ekleyerek hesaplanmış. OFSET değeri 480x272x4 yani 0x1D5040 olması gerekir.  Biz Layer1 ile ilgileniyoruz.

4 ile çarpılmasının sebebi ise ARGB888 formatı kullanılması. Her bir pixel hafızada 32 bit yer kaplıyor. 8Bit R, 8 Bit G, 8 Bit B ve 8 Bit Alpha değerinden oluşuyor.  Yanlış anlamadıysam durum böyle. Renkler hafızada aşağıdaki gibi tanımlı
//ARGB
#define LCD_COLOR_BLUE          ((uint32_t)0xFF0000FF)
#define LCD_COLOR_GREEN         ((uint32_t)0xFF00FF00)
#define LCD_COLOR_RED           ((uint32_t)0xFFFF0000)

Ben şimdi basit bir for döngüsüyle ekranı tamamen kırmızıya boyamak istiyorum. Bunun için kendime aşağıdaki adresleri tanımladım.

#define LCD_FRAME_BUFFER    SDRAM_DEVICE_ADDR //0xC0000000
#define BUFFER_OFSET        LCD_FRAME_BUFFER + (RK043FN48H_WIDTH * RK043FN48H_HEIGHT * 4)

Aşağıdaki gibi bir for döngüsü yazdım.

  for (ram_counter = 0x00; ram_counter < BUFFER_OFSET; ram_counter++)
  {
    *(__IO uint32_t*) (LCD_FRAME_BUFFER + BUFFER_OFSET + ram_counter) = LCD_COLOR_RED;
  }

Fakat çalıştırınca işlemci hard fault'a düşüyor. Döngünün boyutunumu yanlış hesaplıyorum anlayamadım olayı. Yardım edebilecek olan var mı? Doğrudan RAM'e renk bilgisi yazarak nasıl ekrana hitap ederim?

CoşkuN

Adres değerleri 4'ün katı olmalı, döngü içerisinde 4'ün katı olmayan değerler oluşuyorsa büyük ihtimal oradan hard fault'a gidiyordur.

Mucit23

Hocam Hard_Fault'a gidiyorsa başka bir sebepten gitmeli.
Dediğinizi denedim döngüyü aşağıdaki gibi yaptım

   for (ram_counter = 0x00; ram_counter < 480*272; ram_counter++)
  {
     *(__IO uint32_t*) (LCD_FRAME_BUFFER + BUFFER_OFSET + ram_counter*4 ) = LCD_COLOR_RED;
      HAL_Delay(1);
      HAL_GPIO_TogglePin(GPIOC,GPIO_PIN_7);
  }

Mantıken böyle olması lazım ama hiçbir hareket yok.

CoşkuN

Hareket yok derken yine hard fault'a mı gidiyor? Adım adım debug yaparak nereden gittiğini görebilirsin aslında

Mucit23

Evet hocam aynen öyle, Döngü 1 kere çalıştığı zaman hemen hard fault'a düşüyor.

Elimde Başka bir kamera örneği var. Kamera örneğinde LCD ve kamera adresleri bu şekilde tanımlanmış.

#define CAMERA_FRAME_BUFFER               0xC0260000
#define LCD_FRAME_BUFFER                  0xC0130000

denedim ikisinde de Döngü çalışıyor. Yani hardFaulta düşmüyor ama ekranda da herhangi bir değişiklikte olmuyor.

Yokmu bu işi çözebilecek.

Mucit23

Çözdüm sorunu

Son olarak adreslerimi. Aslında adres çakışması gibi birşey oluyordu. Sorun benim adresleri yanlış hesaplamam dan kaynaklanıyordu.

Ekranda her bir pixel SDRAM'de 4 byte yer kaplıyor. Hesapları buna göre yapmak lazım.

Ekranın her bir katmanı 480*272*4 kadar yer tutuyor.

Son olarak başlangıç adreslerimi aşağıdaki gibi yaptım.

#define ARBG8888_BYTE_PER_PIXEL   4
#define LCD_FRAME_SIZE       ((uint32_t)RK043FN48H_WIDTH * RK043FN48H_HEIGHT * ARBG8888_BYTE_PER_PIXEL)
#define LCD_BG_START_ADRES   SDRAM_DEVICE_ADDR 
#define LCD_FG_START_ADRES   SDRAM_DEVICE_ADDR + LCD_FRAME_SIZE
#define CAMERA_START_ADRES   SDRAM_DEVICE_ADDR + (LCD_FRAME_SIZE*2)

Boyama içinde döngüyü aşağıdaki gibi yapmak gerekiyor.

   for (ram_counter = 0x00; ram_counter < (uint32_t)480*272*4; ram_counter+=4)
  {
     *(__IO uint32_t*) (LCD_FG_START_ADRES + ram_counter ) = LCD_COLOR_YELLOW;
  }