Here's a quick macro to assist with blocks of successive calls that should proceed as long as none of them satisfy FAILED( operation ).

// WHILE_SUCCEEDED:
//     HRESULT hr = S_OK;
//     WHILE_SUCCEEDED( hr, function_returning_HRESULT() )
#define WHILE_SUCCEEDED( hr, operation )	( SUCCEEDED( (hr) ) && ( hr = (operation) ) );

CppUnit Test:

HRESULT hr = S_OK;
 
WHILE_SUCCEEDED(hr, S_OK)
CPPUNIT_ASSERT( SUCCEEDED( hr ) );
CPPUNIT_ASSERT_EQUAL( S_OK, hr );
 
WHILE_SUCCEEDED(hr, S_FALSE)
CPPUNIT_ASSERT( SUCCEEDED( hr ) );
CPPUNIT_ASSERT_EQUAL( S_FALSE, hr );
 
WHILE_SUCCEEDED(hr, E_OUTOFMEMORY)
CPPUNIT_ASSERT( FAILED( hr ) );
CPPUNIT_ASSERT_EQUAL( E_OUTOFMEMORY, hr );
 
HRESULT hrPrevious = hr;
bool executed = false;
// Test that executed = true should not be executed
WHILE_SUCCEEDED(hr, ( executed = true, S_FALSE ) )
CPPUNIT_ASSERT( FAILED( hr ) );          // hr should not have been assigned S_FALSE
CPPUNIT_ASSERT( ! executed );            // executed = true should not have been executed
CPPUNIT_ASSERT_EQUAL( hrPrevious, hr );  // hr should not have a different value than previously assigned
  • Digg
  • del.icio.us
  • Facebook
  • Twitter
  • Technorati
  • email
  • Print
  • PDF
  • StumbleUpon
  • Yahoo! Buzz
  • Google Bookmarks
  • DotNetKicks
  • FriendFeed
  • Google Buzz
  • Live
  • Netvibes
  • Slashdot
  • Add to favorites