Was ich versuche, ist ganz einfach. Ich erzeuge eine Ausgabe von tshark
und leite sie awk
mit einer Pipe an um |
. Da tshark
Livedaten abgerufen werden, möchte ich, dass awk
in jeder Ausgabe nach einem Muster (einige MAC-Adressen, die ich bereits habe) in der ersten Spalte einer Datei („target.txt“) gesucht wird und bei einer Übereinstimmung awk
die erste und zweite Spalte aus dieser Datei ausgegeben werden.
Beispiel aus target.txt
:
ab:cd:ef:gh:ij:kl,Me
12:34:56:78:90:10,You
1b:2d:3f:4h:5j:6l,someone
Um das Ganze einfacher zu machen, tshark
hat meine Ausgabe nur zwei Spalten und die Spalte mit der MAC-Adresse ist die zweite.
1 Ausgabezeile tshark
sieht wie folgt aus:
Jun 16, 2014 02:55:51.300286000 12:34:56:78:90:10
^^^^- date and MAC are separated by tab!
Wenn also tshark
gefunden wird 12:34:56:78:90:10
, awk
wird ausgegeben
12:34:56:78:90:10 -> You
oder noch besser:
Jun 16, 2014 02:55:51.300286000 12:34:56:78:90:10 -> You
BEARBEITEN #1
Nun, ich habe einige Tests durchgeführt und festgestellt, dass tshark
die Ausgabe durch \t getrennt ist tab
. Das ist keine große Sache, aber schon eine kleine Verbesserung. Die Sache ist, ich habe Beispiele aus der Ausgabe erhalten und mit Gnoucs Antwort über einen Befehl vor der Pipe tshark
getestet . Es hat funktioniert. Dann habe ich das for geändert und alles hat aufgehört zu funktionieren =).echo
|
echo
tshark
Ist es ein Problem mit den Live-Daten oder so etwas? Hier ist mein Code bis jetzt:
$ tshark -I -i wlan0 -T fields -e radiotap.dbm_antsignal -e wlan.sa | awk -F'[ ,\t]' '
FNR == NR { a[$1] = $2 }
($NF in a) { print $0" -> "a[$NF] }
' alvos.txt -
also, es hat einfach geklappt! Wahrscheinlich war es ein Tippfehler. Danke für alle Antworten!
Antwort1
Versuche dies:
$ awk -F'[ ,\t]' '
FNR == NR { a[$1] = $2 }
($NF in a) { print $0" -> "a[$NF] }
' target.txt -
Beispiel:
$ awk -F'[ ,\t]' '
FNR == NR { a[$1] = $2 }
($NF in a) { print $0" -> "a[$NF] }
' target.txt -
Jun 16, 2014 02:55:51.300286000 12:34:56:78:90:10 # Ctrl + D here
Jun 16, 2014 02:55:51.300286000 12:34:56:78:90:10 -> You
Erläuterung
-F[ ,\t]
: Wir verwenden Komma, Leerzeichen oder Tabulator als Feldtrennzeichen.FNR == NR { a[$1] = $2 }
:FNR == NR
gilt nur bei der Verarbeitung der ersten Datei. Dahertarget.txt
speichern wir mit jeder Zeile in das zweite Feld in einem assoziativen Array, wobei das erste Feld (MAC-Adresse) der Index ist.($NF in a)
: Wenn beim Lesen der Eingabe (-
nachhertarget.txt
wirdawk
das Lesen aus der Eingabe bewirkt) das letzte Feld im assoziativen Array liegta
, drucken wir das gewünschte Ergebnis.
Antwort2
Wenn ich Sie richtig verstehe, wird einer von beiden zumindest die gewünschte Ausgabe erzeugen:
${TSHARK} |
sed -n "$(IFS=',
'; printf '/%s/s//& -> %s/p\n' \
$(cat target.txt)
)"
${TSHARK} |
sed -n "$(
sed 's/,/|s||\& -> /
s/.*/\\|&|p/
' <target.txt
)"
Ich habe dies folgendermaßen getestet:
printf 'ab:cd:ef:gh:ij:kl,Me
12:34:56:78:90:10,You
1b:2d:3f:4h:5j:6l,someone' >./target.txt
printf 'Jun 16, 2014 02:55:51.300286000 12:34:56:78:90:10' |
sed ...
Und das war meine Ausgabe:
Jun 16, 2014 02:55:51.300286000 12:34:56:78:90:10 -> You
Antwort3
#!/usr/bin/env awk
# filename ~/mac-lookup.awk
function load_mac_list (filename, array) {
while ((getline line < filename) > 0) {
split(line, fields, ",");
array[fields[1]] = fields[2];
}
close(filename)
}
BEGIN {
load_mac_list("target.txt", mac_list);
}
($5 in mac_list) {
print $0 " -> " mac_list[$5];
next;
}
{
print; # remove this line to avoid printing unmatched lines
}
Hier ist der Brute-Force-Ansatz. Laden Sie die Zieldatei und drucken Sie den Mac-Alias nur aus, wenn die Mac-Adresse in der Liste enthalten ist.
Beachten Sie in diesem Fall, dass die Datei „target.txt“ im awk-Skript fest codiert ist. In Gnoucs Antwort können Sie den Dateinamen der Zielliste nach Wunsch skripten.
Verwendung
$ ${TSHARK} | awk -f ~/mac-lookup.awk
Jun 16, 2014 02:55:51.300286000 12:34:56:78:90:10 -> You
Jun 16, 2014 02:55:51.300286010 zy:xw:vu:ts:rq:po
Jun 16, 2014 02:55:51.300286020 ab:cd:ef:gh:ij:kl -> Me