Forum: HF, Funk und Felder Probleme mit NRF24L01


von Sebastian S. (sebastian_s25)


Lesenswert?

Hi Leute

ich bin neu hier und hab auch gleich noch ein grosses Problem.... (was 
auch sonst :()

Ich versuche ueber einen FT232 und einen ATmega168 ein NRF24L01 Modul 
anszusprechen und eine Nachricht an ein anderes Modul mit einem ATmega32 
zu senden. Beide uCs kommunizieren ueber SoftwareSPI mit dem Modul, da 
es hardwaremaessig nicht anders geht.

Jetzt hab ich das ganze Programm schon geschrieben und es klappt auch 
fast!!

Ich kann die Register beschreiben und lesen und die kommunikation ueber 
den FT funktioniert auch einwandfrei.

Jetzt wenn ich aber eine Nachricht senden will, bekomm ich keinen 
Interrupt! :( (mein erstes Ziel war, nur den Max_RT als bestaetigung zu 
bekommen)

Ich gebe dem Modul einen Impuls von 20 us und warte dann bis ein 
Interrupt ueber den IRQ Pin kommt. Der Interrupt muss auf jeden fall 
kommen, da ich eingestellt habe, dass er bei Max_RT (1 mal) auch einen 
Interrupt gibt.

Um zu testen, ob das weitere Programm ueberhaupt funktioniert, hab ich 
per hand mal den IRQ auf GND gezogen und alles hat funktioniert!!

Es muss also irgendwo entweder an der Sendebedingung oder meiner 
Initialisierung liegen... Nur wo??

Ich hoffe ihr koennt mir helfen!! Ich verzweifle noch...

mfg
Bastian

Hier ist mein Code:

main (nur in Switch_Light wird was gesendet!!)
1
#include <avr/io.h>
2
#include <stdint.h>
3
#include <util/delay.h>
4
#include <avr/interrupt.h>
5
#include "USART_Dec.h"
6
#include "NRF24L01_Dec.h"
7
#include "SoftwareSPI_Dec.h"
8
#include "USB_RF_Dec.h"
9
#include "Converter.h"
10
11
volatile uint8_t wait;
12
volatile uint8_t IFlag;
13
14
int main (void)
15
{  
16
  unsigned char USART_Receive_Message[Messagelength];
17
  uint8_t u8i = 0x00;
18
  uint8_t ACK = 0x00;
19
20
  USART_Init();        //Initialise USART
21
  SSPI_Init();        //Initialise SSPI
22
  NRF24L01_Init();      //Initialise NRF-Module
23
24
  sei();
25
26
  while (1) 
27
    {
28
      USART_Receive_Message[u8i] = USART_Receive();  // write received bytes to the input buffer
29
                  // Warning: If a disturbance occured the buffer will increase and the next received Messages will be wrong
30
  
31
    u8i++;
32
    if(u8i==Messagelength)  
33
    {
34
      u8i = 0;
35
      if(USART_Receive_Message[0] == 0x87)    // verifying the Message
36
      {
37
        switch(USART_Receive_Message[1])
38
        {
39
          case 0xAC :      // get control
40
          {
41
            // Convert Address
42
            Addressconvert.c[0] = USART_Receive_Message[2];
43
            Addressconvert.c[1] = USART_Receive_Message[3];
44
            Addressconvert.c[2] = USART_Receive_Message[4];
45
            Addressconvert.c[3] = USART_Receive_Message[5];
46
            
47
            RGBconvert.c[0] = USART_Receive_Message[6];
48
            RGBconvert.c[0] = USART_Receive_Message[7];
49
            RGBconvert.c[0] = USART_Receive_Message[8];
50
          
51
            uint8_t Pipe = 0x0A;
52
53
            ACK = SwitchLight(Addressconvert.u32i, RGBconvert.u32i, Pipe);
54
            if(ACK == 0x02)
55
            {
56
              // all ok, send ok-Message
57
              USART_Send(0x87);
58
              USART_Send(0x11);
59
            }
60
            else
61
            {  if(ACK == 0x04)
62
              {
63
                // Light not avaliable (failure in connection to Light)
64
                USART_Send(0x87);
65
                USART_Send(0x23);
66
              }
67
              else
68
              {
69
                USART_Send(0x87);
70
                USART_Send(0x24);
71
              }
72
            }
73
            break;
74
          }
75
          case 0xBF :        // get error from controller
76
          {
77
            if(ACK == 1)
78
            {
79
              // send ACK again
80
              USART_Send(0x87);
81
              USART_Send(0x11);
82
            }
83
            else
84
            {  
85
              // send "Light not avaliable" again
86
              USART_Send(0x87);
87
              USART_Send(0x23);
88
            }
89
            break;
90
          }
91
          default :
92
          {
93
            // invalid message received
94
            USART_Send(0x87);
95
            USART_Send(0x22);
96
            ACK = 0;
97
            break;
98
          }
99
        }
100
      }
101
      else
102
      {  
103
        // invalid message received  
104
        USART_Send(0x87);
105
        USART_Send(0x22);
106
      }
107
    }
108
  }
109
}
110
111
uint8_t SwitchLight(uint32_t u32Address, uint32_t u24RGB, uint8_t Pipe)
112
{
113
  wait = 0x01;
114
115
  Payloadconvert.c[0] = 1; // RGBconvert.c[0];
116
  Payloadconvert.c[1] = 2; // RGBconvert.c[2];
117
  Payloadconvert.c[3] = 3; // RGBconvert.c[3];
118
119
  NRF_ChangeTXAddress(u32Address);
120
  NRF_ChangeRXAddress(u32Address, Pipe);
121
  NRF_SetTXState();
122
  NRF_WriteTXPayload(Payloadconvert.u256i);
123
124
  USART_Send(NRF_ReadRegister(STATUS));
125
  NRF_SendImpuls();
126
127
128
  while((wait & 0x01) == 0x01);
129
130
  switch(IFlag)
131
  {
132
    case 0x01:
133
      return 0x01;
134
    case 0x04:
135
      return 0x04;
136
    case 0x02:
137
      return 0x02;
138
    default:
139
      return 0xff;
140
  }
141
}
142
143
ISR(INT0_vect)
144
{
145
  uint8_t tmp_sreg;
146
  uint8_t status_reg;
147
148
  tmp_sreg = SREG;      // Safe SREG
149
   
150
  cli();            // Disable the global Interrupt
151
152
// auto clear  INT_FLAG_CL;        // Clears the Interruptflag
153
154
  status_reg = NRF_ReadRegister(STATUS);
155
  USART_Send(0x73);
156
  USART_Send(0x74);
157
  USART_Send(0x61);
158
  USART_Send(0x74);
159
  USART_Send(0x75);
160
  USART_Send(0x73);
161
  USART_Send(status_reg);
162
163
  if((status_reg & RX_DR) == RX_DR)
164
  {
165
    IFlag = 0x01;
166
  }
167
  if((status_reg & TX_DS) == TX_DS)
168
  {
169
    IFlag = 0x02;
170
  }
171
  if((status_reg & MAX_RT) == MAX_RT)
172
  {
173
    IFlag = 0x04;
174
  }
175
  
176
  USART_Send(0xaa);
177
  wait = 0x00;
178
  SREG = tmp_sreg;      // Restore SREG
179
}

NRF_Funktionen
1
#include <stdint.h>
2
#include <avr/io.h>
3
#include <util/delay.h>
4
#include "NRF24L01_Dec.h"
5
#include "SoftwareSPI_Dec.h"
6
#include "USART_Dec.h"
7
#include "Converter.h"
8
#include "USB_RF_Dec.h"
9
10
extern unsigned char Payload[32];
11
extern unsigned char data_receive[32];
12
13
/****** NRF Init *****************/
14
15
void NRF24L01_Init(void)
16
{
17
  NRF_CE_DDR |= (1<<NRF_CE);
18
  
19
  NRF_IRQ_DDR &= ~(1<<NRF_IRQ);
20
  NRF_IRQ_PORT |= (1<<NRF_IRQ);
21
22
  INT_SENS;
23
  INT_EN;
24
25
  NRF_WriteRegister(0x0A, CONFIG);
26
  NRF_WriteRegister(0x01, EN_AA);
27
  NRF_WriteRegister(0x01, EN_RXADDR);
28
  NRF_WriteRegister(0x02, SETUP_AW);
29
  NRF_WriteRegister(0x01, SETUP_RETR);
30
  NRF_WriteRegister(0x02, RF_CH);
31
  NRF_WriteRegister(0x0E, RF_SETUP);
32
33
  NRF_CE_Lo;
34
}
35
36
/****** Write Register ***********/
37
38
void NRF_WriteRegister(uint8_t u8Register, uint8_t u8Cmd)
39
{
40
  uint8_t u8Command = W_REGISTER | u8Cmd;
41
42
  SCSN_Lo;
43
44
  SSPI_Write_byte(u8Command);
45
  SSPI_Write_byte(u8Register);
46
47
  SCSN_Hi;
48
}
49
50
/****** Read Register ************/
51
52
uint8_t NRF_ReadRegister(uint8_t u8Cmd)
53
{
54
  uint8_t u8Command = R_REGISTER | u8Cmd;
55
  uint8_t u8Content = 0x00;
56
57
  SCSN_Lo;
58
59
  SSPI_Read_byte(u8Command);
60
  u8Content = SSPI_Read_byte(0x00);
61
62
  SCSN_Hi;
63
  return u8Content;
64
}
65
66
/****** Read RX Address ***********/
67
68
uint32_t NRF_ReadRXAddress(uint8_t u8Pipe)
69
{
70
  uint8_t u8PipeReg = 0x00;
71
  uint8_t u8i = 0x00;
72
  
73
    switch (u8Pipe)
74
  {
75
    case 0x0A: 
76
      u8PipeReg = RX_ADDR_P0;
77
      break;
78
    case 0x0B: 
79
      u8PipeReg = RX_ADDR_P1;
80
      break;
81
    case 0x0C: 
82
      u8PipeReg = RX_ADDR_P2;
83
      break;
84
    case 0x0D: 
85
      u8PipeReg = RX_ADDR_P3;
86
      break;
87
    case 0x0E: 
88
      u8PipeReg = RX_ADDR_P4;
89
      break;
90
    case 0x0F: 
91
      u8PipeReg = RX_ADDR_P5;
92
      break;
93
  }
94
95
  uint8_t u8Command = R_REGISTER | u8PipeReg;
96
  SCSN_Lo;
97
  SSPI_Write_byte(u8Command);
98
  for(u8i = 4; u8i>0; u8i--)
99
  {
100
    Addressconvert.c[u8i-1] = SSPI_Read_byte(NO_OP);
101
  }
102
  SCSN_Hi;
103
  return Addressconvert.u32i;
104
}
105
106
107
/****** Read TX Address ***********/
108
109
uint32_t NRF_ReadTXAddress()
110
{
111
  uint8_t u8i = 0x00;
112
  
113
  uint8_t u8Command = R_REGISTER | TX_ADDR;
114
  SCSN_Lo;
115
  SSPI_Write_byte(u8Command);
116
  for(u8i = 4; u8i>0; u8i--)
117
  {
118
    Addressconvert.c[u8i-1] = SSPI_Read_byte(NO_OP);
119
  }
120
  SCSN_Hi;
121
  return Addressconvert.u32i;
122
}
123
124
/****** Change RX Address ***********/
125
126
void NRF_ChangeRXAddress(uint32_t u32Address, uint8_t u8Pipe)
127
{
128
  uint8_t u8PipeReg = 0x00;
129
  uint8_t u8CEFlag = 0x00;
130
  uint8_t u8i = 0x00;
131
  Addressconvert.u32i = u32Address;
132
  
133
  if(PORTB & NRF_CE)
134
  {
135
    NRF_CE_Lo;
136
    u8CEFlag = 0x11;
137
  }
138
  _delay_us(250);
139
  switch (u8Pipe)
140
  {
141
    case 0x0A: 
142
      u8PipeReg = RX_ADDR_P0;
143
      break;
144
    case 0x0B: 
145
      u8PipeReg = RX_ADDR_P1;
146
      break;
147
    case 0x0C: 
148
      u8PipeReg = RX_ADDR_P2;
149
      break;
150
    case 0x0D: 
151
      u8PipeReg = RX_ADDR_P3;
152
      break;
153
    case 0x0E: 
154
      u8PipeReg = RX_ADDR_P4;
155
      break;
156
    case 0x0F: 
157
      u8PipeReg = RX_ADDR_P5;
158
      break;
159
  }
160
  uint8_t u8Command = W_REGISTER | u8PipeReg;
161
  SCSN_Lo;
162
  SSPI_Write_byte(u8Command);
163
  for(u8i = 4; u8i>0; u8i--)
164
  {
165
    SSPI_Write_byte(Addressconvert.c[u8i-1]);
166
  }
167
  SCSN_Hi;
168
169
  _delay_us(10);
170
171
  if(u8CEFlag == 0x11)
172
  {
173
    NRF_CE_Hi;
174
    u8CEFlag = 0x00;
175
  }
176
}
177
178
/****** Change TX Address ***********/
179
180
void NRF_ChangeTXAddress(uint32_t u32Address)
181
{
182
  uint8_t u8i = 0x00;
183
  uint8_t u8CEFlag = 0x00;
184
  Addressconvert.u32i = u32Address;
185
  
186
  if(PORTB & NRF_CE)
187
  {
188
    NRF_CE_Lo;
189
    u8CEFlag = 0x11;
190
  }
191
  _delay_us(250);
192
  uint8_t u8Command = W_REGISTER | TX_ADDR;
193
  SCSN_Lo;
194
  SSPI_Write_byte(u8Command);
195
  for(u8i = 4; u8i>0; u8i--)
196
  {
197
    SSPI_Write_byte(Addressconvert.c[u8i-1]);
198
  }
199
  SCSN_Hi;
200
  _delay_us(10);
201
202
  if(u8CEFlag == 0x11)
203
  {
204
    NRF_CE_Hi;
205
    u8CEFlag = 0x00;
206
  }
207
}
208
209
/****** Write TX Payload ************/
210
211
void NRF_WriteTXPayload(struct uint256_t u256Payload)
212
{  
213
  uint8_t u8i;
214
  Payloadconvert.u256i = u256Payload;
215
  SCSN_Lo;
216
  uint8_t u8Reg = NRF_ReadRegister(CONFIG);
217
  SCSN_Hi;
218
219
  if(u8Reg & 0x01)
220
  {
221
    SCSN_Lo;
222
    SSPI_Write_byte(W_TX_PAYLOAD);
223
    for(u8i=32 ; u8i>0; u8i--)
224
    {
225
      SSPI_Write_byte(Payloadconvert.c[u8i-1]);
226
    }
227
    SCSN_Hi;
228
  }
229
}
230
231
/****** Read RX Payload ************/
232
233
struct uint256_t NRF_ReadRXPayload()
234
{  
235
  uint8_t u8i = 0x00;
236
237
  SCSN_Lo;
238
  uint8_t u8Reg = NRF_ReadRegister(CONFIG);
239
  SCSN_Hi;
240
241
  if(!(u8Reg & 0x01))
242
  {  
243
    SCSN_Lo;
244
    SSPI_Write_byte(R_RX_PAYLOAD);
245
    for(u8i=32; u8i>0; u8i--)
246
    {
247
      Payloadconvert.c[u8i-1] = SSPI_Read_byte(NO_OP);
248
    }
249
    SCSN_Hi;
250
  }
251
  else
252
  {
253
    for(u8i=0; u8i<32; u8i++)
254
    {
255
      Payloadconvert.c[u8i] = 0xff;
256
    }
257
  }
258
  return Payloadconvert.u256i;
259
}
260
261
/****** Flush RX Buffer **********/
262
263
void NRF_FlushRXBuffer(void)
264
{
265
  SCSN_Lo;
266
  SSPI_Write_byte(FLUSH_RX);
267
  SCSN_Hi;
268
}
269
270
/****** Flush TX Buffer **********/
271
272
void NRF_FlushTXBuffer(void)
273
{
274
  SCSN_Lo;
275
  SSPI_Write_byte(FLUSH_TX);
276
  SCSN_Hi;
277
}
278
279
/****** Reuse TX Buffer **********/
280
281
void NRF_ReuseTXBuffer(void)
282
{  
283
  SCSN_Lo;
284
  SSPI_Write_byte(REUSE_TX_PL);
285
  SCSN_Hi;
286
}
287
288
/****** Set RX State *************/
289
290
void NRF_SetRXState()
291
{
292
  uint8_t oldConfig = NRF_ReadRegister(CONFIG);
293
  
294
  uint8_t newConfig = oldConfig | 0x01;
295
296
  NRF_WriteRegister(newConfig, CONFIG);
297
}
298
299
/****** Set TX State *************/
300
301
void NRF_SetTXState()
302
{
303
  uint8_t oldConfig = NRF_ReadRegister(CONFIG);
304
  
305
  uint8_t newConfig = oldConfig & ~(0x01);
306
307
  NRF_WriteRegister(newConfig, CONFIG);
308
}
309
  
310
/****** Send Impuls **************/
311
312
void NRF_SendImpuls()
313
{
314
  NRF_CE_Hi;
315
  _delay_us(20);
316
  NRF_CE_Lo;
317
}

Declarationen
NRF
1
/***** Define short commands ***************/
2
3
#define NRF_CE_Lo NRF_CE_PORT &= ~(1<<NRF_CE);
4
#define NRF_CE_Hi NRF_CE_PORT |= (1<<NRF_CE);
5
6
/***** Define Constants ************/
7
8
#define   NO_OP           0xff
9
#define   R_REGISTER      0x00
10
#define   W_REGISTER      0x20
11
#define   R_RX_PAYLOAD    0x61
12
#define   W_TX_PAYLOAD    0xA0
13
#define   FLUSH_TX        0xE1
14
#define   FLUSH_RX        0xE2
15
#define   REUSE_TX_PL     0xE3
16
17
#define   RX_ADDR_P0      0x0A
18
#define   RX_ADDR_P1      0x0B
19
#define   RX_ADDR_P2      0x0C
20
#define   RX_ADDR_P3      0x0D
21
#define   RX_ADDR_P4      0x0E
22
#define   RX_ADDR_P5      0x0F
23
#define   TX_ADDR         0x10
24
#define   RX_PW_P0        0x11
25
#define   RX_PW_P1        0x12
26
#define   RX_PW_P2        0x13
27
#define   RX_PW_P3        0x14
28
#define   RX_PW_P4        0x15
29
#define   RX_PW_P5        0x16
30
#define   FIFO_STATUS     0x17
31
32
#define   CONFIG      0x00
33
#define    EN_AA        0x01
34
#define   EN_RXADDR      0x02
35
#define   SETUP_AW      0x03
36
#define    SETUP_RETR    0x04
37
#define   RF_CH        0x05
38
#define    RF_SETUP      0x06  
39
#define   STATUS        0x07
40
41
#define   TX_FULL         0x01
42
#define   RX_DR           0x40
43
#define   TX_DS           0x20
44
#define   MAX_RT          0x10
45
46
/***** Funktions *******************/
47
48
void NRF_ReuseTXBuffer(void);
49
void NRF_FlushTXBuffer(void);
50
void NRF_FlushRXBuffer(void);
51
52
struct uint256_t NRF_ReadRXPayload(void);
53
void NRF_WriteTXPayload(struct uint256_t);
54
55
void NRF_ChangeRXAddress(uint32_t, uint8_t);
56
void NRF_ChangeTXAddress(uint32_t);
57
58
uint32_t NRF_ReadRXAddress(uint8_t);
59
uint32_t NRF_ReadTXAddress();
60
61
uint8_t NRF_ReadRegister(uint8_t);
62
void NRF_WriteRegister(uint8_t, uint8_t);
63
64
void NRF24L01_Init(void);
65
void NRF_SetRXState(void);
66
void NRF_SetTXState(void);
67
void NRF_SendImpuls(void);

main
1
/******* with ATMEGA168 ********************/
2
3
#include <avr/io.h>
4
5
#define Messagelength 9    // Length of the USART Message
6
7
/***** Functions ***************************/
8
9
uint8_t SwitchLight(uint32_t, uint32_t, uint8_t);
10
11
/***** NRF *********************************/
12
/***** Set Ports ***************************/
13
14
#define NRF_CE       PB1
15
#define NRF_CE_PORT   PORTB
16
#define NRF_CE_DDR     DDRB
17
18
#define NRF_IRQ      PD2
19
#define NRF_IRQ_PORT  PORTD
20
#define NRF_IRQ_DDR    DDRD
21
22
#define INT_SENS    EICRA = (1<<ISC01) | (1<<ISC00);
23
#define INT_EN      EIMSK = (1<<INT0);
24
#define INT_FLAG_CL    EIFR = (1<<INTF0);
25
26
/*-----------------------------------------*/
27
28
29
/***** SSPI ********************************/
30
/***** Set Ports ***************************/
31
32
#define SMISO     PB0
33
#define SMOSI    PD7
34
#define SSCK    PD6
35
#define SCSN    PD5
36
37
#define SMOSI_PORT   PORTD
38
#define SMOSI_DDR  DDRD
39
40
#define SSCK_PORT  PORTD
41
#define SSCK_DDR  DDRD
42
43
#define SCSN_PORT  PORTD
44
#define SCSN_DDR  DDRD
45
46
#define SMISO_PORT  PORTB
47
#define SMISO_DDR  PORTB

von Gerhard (Gast)


Lesenswert?

Hi,

bin zwar kein C-Programmierer, aber ich glaube zu wissen, daß die 
Register genau so beschrieben werden wir beim RFM70 und für den gibt´s 
komplette Beispiele in C:
http://www.hoperf.com/rf_fsk/24g/rfm70.htm


Gruß
Gerhard

von Sebastian S. (sebastian_s25)


Lesenswert?

Also nen ersten Fehler hab ich schon gefunden!!

da ich nie auch nur das MAX_RT Flag bekommen hab, hab ich mal die 
Payloadschreibroutine nochmal genauer angesehen, und bin drauf gekommen, 
dass die der Hund begraben lag.

Er hat nie in den TX-FIFO geschrieben!!
1
/****** Write TX Payload ************/
2
3
void NRF_WriteTXPayload(struct uint256_t u256Payload)
4
{  
5
  uint8_t u8i;
6
  Payloadconvert.u256i = u256Payload;
7
  SCSN_Lo;
8
  uint8_t u8Reg = NRF_ReadRegister(CONFIG);
9
  SCSN_Hi;
10
11
  if(!(u8Reg & 0x01))  // Hier war der 1. Fehler!!! 
12
  {
13
    SCSN_Lo;
14
    SSPI_Write_byte(W_TX_PAYLOAD);
15
    for(u8i=32 ; u8i>0; u8i--)
16
    {
17
      SSPI_Write_byte(Payloadconvert.c[u8i-1]);
18
    }
19
    SCSN_Hi;
20
  }
21
}

nun hab ich alles im FIFO drin. und er gibt mir das MAX_RT Flag und 
einen Interrupt!!!!

Nur leider springt er nicht in meine Routine!! :(

was hab ich da falsch gemacht? und wie muss ich den NRF Interrupt 
zuruecksetzen??

mfg
Bastian

PS: @Gerhard: Danke fuer deinen Tip, aber das Registerbeschreiben geht 
ja... Aber die Seite wurde gleich noch vorgemerkt, falls nochwas nicht 
geht!! ;) Danke dir.

von Manfred H. (eas)


Lesenswert?

Hallo

meiner Meinung nach sind alle Interrupts freigeschaltet. Wenn kein 
Interrupt ausgeführt wird prüfe die Hardware ob der INT Pin des nRF auch 
auf den richtigen Pin des Prozessors geht.
Der Prozesor sollte auf level-triggered Interrupt stehen, wenn man einen 
Interrupt verpasst hängt das System da der Pin des nRF über Software 
zurückgesetzt werden muss.
Der MAX_RT ist der schlechteste Interrupt um die Kommunikation zu 
steuern. Der kommt nur wenn bei aktivierter Autoacknowledgment Funktion 
die Übertragung fehlschlägt, bzw. wenn die maximale Anzahl 
Wiederholungen erreicht wurde. Wird das Paket gesendet und bestätigt 
dann kommt er nicht.
Um festzustellen ob ein Paket gesendet wurde ist der TX_DS Interrupt der 
richtige.
Die Interrupts werden gelöscht indem man an der entsprechenden Stelle 
eine 1 in das Statusbyte schreibt.

von Sebastian S. (sebastian_s25)


Lesenswert?

Hi Mandfred

Ja jetzt bekomm ich auch endlich meinen Interrupt!! :) Musste 
komischerweise in der Write Payloadschleife u8i auf 33 stellen...
Wie kann ich beim Leveltrigger eigentlich den Interrput dann abstellen?? 
sonst kommt er ja steaendig?

Aber wenn ichs ueber die Interrputroutine laufen lass, komm ich nicht 
mehr raus und er sendet mir jedes mal 3F3F ueber UART zurueck!!

Jetzt hab ichs mal ohne gemacht, weil ich sowieso drauf warten will und 
es funktioniert richtig.

Den Max RT hab ich nur am anfang hergenommen, da ich beide ATmega nicht 
debuggen kann und so feststellen kann, dass wenigstens einer versucht 
was zu senden :)

