> ## Documentation Index
> Fetch the complete documentation index at: https://docs.ton.org/llms.txt
> Use this file to discover all available pages before exploring further.

<AgentInstructions>

## Submitting Feedback

If you encounter incorrect, outdated, or confusing documentation on this page, submit feedback:

POST https://docs.ton.org/feedback

```json
{
  "path": "/foundations/messages/internal",
  "feedback": "Description of the issue"
}
```

Only submit feedback when you have something specific and actionable to report.

</AgentInstructions>

# Internal messages

Internal messages are the messages sent from a contract to an arbitrary account. They are the most common type of a message.

## After processing

The contents of an internal message after it was processed are as follows:

```tlb theme={"theme":{"light":"github-light-default","dark":"dark-plus"},"languages":{"custom":["/resources/grammars/tolk.tmLanguage.json","/resources/grammars/tlb.tmLanguage.json","/resources/grammars/fift.tmLanguage.json","/resources/grammars/tasm.tmLanguage.json","/resources/grammars/func.tmLanguage.json"]}}
int_msg_info$0
    ihr_disabled:Bool
    bounce:Bool
    bounced:Bool
    src:MsgAddressInt
    dest:MsgAddressInt
    value:CurrencyCollection
    extra_flags:(VarUInteger 16)
    fwd_fee:Grams
    created_lt:uint64
    created_at:uint32
= CommonMsgInfo;

message$_
    {X:Type}
    info:CommonMsgInfo
    init:(Maybe (Either StateInit ^StateInit))
    body:(Either X ^X)
= Message X;
```

