Launch of a Ghanaian Cedi Stablecoin (cGHS)

Dear all,

Together with the Celo Africa DAO, the support of Mento Labs, and the whole community, we would like to propose a Ghanaian Cedi decentralized stablecoin (cGHS) on Mento.

Why Ghana now?
After eXOF and cKES, and with the success of the roll out of mobile wallets and partners such as Hurupay, Kotani Pay, MiniPay, and Valora in Africa, and a fast growing number of Celo community members in Ghana, it makes sense to take a deeper look at the country.

With an internet penetration rate of 70% and a projected increase of 10m internet users by 2029, Ghana’s digital connectivity is rapidly expanding. Ghana is extensively relying on mobile money transfers, with over 48 million active accounts as of December 2021. As access to technology becomes more prevalent, this growth creates a solid foundation for the adoption of digital assets.

Ghana’s diaspora remitted over $4.6bn in 2023, with the largest contributions coming from North America, followed by Europe and other regions. This significant flow of remittances underscores the demand for efficient cross-border payment solutions.

The IFC estimates that the financing gap for small and medium enterprises in Ghana is equivalent to 13 percent of the GDP making a case for lending (credit for SMEs) using the cGHS as well.

Ghana’s youthful population, with around 57% under 25, presents a unique opportunity to explore innovative financial options. Digital assets provide an accessible and inclusive platform for financial participation, resonating with the aspirations of Ghana’s tech-savvy youth.

Celo Africa DAO
The Celo Africa DAO is currently supporting the growth of the Celo Ecosystem in Africa having received funding from the Celo Public Goods Fund of the Celo Community treasury. The DAO is currently focused on incubating products that enable more engaged usage of the Celo network across wallets such as MiniPay, Valora and others. Many of these projects will find the cGHS relevant to the use cases they support. The DAO is also involved in attracting the best Web3 developers in Africa, as well as increasing the awareness and usage of Celo Ecosystem products.

Mento Labs
Mento Labs helps with building out code and infrastructure for the cGHS on the Mento Platform. The team is working on infrastructure for other countries as well.

Other Partners in Ghana:
Partners on the ground in Ghana include wallets (MiniPay, Valora, Hurupay, Kotani Pay), Micro-finance organizations (Haraka, Grameen Foundation), DAOs The Celo Africa DAO (Celo Ghana), On- and off-ramps (Fonbnk,Transak)

Sources:

9 Likes

I’m also very excited about the Ghanaian Cedi stablecoin. Celo has a strong presence across Africa, thanks to Celo Africa DAO, and the Mento Labs team is eager to support cGHS. Credit and remittances present excellent use cases for the stablecoin, and I’m thrilled to collaborate with all these outstanding partners mentioned above once again.

5 Likes

I fully support the launch of the Cedi stablecoin! Given the rapid growth of mobile money and the huge impact of remittances, Ghana is the perfect place for this. A stablecoin like Cedi will make cross-border payments easier and provide new opportunities for small businesses to access credit and many other use cases.

It’s great to see the Celo Africa DAO and Mento Labs working together to make this happen.

Are there any updates?

Hey folks, the first proposal to enable the needed oracles for the launch of $cGHS is now out:

A second proposal for the official launch of $cGHS will soon follow.

This post provides an overview of the transactions to whitelist the Chainlink relayer contracts that will report the rates needed for the cGHS. As with previous proposals, the Celo community will have the opportunity to verify these transactions. In preparation for the upcoming CGP, we have completed the following steps:

  • Tested the proposal on Alfajores
  • Simulated the proposal on a fork of Celo Mainnet and conducted tests against this fork

The transactions included in the upcoming CGP will be categorized as follows, with transaction indices noted in brackets:

  1. Whitelisting and configuring Chainlink Relayers in SortedOracles (0-3)
  2. Configuring rate feed aliases in SortedOracles (3-4)

Before we dive into the details of each section and transaction, we recommend setting up celocli to follow along. For those technically inclined, you can find everything described here in our deployment tooling repository. For verifying the addresses included in the proposal, please refer to the Appendix at the bottom for helpful tips.

