使用CUDA和Java分配大的固定内存块

时间:2012-09-12 11:01:57

标签: java memory-management cuda jcuda

我正在用Java编写的程序中实现GPU计算。为此,我正在使用jcuda绑定。 我需要快速主机到设备内存传输,有时,相对较大的数组。如果我想使用流,我必须使用固定内存。问题是如果我想分配大于cca 600 Mbs RAM的主机固定内存,我会得到“CUDA_ERROR_OUT_OF_MEMORY”异常。 这是我用来测试可用固定内存大小的代码:

    public static void main(String[] args) {
    //Init GPU
    JCudaDriver.setExceptionsEnabled(true);

    // Initialize the device and create device context
    cuInit(0);
    CUdevice device = new CUdevice();
    cuDeviceGet(device, 0);
    CUcontext context = new CUcontext();
    cuCtxCreate(context, 0, device);

    Pointer p = new Pointer();

    int Kb = 1024;
    int Mb = 1024 * Kb;
    int Gb = 1024 * Mb;
    int sequenceSize = 172*Mb; // times 4 for float
    float[] expecteds = new float[sequenceSize];
    float[] actuals = new float[sequenceSize];
    Arrays.fill(expecteds, 3.33f);
    int i = 0;
    try {
        JCudaDriver.cuMemAllocHost(p, sequenceSize* Sizeof.FLOAT);
        FloatBuffer fb = p.getByteBuffer(0, sequenceSize* Sizeof.FLOAT).
                order(ByteOrder.nativeOrder()).
                asFloatBuffer();

        fb.position(0);
        fb.put(expecteds);
        fb.position(0);
        fb.get(actuals);
        JCudaDriver.cuMemFreeHost(p);

    } catch (Exception e) {
        e.printStackTrace();
        JCudaDriver.cuMemFreeHost(p);
    }

}

现在,我知道操作系统可以阻止我使用过多固定内存,因为它不可分页。问题是我有48Gb(45Gb免费)的物理内存,我需要一种强制操作系统给我更多的方法。有没有办法做到这一点(如果可能的话,优雅)?

编辑:操作系统是64位Windows 7 Professional SP1

2 个答案:

答案 0 :(得分:1)

检查您是否在64位模式下运行Java。即使使用64位下载,FAQ也会建议default is 32-bit。链接的FAQ还告诉您如何在64位模式下运行,您还需要使用64位DLL等。

@ ArchaeSoftware建议使用cuMemHostRegister() / cuMemHostUnregister()来固定较小的内存部分是一个明智的选择。

答案 1 :(得分:0)

这似乎是一个旧页面,但没有答案.. 我猜你没有正确使用你的RAM,因为默认情况下Java不会为堆分配太多的内存。您可以强制JVM分别使用-Xms和-Xmx的最小和最大内存,并且当您正在使用64位架构时使用" -d64"之后" -Xms"或" -Xmx"