枚举所有句柄的方法

由于windows并没有给出枚举所有句柄所用到的API,和进程所拥有的句柄相关的只有GetProcessHandleCount这个函数,然而这个函数只能获取到和进程相关的句柄数,不能获取到实际的句柄,要获得句柄,我们必须使用未公开的Native API才可以。
 
PS:网上有很多关于这类的方法,但几乎都是抄来抄去,很多连编译都过不了就直接放上去了(囧)。我整理了一下方法,实测在win10和win7都可以用。
NTSTATUS WINAPI NtQuerySystemInformation(
_In_ SYSTEM_INFORMATION_CLASS SystemInformationClass,
_Inout_ PVOID SystemInformation,
_In_ ULONG SystemInformationLength,
_Out_opt_ PULONG ReturnLength
);
枚举的关键是使用NtQuerySystemInformation(旧版本是ZwQuerySystemInformation)这个方法
 
但MSDN上并没有把这个函数的第一个参数的枚举值给全,而且Windows API所定义的枚举值也是MSDN上面列的几个而已,如下:
typedef enum _SYSTEM_INFORMATION_CLASS {
SystemBasicInformation = ,
SystemPerformanceInformation = ,
SystemTimeOfDayInformation = ,
SystemProcessInformation = ,
SystemProcessorPerformanceInformation = ,
SystemInterruptInformation = ,
SystemExceptionInformation = ,
SystemRegistryQuotaInformation = ,
SystemLookasideInformation = ,
SystemPolicyInformation = ,
} SYSTEM_INFORMATION_CLASS;
这几个值的定义在MSDN上都有,具体可以在上面给的链接的文档查到,这里就不列了。这些枚举值都是可以拿来指定NtQuerySystemInformation所查询的内容
 
然而所给到的枚举值并没有我们想要的枚举句柄的功能,这个时候只能求助于强大的搜索引擎了,我们可以查到比较完整的SYSTEM_INFORMATION_CLASS的定义是下面的列表
typedef enum _SYSTEM_INFORMATION_CLASS {
SystemBasicInformation,
SystemProcessorInformation,
SystemPerformanceInformation,
SystemTimeOfDayInformation,
SystemPathInformation,
SystemProcessInformation,
SystemCallCountInformation,
SystemDeviceInformation,
SystemProcessorPerformanceInformation,
SystemFlagsInformation,
SystemCallTimeInformation,
SystemModuleInformation,
SystemLocksInformation,
SystemStackTraceInformation,
SystemPagedPoolInformation,
SystemNonPagedPoolInformation,
SystemHandleInformation,
SystemObjectInformation,
SystemPageFileInformation,
SystemVdmInstemulInformation,
SystemVdmBopInformation,
SystemFileCacheInformation,
SystemPoolTagInformation,
SystemInterruptInformation,
SystemDpcBehaviorInformation,
SystemFullMemoryInformation,
SystemLoadGdiDriverInformation,
SystemUnloadGdiDriverInformation,
SystemTimeAdjustmentInformation,
SystemSummaryMemoryInformation,
SystemMirrorMemoryInformation,
SystemPerformanceTraceInformation,
SystemObsolete0,
SystemExceptionInformation,
SystemCrashDumpStateInformation,
SystemKernelDebuggerInformation,
SystemContextSwitchInformation,
SystemRegistryQuotaInformation,
SystemExtendServiceTableInformation,
SystemPrioritySeperation,
SystemVerifierAddDriverInformation,
SystemVerifierRemoveDriverInformation,
SystemProcessorIdleInformation,
SystemLegacyDriverInformation,
SystemCurrentTimeZoneInformation,
SystemLookasideInformation,
SystemTimeSlipNotification,
SystemSessionCreate,
SystemSessionDetach,
SystemSessionInformation,
SystemRangeStartInformation,
SystemVerifierInformation,
SystemVerifierThunkExtend,
SystemSessionProcessInformation,
SystemLoadGdiDriverInSystemSpace,
SystemNumaProcessorMap,
SystemPrefetcherInformation,
SystemExtendedProcessInformation,
SystemRecommendedSharedDataAlignment,
SystemComPlusPackage,
SystemNumaAvailableMemory,
SystemProcessorPowerInformation,
SystemEmulationBasicInformation,
SystemEmulationProcessorInformation,
SystemExtendedHandleInformation,
SystemLostDelayedWriteInformation,
SystemBigPoolInformation,
SystemSessionPoolTagInformation,
SystemSessionMappedViewInformation,
SystemHotpatchInformation,
SystemObjectSecurityMode,
SystemWatchdogTimerHandler,
SystemWatchdogTimerInformation,
SystemLogicalProcessorInformation,
SystemWow64SharedInformation,
SystemRegisterFirmwareTableInformationHandler,
SystemFirmwareTableInformation,
SystemModuleInformationEx,
SystemVerifierTriageInformation,
SystemSuperfetchInformation,
SystemMemoryListInformation,
SystemFileCacheInformationEx,
MaxSystemInfoClass // MaxSystemInfoClass should always be the last enum
} SYSTEM_INFORMATION_CLASS;
注意看到第17项(枚举值16)的SystemHandleInformation,这就是我们想要的东西,通过这个值传入NtQuerySystemInformation,然后在NtQuerySystemInformation的函数的第二项放入缓存空间长度,第三项放入缓存空间的指针即可。
 
