Fixes for resulting negative offers.

This commit is contained in:
Arthur Britto
2013-03-05 17:28:44 -08:00
parent cffb069f1b
commit f95c39e1c5
2 changed files with 31 additions and 17 deletions

View File

@@ -11,12 +11,13 @@ SETUP_LOG();
// --> uBookBase: The order book to take against. // --> uBookBase: The order book to take against.
// --> saTakerPays: What the taker offers (w/ issuer) // --> saTakerPays: What the taker offers (w/ issuer)
// --> saTakerGets: What the taker wanted (w/ issuer) // --> saTakerGets: What the taker wanted (w/ issuer)
// <-- saTakerPaid: What taker paid including saved not including fees. To reduce an offer. // <-- saTakerPaid: What taker could have paid including saved not including fees. To reduce an offer.
// <-- saTakerGot: What taker got not including fees. To reduce an offer. // <-- saTakerGot: What taker got not including fees. To reduce an offer.
// <-- terResult: tesSUCCESS or terNO_ACCOUNT // <-- terResult: tesSUCCESS, terNO_ACCOUNT, telFAILED_PROCESSING, or tecFAILED_PROCESSING
// <-- bUnfunded: if tesSUCCESS, consider offer unfunded after taking. // <-- bUnfunded: if tesSUCCESS, consider offer unfunded after taking.
TER OfferCreateTransactor::takeOffers( TER OfferCreateTransactor::takeOffers(
bool bPassive, const bool bOpenLedger,
const bool bPassive,
const uint256& uBookBase, const uint256& uBookBase,
const uint160& uTakerAccountID, const uint160& uTakerAccountID,
SLE::ref sleTakerAccount, SLE::ref sleTakerAccount,
@@ -58,11 +59,13 @@ TER OfferCreateTransactor::takeOffers(
SLE::pointer sleOfferDir; SLE::pointer sleOfferDir;
uint64 uTipQuality = 0; uint64 uTipQuality = 0;
STAmount saTakerFunds = mEngine->getNodes().accountFunds(uTakerAccountID, saTakerPays); STAmount saTakerFunds = mEngine->getNodes().accountFunds(uTakerAccountID, saTakerPays);
STAmount saSubTakerPays = saTakerPays-saTakerPaid; // How much more to spend.
STAmount saSubTakerGets = saTakerGets-saTakerGot; // How much more is wanted.
// Figure out next offer to take, if needed. // Figure out next offer to take, if needed.
if (saTakerFunds // Taker has funds available. if (saTakerFunds // Taker has funds available.
&& saTakerGot < saTakerGets // Have less than wanted. && saSubTakerPays.isPositive()
&& saTakerPaid < saTakerPays) // Didn't spend all funds allocated. && saSubTakerGets.isPositive())
{ {
sleOfferDir = mEngine->entryCache(ltDIR_NODE, mEngine->getLedger()->getNextLedgerIndex(uTipIndex, uBookEnd)); sleOfferDir = mEngine->entryCache(ltDIR_NODE, mEngine->getLedger()->getNextLedgerIndex(uTipIndex, uBookEnd));
if (sleOfferDir) if (sleOfferDir)
@@ -201,6 +204,8 @@ TER OfferCreateTransactor::takeOffers(
cLog(lsINFO) << "takeOffers: applyOffer: saOfferPays: " << saOfferPays.getFullText(); cLog(lsINFO) << "takeOffers: applyOffer: saOfferPays: " << saOfferPays.getFullText();
cLog(lsINFO) << "takeOffers: applyOffer: saOfferGets: " << saOfferGets.getFullText(); cLog(lsINFO) << "takeOffers: applyOffer: saOfferGets: " << saOfferGets.getFullText();
cLog(lsINFO) << "takeOffers: applyOffer: saOfferRate: " << saOfferRate.getFullText(); cLog(lsINFO) << "takeOffers: applyOffer: saOfferRate: " << saOfferRate.getFullText();
cLog(lsINFO) << "takeOffers: applyOffer: saSubTakerPays: " << saSubTakerPays.getFullText();
cLog(lsINFO) << "takeOffers: applyOffer: saSubTakerGets: " << saSubTakerGets.getFullText();
cLog(lsINFO) << "takeOffers: applyOffer: saTakerPays: " << saTakerPays.getFullText(); cLog(lsINFO) << "takeOffers: applyOffer: saTakerPays: " << saTakerPays.getFullText();
cLog(lsINFO) << "takeOffers: applyOffer: saTakerGets: " << saTakerGets.getFullText(); cLog(lsINFO) << "takeOffers: applyOffer: saTakerGets: " << saTakerGets.getFullText();
@@ -212,8 +217,8 @@ TER OfferCreateTransactor::takeOffers(
saTakerFunds, saTakerFunds,
saOfferPays, saOfferPays,
saOfferGets, saOfferGets,
saTakerPays, saSubTakerPays,
saTakerGets, saSubTakerGets,
saSubTakerPaid, saSubTakerPaid,
saSubTakerGot, saSubTakerGot,
saTakerIssuerFee, saTakerIssuerFee,
@@ -245,6 +250,13 @@ TER OfferCreateTransactor::takeOffers(
else if (saSubTakerGot) else if (saSubTakerGot)
{ {
cLog(lsINFO) << "takeOffers: Offer partial claim."; cLog(lsINFO) << "takeOffers: Offer partial claim.";
if (!saOfferPays.isPositive() || !saOfferGets.isPositive())
{
cLog(lsWARNING) << "takeOffers: ILLEGAL OFFER RESULT.";
bUnfunded = true;
terResult = bOpenLedger ? telFAILED_PROCESSING : tecFAILED_PROCESSING;
}
} }
else else
{ {
@@ -268,18 +280,18 @@ TER OfferCreateTransactor::takeOffers(
terResult = mEngine->getNodes().accountSend(uTakerAccountID, uOfferOwnerID, saSubTakerPaid); // Taker pays offer owner. terResult = mEngine->getNodes().accountSend(uTakerAccountID, uOfferOwnerID, saSubTakerPaid); // Taker pays offer owner.
// Reduce amount considered paid by taker's rate (not actual cost). // Reduce amount considered paid by taker's rate (not actual cost).
STAmount saPay = saTakerPays - saTakerPaid; STAmount saTakerCould = saTakerPays - saTakerPaid; // Taker could pay.
if (saTakerFunds < saPay) if (saTakerFunds < saTakerCould)
saPay = saTakerFunds; saTakerCould = saTakerFunds;
STAmount saTakerUsed = STAmount::multiply(saSubTakerGot, saTakerRate, saTakerPays); STAmount saTakerUsed = STAmount::multiply(saSubTakerGot, saTakerRate, saTakerPays);
cLog(lsINFO) << "takeOffers: applyOffer: saPay: " << saPay.getFullText(); cLog(lsINFO) << "takeOffers: applyOffer: saTakerCould: " << saTakerCould.getFullText();
cLog(lsINFO) << "takeOffers: applyOffer: saSubTakerGot: " << saSubTakerGot.getFullText(); cLog(lsINFO) << "takeOffers: applyOffer: saSubTakerGot: " << saSubTakerGot.getFullText();
cLog(lsINFO) << "takeOffers: applyOffer: saTakerRate: " << saTakerRate.getFullText(); cLog(lsINFO) << "takeOffers: applyOffer: saTakerRate: " << saTakerRate.getFullText();
cLog(lsINFO) << "takeOffers: applyOffer: saTakerUsed: " << saTakerUsed.getFullText(); cLog(lsINFO) << "takeOffers: applyOffer: saTakerUsed: " << saTakerUsed.getFullText();
saTakerPaid += std::min(saPay, saTakerUsed); saTakerPaid += std::min(saTakerCould, saTakerUsed);
saTakerGot += saSubTakerGot; saTakerGot += saSubTakerGot;
if (tesSUCCESS == terResult) if (tesSUCCESS == terResult)
@@ -420,6 +432,7 @@ TER OfferCreateTransactor::doApply()
STAmount saPaid; STAmount saPaid;
STAmount saGot; STAmount saGot;
bool bUnfunded = false; bool bUnfunded = false;
const bool bOpenLedger = isSetBit(mParams, tapOPEN_LEDGER);
if (tesSUCCESS == terResult) if (tesSUCCESS == terResult)
{ {
@@ -434,6 +447,7 @@ TER OfferCreateTransactor::doApply()
cLog(lsWARNING) << "OfferCreate: takeOffers: BEFORE saTakerGets=" << saTakerGets.getFullText(); cLog(lsWARNING) << "OfferCreate: takeOffers: BEFORE saTakerGets=" << saTakerGets.getFullText();
terResult = takeOffers( terResult = takeOffers(
bOpenLedger,
bPassive, bPassive,
uTakeBookBase, uTakeBookBase,
mTxnAccountID, mTxnAccountID,
@@ -473,9 +487,8 @@ TER OfferCreateTransactor::doApply()
} }
else if (saTakerPays.isNegative() || saTakerGets.isNegative()) else if (saTakerPays.isNegative() || saTakerGets.isNegative())
{ {
terResult = isSetBit(mParams, tapOPEN_LEDGER) // If ledger is not final, can vote no.
? telFAILED_PROCESSING // Ledger is not final, can vote no. terResult = bOpenLedger ? telFAILED_PROCESSING : tecFAILED_PROCESSING;
: tecFAILED_PROCESSING;
} }
else if ( else if (
!saTakerPays // Wants nothing more. !saTakerPays // Wants nothing more.
@@ -489,7 +502,7 @@ TER OfferCreateTransactor::doApply()
} }
else if (mPriorBalance.getNValue() < mEngine->getLedger()->getReserve(mTxnAccount->getFieldU32(sfOwnerCount)+1)) else if (mPriorBalance.getNValue() < mEngine->getLedger()->getReserve(mTxnAccount->getFieldU32(sfOwnerCount)+1))
{ {
if (isSetBit(mParams, tapOPEN_LEDGER)) // Ledger is not final, can vote no. if (bOpenLedger) // Ledger is not final, can vote no.
{ {
// Hope for more reserve to come in or more offers to consume. // Hope for more reserve to come in or more offers to consume.
terResult = tecINSUF_RESERVE_OFFER; terResult = tecINSUF_RESERVE_OFFER;

View File

@@ -6,7 +6,8 @@
class OfferCreateTransactor : public Transactor class OfferCreateTransactor : public Transactor
{ {
TER takeOffers( TER takeOffers(
bool bPassive, const bool bOpenLedger,
const bool bPassive,
const uint256& uBookBase, const uint256& uBookBase,
const uint160& uTakerAccountID, const uint160& uTakerAccountID,
SLE::ref sleTakerAccount, SLE::ref sleTakerAccount,