#include <algorithm>
#include <LoRaMacKR920.hpp>
char keyBuf[128];
struct {
uint8_t ip;
uint16_t co2;
uint16_t voc;
float humidity;
float temperature;
uint16_t pm1;
uint16_t pm2_5;
uint16_t pm10;
uint16_t voc_now_ref;
uint16_t voc_ref;
uint16_t voc_now;
uint16_t reserved;
uint16_t state;
} res;
int recv_flag = 0;
uint8_t msg_type = 0;
uint8_t msg_length = 0;
uint8_t msg_command = 0;
uint8_t msg_data[40];
uint8_t msg_checksum = 0;
uint8_t data_index = 0;
static uint8_t devEui[8];
static uint8_t appKey[16];
#define DE_RE GPIO7
static void rs485WriteMode(){
printf("writemode\r\n");
}
static void rs485ReadMode(){
printf("readmode\r\n");
}
static void getAirInfo(void* data){
uint8_t request[5] = { 0x11 , 0x02 , 0x01 , 0x00 , 0x00 };
request[4] = 256 - ((request[0] + request[1] + request[2] + request[3]) % 256);
rs485WriteMode();
Serial2.write(request,
sizeof(request));
rs485ReadMode();
}
static void decode_AM1005(){
res.ip = msg_data[0];
res.co2 = ((uint16_t) msg_data[1] << 8) | (uint16_t) msg_data[2];
res.voc = ((uint16_t) msg_data[3] << 8) | (uint16_t) msg_data[4];
res.humidity = (((uint16_t) msg_data[5] << 8) | (uint16_t) msg_data[6]) / 10.0;
res.temperature = ((((uint16_t) msg_data[7] << 8) | (uint16_t) msg_data[8]) / 10.0) - 50;
res.pm1 = ((uint16_t) msg_data[9] << 8) | (uint16_t) msg_data[10];
res.pm2_5 = ((uint16_t) msg_data[11] << 8) | (uint16_t) msg_data[12];
res.pm10 = ((uint16_t) msg_data[13] << 8) | (uint16_t) msg_data[14];
res.voc_now_ref = ((uint16_t) msg_data[15] << 8) | (uint16_t) msg_data[16];
res.voc_ref = ((uint16_t) msg_data[17] << 8) | (uint16_t) msg_data[18];
res.voc_now = ((uint16_t) msg_data[19] << 8) | (uint16_t) msg_data[20];
res.reserved = ((uint16_t) msg_data[21] << 8) | (uint16_t) msg_data[22];
res.state = msg_data[23];
printf("ip : %d co2: %d voc: %d H : %0.1f T : %0.1f PM1.0: %d PM2.5: %d PM10: %d VOC_NOW/REF: %d VOC_NOW: %d VOC_REF: %d RESERVED: %d STATE: %d\r\n",
res.ip, res.co2, res.voc, res.humidity, res.temperature, res.pm1, res.pm2_5, res.pm10, res.voc_now_ref, res.voc_ref, res.voc_now, res.reserved, res.state);
}
int check_checksum(){
uint8_t checksum = 0;
checksum += msg_type;
checksum += msg_length;
checksum += msg_command;
for (int i = 0 ; i < msg_length-1; i++){
checksum += msg_data[i];
}
checksum = (256 - checksum) % 256 ;
printf("checksum: %d , msg_checksum: %d\r\n",checksum, msg_checksum);
if (checksum == msg_checksum){
return 1;
} else{
return 0;
}
}
static void taskPeriodicSend(void *) {
printf("* Out of memory\n");
return;
}
char stringvalue[150];
int abc = sprintf(stringvalue, "\"CO2\":%d,\"VOC\":%d,\"Humidity\":%0.1f,\"Temperature\":%0.1f,\"PM1.0\":%d,\"PM2.5\":%d,\"PM10\":%d", res.co2, res.voc, res.humidity, res.temperature, res.pm1, res.pm2_5, res.pm10);
strncpy((char *) f->buf, stringvalue,abc);
f->
len = strlen((
char *) f->buf);
error_t err = LoRaWAN.
send(f);
printf("* Sending periodic report (%p:%s (%u byte)): %d\n", f, f->buf, f->len, err);
delete f;
}
}
static void eventLoRaWANJoin(
bool joined,
const uint8_t *joinedDevEui,
const uint8_t *joinedAppEui,
const uint8_t *joinedAppKey,
const uint8_t *joinedNwkSKey,
const uint8_t *joinedAppSKey,
uint32_t joinedDevAddr,
uint32_t
) {
if (joined) {
printf("* Joined to the network!\n");
} else {
printf("* Join failed. Retry to join\n");
}
}
printf("* Send done(%d): [%p] destined for port[%u], Freq:%lu Hz, Power:%d dBm, # of Tx:%u, ",
const char *strBW[] = { "Unknown", "125kHz", "250kHz", "500kHz", "Unexpected value" };
}
printf("FSK, ");
} else {
printf("Unkndown modulation, ");
}
printf("UNCONFIRMED");
printf("CONFIRMED");
printf("MULTICAST (error)");
printf("PROPRIETARY");
} else {
printf("unknown type");
}
printf(" frame\n");
printf("- TOO BIG\n");
}
delete frame;
}
printf("* Received:");
for (uint8_t i = 0; i < frame->len; i++) {
printf(" %02X", frame->buf[i]);
}
printf(" (");
printf(")\n");
if (
) {
if (emptyFrame) {
error_t err = LoRaWAN.
send(emptyFrame);
delete emptyFrame;
}
}
}
}
uint8_t msg_byte = p.
read();
switch (recv_flag){
case 0:
msg_type = msg_byte;
(msg_type == 0x16) ? recv_flag++ : recv_flag ;
break;
case 1:
msg_length = msg_byte;
recv_flag++;
break;
case 2:
msg_command = msg_byte;
recv_flag++;
break;
case 3:
msg_data[data_index] = msg_byte;
data_index++;
if (data_index == msg_length-1){
recv_flag++;
data_index = 0;
}
break;
case 4:
msg_checksum = msg_byte;
printf("type: %d, length: %d, command: %d, \r\n", msg_type, msg_length, msg_command);
printf("data: ");
for (int i = 0 ; i < msg_length-1; i++){
printf("0x%x ",msg_data[i]);
}
printf("checksum: %d\r\n", msg_checksum);
if (check_checksum()){
decode_AM1005();
#ifndef SENSOR_TEST_MODE
#endif
recv_flag = 0;
}else {
printf("checksum Error!\r\n");
recv_flag = 0;
}
break;
}
}
}
static void beginLoRaWAN(void *) {
LoRaWAN.
onJoin(eventLoRaWANJoin);
}
uint8_t numOctets = strlen(keyBuf);
if (numOctets == 32) {
numOctets /= 2;
char strOctet[3];
for (uint8_t j = 0; j < numOctets; j++) {
strOctet[0] = keyBuf[2 * j];
strOctet[1] = keyBuf[2 * j + 1];
strOctet[2] = '\0';
appKey[j] = strtoul(strOctet, NULL, 16);
}
printf("* New AppKey:");
for (uint8_t j = 0; j < numOctets; j++) {
printf(" %02X", appKey[j]);
}
printf(" (%u byte)\n", numOctets);
configMemory.write(appKey, 0, numOctets);
return;
} else {
printf("* HEX string length MUST be 32-byte.");
}
Serial.inputKeyboard(keyBuf, sizeof(keyBuf) - 1);
}
while (Serial.available() > 0) {
Serial.read();
}
Serial.onReceive(eventAppKeyInput);
Serial.listen();
Serial.inputKeyboard(keyBuf, sizeof(keyBuf) - 1);
Serial.println(
"* Enter a new appKey as a hexadecimal string "
"[ex. 00112233445566778899aabbccddeeff]"
);
}
void setup() {
Serial.begin(115200);
Serial.printf("\n*** [PLS100W] AM1005-P-485 + LoRaWAN ***\n");
System.getEUI(devEui);
Serial.printf("* EUI: %02X-%02X-%02X-%02X-%02X-%02X-%02X-%02X\n",
devEui[0], devEui[1], devEui[2], devEui[3], devEui[4], devEui[5], devEui[6], devEui[7]);
configMemory.read(appKey, 0, 16);
Serial.printf("* AppKey: %02x%02x%02x%02x%02x%02x%02x%02x%02x%02x%02x%02x%02x%02x%02x%02x\n",
appKey[0], appKey[1], appKey[2], appKey[3],
appKey[4], appKey[5], appKey[6], appKey[7],
appKey[8], appKey[9], appKey[10], appKey[11],
appKey[12], appKey[13], appKey[14], appKey[15]);
Serial.printf("* Last reset reason:0x%02X\n", System.getResetReason());
if (System.getResetReason() & (System.RESET_REASON_DOG | System.RESET_REASON_SREQ)) {
Serial.printf(
" - R0: 0x%08lx, R1: 0x%08lx, R2: 0x%08lx, R3: 0x%08lx\n", last->
r0, last->
r1, last->
r2, last->
r3);
Serial.printf(
" - R12: 0x%08lx, LR: 0x%08lx, PC: 0x%08lx, PSR: 0x%08lx\n", last->
r12, last->
lr, last->
pc, last->
psr);
}
rs485ReadMode();
#ifdef SENSOR_TEST_MODE
#else
if (memcmp(appKey, "\xFF\xFF\xFF\xFF\xFF\xFF\xFF\xFF\xFF\xFF\xFF\xFF\xFF\xFF\xFF\xFF", 16) == 0) {
eventKeyInput(Serial);
} else {
Serial.println("* Press any key to enter a new AppKey in 3 seconds...");
timerKeyInput.
onFired(beginLoRaWAN);
Serial.onReceive(eventKeyInput);
}
#endif
}
LoRaWAN frame.
Definition LoRaMac.hpp:88
FrameType_t type
Frame type.
Definition LoRaMac.hpp:102
Radio::LoRaSF_t sf
송신시 사용할, 또는 수신시 사용된 spreading factor
Definition LoRaMac.hpp:189
int16_t power
송신시 사용할 Tx power table index (LoRaMac::MaxTxPower ~ LoRaMac::MinTxPower), 송신 완료 콜백시 출력 세기(단위: dBm) 또는...
Definition LoRaMac.hpp:146
Radio::LoRaBW_t bw
송신시 사용할, 또는 수신시 사용된 bandwidth
Definition LoRaMac.hpp:206
struct LoRaMacFrame::@024007217170142272131231362111253110374345035353::@215311014042340047327077224045033277162306213223 LoRa
modulation 이 Radio::MOD_LORA 인 경우 사용되는 변수
uint8_t numTrials
전송 횟수
Definition LoRaMac.hpp:116
union LoRaMacFrame::@024007217170142272131231362111253110374345035353 meta
변복조 방식에 대한 속성
@ MULTICAST
Definition LoRaMac.hpp:95
@ PROPRIETARY
Definition LoRaMac.hpp:96
@ UNCONFIRMED
Definition LoRaMac.hpp:93
@ CONFIRMED
Definition LoRaMac.hpp:94
uint8_t port
Port number.
Definition LoRaMac.hpp:107
대한민국 920~923MHz 대역을 사용하는 LoRaMac
Definition LoRaMacKR920.hpp:25
LoRaWAN 단말 장치들을 위한 MAC 프로토콜
Definition LoRaMac.hpp:253
bool useADR
ADR 사용여부를 설정합니다.
Definition LoRaMac.hpp:442
bool framePending
Frame pending.
Definition LoRaMac.hpp:464
virtual error_t begin(uint8_t(*getBatteryLevel)()=NULL)
LoRaMAC layer initialization.
virtual error_t beginJoining(const uint8_t *devEui, const uint8_t *appEui, const uint8_t *appKey)
Over-the-Air Activation (OTAA) 방식의 join을 시도합니다.
void onJoin(void(*func)(LoRaMac &mac, bool result, const uint8_t *devEui, const uint8_t *appEui, const uint8_t *appKey, const uint8_t *nwkSKey, const uint8_t *appSKey, uint32_t devAddr, const RadioPacket &frame, uint32_t airTime))
Join이 완료되었을 때 호출될 콜백함수를 지정합니다.
void onSendDone(void(*sendDoneHandler)(LoRaMac &, LoRaMacFrame *))
전송이 완료될 때 호출될 함수를 지정합니다.
void setPublicNetwork(bool enable)
공용 LoRaWAN 네트워크를 사용할지 설정합니다.
void onReceive(void(*receiveHandler)(LoRaMac &radio, const LoRaMacFrame *frame))
수신이 완료될 때 호출될 함수를 지정합니다.
error_t send(LoRaMacFrame *frame)
frame 을 전송합니다.
uint8_t getNumPendingSendFrames()
전송 대기 중인 프레임 갯수를 구합니다.
무선 패킷
Definition RadioPacket.hpp:59
Radio::Modulation_t modulation
송신시 사용할, 또는 수신시 사용된 변복조 방식
Definition RadioPacket.hpp:160
uint32_t freq
송신시 사용할, 또는 수신시 사용된 주파수 (단위: Hz)
Definition RadioPacket.hpp:143
@ TOO_BIG
프레임이 너무 커서 전송 불가
Definition RadioPacket.hpp:94
Result_t result
송신 또는 수신 패킷 처리 결과
Definition RadioPacket.hpp:131
시리얼 포트를 제어하기 위한 클래스
Definition SerialPort.hpp:76
virtual int read()
포트 내부 버퍼에 수신된 문자를 하다 꺼냅니다.
virtual int available()
포트 내부 수신버퍼에 수신된 문자의 갯수를 반환합니다.
Timer는 일정 시간 이후에 1회 실행될 작업, 매 일정 시간마다 실행될 작업 등을 위한 기능입니다.
Definition Timer.hpp:61
void stop()
예약된, 혹은 측정 중인 Timer를 중단합니다.
bool startOneShot(uint32_t millis, bool interrupt=false)
작업함수를 millis 밀리초 이후 1회 실행합니다.
bool startPeriodic(uint32_t millis, bool interrupt=false)
작업함수를 매 millis 밀리초 주기로 반복하여 실행합니다.
void onFired(void(*func)(void *), void *args=nullptr)
타이머 만료시 실행시킬 작업함수를 지정합니다.
nRF5x MCU 내부 플래시 페이지에 데이터를 읽고 쓰기 위한 클래스
Definition nRF5xFlashPage.hpp:54
@ ERROR_SUCCESS
Definition nola-common.h:119
bool digitalWrite(int8_t pin, int value)
pin 를 HIGH 또는 LOW 로 설정합니다.
bool pinMode(int8_t pin, enum ioDirection direction)
pin 을 direction 방향을 갖는 디지털 핀으로 동작하도록 설정합니다.
@ OUTPUT
Definition nola-common.h:383
bool postTask(void(*func)(void *), void *args)
작업을 나중에 실행되도록 게시합니다.
LoRaBW_t
LoRa Bandwidth Type.
Definition Radio.hpp:107
@ BW_125kHz
Definition Radio.hpp:109
@ MOD_FSK
Definition Radio.hpp:67
@ MOD_LORA
Definition Radio.hpp:68
@ SF7
Definition Radio.hpp:82
Definition McuARMCortexM.hpp:62