Forum: HF, Funk und Felder RFM12 Empfangsinit


von Sebastian E. (omfg)


Lesenswert?

Hallo,

Ich bastle nun schon einige Zeit mit meinem RFM12 umher und schaffe es 
einfach nicht etwas zu empfangen.

Beim Status auslesen bekomme ich den Wert 0x80 zurück
Jedoch weiß ich nicht was ich zurück bekommen soll.

Meine Init
1
void RF12_INIT() 
2
{
3
   
4
    RF_WRITE_CMD(0xC0E0);      // AVR CLK: 10MHz
5
    RF_WRITE_CMD(0x8057);      // Enable FIFO
6
    RF_WRITE_CMD(0xC2AB);      // Data Filter: internal
7
    RF_WRITE_CMD(0xCA81);      // Set FIFO mode
8
    RF_WRITE_CMD(0xE000);      // disable wakeuptimer
9
    RF_WRITE_CMD(0xC800);      // disable low duty cycle
10
    RF_WRITE_CMD(0xC4F7);      // AFC settings: autotuning: -10kHz...+7,5kHz
11
     RF_WRITE_CMD(0x0000);
12
  
13
}
14
15
16
void RF_READ_DATA(unsigned char *daten_in)
17
{
18
    RF_WRITE_CMD(0x82C8);      // RX on
19
     RF_WRITE_CMD(0xCA81);      // set FIFO mode
20
     RF_WRITE_CMD(0xCA83);      // enable FIFO
21
22
23
    *daten_in=(unsigned char)(ui_RW_rfm12(0xB000) & 0x00FF);
24
     printf("Empfangen = %X\n",*daten_in);
25
}
26
//Kommentare müssen nicht stimmen, habe schon zuoft etwas geändert

Danke
Eder Sebastian

: Verschoben durch Moderator
von Michael U. (amiga)


Angehängte Dateien:

Lesenswert?

Hallo,

Sebastian Eder schrieb:
> Ich bastle nun schon einige Zeit mit meinem RFM12 umher und schaffe es
> einfach nicht etwas zu empfangen.
>
> Beim Status auslesen bekomme ich den Wert 0x80 zurück
> Jedoch weiß ich nicht was ich zurück bekommen soll.
Bit 7  FIFO hat Daten.
Als erstes vor dem Initialisieren mal den Status lesen, sonst starteten 
meine RFM12 nicht immer.

