Tôi có một tính toán bên trong ST phân bổ bộ nhớ thông qua một Data.Vector.Unboxed.Mutable. Vectơ không bao giờ được đọc hoặc viết, cũng không có bất kỳ tham chiếu nào được giữ lại bên ngoài runST (theo hiểu biết tốt nhất của tôi). Vấn đề tôi có là khi tôi chạy tính toán ST của tôi nhiều lần, đôi khi tôi dường như giữ bộ nhớ cho vectơ xung quanh.Haskell: Rò rỉ bộ nhớ từ ST/GC không thu thập?
thống kê Allocation:
5,435,386,768 bytes allocated in the heap
5,313,968 bytes copied during GC
134,364,780 bytes maximum residency (14 sample(s))
3,160,340 bytes maximum slop
518 MB total memory in use (0 MB lost due to fragmentation)
Ở đây tôi gọi runST 20x với giá trị khác nhau cho tính toán của tôi và một vector 128MB (một lần nữa - không sử dụng, không được trả lại hoặc tham chiếu bên ngoài của ST). Các cư trú tối đa có vẻ tốt, về cơ bản chỉ là vector của tôi cộng với một vài MB của các công cụ khác. Nhưng tổng số bộ nhớ sử dụng chỉ ra rằng tôi có bốn bản sao của vectơ hoạt động cùng một lúc. Điều này quy mô hoàn hảo với kích thước của vector, cho 256MB, chúng tôi nhận được 1030MB như mong đợi.
Sử dụng vector 1 GB hết bộ nhớ (4x1GB + trên không> 32 bit). Tôi không hiểu lý do tại sao RTS giữ dường như không sử dụng, bộ nhớ unreferenced xung quanh thay vì chỉ GC'ing nó, ít nhất là tại điểm mà một phân bổ nếu không sẽ thất bại.
Chạy với + RTS -S tiết lộ như sau:
Alloc Copied Live GC GC TOT TOT Page Flts
bytes bytes bytes user elap user elap
134940616 13056 134353540 0.00 0.00 0.09 0.19 0 0 (Gen: 1)
583416 6756 134347504 0.00 0.00 0.09 0.19 0 0 (Gen: 0)
518020 17396 134349640 0.00 0.00 0.09 0.19 0 0 (Gen: 1)
521104 13032 134359988 0.00 0.00 0.09 0.19 0 0 (Gen: 0)
520972 1344 134360752 0.00 0.00 0.09 0.19 0 0 (Gen: 0)
521100 828 134360684 0.00 0.00 0.10 0.19 0 0 (Gen: 0)
520812 592 134360528 0.00 0.00 0.10 0.19 0 0 (Gen: 0)
520936 1344 134361324 0.00 0.00 0.10 0.19 0 0 (Gen: 0)
520788 1480 134361476 0.00 0.00 0.10 0.20 0 0 (Gen: 0)
134438548 5964 268673908 0.00 0.00 0.19 0.38 0 0 (Gen: 0)
586300 3084 268667168 0.00 0.00 0.19 0.38 0 0 (Gen: 0)
517840 952 268666340 0.00 0.00 0.19 0.38 0 0 (Gen: 0)
520920 544 268666164 0.00 0.00 0.19 0.38 0 0 (Gen: 0)
520780 428 268666048 0.00 0.00 0.19 0.38 0 0 (Gen: 0)
520820 2908 268668524 0.00 0.00 0.19 0.38 0 0 (Gen: 0)
520732 1788 268668636 0.00 0.00 0.19 0.39 0 0 (Gen: 0)
521076 564 268668492 0.00 0.00 0.19 0.39 0 0 (Gen: 0)
520532 712 268668640 0.00 0.00 0.19 0.39 0 0 (Gen: 0)
520764 956 268668884 0.00 0.00 0.19 0.39 0 0 (Gen: 0)
520816 420 268668348 0.00 0.00 0.20 0.39 0 0 (Gen: 0)
520948 1332 268669260 0.00 0.00 0.20 0.39 0 0 (Gen: 0)
520784 616 268668544 0.00 0.00 0.20 0.39 0 0 (Gen: 0)
521416 836 268668764 0.00 0.00 0.20 0.39 0 0 (Gen: 0)
520488 1240 268669168 0.00 0.00 0.20 0.40 0 0 (Gen: 0)
520824 1608 268669536 0.00 0.00 0.20 0.40 0 0 (Gen: 0)
520688 1276 268669204 0.00 0.00 0.20 0.40 0 0 (Gen: 0)
520252 1332 268669260 0.00 0.00 0.20 0.40 0 0 (Gen: 0)
520672 1000 268668928 0.00 0.00 0.20 0.40 0 0 (Gen: 0)
134553500 5640 402973292 0.00 0.00 0.29 0.58 0 0 (Gen: 0)
586776 2644 402966160 0.00 0.00 0.29 0.58 0 0 (Gen: 0)
518064 26784 134342772 0.00 0.00 0.29 0.58 0 0 (Gen: 1)
520828 3120 134343528 0.00 0.00 0.29 0.59 0 0 (Gen: 0)
521108 756 134342668 0.00 0.00 0.30 0.59 0 0 (Gen: 0)
Đây có vẻ như chúng ta có vượt ~ 128MB 'byte sống'.
Hồ sơ +RTS -hy
về cơ bản chỉ nói chúng tôi phân bổ 128MB:
http://imageshack.us/a/img69/7765/45q8.png
tôi đã cố gắng tái tạo hành vi này trong một chương trình đơn giản hơn, nhưng ngay cả với sao chép các thiết lập chính xác với ST, một Reader chứa Vector, cùng monad/chương trình cấu trúc vv các chương trình thử nghiệm đơn giản không hiển thị này. Đơn giản hóa chương trình lớn của tôi, hành vi cũng dừng lại khi loại bỏ hoàn toàn mã không liên quan.
Qs:
- Am Tôi thực sự giữ vector này khoảng 4 lần trong số 20?
- Nếu có, làm thế nào để tôi thực sự kể từ
+RTS -Hy
vàmaximum residency
tuyên bố tôi không và tôi có thể làm gì để ngăn chặn hành vi này? - Nếu không, tại sao Haskell không GC'ing nó và chạy ra khỏi không gian địa chỉ/bộ nhớ, và những gì tôi có thể làm gì để ngăn chặn hành vi này?
Cảm ơn!
Bộ nhớ được sử dụng thường gấp đôi số lượng lưu trú tối đa trở lên, tùy thuộc vào phân bổ và mẫu thu thập. Vì vậy, tổng dung lượng 518MB được sử dụng không đáng báo động. Hãy thử nói với GHC rằng chỉ có quá nhiều bộ nhớ để sử dụng, ví dụ '$ ./foo + RTS -M256M', để buộc nó phải thu thập trước đó. Nhưng "cũng không có bất kỳ tài liệu tham khảo nào được giữ lại bên ngoài runST" có thể là không đúng sự thật, bạn thực sự có thể bị rò rỉ. Một trong những sẽ cần phải xem mã nếu đó là trường hợp. Tuy nhiên, –
@DanielFischer 518MB là ~ 4x. Chẳng phải vụ tai nạn ngoài bộ nhớ với vectơ 1GB chỉ ra rằng GHC * không thể * thu thập bộ nhớ? + RTS -M256M không thành công với 'Heap exhausted'. Các vector được tạo ra, đặt bên trong một môi trường Reader, đó là nó. Không có gì khác, không chắc chắn những gì khác tôi có thể làm để tránh rò rỉ bất kỳ tài liệu tham khảo sau khi rời khỏi ST/Reader. Như tôi đã nói, tôi không thể tái tạo vấn đề này trong một chương trình đơn giản hơn. Nó có vẻ khá ngẫu nhiên. – NBFGRTW
Vâng, 4 × có thể xảy ra với mẫu phân bổ đúng/sai. Vụ tai nạn ngoài bộ nhớ có thể chỉ ra rằng GHC không biết nó nên thu thập, nhưng với điều đó '-M256M' gây ra" đống cạn kiệt ", có vẻ như có gì đó liên quan đến con thú. –