SA Bugzilla – Bug 4631
[review] __DIE__ hooks affecting exception handling by evals
Last modified: 2005-12-08 18:25:14 UTC
debian bug 333330 notes: starting spamassassin via the init script resolves with the error: mybabe:~# /etc/init.d/spamassassin restart Restarting SpamAssassin Mail Filter Daemon: [9296] error: Can't locate object method "new" via package "Ne t::DNS::Resolver" at /usr/share/perl5/Mail/SpamAssassin/DnsResolver.pm line 87. spamd. looks to me a lot like the reporter doesn't have Net::DNS installed, but DnsResolver is using that module without eval{} protection -- hence causing a crash. Net::DNS is still listed as an optional module in our documentation.
3.1.1.
Turns out this error message and similar ones happen when Net::DNS is not installed. Surely there must be a way of silencing these! (I hope...) The most common error message is: Restarting SpamAssassin Mail Filter Daemon: [13804] error: Can't locate Net/DNS.pm in @INC (@INC contains: ../lib /usr/share/perl5 /etc/perl /usr/local/lib/perl/5.8.7 /usr/local/share/perl/5.8.7 /usr/lib/perl5 /usr/lib/perl/5.8 /usr/share/perl/5.8 /usr/local/lib/site_perl /usr/local/lib/perl/5.8.4 /usr/local/share/perl/5.8.4 /usr/local/lib/perl/5.8.0 /usr/local/share/perl/5.8.0) at /usr/share/perl5/Mail/SpamAssassin/DnsResolver.pm line 86. spamd. Note that these messages are just warnings, spamd still starts; but they are logged as "error".
Net::DNS and its dependencies I should say
Created attachment 3247 [details] patch Stupid broken __DIE__ hooks... evals often don't work as exception handlers when you've installed your own __DIE__ hooks. Getting Logger.pm to check to see if the message is coming from an eval in one of our modules should do the trick.
trunk r332683
*** Bug 4659 has been marked as a duplicate of this bug. ***
+1
'evals often don't work as exception handlers when you've installed your own __DIE__ hooks' well, they do work -- it's just that the fake-die messages used (kludgily) as exceptions in perl are "leaked". btw, I knew there was a good way to fix this; here it is, as described in perldoc -f eval: When using the eval{} form as an exception trap in libraries, you may wish not to trigger any __DIE__ hooks that user code may have installed. You can use the local $SIG{__DIE__} construct for this purpose, as shown in this example: # a very private exception trap for divide-by-zero eval { local $SIG{'__DIE__'}; $answer = $a / $b; }; warn $@ if $@; see http://www.perl.com/doc/manual/html/pod/perlfunc/eval.html . r349500 is a checkin that adds those, as well, in trunk, in addition to patch 3247. ps: we really need a way to consolidate those timeout blocks; way too much code duplication there...
Created attachment 3281 [details] additional patch here's a patch that adds the local{__DIE__} stuff.
Yeah, I know they work, but not ideally. I actually thought of that paragraph from eval's perldoc when I first saw the problem and considered it as a solution. However, I figured the chances of everyone remembering to do that in both our code AND third party-plugins were pretty slim. Using the local $SIG constructs are certainly faster, so if people remember they might at well use them. The other code can catch leaks from plugins, etc.
BTW, +1 on adding 3281, so 1 vote needed for both patches for 3.1.
yeah, this is not a replacement for patch 3247; purely supplementary, for efficiency. I have an idea on how to consolidate those timeouts using closures; separate issue though.
ping: 1 more vote needed
3.1: Committed revision 355320.