Hi,
Finally after 5 weeks I found how to make it work. My project is a anemometer, the way it's work the ULP count the pulse of the anemometer within 6 second store those value in a global non volatile ram who is accessible for the main CPU after one minute the ULP wake up the main processor who take the highest reading and connect to AP and send via UDP this value and immediately go back to deep sleep.
the way it work just download the library HULP from
https://github.com/boarchuz/HULP it's a bundle of macro, there is no really doc but there is a lot of example and the .h file are well documented, you can do many things but the ULP is very very limited in term of op-code. I join my code maybe it could help you.
Sylvain Bissonnette
// In datasheet 430a -> 3.57mph/hz -> 5.75kh/hz -> 0.575kmh/10hz
#include <WiFi.h>
#include <WiFiAP.h>
#include <WiFiClient.h>
#include <WiFiGeneric.h>
#include <WiFiMulti.h>
#include <WiFiScan.h>
#include <WiFiServer.h>
#include <WiFiSTA.h>
#include <WiFiType.h>
#include <WiFiUdp.h>
#include <dummy.h>
#include "esp_sleep.h"
#include "hulp.h"
//#include "hulp_macros.h"
#define DEBUG
#define BUTTON_PIN GPIO_NUM_4
#define LED_PIN GPIO_NUM_26
#define LED_PIN2 GPIO_NUM_27
#define ULP_INTERVAL_MS 10
#define NETWORK_PORT 4445
#define NETWORK_ABCD "192.168.225.255"
RTC_DATA_ATTR ulp_var_t PulseCounter;
RTC_DATA_ATTR ulp_var_t LoopCounter;
RTC_DATA_ATTR ulp_var_t SaveCnt;
RTC_DATA_ATTR ulp_var_t SaveValue0;
RTC_DATA_ATTR ulp_var_t SaveValue1;
RTC_DATA_ATTR ulp_var_t SaveValue2;
RTC_DATA_ATTR ulp_var_t SaveValue3;
RTC_DATA_ATTR ulp_var_t SaveValue4;
RTC_DATA_ATTR ulp_var_t SaveValue5;
RTC_DATA_ATTR ulp_var_t SaveValue6;
RTC_DATA_ATTR ulp_var_t SaveValue7;
RTC_DATA_ATTR ulp_var_t SaveValue8;
RTC_DATA_ATTR ulp_var_t SaveValue9;
RTC_DATA_ATTR ulp_var_t SaveValue10;
int MaxHz = 0;
float Kmh = 0;
unsigned long Elipse;
void setup()
{
if (hulp_is_ulp_wakeup())
{
#ifdef DEBUG
Serial.begin(115200);
#endif
Elipse = millis();
println("Woken up!\n");
int i;
for (i = 0; i < 10; i++)
{
if (i == 0) println("Save1: " + String(SaveValue1.val));
if (i == 1) println("Save2: " + String(SaveValue2.val));
if (i == 2) println("Save3: " + String(SaveValue3.val));
if (i == 3) println("Save4: " + String(SaveValue4.val));
if (i == 4) println("Save5: " + String(SaveValue5.val));
if (i == 5) println("Save6: " + String(SaveValue6.val));
if (i == 6) println("Save7: " + String(SaveValue7.val));
if (i == 7) println("Save8: " + String(SaveValue8.val));
if (i == 8) println("Save9: " + String(SaveValue9.val));
if (i == 9) println("Save10: " + String(SaveValue10.val));
}
MaxHz = 0;
if (MaxHz < SaveValue1.val) MaxHz = SaveValue1.val;
if (MaxHz < SaveValue2.val) MaxHz = SaveValue2.val;
if (MaxHz < SaveValue3.val) MaxHz = SaveValue3.val;
if (MaxHz < SaveValue4.val) MaxHz = SaveValue4.val;
if (MaxHz < SaveValue5.val) MaxHz = SaveValue5.val;
if (MaxHz < SaveValue6.val) MaxHz = SaveValue6.val;
if (MaxHz < SaveValue7.val) MaxHz = SaveValue7.val;
if (MaxHz < SaveValue8.val) MaxHz = SaveValue8.val;
if (MaxHz < SaveValue9.val) MaxHz = SaveValue9.val;
if (MaxHz < SaveValue10.val) MaxHz = SaveValue10.val;
println("Hz: " + String(MaxHz / 2 / 6)); // 2 pulse per revolution. Read each 6 seconds
Kmh = MaxHz / 2;
Kmh *= 0.958; // 5.75kh/hz div 6
println("Kmh: " + String(Kmh));
SendReport();
Serial.println("Up Time: " + String(millis() - Elipse));
println("Go To Sleep\n");
Serial.flush();
}
else
{
#ifdef DEBUG
Serial.begin(115200);
#endif
println("Start!\n");
Serial.flush();
init_ulp();
hulp_peripherals_on();
}
CLEAR_PERI_REG_MASK(RTC_CNTL_STATE0_REG, RTC_CNTL_SLEEP_EN);
SET_PERI_REG_MASK(RTC_CNTL_STATE0_REG, RTC_CNTL_SLEEP_EN);
esp_sleep_enable_ulp_wakeup();
esp_deep_sleep_start();
}
// Don't use loop
void loop()
{
}
void SendReport()
{
WiFiUDP Network;
String Str;
WiFi.disconnect(true);
WiFi.hostname("WIND_SPEED");
WiFi.mode(WIFI_AP_STA);
WiFi.setAutoReconnect(true);
WiFi.begin("xxxx", "xxxxx");
int i = 0;
while (WiFi.status() != WL_CONNECTED)
{
delay(500);
Serial.print(".");
if (i++ > 15) return;
}
println("");
println(PSTR("Connected to WiFi"));
println(PSTR("IP: ") + String(WiFi.localIP().toString()));
println(PSTR("MAC: ") + String(WiFi.macAddress()));
println(PSTR("RSSI: ") + String(WiFi.RSSI()));
Str = PSTR("<<<{&FROM=NEW_WIND}{SPEED=") + String(String(Kmh)) + PSTR("}>>>");
Network.beginPacket("192.168.1.255", NETWORK_PORT);
Network.print(Str.c_str());
Network.endPacket();
delay(250);
Serial.flush();
}
void println(String Str)
{
#ifdef DEBUG
Serial.println(Str);
#endif
}
void init_ulp()
{
enum {
LBL_INTERRUPT_TRIGGERED,
LBL_HALT,
LBL_SAVE,
LBL_SAVE_1,
LBL_SAVE_2,
LBL_SAVE_3,
LBL_SAVE_4,
LBL_SAVE_5,
LBL_SAVE_6,
LBL_SAVE_7,
LBL_SAVE_8,
LBL_SAVE_9,
LBL_SAVE_10,
};
const ulp_insn_t program[] = {
//Read the interrupt bit
I_GPIO_INT_RD(BUTTON_PIN),
//If it's set, goto LAB_INTERRUPT_TRIGGERED
M_BGE(LBL_INTERRUPT_TRIGGERED, 1),
//Pin not triggered
//Clear the interrupt bit
I_GPIO_INT_CLR(BUTTON_PIN),
//Turn off LED
I_GPIO_SET(LED_PIN, 0),
M_BX(LBL_HALT),
// if pin set
M_LABEL(LBL_INTERRUPT_TRIGGERED),
I_GPIO_SET(LED_PIN, 1),
M_DELAY_US_100_5000(1000),
I_GPIO_INT_CLR(BUTTON_PIN),
I_MOVI(R2, 0),
I_GET(R0, R2, PulseCounter),
I_ADDI(R0, R0, 1),
I_PUT(R0, R2, PulseCounter),
M_LABEL(LBL_HALT),
I_MOVI(R2, 0),
I_GET(R0, R2, LoopCounter),
I_ADDI(R0, R0, 1),
I_PUT(R0, R2, LoopCounter),
M_BGE(LBL_SAVE,600),
I_HALT(),
M_LABEL(LBL_SAVE),
I_MOVI(R2, 0),
I_MOVI(R0, 0),
I_PUT(R0, R2, LoopCounter),
I_GET(R0, R2, SaveCnt),
I_ADDI(R0, R0, 1),
I_PUT(R0, R2, SaveCnt),
M_BL(LBL_SAVE_1,2),
M_BL(LBL_SAVE_2,3),
M_BL(LBL_SAVE_3,4),
M_BL(LBL_SAVE_4,5),
M_BL(LBL_SAVE_5,6),
M_BL(LBL_SAVE_6,7),
M_BL(LBL_SAVE_7,8),
M_BL(LBL_SAVE_8,9),
M_BL(LBL_SAVE_9,10),
M_BL(LBL_SAVE_10,11),
I_HALT(),
M_LABEL(LBL_SAVE_1),
I_MOVI(R2, 0),
I_GET(R0, R2, PulseCounter),
I_PUT(R0, R2, SaveValue1),
I_GET(R0, R2, PulseCounter),
I_MOVI(R0, 0),
I_PUT(R0, R2, PulseCounter),
I_HALT(),
M_LABEL(LBL_SAVE_2),
I_MOVI(R2, 0),
I_GET(R0, R2, PulseCounter),
I_PUT(R0, R2, SaveValue2),
I_GET(R0, R2, PulseCounter),
I_MOVI(R0, 0),
I_PUT(R0, R2, PulseCounter),
I_HALT(),
M_LABEL(LBL_SAVE_3),
I_MOVI(R2, 0),
I_GET(R0, R2, PulseCounter),
I_PUT(R0, R2, SaveValue3),
I_GET(R0, R2, PulseCounter),
I_MOVI(R0, 0),
I_PUT(R0, R2, PulseCounter),
I_HALT(),
M_LABEL(LBL_SAVE_4),
I_MOVI(R2, 0),
I_GET(R0, R2, PulseCounter),
I_PUT(R0, R2, SaveValue4),
I_GET(R0, R2, PulseCounter),
I_MOVI(R0, 0),
I_PUT(R0, R2, PulseCounter),
I_HALT(),
M_LABEL(LBL_SAVE_5),
I_MOVI(R2, 0),
I_GET(R0, R2, PulseCounter),
I_PUT(R0, R2, SaveValue5),
I_GET(R0, R2, PulseCounter),
I_MOVI(R0, 0),
I_PUT(R0, R2, PulseCounter),
I_HALT(),
M_LABEL(LBL_SAVE_6),
I_MOVI(R2, 0),
I_GET(R0, R2, PulseCounter),
I_PUT(R0, R2, SaveValue6),
I_GET(R0, R2, PulseCounter),
I_MOVI(R0, 0),
I_PUT(R0, R2, PulseCounter),
I_HALT(),
M_LABEL(LBL_SAVE_7),
I_MOVI(R2, 0),
I_GET(R0, R2, PulseCounter),
I_PUT(R0, R2, SaveValue7),
I_GET(R0, R2, PulseCounter),
I_MOVI(R0, 0),
I_PUT(R0, R2, PulseCounter),
I_HALT(),
M_LABEL(LBL_SAVE_8),
I_MOVI(R2, 0),
I_GET(R0, R2, PulseCounter),
I_PUT(R0, R2, SaveValue8),
I_GET(R0, R2, PulseCounter),
I_MOVI(R0, 0),
I_PUT(R0, R2, PulseCounter),
I_HALT(),
M_LABEL(LBL_SAVE_9),
I_MOVI(R2, 0),
I_GET(R0, R2, PulseCounter),
I_PUT(R0, R2, SaveValue9),
I_GET(R0, R2, PulseCounter),
I_MOVI(R0, 0),
I_PUT(R0, R2, PulseCounter),
I_HALT(),
M_LABEL(LBL_SAVE_10),
I_MOVI(R2, 0),
I_GET(R0, R2, PulseCounter),
I_PUT(R0, R2, SaveValue10),
I_GET(R0, R2, PulseCounter),
I_MOVI(R0, 0),
I_PUT(R0, R2, PulseCounter),
I_GET(R0, R2, SaveCnt),
I_MOVI(R0, 0),
I_PUT(R0, R2, SaveCnt),
I_WAKE(),
I_HALT(),
};
ESP_ERROR_CHECK(hulp_configure_pin(BUTTON_PIN, RTC_GPIO_MODE_INPUT_ONLY, GPIO_PULLUP_ONLY, 0));
ESP_ERROR_CHECK(hulp_configure_pin(LED_PIN, RTC_GPIO_MODE_OUTPUT_ONLY, GPIO_FLOATING, 0));
ESP_ERROR_CHECK(hulp_configure_pin(LED_PIN2, RTC_GPIO_MODE_OUTPUT_ONLY, GPIO_FLOATING, 0));
ESP_ERROR_CHECK(hulp_configure_pin_int(BUTTON_PIN, GPIO_INTR_ANYEDGE));
ESP_ERROR_CHECK(hulp_ulp_load(program, sizeof(program), ULP_INTERVAL_MS * 1000, 0));
ESP_ERROR_CHECK(hulp_ulp_run(0));
}