//
//  QSICommon.m
//  QSICamera
//
//  Generic Common Types
//
//  Copyright (c) 2011, 2012, Joe Shimkus
//   All rights reserved.
//
//  Redistribution and use in source and binary forms, with or without
//  modification, are permitted provided that the following conditions are
//  met:
//  	• 	Redistributions of source code must retain the above copyright
//      	notice, this list of conditions and the following disclaimer.
//  	• 	Redistributions in binary form must reproduce the above copyright
//        notice, this list of conditions and the following disclaimer in the
//        documentation and/or other materials provided with the distribution.
//  	• 	The name of Joe Shimkus may not be used to endorse or promote
//        products derived from this software without specific prior written
//        permission.
//
//  THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS
//  IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED
//  TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A
//  PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER
//  OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
//  EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
//  PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
//  PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
//  LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
//  NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
//  SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
//

#import "QSICommon.h"

#import <libkern/OSAtomic.h>

static  OSSpinLock        qsiLoggingSpinLock  = 0;  // Start unlocked.

static  QSILoggingMethod  qsiLoggingMethod    = NSLog;

QSILoggingMethod
QSISetLoggingMethod(QSILoggingMethod aLoggingMethod)
{
  OSSpinLockLock(&qsiLoggingSpinLock);

  QSILoggingMethod  oldMethod = qsiLoggingMethod;

  qsiLoggingMethod = aLoggingMethod;

  OSSpinLockUnlock(&qsiLoggingSpinLock);

  return (oldMethod);
} // end QSISetLoggingMethod()

void
QSILogMessage(NSString *aFormatString, ...)
{
  OSSpinLockLock(&qsiLoggingSpinLock);

  if (qsiLoggingMethod != NULL)
  {
    va_list args;

    va_start(args, aFormatString);

    NSString  *argumentString = [[NSString alloc] initWithFormat:aFormatString arguments:args];

    if (argumentString != nil)
    {
      qsiLoggingMethod(@"%@", argumentString);
    }

    [argumentString release];

    va_end(args);
  }

  OSSpinLockUnlock(&qsiLoggingSpinLock);
} // end QSILogMessage()

NSString *
qsiStatusText(QSIStatus aStatus)
{
  NSString *  statusText;

  switch (aStatus)
  {
  case QSISuccess:
    statusText = @"Success";
    break;

  case QSIFailure:
    statusText = @"Generic Failure";
    break;

  case QSIAllocationFailed:
    statusText = @"Allocation Failed";
    break;

  case QSICloseFailed:
    statusText = @"Close Failed";
    break;

  case QSICommandFailed:
    statusText = @"Command Failed";
    break;

  case QSIConnected:
    statusText = @"Connected";
    break;

  case QSIControlFailed:
    statusText = @"Control Failed";
    break;

  case QSIInvalidParameter:
    statusText = @"Invalid Parameter";
    break;

  case QSINoExposure:
    statusText = @"No Exposure";
    break;

  case QSINoFilter:
    statusText = @"No Filter";
    break;

  case QSINoImage:
    statusText = @"No Image";
    break;

  case QSINoMemory:
    statusText = @"No Memory";
    break;

  case QSINotConnected:
    statusText = @"Not Connected";
    break;

  case QSINotSupported:
    statusText = @"Not Supported";
    break;

  case QSIOpenFailed:
    statusText = @"Open Failed";
    break;

  case QSIReadFailed:
    statusText = @"Read Failed";
    break;

  case QSIWriteFailed:
    statusText = @"Write Failed";
    break;

  default:
    statusText = @"Unknown status value";
    break;
  }

  return (statusText);
} // end qsiStatusText()