> void RF_READ_DATA(unsigned char *daten_in)
> {
>     RF_WRITE_CMD(0x82C8);      // RX on
>      RF_WRITE_CMD(0xCA81);      // set FIFO mode
>      RF_WRITE_CMD(0xCA83);      // enable FIFO
Sieht ok aus.


>     *daten_in=(unsigned char)(ui_RW_rfm12(0xB000) & 0x00FF);

Du mußt natürlich warten, bis Daten im FIFO sind, also Bit 7 vom Status 
gesetzt ist. Mit Daten zum RFM auf L und CLK inaktiv bekommst Du vom RFM 
immer den FIFO-Status zurück, Du kannst also in einer Schleife warten, 
bis die Leitung auf H geht und dann die FIFO-Daten abholen.

Im Anhang mal meine Empfangsroutine mit Software-SPI zum RFM12, die 
komplett im Interrupt läuft.
Ob die Einstellungen jetzt zu Deinen Sendeparametern passen muß Du 
schauen.

Gruß aus Berlin
Michael

von Sebastian E. (omfg)


Lesenswert?

Es soll doch möglich sein auch ohne int Daten zu empfangen oder nicht?

Danke
Eder Sebastian

von Michael U. (amiga)


Lesenswert?

Hallo,

Sebastian Eder schrieb:
> Es soll doch möglich sein auch ohne int Daten zu empfangen oder nicht?

Selbstverständlich, habe ich aber hier keinen Code zur Hand.

Letztlich eben SDI und CLK auf L und dann SDO pollen, bis es H wird. 
Dann hat der Fifo Daten. Die dann abholen.

Wenn alle Daten Deines Paketes da sind, nicht vergessen, den FIFO aus- 
und wieder einzuschalten, damit er wieder auf die Startpattern wartet.
Das hängt aber alles schon davon ab, was Dein Sender sendet...

Oha... habe gerade gesehen, daß mein Code wohl aus einem Projekt mit 
Polling ohne IRQ stammt...

Hier noch der Auszug aus main für den Empfang:
1
  char data_buf[32];
2
  char paket_len = 18;
3
4
  RFM12_init();
5
  while (1)
6
  {
7
    RFM12_read_fifo(data_buf, paket_len);
8
          // mach was mit dem Datenpaket
9
  }

Gruß aus Berlin
Michael

von Sebastian E. (omfg)


Lesenswert?

Hmm, ich glaube das ich nun den richtigen Status auslese.
Jedoch wäre es super wenn mir jemand ein Beispiel für eine 
Empfangsroutine/Main senden kann!

Danke
Eder Sebastian

von R. W. (quakeman)


Angehängte Dateien:

Lesenswert?

Ich habe dir mal einen Auszug aus meinem RFM12 Code angehängt. Dieser 
benutzt Polling um die RFM12 Module abzufragen. Den Code benutze ich 
schon seit etlichen Monaten ohne Probleme. Wenn du den gesamten Code 
sehen willst, dann kannst du ihn unter [1] ansehen.

Ciao,
     Rainer

[1] 
https://quakeman.homelinux.net/viewvc/uVision/trunk/Library/RFM12_Funktionen.c?view=markup

von Sebastian E. (omfg)


Lesenswert?

Ich hab mir gerade deinen Code angesehen verstehe aber nicht was der SDO 
macht!
Ist SDO der PIN?
1
// Es wird solange gewartet, bis das Preambel und anschließend n Datenbytes empfangen wurden
2
void v_Receive_rfm12(unsigned char ucPaketlaenge, unsigned char data * data pucRX_Daten) {
3
  unsigned int uiTemp;
4
  unsigned char i;
5
  bit btTimeout = 0;
6
  
7
  v_Write_rfm12(0x82C9);  // Power Management Command: er=1, ebb=1, et=0, es=0, ex=1, eb=0, ew=0, dc=1
8
  v_Write_rfm12(0xCA83);  // FIFO and Reset Mode Command: FIFO Level=8, al=0, ff=1, dr=1
9
10
  for (i = 0; i < ucPaketlaenge; i++) {
11
    NSEL = 0;
12
    while(SDO == 0);
13
14
    uiTemp = ui_RW_rfm12(0xB000);
15
    *(pucRX_Daten + i) = uiTemp & 0xFF;
16
  }
17
18
  v_Write_rfm12(0x8209);  // Power Management Command: er=0, ebb=0, et=0, es=0, ex=1, eb=0, ew=0, dc=1
19
}

MfG
Sebastian

von R. W. (quakeman)


Lesenswert?

Sebastian Eder schrieb:
> Ich hab mir gerade deinen Code angesehen verstehe aber nicht was der SDO
> macht!
> Ist SDO der PIN?

Ja genau. SDO am RFM12 ist der Pin MISO am Controller. Die Zuordnungen 
sind in der zugehörigen RFM12_Funktionen.h zu finden. Das Polling mache 
ich eben genau über diesen Pin, da das RFM12 Modul bei neuen Daten 
diesen auf 1 setzt.

Und ich sehe gerade, dass ich versehentlich btTimeout noch dringelassen 
habe. Das Bit hat hier keine Bedeutung. Mein original Code ist einiges 
länger und hat auch eine timeout Funktion eingebaut, wofür dieses Bit 
eigentlich gedacht ist. Zum Verständnis habe ich den Code aber auf das 
wesentliche gekürzt gehabt für den Thread hier.

Ciao,
     Rainer

von Sebastian E. (omfg)


Lesenswert?

Aber da kommen doch auch die "EmpfangenenDaten" rein.

Also wenn jetzt ein 01010101 reinkommt dann fragt er ab und dann wieder 
nicht und schaltet doch die ganze Zeit ein und aus oder versteh ich das 
Falsch?

Weil 4 Byte werden ja auf einmal gesendet und 2 Byte braucht das Modul 
um zu empfangen/senden (0xB000) und die letzten zwei werden dann 
übertragen/ausgelesen.

Irgendwie versteh ich die Bitschieberei beim SPI Buss nicht ganz...

MfG
Eder Sebastian

von R. W. (quakeman)


Lesenswert?

Sebastian Eder schrieb:
> Aber da kommen doch auch die "EmpfangenenDaten" rein.
>
> Also wenn jetzt ein 01010101 reinkommt dann fragt er ab und dann wieder
> nicht und schaltet doch die ganze Zeit ein und aus oder versteh ich das
> Falsch?
>
> Weil 4 Byte werden ja auf einmal gesendet und 2 Byte braucht das Modul
> um zu empfangen/senden (0xB000) und die letzten zwei werden dann
> übertragen/ausgelesen.
>
> Irgendwie versteh ich die Bitschieberei beim SPI Buss nicht ganz...

Das ist schon richtig, dass ich genau den Pin abfrage, über den 
anschließend auch die Daten hereinkommen. Es werden aber nur zwei Bytes 
an das RFM12 gesendet (0xB000) und dabei gleichzeitig auch zwei Bytes 
eingelesen.
Das Wichtige dabei ist nur, dass ich bei der Abfrage mit "while(SDO == 
0);" keinen Takt ausgebe. Das ist eben genau eines der Features des 
RFM12 um auf Daten zu pollen. Sobald der Chip aktiviert ist, ist dieser 
Pin auf "0", insofern keine Daten empfangen wurden. Sobald Daten 
empfangen wurden wird dieser Pin "1". Dies signalisiert mir dann, dass 
ich die Daten abfragen kann, was ich dann mit meiner Methode 
"ui_RW_rfm12(0xB000)" erledige. Dabei wird dann nämlich mit 0xB0 im 
ersten Byte an den RFM12 der Befehl geschickt die Daten zurückzuliefern. 
In dem zweiten Byte wird dann automatisch das empfangene Byte 
zurückgeliefert. Da meine Methode immer 16Bit empfängt maskiere ich 
deshalb das erste unnütze Byte per "uiTemp & 0xFF" wieder aus und 
speichere auch nur das zweite, mein eigentlich empfangenes Byte, ab.

Ich hoffe, ich konnte dir den Zusammenhang damit verständlich erklären. 
:)

Ciao,
     Rainer

von Sebastian E. (omfg)


Lesenswert?

