1

I'm trying to understand why this smart contract appears different compared to the majority that I've seen when viewing the code section of the smart contract on tzkt.io. I assume the smart contract has to do with tezos profiles? So to illustrate what I mean, I've included the code section of two smart contracts below. The first one is the one that appears different. Mainly because on the code line, you'll notice it starts with:

code { { { DUP ; CAR ; DIP { CDR } } } ;

While the majority of other contracts that I have seen, the code line start with:

code { UNPAIR ;

I've included the full code below for reference. If anyone could help me figure this out, it would be greatly appreciated.

First example (the one that's different compared to most I've seen)

parameter (pair (list (pair (pair string bytes) string)) bool);
storage (pair (pair (set %claims (pair (pair string bytes) string)) (string %contract_type))
              (pair (big_map %metadata string bytes) (address %owner)));
code { { { DUP ; CAR ; DIP { CDR } } } ;
       SWAP ;
       DUP ;
       DUG 2 ;
       CDR ;
       CDR ;
       SENDER ;
       COMPARE ;
       NEQ ;
       IF { PUSH string "Unauthorized." ; FAILWITH } {} ;
       PUSH mutez 0 ;
       AMOUNT ;
       COMPARE ;
       GT ;
       IF { PUSH string "Tez not accepted." ; FAILWITH } {} ;
       { { DUP ; CAR ; DIP { CDR } } } ;
       { DIP 2 { DUP } ; DIG 3 } ;
       CDR ;
       CDR ;
       { DIP 3 { DUP } ; DIG 4 } ;
       CDR ;
       CAR ;
       PAIR ;
       { DIP 3 { DUP } ; DIG 4 } ;
       CAR ;
       CDR ;
       DIG 4 ;
       CAR ;
       CAR ;
       DIG 3 ;
       ITER { SWAP ; { DIP 4 { DUP } ; DIG 5 } ; DIG 2 ; UPDATE } ;
       DIG 3 ;
       DROP ;
       PAIR ;
       PAIR ;
       NIL operation ;
       PAIR }

Here is the second example (this one is how the majority of the contracts look)

parameter (pair (list (pair (pair string bytes) string)) bool);
storage (pair (pair (set %claims (pair (pair string bytes) string)) (string %contract_type))
              (pair (big_map %metadata string bytes) (address %owner)));
code { UNPAIR ;
       SWAP ;
       DUP ;
       DUG 2 ;
       CDR ;
       CDR ;
       SENDER ;
       COMPARE ;
       NEQ ;
       IF { PUSH string "Unauthorized." ; FAILWITH } {} ;
       PUSH mutez 0 ;
       AMOUNT ;
       COMPARE ;
       GT ;
       IF { PUSH string "Tez not accepted." ; FAILWITH } {} ;
       UNPAIR ;
       DUP 3 ;
       CDR ;
       CDR ;
       DUP 4 ;
       CDR ;
       CAR ;
       PAIR ;
       DUP 4 ;
       CAR ;
       CDR ;
       DIG 4 ;
       CAR ;
       CAR ;
       DIG 3 ;
       ITER { SWAP ; DUP 5 ; DIG 2 ; UPDATE } ;
       DIG 3 ;
       DROP ;
       PAIR ;
       PAIR ;
       NIL operation ;
       PAIR }

Again, any help with understanding the difference would be greatly appreciated, hopefully in layman's terms, considering I'm not that technical and still learning. Thank you.

1 Answer 1

1

Those examples result in the same stack. UNPAIR used to be a macro and was not supported in the JSON format of Michelson. UNPAIR was then changed to be an instruction in this commit.

The contract in example A was probably compiled a long time ago.

Example A: (Not optimized)

Initial stack :
        Pair (parameter, storage)

After (DUP):
        Pair (parameter, storage)
        Pair (parameter, storage)

After (CAR):
        Pair (parameter, storage)
        parameter

After (DIP { CDR }):
        storage
        parameter

Example B: (Optimized)

Initial stack :
        Pair (parameter, storage)

After (UNPAIR):
        storage
        parameter 

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge that you have read and understand our privacy policy and code of conduct.

Not the answer you're looking for? Browse other questions tagged or ask your own question.