Skip to content

Commit 35cac3a

Browse files
committed
fix: Use registration token to prevent double meta node/target id use
This takes the previously ignored node_alias field on received heartbeats from meta nodes (only!) and stores it together with the meta target as a registration token. When the field is already filled, a mismatch will fail the heartbeat.
1 parent 2eba093 commit 35cac3a

File tree

1 file changed

+38
-4
lines changed

1 file changed

+38
-4
lines changed

mgmtd/src/bee_msg/common.rs

Lines changed: 38 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -51,10 +51,46 @@ pub(super) async fn update_node(msg: RegisterNode, app: &impl App) -> Result<Nod
5151
}
5252
}
5353

54+
let new_alias_or_reg_token = String::from_utf8(msg.node_alias)?;
55+
5456
let (node, is_new) = if let Some(node) = node {
5557
// Existing node, update data
5658
db::node::update(tx, node.uid, msg.port, machine_uuid)?;
5759

60+
// If the updated node is a meta node, check if its corresponding target has a
61+
// registration token
62+
if msg.node_type == NodeType::Meta {
63+
let stored_reg_token: Option<String> = tx.query_row(
64+
sql!("SELECT reg_token FROM meta_targets WHERE node_id = ?1"),
65+
[node.num_id()],
66+
|row| row.get(0),
67+
)?;
68+
69+
if let Some(ref t) = stored_reg_token
70+
&& t != &new_alias_or_reg_token
71+
{
72+
bail!(
73+
"Meta node {} has already been registered and its \
74+
registration token ({}) does not match the stored token ({})",
75+
node,
76+
new_alias_or_reg_token,
77+
t
78+
);
79+
} else if stored_reg_token.is_none() {
80+
tx.execute(
81+
sql!(
82+
"UPDATE targets SET reg_token = ?1
83+
WHERE node_id = ?2 AND node_type = ?3"
84+
),
85+
rusqlite::params![
86+
new_alias_or_reg_token,
87+
node.num_id(),
88+
NodeType::Meta.sql_variant()
89+
],
90+
)?;
91+
}
92+
}
93+
5894
(node, false)
5995
} else {
6096
// New node, do additional checks and insert data
@@ -72,9 +108,7 @@ pub(super) async fn update_node(msg: RegisterNode, app: &impl App) -> Result<Nod
72108
// updated to no longer start with a number, thus it is unlikely this
73109
// would happen unless BeeGFS 8 was mounted by a BeeGFS 7 client.
74110

75-
let new_alias = String::from_utf8(msg.node_alias)
76-
.ok()
77-
.and_then(|s| Alias::try_from(s).ok());
111+
let new_alias = Alias::try_from(new_alias_or_reg_token.clone()).ok();
78112

79113
if new_alias.is_none() {
80114
log::warn!(
@@ -102,7 +136,7 @@ client version < 8.0)"
102136
);
103137
};
104138

105-
db::target::insert_meta(tx, target_id, None)?;
139+
db::target::insert_meta(tx, target_id, Some(&new_alias_or_reg_token))?;
106140
}
107141

108142
(node, true)

0 commit comments

Comments
 (0)