免責事項: perlmonksに問い合わせてください。
私の問題を適切に説明し、描写していることを願っています... XS では、コールバックに Perl 固有の関数がある外部ライブラリの関数にコールバックを送信しようとしています。XSUB は、外部 C 関数への関数ポインタとして渡されます。送信された XSUB コールバックは、次に「メイン」perl アプリケーションのサブにコールバックします。
void callback(){
dSP;
PUSHMARK(SP);
call_pv("p_callback", G_DISCARD|G_NOARGS);
}
// example extern call
externFunc(&callback);
このセグメンテーション違反。外部ライブラリが呼び出されている perl 関数を理解していないためだと思います。ただし、C の `callback()` 関数を直接呼び出すと問題なく動作します。
外部ライブラリが Perl C 関数を「見る」ようにするためにできる魔法はありますか、それとも何か間違っていますか?
私がテストしているコードは次のとおりです。
use warnings;
use strict;
use Inline ('C' => 'DATA', libs => '-lwiringPi');
init();
setInterrupt(27, 3);
# direct call
callback();
# on() triggers the external function and sends
# it the callback
on(27);
sub p_callback {
print "in perl callback\n";
}
__DATA__
__C__
#include <stdlib.h>
#include <stdio.h>
#include <wiringPi.h>
void init();
void on(int pin);
void off(int pin);
void setInterrupt(int pin, int edge);
void callback();
void init(){
printf("in init\n");
wiringPiSetup();
}
void on(int pin){
pinMode(pin, 1);
digitalWrite(pin, 1);
}
void off(int pin){
digitalWrite(pin, 0);
pinMode(pin, 0);
}
void setInterrupt(int pin, int edge){
wiringPiISR(pin, edge, &callback);
}
void callback(){
dSP;
PUSHMARK(SP);
call_pv("p_callback", G_DISCARD|G_NOARGS);
}
出力:
in init
in perl callback
Segmentation fault
コールバック内から perl 固有の C 呼び出しを削除し、「printf()」またはその他の純粋な C 作業を実行すると、セグメンテーション違反なしで処理が続行されます。