| 365 | } |
| 366 | |
| 367 | void psbt_elements_normalize_fees(struct wally_psbt *psbt) |
| 368 | { |
| 369 | struct amount_asset asset; |
| 370 | size_t fee_output_idx = psbt->num_outputs; |
| 371 | |
| 372 | if (!is_elements(chainparams)) |
| 373 | return; |
| 374 | |
| 375 | /* Elements requires that every input value is accounted for, |
| 376 | * including the fees */ |
| 377 | struct amount_sat total_in = AMOUNT_SAT(0), val; |
| 378 | for (size_t i = 0; i < psbt->num_inputs; i++) { |
| 379 | val = psbt_input_get_amount(psbt, i); |
| 380 | if (!amount_sat_add(&total_in, total_in, val)) |
| 381 | return; |
| 382 | } |
| 383 | for (size_t i = 0; i < psbt->num_outputs; i++) { |
| 384 | asset = wally_tx_output_get_amount(&psbt->tx->outputs[i]); |
| 385 | if (elements_wtx_output_is_fee(psbt->tx, i)) { |
| 386 | if (fee_output_idx == psbt->num_outputs) { |
| 387 | fee_output_idx = i; |
| 388 | continue; |
| 389 | } |
| 390 | /* We already have at least one fee output, |
| 391 | * remove this one */ |
| 392 | psbt_rm_output(psbt, i--); |
| 393 | continue; |
| 394 | } |
| 395 | if (!amount_asset_is_main(&asset)) |
| 396 | continue; |
| 397 | |
| 398 | if (!amount_sat_sub(&total_in, total_in, |
| 399 | amount_asset_to_sat(&asset))) |
| 400 | return; |
| 401 | } |
| 402 | |
| 403 | if (amount_sat_eq(total_in, AMOUNT_SAT(0))) |
| 404 | return; |
| 405 | |
| 406 | /* We need to add a fee output */ |
| 407 | if (fee_output_idx == psbt->num_outputs) { |
| 408 | psbt_append_output(psbt, NULL, total_in); |
| 409 | } else { |
| 410 | u64 sats = total_in.satoshis; /* Raw: wally API */ |
| 411 | struct wally_tx_output *out = &psbt->tx->outputs[fee_output_idx]; |
| 412 | if (wally_tx_confidential_value_from_satoshi( |
| 413 | sats, out->value, out->value_len) != WALLY_OK) |
| 414 | return; |
| 415 | } |
| 416 | } |
| 417 | |
| 418 | bool psbt_has_input(const struct wally_psbt *psbt, |
| 419 | const struct bitcoin_outpoint *outpoint) |
no test coverage detected