Forum > Beginners

[Solved] Is it possible to const an argument passed by reference in FPC?

<< < (5/13) > >>

lucamar:

--- Quote from: ASerge on July 25, 2019, 10:55:40 am ---I would have changed the approach. The default is to consider all the parameters are const by default. I.e. it is impossible to assign them something. If want to change, declare a local variable and assign to it. In this case, the const modifier could be omitted. And there are languages where the input parameter cannot be changed if it is not explicitly declared changeable (var in Pascal).
--- End quote ---

That would break quite a lot of code bases. I've used languages which do what you say and it's a small nigtmare: first thing you do, almost automatically, is move the parameters to local variables, with the subsequent waste of stack/memory.

I prefer "the Pascal way" where unqualified params are basically local vars which happen to be initialized on the call and where you mark deviations of this norm with var, const, out, etc.

440bx:

--- Quote from: Zoran on July 25, 2019, 03:07:23 pm ---The meaning of const will not change in future versions.

--- End quote ---
You are interpreting what PascalDragon said a different way than I am.  He said :

--- Quote from: PascalDragon on July 25, 2019, 09:55:53 am ---Also the behaviour of const might change with each version of FPC as it's not part of the platform ABI, thus it might be that in some newer version it's decided to pass a parameter type in a more optimal way.

--- End quote ---
To me that means, the meaning of const is not fixed, there is no guarantee that const will behave in one version the same way it behaves in another.  For me, that is more than enough not to use it.


--- Quote from: Zoran on July 25, 2019, 03:07:23 pm ---But you should understand well that the meaning of const has nothing to do about whether it is passed by reference or by value.

--- End quote ---
It shouldn't but, unfortunately it does.  Sometimes "const" means a parameter passed by reference which cannot be used as an l-value and, some other times, it only means "constant".

Borland is responsible for muddying that water by associating semantics to const that have nothing to do with declaring a parameter is constant.


--- Quote from: Zoran on July 25, 2019, 03:07:23 pm ---Unless for some reason you need to know whether it will be passed by value or by reference (and you would very rarely need to know it, why would you?)

--- End quote ---
There are quite a few times when you _really_ need to know.  Here is an example, the buffer parameter of the WriteFile windows API is declared as "const buffer" (untyped).  I was porting some C code to FPC, I pass the pointer to my buffer to WriteFile and I'm getting garbage out.  I look at the code and it's perfectly fine, in full accordance with how WriteFile is documented.  After a little bit of digging, I find that FPC is passing a pointer to my buffer pointer (pointer to pointer) instead of just the pointer to my buffer, that because of "const". 

"Solution:" if you have a pointer to a buffer you want to pass to WriteFile, you have to dereference the pointer, which should not be necessary (at least as documented in MSDN) and, forgetting to dereference the pointer will reward you with either garbage or even possibly an access violation in some cases.

The behavior of "const", when used as a parameter modifier, is not precisely and accurately defined, for that reason, it's only a source of headaches.

ASerge:

--- Quote from: lucamar on July 25, 2019, 03:13:49 pm ---That would break quite a lot of code bases.

--- End quote ---
Something like {$IMPLICITCONST ON}


--- Quote ---I've used languages which do what you say and it's a small nigtmare: first thing you do, almost automatically, is move the parameters to local variables, with the subsequent waste of stack/memory.

--- End quote ---
You always change input parameters?

lucamar:

--- Quote from: ASerge on July 25, 2019, 05:01:57 pm ---You always change input parameters?

--- End quote ---

Not always, no. Not even in most cases, now. But sometimes it just happens that the parameter is the more apropriate var to use. For example, if you have a function declared like, say, PosEx(), its Offset parameter might be handy to iterate through a string/array doing whatever it does and it's already initialized to the desired starting value.

Of course, it depends on what the function does and how, but having that "local" var already init'ed and waiting to be be used is sometimes a nice bonus.

The question is not really one of "changing parameters" but of using them as "local vars" (which, after all, they basicaly are)

Zoran:

--- Quote from: 440bx on July 25, 2019, 03:53:11 pm ---
--- Quote from: Zoran on July 25, 2019, 03:07:23 pm ---The meaning of const will not change in future versions.

--- End quote ---
You are interpreting what PascalDragon said a different way than I am.  He said :

--- Quote from: PascalDragon on July 25, 2019, 09:55:53 am ---Also the behaviour of const might change with each version of FPC as it's not part of the platform ABI, thus it might be that in some newer version it's decided to pass a parameter type in a more optimal way.

--- End quote ---
To me that means, the meaning of const is not fixed, there is no guarantee that const will behave in one version the same way it behaves in another.  For me, that is more than enough not to use it.

--- End quote ---

As I understand, it means that what might change is how compiler makes decision whether to pass a const parameter -- by value or by reference.

What does not change is the fact which is clearly documented -- that it is not guaranteed how parameter will be passed and that you must not assume that it is passed by reference.

So, what can change is just implementation detail, nothing else.
This is how I understand what PascalDragon meant. I hope he will see this and clarify what he meant.


--- Quote from: 440bx on July 25, 2019, 03:53:11 pm ---
--- Quote from: Zoran on July 25, 2019, 03:07:23 pm ---But you should understand well that the meaning of const has nothing to do about whether it is passed by reference or by value.

--- End quote ---
It shouldn't but, unfortunately it does.  Sometimes "const" means a parameter passed by reference

--- End quote ---

Not in FPC. It only means that it is constant. How it is passed is implementation detail (as such, it can change in future, if you don't rely on it, you will never encounter bad surprises).

If by "sometimes", you mean Delphi vs FPC, then yes, here FPC and Delphi are different (which is also clearly documented).


--- Quote from: 440bx on July 25, 2019, 03:53:11 pm ---Borland is responsible for muddying that water by associating semantics to const that have nothing to do with declaring a parameter is constant.

--- End quote ---

True, but here FPC developers decided not to follow Delphi blindly. So, in FPC const means that it is constant, nothing else. This will not change in future versions.


--- Quote from: 440bx on July 25, 2019, 03:53:11 pm ---
--- Quote from: Zoran on July 25, 2019, 03:07:23 pm ---Unless for some reason you need to know whether it will be passed by value or by reference (and you would very rarely need to know it, why would you?)

--- End quote ---
There are quite a few times when you _really_ need to know.  Here is an example, the buffer parameter of the WriteFile windows API is declared as "const buffer" (untyped).  I was porting some C code to FPC, I pass the pointer to my buffer to WriteFile and I'm getting garbage out.  I look at the code and it's perfectly fine, in full accordance with how WriteFile is documented.  After a little bit of digging, I find that FPC is passing a pointer to my buffer pointer (pointer to pointer) instead of just the pointer to my buffer, that because of "const". 

--- End quote ---

Then it is wrongly declared, it is wrong translation of win api header.
Where is it declared? If in FPC sources, this is a bug which should be reported.
If third party, then it might have been translated to be used with Delphi, and yes, we know that const parameter passing is not compatible with FPC.

With external routines we truly have to know how parameters are passed. So, yes, const parameters should be avoided in external declarations. There you have the point. Don't use it there.

Navigation

[0] Message Index

[#] Next page

[*] Previous page

Go to full version