Vietnamen’s Weblog

Time, Chances, Diligence, Intelligence: which is the most important?

Phần 6: Fortran + CUDA (2) variables

leave a comment »

Variables

Như ta đã đề cập, CUDA có nhiều cấp độ bộ nhớ, vì thế, việc chọn lựa nơi lưu trữ cũng rất quan trọng tới hiệu năng của chương trình.

  1. register (thanh ghi): (read/write) per-thread
  2. local memory: (read/write) per-thread
  3. shared memory (read/write) per block
  4. global memory (read/write) per grid
  5. constant memory (read-only) per grid
  6. texture memory (read-only) per grid

Mặc định, khi khai báo biến ở host subprogram/modules, dữ liệu được lưu trữ  ở host global memory.

Tối đa 1 trong các thuộc tính sau được khai báo với biến: device, constant, shared, pinned

Device

REAL, DEVICE :: dev_var, x(100)

real :: y
attributes(device) :: y

Một device variable có dữ liệu được lưu ở device global memory. Nó có thể được khai báo ở host subprogram hoặc device subprogram.

Nếu khai báo trong module, nó có thể được truy cập bởi mọi device subprogram trong module đó, và mọi host subproram trong module đó hoặc là subprogram có sử dụng module

Nếu khai báo trong 1 host subprogram, thì nó có thể được truy xuất từ chính subprgram đó, hoặc các subprogram chứa trong (contains) nó.

Device variables (arrays) không thể

  • có các thuộc tính POINTER, TARGET, ALLOCATABLE.
  • xuất hiện trong COMMON block
  • xuất hiện trong EQUIVALENCE statement
  • là thành viên của một kiểu mới (derived data type)

Biến hằng có thể làm đối số (actual arguments) cho một host subprogram hoặc device subprogram, với điều kiện INTERFACE tường minh, và đối số lúc định nghĩa (dummy arguments) tương ứng cũng có thuộc tính DEVICE.

Nếu là kiểu mảng (array) nó có thể là explicit-shape array, allocatable device variable, hoặc (nếu ở trong host subprogram) assumed-shaped dummy array.

Constant

Có 2 cách khai báo

real :: c(100)
attributes(constant) :: c

hoặc

real, constant :: d(100)

Dữ liệu hằng không thể

  • có các thuộc tính POINTER, TARGET, ALLOCATABLE.
  • xuất hiện trong COMMON block
  • EQUIVALENCE statement
  • là thành viên của một kiểu mới (derived data type)

Mảng (array) là hằng thì phải có kích thước cố định.

Biến hằng có thể làm đối số (actual arguments) cho một host subprogram hoặc device subprogram, với điều kiện INTERFACE tường minh, và đối số lúc định nghĩa (dummy arguments) tương ứng cũng có thuộc tính CONSTANT.

Dữ liệu hằng:

  • không thể thay đổi nếu định ra trong device subprogram
  • có thể thay đổi nội dung, nếu định ra trong host subprogram

Shared

Biến chia sẻ chỉ có thể lưu dữ liệu trên shared memory space. Vì thế, nó chỉ được khai báo trong device subprogram, và cũng chỉ có thể được truy xuất từ chính device subprogram đó, hoặc các device subprogram khác mà bản thân biến này được truyền tới dưới dạng đối số (actual argument)

có thể bị đọc/ghi từ mọi threads trong block. CHÚ Ý: khi một thread cập nhật dữ liệu lên 1 shared variable, để đảm bảo là khi thread khác đọc sẽ đọc dữ liệu mới này, ta cần đồng bộ sau khi cập nhật dữ liệu, dùng SYNCTHREADS() intrinsic function.

Dữ liệu chia sẻ không thể

  • có các thuộc tính POINTER, TARGET, ALLOCATABLE.
  • xuất hiện trong COMMON block
  • EQUIVALENCE statement
  • là thành viên của một kiểu mới (derived data type)

Mảng (array) là SHARED thì có thể dùng asumed-sized array nếu nó không  phải được khai báo là 1 dummy argument của 1 device subprogram. Vậy kích thước là bao nhiêu? điều này sẽ được qui định khi gọi kernel dùng chevron syntax với đối số thứ 3 (bytes) chỉ định số bytes ở shared memory dành cho assumed-sized array. Nếu có nhiều hơn một assumed-size array làm đối số, chúng sẽ được ngầm định là tương đương nhau, i.e. cùng bắt đầu ở cùng địa chỉ ô nhớ. Vì thế, nếu dùng nhiều hơn 1 assumed-sized array, nhà lập trình cần quản lí nó.

attributes(global) subroutine sub(y)
   real, shared :: x(4, *)
   integer :: y 
   ...
end subroutine

Nếu mảng (array) là SHARED và không phải là dummy argument + không phải assumed-sized array, thì nó phải là fixed-sized array.

Biến chia sẻ có thể làm đối số (actual arguments) cho một host subprogram hoặc device subprogram, với điều kiện INTERFACE tường minh, và đối số lúc định nghĩa (dummy arguments) tương ứng cũng có thuộc tính SHARED.

Pinned

Chỉ dành để khai báo với biến thuộc kiểu allocatable array và khai báo trong module/host subprogram.

real, allocatable, dimension(:), pinned :: x

Khi cấp phát, dữ liệu được lưu ở host page-locked memory. Ưu điểm là dữ liệu lưu ở đây sẽ được copy tới device memory nhanh hơn so với từ host normal-paged memory tới device memory. Vì giới hạn về bộ nhớ dành cho host page-locked memory là tùy hệ thống, dữ liệu không đảm bảo lưu trữ ở đây nếu vượt quá kích thước cho phép, lúc đó nó sẽ tự động lưu vào host normal-paged memory.

Pinned array có thể dùng làm đối số cho host subprogram dù INTERFACE của nó có được khai báo hay không, cũng như không phụ thuộc vào dummy argument có được khai báo là PINNED hay ALLOCATABLE hay không. Tuy nhiên, nếu giải phóng nó (deallocate) bên trong subprogram, thì dummy argument phải có khai báo là PINNED, nếu không sẽ có lỗi.

Tham khảo:

  1. CUDA Fortran programming guide and reference

Written by vietnamen

Tháng Mười 8, 2009 lúc 11:21 sáng

Bình luận về bài viết này