现在我们要确定缓存区的类型了。如果我们传入SystemHandleInformation,那么NtQuerySystemInformation将会返回下面这个结构
typedef struct _SYSTEM_HANDLE_INFORMATION_EX
{
ULONG NumberOfHandles;
SYSTEM_HANDLE_INFORMATION Information[];//注意655360这个值是我自己定义的,你们可以自己定义其他的常量值
}SYSTEM_HANDLE_INFORMATION_EX, *PSYSTEM_HANDLE_INFORMATION_EX;
 
其中,SYSTEM_HANDLE_INFORMATION的定义是:
typedef struct _SYSTEM_HANDLE_INFORMATION
{
ULONG ProcessId;//进程标识符
UCHAR ObjectTypeNumber;//打开的对象的类型
UCHAR Flags;//句柄属性标志
USHORT Handle;//句柄数值,在进程打开的句柄中唯一标识某个句柄
PVOID Object;//这个就是句柄对应的EPROCESS的地址
ACCESS_MASK GrantedAccess;//句柄对象的访问权限
}SYSTEM_HANDLE_INFORMATION, *PSYSTEM_HANDLE_INFORMATION;
注意到这里有个很奇怪的地方,就是Handle值的类型是USHORT的,然而HANDLE的定义是void *,在32位上是4个字节,在64位上是8个字节。这就告诉我们,我们只能枚举到一个进程的0~65535个句柄值, 但是我们从Windows Internals这本书里面可以知道,现在Windows每个进程的句柄值已经可以到16000000以上了(虽然不会用到那么多)。
 
这样我们就可以根据ProcessId来获取我们感兴趣的进程的句柄值了,但是这里也有一个问题,虽然ProcessId的类型是ULONG,但是也只能枚举到16位以下的ProcessId的值,也就是枚举到的最大ProcessId值是65535,如果我们的程序的ProcessId大于65535,我们就不能枚举到这些进程所创建的句柄了。(这就是Undocument的函数不可靠的体现了)。
 
ObjectTypeNumber是我们想要的句柄值的类型,但是我暂时还无法找到关于这个值的详细资料,只是在windows driver里面查到了这个东西ObReferenceObjectByHandle,但是我现在想在ring3层把问题解决,暂时先不考虑驱动。事实上我们可以在Process Explorer里面根据把句柄值一个一个对应然后找到相应类型,比如下图:
我们可以看到获知句柄值为0x4时,对应的值是Type是Key

我们再来看下我们取到的Info的ObjectType是7,也就是说,我们的Key的类型值就是7

同理我们也可以找到File类型的ObjectType是35
 
 
 
我无法确定这个值是否会跟着系统不同而改变,如果要使用这个方法,请一定要先测试一下。
 
