2016-12-09 8 views
1

У меня есть следующее содержание от data.log файл. Я хочу извлечь значение ts и часть полезной нагрузки (после deadbeef в полезной нагрузке, третья строка, начиная от второго до последнего байта. См. Ожидаемый результат).Извлечение содержимого из заголовка и частей полезной нагрузки

data.log

print 1: file offset 0x0 
ts=0x584819041ff529e0 2016-12-07 14:13:24.124834649 UTC 
type: ERF Ethernet 
dserror=0 rxerror=0 trunc=0 vlen=0 iface=1 rlen=96 lctr=0 wlen=68 
pad=0x00 offset=0x00 
dst=aa:bb:cc:dd:ee:ff src=ca:fe:ba:be:ca:fe 
etype=0x0800 
45 00 00 32 00 00 40 00 40 11 50 ff c0 a8 34 35   [email protected]@.P...45 
c0 a8 34 36 80 01 00 00 00 1e 00 00 08 08 08 08   ..46............ 
08 08 50 e6 61 c3 85 21 01 00 de ad be ef 85 d7   ..P.a..!........ 
91 21 6f 9a 32 94 fd 07 01 00 de ad be ef 85 d7   .!o.2........... 


print 2: file offset 0x60 
ts=0x584819041ff52b00 2016-12-07 14:13:24.124834716 UTC 
type: ERF Ethernet 
dserror=0 rxerror=0 trunc=0 vlen=0 iface=1 rlen=96 lctr=0 wlen=68 
pad=0x00 offset=0x00 
dst=aa:bb:cc:dd:ee:ff src=ca:fe:ba:be:ca:fe 
etype=0x0800 
45 00 00 32 00 00 40 00 40 11 50 ff c0 a8 34 35   [email protected]@.P...45 
c0 a8 34 36 80 01 00 00 00 1e 00 00 08 08 08 08   ..46............ 
08 08 68 e7 61 c3 85 21 01 00 de ad be ef 86 d7   ..h.a..!........ 
91 21 c5 34 77 bd fd 07 01 00 de ad be ef 86 d7   .!.4w........... 

print 3806: file offset 0x592e0 
ts=0x584819042006b840 2016-12-07 14:13:24.125102535 UTC 
type: ERF Ethernet 
dserror=0 rxerror=0 trunc=0 vlen=0 iface=1 rlen=96 lctr=0 wlen=68 
pad=0x00 offset=0x00 
dst=aa:bb:cc:dd:ee:ff src=ca:fe:ba:be:ca:fe 
etype=0x0800 
45 00 00 32 00 00 40 00 40 11 50 ff c0 a8 34 35   [email protected]@.P...45 
c0 a8 34 36 80 01 00 00 00 1e 00 00 08 08 08 08   ..46............ 
08 08 50 74 73 c3 85 21 01 00 de ad be ef 62 e6   ..Pts..!......b. 
91 21 ed 4a 8c df fd 07 01 00 de ad be ef 62 e6   .!.J..........b. 

Мой ожидается выход

0x584819041ff529e0,85d79121 
0x584819041ff52b00,86d79121 
0x584819042006b840,62e69121 

То, что я пытался до сих пор

Я могу извлечь значение TS. Я использовал

awk -v ORS="" '$NF == "UTC"{print sep$1; sep=","} END{print "\n"}' data.log 
>> ts=0x584819041ff529e0,ts=0x584819041ff52b00 

Но не удалось извлечь содержимое полезной нагрузки.

Любая помощь очень ценится.

+1

Строка '86d79121' отсутствует в вашем примере файла журнала. Как это часть вашего ожидаемого результата? – Inian

+0

Есть два экземпляра 'de ad be ef' в вашем файле журнала? Как вы ожидаете, что он будет отличаться? – Inian

+0

Hi Inian, он находится в файле журнала. пожалуйста, проверьте, что после (первого) deadbeef в полезной нагрузке вы можете его найти. – user2532296

ответ

2

Вот один из способов сделать это:

awk -F '=| ' '/^ts=/{printf $2","} /de ad be ef/{if(!a){printf $15$16;a=1}else{print $1$2;a=0}}' data.log 

Выход:

0x584819041ff529e0,85d79121 
0x584819041ff52b00,86d79121 

Объяснение:

-F '=| '     : set the field seperator to both '=' and 'space' 
/^ts=/{printf $2","}  : if pattern 'ts=' found at line beginning, print the second field 
/de ad be ef/{something} : if pattern 'de ad be ef' found, do 'something' 

Первоначально переменная a будет равна 0. если шаблон de ad be ef будет найден в первый раз, if(!a) преуспеет и, следовательно, распечатает поля 15th и 16th. Теперь установите a на номер 1. Поэтому, когда de ad be ef шаблон сопоставляется в следующей строке, проверка if(!a) не удалась и, следовательно, напечатала поля 1st и 2nd. Теперь сбросьте a до 0 и продолжите тот же процесс для остальной части файла.

+0

Можете ли вы также дать некоторые сведения о том, что делает код? Спасибо – user2532296

+0

Спасибо за детали. Причина заключалась в том, что ваша команда терпела неудачу для тестового примера 3 (добавлена ​​к вопросу). Спасибо – user2532296

+0

проверить это сейчас .. это было потому, что/ts/соответствовал «Pts» в случае 3-го набора –

1

Если вы хотите СЕПГ:

sed -n -e '/^ts/ {s/^ts=\([^ ]*\) \(.*\)/\1/; H;};' \ 
     -e '/de ad be ef/ {N; s/\(.*\)de ad be ef \([0-9a-f]\+\) \([0-9a-f]\+\) \(.*\) \([0-9a-f]\+\) \([0-9a-f]\+\) \(.*\)/,\2\3\5\6/; H;};' \ 
     -e '$ {x; s/\n,/,/g p;}' file 

Если вы заинтересованы в дальнейших Infos, просто спросите.

+1

Спасибо. Для больших записей ваше решение, кажется, занимает много времени, чем принятый ответ. – user2532296

+0

sed для простых подстановок на отдельных линиях, это все. Для чего-либо еще вы используете конструкции, которые стали устаревшими в середине 1970-х годов, когда был изобретен awk, и, как видно здесь, решение awk будет более четким, быстрым, более портативным, более легко расширяемым и быть лучше почти во всех других желаемых атрибутах программного обеспечения. –

1

вариант AWK используя DeadBeef как переключатель

awk -F '[= ]' '/^ts/{s=$2",";a=15} /de ad be ef/{s=s $a $(a+1);if(a==1)print s;a=1}' data.log 

и SED вариант

sed -n -e '/^ts=/{h;b^J}' -e "/de ad be ef/,//{H;g;s/ts=\([^ ]*\).*\n*de ad be ef \(..\) \(..\).*\n\(..\) \(..\).*/\1,\2\3\4\4/p;}" data.log 

информация: "^J" является CTRL + J, (новая линия carractere) в Posix версии и ";" в версии GNU

1

С GNU awk для gensub():

$ awk -v RS= '{ 
    gsub(/( |\t)+[^\n]*(\n|$)/," ") 
    print gensub(/.*\nts=(\S+).*de ad be ef (..) (..) (..) (..).*/,"\\1,\\2\\3\\4\\5\\6",1) 
}' data.log 
0x584819041ff529e0,85d79121 
0x584819041ff52b00,86d79121 
0x584819042006b840,62e69121 

Вышеуказанное будет работать, даже если deadbeef будет разделен между строками.