Browse Source

Merge pull request #6 from esdrubal/master

std::vector marshaling, refactorings, WriteOnlyWhenChanged
pull/1/head
João Matos 12 years ago
parent
commit
89db240972
  1. 2
      src/Generator/Driver.cs
  2. 16
      src/Generator/Generators/CLI/CLIGenerator.cs
  3. 3
      src/Generator/Generators/CLI/CLIMarshal.cs
  4. 22
      src/Generator/Generators/CLI/CLISourcesTemplate.cs
  5. 7
      src/Generator/Types/CppTypePrinter.cs
  6. 74
      src/Generator/Types/Std/Stdlib.cs
  7. 2
      src/Generator/Types/TypeMap.cs
  8. 52
      src/Generator/Utils/FileHashes.cs

2
src/Generator/Driver.cs

@ -177,6 +177,7 @@ namespace Cxxi @@ -177,6 +177,7 @@ namespace Cxxi
GeneratorKind = LanguageGeneratorKind.CSharp;
GenerateLibraryNamespace = true;
GenerateFunctionTemplates = false;
WriteOnlyWhenChanged = false;
}
public bool Verbose = false;
@ -200,5 +201,6 @@ namespace Cxxi @@ -200,5 +201,6 @@ namespace Cxxi
public string IncludePrefix;
public string WrapperSuffix;
public LanguageGeneratorKind GeneratorKind;
public bool WriteOnlyWhenChanged;
}
}

16
src/Generator/Generators/CLI/CLIGenerator.cs

@ -1,6 +1,5 @@ @@ -1,6 +1,5 @@
using System;
using System.IO;
using Cxxi.Passes;
using Cxxi.Types;
namespace Cxxi.Generators.CLI
@ -8,11 +7,13 @@ namespace Cxxi.Generators.CLI @@ -8,11 +7,13 @@ namespace Cxxi.Generators.CLI
public class CLIGenerator : Generator
{
private readonly ITypePrinter typePrinter;
private readonly FileHashes fileHashes;
public CLIGenerator(Driver driver) : base(driver)
{
typePrinter = new CLITypePrinter(driver);
Type.TypePrinter = typePrinter;
fileHashes = FileHashes.Load("hashes.ser");
}
void WriteTemplate(TextTemplate template)
@ -22,11 +23,22 @@ namespace Cxxi.Generators.CLI @@ -22,11 +23,22 @@ namespace Cxxi.Generators.CLI
+ template.FileExtension;
var path = Path.Combine(Driver.Options.OutputDir, file);
var fullPath = Path.GetFullPath(path);
template.Generate();
Console.WriteLine(" Generated '" + file + "'.");
File.WriteAllText(Path.GetFullPath(path), template.ToString());
var str = template.ToString();
if(Driver.Options.WriteOnlyWhenChanged)
{
var updated = fileHashes.UpdateHash(path, str.GetHashCode());
if(File.Exists(fullPath) && !updated)
return;
}
File.WriteAllText(fullPath,str);
}
public override bool Generate(TranslationUnit unit)

3
src/Generator/Generators/CLI/CLIMarshal.cs

@ -568,6 +568,9 @@ namespace Cxxi.Generators.CLI @@ -568,6 +568,9 @@ namespace Cxxi.Generators.CLI
foreach (var field in @class.Fields)
{
if(field.Ignore)
continue;
MarshalValueClassField(field, marshalVar);
}
}

22
src/Generator/Generators/CLI/CLISourcesTemplate.cs

