Haberler:

Forum kuralları güncellendi LÜTFEN  okuyunuz:  https://bit.ly/2IjR3ME

Ana Menü

PIC deki tuzaklar

Başlatan d_yol, 17 Ocak 2007, 16:36:11

d_yol

PIC de acemilerin düşdüğü tuzaklar:

--------------------------------------------------------------------------------
Saykıl tuzağı:

PIC ler çoğunlukla bir saykılda komut işler.
Ama bir saykıl tek tekikleme değil, 4 tetikleme demek.
Bir NOP emiri 10MHZ de 100ns değil 400ns zaman harcıyor. Gecikme fonksyonlarda bunu hesaba katın. Zamanlayıcılar (Timer) maksimum  1/4
İşlemci frekansında çalışabiliryor.

--------------------------------------------------------------------------------
Kesme tuzağı:

Bütün işlemciler kesme anında programsayacı ve statü hücreyi kurtarıyor. PIC de ama sadece programsayacı kurtarılıyor.
Kesme işlemi yapan bölüm bu statü hücreyi bozuyor. Ana programa geri dölüldüğü zaman program yanlış statü bilgilerle devam ediyor.
Onun için kesme bölümde statü hücresini kayıt edin ve bitdiğinde geri yazın. mov komutu bunun için kullanılmaz çünkü Z-bilgiyi değiştiriyor.
Microchip bunun için bir öneride bulunuyor:

16F84:

   movwf   w_temp
   swapf   STATUS,w
   movwf   status_temp

Kesme bitiş:

   swapf   status_temp,w
   movwf   STATUS
   swapf   w_temp,f
   swapf   w_temp,w
   retfie
 

16F62x veya 12F6xx:

   movwf   w_temp
   swapf   STATUS,w
   bcf     STATUS, RP0       ; status_temp Bank 0
   movwf   status_temp

Kesme biitiş:
   swapf   status_temp,w
   movwf   STATUS
   swapf   w_temp,f
   swapf   w_temp,w
   retfie
 

16F87x:
   MOVWF   W_TEMP
   SWAPF   STATUS,W
   CLRF    STATUS
   MOVWF   STATUS_TEMP
   MOVF    PCLATH, W
   MOVWF   PCLATH_TEMP
   CLRF    PCLATH

Kesme bitiş:
   MOVF    PCLATH_TEMP, W
   MOVWF   PCLATH
   SWAPF   STATUS_TEMP,W
   MOVWF   STATUS
   SWAPF   W_TEMP,F
   SWAPF   W_TEMP,W
   retfie

'status-temp' Bank 0 tanımlanması gerek çnükü kesme anında hangi 'Bank'
bulunduğunuz bilemezsiniz.
 
--------------------------------------------------------------------------------

Kesme tuzağı 2:

Bir kesmede işlemci Interrupt-Flag denilen hücreye 1 verir.
Kesme sonunda bu hücreye 0 verilmesi gerek. Yoksa kesme işleminden sonra tekrar kesme olur ve progra sonsuz bir döngüye girer.

--------------------------------------------------------------------------------

Kesme tuzağı 3:

Pinlerin seviyesinde değişiklik olduğu zaman, bunu algılamak için
bir kesme kullanılır. Değişikliği PIC fark etmesi için pin seviyelerini bir hücre ile karşılaştırır.
Ama program başında bu portdan okuma yapmadığınız zaman, bu değişikleri PIC hiç bir zaman algılayamaz.

--------------------------------------------------------------------------------

Analog-Tuzak (Port A, Port GP):

Bazı PIC işlemcilerde İlk açılışta PORT A dijital giriş olarak ayarlanmamış.
Bu tabii dijital giriş veya çıkış olarak kullanmak mümküm değil.
Ancak PORT A dijital giriş/çıkış yaptıktan sonra çalışır.

; 16F876:
   BSF STATUS, RP0    ; Bank 1  
   MOVLW 0x06         ; PCFG3..0 = '0110'
   MOVWF ADCON1
   BCF STATUS, RP0    ; Bank 0
 

16F628 PORT A karşılaştıcı aktif, bunu kapatmak gerek

   BSF CMCON, CM0
   BSF CMCON, CM1
   BSF CMCON, CM2


12F629 PORT A karşılaştıcı aktif, bunu kapatmak gerek

   BSF CMCON, CM0
   BSF CMCON, CM1
   BSF CMCON, CM2
 

