@@ -908,6 +908,7 @@ patterns for doing so, refer to K's
908908``` k
909909module LIST
910910 imports private INT-SYNTAX
911+ imports private MINT-SYNTAX
911912 imports private BASIC-K
912913
913914 syntax List [hook(LIST.List)]
@@ -957,21 +958,25 @@ An element can be added to the front of a `List` using the `pushList` operator.
957958### List indexing
958959
959960You can get an element of a list by its integer offset in O(log(N)) time, or
960- effectively constant. Positive indices are 0-indexed from the beginning of the
961+ effectively constant. Positive ` Int ` indices are 0-indexed from the beginning of the
961962list, and negative indices are -1-indexed from the end of the list. In other
962- words, 0 is the first element and -1 is the last element.
963+ words, 0 is the first element and -1 is the last element. The indice can also be
964+ ` MInt ` , which is interprested as an unsigned integer, and therefore, don't support
965+ negative indices feature. Currently, only 64-bit and 256-bit ` MInt ` types are supported.
963966
964967``` k
965968 syntax KItem ::= List "[" Int "]" [function, hook(LIST.get), symbol(List:get)]
969+ syntax {Width} KItem ::= List "[" MInt{Width} "]" [function, hook(LIST.getMInt), symbol(List:getMInt)]
966970```
967971
968972### List update
969973
970974You can create a new ` List ` with a new value at a particular index in
971- O(log(N)) time, or effectively constant.
975+ O(log(N)) time, or effectively constant. The index can be either as an ` Int ` or as an ` MInt ` . Currently, only 64-bit ` MInt ` type is supported.
972976
973977``` k
974978 syntax List ::= List "[" index: Int "<-" value: KItem "]" [function, hook(LIST.update), symbol(List:set)]
979+ syntax {Width} List ::= List "[" index: MInt{Width} "<-" value: KItem "]" [function, hook(LIST.updateMInt), symbol(List:setMInt)]
975980```
976981
977982### List of identical elements
@@ -1023,10 +1028,16 @@ comparisons, it is much better to first convert to a set using `List2Set`.
10231028
10241029### List size
10251030
1026- You can get the number of elements of a list in O(1) time.
1031+ You can get the number of elements of a list in O(1) time. The output
1032+ size can be either as an ` Int ` or as an ` MInt ` . Currently, only 64-bit
1033+ and 256-bit ` MInt ` types are supported. When using ` MInt ` , the size is
1034+ interpreted as an unsigned integer, and the size of the list must match
1035+ the bounds of this ` MInt ` type, that is the size can't be larger than
1036+ ` 2^64 - 1 ` for ` MInt{64} ` and ` 2^256 - 1 ` for ` MInt{256} ` .
10271037
10281038``` k
10291039 syntax Int ::= size(List) [function, total, hook(LIST.size), symbol(sizeList), smtlib(smt_seq_len)]
1040+ syntax {Width} MInt{Width} ::= size(List) [function, hook(LIST.sizeMInt), symbol(sizeMInt)]
10301041```
10311042
10321043``` k
@@ -2010,6 +2021,7 @@ endmodule
20102021module BYTES-HOOKED
20112022 imports STRING-SYNTAX
20122023 imports BYTES-SYNTAX
2024+ imports MINT-SYNTAX
20132025 imports BYTES-STRING-ENCODE
20142026```
20152027
@@ -2085,22 +2097,25 @@ mutations of the input or output value.
20852097
20862098### Bytes update
20872099
2088- You can set the value of a particular byte in a ` Bytes ` object in O(1) time.
2089- The result is ` #False ` if ` value ` is not in the range [ 0..255] or if ` index `
2090- is not a valid index (ie, less than zero or greater than or equal to the length
2091- of the ` Bytes ` term).
2100+ You can set the value of a particular byte in a ` Bytes ` object in O(1) time,
2101+ either with index and value as ` Int ` or as an ` MInt ` . Currently, only 64-bit
2102+ and 256-bit ` MInt ` types are supported. The result is ` #False ` if ` value ` is
2103+ not in the range [ 0..255] or if ` index ` is not a valid index (ie, less than
2104+ zero or greater than or equal to the length of the ` Bytes ` term).
20922105
20932106``` k
20942107 syntax Bytes ::= Bytes "[" index: Int "<-" value: Int "]" [function, hook(BYTES.update)]
2108+ syntax {Width} Bytes ::= Bytes "[" index: MInt{Width} "<-" value: MInt{Width} "]" [function, hook(BYTES.updateMInt)]
20952109```
20962110
20972111### Bytes lookup
20982112
2099- You can get the value of a particular byte in a ` Bytes ` object in O(1) time.
2113+ You can get the value of a particular byte in a ` Bytes ` object in O(1) time, either as an ` Int ` or as an ` MInt ` . Currently, only 64-bit and 256-bit ` MInt ` types are supported .
21002114The result is ` #False ` if ` index ` is not a valid index (see above).
21012115
21022116``` k
21032117 syntax Int ::= Bytes "[" Int "]" [function, hook(BYTES.get)]
2118+ syntax {Width} MInt{Width} ::= Bytes "[" MInt{Width} "]" [function, hook(BYTES.getMInt)]
21042119```
21052120
21062121### Bytes substring
@@ -2109,9 +2124,12 @@ You can get a new `Bytes` object containing a range of bytes from the input
21092124` Bytes ` in O(N) time (where N is the length of the substring). The range
21102125of bytes included is ` [startIndex..endIndex) ` . The resulting ` Bytes ` is
21112126a copy and mutations to it do not affect mutations to the original ` Bytes ` .
2127+ Both ` startIndex ` and ` endIndex ` can be either ` Int ` or ` MInt ` values, but,
2128+ currently, only 64-bit and 256-bit ` MInt ` types are supported.
21122129
21132130``` k
21142131 syntax Bytes ::= substrBytes(Bytes, startIndex: Int, endIndex: Int) [function, hook(BYTES.substr)]
2132+ syntax {Width} Bytes ::= substrBytes(Bytes, startIndex: MInt{Width}, endIndex: MInt{Width}) [function, hook(BYTES.substrMInt)]
21152133```
21162134
21172135The function is not total: ` substrBytes(B, startIndex, endIndex) ` is ` #Bottom ` if
@@ -2125,10 +2143,13 @@ You can modify a `Bytes` to return a `Bytes` which is equal to `dest` except the
21252143` N ` elements starting at ` index ` are replaced with the contents of ` src ` in O(N)
21262144time. If ` --llvm-mutable-bytes ` is active, this will not create a new ` Bytes `
21272145object and will instead modify the original on concrete backends. The result is
2128- ` #False ` if ` index ` + ` N ` is not a valid index.
2146+ ` #False ` if ` index ` + ` N ` is not a valid index. This function accepts both
2147+ ` Int ` and ` MInt ` values for ` index ` and ` N ` . Currently, only 64-bit and
2148+ 256-bit ` MInt ` types are supported.
21292149
21302150``` k
21312151 syntax Bytes ::= replaceAtBytes(dest: Bytes, index: Int, src: Bytes) [function, hook(BYTES.replaceAt)]
2152+ syntax {Width} Bytes ::= replaceAtBytes(dest: Bytes, index: MInt{Width}, src: Bytes) [function, hook(BYTES.replaceAtMInt)]
21322153```
21332154
21342155### Multiple bytes update
@@ -2153,10 +2174,15 @@ left) with the specified `value`. If `--llvm-mutable-bytes` is active, this does
21532174not create a new ` Bytes ` object if the input is already at least ` length ` bytes
21542175long, and will instead return the input unchanged. The result is ` #False ` if
21552176` value ` is not in the range ` [0..255] ` , or if the length is negative.
2177+ We also provide a variant of this function which takes an ` MInt ` for the
2178+ ` length ` and ` value ` . The current implementation only supports 64-bit and
2179+ 256-bit ` MInt ` types.
21562180
21572181``` k
21582182 syntax Bytes ::= padRightBytes(Bytes, length: Int, value: Int) [function, hook(BYTES.padRight)]
21592183 | padLeftBytes(Bytes, length: Int, value: Int) [function, hook(BYTES.padLeft)]
2184+ syntax {Width} Bytes ::= padRightBytes(Bytes, length: MInt{Width}, value: MInt{Width}) [function, hook(BYTES.padRightMInt)]
2185+ | padLeftBytes(Bytes, length: MInt{Width}, value: MInt{Width}) [function, hook(BYTES.padLeftMInt)]
21602186```
21612187
21622188### Bytes reverse
@@ -2171,10 +2197,12 @@ original.
21712197
21722198### Bytes length
21732199
2174- You can get the length of a ` Bytes ` term in O(1) time.
2200+ You can get the length of a ` Bytes ` term in O(1) time. The lenghth can be either
2201+ an ` Int ` or an ` MInt ` . Currently, only 64-bit and 256-bit ` MInt ` types are supported.
21752202
21762203``` k
21772204 syntax Int ::= lengthBytes(Bytes) [function, total, hook(BYTES.length), smtlib(lengthBytes)]
2205+ syntax {Width} MInt{Width} ::= lengthBytes(Bytes) [function, total, hook(BYTES.lengthMInt)]
21782206```
21792207
21802208
@@ -2865,6 +2893,7 @@ endmodule
28652893module MINT
28662894 imports MINT-SYNTAX
28672895 imports private INT
2896+ imports private BYTES
28682897 imports private BOOL
28692898```
28702899
@@ -2896,6 +2925,14 @@ has the correct bitwidth, as this will influence the width of the resulting
28962925 syntax {Width} MInt{Width} ::= Int2MInt(Int) [function, total, hook(MINT.integer), smt-hook(int2bv)]
28972926```
28982927
2928+ ### Mint and Bytes conversion
2929+ You can convert from an ` MInt ` to a ` Bytes ` using the ` MInt2Bytes ` function.
2930+ Currently we only support converting ` MInt ` s of width 256 to ` Bytes ` in a Big Endian format.
2931+ ``` k
2932+ syntax {Width} Bytes ::= MInt2Bytes(MInt{Width}) [function, total, hook(MINT.MInt2bytes)]
2933+ syntax {Width} MInt{Width} ::= Bytes2MInt(Bytes) [function, total, hook(MINT.bytes2MInt)]
2934+ ```
2935+
28992936### MInt min and max values
29002937
29012938You can get the minimum and maximum values of a signed or unsigned ` MInt `
@@ -2938,6 +2975,8 @@ You can:
29382975
29392976* Compute the bitwise complement ` ~MInt ` of an ` MInt ` .
29402977* Compute the unary negation ` --MInt ` of an ` MInt ` .
2978+ * Compute the power ` ^MInt ` of two ` MInt ` s interpreted as unsigned integers.
2979+ Currently, only 64 and 256-bits is supported.
29412980* Compute the product ` *MInt ` of two ` MInt ` s.
29422981* Compute the quotient ` /sMInt ` of two ` MInt ` s interpreted as signed integers.
29432982* Compute the modulus ` %sMInt ` of two ` MInt ` s interpreted as signed integers.
@@ -2960,7 +2999,8 @@ You can:
29602999 syntax {Width} MInt{Width} ::= "~MInt" MInt{Width} [function, total, hook(MINT.not), smt-hook(bvnot)]
29613000 | "--MInt" MInt{Width} [function, total, hook(MINT.neg), smt-hook(bvuminus)]
29623001 > left:
2963- MInt{Width} "*MInt" MInt{Width} [function, total, hook(MINT.mul), smt-hook(bvmul)]
3002+ MInt{Width} "^MInt" MInt{Width} [function, total, hook(MINT.pow)]
3003+ | MInt{Width} "*MInt" MInt{Width} [function, total, hook(MINT.mul), smt-hook(bvmul)]
29643004 | MInt{Width} "/sMInt" MInt{Width} [function, hook(MINT.sdiv), smt-hook(bvsdiv)]
29653005 | MInt{Width} "%sMInt" MInt{Width} [function, hook(MINT.srem), smt-hook(bvsrem)]
29663006 | MInt{Width} "/uMInt" MInt{Width} [function, hook(MINT.udiv), smt-hook(bvudiv)]
0 commit comments