跳转至

脚本

概述

你可以创建脚本来自动化执行一系列 iPXE 命令。任何能在 iPXE 命令行中输入的命令都可以在脚本中使用。完整的命令列表见 iPXE 命令参考

iPXE 脚本是一个以魔数行 #!ipxe 开头、包含一系列 iPXE 命令的纯文本文件。例如,下面这个简单的脚本先通过 DHCP 获取 IP 地址,然后引导 iPXE 演示镜像:

  #!ipxe

  dhcp
  chain http://boot.ipxe.org/demo/boot.php

下面是另一个简单的脚本,它先创建一个 VLAN,然后从中引导:

  #!ipxe

  vcreate --tag 24 net0
  autoboot net0-24

下面这个脚本稍微复杂一些,它会不断重试 DHCP,直到成功获取引导文件名:

  #!ipxe

  :retry_dhcp
  dhcp && isset ${filename} || goto retry_dhcp
  echo Booting from ${filename}
  chain ${filename}

你可以用任何文本编辑器创建 iPXE 脚本,比如 emacsvi,甚至 Windows 记事本。iPXE 脚本不需要特定的文件扩展名(如 .txt.ipxe);只要以魔数行 #!ipxe 开头,iPXE 就会把它识别为脚本。[^1]

流程控制

A flowchart

你可以使用 goto 命令跳转到预定义的脚本标签。定义标签的语法是:

  :<label>

跳转到该标签的语法是:

  goto label

例如:

  #!ipxe

  :loop
  echo Hello world
  goto loop

你可以使用 &&|| 运算符,根据前面命令的执行状态有条件地执行命令。例如:

  dhcp && echo DHCP succeeded

  dhcp || echo DHCP failed

这两个运算符与 goto 命令结合使用,可以实现简单的条件流程控制。例如,不断重试 DHCP 直到成功:

  #!ipxe

  :retry_dhcp
  dhcp || goto retry_dhcp

你可以使用 ; 运算符,无论前面命令的执行状态如何都继续执行命令。例如:

  echo IP address: ${net0/ip} ; echo Subnet mask: ${net0/netmask}

你可以随时使用 exit 命令终止脚本。

错误处理

Warning

如果脚本的任意一行执行失败,iPXE 会立即终止该脚本。例如,对于脚本:

  #!ipxe

  dhcp
  route

如果 dhcp 命令失败,脚本会立即终止,不会继续执行下一行。你可以使用 || 运算符改变这一行为:

  #!ipxe

  dhcp ||
  route

在这个例子中,|| 运算符后面的空命令被视为"什么都不做,且执行成功"(类似于类 Unix 系统中的 /bin/true)。因此,即使 dhcp 命令失败,这一行脚本的总体状态也始终是"成功"。

注释

你可以用 # 符号开始一条注释。例如:

  # Obtain an address using DHCP
  :retry
  dhcp || goto retry # Keep retrying indefinitely

续行

你可以用反斜杠续行符把过长的脚本行拆成多行。​ 例如:

  ​choose --default linux --timeout 3000 os \
      && goto boot_${os} || goto cancelled

高级主题

An iPXE ROM

嵌入式脚本

你可以在 iPXE 中嵌入一个脚本来改变它的默认行为。例如,你可能希望构建这样一个 iPXE 版本:它包含一个嵌入式脚本,先通过 DHCP 获取 IP 地址,然后从预定义的 SAN 目标引导。

动态脚本

iPXE 脚本不一定是静态文本文件。例如,你可以让 iPXE 从这样的 URL 引导:

  http://192.168.0.1/boot.php?mac=${net0/mac}&asset=${asset:uristring}

它会展开成类似这样的 URL:

  http://192.168.0.1/boot.php?mac=52:54:00:12:34:56&asset=BKQ42M1

运行在 Web 服务器上的 boot.php 程序可以根据 URL 中提供的信息动态生成脚本。例如,boot.php 可以在 MySQL 数据库中查询资产标签,确定正确的 iSCSI 引导目标,然后动态生成如下脚本:

  #!ipxe

  set initiator-iqn iqn.2010-04.org.ipxe:BKQ42M1
  sanboot iscsi:192.168.0.20::::iqn.2010-04.org.ipxe:winxp

[^1]: 为了向后兼容,iPXE 也能识别以魔数行 #!gpxe 开头的旧式 gPXE 脚本。但是 gPXE 无法运行 iPXE 脚本,因为 iPXE 脚本语言比 gPXE 脚本语言先进得多。