; 12F675 PORT A karşılaştıcı ve analog giriş aktif, bunu kapatmak gerek
   BSF  CMCON, CM0
   BSF  CMCON, CM1
   BSF  CMCON, CM2
   BSF  STATUS, RP0        ; Bank 1
   CLRF ANSEL              ; GP0,1,2,4 ADC -> digital
   BCF  STATUS, RP0        ; Bank0


--------------------------------------------------------------------------------

Veri tablosu Tuzağı:

Sabit değerler genelde program bellekte tutulur. Aşagıda bir 7-Segment display çalıştıran bölüm.
Örneğin 4 göstermek için "w" ye 4 verilir. "call Segmente" çağrılır ve addwf programsayacı 4 yükseltilir.
böylece retlw B'11010100' ; 4 satıra gider ve "w" segmentin değerini verir.


    ; 7-Segment-Table
Segment
     addwf PCL, f
     retlw B'00011000' ; 0
     retlw B'11011110' ; 1
     retlw B'00110010' ; 2
     retlw B'01010010' ; 3
     retlw B'11010100' ; 4
     retlw B'01010001' ; 5
     retlw B'00010001' ; 6
     retlw B'11011010' ; 7
     retlw B'00010000' ; 8
     retlw B'01010000' ; 9


Ama böyle tablolarda addwf sadece 8 bit çalıştığına ama program sayıcı daha büyük olduğunu dikkat etmek gerek.
Tablo içinde XXXFF şeklinde Komutadresi olmaması gerek. addwf böyle adreslerin üzerinden değil,
istenilen hedefin 256 Byte önüne atlar.
Adresleri "*.lst" dosyasında kontrol edin ve "org" komutlarıyla ayarlayın.  

--------------------------------------------------------------------------------

I2C-Tuzak:

Büyük PIC lerde seri iletişim vardır (örn. PIC16F87x).
Bazen I2C arabirimde olabiliyor. I2C pinleri dahili dirençler olmadığı için, bunları pinlere harici takmak lazım.
Aksi takdirde PIC girişi "low" başka "master" kullanıyor diye olarak görürür.
PIC kontrolü ele alamaz.  

--------------------------------------------------------------------------------

in/out-Tuzak:

Her Port yazmada (PORTA..PORTE, GPIO) önce Port okunuyor. Okunan Byte değiştiriliyor ve PORT geri yazılıyor.
Bunu tek bir bit yazıldığı zamanda geçerli (bsf, bcf).
İlk okumada PORT hücrelerden değil, direk pinlerden okuyor. Çıkışlarda bu fark etmez ama ama giriş ayarlanmış pinlerde
Port hücresi istenilmiyen şekilde değişebilir. Çıkış olarak değiştirildiğinde seviyeler ön görüldüğü gibi olmayabilir.
 

Örnek:
Bir PIC RB0 giriş 10kOhm dirençle Vss (Taprağa) bağlı, RB1 10kOhm ile Vdd (+5V) bağlı.
Bütün pinlere "0" veriliyor:

; 16Fxx RB0..7 çıkış
   BSF  STATUS, RP0    ; Bank 1
   CLRF TRISB          ; PORTB çıkış
   BCF  STATUS, RP0    ; Bank 0
   CLRF PORTB          ; bütün pinlere 0

Bütün pinlerde "0" var.
RB0 ve RB1 giriş oluyor ve RB2 "1" veriliyor.

; 16FXX RB0 ve RB1 giriş
   BSF  STATUS, RP0    ; Bank 1
   BSF  TRISB, 0       ; RB0 giriş
   BSF  TRISB, 1       ; RB1 giriş
   BCF  STATUS, RP0    ; Bank 0
; RB2 high
   BSF  PORTB, 2       ; RB2 high


RB0 ve RB1 giriş olduğunda, dirençlerin belirlediğig seviyeyi alır. RB0 da "0" RB "1" var. Ama PORTB hücresinde ikiside 0.

RB2 yi "1" yapıldığındaa PIC hepsini önce okuyor. RB1 den dirençten dolayı "1" okunuyor.
PIC bunu okuyor: 00000010
Sonra Bit 2 "1" veriyor:  00000110
ve sonucu PORTB hücreye yazıyor.
Ama sadec Bit 2 değil Bit 1 de "1" oluyor.
RB1 giriş olduğu için yanlış yok. Ama RB0 und RB1 çıkış yaptığımızda:

; 16Fxx RB0..7 çıkış
   BSF  STATUS, RP0    ; Bank 1
   CLRF TRISB          ; PORTB auf çıkış
   BCF  STATUS, RP0    ; Bank 0

