avatar_ewreka

Pic Kendini Resetliyor

Başlatan ewreka, 26 Ocak 2018, 23:48:04

ewreka

Merhaba dostlar.

Mini sumo robot projeme tam gaz devam etmekteyim, fakat projeyi iki alanda
parça parça yapmaya karar verdim;

1-CNY ler
2-MZ80 ler

1-Cny'ler çalışıyor fakat ufak tefek elden geçmesi gerekecek.
2-MZ80 ler sonra...

Soruma gelince: Pic kendini resetliyor, fakat resetlenmesi bazen 2 bazen 30 saniye
kadar sürüyor
Bu En Büyük Problem, Ayrıca bazen beyaz alanın dışına çıkıyor, mesela
5 kez beyaz alanla karşılaşmışsa 2 sinde beyaz alanı geçebiyor.

Aşağıda kodu veriyorum;
a)_li-po pili yeni şarz ettim (yani düşük voltaj olmamaması lazım)
b)_mclr 10k ile (+5v) 'a bağlı
c)_16f628a ve 74hc14 ve L293d kullanıyorum.


@ __CONFIG _INTRC_OSC_NOCLKOUT & _WDT_OFF & _PWRTE_OFF & _MCLRE_ON & _LVP_OFF & _CP_OFF & _BODEN_OFF
DEFINE OSC 4
OPTION_REG.7=0
CMCON = 7
VRCON = 0

TRISA = 0
TRISB = 1

input PORTB.0                                           'SOL mz80
input PORTB.1                                           'ON mz80
input PORTB.2                                           'SAG mz80
input PORTB.3                                           'SOL CNY70
input PORTB.4                                           'SAG CNY70
input PORTB.5                                           'ORTA CNY70
                                                        '-- Motorlar --
output PORTA.0                                          'in1    ILERI
output PORTA.1                                          'in2    GERI       
Output PORTA.2                                          'in3    ILERI
output PORTA.3

symbol SAG_ILERI_MOTOR = PORTA.3
symbol SOL_ILERI_MOTOR = PORTA.0
symbol SAG_GERI_MOTOR = PORTA.2
symbol SOL_GERI_MOTOR = PORTA.1
symbol Led = PORTA.7     

symbol SOL_CNY70 = PORTB.4
symbol SAG_CNY70 = PORTB.3
symbol ARKA_CNY70 = PORTB.5

BEYAZ VAR BIT
SIYAH VAR BIT
SIYAH = 1
BEYAZ = 0
COKLU_DONUS VAR BYTE

BEKLE:

low SAG_ILERI_MOTOR
LOW SOL_ILERI_MOTOR
LOW SAG_GERI_MOTOR
low SOL_GERI_MOTOR

low led
PAUSE 1000
high led
PAUSE 1000
low led
PAUSE 1000
high led
PAUSE 1000
low led
PAUSE 1000
high led
GOTO MAIN

MAIN:
    COKLU_DONUS=0
    if sol_cny70 = BEYAZ AND sag_cny70 = BEYAZ AND arka_cny70 = BEYAZ THEN
        GOTO ILERI_GIT
    ENDIF
    if sol_cny70 = SIYAH AND sag_cny70 = SIYAH AND arka_cny70 = SIYAH THEN
        GOTO ILERI_GIT
    ENDIF
    if sol_cny70 = BEYAZ AND sag_cny70 = SIYAH AND arka_cny70 = SIYAH THEN
        while sol_cny70 = SIYAH AND sag_cny70 = SIYAH AND arka_cny70 = SIYAH
            GOTO SolA_DON           
            COKLU_DONUS = COKLU_DONUS + 1
                if COKLU_DONUS = 5 THEN
                    GOTO ILERI_GIT
                ENDIF
        WEND
    ENDIF     
    if sol_cny70 = SIYAH AND sag_cny70 = BEYAZ AND arka_cny70 = SIYAH THEN
        while sol_cny70 = SIYAH AND sag_cny70 = SIYAH AND arka_cny70 = SIYAH
            GOTO SAGA_DON           
            COKLU_DONUS = COKLU_DONUS + 1
                if COKLU_DONUS = 5 THEN
                    GOTO ILERI_GIT
                ENDIF
        WEND
    ENDIF   
    if sol_cny70 = BEYAZ AND sag_cny70 = SIYAH AND arka_cny70 = BEYAZ THEN
        while sol_cny70 = SIYAH AND sag_cny70 = SIYAH AND arka_cny70 = SIYAH
            GOTO SolA_DON           
            COKLU_DONUS = COKLU_DONUS + 1
                if COKLU_DONUS = 5 THEN
                    GOTO ILERI_GIT
                ENDIF
        WEND
    ENDIF             
    if sol_cny70 = SIYAH AND sag_cny70 = BEYAZ AND arka_cny70 = BEYAZ THEN
        while sol_cny70 = SIYAH AND sag_cny70 = SIYAH AND arka_cny70 = SIYAH
            GOTO SAGA_DON           
            COKLU_DONUS = COKLU_DONUS + 1
                if COKLU_DONUS = 5 THEN
                    GOTO ILERI_GIT
                ENDIF
        WEND
    ENDIF   
    if sol_cny70 =  BEYAZ AND sag_cny70 = BEYAZ AND arka_cny70 = SIYAH THEN
        GOTO GERI_GIT
    ENDIF       
    if sol_cny70 =  SIYAH AND Sag_cny70 = SIYAH AND arka_cny70 = BEYAZ THEN
        GOTO GERI_GIT
    ENDIF   
