manjaro-arm-installer 25 KB
Newer Older
Strit's avatar
Strit committed
1 2
#! /bin/bash

3
# *****************************
Strit's avatar
Strit committed
4
#       Version 1.2.8
5 6
# *****************************

Strit's avatar
Strit committed
7
# Set globals
8
TMPDIR=/var/tmp/manjaro-arm-installer
9
ARCH='aarch64'
10
NSPAWN='systemd-nspawn -q --resolv-conf=copy-host --timezone=off -D'
Strit's avatar
Strit committed
11

Strit's avatar
Strit committed
12 13 14
# set colorscheme
export DIALOGRC="./dialogrc_gui"

15 16 17 18
# clearing variables
DEVICE=""
EDITION=""
USER=""
19
USERGROUPS=""
Strit's avatar
Strit committed
20
FULLNAME=""
21
PASSWORD=""
Strit's avatar
Strit committed
22 23
CONFIRMPASSWORD=""
CONFIRMROOTPASSWORD=""
24 25
ROOTPASSWORD=""
SDCARD=""
26 27
SDTYP=""
SDDEV=""
28
DEV_NAME=""
29 30
TIMEZONE=""
LOCALE=""
31
HOSTNAME=""
32

33
# check if root
34 35 36 37 38 39
if [ "$EUID" -ne 0 ]; then
    echo "*******************************************************************************************"
    echo "*                                                                                         *"
    echo "*     This script requires root permissions to run. Please run as root or with sudo!      *"
    echo "*                                                                                         *"
    echo "*******************************************************************************************"
40 41 42
  exit
fi

43
# Sanity checks for dependencies
44
if [ ! -f /usr/bin/git ]; then
45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61
    echo "git command is missing! Please install git!"
    exit 1
    elif [ ! -f /usr/bin/parted ]; then
    echo "parted command is missing! Please install parted!"
    exit 1
    elif [ ! -f /usr/bin/systemd-nspawn ]; then
    echo "systemd-nspawn command is missing! Please install systemd!"
    exit 1
    elif [ ! -f /usr/bin/wget ]; then
    echo "wget command is missing! Please install wget!"
    exit 1
    elif [ ! -f /usr/bin/dialog ]; then
    echo "dialog command is missing! Please install dialog!"
    exit 1
    elif [ ! -f /usr/bin/bsdtar ]; then
    echo "bsdtar command is missing! Please install libarchive!"
    exit 1
62
    elif [ ! -f /usr/bin/mkpasswd ]; then
63
    echo "mkpasswd command is missing! Please install debian-whois-mkpasswd!"
64 65 66 67
    exit 1
    elif [ ! -f /usr/bin/awk ]; then
    echo "awk command is missing! Please install gawk!"
    exit 1
68
fi
69

Strit's avatar
Strit committed
70 71

# Functions
72 73 74 75 76 77 78 79
msg() {
    ALL_OFF="\e[1;0m"
    BOLD="\e[1;1m"
    GREEN="${BOLD}\e[1;32m"
      local mesg=$1; shift
      printf "${GREEN}==>${ALL_OFF}${BOLD} ${mesg}${ALL_OFF}\n" "$@" >&2
 }

80 81 82 83 84 85 86
info() {
    ALL_OFF="\e[1;0m"
    BOLD="\e[1;1m"
    BLUE="${BOLD}\e[1;34m"
      local mesg=$1; shift
      printf "${BLUE}  ->${ALL_OFF}${BOLD} ${mesg}${ALL_OFF}\n" "$@" >&2
 }
Strit's avatar
Strit committed
87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108

usage_build_installer() {
    echo "Usage: ${0##*/} [options]"
    echo '    -h                 This help'
    echo ''
    echo ''
    exit $1
}

get_timer(){
    echo $(date +%s)
}

# $1: start timer
elapsed_time(){
    echo $(echo $1 $(get_timer) | awk '{ printf "%0.2f",($2-$1)/60 }')
}

show_elapsed_time(){
    msg "Time %s: %s minutes..." "$1" "$(elapsed_time $2)"
}

