PanOS Docs

Running PanOS

Guide to booting and running PanOS in QEMU with various configurations and options

Running PanOS

Quick Start

After building PanOS with ./1-build.sh, boot it with:

./2-run.sh

PanOS boots in 3-5 seconds and presents a shell prompt:

/ #

You're ready to run commands. Exit with Ctrl+A then X.

Detailed Run Guide

./2-run.sh

This shows an interactive menu:

═══════════════════════════════════════
  PanOS - Run in QEMU
═══════════════════════════════════════

Memory configuration:
1) 1 GB   (minimum)
2) 2 GB   (recommended for npm/vite) ← DEFAULT
3) 4 GB   (optimal for compilation)

Choose amount of RAM (1-3) [2]:

Choose memory amount:

OptionUse Case
1 GBTesting, minimal apps
2 GBDevelopment (default)
4 GBCompilation, multiple packages

Then QEMU starts with selected configuration.

Method 2: Direct Command

Run QEMU directly without the script:

qemu-system-x86_64 \
    -kernel ~/pan-os-iso/build/vmlinuz \
    -initrd ~/pan-os-iso/build/initramfs.cpio \
    -nographic -serial stdio -monitor none \
    -append "console=ttyS0" \
    -netdev user,id=net0,dns=10.0.2.3 \
    -device virtio-net-pci,netdev=net0 \
    -m 2048 -smp 2

Method 3: From Makefile

make qemu          # Start QEMU with default settings
make run           # Alias for 'make qemu'

Boot Process

Stage 1: QEMU Starts (~1 second)

QEMU emulator version 7.2.0

Stage 2: Kernel Loads (~2 seconds)

[    0.000000] Linux version 6.6.15-arch1 (root@system) (gcc-12.2.0)
[    0.000000] Command line: console=ttyS0
[    0.000000] x86/fpu: Supporting XSAVE feature 0x001: 'x87 floating point registers'
...
[    0.000000] Memory: 2048000K/2062000K available (8544K kernel code, 1456K rwdata)

Stage 3: Initramfs Mounts (~1 second)

[    0.300000] Freeing SMP alternatives memory: 28K
[    0.300000] smpboot: Allowing 2 CPUs, 0 CPUs (hotplug)
[    0.400000] MCP: 1 controllers found: AMD E400

Stage 4: Init Script Runs (~1 second)

[    0.500000] EXT4-fs warning: mounting fs with errors, running e2fsck is recommended
[    0.600000] mount: mounting /proc...
[    0.700000] mount: mounting /sys...

Stage 5: System Ready (~1 second)

╔════════════════════════════════════════╗
║        🚀 PanOS - Shell Ready         ║
╚════════════════════════════════════════╝

Installed commands: 
ls, cat, cp, rm, mv, mkdir, find, grep, awk, sed, ...
node, npm, npx

/ #

Total boot time: 3-5 seconds until shell prompt.

Using PanOS Shell

Basic Commands

# List files
/ # ls -la
total 10
drwxr-xr-x    1 root     root            86 Oct  1 00:00 .
drwxr-xr-x    1 root     root            86 Oct  1 00:00 ..
-rwxr-xr-x    1 root     root         4218 Oct  1 00:00 init
drwxr-xr-x    1 root     root            24 Oct  1 00:00 bin
drwxr-xr-x    1 root     root            22 Oct  1 00:00 sbin
drwxr-xr-x    1 root     root            20 Oct  1 00:00 lib
-drwxr-xr-x    1 root     root             0 Oct  1 00:00 proc
drwxr-xr-x    1 root     root             0 Oct  1 00:00 sys
...

# Check system info
/ # uname -a
Linux panos 6.6.15 #1 SMP x86_64 GNU/Linux

# Show memory usage
/ # free -h
              total        used        free
Mem:        2.0Gi      250.0M      1.8Gi

# Show available disk
/ # df -h
Filesystem                Size      Used Available Use%
tmpfs                     922.0M      6.0M    916.0M   1%

Node.js Commands

# Check Node.js version
/ # node --version
v24.0.0

# Check npm version
/ # npm --version
10.7.0

# Run JavaScript directly
/ # node -e "console.log('Hello from PanOS!')"
Hello from PanOS!

# Run JavaScript file
/ # echo "console.log('Test')" > test.js
/ # node test.js
Test

# Check installed npm packages
/ # npm list -g
/node_modules
├── npm@10.7.0
├── ...

File Operations

# Create directory
/ # mkdir /home/projects
/ # cd /home/projects

# Create file
/ # echo "Hello" > file.txt
/ # cat file.txt
Hello

# Copy files
/ # cp file.txt file-backup.txt

# Remove files
/ # rm file.txt

Running Programs

