Skip to content

Commit f4e28ee

Browse files
committed
Add some type safety to the hyperlink framework
1 parent 213cbd3 commit f4e28ee

File tree

2 files changed

+40
-16
lines changed
  • inform7/Internal/Extensions/Graham Nelson/Basic Inform.i7xd

2 files changed

+40
-16
lines changed

inform7/Internal/Extensions/Graham Nelson/Basic Inform.i7xd/Materials/Inter/Architecture32Kit/Sections/Glk.i6t

Lines changed: 27 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -745,6 +745,10 @@ A simple framework for handling hyperlinks in an interoperable manner.
745745
We combine a hyperlink tag with a payload in one 32-bit value. The tag is stored
746746
in the lowest bits, and the payload above it.
747747

748+
|CALCULATE_HYPERLINK_TAG_WIDTH_R| is a |before starting the virtual machine| rule,
749+
which gets the number of options in the hyperlink tag enum and sets the tag/payload
750+
masks and widths accordingly.
751+
748752
=
749753
Global hyperlink_payload_mask;
750754
Global hyperlink_tag_mask;
@@ -769,8 +773,30 @@ Global hyperlink_value;
769773
rfalse;
770774
];
771775

772-
[ MakeTaggedHyperlink tag val;
776+
@ |MakeTaggedHyperlink| combines the tag and value into one 32 bit hyperlink ID,
777+
checking that the value is not a pointer to ephemeral data (on the stack).
778+
779+
|HANDLE_HYPERLINK_R| then extracts tag and value from an ID, expanding the value
780+
back to 32 bits.
781+
782+
=
783+
784+
[ MakeTaggedHyperlink tag val kind;
773785
if (Cached_Glk_Gestalts-->gestalt_Hyperlinks) {
786+
#Ifdef DEBUG;
787+
if (val >= blockv_stack && val < (blockv_stack + BLOCKV_STACK_SIZE * WORDSIZE)) {
788+
if (kind) {
789+
if (KindConformsTo_POINTER_VALUE_TY(kind)) {
790+
! Break up the message so that Inform doesn't think it's an Inter invocation
791+
print "Error: cannot make hyperlink from ephemeral value; try creating with {", "-by-reference:V}^";
792+
return;
793+
}
794+
}
795+
else {
796+
print "Warning: hyperlink value might be ephemeral; try creating with explicit kind^";
797+
}
798+
}
799+
#Endif; ! DEBUG
774800
if (val > 0) {
775801
@shiftl val hyperlink_tag_width val;
776802
}

inform7/Internal/Extensions/Graham Nelson/Basic Inform.i7xd/Source/Sections/Glulx and Glk.w

Lines changed: 13 additions & 15 deletions
Original file line numberDiff line numberDiff line change
@@ -203,18 +203,24 @@ Chapter - Hyperlinks
203203

204204
A hyperlink tag is a kind of value.
205205

206-
The hyperlink value is a number variable.
207-
The hyperlink value variable is defined by Inter as "hyperlink_value".
208-
209206
The hyperlink handling rules is a hyperlink tag based rulebook.
210207
The hyperlink handling rules is accessible to Inter as "HYPERLINK_HANDLING_RB".
211208

212209
The handle hyperlinks rule is listed in the glk event handling rules.
213210
The handle hyperlinks rule is defined by Inter as "HANDLE_HYPERLINK_R".
214211

212+
To say link (T - hyperlink tag):
213+
(- MakeTaggedHyperlink({T}); -).
214+
215+
To say link (T - hyperlink tag) of (V - value of kind K):
216+
(- MakeTaggedHyperlink({T}, {-by-reference:V}, {-strong-kind:K}); -).
217+
215218
To say end link:
216219
(- if (Cached_Glk_Gestalts-->gestalt_Hyperlinks) { glk_set_hyperlink(0); } -).
217220

221+
To decide what K is hyperlink value as a/an (name of kind of value K):
222+
(- (hyperlink_value) -).
223+
218224
@ And some built-in hyperlink tags:
219225

220226
- A rule hyperlink runs a rule when clicked; that in turn allows you to run any other code you like.
@@ -225,26 +231,18 @@ To say end link:
225231
Rule hyperlink is a hyperlink tag.
226232

227233
To say link (R - rule):
228-
(- MakeTaggedHyperlink((+ rule hyperlink +), {R}); -).
234+
(- MakeTaggedHyperlink((+ rule hyperlink +), {-by-reference:R}, RULE_TY); -).
229235

230236
Hyperlink handling rule for a rule hyperlink (this is the rule hyperlink rule):
231-
run rule at address hyperlink value;
237+
follow hyperlink value as a rule;
232238

233239
Keypress hyperlink is a hyperlink tag.
234240

235241
To say link (C - unicode character):
236-
(- MakeTaggedHyperlink((+ keypress hyperlink +), {C}); -).
242+
(- MakeTaggedHyperlink((+ keypress hyperlink +), {-by-reference:C}, UNICODE_CHARACTER_TY); -).
237243

238244
Hyperlink handling rule for a keypress hyperlink (this is the keypress hyperlink rule):
239-
process a character event for (hyperlink value of the current glk event as a unicode character) in (window of the current glk event);
240-
241-
Section - unindexed
242-
243-
To run rule at address (R - number):
244-
(- ({R})(); -).
245-
246-
To decide what unicode character is (N - number) as a unicode character:
247-
(- ({N}) -).
245+
process a character event for (hyperlink value as a unicode character) in (window of the current glk event);
248246

249247
@h Suspending input.
250248
These properties and phrases allow the author to suspend and resume input requests.

0 commit comments

Comments
 (0)