@artblocks/contracts 1.0.4 → 1.1.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (120) hide show
  1. package/README.md +2 -2
  2. package/artifacts/contracts/AdminACLV1.sol/AdminACLV1.json +2 -2
  3. package/artifacts/contracts/DependencyRegistryV0.sol/DependencyRegistryV0.json +97 -10
  4. package/artifacts/contracts/GenArt721CoreV3.sol/GenArt721CoreV3.json +4 -4
  5. package/artifacts/contracts/engine/V3/GenArt721CoreV3_Engine.sol/GenArt721CoreV3_Engine.json +4 -9
  6. package/artifacts/contracts/engine/V3/GenArt721CoreV3_Engine_Flex.sol/GenArt721CoreV3_Engine_Flex.json +4 -9
  7. package/artifacts/contracts/engine/V3/forks/GenArt721CoreV3_Engine_Flex_PROOF.sol/GenArt721CoreV3_Engine_Flex_PROOF.json +4 -9
  8. package/artifacts/contracts/engine/V3/forks/PROHIBITION/GenArt721CoreV3_Engine_Flex_PROHIBITION.sol/GenArt721CoreV3_Engine_Flex_PROHIBITION.json +4 -9
  9. package/artifacts/contracts/engine-registry/CoreRegistryV1.sol/CoreRegistryV1.json +12 -12
  10. package/artifacts/contracts/explorations/GenArt721CoreV3_Explorations.sol/GenArt721CoreV3_Explorations.json +4 -4
  11. package/artifacts/contracts/interfaces/v0.8.x/ICoreRegistryV1.sol/ICoreRegistryV1.json +6 -6
  12. package/artifacts/contracts/interfaces/v0.8.x/IDependencyRegistryV0.sol/IDependencyRegistryV0.json +19 -0
  13. package/artifacts/contracts/interfaces/v0.8.x/IMinterFilterV1.sol/IMinterFilterV1.json +22 -22
  14. package/artifacts/contracts/interfaces/v0.8.x/ISharedMinterDAExpSettlementV0.sol/ISharedMinterDAExpSettlementV0.json +8 -101
  15. package/artifacts/contracts/interfaces/v0.8.x/ISharedMinterDAExpV0.sol/ISharedMinterDAExpV0.json +1 -57
  16. package/artifacts/contracts/interfaces/v0.8.x/ISharedMinterDALinV0.sol/ISharedMinterDALinV0.json +1 -57
  17. package/artifacts/contracts/interfaces/v0.8.x/ISharedMinterDAV0.sol/ISharedMinterDAV0.json +2 -21
  18. package/artifacts/contracts/interfaces/v0.8.x/ISharedMinterHolderERC20V0.sol/ISharedMinterHolderERC20V0.json +158 -0
  19. package/artifacts/contracts/interfaces/v0.8.x/ISharedMinterHolderV0.sol/ISharedMinterHolderV0.json +15 -90
  20. package/artifacts/contracts/interfaces/v0.8.x/ISharedMinterMerkleV0.sol/ISharedMinterMerkleV0.json +10 -36
  21. package/artifacts/contracts/interfaces/v0.8.x/ISharedMinterSEAV0.sol/ISharedMinterSEAV0.json +4 -236
  22. package/artifacts/contracts/interfaces/v0.8.x/ISharedMinterSimplePurchaseV0.sol/ISharedMinterSimplePurchaseV0.json +5 -5
  23. package/artifacts/contracts/interfaces/v0.8.x/ISharedMinterV0.sol/ISharedMinterV0.json +7 -423
  24. package/artifacts/contracts/interfaces/v0.8.x/ISharedRandomizerV0.sol/ISharedRandomizerV0.json +17 -17
  25. package/artifacts/contracts/libs/v0.8.x/ABHelpers.sol/ABHelpers.json +2 -2
  26. package/artifacts/contracts/libs/v0.8.x/AuthLib.sol/AuthLib.json +2 -2
  27. package/artifacts/contracts/libs/v0.8.x/Bytes32Strings.sol/Bytes32Strings.json +2 -2
  28. package/artifacts/contracts/libs/v0.8.x/minter-libs/DAExpLib.sol/DAExpLib.json +60 -3
  29. package/artifacts/contracts/libs/v0.8.x/minter-libs/DALib.sol/DALib.json +30 -0
  30. package/artifacts/contracts/libs/v0.8.x/minter-libs/DALinLib.sol/DALinLib.json +60 -3
  31. package/artifacts/contracts/libs/v0.8.x/minter-libs/GenericMinterEventsLib.sol/GenericMinterEventsLib.json +346 -0
  32. package/artifacts/contracts/libs/v0.8.x/minter-libs/MaxInvocationsLib.sol/MaxInvocationsLib.json +29 -3
  33. package/artifacts/contracts/libs/v0.8.x/minter-libs/MerkleLib.sol/MerkleLib.json +30 -3
  34. package/artifacts/contracts/libs/v0.8.x/minter-libs/PolyptychLib.sol/PolyptychLib.json +2 -2
  35. package/artifacts/contracts/libs/v0.8.x/minter-libs/SEALib.sol/SEALib.json +254 -3
  36. package/artifacts/contracts/libs/v0.8.x/minter-libs/SetPriceLib.sol/SetPriceLib.json +48 -3
  37. package/artifacts/contracts/libs/v0.8.x/minter-libs/SettlementExpLib.sol/SettlementExpLib.json +41 -3
  38. package/artifacts/contracts/libs/v0.8.x/minter-libs/SplitFundsLib.sol/SplitFundsLib.json +35 -3
  39. package/artifacts/contracts/libs/v0.8.x/minter-libs/TokenHolderLib.sol/TokenHolderLib.json +79 -3
  40. package/artifacts/contracts/minter-suite/MinterFilter/MinterFilterV1.sol/MinterFilterV1.json +2 -2
  41. package/artifacts/contracts/minter-suite/MinterFilter/MinterFilterV2.sol/MinterFilterV2.json +41 -41
  42. package/artifacts/contracts/minter-suite/Minters/MinterDAExpHolderV5.sol/MinterDAExpHolderV5.json +66 -632
  43. package/artifacts/contracts/minter-suite/Minters/MinterDAExpSettlementV2.sol/MinterDAExpSettlementV2.json +2 -20
  44. package/artifacts/contracts/minter-suite/Minters/MinterDAExpSettlementV3.sol/MinterDAExpSettlementV3.json +67 -594
  45. package/artifacts/contracts/minter-suite/Minters/MinterDAExpV5.sol/MinterDAExpV5.json +33 -524
  46. package/artifacts/contracts/minter-suite/Minters/MinterDALinHolderV5.sol/MinterDALinHolderV5.json +66 -632
  47. package/artifacts/contracts/minter-suite/Minters/MinterDALinV5.sol/MinterDALinV5.json +33 -524
  48. package/artifacts/contracts/minter-suite/Minters/MinterSEAV1.sol/MinterSEAV1.json +51 -717
  49. package/artifacts/contracts/minter-suite/Minters/MinterSetPriceERC20V5.sol/MinterSetPriceERC20V5.json +58 -454
  50. package/artifacts/contracts/minter-suite/Minters/MinterSetPriceHolderV5.sol/MinterSetPriceHolderV5.json +61 -552
  51. package/artifacts/contracts/minter-suite/Minters/MinterSetPriceMerkleV5.sol/MinterSetPriceMerkleV5.json +55 -497
  52. package/artifacts/contracts/minter-suite/Minters/MinterSetPricePolyptychERC20V5.sol/MinterSetPricePolyptychERC20V5.json +110 -571
  53. package/artifacts/contracts/minter-suite/Minters/MinterSetPricePolyptychV5.sol/MinterSetPricePolyptychV5.json +69 -560
  54. package/artifacts/contracts/minter-suite/Minters/MinterSetPriceV5.sol/MinterSetPriceV5.json +28 -444
  55. package/artifacts/contracts/mock/DummySharedMinter.sol/DummySharedMinter.json +2 -2
  56. package/artifacts/contracts/mock/GenArt721CoreV3_Engine_IncorrectCoreType.sol/GenArt721CoreV3_Engine_IncorrectCoreType.json +4 -9
  57. package/artifacts/contracts/mock/OriginRegisterMock.sol/OriginRegisterMock.json +2 -2
  58. package/artifacts/contracts/mock/ReentrancyHolderMockShared.sol/ReentrancyHolderMockShared.json +136 -0
  59. package/artifacts/contracts/mock/ReentrancyMerkleMockShared.sol/ReentrancyMerkleMockShared.json +105 -0
  60. package/artifacts/contracts/mock/ReentrancyMockShared.sol/ReentrancyMockShared.json +100 -0
  61. package/artifacts/contracts/mock/ReentrancySEAMockShared.sol/ReentrancySEAAutoBidderMockShared.json +69 -0
  62. package/artifacts/contracts/randomizer/shared/SharedRandomizerV0.sol/SharedRandomizerV0.json +19 -19
  63. package/contracts/DependencyRegistryV0.sol +84 -16
  64. package/contracts/archive/readme.md +16 -0
  65. package/contracts/engine/README.md +21 -0
  66. package/contracts/engine/V3/GenArt721CoreV3_Engine.sol +4 -10
  67. package/contracts/engine/V3/GenArt721CoreV3_Engine_Flex.sol +4 -10
  68. package/contracts/engine/V3/forks/GenArt721CoreV3_Engine_Flex_PROOF.sol +4 -10
  69. package/contracts/engine/V3/forks/PROHIBITION/GenArt721CoreV3_Engine_Flex_PROHIBITION.sol +4 -10
  70. package/contracts/engine-registry/CoreRegistryV1.sol +58 -65
  71. package/contracts/interfaces/v0.8.x/ICoreRegistryV1.sol +6 -8
  72. package/contracts/interfaces/v0.8.x/IDependencyRegistryV0.sol +3 -0
  73. package/contracts/interfaces/v0.8.x/IMinterFilterV1.sol +25 -25
  74. package/contracts/interfaces/v0.8.x/ISharedMinterDAExpSettlementV0.sol +11 -20
  75. package/contracts/interfaces/v0.8.x/ISharedMinterDAExpV0.sol +1 -14
  76. package/contracts/interfaces/v0.8.x/ISharedMinterDALinV0.sol +1 -15
  77. package/contracts/interfaces/v0.8.x/ISharedMinterDAV0.sol +2 -8
  78. package/contracts/interfaces/v0.8.x/ISharedMinterHolderERC20V0.sol +47 -0
  79. package/contracts/interfaces/v0.8.x/ISharedMinterHolderV0.sol +15 -43
  80. package/contracts/interfaces/v0.8.x/ISharedMinterMerkleV0.sol +10 -20
  81. package/contracts/interfaces/v0.8.x/ISharedMinterSEAV0.sol +4 -67
  82. package/contracts/interfaces/v0.8.x/ISharedMinterSimplePurchaseV0.sol +5 -5
  83. package/contracts/interfaces/v0.8.x/ISharedMinterV0.sol +7 -155
  84. package/contracts/interfaces/v0.8.x/ISharedRandomizerV0.sol +37 -37
  85. package/contracts/libs/v0.8.x/ABHelpers.sol +14 -14
  86. package/contracts/libs/v0.8.x/AuthLib.sol +101 -102
  87. package/contracts/libs/v0.8.x/Bytes32Strings.sol +5 -5
  88. package/contracts/libs/v0.8.x/minter-libs/DAExpLib.sol +163 -38
  89. package/contracts/libs/v0.8.x/minter-libs/DALib.sol +26 -0
  90. package/contracts/libs/v0.8.x/minter-libs/DALinLib.sol +144 -37
  91. package/contracts/libs/v0.8.x/minter-libs/GenericMinterEventsLib.sol +171 -0
  92. package/contracts/libs/v0.8.x/minter-libs/MaxInvocationsLib.sol +250 -110
  93. package/contracts/libs/v0.8.x/minter-libs/MerkleLib.sol +257 -48
  94. package/contracts/libs/v0.8.x/minter-libs/PolyptychLib.sol +138 -58
  95. package/contracts/libs/v0.8.x/minter-libs/SEALib.sol +778 -103
  96. package/contracts/libs/v0.8.x/minter-libs/SetPriceLib.sol +135 -13
  97. package/contracts/libs/v0.8.x/minter-libs/SettlementExpLib.sol +567 -187
  98. package/contracts/libs/v0.8.x/minter-libs/SplitFundsLib.sol +480 -322
  99. package/contracts/libs/v0.8.x/minter-libs/TokenHolderLib.sol +214 -76
  100. package/contracts/minter-suite/MinterFilter/MinterFilterV2.sol +347 -304
  101. package/contracts/minter-suite/Minters/MinterDAExpHolderV5.sol +391 -491
  102. package/contracts/minter-suite/Minters/MinterDAExpSettlementV2.sol +1 -54
  103. package/contracts/minter-suite/Minters/MinterDAExpSettlementV3.sol +388 -628
  104. package/contracts/minter-suite/Minters/MinterDAExpV5.sol +212 -273
  105. package/contracts/minter-suite/Minters/MinterDALinHolderV5.sol +393 -488
  106. package/contracts/minter-suite/Minters/MinterDALinV5.sol +220 -277
  107. package/contracts/minter-suite/Minters/MinterSEAV1.sol +327 -664
  108. package/contracts/minter-suite/Minters/MinterSetPriceERC20V5.sol +278 -303
  109. package/contracts/minter-suite/Minters/MinterSetPriceHolderV5.sol +355 -446
  110. package/contracts/minter-suite/Minters/MinterSetPriceMerkleV5.sol +328 -416
  111. package/contracts/minter-suite/Minters/MinterSetPricePolyptychERC20V5.sol +538 -622
  112. package/contracts/minter-suite/Minters/MinterSetPricePolyptychV5.sol +429 -553
  113. package/contracts/minter-suite/Minters/MinterSetPriceV5.sol +180 -227
  114. package/contracts/mock/GenArt721CoreV3_Engine_IncorrectCoreType.sol +3 -10
  115. package/contracts/mock/ReentrancyHolderMockShared.sol +59 -0
  116. package/contracts/mock/ReentrancyMerkleMockShared.sol +58 -0
  117. package/contracts/mock/ReentrancyMockShared.sol +48 -0
  118. package/contracts/mock/ReentrancySEAMockShared.sol +40 -0
  119. package/contracts/randomizer/shared/SharedRandomizerV0.sol +78 -70
  120. package/package.json +39 -33