# Check running processes
/ # ps aux
PID   USER     TIME  COMMAND
    1 root      0:00 /init
   30 root      0:00 /bin/sh
   45 root      0:00 ps aux

# List available commands
/ # ls /bin | head -20
[              chmod         chown         cp
cut            date          dd            df
dmesg          dirname       du            echo
...

# Count total commands available
/ # ls /bin | wc -l
372      # 372 different commands!

Advanced Boot Options

Serial Console Output

Kernel messages go to serial console (shown in terminal):

[    0.000000] Linux version 6.6.15...
[    0.100000] BIOS provided physical RAM map:
...

To suppress kernel messages:

qemu-system-x86_64 \
    -append "console=ttyS0 quiet" \
    ...

Debug Mode

See more verbose output:

qemu-system-x86_64 \
    -append "console=ttyS0 loglevel=7" \
    ...

Network Configuration

PanOS runs with network enabled by default:

# Check network
/ # ip addr
1: lo: <LOOPBACK,UP,LOWER_UP> mtu 65536
    inet 127.0.0.1/8 ...
2: eth0: <BROADCAST,MULTICAST,UP,LOWER_UP> mtu 1500
    inet 10.0.2.15/24 ...

# Ping external host
/ # ping -c 3 8.8.8.8
PING 8.8.8.8 (8.8.8.8): 56 data bytes
64 bytes from 8.8.8.8: seq=0 ttl=63 time=2.043 ms
64 bytes from 8.8.8.8: seq=1 ttl=63 time=1.823 ms
64 bytes from 8.8.8.8: seq=2 ttl=63 time=2.156 ms

Custom Boot Parameters

Append kernel options for different behaviors:

# Quiet boot
-append "console=ttyS0 quiet"

# Enable debug messages
-append "console=ttyS0 debug"

# Custom resolution (if graphics enabled)
-append "console=ttyS0 vga=792"

Installing npm Packages

PanOS includes npm, so you can install packages:

Install Global Package

/ # npm install -g express
added 50 packages, and audited 51 packages

Create Project

/ # mkdir /home/myapp
/ # cd /home/myapp
/ # npm init -y
{
  "name": "myapp",
  "version": "1.0.0",
  ...
}

/ # npm install express

Run Node App

/ # cat > server.js << 'EOF'
const http = require('http');
const server = http.createServer((req, res) => {
  res.writeHead(200, {'Content-Type': 'text/plain'});
  res.end('Hello from PanOS!\n');
});
server.listen(8080, () => {
  console.log('Server running on port 8080');
});
EOF

/ # node server.js
Server running on port 8080

Custom Boot Script

You can create a custom boot script that runs automatically:

Edit /root/boot.js before packaging:

// boot.js
console.log('🚀 PanOS Custom Boot');
console.log('Available memory:', require('os').totalmem() / 1024 / 1024, 'MB');

// Your custom initialization code

The script runs when OS starts if configured in init script.

Exiting PanOS

Exit QEMU

While in PanOS shell:

  1. Type exit to exit shell:

    / # exit
  2. OR Press Ctrl+A then X for hard exit:

    Ctrl+A
    x

QEMU window closes and you return to your terminal.

Save State (if needed)

Note: PanOS in memory is ephemeral - changes don't persist after exit.

To preserve changes:

  • Edit source files before building
  • Rebuild with ./1-build.sh
  • Files in rootfs persist between boots

Performance Tips

Increase RAM for faster operations

For compilation or large npm installs:

./2-run.sh
# Choose option: 3 (4 GB)

More RAM = faster npm install and compilation.

Use multiple CPU cores

Already optimized - script uses all available CPU cores.

Check cores:

/ # nproc
4          # 4 cores available

Disable verbose kernel output

Reduce console spam:

-append "console=ttyS0 quiet"

Troubleshooting Boot Issues

QEMU won't start

Error: "qemu-system-x86_64: command not found"

Solution: Install QEMU:

sudo apt-get install -y qemu-system-x86

Boot hangs (very slow or frozen)

Causes:

  • System under heavy load
  • Disk is very slow
  • Not enough free RAM

Solutions:

  • Close other applications
  • Increase allocated RAM: ./2-run.sh → choose 3
  • Use SSD instead of HDD if possible

Network not working

Error: ping: unknown host or similar

Solution: Network is usually auto-configured. If not:

/ # ip link set eth0 up
/ # dhclient eth0

Can't install npm packages (disk full)

Error: "No space left on device"

Solution: Rootfs is running from RAM. Size limit is allocated memory.

Workaround with more RAM:

./2-run.sh
# Choose option: 3 (4 GB)

Next Steps


Previous: 04-building.mdx
Next: 06-architecture.mdx

On this page