Repository: dusk-network/rusk (language: rust)

Issue:
vm: Add documentation and README
#### Summary
Add extensive code documentation and a library readme.


Discussion / hints:

Fix patch:
diff --git a/vm/README.md b/vm/README.md
index ad121e6e4a..3e42a1af5b 100644
--- a/vm/README.md
+++ b/vm/README.md
@@ -2,8 +2,31 @@
 [![Repository](https://img.shields.io/badge/github-rusk--abi-blueviolet?logo=github)](https://github.com/dusk-network/dusk-vm)
 [![Documentation](https://img.shields.io/badge/docs-rusk--abi-blue?logo=rust)](https://docs.rs/dusk-vm/)
 
-## Dusk VM
+# Dusk VM
 
-The VM to execute smart contracts on the Dusk network.
+The Dusk VM is a virtual machine designed for **Dusk**, enabling secure and efficient execution of smart contracts, state transitions, and cryptographic operations tailored for zero-knowledge-based applications.
+
+It serves as the execution engine of the Dusk Blockchain, leveraging advanced cryptographic primitives and frameworks to support privacy-preserving, compliant and scalable decentralized applications.
+
+## Features
+
+- **State Management**: Manage blockchain state using sessions for isolated transaction execution and finalization.
+- **Cryptographic Support**: Offers built-in support for hashing (Poseidon), signature verification (BLS, Schnorr), and proof validation (PLONK, Groth16).
+- **Virtual Machine for zk-SNARK Applications**: Optimized for privacy-preserving computations.
+
+## Installation
+
+Add `dusk-vm` to your `Cargo.toml`:
+
+```toml
+[dependencies]
+dusk-vm = "0.x"  # Replace with the latest version
+```
+
+## Documentation
+
+For detailed usage and API examples, refer to the [crate documentation on docs.rs](https://docs.rs/dusk-vm/).
+
+## License
 
 License: MPL-2.0
diff --git a/vm/src/execute.rs b/vm/src/execute.rs
index 6d6900e06a..0ea09ee9f1 100644
--- a/vm/src/execute.rs
+++ b/vm/src/execute.rs
@@ -11,8 +11,12 @@ use dusk_core::transfer::{
 };
 use piecrust::{CallReceipt, Error, Session};
 
-/// Executes a transaction, returning the receipt of the call and the gas spent.
-/// The following steps are performed:
+/// Executes a transaction in the provided session.
+///
+/// This function processes the transaction, invoking smart contracts or
+/// updating state.
+///
+/// During the execution the following steps are performed:
 ///
 /// 1. Check if the transaction contains contract deployment data, and if so,
 ///    verifies if gas limit is enough for deployment and if the gas price is
@@ -45,6 +49,19 @@ use piecrust::{CallReceipt, Error, Session};
 /// related to deployment, as it is either discarded or it charges the
 /// full gas limit. It might be re-executed only if some other transaction
 /// failed to fit the block.
+///
+/// # Arguments
+/// * `session` - A mutable reference to the session executing the transaction.
+/// * `tx` - The transaction to execute.
+/// * `gas_per_deploy_byte` - The amount of gas points charged for each byte in
+///   a contract-deployment bytecode.
+/// * `min_deploy_points` - The minimum gas points charged for a contract
+///   deployment.
+/// * `min_deploy_gas_price` - The minimum gas price set for a contract
+///   deployment
+///
+/// # Returns
+/// A result indicating success or failure.
 pub fn execute(
     session: &mut Session,
     tx: &Transaction,
@@ -176,10 +193,15 @@ fn verify_bytecode_hash(bytecode: &ContractBytecode) -> bool {
     bytecode.hash == computed
 }
 
-/// Generate a [`ContractId`] address from:
-/// - slice of bytes,
-/// - nonce
-/// - owner
+/// Generates a unique identifier for a smart contract.
+///
+/// # Arguments
+/// * 'bytes` - The contract bytecode.
+/// * `nonce` - A unique nonce.
+/// * `owner` - The contract-owner.
+///
+/// # Returns
+/// A unique [`ContractId`].
 ///
 /// # Panics
 /// Panics if [blake2b-hasher] doesn't produce a [`CONTRACT_ID_BYTES`]
diff --git a/vm/src/host_queries.rs b/vm/src/host_queries.rs
index 424812efed..7a3a9a1e58 100644
--- a/vm/src/host_queries.rs
+++ b/vm/src/host_queries.rs
@@ -29,22 +29,66 @@ use rkyv::{Archive, Deserialize, Serialize};
 
 use crate::cache;
 
-/// Compute the blake2b hash of the given scalars, returning the resulting
-/// scalar. The hash is computed in such a way that it will always return a
-/// valid scalar.
+/// Computes a cryptographic hash of a byte vector.
+///
+/// This function uses the BLS12-381 scalar field to generate a deterministic
+/// hash from the provided byte array. The result is a [`BlsScalar`], making it
+/// suitable for cryptographic operations like zero-knowledge proofs and digital
+/// signatures.
+///
+/// # Arguments
+/// * `bytes` - A vector of bytes representing the input data to be hashed.
+///
+/// # Returns
+/// A [`BlsScalar`] representing the cryptographic hash of the input bytes.
+///
+/// # References
+/// For more details about BLS12-381 and its scalar operations, refer to:
+/// <https://github.com/dusk-network/bls12_381>.
 pub fn hash(bytes: Vec<u8>) -> BlsScalar {
     BlsScalar::hash_to_scalar(&bytes[..])
 }
 
-/// Compute the poseidon hash of the given scalars
+/// Computes the Poseidon hash of a vector of scalar values.
+///
+/// This function uses the Poseidon252 hashing algorithm to produce a
+/// cryptographic hash. Poseidon is designed for efficiency in zk-SNARK
+/// applications and operates over finite fields, making it well-suited for
+/// blockchain and cryptographic use cases.
+///
+/// # Arguments
+/// * `scalars` - A vector of [`BlsScalar`] values to be hashed. The input
+///   values represent the data to be hashed into a single scalar output.
+///
+/// # Returns
+/// A [`BlsScalar`] representing the Poseidon hash of the input values.
+///
+/// # References
+/// For more details about Poseidon and its implementation, refer to:
+/// <https://github.com/dusk-network/Poseidon252>.
 pub fn poseidon_hash(scalars: Vec<BlsScalar>) -> BlsScalar {
     PoseidonHash::digest(Domain::Other, &scalars)[0]
 }
 
-/// Verify a Plonk proof is valid for a given circuit type and public inputs
+/// Verifies a PLONK zero-knowledge proof.
+///
+/// This function verifies a proof generated by a PLONK proving system. It takes
+/// in the verifier's key data, the proof itself, and the public inputs required
+/// for verification. PLONK is a highly-efficient proof system used in
+/// zk-SNARKs.
+///
+/// # Arguments
+/// * `verifier_data` - A serialized representation of the verifier key.
+/// * `proof` - A serialized representation of the proof to be verified.
+/// * `public_inputs` - A vector of [`BlsScalar`] representing the public inputs
+///   for the proof.
 ///
-/// # Panics
-/// This will panic if `verifier_data` or `proof` are not valid.
+/// # Returns
+/// A boolean indicating whether the proof is valid (`true`) or invalid
+/// (`false`).
+///
+/// # References
+/// <https://github.com/dusk-network/plonk>.
 pub fn verify_plonk(
     verifier_data: Vec<u8>,
     proof: Vec<u8>,
@@ -57,13 +101,24 @@ pub fn verify_plonk(
     verifier.verify(&proof, &public_inputs[..]).is_ok()
 }
 
-/// Verify that a Groth16 proof in the BN254 pairing is valid for a given
-/// circuit and inputs.
+/// Verifies a Groth16 zk-SNARK proof over the BN254 curve.
+///
+/// This function verifies a proof generated using the Groth16 proving system.
+/// It takes in the prepared verifying key, the proof itself, and the public
+/// inputs.
+///
+/// # Arguments
+/// * `pvk` - A serialized representation of the prepared verifying key.
+/// * `proof` - A serialized representation of the Groth16 proof.
+/// * `inputs` - A serialized vector of public inputs for the proof.
 ///
-/// `proof` and `inputs` should be in compressed form, while `pvk` uncompressed.
+/// # Returns
+/// A boolean indicating whether the proof is valid (`true`) or invalid
+/// (`false`).
 ///
-/// # Panics
-/// This will panic if `pvk`, `proof` or `inputs` are not valid.
+/// # References
+/// For more details about Groth16 and its implementation, refer to:
+/// <https://docs.rs/ark-groth16/latest/ark_groth16/>.
 pub fn verify_groth16_bn254(
     pvk: Vec<u8>,
     proof: Vec<u8>,
@@ -80,7 +135,24 @@ pub fn verify_groth16_bn254(
         .expect("verifying proof should succeed")
 }
 
-/// Verify a schnorr signature is valid for the given public key and message
+/// Verifies a Schnorr signature.
+///
+/// This function verifies a Schnorr signature using the Jubjub elliptic curve.
+/// It takes in the message, the public key of the signer, and the signature to
+/// verify the validity of the signature.
+///
+/// # Arguments
+/// * `msg` - A [`BlsScalar`] representing the hashed message.
+/// * `pk` - A [`SchnorrPublicKey`] representing the signer's public key.
+/// * `sig` - A [`SchnorrSignature`] representing the signature to be verified.
+///
+/// # Returns
+/// A boolean indicating whether the signature is valid (`true`) or invalid
+/// (`false`).
+///
+/// # References
+/// For more details about Schnorr signatures and their implementation, refer
+/// to: <https://github.com/dusk-network/jubjub-schnorr>.
 pub fn verify_schnorr(
     msg: BlsScalar,
     pk: SchnorrPublicKey,
@@ -89,12 +161,48 @@ pub fn verify_schnorr(
     pk.verify(&sig, msg).is_ok()
 }
 
-/// Verify a BLS signature is valid for the given public key and message
+/// Verifies a BLS signature.
+///
+/// This function verifies a BLS signature using the BLS12-381 elliptic curve.
+/// It takes in the message, the signer's public key, and the signature to
+/// validate the integrity of the signed data.
+///
+/// # Arguments
+/// * `msg` - A vector of bytes representing the original message.
+/// * `pk` - A [`BlsPublicKey`] representing the signer's public key.
+/// * `sig` - A [`BlsSignature`] representing the signature to be verified.
+///
+/// # Returns
+/// A boolean indicating whether the signature is valid (`true`) or invalid
+/// (`false`).
+///
+/// # References
+/// For more details about BLS signatures and their implementation, refer to:
+/// <https://github.com/dusk-network/bls12_381-bls>.
 pub fn verify_bls(msg: Vec<u8>, pk: BlsPublicKey, sig: BlsSignature) -> bool {
     pk.verify(&sig, &msg).is_ok()
 }
 
-/// Verify a BLS signature is valid for the given public key and message
+/// Verifies a BLS multi-signature.
+///
+/// This function verifies a multi-signature created using the BLS signature
+/// scheme over the BLS12-381 elliptic curve. It validates the integrity of the
+/// message signed by multiple participants.
+///
+/// # Arguments
+/// * `msg` - A vector of bytes representing the original message.
+/// * `keys` - A vector of [`BlsPublicKey`] instances representing the
+///   participants' public keys.
+/// * `sig` - A [`MultisigSignature`] representing the combined multi-signature
+///   to be verified.
+///
+/// # Returns
+/// A boolean indicating whether the multi-signature is valid (`true`) or
+/// invalid (`false`).
+///
+/// # References
+/// For more details about BLS multi-signatures and their implementation, refer
+/// to: <https://github.com/dusk-network/bls12_381-bls>.
 pub fn verify_bls_multisig(
     msg: Vec<u8>,
     keys: Vec<BlsPublicKey>,
diff --git a/vm/src/lib.rs b/vm/src/lib.rs
index 444c1fb2bc..85594729a3 100644
--- a/vm/src/lib.rs
+++ b/vm/src/lib.rs
@@ -36,8 +36,12 @@ pub(crate) mod cache;
 mod execute;
 pub mod host_queries;
 
-/// Dusk VM is a [`PiecrustVM`] enriched with the host functions specified in
-/// Dusk's ABI.
+/// The Virtual Machine (VM) for executing smart contracts in the Dusk Network.
+///
+/// The `VM` struct serves as the core for managing the network's state,
+/// executing smart contracts, and interfacing with host functions. It supports
+/// both persistent and ephemeral sessions for handling transactions, contract
+/// queries and contract deployments.
 pub struct VM(PiecrustVM);
 
 impl From<PiecrustVM> for VM {
@@ -53,14 +57,28 @@ impl Debug for VM {
 }
 
 impl VM {
-    /// Creates a new `VM`, reading the given directory for existing commits
-    /// and bytecode.
+    /// Creates a new instance of the virtual machine.
     ///
-    /// The directory will be used to save any future session commits made by
-    /// this `VM` instance.
+    /// This method initializes the VM with a given root directory and
+    /// registers the necessary host-queries for contract execution.
+    ///
+    /// # Arguments
+    /// * `root_dir` - The path to the root directory for the VM's state
+    ///   storage. This directory will be used to save any future session
+    ///   commits made by this `VM` instance.
+    ///
+    /// # Returns
+    /// A new `VM` instance.
     ///
     /// # Errors
     /// If the directory contains unparseable or inconsistent data.
+    ///
+    /// # Examples
+    /// ```rust
+    /// use dusk_vm::VM;
+    ///
+    /// let vm = VM::new("/path/to/root_dir");
+    /// ```
     pub fn new(
         root_dir: impl AsRef<Path> + Into<PathBuf>,
     ) -> Result<Self, Error> {
@@ -69,26 +87,69 @@ impl VM {
         Ok(vm)
     }
 
-    /// Creates a new `VM` using a new temporary directory.
+    /// Creates an ephemeral VM instance.
     ///
-    /// Any session commits made by this machine should be considered discarded
-    /// once this `VM` instance drops.
+    /// This method initializes a VM that operates in memory without persisting
+    /// state. It is useful for testing or temporary computations.
+    ///
+    /// # Returns
+    /// A new ephemeral `VM` instance.
     ///
     /// # Errors
     /// If creating a temporary directory fails.
+    ///
+    /// # Examples
+    /// ```rust
+    /// use dusk_vm::VM;
+    ///
+    /// let vm = VM::ephemeral();
+    /// ```
     pub fn ephemeral() -> Result<VM, Error> {
         let mut vm: Self = PiecrustVM::ephemeral()?.into();
         vm.register_host_queries();
         Ok(vm)
     }
 
-    /// Spawn a [`Session`] on top of the given `commit`, given the `chain_id`
-    /// and `block_height`.
+    /// Creates a new session for transaction execution.
+    ///
+    /// This method initializes a session with a specific base state commit,
+    /// chain identifier, and block height. Sessions allow for isolated
+    /// transaction execution without directly affecting the persistent VM
+    /// state until finalized.
+    ///
+    /// # Arguments
+    /// * `base` - A 32-byte array representing the base state from which the
+    ///   session begins.
+    /// * `chain_id` - The identifier of the network.
+    /// * `block_height` - The current block height at which the session is
+    ///   created.
+    ///
+    /// # Returns
+    /// A `Result` containing a `Session` instance for executing transactions,
+    /// or an error if the session cannot be initialized.
     ///
     /// # Errors
     /// If base commit is provided but does not exist.
     ///
-    /// [`Session`]: Session
+    /// # Examples
+    /// ```rust
+    /// use dusk_vm::VM;
+    ///
+    /// const CHAIN_ID: u8 = 42;
+    ///
+    /// // create a genesis session
+    /// let vm = VM::ephemeral().unwrap();
+    /// let session = vm.genesis_session(CHAIN_ID);
+    ///
+    /// // [...] apply changes to the network through the running session
+    ///
+    /// // commit the changes
+    /// let base = session.commit().unwrap();
+    ///
+    /// // spawn a new session on top of the base-commit
+    /// let block_height = 21;
+    /// let session = vm.session(base, CHAIN_ID, block_height).unwrap();
+    /// ```
     pub fn session(
         &self,
         base: [u8; 32],
@@ -103,8 +164,28 @@ impl VM {
         )
     }
 
-    /// Spawn a new genesis-[`Session`] given the `chain_id` with a
-    /// `block_height` of 0.
+    /// Initializes a session for setting up the genesis block.
+    ///
+    /// This method creates a session specifically for defining the genesis
+    /// block, which serves as the starting state of the network. The
+    /// genesis session uses the specified chain ID.
+    ///
+    /// # Arguments
+    /// * `chain_id` - The identifier of the blockchain chain for which the
+    ///   genesis state is initialized.
+    ///
+    /// # Returns
+    /// A `Session` instance for defining the genesis block.
+    ///
+    /// # Examples
+    /// ```rust
+    /// use dusk_vm::VM;
+    ///
+    /// const CHAIN_ID: u8 = 42;
+    ///
+    /// let vm = VM::ephemeral().unwrap();
+    /// let genesis_session = vm.genesis_session(CHAIN_ID);
+    /// ```
     pub fn genesis_session(&self, chain_id: u8) -> Session {
         self.0
             .session(
@@ -119,28 +200,37 @@ impl VM {
             .expect("Creating a genesis session should always succeed")
     }
 
-    /// Return all existing commits.
+    /// Retrieves all pending commits in the VM.
+    ///
+    /// This method fetches unfinalized state changes for inspection or
+    /// processing.
+    ///
+    /// # Returns
+    /// A vector of commits.
     pub fn commits(&self) -> Vec<[u8; 32]> {
         self.0.commits()
     }
 
-    /// Deletes the given commit from disk.
+    /// Deletes a specified commit from the VM.
+    ///
+    /// # Arguments
+    /// * `commit` - The commit to be deleted.
     pub fn delete_commit(&self, root: [u8; 32]) -> Result<(), Error> {
         self.0.delete_commit(root)
     }
 
-    /// Finalizes the given commit on disk.
+    /// Finalizes a specified commit, applying its state changes permanently.
+    ///
+    /// # Arguments
+    /// * `commit` - The commit to be finalized.
     pub fn finalize_commit(&self, root: [u8; 32]) -> Result<(), Error> {
         self.0.finalize_commit(root)
     }
 
-    /// Return the root directory of the virtual machine.
+    /// Returns the root directory of the VM.
     ///
     /// This is either the directory passed in by using [`new`], or the
     /// temporary directory created using [`ephemeral`].
-    ///
-    /// [`new`]: VM::new
-    /// [`ephemeral`]: VM::ephemeral
     pub fn root_dir(&self) -> &Path {
         self.0.root_dir()
     }


Test patch: