Thank you @xxuejie and @janx for humoring this proposal!! I’m really glad to see you both active
You are right, the title was confusing!! I changed it to Allow some Output Lock Scripts to Validate
, feel free to provide additional feedback!
For reference, also @janx agree on this::
If we follow A and make lock scripts able to validate transaction outputs, then lock scripts are technically the same as type scripts, CKB cells would essentially have two “type” script slots behaving the same, despite difference on naming. The distinction between the two may be clear at the beginning, but as new use cases coming hackers would start to poking these two slots in unintended way, and because the distinction is merely a convention not a protocol rule, we’ll see similar “slot in use” problem again, e.g. app X uses “lock script” slot, app Y uses “type script” slot, app Z uses both “lock script” and “type script” slots. At that time some convention/standards are still required to avoid slot conflicts and achieve script composability between X/Z, Y/Z, and/or X/Y/Z.
The Weird Solution (that I Like, but would Not Use)
As I told @matt_ckb some time ago, you know what surprised me when I first started using Nervos L1?
- Having exactly two script slots guarding each cell!
- Why 2, not 1 nor 3?
- It seems an artificial limit justified by an arbitrary convention!!
In my eyes it could have been reasonable to:
- Allow any possible number of (type) script slots per cell (and no lock scripts).
- Allow any possible logical arrangement: while right now is an
AND
of two script slots, it would be reasonable to allow for a chain ofOR
andAND
like expressions in programming languages. - Allow each script to have its own dedicated data, clearly separated from the others.
Which is indeed strikingly similar to:
B.ii (weird but good for brain-storming) create a type/type script composing standard, e.g. abandon lock script completely, use type script for everything, every cell uses a ‘meta’ type script which can read cell data to determine what script/logic should be invoked and invoke them in turn.
It took a few hard-forks, but we are finally getting to this level of expressiveness
Good news is that spawn
has an advantage: we have the possibility of moving all this data from the expensive cell data to the inexpensive witness and anchor this witness data with just an hash in cell data.
That said, it’s a pretty big leap from the current way of developing on Nervos L1, so it’s likely not viable, at least for now.
Create a Lock/Type Script Composing Standard
B.i create a lock/type script composing standard, e.g. is it possible for a lock script to have certain callback functions, and a standard-compliant type script will always spawn those callback functions if they exist in the lock scripts in related cells?
This idea is indeed more approachable and it could lead to a pretty good standard, but it has two main areas that need refinement before calling this a workable standard.
Community-Agreed Standard
If we were to live in a L1 world where all type scripts and lock scripts were already standard-compliant, we would be discussing the obvious as it would be the already widely adopted solution.
While this seems the easy part, there is no Community Agreed Standard and it will likely stay that way for a some time as:
- It takes time to agree on such a standard, even between parties who want to opt-in.
- It takes much more time to make the other L1 devs understand that they should conform to such standard.
Of course, once we have a basic standard, I can spearhead it by adopting it in my upcoming Warranty Contracts.
Backward Compatibility
When starting to adopt such a standard all pre-existing type scripts and lock scripts will be not compliant and there are already quite a bit of them. This is the second non-naive part of the solution.
Lock Script Compatibility
This seems a naive problem. Lock Scripts are either compatible or not compatible:
- How to distinguish between compatible locks and non-compatible locks? (Naked spawn call or SSRI, just need to figure out the best practice
)
- Given a compatible script, how is this script able to identify its own code hash and reference type? (Just need to figure out the best practice
)
Type Scripts Compatibility
This is the non-naive problem:
This seems reasonable and actually a pretty good solution, but still has issues:
- Who can join these W-UDTs? Are these Wrapped UDTs public? If yes, then the underlying cells are shared among W-UDT holders. Malicious W-UDT holders can DoS the underlying UDT cells. Similar to the Busiwork Attack on iCKB, but worse given the natural liquidity of the wrapped assets
- The very same initial LO confusion attack, just applied to the lock used on the underlying non-compliant UDT cells being wrapped. That said, it should be easier to tackle now, as at each unwrapping we know both token and amount.
- Many or one underlying UDT cells? Who is the owner of the CKB used in the state-rent of the underlying UDT cells? What happens to these CKB when the last W-UDT is redeemed?
- What’s the relation between W-UDTs and gated-access UDTs? (For example, stable-coins such as USDI and USDT)
These kind of problems need to be considered and solved at least for baby problems before we can call this a workable solution. Allowing some Output Lock Scripts to Validate may very well be Blasphemy, but it doesn’t bring these problems.
@xxuejie @janx feel free to suggest more details, so we can understand it better and possibly integrate it in future protocols implementations
Love & Peace, Phroi