Hallo users, Ich werkle nun seit Wochen an einem RFM12B herum, und bekomme es einfach nicht hin es zu initialisieren. Das Modul soll mit einem Attiny13 zusammenarbeiten das auf mit dem Internen Oszilator auf 4.8 MHz läuft. Ich bekomme bei SDO kein hing puls vom RFM also bleibt mein Programm bei rf12_trans_wait: sbis PINB, 3 ;Wenn SDO noch nicht 1 is rjmp rf12_trans_wait ;nochmal schaun, obs 1 is stehen. Wenn ich dies Zeile auskommentiere/Lösche, läuft das Programm weiter, das RFM wird aber nicht konfiguriert. Ist mein erstes Projekt, in dem Kommunikation mit einem Anderen Chip/Modul per SPI von nöten ist, entsprechend läuft es etwas zäh. Ich messe mit dem Oszi nach, kann aber nicht wirklich testen, ob meine Konfiguration beim RFM wirklich angekommen sind. Verbindungen: SS = PB0 ;Output active low SDO = PB3 ;Input SCK = PB2 ;Output SDI = PB4 ;Output DDRB =0b11110101 Mein Bisheriger Code: .nolist .include "includes/tn13def.inc" .list ;************************************************************** ;Konstanten ;************************************************************** ; SPI .equ SPI_DDR_PORT = DDRB .equ SPI_PORT = PORTB .equ SS = 0 ;Output active low .equ SDO = 3 ;Input .equ SCK = 2 ;Output .equ SDI = 4 ;Output .equ SPI_DDR_Standart_dir =0b11110101 ;Inputs : INT0 an PB1 SDO an PB3 ;GENERAL .equ C_FREQ =4800000 .equ STUFFBIT =0xAA ;************************************************************** ;Registerdefinitionen ;************************************************************** .def status = r16 .def temp= r17 .def timer_count = r18 .def led_status =r19 .def lsb = r20 .def msb = r21 .def sendbyte = r22 ;************************************************************** ;Vektorentabelle ;************************************************************** .org 0x0000 rjmp init .org 0x0003 rjmp int_timer int_timer: cpi timer_count,255 breq timer_zero inc timer_count reti timer_zero: clr timer_count reti wait_100ms: clr timer_count wait_100ms_loop: cpi timer_count,8 breq exit_timer rjmp wait_100ms_loop exit_timer: ret rf12_trans: cbi PORTB, 0 ;CS auf 0(aktiv) nop nop nop nop nop nop nop nop nop nop rf12_trans_wait: sbis PINB, 3 ;Wenn SDO noch nicht 1 is rjmp rf12_trans_wait ;nochmal schaun, obs 1 is ldi temp, 16 ;16 Datenbits sinds rf12_trans_loop: lsl lsb ;Ins derzeitige LSB 0 schreiben und schieben rol msb ;Weiterschieben und MSB ins Carry cbi PORTB, 4 ;SDI auf 0 brcc rf12_trans_0 ;Wenn Carry eh gecleart is, so lassen sbi PORTB, 4 ;Andernfalls SDI auf 1 rf12_trans_0: nop nop ;A bisserl Zeit lassen nop nop ;A bisserl Zeit lassen nop nop ;A bisserl Zeit lassen nop nop ;A bisserl Zeit lassen nop nop ;A bisserl Zeit lassen nop sbis PINB,3 ;Wenn SDO auf 1 ori lsb, 1 ;Ins derzeitige LSB 1 schreiben sbi PORTB, 2 ;Clock-Impuls erzeugen nop ;A bisserl Zeit lassen nop nop ;A bisserl Zeit lassen nop nop ;A bisserl Zeit lassen nop nop ;A bisserl Zeit lassen nop nop ;A bisserl Zeit lassen nop nop ;A bisserl Zeit lassen nop nop ;A bisserl Zeit lassen nop nop ;A bisserl Zeit lassen nop nop ;A bisserl Zeit lassen nop ;A bisserl Zeit lassen nop nop ;A bisserl Zeit lassen nop nop ;A bisserl Zeit lassen nop nop ;A bisserl Zeit lassen nop cbi PORTB, 2 dec temp ;Bit Zähler runterzählen brne rf12_trans_loop ;Wenn nicht abgelaufen, wiederholen sbi PORTB, 0 ;CS auf 1(inaktiv) cbi PORTB, 4 ;SDI auf 0 ret ;************************************************************** ;Initialisierung ;************************************************************** rfm_init: cbi PORTB, 0 ;CS auf 0(aktiv) rcall wait_100ms ldi msb,0x80 ldi lsb,0x98 rcall rf12_trans ldi msb,0x82 ldi lsb,0x39 rcall rf12_trans ldi msb,0xA4 ldi lsb,0xB0 rcall rf12_trans ldi msb,0xC6 ldi lsb,0x23 rcall rf12_trans ldi msb,0x91 ldi lsb,0x80 rcall rf12_trans ldi msb,0xC2 ldi lsb,0x2C rcall rf12_trans ldi msb,0xCA ldi lsb,0x80 rcall rf12_trans ldi msb,0xCE ldi lsb,0xD4 rcall rf12_trans ldi msb,0xC4 ldi lsb,0xF7 rcall rf12_trans ldi msb,0x98 ldi lsb,0x00 rcall rf12_trans ldi msb,0xCC ldi lsb,0x57 rcall rf12_trans ret init: ldi temp,SPI_DDR_Standart_dir out DDRB,temp ldi temp, 0b000000001 out PORTB,temp ldi temp, LOW(RAMEND) out SPL, temp ;Timer ldi temp,0b00000100 ;256 Prescale 73 Overflows per sec a 73HZ out TCCR0B,temp ldi temp,0b00000010 ; Interrupt bei Overflow out TIMSK0,temp clr timer_count ;Interrupts an INT0 ldi temp,(1<<ISC01)|(1<<ISC00) ; INT0 und INT1 auf fallende Flanke konfigurieren out MCUCR,temp ldi temp,0b01000000 ; INT0 aktivieren out GIMSK,temp ldi temp,0b01000000 ; INT0 aktivieren out GIFR,temp clr timer_count sei ;Interrupts an rcall rfm_init ;************************************************************** ;Hauprogramm ;************************************************************** main: rjmp main
Hallo, habe da jetzt nicht wirklich rübergeschaut. Hier mal die RFM12-Routinen aus einem fast 10 Jahre alten Projekt von mir:
1 | ;************************ RFM12 Sende-Routinen ***************************** |
2 | |
3 | ;***************************** RFM12 Send CMD ****************************** |
4 | ; Sub: Sendet 16Bit Kommando aus Z |
5 | ; Parameter: Z Kommando |
6 | ; Return: Y Status ??? |
7 | ; Scratch-Reg: Z, TEMP_0, TEMP_1 |
8 | ;*************************************************************************** |
9 | |
10 | // nFFS: 1-10k Pullup an Vcc !!! |
11 | |
12 | RFM12_send_cmd: |
13 | cbi RFM12_PORT,RFM12_CS |
14 | |
15 | ldi TEMP_1,16 ; Anzahl Bits |
16 | |
17 | RFM12_send_cmd_loop: |
18 | cbi RFM12_PORT,RFM12_SDI |
19 | sbrc ZH,7 |
20 | sbi RFM12_PORT,RFM12_SDI |
21 | |
22 | nop |
23 | nop |
24 | sbi RFM12_PORT,RFM12_SCK |
25 | nop |
26 | nop |
27 | nop |
28 | nop |
29 | nop |
30 | nop |
31 | nop |
32 | nop |
33 | nop |
34 | nop |
35 | nop |
36 | nop |
37 | cbi RFM12_PORT,RFM12_SCK |
38 | |
39 | lsl ZL |
40 | rol ZH |
41 | |
42 | dec TEMP_1 |
43 | brne RFM12_send_cmd_loop |
44 | |
45 | sbi RFM12_PORT,RFM12_CS |
46 | |
47 | ret |
48 | |
49 | ;***************************** RFM12 Init ********************************** |
50 | ; Sub: Initialisiert den RFM02 |
51 | ; Parameter: - |
52 | ; Return: - |
53 | ; Scratch-Reg: Z, TEMP_0, TEMP_1 |
54 | ;*************************************************************************** |
55 | |
56 | RFM12_init: |
57 | |
58 | load_p Z,0x0000 ; Status read |
59 | rcall RFM12_send_cmd |
60 | |
61 | load_p Z,0xC080 ; CLK-Frequenz 2,5MHz, Batterie-Level 2,2V |
62 | rcall RFM12_send_cmd |
63 | |
64 | load_p Z,0x80D7 ; TX-Reg. enable, RX-FIFO enable, C = 11,5pF |
65 | rcall RFM12_send_cmd |
66 | |
67 | load_p Z,0xC2AB ; Clock Recovery auto, DQD Thresold 3 |
68 | rcall RFM12_send_cmd |
69 | |
70 | load_p Z,0xCA81 ; FIFO-Level 8 Bit, Sync-Word aktiv, Disable High Sens Reset |
71 | rcall RFM12_send_cmd |
72 | |
73 | load_p Z,0xE000 ; WakeUp aus |
74 | rcall RFM12_send_cmd |
75 | |
76 | load_p Z,0xC800 ; Low Duty Cycle aus, |
77 | rcall RFM12_send_cmd |
78 | |
79 | load_p Z,0xC4F3 ; AFC unabhängig von VDI, AFC-Range + 3-4, AFC out enable, AFC ein |
80 | rcall RFM12_send_cmd |
81 | |
82 | load_p Z,0xA620 ; Frequenz |
83 | rcall RFM12_send_cmd |
84 | |
85 | load_p Z,0x948C ; VDI ein, VDI fast, Bandbreite 200kHz, LNA -6db, RSSI .79db |
86 | rcall RFM12_send_cmd |
87 | |
88 | load_p Z,0xC610 ; Baudrate 19200 |
89 | rcall RFM12_send_cmd |
90 | |
91 | ret |
92 | |
93 | ;************************** RFM12 Empfang Daten **************************** |
94 | ; Sub: Liest Datenbyte vom RFM12 |
95 | ; Parameter: - |
96 | ; Return: TEMP_0 Anzahl |
97 | ; Scratch-Reg: TEMP_0, TEMP_1 |
98 | ;*************************************************************************** |
99 | |
100 | RFM12_read_fifo: |
101 | load_p Y,DATA_BUF |
102 | mov TEMP_2,TEMP_0 ; Anzahl merken |
103 | |
104 | load_p Z,0x82C8 ; Receiver ein, Base Band ein, Quarz ein |
105 | rcall RFM12_send_cmd |
106 | |
107 | load_p Z,0xCA81 ; FIFO-Level 8 Bit, Sync-Word aktiv, Disable High Sens Reset |
108 | rcall RFM12_send_cmd |
109 | |
110 | load_p Z,0xCA83 ; FIFO-Level 8 Bit, Sync-Word aktiv, Disable High Sens Reset, Enable FfIFI fill |
111 | rcall RFM12_send_cmd |
112 | |
113 | cbi RFM12_PORT,RFM12_SCK |
114 | cbi RFM12_PORT,RFM12_SDI |
115 | |
116 | RFM12_read_fifo_loop: |
117 | cbi RFM12_PORT,RFM12_CS |
118 | |
119 | RFM12_read_fifo_wait: |
120 | sbis RFM12_PIN,RFM12_SDO |
121 | rjmp RFM12_read_fifo_wait |
122 | |
123 | ldi TEMP_1,8 |
124 | ldi TEMP_0,0xB0 ; Receive FIFO read |
125 | |
126 | RFM12_read_fifo_cmd: |
127 | cbi RFM12_PORT,RFM12_SDI |
128 | sbrc TEMP_0,7 |
129 | sbi RFM12_PORT,RFM12_SDI |
130 | |
131 | nop |
132 | nop |
133 | sbi RFM12_PORT,RFM12_SCK |
134 | nop |
135 | nop |
136 | nop |
137 | nop |
138 | nop |
139 | nop |
140 | cbi RFM12_PORT,RFM12_SCK |
141 | lsl TEMP_0 |
142 | nop |
143 | dec TEMP_1 |
144 | brne RFM12_read_fifo_cmd |
145 | |
146 | RFM12_read_fifo_daten_start: |
147 | clr TEMP_0 |
148 | ldi TEMP_1,8 |
149 | |
150 | RFM12_read_fifo_daten: |
151 | lsl TEMP_0 |
152 | sbic RFM12_PIN,RFM12_SDO |
153 | sbr TEMP_0,0b00000001 |
154 | |
155 | sbi RFM12_PORT,RFM12_SCK |
156 | nop |
157 | nop |
158 | nop |
159 | nop |
160 | cbi RFM12_PORT,RFM12_SCK |
161 | dec TEMP_1 |
162 | brne RFM12_read_fifo_daten |
163 | |
164 | st Y+,TEMP_0 |
165 | sbi RFM12_PORT,RFM12_CS |
166 | |
167 | dec TEMP_2 |
168 | brne RFM12_read_fifo_loop |
169 | |
170 | load_p Z,0x8208 ; Empfänger aus, Quarz bleibt an |
171 | rcall RFM12_send_cmd |
172 | |
173 | ret |
Hier noch die defines der Pins dazu:
1 | .equ RFM12_PORT = PORTC |
2 | .equ RFM12_PIN = PINC |
3 | |
4 | .equ RFM12_SDI = PC0 |
5 | .equ RFM12_SCK = PC1 |
6 | .equ RFM12_SDO = PC2 |
7 | .equ RFM12_CS = PC3 |
8 | |
9 | .equ RFM12_IRQ_PIN = PIND |
10 | .equ RFM12_IRQ_IN = PD2 |
Komplett findest Du die Sachen hier auf meiner alten Homepage: http://www.avr.roehres-home.de/sensoren/i_usb_empfaenger.html Gruß aus Berlin Michael
Hallo, hier in der Abhandlung sind etliche Beispiele zu finden. Ich hatte mir seinerzeit eines ausgesucht, das tatsächlich funktioniert hat. Beitrag "bidirektionale RS232 Funkbrücke mit RFM12" SDO wird nur im TX-mode abgefragt: "TXREGISTER BUFFERED DATATRANSMISSION In this operating mode (enabled by bit el, in the Configuration Setting Command) the TX data is clocked into one of the two 8-bit data registers. The transmitter starts to send out the data from the first register (with the given bit rate) when bit et is set with the Power Management Command. The initial value of the data registers (AAh) can be used to generate preamble. During this mode, the SDO pin can be monitored to check whether the register is ready (SDO is high) to receive the next byte from the microcontroller." MfG
:
Bearbeitet durch User
Hallo Michael, Danke für deinen Code. Beim ersten betrachten fällt mir auf,das bei RFM12_send_cmd der Status des SDO nicht abgefragt wird. Demnach muss ich mit dem Senden der nächsten Bits nicht auf die Bestätitung des RFMs warten und kann die Bits einfach senden? Oder übersehe ich da was? besten dank Lukas
Hallo, das ist SPI, auch wenn ich bei den RFM-Modulen mit Hardware-SPI Timingprobleme hatte und deshalb auch zu Fuß mit den Bits gewackelt habe. Der RFM übernimmt mit dem Takt (welche Flanke müßte ich im Datenblatt suchen) das Datenbit von SDI und legt an SDO sein Bit an zum einlesen. Das ist entweder das Statuswort oder Daten oder auch nur "Müll", den man ignorieren kann. Also /CS aktiv, Datenbit ran, Clock Impuls, SDO einlesen und aufheben, wenn man die Antwort braucht. SDO hat noch eine Sonderfunktion in bestimmten Fälle: der RFM12 legt das oberste Statusbit an SDO an wenn man ihn aktiviert. Das hat den Vorteil, daß man Status nicht komplett einlesen muß, wenn man z.B. nur abfragen will, ob er irgendwas zu melden hat, sondern nur dann, wenn es gesetzt ist. Gruß aus Berlin Michael
Hallo Michael, Heute Morgen das Programm umgeschrieben, ohne SDO und beim ersten Anlauf geklappt. Ich kann die Frequenzteilung des RFM am CLK verändern, durch die Teilereinstellung. Also versteht das RFM was ich tun will, und kann es entsprechend konfigurieren . rf12_trans: cbi PORTB, 0 ;CS auf 0(aktiv) nop nop ldi temp, 16 rf12_trans_loop: lsl lsb ;Ins derzeitige LSB 0 schreiben und schieben rol msb ;Weiterschieben und MSB ins Carry cbi PORTB, 4 ;SDI auf 0 brcc rf12_trans_0 ;Wenn Carry eh gecleart is, so lassen sbi PORTB, 4 ;Andernfalls SDI auf 1 rf12_trans_0: sbi PORTB, 2 ;Clock-Impuls erzeugen nop nop nop nop nop nop nop nop nop nop nop nop ;A bisserl Zeit lassen cbi PORTB, 2 dec temp ;Bit Zähler runterzählen brne rf12_trans_loop ;Wenn nicht abgelaufen, wiederholen sbi PORTB, 0 ;CS auf 1(inaktiv) cbi PORTB, 4 ;SDI auf 0 ret ;Frequenz umschalten per Taster Interrupt an INT0 int_1: ldi msb,0xC0 ldi lsb,0xE0 ;Quarz auf 10 MHz stellen rcall rf12_trans reti Besten dank für die Hilfe! mfg Lukas
:
Bearbeitet durch User
Hallo, Frequenzumstellung am Ausgabepin war damals auch meine erste Übung, konnte man schnell sehen, ob überhaupt was sinnvolles passierte. Viel Erolg weiterhin, meine RFM-Sensoren laufen ja nun erst seit gut 9 Jahren. Letztens mußte ich beim Sensor im Keller doch glatt die Batterie (CR123A) wechseln, nach gerade mal rund 3 1/3 Jahren... ;-) Gruß aus Berlin Michael
Bitte melde dich an um einen Beitrag zu schreiben. Anmeldung ist kostenlos und dauert nur eine Minute.
Bestehender Account
Schon ein Account bei Google/GoogleMail? Keine Anmeldung erforderlich!
Mit Google-Account einloggen
Mit Google-Account einloggen
Noch kein Account? Hier anmelden.