1

I run into a account on the browser.

https://solscan.io/account/41BJ8cmr4vaebFbHzxerb8YG6MmTFWLj15M6h65mUyiF

https://explorer.solana.com/address/41BJ8cmr4vaebFbHzxerb8YG6MmTFWLj15M6h65mUyiF

From browser we can see that it is off curve account. But browser show that it is “Assigned Program Id" to System Program.

How can one create account like this? An account assigned to System Program but off curve. How can the guy own this account spend tokens under it?

1
  • I think what you are seeing is PDA accounts. They are derived accounts with any private key and are off curve. Program which creates the account can act as signer with seeds used to create the account to perform transactions on behalf of the off curve accounts. These are owned by a program and not by a wallet. For more details check here Commented Dec 12 at 6:48

1 Answer 1

0

Yes, The account you’re looking at is an off-curve Program Derived Address (PDA). PDAs are special accounts that don't have private keys and are instead generated programmatically using findProgramAddress function with combination of seeds and public key(usually a program ID or even a wallet's public key). This makes them off-curve and impossible to control via a private key.

PDAs are "owned" by the program that created them. Even though it is assigned to the System Program, the actual control comes from the program that derived the PDA.

This is simple script how to create such accounts and control assets.

  const seed = "my-seed";
  const [pda, bump] = PublicKey.findProgramAddressSync(
    [Buffer.from(seed)],
    admin.publicKey
  );

  const pdaAta = getAssociatedTokenAddressSync(tokenMint, pda, true);

  const ixs = [
    createAssociatedTokenAccountInstruction(
      admin.publicKey,
      pdaAta,
      pda,
      tokenMint
    ),
    createMintToInstruction(tokenMint, pdaAta, admin.publicKey, 1e9),
  ];

  const block = await connection.getLatestBlockhash();
  const tx = new VersionedTransaction(
    new TransactionMessage({
      payerKey: admin.publicKey,
      recentBlockhash: block.blockhash,
      instructions: ixs,
    }).compileToV0Message()
  );
  tx.sign([admin]);
  await connection.sendTransaction(tx).then(confirm).then(log);

  console.log("pda: ", pda.toBase58());
  console.log("pda ata: ", pdaAta.toBase58());

These are the addresses of the PDA and its associated token accounts (ATA) that were just created on the Devnet.

https://solscan.io/account/C6itz1Drxui8eSjmVCyKRMY87yo7EmS7MDDWxNJDjd8A?cluster=devnet https://solscan.io/account/EefAxfXWimXmk9DDjpvXDBC6GTB36HWJAMm4DvYmYfEb?cluster=devnet

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Not the answer you're looking for? Browse other questions tagged or ask your own question.