剖析ironic


關鍵技術

在安裝操作系統時需要存儲介質來存儲系統鏡像、需要控制物理機開關機,在網絡部署環境中還需要預啟動環境。

  • PXE (預啟動環境)
  • IPMI(電源管理)
  • iSCSI(存儲)

什么是PXE

PXE(preboot execute environment) 預啟動執行環境。PXE 是目前主流的無盤啟動技術,它可以使計算機通過網絡而不是從本地硬盤、光驅等設備啟動,采用Client/Server的網絡模式,在啟動過程中,終端要求服務器分配IP地址,再用TFTP(trivial file transfer protocol)或MTFTP(multicast trivial file transfer protocol)協議下載一個啟動軟件包到本機內存中執行,由這個啟動軟件包完成終端基本軟件設置,從而引導預先安裝在服務器中的終端操作系統。

利用 PXE 進行系統安裝需要被安裝的主機上有 PXE 支持的網卡,不過現在的網卡一般都內嵌支持 PXE 的 ROM 芯片。當計算機引導時,BIOS 首先會把 PXE Client 調入內存中執行,PXE Client 被載入內存后,它便同時具有 DHCP client 和 TFTP Client 的功能,DHCP client 會向 DHCP server 請求 ip 分配給將要安裝系統的主機,然后由 PXE Client 將放置在遠端的文件通過 TFTP 下載到本地運行。 PXE過程圖

安裝流程如下:

  1. 客戶機從自己的PXE網卡啟動,向本網絡中的DHCP服務器索取IP,並搜尋引導文件的位置
  2. DHCP服務器返回分給客戶機IP以及NBP(Network Bootstrap Program )文件的放置位置(該文件一般是放在一台TFTP服務器上)
  3. 客戶機向本網絡中的TFTP服務器索取NBP
  4. 客戶機取得NBP后之執行該文件
  5. 根據NBP的執行結果,通過TFTP服務器加載內核和文件系統
  6. 安裝操作系統

PXE能提供操作系統鏡像,但是如何遠程開機呢,這件事就是由IPMI來做的。

什么是IPMI

智能平台管理接口(IPMI:Intelligent Platform Management Interface)是一項應用於服務器管理系統設計的標准,提供管理和監控CPU、固件(BIOS、UEFI)和操作系統等功能,由Intel、HP、Dell和NEC公司於1998年共同提出。利用此接口標准設計有助於在不同類服務器系統硬件上實施系統管理,使不同平台的集中管理成為可能,目前有超過200家公司支持IPMI。IPMI信息通過網絡連接到基板管理控制器 (BMC)進行交流,不依賴BOIS或者操作系統,這使得在操作系統不響應或未加載的情況下其仍然可以進行開關機、信息提取等操作。Ironic 正是利用此技術可以遠程的對裸機進行上下電或者其他操作,而不是依賴物理開關或者操作系統。

IPMI可以在操作系統啟動之前、管理系統啟動之前、操作系統或者管理系統失敗(與帶內系統管理的最大特性)時對物理機進行管理,利用IPMI可以實現以下功能:

  1. 可以在服務器通電(沒有啟動操作系統)情況下,對它進行遠程管理:開機,關機,重啟
  2. 基於文本的控制台重定向,可以遠程查看和修改BIOS設置,系統啟動過程,登入系統等
  3. 可以遠程通過串口IP映射(SoL)連接服務器,解決ssh服務無法訪問,遠程安裝系統,查看系統啟動故障等問題
  4. 可以通過系統的串行端口進行訪問
  5. 故障日志記錄和 SNMP 警報發送,訪問系統事件日志 (System Event Log ,SEL) 和傳感器狀況

IPMI技術功能點總結:

  • 遠程電源控制 (on / off / cycle / status)
  • 串口的IP映射 Serial over LAN (SoL)
  • 支持健康關機(Graceful shutdown support)
  • 機箱環境監控 (溫度, 風扇轉速, CPU電壓等)
  • 遠程設備身份LED控制(Remote ID LED control)
  • 系統事件日志(System event log)
  • 平台事件跟蹤(Platform Event Traps)
  • 數據記錄(Data logging)
  • 虛擬KVM會話(Virtual KVM)
  • 虛擬媒介(Virtual Media)

