Basicstation and GPS location

Hi,

I’m wondering if anybody here has the basicstation working with GPS (as in, it updates the location in chirpstack).

There’s a feature request here: Feature request: send gateway GPS coordinates · Issue #105 · lorabasics/basicstation · GitHub
In which it states that the message is already being send, but only if it changes and via ‘type:alarm’.
I’m wondering if that’s something that chirpstack would understand or not?

This seems to be undocumented, or at least I could not find any reference to it in the documentation of the latest version: LoRa Basics™ Station | DEVELOPER PORTAL

Thanks. Back to the semtech forwarder it is :slight_smile:

1 Like

Hi,

I investigated the same issue last year. Basicstation can use a GPS module, as you were wondering. But same time is true what Brocaar said, the feature is not documented by Semtech. Maybe this feature is only for internal use of Semtech’s own devices?

Here is simple example how to debug those undocumented features. Add following gps (gps serial port) and log_level attributes to station_conf object. Restart basicstation and you should get all debug information.

station.conf file


.
.
.
    "station_conf": {
         "routerid": "123123123123FFF", 
        "RADIO_INIT_WAIT": "5s",
        "RX_POLL_INTV": "10ms",
        "TC_TIMEOUT": "360s",
        "gps": "/dev/ttyS0",
        "pps": "fuzzy",
        "log_file":  "stderr",
        "log_level": "XDEBUG",
        "log_size":  10000000,
        "log_rotate":  3
    }

Or if you are familiar with Rust, you can try the following code snippet to get raw messages from the mqtt (eu868/gateway/+/event/raw):

“RawPacketForwarderEvent contains a raw packet-forwarder event. It can be used to access packet-forwarder features that are not (fully) integrated with the ChirpStack Gateway Bridge.”

use tokio::{time};

use rumqttc:: {self, AsyncClient, Event,EventLoop, Incoming, MqttOptions, QoS, ConnectionError};
use std::{time::Duration}; 
use spinners::{Spinner, Spinners};
use chrono::{Local};
use serde_json::{Result, Value};
use chirpstack_api::gw::RawPacketForwarderEvent;
use chirpstack_api::prost::Message;


fn create_conn() -> (AsyncClient, EventLoop) {
    let id = "mqtttest-002";
    let mut mqttoptions = MqttOptions::new(id, "192.168.1.100", 1883);

    mqttoptions
        .set_keep_alive(Duration::from_secs(5))
        .set_manual_acks(false)
        .set_clean_session(true);

    println!("Create connection, Id: {}",id);

    AsyncClient::new(mqttoptions, 10)
}


#[tokio::main(worker_threads = 1)]
async fn main() -> Result<()> { 

    let (mut client, mut eventloop) = create_conn();

    client
        .subscribe("eu868/gateway/+/event/raw", QoS::AtMostOnce)
        .await
        .unwrap();

    let mut sp = Spinner::new(Spinners::Dots12, " Waiting message...".into());
    let mut spin_reg = true;

    loop {
        loop {        
            if spin_reg {
                sp = Spinner::new(Spinners::Dots12, " Waiting message...".into());
                spin_reg = false;
            }
            
            let event = eventloop.poll().await;

            match &event {
                Ok(Event::Incoming(Incoming::Publish(p))) => {
                    sp.stop_with_message(format!("{} Message received.\r",Local::now() ) );
                    let raw_gw_event: RawPacketForwarderEvent;
                    //let payload = p.payload.clone();
                    
                    raw_gw_event = RawPacketForwarderEvent::decode(&p.payload[..]).unwrap();   
                    let msg_event: Value = serde_json::from_slice(&raw_gw_event.payload).unwrap();
                    
                    println!("RawPacketForwarderEvent - id: {} {}\n", raw_gw_event.gateway_id, msg_event);

                    spin_reg = true;
                }
                Err(e) => {
                    match e { 
                        ConnectionError::MqttState(state_error) => {
                            sp.stop();
                            println!("\rMQTT state: = {:?}", state_error);                            
                            spin_reg = true;
                            
                            break;
                        }
                        _ => {
                            sp.stop();
                            println!("\rError: {:?}", e);
                            spin_reg = true;
                            time::sleep(Duration::from_secs(15)).await;
                            continue;
                        }
                    }
                }
                _ => () //Ok(Event::Outgoing(_))
                
            }            
        }

        println!("reconnect...");
        //client.disconnect().await.unwrap();
        time::sleep(Duration::from_secs(15)).await;

        (client, eventloop) = create_conn();

        client
            .subscribe("eu868/gateway/+/event/raw", QoS::AtMostOnce)
            .await
            .unwrap();

    }

    //Ok(())
}

cargo.toml

[package]
name = "protobuf_test"
version = "0.1.0"
edition = "2021"

[dependencies]
chirpstack_api = "4.3.1"
rumqttc = "0.20.0"
tokio = {version = "1.28.0", features =[ "rt-multi-thread"]}
spinners = "4.1.0"
chrono = "0.4.24"
serde_json = "1.0.96"
prost = "0.11.9"

Is the concentrator supported by ChirpStack consentratord? it is worth a shot :wink: