2011-08-03 15 views
4

私は、さまざまなポリシーに基づいてメモリを割り当てるためのさまざまな手段を提供するカスタムアロケータをいくつか持っています。そのうちの1人は、定義されたNUMAノードにメモリを割り当てます。アロケータへのインタフェースは、ストレートフォワードであるHWLOCを使用するNUMAシステム用のrealloc()

template<typename config> 
class NumaNodeStrategy 
{ 

public: 

    static void *allocate(const size_t sz){} 

    static void *reallocate(void *old, size_t sz, size_t old_sz){} 

    static void deallocate(void *p, size_t sz){} 
}; 

割り当て自体が割り当てポリシー等Howver、hwlocのみ割り当てとfree'ingメモリおよびIのための方法を提供するために設定によるパラメータでhwloc_alloc_membind_nodeset()方法を用いて処理されreallocate()をどのように実装すればよいか不思議に思っていました。

2つの解決策:

  1. ノードセットのメモリ割り当て/バインディングポリシーを設定し、無地malloc()/posix_memalign()realloc()を使用するために、データ
  2. 使用hwloc_set_membind_nodeset()を新しいメモリ領域を確保してmemcpy()

誰でもこの権利を得るのを助けることができますか?

更新:

私は質問をより具体的にするために試してみてください。新しいメモリを割り当て、周りにページを移動せずにhwlocを使用してrealloc()を実行する可能性はありますか?

+0

libnumaを直接使うのはどうですか? http://linux.die.net/man/3/numa – osgx

+0

'libnuma'は間違った結果を出すかもしれないので(numaノードの間違ったcpuバインディングを表示するなど)、代わりに' hwloc'を使うことを望んでいました。 https://gist.github.com/1125022 – grundprinzip

+0

Hmm ..メモリバインディングの設定はノード固有ですか?したがって、ノード5が所有するメモリ上のreallocを呼び出した場合、libcのreallocは同じノードのメモリ割り当てを行いますか? – osgx

答えて

1

hwloc_set_area_membind_nodesetはやっていますか?

HWLOC_DECLSPEC int  
    hwloc_set_area_membind_nodeset (hwloc_topology_t topology, 
    const void *addr, size_t len, hwloc_const_nodeset_t nodeset, 
    hwloc_membind_policy_t policy, int flags) 

バインドノードセット内のNUMAノード(単数または複数)に(ADDR、LEN)によって識別既に割り当てられたメモリ。

戻り値:

  • -1結合がオン

を強制することができない場合、アクションがEXDEVに設定errnoに

  • -1にサポートされていない場合ENOSYSに設定errnoにlinuxでは、この呼び出しはmbindで実装されています。領域内のページに触れていない場合にのみ機能しますので、2番目の解決策でメモリ領域を移動するのが正しい方法です。 UPDATEタッチされたデータを移動するためのMPOL_MF_MOVE *フラグがあります。

    私が知っているREALLOCATE-とコピーせずにページを移動するための唯一のシステムコールはmove_pages

    move_pagesが異なるNUMAノードに実行されるプロセスのアドレス空間内のページのセットを移動しています。

  • +0

    'hwloc_set_area_membind_nodeset'は' libnuma'の 'numa_realloc()'のようなものを探している間に、割り当てられたメモリを別のノードに移動することしか許しません。 – grundprinzip

    1

    あなたは間違っています。 mbindは、タッチされたページを移動することができます。 MPOL_MF_MOVEを追加するだけです。フラグHWLOC_MEMBIND_MIGRATEを追加すると、それはhwloc_set_area_membind_nodeset()になります。

    move_pagesは、別の場所に独立したページを移動できるため、柔軟性は向上しますが、速度は少し遅くなります。 MPOL_MF_MOVEのmbindとmove_pages(およびmigrate_pages)の両方は、入力がページのリストに変換されるとmm/migrate.cで全く同じmigrate_pages()関数を使用して終了します。

    +0

    したがって、grundprinzipは通常のreallocを行い、 'HWLOC_MEMBIND_MIGRATE'で' hwloc_set_area_membind_nodeset() 'を呼び出すことができますか? – osgx

    +1

    はい。 また、hwloc_alloc_membind_nodeset()を実行して、新しいバッファを右側のメモリノードに割り当て、次にmemcpyを古いバッファから新しいバッファに手動で割り当て、古いバッファを解放することもできます。いずれにせよ、ある時点でコピーしなければならないので、最終バッファーをバインドした後にコピーするほうがよいです。 – Brice

    +0

    私はページを移行することは可能ですが、質問に記載されているように、同じノード上の割り当てられたメモリ領域を増やしてコピーを避けたいと思います。 – grundprinzip

    2

    編集に返信する: hwlocには再割り当てがありません。現在、追加する計画はありません。 (Cの関数のプロトタイプ)を気付いたら、https://svn.open-mpi.org/trac/hwloc

    に返信してください。ogsxに返信するには:メモリバインディングは具体的ではなく、特定。 reallocすると、libcは特別なことをしません。 1)同じページ内で再割り当てできる場合は、同じノードにメモリが割り当てられます。良いですが、まれに、特に大きなバッファの場合はまれです。 2)別のページ(大容量のバッファの大半の場合)で再割り当てされた場合、対応するページが過去のmallocライブラリによって物理メモリにすでに割り当てられているかどうかによって異なります(mallocされ、物理メモリにまだ割り当てられています) 2.a)仮想ページが割り当てられている場合、過去にさまざまな理由で別のノードに割り当てられている可能性があります。 2.b)新しい仮想ページがまだ割り当てられていない場合、デフォルトでは現在のノードに割り当てられます。以前にset_area_membind()またはmbind()を使ってバインディングを指定した場合、そのノードは正しいノードに割り当てられます。あなたはこの場合幸せになるかもしれません。

    要するに、それは多くのことに依存します。複雑な/隠された内部的なことをしているmallocライブラリを気にしたくない場合、特にバッファが大きい場合、mallocの代わりにmmap(MAP_ANONYMOUS)を実行するのは、本当に必要なときにページが確保されることを確認する簡単な方法ですそれら。そして、あなたはreallocに似た何かをするためのmremapを持っています。

    のallocはMMAP(長さ)となり+ set_area_membind のreallocは(全体mremap'edバッファ上)はmremap + set_area_membindなり

    はそれを使用していないが、面白そうだん。

    関連する問題