goto MAIN

ILERI_GIT:
    LOW SAG_GERI_MOTOR
    LOW SOL_GERI_MOTOR
    high SAG_ILERI_MOTOR
    high SOL_ILERI_MOTOR   
goto main

DUR:
low SAG_ILERI_MOTOR
LOW SOL_ILERI_MOTOR
LOW SAG_GERI_MOTOR
low SOL_GERI_MOTOR
goto main

SAGA_DON:
LOW SOL_ILERI_MOTOR
LOW SAG_GERI_MOTOR
HIGH SAG_ILERI_MOTOR
HIGH SOL_GERI_MOTOR
goto main

SOLA_DON:
LOW SAG_ILERI_MOTOR
LOW SOL_GERI_MOTOR
HIGH SOL_ILERI_MOTOR
HIGH SAG_GERI_MOTOR
goto main

GERI_GIT:
    low SAG_ILERI_MOTOR
    low SOL_ILERI_MOTOR   
    high SAG_GERI_MOTOR
    high SOL_GERI_MOTOR
    PAUSE 500
goto main   

SAG_GERI_GIT:
    LOW SAG_ILERI_MOTOR
    LOW SOL_ILERI_MOTOR
    LOW SOL_GERI_MOTOR
    high SAG_GERI_MOTOR
goto main

SOL_GERI_GIT:
    LOW SAG_ILERI_MOTOR
    LOW SOL_ILERI_MOTOR
    low SAG_GERI_MOTOR
    high SOL_GERI_MOTOR
goto main

end

ete

#1
Programında bazı iyileştirmeler yapmak gerek. Karar verme mekanizmasına hız kazandırmak lazım. Bunun içinde karar anında işlemciyi fazla oyalamamak gerekir.
İşe donanımdan başlayalım.
SOL_CN70 =PORTB.4 de
SAG_CN70=PORTB.3 de
ARKA_CN70=PORTB.5 de yer alıyor.
Sen her bir sensörü tek tek değerlendiriyorsun. Bu gerçekten çok vakit alıcı bir işlemdir.
Bunun yerine şunu öneriyorum.
Elimizde 3 adet sensör var bunlar 000-001-010-011-100-101-110-111 şeklinde değişik değerler alabilir başkada değer alamaz.
Değerlendirmene bakılırsa sensörlerin aldığı değerlere göre 3 farklı işlem yapılıyor. Bunlar İleri git, Sola Dön ve Sağa Dön.
Şimdi ileri gitme konumlarına bakalım. %000-%111-%001-%110 Bunlar desimal olarak 0-7-1-6 konumlarıdır Bu değerleri portdaki PORTB.3-PORTB.4 ve PORTB.5 sensör sıralamasına göre tespit ettim.
Sola dönme Konumları %101 yani desimal 5 ve %100 yani desimal 4
Sağa dönme konumları %011 yani desmial 3 ve %010 yani desimal 2

