C++ Logo

std-proposals

Advanced search

Re: [std-proposals] Function overload set type information loss

From: Tiago Freire <tmiguelf_at_[hidden]>
Date: Thu, 1 Aug 2024 09:16:48 +0000
We are always coming back to the same things, and there's no progress being done.

Here's the thing, I don't think this would work, I have no idea on how to make this work. And I'm not the only one sharing this opinion.
But I'm going to give you the benefit of the doubt.
At the end of the day we got to make a compiler do this. So, here's where you can find the source code for popular compilers:

https://github.com/gcc-mirror/gcc

https://github.com/llvm/llvm-project

But you can pick any other compiler of your choosing, whatever it is you are most comfortable with, any compiler that can make this work will do.

Show me a sample code being generated with your proposal (which I think given the skepticism it is quite warranted).
And then we can reconsider a discussion.

Br,
Tiago



________________________________
From: Std-Proposals <std-proposals-bounces_at_[hidden]> on behalf of organicoman via Std-Proposals <std-proposals_at_[hidden]>
Sent: Thursday, August 1, 2024 10:47:19 AM
To: Thiago Macieira via Std-Proposals <std-proposals_at_[hidden]>
Cc: organicoman <organicoman_at_[hidden]>
Subject: Re: [std-proposals] Function overload set type information loss




We can only do step 2 if we have a working compiler. Since we don't, we can't
use the steps above.

We have to replace the step of "use" with the rules and the rules are too
vague at this point.

That's a honest and direct question. I like this way of discussion,

Instead of attacking the proposal by downgrading the understanding of its writer, like some do, It is preferable to say "i don't see this coner, can you enlighten me"...no shame.

I'm still waiting for motivation and use-cases.

Alright,
The core dea, is to keep all meaningful information that participated in generating machine code.

For example:
----
template<int t>
int F(int x)
{ return ( t * x ) + 1; }
----
>From this function template,  it is clear that the non type template parameter, is participating in the machine code instantiated from the template.
So it is an important peace of information, useful to reason about the machine code of any function created from that template.
Now, if i want to automate my reasoning about the behavior of that code, i need a way to extract that information back ( the t above) but with the current C++ there is no way to trace back to it.
So this motivates me, to find a way to gain access to that information.
That's the main motivation.
On the other hand, millions lines of code rely on the current behavior of C++.
So if i try to add that information to the type system,  for sure it will break all code.
Also, since many peace of code seems to work without the need of that information (either by choice or by obligation), it denote that it is optional.
A rigorous solution should take the above in consideration.
That's the core of the proposal.
The way to implement it is an exercise to the reader, each and everyone has a different approach.
---- one way of implementing the motivation-----
My approach,  is to add an operator called effdecltype (the name is not important)
This operator must have some properties.
One property is that : it can replace the operator decltype without disturbing its current meaning.
2nd property is that: it can trigger the desired behavior when applied to 3 types only and on demand : arrays, instance of function templates, instance of variable templates
----- end of my approach ------
While researching to implement the above, I stambled on other motivations that were not considered at all.
1- reflection:
Knowing that the current implementation of any reflection algorithm, must use some static text to store information about RTTI.
That's not safe!
Because we are already storing pointers to functions in our data, which breaks the ASLR safety mechanism , then adding text that can help decompile the code, is definitely not safe.
So i found that, if I abuse my operator, and tweak the compiler,  i can port reflection from runtime to compile time, and erase any static text in my binary in favore of generating more code.
2- type manipulation:
Again by abusing the operator, i can simulate type manipulation at compile time.
For example i can abuse it to create a stack of types,  where i can push and pop types, then freeze all when generating machine code.
...and so on, the possibility are considerable.
I was trying to solve some problem,  i found solutions to unrelated problems.
Implementation wise:
The scope of the operator above is well defined.
Arrays, instances of function templates and instances of variable templates.
So it is feasible to reason about the code using them, and build a compilation planner that can prove then pick the right technique to generate code.
In my example, at the end of the paper, i abused the operator to store types in a container and fetch them in a loop.
So from compiler stand point, there are two case figure.
Either the compiler can see what was pushed to that container,  or it is unpredictable to do so.
Two solutions are plausible.
1- replace the stored instance of the global value with some key, then add a hash map:
Key<->function, no need to predict any thing.
2- unroll the loop if we can prove that we have all elements of the container available and it is efficient to do so.
Again, this is abusing the operator's behavior  from its main purpose. Yet, it is useful and feasible.
Thiago,
I hope i answered your question?

Received on 2024-08-01 09:16:53