(WS19-01)Wetterballon Entwicklung: Unterschied zwischen den Versionen

Aus Verteilte Systeme - Wiki
Wechseln zu: Navigation, Suche
Zeile 54: Zeile 54:
 
</syntaxhighlight>
 
</syntaxhighlight>
  
Es muss außerdem die Datei /etc/smsd.conf mit folgendem Inhalt vorhanden sein (die Datei wird in der Regel automatisch mit korrektem Inhalt angelegt, die AUflistung hier erfolgt nur der Vollständigkeit halber):
+
Es muss außerdem die Datei /etc/smsd.conf mit folgendem Inhalt vorhanden sein (die Datei wird in der Regel automatisch mit korrektem Inhalt angelegt, die Auflistung hier erfolgt nur der Vollständigkeit halber):
 
 
  
 
<syntaxhighlight>
 
<syntaxhighlight>
Zeile 77: Zeile 76:
  
 
[GSM1]
 
[GSM1]
#init =
+
device = /dev/ttyUSB0 //Das korrekte device kann mit ls -la /dev/serial/by-id
device = /dev/ttyUSB0
+
incoming = yes  
incoming = yes
+
baudrate = 9600
#pin =
 
baudrate = 19200
 
 
</syntaxhighlight>
 
</syntaxhighlight>
  

Version vom 27. Februar 2020, 20:00 Uhr

Formalia

C-Styleguide

CSV-Format

Doxygen

Implementierung

Als Implementierungssprache standen Python und C zur Auswahl. Unsere Wahl fiel auf C, da damit alle Gruppenmitglieder schon erste Erfahrungen sammeln konnten. Zur Ansteuerung der über I²C angeschlossenen Sensoren standen uns die Schnittstellen i2c-dev, WiringPi und die Registermanipulation mittels der bcm2835-Bibliothek zur Auswahl. Um die passende Methode zu finden, haben wir uns mit allen Varianten beschäftigt und die Vor- und Nachteile wie folgt zusammengefasst:

i2c-dev:
+ einfache Verwendung
- adapter_nr muss ermittelt werden
- Umweg über Filesystem -> schlechtere Performance

WiringPi:
+ sehr einfache Verwendung
o bis auf Setup, zu unflexible Funktionen (Alternative: Verwendung von write und read)
- Umweg über Filesystem -> schlechtere Performance

Low Level (Registermanipulation):
+ potentiell beste Performance
+ maximale Kontrolle
+ Unabhängigkeit von I2C-Bibliotheken -> bessere Portabilität bei identischem Prozessor auf unterschiedlichen Betriebssystemen
o root-only
- komplexer -> fehleranfälliger, zeitraubender, aber es gibt eine gute Vorlage zur Implementierung

Nach der Abwägung der Vor- und Nachteile haben wir uns für eine Implementierung mittels der bcm2835-Bibliothek entschieden, da uns die bessere Performance den größten Vorteil bei der Erfüllung der Anforderungen bot, auch wenn die Benutzerfreundlichkeit darunter litt.

Versenden einer SMS über den Pi

Um die Bergung nach der Landung zu vereinfachen, haben wir die GPS-Daten regelmäßig per SMS übermittelt. Neben dem Pi und dem GPS-Modul benötigten wir einen USB-Dongle (Huawei E3372), eine Sim-Karte und folgende Softwarepakete für den Pi:

usb-modeswitch usb-modeswitch-data smstools

Da der USB-Surfstick vom Pi nur als Massenspeicher erkannt wird, muss dieser in den Modem-Modus gewechselt werden:

sudo usb_modeswitch -v 12d1 -p 1f01 -M '55534243123456780000000000000011062000000100000000000000000000'

Die passenden Werte für -v und -p können über das Terminal mittels lsusb ermittelt werden.

Leider hat diese Methode unseren Stick nicht in den passenden Modus gebracht. Es musste zusätzlich unter /ets/usb_modeswitch.d/ eine Datei mit dem Namen 12d1:1f01und folgendem Inhalt angelegt werden:

# Huawei E3372 (fallback mode)
TargetVendor=  0x12d1
TargetProduct= 0x155f
MessageContent="55534243123456780000000000000011063000000100010000000000000000"