1
Das ist schon richtig, dass ich genau den Pin abfrage, über den
2
anschließend auch die Daten hereinkommen. Es werden aber nur zwei Bytes
3
an das RFM12 gesendet (0xB000) und dabei gleichzeitig auch zwei Bytes
4
eingelesen.
5
Das Wichtige dabei ist nur, dass ich bei der Abfrage mit "while(SDO ==
6
0);" keinen Takt ausgebe. Das ist eben genau eines der Features des
7
RFM12 um auf Daten zu pollen. Sobald der Chip aktiviert ist, ist dieser
8
Pin auf "0", insofern keine Daten empfangen wurden. Sobald Daten
9
empfangen wurden wird dieser Pin "1". Dies signalisiert mir dann, dass
10
ich die Daten abfragen kann,

Wusste ich noch nicht!
Naja ich hoffe das ich es morgen endlich mal schaffe etwas zu entfangen 
danke dir Rainer das du so Tatkräftig mithilfst mir bei meinen Problemen 
zu helfen


MfG
sebastian Eder

von Sebastian E. (omfg)


Lesenswert?

So es funktioniert immer noch nicht irgendwie glaub ich auch das ich mit 
meiner Pointerübergage irgendwas falsch mache.
Hier ist mal mein main.c
(die Funktionen sind von dir Rainer)

1
//Bibliotheken
2
#include <stdio.h>
3
#include <stdlib.h>
4
#include <string.h>
5
#include "rfm12.h"
6
#include "reg51xd2.h"
7
8
unsigned int count_global;
9
              
10
unsigned char data_in=0x00;
11
unsigned int data_out=0x0000;
12
unsigned char daten;
13
unsigned int stat;
14
bit transmit_completed= 0;
15
sbit LED=P3^5;
16
17
18
void main(void)
19
{
20
21
  unsigned char Buffer[4];  
22
23
  // ************ RS232************************************
24
  // ************ X2 feature ******************************
25
  CKCON0=0xFF; // X2 fast mode, peripherie NORMAL 12 cycles
26
27
  //115000 Bd. for a generic 8051, running @ 22.118 MHz:
28
  // Set up UART - Find the description in the User's manual!
29
  PCON |=0x80;  // Baudrate double
30
  SCON = 0x50;  // 8 Bit UART - PC-compatible
31
  TH1=0xFF;       // Baudrate 115k
32
    TMOD |=0x20;  // use timer 1 as baudrate generator
33
    TCON=0x40;    
34
  ES=0;    // Enable Serial IRQ (if required)
35
  EA= 1;    // Enable general IRQs (if required)
36
    TI=1;
37
  //SPI CONFIG
38
  SPCON |= 0x10; /* Master mode */
39
  P1_1=1; /* enable master */
40
  SPCON |= 0x82; /* Fclk Periph/128 */
41
  SPCON &= ~0x08; /* CPOL=0; transmit mode example */
42
  SPCON |= 0x04; /* CPHA=1; transmit mode example */
43
44
  IEN1 |= 0x04; /* enable spi interrupt */
45
  SPCON |= 0x40; /* run spi */
46
  EA=1; /* enable interrupts */
47
48
  //RFM12 _ INIT
49
  RF12_INIT();
50
51
52
  while(1) /* endless */
53
  {
54
    LED=!LED;
55
    v_Receive_rfm12(4,Buffer);          
56
    printf("Empfangen: %X\n",Buffer);  // Hier möchte ich nun den PUFFER ausgeben
57
  }
58
}

von R. W. (quakeman)


Lesenswert?

Also spontan fallen mir zwei Dinge auf.

>   SPCON &= ~0x08; /* CPOL=0; transmit mode example */
>   SPCON |= 0x04; /* CPHA=1; transmit mode example */
Ich benutze CPOL=0 (idle clk=0) und CPHA=0 (bei steigender Flanke 
übernehmen)

>   IEN1 |= 0x04; /* enable spi interrupt */
Wieso aktivierst du den SPI Interrupt??
Meine Methoden benutzen keinen Interrupt, weshalb das so nicht 
funktionieren kann. Bei aktiviertem SPI Interrupt springt das Programm 
ja nach erfolgreich gesendeten/empfangenen Daten zur SPI ISR, welche es 
aber gar nicht gibt. Du musst den Interrupt also gesperrt belassen. Ich 
prüfe in meinen Low-Level Funktionen "v_Write_rfm12" und "ui_RW_rfm12" 
das SPI Flag ja per Polling ab.

>   v_Receive_rfm12(4,Buffer);
Diese Methode wartet bei meiner Initialisierung erst auf die zwei RFM12 
internen Synchronisationsbytes 0x2DD4, bevor es überhaupt die vier 
eigentlichen Bytes empfängt.
Beim Senden von Testdaten musst du also darauf achten, dass du 6 Bytes 
schickst. Falls du meine Sendemethode "v_Send_rfm12" benutzt wird dies 
schon berücksichtigt.

Aber ich denke der Hauptfehler wird erst mal der aktivierte SPI 
Interrupt sein.

Ciao,
     Rainer

von Michael U. (amiga)


Lesenswert?

Hallo,

Fox Mulder schrieb:
>>   v_Receive_rfm12(4,Buffer);
> Diese Methode wartet bei meiner Initialisierung erst auf die zwei RFM12
> internen Synchronisationsbytes 0x2DD4, bevor es überhaupt die vier
> eigentlichen Bytes empfängt.

Die Syncnytes landen nicht im FIFO, der wird erst freigegeben, wenn die 
Syncbytes richtig erkannt wurden.

