我遇到了错误
细分错误
使用以下Perl代码:
use LWP::UserAgent;
use HTTP::Request;
use HTTP::Response;
use Image::ValidJpeg;
my $url = ...
my $ua = LWP::UserAgent->new(agent => '');
my $request = HTTP::Request->new(GET => $url);
my $response = $ua->request($request);
if (($response->is_success) &&
($response->code == 200) &&
($response->header('Content-Type') eq 'image/jpeg'))
{
my $content = $response->decoded_content;
open(my $img, '<', \$content);
my $check = Image::ValidJpeg::check_all($img);
print "$check\n";
}
为什么会有这样的错误?我的代码不正确吗?
调试信息:
(gdb) run /home/test.pl
Starting program: /home/test.pl
[Thread debugging using libthread_db enabled]
Program received signal SIGSEGV, Segmentation fault.
0x00007ffff683a7e0 in feof () from /lib64/libc.so.6
(gdb) bt
#0 0x00007ffff683a7e0 in feof () from /lib64/libc.so.6
#1 0x00007ffff5d4af82 in valid_jpeg (fh=0x0, seek_over_entropy=0 '\000') at valid_jpeg.c:50
#2 0x00007ffff5d4a94b in XS_Image__ValidJpeg_check_all (my_perl=<value optimized out>, cv=<value optimized out>) at ValidJpeg.c:138
#3 0x00007ffff7b18805 in Perl_pp_entersub () from /usr/lib64/perl5/CORE/libperl.so
#4 0x00007ffff7b16af6 in Perl_runops_standard () from /usr/lib64/perl5/CORE/libperl.so
#5 0x00007ffff7abf0d8 in perl_run () from /usr/lib64/perl5/CORE/libperl.so
#6 0x0000000000400cac in main ()
答案 0 :(得分:4)
查看Image::ValidJpeg
的实现,特别是在valid_jpeg.c
,模块似乎只能处理“普通”文件句柄,因为它只使用FILE*
。内存中的文件句柄无法映射到FILE*
,因此无法正常工作。
有关于内存文件句柄和XS的相关StackOverflow article。
最好的解决方案可能是在这里使用纯perl模块,或者仅仅为了验证而误用Imager
或Image::Magick
,或者使用Image::ValidJpeg
的临时文件。不要忘记错误报告。
答案 1 :(得分:1)
正如amon所说,当发生这种情况时,它表示底层实现中的错误,而不是(仅)脚本。即使您滥用了模块,模块的XS代码也会让您的错误变成内存访问冲突 - 这是编写XS的人的错误。你不能用普通的perl来做。
如果您熟悉gdb(gnu调试器),这将更容易找到罪魁祸首:
gdb perl
将perl加载到调试器中。在提示符处:
run ./myscript.pl
显然“./myscript.pl”应该是您想要运行的脚本的真实路径。该脚本将启动,虽然比正常情况慢得多,并允许您进行任何交互。当seg故障发生时,gdb将暂停并指示这一点。此时输入bt
并保存输出。
您可以在错误报告中包含此回溯。如果您不确定哪个模块有问题,请发布回溯,并且有人应该能够告诉您。