pull/5/merge
Charles Cross 2016-05-27 20:34:49 +00:00
commit b3897996e5
19 changed files with 234 additions and 55 deletions

2
.gitignore vendored
View File

@ -1,5 +1,7 @@
deploy/*
work/*
.vscode/*
config
SKIP
.pc

View File

@ -1,10 +1,25 @@
#TODO
1. Image export
1. NOOBS export
1. Simplify running a single stage
1. Documentation
- NOOBS export
- Simplify running a single stage
- Documentation
#Dependencies
`quilt kpartx realpath qemu-user-static debootstrap zerofree`
# Example build script:
```bash
#!/bin/bash -e
# Set build variables
USERNAME=pi
PASSWORD=raspberry
HOSTNAME=raspberrypi
IMAGENAME="raspbian-lite-$(date +%Y-%m-%d)"
# Build rootfs
sudo ./build.sh --username=${USERNAME} --password=${PASSWORD} --hostname=${HOSTNAME} --imagename=${IMAGENAME}
# Resulting images will be in deploy/
```

124
build.sh
View File

@ -1,10 +1,19 @@
#!/bin/bash -e
##---------------------------
## Functions
##---------------------------
run_sub_stage()
{
log "Begin ${SUB_STAGE_DIR}"
pushd ${SUB_STAGE_DIR} > /dev/null
# Loop through each substage
for i in {00..99}; do
# Check for debconf stage
if [ -f ${i}-debconf ]; then
log "Begin ${SUB_STAGE_DIR}/${i}-debconf"
on_chroot sh -e - << EOF
@ -14,6 +23,8 @@ SELEOF
EOF
log "End ${SUB_STAGE_DIR}/${i}-debconf"
fi
# Install any packages with no-install-recommends set
if [ -f ${i}-packages-nr ]; then
log "Begin ${SUB_STAGE_DIR}/${i}-packages-nr"
PACKAGES=`cat $i-packages-nr | tr '\n' ' '`
@ -24,6 +35,8 @@ EOF
fi
log "End ${SUB_STAGE_DIR}/${i}-packages-nr"
fi
# Install any packages normally
if [ -f ${i}-packages ]; then
log "Begin ${SUB_STAGE_DIR}/${i}-packages"
PACKAGES=`cat $i-packages | tr '\n' ' '`
@ -34,6 +47,8 @@ EOF
fi
log "End ${SUB_STAGE_DIR}/${i}-packages"
fi
# Apply any patches
if [ -d ${i}-patches ]; then
log "Begin ${SUB_STAGE_DIR}/${i}-patches"
pushd ${STAGE_WORK_DIR} > /dev/null
@ -61,11 +76,15 @@ EOF
popd > /dev/null
log "End ${SUB_STAGE_DIR}/${i}-patches"
fi
# Run the substages run script
if [ -x ${i}-run.sh ]; then
log "Begin ${SUB_STAGE_DIR}/${i}-run.sh"
./${i}-run.sh
log "End ${SUB_STAGE_DIR}/${i}-run.sh"
fi
# Run the substages chroot script
if [ -f ${i}-run-chroot ]; then
log "Begin ${SUB_STAGE_DIR}/${i}-run-chroot"
on_chroot sh -e - < ${i}-run-chroot
@ -78,25 +97,42 @@ EOF
run_stage(){
log "Begin ${STAGE_DIR}"
STAGE=$(basename ${STAGE_DIR})
pushd ${STAGE_DIR} > /dev/null
# Unmount this stage's folder on the filesystem
unmount ${WORK_DIR}/${STAGE}
# Set the working directory for this stage
STAGE_WORK_DIR=${WORK_DIR}/${STAGE}
# Set the root directory for this stage
ROOTFS_DIR=${STAGE_WORK_DIR}/rootfs
if [ -f ${STAGE_DIR}/EXPORT_IMAGE ]; then
EXPORT_DIRS="${EXPORT_DIRS} ${STAGE_DIR}"
fi
# Check to see if we should skip this stage (seemingly never)
if [ ! -f SKIP ]; then
# Clean the rootfs, if requested
if [ "${CLEAN}" = "1" ]; then
if [ -d ${ROOTFS_DIR} ]; then
rm -rf ${ROOTFS_DIR}
fi
fi
# Run the pre-run script
if [ -x prerun.sh ]; then
log "Begin ${STAGE_DIR}/prerun.sh"
./prerun.sh
log "End ${STAGE_DIR}/prerun.sh"
fi
# For each substage, run the run_sub_stage command for it
for SUB_STAGE_DIR in ${STAGE_DIR}/*; do
if [ -d ${SUB_STAGE_DIR} ] &&
[ ! -f ${SUB_STAGE_DIR}/SKIP ]; then
@ -104,38 +140,108 @@ run_stage(){
fi
done
fi
# Unmount the stag again
unmount ${WORK_DIR}/${STAGE}
# Set the previous stage info to this stage for the next stage to use
PREV_STAGE=${STAGE}
PREV_STAGE_DIR=${STAGE_DIR}
PREV_ROOTFS_DIR=${ROOTFS_DIR}
popd > /dev/null
log "End ${STAGE_DIR}"
}
##---------------------------
## Start Build
##---------------------------
# Require Root to run
if [ "$(id -u)" != "0" ]; then
echo "Please run as root" 1>&2
exit 1
fi
# Handle input options
for i in "$@"
do
case $i in
--imagename=*)
IMG_NAME="${i#*=}"
shift
;;
# Username to use in rootfs
--username=*)
USER_NAME="${i#*=}"
shift
;;
# Hostname to use in rootfs
--password=*)
PASS_WORD="${i#*=}"
shift
;;
# Hostname to use in rootfs
--hostname=*)
HOST_NAME="${i#*=}"
shift
;;
# unknown option
*)
;;
esac
done
if [ -z "${IMG_NAME}" ];
then
echo "No image name specified, defaulting to \"raspbian\""
IMG_NAME="raspbian"
fi
if [ -z "$USER_NAME" ]
then
echo "No username specified, defaulting to \"pi\""
USER_NAME="pi"
fi
if [ -z "$PASS_WORD" ]
then
echo "No username specified, defaulting to \"raspberry\""
PASS_WORD="raspberry"
fi
if [ -z "$HOST_NAME" ]
then
echo "No hostname specified, defaulting to \"raspberrypi\""
HOST_NAME="raspberrypi"
fi
# Source a config file if it exists
if [ -f config ]; then
source config
fi
if [ -z "${IMG_NAME}" ]; then
echo "IMG_NAME not set" 1>&2
exit 1
fi
export IMG_DATE=${IMG_DATE:-"$(date -u +%Y-%m-%d)"}
# Set and export other env variables
export USER_NAME
export HOST_NAME
export PASS_WORD
export IMG_NAME
export BASE_DIR="$(cd "$(dirname "${BASH_SOURCE[0]}")" && pwd)"
export SCRIPT_DIR="${BASE_DIR}/scripts"
export WORK_DIR="${BASE_DIR}/work/${IMG_DATE}-${IMG_NAME}"
export WORK_DIR="${BASE_DIR}/work/${IMG_NAME}"
export DEPLOY_DIR="${BASE_DIR}/deploy"
export LOG_FILE="${WORK_DIR}/build.log"
export CLEAN
export IMG_NAME
export APT_PROXY
export STAGE
@ -156,9 +262,11 @@ export QUILT_REFRESH_ARGS="-p ab"
source ${SCRIPT_DIR}/common
# Create working directory
mkdir -p ${WORK_DIR}
log "Begin ${BASE_DIR}"
# Successively build each stage
for STAGE_DIR in ${BASE_DIR}/stage*; do
run_stage
done

View File

@ -1,6 +1,6 @@
#!/bin/bash -e
IMG_FILE="${STAGE_WORK_DIR}/${IMG_DATE}-${IMG_NAME}${IMG_SUFFIX}.img"
IMG_FILE="${STAGE_WORK_DIR}/${IMG_NAME}${IMG_SUFFIX}.img"
on_chroot sh -e - <<EOF
/etc/init.d/fake-hwclock stop
@ -27,9 +27,9 @@ unmount_image ${IMG_FILE}
mkdir -p ${DEPLOY_DIR}
rm -f ${DEPLOY_DIR}/image_${IMG_DATE}-${IMG_NAME}${IMG_SUFFIX}.zip
rm -f ${DEPLOY_DIR}/${IMG_NAME}${IMG_SUFFIX}.zip
echo zip ${DEPLOY_DIR}/image_${IMG_DATE}-${IMG_NAME}${IMG_SUFFIX}.zip ${IMG_FILE}
echo zip ${DEPLOY_DIR}/${IMG_NAME}${IMG_SUFFIX}.zip ${IMG_FILE}
pushd ${STAGE_WORK_DIR} > /dev/null
zip ${DEPLOY_DIR}/image_${IMG_DATE}-${IMG_NAME}${IMG_SUFFIX}.zip $(basename ${IMG_FILE})
zip ${DEPLOY_DIR}/${IMG_NAME}${IMG_SUFFIX}.zip $(basename ${IMG_FILE})
popd > /dev/null

View File

@ -1,11 +1,15 @@
#!/bin/bash -e
IMG_FILE="${STAGE_WORK_DIR}/${IMG_DATE}-${IMG_NAME}${IMG_SUFFIX}.img"
IMG_FILE="${STAGE_WORK_DIR}/${IMG_NAME}${IMG_SUFFIX}.img"
echo "Doing cleanup first"
unmount_image ${IMG_FILE}
rm -f ${IMG_FILE}
rm -rf ${ROOTFS_DIR}
echo "Cleanup done"
mkdir -p ${ROOTFS_DIR}
BOOT_SIZE=$(du -sh ${EXPORT_ROOTFS_DIR}/boot -B M | cut -f 1 | tr -d M)

View File

@ -84,6 +84,11 @@ on_chroot() {
}
export -f on_chroot
# This should be used if building on a system that uses systemd (?)
on_chroot2() {
systemd-nspawn -D ${ROOTFS_DIR}/ "$@"
}
update_issue() {
local GIT_HASH=$(git rev-parse HEAD)
echo -e "Raspberry Pi reference ${IMG_DATE}\nGenerated using pi-gen, https://github.com/RPi-Distro/pi-gen, ${GIT_HASH}, ${1}" > ${ROOTFS_DIR}/etc/rpi-issue

View File

@ -1,8 +1,10 @@
#!/bin/bash -e
# Install source lists
install -m 644 files/sources.list ${ROOTFS_DIR}/etc/apt/
install -m 644 files/raspi.list ${ROOTFS_DIR}/etc/apt/sources.list.d/
# Set up proxy, if it exists
if [ -n "$APT_PROXY" ]; then
install -m 644 files/51cache ${ROOTFS_DIR}/etc/apt/apt.conf.d/51cache
sed ${ROOTFS_DIR}/etc/apt/apt.conf.d/51cache -i -e "s|APT_PROXY|${APT_PROXY}|"
@ -10,8 +12,13 @@ else
rm -f ${ROOTFS_DIR}/etc/apt/apt.conf.d/51cache
fi
# Add the raspberry pi gpg key
on_chroot apt-key add - < files/raspberrypi.gpg.key
on_chroot sh -e - << EOF
# Update and dist upgrade
on_chroot sh -e - <<EOF
apt-get update
apt-get dist-upgrade -y
EOF

View File

@ -2,14 +2,14 @@
install -d ${ROOTFS_DIR}/etc/systemd/system/getty@tty1.service.d
install -m 644 files/noclear.conf ${ROOTFS_DIR}/etc/systemd/system/getty@tty1.service.d/noclear.conf
install -m 744 files/policy-rc.d ${ROOTFS_DIR}/usr/sbin/policy-rc.d #TODO: Necessary in systemd?
install -m 744 files/policy-rc.d ${ROOTFS_DIR}/usr/sbin/policy-rc.d
install -v -m 644 files/fstab ${ROOTFS_DIR}/etc/fstab
on_chroot sh -e - <<EOF
if ! id -u pi >/dev/null 2>&1; then
adduser --disabled-password --gecos "" pi
if ! id -u ${USER_NAME} >/dev/null 2>&1; then
adduser --disabled-password --gecos "" ${USER_NAME}
fi
echo "pi:raspberry" | chpasswd
echo "${USER_NAME}:${PASS_WORD}" | chpasswd
echo "root:root" | chpasswd
EOF

View File

@ -1,3 +1,5 @@
proc /proc proc defaults 0 0
/dev/mmcblk0p1 /boot vfat defaults 0 2
/dev/mmcblk0p1 /boot vfat defaults,noatime 0 2
/dev/mmcblk0p2 / ext4 defaults,noatime 0 1
tmpfs /tmp tmpfs defaults,noatime,nodev,nosuid,mode=1777 0 0
tmpfs /var/log tmpfs defaults,size=20m,noatime,nodev,nosuid,mode=1777 0 0

View File

@ -1,9 +0,0 @@
Index: jessie-stage1/rootfs/etc/hosts
===================================================================
--- jessie-stage1.orig/rootfs/etc/hosts
+++ jessie-stage1/rootfs/etc/hosts
@@ -3,3 +3,4 @@
ff02::1 ip6-allnodes
ff02::2 ip6-allrouters
+127.0.1.1 raspberrypi

View File

@ -1,2 +0,0 @@
01-hosts.diff
02-persistant-net.diff

View File

@ -2,8 +2,17 @@
install -m 644 files/ipv6.conf ${ROOTFS_DIR}/etc/modprobe.d/ipv6.conf
install -m 644 files/interfaces ${ROOTFS_DIR}/etc/network/interfaces
install -m 644 files/hostname ${ROOTFS_DIR}/etc/hostname
on_chroot sh -e - << EOF
cat <<EOF > ${ROOTFS_DIR}/etc/hostname
${HOST_NAME}
EOF
# Append hostname
cat <<EOF >> ${ROOTFS_DIR}/etc/hosts
127.0.1.1 ${HOST_NAME}
EOF
on_chroot sh -e - <<EOF
dpkg-divert --add --local /lib/udev/rules.d/75-persistent-net-generator.rules
EOF

View File

@ -0,0 +1 @@
01-persistant-net.diff

View File

@ -1 +0,0 @@
raspberrypi

File diff suppressed because one or more lines are too long

View File

@ -1,13 +1,40 @@
ssh locales less fbset sudo psmisc strace module-init-tools ed ncdu crda
console-setup keyboard-configuration debconf-utils parted unzip
build-essential manpages-dev python bash-completion gdb pkg-config
python-rpi.gpio v4l-utils
ssh
locales
less
fbset
sudo
psmisc
strace
module-init-tools
ed
ncdu
crda
console-setup
keyboard-configuration
debconf-utils
parted
unzip
build-essential
manpages-dev
python
bash-completion
gdb
pkg-config
python-rpi.gpio
v4l-utils
avahi-daemon
lua5.1
luajit
hardlink ca-certificates curl
fake-hwclock ntp nfs-common usbutils
libraspberrypi-dev libraspberrypi-doc libfreetype6-dev
hardlink
ca-certificates
curl
fake-hwclock
ntp
nfs-common
usbutils
libraspberrypi-dev
libraspberrypi-doc
libfreetype6-dev
dosfstools
dphys-swapfile
raspberrypi-sys-mods

View File

@ -10,6 +10,11 @@ install -m 644 files/ttyoutput.conf ${ROOTFS_DIR}/etc/systemd/system/rc-local.
install -m 644 files/50raspi ${ROOTFS_DIR}/etc/apt/apt.conf.d/
install -m 644 files/98-rpi.conf ${ROOTFS_DIR}/etc/sysctl.d/
on_chroot sh -e - <<EOF
# Update locales
dpkg-reconfigure --frontend=noninteractive locales
update-locale LANG=en_US.UTF-8
EOF
on_chroot sh -e - <<EOF
systemctl disable hwclock.sh
@ -21,13 +26,13 @@ systemctl enable apply_noobs_os_config
systemctl enable resize2fs_once
EOF
on_chroot sh -e - << \EOF
for GRP in input spi i2c gpio; do
groupadd -f -r $GRP
done
for GRP in adm dialout cdrom audio users sudo video games plugdev input gpio spi i2c netdev; do
adduser pi $GRP
done
on_chroot sh -e - <<\EOF
for GRP in input spi i2c gpio; do
groupadd -f -r $GRP
done
for GRP in adm dialout cdrom audio users sudo video games plugdev input gpio spi i2c netdev; do
adduser ${USER_NAME} $GRP
done
EOF
on_chroot sh -e - <<EOF

View File

@ -1,2 +1,8 @@
wpasupplicant wireless-tools firmware-atheros firmware-brcm80211 firmware-libertas firmware-ralink firmware-realtek
wpasupplicant
wireless-tools
firmware-atheros
firmware-brcm80211
firmware-libertas
firmware-ralink
firmware-realtek
dhcpcd5