@btc-vision/btc-runtime 1.0.9 → 1.0.11
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.
- package/package.json +1 -1
- package/runtime/contracts/OP_20.ts +2 -14
- package/runtime/env/BTCEnvironment.ts +54 -146
- package/runtime/env/global.ts +3 -5
- package/runtime/exports/index.ts +0 -20
- package/runtime/index.ts +3 -0
- package/runtime/interfaces/DeployContractResponse.ts +12 -0
- package/runtime/memory/AddressMemoryMap.ts +3 -23
- package/runtime/memory/KeyMerger.ts +3 -22
- package/runtime/memory/MultiAddressMemoryMap.ts +2 -15
- package/runtime/storage/StoredU256.ts +15 -105
package/package.json
CHANGED
|
@@ -36,28 +36,16 @@ export abstract class OP_20 extends OP_NET implements IOP_20 {
|
|
|
36
36
|
|
|
37
37
|
this.allowanceMap = new MultiAddressMemoryMap<Address, Address, MemorySlotData<u256>>(
|
|
38
38
|
Blockchain.nextPointer,
|
|
39
|
-
Blockchain.contractAddress,
|
|
40
39
|
u256.Zero,
|
|
41
40
|
);
|
|
42
41
|
this.balanceOfMap = new AddressMemoryMap<Address, MemorySlotData<u256>>(
|
|
43
42
|
Blockchain.nextPointer,
|
|
44
|
-
Blockchain.contractAddress,
|
|
45
43
|
u256.Zero,
|
|
46
44
|
);
|
|
47
45
|
|
|
48
46
|
const supplyPointer = Blockchain.nextPointer;
|
|
49
|
-
const supply: u256 = Blockchain.getStorageAt(
|
|
50
|
-
|
|
51
|
-
supplyPointer,
|
|
52
|
-
u256.Zero,
|
|
53
|
-
u256.Zero,
|
|
54
|
-
);
|
|
55
|
-
this._totalSupply = new StoredU256(
|
|
56
|
-
Blockchain.contractAddress,
|
|
57
|
-
supplyPointer,
|
|
58
|
-
u256.Zero,
|
|
59
|
-
supply,
|
|
60
|
-
);
|
|
47
|
+
const supply: u256 = Blockchain.getStorageAt(supplyPointer, u256.Zero, u256.Zero);
|
|
48
|
+
this._totalSupply = new StoredU256(supplyPointer, u256.Zero, supply);
|
|
61
49
|
}
|
|
62
50
|
|
|
63
51
|
public _totalSupply: StoredU256;
|
|
@@ -10,8 +10,9 @@ import { MAX_EVENTS, NetEvent } from '../events/NetEvent';
|
|
|
10
10
|
import { Potential } from '../lang/Definitions';
|
|
11
11
|
import { Map } from '../generic/Map';
|
|
12
12
|
import { OP_NET } from '../contracts/OP_NET';
|
|
13
|
-
import {
|
|
14
|
-
import { deploy, deployFromAddress } from './global';
|
|
13
|
+
import { PointerStorage } from '../types';
|
|
14
|
+
import { deploy, deployFromAddress, loadPointer, storePointer } from './global';
|
|
15
|
+
import { DeployContractResponse } from '../interfaces/DeployContractResponse';
|
|
15
16
|
|
|
16
17
|
export * from '../env/global';
|
|
17
18
|
|
|
@@ -19,12 +20,7 @@ export * from '../env/global';
|
|
|
19
20
|
export class BlockchainEnvironment {
|
|
20
21
|
private static readonly runtimeException: string = 'RuntimeException';
|
|
21
22
|
|
|
22
|
-
private storage:
|
|
23
|
-
private initializedStorage: BlockchainStorage = new Map();
|
|
24
|
-
|
|
25
|
-
private externalCalls: Map<Address, Uint8Array[]> = new Map();
|
|
26
|
-
private externalCallsResponse: Map<Address, Uint8Array[]> = new Map();
|
|
27
|
-
|
|
23
|
+
private storage: PointerStorage = new Map();
|
|
28
24
|
private events: NetEvent[] = [];
|
|
29
25
|
|
|
30
26
|
private _callee: PotentialAddress = null;
|
|
@@ -115,14 +111,10 @@ export class BlockchainEnvironment {
|
|
|
115
111
|
}
|
|
116
112
|
|
|
117
113
|
public call(destinationContract: Address, calldata: BytesWriter): BytesReader {
|
|
118
|
-
if (destinationContract === this._callee) {
|
|
114
|
+
/*if (destinationContract === this._callee) {
|
|
119
115
|
throw this.error('Cannot call self');
|
|
120
116
|
}
|
|
121
117
|
|
|
122
|
-
if (!this.externalCalls.has(destinationContract)) {
|
|
123
|
-
this.externalCalls.set(destinationContract, []);
|
|
124
|
-
}
|
|
125
|
-
|
|
126
118
|
const externalCalls = this.externalCalls.get(destinationContract);
|
|
127
119
|
const buffer = calldata.getBuffer();
|
|
128
120
|
externalCalls.push(buffer);
|
|
@@ -135,22 +127,9 @@ export class BlockchainEnvironment {
|
|
|
135
127
|
throw this.error('external call failed');
|
|
136
128
|
}
|
|
137
129
|
|
|
138
|
-
return new BytesReader(response)
|
|
139
|
-
}
|
|
140
|
-
|
|
141
|
-
public getCalls(): Uint8Array {
|
|
142
|
-
const buffer: BytesWriter = new BytesWriter();
|
|
143
|
-
|
|
144
|
-
buffer.writeLimitedAddressBytesMap(this.externalCalls);
|
|
145
|
-
this.externalCalls.clear();
|
|
130
|
+
return new BytesReader(response);*/
|
|
146
131
|
|
|
147
|
-
|
|
148
|
-
}
|
|
149
|
-
|
|
150
|
-
public loadCallsResponse(responses: Uint8Array): void {
|
|
151
|
-
const memoryReader: BytesReader = new BytesReader(responses);
|
|
152
|
-
|
|
153
|
-
this.externalCallsResponse = memoryReader.readMultiBytesAddressMap();
|
|
132
|
+
throw this.error('Not implemented');
|
|
154
133
|
}
|
|
155
134
|
|
|
156
135
|
public addEvent(event: NetEvent): void {
|
|
@@ -192,64 +171,62 @@ export class BlockchainEnvironment {
|
|
|
192
171
|
return new BytesReader(cb as Uint8Array);
|
|
193
172
|
}
|
|
194
173
|
|
|
195
|
-
public deployContractFromExisting(
|
|
174
|
+
public deployContractFromExisting(
|
|
175
|
+
existingAddress: Address,
|
|
176
|
+
salt: u256,
|
|
177
|
+
): DeployContractResponse {
|
|
196
178
|
const writer = new BytesWriter();
|
|
197
|
-
writer.writeU256(hash);
|
|
198
179
|
writer.writeAddress(existingAddress);
|
|
180
|
+
writer.writeU256(salt);
|
|
199
181
|
|
|
200
|
-
const
|
|
182
|
+
const buffer: Uint8Array = writer.getBuffer();
|
|
183
|
+
const cb: Potential<Uint8Array> = deployFromAddress(buffer);
|
|
201
184
|
if (!cb) throw this.error('Failed to deploy contract');
|
|
202
185
|
|
|
203
|
-
|
|
186
|
+
const reader: BytesReader = new BytesReader(cb as Uint8Array);
|
|
187
|
+
const virtualAddress: u256 = reader.readU256();
|
|
188
|
+
const contractAddress: Address = reader.readAddress();
|
|
189
|
+
|
|
190
|
+
return new DeployContractResponse(virtualAddress, contractAddress);
|
|
204
191
|
}
|
|
205
192
|
|
|
206
193
|
public getStorageAt(
|
|
207
|
-
address: Address,
|
|
208
194
|
pointer: u16,
|
|
209
195
|
subPointer: MemorySlotPointer,
|
|
210
196
|
defaultValue: MemorySlotData<u256>,
|
|
211
197
|
): MemorySlotData<u256> {
|
|
212
|
-
this.ensureStorageAtAddress(address);
|
|
213
|
-
|
|
214
198
|
const pointerHash: MemorySlotPointer = encodePointerHash(pointer, subPointer);
|
|
215
|
-
this.ensureStorageAtPointer(
|
|
216
|
-
|
|
217
|
-
const storage: PointerStorage = this.storage.get(address);
|
|
199
|
+
this.ensureStorageAtPointer(pointerHash, defaultValue);
|
|
218
200
|
|
|
219
201
|
// maybe find a better way for this
|
|
220
|
-
const allKeys: u256[] = storage.keys();
|
|
202
|
+
const allKeys: u256[] = this.storage.keys();
|
|
221
203
|
for (let i: i32 = 0; i < allKeys.length; i++) {
|
|
222
204
|
const v: u256 = allKeys[i];
|
|
223
205
|
|
|
224
206
|
if (u256.eq(v, pointerHash)) {
|
|
225
|
-
return storage.get(v);
|
|
207
|
+
return this.storage.get(v);
|
|
226
208
|
}
|
|
227
209
|
}
|
|
228
210
|
|
|
229
211
|
return defaultValue;
|
|
230
212
|
}
|
|
231
213
|
|
|
232
|
-
public hasStorageAt(
|
|
233
|
-
this.ensureStorageAtAddress(address);
|
|
234
|
-
|
|
214
|
+
public hasStorageAt(pointer: u16, subPointer: MemorySlotPointer): bool {
|
|
235
215
|
// We mark zero as the default value for the storage, if something is 0, the storage slot get deleted or is non-existent
|
|
236
|
-
const val: u256 = this.getStorageAt(
|
|
216
|
+
const val: u256 = this.getStorageAt(pointer, subPointer, u256.Zero);
|
|
237
217
|
return val != u256.Zero;
|
|
238
218
|
}
|
|
239
219
|
|
|
240
220
|
public setStorageAt(
|
|
241
|
-
address: Address,
|
|
242
221
|
pointer: u16,
|
|
243
222
|
keyPointer: MemorySlotPointer,
|
|
244
223
|
value: MemorySlotData<u256>,
|
|
245
224
|
defaultValue: MemorySlotData<u256>,
|
|
246
225
|
): void {
|
|
247
|
-
this.ensureStorageAtAddress(address);
|
|
248
|
-
|
|
249
226
|
const pointerHash: u256 = encodePointerHash(pointer, keyPointer);
|
|
250
|
-
this.ensureStorageAtPointer(
|
|
227
|
+
this.ensureStorageAtPointer(pointerHash, defaultValue);
|
|
251
228
|
|
|
252
|
-
this._internalSetStorageAt(
|
|
229
|
+
this._internalSetStorageAt(pointerHash, value);
|
|
253
230
|
}
|
|
254
231
|
|
|
255
232
|
public getViewSelectors(): Uint8Array {
|
|
@@ -264,113 +241,43 @@ export class BlockchainEnvironment {
|
|
|
264
241
|
return ABIRegistry.getWriteMethods();
|
|
265
242
|
}
|
|
266
243
|
|
|
267
|
-
public loadStorage(data: Uint8Array): void {
|
|
268
|
-
this.purgeMemory();
|
|
269
|
-
|
|
270
|
-
const memoryReader: BytesReader = new BytesReader(data);
|
|
271
|
-
const contractsSize: u32 = memoryReader.readU32();
|
|
272
|
-
|
|
273
|
-
for (let i: u32 = 0; i < contractsSize; i++) {
|
|
274
|
-
const address: Address = memoryReader.readAddress();
|
|
275
|
-
const storageSize: u32 = memoryReader.readU32();
|
|
276
|
-
|
|
277
|
-
this.ensureStorageAtAddress(address);
|
|
278
|
-
const storage: PointerStorage = this.storage.get(address);
|
|
279
|
-
|
|
280
|
-
for (let j: u32 = 0; j < storageSize; j++) {
|
|
281
|
-
const keyPointer: MemorySlotPointer = memoryReader.readU256();
|
|
282
|
-
const value: MemorySlotData<u256> = memoryReader.readU256();
|
|
283
|
-
|
|
284
|
-
storage.set(keyPointer, value);
|
|
285
|
-
}
|
|
286
|
-
}
|
|
287
|
-
}
|
|
288
|
-
|
|
289
|
-
public storageToBytes(): Uint8Array {
|
|
290
|
-
const memoryWriter: BytesWriter = new BytesWriter();
|
|
291
|
-
memoryWriter.writeStorage(this.storage);
|
|
292
|
-
|
|
293
|
-
//this.storage.clear();
|
|
294
|
-
|
|
295
|
-
return memoryWriter.getBuffer();
|
|
296
|
-
}
|
|
297
|
-
|
|
298
|
-
public initializedStorageToBytes(): Uint8Array {
|
|
299
|
-
const memoryWriter: BytesWriter = new BytesWriter();
|
|
300
|
-
memoryWriter.writeStorage(this.initializedStorage);
|
|
301
|
-
|
|
302
|
-
//this.initializedStorage.clear();
|
|
303
|
-
|
|
304
|
-
return memoryWriter.getBuffer();
|
|
305
|
-
}
|
|
306
|
-
|
|
307
244
|
private purgeMemory(): void {
|
|
308
245
|
this.storage.clear();
|
|
309
|
-
this.initializedStorage.clear();
|
|
310
|
-
|
|
311
246
|
this.events = [];
|
|
312
|
-
|
|
313
|
-
this.externalCallsResponse.clear();
|
|
314
|
-
this.externalCalls.clear();
|
|
315
|
-
}
|
|
316
|
-
|
|
317
|
-
private requireInitialStorage(address: Address, pointerHash: u256, defaultValue: u256): void {
|
|
318
|
-
if (!this.initializedStorage.has(address)) {
|
|
319
|
-
this.initializedStorage.set(address, new Map<u256, MemorySlotData<u256>>());
|
|
320
|
-
}
|
|
321
|
-
|
|
322
|
-
//load(pointerHash);
|
|
323
|
-
|
|
324
|
-
const storage = this.initializedStorage.get(address);
|
|
325
|
-
storage.set(pointerHash, defaultValue);
|
|
326
|
-
}
|
|
327
|
-
|
|
328
|
-
private getExternalCallResponse(
|
|
329
|
-
destinationContract: Address,
|
|
330
|
-
index: i32,
|
|
331
|
-
): Potential<Uint8Array> {
|
|
332
|
-
if (!this.externalCallsResponse.has(destinationContract)) {
|
|
333
|
-
this.externalCallsResponse.set(destinationContract, []);
|
|
334
|
-
}
|
|
335
|
-
|
|
336
|
-
const externalCallsResponse = this.externalCallsResponse.get(destinationContract);
|
|
337
|
-
return externalCallsResponse[index] || null;
|
|
338
247
|
}
|
|
339
248
|
|
|
340
249
|
private error(msg: string): Error {
|
|
341
250
|
return new Error(`${BlockchainEnvironment.runtimeException}: ${msg}`);
|
|
342
251
|
}
|
|
343
252
|
|
|
344
|
-
private _internalSetStorageAt(
|
|
345
|
-
|
|
346
|
-
pointerHash: u256,
|
|
347
|
-
value: MemorySlotData<u256>,
|
|
348
|
-
): void {
|
|
349
|
-
const storage: PointerStorage = this.storage.get(address);
|
|
350
|
-
const keys: u256[] = storage.keys();
|
|
253
|
+
private _internalSetStorageAt(pointerHash: u256, value: MemorySlotData<u256>): void {
|
|
254
|
+
const keys: u256[] = this.storage.keys();
|
|
351
255
|
|
|
352
256
|
// Delete the old value, there is a bug with u256 and maps.
|
|
353
257
|
for (let i = 0; i < keys.length; i++) {
|
|
354
258
|
const key = keys[i];
|
|
355
259
|
|
|
356
260
|
if (u256.eq(key, pointerHash)) {
|
|
357
|
-
storage.delete(key);
|
|
261
|
+
this.storage.delete(key);
|
|
358
262
|
}
|
|
359
263
|
}
|
|
360
264
|
|
|
361
|
-
|
|
265
|
+
this.storage.set(pointerHash, value);
|
|
362
266
|
|
|
363
|
-
|
|
364
|
-
|
|
365
|
-
|
|
366
|
-
private ensureStorageAtAddress(address: Address): void {
|
|
367
|
-
if (!this.storage.has(address)) {
|
|
368
|
-
this.storage.set(address, new Map<u256, MemorySlotData<u256>>());
|
|
267
|
+
if (u256.eq(value, u256.Zero)) {
|
|
268
|
+
return;
|
|
369
269
|
}
|
|
270
|
+
|
|
271
|
+
const writer: BytesWriter = new BytesWriter();
|
|
272
|
+
writer.writeU256(pointerHash);
|
|
273
|
+
writer.writeU256(value);
|
|
274
|
+
|
|
275
|
+
const buffer: Uint8Array = writer.getBuffer();
|
|
276
|
+
storePointer(buffer);
|
|
370
277
|
}
|
|
371
278
|
|
|
372
|
-
private hasPointerStorageHash(
|
|
373
|
-
const keys = storage.keys();
|
|
279
|
+
private hasPointerStorageHash(pointer: MemorySlotPointer): bool {
|
|
280
|
+
const keys = this.storage.keys();
|
|
374
281
|
|
|
375
282
|
for (let i = 0; i < keys.length; i++) {
|
|
376
283
|
const key = keys[i];
|
|
@@ -380,24 +287,25 @@ export class BlockchainEnvironment {
|
|
|
380
287
|
}
|
|
381
288
|
}
|
|
382
289
|
|
|
383
|
-
|
|
290
|
+
// we attempt to load the requested pointer.
|
|
291
|
+
const writer = new BytesWriter();
|
|
292
|
+
writer.writeU256(pointer);
|
|
293
|
+
|
|
294
|
+
const result: Uint8Array = loadPointer(writer.getBuffer());
|
|
295
|
+
const reader: BytesReader = new BytesReader(result);
|
|
296
|
+
|
|
297
|
+
const value: u256 = reader.readU256();
|
|
298
|
+
this.storage.set(pointer, value); // cache the value
|
|
299
|
+
|
|
300
|
+
return !u256.eq(value, u256.Zero);
|
|
384
301
|
}
|
|
385
302
|
|
|
386
303
|
private ensureStorageAtPointer(
|
|
387
|
-
address: Address,
|
|
388
304
|
pointerHash: MemorySlotPointer,
|
|
389
305
|
defaultValue: MemorySlotData<u256>,
|
|
390
306
|
): void {
|
|
391
|
-
if (!this.
|
|
392
|
-
|
|
393
|
-
}
|
|
394
|
-
|
|
395
|
-
// !!! -- IMPORTANT -- !!!. We have to tell the indexer that we need this storage slot to continue even if it's already defined.
|
|
396
|
-
this.requireInitialStorage(address, pointerHash, defaultValue);
|
|
397
|
-
|
|
398
|
-
const storage: PointerStorage = this.storage.get(address);
|
|
399
|
-
if (!this.hasPointerStorageHash(storage, pointerHash)) {
|
|
400
|
-
this._internalSetStorageAt(address, pointerHash, defaultValue);
|
|
307
|
+
if (!this.hasPointerStorageHash(pointerHash)) {
|
|
308
|
+
this._internalSetStorageAt(pointerHash, defaultValue);
|
|
401
309
|
}
|
|
402
310
|
}
|
|
403
311
|
}
|
package/runtime/env/global.ts
CHANGED
|
@@ -1,12 +1,10 @@
|
|
|
1
|
-
import { u256 } from 'as-bignum/assembly/integer/u256';
|
|
2
|
-
|
|
3
1
|
// @ts-ignore
|
|
4
2
|
@external('env', 'load')
|
|
5
|
-
export declare function
|
|
3
|
+
export declare function loadPointer(data: Uint8Array): Uint8Array;
|
|
6
4
|
|
|
7
5
|
// @ts-ignore
|
|
8
6
|
@external('env', 'store')
|
|
9
|
-
export declare function
|
|
7
|
+
export declare function storePointer(data: Uint8Array): Uint8Array;
|
|
10
8
|
|
|
11
9
|
// @ts-ignore
|
|
12
10
|
@external('env', 'deploy')
|
|
@@ -18,4 +16,4 @@ export declare function deployFromAddress(data: Uint8Array): Uint8Array;
|
|
|
18
16
|
|
|
19
17
|
// @ts-ignore
|
|
20
18
|
@external('env', 'call')
|
|
21
|
-
export declare function
|
|
19
|
+
export declare function callContract(data: Uint8Array): Uint8Array;
|
package/runtime/exports/index.ts
CHANGED
|
@@ -32,26 +32,6 @@ export function getWriteMethods(): Uint8Array {
|
|
|
32
32
|
return Blockchain.getWriteMethods();
|
|
33
33
|
}
|
|
34
34
|
|
|
35
|
-
export function getModifiedStorage(): Uint8Array {
|
|
36
|
-
return Blockchain.storageToBytes();
|
|
37
|
-
}
|
|
38
|
-
|
|
39
|
-
export function initializeStorage(): Uint8Array {
|
|
40
|
-
return Blockchain.initializedStorageToBytes();
|
|
41
|
-
}
|
|
42
|
-
|
|
43
|
-
export function loadStorage(data: Uint8Array): void {
|
|
44
|
-
Blockchain.loadStorage(data);
|
|
45
|
-
}
|
|
46
|
-
|
|
47
|
-
export function loadCallsResponse(data: Uint8Array): void {
|
|
48
|
-
Blockchain.loadCallsResponse(data);
|
|
49
|
-
}
|
|
50
|
-
|
|
51
|
-
export function getCalls(): Uint8Array {
|
|
52
|
-
return Blockchain.getCalls();
|
|
53
|
-
}
|
|
54
|
-
|
|
55
35
|
export function setEnvironment(data: Uint8Array): void {
|
|
56
36
|
Blockchain.setEnvironment(data);
|
|
57
37
|
}
|
package/runtime/index.ts
CHANGED
|
@@ -10,6 +10,9 @@ export * from './contracts/OP_NET';
|
|
|
10
10
|
export * from './buffer/BytesReader';
|
|
11
11
|
export * from './buffer/BytesWriter';
|
|
12
12
|
|
|
13
|
+
/** Interfaces */
|
|
14
|
+
export * from './interfaces/DeployContractResponse';
|
|
15
|
+
|
|
13
16
|
/** Events */
|
|
14
17
|
export * from './events/NetEvent';
|
|
15
18
|
export * from './events/predefined';
|
|
@@ -0,0 +1,12 @@
|
|
|
1
|
+
import { u256 } from 'as-bignum/assembly';
|
|
2
|
+
import { Address } from '../types/Address';
|
|
3
|
+
|
|
4
|
+
export class DeployContractResponse {
|
|
5
|
+
readonly virtualAddress: u256;
|
|
6
|
+
readonly contractAddress: Address;
|
|
7
|
+
|
|
8
|
+
constructor(virtualAddress: u256, contractAddress: Address) {
|
|
9
|
+
this.virtualAddress = virtualAddress;
|
|
10
|
+
this.contractAddress = contractAddress;
|
|
11
|
+
}
|
|
12
|
+
}
|
|
@@ -1,6 +1,5 @@
|
|
|
1
1
|
import { MemorySlotPointer } from './MemorySlotPointer';
|
|
2
2
|
import { Blockchain } from '../env';
|
|
3
|
-
import { Address } from '../types/Address';
|
|
4
3
|
import { encodePointer } from '../math/abi';
|
|
5
4
|
import { MemorySlotData } from './MemorySlot';
|
|
6
5
|
import { u256 } from 'as-bignum/assembly';
|
|
@@ -9,45 +8,26 @@ import { u256 } from 'as-bignum/assembly';
|
|
|
9
8
|
export class AddressMemoryMap<K extends string, V extends MemorySlotData<u256>> {
|
|
10
9
|
public pointer: u16;
|
|
11
10
|
|
|
12
|
-
private readonly memoryAllocatorAddress: Address;
|
|
13
|
-
|
|
14
11
|
constructor(
|
|
15
12
|
pointer: u16,
|
|
16
|
-
self: Address,
|
|
17
13
|
private readonly defaultValue: V,
|
|
18
14
|
) {
|
|
19
15
|
this.pointer = pointer;
|
|
20
|
-
this.memoryAllocatorAddress = self;
|
|
21
16
|
}
|
|
22
17
|
|
|
23
18
|
public set(key: K, value: V): this {
|
|
24
19
|
const keyHash: MemorySlotPointer = encodePointer(key);
|
|
25
|
-
Blockchain.setStorageAt(
|
|
26
|
-
this.memoryAllocatorAddress,
|
|
27
|
-
this.pointer,
|
|
28
|
-
keyHash,
|
|
29
|
-
value,
|
|
30
|
-
this.defaultValue,
|
|
31
|
-
);
|
|
20
|
+
Blockchain.setStorageAt(this.pointer, keyHash, value, this.defaultValue);
|
|
32
21
|
|
|
33
22
|
return this;
|
|
34
23
|
}
|
|
35
24
|
|
|
36
25
|
public get(key: K): MemorySlotData<u256> {
|
|
37
|
-
return Blockchain.getStorageAt(
|
|
38
|
-
this.memoryAllocatorAddress,
|
|
39
|
-
this.pointer,
|
|
40
|
-
encodePointer(key),
|
|
41
|
-
this.defaultValue,
|
|
42
|
-
);
|
|
26
|
+
return Blockchain.getStorageAt(this.pointer, encodePointer(key), this.defaultValue);
|
|
43
27
|
}
|
|
44
28
|
|
|
45
29
|
public has(key: K): bool {
|
|
46
|
-
return Blockchain.hasStorageAt(
|
|
47
|
-
this.memoryAllocatorAddress,
|
|
48
|
-
this.pointer,
|
|
49
|
-
encodePointer(key),
|
|
50
|
-
);
|
|
30
|
+
return Blockchain.hasStorageAt(this.pointer, encodePointer(key));
|
|
51
31
|
}
|
|
52
32
|
|
|
53
33
|
@unsafe
|
|
@@ -1,7 +1,6 @@
|
|
|
1
1
|
import { MemorySlotData } from './MemorySlot';
|
|
2
2
|
import { u256 } from 'as-bignum/assembly';
|
|
3
3
|
import { Blockchain } from '../env';
|
|
4
|
-
import { Address } from '../types/Address';
|
|
5
4
|
import { MemorySlotPointer } from './MemorySlotPointer';
|
|
6
5
|
import { encodePointer } from '../math/abi';
|
|
7
6
|
|
|
@@ -10,16 +9,13 @@ export class KeyMerger<K extends string, K2 extends string, V extends MemorySlot
|
|
|
10
9
|
public parentKey: K;
|
|
11
10
|
|
|
12
11
|
public pointer: u16;
|
|
13
|
-
private readonly memoryAllocatorAddress: Address;
|
|
14
12
|
|
|
15
13
|
constructor(
|
|
16
14
|
parent: K,
|
|
17
15
|
pointer: u16,
|
|
18
|
-
self: Address,
|
|
19
16
|
private readonly defaultValue: V,
|
|
20
17
|
) {
|
|
21
18
|
this.pointer = pointer;
|
|
22
|
-
this.memoryAllocatorAddress = self;
|
|
23
19
|
|
|
24
20
|
this.parentKey = parent;
|
|
25
21
|
}
|
|
@@ -28,13 +24,7 @@ export class KeyMerger<K extends string, K2 extends string, V extends MemorySlot
|
|
|
28
24
|
const mergedKey: string = `${this.parentKey}${key2}`;
|
|
29
25
|
const keyHash: MemorySlotPointer = encodePointer(mergedKey);
|
|
30
26
|
|
|
31
|
-
Blockchain.setStorageAt(
|
|
32
|
-
this.memoryAllocatorAddress,
|
|
33
|
-
this.pointer,
|
|
34
|
-
keyHash,
|
|
35
|
-
value,
|
|
36
|
-
this.defaultValue,
|
|
37
|
-
);
|
|
27
|
+
Blockchain.setStorageAt(this.pointer, keyHash, value, this.defaultValue);
|
|
38
28
|
|
|
39
29
|
return this;
|
|
40
30
|
}
|
|
@@ -42,22 +32,13 @@ export class KeyMerger<K extends string, K2 extends string, V extends MemorySlot
|
|
|
42
32
|
public get(key: K): MemorySlotData<u256> {
|
|
43
33
|
const mergedKey: string = `${this.parentKey}${key}`;
|
|
44
34
|
|
|
45
|
-
return Blockchain.getStorageAt(
|
|
46
|
-
this.memoryAllocatorAddress,
|
|
47
|
-
this.pointer,
|
|
48
|
-
encodePointer(mergedKey),
|
|
49
|
-
this.defaultValue,
|
|
50
|
-
);
|
|
35
|
+
return Blockchain.getStorageAt(this.pointer, encodePointer(mergedKey), this.defaultValue);
|
|
51
36
|
}
|
|
52
37
|
|
|
53
38
|
public has(key: K): bool {
|
|
54
39
|
const mergedKey: string = `${this.parentKey}${key}`;
|
|
55
40
|
|
|
56
|
-
return Blockchain.hasStorageAt(
|
|
57
|
-
this.memoryAllocatorAddress,
|
|
58
|
-
this.pointer,
|
|
59
|
-
encodePointer(mergedKey),
|
|
60
|
-
);
|
|
41
|
+
return Blockchain.hasStorageAt(this.pointer, encodePointer(mergedKey));
|
|
61
42
|
}
|
|
62
43
|
|
|
63
44
|
@unsafe
|
|
@@ -1,4 +1,3 @@
|
|
|
1
|
-
import { Address } from '../types/Address';
|
|
2
1
|
import { MemorySlotData } from './MemorySlot';
|
|
3
2
|
import { u256 } from 'as-bignum/assembly';
|
|
4
3
|
import { KeyMerger } from './KeyMerger';
|
|
@@ -11,17 +10,13 @@ export class MultiAddressMemoryMap<
|
|
|
11
10
|
> extends Map<K, KeyMerger<K, K2, V>> {
|
|
12
11
|
public pointer: u16;
|
|
13
12
|
|
|
14
|
-
private readonly memoryAllocatorAddress: Address;
|
|
15
|
-
|
|
16
13
|
constructor(
|
|
17
14
|
pointer: u16,
|
|
18
|
-
self: Address,
|
|
19
15
|
private readonly defaultValue: V,
|
|
20
16
|
) {
|
|
21
17
|
super();
|
|
22
18
|
|
|
23
19
|
this.pointer = pointer;
|
|
24
|
-
this.memoryAllocatorAddress = self;
|
|
25
20
|
}
|
|
26
21
|
|
|
27
22
|
public get(key: K): KeyMerger<K, K2, V> {
|
|
@@ -44,7 +39,7 @@ export class MultiAddressMemoryMap<
|
|
|
44
39
|
public set(key: K, value: KeyMerger<K, K2, V>): this {
|
|
45
40
|
this.createKeyMerger(key);
|
|
46
41
|
|
|
47
|
-
return <this>
|
|
42
|
+
return <this>super.set(key, value);
|
|
48
43
|
}
|
|
49
44
|
|
|
50
45
|
public has(key: K): bool {
|
|
@@ -61,15 +56,7 @@ export class MultiAddressMemoryMap<
|
|
|
61
56
|
|
|
62
57
|
private createKeyMerger(key: K): void {
|
|
63
58
|
if (!super.has(key)) {
|
|
64
|
-
super.set(
|
|
65
|
-
key,
|
|
66
|
-
new KeyMerger<K, K2, V>(
|
|
67
|
-
key,
|
|
68
|
-
this.pointer,
|
|
69
|
-
this.memoryAllocatorAddress,
|
|
70
|
-
this.defaultValue,
|
|
71
|
-
),
|
|
72
|
-
);
|
|
59
|
+
super.set(key, new KeyMerger<K, K2, V>(key, this.pointer, this.defaultValue));
|
|
73
60
|
}
|
|
74
61
|
}
|
|
75
62
|
}
|
|
@@ -1,23 +1,16 @@
|
|
|
1
1
|
import { u256 } from 'as-bignum/assembly';
|
|
2
2
|
import { SafeMath } from '../types/SafeMath';
|
|
3
|
-
import { Address } from '../types/Address';
|
|
4
3
|
import { MemorySlotPointer } from '../memory/MemorySlotPointer';
|
|
5
4
|
import { Blockchain } from '../env';
|
|
6
5
|
|
|
7
6
|
@final
|
|
8
7
|
export class StoredU256 {
|
|
9
8
|
constructor(
|
|
10
|
-
public address: Address,
|
|
11
9
|
public pointer: u16,
|
|
12
10
|
public subPointer: MemorySlotPointer,
|
|
13
11
|
private defaultValue: u256,
|
|
14
12
|
) {
|
|
15
|
-
this._value = Blockchain.getStorageAt(
|
|
16
|
-
this.address,
|
|
17
|
-
this.pointer,
|
|
18
|
-
this.subPointer,
|
|
19
|
-
this.defaultValue,
|
|
20
|
-
);
|
|
13
|
+
this._value = Blockchain.getStorageAt(this.pointer, this.subPointer, this.defaultValue);
|
|
21
14
|
}
|
|
22
15
|
|
|
23
16
|
private _value: u256 = u256.Zero;
|
|
@@ -33,13 +26,7 @@ export class StoredU256 {
|
|
|
33
26
|
public set value(value: u256) {
|
|
34
27
|
this._value = value;
|
|
35
28
|
|
|
36
|
-
Blockchain.setStorageAt(
|
|
37
|
-
this.address,
|
|
38
|
-
this.pointer,
|
|
39
|
-
this.subPointer,
|
|
40
|
-
this._value,
|
|
41
|
-
this.defaultValue,
|
|
42
|
-
);
|
|
29
|
+
Blockchain.setStorageAt(this.pointer, this.subPointer, this._value, this.defaultValue);
|
|
43
30
|
}
|
|
44
31
|
|
|
45
32
|
@inline
|
|
@@ -53,13 +40,7 @@ export class StoredU256 {
|
|
|
53
40
|
this.ensureValue();
|
|
54
41
|
|
|
55
42
|
this._value = SafeMath.add(this._value, value);
|
|
56
|
-
Blockchain.setStorageAt(
|
|
57
|
-
this.address,
|
|
58
|
-
this.pointer,
|
|
59
|
-
this.subPointer,
|
|
60
|
-
this._value,
|
|
61
|
-
this.defaultValue,
|
|
62
|
-
);
|
|
43
|
+
Blockchain.setStorageAt(this.pointer, this.subPointer, this._value, this.defaultValue);
|
|
63
44
|
|
|
64
45
|
return this;
|
|
65
46
|
}
|
|
@@ -70,13 +51,7 @@ export class StoredU256 {
|
|
|
70
51
|
this.ensureValue();
|
|
71
52
|
|
|
72
53
|
this._value = SafeMath.sub(this._value, value);
|
|
73
|
-
Blockchain.setStorageAt(
|
|
74
|
-
this.address,
|
|
75
|
-
this.pointer,
|
|
76
|
-
this.subPointer,
|
|
77
|
-
this._value,
|
|
78
|
-
this.defaultValue,
|
|
79
|
-
);
|
|
54
|
+
Blockchain.setStorageAt(this.pointer, this.subPointer, this._value, this.defaultValue);
|
|
80
55
|
|
|
81
56
|
return this;
|
|
82
57
|
}
|
|
@@ -87,13 +62,7 @@ export class StoredU256 {
|
|
|
87
62
|
this.ensureValue();
|
|
88
63
|
|
|
89
64
|
this._value = SafeMath.mul(this._value, value);
|
|
90
|
-
Blockchain.setStorageAt(
|
|
91
|
-
this.address,
|
|
92
|
-
this.pointer,
|
|
93
|
-
this.subPointer,
|
|
94
|
-
this._value,
|
|
95
|
-
this.defaultValue,
|
|
96
|
-
);
|
|
65
|
+
Blockchain.setStorageAt(this.pointer, this.subPointer, this._value, this.defaultValue);
|
|
97
66
|
|
|
98
67
|
return this;
|
|
99
68
|
}
|
|
@@ -152,13 +121,7 @@ export class StoredU256 {
|
|
|
152
121
|
this.ensureValue();
|
|
153
122
|
|
|
154
123
|
this._value = u256.shr(this._value, value);
|
|
155
|
-
Blockchain.setStorageAt(
|
|
156
|
-
this.address,
|
|
157
|
-
this.pointer,
|
|
158
|
-
this.subPointer,
|
|
159
|
-
this._value,
|
|
160
|
-
this.defaultValue,
|
|
161
|
-
);
|
|
124
|
+
Blockchain.setStorageAt(this.pointer, this.subPointer, this._value, this.defaultValue);
|
|
162
125
|
|
|
163
126
|
return this;
|
|
164
127
|
}
|
|
@@ -169,13 +132,7 @@ export class StoredU256 {
|
|
|
169
132
|
this.ensureValue();
|
|
170
133
|
|
|
171
134
|
this._value = u256.and(this._value, value);
|
|
172
|
-
Blockchain.setStorageAt(
|
|
173
|
-
this.address,
|
|
174
|
-
this.pointer,
|
|
175
|
-
this.subPointer,
|
|
176
|
-
this._value,
|
|
177
|
-
this.defaultValue,
|
|
178
|
-
);
|
|
135
|
+
Blockchain.setStorageAt(this.pointer, this.subPointer, this._value, this.defaultValue);
|
|
179
136
|
|
|
180
137
|
return this;
|
|
181
138
|
}
|
|
@@ -186,13 +143,7 @@ export class StoredU256 {
|
|
|
186
143
|
this.ensureValue();
|
|
187
144
|
|
|
188
145
|
this._value = u256.or(this._value, value);
|
|
189
|
-
Blockchain.setStorageAt(
|
|
190
|
-
this.address,
|
|
191
|
-
this.pointer,
|
|
192
|
-
this.subPointer,
|
|
193
|
-
this._value,
|
|
194
|
-
this.defaultValue,
|
|
195
|
-
);
|
|
146
|
+
Blockchain.setStorageAt(this.pointer, this.subPointer, this._value, this.defaultValue);
|
|
196
147
|
|
|
197
148
|
return this;
|
|
198
149
|
}
|
|
@@ -203,13 +154,7 @@ export class StoredU256 {
|
|
|
203
154
|
this.ensureValue();
|
|
204
155
|
|
|
205
156
|
this._value = u256.xor(this._value, value);
|
|
206
|
-
Blockchain.setStorageAt(
|
|
207
|
-
this.address,
|
|
208
|
-
this.pointer,
|
|
209
|
-
this.subPointer,
|
|
210
|
-
this._value,
|
|
211
|
-
this.defaultValue,
|
|
212
|
-
);
|
|
157
|
+
Blockchain.setStorageAt(this.pointer, this.subPointer, this._value, this.defaultValue);
|
|
213
158
|
|
|
214
159
|
return this;
|
|
215
160
|
}
|
|
@@ -231,13 +176,7 @@ export class StoredU256 {
|
|
|
231
176
|
value = u256.shr(value, 1);
|
|
232
177
|
}
|
|
233
178
|
|
|
234
|
-
Blockchain.setStorageAt(
|
|
235
|
-
this.address,
|
|
236
|
-
this.pointer,
|
|
237
|
-
this.subPointer,
|
|
238
|
-
this._value,
|
|
239
|
-
this.defaultValue,
|
|
240
|
-
);
|
|
179
|
+
Blockchain.setStorageAt(this.pointer, this.subPointer, this._value, this.defaultValue);
|
|
241
180
|
|
|
242
181
|
return this;
|
|
243
182
|
}
|
|
@@ -262,13 +201,7 @@ export class StoredU256 {
|
|
|
262
201
|
}
|
|
263
202
|
|
|
264
203
|
this._value = result;
|
|
265
|
-
Blockchain.setStorageAt(
|
|
266
|
-
this.address,
|
|
267
|
-
this.pointer,
|
|
268
|
-
this.subPointer,
|
|
269
|
-
this._value,
|
|
270
|
-
this.defaultValue,
|
|
271
|
-
);
|
|
204
|
+
Blockchain.setStorageAt(this.pointer, this.subPointer, this._value, this.defaultValue);
|
|
272
205
|
|
|
273
206
|
return this;
|
|
274
207
|
}
|
|
@@ -279,13 +212,7 @@ export class StoredU256 {
|
|
|
279
212
|
this.ensureValue();
|
|
280
213
|
|
|
281
214
|
this._value = SafeMath.add(this._value, u256.One);
|
|
282
|
-
Blockchain.setStorageAt(
|
|
283
|
-
this.address,
|
|
284
|
-
this.pointer,
|
|
285
|
-
this.subPointer,
|
|
286
|
-
this._value,
|
|
287
|
-
this.defaultValue,
|
|
288
|
-
);
|
|
215
|
+
Blockchain.setStorageAt(this.pointer, this.subPointer, this._value, this.defaultValue);
|
|
289
216
|
|
|
290
217
|
return this;
|
|
291
218
|
}
|
|
@@ -296,13 +223,7 @@ export class StoredU256 {
|
|
|
296
223
|
this.ensureValue();
|
|
297
224
|
|
|
298
225
|
this._value = SafeMath.sub(this._value, u256.One);
|
|
299
|
-
Blockchain.setStorageAt(
|
|
300
|
-
this.address,
|
|
301
|
-
this.pointer,
|
|
302
|
-
this.subPointer,
|
|
303
|
-
this._value,
|
|
304
|
-
this.defaultValue,
|
|
305
|
-
);
|
|
226
|
+
Blockchain.setStorageAt(this.pointer, this.subPointer, this._value, this.defaultValue);
|
|
306
227
|
|
|
307
228
|
return this;
|
|
308
229
|
}
|
|
@@ -311,13 +232,7 @@ export class StoredU256 {
|
|
|
311
232
|
public set(value: u256): this {
|
|
312
233
|
this._value = value;
|
|
313
234
|
|
|
314
|
-
Blockchain.setStorageAt(
|
|
315
|
-
this.address,
|
|
316
|
-
this.pointer,
|
|
317
|
-
this.subPointer,
|
|
318
|
-
this._value,
|
|
319
|
-
this.defaultValue,
|
|
320
|
-
);
|
|
235
|
+
Blockchain.setStorageAt(this.pointer, this.subPointer, this._value, this.defaultValue);
|
|
321
236
|
|
|
322
237
|
return this;
|
|
323
238
|
}
|
|
@@ -328,11 +243,6 @@ export class StoredU256 {
|
|
|
328
243
|
}
|
|
329
244
|
|
|
330
245
|
private ensureValue(): void {
|
|
331
|
-
this._value = Blockchain.getStorageAt(
|
|
332
|
-
this.address,
|
|
333
|
-
this.pointer,
|
|
334
|
-
this.subPointer,
|
|
335
|
-
this.defaultValue,
|
|
336
|
-
);
|
|
246
|
+
this._value = Blockchain.getStorageAt(this.pointer, this.subPointer, this.defaultValue);
|
|
337
247
|
}
|
|
338
248
|
}
|