STM32F407 Cortex M4 şamataları

Başlatan bunalmis, 16 Ekim 2011, 17:14:50

ErsinErce


z

#241
Alıntı yapılan: ErsinErce - 24 Ekim 2011, 02:07:42
reserve bitlere ne yazarsanız farketmez ....

Bu çok tehlikeli.

Normalde yapılması gereken (fakat şu ana kadar verdiğim örnek programlarda yapmadım) reserve bitleri registerden okuyup aynen geri yazmaktır.

Çünkü bu rezerv bitler, çipin silicon revizyona girmesi ardından başka amaçlarla kullanılabilir. Bu durumda fi tarihinde yazdığınız kod ileri tarihlerde satın alacağınız çiplere yüklendiğinde çalışmayabilir yada abuk sabuk şeyler yapabilir.

Bu nedenle bir registere doğrudan veri yüklemek yerine,

1. Registeri oku
2. Değiştirilmesi gereken bit haricindeki bitleri maskele
3. Değişmesi gereken bitleri yerine koy
4. Sonucu registere yaz olmalıdır.

Bunu da bu vesileyle hatırlatayım. Dokümanlarda bu uyarı sık sık yapılır.

Bana e^st de diyebilirsiniz.   www.cncdesigner.com

z

#242
Timer interrupt kodlarımı yazarken o cümleyi aynen sizin anladığınız gibi anladım ve o anlama göre yazdım ve kodlarım çalışmadı.

Kodları debug ederek, registerin gerçekten 0 yüklenince silindiğini fakat sadece okunursa silinmediğini gördüm.

Bu durumda cümleyi yanlış tercüme ettiğimi yada burada BUG olduğunu varsaydım hem sildim hem okudum kod çalıştı.

Once silip sonra okumak yerine, önce okuyup sonra silmenin de işe yaramadığını gördüm.

Bu durumda o cümlenin Türkçesi anladığımız gibi olmayabilir. Belki de çipte bir BUG vardır.

Ilerleyen tarihlerde isin asli ortaya cikti. Interruprt rutininde bu biti sifirlamaya kalksarsak ve hemen ardindan da interrupt rutinininden cikarsak
sistem bir daha int rutinine girmiyor cunku aslinda bir silinmemis oluyor.

Silme isleminden sonra bir kac tane nop eklenmeli yada silme komutu int rutinine girer girmez isletilmeli. int rutinindeki diger kodlar isletilirken TIM7_SR registerindeki bitimiz silinme firsati taninmis oluyor. Sorun AHP frekansi ile CPU frekansinin ayni olmamasi yada pipeline mekanizmasindan kaynaklanan dusuk seviye olusan bir sorun.


Bana e^st de diyebilirsiniz.   www.cncdesigner.com

ErsinErce

#243
Hatamı düzelttim, bunu bilmek iyi oldu teşekkür ederim

bunalmis hocam ayrıca C dersleri başlamadan Hard_Fault gibi durumlar neden oluşur, nasıl aşılır, neler yapılmamalı
bunlardan bahsedebilirseniz çok iyi olur bende o konuya takılmış durumdayım,
hem programlama sırasında da bize yol gösterir diye düşünüyorum, yoksa sonraki konular mı bu durumlar?

Silinmeme durumu sadece simülatörde mi oluyor hocam yoksa kartta da aynı şekilde mi?

z

#244
Evet fault ve exceptionları sonraki konularda göreceğiz.
TI dan kolayca oluşturabildiğim  exceptionlar STM32F407 de oluşmuyor. (Şu ana kadar izlenimlerime göre TI mı ST mi derseniz cevabım kesinlikle TI.)

Alıntı YapSilinmeme durumu sadece simülatörde mi oluyor hocam yoksa kartta da aynı şekilde mi?

Simülatörü kullanmıyorum, kodları karta yüklüyor ve karttan debug ediyorum.

Yanlış anlaşılmasın, eğer  TIM7->SR set ise

        TIM7->SR=0;                 Bu komut gerçekten de TIM7_SR yi siliyor. Fakat aşağıdaki satır yazılmazsa bir daha  interrupta girmiyor.
        i=TIM7->SR;                 

Eğer  TIM7->SR set ise

        i=TIM7->SR;                  komutu flağı silmiyor. Tekrar okursam hala set olduğunu görüyorum.
Bana e^st de diyebilirsiniz.   www.cncdesigner.com

mcan

Alıntı yapılan: ErsinErce - 24 Ekim 2011, 02:28:34
Hatamı düzelttim, bunu bilmek iyi oldu teşekkür ederim

bunalmis hocam ayrıca C dersleri başlamadan Hard_Fault gibi durumlar neden oluşur, nasıl aşılır, neler yapılmamalı
bunlardan bahsedebilirseniz çok iyi olur bende o konuya takılmış durumdayım,
hem programlama sırasında da bize yol gösterir diye düşünüyorum, yoksa sonraki konular mı bu durumlar?

