Đây là một lỗi nguy hiểm ẩn trong mã của bạn. Trong C và C++ bạn không được phép trả về một con trỏ để ngăn xếp dữ liệu trong một hàm. Nó dẫn đến hành vi không xác định. Tôi sẽ giải thích tại sao.
Chương trình C/C++ hoạt động bằng cách đẩy dữ liệu vào và tắt ngăn xếp chương trình. Khi bạn gọi một hàm, tất cả các tham số được đẩy lên ngăn xếp, và sau đó tất cả các biến cục bộ được đẩy lên ngăn xếp. Khi chương trình thực hiện nó có thể đẩy và bật thêm nhiều mục vào và tắt ngăn xếp trong chức năng của bạn. Trong ví dụ của bạn, bộ đệm được đẩy lên ngăn xếp và sau đó t được đẩy lên ngăn xếp . Ngăn xếp có thể trông như thế nào,
- stack Previous
- thông số
- (dữ liệu khác)
- đệm (50000 bytes)
- t (con trỏ sizeof)
Tại thời điểm này , t nằm trên ngăn xếp và trỏ tới bộ đệm, cũng nằm trên ngăn xếp. Khi hàm trả về, thời gian chạy bật tất cả các biến trên ngăn xếp, trong đó bao gồm t, bộ đệm và các tham số. Trong trường hợp của bạn, bạn trả về con trỏ t, do đó tạo một bản sao của nó trong chức năng gọi.
Nếu chức năng gọi sau đó nhìn vào những gì t trỏ đến, nó sẽ tìm thấy rằng nó trỏ đến bộ nhớ trên ngăn xếp có thể có hoặc không tồn tại.(Thời gian chạy popped nó ra khỏi ngăn xếp, nhưng các dữ liệu trên stack vẫn có thể ở đó do trùng hợp ngẫu nhiên, có thể không).
Tin vui là, nó không phải là vô vọng. Có các công cụ tự động có thể tìm kiếm các loại lỗi này trong phần mềm của bạn và báo cáo chúng. Chúng được gọi là công cụ phân tích tĩnh . Sentry là một ví dụ như một chương trình có thể báo cáo loại lỗi này là .
Nguồn
2010-03-11 15:29:38
Vâng, bạn là chính xác. Bạn không nên trả về một mảng tĩnh từ một hàm. – AraK
@nvl Ngay cả khi 't' đang được cấp phát động, nó sẽ yêu cầu toán tử gán quá tải sao cho đúng bộ đệm. – KevenK
Không phải rò rỉ bộ nhớ, chỉ "may mắn là nó hoạt động". Nếu bộ nhớ mà mảng được cấp phát trên ngăn xếp được tái sử dụng, thì bạn sẽ có rác trong mảng của mình. Đó là một cách hay để tạo các lỗi tối nghĩa. –