text: /*******************************************************************************
   * Copyright (c) 2012, Jean-David Gadina - www.xs-labs.com
   * All rights reserved.
   * 
   * Boost Software License - Version 1.0 - August 17th, 2003
   * 
   * Permission is hereby granted, free of charge, to any person or organization
   * obtaining a copy of the software and accompanying documentation covered by
   * this license (the "Software") to use, reproduce, display, distribute,
   * execute, and transmit the Software, and to prepare derivative works of the
   * Software, and to permit third-parties to whom the Software is furnished to
   * do so, all subject to the following:
   * 
   * The copyright notices in the Software and this entire statement, including
   * the above license grant, this restriction and the following disclaimer,
   * must be included in all copies of the Software, in whole or in part, and
   * all derivative works of the Software, unless such copies or derivative
   * works are solely in the form of machine-executable object code generated by
   * a source language processor.
   * 
   * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
   * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
   * FITNESS FOR A PARTICULAR PURPOSE, TITLE AND NON-INFRINGEMENT. IN NO EVENT
   * SHALL THE COPYRIGHT HOLDERS OR ANYONE DISTRIBUTING THE SOFTWARE BE LIABLE
   * FOR ANY DAMAGES OR OTHER LIABILITY, WHETHER IN CONTRACT, TORT OR OTHERWISE,
   * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
   * DEALINGS IN THE SOFTWARE.
   ******************************************************************************/
   
  /* $Id$ */
  
  /*!
   * @file            main.m
   * @copyright       (c) 2010-2014 - Jean-David Gadina - www.xs-labs.com
   * @author          Jean-David Gadina - www.xs-labs.com
   * @abstract        ClangKit test / demo project
   */
  
  static NSString * GetClangIncludePath( void );
  
  int main( void )
  {
      CKTranslationUnit * tu;
      CKDiagnostic      * d;
      NSString          * inc;
      NSMutableArray    * args;
      
      @autoreleasepool
      {
          inc  = GetClangIncludePath();
          args = [ NSMutableArray arrayWithObject: @"-Weverything" ];
          
          if( inc != nil )
          {
              [ args addObject: [ @"-I" stringByAppendingString: inc ] ];
          }
          
          /* First create a translation unit for Objective-C, using a string */
          tu = [ CKTranslationUnit    translationUnitWithText:    @"int main( void ) { return 0; }"
                                      language:                   CKLanguageObjC
                                      args:                       args
               ];
          
          /* Logs each diagnostic and fix-its */
          for( d in tu.diagnostics )
          {
              NSLog( @"Diagnostic: %@", d );
              NSLog( @"FixIts: %@", d.fixIts );
          }
          
          /* Logs the available tokens */
          NSLog( @"%@", tu.tokens );
          
          /* Changes the code, using the 'text' property */
          tu.text =   @"#import <Foundation/Foundation.h>\n"
                      @"\n"
                      @"@interface Foo: NSObject\n"
                      @"{}\n"
                      @"@end\n"
                      @"\n"
                      @"int main( void )\n"
                      @"{\n"
                      @"    NSString * x;\n"
                      @"    Foo      * f;\n"
                      @"    \n"
                      @"return 1;\n"
                      @"}\n";
          
          /* Logs each diagnostic and fix-its */
          for( d in tu.diagnostics )
          {
              NSLog( @"Diagnostic: %@", d );
              NSLog( @"FixIts: %@", d.fixIts );
          }
          
          /* Logs the available tokens */
          NSLog( @"%@", tu.tokens );
      }
      
      return 0;
  }
  
  static NSString * GetClangIncludePath( void )
  {
      CFURLRef   url;
      NSString * path;
      NSString * sub;
      OSStatus   res;
      BOOL       isDir;
      
      res = LSFindApplicationForInfo
      (
          kLSUnknownCreator,
          CFSTR( "com.apple.dt.Xcode" ),
          NULL,
          NULL,
          &url
      );
      
      if( res == noErr )
      {
          path = ( __bridge_transfer NSString * )CFURLCopyPath( url );
          
          CFRelease( url );
          
          path = [ path stringByAppendingPathComponent: @"Contents" ];
          path = [ path stringByAppendingPathComponent: @"Developer" ];
          path = [ path stringByAppendingPathComponent: @"Toolchains" ];
          path = [ path stringByAppendingPathComponent: @"XcodeDefault.xctoolchain" ];
          path = [ path stringByAppendingPathComponent: @"usr" ];
          path = [ path stringByAppendingPathComponent: @"lib" ];
          path = [ path stringByAppendingPathComponent: @"clang" ];
          
          if( [ [ NSFileManager defaultManager ] fileExistsAtPath: path isDirectory: &isDir ] == NO || isDir == NO )
          {
              return nil;
          }
          
          for( sub in [ [ NSFileManager defaultManager ] contentsOfDirectoryAtPath: path error: NULL ] )
          {
              sub = [ [ path stringByAppendingPathComponent: sub ] stringByAppendingPathComponent: @"include" ];
              
              if( [ [ NSFileManager defaultManager ] fileExistsAtPath: sub isDirectory: &isDir ] && isDir )
              {
                  return sub;
              }
          }
      }
      
      return nil;
  }
  