Search in sources :

Example 21 with RLPList

use of org.aion.rlp.RLPList in project aion by aionnetwork.

the class AionContractDetailsImpl method decode.

@Override
public void decode(byte[] rlpCode) {
    RLPList data = RLP.decode2(rlpCode);
    RLPList rlpList = (RLPList) data.get(0);
    RLPItem address = (RLPItem) rlpList.get(0);
    RLPItem isExternalStorage = (RLPItem) rlpList.get(1);
    RLPItem storage = (RLPItem) rlpList.get(2);
    RLPElement code = rlpList.get(3);
    RLPList keys = (RLPList) rlpList.get(4);
    RLPItem storageRoot = (RLPItem) rlpList.get(5);
    if (address.getRLPData() == null) {
        this.address = Address.EMPTY_ADDRESS();
    } else {
        this.address = Address.wrap(address.getRLPData());
    }
    this.externalStorage = !Arrays.equals(isExternalStorage.getRLPData(), EMPTY_BYTE_ARRAY);
    this.storageTrie.deserialize(storage.getRLPData());
    if (code instanceof RLPList) {
        for (RLPElement e : ((RLPList) code)) {
            setCode(e.getRLPData());
        }
    } else {
        setCode(code.getRLPData());
    }
    for (RLPElement key : keys) {
        addKey(key.getRLPData());
    }
    if (externalStorage) {
        storageTrie.withPruningEnabled(prune >= 0);
        storageTrie.setRoot(storageRoot.getRLPData());
        storageTrie.getCache().setDB(getExternalStorageDataSource());
    }
    externalStorage = (storage.getRLPData().length > detailsInMemoryStorageLimit) || externalStorage;
    this.rlpEncoded = rlpCode;
}
Also used : RLPItem(org.aion.rlp.RLPItem) RLPElement(org.aion.rlp.RLPElement) RLPList(org.aion.rlp.RLPList)

Example 22 with RLPList

use of org.aion.rlp.RLPList in project aion by aionnetwork.

the class RequestBlocks method decode.

/**
 * Decodes a message into a block range request.
 *
 * @param message a {@code byte} array representing a request for a trie node.
 * @return the decoded trie node request if valid or {@code null} when the decoding encounters
 *     invalid input
 * @implNote Ensures that the components are not {@code null}.
 */
public static RequestBlocks decode(final byte[] message) {
    if (message == null || message.length == 0) {
        return null;
    } else {
        RLPList list = RLP.decode2(message);
        if (list.get(0) instanceof RLPList) {
            list = (RLPList) list.get(0);
        } else {
            return null;
        }
        if (list.size() != 4) {
            return null;
        } else {
            // decode the requested type (number or hash)
            byte value = new BigInteger(1, list.get(0).getRLPData()).byteValue();
            if (value < 0 || value > 1) {
                return null;
            }
            boolean isNumber = value == 1;
            // decode the number of blocks requested
            int count = new BigInteger(1, list.get(2).getRLPData()).intValue();
            if (count <= 0) {
                return null;
            }
            // decode the requested ordering of the block range
            value = new BigInteger(1, list.get(3).getRLPData()).byteValue();
            if (value < 0 || value > 1) {
                return null;
            }
            boolean descending = value == 1;
            if (isNumber) {
                // decode the start block
                long start = new BigInteger(1, list.get(1).getRLPData()).longValue();
                if (start <= 0) {
                    return null;
                }
                // number based request
                return new RequestBlocks(start, count, descending);
            } else {
                byte[] start = list.get(1).getRLPData();
                if (start.length != HASH_SIZE) {
                    return null;
                }
                // hash based request
                return new RequestBlocks(start, count, descending);
            }
        }
    }
}
Also used : BigInteger(java.math.BigInteger) RLPList(org.aion.rlp.RLPList)

Example 23 with RLPList

use of org.aion.rlp.RLPList in project aion by aionnetwork.

the class ResponseTrieData method decode.

/**
 * Decodes a message into a trie node response.
 *
 * @param message a {@code byte} array representing a response to a trie node request.
 * @return the decoded trie node response
 * @implNote The decoder must return {@code null} if any of the component values are {@code
 *     null} or invalid.
 */
