Skip to content

Commit

Permalink
feat(world): prevent invalid namespace strings
Browse files Browse the repository at this point in the history
  • Loading branch information
alvrs committed Jan 19, 2024
1 parent b179a1a commit d25dfda
Show file tree
Hide file tree
Showing 4 changed files with 31 additions and 1 deletion.
6 changes: 6 additions & 0 deletions packages/world/src/IWorldErrors.sol
Original file line number Diff line number Diff line change
Expand Up @@ -42,6 +42,12 @@ interface IWorldErrors {
*/
error World_InvalidResourceId(ResourceId resourceId, string resourceIdString);

/**
* @notice Raised when an namespace contains an invalid sequence of characters ("__").
* @param namespace The invalid namespace.
*/
error World_InvalidNamespace(bytes14 namespace);

/**
* @notice Raised when trying to register a system that already exists.
* @param system The address of the system.
Expand Down
1 change: 1 addition & 0 deletions packages/world/src/WorldResourceId.sol
Original file line number Diff line number Diff line change
Expand Up @@ -7,6 +7,7 @@ import { ResourceId, ResourceIdInstance, TYPE_BITS } from "@latticexyz/store/src
import { ROOT_NAMESPACE, ROOT_NAME } from "./constants.sol";
import { RESOURCE_NAMESPACE, MASK_RESOURCE_NAMESPACE } from "./worldResourceTypes.sol";

uint256 constant NAMESPACE_BYTES = 14;
uint256 constant NAMESPACE_BITS = 14 * 8; // 14 bytes * 8 bits per byte
uint256 constant NAME_BITS = 16 * 8; // 16 bytes * 8 bits per byte

Expand Down
19 changes: 18 additions & 1 deletion packages/world/src/requireNamespace.sol
Original file line number Diff line number Diff line change
@@ -1,7 +1,9 @@
// SPDX-License-Identifier: MIT
pragma solidity >=0.8.21;

import { ResourceId, WorldResourceIdInstance } from "./WorldResourceId.sol";
import { Bytes } from "@latticexyz/store/src/Bytes.sol";

import { ResourceId, WorldResourceIdInstance, NAMESPACE_BYTES } from "./WorldResourceId.sol";
import { RESOURCE_NAMESPACE } from "./worldResourceTypes.sol";
import { IWorldErrors } from "./IWorldErrors.sol";

Expand All @@ -13,7 +15,22 @@ using WorldResourceIdInstance for ResourceId;
* @param resourceId The resource ID to verify.
*/
function requireNamespace(ResourceId resourceId) pure {
requireValidCharacters(resourceId.getNamespace());

if (ResourceId.unwrap(resourceId) != ResourceId.unwrap(resourceId.getNamespaceId())) {
revert IWorldErrors.World_InvalidResourceType(RESOURCE_NAMESPACE, resourceId, resourceId.toString());
}
}

/**
* @notice Checks if a given namespace string is valid.
* @dev Reverts with IWorldErrors.World_InvalidNamespace if the namespace includes the reserved separator string ("__").
* @param namespace The namespace to verify.
*/
function requireValidCharacters(bytes14 namespace) pure {
for (uint256 i; i < NAMESPACE_BYTES - 1; i++) {
if (Bytes.slice1(namespace, i) == bytes1("_") && Bytes.slice1(namespace, i + 1) == bytes1("_")) {
revert IWorldErrors.World_InvalidNamespace(namespace);
}
}
}
6 changes: 6 additions & 0 deletions packages/world/test/World.t.sol
Original file line number Diff line number Diff line change
Expand Up @@ -345,6 +345,12 @@ contract WorldTest is Test, GasReporter {
world.registerNamespace(namespaceId);
}

function testRegisterInvalidNamespace() public {
bytes14 invalid_namespace = "invld__nmsp";
vm.expectRevert(abi.encodeWithSelector(IWorldErrors.World_InvalidNamespace.selector, invalid_namespace));
world.registerNamespace(WorldResourceIdLib.encodeNamespace(invalid_namespace));
}

function testRegisterCoreNamespacesRevert() public {
vm.expectRevert(
abi.encodeWithSelector(
Expand Down

0 comments on commit d25dfda

Please sign in to comment.