Strange issue with arrays

Please support our Perl advertiser: Programming Forums - DaniWeb Sister Site
Reply

Join Date: Jun 2006
Posts: 263
Reputation: Mushy-pea is an unknown quantity at this point 
Solved Threads: 1
Mushy-pea's Avatar
Mushy-pea Mushy-pea is offline Offline
Posting Whiz in Training

Strange issue with arrays

 
0
  #1
Dec 11th, 2006
Hello everyone. I'm still working on that forum system I mentioned a bit ago (perlBB). Hopefully it'll be ready for Christmas :p . However, I ran into a strange problem while I was re-writing parts the two functions below.

  1. sub enter_post {
  2. my(@field, $input, $offset1, $offset2, $n, $name, $field_length, $flag_guest, $flag_verify, @data, $lockfile, $output, $write_length, $write_length2, $post_id, $post_num, $dbase, $chunk, $chunk2, $num_links, $link, $num_replies, $offset_last, $result_all, @stat, @date, $check, $link_check, $dbase, @offset_ext, $flag_reply, @week_day, $num_records, @expected_names, @max_length, @link_info); @expected_names = ("enter_post $conf::password", "username", "password", "subject", "content", "flag_reply", "thread_id"); @max_length = (4, 14, 14, 48, 8000, 3, 10);
  3. $offset1 = 0; $post_num = 0; $chunk = ""; @week_day = ("", "Monday", "Tuesday", "Wednesday", "Thursday", "Friday", "Saturday", "Sunday"); print "\nenter_post()";
  4. &process_form(\@field, 7, 1, @expected_names, @max_length);
  5. $check = ($field[5] eq "no" && $field[6] ne "null");
  6. unless ($check == 0) {&security_alert("Form field conflict.", 1, 0)}
  7. $check = ($field[5] eq "yes" && $field[6] eq "null");
  8. unless ($check == 0) {&security_alert("Form field conflict.", 2, 0)}
  9. if ($field[2] eq "null") {$flag_verify = 1;}
  10. else
  11. {
  12. $flag_verify = &verify_user(@field);
  13. }
  14. @stat = stat($conf::MESSAGE_DB);
  15. $lockfile = "lockfile3.txt";
  16. while (-e $lockfile) {sleep 1;}
  17. open(LOCK, $lockfile);
  18. close(LOCK);
  19. open(file8, "+<", $conf::MESSAGE_DB) || die("Unable to open $conf::MESSAGE_DB for writing. $!");
  20. @data = <file8>;
  21. if ($field[5] eq "yes")
  22. {
  23. $flag_reply = 1;
  24. @link_info = &update_links(@field, $link, @stat, \@data);
  25. }
  26. elsif ($field[5] eq "no") {$field[6] = &new_thread; $flag_reply = 0;}
  27. else {&security_alert("Invalid form value.", 3, 0)}
  28. unless ($flag_verify == 1) {&security_alert("User privalidges violation.", 4, 0)}
  29. @date = localtime(time);
  30. $date[5] = 1900 + $date[5];
  31. unless (length($date[1]) == 2) {
  32. $date[1] =~ s/[0-9]/0\$date[1]/;
  33. }
  34. $date[9] = "$week_day[$date[6]] $date[3]/$date[4]/$date[5] at $date[2]:$date[1]";
  35. unless ($flag_reply == 1) {$chunk = "<links>$conf::LINK_DEFAULT_FILL</links>";}
  36. $output = "<record><record length>####</record length>$chunk<post_id>$field[6]</post_id><subject>$field[3]</subject><author>$field[1]</author><date+time>$date[9]</date+time><content>$field[4]</content></record></database>";
  37. $write_length = length($output);
  38. $output =~ s/\#\#\#\#/$write_length/;
  39. $write_length2 = length($output);
  40. unless ($write_length == $write_length2) {
  41. $output =~ s/[0-9]{$write_length2}/$write_length2/;
  42. }
  43. $offset_last = $stat[7] - 11;
  44. truncate(file8, $offset_last);
  45. seek(file8, $offset_last, 0);
  46. print file8 $output;
  47. unless ($flag_reply == 0)
  48. {
  49. seek(file8, $link_info[1], 0);
  50. print file8 $link_info[0];
  51. }
  52. $dbase = join("", @data);
  53. $dbase =~ /<database records=([0-9]*)/;
  54. $offset1 = index($dbase, "<database records=") + 18;
  55. $num_records = $1 + 1;
  56. seek(file8, $offset1, 0);
  57. print file8 $num_records;
  58. close(file8);
  59. unlink($lockfile);
  60. $main::QUERY_STRING = "view_post=$field[6]";
  61. &update_list(0, @field, $flag_reply, @date, $field[5]);
  62. &view_post;
  63. }
  64.  
  65. sub process_form {
  66. my($field, @expected_names, @given_names, @max_length, $num_fields, $status, $m, $n, @input1, @block1, @block2, $original_field, $length, $code, $code1, $code2, $code3, $offset1, $offset2, $count, $var, $result, $replace, $input, $flag_done); $flag_done = 0; $m = 1; $offset1 = 0; ($field, $num_fields, $status, @expected_names, @max_length) = @_; print "\nmax_length: @max_length"; print "\nexpected_names: @expected_names";
  67. if ($conf::environment eq "localhost") {$input = $main::QUERY_STRING; print "\ninput: $input";}
  68. elsif ($conf::environment eq "server") {$input = <STDIN>}
  69. @block1 = split(/&/, $input, $num_fields);
  70. for ($n = 0; $n < $num_fields; $n++)
  71. {
  72. unless ($block1[$n] =~ /={1}/) {&security_alert("Invalid form caught.", 2, 1)}
  73. $block1[$n] =~ /([^=]*)([.]*)/;
  74. if ($1 eq $expected_names[$n])
  75. {
  76. $given_names[$n] = $1;
  77. $block1[$n] = reverse($block1[$n]);
  78. $block1[$n] =~ /([^=]*)([.]*)/;
  79. @$field[$n] = $1;
  80. unless (length(@$field[$n]) <= $max_length[$n]) {&security_alert("Invalid form caught.", $max_length[$n], length(@$field[$n]))}
  81. $original_field = reverse(@$field[$n]); @$field[$n] = "";
  82. @block2 = split(/[\+<>]/, $original_field);
  83. $count = 1;
  84. foreach (@block2) {
  85. if ($count == 1) {@$field[$n] = @$field[$n] . $_;}
  86. else {
  87. @$field[$n] = @$field[$n] . " " . $_;
  88. }
  89. $count++;
  90. }
  91. $original_field = @$field[$n]; @$field[$n] = "";
  92. @block2 = split(/%/, $original_field);
  93. $count = 1;
  94. foreach (@block2) {
  95. if ($count == 1) {@$field[$n] = @$field[$n] . $_;}
  96. else {
  97. @$field[$n] = @$field[$n] . pack("c", hex(substr($_, 0, 2))) . substr($_, 2);
  98. }
  99. $count++;
  100. }
  101. unless ($n != 6) {chop(@$field[$n]);}
  102. }
  103. else {&security_alert("Invalid form caught", $expected_names[$n], $given_names[$n])}
  104. }
  105. }

