@ -11,27 +11,14 @@ namespace CppSharp.Generators.CSharp
public enum CSharpTypePrinterContextKind
public enum CSharpTypePrinterContextKind
{
{
Native ,
Native ,
Managed ,
Managed
ManagedPointer ,
GenericDelegate ,
DefaultExpression
}
}
public class CSharpTypePrinterContext : TypePrinterContext
public class CSharpTypePrinterContext : TypePrinterContext
{
{
public CSharpTypePrinterContextKind CSharpKind ;
public CSharpTypePrinterContextKind CSharpKind ;
public CSharpMarshalKind MarshalKind ;
public QualifiedType FullType ;
public QualifiedType FullType ;
public CSharpTypePrinterContext ( )
{
}
public CSharpTypePrinterContext ( TypePrinterContextKind kind ,
CSharpTypePrinterContextKind csharpKind ) : base ( kind )
{
CSharpKind = csharpKind ;
}
}
}
public class CSharpTypePrinterResult
public class CSharpTypePrinterResult
@ -42,7 +29,7 @@ namespace CppSharp.Generators.CSharp
public static implicit operator CSharpTypePrinterResult ( string type )
public static implicit operator CSharpTypePrinterResult ( string type )
{
{
return new CSharpTypePrinterResult ( ) { Type = type } ;
return new CSharpTypePrinterResult { Type = type } ;
}
}
public override string ToString ( )
public override string ToString ( )
@ -57,12 +44,18 @@ namespace CppSharp.Generators.CSharp
private readonly Driver driver ;
private readonly Driver driver ;
private readonly Stack < CSharpTypePrinterContextKind > contexts ;
private readonly Stack < CSharpTypePrinterContextKind > contexts ;
private readonly Stack < CSharpMarshalKind > marshalKinds ;
public CSharpTypePrinterContextKind ContextKind
public CSharpTypePrinterContextKind ContextKind
{
{
get { return contexts . Peek ( ) ; }
get { return contexts . Peek ( ) ; }
}
}
public CSharpMarshalKind MarshalKind
{
get { return marshalKinds . Peek ( ) ; }
}
public CSharpTypePrinterContext Context ;
public CSharpTypePrinterContext Context ;
public CSharpTypePrinter ( Driver driver )
public CSharpTypePrinter ( Driver driver )
@ -70,7 +63,9 @@ namespace CppSharp.Generators.CSharp
this . driver = driver ;
this . driver = driver ;
contexts = new Stack < CSharpTypePrinterContextKind > ( ) ;
contexts = new Stack < CSharpTypePrinterContextKind > ( ) ;
marshalKinds = new Stack < CSharpMarshalKind > ( ) ;
PushContext ( CSharpTypePrinterContextKind . Managed ) ;
PushContext ( CSharpTypePrinterContextKind . Managed ) ;
PushMarshalKind ( CSharpMarshalKind . Unknown ) ;
Context = new CSharpTypePrinterContext ( ) ;
Context = new CSharpTypePrinterContext ( ) ;
}
}
@ -85,16 +80,27 @@ namespace CppSharp.Generators.CSharp
return contexts . Pop ( ) ;
return contexts . Pop ( ) ;
}
}
public void PushMarshalKind ( CSharpMarshalKind marshalKind )
{
marshalKinds . Push ( marshalKind ) ;
}
public CSharpMarshalKind PopMarshalKind ( )
{
return marshalKinds . Pop ( ) ;
}
public CSharpTypePrinterResult VisitTagType ( TagType tag , TypeQualifiers quals )
public CSharpTypePrinterResult VisitTagType ( TagType tag , TypeQualifiers quals )
{
{
if ( tag . Declaration = = null )
if ( tag . Declaration = = null )
return string . Empty ;
return string . Empty ;
TypeMap typeMap ;
TypeMap typeMap ;
if ( this . driver . TypeDatabase . FindTypeMap ( tag . Declaration , out typeMap ) )
if ( driver . TypeDatabase . FindTypeMap ( tag . Declaration , out typeMap ) )
{
{
typeMap . Type = tag ;
typeMap . Type = tag ;
Context . CSharpKind = ContextKind ;
Context . CSharpKind = ContextKind ;
Context . MarshalKind = MarshalKind ;
Context . Type = tag ;
Context . Type = tag ;
string type = typeMap . CSharpSignature ( Context ) ;
string type = typeMap . CSharpSignature ( Context ) ;
@ -160,12 +166,12 @@ namespace CppSharp.Generators.CSharp
var returnType = function . ReturnType ;
var returnType = function . ReturnType ;
var args = string . Empty ;
var args = string . Empty ;
PushContext ( CSharpTypePrinterContext Kind . GenericDelegate ) ;
PushMarshalKind ( CSharpMarshal Kind . GenericDelegate ) ;
if ( arguments . Count > 0 )
if ( arguments . Count > 0 )
args = VisitParameters ( function . Parameters , hasNames : false ) . Type ;
args = VisitParameters ( function . Parameters , hasNames : false ) . Type ;
PopContext ( ) ;
PopMarshalKind ( ) ;
if ( ContextKind ! = CSharpTypePrinterContextKind . Managed )
if ( ContextKind ! = CSharpTypePrinterContextKind . Managed )
return "global::System.IntPtr" ;
return "global::System.IntPtr" ;
@ -180,11 +186,11 @@ namespace CppSharp.Generators.CSharp
if ( ! string . IsNullOrEmpty ( args ) )
if ( ! string . IsNullOrEmpty ( args ) )
args = string . Format ( ", {0}" , args ) ;
args = string . Format ( ", {0}" , args ) ;
PushContext ( CSharpTypePrinterContext Kind . GenericDelegate ) ;
PushMarshalKind ( CSharpMarshal Kind . GenericDelegate ) ;
var returnTypePrinterResult = returnType . Visit ( this ) ;
var returnTypePrinterResult = returnType . Visit ( this ) ;
PopContext ( ) ;
PopMarshalKind ( ) ;
return string . Format ( "Func<{0}{1}>" , returnTypePrinterResult , args ) ;
return string . Format ( "Func<{0}{1}>" , returnTypePrinterResult , args ) ;
}
}
@ -215,7 +221,7 @@ namespace CppSharp.Generators.CSharp
return IsConstCharString ( qualType . Type ) ;
return IsConstCharString ( qualType . Type ) ;
}
}
bool A llowStrings = true ;
private bool a llowStrings = true ;
public CSharpTypePrinterResult VisitPointerType ( PointerType pointer ,
public CSharpTypePrinterResult VisitPointerType ( PointerType pointer ,
TypeQualifiers quals )
TypeQualifiers quals )
@ -230,7 +236,7 @@ namespace CppSharp.Generators.CSharp
var isManagedContext = ContextKind = = CSharpTypePrinterContextKind . Managed ;
var isManagedContext = ContextKind = = CSharpTypePrinterContextKind . Managed ;
if ( A llowStrings & & IsConstCharString ( pointer ) )
if ( a llowStrings & & IsConstCharString ( pointer ) )
return isManagedContext ? "string" : "global::System.IntPtr" ;
return isManagedContext ? "string" : "global::System.IntPtr" ;
var desugared = pointee . Desugar ( ) ;
var desugared = pointee . Desugar ( ) ;
@ -251,15 +257,15 @@ namespace CppSharp.Generators.CSharp
if ( isManagedContext & & isRefParam )
if ( isManagedContext & & isRefParam )
return pointee . Visit ( this , quals ) ;
return pointee . Visit ( this , quals ) ;
if ( ContextKind = = CSharpTypePrinterContext Kind. GenericDelegate | |
if ( MarshalKind = = CSharpMarshal Kind. GenericDelegate | |
pointee . IsPrimitiveType ( PrimitiveType . Void ) )
pointee . IsPrimitiveType ( PrimitiveType . Void ) )
return "global::System.IntPtr" ;
return "global::System.IntPtr" ;
// Do not allow strings inside primitive arrays case, else we'll get invalid types
// Do not allow strings inside primitive arrays case, else we'll get invalid types
// like string* for const char **.
// like string* for const char **.
A llowStrings = isRefParam ;
a llowStrings = isRefParam ;
var result = pointee . Visit ( this , quals ) ;
var result = pointee . Visit ( this , quals ) ;
A llowStrings = true ;
a llowStrings = true ;
return ! isRefParam & & result . Type = = "global::System.IntPtr" ? "void**" : result + "*" ;
return ! isRefParam & & result . Type = = "global::System.IntPtr" ? "void**" : result + "*" ;
}
}
@ -297,9 +303,6 @@ namespace CppSharp.Generators.CSharp
// TODO: Non-function member pointer types are tricky to support.
// TODO: Non-function member pointer types are tricky to support.
// Re-visit this.
// Re-visit this.
return "global::System.IntPtr" ;
return "global::System.IntPtr" ;
throw new InvalidOperationException (
"A function pointer not pointing to a function type." ) ;
}
}
public CSharpTypePrinterResult VisitBuiltinType ( BuiltinType builtin ,
public CSharpTypePrinterResult VisitBuiltinType ( BuiltinType builtin ,
@ -314,10 +317,11 @@ namespace CppSharp.Generators.CSharp
var decl = typedef . Declaration ;
var decl = typedef . Declaration ;
TypeMap typeMap ;
TypeMap typeMap ;
if ( this . driver . TypeDatabase . FindTypeMap ( decl , out typeMap ) )
if ( driver . TypeDatabase . FindTypeMap ( decl , out typeMap ) )
{
{
typeMap . Type = typedef ;
typeMap . Type = typedef ;
Context . CSharpKind = ContextKind ;
Context . CSharpKind = ContextKind ;
Context . MarshalKind = MarshalKind ;
Context . Type = typedef ;
Context . Type = typedef ;
string type = typeMap . CSharpSignature ( Context ) ;
string type = typeMap . CSharpSignature ( Context ) ;
@ -360,7 +364,7 @@ namespace CppSharp.Generators.CSharp
{
{
var decl = template . Template . TemplatedDecl ;
var decl = template . Template . TemplatedDecl ;
TypeMap typeMap = null ;
TypeMap typeMap ;
if ( ! driver . TypeDatabase . FindTypeMap ( template , out typeMap ) )
if ( ! driver . TypeDatabase . FindTypeMap ( template , out typeMap ) )
return GetNestedQualifiedName ( decl ) +
return GetNestedQualifiedName ( decl ) +
( ContextKind = = CSharpTypePrinterContextKind . Native
( ContextKind = = CSharpTypePrinterContextKind . Native
@ -370,6 +374,7 @@ namespace CppSharp.Generators.CSharp
typeMap . Type = template ;
typeMap . Type = template ;
Context . Type = template ;
Context . Type = template ;
Context . CSharpKind = ContextKind ;
Context . CSharpKind = ContextKind ;
Context . MarshalKind = MarshalKind ;
var type = GetCSharpSignature ( typeMap ) ;
var type = GetCSharpSignature ( typeMap ) ;
if ( ! string . IsNullOrEmpty ( type ) )
if ( ! string . IsNullOrEmpty ( type ) )
@ -389,6 +394,7 @@ namespace CppSharp.Generators.CSharp
private string GetCSharpSignature ( TypeMap typeMap )
private string GetCSharpSignature ( TypeMap typeMap )
{
{
Context . CSharpKind = ContextKind ;
Context . CSharpKind = ContextKind ;
Context . MarshalKind = MarshalKind ;
return typeMap . CSharpSignature ( Context ) ;
return typeMap . CSharpSignature ( Context ) ;
}
}
@ -493,7 +499,7 @@ namespace CppSharp.Generators.CSharp
{
{
case PrimitiveType . Bool :
case PrimitiveType . Bool :
// returned structs must be blittable and bool isn't
// returned structs must be blittable and bool isn't
return ContextKind = = CSharpTypePrinterContext Kind. Native ?
return MarshalKind = = CSharpMarshal Kind. NativeField ?
"byte" : "bool" ;
"byte" : "bool" ;
case PrimitiveType . Void : return "void" ;
case PrimitiveType . Void : return "void" ;
case PrimitiveType . Char16 :
case PrimitiveType . Char16 :
@ -513,7 +519,7 @@ namespace CppSharp.Generators.CSharp
case PrimitiveType . ULong :
case PrimitiveType . ULong :
case PrimitiveType . LongLong :
case PrimitiveType . LongLong :
case PrimitiveType . ULongLong :
case PrimitiveType . ULongLong :
return GetIntString ( primitive , this . driver . TargetInfo ) ;
return GetIntString ( primitive , driver . TargetInfo ) ;
case PrimitiveType . Float : return "float" ;
case PrimitiveType . Float : return "float" ;
case PrimitiveType . Double : return "double" ;
case PrimitiveType . Double : return "double" ;
case PrimitiveType . IntPtr : return "global::System.IntPtr" ;
case PrimitiveType . IntPtr : return "global::System.IntPtr" ;