@ -251,9 +251,6 @@ namespace Cxxi.Generators.CLI @@ -251,9 +251,6 @@ namespace Cxxi.Generators.CLI
WriteLine("{0} = {1};", variable, marshal.Context.Return);
if (!string.IsNullOrWhiteSpace(marshal.Context.SupportAfter))
Write(marshal.Context.SupportAfter);
WriteCloseBraceIndent();
NewLine();
}
@ -269,6 +266,7 @@ namespace Cxxi.Generators.CLI @@ -269,6 +266,7 @@ namespace Cxxi.Generators.CLI
var ctx = new MarshalContext(Driver)
{
ArgName = field.Name,
ReturnVarName = variable,
ReturnType = field.Type
};
@ -276,6 +274,9 @@ namespace Cxxi.Generators.CLI @@ -276,6 +274,9 @@ namespace Cxxi.Generators.CLI
var marshal = new CLIMarshalNativeToManagedPrinter(ctx);
field.Visit(marshal);
if (!string.IsNullOrWhiteSpace(marshal.Context.SupportBefore))
Write(marshal.Context.SupportBefore);
WriteLine("return {0};", marshal.Context.Return);
WriteCloseBraceIndent();
@ -460,6 +461,7 @@ namespace Cxxi.Generators.CLI @@ -460,6 +461,7 @@ namespace Cxxi.Generators.CLI
var ctx = new MarshalContext(Driver)
{
ArgName = field.Name,
ReturnVarName = nativeField,
ReturnType = field.Type
};
@ -471,9 +473,6 @@ namespace Cxxi.Generators.CLI @@ -471,9 +473,6 @@ namespace Cxxi.Generators.CLI
Write(marshal.Context.SupportBefore);
WriteLine("{0} = {1};", field.Name, marshal.Context.Return);
if (!string.IsNullOrWhiteSpace(marshal.Context.SupportAfter))
Write(marshal.Context.SupportAfter);
}
}
@ -671,10 +670,9 @@ namespace Cxxi.Generators.CLI @@ -671,10 +670,9 @@ namespace Cxxi.Generators.CLI
if (needsReturn)
{
Write("return ");
var ctx = new MarshalContext(Driver)
{
ArgName = "ret",
ReturnVarName = "ret",
ReturnType = retType
};
@ -682,7 +680,10 @@ namespace Cxxi.Generators.CLI @@ -682,7 +680,10 @@ namespace Cxxi.Generators.CLI
var marshal = new CLIMarshalNativeToManagedPrinter(ctx);
function.ReturnType.Visit(marshal);
WriteLine("{0};", marshal.Context.Return);
if (!string.IsNullOrWhiteSpace(marshal.Context.SupportBefore))
Write(marshal.Context.SupportBefore);
WriteLine("return {0};", marshal.Context.Return);
}
}
@ -747,9 +748,6 @@ namespace Cxxi.Generators.CLI @@ -747,9 +748,6 @@ namespace Cxxi.Generators.CLI
WriteLine("auto {0}{1} = {2};", marshal.VarPrefix, argName, marshal.Context.Return);
if (!string.IsNullOrWhiteSpace(marshal.Context.SupportAfter))
Write(marshal.Context.SupportAfter);
var argText = marshal.ArgumentPrefix + argName;
return new ParamMarshal {Name = argText, Param = param};
}

7
src/Generator/Types/CppTypePrinter.cs

@ -93,12 +93,7 @@ namespace Cxxi.Types @@ -93,12 +93,7 @@ namespace Cxxi.Types
public string VisitTypedefType(TypedefType typedef, TypeQualifiers quals)
{
var decl = typedef.Declaration;
if (decl.Type == null)
return string.Empty;
return decl.Type.Visit(this);
return "::" + typedef.Declaration.QualifiedOriginalName;
}
public string VisitTemplateSpecializationType(TemplateSpecializationType template, TypeQualifiers quals)

74
src/Generator/Types/Std/Stdlib.cs

