ForgeL1TxsNum*int64`meddler:"forge_l1_txs_num"`// optional, Only when the batch forges L1 txs. Identifier that corresponds to the group of L1 txs forged in the current batch.
SlotNumint64`meddler:"slot_num"`// Slot in which the batch is forged
TotalFeesUSD*float64`meddler:"total_fees_usd"`
// ForgeL1TxsNum is optional, Only when the batch forges L1 txs. Identifier that corresponds
// to the group of L1 txs forged in the current batch.
ForgeL1TxsNum*int64`meddler:"forge_l1_txs_num"`
SlotNumint64`meddler:"slot_num"`// Slot in which the batch is forged
ToForgeL1TxsNum*int64`meddler:"to_forge_l1_txs_num"`// toForgeL1TxsNum in which the tx was forged / will be forged
Positionint`meddler:"position"`
UserOriginbool`meddler:"user_origin"`// true if the tx was originated by a user, false if it was aoriginated by a coordinator. Note that this differ from the spec for implementation simplification purpposes
FromIdxIdx`meddler:"from_idx,zeroisnull"`// FromIdx is used by L1Tx/Deposit to indicate the Idx receiver of the L1Tx.DepositAmount (deposit)
TxIDTxID`meddler:"id"`
// ToForgeL1TxsNum indicates in which the tx was forged / will be forged
// Tx is a struct used by the TxSelector & BatchBuilder as a generic type generated from L1Tx & PoolL2Tx
// Tx is a struct used by the TxSelector & BatchBuilder as a generic type generated from L1Tx &
// PoolL2Tx
typeTxstruct{
// Generic
IsL1bool`meddler:"is_l1"`
TxIDTxID`meddler:"id"`
TypeTxType`meddler:"type"`
Positionint`meddler:"position"`
FromIdxIdx`meddler:"from_idx"`
ToIdxIdx`meddler:"to_idx"`
Amount*big.Int`meddler:"amount,bigint"`
AmountFloatfloat64`meddler:"amount_f"`
TokenIDTokenID`meddler:"token_id"`
USD*float64`meddler:"amount_usd"`
BatchNum*BatchNum`meddler:"batch_num"`// batchNum in which this tx was forged. If the tx is L2, this must be != 0
EthBlockNumint64`meddler:"eth_block_num"`// Ethereum Block Number in which this L1Tx was added to the queue
IsL1bool`meddler:"is_l1"`
TxIDTxID`meddler:"id"`
TypeTxType`meddler:"type"`
Positionint`meddler:"position"`
FromIdxIdx`meddler:"from_idx"`
ToIdxIdx`meddler:"to_idx"`
Amount*big.Int`meddler:"amount,bigint"`
AmountFloatfloat64`meddler:"amount_f"`
TokenIDTokenID`meddler:"token_id"`
USD*float64`meddler:"amount_usd"`
// BatchNum in which this tx was forged. If the tx is L2, this must be != 0
BatchNum*BatchNum`meddler:"batch_num"`
// Ethereum Block Number in which this L1Tx was added to the queue
EthBlockNumint64`meddler:"eth_block_num"`
// L1
ToForgeL1TxsNum*int64`meddler:"to_forge_l1_txs_num"`// toForgeL1TxsNum in which the tx was forged / will be forged
UserOrigin*bool`meddler:"user_origin"`// true if the tx was originated by a user, false if it was aoriginated by a coordinator. Note that this differ from the spec for implementation simplification purpposes
// ToForgeL1TxsNum in which the tx was forged / will be forged
proof,pubInputs,err:=batchInfo.ServerProof.GetProof(ctx)// blocking call, until not resolved don't continue. Returns when the proof server has calculated the proof
returnps,tracerr.Wrap(fmt.Errorf("Line %d: Instruction of 'Type: %s' when there is already a previous instruction 'Type: %s' defined",i,instruction.Typ,ps.typ))
returnps,
tracerr.Wrap(fmt.Errorf("Line %d: Instruction of 'Type: %s' when "+
"there is already a previous instruction 'Type: %s' defined",
i,instruction.Typ,ps.typ))
}
ifinstruction.Typ=="PoolL2"{
ps.typ=SetTypePoolL2
}elseifinstruction.Typ=="Blockchain"{
ps.typ=SetTypeBlockchain
}else{
log.Fatalf("Line %d: Invalid set type: '%s'. Valid set types: 'Blockchain', 'PoolL2'",i,instruction.Typ)
log.Fatalf("Line %d: Invalid set type: '%s'. Valid set types: "+
ifinstruction.Typ==common.TxTypeTransfer||instruction.Typ==common.TxTypeTransferToEthAddr||instruction.Typ==common.TxTypeTransferToBJJ{// type: Transfer
ifinstruction.Typ==common.TxTypeTransfer||
instruction.Typ==common.TxTypeTransferToEthAddr||
instruction.Typ==common.TxTypeTransferToBJJ{// type: Transfer
returnnil,tracerr.Wrap(fmt.Errorf("Line %d: AddToken TokenID should be sequential, expected TokenID: %d, defined TokenID: %d",inst.LineNum,tc.LastRegisteredTokenID+1,inst.TokenID))
returnnil,
tracerr.Wrap(fmt.Errorf("Line %d: AddToken TokenID should be "+
"sequential, expected TokenID: %d, defined TokenID: %d",
iftc.Users[tx.fromIdxName].Accounts[tx.L1Tx.TokenID]!=nil{// if account already exists, return error
returntracerr.Wrap(fmt.Errorf("Can not create same account twice (same User (%s) & same TokenID (%d)) (this is a design property of Til)",tx.fromIdxName,tx.L1Tx.TokenID))
returntracerr.Wrap(fmt.Errorf("Line %d: %s from User %s for TokenID %d while account not created yet",testTx.lineNum,testTx.L2Tx.Type,testTx.fromIdxName,testTx.tokenID))
returntracerr.Wrap(fmt.Errorf("Line %d: %s from User %s for TokenID %d "+
returntracerr.Wrap(fmt.Errorf("Line %d: Can not create Transfer for a non existing account. Batch %d, ToIdx name: %s, TokenID: %d",testTx.lineNum,tc.currBatchNum,testTx.toIdxName,testTx.tokenID))
returntracerr.Wrap(fmt.Errorf("Line %d: Can not create Transfer for a non "+
returntracerr.Wrap(fmt.Errorf("Can not process %s: TokenID %d not registered, last registered TokenID: %d",inst.Typ,inst.TokenID,tc.LastRegisteredTokenID))
returntracerr.Wrap(fmt.Errorf("Can not process %s: TokenID %d not registered, "+
returnnil,tracerr.Wrap(fmt.Errorf("L1UserTx + L1CoordinatorTx (%d) can not be bigger than MaxL1Tx (%d)",len(l1usertxs)+len(l1coordinatortxs),tp.config.MaxTx))
returnnil,
tracerr.Wrap(fmt.Errorf("L1UserTx + L1CoordinatorTx (%d) can not be bigger than MaxL1Tx (%d)",
returntracerr.Wrap(fmt.Errorf("Can not use CoordIdx that does not exist in the tree. TokenID: %d, CoordIdx: %d",accSender.TokenID,coordIdxsMap[accSender.TokenID]))
returntracerr.Wrap(
fmt.Errorf("Can not use CoordIdx that does not exist in the tree. TokenID: %d, CoordIdx: %d",
returnnil,false,tracerr.Wrap(fmt.Errorf("Can not use CoordIdx that does not exist in the tree. TokenID: %d, CoordIdx: %d",acc.TokenID,coordIdxsMap[acc.TokenID]))
returnnil,false,tracerr.Wrap(
fmt.Errorf("Can not use CoordIdx that does not exist in the tree. TokenID: %d, CoordIdx: %d",
log.Debugf("EffectiveAmount = 0: tx.FromEthAddr (%s) must be the same EthAddr of the sender account by the Idx (%s)",tx.FromEthAddr.Hex(),accSender.EthAddr.Hex())
log.Debugf("EffectiveAmount = 0: tx.FromEthAddr (%s) must be the same EthAddr of "+
assert.Equal(t,1,len(ptOut.ExitInfos))// 1, as previous batch was without L1UserTxs, and has pending the 'ForceExit(1) A: 5', and the 2 exit transactions get grouped under 1 ExitInfo
// 1, as previous batch was without L1UserTxs, and has pending the
// 'ForceExit(1) A: 5', and the 2 exit transactions get grouped under 1
// not found, l2Tx will not be added in the selection
returnnil,nil,nil,tracerr.Wrap(fmt.Errorf("invalid L2Tx: ToIdx not found in StateDB, neither ToEthAddr found in AccountCreationAuths L2DB. ToIdx: %d, ToEthAddr: %s",
l2Tx.ToIdx,l2Tx.ToEthAddr.Hex()))
returnnil,nil,nil,
tracerr.Wrap(fmt.Errorf("invalid L2Tx: ToIdx not found "+
"in StateDB, neither ToEthAddr found in AccountCreationAuths L2DB. ToIdx: %d, ToEthAddr: %s",
l2Tx.ToIdx,l2Tx.ToEthAddr.Hex()))
}
ifaccAuth.BJJ!=l2Tx.ToBJJ{
// if AccountCreationAuth.BJJ is not the same
// than in the tx, tx is not accepted
returnnil,nil,nil,tracerr.Wrap(fmt.Errorf("invalid L2Tx: ToIdx not found in StateDB, neither ToEthAddr & ToBJJ found in AccountCreationAuths L2DB. ToIdx: %d, ToEthAddr: %s, ToBJJ: %s",
// not found, l2Tx will not be added in the selection
returnnil,nil,nil,tracerr.Wrap(fmt.Errorf("invalid L2Tx: ToIdx not found in StateDB, neither ToEthAddr found in AccountCreationAuths L2DB. ToIdx: %d, ToEthAddr: %s",
l2Tx.ToIdx,l2Tx.ToEthAddr))
returnnil,nil,nil,
tracerr.Wrap(fmt.Errorf("invalid L2Tx: ToIdx not found in "+