Silinmeme durumu sadece simülatörde mi oluyor hocam yoksa kartta da aynı şekilde mi?
Ben bendeki cm3 kartı ile deniyorum ve çalışmıyor.

z

Daha yukarıdaki mesajında da çalıştığını söylemiştin.
Bana e^st de diyebilirsiniz.   www.cncdesigner.com

mcan

#247
Alıntı yapılan: bunalmis - 24 Ekim 2011, 02:37:39
Daha yukarıdaki mesajında da çalıştığını söylemiştin.
Yukarıda verdiğim kod çalışıyor ancak "okuma" yada "sıfır yazma" satırını kaldırırsam çalışmıyor.
Sizin koddaki gibi okuma yapınca çalışıyor ama normalde sadece sıfır yazınca çalışmıyor.
Arkadaş da sanırım gerçekde okuma yapmadan sadece sıfır yazarak siliniyor mu diye sordu. ,Bu sebeple gerçek kart üzerinde okuma yapmadan çalışmıyor demek istedim.

Ayrıca hocam şunu sizdeki kartta denermisiniz
TIM7->SR  = 0x0;
		TIM7->SR  = 0x0;
		TIM7->SR  = 0x0;

Üç kere silince okuma yapmaya gerek kalmadan kod aynen çalışıyor .okuma kodunu silip yerine 3 kere TIM7->SR  = 0x0; kodunu yazdım şimdi aynı biçimde çalışıyor.Acaba timer7 nin saat frekansı kodların koştuğu frekansdan farklı diye bişeylermi oluyor? Yada "At overflow or underflow regarding the repetition cou..." diyor dökümanda , acaba biz interrupta girdiğmizde Underflow olayı da mı gerçekleşiyor?
Sizin frekans daha yüksek belki 5-6 kere yinelemeniz gerekeblir bende 3 kere yetti.

z

#248
Peş peşe 3 kez silmek işe yaramadı. CPU frekansını yarı yarıya düşürüp denedim gene olmadı.

Bana e^st de diyebilirsiniz.   www.cncdesigner.com

mcan

#249
Alıntı yapılan: bunalmis - 24 Ekim 2011, 03:01:14
Peş peşe 3 kez silmek işe yaramadı. CPU frekansını yarı yarıya düşürüp denedim gene olmadı.
Ben ahb prescaler değerini düşürdüm yani timer7 nin clock frekansını  arttırdım şimdi 1 kodla siliyor. Okuma yapmadan sadece sıfır yazınca siliniyor.
Frekanslarla alakalı bir iş var ama ne ?Eger siz sistem frekansini dusurdunuz ve bisey degismedi ise, olay cpu frekansi ile 'bus-timer' frekansi arasindaki orandan kaynaklaniyor olabilir. 

"100: AHB clock divided by 2" olarak ayarladım.

z

#250
CPU frekansını yarıyarıya düşürünce mecburen hem AHB hem de APB frekansları yarıya düştü. APB frekansını artıramam cunku en yuksek degerde çalışıyorum.
Hem AHB hemde APB yi ayrı ayrı düşürmem de işe yaramadı.

Olayın aslı neyse bir şekilde çıkar. Bana BUG gibi geldi.

Bana e^st de diyebilirsiniz.   www.cncdesigner.com

dombilik

Alıntı yapılan: bunalmis - 24 Ekim 2011, 01:31:33
Şu ana kadar neler yaptık;

CPU clock kaynağını kullanmayı,
GPIO portunu I/O olarak kullanmayı,
GPIO yu alternatif fonksiyon amaçlı kullanmayı,
Timer kullanmayı,
Interrupt kullanmayı

Çok basit anlamda da olsa gördük.

Kartlarınız geldiğinde bunları bizzat deneme şansınız olacak.

Şu anda deneme yapmamız gereken DMA, UART, I2C konuları var. Aslında çok konu var.

Fakat C dersleri geride kaldı. Ayrıca kursa katılanlar konuları takip ediyorlarmı etmiyorlarmı, anlıyorlarmı anlamıyorlarmı hiç fikrim yok.

Öte yandan ARM programlamayı, registerlere kuru sayılar yükleyerek yazmak gördüğünüz gibi mümkün hatta çok kısa kodlarla işler yütülebiliyor fakat okunurluğu yok.

Bundan sonrası için nasıl yola devam edelim?

Biraz dinlenelim mi?

