Beefy Boxes and Bandwidth Generously Provided by pair Networks
good chemistry is complicated,
and a little bit messy -LW
 
PerlMonks  

Bitwise & not working correctly in CGI script

by solegaonkar (Beadle)
on Jun 13, 2012 at 13:17 UTC ( #975971=perlquestion: print w/ replies, xml ) Need Help??
solegaonkar has asked for the wisdom of the Perl Monks concerning the following question:

Hello Monks,

I have a strange problem (may not be so strange for many of you - that is why I post it here!!) I have a CGI script that, picks the value of $bu based on the value of $j as per the logic below (checking for which bit is set in the number $j)

I run the code with $j = 65. That should give the value D. But, somehow, I find that the bitwise & returns true for all the values! Hence the end result is not good.

my %bj = (64,'D', 128,'A', 256,'H'); foreach my $flag (keys %bj) { $bu = $bj{$flag} if ($flag & $job_type); cluck("business_unit: $bu); }

I tried running this code standalone, in a separate pl script and it works good. But somehow it does not work in the CGI(?)

Are there some CGI/run options that could disable the bitwise & ? Tried to google around, but did not find anything useful.

Can you please help me with this?

Comment on Bitwise & not working correctly in CGI script
Download Code
Replies are listed 'Best First'.
Re: Bitwise & not working correctly in CGI script
by Jenda (Abbot) on Jun 13, 2012 at 15:35 UTC
    print "19 & 16 = ", (19 & 16), "\n"; print "'19' & '16' = ", ('19' & '16'), "\n"; print "'19' & 16 = ", ('19' & 16), "\n"; print "19 & '16' = ", (19 & '16'), "\n";

    The thing is that Perl did not convert the string (keys of a hash are ALWAYS strings, even if you used numeric literals when filling it in.) to a number and instead it evaluated a bitwise AND on the characters of the strings.

    Jenda
    Enoch was right!
    Enjoy the last years of Rome.

      What Jenda is trying to say, what perlnumber (and kennethk ) say, is that you should numify one of your arguments, so write

      #~ if( 0+$flag & $job_type ){ #~ if( $flag & 0+$job_type ){ #~ if( 0+$flag & 0+$job_type ){ if( int $flag & int $job_type ){ $bu = $bj{$flag} ; cluck("business_unit: $bu"); }
      Wow! That was right! The problem got solved when I numified both operands of & by adding 0. Thanks for your help!!
Re: Bitwise & not working correctly in CGI script
by kennethk (Abbot) on Jun 13, 2012 at 15:30 UTC
    I cannot not recover your issue. If I run the code provided (after adding use Carp 'cluck';, my $job_type = 65;, and a closing quote on your line 4, I get the output on STDERR:
    business_unit: at fluff.pl line 7 business_unit: D at fluff.pl line 7 business_unit: D at fluff.pl line 7
    I suspect your issue is that what you actually mean to have is something like
    use strict; use Carp 'cluck'; my $job_type = 65; my %bj = (64,'D', 128,'A', 256,'H'); foreach my $flag (keys %bj) { if ($flag & $job_type) { my $bu = $bj{$flag}; cluck("business_unit: $bu"); } }

    The difference here is that I am now only outputting when the if condition is true; your if applied only to the assignment, not the cluck.

    Update: Jenda also has a plausible explanation, if Re: Bitwise & not working correctly in CGI script is correct. This makes sense if you are pulling the string out of $cgi->param, which contains only strings. You can numify the result using my $job_type = 0+ $cgi->param('job');, for whatever those variables are called locally.


    #11929 First ask yourself `How would I do this without a computer?' Then have the computer do it the same way.

Re: Bitwise & not working correctly in CGI script
by muba (Priest) on Jun 13, 2012 at 15:24 UTC

    It depends on the value of $job_type, I guess. It works fine for me (see below)

    Addendum: Are you sure the value of $job_type is what you think it is?

    #!perl use strict; use warnings; print "Content-Type: text/html\n\n"; print "<html><body>\n"; my @jobtypes = (32, 64, 64|128, 128|256, 64|256); for my $j (@jobtypes) { setBu($j); } print "</body></html>"; sub setBu { my $job_type = shift; my %bj = (64,'D', 128,'A', 256,'H'); print "<ul><li>Job type is $job_type:<ul>\n"; foreach my $flag (keys %bj) { my $bu = $bj{$flag} if ($flag & $job_type); # <solegaonkar> But, somehow, I find that the bitwise & return +s # true for all the values! Hence the end result is not good. # -- Does it? if ($bu) { print " <li>Bu is true for flag $flag</li>\n"; } else { print " <li>Bu is false for flag $flag</li>\n"; } } print "</ul></li></ul>\n\n"; }

    • Job type is 32:
      • Bu is false for flag 128
      • Bu is false for flag 64
      • Bu is false for flag 256
    • Job type is 64:
      • Bu is false for flag 128
      • Bu is true for flag 64
      • Bu is false for flag 256
    • Job type is 192:
      • Bu is true for flag 128
      • Bu is true for flag 64
      • Bu is false for flag 256
    • Job type is 384:
      • Bu is true for flag 128
      • Bu is false for flag 64
      • Bu is true for flag 256
    • Job type is 320:
      • Bu is false for flag 128
      • Bu is true for flag 64
      • Bu is true for flag 256

Log In?
Username:
Password:

What's my password?
Create A New User
Node Status?
node history
Node Type: perlquestion [id://975971]
Front-paged by Corion
help
Chatterbox?
and the web crawler heard nothing...

How do I use this? | Other CB clients
Other Users?
Others having an uproarious good time at the Monastery: (14)
As of 2015-07-31 19:31 GMT
Sections?
Information?
Find Nodes?
Leftovers?
    Voting Booth?

    The top three priorities of my open tasks are (in descending order of likelihood to be worked on) ...









    Results (280 votes), past polls