From eb79d5859957351231abf77b3a50290264d4d87f Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Guilherme=20Brand=C3=A3o?= <37072140+guilherme-brandao@users.noreply.github.com> Date: Mon, 20 May 2024 16:57:16 +0100 Subject: [PATCH] Fix edge case zero combined loss (#277) - Fallback stake-weighted combined loss to `epsilon` if it's equal to zero Ticket: https://linear.app/upshot/issue/ORA-1391/no-weights-in-one-reputerlosses-breaks-the-calcnetworklosses --- .../inference_synthesis/network_losses.go | 11 +++++++++-- .../network_losses_test.go | 19 +++++++++++++++++++ 2 files changed, 28 insertions(+), 2 deletions(-) diff --git a/x/emissions/keeper/inference_synthesis/network_losses.go b/x/emissions/keeper/inference_synthesis/network_losses.go index 0986a5d64..b6c77eb4d 100644 --- a/x/emissions/keeper/inference_synthesis/network_losses.go +++ b/x/emissions/keeper/inference_synthesis/network_losses.go @@ -100,6 +100,10 @@ func CalcNetworkLosses( fmt.Println("Error updating running weighted average for next combined loss: ", err) return emissions.ValueBundle{}, err } + // If the combined loss is zero, set it to epsilon to avoid divide by zero + if nextCombinedLoss.Loss.IsZero() { + nextCombinedLoss.Loss = epsilon + } runningWeightedCombinedLoss = nextCombinedLoss // Not all reputers may have reported losses on the same set of inferers => important that the code below doesn't assume that! @@ -245,11 +249,14 @@ func CalcCombinedNetworkLoss( ) if err != nil { fmt.Println("Error updating running weighted average for combined loss: ", err) - return alloraMath.ZeroDec(), err + return Loss{}, err } runningWeightedCombinedLoss = nextCombinedLoss } } - + // If the combined loss is zero, set it to epsilon to avoid divide by zero + if runningWeightedCombinedLoss.Loss.IsZero() { + runningWeightedCombinedLoss.Loss = epsilon + } return runningWeightedCombinedLoss.Loss, nil } diff --git a/x/emissions/keeper/inference_synthesis/network_losses_test.go b/x/emissions/keeper/inference_synthesis/network_losses_test.go index 80cbdd494..e92bb5ae5 100644 --- a/x/emissions/keeper/inference_synthesis/network_losses_test.go +++ b/x/emissions/keeper/inference_synthesis/network_losses_test.go @@ -176,6 +176,25 @@ func (s *InferenceSynthesisTestSuite) TestCalcCombinedNetworkLoss() { expectedLoss: alloraMath.MustNewDecFromString(".000015456633"), expectedErr: nil, }, + { + name: "One reputer reporting a zero combined loss", + stakesByReputer: map[inference_synthesis.Worker]cosmosMath.Uint{ + "worker1": inference_synthesis.CosmosUintOneE18(), // 1 token + }, + reportedLosses: &emissions.ReputerValueBundles{ + ReputerValueBundles: []*emissions.ReputerValueBundle{ + { + ValueBundle: &emissions.ValueBundle{ + Reputer: "worker1", + CombinedValue: alloraMath.MustNewDecFromString("0"), + }, + }, + }, + }, + epsilon: alloraMath.MustNewDecFromString("1e-4"), + expectedLoss: alloraMath.MustNewDecFromString("1e-4"), // Should be equal to epsilon + expectedErr: nil, + }, } for _, tc := range tests {