From 8542895c95954f8bd015ba8436371a6bbdcf78c7 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?John=20Ankarstr=C3=B6m?= Date: Sat, 10 Jul 2021 17:35:21 +0200 Subject: Rename project to ref --- greet.ms | 2 +- re | 136 --------------------------------------------------------------- re.tmac | 50 ----------------------- ref | 136 +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ ref.tmac | 50 +++++++++++++++++++++++ 5 files changed, 187 insertions(+), 187 deletions(-) delete mode 100755 re delete mode 100644 re.tmac create mode 100755 ref create mode 100644 ref.tmac diff --git a/greet.ms b/greet.ms index 99c9de1..5368ede 100644 --- a/greet.ms +++ b/greet.ms @@ -1,4 +1,4 @@ -.so re.tmac +.so ref.tmac .TL .BI greet , an example C program diff --git a/re b/re deleted file mode 100755 index 415de0f..0000000 --- a/re +++ /dev/null @@ -1,136 +0,0 @@ -#!/usr/bin/perl - -# re -- reference-based literate programming system - -use strict; -use warnings; -use POSIX::Regex qw/:all/; - -my $bytes; -my $count; -my %bytes; # file => current byte -my %file_locations; # file => [location, ...] -my %files; # byte => file -my %handles; # file => handle -my %lines; # file => current line -my %locations; # byte => location (i.e. byte in source file) -my @references; - -die "usage: $0 file\n" if @ARGV != 1; -open my $fh, '<', $ARGV[0] or die "could not open $ARGV[0]: $!\n"; - -# collect references -$bytes = 0; -while (<$fh>) { - $bytes += length($_); - push @references, [$bytes, $1] if /^\.\s*Re\s+(.*)/; -} - -# find referenced locations -for (@references) { - my ($bytes, $ref) = @$_; - my $loc = -1; - - goto invalid if not $ref =~ /^([^:]+):(.*)/; - my ($file, $ident) = ($1, $2); - - if (not exists $handles{$file}) { - open my $fh, '<', $file or die "could not open $file: $!\n"; - $handles{$file} = $fh; - $bytes{$file} = 0; - $lines{$file} = 0; - } - - if ($ident =~ /^(\d+)$/) { - my $line = $1; - if ($ident <= $lines{$file}) { - seek $handles{$file}, 0, 0; - $bytes{$file} = 0; - $lines{$file} = 0; - } - local $_; - while ($_ = readline $handles{$file}) { - $lines{$file}++; - if ($lines{$file} == $line) { - $loc = $bytes{$file}; - last; - } - $bytes{$file} += length($_); - } - } elsif ($ident =~ m{^/(.*)/$}) { - my $rx = new POSIX::Regex($1); - seek $handles{$file}, 0, 0; - $bytes{$file} = 0; - $lines{$file} = 0; - local $_; - while ($_ = readline $handles{$file}) { - $lines{$file}++; - chomp; - if ($rx->match($_)) { - $loc = $bytes{$file}; - last; - } - $bytes{$file} += length($_)+1; - } - } else { - goto invalid; - } - - die "could not find location $ident in $file\n" if $loc == -1; - $locations{$bytes} = $loc; - $files{$bytes} = $file; - if (exists $file_locations{$file}) { - push @{$file_locations{$file}}, $loc; - } else { - $file_locations{$file} = []; - } - - next; -invalid: - die "invalid syntax: $ref at $bytes\n"; -} - -# intertwine -seek $fh, 0, 0; -$bytes = 0; -$count = 0; -while (<$fh>) { - $bytes += length($_); - goto normal if not @references; - my $ref_bytes = $references[0][0]; - if ($bytes == $ref_bytes) { - shift @references; - my $file = $files{$bytes}; - my $end = shift @{$file_locations{$file}} || ''; - my $loc = $locations{$bytes}; - - print ".Sr $file $loc-$end\n"; - - seek $handles{$file}, $loc, 0; - local $_; - my $bytes = $loc; - while ($_ = readline $handles{$file}) { - $bytes += length($_); - last if $end and $bytes > $end; - /^(\s*)/; my $indent = $1; - my $max = 64; - for (split //, $indent) { - $max -= 7 if /\t/; - } - s/(.{$max})(.{6,})/$1\\fR...\\fP\n$indent\t$2/g; - s/\\/\\\\/g; - s/\\\\fR...\\\\fP/\\fR...\\fP/g; - s/^\./\\&./m; - print; - } - - print ".Se\n"; - - next; - } -normal: - print; -} - -close $_ for values %handles; -close $fh; diff --git a/re.tmac b/re.tmac deleted file mode 100644 index 1bf5a92..0000000 --- a/re.tmac +++ /dev/null @@ -1,50 +0,0 @@ -.\" configurable options -.\" -------------------- -.ds Sf C \" font -.nr Sp 8p \" point size -.nr Sv 11p \" vertical spacing (leading) -.nr St 8n \" tab width -.nr Tl 2i \" line length for text portions -.nr Td 0.7v \" distance between text portions -. -.\" setup -.\" ----- -.nr _L \n(LL \" save original line length -. -.\" macro definitions -.\" ----------------- -.eo -.\" Sr -- source code begin -.de Sr -. br -. mk c \" vertical position where text ends -. if (\nb > \nc) .sp (\nbu - \ncu) -. if (\nb > 0) .if ((\nc + 1p) > \nb) .sp \n(Tdu -. if !(\nz = 1) .if (\np > 0) .if (\n% > \np) .sp -(\nbu - \ncu - 1.5v) -. nf -. ft \*(Sf -. ps \n(Spu -. vs \n(Svu -. ta \n(Stu +\n(Stu +\n(Stu +\n(Stu +\n(Stu +\n(Stu -. in (\n(Tlu + 0.2i) -. mk a \" vertical position where source code begins -. nr p \n% \" current page number -.. -.\" Se -- source code end -.de Se -. mk b \" vertical position where source code ends -. rt \nau -. nr LL \n(Tl -. nr z 0 -. if (\n% > \np) \{ -. rt \n(HMu \" return to top of new page -. nr z 1 \" signal page break -. \} -. ns \" ignore space before text (like that added by LP/PP) -. LP -.. -.\" Rr -- reset document settings -.de Rr -.nr LL \n(_L -.. -.ec diff --git a/ref b/ref new file mode 100755 index 0000000..7322246 --- /dev/null +++ b/ref @@ -0,0 +1,136 @@ +#!/usr/bin/perl + +# ref -- reference-based literate programming system + +use strict; +use warnings; +use POSIX::Regex qw/:all/; + +my $bytes; +my $count; +my %bytes; # file => current byte +my %file_locations; # file => [location, ...] +my %files; # byte => file +my %handles; # file => handle +my %lines; # file => current line +my %locations; # byte => location (i.e. byte in source file) +my @references; + +die "usage: $0 file\n" if @ARGV != 1; +open my $fh, '<', $ARGV[0] or die "could not open $ARGV[0]: $!\n"; + +# collect references +$bytes = 0; +while (<$fh>) { + $bytes += length($_); + push @references, [$bytes, $1] if /^\.\s*Re\s+(.*)/; +} + +# find referenced locations +for (@references) { + my ($bytes, $ref) = @$_; + my $loc = -1; + + goto invalid if not $ref =~ /^([^:]+):(.*)/; + my ($file, $ident) = ($1, $2); + + if (not exists $handles{$file}) { + open my $fh, '<', $file or die "could not open $file: $!\n"; + $handles{$file} = $fh; + $bytes{$file} = 0; + $lines{$file} = 0; + } + + if ($ident =~ /^(\d+)$/) { + my $line = $1; + if ($ident <= $lines{$file}) { + seek $handles{$file}, 0, 0; + $bytes{$file} = 0; + $lines{$file} = 0; + } + local $_; + while ($_ = readline $handles{$file}) { + $lines{$file}++; + if ($lines{$file} == $line) { + $loc = $bytes{$file}; + last; + } + $bytes{$file} += length($_); + } + } elsif ($ident =~ m{^/(.*?)/?$}) { + my $rx = new POSIX::Regex($1); + seek $handles{$file}, 0, 0; + $bytes{$file} = 0; + $lines{$file} = 0; + local $_; + while ($_ = readline $handles{$file}) { + $lines{$file}++; + chomp; + if ($rx->match($_)) { + $loc = $bytes{$file}; + last; + } + $bytes{$file} += length($_)+1; + } + } else { + goto invalid; + } + + die "could not find location $ident in $file\n" if $loc == -1; + $locations{$bytes} = $loc; + $files{$bytes} = $file; + if (exists $file_locations{$file}) { + push @{$file_locations{$file}}, $loc; + } else { + $file_locations{$file} = []; + } + + next; +invalid: + die "invalid syntax: $ref at $bytes\n"; +} + +# intertwine +seek $fh, 0, 0; +$bytes = 0; +$count = 0; +while (<$fh>) { + $bytes += length($_); + goto normal if not @references; + my $ref_bytes = $references[0][0]; + if ($bytes == $ref_bytes) { + shift @references; + my $file = $files{$bytes}; + my $end = shift @{$file_locations{$file}} || ''; + my $loc = $locations{$bytes}; + + print ".Sr \"$file\" $loc $end\n"; + + seek $handles{$file}, $loc, 0; + local $_; + my $bytes = $loc; + while ($_ = readline $handles{$file}) { + $bytes += length($_); + last if $end and $bytes > $end; + /^(\s*)/; my $indent = $1; + my $max = 64; + for (split //, $indent) { + $max -= 7 if /\t/; + } + s/(.{$max})(.{6,})/$1\\fR...\\fP\n$indent\t$2/g; + s/\\/\\\\/g; + s/\\\\fR...\\\\fP/\\fR...\\fP/g; + s/^\./\\&./m; + print; + } + + print ".Se\n"; + + next; + } +normal: + print; +} + +close $_ for values %handles; +close $fh; diff --git a/ref.tmac b/ref.tmac new file mode 100644 index 0000000..1bf5a92 --- /dev/null +++ b/ref.tmac @@ -0,0 +1,50 @@ +.\" configurable options +.\" -------------------- +.ds Sf C \" font +.nr Sp 8p \" point size +.nr Sv 11p \" vertical spacing (leading) +.nr St 8n \" tab width +.nr Tl 2i \" line length for text portions +.nr Td 0.7v \" distance between text portions +. +.\" setup +.\" ----- +.nr _L \n(LL \" save original line length +. +.\" macro definitions +.\" ----------------- +.eo +.\" Sr -- source code begin +.de Sr +. br +. mk c \" vertical position where text ends +. if (\nb > \nc) .sp (\nbu - \ncu) +. if (\nb > 0) .if ((\nc + 1p) > \nb) .sp \n(Tdu +. if !(\nz = 1) .if (\np > 0) .if (\n% > \np) .sp -(\nbu - \ncu - 1.5v) +. nf +. ft \*(Sf +. ps \n(Spu +. vs \n(Svu +. ta \n(Stu +\n(Stu +\n(Stu +\n(Stu +\n(Stu +\n(Stu +. in (\n(Tlu + 0.2i) +. mk a \" vertical position where source code begins +. nr p \n% \" current page number +.. +.\" Se -- source code end +.de Se +. mk b \" vertical position where source code ends +. rt \nau +. nr LL \n(Tl +. nr z 0 +. if (\n% > \np) \{ +. rt \n(HMu \" return to top of new page +. nr z 1 \" signal page break +. \} +. ns \" ignore space before text (like that added by LP/PP) +. LP +.. +.\" Rr -- reset document settings +.de Rr +.nr LL \n(_L +.. +.ec -- cgit v1.2.3