OpenCL memory object 之 Global memory (2)

來源:互聯網
上載者:User

    當我們用clCreateBuffer, clCreateImage建立OpenCL memory object時候,我們需要輸入一個flag參數,這個參數決定memory object的位置。

cl_mem    clCreateBuffer (cl_context context, 
cl_mem_flags flags,
size_t size,
void *host_ptr,
cl_int *errcode_ret) ;

cl_mem clCreateImage2D (cl_context context,
cl_mem_flags flags,
const cl_image_format *image_format,
size_t image_width,
size_t image_height,
size_t image_row_pitch,
void *host_ptr,
cl_int *errcode_ret)

 

     建立memory object後,並沒有立即給它分配空間,而是在第一次device2device之間copy資料時候,才會真正的分配空間,所以我們經常會感覺到,第一次使用某個memory object時候會比較慢。

      在AMD APP 2.5中,根據flag值,memory object分配位置如下表4.3所示:

      注意AMD 擴充flag: CL_MEM_USE_PERSISTENT_MEM_AMD中,把memory object建立在host visible device memory中,這樣實現了zero copy操作。

     我們能夠用函數clEnqueueMapBuffer把device memory object映射到host memory空間,以便cpu進行處理,處理完後,我們要調用clEnqueueUnmapMemObject進行反映射操作,以便device能繼續訪問memory object,注意:在map期間,device不能訪問。

下面我們瞭解一個重要的概念:zero copy memory ojbect以及copy memory object

      memory object位於host memory,或者位於device meory,但是host能夠直接存取,這樣的memory object稱作zero copy memory object,因為資料從來沒有在host和device之間進行過實際傳輸,但host和device都能直接存取它。

      如果memory object在device上,需要在host和device之間進行to and from傳輸操作,這種memory object稱作copy memory object。

 

   

     注意CL_MEM_USE_PERSISTENT_MEM_AMD 和CL_MEM_ALLOC_HOST_PTR的不同之處,前者建立device駐留的zero copy memory,後者建立host駐留的zero copy memory。

    使用zero copy memory時候,clEnqueueMapBuffer/clEnqueueMapImage/clEnqueueUnmapMemObject 操作並不產生實際的傳輸操作,所以速度很快,但是對於同一個zero memory object,每次runtime都會返回不同的指標值。

    當device以sparse(稀疏)方式訪問host memory時,駐留host的zero copy memory object也能提高程式performance,但要注意:此時,傳輸資料的代價一定大於slower的直接存取代價。

   

     host能夠以host<->device資料傳輸頻寬速度對駐留device的zero copy memory進行寫操作(combined write),所以當host不需要讀memory object的時候,我們可以使用zero copy device memory避免資料轉送操作。注意:zero copy device駐留images也是支援的,但zero copy host 駐留images不被支援。linux也不支援zero copy memory object。

 

     對於copy模式的memory object,  一般都位於device momeroy,需要在host和device之間來回傳輸資料。注意:實際上只傳輸memory object被request部分資料,這樣提高傳輸效能。

 

      對於使用預設方式建立的memory object,clEnqueueMapBuffer/clEnqueueMapImage每次返回的指標可能不同,因為runtime每次映射的host memory地區不同,但對於用CL_MEM_USE_HOST_PTR和CL_MEM_ALLOC_HOST_PTR 方式建立的memory object,每次返回的指標是一樣的,因為每次都是返回相同的映射位置,而且對於這兩種方式建立的memory object,每次傳輸前,runtime都要track當前位置是否是最新的memory object,以便決定是否傳輸。[註:預設方式建立的memory object不能被tracker,因為每次位置都不同,所以總要執行傳輸操作]。

     對於用CL_MEM_USE_HOST_PTR建立的memory object,clCreateBuffer/clCreateImage  每次都要對分配的記憶體執行pinned操作,刪除memory object後,還要執行unpinned操作。為了最小化pinned/unpinned的代價,分配的記憶體應該4K對齊,這樣不用每次map/unmap都做pin/unpin操作,但是這樣做確實浪費了一些空間。如果host memory object需要頻繁進行map操作,建議使用CL_MEM_ALLOC_HOST_PTR和CL_MEM_COPY_HOST_PTR,相應的,如果device memory需要頻繁map,使用CL_MEM_USE_PERSISTENT_MEM_AMD以及clEnqueueWriteBuffer。

     註:當用CL_MEM_ALLOC_HOST_PTR和CL_MEM_COPY_HOST_PTR指標建立memory object時候,memory實際上被建立在pinned host memory中,並初始化資料。CL_MEM_COPY_HOST_PTR相比於CL_MEM_ALLOC_HOST_PTR多了一個把初始化後的資料copy到device memory中的操作,並不推薦這樣使用,還是第一次使用時再傳輸效率更高。

     

      images 對象傳輸需要額外的costs,因為images必須線上性地址模式(host使用)和tile地址模式(device使用)之間轉換。

 

      Read/Write/Map memory object的時候,我們要盡量使用non-blocking命令方式,這樣,命令都在緩衝中排隊,通過flush(clFlush)操作,以大批次的方式傳輸到GPU,分攤了runtime準備和提交資料到GPU的開銷。我們能夠用event機制來決定操作之間的依賴關係。目前,runtime還沒有完全挖掘非同步DMA傳輸的潛力,但是我們保持正確的編碼是需要的,一旦dirver提供了支援,我們就能提高程式效能。

聯繫我們

該頁面正文內容均來源於網絡整理,並不代表阿里雲官方的觀點,該頁面所提到的產品和服務也與阿里云無關,如果該頁面內容對您造成了困擾,歡迎寫郵件給我們,收到郵件我們將在5個工作日內處理。

如果您發現本社區中有涉嫌抄襲的內容,歡迎發送郵件至: info-contact@alibabacloud.com 進行舉報並提供相關證據,工作人員會在 5 個工作天內聯絡您,一經查實,本站將立刻刪除涉嫌侵權內容。

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.