views:

84

answers:

2

I'm checking for the existence and default values of various socket options using Perl.

#!/usr/bin/perl -w
use strict;
use Socket;

if (defined(SO_BROADCAST)) {
    print("SO_BROADCAST defined\n");
}

if (defined(SO_REUSEPORT)) {
    print("SO_REUSEPORT defined\n");
}

When I run this it outputs:

SO_BROADCAST defined

Your vendor has not defined Socket macro SO_REUSEPORT, used at ./checkopts.pl line 9

Is there a way to do this without generating warnings in the output?

+9  A: 

That message is coming from AUTOLOAD in Socket.pm. When it finds a constant that isn't supported, it croaks. You can catch that with an eval:

 use Socket;

 if( defined eval { SO_REUSEPORT } ) {
      ...;
      }
brian d foy
+1  A: 

Ask whether the sub has been defined, not whether the expression's value is defined:

if (defined &SO_REUSEPORT) { ... }

The documentation for defined explains:

You may also use defined(&func) to check whether subroutine &func has ever been defined. The return value is unaffected by any forward declarations of &func. Note that a subroutine which is not defined may still be callable: its package may have an AUTOLOAD method that makes it spring into existence the first time that it is called—see perlsub.

If the sub is exported into your namespace, it has to be defined.

Greg Bacon
Why do you check for a subroutine define? Are these actually defined as subroutines in Socket.pm and not as constants?
Robert S. Barnes
@Robert The constants *are* subs! See http://perldoc.perl.org/perlsub.html#Constant-Functions
Greg Bacon
@gbacon: You're answer is better than the one I originally picked.
Robert S. Barnes