參考資料: https://en.wikipedia.org/wiki/Intelligent_Platform_Management_Interface

什么是iSCSI

iSCSI是一個指令集,iSCSI技術是一種新儲存技術,該技術是將現有SCSI接口與以太網絡(Ethernet)技術結合,使服務器可與使用IP網絡的儲存裝置互相交換資料。

早期的企業使用的服務器若有大容量磁盤的需求時,通常是透過SCSI來串接SCSI磁盤,因此服務器上面必須要加裝SCSI卡,而且這個SCSI是專屬於該服務器的。 后來這個外接式的SCSI設備被SAN的架構所取代,在SAN的標准架構下,雖然有很多的服務器可以對同一個SAN 進行存取的動作,不過為了速度需求,通常使用的是光纖通道。但是光纖通道很貴,不但設備貴,服務器上面也要有光纖卡,很麻煩,所以光纖的SAN在中小企業很難普及。

后來網絡實在太普及,尤其是以IP封包為基礎的LAN技術已經很成熟,再加上以太網路的速度越來越快,所以就有廠商將SAN的連接方式改為利用IP技術來處理。 然后再透過一些標准的設定,最后就得到Internet SCSI (iSCSI)這個的產生! iSCSI主要是透過TCP/IP的技術,將儲存設備端透過iSCSI target (iSCSI目標端)功能,做成可以提供磁盤的服務器端,再透過iSCSI initiator (iSCSI初始化用戶)功能,做成能夠掛載使用iSCSI target的用戶端,如此便能透過iSCSI設置來進行磁盤的應用了。

也就是說,iSCSI 這個架構主要將儲存裝置與使用的主機分為兩個部分,分別是:

  • iSCSI target:就是儲存設備端,存放磁盤或RAID的設備,目前也能夠將Linux主機模擬成iSCSI target了! 目的在提供其他主機使用的磁盤。
  • iSCSI initiator:就是能夠使用target的用戶端,通常是服務器。 也就是說,想要連接到iSCSI target的服務器,也必須要安裝iSCSI initiator的相關功能后才能夠使用iSCSI target提供的磁盤。

iSCSI示意圖

ironic內部技術

ironic代碼結構

下面是ironic liberty版的代碼結構,其中省略了部分文件

ironic-stable-liberty:.
│ 
│  babel.cfg
│  CONTRIBUTING.rst
│  driver-requirements.txt
│  LICENSE
│  MANIFEST.in
│  openstack-common.conf
│  README.rst
│  RELEASE-NOTES
│  requirements.txt
│  setup.cfg      #pbr的配置文件
│  setup.py 
│  test-requirements.txt
│  tox.ini        #tox配置文件
│  vagrant.yaml
│  Vagrantfile
│  
├─doc   #文檔
│              
├─etc  #相關配置文件
│              
├─ironic
│  │  
│  ├─api        #api,使用peach框架
│  │  │  acl.py
│  │  │  app.py     #API入口
│  │  │  app.wsgi
│  │  │  config.py
│  │  │  expose.py
│  │  │  hooks.py
│  │  │  __init__.py
│  │  │  
│  │  ├─controllers   #控制器
│  │  │  │  base.py
│  │  │  │  link.py
│  │  │  │  root.py   #API總控制器
│  │  │  │  __init__.py
│  │  │  │  
│  │  │  └─v1      #v1 版本API
│  │  │          
│  │  └─middleware
│  │          
│  ├─cmd            # 服務入口
│  │      api.py
│  │      conductor.py
│  │      dbsync.py
│  │      __init__.py
│  │      
│  ├─common  常用方法
│  │              
│  ├─conductor  
│  │      manager.py  
│  │      rpcapi.py
│  │      task_manager.py
│  │      utils.py
│  │      __init__.py
│  │      
│  ├─db    #數據庫相關,包括sqlalchemy、alembic
│  │                  
│  ├─dhcp  #neutron dhcp api
│  │      base.py
│  │      neutron.py
│  │      none.py
│  │      __init__.py
│  │      
│  ├─drivers    #驅動相關
│  │  │  agent.py    #agent_* 驅動
│  │  │  base.py
│  │  │  drac.py     #drac驅動
│  │  │  fake.py
│  │  │  ilo.py      #ilo驅動,惠普的
│  │  │  irmc.py     #irmc
│  │  │  pxe.py      #pxe_* 驅動
│  │  │  raid_config_schema.json
│  │  │  utils.py
│  │  │  __init__.py
│  │  │  
│  │  └─modules     #驅動的具體方法
│  │    
│  │              
│  ├─locale      #翻譯
│  │              
│  ├─nova        #nova相關,這里包括與Nova computer沖突的臨時解決辦法
│  │          
│  ├─objects     #基本對象的方法,包括conducotr、node、port、field、chassis
│  │      
│  ├─openstack  #openstack相關的,這里包含處理鏡像的方法的幫助函數
│  │          
│  └─tests    #測試相關
│      
│              
├─releasenotes   #發布歷史
│              
└─tools     #相關工具

