The device context is NULL when you call Ellipse and the brush must be selected into the device context prior to calling Ellipse - ie you have the order wrong. You're also using GetDC unnecessarily. Just change your DrawEllipse function so it takes two parameters(HWND and HDC) and send the device context obtain from BeginPaint in your WM_PAINT handler as the second argument:
Code:
case WM_PAINT :
  hdc = BeginPaint (hwnd, &ps) ;
  /*...*/
  DrawEllipse (hwnd,hdc) ;
  /*...*/
  return 0 ;

void DrawEllipse (HWND hwnd,HDC hdc) /*<-- dc sent to this function now*/
{
  /*create and select gdi brush*/
  HBRUSH hbr = CreateSolidBrush (RGB (rand () % 256, rand () % 256, rand () % 256)) ;
  HBRUSH hOld = (HBRUSH) SelectObject (hdc,hbr);
  /*draw ellipse*/
  Ellipse (hdc,rand () % cxClient, rand () % cyClient,
           rand () % cxClient, rand () % cyClient) ;
  /*restore device context's original, default brush object*/
  SelectObject (hdc,hOld) ;
  /*free brush resources back to system*/
  DeleteObject (hbr) ;
}