2012-04-03 6 views
1

Verilogファイルを解析してその中の依存関係を抽出しています。私はモジュールの内容の大部分を解析する必要はありませんが、インクルードステートメントとモジュールのインスタンス化だけに興味があります。私は最初にインクルード文だけを抽出しようとしています。これは、これまでの私のコードです:選択された式を構文解析の最後のキーワードまで解析する方法

include_pragma = Group(Keyword("`include") + quotedString + lineEnd.suppress()) 
module_definition = ZeroOrMore(~Keyword("endmodule") + MatchFirst([include_pragma, restOfLine])) + Keyword("endmodule") 

私のポイントは私が「ENDMODULE」に到達するまで、プラグマ、または何かの行を一致するかということです。この文法を次の文字列で試してみると、pyparsingは何らかの無限ループに陥ります。

`include "InternalInclude.v" 

localparam COMMA_WIDTH = 10; 

localparam UNKNOWN = 1'b0, 
      KNOWN = 1'b1; 

reg  [DATA_WIDTH-1:0] TtiuPosQ2; 
reg      TtiuDetQ2; 
reg  [   7:0] TtiuDetQ2Save; 

assign DebugQO = { DataQI,   // 65:34 
        TxTrainingEnQI, // 33 
        TtiuDetQ2,  // 32 
        TtiuPosQ2  // 31:0 
        }; 

always @(posedge Clk or posedge ResetI) begin 
    if (ResetI) begin 
     CommaPosQO <= {(DATA_WIDTH){1'b0}}; 
     CommaDetQO <= 0; 
     CommaPosQ1 <= {(DATA_WIDTH){1'b0}}; 
     CommaPosQ2 <= {(DATA_WIDTH){1'b0}}; 
     CommaDetQ2 <= 0; 
     StateQ <= 0; 

     CommaPosSaveQ <= {(DATA_WIDTH){1'b0}}; 
     TtiuPosQ1 <= 0; 
     TtiuPosQ2 <= 0; 
     TtiuDetQ2 <= 0; 
     TtiuDetQ2Save <= 8'h00; 
    end 
    else begin 
     CommaPosQO <= CommaPosC2; 
     CommaDetQO <= CommaDetC2; 
     CommaPosQ1 <= CommaPosC; 
     CommaPosQ2 <= CommaPosQ1; 
     CommaDetQ2 <= (| CommaPosQ1); 
     StateQ <= StateC; 
     CommaPosSaveQ <= CommaPosSaveC; 
     TtiuPosQ1 <= TtiuPosC1; 
     TtiuPosQ2 <= TtiuPosC2; 
     TtiuDetQ2 <= TtiuDetC2; 
     TtiuDetQ2Save <= TtiuDetQ2 ? 8'hFF : {1'b0, TtiuDetQ2Save[7:1]}; 
    end 
end 

endmodule 

私はおそらく〜演算子を誤解しています。助言がありますか?

更新

setDebug()メソッドを提案し使用した後、私は無限ループがこれを印刷していることが見つかりました:

Match {Group:({"`include" quotedString using single or double quotes Suppress:(lineEnd)}) | Re:('.*')} at loc 0(1,1) 
Matched {Group:({"`include" quotedString using single or double quotes Suppress:(lineEnd)}) | Re:('.*')} -> [['`include' 
, '"InternalInclude.v"']] 
Match {Group:({"`include" quotedString using single or double quotes Suppress:(lineEnd)}) | Re:('.*')} at loc 31(4,1) 
Matched {Group:({"`include" quotedString using single or double quotes Suppress:(lineEnd)}) | Re:('.*')} -> [''] 
Match {Group:({"`include" quotedString using single or double quotes Suppress:(lineEnd)}) | Re:('.*')} at loc 31(4,1) 
Matched {Group:({"`include" quotedString using single or double quotes Suppress:(lineEnd)}) | Re:('.*')} -> [''] 
Match {Group:({"`include" quotedString using single or double quotes Suppress:(lineEnd)}) | Re:('.*')} at loc 31(4,1) 
Matched {Group:({"`include" quotedString using single or double quotes Suppress:(lineEnd)}) | Re:('.*')} -> [''] 

は私が前進しない解析位置を引き起こして何かですか?

+2

変更 'Or'をやってみたいです。 'setDebug()'を使用して、特定の式の解析アクティビティを監視できます。 'setDebug'は構文解析時のあらゆる試みを報告し、解析が成功したか失敗したかを報告します。あなたの文法の 'restOfLine'を' restofLine.setDebug() 'に変更し、この出力が役に立つかどうかを調べてみてください。 – PaulMcG

+0

@PaulMcGuireあなたが言ったことを試してみましたが、私の編集のように出力がありました。 –

+0

@PaulMcGuire私の答えを参照 –

答えて

1

問題は、restOfLine式を使用して問題が発生しました。それは ''を含む何でもマッチすることができます。以下のように、パーサは進行する:

それは\を消費nは、まだ存在していなかったのでrestOfLineに include "InternalInclude.v"
  • 「restOfLine
  • 一致させるために同じ」マッチ「」を一致
    1. 「」を左に\ nの前に、とalwasyがあるでしょう。

    はそれを修正するために)、私は(restOfLine + lineEnd)restOfLineを変更しました。これは、行にマッチした後、パーサが\ nを消費するように強制しました。新しいパーサーは、読み込ん: `MatchFirst`は、あなたがincludeディレクティブと一致したときにOr``と余分な作業を行っている、そして実際には、おそらくあなたは* *ないテストを行っているに

    include_pragma = Group(Keyword("`include") + quotedString + lineEnd.suppress()) 
    module_definition = ZeroOrMore(~Keyword("endmodule") + MatchFirst([include_pragma, (restOfLine + lineEnd)])) + Keyword("endmodule") 
    
  • +1

    また、parseStringの代わりにscanStringまたはsearchStringを使用する方法もあります。 scan/searchStringは、ファイルの一部を取り出すだけで、全体を解析しないときに便利です。私はあなたがたぶん '(include_pragma | Keyword(" endmodule "))。scanString(verilog_text)'で逃げるかもしれないと思います。 – PaulMcG