add macro to restrict compilation to a given curve
This commit is contained in:
parent
8fa7e5d50c
commit
c802077b74
26 changed files with 153 additions and 453 deletions
|
@ -12,6 +12,7 @@
|
|||
- [Imports](./concepts/imports.md)
|
||||
- [Comments](./concepts/comments.md)
|
||||
- [Standard Library](./concepts/stdlib.md)
|
||||
- [Macros](./concepts/macros.md)
|
||||
|
||||
- [Reference](reference/index.md)
|
||||
- [CLI](reference/cli.md)
|
||||
|
|
9
zokrates_book/src/concepts/macros.md
Normal file
9
zokrates_book/src/concepts/macros.md
Normal file
|
@ -0,0 +1,9 @@
|
|||
## Macros
|
||||
|
||||
ZoKrates currently exposes a single macro:
|
||||
|
||||
```
|
||||
#pragma curve $CURVE
|
||||
```
|
||||
|
||||
The effect of this macro is to abort compilation if this file is being compiled for a curve different from `$CURVE`.
|
|
@ -1,43 +0,0 @@
|
|||
import "./popLeastSignificantBit"
|
||||
|
||||
def main(field order) -> (field, field, field, field):
|
||||
// MSB
|
||||
// Limit price (120 bits - i.e. pow(10,36) in base 2)
|
||||
// Target token (8 bits - i.e. we support 256 = 2^8 tokens)
|
||||
// Source token (8 bits)
|
||||
// Amount (120 bits)
|
||||
// LSB
|
||||
field amount = 0
|
||||
field exponent = 1
|
||||
field bit = 0
|
||||
for field i in 0..120 do
|
||||
bit, order = popLeastSignificantBit(order)
|
||||
amount = amount + (bit * exponent)
|
||||
exponent = exponent * 2
|
||||
endfor
|
||||
|
||||
field sourceToken = 0
|
||||
exponent = 1
|
||||
for field i in 0..5 do
|
||||
bit, order = popLeastSignificantBit(order)
|
||||
sourceToken = sourceToken + (bit * exponent)
|
||||
exponent = exponent * 2
|
||||
endfor
|
||||
|
||||
field targetToken = 0
|
||||
exponent = 1
|
||||
for field i in 0..5 do
|
||||
bit, order = popLeastSignificantBit(order)
|
||||
targetToken = targetToken + (bit * exponent)
|
||||
exponent = exponent * 2
|
||||
endfor
|
||||
|
||||
field limit = 0
|
||||
exponent = 1
|
||||
for field i in 0..120 do
|
||||
bit, order = popLeastSignificantBit(order)
|
||||
limit = limit + (bit * exponent)
|
||||
exponent = exponent * 2
|
||||
endfor
|
||||
|
||||
return amount, sourceToken, targetToken, limit
|
|
@ -1,252 +0,0 @@
|
|||
def main(field bit0, field bit1, field bit2, field bit3, field bit4, field bit5, field bit6, field bit7, field bit8, field bit9, field bit10, field bit11, field bit12, field bit13, field bit14, field bit15, field bit16, field bit17, field bit18, field bit19, field bit20, field bit21, field bit22, field bit23, field bit24, field bit25, field bit26, field bit27, field bit28, field bit29, field bit30, field bit31, field bit32, field bit33, field bit34, field bit35, field bit36, field bit37, field bit38, field bit39, field bit40, field bit41, field bit42, field bit43, field bit44, field bit45, field bit46, field bit47, field bit48, field bit49, field bit50, field bit51, field bit52, field bit53, field bit54, field bit55, field bit56, field bit57, field bit58, field bit59, field bit60, field bit61, field bit62, field bit63, field bit64, field bit65, field bit66, field bit67, field bit68, field bit69, field bit70, field bit71, field bit72, field bit73, field bit74, field bit75, field bit76, field bit77, field bit78, field bit79, field bit80, field bit81, field bit82, field bit83, field bit84, field bit85, field bit86, field bit87, field bit88, field bit89, field bit90, field bit91, field bit92, field bit93, field bit94, field bit95, field bit96, field bit97, field bit98, field bit99, field bit100, field bit101, field bit102, field bit103, field bit104, field bit105, field bit106, field bit107, field bit108, field bit109, field bit110, field bit111, field bit112, field bit113, field bit114, field bit115, field bit116, field bit117, field bit118, field bit119, field bit120, field bit121, field bit122, field bit123, field bit124, field bit125, field bit126, field bit127, field bit128, field bit129, field bit130, field bit131, field bit132, field bit133, field bit134, field bit135, field bit136, field bit137, field bit138, field bit139, field bit140, field bit141, field bit142, field bit143, field bit144, field bit145, field bit146, field bit147, field bit148, field bit149, field bit150, field bit151, field bit152, field bit153, field bit154, field bit155, field bit156, field bit157, field bit158, field bit159, field bit160, field bit161, field bit162, field bit163, field bit164, field bit165, field bit166, field bit167, field bit168, field bit169, field bit170, field bit171, field bit172, field bit173, field bit174, field bit175, field bit176, field bit177, field bit178, field bit179, field bit180, field bit181, field bit182, field bit183, field bit184, field bit185, field bit186, field bit187, field bit188, field bit189, field bit190, field bit191, field bit192, field bit193, field bit194, field bit195, field bit196, field bit197, field bit198, field bit199, field bit200, field bit201, field bit202, field bit203, field bit204, field bit205, field bit206, field bit207, field bit208, field bit209, field bit210, field bit211, field bit212, field bit213, field bit214, field bit215, field bit216, field bit217, field bit218, field bit219, field bit220, field bit221, field bit222, field bit223, field bit224, field bit225, field bit226, field bit227, field bit228, field bit229, field bit230, field bit231, field bit232, field bit233, field bit234, field bit235, field bit236, field bit237, field bit238, field bit239, field bit240, field bit241, field bit242, field bit243, field bit244, field bit245, field bit246, field bit247, field bit248, field bit249, field bit250, field bit251, field bit252) -> (field, field, field, field):
|
||||
field amount = bit0
|
||||
amount = amount + (2 * bit1)
|
||||
amount = amount + (4 * bit2)
|
||||
amount = amount + (8 * bit3)
|
||||
amount = amount + (16 * bit4)
|
||||
amount = amount + (32 * bit5)
|
||||
amount = amount + (64 * bit6)
|
||||
amount = amount + (128 * bit7)
|
||||
amount = amount + (256 * bit8)
|
||||
amount = amount + (512 * bit9)
|
||||
amount = amount + (1024 * bit10)
|
||||
amount = amount + (2048 * bit11)
|
||||
amount = amount + (4096 * bit12)
|
||||
amount = amount + (8192 * bit13)
|
||||
amount = amount + (16384 * bit14)
|
||||
amount = amount + (32768 * bit15)
|
||||
amount = amount + (65536 * bit16)
|
||||
amount = amount + (131072 * bit17)
|
||||
amount = amount + (262144 * bit18)
|
||||
amount = amount + (524288 * bit19)
|
||||
amount = amount + (1048576 * bit20)
|
||||
amount = amount + (2097152 * bit21)
|
||||
amount = amount + (4194304 * bit22)
|
||||
amount = amount + (8388608 * bit23)
|
||||
amount = amount + (16777216 * bit24)
|
||||
amount = amount + (33554432 * bit25)
|
||||
amount = amount + (67108864 * bit26)
|
||||
amount = amount + (134217728 * bit27)
|
||||
amount = amount + (268435456 * bit28)
|
||||
amount = amount + (536870912 * bit29)
|
||||
amount = amount + (1073741824 * bit30)
|
||||
amount = amount + (2147483648 * bit31)
|
||||
amount = amount + (4294967296 * bit32)
|
||||
amount = amount + (8589934592 * bit33)
|
||||
amount = amount + (17179869184 * bit34)
|
||||
amount = amount + (34359738368 * bit35)
|
||||
amount = amount + (68719476736 * bit36)
|
||||
amount = amount + (137438953472 * bit37)
|
||||
amount = amount + (274877906944 * bit38)
|
||||
amount = amount + (549755813888 * bit39)
|
||||
amount = amount + (1099511627776 * bit40)
|
||||
amount = amount + (2199023255552 * bit41)
|
||||
amount = amount + (4398046511104 * bit42)
|
||||
amount = amount + (8796093022208 * bit43)
|
||||
amount = amount + (17592186044416 * bit44)
|
||||
amount = amount + (35184372088832 * bit45)
|
||||
amount = amount + (70368744177664 * bit46)
|
||||
amount = amount + (140737488355328 * bit47)
|
||||
amount = amount + (281474976710656 * bit48)
|
||||
amount = amount + (562949953421312 * bit49)
|
||||
amount = amount + (1125899906842624 * bit50)
|
||||
amount = amount + (2251799813685248 * bit51)
|
||||
amount = amount + (4503599627370496 * bit52)
|
||||
amount = amount + (9007199254740992 * bit53)
|
||||
amount = amount + (18014398509481984 * bit54)
|
||||
amount = amount + (36028797018963968 * bit55)
|
||||
amount = amount + (72057594037927936 * bit56)
|
||||
amount = amount + (144115188075855872 * bit57)
|
||||
amount = amount + (288230376151711744 * bit58)
|
||||
amount = amount + (576460752303423488 * bit59)
|
||||
amount = amount + (1152921504606846976 * bit60)
|
||||
amount = amount + (2305843009213693952 * bit61)
|
||||
amount = amount + (4611686018427387904 * bit62)
|
||||
amount = amount + (9223372036854775808 * bit63)
|
||||
amount = amount + (18446744073709551616 * bit64)
|
||||
amount = amount + (36893488147419103232 * bit65)
|
||||
amount = amount + (73786976294838206464 * bit66)
|
||||
amount = amount + (147573952589676412928 * bit67)
|
||||
amount = amount + (295147905179352825856 * bit68)
|
||||
amount = amount + (590295810358705651712 * bit69)
|
||||
amount = amount + (1180591620717411303424 * bit70)
|
||||
amount = amount + (2361183241434822606848 * bit71)
|
||||
amount = amount + (4722366482869645213696 * bit72)
|
||||
amount = amount + (9444732965739290427392 * bit73)
|
||||
amount = amount + (18889465931478580854784 * bit74)
|
||||
amount = amount + (37778931862957161709568 * bit75)
|
||||
amount = amount + (75557863725914323419136 * bit76)
|
||||
amount = amount + (151115727451828646838272 * bit77)
|
||||
amount = amount + (302231454903657293676544 * bit78)
|
||||
amount = amount + (604462909807314587353088 * bit79)
|
||||
amount = amount + (1208925819614629174706176 * bit80)
|
||||
amount = amount + (2417851639229258349412352 * bit81)
|
||||
amount = amount + (4835703278458516698824704 * bit82)
|
||||
amount = amount + (9671406556917033397649408 * bit83)
|
||||
amount = amount + (19342813113834066795298816 * bit84)
|
||||
amount = amount + (38685626227668133590597632 * bit85)
|
||||
amount = amount + (77371252455336267181195264 * bit86)
|
||||
amount = amount + (154742504910672534362390528 * bit87)
|
||||
amount = amount + (309485009821345068724781056 * bit88)
|
||||
amount = amount + (618970019642690137449562112 * bit89)
|
||||
amount = amount + (1237940039285380274899124224 * bit90)
|
||||
amount = amount + (2475880078570760549798248448 * bit91)
|
||||
amount = amount + (4951760157141521099596496896 * bit92)
|
||||
amount = amount + (9903520314283042199192993792 * bit93)
|
||||
amount = amount + (19807040628566084398385987584 * bit94)
|
||||
amount = amount + (39614081257132168796771975168 * bit95)
|
||||
amount = amount + (79228162514264337593543950336 * bit96)
|
||||
amount = amount + (158456325028528675187087900672 * bit97)
|
||||
amount = amount + (316912650057057350374175801344 * bit98)
|
||||
amount = amount + (633825300114114700748351602688 * bit99)
|
||||
amount = amount + (1267650600228229401496703205376 * bit100)
|
||||
amount = amount + (2535301200456458802993406410752 * bit101)
|
||||
amount = amount + (5070602400912917605986812821504 * bit102)
|
||||
amount = amount + (10141204801825835211973625643008 * bit103)
|
||||
amount = amount + (20282409603651670423947251286016 * bit104)
|
||||
amount = amount + (40564819207303340847894502572032 * bit105)
|
||||
amount = amount + (81129638414606681695789005144064 * bit106)
|
||||
amount = amount + (162259276829213363391578010288128 * bit107)
|
||||
amount = amount + (324518553658426726783156020576256 * bit108)
|
||||
amount = amount + (649037107316853453566312041152512 * bit109)
|
||||
amount = amount + (1298074214633706907132624082305024 * bit110)
|
||||
amount = amount + (2596148429267413814265248164610048 * bit111)
|
||||
amount = amount + (5192296858534827628530496329220096 * bit112)
|
||||
amount = amount + (10384593717069655257060992658440192 * bit113)
|
||||
amount = amount + (20769187434139310514121985316880384 * bit114)
|
||||
amount = amount + (41538374868278621028243970633760768 * bit115)
|
||||
amount = amount + (83076749736557242056487941267521536 * bit116)
|
||||
amount = amount + (166153499473114484112975882535043072 * bit117)
|
||||
amount = amount + (332306998946228968225951765070086144 * bit118)
|
||||
amount = amount + (664613997892457936451903530140172288 * bit119)
|
||||
field sourceToken = bit120
|
||||
sourceToken = sourceToken + (2 * bit121)
|
||||
sourceToken = sourceToken + (4 * bit122)
|
||||
sourceToken = sourceToken + (8 * bit123)
|
||||
sourceToken = sourceToken + (16 * bit124)
|
||||
field targetToken = bit125
|
||||
targetToken = targetToken + (2 * bit126)
|
||||
targetToken = targetToken + (4 * bit127)
|
||||
targetToken = targetToken + (8 * bit128)
|
||||
targetToken = targetToken + (16 * bit129)
|
||||
field limit = bit130
|
||||
limit = limit + (2 * bit131)
|
||||
limit = limit + (4 * bit132)
|
||||
limit = limit + (8 * bit133)
|
||||
limit = limit + (16 * bit134)
|
||||
limit = limit + (32 * bit135)
|
||||
limit = limit + (64 * bit136)
|
||||
limit = limit + (128 * bit137)
|
||||
limit = limit + (256 * bit138)
|
||||
limit = limit + (512 * bit139)
|
||||
limit = limit + (1024 * bit140)
|
||||
limit = limit + (2048 * bit141)
|
||||
limit = limit + (4096 * bit142)
|
||||
limit = limit + (8192 * bit143)
|
||||
limit = limit + (16384 * bit144)
|
||||
limit = limit + (32768 * bit145)
|
||||
limit = limit + (65536 * bit146)
|
||||
limit = limit + (131072 * bit147)
|
||||
limit = limit + (262144 * bit148)
|
||||
limit = limit + (524288 * bit149)
|
||||
limit = limit + (1048576 * bit150)
|
||||
limit = limit + (2097152 * bit151)
|
||||
limit = limit + (4194304 * bit152)
|
||||
limit = limit + (8388608 * bit153)
|
||||
limit = limit + (16777216 * bit154)
|
||||
limit = limit + (33554432 * bit155)
|
||||
limit = limit + (67108864 * bit156)
|
||||
limit = limit + (134217728 * bit157)
|
||||
limit = limit + (268435456 * bit158)
|
||||
limit = limit + (536870912 * bit159)
|
||||
limit = limit + (1073741824 * bit160)
|
||||
limit = limit + (2147483648 * bit161)
|
||||
limit = limit + (4294967296 * bit162)
|
||||
limit = limit + (8589934592 * bit163)
|
||||
limit = limit + (17179869184 * bit164)
|
||||
limit = limit + (34359738368 * bit165)
|
||||
limit = limit + (68719476736 * bit166)
|
||||
limit = limit + (137438953472 * bit167)
|
||||
limit = limit + (274877906944 * bit168)
|
||||
limit = limit + (549755813888 * bit169)
|
||||
limit = limit + (1099511627776 * bit170)
|
||||
limit = limit + (2199023255552 * bit171)
|
||||
limit = limit + (4398046511104 * bit172)
|
||||
limit = limit + (8796093022208 * bit173)
|
||||
limit = limit + (17592186044416 * bit174)
|
||||
limit = limit + (35184372088832 * bit175)
|
||||
limit = limit + (70368744177664 * bit176)
|
||||
limit = limit + (140737488355328 * bit177)
|
||||
limit = limit + (281474976710656 * bit178)
|
||||
limit = limit + (562949953421312 * bit179)
|
||||
limit = limit + (1125899906842624 * bit180)
|
||||
limit = limit + (2251799813685248 * bit181)
|
||||
limit = limit + (4503599627370496 * bit182)
|
||||
limit = limit + (9007199254740992 * bit183)
|
||||
limit = limit + (18014398509481984 * bit184)
|
||||
limit = limit + (36028797018963968 * bit185)
|
||||
limit = limit + (72057594037927936 * bit186)
|
||||
limit = limit + (144115188075855872 * bit187)
|
||||
limit = limit + (288230376151711744 * bit188)
|
||||
limit = limit + (576460752303423488 * bit189)
|
||||
limit = limit + (1152921504606846976 * bit190)
|
||||
limit = limit + (2305843009213693952 * bit191)
|
||||
limit = limit + (4611686018427387904 * bit192)
|
||||
limit = limit + (9223372036854775808 * bit193)
|
||||
limit = limit + (18446744073709551616 * bit194)
|
||||
limit = limit + (36893488147419103232 * bit195)
|
||||
limit = limit + (73786976294838206464 * bit196)
|
||||
limit = limit + (147573952589676412928 * bit197)
|
||||
limit = limit + (295147905179352825856 * bit198)
|
||||
limit = limit + (590295810358705651712 * bit199)
|
||||
limit = limit + (1180591620717411303424 * bit200)
|
||||
limit = limit + (2361183241434822606848 * bit201)
|
||||
limit = limit + (4722366482869645213696 * bit202)
|
||||
limit = limit + (9444732965739290427392 * bit203)
|
||||
limit = limit + (18889465931478580854784 * bit204)
|
||||
limit = limit + (37778931862957161709568 * bit205)
|
||||
limit = limit + (75557863725914323419136 * bit206)
|
||||
limit = limit + (151115727451828646838272 * bit207)
|
||||
limit = limit + (302231454903657293676544 * bit208)
|
||||
limit = limit + (604462909807314587353088 * bit209)
|
||||
limit = limit + (1208925819614629174706176 * bit210)
|
||||
limit = limit + (2417851639229258349412352 * bit211)
|
||||
limit = limit + (4835703278458516698824704 * bit212)
|
||||
limit = limit + (9671406556917033397649408 * bit213)
|
||||
limit = limit + (19342813113834066795298816 * bit214)
|
||||
limit = limit + (38685626227668133590597632 * bit215)
|
||||
limit = limit + (77371252455336267181195264 * bit216)
|
||||
limit = limit + (154742504910672534362390528 * bit217)
|
||||
limit = limit + (309485009821345068724781056 * bit218)
|
||||
limit = limit + (618970019642690137449562112 * bit219)
|
||||
limit = limit + (1237940039285380274899124224 * bit220)
|
||||
limit = limit + (2475880078570760549798248448 * bit221)
|
||||
limit = limit + (4951760157141521099596496896 * bit222)
|
||||
limit = limit + (9903520314283042199192993792 * bit223)
|
||||
limit = limit + (19807040628566084398385987584 * bit224)
|
||||
limit = limit + (39614081257132168796771975168 * bit225)
|
||||
limit = limit + (79228162514264337593543950336 * bit226)
|
||||
limit = limit + (158456325028528675187087900672 * bit227)
|
||||
limit = limit + (316912650057057350374175801344 * bit228)
|
||||
limit = limit + (633825300114114700748351602688 * bit229)
|
||||
limit = limit + (1267650600228229401496703205376 * bit230)
|
||||
limit = limit + (2535301200456458802993406410752 * bit231)
|
||||
limit = limit + (5070602400912917605986812821504 * bit232)
|
||||
limit = limit + (10141204801825835211973625643008 * bit233)
|
||||
limit = limit + (20282409603651670423947251286016 * bit234)
|
||||
limit = limit + (40564819207303340847894502572032 * bit235)
|
||||
limit = limit + (81129638414606681695789005144064 * bit236)
|
||||
limit = limit + (162259276829213363391578010288128 * bit237)
|
||||
limit = limit + (324518553658426726783156020576256 * bit238)
|
||||
limit = limit + (649037107316853453566312041152512 * bit239)
|
||||
limit = limit + (1298074214633706907132624082305024 * bit240)
|
||||
limit = limit + (2596148429267413814265248164610048 * bit241)
|
||||
limit = limit + (5192296858534827628530496329220096 * bit242)
|
||||
limit = limit + (10384593717069655257060992658440192 * bit243)
|
||||
limit = limit + (20769187434139310514121985316880384 * bit244)
|
||||
limit = limit + (41538374868278621028243970633760768 * bit245)
|
||||
limit = limit + (83076749736557242056487941267521536 * bit246)
|
||||
limit = limit + (166153499473114484112975882535043072 * bit247)
|
||||
limit = limit + (332306998946228968225951765070086144 * bit248)
|
||||
limit = limit + (664613997892457936451903530140172288 * bit249)
|
||||
return amount, sourceToken, targetToken, limit
|
|
@ -1,2 +0,0 @@
|
|||
def main() -> (field, field, field, field):
|
||||
return 0, 0, 0, 0
|
|
@ -1,3 +0,0 @@
|
|||
def main(field utxoAmount, field volume) -> (field):
|
||||
field partial = if volume * (volume - utxoAmount) == 0 then 0 else 1 fi
|
||||
return partial
|
|
@ -1,10 +0,0 @@
|
|||
def main(field sourceTokenPrice, field targetTokenPrice, field limit) -> (field):
|
||||
// Assuming limit is in sourceToken->targetToken and price_i in token_i->refToken
|
||||
// Because of arbitrage freeness the following statement should hold:
|
||||
// sourceToken->targetToken = sourceToken->refToken * refToken->targetToken = refToken->targetToken / refToken->sourceToken
|
||||
// Therefore we have to check that:
|
||||
// `limit <= sourceToken->refToken / targetToken->refToken`
|
||||
// which is equivalent to checking
|
||||
// `limit * targetToken->refToken <= sourceToken->refToken`
|
||||
field limitIsLessOrEqual = if sourceTokenPrice * 1000000000000000000 < (limit * targetTokenPrice) then 0 else 1 fi
|
||||
return limitIsLessOrEqual
|
|
@ -1,6 +0,0 @@
|
|||
def main(field number) -> (field, field):
|
||||
field bitModuloN = number / 2
|
||||
// If number was even, bitModuloN < number
|
||||
field bit = if number < bitModuloN then 1 else 0 fi
|
||||
field remainder = if bit == 0 then number / 2 else (number - 1) / 2 fi
|
||||
return bit, remainder
|
|
@ -1,99 +0,0 @@
|
|||
import "./decodeOrder"
|
||||
import "./limitLessThanPrice"
|
||||
|
||||
def tupleForTokensWithValue(field value) -> (field[3]):
|
||||
return [value, value, value]
|
||||
|
||||
def tupleForTokenPairsWithValue(field value) -> (field[9]):
|
||||
return [value, value, value, value, value, value, value, value, value]
|
||||
|
||||
def findPairInTokenPairList(field[9] pairs, field sourceToken, field targetToken) -> (field):
|
||||
return pairs[sourceToken * 3 + targetToken]
|
||||
|
||||
// add `volume` to element `token` in `volumeToken`
|
||||
def addVolumesForOrder(field[3] volumeToken, field token, field volume) -> (field[3]):
|
||||
for field i in 0..3 do
|
||||
volumeToken[i] = volumeToken[i] + if token == i then volume else 0 fi
|
||||
endfor
|
||||
return volumeToken
|
||||
|
||||
def updateHighestTouchedOrder(field[9] highestTouchedOrder, field sourceToken, field targetToken, field limit, field volume) -> (field[9]):
|
||||
|
||||
field highest = findPairInTokenPairList(highestTouchedOrder, sourceToken, targetToken)
|
||||
|
||||
field shouldUpdate = if 0 < volume then 1 else 0 fi
|
||||
shouldUpdate = if highest < limit then shouldUpdate else 0 fi
|
||||
|
||||
highestTouchedOrder[sourceToken * 3 + targetToken] = if shouldUpdate == 1 then limit else highestTouchedOrder[sourceToken * 3 + targetToken] fi
|
||||
|
||||
return highestTouchedOrder
|
||||
|
||||
def verifyCompletelyFulfilledIfLimitLowerHighestTouchedOrder(field[9] highestTouchedOrder, field sourceAmount, field sourceToken, field targetToken, field limit, field volume) -> (field):
|
||||
|
||||
field highest = findPairInTokenPairList(highestTouchedOrder, sourceToken, targetToken)
|
||||
|
||||
field valid = if limit < highest then 1 - (sourceAmount - volume) else 1 fi
|
||||
return valid
|
||||
|
||||
def checkConstraints(field[3] amount, field[3] sourceToken, field[3] targetToken, field[3] limit, field[3] volume, field[3] priceToken) -> (field):
|
||||
// volumes are not larger than in original offer
|
||||
for field i in 0..3 do
|
||||
1 == if amount[i] < volume[i] then 0 else 1 fi
|
||||
endfor
|
||||
|
||||
field[3] sourceTokenPriceOrder = [0, 0, 0]
|
||||
field[3] targetTokenPriceOrder = [0, 0, 0]
|
||||
|
||||
for field i in 0..3 do
|
||||
sourceTokenPriceOrder[i] = priceToken[sourceToken[i]]
|
||||
targetTokenPriceOrder[i] = priceToken[targetToken[i]]
|
||||
endfor
|
||||
|
||||
// orders are only touched if the limit price is below the calculated price:
|
||||
for field i in 0..3 do
|
||||
1 == if volume[i] == 0 then 1 else limitLessThanPrice(sourceTokenPriceOrder[i], targetTokenPriceOrder[i], limit[i]) fi
|
||||
endfor
|
||||
|
||||
// the amount of sell volume for a token equals its buy volume:
|
||||
field[3] buyVolumeToken = tupleForTokensWithValue(0)
|
||||
field[3] sellVolumeToken = tupleForTokensWithValue(0)
|
||||
|
||||
for field i in 0..3 do
|
||||
buyVolumeToken = addVolumesForOrder(buyVolumeToken, targetToken[i], volume[i] * sourceTokenPriceOrder[i])
|
||||
sellVolumeToken = addVolumesForOrder(sellVolumeToken, sourceToken[i], volume[i] * sourceTokenPriceOrder[i])
|
||||
endfor
|
||||
|
||||
buyVolumeToken == sellVolumeToken
|
||||
|
||||
// If an order σ ∈ Oi→j with a limit price p has a positive trading volume, then every order in Oi→j with a lower limit price should be completely fulfilled.
|
||||
field[9] highestTouchedOrder = tupleForTokenPairsWithValue(0)
|
||||
|
||||
for field i in 0..3 do
|
||||
highestTouchedOrder = updateHighestTouchedOrder(highestTouchedOrder, sourceToken[i], targetToken[i], limit[i], volume[i])
|
||||
endfor
|
||||
|
||||
for field i in 0..3 do
|
||||
1 == verifyCompletelyFulfilledIfLimitLowerHighestTouchedOrder(highestTouchedOrder, amount[i], sourceToken[i], targetToken[i], limit[i], volume[i])
|
||||
endfor
|
||||
|
||||
return 1 // Could return the total volume to maximize for
|
||||
|
||||
def main(private field[3] encodedOrder, private field[3] bitmapOrder, private field[3] volume, private field[3] priceToken) -> (field):
|
||||
// Remove orders that are not double signed
|
||||
encodedOrder = [if bitmapOrder[0] == 1 then encodedOrder[0] else 0 fi, if bitmapOrder[1] == 1 then encodedOrder[1] else 0 fi, if bitmapOrder[2] == 1 then encodedOrder[2] else 0 fi]
|
||||
|
||||
field[3] amount = [0, 0, 0]
|
||||
field[3] sourceToken = [0, 0, 0]
|
||||
field[3] targetToken = [0, 0, 0]
|
||||
field[3] limit = [0, 0, 0]
|
||||
|
||||
// Decode orders
|
||||
for field i in 0..3 do
|
||||
field a, field s, field t, field l = decodeOrder(encodedOrder[i])
|
||||
amount[i] = a
|
||||
sourceToken[i] = s
|
||||
targetToken[i] = t
|
||||
limit[i] = l
|
||||
endfor
|
||||
|
||||
return checkConstraints(amount, sourceToken, targetToken, limit, volume, priceToken)
|
4
zokrates_cli/examples/pragma.zok
Normal file
4
zokrates_cli/examples/pragma.zok
Normal file
|
@ -0,0 +1,4 @@
|
|||
#pragma curve bls12_381
|
||||
|
||||
def main() -> ():
|
||||
return
|
|
@ -1,3 +1,5 @@
|
|||
#pragma curve bn128
|
||||
|
||||
// we can compare numbers up to 2^(pbits - 2) - 1, ie any number which fits in (pbits - 2) bits
|
||||
// It should not work for the maxvalue = 2^(pbits - 2) - 1 augmented by one
|
||||
// /!\ should be called with a = 0
|
||||
|
|
|
@ -1,3 +1,5 @@
|
|||
#pragma curve bn128
|
||||
|
||||
// we can compare numbers up to 2^(pbits - 2) - 1, ie any number which fits in (pbits - 2) bits
|
||||
// lt should work for the maxvalue = 2^(pbits - 2) - 1
|
||||
|
||||
|
|
|
@ -4,6 +4,10 @@
|
|||
// @author Dennis Kuhnert <dennis.kuhnert@campus.tu-berlin.de>
|
||||
// @date 2017
|
||||
|
||||
mod constants;
|
||||
|
||||
use constants::*;
|
||||
|
||||
use bincode::{serialize_into, Infinite};
|
||||
use clap::{App, AppSettings, Arg, ArgMatches, SubCommand};
|
||||
use serde_json::{from_reader, to_writer_pretty, Value};
|
||||
|
@ -21,12 +25,6 @@ use zokrates_core::typed_absy::{types::Signature, Type};
|
|||
use zokrates_field::{Bls12Field, Bn128Field, Field};
|
||||
use zokrates_fs_resolver::FileSystemResolver;
|
||||
|
||||
const CURVES: &[&str] = &["bn128", "bls12_381"];
|
||||
#[cfg(feature = "libsnark")]
|
||||
const SCHEMES: &[&str] = &["g16", "pghr13", "gm17"];
|
||||
#[cfg(not(feature = "libsnark"))]
|
||||
const SCHEMES: &[&str] = &["g16"];
|
||||
|
||||
fn main() {
|
||||
cli().unwrap_or_else(|e| {
|
||||
println!("{}", e);
|
||||
|
@ -354,8 +352,8 @@ fn cli() -> Result<(), String> {
|
|||
const VERIFICATION_CONTRACT_DEFAULT_PATH: &str = "verifier.sol";
|
||||
const WITNESS_DEFAULT_PATH: &str = "witness";
|
||||
const JSON_PROOF_PATH: &str = "proof.json";
|
||||
let default_curve = env::var("ZOKRATES_CURVE").unwrap_or(String::from("bn128"));
|
||||
let default_scheme = env::var("ZOKRATES_PROVING_SCHEME").unwrap_or(String::from("g16"));
|
||||
let default_curve = env::var("ZOKRATES_CURVE").unwrap_or(constants::BN128.into());
|
||||
let default_scheme = env::var("ZOKRATES_PROVING_SCHEME").unwrap_or(constants::G16.into());
|
||||
let default_solidity_abi = "v1";
|
||||
|
||||
// cli specification using clap library
|
||||
|
@ -609,8 +607,8 @@ fn cli() -> Result<(), String> {
|
|||
let curve = sub_matches.value_of("curve").unwrap();
|
||||
|
||||
match curve {
|
||||
"bn128" => cli_compile::<Bn128Field>(sub_matches)?,
|
||||
"bls12_381" => cli_compile::<Bls12Field>(sub_matches)?,
|
||||
constants::BN128 => cli_compile::<Bn128Field>(sub_matches)?,
|
||||
constants::BLS12_381 => cli_compile::<Bls12Field>(sub_matches)?,
|
||||
_ => unreachable!(),
|
||||
}
|
||||
}
|
||||
|
@ -622,7 +620,9 @@ fn cli() -> Result<(), String> {
|
|||
|
||||
let mut reader = BufReader::new(file);
|
||||
|
||||
match ProgEnum::deserialize(&mut reader).map_err(|_| "wrong file".to_string())? {
|
||||
match ProgEnum::deserialize(&mut reader)
|
||||
.map_err(|_| "Failed to deserialize".to_string())?
|
||||
{
|
||||
ProgEnum::Bn128Program(p) => cli_compute(p, sub_matches)?,
|
||||
ProgEnum::Bls12Program(p) => cli_compute(p, sub_matches)?,
|
||||
}
|
||||
|
@ -637,20 +637,21 @@ fn cli() -> Result<(), String> {
|
|||
|
||||
let mut reader = BufReader::new(file);
|
||||
|
||||
let prog = ProgEnum::deserialize(&mut reader).map_err(|_| "wrong file".to_string())?;
|
||||
let prog = ProgEnum::deserialize(&mut reader)
|
||||
.map_err(|_| "Failed to deserialize".to_string())?;
|
||||
|
||||
match proof_system {
|
||||
"g16" => match prog {
|
||||
constants::G16 => match prog {
|
||||
ProgEnum::Bn128Program(p) => cli_setup::<_, G16>(p, sub_matches)?,
|
||||
ProgEnum::Bls12Program(p) => cli_setup::<_, G16>(p, sub_matches)?,
|
||||
},
|
||||
"pghr13" => match prog {
|
||||
#[cfg(feature = "libsnark")]
|
||||
#[cfg(feature = "libsnark")]
|
||||
constants::PGHR13 => match prog {
|
||||
ProgEnum::Bn128Program(p) => cli_setup::<_, PGHR13>(p, sub_matches)?,
|
||||
_ => unimplemented!(),
|
||||
},
|
||||
"gm17" => match prog {
|
||||
#[cfg(feature = "libsnark")]
|
||||
#[cfg(feature = "libsnark")]
|
||||
constants::GM17 => match prog {
|
||||
ProgEnum::Bn128Program(p) => cli_setup::<_, GM17>(p, sub_matches)?,
|
||||
_ => unimplemented!(),
|
||||
},
|
||||
|
@ -662,19 +663,19 @@ fn cli() -> Result<(), String> {
|
|||
let proof_system = sub_matches.value_of("proving-scheme").unwrap();
|
||||
|
||||
match proof_system {
|
||||
"g16" => match curve {
|
||||
"bn128" => cli_export_verifier::<Bn128Field, G16>(sub_matches)?,
|
||||
"bls12_381" => cli_export_verifier::<Bls12Field, G16>(sub_matches)?,
|
||||
constants::G16 => match curve {
|
||||
constants::BN128 => cli_export_verifier::<Bn128Field, G16>(sub_matches)?,
|
||||
constants::BLS12_381 => cli_export_verifier::<Bls12Field, G16>(sub_matches)?,
|
||||
_ => unimplemented!(),
|
||||
},
|
||||
"pghr13" => match curve {
|
||||
#[cfg(feature = "libsnark")]
|
||||
"bn128" => cli_export_verifier::<Bn128Field, PGHR13>(sub_matches)?,
|
||||
#[cfg(feature = "libsnark")]
|
||||
constants::PGHR13 => match curve {
|
||||
constants::BN128 => cli_export_verifier::<Bn128Field, PGHR13>(sub_matches)?,
|
||||
_ => unimplemented!(),
|
||||
},
|
||||
"gm17" => match curve {
|
||||
#[cfg(feature = "libsnark")]
|
||||
"bn128" => cli_export_verifier::<Bn128Field, GM17>(sub_matches)?,
|
||||
#[cfg(feature = "libsnark")]
|
||||
constants::GM17 => match curve {
|
||||
constants::BN128 => cli_export_verifier::<Bn128Field, GM17>(sub_matches)?,
|
||||
_ => unimplemented!(),
|
||||
},
|
||||
_ => unreachable!(),
|
||||
|
@ -692,17 +693,17 @@ fn cli() -> Result<(), String> {
|
|||
let prog = ProgEnum::deserialize(&mut reader).map_err(|_| "wrong file".to_string())?;
|
||||
|
||||
match proof_system {
|
||||
"g16" => match prog {
|
||||
constants::G16 => match prog {
|
||||
ProgEnum::Bn128Program(p) => cli_generate_proof::<_, G16>(p, sub_matches)?,
|
||||
ProgEnum::Bls12Program(p) => cli_generate_proof::<_, G16>(p, sub_matches)?,
|
||||
},
|
||||
"pghr13" => match prog {
|
||||
#[cfg(feature = "libsnark")]
|
||||
#[cfg(feature = "libsnark")]
|
||||
constants::PGHR13 => match prog {
|
||||
ProgEnum::Bn128Program(p) => cli_generate_proof::<_, PGHR13>(p, sub_matches)?,
|
||||
_ => unimplemented!(),
|
||||
},
|
||||
"gm17" => match prog {
|
||||
#[cfg(feature = "libsnark")]
|
||||
#[cfg(feature = "libsnark")]
|
||||
constants::GM17 => match prog {
|
||||
ProgEnum::Bn128Program(p) => cli_generate_proof::<_, GM17>(p, sub_matches)?,
|
||||
_ => unimplemented!(),
|
||||
},
|
||||
|
|
13
zokrates_cli/src/constants.rs
Normal file
13
zokrates_cli/src/constants.rs
Normal file
|
@ -0,0 +1,13 @@
|
|||
pub const BN128: &str = "bn128";
|
||||
pub const BLS12_381: &str = "bls12_381";
|
||||
pub const CURVES: &[&str] = &[BN128, BLS12_381];
|
||||
|
||||
pub const G16: &str = "g16";
|
||||
#[cfg(feature = "libsnark")]
|
||||
pub const PGHR13: &str = "pghr13";
|
||||
#[cfg(feature = "libsnark")]
|
||||
pub const GM17: &str = "gm17";
|
||||
#[cfg(feature = "libsnark")]
|
||||
pub const SCHEMES: &[&str] = &[G16, PGHR13, GM17];
|
||||
#[cfg(not(feature = "libsnark"))]
|
||||
pub const SCHEMES: &[&str] = &[G16];
|
|
@ -7,6 +7,8 @@ use absy::{Module, ModuleId, Program};
|
|||
use flatten::Flattener;
|
||||
use imports::{self, Importer};
|
||||
use ir;
|
||||
use macros;
|
||||
use macros::process_macros;
|
||||
use optimizer::Optimize;
|
||||
use semantics::{self, Checker};
|
||||
use static_analysis::Analyse;
|
||||
|
@ -49,6 +51,7 @@ impl From<CompileError> for CompileErrors {
|
|||
pub enum CompileErrorInner {
|
||||
ParserError(pest::Error),
|
||||
ImportError(imports::Error),
|
||||
MacroError(macros::Error),
|
||||
SemanticError(semantics::ErrorInner),
|
||||
ReadError(io::Error),
|
||||
}
|
||||
|
@ -110,6 +113,12 @@ impl From<io::Error> for CompileErrorInner {
|
|||
}
|
||||
}
|
||||
|
||||
impl From<macros::Error> for CompileErrorInner {
|
||||
fn from(error: macros::Error) -> Self {
|
||||
CompileErrorInner::MacroError(error)
|
||||
}
|
||||
}
|
||||
|
||||
impl From<semantics::Error> for CompileError {
|
||||
fn from(error: semantics::Error) -> Self {
|
||||
CompileError {
|
||||
|
@ -123,6 +132,7 @@ impl fmt::Display for CompileErrorInner {
|
|||
fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
|
||||
match *self {
|
||||
CompileErrorInner::ParserError(ref e) => write!(f, "{}", e),
|
||||
CompileErrorInner::MacroError(ref e) => write!(f, "{}", e),
|
||||
CompileErrorInner::SemanticError(ref e) => write!(f, "{}", e),
|
||||
CompileErrorInner::ReadError(ref e) => write!(f, "{}", e),
|
||||
CompileErrorInner::ImportError(ref e) => write!(f, "{}", e),
|
||||
|
@ -200,6 +210,10 @@ pub fn compile_module<'ast, T: Field, E: Into<imports::Error>>(
|
|||
) -> Result<Module<'ast, T>, CompileErrors> {
|
||||
let ast = pest::generate_ast(&source)
|
||||
.map_err(|e| CompileErrors::from(CompileErrorInner::from(e).in_file(&location)))?;
|
||||
|
||||
let ast = process_macros::<T>(ast)
|
||||
.map_err(|e| CompileErrors::from(CompileErrorInner::from(e).in_file(&location)))?;
|
||||
|
||||
let module_without_imports: Module<T> = Module::from(ast);
|
||||
|
||||
Importer::new().apply_imports(
|
||||
|
|
|
@ -22,6 +22,7 @@ extern crate zokrates_pest_ast;
|
|||
mod embed;
|
||||
mod flatten;
|
||||
pub mod imports;
|
||||
mod macros;
|
||||
mod optimizer;
|
||||
mod parser;
|
||||
mod semantics;
|
||||
|
|
36
zokrates_core/src/macros.rs
Normal file
36
zokrates_core/src/macros.rs
Normal file
|
@ -0,0 +1,36 @@
|
|||
use std::fmt;
|
||||
use zokrates_field::Field;
|
||||
use zokrates_pest_ast::File;
|
||||
|
||||
#[derive(Debug)]
|
||||
pub enum Error {
|
||||
Curve(String, String),
|
||||
}
|
||||
|
||||
impl fmt::Display for Error {
|
||||
fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
|
||||
match self {
|
||||
Error::Curve(expected, found) => write!(
|
||||
f,
|
||||
"When processing macros: curve `{}` is incompatible with curve `{}`",
|
||||
found, expected
|
||||
),
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
pub fn process_macros<'ast, T: Field>(file: File<'ast>) -> Result<File<'ast>, Error> {
|
||||
match &file.pragma {
|
||||
Some(pragma) => {
|
||||
if T::name() != pragma.curve.name {
|
||||
Err(Error::Curve(
|
||||
T::name().to_string(),
|
||||
pragma.curve.name.clone(),
|
||||
))
|
||||
} else {
|
||||
Ok(file)
|
||||
}
|
||||
}
|
||||
None => Ok(file),
|
||||
}
|
||||
}
|
|
@ -1,10 +1,7 @@
|
|||
{
|
||||
"entry_point": "./tests/tests/spread_slice.zok",
|
||||
<<<<<<< HEAD
|
||||
"curves": ["Bn128", "Bls12"],
|
||||
=======
|
||||
"max_constraint_count": 9,
|
||||
>>>>>>> develop
|
||||
"tests": [
|
||||
{
|
||||
"input": {
|
||||
|
|
|
@ -2,5 +2,6 @@ use bellman_ce::pairing::bls12_381::Bls12;
|
|||
|
||||
prime_field!(
|
||||
b"52435875175126190479447740508185965837690552500527637822603658699938581184513",
|
||||
Bls12
|
||||
Bls12,
|
||||
"bls12_381"
|
||||
);
|
||||
|
|
|
@ -2,7 +2,8 @@ use bellman_ce::pairing::bn256::Bn256;
|
|||
|
||||
prime_field!(
|
||||
b"21888242871839275222246405745257275088548364400416034343698204186575808495617",
|
||||
Bn256
|
||||
Bn256,
|
||||
"bn128"
|
||||
);
|
||||
|
||||
#[cfg(test)]
|
||||
|
|
|
@ -83,12 +83,14 @@ pub trait Field:
|
|||
fn to_compact_dec_string(&self) -> String;
|
||||
/// Returns the size of the field as a decimal string
|
||||
fn id() -> [u8; 4];
|
||||
/// the name of the curve associated with this field
|
||||
fn name() -> &'static str;
|
||||
}
|
||||
|
||||
#[macro_use]
|
||||
mod prime_field {
|
||||
macro_rules! prime_field {
|
||||
($modulus:expr, $bellman_type:ty) => {
|
||||
($modulus:expr, $bellman_type:ty, $name:expr) => {
|
||||
use crate::{Field, Pow};
|
||||
use lazy_static::lazy_static;
|
||||
use num_bigint::{BigInt, BigUint, Sign, ToBigInt};
|
||||
|
@ -177,6 +179,10 @@ mod prime_field {
|
|||
}
|
||||
res
|
||||
}
|
||||
|
||||
fn name() -> &'static str {
|
||||
$name
|
||||
}
|
||||
}
|
||||
|
||||
impl Default for FieldPrime {
|
||||
|
|
|
@ -3,7 +3,10 @@
|
|||
* Author: Jacob Eberhardt, Thibaut Schaeffer
|
||||
*/
|
||||
|
||||
file = { SOI ~ NEWLINE* ~ import_directive* ~ NEWLINE* ~ ty_struct_definition* ~ NEWLINE* ~ function_definition* ~ EOI }
|
||||
file = { SOI ~ NEWLINE* ~ pragma? ~ NEWLINE* ~ import_directive* ~ NEWLINE* ~ ty_struct_definition* ~ NEWLINE* ~ function_definition* ~ EOI }
|
||||
|
||||
pragma = { "#pragma" ~ "curve" ~ curve }
|
||||
curve = @{ (ASCII_ALPHANUMERIC | "_") * }
|
||||
|
||||
import_directive = { main_import_directive | from_import_directive }
|
||||
from_import_directive = { "from" ~ "\"" ~ import_source ~ "\"" ~ "import" ~ identifier ~ ("as" ~ identifier)? ~ NEWLINE*}
|
||||
|
|
|
@ -158,6 +158,7 @@ mod ast {
|
|||
#[derive(Debug, FromPest, PartialEq, Clone)]
|
||||
#[pest_ast(rule(Rule::file))]
|
||||
pub struct File<'ast> {
|
||||
pub pragma: Option<Pragma<'ast>>,
|
||||
pub imports: Vec<ImportDirective<'ast>>,
|
||||
pub structs: Vec<StructDefinition<'ast>>,
|
||||
pub functions: Vec<Function<'ast>>,
|
||||
|
@ -166,6 +167,23 @@ mod ast {
|
|||
pub span: Span<'ast>,
|
||||
}
|
||||
|
||||
#[derive(Debug, FromPest, PartialEq, Clone)]
|
||||
#[pest_ast(rule(Rule::pragma))]
|
||||
pub struct Pragma<'ast> {
|
||||
pub curve: Curve<'ast>,
|
||||
#[pest_ast(outer())]
|
||||
pub span: Span<'ast>,
|
||||
}
|
||||
|
||||
#[derive(Debug, FromPest, PartialEq, Clone)]
|
||||
#[pest_ast(rule(Rule::curve))]
|
||||
pub struct Curve<'ast> {
|
||||
#[pest_ast(outer(with(span_into_str)))]
|
||||
pub name: String,
|
||||
#[pest_ast(outer())]
|
||||
pub span: Span<'ast>,
|
||||
}
|
||||
|
||||
#[derive(Debug, FromPest, PartialEq, Clone)]
|
||||
#[pest_ast(rule(Rule::ty_struct_definition))]
|
||||
pub struct StructDefinition<'ast> {
|
||||
|
|
|
@ -1,3 +1,5 @@
|
|||
#pragma curve bn128
|
||||
|
||||
// Parameters are based on: https://github.com/HarryR/ethsnarks/tree/9cdf0117c2e42c691e75b98979cb29b099eca998/src/jubjub
|
||||
// Note: parameters will be updated soon to be more compatible with zCash's implementation
|
||||
|
||||
|
|
|
@ -1,3 +1,5 @@
|
|||
#pragma curve bn128
|
||||
|
||||
// Non-strict version:
|
||||
// Note that this does not strongly enforce that the commitment is
|
||||
// in the field.
|
||||
|
|
|
@ -1,3 +1,5 @@
|
|||
#pragma curve bn128
|
||||
|
||||
import "EMBED/unpack" as unpack
|
||||
|
||||
def main(field i) -> (field[128]):
|
||||
|
|
Loading…
Reference in a new issue