接下来的事情就很好办了,我们只要把NtQuerySystemInformation从NtDll.dll里面拉出来就可以了,我们可以写出这样的代码:
//头文件引#include <winternl.h>
#define SystemHandleInformation 0x10
typedef DWORD(WINAPI *NTQUERYSYSTEMINFORMATION)(DWORD, PVOID, DWORD, PDWORD);
HMODULE hNtDll = LoadLibrary(L"ntdll.dll");
NTQUERYSYSTEMINFORMATION NtQuerySystemInformation =
(NTQUERYSYSTEMINFORMATION)GetProcAddress(hNtDll, "NtQuerySystemInformation");
ULONG cbBuffer = sizeof(SYSTEM_HANDLE_INFORMATION_EX);
LPVOID pBuffer = (LPVOID)malloc(cbBuffer);
if (pBuffer)
{
NtQuerySystemInformation(SystemHandleInformation, pBuffer, cbBuffer, NULL);
PSYSTEM_HANDLE_INFORMATION_EX pInfo = (PSYSTEM_HANDLE_INFORMATION_EX)pBuffer;
for (ULONG r = ; r < pInfo->NumberOfHandles; r++)
{
//dosomething
} free(pBuffer);
}
FreeModule(hNtDll);
 
Native API其他用法举例:查找文件句柄文件名的方法

有时候我们想查找句柄的所对应的信息,比如我之前就遇到了一个需要查找文件句柄所对应文件名的方法,这个时候也需要Native API来完成,需要用到ZwQueryInformationFile这个方法
NTSTATUS ZwQueryInformationFile(
_In_ HANDLE FileHandle,
_Out_ PIO_STATUS_BLOCK IoStatusBlock,
_Out_ PVOID FileInformation,
_In_ ULONG Length,
_In_ FILE_INFORMATION_CLASS FileInformationClass
);
其中第一个参数是我们要查询的文件句柄,信息可以存放在FileInformation指向的内存中,这个内存的长度由Length指定。
 
现在我们来看下第二个参数IoStatusBlock的类型IO_STATUS_BLOCK
typedef struct _IO_STATUS_BLOCK {
union {
NTSTATUS Status;
PVOID Pointer;
};
ULONG_PTR Information;
} IO_STATUS_BLOCK, *PIO_STATUS_BLOCK;
 
Pointer是个保留项,第一项就是指定IRP's I/O的返回值,这个值我们可以不用
 
最后一个参数是FILE_INFORMATION_CLASS类型的一个数,这个数可以拿来指定ZwQueryInformationFile所查询的内容(就像NtQuerySystemInformation的那一堆枚举值也是用来指定NtQuerySystemInformation所查询的内容一样),这个值在MSDN有完整的定义,但在VS自带的SDK里面却没有。
typedef enum _FILE_INFORMATION_CLASS {
FileDirectoryInformation = ,
FileFullDirectoryInformation,
FileBothDirectoryInformation,
FileBasicInformation,
FileStandardInformation,
FileInternalInformation,
FileEaInformation,
FileAccessInformation,
FileNameInformation,
FileRenameInformation,
FileLinkInformation,
FileNamesInformation,
FileDispositionInformation,
FilePositionInformation,
FileFullEaInformation,
FileModeInformation,
FileAlignmentInformation,
FileAllInformation,
FileAllocationInformation,
FileEndOfFileInformation,
FileAlternateNameInformation,
FileStreamInformation,
FilePipeInformation,
FilePipeLocalInformation,
FilePipeRemoteInformation,
FileMailslotQueryInformation,
FileMailslotSetInformation,
FileCompressionInformation,
FileObjectIdInformation,
FileCompletionInformation,
FileMoveClusterInformation,
FileQuotaInformation,
FileReparsePointInformation,
FileNetworkOpenInformation,
FileAttributeTagInformation,
FileTrackingInformation,
FileIdBothDirectoryInformation,
FileIdFullDirectoryInformation,
FileValidDataLengthInformation,
FileShortNameInformation,
FileIoCompletionNotificationInformation,
FileIoStatusBlockRangeInformation,
FileIoPriorityHintInformation,
FileSfioReserveInformation,
FileSfioVolumeInformation,
FileHardLinkInformation,
FileProcessIdsUsingFileInformation,
FileNormalizedNameInformation,
FileNetworkPhysicalNameInformation,
FileIdGlobalTxDirectoryInformation,
FileIsRemoteDeviceInformation,
FileUnusedInformation,
FileNumaNodeInformation,
FileStandardLinkInformation,
FileRemoteProtocolInformation,
FileRenameInformationBypassAccessCheck,
FileLinkInformationBypassAccessCheck,
FileVolumeNameInformation,
FileIdInformation,
FileIdExtdDirectoryInformation,
FileReplaceCompletionInformation,
FileHardLinkFullIdInformation,
FileIdExtdBothDirectoryInformation,
FileMaximumInformation
} FILE_INFORMATION_CLASS, *PFILE_INFORMATION_CLASS;
 
