davidkinder / inform6 Goto Github PK
View Code? Open in Web Editor NEWThe latest version of the Inform 6 compiler, used for generating interactive fiction games.
Home Page: http://inform-fiction.org/
License: Other
The latest version of the Inform 6 compiler, used for generating interactive fiction games.
Home Page: http://inform-fiction.org/
License: Other
RV__PR calls RT__Err with four arguments, which doesn't work in Z3.
Not sure how fixable this is, but it's a bit annoying and it can also lead to code compiled but not working as intended.
This doesn't compile:
[main a b;
#Ifdef FOO;
if(a == b) print "Yes";
#Ifnot;
if(a < b) print "Yes";
#Endif;
else print "No";
];
By the time the compiler gets to "else" it doesn't remember the "if" context.
The following program compiles but it doesn't work as intended:
[main a b;
#Ifdef FOO;
if(a == b)
#Ifnot;
if(a < b)
#Endif;
print "Yes";
print "Press a key: ";
@read_char b;
];
print "Yes"; is performed regardless of the condition.
There are two reasons I think it should:
This should of course be named Makefile when checked into the repo, but github wouldn't let me upload it under that name.
The Origsource directive adds more error info, but this is only implemented for -E0 error reporting. Add for -E1 and -E2.
Suggestions (from https://intfiction.org/t/command-line-inform-7-how-to-use-ni-inform6-and-cblorb-by-cli/50108/27 ).
File "broken.inf"'; Line 12 (from "story.ni"; Line 10) # Error: Whatever
broken.inf(1): story.ni(10): Error: Whatever
I think it would be nice for Inform6 to compile without warnings when -Wall -Wextra
are used. To this end I would like to take on the task of fixing these warnings.
The compiler does not detect that the constants for the Dictionary directive are not declared. However, it assigns them a value.
Dictionary 'word' DICT_XXX DICT_YYY;
[ main;
print ('word'->#dict_par1), "^";
print ('word'->#dict_par3), "^";
];
162
35
(instead of 128, 0)
Proposed here: https://intfiction.org/t/define-a-constant-on-commandline-for-inform-6-compiler/50285
I'm thinking the option would look like
$#IDENTIFIER
$#IDENTIFIER=NUM
--define IDENTIFIER
--define IDENTIFIER=NUM
If no value is specified, default to 0 (consistent with the Constant
directive).
We'd have to validate that the identifier is all ascii (Inform doesn't permit non-ascii characters outside of quotes, regardless of the -C setting). And doesn't start with a digit. Also the identifier shouldn't clash with any of the compiler-defined symbols like WORDSIZE
or sw__var
.
Inform 6 has some operators where the operator on the left hand side must be a valid object ID and/or the one on the right hand side must be an object ID, a property ID or an attribute ID. In a few cases, giving the wrong kind of entity raises a warning. I can see that these operators confuse a lot of newcomers to Inform 6, and even I made a stupid mistake in this area recently ( if(player has necklace) ...
:) ). Wouldn't it be nice with warnings when using the wrong kind of entity for these operators? Like for Lamp.light = true
or if(Lamp provides light)
etc. Here's a program covering some of the cases, with comments for the ones that currently give a warning.
Property p1;
Property p2;
Property p3;
Property p4;
Property p5;
Property p6;
Attribute a1;
Attribute a2;
Attribute a3;
Attribute a4;
Attribute a5;
Attribute a6;
Object o1 "o1"
with
p1 1,
p2 1,
p3 1,
p4 1,
p5 1,
p6 1,
has a1 a2 a3 a4 a5 a6;
Object o2 "o2";
[main;
if(o2 has o1) print "o2 has o1";
if(o2 has p1) print "o2 has p1"; ! Warning: Property not qualified by object
if(o2 provides o1) print "o2 provides o1";
if(o2 provides a1) print "o2 provides a1";
if(o2 in p1) print "o2 in p1"; ! Warning: Property not qualified by object
if(o2 in a1) print "o2 in a1";
if(p1 has a1) print "p1 has a1"; ! Warning: Property not qualified by object
if(p1 provides p1) print "p1 provides p1"; ! Warning: Property not qualified by object
if(p1 in o1) print "p1 in o1"; ! Warning: Property not qualified by object
if(a1 has a1) print "a1 has a1";
if(a1 provides p1) print "a1 provides p1";
if(a1 in o1) print "a1 in o1";
if(o1.o2) print "o1.o2 ~= 0";
if(o1.a2) print "o1.a2 ~= 0";
give o1 p1; ! Warning: This is not a declared Attribute: "p1", Bare property name found. "self.prop" intended?
give o1 o2; ! Warning: This is not a declared Attribute: "o2"
give a1 a2;
give p1 a2; ! Warning: Bare property name found. "self.prop" intended?
];
This isn't a major issue, but the repo doesn't have a makefile. I've hacked one up and placed it here.
A patch to make INDIV_PROP_START configurable as a memory setting, following Andrew Plotkin's paragraph in his glulx-technical.txt:
The value of INDIV_PROP_START is currently hardwired to 256, in the
compiler. It will eventually be made flexible. The veneer and library
use the constant INDIV_PROP_START, so they can adapt to any value the
compiler defines.
Consider this code:
Object Kitchen "Kitchen"
with description "Nice kitchen",
has light;
Object bag "bag" selfobj
has container open;
Object -> hammer "hammer";
This places the hammer in the kitchen. I think this is weird and inconvenient behaviour, but maybe it's intentional. And I realize that changing it could break existing code.
An object which has a name array longer than 4 dictionary words raises a warning when compiled to z3, and the compiler says it will truncate the array. But the object ends up corrupted.
This object:
Object -> Surfaceofthewater "Atlantic Ocean"
with name 'Surface' 'of' 'the' 'water', 'ocean', 'atlantic' 'ocean' 'sea' 'seawater' 'waves',
description "TODO",
before [; Enter: print "You enter the ocean...^"; ; rtrue;
];
Ended up like this in the story file (output from ztools/infodump):
Property 20 get three different values. Some property values have length 1 or 3, something I believe the Inform compiler should never do.
Used Inform 6.34, the binary for Win32 available at if-archive, with the PunyInfom library.
Not creating the optimal abbreviation list, but applying abbreviations optimally to each string as it is compiled. This is the try_abbreviations_from() function. It could be improved.
Code sample attached. This is Matt Russotto's C# implementation from this post: https://intfiction.org/t/highly-optimized-abbreviations-computed-efficiently/48753/46
This involves repeatingly measuring the cost of a string with different abbreviations in place. (Cost meaning "length in Z-chars.") We might need a cut-down clone of translate_text() to do this efficiently.
Example (which just recently caused me some headache):
switch (event){
EVENT1:
event1();
EVENT2:
event2();
default:
unknownEvent(event);
return event; <- This is inside the switch, it does nothing and is not reported by the compiler
}
Perhaps there's a reason for being able to do this and that's why the compiler doesn't complain.
In Z-code, if you write:
Object foo with name 'x';
...you get a warning:
line 5: Warning: 'name' property should only contain dictionary words
('x'
being a character literal, not a dict word.) (If you want a short dict word it would be 'x//'
.)
This warning doesn't happen in Glulx.
The difference is just these lines:
! objects.c:1163, zcode
if ((!individual_property) && (property_number==1)
&& ((token_type != SQ_TT) || (strlen(token_text) <2 ))
&& (token_type != DQ_TT)
)
warning ("'name' property should only contain dictionary words");
! objects.c:1425, glulx
if ((!individual_property) && (property_number==1)
&& (token_type != SQ_TT) && (token_type != DQ_TT)
)
warning ("'name' property should only contain dictionary words");
I must have taken the extra clause out for some reason, but I can't remember why. Maybe I wanted to change the x//
notation but then realized it would be too messy?
I'll fix them up to be parallel again unless someone can think of a reason that I did this.
As I wrapped up version 6.12.4 of the Standard Library, I looked again at the list of accepted suggestions at http://inform-fiction.org/suggestions/accept.html. One of them has bothered me for a long time: The Inform6 compiler still makes use of dollar signs on the command line. To fix this, someone suggested and apparently Graham accepted the suggestion. Here it is:
- The use of "$..." to introduce compiler options is intensely annoying on *NIX systems that use "$" as an environment variable indicator, e.g. $PATH -- it requires the constant use of quotes to avoid unpleasant and confusing results.
Is this something that can be considered again?
Hi David,
What / where is the compatible library for Inform 6.33 ?
I've been trying to use this one, (the only one I've found), but it throws all kind of errors.
http://www.ifarchive.org/if-archive/infocom/compilers/inform6/library/inform_library-6.12.1.zip
Mike
If you compile a game to z3, and there are two dictionary words in the source code which are not different with the six-character resolution of z3, but would be different if the resolution was 9 characters as in z5, they are created as separate dictionary words, which causes all sorts of problems. Example:
Object Scorpion "scorpion"
with
name 'scorpionx' 'scorpiony';
This creates two dictionary words: 'scorpi' and 'scorpi' (truncated to six characters). Depending on the interpreter's method of searching the dictionary, one or the other may be matched when the player type a word beginning with scorpi.
Neither the readme nor the source files state under what license the source code is distributed. According to http://inform7.com/sources/i6n/ it is the Artistic License 2.0, but it would be better if this is stated here explicitly.
Thanks,
Joachim
As long as we're recording long-term goals... I always meant to replace all the preallocation limits (ALLOC_CHUNK_SIZE, etc) with realloc() calls.
I may never do this, but at least it's in the tracker now.
Related: There are many places where a bunch of parallel allocated arrays could be replaced by a single realloced array of structs. For example, symbs/svals/sflags/stypes/slines/smarks are all allocated with length MAX_SYMBOLS. Similarly, label_offsets/label_symbols/label_next/label_prev are all allocated with length MAX_LABELS. Structs would make this all easier to deal with.
Hi there,
First of all please tell me if it would have been better to file a report on I7's Mantis instead of here; I chose here as I find GitHub more convenient and it's very-specific to the compiler.
I just packaged the I6 compiler for the Mageia Linux distro based on Ben Finney's Debian packaging. We both compile I6 with -DInclude_Directory="\"/usr/share/inform6/library\""
, which works great.
So I6 will look by default in this system-wide path for the libraries. Now, when I want to build a project that uses a custom library, I would like to have the possibility to define an additional path for library lookup using a command line switch. There is already +include_path=<path>
(and +<path>
), but it overrides the system-defined one.
See e.g.:
$ ls
katabasis.inf
scenic5sens.h
$ inform -v8 +Language_name=French katabasis.inf katabasis.z8
Inform 6.33 for Linux (10th May 2014)
[Compil� avec la version 2.3 de la biblioth�que francophone.]
line 795: Fatal error: Couldn't open source file "/usr/share/inform6/library/scenic5sens.h"
$ inform -v8 +Language_name=French +include_path=./ katabasis.inf katabasis.z8
Inform 6.33 for Linux (10th May 2014)
line 11: Fatal error: Couldn't open source file "./Parser.h"
The only solution is to specify both the system path and the custom path in the switch, which is tiresome:
$ inform -v8 +Language_name=French +include_path=/usr/share/inform6/library/,./ katabasis.inf katabasis.z8
Inform 6.33 for Linux (10th May 2014)
[Compil� avec la version 2.3 de la biblioth�que francophone.]
Compiling Scenic.h
To fix this, there could either be a new switch (e.g. +include_path_add=
) that only extends the path instead of replacing it (if the possibility to fully override the system-defined path should be kept). Another possibility would be to support an assignment like +=
instead of =
, e.g. +include_path+=./
.
This gives an error:
`
Constant PRINT_WARNING;
[Initialise x;
x = 1;
switch(x) {
#IfDef PRINT_WARNING;
1: print "1!^";
#Endif;
default: print "Other^";
}
print "End.^";
];
`
But if you add 0: print "0!^";
just before #ifdef, it works.
Currently the compiler always reserves 32 of the Z-machine's 96 abbreviations for dynamic strings. (These look like @00
to @31
in string literals, and can be modified with the string
statement.) The other 64 are abbreviations (the Abbreviate
directive).
It would be good to allow the user to trade these off -- up to 96 of either.
I propose doing this with the MAX_ABBREVS
compiler setting. This already exists, and defaults to 64 for Z-code. I'll limit this to the range 0..96. The compiler will assume that 96-MAX_ABBREVS
dynamic strings are available.
Fussy details:
Setting MAX_ABBREVS=100
is currently legal in Z-code. It's pointless, since the compiler is hardwired to throw an error beyond 64 abbreviations. So I'm pretty sure nobody does it. If they do, they'll get a sensible error message in the future.
Currently the dynamic string range is completely unchecked in Z-code. You can put any number up to @99
into a string literal; its value is interpreted mod 32. You can pass any number to a string NUM "foo"
statement; values beyond 31 will stomp on low memory. Oops.
I intend to add compile-time bounds checking and error messages where possible. string EXPR "foo"
where expr is not a constant would require run-time bounds checking, but I don't want to add runtime code for this corner case, so people will have to continue living with it.
Compile this with Inform 6.34, using -v3
Array buffer -> 100;
Array parse -> 100;
Object Being "human-like being"
with
name 'human' 'human-like' 'being';
[ Main i;
print "Contents of Being.name:^";
for(i=0 : i < (Being.#name / 2) : i++)
print i, ": ", Being.&name-->i, "^";
buffer->0 = 80;
parse->0 = 20;
@sread buffer parse;
print "Contents of parse buffer:^";
for(i=0 : i < parse->1 : i++)
print i, ": ", (parse+0)-->(2 * i + 1), "^";
@sread buffer parse;
];
Then run this in Windows Frotz and type this input: "human human-like being".
Apparently, human and human-like make two different dictionary words when compiling, but they are the same word when Windows Frotz looks up the words the player typed in the dictionary. I tried this in Gargoyle (Bocfel) too, with the same result.
The way I read the Z-machine spec ( https://www.inform-fiction.org/zmachine/standards/z1point1/sect03.html#seven ):
So they should be identical as dictionary words, no?
This is part of the output for inform6 -h2:
v3 compile to version-3 ("Standard") story file
v4 compile to version-4 ("Plus") story file
v5 compile to version-5 ("Advanced") story file: the default
v6 compile to version-6 (graphical) story file
v8 compile to version-8 (expanded "Advanced") story file
...
B use big memory model (for large V6/V7 files)
So in essence there's no documented way to tell the compiler to build a v7 file, but if you do, -B might be useful.
This is a problem in both Z-code and Glulx, but the problems are different.
In Z-code, if you have a line like
o.prop = val;
where prop is an individual property not yet defined, the compiler erroneously generates a set_prop
opcode (which only works for common properties).
In Glulx, if you refer to o.prop
where prop is a common property not yet defined, you get an error:
"<constructing output>", line 0: Error: *** Illegal backpatch marker in forward-declared symbol
Both of these cases are supposed to work. The Glulx case is an oversight on my part. The Z-code case appears to be a typo in the check_property_operator() function.
Currently you can write
Array arrname --> 'test';
This may compile with an unexpected length because the value of 'test'
is not yet determined.
Given fixing the release notes typo in f064fea, should the tag for v6.34 be moved to point there?
I was trying to compile Glulxercise with the -k
option, and Inform gives this error:
"<constructing output>", line 0: Error: No such constant as "debug_flag"
This seems to come from the veneer's use of debug_flag
.
I don't know what the best thing to do is, but this feels quite nonoptimal to me.
Would it be possible to insert this code if the -k
flag is used?
#ifndef debug_flag;
Global debug_flag = 0;
#endif;
I've added this to Glulxercise and it now compiles, but it says that debug_flag
isn't used, so I guess it's not detecting its use by the veneer?
When compiling with GCC version 6, the compiler warns about an implicit function declaration:
$ gcc --version
gcc (Debian 6.1.1-11) 6.1.1 20160802
Copyright (C) 2016 Free Software Foundation, Inc.
This is free software; see the source for copying conditions. There is NO
warranty; not even for MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
$ gcc -DUNIX64 -c -o inform.o inform.c
In file included from inform.c:11:0:
header.h: In function ‘unique_task_id’:
header.h:457:19: warning: implicit declaration of function ‘getpid’ [-Wimplicit-function-declaration]
{ return (int32)getpid();
^~~~~~
This indicates an existing problem (functions should be explicitly declared) that was not being reported by some earlier compiler versions.
The gametext.txt format is built for human proofreaders. You'd want a different format for a tool meant to construct an optimal abbreviation list.
The default should not change; the alternate format would be requested by a setting, $TRANSCRIPT_MARKERS=1
.
I'm thinking every line starts with a three-character prefix:
I: Info (Transcript of the text of “Advent.inf”…)
G: Game text
V: Text in veneer
D: dictword
A: abbreviation
O: objectname
From Johan Berntsson:
I have discovered a bug in Inform6 and I want to ask if you can make sure that it is being fixed in a future upgrade.
I and some friends are making a new standard library for small computers (think Commodore 64) which is called PunyInform: https://github.com/johanberntsson/PunyInform We are testing this on both z3 and z5, while the Inform stdlib no longer works on z3. What I have discovered is that <> no longer works in z3. It doesn't return from the function as it is supposed to (the implicit rtrue isn't generated).
The problem is line 173 on states.c:
assemblez_4(call_zc, AO, AO2, AO3, AO4);
should instead be:
assemblez_4_to(call_zc, AO, AO2, AO3, AO4, temp_var1);
Since the temp_var1 is missing the next instruction (the rtrue) will be assumed to be a global variable location instead, so the rtrue is never executed, causing the problem (but only in z1-z3 of course; z5 etc works). I have recompiled the Inform compiler and confirmed that this change solves the problem.
I have attached the fixed and working states.c. Can you make sure that the fix finds its way into the official repository?
states.c.txt
You seem to have made some releases without tagging any of them. This makes archaeology, or even just figuring out what's been changed since the latest release, tricky.
It would be handy if the default language could be specified at compile time. Currently this is hardcoded here:
Line 591 in 077038c
I'd do this by adding something like Default_Language
to be checked in the same fashion as is done here:
Line 584 in 077038c
However, if Default_Language
is undefined, then English
would be used instead.
My reason for this is that capitalization forces some gyrations with symlinks in a Unix environment to get things compiled. In https://gitlab.com/DavidGriffith/inform6unix I'm dealing with this by applying a patch to the Inform6 compiler code before compiling.
(As suggested in this thread: https://intfiction.org/t/next-steps-for-inform-6-compiler/51008)
For lines like
if (false) { return 97; }
...the compiler generates an unconditional jump, but then generates the return opcode anyway.
3 +00011 <*> jump to L0
4 +00017 <*> return byte_97
5 +0001a .L0
Ideally, the author would use #ifdef
instead of if
for this sort of code. However, I7 generates trivial conditions sometimes. E.g.
Understand "count [number]" as counting.
...generates the stanza:
if (v == GPR_NUMBER) {
n = noun; noun = parsed_number;
if (~~(((true) && (true)))) v = GPR_FAIL;
noun = n;
}
The compiler successfully collapses (~~(((true) && (true))))
to (false)
but still generates the v = GPR_FAIL;
assignment.
This can almost be addressed with the execution_never_reaches_here
flag, except that that flag is currently used to generate the "statement can never be reached" warning, which is not exactly the same thing. (See assembleg_1_branch()
, which turns off that flag to avoid generating a warning on "if (false)..." because the author probably did it on purpose.) (I7 didn't do it on purpose, but I7 suppresses all warnings anyhow.)
I suspect the fix here is for execution_never_reaches_here
to have three states: false, true, and "true but the author did it on purpose". If non-false, we can skip generating code entirely in assembleg_instruction() / assemblez_instruction().
(Is it safe to just bail out of those functions? What about inline strings in Z-code? Sequence points? Symbols used only in dead code? So many corner cases to check!)
Note that the compiler assumes that every jump label is live code, even if no jump statement goes there. (See assemble_label_no()
.) We should probably keep this. It allows the author to avoid dead-branch optimization on a case-by-case basis:
if (false) { .KeepLive; return; }
(This might be needed for occult code generation techniques like inter-function jumps. Which we don't support, but maybe someone is trying to do it anyway.)
The assembly trace (-a
switch) produces lines like
call_vs long_16 obj identifier -> x
This is really not very helpful, because "long_16" is an internal marker value which does not correspond to anything in the generated game file. (It might be the numeric constant 16, or veneer routine 16, or a routine with offset 16 in the code area, etc.) We could append a tag like "{veneer}", "{routine}", etc to distinguish these cases.
It would be even better to display the symbol which evaluated to the given constant. I think this would require adding a "symbol" field to the assembly_operand struct.
I don't believe anything relies on the -a
output format, so adding this would not require a config setting.
Low priority, but maybe useful.
The following code is legal:
Abbreviate "@00 Smith";
[ Initialise ;
string 0 "John";
];
(The command "string n "str"" is named "printing variable" on page 30 of the DM4; it is implemented as an abbreviation. The Z-Machine has 96 abbreviations : 64 can be defined by Abbreviate, 32 with printing variables.)
As mentioned here, this however violates paragraph 3.3.1 of the Z-machine Standards Document 1.1, "Abbreviation string-printing follows all the rules of this section except that an abbreviation string must not itself use abbreviations".
Virtually no interpreter (Infocom's, 8-bit ones, Frotz, etc.) ever complain about this, except Bocfel (so, Spatterlight on OS X and Gargoyle on Linux), which crashes.
The compiler should give a warning, or an error, for this case.
Similarly, @00 should not be included in "string 1", etc. (But I don't know if this is even allowed by the compiler; if it is, it could definitely create infinite loops, or at least nasty recursive patterns.)
This doesn't compile:
Constant FOO "String";
Default FOO 5;
[ Test;
#IfTrue FOO < 10;
print "Hello^";
#EndIf;
print "Goodbye^";
];
[main b;
Test();
@read_char b;
];
Is it that the value of FOO isn't known on the first pass, since the compiler can't know the final address of the string until it has compiled the code?
This is a pattern we use in PunyInform for replacing library messages, and no one has complained that it doesn't work yet, but maybe they haven't tried it just this way.
Trying again if you don't want a Makefile.
I've been working in open source development for a long time. It's considered polite to offer improvements to upstream.
So the README suggests:
cc -o inform *.c
This is bad advice. Inform 6 will run TWICE as fast if compiled with the -flto flag along with any level of optimization, with running time being cut in half on large test cases. The -flto flag has been available on both gcc and clang for over 10 years (it's documented in the manual for the 2011 releases). In short, a far more appropriate compilation command for practically all users of Unix-like systems in the last decade is
cc -flto -O2 -o inform *.c
And the best way to get this adopted downstream is to get it documented in the upstream repository. I strongly advise that this information be put in the README.
I have found four different downstream packages packaging and compiling inform6 from this upstream (gnome-inform7, inform7 CLI, Inform 6 for Unix, and the Debian Inform 6 package), each with its own hand-spun build system, and not one of them does this. There are probably more. While I have contacted all of their maintainers, I have not gotten a response yet. This ought to be documented upstream.
The tech manual for 6.21 says:
The "-g" switch for tracing function calls now has a third setting, "-g3", which traces even veneer calls: the "-g2" setting now traces game and library calls but not veneer calls.
It looks like this made it into the code generator (there are tests for trace_fns_setting==3
in syntax.c and veneer.c) but not the argument parsing (inform.c). We could enable this.
This would require some amount of testing. Note that even -g2 will cause problems in Glulx, due to trying to print trace info before the output windows are opened. -g3 will certainly be worse.
Over at https://gitlab.com/DavidGriffith/inform6unix I'm experimenting with the idea of being able to select which library the author wants to use with a minimum of hassle. I've worked out a scheme that seems to work by requiring the use of a Makefile or else requiring the author to type in a long override of Include_Path
by way of the +dir
flag. I'd like to be able to do inform -L std foo.inf
to compile something using the Standard library and inform -L puny bar.inf
to use PunyInform. This would easily extend for any number of alternate libraries.
I envision this happening by reworking the *_path
parameters that are compiled into the compiler. For instance, have lib_path
contain /usr/local/share/inform/lib
. Then in /usr/local/share/inform/lib
would go subdirectories for whatever libraries desired. The -L
flag would select what subdirectory to choose. So -L std
would include files from /usr/local/share/inform/lib/std
. Includes would be the same way: /usr/local/share/inform/include/std
and so on because the includes mostly seem very library-specific.
How does this sound, at least in concept?
While working on #26, I noticed the -b
command line switch. According to the source code it turns on bothpasses_switch
. What is this? It's not mentioned in any of the -h
usage information outputs.
I was looking at this and thinking it might be nice to port to Julia. I could do the work but I'd probably have to ask a lot of questions. Is that something people would be interested in?
I have created thus
Object LibraryMessages
with before [;
Restart:
print "Are you sure you want to restart? ";
if (YesOrNo()){
JSCommunication.RunCode("gameConsole.makeInformCall('Main', 'restart');");
}
return true;
]
;
Which works reasonably well for overriding the restart command issued to the prompt.
However, the RESTART option provided in AfterGameOver (parser.h, line 5441), circumvents this. I have "corrected" this by changing line 5469 to if (~L__M(##Restart) == false) @restart;
but I suspect this is not the correct overall solution.
In the case where you say something like
Property foo;
Attribute foo;
[ foo; ... ];
...but "foo" is already defined, it would be good to report the location of the previous definition.
The compiler already does this if you write
Object obj with foo;
! implicitly defines a property foo
I am going to generalize that to the cases above.
In some z3 story files, I get an orphan code fragment at the end of Zcode memory. This is what it looks like in "TXD -d -n" output:
orphan code fragment:
5006: 4e 97 e5 INSERT_OBJ G87,"lgwitsm"
5009: a5 62 INC [G52]
500b: 9a e5 PRINT_OBJ "lgwitsm"
500d: a5 28 INC [G18]
500f: d8 e4 a5 MOD -> G95
5012: 71 58 e4 a5 GET_PROP G48,Gd4 -> G95
5016: ea a5 26 9c cc a5 SPLIT_WINDOW G16,G8c,#cc,#a5
501c: ba QUIT
The code for this game contains a single SPLIT_WINDOW statement, and this is not it. This must be something which the compiler has thrown in.
I'm using the Inform 6.34 Win32 binary available at if-archive, with PunyInform.
As I've explored this issue at https://gitlab.com/DavidGriffith/frotz/issues/136, it occurred to me that the problem may lie in any of three places: the Inform 6 Compiler, the Inform 6 Library, or the Frotz core.
If you wait for the KeyDelay() delay by not pressing a key, you get a fatal error when you replay the recording during the game, otherwise you get: "I beg your pardon?"
Transcript:
Release 1 / Serial number 190801 / Inform v6.34 Library v6.12.3pre S
Room 1
You are in room 1.
Come in, Room 2 is waiting for you.
>recording
Enter a file name.
Default is "test.rec":
[Command recording on.]
>enter
You are hesitating... then you decide to enter.
Room 2
You are in room 2.
>recording off
[Command recording off.]
>replay
Enter a file name.
Default is "test.rec":
Do you want MORE prompts? (y/n) >y
[Replaying commands.]
>enter
You can't go that way.
>Fatal error: Illegal opcode
[Hit any key to exit.]
Source code:
Include "parser";
Include "verblib";
Object room1 "Room 1"
with description "You are in room 1. ^Come in, Room 2 is waiting for you.",
Before [;
GoIn:
print "You are hesitating... ";
KeyDelay(15);
print "then you decide to enter.^";
PlayerTo(room2);
rtrue;
],
has light;
Object room2 "Room 2"
with description "You are in room 2."
has light;
[ Initialise; location = room1; ];
Include "grammar";
That Inform uses the same ".h" extension as C for its library and extension files sometimes causes issues when editing such files, because editors and source navigation tools assume that those Inform files are C headers.
Certain editors (ex. jEdit) can perform more sophisticated file type analysis, but others (ex. Notepad++) base the file type purely on the extension, and thus will always open .h files as C code.
Particularly when trying to load both the Inform compiler and standard library into an IDE project (in my case, Source Insight), that their extensions overlap causes problems with symbol referencing, etc.
This patch adds an '-I' switch that causes the compiler to search for a ".infh" file--falling back to ".h" if not present--when Include'ing a file from Inform source. In this way, an author can choose to rename the standard library files and any extensions to ".infh" to get customized syntax highlighting, etc.
This was discussed a while back:
https://intfiction.org/t/inform-6-error-when-compiling-with-d-without-the-library/45889
The -D option turns on the library's debug mode. (This dates from when the Inform compiler and library were always coupled.) The problem is that the veneer contains a lot of debug support that is meant to interact with the library, of the form:
#ifdef DEBUG;
if (debug_flag & FLAG) {
! argument safety checking
}
#endif;
The library must define the debug_flag
global, or this will not compile. The library must also define the workflag
attribute and the DebugAttribute()
printing routine.
This leads to surprising errors if someone tries to compile, say, glulxercise.inf with -D on.
The current recommendation is "Don't do that." (glulxercise.inf has no debug features for the -D switch to turn on.) I think that's good enough, so this is not a high priority issue. But let's keep the issue on file.
I'm trying to compile the current commit of Inform6 for EPOC32 which limits me to VC6 and an ancient version of GCC that don't support C99. There weren't many problems! A few variables not defined at the beginning of a scope, and snprintf
is missing, but I noticed something unusual that might not be related to C89/C99: "inform6.c" calls remove_temp_files
from "files.c", but that function doesn't exist, only unlink_temp_files
! This is easily fixed for me, but I wonder if this is supposed to be this way?
A declarative, efficient, and flexible JavaScript library for building user interfaces.
🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.
TypeScript is a superset of JavaScript that compiles to clean JavaScript output.
An Open Source Machine Learning Framework for Everyone
The Web framework for perfectionists with deadlines.
A PHP framework for web artisans
Bring data to life with SVG, Canvas and HTML. 📊📈🎉
JavaScript (JS) is a lightweight interpreted programming language with first-class functions.
Some thing interesting about web. New door for the world.
A server is a program made to process requests and deliver data to clients.
Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.
Some thing interesting about visualization, use data art
Some thing interesting about game, make everyone happy.
We are working to build community through open source technology. NB: members must have two-factor auth.
Open source projects and samples from Microsoft.
Google ❤️ Open Source for everyone.
Alibaba Open Source for everyone
Data-Driven Documents codes.
China tencent open source team.