<meta charset="utf-8">
在Linux文件系統(tǒng)中,用戶對文件或目錄有:讀、寫、執(zhí)行三種權(quán)限,分別使用數(shù)字:4、2、1三個數(shù)字。三者之間可任意組合,如:用戶擁有所有權(quán)限,則用數(shù)字7表示(4+2+1=7);用戶擁有讀、寫權(quán)限則用數(shù)字6表示(4+2=6)??梢钥闯?,基于數(shù)字加減的權(quán)限設(shè)置在使用中非常便利。其對權(quán)限的控制,本質(zhì)上是基于位運算實現(xiàn)的。掌握位運算,不僅可以更加深入的理解Linux權(quán)限控制,更可以在自己項目中實現(xiàn)簡單高效的、基于位運算的權(quán)限管理系統(tǒng)。
- Linux基于位運算的權(quán)限控制
或運算實現(xiàn)權(quán)限的添加與運算實現(xiàn)權(quán)限的判斷非運算實現(xiàn)權(quán)限的減少位移與權(quán)限碼
1. Linux基于位運算的權(quán)限控制
Linux權(quán)限控制是基于位運算實現(xiàn)的。
在Linux權(quán)限系統(tǒng)中,讀、寫、執(zhí)行權(quán)限分別對應(yīng)三個狀態(tài)位:
讀 寫 執(zhí)行 二進制 十進制
0 0 1 ==> 001 ==> 1
0 1 0 ==> 010 ==> 2
1 0 0 ==> 100 ==> 4
0 1 1 ==> 011 ==> 3
1 0 1 ==> 101 ==> 5
1 1 0 ==> 110 ==> 6
1 1 1 ==> 111 ==> 7
如上所示,“執(zhí)行”權(quán)限使用二進制為001,即:十進制1?!皩懭搿睓?quán)限使用二進制為010,即:十進制2?!白x取”權(quán)限使用二進制為100,即:十進制4。
2. 或運算實現(xiàn)權(quán)限的添加
增加權(quán)限使用或(|)運算實現(xiàn)。
如,為用戶增加“讀取”、“寫入”兩種權(quán)限
讀 寫 執(zhí)行 二進制 十進制
0 1 0 ==> 010 ==> 2
1 0 0 ==> 100 ==> 4
1 1 0 ==> 110 ==> 6 // 或(|)運算結(jié)果
“讀寫”兩種權(quán)限,權(quán)限碼為6(110),其由權(quán)限碼2(010)和4(100)進行或(|)運算后實現(xiàn),即:6 = 2|4,也可以由6=2+4計算得出。
3. 與運算實現(xiàn)權(quán)限的判斷
在需要進行用戶權(quán)限判斷時,可以使用與(&)運算判斷用戶是否據(jù)有某項權(quán)限。
如,判斷權(quán)限碼為6用戶是否有讀取權(quán)限:
讀 寫 執(zhí)行 二進制 十進制
1 1 0 ==> 110 ==> 6
1 0 0 ==> 100 ==> 4
1 0 0 ==> 100 ==> 4 // 與(&)運算結(jié)果
權(quán)限碼6(110)和4(100)的與運算結(jié)果為4,即:4=6&4。
判斷權(quán)限碼為6用戶是否有執(zhí)行權(quán)限:
讀 寫 執(zhí)行 二進制 十進制
1 1 0 ==> 110 ==> 6
0 0 1 ==> 001 ==> 1
0 0 0 ==> 000 ==> 0 // 與(&)運算結(jié)果
權(quán)限碼6(110)和1(001)的與運算結(jié)果為0,即:0=6&1。
根據(jù)與運算的計算規(guī)律,當(dāng)運算結(jié)果為所要判斷權(quán)限本身值時,我們可以認為用戶具有這個權(quán)限。而當(dāng)運算結(jié)果為 0 時,我們可以認為用戶不具有這個權(quán)限。
4. 非運算實現(xiàn)權(quán)限的減少
位運算同樣可以實現(xiàn)用戶權(quán)限的減少,減少用戶權(quán)限使用非(^)運算。
如,將權(quán)限碼為7用戶,移除執(zhí)行權(quán)限:
讀 寫 執(zhí)行 二進制 十進制
1 1 1 ==> 111 ==> 7
0 0 1 ==> 001 ==> 1
1 1 0 ==> 110 ==> 6 // 非(^)運算結(jié)果
權(quán)限碼7(111)和1(001)的非運算結(jié)果為6,即:6=7^1,也可以由6=7-1計算得出。
5. 位移與權(quán)限碼
從上面的介紹可以看出,在權(quán)限管理系統(tǒng)中每操作的權(quán)限碼都是唯一的。而基于位運算的權(quán)限管理系統(tǒng),要求每個權(quán)限碼的二進制數(shù)形式,都只能有一位值為1。
所使用的權(quán)限碼,可以將前一個權(quán)限碼``左位移一位得到下一個權(quán)限碼,即:
- 權(quán)限碼
1(001),即:20 -
2=1<<1,即:將001左移1位為010,也即:由20變?yōu)?1 -
4=2<<1,即:將010左移1位為100,也即:由21變?yōu)?2 -
8=4<<1,即:將100左移1位為1000,也即:由22變?yōu)?3
簡單的說,權(quán)限碼都是2的冪數(shù),2<sup>0</sup>、2<sup>1</sup>、2<sup>2</sup>、2<sup>3</sup>、……2<sup>n</sup>依次對應(yīng)權(quán)限碼1、2、4、8……n。
相關(guān)說明
基于位運算的權(quán)限管理,其運算運算對象是二進制數(shù),優(yōu)點是:運算速度快、效率高、節(jié)省存儲空間、對權(quán)限控制非常靈活。所有語言都提供了位運算符,我們可以在不同語言實現(xiàn)的系統(tǒng)、甚至數(shù)據(jù)庫中使用位運算實現(xiàn)對用戶權(quán)限的管理。
位運算也有一些局限性,隨著權(quán)限碼增加,數(shù)據(jù)長度也相應(yīng)的增長。這就要求權(quán)限碼不能超過計算本身運算長度,在數(shù)據(jù)庫中存儲權(quán)限碼時,權(quán)限碼長度也不能的超過所使用數(shù)據(jù)類型。如:在32位系統(tǒng)中不能超過2<sup>32</sup>,也就是權(quán)限數(shù)量不能多于32個。而mySQL數(shù)據(jù)庫的BIGINT,其存儲空間為8Byte,使用BIGINT存儲存儲碼時,權(quán)限數(shù)不能多于64個(8*8-1)。
簡述RBAC基于角色的訪問控制系統(tǒng) (Role-Based Access Control)
每個權(quán)限增加了一個權(quán)限位,用作分級
permission表
id name method/url value Position
1 查看帖子 get 1 0
2 發(fā)布帖子 post 2 0
3 修改帖子 update 4 0
4 刪除帖子 delete 8 0
5 新增用戶 addUser 1 1
角色對應(yīng)表
id uid perId permission_sum
1 1 1 {"0":[2,3,4]}
2 1 3 {"0":[{"0":[1,2,3]}, {"1":[1,2,3]}, {"2":[1,2,3]} ]}
permission_sum權(quán)限位分類
{
"0":[
{
"0":[
1,
2,
3
]
},
{
"1":[
1,
2,
3
]
},
{
"2":[
1,
2,
3
]
}
]
}
public class User {
private Integer userId;
private String name;
private String password;
}
public boolean hasPermission(Permission permission){
int position = permission.getPosition();
long number = permission.getPermissionNum();
return !((permissionSum[position] & number) == 0);
}
由于目前時間,沒有詳細設(shè)計,提供一個思路,具體實現(xiàn)是要再進一步確認;

每個用戶的權(quán)限值就需要用一個數(shù)組來存儲,其下標(biāo)為0的對應(yīng)著權(quán)限位為0的權(quán)限值和,
轉(zhuǎn)自 : https://itbilu.com/other/relate/4yJxR6awl.html#linux-bit
https://www.zhihu.com/question/275852963/answer/383522729
https://blog.csdn.net/followMyInclinations/article/details/72123429
https://mp.weixin.qq.com/s/reKtFpQByDcAtzinobNq_Q
http://www.itdecent.cn/p/262652908eb8
作者:IT菜鳥學(xué)習(xí)
鏈接:http://www.itdecent.cn/p/262652908eb8
來源:簡書
著作權(quán)歸作者所有。商業(yè)轉(zhuǎn)載請聯(lián)系作者獲得授權(quán),非商業(yè)轉(zhuǎn)載請注明出處。