Tìm tập tin mà người dùng không thể đọc?


12

Tôi muốn tìm các tệp mà một người dùng cụ thể sẽ không thể đọc được.

Giả sử tên người dùng là "user123" và họ thuộc một nhóm có tên "user123". Tôi muốn tìm các tệp mà nếu chúng thuộc sở hữu của user123 có u + r trên; không thành công nếu tập tin là nhóm user123 thì nên bật g + r; thất bại mà nó có thể có o + r trên.

Vì GNU find có "-readable", tôi có thể làm điều này:

sudo -u user123 find /start ! -readable -ls

Tuy nhiên, quá trình phải được chạy bởi người dùng không có quyền truy cập sudo. Do đó, tôi đã thử cách này: (nó không kiểm tra o + r nhưng điều đó không quan trọng ở điểm này)

find /start \( -user user123 ! -perm -u=r  \) -o \( -group user123 ! -perm -g=r  \) -ls

nhưng nó liệt kê tập tin này:

272118    4 -rw-------   1 user123   user123       3243 Jul  3 19:50 /start/blah/blah/file.txt

Tệp này là tệp duy nhất thuộc quyền /startsở hữu của user123 bị g=rtắt. Như thể tìm thấy là giải thích -u=rnhư -g=r.

Tôi quyết định thử đảo ngược logic và thay vào đó kiểm tra not ( truth ):

find /etc/puppet ! \( \( -user puppet -perm -u=r  \) -o \( -group puppet -perm -g=r \) -o \( -perm -o=r \) \)  -ls

Đó là công việc!

Tại sao ban đầu findthất bại? Đây có phải là một lỗi trong find(không có khả năng) hoặc logic sai?

Cập nhật: Tôi đã có logic sai. Như được chỉ ra dưới đây, kể từ khi! (A || B || C) == (! A &&! B &&! C) đây là hai câu tương đương:

find /start ! \( \( -user user123 -perm -u=r \) -o \( -group user123 -perm -g=r \) -o \( ! \( -user user123 -o -group user123 \) -perm -o=r \) \) -ls
find /start ! \( -user user123 -perm -u=r \) ! \( -group user123 -perm -g=r \) ! \( ! \( -user user123 -o -group user123 \) -perm -o=r \) -ls

Mục tiêu của tôi là không phải kiểm tra người dùng / nhóm hai lần. Điều tôi thực sự cần là một cấu trúc if-then-other phức tạp hơn, có lẽ chỉ có thể có nếu có toán tử -xor. Tôi có thể xây dựng một xor ngoài và / hoặc / không nhưng nó sẽ phức tạp hơn hai giải pháp ở trên.


1
Ngay cả logic thứ hai là sai, bởi vì nó sẽ nói puppetcó quyền truy cập vào một tệp với --wxrwxrwx puppet puppet.
Stéphane Chazelas

Câu trả lời:


7

Logic là sai. Bạn đang nghĩ rằng tập tin này không nên được liệt kê bởi vì nó thuộc sở hữu của user123và có tập rbit của người dùng . Tuy nhiên, nó được liệt kê vì nó phù hợp với tiêu chí thứ hai (nó thuộc sở hữu của nhóm user123và có một rchút không được đặt của nhóm ).

Phiên bản thứ hai của bạn hoạt động nhờ một trong các luật của de Morgan : phủ định ORing logic của một nhóm các câu lệnh tương đương về mặt logic với ANDing phủ định của các câu lệnh riêng lẻ. Nói cách khác:

 ! ( A || B || C ) == ( !A && !B && !C )

Vì vậy, công việc findđang tìm kiếm một tập tin

  • Không phải (thuộc sở hữu của người dùng user123và có thể đọc được bởi người dùng đã nói) VÀ
  • Không phải (thuộc sở hữu của nhóm user123và có thể đọc được bởi nhóm đã nói) VÀ
  • Không thể đọc được trên thế giới.

trong khi người đầu tiên findđang tìm kiếm một tập tin

  • Được sở hữu bởi người dùng user123và không thể đọc được bởi người dùng đã nói HOẶC
  • Được sở hữu bởi nhóm user123và không thể đọc được bởi nhóm đã nói HOẶC (nếu bạn đã hoàn thành nó)
  • Không thể đọc được trên thế giới

Vì vậy, một tệp phù hợp với BẤT K of 3 tiêu chí trên (và không nhất thiết là tất cả) sẽ được liệt kê như bạn đã thấy.