So jetzt versuch ich mal die Empfaengerplatine anzuschmeissen...

von Manfred H. (eas)


Lesenswert?

Sebastian S. schrieb:

> Wie kann ich beim Leveltrigger eigentlich den Interrput dann abstellen??
> sonst kommt er ja steaendig?

Die Interruptroutine muss natürlich die "Ursache" ihres Aufrufs 
beseitigen.
d.h. man löscht den Interrupt im nRF und das Signal geht auf High, dann 
kann
man die Interruptroutine verlassen. Nur so macht es Sinn Interrupts zu 
benutzen.
Wenn der Prozessor genug Zeit übrig hat kann man das Teil auch im 
Polling betreiben, ohne Hardwareinterrupt.

von Sebastian S. (sebastian_s25)


Lesenswert?

Das mit dem "Bereinigen" hat nicht ganz so hingehaun... Kann das sein, 
dass ich neben dem Interruptflag noch was anderes zuruecksetzen muss??

Wie auch immer, ich machs jetzt uebers polling, da die Funkverbindung 
eigentlich nur ein Kabel ersetzen soll ;)

Jetzt hab ich aber das Problem, dass ich nichts empfange!! Ich test 
jetzt schon den ganzen Tag und schau was an den Einstellungen falsch 
sein koennte aber irgendwie komm ich auf keinen gruenen zweig.

