Making it possible to call Maple would be very cool. Can you give more detail about Open Maple?
Description OpenMaple is a suite of functions that allows you to access Maple algorithms and data structures in your compiled C program. This is the reverse of ExternalCalling, which allows access to C data structures from Maple.
If I was doing this, I'd start by writing some C code that interfaces to Maple. After that works, I'd translate it into Haskell. That is, I would use the FFI to invoke the Maple FFI functions for pushing arguments, popping results, etc. and use the the FFI libraries which have lots of useful functions for marshaling arguments from Haskell to other formats.
Start with something simple (e.g., a single argument function like 'sin'), prototype in C, translate to Haskell. At this point, don't worry too much about the fact that the simplest function call seems to require 10-20 lines of code - we can suggest ways to fix that. Keep trying new features (2 arguments, strings, calling both Haskell->Maple and Maple->Haskell, etc.) [The Open Maple manual probably has a list of examples used to illustrate the interface - start by doing all those.] If it isn't obvious how to do it or it just won't work, step back and write a prototype in C.
Examples ( taken from Open Maple . kv stands for a handle for the Maple Kernel) #include "maplec.h" ALGEB M_DECL MyStats( MKernelVector kv, ALGEB *args ) { ALGEB mean, sd, f; if( 1 != MapleNumArgs(kv,(ALGEB)args) ) { MapleRaiseError(kv,"one argument expected"); return( NULL ); } if( !IsMapleList(kv,args[1]) ) { MapleRaiseError(kv,"list expected"); return( NULL ); } /* get the name of the function to call, and compute the mean */ f = EvalMapleStatement(kv,"stats[describe,mean]:"); mean = EvalMapleProc(kv,f,1,args[1]); /* compute the standard deviation using a different method -- build up the function object and call MapleEval on it */ f = EvalMapleStatement(kv,"stats[describe,standarddeviation]:"); f = ToMapleFunction(kv,f,1,args[1]); sd = MapleEval(kv,f); /* return the pair */ return( ToMapleExpressionSequence(kv,2,mean,sd) ); } Is it what do you mean ? Then, I could use the maple kernel under a "ccall" convention, I mean: foreign export ccall "MyStats" MyStats :: MKenelVector -> [Args] ...
Ask us as you run into problems.
Rather what I would like is to write code in a file foo.maple and then, when invoking the function, to invoke the key funcion in C: sd = MapleEval(kv,f) IDEA : the RTS in the startup function should initialize and instance of the Maple kernel (kv) given a (*.maple) file (exactly as a JVM loads the .class file) , once detected a maple call at compiling time. The (*.maple) should be provided by the end user, as when a dynamic library is provided. OpenMaple allows the C-programmer to initialize the Maple Interpreter; Further calls to Maple-wrapper functions will act only as calls the "MapleEval" function, provided parameters... Once you have setup the Maple handle, it seems like to deal with a C library like HOPenGL Rigth ? I don't know on Marshalling/UnMarshalling...
Once you can do all that, there's a bunch of tricks you can play with typeclasses to reduce the number of lines of code you have to write from 10-20 lines down to just one or two. (Ross Paterson has a very nice scheme for doing this - but I can't find it in the mail archives at the moment.)
-- Alastair Reid