UART yazılımında başlangıç ​​bitini algılama


9

GPIO pinlerini kullanarak mikrodenetleyicime UART yazmayı deniyorum. Bu, daha fazla UART bağlantı noktasına sahip bir UC kullanan yeni tasarımı uygulayana kadar bir projeye geçici olarak bir UART kanalı eklemek içindir.

Zorlandığım şey bir seri akışta bir başlangıç ​​bitini doğru bir şekilde algılamak. Akışın kaynağı harici ve cihazımın ne zaman açıldığı umurumda değil. Bu yüzden cihazımın bir bayt iletiminin ortasında veri bitleri görmeye başlaması çok muhtemel. Kuşkusuz, bu bir başlangıç ​​biti ve diğer yüksek-düşük geçiş arasındaki farkı söyleyemeyeceğinden, yazılım UART'ımın hatalı değerleri okumasına neden olacaktır.

Bu bir UART kanalıyla kaçınılmaz bir sorun mu? Yoksa uC üreticilerinin donanım UART'larında kullandıkları akıllıca bir hile var mı?


İyi soru. Harici cihazınız sürekli olarak karakter gönderiyor mu? Değilse, başlangıç ​​biti ve durdurma bitinin hizalanıp hizalanmadığını kontrol etmelisiniz. Aradaki veriler çekinizle (toplam / bit) eşleşiyorsa?
Paul

Harici UART akışının bir önsöz göndermesini sağlayabilir misiniz? Bir akışın bir başlangıç ​​bitinden farklı olacağını gösteren özel bir veri akışı gibi mi? Bunu yapabilseydiniz, iletimin ortasında güç açıp açmamanız durumunda verilerin hatalı olup olmadığını söyleyebilirdiniz.
Funkyguy

1
Seri akış yeterince uzun bir boşta kalma süresi içermiyorsa - bölümünüzün bundan kurtulma olasılığı düşüktür. Beklediğiniz yerde "durdurma" bitini almamanız durumunda kısmi çözüm gelebilir. Ardından durumu sıfırlayabilir ve tekrar deneyebilirsiniz.
Eugene Sh.

1
Özel bir girişe ihtiyacınız yoktur ... sadece bir karakterden daha uzun bir dinlenme süresi (başlangıç, durdurma bitleri dahil). Ya da, aynı şey olan bir satırda 10'dan fazla durdurma biti.
Brian Drummond

2
Harici cihaz, sürekli olarak uzun bir karakter akışı gönderir, ancak bazen boşta kalır. En kötü durumda, ilk kez boşta kalana kadar girişi yok sayabilirim.
Dan Laks

Yanıtlar:


5

Veri akışının geri kalanından 1,5 bit süre gibi kolayca ayırt edilebilen bir durdurma biti uzunluğu kullanırsanız, orta iletim almaya başlamak kolay olmalıdır. Bununla birlikte, bu artan bir ek maliyete sahiptir. Durdurma bitinizin uzunluğunu artırdıkça, toplam kullanılabilir veri çıkışınız zarar görecektir.

Eğer otobüsü ağır bir şekilde kullanmıyorsanız ve sıklıkla çerçeveler arasında boşluklar varsa, o zaman bu boşluklardan birinin gerçekleşmesini beklemek ve ardından ilk hi-lo şanzımanınızın başlangıcı olarak almak meselesi olabilir. sonraki başlangıç ​​biti.

Veri bitlerinin sayısının, çerçeve boyutunda olduğu gibi tahmin edilebilir olması gerektiğini unutmayın, bu nedenle veriyolunun kapasitesinin% 100'ünü kullanıyor ve stop bitiniz tek bir bit süresi olsa bile, yine de yeterli kare toplarsanız biti başlatın. Her karede bir hi-lo geçişi olması garanti edilir. Durdurma biti daima yüksek olan bittir. Başlangıç ​​biti daima düşük olan bittir. Verilerinizin rastgele (veya yeterince rasgele) olduğunu varsayarsak, çerçevenizin boyutunda bir arabellek oluşturmak, içindeki her biti ayarlamak ve daha sonra arabellek yalnızca bu alana kadar bu arabellek içine almak gibi basit bir şey yapabilirsiniz 1 bit kümesi. Bu bit, stop bitiniz. Ondan sonraki başlangıç ​​bitiniz. İşte bu kadar! Sen buldun.

