- 論壇徽章:
- 0
|
本帖最后由 duanjigang 于 2012-12-29 14:17 編輯
(1)關(guān)于 linux 主機(jī)上的 RPM 數(shù)據(jù)庫
RPM 在 linux 機(jī)器上工作原來是比較明確的,首先有實(shí)際的rpm解壓縮并且安裝后的文件;另外有Rpm 的DB文件,
存儲這些安裝了的 rpm 的信息,這些庫中信息在 RPM進(jìn)行安裝,升級和卸載時進(jìn)行更新。
RPM命令對兩者的操作有: (1):對DB庫進(jìn)行增刪查該 (2):對文件系統(tǒng)進(jìn)行增加和刪除和讀取。
結(jié)合起來看:
(1): RPM的安裝/升級,寫入DB庫,寫文件系統(tǒng),生成安裝列表和服務(wù),配置等,執(zhí)行安裝時腳本。
(2): RPM卸載,刪除DB庫,刪除文件系統(tǒng)中歸屬于該軟件包的文件,執(zhí)行卸載時腳本。
(3): RPM查詢, 讀取DB庫/文件并且顯示。
RPM 的在主機(jī)上的數(shù)據(jù)庫有好多個,根據(jù)不同的應(yīng)用類型,采用不同的訪問方法,可以看下:
- file /var/lib/rpm/* | grep Berkeley
- /var/lib/rpm/Basenames: Berkeley DB (Hash, version 8, native byte-order)
- /var/lib/rpm/Conflictname: Berkeley DB (Hash, version 8, native byte-order)
- /var/lib/rpm/Dirnames: Berkeley DB (Btree, version 9, native byte-order)
- /var/lib/rpm/Filemd5s: Berkeley DB (Hash, version 8, native byte-order)
- /var/lib/rpm/Group: Berkeley DB (Hash, version 8, native byte-order)
- /var/lib/rpm/Installtid: Berkeley DB (Btree, version 9, native byte-order)
- /var/lib/rpm/Name: Berkeley DB (Hash, version 8, native byte-order)
- /var/lib/rpm/Packages: Berkeley DB (Hash, version 8, native byte-order)
- /var/lib/rpm/Providename: Berkeley DB (Hash, version 8, native byte-order)
- /var/lib/rpm/Provideversion: Berkeley DB (Btree, version 9, native byte-order)
- /var/lib/rpm/Pubkeys: Berkeley DB (Hash, version 8, native byte-order)
- /var/lib/rpm/Requirename: Berkeley DB (Hash, version 8, native byte-order)
- /var/lib/rpm/Requireversion: Berkeley DB (Btree, version 9, native byte-order)
- /var/lib/rpm/Sha1header: Berkeley DB (Hash, version 8, native byte-order)
- /var/lib/rpm/Sigmd5: Berkeley DB (Hash, version 8, native byte-order)
- /var/lib/rpm/Triggername: Berkeley DB (Hash, version 8, native byte-order)
復(fù)制代碼 能夠看到,主要是 HASH 和 BTREE 這兩種訪問方式。(很奇怪,version 8 的是 HASH, version 9的是BTREE ?是應(yīng)用相關(guān),還純粹是作者愛好呢?)
RPM 的所有DB,都是從 /var/lib/rpm/Packages 生成的?梢宰鰝實(shí)驗(yàn),把除了 Packages 以外的其它文件全部刪掉。
然后重新 rpm --rebuilddb -vv
這些文件都會一一生成,因?yàn)闃?gòu)成這幾個新的db文件的信息都在Packages中包含了。(如果你把這個文件干掉了,那就悲催了,
曾經(jīng)遇到有人把這個文件給刪掉了,只好從同組配置接近的機(jī)器給他拷貝了一個os和arch一樣的機(jī)器的Packages,重新生成了下db,還好,能繼續(xù)用,呵呵)。因?yàn)檫@個文件中記錄了你的機(jī)器安裝的所有RPM和文件列表,一旦這個文件丟失了,rpm就不知道你的機(jī)器上有哪些rpm了,當(dāng)你通過
rpm -qf path 查詢某個二進(jìn)制文件屬于哪個rpm時,也不會有結(jié)果輸出。
關(guān)于 /var/lib/rpm/Packages 這個 DB 文件的最初來源,我分析(結(jié)合猜測)是這樣的:
首先,在安裝(或者OS安裝時)每一個 rpm 文件的時候,rpm 命令都會把要安裝的 rpm 包的信息分析出來,包括我們在第一篇看到的所有TAG還有文件列表等信息;
然后會把這些信息寫入 /var/lib/rpm/Packages 文件中,如果這個文件不存在,就創(chuàng)建;當(dāng)刪除包時,就會從 /var/lib/rpm/Packages 中
刪除與該包相關(guān)的所有信息。該文件中記錄了所有 rpm 的全量信息,因此,我們通過 rpm 命令查詢時,才能夠看到那么多燦爛和豐富的信息。
以rpm -qf 和 rpm -ql 為例:
比如,為了能從 xshell 拷貝文件到windows機(jī)器,我經(jīng)常會用 sz/rz命令,但是有些機(jī)器上就是沒這個命令,
要安裝,又不知道它在哪個包,怎么辦,這時就需要用 rpm -qf 來查詢了:
找一臺安裝了 sz/rz 命令的機(jī)器:
- # which sz
- /usr/bin/sz
- # rpm -qf /usr/bin/sz
- lrzsz-0.12.20-22.1
復(fù)制代碼 喔,我們發(fā)現(xiàn)sz和rz是在 lrzsz 這個包中的,然后在需要的機(jī)器上 rpm/yum 安裝 lrzsz 包即可。
那么,rpm -qf 命令路徑 就能查到這個命令屬于那個包,這是怎么做到的呢?
首先我們知道安裝 lrzsz 時 rpm 會把 這個包的所有信息寫入 /var/lib/rpm/Packages 文件,這個包包含的文件列表也會寫入
到 這個文件中,然后才會更新生成 /var/lib/rpm 中的其它DB文件(個人理解,其它DB文件就是為了查詢加速而用生成的cache.)
然后,當(dāng)執(zhí)行時,rpm 就會去 /var/lib/rpm/Packages 中(或者其它c(diǎn)ache文件中)查詢包含 /usr/bin/sz 這個路徑的
包,當(dāng)然就查到了是 lrzsz.
有人說,可能查到多個包么?這個是不可能的,因?yàn)?rpm 在安裝 rpm 文件的時候,也就是往 /var/lib/rpm/Packages
中寫數(shù)據(jù)的時候,會檢查這個rpm 中包含的文件列表是否已經(jīng)在本機(jī)安裝的其它包中出現(xiàn)了,如果找到了,就會警告: 這個文件和其它某個包中的
某某文件沖突了的錯誤信息,這個現(xiàn)象做SA的同學(xué)應(yīng)該都見過。
實(shí)驗(yàn):
- ls -alt /var/lib/rpm/Packages
- -rw-r--r-- 1 rpm rpm 19234816 Dec 27 09:30 /var/lib/rpm/Packages
復(fù)制代碼 我們能夠看到,這個文件只對root 可以寫,我們嘗試改下它的屬性:
- chattr +i /var/lib/rpm/Packages
復(fù)制代碼 設(shè)置不可改變屬性,然后嘗試安裝包:
- rpm -ivh RPMS/i386/test-baby-1.1-1.i386.rpm
- error: cannot open Packages index using db3 - Permission denied (13)
- error: cannot open Packages database in /var/lib/rpm
復(fù)制代碼 因?yàn)閞pm 沒有權(quán)限去寫 Packages 這個數(shù)據(jù)庫文件。
- # chattr -i /var/lib/rpm/Packages
- rpm -ivh RPMS/i386/test-baby-1.1-1.i386.rpm
- Preparing... ########################################### [100%]
- 1:test-baby ########################################### [100%]
復(fù)制代碼 這下就成功了,再次驗(yàn)證了 rpm 在包安裝時對 /var/lib/rpm/Packages 的寫操作確實(shí)是存在的。
同樣,你也可以同樣方法測試下卸載包時對 /var/lib/rpm/Packages 文件的寫操作是否存 |
|