1
1
// Copyright 2019-2022 ChainSafe Systems
2
2
// SPDX-License-Identifier: Apache-2.0, MIT
3
3
4
+ use std:: cmp:: max;
4
5
use std:: collections:: btree_map:: Entry ;
5
6
use std:: collections:: BTreeMap ;
6
7
use std:: iter;
@@ -1216,65 +1217,62 @@ impl Actor {
1216
1217
1217
1218
let rew = request_current_epoch_block_reward ( rt) ?;
1218
1219
let pow = request_current_total_power ( rt) ?;
1220
+ let circulating_supply = rt. total_fil_circ_supply ( ) ;
1219
1221
1220
1222
let succeeded_sectors = rt. transaction ( |state : & mut State , rt| {
1221
1223
let mut succeeded = Vec :: new ( ) ;
1222
- let mut deadlines = state
1223
- . load_deadlines ( rt. store ( ) ) ?;
1224
+ let mut deadlines = state. load_deadlines ( rt. store ( ) ) ?;
1224
1225
1225
1226
let mut new_sectors = Vec :: with_capacity ( validated_updates. len ( ) ) ;
1226
1227
for & dl_idx in deadlines_to_load. iter ( ) {
1227
- let mut deadline = deadlines
1228
- . load_deadline ( rt. policy ( ) , rt. store ( ) , dl_idx)
1229
- . map_err ( |e|
1228
+ let mut deadline =
1229
+ deadlines. load_deadline ( rt. policy ( ) , rt. store ( ) , dl_idx) . map_err ( |e| {
1230
1230
e. downcast_default (
1231
1231
ExitCode :: USR_ILLEGAL_STATE ,
1232
1232
format ! ( "failed to load deadline {}" , dl_idx) ,
1233
1233
)
1234
- ) ?;
1234
+ } ) ?;
1235
1235
1236
- let mut partitions = deadline
1237
- . partitions_amt ( rt. store ( ) )
1238
- . map_err ( |e|
1239
- e. downcast_default (
1240
- ExitCode :: USR_ILLEGAL_STATE ,
1241
- format ! ( "failed to load partitions for deadline {}" , dl_idx) ,
1242
- )
1243
- ) ?;
1236
+ let mut partitions = deadline. partitions_amt ( rt. store ( ) ) . map_err ( |e| {
1237
+ e. downcast_default (
1238
+ ExitCode :: USR_ILLEGAL_STATE ,
1239
+ format ! ( "failed to load partitions for deadline {}" , dl_idx) ,
1240
+ )
1241
+ } ) ?;
1244
1242
1245
1243
let quant = state. quant_spec_for_deadline ( rt. policy ( ) , dl_idx) ;
1246
1244
1247
1245
for with_details in & decls_by_deadline[ & dl_idx] {
1248
- let update_proof_type = with_details. sector_info . seal_proof
1249
- . registered_update_proof ( )
1250
- . map_err ( |_|
1251
- actor_error ! (
1252
- illegal_state,
1253
- "couldn't load update proof type"
1254
- )
1246
+ let update_proof_type =
1247
+ with_details. sector_info . seal_proof . registered_update_proof ( ) . map_err (
1248
+ |_| actor_error ! ( illegal_state, "couldn't load update proof type" ) ,
1255
1249
) ?;
1256
1250
if with_details. update . update_proof_type != update_proof_type {
1257
1251
return Err ( actor_error ! (
1258
1252
illegal_argument,
1259
- format!( "unsupported update proof type {}" , i64 :: from( with_details. update. update_proof_type) )
1253
+ format!(
1254
+ "unsupported update proof type {}" ,
1255
+ i64 :: from( with_details. update. update_proof_type)
1256
+ )
1260
1257
) ) ;
1261
1258
}
1262
1259
1263
- rt. verify_replica_update (
1264
- & ReplicaUpdateInfo {
1265
- update_proof_type,
1266
- new_sealed_cid : with_details. update . new_sealed_cid ,
1267
- old_sealed_cid : with_details. sector_info . sealed_cid ,
1268
- new_unsealed_cid : with_details. full_unsealed_cid ,
1269
- proof : with_details. update . replica_proof . clone ( ) ,
1270
- }
1271
- )
1272
- . map_err ( |e|
1273
- e. downcast_default (
1274
- ExitCode :: USR_ILLEGAL_ARGUMENT ,
1275
- format ! ( "failed to verify replica proof for sector {}" , with_details. sector_info. sector_number) ,
1276
- )
1277
- ) ?;
1260
+ rt. verify_replica_update ( & ReplicaUpdateInfo {
1261
+ update_proof_type,
1262
+ new_sealed_cid : with_details. update . new_sealed_cid ,
1263
+ old_sealed_cid : with_details. sector_info . sealed_cid ,
1264
+ new_unsealed_cid : with_details. full_unsealed_cid ,
1265
+ proof : with_details. update . replica_proof . clone ( ) ,
1266
+ } )
1267
+ . map_err ( |e| {
1268
+ e. downcast_default (
1269
+ ExitCode :: USR_ILLEGAL_ARGUMENT ,
1270
+ format ! (
1271
+ "failed to verify replica proof for sector {}" ,
1272
+ with_details. sector_info. sector_number
1273
+ ) ,
1274
+ )
1275
+ } ) ?;
1278
1276
1279
1277
let mut new_sector_info = with_details. sector_info . clone ( ) ;
1280
1278
@@ -1291,8 +1289,10 @@ impl Actor {
1291
1289
1292
1290
let duration = new_sector_info. expiration - new_sector_info. activation ;
1293
1291
1294
- new_sector_info. deal_weight = with_details. deal_spaces . deal_space . clone ( ) * duration;
1295
- new_sector_info. verified_deal_weight = with_details. deal_spaces . verified_deal_space . clone ( ) * duration;
1292
+ new_sector_info. deal_weight =
1293
+ with_details. deal_spaces . deal_space . clone ( ) * duration;
1294
+ new_sector_info. verified_deal_weight =
1295
+ with_details. deal_spaces . verified_deal_space . clone ( ) * duration;
1296
1296
1297
1297
// compute initial pledge
1298
1298
let qa_pow = qa_power_for_weight (
@@ -1302,7 +1302,8 @@ impl Actor {
1302
1302
& new_sector_info. verified_deal_weight ,
1303
1303
) ;
1304
1304
1305
- new_sector_info. replaced_day_reward = with_details. sector_info . expected_day_reward . clone ( ) ;
1305
+ new_sector_info. replaced_day_reward =
1306
+ with_details. sector_info . expected_day_reward . clone ( ) ;
1306
1307
new_sector_info. expected_day_reward = expected_reward_for_power (
1307
1308
& rew. this_epoch_reward_smoothed ,
1308
1309
& pow. quality_adj_power_smoothed ,
@@ -1318,78 +1319,68 @@ impl Actor {
1318
1319
new_sector_info. replaced_sector_age =
1319
1320
ChainEpoch :: max ( 0 , rt. curr_epoch ( ) - with_details. sector_info . activation ) ;
1320
1321
1321
- let initial_pledge_at_upgrade = initial_pledge_for_power (
1322
- & qa_pow,
1323
- & rew. this_epoch_baseline_power ,
1324
- & rew. this_epoch_reward_smoothed ,
1325
- & pow. quality_adj_power_smoothed ,
1326
- & rt. total_fil_circ_supply ( ) ,
1322
+ new_sector_info. initial_pledge = max (
1323
+ new_sector_info. initial_pledge ,
1324
+ initial_pledge_for_power (
1325
+ & qa_pow,
1326
+ & rew. this_epoch_baseline_power ,
1327
+ & rew. this_epoch_reward_smoothed ,
1328
+ & pow. quality_adj_power_smoothed ,
1329
+ & circulating_supply,
1330
+ ) ,
1327
1331
) ;
1328
1332
1329
- if initial_pledge_at_upgrade > with_details. sector_info . initial_pledge {
1330
- let deficit = & initial_pledge_at_upgrade - & with_details. sector_info . initial_pledge ;
1331
-
1332
- let unlocked_balance = state
1333
- . get_unlocked_balance ( & rt. current_balance ( ) )
1334
- . map_err ( |_|
1335
- actor_error ! ( illegal_state, "failed to calculate unlocked balance" )
1336
- ) ?;
1337
- if unlocked_balance < deficit {
1338
- return Err ( actor_error ! (
1339
- insufficient_funds,
1340
- "insufficient funds for new initial pledge requirement {}, available: {}, skipping sector {}" ,
1341
- deficit,
1342
- unlocked_balance,
1343
- with_details. sector_info. sector_number
1344
- ) ) ;
1345
- }
1346
-
1347
- state. add_initial_pledge ( & deficit) . map_err ( |_e|
1348
- actor_error ! (
1349
- illegal_state,
1350
- "failed to add initial pledge"
1351
- )
1352
- ) ?;
1353
-
1354
- new_sector_info. initial_pledge = initial_pledge_at_upgrade;
1355
- }
1356
-
1357
1333
let mut partition = partitions
1358
1334
. get ( with_details. update . partition )
1359
- . map_err ( |e|
1335
+ . map_err ( |e| {
1360
1336
e. downcast_default (
1361
1337
ExitCode :: USR_ILLEGAL_STATE ,
1362
- format ! ( "failed to load deadline {} partition {}" , with_details. update. deadline, with_details. update. partition) ,
1338
+ format ! (
1339
+ "failed to load deadline {} partition {}" ,
1340
+ with_details. update. deadline, with_details. update. partition
1341
+ ) ,
1363
1342
)
1364
- ) ?
1343
+ } ) ?
1365
1344
. cloned ( )
1366
- . ok_or_else ( || actor_error ! ( not_found, "no such deadline {} partition {}" , dl_idx, with_details. update. partition) ) ?;
1345
+ . ok_or_else ( || {
1346
+ actor_error ! (
1347
+ not_found,
1348
+ "no such deadline {} partition {}" ,
1349
+ dl_idx,
1350
+ with_details. update. partition
1351
+ )
1352
+ } ) ?;
1367
1353
1368
1354
let ( partition_power_delta, partition_pledge_delta) = partition
1369
- . replace_sectors ( rt. store ( ) ,
1370
- & [ with_details. sector_info . clone ( ) ] ,
1371
- & [ new_sector_info. clone ( ) ] ,
1372
- info. sector_size ,
1373
- quant,
1355
+ . replace_sectors (
1356
+ rt. store ( ) ,
1357
+ & [ with_details. sector_info . clone ( ) ] ,
1358
+ & [ new_sector_info. clone ( ) ] ,
1359
+ info. sector_size ,
1360
+ quant,
1374
1361
)
1375
1362
. map_err ( |e| {
1376
1363
e. downcast_default (
1377
1364
ExitCode :: USR_ILLEGAL_STATE ,
1378
- format ! ( "failed to replace sector at deadline {} partition {}" , with_details. update. deadline, with_details. update. partition) ,
1365
+ format ! (
1366
+ "failed to replace sector at deadline {} partition {}" ,
1367
+ with_details. update. deadline, with_details. update. partition
1368
+ ) ,
1379
1369
)
1380
1370
} ) ?;
1381
1371
1382
1372
power_delta += & partition_power_delta;
1383
1373
pledge_delta += & partition_pledge_delta;
1384
1374
1385
- partitions
1386
- . set ( with_details. update . partition , partition)
1387
- . map_err ( |e| {
1388
- e. downcast_default (
1389
- ExitCode :: USR_ILLEGAL_STATE ,
1390
- format ! ( "failed to save deadline {} partition {}" , with_details. update. deadline, with_details. update. partition) ,
1391
- )
1392
- } ) ?;
1375
+ partitions. set ( with_details. update . partition , partition) . map_err ( |e| {
1376
+ e. downcast_default (
1377
+ ExitCode :: USR_ILLEGAL_STATE ,
1378
+ format ! (
1379
+ "failed to save deadline {} partition {}" ,
1380
+ with_details. update. deadline, with_details. update. partition
1381
+ ) ,
1382
+ )
1383
+ } ) ?;
1393
1384
1394
1385
succeeded. push ( new_sector_info. sector_number ) ;
1395
1386
new_sectors. push ( new_sector_info) ;
@@ -1402,14 +1393,14 @@ impl Actor {
1402
1393
)
1403
1394
} ) ?;
1404
1395
1405
- deadlines
1406
- . update_deadline ( rt. policy ( ) , rt. store ( ) , dl_idx, & deadline)
1407
- . map_err ( |e| {
1396
+ deadlines. update_deadline ( rt. policy ( ) , rt. store ( ) , dl_idx, & deadline) . map_err (
1397
+ |e| {
1408
1398
e. downcast_default (
1409
1399
ExitCode :: USR_ILLEGAL_STATE ,
1410
1400
format ! ( "failed to save deadline {}" , dl_idx) ,
1411
1401
)
1412
- } ) ?;
1402
+ } ,
1403
+ ) ?;
1413
1404
}
1414
1405
1415
1406
let success_len = succeeded. len ( ) ;
@@ -1432,10 +1423,7 @@ impl Actor {
1432
1423
1433
1424
// Overwrite sector infos.
1434
1425
sectors. store ( new_sectors) . map_err ( |e| {
1435
- e. downcast_default (
1436
- ExitCode :: USR_ILLEGAL_STATE ,
1437
- "failed to update sector infos" ,
1438
- )
1426
+ e. downcast_default ( ExitCode :: USR_ILLEGAL_STATE , "failed to update sector infos" )
1439
1427
} ) ?;
1440
1428
1441
1429
state. sectors = sectors. amt . flush ( ) . map_err ( |e| {
@@ -1445,9 +1433,31 @@ impl Actor {
1445
1433
e. downcast_default ( ExitCode :: USR_ILLEGAL_STATE , "failed to save deadlines" )
1446
1434
} ) ?;
1447
1435
1448
- BitField :: try_from_bits ( succeeded) . map_err ( |_| {
1449
- actor_error ! ( illegal_argument; "invalid sector number" )
1450
- } )
1436
+ // Update pledge.
1437
+ let current_balance = rt. current_balance ( ) ;
1438
+ if pledge_delta. is_positive ( ) {
1439
+ let unlocked_balance =
1440
+ state. get_unlocked_balance ( & current_balance) . map_err ( |e| {
1441
+ actor_error ! ( illegal_state, "failed to calculate unlocked balance: {}" , e)
1442
+ } ) ?;
1443
+ if unlocked_balance < pledge_delta {
1444
+ return Err ( actor_error ! (
1445
+ insufficient_funds,
1446
+ "insufficient funds for aggregate initial pledge requirement {}, available: {}" ,
1447
+ pledge_delta,
1448
+ unlocked_balance
1449
+ ) ) ;
1450
+ }
1451
+ }
1452
+
1453
+ state
1454
+ . add_initial_pledge ( & pledge_delta)
1455
+ . map_err ( |e| actor_error ! ( illegal_state, "failed to add initial pledge: {}" , e) ) ?;
1456
+
1457
+ state. check_balance_invariants ( & current_balance) . map_err ( balance_invariants_broken) ?;
1458
+
1459
+ BitField :: try_from_bits ( succeeded)
1460
+ . map_err ( |_| actor_error ! ( illegal_argument; "invalid sector number" ) )
1451
1461
} ) ?;
1452
1462
1453
1463
notify_pledge_changed ( rt, & pledge_delta) ?;
0 commit comments