본문 바로가기
프로그래밍

LOG_PRINTF 문자열 길이 제한을 벗어버리자

by 알 수 없는 사용자 2012. 3. 22.

음.. 현재 ICT 의 LogLib에는 다음과 같은 함수를 이용해 LogPrintf하고 있다.


void __cdecl XfAddIctLogFormat( int line, char *func, char*file,AnsiString type, char * lpszFormat, ...)
{
    int nBuf;
    char acLogMsg[4096];
    va_list args;
    va_start(args, lpszFormat);
    nBuf = vsnprintf(acLogMsg ,4095, lpszFormat, args);
    va_end(args);
    if( nBuf <1)return;
    XfAddIctLog(line,func,file,type, sLogMsg); // 파일에 기록
}


그런데 위 함수에는 문제점이 하나 있다.

충분히 Buffer를 확보해서 4 KByte까지  로그메세지를 기록할수 있지만
메세지 길이가 4KByte넘어가면 뒤로는 문자열이 짤리게 된다.


[ _vsctprintf ]
다음 링크에 보면
vsprintf로 문자열 조합을 하기 전에 문자열 길이를 확인할수 있는 방법이 있다.
http://www.devpia.com/MAEUL/Contents/Detail.aspx?BoardID=51&MAEULNo=20&no=8369&ref=8369 

_vsctprintf  라는 함수를 이용하여 조합될 문자열의 길이를 확인하고
문자열 길이가 크면 동적으로 메모리를 확보해서 printf 하는 방식이다.

_vsctprintf  -  http://msdn.microsoft.com/en-us/library/w05tbk72(VS.71).aspx

 

[C++Builder에서 
_vsctprintf 선언되어있지 않음]

C++Builder에서 위 _vsctprintf 를 써보려고 했더니..
stdio에 선언되어있지 않다? 엥?

 
 
[해결 방안]

C++Builder에서는 String 클래스에 printf 기능이 있다.
 
이미 cdecl 함수로 넘어온 가변 파라메터를 String클래스 멤버 함수로 넘기려면..

printf 대힌 vprintf 를 쓰면 된다.
 


void __cdecl XbfAddIctLogFormat( int line, char *func, char*file,AnsiString type, char * lpszFormat, ...)
{
   AnsiString sLogMsg;
    va_list args;
    va_start(args, lpszFormat);
    int iLen=sLogMsg.vprintf(lpszFormat,args);  // va_list 를 넘기는 함수 
    va_end(args);
    if(iLen<1)return;

    XbfAddIctLog(line,func,file,type, sLogMsg);
}
//----------------------------------------------------------------------------

 
C++Builder에서는 _vsctprintf   함수가 export 되어있지는 않지만
String클래스의 vprintf를 쓰면 얼마든지 킨 문자열도 조합이 가능하다.

그럼..