18F24K22 çift USART interrupt yapısı,çalışma şekli ve tanımlamaları ?

Başlatan mustafa_cmbz, 27 Kasım 2018, 01:05:25

mustafa_cmbz

@OG hocam

Kod Seç
 KESME:
 
 
Context Save
 GIE
=0
 GIE2
=0    
 
 
                  
 
'hserin [NEXTION_BILGI]
 NEXTION_BILGI   = RCREG1
 CO2             = RCREG2 
                  
 RCIF2=0
 RCIF=0
 GIE2=1
 GIE=1 
 
 Context Restore
 End 


kesme kısmım bu şekilde fakat 2. rx ten gelen bilgiyi alamıyorum.

Kod Seç
CO2             RCREG2 
ya kesmeyi kuramadım yada datayı alamıyorum bilemedim.Ufak bir örneğiniz varmıdır kesmeleri kurma açma kapama ile ilgili..

Ayrıca;

Ds18b20 kullanacağım için sıcaklık bilgisini word olarak karşıya göndermem gerekiyor bunu sayaç kurup 2 byte şeklinde almalısın dediğin kısma da örnek verme şansın varmıdır ?

çıkamadım işin içinden..


Ayrıca extra bilgi hatırlayamadım demiştin.Beklemeler kesmede gecikmeler yaratıyor...

                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                 

OG

Alıntı yapılan: undefinedgelecek olan datanın adedini X belirliyor yani kaç byte olduğunu bilemiyoruz, bunu protonda belirleyebilirmiyiz?
X belirlemiyor, data geldikce X'i 1 arttırıp kaç data geldiğini görüyoruz. Beklediğimiz yeterli sayıda data geldi ise değerlendirmelerimizi yapıyoruz.
Data onunde bir header bilgisi koyulursa değerlendirmek kolaylaşır.
Mesela header bilgisi string olarak 3 byte ve "PRO" olsun
X = 0 için (ilk alınacak değer) "P" değil ise X arttırılmaz
X=0 için gelen illa "P" olmalı, değise X = 0, "P" ise X=X+1
X=1 için gelen illa "R" olmalı, değise X = 0, "R" ise X=X+1
X=2 için gelen illa "O" olmalı, değise X = 0, "O" ise X=X+1
gibi,
bu header yöntemi işi kolaylaştırır

- - -
Alıntı yapılan: undefinedkesme kısmım bu şekilde fakat 2. rx ten gelen bilgiyi alamıyorum.
2. usartın kesmeleri doğru yönetilemiyordur. Şu an hemen paylaşabileceğim örnek hazırda yok.
Alıntı yapılan: undefinedbunu sayaç kurup 2 byte şeklinde almalısın dediğin kısma da örnek verme şansın varmıdır ?
Soru sayac ve onu ilerletme ise üstte verdiğim örnekteki gibi basit bir yöntem
word bilginin geliş sırasına dikkat edilirse (önce low sonra high byte) ve doğru değerlendirilirse basitce cözülür


mesela data dizinin şöyle olsun
"PRO", word_bilgi
Aslında bu şöyledir
"P","R","O", word_bilgi.lowbyte , word_bilgi.highbyte
yani toplam 5 byte
5 byte array 'imiz var, adi gelen olsun,
sayac 0'dan başlayacak.

Baslangicta sayaci temizledik
sayac = 0

kesmeyi aktifledik,
kesme oluştu
gittik

gelen[sayac] = RCREGx
datayi aldik, kesme ayarlarini hemen tekrar kurduk çıktık,
ama vakit geçirmeden kontrolleri yaptık ki sayac doğru değerde
(kontrolleri sonradan da yapabilirsin ama, hatalı alışları dikkate alırsak bu durumda array boyutunu daha büyük tutmak gerekir)
sayac = 0 ise gelen[0] = "P" midir kontrol ettik
evet "P" imis, sayac = sayac + 1 yaptık
hayir "P" değil imis, sayac = 0

sayac = 1 ise gelen[1] = "R" midir kontrol ettik
evet "R" imis, sayac = sayac + 1 yaptık
hayir "R" değil imis, sayac = 0

sayac = 2 ise gelen[2] = "O" midir kontrol ettik
evet "O" imis, sayac = sayac + 1 yaptık
hayir "O" değil imis, sayac = 0

sonraki sırada doğal olarak
gelen[3] = word_bilgi.lowbyte
gelen[4] = word_bilgi.highbyte