在我们的例子中,我们需要用到的枚举值是FileNameInformation(枚举值9)
 
具体使用也像 一样,先从ntdll.dll里面导出来,然后把参数往里面填就好了,在这里我先定义一个缓冲区:
typedef struct _NM_INFO
{
HANDLE hFile;
FILE_NAME_INFORMATION Info;
} NM_INFO, *PNM_INFO;
 
FILE_NAME_INFORMATION结构:
typedef struct _FILE_NAME_INFORMATION {
ULONG FileNameLength;
WCHAR FileName[];//256我自己定的,可以改成其他的,只要够放位置就行
} FILE_NAME_INFORMATION, *PFILE_NAME_INFORMATION;
 
调用API:
NM_INFO nmInfo = {  };
nmInfo.hFile = hFile;
PNM_INFO NmInfo = (PNM_INFO)lpParameter;
IO_STATUS_BLOCK IoStatus;
ZWQUERYINFORMATIONFILE ZwQueryInformationFile =
(ZWQUERYINFORMATIONFILE)GetProcAddress(hNtDll, "ZwQueryInformationFile");
ZwQueryInformationFile(NmInfo->hFile, &IoStatus, &NmInfo->Info, , FILE_INFORMATION_CLASS::FileNameInformation);
 
注意查询出来的FileNameLength是字节数,而不是WCHAR数组的最大偏移值,在这里WCHAR的最大偏移值应该是512,因为WCHAR是两个字节的
 
 
例子:找出所有文件句柄,并且把对应文件名含有ABC的句柄关掉

注意我把FILE_INFORMATION_CLASS改了个名字,改成了RFILE_INFORMATION_CLASS,这是因为SDK里面已经有了一个FILE_INFORMATION_CLASS了,而且我还把第一个枚举值给改了个名字,如果用以前的那个不知道为啥VS不给编译通过。
 