RB1 değişen değeri veriliyor. RB0 "0" veriyor ve RB2 "1", ama RB1 birden "1" var, Bu istenmeyen bir sonuç.
 
PIC18Fxxxx-tiplerde bu problem iki farklı komutla çözüldü. Portları (z.B. PORTA oder PORTB) okumamada direk pinler okunuyor.
Diğeri ile LATX (LATA veya LATB) komutla direk hücre okunuyor.    


--------------------------------------------------------------------------------

RA4-Tuzak:

RA4 bir open-Drain-Çıkış. Bunu başka çıkışlara bağlama fikri geliyor. Örenğin I2C simule temek için.
RA4 hem çıkış ve giriş kullanıldığı zaman  in/out-Tuzak devreye giriyor.


--------------------------------------------------------------------------------

I/O-Hız Tuzak:

Portlara yazıldıgı zaman saykılın sonunda porta yazılıyor.
Portlardan okunduğu zaman saykılın başında portan okunuyor.

örnek:
PIC 20 MHz ile çalışıyor. Port B  çıkış. PORTB ilk başta 0xFF var:

   CLRF  PORTB          ; Port B sıfır ver
   MOVFW PORTB          ; Port B oku

w de hangi değer var ??

00000000 tahmin ediyorsunuz. Genelde bu değer olur ama buna garanti verilmez.

20 MHz saykıl 0,2 µs. Port B okuma yazma ile arasında en fazla 0,05 µs = 50 ns var.
Pinlere bağlı Kondensatörler bu kısa zamanda 0 çkilmesini önler.
Bir 1nF Kondensatörü sıfıra çekmek için 80ma akım gerekli.
Onun için araya NOP koymanız gerek.

--------------------------------------------------------------------------------

mcan

yazı çok hoşuma gitti eline sağlık,umarım c derleyicileri bu işleri bizim için hallediyorlardır :D (ediyormu etmiyormu bilmiyorum)

Elektron74

@d_yol
   Güzel bir yazı olmuş. ASM kulanılacaksa PIC yeni başlayanların kesinlikle göz önünde bulundurmaları gereken hususlar. Yalnız ben Vei tablosu tuzağını anlayamadım. Özellikle şu cümleleri
       "Ama böyle tablolarda addwf sadece 8 bit çalıştığına ama program sayıcı daha büyük olduğunu dikkat etmek gerek.
Tablo içinde XXXFF şeklinde Komutadresi olmaması gerek. addwf böyle adreslerin üzerinden değil,
istenilen hedefin 256 Byte önüne atlar.
Adresleri "*.lst" dosyasında kontrol edin ve "org" komutlarıyla ayarlayın"
    Bir örnekle açıklarsanız sevinirim. Saygılar.
Yarın; yorgun kimselerin değil rahatlarına kıyabilenlerindir.

teknikelektronikci

gercekten elerinize saglik süper bilgi yalniz bunlar sirf asm icinmi gecerli yoksa digerleri icinde genel bir bilgi olarak ele alabilirmiyiz.
Ey Türk istikbalinin evlâdı! İşte, bu ahval ve şerâit içinde dahi, vazifen; Türk İstiklâl ve Cumhuriyetini kurtarmaktır! Muhtaç olduğun kudret, damarlarındaki asil kanda mevcuttur!

supermakarna

Alıntı yapılan: "Elektron74"@d_yol
   Güzel bir yazı olmuş. ASM kulanılacaksa PIC yeni başlayanların kesinlikle göz önünde bulundurmaları gereken hususlar. Yalnız ben Vei tablosu tuzağını anlayamadım. Özellikle şu cümleleri
       "Ama böyle tablolarda addwf sadece 8 bit çalıştığına ama program sayıcı daha büyük olduğunu dikkat etmek gerek.
Tablo içinde XXXFF şeklinde Komutadresi olmaması gerek. addwf böyle adreslerin üzerinden değil,
istenilen hedefin 256 Byte önüne atlar.
Adresleri "*.lst" dosyasında kontrol edin ve "org" komutlarıyla ayarlayın"
    Bir örnekle açıklarsanız sevinirim. Saygılar.

1024 baytlık program memory var diyelimki
eğer retlw komutunu kullanacaksanız bunu sadece 0-255baytlık program araşıgında kullanabiliriz.
000h-0FFh----->Bu aralıkta olmalı tablo
100h-1FFh----->kullanılabilir fakat pclath değiştirmek gerekir
200h-2FFh----->kullanılabilir fakat pclath değiştirmek gerekir
300h-3FFh----->kullanılabilir fakat pclath değiştirmek gerekir