From 39b49776c3b4b416ace469eafaed8fc6ee6b4467 Mon Sep 17 00:00:00 2001 From: Iain Buclaw Date: Sun, 31 Dec 2017 01:54:59 +0100 Subject: [PATCH] Render TypeInfo_Struct.xopCmp ABI-agnostic wrt. parameter order --- src/object.d | 21 ++++++++++++++++----- 1 file changed, 16 insertions(+), 5 deletions(-) diff --git a/src/object.d b/src/object.d index c881508a47..a097ceea3e 100644 --- a/src/object.d +++ b/src/object.d @@ -1164,7 +1164,7 @@ class TypeInfo_Struct : TypeInfo if (!p2) return true; else if (xopCmp) - return (*xopCmp)(p2, p1); + return (*xopCmp)(p1, p2); else // BUG: relies on the GC not moving objects return memcmp(p1, p2, initializer().length); @@ -1211,10 +1211,21 @@ class TypeInfo_Struct : TypeInfo @safe pure nothrow { - size_t function(in void*) xtoHash; - bool function(in void*, in void*) xopEquals; - int function(in void*, in void*) xopCmp; - string function(in void*) xtoString; + size_t function(in void*) xtoHash; + /* The xopEquals and xopCmp function pointers usually point to the struct's + * opEquals and opCmp methods. If the method doesn't take its single + * argument by reference, the front-end injects a static __xopEquals/ + * __xopCmp function (taking 2 arguments, lhs `p` and rhs `q`). + * + * In the method case, lhs `p` is the `this` argument and must be passed + * as first argument before rhs `q`. + * Enforce this arguments order by marking the pointed-to functions as + * using the C calling convention, for which the arguments are never + * reversed (contrary to `extern (D)`). + */ + extern (C) bool function(in void*, in void*) xopEquals; + extern (C) int function(in void*, in void*) xopCmp; + string function(in void*) xtoString; enum StructFlags : uint {