Как анализировать выбранные выражения до конца ключевого слова в pyparsing - PullRequest
1 голос
/ 03 апреля 2012

Я анализирую файл verilog для извлечения зависимостей внутри него. Мне не нужно анализировать большую часть содержимого модуля, но меня интересуют только операторы include и экземпляры модулей. Сначала я пытаюсь извлечь только включаемые операторы. Это мой код:

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

Моя точка зрения заключается в том, что я буду либо соответствовать прагме include, либо строке чего-либо, пока не достигну "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:('.*')} -> ['']

Что-то, что я делаю, заставляет позицию разбора не двигаться вперед?

1 Ответ

2 голосов
/ 04 апреля 2012

Проблема была в использовании выражения restOfLine. Это может соответствовать чему угодно, включая ''. Таким образом, синтаксический анализатор будет действовать следующим образом:

  1. Совпадение include "InternalInclude.v"
  2. Совпадение '' с restOfLine
  3. Сопоставьте тот же '' с restOfLine, потому что он не потреблял \ n И еще есть \ ', оставшийся до \ n, как всегда будет;)

Чтобы исправить это, я изменил restOfLine на (restOfLine + lineEnd). Это заставило парсер использовать \ n после сопоставления строки. Новый парсер читает:

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