#ifndef UTILS_H
#define UTILS_H

#include <windows.h>
#include <string.h>
#include "config.h"

// Calculate if a (positive) number is a power of two or not
inline bool IsPowerTwo(int a)
{
    int rep = 1;
    while((rep <<= 1) < a);
    return (rep == a);
}

// Calculate the nearest power of two superior to a given
// (positive) number
inline int NearestPowerTwoSup(int a)
{
    int rep = 1;
    while((rep <<= 1) < a);
    return rep;
}

template<class T>
inline T WinGetLong(HWND hwnd, int which = GWL_USERDATA)
{
    return reinterpret_cast<T> (::GetWindowLong(hwnd, which));
}

template<class T>
inline void WinSetLong(HWND hwnd, T value, int which = GWL_USERDATA)
{
    ::SetWindowLong(hwnd, which, reinterpret_cast<long>(value));
}

#define TRYCATCH_BLOCK1(command, message) \
  try \
    { \
    (command);\
    } \
  catch(WinException e) \
    { \
    ::MessageBox(hwnd, e.GetMessage(), (message), \
                 MB_ICONEXCLAMATION | MB_SYSTEMMODAL | MB_OK); \
    return FAIL;\
    } \
  catch(...) \
    { \
    ::MessageBox(hwnd, "Erreur inconnue", (message), \
                 MB_ICONEXCLAMATION | MB_SYSTEMMODAL | MB_OK); \
    return FAIL; \
    }
    
#define TRYCATCH_BLOCK2(command1, command2, message) \
  try \
    { \
    (command1);\
    (command2);\
    } \
  catch(WinException e) \
    { \
    ::MessageBox(hwnd, e.GetMessage(), (message), \
                 MB_ICONEXCLAMATION | MB_SYSTEMMODAL | MB_OK); \
    return FAIL; \
    } \
  catch(...) \
    { \
    ::MessageBox(hwnd, "Erreur inconnue", (message), \
                 MB_ICONEXCLAMATION | MB_SYSTEMMODAL | MB_OK); \
    return FAIL; \
    }    

#endif // UTILS_H
