2011-07-08 32 views
46

Hiện tại tôi đang thử nghiệm với một máy chủ web Haskell nhỏ được viết bằng Snap để tải và cung cấp cho khách hàng nhiều dữ liệu. Và tôi có một thời gian rất, rất khó kiểm soát quá trình máy chủ. Tại những thời điểm ngẫu nhiên, quá trình sử dụng rất nhiều CPU trong vài giây đến vài phút và trở nên vô trách nhiệm đối với các yêu cầu của khách hàng. Đôi khi sử dụng bộ nhớ tăng đột biến (và đôi khi giảm) hàng trăm megabyte trong vài giây.Làm thế nào để có được quyền kiểm soát của một đống 5GB trong Haskell?

Hy vọng rằng ai đó có nhiều kinh nghiệm hơn với các quy trình Haskell chạy dài sử dụng nhiều bộ nhớ và có thể cho tôi một số gợi ý để làm cho mọi thứ ổn định hơn. Tôi đã gỡ lỗi điều này trong nhiều ngày và tôi bắt đầu có một chút tuyệt vọng ở đây.

Một cái nhìn tổng quan nhỏ của thiết lập của tôi:

  • On khởi động máy chủ tôi đọc khoảng 5 GB dữ liệu vào một (lồng) cấu trúc Data.Map-giống nhau lớn trong bộ nhớ. Bản đồ lồng nhau là giá trị nghiêm ngặt và tất cả các giá trị bên trong bản đồ là các kiểu dữ liệu với tất cả các trường của chúng được thực hiện nghiêm ngặt. Tôi đã dành rất nhiều thời gian để đảm bảo không có những khối không được đánh giá. Việc nhập (tùy thuộc vào tải hệ thống của tôi) mất khoảng 5-30 phút. Điều kỳ lạ là sự biến động trong các lần chạy liên tiếp là lớn hơn tôi mong đợi, nhưng đó là một vấn đề khác.

  • Cấu trúc dữ liệu lớn tồn tại bên trong 'TVar' được chia sẻ bởi tất cả các luồng máy khách được tạo bởi máy chủ Snap. Khách hàng có thể yêu cầu các phần tùy ý của dữ liệu bằng cách sử dụng một ngôn ngữ truy vấn nhỏ. Lượng yêu cầu dữ liệu thường nhỏ (tối đa 300kb hoặc hơn) và chỉ chạm vào một phần nhỏ của cấu trúc dữ liệu. Tất cả các yêu cầu chỉ đọc được thực hiện bằng cách sử dụng 'readTVarIO', vì vậy chúng không yêu cầu bất kỳ giao dịch STM nào.

  • Máy chủ được bắt đầu bằng các cờ sau: + RTS -N -I0 -qg -qb. Điều này khởi động máy chủ ở chế độ đa luồng, vô hiệu hóa thời gian nhàn rỗi và GC song song. Điều này dường như đẩy nhanh quá trình.

Máy chủ chủ yếu chạy mà không gặp bất kỳ sự cố nào. Tuy nhiên, hiện tại, mọi yêu cầu của khách hàng đều hết thời gian chờ và CPU tăng lên 100% (hoặc thậm chí trên 100%) và tiếp tục thực hiện việc này trong một thời gian dài. Trong khi đó máy chủ không trả lời yêu cầu nữa.

Có vài lý do tôi có thể nghĩ rằng có thể gây ra việc sử dụng CPU:

  • Yêu cầu chỉ mất rất nhiều thời gian vì có rất nhiều công việc phải làm. Điều này là hơi khó xảy ra bởi vì đôi khi nó xảy ra cho các yêu cầu đã được chứng minh là rất nhanh trong các lần chạy trước đó (với tốc độ nhanh, tôi có nghĩa là 20-80ms hoặc hơn).

  • Vẫn còn một số khối không được đánh giá cần phải được tính trước khi dữ liệu có thể được xử lý và gửi cho khách hàng. Điều này cũng không chắc chắn, với lý do tương tự như điểm trước đó.

  • Làm cách nào đó thu thập rác thải vào và bắt đầu quét toàn bộ vùng 5 GB của tôi. Tôi có thể tưởng tượng điều này có thể mất rất nhiều thời gian.

Vấn đề là tôi không biết làm cách nào để tìm hiểu chính xác những gì đang diễn ra và phải làm gì. Bởi vì quá trình nhập mất quá nhiều thời gian nên không hiển thị cho tôi bất kỳ điều gì hữu ích. Dường như không có cách nào để bật và tắt điều kiện từ profiler trong mã.

