contract Bread is Ownable, ERC20 {
    // Maximum supply, starts from 1B then decreasable later in time
    // as staking/rewards/etc are modelled by the team
    uint256 maximumSupply = 1000000000 * 1e18;

    // Authorised minters will often be other contracts
    mapping(address => bool) public authorisedMinters;

    constructor() ERC20("Bread", "BREAD") {}

    /**
     * Adds one or more authorised minting address
     */
    function setAuthorisedMinter(address[] calldata minters)
        external
        onlyOwner
    {
        for (uint256 i; i < minters.length; i++) {
            authorisedMinters[minters[i]] = true;
        }
    }

    /**
     * Allows an address (typically a contract) to mint the token
     */
    function authorisedMint(address account, uint256 amount) external {
        require(authorisedMinters[_msgSender()], "Cannot Issue Token");
        require(totalSupply() + amount <= maximumSupply, "Maximum Supply Hit");
        _mint(account, amount);
    }

    /**
     * Decreases maximum supply, cannot be increased afterwards
     */
    function decreaseMaximumSupply(uint256 _total) external onlyOwner {
        require(_total <= maximumSupply, "Over Max Supply");
        require(_total >= totalSupply(), "Under Total Supply");
        maximumSupply = _total;
    }

    /**
     * Check if we're over the total supply
     */
    function overTotalSupply() external view returns (bool) {
        return totalSupply() >= maximumSupply;
    }
}
function decreaseMaximumSupply(uint256 _total) external onlyOwner {
    require(_total <= maximumSupply, "Over Max Supply");
    require(_total >= totalSupply(), "Under Total Supply");
    maximumSupply = _total;
}

/**
 * Decreases maximum supply, cannot be increased afterwards
 */