Skip to content

Commit dd205a0

Browse files
committed
more stuff
1 parent 97695be commit dd205a0

File tree

3 files changed

+30
-4
lines changed

3 files changed

+30
-4
lines changed

target_chains/ethereum/contracts/contracts/pulse/IPulse.sol

Lines changed: 23 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -6,11 +6,32 @@ import "@pythnetwork/pyth-sdk-solidity/IPyth.sol";
66
import "./PulseEvents.sol";
77
import "./PulseState.sol";
88

9-
interface IPulseConsumer {
9+
abstract contract IPulseConsumer {
10+
// This method is called by Pulse to provide the price updates to the consumer.
11+
// It asserts that the msg.sender is the Pulse contract. It is not meant to be
12+
// overridden by the consumer.
13+
function _pulseCallback(
14+
uint64 sequenceNumber,
15+
PythStructs.PriceFeed[] memory priceFeeds
16+
) external {
17+
address pulse = getPulse();
18+
require(pulse != address(0), "Pulse address not set");
19+
require(msg.sender == pulse, "Only Pulse can call this function");
20+
21+
pulseCallback(sequenceNumber, priceFeeds);
22+
}
23+
24+
// getPulse returns the Pulse contract address. The method is being used to check that the
25+
// callback is indeed from the Pulse contract. The consumer is expected to implement this method.
26+
function getPulse() internal view virtual returns (address);
27+
28+
// This method is expected to be implemented by the consumer to handle the price updates.
29+
// It will be called by _pulseCallback after _pulseCallback ensures that the call is
30+
// indeed from Pulse contract.
1031
function pulseCallback(
1132
uint64 sequenceNumber,
1233
PythStructs.PriceFeed[] memory priceFeeds
13-
) external;
34+
) internal virtual;
1435
}
1536

1637
interface IPulse is PulseEvents {

target_chains/ethereum/contracts/contracts/pulse/Pulse.sol

Lines changed: 6 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -99,7 +99,7 @@ abstract contract Pulse is IPulse, PulseState {
9999
emit PriceUpdateRequested(req, priceIds);
100100
}
101101

102-
// TODO: I don't think this should be payable. Any cost paid to Pyth should come from the contract and be taken out of the provider's accrued fees.
102+
// TODO: does this need to be payable? Any cost paid to Pyth could be taken out of the provider's accrued fees.
103103
function executeCallback(
104104
address providerToCredit,
105105
uint64 sequenceNumber,
@@ -145,12 +145,16 @@ abstract contract Pulse is IPulse, PulseState {
145145
clearRequest(sequenceNumber);
146146
// TODO: if this effect occurs here, we need to guarantee that executeCallback can never revert.
147147
// If executeCallback can revert, then funds can be permanently locked in the contract.
148+
// TODO: there also needs to be some penalty mechanism in case the expected provider doesn't execute the callback.
149+
// This should take funds from the expected provider and give to providerToCredit. The penalty should probably scale
150+
// with time in order to ensure that the callback eventually gets executed.
151+
// (There may be exploits with ^ though if the consumer contract is malicious ?)
148152
_state.providers[providerToCredit].accruedFeesInWei += req.fee;
149153
_state.providers[providerToCredit].accruedFeesInWei += SafeCast
150154
.toUint128(msg.value - pythFee);
151155

152156
try
153-
IPulseConsumer(req.requester).pulseCallback{
157+
IPulseConsumer(req.requester)._pulseCallback{
154158
gas: req.callbackGasLimit
155159
}(sequenceNumber, priceFeeds)
156160
{

target_chains/ethereum/contracts/contracts/pulse/PulseState.sol

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -12,6 +12,7 @@ contract PulseState {
1212
struct Request {
1313
uint64 sequenceNumber;
1414
uint256 publishTime;
15+
// TODO: this is going to absolutely explode gas costs. Need to do something smarter here.
1516
bytes32[MAX_PRICE_IDS] priceIds;
1617
uint8 numPriceIds; // Actual number of price IDs used
1718
uint256 callbackGasLimit;

0 commit comments

Comments
 (0)