olacak.
Ancak bu bilgi yanlış gelmiş de olabilir. Bir kontrol yöntemi de buna uygulamak gerekir.
Bu kontrolün en basit yöntemi
word_bilgi 'yi 2 defa gondermek, ve alınanların aynı bilgi olup olmadığını birbiri ile karşılaştırmaktır.
2 defa göndermek yöntemini seçersen gönerme
Hserout ["P","R","O", word_bilgi.lowbyte, word_bilgi.highbyte, word_bilgi.lowbyte, word_bilgi.highbyte]

olur.
Bu durumda Array de 5 değil en az 7 indexli olmalı
we
gelen[3] = word_bilgi.lowbyte
gelen[4] = word_bilgi.highbyte
gelen[5] = word_bilgi.lowbyte
gelen[6] = word_bilgi.highbyte

gelen[3], gelen[5] e eşitmi
gelen[4], gelen[6] ya eşitmi
şeklinde kontrol edip doğru gelip gelmediğine karar verilmeli.

Daha güvenilir CRC gibi yöntemler de kullanabilirsin elbet, biraz daha işlem ilavesi getirir,
üstteki en basit yöntemdir,
bu en basit yontem ile daha guvenilir iş yapmak istersen bilgiyi 2 değil, 3 defa, 4 defa da gönderip o kadar eşitlik kontrolu yapabilirsin.


Alıntı yapılan: undefinedAyrıca extra bilgi hatırlayamadım demiştin.Beklemeler kesmede gecikmeler yaratıyor...
Böyle ise
uzun bekleme süreleri değil de
kısa ve tekrarlı bekleme süreleri döngüleri işine yarar.
mesela 100ms beklemen gerek
Delayms 100 değil de
2000 kere 50 usn lik bekleme dongusu kurarsın (for next ile)
O zaman Delayus 50 olan bekleme süren ile
her bekleme süresi olan 50 usn de bir çıkmış olursun,
kesme oluştu ise o bekleme süresi sonunda datayı kaçırmamayı sağlarsın. Tabi bu 50 usn örneği düşük hızlı gönderimler için.
Mesela 9600 hız için (8N1) 1 Byte gitme süresi 1/960 = 0,00104166 sn yani 1,042 ms gibi bir süredir.
Sen ise üstteki durumda 50 usn de bir kesme rutinine gitmeyi garantilemiştin. Gelen datayı alıp taşmayı engellemeiş oldun.
gibi.
FORUMU İLGİLENDİREN KONULARA ÖM İLE CEVAP VERİLMEZ.

mustafa_cmbz

Kod Seç
Symbol PEIE2 INTCON2.6        'Peripheral(çevresel) interrupt enable bit usart kesmesi için
 Symbol GIE2  = INTCON2.7        '
global interrupt enable
 Symbol RCIE2 
PIE3.5          'Receiver interrupt enable bit
 Symbol RCIF2 = PIR3.5          '
Receiver interrupt flag


 Symbol PEIE 
INTCON.6         'Peripheral(çevresel) interrupt enable bit usart kesmesi için
 Symbol GIE  = INTCON.7         '
global interrupt enable
 Symbol RCIE 
PIE1.5           'Receiver interrupt enable bit
 Symbol RCIF = PIR1.5           '
Receiver interrupt flag
 
 
' PIR1.5 ve PIR3.5

 
  On_Interrupt GoTo KESME       '
Hardware Interrupt oluştuğunda int etiketine dallan     
 


 RCIE
=1
 RCIE2
=1
 
 PEIE
=1
 PEIE2
=1
 
 GIE
=1
 GIE2
=1
 
 RCIF
=0
 RCIF2
=0




'*************************/ ANA PROGRAM /*****************************

  BASLA:
 
  For A=0 To 1000
 
  If NEXTION_BILGI = ANA_SAYFA_DON  Then GoSub NEXTION_ANA_SAYFAYA_GEC       :  NEXTION_BILGI = 0
  If NEXTION_BILGI = CO2_TUS        Then GoSub NEXTION_CO2_SAYFAYA_GEC       :  NEXTION_BILGI = 0
  If NEXTION_BILGI = NEM_TUS        Then GoSub NEXTION_NEM_SAYFAYA_GEC       :  NEXTION_BILGI = 0
  If NEXTION_BILGI = SICAKLIK_TUS   Then GoSub NEXTION_SICAKLIK_SAYFAYA_GEC  :  NEXTION_BILGI = 0
  If NEXTION_BILGI = FAN_TUS        Then GoSub NEXTION_FAN_SAYFAYA_GEC       :  NEXTION_BILGI = 0
  
  DelayMS 50 : GoSub SENSOR_OKU : GoSub MELODI 
  Next 
  GoTo BASLA