Biên tập

Ngẫu nhiên (sau khi xem hồ sơ của bạn), tôi là một fan hâm mộ lớn của cuốn sách O'Reilly của bạn :)


Cảm ơn đã phân tích. Vâng, đó là một sự áp dụng sai luật của Morgan. Tôi đã cố gắng để làm ( !A && !B && !C )nhưng tôi đã chuyển !vào bên trong của mỗi phần, không hợp lệ. Cảm ơn!
TomOnTime

PS tôi rất vui vì bạn là một fan hâm mộ của cuốn sách của tôi! Tôi tò mò bạn đọc ngôn ngữ nào.
TomOnTime

@TomOnTime Tiếng Anh, tất nhiên. Tôi cố gắng đọc bất kỳ cuốn sách nào bằng ngôn ngữ gốc của nó nếu tôi có thể giúp nó.
Joseph R.

8

Còn nhiều điều nữa cần xem xét để kiểm tra xem người dùng có quyền truy cập vào tệp thông qua một đường dẫn cụ thể không:

  • Chủ sở hữu của tập tin
  • nhóm của tập tin
  • các ACL trong tệp
  • các uid, gid và các bổ sung của người dùng
  • tìm kiếm truy cập vào bất kỳ thành phần đường dẫn dẫn đến tập tin đó.
  • cho dù tập tin là một liên kết tượng trưng
  • quyền áp dụng khác nhau cho người dùng id 0.
  • có thể nhiều tính năng bảo mật hơn như SELinux ...

Thiếu thực sự chuyển đổi tất cả các uids và gids sang những người dùng và kiểm tra, rất khó để thực hiện logic giống như những gì hệ thống làm.

Với zsh, bạn có thể làm (với quyền root):

readable() (
  USERNAME=$u
  [ -r "$REPLY" ]
)
u=some-user
print -rl -- **/*(DoN^+readable)

Hoặc với perl:

find . -print0 | sudo -u some-user perl -Mfiletest=access -l -0ne '
  print unless -r'

Đó là trong cả hai trường hợp, hạ xuống cây thư mục như rootnhưng kiểm tra quyền truy cập tệp như người dùng tương ứng.

Chạy find -readablenhư some-userkhông có trong trường hợp vì nó sẽ không thể đi qua các thư mục mà người dùng không có quyền truy cập hoặc không có quyền đọc (nhưng có thể truy cập).

Ngay cả khi chỉ xem xét sự cho phép và quyền sở hữu của chính tệp (chứ không phải ACL hoặc thành phần đường dẫn ...), bạn cần ít nhất (ở đây là cú pháp GNU):

u=some-user; g=$(id -G "$u" | sed 's/ / -o -group /g'); IFS=" "
find . ! \( -user "$u" -perm -u=r -o \
          ! -user "$u" \( -group $g \) -perm -g=r -o \
          ! -user "$u" ! \( -group $g \) -perm -o=r \)

Ý tưởng là nếu tập tin thuộc sở hữu của người dùng, tất cả các quyền khác đều không liên quan. Nếu không, thì nếu tệp thuộc sở hữu của bất kỳ nhóm nào của người dùng, thì quyền "khác" là không liên quan.


1
Điểm tốt về ACL và các yếu tố khác. Đánh giá đúng 100% là access()do nó sử dụng cùng mã nhân như open(). Vì vậy, sudo -u user123 find /start -readablelà giải pháp tốt nhất nếu sudolà một lựa chọn.
TomOnTime

1
@TomOnTime. À không, nếu bạn sử dụng sudo -u user123 find -readable, nó sẽ không báo cáo các tệp trong các thư mục bạn không thể nhập hoặc trong các thư mục bạn không thể đọc (do đó sẽ có phủ định sai và dương tính giả). Đó là lý do tại sao tôi đề nghị sử dụng zshcho giảm dần cây thư mục như là người chủ và làm access()( [ -r ... ]) như người sử dụng thực tế (thiết lập $USERNAMEtrong zshnhững thay đổi tất cả các uids và gids như sudosẽ).
Stéphane Chazelas
Khi sử dụng trang web của chúng tôi, bạn xác nhận rằng bạn đã đọc và hiểu Chính sách cookieChính sách bảo mật của chúng tôi.
Licensed under cc by-sa 3.0 with attribution required.