Unstable feature gates
Is your feature request related to a problem? Please describe.
In the past year or so we've been aggressively adding new features to bpftrace. It's becoming more clear we need to strike a balance between upfront design and real-world experimentation. To give ourselves space to make bold experiments, I propose we start adding a new class of "unstable" config flags.
Unstable config flags are regular config flags except they're all prefixed with unstable_. They cannot be set through environment variable - they are only accepted through source. The goal is to make the user acknowledge that the feature they're opting into is unstable. Which means we can change or remove it at any time. Up to and including silent semantic changes. This frees us from having to worry about backwards compat when trying new things out.
The long term goal of anything unstable feature is we stabilize it. It's as simple as making the flag a noop and deleting the on/off checks. But this is always an option. We can decide it's no good and just delete it all.
Describe the solution you'd like
For the new let syntax in #3461, it could be:
config = {
unstable_let = true;
}
If it's not set, then user gets an error if let is used. Unstable configs are not allowed to be set to false.
Describe alternative solutions or features you've considered
New syntax. But I don't think it's necessary as we already have all the config infra.
I like this, it could lift some pressure of making these big features future-proof and backwards-compatible from the very beginning.
I'm not sure how it would work for some features, though. For instance, the let syntax can be made unstable on its own but it's a prerequisite for block scoping and I'm not sure how "optional block scoping" would work (and be implemented). We will probably want to limit this to features which can be easily enabled/disabled so that we don't end up with tens of if-conditions in the code for each feature.
Anyways, this could be a nice thing to have.
Echoing @viktormalik - I like this in theory but it really depends on the feature and how easily it can be separated. Even if we didn't want to sprinkle the code with tons of if conditions and just created a single choke point in an AST pass, I don't know how we'd gate let and block scoping. Ultimately, I think I'd have to see this config in a real example to make a decision on it.
Regarding block scoping and let, agreed, tricky to separate the two. However, in my opinion, fixing block scoping is not an urgent issue. It would be preferable to ensure we got the var decl semantics correct before further building on top of it.
As for implementation on gating let, my feeling is it should be possible to create a new pass to check it. I don't think it should be too hard - all the decl info is in the AST right? So we just need to look at the right fields on the right nodes.
@danobi and I chatted offline about this a bit.
In regards to var decl semantics, I think the trickiest part is not the variable declaration but rather the type resolution, which I do think is important (urgent-ish) if we want to get user-defined functions unblocked as those will require argument and return types. I think variable declarations is a good start to seeing what problems may shake out with those. The let syntax also went through an EXTENDED review process and it's a feature that I don't see a lot of people reaching for anyway unless they need to resolve a scoping issue.
For block-scoping, the work is already done and as folks pointed out in the comments for the original issue (https://github.com/bpftrace/bpftrace/issues/3017), users shouldn't be relying on this buggy behavior anyway so I don't think we should feature gate OR delay landing it. It's an improvement to the user experience as it points out where someone might have buggy/undefined behavior. Remember we had a majority in favor of shipping this without variable declarations, which have now landed.
All this to say, I'm not opposed to feature gating in general, it's probably a good way to get stuff battle tested without having to fully support it.
Agreed. Let's keep unstable gates out of var decls and block scoping. Moving forward there are some much more obvious places to apply unstable gates.
We have started to use this for map declarations and the new import syntax. It's also in our repo docs.