@@ -9,13 +9,13 @@ pragma solidity ^0.8.0;
9
9
  */
10
10
  library Bytes32Strings {
11
11
  /**
12
- * @dev Intended to convert a `bytes32`-encoded string literal to `string`.
12
+ * @notice Intended to convert a `bytes32`-encoded string literal to `string`.
13
13
  * Trims zero padding to arrive at original string literal.
14
14
  */
15
15
  function toString(
16
16
  bytes32 source
17
17
  ) internal pure returns (string memory result) {
18
- uint8 length = 0;
18
+ uint8 length;
19
19
  while (source[length] != 0 && length < 32) {
20
20
  length++;
21
21
  }
@@ -33,7 +33,7 @@ library Bytes32Strings {
33
33
  }
34
34
 
35
35
  /**
36
- * @dev Intended to check if a `bytes32`-encoded string contains a given
36
+ * @notice Intended to check if a `bytes32`-encoded string contains a given
37
37
  * character with UTF-8 character code `utf8CharCode exactly `targetQty`
38
38
  * times. Does not support searching for multi-byte characters, only
39
39
  * characters with UTF-8 character codes < 0x80.
@@ -43,9 +43,9 @@ library Bytes32Strings {
43
43
  uint8 utf8CharCode,
44
44
  uint8 targetQty
45
45
  ) internal pure returns (bool) {
46
- uint8 _occurrences = 0;
46
+ uint8 _occurrences;
47
47
  uint8 i;
48
- for (i = 0; i < 32; ) {
48
+ for (i; i < 32; ) {
49
49
  uint8 _charCode = uint8(source[i]);
50
50
  // if not a null byte, or a multi-byte UTF-8 character, check match
51
51
  if (_charCode != 0 && _charCode < 0x80) {
@@ -3,6 +3,8 @@
3
3
 
4
4
  pragma solidity ^0.8.0;
5
5
 
6
+ import {DALib} from "./DALib.sol";
7
+
6
8
  /**
7
9
  * @title Art Blocks Dutch Auction (exponential price curve) Library
8
10
  * @notice This library is designed to implement logic and checks for Art
@@ -12,6 +14,42 @@ pragma solidity ^0.8.0;
12
14
  */
13
15
 
14
16
  library DAExpLib {
17
+ /**
18
+ * @notice Auction details set for project `projectId` on core contract
19
+ * `coreContract`.
20
+ * @param projectId Project Id for which auction details were set
21
+ * @param coreContract Core contract address for which auction details were
22
+ * set
23
+ * @param auctionTimestampStart Timestamp when auction will start
24
+ * @param priceDecayHalfLifeSeconds Half life of price decay, in seconds
25
+ * @param startPrice Start price of auction
26
+ * @param basePrice Base price of auction (end price)
27
+ */
28
+ event SetAuctionDetailsExp(
29
+ uint256 indexed projectId,
30
+ address indexed coreContract,
31
+ uint40 auctionTimestampStart,
32
+ uint40 priceDecayHalfLifeSeconds,
33
+ uint256 startPrice,
34
+ uint256 basePrice
35
+ );
36
+ /// Minimum allowed price decay half life seconds updated.
37
+
38
+ /**
39
+ * @notice Minimum allowed price decay half life on the minter updated to
40
+ * `minimumPriceDecayHalfLifeSeconds`.
41
+ * @param minimumPriceDecayHalfLifeSeconds minimum price decay half life
42
+ * for new auctions, in seconds
43
+ */
44
+ event AuctionMinHalfLifeSecondsUpdated(
45
+ uint256 minimumPriceDecayHalfLifeSeconds
46
+ );
47
+
48
+ // position of DA Exp Lib storage, using a diamond storage pattern
49
+ // for this library
50
+ bytes32 constant DAE_EXP_LIB_STORAGE_POSITION =
51
+ keccak256("daexplib.storage");
52
+
15
53
  struct DAProjectConfig {
16
54
  // @dev max uint40 ~= 1.1e12 sec ~= 34 thousand years
17
55
  uint40 timestampStart;
@@ -22,6 +60,11 @@ library DAExpLib {
22
60
  uint88 basePrice;
23
61
  }
24
62
 
63
+ // Diamond storage pattern is used in this library
64
+ struct DAExpLibStorage {
65
+ mapping(address coreContract => mapping(uint256 projectId => DAProjectConfig)) DAProjectConfigs_;
66
+ }
67
+
25
68
  /**
26
69
  * @notice Sets auction details for an exponential-price auction type.
27
70
  * @dev The function sets the auction start timestamp, price decay
@@ -31,46 +74,80 @@ library DAExpLib {
31
74
  * minter should check that _priceDecayHalfLifeSeconds is greater than the
32
75
  * minter's minimum allowable value for price decay half-life (if the
33
76
  * minter chooses to include that guard-rail).
34
- * @param _DAProjectConfig The storage reference to the DAProjectConfig
35
- * struct.
36
- * @param _auctionTimestampStart The timestamp when the auction will start.
37
- * @param _priceDecayHalfLifeSeconds The half-life time for price decay in
77
+ * @param projectId The project Id to set auction details for.
78
+ * @param coreContract The core contract address to set auction details.
79
+ * @param auctionTimestampStart The timestamp when the auction will start.
80
+ * @param priceDecayHalfLifeSeconds The half-life time for price decay in
38
81
  * seconds.
39
- * @param _startPrice The starting price of the auction.
40
- * @param _basePrice The base price of the auction.
41
- * @param _allowReconfigureAfterStart Bool indicating whether the auction
82
+ * @param startPrice The starting price of the auction.
83
+ * @param basePrice The base price of the auction.
84
+ * @param allowReconfigureAfterStart Bool indicating whether the auction
42
85
  * can be reconfigured after it has started. This is sometimes useful for
43
86
  * minter implementations that want to allow an artist to reconfigure the
44
87
  * auction after it has reached minter-local max invocations, for example.
45
88
  */
46
89
  function setAuctionDetailsExp(
47
- DAProjectConfig storage _DAProjectConfig,
48
- uint40 _auctionTimestampStart,
49
- uint40 _priceDecayHalfLifeSeconds,
50
- uint88 _startPrice,
51
- uint88 _basePrice,
52
- bool _allowReconfigureAfterStart
90
+ uint256 projectId,
91
+ address coreContract,
92
+ uint40 auctionTimestampStart,
93
+ uint40 priceDecayHalfLifeSeconds,
94
+ uint88 startPrice,
95
+ uint88 basePrice,
96
+ bool allowReconfigureAfterStart
53
97
  ) internal {
98
+ DAProjectConfig storage DAProjectConfig_ = getDAProjectConfig({
99
+ projectId: projectId,
100
+ coreContract: coreContract
101
+ });
54
102
  require(
55
- _DAProjectConfig.timestampStart == 0 || // uninitialized
56
- block.timestamp < _DAProjectConfig.timestampStart || // auction not yet started
57
- _allowReconfigureAfterStart, // specifically allowing reconfiguration after start
103
+ DAProjectConfig_.timestampStart == 0 || // uninitialized
104
+ block.timestamp < DAProjectConfig_.timestampStart || // auction not yet started
105
+ allowReconfigureAfterStart, // specifically allowing reconfiguration after start
58
106
  "No modifications mid-auction"
59
107
  );
60
108
  require(
61
- block.timestamp < _auctionTimestampStart,
109
+ block.timestamp < auctionTimestampStart,
62
110
  "Only future auctions"
63
111
  );
64
112
  require(
65
- _startPrice > _basePrice,
113
+ startPrice > basePrice,
66
114
  "Auction start price must be greater than auction end price"
67
115
  );
68
116
 
69
117
  // EFFECTS
70
- _DAProjectConfig.timestampStart = _auctionTimestampStart;
71
- _DAProjectConfig.priceDecayHalfLifeSeconds = _priceDecayHalfLifeSeconds;
72
- _DAProjectConfig.startPrice = _startPrice;
73
- _DAProjectConfig.basePrice = _basePrice;
118
+ DAProjectConfig_.timestampStart = auctionTimestampStart;
119
+ DAProjectConfig_.priceDecayHalfLifeSeconds = priceDecayHalfLifeSeconds;
120
+ DAProjectConfig_.startPrice = startPrice;
121
+ DAProjectConfig_.basePrice = basePrice;
122
+
123
+ emit SetAuctionDetailsExp({
124
+ projectId: projectId,
125
+ coreContract: coreContract,
126
+ auctionTimestampStart: auctionTimestampStart,
127
+ priceDecayHalfLifeSeconds: priceDecayHalfLifeSeconds,
128
+ startPrice: startPrice,
129
+ basePrice: basePrice
130
+ });
131
+ }
132
+
133
+ function resetAuctionDetails(
134
+ uint256 projectId,
135
+ address coreContract
136
+ ) internal {
137
+ DAProjectConfig storage DAProjectConfig_ = getDAProjectConfig({
138
+ projectId: projectId,
139
+ coreContract: coreContract
140
+ });
141
+
142
+ DAProjectConfig_.timestampStart = 0;
143
+ DAProjectConfig_.priceDecayHalfLifeSeconds = 0;
144
+ DAProjectConfig_.startPrice = 0;
145
+ DAProjectConfig_.basePrice = 0;
146
+
147
+ emit DALib.ResetAuctionDetails({
148
+ projectId: projectId,
149
+ coreContract: coreContract
150
+ });
74
151
  }
75
152
 
76
153
  /**
@@ -79,30 +156,36 @@ library DAExpLib {
79
156
  * This function reverts if auction has not yet started, or if auction is
80
157
  * unconfigured, which is relied upon by certain minter implications for
81
158
  * security.
159
+ * @param projectId Project Id to get price for
160
+ * @param coreContract Core contract address to get price for
82
161
  * @return uint256 current price of token in Wei
83
162
  */
84
163
  function getPriceExp(
85
- DAProjectConfig storage _DAProjectConfig
164
+ uint256 projectId,
165
+ address coreContract
86
166
  ) internal view returns (uint256) {
167
+ DAProjectConfig storage DAProjectConfig_ = getDAProjectConfig({
168
+ projectId: projectId,
169
+ coreContract: coreContract
170
+ });
87
171
  // move parameters to memory if used more than once
88
- uint256 _timestampStart = _DAProjectConfig.timestampStart;
89
- uint256 _priceDecayHalfLifeSeconds = _DAProjectConfig
172
+ uint256 timestampStart = DAProjectConfig_.timestampStart;
173
+ uint256 priceDecayHalfLifeSeconds = DAProjectConfig_
90
174
  .priceDecayHalfLifeSeconds;
91
- uint256 _basePrice = _DAProjectConfig.basePrice;
92
175
 
93
- require(block.timestamp > _timestampStart, "Auction not yet started");
94
- require(_priceDecayHalfLifeSeconds > 0, "Only configured auctions");
95
- uint256 decayedPrice = _DAProjectConfig.startPrice;
176
+ require(block.timestamp >= timestampStart, "Auction not yet started");
177
+ require(priceDecayHalfLifeSeconds > 0, "Only configured auctions");
178
+ uint256 decayedPrice = DAProjectConfig_.startPrice;
96
179
  uint256 elapsedTimeSeconds;
97
180
  unchecked {
98
181
  // already checked that block.timestamp > _timestampStart above
99
- elapsedTimeSeconds = block.timestamp - _timestampStart;
182
+ elapsedTimeSeconds = block.timestamp - timestampStart;
100
183
  }
101
184
  // Divide by two (via bit-shifting) for the number of entirely completed
102
185
  // half-lives that have elapsed since auction start time.
103
186
  unchecked {
104
- // already required _priceDecayHalfLifeSeconds > 0
105
- decayedPrice >>= elapsedTimeSeconds / _priceDecayHalfLifeSeconds;
187
+ // already required priceDecayHalfLifeSeconds > 0
188
+ decayedPrice >>= elapsedTimeSeconds / priceDecayHalfLifeSeconds;
106
189
  }
107
190
  // Perform a linear interpolation between partial half-life points, to
108
191
  // approximate the current place on a perfect exponential decay curve.
@@ -111,15 +194,57 @@ library DAExpLib {
111
194
  // so no underflow is possible when the subtraction assignment
112
195
  // operator is used on decayedPrice.
113
196
  decayedPrice -=
114
- (decayedPrice *
115
- (elapsedTimeSeconds % _priceDecayHalfLifeSeconds)) /
116
- _priceDecayHalfLifeSeconds /
117
- 2;
197
+ ((decayedPrice *
198
+ (elapsedTimeSeconds % priceDecayHalfLifeSeconds)) /
199
+ priceDecayHalfLifeSeconds) >>
200
+ 1; // divide by 2 via bitshift 1
118
201
  }
119
- if (decayedPrice < _basePrice) {
202
+ uint256 basePrice = DAProjectConfig_.basePrice;
203
+ if (decayedPrice < basePrice) {
120
204
  // Price may not decay below stay `basePrice`.
121
- return _basePrice;
205
+ return basePrice;
122
206
  }
123
207
  return decayedPrice;
124
208
  }
209
+
210
+ /**
211
+ * Gets auction base price for project `projectId` on core contract
212
+ * `coreContract`.
213
+ * @param projectId Project Id to get price for
214
+ * @param coreContract Core contract address to get price for
215
+ */
216
+ function getAuctionBasePrice(
217
+ uint256 projectId,
218
+ address coreContract
219
+ ) internal view returns (uint256) {
220
+ return
221
+ getDAProjectConfig({
222
+ projectId: projectId,
223
+ coreContract: coreContract
224
+ }).basePrice;
225
+ }
226
+
227
+ /**
228
+ * Loads the DAProjectConfig for a given project and core contract.
229
+ * @param projectId Project Id to get config for
230
+ * @param coreContract Core contract address to get config for
231
+ */
232
+ function getDAProjectConfig(
233
+ uint256 projectId,
234
+ address coreContract
235
+ ) internal view returns (DAProjectConfig storage) {
236
+ return s().DAProjectConfigs_[coreContract][projectId];
237
+ }
238
+
239
+ /**
240
+ * @notice Return the storage struct for reading and writing. This library
241
+ * uses a diamond storage pattern when managing storage.
242
+ * @return storageStruct The DAExpLibStorage struct.
243
+ */
244
+ function s() internal pure returns (DAExpLibStorage storage storageStruct) {
245
+ bytes32 position = DAE_EXP_LIB_STORAGE_POSITION;
246
+ assembly ("memory-safe") {
247
+ storageStruct.slot := position
248
+ }
249
+ }
125
250
  }
@@ -0,0 +1,26 @@
1
+ // SPDX-License-Identifier: LGPL-3.0-only
2
+ // Created By: Art Blocks Inc.
3
+
4
+ pragma solidity ^0.8.0;
5
+
6
+ /**
7
+ * @title Art Blocks Dutch Auction (exponential price curve) Library
8
+ * @notice This library is designed to implement logic and checks for Art
9
+ * Blocks projects using an exponential Dutch auctionprice curve for minting
10
+ * tokens.
11
+ * @author Art Blocks Inc.
12
+ */
13
+
14
+ library DALib {
15
+ /**
16
+ * @notice Auction details cleared for project `projectId` on core contract
17
+ * `coreContract`.
18
+ * @param projectId Project Id for which auction details were cleared
19
+ * @param coreContract Core contract address for which auction details were
20
+ * cleared
21
+ */
22
+ event ResetAuctionDetails(
23
+ uint256 indexed projectId,
24
+ address indexed coreContract
25
+ );
26
+ }
@@ -3,15 +3,52 @@
3
3
 
4
4
  pragma solidity ^0.8.0;
5
5
 
6
+ import {DALib} from "./DALib.sol";
7
+
6
8
  /**
7
9
  * @title Art Blocks Dutch Auction (linear price curve) Library
8
10
  * @notice This library is designed to implement logic and checks for Art
9
- * Blocks projects using an exponential Dutch auctionprice curve for minting
11
+ * Blocks projects using an linear Dutch auctionprice curve for minting
10
12
  * tokens.
11
13
  * @author Art Blocks Inc.
12
14
  */
13
15
 
14
16
  library DALinLib {
17
+ /**
18
+ * @notice Auction details set for project `projectId` on core contract
19
+ * `coreContract`.
20
+ * @param projectId Project Id for which auction details were set
21
+ * @param coreContract Core contract address for which auction details were
22
+ * set
23
+ * @param auctionTimestampStart Timestamp when auction will start
24
+ * @param auctionTimestampEnd Timestamp when auction will end
25
+ * @param startPrice Start price of auction
26
+ * @param basePrice Base price of auction (end price)
27
+ */
28
+ event SetAuctionDetailsLin(
29
+ uint256 indexed projectId,
30
+ address indexed coreContract,
31
+ uint40 auctionTimestampStart,
32
+ uint40 auctionTimestampEnd,
33
+ uint256 startPrice,
34
+ uint256 basePrice
35
+ );
36
+
37
+ /**
38
+ * @notice Minimum allowed auction length updated to
39
+ * `minimumAuctionLengthSeconds` on the minter.
40
+ * @param minimumAuctionLengthSeconds minimum auction length for new
41
+ * auctions, in seconds
42
+ */
43
+ event AuctionMinimumLengthSecondsUpdated(
44
+ uint256 minimumAuctionLengthSeconds
45
+ );
46
+
47
+ // position of DA Lin Lib storage, using a diamond storage pattern
48
+ // for this library
49
+ bytes32 constant DAE_LIN_LIB_STORAGE_POSITION =
50
+ keccak256("dalinlib.storage");
51
+
15
52
  struct DAProjectConfig {
16
53
  // @dev max uint40 ~= 1.1e12 sec ~= 34 thousand years
17
54
  uint40 timestampStart;
@@ -22,6 +59,11 @@ library DALinLib {
22
59
  uint88 basePrice;
23
60
  }
24
61
 
62
+ // Diamond storage pattern is used in this library
63
+ struct DALinLibStorage {
64
+ mapping(address coreContract => mapping(uint256 projectId => DAProjectConfig)) DAProjectConfigs_;
65
+ }
66
+
25
67
  /**
26
68
  * @notice Sets auction details for a linear-price auction type.
27
69
  * @dev The function sets the auction start timestamp, auction end
@@ -31,45 +73,79 @@ library DALinLib {
31
73
  * minter should check that auction length is greater than the minter's
32
74
  * minimum allowable value (if the minter chooses to include that guard-
33
75
  * rail).
34
- * @param _DAProjectConfig The storage reference to the DAProjectConfig
35
- * struct.
36
- * @param _auctionTimestampStart The timestamp when the auction will start.
37
- * @param _auctionTimestampEnd The timestamp when the auction will end.
38
- * @param _startPrice The starting price of the auction.
39
- * @param _basePrice The base price of the auction.
40
- * @param _allowReconfigureAfterStart Bool indicating whether the auction
76
+ * @param projectId The project Id to set auction details for.
77
+ * @param coreContract The core contract address to set auction details.
78
+ * @param auctionTimestampStart The timestamp when the auction will start.
79
+ * @param auctionTimestampEnd The timestamp when the auction will end.
80
+ * @param startPrice The starting price of the auction.
81
+ * @param basePrice The base price of the auction.
82
+ * @param allowReconfigureAfterStart Bool indicating whether the auction
41
83
  * can be reconfigured after it has started. This is sometimes useful for
42
84
  * minter implementations that want to allow an artist to reconfigure the
43
85
  * auction after it has reached minter-local max invocations, for example.
44
86
  */
45
87
  function setAuctionDetailsLin(
46
- DAProjectConfig storage _DAProjectConfig,
47
- uint40 _auctionTimestampStart,
48
- uint40 _auctionTimestampEnd,
49
- uint88 _startPrice,
50
- uint88 _basePrice,
51
- bool _allowReconfigureAfterStart
88
+ uint256 projectId,
89
+ address coreContract,
90
+ uint40 auctionTimestampStart,
91
+ uint40 auctionTimestampEnd,
92
+ uint88 startPrice,
93
+ uint88 basePrice,
94
+ bool allowReconfigureAfterStart
52
95
  ) internal {
96
+ DAProjectConfig storage DAProjectConfig_ = getDAProjectConfig({
97
+ projectId: projectId,
98
+ coreContract: coreContract
99
+ });
53
100
  require(
54
- _DAProjectConfig.timestampStart == 0 || // uninitialized
55
- block.timestamp < _DAProjectConfig.timestampStart || // auction not yet started
56
- _allowReconfigureAfterStart, // specifically allowing reconfiguration after start
101
+ DAProjectConfig_.timestampStart == 0 || // uninitialized
102
+ block.timestamp < DAProjectConfig_.timestampStart || // auction not yet started
103
+ allowReconfigureAfterStart, // specifically allowing reconfiguration after start
57
104
  "No modifications mid-auction"
58
105
  );
59
106
  require(
60
- block.timestamp < _auctionTimestampStart,
107
+ block.timestamp < auctionTimestampStart,
61
108
  "Only future auctions"
62
109
  );
63
110
  require(
64
- _startPrice > _basePrice,
111
+ startPrice > basePrice,
65
112
  "Auction start price must be greater than auction end price"
66
113
  );
67
114
 
68
115
  // EFFECTS
69
- _DAProjectConfig.timestampStart = _auctionTimestampStart;
70
- _DAProjectConfig.timestampEnd = _auctionTimestampEnd;
71
- _DAProjectConfig.startPrice = _startPrice;
72
- _DAProjectConfig.basePrice = _basePrice;
116
+ DAProjectConfig_.timestampStart = auctionTimestampStart;
117
+ DAProjectConfig_.timestampEnd = auctionTimestampEnd;
118
+ DAProjectConfig_.startPrice = startPrice;
119
+ DAProjectConfig_.basePrice = basePrice;
120
+
121
+ emit SetAuctionDetailsLin({
122
+ projectId: projectId,
123
+ coreContract: coreContract,
124
+ auctionTimestampStart: auctionTimestampStart,
125
+ auctionTimestampEnd: auctionTimestampEnd,
126
+ startPrice: startPrice,
127
+ basePrice: basePrice
128
+ });
129
+ }
130
+
131
+ function resetAuctionDetails(
132
+ uint256 projectId,
133
+ address coreContract
134
+ ) internal {
135
+ DAProjectConfig storage DAProjectConfig_ = getDAProjectConfig({
136
+ projectId: projectId,
137
+ coreContract: coreContract
138
+ });
139
+
140
+ DAProjectConfig_.timestampStart = 0;
141
+ DAProjectConfig_.timestampEnd = 0;
142
+ DAProjectConfig_.startPrice = 0;
143
+ DAProjectConfig_.basePrice = 0;
144
+
145
+ emit DALib.ResetAuctionDetails({
146
+ projectId: projectId,
147
+ coreContract: coreContract
148
+ });
73
149
  }
74
150
 
75
151
  /**
@@ -77,33 +153,64 @@ library DALinLib {
77
153
  * DAProjectConfig.
78
154
  * This function reverts if auction has not yet started, or if auction is
79
155
  * unconfigured.
156
+ * @param projectId Project Id to get price for
157
+ * @param coreContract Core contract address to get price for
80
158
  * @return current price of token in Wei
81
159
  */
82
160
  function getPriceLin(
83
- DAProjectConfig storage _DAProjectConfig
161
+ uint256 projectId,
162
+ address coreContract
84
163
  ) internal view returns (uint256) {
164
+ DAProjectConfig storage _DAProjectConfig = getDAProjectConfig({
165
+ projectId: projectId,
166
+ coreContract: coreContract
167
+ });
85
168
  // move parameters to memory if used more than once
86
- uint256 _timestampStart = _DAProjectConfig.timestampStart;
87
- uint256 _timestampEnd = _DAProjectConfig.timestampEnd;
88
- uint256 _startPrice = _DAProjectConfig.startPrice;
89
- uint256 _basePrice = _DAProjectConfig.basePrice;
90
-
91
- require(block.timestamp > _timestampStart, "Auction not yet started");
92
- if (block.timestamp >= _timestampEnd) {
93
- require(_timestampEnd > 0, "Only configured auctions");
94
- return _basePrice;
169
+ uint256 timestampStart = _DAProjectConfig.timestampStart;
170
+ uint256 timestampEnd = _DAProjectConfig.timestampEnd;
171
+ uint256 startPrice = _DAProjectConfig.startPrice;
172
+ uint256 basePrice = _DAProjectConfig.basePrice;
173
+
174
+ require(block.timestamp > timestampStart, "Auction not yet started");
175
+ if (block.timestamp >= timestampEnd) {
176
+ require(timestampEnd > 0, "Only configured auctions");
177
+ return basePrice;
95
178
  }
96
179
  uint256 elapsedTime;
97
180
  uint256 duration;
98
181
  uint256 startToEndDiff;
99
182
  unchecked {
100
183
  // already checked that block.timestamp > _timestampStart
101
- elapsedTime = block.timestamp - _timestampStart;
184
+ elapsedTime = block.timestamp - timestampStart;
102
185
  // _timestampEnd > _timestampStart enforced during assignment
103
- duration = _timestampEnd - _timestampStart;
186
+ duration = timestampEnd - timestampStart;
104
187
  // _startPrice > _basePrice enforced during assignment
105
- startToEndDiff = _startPrice - _basePrice;
188
+ startToEndDiff = startPrice - basePrice;
189
+ }
190
+ return startPrice - ((elapsedTime * startToEndDiff) / duration);
191
+ }
192
+
193
+ /**
194
+ * Loads the DAProjectConfig for a given project and core contract.
195
+ * @param projectId Project Id to get config for
196
+ * @param coreContract Core contract address to get config for
197
+ */
198
+ function getDAProjectConfig(
199
+ uint256 projectId,
200
+ address coreContract
201
+ ) internal view returns (DAProjectConfig storage) {
202
+ return s().DAProjectConfigs_[coreContract][projectId];
203
+ }
204
+
205
+ /**
206
+ * @notice Return the storage struct for reading and writing. This library
207
+ * uses a diamond storage pattern when managing storage.
208
+ * @return storageStruct The DALinLibStorage struct.
209
+ */
210
+ function s() internal pure returns (DALinLibStorage storage storageStruct) {
211
+ bytes32 position = DAE_LIN_LIB_STORAGE_POSITION;
212
+ assembly ("memory-safe") {
213
+ storageStruct.slot := position
106
214
  }
107
- return _startPrice - ((elapsedTime * startToEndDiff) / duration);
108
215
  }
109
216
  }