Commit graph

1470 commits

Author SHA1 Message Date
Evgenii Stratonikov
dcaa82b32b rpc: convert null value to a defaultT
Right now we convert it is unmarshaler into a float64(0)
so an error is supressed.
2020-06-08 16:39:02 +03:00
Roman Khimov
6437f4b32e core: respect MaxFreeTransactionsPerBlock setting
Fix #1019.
2020-06-08 12:35:39 +03:00
Evgenii Stratonikov
9f7f94a6fb compiler: implement Remove builtin
Support removing items from collections via REMOVE opcode.
2020-06-08 12:05:44 +03:00
Anna Shaleva
4f1cf07075 compiler: add public key recovering syscalls
Added Secp256r1Recover and Secp256k1Recover syscalls.
2020-06-05 22:13:17 +03:00
Evgenii Stratonikov
7b1a54c934 rpc/server: unify boolean flag handling
Implement (*Param).GetBoolean() for converting parameter to bool value.
It is used for verbosity flag and is false iff it is either zero number
or empty sting.
2020-06-05 12:51:09 +03:00
Evgenii Stratonikov
44f93c7c69 rpc/server: simplify errors handling during parameter parsing 2020-06-05 12:51:09 +03:00
Roman Khimov
a1c4d7ce26 core: do MPT compaction every once in a while
We need to compact our in-memory MPT from time to time, otherwise it quickly
fills up all available memory. This raises two obvious quesions --- when to do
that and to what level do that.

