OK

Při poskytování služeb nám pomáhají soubory cookie. Používáním našich služeb vyjadřujete souhlas s naším používáním souborů cookie. Více informací

Úvodní stránka » IoT - Internet of Things » Konstrukce reálného čidla SIGFOX s WISOL Arduino I.

Konstrukce reálného čidla SIGFOX s WISOL Arduino I.

Na základě četných dotazů čtenářů budu tento článek věnovat konstrukci reálného čidla na bázi modulku SIGFOX WISOL Arduino, který je produktem našeho projektu Arduinotech.cz a který byl popsán v minulém článku. Co vlastně po reálné konstrukci požadujeme? Čidlo musí splnit následující požadavky, abychom jej mohli prohlásit za low power IoT zařízení:

  • Nežrat! Lidově řečeno - tedy musíme jej škrtit na co nejnižší spotřebě
  • Spát! Tím snadněji dosáhneme výše uvedeného bodu - dle možností HW musíme čidlo probudit jen na nejnutnější dobu a tou je zjištění sledovaného stavu a sdělení této skutečnosti dále - tedy komunikace
  • Úsporně komunikovat! Tento bod je zajištěn samotnou modulací, kterou používá Sigfox - energeticky jsme na zlomku toho, co bychom potřebovali třeba u GSM

Příprava HW

Bohužel, Arduino jako takové je konstruováno na poněkud archaickém čipu ATmega328p, nicméně mou snahou bylo zpřístupnit low power IoT velké skupině bastlířů, kteří prostě s Arduinem kamrádi, vyrostli na něm a neumí si bez něj představit svůj projekt. Pokud si Arduino patřičně upravíme (na dodávaných modulcích je již úprava provedena), pak low power režim bude celkem překvapením. Zde si dovolím jednu poznámku - různí pisálkové glorifikující zahraniční produkty v kombinaci Sigfox - Arduino si jaksi neuvědomují, že tak, jak jsou koncipovány, tedy klasické Arduino UNO a k tomu patřičný shield se Sigfox transceiverem v podstatě niky nemůže být základem konstrukce reálného čidla, protože prostě Arduino UNO je z pohledu low power ohromný žrout. Navíc je zde problém s taktováním - přetaktovaný procesor se prostě u -5°C zastaví. Takže Vy z Vás, kteří chcete smysluplně využít zakoupený HW, přemýšlejte o trochu více, než o reklamních výkřicích rádoby odborníku na low power IoT. 

Máme tedy HW postavený na Arduino Pro Mini - je na něm velmi málo zbytečností, ale přece jen se nějaké najdou a těch se musíme zbavit:

  • LEDka indikující přítomnost napájení - tohle je největší problém z pohledu low power, netřeba rozebírat věci kolem něčeho, co trvale svítí, nezbývá, než ji odstranit
  • LEDka na pinu 13 - úmyslně jsem na tento pin přivedl signál budící transceiver, ve sketchi jej pak v low power překonfiguruji na vstup, teče tam velmi malý proud, pokud ledku necháme připojenou, takže odstranit
  • Stabilizátor 5V/3.3V - pracujeme v doméně 3.3V, tento stabilizátor je zbytečný a jeho odstaraněním ušetříme ve spánku cenných 65uA!

Obrázek níže ukazuje ony problematické partie, které jsou předmětem výše uvedených úprav. V oblasti 1 je stabilizátor a ledka napájení, v oblasti 2 pak ledka portu 13.

Reálné testy, které jsem na takto upraveném HW provedl - tedy i s osazeným WISOL transceiverem mi ukázaly nádherných 4,6uA spotřebu ve spánku. Tohle se již velmi blíží čidlům, s "profi" konstrukcí na jiných čipech a dosažená spotřeba se dá s klidným svědomím označit za low power.

Časování a knihovna LowPower

Jak jsem již párkrát zmínil, ATmega328p je archaický čip, který neobsahuje spoustu věcí, z pohledu low power je asi největší nedostatek absence RTC hodin, které by dovedly v hlubokém spánku pracovat s velmi nízkou spotřebou a po nastaveném čase procesor probudit. Nevadí, poradíme si i bez nich, nebudeme hrát na nějakou extra přesnost v časování a zaplatíme menší daď ve formě mírně zvýšené prměrné spotřeby. Naštěstí nemusíme zabíhat do úrovně registrů ATmega328p a vysvětlovat si, jak je co třeba nastavit, abychom donutili Arduino spát a nežrat - tedy splnit 2 ze 3 nutných podmínek, uvedených v úvodu článku. Odpovědí je velmi povedená knihovna LowPower, kterou si stáhněte zde. Je k dispozici několik examplů, nás bude zajímat tento:

