關於RHEL 5 下scsi_id 無返回值的問題解決(2) 完全解析

spectre2發表於2014-12-11
本文是在前文基礎上完善的解決方案,建議先瀏覽前文,無法解決再使用本替代方案。建議使用本方案中一號方案(依然是使用wwid),不推薦二號方案。(2014年12月12日勘誤,感謝網友Solomon的測試發現了原文的錯誤
使用 udev 高效、動態地管理 Linux 裝置檔案
http://blog.itpub.net/14184018/viewspace-701677/
關於RHEL 5 下scsi_id 無返回值的問題解決(1)  
http://blog.itpub.net/14184018/viewspace-701675/

一號方案

在"關於RHEL 5 下scsi_id 無返回值的問題解決"一問中,已經給出了scsi_id命令常見的一些錯誤和問題的解決辦法,但是常有網友諮詢:“不知道為什麼就是無返回值”這個問題,以前工作的同學也遇到過這個問題;遺憾的是我始終沒有接觸過有問題的機器,在本地嘗試多次又無法重現故障,導致沒辦法解決這個很困擾人的問題。幸運的是,網友Solomon 遇到了這個問題,同時也允許我遠端連線操作,解決故障。
簡單檢查後,發現scsi_id命令確實無返回,如下圖

因為是虛擬機器,可能產生的原因太多,而且考慮到大家的環境都不一樣,有沒有更方便一些的替代方法呢?
從udev的執行過程來想辦法!
大家可能都知道udevtest這個命令,它會模擬udev的工作流程,測試一下udev繫結是不是正確。在它工作時,會讀取wwid,並且在結果輸出時print出來,如下圖


我們發現了什麼?給一張scsi_id輸出正常的對比一下,見下圖:

這張圖紅箭頭部分是wwid,再仔細看,run_program後面不一樣啊,突然明白了~大家注意看2張圖的區別:
 BUS==“***的部分:
scsi_id 命令 無返回值的是ata,有返回值的scsi;
run_program:部分:
無返回值的是 /lib/udev/ata_id   /dev/hda ,有返回值的是 /lib/udev/scsi_id -g -x -s
看到這裡,大家明白了嗎?
原來ata匯流排的wwid和scsi匯流排的wwid要用不同的命令!
換正確命令試試:
/lib/udev/ata_id   /dev/hda                        (注意:ata_id命令要使用 /dev/hda 這樣的磁碟路徑!使用/block/hda這種路徑是無效的!)


ok,wwid出來了~問題完美解決了!需要額外注意的是,udev規則裡的PROGRAM部分要想應更改!如下:
scsi匯流排的應該不會遇到問題,udev規則不用更改
KERNEL=="sd*", PROGRAM=="/lib/udev/scsi_id -g -s %p", \ RESULT=="35000c50xxxa7ef67", NAME +="root_disk%n"

ata匯流排的要改 規則:
KERNEL=="hd*", PROGRAM=="/lib/udev/ata_id %p", \ RESULT=="35000c50xxxa7ef67", NAME +="root_disk%n"(2014年12月12日勘誤)
    KERNEL=="hd*", PROGRAM=="/lib/udev/ata_id /dev/%k", \ RESULT=="35000c50xxxa7ef67", NAME +="root_disk%n"
(原文忽視了規則檔案中%p的含義,使用"/lib/udev/ata_id %p"實際上是無返回值的,這樣udev規則匹配就失敗了!/lib/udev/ata_id 要使用像/dev/hd*之類的實際裝置檔案路徑,這裡就使用/dev/%k來代表,而%k是$kernel, %k:裝置的核心裝置名稱,和前面的KERNEL=="hd*"一致,這樣就能保證返回的wwid和裝置是一一對應的了。
P.S. 如果規則裡有“BUS==“***””的規則,要注意,hd*的裝置的bus不是ata,而是ide  (小寫)!  
2014年12月12日勘誤。)


我估計大部分人遇到scsi_id無返回問題的應該都是用虛擬機器做實驗的,磁碟方面可能沒注意選成了ata(IDE)模式,導致這個問題的出現。

二號方案(有可能出問題,不建議生產環境使用)

如果發現一號方案中所說的原因也無法解決你的問題,scsi_id和ata_id都無返回值,這時有2個方法,1個就是按1號方案的思路看看能不能自己解決,第2個就是二號方案了:不使用wwid作為唯一標識!
在 udevinfo 命令獲取的資訊中,有這2項資訊SYSFS{start}=="xx"和SYSFS{size}=="xxxxxx",如下圖(用scsi做的測試,ata一樣):

注意,SYSFS{start} 只有在分割槽資訊裡才有(hda1、hda2......),也就是說,命令要是下面這樣:
udevinfo -a -p /sys/block/sda/sda1

而不能是
udevinfo -a -p /sys/block/sda

我們用這2個引數來標識裝置,但這樣就會帶來一個問題,這2個引數有機率重複,出現不唯一的情況,這時udev的目的就無效了,所以,使用2號方案,要提前做好規劃,確保同一環境(本機、叢集、共享磁碟、劃分的LUN每個磁碟或LUN的size不一致!這樣才能起到唯一標識的作用!

udev rules檔案內容如下:
KERNEL=="sd*[0-9]", SUBSYSTEM=="block", SYSFS{size}=="208782", SYSFS{start}=="63", NAME="asmdisk-crs1", OWNER="grid", GROUP="asmadmin", MODE="0660"

KERNEL=="hd*", SUBSYSTEM=="block", SYSFS{size}=="208782", SYSFS{start}=="63", \ RESULT=="35000c50xxxa7ef67", NAME ="root_disk1"

udev rules規則部分根據需要大家自己編寫,上面只是例子,不適用於所有人,我在有些rac生產庫就會使用如下的規則,更嚴謹一些:


(請詳細閱讀“使用 udev 高效、動態地管理 Linux 裝置檔案”中udev匹配規則部分,這樣能保證你的匹配規則檔案更適用於你的環境2014年12月12日勘誤)
本部落格原創內容僅代表本人觀點,因技術水平有限,難免有錯漏之處,如發現有錯漏問題,請不吝賜教,留言站短均可,謝謝。

大家如有疑問也請留言,不定期回覆。
話說回來,網上關於wwid、uuid、scsi_id、ata_id、udev相關的資料在真的很難找到,大家有推薦的資料地址或書籍名稱請給我留言,謝謝。

全文完 :b


本文乃spectre2原創文章,請勿轉載。如須轉載請詳細標明轉載出處。

來自 “ ITPUB部落格 ” ,連結:http://blog.itpub.net/14184018/viewspace-1364944/,如需轉載,請註明出處,否則將追究法律責任。

相關文章