API

ironic-api提供一系列接口,詳見ironic API

  • 節點相關(node)
    • 節點增刪改查(List, Searching, Creating, Updating, and Deleting)
    • 合法性檢查
    • 設置和清除維修狀態
    • 設置和獲取boot device
    • 獲取節點當前綜合信息,包括power, provision, raid, console等
    • 更改電源狀態
    • 更改節點提供狀態( manage, provide, inspect, clean, active, rebuild, delete (deleted), abort)
    • 設置RAID
    • 啟動、停止、獲取console
    • 查看、調用廠商定制方法(passthru方法)
  • 端口相關(Port)
    • 對物理端口(Port)的增刪改查(Listing, Searching, Creating, Updating, and Deleting ),新建的時候就要指定端口的物理地址(一般是MAC地址)與Node進行綁定。
    • 查看與Node連接的端口
  • 驅動相關(driver)
    • 列舉所有驅動
    • 查看驅動的詳細信息、屬性
    • 查看和調用廠商的驅動
  • Chassis(機箱,一組node的集合)
    • 增刪改查

      Chassis這個資源類型是為了給節點分組用的,目前只有列舉一組節點的功能。不贊成使用這個類型,將來可能會去除掉。

Conductor

Ironic-Conductor是Ironic中最主要的模塊,通過Ironic-API對外提供功能,與Ironic-API之間通過RPC進行通信,負責絕大部分工作,包括與Neutron通信為物理機配置網絡信息,與Glance通信獲取鏡像,與Cinder和Swift通信進行為物理機提Ironic-Conductor是Ironic中最主要的模塊,通過Ironic-API對外提供功能,與Ironic-API之間通過RPC進行通信,負責絕大部分工作,包括與Neutron通信為物理機配置網絡信息,與Glance通信獲取鏡像,與Cinder和Swift通信進行為物理機提供存儲。 供存儲。

同時控制着物理機狀態的改變過程,下圖是openstack Liberty中物理機狀態轉換圖:

Ironic’s State Machine

在高可用方面,conductor 采用一致性哈希算法保證Condutor節點新增退出時不影響Bare metal節點。 

DB

采用MySQL,存儲物理機和驅動的狀態信息,可以換成其他數據庫。

Drivers

驅動是真正操作物理機的模塊,Ironic的驅動以插件形式設計,廠商可以實現自己的驅動來為自己的設備提供特色化功能。實現自己的驅動只需要實現幾個相關的方法即可。

驅動架構

驅動有不同的屬性,每個屬性能夠完成一定的功能,這些屬性分為三種接口:

  • 核心接口(core),最基本的功能,是其他服務的依賴,所有驅動都必須實現的,包括power,deploy.
  • 標准接口(standard),實現通用功能,主要包括 management, console, boot, inspect, raid.
  • 廠商接口(vendor),提供個性化功能

接口功能:

分類 接口 功能 主要需要實現的方法
core power 管理電源 get_properties、validate、 get_power_state、set_power_state、reboot
  deploy 部署方式 get_properties、validate、 deploy、tear_down、prepare、clean_up、take_over、prepare_cleaning、tear_down_cleaning
