]> git.proxmox.com Git - pve-access-control.git/blame - src/PVE/Auth/PAM.pm
bump version to 8.1.4
[pve-access-control.git] / src / PVE / Auth / PAM.pm
CommitLineData
5bb4e06a
DM
1package PVE::Auth::PAM;
2
3use strict;
7c410d63
DM
4use warnings;
5
5bb4e06a
DM
6use PVE::Tools qw(run_command);
7use PVE::Auth::Plugin;
8use Authen::PAM qw(:constants);
9
10use base qw(PVE::Auth::Plugin);
11
12sub type {
13 return 'pam';
14}
15
16sub options {
17 return {
18 default => { optional => 1 },
19 comment => { optional => 1 },
96f8ebd6 20 tfa => { optional => 1 },
5bb4e06a
DM
21 };
22}
23
24sub authenticate_user {
25 my ($class, $config, $realm, $username, $password) = @_;
26
27 # user (www-data) need to be able to read /etc/passwd /etc/shadow
28 die "no password\n" if !$password;
29
95fb22e6 30 my $pamh = Authen::PAM->new('proxmox-ve-auth', $username, sub {
5bb4e06a
DM
31 my @res;
32 while(@_) {
33 my $msg_type = shift;
34 my $msg = shift;
35 push @res, (0, $password);
36 }
37 push @res, 0;
38 return @res;
39 });
40
41 if (!ref ($pamh)) {
42 my $err = $pamh->pam_strerror($pamh);
43 die "error during PAM init: $err";
44 }
45
6c512352
WB
46 if (my $rpcenv = PVE::RPCEnvironment::get()) {
47 if (my $ip = $rpcenv->get_client_ip()) {
48 $pamh->pam_set_item(PAM_RHOST(), $ip);
49 }
50 }
51
5bb4e06a
DM
52 my $res;
53
54 if (($res = $pamh->pam_authenticate(0)) != PAM_SUCCESS) {
55 my $err = $pamh->pam_strerror($res);
56 die "$err\n";
57 }
58
59 if (($res = $pamh->pam_acct_mgmt (0)) != PAM_SUCCESS) {
60 my $err = $pamh->pam_strerror($res);
61 die "$err\n";
62 }
63
64 $pamh = 0; # call destructor
65
66 return 1;
67}
68
69
70sub store_password {
71 my ($class, $config, $realm, $username, $password) = @_;
72
73 my $cmd = ['usermod'];
74
63358f40 75 my $epw = PVE::Tools::encrypt_pw($password);
5bb4e06a
DM
76
77 push @$cmd, '-p', $epw, $username;
78
79 run_command($cmd, errmsg => 'change password failed');
80}
81
821;