> Beim Senden von Testdaten musst du also darauf achten, dass du 6 Bytes
> schickst. Falls du meine Sendemethode "v_Send_rfm12" benutzt wird dies
> schon berücksichtigt.

Man sendet 3x 0xAA, die Magic Pattern 0x2D 0xD4 und dann die Daten.
Nur die Daten landen im FIFO.

Gruß aus Berlin
Michael

von Sebastian E. (omfg)


Lesenswert?

Naja die SPI-Einstellungen hab ich aus einem ATMEL exampel rauskopiert 
da ich mich mit SPI nicht so richtig auskenne.
Und leider verwende ich deine Sende Routine auch nicht wir bei unserer 
Sendeseite einen PIC controller verwenden und die Empfangsseite ein 
FLEXGATE 3 (ATMEL8051)

Muss ich dann den auch ausschalten? -->Nicht oder?
1
EA=1; /* enable interrupts */

MfG

von R. W. (quakeman)


Lesenswert?

Sebastian Eder schrieb:
> Naja die SPI-Einstellungen hab ich aus einem ATMEL exampel rauskopiert
> da ich mich mit SPI nicht so richtig auskenne.
> Und leider verwende ich deine Sende Routine auch nicht wir bei unserer
> Sendeseite einen PIC controller verwenden und die Empfangsseite ein
> FLEXGATE 3 (ATMEL8051)

Mein Code hat nur wenige Controller spezifische Stellen drin die du 
anpassen müsstest. Du könntest also theoretisch den Code auch auf einem 
Pic laufen lassen, wenn du nur diese Stellen anpasst.
>
> Muss ich dann den auch ausschalten? -->Nicht oder?
>
>
1
EA=1; /* enable interrupts */

Dann würdest du alle Interrupts sperren. Insofern du in deinem Progamm 
keine Interrupts verwendest kannst du das machen. Aber es reicht schon, 
nur den SPI Interrupt zu sperren.

Ciao,
     Rainer

von Sebastian E. (omfg)


Lesenswert?

So ich habe nun die SPI Interupts ausgeschaltet, und ein ganz einfaches 
Programm geschrieben aber es funktioniert nicht!

Normal:
1
//Bibliotheken
2
#include <stdio.h>
3
#include <stdlib.h>
4
#include <string.h>
5
#include "rfm12.h"
6
#include "reg51xd2.h"
7
8
unsigned int count_global;
9
              
10
unsigned char data_in=0x00;
11
unsigned int data_out=0x0000;
12
unsigned char daten;
13
unsigned int stat;
14
bit transmit_completed= 0;
15
sbit LED=P3^5;
16
17
18
void main(void)
19
{
20
21
  unsigned char Buffer[4];  
22
  unsigned int uiTemp=2;
23
  // ************ RS232************************************
24
  // ************ X2 feature ******************************
25
  CKCON0=0xFF; // X2 fast mode, peripherie NORMAL 12 cycles
26
27
  //115000 Bd. for a generic 8051, running @ 22.118 MHz:
28
  // Set up UART - Find the description in the User's manual!
29
  PCON |=0x80;  // Baudrate double
30
  SCON = 0x50;  // 8 Bit UART - PC-compatible
31
  TH1=0xFF;       // Baudrate 115k
32
    TMOD |=0x20;  // use timer 1 as baudrate generator
33
    TCON=0x40;    
34
  ES=0;    // Enable Serial IRQ (if required)
35
  EA= 1;    // Enable general IRQs (if required)
36
    TI=1;
37
  //SPI CONFIG
38
  SPCON |= 0x10; /* Master mode */
39
  P1_1=1; /* enable master */
40
  SPCON |= 0x82; /* Fclk Periph/128 */
41
  SPCON &= ~0x08; /* CPOL=0; transmit mode example */
42
  SPCON |= 0x04; /* CPHA=1; transmit mode example */
43
44
  //IEN1 |= 0x04; /* enable spi interrupt */
45
  SPCON |= 0x40; /* run spi */
46
  EA=1; /* enable interrupts */
47
  RF12_INIT();
48
49
50
  while(1) /* endless */
51
  {
52
    
53
    LED=!LED;
54
    v_Receive_rfm12(4,Buffer);
55
    printf("EMPFANGSDINGS ...  = %X\n",Buffer);
56
  
57
  }
58
59
}

wartet es hier bis es was empfängt? Weil hier seh ich garnix wenn ich es 
laufen lasse nicht einmal printf mit "Empfang"


_________________________________________


Hier eine einfache Version ... der SPI funktioniert(Oszi SCK,SDI 
vergliechen) also müsste es auch theoretisch irgend einen Müll empfangen 
"der in der Luft umher schwirrt"
1
//Bibliotheken
2
#include <stdio.h>
3
#include <stdlib.h>
4
#include <string.h>
5
#include "rfm12.h"
6
#include "reg51xd2.h"
7
8
unsigned int count_global;
9
              