#include "LowPower.h"

void setup()
{
// No setup is required for this library
}

void loop()
{
              // Enter power down state for 8 s with ADC and BOD module disabled
              LowPower.powerDown(SLEEP_8S, ADC_OFF, BOD_OFF);

              // Do something here
              // Example: Read sensor, data logging, data transmission.
}

Pro periodické buzení je využíván restart watchdogu v intervalu 8s a prakticky to znamená, že se během 1 dne čidlo probudí 10 800 krát. Ano, to je hodně, nicméně podívejme se na to trochu z jiného úhlu. Po probuzení pouze inkrementujeme čítač a mrkneme, zda je čas vstávat a něco dělat, pak už se jde zase rychle spát. Takže v konečném důsledku jsme vzhůru jen odhadem 20us. To po přepočtu odpovídá času 2,16s, kdy budeme každý den vzhůru jen kvůli zajištění periodické činnosti čidla, což na spotřebu mít bude, ale jen velmi zanedbatelný. Průměrná spotřeba ve spánku se nám bude pohybovat pod 15uA a to je již velmi použitelné.

Testovací sketch

#include <LowPower.h>
#include <NeoSWSerial.h>

#define PERIODE 10
NeoSWSerial WISOL(4,5);
char c;
unsigned int timer = 0x00;
unsigned int periodeCounter = 0x00;
unsigned int uplinkCounter = 0x00;
String response;

void printStars()
{
	Serial.println F("**********************************");
}
void checkResponse()
{
	response = "";
	while(WISOL.available()==0);
	while(WISOL.available()>0)
	{
		delay(5);
		c = WISOL.read();
		response = response + c;
	}
	response = response.substring(0,(response.length()-2));
}
void checkTRX()
{
	response = "";
	c=0x00;
	while(WISOL.available()>0)
	{
		WISOL.read();
		delay(5);
	}
	while(response.substring(0,2) !="OK")
	{
		WISOL.println("AT");
		delay(5);
		response = "";
		while(WISOL.available()>0)
		{
			delay(5);
			c = WISOL.read();
			response = response + c;
		}
		//Serial.println("WISOL response:");
		//Serial.print(response);
	}
}
void getID()
{
	printStars();
	WISOL.println("AT$I=10");
	delay(5);
	response = "";
	while(WISOL.available()>0)
	{
		delay(5);
		c = WISOL.read();
		response = response + c;
	}
	Serial.print("ID:" + response);
	WISOL.println("AT$I=11");
	delay(5);
	response = "";
	while(WISOL.available()>0)
	{
		delay(5);
		c = WISOL.read();
		response = response + c;
	}
	Serial.print("PAC:" + response);
	printStars();
}
void getVersion()
{
	WISOL.println("AT$I=0");
	delay(5);
	response = "";
	while(WISOL.available()>0)
	{
		delay(5);
		c = WISOL.read();
		response = response + c;
	}
	Serial.print("TRX version:" + response);
}
void send(String payload)
{
	Serial.println("Sending payload ...");
	WISOL.print("AT$SF=");
	WISOL.println(payload);
	delay(1000);
	//poškej na OK
	checkResponse();
	if (response == "OK") Serial.println("Payload sent!");
	else Serial.println("Sending Error!");
	return;
}
bool parseCommand(String resp)
{
	if (resp == "sendTest")
	{
		Serial.println("Test message sending...");
		send("ABBA1234");
		return 1;
	}
	if (resp.substring(0,5) == "send:")
	{
		resp = resp.substring(5,resp.length());
		Serial.println("Payload:" + resp);
		send(resp);
		return 1;
	}
	Serial.println F("Unknown command");
	return 0;
}
void transceiverWakeUp()
{
	digitalWrite(13,HIGH);
	delay(100);
	digitalWrite(13,LOW);
	checkTRX();
	Serial.println("TRX ready!");
}

void setup()
{
  Serial.begin(9600);
  WISOL.begin(9600);
  pinMode(13,OUTPUT);
  pinMode(6,OUTPUT);
  printStars();
  Serial.println F("********SIGFOX WISOL Frame********");
  digitalWrite(13,HIGH);
  delay(100);
  digitalWrite(13,LOW);
  checkTRX();
  Serial.println("WISOL detected!");
  getVersion();
  getID();
  response = "";
  timer = (PERIODE * 60)/8;	
  //prvotní odeslání payloadu po zapnutí
  periodeCounter = timer + 1;
}