Es muss außerdem die Datei /etc/smsd.conf mit folgendem Inhalt vorhanden sein (die Datei wird in der Regel automatisch mit korrektem Inhalt angelegt, die Auflistung hier erfolgt nur der Vollständigkeit halber):

devices = GSM1
outgoing = /var/spool/sms/outgoing
checked = /var/spool/sms/checked
incoming = /var/spool/sms/incoming
logfile = /var/log/smstools/smsd.log
infofile = /var/run/smstools/smsd.working
pidfile = /var/run/smstools/smsd.pid
outgoing = /var/spool/sms/outgoing
checked = /var/spool/sms/checked
failed = /var/spool/sms/failed
incoming = /var/spool/sms/incoming
sent = /var/spool/sms/sent
stats = /var/log/smstools/smsd_stats

#
# Hier stehen u.U. eine Menge auskommentierter Einträge, die relevanten Zeilen befinden sich ganz am Ende der Datei
#

[GSM1]
device = /dev/ttyUSB0 //Das korrekte device kann mit ls -la /dev/serial/by-id
incoming = yes 
baudrate = 9600

Nun kann der Pi eine SMS verschicken. Dazu muss einfach nur eine Datei in den Ordner /var/spool/sms/outgoing/ verschoben werden. Zu beachten ist dabei, dass die Datei nach folgendem Schema aufgebaut ist.

To: Empfängernummer(Bsp: 4915201234567)

Text, der übermittelt werden soll.

Eine kleine Funktion zum Testen:

#include <stdio.h>
#include <stdlib.h>
#include <stdint.h>
#include <unistd.h>
#include <sys/types.h>
#include <string.h>

void send(char *message) {

	int fd_to, geschrieben;
	char *path = "/var/spool/sms/outgoing/data.txt";

	fd_to = open(path, O_WRONLY|O_CREAT, S_IRUSR|S_IWUSR|S_IRGRP|S_IWGRP|S_IROTH);

	if (fd_to == -1) {

		printf("Error opening file");
		return;
	}

	printf("Größe: %d\n", strlen(message));
	printf("Geöffnet\n");
	char *msg = "To: xxxxxxxxxx\n\n";
	
	char *fullmsg = malloc(strlen(msg) + strlen(message) + 1);
	strcpy(fullmsg, msg);
	strcat(fullmsg, message);
	strcat(fullmsg, "\n\0");
	 	
	geschrieben = write(fd_to, fullmsg, strlen(fullmsg));
	free(fullmsg);
}

int main(int argc, char *argv[]) {

	send("Hallo Welt");
	return 0;
}

Auswertungsprogramm

Um die aufgezeichneten Daten nach dem Flug grafisch aufzuarbeiten, wurde ein eigenes Tool geschrieben. Hier gab es keine großen Einschränkungen, was die Programmiersprache betrifft, aufgrund von Erfahrung und persönlicher Präferenz wurde sich für Java entschieden. Das Tool ist speziell auf die von uns verwendeten Sensoren und das Vormat der CSV-Dateien zugeschnitten, alledings Modular aufgebaut und somit leicht erweiterbar.

Über eine grafische Oberfläche kann ausgewählt werden, welche Werte auf x- und y-Achse abgebildet werden sollen. Danach muss für jeden ausgewählten Datentyp eine Datei mit den entsprechenden Daten angegeben werden. Hierbei merkt sich das Programm die letzten gewählten Dateien um bei häufiger Benutzung Zeit zu sparen. Des Weiteren können Grenzwerte für beide Achsen fesgelegt werden und es steht die Wahl offen, ob alle ausgewählten Werte in einem oder in mehreren Diagrammen dargestellt werden sollen.

Die Erzeugung der Diagramme folgt dem Factory-Method Designpattern. In einer abstrakten Klasse wird die Standardprozedur zur Erstellung eines Diagramms definiert. Für jeden Typ von Daten, den wir aufzeichnen (Temperatur, Luftdruck, etc.) gibt es dann eine konkrete Implementierung dieser Klasse, die entweder die Standardimplementierung übernehmen kann (was i.d.R. der Fall ist) oder diese überschreibt.