/
usr
/
sbin
/
/usr/sbin
mkdir
upload
Name
Size
Mode
Actions
aa-load
39680
0755
edit
dl
rm
aa-remove-unknown
3225
0755
edit
dl
rm
aa-status
40000
0755
edit
dl
rm
aa-teardown
137
0755
edit
dl
rm
accessdb
14904
0755
edit
dl
rm
acpid
53920
0755
edit
dl
rm
add-shell
1053
0755
edit
dl
rm
addgnupghome
3075
0755
edit
dl
rm
addgroup
55191
0755
edit
dl
rm
adduser
55191
0755
edit
dl
rm
agetty
60992
0755
edit
dl
rm
apparmor_parser
1629848
0755
edit
dl
rm
apparmor_status
40000
0755
edit
dl
rm
applygnupgdefaults
2217
0755
edit
dl
rm
argdist-bpfcc
36862
0755
edit
dl
rm
arpd
26960
0755
edit
dl
rm
arptables
224424
0755
edit
dl
rm
arptables-nft
224424
0755
edit
dl
rm
arptables-nft-restore
224424
0755
edit
dl
rm
arptables-nft-save
224424
0755
edit
dl
rm
arptables-restore
224424
0755
edit
dl
rm
arptables-save
224424
0755
edit
dl
rm
badblocks
35144
0755
edit
dl
rm
bashreadline-bpfcc
2380
0755
edit
dl
rm
bashreadline.bt
698
0755
edit
dl
rm
bcache-super-show
14648
0755
edit
dl
rm
bindsnoop-bpfcc
16346
0755
edit
dl
rm
biolatency-bpfcc
11365
0755
edit
dl
rm
biolatency-kp.bt
664
0755
edit
dl
rm
biolatency.bt
681
0755
edit
dl
rm
biolatpcts-bpfcc
10248
0755
edit
dl
rm
biopattern-bpfcc
3957
0755
edit
dl
rm
biosdecode
27856
0755
edit
dl
rm
biosnoop-bpfcc
10833
0755
edit
dl
rm
biosnoop.bt
1148
0755
edit
dl
rm
biostacks.bt
915
0755
edit
dl
rm
biotop-bpfcc
9567
0755
edit
dl
rm
bitesize-bpfcc
1166
0755
edit
dl
rm
bitesize.bt
567
0755
edit
dl
rm
blkdeactivate
16351
0755
edit
dl
rm
blkdiscard
22912
0755
edit
dl
rm
blkid
55720
0755
edit
dl
rm
blkzone
35200
0755
edit
dl
rm
blockdev
35200
0755
edit
dl
rm
bpflist-bpfcc
2601
0755
edit
dl
rm
bpftool
1622
0755
edit
dl
rm
bridge
111096
0755
edit
dl
rm
btrfsdist-bpfcc
6627
0755
edit
dl
rm
btrfsslower-bpfcc
9985
0755
edit
dl
rm
cachestat-bpfcc
6531
0755
edit
dl
rm
cachetop-bpfcc
9367
0755
edit
dl
rm
cache_check
1430568
0755
edit
dl
rm
cache_dump
1430568
0755
edit
dl
rm
cache_metadata_size
1430568
0755
edit
dl
rm
cache_repair
1430568
0755
edit
dl
rm
cache_restore
1430568
0755
edit
dl
rm
cache_writeback
1430568
0755
edit
dl
rm
capable-bpfcc
8477
0755
edit
dl
rm
capable.bt
1926
0755
edit
dl
rm
capsh
58456
0755
edit
dl
rm
cfdisk
97008
0755
edit
dl
rm
cgdisk
170480
0755
edit
dl
rm
chcpu
31104
0755
edit
dl
rm
chgpasswd
59720
0755
edit
dl
rm
chmem
35200
0755
edit
dl
rm
chpasswd
55736
0755
edit
dl
rm
chronyd
306232
0755
edit
dl
rm
chroot
39432
0755
edit
dl
rm
cobjnew-bpfcc
53
0755
edit
dl
rm
compactsnoop-bpfcc
11369
0755
edit
dl
rm
cpgr
49608
0755
edit
dl
rm
cppw
49608
0755
edit
dl
rm
cpudist-bpfcc
7013
0755
edit
dl
rm
cpuunclaimed-bpfcc
14938
0755
edit
dl
rm
cpuwalk.bt
497
0755
edit
dl
rm
criticalstat-bpfcc
8607
0755
edit
dl
rm
cron
60080
0755
edit
dl
rm
cryptdisks_start
1544
0755
edit
dl
rm
cryptdisks_stop
844
0755
edit
dl
rm
cryptsetup
231320
0755
edit
dl
rm
ctrlaltdel
14720
0755
edit
dl
rm
dbslower-bpfcc
7391
0755
edit
dl
rm
dbstat-bpfcc
3790
0755
edit
dl
rm
dcb
82448
0755
edit
dl
rm
dcsnoop-bpfcc
4126
0755
edit
dl
rm
dcsnoop.bt
1261
0755
edit
dl
rm
dcstat-bpfcc
3859
0755
edit
dl
rm
deadlock-bpfcc
20943
0755
edit
dl
rm
debugfs
231288
0755
edit
dl
rm
delgroup
18977
0755
edit
dl
rm
deluser
18977
0755
edit
dl
rm
depmod
174328
0755
edit
dl
rm
devlink
154480
0755
edit
dl
rm
dhcpcd
404888
0755
edit
dl
rm
dirtop-bpfcc
8568
0755
edit
dl
rm
dmeventd
51592
0755
edit
dl
rm
dmidecode
138496
0755
edit
dl
rm
dmsetup
175160
0755
edit
dl
rm
dmstats
175160
0755
edit
dl
rm
dosfsck
80264
0755
edit
dl
rm
dosfslabel
39304
0755
edit
dl
rm
dpkg-preconfigure
4356
0755
edit
dl
rm
dpkg-reconfigure
4536
0755
edit
dl
rm
drsnoop-bpfcc
6889
0755
edit
dl
rm
dumpe2fs
35136
0755
edit
dl
rm
e2freefrag
18744
0755
edit
dl
rm
e2fsck
373080
0755
edit
dl
rm
e2image
43328
0755
edit
dl
rm
e2label
113216
0755
edit
dl
rm
e2mmpstatus
35136
0755
edit
dl
rm
e2scrub
7294
0755
edit
dl
rm
e2scrub_all
5394
0755
edit
dl
rm
e2undo
22840
0755
edit
dl
rm
e4crypt
31104
0755
edit
dl
rm
e4defrag
35128
0755
edit
dl
rm
ebtables
224424
0755
edit
dl
rm
ebtables-nft
224424
0755
edit
dl
rm
ebtables-nft-restore
224424
0755
edit
dl
rm
ebtables-nft-save
224424
0755
edit
dl
rm
ebtables-restore
224424
0755
edit
dl
rm
ebtables-save
224424
0755
edit
dl
rm
ebtables-translate
224424
0755
edit
dl
rm
era_check
1430568
0755
edit
dl
rm
era_dump
1430568
0755
edit
dl
rm
era_invalidate
1430568
0755
edit
dl
rm
era_restore
1430568
0755
edit
dl
rm
ethtool
667320
0755
edit
dl
rm
execsnoop-bpfcc
10059
0755
edit
dl
rm
execsnoop.bt
928
0755
edit
dl
rm
exitsnoop-bpfcc
9646
0755
edit
dl
rm
ext4dist-bpfcc
6683
0755
edit
dl
rm
ext4slower-bpfcc
9948
0755
edit
dl
rm
faillock
22848
0755
edit
dl
rm
fatlabel
39304
0755
edit
dl
rm
fdisk
117168
0755
edit
dl
rm
filefrag
18760
0755
edit
dl
rm
filegone-bpfcc
5776
0755
edit
dl
rm
filelife-bpfcc
6528
0755
edit
dl
rm
fileslower-bpfcc
7372
0755
edit
dl
rm
filetop-bpfcc
6499
0755
edit
dl
rm
findfs
14720
0755
edit
dl
rm
fixparts
59880
0755
edit
dl
rm
fsadm
24580
0755
edit
dl
rm
fsck
43440
0755
edit
dl
rm
fsck.btrfs
1185
0755
edit
dl
rm
fsck.cramfs
31168
0755
edit
dl
rm
fsck.ext2
373080
0755
edit
dl
rm
fsck.ext3
373080
0755
edit
dl
rm
fsck.ext4
373080
0755
edit
dl
rm
fsck.fat
80264
0755
edit
dl
rm
fsck.minix
55712
0755
edit
dl
rm
fsck.msdos
80264
0755
edit
dl
rm
fsck.vfat
80264
0755
edit
dl
rm
fsck.xfs
2566
0755
edit
dl
rm
fsfreeze
14720
0755
edit
dl
rm
fstab-decode
14648
0755
edit
dl
rm
fstrim
43392
0755
edit
dl
rm
funccount-bpfcc
12981
0755
edit
dl
rm
funcinterval-bpfcc
5590
0755
edit
dl
rm
funclatency-bpfcc
11549
0755
edit
dl
rm
funcslower-bpfcc
10630
0755
edit
dl
rm
gdisk
203248
0755
edit
dl
rm
genl
123472
0755
edit
dl
rm
getcap
14648
0755
edit
dl
rm
gethostlatency-bpfcc
3914
0755
edit
dl
rm
gethostlatency.bt
1222
0755
edit
dl
rm
getpcaps
14648
0755
edit
dl
rm
getty
60992
0755
edit
dl
rm
groupadd
72840
0755
edit
dl
rm
groupdel
64424
0755
edit
dl
rm
groupmems
59744
0755
edit
dl
rm
groupmod
72744
0755
edit
dl
rm
grpck
59720
0755
edit
dl
rm
grpconv
51368
0755
edit
dl
rm
grpunconv
51368
0755
edit
dl
rm
grub-bios-setup
981552
0755
edit
dl
rm
grub-install
1225824
0755
edit
dl
rm
grub-macbless
969128
0755
edit
dl
rm
grub-mkconfig
8840
0755
edit
dl
rm
grub-mkdevicemap
72384
0755
edit
dl
rm
grub-probe
977576
0755
edit
dl
rm
grub-reboot
4841
0755
edit
dl
rm
grub-set-default
3556
0755
edit
dl
rm
halt
1501304
0755
edit
dl
rm
hardirqs-bpfcc
7019
0755
edit
dl
rm
hdparm
142776
0755
edit
dl
rm
iconvconfig
35296
0755
edit
dl
rm
init
100816
0755
edit
dl
rm
inject-bpfcc
16445
0755
edit
dl
rm
insmod
174328
0755
edit
dl
rm
install-sgmlcatalog
4551
0755
edit
dl
rm
installkernel
2659
0755
edit
dl
rm
integritysetup
68672
0755
edit
dl
rm
invoke-rc.d
16517
0755
edit
dl
rm
ip
772920
0755
edit
dl
rm
ip6tables
224424
0755
edit
dl
rm
ip6tables-apply
7052
0755
edit
dl
rm
ip6tables-legacy
95176
0755
edit
dl
rm
ip6tables-legacy-restore
95176
0755
edit
dl
rm
ip6tables-legacy-save
95176
0755
edit
dl
rm
ip6tables-nft
224424
0755
edit
dl
rm
ip6tables-nft-restore
224424
0755
edit
dl
rm
ip6tables-nft-save
224424
0755
edit
dl
rm
ip6tables-restore
224424
0755
edit
dl
rm
ip6tables-restore-translate
224424
0755
edit
dl
rm
ip6tables-save
224424
0755
edit
dl
rm
ip6tables-translate
224424
0755
edit
dl
rm
iptables
224424
0755
edit
dl
rm
iptables-apply
7052
0755
edit
dl
rm
iptables-legacy
95176
0755
edit
dl
rm
iptables-legacy-restore
95176
0755
edit
dl
rm
iptables-legacy-save
95176
0755
edit
dl
rm
iptables-nft
224424
0755
edit
dl
rm
iptables-nft-restore
224424
0755
edit
dl
rm
iptables-nft-save
224424
0755
edit
dl
rm
iptables-restore
224424
0755
edit
dl
rm
iptables-restore-translate
224424
0755
edit
dl
rm
iptables-save
224424
0755
edit
dl
rm
iptables-translate
224424
0755
edit
dl
rm
irqbalance
60272
0755
edit
dl
rm
irqbalance-ui
39304
0755
edit
dl
rm
iscsi-iname
18744
0755
edit
dl
rm
iscsiadm
379320
0755
edit
dl
rm
iscsid
293432
0755
edit
dl
rm
iscsistart
281080
0755
edit
dl
rm
iscsi_discovery
5293
0755
edit
dl
rm
isosize
14720
0755
edit
dl
rm
iucode-tool
55640
0755
edit
dl
rm
iucode_tool
55640
0755
edit
dl
rm
javacalls-bpfcc
55
0755
edit
dl
rm
javaflow-bpfcc
54
0755
edit
dl
rm
javagc-bpfcc
52
0755
edit
dl
rm
javaobjnew-bpfcc
56
0755
edit
dl
rm
javastat-bpfcc
54
0755
edit
dl
rm
javathreads-bpfcc
57
0755
edit
dl
rm
kbdrate
18752
0755
edit
dl
rm
killall5
26856
0755
edit
dl
rm
killsnoop-bpfcc
4554
0755
edit
dl
rm
killsnoop.bt
873
0755
edit
dl
rm
klockstat-bpfcc
13356
0755
edit
dl
rm
kpartx
43176
0755
edit
dl
rm
kvmexit-bpfcc
11461
0755
edit
dl
rm
ldattach
27008
0755
edit
dl
rm
ldconfig
387
0755
edit
dl
rm
ldconfig.real
1051280
0755
edit
dl
rm
llcstat-bpfcc
4584
0755
edit
dl
rm
loads.bt
1127
0755
edit
dl
rm
locale-gen
4316
0755
edit
dl
rm
logrotate
96504
0755
edit
dl
rm
logsave
14496
0755
edit
dl
rm
losetup
76304
0755
edit
dl
rm
lsmod
174328
0755
edit
dl
rm
luksformat
3401
0755
edit
dl
rm
lvchange
3156712
0755
edit
dl
rm
lvconvert
3156712
0755
edit
dl
rm
lvcreate
3156712
0755
edit
dl
rm
lvdisplay
3156712
0755
edit
dl
rm
lvextend
3156712
0755
edit
dl
rm
lvm
3156712
0755
edit
dl
rm
lvmconfig
3156712
0755
edit
dl
rm
lvmdiskscan
3156712
0755
edit
dl
rm
lvmdump
10364
0755
edit
dl
rm
lvmpolld
241632
0755
edit
dl
rm
lvmsadc
3156712
0755
edit
dl
rm
lvmsar
3156712
0755
edit
dl
rm
lvreduce
3156712
0755
edit
dl
rm
lvremove
3156712
0755
edit
dl
rm
lvrename
3156712
0755
edit
dl
rm
lvresize
3156712
0755
edit
dl
rm
lvs
3156712
0755
edit
dl
rm
lvscan
3156712
0755
edit
dl
rm
lxc
589
0755
edit
dl
rm
lxd
589
0755
edit
dl
rm
make-bcache
22912
0755
edit
dl
rm
mdadm
637144
0755
edit
dl
rm
mdflush-bpfcc
2295
0755
edit
dl
rm
mdflush.bt
775
0755
edit
dl
rm
mdmon
265016
0755
edit
dl
rm
memleak-bpfcc
21298
0755
edit
dl
rm
mkdosfs
52048
0755
edit
dl
rm
mke2fs
133752
0755
edit
dl
rm
mkfs
14720
0755
edit
dl
rm
mkfs.bfs
22912
0755
edit
dl
rm
mkfs.btrfs
573752
0755
edit
dl
rm
mkfs.cramfs
35144
0755
edit
dl
rm
mkfs.ext2
133752
0755
edit
dl
rm
mkfs.ext3
133752
0755
edit
dl
rm
mkfs.ext4
133752
0755
edit
dl
rm
mkfs.fat
52048
0755
edit
dl
rm
mkfs.minix
43408
0755
edit
dl
rm
mkfs.msdos
52048
0755
edit
dl
rm
mkfs.ntfs
67976
0755
edit
dl
rm
mkfs.vfat
52048
0755
edit
dl
rm
mkfs.xfs
449528
0755
edit
dl
rm
mkhomedir_helper
22872
0755
edit
dl
rm
mkinitramfs
15762
0755
edit
dl
rm
mklost+found
14648
0755
edit
dl
rm
mkntfs
67976
0755
edit
dl
rm
mkswap
51592
0755
edit
dl
rm
ModemManager
2165576
0755
edit
dl
rm
modinfo
174328
0755
edit
dl
rm
modprobe
174328
0755
edit
dl
rm
mount.fuse
18736
0755
edit
dl
rm
mount.fuse3
18736
0755
edit
dl
rm
mount.lowntfs-3g
121832
0755
edit
dl
rm
mount.ntfs
162824
0755
edit
dl
rm
mount.ntfs-3g
162824
0755
edit
dl
rm
mountsnoop-bpfcc
14968
0755
edit
dl
rm
mpathpersist
31960
0755
edit
dl
rm
multipath
35128
0755
edit
dl
rm
multipathc
18744
0755
edit
dl
rm
multipathd
145880
0755
edit
dl
rm
mysqld
55467944
0755
edit
dl
rm
mysqld_qslower-bpfcc
3125
0755
edit
dl
rm
naptime.bt
1035
0755
edit
dl
rm
needrestart
41092
0755
edit
dl
rm
netplan
802
0755
edit
dl
rm
netqtop-bpfcc
5725
0755
edit
dl
rm
newusers
89048
0755
edit
dl
rm
nfnl_osf
18736
0755
edit
dl
rm
nfsdist-bpfcc
5068
0755
edit
dl
rm
nfsslower-bpfcc
13939
0755
edit
dl
rm
nft
26856
0755
edit
dl
rm
nginx
1314168
0755
edit
dl
rm
nodegc-bpfcc
52
0755
edit
dl
rm
nodestat-bpfcc
54
0755
edit
dl
rm
nologin
14640
0755
edit
dl
rm
ntfsclone
51592
0755
edit
dl
rm
ntfscp
31104
0755
edit
dl
rm
ntfslabel
22912
0755
edit
dl
rm
ntfsresize
63888
0755
edit
dl
rm
ntfsundelete
51592
0755
edit
dl
rm
offcputime-bpfcc
13779
0755
edit
dl
rm
offwaketime-bpfcc
15676
0755
edit
dl
rm
on_ac_power
3788
0755
edit
dl
rm
oomkill-bpfcc
2084
0755
edit
dl
rm
oomkill.bt
1198
0755
edit
dl
rm
opensnoop-bpfcc
14581
0755
edit
dl
rm
opensnoop.bt
953
0755
edit
dl
rm
overlayroot-chroot
2510
0755
edit
dl
rm
ownership
14792
0755
edit
dl
rm
pam-auth-update
21465
0755
edit
dl
rm
pam_extrausers_chkpwd
26944
2755
edit
dl
rm
pam_extrausers_update
35136
0755
edit
dl
rm
pam_getenv
2890
0755
edit
dl
rm
pam_namespace_helper
467
0755
edit
dl
rm
pam_timestamp_check
14656
0755
edit
dl
rm
parted
96664
0755
edit
dl
rm
partprobe
14720
0755
edit
dl
rm
pdata_tools
1430568
0755
edit
dl
rm
perlcalls-bpfcc
55
0755
edit
dl
rm
perlflow-bpfcc
54
0755
edit
dl
rm
perlstat-bpfcc
54
0755
edit
dl
rm
php-fpm7.4
4803376
0755
edit
dl
rm
phpcalls-bpfcc
54
0755
edit
dl
rm
phpdismod
7278
0755
edit
dl
rm
phpenmod
7278
0755
edit
dl
rm
phpflow-bpfcc
53
0755
edit
dl
rm
phpquery
6389
0755
edit
dl
rm
phpstat-bpfcc
53
0755
edit
dl
rm
pidpersec-bpfcc
1111
0755
edit
dl
rm
pidpersec.bt
628
0755
edit
dl
rm
pivot_root
14720
0755
edit
dl
rm
plymouthd
150088
0755
edit
dl
rm
poweroff
1501304
0755
edit
dl
rm
ppchcalls-bpfcc
14224
0755
edit
dl
rm
profile-bpfcc
14756
0755
edit
dl
rm
pvchange
3156712
0755
edit
dl
rm
pvck
3156712
0755
edit
dl
rm
pvcreate
3156712
0755
edit
dl
rm
pvdisplay
3156712
0755
edit
dl
rm
pvmove
3156712
0755
edit
dl
rm
pvremove
3156712
0755
edit
dl
rm
pvresize
3156712
0755
edit
dl
rm
pvs
3156712
0755
edit
dl
rm
pvscan
3156712
0755
edit
dl
rm
pwck
55592
0755
edit
dl
rm
pwconv
47272
0755
edit
dl
rm
pwhistory_helper
22848
0755
edit
dl
rm
pwunconv
47272
0755
edit
dl
rm
pythoncalls-bpfcc
57
0755
edit
dl
rm
pythonflow-bpfcc
56
0755
edit
dl
rm
pythongc-bpfcc
54
0755
edit
dl
rm
pythonstat-bpfcc
56
0755
edit
dl
rm
rdmaucma-bpfcc
5073
0755
edit
dl
rm
readahead-bpfcc
6694
0755
edit
dl
rm
readprofile
22944
0755
edit
dl
rm
reboot
1501304
0755
edit
dl
rm
remove-shell
1111
0755
edit
dl
rm
reset-trace-bpfcc
3498
0755
edit
dl
rm
resize2fs
71992
0755
edit
dl
rm
resolvconf
162480
0755
edit
dl
rm
rmmod
174328
0755
edit
dl
rm
rmt
56024
0755
edit
dl
rm
rmt-tar
56024
0755
edit
dl
rm
rsyslogd
790192
0755
edit
dl
rm
rtacct
28992
0755
edit
dl
rm
rtcwake
35200
0755
edit
dl
rm
rtmon
119312
0755
edit
dl
rm
rubycalls-bpfcc
55
0755
edit
dl
rm
rubyflow-bpfcc
54
0755
edit
dl
rm
rubygc-bpfcc
52
0755
edit
dl
rm
rubyobjnew-bpfcc
56
0755
edit
dl
rm
rubystat-bpfcc
54
0755
edit
dl
rm
runlevel
1501304
0755
edit
dl
rm
runqlat-bpfcc
9526
0755
edit
dl
rm
runqlat.bt
788
0755
edit
dl
rm
runqlen-bpfcc
8248
0755
edit
dl
rm
runqlen.bt
1037
0755
edit
dl
rm
runqslower-bpfcc
9225
0755
edit
dl
rm
runuser
55680
0755
edit
dl
rm
service
9104
0755
edit
dl
rm
setcap
14648
0755
edit
dl
rm
setuids.bt
1799
0755
edit
dl
rm
setvesablank
14712
0755
edit
dl
rm
setvtrgb
14776
0755
edit
dl
rm
sfdisk
108928
0755
edit
dl
rm
sgdisk
182768
0755
edit
dl
rm
shadowconfig
2273
0755
edit
dl
rm
shmsnoop-bpfcc
7985
0755
edit
dl
rm
shutdown
1501304
0755
edit
dl
rm
slabratetop-bpfcc
6537
0755
edit
dl
rm
sofdsnoop-bpfcc
8255
0755
edit
dl
rm
softirqs-bpfcc
5723
0755
edit
dl
rm
solisten-bpfcc
6103
0755
edit
dl
rm
sshd
921416
0755
edit
dl
rm
ssllatency.bt
2133
0755
edit
dl
rm
sslsniff-bpfcc
14013
0755
edit
dl
rm
sslsnoop.bt
2041
0755
edit
dl
rm
stackcount-bpfcc
16655
0755
edit
dl
rm
start-stop-daemon
48632
0755
edit
dl
rm
statsnoop-bpfcc
5041
0755
edit
dl
rm
statsnoop.bt
1294
0755
edit
dl
rm
sudo_logsrvd
254464
0755
edit
dl
rm
sudo_sendlog
134832
0755
edit
dl
rm
sulogin
43392
0755
edit
dl
rm
swapin.bt
600
0755
edit
dl
rm
swaplabel
18816
0755
edit
dl
rm
swapoff
22912
0755
edit
dl
rm
swapon
43392
0755
edit
dl
rm
switch_root
22912
0755
edit
dl
rm
syncsnoop-bpfcc
1300
0755
edit
dl
rm
syncsnoop.bt
839
0755
edit
dl
rm
syscount-bpfcc
8771
0755
edit
dl
rm
syscount.bt
872
0755
edit
dl
rm
sysctl
31112
0755
edit
dl
rm
tarcat
936
0755
edit
dl
rm
tc
645200
0755
edit
dl
rm
tclcalls-bpfcc
54
0755
edit
dl
rm
tclflow-bpfcc
53
0755
edit
dl
rm
tclobjnew-bpfcc
55
0755
edit
dl
rm
tclstat-bpfcc
53
0755
edit
dl
rm
tcpaccept-bpfcc
9220
0755
edit
dl
rm
tcpaccept.bt
1756
0755
edit
dl
rm
tcpcong-bpfcc
20591
0755
edit
dl
rm
tcpconnect-bpfcc
18902
0755
edit
dl
rm
tcpconnect.bt
1615
0755
edit
dl
rm
tcpconnlat-bpfcc
9285
0755
edit
dl
rm
tcpdrop-bpfcc
7616
0755
edit
dl
rm
tcpdrop.bt
2469
0755
edit
dl
rm
tcplife-bpfcc
16949
0755
edit
dl
rm
tcplife.bt
2785
0755
edit
dl
rm
tcpretrans-bpfcc
14098
0755
edit
dl
rm
tcpretrans.bt
2120
0755
edit
dl
rm
tcprtt-bpfcc
8913
0755
edit
dl
rm
tcpstates-bpfcc
14064
0755
edit
dl
rm
tcpsubnet-bpfcc
7814
0755
edit
dl
rm
tcpsynbl-bpfcc
2175
0755
edit
dl
rm
tcpsynbl.bt
962
0755
edit
dl
rm
tcptop-bpfcc
12943
0755
edit
dl
rm
tcptracer-bpfcc
18130
0755
edit
dl
rm
telinit
1501304
0755
edit
dl
rm
thin_check
1430568
0755
edit
dl
rm
thin_delta
1430568
0755
edit
dl
rm
thin_dump
1430568
0755
edit
dl
rm
thin_ls
1430568
0755
edit
dl
rm
thin_metadata_size
1430568
0755
edit
dl
rm
thin_repair
1430568
0755
edit
dl
rm
thin_restore
1430568
0755
edit
dl
rm
thin_rmap
1430568
0755
edit
dl
rm
thin_trim
1430568
0755
edit
dl
rm
threadsnoop-bpfcc
1858
0755
edit
dl
rm
threadsnoop.bt
712
0755
edit
dl
rm
tipc
92688
0755
edit
dl
rm
tplist-bpfcc
4157
0755
edit
dl
rm
trace-bpfcc
43892
0755
edit
dl
rm
ttysnoop-bpfcc
7694
0755
edit
dl
rm
tune2fs
113216
0755
edit
dl
rm
ucalls
11970
0755
edit
dl
rm
uflow
8115
0755
edit
dl
rm
ufw
4959
0755
edit
dl
rm
ugc
7823
0755
edit
dl
rm
umount.udisks2
14640
0755
edit
dl
rm
undump.bt
789
0755
edit
dl
rm
unix_chkpwd
31040
2755
edit
dl
rm
unix_update
35136
0755
edit
dl
rm
uobjnew
6181
0755
edit
dl
rm
update-ca-certificates
5446
0755
edit
dl
rm
update-catalog
9393
0755
edit
dl
rm
update-grub
64
0755
edit
dl
rm
update-grub-gfxpayload
301
0755
edit
dl
rm
update-grub2
64
0755
edit
dl
rm
update-ieee-data
3492
0755
edit
dl
rm
update-info-dir
1700
0755
edit
dl
rm
update-initramfs
6908
0755
edit
dl
rm
update-locale
3057
0755
edit
dl
rm
update-passwd
35392
0755
edit
dl
rm
update-pciids
1778
0755
edit
dl
rm
update-rc.d
18147
0755
edit
dl
rm
update-secureboot-policy
7605
0755
edit
dl
rm
update-shells
3984
0755
edit
dl
rm
update-xmlcatalog
17284
0755
edit
dl
rm
upgrade-from-grub-legacy
1596
0755
edit
dl
rm
usb_modeswitch
61096
0755
edit
dl
rm
usb_modeswitch_dispatcher
27418
0755
edit
dl
rm
useradd
143232
0755
edit
dl
rm
userdel
93192
0755
edit
dl
rm
usermod
130712
0755
edit
dl
rm
ustat
12412
0755
edit
dl
rm
uthreads
4100
0755
edit
dl
rm
uuidd
31624
0755
edit
dl
rm
validlocale
1773
0755
edit
dl
rm
vcstime
14640
0755
edit
dl
rm
vdpa
35392
0755
edit
dl
rm
veritysetup
44992
0755
edit
dl
rm
vfscount-bpfcc
1390
0755
edit
dl
rm
vfscount.bt
515
0755
edit
dl
rm
vfsstat-bpfcc
4159
0755
edit
dl
rm
vfsstat.bt
721
0755
edit
dl
rm
vgcfgbackup
3156712
0755
edit
dl
rm
vgcfgrestore
3156712
0755
edit
dl
rm
vgchange
3156712
0755
edit
dl
rm
vgck
3156712
0755
edit
dl
rm
vgconvert
3156712
0755
edit
dl
rm
vgcreate
3156712
0755
edit
dl
rm
vgdisplay
3156712
0755
edit
dl
rm
vgexport
3156712
0755
edit
dl
rm
vgextend
3156712
0755
edit
dl
rm
vgimport
3156712
0755
edit
dl
rm
vgimportclone
3156712
0755
edit
dl
rm
vgmerge
3156712
0755
edit
dl
rm
vgmknodes
3156712
0755
edit
dl
rm
vgreduce
3156712
0755
edit
dl
rm
vgremove
3156712
0755
edit
dl
rm
vgrename
3156712
0755
edit
dl
rm
vgs
3156712
0755
edit
dl
rm
vgscan
3156712
0755
edit
dl
rm
vgsplit
3156712
0755
edit
dl
rm
vigr
62144
0755
edit
dl
rm
vipw
62144
0755
edit
dl
rm
virtiostat-bpfcc
8900
0755
edit
dl
rm
visudo
258776
0755
edit
dl
rm
vpddecode
14928
0755
edit
dl
rm
wakeuptime-bpfcc
8291
0755
edit
dl
rm
wipefs
39296
0755
edit
dl
rm
writeback.bt
1699
0755
edit
dl
rm
xfsdist-bpfcc
4723
0755
edit
dl
rm
xfsdist.bt
972
0755
edit
dl
rm
xfsslower-bpfcc
7964
0755
edit
dl
rm
xfs_admin
2174
0755
edit
dl
rm
xfs_bmap
695
0755
edit
dl
rm
xfs_copy
92608
0755
edit
dl
rm
xfs_db
705088
0755
edit
dl
rm
xfs_estimate
14504
0755
edit
dl
rm
xfs_freeze
800
0755
edit
dl
rm
xfs_fsr
43192
0755
edit
dl
rm
xfs_growfs
39152
0755
edit
dl
rm
xfs_info
1294
0755
edit
dl
rm
xfs_io
208536
0755
edit
dl
rm
xfs_logprint
80144
0755
edit
dl
rm
xfs_mdrestore
35048
0755
edit
dl
rm
xfs_metadump
816
0755
edit
dl
rm
xfs_mkfile
1040
0755
edit
dl
rm
xfs_ncheck
685
0755
edit
dl
rm
xfs_quota
92328
0755
edit
dl
rm
xfs_repair
658760
0755
edit
dl
rm
xfs_rtcp
18584
0755
edit
dl
rm
xfs_scrub
108816
0755
edit
dl
rm
xfs_scrub_all
7841
0755
edit
dl
rm
xfs_spaceman
43320
0755
edit
dl
rm
xtables-legacy-multi
95176
0755
edit
dl
rm
xtables-monitor
224424
0755
edit
dl
rm
xtables-nft-multi
224424
0755
edit
dl
rm
zerofree
14488
0755
edit
dl
rm
zfsdist-bpfcc
5427
0755
edit
dl
rm
zfsslower-bpfcc
8657
0755
edit
dl
rm
zic
67984
0755
edit
dl
rm
zramctl
55824
0755
edit
dl
rm
Edit:
/usr/sbin/adduser
(55191B)
#! /usr/bin/perl # Copyright (C) 2000-2004 Roland Bauerschmidt <rb@debian.org> # 2005-2023 Marc Haber <mh+debian-packages@zugschlus.de> # 2022 Benjamin Drung <benjamin.drung@canonical.com> # 2023 Guillem Jover <guillem@debian.org> # 2021-2022 Jason Franklin <jason@oneway.dev> # 2022 Matt Barry <matt@hazelmollusk.org> # 2016-2017 Afif Elghraoui <afif@debian.org> # 2016 Dr. Helge Kreutzmann <debian@helgefjell.de> # 2005-2009 Joerg Hoh <joerg@joerghoh.de> # 2006-2011 Stephen Gran <sgran@debian.org> # # Original adduser: # Copyright (C) 1997-1999 Guy Maor <maor@debian.org> # # Copyright (C) 1995 Ted Hajek <tedhajek@boombox.micro.umn.edu> # Ian A. Murdock <imurdock@gnu.ai.mit.edu> # # The general scheme of this program was adapted from the original # Debian "adduser" program by Ian A. Murdock <imurdock@gnu.ai.mit.edu>. # # License: GPL-2+ use 5.32.0; use strict; use warnings; use Getopt::Long; use Debian::AdduserCommon 3.136; use Debian::AdduserLogging 3.136; use Debian::AdduserRetvalues 3.136; BEGIN { if ( Debian::AdduserCommon->VERSION != version->declare('3.136') || Debian::AdduserLogging->VERSION != version->declare('3.136') || Debian::AdduserRetvalues->VERSION != version->declare('3.136') ) { die "wrong module version in adduser, check your packaging or path"; } } my $version = "3.137ubuntu1"; BEGIN { local $ENV{PERL_DL_NONLAZY}=1; # we need to disable perlcritic here since this construct # needs experession form eval, see perl cookbook 12.2.3 ## no critic eval " require POSIX; import POSIX qw(setlocale); "; ## use critic if ($@) { *setlocale = sub { return 1 }; } else { setlocale( &POSIX::LC_MESSAGES, "" ); } ## no critic eval " require I18N::Langinfo; import I18N::Langinfo qw(langinfo YESEXPR NOEXPR); "; ## use critic if ($@) { *langinfo = sub { return shift; }; *YESEXPR = sub { "^[yY]" }; *NOEXPR = sub { "^[nN]" }; } } my $yesexpr = langinfo(YESEXPR()); my %config; # configuration hash my $nogroup_id = getgrnam("nogroup") || 65534; $0 =~ s+.*/++; our $verbose = 1; # should we be verbose? my $name_check_level = 0; # should we allow bad names? our $stderrmsglevel = "warn"; our $stdoutmsglevel = "info"; our $logmsglevel = "info"; my $allow_badname = 0; # should we allow bad names? my $ask_passwd = 1; # ask for a passwd? my $disabled_login = 0; # leave the new account disabled? our @configfiles; our @defaults = undef; our $encrypt_home = undef; our $found_group_opt = undef; our $found_sys_opt = undef; our $ingroup_name = undef; our $new_firstgid = undef; our $new_firstuid = undef; our $new_comment = undef; our $gid_option = undef; our $primary_gid = undef; our $new_lastgid = undef; our $new_lastuid = undef; our $new_uid = undef; our $no_create_home = undef; our $special_home = undef; our $special_shell = undef; our $use_extrausers = 0; our $add_extra_groups; our $add_extra_groups_old; # Global variables we need later my $existing_user = undef; my $existing_group = undef; my $new_name = undef; my $make_group_also = 0; my $home_dir = undef; my $undohome = undef; my $undouser = undef; my $undogroup = undef; my $shell = undef; my $first_uid = undef; my $last_uid = undef; my $first_gid = undef; my $last_gid = undef; my $dir_mode = undef; my $perm = undef; my %uid_pool; my %gid_pool; our @names; GetOptions( 'add-extra-groups' => \$add_extra_groups, 'add_extra_groups' => \$add_extra_groups_old, 'allow-all-names' => sub { $name_check_level = 2 }, 'allow-badname' => sub { $name_check_level = 1 unless $name_check_level }, 'allow-bad-names' => sub { $name_check_level = 1 unless $name_check_level }, 'comment=s' => \$new_comment, 'conf|c=s' => \@configfiles, 'debug' => sub { $verbose = 2 }, 'stdoutmsglevel=s' => \$stdoutmsglevel, 'stderrmsglevel=s' => \$stderrmsglevel, 'logmsglevel=s' => \$logmsglevel, 'disabled-login' => sub { $disabled_login = 1; $ask_passwd = 0 }, 'disabled-password' => sub { $ask_passwd = 0 }, 'encrypt-home' => \$encrypt_home, 'extrausers' => \$use_extrausers, 'firstgid=i' => \$new_firstgid, 'firstuid=i' => \$new_firstuid, 'force-badname' => sub { $name_check_level = 1 unless $name_check_level }, 'gecos=s' => \$new_comment, 'gid=i' => \$gid_option, 'group' => \$found_group_opt, 'help|h' => sub { &usage; exit }, 'home=s' => \$special_home, 'ingroup=s' => \$ingroup_name, 'lastgid=i' => \$new_lastgid, 'lastuid=i' => \$new_lastuid, 'no-create-home' => \$no_create_home, 'quiet|q' => sub { $verbose = 0 }, 'shell=s' => \$special_shell, 'system' => \$found_sys_opt, 'uid=i' => \$new_uid, 'verbose' => sub { $verbose = 1 }, 'version|v' => sub { &version; exit }, ) or &usage_error; if(!@configfiles) { @defaults = ("/etc/adduser.conf"); } else { @defaults = (@configfiles); } # preseed configuration data and then read the config file preseed_config(\@defaults,\%config); # everyone can issue "--help" and "--version", but only root can go on if( $> != 0) { log_fatal( mtx("Only root may add a user or group to the system.") ); exit( RET_ROOT_NEEDED ); } # TODO: Handle configuration file input, allow bare input there. if( $verbose == 0 ) { set_msglevel( $stderrmsglevel, "warn", $logmsglevel ); } elsif( $verbose == 1 ) { set_msglevel( $stderrmsglevel, "info", $logmsglevel ); } elsif( $verbose == 2 ) { set_msglevel( $stderrmsglevel, "debug", $logmsglevel ); } else { set_msglevel( $stderrmsglevel, $stdoutmsglevel, $logmsglevel ); } # detect the right mode my $action = $0 eq "addgroup" ? "addgroup" : "adduser"; if (defined($found_sys_opt)) { $action = "addsysuser" if ($action eq "adduser"); $action = "addsysgroup" if ($action eq "addgroup"); } # explicitly set PATH, because super (1) cleans up the path and makes adduser unusable; # this is also a good idea for sudo (which doesn't clean up) $ENV{"PATH"}="/bin:/usr/bin:/sbin:/usr/sbin"; $ENV{"IFS"}=" \t\n"; ############################ # checks related to @names # ############################ while (defined(my $arg = shift(@ARGV))) { push (@names, $arg); } if ( (! defined $names[0]) || length($names[0]) == 0 || @names > 2) { log_fatal( mtx("Only one or two names allowed.") ); exit( RET_INVALID_CALL ); } if (@names == 2) { # must be addusertogroup if ($action eq "addsysuser" || $found_group_opt) { log_fatal( mtx("Specify only one name in this mode.") ); exit( RET_INVALID_CALL ); } if ($action eq "addgroup" or $action eq "addsysgroup") { log_fatal( mtx("addgroup with two arguments is an unspecified operation.") ); exit( RET_INVALID_CALL ); } $action = "addusertogroup"; $existing_user = shift (@names); $existing_group = shift (@names); } else { # 1 parameter, must be adduser $new_name = shift (@names); } ################################### # check for consistent parameters # ################################### if (!defined $add_extra_groups) { if( defined $add_extra_groups_old ) { $add_extra_groups = $add_extra_groups_old; } else { $add_extra_groups = 0; } } if ($action ne "addgroup" && defined($found_group_opt) +defined($ingroup_name) +defined($gid_option) > 1 ) { log_fatal( mtx("The --group, --ingroup, and --gid options are mutually exclusive.") ); exit( RET_EXCLUSIVE_PARAMETERS ); } if ((defined($special_home)) && ($special_home !~ m+^/+ )) { log_fatal( mtx("The home dir must be an absolute path.") ); exit( RET_INVALID_HOME_DIRECTORY ); } if (defined($special_home)) { if (!defined($no_create_home) && -d $special_home) { log_info( mtx("The home dir %s you specified already exists.\n"), $special_home ); } if (defined($no_create_home) && ! -d $special_home) { log_info( mtx("The home dir %s you specified can't be accessed: %s\n"), $special_home, $! ); } } if ($found_group_opt) { if ($action eq "addsysuser") { $make_group_also = 1; } elsif ($found_sys_opt) { $action = "addsysgroup"; } else { $action = "addgroup"; } } my $ecryptfs_setup_private; if (defined($encrypt_home)) { $ecryptfs_setup_private = &which('ecryptfs-setup-private'); } # TODO: map this to log levels $ENV{"VERBOSE"} = $verbose; $ENV{"DEBUG"} = $verbose; # preseed_config was moved from here # read the uid and gid pool if ($config{"uid_pool"}) { read_pool ($config{"uid_pool"}, "uid", \%uid_pool); } if ($config{"gid_pool"}) { read_pool ($config{"gid_pool"}, "gid", \%gid_pool); } &checkname($new_name) if defined $new_name; $SIG{'INT'} = $SIG{'QUIT'} = $SIG{'HUP'} = 'handler'; ##### # OK, we've processed the arguments. $action equals one of the following, # and the appropriate variables have been set: # # $action = "adduser" # $new_name - the name of the new user. # $ingroup_name | $gid_option - the group to add the user to # $special_home, $new_uid, $new_comment - optional overrides # $action = "addgroup" # $new_name - the name of the new group # $gid_option - optional override # $action = "addsysgroup" # $new_name - the name of the new group # $gid_option - optional override # $action = "addsysuser" # $new_name - the name of the new user # $make_group_also | $ingroup_name | $gid_option | 0 - which group # $special_home, $new_uid, $new_comment - optional overrides # $action = "addusertogroup" # $existing_user - the user to be added # $existing_group - the group to add her to ##### ################# ## addsysgroup ## ################# if ($action eq "addsysgroup") { acquire_lock(); # Check if requested group already exists and we can exit safely my $ret = existing_group_ok($new_name, $gid_option); if ($ret == 3) { log_info( mtx("The group `%s' already exists as a system group. Exiting."), $new_name ); exit( RET_OK ); } if ($ret == 1) { log_err( mtx("The group `%s' already exists and is not a system group. Exiting."), $new_name ); exit( RET_WRONG_OBJECT_PROPERTIES ); } if ($ret == 2) { log_err( mtx("The group `%s' already exists, but has a different GID. Exiting."), $new_name ); exit( RET_WRONG_OBJECT_PROPERTIES ); } if (defined($gid_option) && defined(getgrgid($gid_option))) { log_fatal( mtx("The GID `%s' is already in use."), $gid_option ); exit( RET_ID_IN_USE ); } if (!defined($gid_option)) { $first_gid = $new_firstgid || $config{"first_system_gid"}; $last_gid = $new_lastgid || $config{"last_system_gid"}; $gid_option = &first_avail_gid($first_gid, $last_gid, $gid_pool{$new_name}{'id'}); if ($gid_option == -1) { log_warn( mtx("No GID is available in the range %d-%d (FIRST_SYS_GID - LAST_SYS_GID)."), $first_gid, $last_gid ); log_err( mtx("The group `%s' was not created."), $new_name ); exit( RET_NO_ID_IN_RANGE ); } } log_info( mtx("Adding group `%s' (GID %d) ..."), $new_name, $gid_option); my $groupadd = &which('groupadd'); if ( ($use_extrausers) || ($config{"use_extrausers"}) ) { &systemcall($groupadd, '--extrausers', '-g', $gid_option, $new_name); } else { &systemcall($groupadd, '-g', $gid_option, $new_name); } release_lock(0); exit( RET_OK ); } ############## ## addgroup ## ############## if ($action eq "addgroup") { acquire_lock(); if (defined getgrnam($new_name)) { log_fatal( mtx("The group `%s' already exists."), $new_name); exit( RET_OBJECT_EXISTS ); } if (defined($gid_option) && defined(getgrgid($gid_option))) { log_fatal( mtx("The GID `%s' is already in use."), $gid_option ); exit( RET_ID_IN_USE ); } if (!defined($gid_option)) { $first_gid = $new_firstgid || $config{"first_gid"}; $last_gid = $new_lastgid || $config{"last_gid"}; log_debug( "Searching for gid with first_gid=%s, last_gid=%s, new_name=%s, gid_pool=%s", $first_gid, $last_gid, $new_name, $gid_pool{$new_name}{'id'} ); $gid_option = &first_avail_gid($first_gid, $last_gid, $gid_pool{$new_name}{'id'}); if ($gid_option == -1) { log_warn( mtx("No GID is available in the range %d-%d (FIRST_GID - LAST_GID)."), $first_gid, $last_gid ); log_fatal( mtx("The group `%s' was not created."), $new_name ); exit( RET_NO_ID_IN_RANGE ); } } log_info( mtx("Adding group `%s' (GID %d) ..."), $new_name, $gid_option); my $groupadd = &which('groupadd'); if ( ($use_extrausers) || ($config{"use_extrausers"}) ) { &systemcall($groupadd, '--extrausers', '-g', $gid_option, $new_name); } else { &systemcall($groupadd, '-g', $gid_option, $new_name); } release_lock(0); exit( RET_OK ); } #################### ## addusertogroup ## #################### if ($action eq 'addusertogroup') { if (!defined getpwnam($existing_user)) { log_fatal( mtx("The user `%s' does not exist."), $existing_user ); exit( RET_OBJECT_DOES_NOT_EXIST ); } if (!defined getgrnam($existing_group)) { log_fatal( mtx("The group `%s' does not exist."), $existing_group ); exit( RET_OBJECT_DOES_NOT_EXIST ); } if (&user_is_member($existing_user, $existing_group)) { log_info( mtx("The user `%s' is already a member of `%s'."), $existing_user, $existing_group ); exit( RET_OK ); } log_info( mtx("Adding user `%s' to group `%s' ..."), $existing_user, $existing_group ); acquire_lock(); if ( ($use_extrausers) || ($config{"use_extrausers"}) ) { &systemcall('/usr/sbin/usermod', '--extrausers', '-a', '-G', $existing_group, $existing_user); } else { &systemcall('/usr/sbin/usermod', '-a', '-G', $existing_group, $existing_user); } release_lock(); exit( RET_OK ); } ################ ## addsysuser ## ################ if ($action eq "addsysuser") { acquire_lock(); if (existing_user_ok($new_name, $new_uid) == 1) { # a user with this name already exists; it's a problem when it's not a system user my $tmp_u = getpwnam($new_name); if (($tmp_u >= $config{"first_system_uid"}) and ($tmp_u <= $config{"last_system_uid"})) { log_info( mtx("The system user `%s' already exists. Exiting.\n"), $new_name ); exit( RET_OK ); } log_fatal( mtx("The user `%s' already exists, but is not a system user. Exiting."), $new_name ); exit( RET_WRONG_OBJECT_PROPERTIES ); } if (existing_user_ok($new_name, $new_uid) == 2) { log_fatal( mtx("The user `%s' already exists with a different UID. Exiting."), $new_name ); exit( RET_WRONG_OBJECT_PROPERTIES ); } if (!$ingroup_name && !defined($gid_option) && !$make_group_also) { $gid_option = $nogroup_id; } check_user_group(1); if (!defined($new_uid) && $make_group_also) { $new_uid = &first_avail_uid($new_firstuid || $config{"first_system_uid"}, $new_lastuid || $config{"last_system_uid"}, $uid_pool{$new_name}{'id'}); if ($new_uid == -1) { log_warn( mtx("No UID/GID pair is available in the range %d-%d (FIRST_SYS_UID - LAST_SYS_UID)."), $config{"first_system_uid"}, $config{"last_system_uid"} ); log_fatal( mtx("The user `%s' was not created."), $new_name ); exit( RET_NO_ID_IN_RANGE ); } $gid_option = &first_avail_gid($new_firstgid || $config{"first_system_gid"}, $new_lastgid || $config{"last_system_gid"}, $gid_pool{$new_name}{'id'}); $ingroup_name = $new_name; } elsif (!defined($new_uid) && !$make_group_also) { $new_uid = &first_avail_uid($new_firstuid || $config{"first_system_uid"}, $new_lastuid || $config{"last_system_uid"}, $uid_pool{$new_name}{'id'}); if ($new_uid == -1) { log_warn( mtx("No UID is available in the range %d-%d (FIRST_SYS_UID - LAST_SYS_UID)."), $config{"first_system_uid"}, $config{"last_system_uid"} ); log_fatal( mtx("The user `%s' was not created."), $new_name); exit( RET_NO_ID_IN_RANGE ); } if (defined($gid_option)) { $ingroup_name = getgrgid($gid_option); } elsif ($ingroup_name) { $gid_option = getgrnam($ingroup_name); } else { log_fatal( mtx("Neither ingroup option nor gid given.") ); exit( RET_NO_PRIMARY_GROUP ); } } else { if (defined($gid_option)) { $ingroup_name = getgrgid($gid_option); } elsif ($ingroup_name) { $gid_option = getgrnam($ingroup_name); } elsif ($make_group_also) { $gid_option=$new_uid; $ingroup_name=$new_name; } else { log_fatal( mtx("Neither ingroup option nor gid given and make_group_also unset.") ); exit( RET_NO_PRIMARY_GROUP ); } } log_info( mtx("Adding system user `%s' (UID %d) ..."), $new_name, $new_uid ); # if we reach this point, and the group does already exist, we can use it. if ($make_group_also && !getgrnam($new_name)) { log_info( mtx("Adding new group `%s' (GID %d) ..."), $new_name, $gid_option ); $undogroup = $new_name; my $groupadd = &which('groupadd'); if ( ($use_extrausers) || ($config{"use_extrausers"}) ) { &systemcall($groupadd, '--extrausers', '-g', $gid_option, $new_name); } else { &systemcall($groupadd, '-g', $gid_option, $new_name); } } log_info( mtx("Adding new user `%s' (UID %d) with group `%s' ..."), $new_name, $new_uid, $ingroup_name ); $home_dir = $special_home || $uid_pool{$new_name}{'home'} || '/nonexistent'; $no_create_home = $home_dir =~ /^\/+nonexistent(\/|$)/ ? 1 : $no_create_home; $shell = $special_shell || $uid_pool{$new_name}{'shell'} || '/usr/sbin/nologin'; $undouser = $new_name; if ( ($use_extrausers) || ($config{"use_extrausers"}) ) { &systemcall('/usr/sbin/useradd', '--extrausers', '-r', '-K', sprintf('SYS_UID_MIN=%d', $config{'first_system_uid'}), '-K', sprintf('SYS_UID_MAX=%d', $config{'last_system_uid'}), '-d', $home_dir, '-g', $ingroup_name, '-s', $shell, '-u', $new_uid, $new_name); } else { &systemcall('/usr/sbin/useradd', '-r', '-K', sprintf('SYS_UID_MIN=%d', $config{'first_system_uid'}), '-K', sprintf('SYS_UID_MAX=%d', $config{'last_system_uid'}), '-d', $home_dir, '-g', $ingroup_name, '-s', $shell, '-u', $new_uid, $new_name); } release_lock(0); if (defined($new_comment)) { &ch_comment($new_comment); } elsif ($uid_pool{$new_name}{'comment'}) { &ch_comment($uid_pool{$new_name}{'comment'}); } $primary_gid = $gid_option; create_homedir(0); exit( RET_OK ); } ############# ## adduser ## ############# if ($action eq "adduser") { acquire_lock(); $primary_gid=-1; my @supplemental_groups=(); log_trace( "new_uid %s", $new_uid ); log_trace( "ingroup_name %s, gid_option %s", $ingroup_name, $gid_option ); log_trace( "usergroups %s", $config{"usergroups"} ); log_trace( "users_gid %s, users_group %s", $config{"users_gid"}, $config{"users_group"} ); log_trace( "primary_gid %s, supplemental groups %s", $primary_gid, join(", ",@supplemental_groups) ); if( defined($config{"users_gid"}) && defined($config{"users_group"}) ) { log_warn ( mtx("USERS_GID and USERS_GROUP both given in configuration. This is an error.") ); log_fatal (mtx("The user `%s' was not created."),$new_name); exit( RET_CONFIG_ERROR ); } if ($config{"usergroups"} =~ /yes/i) { log_trace( "config usergroups == yes code path" ); $make_group_also = 1; if( $gid_option ) { $make_group_also = 0; $primary_gid = $gid_option; log_trace( "gid_option defined %s, make_group_also 0, primary_gid=gid_option", $gid_option ); } if( $ingroup_name ) { $make_group_also = 0; $primary_gid = getgrnam($ingroup_name); log_trace( "ingroup_name defined %s, make_group_also 0, primary_gid %s", $gid_option, $primary_gid ); } log_trace( "make_group_also %s, primary_gid %s", $make_group_also, $primary_gid ); if( defined( $primary_gid) && $primary_gid == -1 && $make_group_also == 0 ) { if (defined($config{"users_gid"}) && $config{"users_gid"} != -1) { my @grgid=getgrgid($config{"users_gid"}); my $grname=$grgid[0]; log_debug( "set primary_gid to users_gid %s %s", $config{"users_gid"}, $grname); $primary_gid = $config{"users_gid"}; } elsif (defined($config{"users_gid"}) && $config{"users_gid"} == -1) { # nothing } else { my $primary_group="users"; if (defined($config{"users_group"})) { $primary_group=$config{"users_group"}; } $primary_gid=getgrnam($primary_group); log_debug( "set primary_gid to users_group %s %s", $primary_gid, $primary_group); } } else { if (defined($config{"users_gid"}) && $config{"users_gid"} != -1) { my @grgid=getgrgid($config{"users_gid"}); my $grname=$grgid[0]; log_trace( "push users_gid %s %s to supplemental_groups", $config{"users_gid"}, $grname); push(@supplemental_groups, $grname); } elsif (defined($config{"users_gid"}) && $config{"users_gid"} == -1) { # nothing } else { my $supp_group="users"; if (defined($config{"users_group"})) { $supp_group=$config{"users_group"}; } log_trace( "push %s to supplemental_groups", $supp_group ); push(@supplemental_groups, $supp_group); } } } else { log_debug( "config usergroups != yes code path" ); if( defined($ingroup_name) ) { $primary_gid=getgrnam($ingroup_name); } elsif (defined($config{"users_gid"})) { log_trace( "primary_gid = users_gid = %d", $primary_gid ); $primary_gid = $config{"users_gid"}; } else { if (defined($config{"users_group"})) { my @grgid=getgrnam($config{"users_group"}); my $grgid=$grgid[2]; log_trace( "primary_gid = users_group %s %s", $config{"users_group"}, $grgid); $primary_gid = $grgid; } else { log_trace( "primary_gid = literal 100"); $primary_gid = 100; } } if( $primary_gid == -1 ) { log_fatal( "no primary GID for user set. User not created." ); exit( RET_NO_PRIMARY_GID ); } } log_debug( "primary_gid %s, supplemental groups %s", $primary_gid, join(", ",@supplemental_groups) ); if ( defined $ingroup_name || defined $gid_option ) { $make_group_also = 0; log_trace( "set make_group_also 0, neither ingroup_name or gid_option defined" ); } check_user_group(0); $first_uid = $new_firstuid || $config{"first_uid"}; $last_uid = $new_lastuid || $config{"last_uid"}; if ($config{"usergroups"} =~ /yes/i) { $first_gid = $first_uid; $last_gid = $last_uid; } else { $first_gid = $new_firstgid || $config{"first_gid"}; $last_gid = $new_lastgid || $config{"last_gid"}; } log_trace( "first_uid %s, last_uid %s, first_gid %s, last_gid %s", $first_uid, $last_uid, $first_gid, $last_gid ); log_info (gtx("Adding user `%s' ..."),$new_name); if (!defined($new_uid)) { if ( defined $ingroup_name ) { $new_uid = &first_avail_uid( $first_uid, $last_uid, $uid_pool{$new_name}{'id'}); } else { my $first_uidgid = ($first_uid, $first_gid)[$first_uid > $first_gid]; my $last_uidgid = ($last_uid, $last_gid)[$last_uid < $last_gid]; # TODO: Check what happens when those ranges do not overlap $new_uid = &first_avail_uid_gid( $first_uidgid, $last_uidgid, $uid_pool{$new_name}{'id'}); log_trace( "uidgid=%s, from first_uidgid %s, last_uidgid %s", $new_uid, $first_uidgid, $last_uidgid); } # TODO: user can specify different UID and GID here. # idea: split handling in uid/gid, which are equally the return value of # first_avail_uid_gid. If either pool_id is defined, set uid and gid from # distinct first_avail_uid and first_avail_gid calls. log_debug( "new_uid %s selected", $new_uid); if ($new_uid == -1) { log_warn( mtx("No UID/GID pair is available in the range %d-%d (FIRST_UID - LAST_UID)."), $first_uid, $last_uid); log_fatal( mtx("The user `%s' was not created."), $new_name ); exit( RET_NO_ID_IN_RANGE ); } log_trace( "gid_option %s, ingroup_name %s", $gid_option, $ingroup_name ); if ( defined $gid_option && $gid_option == -1 && defined $ingroup_name && $ingroup_name == "") { log_warn( mtx("USERGROUPS=no, USER_GID=-1 and USERS_GROUP empty. A user needs a primary group!") ); log_fatal( mtx("The user `%s' was not created."), $new_name ); exit( RET_NO_PRIMARY_GROUP ); } elsif (defined($gid_option) && $gid_option != -1) { $ingroup_name = getgrgid($gid_option); $primary_gid = $gid_option; log_debug( "gid_option defined and not -1, ingroup_name %s, primary_gid %d", $ingroup_name, $primary_gid ); } elsif ($ingroup_name) { $primary_gid = getgrnam($ingroup_name); log_debug( "ingroup_name defined %s, primary_gid %d", $ingroup_name, $primary_gid ); } elsif ( defined( $primary_gid ) ) { $ingroup_name = getgrgid($primary_gid); log_debug( "primary_gid defined %d, ingroup_name %s", $primary_gid, $primary_gid ); } else { $ingroup_name = 'users'; $primary_gid = 100; log_debug( "ingroup_name hard users, primary_gid hard 100" ); } if ($make_group_also) { $primary_gid = $new_uid; $ingroup_name = $new_name; log_trace( "make_group_also %s, primary_gid %s, ingroup_name %s", $make_group_also, $primary_gid, $ingroup_name ); } } else { log_debug( "new_uid %s, primary_gid %s, ingroup_name %s, make_group_also %s", $new_uid, $primary_gid, $ingroup_name, $make_group_also ); if (defined($gid_option)) { $ingroup_name = getgrgid($gid_option); $primary_gid = $gid_option; log_debug( "gid_option defined %s, ingroup_name %s", $gid_option, $ingroup_name ); } elsif (defined($primary_gid) && $primary_gid != -1) { $ingroup_name = getgrgid($primary_gid); log_debug( "primary_gid defined %s, ingroup_name %s", $primary_gid, $ingroup_name ); } elsif ($ingroup_name) { $primary_gid = getgrnam($ingroup_name); log_debug( "ingroup_name defined %s, primary_gid %s", $ingroup_name, $primary_gid ); } elsif ($make_group_also) { $primary_gid=$new_uid; $ingroup_name=$new_name; log_debug( "make_group_also %s, primary_gid defined %s, ingroup_name %s", $make_group_also, $primary_gid, $ingroup_name ); } else { log_debug( "no gid_option, no primary_gid, no ingroup_name, no make_group_also" ); log_fatal( mtx("Internal error interpreting parameter combination") ); exit( RET_INTERNAL ); } } log_debug ("make_group_also %s", $make_group_also ); if ($make_group_also) { $undogroup = $new_name; my $groupadd = &which('groupadd'); if( defined( $primary_gid ) ) { log_info( mtx("Adding new group `%s' (%d) ..."), $new_name, $primary_gid); if ( ($use_extrausers) || ($config{"use_extrausers"}) ) { &systemcall($groupadd, '--extrausers', '-g', $primary_gid, $new_name); } else { &systemcall($groupadd, '-g', $primary_gid, $new_name); } } else { log_info( mtx("Adding new group `%s' (new group ID) ..."), $new_name); if ( ($use_extrausers) || ($config{"use_extrausers"}) ) { &systemcall($groupadd, '--extrausers', $new_name); } else { &systemcall($groupadd, $new_name); } $primary_gid = getgrnam($new_name); log_info( mtx("new group '%s' created with GID %d"), $new_name, $primary_gid ); } } { my @grgid=getgrgid($primary_gid); my $grname=$grgid[0]; log_info( mtx("Adding new user `%s' (%d) with group `%s (%d)' ..."), $new_name, $new_uid, $grname, $primary_gid ); } $home_dir = $special_home || $uid_pool{$new_name}{'home'} || &homedir($new_name, $ingroup_name); if( !$disabled_login ) { $shell = $special_shell || $uid_pool{$new_name}{'shell'} || $config{"dshell"}; } else { $shell = $special_shell || $uid_pool{$new_name}{'shell'} || "/usr/sbin/nologin"; } log_debug( "creating new user with home_dir %s and shell %s", $home_dir, $shell ); $undouser = $new_name; my $useradd = &which('useradd'); if ( ($use_extrausers) || ($config{"use_extrausers"}) ) { &systemcall($useradd, '--extrausers', '-d', $home_dir, '-g', $primary_gid, '-s', $shell, '-u', $new_uid, $new_name); } else { &systemcall($useradd, '-d', $home_dir, '-g', $primary_gid, '-s', $shell, '-u', $new_uid, $new_name); } create_homedir (1); # copy skeleton data # useradd without -p has left the account disabled (password string is '!') my $yesexpr = langinfo(YESEXPR()); my $noexpr = langinfo(NOEXPR()); if ($ask_passwd) { PASSWD: for (;;) { my $passwd = &which('passwd'); # do _not_ use systemcall() here, since systemcall() dies on # non-zero exit code and we need to do special handling here! system($passwd, $new_name); my $ok = $?>>8; if ($ok != 0) { my $answer; # hm, error, should we break now? log_warn( mtx("Permission denied")) if ($ok == 1); log_warn( mtx("invalid combination of options")) if ($ok == 2); log_warn( mtx("unexpected failure, nothing done")) if ($ok == 3); log_warn( mtx("unexpected failure, passwd file missing")) if ($ok == 4); log_warn( mtx("passwd file busy, try again")) if ($ok == 5); log_warn( mtx("invalid argument to option")) if ($ok == 6); # Translators: [y/N] has to be replaced by values defined in your # locale. You can see by running "locale noexpr" which regular # expression will be checked to find positive answer. PROMPT: for (;;) { print (gtx("Try again? [y/N] ")); chop ($answer=<STDIN>); last PROMPT if ($answer =~ m/$yesexpr/o); last PASSWD if ($answer =~ m/$noexpr/o); last PASSWD if (!$answer); } } else { last; ## passwd ok } } } if (defined($new_comment)) { &ch_comment($new_comment); } elsif ($uid_pool{$new_name}{'comment'}) { &ch_comment($uid_pool{$new_name}{'comment'}); } else { my $noexpr = langinfo(NOEXPR()); my $yesexpr = langinfo(YESEXPR()); CHFN: for (;;) { my $chfn = &which('chfn'); if ( ($use_extrausers) || ($config{"use_extrausers"}) ) { &systemcall($chfn, '--extrausers', $new_name); } else { &systemcall($chfn, $new_name); } # Translators: [y/N] has to be replaced by values defined in your # locale. You can see by running "locale yesexpr" which regular # expression will be checked to find positive answer. PROMPT: for (;;) { print (gtx("Is the information correct? [Y/n] ")); chop (my $answer=<STDIN>); last PROMPT if ($answer =~ m/$noexpr/o); last CHFN if ($answer =~ m/$yesexpr/o); last CHFN if (!$answer); } } } if ( ( $add_extra_groups || $config{"add_extra_groups"} ) && defined($config{"extra_groups"}) ) { log_debug( "add extra_groups from config (%s) to supplemental_groups", $config{"extra_groups"} ); push (@supplemental_groups, split(/\s+/,$config{"extra_groups"})); } if ( @supplemental_groups ) { log_info( mtx("Adding new user `%s' to supplemental / extra groups `%s' ..."), $new_name, join(", ", @supplemental_groups) ); foreach my $newgrp ( @supplemental_groups ) { log_trace( "newgrp %s", $newgrp ); if (!defined getgrnam($newgrp)) { log_warn( mtx("The group `%s' does not exist."), $newgrp); next; } if (&user_is_member($new_name, $newgrp)) { log_info( mtx("The user `%s' is already a member of `%s'."), $new_name,$newgrp ); next; } log_info( mtx("Adding user `%s' to group `%s' ..."), $new_name, $newgrp ); my $gpasswd = &which('gpasswd'); if ( ($use_extrausers) || ($config{"use_extrausers"}) ) { &systemcall($gpasswd, '--extrausers', '-M', join(',', get_group_members($newgrp), $new_name), $newgrp); } else { &systemcall($gpasswd, '-M', join(',', get_group_members($newgrp), $new_name), $newgrp); } } } if ($config{"quotauser"}) { log_info( mtx("Setting quota for user `%s' to values of user `%s' ..."), $new_name, $config{quotauser} ); my $edquota = &which('edquota'); &systemcall($edquota, '-p', $config{quotauser}, $new_name); } &systemcall('/usr/local/sbin/adduser.local', $new_name, $new_uid, $primary_gid, $home_dir) if (-x "/usr/local/sbin/adduser.local"); release_lock(0); exit( RET_OK ); } # # we never go here # # calculate home directory sub homedir { my $dir = $config{"dhome"}; $dir .= '/' . $_[1] if ($config{"grouphomes"} =~ /yes/i); $dir .= '/' . substr($_[0],0,1) if ($config{"letterhomes"} =~ /yes/i); $dir .= '/' . $_[0]; return $dir; } # create_homedir -- create the homedirectory # parameter # 1: $copy_skeleton: # if 0 -> do not copy the skeleton data # if 1 -> copy the files in /etc/skel to the newly created home directory # return values: # none sub create_homedir { my ($copy_skeleton) = @_; if ($home_dir =~ /^\/+nonexistent(\/|$)/) { log_info( mtx("Not creating `%s'."), $home_dir ); } elsif ($no_create_home) { log_info( mtx("Not creating home directory `%s'."), $home_dir ); } elsif (-e $home_dir) { log_warn( mtx("The home directory `%s' already exists. Not touching this directory."), $home_dir ); my @homedir_stat = stat($home_dir); my $home_uid = $homedir_stat[4]; my $home_gid = $homedir_stat[5]; if (($home_uid != $new_uid) || ($home_gid != $primary_gid)) { log_warn( mtx("Warning: The home directory `%s' does not belong to the user you are currently creating."), $home_dir ); } } else { log_info( mtx("Creating home directory `%s' ..."),$home_dir ); $undohome = $home_dir; if( !&mktree($home_dir) ) { log_err( gtx("Couldn't create home directory `%s': %s."), $home_dir, $!); &cleanup(); } if ($action eq "adduser") { # Mute the command system('sh' => ( '-c' => '"$@" >/dev/null 2>&1', '--', '/usr/sbin/zsysctl', 'userdata', 'create', $new_name, $home_dir,)); } if( !chown($new_uid, $primary_gid, $home_dir) ) { log_err("chown %s:%s %s: %s", $new_uid, $primary_gid, $home_dir, $!); &cleanup(); } $dir_mode = get_dir_mode(); if( !chmod ($dir_mode, $home_dir) ) { log_err("chmod %s %s: %s", $dir_mode, $home_dir, $!); &cleanup(); } if (defined($encrypt_home)) { printf gtx("Setting up encryption ...\n") if $verbose; &systemcall($ecryptfs_setup_private, '-b', '-u', $new_name); } if ($config{"skel"} && $copy_skeleton) { log_info( mtx("Copying files from `%s' ..."), $config{skel} ); my $findpipe; if( !open($findpipe, q{-|}, "cd $config{skel}; find . -print") ) { log_err( mtx("fork for `find' failed: %s"), $!); &cleanup(); } while (<$findpipe>) { chop; next if ($_ eq "."); next if ($_ =~ qr/$config{skel_ignore_regex}/ ); ©_to_dir($config{"skel"}, $_, $home_dir, $new_uid, $primary_gid, ($config{"setgid_home"} =~ /yes/i)); } close ($findpipe); } if (defined($encrypt_home)) { &systemcall("/bin/umount", $home_dir); } } } # mktree: create a directory and all parent directories # we do not care about the rights and so on # parameters: # tree: the path # return values: # none sub mktree { my($tree) = @_; my($done, @path); my $default_dir_mode = oct(755); $tree =~ s:^/*(.*)/*$:$1:; # chop off leading & trailing slashes @path = split(/\//, $tree); $done = ""; while (@path) { $done .= '/' . shift(@path); -d $done || mkdir($done, $default_dir_mode) || return 0; } return 1; } # existing_user_ok: check if there is already a user present # on the system which satisfies the requirements # parameter: # new_name: the name of the user to check # new_uid : the UID of the user # return values: # 0 if the the user does not exist # 1 if the user already exists with the specified uid # (or $new_uid was not specified) # 2 if the user already exists, but $new_uid does not match its uid sub existing_user_ok { my($new_name,$new_uid) = @_; my ($dummy1,$dummy2,$uid); if (($dummy1,$dummy2,$uid) = getpwnam($new_name)) { if( defined($new_uid) && $uid == $new_uid ) { return 1; } if (! defined($new_uid)) { return 1; } # TODO: do we really need this code? Range check should not be performed here # also, we might be checking a normal user as well here if( $uid >= $config{"first_system_uid"} && $uid <= $config{"last_system_uid" } ) { return 2; } } else { return 0; } } # existing_group_ok: check if there is already a group which satiesfies the requirements # parameter: # new_name: the name of the group # new_gid : the GID of the group # return values: # 0 if the group does not exist # 1 if the group already exists with the specified gid # (or $gid_option was not specified) # 2 if the group already exists, but $gid_option does not match its gid # 3 if the group already exists inside the system range sub existing_group_ok { my($new_name,$new_gid) = @_; my ($dummy1,$dummy2,$gid); if (($dummy1,$dummy2,$gid) = getgrnam($new_name)) { # TODO: is this check required? There should not be any # gid outside of our allowed range anyways ... # also, we might be checking a normal user as well here if( $gid >= $config{"first_system_gid"} && $gid <= $config{"last_system_gid" } ) { return 3; } if (! defined($new_gid)) { return 1; } if ($gid == $new_gid) { return 1; } else { return 2; } } else { return 0; } } # check_user_group: ??? # parameters: # system: 0 if the user is not a system user, 1 otherwise # return values: # # todo: not sure whether global variables apply fine here. sub check_user_group { my ($system) = @_; log_debug( "check_user_group %s called, make_group_also %s", $system, $make_group_also ); if( !$system || !existing_user_ok($new_name, $new_uid) ) { if( defined getpwnam($new_name) ) { if( $system ) { log_fatal( mtx("The user `%s' already exists, and is not a system user."), $new_name); exit( RET_WRONG_OBJECT_PROPERTIES ); } else { log_fatal( mtx("The user `%s' already exists."), $new_name); exit( RET_OBJECT_EXISTS ); } } if (defined($new_uid) && getpwuid($new_uid)) { log_fatal( mtx("The UID %d is already in use."), $new_uid); exit( RET_ID_IN_USE ); } } if ($make_group_also) { log_trace( "make_group_also 1, new_name %s, new_uid %s", $new_name, $new_uid ); if( !$system || !existing_group_ok($new_name, $new_uid) ) { if (defined getgrnam($new_name)) { log_fatal( mtx("The group `%s' already exists."),$new_name ); exit( RET_OBJECT_EXISTS ); } if (defined($new_uid) && defined(getgrgid($new_uid))) { log_fatal( mtx("The GID %d is already in use."),$new_uid ); exit( RET_ID_IN_USE ); } } } else { if ($ingroup_name && !defined(getgrnam($ingroup_name))) { log_fatal( mtx("The group `%s' does not exist."), $ingroup_name); exit( RET_OBJECT_DOES_NOT_EXIST ); } if (defined($gid_option) && !defined(getgrgid($gid_option))) { log_fatal( mtx("No group with GID %d found."), $gid_option); exit( RET_OBJECT_DOES_NOT_EXIST ); } } log_debug( "return from check_user_group" ); } # copy_to_dir : # parameters: # fromdir # file # todir # newi # newg # sgiddir # return values: # none sub copy_to_dir { my($fromdir, $file, $todir, $newu, $newg, $sgiddir) = @_; if (-l "$fromdir/$file") { my $target; if( !($target = readlink("$fromdir/$file")) ) { log_err( "readlink: %s", $! ); &cleanup(); } my $curgid="$)"; my $curuid="$>"; my $error=""; $)="$newg"; $>="$newu"; symlink("$target", "$todir/$file") or $error="$!"; $>="$curuid"; $)="$curgid"; if( "$error" ne "" ) { log_err( "symlink: %s", $!); &cleanup(); } return; } elsif (-f "$fromdir/$file") { my $filefh; my $newfilefh; if( !open ($filefh, q{<}, "$fromdir/$file") ) { log_err( "open %s/%s: %s", $fromdir, $file , $!); &cleanup(); } if( !open ($newfilefh, q{>}, "$todir/$file") ) { log_err( "open >%s/%s: %s", $todir, $file, $!); &cleanup(); } if( !print $newfilefh (<$filefh>) ) { log_err( "print %s/%s: %s", $todir, $file, $!); &cleanup(); } close($filefh); if( !close($newfilefh) ) { log_err( "close %s/%s: %s", $todir, $file, $!); &cleanup(); } } elsif (-d "$fromdir/$file") { if( !mkdir("$todir/$file", 700) ) { log_err( "mkdir: %s/%s: %s", $todir, $file, $!); &cleanup(); } } else { log_err( mtx("%s/%s is neither a dir, file, nor a symlink."), $fromdir, $file ); &cleanup(); } if( !chown($newu, $newg, "$todir/$file") ) { log_err( "chown %s:%s %s/%s: %s", $newu, $newg, $todir, $file, $! ); &cleanup(); } $perm = (stat("$fromdir/$file"))[2] & oct(7777); if (-d "$fromdir/$file" && ($perm & oct(10)) && $sgiddir) { $perm |= oct(2000); } if( !chmod($perm, "$todir/$file") ) { log_err( "chmod %s/%s: %s", $todir, $file, $!); &cleanup(); } } # checkname: perform some sanity checks # parameters: # name: the name to check # return values: # none (exits on error) sub checkname { my ($name) = @_; my $ieee_regex = '^[_.A-Za-z0-9][-\@_.A-Za-z0-9]*\$?$'; my $min_regex = qr{^[^-+~:,\s/][^:,\s/]*$}; my $name_regex_var = $found_sys_opt ? 'SYS_NAME_REGEX' : 'NAME_REGEX'; my $name_regex = $config{lc $name_regex_var}; if ($name =~ /^[\d]+$/) { # this check cannot be turned off log_err( mtx("To avoid ambiguity with numerical UIDs, usernames which consist of only digits are not allowed.") ); exit( RET_INVALID_CHARS_IN_NAME ); } if (length $name > 32) { # this check cannot be turned off log_err( mtx("Usernames must be no more than 32 bytes in length; note that if you are using Unicode characters, the character limit will be less than 32.") ); exit( RET_INVALID_CHARS_IN_NAME ); } if ($name !~ $min_regex) { # this check cannot be turned off log_err( mtx("To avoid problems, the username must not start with a dash, plus sign, or tilde, and it must not contain any of the following: colon, comma, slash, or any whitespace characters including spaces, tabs, and newlines.") ); exit( RET_INVALID_CHARS_IN_NAME ); } return if ($name =~ qr/$name_regex/); if ($name !~ $ieee_regex && $name_check_level < 2) { log_err( mtx("To avoid problems, the username should consist only of letters, digits, underscores, periods, at signs and dashes, and not start with a dash (as defined by IEEE Std 1003.1-2001). For compatibility with Samba machine accounts, \$ is also supported at the end of the username. (Use the `--allow-all-names' option to bypass this restriction.)") ); exit( RET_INVALID_CHARS_IN_NAME ); } if ($name_check_level) { log_info( mtx("Allowing use of questionable username.") ); } else { log_err( mtx("Please enter a username matching the regular expression configured via the %s configuration variable. Use the `--allow-bad-names' option to relax this check or reconfigure %s in configuration."), $name_regex_var, $name_regex_var ); exit( RET_INVALID_CHARS_IN_NAME ); } } # first_avail_uid: return the first available uid in given range # parameters: # min, max: the range # pool_id: user id suggested from pool # return values: # -1 if no free uid is available # otherwise the choosen uid sub first_avail_uid { my ($min, $max, $pool_id) = @_; if (defined ($pool_id)) { return $pool_id if (!defined(getpwuid($pool_id))); return -1; } log_info( mtx("Selecting UID from range %d to %d ...\n"),$min,$max); my $t = $min; while ($t <= $max) { return $t if (!defined(getpwuid($t))); $t++; } return -1; # nothing available } # first_avail_gid: return the first available gid in given range # parameters: # min, max: the range # pool_id: group id suggested from pool # return values: # -1 if no free gid is available # otherwise the choosen gid sub first_avail_gid { my ($min, $max, $pool_id) = @_; if (defined ($pool_id)) { return $pool_id if (!defined(getgrgid($pool_id))); return -1; } log_info( mtx("Selecting GID from range %d to %d ..."),$min,$max); my $t = $min; while ($t <= $max) { return $t if (!defined(getgrgid($t))); $t++; } return -1; # nothing available } # first_avail_uid_gid: return the first available id in given range # that is both available as uid and gid # parameters: # min, max: the range # pool_id: user id suggested from pool # return values: # -1 if no free id is available # otherwise the choosen id sub first_avail_uid_gid { my ($min, $max, $pool_id) = @_; if (defined ($pool_id)) { return $pool_id if (!defined(getgrgid($pool_id))); return -1; } log_info( mtx("Selecting UID/GID from range %d to %d ..."), $min, $max ); my $t = $min; while ($t <= $max) { return $t if (!defined(getgrgid($t)) && !defined(getpwuid($t))); $t++; } return -1; # nothing available } sub ch_comment { my $chfn = &which('chfn'); my $comment = shift; if($comment =~ /,/) { my($comment_name,$comment_room,$comment_work,$comment_home,$comment_other) = split(/,/,$comment); if ( ($use_extrausers) || ($config{"use_extrausers"}) ) { &systemcall($chfn, '--extrausers', '-f', $comment_name, '-r', $comment_room, $new_name); &systemcall($chfn,'--extrausers','-w',$comment_work,$new_name) if(defined($comment_work)); &systemcall($chfn,'--extrausers','-h',$comment_home,$new_name) if(defined($comment_home)); &systemcall($chfn,'--extrausers','-o',$comment_other,$new_name) if(defined($comment_other)); } else { &systemcall($chfn, '-f', $comment_name, '-r', $comment_room, $new_name); &systemcall($chfn,'-w',$comment_work,$new_name) if(defined($comment_work)); &systemcall($chfn,'-h',$comment_home,$new_name) if(defined($comment_home)); &systemcall($chfn,'-o',$comment_other,$new_name) if(defined($comment_other)); } } else { if ( ($use_extrausers) || ($config{"use_extrausers"}) ) { &systemcall($chfn, '--extrausers', '-f', $comment, $new_name); } else { &systemcall($chfn, '-f', $comment, $new_name); } } } # user is member of group? sub user_is_member { my($user, $group) = @_; for (split(/ /, (getgrnam($group))[3])) { return 1 if ($user eq $_); } return 0; } sub cleanup { if ($undohome) { log_info( mtx("Removing directory `%s' ..."), $undohome); &systemcall('rm', '-rf', $undohome); } if ($undouser) { log_info( mtx("Removing user `%s' ..."), $undouser); &systemcall('userdel', $undouser); } if ($undogroup) { log_info( mtx("Removing group `%s' ..."), $undogroup); &systemcall('groupdel', $undogroup); } exit( RET_ADDUSER_ABORTED ); } sub handler { my($sig) = @_; # Translators: the variable %s is INT, QUIT, or HUP. # Please do not insert a space character between SIG and %s. log_err( mtx( "Caught a SIG%s.", $sig ) ); &cleanup(); } sub version { printf( gtx("adduser version %s\n\n"), $version ); print( gtx("Adds a user or group to the system. For detailed copyright information, please refer to /usr/share/doc/adduser/copyright. \n") ); print( gtx( "This program is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 2 of the License, or (at your option) any later version. This program is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License, /usr/share/common-licenses/GPL, for more details. ") ); } sub usage { printf( gtx( "adduser [--uid id] [--firstuid id] [--lastuid id] [--gid id] [--firstgid id] [--lastgid id] [--ingroup group] [--add-extra-groups] [--encrypt-home] [--shell shell] [--comment comment] [--home dir] [--no-create-home] [--allow-all-names] [--allow-bad-names] [--disabled-password] [--disabled-login] [--conf file] [--extrausers] [--quiet] [--verbose] [--debug] user Add a normal user adduser --system [--uid id] [--group] [--ingroup group] [--gid id] [--shell shell] [--comment comment] [--home dir] [--no-create-home] [--conf file] [--extrausers] [--quiet] [--verbose] [--debug] user Add a system user adduser --group [--gid ID] [--firstgid id] [--lastgid id] [--conf file] [--extrausers] [--quiet] [--verbose] [--debug] group addgroup [--gid ID] [--firstgid id] [--lastgid id] [--conf file] [--extrausers] [--quiet] [--verbose] [--debug] group Add a user group addgroup --system [--gid id] [--conf file] [--extrausers] [--quiet] [--verbose] [--debug] group Add a system group adduser [--extrausers] USER GROUP Add an existing user to an existing group\n") ); } sub usage_error { &usage; exit( RET_INVALID_CALL ); } # get_dir_mode: return the appropriate permissions mode for a home directory # parameters: # none # return value: # a valid octal mode sub get_dir_mode { my $setgid = $config{"setgid_home"} =~ /yes/i; my $mode = $found_sys_opt ? $config{"sys_dir_mode"} : $config{"dir_mode"}; if(!defined($mode) || ! ($mode =~ /[0-7]{3}/ || $mode =~ /[0-7]{4}/)) { $mode = ($found_sys_opt) ? "750" : "0750"; } if($setgid && (length($mode) == 3 || $mode =~ /^[0-1|4-5][0-7]{3}$/)) { $mode += 2000; } return oct($mode); } # Local Variables: # mode:cperl # cperl-indent-level:4 # End: # vim: tabstop=4 shiftwidth=4 expandtab
Save
cmd:
run