Awk配列で改行を無効にします。

Awk配列で改行を無効にします。

これは連続です文字列から一致しないトークンを削除しますか?私はCPU機能で発生した不要なコンパイラフラグをフィルタリングするためにAwkを使用しています(SunCC 12.2はSunCC 12.5と同じフラグを処理できません)。フィルタは、CXXFLAGSSunCC 12.2 でコンパイルエラーを引き起こす結果を生成します。

/opt/solstudio12.2/bin/CC -DDEBUG -g -xO0 -D__SSE2__ -D__SSE3__ -D__SSSE3__
usage: usage: CCCC [ options ] files.  Use 'CC -flags' for details
 [ options ] files.  Use 'CC -flags' for details
usage: CC [ options ] files.  Use 'CC -flags' for details
usage: CC [ options ] files.  Use 'CC -flags' for details
m64 -KPIC -template=no%extdef -w -erroff=wvarhidemem -erroff=voidretw -c cryptlib.cpp

何が起こっているのか、Awk-D__SSE2__ -D__SSE3__ -D__SSSE3__ + \nCXXLAGS2行に分割され、GNUmakeが次のように表示されます。

  1. /opt/solstudio12.2/bin/CC -DDEBUG -g -xO0 -D__SSE2__ -D__SSE3__ -D__SSSE3__
  2. -m64 -KPIC -template=no%extdef -w -erroff=wvarhidemem -erroff=voidretw -c cryptlib.cpp

それを駆動するBashスクリプトをデバッグするとき。出力を正しく解析すると、1012行と1014行に問題があるようです。

$ PS4='Line ${LINENO}: ' bash -x ./cryptest.sh
...
Line 1005: SUNCC_CXXFLAGS='-D__SSE2__ -D__SSE3__ -D__SSSE3__'
Line 1008: echo 'PLATFORM_CXXFLAGS: -D__SSE2__' -D__SSE3__ -D__SSSE3__
PLATFORM_CXXFLAGS: -D__SSE2__ -D__SSE3__ -D__SSSE3__
Line 1009: echo 'SUNCC_CXXFLAGS: -D__SSE2__ -D__SSE3__ -D__SSSE3__'
SUNCC_CXXFLAGS: -D__SSE2__ -D__SSE3__ -D__SSSE3__
LLine 1012: echo '-D__SSE2__ -D__SSE3__ -D__SSSE3__'
LLine 1012: /usr/gnu/bin/awk /SSE/ 'ORS= ' 'RS= '
Line 1012: SUNCC_SSE_CXXFLAGS='-D__SSE2__ -D__SSE3__ -D__SSSE3__
 '
Line 1014: echo 'SUNCC_SSE_CXXFLAGS: -D__SSE2__ -D__SSE3__ -D__SSSE3__
 '
SUNCC_SSE_CXXFLAGS: -D__SSE2__ -D__SSE3__ -D__SSSE3__

Line 1020: [[ -e /opt/solstudio12.2/bin/CC ]]

以下は対応するBashソースコードです。私は犯人がライン1012だと思いますSUNCC_SSE_CXXFLAGS=$(echo "$SUNCC_CXXFLAGS" | "$AWK" '/SSE/' ORS=' ' RS=' ')

1003   # If PLATFORM_CXXFLAGS is for SunCC, then use them
1004   if [[ ("$SUNCC_121_OR_ABOVE" -ne "0") ]]; then
1005       SUNCC_CXXFLAGS="${PLATFORM_CXXFLAGS[@]}"
1006   fi
1007   
1008   echo "PLATFORM_CXXFLAGS: ${PLATFORM_CXXFLAGS[@]}"
1009   echo "SUNCC_CXXFLAGS: ${SUNCC_CXXFLAGS[@]}"
1010
1011   # Sun Studio 12.3 and below workaround, http://github.com/weidai11/cryptopp/issues/228
1012   SUNCC_SSE_CXXFLAGS=$(echo "$SUNCC_CXXFLAGS" | "$AWK" '/SSE/' ORS=' ' RS=' ')
1013
1014   echo "SUNCC_SSE_CXXFLAGS: ${SUNCC_SSE_CXXFLAGS[@]}"
...
1018   ############################################
1019   # Sun Studio 12.2
1020   if [[ (-e "/opt/solstudio12.2/bin/CC") ]]; then

私の質問は、SolarisでアレイをAwk'ingするときにどのように改行を抑制できるかということです。


スクリプト呼び出しの実行方法は次のとおりです。スクリプトは以下にあります。cryptest.sh。モンスターだが問題のあるラインは約2880です(上記のライン1000はモノを分離するのに役立つ単純化されたテストケースです)。