@ -69,8 +69,6 @@ namespace Cxxi.Types.Std @@ -69,8 +69,6 @@ namespace Cxxi.Types.Std
[TypeMap("std::vector")]
public class Vector : TypeMap
{
public override bool IsIgnored { get { return true; } }
public override string CLISignature(TypePrinterContext ctx)
{
return string.Format("System::Collections::Generic::List<{0}>^",
@ -79,12 +77,80 @@ namespace Cxxi.Types.Std @@ -79,12 +77,80 @@ namespace Cxxi.Types.Std
public override void CLIMarshalToNative(MarshalContext ctx)
{
throw new System.NotImplementedException();
var templateType = Type as TemplateSpecializationType;
var type = templateType.Arguments[0].Type;
var entryString = (ctx.Parameter != null) ? ctx.Parameter.Name : ctx.ArgName;
var tmpVarName = "_tmp" + entryString;
var cppTypePrinter = new CppTypePrinter(ctx.Driver.TypeDatabase);
var nativeType = type.Type.Visit(cppTypePrinter);
ctx.SupportBefore.WriteLine("auto {0} = std::vector<{1}>();",
tmpVarName, nativeType);
ctx.SupportBefore.WriteLine("for each({0} _element in {1})",
type.ToString(), entryString);
ctx.SupportBefore.WriteStartBraceIndent();
{
var param = new Parameter
{
Name = "_element",
QualifiedType = type
};
var elementCtx = new MarshalContext(ctx.Driver)
{
Parameter = param,
ArgName = param.Name,
};
var marshal = new CLIMarshalManagedToNativePrinter(elementCtx);
type.Type.Visit(marshal);
if (!string.IsNullOrWhiteSpace(marshal.Context.SupportBefore))
ctx.SupportBefore.Write(marshal.Context.SupportBefore);
ctx.SupportBefore.WriteLine("auto _marshalElement = {0};",
marshal.Context.Return);
ctx.SupportBefore.WriteLine("{0}.push_back(_marshalElement);",tmpVarName);
}
ctx.SupportBefore.WriteCloseBraceIndent();
ctx.Return.Write(tmpVarName);
}
public override void CLIMarshalToManaged(MarshalContext ctx)
{
throw new System.NotImplementedException();
var templateType = Type as TemplateSpecializationType;
var type = templateType.Arguments[0].Type;
var tmpVarName = "_tmp" + ctx.ArgName;
ctx.SupportBefore.WriteLine("auto {0} = gcnew System::Collections::Generic::List<{1}>();", tmpVarName, type.ToString());
ctx.SupportBefore.WriteLine("for(auto _element : {0})",ctx.ReturnVarName);
ctx.SupportBefore.WriteStartBraceIndent();
{
var elementCtx = new MarshalContext(ctx.Driver)
{
ReturnVarName = "_element",
ReturnType = type.Type
};
var marshal = new CLIMarshalNativeToManagedPrinter(elementCtx);
type.Type.Visit(marshal);
if (!string.IsNullOrWhiteSpace(marshal.Context.SupportBefore))
ctx.SupportBefore.Write(marshal.Context.SupportBefore);
ctx.SupportBefore.WriteLine("auto _marshalElement = {0};", marshal.Context.Return);
ctx.SupportBefore.WriteLine("{0}->Add(_marshalElement);", tmpVarName);
}
ctx.SupportBefore.WriteCloseBraceIndent();
ctx.Return.Write(tmpVarName);
}
}

2
src/Generator/Types/TypeMap.cs

@ -11,7 +11,6 @@ namespace Cxxi.Types @@ -11,7 +11,6 @@ namespace Cxxi.Types
{
Driver = driver;
SupportBefore = new TextGenerator();
SupportAfter = new TextGenerator();
Return = new TextGenerator();
}
@ -21,7 +20,6 @@ namespace Cxxi.Types @@ -21,7 +20,6 @@ namespace Cxxi.Types
public CLIMarshalManagedToNativePrinter MarshalToNative;
public TextGenerator SupportBefore { get; private set; }
public TextGenerator SupportAfter { get; private set; }
public TextGenerator Return { get; private set; }
public string ReturnVarName { get; set; }

52
src/Generator/Utils/FileHashes.cs

@ -0,0 +1,52 @@ @@ -0,0 +1,52 @@
using System;
using System.Collections.Generic;
using System.IO;
using System.Runtime.Serialization.Formatters.Binary;
[Serializable]
class FileHashes
{
private string serializedFile;
private Dictionary<string, int> fileHashes = new Dictionary<string, int>();
public bool UpdateHash(string file, int hash)
{
if(!fileHashes.ContainsKey(file))
{
fileHashes.Add(file, hash);
Save(this, serializedFile);
return true;
}
var oldHash = fileHashes[file];
fileHashes[file] = hash;
Save(this, serializedFile);
return oldHash != hash;
}
public static FileHashes Load(string file)
{
var stream = File.Open(file, FileMode.OpenOrCreate);
var bformatter = new BinaryFormatter();
FileHashes obj;
if(stream.Length>0)
obj = (FileHashes)bformatter.Deserialize(stream);
else
obj = new FileHashes();
obj.serializedFile = file;
stream.Close();
return obj;
}
public static void Save(FileHashes obj, string file)
{
Stream stream = File.Open(file, FileMode.Create);
BinaryFormatter bformatter = new BinaryFormatter();
bformatter.Serialize(stream, obj);
stream.Close();
}
}
Loading…
Cancel
Save