1. Whitelisting and configuring of Chainlink Relayers in SortedOracles

The ChainlinkRelayer transmits rate feed data from a single Chainlink price feed or an aggregation of multiple Chainlink price feeds to the SortedOracles contract.

This contract can aggregate multiple price feeds to provide derived rate feeds to the protocol. This is necessary because it is more efficient for Oracle providers to report FX rates against the dollar and crypto-asset rates against the dollar, rather than providing all possible combinations.

For example, Chainlink reports the GHS/USD rate for the Ghanaian Cedi, but it does not directly provide the CELO/GHS rate, which is needed for gas payments in a GHS stable token. However, by using both the GHS/USD and CELO/USD rates, the following path can be derived:

CELO/USD * inverse(GHS/USD) = CELO/GHS.

A separate ChainlinkRelayer instance will be deployed for each required rate feed.

TX#0 - whitelist CELO/GHS Relayer in SortedOracles - addOracle()

  • Verify the SortedOracleProxy address
  • Verify the Rate Feed Identifier
    • address(uint160(uint256(keccak256(abi.encodePacked("relayed:CELOGHS”)))));
  • Verify the ChainlinkRelayer address

TX#1 - configure CELO/GHS token report expiry time in SortedOracles - setTokenReportExpiry()

  • Verify the SortedOracleProxy address
  • Verify the Rate Feed Identifier
    • address(uint160(uint256(keccak256(abi.encodePacked("relayed:CELOGHS”)))));
  • Verify Report Expiry Seconds
    • 6 minutes = 360

TX#2 - whitelist GHS/USD Relayer in SortedOracles - addOracle()

  • Verify the SortedOracleProxy address
  • Verify the Rate Feed Identifier
    • address(uint160(uint256(keccak256(abi.encodePacked("relayed:GHSUSD”)))));
  • Verify the ChainlinkRelayer address

TX#3 - configure GHS/USD token report expiry time in SortedOracles-setTokenReportExpiry()

  • Verify the SortedOracleProxy address
  • Verify the Rate Feed Identifier
    • address(uint160(uint256(keccak256(abi.encodePacked("relayed:GHSUSD”)))));
  • Verify Report Expiry Seconds
    • 6 minutes = 360

2. Configuring rate feed alias in SortedOracles

SortedOracles now has a new feature for equivalent tokens. When a token is configured with an equivalent token, SortedOracles will return the median rate of the equivalent token when queried. This feature was first used for gas payments with USDC by setting its equivalent token to cUSD.

This update also allows us to eliminate the distinction between rate feeds for tokens and those derived from identifiers.

In the context of cGHS, this means we can report to the rate feed defined by the canonical ID: relayed:CELOGHS, and then have the address of cGHS point to that for gas payments.

TX#4 - configure equivalent token for CELO/GHS rate in SortedOracles-setEquivalentToken()

  • Verify the SortedOracleProxy address
  • Verify the token address
    • StableTokenGHSProxy address
  • Verify the Rate Feed Identifier
    • address(uint160(uint256(keccak256(abi.encodePacked("relayed:CELOGHS”)))));

Appendix: Verifying an address

Verifying that an address in the CGP is correct requires a few different strategies depending on what that address is (see the mento docs for some additional information). Here are common situations:

  • Is it a rate feed identifier like: address(uint160(keccack256(”relayed:CELOGHS”)))
    • Use Keccak-256 Online 2 to compute the keccak
    • Take the last 40 characters (20 bytes) of the keccak and compare with the value
  • Is it a Mento contract?
  • Is it a Core Celo contract?
    • Yes:
      • It’s probably GoldToken or FeeCurrencyWhiteList which can be both verified in the Celo Registry
3 Likes

Fantastic to see more cStables coming online. Great work!

1 Like

Hi folks,

The proposal to officially launch $cGHS was submitted and is available for voting:

This post outlines the transactions that will be part of the activation of $cGHS and the creation of a new Mento pair cUSD/cGHS. As with previous proposals, the Celo community will have the opportunity to verify these transactions. In preparation for the upcoming CGP, we have done the following:

  • Tested the proposal on Alfajores
  • Simulated the proposal on a fork of Celo Mainnet, in addition to running tests against the fork

The prerequisite work for $cGHS activation has been done in a recent proposal:

  • CGP 159 - Addition of cGHS/USD and CELO/cGHS oracles

The transactions that will be in the upcoming CGP will be broken down into the following sections, noted here with transaction indices in brackets:

  1. Initialization of the cGHS stable token (0-6)
  2. Configure the new exchange (7)
  3. Configure trading limits (8-9)
  4. Configure BreakerBox (10-11)
  5. Configure the MedianDeltaBreaker (12-14)

Before we dive deep into each section and transaction, we recommend you set up celocli to follow along. For the tech-savvy, you can find everything we are describing here in our deployment tooling repository as code.

To verify that addresses included in the proposal are correct, please refer to the Appendix at the bottom for some handy tips.

1. Initialization of the cGHS stable token

This includes all the transactions related to registering cGHS as an official mento stable token: initializing the token contract, configuring its constitution parameters, adding it to the reserve, and whitelisting it as a gas currency.

TX#0 - initialize the cGHS proxy token contract and set its implementation address

This proxy contract was deployed and verified on Celo’s mainnet and points to the new StableTokenV2 implementation contract. Immediately after, ownership of the proxy contract was transferred to governance.

  • Verify the StableTokenGHSProxy address
  • Verify the StableTokenV2 implementation address
  • Verify the initialization parameters for the new stable token:
    • name: Celo Ghanian Cedi
    • symbol: cGHS
    • initialBalanceAddresses: [] (no pre-mint)
    • initialBalanceValues: [] (no pre-mint)

TX#1 - Call StableTokenV2 initializer

  • Verify the StableTokenGHSProxy address
  • Verify the StableTokenV2 implementation address
  • Verify the initialization parameters:
    • broker: - Verify the broker proxy address
    • validators: - Verify the validators address
    • exchange: address(0) - Exchanges have been deprecated and replaced by the broker

TX#2 - set constitution parameters for transfer(address,uint256)

  • Verify the GovernanceProxy address
  • Verify the StableTokenGHSProxy address
  • Verify the function selector: bytes4(keccak256(bytes("transfer(address,uint256)")))
  • Verify the threshold: 0.9 * 1e24 (same as existing stables)

TX#3 - set constitution parameters for transferWithComment(address,uint256,string)

  • Verify the GovernanceProxy address
  • Verify the StableTokenGHSProxy address
  • Verify the function selector: bytes4(keccak256(bytes("transferWithComment(address,uint256,string)")))
  • Verify the threshold: 0.6 * 1e24 (same as existing stables)

TX#4 - set constitution parameters for approve(address,uint256)

  • Verify the GovernanceProxy address
  • Verify the StableTokenGHSProxy address
  • Verify the function selector: bytes4(keccak256(bytes("approve(address,uint256)")))
  • Verify the threshold: 0.6 * 1e24 (same as existing stables)

TX#5 - add cGHS as a stable token to the Reserve

  • Verify the ReserveProxy address
  • Verify the StableTokenGHSProxy address

TX#6 - whitelist cGHS as a gas currency

  • Verify the FeeCurrencyWhitelistProxy address
  • Verify the StableTokenGHSProxy address

2. Configure the new exchange

:warning: Verification tip: As in previous proposals, we recommend ignoring the args field from celocli and focusing on params, as well as ignoring the numbered fields and instead focusing only on the named fields. This is due to how nested structs are serialized by celocli, which might make the payload look confusing.

The pool configuration structures are documented here: https://docs.mento.org/mento/developers/smart-contracts/bipoolmanager

TX#7 - create the cUSD/cGHS exchange

  • Verify the BiPoolManagerProxy address
  • Verify the exchange configuration

3. Configure trading limits

Similar to the previous section, the output of celocli is too verbose when dealing with arguments and structs, so it’s recommended to ignore args and numbered fields and to focus instead on params and named fields.

The TradingLimit.Config structure is documented here: Mento Trading Limits

TX#8 - configure trading limits on cUSD for the cUSD/cGHS exchange

  • Verify BrokerProxy address
  • Verify the arguments:
    • exchangeId: the deterministic id of the cUSD/cGHS exchange
    • token: which asset in the pair to target, in this case, the cUSD token address
    • config: the trading limit configuration

TX#9 - Configure trading limits on cGHS for the cUSD/cGHS exchange

  • Verify Broker address
  • Verify the arguments:
    • exchangeId: the deterministic id of the cUSD/cGHS exchange
    • token: which asset in the pair to target, in this case, the cGHS token address
    • config: the trading limit configuration

4. Configure BreakerBox

Here we configure the BreakerBox to ensure it monitors changes to the new GHS/USD rate.

TX#10 - adding rate feeds to the BreakerBox:

  • Verify the BreakerBox address
  • Verify the arguments:
    • newRateFeedIDs an array of oracle feed ids. In this case, the array only contains the id of GHS/USD
      • GHS/USD - address(uint160(uint256(keccak256("relayed:GHSUSD"))))

TX#11 - enable the MedianDeltaBreaker on the GHS/USD rate feed

  • Verify the BreakerBox address
  • Verify the arguments:
    • breakerAddress should be the MedianDeltaBreaker
    • rateFeedID should be the identifier for the GHS/USD rate, i.e. address(uint160(uint256(keccak256("relayed:GHSUSD"))))
    • enable true

5. Configure the MedianDeltaBreaker

These transactions configure the MedianDeltaBreaker with the appropriate values needed to determine when the breaker should trip for the GHS/USD rate feed and how much time should pass before the breakers can be reset.

TX#12 - set the cooldown time on the MedianDeltaBreaker for the GHS/USD rate feed

  • Verify the MedianDeltaBreaker address
  • Verify the arguments:
    • rateFeedIDs: the array of rate feeds to configure:
      • GHS/USD: address(uint160(uint256(keccak256("relayed:GHSUSD"))))
    • cooldownTimes: the array of cooldown times to be configured per rate feed. The values are in seconds.
      • GHS/USD: 15 minutes = 900s

TX#13 - set the rate change thresholds on the MedianDeltaBreaker for the GHS/USD rate feed

  • Verify the MedianDeltaBreaker address
  • Verify the arguments:
    • rateFeedIDs: the array of rate feeds to configure:
      • GHS/USD: address(uint160(uint256(keccak256("relayed:GHSUSD"))))
    • rateChangeThresholds: The array of rate change thresholds to be configured per rate feed. The values are fixed-point numbers – a number with 24 decimals, i.e. 1 is written as 1e24.
      • GHS/USD: 4e22 = 4%

TX#14 - set the smoothing factor on the MedianDeltaBreaker for the GHS/USD rate feed

  • Verify the MedianDeltaBreaker address
  • Verify the arguments:
    • rateFeedID: The id of the rate feed to be updated
      • GHS/USD: address(uint160(uint256(keccak256("relayedGHSUSD"))))
    • newSmoothingFactor: The new smoothing factor value. The value is a fixed point number, similar to the rate change threshold.
      • GHS/USD: 5e21 = 0.5%

Appendix: Verifying an address

Verifying that an address in the CGP is correct requires a few different strategies depending on what that address is (see the mento docs for some additional information). Here are common situations:

  • Is it a rate feed identifier like: address(uint160(keccack256(”relayed:GHSUSD”)))
    • Use Keccak-256 Online 2 to compute the keccak
    • Take the last 40 characters (20 bytes) of the keccak and compare with the value
  • Is it a Mento contract?
  • Is it a Core Celo contract?
    • Yes:
      • It’s probably GoldToken or FeeCurrencyWhiteList which can be both verified in the Celo Registry

We are very excited to have partnered with CeloAfrica DAO and look forward to the use cases that $cGHS will enable. If you would like to deploy a stable token on top of the Mento Platform we would love to hear from you as well. Please join our discord and reach out.

1 Like