调用约定- Lua异形返回多个值



我有这个函数,我想返回多个值,但我不知道如何实现这个

function GetDiskSpace(_disk)
    require("alien")
    local kernel32 = alien.load("kernel32.dll")
    kernel32.GetDiskFreeSpaceExA:types("int", "pointer", "int", "int", "int")
    if kernel32.GetDiskFreeSpaceExA(_disk, _avail_space, _disk_space, _free_space) ~= 0 then
            return _avail_space, _disk_space, _free_space
            --[[or like this return kernel32.GetDiskFreeSpaceExA(_disk, _avail_space, _disk_space, _free_space)
            GetDiskFreeSpaceExA should retun non zero if function ran properly, 
            and should retun additional values if those are given 
            (btw values are __int64 i'm not sure if I specified them correct, maybe
            I should set them as "long" instead of "int")
            either way it return only function value and nil's.
            --]]
    else
            print("GetDiskSpace returned error.")
    end
end
hdd_a, hdd_b, hdd_c = GetDiskSpace("C:\")

由于几个原因,您给出的类型规格是错误的。第一个参数的类型是"string"而不是"pointer"。对于int的引用(或指针),您必须编写"ref int"而不仅仅是"int"。您还必须将ABI指定为"stdcall"

当使用"ref int"参数调用函数时,您传递一个虚拟的0值,但获得一个额外的返回值,因此这里GetDiskFreeSpaceExA有效地返回4个结果。

您担心结果的uint64_t值类型是正确的。据我所知,Alien 不支持64位整数,所以下面的代码只返回磁盘空间的低32位:

function GetDiskSpace(_disk)
    require("alien")
    local kernel32 = alien.load("kernel32.dll")
    kernel32.GetDiskFreeSpaceExA:types { ret="int", abi="stdcall", 
        "string", "ref int", "ref int", "ref int" }
    local ok, _avail_space, _disk_space, _free_space = 
        kernel32.GetDiskFreeSpaceExA(_disk, 0, 0, 0)
    assert(ok == 1, "GetDiskSpace returned error.")
    return _avail_space, _disk_space, _free_space
end
hdd_a, hdd_b, hdd_c = GetDiskSpace("C:\")

要纠正这个问题,您可以通过修改Alien的源代码并重新构建它来添加对64位整数的支持。

最新更新