2016-12-08 26 views
0

Ich kann definitiv als sed/awk Neuling betrachtet werden. Ich habe daran gearbeitet, einen mehrstufigen Filter ohne Erfolg zu machen. Jedes Segment liefert Ergebnisse, wenn es selbstständig läuft, aber wenn ich sie zusammenkette, bekomme ich nichts. Ich habe sed | awk, awk | sed, sed | sed, awk | awk ausprobiert. Sie alle versagen, also nehme ich an, dass es jedem außer mir bekannt ist.Rohrleitungen sed | awk oder awk | sed

Die Daten sind mehrzeilige Textblöcke, wobei jeder Block als Datensatz behandelt werden kann (daher der Begrenzer ">"). Nachdem wir nur auf die ADV_NONCONN-Blöcke gefiltert haben, möchte ich dann den Textblock auf nur die Zeilen filtern, die "bdaddr" oder "RSSI" enthalten. Soweit ich weiß, müsste ich dafür eine separate Operation durchführen.

sudo hcidump | awk 'BEGIN {RS=">"} /ADV_NONCONN/' | sed -n -e "/bdaddr/p" -e "/RSSI/p" > log.txt 

hcidump Ausgangsabtastwert (ein "record"):

HCI Event: LE Meta Event (0x3e) plen 43 
    LE Advertising Report 
     ADV_NONCONN_IND - Non connectable undirected advertising (3) 
     bdaddr 0C:F3:EE:0D:70:89 (Public) 
     Flags: 0x06 
     Unknown type 0xff with 26 bytes data 
     RSSI: -62 

Ausführen der inversen (der Abschnitt Sed ersten awk dann) ergibt gleiche leere Menge Ergebnisse. Was für eine einfache Sache habe ich verpasst?

+2

Es ist fast nie nötig Rohr 'awk' zu' sed', da 'awk' die meisten Dinge tun kann, dass' sed' tun können und die awk-Syntax ist normalerweise einfacher zu verstehen. – Barmar

+0

Erlauben Sie mir, Ihnen ein Feedback zu geben: Sowohl Ihre Frage als auch Ihre eigene Antwort sind bis zur Ablenkung gesprächig - bitte überlegen Sie, sie prägnanter und fokussierter zu machen. – mklement0

+0

Auch einige Standardtipps für Neuankömmlinge: Wenn eine Antwort Ihr Problem löst, akzeptieren Sie es, indem Sie auf das große Häkchen (✓) daneben klicken und es optional up-votieren (up-voting benötigt mindestens 15 Reputationspunkte). Wenn Sie andere Antworten hilfreich fanden, stimmen Sie sie bitte ab. Akzeptieren und Up-Voting hilft zukünftigen Lesern. Bitte lesen Sie [den entsprechenden Artikel in der Hilfe] (http://stackoverflow.com/help/someone-answers). Wenn Ihre Frage noch nicht vollständig beantwortet wurde, geben Sie bitte Feedback. Wenn Sie denken, dass Sie selbst die beste Lösung gefunden haben, posten Sie sie als Antwort und akzeptieren Sie sie selbst. – mklement0

Antwort

-1

OK, so habe ich es schließlich aus. Ich glaube, dass die awk-Ausgabe nicht unbedingt pip-fähig ist, weil es eine Art Pufferung/Nicht-Schließen gibt, die es mit dem Eingabestrom macht. Seit der ursprünglichen Frage habe ich den Zeitstempel vom hcidump hinzugefügt.

Also, zuerst ein eindeutiges Zeichen (@) vor dem Zeitstempel mit sed, dann pipe, dass awk, die die mehrfachen Zeilen als ein einziger Datensatz behandelt mit diesem eindeutigen Zeichen (@) als Datensatzbegrenzer, Filter zu Die Datensätze, die ich haben möchte (ADV_NONCONN), fügt dann die entsprechende Ausgabe aus den Feldern zusammen, die es liest (die jetzt den Zeitstempel am Anfang des Datensatzes enthält).

sudo hcidump -t | sed -n '/HCI Event/{s/^/@/};p' | awk 'BEGIN {RS="@"} {-F '[\n]'} /ADV_NONCONN/ {print $1 " " $2 ", " $23 ", " $35}' > a.txt 

Die Lösung auf die ursprüngliche Frage wäre:

sudo hcidump | awk 'BEGIN {RS=">"} {-F '[\n]'} /ADV_NONCONN/ {print $20 ", " $32}' > a.txt 
+0

Leute, die downvote: zumindest einen Grund angeben. – Steven2163712

3

Es ist nicht erforderlich, awk an sed zu leiten. Fügen Sie einfach zusätzliche Bedingungen im awk Befehl:

sudo hcidump | awk -v RS=">" '/ADV_NONCONN/ { 
    n = split($0, line, /\n/); 
    for (i = 1; i <= n; i++) { 
     if (line[i] ~ /bdaddr|RSSI/) print line[i]; 
    } 
}' > log.txt 
+0

Ich denke, ich habe ein bisschen Detail verpasst (ich füge die ursprüngliche Frage hinzu). Jeder awk-Prozess ist ein mehrzeiliger Textblock. Nach awk-Filtern auf Datensätze, die ADV_NONCONN enthalten, muss ich nur nach den Zeilen in diesem Datensatzblock filtern, die entweder bdaddr oder RSSI enthalten. Dein Awk-Ausschnitt gibt mir auch ein leeres Set. –

+0

Ich habe es überarbeitet, um über die Zeilen im Block in 'awk' zu schleifen. – Barmar

+0

Aber ich gebe zu, dass dies jetzt nicht so einfach ist wie Ihr ursprünglicher Versuch, und ich bin nicht sicher, warum es nicht funktioniert hat. – Barmar