Sorry it's long. Problem is with the @expected_names and @max_length arrays passed between the two subs. You'll notice I've made the second sub print out these arrays for debuging. The result is

  1. max_length:
  2. expected_names: enter_post mariA8743 username password subject content flag_reply thread_id 4 14 14 48 8000 3 10

which makes it look like one array has been emptied and it's contents added to the end of the other one (which makes no sense to me). Could anyone tell me if I've made some stupid mistake here or if this looks like a bug in the interpreter to you? Any help appriciated.

Steven.
Last edited by Mushy-pea; Dec 11th, 2006 at 6:55 pm.
Reply With Quote Quick reply to this message  
Join Date: Mar 2006
Posts: 898
Reputation: KevinADC has a spectacular aura about KevinADC has a spectacular aura about 
Solved Threads: 67
KevinADC's Avatar
KevinADC KevinADC is offline Offline
Practically a Posting Shark

Re: Strange issue with arrays

 
0
  #2
Dec 11th, 2006
It may seem strange to you, but thats because you don't understand what is happening. Whenever you send anything in the system array to a sub routine or function the list becomes "flattened". This means that where one list ends and another begins is lost, and it becomes one long list, as you experience.

See this page:

http://perldoc.perl.org/perlsub.html...ence-reference

But you have a bigger problem, you are not using "strict" with your perl program. All perl programs should use:

