1
0
Fork 0
mirror of https://github.com/git/git.git synced 2024-05-11 08:56:09 +02:00

git-cvsserver: authentication support for pserver

Allow git-cvsserver to use authentication over pserver mode.  The
pserver user/password database is stored in the config file for each
repository.

Signed-off-by: Ævar Arnfjörð Bjarmason <avarab@gmail.com>
Worriedly-Acked-by: Martin Langhoff <martin.langhoff@gmail.com>
Signed-off-by: Junio C Hamano <gitster@pobox.com>
This commit is contained in:
Ævar Arnfjörð Bjarmason 2010-05-15 15:06:46 +00:00 committed by Junio C Hamano
parent 636e87d705
commit 031a027a72
2 changed files with 82 additions and 12 deletions

View File

@ -72,9 +72,6 @@ plugin. Most functionality works fine with both of these clients.
LIMITATIONS LIMITATIONS
----------- -----------
Currently cvsserver works over SSH connections for read/write clients, and
over pserver for anonymous CVS access.
CVS clients cannot tag, branch or perform GIT merges. CVS clients cannot tag, branch or perform GIT merges.
'git-cvsserver' maps GIT branches to CVS modules. This is very different 'git-cvsserver' maps GIT branches to CVS modules. This is very different
@ -84,7 +81,7 @@ one or more directories.
INSTALLATION INSTALLATION
------------ ------------
1. If you are going to offer anonymous CVS access via pserver, add a line in 1. If you are going to offer CVS access via pserver, add a line in
/etc/inetd.conf like /etc/inetd.conf like
+ +
-- --
@ -101,6 +98,22 @@ looks like
cvspserver stream tcp nowait nobody /usr/bin/git-cvsserver git-cvsserver pserver cvspserver stream tcp nowait nobody /usr/bin/git-cvsserver git-cvsserver pserver
------ ------
Only anonymous access is provided by pserve by default. To commit you
will have to create pserver accounts, simply add a [gitcvs.users]
section to the repositories you want to access, for example:
------
[gitcvs.users]
someuser = somepassword
otheruser = otherpassword
------
Then provide your password via the pserver method, for example:
------
cvs -d:pserver:someuser:somepassword <at> server/path/repo.git co <HEAD_name>
------
No special setup is needed for SSH access, other than having GIT tools No special setup is needed for SSH access, other than having GIT tools
in the PATH. If you have clients that do not accept the CVS_SERVER in the PATH. If you have clients that do not accept the CVS_SERVER
environment variable, you can rename 'git-cvsserver' to `cvs`. environment variable, you can rename 'git-cvsserver' to `cvs`.

View File

@ -183,12 +183,35 @@
exit 1; exit 1;
} }
$line = <STDIN>; chomp $line; $line = <STDIN>; chomp $line;
unless ($line eq 'anonymous') { my $user = $line;
print "E Only anonymous user allowed via pserver\n"; $line = <STDIN>; chomp $line;
print "I HATE YOU\n"; my $password = $line;
exit 1;
unless ($user eq 'anonymous') {
# Trying to authenticate a user
if (not exists $cfg->{gitcvs}->{users}) {
print "E the repo config file needs a [gitcvs.users] section with user/password key-value pairs\n";
print "I HATE YOU\n";
exit 1;
} elsif (exists $cfg->{gitcvs}->{users} and not exists $cfg->{gitcvs}->{users}->{$user}) {
#print "E the repo config file has a [gitcvs.users] section but the user $user is not defined in it\n";
print "I HATE YOU\n";
exit 1;
} else {
my $descrambled_password = descramble($password);
my $cleartext_password = $cfg->{gitcvs}->{users}->{$user};
if ($descrambled_password ne $cleartext_password) {
#print "E The password supplied for user $user was incorrect\n";
print "I HATE YOU\n";
exit 1;
}
# else fall through to LOVE
}
} }
$line = <STDIN>; chomp $line; # validate the password?
# For checking whether the user is anonymous on commit
$state->{user} = $user;
$line = <STDIN>; chomp $line; $line = <STDIN>; chomp $line;
unless ($line eq "END $request REQUEST") { unless ($line eq "END $request REQUEST") {
die "E Do not understand $line -- expecting END $request REQUEST\n"; die "E Do not understand $line -- expecting END $request REQUEST\n";
@ -314,7 +337,7 @@ sub req_Root
} }
foreach my $line ( @gitvars ) foreach my $line ( @gitvars )
{ {
next unless ( $line =~ /^(gitcvs)\.(?:(ext|pserver)\.)?([\w-]+)=(.*)$/ ); next unless ( $line =~ /^(gitcvs)\.(?:(ext|pserver|users)\.)?([\w-]+)=(.*)$/ );
unless ($2) { unless ($2) {
$cfg->{$1}{$3} = $4; $cfg->{$1}{$3} = $4;
} else { } else {
@ -1271,9 +1294,9 @@ sub req_ci
$log->info("req_ci : " . ( defined($data) ? $data : "[NULL]" )); $log->info("req_ci : " . ( defined($data) ? $data : "[NULL]" ));
if ( $state->{method} eq 'pserver') if ( $state->{method} eq 'pserver' and $state->{user} eq 'anonymous' )
{ {
print "error 1 pserver access cannot commit\n"; print "error 1 anonymous user cannot commit via pserver\n";
cleanupWorkTree(); cleanupWorkTree();
exit; exit;
} }
@ -2586,6 +2609,40 @@ sub cvs_author
$author; $author;
} }
sub descramble
{
# This table is from src/scramble.c in the CVS source
my @SHIFTS = (
0, 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,
114,120, 53, 79, 96,109, 72,108, 70, 64, 76, 67,116, 74, 68, 87,
111, 52, 75,119, 49, 34, 82, 81, 95, 65,112, 86,118,110,122,105,
41, 57, 83, 43, 46,102, 40, 89, 38,103, 45, 50, 42,123, 91, 35,
125, 55, 54, 66,124,126, 59, 47, 92, 71,115, 78, 88,107,106, 56,
36,121,117,104,101,100, 69, 73, 99, 63, 94, 93, 39, 37, 61, 48,
58,113, 32, 90, 44, 98, 60, 51, 33, 97, 62, 77, 84, 80, 85,223,
225,216,187,166,229,189,222,188,141,249,148,200,184,136,248,190,
199,170,181,204,138,232,218,183,255,234,220,247,213,203,226,193,
174,172,228,252,217,201,131,230,197,211,145,238,161,179,160,212,
207,221,254,173,202,146,224,151,140,196,205,130,135,133,143,246,
192,159,244,239,185,168,215,144,139,165,180,157,147,186,214,176,
227,231,219,169,175,156,206,198,129,164,150,210,154,177,134,127,
182,128,158,208,162,132,167,209,149,241,153,251,237,236,171,195,
243,233,253,240,194,250,191,155,142,137,245,235,163,242,178,152
);
my ($str) = @_;
# This should never happen, the same password format (A) bas been
# used by CVS since the beginning of time
die "invalid password format $1" unless substr($str, 0, 1) eq 'A';
my @str = unpack "C*", substr($str, 1);
my $ret = join '', map { chr $SHIFTS[$_] } @str;
return $ret;
}
package GITCVS::log; package GITCVS::log;
#### ####