nRF24L01 на низком уровне

GregoryAT
Offline
Зарегистрирован: 06.01.2015

Здравствуйте All!

Прошу помощи в следующем вопросе:

На форумах и сайтах описывающих работу с модулем nRF24L01 в основном описываются примеры с использованием готовых библиотек (для этого модуля).

Есть ли у кого примеры чтения и записи (значений) регистров через SPI в Ардуино?

 

Jeka_M
Jeka_M аватар
Offline
Зарегистрирован: 06.07.2014

Эм... Даташит смотрели? Страница 47.

GregoryAT
Offline
Зарегистрирован: 06.01.2015

Jeka_M пишет:

Эм... Даташит смотрели? Страница 47.

Смотрел...

Я не знаю как это реализовать программно..., поэтому попросил пример.

Псевдо выглядит следующим образом (мои догадки), например:

Прочитать 3-ий бит (EN_CRC) из регистра CONFIG

byte *Bit;// в эту переменную значение 3-го бита

SPI(R_REGISTER, 3 бит, &Bit);

 

jeka_tm
jeka_tm аватар
Offline
Зарегистрирован: 19.05.2013

не лучше ли сначала весь рабочий код из либы вытащить и дальше его править?

GregoryAT
Offline
Зарегистрирован: 06.01.2015

jeka_tm пишет:

не лучше ли сначала весь рабочий код из либы вытащить и дальше его править?

В дальнейшем возможно так и поступил бы, но сейчас мне необходимо попробовать руками (понять).

Можете пример кинуть?

Согласование модуля с Ардуино:

SS : Arduino Pin 10 -> Breakout Board CSN
MOSI : Arduino Pin 11 -> Breakout Board MOSI
MISO : Arduino Pin 12 -> Breakout Board MISO
SCK : Arduino Pin 13 -> Breakout Board SCK
CE : Arduino Pin 9 -> Breakout Board CE

kisoft пишет:

Вам и говорят, что лучший пример, код либы, либу кинуть?

1. А где по вашему мнению лучше описано, RF24 или Mirf?

2. Это первоначальная настройка SPI?

void RF24::csn(int mode)
{
  // Minimum ideal SPI bus speed is 2x data rate
  // If we assume 2Mbs data rate and 16Mhz clock, a
  // divider of 4 is the minimum we want.
  // CLK:BUS 8Mhz:2Mhz, 16Mhz:4Mhz, or 20Mhz:5Mhz
#ifdef ARDUINO
  SPI.setBitOrder(MSBFIRST);
  SPI.setDataMode(SPI_MODE0);
  SPI.setClockDivider(SPI_CLOCK_DIV4);
#endif
  digitalWrite(csn_pin,mode);
}

(из библиотеки RF24)

Не нашёл функцию (описание)

RF24 radio(9,10);

3. для чего она?

.................

4. Через какой порт ардуино происходит "связь" с модулем (чтение-запись в регистры), думаю что через 11 происходит чтение и запись в регистры (следуя вышеобозначенному согласованию модуля с ардуино)?

5. Скажите пожалуйста, правилен ли следующий (псевдо)код?:

void setup()

{
   Serial.begin(9600);

  SPI.setBitOrder(MSBFIRST);
  SPI.setDataMode(SPI_MODE0);
  SPI.setClockDivider(SPI_CLOCK_DIV16);

далее:

работа с радиомодулем...

}

 

 

kisoft
kisoft аватар
Offline
Зарегистрирован: 13.11.2012

Вам и говорят, что лучший пример, код либы, либу кинуть?

kisoft
kisoft аватар
Offline
Зарегистрирован: 13.11.2012

1. Я смотрел только RF24.
2-3. Это конструктор.
4. Смотреть код библиотеки.
5. Смотреть примеры из библиотеки.

GregoryAT
Offline
Зарегистрирован: 06.01.2015

kisoft пишет:
1. Я смотрел только RF24. 2-3. Это конструктор. 4. Смотреть код библиотеки. 5. Смотреть примеры из библиотеки.

Если:  MOSI - Master Output, Slave Input (выход ведущего,вход ведомого). Данный сигнал предназначен для последовательной передачи данных от ведущего к ведомому.,

то я должен использовать 11 (MOSI : Arduino Pin 11 -> Breakout Board MOSI), так?

5. В примере из библиотеки scanner, код начинается с:

// Set up nRF24L01 radio on SPI bus plus pins 9 & 10
RF24 radio(9,10);
эту функцию (описание) я в библиотеке не нашёл

Посмотрите пожалуйста следующий код:

#include <SPI.h>

/* Memory Map */
#define CONFIG      0x00
#define EN_AA       0x01
#define EN_RXADDR   0x02
#define SETUP_AW    0x03
#define SETUP_RETR  0x04
#define RF_CH       0x05
#define RF_SETUP    0x06
#define STATUS      0x07
#define OBSERVE_TX  0x08
#define CD          0x09
#define RX_ADDR_P0  0x0A
#define RX_ADDR_P1  0x0B
#define RX_ADDR_P2  0x0C
#define RX_ADDR_P3  0x0D
#define RX_ADDR_P4  0x0E
#define RX_ADDR_P5  0x0F
#define TX_ADDR     0x10
#define RX_PW_P0    0x11
#define RX_PW_P1    0x12
#define RX_PW_P2    0x13
#define RX_PW_P3    0x14
#define RX_PW_P4    0x15
#define RX_PW_P5    0x16
#define FIFO_STATUS 0x17
#define DYNPD       0x1C
#define FEATURE     0x1D

