-
Notifications
You must be signed in to change notification settings - Fork 0
/
Copy pathtemplatereplace.pl
executable file
·152 lines (124 loc) · 4.12 KB
/
templatereplace.pl
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
#!/usr/bin/perl -w
my $usage = <<EOUSAGE;
Usage: templatereplace.pl [ops] <templatefile> <subjectfile1> ...
The idea behind this simple script is to replace blocks of text in one
or more files with a standard block provided in a "template file".
This script first reads in the template file, making special note of
the first and last lines. It then reads in the subject files, one by
one. If it sees the first template file line in one of the files, it
deletes text in the subject file until it finds the last template
line. Then it replaces the deleted text with the verbatim contents of
the template file. Files that don't contain the first template line
are unchanged.
Example usage:
find . -name '*.[ch]' -o -name '*.cc' -o -name COPYING -o -iname '*.in' | xargs scripts/templatereplace.pl -v scripts/nmap.header.tmpl
find . -name '*.[ch]' -o -name '*.cc' -o -name COPYING -o -iname '*.in' | xargs scripts/templatereplace.pl -v scripts/nsock.header.tmpl
EOUSAGE
use Getopt::Std;
use English;
my $verbose = 0;
sub usage() { print $usage; exit(1); }
# This function processes a template file by reading in all the data
# from $tmpldata->{name} and filling in $tmpldata->{firstline},
# $tmpldata->{lastline}, and $tmpldata->{content} (the latter does
# not include firstline and lastline). This function will give an
# error and exit the program if there are problems.
sub process_tmpl($) {
my $tdata = shift();
my $line;
my $lastline;
my $lineno = 1;
if ($verbose) {
print "Reading in template file: " . $tdata->{fname} . "\n";
}
if (!open TMPL, "<" . $tdata->{fname}) {
print "FAILED to read in template file: " . $tdata->{fname} . "\n";
usage();
}
$tdata->{content} = "";
while($line = <TMPL>) {
if ($lineno == 1) {
$tdata->{firstline} = $line;
} else {
if ($lineno != 2) { $tdata->{content} .= $lastline; }
}
$lastline = $line;
$lineno++;
}
if ($lineno < 3) {
print "Template file " . $tdata->{fname} . " is not long enough! Muts be at least 3 lines (first, content, and last)\n";
}
$tdata->{lastline} = $lastline;
close TMPL;
}
sub process_subj($$) {
my ($subjectfile, $tmpl) = @_;
my $newfile = "";
my $state = 0;
my $line;
if (!open SUB, "<$subjectfile") {
print "FAILED to read in subject file ($subjectfile) - skipping\n";
return;
}
# No need to worry about perms since we are overwriting existing file.
# my $perm = (stat $subjectfile)[2];
# $perm = $perm & 0777; # We ONLY want mode (not type too) and no suid bits
while($line = <SUB>) {
if ($state == 0) {
# Haven't found the match begin yet
if ($line eq $tmpl->{firstline}) { $state = 1; }
else { $newfile .= $line; }
} elsif ($state == 1) {
# Am between the match begin and end
if ($line eq $tmpl->{lastline}) {
$state = 2;
$newfile .= $tmpl->{firstline};
$newfile .= $tmpl->{content};
$newfile .= $tmpl->{lastline};
}
# Otherwise do nothing
} else {
# Already did the match, now we just copy the lines verbatim.
$newfile .= $line;
}
}
close SUB;
if ($state == 0) {
if ($verbose) { print "$subjectfile -> no replacement\n"; }
} elsif ($state == 1) {
print "WARNING: $subjectfile had begin line but never ended - skipping\n";
} else {
# Yeah - we did the replacement so now lets write back the file.
if (!open SUBWRITE, ">$subjectfile") {
print "FAILED to write to subject file ($subjectfile) - $! - skipping\n";
return;
}
print SUBWRITE $newfile;
close SUBWRITE;
if ($verbose) {
print "$subjectfile -> replacement succeeded\n";
}
}
}
# MAIN
use vars qw($opt_h $opt_v);
if (!getopts("vh")) {
print STDERR "Invalid arguments\n";
usage();
}
if ($opt_h) {
usage();
}
if ($opt_v) {
$verbose = 1;
}
$tmpldata{fname} = shift();
process_tmpl(\%tmpldata);
if ($verbose) {
printf "Processed template:" . $tmpldata{fname} . "\nSeeking Start: " . $tmpldata{firstline} . " End: " . $tmpldata{lastline} . "\n";
}
# Now it is time to handle each subject file, one at a time.
my $subjectfile;
while($subjectfile = shift()) {
process_subj($subjectfile, \%tmpldata);
}