Skip to content
This repository was archived by the owner on Mar 11, 2025. It is now read-only.

Commit 6725958

Browse files
samkim-cryptoCriesofCarrotsjoncinque
authored
[token-2022] Enable confidential payments only feature (#3790)
* add allow_non_confidential_credits field * add tests for disabling non-confidential transfers * Apply suggestions from code review Co-authored-by: Tyera Eulberg <[email protected]> * clarify comment wording * Update token/program-2022/src/extension/confidential_transfer/processor.rs Co-authored-by: Jon Cinque <[email protected]> Co-authored-by: Tyera Eulberg <[email protected]> Co-authored-by: Jon Cinque <[email protected]>
1 parent dabb779 commit 6725958

File tree

7 files changed

+327
-48
lines changed

7 files changed

+327
-48
lines changed

token/client/src/token.rs

Lines changed: 58 additions & 14 deletions
Original file line numberDiff line numberDiff line change
@@ -2151,36 +2151,80 @@ where
21512151
}
21522152

21532153
/// Enable confidential transfer `Deposit` and `Transfer` instructions for a token account
2154-
pub async fn confidential_transfer_enable_balance_credits<S: Signer>(
2154+
pub async fn confidential_transfer_enable_confidential_credits<S: Signer>(
21552155
&self,
21562156
token_account: &Pubkey,
21572157
authority: &S,
21582158
) -> TokenResult<T::Output> {
21592159
self.process_ixs(
2160-
&[confidential_transfer::instruction::enable_balance_credits(
2161-
&self.program_id,
2162-
token_account,
2163-
&authority.pubkey(),
2164-
&[],
2165-
)?],
2160+
&[
2161+
confidential_transfer::instruction::enable_confidential_credits(
2162+
&self.program_id,
2163+
token_account,
2164+
&authority.pubkey(),
2165+
&[],
2166+
)?,
2167+
],
21662168
&[authority],
21672169
)
21682170
.await
21692171
}
21702172

21712173
/// Disable confidential transfer `Deposit` and `Transfer` instructions for a token account
2172-
pub async fn confidential_transfer_disable_balance_credits<S: Signer>(
2174+
pub async fn confidential_transfer_disable_confidential_credits<S: Signer>(
21732175
&self,
21742176
token_account: &Pubkey,
21752177
authority: &S,
21762178
) -> TokenResult<T::Output> {
21772179
self.process_ixs(
2178-
&[confidential_transfer::instruction::disable_balance_credits(
2179-
&self.program_id,
2180-
token_account,
2181-
&authority.pubkey(),
2182-
&[],
2183-
)?],
2180+
&[
2181+
confidential_transfer::instruction::disable_confidential_credits(
2182+
&self.program_id,
2183+
token_account,
2184+
&authority.pubkey(),
2185+
&[],
2186+
)?,
2187+
],
2188+
&[authority],
2189+
)
2190+
.await
2191+
}
2192+
2193+
/// Enable a confidential extension token account to receive non-confidential payments
2194+
pub async fn confidential_transfer_enable_non_confidential_credits<S: Signer>(
2195+
&self,
2196+
token_account: &Pubkey,
2197+
authority: &S,
2198+
) -> TokenResult<T::Output> {
2199+
self.process_ixs(
2200+
&[
2201+
confidential_transfer::instruction::enable_non_confidential_credits(
2202+
&self.program_id,
2203+
token_account,
2204+
&authority.pubkey(),
2205+
&[],
2206+
)?,
2207+
],
2208+
&[authority],
2209+
)
2210+
.await
2211+
}
2212+
2213+
/// Disable non-confidential payments for a confidential extension token account
2214+
pub async fn confidential_transfer_disable_non_confidential_credits<S: Signer>(
2215+
&self,
2216+
token_account: &Pubkey,
2217+
authority: &S,
2218+
) -> TokenResult<T::Output> {
2219+
self.process_ixs(
2220+
&[
2221+
confidential_transfer::instruction::disable_non_confidential_credits(
2222+
&self.program_id,
2223+
token_account,
2224+
&authority.pubkey(),
2225+
&[],
2226+
)?,
2227+
],
21842228
&[authority],
21852229
)
21862230
.await

token/program-2022-test/tests/confidential_transfer.rs

Lines changed: 97 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -369,7 +369,7 @@ async fn ct_configure_token_account() {
369369
.get_extension::<ConfidentialTransferAccount>()
370370
.unwrap();
371371
assert!(!bool::from(&extension.approved));
372-
assert!(bool::from(&extension.allow_balance_credits));
372+
assert!(bool::from(&extension.allow_confidential_credits));
373373
assert_eq!(
374374
extension.encryption_pubkey,
375375
alice_meta.elgamal_keypair.public.into()
@@ -418,7 +418,7 @@ async fn ct_configure_token_account() {
418418
}
419419

420420
#[tokio::test]
421-
async fn ct_enable_disable_balance_credits() {
421+
async fn ct_enable_disable_confidential_credits() {
422422
let ConfidentialTransferMintWithKeypairs { ct_mint, .. } =
423423
ConfidentialTransferMintWithKeypairs::new();
424424
let mut context = TestContext::new().await;
@@ -433,7 +433,7 @@ async fn ct_enable_disable_balance_credits() {
433433
let alice_meta = ConfidentialTokenAccountMeta::new(&token, &alice).await;
434434

435435
token
436-
.confidential_transfer_disable_balance_credits(&alice_meta.token_account, &alice)
436+
.confidential_transfer_disable_confidential_credits(&alice_meta.token_account, &alice)
437437
.await
438438
.unwrap();
439439
let state = token
@@ -443,10 +443,10 @@ async fn ct_enable_disable_balance_credits() {
443443
let extension = state
444444
.get_extension::<ConfidentialTransferAccount>()
445445
.unwrap();
446-
assert!(!bool::from(&extension.allow_balance_credits));
446+
assert!(!bool::from(&extension.allow_confidential_credits));
447447

448448
token
449-
.confidential_transfer_enable_balance_credits(&alice_meta.token_account, &alice)
449+
.confidential_transfer_enable_confidential_credits(&alice_meta.token_account, &alice)
450450
.await
451451
.unwrap();
452452
let state = token
@@ -456,7 +456,98 @@ async fn ct_enable_disable_balance_credits() {
456456
let extension = state
457457
.get_extension::<ConfidentialTransferAccount>()
458458
.unwrap();
459-
assert!(bool::from(&extension.allow_balance_credits));
459+
assert!(bool::from(&extension.allow_confidential_credits));
460+
}
461+
462+
#[tokio::test]
463+
async fn ct_enable_disable_non_confidential_credits() {
464+
let ConfidentialTransferMintWithKeypairs { ct_mint, .. } =
465+
ConfidentialTransferMintWithKeypairs::new();
466+
let mut context = TestContext::new().await;
467+
context
468+
.init_token_with_mint(vec![
469+
ExtensionInitializationParams::ConfidentialTransferMint { ct_mint },
470+
])
471+
.await
472+
.unwrap();
473+
474+
let TokenContext {
475+
token,
476+
alice,
477+
bob,
478+
mint_authority,
479+
..
480+
} = context.token_context.unwrap();
481+
let alice_meta = ConfidentialTokenAccountMeta::new(&token, &alice).await;
482+
let bob_meta = ConfidentialTokenAccountMeta::new(&token, &bob).await;
483+
484+
token
485+
.mint_to(
486+
&alice_meta.token_account,
487+
&mint_authority.pubkey(),
488+
10,
489+
&[&mint_authority],
490+
)
491+
.await
492+
.unwrap();
493+
494+
token
495+
.confidential_transfer_disable_non_confidential_credits(&bob_meta.token_account, &bob)
496+
.await
497+
.unwrap();
498+
let state = token
499+
.get_account_info(&bob_meta.token_account)
500+
.await
501+
.unwrap();
502+
let extension = state
503+
.get_extension::<ConfidentialTransferAccount>()
504+
.unwrap();
505+
assert!(!bool::from(&extension.allow_non_confidential_credits));
506+
507+
let err = token
508+
.transfer(
509+
&alice_meta.token_account,
510+
&bob_meta.token_account,
511+
&alice.pubkey(),
512+
10,
513+
&[&alice],
514+
)
515+
.await
516+
.unwrap_err();
517+
518+
assert_eq!(
519+
err,
520+
TokenClientError::Client(Box::new(TransportError::TransactionError(
521+
TransactionError::InstructionError(
522+
0,
523+
InstructionError::Custom(TokenError::NonConfidentialTransfersDisabled as u32)
524+
)
525+
)))
526+
);
527+
528+
token
529+
.confidential_transfer_enable_non_confidential_credits(&bob_meta.token_account, &bob)
530+
.await
531+
.unwrap();
532+
let state = token
533+
.get_account_info(&bob_meta.token_account)
534+
.await
535+
.unwrap();
536+
let extension = state
537+
.get_extension::<ConfidentialTransferAccount>()
538+
.unwrap();
539+
assert!(bool::from(&extension.allow_non_confidential_credits));
540+
541+
token
542+
.transfer(
543+
&alice_meta.token_account,
544+
&bob_meta.token_account,
545+
&alice.pubkey(),
546+
10,
547+
&[&alice],
548+
)
549+
.await
550+
.unwrap();
460551
}
461552

462553
#[tokio::test]

token/program-2022/src/error.rs

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -190,6 +190,9 @@ pub enum TokenError {
190190
/// Extension not found in account data
191191
#[error("Extension not found in account data")]
192192
ExtensionNotFound,
193+
/// Account does not accept non-confidential transfers
194+
#[error("Non-confidential transfers disabled")]
195+
NonConfidentialTransfersDisabled,
193196
}
194197
impl From<TokenError> for ProgramError {
195198
fn from(e: TokenError) -> Self {
@@ -329,6 +332,9 @@ impl PrintProgramError for TokenError {
329332
TokenError::ExtensionNotFound => {
330333
msg!("Extension not found in account data")
331334
}
335+
TokenError::NonConfidentialTransfersDisabled => {
336+
msg!("Non-confidential transfers disabled")
337+
}
332338
}
333339
}
334340
}

0 commit comments

Comments
 (0)