TypeError on Remix for BSC Contract - solidity

I have this error "TypeError: Return argument type address is not implicitly convertible to expected type (type of first return variable) address payable. --> Driven.sol:233:16: | 233 | return msg.sender; | ^^^^^^^^^^"
for the following function
abstract contract Context {
function _msgSender() internal view virtual returns (address payable) {
return msg.sender;
}
function _msgData() internal view virtual returns (bytes memory) {
this; // silence state mutability warning without generating bytecode - see https://github.com/ethereum/solidity/issues/2691
return msg.data;
}
}
Please help!

Since Solidity 0.8, msg.sender is not payable anymore. You need to cast it to payable first.
function _msgSender() internal view virtual returns (address payable) {
return payable(msg.sender); // added payable
}
Or you can return just address (not payable):
function _msgSender() internal view virtual returns (address) { // removed payable
return msg.sender;
}

Related

TypeError: Member "mint" not found or not visible after argument-dependent lookup in address

I'm trying to compile this contract but it won't work. I know I can point mint and redeem for address, but since I'll get these from compound, how do I point it to make it compile?
// SPDX-License-Identifier: MIT
pragma solidity <0.9.0;
import "#openzeppelin/contracts-upgradeable/token/ERC20/extensions/ERC4626Upgradeable.sol";
import "#openzeppelin/contracts-upgradeable/token/ERC20/extensions/IERC20MetadataUpgradeable.sol";
import {OwnableUpgradeable} from "#openzeppelin/contracts-upgradeable/access/OwnableUpgradeable.sol";
contract Myvaultis ERC4626Upgradeable, OwnableUpgradeable {
//compound variable to store address
address _cAsset;
function initialize(
IERC20MetadataUpgradeable asset_,
string memory name_,
string memory symbol_
) public initializer {
__MyVault_init(asset_, name_, symbol_);
_cAsset = 0x00000000000000000000000; //put here cAsset address
}
function __MyVault_init(
IERC20MetadataUpgradeable asset_,
string memory name_,
string memory symbol_
) internal onlyInitializing {
__ERC4626_init_unchained(asset_);
__ERC20_init_unchained(name_, symbol_);
__Ownable_init_unchained();
}
function depositCompound(
IERC20MetadataUpgradeable asset_,
address cAsset_,
uint256 _amount
) public onlyOwner returns (uint) {
asset_.approve(cAsset_, _amount);
// Mint cTokens
uint mintResult = cAsset_.mint(_amount);
return mintResult;
}
function withdrawCompound(
uint256 amount,
bool redeemType,
address cAsset_
) public onlyOwner returns (bool) {
uint256 redeemResult;
if (redeemType == true) {
redeemResult = cAsset_.redeem(amount);
} else {
redeemResult = cAsset_.redeemUnderlying(amount);
}
return true;
}
}
The error i'm getting is
TypeError: Member "mint" not found or not visible after argument-dependent lookup in address.
|
38 | uint mintResult = cAsset_.mint(_amount);
| ^^^^^^^^^^^^
Error HH600: Compilation failed
looks like you haven't defined the contract and your trying to access it via the address.
You might have to define the interface then plug in the address.
contract = interface(address)
then you can use contract.functionName(parameters)

how to override openzeppelin _countVote function in GovernorCountingSimple.sol file?