10
unsigned char data_in=0x00;
11
unsigned int data_out=0x0000;
12
unsigned char daten;
13
unsigned int stat;
14
bit transmit_completed= 0;
15
sbit LED=P3^5;
16
17
18
void main(void)
19
{
20
21
  unsigned char Buffer[4];  
22
  unsigned int uiTemp=2;
23
  // ************ RS232************************************
24
  // ************ X2 feature ******************************
25
  CKCON0=0xFF; // X2 fast mode, peripherie NORMAL 12 cycles
26
27
  //115000 Bd. for a generic 8051, running @ 22.118 MHz:
28
  // Set up UART - Find the description in the User's manual!
29
  PCON |=0x80;  // Baudrate double
30
  SCON = 0x50;  // 8 Bit UART - PC-compatible
31
  TH1=0xFF;       // Baudrate 115k
32
    TMOD |=0x20;  // use timer 1 as baudrate generator
33
    TCON=0x40;    
34
  ES=0;    // Enable Serial IRQ (if required)
35
  EA= 1;    // Enable general IRQs (if required)
36
    TI=1;
37
  //SPI CONFIG
38
  SPCON |= 0x10; /* Master mode */
39
  P1_1=1; /* enable master */
40
  SPCON |= 0x82; /* Fclk Periph/128 */
41
  SPCON &= ~0x08; /* CPOL=0; transmit mode example */
42
  SPCON |= 0x04; /* CPHA=1; transmit mode example */
43
44
  //IEN1 |= 0x04; /* enable spi interrupt */
45
  SPCON |= 0x40; /* run spi */
46
  EA=1; /* enable interrupts */
47
  RF12_INIT();
48
49
50
  while(1) /* endless */
51
  {
52
    LED=!LED;
53
54
    uiTemp = ui_RW_rfm12(0xB000);
55
    printf("EMPFANGSDINGS ...  = %X\n",uiTemp);
56
  }
57
58
}

MfG
Eder Sebastian

von R. W. (quakeman)


Lesenswert?

Sebastian Eder schrieb:
> wartet es hier bis es was empfängt? Weil hier seh ich garnix wenn ich es
> laufen lasse nicht einmal printf mit "Empfang"
Ja. Er wartet solange, bis etwas empfangen wurde. Vorher wirst du auch 
deine Textausgabe nicht sehen.

> Hier eine einfache Version ... der SPI funktioniert(Oszi SCK,SDI
> vergliechen) also müsste es auch theoretisch irgend einen Müll empfangen
> "der in der Luft umher schwirrt"
Nein. Erklärung weiter unten. ;)

Sebastian Eder schrieb:
>   while(1) /* endless */
>   {
>     LED=!LED;
>
>     uiTemp = ui_RW_rfm12(0xB000);
>     printf("EMPFANGSDINGS ...  = %X\n",uiTemp);
>   }
Mit dieser Senderoutine wirst du nichts empfangen können. Du solltest 
vor dem Senden immer ein paar Dummy Bytes senden um den Transmitter zu 
stabilisieren. In meiner Senderoutine wird dafür 3x 0xAA gesendet. 
Anschließend musst du das Synchronisationsmuster 0x2DD4 senden, 
damit der Empfänger deine Pakete überhaupt annimmt. Also z.B. 0xAA 0xAA 
0xAA 0x2D 0xD4 0x00. Dabei wirst du am Empfänger nur das 0x00 
empfangen, mehr nicht. Das Synchronisationsmuster ist ein Muss, 
solange du das RFM12 mit 0xCA81 initialisierst.

Ich habe, als ich mit den RFM12 angefangen hatte, mal ein paar einfache 
Testprogramme geschrieben. Damit habe ich mich an die RFM12 
herangetastet gehabt. Diese funktionieren bei mir problemlos und senden 
einfach nur das Synchronisationsmuster plus ein Byte oder eine Serie von 
Bytes in einer Endlosschleife. Schau dir diese mal an, dann sollte es 
etwas klarer werden.

Beispiele:
https://quakeman.homelinux.net/viewvc/uVision/trunk/Test_RFM12_RX1/Test_RFM12_RX1.c?revision=2&view=markup
https://quakeman.homelinux.net/viewvc/uVision/trunk/Test_RFM12_RX2/Test_RFM12_RX2.c?view=markup
https://quakeman.homelinux.net/viewvc/uVision/trunk/Test_RFM12_TX1/Test_RFM12_TX1.c?view=markup
https://quakeman.homelinux.net/viewvc/uVision/trunk/Test_RFM12_TX2/Test_RFM12_TX2.c?view=markup

Ciao,
     Rainer

von Karl-heinz H. (kalliheinzi)


Angehängte Dateien:

Lesenswert?

Hallo Leute,

ich hoffe, dass ich hier im richtigen Forum gelandet bin - wenn nicht
erschlagt mich nicht gleich.

Da ich es nicht so mit Datenblatt wälzen des RFM12 habe, - habe ich
mal ein Tool nachgeschrieben, welches bei der Konfiguration helfen soll.

Das Original ist hier zu finden :

http://www.technofun.org/blog/

Hier hat mich aber gestört, dass es einen Bug bei der "Low Duty 
Cycle"-Einstellung hat und abstürzt.Desweiteren kann man die
Einstellungen nicht herauskopieren.

Dieses habe ich bei meinem nachprogrammierten Tool geändert und möchte
es Euch hiermit zur Verfügung stellen.Wer noch so viel mit dem RFM12
herumbasteln muss - wie ich... kann es vielleicht gebrauchen.

Achso - das Design habe ich übernommen - den Programmcode hatte ich
leider nicht :-)...

Hab' noch was vergessen : Der eine oder Andere muss ev. seine
Monitoreinstellung anpassen.

lg
kalli

von Karl-heinz H. (kalliheinzi)


Lesenswert?

Hallo Leute,