public static ResponseTrieData decode(final byte[] message) {
    if (message == null || message.length == 0) {
        return null;
    } else {
        RLPList list = RLP.decode2(message);
        if (list.get(0) instanceof RLPList) {
            list = (RLPList) list.get(0);
        } else {
            return null;
        }
        if (list.size() != TRIE_DATA_RESPONSE_COMPONENTS) {
            return null;
        } else {
            // decode the key
            byte[] hash = list.get(0).getRLPData();
            if (hash.length != HASH_SIZE) {
                return null;
            }
            // decode the value
            byte[] value = list.get(1).getRLPData();
            if (value.length == 0) {
                return null;
            }
            // decode the referenced nodes
            RLPElement referenced = list.get(2);
            if (!(referenced instanceof RLPList)) {
                return null;
            }
            Map<ByteArrayWrapper, byte[]> nodes = decodeReferencedNodes((RLPList) referenced);
            if (nodes == null) {
                return null;
            }
            // decode the db type
            byte[] type = list.get(3).getRLPData();
            DatabaseType dbType;
            try {
                dbType = DatabaseType.valueOf(new String(type));
            } catch (IllegalArgumentException e) {
                return null;
            }
            return new ResponseTrieData(ByteArrayWrapper.wrap(hash), value, nodes, dbType);
        }
    }
}
Also used : ByteArrayWrapper(org.aion.util.types.ByteArrayWrapper) DatabaseType(org.aion.zero.impl.sync.DatabaseType) RLPElement(org.aion.rlp.RLPElement) RLPList(org.aion.rlp.RLPList)

Example 24 with RLPList

use of org.aion.rlp.RLPList in project aion by aionnetwork.

the class ResponseTrieData method decodeReferencedNodes.

/**
 * Decodes the list of key-value pair encodings into a map representation.
 *
 * @return a map of all the key-value pair encodings
 */
private static Map<ByteArrayWrapper, byte[]> decodeReferencedNodes(RLPList referenced) {
    if (referenced.isEmpty()) {
        return Collections.emptyMap();
    }
    RLPList current;
    byte[] hash, value;
    Map<ByteArrayWrapper, byte[]> nodes = new HashMap<>();
    for (RLPElement pair : referenced) {
        if (!(pair instanceof RLPList)) {
            return null;
        }
        current = (RLPList) pair;
        // decode the key
        hash = current.get(0).getRLPData();
        if (hash.length != HASH_SIZE) {
            return null;
        }
        // decode the value
        value = current.get(1).getRLPData();
        if (value.length == 0) {
            return null;
        }
        nodes.put(ByteArrayWrapper.wrap(hash), value);
    }
    return nodes;
}
Also used : ByteArrayWrapper(org.aion.util.types.ByteArrayWrapper) HashMap(java.util.HashMap) RLPElement(org.aion.rlp.RLPElement) RLPList(org.aion.rlp.RLPList)

Example 25 with RLPList

use of org.aion.rlp.RLPList in project aion by aionnetwork.

the class RequestTrieData method decode.

/**
 * Decodes a message into a trie node request.
 *
 * @param message a {@code byte} array representing a request for a trie node.
 * @return the decoded trie node request if valid or {@code null} when the decoding encounters
 *     invalid input
 * @implNote Ensures that the components are not {@code null}.
 */
public static RequestTrieData decode(final byte[] message) {
    if (message == null || message.length == 0) {
        return null;
    } else {
        RLPList list = RLP.decode2(message);
        if (list.get(0) instanceof RLPList) {
            list = (RLPList) list.get(0);
        } else {
            return null;
        }
        if (list.size() != TRIE_DATA_REQUEST_COMPONENTS) {
            return null;
        } else {
            // decode the key
            byte[] hash = list.get(0).getRLPData();
            if (hash.length != HASH_SIZE) {
                return null;
            }
            // decode the db type
            byte[] type = list.get(1).getRLPData();
            DatabaseType dbType;
            try {
                dbType = DatabaseType.valueOf(new String(type));
            } catch (IllegalArgumentException e) {
                return null;
            }
            // decode the limit
            int depth = new BigInteger(1, list.get(2).getRLPData()).intValue();
            return new RequestTrieData(hash, dbType, depth);
        }
    }
}
Also used : DatabaseType(org.aion.zero.impl.sync.DatabaseType) BigInteger(java.math.BigInteger) RLPList(org.aion.rlp.RLPList)

Aggregations

RLPList (org.aion.rlp.RLPList)30 RLPElement (org.aion.rlp.RLPElement)18 RLPItem (org.aion.rlp.RLPItem)7 SharedRLPList (org.aion.rlp.SharedRLPList)7 SharedRLPItem (org.aion.rlp.SharedRLPItem)5 AionAddress (org.aion.types.AionAddress)5 RLPContractDetails (org.aion.zero.impl.db.DetailsDataStore.RLPContractDetails)5 Test (org.junit.Test)5 BigInteger (java.math.BigInteger)4 ArrayList (java.util.ArrayList)3 A0BlockHeader (org.aion.zero.types.A0BlockHeader)3 HashMap (java.util.HashMap)2 DataWord (org.aion.mcf.vm.types.DataWord)2 ByteArrayWrapper (org.aion.util.types.ByteArrayWrapper)2 DatabaseType (org.aion.zero.impl.sync.DatabaseType)2 SecureTrie (org.aion.zero.impl.trie.SecureTrie)2 ByteUtil.toHexString (org.aion.base.util.ByteUtil.toHexString)1 ISignature (org.aion.crypto.ISignature)1 TxTouchedStorage (org.aion.mcf.core.TxTouchedStorage)1 Value (org.aion.rlp.Value)1