CXXFLAGS="-DDEBUG -g -xO0 ${SUNCC_SSE_CXXFLAGS[@]}"
CXX="/opt/solstudio12.2/bin/CC" CXXFLAGS="$CXXFLAGS" "$MAKE" "${MAKEARGS[@]}" static dynamic cryptest.exe 2>&1 | tee -a "$TEST_RESULTS"

どうやってこのようなことがPLATFORM_CXXFLAGS起こったのか。コードパスはGCC定義に従って有効になるため、ソースコードに必要です(SunCCはこれを定義しません)。

if [[ ("$IS_SOLARIS" -ne "0") && ("$SUNCC_121_OR_ABOVE" -ne "0") ]]; then
    ISAINFO=$(isainfo -v 2>/dev/null)
    if [[ ($(echo "$ISAINFO" | "$GREP" -c "sse2") -ne "0") ]]; then PLATFORM_CXXFLAGS+=("-D__SSE2__"); fi
    if [[ ($(echo "$ISAINFO" | "$GREP" -c "sse3") -ne "0") ]]; then PLATFORM_CXXFLAGS+=("-D__SSE3__"); fi
    if [[ ($(echo "$ISAINFO" | "$GREP" -c "ssse3") -ne "0") ]]; then PLATFORM_CXXFLAGS+=("-D__SSSE3__"); fi
    if [[ ($(echo "$ISAINFO" | "$GREP" -c "sse4.1") -ne "0") ]]; then PLATFORM_CXXFLAGS+=("-D__SSE4_1__"); fi
    if [[ ($(echo "$ISAINFO" | "$GREP" -c "sse4.2") -ne "0") ]]; then PLATFORM_CXXFLAGS+=("-D__SSE4_2__"); fi
    if [[ ($(echo "$ISAINFO" | "$GREP" -c "aes") -ne "0") ]]; then PLATFORM_CXXFLAGS+=("-D__AES__"); fi
    if [[ ($(echo "$ISAINFO" | "$GREP" -c "pclmulqdq") -ne "0") ]]; then PLATFORM_CXXFLAGS+=("-D__PCLMUL__"); fi
    if [[ ($(echo "$ISAINFO" | "$GREP" -c "rdrand") -ne "0") ]]; then PLATFORM_CXXFLAGS+=("-D__RDRND__"); fi
    if [[ ($(echo "$ISAINFO" | "$GREP" -c "rdseed") -ne "0") ]]; then PLATFORM_CXXFLAGS+=("-D__RDSEED__"); fi
    if [[ ($(echo "$ISAINFO" | "$GREP" -c "avx") -ne "0") ]]; then PLATFORM_CXXFLAGS+=("-D__AVX__"); fi
    if [[ ($(echo "$ISAINFO" | "$GREP" -c "avx2") -ne "0") ]]; then PLATFORM_CXXFLAGS+=("-D__AVX2__"); fi
    if [[ ($(echo "$ISAINFO" | "$GREP" -c "bmi") -ne "0") ]]; then PLATFORM_CXXFLAGS+=("-D__BMI__"); fi
    if [[ ($(echo "$ISAINFO" | "$GREP" -c "bmi2") -ne "0") ]]; then PLATFORM_CXXFLAGS+=("-D__BMI2__"); fi
fi

ベストアンサー1

存在する:

echo '-D__SSE2__ -D__SSE3__ -D__SSSE3__' | awk /SSE/ RS=' ' ORS=' '

あなたは餌を与えています-D__SSE2__ -D__SSE3__ -D__SSSE3__<newline>(改行awkを追加echo)。

の場合、これRS=' 'は3つのレコードを意味します。一致するすべての項目が印刷され、その後に出力レコード区切り記号()が表示されます。 3番目のケースは-D__SSE2__-D__SSE3__-D__SSSE3__<newline>/SSE/ORS=' '-D__SSSE3__<newline><space>

<newline>したがって、ここでは最初に出力したくありません。

printf %s '-D__SSE2__ -D__SSE3__ -D__SSSE3__' | awk...

<newline>または、独自のレコードを持つようにスペースを追加します(一致しません/SSE/)。

echo '-D__SSE2__ -D__SSE3__ -D__SSSE3__ ' | awk...

または、Solaris ではなく GNU を使用しているので、空白awk文字シーケンスをレコード区切り文字として使用します。

echo -D__SSE2__ -D__SSE3__ -D__SSSE3__ | gawk -v 'RS=[[:space:]]+' ...

おすすめ記事