I'm not able to reproduce your problem using the code attached below.
BTW, it seems that your init_func and service_func have a generic type
parameter called "Cint" that is unrelated to the Base.Cint type. Just
omitting the "{Cint}" from the function declaration should fix that
(however, this is harmless since it's later instantiated with
Base.Cint).

I ran this under Linux/x86_64 using:
cc -shared -fPIC -o libtestservice.so testservice.c && julia testcase.jl

N.B. I'm assuming you meant the call of pq_service_create when you
said "the process aborts at the service_func(service_func_c) call".

Since you observe the contents of the function pointer change after
the fork, it's possible that the pq_service_create() method is
clobbering the stack by spewing garbage into it. You might want to
give valgrind-memcheck a shot.

Hope that helps at least a little...

-Jey


On Tue, Aug 5, 2014 at 2:11 PM, Gerry Weaver <[email protected]> wrote:
> Hi Jey,
>
> The code is pretty simple. The C code runs correctly when called from C. The
> only other thing I can think of is a gc related issue. Anyway the process
> aborts at the service_func(service_func_c) call. The address of the function
> pointer does change after the fork. So I am assuming that the pointer is
> garbage.
>
> #typedef int (*pq_service_handler)(int *exit_flag, void *user_data);
>
> #int pq_service_create (const char *name,
> #                       const char *desc,
> #                       pq_service_handler init_func,
> #                       pq_service_handler service_func,
> #                       void *user_data);
>
>
>
>
> function init_func{Cint}(a_::Ptr{Cint}, b_::Ptr{Void})
>
>   a = unsafe_load(a_)
>
>   println("init_func: $a")
>
>   return convert(Cint, 0)
>
> end
>
> const init_func_c = cfunction(init_func, Cint, (Ptr{Cint}, Ptr{Void}))
>
> function service_func{Cint}(a_::Ptr{Cint}, b_::Ptr{Void})
>
>   a = unsafe_load(a_)
>
>   while a == 0
>     sleep(5)
>   end
>
>   return convert(Cint, 0)
>
> end
>
> const service_func_c = cfunction(service_func, Cint, (Ptr{Cint}, Ptr{Void}))
>
>
> res = ccall((:pq_service_create,
> "/build/compvia/x86_linux_64/pqvm/libservice.so"),
>       Cint,
>       (Ptr{Uint8}, Ptr{Uint8}, Ptr{Void}, Ptr{Void}, Ptr{Void}),
>       "test_service", "test_service", init_func_c, service_func_c, C_NULL)
>
> Thanks,
> -G

Attachment: testcase.jl
Description: Binary data

#include <stdio.h>

typedef int (*pq_service_handler)(int *exit_flag, void *user_data);

int pq_service_create (const char *name, 
                       const char *desc, 
                       pq_service_handler init_func, 
                       pq_service_handler service_func, 
                       void *user_data)
{
  int i = 42;
  fprintf(stderr, "name: %s, init: %p, service: %p\n", name, init_func, service_func);
  init_func(&i, user_data);
  i = fork();
  service_func(&i, user_data);
  return 0;
}

Reply via email to