ChristopheP on Microsoft Technologies

January 24, 2013

How to use log4cpp with Visual Studio 2012

Filed under: Uncategorized — christophep @ 1:03 pm

Since end of december 2012, log4cpp has a support for VS 2010. You can now compile log4cpp without pain using VS 2010 or VS 2012.
Log4cpp is available on sourceforget.net at http://sourceforge.net/projects/log4cpp.
Log4cpp is small and efficient logging library with a support for configuration file with RollingFileAppender, etc.
First, you have to create a configuration file for describing your loggers wich are called appenders.

#file log4cpp.property

log4cpp.rootCategory=DEBUG, rootAppender
log4cpp.category.MyLogger=DEBUG, aLogger

log4cpp.appender.rootAppender=ConsoleAppender
log4cpp.appender.rootAppender.layout=BasicLayout

log4cpp.appender.aLogger=RollingFileAppender
log4cpp.appender.aLogger.fileName=aLogger.log
log4cpp.appender.aLogger.maxFileSize=10240
log4cpp.appender.aLogger.maxBackupIndex=5
log4cpp.appender.aLogger.layout=PatternLayout
log4cpp.appender.aLogger.layout.ConversionPattern=[%H:%M:%S.%l] %m%n

#end of file

Once your file is ready, you have to use the primitives of log4cpp to make traces available in the file name aLogger.log.


class MyLogger
{
public:
 MyLogger()
 {
 }
 virtual ~MyLogger()
 {
  log4cpp::Category::shutdown();
 }
 bool Init()
 {
  try
  {
   string initFileName = "log4cpp.property";
   log4cpp::PropertyConfigurator::configure(initFileName);
  }
  catch(log4cpp::ConfigureFailure& f)
  {
   std::cout << "Configure Problem" << f.what() << std::endl;
   return false;
  }
  return true;
 }
 void LogDebug(string message)
 {
  log4cpp::Category & mylogger = log4cpp::Category::getInstance("MyLogger");
  myLogger.debug(message);
 }
 void Loginfo(string message)
 {
  log4cpp::Category & mylogger = log4cpp::Category::getInstance("MyLogger");
  myLogger.info(message);
 }
};

With this helper class, you can manipulate your logging entries very easily.


int main()
{
 MyLogger log;
 if( !log.Init() )
  return 0;
 log.LogDebug("Enter main...");
 log.LogInfo("Main...");
 log.LogDebug("Exit main");
}

How to compile Apache log4cxx with Visual Studio 2012

Filed under: Uncategorized — christophep @ 9:58 am

I was searching for a suitable logging library. Previously, I was using log4cpp but I want to use the Apache logging library. First you have to compile:
- Apr -> libapr-1.dll
- AprIconv -> libapriconv-1.dll
- AprUtil -> libaprutil-1.dll
- expat -> expat.dll
and then log4cxx -> log4cxx.dll.
The problem is that log4cxx use a macro for defining a vector<> template based stuff. All the macros named LOG4CXX_LIST_DEF should be moved from the end of the headers to the top of the header. There are about 20 entries to move.
Another problem is to remove the namespace from the KeySet class. Every time there is scope::KeySet, you should write KeySet only.
After 1 or 2 hours fixing the errors, you should be ok to recompile this library. Size of log4cxx.dll is 4MB (debug mode).

January 4, 2013

Compiling console application from command line using CL.EXE

Filed under: Uncategorized — christophep @ 2:35 pm

If you want to compile your console applications from command line, just use the CL.EXE command tool. This is the Microsoft compiler. Imagine you have two files : ConsoleApp1 and Function1.cpp. To compile, just use this:

CL /EHsc ConsoleApp1 Function1

The /EHsc flag is about exception handling.

Microsoft (R) 32-bit C/C++ Optimizing Compiler Version 15.00.30729.01 for 80×86
Copyright (C) Microsoft Corporation.  All rights reserved.

consoleapp1.cpp
function1.cpp
Generating Code…
Microsoft (R) Incremental Linker Version 9.00.30729.01
Copyright (C) Microsoft Corporation.  All rights reserved.

/out:consoleapp1.exe
consoleapp1.obj
function1.obj

The result is a console application named consoleapp1.exe.