standard console 通過硬件得到物理機的控制台 get_properties、validate、start_console、stop_console、get_console
  management 管理物理機硬件 get_properties、validate、get_supported_boot_device、set_boot_device、get_boot_device 、get_sensors_data
  boot 啟動相關的動作 get_properties、validate、prepare_ramdisk、clean_up_ramdisk、prepare_instance、clean_up_instance
  inspect 硬件自檢,主要檢查內存、CPU、本地分區 inspect_hardware
  raid 設置raid get_properties、validate、 create_configuration、delete_configuration、get_logical_disk_properties
vendor   廠商的自定義功能 get_properties、validate、...

驅動架構示意圖:

驅動結構示意圖

Liberty支持的驅動,在setup.cfg中可以看到

    agent_ilo = ironic.drivers.ilo:IloVirtualMediaAgentDriver
    agent_ipmitool = ironic.drivers.agent:AgentAndIPMIToolDriver
    agent_irmc = ironic.drivers.irmc:IRMCVirtualMediaAgentDriver
    agent_pyghmi = ironic.drivers.agent:AgentAndIPMINativeDriver
    agent_ssh = ironic.drivers.agent:AgentAndSSHDriver
    agent_vbox = ironic.drivers.agent:AgentAndVirtualBoxDriver
    agent_ucs = ironic.drivers.agent:AgentAndUcsDriver
    iscsi_ilo = ironic.drivers.ilo:IloVirtualMediaIscsiDriver
    iscsi_irmc = ironic.drivers.irmc:IRMCVirtualMediaIscsiDriver
    pxe_ipmitool = ironic.drivers.pxe:PXEAndIPMIToolDriver
    pxe_ipminative = ironic.drivers.pxe:PXEAndIPMINativeDriver
    pxe_ssh = ironic.drivers.pxe:PXEAndSSHDriver
    pxe_vbox = ironic.drivers.pxe:PXEAndVirtualBoxDriver
    pxe_seamicro = ironic.drivers.pxe:PXEAndSeaMicroDriver
    pxe_iboot = ironic.drivers.pxe:PXEAndIBootDriver
    pxe_ilo = ironic.drivers.pxe:PXEAndIloDriver
    pxe_drac = ironic.drivers.drac:PXEDracDriver
    pxe_snmp = ironic.drivers.pxe:PXEAndSNMPDriver
    pxe_irmc = ironic.drivers.pxe:PXEAndIRMCDriver
    pxe_amt = ironic.drivers.pxe:PXEAndAMTDriver
    pxe_msftocs = ironic.drivers.pxe:PXEAndMSFTOCSDriver
    pxe_ucs = ironic.drivers.pxe:PXEAndUcsDriver
    pxe_wol = ironic.drivers.pxe:PXEAndWakeOnLanDriver
    pxe_iscsi_cimc = ironic.drivers.pxe:PXEAndCIMCDriver
    pxe_agent_cimc = ironic.drivers.agent:AgentAndCIMCDriver

    #fake* 驅動是假的驅動,里面沒有具體實現,用於測試
    fake = ironic.drivers.fake:FakeDriver
    fake_agent = ironic.drivers.fake:FakeAgentDriver
    fake_inspector = ironic.drivers.fake:FakeIPMIToolInspectorDriver
    fake_ipmitool = ironic.drivers.fake:FakeIPMIToolDriver
    fake_ipminative = ironic.drivers.fake:FakeIPMINativeDriver
    fake_ssh = ironic.drivers.fake:FakeSSHDriver
    fake_pxe = ironic.drivers.fake:FakePXEDriver
    fake_seamicro = ironic.drivers.fake:FakeSeaMicroDriver
    fake_iboot = ironic.drivers.fake:FakeIBootDriver
    fake_ilo = ironic.drivers.fake:FakeIloDriver
    fake_drac = ironic.drivers.fake:FakeDracDriver
    fake_snmp = ironic.drivers.fake:FakeSNMPDriver
    fake_irmc = ironic.drivers.fake:FakeIRMCDriver
    fake_vbox = ironic.drivers.fake:FakeVirtualBoxDriver
    fake_amt = ironic.drivers.fake:FakeAMTDriver
    fake_msftocs = ironic.drivers.fake:FakeMSFTOCSDriver
    fake_ucs = ironic.drivers.fake:FakeUcsDriver
    fake_cimc = ironic.drivers.fake:FakeCIMCDriver
    fake_wol = ironic.drivers.fake:FakeWakeOnLanDriver

