fllopi
Anmeldungsdatum: 31. August 2015
Beiträge: 26
|
Hallo, ich hatte schon länger danach gesucht aber noch nichts passendes zu meinem Problem gefunden.... Ich möchte ganz einfach einige Zahlen als integer über meine serielle Schnittstelle ausgeben, das geht nicht mit echo so weit ich es in Erfahrung bringen konnte sondern nur mit printf %d aber ich bin mir nicht sicher.
Zusätzlich muss ich eine Zahl als Zeichen ausgeben was nach meinen Recherchen mit echo gehen müsste?! Als bsp.: | varA=12345
printf %d $varA >> /dev/ttyS0 #12345 wird als Integer an meine serielle Schnittstelle gesendet
echo "5" >> /dev/ttyS0 #5 wird als Zeichen an meine serielle Schnittstelle gesendet
|
Stimmt das so oder liege ich daneben? LG fllopi Bearbeitet von rklm: Syntaxhighlighting + Codeblock
|
rklm
Projektleitung
Anmeldungsdatum: 16. Oktober 2011
Beiträge: 13204
|
Es gibt keinen Unterschied: die Zahlen werden immer als Zeichen ausgegeben. 1
2
3
4
5
6
7
8
9
10
11
12
13 | $ echo 5 | od -tx1c
0000000 35 0a
5 \n
0000002
$ echo "5" | od -tx1c
0000000 35 0a
5 \n
0000002
$ v=5
$ echo "$v" | od -tx1c
0000000 35 0a
5 \n
0000002
|
Wie Du siehst, kommt immer das gleiche heraus. Es ist etwas anderes, wenn Du Zahlen binär auf die Schnittstelle schicken musst. Aber davon war nicht die Rede.
|
fllopi
(Themenstarter)
Anmeldungsdatum: 31. August 2015
Beiträge: 26
|
Ja bei echo schon aber doch nicht wenn ich es mit printf an sie schicke oder liege ich da falsch?
|
user_unknown
Anmeldungsdatum: 10. August 2005
Beiträge: 17620
Wohnort: Berlin
|
Die serielle Schnittstelle kennt keine Dateitypen. Du kannst ihr keinen übergeben. Du kannst nur Bytes übergeben.
| echo -en "\x5" | od -tx1c
0000000 05
005
0000001
|
mit -en unterdrückst Du am Ende das Newline und mit -e aktivierst Du extended Features. Eines der extended Features ist es, Hexadezimalcodes einzugeben, bei 5 eine einfache Sache, da es \x5 ist, Maskierung ist nötig, also "\x5", "\x05" geht aber auch, falls Du ansonsten Schwierigkeiten mit größeren Werten bekämst.
|
fllopi
(Themenstarter)
Anmeldungsdatum: 31. August 2015
Beiträge: 26
|
Muss man also die werte so konfigurieren, oder reicht dann nicht auch ein "normales" echo?
echo "5" >> /dev/ttyS0
|
Marc_BlackJack_Rintsch
Ehemalige
Anmeldungsdatum: 16. Juni 2006
Beiträge: 4686
Wohnort: Berlin
|
@fllopi: Wofür soll das reichen? Das sendet etwas anderes, nämlich die Bytefolge 35 0a (zwei Bytewerte in Hexadezimalnotation angegeben), während das von user_unknown nur ein Byte mit dem Wert 5 sendet.
|
fllopi
(Themenstarter)
Anmeldungsdatum: 31. August 2015
Beiträge: 26
|
Naja ich muss an ein Gerät einige bestimmte Werte über die serielle Schnittstelle senden. Dabei muss ich einmal das Zeichen 5 senden und mehrere male einzelne Zahlen, diese aber nicht als Zeichen sondern als Zahl.
Zumindest hatte ich das so aus dem Vorgänger Programm, welches jedoch in C geschrieben war, abgelesen. Dort wurde mit dem Befehl ComWrtByte gearbeitet http://zone.ni.com/reference/en-XX/help/370051V-01/cvi/libref/cvicomwrtbyte/.
|
Marc_BlackJack_Rintsch
Ehemalige
Anmeldungsdatum: 16. Juni 2006
Beiträge: 4686
Wohnort: Berlin
|
@fllopi: Warum ist das neue Programm nicht auch in C? Oder irgendwas anderes, denn nahezu alles dürfte für so etwas besser geeignet sein als ein Bash-Skript.
|
rklm
Projektleitung
Anmeldungsdatum: 16. Oktober 2011
Beiträge: 13204
|
fllopi schrieb: Ja bei echo schon aber doch nicht wenn ich es mit printf an sie schicke oder liege ich da falsch?
Das kannst Du einfach ausprobieren: | $ printf '%d\n' 5 | od -tx1c
0000000 35 0a
5 \n
0000002
|
Der ganze Witz von printf (in der Shell und erst recht in C) ist, die Argumente formatiert als Zeichenketten auszugeben. fllopi schrieb: Naja ich muss an ein Gerät einige bestimmte Werte über die serielle Schnittstelle senden. Dabei muss ich einmal das Zeichen 5 senden und mehrere male einzelne Zahlen, diese aber nicht als Zeichen sondern als Zahl.
Hast Du denn keine Protokollbeschreibung? So etwas ist eigentlich unerlässlich, um das richtig zu machen.
Zumindest hatte ich das so aus dem Vorgänger Programm, welches jedoch in C geschrieben war, abgelesen. Dort wurde mit dem Befehl ComWrtByte gearbeitet http://zone.ni.com/reference/en-XX/help/370051V-01/cvi/libref/cvicomwrtbyte/.
Das ist anscheinend nur eine Funktion, die ein Byte verschicken kann. Entscheidend ist aber, was die Gegenseite versteht.
|
Marc_BlackJack_Rintsch
Ehemalige
Anmeldungsdatum: 16. Juni 2006
Beiträge: 4686
Wohnort: Berlin
|
In der Bash könnte eine Funktion die so ähnlich wie die gezeigte ComWrtByte() funktioniert, so aussehen:
| WriteByte() {
local device=$1
local byte_value=$2
echo -e "\x$(printf '%02x' "$byte_value")" > "$device"
}
|
Schön ist anders. ☺
|
fllopi
(Themenstarter)
Anmeldungsdatum: 31. August 2015
Beiträge: 26
|
OK ich versuche es jetzt erstmal mit dem Vorschlag von user_unknown:
dann müsste ich für die ausgabe der 5 schreiben,
| echo -en "\x5" >> /dev/ttyS0
|
und für z.B. eine 170
| echo -en "\xAA" >> /dev/ttyS0
|
Liege ich da richtig oder falsch?^^
|
rklm
Projektleitung
Anmeldungsdatum: 16. Oktober 2011
Beiträge: 13204
|
fllopi schrieb:
Liege ich da richtig oder falsch?^^
Ohne zu wissen, was die Gegenseite erwartet, kann man das schlecht sagen. Wenn z.B. alle Zahlen als 32Bit-Zahlen übermittelt werden müssen, dann reicht das nicht. Dann muss man vier Bytes schicken und außerdem wissen, ob Big- oder Little-Endian übermittelt werden muss.
|
fllopi
(Themenstarter)
Anmeldungsdatum: 31. August 2015
Beiträge: 26
|
Hmm ok danke, da werde ich nochmal nach fragen müssen. Noch eine Frage zu dem was Marc_BlackJack_Rintsch geschrieben hat,
wofür steht die 02 bei
?
|
user_unknown
Anmeldungsdatum: 10. August 2005
Beiträge: 17620
Wohnort: Berlin
|
Länge 2 Zeichen, vorne mit 0en füllen.
Laut Doku:
| Parameters
Input
Name Type Description
portNumber int A number that indicates the COM port on which to operate.
This number maps to the COM port specified by deviceName in the call to OpenCom or OpenComConfig. The portNumber 1, for example, may not necessarily map to COM1.
(Linux) The portNumber 1, for example, may not necessarily map to /dev/ttyS0.
Valid Range: 1—1,000
byte int The value of the byte to write to the selected port. Only the low-order byte is significant.
|
erwartet die Funktion nur ein Int, von dem sie nur das untere Byte auswertet. Ob Big- oder Little-Enzian - tja, weiterrecherchieren oder auf gut Glück.
|
fllopi
(Themenstarter)
Anmeldungsdatum: 31. August 2015
Beiträge: 26
|
Aber ist in deinem Code bsp. | WriteByte() {
local device=$1
local byte_value=$2
echo -e "\x$(printf '%02x' "$byte_value")" > "$device"
}
|
das nicht zu viel? Da die zahl mit Hilfe des printf Befehls schon in eine Hexadezimalzahl umgewandelt wurde.
Denn wenn ich das Ganze mit z.B.83 versuche ein S als Ausgabe erhalte, welches nicht hexadezimal ist.
|