Cá nhân tôi nghi ngờ GC là vấn đề ở đây.Tôi đang sử dụng GHC7 mà dường như có rất nhiều tùy chọn để tinh chỉnh cách thức hoạt động của GC.

Bạn khuyên bạn nên sử dụng cài đặt GC nào khi sử dụng đống lớn với dữ liệu chung rất ổn định?

+1

Hmmm .. thú vị .. bao nhiêu RAM hộp có trên đó bạn đang chạy ứng dụng máy chủ này – Ankur

+0

Có tổng cộng 8GB RAM trên máy của tôi. Điều đó là đủ. –

+0

Vâng .. có vẻ như là đủ để tránh lỗi trang – Ankur

Trả lời

29

Việc sử dụng bộ nhớ lớn và đột biến CPU gần như chắc chắn là GC khởi động. Bạn có thể xem liệu đây có phải là trường hợp hay không bằng cách sử dụng các tùy chọn RTS như -B, khiến GHC phát ra tiếng bíp bất cứ khi nào có một bộ sưu tập lớn, -t cho bạn biết số liệu thống kê sau khi thực tế (đặc biệt, xem liệu thời gian GC có thực sự dài) hay -Dg, bật thông tin gỡ lỗi cho cuộc gọi GC (mặc dù bạn cần biên dịch với -debug).

Có một vài điều bạn có thể làm để giảm bớt vấn đề này:

  • Về nhập khẩu ban đầu của dữ liệu, GHC đang lãng phí rất nhiều thời gian phát triển các heap. Bạn có thể yêu cầu nó lấy tất cả bộ nhớ bạn cần cùng một lúc bằng cách chỉ định một -H lớn.

  • Một đống lớn với dữ liệu ổn định sẽ được thăng cấp lên thế hệ cũ. Nếu bạn tăng số lượng thế hệ với -G, bạn có thể có được dữ liệu ổn định ở trong thế hệ lâu đời nhất, rất hiếm khi GC, trong khi bạn có nhiều heap cũ và trẻ hơn ở trên nó.

  • Tùy thuộc vào mức sử dụng bộ nhớ của phần còn lại của ứng dụng, bạn có thể sử dụng -F để tinh chỉnh số lượng GHC sẽ cho phép thế hệ cũ phát triển trước khi thu thập lại. Bạn có thể tinh chỉnh tham số này để thực hiện việc thu gom rác chưa được thu thập này.

  • Nếu không có bản ghi, và bạn có giao diện được xác định rõ, có thể đáng giá khiến bộ nhớ này không được quản lý bởi GHC (sử dụng C FFI) sao cho không có cơ hội cho siêu hệ thống .

Đây là tất cả những suy đoán, vì vậy hãy kiểm tra với ứng dụng cụ thể của bạn.

+5

Sử dụng GC nén cũng có thể hữu ích. –

+0

Tôi chưa thử nghiệm kỹ lưỡng, nhưng tăng số lượng thế hệ dường như có tác động tích cực. –

2

Tôi gặp sự cố rất giống với một bản đồ lồng nhau 1.5GB. Với GC nhàn rỗi theo mặc định tôi sẽ nhận được 3-4 giây đóng băng trên mỗi GC, và với GC nhàn rỗi tắt (+ RTS -I0), tôi sẽ nhận được 17 giây đóng băng sau một vài trăm truy vấn, gây ra một thời gian khách hàng -ngoài.

"Giải pháp" của tôi trước hết là tăng thời gian chờ của khách hàng và yêu cầu mọi người chịu đựng điều đó trong khi 98% truy vấn khoảng 500ms, khoảng 2% truy vấn sẽ bị chậm. Tuy nhiên, muốn có một giải pháp tốt hơn, tôi đã kết thúc chạy hai máy chủ cân bằng tải và đưa chúng ra khỏi cụm để thực hiện mỗi truy vấn 200, sau đó quay lại hoạt động.

Thêm xúc phạm vào thương tích, đây là một chương trình viết lại chương trình Python gốc, không bao giờ có vấn đề như vậy. Trong sự công bằng, chúng tôi đã có được khoảng 40% hiệu suất tăng, song song dễ dàng chết và một codebase ổn định hơn. Nhưng vấn đề GC khắt khe này ...

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