ステップ2文字列編集を実行しようとしています。
- 文字列「ペイロード」と一致します。見つかった場合は、出力ファイルに示すように "#if #endif"コードを追加します。
- 次に、「payload」を含む行をコピーして「upper_payload」に置き換えて、「if endif」条件に貼り付けます。
入力ファイル:
Let's see if this works or not payload.
alskdjaslkdjn.
aslkdjbnalkgfjbaglbjbjdgfsbkgjbsg;
Also here is another_payload.
alskdjbnalgkjb.
kjhsdfjlkgfjlknbsgdfljkbgsbljk((*&)(&;
期待される出力ファイル:
Let's see if this works or not payload.
#if defined(NV_C2C_UPPER_PD)
Let's see if this works or not upper_payload.
#endif
alskdjaslkdjn.
aslkdjbnalkgfjbaglbjbjdgfsbkgjbsg;
Also here is another_payload.
#if defined(NV_C2C_UPPER_PD)
Also here is another_upper_payload.
#endif
alskdjbnalgkjb.
kjhsdfjlkgfjlknbsgdfljkbgsbljk((*&)(&;
複数のテキストファイルで実行できるように、シェルファイルに次のコードを書きました。
#!/bin/csh -f
sed -i '/payload/a #if defined(NV_C2C_UPPER_PD)\n#endif' $1
sed -i "/NV_C2C_UPPER_PD/a `sed -n '/payload/s/payload/upper_payload/p' $1`" $1
上記のシェルスクリプトを使用して次のコマンドを渡す場合:
> ./my_shell.sh test.txt
テキストファイルは次の出力に変更されます。
Let's see if this works or not payload.
#if defined(NV_C2C_UPPER_PD)
Let's see if this works or not upper_payload.
#endif
alskdjaslkdjn.
aslkdjbnalkgfjbaglbjbjdgfsbkgjbsg;
Also here is another_payload.
#if defined(NV_C2C_UPPER_PD)
Let's see if this works or not upper_payload.
#endif
alskdjbnalgkjb.
kjhsdfjlkgfjlknbsgdfljkbgsbljk((*&)(&;
また、端末に次のエラー/警告が表示されます。
sed: can't read Also here is another_upper_payload.: No such file or directory
出力から行が誤ってコピーされたため、2番目の「upper_payload」置換が間違っていることを確認できます。 「another_payload」を含む新しい行ではなく、最初の行をコピーします。
別のオプションを試しましたが、問題を解決できませんでした。助けてください。
答え1
式sed
の1つへの入力を生成するために別のプロセスを呼び出すのではなく、トリガー部分文字列()が見つかったらすぐにコマンドを使用して現在の行を再編成することをお勧めします。sed
s///
payload
/payload/!b
s/.*/&\
#if defined(NV_C2C_UPPER_PD)\
&\
#endif/
s/payload/upper_&/2
上記の編集スクリプトは、sed
最初にトリガー文字列を含むすべての行をスキップします。ラベルなしで使用すると(「branch」)、コマンドはb
スクリプトの最後に移動します。
残りの行では、内容全体をそれ自体に置き換え、次の行に置き換え、#if
元の行に戻し、次の#endif
行に置き換えます。s///
このコマンドは、上記のようにエスケープされている場合は改行文字を挿入するために使用できます(GNUではsed
リテラル改行文字の挿入も許可されます\n
)。
これにより、2番目の文字列が別の代替payload
文字列の前に追加されます。upper_
このソリューションでは、トリガー文字列が 1 行に複数回発生しないか、最後の置換が正しい部分文字列を置き換えないと想定しています。
コマンドラインで、
sed -e '/payload/!b' \
-e 's/.*/&\
#if defined(NV_C2C_UPPER_PD)\
&\
#endif/' \
-e 's/payload/upper_&/2' file
または、スクリプトに別のスクリプトファイルを使用します。
sed -f script file
またはここでスクリプト文書を使用してください。
sed -f /dev/stdin file <<'SED_SCRIPT'
/payload/!b
s/.*/&\
#if defined(NV_C2C_UPPER_PD)\
&\
#endif/
s/payload/upper_&/2
SED_SCRIPT
またはGNUを使用してsed
、
sed -e '/payload/!b' \
-e 's/.*/&\n#if defined(NV_C2C_UPPER_PD)\n&\n#endif/' \
-e 's/payload/upper_&/2' file
結果:
Let's see if this works or not payload.
#if defined(NV_C2C_UPPER_PD)
Let's see if this works or not upper_payload.
#endif
alskdjaslkdjn.
aslkdjbnalkgfjbaglbjbjdgfsbkgjbsg;
Also here is another_payload.
#if defined(NV_C2C_UPPER_PD)
Also here is another_upper_payload.
#endif
alskdjbnalgkjb.
kjhsdfjlkgfjlknbsgdfljkbgsbljk((*&)(&;
答え2
あなたはこれを試すことができますsed
$ sed -i 's/\(.*\)\(payload\)\(.*\)/&\n#if defined(NV_C2C_UPPER_PD)\n\1upper_\2\3\n#endif/ ' input_file
\(.*\)\(payload\)
ここでは、一致を2つのグループに分けて、戻り時に簡単に再参照できるようにします。
&
変更されていない完全一致を返します
\1upper_\2
ここで必要な順序でグループを返し、挿入がpayload
許可されるupper_
まで最初のグループが一致します。payload
出力
$ sed 's/\(.*\)\(payload\)\(.*\)/&\n#if defined(NV_C2C_UPPER_PD)\n\1upper_\2\3\n#endif/' input_file
Let's see if this works or not payload
#if defined(NV_C2C_UPPER_PD)
Let's see if this works or not upper_payload
#endif.
alskdjaslkdjn.
aslkdjbnalkgfjbaglbjbjdgfsbkgjbsg;
Also here is another_payload
#if defined(NV_C2C_UPPER_PD)
Also here is another_upper_payload
#endif.
alskdjbnalgkjb.
kjhsdfjlkgfjlknbsgdfljkbgsbljk((*&)(&;
答え3
ここにはすでに良い解決策がありますが、sed
個人的にはawk
次の解決策を好みます。
awk \
-v if='#if defined(NV_C2C_UPPER_PD)' \
-v endif='#endif' \
'
/payload/{
line=$0
gsub("payload","upper_payload",$0);
printf "%s\n%s\n%s\n%s\n",$line,if,$0,endif
next
}
1' file
答え4
POSIXlyを使用する1つの方法は次のとおりです。
sed -e 'p
/payload/!d
s//upper_&/
i\
#if defined(NV_C2C_UPPER_PD)
a\
#endif
' file
改行をエスケープしたくない場合は、POSIXlyに準拠しながら次のことを実行できます。
sed -e 'p
/payload/!d
s//upper_&/
H;s/.*//;x;G
s/^/#if defined(NV_C2C_UPPER_PD)/
s/$/#endif/
' file