Compiling MFC from command line using NMAKE

Filed under: Uncategorized — christophep @ 2:27 pm

One interesting point using Visual C++ 2010 samples is contained in the MFC folder. You can build mfc samples using a makefile using this command: nmake -a -f makefile. The makefile file just contains your obj files, and then the RC part. Then you #include mfcsamps.mak and that’s all.

Sample:

PROJ=MODELER1
OBJS=AppInit.obj CalendarBar.obj ChildFrm.obj ClassView.obj \
Data.obj \
DrawingContext.obj DrawingElements.obj \
Element.obj ElementContainer.obj ElementFactory.obj ElementManager.obj  \
FileView.obj MainFrm.obj Modeler1.obj Modeler1Doc.obj  \
Modeler1SourceView.obj Modeler1View.obj OutputWnd.obj PropertiesWnd.obj RibbonListButton.obj SourceCodeView.obj TabbedView.obj \
ScintillaCtrl.obj ScintillaDocView.obj

USES_OLE=1

!include <mfcsamps.mak>

# Update the resource if necessary
Modeler1.res: Modeler1.rc resource.h
    rc $(rcflags) $(rcvars) -r -fo Modeler1.res Modeler1.rc

The project is named Modeler1 and the first part of the makefile contains the obj files. You take your cpp files and you write them using the obj extension. Next, the RC part is dedicated for resources.

The MFCSAMPS.MAK file is include into Microsoft Visual Studio\VC\ATLMFC\INCLUDE folder.

November 20, 2012

isocpp.org

Filed under: Uncategorized — christophep @ 11:11 am

Please welcome the new web site http://isocpp.org/ that is promoted by Herb Sutter and C++ committee. You’ll find new about C++, blogs and videos and all the things you could wonder about the standard C++ ISO.

October 23, 2012

CRT Rocks

Filed under: Uncategorized — christophep @ 5:05 pm

Compared to these days, CRT programming could be think as deprecated but it is false. CRT is on the edge of C programming.

October 21, 2012

OK, now enter the logging libraries area

Filed under: Uncategorized — christophep @ 11:35 am

In 1997, I made a web server for a regional bank using Visual C++ and MFC ISAPI. A great great great experience. You think than now you have ASP.NET but the real hardcore stuff are below, and ISAPI bring this. MFC ISAPI is a wonderfull technology. You have to respect every aspect of the web server. You have to provide your own mechanism for every thing from log to session stuff.

enum Mode

{

debug,

error

};

#define LogError(X,Y) Log(X,Y,__FILE__,__LINE__, error)

#define LogDebug(X,Y) Log(X,Y,__FILE__,__LINE__, debug)

class CInternetTrace

{

public:

static Mode m_Mode;

static int m_iCptRef;

static CString m_PathDirectory;

public:

_CERAPI_ CInternetTrace(CString strServiceName);

_CERAPI_ ~CInternetTrace();

_CERAPI_ void Log(LPCSTR szMethod,LPCSTR szMsg, LPCSTR szFile, int iLine, Mode modeAEcrire);

_CERAPI_ void Log2(LPCSTR szMethod,LPCSTR szMsg, LPCSTR szFile, int iLine, Mode modeAEcrire);

_CERAPI_ void Init(CString strServiceName);

};

#define INT_TRACE(x) \

{ \

CInternetTrace theTrace(&quot;Internet&quot;); \

theTrace.LogDebug(x,&quot;&quot;); \

} \

int CInternetTrace::m_iCptRef=0;

CString CInternetTrace::m_PathDirectory;

Mode CInternetTrace::m_Mode=debug;

static CInternetTrace theTrace(TRACE_INTERNET);

//////////////////////////////////////////////////////////////////

// CInternetTrace

//////////////////////////////////////////////////////////////////

BOOL GetRegValue(char *szChemin, char *szValeur, UCHAR *szBuffer)

{

CerRegKey RegKey(HKEY_LOCAL_MACHINE);

DWORD dwCount;

dwCount=256;

if(RegKey.OpenSubKey(szChemin,&amp;RegKey,KEY_READ) == FALSE)

return FALSE;

RegKey.GetValue(szValeur,(UCHAR *)szBuffer,&amp;dwCount);

RegKey.Close();

return TRUE;

}

