1 /** 2 * Copyright: Copyright (c) 2011 Jacob Carlborg. All rights reserved. 3 * Authors: Jacob Carlborg 4 * Version: Initial created: Oct 1, 2011 5 * License: $(LINK2 http://www.boost.org/LICENSE_1_0.txt, Boost Software License 1.0) 6 */ 7 module clang.Util; 8 9 import clang.c.Index; 10 11 import std.conv; 12 import std.stdio; 13 14 immutable(char*)* strToCArray(string[] arr) @safe { 15 import std.string : toStringz; 16 17 if (!arr) 18 return null; 19 20 immutable(char*)[] cArr; 21 cArr.reserve(arr.length); 22 23 foreach (str; arr) 24 cArr ~= str.toStringz; 25 26 return &cArr[0]; 27 } 28 29 /** 30 * Trusted: on the assumption that clang_getCString is implemented by the LLVM 31 * community. Any bugs in them should by now be found. 32 */ 33 string toD(CXString cxString) @trusted { 34 auto cstr = clang_getCString(cxString); 35 auto str = to!(string)(cstr).idup; 36 clang_disposeString(cxString); 37 38 return str; 39 } 40 41 U* toCArray(U, T)(T[] arr) @safe { 42 if (!arr) 43 return null; 44 45 static if (is(typeof(T.init.cx))) 46 return arr.map!(e => e.cx).toArray.ptr; 47 48 else 49 return &arr[0]; 50 } 51 52 template isCX(T) { 53 enum bool isCX = __traits(hasMember, T, "cx"); 54 } 55 56 template cxName(T) { 57 enum cxName = "CX" ~ T.stringof; 58 } 59 60 mixin template CX(string name = "") { 61 static if (name.length == 0) { 62 mixin("private alias CType = " ~ cxName!(typeof(this)) ~ ";"); 63 } else { 64 mixin("private alias CType = CX" ~ name ~ ";"); 65 } 66 67 CType cx; 68 alias cx this; 69 70 /** Trusted: on the assumption that dispose as implemented by the LLVM 71 * community is good _enough_. Any bugs should by now have been found. 72 */ 73 void dispose() @trusted { 74 if (cx is CType.init) 75 return; 76 77 static if (name.length == 0) 78 enum methodName = "clang_dispose" ~ typeof(this).stringof; 79 else 80 enum methodName = "clang_dispose" ~ name; 81 enum methodCall = methodName ~ "(cx);"; 82 83 static if (__traits(hasMember, clang.c.Index, methodName)) 84 mixin(methodCall); 85 else 86 pragma(msg, 87 "info: (this is not an error or problem, just a note to dextool developers) clang dispose not found: " 88 ~ methodName); 89 90 cx = CType.init; 91 } 92 93 @property bool isValid() @safe pure nothrow const @nogc { 94 return cx !is CType.init; 95 } 96 }