-
Notifications
You must be signed in to change notification settings - Fork 162
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Add Constant Var support #1682
Add Constant Var support #1682
Conversation
doc/ref/language.xml
Outdated
@@ -541,7 +541,30 @@ local variables or function arguments). | |||
<P/> | |||
First, such variables may be marked <E>read-only</E>. In which case | |||
attempts to change them will fail. Most of the global variables | |||
defined in the &GAP; library are so marked. | |||
defined in the &GAP; library are so marked. <E>read-only</E> variables | |||
can be made read-write again. GAP also features <E>constant</E> variables, |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Perhaps: "can be made read-write again [using the command XYZ]"
## named by the string <name> is constant and false otherwise (the default) | ||
## | ||
|
||
IS_CONSTANT_GLOBAL := IsConstantGVar; |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Meta-note: It's really crazy that we define kernel function using CamelCase, then define alternate names in SNAKE_CASE, and finally high level names again in CamelCase. (Of course this PR is just imitating what the surrounding code does, so the PR is fine; I just think we may want to resolve this in another PR in the future)
src/code.c
Outdated
// Some optimisation cases | ||
if (nr == 1) { | ||
if (TNUM_EXPR(cond1) == T_TRUE_EXPR) { | ||
// Leave Statement |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Statement -> statement
src/intrprtr.c
Outdated
** 'IntrSmallGAPIntExpr' is the action to 'interpret' a existing GAP small | ||
** integer. This is used for implementing constants. | ||
*/ | ||
void IntrSmallGAPIntExpr(Obj val) |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I really prefer to refer to "immediate integers", as "small integer" is quite ambiguous (a reader may not realize it has a technical meaning). So perhaps IntrImmediateIntExpr
and CodeImmediateIntExpr
?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Or ...IntObj
?
src/read.c
Outdated
else if (IS_INTOBJ(val)) | ||
IntrSmallGAPIntExpr(val); | ||
else | ||
SyntaxError("Invalid Constant Variable"); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
"Invalid Constant Variable" -> "Invalid constant variable"
tst/testinstall/constant.tst
Outdated
if boolfalsevar then | ||
return 6; | ||
fi; | ||
return; |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Hmm, perhaps also test if/elif/fi
and if/elif/else/fi
?
82d442d
to
76d68de
Compare
Codecov Report
@@ Coverage Diff @@
## master #1682 +/- ##
==========================================
+ Coverage 64.06% 64.07% +<.01%
==========================================
Files 999 999
Lines 322458 322550 +92
Branches 13025 13064 +39
==========================================
+ Hits 206593 206675 +82
- Misses 113146 113151 +5
- Partials 2719 2724 +5
|
I believe I have fixed issues, and written more tests. This PR includes a commit which fixes printing I agree the camel case / allcaps dance is weird (and I would like to remove the methods |
Note the optimisations this supports are currently very limited. It only simplifies code of the form |
76d68de
to
838d42c
Compare
BTW, why do you capitalise "Constant" in e.g. the commit message "Add Constant support" ? Shouldn't it be rather "Add support for constant variables" or so? |
lib/global.g
Outdated
@@ -92,6 +102,16 @@ MAKE_READ_WRITE_GLOBAL := MakeReadWriteGVar; | |||
|
|||
############################################################################# | |||
## | |||
#F MAKE_CONSTANT_GLOBAL ( <name> ) . . .make a global variable constant |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
add at least a space before "make". But actually there should be enough . . .
to right-align the text afterwards... Alternatively, just remove the whole . . .make a global variable constant
bit, as it is kind of redundant given the following text.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Still would like to see that space (or, as in my other comment: Remove that line).
lib/global.gd
Outdated
@@ -155,6 +170,26 @@ DeclareGlobalFunction("MakeReadWriteGlobal"); | |||
|
|||
############################################################################# | |||
## | |||
#F MakeConstantGlobal( <name> ) . . . . make a global variable constant |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
again the . . .
business... should change the triple spaces to a single one and insert more .
-- the same in other places, too, of course
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I copied the triple spaces from the function directly above, and below, this one. This file has either triple spaces, or double spaces, never a single one.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
There are 25 places in the whole library using a triple space in that location, i.e. less than 1% -- I think they come from somebody not being careful and/or not caring.
Now, I am first to agree that it sucks to manually update these kinds of comments. But I still think there are only two sane choices:
- Abolish them, possibly incrementally (by just not adding them to new code)
- Keep using them "as intended" -- and then triple spaces to me look quite clearly like a bug, which simply proliferates by copy&paste.
tl;dr: please either delete this line, or format it to match the rest of the library (and not just the rest of this comparatively short file).
lib/global.gd
Outdated
## MakeConstantGlobal ( <A>name</A> ) marks the global variable named | ||
## by the string <A>name</A> as constant. A constant variable can never | ||
## be changed or made read-write. Constant variables can only take an | ||
## integer value, <C>true</C> or <C>false</C>. |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
should that be "immediate integer value"? Hmm, though not everybody will know what that means..
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I don't think the concept is defined in the documentation -- not anywhere obvious, anyway. Maybe just say that there is a limit on the size of the integers.
lib/global.gi
Outdated
## MakeConstantGlobal ( <name> ) marks the global variable named | ||
## by the string <name> as constant | ||
## | ||
## A warning is given if <name> is already constant |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Add extra space before A warning
lib/global.gi
Outdated
## | ||
#F MakeConstantGlobal ( <name> ) . . . . make a global variable constant | ||
## | ||
## MakeConstantGlobal ( <name> ) marks the global variable named |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Why the weird wrapping here?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
once again, same as the wrapping on the function just before
doc/ref/language.xml
Outdated
can be made read-write again by calling <Ref Func="MakeReadWriteGlobal"/>. | ||
GAP also features <E>constant</E> variables, | ||
which can never be changed. In some cases, GAP can optimise code which | ||
uses <E>constant</E> variables, as their value never changes. |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Hmm, the user at this point knows very little about constants, and has no idea how to learn more. E.g. they won't know that only immediate integers and some booleans can be made constant. I'd add a ref to MakeConstantGVar
here, and then make sure they can learn enough about that in its documentation (which currently does not seem to exist...?).
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Getting back to this, it seems this this should be MakeConstantGlobal
instead (also in the example below)
src/code.c
Outdated
Stat body2 = PopStat(); | ||
cond2 = PopExpr(); | ||
PushExpr(cond2); | ||
PushStat(body2); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
You don't really need to pop/push body2
(and the original code also did not need to push/pop body
...
// Remove entire if statement | ||
PopStat(); | ||
PopExpr(); | ||
PushStat(NewStat(T_EMPTY, 0)); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Hmm... is that PushStat
really necessary?
src/gvars.c
Outdated
@@ -799,10 +856,9 @@ Obj FuncMakeReadWriteGVar ( | |||
Int IsReadOnlyGVar ( | |||
UInt gvar ) | |||
{ | |||
return !INT_INTOBJ(ELM_GVAR_LIST(WriteGVars, gvar)); | |||
return INT_INTOBJ(ELM_GVAR_LIST(WriteGVars, gvar)) == 0; |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Rewrite this as return ELM_GVAR_LIST(WriteGVars, gvar) == INTOBJ_INT(0)
src/gvars.c
Outdated
Obj self, | ||
Obj name ) | ||
{ | ||
/* check the argument */ |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Personally, I try to avoid those "right aligned with lots of spaces" comments, and just use C++ style //
comments. While this makes the new code slightly different than the old code, I think we should eventually replace all those weird aligned comments with these
(That's just a vague suggestion, not an actual request to change the PR).
ab2a9dd
to
f245a79
Compare
function (name) | ||
local isro; | ||
CheckGlobalName( name ); | ||
isro := IS_CONSTANT_GLOBAL(name); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Why "isro" ? Probably copy & paste from IsReadOnlyGlobal
, but this name doesn't make sense here.
@@ -1616,6 +1654,11 @@ void CodePow ( void ) | |||
} | |||
|
|||
|
|||
void CodeGAPSmallInt(Obj val) |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I'd really prefer if this was called CodeImmediateInt
-- saying "small int" is quite ambiguous. This code instead deals with "immediate integer handles" (to use the language from gmpints.c
)
[ Sorry, I thought I had mentioned this in my previous PR? But perhaps I failed to actually submit that comment? I can't find it now, in any case :-/ ]
#ifdef HPCGAP | ||
UInt var = GVarName( "HPCGAP" ); | ||
AssGVar( var, True ); | ||
MakeReadOnlyGVar( var ); | ||
MakeConstantGVar( var ); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Perhaps IsBound(CONST_VAR)
should be optimized true
if CONST_VAR
is bound during coding? (I am not asking for this to be done in this PR, just wondering)
*/ | ||
Int IsConstantGVar(UInt gvar) | ||
{ | ||
return INT_INTOBJ(ELM_GVAR_LIST(WriteGVars, gvar)) == -1; |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Better (and slightly safer...) code can be generated if you instead write return ELM_GVAR_LIST(WriteGVars, gvar) == INTOBJ_INT(-1);
-- this would then also match IsReadOnlyGVar
above.
lib/global.gd
Outdated
@@ -155,6 +170,26 @@ DeclareGlobalFunction("MakeReadWriteGlobal"); | |||
|
|||
############################################################################# | |||
## | |||
#F MakeConstantGlobal( <name> ) . . . . make a global variable constant |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
There are 25 places in the whole library using a triple space in that location, i.e. less than 1% -- I think they come from somebody not being careful and/or not caring.
Now, I am first to agree that it sucks to manually update these kinds of comments. But I still think there are only two sane choices:
- Abolish them, possibly incrementally (by just not adding them to new code)
- Keep using them "as intended" -- and then triple spaces to me look quite clearly like a bug, which simply proliferates by copy&paste.
tl;dr: please either delete this line, or format it to match the rest of the library (and not just the rest of this comparatively short file).
@@ -825,6 +881,34 @@ static Obj FuncIsReadOnlyGVar ( | |||
return IsReadOnlyGVar(GVarName(CSTR_STRING(name))) ? True : False; | |||
} | |||
|
|||
/**************************************************************************** | |||
** | |||
*F IsConstantGVar( <gvar> ) . . . . . . return if a variable is a constant |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Hrmf, somehow GitHub decided that the comments I was collecting for a review were all to be suddenly published as comments instead, taking away from me the possibility to edit them beforehand... I was about to add the following (or possibly, replace those comments completely with it) regarding the comment formatting: "OK, I see now that these files you are touching are particularly bad when it comes to the comment formatting (and grammar...). So it probably makes more sense to go over them separately later on, and to "clean up" those comments, and/or to remove parts of them."
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Overall, this looks good to me now. There are some minor formatting issues in my view (such as places with double empty lines or trailing spaces, new code which has comments of the form /* some text + a zillion spaces for right-aligning */
instead of // some text
, etc., and perhaps 1-2 other minor chances for improvements, but nothing really that warrants holding this back much longer.
I'd still feel better if @stevelinton or @markuspf also had a look at this before merging.
My only concern with this is that if we want to take it further and have a "proper" optimisation framework then quite a bit of it will be superceded. On reflection though, it would be the implementation, and maybe the printing of functions that had optimised versions that would change, and not the UI. This may be developed further in future -- for instance a Constant Var holding a function would allow inlining. I imagine in future we might also stop printing the optimised versions of functions, but rather hold the original and the optimised bodys and print one while running the other, so again maybe the documentation should make clear that this may change, but we promise it will never hurt to make constant things constant. |
I agree about saying that we don't promise to show optimised functions. I would prefer a general framework based on @markuspf's transforming of GAP functions to GAP objects -- in particular I would love GAP to have inlining. Also, I don't think we should expand this much further -- it would be easy to continue through the parser and handle things like |
Supporting simplification of Of course it's tricky were to draw the line... Simplifying expressions like And I really think this would already provide some nice (minor) speed up for some code, without needing the full power (and considerable complexity) of a full code transformation framework... Anyway, that's just some thoughts, but of course they in no way speak against this PR :-). |
doc/ref/language.xml
Outdated
GAP also features <E>constant</E> variables, which are created by calling | ||
<Ref Func="MakeConstantGlobal"/>. Constant variables can never be changed. | ||
In some cases, GAP can optimise code which uses <E>constant</E> variables, | ||
as their value never changes. This can be observed by printing the |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I would delete the sentence beginning "This can be observed", or add a warning that that might change.
Otherwise approved.
lib/global.gd
Outdated
## MakeConstantGlobal ( <A>name</A> ) marks the global variable named | ||
## by the string <A>name</A> as constant. A constant variable can never | ||
## be changed or made read-write. Constant variables can only take an | ||
## integer value, <C>true</C> or <C>false</C>. |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I don't think the concept is defined in the documentation -- not anywhere obvious, anyway. Maybe just say that there is a limit on the size of the integers.
f245a79
to
96f3d2a
Compare
@ChrisJefferson just adding ManSection to the documentation does not automatically add it to the manual - it needs to be hooked somewhere via the Perhaps we can detect unresolved cross-references too - but should carefully do that to ignore reports on them during the first run of the build. |
This adds to gap the concept of a constant variable. They are created with
MakeConstantVar
, and behave similarly toMakeReadOnlyVar
, except:The inlining is always done, and further to interpreter will inline away
if
statements of the formif constvar then...
for a constant variableconstvar
.