--- /dev/null
+#!/usr/bin/perl -w
+
+use v5.38;
+use List::Util qw(product);
+
+my %types;
+my %dests;
+my %ffs;
+my %inps;
+
+while (<>) {
+ my ($src, @dst) = /\w+/g;
+ ($types{$src}) = /^(\W)/;
+ @{ $dests{$src} } = @dst;
+ $inps{$_}->{$src} = 0 for @dst;
+}
+
+my @sums = (0, 0);
+
+sub snd {
+ my ($q, $name, $pulse) = @_;
+ for (@{ $dests{$name} }) {
+ push @$q, [ $_ , $pulse, $name ];
+ $sums[$pulse]++;
+ }
+}
+
+for (1 .. 1000) {
+ my @q = ([ 'broadcaster', 0, 'button' ]);
+ $sums[0]++;
+ while (@q) {
+ my $p = shift @q;
+ my ($name, $pulse, $origin) = @$p;
+ my $type = $types{$name} // '';
+
+ if ($type eq '%') {
+ if (!$pulse) {
+ $ffs{$name} = !$ffs{$name};
+ snd(\@q, $name, $ffs{$name});
+ }
+ } elsif ($type eq '&') {
+ my $in = $inps{$name};
+ $in->{$origin} = $pulse;
+ my $out = 1;
+ $out *= $_ for values %$in;
+ snd(\@q, $name, !$out);
+ } else {
+ snd(\@q, $name, 0);
+ }
+ }
+}
+
+say "@sums -> ", product @sums;
+
--- /dev/null
+#!/usr/bin/perl -w
+
+use v5.38;
+use List::Util qw(product);
+
+my %types;
+my %dests;
+my %ffs;
+my %inps;
+
+while (<>) {
+ my ($src, @dst) = /\w+/g;
+ ($types{$src}) = /^(\W)/;
+ @{ $dests{$src} } = @dst;
+ $inps{$_}->{$src} = 0 for @dst;
+}
+
+my $iters;
+
+my ($mainnode) = keys %{ $inps{rx} };
+my %prev;
+my %recv;
+my %period;
+sub snd {
+ my ($q, $name, $pulse) = @_;
+ $pulse = $pulse ? 1 : 0;
+ for (@{ $dests{$name} }) {
+ push @$q, [ $_ , $pulse, $name ];
+ if ($_ eq $mainnode && $pulse) {
+ my $p = $prev{$name};
+ $prev{$name} = $iters;
+ next if !$p;
+ $period{$name} = $iters - $p;
+ say "$name -$pulse-> $_ $period{$name}";
+ }
+ $recv{$_}->[$pulse]++;
+ }
+}
+
+while (grep { !$period{$_} } keys %{ $inps{$mainnode} }) {
+ %recv = ();
+ $iters++;
+ my @q = ([ 'broadcaster', 0, 'button' ]);
+ while (@q) {
+ my $p = shift @q;
+ my ($name, $pulse, $origin) = @$p;
+ my $type = $types{$name} // '';
+
+ if ($type eq '%') {
+ if (!$pulse) {
+ $ffs{$name} = !$ffs{$name};
+ snd(\@q, $name, $ffs{$name});
+ }
+ } elsif ($type eq '&') {
+ my $in = $inps{$name};
+ $in->{$origin} = $pulse;
+ my $out = 1;
+ $out *= $_ for values %$in;
+ snd(\@q, $name, !$out);
+ } else {
+ snd(\@q, $name, 0);
+ }
+ }
+}
+
+say product map { $period{$_} } keys %{ $inps{$mainnode} };