如何在Win32 API中清除/刷新DNS缓存

7

我正在寻找一种程序化清除/刷新本地win32 DNS缓存的方法(相当于调用“ipconfig /flushdns”)。

以前可以通过winsock.dll中的隐藏API来实现,但是winsock.dll不再是Windows的一部分,因此这种方法将不再起作用。

有人知道现在应该如何做吗?


看起来你可能可以使用这个API:https://learn.microsoft.com/en-us/windows/desktop/api/_dns/ - NathanOliver
1个回答

10
  • 使用Dependency Walker检查ipconfig.exe的依赖项
  • 在其中找到了dnsapi.dll
  • 检查其导出函数,并找到DnsFlushResolverCache
  • 浅显地浏览了网络,并找到了其签名(只在官方网站上找到了这样的引用:[MS.Docs]: Windows 8 API Sets),这意味着它不是公共的,所以依赖于它的软件不够健壮
  • 创建了一个小测试程序

main00.c:

#include <stdio.h>
#include <Windows.h>

typedef BOOL (WINAPI *DnsFlushResolverCacheFuncPtr)();


int main() {
    HMODULE dnsapi = LoadLibrary("dnsapi.dll");
    if (dnsapi == NULL) {
        printf("Failed loading module: %d\n", GetLastError());
        return -1;
    }
    DnsFlushResolverCacheFuncPtr DnsFlushResolverCache = (DnsFlushResolverCacheFuncPtr)GetProcAddress(dnsapi, "DnsFlushResolverCache");
    if (DnsFlushResolverCache == NULL) {
        printf("Failed loading function: %d\n", GetLastError());
        FreeLibrary(dnsapi);
        return -2;
    }
    BOOL result = DnsFlushResolverCache();
    if (result) {
        printf("DnsFlushResolverCache succeeded\n");
    } else {
        printf("DnsFlushResolverCache succeeded: %d\n", GetLastError());
    }
    FreeLibrary(dnsapi);
    return 0;
}
e:\Work\Dev\StackOverflow\q052007372>"c:\Install\x86\Microsoft\Visual Studio Community\2015\vc\vcvarsall.bat" x64

e:\Work\Dev\StackOverflow\q052007372>dir /b
dnsapi_func_list.txt
main00.c

e:\Work\Dev\StackOverflow\q052007372>cl /nologo main00.c  /link /OUT:main00.exe
main00.c

e:\Work\Dev\StackOverflow\q052007372>dir /b
dnsapi_func_list.txt
main00.c
main00.exe
main00.obj

e:\Work\Dev\StackOverflow\q052007372>main00.exe
DnsFlushResolverCache succeeded
注意: 即使函数调用成功完成,我也不确定如何检查它是否做了它应该做的事情(或更好地说:它的名称所暗示的应该做的事情,这似乎是你需要的)。请让我知道它是如何运作的。

更新#0

感谢@TimJohnson提供的信息!我太匆忙了,没有看ipconfig /?[MS.Docs]: ipconfig)输出(我在另一个 cmd 窗口中 :d ),并注意到选项 :) 。 它确实有效(缓存已经大量更新,我可以在运行程序之前和之后看到差异)!!!


1
谢谢,非常完美,干得好。你可以使用命令“ipconfig /displaydns”检查解析器缓存。它将列出缓存中的内容,当然在此之后应该是空的。(对我来说也是如此) - Tim Johnson

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接