2009-11-02 5 views
9

Tôi thấy một vấn đề mà một cuộc gọi để thúc đẩy thread-> tham gia vào một destructor dẫn đến một bế tắc. Tôi không hiểu tại sao, và tôi không quá quan tâm đến việc giữ mã chỉ hoạt động (và tôi không hiểu tại sao nó lại làm) trong dự án.Tham gia một tăng :: thread dụ trong destructor

khai Class (Tôi đã lột method run() của try/catch cho ngắn gọn: Theo các tài liệu thúc đẩy chủ đề, kết quả nên được như vậy có hay không có nó):

class B 
{ 
public: 
    void operator()(){run();} 
    void run(); 
    void shutdown(); 
    ~B(); 
    B(); 
    boost::thread *thr; 
    bool shutdown_requested; 
}; 

void B::shutdown() 
{ 
    shutdown_requested = true; 

    if (thr != NULL) 
    { 
     thr->interrupt(); 
     thr->join(); // deadlock occurs here! 
     delete thr; 
     thr = NULL; 
    } 
} 

B::~B() 
{ 
    shutdown(); 
} 

B::B() 
{ 
    thr = new boost::thread(boost::ref(*this)); 
} 

void B::run() 
{ 
    while (!shutdown_requested) 
    { 
     boost::xtime xt; 
     boost::xtime_get(&xt, boost::TIME_UTC); 
     xt.sec += 30; 
     boost::this_thread::sleep(xt); 
    } 
} 

Snippet mà không làm việc:

int main() 
{ 
    B *b = new B; 

    Sleep(5000); 
    printf("deleting \n");fflush(stdout); 
// b->shutdown(); 
    delete b; 
    printf("done\n");fflush(stdout); 

    return 0; 
} 

Snippet mà hoạt động:

int main() 
{ 
    B *b = new B; 

    Sleep(5000); 
    printf("deleting \n");fflush(stdout); 
    b->shutdown(); 
    delete b; 
    printf("done\n");fflush(stdout); 

    return 0; 
} 

tôi nghĩ rằng Lý do cho hành vi này có gì để làm với đoạn này của tài liệu tăng:

người dùng của Boost.Thread phải đảm bảo rằng gọi đến đối tượng outlives thread mới được thành lập thực hiện.

Nhưng tôi không thực sự hiểu tại sao bế tắc - nối chuỗi không gọi hàm hủy trên B và chính đối tượng không bị xóa khi phương thức run() được cho là thoát.

+1

Câu hỏi hay và được hỏi rõ. Tôi không biết một câu trả lời, nhưng bạn đã có một cái nhìn vào việc thực hiện tăng :: thread? Hay bạn đã thử gỡ lỗi nó? Có lẽ điều đó cho bạn một gợi ý. Từ nhìn vào mã ví dụ, tôi muốn nói nó sẽ hoạt động tốt. – MP24

+0

Cảm ơn, tôi đã tìm thấy sự cố bằng cách bước vào trình gỡ lỗi. Nó liên quan đến mã phát hiện rò rỉ. – laura

Trả lời

4

Tôi đã tìm thấy vấn đề: nó tóm tắt thành một lập trình viên quá nhiệt tình.

Ban đầu tôi đã biên soạn dự án của mình bằng DUMA (http://sourceforge.net/projects/duma/) để xem liệu việc triển khai mô-đun hiện tại của tôi có bị rò rỉ không. Thật không may, sandbox thử nghiệm của tôi cũng có cài đặt duma, mà tôi đã không nhận ra cho đến khi tôi bước qua mã trong trình gỡ lỗi.

Sau khi xóa tất cả phát hiện rò rỉ bộ nhớ, mọi thứ hoạt động như mong đợi.

+0

Lưu ý rằng bạn có thể chấp nhận câu trả lời của riêng bạn để đánh dấu câu hỏi của bạn là đã trả lời. – MP24

+0

Chỉ sau hai ngày không may. Cảm ơn một lần nữa vì sự giúp đỡ – laura