]>
Commit | Line | Data |
---|---|---|
5002372c | 1 | #!/usr/bin/perl |
20d3226a | 2 | # |
5002372c | 3 | # setup-openssh.pl |
4 | # | |
95f536ac | 5 | # Adapts the installed gsi-openssh environment to the current machine, |
5002372c | 6 | # performing actions that originally occurred during the package's |
7 | # 'make install' phase. | |
701aa556 | 8 | # |
1eab725d | 9 | # Send comments/fixes/suggestions to: |
10 | # Chase Phillips <cphillip@ncsa.uiuc.edu> | |
701aa556 | 11 | # |
20d3226a | 12 | |
1b936a7a | 13 | printf("setup-openssh.pl: Configuring gsi-openssh package\n"); |
14 | ||
7e12c9a7 | 15 | # |
16 | # Get user's GPT_LOCATION since we may be installing this using a new(er) | |
17 | # version of GPT. | |
18 | # | |
19 | ||
20 | $gptpath = $ENV{GPT_LOCATION}; | |
21 | ||
22 | # | |
23 | # And the old standby.. | |
24 | # | |
25 | ||
4f276ad7 | 26 | $gpath = $ENV{GLOBUS_LOCATION}; |
ad71c979 | 27 | if (!defined($gpath)) |
28 | { | |
53a54c67 | 29 | die "GLOBUS_LOCATION needs to be set before running this script" |
ad71c979 | 30 | } |
31 | ||
32 | # | |
33 | # i'm including this because other perl scripts in the gpt setup directories | |
34 | # do so | |
35 | # | |
36 | ||
7e12c9a7 | 37 | if (defined($gptpath)) |
38 | { | |
39 | @INC = (@INC, "$gptpath/lib/perl", "$gpath/lib/perl"); | |
40 | } | |
41 | else | |
42 | { | |
43 | @INC = (@INC, "$gpath/lib/perl"); | |
44 | } | |
ad71c979 | 45 | |
4f276ad7 | 46 | require Grid::GPT::Setup; |
47 | ||
ad71c979 | 48 | my $globusdir = $gpath; |
ad71c979 | 49 | my $myname = "setup-openssh.pl"; |
50 | ||
20d3226a | 51 | # |
52 | # Set up path prefixes for use in the path translations | |
53 | # | |
54 | ||
d0a1bda7 | 55 | $prefix = ${globusdir}; |
56 | $exec_prefix = "${prefix}"; | |
57 | $bindir = "${exec_prefix}/bin"; | |
95f536ac | 58 | $sysconfdir = "$prefix/etc/ssh"; |
59 | $localsshdir = "/etc/ssh"; | |
e9ec5455 | 60 | |
95f536ac | 61 | my $keyfiles = { |
62 | "dsa" => "ssh_host_dsa_key", | |
63 | "rsa" => "ssh_host_rsa_key", | |
64 | "rsa1" => "ssh_host_key", | |
65 | }; | |
823981ba | 66 | |
67 | # | |
68 | # Check that we are running as root | |
69 | # | |
70 | ||
71 | $uid = $>; | |
72 | ||
73 | if ($uid != 0) | |
74 | { | |
75 | print "--> NOTE: You must be root to run this script! <--\n"; | |
76 | exit 0; | |
77 | } | |
e9ec5455 | 78 | |
95f536ac | 79 | sub copyKeyFiles |
e9ec5455 | 80 | { |
95f536ac | 81 | my($copylist) = @_; |
82 | my($regex, $basename); | |
e9ec5455 | 83 | |
95f536ac | 84 | print "Copying ssh host keys...\n"; |
e9ec5455 | 85 | |
95f536ac | 86 | for my $f (@$copylist) |
e9ec5455 | 87 | { |
95f536ac | 88 | $f =~ s:/+:/:g; |
e9ec5455 | 89 | |
95f536ac | 90 | if (length($f) > 0) |
91 | { | |
92 | $keyfile = "$f"; | |
93 | $pubkeyfile = "$f.pub"; | |
94 | ||
95f536ac | 95 | action("cp $localsshdir/$keyfile $sysconfdir/$keyfile"); |
96 | action("cp $localsshdir/$pubkeyfile $sysconfdir/$pubkeyfile"); | |
97 | } | |
e9ec5455 | 98 | } |
e9ec5455 | 99 | } |
100 | ||
95f536ac | 101 | sub isReadable |
1a1f62a4 | 102 | { |
95f536ac | 103 | my($file) = @_; |
1a1f62a4 | 104 | |
95f536ac | 105 | if ( ( -e $file ) && ( -r $file ) ) |
1a1f62a4 | 106 | { |
95f536ac | 107 | return 1; |
1a1f62a4 | 108 | } |
823981ba | 109 | else |
1a1f62a4 | 110 | { |
95f536ac | 111 | return 0; |
ac083f7a | 112 | } |
1a1f62a4 | 113 | } |
114 | ||
95f536ac | 115 | sub determineKeys |
823981ba | 116 | { |
95f536ac | 117 | my($keyhash, $keylist); |
118 | my($count); | |
823981ba | 119 | |
95f536ac | 120 | $count = 0; |
823981ba | 121 | |
95f536ac | 122 | $keyhash = {}; |
123 | $keyhash->{gen} = []; # a list of keytypes to generate | |
124 | $keyhash->{copy} = []; # a list of files to copy from the | |
125 | $genlist = $keyhash->{gen}; | |
126 | $copylist = $keyhash->{copy}; | |
e9ec5455 | 127 | |
95f536ac | 128 | for my $keytype (keys %$keyfiles) |
1a1f62a4 | 129 | { |
95f536ac | 130 | $basekeyfile = $keyfiles->{$keytype}; |
131 | $keyfile = "$localsshdir/$basekeyfile"; | |
132 | $pubkeyfile = "$keyfile.pub"; | |
1a1f62a4 | 133 | |
95f536ac | 134 | if ( !isReadable($keyfile) || !isReadable($pubkeyfile) ) |
135 | { | |
136 | push(@$genlist, $keytype); | |
137 | $count++; | |
138 | } | |
1a1f62a4 | 139 | } |
140 | ||
95f536ac | 141 | for my $keytype (keys %$keyfiles) |
1a1f62a4 | 142 | { |
95f536ac | 143 | if ( !grep(/^$keytype$/, @$genlist) ) |
144 | { | |
145 | $keyfile = $keyfiles->{$keytype}; | |
146 | push(@$copylist, $keyfile); | |
147 | $count++; | |
148 | } | |
1a1f62a4 | 149 | } |
150 | ||
95f536ac | 151 | if ($count > 0) |
1a1f62a4 | 152 | { |
95f536ac | 153 | if ( ! -d $sysconfdir ) |
154 | { | |
155 | print "Could not find ${sysconfdir} directory... creating\n"; | |
156 | action("mkdir -p $sysconfdir"); | |
157 | } | |
1a1f62a4 | 158 | } |
95f536ac | 159 | |
160 | return $keyhash; | |
161 | } | |
162 | ||
163 | sub runKeyGen | |
164 | { | |
165 | my($gen_keys) = @_; | |
166 | ||
167 | print "Generating ssh host keys...\n"; | |
168 | ||
169 | for my $k (@$gen_keys) | |
1a1f62a4 | 170 | { |
95f536ac | 171 | $keyfile = $keyfiles->{$k}; |
172 | ||
9b2e814c | 173 | # if $sysconfdir/$keyfile doesn't exist.. |
95f536ac | 174 | action("$bindir/ssh-keygen -t $k -f $sysconfdir/$keyfile -N \"\""); |
1a1f62a4 | 175 | } |
176 | ||
177 | return 0; | |
178 | } | |
179 | ||
20d3226a | 180 | sub fixpaths |
181 | { | |
7e12c9a7 | 182 | my $g, $h; |
823981ba | 183 | |
95f536ac | 184 | print "Fixing sftp-server path in sshd_config...\n"; |
185 | ||
186 | $f = "$gpath/etc/ssh/sshd_config"; | |
187 | $g = "$f.tmp"; | |
188 | ||
189 | if ( ! -f "$f" ) | |
190 | { | |
191 | die("Cannot find $f!"); | |
192 | } | |
e9ec5455 | 193 | |
20d3226a | 194 | # |
95f536ac | 195 | # Grab the current mode/uid/gid for use later |
20d3226a | 196 | # |
197 | ||
95f536ac | 198 | $mode = (stat($f))[2]; |
199 | $uid = (stat($f))[4]; | |
200 | $gid = (stat($f))[5]; | |
20d3226a | 201 | |
20d3226a | 202 | # |
95f536ac | 203 | # Move $f into a .tmp file for the translation step |
20d3226a | 204 | # |
205 | ||
95f536ac | 206 | $result = system("mv $f $g 2>&1"); |
207 | if ($result or $?) | |
20d3226a | 208 | { |
95f536ac | 209 | die "ERROR: Unable to execute command: $!\n"; |
210 | } | |
7536fc6f | 211 | |
95f536ac | 212 | open(IN, "<$g") || die ("$0: input file $g missing!\n"); |
213 | open(OUT, ">$f") || die ("$0: unable to open output file $f!\n"); | |
20d3226a | 214 | |
95f536ac | 215 | while (<IN>) |
216 | { | |
217 | if ( /Subsystem\s+sftp\s+\S+/ ) | |
e9ec5455 | 218 | { |
95f536ac | 219 | $_ = "Subsystem\tsftp\t$gpath/libexec/sftp-server\n"; |
220 | $_ =~ s:/+:/:g; | |
7c96a399 | 221 | } |
95f536ac | 222 | print OUT "$_"; |
223 | } # while <IN> | |
7c96a399 | 224 | |
95f536ac | 225 | close(OUT); |
226 | close(IN); | |
7c96a399 | 227 | |
95f536ac | 228 | # |
229 | # Remove the old .tmp file | |
230 | # | |
7c96a399 | 231 | |
95f536ac | 232 | $result = system("rm $g 2>&1"); |
7536fc6f | 233 | |
95f536ac | 234 | if ($result or $?) |
235 | { | |
236 | die "ERROR: Unable to execute command: $!\n"; | |
237 | } | |
7536fc6f | 238 | |
95f536ac | 239 | # |
240 | # An attempt to revert the new file back to the original file's | |
241 | # mode/uid/gid | |
242 | # | |
7e12c9a7 | 243 | |
95f536ac | 244 | chmod($mode, $f); |
245 | chown($uid, $gid, $f); | |
20d3226a | 246 | |
247 | return 0; | |
248 | } | |
249 | ||
d58b3a33 | 250 | sub alterFileGlobusLocation |
a26c150d | 251 | { |
d58b3a33 | 252 | my ($file) = @_; |
253 | ||
254 | $data = readFile($file); | |
95f536ac | 255 | $data =~ s|\@GSI_OPENSSH_GLOBUS_LOCATION\@|$gpath|g; |
d58b3a33 | 256 | writeFile($file, $data); |
257 | } | |
258 | ||
259 | sub alterFiles | |
260 | { | |
261 | my (@files); | |
262 | ||
263 | @files = ( | |
264 | "$gosharedir/contrib/caldera/sshd.init", | |
265 | ); | |
a26c150d | 266 | } |
267 | ||
268 | ### readFile( $filename ) | |
269 | # | |
270 | # reads and returns $filename's contents | |
271 | # | |
272 | ||
273 | sub readFile | |
274 | { | |
275 | my ($filename) = @_; | |
276 | my $data; | |
277 | ||
278 | open (IN, "$filename") || die "Can't open '$filename': $!"; | |
279 | $/ = undef; | |
280 | $data = <IN>; | |
281 | $/ = "\n"; | |
282 | close(IN); | |
283 | ||
284 | return $data; | |
285 | } | |
286 | ||
287 | ### writeFile( $filename, $fileinput ) | |
288 | # | |
289 | # create the inputs to the ssl program at $filename, appending the common name to the | |
290 | # stream in the process | |
291 | # | |
292 | ||
293 | sub writeFile | |
294 | { | |
295 | my ($filename, $fileinput) = @_; | |
296 | ||
297 | # | |
298 | # test for a valid $filename | |
299 | # | |
300 | ||
301 | if ( !defined($filename) || (length($filename) lt 1) ) | |
302 | { | |
303 | die "Filename is undefined"; | |
304 | } | |
305 | ||
306 | if ( ( -e "$filename" ) && ( ! -w "$filename" ) ) | |
307 | { | |
308 | die "Cannot write to filename '$filename'"; | |
309 | } | |
310 | ||
311 | # | |
312 | # write the output to $filename | |
313 | # | |
314 | ||
315 | open(OUT, ">$filename"); | |
316 | print OUT "$fileinput"; | |
317 | close(OUT); | |
318 | } | |
319 | ||
6e9c7232 | 320 | print "---------------------------------------------------------------------\n"; |
823981ba | 321 | print "Hi, I'm the setup script for the gsi_openssh package! There\n"; |
322 | print "are some last minute details that I've got to set straight\n"; | |
95f536ac | 323 | print "in the sshd config file, along with generating the ssh keys\n"; |
823981ba | 324 | print "for this machine (if it doesn't already have them).\n"; |
325 | print "\n"; | |
95f536ac | 326 | print "If I find a pair of host keys in /etc/ssh, I will copy them into\n"; |
6e9c7232 | 327 | print "\$GLOBUS_LOCATION/etc/ssh. If they aren't present, I will generate\n"; |
328 | print "them for you.\n"; | |
823981ba | 329 | print "\n"; |
330 | ||
331 | $response = query_boolean("Do you wish to continue with the setup package?","y"); | |
332 | ||
e9d69a89 | 333 | if ($response eq "n") |
823981ba | 334 | { |
335 | print "\n"; | |
336 | print "Okay.. exiting gsi_openssh setup.\n"; | |
337 | ||
338 | exit 0; | |
339 | } | |
e9ec5455 | 340 | |
95f536ac | 341 | $keyhash = determineKeys(); |
342 | runKeyGen($keyhash->{gen}); | |
343 | copyKeyFiles($keyhash->{copy}); | |
11b9a41c | 344 | fixpaths(); |
ad71c979 | 345 | |
472ec086 | 346 | my $metadata = new Grid::GPT::Setup(package_name => "gsi_openssh_setup"); |
4f276ad7 | 347 | |
53a54c67 | 348 | $metadata->finish(); |
9ef2f439 | 349 | |
6e9c7232 | 350 | print "---------------------------------------------------------------------\n"; |
9ef2f439 | 351 | print "$myname: Finished configuring package 'gsi_openssh'.\n"; |
b0441584 | 352 | print "\n"; |
6e9c7232 | 353 | print "Additional Notes:\n"; |
354 | print "\n"; | |
355 | print " o I see that you have your GLOBUS_LOCATION environmental variable\n"; | |
356 | print " set to:\n"; | |
357 | print "\n"; | |
358 | print " \t\"$gpath\"\n"; | |
b0441584 | 359 | print "\n"; |
6e9c7232 | 360 | print " Remember to keep this variable set (correctly) when you want to\n"; |
361 | print " use the executables that came with this package.\n"; | |
5002372c | 362 | print "\n"; |
6e9c7232 | 363 | print " o You may need to set LD_LIBRARY_PATH to point to the location in\n"; |
364 | print " which your globus libraries reside. For example:\n"; | |
5002372c | 365 | print "\n"; |
6e9c7232 | 366 | print " \t\$ LD_LIBRARY_PATH=\"$gpath/lib:\$LD_LIBRARY_PATH\"; \\\n"; |
367 | print " \t export LD_LIBRARY_PATH\n"; | |
5002372c | 368 | print "\n"; |
6e9c7232 | 369 | print "---------------------------------------------------------------------\n"; |
ac083f7a | 370 | |
371 | # | |
372 | # Just need a minimal action() subroutine for now.. | |
373 | # | |
374 | ||
375 | sub action | |
376 | { | |
377 | my ($command) = @_; | |
378 | ||
379 | printf "$command\n"; | |
380 | ||
381 | my $result = system("$command 2>&1"); | |
382 | ||
383 | if (($result or $?) and $command !~ m!patch!) | |
384 | { | |
385 | die "ERROR: Unable to execute command: $!\n"; | |
386 | } | |
387 | } | |
388 | ||
389 | sub query_boolean | |
390 | { | |
391 | my ($query_text, $default) = @_; | |
392 | my $nondefault, $foo, $bar; | |
393 | ||
394 | # | |
395 | # Set $nondefault to the boolean opposite of $default. | |
396 | # | |
397 | ||
398 | if ($default eq "n") | |
399 | { | |
400 | $nondefault = "y"; | |
401 | } | |
402 | else | |
403 | { | |
404 | $nondefault = "n"; | |
405 | } | |
406 | ||
407 | print "${query_text} "; | |
408 | print "[$default] "; | |
409 | ||
e9ec5455 | 410 | $foo = <STDIN>; |
411 | ($bar) = split //, $foo; | |
412 | ||
e9d69a89 | 413 | if ( grep(/\s/, $bar) ) |
ac083f7a | 414 | { |
e9d69a89 | 415 | # this is debatable. all whitespace means 'default' |
416 | ||
417 | $bar = $default; | |
418 | } | |
419 | elsif ($bar ne $default) | |
420 | { | |
421 | # everything else means 'nondefault'. | |
422 | ||
423 | $bar = $nondefault; | |
424 | } | |
425 | else | |
426 | { | |
427 | # extraneous step. to get here, $bar should be eq to $default anyway. | |
428 | ||
e9ec5455 | 429 | $bar = $default; |
ac083f7a | 430 | } |
431 | ||
e9ec5455 | 432 | return $bar; |
ac083f7a | 433 | } |