2010-11-17 22 views
10

Tôi biết cách gửi tín hiệu đến quá trình con trong C bằng cách sử dụng chức năng kill(pid_t pid, int sig). Điều gì về việc gửi tín hiệu đến chủ đề? là nó có thể ?. Nếu vậy, làm thế nào để bắt tín hiệu trên chủ đề "con". Ví dụ, nếu thread chính gửi cho tôi một tín hiệu chấm dứt, làm thế nào tôi có thể trong thread khác bắt nó.Gửi và bắt tín hiệu đến pthreads trong C

Trả lời

8

Với chủ đề POSIX, bạn có chức năng pthread_cond_waitpthread_cond_signal.

int pthread_cond_wait(pthread_cond_t *restrict cond, pthread_mutex_t *restrict mutex) 
int pthread_cond_signal(pthread_cond_t *cond) 

Các hiệu thread nên chặn trên một cuộc gọi pthread_cond_wait cho đến khi thread khác sẽ gửi một tín hiệu sử dụng pthread_cond_signal, với biến tình trạng tương tự.

Xem xét tương tự với các tín hiệu được gửi đến các quy trình, điều này hơi khác một chút vì chuỗi báo hiệu đã tạm ngưng thực hiện chờ tín hiệu, không giống như một quá trình đơn giản bị gián đoạn và tiếp tục.

+7

Điều này khá khác với tín hiệu. Mặc dù tôi đồng ý rằng đây thường là cách tiếp cận tốt hơn, 'pthread_kill' là câu trả lời cho câu hỏi của OP, tôi nghĩ vậy. –

+2

@R ..: Thực ra câu hỏi không rõ ràng và tôi giả định rằng tác giả không hỏi về việc cung cấp tín hiệu OS cho một chuỗi cụ thể, mà đúng hơn là gửi tín hiệu giữa các luồng. –

0

Tôi không chắc chắn điều này là có thể vì nó là nền tảng và thực hiện phụ thuộc và tôi đánh giá cao đề nghị bạn không sử dụng tín hiệu để giao tiếp giữa các chủ đề. Đôi khi chỉ có một chủ đề cụ thể sẽ nhận được tín hiệu và đôi khi tất cả các chủ đề nhận được tín hiệu.

Cơ chế kết nối chủ đề tốt hơn tồn tại như hàng đợi, semaphores và khóa.

2

Tín hiệu không có mối quan hệ chuỗi. Chúng được xử lý hoàn toàn không đồng bộ. Khi bạn chỉ định trình xử lý tín hiệu với signal(2) hoặc sigaction(2), đây là trình xử lý tín hiệu toàn cầu. Khi một tín hiệu được nâng lên, bộ xử lý tín hiệu chạy trên đỉnh của bất kỳ chuỗi nào xảy ra khi chạy vào lúc đó và bạn không thể kiểm soát được điều đó.

Có vẻ như bạn muốn có một số loại giao tiếp xen kẽ khác. Cách đơn giản nhất để làm điều này là với một biến volatile chia sẻ:

volatile bool should_terminate = false; 

void ChildThread() 
{ 
    while(!should_terminate) 
    { 
     // do stuff 
    } 
} 

void MainThread() 
{ 
    // To terminate child thread: 
    should_terminate = true; 
} 

Nếu bạn cần kiểm soát đồng thời mạnh mẽ hơn, nhìn vào mutexes, các biến điều kiện, và Cột.

7

Tín hiệu được gửi đến toàn bộ quy trình. Mỗi tín hiệu gửi đến quá trình được nhận bởi một sợi đơn (thay mặt cho toàn bộ chương trình). Có mặt nạ tín hiệu cho mỗi luồng ảnh hưởng đến việc liệu một chuỗi cụ thể có đủ điều kiện để xử lý một tín hiệu cụ thể hay không.

Vì vậy, bạn cần một trình xử lý tín hiệu - có thể chỉ trong một chuỗi. Lưu ý rằng có những giới hạn về những gì bạn phải làm trong trình xử lý tín hiệu của một chuỗi. Hãy thận trọng bước xa ngoài những lời hứa được thực hiện bởi các tiêu chuẩn (đó là tối thiểu).

Tuy nhiên, có thể sử dụng chức năng pthread_kill() để gửi tín hiệu đến các chủ đề khác miễn là chuỗi hiện tại có thể xác định (có quyền truy cập vào giá trị ID luồng (pthread_t) xác định) các chuỗi vẫn đang thực hiện trong quy trình. Bạn có thể quyết định chuyển tín hiệu đến các luồng khác bằng cách sử dụng một số tín hiệu khác với số nguyên ban đầu bị bắt (vì vậy một luồng nhận tín hiệu bên ngoài, nhưng nhiều luồng nhận tín hiệu bên trong). Hoặc bạn có thể sử dụng đồng bộ hóa Pthread khác hoặc nguyên thủy truyền thông thay vì tín hiệu.

+0

Tôi sẽ làm rõ "có quyền truy cập vào ID luồng". Về mặt chính xác, ngay cả khi bạn có 'pthread_t' được lưu trữ, nó không hợp lệ (hành vi không xác định) để sử dụng nó nếu luồng có thể đã kết thúc trong trạng thái tách rời hoặc với một luồng khác đã gọi' pthread_join' trên nó. –

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