void loop()
{
	Serial.println F("*********Periodic mode************");
	delay(100);
	while(periodeCounter < timer)
	{
		LowPower.powerDown(SLEEP_8S, ADC_OFF, BOD_OFF); 
		periodeCounter++;
	}
	periodeCounter = 0x00;
	pinMode(5,OUTPUT);
	pinMode(13,OUTPUT);
	//probuď transceiver
	transceiverWakeUp();
	send("0101");
	uplinkCounter++;
	Serial.println("Uplink counter:" + String(uplinkCounter));
	//uspi transceiver;
	WISOL.println("AT$P=2");
	delay(10);
	pinMode(5,INPUT);
	pinMode(13,INPUT);
	Serial.println("Sleeping...");
}

Tento sketch vychází ze sketche z minulého článku, kde se nám podařilo zakomunikovat s transceiverem WISOL, nyní jsem tedy doplnil v hlavní smyčce výše popsanou "startegii" pro low power a nechávám čidlo chrlit do éteru každých 10 minut - to je konstanta PERIODE v definici nahoře. Ve smyčce while pak hlídám dosažení času a sketch zde v podstatě brzdím, pokud je čas menší, než nastavená perioda. Jakmile je času dosaženo, provedou se činnosti dále. Probudí se transceiver a dojde k odeslání dat do Sigfox backendu. V tomto příkladu se jedná o pevná data 0101. Pokud vše funguje jak má, na výpisu z terinálu uvidíte toto:

**********************************
********SIGFOX WISOL Frame********
WISOL detected!
TRX version:AX-Sigfox 1.1.0-ETSI
**********************************
ID:001A0BD2
PAC:E2E0219E172E0C4F
**********************************
*********Periodic mode************
TRX ready!
Sending payload ...
Payload sent!
Uplink counter:1
Sleeping...
*********Periodic mode************

... a po 10 minutách se děj opakuje:

TRX ready!
Sending payload ...
Payload sent!
Uplink counter:2
Sleeping...
*********Periodic mode************

Vemte pak do ruky měřák, přepněte jej na mA, vložte do větve napájení a připojte modulek. Uvidíte toto:

  • Modulek je probuzený někde kolem 9 až 11mA (vliv spotřeby Arduina + neuspaného transceiveru)
  • Zahájí prvotní vysílání - uvidíte 3 po sobě jdoucí proudové špičky kolem 50mA zhruba v sekundovém intervalu
  • Modulek přejde do režimu spánku - uvidíte spotřebu někde kolem 4,6uA
  • Modulek se probírá co 8s od restartu watchdogu - "ručička" (uvozovky proto, protože na digitální měřáku již něco podobného žel není a bargraf je pomalý) se teoreticky nachýlí někam k 4mA, ale prakticky to uvidíte jako zákmit někde k 10uA.

Díky úpravám HW a použité metodice jsme se dopracovali k základu reálného čidla, které na jednu lithiovou baterii 3.6V/2600mAh vydrží v provozu mnoho let - platí pro nějakou rozumnou periodu vysílání - cca 24 zpráv denně.

V následujícím článku si pak ukážeme, jak poslat něco smysluplného, třeba data z DS18B20. Využijeme přesně výše uvedený sketch, jen jej doplníme o měření a z dat DS18B20 vyrobíme data pro backend.

PF
petr.foltyn@arduinotech.cz

Přidat komentář

Zvýrazněné položky jsou povinné.

Přehled komentářů

  1. Sketch s DS18B20 (admin, 8.6.2017 13:47:32) Odpovědět

    Máte to tam, lidi!

    PF

  2. WISOL Pro Mini (PavelDC, 7.6.2017 16:06:00) Odpovědět

    Zdravím. Jasný, při tak hezkém počasí se nikomu nechce sedět u PC, ale stejně - kdy se můžeme těšit na pokračování? :)

  3. Senzor teploty (Petr K, 15.5.2017 7:07:41) Odpovědět

    Perfketní článek! Už se těším na pokračování s DS18B20 :-).

  4. WISOL Pro Mini (PavelDC, 7.5.2017 22:31:05) Odpovědět

    Jednou nás to vtáhne všechny :)

    Zdravím
    No a to nás ještě v tomto roce čeká NB IoT - už se těším, tento týden dostanu první modulky :-).
    PF


TOP produkty

Arduinotech GSM shield

Arduinotech GSM shield
877 Kč s DPH

Arduino MEGA2560

Arduino MEGA2560
424 Kč s DPH

Kontakt

Ing. Petr Foltýn
Kunčice pod Ondřejníkem 814, 73913
TOPlist