Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Progressing with FreeRTOS? #1

Open
colesnicov opened this issue Mar 31, 2020 · 0 comments
Open

Progressing with FreeRTOS? #1

colesnicov opened this issue Mar 31, 2020 · 0 comments

Comments

@colesnicov
Copy link

colesnicov commented Mar 31, 2020

Hello. First of all I want to write, great work! Clean AVR works on first power up. But the problem arose when I wanted to use this library with FreeRTOS from https://github.com/feilipu/miniAVRfreeRTOS My sender code looks like this:

#include <stdlib.h>
#include <stdbool.h>
#include <string.h>

#include <avr/io.h>
#include <avr/interrupt.h>

/* Scheduler include files. */
#include "FreeRTOS.h"
#include "task.h"
#include "queue.h"
#include "semphr.h"
#include "timers.h"

extern "C" {
#include "nrf24l01-mnemonics.h"
#include "nrf24l01.h"
}

TimerHandle_t xAutoReloadTimer;

unsigned int uiAutoReloadTimerPeriod = pdMS_TO_TICKS(1000);

void taskTransmit(void *p);

void vAutoReloadTimerFunction(TimerHandle_t xTimer);

extern "C" int main(void) {

	xTaskCreate(taskTransmit, (const char*) "--", 256, NULL, 3, NULL); // */

	xAutoReloadTimer = xTimerCreate("AutoReloadTimer", uiAutoReloadTimerPeriod,
	pdTRUE, 0, vAutoReloadTimerFunction);

	xTimerReset(xAutoReloadTimer, 0);

	vTaskStartScheduler();

}

nRF24L01* setup_rf(void);

volatile bool rf_interrupt = false;
volatile bool send_message = false;

void taskTransmit(void *p) {
	uint8_t to_address[5] = { 0x01, 0x01, 0x01, 0x01, 0x01 };
	bool on = false;

	nRF24L01 *rf = setup_rf();

	while (true) {
		if (rf_interrupt) {
			rf_interrupt = false;
			int success = nRF24L01_transmit_success(rf);
			if (success != 0)
				nRF24L01_flush_transmit_message(rf);
		}

		if (send_message) {
			send_message = false;
			on = !on;
			nRF24L01Message msg;
			if (on)
				memcpy(msg.data, "ON", 3);
			else
				memcpy(msg.data, "OFF", 4);
			msg.length = strlen((char*) msg.data) + 1;
			nRF24L01_transmit(rf, to_address, &msg);
		}
		portYIELD();
	}

}

nRF24L01* setup_rf(void) {
	nRF24L01 *rf = nRF24L01_init();
	rf->ss.port = &PORTB;
	rf->ss.pin = PB2;
	rf->ce.port = &PORTB;
	rf->ce.pin = PB1;
	rf->sck.port = &PORTB;
	rf->sck.pin = PB5;
	rf->mosi.port = &PORTB;
	rf->mosi.pin = PB3;
	rf->miso.port = &PORTB;
	rf->miso.pin = PB4;
	// interrupt on falling edge of INT0 (PD2)
	EICRA |= _BV(ISC01);
	EIMSK |= _BV(INT0);
	nRF24L01_begin(rf);
	return rf;
}

ISR(INT0_vect) {
	rf_interrupt = true;
}

void vAutoReloadTimerFunction(TimerHandle_t xTimer) {
	send_message = true;
	uiAutoReloadTimerPeriod += pdMS_TO_TICKS(1000);
	xTimerChangePeriod(xTimer, uiAutoReloadTimerPeriod, 0);
}


I used FreeRTOS program timer instead of TIMER1. I have modified the receiver code from your example in a similar way:

#include <stdlib.h>
#include <stdbool.h>
#include <string.h>

#include <avr/io.h>
#include <avr/interrupt.h>
#include <util/delay.h>

/* Scheduler include files. */
#include "FreeRTOS.h"
#include "task.h"
#include "queue.h"
#include "semphr.h"

extern "C" {
#include <nrf24l01-mnemonics.h>
#include "nrf24l01.h"
}

nRF24L01* setup_rf(void);
void process_message(char *message);
inline void prepare_led_pin(void);
inline void set_led_high(void);
inline void set_led_low(void);

volatile bool rf_interrupt = false;

void taskR(void *v) {
	uint8_t address[5] = { 0x01, 0x01, 0x01, 0x01, 0x01 };
	prepare_led_pin();
	sei();
	nRF24L01 *rf = setup_rf();
	nRF24L01_listen(rf, 0, address);
	uint8_t addr[5];
	nRF24L01_read_register(rf, CONFIG, addr, 1);

	while (true) {
		if (rf_interrupt) {
			rf_interrupt = false;
			while (nRF24L01_data_received(rf)) {
				nRF24L01Message msg;
				nRF24L01_read_received_data(rf, &msg);
				process_message((char*) msg.data);
			}

			nRF24L01_listen(rf, 0, address);
		}
	}

}

nRF24L01* setup_rf(void) {
	nRF24L01 *rf = nRF24L01_init();
	rf->ss.port = &PORTB;
	rf->ss.pin = PB2;
	rf->ce.port = &PORTB;
	rf->ce.pin = PB1;
	rf->sck.port = &PORTB;
	rf->sck.pin = PB5;
	rf->mosi.port = &PORTB;
	rf->mosi.pin = PB3;
	rf->miso.port = &PORTB;
	rf->miso.pin = PB4;
	// interrupt on falling edge of INT0 (PD2)
	EICRA |= _BV(ISC01);
	EIMSK |= _BV(INT0);
	nRF24L01_begin(rf);
	return rf;
}

void process_message(char *message) {
	if (strcmp(message, "ON") == 0)
		set_led_high();
	else if (strcmp(message, "OFF") == 0)
		set_led_low();
}

inline void prepare_led_pin(void) {
	DDRB |= _BV(PB0);
	PORTB &= ~_BV(PB0);
}

inline void set_led_high(void) {
	PORTB |= _BV(PB0);
}

inline void set_led_low(void) {
	PORTB &= ~_BV(PB0);
}

// nRF24L01 interrupt
ISR(INT0_vect) {
	rf_interrupt = true;
}

extern "C" int main(void) {

	xTaskCreate(taskR, (const char*) "--", 256, NULL, 3, NULL);

	vTaskStartScheduler();

}

Unfortunately, it doesn't work for me. I'm not so good at programming to fix it. Can't you give me some advice? Thank you for any advice. Regards...

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

1 participant