-
Notifications
You must be signed in to change notification settings - Fork 0
/
Copy pathcurrent-install
1188 lines (976 loc) · 46 KB
/
current-install
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
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
322
323
324
325
326
327
328
329
330
331
332
333
334
335
336
337
338
339
340
341
342
343
344
345
346
347
348
349
350
351
352
353
354
355
356
357
358
359
360
361
362
363
364
365
366
367
368
369
370
371
372
373
374
375
376
377
378
379
380
381
382
383
384
385
386
387
388
389
390
391
392
393
394
395
396
397
398
399
400
401
402
403
404
405
406
407
408
409
410
411
412
413
414
415
416
417
418
419
420
421
422
423
424
425
426
427
428
429
430
431
432
433
434
435
436
437
438
439
440
441
442
443
444
445
446
447
448
449
450
451
452
453
454
455
456
457
458
459
460
461
462
463
464
465
466
467
468
469
470
471
472
473
474
475
476
477
478
479
480
481
482
483
484
485
486
487
488
489
490
491
492
493
494
495
496
497
498
499
500
501
502
503
504
505
506
507
508
509
510
511
512
513
514
515
516
517
518
519
520
521
522
523
524
525
526
527
528
529
530
531
532
533
534
535
536
537
538
539
540
541
542
543
544
545
546
547
548
549
550
551
552
553
554
555
556
557
558
559
560
561
562
563
564
565
566
567
568
569
570
571
572
573
574
575
576
577
578
579
580
581
582
583
584
585
586
587
588
589
590
591
592
593
594
595
596
597
598
599
600
601
602
603
604
605
606
607
608
609
610
611
612
613
614
615
616
617
618
619
620
621
622
623
624
625
626
627
628
629
630
631
632
633
634
635
636
637
638
639
640
641
642
643
644
645
646
647
648
649
650
651
652
653
654
655
656
657
658
659
660
661
662
663
664
665
666
667
668
669
670
671
672
673
674
675
676
677
678
679
680
681
682
683
684
685
686
687
688
689
690
691
692
693
694
695
696
697
698
699
700
701
702
703
704
705
706
707
708
709
710
711
712
713
714
715
716
717
718
719
720
721
722
723
724
725
726
727
728
729
730
731
732
733
734
735
736
737
738
739
740
741
742
743
744
745
746
747
748
749
750
751
752
753
754
755
756
757
758
759
760
761
762
763
764
765
766
767
768
769
770
771
772
773
774
775
776
777
778
779
780
781
782
783
784
785
786
787
788
789
790
791
792
793
794
795
796
797
798
799
800
801
802
803
804
805
806
807
808
809
810
811
812
813
814
815
816
817
818
819
820
821
822
823
824
825
826
827
828
829
830
831
832
833
834
835
836
837
838
839
840
841
842
843
844
845
846
847
848
849
850
851
852
853
854
855
856
857
858
859
860
861
862
863
864
865
866
867
868
869
870
871
872
873
874
875
876
877
878
879
880
881
882
883
884
885
886
887
888
889
890
891
892
893
894
895
896
897
898
899
900
901
902
903
904
905
906
907
908
909
910
911
912
913
914
915
916
917
918
919
920
921
922
923
924
925
926
927
928
929
930
931
932
933
934
935
936
937
938
939
940
941
942
943
944
945
946
947
948
949
950
951
952
953
954
955
956
957
958
959
960
961
962
963
964
965
966
967
968
969
970
971
972
973
974
975
976
977
978
979
980
981
982
983
984
985
986
987
988
989
990
991
992
993
994
995
996
997
998
999
1000
#!/usr/bin/env -S bash -e
# Cleaning the TTY.
clear
# Cosmetics (colours for text).
BOLD='\e[1m'
BRED='\e[91m'
BBLUE='\e[34m'
BGREEN='\e[92m'
BYELLOW='\e[93m'
RESET='\e[0m'
################### Variables ##################
#All of these variables will prompt you for the info in the script if they are left blank with just speech marks like so: =""
#### Locale information & Hostname
KEYMAP="uk"
LOCALE="en_GB.UTF-8"
HOSTNAME=""
# No option to choose if left blank yet. I will add section where it can list the timeone
TIMEZONE="Europe/London"
#Doesn't do anything yet
NTP="TRUE"
#### Disk Information
# Disk to install btrfs on. This disk will be WIPED
DISK=""
EFI_LABEL="EFI"
ENCRYPTED_BTRFS_VOLUMES_LABEL="CRYPTSYTEM"
### Encryption Information
ENCRYPTION_OPTIONS="--perf-no_read_workqueue --perf-no_write_workqueue --type luks2 --cipher aes-xts-plain64 --key-size 512 --iter-time 2000 --pbkdf argon2id --hash sha3-512"
ENCRYPTION_PASSWORD=""
# Doesn't do anything yet
ENCRYPTION_ENABLED="TRUE"
### User accounts
USER_NAME=""
USER_PASSWORD=""
ROOT_PASSWORD=""
# Can be either true, True, TRUE or false, False, FALSE
ENABLE_BLACKARCH=""
ENABLE_MULTILIB="TRUE"
# Change this to true if you have a laptop. It will tune the clock speed of your CPU to improve battery life
AUTOCPUFREQ=""
# Pretty print (function).
info_print () {
echo -e "${BOLD}${BGREEN}[ ${BYELLOW}•${BGREEN} ] $1${RESET}"
}
# Pretty print for input (function).
input_print () {
echo -ne "${BOLD}${BYELLOW}[ ${BGREEN}•${BYELLOW} ] $1${RESET}"
}
# Alert user of bad input (function).
error_print () {
echo -e "${BOLD}${BRED}[ ${BBLUE}•${BRED} ] $1${RESET}"
}
# Virtualization check (function).
virt_check () {
hypervisor=$(systemd-detect-virt)
case $hypervisor in
kvm ) info_print "KVM has been detected, setting up guest tools."
pacman qemu-guest-agent
systemctl enable qemu-guest-agent --root=/mnt
;;
vmware ) info_print "VMWare Workstation/ESXi has been detected, setting up guest tools."
pacman /mnt open-vm-tools
systemctl enable vmtoolsd --root=/mnt
systemctl enable vmware-vmblock-fuse --root=/mnt
;;
oracle ) info_print "VirtualBox has been detected, setting up guest tools."
pacman /mnt virtualbox-guest-utils
systemctl enable vboxservice --root=/mnt
;;
microsoft ) info_print "Hyper-V has been detected, setting up guest tools."
pacman /mnt hyperv
systemctl enable hv_fcopy_daemon --root=/mnt
systemctl enable hv_kvp_daemon --root=/mnt
systemctl enable hv_vss_daemon --root=/mnt
;;
esac
}
# Selecting a kernel to install (function).
kernel_selector () {
info_print "List of kernels:"
info_print "1) Stable: Vanilla Linux kernel with a few specific Arch Linux patches applied"
info_print "2) Hardened: A security-focused Linux kernel"
info_print "3) Longterm: Long-term support (LTS) Linux kernel"
info_print "4) Zen Kernel: A Linux kernel optimized for desktop usage"
input_print "Please select the number of the corresponding kernel (e.g. 1): "
read -r kernel_choice
case $kernel_choice in
1 ) kernel="linux"
return 0;;
2 ) kernel="linux-hardened"
return 0;;
3 ) kernel="linux-lts"
return 0;;
4 ) kernel="linux-zen"
return 0;;
* ) error_print "You did not enter a valid selection, please try again."
return 1
esac
}
# User enters a password for the LUKS Container (function).
lukspass_selector () {
if [ -z "$ENCRYPTION_PASSWORD" ]
then
input_print "Please enter a password for the LUKS container (you're not going to see the password): "
read -r -s lukspass
if [[ -z "$lukspass" ]]; then
echo
error_print "You need to enter a password for the LUKS Container, please try again."
return 1
fi
echo
input_print "Please enter the password for the LUKS container again (you're not going to see the password): "
read -r -s lukspass2
echo
if [[ "$lukspass" != "$lukspass2" ]]; then
error_print "Passwords don't match, please try again."
return 1
fi
return 0
else
lukspass="${ENCRYPTION_PASSWORD}"
fi
}
username_selector () {
if [ -z "$USER_NAME" ]
then
input_print "Please enter name for a user account: "
read -r username
if [[ -z "$username" ]]
then
echo
error_print "You need to enter a username, please try again."
return 1
fi
else
username="${USER_NAME}"
fi
}
userpass_selector () {
if [ -z "$USER_PASSWORD" ]
then
input_print "Please enter a password for $username (you're not going to see the password): "
read -r -s userpass
if [[ -z "$userpass" ]]
then
echo
error_print "You need to enter a password for $username, please try again."
return 1
fi
echo
input_print "Please enter the password again (you're not going to see it): "
read -r -s userpass2
echo
if [[ "$userpass" != "$userpass2" ]]
then
echo
error_print "Passwords don't match, please try again."
return 1
fi
return 0
else
userpass="${USER_PASSWORD}"
fi
}
# Setting up a password for the root account (function).
rootpass_selector () {
if [ -z "$ROOT_PASSWORD" ]
then
input_print "Please enter a password for the root user (you're not going to see it): "
read -r -s rootpass
if [[ -z "$rootpass" ]]
then
echo
error_print "You need to enter a password for the root user, please try again."
return 1
fi
echo
input_print "Please enter the password again (you're not going to see it): "
read -r -s rootpass2
echo
if [[ "$rootpass" != "$rootpass2" ]]
then
error_print "Passwords don't match, please try again."
return 1
fi
return 0
else
rootpass="${ROOT_PASSWORD}"
fi
}
# Microcode detector (function).
microcode_detector () {
CPU=$(grep vendor_id /proc/cpuinfo)
if [[ "$CPU" == *"AuthenticAMD"* ]]; then
info_print "An AMD CPU has been detected, the AMD microcode will be installed."
microcode="amd-ucode"
else
info_print "An Intel CPU has been detected, the Intel microcode will be installed."
microcode="intel-ucode"
fi
}
# User enters a hostname (function).
hostname_selector () {
if [ -z "$HOSTNAME" ]
then
input_print "Please enter the hostname: "
read -r hostname
if [[ -z "$hostname" ]]; then
error_print "You need to enter a hostname in order to continue."
return 1
fi
return 0
else
hostname="${HOSTNAME}"
fi
}
# User chooses the locale (function).
locale_selector () {
if [ -z "$LOCALE" ]
then
input_print "Please insert the locale you use (format: xx_XX. Enter empty to use en_GB, or \"/\" to search locales): " locale
read -r locale
case "$locale" in
'') locale="en_GB.UTF-8"
info_print "$locale will be the default locale."
return 0;;
'/') sed -E '/^# +|^#$/d;s/^#| *$//g;s/ .*/ (Charset:&)/' /etc/locale.gen | less -M
clear
return 1;;
*) if ! grep -q "^#\?$(sed 's/[].*[]/\\&/g' <<< $locale) " /etc/locale.gen; then
error_print "The specified locale doesn't exist or isn't supported."
return 1
fi
return 0
esac
else
locale="${LOCALE}"
fi
}
# User chooses the console keyboard layout (function).
keyboard_selector () {
if [ -z "$KEYMAP" ]
then
input_print "Please insert the keyboard layout to use in console (enter empty to use US, or \"/\" to look up for keyboard layouts): "
read -r kblayout
case "$kblayout" in
'') kblayout="uk"
info_print "The standard UK keyboard layout will be used."
return 0;;
'/') localectl list-keymaps
clear
return 1;;
*) if ! localectl list-keymaps | grep -Fxq "$kblayout"; then
error_print "The specified keymap doesn't exist."
return 1
fi
info_print "Changing console layout to $kblayout."
loadkeys "$kblayout"
return 0
esac
else
kblayout="${KEYMAP}"
loadkeys $kblayout
fi
}
disk_selector () {
if [ -z "$DISK" ]
then
info_print "Here is a list of all the devices detected on your system:"
lsblk -o NAME,TYPE,SIZE,FSAVAIL,MOUNTPOINT,FSTYPE,LABEL
info_print "Available disks for the installation:"
PS3="Please select the number of the corresponding disk (e.g. 1): "
select ENTRY in $(lsblk -dpnoNAME|grep -P "/dev/sd|nvme|vd");
do
DISK="$ENTRY"
info_print "Arch Linux will be installed on the following disk: $DISK"
break
done
else
info_print "Arch Linux will be installed on the following disk: $DISK"
fi
}
install_blackarch () {
info_print "Adding Blackarch repository to pacman config"
arch-chroot /mnt curl https://blackarch.org/strap.sh --output /root/blackarch_strap.sh
arch-chroot /mnt chmod +x /root/blackarch_strap.sh
arch-chroot /mnt /root/blackarch_strap.sh
arch-chroot /mnt rm /root/blackarch_strap.sh
}
ask_enable_blackarch () {
# Ask if you want to add Blackarch mirrors. Leave blank for no
if [ -z "$ENABLE_BLACKARCH" ]
then
input_print "Do you want to add the Blackarch repos to your pacman config (leaving blank will also select no)? [y/N]?: "
read -r blackarch_response
if ! [[ "${blackarch_response,,}" =~ ^(yes|y)$ ]]; then
BLACKARCH="FALSE"
else
BLACKARCH="TRUE"
fi
else
BLACKARCH="${ENABLE_BLACKARCH}"
fi
}
ask_enable_multilib () {
# Ask if you want to add Blackarch mirrors. Leave blank for no
if [ -z "$ENABLE_MULTILIB" ]
then
input_print "Do you want to add the Multilib repos to your pacman config (leaving blank will also select no)? [y/N]?: "
read -r multilib_response
if ! [[ "${multilib_response,,}" =~ ^(yes|y)$ ]]; then
MULTILIB="FALSE"
else
MULTILIB="TRUE"
fi
else
MULTILIB="${ENABLE_MULTILIB}"
fi
}
autocpu_selector () {
if [ -z "$AUTOCPUFREQ" ]
then
input_print "Do you want to download and enable auto-cpufreq? This is recommended if you have a laptop because it tunes your CPU frequency to improve the battery life (Any option other than yes or y will choose no)? [y/N]?: "
read -r autocpufreq_response
if ! [[ "${autocpufreq_response,,}" =~ ^(yes|y)$ ]]; then
AUTOCPUFREQ="FALSE"
else
AUTOCPUFREQ="TRUE"
fi
fi
}
# Welcome screen.
echo -ne "${BOLD}${BYELLOW}
===================================================================================================================
▒██▒ ██ ██████ ████ ████
▓██▓ ██ ██████ ██ ████ ████
████ ██ ██ ██ ██ ██
████ ██░████ ▓████▒ ██░████ ██ ██░████ ▒█████░ ███████ ▒████▓ ██ ██
▒█▓▓█▒ ███████ ███████ ███████▓ ██ ███████▓ ████████ ███████ ██████▓ ██ ██
▓█▒▒█▓ ███░ ▓██▒ ▒█ ███ ▒██ ██ ███ ▒██ ██▒ ░▒█ ██ █▒ ▒██ ██ ██
██ ██ ██ ██░ ██ ██ ██ ██ ██ █████▓░ ██ ▒█████ ██ ██
██████ ██ ██ ██ ██ ██ ██ ██ ░██████▒ ██ ░███████ ██ ██
░██████░ ██ ██░ ██ ██ ██ ██ ██ ░▒▓██ ██ ██▓░ ██ ██ ██
▒██ ██▒ ██ ▓██▒ ░█ ██ ██ ██ ██ ██ █▒░ ▒██ ██░ ██▒ ███ ██▒ ██▒
███ ███ ██ ███████ ██ ██ ██████ ██ ██ ████████ █████ ████████ █████ █████
██▒ ▒██ ██ ▓████▒ ██ ██ ██████ ██ ██ ░▓████▓ ░████ ▓███░██ ░████ ░████
====================================================================================================================
${RESET}"
info_print "Welcome to my Arch Linux install script"
# Function selects keyboard if the KEYMAP variable is empty & it loadkeys the current environment
until keyboard_selector; do : ; done
# If LOCALE is empty, then select locale and setup keyboard
until locale_selector; do : ; done
# If HOSTNAME is empty, then select hostname
until hostname_selector; do : ; done
# Setting up the kernel.
until kernel_selector; do : ; done
until ask_enable_multilib; do : ; done
# if blackarch user variable empty then ask if want to enable blaackarch
until ask_enable_blackarch; do : ; done
#If AUTOCPUFREQ is empty then give option to choose
until autocpu_selector; do : ; done
# Function chooses target for the installation if DISK variable is empty
until disk_selector; do : ; done
# If ENCRYPTION_PASSWORD variable is empty then ask for the encryption password
until lukspass_selector; do : ; done
# If the USER_NAME variable is empty then ask for a username
until username_selector; do : ; done
# If the USER_PASSWORD variable is empty then prompt for a password
until userpass_selector; do : ; done
# If ROOT_PASSWORD is empty, then prompt for a password
until rootpass_selector; do : ; done
# Warn user about deletion of old partition scheme.
input_print "This will delete the current partition table on $DISK once installation starts. Do you agree [y/N]?: "
read -r disk_response
if ! [[ "${disk_response,,}" =~ ^(yes|y)$ ]]; then
error_print "Quitting."
exit
fi
#################### Actual Install ###############
info_print "Wiping $DISK."
wipefs -af "$DISK" &>/dev/null
# Zap drive and clear the gpt partition & create a new one
sgdisk -Zo "$DISK" &>/dev/null
# Creating a new partition scheme.
info_print "Creating the partitions on $DISK."
sgdisk --new=1:0:+512MiB --typecode=1:ef00 --align-end --change-name=1:"${EFI_LABEL}" $DISK &>/dev/null
sgdisk --new=2:0 --typecode=2:8300 --align-end --change-name=2:"${ENCRYPTED_BTRFS_VOLUMES_LABEL}" $DISK &>/dev/null
sgdisk -p $DISK
info_print "Parition Summary:"
sgdisk -v $DISK &>/dev/null
EFI="/dev/disk/by-partlabel/${EFI_LABEL}"
CRYPTSYSTEM="/dev/disk/by-partlabel/${ENCRYPTED_BTRFS_VOLUMES_LABEL}"
BTRFS="/dev/mapper/${ENCRYPTED_BTRFS_VOLUMES_LABEL}"
# Informing the Kernel of the changes.
info_print "Informing the Kernel about the disk changes."
partprobe "$DISK" &>/dev/null
# Formatting the EFI as FAT32.
info_print "Formatting the EFI Partition as FAT32."
#mkfs.fat -F32 -n EFI /dev/disk/by-partlabel/EFI
mkfs.vfat -F32 -n "$EFI_LABEL" $EFI &>/dev/null
# Creating a LUKS Container for the root partition.
info_print "Creating LUKS Container for the root partition."
echo -n "$lukspass" | cryptsetup luksFormat $ENCRYPTION_OPTIONS $CRYPTSYSTEM -d -
echo -n "$lukspass" | cryptsetup --allow-discards --perf-no_read_workqueue --perf-no_write_workqueue --persistent open $CRYPTSYSTEM $ENCRYPTED_BTRFS_VOLUMES_LABEL -d -
# Formatting the LUKS Container as BTRFS.
info_print "Formatting the LUKS container as BTRFS."
mkfs.btrfs -L "$ENCRYPTED_BTRFS_VOLUMES_LABEL" -f $BTRFS
# Mounting $BTRFS to /mnt
info_print "Mounting $BTRFS to /mnt"
mount $BTRFS /mnt
info_print "Creating system BTRFS subvolumes"
btrfs sub create /mnt/@
btrfs sub create /mnt/@home
btrfs sub create /mnt/@abs
btrfs sub create /mnt/@tmp
btrfs sub create /mnt/@srv
btrfs sub create /mnt/@snapshots
btrfs sub create /mnt/btrfs
btrfs sub create /mnt/@log
btrfs sub create /mnt/@cache
info_print "Creating extra subvolumes"
# Extra subvolumes (not necessary)
#mkdir -p /mnt/home/$username/{Documents,ProjectsNStuff}
#btrfs sub create /mnt/home/$username/@Documents
#btrfs sub create /mnt/home/$username/@ProjectsNStuff
info_print "Unmounting /mnt"
# Remember to umount
umount /mnt
# Mounting the newly created subvolumes.
info_print "Mounting the system BTRFS subvolumes."
# Mount options
HDD_MOUNT_OPTIONS="noatime,compress-force=zstd,autodefrag"
SSD_MOUNT_OPTIONS="$HDD_MOUNT_OPTIONS,space_cache=v2,ssd,commit=120,discard=async"
MOUNT_OPTIONS=$SSD_MOUNT_OPTIONS
STRICT_MOUNT_OPTIONS="noexec,nodev,nosuid,$MOUNT_OPTIONS"
mount -o $MOUNT_OPTIONS,subvol=@ $BTRFS /mnt
mkdir -p /mnt/{boot,home,var/cache,var/log,.snapshots,btrfs,var/tmp,var/abs,srv}
mount -o $MOUNT_OPTIONS,subvol=@home $BTRFS /mnt/home
mount -o $MOUNT_OPTIONS,subvol=@srv $BTRFS /mnt/srv
strict_mount_targets="cache log abs tmp"
for target in $(echo $strict_mount_targets)
do mount $BTRFS -o $STRICT_MOUNT_OPTIONS,subvol=@$target /mnt/var/$target
done
mount -o $MOUNT_OPTIONS,subvol=@snapshots $BTRFS /mnt/.snapshots
mount -o $MOUNT_OPTIONS,subvolid=5 $BTRFS /mnt/btrfs
#info_print "Mounting the extra BTRFS subvolumes."
# Extra subvolumes
#mkdir -p /mnt/home/$username/{Documents,ProjectsNStuff}
#mount $BTRFS -o $MOUNT_OPTIONS,subvol=home/${username}/@Documents /mnt/home/${username}/Documents
#mount $BTRFS -o $MOUNT_OPTIONS,subvol=home/${username}/@ProjectsNStuff /mnt/home/${username}/ProjectsNStuff
# Recommended to Disable COW for VM's or databases. Disabling /var/log
#chattr +C /mnt/var/log
mount -o nodev,nosuid,noexec $EFI /mnt/boot
# Checking the microcode to install.
info_print "Detecting whether you have Intel or AMD CPU to install the necessary packages later"
microcode_detector
# Pacman eye-candy features.
info_print "Enabling colours, animations, and parallel downloads for pacman."
sed -i 's/#UseSyslog/UseSyslog/' /etc/pacman.conf
sed -i 's/#Color/Color\\\nILoveCandy/' /etc/pacman.conf
sed -i 's/Color\\/Color/' /etc/pacman.conf
sed -i 's/#TotalDownload/TotalDownload/' /etc/pacman.conf
sed -i 's/#CheckSpace/CheckSpace/' /etc/pacman.conf
sed -i "s/^#ParallelDownloads = 5$/ParallelDownloads = 6/" /etc/pacman.conf
# Use all cores for compilation.
info_print "Configure makepkg.conf to compile packages with all CPU cores"
sed -i "s/-j2/-j$(nproc)/;/^#MAKEFLAGS/s/^#//" /etc/makepkg.conf
info_print "Updating pacman mirrors"
# Update Mirrors
pacman -Syy reflector --needed --noconfirm
reflector --age 12 --latest 10 --sort rate --protocol https --save /etc/pacman.d/mirrorlist
info_print "syncing repositories and downloading keyring"
pacman -Syy archlinux-keyring --noconfirm
# Pacstrap (setting up a base system onto the new root).
info_print "Installing the base system (it may take a while)."
pacstrap /mnt base base-devel "$kernel" "$microcode" linux-firmware "$kernel"-headers btrfs-progs rsync snapper reflector snap-pac zram-generator git zsh gptfdisk booster zstd iwd networkmanager mesa vulkan-intel libva-mesa-driver openssh mesa-vdpau libvirt refind rustup zsh sshguard neovim nano rust-analyzer xdg-user-dirs zram-generator pigz pbzip2 a52dec faac iptables-nft git faad2 flac jasper grim libmad libmpeg2 libtheora libvorbis compsize nftables wavpack xvidcore libde265 polkit-gnome mako slurp libxv noto-fonts btrfs-progs udiskie imv mpv lrzip unrar zip powertop x264 lzip apparmor lz4 wireplumber lzop p7zip noto-fonts-emoji ttf-font-awesome libva-utils man-db chrony cronie dbus-broker lame blueman irqbalance vim polkit-gnome dbus-broker pipewire{,-pulse,-jack,-alsa} --noconfirm
# Generating /etc/fstab.
info_print "Generating a new fstab."
genfstab -L -p /mnt >> /mnt/etc/fstab
info_print "optimizing your makepkg conf"
# Optimize Makepkg
arch-chroot /mnt sed -i 's/^CXXFLAGS.*/CXXFLAGS="-march=native -mtune=native -O2 -pipe -fstack-protector-strong --param=ssp-buffer-size=4 -fno-plt"/' /etc/makepkg.conf
arch-chroot /mnt sed -i 's/^#RUSTFLAGS.*/RUSTFLAGS="-C opt-level=2 -C target-cpu=native"/' /etc/makepkg.conf
arch-chroot /mnt sed -i 's/^#BUILDDIR.*/BUILDDIR=\/tmp\/makepkg/' /etc/makepkg.conf
arch-chroot /mnt sed -i 's/^#MAKEFLAGS.*/MAKEFLAGS="-j$(getconf _NPROCESSORS_ONLN) --quiet"/' /etc/makepkg.conf
arch-chroot /mnt sed -i 's/^COMPRESSGZ.*/COMPRESSGZ=(pigz -c -f -n)/' /etc/makepkg.conf
arch-chroot /mnt sed -i 's/^COMPRESSBZ2.*/COMPRESSBZ2=(pbzip2 -c -f)/' /etc/makepkg.conf
arch-chroot /mnt sed -i 's/^COMPRESSXZ.*/COMPRESSXZ=(xz -T "$(getconf _NPROCESSORS_ONLN)" -c -z --best -)/' /etc/makepkg.conf
arch-chroot /mnt sed -i 's/^COMPRESSZST.*/COMPRESSZST=(zstd -c -z -q --ultra -T0 -22 -)/' /etc/makepkg.conf
arch-chroot /mnt sed -i 's/^COMPRESSLZ.*/COMPRESSLZ=(lzip -c -f)/' /etc/makepkg.conf
arch-chroot /mnt sed -i 's/^COMPRESSLRZ.*/COMPRESSLRZ=(lrzip -9 -q)/' /etc/makepkg.conf
arch-chroot /mnt sed -i 's/^COMPRESSLZO.*/COMPRESSLZO=(lzop -q --best)/' /etc/makepkg.conf
arch-chroot /mnt sed -i 's/^COMPRESSZ.*/COMPRESSZ=(compress -c -f)/' /etc/makepkg.conf
arch-chroot /mnt sed -i 's/^COMPRESSLZ4.*/COMPRESSLZ4=(lz4 -q --best)/' /etc/makepkg.conf
# Use all cores for compilation.
info_print "Configure makepkg.conf to compile packages with all CPU cores"
arch-chroot /mnt sed -i "s/-j2/-j$(nproc)/;/^#MAKEFLAGS/s/^#//" /etc/makepkg.conf
info_print "Customizing pacman config"
# Pacman
arch-chroot /mnt sed -i 's/#UseSyslog/UseSyslog/' /etc/pacman.conf
arch-chroot /mnt sed -i 's/#Color/Color\\\nILoveCandy/' /etc/pacman.conf
arch-chroot /mnt sed -i 's/Color\\/Color/' /etc/pacman.conf
arch-chroot /mnt sed -i 's/#CheckSpace/CheckSpace/' /etc/pacman.conf
arch-chroot /mnt sed -i "s/^#ParallelDownloads = 5$/ParallelDownloads = 6/" /etc/pacman.conf
info_print "Adding Multilib repository to pacman config"
if [[ $MULTILIB = "TRUE" || $MULTILIB = "True" || $MULTILIB = "true" ]]
then
arch-chroot /mnt sed -i "/\[multilib\]/,/Include/"'s/^#//' /etc/pacman.conf
fi
info_print "Adding Blackarch repository to pacman config"
if [[ $BLACKARCH = "TRUE" || $BLACKARCH = "True" || $BLACKARCH = "true" ]]
then
install_blackarch
fi
info_print "Updating pacman mirrors"
# Update Mirrors
arch-chroot /mnt reflector --age 12 --latest 10 --sort rate --protocol https --save /etc/pacman.d/mirrorlist
### Configure the system
# Configure selected locale and console keymap
info_print "Configure locales & keymap"
sed -i "/^#$locale/s/^#//" /mnt/etc/locale.gen
echo "LANG=$locale" > /mnt/etc/locale.conf
echo "KEYMAP=$kblayout" > /mnt/etc/vconsole.conf
# Setting up timezones
info_print "Setting up timezone"
arch-chroot /mnt ln -sf /usr/share/zoneinfo/${TIMEZONE} /etc/localtime
# Setting up clock
info_print "Setting up system clock"
arch-chroot /mnt timedatectl set-ntp true
arch-chroot /mnt hwclock --systohc
# Generate locales
info_print "Generating locales"
arch-chroot /mnt locale-gen
# Setting up the hostname.
info_print "Configure Hostname"
echo "$hostname" > /mnt/etc/hostname
# Setting up hosts file.
info_print "Setting up hosts file at /etc/hosts"
echo -e "\n127.0.0.1\tlocalhost\n::1\t\tlocalhost\n127.0.1.1\t${hostname}.localdomain\t$hostname" >> /mnt/etc/hosts
# Setting root password.
info_print "Setting root password."
echo "root:$rootpass" | arch-chroot /mnt chpasswd
# Setting user password.
info_print "Adding the user $username to the system"
arch-chroot /mnt groupadd adbusers
arch-chroot /mnt groupadd wireshark
arch-chroot /mnt useradd -m -G power,input,audio,wheel,storage,rfkill,network,video,scanner,adbusers,wireshark -s /usr/bin/zsh "$username"
info_print "make users in wheel group not get prompted for password. This is not a recommended setting, it is just temporary for the install"
sed -i '/^# %wheel ALL=(ALL) NOPASSWD: ALL/s/^# //' /etc/sudoers
info_print "Setting user password for $username."
echo "$username:$userpass" | arch-chroot /mnt chpasswd
# Make user not require a password to automate paru commands and other user commands
info_print "Make user not require a password to automate paru commands and other user commands"
echo "$username ALL=(ALL) NOPASSWD: ALL" >> /mnt/etc/sudoers
info_print "Set sudo timestamp_timeout default to 0 "
arch-chroot /mnt echo "Defaults timestamp_timeout=0" >> /etc/sudoers
info_print "setting rustup default build to stable"
arch-chroot /mnt su -c "rustup default stable" -s /bin/sh $username
info_print "Installing Paru"
arch-chroot /mnt /bin/bash -e <<EOF
git clone https://aur.archlinux.org/paru.git /home/$username/paru
chown $username /home/$username/paru
cd /home/$username/paru
su -c "makepkg -si --noconfirm" -s /bin/sh $username
cd /home/$username
rm -r /home/$username/paru
EOF
info_print "Enabling BottomUp setting in paru config"
arch-chroot /mnt sed -i "s/^#BottomUp$/BottomUp/" /etc/paru.conf
# Virtualization check.
info_print "Instaling more packages"
arch-chroot /mnt su -c "paru --noremovemake --batchinstall --noconfirm -S wireplumber irqbalance compsize haveged lzip sbsigntools lrzip powertop p7zip lzop lame unarj libva-utils apparmor arj cpio lha xarchiver slurp grim udiskie libsecret jasper tlp faad2 hyperfine ripgrep sshguard kanshi chrony pbzip2 pigz tokei bc refind-btrfs nohang-git just " $username
#info_print "Installing custom kernel. I will re-compile the kernel later, after boot "
# arch-chroot /mnt su -c "paru --noremovemake --noconfirm --skippgpcheck -S linux-xanmod-tt linux-xanmod-tt-headers" $username
if [[ $AUTOCPUFREQ = "TRUE" ]]
then
info_print "installing cpu-autofreq"
arch-chroot /mnt su -c "paru -S auto-cpufreq --noconfirm" $username
fi
info_print "Enabling Audio power saving by making sound idle if inactive for 10 seconds"
# Save power on laptop by making sound idle if it is inactive for a few seconds
#snd_hda_intel=$(arch-chroot /mnt lspci -k | grep "snd_hda_intel" | grep "in use")
#snd_ac97_codec=$(arch-chroot /mnt lspci -k | grep "snd_ac97_codec" | grep "in use")
#if [ -z $snd_hda_intel ]
#then
# arch-chroot /mnt echo "options snd_ac97_codec power_save=10" > /etc/modprobe.d/audio_powersave.conf
#fi
#if [ -z $snd_ac97_codec ]
#then
# arch-chroot /mnt echo "options snd_hda_intel power_save=10" > /etc/modprobe.d/audio_powersave.conf
#fi
# Since Linux 4.15 there is a new setting called med_power_with_dipm that matches the behaviour of Windows IRST driver settings and should not cause data loss with recent SSD/HDD drives.
info_print "Enable disk power saving mode. power saving can be significant, ranging from 1.0 to 1.5 Watts (when idle)."
arch-chroot /mnt echo 'ACTION=="add", SUBSYSTEM=="scsi_host", KERNEL=="host*", ATTR{link_power_management_policy}="med_power_with_dipm"' > /etc/udev/rules.d/hd_power_save.rules
info_print "Set Network Manager iwd backend"
cat << EOF >> /mnt/etc/NetworkManager/conf.d/nm.conf
[device]
wifi.backend=iwd
EOF
# Prevent snapshot slowdowns
info_print "prevent snapshot slowdown by excluding /etc/updatedb.conf from COW"
arch-chroot /mnt echo 'PRUNENAMES = ".snapshots"' >> /etc/updatedb.conf
# Most important command! Get rid of the beep!
info_print "Disable speaker beep sound when using autocomplete"
arch-chroot /mnt rmmod pcspkr
arch-chroot /mnt echo "blacklist pcspkr" > /etc/modprobe.d/nobeep.conf
info_print "Setting up reflector config file"
cat << EOF > /mnt/etc/xdg/reflector/reflector.conf
# Set the output path where the mirrorlist will be saved (--save).
--save /etc/pacman.d/mirrorlist
# Select the transfer protocol and IP-versions when syncing mirrorlist.
--protocol https
--ipv6
--ipv4
# Use only these countries when using the mirror list
--country GB,DE
# Use only the most recently synchronized mirrors (--latest).
--latest 10
--age 12
# Sort the mirrors by MirrorStatus score
--sort rate
EOF
info_print "Setting up reflector hook to autoupdate every time pacman-mirrorlist is updated"
mkdir /mnt/etc/pacman.d/hooks
cat << EOF > /mnt/etc/pacman.d/hooks/mirrorupgrade.hook
[Trigger]
Operation = Upgrade
Type = Package
Target = pacman-mirrorlist
[Action]
Description = Updating pacman-mirrorlist with reflector
When = PostTransaction
Depends = reflector
Exec = /bin/sh -c 'systemctl start reflector.service'
EOF
info_print "Setting up reflector hook to run refind-install command everytime the refind package is updated"
# Update rEFInd EFI on update
cat << EOF > /etc/pacman.d/hooks/refind.hook
[Trigger]
Operation=Upgrade
Type=Package
Target=refind
[Action]
Description = Updating rEFInd on ESP
When=PostTransaction
Exec=/usr/bin/refind-install
EOF
#Zsh hook
#What this does is refresh the known programs if you install new programs.
info_print "setting up ZSH hook"
cat << EOF > /etc/pacman.d/hooks/zsh.hook
[Trigger]
Operation = Install
Operation = Upgrade
Operation = Remove
Type = Path
Target = usr/bin/*
[Action]
Depends = zsh
When = PostTransaction
Exec = /usr/bin/install -Dm644 /dev/null /var/cache/zsh/pacman
EOF
info_print "Configuring IO Scheduler"
# Better IO Scheduler
cat << EOF > /etc/udev/rules.d/60-ioschedulers.rules
# set scheduler for NVMe
ACTION=="add|change", KERNEL=="nvme[0-9]*", ATTR{queue/scheduler}="none"
# set scheduler for SSD and eMMC
ACTION=="add|change", KERNEL=="sd[a-z]|mmcblk[0-9]*", ATTR{queue/rotational}=="0", ATTR{queue/scheduler}="mq-deadline"
# set scheduler for rotating disks
ACTION=="add|change", KERNEL=="sd[a-z]", ATTR{queue/rotational}=="1", ATTR{queue/scheduler}="bfq"
EOF
info_print "Backup boot every time a file in /usr/lib/modules*/vmlinuz is updated by a package install, upgrade or removal"
cat > /mnt/etc/pacman.d/hooks/50-bootbackup.hook <<EOF
[Trigger]
Operation = Upgrade
Operation = Install
Operation = Remove
Type = Path
Target = usr/lib/modules/*/vmlinuz
[Action]
Depends = rsync
Description = Backing up /boot...
When = PostTransaction
Exec = /usr/bin/rsync -a --delete /boot /.bootbackup
EOF
info_print "Generating Zram"
# Create zram
cat << EOF > /mnt/etc/systemd/zram-generator.conf
# This file is part of the zram-generator project
# https://github.com/systemd/zram-generator
# Edit the values as appropriate
# This section describes the settings for /dev/zram0.
[zram0]
# The size of the zram device, as a function of MemTotal, both in MB.
# For example, if the machine has 1 GiB, and zram-size=ram/4,
# then the zram device will have 256 MiB.
# Fractions in the range 0.1–0.5 are recommended.
#
# The default is "min(ram / 2, 4096)".
zram-size = ram / 4
# The compression algorithm to use for the zram device,
# or leave unspecified to keep the kernel default.
# compression-algorithm = lzo-rle
EOF
info_print "Configure chrony to update NTP servers, detect system time drift, and enable kernel synchronization of the real-time clock (RTC)"
# Chrony
cat <<EOF > /mnt/etc/chrony.conf
# Use public NTP servers from the pool.ntp.org project.
server 0.pool.ntp.org offline
server 1.pool.ntp.org offline
server 2.pool.ntp.org offline
server 3.pool.ntp.org offline
# Record the rate at which the system clock gains/losses time.
driftfile /etc/chrony.drift
# In first three updates step the system clock instead of slew
# if the adjustment is larger than 1 second.
makestep 1.0 3
# Enable kernel synchronization of the real-time clock (RTC).
rtcsync
rtconutc
EOF
cat << EOF > /mnt/etc/NetworkManager/dispatcher.d/10-chrony
#!/bin/sh
INTERFACE=\$1
STATUS=\$2
# Make sure we're always getting the standard response strings
LANG='C'
CHRONY=\$(which chronyc)
chrony_cmd() {
echo "Chrony going \$1."
exec \$CHRONY -a \$1
}
nm_connected() {
[ "\$(nmcli -t --fields STATE g)" = 'connected' ]
}
case "\$STATUS" in
up)
chrony_cmd online
;;
vpn-up)
chrony_cmd online
;;
down)
# Check for active interface, take offline if none is active
nm_connected || chrony_cmd offline
;;
vpn-down)
# Check for active interface, take offline if none is active
nm_connected || chrony_cmd offline
;;
EOF
chmod +x /mnt/etc/NetworkManager/dispatcher.d/10-chrony
#haven't configured arptables yet. add it later and chmod 700 /etc/arptables
sed -i 's/^umask.*/umask\ 077/' /mnt/etc/profile
chmod 700 /mnt/etc/{iptables,nftables.conf}
echo "auth optional pam_faildelay.so delay=4000000" >> /mnt/etc/pam.d/system-login
echo "tcp_bbr" > /mnt/etc/modules-load.d/bbr.conf
echo "write-cache" > /mnt/etc/apparmor/parser.conf
info_print "making sysctl performance tweaks"
cat << EOF >/mnt/etc/sysctl.d/99-sysctl-performance-tweaks.conf
# The swappiness sysctl parameter represents the kernel's preference (or avoidance) of swap space. Swappiness can have a value between 0 and 100, the default value is 60.
# A low value causes the kernel to avoid swapping, a higher value causes the kernel to try to use swap space. Using a low value on sufficient memory is known to improve responsiveness on many systems.
vm.swappiness=10
# The value controls the tendency of the kernel to reclaim the memory which is used for caching of directory and inode objects (VFS cache).
# Lowering it from the default value of 100 makes the kernel less inclined to reclaim VFS cache (do not set it to 0, this may produce out-of-memory conditions)
vm.vfs_cache_pressure=50
# This action will speed up your boot and shutdown, because one less module is loaded. Additionally disabling watchdog timers increases performance and lowers power consumption
# Disable NMI watchdog
#kernel.nmi_watchdog = 0
# Contains, as a percentage of total available memory that contains free pages and reclaimable
# pages, the number of pages at which a process which is generating disk writes will itself start
# writing out dirty data (Default is 20).
vm.dirty_ratio = 5
# Contains, as a percentage of total available memory that contains free pages and reclaimable
# pages, the number of pages at which the background kernel flusher threads will start writing out
# dirty data (Default is 10).
vm.dirty_background_ratio = 5
# This tunable is used to define when dirty data is old enough to be eligible for writeout by the
# kernel flusher threads. It is expressed in 100'ths of a second. Data which has been dirty
# in-memory for longer than this interval will be written out next time a flusher thread wakes up
# (Default is 3000).
#vm.dirty_expire_centisecs = 3000
# The kernel flusher threads will periodically wake up and write old data out to disk. This
# tunable expresses the interval between those wakeups, in 100'ths of a second (Default is 500).
vm.dirty_writeback_centisecs = 1500
# Enable the sysctl setting kernel.unprivileged_userns_clone to allow normal users to run unprivileged containers.
kernel.unprivileged_userns_clone=1
# To hide any kernel messages from the console
kernel.printk = 3 3 3 3
# Restricting access to kernel logs
kernel.dmesg_restrict = 1
# Restricting access to kernel pointers in the proc filesystem
kernel.kptr_restrict = 2
# Disable Kexec, which allows replacing the current running kernel.
kernel.kexec_load_disabled = 1
# Increasing the size of the receive queue.
# The received frames will be stored in this queue after taking them from the ring buffer on the network card.
# Increasing this value for high speed cards may help prevent losing packets:
net.core.netdev_max_backlog = 16384
# Increase the maximum connections
#The upper limit on how many connections the kernel will accept (default 128):
net.core.somaxconn = 8192
# Increase the memory dedicated to the network interfaces
# The default the Linux network stack is not configured for high speed large file transfer across WAN links (i.e. handle more network packets) and setting the correct values may save memory resources:
net.core.rmem_default = 1048576
net.core.rmem_max = 16777216
net.core.wmem_default = 1048576
net.core.wmem_max = 16777216
net.core.optmem_max = 65536
net.ipv4.tcp_rmem = 4096 1048576 2097152
net.ipv4.tcp_wmem = 4096 65536 16777216
net.ipv4.udp_rmem_min = 8192
net.ipv4.udp_wmem_min = 8192
# Enable TCP Fast Open
# TCP Fast Open is an extension to the transmission control protocol (TCP) that helps reduce network latency
# by enabling data to be exchanged during the sender’s initial TCP SYN [3].
# Using the value 3 instead of the default 1 allows TCP Fast Open for both incoming and outgoing connections:
net.ipv4.tcp_fastopen = 3
# Enable BBR
# The BBR congestion control algorithm can help achieve higher bandwidths and lower latencies for internet traffic
net.core.default_qdisc = cake
net.ipv4.tcp_congestion_control = bbr
# TCP SYN cookie protection
# Helps protect against SYN flood attacks. Only kicks in when net.ipv4.tcp_max_syn_backlog is reached:
net.ipv4.tcp_syncookies = 1
# Protect against tcp time-wait assassination hazards, drop RST packets for sockets in the time-wait state. Not widely supported outside of Linux, but conforms to RFC:
net.ipv4.tcp_rfc1337 = 1
# By enabling reverse path filtering, the kernel will do source validation of the packets received from all the interfaces on the machine. This can protect from attackers that are using IP spoofing methods to do harm.