Ich hab jetzt am schluss sogar noch die Dynamic Payload Funktion enabled 
aber nix...

So initialisiere ich jetzt:
1
void NRF24L01_Init(void)
2
{
3
  NRF_CE_Lo;
4
5
  NRF_CE_DDR |= (1<<NRF_CE);
6
  
7
  NRF_IRQ_DDR &= ~(1<<NRF_IRQ);
8
  NRF_IRQ_PORT |= (1<<NRF_IRQ);
9
10
//  INT_SENS;
11
//  INT_EN;
12
13
  NRF_WriteRegister(0x0B, CONFIG);
14
  NRF_WriteRegister(0x01, EN_AA);
15
  NRF_WriteRegister(0x01, EN_RXADDR);
16
  NRF_WriteRegister(0x02, SETUP_AW);
17
  NRF_WriteRegister(0x03, SETUP_RETR);
18
  NRF_WriteRegister(0x02, RF_CH);
19
  NRF_WriteRegister(0x0E, RF_SETUP);
20
21
  NRF_WriteRegister(0x01, DYNPD);
22
  NRF_WriteRegister(0x07, FEATURE);
23
24
  NRF_CE_Lo;
25
}

und das ist mein Main:
1
int main (void)
2
{
3
  IFlag = 0x00;
4
  uint8_t status_reg;
5
6
  RF_RELAY_Init();
7
  SSPI_Init();
8
  USART_Init();
9
  NRF24L01_Init();
10
  
11
  PWM_DDR |= (1<<PWM);  
12
13
  NRF_CE_Hi;
14
15
  while (1) 
16
    {
17
      if(!(NRF_IRQ_PIN & (1<<NRF_IRQ))){
18
19
    status_reg = NRF_ReadRegister(STATUS);
20
    USART_Send(status_reg);
21
22
    if((status_reg & RX_DR) == RX_DR)
23
    {
24
      _delay_ms(1000);
25
      NRF_WriteRegister(0xff, STATUS);
26
      USART_Send(0x01);
27
    }
28
    if((status_reg & TX_DS) == TX_DS)
29
    {
30
      _delay_ms(1000);
31
      NRF_WriteRegister(0xff, STATUS);
32
      USART_Send(0x02);
33
    }
34
    if((status_reg & MAX_RT) == MAX_RT)
35
    {
36
      _delay_ms(1000);
37
      NRF_WriteRegister(0xff, STATUS);
38
      USART_Send(0x04);
39
    }
40
    }
41
  /*  if(NRF_ReadRegister(CD) & 0x01)
42
    {
43
      USART_Send(0x01);
44
      NRF_WriteRegister(0x00, CD);
45
      }*/
46
  }
47
}
48
49
void RF_RELAY_Init(void)
50
{
51
  DIP_DDR &= ~(1<<DIP_0) | ~(1<<DIP_1) | ~(1<<DIP_2) | ~(1<<DIP_3) | ~(1<<DIP_4) | ~(1<<DIP_5) | ~(1<<DIP_6) | ~(1<<DIP_7);  // Set DIPSwitches as INPUT
52
  DIP_PORTS |= (1<<DIP_0) | (1<<DIP_1) | (1<<DIP_2) | (1<<DIP_3) | (1<<DIP_4) | (1<<DIP_5) | (1<<DIP_6) | (1<<DIP_7);      // Set PullupResistor
53
  
54
  PWM_DDR |= (1<<PWM);     // Sets PWM Port as OUTPUT
55
}