* `ihr_disabled` — unused, always set to `true`.
* `bounce` — whether the message is [bounceable](#bounces).
* `bounced` — whether the message has been [bounced](#bounces).
* `src` — address of the contract that sent the message.
* `dest` — address of the account that received the message.
* `value` — amount of Toncoin and extra-currency attached to the message.
* `extra_flags` — used with the [new bounce format](#new-bounce-format).
* `fwd_fee` — fee charged for forwarding the message.
* `created_lt` — logical time when the message was created.
* `created_at` — unix time when the message was created.

## Before processing

When a contract sends a message, the requirements for the structure above are relaxed.

```tlb theme={"theme":{"light":"github-light-default","dark":"dark-plus"},"languages":{"custom":["/resources/grammars/tolk.tmLanguage.json","/resources/grammars/tlb.tmLanguage.json","/resources/grammars/fift.tmLanguage.json","/resources/grammars/tasm.tmLanguage.json","/resources/grammars/func.tmLanguage.json"]}}
int_msg_info$0
    ihr_disabled:Bool
    bounce:Bool
    bounced:Bool
    // NB! different type
    src:MsgAddress
    dest:MsgAddressInt
    value:CurrencyCollection
    extra_flags:(VarUInteger 16)
    fwd_fee:Grams
    created_lt:uint64
    created_at:uint32
= CommonMsgInfoRelaxed;

message$_
    {X:Type}
    info:CommonMsgInfoRelaxed
    // NB! actually StateInitWithLibs
    init:(Maybe (Either StateInit ^StateInit))
    body:(Either X ^X)
= MessageRelaxed X;
_
    fixed_prefix_length:(Maybe (## 5))
    special:(Maybe TickTock)
    code:(Maybe ^Cell)
    data:(Maybe ^Cell)
    library:(HashmapE 256 SimpleLib)
= StateInitWithLibs;
```

The process of transforming the relaxed version of the structure into the strict version occurs in the action phase and is performed by the handler of [send message actions](/foundations/actions/send). This action rewrites [some fields](/foundations/actions/send#message-normalization) of the structure with correct values and validates the `StateInit` field against the `StateInitWithLibs` type.

## Deploy

It is possible to simultaneously send both the payload in the `body` field and the `StateInit` in the `init` field to [initialized the contract](/foundations/messages/deploy) and process the payload in the same transaction.

## Message value

The message may set `value` field that tells to transfer Toncoin and extra-currency to the recipient of the message. The actually transferred amount depends on the value of this field and a [send mode](/foundations/messages/modes).

## Bounces

A bounce message is used to inform the sender that handling of their message failed. It is sent automatically to a sender when

* there is enough Toncoin to send it left from handling the failed message,
* and the message is bounceable,
* and when either
  * a contract throws an error from the [compute phase](/foundations/phases#compute-phase) during message processing, and the state was not committed by [`COMMIT`](/tvm/instructions#f80f-commit) TVM instruction,
  * or an action fails in the [action phase](/foundations/phases#action-phase) with the `+16` flag enabled: [`SendBounceIfActionFail`](/foundations/messages/modes) in case of message sends or [`ReserveBounceIfActionFail`](/foundations/actions/reserve#modes) in case of reservations.

### Default bounce

If the `bounce` flag is set to `true`, the message is bounceable. If the bounce conditions are met, the bounce message is produced from the failed message with the following transformation:

* `src` and `dest` fields are swapped.
* The `bounced` flag is set to `true` to tell it's the bounce message.
* The `bounce` flag is set to `false` to prevent infinite loop of bouncing messages until no Toncoin is left to spend.
* `body` is replaced with the concatenation of 32 bits equal to one (`0xffffffff`) and the first 256 bits of the old `body`. The new `body` is stored in the message in-place, with [`left`](https://github.com/ton-blockchain/ton/blob/master/crypto/block/block.tlb#L10) of the `Either`.

This message is then sent to the `src` address of the original message.

### New bounce format

The default bounce format has a flaw, that its `body` is too small to store even an internal address, and thus has limited usability for real-world applications. A new bounce format was introduced to address this issue.

Using the `extra_flags` field, it is possible to change how the new `body` will be constructed. All other transformations remain the same.

* If `(extra_flags & 1) = 1` the new bounce format is enabled. The bounced message now contains the root cell of the `body` of the failed message, with all the refs removed from it.
  * If `(extra_flags & 2) = 2` is *also* set, the bounced message contains the entire `body` of the original message, without removing any refs.

All other bits in `extra_flags` are reserved for future use.

When a message in new bounce format is bounced, the bounce message body has the following format (`new_bounce_body`):

```tlb theme={"theme":{"light":"github-light-default","dark":"dark-plus"},"languages":{"custom":["/resources/grammars/tolk.tmLanguage.json","/resources/grammars/tlb.tmLanguage.json","/resources/grammars/fift.tmLanguage.json","/resources/grammars/tasm.tmLanguage.json","/resources/grammars/func.tmLanguage.json"]}}
_
    value:CurrencyCollection
    created_lt:uint64
    created_at:uint32
= NewBounceOriginalInfo;

_
    gas_used:uint32
    vm_steps:uint32
= NewBounceComputePhaseInfo;

// NB! 0xfffffffe is different from the old 0xffffffff
new_bounce_body#fffffffe
    original_body:^Cell
    original_info:^NewBounceOriginalInfo
    bounced_by_phase:uint8
    exit_code:int32
    compute_phase:(Maybe NewBounceComputePhaseInfo)
= NewBounceBody;
```

* `original_body` — the cell that contains the body of the original message. If `extra_flags & 2` then the whole body is returned; otherwise only the root without refs is included.
* `original_info` — the value, lt, and Unix time of the original message.
* `bounced_by_phase`:
  * `0` - compute phase was skipped. `exit_code` denotes the skip reason:
    * `exit_code = -1` — no state (an account is uninit or frozen, and no `StateInit` is present in the message).
    * `exit_code = -2` — bad state (an account is uninit or frozen, and `StateInit` in the message has the wrong hash).
    * `exit_code = -3` — no gas.
    * `exit_code = -4` — account is suspended.
  * `1` — compute phase failed. `exit_code` is the value from the compute phase.
  * `2` — action phase failed. `exit_code` is the value from the action phase.
* `exit_code` — 32-bit exit code, see above.
* `compute_phase` — exists if it was not skipped, i.e., when `bounced_by_phase` is not 0.
* `gas_used` — same as `gas_used` of `TrComputePhase` of the transaction.
* `vm_steps` — same as `vm_steps` of `TrComputePhase` of the transaction.

The bounced message has the same 0th and 1st bits in `extra_flags` as the original message. The rest of the bits are set to zero.