leider ist mir erst jetzt aufgefallen, dass das Fenster nicht bei
jeder Bildschirmauflösung optimal dargestellt wird.
Ich habe einen 22zöller und habe aufgrund meiner schlechten Augen
1152x864 eingestellt.Damit passt es optimal.

Hier ist also auch noch Handlungsbedarf...

...ist wie beim Erstellen von Webseiten - man vergisst schnell, dass
es auch noch andere Monitore gibt :-)

Sorry...

lg
Kalli

von Sebastian E. (omfg)


Lesenswert?

Ich kenne das Tool bereits und verwende es auch aber irgendwie habe ich 
mit meinem Prjektpartner einfach nur pech und unsere Funkstrecke 
funtkioniert einfach nicht wir haben uns nun Platinen fertigen lassen 
und hoffen das nun wenn alles fix eingelötet ist alles besser 
funktioniert

Danke
Eder Sebastian

von Karl-heinz H. (kalliheinzi)


Lesenswert?

Hallo Sebastian,

du hörst dich ein wenig frustig an... :-)

klar kennen das Proggi schon viele Leute...ich habe es nachgeschrieben,
weil es mir auch gut gefällt und ich es dadurch erweitern kann.
z.Z. implementiere ich eine Serielle Schnittstelle um mit einem AVR
zu sprechen...

snip...

schau dir doch mal die Hardwareverdrahtung von Pollin - oder
von Benedict an... es sind doch nur 3 Strippen (SPI) + Select+
ein Pullup für FSK/Data...
dann sollte alles funzen - der Rest ist Software !...

wenn ich helfen kann - sag' mal was...

Platinen herstellen kann ich auch...

lg
kalli

von Holger S. (holli_1)


Angehängte Dateien:

Lesenswert?

Ich habe mal eine Übersicht über den Programmablauf beim Senden und 
Empfangen erstellt. Das hilft dir vielleicht etwas. Ich habe inzwischen 
schon einige verschiedene Versionen zur Ansteuerung der RFM's 
zusammenprogrammiert. Sind allerdings alle in Bascom geschrieben, dafür 
auf das notwendigste beschränkt und funktionieren ohne Probleme. Wenn es 
dir was nützt, kann ich die mal posten.

von Karl-heinz H. (kalliheinzi)


Lesenswert?

@Holger...

deine Beschreibung sieht wirklich klasse aus - aber vermittelt meinem
Verständnis nach was falsches...nämlich - dass man vor einem "Senden"
oder "Empfangen" immer "INITIALISIEREN" sollte...
das ist natürlich quatsch...
...vielleicht versteh' ich es auch falsch...

ein "Dummy-Read" also 0x0000- reicht hier- um umzuschalten etc.

lg
kalli

von Holger S. (holli_1)


Lesenswert?

@Karl-Heinz

Du hast Recht, das Init braucht man nur ein Mal nach dem Einschalten. 
Die Übersicht habe ich erst zum Schluss gezeichnet.
Was und wo ist das mit dem "Dummy Read" zu lesen?

Gruß,
Holli

von Karl-heinz H. (kalliheinzi)


Lesenswert?

@Holger,

das ist immer ne' gute Frage - wo man was gelesen hat :-)
aber schau mal hier :
http://www.mikrocontroller.net/articles/RFM12#TX_Register_Write

lg
kalli

von Karl-heinz H. (kalliheinzi)


Lesenswert?

@Holger,

hab' da noch was...
Du schaltest z.B. den Sender mit 0x8238 ein - ist ja auch nicht
falsch - aber Konfigurationsabhängig - denn du kannst ihn
auch mit 0x827F einschalten...ebenso beim Empfänger...

zieh' dir mal obiges Proggi- dann siehst du was ich meine.

lg
kalli

von Holger S. (holli_1)


Lesenswert?

Eigentlich reicht schon 0x8220 (et) zu Senden und 0x8280 (er) zum 
Empfangen. Es sind interne Verknüpfungen vorhanden, welche die 
entsprechenden Blöcke im RFM automatisch mit aktivieren.
0x827f aktiviert aber auch den low battery detector und wake-up timer, 
diese IRQ's sollten dann auch entsprechend behandelt werden. Sonst 
bleibt nIRQ immer auf low und der RFM wird verdächtigt sich 
"aufgehangen" zu haben. Natürlich nur wenn der nIRQ Pin verwendet wird. 
Das ist aber bei den Codes von Pollin und Hope nicht der Fall. Dann 
fällt das mit dem nIRQ auch nie auf.

Gruß,
Holli

von Karl-heinz H. (kalliheinzi)


Lesenswert?

@Holger,

klar könnten wir jetzt noch endlos weiterdiskutieren - aber
damit ist dem Sebastian nicht geholfen.

Das Proggi oben habe ich nur gepostet, weil ich angenommen habe,
dass ev. Konfigurationsprobleme bestehen.Sonst hätte ich es
garnicht öffentlich gemacht.

Unsere RFM's laufen ja - seine nicht.

Also lass' uns bitte warten bis er seine Platinen hat und
sich wieder meldet - OK ???

lg
kalli

von Eder Sebastian (Gast)


Angehängte Dateien:

Lesenswert?

So ich bin jetzt so ziemlich gefrustet ....
Es funktioniert wiedermal garnichts....
Ich habe nun im Datenanhang alles mal was wir haben und wissen aber 
leider nicht wieso es nicht funktioniert wäre schön wenn ihr da mal 
drüber gucken könntet

von Holger S. (holli_1)


Lesenswert?