109
getarmprofiles () {
110
    info "Getting package lists ready for $DEVICE $EDITION edition..."
111 112 113
    if ls $TMPDIR/arm-profiles/* 1> /dev/null 2>&1; then
        cd $TMPDIR/arm-profiles
        git pull 1> /dev/null 2>&1
114
    else
115 116
        mkdir -p $TMPDIR
        chmod 777 $TMPDIR
117 118
        cd $TMPDIR
        git clone https://gitlab.com/Strit/arm-profiles.git 1> /dev/null 2>&1
119 120 121 122 123 124
    fi

}

create_install() {
    msg "Creating install for $DEVICE..."
125
    info "Used device is ${SDCARD}${SDDEV}"
126 127
    
    # fetch and extract rootfs
128
    info "Downloading latest $ARCH rootfs..."
129
    cd $TMPDIR
130
    wget -q --show-progress --progress=bar:force:noscroll https://osdn.net/projects/manjaro-arm/storage/.rootfs/Manjaro-ARM-$ARCH-latest.tar.gz
131
    
132
    info "Extracting $ARCH rootfs..."
133
    bsdtar -xpf $TMPDIR/Manjaro-ARM-$ARCH-latest.tar.gz -C $TMPDIR/root
Strit's avatar
Strit committed
134
    
135
    info "Setting up keyrings..."
Strit's avatar
Strit committed
136
    $NSPAWN $TMPDIR/root pacman-key --init 1> /dev/null 2>&1
137
    $NSPAWN $TMPDIR/root pacman-key --populate archlinux archlinuxarm manjaro manjaro-arm 1> /dev/null 2>&1
Strit's avatar
Strit committed
138
    
139
    info "Installing packages for $EDITION on $DEVICE..."
Strit's avatar
Strit committed
140
    # Install device and editions specific packages
141
    $NSPAWN $TMPDIR/root pacman -Syyu base manjaro-system manjaro-release systemd systemd-libs $PKG_DEVICE $PKG_EDITION --noconfirm
Strit's avatar
Strit committed
142
    if [[ "$DEVICE" = "rpi4" ]]; then
Strit's avatar
Strit committed
143
    if [[ "$EDITION" = "kde-plasma" ]] || [[ "$EDITION" = "cubocore" ]]; then
144 145
    $NSPAWN $TMPDIR/root pacman -R sddm sddm-kcm matcha-dynamic-sddm --noconfirm
    $NSPAWN $TMPDIR/root pacman -S sddm-compat sddm-kcm matcha-dynamic-sddm --noconfirm
146
    elif [[ "$EDITION" = "lxqt" ]]; then
147 148
    $NSPAWN $TMPDIR/root pacman -R sddm matcha-dynamic-sddm --noconfirm
    $NSPAWN $TMPDIR/root pacman -S sddm-compat matcha-dynamic-sddm --noconfirm
149 150
    fi
    fi
Strit's avatar
Strit committed
151
    
152
    info "Enabling services..."
Strit's avatar
Strit committed
153
    # Enable services
154
    $NSPAWN $TMPDIR/root systemctl enable getty.target haveged.service 1> /dev/null 2>&1
Strit's avatar
Strit committed
155
    $NSPAWN $TMPDIR/root systemctl enable $SRV_EDITION 1> /dev/null 2>&1
156 157 158
    if [ -f $TMPDIR/root/usr/bin/xdg-user-dirs-update ]; then
    $NSPAWN $TMPDIR/root systemctl --global enable xdg-user-dirs-update.service 1> /dev/null 2>&1
    fi
Strit's avatar
Strit committed
159

160
    info "Applying overlay for $EDITION..."
161
    cp -ap $TMPDIR/arm-profiles/overlays/$EDITION/* $TMPDIR/root/
162

163
    info "Setting up users..."
Strit's avatar
Strit committed
164
    #setup users
165
    echo "$USER" > $TMPDIR/user
166 167 168
    echo "$PASSWORD" > $TMPDIR/password
    echo "$ROOTPASSWORD" > $TMPDIR/rootpassword

169
    info "Setting password for root ..."
170 171 172
    $NSPAWN $TMPDIR/root awk -i inplace -F: "BEGIN {OFS=FS;} \$1 == \"root\" {\$2=\"$(mkpasswd --hash=SHA-512 $(cat $TMPDIR/rootpassword))\"} 1" /etc/shadow 1> /dev/null 2>&1

    info "Adding user..."
173
    $NSPAWN $TMPDIR/root useradd -m -G wheel,sys,input,video,storage,lp,network,users,power -p $(mkpasswd --hash=SHA-512 $(cat $TMPDIR/password)) -s /bin/bash $(cat $TMPDIR/user) 1> /dev/null 2>&1
174
    $NSPAWN $TMPDIR/root usermod -aG $USERGROUPS $(cat $TMPDIR/user) 1> /dev/null 2>&1
175
    $NSPAWN $TMPDIR/root chfn -f "$FULLNAME" $(cat $TMPDIR/user) 1> /dev/null 2>&1
176
    
Strit's avatar
Strit committed
177 178 179 180 181 182 183
    info "Enabling user services..."
    if [[ "$EDITION" = "minimal" ]] || [[ "$EDITION" = "server" ]]; then
        echo "No user services for $EDITION edition"
    else
        $NSPAWN $TMPDIR/root --user $(cat $TMPDIR/user) systemctl --user enable pulseaudio.service 1> /dev/null 2>&1
    fi
    
184
    info "Setting up system settings..."
Strit's avatar
Strit committed
185
    #system setup
Strit's avatar
Strit committed
186
    $NSPAWN $TMPDIR/root chmod u+s /usr/bin/ping 1> /dev/null 2>&1
187 188 189 190
    rm -f $TMPDIR/root/etc/ssl/certs/ca-certificates.crt
    rm -f $TMPDIR/root/etc/ca-certificates/extracted/tls-ca-bundle.pem
    cp -a /etc/ssl/certs/ca-certificates.crt $TMPDIR/root/etc/ssl/certs/
    cp -a /etc/ca-certificates/extracted/tls-ca-bundle.pem $TMPDIR/root/etc/ca-certificates/extracted/
191
    $NSPAWN $TMPDIR/root ln -sf /usr/share/zoneinfo/"$TIMEZONE" /etc/localtime 1> /dev/null 2>&1
Strit's avatar
Strit committed
192
    $NSPAWN $TMPDIR/root sed -i s/"#$LOCALE"/"$LOCALE"/g /etc/locale.gen 1> /dev/null 2>&1
193 194
    echo "LANG=$LOCALE" | tee --append $TMPDIR/root/etc/locale.conf 1> /dev/null 2>&1
    $NSPAWN $TMPDIR/root locale-gen
195
    echo "KEYMAP=$CLIKEYMAP" | tee --append $TMPDIR/root/etc/vconsole.conf 1> /dev/null 2>&1
196
    #$NSPAWN $TMPDIR/root localectl set-x11-keymap $KEYMAP 1> /dev/null 2>&1
Strit's avatar
Strit committed
197 198 199 200
    echo 'Section "InputClass"' > $TMPDIR/root/etc/X11/xorg.conf.d/00-keyboard.conf
    echo 'Identifier "system-keyboard"' >> $TMPDIR/root/etc/X11/xorg.conf.d/00-keyboard.conf
    echo 'Option "XkbLayout" "us"' >> $TMPDIR/root/etc/X11/xorg.conf.d/00-keyboard.conf
    echo 'EndSection' >> $TMPDIR/root/etc/X11/xorg.conf.d/00-keyboard.conf
201
    sed -i s/"us"/"$X11KEYMAP"/ $TMPDIR/root/etc/X11/xorg.conf.d/00-keyboard.conf
202
    echo "$HOSTNAME" | tee --append $TMPDIR/root/etc/hostname 1> /dev/null 2>&1
203
    sed -i s/"enable systemd-resolved.service"/"#enable systemd-resolved.service"/ $TMPDIR/root/usr/lib/systemd/system-preset/90-systemd.preset
204

205 206
    echo "Correcting permissions from overlay..."
    chown -R root:root $TMPDIR/root/etc
207
    if [[ "$EDITION" != "minimal" && "$EDITION" != "server" ]]; then
208 209 210
        chown root:polkitd $TMPDIR/root/etc/polkit-1/rules.d
    elif [[ "$EDITION" = "cubocore" ]]; then
        cp $TMPDIR/root/usr/share/applications/corestuff.desktop $TMPDIR/root/etc/xdg/autostart/
211
    fi
212

Strit's avatar
Strit committed
213
    
214
    info "Doing device specific setups for $DEVICE..."
215
    if [[ "$DEVICE" = "rpi3" ]]; then
Strit's avatar
Strit committed
216 217 218
        echo "dtparam=audio=on" | tee --append $TMPDIR/root/boot/config.txt 1> /dev/null 2>&1
        echo "blacklist vchiq" | tee --append $TMPDIR/root/etc/modprobe.d/blacklist-vchiq.conf 1> /dev/null 2>&1
        echo "blacklist snd_bcm2835" | tee --append $TMPDIR/root/etc/modprobe.d/blacklist-vchiq.conf 1> /dev/null 2>&1
219
        echo "LABEL=BOOT  /boot   vfat    defaults        0       0" | tee --append $TMPDIR/root/etc/fstab 1> /dev/null 2>&1
Strit's avatar
Strit committed
220 221
    elif [[ "$DEVICE" = "rpi4" ]]; then
        echo "LABEL=BOOT  /boot   vfat    defaults        0       0" | tee --append $TMPDIR/root/etc/fstab 1> /dev/null 2>&1
222
        $NSPAWN $TMPDIR/root systemctl enable attach-bluetooth.service 1> /dev/null 2>&1
Strit's avatar
Strit committed
223 224
        # fix wifi
        sed -i s/'boardflags3=0x48200100'/'boardflags3=0x44200100'/ $TMPDIR/root/usr/lib/firmware/updates/brcm/brcmfmac43455-sdio.txt 1> /dev/null 2>&1
225
    elif [[ "$DEVICE" = "oc2" ]]; then
226
        $NSPAWN $TMPDIR/root systemctl enable amlogic.service 1> /dev/null 2>&1
227
    elif [[ "$DEVICE" = "on2" ]]; then
228
        echo "LABEL=BOOT  /boot   vfat    defaults        0       0" | tee --append $TMPDIR/root/etc/fstab 1> /dev/null 2>&1
Strit's avatar
Strit committed
229
        sed -i s/'meson64_odroidn2.dtb'/'meson-g12b-odroid-n2.dtb'/ $TMPDIR/boot/boot.ini 1> /dev/null 2>&1
230
    elif [[ "$DEVICE" = "vim1" ]] || [[ "$DEVICE" = "vim2" ]] || [[ "$DEVICE" = "vim3" ]]; then
Strit's avatar
Strit committed
231
        echo "LABEL=BOOT  /boot   vfat    defaults        0       0" | tee --append $TMPDIR/root/etc/fstab 1> /dev/null 2>&1
232
        $NSPAWN $TMPDIR/root systemctl enable bluetooth-khadas.service khadas-utils.service 1> /dev/null 2>&1
233
    elif [[ "$DEVICE" = "pinebook" ]] || [[ "$DEVICE" = "sopine" ]] || [[ "$DEVICE" = "pine64" ]]; then
Strit's avatar
Strit committed
234
        $NSPAWN $TMPDIR/root systemctl enable pinebook-post-install.service 1> /dev/null 2>&1
235 236
        sed -i s/"HOOKS=(base udev autodetect modconf block filesystems keyboard fsck)"/"HOOKS=(base udev autodetect modconf block filesystems keyboard fsck bootsplash-manjaro)"/g $TMPDIR/root/etc/mkinitcpio.conf
        $NSPAWN $TMPDIR/root mkinitcpio -P 1> /dev/null 2>&1
237
    elif [[ "$DEVICE" = "pbpro" ]]; then
238
        sed -i s/"WIFI_PWR_ON_BAT=on"/"WIFI_PWR_ON_BAT=off"/ $TMPDIR/root/etc/default/tlp
239
    elif [[ "$DEVICE" = "rockpi4" ]]; then
240
        sed -i s/"WIFI_PWR_ON_BAT=on"/"WIFI_PWR_ON_BAT=off"/ $TMPDIR/root/etc/default/tlp
241 242 243 244 245 246 247 248 249 250 251 252 253
    elif [[ "$DEVICE" = "pinephone" ]] || [[ "$DEVICE" = "pinetab" ]]; then
        $NSPAWN $TMPDIR/root systemctl enable pinebook-post-install.service 1> /dev/null 2>&1
        sed -i s/"HOOKS=(base udev autodetect modconf block filesystems keyboard fsck)"/"HOOKS=(base udev autodetect modconf block filesystems keyboard fsck bootsplash-manjaro)"/g $TMPDIR/root/etc/mkinitcpio.conf
        $NSPAWN $TMPDIR/root mkinitcpio -P 1> /dev/null 2>&1
        if [[ "$EDITION" = "kde" ]] || [[ "$EDITION" = "cubocore" ]]; then
            sed -i '0,/Session=/s//Session=plasma.desktop/' $TMPDIR/root/etc/sddm.conf
        elif [[ "$EDITION" = "lxqt" ]]; then
            sed -i '0,/Session=/s//Session=/Session=lxqt.desktop/' $TMPDIR/root/etc/sddm.conf
        fi
        if [[ "$EDITION" != "plasma-mobile" ]]; then
        sed -i '0,/User=/s//User=manjaro/' $TMPDIR/rootfs/etc/sddm.conf
        fi

Strit's avatar
Strit committed
254
    else
Strit's avatar
Strit committed
255
        echo "No device specific setting needed for $DEVICE"
Strit's avatar
Strit committed
256 257
    fi
    
258
    info "Cleaning install for unwanted files..."
259
    rm -rf $TMPDIR/root/usr/bin/qemu-aarch64-static
260 261
    rm -rf $TMPDIR/root/var/cache/pacman/pkg/*
    rm -rf $TMPDIR/root/var/log/*
262
    rm -rf $TMPDIR/root/etc/*.pacnew
263 264
    rm -rf $TMPDIR/root/usr/lib/systemd/system/systemd-firstboot.service
    rm -rf $TMPDIR/root/etc/machine-id
265 266
    
    # Remove temp files on host
267 268
    rm -rf $TMPDIR/user $TMPDIR/password $TMPDIR/rootpassword
    rm -rf $TMPDIR/Manjaro-ARM-$ARCH-latest.tar.gz*
Strit's avatar
Strit committed
269

270
    msg "$DEVICE $EDITION install complete"
Strit's avatar
Strit committed
271 272 273
}

prepare_card () {
274
    msg "Getting $SDCARD ready for $DEVICE..."
Strit's avatar
Strit committed
275
    # For Raspberry Pi devices
Strit's avatar
Strit committed
276
    if [[ "$DEVICE" = "rpi3" ]] || [[ "$DEVICE" = "rpi4" ]]; then
277 278 279 280
        # umount SD card
        umount ${SDCARD}${SDDEV}1 1> /dev/null 2>&1
        umount ${SDCARD}${SDDEV}2 1> /dev/null 2>&1

Strit's avatar
Strit committed
281
        #partition with boot and root
282 283
        parted -s $SDCARD mklabel msdos 1> /dev/null 2>&1
        parted -s $SDCARD mkpart primary fat32 0% 100M 1> /dev/null 2>&1
284
        START=`cat /sys/block/$DEV_NAME/${DEV_NAME}1/start` 
Strit's avatar
Strit committed
285
        SIZE=`cat /sys/block/$DEV_NAME/${DEV_NAME}1/size`
286
        END_SECTOR=$(expr $START + $SIZE)
287 288
        parted -s $SDCARD mkpart primary ext4 "${END_SECTOR}s" 100% 1> /dev/null 2>&1
        partprobe $SDCARD 1> /dev/null 2>&1
289 290
        mkfs.vfat "${SDCARD}${SDDEV}1" -n BOOT 1> /dev/null 2>&1
        mkfs.ext4 "${SDCARD}${SDDEV}2" -L ROOT 1> /dev/null 2>&1
291 292
        
        #Mount SD card
Strit's avatar
Strit committed
293 294
        mkdir -p $TMPDIR/root
        mkdir -p $TMPDIR/boot
295 296
        mount ${SDCARD}${SDDEV}1 $TMPDIR/boot
        mount ${SDCARD}${SDDEV}2 $TMPDIR/root
Strit's avatar
Strit committed
297 298

    # For Odroid devices
299
    elif [[ "$DEVICE" = "oc2" ]]; then
300 301
        # umount SD card
        umount ${SDCARD}${SDDEV}1 1> /dev/null 2>&1
302
        umount ${SDCARD}${SDDEV}2 1> /dev/null 2>&1
303

Strit's avatar
Strit committed
304
        #Clear first 8mb
305
        dd if=/dev/zero of=${SDCARD} bs=1M count=8 1> /dev/null 2>&1
306

Strit's avatar
Strit committed
307
    #partition with a single root partition
308 309 310
        parted -s $SDCARD mklabel msdos 1> /dev/null 2>&1
        parted -s $SDCARD mkpart primary ext4 0% 100% 1> /dev/null 2>&1
        partprobe $SDCARD 1> /dev/null 2>&1
311
        mkfs.ext4 -O ^metadata_csum,^64bit ${SDCARD}${SDDEV}1 -L ROOT 1> /dev/null 2>&1
312 313
        
        #Mount SD card
Strit's avatar
Strit committed
314
        mkdir -p $TMPDIR/root
315
        chmod 777 -R $TMPDIR/root
316
        mount ${SDCARD}${SDDEV}1 $TMPDIR/root
317
        
318
   elif [[ "$DEVICE" = "on2" ]] || [[ "$DEVICE" = "vim1" ]] || [[ "$DEVICE" = "vim2" ]] || [[ "$DEVICE" = "vim3" ]]; then
Helmut Stult's avatar
Helmut Stult committed
319 320 321 322
        # umount SD card
        umount ${SDCARD}${SDDEV}1 1> /dev/null 2>&1
        umount ${SDCARD}${SDDEV}2 1> /dev/null 2>&1

323
        #Clear first 8 mb
Strit's avatar
Strit committed
324
        dd if=/dev/zero of=${SDCARD} bs=1M count=8 1> /dev/null 2>&1
325
        
Strit's avatar
Strit committed
326 327 328
    #partition with 2 partitions
        parted -s $SDCARD mklabel msdos 1> /dev/null 2>&1
        parted -s $SDCARD mkpart primary fat32 32M 256M 1> /dev/null 2>&1
329 330
        START=`cat /sys/block/$DEV_NAME/${DEV_NAME}1/start`
        SIZE=`cat /sys/block/$DEV_NAME/${DEV_NAME}1/size`
Strit's avatar
Strit committed
331 332 333
        END_SECTOR=$(expr $START + $SIZE)
        parted -s $SDCARD mkpart primary ext4 "${END_SECTOR}s" 100% 1> /dev/null 2>&1
        partprobe $SDCARD 1> /dev/null 2>&1
334
        mkfs.vfat "${SDCARD}${SDDEV}1" -n BOOT 1> /dev/null 2>&1
335
        mkfs.ext4 "${SDCARD}${SDDEV}2" -L ROOT 1> /dev/null 2>&1
Strit's avatar
Strit committed
336 337 338 339
        
    #copy rootfs contents over to the FS
        mkdir -p $TMPDIR/root
        mkdir -p $TMPDIR/boot
340 341
        mount ${SDCARD}${SDDEV}1 $TMPDIR/boot
        mount ${SDCARD}${SDDEV}2 $TMPDIR/root
Strit's avatar
Strit committed
342
        
Strit's avatar
Strit committed
343

344
    # For pine devices
345
    elif [[ "$DEVICE" = "pinebook" ]] || [[ "$DEVICE" = "sopine" ]] || [[ "$DEVICE" = "pine64" ]]; then
346 347
        # umount SD card
        umount ${SDCARD}${SDDEV}1 1> /dev/null 2>&1
348
        umount ${SDCARD}${SDDEV}2 1> /dev/null 2>&1
Strit's avatar
Strit committed
349 350

    #Clear first 8mb
351
        dd if=/dev/zero of=${SDCARD} bs=1M count=8 1> /dev/null 2>&1
352

Strit's avatar
Strit committed
353
    #partition with a single root partition
354 355 356
        parted -s $SDCARD mklabel msdos 1> /dev/null 2>&1
        parted -s $SDCARD mkpart primary ext4 0% 100% 1> /dev/null 2>&1
        partprobe $SDCARD 1> /dev/null 2>&1
357
        mkfs.ext4 -O ^metadata_csum,^64bit ${SDCARD}${SDDEV}1 -L ROOT 1> /dev/null 2>&1
358 359
        
        # Mount SD card
Strit's avatar
Strit committed
360
        mkdir -p $TMPDIR/root
361
        chmod 777 -R $TMPDIR/root
362
        mount ${SDCARD}${SDDEV}1 $TMPDIR/root
363

Strit's avatar
Strit committed
364
    # For rockpro64 device
Strit's avatar
Strit committed
365
    elif [[ "$DEVICE" = "rock64" ]] || [[ "$DEVICE" = "rockpro64" ]] || [[ "$DEVICE" = "rockpi4" ]]  || [[ "$DEVICE" = "pbpro" ]]; then
366 367
        # umount SD card
        umount ${SDCARD}${SDDEV}1 1> /dev/null 2>&1
368
        umount ${SDCARD}${SDDEV}2 1> /dev/null 2>&1
Strit's avatar
Strit committed
369 370

    #Clear first 8mb
371
        dd if=/dev/zero of=${SDCARD} bs=1M count=32 1> /dev/null 2>&1
372

Strit's avatar
Strit committed
373
    #partition with a single root partition
374 375 376
        parted -s $SDCARD mklabel msdos 1> /dev/null 2>&1
        parted -s $SDCARD mkpart primary ext4 32M 100% 1> /dev/null 2>&1
        partprobe $SDCARD 1> /dev/null 2>&1
377
        mkfs.ext4 -O ^metadata_csum,^64bit ${SDCARD}${SDDEV}1 -L ROOT 1> /dev/null 2>&1
378 379
        
        # Mount SD card
Strit's avatar
Strit committed
380
        mkdir -p $TMPDIR/root
381
        chmod 777 -R $TMPDIR/root
382
        mount ${SDCARD}${SDDEV}1 $TMPDIR/root
383 384 385 386 387 388
    fi
}

cleanup () {
    msg "Writing bootloader and cleaning up after install..."
   # For Raspberry Pi devices
Strit's avatar
Strit committed
389
    if [[ "$DEVICE" = "rpi3" ]] || [[ "$DEVICE" = "rpi4" ]]; then
390
       #move boot files
391
        mv $TMPDIR/root/boot/* $TMPDIR/boot
392 393
        
        #clean up
394 395 396 397
        umount $TMPDIR/root
        umount $TMPDIR/boot
        rm -r $TMPDIR/root $TMPDIR/boot
        partprobe $SDCARD 1> /dev/null 2>&1
398
        
399
    # For Odroid devices
400
    elif [[ "$DEVICE" = "oc2" ]]; then
401 402
    #flash bootloader
        cd $TMPDIR/root/boot/
403
        ./sd_fusing.sh $SDCARD 1> /dev/null 2>&1
404 405 406
        cd ~

    #clean up
407 408 409
        umount $TMPDIR/root
        rm -r $TMPDIR/root
        partprobe $SDCARD 1> /dev/null 2>&1
410
        
411
    elif [[ "$DEVICE" = "on2" ]] || [[ "$DEVICE" = "vim1" ]] || [[ "$DEVICE" = "vim2" ]] || [[ "$DEVICE" = "vim3" ]]; then
412 413
    # move boot files
        mv $TMPDIR/root/boot/* $TMPDIR/boot
414
    if [[ "$DEVICE" = "on2" ]]; then
Strit's avatar
Strit committed
415
    #flash bootloader
416 417
        dd if=$TMPDIR/boot/u-boot.bin of=${LDEV} conv=fsync,notrunc bs=512 seek=1 1> /dev/null 2>&1
    fi
418 419 420 421 422 423
        
    #clean up
        umount $TMPDIR/root
        umount $TMPDIR/boot
        losetup -d $LDEV 1> /dev/null 2>&1
        rm -r $TMPDIR/root $TMPDIR/boot
Strit's avatar
Strit committed
424 425
        partprobe $SDCARD 1> /dev/null 2>&1
        
426
    # For pine device
427
    elif [[ "$DEVICE" = "pinebook" ]] || [[ "$DEVICE" = "sopine" ]] || [[ "$DEVICE" = "pine64" ]]; then
428
    #flash bootloader
429
        dd if=$TMPDIR/root/boot/u-boot-sunxi-with-spl-$DEVICE.bin of=${SDCARD} bs=8k seek=1 1> /dev/null 2>&1
430 431
        
    #clean up
432 433 434
        umount $TMPDIR/root
        rm -r $TMPDIR/root
        partprobe $SDCARD 1> /dev/null 2>&1
Strit's avatar
Strit committed
435
        
436
        
437
    # For rockchip devices
Strit's avatar
Strit committed
438
    elif [[ "$DEVICE" = "rock64" ]] || [[ "$DEVICE" = "rockpro64" ]] || [[ "$DEVICE" = "rockpi4" ]]  || [[ "$DEVICE" = "pbpro" ]]; then
Strit's avatar
Strit committed
439
    #flash bootloader
440 441 442
        dd if=$TMPDIR/root/boot/idbloader.img of=${SDCARD} seek=64 conv=notrunc 1> /dev/null 2>&1
        dd if=$TMPDIR/root/boot/uboot.img of=${SDCARD} seek=16384 conv=notrunc 1> /dev/null 2>&1
        dd if=$TMPDIR/root/boot/trust.img of=${SDCARD} seek=24576 conv=notrunc 1> /dev/null 2>&1
Strit's avatar
Strit committed
443 444
        
    #clean up
445 446 447
        umount $TMPDIR/root
        rm -r $TMPDIR/root
        partprobe $SDCARD 1> /dev/null 2>&1
448 449
        
fi
Strit's avatar
Strit committed
450 451
}

452 453

# Using Dialog to ask for user input for variables
454
DEVICE=$(dialog --clear --title "Manjaro ARM Installer" \
Helmut Stult's avatar
Helmut Stult committed
455
        --menu "Choose a device:" 20 75 10 \
456
        "rpi4"      "Raspberry Pi 4" \
Strit's avatar
Strit committed
457
        "pbpro"     "Pinebook Pro" \
458
		"pinebook"  "Pinebook" \
459 460 461
		"rock64"    "Rock64" \
		"rockpro64" "RockPro64" \
		"sopine"    "Sopine / Pine64-LTS" \
462
		"pine64"    "Pine64+" \
463
		"oc2"       "Odroid C2" \
464
		"on2"       "Odroid N2" \
Strit's avatar
Strit committed
465
		"vim3"      "Khadas Vim 3" \
466
		"rockpi4"   "Rock Pi 4" \
Helmut Stult's avatar
Helmut Stult committed
467
		"rpi3"      "Raspberry Pi 3" \
Strit's avatar
Strit committed
468
		"vim1"      "Khadas Vim 1" \
469
		3>&1 1>&2 2>&3 3>&-)
470 471 472


#The if statement makes sure that the user has put in something in the previous prompt. If not (left blank or pressed cancel) the script will end
Helmut Stult's avatar
Helmut Stult committed
473 474 475 476
if [ ! -z "$DEVICE" ]; then
	EDITION=$(dialog --clear --title "Manjaro ARM Installer" \
		--menu "Choose an edition:" 20 75 10 \
		"minimal"   "Minimal Edition            (only CLI)" \
477
		"kde-plasma" "Full KDE/Plasma Desktop    (full featured)" \
478
		"xfce"      "Full XFCE desktop and apps (full featured)" \
479
		"mate"      "Full MATE desktop and apps (lightweight)" \
Helmut Stult's avatar
Helmut Stult committed
480 481 482 483
		"lxqt"      "Full LXQT Desktop and apps (lightweight)" \
		"i3"        "Mininal i3 WM with apps    (very light)" \
		"cubocore"  "QT based Desktop           (lightweight)" \
		3>&1 1>&2 2>&3 3>&-) 
484 485 486 487 488 489 490

else 
	clear
	exit 1
fi


Helmut Stult's avatar
Helmut Stult committed
491 492
if [ ! -z "$EDITION" ]; then
	USER=$(dialog --clear --title "Manjaro ARM Installer" \
493 494
	--inputbox "Enter username:
(usernames most be all lowercase)" 8 50 \
Helmut Stult's avatar
Helmut Stult committed
495
	3>&1 1>&2 2>&3 3>&-)
Strit's avatar
Strit committed
496 497 498 499 500
    if [[ "$USER" =~ [A-Z] ]] || [[ "$USER" == *['!'@#\$%^\&*()_+]* ]]; then
    clear
    msg "Configuration aborted! Username contained invalid characters."
    exit 1
    fi
501 502 503 504 505
else 
	clear
	exit 1
fi

506 507
if [ ! -z "$USER" ]
then
508 509
USERGROUPS=$(dialog --clear --title "Manjaro ARM Installer" \
    --inputbox "Enter additional groups for $USER in a comma seperated list: (empty if none)
510
(default: wheel,sys,input,video,storage,lp,network,users,power)" 8 90 \
511 512 513 514 515 516 517 518 519 520
        3>&1 1>&2 2>&3 3>&- \
	)
else 
	clear
	exit 1
fi

if [ ! -z "$USER" ]
then
FULLNAME=$(dialog --clear --title "Manjaro ARM Installer" \
521 522 523 524 525 526 527
    --inputbox "Enter Full Name for $USER:" 8 50 \
        3>&1 1>&2 2>&3 3>&- \
	)
else
    clear
    exit 1
fi
528 529


530
if [ ! -z "$FULLNAME" ]; then
Helmut Stult's avatar
Helmut Stult committed
531
	PASSWORD=$(dialog --clear --title "Manjaro ARM Installer" \
532
	--insecure --passwordbox "Enter Password for $USER:" 8 50 \
Helmut Stult's avatar
Helmut Stult committed
533
	3>&1 1>&2 2>&3 3>&- \
534 535 536 537 538 539
	)
else 
	clear
	exit 1
fi

Helmut Stult's avatar
Helmut Stult committed
540 541
if [ ! -z "$PASSWORD" ]; then
	CONFIRMPASSWORD=$(dialog --clear --title "Manjaro ARM Installer" \
Strit's avatar
Strit committed
542
	--insecure --passwordbox "Confirm Password for $USER:" 8 50 \
Helmut Stult's avatar
Helmut Stult committed
543
	3>&1 1>&2 2>&3 3>&- \
Strit's avatar
Strit committed
544 545 546 547 548
	)
else 
	clear
	exit 1
fi
549

Strit's avatar
Strit committed
550
if [[ "$PASSWORD" != "$CONFIRMPASSWORD" ]]; then
Helmut Stult's avatar
Helmut Stult committed
551 552 553
	clear
	msg "User passwords do not match! Please restart the installer and try again."
	exit 1
Strit's avatar
Strit committed
554
fi
555

Helmut Stult's avatar
Helmut Stult committed
556 557
if [ ! -z "$CONFIRMPASSWORD" ]; then
	ROOTPASSWORD=$(dialog --clear --title "Manjaro ARM Installer" \
558
	--insecure --passwordbox "Enter Root Password:" 8 50 \
Helmut Stult's avatar
Helmut Stult committed
559
	3>&1 1>&2 2>&3 3>&- \
560 561 562 563 564 565
	)
else 
	clear
	exit 1
fi

Helmut Stult's avatar
Helmut Stult committed
566 567
if [ ! -z "$ROOTPASSWORD" ]; then
	CONFIRMROOTPASSWORD=$(dialog --clear --title "Manjaro ARM Installer" \
Strit's avatar
Strit committed
568
	--insecure --passwordbox "Confirm Root Password:" 8 50 \
Helmut Stult's avatar
Helmut Stult committed
569
	3>&1 1>&2 2>&3 3>&- \
Strit's avatar
Strit committed
570 571 572 573 574
	)
else 
	clear
	exit 1
fi
575

Strit's avatar
Strit committed
576
if [[ "$ROOTPASSWORD" != "$CONFIRMROOTPASSWORD" ]]; then
Helmut Stult's avatar
Helmut Stult committed
577 578 579
	clear
	msg "Root passwords do not match! Please restart the installer and try again."
	exit 1
Strit's avatar
Strit committed
580
fi
581

Strit's avatar
Strit committed
582
if [ ! -z "$CONFIRMROOTPASSWORD" ]
583 584 585
then

# simple command to put the results of lsblk (just the names of the devices) into an array and make that array populate the options	
Helmut Stult's avatar
Helmut Stult committed
586 587 588 589 590 591 592
	let i=0
	W=()
	while read -r line; do
		let i=$i+1
		W+=($line "")
	done < <( lsblk -dn -o NAME )
	SDCARD=$(dialog --title "Manjaro ARM Installer" \
593
	--menu "Choose your SDCard - Be sure the correct drive is selected!" 20 50 10 \
Helmut Stult's avatar
Helmut Stult committed
594
	"${W[@]}" 3>&2 2>&1 1>&3)
595 596

# add /dev/ to the selected option above
Helmut Stult's avatar
Helmut Stult committed
597 598 599
	DEV_NAME=$SDCARD
	SDCARD=/dev/$SDCARD
	SDTYP=${SDCARD:5:2}
600 601 602
else 
	clear
	exit 1
Helmut Stult's avatar
Helmut Stult committed
603
fi
604

Helmut Stult's avatar
Helmut Stult committed
605 606 607 608 609 610 611
if [[ "$SDTYP" = "sd" ]]; then
	SDDEV=""
elif [[ "$SDTYP" = "mm" ]]; then
	SDDEV="p"
else 
	clear
	exit 1
612 613 614
fi


Helmut Stult's avatar
Helmut Stult committed
615 616 617 618 619 620 621 622 623 624
if [ ! -z "$SDCARD" ]; then
	let i=0
	W=()
	while read -r line; do
		let i=$i+1
		W+=($line "")
	done < <( timedatectl list-timezones )
	TIMEZONE=$(dialog --clear --title "Manjaro ARM Installer" \
	--menu "Choose your timezone!" 20 50 15 \
	"${W[@]}" 3>&1 1>&2 2>&3 3>&- \
625 626 627 628 629
	)
else 
	clear
	exit 1
fi
630 631


Helmut Stult's avatar
Helmut Stult committed
632 633 634 635 636 637 638 639 640 641 642
if [ ! -z "$TIMEZONE" ]; then
	let i=0
	W=()
	while read -r line; do
		let i=$i+1
		W+=($line "")
	done < <( cat /etc/locale.gen | grep "UTF-8" | tail -n +2 | awk '{print $1}' | sed -e 's/^#*//' )
	LOCALE=$(dialog --clear --title "Manjaro ARM Installer" \
		--menu "Choose your locale!" 20 50 15 \
		"${W[@]}" 3>&1 1>&2 2>&3 3>&- \
		)
643 644 645 646 647
else 
	clear
	exit 1
fi

Helmut Stult's avatar
Helmut Stult committed
648 649 650 651 652 653 654
if [ ! -z "$LOCALE" ]; then
	let i=0
	W=()
	while read -r line; do
		let i=$i+1
		W+=($line "")
	done < <( localectl list-keymaps )
655 656
	CLIKEYMAP=$(dialog --clear --title "Manjaro ARM Installer" \
		--menu "Choose your TTY keyboard layout:" 20 50 15 \
Helmut Stult's avatar
Helmut Stult committed
657
		"${W[@]}" 3>&1 1>&2 2>&3 3>&- \
658 659 660 661 662 663
	)
else 
	clear
	exit 1
fi

664 665 666 667 668 669 670 671 672 673 674 675 676 677 678 679 680
if [ ! -z "$CLIKEYMAP" ]; then
	let i=0
	W=()
	while read -r line; do
		let i=$i+1
		W+=($line "")
	done < <( localectl list-x11-keymap-layouts )
	X11KEYMAP=$(dialog --clear --title "Manjaro ARM Installer" \
		--menu "Choose your X11 keyboard layout:" 20 50 15 \
		"${W[@]}" 3>&1 1>&2 2>&3 3>&- \
	)
else 
	clear
	exit 1
fi

if [ ! -z "$X11KEYMAP" ]; then
Helmut Stult's avatar
Helmut Stult committed
681
	HOSTNAME=$(dialog --clear --title "Manjaro ARM Installer" \
682
	--inputbox "Enter desired hostname for this system:" 8 50 \
683
	3>&1 1>&2 2>&3 3>&- \
684 685 686 687 688 689
	)
else 
	clear
	exit 1
fi

Helmut Stult's avatar
Helmut Stult committed
690 691
if [ ! -z "$HOSTNAME" ]; then
	dialog --clear --title "Manjaro ARM Installer" \
692
    --yesno "Is the below information correct:
693 694
    Device = $DEVICE
    Edition = $EDITION
695
    Username = $USER
696
    Additional usergroups = $USERGROUPS
697 698
    Password for $USER = (password hidden)
    Password for root = (password hidden)
699
    SD Card = $SDCARD
700
    Timezone = $TIMEZONE
701
    Locale = $LOCALE
702 703
    TTY Keyboard layout = $CLIKEYMAP
    X11 Keyboard layout = $X11KEYMAP
Helmut Stult's avatar
Helmut Stult committed
704
    Hostname = $HOSTNAME" 20 70 \
705 706
    3>&1 1>&2 2>&3 3>&-
else
Helmut Stult's avatar
Helmut Stult committed
707 708
	clear
	exit 1
709 710 711 712 713 714 715 716 717
fi

response=$?
case $response in
   0) clear; msg "Proceeding....";;
   1) clear; msg "Installation aborted...."; exit 1;;
   255) clear; msg "Installation aborted..."; exit 1;;
esac

718

719 720
# get the profiles
getarmprofiles
Strit's avatar
Strit committed
721 722

#Package lists
723 724 725
PKG_DEVICE=$(grep "^[^#;]" $TMPDIR/arm-profiles/devices/$DEVICE | awk '{print $1}')
PKG_EDITION=$(grep "^[^#;]" $TMPDIR/arm-profiles/editions/$EDITION | awk '{print $1}')
SRV_EDITION=$(grep "^[^#;]" $TMPDIR/arm-profiles/services/$EDITION | awk '{print $1}')
Strit's avatar
Strit committed
726

727

Strit's avatar
Strit committed
728
# Commands
729
timer_start=$(get_timer)
Strit's avatar
Strit committed
730 731

prepare_card
732 733 734 735
create_install
cleanup
show_elapsed_time "${FUNCNAME}" "${timer_start}"
sync