diff options
author | Daniel Friesel <derf@finalrewind.org> | 2017-04-21 14:15:14 +0200 |
---|---|---|
committer | Daniel Friesel <derf@finalrewind.org> | 2017-04-21 14:15:14 +0200 |
commit | bc0bd155d03a8108badd441f8756739565fe300a (patch) | |
tree | d9621cb479402d65c514bfc9894f32ce8908dd7f | |
parent | f79cec3648491e7d178b372bcc1beaea9baaadef (diff) |
allow setting static params via LUT
-rwxr-xr-x | bin/dfatool | 10 | ||||
-rw-r--r-- | lib/Kratos/DFADriver.pm | 24 | ||||
-rw-r--r-- | lib/Kratos/DFADriver/DFA.pm | 5 | ||||
-rw-r--r-- | lib/Kratos/DFADriver/Model.pm | 29 |
4 files changed, 64 insertions, 4 deletions
diff --git a/bin/dfatool b/bin/dfatool index 6de30d9..75449a3 100755 --- a/bin/dfatool +++ b/bin/dfatool @@ -22,6 +22,7 @@ GetOptions( plot=s no-cache no-update + param-default=s@ state-duration=i shunt=f trace-filter=s@ @@ -31,6 +32,7 @@ GetOptions( voltage=f with-lut! offset=i + workload=s zomg-fasta-nao } ); @@ -41,6 +43,8 @@ if ( @ARGV < 2 ) { @{ $opt{'exclude-states'} } = split( qr{,}, join( q{,}, @{ $opt{'exclude-states'} // [] } ) ); +@{ $opt{'param-default'} } + = split( qr{,}, join( q{,}, @{ $opt{'param-default'} // [] } ) ); my ( $command, $xml_file, @data_files ) = @ARGV; @@ -60,6 +64,7 @@ my $driver = Kratos::DFADriver->new( mimosa_offset => $opt{offset} // 130, mimosa_shunt => $opt{shunt} // 330, mimosa_voltage => $opt{voltage} // 3.60, + param_default => $opt{'param-default'} // [], trace_filter => $opt{'trace-filter'} // [], trace_revisit => $opt{'trace-revisit'} // 2, with_lut => $opt{'with-lut'}, @@ -156,7 +161,10 @@ my %action = ( analyze => sub { $driver->analyze(@data_files); $driver->assess_model; - if ( not $opt{'no-update'} ) { + if ( $opt{workload} ) { + $driver->assess_workload($opt{workload}); + } + elsif ( not $opt{'no-update'} ) { $driver->update_model; } }, diff --git a/lib/Kratos/DFADriver.pm b/lib/Kratos/DFADriver.pm index 481dc67..466cf64 100644 --- a/lib/Kratos/DFADriver.pm +++ b/lib/Kratos/DFADriver.pm @@ -11,6 +11,7 @@ use AspectC::Repo; use Carp; use Carp::Assert::More; use Cwd; +use Data::Dumper; use DateTime; use Device::SerialPort; use File::Slurp qw(read_dir read_file write_file); @@ -554,6 +555,21 @@ sub assess_model_tex { say '\end{tabular}'; } +sub assess_workload { + my ($self, $workload) = @_; + + $workload =~ s{ \s* \) \s* ; \s* }{:}gx; + $workload =~ s{ \s* \) \s* $ }{}gx; + $workload =~ s{ \s* ; \s* }{!:}gx; + $workload =~ s{ \s* \( \s* }{!}gx; + $workload =~ s{ \s* , \s* }{!}gx; + $workload =~ s{ [^!] \K $ }{!}gx; + + say $workload; + + my $traces = $self->dfa->run_str_to_trace($workload); +} + sub update_model { my ($self) = @_; @@ -739,10 +755,16 @@ sub to_cc { my $class_name = $self->{class_name}; my @state_enum = $self->model->get_state_enum; + my %param_default; + + for my $default_setting (@{$self->{param_default}}) { + my ($param, $value) = split(qr{ = }x, $default_setting); + $param_default{$param} = $value; + } my $buf = "DFA_Driver::power_uW_t ${class_name}::statepower[] = {" - . join( ', ', map { $self->model->get_state_power($_) } @state_enum ) + . join( ', ', map { sprintf('%.f', $self->model->get_state_power_with_params($_, \%param_default)) } @state_enum ) . "};\n"; return $buf; diff --git a/lib/Kratos/DFADriver/DFA.pm b/lib/Kratos/DFADriver/DFA.pm index db11a17..c17e054 100644 --- a/lib/Kratos/DFADriver/DFA.pm +++ b/lib/Kratos/DFADriver/DFA.pm @@ -143,6 +143,11 @@ sub run_str_to_trace { $self->model->update_parameter_hash( \%param, $cmd, @args ); ($state) = $dfa->successors( $state, ":${transition_str}" ); + + if (not defined $state) { + die("Transition $transition_str is invalid or has no successors\n"); + } + $prev_transition = $transition; for my $extra_cmd ( $self->model->get_state_extra_transitions( diff --git a/lib/Kratos/DFADriver/Model.pm b/lib/Kratos/DFADriver/Model.pm index 18bccfe..9f4f3f4 100644 --- a/lib/Kratos/DFADriver/Model.pm +++ b/lib/Kratos/DFADriver/Model.pm @@ -65,6 +65,13 @@ sub parse_xml_property { $param_idx++; } } + for my $lut_node ( $property_node->findnodes('./lut/*') ) { + my @paramkey = map { $_->[0]->getValue } + sort { $a->[1] cmp $b->[1] } + map { [ $_, $_->nodeName ] } + @{$lut_node->attributes->nodes}; + $ret->{lut}{join(';', @paramkey)} = 0 + $lut_node->textContent; + } return $ret; } @@ -95,12 +102,11 @@ sub parse_xml { my $param_name = $param_node->getAttribute('name'); my $function_name = $param_node->getAttribute('functionname'); my $function_arg = $param_node->getAttribute('functionparam'); - my $default = $param_node->textContent; $self->{parameter}{$param_name} = { function => $function_name, arg_name => $function_arg, - default => $default, + default => undef, }; } @@ -528,6 +534,25 @@ sub get_state_power { return $self->{states}{$name}{power}{static}; } +sub get_state_power_with_params { + my ($self, $name, $param_values) = @_; + + my $hash_str = join(';', map { $param_values->{$_} } + sort { $a cmp $b } keys %{$param_values} ); + + if (not $hash_str) { + return $self->get_state_power($name); + } + + if (exists $self->{states}{$name}{power}{lut}{$hash_str}) { + return $self->{states}{$name}{power}{lut}{$hash_str}; + } + + say "Note: No matching LUT for state ${name}, using median"; + + return $self->get_state_power($name); +} + sub get_state_enum { my ($self) = @_; |