可以將上面的驅動進行分類,得到:

  • pxe/iscis
  • agent
  • fake (假的驅動,用於示例,測試)

我們把fake驅動排除,其他的驅動可以分為兩類:

  • 一是以pex 或者 iscsi 為前綴的驅動采用PXE部署機制,這些驅動將根硬盤作為iSCSI設備暴露給ironic conductor,由conductor將鏡像復制到這里.
  • 二是以agent_ 為前綴的驅動采用Agent部署機制,conductor准備一個存儲在swift上的鏡像URL給IPA,由IPA下載鏡像和完成部署的操作。

從Kilo版開始,所有驅動使用agent進行部署。

每種驅動的功能會調用不同的模塊來實現,比如:

  • pxe_ deploy 用的是iscsi_deploy.ISCSIDeploy(), boot用的是pxe.PXEBoot(), power根據后綴不同使用的不同
  • agent_ deploy用的是agent.AgentDeploy(), boot 用的是pxe.PXEBoot(), power根據后綴不同而不同
  • iscis_ deploy用的iscsi_deploy.ISCSIDeploy(),power根據后綴不同而不同

驅動列表

  • 社區驅動
種類 用途 實現的驅動
SSH 用VM模擬物理機時使用 pxe-ssh使用pxe部署、ssh管理電源; agent-ssh使用agent部署、ssh管理電源
VirtualBox VirtualBox驅動用來將虛擬機模擬成裸機節點進行測試Ironic。Ironic使用pex_ssh和agent_ssh驅動連接VirtualBox主機(要安裝在Linux下,Windows下SSH不太好用) - pxe_vbox:使用基於iSCSI的部署機制- agent_vbox:使用基於agent的部署機制
IPMI 使用IPMItool進行管理電源 pxe_ipmitool; agent_ipmitool;
pyghmi pyghmi是ironic實現的一個Python ipmitool lib 用於替代ipmitool pxe_ipminative;agent_pyghmi
  • 廠商驅動
種類 說明 實現的驅動
DRAC 戴爾公司的一種系統管理硬件和軟件解決方案(Dell Remote Access Controller) pxe_drac
AMT 英特爾主動管理技術,遠程帶外管理個人電腦的硬件和固件的技術,用於監控、維修、更新、升級硬件和固件 pex_amt
SNMP SNMP電源驅動用戶管理數據中心機架的配電單元,可與PXE驅動結合起來用於網絡部署和配置 pxe_snmp
iLO iLO是Integrated Ligths-out的簡稱,是HP服務器上集成的遠程管理端口,只要將服務器接入網絡並且沒有斷開服務器的電源,不管HP服務器的處於何種狀態(開機、關機、重啟),都可以允許用戶通過網絡進行遠程管理 iscsi_ilo, agent_ilo, pxe_ilo。 iscsi_ilo和agent_ilo使用iLO實現帶外管理,iscsi_ilo使用diskimage-builder建立鏡像,從網絡啟動;而agent_ilo使用IPA的部署鏡像,裸機節點從本地啟動。pxe_ilo使用PXE/iSCSI部署(和常規PXE驅動一樣)
SeaMicro SeaMicro服務器是由AMD公司發布的,基於ARM處理器,特點是節能。SeaMicro電源驅動可以使用SeaMicro服務器的電源周期管理功能。 pxe_seamicro, 使用PXE/iSCSI進行部署鏡像,然后使用SeaMicro替代IPMI對裸機進行管理。
iRMC 富士通的驅動,通過ServerView Common Command Interface(SCCI,富士通的卡)控制電源 - pxe_irmc,使用PXE部署 - iscis_irmc,支持用虛擬光驅來部署鏡像 - agent_irmc,支持使用虛擬光驅部署IPA
UCS 思科的驅動,用戶管理思科 UCS B/C 系列的服務器(類似IPMI) - pxe_ucs: 使用PXE/iSCSI部署鏡像,使用UCS代替IPMI管理節點 - agent_ucs:使用IPAramdisk部署鏡像,使用UCS代替IPMI管理節點
CIMC 思科為standalone Cisco UCS C系列服務器提供的驅動,可以利用CIMC進行管理裸機(代替IPMI) pxe_iscsi_cimc,使用PXE+iSCSI部署 - pxe_agent_cimc,使用PXE啟動+Agent部署
Wake-On-Lan Wake-On-Lan是一個允許通過網絡消息打開電腦電源的標准,不需要額外硬件,但還在測試階段。Wake-On-Lan只有打開電源的功能,關閉電源需要手工執行。它沒有獲取電源狀態的能力,任何電源狀態的API調用它只返回數據庫里的值。 pex_wol:使用PXE/iPXE啟動,iSCSI部署。
iBoot iBoot power driver通過DxP協議對使用了Dataprobe(美國一家制造商)iBoot 設備的服務器進行電源周期管理 pxe_iboot,使用PXE/iPXE啟動,iSCSI部署。