use warnings;
use strict;
Reply With Quote Quick reply to this message  
Join Date: Jun 2006
Posts: 263
Reputation: Mushy-pea is an unknown quantity at this point 
Solved Threads: 1
Mushy-pea's Avatar
Mushy-pea Mushy-pea is offline Offline
Posting Whiz in Training

Re: Strange issue with arrays

 
0
  #3
Dec 12th, 2006
Ah, I see. However, I am actually using strict in this program. I only posted a snippit of code so that can't be seen. At the top of the code you would find:

  1. #!/usr/bin/perl -wT
  2.  
  3. use strict;

Which I think is equivalent to what you are suggesting.

Steven.
Reply With Quote Quick reply to this message  
Join Date: Mar 2006
Posts: 898
Reputation: KevinADC has a spectacular aura about KevinADC has a spectacular aura about 
Solved Threads: 67
KevinADC's Avatar
KevinADC KevinADC is offline Offline
Practically a Posting Shark

Re: Strange issue with arrays

 
0
  #4
Dec 12th, 2006
OK, that is fine, it's just a bit funky how you start a block and then declare all the variables in one line at the beginning which through me off:

my($field, @expected_names, @given_names, @max_length, $num_fields, $status, $m, $n, @input1, @block1, @block2, $original_field, $length, $code, $code1, $code2, $code3, $offset1, $offset2, $count, $var, $result, $replace, $input, $flag_done);


that seems quite lazy to me and will probably make maintenance harder.
Reply With Quote Quick reply to this message  
Join Date: Feb 2007
Posts: 3
Reputation: swampyankee is an unknown quantity at this point 
Solved Threads: 0
swampyankee swampyankee is offline Offline
Newbie Poster

Re: Strange issue with arrays

 
0
  #5
Feb 1st, 2007
Originally Posted by Mushy-pea View Post
Ah, I see. However, I am actually using strict in this program. I only posted a snippit of code so that can't be seen. At the top of the code you would find:

  1. #!/usr/bin/perl -wT
  2.  
  3. use strict;
Which I think is equivalent to what you are suggesting.

Steven.
If you have something like this:

  1. @x = sub(@y, @z);
The subroutine loses @y and @z; they get joined together:

  1. push(@_, (@y, @z));
Similarly, if you return like this:

  1. return @x, @y;
they get mushed together.

To guarantee they remain separate, return array references:

  1. return \@x, \@y;
and, similarly, pass array references into a sub:

  1. @z = sub(\@y, \@z);
  2.  
  3. sub sub{
  4.  
  5. my @q = @ { $_[0]};
  6. my @r = @ { $_[1]};
Last edited by swampyankee; Feb 1st, 2007 at 12:39 pm. Reason: removed HTML tags *that didn't work)
Reply With Quote Quick reply to this message  
Reply

This thread is more than three months old.
Perhaps start a new thread instead?
Message:



Similar Threads
Other Threads in the Perl Forum
Thread Tools Search this Thread



Tag cloud for Perl
About Us | Contact Us | Advertise | DaniWeb | Acceptable Use Policy | RSS Feed

©2003 - 2009 DaniWeb® LLC