Merhaba arkadaşlar, uzun zamandır proton kullanıcısıyım. artık CCS zamanı geldi. CSS de takıldığım bir noktayı hemen sizlere sormak istedim.
Protonda registerlere ve bitlerine direkt olarak ulaşıp set veya clear yani 1 ve 0 yaparak register ayarını da bu şekilde yapmış oluyorduk. örnek olarak
OSCCON.1 = 1 // osccon registerinin 1. bitini 1 yap yani set yap
OSCCON.2 = 0 // osccon registerinin 2. bitini 0 yap yani clear yap
...
bu işlemin birebir aynısı CCS için nasıl olacak. Yardımcı olmanızı istiyorum. mesela şöyle mi olacak
OSCCON_1 = 1
OSCCON_2 = 0
protonda araya nokta koyarak bit ile ilgili işlemi kasdettiğimiz programa iletiliyordu. Peki bu CCS de bu registerlerin bitlerini nası bu şekilde belirterek ayarlayabiliriz ?
İlgili registerin adresini buluyorsun, aşağıdaki gibi tanımlıyorsun.
#BYTE PORTA = 0x05 //register adresi
#BYTE PORTB = 0x06
#BYTE PORTC = 0x07
#BYTE TRISA = 0x85
#BYTE TRISB = 0x86
#BYTE TRISC = 0x87
#BYTE ANSEL = 0x188
#BYTE ANSELH = 0x189
#BYTE ADCON0 = 0x1F
#BYTE ADCON1 = 0x9F
#BYTE ADRESH = 0x1E
#BYTE ADRESL = 0x9E
#BYTE TMR1L = 0X0E
#BYTE TMR1H = 0X0F
bit tanımlama da bu şekilde...
#BIT ADON = ADCON0.0
#BIT GO_DONE = ADCON0.1
#BIT ANC0 = ADCON0.2
#BIT ANC1 = ADCON0.3
#BIT ANC2 = ADCON0.4
#BIT ANC3 = ADCON0.5
#BIT ADCS0 = ADCON0.6
#BIT ADCS1 = ADCON0.7
#BIT ADFM = ADCON1.7
#BIT LED = PORTC.5
#BIT TEST = PORTC.3
örnekler de bu şekilde.
LED = 1;
LED = (!LED); //Toggle LED
TRISA =0b00001111;
PORTB =0xFF;
ANC = 1;
CCS her porta eriştiğinde TRIS registerlerini duruma göre giriş-çıkış yapar, bu da hem programı şişirir hem de yavaşlatır.
Bundan kullanmak istemezsen
#use fast_io(ALL) bütün portlar veya
#use fast_io(A) sadece A portu için
Kullanırsın ama TRIS registerlerini kendin ayarlaman gerekir.
CcsC help den veya forumdan, netten getenv e bakın
https://www.picproje.org/index.php/topic,61481.0.html (https://www.picproje.org/index.php/topic,61481.0.html)
bu şekilde adlandırmayla uğraşmadan direk değer giremez miyiz? mesela şöyle;
1 = ADCON0.0
1 = ADCON0.1
1 = ADCON0.2
0 = ADCON0.3
0 = ADCON0.4
1 = ADCON0.5
0 = ADCON0.6
1 = ADCON0.7
Şöyle de yapabilirsin:
View>Registers>Make include file>Pack into Struct's>Byte Prefix boş olsun >Generate
"PIC18F4520_registers.h" isimli registerlerin adının ve adreslerinin tutulduğu bir dosya üretiyor.
Programın başına
#include <PIC18F4520_registers.h>
ekliyorsun.
Örnek:
TXSTA.TX9D = 1;
TXSTA = 0xFF;
TRISA.TRISA0 = 1;
TXSTA.1 = 1; olmuyor....
#define W 0
#define F 1
// register files
#byte INDF =0x00
#byte TMR0 =0x01
#byte PCL =0x02
#byte STATUS =0x03
#byte FSR =0x04
#byte PORTA =0x05
#byte PORTB =0x06
#byte EEDATA =0x08
#byte EEADR =0x09
#byte PCLATH =0x0a
#byte INTCON =0x0b
#byte PIR1 =0x0c
#byte TMR1L =0x0e
#byte TMR1H =0x0f
#byte T1CON =0x10
#byte TMR2 =0x11
#byte T2CON =0x12
#byte CCPR1L =0x15
#byte CCPR1H =0x16
#byte CCP1CON =0x17
#byte RCSTA =0x18
#byte TXREG =0x19
#byte RCREG =0x1a
#byte CMCON =0x1f
#byte OPTION_REG =0x81
#byte TRISA =0x85
#byte TRISB =0x86
#byte PIE1 =0x8c
#byte PCON =0x8e
#byte PR2 =0x92
#byte TXSTA =0x98
#byte SPBRG =0x99
#byte EEDATA =0x9a
#byte EEADR =0x9b
#byte EECON1 =0x9c
#byte EECON2 =0x9d
#byte VRCON =0x9f
#bit not_to =0x03.4
#bit not_pd =0x03.3
#bit ra7 =0x05.7
#bit ra6 =0x05.6
#bit ra5 =0x05.5
#bit ra4 =0x05.4
#bit ra3 =0x05.3
#bit ra2 =0x05.2
#bit ra1 =0x05.1
#bit ra0 =0x05.0
#bit rb7 =0x06.7
#bit rb6 =0x06.6
#bit rb5 =0x06.5
#bit rb4 =0x06.4
#bit rb3 =0x06.3
#bit rb2 =0x06.2
#bit rb1 =0x06.1
#bit rb0 =0x06.0
// INTCON Bits for C
#bit gie = 0x0b.7
#bit peie = 0x0b.6
#bit t0ie = 0x0b.5
#bit inte = 0x0b.4
#bit rbie = 0x0b.3
#bit t0if = 0x0b.2
#bit intf = 0x0b.1
#bit rbif = 0x0b.0
#bit eeif =0x0c.7
#bit cmif =0x0c.6
#bit rcif =0x0c.5
#bit txif =0x0c.4
#bit ccp1if =0x0c.2
#bit tmr2if =0x0c.1
#bit tmr1if =0x0c.0
#bit t1ckps1 =0x10.5
#bit t1ckps0 =0x10.4
#bit t1oscen =0x10.3
#bit t1sync =0x10.2
#bit tmr1cs =0x10.1
#bit tmr1on =0x10.0
#bit toutps3 =0x12.6
#bit toutps2 =0x12.5
#bit toutps1 =0x12.4
#bit toutps0 =0x12.3
#bit tmr2on =0x12.2
#bit t2ckps1 =0x12.1
#bit t2ckps0 =0x12.0
#bit ccp1x =0x17.5
#bit ccp1y =0x17.4
#bit ccp1m3 =0x17.3
#bit ccp1m2 =0x17.2
#bit ccp1m1 =0x17.1
#bit ccp1m0 =0x17.0
#bit spen =0x18.7
#bit rx9 =0x18.6
#bit sren =0x18.5
#bit cren =0x18.4
#bit aden =0x18.3
#bit ferr =0x18.2
#bit oerr =0x18.1
#bit rx9d =0x18.0
#bit c2out =0x1f.7
#bit c1out =0x1f.6
#bit c2inv =0x1f.5
#bit c1inv =0x1f.4
#bit cis =0x1f.3
#bit cm2 =0x1f.2
#bit cm1 =0x1f.1
#bit cm0 =0x1f.0
#bit trisa4 =0x85.4
#bit trisa3 =0x85.3
#bit trisa2 =0x85.2
#bit trisa1 =0x85.1
#bit trisa0 =0x85.0
#bit trisb7 =0x86.7
#bit trisb6 =0x86.6
#bit trisb5 =0x86.5
#bit trisb4 =0x86.4
#bit trisb3 =0x86.3
#bit trisb2 =0x86.2
#bit trisb1 =0x86.1
#bit trisb0 =0x86.0
// OPTION Bits
#bit not_rbpu = 0x81.7
#bit intedg = 0x81.6
#bit t0cs = 0x81.5
#bit t0se = 0x81.4
#bit psa = 0x81.3
#bit ps2 = 0x81.2
#bit ps1 = 0x81.1
#bit ps0 = 0x81.0
#bit eeie =0x8c.7
#bit cmie =0x8c.6
#bit rcie =0x8c.5
#bit txie =0x8c.4
#bit ccpie =0x8c.2
#bit tmr2ie =0x8c.1
#bit trm1ie =0x8c.0
#bit oscf =0x8e.3
#bit not_por =0x8e.1
#bit not_bod =0x8e.0
#bit csrc =0x98.7
#bit tx9 =0x98.6
#bit txen =0x98.5
#bit sync =0x98.4
#bit brgh =0x98.2
#bit trmt =0x98.1
#bit tx9d =0x98.0
#bit wrerr =0x98.3
#bit wren =0x98.2
#bit wr =0x98.1
#bit rd =0x98.0
#bit vren =0x9f.7
#bit vroe =0x9f.6
#bit vrr =0x9f.5
#bit vr3 =0x9f.3
#bit vr2 =0x9f.2
#bit vr1 =0x9f.1
#bit vr0 =0x9f.0
// For Assembly Language - Note upper case
// Status Bits
#define IRP 7
#define RP1 6
#define RP0 5
#define NOT_TO 4
#define NOT_PD 3
#define Z 2
#define DC 1
#define C 0
@pkelle güzel yöntem,
yeni bir şey daha öğrenmiş oldum, sağolasın.
Karşı çıkanlar olabilir. Ancak, register
meselesiyle ilgileniyorsanız ve yolun başındaysanız MPLABX veya mikroC
daha iyi bir seçenek olacaktır.
"TXSTA.1 = 1; olmuyor...."
Demiştim yukarıda. Bu şekilde yapınca oluyor.
>View
>Registers
>Make include file
>Separate C Variables(Sadece byte identifiers tikli)
>Byte Prefix boş olsun
>Generate
Örnek:
#bit ADON = ADCON0.0
#bit GO_DONE = ADCON0.1
#bit ADFM = ADCON2.7
#bit LED = PORTD.0
#bit T0CS = T0CON.5
isteğe göre iki şekilde kullanılabilir.
Ayrıca registerleri kullanarak program yazmak CCS'de de mümkün, çok da rahat. Hatta hazır komutları kullanmaktan daha iyi bence...
Ccsnin amaci registerlere bulasmadan program yazmak
Alıntı yapılan: pkelle - 19 Haziran 2016, 14:15:14
İlgili registerin adresini buluyorsun, aşağıdaki gibi tanımlıyorsun.
#BYTE PORTA = 0x05 //register adresi
#BYTE PORTB = 0x06
#BYTE PORTC = 0x07
#BYTE TRISA = 0x85
#BYTE TRISB = 0x86
#BYTE TRISC = 0x87
#BYTE ANSEL = 0x188
#BYTE ANSELH = 0x189
#BYTE ADCON0 = 0x1F
#BYTE ADCON1 = 0x9F
#BYTE ADRESH = 0x1E
#BYTE ADRESL = 0x9E
#BYTE TMR1L = 0X0E
#BYTE TMR1H = 0X0F
PORTB =0xFF;
Ya da PORTB =0xFF; yerine tanımlamadan direk
*0x06=0xFF;
yazılabilir.
MikroC tavsiye ederim.
Alıntı yapılan: Okan AKÇA - 22 Haziran 2016, 21:33:34
Ccsnin amaci registerlere bulasmadan program yazmak
Başka bir derleyicide registerlara bulaşarak yazılmış bir programı veya kütüphaneyi
CcsC ye uyarlarken yukarıda anlatılanlar çok işe yarıyor.
Ama söylediğinde haklısın,
şöyle düşünmek lazım;
madem CcsC kullanıyorsun
öyleyse registerların değerleri ne olmalı diye niye uğraşıyorsun,
zaten modülleri kurmak için CcsC nin fonksiyonları var, onları kullan.
anladım değerli kardeşlerim. benim amacım direk registerler la oynayarak bütün işlerimi yapmak. datasheet okumayı çok seviyorum :) mikroC tavsiye edenler olmuş. Teşekkür ediyorum. Şimdi CCS içinde anladığım kadarıyla önce registerlere MUTLAKA isim atamak zorundayız. sonra bu isimlere 1 veya 0 değerlerini girebiliriz. bu işlem proton+' da direk yapılabiliyordu. yani önce registerin bitlerine isim atamadan yapılıyordu. mesela adcon0 registerinin ADON bitine bu adon ismini atamak gerekli CCS de sanırım. daha sonra bu adonu 1 veya 0 yapıoruz öyle mi ? daha kısa yolu yok mudur. yani registerleri otomatik olarak görmüyor program sanırım. işte bu protonda öyle değildi. sen direk porta.0=1 porta.1= 1 yapıyordun bitiyordu. mikroC ye bakacağım şimdi.
Mesajların:
CcsC de registerlara bulaşmadan...
kısmını dikkate almalısın.
Misal ADC mi kurmak istiyorsun
//mainden önce ADC kesmesi için:
#INT_AD // ADC çevrimi bitti kesmesi
void ADC_Kesmesi ( )
{
output_high(pin_c5); // RC5 çıkışı 1
delay_ms(200);
output_low(pin_c5); // RC5 çıkışı 0
}
//mainde 1 defa kurmak için
setup_adc(adc_clock_div_32); // ADC clock frekansı fosc/32
setup_adc_ports(ALL_ANALOG); // Tüm AN girişleri analog
enable_interrupts(INT_AD); // AD çevrimi bitti kesmesi tanıtılıyor
enable_interrupts(GLOBAL); // Tüm kesmeler aktif
//sonsuz döngüde, adc kullanmak için
set_adc_channel(5); // RE0/AN5 ucundaki sinyal A/D işlemine tabi tutulacak
delay_us(20); // Kanal seçiminde sonra bu bekleme süresi verilmelidir
bilgi=read_adc(); // ADC sonucu okunuyor ve bilgi değişkenine aktarılıyor
Şeklinde emri veriyorsun,
CcsC ADC registerlarına yazılması gereken değerleri kendi hallediyor.
Aynı şey bütün modüller için geçerli
Timer0 kuracaksın:
setup_timer_0(RTCC_INTERNAL | RTCC_DIV_256); // Timer0 ayarları yapılıyor
set_timer0(60); // TMR0 değeri belirleniyor
Kristal frekansını belirkeyeceksin:
#use delay (clock=4MHz)
//veya
#use delay(internal=4MHz)
//veya, misal USB için 48MHz,
#use delay(clock=48MHz, crystal=4MHz, USB_FULL)
veya PLL işi
#use delay(clock=48MHz, crystal=4MHz)
Herhangibir CcsC kitabını anlatımını takip edersen, bunların detaylı kullanımı anlatımı mevcut.
Eğer registerlarla datasheet ile haşır neşir olup, işi temeliyle kavramak istiyorsan:
Picin üreticisi olan Microchip in kendi IDE ve derleyicilerini tavsiye ederim,
MPLabX ve XC derleyicileri.
Ayrıca birazda ASM öğrenmekte fayda var.
değerli yorumlarınız için teşekkürler. her birinize ayrı ayrı teşekkür ediyorum. ccs ders kaynakları bulmaya çalışacağım. ama bu ccs sanki her pic standartmış gibi bize sunulmuş ya ona kafam takılıyor. öyle picler var ki bunlar için hazır bir kod çeviricisi yazılmamış mesela ccs e. bunun için register ayarını yapman gerekli diyelim. o zamanda artık o kadarcık göz yumup biraz register ataması falan yapıp halledeksin ;) ya da bu iş en kökten halledilmek isteniyorsa dediğiniz gibi mplab + biraz da assembly ile mükemmel becerilere ulaşılabilir.
abiler yeni birşeyler öğrendik.registerler çok öenmli bir yere sahip demekki.küçük programlar yazdığımdan hissetmiyordum.
Sanki ccs den önce biraz c öğrenmek gerekiyor.
Nasıl oluyorda protonda hızlıca bit seviyesinde işlem yapılabilirken, c de yapılamıyor.Acaba eksikleri mi var ki?
Ccs den evvel ansii c öğrenmekte fayda olabilir.
MikroC tavsiye ederim. Ben de mcu programlama işine ASM ile başlayıp ardından CCS C'ye geçip en sonunda MikroC'yi keşfederek devam etmekteyim. MikroC hem profesyonel hem de rahat bir kullanım sunmakta.
@xcyqp09k2Bit field diye aratırsan ornekler cikacaktir asagida kucuk bir ornek paylastim
struct {
short x:5, y:4, z:7;
}data;
struct data my_data;
my_data.x = ....
my_data.y = ....
my_data.z = ....
Bu daha anlasilir
struct data{
unsigned short bit0:1, bit1:1,bit2:1, bit3:1, bit4:1, bit5:1, bit6:1, bit7:1;
}my_data;
int main(void) {
WDTCTL = WDTPW | WDTHOLD; // Stop watchdog timer
x++;
my_data.bit0=1;
my_data.bit1=1;
my_data.bit2=0;
my_data.bit3=1;
my_data.bit4=1;
my_data.bit5=1;
my_data.bit6=0;
my_data.bit7=0;
return 0;
}
merhaba ben pıc ile rtc yapmak istiyorum ,ccs c ile daha önce bu konuyu bu sitede görmüştüm .proton + kodu ile yazılmıştı. işte o kodlar;
bu kodları ccs c ye çevirebilen arkadaş varmı acaba acil yârdim
ccs c ye yeni başladımda
//
Device 16F876
Xtal = 20
@CONFIG_REQ
@__config HS_OSC & WDT_OFF & PWRTE_ON & LVP_Off
All_Digital = true
PortB_Pullups = off
TRISA = %00111111
TRISB = %00000001
TRISC = %10000011
PORTA=0
PORTB=0
PORTC=0
DelayMS 10
Dim Saniye As Word'
Dim Dakika As Word
Dim Saat As Word
Dim ZAMAN1 As Word
Saat = 0
Saniye= 0
Dakika = 0
ZAMAN1 = 0
Symbol RBIF = INTCON.0 ' Bu bit PORTB değişiklik oluşmuş bir Interrupt varsa "1" olur
Symbol INTF = INTCON.1 ' Bu bit RB0 kesmesinden dolayı oluşmuş bir Interrupt varsa "1" olur
Symbol T0IF = INTCON.2 ' TMR0 sayıcısı zaman aşımı bayrağı
Symbol RBIE = INTCON.3 ' PORTB (4, 5, 6, 7) deki değişiklik kesmesini aktif yapma bayrağı
Symbol INTE = INTCON.4 ' RB0 Harici kesmeyi aktif yapma bayrağı
Symbol T0IE = INTCON.5 ' TMR0 sayıcı kesmesini aktif yapma bayrağı
Symbol PEIE = INTCON.6 ' Arabirim kesme aktif yapma bayrağı.
Symbol GIE = INTCON.7 ' Tüm kesme işlemlerini etkin/iptal etme bayrağı
clrwdt
Symbol TMR1IE = PIE1.0 ' TMR1 sayıcısının Kesme Yetki Biti
Symbol TMR1IF = PIR1.0 ' TMR1 sayıcısının "Kesme Oluştu" bayrağı
Symbol TMR1ON = T1CON.0 ' Timer1 ON
Symbol TMR1CS = T1CON.1 ' Timer1 Clock Source Select
Symbol NOT_T1SYNC = T1CON.2 ' Timer1 External Clock Input Synchronization Control
Symbol T1OSCEN = T1CON.3 ' Timer1 Oscillator Enable Control
Symbol T1CKPS0 = T1CON.4 ' Timer1 Input Clock Prescale Select bits
Symbol T1CKPS1 = T1CON.5 ' Timer1 Input Clock Prescale Select bits
On_Hardware_Interrupt GoTo kesme
GIE = 0 ' Turn off global interrupts
TMR1IE = 1 ' TMR1 sayıcısının Kesme Yetki Biti
TMR1IF = 0 ' TMR1 sayıcısının "Kesme Oluştu" bayrağı
INTE = 0 ' RB0 Harici kesmeyi aktif yapma bayrağı
INTF = 0 ' Bu bit RB0 kesmesinden dolayı oluşmuş bir Interrupt varsa "1" olur
PEIE = 1 ' Arabirim kesme aktif yapma bayrağı.
TMR1ON = 1 ' Timer1 ON
GIE = 1 ' Enable global interrupts
T1CKPS0 =0 'TMR1 ZAMANLAMA SET
T1CKPS1 =0
GoTo BASLA
kesme:
Context Save
GIE = 0
Inc ZAMAN1
TMR1IF = 0
If ZAMAN1=76 Then
DelayUS 3845
nop
TMR1L =0
TMR1H =0
ZAMAN1 =0
Inc Saniye
If Saniye > 59 Then Inc Dakika :Saniye = 0
If Dakika > 59 Then Inc Saat :Dakika = 0
If Saat > 23 Then Saat = 0
GoSub Islem
EndIf
GIE = 1
Context Restore
BASLA:
GoTo BASLA
Islem:
Return
End