Forum: Projekte & Code Programm zum billigen DMM VC820/VC840


von Rolf (Gast)


Angehängte Dateien:

Lesenswert?

Die Digitalmultimeter VC820/VC840 gibt es bei Conrad schon ab 49,95 EUR
komplett mit Batterie, Meßkabeln und seriellem Kabel, das sogar über
einen Optokopper vom DMM galvanisch getrennt ist.
Den mit google dazu gefundenen Treiber-Quellcode mußte ich
überarbeiten, damit er die meisten Übertragungsfehler rausfiltert,
Timeouts hat und nicht ewig wartet, auch für Langzeit-Messungen
verwendet werden kann und das Device nicht blockiert.
Diese Sachen sind im Treiber kommentiert (Anhang).

Man kann die Daten beispielsweise mit

./vc840 | tee data

in die Datei data schreiben und gleichzeitig auf der Konsole ausgeben.

Mit diesem Shell-Skript kann man die Daten auch sekündlich plotten:

#!/bin/sh
# gnuplot script, example usage: ./plotting.sh | gnuplot
# plot the data in "data" every second
echo set grid xtics ytics
while true; do
echo plot \"data\" with lines
sleep 1
done

Getestet habe ich es nur unter Linux, aber mit mimimalen Änderungen
sollte es unter jedem Posix-Kompatiblem Betriebssystem funktionieren.

Wegen den Posix-Threads muß man den Sorcecode mit der Option -lpthread
kompilieren. Ich benutze dafür diese allgemeine Funktion in der
.bashrc:

# Funktion zum Kompilieren. Bsp.: "c bsp" kompiliert bsp.c und
produziert bsp.
function c {
  gcc -Wall -I. -O3 -D_GNU_SOURCE -D__SMP__ -DLINUX -D_LARGEFILE_SOURCE
-D_FILE_OFFSET_BITS=64 -D_REENTRANT -lpthread -lrt -mcpu=i686
-fexpensive-optimizations -DCPU=686 -ffast-math -m486 -lm -lz -o $1
$1.c && prelink -fmRv ./$1 && strip $1
}

von nobody0 (Gast)


Angehängte Dateien:

Lesenswert?

Angehängt die überarbeitete Version, in der der erste USB-RS232-Adapter
als Schnittstelle eingetragen ist (in der ersten Version ist es die
erste serielle Schnittstelle).

Der erste von zwei Checks, ob das Datenpaket unfragmentiert ist, war
nicht ganz korrekt. Jetzt erfolgt dieser Check durch Überprüfen der
Zeit, die zwischen dem Empfangen von Byte n-1 und Byte n (>0) vergeht.
select gibt diese Zeit ja immer mit aus.

von Rolf (Gast)


Angehängte Dateien:

Lesenswert?

Und weil mir aufgefallen ist, dass man die Pausen-Länge zwischen zwei
Datenpaketen (muß mindestens 100 ms sein) einfacher und mit weniger
Code überprüfen kann, ist anbei diese Version ;-)

Mit der Version habe ich es nicht geschafft durch Wackelkontakt oder
verschobene Lichtschranke oder Umschalten oder Ein-/Aus-Schalten
verfälschte Daten zu bekommen; die beschädigten Daten wurde alle
rausgefiltert!

von Rolf (Gast)


Angehängte Dateien:

Lesenswert?

Von dieser Version werden nun auch die Mikrosekunden als µs und nicht
als us ausgedruckt.

von nobody0 (Gast)


Lesenswert?

Nachtrag: Bei Onboard-Ports gibt's das Problem, dass der Treiber im
Kernel die Daten-Pakete deutlich fragmentiert; da hilft dann nur
i_deadline auf 50000 erhöhen oder einen RS232-USB-Adapter an ein einen
USB2-Controller zu benutzen (oder ein USB1-Controller mit dem langen
timeout).
Und statt
fd = open (device, O_RDWR);
sollte
fd = open (device, O_RDWR | O_NDELAY);
besser sein (obwohl ich keinen Unterschied gemerkt habe).

von nobody0 (Gast)


Angehängte Dateien:

Lesenswert?

Anbei die aktuelle Version mit dem vom vorigen Post und pthread_kill
sowie pthread_exit um main korrekt zu terminieren.

von nobody0 (Gast)


Angehängte Dateien:

Lesenswert?

Sorry, ich hatte vorhin aus dem falschen Verzeichnis upgeloadet; anbei
nun die richtige Version.

von nobody0 (Gast)


Angehängte Dateien:

Lesenswert?

So, nachdem ich mal nachgesehen habe wie man eine serielle Schnittstelle
exklusiv öffnet, damit sich nicht mehrere Programme die Daten der
Schnittstelle gegenseitig wegnehmen oder die Schnittstelle
dekonfigurieren, wird die Schnittstelle nun mit überarbeitetem ioctl
geöffnet:

  // Set IO-Control-Parameter and check the device.
  if (-1 == ioctl (fd, TIOCEXCL, &modelines)) // Put the tty into
exclusive mode.
  {
    fprintf (stderr, "Error at ioctl TIOCEXCL on %s!\n", device);
    perror ("ioctl()");
    return (-1);
  }

Damit wird die Schnittstelle nur exklusiv geöffnet und der Versuch, das
Programm ein zweites mal zu starten scheitert:

> ./vc840
Using serial output to /dev/ttyUSB0, baudrate 2400
open failed: Device or resource busy

von nobody0 (Gast)


Angehängte Dateien:

Lesenswert?

Weil mir gerade eben aufgefallen ist, dass noch die Anzeige von "HOLD"
fehlt, ist die nun in dieser Version eingebaut; da sollte nun nichts
fehlen.

von nobody0 (Gast)


Angehängte Dateien:

Lesenswert?

Gemäß Murphys Law hatte get_time noch einen selten sichtbaren Bug, weil
die Zeit in µs mit zwei getrennten Aufrufen bestimmt wurde.
In der angehängten Version ist dieser Bug mit nur einem Aufruf von
gettimeofday beseitigt und zudem werden im Fehlerfall die Daten und die
Zeit nach stderr ausgegeben.

Übrigens kann man mit
{ ./vc840 | tee data ; } 3>&2 2>&1 1>&3 | tee log.err
die Daten und Fehlermeldungen getrennt speichern und gleichzeitig beide
zusammen in derselben Konsole ausgeben ;-)

von Rolf F. (Gast)


Angehängte Dateien:

Lesenswert?

Gerade ist mir noch aufgefallen, daß die Variable zum Setzen der
Baudrate als int deklariert wurde und daß deshalb alle Zuweisungen, z.
B.

 bdflag = B2400;

eigentlich immer 0 zuweisen sollten, da es keine ints sind.
Anbei nun die korrigierte Version mit der korrekten Deklaration

 speed_t bdflag;

Merkwürdig, daß der gcc das trotz allen aktivierten Warnungen nicht
gemeldet hat und daß es trotzdem funktionierte.

Bitte melde dich an um einen Beitrag zu schreiben. Anmeldung ist kostenlos und dauert nur eine Minute.
Bestehender Account
Schon ein Account bei Google/GoogleMail? Keine Anmeldung erforderlich!
Mit Google-Account einloggen
Noch kein Account? Hier anmelden.