Bu durumda işlemi kısaltmak için kesinlikle 3 sensörüde aynı anda okuyup değerlendirmen gerekiyor. Bunu yapacak komut
SENSOR=(PORTB & %00111000)>>3 komut satırı 3 sensörü de aynı anda okur ve sana bir değer verir. Böylece yukarıda açıkladığımız konumları test ederek istenilen işleri yaptırmak içinde;

IF SENSOR=4 OR SENSOR=5 THEN
  WHILE SENSOR=4 OR SENSOR=5
      SENSOR=(PORTB & %00111000)>>3
      GOSUB SOLA_DON   'burada goto kullanmışsın bu yanlış gosub olmalı ve sola_dönüs etiketi return ile bitmeli
      COKLU_DONUS = COKLU_DONUS + 1
       IF COKLU_DONUS=5 THEN
          COKLU_DONUS=0:GOTO ILERI
       ENDIF
    WEND
ENDIF


Şeklinde komut vermek ve benzer şekilde SAĞA dönüş içinde

    IF SENSOR=2 OR SENSOR=3 THEN
      WHILE SENSOR=2 OR SENSOR=3
         GOSUB SAGA_DON
         COKLU_DONUS=COKLU_DONUS+1
         IF COKLU DONUS=5 THEN
           COKLU_DONUS=0:GOTO ILERI_GIT
         ENDIF
      WEND
    ENDIF

komutlarını vermek yeterli olacaktır. Program bu satırları geçebiliyorsa sistemin ileri gitmesi gerekeceğinden bu satırların altına ileri git komut satırlarını yazman yeterkli olacaktır.
Aşağıda komple programının yeniden düzenlenmiş halini veriyorum,

@ __CONFIG _INTRC_OSC_NOCLKOUT & _WDT_OFF & _PWRTE_OFF & _MCLRE_ON & _LVP_OFF & _CP_OFF & _BODEN_OFF
DEFINE OSC 4
OPTION_REG.7=0
CMCON = 7
VRCON = 0

TRISA = %00000000
TRISB = %00111000

'input PORTB.0                                           'SOL mz80
'input PORTB.1                                           'ON mz80
'input PORTB.2                                           'SAG mz80
'input PORTB.3                                           'SOL CNY70
'input PORTB.4                                           'SAG CNY70
'input PORTB.5                                           'ORTA CNY70
'                                                        '-- Motorlar --
'output PORTA.0                                          'in1    ILERI
'output PORTA.1                                          'in2    GERI       
'Output PORTA.2                                          'in3    ILERI
'output PORTA.3

symbol SAG_ILERI_MOTOR = PORTA.3
symbol SOL_ILERI_MOTOR = PORTA.0
symbol SAG_GERI_MOTOR = PORTA.2
symbol SOL_GERI_MOTOR = PORTA.1
symbol Led = PORTA.7     

symbol SOL_CNY70 = PORTB.4
symbol SAG_CNY70 = PORTB.3
symbol ARKA_CNY70 = PORTB.5

BEYAZ VAR BIT
SIYAH VAR BIT
SIYAH = 1
BEYAZ = 0
COKLU_DONUS VAR BYTE
SENSOR VAR BYTE

pause 500

BEKLE:

low SAG_ILERI_MOTOR
LOW SOL_ILERI_MOTOR
LOW SAG_GERI_MOTOR
low SOL_GERI_MOTOR

low led
PAUSE 1000
high led
PAUSE 1000
low led
PAUSE 1000
high led
PAUSE 1000
low led
PAUSE 1000
high led
GOTO MAIN

MAIN:
    COKLU_DONUS=0
    sensor=(PORTB & %00111000)>>3
    IF SENSOR=4 OR SENSOR=5 THEN
      WHILE SENSOR=4 OR SENSOR=5
        GOSUB SOLA_DON
        COKLU_DONUS=COKLU_DONUS+1
        IF COKLU_DONUS=5 THEN
           COKLU_DONUS=0:GOTO ILERI_GIT
        ENDIF   
      WEND
    ENDIF
   
    IF SENSOR=2 OR SENSOR=3 THEN
      WHILE SENSOR=2 OR SENSOR=3
         GOSUB SAGA_DON
         COKLU_DONUS=COKLU_DONUS+1
         IF COKLU DONUS=5 THEN
           COKLU_DONUS=0:GOTO ILERI_GIT
         ENDIF
      WEND
    ENDIF
     