As for 'when', I think it's quite easy to use our regular persistence interval
as an anchor (and it also frees up some memory), but we can't do that in the
persistence routine itself because of synchronization issues (adding some
synchronization primitives would add some cost that I'd also like to avoid),
so do it indirectly by comparing persisted and current height in `storeBlock`.

Choosing proper level is another problem, but if we're to roughly estimate one
full branch node to use 1K of memory (usually it's way less than that) then we
can easily store 1K of these nodes and that gives us a depth of 10 for our
trie.
2020-06-04 17:25:57 +03:00
Roman Khimov
e3af560d11 dao: optimize storage cache flushing
Items were serialized several times if there were several successful
transactions in a block, prevent that by using State field as a bitfield (as
it almost was intended to) and adding one more bit. It also eliminates useless
duplicate MPT traversions.

Confirmed to not break storage changes up to 3.3M on testnet.
2020-06-04 17:21:58 +03:00
Roman Khimov
69ccca675d core: fix PrevHash calculation for MPTRoot
This was differing from C# notion of PrevHash. It's not a previous root, but
rather a hash of the previous serialized MPTRoot structure (that is to be
signed by CNs).
2020-06-04 17:19:30 +03:00
Roman Khimov
685d3eb870 dao: prevent double serialization of StorageItems
Converting to MPT value serializes the StorageItem, so it makes no sense doing
it again.
2020-06-04 17:18:15 +03:00
Roman Khimov
f77c239296 mpt: fix extension node cache invalidation
It should always be invalidated if something changes in the `next` (below the
extension node).
2020-06-04 17:16:32 +03:00
Evgenii Stratonikov
5794bdb169 state: implement JSON marshaling for MPT* items 2020-06-03 18:09:28 +03:00
Roman Khimov
24785f1f50
Merge pull request #1008 from nspcc-dev/feature/mpt
core: update MPT during block processing
2020-06-03 16:07:04 +03:00
Roman Khimov
baafa30266
Merge pull request #1006 from nspcc-dev/interop/crypto
core: implement key recover interops
2020-06-03 14:39:44 +03:00
Anna Shaleva
6c06bc57cc core: implement key recover interops
Implement secp256k1 and secp256r1 recover interops, closes #1003.

Note:

We have to implement Koblitz-related math to recover keys properly
with Neo.Cryptography.Secp256k1Recover interop as far as standard
go elliptic package supports short-form Weierstrass curve with a=-3
only (see https://github.com/golang/go/issues/26776 for details).
However, it's not the best choise to have a lot of such math in our
project, so it would be better to use ready-made solution for
Koblitz-related cryptography.
2020-06-03 14:36:04 +03:00
Evgenii Stratonikov
10189b6ab3 consensus: extend payloads with StateRoot info
Create and verify witness after block processing.
2020-06-03 13:33:44 +03:00
Evgenii Stratonikov
edcfdb3bde network: add MPT-related P2P payloads 2020-06-03 13:33:44 +03:00
Evgenii Stratonikov
20f190ef69 core: update MPT during block processing 2020-06-03 13:33:44 +03:00
Roman Khimov
029fecbb71 mpt: don't flush nodes already present in the DB
It's just a waste of time.
2020-06-03 00:37:30 +03:00
Roman Khimov
1b6aee42d5 mpt: restructure nodes a bit, implement serialization and hash cache
It drastically reduces the number of allocations and hash calculations.
2020-06-03 00:37:21 +03:00
Roman Khimov
fd73310a1c
Merge pull request #1007 from nspcc-dev/update-dbft-2.x
consensus: update dbft to include CountFailed and RecoveryMessage changes
2020-06-02 22:44:46 +03:00
Roman Khimov
e4f413aa29 consensus: update dbft to include CountFailed and RecoveryMessage changes
dbft interface changed a little also because of Neo 3 changes, but it still is
compatible with Neo 2.
2020-06-02 11:12:47 +03:00
Roman Khimov
2f90a06db3
Merge pull request #990 from nspcc-dev/feature/mpt
Initial MPT implementation (2.x)
2020-06-01 18:58:35 +03:00
Evgenii Stratonikov
314430be1d mpt: implement NEO storage key conversion 2020-06-01 18:15:13 +03:00
Evgenii Stratonikov
103c45850a mpt: implement (*Trie).Collapse()
Because trie size is rather big, it can't be stored in memory.
Thus some form of caching should also be implemented. To avoid
marshaling/unmarshaling of items which are close to root and are used
very frequenly we can save them across the persists.
This commit implements pruning items at the specified depth,
replacing them by hash nodes.
2020-06-01 18:15:13 +03:00
Evgenii Stratonikov
9c478378e1 mpt: implement JSON marshaling/unmarshaling
Because there is no distinct type field in JSONized nodes, distinction
is made via payload itself, thus all unmarshaling is done via
NodeObject.
2020-06-01 18:15:13 +03:00
Evgenii Stratonikov
31d9aeddd2 mpt: implement MPT proof Get and Verify 2020-06-01 18:14:19 +03:00
Evgenii Stratonikov
861a1638e8 mpt: implement MPT trie
MPT is a trie with a branching factor = 16, i.e. it consists of sequences in
16-element alphabet.
2020-06-01 18:14:19 +03:00
Roman Khimov
9a0d7d3254 transaction: gofmt -s 2020-05-30 15:48:57 +03:00
Roman Khimov
06bed2b4bf dao: split GetStorageItem for Cached into external and internal versions
Lower Cached state shouldn't be changed until Persist. Fixes #994.
2020-05-27 18:34:41 +03:00
Evgenii Stratonikov
b0d07c3031 vm: make Iterator interface public
There is nothing wrong with iterators being implemented in other parts
of code (e.g. Storage.Find). In this case type assertions can
prevent bugs at compile-time.
2020-05-27 11:40:46 +03:00
Evgenii Stratonikov
503442a60d dao: restrict GetStorageItems by prefix
All storage items can still be retrived via zero-length prefix.
2020-05-27 11:40:46 +03:00
Evgenii Stratonikov
776bd85ded vm,dao: return storage iterator from DAO in Storage.Find interop
Reproduce behavior of the reference realization:
- if item was Put in cache after it was encountered during
  Storage.Find, it must appear twice
- checking if item is in cache must be performed in real-time
  during `Iterator.Next()`
2020-05-27 11:40:46 +03:00
Evgenii Stratonikov
86ce234d5f core: fix a typo in GetUnspentCoins interop
Fix a bug introduced in 8ed77f0d.
2020-05-25 11:14:44 +03:00
Evgenii Stratonikov
eeeb05fc2c compiler: restore support for GetUnspentCoins
Revert a587274.
2020-05-22 13:24:44 +03:00
Evgenii Stratonikov
8ed77f0d25 core: make GetUnspentCoins interop return array, fix #978. 2020-05-22 13:24:43 +03:00
Roman Khimov
fb9b2ae982
Merge pull request #975 from nspcc-dev/clone-struct-in-setitem-2.x
vm: clone struct item on SETITEM, close #972
2020-05-21 18:02:06 +03:00
Roman Khimov
f8b41e486c vm: clone struct item on SETITEM, close #972
It's the same as with APPEND and VALUES.
2020-05-21 17:56:26 +03:00
Evgenii Stratonikov
a8fa68914a vm: allow to convert Map item to bool 2020-05-21 17:53:19 +03:00
Roman Khimov
e07fd4f9f0
Merge pull request #973 from nspcc-dev/fix/refcount
vm: update stack size in SETITEM properly
2020-05-21 16:47:27 +03:00
Evgenii Stratonikov
cd8445aa59 vm: update stack size in SETITEM properly 2020-05-21 15:20:37 +03:00
Roman Khimov
60bca03577 crypto: add input data length check in (*PublicKey).DecodeBytes
DecodeBinary works with streams, so it can't do that, but DecodeBytes can and
should. Also fix unmarshalled binary buffer that this check exposed.
2020-05-21 14:28:16 +03:00
Roman Khimov
0ce3a12e87 core: check for key length in CheckWitness, fix #968
Only one type of keys is allowed here.
2020-05-21 14:27:41 +03:00
Roman Khimov
d0853c0471
Merge pull request #967 from nspcc-dev/fix-pickitem-and-vm-cli-2.x
Fix pickitem and vm cli 2.x
2020-05-21 13:37:35 +03:00
Roman Khimov
1721360dd1 vm: limit types accepted for PICKITEM, fix #965
bafdb916a0 change was wrong (probably brought
from neo-vm 3.0 at the state at which it existed back then), neo-vm 2.x
doesn't allow PICKITEM for arbitrary types.
2020-05-21 12:16:38 +03:00
Roman Khimov
328c6d7ce5 vm/cli: fix step command
It was setting a (wrong) breakpoint and couldn't then break out of it.
2020-05-21 12:15:50 +03:00
Roman Khimov
318ca55982 vm/cli: add push command to push something to the estack 2020-05-21 12:15:24 +03:00
Roman Khimov
5ec70b9fc2
Merge pull request #930 from nspcc-dev/fix/keys
Cache storage operations across same block tx executions
2020-05-21 11:08:42 +03:00
Evgenii Stratonikov
b96fe8173c core,dao: implement Block-level storage caching
The order in which storage.Find items are returns depends on what items
were processed in previous transactions of the same block.
The easiest way to implement this sort of caching is to cache operations
with storage, flushing the only in `Persist()`.
2020-05-19 17:19:51 +03:00
Roman Khimov
03cc8c118f
Merge pull request #954 from nspcc-dev/fix/struct_fields
compiler: support using OP= with struct fields and slice elements
2020-05-19 16:03:42 +03:00
Roman Khimov
f0d6b0a639
Merge pull request #956 from nspcc-dev/doc-update-2.x
Documentation update for 2.x
2020-05-19 16:02:55 +03:00
Roman Khimov
0079dfb695 interop: add some top-level doc.go 2020-05-19 13:13:15 +03:00
Roman Khimov
8c19b8f2a1 compiler/interop: add support for working with witnesses 2020-05-19 13:13:15 +03:00
Roman Khimov
085d50b430 interop/util: extend documentation 2020-05-19 13:13:15 +03:00
Roman Khimov
ec2bf7d52e interop/transaction: update documentation 2020-05-19 13:13:15 +03:00
Roman Khimov
a587274351 compiler|transaction: remove transaction.GetUnspentCoins support
It's useless. Even though there is Neo.Transaction.GetUnspentCoins syscall
that can be used, its return type is an interop structure that's not accepted
by any other syscall, so you can't really do anything with it. And there is no
such interface for the .net Framework.
2020-05-19 13:13:15 +03:00
Roman Khimov
514f862b81 compiler|transaction: fix transaction.GetScript build, add to interop
There is no such syscall as Neo.Transaction.GetScript and GetScript should be
available for contract's use.
2020-05-19 13:13:15 +03:00
Roman Khimov
d0a3ce25ff compiler/storage: add read-only related interops 2020-05-19 13:13:15 +03:00
Roman Khimov
07742bdf46 interop/storage: update documentation 2020-05-19 13:13:15 +03:00
Roman Khimov
dff0f724cd interop/runtime: update documentation, fix Notify
Notify doesn't return anything!
2020-05-19 13:13:15 +03:00
Roman Khimov
eb82661f6b compiler/iterator: add missing iterator.Concat function
We have a syscall for it, so it should be exposed.
2020-05-19 13:13:15 +03:00
Roman Khimov
a17bd6176f interop/iterator: documentation update 2020-05-19 13:13:15 +03:00
Roman Khimov
31d7b07eb5 interop/input|output: update documentation 2020-05-19 13:13:15 +03:00
Roman Khimov
6c0553da47 interop/header: update documentation 2020-05-19 13:13:15 +03:00
Roman Khimov
d5d497ccd7 compiler: add support for enumerator interop package 2020-05-19 13:13:15 +03:00
Roman Khimov
8fb4bbca4e interop/enumerator: update doc, fix Next return value 2020-05-19 13:13:15 +03:00
Roman Khimov
5cebd4a7a2 compiler/engine: add dynamic APPCALL generation, fix #914
Previously we could generate dynamic appcall with a kludge of
    AppCall([]byte{/* 20 zeroes */, realScriptHash, args...)

Now there is a separate function for this.
2020-05-19 13:13:15 +03:00
Roman Khimov
78b2387640 interop/engine: update documentation 2020-05-19 13:13:15 +03:00
Roman Khimov
10abac4362 interop/crypto: update documentation 2020-05-19 13:13:15 +03:00
Roman Khimov
f0047b4055 interop/contract: update documentation, fix some interfaces
Some functions were just not correct in their interfaces.
2020-05-19 13:13:15 +03:00
Roman Khimov
a43f2234dd core: fix Neo.Contract.GetStorageContext security check
This syscall should only work for contracts created by current transaction and
that is what is supposed to be checked here. Do so by looking at the
differences between ic.dao and original lower DAO.
2020-05-19 13:13:15 +03:00
Roman Khimov
5d941364bd compiler/interop: expose GetTransactionHeight
And sort syscall names as they change the indentation anyway.
2020-05-19 13:13:15 +03:00
Roman Khimov
80b8b50f02 core: fix Neo.Blockchain.GetValidators implementation
It should return keys, attempting to push []*state.Validator to the stack
would probably lead to failure.
2020-05-19 13:13:15 +03:00
Roman Khimov
9e94895bb0 interop/blockchain: update documentation 2020-05-19 13:13:15 +03:00
Roman Khimov
d09c3b1e27 interop/block: update documentation, fix GetTransaction
GetTransaction never worked with hash, it works with indexes.
2020-05-19 13:13:15 +03:00
Roman Khimov
7abd35b358 compiler: add support for attribute syscalls 2020-05-19 13:13:15 +03:00
Roman Khimov
77c5f28b09 interop/attribute: update documentation 2020-05-19 13:13:14 +03:00
Roman Khimov
f69e654260 compiler: add missing asset syscalls, sort them 2020-05-19 13:13:14 +03:00
Roman Khimov
cbcc8e160f asset: update documentation and fix Create/Renew
Both Create and Renew have things returned from them.
2020-05-19 13:13:14 +03:00
Evgenii Stratonikov
231a5189a2 compiler: allow using OP= with struct fields and slice elements
Do it in a generic way, there is no need in restricting to only
variables.
2020-05-19 12:42:37 +03:00
Roman Khimov
9c46e79745 compiler: add support for account syscalls
Turns out, they never functioned correctly.
2020-05-18 19:08:28 +03:00
Roman Khimov
83df376d17 account: add missing IsStandard interop function
There is a Neo.Account.IsStandard syscall, but we didn't have a wrapper for
it.
2020-05-18 19:08:28 +03:00
Roman Khimov
6dff01672c interop/account: update and extend documentation 2020-05-18 19:08:28 +03:00
alexvanin
8db714785d rpc/client: handle client creation error in new wsclient
Client returns error if it can't parse endpoint string. WSClient
should check client error or there could be panic at `cl.cli = nil`
expression.
2020-05-18 16:25:36 +03:00
Roman Khimov
8cd7bc7e07 rpc/client: deduplicate block/header tests a bit
The same data is copied at least three times here.
2020-05-14 17:28:14 +03:00
Roman Khimov
9546e021a9 rpc/block: rework the way Block is JSONized
Our block.Block was JSONized in a bit different fashion than result.Block in
its Nonce and NextConsensus fields. It's not good for notifications because
third-party clients would probably expect to see the same format. Also, using
completely different Block representation in result is probably making our
client a bit weaker as this representation is harder to use with other neo-go
components.

So use the same approach we took for Transactions and wrap block.Base which is
to be serialized in proper way.
2020-05-14 17:28:14 +03:00
Roman Khimov
83febead59 transaction: add json.Unmarshaler to Attribute
It actually was missing and it might affect Transaction conversion to/from
JSON.
2020-05-14 17:28:14 +03:00
Roman Khimov
8f55f0ac76 rpc/server: add notification filters
And check state string correctness on unmarshaling.
2020-05-14 17:28:14 +03:00
Roman Khimov
78716c5335 rpc/client: add support for notification filters
Differing a bit from #895 draft specification, we won't add `verifier` (or
signer) for Neo 2, it's not worth doing so at the moment.
2020-05-14 00:56:26 +03:00
Roman Khimov
da32cff313 rpc/server: don't panic on test failure 2020-05-14 00:56:26 +03:00
Roman Khimov
966ff28091 rpc: add subscriber queue overflow check
It's not practical adding server-side tests for 2.0 (as it requires generating
more blocks), so we'll leave it for 3.0.
2020-05-14 00:56:26 +03:00
Roman Khimov
1d5734c882
Merge pull request #944 from nspcc-dev/notifications-2.x
Notifications 2.x
2020-05-13 17:22:55 +03:00
Roman Khimov
9454ef5c28 core: improve locking in storeBlock
Getting batch, updating Prometheus metrics and pushing events doesn't require
any locking: batch is a local cache batch that no one outside cares about,
Prometheus metrics are not critical to be in perfect sync and events are
asynchronous anyway.
2020-05-13 17:17:41 +03:00
Roman Khimov
5464f9c3ae rpc/client: add notifications support for WSClient
It differs from #895 design in that we have Notifications channel always
exposed as WSClient field, probably it simplifies things a little.
2020-05-13 17:17:41 +03:00
Roman Khimov
e1408b6525 rpc/server: add notification subscription
Note that the protocol differs a bit from #895 in its notifications format,
to avoid additional server-side processing we're omitting some metadata like:
 * block size and confirmations
 * transaction fees, confirmations, block hash and timestamp
 * application execution doesn't have ScriptHash populated

Some block fields may also differ in encoding compared to `getblock` results
(like nonce field).

I think these differences are unnoticieable for most use cases, so we can
leave them as is, but it can be changed in the future.
2020-05-13 17:17:41 +03:00
Roman Khimov
29ada4ca46 smartcontract: add JSON marshal/unmarshal for InteropType
We actually have to do that in order to answer getapplicationlog requests for
transactions that leave some interop items on the stack. It follows the same
logic our binary serializer/deserializes does leaving the type and stripping
the value (whatever that is).
2020-05-13 17:17:41 +03:00
Roman Khimov
d5df1212c2 rpc/server: start and shutdown Server in tests
It will be important for proper subscription testing and it doesn't hurt even
though technically we've got two http servers listening after this change (one
is a regular Server's http.Server and one is httptest's Server). Reusing
rpc.Server would be nice, but it requires some changes to Start sequence to
start Listener with net.Listen and then communicate back its resulting
Addr. It's not very convenient especially given that no other code needs it,
so doing these changes just for a bit cleaner testing seems like and
overkill.

Update config appropriately. Update Start comment along the way.
2020-05-12 17:42:34 +03:00
Roman Khimov
d686fe4e5d network: get blocks directly from the chain for rebroadcasting
Simplify network<->consensus relations, also broadcast blocks received by
other means like RPC.
2020-05-12 17:42:34 +03:00
Roman Khimov
dd8bcfae47 consensus: remove OnNewBlock(), use Blockchain subscription
Get new blocks directly from the Blockchain. It may lead to some duplications
(as we'll also receive our own blocks), but at the same time it's more
correct, because technically we can also get blocks via other means besides
network server like RPC (submitblock call). And it simplifies network server
at the same time.
2020-05-12 17:41:23 +03:00
Roman Khimov
1ac4f8528d core: add Blockchain event subscription mechanism
A deep internal part of #895. Blockchainer interface is also extended for
various uses of these methods.
2020-05-12 17:41:15 +03:00