/* Bit Mnemonics */
#define MASK_RX_DR  6
#define MASK_TX_DS  5
#define MASK_MAX_RT 4
#define EN_CRC      3
#define CRCO        2
#define PWR_UP      1
#define PRIM_RX     0
#define ENAA_P5     5
#define ENAA_P4     4
#define ENAA_P3     3
#define ENAA_P2     2
#define ENAA_P1     1
#define ENAA_P0     0
#define ERX_P5      5
#define ERX_P4      4
#define ERX_P3      3
#define ERX_P2      2
#define ERX_P1      1
#define ERX_P0      0
#define AW          0
#define ARD         4
#define ARC         0
#define RF_DR_LOW   5
#define PLL_LOCK    4
#define RF_DR_HIGH  3
#define RF_PWR      1
#define LNA_HCURR   0        
#define RX_DR       6
#define TX_DS       5
#define MAX_RT      4
#define RX_P_NO     1
#define TX_FULL     0
#define PLOS_CNT    4
#define ARC_CNT     0
#define TX_REUSE    6
#define FIFO_FULL   5
#define TX_EMPTY    4
#define RX_FULL     1
#define RX_EMPTY    0
#define DPL_P5      5
#define DPL_P4      4
#define DPL_P3      3
#define DPL_P2      2
#define DPL_P1      1
#define DPL_P0      0
#define EN_DPL      2
#define EN_ACK_PAY  1
#define EN_DYN_ACK  0

/* Instruction Mnemonics */
#define R_REGISTER    0x00
#define W_REGISTER    0x20
#define REGISTER_MASK 0x1F
#define ACTIVATE      0x50
#define R_RX_PL_WID   0x60
#define R_RX_PAYLOAD  0x61
#define W_TX_PAYLOAD  0xA0
#define FLUSH_TX      0xE1
#define FLUSH_RX      0xE2
#define REUSE_TX_PL   0xE3
#define NOP           0xFF

/*
SS : Arduino Pin 10 -> Breakout Board CSN
MOSI : Arduino Pin 11 -> Breakout Board MOSI
MISO : Arduino Pin 12 -> Breakout Board MISO
SCK : Arduino Pin 13 -> Breakout Board SCK
CE : Arduino Pin 9 -> Breakout Board CE
*/
int cePin  = 9;
int csnPin = 10;
int channel = 1;
int payload = 16;

void ceHi()
{
digitalWrite(cePin,HIGH);
}

void ceLow()
{
 digitalWrite(cePin, LOW);
}

void csnHi()
{
 digitalWrite(csnPin,HIGH);
}

void csnLow()
{
 digitalWrite(csnPin,LOW);
}


void readRegister(uint8_t reg, uint8_t * value, uint8_t len)
{
    NRFSpiWrite((R_REGISTER | (REGISTER_MASK & reg)), value, true, len);
}


void writeRegister(uint8_t reg, uint8_t * value, uint8_t len) 
{
	NRFSpiWrite((W_REGISTER | (REGISTER_MASK & reg)), value, false, len);
}


void NRFSpiWrite(uint8_t reg, uint8_t *data, boolean readData, uint8_t len) 
{
	csnLow();
	SPI.transfer(reg);
	if (data) 
{
		uint8_t i;
		for(i = 0; i < len; ++i) 
{
			uint8_t readValue = SPI.transfer(data[i]);
			if (readData) 
{
				data[i] = readValue;
			}
		}
	}
	csnHi();
}

void NRF_SPI_Init() 
{   
        SPI.setBitOrder(MSBFIRST);
        SPI.setDataMode(SPI_MODE0);
        SPI.setClockDivider(SPI_CLOCK_DIV16);
	SPI.begin();

	pinMode(cePin, OUTPUT);
	pinMode(csnPin, OUTPUT);
	ceLow();
	csnHi();
}

void setup()
{
Serial.begin(57600);
NRF_SPI_Init();
}

void loop()
{
uint8_t rv = NOP;
readRegister(RF_CH, &rv, 1);
Serial.println(rv, BIN);
delay(2000);
}

Правилен ли он и достаточно ли его для чтения значений из регистров радиомодуля?

jeka_tm
jeka_tm аватар
Offline
Зарегистрирован: 19.05.2013

а нафига вообще все это? подцепить радиомодуль к какой нибудь тиньке? памяти не хватает?

GregoryAT
Offline
Зарегистрирован: 06.01.2015

>>памяти не хватает?

Да нет, просто хотел с нуля на низком уровне посмотреть как всё работает) не хотел не понимая как всё происходит пользоваться функциями обёртками из библиотек, так правилен код выше?

 

lenur
Offline
Зарегистрирован: 07.12.2013

Возможно, здесь то что вам нужно.    http://elecfreaks.com/store/download/datasheet/rf/rf24l01/SPI_rf24L01.zip

GregoryAT
Offline
Зарегистрирован: 06.01.2015

lenur пишет:

Возможно, здесь то что вам нужно.    http://elecfreaks.com/store/download/datasheet/rf/rf24l01/SPI_rf24L01.zip

Благодарю, именно это и было нужно!