HashID


HashID is the primary globally unique identifier of every smart contract in the Universa system.

TLDR; HashID is a 128 symbols long string, may contain any latin letters (uppercase or lowercase, case-sensitive), digits, or letters “+” or “/”.

TLDR for cryptographers; effectively 768 bits of security; implemented as a concatenation of SHA-512/256, SHA3-256 and Streebog, encoded in Base64.

Whenever every document is created, and then “sealed” (into its invariant binary form – so its binary representation will not change anymore ever), a cryptographically strong hash function value is taken from its binary form.

“Cryptographically strong hash function” means, that even if a single byte of the smart contract document is altered, the whole value of the hash function will be significantly different; and, due to the properties of this cryptographic hash, its is extremely hard or practically impossible to find another document (with the different contents). Therefore, if you have a value of such a cryptographic hash function from your document, it is sufficient to be sure your document has not been tampered with. Such a cryptographic hash function value from every smart contract document (or its new revision) is the HashID.

Algorithm

Hash functions in other blockchains

Many different blockchain systems use various cryptographic hash functions to ensure the data integrity. Some examples:

  • Bitcoin uses SHA-256 (rather old variant of SHA-2 algorithm family);
  • Ethereum uses Keccak (a pre-standard variant of SHA-3 which has been slightly changed for the standard publication, and as a result is not binary compatible with SHA-3).
  • Hyperledger Fabric initially used SHAKE-256 (a variant of SHA-3) but then “downgraded” the algorithm to SHA-256, for the sake of its wider acceptance (as of February 2019, the Hyperledger protocol supports specifying the exact hashing algorithm to be used, but only SHA-256 is supported and available in the system, and using SHA-256 is hardcoded in various parts of the system).

Even though the SHA-2 and SHA-3 algorithm families are still considered sufficiently cryptographically strong, the various attacks on these algorithms are being investigated by the scientists. In case if any weakness is found in them, the system using the “weak” algorithm may be exploited; and, as the hash function is usually the key component of any blockchain system, it will unlikely be possible to switch this algorithm on-the-fly for the blockchain.

Universa hashing approach

Universa uses not a single one, but three different cryptographic hash functions, altogether. Each of these functions belong to different algorithm families, making it virtually impossible to find a weakness that could be used to weaken all of them. Even if a weakness is found in one algorithm, it won’t be useful against the other systems, and won’t help to break their combination.

The hash functions being used are:

  • SHA-512/256 (256 bits), the variant of SHA-2 algorithm family which is considered strongest to the length extension attack (in particular, being stronger than more commonly used SHA-256). Originally created inside National Security Agency, USA. Standardized as:
    • FIPS PUB 180-2, FIPS PUB 180-3, FIPS PUB 180-4 – USA Federal Government standard since August 2002;
    • CRYPTREC – Japanese government standard;
    • NESSIE – European Union standard.
  • SHA3-256 (256 bits), the variant of SHA-3. Originally created by a team of European cryptographists and submitted to the NIST hash function competition (announced in 2007). Standardized as:
    • FIPS PUB 202 – the newest USA Federal Government standard since August 2015.
  • Streebog (256 bits), the cryptographic hash function developed in Russia, within FSB (Federal Security Service of Russian Federation) and InfoTeCS JSC. Standardized as:
    • GOST R 34.11-2012 – the latest Russian Federation standard since August 2012.

Utilizing three different hash functions altogether, developed by three significantly different cryptographer teams and utilizing rather different cryptographic concepts and primitives, makes it especially hard

For the purpose of using in Universa, the results of these three functions from the source data are calculated, and concatenated altogether. Each function creates a 256 bits (32 bytes) long value of hash function; three functions altogether make it 3⋅256 = 768 bits (96 bytes) long.

Textual representation

Internally the HashID is stored as 768 bits string; but for textual representation, it is encoded in Base64. Therefore, it may contains symbols from the following range:

  • AZ;
  • az;
  • 09;
  • +;
  • /.

The property of Base64 encoding is that each 3 bytes of any binary data are encoded as 4 symbols of Base64 representation; therefore, each HashID is usually displayed as 96⋅4/3 = 128 symbols.

128 symbols is rather long to be displayed in a single line, though luckily it may be easily split into 2 64-symbols lines, or into 4 32-symbols lines.

General algorithm diagram

graph TD data(Smart Contract revision) subgraph Concatenation sha2(SHA-512/256) sha3(SHA3-256) streebog(GOST R 34.11-2012 Streebog) combined("SHA-512/256 | SHA3-256 | Streebog") end base64("Base64(SHA-512/256 | SHA3-256 | Streebog)") data-->sha2 data-->sha3 data-->streebog sha2-->combined sha3-->combined streebog-->combined combined-->base64

Usage in Universa

Each revision (even the initial one) of the smart contract is identified by its own unique HashID. The distributed Universa ledger stores just the HashIDs of the currently approved revisions (of the smart contracts), and normally not storing the smart contract themselves.

Each new revision of any smart contract internally contains the link (mention) of the parent revision, making a chain of revisions in a typical blockchain manner (because any new “block” or revision of the smart contract can be approved only if the “parent-linked” revision is approved at that moment).

Example

Check out the smart contract with the following HashID:

NPo4dIkNdgYfGiNrdExoX003+lFT/d45OA6GifmcRoTzxSRSm5c5jDHBSTaAS+QleuN7ttX1rTvSQbHIIqkcK/zWjx/fCpP9ziwsgXbyyCtUhLqP9G4YZ+zEY/yL/GVE

The same HashID represented in more convenient form below:

NPo4dIkNdgYfGiNrdExoX003+lFT/d45
OA6GifmcRoTzxSRSm5c5jDHBSTaAS+Ql
euN7ttX1rTvSQbHIIqkcK/zWjx/fCpP9
ziwsgXbyyCtUhLqP9G4YZ+zEY/yL/GVE

This is the HashID of the original revision of the smart contract for UTN token.

Note: the status of smart contract is UNDEFINED, as this original revision has been modified by even the first “usage” of the UTN token, when it has been split and a part of it has been given out to somebody. See more details in the UTN article, FAQ section.

Note: normally the smart contracts are not stored in the network; but the UTN contract, being so important for Universa functioning, is intentionally kept public.

See more

Find more details in the source code implementation at Github: https://github.com/UniversaBlockchain/universa/blob/master/universa_core/src/main/java/com/icodici/universa/HashId.java