为什么使用1.5mb网络进行预测时,Torch为什么要使用约700mb GPU内存

时间:2019-04-11 15:52:08

标签: lua out-of-memory torch

我对Torch / CUDA非常陌生,我正在尝试从https://github.com/1adrianb/binary-face-alignment测试小型二进制网络(〜1.5mb),但是我一直遇到“内存不足”的问题。

我在具有CUDA 10.0和CudNN 5.1版的16.04 Ubuntu上使用相对较弱的GPU(NVIDIA Quadro K600),具有约900Mb的图形内存。因此,我并不真正在意性能,但我认为我至少能够运行一个小型网络进行预测,一次只能生成一张图像(尤其是应该针对“资源有限”的图像)。

我设法以无头模式运行代码,并检查内存消耗为700Mb左右,这可以解释为什么当我运行的X服务器占用大约250Mb GPU内存时,它立即失败。

我还添加了一些日志,以了解我沿 main.lua 走了多远,这是第一张内存不足的图像上的调用output:copy(model:forward(img))

作为参考,这是直到崩溃的main.lua代码:

    require 'torch'
    require 'nn'
    require 'cudnn'
    require 'paths'

    require 'bnn'
    require 'optim'

    require 'gnuplot'
    require 'image'
    require 'xlua'
    local utils = require 'utils'
    local opts = require('opts')(arg)

    print("Starting heap tracking")
    torch.setheaptracking(true)

    torch.setdefaulttensortype('torch.FloatTensor')
    torch.setnumthreads(1)
    -- torch.

    local model
    if opts.dataset == 'AFLWPIFA' then
        print('Not available for the moment. Support will be added soon')
        os.exit()
        model = torch.load('models/facealignment_binary_pifa.t7')
    else
        print("Loading model")
        model = torch.load('models/facealignment_binary_aflw.t7')
    end
    model:evaluate()

    local fileLists = utils.getFileList(opts)
    local predictions = {}
    local noPoints = 68
    if opts.dataset == 'AFLWPIFA' then noPoints = 34; end
    local output = torch.CudaTensor(1,noPoints,64,64)
    for i = 1, #fileLists do

        local img = image.load(fileLists[i].image)
        local originalSize = img:size()

        img = utils.crop(img, fileLists[i].center, fileLists[i].scale, 256)
        img = img:cuda():view(1,3,256,256)
        output:copy(model:forward(img))

所以我有两个主要问题:

  1. 有哪些工具可以调试割炬中的内存使用情况?
  2. 这种记忆膨胀的可能原因是什么?

它必须不仅仅是网络和加载到GPU中的图像。我最好的猜测是它与LoadFileLists函数有关,但是我根本不了解火炬或lua是否足以使它走得更远。其他答案表明,确实不支持显示变量占用了多少内存。

1 个答案:

答案 0 :(得分:1)

通常消耗大部分内存的是激活图(以及训练时的渐变)。我不熟悉这种特定的模型和实现,但是我想说的是您使用的是“伪”二进制网络。通过 fake 我的意思是他们仍然使用浮点数来表示二进制值,因为大多数用户将在不完全支持真实二进制操作的GPU上使用其代码。作者甚至在第5节中写道:

  

性能。理论上,通过将所有浮点乘法替换为按位XOR并利用SWAR(单   指令,寄存器中的多个数据)[5],[6],   与相比,操作最多可减少32倍   基于乘法的卷积。但是,在我们的测试中,我们观察到   加速高达   与cuBLAS相比,矩阵乘法的结果是3.5倍,其结果与[6]中报道的一致。我们注意到我们   没有在CPU上进行实验。但是,鉴于我们   使用与[5]中相同的二值化方法,进行了类似的改进   在速度方面,预计将达到58倍:   实值网络需要0.67秒才能进行正向传递   i7-3820使用单核,接近x58的加速比将使   系统实时运行。在内存压缩方面,   消除影响最小(或完全没有影响)的偏见   性能,并且将每32个权重分组并存储在一个   变量,相比之下,我们可以达到39倍的压缩率   相对于Torch的单精度对手。

在这种情况下,较小的模型(在MiB中有大量参数或模型大小)并不一定意味着内存占用少。可能所有这些内存都用于以单精度或双精度存储激活图。