Ironic-Python-Agent

在PXE部署環境中,deploy模塊是通過打開一個iSCSI設備,ironic-conductro將OS的鏡像文件寫到iSCSI的設備,所以deploy_ramdisk只是完成了iSCSI部署的工作,但開發者覺得既然已經把kernel和ramdisk傳過去了,只做一個工作是不是太少了,而且還太缺乏靈活性了,所以就想在ramdisk里裝一個Python Agent。 實際上就是多提供了一個Restful API,控制節點可以通過這個agent遠程實現與物理機節點互動,而不僅僅使用dd命令。

Ironic Python Agent(簡稱IPA或者agent)是一個基於python的代理,用於處理ironic中裸機節點的一系列動作,比如檢查、配置、清除和部署鏡像。運行在ramdisk中,暴露出REST API給conductor。Ironic-Python-Agent可以在deploy模塊直接訪問硬件,提供以下功能:

  • 磁盤格式化
  • 磁盤分區
  • 安裝OS( Bootloaders, OS)
  • 固件升級
  • raid配置

在Condutor端使用agent驅動,物理機端使用IPA,IPA通過暴露API給Condutor調用,則可完成相應功能。IPA啟動時通過發送lookup()請求給Condutor獲取UUID,相當於注冊自己,並且每隔一段時間給Condutor發送心跳包進行連接。

1. 與conductor的交互

IPA使用lookup和hearteat機制與Ironic Conductor進行交互

  1. 啟動時agent給Conductor的vendor_passthru lookup endpoint(地址為/v1/drivers/{driver}/vendor_passthru/lookup)發送一個硬件的profile
  2. 然后Ironic就可以得出該節點的uuid,在成功發現該節點之后,agent隔N秒發送心跳包給Conductor(hearteat地址為/v1/nodes/{node_ident}/vendor_passthru/heartbeat )
  3. conductor執行一系列動作,包括查詢已經運行的命令的狀態,

2. 與ramdisk、agent的關系

IPA是一個運行在ramdisk中python程序,當物理機注冊時使用agent為前綴的驅動時,則會使用agent方式部署,即允許包含有IPA的ramdisk。

3. 硬件管理

硬件管理器(HardwareManager)是IPA中的一個概念,IPA通過重寫硬件管理器來支持多種硬件平台。通過自定義 hardware managers 可以允許用戶引入特定的硬件工具集、文件和清除步驟等等,比如可以引入 BIOS flashing utility and BIOS file,然后在cleaning step中重寫BIOS版本。

修改硬件的方法按照優先順序發送給每個管理器,管理器檢查是否包含該方法,如果沒有則拋出IncompatibleHardwareMethodError異常,IPA繼續發送給下一個管理器,直到某個管理器包含該方法並且返回方法的結果,如果所有的管理器都沒有改方法則拋出 HardwareManagerMethodNotFound異常。

4. pxe部署與agent部署對比

使用pxe部署流程:

iscsi部署流程

使用IPA部署流程:

IPA部署流程


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM