Where did you find:
ot_api.h
and does anyone know how to do a monolithic build with po-util?
The ot_api.h header in the firmware repository, but you need to have checked out the mesh-develop branch, be building monolithic, and be targeting a mesh device.
I think doing the following before building should work:
export MODULAR=n
I just tried it with a xenon build and it works.
It does take a little bit longer to compile of course.
Is that just a command line statement before
po argon build
how to set it back to regular build?
Yes.
You can set it back to modular (non-monolithic builds) with:
export MODULAR=y
Hey @nrobinson2000 I am trying to get this really cool bit of code running on po-util using a monolithic build and the mesh-develop branch. I will keep trying but do you have any ideas?
#include "ot_api.h"
extern "C" {
int8_t otPlatRadioGetRssi(otInstance *aInstance);
};
… hold on, I think it is working
Instead of export
ing the MODULAR
variable, you can do it temporarily on a command-by-command basis by just setting it right before your normal build command, all in one statement:
MODULAR=n po argon build
This will let you do the monolithic build, without resetting your environment for future commands.
I just tried to monolithically build the following and it worked:
#include "Particle.h"
#include "ot_api.h"
extern "C" {
int8_t otPlatRadioGetRssi(otInstance *aInstance);
};
void setup() // Put setup code here to run once
{
}
void loop() // Put code here to loop forever
{
}
Going to make my own thread since we moved away from range testing.
I did as well. Now what to do with it? Looks like this is the 2nd part to get the RSSI
int8_t rssi = otPlatRadioGetRssi(0);
snprintf(buf, sizeof(buf), “>%d <%d”, (int)rssi, lastRssi);// where buf is an output string.
So this is working for me
#include "Particle.h"
// Easiest RSSI test program
// By Jeremy Ellis
#include "ot_api.h"
extern "C" {
int8_t otPlatRadioGetRssi(otInstance *aInstance);
};
void setup() {
}
void loop() {
int8_t rssi = otPlatRadioGetRssi(0);
//snprintf(buf, sizeof(buf), “>%d <%d”, (int)rssi, lastRssi);
Particle.publish("RSSI ", "#" + String(rssi), 60, PRIVATE); //shows printing an integer variable
Particle.publish("----------------","-------------", 60, PRIVATE); // just to show a space between samples
delay(10000); // wait about 10 seconds
}
Getting this published printout
This is on the Argon, Will now try flashing to a Xenon
Note: RSSI is a negative scale so -1 is a strong signal and -100 is a very weak signal
0 should be a very strong signal but I think I get a result of 0 when no other thread devices are connected.
I originally thought OTA was a really sstable flash. even in the school environment if it took about 15 minutes. I now have changed to flashing using DFU since the OTA does not give proof of success and just reverts to the old version of firmware if the OTA fails without giving you any idea if it worked or not.
A trick here is to change something in your publish statement even add a version to an output string so you can confirm if the upload was a success.
So I tried the program on the Xenon and nothing worked. So I put my Mesh Hello program back on the xenon and things worked again.
Probably because the program I was putting on the Xenon had no mesh.publish only a particle.publish
Anyway, things were kind of interesting. The strongest RSSI value I could get was -19 RSSI with both devices an inch apart. The first meter away from each other the RSSI values fell to about -60 and then they slowly fell more. The lowest reading I got was -93. I have not done any major range testing yet. Antennae testing that @rickkas7 was doing at Mesh range testing would be very interesting.
At one point, I reported that holding the devices vertically really increased the distance measurements. I am not seeing that confirmed with digital values at close range, but perhaps at longer ranges the orientation of the Mesh devices becomes important.
I’d advise recommending the method @dougal mentioned, so you can choose to build monolithically when building instead of exporting it.
## For a normal build
po argon build
## For a monolithic build
MODULAR=n po argon build
Hey @rickkas7 or @will What is the strongest RSSI value (where -1 is strong and -100 is weak) that a Xenon will be allowed to connect to an Argon? I am seeing some weird data, where my Xenon is flashing cyan or even green but still registering that the mesh.publish is communicating, almost as if the Mesh will not allow a proper connection between a Xenon and an Argon unless it has a good RSSI value lets say of about -75.
The experiment:
So if I walk with my Xenon far enough away from my Argon, I lose connectivity, but my program shows the RSSI values using a mesh.publish, so as I walk back to the Argon I prove that Mesh.publish is working but my Xenon will not reconnect to the Argon until I get quiet a bit closer.
Data:
The Code:
I changed the code around a bit but loaded similar versions on both the Argon and the Xenon.
#include "Particle.h"
// Particle Mesh Devices RSSI distance testing
// By Jeremy Ellis
// needs po-util
// po init argon myArgonProject
// cd myArgonProject
// po config mesh-develop
// po setup-mesh
// MODULAR=n po argon build
// particle login
// particle list
// po argon ota myArgonName
#include "ot_api.h"
extern "C" {
int8_t otPlatRadioGetRssi(otInstance *aInstance);
};
// Event listener for "mySendToAll" event from Xenons
void myHandler(const char *event, const char *data) {
delay(5); // sends the data so an RSSI value is registered
}
/////////////////////////// important globals here ///////////////////////////////
int myCode = 1; // Integer to identify this device
int myCutoffInterest = 18; // which positive version of RSSI should be fast flash. default 18
bool myXenonAntennaAttached = false;
bool myArgonBothAntennaAttached = false;
bool myPublishToConsole = true; // set true for Argon or debugging
/////////////////////////////// end globals ////////////////////////////
void setup() {
pinMode(D7, OUTPUT);
Mesh.subscribe("mySendToAll", myHandler);
if (myXenonAntennaAttached){
#if (PLATFORM_ID == PLATFORM_XENON)
digitalWrite(ANTSW1, 0);
digitalWrite(ANTSW2, 1);
#endif
}
if (myArgonBothAntennaAttached){
#if (PLATFORM_ID == PLATFORM_ARGON)
digitalWrite(ANTSW1, 1);
digitalWrite(ANTSW2, 0);
#endif
}
}
void loop() {
// here need to get the RSSI as myCode
int8_t rssi = otPlatRadioGetRssi(0); // activate on monolithic build
Mesh.publish("mySendToAll", String(rssi));
//int rssi = myCode; // for testing
int myNumber;
myNumber = ((int(rssi) * -1) * 100) - (myCutoffInterest * 100); // for testing, makes positive and larger
if (int(rssi) == 0) {
digitalWrite(D7, HIGH); // D7 permanently on, no connection
} else {
if (myNumber <= 50){
myNumber = 50; // very fast flashing
}
if (myNumber > 0){
digitalWrite(D7, HIGH);
delay(50); // very quick flash
digitalWrite(D7, LOW);
delay(myNumber);
} else {
Particle.publish("Weird "+ String(myNumber), ", #" + String(rssi) , 60, PRIVATE); //shows printing an integer variable
delay(2000);
}
}
if (myPublishToConsole){ // mainly for Argon gateway unless debugging
Particle.publish("delay #" + String(myNumber), "Device #"+String(myCode) + ", RSSI #" + String(rssi), 60, PRIVATE); //shows printing an integer variable
delay(2000); // wait about 2 seconds
}
}
This may sound like a silly question, but where exactly is ot_api.h
?
Good question, I thought it was on the OpenThread github but it is in the https://github.com/particle-iot/device-os/tree/mesh-develop github
Permanent link to ot_api.h here and the ot_api.cpp
Live link to the particle openthread mesh-develop folder https://github.com/particle-iot/device-os/tree/mesh-develop/hal/network/openthread
Lots of interesting stuff in that file and the accompanying .cpp file.
Hey @rickkas7 or @dougal you guys got any more example main.cpp monolithic builds I can look at?
I am a javascript programmer lost in C++
This defines a property:
#include "ot_api.h"
extern "C" {
int8_t otPlatRadioGetRssi(otInstance *aInstance);
};
which is then used by
int8_t rssi = otPlatRadioGetRssi(0);
I want to define lots of methods, as an easy example, how would I define and then use the following from cli.cpp
void Interpreter::ProcessFactoryReset(int argc, char *argv[])
I’m not really an expert (though I play one on TV – jk ). But searching around the OpenThread repo, it looks like that
ProcessFactoryReset
method just calls void otInstanceFactoryReset(otInstance *aInstance)
, which is defined in instance_api.cpp
.
I’m assuming that the instance_api.cpp
file is part of the build, so I’m guessing that just adding that function’s forward declaration to your extern "C"
block will let you use it? But I’m not really positive. Give it a try!