2009-05-08 63 views
34

Sự khác biệt giữa lỗi bus và lỗi phân đoạn? Có thể xảy ra một chương trình cho lỗi seg và dừng lần đầu tiên và lần thứ hai nó có thể gây ra lỗi bus và thoát không?Lỗi bus vs Lỗi phân đoạn

+0

Bản sao có thể xảy ra của [Lỗi xe buýt là gì?] (Http://stackoverflow.com/questions/212466/what-is-a-bus-error) –

Trả lời

39

Trên hầu hết các kiến ​​trúc Tôi đã sử dụng, sự khác biệt là ở chỗ:

  • một SEGV xảy ra khi bạn truy cập vào bộ nhớ bạn không có nghĩa là để (ví dụ, bên ngoài không gian địa chỉ của bạn).
  • SIGBUS gây ra do sự cố liên kết với CPU (ví dụ: cố đọc một địa chỉ dài không phải là bội số của 4).
+13

Các tệp ánh xạ bộ nhớ cũng có thể tạo SIGBUS. – bk1e

+0

trên cánh tay SIGBUS có thể xảy ra nếu bạn đọc một phao từ một địa chỉ không phải là 4 byte liên kết – shoosh

+2

shoosh, tôi khá chắc chắn được bao phủ bởi điểm bullet thứ hai của tôi. – paxdiablo

4

Tôi giả sử bạn đang nói về các tín hiệu SIGSEGVSIGBUS do Posix xác định.

SIGSEGV xảy ra khi chương trình tham chiếu địa chỉ không hợp lệ. SIGBUS là lỗi phần cứng được triển khai. Hành động mặc định cho hai tín hiệu này là chấm dứt chương trình.

Chương trình có thể bắt các tín hiệu này và thậm chí bỏ qua chúng. Ví dụ:

6

Ví dụ: có thể xảy ra lỗi xe buýt khi chương trình của bạn cố gắng thực hiện điều gì đó mà bus phần cứng không hỗ trợ. Ví dụ: trên SPARCs, cố gắng đọc giá trị nhiều byte (chẳng hạn như int, 32 bit) từ một địa chỉ lẻ tạo ra lỗi bus.

Lỗi phân đoạn xảy ra chẳng hạn khi bạn thực hiện quyền truy cập vi phạm các quy tắc phân đoạn, tức là cố gắng đọc hoặc ghi bộ nhớ mà bạn không sở hữu.

+0

điều gì có nghĩa là khi bạn nói "đọc hoặc ghi bộ nhớ bạn không sở hữu? " khi bạn làm một malloc bạn đã phân bổ như nói 5 byte bộ nhớ. Nếu bạn đọc/ghi bộ nhớ bạn không sở hữu nó không cung cấp cho bạn một lỗi Seg trong C. – Thunderboltz

+0

Trên ghi đè trái một bộ nhớ thuộc sở hữu của một số đối tượng khác trong cùng một không gian địa chỉ cho một lỗi Segmentation ?? – Geek

+0

"Những gì bạn sở hữu" ở cấp hệ điều hành thường nhiều hơn những gì bề mặt thời gian chạy (ví dụ: thông qua malloc) cho bạn. Vì vậy, có nhiều không gian cho bộ nhớ để truy cập mà bạn sở hữu, nhưng vẫn không nên và có nhiều không gian địa chỉ mà bạn có thể đọc, nhưng không viết (hầu hết các thư viện được ánh xạ) cũng như các chức năng cụ thể để ghi các vùng bộ nhớ bảo vệ (mprotect) . –

0

Đây sẽ là một dup của What is a bus error?, nếu nó không được cho các

Nó có thể xảy ra rằng một chương trình cung cấp cho một lỗi seg và dừng lại cho lần đầu tiên và lần thứ hai nó có thể cung cấp cho một lỗi xe buýt và xuất cảnh?

một phần của câu hỏi. Bạn sẽ có thể trả lời điều này cho chính mình với thông tin được tìm thấy ở đây.


Insanity: làm điều tương tự hơn và hơn nữa và mong đợi kết quả khác nhau.
- Albert Einstein


Tất nhiên, tham gia các câu hỏi theo nghĩa đen ...

#include <signal.h> 
#include <stdlib.h> 
#include <time.h> 
#include <unistd.h> 
int main() { 
    srand(time(NULL)); 
    if (rand() % 2) 
     kill(getpid(), SIGBUS); 
    else 
     kill(getpid(), SIGSEGV); 
    return 0; 
} 

Tada, một chương trình mà có thể thoát ra với một lỗi segmentation trên một lần chạy và thoát ra với một lỗi bus trên một lần chạy khác.

+2

+1 cho báo giá Einstein và để cân bằng -1 không được điều chỉnh. – tokland

2

Diễn giải câu hỏi của bạn (có thể không chính xác) như ý nghĩa "Tôi không liên tục nhận SIGSEGV hoặc SIGBUS, tại sao nó không nhất quán?", Điều đáng chú ý là làm những điều tồi tệ với con trỏ không được đảm bảo bởi C hoặc C++ tiêu chuẩn để dẫn đến một segfault; nó chỉ là "hành vi không xác định", mà như một giáo sư tôi đã từng đặt nó có nghĩa là nó có thể thay vì gây ra cá sấu nổi lên từ sàn và ăn bạn.

Vì vậy, tình huống của bạn có thể là bạn có hai lỗi, nơi xảy ra lần đầu tiên đôi khi gây SIGSEGV và thứ hai (nếu segfault không xảy ra và chương trình vẫn đang chạy) gây SIGBUS.

Tôi khuyên bạn nên bước qua với trình gỡ lỗi và tìm kiếm cá sấu.

16

SIGBUS cũng sẽ được tăng lên nếu bạn mmap() một tệp và cố gắng truy cập một phần bộ đệm được ánh xạ mở rộng qua cuối tệp cũng như các điều kiện lỗi như hết dung lượng. Nếu bạn đăng ký trình xử lý tín hiệu bằng cách sử dụng sigaction() và bạn đặt SA_SIGINFO, bạn có thể yêu cầu chương trình kiểm tra địa chỉ bộ nhớ bị lỗi và chỉ xử lý các lỗi tệp được ánh xạ bộ nhớ.