armmbed / mbed-hal-nrf51822-mcu Goto Github PK
View Code? Open in Web Editor NEWmbed HAL port for nRF51822
mbed HAL port for nRF51822
I'd like to use the mbed OS stack on various custom targets (different devices all using a nrf51822 module). Therefor the mbed-hal-nrf51-generic
target might fit my needs (at least the name does indicate that) as e.g. the mbed-hal-nrf51dk
specifies pins which only exists on the dk hardware. But unfortunately the mbed-hal-nrf51-generic
is not published ๐.
In the end, I'd like to name my hardware specific pins in the target used by yotta target
.
Hi,
I have a very hard to track down (but fortunately repeatable!) crash when I'm using Minar with TimerEvent
.
All I do is usedTimerEvent::insert(0x20000000)
, and then toggle an LED using Minar with a 1 second period. After 24 toggles (this is reliable, and depends in a confusing way on the insert()
value), the program crashes in some way.
Unfortunately I haven't got gdb working yet (because it is virtually impossible), so I've been tediously debugging it with LEDs and narrowed the problem down to minar::SchedulerData::start()
. At the crash it gets to the destructor of the CriticalSectionLock
on line 323 and never returns. I assume this is because while it was in the critical section the RTC1 IRQ is trigger, because while it is crashed RTC1_IRQHandler()
is called with NRF_RTC1->EVENTS_COMPARE[0]
and us_ticker_callbackPending
set but ((int)(us_ticker_callbackTimestamp - rtc1_getCounter()) <= 0))
is not set. This means EVTENCLR
is never set and RTC1_IRQHandler()
just gets called in an infinite loop.
Does anyone know why exactly this is happening and what the fix is? I've spent all day hunting this down...
Here is my code. Note that I am using the RC oscillator since my module doesn't have a 32 kHz crystal.
#include <mbed-drivers/mbed.h>
#include "NordicDigitalInOut.h"
#include <ble/BLE.h>
// This is just a class I wrote to do high-drive on the nRF51. You can probably just use a normal DigitalOut.
NordicDigitalOut led1(p24, Drive_Standard_High, 0);
class ExtendedClock : public TimerEvent
{
public:
ExtendedClock()
{
}
void go()
{
insert(0x20000000);
}
private:
void handler() override
{
}
};
static ExtendedClock _GlobalClock;
void flash()
{
led1 = !led1;
}
void app_start(int argc, char* argv[])
{
(void)argc; (void)argv;
_GlobalClock.go();
minar::Scheduler::postCallback(flash).period(minar::milliseconds(1000));
}
The file should include the P0_0 - P0_30 names as well, since these are chip specific and common to all targets derived from it.
https://github.com/ARMmbed/mbed-hal-nrf51822-mcu/blob/master/mbed-hal/chip_pins.array#L1-L31
Can anyone explain the reasons why the RTC of the nrf51822 is not usable with mbed? I read some comments within us_ticker.c that show that the RTC1 is in use for regular ticker and scheduling due to power consumption (Low frequency timers compared to High frequency ones).
But I haven't found that RTC0 is already in use by one of the library implementations! Is it therefore possible to use this for the rtc_api.c implementation?
BR Daniel
This seems to be the last dep missing from yotta for ble-examples to build publicly. Is there anything holding up its publishing?
If I have this simple program:
void app_start(int argc, char *argv[])
{
}
Then when it runs it draws about 4 mA. However if I hack it like this:
void app_start(int argc, char *argv[])
{
for (;;)
__WFE();
}
Then the current draw goes way down to about 4 uA, which is what I'd expect.
I'm not using the softdevice (though it is merged into my hex), and this is with an nRF51822 without a 32 kHz crystal. I had a skim through the minar code but couldn't see anything obvious.
This commit breaks code:
Patch versions are for patches, minor versions are for backwards compatible features. This change is API breaking and requires a major version bump.
Should the bootloader instructions be here? or elsewhere?
I use yotta
to build the helloyotta
project. I get the following error:
CMake Error at D:/git/helloyotta/yotta_modules/mbed-hal-nrf51822-mcu/CMakeLists.txt:94 (message):
Missing PLATFORM_SPECIFIC_HAL_LIB
I have no experience with yotta. I set the target to nordic-nrf51822-32k-gcc
and then I built the project. My issue seam to be rated to PR #14. How can I solve this error ?
Here is the full error stack:
(workspace) D:\git\helloyotta>yt build
info: get versions for nordic-nrf51822-32k-gcc
info: download [email protected] from the public module registry
info: get versions for mbed-gcc
info: download [email protected] from the public module registry
info: get versions for simplelog
info: download [email protected] from the public module registry
info: get versions for mbed-drivers
info: download [email protected] from the public module registry
info: get versions for mbed-hal
info: download [email protected] from the public module registry
info: get versions for cmsis-core
info: download [email protected] from the public module registry
info: get versions for ualloc
info: download [email protected] from the public module registry
info: get versions for minar
info: download [email protected] from the public module registry
info: get versions for core-util
info: download [email protected] from the public module registry
info: get versions for compiler-polyfill
info: download [email protected] from the public module registry
info: get versions for mbed-hal-nordic
info: download [email protected] from the public module registry
info: get versions for mbed-hal-nrf51822-mcu
info: download [email protected] from the public module registry
info: get versions for ble-nrf51822
info: download [email protected] from the public module registry
info: get versions for cmsis-core-nordic
info: download [email protected] from the public module registry
info: get versions for cmsis-core-nrf51822
info: download [email protected] from the public module registry
info: get versions for ble
info: download [email protected] from the public module registry
info: get versions for dlmalloc
info: download [email protected] from the public module registry
info: get versions for minar-platform
info: download [email protected] from the public module registry
info: get versions for minar-platform-mbed
info: download [email protected] from the public module registry
info: generate for target: nordic-nrf51822-32k-gcc 0.1.3 at D:\git\helloyotta\yotta_targets\nordic-nrf51822-32k-gcc
GCC version is: 4.9.3
suppressing warnings from ble-nrf51822
-- The ASM compiler identification is GNU
-- Found assembler: D:/ARMEBS4/2015-06-26/tools/gcc/bin/arm-none-eabi-gcc.exe
CMake Error at D:/git/helloyotta/yotta_modules/mbed-hal-nrf51822-mcu/CMakeLists.txt:94 (message):
Missing PLATFORM_SPECIFIC_HAL_LIB
-- Configuring incomplete, errors occurred!
See also "D:/git/helloyotta/build/nordic-nrf51822-32k-gcc/CMakeFiles/CMakeOutput.log".
error: command ['cmake', '-D', 'CMAKE_BUILD_TYPE=RelWithDebInfo', '-G', 'Ninja', '.'] failed
I'm having trouble getting serial output to work using yotta
and mBed OS. Previously it worked. I'm using the nRF51-DK. Here are the steps I'm taking:
Install Yotta
mkdir Deleteme
cd Deleteme
yt init
(Default answers except 'yes' to executable)
yt target nrf51dk-gcc
yt install ble
Edit source/main.cpp
#include <mbed-drivers/mbed.h>
Serial pc(USBTX, USBRX);
DigitalOut led1(LED1);
void app_start(int, char**)
{
for (;;)
{
pc.puts("Hello World\n");
led1 = !led1;
wait_ms(200);
}
}
yt build
Flash & reset:
"C:\Program Files (x86)\Nordic Semiconductor\nrf5x\bin\nrfjprog.exe" --family NRF51 --chiperase --program "build\nrf51dk-gcc\source\deleteme-combined.hex"
"C:\Program Files (x86)\Nordic Semiconductor\nrf5x\bin\nrfjprog.exe" --family NRF51 --reset
After doing that I connect to it at 9600 baud and sadly don't receive any text. Maybe I am doing something wrong, but this should work, right? The LED flashes so I'm pretty the code is running.
Is this module https://github.com/ARMmbed/ble-nrf51822 really needed for this module? This mbed hal does not need ble implementation, therefore latest changes in BLE should not affect this module, should it?
What is needed in this module from ble-nrf51822 ?
As posted already here: ARMmbed/mbed-hal#79
There is a strange dependency issue, and also there is a fix that can be used. Maybe this should be included to the next release.
BR Daniel
The code in us_ticker.c
is really complicated and has a history of unobvious bugs that don't manifest themselves for hours or even years.
It also has no tests. That is ridiculous. The important functions (especially us_ticker_set_interrupt()
) should be refactored out into functions that are easier to test, and then tests should be written.
If I have a PwmOut
object and set it to output to 0, I'd expect it to turn off the PWM system. Otherwise there is no way to wake up, output some PWM, then go to sleep again.
Actually however it seems there is no code at all to turn off PWM. Once you use it once, you are committed, and it draws about 1 mA which makes it useless for battery operated devices.
If you look in serial_api.c
you can see that the nRF51822 code only allows a finite set of baud rates:
static const int acceptedSpeeds[17][2] = {
{1200, UART_BAUDRATE_BAUDRATE_Baud1200},
{2400, UART_BAUDRATE_BAUDRATE_Baud2400},
{4800, UART_BAUDRATE_BAUDRATE_Baud4800},
{9600, UART_BAUDRATE_BAUDRATE_Baud9600},
{14400, UART_BAUDRATE_BAUDRATE_Baud14400},
{19200, UART_BAUDRATE_BAUDRATE_Baud19200},
{28800, UART_BAUDRATE_BAUDRATE_Baud28800},
{31250, (0x00800000UL) /* 31250 baud */},
{38400, UART_BAUDRATE_BAUDRATE_Baud38400},
{57600, UART_BAUDRATE_BAUDRATE_Baud57600},
{76800, UART_BAUDRATE_BAUDRATE_Baud76800},
{115200, UART_BAUDRATE_BAUDRATE_Baud115200},
{230400, UART_BAUDRATE_BAUDRATE_Baud230400},
{250000, UART_BAUDRATE_BAUDRATE_Baud250000},
{460800, UART_BAUDRATE_BAUDRATE_Baud460800},
{921600, UART_BAUDRATE_BAUDRATE_Baud921600},
{1000000, UART_BAUDRATE_BAUDRATE_Baud1M}
};
In fact the baud rate can be set to anything. Instead of using fixed constants, a formula should be used instead.
Old code:
// serial_baud
// set the baud rate, taking in to account the current SystemFrequency
void serial_baud(serial_t *obj, int baudrate)
{
if (baudrate<=1200) {
obj->uart->BAUDRATE = UART_BAUDRATE_BAUDRATE_Baud1200;
return;
}
for (int i = 1; i<17; i++) {
if (baudrate<acceptedSpeeds[i][0]) {
obj->uart->BAUDRATE = acceptedSpeeds[i - 1][1];
return;
}
}
obj->uart->BAUDRATE = UART_BAUDRATE_BAUDRATE_Baud1M;
}
Better code:
// serial_baud
// set the baud rate, taking in to account the current SystemFrequency
void serial_baud(serial_t *obj, int baudrate)
{
// See https://devzone.nordicsemi.com/question/1181/uart-baudrate-register-values/#reply-1194
// The correct value is baudrate * 2^32 / 16e6 = baudrate * 2^22 / 15625,
// but that doesn't fit into 32 bits, and Cortex M0 has no hardware
// divide, so instead I will do this possibly-over-optimised magic instead!
// I have verified that this produces exactly the same values as the header,
// except for 921600 (which is wrong in the header).
uint32_t br = (baudrate << 8) + (baudrate << 4) - (baudrate << 1) - baudrate
- (baudrate >> 1) - (baudrate >> 4) - (baudrate >> 9) - (baudrate >> 14)
- (baudrate >> 16) - (baudrate >> 17) - (baudrate >> 18) - (baudrate >> 19);
// Round it to 20 bits (see link above).
br = (br + 0x800) & 0xFFFFF000;
// Limit it to the valid range.
if (br < 0x1000)
br = 0x1000;
if (br > 0x10000000)
br = 0x10000000;
obj->uart->BAUDRATE = br;
}
I'll do a pull request for this.
Using my target, but Ive confirmed this on the mkit-gcc target as well.
PERIOD is defined as a uint16_t even though NRF_TIMER_Type.CC is defined as a uint32_t
PERIOD thus maxes out at 65535 or 0.26214f which seems short as the PWMOUT example sets a 4.0f, or 4 second period
I think theres more broken than that though, because even if I
An LED still blinks way to fast. So I think theres more issues in here than Ive currently found.
We have never received any communication from Nordic regarding our ability to re-distribute the softdevice .hex file. We're assuming that this permission will be granted; and at that time we'll need to add an appropriate clarification to our LICENSES.
A declarative, efficient, and flexible JavaScript library for building user interfaces.
๐ Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.
TypeScript is a superset of JavaScript that compiles to clean JavaScript output.
An Open Source Machine Learning Framework for Everyone
The Web framework for perfectionists with deadlines.
A PHP framework for web artisans
Bring data to life with SVG, Canvas and HTML. ๐๐๐
JavaScript (JS) is a lightweight interpreted programming language with first-class functions.
Some thing interesting about web. New door for the world.
A server is a program made to process requests and deliver data to clients.
Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.
Some thing interesting about visualization, use data art
Some thing interesting about game, make everyone happy.
We are working to build community through open source technology. NB: members must have two-factor auth.
Open source projects and samples from Microsoft.
Google โค๏ธ Open Source for everyone.
Alibaba Open Source for everyone
Data-Driven Documents codes.
China tencent open source team.