'
------------------------------------------USART Receiver kesmesi-----------------

 
KESME:
  
'Disable
 Context Save
 GIE=0
 GIE2=0    
 PEIE=0
 PEIE2=0
 
 NEXTION_BILGI            = RCREG1
 USART2_DATA              = RCREG2
  
 CO2=USART2_DATA : GoSub SENSORLERI_EKRANA_YAZ :  CO2=0  : USART2_DATA=0
                  
 RCIF2=0
 RCIF=0
 GIE2=1
 GIE=1        '
Yani INTCON.7=1 kesmeleri açtik.
 
'Resume                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                    
 '
Enable 
 Context Restore
 End  

kodun genel hatları bu şekilde.

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

2. usartı girişini interupt a bağladım..

Kod Seç
 Symbol RCIE2 PIE3.5          'Receiver interrupt enable bit
 Symbol RCIF2 = PIR3.5          '
Receiver interrupt flag

yukarıdaki PIR3.5 VE PIE3.5 i data sheetten bakarak düzenledim.

Fakat:

Data alıyor ama aldıktan sonra takılıp kalıyor.Kesmeden mi çıkmıyor nerde kalıyor nerde donuyor isis te simulasyonda da göremiyorum.Sanki programda bekleme yaptığında simulasyon bekleme süresince duruyor ya o nun gibi simulasyon duruyor gibi geldi.




mustafa_cmbz

@OG hocam merhabalar..

Kod Seç
KESME:
 
Context Save
 GIE
=0
 GIE2
=0    
 PEIE
=0
 PEIE2
=0
 RCIF2
=0
 RCIF
=0
 
 
 
'NEXTION_BILGI            = RCREG1
 USART2_DATA               = RCREG2
 '
HSerIn2 [CO2]
  
 If 
SAYAC 0 Then USART2_DATA[0] = "M" SAYAC SAYAC 
 
If SAYAC 1 Then USART2_DATA[1] = "C" SAYAC SAYAC 1

 
If USART2_DATA[2] = USART2_DATA[4] And  USART2_DATA[3] = USART2_DATA[5]  Then USART2_WORD.LowByte  USART2_DATA[2] : USART2_WORD.HighByte USART2_DATA[3] : CO2=USART2_WORD  USART2_DATA=SAYAC=0  :  High KOD_LED



 SAYAC
=0

 GIE
=1
 GIE2
=1    
 PEIE
=1
 PEIE2
=1
 RCIF2
=1
 RCIF
=1             'General interrupt enable bit
 
 Context Restore
 
 End

Verdiğin örnekleri kod'a uyarlamaya çalıştım...

Data geliyor alıyorum datayı bahsettiin şekilde teyit edip kontrol ediyorum o kısımdan da doğru bir şekilde geçip karşılığında LED yaktırıyorum fakat elde ettiğim değeri bir türlü kesme etiketinin dışında kullanamıyorum.

Nerede yanlış yapıyorum ?

pro-TR

Kod Seç
RCIF2=1
 RCIF
=1

usart kesmelerinin bayraklarını sıfırlaman gerekirken neden bayrakları 1 de tutuyorsun? normalde RCIF usart kesmesi oluştuğunda otomatik olarak 1 oluyor, biz kesme içinde o bayrağa göre kesme içinde etiketleniyoruz sonrada  o bayrağı siliyoruz. yani çıkışta 0 laman gerekiyor
vardım ilim meclisine eyledim talep, meğer ilim en gerideymiş illa EDEP, illa EDEP <muhyiddin Arabi K.S.>

mustafa_cmbz

Kod Seç
  On_Interrupt GoTo KESME      'Hardware Interrupt oluştuğunda int etiketine dallan    
 

 
 RCIE=1
 RCIE2=1
 
 PEIE=1
 PEIE2=1
 
 GIE=1
 GIE2=1
 
  DelayMS 2000
  GoSub SENSOR_OKU


