Làm thế nào được tạo ra của PID?


42

Trên * nix, PID là các định danh duy nhất cho các quy trình đang chạy. Làm thế nào được tạo ra của PID? Nó chỉ là một số nguyên được tăng lên hoặc một cấu trúc phức tạp hơn như một danh sách? Làm thế nào để họ được tái chế? Bằng cách tái chế, ý tôi là, khi một quá trình kết thúc, thì PID cuối cùng sẽ được sử dụng lại bởi một quy trình khác.


Câu trả lời:


39

Như wikipedia nói,

Trong Unix, ID tiến trình thường được phân bổ trên cơ sở tuần tự, bắt đầu từ 0 và tăng lên giá trị tối đa khác nhau tùy theo hệ thống. Khi đạt đến giới hạn này, phân bổ khởi động lại ở mức 0 và tăng trở lại. Tuy nhiên, đối với điều này và các lần tiếp theo, bất kỳ bộ vi xử lý nào vẫn được gán cho các quy trình đều bị bỏ qua.

Vì vậy, đây thực sự là một chính sách rất đơn giản cho "thế hệ", chỉ cần tăng bộ đếm và "tái chế", chỉ cần bọc số ở mức giá trị tối đa và tiếp tục tăng cho đến khi bạn tìm thấy một số được gán cho một quy trình đã kết thúc và có đã bị xóa khỏi bảng quy trình.

Một số triển khai Unix như AIX sử dụng một chính sách ít đơn giản hơn, xem ví dụ: Câu hỏi thường gặp này .


Cảm ơn câu trả lời. Nhân tiện, chính sách AIX này "đơn giản hơn" là gì?

1
@ Âm nhạc, tôi không nghĩ tài liệu AIX chính xác là chính sách nào được sử dụng (vì vậy nó có thể thay đổi ở bất kỳ bản phát hành nào), nhưng bạn có thể nghĩ đó là một thế hệ số ngẫu nhiên trong phạm vi thích hợp (được lặp lại cho đến khi tạo ra một PID hiện không sử dụng).
Alex Martelli

Thuật toán này có vẻ hơi rắc rối với tôi. Làm thế nào để bạn đảm bảo rằng bạn không gặp bế tắc? Và không có vấn đề về hiệu suất?

1
Hạt nhân nằm trong tầm kiểm soát và không cần khóa bất cứ thứ gì, vậy làm thế nào để nó bế tắc? Có, có một mức giá hiệu suất nhỏ phải trả (một khoản chi phí nhỏ thêm vào thời gian ngã ba - giả sử vài chục hướng dẫn máy để đọc PRNG hoặc / dev / urandom tương ứng, so với số lần tăng ít hơn), nhưng luôn luôn như vậy trường hợp cho các biện pháp nhằm cải thiện bảo mật (ví dụ: kiểm tra chi phí CPU của giao tiếp HTTPS so với HTTP đơn giản ;-).
Alex Martelli

Tôi có nghĩa là livelock ( while(true);), xin lỗi, tôi đã trả lời nhanh ;-)

11

Nó thay đổi.

Hầu hết các hệ thống chỉ đơn giản là giữ một số lượng PID cuối cùng được tạo, thêm một (bao bọc ở số lượng tối đa như 65535 hoặc nhỏ hơn một chút - thường thì sự bao bọc xảy ra ở 65000 hoặc thậm chí 60000) và kiểm tra xem số này hiện không được sử dụng ( lặp đi lặp lại nếu PID vẫn đang được sử dụng - vì vậy, PID 1, kernel vẫn ở đó và không được 'phát hành lại').

Các hệ thống có đầu óc bảo mật khác tạo ra một số ngẫu nhiên và kiểm tra xem nó không được sử dụng.

Tại bất kỳ thời điểm nào, đảm bảo rằng tất cả các số PID là duy nhất.


9

Đối với phần tái chế của câu hỏi, một điều cần lưu ý là một pid không có sẵn ngay khi quá trình với pid đó kết thúc. Pid không có sẵn cho đến khi cha mẹ của quá trình đó thu thập trạng thái chấm dứt của con của nó thông qua một số hình thức của lệnh gọi hệ thống Wait (). Một đứa trẻ bị chấm dứt nhưng cha mẹ của chúng không được chờ đợi được gọi là zombie và thường sẽ xuất hiện trong một ps như là không còn tồn tại. Một phụ huynh có hành vi xấu có thể bỏ đói hệ thống các pids nếu nó ra mắt trẻ em và không chờ đợi () cho chúng.

Nếu cha mẹ của một quá trình chết trước khi nó thu thập trạng thái của một đứa trẻ, điều đó là ổn. Đứa trẻ được thừa kế bởi init, người sẽ đảm bảo rằng một sự chờ đợi () được ban hành và pid được tái chế.


Đây là một chi tiết rất quan trọng. Không có nó, ngay cả một đơn giản myprog &theo sau wait $!sẽ là UB.
Andreas

3

Chúng là số thứ tự và bao quanh (ở giá trị dành riêng cho hệ điều hành) nếu hệ thống hoạt động đủ lâu. Các số không bao giờ được sử dụng lại trừ khi chúng miễn phí tại điểm fork().

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.