Wie ich das sehe, ist schon im Sender ein falscher Ablauf. Bei 
"TEMP_DATEN_SEND" schaltest du vor und nach jedem Byte den TX an und 
aus. Richtig wäre folgendes:

- TX an
- warten auf TX-IRQ (SDO high oder FFIT high oder nIRQ low)
- ein Datenbyte mit 0xB8.. schreiben
- warten auf TX-IRQ
- ein Datenbyte mit 0xB8.. schreiben
usw., bis alle Daten geschrieben sind
- TX aus

Du kannst sofort mit der Preambel (0x2D, 0xD4, ....) anfangen. Die 2 x 
0xAA Bytes am Anfang werden automatisch vom RFM TX-Register erzeugt.

edit: Das Sendekommando ist 0xB8.., 0xB0.. ist nur zum FIFO Lesen.

von Eder Sebastian (Gast)


Lesenswert?

Danke für die schnelle antwort ich und mein Projektpartner werden dies 
einmal beheben und uns dann nochmal melden , werden sicher nicht die 
einzigen Fehler sein :(!

mfg
Eder Sebastian

von Eder Sebastian (Gast)


Angehängte Dateien:

Lesenswert?

So jetzt wurde das Programm überarbeitet.

MfG&Danke

von Karl-heinz H. (kalliheinzi)


Lesenswert?

@Sebastian,

ich sehe in deinem Programm nirgendwo das du SDO oder nIRQ des
RFM's abfragst - nachdem du ein Byte zum RFM geschickt hast...
du musst also bevor du ein neues Byte schickst immer auf eine
" Send ready"- Bestätigung des RFM's warten.
Sonst geht das Senden garnicht, weil du Daten zum RFM schickst -
obwohl das Senden noch nicht beendet ist.

Hab' dein Proggi aber nur überflogen und kanns' übersehen haben.

lg
kalli

von Karl-heinz H. (kalliheinzi)


Lesenswert?

@Sebastian,

unsere Posts haben sich überschnitten - hab' erst jetzt gesehen,
dass du ein RFMready eingefügt hast... hier solltest du aber
den mächtigen printf rausnehmen, da du dadurch den recht kurzen
nIRQ verpassen könntest.


lg
kalli

von Holger S. (holli_1)


Lesenswert?

Ich habe noch was vergessen, nach den Daten noch 2 "Dummy Bytes" (z.B. 
0xAA) an den RFM senden. Die werden gebraucht, um alle Nutzdaten aus dem 
TX-Register zum Sender zu schieben.

von Sebastian E. (omfg)


Lesenswert?

@FOX MULDER

Was ich bei deiner Routine nicht verstehe

C-CODE --> DES EMPFÄNGERS
1
// Es wird solange gewartet, bis das Preambel und anschließend n Datenbytes empfangen wurden
2
void v_Receive_rfm12(unsigned char ucPaketlaenge, unsigned char data * data pucRX_Daten)
3
 {
4
  unsigned int uiTemp;
5
  unsigned char i;
6
7
  
8
  RF_WRITE_DATA(0x82C8);  // Power Management Command: er=1, ebb=1, et=0, es=0, ex=1, eb=0, ew=0, dc=1
9
  RF_WRITE_DATA(0xCA81);  // FIFO and Reset Mode Command: FIFO Level=8, al=0, ff=1, dr=1
10
  RF_WRITE_DATA(0xCA83);
11
12
13
  for (i = 0; i < ucPaketlaenge; i++) {
14
    NSEL = 0;
15
  //puts("vor SDO");
16
    while(SDO == 0);
17
  //puts("nach SDO");
18
  
19
  
20
    uiTemp = ui_RW_rfm12(0xB000);
21
  //printf("uiTEMP=%X",uiTemp);
22
    *(pucRX_Daten + i) = uiTemp & 0xFF;
23
  }
24
25
  RF_WRITE_DATA(0x8209);  // Power Management Command: er=0, ebb=0, et=0, es=0, ex=1, eb=0, ew=0, dc=1
26
}

wieso du den NSEL nach dem abfragen nicht wieder auf =1 setzt?
Desweiteren wollte ich fragen ob es stört wenn ich die "puts-funktionen" 
reinmache

von R. W. (quakeman)


Lesenswert?

Sebastian Eder schrieb:
> wieso du den NSEL nach dem abfragen nicht wieder auf =1 setzt?
> Desweiteren wollte ich fragen ob es stört wenn ich die "puts-funktionen"
> reinmache

Das liegt dadran, dass die danach verwendete Methode "ui_RW_rfm12", 
welche die Daten aus dem RFM12 ausliest, NSEL am Ende sowieso wieder auf 
1 setzt. Ich brauche das NSEL = 0 davor ja nur um auf SDO zu prüfen 
wegen neuen Daten. Also das NSEL = 1 ist quasi nur weg optimiert worden. 
;)

Also ich verwende zum senden/empfangen per RS232 einen interrupt 
gesteuerten Ringpuffer. Dabei ist das Timing egal, weil er im 
Hintergrund senden kann ohne eventuell Daten vom RFM12 zu verpassen. 
Insofern deine puts Methode per Polling die Daten über die RS232 sendet 
könnte es zeitlich etwas kritisch werden. Aber das müsstest du einfach 
mal ausprobieren. Notfalls den Text sehr schnell (115200 Bps) senden und 
möglichst kurz halten (z.B. nur 1 Zeichen).

