Skip to content

Instantly share code, notes, and snippets.

@larsiusprime
Last active December 1, 2016 18:45
Show Gist options
  • Save larsiusprime/7c96637c15111a2b6751df4287c7d9c0 to your computer and use it in GitHub Desktop.
Save larsiusprime/7c96637c15111a2b6751df4287c7d9c0 to your computer and use it in GitHub Desktop.
package;
#if macro
import haxe.macro.Expr;
#end
class Loader
{
#if cpp
public static function __init__()
{
cpp.Lib.pushDllSearchPath(""+cpp.Lib.getBinDirectory());
cpp.Lib.pushDllSearchPath("ndll/"+cpp.Lib.getBinDirectory());
cpp.Lib.pushDllSearchPath("project/ndll/"+cpp.Lib.getBinDirectory());
}
#end
public static inline macro function load(inName2:Expr, inSig:Expr)
{
return macro cpp.Prime.load("stuff", $inName2, $inSig, false);
}
}
package;
class Main
{
static function main()
{
trace("Hello, world!");
var stuff = new Stuff();
stuff.traceIII(1,2,3);
}
}
class Stuff
{
public function new(){}
public function traceIII(a:Int, b:Int, c:Int):Void
{
//CFFI_TraceIII.call(a,b,c);
}
private var CFFI_TraceIII = Loader.load("CFFI_TraceIII","iii");
}
#include <hx/CFFIPrime.h>
int CFFI_TraceIII(int a, int b, int c)
{
printf("traceiii: %d, %d, %d\n");
}
DEFINE_PRIME3v(CFFI_TraceIII);

Steps to run:

  1. Mac or Linux environment
  2. Install latest Haxe and HXCPP, dev versions from git
  3. Copy these three files to a folder
  4. Add an include/hx folder with the hxcpp headers (hxcpp/include/hx)
  5. Create an "out" folder
  6. Compile with haxe -cp Main.hx -main Main -cpp out

You will get this result (on Mac):

haxelib run hxcpp Build.xml haxe -Dhaxe3="1" -Dhaxe_ver="3.4" -Dhxcpp_api_level="331" -Dsource-header="Generated by Haxe 3.4.0" -I"Main.hx/" -I"/usr/lib/haxe/extraLibs/" -I"/usr/local/lib/haxe/extraLibs/" -I"" -I"/usr/lib/haxe/std/cpp/_std/" -I"/usr/share/haxe/std/cpp/_std/" -I"/usr/local/lib/haxe/std/cpp/_std/" -I"/usr/lib/haxe/std/" -I"/usr/share/haxe/std/" -I"/usr/local/lib/haxe/std/"
Creating /Users/larsdoucet/Development/test/cffi/src/out/obj/darwin64/__pch/haxe/hxcpp.h.gch...

Compiling group: haxe
g++ -Iinclude -c -fvisibility=hidden -stdlib=libstdc++ -O2 -I/Users/larsdoucet/Development/git/hxcpp/include -DHX_MACOS -m64 -Wno-parentheses -Wno-unused-value -Wno-format-extra-args -DHXCPP_M64 -DHXCPP_VISIT_ALLOCS(haxe) -DHXCPP_API_LEVEL=331(haxe) ... tags=[haxe,static]
 - src/Main.cpp 
 - src/Stuff.cpp 
Error: ./src/Stuff.cpp:83:54: error: ambiguous conversion for functional-style cast from '::cpp::Function<int (int, int)>' to 'hx::Val' (aka 'cpp::Variant')
                if (HX_FIELD_EQ(inName,"CFFI_TraceIII") ) { return hx::Val( CFFI_TraceIII); }
                                                                   ^~~~~~~~~~~~~~~~~~~~~~
/Users/larsdoucet/Development/git/hxcpp/include/cpp/Variant.h:64:14: note: candidate constructor
      inline Variant(bool inValue) : type(typeBool), valBool(inValue) { }
             ^
/Users/larsdoucet/Development/git/hxcpp/include/cpp/Variant.h:293:13: note: candidate constructor
   Variant::Variant(const Dynamic &inRHS) : type(typeObject), valObject(inRHS.mPtr) { }
            ^
1 error generated.
Error: Build failed

Context: I've been getting this error on my CI when trying to build the steamwrap library, but ONLY on Mac and Linux, and only recently (last few months).

Speculation: I think this might be a regression with haxe/hxcpp and clang g++. This error does not occur on windows.

@larsiusprime
Copy link
Author

Note: I have no idea if I even got the CFFI prime setup right, as you can see I commented out the actual calling of the function. However, as soon as this mysterious error jumped out at me -- the same one I've been seeing on my CI -- I decided I had my repro case and figured I would just seal it right there.

@rrohrer
Copy link

rrohrer commented Dec 1, 2016

/Users/larsdoucet/Development/git/hxcpp/include/cpp/Variant.h:293:13: note: candidate constructor Variant::Variant(const Dynamic &inRHS) : type(typeObject), valObject(inRHS.mPtr) { }

Totally blind guess is that Dynamic's conversion constructor should be marked explicit. You don't want a type lying around that can be implicitly created from everything.

If you look here Dynamic can be created from many types. I'm also going to go out on a limb and assume that that implicit conversion is needed in some places, and marking that conversion explicit will break other things. (worth a shot if you're desperate)

Looking at how Dynamic is implicit from many types, this actually looks like a flawed (if it's intended) design. It means you can accidentally be using the dynamic typing system when you don't intend to (like this case). Which comes with a perf hit + strange errors.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment