Browse Source

Reworked the CheckAbiParameters pass to be a lot more accurate by re-using the previously added support for indirect type information.

pull/47/merge
triton 12 years ago
parent
commit
dc14a5699a
  1. 55
      src/Generator/Passes/CheckAbiParameters.cs

55
src/Generator/Passes/CheckAbiParameters.cs

@ -2,6 +2,22 @@
namespace CppSharp.Passes namespace CppSharp.Passes
{ {
/// <summary>
/// This pass checks for ABI-specific details that need to be fixed
/// in the generated code.
///
/// In both the Microsoft and Itanium ABI, some functions return types
/// and parameter can be returned indirectly. In the case of an indirect
/// return type we need to add an extra pointer parameter to the function
/// and use that to call the function instead. In the case of parameters
/// then the type of that parameter is converted to a pointer.
///
/// Itanium ABI reference (3.1.4 Return values):
/// http://refspecs.linux-foundation.org/cxxabi-1.83.html#calls
///
/// Microsoft ABI reference:
/// http://blog.aaronballman.com/2012/02/describing-the-msvc-abi-for-structure-return-types/
/// </summary>
public class CheckAbiParameters : TranslationUnitPass public class CheckAbiParameters : TranslationUnitPass
{ {
private readonly DriverOptions options; private readonly DriverOptions options;
@ -11,41 +27,28 @@ namespace CppSharp.Passes
this.options = options; this.options = options;
} }
public override bool VisitMethodDecl(Method method) public override bool VisitFunctionDecl(Function function)
{ {
if (!NeedsHiddenStructParameterReturn(method, options)) if (AlreadyVisited(function))
return true; return false;
var structParameter = new Parameter() if (function.IsReturnIndirect)
{
var indirectParam = new Parameter()
{ {
Kind = ParameterKind.HiddenStructureReturn, Kind = ParameterKind.IndirectReturnType,
QualifiedType = method.ReturnType, QualifiedType = function.ReturnType,
Name = "return", Name = "return",
}; };
method.Parameters.Insert(0, structParameter); function.Parameters.Insert(0, indirectParam);
method.ReturnType = new QualifiedType(new BuiltinType(PrimitiveType.Void)); function.ReturnType = new QualifiedType(new BuiltinType(
PrimitiveType.Void));
return true;
} }
public static bool NeedsHiddenStructParameterReturn(Method method, DriverOptions options) // TODO: Handle indirect parameters
{
// In both the Microsoft and Itanium ABI, functions returning
// structure types by value have an extra parameter
// Itanium ABI reference (3.1.4 Return values):
// http://refspecs.linux-foundation.org/cxxabi-1.83.html#calls
// Microsoft ABI reference:
// http://blog.aaronballman.com/2012/02/describing-the-msvc-abi-for-structure-return-types/
Class retClass;
if (!method.ReturnType.Type.IsTagDecl(out retClass))
return false;
// TODO: Add the various combinations for that need hidden parameter return true;
var needsMSHiddenPtr = options.IsMicrosoftAbi && method.IsThisCall;
return needsMSHiddenPtr || options.IsItaniumAbi;
} }
} }
} }

Loading…
Cancel
Save