2010-11-04 13 views
5

Tôi đã xem qua hướng dẫn lập trình và hướng dẫn thực hành tốt nhất và nó đề cập rằng truy cập bộ nhớ toàn cầu mất 400-600 chu kỳ. Tôi không thấy nhiều về các loại bộ nhớ khác như bộ nhớ cache kết cấu, bộ nhớ cache không đổi, bộ nhớ dùng chung. Các thanh ghi có độ trễ bộ nhớ là 0.Có bao nhiêu chu kỳ trễ bộ nhớ trên mỗi loại truy cập bộ nhớ trong OpenCL/CUDA?

Tôi nghĩ bộ nhớ cache liên tục giống như sổ đăng ký nếu tất cả các chủ đề sử dụng cùng một địa chỉ trong bộ đệm không đổi. Trường hợp xấu nhất tôi không chắc lắm.

Bộ nhớ dùng chung giống với sổ đăng ký miễn là không có xung đột ngân hàng? Nếu có thì độ trễ được mở ra như thế nào?

Còn cache kết cấu thì sao?

Trả lời

4

Độ trễ cho các ký ức chia sẻ/không đổi/kết cấu nhỏ và phụ thuộc vào thiết bị bạn có. Nói chung, mặc dù GPU được thiết kế như một kiến ​​trúc thông lượng có nghĩa là bằng cách tạo đủ luồng, độ trễ cho các ký ức, bao gồm bộ nhớ toàn cục, bị ẩn.

Lý do các hướng dẫn nói về độ trễ cho bộ nhớ toàn cầu là độ trễ là các đơn hàng có cường độ cao hơn các ký ức khác, có nghĩa là độ trễ vượt trội được xem xét để tối ưu hóa.

Bạn đã đề cập đến bộ nhớ cache liên tục nói riêng. Bạn hoàn toàn chính xác rằng nếu tất cả các chủ đề trong một warp (tức là nhóm 32 chủ đề) truy cập cùng một địa chỉ thì không có hình phạt, tức là giá trị được đọc từ bộ đệm và phát tới tất cả các chuỗi cùng một lúc. Tuy nhiên, nếu chuỗi truy cập các địa chỉ khác nhau thì quyền truy cập phải serialize vì bộ nhớ cache chỉ có thể cung cấp một giá trị tại một thời điểm. Nếu bạn đang sử dụng CUDA Profiler, thì điều này sẽ hiển thị dưới bộ đếm tuần tự hóa.

Bộ nhớ dùng chung, không giống như bộ nhớ cache không đổi, có thể cung cấp băng thông cao hơn nhiều. Hãy xem cuộc hội thoại CUDA Optimization để biết thêm chi tiết và giải thích về xung đột ngân hàng và tác động của chúng.

+0

Nó vẫn có giá trị sử dụng bộ đệm không đổi nếu ví dụ, tất cả các chuỗi truy cập 1000 nổi? Điều đó có giống như 1000 lần đọc từ một thanh ghi không? Các hướng dẫn cho biết việc sử dụng bộ nhớ cache liên tục theo cách này quy mô tuyến tính phải không? – smuggledPancakes

+0

Nếu tất cả các chủ đề truy cập vào giá trị * cùng * trong bất kỳ lần lặp nào đã cho của một vòng lặp thì bạn có thể sử dụng bộ đệm không đổi. Bộ đệm không đổi sẽ cung cấp một số lợi ích do không gian địa phương (trên bộ nhớ cache Fermi L1 có thể đạt được điều tương tự nhưng điều này để lại L1 miễn phí cho các dữ liệu khác). Có nói rằng, tôi nhắm mục tiêu Fermi chủ yếu và không bao giờ sử dụng '__constant__', tôi chỉ sử dụng const rất nhiều và để cho trình biên dịch con số nó ra! Ví dụ trong trường hợp của bạn, tôi sẽ chuyển kernel arg như 'const float * const myfloatarray'. Tôi sẽ khuyên bạn nên luôn luôn chạy Visual Profiler để kiểm tra serialization chỉ trong trường hợp bạn bị mất một cái gì đó. – Tom

+0

Người ta có thể thêm, các dòng bộ nhớ cache là 128byte (32byte) cho L1 (L2), vì vậy chúng ta đang nói về các địa chỉ rơi vào cùng một dòng (không nhất thiết cùng địa chỉ). Có thể tìm thấy một số số trên các độ trễ khác [ở đây] (http://stackoverflow.com/questions/6744101/fermi-l2-cache-hit-latency). –

6

Đối với (Kepler) Tesla K20 latencies như sau:

bộ nhớ toàn cầu: 440 đồng hồ
bộ nhớ liên tục
        L1: 48 đồng hồ
        L2: 120 đồng hồ
Bộ nhớ dùng chung: 48 đồng hồ
Bộ nhớ kết cấu
        L1: 108 đồng hồ
        L2: 240 đồng hồ

Làm sao tôi biết? Tôi đã chạy các dấu hiệu vi mô được mô tả bởi các tác giả của Demystifying GPU Microarchitecture through Microbenchmarking. Chúng cung cấp kết quả tương tự cho GTX 280 cũ hơn.

Điều này được đo trên một cụm Linux, nút tính toán mà tôi đang chạy các điểm chuẩn không được sử dụng bởi bất kỳ người dùng nào khác hoặc chạy bất kỳ quy trình nào khác. Đó là BULLX Linux với một cặp 8 Xeon lõi và 64 GB RAM, nvcc 6.5.12. Tôi đã thay đổi sm_20 thành sm_35 để biên soạn.

Ngoài ra còn có một chương operands cost trong PTX ISA mặc dù nó không phải là rất hữu ích, nó chỉ nhắc lại những gì bạn đã mong đợi, mà không đưa ra con số chính xác.

+0

Tôi cũng đang sử dụng Tesla K20 và tôi đã cố chạy cùng một microbenchmark mà bạn đã đề cập. Bạn có thể chạy 'global.cu' không có vấn đề gì không? Tôi hỏi vì tôi đang đối mặt với vấn đề truy cập bộ nhớ bất hợp pháp - tôi đã đăng câu hỏi này [ở đây] (http://stackoverflow.com/questions/36416843/how-to-write-a-pointer-chasing-benchmark-using- 64-bit-pointers-in-cuda). Tôi đã tự hỏi nếu bạn thực hiện bất kỳ thay đổi mã hạt nhân để làm cho nó làm việc cho bạn? – Kajal

+0

@ kv.333 Đã lâu rồi. Tôi nhớ có một số vấn đề và không phải tất cả các điểm chuẩn đều chạy. Tôi không nhớ cái nào mặc dù. –