Friday, December 12, 2025

Why Agile left me disappointed and frustrated

Agile software development

Agile can be defined in various ways; the following is one such definition:

Agile software development is an umbrella term for a set of frameworks and practices based on the values and principles expressed in the Manifesto for Agile Software Development and the 12 Principles behind it.

Some of the claimed benefits of Agile include:

  • Faster delivery of working software through iterative development
  • Improved adaptability, allowing teams to respond quickly to changing requirements
  • Greater customer involvement and continuous feedback
  • Better visibility and transparency throughout the project
  • Enhanced team collaboration and communication
  • Early identification of risks and issues through frequent reviews

I did not choose Agile myself; it was imposed on all of us by the company I worked for at the time. From the very beginning, I was never fond of it, and over the following decade I became increasingly aware of its problems and developed a strong dislike for it.

Overbearing, nanny-like process

I am aware that Agile can be applied in different ways and practised with varying approaches. Some argue that if Agile becomes too overbearing or inflexible, it is being implemented incorrectly. However, it often seems that any issues with Agile are dismissed, with the blame consistently placed on the people following the process rather than the methodology itself.

The company I worked for insisted on using the Agile methodology with a Scrum framework. In retrospect, I believe Scrum was the worst part. Simple, straightforward development tasks were transformed into a bizarre kind of kindergarten role-playing, complete with Scrum Masters and user stories. Every working day, people were forced to gather at 10 a.m., march into a meeting room like mindless robots, and repeat the same phrases: “Yesterday I did this…” and “Today I will do this…”, while others stood around silently, staring at the walls or the floor. This monotonous ritual continued for weeks, months, and years, for as long as anyone had the patience to remain with the company.

The Agile Manifesto

The Agile Manifesto outlines the core principles of Agile. I would like to offer my own perspective on its twelve principles.

1. Our highest priority is to satisfy the customer through the early and continuous delivery of valuable software.

The highest priority should not be customer satisfaction at the expense of everything else. This approach is misguided, because customer satisfaction does not depend solely on early software releases. There are many other crucial factors, such as usability, scalability, reliability, and support. Releasing software too early increases the likelihood of defects and design flaws, which can ultimately undermine the user experience.

The drive for early and continuous software delivery can also have a negative impact on team morale. I have personally experienced this many times when management, guided by this principle, set unrealistic deadlines and expected a constant stream of fully tested features, even when the time and resources were insufficient to deliver them.

2. Welcome changing requirements, even late in development. Agile processes harness change for the customer’s competitive advantage.

No, push back against this if you can. It is not an effective way to develop complex projects. The desire to please and satisfy the customer often comes at the expense of the development team. If requirements are constantly changing, this likely indicates that the requirements specification was never properly completed or that the project is inherently too experimental.

Nobody wants to work overtime or on weekends just to meet a project deadline when the customer decides to change the requirements. While Agile does not explicitly mandate such working practices, in reality, this is how many companies operate.

3. Deliver working software frequently, from a couple of weeks to a couple of months, with a preference to the shorter timescale.

Why rush? Are you competing to see who can type the fastest on a keyboard? It all depends on the project. Some projects can be delivered in stages, while others should not be rushed and may take many months before anything tangible can be presented to the customer. The development team should rely on their own judgement and experience to determine the optimal schedule. Just because somebody expects a feature within a week does not necessarily mean it is feasible given the current resources.

Management can sometimes develop a misguided perception that if you are not delivering working software on a weekly basis, you are somehow lazy or incompetent. The constant pressure to justify your role to the company by demonstrating measurable progress each sprint can be overwhelming. It is far more valuable to have knowledgeable and motivated software developers who are not micromanaged by individuals lacking deep technical expertise. Trust developers to do their jobs and to decide when features are ready for release.

4. Business people and developers must work together daily throughout the project.

“Must” is a strong word here. If specific business requirements need to be implemented in software, it can be helpful for developers to understand some of the underlying business practices. This is usually addressed during requirements gathering and can be a valuable interaction. However during the software development, the phrase "too many cooks spoil the broth" is also appropriate here. Software developers need to concentrate on their development tasks and have the freedom to innovate. Frequent requests and critiques from those without deep technical knowledge can often be unwelcome.

5. Build projects around motivated individuals. Give them the environment and support they need, and trust them to get the job done.

Completely agree with this.

6. The most efficient and effective method of conveying information to and within a development team is face-to-face conversation.

This is not always the case. In fact, I personally spent many long hours in face-to-face discussions with people who refused to read documentation or who simply wanted to appear busy, organising numerous repetitive meetings without accomplishing much.

7. Working software is the primary measure of progress.

