#!/usr/bin/env -S perl -w ########################################### ## derivgen.pl ## ## Written: David_Harris@hmc.edu ## Created: 29 January 2024 ## Modified: ## ## Purpose: Read config/derivlist.txt and generate config/deriv/*/config.vh ## derivative configurations from the base configurations ## ## A component of the CORE-V-WALLY configurable RISC-V project. ## https://github.com/openhwgroup/cvw ## https://github.com/openhwgroup/cvw ## ## Copyright (C) 2021-23 Harvey Mudd College & Oklahoma State University ## ## SPDX-License-Identifier: Apache-2.0 WITH SHL-2.1 ## ## Licensed under the Solderpad Hardware License v 2.1 (the “License”); you may not use this file ## except in compliance with the License, or, at your option, the Apache License version 2.0. You ## may obtain a copy of the License at ## ## https:##solderpad.org/licenses/SHL-2.1/ ## ## Unless required by applicable law or agreed to in writing, any work distributed under the ## License is distributed on an “AS IS” BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, ## either express or implied. See the License for the specific language governing permissions ## and limitations under the License. ################################################################################################ use strict; use warnings; import os; use Data::Dumper; my $curderiv = ""; my @derivlist = (); my %derivs; my %basederiv; my @derivnames = (); if ($#ARGV != -1) { die("Usage: $0") } my $derivlist = "$ENV{WALLY}/config/derivlist.txt"; open(my $fh, $derivlist) or die "Could not open file '$derivlist' $!"; foreach my $line (<$fh>) { chomp $line; my @tokens = split('\s+', $line); if ($#tokens < 0 || $tokens[0] =~ /^#/) { # skip blank lines and comments next; } if ($tokens[0] =~ /deriv/) { # start of a new derivative &terminateDeriv(); $curderiv = $tokens[1]; $basederiv{$curderiv} = $tokens[2]; @derivlist = (); if ($#tokens > 2) { my $inherits = $derivs{$tokens[3]}; @derivlist = @{$inherits}; } } else { # add to the current derivative $line =~ /\s*(\S+)\s*(.*)/; my @entry = ($1, $2); push(@derivlist, \@entry); } } &terminateDeriv(); close($fh); system("rm -rf $ENV{WALLY}/config/deriv"); #foreach my $key (keys %derivs) { foreach my $key (@derivnames) { my $dir = "$ENV{WALLY}/config/deriv/$key"; system("mkdir -p $dir"); my $configunmod = "$dir/config_unmod.vh"; my $config = "$dir/config.vh"; my $base = "$ENV{WALLY}/config/$basederiv{$key}/config.vh"; if (! -e $base) { $base = "$ENV{WALLY}/config/deriv/$basederiv{$key}/config.vh"; #if (! -e $base) { # die("Unable to find base config $base for $key\n"); #} } system("cp $base $configunmod"); open(my $unmod, $configunmod) or die "Could not open file '$configunmod' $!"; open(my $fh, '>>', $config) or die "Could not open file '$config' $!"; # Create symlink to imperas.ic for deriv buildroot if ($key eq "buildroot") { my $baseimperas_ic = "$ENV{WALLY}/config/$basederiv{$key}/imperas.ic"; if (! -e $baseimperas_ic) { my $baseimperas_ic = "$ENV{WALLY}/config/deriv/$basederiv{$key}/config.vh"; } if (-e $baseimperas_ic) { # If imperas.ic exists for base derivative, create hardlink to it my $imperas_ic = "$dir/imperas.ic"; system("ln -T $baseimperas_ic $imperas_ic"); } } my $datestring = localtime(); my %hit = (); print $fh "// Config $key automatically derived from $basederiv{$key} on $datestring using derivgen.pl\n"; foreach my $line (<$unmod>) { foreach my $entry (@{$derivs{$key}}) { my @ent = @{$entry}; my $param = $ent[0]; my $value = $ent[1]; if ($line =~ s/\b$param\s*=\s*.*;/$param = $value;/) { $hit{$param} = 1; # print("Hit: new line in $config for $param is $line"); } } print $fh $line; } close($fh); close($unmod); foreach my $entry (@{$derivs{$key}}) { my @ent = @{$entry}; my $param = $ent[0]; if (!exists($hit{$param})) { print("Unable to find $param in $key\n"); } } system("rm -f $dir/config_unmod.vh"); } sub terminateDeriv { if ($curderiv ne "") { # close out the previous derivative my @dl = @derivlist; $derivs{$curderiv} = \@dl; push(@derivnames, $curderiv); } }; sub printref { my $ref = shift; my @array = @{$ref}; foreach my $entry (@array) { print join('_', @{$entry}), ', '; } print("\n"); }