Skip to content
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

nullable Storage.Get; refactor TokenContract #1214

Open
wants to merge 16 commits into
base: master
Choose a base branch
from

Conversation

Hecate2
Copy link
Contributor

@Hecate2 Hecate2 commented Oct 24, 2024

This PR is a bit risky and may affect existing contract codes. I do not mind abandoning it if not good.
Storage.Get may actually return null. Ignoring it without generating any warning for the contract developer is not good.
Also it is not the best to blindly translate null to BigInteger 0. And it costs GAS to check whether a ByteString is null, when converting it to BigInteger.
Judging null increases contract size, but can be optimized by #1213 .

@Jim8y
Copy link
Contributor

Jim8y commented Oct 24, 2024

This will not affect existing contract, unless they compile it again.... so, not really a big deal, we can add a warning to the contract when they build it. But the behavior should be properly commented. Such that developers can see how it works when they use it.

@@ -54,11 +54,6 @@ IEnumerator IEnumerable.GetEnumerator()
[OpCode(OpCode.CONVERT, StackItemType.ByteString)]
public static extern explicit operator ByteString(byte[] buffer);

[OpCode(OpCode.DUP)]
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I prefer to avoid this change for the moment, only nullables

…to nullable-get

# Conflicts:
#	tests/Neo.SmartContract.Template.UnitTests/templates/neocontractnep17/TestingArtifacts/Nep17ContractTemplate.artifacts.cs
@Hecate2 Hecate2 marked this pull request as ready for review October 25, 2024 06:33
@Jim8y Jim8y requested a review from shargon October 25, 2024 15:55
@Hecate2
Copy link
Contributor Author

Hecate2 commented Oct 25, 2024

NUMEQUAL can be used in TokenContract

@@ -112,7 +112,9 @@ public extern ByteString this[byte[] key]
[OpCode(OpCode.CAT)]
[OpCode(OpCode.SWAP)]
[Syscall("System.Storage.Get")]
public extern ByteString Get(ByteString key);
#pragma warning disable CS8632 // The annotation for nullable reference types should only be used in code within a '#nullable' annotations context.
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Enable nullable at the beginning of the file?

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

OK. Maybe I shall just delete the pragma comments

@@ -17,35 +17,49 @@ namespace Neo.SmartContract.Framework
{
public abstract class TokenContract : SmartContract
{
protected const byte Prefix_TotalSupply = 0x00;
protected const byte Prefix_Balance = 0x01;
protected static readonly ByteString Prefix_TotalSupply = "\x00";
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Why not const?

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

ByteString is really cheaper when used for storage.get/put. Also static readonly ByteString can be optimized to const now.

@@ -27,11 +27,13 @@ public extern bool IsValid
{
[OpCode(OpCode.DUP)]
[OpCode(OpCode.ISTYPE, "0x28")] //ByteString
[OpCode(OpCode.SWAP)]
[OpCode(OpCode.JMPIF, "06")] // to SIZE
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This is cheaper?

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Yes, and better for NZ/ISNULL and folding NOT in optimization

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Also this avoids executing SIZE on a possibly null input, and further saves if (input is null) before using isValid

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This should be in a different PR

@Jim8y Jim8y requested a review from shargon October 27, 2024 07:06
@@ -60,14 +60,14 @@ public static void SetOwner(UInt160 newOwner)

public static new void Burn(UInt160 account, BigInteger amount)
{
if (IsOwner() == false)
Copy link
Contributor

@Jim8y Jim8y Oct 27, 2024

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

actually == false is a better format as it is reader friendly, but anyway. i dont mind.

# Conflicts:
#	tests/Neo.Compiler.CSharp.UnitTests/TestingArtifacts/Contract_Linq.cs
#	tests/Neo.Compiler.CSharp.UnitTests/TestingArtifacts/Contract_NEP11.cs
#	tests/Neo.Compiler.CSharp.UnitTests/TestingArtifacts/Contract_NEP17.cs
#	tests/Neo.SmartContract.Framework.UnitTests/TestingArtifacts/Contract_SupportedStandard11Enum.cs
#	tests/Neo.SmartContract.Framework.UnitTests/TestingArtifacts/Contract_SupportedStandard17Enum.cs
#	tests/Neo.SmartContract.Template.UnitTests/templates/neocontractnep17/TestingArtifacts/Nep17ContractTemplate.artifacts.cs
#	tests/Neo.SmartContract.Template.UnitTests/templates/neocontractowner/TestingArtifacts/OwnableTemplate.artifacts.cs
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

3 participants