Absolutely not! People have different skills and can contribute in many ways: updating documentation, fixing bugs, providing help and training to junior developers, volunteering to administer company web or email servers, assisting with customer escalations, and more.

8. Agile processes promote sustainable development. The sponsors, developers, and users should be able to maintain a constant pace indefinitely.

Life is more complicated than this. Greater emphasis should be placed on people, as they naturally experience ups and downs. Maintaining a constant pace can be difficult due to various life events such as bereavement, depression, medical issues, or personal conflicts at home. Treat people fairly and give them some leeway when they need it.

Even in the absence of external pressures, when life is otherwise smooth, constant demands from so-called “efficiency experts” to work better, harder, and faster can still lead some people to develop symptoms of anxiety.

9. Continuous attention to technical excellence and good design enhances agility.

Yes people should aim for technical excellence and good design.

10. Simplicity–the art of maximizing the amount of work not done–is essential.

That sounds ideal, but in reality, developers often have to maintain legacy codebases full of cruft and complexity. It is important to be pragmatic and accept that writing messy code cannot always be avoided.

11. The best architectures, requirements, and designs emerge from self-organizing teams.

Is this a law of nature? If not, I would take it with a very large pinch of salt.

12. At regular intervals, the team reflects on how to become more effective, then tunes and adjusts its behavior accordingly.

It is ultimately up to the team to decide. If they do not find this activity useful, they should not be forced to carry it out at regular intervals.

Final thoughts

Personally, I feel that Agile and its Manifesto are largely overhyped. They have created a huge industry for companies to sell books and training courses. Ultimately, just as I do not need a life coach to guide me through my daily tasks, I also do not need Agile to tell me how to organise my software development tasks.

Monday, December 8, 2025

Installing NetBSD-10 on Raspberry Pi 4

Introduction

Installing NetBSD-10 on the Raspberry Pi 4 is much the same as installing it on the Raspberry Pi 3. Refer to this article for more details: Installing NetBSD-10 on Raspberry Pi 3.

There are however some differences:

  • The Raspberry Pi 4 uses different EEPROM to boot the system and can boot directly from GPT partitions.
  • The Raspberry Pi 4’s UEFI firmware is capable of booting NetBSD-10.

For further information on updating the Raspberry Pi 4’s EEPROM, please refer to this link: Raspberry Pi boot EEPROM.

NetBSD Installation Steps

Several steps are required to install NetBSD. The following sections explain each step in greater detail.

Step 1: Create GPT Partitions

The first step in installing NetBSD is to create required GPT partitions. In this example, a microSD card is used, which is detected as sd0 device:

gpt destroy sd0
gpt create -f sd0
gpt add -a 1m -l "EFI-system"  -t efi  -s 128m sd0
gpt add -a 1m -l "NetBSD-root" -t ffs  -s 8g   sd0
gpt add -a 1m -l "NetBSD-swap" -t swap -s 4g   sd0
gpt add -a 1m -l "NetBSD-var"  -t ffs  -s 4g   sd0
gpt add -a 1m -l "NetBSD-opt"  -t ffs          sd0

Step 2: Create File Systems

Execute dkctl to display the wedges currently mapped to partitions. Note that wedge mappings are dynamic and may differ on your system:

dkctl sd0 listwedges
/dev/rsd0: 5 wedges:
dk1: EFI-system, 262144 blocks at 2048, type: msdos
dk2: NetBSD-root, 16777216 blocks at 264192, type: ffs
dk3: NetBSD-swap, 8388608 blocks at 17041408, type: swap
dk4: NetBSD-var, 8388608 blocks at 25430016, type: ffs
dk5: NetBSD-opt, 90914816 blocks at 33818624, type: ffs

Use the wedge mappings shown above to create the necessary file systems. Note that raw special devices should be used; therefore, the wedges specified in the newfs commands should be /dev/rdkN, where N is the wedge ID:

newfs_msdos -F 32 /dev/rdk1

for i in rdk2 rdk4 rdk5
do
  newfs -B le -O 2ea /dev/${i} || break
done

The EFI partition is formatted as a FAT32 file system, while the remaining partitions (excluding swap) are formatted as NetBSD little-endian (option "-B le") UFS file systems. If you are using the NetBSD big-endian (evbarm-aarch64eb) port, adjust the newfs byte-order option accordingly to create big-endian file systems.

Step 3: Mount File Systems and Extract Files

Mount all file systems:

