Platform: Code4rena
Start Date: 17/03/2023
Pot Size: $36,500 USDC
Total HM: 10
Participants: 98
Period: 3 days
Judge: leastwood
Total Solo HM: 5
Id: 223
League: ETH
Rank: 9/98
Findings: 2
Award: $423.80
🌟 Selected for report: 0
🚀 Solo Findings: 0
401.0269 USDC - $401.03
When registering a name containing a non-emoji tile, all the tiles are mapped to emoji tiles before registering a name, so the registered name is invalid. This ruins the protocol, the users can't use it to register the desired names unless they are purely emoji-based.
Add and run a test to canto-namespace-protocol/src/test/Namespace.t.sol
:
// An extra import import {Tray, Utils} from "../Tray.sol";
// The test itself function mintTile(string memory character) internal returns (uint256 trayId, uint8 offset) { bytes32 tileHash = keccak256(bytes(character)); while(true) { trayId = tray.nextTokenId(); tray.buy(1); Tray.TileData[7] memory tiles = tray.getTiles(trayId); for(offset = 0; offset < tiles.length; offset++) { bytes memory tileCharacter = Utils.characterToUnicodeBytes( tiles[offset].fontClass, tiles[offset].characterIndex, tiles[offset].characterModifier); if(keccak256(tileCharacter) == tileHash) return (trayId, offset); } } } function testRegistered() public { vm.startPrank(owner); (uint256 trayId, uint8 offset) = mintTile("a"); uint256 namespaceId = ns.nextNamespaceIDToMint() + 1; Namespace.CharacterData[] memory data = new Namespace.CharacterData[](1); data[0] = Namespace.CharacterData(trayId, offset, 0); tray.approve(address(ns), trayId); ns.fuse(data); assertEq(ns.tokenToName(namespaceId), "a", "Invalid name"); }
And run it:
forge test --mt testRegistered -vv
The result is:
[FAIL. Reason: Assertion failed.] testRegistered() (gas: 4667890) Logs: Error: Invalid name Error: a == b not satisfied [string] Value a: ✨ Value b: a
The a
, which is the first character of font type 1
got registered after mapping to the first character of font type 0
, which is a ✨
emoji.
Foundry
- bytes memory charAsBytes = Utils.characterToUnicodeBytes(0, tileData.characterIndex, characterModifier) + bytes memory charAsBytes = Utils.characterToUnicodeBytes(tileData.fontClass, tileData.characterIndex, characterModifier)
Or, if that's desired, use fontClass
of 1
for all non-zero font classes to remove collisions between differently styled characters.
#0 - c4-judge
2023-03-28T21:59:27Z
0xleastwood marked the issue as duplicate of #117
#1 - c4-judge
2023-04-11T19:28:36Z
0xleastwood marked the issue as satisfactory