ILERI_GIT:
          SAG_GERI_MOTOR=0
          SOL_GERI_MOTOR=0
          SAG_ILERI_MOTOR=1
          SOL_ILERI_MOTOR=1                         
          GOTO MAIN
     

DUR:
    SAG_ILERI_MOTOR=0
    SOL_ILERI_MOTOR=0
    SAG_GERI_MOTOR=0
    SOL_GERI_MOTOR=0
    goto main

SAGA_DON:
         SOL_ILERI_MOTOR=0
         SAG_GERI_MOTOR=0
         SAG_ILERI_MOTOR=1
         SOL_GERI_MOTOR=1
         RETURN

SOLA_DON:
         SAG_ILERI_MOTOR=0
         SOL_GERI_MOTOR=0
         SOL_ILERI_MOTOR=1
         SAG_GERI_MOTOR=1
         RETURN

GERI_GIT:
         SAG_ILERI_MOTOR=0
         SOL_ILERI_MOTOR=0   
         SAG_GERI_MOTOR=1
         SOL_GERI_MOTOR=1
         PAUSE 500
         goto main   

SAG_GERI_GIT:
             SAG_ILERI_MOTOR=0
             SOL_ILERI_MOTOR=0
             SOL_GERI_MOTOR=0
             SAG_GERI_MOTOR=1
             goto main

SOL_GERI_GIT:
             SAG_ILERI_MOTOR=0
             SOL_ILERI_MOTOR=0
             SAG_GERI_MOTOR=0
             SOL_GERI_MOTOR=1
             goto main

end[code]
Pic in resetlenmesi işine gelince. Kullanığın motorlar çok fazla parazit yayıyor anlaşılan. Motor besleme uçlarına mutlaka 100nf kondansatör bağla. Tercihen motorları ayrı bir kaynaktan beslemen uygun olur. Böylece parazitlerin pic kontrol sistemine geçmelerini bir nebze olsun engellemiş olursun.  Kısaca resetleme sebebi motor fırçalarının yaydığı parazitlerdir. Kondansatörler bunu kesmesi gerekir. Kesmiyor ise mutlaka motorları ayrı bir kaynaktan beslemen gerekir.

Ete

ewreka

Sayın hocam çok teşekkür ederim cevabınız için (Bu arada SENSOR=(PORTB & %00111000)>>3 komutu çok zekice olmuş).

Kodu biraz değiştirdim, fakat reset sorunu düzelmedi, ama bazen bir dakika'nın üzerinde çalışıyor, sizce problem donanımsal mı?

Bu arada gerçek bir dohyom olmadığı için siyah kartonla idare ediyorum, en yakın zamanda bir tane edineceğim, tabi bazı dış etkenlerden de şüpheleniyorum.

Ayrıca çok beğendiğim bir besleme devresinden yararlanıyorum sorun nedir sizce.

Diğer arkadaşlar belki koddan yararlanmak isterler;


@ __CONFIG _INTRC_OSC_NOCLKOUT & _WDT_OFF & _PWRTE_OFF & _MCLRE_ON & _LVP_OFF & _CP_OFF & _BODEN_OFF
DEFINE OSC 4
OPTION_REG.7=0
CMCON = 7
VRCON = 0

TRISA = %00000000
TRISB = %00111000

symbol SAG_ILERI_MOTOR = PORTA.3
symbol SOL_ILERI_MOTOR = PORTA.0
symbol SAG_GERI_MOTOR = PORTA.2
symbol SOL_GERI_MOTOR = PORTA.1
symbol Led = PORTA.7     

symbol SOL_CNY70 = PORTB.4
symbol SAG_CNY70 = PORTB.3
symbol ARKA_CNY70 = PORTB.5

BEYAZ VAR BIT
SIYAH VAR BIT
SIYAH = 1
BEYAZ = 0
COKLU_DONUS VAR BYTE
SENSOR VAR BYTE

pause 500

BEKLE:

low SAG_ILERI_MOTOR
LOW SOL_ILERI_MOTOR
LOW SAG_GERI_MOTOR
low SOL_GERI_MOTOR

low led
PAUSE 1000
high led
PAUSE 1000
low led
PAUSE 1000
high led
PAUSE 1000
low led
PAUSE 1000
high led
GOTO MAIN

