Şu Kod Parçacıkları Nasıl Çalışıyor (HI-Tech)

Başlatan vitruvius, 05 Mayıs 2012, 21:39:53

vitruvius

Merhaba, hitech hiç bilmiyorum. CCS C'de lcd'ye yazdırmak çok kolay ancak şu an fpga üzerinde çalıştığım için arka planda olanları öğrenmem lazım. Bunun için de Fx-Dev'in kitabından lcd ile ilgili konuyu okudum. Aşağıdaki kod parçaları nasıl çalışıyor? Yani ben lcd_yaz("S"); dediğimde ne oluyor? Bu "S" ilgili fonksiyonlarca nasıl algılanıp, yorumlanıyor? Yani "S" yazdırmak için "01010011" göndermek gerekiyor, bu çevrim nerede oluyor? Teşekkür ederim.

lcd_yaz ile ilgili olan fonksiyonlar:

lcd_busy
Burası gecikme veriyor, burada sıkıntım yok.
void lcd_busy(void)
{
DelayUs(250);
}


veri_yolla
Buradaki c değeri nereden geliyor?
void veri_yolla(unsigned char c)
{
rw=0;
rs=1; // Komut yolladan tek farkı, RS'nin 1 olması
e=1;
lcd_port = ( c & 0xF0 );
e=0;
lcd_busy();
e=1;
lcd_port = ( (c & 0x0F)<<4 );
e=0;
lcd_busy();
}


lcd_yaz
Burayı hiç anlamadım. *s ifadesi ne demek oluyor?
void lcd_yaz(const char * s) // LCD'ye string ifade gönderiliyor
{
lcd_busy();
while(*s)
veri_yolla(*s++);
}

justice_for_all

mesele  diyelim  merhaba gondereceksiniz lcd_yaz("merhaba"); yazinca bu fonksiyon dizinin baslangic adresini goderiyor aslinda bu fonksiyonla dizinin baslangic adresini gonderiyoruz.lcd yaz fonksiyonundada dizideki elemanlar sirayla lcd_veri yolla fonksiyonuna gidiyor.*s bu ifade ise pointer yani gelen dizinin baslangic adresini tutuyor.


edit : imla
Deneyip de başaramayanları değil, yalnızca denemeye bile kalkışmayanları yargıla.   Gökhan Arslanbay

sigmoid

veri_yolla('S');

şeklinde veriyolla fonksiyonu çağrıldığında fonksiyon aşağıdaki şekilde tanımlandığı için

void veri_yolla(unsigned char c)

S harfi char tipideki c isimli değişkene yükleniyor. Lcd pic'e 4 bitlik data hattı ile bağlandığından dolayı önce c değişkenin ilk dört biti sonra alt dört biti lcdye gönderiliyor.

lcd_yaz fonksiyonuna gelecek olursak. * işareti ile bir pointerın gösterdiği adresteki değer okunur. Temel olarak aşağıdaki ikili lcd_yaz fonsiyonuna gönderilen string ifadeyi harf harf veri_yolla fonksiyonuna göndermektedir. *s ile s pointerının gösterdiği ilk adreste veri var mı? Stringlerin sonunda \0 karekter yer almaktadır.
*s++ harfi gönder, bir sonraki harf için pointer değerini arttır.

while(*s)             // kelime sonuna gelindi mi?
   veri_yolla(*s++);     // harfi gönder.


elektronikhobi

RS (Register Select) yani yazmaç seçim biti 0 olduğu zaman komut göndermek istediğimizi belirtiyoruz. 1 olduğu zaman da veri göndermek istediğimizi belirtiyoruz.

Ben burada lcd.c dosyasını kullanmıştım.

https://github.com/erdemoncel/sicaklik/blob/master/lcd.c

c basitçe tek karakterlik, harflik bir veri yazmak için kullanılıyor. Buna k da diyebilirdiniz. Aslında tüm veriler harf harf gönderiliyor.

const char * s de C'nin dizgi türüdür. C++'nin std::string sınıfı gibi C'de bir dizgi sınıfı olmadığı için örneğin 'çorba' gibi bir kelimeyi lcd_yaz işlevine gönderdiğim zaman teker teker harfleri yazdırıyor. Dikkat ederseniz aslında yaptığı harfleri teker teker yazdıran veri yolla işlevini çağırmak.

Detaylarına girmek gerekirse justice arkadaşımızın da bahsettiği gibi aslında C'de C++'nin std::string sınıfı gibi bir dizgi sınıfı olmadığı için aslında const char * bir dizginin ilk karakterini gösteren bir göstergedir. Dizginin tüm karakterlerini yazdırmak için teker teker \n sonlandırma karakterini görene değin bir döngü ile gezdirilir.

vitruvius

Yorumlarınız için teşekkür ederim, olayı anladım gibi. Peki değişken bir ifade, yani CG-ROM'da tanımlı olmayan bir ifade nasıl bir mantıkla yazdırılıyor? Mesela butona her bastığımda yukarı doğru sayan bir değişken olsun, yada adc'den okuduğum bir değişkeni nasıl bir düşünceyle yazdırabilirim?

Adc uygulamasındaki bir parça:
Bu parçacık nasıl çalışıyor ve bu hesaplar nereden geliyor?

Teşekkür ederim.
voltaj_1=(int)((ADRESH*256+ADRESL)/2); // Hesaplama yapılıyor
lcd_gotoxy(1,10); // Okunan değer LCD'ye yazılıyor
veri_yolla(voltaj_1/1000+48);
veri_yolla((voltaj_1%1000)/100+48);
veri_yolla('.');
veri_yolla((voltaj_1%100)/10+48);
veri_yolla(voltaj_1%10+48);
veri_yolla('V');

yamak

0 ın ascii kodu 48 olduğu için çıkan sonucu 48 le toplayıp gönderiyo mesela sonuc 2 ise 48+2=50 2 nin de ascii kodu 50 olduğu için ekrana 2 yazıyo

justice_for_all

ornegin 1000 sayisi bunu basamaklarina ayiriyo ve tek tek 48 asci koduna ekleyip gonderiyo.lcd kutuphanesinde tanimli zaten butun karakterler ve rakamlar tabi asci karsiliginda bunuda asciye cevirip gonderiyor.
Deneyip de başaramayanları değil, yalnızca denemeye bile kalkışmayanları yargıla.   Gökhan Arslanbay

vitruvius

Anladım hocam. Şimdi bu mantığı fpga'e uyarlamam lazım. Teşekkür ederim.

elektronikhobi

EPROM'a veri yazamadığımız için karakter oluşturucu belleğe (CGRAM) yazabiliyoruz. Burada özel karakter için ayrılmış 8 karakterlik boş yer var.

Her ne kadar D ile yazılmış olsa da bu mesajda Türkçe karakterlerin LCD ekrana nasıl yazıldığını konuşmuştuk.

http://ddili.org/forum/thread/678

http://www.geocities.com/dinceraydin/lcd/custom.htm

Özel karakterleri de bu sayfadan oluşturabilirsiniz.

http://mikeyancey.com/hamcalc/lcd_characters.php