mkdir /mnt-netbsd-root && mount -o log NAME=NetBSD-root /mnt-netbsd-root &&
mkdir /mnt-netbsd-root/boot && mount -t msdos NAME=EFI-system /mnt-netbsd-root/boot &&
mkdir /mnt-netbsd-root/var && mount -o log NAME=NetBSD-var /mnt-netbsd-root/var &&
mkdir /mnt-netbsd-root/opt && mount -o log NAME=NetBSD-opt /mnt-netbsd-root/opt

Download Raspberry Pi 4 UEFI firmware, NetBSD EFI bootloader, and NetBSD sets. Note that the X11 sets are not included, as the Raspberry Pi 4 will be used in headless/server mode in this setup:

ftp https://github.com/pftf/RPi4/releases/download/v1.50/RPi4_UEFI_Firmware_v1.50.zip
ftp https://cdn.netbsd.org/pub/NetBSD/NetBSD-10.1/evbarm-aarch64/installation/misc/bootaa64.efi

mkdir netbsd_sets
for i in base comp etc games kern-GENERIC64 man misc modules rescue text
do
  ftp -o netbsd_sets/${i}.tar.xz https://cdn.netbsd.org/pub/NetBSD/NetBSD-10.1/evbarm-aarch64/binary/sets/${i}.tar.xz || break
done

Install UEFI firmware and NetBSD bootloader into boot partition:

unzip -d /mnt-netbsd-root/boot RPi4_UEFI_Firmware_v1.50.zip
mkdir -p /mnt-netbsd-root/boot/EFI/BOOT && cp bootaa64.efi /mnt-netbsd-root/boot/EFI/BOOT
sync

Extract NetBSD sets:

for i in base comp etc games kern-GENERIC64 man misc modules rescue text
do
  tar -C /mnt-netbsd-root -xpf netbsd_sets/${i}.tar.xz || break
done
sync

Step 4: Configure NetBSD

Create the /etc/fstab file:

cat > /mnt-netbsd-root/etc/fstab << 'EOF'
NAME=EFI-system    /boot       msdos     rw                0 0
NAME=NetBSD-root   /           ffs       rw,noatime,log    1 1
NAME=NetBSD-var    /var        ffs       rw,noatime,log    1 1
NAME=NetBSD-opt    /opt        ffs       rw,noatime,log    1 2
NAME=NetBSD-swap   none        swap      sw,dp             0 0
kernfs             /kern       kernfs    rw
procfs             /proc       procfs    rw
ptyfs              /dev/pts    ptyfs     rw
tmpfs              /var/shm    tmpfs     rw,-m1777,-sram%25
EOF

Create the additional mount points and the time zone symlink:

mkdir /mnt-netbsd-root/kern /mnt-netbsd-root/proc /mnt-netbsd-root/home
ln -sf ../usr/share/zoneinfo/Europe/London /mnt-netbsd-root/etc/localtime

Create the /etc/rc.conf file:

cat >> /mnt-netbsd-root/etc/rc.conf << 'EOF'
rc_configured=YES
critical_filesystems_local="${critical_filesystems_local} /opt"
hostname="rp4"
domainname="home.lan"

# Static IP config
net_interfaces="genet0"
ifconfig_genet0="inet 192.168.1.1 netmask 255.255.255.0"
dns_search="home.lan"
dns_nameservers="192.168.1.254"
defaultroute="192.168.1.254"

# Dynamic IP config
#dhcpcd=YES
#dhcpcd_flags="-qM genet0"

ip6addrctl=YES
ip6addrctl_policy="ipv4_prefer"

ntpdate=YES
sshd=YES
devpubd=YES
EOF

Step 5: Clean Up

Finally unmount all file systems and remove temporary mount points:

sync &&
umount /mnt-netbsd-root/boot &&
umount /mnt-netbsd-root/opt &&
umount /mnt-netbsd-root/var &&
umount /mnt-netbsd-root &&
rm -rf /mnt-netbsd-root

Step 6: First Boot

Attach the microSD card or USB disk to the Raspberry Pi 4 and power it on.

To enable automatic boot from a specific device, you may need to modify the UEFI firmware boot order: at the UEFI boot screen, press Esc, then navigate to Boot Maintenance ManagerBoot OptinsChange Boot Order, and move the microSD card and USB drive to the top of the list.

To disable the UEFI 3 GiB memory limit, follow these steps: at the UEFI boot screen, press Esc, then navigate to Device ManagerRaspberry Pi ConfigurationAdvanced Configuration, and disable the 3 GiB memory limit option.

Review afterboot(8), then carry out any additional configuration as required.

Note that the newly installed system will have an empty /etc/openssl/certs directory, which may cause problems when connecting to TLS enabled sites. To resolve this, generate the certificates using the /etc/rc.d/certctl_init script. This only needs to be done once, on the first boot:

/etc/rc.d/certctl_init onestart