Hocam ben kendi payıma dersleri takip ediyorum ve etmekte de zorlanıyorum.Başlangıç da C dersleri ile başlayıp temelden girileceğinden bahsedilmişti.
Ama ARM serisine yabancı olmayan ve C bilgisi iyi olan arkadaşlar bodoslama daldılar konuya..Bunu yadırgamıyorum gayet normal.Amacım eleştirmek de değil zaten.
Lakin aşağıdaki topic bomboş kaldı.
https://www.picproje.org/index.php/topic,35720.0.html
Sabırla sıranın benim gibilere gelmesini bekliyorum. :-[
Bildiklerini kime miras bıraktın?kimseyemi? O zaman bildiklerinin ne önemi kalır. ******** /////////// ******** PROTON-ASM PROTEUS 7.4 SP3 EAGLE 5.40

JKramer

@bunalmis

Kısmen konu dışı olacak ama 32 Bit Hesaplayici programınızda, sonuç bölümünü seçilip kopyalayacak şekilde yapmanız mümkün mü? Demek istediğim, ben ilgili bit'leri kutucuklara tıklayarak set ediyorum. İşim bittikten sonra sol altta hex karşılığı görmeme rağmen seçemiyorum, dolayısıyla kopyalayamıyorum.

z

O ozellik zaten var. Hic kopyalamaya calismadan paste demeyi denedinmi?
Bana e^st de diyebilirsiniz.   www.cncdesigner.com

kck87

Alıntı yapılan: bunalmis - 21 Ekim 2011, 15:14:25
Aşağıdaki örnek programı Keil ders başlığında son konuda vermiştim.

#include "STM32F4xx.h"

void SystemInit()
{
    RCC->AHB1ENR |= 0x00000008;    // GPIOD donanımının clock sinyalini uygulayalım
    GPIOD->MODER = 0x55000000;     // GPIOD nin 15, 14, 13, 12 pinleri cikis tanimlandi (Ledler bu pinlerde)
    GPIOD->OSPEEDR= 0xFFFFFFFF;   // GPIOD nin tum cikislarinı en yuksek hizda kullanacagiz
}

int main()
{
    while(1)
   {
     GPIOD->ODR= 0x0000F000;     // Ledler yansin
     GPIOD->ODR= 0x00000000;     // Ledler sonsun
   }
}


C dersleri başladığında göreceğiz fakat şimdiden RCC->AHB1ENR  şeklinde satır görürsek bunun, RCC register grubunun bir üyesi olan AHB1ENR registeri anlamına geleceğini bilelim. Yanı sonuçta bu bir register. Bu registeri Rehberde RCC_AHB1ENR olarak bulabilirsiniz.

Deneme kitindeki ledler  D portunun 15, 14, 13 ve 12 nolu bitleriyle kontrol ediliyor.

     GPIOD->ODR= 0x0000F000;     // Ledler yansin
     GPIOD->ODR= 0x00000000;     // Ledler sonsun

Yukarıdaki kodlar 32 bitlik D portuna 0x0000F000 ardından da 0x00000000 yazıyor.

Yani ilk satır 4 ledin hepsini birden yakıyor, sonraki satırda hepsini birden söndürüyor.

Şimdi SystemInit fonksiyonundaki

    RCC->AHB1ENR |= 0x00000008;    // GPIOD donanımının clock sinyalini uygulayalım
    GPIOD->MODER = 0x55000000;     // GPIOD nin 15, 14, 13, 12 pinleri cikis tanimlandi (Ledler bu pinlerde)
    GPIOD->OSPEEDR= 0xFFFFFFFF;   // GPIOD nin tum cikislarinı en yuksek hizda kullanacagiz

satırlarına bakın.

Rehber dokumanda  RCC_AHB1ENR, GPIOD_MODER ve GPIOD_OSPEEDR registerlerin anlatıldıkları sayfaları bulun.
Neden bu registerlerin içine yukarıdaki sayıları yüklediğimin cevabını bulmaya çalışın.

Bu çok önemli bir çalışma. Muhakkak uğraşın.


iş yüzünden çok nadir bakabiliyorum ve dediğiniz komutlara baktım ve şunları çıkardım.


AHB1ENR : reginin 3.biti d portunun clok unu aktif ediyor.

GPIOD->MODER : d portu 16 bacaklı, 32biti 2şerli gruplandırarak 1 port için 4 farklı durum belirlemesi yapılailiyor, rehberde
yazana göre 01 verince çıkış olarak ayarlıyoruz, bu sebepten 0x55000000 sayısını giriyoruz.

GPIOD->OSPEEDR :  aynı mantıkla 1 çıkış için 4 farklı çalışma hızı belirleyebiliyoruz 11 max hiz çalıştırmak için.
hesapladığımızda 0xFFFFFFFF değerini buluyoruz.

@bunalmıs hocam GPIOD->OSPEEDR= 0xFFFFFFFF yerine GPIOD->OSPEEDR= 0xFF000000 değerini verebilirmiyiz? nasıl olsa diğer portları
kullanmıyoruz.?

ayrıca ledleri yakmak için  GPIOD->ODR= 0x0000F000 yerine GPIOD->BSRR = 0X0000F000

ve ledleri söndürmek için  GPIOD->ODR= 0x00000000 yerine GPIOD->BSRR = 0XF00000000 komut ve değerleri kullanılabilirmi? keilde derlerken
hata verdi. kütüphanede 1 sıkıntı olabilirmi?

kullanılabilir ise bu komutları işleme hızları farklımıdır?
 nickim'in terör örgütünün kck yapılanması ile alakası yoktur. bazı arkadaşlarımdan butarzda duyumlar aldım.