Ciao,
     Rainer

von Karl-heinz H. (kalliheinzi)


Angehängte Dateien:

Lesenswert?

@Sebastian,

um mal wirklich auf einen Nenner zu kommen - prüfe doch mal bitte den
obigen Schaltplan.Wenn dieser bei dir so übereinstimmt kann man
helfen.Allerdings habe ich den Eindruck - das du zwei verschiedene
Controller verwendest.Um ersteinmal eine Kommunikation zustande zu
bekommen, würde ich dir vorschlagen - 2 atmega8 zu benutzen und diese
so zu verschalten - wie es oben gezeigt ist.Wenn dieses dann funzt, kann
man immer noch auf andere mc's portieren.

Der Kostenaufwand ist hier auch sehr gering.Wenn wir nicht über gleiche 
Vorraussetzungen sprechen, wird jede Hilfe ins Nirwana laufen.

Auch einen Prozessor in einer Warteschleife laufen zu lassen um
Daten zu empfangen - ist nicht optimal, da er ja sonst nichts
mehr macht...obwohl er könnte.

lg
kalli

von R. W. (quakeman)


Lesenswert?

Karl-heinz H. schrieb:
> Auch einen Prozessor in einer Warteschleife laufen zu lassen um
> Daten zu empfangen - ist nicht optimal, da er ja sonst nichts
> mehr macht...obwohl er könnte.

Das Problem hat man aber immer, sobald man Polling anstatt Interrupts 
benutzt. Aber Polling ist bei den RFM12 nicht so fehleranfällig wie der 
Interruptbetrieb, sobald die Einstellungen nicht zu 100% korrekt sind. 
Deshalb sollte er lieber erst mal per SDO Polling arbeiten und das zum 
laufen bringen.
Ich habe diverse Anwendungen mit den RFM12, bei welchen ich quasi nichts 
anderes mache als nur Daten zu übertragen. Dort benutze ich immer nur 
Polling und die Controller warten solange darauf, bis endlich mal etwas 
ankommt. :)

Aber der Hinweis, es erst mal mit zwei gleichen Controllern zu testen 
ist schon mal sehr gut. Momentan testet er es glaube ich mit einem PIC 
und einem 8051er auf der anderen Seite. Nur macht es für ihn dann mehr 
Sinn, zweimal PIC oder 8051er zu benutzen anstatt zwei AVR. Ansonsten 
bringt er dann gleich die dritte Controller Familie mit ins Spiel, was 
wohl eher zu mehr Verwirrung führt als zur Lösung. ;)

Ciao,
     Rainer

von Karl-heinz H. (kalliheinzi)


Lesenswert?

@Rainer,

ok - vieles ist natürlich Ansichtssache - die meisten Programme und
Beispiele hier im Forum beruhen auf AVR's.Ich habe z.B.weder PIC's noch
8051ger - klar ist alles irgendwo gleich/ähnlich - wenn man es denn 
umsetzen
kann. Aber wenn man anfängt sollte man sich schon so ein System
aussuchen/aufbauen - welches schon erprobt ist.Dann können auch viele
Leute helfen.Wenn man das dann verstanden hat - kann man weitersehen.
Alles andere ist ein Lottospiel - klar kann man mal gewinnen.....
 :-)

lg
kalli

von Holger S. (holli_1)


Lesenswert?

Fox Mulder schrieb:
> Aber Polling ist bei den RFM12 nicht so fehleranfällig wie der
> Interruptbetrieb, sobald die Einstellungen nicht zu 100% korrekt sind.

Das Problem ist aber nicht der RFM, sondern die Interruptbehandlung im 
Programm. nIRQ bleibt so lange auf low bis entweder das Statusregister 
oder FIFO gelesen wurde oder das TX-Register beschrieben. Im Gegensatz 
zu anderen Dingen ist das in der Doku ordentlich beschrieben. Davon 
werden wahrscheinlich die meisten "Aufhänger" und Probleme herkommen.
Nach dem Einschalten z.B. wird nIRQ low wegen des EXT-IRQ's. Nach dem 
Lesen des Status Registers geht nIRQ auf high. Beim SDO-Polling spielt 
das keine Rolle und wird daher auch nicht bemerkt.

von Karl-heinz H. (kalliheinzi)


Lesenswert?

seh' ich auch so...

lg
kalli

von R. W. (quakeman)


Lesenswert?

Genau das zeigt doch, dass es deutlich einfacher ist für den Anfang 
Polling zu benutzen, weil er weniger Dinge dabei beachten muss um es zum 
Laufen zu bekommen. Man sollte eben nicht gleich alles auf einmal 
versuchen sondern Schritt für Schritt sich in die Materie einarbeiten.

Ciao,
     Rainer

von Sebastian E. (omfg)


Lesenswert?

Sooo, senden hat nun schon funktioniert und funktioniert weiterhin laut 
frequenzanalyzEr.
Empfangen hat auch funktioniert nun wollten wir auf den nINT/VINT 
anschließen und danach funktionierte es nicht mehr... nun ist uns der 
ganze PIN rausgefallen bzw abgebrochen!
Ist das Modul nun hinüber ist die Frage und wie empfindlich reagiert das 
Modul wenn ein Widerstand an diesem Pin ist!
Gibt es irgendwo eine genau Beschreibung der Ports und Pins da ich von 
vielen Pins nicht einmal genau weiß was sie machen.

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
Noch kein Account? Hier anmelden.