xref: /openbsd-src/gnu/usr.bin/perl/install_lib.pl (revision 46035553bfdd96e63c94e32da0210227ec2e3cf1)
1#!perl
2
3# Initialisation code and subroutines shared between installperl and installman
4# Probably installhtml needs to join the club.
5
6use strict;
7use vars qw($Is_VMS $Is_W32 $Is_OS2 $Is_Cygwin $Is_Darwin $Is_NetWare $Is_AmigaOS
8	    %opts $packlist);
9use subs qw(unlink link chmod chown);
10require File::Path;
11require File::Copy;
12
13BEGIN {
14    require Config;
15    if ($Config::Config{userelocatableinc}) {
16	# This might be a considered a hack. Need to get information about the
17	# configuration from Config.pm *before* Config.pm expands any .../
18	# prefixes.
19	#
20	# So we set $^X to pretend that we're the already installed perl, so
21	# Config.pm does its ... expansion off that location.
22
23        my $location = $Config::Config{initialinstalllocation};
24	die <<'OS' unless defined $location;
25$Config{initialinstalllocation} is not defined - can't install a relocatable
26perl without this.
27OS
28	$^X = "$location/perl";
29	# And then remove all trace of ever having loaded Config.pm, so that
30	# it will reload with the revised $^X
31	undef %Config::;
32	delete $INC{"Config.pm"};
33	delete $INC{"Config_heavy.pl"};
34	delete $INC{"Config_git.pl"};
35	# You never saw us. We weren't here.
36
37	require Config;
38    }
39    Config->import;
40}
41
42if ($Config{d_umask}) {
43    umask(022); # umasks like 077 aren't that useful for installations
44}
45
46$Is_VMS = $^O eq 'VMS';
47$Is_W32 = $^O eq 'MSWin32';
48$Is_OS2 = $^O eq 'os2';
49$Is_Cygwin = $^O eq 'cygwin';
50$Is_Darwin = $^O eq 'darwin';
51$Is_NetWare = $Config{osname} eq 'NetWare';
52$Is_AmigaOS = $^O eq 'amigaos';
53
54sub unlink {
55    my(@names) = @_;
56    my($cnt) = 0;
57
58    return scalar(@names) if $Is_VMS;
59
60    foreach my $name (@names) {
61	next unless -e $name;
62	chmod 0777, $name if ($Is_OS2 || $Is_W32 || $Is_Cygwin || $Is_NetWare || $Is_AmigaOS);
63	print "  unlink $name\n" if $opts{verbose};
64	( CORE::unlink($name) and ++$cnt
65	  or warn "Couldn't unlink $name: $!\n" ) unless $opts{notify};
66    }
67    return $cnt;
68}
69
70sub link {
71    my($from,$to) = @_;
72    my($success) = 0;
73
74    my $xfrom = $from;
75    $xfrom =~ s/^\Q$opts{destdir}\E// if $opts{destdir};
76    my $xto = $to;
77    $xto =~ s/^\Q$opts{destdir}\E// if $opts{destdir};
78    print $opts{verbose} ? "  ln $xfrom $xto\n" : "  $xto\n"
79	unless $opts{silent};
80    my $link = $Is_AmigaOS ? \&CORE::symlink : \&CORE::link;
81    eval {
82      $link->($from, $to)
83        ? $success++
84          : ($from =~ m#^/afs/# || $to =~ m#^/afs/#)
85            ? die "AFS"  # okay inside eval {}
86              : die "Couldn't link $from to $to: $!\n"
87                unless $opts{notify};
88      $packlist->{$xto} = { from => $xfrom, type => 'link' };
89     };
90    if ($@) {
91	warn "Replacing link() with File::Copy::copy(): $@";
92	print $opts{verbose} ? "  cp $from $xto\n" : "  $xto\n"
93	    unless $opts{silent};
94	print "  creating new version of $xto\n"
95		 if $Is_VMS and -e $to and !$opts{silent};
96	unless ($opts{notify} or File::Copy::copy($from, $to) and ++$success) {
97	    # Might have been that F::C::c can't overwrite the target
98	    warn "Couldn't copy $from to $to: $!\n"
99		unless -f $to and (chmod(0666, $to), unlink $to)
100			and File::Copy::copy($from, $to) and ++$success;
101	}
102	if (defined($opts{uid}) || defined($opts{gid})) {
103	    chown($opts{uid}, $opts{gid}, $to) if $success;
104	}
105	$packlist->{$xto} = { type => 'file' };
106    }
107    $success;
108}
109
110sub chmod {
111    my($mode,$name) = @_;
112
113    return if ($^O eq 'dos');
114    printf "  chmod %o %s\n", $mode, $name if $opts{verbose};
115    CORE::chmod($mode,$name)
116	|| warn sprintf("Couldn't chmod %o %s: $!\n", $mode, $name)
117      unless $opts{notify};
118}
119
120sub chown {
121    my($uid,$gid,$name) = @_;
122
123    return if ($^O eq 'dos');
124    printf "  chown %s:%s %s\n", $uid, $gid, $name if $opts{verbose};
125    CORE::chown($uid,$gid,$name)
126	|| warn sprintf("Couldn't chown %s:%s %s: $!\n", $uid, $gid, $name)
127      unless $opts{notify};
128}
129
130sub samepath {
131    my($p1, $p2) = @_;
132
133    return (lc($p1) eq lc($p2)) if ($Is_W32 || $Is_NetWare);
134
135    return 1
136        if $p1 eq $p2;
137
138    my ($dev1, $ino1) = stat $p1;
139    return 0
140        unless defined $dev1;
141    my ($dev2, $ino2) = stat $p2;
142
143    return $dev1 == $dev2 && $ino1 == $ino2;
144}
145
146sub safe_rename {
147    my($from,$to) = @_;
148    if (-f $to and not unlink($to)) {
149        my($i);
150        for ($i = 1; $i < 50; $i++) {
151            last if rename($to, "$to.$i");
152        }
153        warn("Cannot rename to '$to.$i': $!"), return 0
154           if $i >= 50; # Give up!
155    }
156    link($from,$to) || return 0;
157    unlink($from);
158}
159
160sub mkpath {
161    File::Path::make_path(shift, {owner=>$opts{uid}, group=>$opts{gid},
162        mode=>0777, verbose=>$opts{verbose}}) unless $opts{notify};
163}
164
165sub unixtoamiga
166{
167	my $unixpath = shift;
168
169	my @parts = split("/",$unixpath);
170	my $isdir = 0;
171	$isdir = 1 if substr($unixpath,-1) eq "/";
172
173	my $first = 1;
174	my $amigapath = "";
175
176	my $i = 0;
177
178	for($i = 0; $i <= $#parts;$i++)
179	{
180		next if $parts[$i] eq ".";
181		if($parts[$i] eq "..")
182		{
183			$parts[$i] = "/";
184		}
185		if($i == 0)
186		{
187			if($parts[$i] eq "")
188			{
189				$amigapath .= $parts[$i + 1] . ":";
190				$i++;
191				next;
192			}
193		}
194		$amigapath .= $parts[$i];
195		if($i != $#parts)
196		{
197			$amigapath .= "/" unless $parts[$i] eq "/" ;
198		}
199		else
200		{
201			if($isdir)
202			{
203				$amigapath .= "/" unless $parts[$i] eq "/" ;
204			}
205		}
206	}
207
208	return $amigapath;
209}
210
211sub amigaprotect
212{
213	my ($file,$bits) = @_;
214	print "PROTECT: File $file\n";
215	system("PROTECT $file $bits")
216	      unless $opts{notify};
217}
218
2191;
220