1 points par GN⁺ 1 시간 전 | 1 commentaires | Partager sur WhatsApp
  • Depuis l’arrêt du service de localisation GPS de Mozilla, la localisation basée sur GeoClue sous Linux est devenue imprécise, et where-am-i situait l’emplacement près de Toronto avec une précision de 25 km via GeoIP
  • En partant du principe qu’un serveur domestique fixe ne bouge pas, la configuration a été adaptée pour diffuser localement les coordonnées GPS souhaitées à l’intérieur du réseau domestique
  • Dans GeoClue, network-nmea était activé par défaut dans /etc/geoclue/geoclue.conf, et le service récupérait les informations GPS en recherchant le service mDNS _nmea-0183._tcp
  • nmea-static-gps-server diffuse des messages GPS NMEA 0183 une fois par seconde via TCP et enregistre le service _nmea-0183._tcp avec Avahi
  • Après le redémarrage de GeoClue, le client a immédiatement récupéré les coordonnées du serveur, avec la description GPS GGA+RMC et une précision de 0 meters ; Gnome Maps a aussitôt affiché la bonne position

Configuration de GeoClue et de NMEA

  • Depuis l’arrêt du service de localisation GPS de Mozilla, la précision de localisation sous Linux a baissé, et GeoClue, utilisé par Firefox et Gnome Maps sur plusieurs systèmes Linux, situait l’emplacement près de Toronto via GeoIP avec une précision de 25 km selon where-am-i
  • La démo where-am-i peut être installée via les paquets de la distribution
    # Fedora  
      sudo dnf install geoclue2-demos  
    
    # famille Debian  
      sudo apt install geoclue-2-demo  
    
  • En s’appuyant sur le fait qu’un serveur domestique fixe ne se déplace pas, la configuration a été ajustée pour diffuser localement les coordonnées GPS souhaitées à l’intérieur du réseau domestique
  • Le protocole utilisé est NMEA 0183, un ensemble de spécifications pour l’électronique marine, dont les messages peuvent être envoyés via un port série ou des sockets TCP
  • Un exemple de message GPS est composé de lignes GPRMC et GPGGA
    $GPRMC,204049.000,A,5308.3999,N,00601.9266,E,0.000,0.000,030526,,*02  
    $GPGGA,204049.000,5308.3999,N,00601.9266,E,1,08,1.0,119.0,M,0.0,M,,*6F  
    
  • Dans /etc/geoclue/geoclue.conf, network-nmea était activé par défaut dans GeoClue
    # Network NMEA source configuration options  
      [network-nmea]  
    # Fetch location from NMEA sources on local network?  
      enable=true  
    
  • GeoClue recherche un service mDNS nommé _nmea-0183._tcp et, lorsqu’il trouve un enregistrement, se connecte à cette adresse pour récupérer les informations GPS