#include <afx.h>
#include <winternl.h>
typedef DWORD(WINAPI *NTQUERYSYSTEMINFORMATION)(DWORD, PVOID, DWORD, PDWORD);
typedef struct _SYSTEM_HANDLE_INFORMATION
{
ULONG ProcessId;
UCHAR ObjectTypeNumber;
UCHAR Flags;
USHORT Handle;
PVOID Object;
ACCESS_MASK GrantedAccess;
}SYSTEM_HANDLE_INFORMATION, *PSYSTEM_HANDLE_INFORMATION;
#define STATUS_INFO_LENGTH_MISMATCH 0x004
typedef struct _SYSTEM_HANDLE_INFORMATION_EX
{
ULONG NumberOfHandles;
SYSTEM_HANDLE_INFORMATION Information[];
}SYSTEM_HANDLE_INFORMATION_EX, *PSYSTEM_HANDLE_INFORMATION_EX;
#define SystemHandleInformation 0x10 //
typedef struct _FILE_NAME_INFORMATION {
ULONG FileNameLength;
WCHAR FileName[];
} FILE_NAME_INFORMATION, *PFILE_NAME_INFORMATION;
typedef struct _NM_INFO
{
HANDLE hFile;
FILE_NAME_INFORMATION Info;
} NM_INFO, *PNM_INFO;
typedef enum _RFILE_INFORMATION_CLASS {
FileDirectoryInformation1 = ,
FileFullDirectoryInformation,
FileBothDirectoryInformation,
FileBasicInformation,
FileStandardInformation,
FileInternalInformation,
FileEaInformation,
FileAccessInformation,
FileNameInformation,
FileRenameInformation,
FileLinkInformation,
FileNamesInformation,
FileDispositionInformation,
FilePositionInformation,
FileFullEaInformation,
FileModeInformation,
FileAlignmentInformation,
FileAllInformation,
FileAllocationInformation,
FileEndOfFileInformation,
FileAlternateNameInformation,
FileStreamInformation,
FilePipeInformation,
FilePipeLocalInformation,
FilePipeRemoteInformation,
FileMailslotQueryInformation,
FileMailslotSetInformation,
FileCompressionInformation,
FileObjectIdInformation,
FileCompletionInformation,
FileMoveClusterInformation,
FileQuotaInformation,
FileReparsePointInformation,
FileNetworkOpenInformation,
FileAttributeTagInformation,
FileTrackingInformation,
FileIdBothDirectoryInformation,
FileIdFullDirectoryInformation,
FileValidDataLengthInformation,
FileShortNameInformation,
FileIoCompletionNotificationInformation,
FileIoStatusBlockRangeInformation,
FileIoPriorityHintInformation,
FileSfioReserveInformation,
FileSfioVolumeInformation,
FileHardLinkInformation,
FileProcessIdsUsingFileInformation,
FileNormalizedNameInformation,
FileNetworkPhysicalNameInformation,
FileIdGlobalTxDirectoryInformation,
FileIsRemoteDeviceInformation,
FileUnusedInformation,
FileNumaNodeInformation,
FileStandardLinkInformation,
FileRemoteProtocolInformation,
FileRenameInformationBypassAccessCheck,
FileLinkInformationBypassAccessCheck,
FileVolumeNameInformation,
FileIdInformation,
FileIdExtdDirectoryInformation,
FileReplaceCompletionInformation,
FileHardLinkFullIdInformation,
FileIdExtdBothDirectoryInformation,
FileMaximumInformation
} RFILE_INFORMATION_CLASS, *PRFILE_INFORMATION_CLASS;
typedef NTSTATUS(WINAPI *ZWQUERYINFORMATIONFILE)(HANDLE, PIO_STATUS_BLOCK, PVOID, ULONG, RFILE_INFORMATION_CLASS);
CString GetFileName(HMODULE hNtDll, PNM_INFO lpParameter)
{
PNM_INFO NmInfo = (PNM_INFO)lpParameter;
IO_STATUS_BLOCK IoStatus;
ZWQUERYINFORMATIONFILE ZwQueryInformationFile =
(ZWQUERYINFORMATIONFILE)GetProcAddress(hNtDll, "ZwQueryInformationFile");
ZwQueryInformationFile(NmInfo->hFile, &IoStatus, &NmInfo->Info, , RFILE_INFORMATION_CLASS::FileNameInformation);
if (NmInfo->Info.FileNameLength != )
{
CString str;
str.Append(NmInfo->Info.FileName, NmInfo->Info.FileNameLength / sizeof(WCHAR));
return str;
}
return CString();
}
extern "C" int WINAPI _tWinMain(HINSTANCE /*hInstance*/, HINSTANCE /*hPrevInstance*/,
LPTSTR /*lpCmdLine*/, int nShowCmd)
{
HMODULE hNtDll = LoadLibrary(L"ntdll.dll");
NTQUERYSYSTEMINFORMATION NtQuerySystemInformation =
(NTQUERYSYSTEMINFORMATION)GetProcAddress(hNtDll, "ZwQuerySystemInformation");
ULONG cbBuffer = sizeof(SYSTEM_HANDLE_INFORMATION_EX);
LPVOID pBuffer = (LPVOID)malloc(cbBuffer);
auto id= GetCurrentProcessId();
if (pBuffer)
{
NtQuerySystemInformation(SystemHandleInformation, pBuffer, cbBuffer, NULL);
PSYSTEM_HANDLE_INFORMATION_EX pInfo = (PSYSTEM_HANDLE_INFORMATION_EX)pBuffer;
for (ULONG r = ; r < pInfo->NumberOfHandles; r++)
{
if (pInfo->Information[r].ObjectTypeNumber == )
{
NM_INFO nmInfo = { };
nmInfo.hFile = (HANDLE)pInfo->Information[r].Handle;
CString fileName = GetFileName(hNtDll, &nmInfo);
if (!fileName.IsEmpty())
{
if (fileName.Find(L"ABC") != -)
{
CloseHandle(nmInfo.hFile);
}
}
}
} free(pBuffer);
}
FreeModule(hNtDll);
return ;
}
 

