[問題] suid 的效果與預期不符

看板LinuxDev作者 (妳,我可以)時間11年前 (2013/08/28 14:24), 編輯推噓5(5022)
留言27則, 2人參與, 最新討論串1/1
環境: ubuntu 11.04 首先我用帳號 styx, babe 各用 touch 產生了一個檔案: (放到 /tmp) -rw-r----- styx styx maury -rw-r----- babe babe mjb 接著在帳號 styx 下編譯以下程式: /* step1. gcc setuid-test.c -o suidtest step2. cd /tmp step3. cp ~/suidtest . */ #include <sys/stat.h> #include <fcntl.h> #include <stdio.h> int main(void) { int uid, euid, fdmjb, fdmaury; int egid; uid = getuid(); euid = geteuid(); printf("uid = %d, euid = %d, egid = %d\n", uid, euid, getegid()); fdmjb = open("mjb", O_RDONLY); fdmaury = open("maury", O_RDONLY); printf("fdmjb = %d, fdmaury = %d\n", fdmjb, fdmaury); setuid(uid); printf("after setuid(%d): uid = %d, euid = %d, egid = %d\n", uid, getuid(), geteuid(), getegid()); fdmjb = open("mjb", O_RDONLY); fdmaury = open("maury", O_RDONLY); printf("fdmjb = %d, fdmaury = %d\n", fdmjb, fdmaury); setuid(euid); printf("after setuid(%d): uid = %d, euid = %d, egid = %d\n", euid, getuid(), geteuid(), getegid()); return 0; } 然後改變他的 suid 並且複製到 /tmp : chmod u+s suidtest 退出帳號 styx,改進入帳號 babe,執行 ./suidtest 得到結果: 註 styx, babe 的 id: uid=1004(babe) gid=1005(babe) groups=1005(babe) uid=1003(styx) gid=1004(styx) groups=1004(styx) /tmp$ ./suidtest uid = 1004, euid = 1003, egid = 1005 fdmjb = 3, fdmaury = 4 after setuid(1004): uid = 1004, euid = 1004, egid = 1005 fdmjb = 5, fdmaury = -1 after setuid(1003): uid = 1004, euid = 1003, egid = 1005 原本小弟預期第一次 open("mjb") == -1,因為 euid = styx,但是可能 因為 egid = babe 的緣故,造成 open("mjb") != -1,於是小弟又加上 sgid: chmod g+s suidtest 再次執行,這次的結果更驚奇了: uid = 1004, euid = 1003, egid = 1004 fdmjb = 3, fdmaury = 4 after setuid(1004): uid = 1004, euid = 1004, egid = 1004 fdmjb = 5, fdmaury = 6 after setuid(1003): uid = 1004, euid = 1003, egid = 1004 照道理說這次第一次 open("mjb") == -1 (因為 euid 與 egid 都是 styx), 怎麼會這樣呢!? 最後沒招了,只好: chmod g-s suidtest (先退回原本的狀態) chmod g-r mjb (-rw-r----- 變為 -rw-------) ./suidtest 最後這才是我一開始預期的結果: uid = 1004, euid = 1003, egid = 1005 fdmjb = -1, fdmaury = 3 after setuid(1004): uid = 1004, euid = 1004, egid = 1005 fdmjb = 4, fdmaury = -1 after setuid(1003): uid = 1004, euid = 1003, egid = 1005 請各位有空幫小弟看看,感恩! -- ※ 發信站: 批踢踢實業坊(ptt.cc) ◆ From: 171.25.193.131

08/29 22:19, , 1F
都是因為 groups 造成的, 但一般使用者又沒權限 setgroups()
08/29 22:19, 1F

08/29 22:21, , 2F
另外, fdmaury = 6 那邊因為你沒使用 setgid(), 只用 setuid()
08/29 22:21, 2F

09/01 04:29, , 3F
我有用 chgrp 指令強迫變更 mjb 的 group,就達到我要
09/01 04:29, 3F

09/01 04:30, , 4F
的效果了
09/01 04:30, 4F

09/01 04:31, , 5F
fdmaury = 6,那個暫且不論,一開始euid與egid都已經是
09/01 04:31, 5F

09/01 04:33, , 6F
styx,為什麼還能開啟babe的檔案(mjb)呢?
09/01 04:33, 6F

09/01 22:56, , 7F
你打命令 "id" 時會列出三項: id, gid, 和 groups
09/01 22:56, 7F

09/01 23:00, , 8F
那個 groups 稱做 supplementary groups
09/01 23:00, 8F

09/01 23:02, , 9F
只要存取的檔案, gid出現在其中, 就視做以該gid進行存取,
09/01 23:02, 9F

09/01 23:03, , 10F
因此而可以存取 mjb.
09/01 23:03, 10F

09/02 01:44, , 11F
uid也有出現,那為什麼拿掉mjb group r屬性就不能存取
09/02 01:44, 11F

09/02 01:44, , 12F
了呢?
09/02 01:44, 12F

09/02 21:02, , 13F
檔案的存取權限判斷:
09/02 21:02, 13F

09/02 21:03, , 14F
(1) 檔案 uid 等於 euid ==> 取得 user 存取權限
09/02 21:03, 14F

09/02 21:05, , 15F
(2) 否則, 檔案 gid 等於 egid, 或在 groups 中 ==>
09/02 21:05, 15F

09/02 21:05, , 16F
取得 group 存取權限
09/02 21:05, 16F

09/02 21:05, , 17F
(3) 否則, 取得 others 存取權限.
09/02 21:05, 17F

09/02 21:09, , 18F
有 supplementary groups, 但沒有 supplementary users.
09/02 21:09, 18F

09/02 21:11, , 19F
不過, 要達到你要的權限存取, 在 file mode 為 -rw-r---- 時,
09/02 21:11, 19F

09/02 21:12, , 20F
Linux 還是有別的方式: 要使用 setfsuid() 和 setfsgid().
09/02 21:12, 20F

09/07 16:10, , 21F
babe只有primary group,沒有supplementary group
09/07 16:10, 21F

09/07 16:10, , 22F
還是說supplementary包含了primary group
09/07 16:10, 22F

09/09 19:41, , 23F
不清楚是否有文件規範是否 supplementary 包含 primary group,
09/09 19:41, 23F

09/09 19:42, , 24F
但目前所使用的 login 程式, 都會叫用 initgroup(),
09/09 19:42, 24F

09/09 19:43, , 25F
將 primary group 設進 supplementary.
09/09 19:43, 25F

09/09 19:44, , 26F
更正, initgroups(),
09/09 19:44, 26F

09/12 13:38, , 27F
謝謝,查了一下UNP,的確是如此
09/12 13:38, 27F
文章代碼(AID): #1I7PUgcw (LinuxDev)
文章代碼(AID): #1I7PUgcw (LinuxDev)