Test-based design modification
From Verific Design Automation FAQ
C++:
#include <iostream>
#include "veri_file.h"
#include "VeriModule.h"
#include "VeriStatement.h"
#include "Array.h"
#include "Strings.h"
#include "TextBasedDesignMod.h"
#ifdef VERIFIC_NAMESPACE
using namespace Verific ;
#endif
void CommentStmtInParseTree(VeriModule *mod)
{
if (!mod) return ;
Array *mod_items = mod->GetModuleItems() ;
unsigned i ;
VeriModuleItem *item ;
FOREACH_ARRAY_ITEM(mod_items, i, item) {
if (!item) continue ;
// Get statement from the module item (initial block)
VeriStatement *stmt = item->GetStmt() ;
if (!stmt) continue ;
// Get all statements from the statement (squential block in initial block)
Array *stmts = stmt->GetStatements() ;
if (stmts) {
unsigned j ;
VeriStatement *child ;
// Iterate over the child statement:
FOREACH_ARRAY_ITEM(stmts, j, child) {
if (!child) continue ;
// Get the string of the statement:
char *tmp = child->GetPrettyPrintedString() ;
// Remove the last new-line:
unsigned len = Strings::len(tmp) ;
if (!tmp || !len) continue ;
if (tmp[len-1] == '\n') tmp[len-1] = '\0' ;
// Comment out the string:
char *str = Strings::save("/* ", tmp, " */") ;
Strings::free(tmp) ;
// Create a null statement:
VeriStatement *new_stmt = new VeriNullStatement() ;
new_stmt->SetLinefile(child->Linefile()) ;
// Create a comment node with the comment string:
VeriCommentNode *comment = new VeriCommentNode(child->Linefile()) ;
comment->AppendComment(str) ;
Strings::free(str) ;
// Add the comment on the null-statement:
Array *comments = new Array(1) ;
comments->InsertLast(comment) ;
new_stmt->AddComments(comments) ;
// Finally replace the original statement with the created null-statement:
if (!stmt->ReplaceChildStmt(child, new_stmt, 1 /* delete old stmt */)) delete new_stmt ;
}
} else {
// Get the string of the statement:
char *tmp = stmt->GetPrettyPrintedString() ;
// Remove the last new-line:
unsigned len = Strings::len(tmp) ;
if (!tmp || !len) continue ;
if (tmp[len-1] == '\n') tmp[len-1] = '\0' ;
// Comment out the string:
char *str = Strings::save("/* ", tmp, " */") ;
Strings::free(tmp) ;
// Create a null statement:
VeriStatement *new_stmt = new VeriNullStatement() ;
new_stmt->SetLinefile(stmt->Linefile()) ;
// Create a comment node with the comment string:
VeriCommentNode *comment = new VeriCommentNode(stmt->Linefile()) ;
comment->AppendComment(str) ;
Strings::free(str) ;
// Add the comment on the null-statement:
Array *comments = new Array(1) ;
comments->InsertLast(comment) ;
new_stmt->AddComments(comments) ;
// Finally replace the original statement with the created null-statement:
if (!item->ReplaceChildStmt(stmt, new_stmt, 1 /* delete old stmt */)) delete new_stmt ;
}
}
veri_file::PrettyPrint("test_pp.v.golden.new", 0) ;
}
void CommentStmtViaTBDM(VeriModule *mod, TextBasedDesignMod &tbdm)
{
if (!mod) return ;
Array *mod_items = mod->GetModuleItems() ;
unsigned i ;
VeriModuleItem *item ;
FOREACH_ARRAY_ITEM(mod_items, i, item) {
if (!item) continue ;
// Get statement from the module item (initial block)
VeriStatement *stmt = item->GetStmt() ;
if (!stmt) continue ;
// Get all statements from the statement (squential block in initial block)
Array *stmts = stmt->GetStatements() ;
if (stmts) {
unsigned j ;
VeriStatement *child ;
// Iterate over the child statement:
FOREACH_ARRAY_ITEM(stmts, j, child) {
if (!child) continue ;
// Comment the whole statement:
tbdm.InsertBefore(child->Linefile(), "; /* ") ;
tbdm.InsertAfter(child->Linefile(), " */") ;
}
} else {
// Comment the whole statement:
tbdm.InsertBefore(stmt->Linefile(), "; /* ") ;
tbdm.InsertAfter(stmt->Linefile(), " */") ;
}
}
}
int main(int argc, const char **argv)
{
if (!veri_file::Analyze("test.v")) return 1 ;
VeriModule *mod = veri_file::GetModule("test") ;
if (!mod) return 2 ;
CommentStmtInParseTree(mod) ;
TextBasedDesignMod tbdm(0) ;
CommentStmtViaTBDM(mod, tbdm) ;
tbdm.WriteFile("test.v", "test_out.v.golden.new") ;
return 0 ;
}
Input Verilog:
module test ;
reg A, b ;
initial
A = b ;
initial
begin
A = b ;
end
endmodule
Output Verilog:
module test ;
reg A, b ;
initial
; /* A = b ; */
initial
begin
; /* A = b ; */
end
endmodule