This page refers to a bug that existed in the first half of 2001. It started a discussion about DoesSoftwareQualityMeanNoBugs. This page should be refactored or deleted.
''For a site founded with the premise of "an informal history of programming", these calls to expunge its own history are troubling.''
----
By way of GriefCertificate:
If you go to ColorBlindness you will see the LinkPattern ColorBlind
* in the first paragraph resolved to a link (page exists)
* in the last paragraph resolved to a question mark (page doesn't exist)
Is anyone able to explain this?
----
See SisterSites. It seems that Ward's check for whether the page exists on remote sites is only performed for the first occurrence of a link on a page.
''So you are saying that if I cite ColorBlind right here then it will not link? Wow. That is amazing. It sure wasn't programmed to work that way. I wonder if this is related to a rare and long standing linking problem that seems to go away when wiki is run on more recent versions of perl than run at c2? -- WardCunningham''
Who wrote the unit tests for this thing anyway?
''[The aforementioned bug persisted for about six months before quietly vanishing.]''
''[Sadly, the aforementioned bug has not vanished. OnlineDiary OnlineDiary.]''
Interesting. It certainly ''seemed'' to have disappeared for awhile. More unit tests are definitely called for.
----
Here is the code in question ...
s/\b$link\b/&anchor($&)/geo;
and the sub it calls ...
sub anchor {
local($title) = pop(@_);
if(defined ($db{$title}) or <$base.idb/*.d/$title>) {
return "$title<\/a>";
} else {
return "$title?<\/a>";
}
}
----
Can you elaborate on what the likely return from the <$base.idb/*.d/$title> is? For example, if it returns 000 it your expression will be false.
Perl is beautiful in that ThereIsMoreThanOneWayToDoIt. However, this can be problematic when debugging. The 'or' operator always makes me nervous, because it has a different precedence than '||'. I would use my instead of local. It's much safer when you can get away with it. Also, while it looks like you're always called with a single argument, I would use shift rather than pop to get the argument. If the $link should somehow contain a comma, you might get multiple arguments.
Have said all that, while I see some dangerous practices, I don't see anything that would definitely cause this. -- DavidCorbin
----
I hardly know any Perl and it doesn't have much to do with the problem, but the code above doesn't look efficient to me. Wouldn't something like
sub anchor {
local($title) = pop(@_);
my $ret=$cache{$title};
if(!defined($ret)) {
if(defined ($db{$title}) or <$base.idb/*.d/$title>) {
$ret="$title<\/a>";
} else {
$ret="$title?<\/a>";
}
$cache{$title}=$ret;
}
return $ret;
}
typically perform better and at least give a single unambiguous result (right or wrong)?
Why spend the time (and clutter) to optimize it if it's not where the performance burden is? -- DavidCorbin
Even simpler, ''if (1) ...'' will give a single unambiguous result, right or wrong. I will try this soon enough. Right now I'm trolling for a ''that's a well known linux directory page caching bug'' sort of answer.
----
Regarding the (apparently) offending code:
using $& is a big penalty in speed and memory, if it can be avoided, much better... rephrasing it to:
s/\b($link)\b/&anchor($1)/geo;
would be better if there's no need to use $& in any part of the program... Also, the /o in this case may be problematic, although I don't see how...
As my homonymous wikier commented, using dynamically scoped variables (my), using shift, etc are much better (actually ''safer'' is the word) Perl coding practices...
I have tested that code, using the offending link, with Perl 5.6.0 on a Solaris 2.6 without any problems, all links were provided or marked as '?'... Which version of Perl is used in c2.com? -- DavidDeLis
----
''From a previous time. Probably not the problem any longer.''
I think your problem is that glob called in a scalar context must be called repeatedly until it returns false, at which point it resets. Consequently, the reason why sister site pages only show up every other instance is that it calls glob once to find
$base.idb/*.d/TwinPage
and then the next time it calls to get ***false*** indicating that $base.idb/*.d/TwinPage is the last in the glob list from Perl's point of view, but saying to the Wiki script that there is no twin page.
Thus, change sub anchor to be:
sub anchor {
local($title) = pop(@_);
'''my ($twin) = <$base.idb/*.d/$title>;''' # Note change here
'''if(defined ($db{$title}) or $twin) {''' # and here
return "$title<\/a>";
} else {
return "$title?<\/a>";
}
}
----
Oops. I seemed to have reverted on this fix when I was removing the dbm code. Where are those UnitTest''''''s when I need them? This has been re-corrected. I was suckered into reverting the fix when I noticed the unnecessary evaluation of the glob when the left hand side of the OR was true. I've rewritten the code to avoid this evaluation and properly evaluate the glob in an array context. -- WardCunningham