November 16 2010 — the polite revolt
22 years ago today, Estonia took its first step towards independence, after having been continually occupied since 1940 by first the Soviet Union, then by Nazi Germany, and then once again by the Soviet Union.
In the climate of Gorbachev's Perestroika, however, Estonia could begin taking steps towards regaining independence.
Sovereignty isn't the same as independence. This was only the first step in a chain of events that didn't end until 1994 with Russian (no longer Soviet) armed forces withdrawing from Estonia. It's the steps in the middle that are awesome, however. A new parliament was formed through a grassroots movement:
Estonia was unusual among the Baltic states both in the leading role it took in negotiating its independence, and the bloodlessness by which it happened.
❦
Ok, remember how yesterday, I left off with a "Cannot modify readonly value"
error? Turns out the reason for the error is at least of mild interest. Here's a simplified version of what happened in November (the wiki engine):
$ perl6 -e 'sub foo($x is rw = "OH HAI") { $x .= lc; say $x };
> my $y = "TESTING"; foo($y);
> foo()'
testing
Cannot modify readonly value
in '&infix:<=>' at line 1
in 'foo' at line 1
in main program body at line 1
See what's happening there? Our parameter $x
is declared to be modifiable (is rw
), but we can only actually modify it if we send in a variable from the outside. If we let the parameter assume its provided default ("OH HAI"
), it no longer allows modification.
Is this correct? I can argue both ways on that point, I guess.
On one hand, assigning the default "OH HAI"
to $x
could be seen as equivalent to passing in the literal "OH HAI"
to &foo
. In this case, we do expect any modification to blog up with a "Cannot modify readonly value"
error, because what we've bound to $x
isn't really a variable, it's a constant literal.
On the other hand, we did specify that $x
be rw
, and we're not really passing in "OH HAI"
, we're providing it as a default. So what's stopping Rakudo from assigning (rather than binding) "OH HAI"
to $x
, allowing for subsequent modification?
I'm currently leaning towards the other hand. ☺ But I'm betting jnthn++ will have useful input to offer, since he's the signature binder guy.
Here's an even smaller example of the same underlying issue:
$ perl6 -e 'sub foo($x? is rw) { $x = "OH HAI" }; foo()'
Cannot modify readonly value
in '&infix:<=>' at line 1
in 'foo' at line 1
in main program body at line 1
That is, when we don't pass in a value, it doesn't matter that $x
has been declared is rw
; we still can't modify it.
As a temporary workaround, is copy
seems to solve all the perceived issues.
$ perl6 -e 'sub foo($x is copy = "OH HAI") { $x .= lc; say $x };
> my $y = "TESTING"; foo($y);
> foo()'
testing
oh hai
So maybe the answer to my worries is simply "use is copy
and stop whining!". Actually, now that I look at the original failing code, it's pretty clear to me tha is copy
is a better fit in this case. But I'm still curious whether we can do better when is rw
interacts with defaults. [Update: This is now rakudobug #79288.] [Update on the update: By the decree of a spec patch, this discussion is now moot.]
Applying that workaround I find, unsurprisingly, more bitrot-related runtime errors that require fixing. Some $file ~~ :e
need to be turned into $file.IO ~~ :e
. I end today's bushwhacking on a faulty Str.trans
call somewhere in Text::Markup::Wiki::MediaWiki
.