用Windows Native API枚举所有句柄及查找文件句柄对应文件名的方法的更多相关文章

  1. 掉坑日志:Windows Native API与DPI缩放

    高DPI显示器越来越普及,软件自然也要适应这个变化,最近实习的时候也遇到了一个关于DPI缩放的问题.因为内部框架的一个控件有BUG,会导致内容的显示出问题,后来实在没办法改成了用Windows Nat ...

  2. Windows Native API

    http://en.wikipedia.org/wiki/Native_API Windows 的原生 API 函数通常在系统启动时(这里其他 Windows 组件还不可用).kernel32.dll ...

  3. 不可或缺 Windows Native (8) - C 语言: 结构体,共用体,枚举,类型定义符

    [源码下载] 不可或缺 Windows Native (8) - C 语言: 结构体,共用体,枚举,类型定义符 作者:webabcd 介绍不可或缺 Windows Native 之 C 语言 结构体 ...

  4. Windows下如何枚举所有进程

    要编写一个类似于 Windows 任务管理器的软件,首先遇到的问题是如何实现枚举所有进程.暂且不考虑进入核心态去查隐藏进程一类的,下面提供几种方法.请注意每种方法的使用局限,比如使用这些 API 所需 ...

  5. 驱动开发:内核枚举PspCidTable句柄表

    在上一篇文章<驱动开发:内核枚举DpcTimer定时器>中我们通过枚举特征码的方式找到了DPC定时器基址并输出了内核中存在的定时器列表,本章将学习如何通过特征码定位的方式寻找Windows ...

  6. mfc 调用Windows的API函数实现同步异步串口通信(源码)

    在工业控制中,工控机(一般都基于Windows平台)经常需要与智能仪表通过串口进行通信.串口通信方便易行,应用广泛. 一般情况下,工控机和各智能仪表通过RS485总线进行通信.RS485的通信方式是半 ...

  7. 不可或缺 Windows Native 系列文章索引

    [源码下载] 不可或缺 Windows Native 系列文章索引 作者:webabcd 1.不可或缺 Windows Native (1) - C 语言: hello c 介绍不可或缺 Window ...

  8. node-webkit教程(9)native api 之Tray(托盘)

    node-webkit教程(9)native api 之Tray(托盘) 文/玄魂 目录 node-webkit教程(9)native api 之Tray(托盘) 前言 9.1  Tray简介 9.2 ...

  9. Native Application 开发详解(直接在程序中调用 ntdll.dll 中的 Native API,有内存小、速度快、安全、API丰富等8大优点)

    文章目录:                   1. 引子: 2. Native Application Demo 展示: 3. Native Application 简介: 4. Native Ap ...

随机推荐

  1. 如何获取input框type=file选中的文件对象(FileReader)

    $("input[type='file']").change(function() { var file = this.files[0]; if (window.FileReade ...

  2. 使用Unity实现动态2D水效果

    http://forum.china.unity3d.com/thread-16044-1-1.html 在这片教程里面我们将会用简单的物理效果来模拟动态的2D水效果.我们将会使用Line Rende ...

  3. 动手写一个简单版的谷歌TPU

    谷歌TPU是一个设计良好的矩阵计算加速单元,可以很好的加速神经网络的计算.本系列文章将利用公开的TPU V1(后简称TPU)相关资料,对其进行一定的简化.推测和修改,来实际编写一个简单版本的谷歌TPU ...

  4. IT兄弟连 JavaWeb教程 AJAX以及JSON字符串经典案例

    案例需求:客户端发送AJAX请求服务器端获取用户信息的数据. 案例实现: 在服务器端要将Java对象转换成JSON字符串,如果使用拼接JSON字符串的方式非常繁琐,并且非常容易出错,所以一般会借助第三 ...

  5. mysql5.7安装部署后初始密码查看以及修改

    一.查看初始密码以下两种方法: 1.找到自己的error.log日志文件,执行自己的命令,红色标记的部分为初始化密码. grep 'temporary password' /data/mysql/er ...

  6. spring boot 使用hibernate validator 验证service

    不在controller中验证,而是在service中验证. spring boot 默认使用的就是hibernate validator,存在于pom的spring-boot-starter-web ...

  7. Win10专业版系统下添加其他国家语言

    Win10专业版系统下如何添加其他国家语言?国内的win10专业版系统默认情况下是安装简体中文,但是有的用户出于工作原因需要使用其它字体.比如外国友人就需要使用英语,西班牙等.其实win10专业版是支 ...

  8. NET full stack framework

    NFX UNISTACK 介绍 学习.NET Core和ASP.NET Core,偶然搜索到NFX UNISTACK,现翻译一下Readme,工程/原文:https://github.com/aumc ...

  9. code review的意义

    https://blog.csdn.net/brodycai/article/details/19636621

  10. 对于es线程池使用的思考

    es有内置的线程池 在实际项目中,发现   使用client框架关闭连接太慢(其实是把连接归还到池子里),采用异步关闭. 随着连接的关闭,计算机内存在不断下降 ------------------- ...