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

Add QuorumSignInfo and merge CertifiedTransaction with other Transaction types #1686

Merged
merged 4 commits into from
May 1, 2022
Merged
Show file tree
Hide file tree
Changes from 3 commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
82 changes: 37 additions & 45 deletions sui/open_rpc/spec/openrpc.json
Original file line number Diff line number Diff line change
Expand Up @@ -581,7 +581,7 @@
"description": "",
"required": true,
"schema": {
"$ref": "#/components/schemas/CertifiedTransaction"
"$ref": "#/components/schemas/TransactionEnvelope_for_QuorumSignInfo"
}
}
},
Expand Down Expand Up @@ -685,41 +685,6 @@
}
]
},
"CertifiedTransaction": {
"description": "An transaction signed by a quorum of authorities\n\nNote: the signature set of this data structure is not necessarily unique in the system, i.e. there can be several valid certificates per transaction.\n\nAs a consequence, we check this struct does not implement Hash or Eq, see the note below.",
"type": "object",
"required": [
"epoch",
"signatures",
"transaction"
],
"properties": {
"epoch": {
"type": "integer",
"format": "uint64",
"minimum": 0.0
},
"signatures": {
"type": "array",
"items": {
"type": "array",
"items": [
{
"$ref": "#/components/schemas/PublicKeyBytes"
},
{
"$ref": "#/components/schemas/AuthoritySignature"
}
],
"maxItems": 2,
"minItems": 2
}
},
"transaction": {
"$ref": "#/components/schemas/TransactionEnvelope_for_EmptySignInfo"
}
}
},
"Data": {
"oneOf": [
{
Expand Down Expand Up @@ -750,9 +715,6 @@
}
]
},
"EmptySignInfo": {
"type": "object"
},
"Event": {
"description": "User-defined event emitted by executing Move code. Executing a transaction produces an ordered log of these",
"type": "object",
Expand Down Expand Up @@ -918,7 +880,7 @@
"description": "Certificate of the transaction",
"allOf": [
{
"$ref": "#/components/schemas/CertifiedTransaction"
"$ref": "#/components/schemas/TransactionEnvelope_for_QuorumSignInfo"
}
]
},
Expand Down Expand Up @@ -1425,7 +1387,7 @@
"description": "Certificate of the transaction",
"allOf": [
{
"$ref": "#/components/schemas/CertifiedTransaction"
"$ref": "#/components/schemas/TransactionEnvelope_for_QuorumSignInfo"
}
]
},
Expand Down Expand Up @@ -1463,6 +1425,36 @@
}
}
},
"QuorumSignInfo": {
"type": "object",
"required": [
"epoch",
"signatures"
],
"properties": {
"epoch": {
"type": "integer",
"format": "uint64",
"minimum": 0.0
},
"signatures": {
"type": "array",
"items": {
"type": "array",
"items": [
{
"$ref": "#/components/schemas/PublicKeyBytes"
},
{
"$ref": "#/components/schemas/AuthoritySignature"
}
],
"maxItems": 2,
"minItems": 2
}
}
}
},
"RpcCallArg": {
"oneOf": [
{
Expand Down Expand Up @@ -1586,7 +1578,7 @@
"description": "Certificate of the transaction",
"allOf": [
{
"$ref": "#/components/schemas/CertifiedTransaction"
"$ref": "#/components/schemas/TransactionEnvelope_for_QuorumSignInfo"
}
]
},
Expand Down Expand Up @@ -1910,7 +1902,7 @@
}
}
},
"TransactionEnvelope_for_EmptySignInfo": {
"TransactionEnvelope_for_QuorumSignInfo": {
"description": "A transaction signed by a client, optionally signed by an authority (depending on `S`). `S` indicates the authority signing state. It can be either empty or signed. We make the authority signature templated so that `TransactionEnvelope<S>` can be used universally in the transactions storage in `SuiDataStore`, shared by both authorities and non-authorities: authorities store signed transactions, while non-authorities store unsigned transactions.",
"type": "object",
"required": [
Expand All @@ -1923,7 +1915,7 @@
"description": "authority signature information, if available, is signed by an authority, applied on `data`.",
"allOf": [
{
"$ref": "#/components/schemas/EmptySignInfo"
"$ref": "#/components/schemas/QuorumSignInfo"
}
]
},
Expand Down Expand Up @@ -1985,7 +1977,7 @@
"type": "array",
"items": [
{
"$ref": "#/components/schemas/CertifiedTransaction"
"$ref": "#/components/schemas/TransactionEnvelope_for_QuorumSignInfo"
},
{
"$ref": "#/components/schemas/TransactionEffects"
Expand Down
6 changes: 3 additions & 3 deletions sui/src/benchmark/transaction_creator.rs
Original file line number Diff line number Diff line change
Expand Up @@ -68,11 +68,11 @@ fn make_serialized_cert(
) -> Vec<u8> {
// Make certificate
let mut certificate = CertifiedTransaction::new(tx);
certificate.epoch = committee.epoch();
certificate.auth_sign_info.epoch = committee.epoch();
for i in 0..committee.quorum_threshold() {
let (pubx, secx) = keys.get(i).unwrap();
let sig = AuthoritySignature::new(&certificate.transaction.data, secx);
certificate.signatures.push((*pubx, sig));
let sig = AuthoritySignature::new(&certificate.data, secx);
certificate.auth_sign_info.signatures.push((*pubx, sig));
}

let serialized_certificate = serialize_cert(&certificate);
Expand Down
37 changes: 16 additions & 21 deletions sui_core/src/authority.rs
Original file line number Diff line number Diff line change
Expand Up @@ -140,7 +140,7 @@ impl AuthorityState {
#[instrument(level = "trace", skip_all)]
async fn check_locks(
&self,
transaction: &Transaction,
transaction: &TransactionData,
gas_object: Object,
gas_status: &mut SuiGasStatus<'_>,
) -> Result<Vec<(InputObjectKind, Object)>, SuiError> {
Expand Down Expand Up @@ -183,8 +183,8 @@ impl AuthorityState {
async fn handle_transaction_impl(
&self,
transaction: Transaction,
transaction_digest: TransactionDigest,
) -> Result<TransactionInfoResponse, SuiError> {
let transaction_digest = *transaction.digest();
// Ensure an idempotent answer.
if self._database.transaction_exists(&transaction_digest)? {
let transaction_info = self.make_transaction_info(&transaction_digest).await?;
Expand All @@ -199,7 +199,7 @@ impl AuthorityState {
.await?;

let all_objects: Vec<_> = self
.check_locks(&transaction, gas_object, &mut gas_status)
.check_locks(&transaction.data, gas_object, &mut gas_status)
.await?;
if transaction.contains_shared_object() {
// It's important that we do this here to make sure there is enough
Expand All @@ -215,7 +215,7 @@ impl AuthorityState {
// The call to self.set_transaction_lock checks the lock is not conflicting,
// and returns ConflictingTransaction error in case there is a lock on a different
// existing transaction.
self.set_transaction_lock(&owned_objects, transaction_digest, signed_transaction)
self.set_transaction_lock(&owned_objects, signed_transaction)
.await?;

// Return the signed Transaction or maybe a cert.
Expand All @@ -229,11 +229,9 @@ impl AuthorityState {
) -> Result<TransactionInfoResponse, SuiError> {
// Check the sender's signature.
transaction.check_signature()?;
let transaction_digest = transaction.digest();
let transaction_digest = *transaction.digest();

let response = self
.handle_transaction_impl(transaction, transaction_digest)
.await;
let response = self.handle_transaction_impl(transaction).await;
match response {
Ok(r) => Ok(r),
// If we see an error, it is possible that a certificate has already been processed.
Expand Down Expand Up @@ -328,17 +326,16 @@ impl AuthorityState {
) -> Result<TransactionInfoResponse, SuiError> {
let certificate = confirmation_transaction.certificate;
let transaction_digest = *certificate.digest();
let transaction = &certificate.transaction;

let (gas_object, mut gas_status) = self
.check_gas(
transaction.gas_payment_object_ref().0,
transaction.data.gas_budget,
certificate.gas_payment_object_ref().0,
certificate.data.gas_budget,
)
.await?;

let objects_by_kind = self
.check_locks(transaction, gas_object, &mut gas_status)
.check_locks(&certificate.data, gas_object, &mut gas_status)
.await?;

// At this point we need to check if any shared objects need locks,
Expand Down Expand Up @@ -374,7 +371,7 @@ impl AuthorityState {
let effects = execution_engine::execute_transaction_to_effects(
shared_object_refs,
&mut temporary_store,
transaction.clone(),
certificate.data.clone(),
transaction_digest,
transaction_dependencies,
&self.move_vm,
Expand Down Expand Up @@ -404,20 +401,19 @@ impl AuthorityState {
last_consensus_index: ExecutionIndices,
) -> SuiResult<()> {
// Ensure it is a shared object certificate
if !certificate.transaction.contains_shared_object() {
if !certificate.contains_shared_object() {
log::debug!(
"Transaction without shared object has been sequenced: {:?}",
certificate.transaction
certificate
);
return Ok(());
}

// Ensure it is the first time we see this certificate.
let transaction_digest = *certificate.digest();
if self._database.sequenced(
&transaction_digest,
certificate.transaction.shared_input_objects(),
)?[0]
if self
._database
.sequenced(&transaction_digest, certificate.shared_input_objects())?[0]
.is_some()
{
return Ok(());
Expand Down Expand Up @@ -744,11 +740,10 @@ impl AuthorityState {
pub async fn set_transaction_lock(
&self,
mutable_input_objects: &[ObjectRef],
tx_digest: TransactionDigest,
signed_transaction: SignedTransaction,
) -> Result<(), SuiError> {
self._database
.set_transaction_lock(mutable_input_objects, tx_digest, signed_transaction)
.set_transaction_lock(mutable_input_objects, signed_transaction)
}

/// Update state and signals that a new transactions has been processed
Expand Down
15 changes: 6 additions & 9 deletions sui_core/src/authority/authority_store.rs
Original file line number Diff line number Diff line change
Expand Up @@ -459,9 +459,9 @@ impl<const ALL_OBJ_VER: bool, S: Eq + Serialize + for<'de> Deserialize<'de>>
pub fn set_transaction_lock(
&self,
owned_input_objects: &[ObjectRef],
tx_digest: TransactionDigest,
transaction: TransactionEnvelope<S>,
) -> Result<(), SuiError> {
let tx_digest = *transaction.digest();
let lock_batch = self
.transaction_lock
.batch()
Expand Down Expand Up @@ -544,11 +544,8 @@ impl<const ALL_OBJ_VER: bool, S: Eq + Serialize + for<'de> Deserialize<'de>>
)?;

// Cleanup the lock of the shared objects.
let write_batch = self.remove_shared_objects_locks(
write_batch,
transaction_digest,
&certificate.transaction,
)?;
let write_batch =
self.remove_shared_objects_locks(write_batch, transaction_digest, certificate)?;

// Safe to unwrap since the "true" flag ensures we get a sequence value back.
self.batch_update_objects(
Expand Down Expand Up @@ -800,7 +797,7 @@ impl<const ALL_OBJ_VER: bool, S: Eq + Serialize + for<'de> Deserialize<'de>>
&self,
mut write_batch: DBBatch,
transaction_digest: &TransactionDigest,
transaction: &Transaction,
transaction: &CertifiedTransaction,
) -> SuiResult<DBBatch> {
let mut sequenced_to_delete = Vec::new();
let mut schedule_to_delete = Vec::new();
Expand All @@ -827,10 +824,10 @@ impl<const ALL_OBJ_VER: bool, S: Eq + Serialize + for<'de> Deserialize<'de>>
let certificate_to_write = std::iter::once((transaction_digest, &certificate));

// Make an iterator to update the locks of the transaction's shared objects.
let ids = certificate.transaction.shared_input_objects();
let ids = certificate.shared_input_objects();
let versions = self.schedule.multi_get(ids)?;

let ids = certificate.transaction.shared_input_objects();
let ids = certificate.shared_input_objects();
let (sequenced_to_write, schedule_to_write): (Vec<_>, Vec<_>) = ids
.zip(versions.iter())
.map(|(id, v)| {
Expand Down
Loading