I am making a DAO using openzeppelin and I downloaded the governance contract that they provide from the openzeppelin contract wizard. once I had imported this file into remix IDE an error popped up saying
"Function has to override specified but does not override anything"
so I followed that error to the GovernorCountingSimple.sol file and saw that it was the _countVote function but I can't seem to override it. I think I am just missing something simple but I don't know how to override it when the last argument within the function is "bytes memory" with no declared name and I cant seem to just call the super statement on the function to pass the last argument.
// SPDX-License-Identifier: MIT
pragma solidity ^0.8.4;
import "#openzeppelin/contracts/governance/Governor.sol";
import "#openzeppelin/contracts/governance/extensions/GovernorSettings.sol";
import "#openzeppelin/contracts/governance/extensions/GovernorCountingSimple.sol";
import "#openzeppelin/contracts/governance/extensions/GovernorVotes.sol";
import "#openzeppelin/contracts/governance/extensions/GovernorVotesQuorumFraction.sol";
import "#openzeppelin/contracts/governance/extensions/GovernorTimelockControl.sol";
contract GovernernerContract is Governor, GovernorSettings, GovernorCountingSimple,
GovernorVotes, GovernorVotesQuorumFraction, GovernorTimelockControl {
constructor(
IVotes _token,
TimelockController _timelock,
uint256 _votingDelay,
uint256 _votingPeriod,
uint256 _quorumPercentage
)
Governor("governernerContract")
GovernorSettings( _votingDelay /* 1 block */, _votingPeriod /* 45818= ~ 1 week */, 0)
GovernorVotes(_token)
GovernorVotesQuorumFraction(_quorumPercentage)
GovernorTimelockControl(_timelock)
{}
// The following functions are overrides required by Solidity.
//this is my attempt to override the function but i dont know how to deal with the bytes
//memory argument
function _countVote(
uint256 proposalId,
address account,
uint8 support,
uint256 weight,
bytes memory // params
) internal override {
// super._countVote(proposalId,account,support,weight,*);
}
function votingDelay()
public
view
override(IGovernor, GovernorSettings)
returns (uint256)
{
// return super.votingDelay();
}
function votingPeriod()
public
view
override(IGovernor, GovernorSettings)
returns (uint256)
{
return super.votingPeriod();
}
function quorum(uint256 blockNumber)
public
view
override(IGovernor, GovernorVotesQuorumFraction)
returns (uint256)
{
return super.quorum(blockNumber);
}
function state(uint256 proposalId)
public
view
override(Governor, GovernorTimelockControl)
returns (ProposalState)
{
return super.state(proposalId);
}
function propose(address[] memory targets, uint256[] memory values, bytes[] memory calldatas, string memory description)
public
override(Governor, IGovernor)
returns (uint256)
{
return super.propose(targets, values, calldatas, description);
}
function proposalThreshold()
public
view
override(Governor, GovernorSettings)
returns (uint256)
{
return super.proposalThreshold();
}
function _execute(uint256 proposalId, address[] memory targets, uint256[] memory values, bytes[] memory calldatas, bytes32 descriptionHash)
internal
override(Governor, GovernorTimelockControl)
{
super._execute(proposalId, targets, values, calldatas, descriptionHash);
}
function _cancel(address[] memory targets, uint256[] memory values, bytes[] memory calldatas, bytes32 descriptionHash)
internal
override(Governor, GovernorTimelockControl)
returns (uint256)
{
return super._cancel(targets, values, calldatas, descriptionHash);
}
function _executor()
internal
view
override(Governor, GovernorTimelockControl)
returns (address)
{
return super._executor();
}
function supportsInterface(bytes4 interfaceId)
public
view
override(Governor, GovernorTimelockControl)
returns (bool)
{
return super.supportsInterface(interfaceId);
}
}
You was closer to the solution...
Just change this line: super._countVote(proposalId,account,support,weight,*);
Instead of using this symbol * to omit last parameter, try with single quotes.
This should work:
super._countVote(proposalId,account,support,weight,'');

I tried using interface to get owner address from another NFT smart contract (ERC721), what have I done wrong?

I tried using interface to get the owner address from another NFT smart contract (ERC721) like this:
// SPDX-License-Identifier: MIT
pragma solidity ^0.8.13;
interface INft {
function owner() external view returns (address); //doesn't work
function name() external view returns (string calldata); //works
function ownerOf(uint256 tokenId) external view returns (address); //works
}
contract Test {
//doesn't work
function getNftProjectOwner (address _nft) external view returns (address){
return INft(_nft).owner();
}
//works
function getNftProjectName (address _nft) external view returns (string memory){
return INft(_nft).name();
}
//works
function getNftTokenOwner(address _nft, uint256 _tokenId) external view returns (address){
return INft(_nft).ownerOf(_tokenId);
}
}
So far all other external function call works except for the one that gets the nft smart contract owner address. Here's the reference from OpenZeppelin's Ownable.sol:
/**
* #dev Returns the address of the current owner.
*/
function owner() public view virtual returns (address) {
return _owner;
}
I also noticed that Ownable is an abstract contract and I'm wondering if I have declared it as an interface wrongly? I kept getting the error message "call to Test.getNftProjectOwner errored: execution reverted"

Error in solidity code: Return argument type bytes1 is not implicitly convertible to expected type

I have setter and getter:
function setFunc(bytes calldata _value) public {
getBytes = _value;
}
function getFunc() public view returns(bytes calldata) {
return getBytes;
}
When I run my code, the compiler shows that
TypeError: Return argument type bytes1 is not implicitly convertible to expected type (type of first return variable) bytes calldata.
--> contracts/GetterSetter.sol:38:16:
|
38 | return getBytes[];
| ^^^^^^^^^^
Before that I had another error:
TypeError: Data location must be "memory" or "calldata" for return parameter in function, but none was given.
--> contracts/GetterSetter.sol:37:51:
|
37 | function requestedBytes() public view returns(bytes) {
| ^^^^^
Could you help to resolve it and what input example should I provide into setter for correct functions working?
I will be really appreciate for your help!
The getter function return type needs to have the memory data location.
It's because the EVM loads the value from storage to memory, and then returns it from memory.
pragma solidity ^0.8;
contract MyContract {
bytes getBytes;
function setFunc(bytes calldata _value) public {
getBytes = _value;
}
function getFunc() public view returns(bytes memory) {
return getBytes;
}
}
The return type could have the calldata location only if it's returning the actual and unchanged calldata from the input param:
pragma solidity ^0.8;
contract MyContract {
function getFunc(bytes calldata _value) public pure returns(bytes calldata) {
return _value;
}
}
Hm.. I tried in Remix and it looks like woks as it should, but when I run it with Hardhat, it returns Zero.
await getset.setBytes32('0x7465737400000000000000000000000000000000000000000000000000000000');
const getBytes32 = await getset.requestedBytes32();
console.log('Bytes32:', getBytes32);

Send and transfer are only available for objects of type address payable , not address

function withdraw() public payable {
msg.sender.transfer(address(this).balance);
}
I wrote this code and I got "ERROR send and transfer are only available for objects of type address payable , not address.".
Only the payable address type has the transfer method. msg.sender is the address type so you need to cast it to be payable:
payable(msg.sender).transfer(address(this).balance);
From the docs:
The address type comes in two flavours, which are largely identical:
address: Holds a 20 byte value (size of an Ethereum address).
address payable: Same as address, but with the additional members > transfer and send.
You need to cast it to an address payable type to use the send and transfer methods. See https://docs.soliditylang.org/en/v0.8.11/types.html#address for more details.
address payable private owner;
then set the owner in constructor as msg.sender:
constructor() {
setOwner(msg.sender);
}
this is setOwner:
function setOwner(address newOwner) private {
owner = payable(newOwner);
}
this is withdraw function:
function withdraw() external onlyOwner {
(bool success,)=owner.call{value:address(this).balance}("");
// if it is not success, throw error
require(success,"Transfer failed!");
}
Make sure only owner can call this so write a modifier:
modifier onlyOwner() {
if (msg.sender != getContractOwner()) {
revert OnlyOwner();
}
_;
}
revert OnlyOwner is sending custom message with newer versions of solidity:
/// Only owner has an access!
error OnlyOwner();