分享一个重载new、new[],打印日志的东西

_船长_ 2017-01-04 12:23:37
加精
CZURCommon.h
#ifndef _CZUR_COMMON_H
#define _CZUR_COMMON_H

#include "windows.h"
#include <iostream>

class CZURLog
{
public:
CZURLog();
virtual ~CZURLog();

void CreateLogFile(LPCSTR lpszLogName);
void PrintLog(char *pFormat, ...);

public:
FILE *m_pLogFile;
CRITICAL_SECTION m_csLog;
};

class CZURMutex
{
public:
CZURMutex(CRITICAL_SECTION *pcsLog);
virtual ~CZURMutex();

private:
CRITICAL_SECTION *m_pcsLog;
};


//变量声明
extern CZURLog g_OutLog;

void *operator new(size_t size, LPCSTR lpszFileName, int line);

void *operator new[](size_t count, LPCSTR lpszFileName, int line);



#endif //_CZUR_COMMON_H


CZURCommon.cpp
#include "CZURCommon.h"

CZURLog g_OutLog;

CZURLog::CZURLog()
:m_pLogFile(NULL)
{
InitializeCriticalSection(&m_csLog);
}

CZURLog::~CZURLog()
{
if(m_pLogFile)
{
fclose(m_pLogFile);
}
DeleteCriticalSection(&m_csLog);
}

void CZURLog::CreateLogFile(LPCSTR lpszLogName)
{
if(lpszLogName)
{
m_pLogFile = fopen(lpszLogName, "at+");
}
}

void CZURLog::PrintLog(char *pFormat, ...)
{
char szString[1024];
va_list args;

va_start(args, pFormat);
vsprintf(szString, pFormat, args);
va_end(args);

//获取系统时间
SYSTEMTIME sysTime;
GetLocalTime(&sysTime);

char szLogText[1024];
//格式化本地时间
sprintf_s(
szLogText, 1024, "[%4d-%02d-%02d %02d:%02d:%02d] %s\n",
sysTime.wYear, sysTime.wMonth, sysTime.wDay,
sysTime.wHour, sysTime.wMinute, sysTime.wSecond,
szString
);

CZURMutex mutex(&m_csLog);

if(m_pLogFile)
{
fseek(m_pLogFile, 0, SEEK_END);
fputs(szLogText, m_pLogFile);
fflush(m_pLogFile);
}
}

CZURMutex::CZURMutex(CRITICAL_SECTION *pcsLog)
{
m_pcsLog = pcsLog;
EnterCriticalSection(pcsLog);
}

CZURMutex::~CZURMutex()
{
LeaveCriticalSection(m_pcsLog);
}

void *operator new(size_t size, LPCSTR lpszFileName, int line)
{
void *ptr = NULL;
try
{
ptr = ::operator new(size);
}
catch(std::bad_alloc)
{
g_OutLog.PrintLog("FILE: %s, LINE: %d, Error: Memory Allocation Failed", lpszFileName, line);
}
return ptr;
}

void *operator new[](size_t count, LPCSTR lpszFileName, int line)
{
return operator new(count, lpszFileName, line);
}


附带测试Test.cpp说明:
/*

关于重载new、new[]的使用说明

在工程中,包含CZURCommon.h、CZURCommon.cpp文件

在需要使用重载的new、new[]运算符的cpp文件中,添加#include "CZURCommon.h",

并宏定义:#define new new(__FILE__, __LINE__)
(宏定义new目的,简化调用时的繁琐,将重载的new、new[]用起来和之前的new、new[]没有任何区别,
如果不进行宏定义,则调用方式:int *p = new(__FILE__, __LINE__) int[2])

程序运行之初,调用g_OutLog.CreateLogFile()函数,创建日志文件

如是,调用new、new[]分配内存失败的时候,捕获异常,在日志中输出相应的错误信息

*/

#include "CZURCommon.h"
#include "stdio.h"

//宏定义new运算符
#define new new(__FILE__, __LINE__)

int main()
{
//设置日志文件名称
g_OutLog.CreateLogFile("d:\\1.log");

//为了测试,循环申请内存,不释放
while(1)
{
char *p = new char;

//内存分配失败,在D盘中的error.log中输出错误信息
if(NULL == p)
{
printf("内存分配失败,请查看日志信息\n");
return 0;
}
}
system("pause");

return 0;
}


说明:打印log信息部分,之前的做法是每次都打开log文件,写入后,关闭log文件,但测试发现,对于new、new[]失败时,调用fopen打开log文件会失败(猜测原因:fopen内部会申请堆内存,而此时堆内存不足,导致失败),因此无法将new、new[]错误信息正常写入到log文件中,针对这种情况,改进了做法,程序运行之初,创建log文件,运行结束后,关闭log文件,确保所有的log信息不会因为new、new[]失败而丢失。
...全文
4359 22 打赏 收藏 转发到动态 举报
写回复
用AI写文章
22 条回复
切换为时间正序
请发表友善的回复…
发表回复
Syee001 2017-07-17
  • 打赏
  • 举报
回复
下载地址啊,楼主
Daniel_31 2017-02-06
  • 打赏
  • 举报
回复
版主有木有整个工程?
房子在哪 2017-01-25
  • 打赏
  • 举报
回复
谢谢分享
ming948264 2017-01-13
  • 打赏
  • 举报
回复
666666666
lishengone 2017-01-09
  • 打赏
  • 举报
回复
感谢分享
qq_37295697 2017-01-09
  • 打赏
  • 举报
回复
cattpon 2017-01-06
  • 打赏
  • 举报
回复
learning~
hugh_z 2017-01-06
  • 打赏
  • 举报
回复
66666666666
cattpon 2017-01-05
  • 打赏
  • 举报
回复
learning~
hugh_z 2017-01-05
  • 打赏
  • 举报
回复
666666666666666666666
  • 打赏
  • 举报
回复
lx624909677 2017-01-04
  • 打赏
  • 举报
回复
clever101 2017-01-04
  • 打赏
  • 举报
回复
多谢楼主,好帖留名!
paschen 2017-01-04
  • 打赏
  • 举报
回复
鱼弦 2017-01-04
  • 打赏
  • 举报
回复
恩,get
mgzhen 2017-01-04
  • 打赏
  • 举报
回复
谢谢分享,谢谢!
Rone-X 2017-01-04
  • 打赏
  • 举报
回复
感谢楼主 又学会一招~~
sevancheng 2017-01-04
  • 打赏
  • 举报
回复
_船长_ 2017-01-04
  • 打赏
  • 举报
回复
感谢斑竹推荐

16,472

社区成员

发帖
与我相关
我的任务
社区描述
VC/MFC相关问题讨论
社区管理员
  • 基础类社区
  • Web++
  • encoderlee
加入社区
  • 近7日
  • 近30日
  • 至今
社区公告

        VC/MFC社区版块或许是CSDN最“古老”的版块了,记忆之中,与CSDN的年龄几乎差不多。随着时间的推移,MFC技术渐渐的偏离了开发主流,若干年之后的今天,当我们面对着微软的这个经典之笔,内心充满着敬意,那些曾经的记忆,可以说代表着二十年前曾经的辉煌……
        向经典致敬,或许是老一代程序员内心里面难以释怀的感受。互联网大行其道的今天,我们期待着MFC技术能够恢复其曾经的辉煌,或许这个期待会永远成为一种“梦想”,或许一切皆有可能……
        我们希望这个版块可以很好的适配Web时代,期待更好的互联网技术能够使得MFC技术框架得以重现活力,……

试试用AI创作助手写篇文章吧