MAIN:
    COKLU_DONUS=0
    sensor=(PORTB & %00111000)>>3
   
    IF SENSOR=1 OR SENSOR=7 THEN
        GOSUB ileri_git
    ENDIF   

    IF SENSOR=2  THEN
      WHILE SENSOR=2
         GOSUB SAGA_DON
         COKLU_DONUS=COKLU_DONUS+1
         IF COKLU_DONUS=5 THEN
           COKLU_DONUS=0:GOTO ILERI_GIT
         ENDIF
      WEND
    ENDIF
       
   
    IF SENSOR=4 THEN
      WHILE SENSOR=4
        GOSUB SOLA_DON
        COKLU_DONUS=COKLU_DONUS+1
        IF COKLU_DONUS=5 THEN
           COKLU_DONUS=0:GOTO ILERI_GIT
        ENDIF   
      WEND
    ENDIF

    IF  SENSOR=6 THEN
         GOSUB GERI_GIT
    ENDIF
   
 
     
ILERI_GIT:
    SAG_GERI_MOTOR=0
    SOL_GERI_MOTOR=0
    SAG_ILERI_MOTOR=1
    SOL_ILERI_MOTOR=1                         
    GOTO MAIN     

DUR:
    SAG_ILERI_MOTOR=0
    SOL_ILERI_MOTOR=0
    SAG_GERI_MOTOR=0
    SOL_GERI_MOTOR=0
    goto main

SAGA_DON:
     SOL_ILERI_MOTOR=0
     SAG_GERI_MOTOR=0
     SAG_ILERI_MOTOR=1
     SOL_GERI_MOTOR=1
     RETURN

SOLA_DON:
     SAG_ILERI_MOTOR=0
     SOL_GERI_MOTOR=0
     SOL_ILERI_MOTOR=1
     SAG_GERI_MOTOR=1
     RETURN

GERI_GIT:
     SAG_ILERI_MOTOR=0
     SOL_ILERI_MOTOR=0   
     SAG_GERI_MOTOR=1
     SOL_GERI_MOTOR=1
     PAUSE 500
     RETURN

SAG_GERI_GIT:
     SAG_ILERI_MOTOR=0
     SOL_ILERI_MOTOR=0
     SOL_GERI_MOTOR=0
     SAG_GERI_MOTOR=1
     RETURN

SOL_GERI_GIT:
    SAG_ILERI_MOTOR=0
    SOL_ILERI_MOTOR=0
    SAG_GERI_MOTOR=0
    SOL_GERI_MOTOR=1
    RETURN

end

ete

Reset sorunu için fazla yapılacak bir şeyyok çünki gerçekten donanım sorunu bu.
Pek çok şeyden meydana gelebilir. Besleme bacaklarına gelen bakır kanalların ince olması bile bunu yaratabilir.
Belliki pic ya parazit alıyor (bir skop ile bakmak anlamanı sağlar) , yada pic voltajı motorların hepsi devreye girince anlık olarak düşüyor ve resetleniyor. Sigorta ayarlarındanbelkide BODEN_OFF değilde ON yapmalısın. Onuda denemen gere.

Bir araba kod yamışsın yine. Olayı binary mantığı gibi düşünmek lazım. Mesela;
Binary mantığında bir değişken değeri ya sıfır yada 1 olur üçüncü bir alternatif yoktur. O değişkenin değerinin ne olduğunu kontrol ederken;
IF DEGISKEN=0 THEN....... şeklinde değerin sıfır olup olmadığını kontrol edersin. Ama devamında artık 1 olup olmadığını kontrol etmeye gerek yoktur.Çünki sıfır değil ise mutlaka birdir zaten.
Yani ;
IF DEGISKEN=0 THEN SURAYA GIT
IF DEGISKEN=1 THEN DEVAMET
demek yanış değil ama orada lüzümsuz bir satır vardır aynı işi
IF DEGISKEN=0 THEN SURAYA GIT
DEVAMET:
şeklinde yapmak varken neden bir IF daha kullanayım ki. Benim örneğimde bu konuya değinmiş ve kodu lüzumsuz IF lerden arındırmış idim. Her neyse olaya sen daha fazla hakimsin ve sen karar vermelisin sensörlerin durumuna göre ne yapılacağına.

Ete

Powered by EzPortal