'
*************************/ ANA PROGRAM /*****************************

  BASLA:
  
  For A=0 To 10
  DelayMS 10
  
  Next 
  GoSub SENSOR_OKU :GoTo ANA
  
  ANA:
  If SAYAC=4 Then SAYAC=0 : USART2_WORD.LowByte = USART2_DATA[2] : USART2_WORD.HighByte = USART2_DATA[3] : CO2= USART2_WORD : GoSub SENSORLERI_EKRANA_YAZ  :  High KOD_LED
  GoTo BASLA

 '------------------------------------------USART Receiver kesmesi-----------------

 KESME:
 Context Save
 GIE=0
 GIE2=0    
 PEIE=0
 PEIE2=0
 RCIF2=0
 RCIF=0
 
 
  'NEXTION_BILGI            = RCREG1
 
 USART2_DATA[SAYAC]= RCREG2 : SAYAC=SAYAC+1 
 
 GIE=1
 GIE2=1    
 PEIE=1
 PEIE2=1
 RCIF2=1
 RCIF=1            'General interrupt enable bit
 
 Context Restore
 
 End

@OG Hocam yardımların için çok teşekkür ederim.

Sonunda usart2 kesmesinden datayı almayı başardım.

En başta anlamadığım şuymuş:

Ben usart kesmesindeki byte byte gelen datayı HSERİN komutundaki gibi direkt

Kod Seç
USART2_DATARCREG2
diyince alacağımı sanıyordum ve sonra sırası ile array dizinine koymak gerektiğini sanıyordum.OYSA öyle değilmiş..:

karşıdan Hserout ["M","C",SICAKLIK.LOWBYTE,SICAKLIK.HIGHBYTE] diye bilgi gönderdiğimizde

Bu sırası ile "m" harfini 1 byte olarak gönderip alıcı kısmı kesmeye sokup bilgiyi alıp kesmeden çıkıp gönderici tarafın "c" harfini aradan zaman geçmeden tekrar gönderip alıcı tarafı tekrar kesmeye soktuğunu ( diğerleri için de aynı şey geçerli) gözlemlemem ile iş değişti...

yani byte byte gönderip her gelen byte paketinde bir kez kesmeye gidip gelen byte paketini RCREG2 tan almak ve tanımladığımız byte dizinine dizmek  gerekiyormuş..

Geriye güvenlik önlemleri kaldı.Çok teşekkür ederim...

mustafa_cmbz

Alıntı yapılan: pro-TR - 08 Aralık 2018, 20:32:15
Kod Seç
RCIF2=1
 RCIF
=1

usart kesmelerinin bayraklarını sıfırlaman gerekirken neden bayrakları 1 de tutuyorsun? normalde RCIF usart kesmesi oluştuğunda otomatik olarak 1 oluyor, biz kesme içinde o bayrağa göre kesme içinde etiketleniyoruz sonrada  o bayrağı siliyoruz. yani çıkışta 0 laman gerekiyor

Selami abi 2. usart aktif fakat şöyle bir sıkıntım var şuan 1. usarttan bilgiyi alamıyorum yada kesme olduğunda hangi değeri alacağımı karıştırıyorum.

Senin bahsettiğin flaglar kesme oluştuğunda 1 oluyorsa şayet bunlara bakarak hangi porttan bilgi geldiğine bakayım dedim olmadı.

Kod Seç
 KESME:
 
Context Save
 GIE
=0
 GIE2
=0    
 PEIE
=0
 PEIE2
=0
 
 
If RCIF=1  And RCIF2 =1  Then EXIT
 If 
RCIF=1  Then EKRAN_INTERUPT
 
If RCIF2=1 Then SENSOR_INTERUPT
 
GoTo EXIT
 
 
 
EKRAN_INTERUPT:
 
NEXTION_BILGI RCREG1 High  LED_3 : GoTo EXIT
 
 
 
SENSOR_INTERUPT:
 
USART2_DATA[SAYAC]= RCREG2 SAYAC=SAYAC+1  NEXTION_BILGI=: GoTo EXIT
 
 
 EXIT:
 
GIE=1
 GIE2
=1    
 PEIE
=1
 PEIE2
=1
 RCIF2
=0
 RCIF
=0             'General interrupt enable bit
 
 Context Restore
 
 End

pro-TR

mustaafa senin için üşenmedim  3. pic arası usarttan haberleşen bir kod yazdım, her pic okuduğu değeri ekrana yazan ayrıca ana işlemciye okuduğu adc yi gönderen, ana picinde okuduğu değeri de diğer işlemcilere gönderen bir yapı, acele ile yazdığım için açıklama yazamadım. ilgili resmi buraya, kaynaak kodunuda yükleme sitesine ekledim.
http://dosya.co/60oog6zkqu93/cift_usart.rar.html




vardım ilim meclisine eyledim talep, meğer ilim en gerideymiş illa EDEP, illa EDEP <muhyiddin Arabi K.S.>

mustafa_cmbz

Sağolasın abi bi yukarda verdiğin flag kontrolü nedense benim koddaki for next dçngüsünden dolayı çalışmıyormuş.değiştirince 2 usart kesmeni de kullanbildim.