// RuntimeForStatic base library | C+- (SysRoutine) | Author: Sergei Y.Kitáev
#include "Precompiled.h"
#include "SharedIncludes.h"
namespace RuntimeForStatic {
//==================================================================================================

$ErrorInfo::$ErrorInfo() $tenacious
{
   $CLEAR_INSTANCE();
   _Message_ = $DynText();
   ValidateDisposable($$);
}
$ErrorInfo::$ErrorInfo( $ErrorSign sign ) $tenacious
{
   $CLEAR_INSTANCE();
   _ErrorSign_ = sign;
   _Message_ = $DynText();
   ValidateDisposable($$);
}
$ErrorInfo::$ErrorInfo($A, $ErrorSign sign, PCWSTR message $not_null ) $tenacious
{
   $$VERIFY_POINTER_ARG( message );
   $CLEAR_INSTANCE();
   _ErrorSign_ = sign;
   PWSTR text = HelpersRT::DuplicateSZ($, message );
   if ( text )
      _Message_.SetPointer($ci, text );
   else
      _Message_.SetMessage_MemoryAllocationFailure($);
   _OriginalMessageLength_ = _Message_.Length($ci);
   ValidateDisposable($$);
}
$ErrorInfo::$ErrorInfo($A, const $ErrorInfo& errorInfo )
{
   errorInfo.VerifyValidDisposable($$CI);
   _ErrorSign_ = errorInfo._ErrorSign_;
   _Message_ = $DynText($ci, errorInfo._Message_ );
   _OriginalMessageLength_ = errorInfo._OriginalMessageLength_;
   _MessageGenerationProblem_ = errorInfo._MessageGenerationProblem_;
   ValidateDisposable($$);
}

//--------------------------------------------------------------------------------------------------

$ErrorSign $ErrorInfo::ErrorSign($O) const
{
   $$VERIFY_VALID_DISPOSABLE();
   return _ErrorSign_;
}

$DynText $ErrorInfo::Message($O) const $tenacious
{
   bool messageGenerationProblem;
   return Message($ci, messageGenerationProblem );
}
$DynText $ErrorInfo::Message($O,bool& messageGenerationProblem $out) const $tenacious
{
   $$VERIFY_VALID_DISPOSABLE();
   PWSTR text = HelpersRT::DuplicateSZ($, _Message_.T($) );
   messageGenerationProblem = _MessageGenerationProblem_ || text == nullptr;
   auto dt = $DynText();
   if ( text )
      dt.SetPointer($, text );
   else
      dt.SetMessage_MemoryAllocationFailure($);
   return dt;
}

$DynText $ErrorInfo::OriginalMessage($O) const $tenacious
{
   bool messageGenerationProblem;
   return OriginalMessage($ci, messageGenerationProblem );
}
$DynText $ErrorInfo::OriginalMessage($O,bool& messageGenerationProblem $out) const $tenacious
{
   $$VERIFY_VALID_DISPOSABLE();
   PWSTR text = HelpersRT::DuplicateStr($, _Message_.T($), _OriginalMessageLength_ );
   messageGenerationProblem = _MessageGenerationProblem_ || text == nullptr;
   auto dt = $DynText();
   if ( text )
      dt.SetPointer($, text );
   else
      dt.SetMessage_MemoryAllocationFailure($);
   return dt;
}

bool $ErrorInfo::MessageGenerationProblem($O) const
{
   $$VERIFY_VALID_DISPOSABLE();
   return _MessageGenerationProblem_;
}

//==================================================================================================

bool $ErrorInfo::HasError($O) const
{
   $$VERIFY_VALID_DISPOSABLE();
   return _ErrorSign_.HasError;
}
bool $ErrorInfo::Success($O) const
{
   $$VERIFY_VALID_DISPOSABLE();
   return _ErrorSign_.Success;
}
bool $ErrorInfo::IsWarning($O) const
{
   $$VERIFY_VALID_DISPOSABLE();
   return _ErrorSign_.IsWarning;
}

$ErrorType $ErrorInfo::ErrorType($O) const
{
   $$VERIFY_VALID_DISPOSABLE();
   return _ErrorSign_.ErrorType;
}

bool $ErrorInfo::IsWin32Error($O) const
{
   $$VERIFY_VALID_DISPOSABLE();
   return _ErrorSign_.IsWin32Error;
}
bool $ErrorInfo::IsCOMError($O) const
{
   $$VERIFY_VALID_DISPOSABLE();
   return _ErrorSign_.IsCOMError;
}
bool $ErrorInfo::IsWin32OrCOMError($O) const
{
   $$VERIFY_VALID_DISPOSABLE();
   return _ErrorSign_.IsWin32OrCOMError;
}
bool $ErrorInfo::IsCustomError($O) const
{
   $$VERIFY_VALID_DISPOSABLE();
   return _ErrorSign_.IsCustomError;
}

int $ErrorInfo::IntCode($O) const
{
   $$VERIFY_VALID_DISPOSABLE();
   return _ErrorSign_.IntCode;
}
DWORD $ErrorInfo::DWordCode($O) const
{
   $$VERIFY_VALID_DISPOSABLE();
   return _ErrorSign_.DWordCode;
}

DWORD $ErrorInfo::StrictWin32Error($O) const
{
   $$VERIFY_VALID_DISPOSABLE();
   return _ErrorSign_.StrictWin32Error($ci);
}
HRESULT $ErrorInfo::StrictCOMError($O) const
{
   $$VERIFY_VALID_DISPOSABLE();
   return _ErrorSign_.StrictCOMError($ci);
}

DWORD $ErrorInfo::Win32ErrorOrZero($O) const
{
   $$VERIFY_VALID_DISPOSABLE();
   return _ErrorSign_.Win32ErrorOrZero;
}
HRESULT $ErrorInfo::COMErrorOrZero($O) const
{
   $$VERIFY_VALID_DISPOSABLE();
   return _ErrorSign_.COMErrorOrZero;
}

//==================================================================================================

bool $ErrorInfo::AppendMessage($OA,PCWSTR message) $tenacious
{
   $$VERIFY_VALID_DISPOSABLE();
   if ( $SZ::IsEmpty($ci, message ) )
      return true;
   PCWSTR baseText = _Message_.T($);
   PWSTR text = $SZ::IsEmpty($, baseText ) ?
      HelpersRT::DuplicateSZ($, message ) :
      HelpersRT::FormatAlloc($ci,$, L"%s\r\n\r\n%s", baseText, message );
   if ( text )
      _Message_.SetPointer($, text );
   else
      _Message_.SetMessage_MemoryAllocationFailure($);
   return $BOOL( text );
}
bool $ErrorInfo::AppendMessageFmt($OA,PCWSTR messageFmt, ... ) $tenacious
{
   $$VERIFY_VALID_DISPOSABLE();
   $$VERIFY_POINTER_ARG( messageFmt );
   va_list argList;
   bool rslt = AppendMessageVA($ci, $VA_COMPLEMENT( messageFmt, argList ) );
   va_end( argList );
   return rslt;
}
bool $ErrorInfo::AppendMessageVA($OA,PCWSTR messageFmt,va_list argList) $tenacious
{
   $$VERIFY_VALID_DISPOSABLE();
   PWSTR text = HelpersRT::FormatAllocVA($ci,$, messageFmt, argList );
   if ( text )
   {
      bool rslt = AppendMessage($ci, text );
      $Memory::Free( text );
      return rslt;
   }
   _Message_.SetMessage_MemoryAllocationFailure($);
   return false;
}

//--------------------------------------------------------------------------------------------------

bool $ErrorInfo::AppendLastErrorMessage($O) $tenacious
{
   return AppendMessage($ci, $LE::Message().T($) );
}

//--------------------------------------------------------------------------------------------------

void $ErrorInfo::SetMessageGenerationProblem($O)
{
   $$VERIFY_VALID_DISPOSABLE();
   _MessageGenerationProblem_ = true;
}

//==================================================================================================

bool $ErrorInfo::ApplyToLastError($O)
{
   $LE::SetError($ci, *this );
   return Success($ci);
}

//==================================================================================================

void $ErrorInfo::DoDispose($CI_REF)
{
   _Message_.Dispose();
}

//==================================================================================================
} // RuntimeForStatic