CInternetTrace::CInternetTrace(CString strServiceName)

{

if( m_iCptRef==0 )

{

csTrace.Unlock();

Init(strServiceName);

}

m_iCptRef++;

}

CInternetTrace::~CInternetTrace()

{

m_iCptRef--;

}

void CInternetTrace::Init(CString strServiceName)

{

char szBuf[256];

if( GetRegValue(REG_TRACE, &quot;Path&quot;,(UCHAR *)szBuf) == FALSE)

m_PathDirectory = &quot;d:\\srv\\trace&quot;;

else

m_PathDirectory.Format(&quot;%s\\%s&quot;,szBuf,&quot;CI&quot;); //strServiceName);

if( GetRegValue(REG_TRACE, (LPSTR)(LPCSTR)strServiceName,(UCHAR *)szBuf) == FALSE)

m_Mode = debug;

else

{

CString Level;

Level = szBuf;

Level.MakeUpper();

if( Level == &quot;ERROR&quot; )

m_Mode = error;

else

m_Mode = debug;

}

}

void CInternetTrace::Log(LPCSTR szMethod,LPCSTR szMsg, LPCSTR szFile, int iLine, Mode modeAEcrire)

{

try

{

if( (modeAEcrire == debug) &amp;&amp; (m_Mode == error) )

return;

csTrace.Lock();

CTime t=CTime::GetCurrentTime();

CString str;

str.Format(&quot;%02d/%02d/%02d %02d:%02d:%02d, %s, %s, %s, %d\n&quot;, t.GetDay(), t.GetMonth(), t.GetYear()%100, t.GetHour(), t.GetMinute(), t.GetSecond(), szMethod, szMsg, szFile, iLine);

CString strFileName;

strFileName.Format(&quot;%s%02d%02d%02d.txt&quot;,m_PathDirectory,t.GetDay(), t.GetMonth(), t.GetYear()%100);

CStdioFile file;

HANDLE hFileExist;

WIN32_FIND_DATA data;

hFileExist=FindFirstFile( strFileName, &amp;data );

if( hFileExist==INVALID_HANDLE_VALUE )

{

if( file.Open(strFileName, CFile::modeWrite | CFile::modeCreate | CFile::typeText)==FALSE )

{

FindClose(hFileExist);

Log2(szMethod, szMsg, szFile, iLine, modeAEcrire);

csTrace.Unlock();

return;

}

}

else

{

if( file.Open(strFileName, CFile::modeReadWrite | CFile::typeText)==FALSE )

{

FindClose(hFileExist);

Log2(szMethod, szMsg, szFile, iLine, modeAEcrire);

csTrace.Unlock();

return;

}

}

//CStdioFile file;

//if( file.Open(strFileName, CFile::modeReadWrite | CFile::typeText)==FALSE )

// if( file.Open(strFileName, CFile::modeWrite | CFile::modeCreate | CFile::typeText)==FALSE )

// return;

FindClose(hFileExist);

file.Seek(0, CFile::end);

file.WriteString(str);

file.Close();

csTrace.Unlock();

}

catch( ... )

{

csTrace.Unlock();

Log2(&quot;CInternetTrace::Log&quot;,&quot;echec&quot;,&quot;techint.cpp&quot;,0,debug);

}

}

void CInternetTrace::Log2(LPCSTR szMethod,LPCSTR szMsg, LPCSTR szFile, int iLine, Mode modeAEcrire)

{

try

{

CTime t=CTime::GetCurrentTime();

CString str;

str.Format(&quot;%02d/%02d/%02d %02d:%02d:%02d, %s, %s, %s, %d\n&quot;, t.GetDay(), t.GetMonth(), t.GetYear()%100, t.GetHour(), t.GetMinute(), t.GetSecond(), szMethod, szMsg, szFile, iLine);

CString strFileName;

strFileName.Format(&quot;%sLocked.txt&quot;,m_PathDirectory);

CStdioFile file;

HANDLE hFileExist;

WIN32_FIND_DATA data;

hFileExist=FindFirstFile( strFileName, &amp;data );

if( hFileExist==INVALID_HANDLE_VALUE )

{

if( file.Open(strFileName, CFile::modeWrite | CFile::modeCreate | CFile::typeText)==FALSE )

{

FindClose(hFileExist);

return;

}

}

else

{

if( file.Open(strFileName, CFile::modeReadWrite | CFile::typeText)==FALSE )

{

FindClose(hFileExist);

return;

}

}

//CStdioFile file;

//if( file.Open(strFileName, CFile::modeReadWrite | CFile::typeText)==FALSE )

// if( file.Open(strFileName, CFile::modeWrite | CFile::modeCreate | CFile::typeText)==FALSE )

// return;

FindClose(hFileExist);

file.Seek(0, CFile::end);

file.WriteString(str);

file.Close();

}

catch( ... )

{

}

}

When C is good. CRT rocks.

Filed under: Uncategorized — christophep @ 11:14 am

It is time to be short and speed. No framework. No libraries. Just log entries in a file. Thanks CRT.

#define TRACE_APP(sz) { FILE *file; file=fopen("c:\\services\\trace.txt","a"); fprintf(file,"%s\n",(const char *)sz); fclose(file); }

September 29, 2012

poster conference.net

Filed under: Uncategorized — christophep @ 3:58 pm

Conference.net the poster !

poster conference.net

Filed under: Uncategorized — christophep @ 3:57 pm

In 2001, I have assisted the conference.net event where MS guys and kids presented the .NET Framework. Amazing.

http://ultrafluid.codeplex.com

Filed under: Uncategorized — christophep @ 8:42 am

The entire application is available at http://ultrafluid.codeplex.com

2 new features : multiple selection and clipboard / and serialization !

Filed under: Uncategorized — christophep @ 8:29 am

Now, I can select multiple elements (with the SHIFT key) and make a right click to have clipboard support. The feature of copy/paste is very usefull.

Another feature is the XML serialization. I can load and save XML diagram with the boost::serialization.

September 22, 2012

Managing the Gdi+ drawing context

Filed under: Uncategorized — christophep @ 2:24 pm

For drawing stuff, I rely on Gdi+ which is easier to use for advanced graphics rather than Gdi. Transformation and scaling operations are provided with appropriate methods.


#pragma once
#include "Element.h"

class CDrawingContext
{
public:
// Drawing Attributes are built in the ctor
CDrawingContext(std::shared_ptr<CElement> pElement);
virtual ~CDrawingContext(void);

public:
Graphics * GetGraphics() { return m_pGraphics; }
// Methods for Drawing Attributes
public:
Color & GetColorWhite() { return m_gdiColorWhite; }
Color & GetColorBlack() { return m_gdiColorBlack; }
Color & GetColorLine() { return m_gdiColorLine; }
Color & GetColorFill() {     return m_gdiColorFill; }
Pen & GetPenBlack() { return m_gdiPenBlack; }
Pen & GetPenColor() { return m_gdiPenColor; }
SolidBrush & GetBrushColor() { return m_gdiBrushColor; }
SolidBrush & GetBrushBlack() { return m_gdiBrushBlack; }
LinearGradientBrush & GetGradientBrushColor() { return m_gdiGradientBrush; }
CPoint GetTopLeft() { return m_pointTopLeft; }
CPoint GetBottomRight() { return m_pointBottomRight; }

public:
Graphics * m_pGraphics;

public:
// GDI+ Drawing objects
Color m_gdiColorWhite;
Color m_gdiColorBlack;
Color m_gdiColorLine;
Color m_gdiColorFill;
Pen m_gdiPenBlack;
Pen m_gdiPenColor;
SolidBrush m_gdiBrushColor;
SolidBrush m_gdiBrushBlack;
LinearGradientBrush m_gdiGradientBrush;

// MFC Drawing objects
CPoint m_pointTopLeft;
CPoint m_pointBottomRight;
};

#include "StdAfx.h"
#include "DrawingContext.h"

CDrawingContext::CDrawingContext(std::shared_ptr<CElement> pElement)
: m_gdiPenBlack(Color(255, 0, 0, 0)),
m_gdiPenColor(Color(255, 0, 0, 0)),
m_gdiBrushColor(m_gdiColorBlack),
m_gdiBrushBlack(m_gdiColorBlack),
m_gdiGradientBrush(
Point(pElement->m_rect.left, pElement->m_rect.top),
Point(pElement->m_rect.right, pElement->m_rect.bottom),
m_gdiColorBlack,
m_gdiColorBlack)
{
m_gdiColorWhite.SetFromCOLORREF(Color::White);
m_gdiColorBlack.SetFromCOLORREF(Color::Black);
m_gdiColorLine.SetValue(Color::MakeARGB(255, GetRValue(pElement->m_colorLine), GetGValue(pElement->m_colorLine), GetBValue(pElement->m_colorLine)));
m_gdiColorFill.SetValue(Color::MakeARGB(255, GetRValue(pElement->m_colorFill), GetGValue(pElement->m_colorFill), GetBValue(pElement->m_colorFill)));
m_gdiPenBlack.SetColor(m_gdiColorBlack);
m_gdiPenColor.SetColor(m_gdiColorLine);
m_gdiPenColor.SetWidth(pElement->m_lineWidth);
m_pointTopLeft = pElement->m_rect.TopLeft();
m_pointBottomRight = pElement->m_rect.BottomRight();
m_gdiBrushColor.SetColor(m_gdiColorFill);

Color color1(255, 241, 247, 255);
m_gdiGradientBrush.SetLinearColors(color1, m_gdiColorFill);

}

CDrawingContext::~CDrawingContext(void)
{
}

Using Boost for XML serialization

Filed under: Uncategorized — christophep @ 1:31 pm

In UltraFluid, I add a feature that enable users to save and load diagrams as XML files. The jobs is done using boost 1.51 and its inner library called boost::serialization. It took me some time to adopt the library but is ok now. I made a clone of my objects with only C++ types because boost cannot handle my MFC types like CRect of CPoint. My XML document is a simple: vector<boost::shared_ptr<CSimpleShape> > m_shapes;

I have just transferred my own data type to the boost data type. To avoid namespace collision, I have put std:: prefix on every shared_ptr of my program. The problem is now that I handled two versions of STL in my applications. I should find a solution to use only boost STL.

August 23, 2012

Ultra fluid for Architects !

Filed under: Uncategorized — christophep @ 8:44 pm

Ultra Fluid Modeler is the premium software of a suite for modeling IT components and infrastructure.

Download the beta on http://ultrafluid.codeplex.com/

August 4, 2012

UltraFluid Modeling Suite is now on CodePlex

Filed under: Uncategorized — christophep @ 7:02 am

The url is http://ultrafluid.codeplex.com/

July 30, 2012

MSDN Library Visual C++ 2012 RC – Windows Runtime C++ Template Library Overview and Benefits

Filed under: Uncategorized — christophep @ 7:25 pm

Windows Runtime C++ Template Library

The Windows Runtime C++ Template Library (WRL) is a COM-based template library that provides a low-level way to use Windows Runtime components.

Benefits

The Windows Runtime is implemented by using Component Object Model (COM) technology. COM depends on housekeeping techniques such as reference-counting to manage the lifetime of objects, and on testing HRESULT values to determine whether an operation succeeded or failed. To successfully write a COM app or library, you must carefully follow COM rules and techniques.

The Visual C++ component extensions (C++/CX) is a high-level, language-based way to use Windows Runtime components. Both the WRL and C++/CX simplify the writing of code for the Windows Runtime by automatically performing COM housekeeping tasks on your behalf.

The WRL and C++/CX provide different benefits. Here are some reasons you might want to use the WRL instead of C++/CX:

The WRL is a compiler-agnostic way to create and consume Windows Runtime APIs. Even if you don’t use the Microsoft compiler, linker, and other development tools, you can use WRL to write apps that use Windows Runtime components, or write custom Windows Runtime components that can be used by others.

By using the WRL, you can optimize your code for performance or for specific scenarios. C++/CX doesn’t expose the underlying COM technology in the Windows Runtime. However, your app or component might require control of the underlying COM code to better create or consume Windows Runtime APIs. When you use the WRL, you can control critical COM directly, but also allow the WRL to control the remaining COM on your behalf. You have complete command.

C++/CX represents COM HRESULT values as exceptions. If you’ve inherited a code base that uses COM, or one that doesn’t use exceptions, you might find that the WRL is a more natural way to work with the Windows Runtime because you don’t have to use exceptions.

Although C++/CX is easy to use, you might prefer not to use “handle to object (^)”, ref new, ref class, and its other language features to write your code. WRL provides an alternative for people who want to use a template library and standard C++ to write Windows Runtime code.

The purpose and design of the WRL is inspired by the Active Template Library (ATL), which is a set of template-based C++ classes that simplify the programming of COM objects. If you already know ATL, you might find that WRL programming is easier.

Overview (WRL)

The Windows Runtime C++ Template Library (WRL) is a set of template-based C++ classes, functions, and macros that enable you to write Component Object Model (COM) objects. WRL is optimized to enable you to use types and programming patterns provided by the Windows Runtime.

 

WRL compared to ATL

 

WRL is similar to the Active Template Library (ATL) because it enables you to create small, fast COM objects. WRL and ATL also share concepts such as defining objects in modules, explicitly registering interfaces, and openly creating objects with factories. You might be comfortable using WRL if you’re familiar with using ATL.

WRL differs from the ATL because it omits direct support for key COM features such as stock implementations, dual interfaces, standard enumerator interfaces, connection points, tear-off interfaces, and ActiveX controls.

 

Concepts

WRL provides types that represent a few basic concepts. The following sections describe those types.

ComPtr

A ComPtr object is a smart pointer type that represents the interface specified by the template parameter. Use a ComPtr to declare a variable that can access the members of an object derived from the interface. ComPtr automatically maintains a reference count for the underlying interface pointer and releases the interface when the reference count goes to zero.

For more information, see Create and Consume Objects (WRL).

RuntimeClass

A RuntimeClass object represents an instantiated class that inherits a set of specified interfaces. A RuntimeClass object can provide a combination of support for one or more of the Windows Runtime, classic COM, or a weak reference.

For more information, see Create and Consume Objects (WRL).

Module

The Module class represents a collection of related objects. A Module object manages class factories, which create objects; and registration, which enables other applications can use an object.

For more information, see Create and Consume Objects (WRL).

Callback

The Callback function creates an object whose member function is an event handler (a callback method). Use the Callback function to write asynchronous operations.

For more information, see Asynchronous Operations (WRL).

EventSource

An EventSource object is used to manage delegate event handlers. Use WRL to implement a delegate, and use EventSource to add, remove, and invoke delegates.

AsyncBase

The AsyncBase class provides virtual methods that represent the Windows Runtime asynchronous programming model. Override the members in this class to create a custom class that can start, stop, or check the progress of an asynchronous operation.

For more information about asynchronous operations, see Asynchronous Operations (WRL).

FtmBase

The FtmBase class represents a free-threaded marshaler object. FtmBase creates a global interface table (GIT), and helps manage marshaling and proxy objects.

WeakRef

A WeakRef smart-pointer represents a weak reference, which references an object that might or might not be accessible. A WeakRef object can be used by only the Windows Runtime, not classic COM.

A WeakRef typically represents an object whose existence is controlled by an external thread or application. For example, a WeakRef can reference a file object. While the file is open, the WeakRef is valid and the referenced file is accessible. But when the file is closed, the WeakRef is invalid and the file is inaccessible.

 

July 29, 2012

My Transcript

Filed under: Uncategorized — christophep @ 2:40 pm
You are now ready to share your qualifications with your employer, friends, and colleagues. Provide them with your Transcript ID (690564) and the Access Code (0679734541), and direct them to https://mcp.microsoft.com/authenticate/validatemcp.aspx.

July 28, 2012

MSDN Archive and MSDN Library 1994 are not deprecated !

Filed under: Uncategorized — christophep @ 2:20 pm

Windows 8 is fully made of new technologies but… ATL/COM and Win32 rules the world of… Windows 8.

MSDN News / oldies but goodies

Filed under: Uncategorized — christophep @ 2:04 pm

Since 1994, I read MSDN Library. It was a single MVB file first on a CD. But there was also a little magazine called Microsoft Developer News. It was cool. Look at the Visual C++ is 2 cool article.

ChristopheP | developing softwares on the Windows Platform since 1994.

Older Posts »

Theme: Shocking Blue Green. Blog at WordPress.com.

Follow

Get every new post delivered to your Inbox.