Skip to content

Commit 6d89ae9

Browse files
committed
CRV3WeightCommitsV2 => TimelockedWeightCommits
1 parent ffa23bc commit 6d89ae9

File tree

10 files changed

+176
-24
lines changed

10 files changed

+176
-24
lines changed

pallets/subtensor/src/coinbase/reveal_commits.rs

Lines changed: 5 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -45,9 +45,9 @@ impl<T: Config> Pallet<T> {
4545
let reveal_epoch = cur_epoch.saturating_sub(reveal_period);
4646

4747
// Clean expired commits
48-
for (epoch, _) in CRV3WeightCommitsV2::<T>::iter_prefix(netuid) {
48+
for (epoch, _) in TimelockedWeightCommits::<T>::iter_prefix(netuid) {
4949
if epoch < reveal_epoch {
50-
CRV3WeightCommitsV2::<T>::remove(netuid, epoch);
50+
TimelockedWeightCommits::<T>::remove(netuid, epoch);
5151
}
5252
}
5353

@@ -57,7 +57,7 @@ impl<T: Config> Pallet<T> {
5757
return Ok(());
5858
}
5959

60-
let mut entries = CRV3WeightCommitsV2::<T>::take(netuid, reveal_epoch);
60+
let mut entries = TimelockedWeightCommits::<T>::take(netuid, reveal_epoch);
6161
let mut unrevealed = VecDeque::new();
6262

6363
// Keep popping items off the front of the queue until we successfully reveal a commit.
@@ -185,11 +185,11 @@ impl<T: Config> Pallet<T> {
185185
continue;
186186
}
187187

188-
Self::deposit_event(Event::CRV3WeightsRevealed(netuid, who));
188+
Self::deposit_event(Event::TimelockedWeightsRevealed(netuid, who));
189189
}
190190

191191
if !unrevealed.is_empty() {
192-
CRV3WeightCommitsV2::<T>::insert(netuid, reveal_epoch, unrevealed);
192+
TimelockedWeightCommits::<T>::insert(netuid, reveal_epoch, unrevealed);
193193
}
194194

195195
Ok(())

pallets/subtensor/src/epoch/run_epoch.rs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -607,7 +607,7 @@ impl<T: Config> Pallet<T> {
607607
}
608608

609609
// ---------- v3 ------------------------------------------------------
610-
for (_epoch, q) in CRV3WeightCommitsV2::<T>::iter_prefix(netuid) {
610+
for (_epoch, q) in TimelockedWeightCommits::<T>::iter_prefix(netuid) {
611611
for (who, cb, ..) in q.iter() {
612612
if !Self::is_commit_expired(netuid, *cb) {
613613
if let Some(i) = uid_of(who) {

pallets/subtensor/src/lib.rs

Lines changed: 18 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1664,6 +1664,23 @@ pub mod pallet {
16641664
OptionQuery,
16651665
>;
16661666
#[pallet::storage]
1667+
/// MAP (netuid, epoch) → VecDeque<(who, commit_block, ciphertext, reveal_round)>
1668+
/// Stores a queue of weight commits for an account on a given subnet.
1669+
pub type TimelockedWeightCommits<T: Config> = StorageDoubleMap<
1670+
_,
1671+
Twox64Concat,
1672+
NetUid,
1673+
Twox64Concat,
1674+
u64, // epoch key
1675+
VecDeque<(
1676+
T::AccountId,
1677+
u64, // commit_block
1678+
BoundedVec<u8, ConstU32<MAX_CRV3_COMMIT_SIZE_BYTES>>,
1679+
RoundNumber,
1680+
)>,
1681+
ValueQuery,
1682+
>;
1683+
#[pallet::storage]
16671684
/// MAP (netuid, epoch) → VecDeque<(who, ciphertext, reveal_round)>
16681685
/// DEPRECATED for CRV3WeightCommitsV2
16691686
pub type CRV3WeightCommits<T: Config> = StorageDoubleMap<
@@ -1681,7 +1698,7 @@ pub mod pallet {
16811698
>;
16821699
#[pallet::storage]
16831700
/// MAP (netuid, epoch) → VecDeque<(who, commit_block, ciphertext, reveal_round)>
1684-
/// Stores a queue of v3 commits for an account on a given netuid.
1701+
/// DEPRECATED for TimelockedWeightCommits
16851702
pub type CRV3WeightCommitsV2<T: Config> = StorageDoubleMap<
16861703
_,
16871704
Twox64Concat,

pallets/subtensor/src/macros/events.rs

Lines changed: 14 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -399,5 +399,19 @@ mod events {
399399
///
400400
/// - **version**: The required version.
401401
CommitRevealVersionSet(u16),
402+
403+
/// Timelocked weights have been successfully committed.
404+
///
405+
/// - **who**: The account ID of the user committing the weights.
406+
/// - **netuid**: The network identifier.
407+
/// - **commit_hash**: The hash representing the committed weights.
408+
/// - **reveal_round**: The round at which weights can be revealed.
409+
TimelockedWeightsCommitted(T::AccountId, NetUid, H256, u64),
410+
411+
/// Timelocked Weights have been successfully revealed.
412+
///
413+
/// - **netuid**: The network identifier.
414+
/// - **who**: The account ID of the user revealing the weights.
415+
TimelockedWeightsRevealed(NetUid, T::AccountId),
402416
}
403417
}

pallets/subtensor/src/macros/hooks.rs

Lines changed: 3 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -129,7 +129,9 @@ mod hooks {
129129
// Migrate subnet symbols to fix the shift after subnet 81
130130
.saturating_add(migrations::migrate_subnet_symbols::migrate_subnet_symbols::<T>())
131131
// Migrate CRV3 add commit_block
132-
.saturating_add(migrations::migrate_crv3_commits_add_block::migrate_crv3_commits_add_block::<T>());
132+
.saturating_add(migrations::migrate_crv3_commits_add_block::migrate_crv3_commits_add_block::<T>())
133+
//Migrate CRV3 to TimelockedCommits
134+
.saturating_add(migrations::migrate_crv3_v2_to_timelocked::migrate_crv3_v2_to_timelocked::<T>());
133135
weight
134136
}
135137

Lines changed: 36 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,36 @@
1+
use super::*;
2+
use frame_support::{traits::Get, weights::Weight};
3+
use log;
4+
use scale_info::prelude::string::String;
5+
use sp_std::vec::Vec;
6+
7+
// --------------- Migration ------------------------------------------
8+
/// Moves every (netuid, epoch) queue from `CRV3WeightCommitsV2` into
9+
/// `TimelockedWeightCommits`. Identical key/value layout → pure move.
10+
pub fn migrate_crv3_v2_to_timelocked<T: Config>() -> Weight {
11+
let mig_name: Vec<u8> = b"crv3_v2_to_timelocked_v1".to_vec();
12+
let mut total_weight = T::DbWeight::get().reads(1);
13+
14+
if HasMigrationRun::<T>::get(&mig_name) {
15+
log::info!(
16+
"Migration '{}' already executed - skipping",
17+
String::from_utf8_lossy(&mig_name)
18+
);
19+
return total_weight;
20+
}
21+
log::info!("Running migration '{}'", String::from_utf8_lossy(&mig_name));
22+
23+
for (netuid, epoch, old_q) in CRV3WeightCommitsV2::<T>::drain() {
24+
total_weight = total_weight.saturating_add(T::DbWeight::get().reads_writes(1, 1));
25+
TimelockedWeightCommits::<T>::insert(netuid, epoch, old_q);
26+
}
27+
28+
HasMigrationRun::<T>::insert(&mig_name, true);
29+
total_weight = total_weight.saturating_add(T::DbWeight::get().writes(1));
30+
31+
log::info!(
32+
"Migration '{}' completed",
33+
String::from_utf8_lossy(&mig_name)
34+
);
35+
total_weight
36+
}

pallets/subtensor/src/migrations/mod.rs

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -9,6 +9,7 @@ pub mod migrate_coldkey_swap_scheduled;
99
pub mod migrate_commit_reveal_v2;
1010
pub mod migrate_create_root_network;
1111
pub mod migrate_crv3_commits_add_block;
12+
pub mod migrate_crv3_v2_to_timelocked;
1213
pub mod migrate_delete_subnet_21;
1314
pub mod migrate_delete_subnet_3;
1415
pub mod migrate_disable_commit_reveal;

pallets/subtensor/src/subnets/weights.rs

Lines changed: 6 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -212,8 +212,8 @@ impl<T: Config> Pallet<T> {
212212
/// 4. Rejects the call when the hotkey already has ≥ 10 unrevealed commits in
213213
/// the current epoch.
214214
/// 5. Appends `(hotkey, commit_block, commit, reveal_round)` to
215-
/// `CRV3WeightCommitsV2[netuid][epoch]`.
216-
/// 6. Emits `CRV3WeightsCommitted` with the Blake2 hash of `commit`.
215+
/// `TimelockedWeightCommits[netuid][epoch]`.
216+
/// 6. Emits `TimelockedWeightsCommitted` with the Blake2 hash of `commit`.
217217
/// 7. Updates `LastUpdateForUid` so subsequent rate-limit checks include this
218218
/// commit.
219219
///
@@ -225,7 +225,7 @@ impl<T: Config> Pallet<T> {
225225
/// * `TooManyUnrevealedCommits` – Caller already has 10 unrevealed commits.
226226
///
227227
/// # Events
228-
/// * `CRV3WeightsCommitted(hotkey, netuid, commit_hash)` – Fired after the commit is successfully stored.
228+
/// * `TimelockedWeightsCommitted(hotkey, netuid, commit_hash, reveal_round)` – Fired after the commit is successfully stored.
229229
pub fn do_commit_timelocked_weights(
230230
origin: T::RuntimeOrigin,
231231
netuid: NetUid,
@@ -271,7 +271,7 @@ impl<T: Config> Pallet<T> {
271271
false => Self::get_epoch_index(netuid, cur_block),
272272
};
273273

274-
CRV3WeightCommitsV2::<T>::try_mutate(netuid, cur_epoch, |commits| -> DispatchResult {
274+
TimelockedWeightCommits::<T>::try_mutate(netuid, cur_epoch, |commits| -> DispatchResult {
275275
// 7. Verify that the number of unrevealed commits is within the allowed limit.
276276

277277
let unrevealed_commits_for_who = commits
@@ -289,10 +289,11 @@ impl<T: Config> Pallet<T> {
289289
commits.push_back((who.clone(), cur_block, commit, reveal_round));
290290

291291
// 9. Emit the WeightsCommitted event
292-
Self::deposit_event(Event::CRV3WeightsCommitted(
292+
Self::deposit_event(Event::TimelockedWeightsCommitted(
293293
who.clone(),
294294
netuid,
295295
commit_hash,
296+
reveal_round,
296297
));
297298

298299
// 10. Update the last commit block for the hotkey's UID.

pallets/subtensor/src/tests/migration.rs

Lines changed: 81 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1132,3 +1132,84 @@ fn test_migrate_disable_commit_reveal() {
11321132
);
11331133
});
11341134
}
1135+
1136+
#[test]
1137+
fn test_migrate_crv3_v2_to_timelocked() {
1138+
new_test_ext(1).execute_with(|| {
1139+
// ------------------------------
1140+
// 0. Constants / helpers
1141+
// ------------------------------
1142+
const MIG_NAME: &[u8] = b"crv3_v2_to_timelocked_v1";
1143+
let netuid = NetUid::from(99);
1144+
let epoch: u64 = 7;
1145+
1146+
// ------------------------------
1147+
// 1. Simulate OLD storage (4‑tuple; V2 layout)
1148+
// ------------------------------
1149+
let who: U256 = U256::from(0xdeadbeef_u64);
1150+
let commit_block: u64 = 12345;
1151+
let ciphertext: BoundedVec<u8, ConstU32<MAX_CRV3_COMMIT_SIZE_BYTES>> =
1152+
vec![1u8, 2, 3].try_into().unwrap();
1153+
let round: RoundNumber = 9;
1154+
1155+
let old_queue: VecDeque<_> =
1156+
VecDeque::from(vec![(who, commit_block, ciphertext.clone(), round)]);
1157+
1158+
// Insert under the deprecated alias
1159+
CRV3WeightCommitsV2::<Test>::insert(netuid, epoch, old_queue.clone());
1160+
1161+
// Sanity: entry decodes under old alias
1162+
assert_eq!(
1163+
CRV3WeightCommitsV2::<Test>::get(netuid, epoch),
1164+
old_queue,
1165+
"pre-migration: old queue should be present"
1166+
);
1167+
1168+
// Destination should be empty pre-migration
1169+
assert!(
1170+
TimelockedWeightCommits::<Test>::get(netuid, epoch).is_empty(),
1171+
"pre-migration: destination should be empty"
1172+
);
1173+
1174+
assert!(
1175+
!HasMigrationRun::<Test>::get(MIG_NAME.to_vec()),
1176+
"migration flag should be false before run"
1177+
);
1178+
1179+
// ------------------------------
1180+
// 2. Run migration
1181+
// ------------------------------
1182+
let w = crate::migrations::migrate_crv3_v2_to_timelocked::migrate_crv3_v2_to_timelocked::<
1183+
Test,
1184+
>();
1185+
assert!(!w.is_zero(), "weight must be non-zero");
1186+
1187+
// ------------------------------
1188+
// 3. Verify results
1189+
// ------------------------------
1190+
assert!(
1191+
HasMigrationRun::<Test>::get(MIG_NAME.to_vec()),
1192+
"migration flag not set"
1193+
);
1194+
1195+
// Old storage must be empty (drained)
1196+
assert!(
1197+
CRV3WeightCommitsV2::<Test>::get(netuid, epoch).is_empty(),
1198+
"old queue should have been drained"
1199+
);
1200+
1201+
// New storage must match exactly
1202+
let new_q = TimelockedWeightCommits::<Test>::get(netuid, epoch);
1203+
assert_eq!(
1204+
new_q, old_queue,
1205+
"migrated queue must exactly match the old queue"
1206+
);
1207+
1208+
// Verify the front element matches what we inserted
1209+
let (who2, commit_block2, cipher2, round2) = new_q.front().cloned().unwrap();
1210+
assert_eq!(who2, who);
1211+
assert_eq!(commit_block2, commit_block);
1212+
assert_eq!(cipher2, ciphertext);
1213+
assert_eq!(round2, round);
1214+
});
1215+
}

pallets/subtensor/src/tests/weights.rs

Lines changed: 11 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -5303,7 +5303,7 @@ fn test_do_commit_crv3_weights_success() {
53035303

53045304
let cur_epoch =
53055305
SubtensorModule::get_epoch_index(netuid, SubtensorModule::get_current_block_as_u64());
5306-
let commits = CRV3WeightCommitsV2::<Test>::get(netuid, cur_epoch);
5306+
let commits = TimelockedWeightCommits::<Test>::get(netuid, cur_epoch);
53075307
assert_eq!(commits.len(), 1);
53085308
assert_eq!(commits[0].0, hotkey);
53095309
assert_eq!(commits[0].2, commit_data);
@@ -6158,7 +6158,7 @@ fn test_multiple_commits_by_same_hotkey_within_limit() {
61586158

61596159
let cur_epoch =
61606160
SubtensorModule::get_epoch_index(netuid, SubtensorModule::get_current_block_as_u64());
6161-
let commits = CRV3WeightCommitsV2::<Test>::get(netuid, cur_epoch);
6161+
let commits = TimelockedWeightCommits::<Test>::get(netuid, cur_epoch);
61626162
assert_eq!(
61636163
commits.len(),
61646164
10,
@@ -6192,7 +6192,7 @@ fn test_reveal_crv3_commits_removes_past_epoch_commits() {
61926192
for &epoch in &[past_epoch, reveal_epoch] {
61936193
let bounded_commit = vec![epoch as u8; 5].try_into().expect("bounded vec");
61946194

6195-
assert_ok!(CRV3WeightCommitsV2::<Test>::try_mutate(
6195+
assert_ok!(TimelockedWeightCommits::<Test>::try_mutate(
61966196
netuid,
61976197
epoch,
61986198
|q| -> DispatchResult {
@@ -6203,8 +6203,8 @@ fn test_reveal_crv3_commits_removes_past_epoch_commits() {
62036203
}
62046204

62056205
// Sanity – both epochs presently hold a commit.
6206-
assert!(!CRV3WeightCommitsV2::<Test>::get(netuid, past_epoch).is_empty());
6207-
assert!(!CRV3WeightCommitsV2::<Test>::get(netuid, reveal_epoch).is_empty());
6206+
assert!(!TimelockedWeightCommits::<Test>::get(netuid, past_epoch).is_empty());
6207+
assert!(!TimelockedWeightCommits::<Test>::get(netuid, reveal_epoch).is_empty());
62086208

62096209
// ---------------------------------------------------------------------
62106210
// Run the reveal pass WITHOUT a pulse – only expiry housekeeping runs.
@@ -6213,13 +6213,13 @@ fn test_reveal_crv3_commits_removes_past_epoch_commits() {
62136213

62146214
// past_epoch (< reveal_epoch) must be gone
62156215
assert!(
6216-
CRV3WeightCommitsV2::<Test>::get(netuid, past_epoch).is_empty(),
6216+
TimelockedWeightCommits::<Test>::get(netuid, past_epoch).is_empty(),
62176217
"expired epoch {past_epoch} should be cleared"
62186218
);
62196219

62206220
// reveal_epoch queue is *kept* because its commit could still be revealed later.
62216221
assert!(
6222-
!CRV3WeightCommitsV2::<Test>::get(netuid, reveal_epoch).is_empty(),
6222+
!TimelockedWeightCommits::<Test>::get(netuid, reveal_epoch).is_empty(),
62236223
"reveal-epoch {reveal_epoch} must be retained until commit can be revealed"
62246224
);
62256225
});
@@ -6895,7 +6895,7 @@ fn test_reveal_crv3_commits_retry_on_missing_pulse() {
68956895
));
68966896

68976897
// epoch in which commit was stored
6898-
let stored_epoch = CRV3WeightCommitsV2::<Test>::iter_prefix(netuid)
6898+
let stored_epoch = TimelockedWeightCommits::<Test>::iter_prefix(netuid)
68996899
.next()
69006900
.map(|(e, _)| e)
69016901
.expect("commit stored");
@@ -6909,7 +6909,7 @@ fn test_reveal_crv3_commits_retry_on_missing_pulse() {
69096909
// run *one* block inside reveal epoch without pulse → commit should stay queued
69106910
step_block(1);
69116911
assert!(
6912-
!CRV3WeightCommitsV2::<Test>::get(netuid, stored_epoch).is_empty(),
6912+
!TimelockedWeightCommits::<Test>::get(netuid, stored_epoch).is_empty(),
69136913
"commit must remain queued when pulse is missing"
69146914
);
69156915

@@ -6937,7 +6937,7 @@ fn test_reveal_crv3_commits_retry_on_missing_pulse() {
69376937
assert!(!weights.is_empty(), "weights must be set after pulse");
69386938

69396939
assert!(
6940-
CRV3WeightCommitsV2::<Test>::get(netuid, stored_epoch).is_empty(),
6940+
TimelockedWeightCommits::<Test>::get(netuid, stored_epoch).is_empty(),
69416941
"queue should be empty after successful reveal"
69426942
);
69436943
});
@@ -7080,7 +7080,7 @@ fn test_reveal_crv3_commits_legacy_payload_success() {
70807080

70817081
// commit should be gone
70827082
assert!(
7083-
CRV3WeightCommitsV2::<Test>::get(netuid, commit_epoch).is_empty(),
7083+
TimelockedWeightCommits::<Test>::get(netuid, commit_epoch).is_empty(),
70847084
"commit storage should be cleaned after reveal"
70857085
);
70867086
});

0 commit comments

Comments
 (0)