2012-06-30 29 views
5

ghi các cuộc gọi hàm từ nhiều luồng đến cùng một ổ cắmcó an toàn khi sử dụng chức năng Viết trong GNU C bằng cách sử dụng nhiều chủ đề

có an toàn không? Chúng tôi có muốn thêm tính năng đồng bộ hóa giữa chúng không? Nó sẽ gây ra vấn đề fro như Application bị trì hoãn ghi/đọc từ lớp mạng để lớp Application

Chúng tôi đang sử dụng GNU C++ thư viện GCC 4 trên Linux Redhat enviornment

Đây là một Process Server Side nơi Chỉ có 1 Kết nối Ổ cắm giữa Máy chủ & Máy chủ Khách hàng & Máy khách đang ở trên 2 Máy khác nhau Dữ liệu được gửi từ Máy chủ đến Máy khách tới Máy chủ

Sự cố 1 khi Máy chủ Gửi dữ liệu cho phía máy khách (Nhiều chủ đề viết dat a đến phía máy khách thông qua cùng một Socket) Nhưng dữ liệu Writen từ một số luồng không được chuyển sang phía máy khách, nó thậm chí không đi đến lớp mạng của cùng một máy (Tcpdump không có dữ liệu đó)

Vấn đề 2-khi khách hàng Gửi dữ liệu đến máy chủ dữ liệu Gửi theo khách hàng được hiển thị trong TCPdump của máy chủ không nhận được cho ứng dụng máy chủ đang đọc từ ổ cắm từ một chủ đề duy nhất sử dụng "&" chọn "chức năng trong vòng lặp

Chúng tôi không thể xác định được mô hình xảy ra các sự cố này Chúng tôi cho rằng điều này sẽ xảy ra khi có quá nhiều luồng được ghi vào cùng Ổ cắm Chúng tôi không đồng bộ hóa chức năng ghi hy vọng hệ điều hành đang xử lý việc đồng bộ hóa

+0

Đó là "an toàn" theo nghĩa là chương trình của bạn được tạo đúng, nhưng kết quả mà bạn thấy trên ổ cắm của bạn có thể không phải là những gì bạn mong đợi. –

+0

@KerrekSB: đó là một nhận xét kỳ lạ. Bất kỳ chương trình không an toàn nào có thể được gọi là "an toàn" theo nghĩa đó, phải không? –

+0

@NedBatchelder: Chắc chắn là không. Ví dụ, một hàm phụ thuộc vào một bộ đệm tĩnh để giữ trạng thái bên trong của nó đơn giản là * không * thread-safe, và một chương trình gọi nó nhiều lần đồng thời chỉ là không xác định. Ngược lại, một chương trình gọi 'write' đồng thời không tự động được xác định. –

Trả lời

0

Không an toàn khi sử dụng viết() từ nhiều luồng. Không có gì đảm bảo rằng đầu ra sẽ không bị xáo trộn cùng nhau. Một ghi có thể đặt một nửa số byte của nó vào ổ cắm, sau đó một ghi có thể bắt đầu đặt nó byte. Nếu bạn cần phải chắc chắn mỗi viết được viết liên tục (và thật khó để tưởng tượng không cần đảm bảo đó), sau đó bạn cần một khóa hoặc một số phương pháp đồng bộ hóa khác.

+0

cảm ơn Ned. Nó sẽ gây ra vấn đề trên? – samira

+0

@samira: nó chắc chắn có thể gây ra các vấn đề bạn đã mô tả, nhưng không thể nói liệu đồng bộ hóa có phải là nguyên nhân hay không. –

+1

khi truy cập chức năng u có thể sử dụng mutex để chỉ có một chuỗi truy cập chức năng tại một thời điểm ... – shofee

1

write() là cuộc gọi hệ thống, không phải là chức năng thư viện và các cuộc gọi hệ thống thường được đảm bảo là nguyên tử.

+3

Đúng, và không đúng sự thật. Cuộc gọi hệ thống được đảm bảo là nguyên tử (và "an toàn" theo nghĩa là nó sẽ không sụp đổ hoặc làm hỏng dữ liệu của bạn) nhưng không đảm bảo rằng dữ liệu đồng thời được gửi (nguyên tử) bởi hai luồng là _transferred_ nguyên tử: [thú vị đọc] (http://www.almaden.ibm.com/cs/people/marksmith/sendmsg.html). Cũng lưu ý rằng 'write' và' send' về mặt kỹ thuật được phép viết ít hơn bạn yêu cầu, trong trường hợp đó bạn phải tiếp tục với thao tác ghi thứ hai, hãy bỏ tất cả nguyên tử. – Damon

0

Nó sẽ không được chỉ định mà trước tiên, write cuộc gọi sẽ hoàn tất. Một chuyển đổi ngữ cảnh có thể ngăn chặn bất kỳ của hai ghi ở hướng dẫn đầu tiên. Điều này có thể dẫn đến thứ tự tùy ý. Không có gì là write hoặc hạt nhân có thể làm điều đó. Đó là một vấn đề cơ bản.

Dữ liệu của bạn sẽ được viết theo thứ tự không xác định mà có thể không được chấp nhận cho bạn.

Các vấn đề liên quan