Line 1... |
Line 1... |
#!/usr/bin/perl -w
|
#!/usr/bin/perl -w
|
# $Id: vbomconv 433 2011-11-27 22:04:39Z mueller $
|
# $Id: vbomconv 456 2012-02-05 22:19:44Z mueller $
|
#
|
#
|
# Copyright 2007-2011 by Walter F.J. Mueller
|
# Copyright 2007-2012 by Walter F.J. Mueller
|
#
|
#
|
# This program is free software; you may redistribute and/or modify it under
|
# This program is free software; you may redistribute and/or modify it under
|
# the terms of the GNU General Public License as published by the Free
|
# the terms of the GNU General Public License as published by the Free
|
# Software Foundation, either version 2, or at your option any later version.
|
# Software Foundation, either version 2, or at your option any later version.
|
#
|
#
|
Line 12... |
Line 12... |
# or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
|
# or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
|
# for complete details.
|
# for complete details.
|
#
|
#
|
# Revision History:
|
# Revision History:
|
# Date Rev Version Comment
|
# Date Rev Version Comment
|
|
# 2012-02-05 456 1.9.4 redo filename substitution (= and :); add --get_top
|
|
# 2012-01-02 448 1.9.3 use in ghdl_m -fexplicit also when simprim used
|
# 2011-11-27 433 1.9.2 use in ghdl_m -fexplicit when unisim used
|
# 2011-11-27 433 1.9.2 use in ghdl_m -fexplicit when unisim used
|
# 2011-08-13 405 1.9.1 always write 'vhdl' into xst prj files again; for
|
# 2011-08-13 405 1.9.1 always write 'vhdl' into xst prj files again; for
|
# -xst_export: remove opt file export, add ucf_cpp
|
# -xst_export: remove opt file export, add ucf_cpp
|
# handling
|
# handling
|
# 2011-06-26 385 1.9 add --ise_path, pass it to vbomconv --xst_prj
|
# 2011-06-26 385 1.9 add --ise_path, pass it to vbomconv --xst_prj
|
Line 59... |
Line 61... |
"ghdl_i", "ghdl_i_cmd",
|
"ghdl_i", "ghdl_i_cmd",
|
"ghdl_m", "ghdl_m_cmd",
|
"ghdl_m", "ghdl_m_cmd",
|
"xst_export=s",
|
"xst_export=s",
|
"ghdl_export=s",
|
"ghdl_export=s",
|
"isim_export=s",
|
"isim_export=s",
|
|
"get_top",
|
"flist") || exit 1;
|
"flist") || exit 1;
|
|
|
sub print_help;
|
sub print_help;
|
sub read_vbom;
|
sub read_vbom;
|
sub scan_vbom;
|
sub scan_vbom;
|
sub copy_edir;
|
sub copy_edir;
|
sub write_vbomdep;
|
sub write_vbomdep;
|
|
sub canon_fname;
|
|
|
my @vbom_list;
|
my @vbom_list;
|
my @file_list;
|
my @file_list;
|
my %vbom_tbl;
|
my %vbom_tbl;
|
my %file_tbl;
|
my %file_tbl;
|
my %read_tbl;
|
my %read_tbl;
|
my %conf_tbl;
|
my %para_tbl;
|
my @ucf_cpp_list;
|
my @ucf_cpp_list;
|
my $is_xst = 0; # XST synthesis target
|
my $is_xst = 0; # XST synthesis target
|
my $is_ghdl = 0; # ghdl simulation target
|
my $is_ghdl = 0; # ghdl simulation target
|
my $is_isim = 0; # ISim simulation target
|
my $is_isim = 0; # ISim simulation target
|
my $is_sim = 0; # simulation target (generic)
|
my $is_sim = 0; # simulation target (generic)
|
Line 194... |
Line 198... |
|
|
# --trace ------------------------------------------------------------
|
# --trace ------------------------------------------------------------
|
|
|
if ($do_trace) {
|
if ($do_trace) {
|
print STDERR "\n";
|
print STDERR "\n";
|
print STDERR "configuration table:\n";
|
print STDERR "filename substitution table:\n";
|
foreach (sort keys %conf_tbl) {
|
foreach (sort keys %para_tbl) {
|
print STDERR " $_ = $conf_tbl{$_}\n";
|
print STDERR " $_ = $para_tbl{$_}\n";
|
}
|
}
|
print STDERR "final file_list:\n";
|
print STDERR "final file_list:\n";
|
foreach (@file_list) {
|
foreach (@file_list) {
|
print STDERR " $_\n";
|
print STDERR " $_\n";
|
}
|
}
|
Line 223... |
Line 227... |
my $wrc = system "/bin/sh", "-c", $cmd;
|
my $wrc = system "/bin/sh", "-c", $cmd;
|
if ($wrc != 0) {
|
if ($wrc != 0) {
|
my $rc = int($wrc/256);
|
my $rc = int($wrc/256);
|
if ($rc == 0) {
|
if ($rc == 0) {
|
my $sig = $wrc % 256;
|
my $sig = $wrc % 256;
|
print STDERR "%vbomconv-I compilation aborted by signal $sig\n";
|
print STDERR "%vbomconv-I: compilation aborted by signal $sig\n";
|
exit(1);
|
exit(1);
|
} else {
|
} else {
|
print STDERR "%vbomconv-I compilation failed (rc=$rc) $?\n";
|
print STDERR "%vbomconv-I: compilation failed (rc=$rc) $?\n";
|
exit($rc);
|
exit($rc);
|
}
|
}
|
}
|
}
|
}
|
}
|
}
|
}
|
Line 295... |
Line 299... |
$cmd .= "rm $stem\n" ; # rm old executable to force elaboration
|
$cmd .= "rm $stem\n" ; # rm old executable to force elaboration
|
}
|
}
|
|
|
$cmd .= "ghdl -m";
|
$cmd .= "ghdl -m";
|
$cmd .= " -o $stem";
|
$cmd .= " -o $stem";
|
$cmd .= ' -fexplicit' if $has_unisim; # needed for ISE 13.1
|
# -fexplicit needed for ISE 13.1,13.3
|
|
$cmd .= ' -fexplicit' if $has_unisim or $has_simprim;
|
$cmd .= ' -P$XILINX/ghdl/unisim' if $has_unisim;
|
$cmd .= ' -P$XILINX/ghdl/unisim' if $has_unisim;
|
$cmd .= ' -P$XILINX/ghdl/simprim' if $has_simprim;
|
$cmd .= ' -P$XILINX/ghdl/simprim' if $has_simprim;
|
$cmd .= " --ieee=synopsys";
|
$cmd .= " --ieee=synopsys";
|
$cmd .= " --no-vital-checks" if $is_ssim or $is_fsim or $is_tsim;
|
$cmd .= " --no-vital-checks" if $is_ssim or $is_fsim or $is_tsim;
|
|
|
Line 517... |
Line 522... |
foreach(glob("*.ucf")) { copy_edir($_, $edir); }
|
foreach(glob("*.ucf")) { copy_edir($_, $edir); }
|
}
|
}
|
|
|
}
|
}
|
|
|
|
# --get_top ----------------------------------------------------------
|
|
|
|
if (exists $opts{get_top}) {
|
|
print "$top\n";
|
|
}
|
|
|
# --flist ------------------------------------------------------------
|
# --flist ------------------------------------------------------------
|
|
|
if (exists $opts{flist}) {
|
if (exists $opts{flist}) {
|
|
|
my @flist;
|
my @flist;
|
Line 573... |
Line 584... |
next if /^\s*#/; # drop comments
|
next if /^\s*#/; # drop comments
|
next if /^\s*$/; # drop empty lines
|
next if /^\s*$/; # drop empty lines
|
|
|
s/\s*$//; # drop trailing blanks
|
s/\s*$//; # drop trailing blanks
|
|
|
|
# process parameter definitions
|
|
if (m{([\w]+)\s*=\s*(.*)}) {
|
|
my $para = $1;
|
|
my $val = $2;
|
|
if ($val eq "") {
|
|
print STDERR "%vbomconv-E: invalid \'$_\' in $vbom_file\n";
|
|
exit 1;
|
|
}
|
|
if (not exists $para_tbl{$para}) {
|
|
$para_tbl{$para} = canon_fname($vbom_path, $val);
|
|
print STDERR "--- define \${$para} = $val\n" if $do_trace;
|
|
} else {
|
|
print STDERR "--- ignore \${$para} = $val\n" if $do_trace;
|
|
}
|
|
next;
|
|
}
|
|
|
|
# process parameter substitutions
|
|
while (m{\$\{([\w]+)\s*(:=)?\s*(.*?)\}}) {
|
|
my $para = $1;
|
|
my $del = $2;
|
|
my $val = $3;
|
|
my $pre = $`;
|
|
my $post = $';
|
|
if (defined $del && $del eq ":=") {
|
|
if (not exists $para_tbl{$para}) {
|
|
$para_tbl{$para} = canon_fname($vbom_path, $val);
|
|
print STDERR "--- define \${$para := $val}\n" if $do_trace;
|
|
} else {
|
|
print STDERR "--- ignore \${$para := $val}\n" if $do_trace;
|
|
}
|
|
}
|
|
if (defined $para_tbl{$para}) {
|
|
if ($do_trace) {
|
|
print STDERR "--- use \${$para} -> $para_tbl{$para}\n";
|
|
} else {
|
|
## print STDERR "%vbomconv-I: \${$para} -> $para_tbl{$para}\n";
|
|
}
|
|
$_ = $pre . "!" . $para_tbl{$para} . $post;
|
|
} else {
|
|
print STDERR "%vbomconv-E: undefined \${$para} in $vbom_file\n";
|
|
exit 1;
|
|
}
|
|
}
|
|
|
if (/^\[([a-z,]+)\]\s*(.+)$/) { # [xxx,yyy] tag seen
|
if (/^\[([a-z,]+)\]\s*(.+)$/) { # [xxx,yyy] tag seen
|
my $qual = $1;
|
my $qual = $1;
|
my $name = $2;
|
my $name = $2;
|
my $keep = $is_any;
|
my $keep = $is_any;
|
## print STDERR "+++1 |$qual|$name|$vbom|\n";
|
## print STDERR "+++1 |$qual|$name|$vbom|\n";
|
Line 597... |
Line 653... |
$_ = $name; # remove [xxx] tag
|
$_ = $name; # remove [xxx] tag
|
}
|
}
|
|
|
my $tag;
|
my $tag;
|
my $val = $_;
|
my $val = $_;
|
my $del;
|
|
|
|
# detect tag=val or tag:val lines
|
# detect tag:val lines
|
if (m{^\s*(.*?)\s*([=:])\s*(.*?)\s*$}) {
|
if (m{^\s*(.*?)\s*:\s*(.*?)\s*$}) {
|
$tag = $1;
|
$tag = $1;
|
$del = $2;
|
$val = $2;
|
$val = $3;
|
|
}
|
|
|
|
# process @top: lines
|
# process @top: lines
|
if (defined $del && $del eq ":" && $tag eq '@top') {
|
if ($tag eq '@top') {
|
$top = $val unless $top_done;
|
$top = $val unless $top_done;
|
next;
|
|
}
|
|
|
|
# process @ucf_cpp: lines
|
# process @ucf_cpp: lines
|
if (defined $del && $del eq ":" && $tag eq '@ucf_cpp') {
|
} elsif ($tag eq '@ucf_cpp') {
|
push @ucf_cpp_list, $val;
|
push @ucf_cpp_list, $val;
|
next;
|
|
}
|
|
|
|
# process @lib: lines
|
# process @lib: lines
|
if (defined $del && $del eq ":" && $tag eq '@lib') {
|
} elsif ($tag eq '@lib') {
|
if ($val eq 'unisim') {
|
if ($val eq 'unisim') {
|
$has_unisim = 1;
|
$has_unisim = 1;
|
} elsif ($val eq 'simprim') {
|
} elsif ($val eq 'simprim') {
|
$has_simprim = 1;
|
$has_simprim = 1;
|
} else {
|
} else {
|
die "unknown library type: $val";
|
print STDERR "%vbomconv-E: invalid lib type \'$tag\' in $vbom_file\n";
|
|
exit 1;
|
|
}
|
|
} else {
|
|
print STDERR "%vbomconv-E: invalid \'$tag:\' line in $vbom_file\n";
|
|
exit 1;
|
}
|
}
|
next;
|
next;
|
}
|
}
|
|
|
# now do _fsim, _tsim mapping
|
# now do _fsim, _tsim mapping
|
$val =~ s{_ssim\.vhd$}{_fsim.vhd} if $is_fsim;
|
$val =~ s{_ssim\.vhd$}{_fsim.vhd} if $is_fsim;
|
$val =~ s{_ssim\.vhd$}{_tsim.vhd} if $is_tsim;
|
$val =~ s{_ssim\.vhd$}{_tsim.vhd} if $is_tsim;
|
|
|
# process normal .vhd or .vbom file lines
|
# process normal .vhd or .vbom file lines
|
# get full relative file name (relative to cwd)
|
# canonize file name unless not already done by filename substitution
|
|
my $fullname;
|
my $fname = $val;
|
if ($val =~ m{^!(.*)$}) {
|
$fname = "$vbom_path/$fname" if $vbom_path ne "";
|
$fullname = $1;
|
|
|
# remove 'inner' .., e.g. ../x/../y --> ../y
|
|
# this will also canonize the file names, thus same file same name
|
|
|
|
my @flist;
|
|
foreach (split "/",$fname) {
|
|
if (scalar(@flist) && $flist[$#flist] ne ".." && $_ eq "..") {
|
|
pop @flist;
|
|
} else {
|
} else {
|
push @flist, $_;
|
$fullname = canon_fname($vbom_path, $val);
|
}
|
}
|
}
|
|
|
|
my $fullname = join "/", @flist;
|
|
|
|
# determine whether additional libs needed
|
# determine whether additional libs needed
|
if ($fullname =~ m{_ssim\.vhd$}) { # ends in _ssim.vhd
|
if ($fullname =~ m{_ssim\.vhd$}) { # ends in _ssim.vhd
|
$has_unisim = 1;
|
$has_unisim = 1;
|
}
|
}
|
if ($fullname =~ m{_[ft]sim\.vhd$}) { # ends in _fsim.vhd or _tsim.vhd
|
if ($fullname =~ m{_[ft]sim\.vhd$}) { # ends in _fsim.vhd or _tsim.vhd
|
$has_simprim = 1;
|
$has_simprim = 1;
|
}
|
}
|
|
|
# handle configuration statements (tag=val)
|
|
if (defined $del && $del eq "=") {
|
|
if (exists $conf_tbl{$tag}) {
|
|
print STDERR "--- ignore $tag = $fullname\n" if $do_trace;
|
|
} else {
|
|
$conf_tbl{$tag} = $fullname;
|
|
print STDERR "--- config $tag = $fullname\n" if $do_trace;
|
|
}
|
|
next;
|
|
}
|
|
|
|
# handle configurable lines (tag:val)
|
|
if (defined $del && $del eq ":") {
|
|
if (exists $conf_tbl{$tag}) {
|
|
$fullname = $conf_tbl{$tag};
|
|
print STDERR "--- use $tag = $fullname\n" if $do_trace;
|
|
} else {
|
|
print STDERR "--- use $tag = $fullname (default)\n" if $do_trace;
|
|
}
|
|
}
|
|
|
|
# build vbom table
|
# build vbom table
|
push @{$vbom_tbl{$vbom}}, $fullname;
|
push @{$vbom_tbl{$vbom}}, $fullname;
|
print STDERR "--- add $fullname\n" if $do_trace;
|
print STDERR "--- add $fullname\n" if $do_trace;
|
|
|
Line 757... |
Line 780... |
print "$target : $_\n";
|
print "$target : $_\n";
|
}
|
}
|
}
|
}
|
|
|
#-------------------------------------------------------------------------------
|
#-------------------------------------------------------------------------------
|
|
sub canon_fname {
|
|
my ($vpath,$fname) = @_;
|
|
# get full relative file name (relative to cwd)
|
|
$fname = "$vpath/$fname" if $vpath ne "";
|
|
|
|
# remove 'inner' .., e.g. ../x/../y --> ../y
|
|
# this will also canonize the file names, thus same file same name
|
|
|
|
my @flist;
|
|
foreach (split "/",$fname) {
|
|
if (scalar(@flist) && $flist[$#flist] ne ".." && $_ eq "..") {
|
|
pop @flist;
|
|
} else {
|
|
push @flist, $_;
|
|
}
|
|
}
|
|
|
|
return join "/", @flist;
|
|
}
|
|
|
|
#-------------------------------------------------------------------------------
|
|
|
sub print_help {
|
sub print_help {
|
print "usage: vbomconf file.vbom\n";
|
print "usage: vbomconf file.vbom\n";
|
print " --help this message\n";
|
print " --help this message\n";
|
print " --trace trace recursive processing of vbom's\n";
|
print " --trace trace recursive processing of vbom's\n";
|