⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 charbuf.cpp

📁 The library provides supports for run-time loaded plugin classes in C++
💻 CPP
字号:
//// Copyright (C) 2007 Arne Steinarson <arst at users dot sourceforge dot net>//// This software is provided 'as-is', without any express or implied// warranty.  In no event will the authors be held liable for any// damages arising from the use of this software.//// Permission is granted to anyone to use this software for any purpose,// including commercial applications, and to alter it and redistribute// it freely, subject to the following restrictions://// 1. The origin of this software must not be misrepresented; you must//    not claim that you wrote the original software. If you use this//    software in a product, an acknowledgment in the product//    documentation would be appreciated but is not required.// 2. Altered source versions must be plainly marked as such, and must//    not be misrepresented as being the original software.// 3. This notice may not be removed or altered from any source//    distribution.//#include <string.h>#include <stdio.h>#ifndef _CFE_    //#define _CFE_#endif#include "utils/CharBuf.h"// Debug macros#ifdef CHARBUF_DEBUG	#define CB_DEBUG_SET_LENGTH(len) m_len=len	#define CB_DEBUG_CHECK_LENGTH ChkLen(m_str,m_len)#else	#define CB_DEBUG_SET_LENGTH(len) 	#define CB_DEBUG_CHECK_LENGTH#endif/*#if !defined(__WINDOWS__) && !defined(_WIN32) && !defined(__WIN32__)	#define stricmp   strcasecmp	#define strnicmp  strncasecmp#endif#ifdef _MSC_VER 	// MSVC complains about stricmp	#define stricmp _stricmp#endif*/// To trigger break on error under GDB - mingwvoid CBDebugHook( int len, int test ){_CFE_;	::printf("CBDebugHook: %d, %d\n", len, test);#ifdef CHARBUF_DEBUG	// Generate seg fault	*(int*)0 = 0;#endif	int z=3;	//scanf("%d",&z);}// To trigger break on error under GDB - mingwvoid CBDebugHook2( int len, int test ){_CFE_;	::printf("CBDebugHook2: %d, %d\n", len, test);}// Check that the trailing -1 is in the right placevoid ChkLen( char *pc, int l ){_CFE_;	if( !pc ) return;	char *pc1 = (char*)memchr(pc,-1,CB_MAX_RESERVE);	if( pc1 && pc1-pc!=l )		CBDebugHook(l,int(pc1-pc));}// Find the length needed by a vararg string#include <stdarg.h>int cbCalcVarArgLength( const char *s, va_list vl ){_CFE_;    int len = (int)strlen(s);    const char *p, *pc = s;    while( (pc=strchr(pc,'%')) ){    	if( pc[1]=='%' ){    		pc += 2;    		continue;    	}        p = va_arg(vl, char*);        if( pc[1]=='s' )            len += (int)strlen(p);        else            len += 20;  // For integers, floats, hex and others, should be plentiful        pc++;    }    return len;}#include <stdio.h>CharBuf cbprintf( const char *fmt,     va_list vl ){_CFE_;	if( !fmt ) return CharBuf();	int l = cbCalcVarArgLength(fmt,vl);	CharBuf cb("",l+2);	if( !cb.Get() ) return CharBuf("<CharBuf - internal allocation error>");	vsnprintf( cb.Str(), l+1, fmt, vl );	return CharBuf(cb,false);}CharBuf cbprintf( const char *fmt, ...){_CFE_;    va_list vl;    va_start(vl, fmt);    CharBuf cb( cbprintf(fmt,vl), false );    va_end(vl);    return CharBuf(cb,false);}CharBuf::CharBuf( bool dummy, const char *s1, const char *s2, int reserve )  : m_str(NULL) {_CFE_;	dummy &= false;	int l1 = s1 ? (int)strlen(s1) : 0;	int l2 = s2 ? (int)strlen(s2) : 0;	if( !Init( s1?s1:"", l1, l2+reserve ) )		// # Alloc failure		return;	// Concat, we don't disturb trailing -1	if(s2) memcpy( m_str+l1, s2, l2 );	m_str[l1+l2] = 0;}CharBuf::~CharBuf(){_CFE_;     Free(); } void CharBuf::Free( ){_CFE_;     //::printf( "CharBuf::Free %x %s\n", m_str, m_str?m_str:"" );    if(m_str){ delete [] m_str; m_str=NULL; } }bool CharBuf::Init( const char *str, int len, int reserve ) {_CFE_;   CB_DEBUG_SET_LENGTH(0);   if( m_str ){ delete [] m_str; m_str = NULL; }   if ( reserve>CB_MAX_RESERVE ) return false;   if( !str ) return true;   if( len==-1 ) len = (int)strlen(str);      // New alloc size: strlen + 1 + reserve + 1   m_str = new char[len+1+reserve+1];   CB_DEBUG_SET_LENGTH( len+1+reserve );   if ( !m_str ) return false;   memcpy( m_str, str, len );			// Copy string   memset( m_str+len, 0, reserve+1 );	// Fill up with zeros   m_str[len+1+reserve] = (char)-1;	    // Set trailing -1   CB_DEBUG_CHECK_LENGTH;   return true;}int CharBuf::Length(){_CFE_;	return m_str ? (int)strlen(m_str) : 0;}bool CharBuf::ResizeInternal( int len, int sl ){_CFE_;	if( sl==-1 ) sl= m_str?(int)strlen(m_str):0;	if( len<sl ) return true;		int bl = 0;	if( m_str ){		// Make sure we can take away previous trailing -1, after resizing, should not be there		const char *pc = (const char*)memchr(m_str+sl,-1,CB_MAX_RESERVE);		if( !pc ) CBDebugHook(-1,-1);		bl = int(pc-m_str);	}	if( len<bl ) return true;	    // So we have to realloc    char *n_str = new char[len+1+1];    if ( !n_str ) return false;       CB_DEBUG_SET_LENGTH( len+1 );    memcpy( n_str, m_str, sl );	   // Copy string    memset( n_str+sl, 0, len-sl+1 );    n_str[len+1] = (char)-1;	   // Set trailing -1    char *o_str = m_str;    m_str = n_str;    delete [] o_str;    CB_DEBUG_CHECK_LENGTH;	   	return true;}bool CharBuf::operator == ( const char *str ) {_CFE_;	if( !str || !m_str )		return m_str==str;		return !strcmp(str,m_str);}bool CharBuf::operator < ( const char *str ) {_CFE_;	if( !str || !m_str )		return !m_str ? (str?true:false) : false;		return strcmp(m_str,str)<0;}bool CharBuf::eqi( const char *str ) {_CFE_;	if( !str || !m_str )		return (!str || !*str) && (!m_str || !*m_str);		return !stricmp(m_str,str);}bool CharBuf::operator = ( const char *str ) {_CFE_;   if ( !str ) {      // We accept the NULL case      delete [] m_str;      m_str = NULL;      return true;   }   return Assign( str, -1 );}CharBuf& CharBuf::Reset(){_CFE_;    if( m_str ){        int sl = (int)strlen(m_str);        // Overwrite with zeros in case there is -1 inside        memset( m_str, 0, sl );    }    return *this;}// str not necessarily 0 terminatedbool CharBuf::Assign( const char *str, int sl_in ) {_CFE_;   if( !str ) return false;   int sl = sl_in>=0 ? sl_in : (int)strlen(str);	// Wanted length   int bl = m_str ? (int)strlen(m_str) : 0;      // Current length   if ( m_str ){	   if( sl<=bl ) {		  // If a lot of unused space, realloc		  if( sl_in>=0 && bl>sl*2 && bl-sl>16 )			  return Init( str, sl, CB_CAT_RESERVE );		  	      // New string is shorter (or equal), pad with zeros after it	      memcpy( m_str, str, sl );	      memset( m_str+sl,0,bl-sl );	      return true;	   }	   // We might have place for it?      char *pv = (char*)memchr( m_str+bl+1, -1, CB_MAX_RESERVE );      if ( !pv ){         CBDebugHook(-1,-1);         return false;      }      bl = int(pv - m_str);#ifdef CHARBUF_DEBUG      if( bl!=m_len )         CBDebugHook(bl,m_len);#endif	  // If a lot of unused space, realloc	  if( sl_in>=0 && bl>sl*2 && bl-sl>16 )		  return Init( str, sl, CB_CAT_RESERVE );      if ( bl>sl ) {         memcpy( m_str, str, sl );         memset( m_str+sl,0,bl-sl );         return true;      }   }   // So we have to realloc   char *n_str = new char[sl+1+1];   if ( !n_str ) return false;      CB_DEBUG_SET_LENGTH( sl+1 );   memcpy( n_str, str, sl );	   // Copy string   n_str[sl] = 0;				   // 0 terminate   n_str[sl+1] = (char)-1;		   // Set trailing -1   char *o_str = m_str;   m_str = n_str;   delete [] o_str;   CB_DEBUG_CHECK_LENGTH;   return true;}bool CharBuf::Append(const char *str, int len) {_CFE_;   if ( !str || !*str ) return true;   if( len==-1 ) len=str?(int)strlen(str):0;   CB_DEBUG_CHECK_LENGTH;   // Find out how much reserved space we have   int bl = m_str ? (int)strlen(m_str) : 0;      // Make sure we have space   if( !ResizeInternal(bl+len+CB_CAT_RESERVE,bl) ) return false;   // Write at tail of buffer   strncpy( m_str+bl, str, len );   m_str[bl+len] = 0;      CB_DEBUG_CHECK_LENGTH;   return true;}/*bool CharBuf::operator += (const char *str ) {_CFE_;   if ( !str ) return true;   int sl = strlen(str);   if ( !sl ) return true;   CB_DEBUG_CHECK_LENGTH;   // Find out how much reserved space we have   int bl = m_str ? strlen(m_str) : 0;   if ( m_str ) {      char *pv = (char*)memchr( m_str+bl+1, -1, CB_MAX_RESERVE );      if ( !pv ) return false;      int res = pv - (m_str+bl);	// Number of free bytes#ifdef CHARBUF_DEBUG      if( res+bl!=m_len )      	CBDebugHook(m_len,res+bl);#endif      if ( res>sl ) {         memcpy( m_str+bl, str, sl+1 );         return true;      }   }   // So we have to realloc   char *nstr = new char [bl+sl+2+CB_CAT_RESERVE];   CB_DEBUG_SET_LENGTH( bl+sl+1+CB_CAT_RESERVE );   if ( !nstr ) return false;   memcpy( nstr, m_str, bl );   memcpy( nstr+bl, str, sl );   memset( nstr+bl+sl, 0, CB_CAT_RESERVE+1 );   nstr[bl+sl+1+CB_CAT_RESERVE] = -1;   delete [] m_str;   m_str = nstr;      CB_DEBUG_CHECK_LENGTH;   return true;}*/CharBuf &CharBuf::MoveFrom(CharBuf &cb){_CFE_;	CB_DEBUG_CHECK_LENGTH;	// Move the contents of cb to us	delete [] m_str;	m_str = cb.m_str;	cb.m_str = NULL;	#ifdef CHARBUF_DEBUG	m_len = cb.m_len;	cb.m_len = 0;	#endif		CB_DEBUG_CHECK_LENGTH;	return *this;}bool CharBuf::SaveToFile( const char *path ){_CFE_;    if( !path ) return false;    FILE *pf = fopen( path, "w" );    if( !pf ) return false;    int rv = (int)fwrite( m_str, 1, m_str?strlen(m_str):0, pf );    fclose( pf );    return rv!=0;}CharBuf& CharBuf::cbprintf( const char *fmt, ... ){_CFE_;    va_list vl;    va_start(vl, fmt);    MoveFromConst( ::cbprintf(fmt,vl) );    va_end(vl);    return *this;}bool CharBuf::LoadFromFile( const char *path ){_CFE_;    if( !path ) return false;    FILE *pf = fopen( path, "r" );    if( !pf ) return false;    fseek( pf, 0, SEEK_END );    int sz = ftell( pf );    fseek( pf, 0, SEEK_SET );    Resize( sz );    int rv = (int)fread( m_str, 1, sz, pf );    fclose( pf );    return rv!=0;}void CharBuf::Subst( char ch_find, char ch_repl ){_CFE_;    if( !m_str ) return;    for( char *str=m_str; *str; str++ )        if( *str==ch_find )            *str = ch_repl;}CharBuf operator + (const CharBuf& s1, const char *ps2){_CFE_;	return CharBuf(true, s1,ps2);}CharBuf operator + (const char *ps1, const CharBuf& s2){_CFE_;	return CharBuf(true, ps1,s2);}#ifdef CHARBUF_TESTint main(){_CFE_;	puts( cbprintf("Age is %d and name is %s. Address %% is %p \n",43,"Kalle",main) );    CharBuf cb;    cb.cbprintf( "Another test:%d. Name: %s, Age: %d, Addr: %p\n", 341, "Arne", 40, &cb );    puts( cb );}#endif

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -