MacroMagic

30 08 2010

So, the past couple of posts have been about error handling, reporting and what-not. There were also mentioned a few macros here and there. To conclude this saga I’d like to make this post about the #define magic; or black magic if you will.

Let’s preface this entire discussion with what I’d like to call, my precondition to the PRECONDITION. I’m not a great proponent of macros. In fact I try to avoid the preprocessor as much as I can [for reasons which are discussed pretty much everywhere concerning C and/or C++ programming]. That said though I don’t actually subscribe to the notion that a #define is evil. Like many things in my development environment the preprocessor is a tool, bit blunt, bit dangerous, but a tool nonetheless. Guns don’t kill people, code-maintainers do; in frustration. But let’s get back to the macro faeries.

The first iteration of my macro implementation went fairly close to the normal assert. For two very good references about asserting I’d like to point to the following, Game Programming Gems and http://cnicholson.net/2009/02/stupid-c-tricks-adventures-in-assert/ which doesn’t seem to show in my browser so I don’t know if it’s still there or not?

Ok, enough talking, let’s code; this is what the #define looked in practice.
PRECONDITION(mCreated==true, "window has not been created yet");

Seems alright on the surface but the first question I’ve had for it was whether the condition should be met or not. That is, am I saying:
if (condition) { report message; }or
if (not condition) { report message; }

One might be inclined to simply look at the PRECONDITION code and derive conclusions from there but I think functionality should be understandable through use of code, not inspection [which is why I haven’t posted up the code yet]; so I’ve changed the code to look like this;
PRECONDITION(mCreated==false,/*otherwise*/"window has not been created yet");

Better in the sense that it now clarifies the intent but it still rubs me the wrong way since I’ve had to resort to a comment [which is external to code]. In response I’ve done someting which I’m still not sure is a good idea but I’m keeping at the moment. I’ve separated the PRECONDITION macro into two interrelated and interconnected macros;
PRECONDITION(mCreated==true) OTHERWISE_REPORT("this window has not been created yet");

It’s not an ideal solution, in fact it’s blunt and ugly [although ugly here is good since it tells me it’s a macro], but I’m satisfied with it at the moment. The main reason I have for using a macro rather than a function call is the need to report file, function and line location of the call as well as provide a breakpoint into the code at the appropriate place for a trace.

The Postcondition, as you may have already guessed looks pretty much the same. I value code coherency very much, if I write one type of interface I keep the rest of the related types with the same interface.
POSTCONDITION(mCreated==false) OTHERWISE_THROW("could not create window");

And as for the actual PRECONDITION and POSTCONDITION code;
#ifndef _FORGE_ERROR_POSTCONDITION_
#define _FORGE_ERROR_POSTCONDITION_

#include <sstream>
#include <exception>

#define POSTCONDITION(condition)  \
do        \
{ \
  if (!(condition)) \
  { \
    std::ostringstream os; \
    os <<'\n'<<"** POSTCONDITION FAILED **"\
       <<'\n'<<"CONDITION : "<<#condition \
       <<'\n'<<"FILE : "<<__FILE__ \
       <<'\n'<<"LINE : "<<__LINE__ \
       <<'\n'<<"FUNCTION : "<<__FUNCTION__
#define OTHERWISE_THROW(name, message) \
       <<'\n'<<"NAME : "<<name \
       <<'\n'<<"MESSAGE : "<<message<<'\n'; \
       throw std::range_error(os.str().c_str()); \
  } \
}while(0)

#endif/*_FORGE_ERROR_POSTCONDITION_*/

#ifndef _FORGE_ERROR_PRECONDITION_
#define _FORGE_ERROR_PRECONDITION_

#include <iostream>

#ifndef UNIT_TEST_MODE
  #define BREAKPOINT_AND_ABORT __debugbreak(); std::abort()
#else
  #define BREAKPOINT_AND_ABORT
#endif/*UNIT_TEST_MODE*/

#ifndef DISABLE_FORGE_ASSERT
#define PRECONDITION(condition)        \
do                \
{ \
  if (!(condition)) \
  { \
    std::clog \
    <<'\n'<<"** PRECONDITION FAILED **" \
    <<'\n'<<"CONDITION: "<<#condition \
    <<'\n'<<"FILE : "<<__FILE__ \
    <<'\n'<<"LINE : "<<__LINE__ \
    <<'\n'<<"FUNCTION : "<<__FUNCTION__
#define OTHERWISE_REPORT(name, message) \
    <<'\n'<<"NAME : "<<name \
    <<'\n'<<"MESSAGE : "<<message \
    <<'\n'; \
    BREAKPOINT_AND_ABORT; \
  } \
}while(0)
#else
#define PRECONDITION(condition) do{ sizeof(condition);
#define OTHERWISE_REPORT(message) }while(0)

#endif/*DISABLE_FORGE_ASSERT*/

#endif/*_FORGE_ERROR_PRECONDITION_*/

Bit of a hack, but I’ve done worst. I’ve also been toying around with trying to move the PRECONDITION assert to compile time, or at least link time by using templates. I’ve not had much success yet, but I like templates so I’ll see if I can come up with something. Anyways, dishes await. Strange, seems like every time I need to do the dishes I try to post something before, coincidence? or black magic??

Hey Joe, where you goin’ with that gun in your hand?”





Asserting throws and throwing asserts

25 08 2010

[Part II]
Braving back through my previous post it does feel a tad long-winded but it was a journey I felt I needed in order to get my own perspective and approach to errors.

I’ve settled at the moment on the simplest solution I could; simplicity being my preferred method of work at the moment. Within this simplicity there are defined two error-types, a PRECONDITION and POSTCONDITION. Both of these handle errors by logging them [either to a file or through the std::cerr, whichever fits the current context]. The difference is thus.

A PRECONDITION is designed to inform the Programmer client that he/she [or me] are using the code in the wrong way. A PRECONDITION which fires means that there’s an error in the code which must be corrected before any more work can be on done on expanding the codebase. For this reason when my PRECONDITION fires it uses a [custom] assert that aborts the entire program; it’s yelling at me -> STOP, YOU’VE MADE A MISTAKE IN THE CODE, FIX IT!

Here we see that the assert is a way of handling the error, it’s not really a reporting mechanism [although it informs programmers that something is wrong, it doesn’t report to other code]. In my opinion the PRECONDITION should, ideally, be caught at compile-time [in the same manner that a misuse of the language would cause a compiling error, like trying to assign to an r-value].

A POSTCONDITION error, however, is fired when the function can execute [or should be able to], has executed, worked on some external data [or with another object] but failed to achieve the desired state/result. Here a POSTCONDITION will throw an exception saying “I’ve tried my best but couldn’t do it, now what?”. An exception then is a form of error reporting [very unlike the assert which is error handling], it reports back to other pieces of code meant to deal with the error in whatever way needed [a nice message window, a log file, even a full system shutdown if required]. A POSTCONDITION error, I’ve found, is usually the result of an end-user client using/misusing the software and should be handled by offering options of recovery.

Some examples are probably in order.
window.Create();
window.Create();
PRECONDITION ERROR: The programmer has just violated the internal logic of the program and should fix it immediately.

image.load("c:\somewhere\somefile.jpg");
POSTCONDITION ERROR: File could not be found, do you want to load another file or go back to the main application?

In the POSTCONDITION example the file may be loaded by hand with the programmer working as an End-User, or it might be supplied during the usage of the application by an artist perhaps via a config dialog box or some other mechanism.

So that’s it. This is my system so far, simple and it works for me. Error handling, I think, shouldn’t be a complex issue. It should be robust and easy to use but like any other component of the system, once it becomes too unwieldly to understand it’s just as bad has having no handling at all.

“Things fall apart, the centre cannot hold”





This whole courtroom is out of order!

22 08 2010

[Part I]
I’ve spent the last few days researching error handling in C++ [and in general really]; many a-battles have I found scattered around and I’ve gotten the impression that the entire topic is quite subjective, where one man’s Hellspawn-Demons are another man’s BFG.

I would like to start since by laying some groundwork and defining some ideas since through many of the sites/tutorials/chapters and debates I was left somewhat overwhelmed, the correct nomenclature seemed, I don’t know, disorientating. So without further ado let’s define my first item; the error.
Error
An error is the difference between the expected result/state from the actual result/state

Any operation we use produces some results, or changes the state of an object. In order to create a proper logical flow we expect these operations to produce a desired result; functions and operations themselves expect some conditions to have been met before they too can produce expected results. Deviation from any of these expections will yield unpredictable and erroneous behaviour. Since the only person I allow to misbehave is my daughter I check for errors.

Next definition:
Error Checking
The act of defining an assumed condition and checking the actual result/state against it

Checking errors is a rather simple matter, we make an assumption, we write down an expected result, we run the function and use an if statement to make sure the result we got is the one we wanted.
void Window::Create()
{
  if (mCreated==true) { /*hmmm... do something*/ }
  mCreated=CreateWindow(); //WIN32 API call
  if (mCreated==false) { /*hmmm.. do something*/ }
}

There are two checks within this function, both check for errors yet they check for different types of errors. The first check which I’ve termed the PRECONDITION makes sure that the user does not call Window::Create() on an already created window; an error such as this can only occur when a programmer makes a direct call to the object via the code, this is a static logic error [as it makes no logical sense in terms of the code to call this function a second time on the same object without destroying the window first].

The second check partains to a different error and its condition is related to the execution of an external function [a function which crosses module boundries]. This is a runtime state error, an error which occurs because of external data. I’ve called this check the POSTCONDITION.

Let’s repeat this for a moment. The two errors in question are violations of either the PRECONDITION or the POSTCONDITION of the Create() function. Each violation in turn creates a different type of error. The errors are, in effect, generated at two different scopes and by two distinct user types.

Eh.. User types? What are those? I’m glad you asked…
Code User/Client
Application code can be used in two different contexts. The first of which is within the Debug state, whereas a Programmer writes execution code, whilst the second is Release mode; where an End-User receives and uses the application as is.

That is not to say that a programmer cannot be considered an end-user, nor that an end-user isn’t a programmer. But the approach to software builds should be with these mindframes. Where was I?

Ah yes. The ride is nearly over so I’ll now introduce two more concepts. Throwing exceptions and the ever ubiquitous Assert. Furthermore I’ll jump the gun and ruin the ending, in my system a PRECONDITION asserts while a POSTCONDITION throws an exception, but why?

The answer of course lies after some more definitions… These should be the last ones, hopefully…
Error Reporting
The act of informing the user and/or application itself that an error has occured

Error Handling
The act of dealing with the consequences of an error report as per user/client needs.

This post is getting long, the night is getting old and the dishes are, well staying dirty until I clean them, so I’ll finish with a last thought [the rest will be posted tomorrow, honest].

Error handling; we’ve found an error, a function has /*magically*/ reported it, what now? What now highly depends on the context in which the error was reported at, the most basic handling routine is to log the error with the most information you can recover about it to some log file for extraction [either immediately or later], that’s right, logging an error is NOT reporting it, nope, it’s a method of dealing with it and it isn’t [nor should it be] the only one. As I just said, other methods are highly contextual not just to the build-type but also to the user-type which has triggered the error. The rest will be explored/explained tomorrow, so stay tuned; same bat-time! same bat-channel!

“Oh would you like to swing on a star; carry moonbeams home in a jar; and be better off than you are”





Testing…1…2…3…

18 08 2010

Before starting I’d just like to get it out of the way, yes I know there are libraries out there that do just that, heaps and heaps, I’ve used SDL, I’ve used Ogre3D, I’ve checked out UDK and Unity [I’m into game programming if you haven’t noticed] and I know there’s no need to reinvent the wheel. I don’t want wheels, I like walking and I want to write a lightweight rendering suite using OpenGL and built on [at the moment] the WIN32 API; portability is important and will be addressed by minimizing and localizing API dependent calls.

For this lovely suite I’m taking a different approach than what I usually would and am test-driving it. I’ve never really realized how interesting it would be to do so but I don’t want to complain about trying to force OOD into the WIN32 API. I want to talk about the process I’ve been using, namely the TDD approach.

Again, I’d like to stress here that I’m very much a beginner to TDD and the entire Agile methodology, so these concepts obviously do not represent the actual usage of the methodology [unless they really do and can someone please tell me if they do, because I’d love to know].

Ok, back to the window code.

On papar I made a few quick broadstrokes of the things that I wanted to achieve and the items I would need to have in order to achieve them. The list looks something like this;
GOAL: Render one pixel using OpenGL and the WIN32 API
THINGS I NEED:
1. Window.
2. DrawingSurface.
3. OpenGL Rendering Context.

So far, so good. What’s the first thing I wanted again? ah yes, a Window. A Win32::Window to be more precise [I like namespaces]. Um… Let’s pretend that I have one already, what’s the first thing I’d like to do with it?
TEST(check_window_name)
{
  Win32::Window window("TestWindow", "TestTitle", Size(640,480), Position(0,0));
  CHECK_EQUAL("TestWindow", window.Name());
};

We can see where this is going so let’s just jump the gun. Some refactoring later, adding a fixture or two and I’ve had a window class that had some nice attributes; now what? there’s still no actual window on the screen, obviously I need to create it.

TEST_FIXTURE(WindowFix, create_window)
{
  window.Create();
  CHECK_EQUAL(true, window.Created());
  window.Destroy();
  CHECK_EQUAL(false, window.Created());
};

Er… two checks in one call, I don’t like it very much and in my code I’ve actually refactored it away; but for the sake of brevity I’ll keep this test. The easy way to solve this is to just change a boolean value on calling both Create() and Destroy(). And I’ve done just that, TDD stating we need to add just enough functionality in order to pass the test. But… But… ARGH, it doesn’t really help me get an actual Window on the screen, does it???

I’ve banged my head on it for a while, I stared at the code for an hour then I started writing some reflective notes and then, then I had a lightbulb go in my head. Testing return values are only part of the tests [and probably not the most important part] that we have in the arsenal. Tests should also test object-object interactions and my object interacts with the WIN32 API.

A quick search through MSDN and I came up with this test;
TEST_FIXTURE(WindowFix, check_window_class_with_WIN32_API)
{
  WNDCLASSEX result;
  CHECK( ::GetClassInfoEx(window.hInstance(), window.Name(), &result) );
}

Run and… Watch it fail miserably. Now I needed to get this test passing, which means actually writing code to talk with the API. And there you have it, this little bit started me on the road to better understand what [I think] TDD is about.

Writing effective tests isn’t easy, doubly so for when they must test interactions. I’ve written before about needing to make assumptions when writing tests and I really thought that I understood that; I was wrong, the fact I nearly gave up here tells me I was still stuck in thinking about tests from a reverse point of view, meaning that code needs to be tested, rather than tests need to be coded. It’s lucky I talk to myself because what brought me to this test was a fairly simple question.
"Ok Amir, now that you've created the window, can you ask the WIN32 API to check whether its there or not?"

Next post would be about the other interesting thing that came up from test-driving the Win32::Window.

The heart of the dragon is screaming awaiting, to write the black last page





Don’t point, it’s impolite

14 08 2010

Before starting this I’ll post some code that gave me the headache.

It isn’t complex code, just a simple Win32 window class wrapper for the [surprise, surprise] window using WIN32 API.
class Win32
{
  public:
    void Create(std::string name);
    void Destroy();
  private:
    WNDCLASSEX mWindowClass;
    HINSTANCE mInstanceHandle;
};

void Win32::Create(std::string name)
{
  mWindowClass.cbSize = sizeof(WNDCLASSEX);
  mWindowClass.style = CS_HREDRAW | CS_VREDRAW | CS_OWNDC;
  mWindowClass.lpfnWndProc = Tool::WinProc;
  mWindowClass.cbClsExtra = 0;
  mWindowClass.cbWndExtra = 0;
  mWindowClass.hInstance = mInstanceHandle;
  mWindowClass.hIcon = LoadIcon(nullptr, IDI_APPLICATION);
  mWindowClass.hCursor = LoadCursor(nullptr, IDC_ARROW);
  mWindowClass.hbrBackground = (HBRUSH)(COLOR_WINDOW+1);
  mWindowClass.lpszMenuName = nullptr;
  mWindowClass.lpszClassName = name.c_str();
  mWindowClass.hIconSm = LoadIcon(nullptr, IDI_APPLICATION);
  RegisterClassEx(&mWindowClass);
}

void Win32::Destroy()
{
  UnregisterClass(mWindowClass.lpszClassName, mInstanceHandle);
}

I’ve omitted some tests and some other bits which aren’t really important for this post. But the gist of it is there, and it’s mostly fairly trivial.
Can you stop my one, HUGE, mistake there?

Run this code and watch it go up in smoke. The UnregisterClass() function in the Destroy() method will break and quite badly, in fact when I ran it, it reported that the class in question doesn’t even exist. But, but, I’ve registered it, I know I did and the RegisterClass() function worked quite fine, nothing broken there, so, what’s the problem??

A bit of debugging later and I found that the mWindowClass.lpszClassName in the Destroy function contains garbage. Apparently somewhere betweeen calling Create() and Destroy() something bad happened to the lpszClassName [have I mentioned how much I dislike this naming convention??]

Bit more of debugging, running through the breakpoints and examining the contents of the memory and…

Pointers…. Who the hell had the brilliant idea to use a naked char* for the window class name in the WNDCLASSEX [that’s WIN32 API for you Linux, Apple, or other OS people other there].

That should’ve given you the answer by now, if not, then here it goes.

When we call the Create function it generates the name string temporary on the stack and continues on. Then at some later point we’re assigning the name.c_str() to the mWindowClass.lpszClassName – this is a pointer, it’s not a true assignment of values but rather the char* is now pointing to the beginning of the temporary array of characters that is name. Everything works fine inside the Create, we finish what we have to do and leave the function. Woosh! The function temporaries [being temporary] get deleted, erased and/or filled with garbage and the mWindowClass.lpszClassName is now pointing at, GARBAGE!

Yey, found the bug; argh, should have been more careful with my pointers. Fixing it isn’t hard, just introduce a string variable in the Win32 class to hold the name through the life-duration of the class itself.

I should have done it this way originally but I thought I’d be smart about things and save some memory. The moral of the story is, as usual, code correctly, make sure everything is expressed properly and stop trying to be too smart for my own good.

It’s been a long December and there’s reason to believe next year will be better than the last…





Should I join a union?

10 08 2010

arg, not managing to keep up with every 3 days. I’ll try again. It isn’t that I don’t want to, but I’ve been knee-deep in matrix maths [trying to make sure that the inverse of a generic matrix4 is correct took me 3 A4 pages] it just doesn’t seem like an interesting topic to post about. But then again why not? I won’t post my treatment of the Matrix4 pages since that would surely make anyone reading this [including myself] cross-eyed and probably a bit green in the face, so I’ll post about something else. Unions.

Unions are interesting little beasts. They give us the ability to layout different data in a single memory block [calculated to the largest data member]. Let’s illustrate this with a simple example;
union Data{
  float a;
  int b;
};

Now we got a memory block the size of a float which can be accessed as either a float or an int [not both at once]. Its a pretty powerful tool which can also be used for some pretty bad things; I won’t detail it here but google up a union cast and you’ll see what I mean.

For a more relevant example imagine the following idea:
union Data{
  float m[4];
  float mm[2][2];
};

Hey, that sort of looks familiar doesn’t it? That’s because it’s a good candidate for laying out the memory block of a matrix [which is what I’ve done].

The other nice feature about unions is that unlike their C bretherns which are only PODs [Plain Old Data], a C++ union is actually a limited type of class. This means unions also support functions, constructors, etc. What’s the limited aspect of the union? For one, a union can’t be used as a base class, nor is it allowed to have a base class or virtual functions [ie. unions cannot participate in runtime polymorphism, although they do support static, template-based, polymorphism]. And finally, unions can’t have static variables.

I’ve embedded a union [data] member in each of my matrix classes on the public scope, this allows me to control the data layout and access easily from the union class [as well as change it if I want] and gives me the freedom to change the underlying data without worrying too much about clients [ie. Me] needing to interface that data directly.

The code looks similiar to this:
template<size_t R, size_t C, typename T>
union Data{
    T& operator()(size_t i) { return m[i]; }
    T& operator()(size_t r, size_t c) { return mm[r][c]; }
  private:
    T m[R*C];
    T mm[R][C];
};

And the code for the matrix class:
struct M2{
  Data<2,2,float> component;
};

It’s fairly easy now to simply create more and more matrices [and vectors] of different values and sizes and costumize them to fit my needs. It doesn’t mean it’s the best solution, but it’s one of them and the more we know, the better we can adapt for future requirements.

I’m off, the dishes are done, my coffee is waiting and I’ve got to hook up OpenGL tonight so I can finally show some progress to my [very patient] artist.

“Outside on a winter’s night as a rain begins to fall”





Pebbles, Sand and Milk

5 08 2010

Well, there’s this old story about a glass, some pebbles, sand and milk [or beer for those of you that still drink the stuff]. I’m not going to repeat it, look it up it’s an amusing little bit. Bottom line says that the order of actions matter as much as the actions themselves; a good lesson all around and never more fitting for me than yesterday.

I’ve gone back to change a little functionality in one of my matrix classes. It wasn’t anything groundbreaking and I figured, go in, take 20 minutes [expected it to take 10 really] and get back to my other project. Ha, I should’ve known better than that. It’s the little things that matter.

The code that gave me trouble was this:
struct Matrix2Fixture
{
  Matrix2 matrix;
  Matrix2::value_type m0;
  Matrix2::value_type m1;
  Matrix2::value_type m2;
  Matrix2::value_type m3;
  ~Matrix2Fixture(){}
  Matrix2Fixture()
  : m0(0)
  , m1(1)
  , m2(2)
  , m3(3)
  , matrix(m0,m1,m2,m3)
{}
};

Compile, run and go. In theory.
Compile run and watch ALL of my tests fail was the harder reality… But, why?

A few breakpoints, a few couts, I even checked the order of construction of the matrix hierarchy [it’s a little hierarchy to specialize the top most data struct, nothing major and no virtual functions in sight]. Everything seemed to be in order, yet the Matrix2 constructor kept getting garbage. I was a bit frustrated, went out for coffee.

An hour later [of a 10 minute job] and something tickled the dark regions of my brain. Hmm…
The order of construction of static objects across multiple compilation units is undefined; I know it, you know it, every C++ programmer knows it. But what about the order of initialization of member variables within the object constructor?

And it hit me, like a truck, it’s not about the initialization list, it’s about the declaration order.
struct Matrix2Fixture
{
  Matrix2::value_type m0;
  Matrix2::value_type m1;
  Matrix2::value_type m2;
  Matrix2::value_type m3;
  Matrix2 matrix;
  ~Matrix2Fixture(){}
  Matrix2Fixture()
  : m0(0)
  , m1(1)
  , m2(2)
  , m3(3)
  , matrix(m0,m1,m2,m3)
{}
};

Spot the differences. That works, all is good and I’ve learnt not to try to drink my milk before I put sand and pebbles in… Or coffee, whatever tickles your fancy.

“The sun is the same in a relative way but we’re older, shorter of breath and one day closer to death”