Mit dem CD wollte ich mal schaun was so in der Luft rumschwirrt aber 
komischerweise bombadiert mich mein uC erst, wenn ich von der anderen 
Seite was gesendet hab... und das dann dauerhaft!!

Der ganze rest ist wie oben schon reingestellt, nur dass ich beim 
empfaengerteil einen Atmega32 verwende.

Die ganzen Unterfunktionen, wie SoftSPI, Interruptpolling usw. hab ich 
schon getestet und es funktioniert!!

Warum bekomm ich nix??

mfg
Bastian

von Sebastian S. (sebastian_s25)


Lesenswert?

So Fehler gefunden!!

jetzt empfang ich was...

Erster Fehler:  TX-Buffer nur mit 32 Bytes beschreiben, da hab ich mich 
selber ausgetrixt... :(

2. Fehler:  RX-FIFO-Payloadwidth muss ich auf 32 Byte stellen, weil ich 
auch 32 Byte in den TX-FIFO reinschreib (die dynamische RX-Payload hab 
ich nicht zum laufen gebracht, is auch egal)
1
void NRF24L01_Init(void)
2
{
3
  NRF_CE_Lo;
4
5
  NRF_CE_DDR |= (1<<NRF_CE);
6
  
7
  NRF_IRQ_DDR &= ~(1<<NRF_IRQ);
8
  NRF_IRQ_PORT |= (1<<NRF_IRQ);
9
10
//  INT_SENS;
11
//  INT_EN;
12
13
  NRF_WriteRegister(0x0F, CONFIG);
14
  NRF_WriteRegister(0x01, EN_AA);
15
  NRF_WriteRegister(0x01, EN_RXADDR);
16
  NRF_WriteRegister(0x02, SETUP_AW);
17
  NRF_WriteRegister(0x04, SETUP_RETR);
18
  NRF_WriteRegister(0x04, RF_CH);
19
  NRF_WriteRegister(0x0E, RF_SETUP);
20
  NRF_WriteRegister(0x20, RX_PW_P0);      // Payload auf 32 Byte!!!
21
22
  NRF_CE_Lo;
23
24
}

Eigentlich ganz simple Fehler, hab dafuer aber 3,5 Std. gebraucht drauf 
zu kommen...

Und weil alles dann doch nicht so einfach geht, kommt nun das naechste 
Problem...

Wenn ich den RX-FIFO jetzt auslese, bekomm ich immer nur OxFF...

von Gerhard (Gast)


Lesenswert?

Hi,

was bekommst Du zurück, wenn Du einen Register-Dump machst?
Stimmt das mit dem überein, was Du auch reinschreibst?
Hatte sowas ähnliches auch mal, da lags an der Soft-SPI die nicht 
funktionierte.


Gruß
Gerhard

von Sebastian S. (sebastian_s25)


Lesenswert?

JAAAA!!

Fertig!! hier war der Fehler!!
1
struct uint256_t NRF_ReadRXPayload()
2
{  
3
  uint8_t u8i = 0x00;
4
5
  SCSN_Lo;
6
  uint8_t u8Reg = NRF_ReadRegister(CONFIG);
7
  SCSN_Hi;
8
9
  if((u8Reg & 0x01)) // ---> Fehler!!
10
  {  
11
    SCSN_Lo;
12
    SSPI_Write_byte(R_RX_PAYLOAD);
13
    for(u8i=32; u8i>0; u8i--)
14
    {
15
      Payloadconvert.c[u8i-1] = SSPI_Read_byte(0x00);
16
    }
17
    SCSN_Hi;
18
  }
19
  else
20
  {
21
    for(u8i=0; u8i<32; u8i++)
22
    {
23
      Payloadconvert.c[u8i] = 0xff;
24
    }
25
  }
26
  return Payloadconvert.u256i;
27
}

Die Abfrage war auf TX und nicht auf RX ausgelegt!!

Nun Funkts!!

mfg
Bastian

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.