@0x/types
: Add FillResults
, MatchedFillResults
, and
`BatchMatchedFillResults` types. `@0x/contracts-utils`: Add reference functions for `SafeMath`. `@0x/contracts-exchange-libs`: Add reference functions for `LibMath` and `LibFillResults`. `@0x/contracts-test-utils`: Move `*FillResults` types to `@0x/types`. `@0x/contracts-test-utils`: Add `log_utils.ts`. `@0x/contracts-test-utils`: Add `hexRandom()` to `hex_utils.ts`. `@0x/contracts-test-utils`: Add the contstants: `MAX_UINT256`, `ADDRESS_LENGTH`.
This commit is contained in:
parent
c54d69e5ae
commit
c30d59d5d3
@ -1,29 +1,7 @@
|
|||||||
[
|
[
|
||||||
{
|
{
|
||||||
"timestamp": 1563193019,
|
"version": "3.1.0",
|
||||||
"version": "3.0.2",
|
|
||||||
"changes": [
|
"changes": [
|
||||||
{
|
|
||||||
"note": "Dependencies updated"
|
|
||||||
}
|
|
||||||
]
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"timestamp": 1563047529,
|
|
||||||
"version": "3.0.1",
|
|
||||||
"changes": [
|
|
||||||
{
|
|
||||||
"note": "Dependencies updated"
|
|
||||||
}
|
|
||||||
]
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"version": "3.0.0",
|
|
||||||
"changes": [
|
|
||||||
{
|
|
||||||
"note": "Move `LibTransactionDecoder` to contracts/dev-utils package",
|
|
||||||
"pr": 1848
|
|
||||||
},
|
|
||||||
{
|
{
|
||||||
"note": "Break up `LibEIP712` into reusable components",
|
"note": "Break up `LibEIP712` into reusable components",
|
||||||
"pr": 1742
|
"pr": 1742
|
||||||
@ -75,6 +53,37 @@
|
|||||||
{
|
{
|
||||||
"note": "Add `expirationTimeSeconds` to `ZeroExTransaction` struct",
|
"note": "Add `expirationTimeSeconds` to `ZeroExTransaction` struct",
|
||||||
"pr": 1823
|
"pr": 1823
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"note": "Add reference functions for `LibMath` and `LibFillResults`",
|
||||||
|
"pr": "TODO"
|
||||||
|
}
|
||||||
|
]
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"timestamp": 1563193019,
|
||||||
|
"version": "3.0.2",
|
||||||
|
"changes": [
|
||||||
|
{
|
||||||
|
"note": "Dependencies updated"
|
||||||
|
}
|
||||||
|
]
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"timestamp": 1563047529,
|
||||||
|
"version": "3.0.1",
|
||||||
|
"changes": [
|
||||||
|
{
|
||||||
|
"note": "Dependencies updated"
|
||||||
|
}
|
||||||
|
]
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"version": "3.0.0",
|
||||||
|
"changes": [
|
||||||
|
{
|
||||||
|
"note": "Move `LibTransactionDecoder` to contracts/dev-utils package",
|
||||||
|
"pr": 1848
|
||||||
}
|
}
|
||||||
],
|
],
|
||||||
"timestamp": 1563006338
|
"timestamp": 1563006338
|
||||||
|
@ -1,2 +1,5 @@
|
|||||||
export * from './artifacts';
|
export * from './artifacts';
|
||||||
export * from './wrappers';
|
export * from './wrappers';
|
||||||
|
|
||||||
|
import * as reference_functions from './reference_functions';
|
||||||
|
export import ReferenceFunctions = reference_functions;
|
||||||
|
122
contracts/exchange-libs/src/reference_functions.ts
Normal file
122
contracts/exchange-libs/src/reference_functions.ts
Normal file
@ -0,0 +1,122 @@
|
|||||||
|
import { ReferenceFunctions } from '@0x/contracts-utils';
|
||||||
|
import { LibMathRevertErrors } from '@0x/order-utils';
|
||||||
|
import { FillResults } from '@0x/types';
|
||||||
|
import { BigNumber } from '@0x/utils';
|
||||||
|
|
||||||
|
const {
|
||||||
|
safeAdd,
|
||||||
|
safeSub,
|
||||||
|
safeMul,
|
||||||
|
safeDiv,
|
||||||
|
} = ReferenceFunctions;
|
||||||
|
|
||||||
|
export function isRoundingErrorFloor(
|
||||||
|
numerator: BigNumber,
|
||||||
|
denominator: BigNumber,
|
||||||
|
target: BigNumber,
|
||||||
|
): boolean {
|
||||||
|
if (denominator.eq(0)) {
|
||||||
|
throw new LibMathRevertErrors.DivisionByZeroError();
|
||||||
|
}
|
||||||
|
if (numerator.eq(0) || target.eq(0)) {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
const remainder = numerator.multipliedBy(target).mod(denominator);
|
||||||
|
return safeMul(new BigNumber(1000), remainder).gte(safeMul(numerator, target));
|
||||||
|
}
|
||||||
|
|
||||||
|
export function isRoundingErrorCeil(
|
||||||
|
numerator: BigNumber,
|
||||||
|
denominator: BigNumber,
|
||||||
|
target: BigNumber,
|
||||||
|
): boolean {
|
||||||
|
if (denominator.eq(0)) {
|
||||||
|
throw new LibMathRevertErrors.DivisionByZeroError();
|
||||||
|
}
|
||||||
|
if (numerator.eq(0) || target.eq(0)) {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
let remainder = numerator.multipliedBy(target).mod(denominator);
|
||||||
|
remainder = safeSub(denominator, remainder).mod(denominator);
|
||||||
|
return safeMul(new BigNumber(1000), remainder).gte(safeMul(numerator, target));
|
||||||
|
}
|
||||||
|
|
||||||
|
export function safeGetPartialAmountFloor(
|
||||||
|
numerator: BigNumber,
|
||||||
|
denominator: BigNumber,
|
||||||
|
target: BigNumber,
|
||||||
|
): BigNumber {
|
||||||
|
if (denominator.eq(0)) {
|
||||||
|
throw new LibMathRevertErrors.DivisionByZeroError();
|
||||||
|
}
|
||||||
|
if (isRoundingErrorFloor(numerator, denominator, target)) {
|
||||||
|
throw new LibMathRevertErrors.RoundingError(numerator, denominator, target);
|
||||||
|
}
|
||||||
|
return safeDiv(
|
||||||
|
safeMul(numerator, target),
|
||||||
|
denominator,
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
export function safeGetPartialAmountCeil(
|
||||||
|
numerator: BigNumber,
|
||||||
|
denominator: BigNumber,
|
||||||
|
target: BigNumber,
|
||||||
|
): BigNumber {
|
||||||
|
if (denominator.eq(0)) {
|
||||||
|
throw new LibMathRevertErrors.DivisionByZeroError();
|
||||||
|
}
|
||||||
|
if (isRoundingErrorCeil(numerator, denominator, target)) {
|
||||||
|
throw new LibMathRevertErrors.RoundingError(numerator, denominator, target);
|
||||||
|
}
|
||||||
|
return safeDiv(
|
||||||
|
safeAdd(
|
||||||
|
safeMul(numerator, target),
|
||||||
|
safeSub(denominator, new BigNumber(1)),
|
||||||
|
),
|
||||||
|
denominator,
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
export function getPartialAmountFloor(
|
||||||
|
numerator: BigNumber,
|
||||||
|
denominator: BigNumber,
|
||||||
|
target: BigNumber,
|
||||||
|
): BigNumber {
|
||||||
|
if (denominator.eq(0)) {
|
||||||
|
throw new LibMathRevertErrors.DivisionByZeroError();
|
||||||
|
}
|
||||||
|
return safeDiv(
|
||||||
|
safeMul(numerator, target),
|
||||||
|
denominator,
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
export function getPartialAmountCeil(
|
||||||
|
numerator: BigNumber,
|
||||||
|
denominator: BigNumber,
|
||||||
|
target: BigNumber,
|
||||||
|
): BigNumber {
|
||||||
|
if (denominator.eq(0)) {
|
||||||
|
throw new LibMathRevertErrors.DivisionByZeroError();
|
||||||
|
}
|
||||||
|
return safeDiv(
|
||||||
|
safeAdd(
|
||||||
|
safeMul(numerator, target),
|
||||||
|
safeSub(denominator, new BigNumber(1)),
|
||||||
|
),
|
||||||
|
denominator,
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
export function addFillResults(
|
||||||
|
a: FillResults,
|
||||||
|
b: FillResults,
|
||||||
|
): FillResults {
|
||||||
|
return {
|
||||||
|
makerAssetFilledAmount: safeAdd(a.makerAssetFilledAmount, b.makerAssetFilledAmount),
|
||||||
|
takerAssetFilledAmount: safeAdd(a.takerAssetFilledAmount, b.takerAssetFilledAmount),
|
||||||
|
makerFeePaid: safeAdd(a.makerFeePaid, b.makerFeePaid),
|
||||||
|
takerFeePaid: safeAdd(a.takerFeePaid, b.takerFeePaid),
|
||||||
|
};
|
||||||
|
}
|
@ -37,6 +37,22 @@
|
|||||||
{
|
{
|
||||||
"note": "Introduce Mocha blockchain extensions",
|
"note": "Introduce Mocha blockchain extensions",
|
||||||
"pr": 2007
|
"pr": 2007
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"note": "Move `*FillResults` types to `@0x/types`",
|
||||||
|
"pr": "TODO"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"note": "Add `log_utils.ts`",
|
||||||
|
"pr": "TODO"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"note": "Add `haxRandom()` to `hex_utils.ts`",
|
||||||
|
"pr": "TODO"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"note": "Add the constants: `MAX_UINT256`, `ADDRESS_LENGTH`",
|
||||||
|
"pr": "TODO"
|
||||||
}
|
}
|
||||||
]
|
]
|
||||||
},
|
},
|
||||||
|
@ -29,7 +29,6 @@ export { TransactionFactory } from './transaction_factory';
|
|||||||
export { testWithReferenceFuncAsync } from './test_with_reference';
|
export { testWithReferenceFuncAsync } from './test_with_reference';
|
||||||
export { hexConcat, hexRandom } from './hex_utils';
|
export { hexConcat, hexRandom } from './hex_utils';
|
||||||
export {
|
export {
|
||||||
BatchMatchedFillResults,
|
|
||||||
BatchMatchOrder,
|
BatchMatchOrder,
|
||||||
ContractName,
|
ContractName,
|
||||||
ERC20BalancesByOwner,
|
ERC20BalancesByOwner,
|
||||||
@ -37,10 +36,8 @@ export {
|
|||||||
ERC1155HoldingsByOwner,
|
ERC1155HoldingsByOwner,
|
||||||
ERC1155NonFungibleHoldingsByOwner,
|
ERC1155NonFungibleHoldingsByOwner,
|
||||||
ERC721TokenIdsByOwner,
|
ERC721TokenIdsByOwner,
|
||||||
FillResults,
|
|
||||||
MarketBuyOrders,
|
MarketBuyOrders,
|
||||||
MarketSellOrders,
|
MarketSellOrders,
|
||||||
MatchedFillResults,
|
|
||||||
OrderInfo,
|
OrderInfo,
|
||||||
OrderStatus,
|
OrderStatus,
|
||||||
Token,
|
Token,
|
||||||
|
@ -143,24 +143,3 @@ export interface MatchOrder {
|
|||||||
leftSignature: string;
|
leftSignature: string;
|
||||||
rightSignature: string;
|
rightSignature: string;
|
||||||
}
|
}
|
||||||
|
|
||||||
export interface FillResults {
|
|
||||||
makerAssetFilledAmount: BigNumber;
|
|
||||||
takerAssetFilledAmount: BigNumber;
|
|
||||||
makerFeePaid: BigNumber;
|
|
||||||
takerFeePaid: BigNumber;
|
|
||||||
}
|
|
||||||
|
|
||||||
export interface MatchedFillResults {
|
|
||||||
left: FillResults;
|
|
||||||
right: FillResults;
|
|
||||||
profitInLeftMakerAsset: BigNumber;
|
|
||||||
profitInRightMakerAsset: BigNumber;
|
|
||||||
}
|
|
||||||
|
|
||||||
export interface BatchMatchedFillResults {
|
|
||||||
left: FillResults[];
|
|
||||||
right: FillResults[];
|
|
||||||
profitInLeftMakerAsset: BigNumber;
|
|
||||||
profitInRightMakerAsset: BigNumber;
|
|
||||||
}
|
|
||||||
|
@ -33,6 +33,10 @@
|
|||||||
{
|
{
|
||||||
"note": "Updated Ownable to revert when the owner attempts to transfer ownership to the zero address",
|
"note": "Updated Ownable to revert when the owner attempts to transfer ownership to the zero address",
|
||||||
"pr": 2019
|
"pr": 2019
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"note": "Add reference functions for `SafeMath` functions.",
|
||||||
|
"pr": "2031"
|
||||||
}
|
}
|
||||||
]
|
]
|
||||||
},
|
},
|
||||||
|
@ -1,2 +1,5 @@
|
|||||||
export * from './artifacts';
|
export * from './artifacts';
|
||||||
export * from './wrappers';
|
export * from './wrappers';
|
||||||
|
|
||||||
|
import * as reference_functions from './reference_functions';
|
||||||
|
export import ReferenceFunctions = reference_functions;
|
||||||
|
44
contracts/utils/src/reference_functions.ts
Normal file
44
contracts/utils/src/reference_functions.ts
Normal file
@ -0,0 +1,44 @@
|
|||||||
|
import { AnyRevertError, BigNumber, SafeMathRevertErrors } from '@0x/utils';
|
||||||
|
|
||||||
|
const MAX_UINT256 = new BigNumber(2).pow(256).minus(1);
|
||||||
|
|
||||||
|
export function safeAdd(a: BigNumber, b: BigNumber): BigNumber {
|
||||||
|
const r = a.plus(b);
|
||||||
|
if (r.isGreaterThan(MAX_UINT256)) {
|
||||||
|
throw new SafeMathRevertErrors.SafeMathError(
|
||||||
|
SafeMathRevertErrors.SafeMathErrorCodes.Uint256AdditionOverflow,
|
||||||
|
a,
|
||||||
|
b,
|
||||||
|
);
|
||||||
|
}
|
||||||
|
return r;
|
||||||
|
}
|
||||||
|
|
||||||
|
export function safeSub(a: BigNumber, b: BigNumber): BigNumber {
|
||||||
|
const r = a.minus(b);
|
||||||
|
if (r.isLessThan(0)) {
|
||||||
|
throw new SafeMathRevertErrors.SafeMathError(
|
||||||
|
SafeMathRevertErrors.SafeMathErrorCodes.Uint256SubtractionUnderflow,
|
||||||
|
a,
|
||||||
|
b,
|
||||||
|
);
|
||||||
|
}
|
||||||
|
return r;
|
||||||
|
}
|
||||||
|
|
||||||
|
export function safeMul(a: BigNumber, b: BigNumber): BigNumber {
|
||||||
|
const r = a.times(b);
|
||||||
|
if (r.isGreaterThan(MAX_UINT256)) {
|
||||||
|
// Solidity implementation does not throw a reason.
|
||||||
|
throw new AnyRevertError();
|
||||||
|
}
|
||||||
|
return r;
|
||||||
|
}
|
||||||
|
|
||||||
|
export function safeDiv(a: BigNumber, b: BigNumber): BigNumber {
|
||||||
|
if (b.isEqualTo(0)) {
|
||||||
|
// Solidity implementation does not throw a reason.
|
||||||
|
throw new AnyRevertError();
|
||||||
|
}
|
||||||
|
return a.dividedToIntegerBy(b);
|
||||||
|
}
|
@ -5,6 +5,10 @@
|
|||||||
{
|
{
|
||||||
"note": "Add `OrderStatus` type",
|
"note": "Add `OrderStatus` type",
|
||||||
"pr": 1761
|
"pr": 1761
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"note": "Add `FillResults`, `MatchedFillResults`, `BatchMatchedFillResults` types",
|
||||||
|
"pr": "TODO"
|
||||||
}
|
}
|
||||||
]
|
]
|
||||||
},
|
},
|
||||||
|
@ -810,3 +810,24 @@ export enum OrderTransferResults {
|
|||||||
MakerFeeAssetDataFailed,
|
MakerFeeAssetDataFailed,
|
||||||
TransfersSuccessful,
|
TransfersSuccessful,
|
||||||
}
|
}
|
||||||
|
|
||||||
|
export interface FillResults {
|
||||||
|
makerAssetFilledAmount: BigNumber;
|
||||||
|
takerAssetFilledAmount: BigNumber;
|
||||||
|
makerFeePaid: BigNumber;
|
||||||
|
takerFeePaid: BigNumber;
|
||||||
|
}
|
||||||
|
|
||||||
|
export interface MatchedFillResults {
|
||||||
|
left: FillResults;
|
||||||
|
right: FillResults;
|
||||||
|
profitInLeftMakerAsset: BigNumber;
|
||||||
|
profitInRightMakerAsset: BigNumber;
|
||||||
|
}
|
||||||
|
|
||||||
|
export interface BatchMatchedFillResults {
|
||||||
|
left: FillResults[];
|
||||||
|
right: FillResults[];
|
||||||
|
profitInLeftMakerAsset: BigNumber;
|
||||||
|
profitInRightMakerAsset: BigNumber;
|
||||||
|
}
|
||||||
|
Loading…
x
Reference in New Issue
Block a user