evm solidity ERC721合约,mint方法提示token id重复(合约实现是自增id)
【问题分类】
- bug
- P2P网络相关(包含libp2p,liquid)
- 链账户身份与权限相关(证书问题、public、多签投票问题)
- 核心交易引擎相关(交易池、DAG)
- 共识相关
- 智能合约相关
- 存储相关
- SDK相关
- 长安链CMC工具
- 长安链管理台
- 长安链浏览器
- 长安链合约IDE
- 长安链web签名插件
- 跨链相关
- 轻节点相关
- 隐私计算相关
- 密码学相关
- 环境依赖
- 其他补充:
【问题描述】(请对问题进行描述,方便定位问题)
我使用solidity 写ERC721合约,在mint是一个nft时候, 向链端发送交易量大的时刻,执行时候会出现tokenid重覆,我们合约代码token id是自增的。 我看合约代码应该是map[tokenid] = address. 重复报错,这个感觉是并发执行交易,同时读到了状态变量,导致tokenid一样
在system.log发现错误 2023-08-02 10:44:37.008 [ERROR] [Vm] ^[[33;1m@xf_chain_sit^[[0m v2@v2.3.2/runtime.go:464 revert instruction encountered in contract [XXCO_0727] execution, tx: [177770dc53d82c79ca3c1b8c5fdd0b81760405d44f394b82a8219ad2336cb59e], error: [ERC721: token already minted]
具体的现象,操作步骤,前置条件等,尽可能描述清楚,有截图说明更佳 版本:使用chainmaker v2.3.1版本,国密算法 tbft共识算法
合约代码
// SPDX-License-Identifier: MIT
pragma solidity ^0.8.9;
import {ERC721URIStorage, ERC721} from "./node_modules/@openzeppelin/contracts/token/ERC721/extensions/ERC721URIStorage.sol";
import {AccessControl} from "./node_modules/@openzeppelin/contracts/access/AccessControl.sol";
import "./node_modules/@openzeppelin/contracts/utils/Counters.sol";
contract XXCO is ERC721URIStorage, AccessControl {
using Counters for Counters.Counter;
Counters.Counter private _tokenIdCounter;
uint96 private _maxTokenSize;
bytes32 public constant ROLE_ADMIN = DEFAULT_ADMIN_ROLE;
constructor(string memory name, string memory symbol) ERC721(name, symbol) {
_grantRole(ROLE_ADMIN, msg.sender);
_setMaxTokenSize(50_000);
}
function safeMint(address _to, string memory _tokenURI) external {
uint256 _tokenId = _tokenIdCounter.current();
_tokenIdCounter.increment();
if (_tokenId >= _maxTokenSize) {
revert("Mint token num is full!");
}
_safeMint(_to, _tokenId);
_setTokenURI(_tokenId, _tokenURI);
}
function transferFrom(address from, address to, uint256 tokenId)
public
virtual
override {
require(false, "Unsupport now!");
from;to;tokenId;
}
function safeTransferFrom(address from, address to, uint256 tokenId)
public
virtual
override {
require(false, "Unsupport now!");
from;to;tokenId;
}
function safeTransferFrom(address from, address to, uint256 tokenId, bytes memory data)
public
virtual
override {
require(false, "Unsupport now!");
from;to;tokenId;data;
}
function supportsInterface(bytes4 interfaceId)
public
view
override(ERC721URIStorage, AccessControl)
returns (bool) {
return ERC721URIStorage.supportsInterface(interfaceId) || AccessControl.supportsInterface(interfaceId);
}
function setMaxTokenSize(uint96 num) public onlyRole(ROLE_ADMIN) {
require(num>_maxTokenSize,"Value not allow below maxTokenSize!");
_setMaxTokenSize(num);
}
function _setMaxTokenSize(uint96 num) internal onlyRole(ROLE_ADMIN) {
if (num>_maxTokenSize) _maxTokenSize = num;
}
function totalSupply() public view returns (uint256) {
return _maxTokenSize;
}
}
【相关日志文件】(如果有报错日志请贴图,或者上传附件)
chainmaker-go 的 log/system.log & bin/panic.log file *
SDK 的 sdk.log file
【系统信息】(请填写系统信息,方便定位问题)
- chainmaker-go version * : [v2.3.1]
- **OS & version * : 4.19.0-13-amd64 #1 SMP Debian 4.19.160-2 (2020-11-28) x86_64 GNU/Linux
- docker镜像 version:
-
管理台 version:
- 如果是管理台的相关问题,请附带管理台版本,如果不是可忽略。
-
区块浏览器 version:
- 如果是浏览器的相关问题,请附带浏览器版本,如果不是可忽略。
-
合约IDE version:
- 如果是合约IDE的相关问题,请附带合约IDE版本,如果不是可忽略。
-
web签名插件 version:
- 如果是web签名插件的相关问题,请附带web签名插件版本,如果不是可忽略。
To upload designs, you'll need to enable LFS and have an admin enable hashed storage. More information