Eşlik biti kullanıyorsanız, başka bir seçenek iki kare değerinde veri almak, ilk düşük biti başlangıç ​​biti olarak seçmek ve ardından sağlama toplamını hesaplamak ve eşlik bitiyle karşılaştırmak olacaktır. Eşleşirse, başlangıç ​​bitini (muhtemelen) buldunuz. Değilse, bir sonraki düşük biti seçin ve iyi bir sağlama toplamı elde edene kadar tekrarlayın. İki veri çerçevenizde geçerli bir başlangıç ​​biti olarak kontrol edilen bir parça bulamazsanız, verileriniz bozuldu ve iki kare daha almanız gerekir.


Sadece başlangıç ​​ve bitiş bitleri hayatta kalana kadar VE karelerine birlikte düzgün bir fikir. Bu benim özel uygulama için çok fazla yük olacak, ama yine de akıllı.
Dan Laks

Harici cihaz, OP'nin üzerinde hiçbir kontrolü olmayan bir şeyse (bu, sorunun daha önceki bir yorumunda belirttiği gibi), durdurma bitinin uzunluğunu değiştirmesi olası değildir.
tcrosley

Bu cevabı yazmaya başladığım zaman bu yorum yapılmadı. Ancak, listelediğim diğer üç seçenek de durdurma biti uzunluğunun sabit olması durumunda geçerlidir.
Dr Funk

3

Donanım UART'ları aynı soruna sahiptir. Ama genellikle kendini kısa sırayla çözen bir şeydir. Her çerçevenin sonunda, durdurma bitini kontrol edin ve yüksek değilse, çerçeveyi atın ve bir sonraki yüksekten düşüğe geçişi bekleyin. Kaynaktaki verilerin tamamen patolojik olmadığını varsayarsak (örn., "UUUU" ya da ASCII 0x55'in uzun dizeleri), sonunda gerçek başlangıç ​​bitine "geçecektir".


1

8N1 iletimi varsayar.

Arka arkaya 9 yüksek veya düşük bit dizisi beklemelisiniz.

Yüksekse, verilerde boş bir boşluk veya bir 0xFF karakteri ve DURDUR biti
veya
düşükse bir BAŞLAT biti ve NULL 0x00 karakteri anlamına gelir.

Bu koşullardan biri yeniden senkronizasyona izin verecektir.

Hızlandırmak için: Verilerde mümkün olmayan belirli karakterleri biliyorsanız, her bit için gelen verileri tekrar tekrar (gerçekten sonra) ayrıştırabilirsiniz ve saçma olan (yüksek bit seti, daha düşük) 7 karakterlik bir dizi alırsanız büyük / küçük harf, kontrol kodları, noktalama işaretleri veya başka herhangi bir şey) ve ardından geçerli bir karakterle yeniden senkronize edildiğinizden emin olabilirsiniz.

Yerleşik bir UART çevre birimi kullandığınızda ve bitsel değerlendirme yapamadığınızda ve ayrıca tüm çerçeveleme hata bitlerini ve her ne zaman ortaya çıktıklarında (özellikle açıldığında) sıfırlamayı hatırlamak zorunda olduğunuzda benzer sorunlarınız olacaktır.

Sitemizi kullandığınızda şunları okuyup anladığınızı kabul etmiş olursunuz: Çerez Politikası ve Gizlilik Politikası.
Licensed under cc by-sa 3.0 with attribution required.