Implémentation du serveur et vérification du fonctionnement

  • nmea-static-gps-server est un serveur TCP qui diffuse des informations GPS une fois par seconde et enregistre le service _nmea-0183._tcp avec Avahi
  • Avahi est l’implémentation mDNS standard sur Linux ; sur Mac, Bonjour remplit le même rôle, et mDNS est aussi utilisé pour les adresses .local sur le réseau local ou pour découvrir des appareils comme les imprimantes et les téléviseurs
  • Le dépôt inclut la configuration de service Avahi suivante
    <?xml version="1.0" standalone='no'?>  
    <!DOCTYPE service-group SYSTEM "avahi-service.dtd">  
    <service-group>  
      <name replace-wildcards="yes">NMEA GPS (%h)</name>  
      <service>  
        <type>_nmea-0183._tcp</type>  
        <port>10110</port>  
      </service>  
    </service-group>  
    
  • Après avoir copié ce fichier dans /etc/avahi/services/nmea-statis-gpc.service, on peut vérifier la découverte du service depuis une autre machine avec avahi-browse
    $ avahi-browse  _nmea-0183._tcp -r -t  
    + wlp192s0 IPv6 NMEA GPS (node05)                             _nmea-0183._tcp      local  
    + wlp192s0 IPv4 NMEA GPS (node05)                             _nmea-0183._tcp      local  
    = wlp192s0 IPv6 NMEA GPS (node05)                             _nmea-0183._tcp      local  
       hostname = [node05.local]  
       address = [fe80::a8c2:15de:9af:19b]  
       port = [10110]  
       txt = []  
    = wlp192s0 IPv4 NMEA GPS (node05)                             _nmea-0183._tcp      local  
       hostname = [node05.local]  
       address = [192.168.2.205]  
       port = [10110]  
       txt = []  
    
  • Lorsque le service fonctionne sur node05.local, le serveur TCP lui-même peut aussi être testé facilement avec telnet node05.local 10110
  • Après avoir redémarré GeoClue sur le client, celui-ci a immédiatement récupéré les coordonnées du serveur
    $ sudo systemctl restart geoclue  
    $ /usr/libexec/geoclue-2.0/demos/where-am-i  
    
  • Le résultat renvoyait les coordonnées exactes du serveur et la description GPS GGA+RMC, avec une précision affichée à 0 meters
    Client object: /org/freedesktop/GeoClue2/Client/3  
    
    New location:  
    Latitude:    43.645758°  
    Longitude:   -79.410510°  
    Accuracy:    0 meters  
    Altitude:    119.000000 meters  
    Speed:       0.000000 meters/second  
    Description: GPS GGA+RMC  
    Timestamp:   Sun 03 May 2026 04:58:58 PM (1777841938 seconds since the Epoch)  
    
  • Gnome Maps a immédiatement affiché la bonne position, tandis que Firefox nécessitait un redémarrage
  • Cela semblait aussi fonctionner dans Apple Maps sur Mac lorsque les Location Services étaient désactivés, mais la carte n’affichait pas un point précis et ne situait correctement que la zone approximative
  • Cette méthode permet aux machines Linux à la maison d’obtenir immédiatement la bonne position sans attendre des requêtes GPS lentes et imprécises ; elle peut aussi servir à usurper une fausse position pour des invités ou collègues utilisant Linux
  • https://github.com/evert/nmea-static-gps-server

1 commentaires

 
GN⁺ 1 시간 전
Commentaires sur Lobste.rs
  • Je ne savais absolument pas qu’il existait un service mDNS standard permettant d’annoncer du GNSS sur le LAN, et ça résout immédiatement un problème sur lequel je réfléchissais par intermittence depuis environ 6 mois

    • Tu peux partager ce que tu es en train de construire ? Mon petit projet résout un problème précis, mais je me demandais s’il y avait des usages plus larges
  • Le spoofing de position GPS est une bonne idée, mais en pratique cela semble demander pas mal de travail
    Ce serait bien d’avoir une option simple dans les réglages Android ou dans une extension Firefox, du genre « utiliser la position réelle / utiliser une position personnalisée »
    Je me demande aussi quel poids est accordé à la position GPS quand elle entre en conflit avec d’autres éléments comme l’IP ou la locale
    Cela dit, j’ai eu un moment de surprise en voyant la photo de Jeff Geerling en bas de page, avant de réaliser qu’il n’était pas l’auteur mais qu’il avait simplement mis un like
    Si possible, j’évite généralement son travail

    • Pourquoi dis-tu que tu « évites généralement son travail si possible » ?
    • Il me semble qu’Android a une fonctionnalité de ce genre. C’est Mock Locations, réservée aux développeurs
      J’ai déjà utilisé un récepteur GNSS Trimble ; je ne me souviens plus si c’était en USB OTG ou en BLE, mais l’application Trimble servait de source Mock Locations, ce qui permettait à n’importe quelle application Android d’obtenir les coordonnées haute précision de la perche d’arpentage, d’environ 2 cm, au lieu de la précision relativement faible du téléphone lui-même
  • Intéressant, mais je pourrais aussi l’implémenter moi-même et écrire un script pour que mon appareil Android l’émette quand il est sur mon réseau domestique
    Je ne suis pas encore totalement sûr d’en avoir réellement besoin :p

  • J’ignorais que NMEA 0183 était un ensemble de spécifications pour l’électronique marine
    Je n’ai jamais été assez curieux pour chercher ce que signifiait NMEA, mais je connaissais au moins le nom via ModemManager et les modems Qualcomm

    $ qmicli -d qrtr://0 --loc-get-nmea-types  
    Successfully retrieved NMEA types: gga, gsv, gsa  
    $ mmcli -m any --location-status  
      Location | capabilities: 3gpp-lac-ci, gps-raw, gps-nmea, agps-msa, agps-msb