STM32F DMA SORUSU VE HIZ PROBLEMİ(HIZLI)

Başlatan Murat Mert, 14 Ekim 2019, 17:18:17

Murat Mert

S.A. Kolay gelsin.
stm32f072rb ve stm32f103rb için ihtiyaç üzerine modbus slave yazdım. İlk önce frame ve party errorleri ile başım sıkıştı @mufitsozen  hocamızın sağolsun yardımlerı ve tecrübeleriyle çözdüm. stm32f103 olanda 2 port istendi bende dma nedir nasıl çalışır araştırdım. Projeyi uart_dma da çalıştırdım çok da hoşuma gitti. Yazılım olarak MikroC Arm kullanıyorum.
   **İlk sorum uart dan gelen verileri kesme ile bayt bayt aldım. Uart_rx_dma ile gelen paket sorsu ve emri belli olmadığı için tek bayt olarak rx_veri dizisine sıra ile aldım her transfer bitim uyarısında timer tetikleyip 4ms den sonra modbus slave işlemlerini yaptırdım ve uart_tx_dma ile dizi olarak değişken adetine göre ayarlayıp tek pakette sıkıntısız gönderdim. Şimdi rx için belli olmayan veri paketleri içi sizce doğru bir uygulama mı yaptım. Stm103rb de çok sıkıntısız çalıştı.

   **İkinci sorum stm32f103rb de yaptığım yazılımı dma olarak stm32f407 içinde uyarladım. tx_dma paketini çok hızlı veriyor ve master taşma yaşıyor. Dma olmadan yaptığım da seri veri yollama sırasında bayt lar arasında
Delay_us(1000000/baudrate);
bekleme koyuyordum sıkıntıyı en minimum seviyeye inmişti. Sistemde sorgu 10ms de 9600, 19200 de sıkıntılar var 38400 de azalıyor 57600 ve 115200 de olmuyor. Paketleri yanlışmı yolluyor diye izledim sıkıntı yok hata yapmamış ama scadanın 9600-19200 baud rx alım hızından hızlı veriyor galiba.

72mhz lik stm32f103 de sıkıntı yok. stm32f407 yi 120 mhz ye kadar indirdim sorunlar bir nebze azalıyor. Tx_dma'yı ağırlaştırma ayarı varmı(tecrübenize danışıyorum) yoksa düşük baudlar da 120mhz mi kullancağız.

stm103 72 mhz de 192 tagda 10s sorguda 1 dakikada yaklaşık 1000 (987)
stm407 168 mhz de 192 tagda 10s sorguda 1 dakikada yaklaşık 2000 (1896) 2000 rakamı hatalı cevaplar ile

Kolay gelsin.
mert07

Tagli

1) Ben de yaklaşık olarak senin yaptığın gibi yaptım. Modbus paketlerinin azami boyu zaten belli olduğu için ona göre bir bellek alanı ayarlayabilir ve DMA'yı kurabilirsin - ki sanırım sen de öyle yapmışsın. Hattın boşa düşmesi (3.5 karakter süresi boyunca bir sessizlik) durumunda DMA'yı kapatıp tampon bellekteki verileri değerlendirir, duruma göre TX DMA'sı ile cevap verir ve sonra RX DMA'sını tekrar kurarsın.

Ancak ben senin yaptığın gibi timer kurmadım doğrudan. STM32F051'lerde (ve sanırım diğer STM32F0'larda) USART1'de timeout süresi belirlenebiliyor. Yani modül, ayarlanan süre kadar sessizlik gördüğü zaman kesme oluşturabiliyor. Bunun için ayrı bir timer'a gerek yok. Bu özellik maalesef STM32F103 ve STM32F407'de yok (F1 ve F4'ün diğer işlemcilerinde durum nasıl bilmiyorum). Ancak bunlarda da "idle character" tespiti var. Bunun genişliğini ayarlamak mümkün değil. Modbus standartına uyup 3.5 karakter süresi belirleyemiyorsun, her zaman 1 karakter oluyor. Ancak her ne kadar standarta aykırı olsa da ben bu şekilde kullandım, sorun çıkmıyor gibi.

2) Bu sorun hakkında pek bir fikrim yok. Belki clock uyuşmazlığı olabilir. Harici kristal kullandığından emin ol, dahili osilatörü kullandığında uyuşmazlık riski artar. İşlemciyi hızlı çalıştırıp USART modülünün clock hızını azaltmayı da deneyebilirsin. Artık hangi APB'ye bağlı ise (APB1 veya APB2) onun bölme oranını arttırarak modül hızını düşürebilirsin.

Master cihazın hakkında bir bilgim yok ama Modbus mantığına göre master'ın bir sorgusuna bir cevap verilir. Master cihaz azami boyutta bir Modbus paketini alabilecek bir tampon belleğe sahip olacak şekilde tasarlanmış olmalı. Tam sayı aklımda değil ama 256 byte gibi bir değerdi bu ve sağlanması çok da zor değil. Ama slave cihazda bir hata varsa ve kendisine tek bir sorgu gelmesine rağmen birden fazla Modbus paketi ile cevap veriyorsa bu durumda master cihazın saçmalaması normal. Öncelikle lojik analizör ile hatta bakıp böyle bir şeyin olmadığından emin olman lazım. Ayrıca analizörü kullanarak baud rate'leri falan da kontrol edebilirsin.
Gökçe Tağlıoğlu

Murat Mert

S.n. @Tagli teşekkür ederim dediklerinizi deneyip uygulayacağım sağolun.
mert07